From b5c56d4946732ceba26f96992809d40d4ffd203d Mon Sep 17 00:00:00 2001 From: lixinran Date: Wed, 10 Sep 2025 15:27:37 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E4=BF=AE=E5=A4=8Dmarkdown=E8=A1=A8?= =?UTF-8?q?=E6=A0=BC=E6=B8=B2=E6=9F=93=E9=97=AE=E9=A2=98=20-=20=E6=AD=A3?= =?UTF-8?q?=E7=A1=AE=E9=85=8D=E7=BD=AEMind=20Elixir=E7=9A=84markdown?= =?UTF-8?q?=E6=B8=B2=E6=9F=93=E5=99=A8=EF=BC=8C=E6=94=AF=E6=8C=81=E8=A1=A8?= =?UTF-8?q?=E6=A0=BC=E6=B8=B2=E6=9F=93=E4=B8=BAHTML=E6=A0=BC=E5=BC=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .DS_Store | Bin 6148 -> 6148 bytes backend/mindmap.db | Bin 2437120 -> 2854912 bytes frontend/debug-current-issue.html | 182 + frontend/debug-mindelixir-styles.html | 196 + frontend/debug-table-detection.html | 123 + frontend/node_modules/.bin/csv2json | 1 + frontend/node_modules/.bin/csv2tsv | 1 + frontend/node_modules/.bin/dsv2dsv | 1 + frontend/node_modules/.bin/dsv2json | 1 + frontend/node_modules/.bin/json2csv | 1 + frontend/node_modules/.bin/json2dsv | 1 + frontend/node_modules/.bin/json2tsv | 1 + frontend/node_modules/.bin/katex | 1 + frontend/node_modules/.bin/markdown-it | 1 + frontend/node_modules/.bin/tsv2csv | 1 + frontend/node_modules/.bin/tsv2json | 1 + frontend/node_modules/.bin/yaml | 1 + frontend/node_modules/.package-lock.json | 947 +- .../node_modules/.vite/deps/_metadata.json | 56 +- .../node_modules/.vite/deps/mind-elixir.js | 2501 -- .../.vite/deps/mind-elixir.js.map | 7 - frontend/node_modules/.vite/deps/prismjs.js | 1466 ++ .../node_modules/.vite/deps/prismjs.js.map | 7 + .../deps/prismjs_components_prism-css.js | 61 + .../deps/prismjs_components_prism-css.js.map | 7 + .../prismjs_components_prism-javascript.js | 142 + ...prismjs_components_prism-javascript.js.map | 7 + .../deps/prismjs_components_prism-json.js | 27 + .../deps/prismjs_components_prism-json.js.map | 7 + .../deps/prismjs_components_prism-python.js | 65 + .../prismjs_components_prism-python.js.map | 7 + .../deps/prismjs_components_prism-sql.js | 35 + .../deps/prismjs_components_prism-sql.js.map | 7 + frontend/node_modules/@babel/runtime/LICENSE | 22 + .../node_modules/@babel/runtime/README.md | 19 + .../@babel/runtime/helpers/AwaitValue.js | 4 + .../@babel/runtime/helpers/OverloadYield.js | 4 + .../helpers/applyDecoratedDescriptor.js | 9 + .../@babel/runtime/helpers/applyDecs.js | 236 + .../@babel/runtime/helpers/applyDecs2203.js | 184 + .../@babel/runtime/helpers/applyDecs2203R.js | 191 + .../@babel/runtime/helpers/applyDecs2301.js | 222 + .../@babel/runtime/helpers/applyDecs2305.js | 133 + .../@babel/runtime/helpers/applyDecs2311.js | 124 + .../runtime/helpers/arrayLikeToArray.js | 6 + .../@babel/runtime/helpers/arrayWithHoles.js | 4 + .../runtime/helpers/arrayWithoutHoles.js | 5 + .../runtime/helpers/assertClassBrand.js | 5 + .../runtime/helpers/assertThisInitialized.js | 5 + .../runtime/helpers/asyncGeneratorDelegate.js | 24 + .../@babel/runtime/helpers/asyncIterator.js | 45 + .../runtime/helpers/asyncToGenerator.js | 26 + .../runtime/helpers/awaitAsyncGenerator.js | 5 + .../@babel/runtime/helpers/callSuper.js | 7 + .../@babel/runtime/helpers/checkInRHS.js | 6 + .../helpers/checkPrivateRedeclaration.js | 4 + .../classApplyDescriptorDestructureSet.js | 10 + .../helpers/classApplyDescriptorGet.js | 4 + .../helpers/classApplyDescriptorSet.js | 7 + .../@babel/runtime/helpers/classCallCheck.js | 4 + .../helpers/classCheckPrivateStaticAccess.js | 5 + .../classCheckPrivateStaticFieldDescriptor.js | 4 + .../helpers/classExtractFieldDescriptor.js | 5 + .../runtime/helpers/classNameTDZError.js | 4 + .../classPrivateFieldDestructureSet.js | 7 + .../runtime/helpers/classPrivateFieldGet.js | 7 + .../runtime/helpers/classPrivateFieldGet2.js | 5 + .../helpers/classPrivateFieldInitSpec.js | 5 + .../helpers/classPrivateFieldLooseBase.js | 5 + .../helpers/classPrivateFieldLooseKey.js | 5 + .../runtime/helpers/classPrivateFieldSet.js | 7 + .../runtime/helpers/classPrivateFieldSet2.js | 5 + .../runtime/helpers/classPrivateGetter.js | 5 + .../runtime/helpers/classPrivateMethodGet.js | 5 + .../helpers/classPrivateMethodInitSpec.js | 5 + .../runtime/helpers/classPrivateMethodSet.js | 4 + .../runtime/helpers/classPrivateSetter.js | 5 + .../classStaticPrivateFieldDestructureSet.js | 7 + .../helpers/classStaticPrivateFieldSpecGet.js | 7 + .../helpers/classStaticPrivateFieldSpecSet.js | 7 + .../helpers/classStaticPrivateMethodGet.js | 5 + .../helpers/classStaticPrivateMethodSet.js | 4 + .../@babel/runtime/helpers/construct.js | 10 + .../@babel/runtime/helpers/createClass.js | 13 + .../helpers/createForOfIteratorHelper.js | 50 + .../helpers/createForOfIteratorHelperLoose.js | 19 + .../@babel/runtime/helpers/createSuper.js | 16 + .../@babel/runtime/helpers/decorate.js | 250 + .../@babel/runtime/helpers/defaults.js | 9 + .../@babel/runtime/helpers/defineAccessor.js | 8 + .../helpers/defineEnumerableProperties.js | 12 + .../@babel/runtime/helpers/defineProperty.js | 10 + .../@babel/runtime/helpers/dispose.js | 28 + .../@babel/runtime/helpers/esm/AwaitValue.js | 4 + .../runtime/helpers/esm/OverloadYield.js | 4 + .../helpers/esm/applyDecoratedDescriptor.js | 9 + .../@babel/runtime/helpers/esm/applyDecs.js | 236 + .../runtime/helpers/esm/applyDecs2203.js | 184 + .../runtime/helpers/esm/applyDecs2203R.js | 191 + .../runtime/helpers/esm/applyDecs2301.js | 222 + .../runtime/helpers/esm/applyDecs2305.js | 133 + .../runtime/helpers/esm/applyDecs2311.js | 124 + .../runtime/helpers/esm/arrayLikeToArray.js | 6 + .../runtime/helpers/esm/arrayWithHoles.js | 4 + .../runtime/helpers/esm/arrayWithoutHoles.js | 5 + .../runtime/helpers/esm/assertClassBrand.js | 5 + .../helpers/esm/assertThisInitialized.js | 5 + .../helpers/esm/asyncGeneratorDelegate.js | 24 + .../runtime/helpers/esm/asyncIterator.js | 45 + .../runtime/helpers/esm/asyncToGenerator.js | 26 + .../helpers/esm/awaitAsyncGenerator.js | 5 + .../@babel/runtime/helpers/esm/callSuper.js | 7 + .../@babel/runtime/helpers/esm/checkInRHS.js | 6 + .../helpers/esm/checkPrivateRedeclaration.js | 4 + .../esm/classApplyDescriptorDestructureSet.js | 10 + .../helpers/esm/classApplyDescriptorGet.js | 4 + .../helpers/esm/classApplyDescriptorSet.js | 7 + .../runtime/helpers/esm/classCallCheck.js | 4 + .../esm/classCheckPrivateStaticAccess.js | 5 + .../classCheckPrivateStaticFieldDescriptor.js | 4 + .../esm/classExtractFieldDescriptor.js | 5 + .../runtime/helpers/esm/classNameTDZError.js | 4 + .../esm/classPrivateFieldDestructureSet.js | 7 + .../helpers/esm/classPrivateFieldGet.js | 7 + .../helpers/esm/classPrivateFieldGet2.js | 5 + .../helpers/esm/classPrivateFieldInitSpec.js | 5 + .../helpers/esm/classPrivateFieldLooseBase.js | 5 + .../helpers/esm/classPrivateFieldLooseKey.js | 5 + .../helpers/esm/classPrivateFieldSet.js | 7 + .../helpers/esm/classPrivateFieldSet2.js | 5 + .../runtime/helpers/esm/classPrivateGetter.js | 5 + .../helpers/esm/classPrivateMethodGet.js | 5 + .../helpers/esm/classPrivateMethodInitSpec.js | 5 + .../helpers/esm/classPrivateMethodSet.js | 4 + .../runtime/helpers/esm/classPrivateSetter.js | 5 + .../classStaticPrivateFieldDestructureSet.js | 7 + .../esm/classStaticPrivateFieldSpecGet.js | 7 + .../esm/classStaticPrivateFieldSpecSet.js | 7 + .../esm/classStaticPrivateMethodGet.js | 5 + .../esm/classStaticPrivateMethodSet.js | 4 + .../@babel/runtime/helpers/esm/construct.js | 10 + .../@babel/runtime/helpers/esm/createClass.js | 13 + .../helpers/esm/createForOfIteratorHelper.js | 50 + .../esm/createForOfIteratorHelperLoose.js | 19 + .../@babel/runtime/helpers/esm/createSuper.js | 16 + .../@babel/runtime/helpers/esm/decorate.js | 250 + .../@babel/runtime/helpers/esm/defaults.js | 9 + .../runtime/helpers/esm/defineAccessor.js | 8 + .../helpers/esm/defineEnumerableProperties.js | 12 + .../runtime/helpers/esm/defineProperty.js | 10 + .../@babel/runtime/helpers/esm/dispose.js | 28 + .../@babel/runtime/helpers/esm/extends.js | 10 + .../@babel/runtime/helpers/esm/get.js | 11 + .../runtime/helpers/esm/getPrototypeOf.js | 6 + .../@babel/runtime/helpers/esm/identity.js | 4 + .../runtime/helpers/esm/importDeferProxy.js | 27 + .../@babel/runtime/helpers/esm/inherits.js | 14 + .../runtime/helpers/esm/inheritsLoose.js | 5 + .../helpers/esm/initializerDefineProperty.js | 9 + .../helpers/esm/initializerWarningHelper.js | 4 + .../@babel/runtime/helpers/esm/instanceof.js | 4 + .../helpers/esm/interopRequireDefault.js | 6 + .../helpers/esm/interopRequireWildcard.js | 22 + .../runtime/helpers/esm/isNativeFunction.js | 8 + .../helpers/esm/isNativeReflectConstruct.js | 9 + .../runtime/helpers/esm/iterableToArray.js | 4 + .../helpers/esm/iterableToArrayLimit.js | 28 + .../@babel/runtime/helpers/esm/jsx.js | 22 + .../runtime/helpers/esm/maybeArrayLike.js | 9 + .../runtime/helpers/esm/newArrowCheck.js | 4 + .../runtime/helpers/esm/nonIterableRest.js | 4 + .../runtime/helpers/esm/nonIterableSpread.js | 4 + .../helpers/esm/nullishReceiverError.js | 4 + .../helpers/esm/objectDestructuringEmpty.js | 4 + .../runtime/helpers/esm/objectSpread.js | 14 + .../runtime/helpers/esm/objectSpread2.js | 23 + .../helpers/esm/objectWithoutProperties.js | 13 + .../esm/objectWithoutPropertiesLoose.js | 10 + .../@babel/runtime/helpers/esm/package.json | 3 + .../helpers/esm/possibleConstructorReturn.js | 8 + .../runtime/helpers/esm/readOnlyError.js | 4 + .../@babel/runtime/helpers/esm/regenerator.js | 89 + .../runtime/helpers/esm/regeneratorAsync.js | 8 + .../helpers/esm/regeneratorAsyncGen.js | 6 + .../helpers/esm/regeneratorAsyncIterator.js | 33 + .../runtime/helpers/esm/regeneratorDefine.js | 22 + .../runtime/helpers/esm/regeneratorKeys.js | 10 + .../runtime/helpers/esm/regeneratorRuntime.js | 77 + .../runtime/helpers/esm/regeneratorValues.js | 19 + .../@babel/runtime/helpers/esm/set.js | 22 + .../runtime/helpers/esm/setFunctionName.js | 12 + .../runtime/helpers/esm/setPrototypeOf.js | 6 + .../helpers/esm/skipFirstGeneratorNext.js | 7 + .../runtime/helpers/esm/slicedToArray.js | 8 + .../runtime/helpers/esm/superPropBase.js | 6 + .../runtime/helpers/esm/superPropGet.js | 9 + .../runtime/helpers/esm/superPropSet.js | 6 + .../helpers/esm/taggedTemplateLiteral.js | 8 + .../helpers/esm/taggedTemplateLiteralLoose.js | 4 + .../@babel/runtime/helpers/esm/tdz.js | 4 + .../@babel/runtime/helpers/esm/temporalRef.js | 6 + .../runtime/helpers/esm/temporalUndefined.js | 2 + .../@babel/runtime/helpers/esm/toArray.js | 8 + .../runtime/helpers/esm/toConsumableArray.js | 8 + .../@babel/runtime/helpers/esm/toPrimitive.js | 12 + .../runtime/helpers/esm/toPropertyKey.js | 7 + .../@babel/runtime/helpers/esm/toSetter.js | 10 + .../esm/tsRewriteRelativeImportExtensions.js | 6 + .../@babel/runtime/helpers/esm/typeof.js | 10 + .../helpers/esm/unsupportedIterableToArray.js | 9 + .../@babel/runtime/helpers/esm/using.js | 12 + .../@babel/runtime/helpers/esm/usingCtx.js | 59 + .../runtime/helpers/esm/wrapAsyncGenerator.js | 69 + .../runtime/helpers/esm/wrapNativeSuper.js | 27 + .../@babel/runtime/helpers/esm/wrapRegExp.js | 52 + .../runtime/helpers/esm/writeOnlyError.js | 4 + .../@babel/runtime/helpers/extends.js | 10 + .../@babel/runtime/helpers/get.js | 11 + .../@babel/runtime/helpers/getPrototypeOf.js | 6 + .../@babel/runtime/helpers/identity.js | 4 + .../runtime/helpers/importDeferProxy.js | 27 + .../@babel/runtime/helpers/inherits.js | 14 + .../@babel/runtime/helpers/inheritsLoose.js | 5 + .../helpers/initializerDefineProperty.js | 9 + .../helpers/initializerWarningHelper.js | 4 + .../@babel/runtime/helpers/instanceof.js | 4 + .../runtime/helpers/interopRequireDefault.js | 6 + .../runtime/helpers/interopRequireWildcard.js | 22 + .../runtime/helpers/isNativeFunction.js | 8 + .../helpers/isNativeReflectConstruct.js | 9 + .../@babel/runtime/helpers/iterableToArray.js | 4 + .../runtime/helpers/iterableToArrayLimit.js | 28 + .../@babel/runtime/helpers/jsx.js | 22 + .../@babel/runtime/helpers/maybeArrayLike.js | 9 + .../@babel/runtime/helpers/newArrowCheck.js | 4 + .../@babel/runtime/helpers/nonIterableRest.js | 4 + .../runtime/helpers/nonIterableSpread.js | 4 + .../runtime/helpers/nullishReceiverError.js | 4 + .../helpers/objectDestructuringEmpty.js | 4 + .../@babel/runtime/helpers/objectSpread.js | 14 + .../@babel/runtime/helpers/objectSpread2.js | 23 + .../helpers/objectWithoutProperties.js | 13 + .../helpers/objectWithoutPropertiesLoose.js | 10 + .../helpers/possibleConstructorReturn.js | 8 + .../@babel/runtime/helpers/readOnlyError.js | 4 + .../@babel/runtime/helpers/regenerator.js | 89 + .../runtime/helpers/regeneratorAsync.js | 8 + .../runtime/helpers/regeneratorAsyncGen.js | 6 + .../helpers/regeneratorAsyncIterator.js | 33 + .../runtime/helpers/regeneratorDefine.js | 22 + .../@babel/runtime/helpers/regeneratorKeys.js | 10 + .../runtime/helpers/regeneratorRuntime.js | 77 + .../runtime/helpers/regeneratorValues.js | 19 + .../@babel/runtime/helpers/set.js | 22 + .../@babel/runtime/helpers/setFunctionName.js | 12 + .../@babel/runtime/helpers/setPrototypeOf.js | 6 + .../runtime/helpers/skipFirstGeneratorNext.js | 7 + .../@babel/runtime/helpers/slicedToArray.js | 8 + .../@babel/runtime/helpers/superPropBase.js | 6 + .../@babel/runtime/helpers/superPropGet.js | 9 + .../@babel/runtime/helpers/superPropSet.js | 6 + .../runtime/helpers/taggedTemplateLiteral.js | 8 + .../helpers/taggedTemplateLiteralLoose.js | 4 + .../@babel/runtime/helpers/tdz.js | 4 + .../@babel/runtime/helpers/temporalRef.js | 6 + .../runtime/helpers/temporalUndefined.js | 2 + .../@babel/runtime/helpers/toArray.js | 8 + .../runtime/helpers/toConsumableArray.js | 8 + .../@babel/runtime/helpers/toPrimitive.js | 12 + .../@babel/runtime/helpers/toPropertyKey.js | 7 + .../@babel/runtime/helpers/toSetter.js | 10 + .../tsRewriteRelativeImportExtensions.js | 6 + .../@babel/runtime/helpers/typeof.js | 10 + .../helpers/unsupportedIterableToArray.js | 9 + .../@babel/runtime/helpers/using.js | 12 + .../@babel/runtime/helpers/usingCtx.js | 59 + .../runtime/helpers/wrapAsyncGenerator.js | 69 + .../@babel/runtime/helpers/wrapNativeSuper.js | 27 + .../@babel/runtime/helpers/wrapRegExp.js | 52 + .../@babel/runtime/helpers/writeOnlyError.js | 4 + .../node_modules/@babel/runtime/package.json | 1107 + .../@babel/runtime/regenerator/index.js | 15 + .../node_modules/@gera2ld/jsx-dom/LICENSE | 21 + .../node_modules/@gera2ld/jsx-dom/README.md | 130 + .../@gera2ld/jsx-dom/dist/index.cjs | 169 + .../@gera2ld/jsx-dom/dist/index.js | 170 + .../@gera2ld/jsx-dom/dist/index.mjs | 159 + .../@gera2ld/jsx-dom/jsx-runtime.d.ts | 1 + .../@gera2ld/jsx-dom/jsx-runtime.js | 1 + .../@gera2ld/jsx-dom/package.json | 52 + .../@gera2ld/jsx-dom/types/consts.d.ts | 9 + .../@gera2ld/jsx-dom/types/h.d.ts | 9 + .../@gera2ld/jsx-dom/types/index.d.ts | 3 + .../@gera2ld/jsx-dom/types/mount.d.ts | 13 + .../@gera2ld/jsx-dom/types/types.d.ts | 34 + .../@vscode/markdown-it-katex/LICENSE | 65 + .../@vscode/markdown-it-katex/README.md | 121 + .../@vscode/markdown-it-katex/dist/index.js | 485 + .../@vscode/markdown-it-katex/package.json | 44 + .../@vscode/markdown-it-katex/types.d.ts | 42 + frontend/node_modules/boolbase/README.md | 10 + frontend/node_modules/boolbase/index.js | 8 + frontend/node_modules/boolbase/package.json | 23 + frontend/node_modules/cheerio-select/LICENSE | 11 + .../node_modules/cheerio-select/README.md | 18 + .../cheerio-select/lib/esm/helpers.d.ts | 5 + .../cheerio-select/lib/esm/helpers.d.ts.map | 1 + .../cheerio-select/lib/esm/helpers.js | 20 + .../cheerio-select/lib/esm/helpers.js.map | 1 + .../cheerio-select/lib/esm/index.d.ts | 12 + .../cheerio-select/lib/esm/index.d.ts.map | 1 + .../cheerio-select/lib/esm/index.js | 241 + .../cheerio-select/lib/esm/index.js.map | 1 + .../cheerio-select/lib/esm/package.json | 1 + .../cheerio-select/lib/esm/positionals.d.ts | 10 + .../lib/esm/positionals.d.ts.map | 1 + .../cheerio-select/lib/esm/positionals.js | 47 + .../cheerio-select/lib/esm/positionals.js.map | 1 + .../cheerio-select/lib/helpers.d.ts | 5 + .../cheerio-select/lib/helpers.d.ts.map | 1 + .../cheerio-select/lib/helpers.js | 26 + .../cheerio-select/lib/helpers.js.map | 1 + .../cheerio-select/lib/index.d.ts | 12 + .../cheerio-select/lib/index.d.ts.map | 1 + .../node_modules/cheerio-select/lib/index.js | 302 + .../cheerio-select/lib/index.js.map | 1 + .../cheerio-select/lib/positionals.d.ts | 10 + .../cheerio-select/lib/positionals.d.ts.map | 1 + .../cheerio-select/lib/positionals.js | 52 + .../cheerio-select/lib/positionals.js.map | 1 + .../node_modules/cheerio-select/package.json | 76 + frontend/node_modules/cheerio/LICENSE | 21 + frontend/node_modules/cheerio/Readme.md | 247 + .../cheerio/dist/browser/api/attributes.d.ts | 385 + .../dist/browser/api/attributes.d.ts.map | 1 + .../cheerio/dist/browser/api/attributes.js | 619 + .../dist/browser/api/attributes.js.map | 1 + .../cheerio/dist/browser/api/css.d.ts | 42 + .../cheerio/dist/browser/api/css.d.ts.map | 1 + .../cheerio/dist/browser/api/css.js | 116 + .../cheerio/dist/browser/api/css.js.map | 1 + .../cheerio/dist/browser/api/extract.d.ts | 29 + .../cheerio/dist/browser/api/extract.d.ts.map | 1 + .../cheerio/dist/browser/api/extract.js | 42 + .../cheerio/dist/browser/api/extract.js.map | 1 + .../cheerio/dist/browser/api/forms.d.ts | 36 + .../cheerio/dist/browser/api/forms.d.ts.map | 1 + .../cheerio/dist/browser/api/forms.js | 81 + .../cheerio/dist/browser/api/forms.js.map | 1 + .../dist/browser/api/manipulation.d.ts | 528 + .../dist/browser/api/manipulation.d.ts.map | 1 + .../cheerio/dist/browser/api/manipulation.js | 829 + .../dist/browser/api/manipulation.js.map | 1 + .../cheerio/dist/browser/api/traversing.d.ts | 657 + .../dist/browser/api/traversing.d.ts.map | 1 + .../cheerio/dist/browser/api/traversing.js | 853 + .../dist/browser/api/traversing.js.map | 1 + .../cheerio/dist/browser/cheerio.d.ts | 85 + .../cheerio/dist/browser/cheerio.d.ts.map | 1 + .../cheerio/dist/browser/cheerio.js | 58 + .../cheerio/dist/browser/cheerio.js.map | 1 + .../dist/browser/index-browser.d.mts.map | 1 + .../dist/browser/index-browser.mjs.map | 1 + .../cheerio/dist/browser/index.d.ts | 5 + .../cheerio/dist/browser/index.js | 3 + .../cheerio/dist/browser/load-parse.d.ts | 20 + .../cheerio/dist/browser/load-parse.d.ts.map | 1 + .../cheerio/dist/browser/load-parse.js | 28 + .../cheerio/dist/browser/load-parse.js.map | 1 + .../cheerio/dist/browser/load.d.ts | 91 + .../cheerio/dist/browser/load.d.ts.map | 1 + .../node_modules/cheerio/dist/browser/load.js | 123 + .../cheerio/dist/browser/load.js.map | 1 + .../cheerio/dist/browser/options.d.ts | 95 + .../cheerio/dist/browser/options.d.ts.map | 1 + .../cheerio/dist/browser/options.js | 34 + .../cheerio/dist/browser/options.js.map | 1 + .../cheerio/dist/browser/package.json | 3 + .../cheerio/dist/browser/parse.d.ts | 18 + .../cheerio/dist/browser/parse.d.ts.map | 1 + .../cheerio/dist/browser/parse.js | 73 + .../cheerio/dist/browser/parse.js.map | 1 + .../dist/browser/parsers/parse5-adapter.d.ts | 20 + .../browser/parsers/parse5-adapter.d.ts.map | 1 + .../dist/browser/parsers/parse5-adapter.js | 50 + .../browser/parsers/parse5-adapter.js.map | 1 + .../cheerio/dist/browser/slim.d.ts | 25 + .../cheerio/dist/browser/slim.d.ts.map | 1 + .../node_modules/cheerio/dist/browser/slim.js | 22 + .../cheerio/dist/browser/slim.js.map | 1 + .../cheerio/dist/browser/static.d.ts | 112 + .../cheerio/dist/browser/static.d.ts.map | 1 + .../cheerio/dist/browser/static.js | 204 + .../cheerio/dist/browser/static.js.map | 1 + .../cheerio/dist/browser/types.d.ts | 21 + .../cheerio/dist/browser/types.d.ts.map | 1 + .../cheerio/dist/browser/types.js | 3 + .../cheerio/dist/browser/types.js.map | 1 + .../cheerio/dist/browser/utils.d.ts | 55 + .../cheerio/dist/browser/utils.d.ts.map | 1 + .../cheerio/dist/browser/utils.js | 81 + .../cheerio/dist/browser/utils.js.map | 1 + .../cheerio/dist/commonjs/api/attributes.d.ts | 385 + .../dist/commonjs/api/attributes.d.ts.map | 1 + .../cheerio/dist/commonjs/api/attributes.js | 630 + .../dist/commonjs/api/attributes.js.map | 1 + .../cheerio/dist/commonjs/api/css.d.ts | 42 + .../cheerio/dist/commonjs/api/css.d.ts.map | 1 + .../cheerio/dist/commonjs/api/css.js | 119 + .../cheerio/dist/commonjs/api/css.js.map | 1 + .../cheerio/dist/commonjs/api/extract.d.ts | 29 + .../dist/commonjs/api/extract.d.ts.map | 1 + .../cheerio/dist/commonjs/api/extract.js | 45 + .../cheerio/dist/commonjs/api/extract.js.map | 1 + .../cheerio/dist/commonjs/api/forms.d.ts | 36 + .../cheerio/dist/commonjs/api/forms.d.ts.map | 1 + .../cheerio/dist/commonjs/api/forms.js | 85 + .../cheerio/dist/commonjs/api/forms.js.map | 1 + .../dist/commonjs/api/manipulation.d.ts | 528 + .../dist/commonjs/api/manipulation.d.ts.map | 1 + .../cheerio/dist/commonjs/api/manipulation.js | 848 + .../dist/commonjs/api/manipulation.js.map | 1 + .../cheerio/dist/commonjs/api/traversing.d.ts | 657 + .../dist/commonjs/api/traversing.d.ts.map | 1 + .../cheerio/dist/commonjs/api/traversing.js | 900 + .../dist/commonjs/api/traversing.js.map | 1 + .../cheerio/dist/commonjs/cheerio.d.ts | 85 + .../cheerio/dist/commonjs/cheerio.d.ts.map | 1 + .../cheerio/dist/commonjs/cheerio.js | 85 + .../cheerio/dist/commonjs/cheerio.js.map | 1 + .../cheerio/dist/commonjs/index.d.ts | 104 + .../cheerio/dist/commonjs/index.d.ts.map | 1 + .../cheerio/dist/commonjs/index.js | 229 + .../cheerio/dist/commonjs/index.js.map | 1 + .../cheerio/dist/commonjs/load-parse.d.ts | 20 + .../cheerio/dist/commonjs/load-parse.d.ts.map | 1 + .../cheerio/dist/commonjs/load-parse.js | 34 + .../cheerio/dist/commonjs/load-parse.js.map | 1 + .../cheerio/dist/commonjs/load.d.ts | 91 + .../cheerio/dist/commonjs/load.d.ts.map | 1 + .../cheerio/dist/commonjs/load.js | 149 + .../cheerio/dist/commonjs/load.js.map | 1 + .../cheerio/dist/commonjs/options.d.ts | 95 + .../cheerio/dist/commonjs/options.d.ts.map | 1 + .../cheerio/dist/commonjs/options.js | 37 + .../cheerio/dist/commonjs/options.js.map | 1 + .../cheerio/dist/commonjs/package.json | 3 + .../cheerio/dist/commonjs/parse.d.ts | 18 + .../cheerio/dist/commonjs/parse.d.ts.map | 1 + .../cheerio/dist/commonjs/parse.js | 77 + .../cheerio/dist/commonjs/parse.js.map | 1 + .../dist/commonjs/parsers/parse5-adapter.d.ts | 20 + .../commonjs/parsers/parse5-adapter.d.ts.map | 1 + .../dist/commonjs/parsers/parse5-adapter.js | 54 + .../commonjs/parsers/parse5-adapter.js.map | 1 + .../cheerio/dist/commonjs/slim.d.ts | 25 + .../cheerio/dist/commonjs/slim.d.ts.map | 1 + .../cheerio/dist/commonjs/slim.js | 30 + .../cheerio/dist/commonjs/slim.js.map | 1 + .../cheerio/dist/commonjs/static.d.ts | 112 + .../cheerio/dist/commonjs/static.d.ts.map | 1 + .../cheerio/dist/commonjs/static.js | 214 + .../cheerio/dist/commonjs/static.js.map | 1 + .../cheerio/dist/commonjs/types.d.ts | 21 + .../cheerio/dist/commonjs/types.d.ts.map | 1 + .../cheerio/dist/commonjs/types.js | 4 + .../cheerio/dist/commonjs/types.js.map | 1 + .../cheerio/dist/commonjs/utils.d.ts | 55 + .../cheerio/dist/commonjs/utils.d.ts.map | 1 + .../cheerio/dist/commonjs/utils.js | 88 + .../cheerio/dist/commonjs/utils.js.map | 1 + .../cheerio/dist/esm/api/attributes.d.ts | 385 + .../cheerio/dist/esm/api/attributes.d.ts.map | 1 + .../cheerio/dist/esm/api/attributes.js | 619 + .../cheerio/dist/esm/api/attributes.js.map | 1 + .../cheerio/dist/esm/api/css.d.ts | 42 + .../cheerio/dist/esm/api/css.d.ts.map | 1 + .../node_modules/cheerio/dist/esm/api/css.js | 116 + .../cheerio/dist/esm/api/css.js.map | 1 + .../cheerio/dist/esm/api/extract.d.ts | 29 + .../cheerio/dist/esm/api/extract.d.ts.map | 1 + .../cheerio/dist/esm/api/extract.js | 42 + .../cheerio/dist/esm/api/extract.js.map | 1 + .../cheerio/dist/esm/api/forms.d.ts | 36 + .../cheerio/dist/esm/api/forms.d.ts.map | 1 + .../cheerio/dist/esm/api/forms.js | 81 + .../cheerio/dist/esm/api/forms.js.map | 1 + .../cheerio/dist/esm/api/manipulation.d.ts | 528 + .../dist/esm/api/manipulation.d.ts.map | 1 + .../cheerio/dist/esm/api/manipulation.js | 829 + .../cheerio/dist/esm/api/manipulation.js.map | 1 + .../cheerio/dist/esm/api/traversing.d.ts | 657 + .../cheerio/dist/esm/api/traversing.d.ts.map | 1 + .../cheerio/dist/esm/api/traversing.js | 853 + .../cheerio/dist/esm/api/traversing.js.map | 1 + .../cheerio/dist/esm/cheerio.d.ts | 85 + .../cheerio/dist/esm/cheerio.d.ts.map | 1 + .../node_modules/cheerio/dist/esm/cheerio.js | 58 + .../cheerio/dist/esm/cheerio.js.map | 1 + .../node_modules/cheerio/dist/esm/index.d.ts | 104 + .../cheerio/dist/esm/index.d.ts.map | 1 + .../node_modules/cheerio/dist/esm/index.js | 191 + .../cheerio/dist/esm/index.js.map | 1 + .../cheerio/dist/esm/load-parse.d.ts | 20 + .../cheerio/dist/esm/load-parse.d.ts.map | 1 + .../cheerio/dist/esm/load-parse.js | 28 + .../cheerio/dist/esm/load-parse.js.map | 1 + .../node_modules/cheerio/dist/esm/load.d.ts | 91 + .../cheerio/dist/esm/load.d.ts.map | 1 + .../node_modules/cheerio/dist/esm/load.js | 123 + .../node_modules/cheerio/dist/esm/load.js.map | 1 + .../cheerio/dist/esm/options.d.ts | 95 + .../cheerio/dist/esm/options.d.ts.map | 1 + .../node_modules/cheerio/dist/esm/options.js | 34 + .../cheerio/dist/esm/options.js.map | 1 + .../cheerio/dist/esm/package.json | 3 + .../node_modules/cheerio/dist/esm/parse.d.ts | 18 + .../cheerio/dist/esm/parse.d.ts.map | 1 + .../node_modules/cheerio/dist/esm/parse.js | 73 + .../cheerio/dist/esm/parse.js.map | 1 + .../dist/esm/parsers/parse5-adapter.d.ts | 20 + .../dist/esm/parsers/parse5-adapter.d.ts.map | 1 + .../dist/esm/parsers/parse5-adapter.js | 50 + .../dist/esm/parsers/parse5-adapter.js.map | 1 + .../node_modules/cheerio/dist/esm/slim.d.ts | 25 + .../cheerio/dist/esm/slim.d.ts.map | 1 + .../node_modules/cheerio/dist/esm/slim.js | 22 + .../node_modules/cheerio/dist/esm/slim.js.map | 1 + .../node_modules/cheerio/dist/esm/static.d.ts | 112 + .../cheerio/dist/esm/static.d.ts.map | 1 + .../node_modules/cheerio/dist/esm/static.js | 204 + .../cheerio/dist/esm/static.js.map | 1 + .../node_modules/cheerio/dist/esm/types.d.ts | 21 + .../cheerio/dist/esm/types.d.ts.map | 1 + .../node_modules/cheerio/dist/esm/types.js | 3 + .../cheerio/dist/esm/types.js.map | 1 + .../node_modules/cheerio/dist/esm/utils.d.ts | 55 + .../cheerio/dist/esm/utils.d.ts.map | 1 + .../node_modules/cheerio/dist/esm/utils.js | 81 + .../cheerio/dist/esm/utils.js.map | 1 + frontend/node_modules/cheerio/package.json | 178 + .../cheerio/src/__fixtures__/fixtures.ts | 147 + .../cheerio/src/__tests__/deprecated.spec.ts | 266 + .../cheerio/src/__tests__/xml.spec.ts | 66 + .../cheerio/src/api/attributes.spec.ts | 1165 + .../cheerio/src/api/attributes.ts | 1130 + .../node_modules/cheerio/src/api/css.spec.ts | 138 + frontend/node_modules/cheerio/src/api/css.ts | 224 + .../cheerio/src/api/extract.spec.ts | 121 + .../node_modules/cheerio/src/api/extract.ts | 92 + .../cheerio/src/api/forms.spec.ts | 155 + .../node_modules/cheerio/src/api/forms.ts | 103 + .../cheerio/src/api/manipulation.spec.ts | 1988 ++ .../cheerio/src/api/manipulation.ts | 1111 + .../cheerio/src/api/traversing.spec.ts | 1677 ++ .../cheerio/src/api/traversing.ts | 1171 + .../node_modules/cheerio/src/cheerio.spec.ts | 455 + frontend/node_modules/cheerio/src/cheerio.ts | 143 + .../cheerio/src/index-browser.mts | 10 + .../node_modules/cheerio/src/index.spec.ts | 180 + frontend/node_modules/cheerio/src/index.ts | 274 + .../node_modules/cheerio/src/load-parse.ts | 39 + .../node_modules/cheerio/src/load.spec.ts | 31 + frontend/node_modules/cheerio/src/load.ts | 277 + frontend/node_modules/cheerio/src/options.ts | 135 + .../node_modules/cheerio/src/parse.spec.ts | 452 + frontend/node_modules/cheerio/src/parse.ts | 105 + .../cheerio/src/parsers/parse5-adapter.ts | 66 + frontend/node_modules/cheerio/src/slim.ts | 33 + .../node_modules/cheerio/src/static.spec.ts | 325 + frontend/node_modules/cheerio/src/static.ts | 312 + frontend/node_modules/cheerio/src/types.ts | 58 + .../node_modules/cheerio/src/utils.spec.ts | 32 + frontend/node_modules/cheerio/src/utils.ts | 93 + frontend/node_modules/commander/LICENSE | 22 + frontend/node_modules/commander/Readme.md | 1015 + frontend/node_modules/commander/esm.mjs | 15 + frontend/node_modules/commander/index.js | 27 + .../node_modules/commander/lib/argument.js | 147 + .../node_modules/commander/lib/command.js | 1944 ++ frontend/node_modules/commander/lib/error.js | 45 + frontend/node_modules/commander/lib/help.js | 396 + frontend/node_modules/commander/lib/option.js | 208 + .../commander/lib/suggestSimilar.js | 100 + .../commander/package-support.json | 16 + frontend/node_modules/commander/package.json | 69 + .../node_modules/commander/typings/index.d.ts | 774 + frontend/node_modules/css-select/LICENSE | 11 + frontend/node_modules/css-select/README.md | 264 + .../css-select/lib/attributes.d.ts | 7 + .../css-select/lib/attributes.d.ts.map | 1 + .../node_modules/css-select/lib/attributes.js | 236 + .../css-select/lib/attributes.js.map | 1 + .../node_modules/css-select/lib/compile.d.ts | 13 + .../css-select/lib/compile.d.ts.map | 1 + .../node_modules/css-select/lib/compile.js | 151 + .../css-select/lib/compile.js.map | 1 + .../css-select/lib/esm/attributes.d.ts | 7 + .../css-select/lib/esm/attributes.d.ts.map | 1 + .../css-select/lib/esm/attributes.js | 222 + .../css-select/lib/esm/attributes.js.map | 1 + .../css-select/lib/esm/compile.d.ts | 13 + .../css-select/lib/esm/compile.d.ts.map | 1 + .../css-select/lib/esm/compile.js | 115 + .../css-select/lib/esm/compile.js.map | 1 + .../css-select/lib/esm/general.d.ts | 3 + .../css-select/lib/esm/general.d.ts.map | 1 + .../css-select/lib/esm/general.js | 144 + .../css-select/lib/esm/general.js.map | 1 + .../css-select/lib/esm/helpers/cache.d.ts | 12 + .../css-select/lib/esm/helpers/cache.d.ts.map | 1 + .../css-select/lib/esm/helpers/cache.js | 41 + .../css-select/lib/esm/helpers/cache.js.map | 1 + .../css-select/lib/esm/helpers/querying.d.ts | 24 + .../lib/esm/helpers/querying.d.ts.map | 1 + .../css-select/lib/esm/helpers/querying.js | 105 + .../lib/esm/helpers/querying.js.map | 1 + .../css-select/lib/esm/helpers/selectors.d.ts | 20 + .../lib/esm/helpers/selectors.d.ts.map | 1 + .../css-select/lib/esm/helpers/selectors.js | 103 + .../lib/esm/helpers/selectors.js.map | 1 + .../css-select/lib/esm/index.d.ts | 50 + .../css-select/lib/esm/index.d.ts.map | 1 + .../node_modules/css-select/lib/esm/index.js | 115 + .../css-select/lib/esm/index.js.map | 1 + .../css-select/lib/esm/package.json | 1 + .../lib/esm/pseudo-selectors/aliases.d.ts | 5 + .../lib/esm/pseudo-selectors/aliases.d.ts.map | 1 + .../lib/esm/pseudo-selectors/aliases.js | 35 + .../lib/esm/pseudo-selectors/aliases.js.map | 1 + .../lib/esm/pseudo-selectors/filters.d.ts | 4 + .../lib/esm/pseudo-selectors/filters.d.ts.map | 1 + .../lib/esm/pseudo-selectors/filters.js | 143 + .../lib/esm/pseudo-selectors/filters.js.map | 1 + .../lib/esm/pseudo-selectors/index.d.ts | 8 + .../lib/esm/pseudo-selectors/index.d.ts.map | 1 + .../lib/esm/pseudo-selectors/index.js | 40 + .../lib/esm/pseudo-selectors/index.js.map | 1 + .../lib/esm/pseudo-selectors/pseudos.d.ts | 6 + .../lib/esm/pseudo-selectors/pseudos.d.ts.map | 1 + .../lib/esm/pseudo-selectors/pseudos.js | 79 + .../lib/esm/pseudo-selectors/pseudos.js.map | 1 + .../lib/esm/pseudo-selectors/subselects.d.ts | 9 + .../esm/pseudo-selectors/subselects.d.ts.map | 1 + .../lib/esm/pseudo-selectors/subselects.js | 94 + .../esm/pseudo-selectors/subselects.js.map | 1 + .../node_modules/css-select/lib/esm/sort.d.ts | 12 + .../css-select/lib/esm/sort.d.ts.map | 1 + .../node_modules/css-select/lib/esm/sort.js | 79 + .../css-select/lib/esm/sort.js.map | 1 + .../css-select/lib/esm/types.d.ts | 167 + .../css-select/lib/esm/types.d.ts.map | 1 + .../node_modules/css-select/lib/esm/types.js | 2 + .../css-select/lib/esm/types.js.map | 1 + .../node_modules/css-select/lib/general.d.ts | 3 + .../css-select/lib/general.d.ts.map | 1 + .../node_modules/css-select/lib/general.js | 148 + .../css-select/lib/general.js.map | 1 + .../css-select/lib/helpers/cache.d.ts | 12 + .../css-select/lib/helpers/cache.d.ts.map | 1 + .../css-select/lib/helpers/cache.js | 45 + .../css-select/lib/helpers/cache.js.map | 1 + .../css-select/lib/helpers/querying.d.ts | 24 + .../css-select/lib/helpers/querying.d.ts.map | 1 + .../css-select/lib/helpers/querying.js | 111 + .../css-select/lib/helpers/querying.js.map | 1 + .../css-select/lib/helpers/selectors.d.ts | 20 + .../css-select/lib/helpers/selectors.d.ts.map | 1 + .../css-select/lib/helpers/selectors.js | 111 + .../css-select/lib/helpers/selectors.js.map | 1 + .../node_modules/css-select/lib/index.d.ts | 50 + .../css-select/lib/index.d.ts.map | 1 + frontend/node_modules/css-select/lib/index.js | 154 + .../node_modules/css-select/lib/index.js.map | 1 + .../lib/pseudo-selectors/aliases.d.ts | 5 + .../lib/pseudo-selectors/aliases.d.ts.map | 1 + .../lib/pseudo-selectors/aliases.js | 34 + .../lib/pseudo-selectors/aliases.js.map | 1 + .../lib/pseudo-selectors/filters.d.ts | 4 + .../lib/pseudo-selectors/filters.d.ts.map | 1 + .../lib/pseudo-selectors/filters.js | 157 + .../lib/pseudo-selectors/filters.js.map | 1 + .../lib/pseudo-selectors/index.d.ts | 8 + .../lib/pseudo-selectors/index.d.ts.map | 1 + .../css-select/lib/pseudo-selectors/index.js | 46 + .../lib/pseudo-selectors/index.js.map | 1 + .../lib/pseudo-selectors/pseudos.d.ts | 6 + .../lib/pseudo-selectors/pseudos.d.ts.map | 1 + .../lib/pseudo-selectors/pseudos.js | 93 + .../lib/pseudo-selectors/pseudos.js.map | 1 + .../lib/pseudo-selectors/subselects.d.ts | 9 + .../lib/pseudo-selectors/subselects.d.ts.map | 1 + .../lib/pseudo-selectors/subselects.js | 112 + .../lib/pseudo-selectors/subselects.js.map | 1 + .../node_modules/css-select/lib/sort.d.ts | 12 + .../node_modules/css-select/lib/sort.d.ts.map | 1 + frontend/node_modules/css-select/lib/sort.js | 84 + .../node_modules/css-select/lib/sort.js.map | 1 + .../node_modules/css-select/lib/types.d.ts | 167 + .../css-select/lib/types.d.ts.map | 1 + frontend/node_modules/css-select/lib/types.js | 3 + .../node_modules/css-select/lib/types.js.map | 1 + frontend/node_modules/css-select/package.json | 81 + frontend/node_modules/css-what/LICENSE | 11 + .../css-what/lib/commonjs/index.d.ts | 4 + .../css-what/lib/commonjs/index.d.ts.map | 1 + .../css-what/lib/commonjs/index.js | 23 + .../css-what/lib/commonjs/parse.d.ts | 20 + .../css-what/lib/commonjs/parse.d.ts.map | 1 + .../css-what/lib/commonjs/parse.js | 425 + .../css-what/lib/commonjs/stringify.d.ts | 8 + .../css-what/lib/commonjs/stringify.d.ts.map | 1 + .../css-what/lib/commonjs/stringify.js | 138 + .../css-what/lib/commonjs/types.d.ts | 70 + .../css-what/lib/commonjs/types.d.ts.map | 1 + .../css-what/lib/commonjs/types.js | 42 + .../node_modules/css-what/lib/es/index.d.ts | 4 + .../css-what/lib/es/index.d.ts.map | 1 + .../node_modules/css-what/lib/es/index.js | 3 + .../node_modules/css-what/lib/es/parse.d.ts | 20 + .../css-what/lib/es/parse.d.ts.map | 1 + .../node_modules/css-what/lib/es/parse.js | 420 + .../css-what/lib/es/stringify.d.ts | 8 + .../css-what/lib/es/stringify.d.ts.map | 1 + .../node_modules/css-what/lib/es/stringify.js | 126 + .../node_modules/css-what/lib/es/types.d.ts | 70 + .../css-what/lib/es/types.d.ts.map | 1 + .../node_modules/css-what/lib/es/types.js | 39 + frontend/node_modules/css-what/package.json | 59 + frontend/node_modules/css-what/readme.md | 69 + frontend/node_modules/d3-array/LICENSE | 13 + frontend/node_modules/d3-array/README.md | 954 + .../node_modules/d3-array/dist/d3-array.js | 1455 ++ .../d3-array/dist/d3-array.min.js | 2 + frontend/node_modules/d3-array/package.json | 61 + frontend/node_modules/d3-array/src/array.js | 4 + .../node_modules/d3-array/src/ascending.js | 3 + frontend/node_modules/d3-array/src/bin.js | 125 + frontend/node_modules/d3-array/src/bisect.js | 9 + .../node_modules/d3-array/src/bisector.js | 56 + frontend/node_modules/d3-array/src/blur.js | 115 + .../node_modules/d3-array/src/constant.js | 3 + frontend/node_modules/d3-array/src/count.js | 18 + frontend/node_modules/d3-array/src/cross.js | 33 + frontend/node_modules/d3-array/src/cumsum.js | 6 + .../node_modules/d3-array/src/descending.js | 7 + .../node_modules/d3-array/src/deviation.js | 6 + .../node_modules/d3-array/src/difference.js | 11 + .../node_modules/d3-array/src/disjoint.js | 15 + frontend/node_modules/d3-array/src/every.js | 10 + frontend/node_modules/d3-array/src/extent.js | 29 + frontend/node_modules/d3-array/src/filter.js | 11 + frontend/node_modules/d3-array/src/fsum.js | 69 + .../node_modules/d3-array/src/greatest.js | 29 + .../d3-array/src/greatestIndex.js | 19 + frontend/node_modules/d3-array/src/group.js | 65 + .../node_modules/d3-array/src/groupSort.js | 10 + .../node_modules/d3-array/src/identity.js | 3 + frontend/node_modules/d3-array/src/index.js | 57 + .../node_modules/d3-array/src/intersection.js | 19 + frontend/node_modules/d3-array/src/least.js | 29 + .../node_modules/d3-array/src/leastIndex.js | 19 + frontend/node_modules/d3-array/src/map.js | 5 + frontend/node_modules/d3-array/src/max.js | 20 + .../node_modules/d3-array/src/maxIndex.js | 22 + frontend/node_modules/d3-array/src/mean.js | 19 + frontend/node_modules/d3-array/src/median.js | 9 + frontend/node_modules/d3-array/src/merge.js | 9 + frontend/node_modules/d3-array/src/min.js | 20 + .../node_modules/d3-array/src/minIndex.js | 22 + frontend/node_modules/d3-array/src/mode.js | 28 + frontend/node_modules/d3-array/src/nice.js | 18 + frontend/node_modules/d3-array/src/number.js | 20 + frontend/node_modules/d3-array/src/pairs.js | 15 + frontend/node_modules/d3-array/src/permute.js | 3 + .../node_modules/d3-array/src/quantile.js | 47 + .../node_modules/d3-array/src/quickselect.js | 53 + frontend/node_modules/d3-array/src/range.js | 13 + frontend/node_modules/d3-array/src/rank.js | 24 + frontend/node_modules/d3-array/src/reduce.js | 14 + frontend/node_modules/d3-array/src/reverse.js | 4 + frontend/node_modules/d3-array/src/scan.js | 6 + frontend/node_modules/d3-array/src/shuffle.js | 13 + frontend/node_modules/d3-array/src/some.js | 10 + frontend/node_modules/d3-array/src/sort.js | 39 + frontend/node_modules/d3-array/src/subset.js | 5 + frontend/node_modules/d3-array/src/sum.js | 18 + .../node_modules/d3-array/src/superset.js | 19 + .../src/threshold/freedmanDiaconis.js | 7 + .../d3-array/src/threshold/scott.js | 7 + .../d3-array/src/threshold/sturges.js | 5 + frontend/node_modules/d3-array/src/ticks.js | 55 + .../node_modules/d3-array/src/transpose.js | 15 + frontend/node_modules/d3-array/src/union.js | 11 + .../node_modules/d3-array/src/variance.js | 25 + frontend/node_modules/d3-array/src/zip.js | 5 + frontend/node_modules/d3-axis/LICENSE | 13 + frontend/node_modules/d3-axis/README.md | 210 + frontend/node_modules/d3-axis/dist/d3-axis.js | 192 + .../node_modules/d3-axis/dist/d3-axis.min.js | 2 + frontend/node_modules/d3-axis/package.json | 54 + frontend/node_modules/d3-axis/src/axis.js | 174 + frontend/node_modules/d3-axis/src/identity.js | 3 + frontend/node_modules/d3-axis/src/index.js | 6 + frontend/node_modules/d3-brush/LICENSE | 13 + frontend/node_modules/d3-brush/README.md | 185 + .../node_modules/d3-brush/dist/d3-brush.js | 656 + .../d3-brush/dist/d3-brush.min.js | 2 + frontend/node_modules/d3-brush/package.json | 55 + frontend/node_modules/d3-brush/src/brush.js | 621 + .../node_modules/d3-brush/src/constant.js | 1 + frontend/node_modules/d3-brush/src/event.js | 16 + frontend/node_modules/d3-brush/src/index.js | 6 + frontend/node_modules/d3-brush/src/noevent.js | 8 + frontend/node_modules/d3-chord/LICENSE | 13 + frontend/node_modules/d3-chord/README.md | 234 + .../node_modules/d3-chord/dist/d3-chord.js | 284 + .../d3-chord/dist/d3-chord.min.js | 2 + frontend/node_modules/d3-chord/package.json | 54 + frontend/node_modules/d3-chord/src/array.js | 1 + frontend/node_modules/d3-chord/src/chord.js | 122 + .../node_modules/d3-chord/src/constant.js | 5 + frontend/node_modules/d3-chord/src/index.js | 2 + frontend/node_modules/d3-chord/src/math.js | 8 + frontend/node_modules/d3-chord/src/ribbon.js | 134 + frontend/node_modules/d3-color/LICENSE | 13 + frontend/node_modules/d3-color/README.md | 203 + .../node_modules/d3-color/dist/d3-color.js | 606 + .../d3-color/dist/d3-color.min.js | 2 + frontend/node_modules/d3-color/package.json | 54 + frontend/node_modules/d3-color/src/color.js | 396 + .../node_modules/d3-color/src/cubehelix.js | 61 + frontend/node_modules/d3-color/src/define.js | 10 + frontend/node_modules/d3-color/src/index.js | 3 + frontend/node_modules/d3-color/src/lab.js | 123 + frontend/node_modules/d3-color/src/math.js | 2 + frontend/node_modules/d3-contour/LICENSE | 13 + frontend/node_modules/d3-contour/README.md | 187 + .../d3-contour/dist/d3-contour.js | 420 + .../d3-contour/dist/d3-contour.min.js | 2 + frontend/node_modules/d3-contour/package.json | 66 + frontend/node_modules/d3-contour/src/area.js | 5 + frontend/node_modules/d3-contour/src/array.js | 3 + .../node_modules/d3-contour/src/ascending.js | 3 + .../node_modules/d3-contour/src/constant.js | 1 + .../node_modules/d3-contour/src/contains.js | 27 + .../node_modules/d3-contour/src/contours.js | 225 + .../node_modules/d3-contour/src/density.js | 149 + frontend/node_modules/d3-contour/src/index.js | 2 + frontend/node_modules/d3-contour/src/noop.js | 1 + frontend/node_modules/d3-delaunay/LICENSE | 14 + frontend/node_modules/d3-delaunay/README.md | 216 + .../d3-delaunay/dist/d3-delaunay.js | 1391 ++ .../d3-delaunay/dist/d3-delaunay.min.js | 2 + .../node_modules/d3-delaunay/package.json | 62 + .../node_modules/d3-delaunay/src/delaunay.js | 248 + .../node_modules/d3-delaunay/src/index.js | 2 + frontend/node_modules/d3-delaunay/src/path.js | 37 + .../node_modules/d3-delaunay/src/polygon.js | 17 + .../node_modules/d3-delaunay/src/voronoi.js | 332 + frontend/node_modules/d3-dispatch/LICENSE | 13 + frontend/node_modules/d3-dispatch/README.md | 94 + .../d3-dispatch/dist/d3-dispatch.js | 95 + .../d3-dispatch/dist/d3-dispatch.min.js | 2 + .../node_modules/d3-dispatch/package.json | 50 + .../node_modules/d3-dispatch/src/dispatch.js | 84 + .../node_modules/d3-dispatch/src/index.js | 1 + frontend/node_modules/d3-drag/LICENSE | 13 + frontend/node_modules/d3-drag/README.md | 248 + frontend/node_modules/d3-drag/dist/d3-drag.js | 273 + .../node_modules/d3-drag/dist/d3-drag.min.js | 2 + frontend/node_modules/d3-drag/package.json | 54 + frontend/node_modules/d3-drag/src/constant.js | 1 + frontend/node_modules/d3-drag/src/drag.js | 194 + frontend/node_modules/d3-drag/src/event.js | 28 + frontend/node_modules/d3-drag/src/index.js | 2 + frontend/node_modules/d3-drag/src/nodrag.js | 28 + frontend/node_modules/d3-drag/src/noevent.js | 13 + frontend/node_modules/d3-dsv/LICENSE | 13 + frontend/node_modules/d3-dsv/README.md | 492 + frontend/node_modules/d3-dsv/bin/dsv2dsv.js | 35 + frontend/node_modules/d3-dsv/bin/dsv2json.js | 38 + frontend/node_modules/d3-dsv/bin/json2dsv.js | 36 + frontend/node_modules/d3-dsv/dist/d3-dsv.js | 233 + .../node_modules/d3-dsv/dist/d3-dsv.min.js | 2 + .../node_modules/commander/CHANGELOG.md | 440 + .../d3-dsv/node_modules/commander/LICENSE | 22 + .../d3-dsv/node_modules/commander/Readme.md | 917 + .../d3-dsv/node_modules/commander/esm.mjs | 4 + .../d3-dsv/node_modules/commander/index.js | 2217 ++ .../commander/package-support.json | 16 + .../node_modules/commander/package.json | 68 + .../node_modules/commander/typings/index.d.ts | 627 + frontend/node_modules/d3-dsv/package.json | 68 + frontend/node_modules/d3-dsv/src/autoType.js | 20 + frontend/node_modules/d3-dsv/src/csv.js | 11 + frontend/node_modules/d3-dsv/src/dsv.js | 164 + frontend/node_modules/d3-dsv/src/index.js | 4 + frontend/node_modules/d3-dsv/src/tsv.js | 11 + frontend/node_modules/d3-ease/LICENSE | 28 + frontend/node_modules/d3-ease/README.md | 253 + frontend/node_modules/d3-ease/dist/d3-ease.js | 262 + .../node_modules/d3-ease/dist/d3-ease.min.js | 2 + frontend/node_modules/d3-ease/package.json | 51 + frontend/node_modules/d3-ease/src/back.js | 37 + frontend/node_modules/d3-ease/src/bounce.js | 22 + frontend/node_modules/d3-ease/src/circle.js | 11 + frontend/node_modules/d3-ease/src/cubic.js | 11 + frontend/node_modules/d3-ease/src/elastic.js | 46 + frontend/node_modules/d3-ease/src/exp.js | 13 + frontend/node_modules/d3-ease/src/index.js | 66 + frontend/node_modules/d3-ease/src/linear.js | 1 + frontend/node_modules/d3-ease/src/math.js | 4 + frontend/node_modules/d3-ease/src/poly.js | 37 + frontend/node_modules/d3-ease/src/quad.js | 11 + frontend/node_modules/d3-ease/src/sin.js | 14 + frontend/node_modules/d3-fetch/LICENSE | 13 + frontend/node_modules/d3-fetch/README.md | 111 + .../node_modules/d3-fetch/dist/d3-fetch.js | 100 + .../d3-fetch/dist/d3-fetch.min.js | 2 + frontend/node_modules/d3-fetch/package.json | 53 + frontend/node_modules/d3-fetch/src/blob.js | 8 + frontend/node_modules/d3-fetch/src/buffer.js | 8 + frontend/node_modules/d3-fetch/src/dsv.js | 22 + frontend/node_modules/d3-fetch/src/image.js | 9 + frontend/node_modules/d3-fetch/src/index.js | 7 + frontend/node_modules/d3-fetch/src/json.js | 9 + frontend/node_modules/d3-fetch/src/text.js | 8 + frontend/node_modules/d3-fetch/src/xml.js | 12 + frontend/node_modules/d3-force/LICENSE | 13 + frontend/node_modules/d3-force/README.md | 480 + .../node_modules/d3-force/dist/d3-force.js | 693 + .../d3-force/dist/d3-force.min.js | 2 + frontend/node_modules/d3-force/package.json | 58 + frontend/node_modules/d3-force/src/center.js | 40 + frontend/node_modules/d3-force/src/collide.js | 100 + .../node_modules/d3-force/src/constant.js | 5 + frontend/node_modules/d3-force/src/index.js | 8 + frontend/node_modules/d3-force/src/jiggle.js | 3 + frontend/node_modules/d3-force/src/lcg.js | 9 + frontend/node_modules/d3-force/src/link.js | 117 + .../node_modules/d3-force/src/manyBody.js | 116 + frontend/node_modules/d3-force/src/radial.js | 57 + .../node_modules/d3-force/src/simulation.js | 156 + frontend/node_modules/d3-force/src/x.js | 41 + frontend/node_modules/d3-force/src/y.js | 41 + frontend/node_modules/d3-format/LICENSE | 13 + frontend/node_modules/d3-format/README.md | 350 + .../node_modules/d3-format/dist/d3-format.js | 345 + .../d3-format/dist/d3-format.min.js | 2 + .../node_modules/d3-format/locale/ar-001.json | 7 + .../node_modules/d3-format/locale/ar-AE.json | 7 + .../node_modules/d3-format/locale/ar-BH.json | 7 + .../node_modules/d3-format/locale/ar-DJ.json | 7 + .../node_modules/d3-format/locale/ar-DZ.json | 6 + .../node_modules/d3-format/locale/ar-EG.json | 7 + .../node_modules/d3-format/locale/ar-EH.json | 6 + .../node_modules/d3-format/locale/ar-ER.json | 7 + .../node_modules/d3-format/locale/ar-IL.json | 7 + .../node_modules/d3-format/locale/ar-IQ.json | 7 + .../node_modules/d3-format/locale/ar-JO.json | 7 + .../node_modules/d3-format/locale/ar-KM.json | 7 + .../node_modules/d3-format/locale/ar-KW.json | 7 + .../node_modules/d3-format/locale/ar-LB.json | 7 + .../node_modules/d3-format/locale/ar-LY.json | 6 + .../node_modules/d3-format/locale/ar-MA.json | 6 + .../node_modules/d3-format/locale/ar-MR.json | 7 + .../node_modules/d3-format/locale/ar-OM.json | 7 + .../node_modules/d3-format/locale/ar-PS.json | 7 + .../node_modules/d3-format/locale/ar-QA.json | 7 + .../node_modules/d3-format/locale/ar-SA.json | 7 + .../node_modules/d3-format/locale/ar-SD.json | 7 + .../node_modules/d3-format/locale/ar-SO.json | 7 + .../node_modules/d3-format/locale/ar-SS.json | 7 + .../node_modules/d3-format/locale/ar-SY.json | 7 + .../node_modules/d3-format/locale/ar-TD.json | 7 + .../node_modules/d3-format/locale/ar-TN.json | 6 + .../node_modules/d3-format/locale/ar-YE.json | 7 + .../node_modules/d3-format/locale/ca-ES.json | 6 + .../node_modules/d3-format/locale/cs-CZ.json | 6 + .../node_modules/d3-format/locale/da-DK.json | 6 + .../node_modules/d3-format/locale/de-CH.json | 6 + .../node_modules/d3-format/locale/de-DE.json | 6 + .../node_modules/d3-format/locale/en-CA.json | 6 + .../node_modules/d3-format/locale/en-GB.json | 6 + .../node_modules/d3-format/locale/en-IE.json | 6 + .../node_modules/d3-format/locale/en-IN.json | 6 + .../node_modules/d3-format/locale/en-US.json | 6 + .../node_modules/d3-format/locale/es-BO.json | 7 + .../node_modules/d3-format/locale/es-ES.json | 6 + .../node_modules/d3-format/locale/es-MX.json | 6 + .../node_modules/d3-format/locale/fi-FI.json | 6 + .../node_modules/d3-format/locale/fr-CA.json | 6 + .../node_modules/d3-format/locale/fr-FR.json | 7 + .../node_modules/d3-format/locale/he-IL.json | 6 + .../node_modules/d3-format/locale/hu-HU.json | 6 + .../node_modules/d3-format/locale/it-IT.json | 6 + .../node_modules/d3-format/locale/ja-JP.json | 6 + .../node_modules/d3-format/locale/ko-KR.json | 6 + .../node_modules/d3-format/locale/mk-MK.json | 6 + .../node_modules/d3-format/locale/nl-NL.json | 6 + .../node_modules/d3-format/locale/pl-PL.json | 6 + .../node_modules/d3-format/locale/pt-BR.json | 6 + .../node_modules/d3-format/locale/pt-PT.json | 6 + .../node_modules/d3-format/locale/ru-RU.json | 6 + .../node_modules/d3-format/locale/sl-SI.json | 6 + .../node_modules/d3-format/locale/sv-SE.json | 6 + .../node_modules/d3-format/locale/uk-UA.json | 6 + .../node_modules/d3-format/locale/zh-CN.json | 6 + frontend/node_modules/d3-format/package.json | 55 + .../d3-format/src/defaultLocale.js | 18 + .../node_modules/d3-format/src/exponent.js | 5 + .../d3-format/src/formatDecimal.js | 20 + .../node_modules/d3-format/src/formatGroup.js | 18 + .../d3-format/src/formatNumerals.js | 7 + .../d3-format/src/formatPrefixAuto.js | 16 + .../d3-format/src/formatRounded.js | 11 + .../d3-format/src/formatSpecifier.js | 47 + .../node_modules/d3-format/src/formatTrim.js | 11 + .../node_modules/d3-format/src/formatTypes.js | 19 + .../node_modules/d3-format/src/identity.js | 3 + frontend/node_modules/d3-format/src/index.js | 6 + frontend/node_modules/d3-format/src/locale.js | 148 + .../d3-format/src/precisionFixed.js | 5 + .../d3-format/src/precisionPrefix.js | 5 + .../d3-format/src/precisionRound.js | 6 + frontend/node_modules/d3-geo/LICENSE | 34 + frontend/node_modules/d3-geo/README.md | 12 + frontend/node_modules/d3-geo/dist/d3-geo.js | 3167 +++ .../node_modules/d3-geo/dist/d3-geo.min.js | 2 + frontend/node_modules/d3-geo/package.json | 59 + frontend/node_modules/d3-geo/src/area.js | 76 + frontend/node_modules/d3-geo/src/bounds.js | 179 + frontend/node_modules/d3-geo/src/cartesian.js | 33 + frontend/node_modules/d3-geo/src/centroid.js | 143 + frontend/node_modules/d3-geo/src/circle.js | 72 + .../d3-geo/src/clip/antimeridian.js | 92 + .../node_modules/d3-geo/src/clip/buffer.js | 24 + .../node_modules/d3-geo/src/clip/circle.js | 177 + .../node_modules/d3-geo/src/clip/extent.js | 20 + .../node_modules/d3-geo/src/clip/index.js | 131 + frontend/node_modules/d3-geo/src/clip/line.js | 59 + .../node_modules/d3-geo/src/clip/rectangle.js | 168 + .../node_modules/d3-geo/src/clip/rejoin.js | 103 + frontend/node_modules/d3-geo/src/compose.js | 12 + frontend/node_modules/d3-geo/src/constant.js | 5 + frontend/node_modules/d3-geo/src/contains.js | 97 + frontend/node_modules/d3-geo/src/distance.js | 10 + frontend/node_modules/d3-geo/src/graticule.js | 105 + frontend/node_modules/d3-geo/src/identity.js | 1 + frontend/node_modules/d3-geo/src/index.js | 34 + .../node_modules/d3-geo/src/interpolate.js | 36 + frontend/node_modules/d3-geo/src/length.js | 53 + frontend/node_modules/d3-geo/src/math.js | 36 + frontend/node_modules/d3-geo/src/noop.js | 1 + frontend/node_modules/d3-geo/src/path/area.js | 50 + .../node_modules/d3-geo/src/path/bounds.js | 28 + .../node_modules/d3-geo/src/path/centroid.js | 100 + .../node_modules/d3-geo/src/path/context.js | 45 + .../node_modules/d3-geo/src/path/index.js | 76 + .../node_modules/d3-geo/src/path/measure.js | 45 + .../node_modules/d3-geo/src/path/string.js | 86 + .../node_modules/d3-geo/src/pointEqual.js | 5 + .../d3-geo/src/polygonContains.js | 74 + .../d3-geo/src/projection/albers.js | 10 + .../d3-geo/src/projection/albersUsa.js | 111 + .../d3-geo/src/projection/azimuthal.js | 27 + .../src/projection/azimuthalEqualArea.js | 17 + .../src/projection/azimuthalEquidistant.js | 17 + .../d3-geo/src/projection/conic.js | 15 + .../d3-geo/src/projection/conicConformal.js | 38 + .../d3-geo/src/projection/conicEqualArea.js | 33 + .../d3-geo/src/projection/conicEquidistant.js | 32 + .../src/projection/cylindricalEqualArea.js | 15 + .../d3-geo/src/projection/equalEarth.js | 36 + .../d3-geo/src/projection/equirectangular.js | 12 + .../node_modules/d3-geo/src/projection/fit.js | 47 + .../d3-geo/src/projection/gnomonic.js | 16 + .../d3-geo/src/projection/identity.js | 85 + .../d3-geo/src/projection/index.js | 177 + .../d3-geo/src/projection/mercator.js | 52 + .../d3-geo/src/projection/naturalEarth1.js | 28 + .../d3-geo/src/projection/orthographic.js | 15 + .../d3-geo/src/projection/resample.js | 102 + .../d3-geo/src/projection/stereographic.js | 18 + .../src/projection/transverseMercator.js | 27 + frontend/node_modules/d3-geo/src/rotation.js | 79 + frontend/node_modules/d3-geo/src/stream.js | 69 + frontend/node_modules/d3-geo/src/transform.js | 26 + frontend/node_modules/d3-hierarchy/LICENSE | 13 + frontend/node_modules/d3-hierarchy/README.md | 592 + .../d3-hierarchy/dist/d3-hierarchy.js | 1410 ++ .../d3-hierarchy/dist/d3-hierarchy.min.js | 2 + .../node_modules/d3-hierarchy/package.json | 56 + .../d3-hierarchy/src/accessors.js | 8 + .../node_modules/d3-hierarchy/src/array.js | 20 + .../node_modules/d3-hierarchy/src/cluster.js | 84 + .../node_modules/d3-hierarchy/src/constant.js | 9 + .../d3-hierarchy/src/hierarchy/ancestors.js | 7 + .../d3-hierarchy/src/hierarchy/count.js | 12 + .../d3-hierarchy/src/hierarchy/descendants.js | 3 + .../d3-hierarchy/src/hierarchy/each.js | 7 + .../d3-hierarchy/src/hierarchy/eachAfter.js | 15 + .../d3-hierarchy/src/hierarchy/eachBefore.js | 12 + .../d3-hierarchy/src/hierarchy/find.js | 8 + .../d3-hierarchy/src/hierarchy/index.js | 91 + .../d3-hierarchy/src/hierarchy/iterator.js | 14 + .../d3-hierarchy/src/hierarchy/leaves.js | 9 + .../d3-hierarchy/src/hierarchy/links.js | 9 + .../d3-hierarchy/src/hierarchy/path.js | 30 + .../d3-hierarchy/src/hierarchy/sort.js | 7 + .../d3-hierarchy/src/hierarchy/sum.js | 9 + .../node_modules/d3-hierarchy/src/index.js | 15 + frontend/node_modules/d3-hierarchy/src/lcg.js | 9 + .../d3-hierarchy/src/pack/enclose.js | 123 + .../d3-hierarchy/src/pack/index.js | 81 + .../d3-hierarchy/src/pack/siblings.js | 120 + .../d3-hierarchy/src/partition.js | 52 + .../node_modules/d3-hierarchy/src/stratify.js | 145 + .../node_modules/d3-hierarchy/src/tree.js | 237 + .../d3-hierarchy/src/treemap/binary.js | 46 + .../d3-hierarchy/src/treemap/dice.js | 12 + .../d3-hierarchy/src/treemap/index.js | 94 + .../d3-hierarchy/src/treemap/resquarify.js | 36 + .../d3-hierarchy/src/treemap/round.js | 6 + .../d3-hierarchy/src/treemap/slice.js | 12 + .../d3-hierarchy/src/treemap/sliceDice.js | 6 + .../d3-hierarchy/src/treemap/squarify.js | 66 + frontend/node_modules/d3-interpolate/LICENSE | 13 + .../node_modules/d3-interpolate/README.md | 268 + .../d3-interpolate/dist/d3-interpolate.js | 590 + .../d3-interpolate/dist/d3-interpolate.min.js | 2 + .../node_modules/d3-interpolate/package.json | 53 + .../node_modules/d3-interpolate/src/array.js | 22 + .../node_modules/d3-interpolate/src/basis.js | 19 + .../d3-interpolate/src/basisClosed.js | 13 + .../node_modules/d3-interpolate/src/color.js | 29 + .../d3-interpolate/src/constant.js | 1 + .../d3-interpolate/src/cubehelix.js | 29 + .../node_modules/d3-interpolate/src/date.js | 6 + .../d3-interpolate/src/discrete.js | 6 + .../node_modules/d3-interpolate/src/hcl.js | 21 + .../node_modules/d3-interpolate/src/hsl.js | 21 + .../node_modules/d3-interpolate/src/hue.js | 9 + .../node_modules/d3-interpolate/src/index.js | 21 + .../node_modules/d3-interpolate/src/lab.js | 16 + .../node_modules/d3-interpolate/src/number.js | 5 + .../d3-interpolate/src/numberArray.js | 14 + .../node_modules/d3-interpolate/src/object.js | 23 + .../d3-interpolate/src/piecewise.js | 11 + .../d3-interpolate/src/quantize.js | 5 + .../node_modules/d3-interpolate/src/rgb.js | 55 + .../node_modules/d3-interpolate/src/round.js | 5 + .../node_modules/d3-interpolate/src/string.js | 64 + .../d3-interpolate/src/transform/decompose.js | 26 + .../d3-interpolate/src/transform/index.js | 63 + .../d3-interpolate/src/transform/parse.js | 18 + .../node_modules/d3-interpolate/src/value.js | 22 + .../node_modules/d3-interpolate/src/zoom.js | 71 + frontend/node_modules/d3-path/LICENSE | 13 + frontend/node_modules/d3-path/README.md | 94 + frontend/node_modules/d3-path/dist/d3-path.js | 169 + .../node_modules/d3-path/dist/d3-path.min.js | 2 + frontend/node_modules/d3-path/package.json | 54 + frontend/node_modules/d3-path/src/index.js | 1 + frontend/node_modules/d3-path/src/path.js | 156 + frontend/node_modules/d3-polygon/LICENSE | 13 + frontend/node_modules/d3-polygon/README.md | 52 + .../d3-polygon/dist/d3-polygon.js | 150 + .../d3-polygon/dist/d3-polygon.min.js | 2 + frontend/node_modules/d3-polygon/package.json | 51 + frontend/node_modules/d3-polygon/src/area.js | 15 + .../node_modules/d3-polygon/src/centroid.js | 20 + .../node_modules/d3-polygon/src/contains.js | 16 + frontend/node_modules/d3-polygon/src/cross.js | 7 + frontend/node_modules/d3-polygon/src/hull.js | 49 + frontend/node_modules/d3-polygon/src/index.js | 5 + .../node_modules/d3-polygon/src/length.js | 23 + frontend/node_modules/d3-quadtree/LICENSE | 13 + frontend/node_modules/d3-quadtree/README.md | 181 + .../d3-quadtree/dist/d3-quadtree.js | 419 + .../d3-quadtree/dist/d3-quadtree.min.js | 2 + .../node_modules/d3-quadtree/package.json | 49 + frontend/node_modules/d3-quadtree/src/add.js | 84 + .../node_modules/d3-quadtree/src/cover.js | 43 + frontend/node_modules/d3-quadtree/src/data.js | 7 + .../node_modules/d3-quadtree/src/extent.js | 5 + frontend/node_modules/d3-quadtree/src/find.js | 70 + .../node_modules/d3-quadtree/src/index.js | 1 + frontend/node_modules/d3-quadtree/src/quad.js | 7 + .../node_modules/d3-quadtree/src/quadtree.js | 73 + .../node_modules/d3-quadtree/src/remove.js | 62 + frontend/node_modules/d3-quadtree/src/root.js | 3 + frontend/node_modules/d3-quadtree/src/size.js | 7 + .../node_modules/d3-quadtree/src/visit.js | 16 + .../d3-quadtree/src/visitAfter.js | 21 + frontend/node_modules/d3-quadtree/src/x.js | 7 + frontend/node_modules/d3-quadtree/src/y.js | 7 + frontend/node_modules/d3-random/LICENSE | 13 + frontend/node_modules/d3-random/README.md | 133 + .../node_modules/d3-random/dist/d3-random.js | 358 + .../d3-random/dist/d3-random.min.js | 2 + frontend/node_modules/d3-random/package.json | 51 + frontend/node_modules/d3-random/src/bates.js | 19 + .../node_modules/d3-random/src/bernoulli.js | 14 + frontend/node_modules/d3-random/src/beta.js | 19 + .../node_modules/d3-random/src/binomial.js | 38 + frontend/node_modules/d3-random/src/cauchy.js | 15 + .../d3-random/src/defaultSource.js | 1 + .../node_modules/d3-random/src/exponential.js | 13 + frontend/node_modules/d3-random/src/gamma.js | 34 + .../node_modules/d3-random/src/geometric.js | 17 + frontend/node_modules/d3-random/src/index.js | 18 + frontend/node_modules/d3-random/src/int.js | 16 + .../node_modules/d3-random/src/irwinHall.js | 15 + frontend/node_modules/d3-random/src/lcg.js | 9 + .../node_modules/d3-random/src/logNormal.js | 17 + .../node_modules/d3-random/src/logistic.js | 16 + frontend/node_modules/d3-random/src/normal.js | 28 + frontend/node_modules/d3-random/src/pareto.js | 15 + .../node_modules/d3-random/src/poisson.js | 27 + .../node_modules/d3-random/src/uniform.js | 17 + .../node_modules/d3-random/src/weibull.js | 22 + .../node_modules/d3-scale-chromatic/LICENSE | 28 + .../node_modules/d3-scale-chromatic/README.md | 12 + .../dist/d3-scale-chromatic.js | 522 + .../dist/d3-scale-chromatic.min.js | 2 + .../d3-scale-chromatic/package.json | 55 + .../src/categorical/Accent.js | 3 + .../src/categorical/Dark2.js | 3 + .../src/categorical/Paired.js | 3 + .../src/categorical/Pastel1.js | 3 + .../src/categorical/Pastel2.js | 3 + .../src/categorical/Set1.js | 3 + .../src/categorical/Set2.js | 3 + .../src/categorical/Set3.js | 3 + .../src/categorical/Tableau10.js | 3 + .../src/categorical/category10.js | 3 + .../src/categorical/observable10.js | 3 + .../d3-scale-chromatic/src/colors.js | 5 + .../d3-scale-chromatic/src/diverging/BrBG.js | 16 + .../d3-scale-chromatic/src/diverging/PRGn.js | 16 + .../d3-scale-chromatic/src/diverging/PiYG.js | 16 + .../d3-scale-chromatic/src/diverging/PuOr.js | 16 + .../d3-scale-chromatic/src/diverging/RdBu.js | 16 + .../d3-scale-chromatic/src/diverging/RdGy.js | 16 + .../src/diverging/RdYlBu.js | 16 + .../src/diverging/RdYlGn.js | 16 + .../src/diverging/Spectral.js | 16 + .../d3-scale-chromatic/src/index.js | 44 + .../d3-scale-chromatic/src/ramp.js | 3 + .../d3-scale-chromatic/src/rampClosed.js | 9 + .../src/sequential-multi/BuGn.js | 14 + .../src/sequential-multi/BuPu.js | 14 + .../src/sequential-multi/GnBu.js | 14 + .../src/sequential-multi/OrRd.js | 14 + .../src/sequential-multi/PuBu.js | 14 + .../src/sequential-multi/PuBuGn.js | 14 + .../src/sequential-multi/PuRd.js | 14 + .../src/sequential-multi/RdPu.js | 14 + .../src/sequential-multi/YlGn.js | 14 + .../src/sequential-multi/YlGnBu.js | 14 + .../src/sequential-multi/YlOrBr.js | 14 + .../src/sequential-multi/YlOrRd.js | 14 + .../src/sequential-multi/cividis.js | 8 + .../src/sequential-multi/cubehelix.js | 4 + .../src/sequential-multi/rainbow.js | 17 + .../src/sequential-multi/sinebow.js | 14 + .../src/sequential-multi/turbo.js | 8 + .../src/sequential-multi/viridis.js | 16 + .../src/sequential-single/Blues.js | 14 + .../src/sequential-single/Greens.js | 14 + .../src/sequential-single/Greys.js | 14 + .../src/sequential-single/Oranges.js | 14 + .../src/sequential-single/Purples.js | 14 + .../src/sequential-single/Reds.js | 14 + frontend/node_modules/d3-scale/LICENSE | 13 + frontend/node_modules/d3-scale/README.md | 1003 + .../node_modules/d3-scale/dist/d3-scale.js | 1196 + .../d3-scale/dist/d3-scale.min.js | 2 + frontend/node_modules/d3-scale/package.json | 57 + frontend/node_modules/d3-scale/src/band.js | 101 + frontend/node_modules/d3-scale/src/colors.js | 5 + .../node_modules/d3-scale/src/constant.js | 5 + .../node_modules/d3-scale/src/continuous.js | 125 + .../node_modules/d3-scale/src/diverging.js | 104 + .../node_modules/d3-scale/src/identity.js | 28 + frontend/node_modules/d3-scale/src/index.js | 78 + frontend/node_modules/d3-scale/src/init.js | 26 + frontend/node_modules/d3-scale/src/linear.js | 70 + frontend/node_modules/d3-scale/src/log.js | 140 + frontend/node_modules/d3-scale/src/nice.js | 18 + frontend/node_modules/d3-scale/src/number.js | 3 + frontend/node_modules/d3-scale/src/ordinal.js | 46 + frontend/node_modules/d3-scale/src/pow.js | 50 + .../node_modules/d3-scale/src/quantile.js | 57 + .../node_modules/d3-scale/src/quantize.js | 56 + frontend/node_modules/d3-scale/src/radial.js | 63 + .../node_modules/d3-scale/src/sequential.js | 107 + .../d3-scale/src/sequentialQuantile.js | 38 + frontend/node_modules/d3-scale/src/symlog.js | 35 + .../node_modules/d3-scale/src/threshold.js | 39 + .../node_modules/d3-scale/src/tickFormat.js | 29 + frontend/node_modules/d3-scale/src/time.js | 71 + frontend/node_modules/d3-scale/src/utcTime.js | 8 + frontend/node_modules/d3-selection/LICENSE | 13 + frontend/node_modules/d3-selection/README.md | 863 + .../d3-selection/dist/d3-selection.js | 1022 + .../d3-selection/dist/d3-selection.min.js | 2 + .../node_modules/d3-selection/package.json | 51 + .../node_modules/d3-selection/src/array.js | 9 + .../node_modules/d3-selection/src/constant.js | 5 + .../node_modules/d3-selection/src/create.js | 6 + .../node_modules/d3-selection/src/creator.js | 25 + .../node_modules/d3-selection/src/identity.js | 3 + .../node_modules/d3-selection/src/index.js | 15 + .../node_modules/d3-selection/src/local.js | 27 + .../node_modules/d3-selection/src/matcher.js | 12 + .../d3-selection/src/namespace.js | 7 + .../d3-selection/src/namespaces.js | 9 + .../node_modules/d3-selection/src/pointer.js | 20 + .../node_modules/d3-selection/src/pointers.js | 11 + .../node_modules/d3-selection/src/select.js | 7 + .../d3-selection/src/selectAll.js | 8 + .../d3-selection/src/selection/append.js | 8 + .../d3-selection/src/selection/attr.js | 57 + .../d3-selection/src/selection/call.js | 6 + .../d3-selection/src/selection/classed.js | 75 + .../d3-selection/src/selection/clone.js | 13 + .../d3-selection/src/selection/data.js | 128 + .../d3-selection/src/selection/datum.js | 5 + .../d3-selection/src/selection/dispatch.js | 34 + .../d3-selection/src/selection/each.js | 10 + .../d3-selection/src/selection/empty.js | 3 + .../d3-selection/src/selection/enter.js | 22 + .../d3-selection/src/selection/exit.js | 6 + .../d3-selection/src/selection/filter.js | 16 + .../d3-selection/src/selection/html.js | 25 + .../d3-selection/src/selection/index.js | 90 + .../d3-selection/src/selection/insert.js | 14 + .../d3-selection/src/selection/iterator.js | 7 + .../d3-selection/src/selection/join.js | 15 + .../d3-selection/src/selection/lower.js | 7 + .../d3-selection/src/selection/merge.js | 19 + .../d3-selection/src/selection/node.js | 11 + .../d3-selection/src/selection/nodes.js | 3 + .../d3-selection/src/selection/on.js | 67 + .../d3-selection/src/selection/order.js | 13 + .../d3-selection/src/selection/property.js | 28 + .../d3-selection/src/selection/raise.js | 7 + .../d3-selection/src/selection/remove.js | 8 + .../d3-selection/src/selection/select.js | 17 + .../d3-selection/src/selection/selectAll.js | 25 + .../d3-selection/src/selection/selectChild.js | 18 + .../src/selection/selectChildren.js | 18 + .../d3-selection/src/selection/size.js | 5 + .../d3-selection/src/selection/sort.js | 24 + .../d3-selection/src/selection/sparse.js | 3 + .../d3-selection/src/selection/style.js | 35 + .../d3-selection/src/selection/text.js | 25 + .../node_modules/d3-selection/src/selector.js | 7 + .../d3-selection/src/selectorAll.js | 9 + .../d3-selection/src/sourceEvent.js | 5 + .../node_modules/d3-selection/src/window.js | 5 + frontend/node_modules/d3-shape/LICENSE | 13 + frontend/node_modules/d3-shape/README.md | 1227 + .../node_modules/d3-shape/dist/d3-shape.js | 2141 ++ .../d3-shape/dist/d3-shape.min.js | 2 + frontend/node_modules/d3-shape/package.json | 55 + frontend/node_modules/d3-shape/src/arc.js | 268 + frontend/node_modules/d3-shape/src/area.js | 112 + .../node_modules/d3-shape/src/areaRadial.js | 29 + frontend/node_modules/d3-shape/src/array.js | 7 + .../node_modules/d3-shape/src/constant.js | 5 + .../node_modules/d3-shape/src/curve/basis.js | 51 + .../d3-shape/src/curve/basisClosed.js | 52 + .../d3-shape/src/curve/basisOpen.js | 39 + .../node_modules/d3-shape/src/curve/bump.js | 75 + .../node_modules/d3-shape/src/curve/bundle.js | 56 + .../d3-shape/src/curve/cardinal.js | 61 + .../d3-shape/src/curve/cardinalClosed.js | 61 + .../d3-shape/src/curve/cardinalOpen.js | 49 + .../d3-shape/src/curve/catmullRom.js | 88 + .../d3-shape/src/curve/catmullRomClosed.js | 74 + .../d3-shape/src/curve/catmullRomOpen.js | 62 + .../node_modules/d3-shape/src/curve/linear.js | 31 + .../d3-shape/src/curve/linearClosed.js | 25 + .../d3-shape/src/curve/monotone.js | 104 + .../d3-shape/src/curve/natural.js | 65 + .../node_modules/d3-shape/src/curve/radial.js | 36 + .../node_modules/d3-shape/src/curve/step.js | 53 + .../node_modules/d3-shape/src/descending.js | 3 + .../node_modules/d3-shape/src/identity.js | 3 + frontend/node_modules/d3-shape/src/index.js | 53 + frontend/node_modules/d3-shape/src/line.js | 58 + .../node_modules/d3-shape/src/lineRadial.js | 19 + frontend/node_modules/d3-shape/src/link.js | 73 + frontend/node_modules/d3-shape/src/math.js | 20 + frontend/node_modules/d3-shape/src/noop.js | 1 + .../d3-shape/src/offset/diverging.js | 14 + .../d3-shape/src/offset/expand.js | 10 + .../node_modules/d3-shape/src/offset/none.js | 9 + .../d3-shape/src/offset/silhouette.js | 10 + .../d3-shape/src/offset/wiggle.js | 24 + .../d3-shape/src/order/appearance.js | 12 + .../d3-shape/src/order/ascending.js | 12 + .../d3-shape/src/order/descending.js | 5 + .../d3-shape/src/order/insideOut.js | 27 + .../node_modules/d3-shape/src/order/none.js | 5 + .../d3-shape/src/order/reverse.js | 5 + frontend/node_modules/d3-shape/src/path.js | 19 + frontend/node_modules/d3-shape/src/pie.js | 80 + frontend/node_modules/d3-shape/src/point.js | 7 + .../node_modules/d3-shape/src/pointRadial.js | 3 + frontend/node_modules/d3-shape/src/stack.js | 58 + frontend/node_modules/d3-shape/src/symbol.js | 66 + .../d3-shape/src/symbol/asterisk.js | 17 + .../d3-shape/src/symbol/circle.js | 9 + .../node_modules/d3-shape/src/symbol/cross.js | 20 + .../d3-shape/src/symbol/diamond.js | 16 + .../d3-shape/src/symbol/diamond2.js | 12 + .../node_modules/d3-shape/src/symbol/plus.js | 11 + .../d3-shape/src/symbol/square.js | 9 + .../d3-shape/src/symbol/square2.js | 12 + .../node_modules/d3-shape/src/symbol/star.js | 24 + .../node_modules/d3-shape/src/symbol/times.js | 11 + .../d3-shape/src/symbol/triangle.js | 13 + .../d3-shape/src/symbol/triangle2.js | 15 + .../node_modules/d3-shape/src/symbol/wye.js | 25 + frontend/node_modules/d3-time-format/LICENSE | 13 + .../node_modules/d3-time-format/README.md | 209 + .../d3-time-format/dist/d3-time-format.js | 745 + .../d3-time-format/dist/d3-time-format.min.js | 2 + .../d3-time-format/locale/ar-EG.json | 10 + .../d3-time-format/locale/ar-SY.json | 10 + .../d3-time-format/locale/ca-ES.json | 10 + .../d3-time-format/locale/cs-CZ.json | 10 + .../d3-time-format/locale/da-DK.json | 10 + .../d3-time-format/locale/de-CH.json | 10 + .../d3-time-format/locale/de-DE.json | 10 + .../d3-time-format/locale/en-CA.json | 10 + .../d3-time-format/locale/en-GB.json | 10 + .../d3-time-format/locale/en-US.json | 10 + .../d3-time-format/locale/es-ES.json | 10 + .../d3-time-format/locale/es-MX.json | 10 + .../d3-time-format/locale/fa-IR.json | 10 + .../d3-time-format/locale/fi-FI.json | 10 + .../d3-time-format/locale/fr-CA.json | 10 + .../d3-time-format/locale/fr-FR.json | 10 + .../d3-time-format/locale/he-IL.json | 10 + .../d3-time-format/locale/hr-HR.json | 10 + .../d3-time-format/locale/hu-HU.json | 10 + .../d3-time-format/locale/it-IT.json | 10 + .../d3-time-format/locale/ja-JP.json | 10 + .../d3-time-format/locale/ko-KR.json | 10 + .../d3-time-format/locale/mk-MK.json | 10 + .../d3-time-format/locale/nb-NO.json | 10 + .../d3-time-format/locale/nl-BE.json | 10 + .../d3-time-format/locale/nl-NL.json | 10 + .../d3-time-format/locale/pl-PL.json | 10 + .../d3-time-format/locale/pt-BR.json | 10 + .../d3-time-format/locale/ru-RU.json | 10 + .../d3-time-format/locale/sv-SE.json | 10 + .../d3-time-format/locale/tr-TR.json | 10 + .../d3-time-format/locale/uk-UA.json | 10 + .../d3-time-format/locale/zh-CN.json | 10 + .../d3-time-format/locale/zh-TW.json | 10 + .../node_modules/d3-time-format/package.json | 60 + .../d3-time-format/src/defaultLocale.js | 27 + .../node_modules/d3-time-format/src/index.js | 4 + .../d3-time-format/src/isoFormat.js | 13 + .../d3-time-format/src/isoParse.js | 13 + .../node_modules/d3-time-format/src/locale.js | 697 + frontend/node_modules/d3-time/LICENSE | 13 + frontend/node_modules/d3-time/README.md | 380 + frontend/node_modules/d3-time/dist/d3-time.js | 445 + .../node_modules/d3-time/dist/d3-time.min.js | 2 + frontend/node_modules/d3-time/package.json | 53 + frontend/node_modules/d3-time/src/day.js | 35 + frontend/node_modules/d3-time/src/duration.js | 7 + frontend/node_modules/d3-time/src/hour.js | 26 + frontend/node_modules/d3-time/src/index.js | 96 + frontend/node_modules/d3-time/src/interval.js | 69 + .../node_modules/d3-time/src/millisecond.js | 25 + frontend/node_modules/d3-time/src/minute.js | 26 + frontend/node_modules/d3-time/src/month.js | 27 + frontend/node_modules/d3-time/src/second.js | 14 + frontend/node_modules/d3-time/src/ticks.js | 58 + frontend/node_modules/d3-time/src/week.js | 56 + frontend/node_modules/d3-time/src/year.js | 49 + frontend/node_modules/d3-timer/LICENSE | 13 + frontend/node_modules/d3-timer/README.md | 87 + .../node_modules/d3-timer/dist/d3-timer.js | 153 + .../d3-timer/dist/d3-timer.min.js | 2 + frontend/node_modules/d3-timer/package.json | 53 + frontend/node_modules/d3-timer/src/index.js | 13 + .../node_modules/d3-timer/src/interval.js | 17 + frontend/node_modules/d3-timer/src/timeout.js | 11 + frontend/node_modules/d3-timer/src/timer.js | 110 + frontend/node_modules/d3-transition/LICENSE | 13 + frontend/node_modules/d3-transition/README.md | 490 + .../d3-transition/dist/d3-transition.js | 900 + .../d3-transition/dist/d3-transition.min.js | 2 + .../node_modules/d3-transition/package.json | 65 + .../node_modules/d3-transition/src/active.js | 21 + .../node_modules/d3-transition/src/index.js | 4 + .../d3-transition/src/interrupt.js | 24 + .../d3-transition/src/selection/index.js | 6 + .../d3-transition/src/selection/interrupt.js | 7 + .../d3-transition/src/selection/transition.js | 42 + .../d3-transition/src/transition/attr.js | 78 + .../d3-transition/src/transition/attrTween.js | 44 + .../d3-transition/src/transition/delay.js | 23 + .../d3-transition/src/transition/duration.js | 23 + .../d3-transition/src/transition/ease.js | 16 + .../src/transition/easeVarying.js | 14 + .../d3-transition/src/transition/end.js | 29 + .../d3-transition/src/transition/filter.js | 16 + .../d3-transition/src/transition/index.js | 73 + .../src/transition/interpolate.js | 10 + .../d3-transition/src/transition/merge.js | 19 + .../d3-transition/src/transition/on.js | 32 + .../d3-transition/src/transition/remove.js | 11 + .../d3-transition/src/transition/schedule.js | 153 + .../d3-transition/src/transition/select.js | 22 + .../d3-transition/src/transition/selectAll.js | 26 + .../d3-transition/src/transition/selection.js | 7 + .../d3-transition/src/transition/style.js | 80 + .../src/transition/styleTween.js | 24 + .../d3-transition/src/transition/text.js | 20 + .../d3-transition/src/transition/textTween.js | 24 + .../src/transition/transition.js | 24 + .../d3-transition/src/transition/tween.js | 81 + frontend/node_modules/d3-zoom/LICENSE | 13 + frontend/node_modules/d3-zoom/README.md | 414 + frontend/node_modules/d3-zoom/dist/d3-zoom.js | 531 + .../node_modules/d3-zoom/dist/d3-zoom.min.js | 2 + frontend/node_modules/d3-zoom/package.json | 57 + frontend/node_modules/d3-zoom/src/constant.js | 1 + frontend/node_modules/d3-zoom/src/event.js | 14 + frontend/node_modules/d3-zoom/src/index.js | 2 + frontend/node_modules/d3-zoom/src/noevent.js | 8 + .../node_modules/d3-zoom/src/transform.js | 51 + frontend/node_modules/d3-zoom/src/zoom.js | 447 + frontend/node_modules/d3/LICENSE | 13 + frontend/node_modules/d3/README.md | 12 + frontend/node_modules/d3/dist/d3.js | 20625 ++++++++++++++++ frontend/node_modules/d3/dist/d3.min.js | 2 + frontend/node_modules/d3/package.json | 92 + frontend/node_modules/d3/src/index.js | 30 + frontend/node_modules/delaunator/LICENSE | 15 + frontend/node_modules/delaunator/README.md | 141 + .../node_modules/delaunator/delaunator.js | 753 + .../node_modules/delaunator/delaunator.min.js | 1 + frontend/node_modules/delaunator/index.js | 480 + frontend/node_modules/delaunator/package.json | 56 + frontend/node_modules/dom-serializer/LICENSE | 11 + .../node_modules/dom-serializer/README.md | 109 + .../dom-serializer/lib/esm/foreignNames.d.ts | 3 + .../lib/esm/foreignNames.d.ts.map | 1 + .../dom-serializer/lib/esm/foreignNames.js | 100 + .../dom-serializer/lib/esm/index.d.ts | 52 + .../dom-serializer/lib/esm/index.d.ts.map | 1 + .../dom-serializer/lib/esm/index.js | 190 + .../dom-serializer/lib/esm/package.json | 1 + .../dom-serializer/lib/foreignNames.d.ts | 3 + .../dom-serializer/lib/foreignNames.d.ts.map | 1 + .../dom-serializer/lib/foreignNames.js | 103 + .../dom-serializer/lib/index.d.ts | 52 + .../dom-serializer/lib/index.d.ts.map | 1 + .../node_modules/dom-serializer/lib/index.js | 229 + .../node_modules/dom-serializer/package.json | 69 + frontend/node_modules/domelementtype/LICENSE | 11 + .../domelementtype/lib/esm/index.d.ts | 48 + .../domelementtype/lib/esm/index.d.ts.map | 1 + .../domelementtype/lib/esm/index.js | 51 + .../domelementtype/lib/esm/package.json | 1 + .../domelementtype/lib/index.d.ts | 48 + .../domelementtype/lib/index.d.ts.map | 1 + .../node_modules/domelementtype/lib/index.js | 55 + .../node_modules/domelementtype/package.json | 54 + .../node_modules/domelementtype/readme.md | 1 + frontend/node_modules/domhandler/LICENSE | 11 + .../domhandler/lib/esm/index.d.ts | 76 + .../domhandler/lib/esm/index.d.ts.map | 1 + .../node_modules/domhandler/lib/esm/index.js | 146 + .../node_modules/domhandler/lib/esm/node.d.ts | 245 + .../domhandler/lib/esm/node.d.ts.map | 1 + .../node_modules/domhandler/lib/esm/node.js | 338 + .../domhandler/lib/esm/package.json | 1 + .../node_modules/domhandler/lib/index.d.ts | 76 + .../domhandler/lib/index.d.ts.map | 1 + frontend/node_modules/domhandler/lib/index.js | 165 + .../node_modules/domhandler/lib/node.d.ts | 245 + .../node_modules/domhandler/lib/node.d.ts.map | 1 + frontend/node_modules/domhandler/lib/node.js | 474 + frontend/node_modules/domhandler/package.json | 73 + frontend/node_modules/domhandler/readme.md | 92 + frontend/node_modules/domutils/LICENSE | 11 + .../node_modules/domutils/lib/esm/feeds.d.ts | 71 + .../domutils/lib/esm/feeds.d.ts.map | 1 + .../node_modules/domutils/lib/esm/feeds.js | 183 + .../domutils/lib/esm/feeds.js.map | 1 + .../domutils/lib/esm/helpers.d.ts | 59 + .../domutils/lib/esm/helpers.d.ts.map | 1 + .../node_modules/domutils/lib/esm/helpers.js | 136 + .../domutils/lib/esm/helpers.js.map | 1 + .../node_modules/domutils/lib/esm/index.d.ts | 10 + .../domutils/lib/esm/index.d.ts.map | 1 + .../node_modules/domutils/lib/esm/index.js | 10 + .../domutils/lib/esm/index.js.map | 1 + .../node_modules/domutils/lib/esm/legacy.d.ts | 79 + .../domutils/lib/esm/legacy.d.ts.map | 1 + .../node_modules/domutils/lib/esm/legacy.js | 152 + .../domutils/lib/esm/legacy.js.map | 1 + .../domutils/lib/esm/manipulation.d.ts | 49 + .../domutils/lib/esm/manipulation.d.ts.map | 1 + .../domutils/lib/esm/manipulation.js | 134 + .../domutils/lib/esm/manipulation.js.map | 1 + .../domutils/lib/esm/package.json | 1 + .../domutils/lib/esm/querying.d.ts | 64 + .../domutils/lib/esm/querying.d.ts.map | 1 + .../node_modules/domutils/lib/esm/querying.js | 142 + .../domutils/lib/esm/querying.js.map | 1 + .../domutils/lib/esm/stringify.d.ts | 46 + .../domutils/lib/esm/stringify.d.ts.map | 1 + .../domutils/lib/esm/stringify.js | 81 + .../domutils/lib/esm/stringify.js.map | 1 + .../domutils/lib/esm/traversal.d.ts | 67 + .../domutils/lib/esm/traversal.d.ts.map | 1 + .../domutils/lib/esm/traversal.js | 112 + .../domutils/lib/esm/traversal.js.map | 1 + frontend/node_modules/domutils/lib/feeds.d.ts | 71 + .../node_modules/domutils/lib/feeds.d.ts.map | 1 + frontend/node_modules/domutils/lib/feeds.js | 190 + .../node_modules/domutils/lib/feeds.js.map | 1 + .../node_modules/domutils/lib/helpers.d.ts | 59 + .../domutils/lib/helpers.d.ts.map | 1 + frontend/node_modules/domutils/lib/helpers.js | 142 + .../node_modules/domutils/lib/helpers.js.map | 1 + frontend/node_modules/domutils/lib/index.d.ts | 10 + .../node_modules/domutils/lib/index.d.ts.map | 1 + frontend/node_modules/domutils/lib/index.js | 33 + .../node_modules/domutils/lib/index.js.map | 1 + .../node_modules/domutils/lib/legacy.d.ts | 79 + .../node_modules/domutils/lib/legacy.d.ts.map | 1 + frontend/node_modules/domutils/lib/legacy.js | 168 + .../node_modules/domutils/lib/legacy.js.map | 1 + .../domutils/lib/manipulation.d.ts | 49 + .../domutils/lib/manipulation.d.ts.map | 1 + .../node_modules/domutils/lib/manipulation.js | 142 + .../domutils/lib/manipulation.js.map | 1 + .../node_modules/domutils/lib/querying.d.ts | 64 + .../domutils/lib/querying.d.ts.map | 1 + .../node_modules/domutils/lib/querying.js | 155 + .../node_modules/domutils/lib/querying.js.map | 1 + .../node_modules/domutils/lib/stringify.d.ts | 46 + .../domutils/lib/stringify.d.ts.map | 1 + .../node_modules/domutils/lib/stringify.js | 91 + .../domutils/lib/stringify.js.map | 1 + .../node_modules/domutils/lib/traversal.d.ts | 67 + .../domutils/lib/traversal.d.ts.map | 1 + .../node_modules/domutils/lib/traversal.js | 125 + .../domutils/lib/traversal.js.map | 1 + frontend/node_modules/domutils/package.json | 79 + frontend/node_modules/domutils/readme.md | 31 + .../node_modules/encoding-sniffer/LICENSE | 18 + .../node_modules/encoding-sniffer/README.md | 68 + .../encoding-sniffer/dist/commonjs/index.d.ts | 31 + .../dist/commonjs/index.d.ts.map | 1 + .../encoding-sniffer/dist/commonjs/index.js | 72 + .../dist/commonjs/index.js.map | 1 + .../dist/commonjs/package.json | 3 + .../dist/commonjs/sniffer.d.ts | 148 + .../dist/commonjs/sniffer.d.ts.map | 1 + .../encoding-sniffer/dist/commonjs/sniffer.js | 990 + .../dist/commonjs/sniffer.js.map | 1 + .../encoding-sniffer/dist/esm/index.d.ts | 31 + .../encoding-sniffer/dist/esm/index.d.ts.map | 1 + .../encoding-sniffer/dist/esm/index.js | 63 + .../encoding-sniffer/dist/esm/index.js.map | 1 + .../encoding-sniffer/dist/esm/package.json | 3 + .../encoding-sniffer/dist/esm/sniffer.d.ts | 148 + .../dist/esm/sniffer.d.ts.map | 1 + .../encoding-sniffer/dist/esm/sniffer.js | 985 + .../encoding-sniffer/dist/esm/sniffer.js.map | 1 + .../encoding-sniffer/package.json | 94 + .../encoding-sniffer/sniffer.d.ts | 2 + .../node_modules/encoding-sniffer/sniffer.js | 3 + frontend/node_modules/highlight.js/CHANGES.md | 3556 +++ frontend/node_modules/highlight.js/LICENSE | 29 + frontend/node_modules/highlight.js/README.md | 521 + .../node_modules/highlight.js/SECURITY.md | 19 + .../highlight.js/SUPPORTED_LANGUAGES.md | 283 + .../highlight.js/VERSION_10_UPGRADE.md | 58 + .../highlight.js/VERSION_11_UPGRADE.md | 203 + .../node_modules/highlight.js/es/common.d.ts | 3 + .../node_modules/highlight.js/es/common.js | 4 + .../node_modules/highlight.js/es/core.d.ts | 3 + frontend/node_modules/highlight.js/es/core.js | 4 + .../node_modules/highlight.js/es/index.js | 4 + .../highlight.js/es/languages/1c.js | 544 + .../highlight.js/es/languages/1c.js.js | 11 + .../highlight.js/es/languages/abnf.js | 83 + .../highlight.js/es/languages/abnf.js.js | 11 + .../highlight.js/es/languages/accesslog.js | 92 + .../highlight.js/es/languages/accesslog.js.js | 11 + .../highlight.js/es/languages/actionscript.js | 153 + .../es/languages/actionscript.js.js | 11 + .../highlight.js/es/languages/ada.js | 265 + .../highlight.js/es/languages/ada.js.js | 11 + .../highlight.js/es/languages/angelscript.js | 178 + .../es/languages/angelscript.js.js | 11 + .../highlight.js/es/languages/apache.js | 105 + .../highlight.js/es/languages/apache.js.js | 11 + .../highlight.js/es/languages/applescript.js | 149 + .../es/languages/applescript.js.js | 11 + .../highlight.js/es/languages/arcade.js | 428 + .../highlight.js/es/languages/arcade.js.js | 11 + .../highlight.js/es/languages/arduino.js | 1008 + .../highlight.js/es/languages/arduino.js.js | 11 + .../highlight.js/es/languages/armasm.js | 124 + .../highlight.js/es/languages/armasm.js.js | 11 + .../highlight.js/es/languages/asciidoc.js | 261 + .../highlight.js/es/languages/asciidoc.js.js | 11 + .../highlight.js/es/languages/aspectj.js | 231 + .../highlight.js/es/languages/aspectj.js.js | 11 + .../highlight.js/es/languages/autohotkey.js | 75 + .../es/languages/autohotkey.js.js | 11 + .../highlight.js/es/languages/autoit.js | 178 + .../highlight.js/es/languages/autoit.js.js | 11 + .../highlight.js/es/languages/avrasm.js | 78 + .../highlight.js/es/languages/avrasm.js.js | 11 + .../highlight.js/es/languages/awk.js | 68 + .../highlight.js/es/languages/awk.js.js | 11 + .../highlight.js/es/languages/axapta.js | 188 + .../highlight.js/es/languages/axapta.js.js | 11 + .../highlight.js/es/languages/bash.js | 409 + .../highlight.js/es/languages/bash.js.js | 11 + .../highlight.js/es/languages/basic.js | 236 + .../highlight.js/es/languages/basic.js.js | 11 + .../highlight.js/es/languages/bnf.js | 39 + .../highlight.js/es/languages/bnf.js.js | 11 + .../highlight.js/es/languages/brainfuck.js | 54 + .../highlight.js/es/languages/brainfuck.js.js | 11 + .../highlight.js/es/languages/c.js | 333 + .../highlight.js/es/languages/c.js.js | 11 + .../highlight.js/es/languages/cal.js | 160 + .../highlight.js/es/languages/cal.js.js | 11 + .../highlight.js/es/languages/capnproto.js | 99 + .../highlight.js/es/languages/capnproto.js.js | 11 + .../highlight.js/es/languages/ceylon.js | 140 + .../highlight.js/es/languages/ceylon.js.js | 11 + .../highlight.js/es/languages/clean.js | 67 + .../highlight.js/es/languages/clean.js.js | 11 + .../highlight.js/es/languages/clojure-repl.js | 27 + .../es/languages/clojure-repl.js.js | 11 + .../highlight.js/es/languages/clojure.js | 184 + .../highlight.js/es/languages/clojure.js.js | 11 + .../highlight.js/es/languages/cmake.js | 64 + .../highlight.js/es/languages/cmake.js.js | 11 + .../highlight.js/es/languages/coffeescript.js | 368 + .../es/languages/coffeescript.js.js | 11 + .../highlight.js/es/languages/coq.js | 445 + .../highlight.js/es/languages/coq.js.js | 11 + .../highlight.js/es/languages/cos.js | 140 + .../highlight.js/es/languages/cos.js.js | 11 + .../highlight.js/es/languages/cpp.js | 605 + .../highlight.js/es/languages/cpp.js.js | 11 + .../highlight.js/es/languages/crmsh.js | 100 + .../highlight.js/es/languages/crmsh.js.js | 11 + .../highlight.js/es/languages/crystal.js | 312 + .../highlight.js/es/languages/crystal.js.js | 11 + .../highlight.js/es/languages/csharp.js | 412 + .../highlight.js/es/languages/csharp.js.js | 11 + .../highlight.js/es/languages/csp.js | 58 + .../highlight.js/es/languages/csp.js.js | 11 + .../highlight.js/es/languages/css.js | 949 + .../highlight.js/es/languages/css.js.js | 11 + .../highlight.js/es/languages/d.js | 272 + .../highlight.js/es/languages/d.js.js | 11 + .../highlight.js/es/languages/dart.js | 271 + .../highlight.js/es/languages/dart.js.js | 11 + .../highlight.js/es/languages/delphi.js | 246 + .../highlight.js/es/languages/delphi.js.js | 11 + .../highlight.js/es/languages/diff.js | 62 + .../highlight.js/es/languages/diff.js.js | 11 + .../highlight.js/es/languages/django.js | 75 + .../highlight.js/es/languages/django.js.js | 11 + .../highlight.js/es/languages/dns.js | 78 + .../highlight.js/es/languages/dns.js.js | 11 + .../highlight.js/es/languages/dockerfile.js | 44 + .../es/languages/dockerfile.js.js | 11 + .../highlight.js/es/languages/dos.js | 167 + .../highlight.js/es/languages/dos.js.js | 11 + .../highlight.js/es/languages/dsconfig.js | 66 + .../highlight.js/es/languages/dsconfig.js.js | 11 + .../highlight.js/es/languages/dts.js | 157 + .../highlight.js/es/languages/dts.js.js | 11 + .../highlight.js/es/languages/dust.js | 47 + .../highlight.js/es/languages/dust.js.js | 11 + .../highlight.js/es/languages/ebnf.js | 54 + .../highlight.js/es/languages/ebnf.js.js | 11 + .../highlight.js/es/languages/elixir.js | 279 + .../highlight.js/es/languages/elixir.js.js | 11 + .../highlight.js/es/languages/elm.js | 143 + .../highlight.js/es/languages/elm.js.js | 11 + .../highlight.js/es/languages/erb.js | 29 + .../highlight.js/es/languages/erb.js.js | 11 + .../highlight.js/es/languages/erlang-repl.js | 54 + .../es/languages/erlang-repl.js.js | 11 + .../highlight.js/es/languages/erlang.js | 235 + .../highlight.js/es/languages/erlang.js.js | 11 + .../highlight.js/es/languages/excel.js | 580 + .../highlight.js/es/languages/excel.js.js | 11 + .../highlight.js/es/languages/fix.js | 39 + .../highlight.js/es/languages/fix.js.js | 11 + .../highlight.js/es/languages/flix.js | 79 + .../highlight.js/es/languages/flix.js.js | 11 + .../highlight.js/es/languages/fortran.js | 574 + .../highlight.js/es/languages/fortran.js.js | 11 + .../highlight.js/es/languages/fsharp.js | 627 + .../highlight.js/es/languages/fsharp.js.js | 11 + .../highlight.js/es/languages/gams.js | 181 + .../highlight.js/es/languages/gams.js.js | 11 + .../highlight.js/es/languages/gauss.js | 306 + .../highlight.js/es/languages/gauss.js.js | 11 + .../highlight.js/es/languages/gcode.js | 189 + .../highlight.js/es/languages/gcode.js.js | 11 + .../highlight.js/es/languages/gherkin.js | 49 + .../highlight.js/es/languages/gherkin.js.js | 11 + .../highlight.js/es/languages/glsl.js | 128 + .../highlight.js/es/languages/glsl.js.js | 11 + .../highlight.js/es/languages/gml.js | 3130 +++ .../highlight.js/es/languages/gml.js.js | 11 + .../highlight.js/es/languages/go.js | 156 + .../highlight.js/es/languages/go.js.js | 11 + .../highlight.js/es/languages/golo.js | 81 + .../highlight.js/es/languages/golo.js.js | 11 + .../highlight.js/es/languages/gradle.js | 190 + .../highlight.js/es/languages/gradle.js.js | 11 + .../highlight.js/es/languages/graphql.js | 78 + .../highlight.js/es/languages/graphql.js.js | 11 + .../highlight.js/es/languages/groovy.js | 190 + .../highlight.js/es/languages/groovy.js.js | 11 + .../highlight.js/es/languages/haml.js | 113 + .../highlight.js/es/languages/haml.js.js | 11 + .../highlight.js/es/languages/handlebars.js | 258 + .../es/languages/handlebars.js.js | 11 + .../highlight.js/es/languages/haskell.js | 217 + .../highlight.js/es/languages/haskell.js.js | 11 + .../highlight.js/es/languages/haxe.js | 167 + .../highlight.js/es/languages/haxe.js.js | 11 + .../highlight.js/es/languages/hsp.js | 59 + .../highlight.js/es/languages/hsp.js.js | 11 + .../highlight.js/es/languages/http.js | 97 + .../highlight.js/es/languages/http.js.js | 11 + .../highlight.js/es/languages/hy.js | 137 + .../highlight.js/es/languages/hy.js.js | 11 + .../highlight.js/es/languages/inform7.js | 70 + .../highlight.js/es/languages/inform7.js.js | 11 + .../highlight.js/es/languages/ini.js | 121 + .../highlight.js/es/languages/ini.js.js | 11 + .../highlight.js/es/languages/irpf90.js | 107 + .../highlight.js/es/languages/irpf90.js.js | 11 + .../highlight.js/es/languages/isbl.js | 3205 +++ .../highlight.js/es/languages/isbl.js.js | 11 + .../highlight.js/es/languages/java.js | 291 + .../highlight.js/es/languages/java.js.js | 11 + .../highlight.js/es/languages/javascript.js | 769 + .../es/languages/javascript.js.js | 11 + .../highlight.js/es/languages/jboss-cli.js | 63 + .../highlight.js/es/languages/jboss-cli.js.js | 11 + .../highlight.js/es/languages/json.js | 54 + .../highlight.js/es/languages/json.js.js | 11 + .../highlight.js/es/languages/julia-repl.js | 51 + .../es/languages/julia-repl.js.js | 11 + .../highlight.js/es/languages/julia.js | 442 + .../highlight.js/es/languages/julia.js.js | 11 + .../highlight.js/es/languages/kotlin.js | 286 + .../highlight.js/es/languages/kotlin.js.js | 11 + .../highlight.js/es/languages/lasso.js | 171 + .../highlight.js/es/languages/lasso.js.js | 11 + .../highlight.js/es/languages/latex.js | 278 + .../highlight.js/es/languages/latex.js.js | 11 + .../highlight.js/es/languages/ldif.js | 31 + .../highlight.js/es/languages/ldif.js.js | 11 + .../highlight.js/es/languages/leaf.js | 97 + .../highlight.js/es/languages/leaf.js.js | 11 + .../highlight.js/es/languages/less.js | 1050 + .../highlight.js/es/languages/less.js.js | 11 + .../highlight.js/es/languages/lisp.js | 139 + .../highlight.js/es/languages/lisp.js.js | 11 + .../es/languages/livecodeserver.js | 173 + .../es/languages/livecodeserver.js.js | 11 + .../highlight.js/es/languages/livescript.js | 380 + .../es/languages/livescript.js.js | 11 + .../highlight.js/es/languages/llvm.js | 135 + .../highlight.js/es/languages/llvm.js.js | 11 + .../highlight.js/es/languages/lsl.js | 76 + .../highlight.js/es/languages/lsl.js.js | 11 + .../highlight.js/es/languages/lua.js | 81 + .../highlight.js/es/languages/lua.js.js | 11 + .../highlight.js/es/languages/makefile.js | 89 + .../highlight.js/es/languages/makefile.js.js | 11 + .../highlight.js/es/languages/markdown.js | 248 + .../highlight.js/es/languages/markdown.js.js | 11 + .../highlight.js/es/languages/mathematica.js | 7359 ++++++ .../es/languages/mathematica.js.js | 11 + .../highlight.js/es/languages/matlab.js | 107 + .../highlight.js/es/languages/matlab.js.js | 11 + .../highlight.js/es/languages/maxima.js | 414 + .../highlight.js/es/languages/maxima.js.js | 11 + .../highlight.js/es/languages/mel.js | 235 + .../highlight.js/es/languages/mel.js.js | 11 + .../highlight.js/es/languages/mercury.js | 108 + .../highlight.js/es/languages/mercury.js.js | 11 + .../highlight.js/es/languages/mipsasm.js | 104 + .../highlight.js/es/languages/mipsasm.js.js | 11 + .../highlight.js/es/languages/mizar.js | 27 + .../highlight.js/es/languages/mizar.js.js | 11 + .../highlight.js/es/languages/mojolicious.js | 36 + .../es/languages/mojolicious.js.js | 11 + .../highlight.js/es/languages/monkey.js | 184 + .../highlight.js/es/languages/monkey.js.js | 11 + .../highlight.js/es/languages/moonscript.js | 141 + .../es/languages/moonscript.js.js | 11 + .../highlight.js/es/languages/n1ql.js | 365 + .../highlight.js/es/languages/n1ql.js.js | 11 + .../highlight.js/es/languages/nestedtext.js | 83 + .../es/languages/nestedtext.js.js | 11 + .../highlight.js/es/languages/nginx.js | 153 + .../highlight.js/es/languages/nginx.js.js | 11 + .../highlight.js/es/languages/nim.js | 187 + .../highlight.js/es/languages/nim.js.js | 11 + .../highlight.js/es/languages/nix.js | 372 + .../highlight.js/es/languages/nix.js.js | 11 + .../highlight.js/es/languages/node-repl.js | 33 + .../highlight.js/es/languages/node-repl.js.js | 11 + .../highlight.js/es/languages/nsis.js | 557 + .../highlight.js/es/languages/nsis.js.js | 11 + .../highlight.js/es/languages/objectivec.js | 253 + .../es/languages/objectivec.js.js | 11 + .../highlight.js/es/languages/ocaml.js | 83 + .../highlight.js/es/languages/ocaml.js.js | 11 + .../highlight.js/es/languages/openscad.js | 77 + .../highlight.js/es/languages/openscad.js.js | 11 + .../highlight.js/es/languages/oxygene.js | 87 + .../highlight.js/es/languages/oxygene.js.js | 11 + .../highlight.js/es/languages/parser3.js | 55 + .../highlight.js/es/languages/parser3.js.js | 11 + .../highlight.js/es/languages/perl.js | 504 + .../highlight.js/es/languages/perl.js.js | 11 + .../highlight.js/es/languages/pf.js | 60 + .../highlight.js/es/languages/pf.js.js | 11 + .../highlight.js/es/languages/pgsql.js | 525 + .../highlight.js/es/languages/pgsql.js.js | 11 + .../highlight.js/es/languages/php-template.js | 54 + .../es/languages/php-template.js.js | 11 + .../highlight.js/es/languages/php.js | 625 + .../highlight.js/es/languages/php.js.js | 11 + .../highlight.js/es/languages/plaintext.js | 19 + .../highlight.js/es/languages/plaintext.js.js | 11 + .../highlight.js/es/languages/pony.js | 90 + .../highlight.js/es/languages/pony.js.js | 11 + .../highlight.js/es/languages/powershell.js | 317 + .../es/languages/powershell.js.js | 11 + .../highlight.js/es/languages/processing.js | 434 + .../es/languages/processing.js.js | 11 + .../highlight.js/es/languages/profile.js | 43 + .../highlight.js/es/languages/profile.js.js | 11 + .../highlight.js/es/languages/prolog.js | 97 + .../highlight.js/es/languages/prolog.js.js | 11 + .../highlight.js/es/languages/properties.js | 68 + .../es/languages/properties.js.js | 11 + .../highlight.js/es/languages/protobuf.js | 79 + .../highlight.js/es/languages/protobuf.js.js | 11 + .../highlight.js/es/languages/puppet.js | 146 + .../highlight.js/es/languages/puppet.js.js | 11 + .../highlight.js/es/languages/purebasic.js | 100 + .../highlight.js/es/languages/purebasic.js.js | 11 + .../highlight.js/es/languages/python-repl.js | 32 + .../es/languages/python-repl.js.js | 11 + .../highlight.js/es/languages/python.js | 436 + .../highlight.js/es/languages/python.js.js | 11 + .../highlight.js/es/languages/q.js | 38 + .../highlight.js/es/languages/q.js.js | 11 + .../highlight.js/es/languages/qml.js | 189 + .../highlight.js/es/languages/qml.js.js | 11 + .../highlight.js/es/languages/r.js | 257 + .../highlight.js/es/languages/r.js.js | 11 + .../highlight.js/es/languages/reasonml.js | 142 + .../highlight.js/es/languages/reasonml.js.js | 11 + .../highlight.js/es/languages/rib.js | 37 + .../highlight.js/es/languages/rib.js.js | 11 + .../highlight.js/es/languages/roboconf.js | 82 + .../highlight.js/es/languages/roboconf.js.js | 11 + .../highlight.js/es/languages/routeros.js | 164 + .../highlight.js/es/languages/routeros.js.js | 11 + .../highlight.js/es/languages/rsl.js | 149 + .../highlight.js/es/languages/rsl.js.js | 11 + .../highlight.js/es/languages/ruby.js | 448 + .../highlight.js/es/languages/ruby.js.js | 11 + .../es/languages/ruleslanguage.js | 76 + .../es/languages/ruleslanguage.js.js | 11 + .../highlight.js/es/languages/rust.js | 326 + .../highlight.js/es/languages/rust.js.js | 11 + .../highlight.js/es/languages/sas.js | 557 + .../highlight.js/es/languages/sas.js.js | 11 + .../highlight.js/es/languages/scala.js | 214 + .../highlight.js/es/languages/scala.js.js | 11 + .../highlight.js/es/languages/scheme.js | 196 + .../highlight.js/es/languages/scheme.js.js | 11 + .../highlight.js/es/languages/scilab.js | 73 + .../highlight.js/es/languages/scilab.js.js | 11 + .../highlight.js/es/languages/scss.js | 939 + .../highlight.js/es/languages/scss.js.js | 11 + .../highlight.js/es/languages/shell.js | 33 + .../highlight.js/es/languages/shell.js.js | 11 + .../highlight.js/es/languages/smali.js | 126 + .../highlight.js/es/languages/smali.js.js | 11 + .../highlight.js/es/languages/smalltalk.js | 69 + .../highlight.js/es/languages/smalltalk.js.js | 11 + .../highlight.js/es/languages/sml.js | 75 + .../highlight.js/es/languages/sml.js.js | 11 + .../highlight.js/es/languages/sqf.js | 2662 ++ .../highlight.js/es/languages/sqf.js.js | 11 + .../highlight.js/es/languages/sql.js | 693 + .../highlight.js/es/languages/sql.js.js | 11 + .../highlight.js/es/languages/stan.js | 521 + .../highlight.js/es/languages/stan.js.js | 11 + .../highlight.js/es/languages/stata.js | 53 + .../highlight.js/es/languages/stata.js.js | 11 + .../highlight.js/es/languages/step21.js | 67 + .../highlight.js/es/languages/step21.js.js | 11 + .../highlight.js/es/languages/stylus.js | 999 + .../highlight.js/es/languages/stylus.js.js | 11 + .../highlight.js/es/languages/subunit.js | 44 + .../highlight.js/es/languages/subunit.js.js | 11 + .../highlight.js/es/languages/swift.js | 972 + .../highlight.js/es/languages/swift.js.js | 11 + .../highlight.js/es/languages/taggerscript.js | 59 + .../es/languages/taggerscript.js.js | 11 + .../highlight.js/es/languages/tap.js | 47 + .../highlight.js/es/languages/tap.js.js | 11 + .../highlight.js/es/languages/tcl.js | 191 + .../highlight.js/es/languages/tcl.js.js | 11 + .../highlight.js/es/languages/thrift.js | 77 + .../highlight.js/es/languages/thrift.js.js | 11 + .../highlight.js/es/languages/tp.js | 172 + .../highlight.js/es/languages/tp.js.js | 11 + .../highlight.js/es/languages/twig.js | 260 + .../highlight.js/es/languages/twig.js.js | 11 + .../highlight.js/es/languages/typescript.js | 913 + .../es/languages/typescript.js.js | 11 + .../highlight.js/es/languages/vala.js | 61 + .../highlight.js/es/languages/vala.js.js | 11 + .../highlight.js/es/languages/vbnet.js | 157 + .../highlight.js/es/languages/vbnet.js.js | 11 + .../es/languages/vbscript-html.js | 24 + .../es/languages/vbscript-html.js.js | 11 + .../highlight.js/es/languages/vbscript.js | 220 + .../highlight.js/es/languages/vbscript.js.js | 11 + .../highlight.js/es/languages/verilog.js | 550 + .../highlight.js/es/languages/verilog.js.js | 11 + .../highlight.js/es/languages/vhdl.js | 216 + .../highlight.js/es/languages/vhdl.js.js | 11 + .../highlight.js/es/languages/vim.js | 129 + .../highlight.js/es/languages/vim.js.js | 11 + .../highlight.js/es/languages/wasm.js | 139 + .../highlight.js/es/languages/wasm.js.js | 11 + .../highlight.js/es/languages/wren.js | 302 + .../highlight.js/es/languages/wren.js.js | 11 + .../highlight.js/es/languages/x86asm.js | 153 + .../highlight.js/es/languages/x86asm.js.js | 11 + .../highlight.js/es/languages/xl.js | 205 + .../highlight.js/es/languages/xl.js.js | 11 + .../highlight.js/es/languages/xml.js | 241 + .../highlight.js/es/languages/xml.js.js | 11 + .../highlight.js/es/languages/xquery.js | 360 + .../highlight.js/es/languages/xquery.js.js | 11 + .../highlight.js/es/languages/yaml.js | 213 + .../highlight.js/es/languages/yaml.js.js | 11 + .../highlight.js/es/languages/zephir.js | 129 + .../highlight.js/es/languages/zephir.js.js | 11 + .../node_modules/highlight.js/es/package.json | 1 + .../highlight.js/es/utils/regex.js | 155 + .../node_modules/highlight.js/lib/common.d.ts | 3 + .../node_modules/highlight.js/lib/common.js | 42 + .../node_modules/highlight.js/lib/core.d.ts | 3 + .../node_modules/highlight.js/lib/core.js | 2597 ++ .../node_modules/highlight.js/lib/index.js | 198 + .../highlight.js/lib/languages/1c.js | 544 + .../highlight.js/lib/languages/1c.js.js | 10 + .../highlight.js/lib/languages/abnf.js | 83 + .../highlight.js/lib/languages/abnf.js.js | 10 + .../highlight.js/lib/languages/accesslog.js | 92 + .../lib/languages/accesslog.js.js | 10 + .../lib/languages/actionscript.js | 153 + .../lib/languages/actionscript.js.js | 10 + .../highlight.js/lib/languages/ada.js | 265 + .../highlight.js/lib/languages/ada.js.js | 10 + .../highlight.js/lib/languages/angelscript.js | 178 + .../lib/languages/angelscript.js.js | 10 + .../highlight.js/lib/languages/apache.js | 105 + .../highlight.js/lib/languages/apache.js.js | 10 + .../highlight.js/lib/languages/applescript.js | 149 + .../lib/languages/applescript.js.js | 10 + .../highlight.js/lib/languages/arcade.js | 428 + .../highlight.js/lib/languages/arcade.js.js | 10 + .../highlight.js/lib/languages/arduino.js | 1008 + .../highlight.js/lib/languages/arduino.js.js | 10 + .../highlight.js/lib/languages/armasm.js | 124 + .../highlight.js/lib/languages/armasm.js.js | 10 + .../highlight.js/lib/languages/asciidoc.js | 261 + .../highlight.js/lib/languages/asciidoc.js.js | 10 + .../highlight.js/lib/languages/aspectj.js | 231 + .../highlight.js/lib/languages/aspectj.js.js | 10 + .../highlight.js/lib/languages/autohotkey.js | 75 + .../lib/languages/autohotkey.js.js | 10 + .../highlight.js/lib/languages/autoit.js | 178 + .../highlight.js/lib/languages/autoit.js.js | 10 + .../highlight.js/lib/languages/avrasm.js | 78 + .../highlight.js/lib/languages/avrasm.js.js | 10 + .../highlight.js/lib/languages/awk.js | 68 + .../highlight.js/lib/languages/awk.js.js | 10 + .../highlight.js/lib/languages/axapta.js | 188 + .../highlight.js/lib/languages/axapta.js.js | 10 + .../highlight.js/lib/languages/bash.js | 409 + .../highlight.js/lib/languages/bash.js.js | 10 + .../highlight.js/lib/languages/basic.js | 236 + .../highlight.js/lib/languages/basic.js.js | 10 + .../highlight.js/lib/languages/bnf.js | 39 + .../highlight.js/lib/languages/bnf.js.js | 10 + .../highlight.js/lib/languages/brainfuck.js | 54 + .../lib/languages/brainfuck.js.js | 10 + .../highlight.js/lib/languages/c.js | 333 + .../highlight.js/lib/languages/c.js.js | 10 + .../highlight.js/lib/languages/cal.js | 160 + .../highlight.js/lib/languages/cal.js.js | 10 + .../highlight.js/lib/languages/capnproto.js | 99 + .../lib/languages/capnproto.js.js | 10 + .../highlight.js/lib/languages/ceylon.js | 140 + .../highlight.js/lib/languages/ceylon.js.js | 10 + .../highlight.js/lib/languages/clean.js | 67 + .../highlight.js/lib/languages/clean.js.js | 10 + .../lib/languages/clojure-repl.js | 27 + .../lib/languages/clojure-repl.js.js | 10 + .../highlight.js/lib/languages/clojure.js | 184 + .../highlight.js/lib/languages/clojure.js.js | 10 + .../highlight.js/lib/languages/cmake.js | 64 + .../highlight.js/lib/languages/cmake.js.js | 10 + .../lib/languages/coffeescript.js | 368 + .../lib/languages/coffeescript.js.js | 10 + .../highlight.js/lib/languages/coq.js | 445 + .../highlight.js/lib/languages/coq.js.js | 10 + .../highlight.js/lib/languages/cos.js | 140 + .../highlight.js/lib/languages/cos.js.js | 10 + .../highlight.js/lib/languages/cpp.js | 605 + .../highlight.js/lib/languages/cpp.js.js | 10 + .../highlight.js/lib/languages/crmsh.js | 100 + .../highlight.js/lib/languages/crmsh.js.js | 10 + .../highlight.js/lib/languages/crystal.js | 312 + .../highlight.js/lib/languages/crystal.js.js | 10 + .../highlight.js/lib/languages/csharp.js | 412 + .../highlight.js/lib/languages/csharp.js.js | 10 + .../highlight.js/lib/languages/csp.js | 58 + .../highlight.js/lib/languages/csp.js.js | 10 + .../highlight.js/lib/languages/css.js | 949 + .../highlight.js/lib/languages/css.js.js | 10 + .../highlight.js/lib/languages/d.js | 272 + .../highlight.js/lib/languages/d.js.js | 10 + .../highlight.js/lib/languages/dart.js | 271 + .../highlight.js/lib/languages/dart.js.js | 10 + .../highlight.js/lib/languages/delphi.js | 246 + .../highlight.js/lib/languages/delphi.js.js | 10 + .../highlight.js/lib/languages/diff.js | 62 + .../highlight.js/lib/languages/diff.js.js | 10 + .../highlight.js/lib/languages/django.js | 75 + .../highlight.js/lib/languages/django.js.js | 10 + .../highlight.js/lib/languages/dns.js | 78 + .../highlight.js/lib/languages/dns.js.js | 10 + .../highlight.js/lib/languages/dockerfile.js | 44 + .../lib/languages/dockerfile.js.js | 10 + .../highlight.js/lib/languages/dos.js | 167 + .../highlight.js/lib/languages/dos.js.js | 10 + .../highlight.js/lib/languages/dsconfig.js | 66 + .../highlight.js/lib/languages/dsconfig.js.js | 10 + .../highlight.js/lib/languages/dts.js | 157 + .../highlight.js/lib/languages/dts.js.js | 10 + .../highlight.js/lib/languages/dust.js | 47 + .../highlight.js/lib/languages/dust.js.js | 10 + .../highlight.js/lib/languages/ebnf.js | 54 + .../highlight.js/lib/languages/ebnf.js.js | 10 + .../highlight.js/lib/languages/elixir.js | 279 + .../highlight.js/lib/languages/elixir.js.js | 10 + .../highlight.js/lib/languages/elm.js | 143 + .../highlight.js/lib/languages/elm.js.js | 10 + .../highlight.js/lib/languages/erb.js | 29 + .../highlight.js/lib/languages/erb.js.js | 10 + .../highlight.js/lib/languages/erlang-repl.js | 54 + .../lib/languages/erlang-repl.js.js | 10 + .../highlight.js/lib/languages/erlang.js | 235 + .../highlight.js/lib/languages/erlang.js.js | 10 + .../highlight.js/lib/languages/excel.js | 580 + .../highlight.js/lib/languages/excel.js.js | 10 + .../highlight.js/lib/languages/fix.js | 39 + .../highlight.js/lib/languages/fix.js.js | 10 + .../highlight.js/lib/languages/flix.js | 79 + .../highlight.js/lib/languages/flix.js.js | 10 + .../highlight.js/lib/languages/fortran.js | 574 + .../highlight.js/lib/languages/fortran.js.js | 10 + .../highlight.js/lib/languages/fsharp.js | 627 + .../highlight.js/lib/languages/fsharp.js.js | 10 + .../highlight.js/lib/languages/gams.js | 181 + .../highlight.js/lib/languages/gams.js.js | 10 + .../highlight.js/lib/languages/gauss.js | 306 + .../highlight.js/lib/languages/gauss.js.js | 10 + .../highlight.js/lib/languages/gcode.js | 189 + .../highlight.js/lib/languages/gcode.js.js | 10 + .../highlight.js/lib/languages/gherkin.js | 49 + .../highlight.js/lib/languages/gherkin.js.js | 10 + .../highlight.js/lib/languages/glsl.js | 128 + .../highlight.js/lib/languages/glsl.js.js | 10 + .../highlight.js/lib/languages/gml.js | 3130 +++ .../highlight.js/lib/languages/gml.js.js | 10 + .../highlight.js/lib/languages/go.js | 156 + .../highlight.js/lib/languages/go.js.js | 10 + .../highlight.js/lib/languages/golo.js | 81 + .../highlight.js/lib/languages/golo.js.js | 10 + .../highlight.js/lib/languages/gradle.js | 190 + .../highlight.js/lib/languages/gradle.js.js | 10 + .../highlight.js/lib/languages/graphql.js | 78 + .../highlight.js/lib/languages/graphql.js.js | 10 + .../highlight.js/lib/languages/groovy.js | 190 + .../highlight.js/lib/languages/groovy.js.js | 10 + .../highlight.js/lib/languages/haml.js | 113 + .../highlight.js/lib/languages/haml.js.js | 10 + .../highlight.js/lib/languages/handlebars.js | 258 + .../lib/languages/handlebars.js.js | 10 + .../highlight.js/lib/languages/haskell.js | 217 + .../highlight.js/lib/languages/haskell.js.js | 10 + .../highlight.js/lib/languages/haxe.js | 167 + .../highlight.js/lib/languages/haxe.js.js | 10 + .../highlight.js/lib/languages/hsp.js | 59 + .../highlight.js/lib/languages/hsp.js.js | 10 + .../highlight.js/lib/languages/http.js | 97 + .../highlight.js/lib/languages/http.js.js | 10 + .../highlight.js/lib/languages/hy.js | 137 + .../highlight.js/lib/languages/hy.js.js | 10 + .../highlight.js/lib/languages/inform7.js | 70 + .../highlight.js/lib/languages/inform7.js.js | 10 + .../highlight.js/lib/languages/ini.js | 121 + .../highlight.js/lib/languages/ini.js.js | 10 + .../highlight.js/lib/languages/irpf90.js | 107 + .../highlight.js/lib/languages/irpf90.js.js | 10 + .../highlight.js/lib/languages/isbl.js | 3205 +++ .../highlight.js/lib/languages/isbl.js.js | 10 + .../highlight.js/lib/languages/java.js | 291 + .../highlight.js/lib/languages/java.js.js | 10 + .../highlight.js/lib/languages/javascript.js | 769 + .../lib/languages/javascript.js.js | 10 + .../highlight.js/lib/languages/jboss-cli.js | 63 + .../lib/languages/jboss-cli.js.js | 10 + .../highlight.js/lib/languages/json.js | 54 + .../highlight.js/lib/languages/json.js.js | 10 + .../highlight.js/lib/languages/julia-repl.js | 51 + .../lib/languages/julia-repl.js.js | 10 + .../highlight.js/lib/languages/julia.js | 442 + .../highlight.js/lib/languages/julia.js.js | 10 + .../highlight.js/lib/languages/kotlin.js | 286 + .../highlight.js/lib/languages/kotlin.js.js | 10 + .../highlight.js/lib/languages/lasso.js | 171 + .../highlight.js/lib/languages/lasso.js.js | 10 + .../highlight.js/lib/languages/latex.js | 278 + .../highlight.js/lib/languages/latex.js.js | 10 + .../highlight.js/lib/languages/ldif.js | 31 + .../highlight.js/lib/languages/ldif.js.js | 10 + .../highlight.js/lib/languages/leaf.js | 97 + .../highlight.js/lib/languages/leaf.js.js | 10 + .../highlight.js/lib/languages/less.js | 1050 + .../highlight.js/lib/languages/less.js.js | 10 + .../highlight.js/lib/languages/lisp.js | 139 + .../highlight.js/lib/languages/lisp.js.js | 10 + .../lib/languages/livecodeserver.js | 173 + .../lib/languages/livecodeserver.js.js | 10 + .../highlight.js/lib/languages/livescript.js | 380 + .../lib/languages/livescript.js.js | 10 + .../highlight.js/lib/languages/llvm.js | 135 + .../highlight.js/lib/languages/llvm.js.js | 10 + .../highlight.js/lib/languages/lsl.js | 76 + .../highlight.js/lib/languages/lsl.js.js | 10 + .../highlight.js/lib/languages/lua.js | 81 + .../highlight.js/lib/languages/lua.js.js | 10 + .../highlight.js/lib/languages/makefile.js | 89 + .../highlight.js/lib/languages/makefile.js.js | 10 + .../highlight.js/lib/languages/markdown.js | 248 + .../highlight.js/lib/languages/markdown.js.js | 10 + .../highlight.js/lib/languages/mathematica.js | 7359 ++++++ .../lib/languages/mathematica.js.js | 10 + .../highlight.js/lib/languages/matlab.js | 107 + .../highlight.js/lib/languages/matlab.js.js | 10 + .../highlight.js/lib/languages/maxima.js | 414 + .../highlight.js/lib/languages/maxima.js.js | 10 + .../highlight.js/lib/languages/mel.js | 235 + .../highlight.js/lib/languages/mel.js.js | 10 + .../highlight.js/lib/languages/mercury.js | 108 + .../highlight.js/lib/languages/mercury.js.js | 10 + .../highlight.js/lib/languages/mipsasm.js | 104 + .../highlight.js/lib/languages/mipsasm.js.js | 10 + .../highlight.js/lib/languages/mizar.js | 27 + .../highlight.js/lib/languages/mizar.js.js | 10 + .../highlight.js/lib/languages/mojolicious.js | 36 + .../lib/languages/mojolicious.js.js | 10 + .../highlight.js/lib/languages/monkey.js | 184 + .../highlight.js/lib/languages/monkey.js.js | 10 + .../highlight.js/lib/languages/moonscript.js | 141 + .../lib/languages/moonscript.js.js | 10 + .../highlight.js/lib/languages/n1ql.js | 365 + .../highlight.js/lib/languages/n1ql.js.js | 10 + .../highlight.js/lib/languages/nestedtext.js | 83 + .../lib/languages/nestedtext.js.js | 10 + .../highlight.js/lib/languages/nginx.js | 153 + .../highlight.js/lib/languages/nginx.js.js | 10 + .../highlight.js/lib/languages/nim.js | 187 + .../highlight.js/lib/languages/nim.js.js | 10 + .../highlight.js/lib/languages/nix.js | 372 + .../highlight.js/lib/languages/nix.js.js | 10 + .../highlight.js/lib/languages/node-repl.js | 33 + .../lib/languages/node-repl.js.js | 10 + .../highlight.js/lib/languages/nsis.js | 557 + .../highlight.js/lib/languages/nsis.js.js | 10 + .../highlight.js/lib/languages/objectivec.js | 253 + .../lib/languages/objectivec.js.js | 10 + .../highlight.js/lib/languages/ocaml.js | 83 + .../highlight.js/lib/languages/ocaml.js.js | 10 + .../highlight.js/lib/languages/openscad.js | 77 + .../highlight.js/lib/languages/openscad.js.js | 10 + .../highlight.js/lib/languages/oxygene.js | 87 + .../highlight.js/lib/languages/oxygene.js.js | 10 + .../highlight.js/lib/languages/parser3.js | 55 + .../highlight.js/lib/languages/parser3.js.js | 10 + .../highlight.js/lib/languages/perl.js | 504 + .../highlight.js/lib/languages/perl.js.js | 10 + .../highlight.js/lib/languages/pf.js | 60 + .../highlight.js/lib/languages/pf.js.js | 10 + .../highlight.js/lib/languages/pgsql.js | 525 + .../highlight.js/lib/languages/pgsql.js.js | 10 + .../lib/languages/php-template.js | 54 + .../lib/languages/php-template.js.js | 10 + .../highlight.js/lib/languages/php.js | 625 + .../highlight.js/lib/languages/php.js.js | 10 + .../highlight.js/lib/languages/plaintext.js | 19 + .../lib/languages/plaintext.js.js | 10 + .../highlight.js/lib/languages/pony.js | 90 + .../highlight.js/lib/languages/pony.js.js | 10 + .../highlight.js/lib/languages/powershell.js | 317 + .../lib/languages/powershell.js.js | 10 + .../highlight.js/lib/languages/processing.js | 434 + .../lib/languages/processing.js.js | 10 + .../highlight.js/lib/languages/profile.js | 43 + .../highlight.js/lib/languages/profile.js.js | 10 + .../highlight.js/lib/languages/prolog.js | 97 + .../highlight.js/lib/languages/prolog.js.js | 10 + .../highlight.js/lib/languages/properties.js | 68 + .../lib/languages/properties.js.js | 10 + .../highlight.js/lib/languages/protobuf.js | 79 + .../highlight.js/lib/languages/protobuf.js.js | 10 + .../highlight.js/lib/languages/puppet.js | 146 + .../highlight.js/lib/languages/puppet.js.js | 10 + .../highlight.js/lib/languages/purebasic.js | 100 + .../lib/languages/purebasic.js.js | 10 + .../highlight.js/lib/languages/python-repl.js | 32 + .../lib/languages/python-repl.js.js | 10 + .../highlight.js/lib/languages/python.js | 436 + .../highlight.js/lib/languages/python.js.js | 10 + .../highlight.js/lib/languages/q.js | 38 + .../highlight.js/lib/languages/q.js.js | 10 + .../highlight.js/lib/languages/qml.js | 189 + .../highlight.js/lib/languages/qml.js.js | 10 + .../highlight.js/lib/languages/r.js | 257 + .../highlight.js/lib/languages/r.js.js | 10 + .../highlight.js/lib/languages/reasonml.js | 142 + .../highlight.js/lib/languages/reasonml.js.js | 10 + .../highlight.js/lib/languages/rib.js | 37 + .../highlight.js/lib/languages/rib.js.js | 10 + .../highlight.js/lib/languages/roboconf.js | 82 + .../highlight.js/lib/languages/roboconf.js.js | 10 + .../highlight.js/lib/languages/routeros.js | 164 + .../highlight.js/lib/languages/routeros.js.js | 10 + .../highlight.js/lib/languages/rsl.js | 149 + .../highlight.js/lib/languages/rsl.js.js | 10 + .../highlight.js/lib/languages/ruby.js | 448 + .../highlight.js/lib/languages/ruby.js.js | 10 + .../lib/languages/ruleslanguage.js | 76 + .../lib/languages/ruleslanguage.js.js | 10 + .../highlight.js/lib/languages/rust.js | 326 + .../highlight.js/lib/languages/rust.js.js | 10 + .../highlight.js/lib/languages/sas.js | 557 + .../highlight.js/lib/languages/sas.js.js | 10 + .../highlight.js/lib/languages/scala.js | 214 + .../highlight.js/lib/languages/scala.js.js | 10 + .../highlight.js/lib/languages/scheme.js | 196 + .../highlight.js/lib/languages/scheme.js.js | 10 + .../highlight.js/lib/languages/scilab.js | 73 + .../highlight.js/lib/languages/scilab.js.js | 10 + .../highlight.js/lib/languages/scss.js | 939 + .../highlight.js/lib/languages/scss.js.js | 10 + .../highlight.js/lib/languages/shell.js | 33 + .../highlight.js/lib/languages/shell.js.js | 10 + .../highlight.js/lib/languages/smali.js | 126 + .../highlight.js/lib/languages/smali.js.js | 10 + .../highlight.js/lib/languages/smalltalk.js | 69 + .../lib/languages/smalltalk.js.js | 10 + .../highlight.js/lib/languages/sml.js | 75 + .../highlight.js/lib/languages/sml.js.js | 10 + .../highlight.js/lib/languages/sqf.js | 2662 ++ .../highlight.js/lib/languages/sqf.js.js | 10 + .../highlight.js/lib/languages/sql.js | 693 + .../highlight.js/lib/languages/sql.js.js | 10 + .../highlight.js/lib/languages/stan.js | 521 + .../highlight.js/lib/languages/stan.js.js | 10 + .../highlight.js/lib/languages/stata.js | 53 + .../highlight.js/lib/languages/stata.js.js | 10 + .../highlight.js/lib/languages/step21.js | 67 + .../highlight.js/lib/languages/step21.js.js | 10 + .../highlight.js/lib/languages/stylus.js | 999 + .../highlight.js/lib/languages/stylus.js.js | 10 + .../highlight.js/lib/languages/subunit.js | 44 + .../highlight.js/lib/languages/subunit.js.js | 10 + .../highlight.js/lib/languages/swift.js | 972 + .../highlight.js/lib/languages/swift.js.js | 10 + .../lib/languages/taggerscript.js | 59 + .../lib/languages/taggerscript.js.js | 10 + .../highlight.js/lib/languages/tap.js | 47 + .../highlight.js/lib/languages/tap.js.js | 10 + .../highlight.js/lib/languages/tcl.js | 191 + .../highlight.js/lib/languages/tcl.js.js | 10 + .../highlight.js/lib/languages/thrift.js | 77 + .../highlight.js/lib/languages/thrift.js.js | 10 + .../highlight.js/lib/languages/tp.js | 172 + .../highlight.js/lib/languages/tp.js.js | 10 + .../highlight.js/lib/languages/twig.js | 260 + .../highlight.js/lib/languages/twig.js.js | 10 + .../highlight.js/lib/languages/typescript.js | 913 + .../lib/languages/typescript.js.js | 10 + .../highlight.js/lib/languages/vala.js | 61 + .../highlight.js/lib/languages/vala.js.js | 10 + .../highlight.js/lib/languages/vbnet.js | 157 + .../highlight.js/lib/languages/vbnet.js.js | 10 + .../lib/languages/vbscript-html.js | 24 + .../lib/languages/vbscript-html.js.js | 10 + .../highlight.js/lib/languages/vbscript.js | 220 + .../highlight.js/lib/languages/vbscript.js.js | 10 + .../highlight.js/lib/languages/verilog.js | 550 + .../highlight.js/lib/languages/verilog.js.js | 10 + .../highlight.js/lib/languages/vhdl.js | 216 + .../highlight.js/lib/languages/vhdl.js.js | 10 + .../highlight.js/lib/languages/vim.js | 129 + .../highlight.js/lib/languages/vim.js.js | 10 + .../highlight.js/lib/languages/wasm.js | 139 + .../highlight.js/lib/languages/wasm.js.js | 10 + .../highlight.js/lib/languages/wren.js | 302 + .../highlight.js/lib/languages/wren.js.js | 10 + .../highlight.js/lib/languages/x86asm.js | 153 + .../highlight.js/lib/languages/x86asm.js.js | 10 + .../highlight.js/lib/languages/xl.js | 205 + .../highlight.js/lib/languages/xl.js.js | 10 + .../highlight.js/lib/languages/xml.js | 241 + .../highlight.js/lib/languages/xml.js.js | 10 + .../highlight.js/lib/languages/xquery.js | 360 + .../highlight.js/lib/languages/xquery.js.js | 10 + .../highlight.js/lib/languages/yaml.js | 213 + .../highlight.js/lib/languages/yaml.js.js | 10 + .../highlight.js/lib/languages/zephir.js | 129 + .../highlight.js/lib/languages/zephir.js.js | 10 + .../node_modules/highlight.js/package.json | 119 + .../highlight.js/scss/1c-light.scss | 107 + .../highlight.js/scss/a11y-dark.scss | 94 + .../highlight.js/scss/a11y-light.scss | 94 + .../node_modules/highlight.js/scss/agate.scss | 127 + .../highlight.js/scss/an-old-hope.scss | 75 + .../highlight.js/scss/androidstudio.scss | 60 + .../highlight.js/scss/arduino-light.scss | 78 + .../node_modules/highlight.js/scss/arta.scss | 66 + .../highlight.js/scss/ascetic.scss | 45 + .../scss/atom-one-dark-reasonable.scss | 105 + .../highlight.js/scss/atom-one-dark.scss | 90 + .../highlight.js/scss/atom-one-light.scss | 90 + .../highlight.js/scss/base16/3024.scss | 163 + .../highlight.js/scss/base16/apathy.scss | 163 + .../highlight.js/scss/base16/apprentice.scss | 163 + .../highlight.js/scss/base16/ashes.scss | 163 + .../scss/base16/atelier-cave-light.scss | 163 + .../scss/base16/atelier-cave.scss | 163 + .../scss/base16/atelier-dune-light.scss | 163 + .../scss/base16/atelier-dune.scss | 163 + .../scss/base16/atelier-estuary-light.scss | 163 + .../scss/base16/atelier-estuary.scss | 163 + .../scss/base16/atelier-forest-light.scss | 163 + .../scss/base16/atelier-forest.scss | 163 + .../scss/base16/atelier-heath-light.scss | 163 + .../scss/base16/atelier-heath.scss | 163 + .../scss/base16/atelier-lakeside-light.scss | 163 + .../scss/base16/atelier-lakeside.scss | 163 + .../scss/base16/atelier-plateau-light.scss | 163 + .../scss/base16/atelier-plateau.scss | 163 + .../scss/base16/atelier-savanna-light.scss | 163 + .../scss/base16/atelier-savanna.scss | 163 + .../scss/base16/atelier-seaside-light.scss | 163 + .../scss/base16/atelier-seaside.scss | 163 + .../base16/atelier-sulphurpool-light.scss | 163 + .../scss/base16/atelier-sulphurpool.scss | 163 + .../highlight.js/scss/base16/atlas.scss | 163 + .../highlight.js/scss/base16/bespin.scss | 163 + .../scss/base16/black-metal-bathory.scss | 163 + .../scss/base16/black-metal-burzum.scss | 163 + .../scss/base16/black-metal-dark-funeral.scss | 163 + .../scss/base16/black-metal-gorgoroth.scss | 163 + .../scss/base16/black-metal-immortal.scss | 163 + .../scss/base16/black-metal-khold.scss | 163 + .../scss/base16/black-metal-marduk.scss | 163 + .../scss/base16/black-metal-mayhem.scss | 163 + .../scss/base16/black-metal-nile.scss | 163 + .../scss/base16/black-metal-venom.scss | 163 + .../highlight.js/scss/base16/black-metal.scss | 163 + .../highlight.js/scss/base16/brewer.scss | 163 + .../highlight.js/scss/base16/bright.scss | 163 + .../highlight.js/scss/base16/brogrammer.scss | 163 + .../scss/base16/brush-trees-dark.scss | 163 + .../highlight.js/scss/base16/brush-trees.scss | 163 + .../highlight.js/scss/base16/chalk.scss | 163 + .../highlight.js/scss/base16/circus.scss | 163 + .../scss/base16/classic-dark.scss | 163 + .../scss/base16/classic-light.scss | 163 + .../highlight.js/scss/base16/codeschool.scss | 163 + .../highlight.js/scss/base16/colors.scss | 163 + .../highlight.js/scss/base16/cupcake.scss | 163 + .../highlight.js/scss/base16/cupertino.scss | 163 + .../highlight.js/scss/base16/danqing.scss | 163 + .../highlight.js/scss/base16/darcula.scss | 163 + .../highlight.js/scss/base16/dark-violet.scss | 163 + .../highlight.js/scss/base16/darkmoss.scss | 163 + .../highlight.js/scss/base16/darktooth.scss | 163 + .../highlight.js/scss/base16/decaf.scss | 163 + .../scss/base16/default-dark.scss | 163 + .../scss/base16/default-light.scss | 163 + .../highlight.js/scss/base16/dirtysea.scss | 163 + .../highlight.js/scss/base16/dracula.scss | 163 + .../highlight.js/scss/base16/edge-dark.scss | 163 + .../highlight.js/scss/base16/edge-light.scss | 163 + .../highlight.js/scss/base16/eighties.scss | 163 + .../highlight.js/scss/base16/embers.scss | 163 + .../scss/base16/equilibrium-dark.scss | 163 + .../scss/base16/equilibrium-gray-dark.scss | 163 + .../scss/base16/equilibrium-gray-light.scss | 163 + .../scss/base16/equilibrium-light.scss | 163 + .../highlight.js/scss/base16/espresso.scss | 163 + .../highlight.js/scss/base16/eva-dim.scss | 163 + .../highlight.js/scss/base16/eva.scss | 163 + .../highlight.js/scss/base16/flat.scss | 163 + .../highlight.js/scss/base16/framer.scss | 163 + .../highlight.js/scss/base16/fruit-soda.scss | 163 + .../highlight.js/scss/base16/gigavolt.scss | 163 + .../highlight.js/scss/base16/github.scss | 163 + .../highlight.js/scss/base16/google-dark.scss | 163 + .../scss/base16/google-light.scss | 163 + .../scss/base16/grayscale-dark.scss | 163 + .../scss/base16/grayscale-light.scss | 163 + .../scss/base16/green-screen.scss | 163 + .../scss/base16/gruvbox-dark-hard.scss | 163 + .../scss/base16/gruvbox-dark-medium.scss | 163 + .../scss/base16/gruvbox-dark-pale.scss | 163 + .../scss/base16/gruvbox-dark-soft.scss | 163 + .../scss/base16/gruvbox-light-hard.scss | 163 + .../scss/base16/gruvbox-light-medium.scss | 163 + .../scss/base16/gruvbox-light-soft.scss | 163 + .../highlight.js/scss/base16/hardcore.scss | 163 + .../scss/base16/harmonic16-dark.scss | 163 + .../scss/base16/harmonic16-light.scss | 163 + .../highlight.js/scss/base16/heetch-dark.scss | 163 + .../scss/base16/heetch-light.scss | 163 + .../highlight.js/scss/base16/helios.scss | 163 + .../highlight.js/scss/base16/hopscotch.scss | 163 + .../scss/base16/horizon-dark.scss | 163 + .../scss/base16/horizon-light.scss | 163 + .../scss/base16/humanoid-dark.scss | 163 + .../scss/base16/humanoid-light.scss | 163 + .../highlight.js/scss/base16/ia-dark.scss | 163 + .../highlight.js/scss/base16/ia-light.scss | 163 + .../highlight.js/scss/base16/icy-dark.scss | 163 + .../highlight.js/scss/base16/ir-black.scss | 163 + .../highlight.js/scss/base16/isotope.scss | 163 + .../highlight.js/scss/base16/kimber.scss | 163 + .../highlight.js/scss/base16/london-tube.scss | 163 + .../highlight.js/scss/base16/macintosh.scss | 163 + .../highlight.js/scss/base16/marrakesh.scss | 163 + .../highlight.js/scss/base16/materia.scss | 163 + .../scss/base16/material-darker.scss | 163 + .../scss/base16/material-lighter.scss | 163 + .../scss/base16/material-palenight.scss | 163 + .../scss/base16/material-vivid.scss | 163 + .../highlight.js/scss/base16/material.scss | 163 + .../scss/base16/mellow-purple.scss | 163 + .../scss/base16/mexico-light.scss | 163 + .../highlight.js/scss/base16/mocha.scss | 163 + .../highlight.js/scss/base16/monokai.scss | 163 + .../highlight.js/scss/base16/nebula.scss | 163 + .../highlight.js/scss/base16/nord.scss | 163 + .../highlight.js/scss/base16/nova.scss | 163 + .../highlight.js/scss/base16/ocean.scss | 163 + .../highlight.js/scss/base16/oceanicnext.scss | 163 + .../highlight.js/scss/base16/one-light.scss | 163 + .../highlight.js/scss/base16/onedark.scss | 163 + .../highlight.js/scss/base16/outrun-dark.scss | 163 + .../scss/base16/papercolor-dark.scss | 163 + .../scss/base16/papercolor-light.scss | 163 + .../highlight.js/scss/base16/paraiso.scss | 163 + .../highlight.js/scss/base16/pasque.scss | 163 + .../highlight.js/scss/base16/phd.scss | 163 + .../highlight.js/scss/base16/pico.scss | 163 + .../highlight.js/scss/base16/pop.scss | 163 + .../highlight.js/scss/base16/porple.scss | 163 + .../highlight.js/scss/base16/qualia.scss | 163 + .../highlight.js/scss/base16/railscasts.scss | 163 + .../highlight.js/scss/base16/rebecca.scss | 163 + .../scss/base16/ros-pine-dawn.scss | 163 + .../scss/base16/ros-pine-moon.scss | 163 + .../highlight.js/scss/base16/ros-pine.scss | 163 + .../highlight.js/scss/base16/sagelight.scss | 163 + .../highlight.js/scss/base16/sandcastle.scss | 163 + .../highlight.js/scss/base16/seti-ui.scss | 163 + .../scss/base16/shapeshifter.scss | 163 + .../highlight.js/scss/base16/silk-dark.scss | 163 + .../highlight.js/scss/base16/silk-light.scss | 163 + .../highlight.js/scss/base16/snazzy.scss | 163 + .../scss/base16/solar-flare-light.scss | 163 + .../highlight.js/scss/base16/solar-flare.scss | 163 + .../scss/base16/solarized-dark.scss | 163 + .../scss/base16/solarized-light.scss | 163 + .../highlight.js/scss/base16/spacemacs.scss | 163 + .../highlight.js/scss/base16/summercamp.scss | 163 + .../scss/base16/summerfruit-dark.scss | 163 + .../scss/base16/summerfruit-light.scss | 163 + .../base16/synth-midnight-terminal-dark.scss | 163 + .../base16/synth-midnight-terminal-light.scss | 163 + .../highlight.js/scss/base16/tango.scss | 163 + .../highlight.js/scss/base16/tender.scss | 163 + .../scss/base16/tomorrow-night.scss | 163 + .../highlight.js/scss/base16/tomorrow.scss | 163 + .../highlight.js/scss/base16/twilight.scss | 163 + .../scss/base16/unikitty-dark.scss | 163 + .../scss/base16/unikitty-light.scss | 163 + .../highlight.js/scss/base16/vulcan.scss | 163 + .../scss/base16/windows-10-light.scss | 163 + .../highlight.js/scss/base16/windows-10.scss | 163 + .../scss/base16/windows-95-light.scss | 163 + .../highlight.js/scss/base16/windows-95.scss | 163 + .../base16/windows-high-contrast-light.scss | 163 + .../scss/base16/windows-high-contrast.scss | 163 + .../scss/base16/windows-nt-light.scss | 163 + .../highlight.js/scss/base16/windows-nt.scss | 163 + .../highlight.js/scss/base16/woodland.scss | 163 + .../highlight.js/scss/base16/xcode-dusk.scss | 163 + .../highlight.js/scss/base16/zenburn.scss | 163 + .../highlight.js/scss/brown-paper.scss | 63 + .../highlight.js/scss/codepen-embed.scss | 57 + .../highlight.js/scss/color-brewer.scss | 66 + .../highlight.js/scss/cybertopia-cherry.scss | 103 + .../highlight.js/scss/cybertopia-dimmer.scss | 103 + .../highlight.js/scss/cybertopia-icecap.scss | 103 + .../scss/cybertopia-saturated.scss | 103 + .../node_modules/highlight.js/scss/dark.scss | 62 + .../highlight.js/scss/default.scss | 117 + .../highlight.js/scss/devibeans.scss | 90 + .../node_modules/highlight.js/scss/docco.scss | 83 + .../node_modules/highlight.js/scss/far.scss | 67 + .../highlight.js/scss/felipec.scss | 94 + .../highlight.js/scss/foundation.scss | 80 + .../highlight.js/scss/github-dark-dimmed.scss | 117 + .../highlight.js/scss/github-dark.scss | 118 + .../highlight.js/scss/github.scss | 118 + .../node_modules/highlight.js/scss/gml.scss | 72 + .../highlight.js/scss/googlecode.scss | 79 + .../highlight.js/scss/gradient-dark.scss | 90 + .../highlight.js/scss/gradient-light.scss | 90 + .../highlight.js/scss/grayscale.scss | 89 + .../highlight.js/scss/hybrid.scss | 88 + .../node_modules/highlight.js/scss/idea.scss | 86 + .../highlight.js/scss/intellij-light.scss | 107 + .../highlight.js/scss/ir-black.scss | 66 + .../highlight.js/scss/isbl-editor-dark.scss | 94 + .../highlight.js/scss/isbl-editor-light.scss | 93 + .../highlight.js/scss/kimbie-dark.scss | 69 + .../highlight.js/scss/kimbie-light.scss | 69 + .../highlight.js/scss/lightfair.scss | 81 + .../highlight.js/scss/lioshi.scss | 76 + .../highlight.js/scss/magula.scss | 66 + .../highlight.js/scss/mono-blue.scss | 56 + .../highlight.js/scss/monokai-sublime.scss | 76 + .../highlight.js/scss/monokai.scss | 70 + .../highlight.js/scss/night-owl.scss | 174 + .../highlight.js/scss/nnfx-dark.scss | 104 + .../highlight.js/scss/nnfx-light.scss | 104 + .../node_modules/highlight.js/scss/nord.scss | 275 + .../highlight.js/scss/obsidian.scss | 79 + .../highlight.js/scss/panda-syntax-dark.scss | 92 + .../highlight.js/scss/panda-syntax-light.scss | 89 + .../highlight.js/scss/paraiso-dark.scss | 67 + .../highlight.js/scss/paraiso-light.scss | 67 + .../highlight.js/scss/pojoaque.scss | 76 + .../highlight.js/scss/purebasic.scss | 103 + .../highlight.js/scss/qtcreator-dark.scss | 76 + .../highlight.js/scss/qtcreator-light.scss | 74 + .../highlight.js/scss/rainbow.scss | 77 + .../highlight.js/scss/rose-pine-dawn.scss | 107 + .../highlight.js/scss/rose-pine-moon.scss | 109 + .../highlight.js/scss/rose-pine.scss | 109 + .../highlight.js/scss/routeros.scss | 86 + .../highlight.js/scss/school-book.scss | 62 + .../highlight.js/scss/shades-of-purple.scss | 84 + .../highlight.js/scss/srcery.scss | 89 + .../highlight.js/scss/stackoverflow-dark.scss | 117 + .../scss/stackoverflow-light.scss | 117 + .../highlight.js/scss/sunburst.scss | 89 + .../highlight.js/scss/tokyo-night-dark.scss | 114 + .../highlight.js/scss/tokyo-night-light.scss | 114 + .../scss/tomorrow-night-blue.scss | 69 + .../scss/tomorrow-night-bright.scss | 68 + .../node_modules/highlight.js/scss/vs.scss | 63 + .../highlight.js/scss/vs2015.scss | 100 + .../node_modules/highlight.js/scss/xcode.scss | 90 + .../node_modules/highlight.js/scss/xt256.scss | 79 + .../highlight.js/styles/1c-light.css | 107 + .../highlight.js/styles/1c-light.min.css | 9 + .../highlight.js/styles/a11y-dark.css | 94 + .../highlight.js/styles/a11y-dark.min.css | 7 + .../highlight.js/styles/a11y-light.css | 94 + .../highlight.js/styles/a11y-light.min.css | 7 + .../highlight.js/styles/agate.css | 127 + .../highlight.js/styles/agate.min.css | 20 + .../highlight.js/styles/an-old-hope.css | 75 + .../highlight.js/styles/an-old-hope.min.css | 9 + .../highlight.js/styles/androidstudio.css | 60 + .../highlight.js/styles/androidstudio.min.css | 1 + .../highlight.js/styles/arduino-light.css | 78 + .../highlight.js/styles/arduino-light.min.css | 1 + .../node_modules/highlight.js/styles/arta.css | 66 + .../highlight.js/styles/arta.min.css | 1 + .../highlight.js/styles/ascetic.css | 45 + .../highlight.js/styles/ascetic.min.css | 1 + .../styles/atom-one-dark-reasonable.css | 105 + .../styles/atom-one-dark-reasonable.min.css | 1 + .../highlight.js/styles/atom-one-dark.css | 90 + .../highlight.js/styles/atom-one-dark.min.css | 1 + .../highlight.js/styles/atom-one-light.css | 90 + .../styles/atom-one-light.min.css | 1 + .../highlight.js/styles/base16/3024.css | 163 + .../highlight.js/styles/base16/3024.min.css | 7 + .../highlight.js/styles/base16/apathy.css | 163 + .../highlight.js/styles/base16/apathy.min.css | 7 + .../highlight.js/styles/base16/apprentice.css | 163 + .../styles/base16/apprentice.min.css | 7 + .../highlight.js/styles/base16/ashes.css | 163 + .../highlight.js/styles/base16/ashes.min.css | 7 + .../styles/base16/atelier-cave-light.css | 163 + .../styles/base16/atelier-cave-light.min.css | 7 + .../styles/base16/atelier-cave.css | 163 + .../styles/base16/atelier-cave.min.css | 7 + .../styles/base16/atelier-dune-light.css | 163 + .../styles/base16/atelier-dune-light.min.css | 7 + .../styles/base16/atelier-dune.css | 163 + .../styles/base16/atelier-dune.min.css | 7 + .../styles/base16/atelier-estuary-light.css | 163 + .../base16/atelier-estuary-light.min.css | 7 + .../styles/base16/atelier-estuary.css | 163 + .../styles/base16/atelier-estuary.min.css | 7 + .../styles/base16/atelier-forest-light.css | 163 + .../base16/atelier-forest-light.min.css | 7 + .../styles/base16/atelier-forest.css | 163 + .../styles/base16/atelier-forest.min.css | 7 + .../styles/base16/atelier-heath-light.css | 163 + .../styles/base16/atelier-heath-light.min.css | 7 + .../styles/base16/atelier-heath.css | 163 + .../styles/base16/atelier-heath.min.css | 7 + .../styles/base16/atelier-lakeside-light.css | 163 + .../base16/atelier-lakeside-light.min.css | 7 + .../styles/base16/atelier-lakeside.css | 163 + .../styles/base16/atelier-lakeside.min.css | 7 + .../styles/base16/atelier-plateau-light.css | 163 + .../base16/atelier-plateau-light.min.css | 7 + .../styles/base16/atelier-plateau.css | 163 + .../styles/base16/atelier-plateau.min.css | 7 + .../styles/base16/atelier-savanna-light.css | 163 + .../base16/atelier-savanna-light.min.css | 7 + .../styles/base16/atelier-savanna.css | 163 + .../styles/base16/atelier-savanna.min.css | 7 + .../styles/base16/atelier-seaside-light.css | 163 + .../base16/atelier-seaside-light.min.css | 7 + .../styles/base16/atelier-seaside.css | 163 + .../styles/base16/atelier-seaside.min.css | 7 + .../base16/atelier-sulphurpool-light.css | 163 + .../base16/atelier-sulphurpool-light.min.css | 7 + .../styles/base16/atelier-sulphurpool.css | 163 + .../styles/base16/atelier-sulphurpool.min.css | 7 + .../highlight.js/styles/base16/atlas.css | 163 + .../highlight.js/styles/base16/atlas.min.css | 7 + .../highlight.js/styles/base16/bespin.css | 163 + .../highlight.js/styles/base16/bespin.min.css | 7 + .../styles/base16/black-metal-bathory.css | 163 + .../styles/base16/black-metal-bathory.min.css | 7 + .../styles/base16/black-metal-burzum.css | 163 + .../styles/base16/black-metal-burzum.min.css | 7 + .../base16/black-metal-dark-funeral.css | 163 + .../base16/black-metal-dark-funeral.min.css | 7 + .../styles/base16/black-metal-gorgoroth.css | 163 + .../base16/black-metal-gorgoroth.min.css | 7 + .../styles/base16/black-metal-immortal.css | 163 + .../base16/black-metal-immortal.min.css | 7 + .../styles/base16/black-metal-khold.css | 163 + .../styles/base16/black-metal-khold.min.css | 7 + .../styles/base16/black-metal-marduk.css | 163 + .../styles/base16/black-metal-marduk.min.css | 7 + .../styles/base16/black-metal-mayhem.css | 163 + .../styles/base16/black-metal-mayhem.min.css | 7 + .../styles/base16/black-metal-nile.css | 163 + .../styles/base16/black-metal-nile.min.css | 7 + .../styles/base16/black-metal-venom.css | 163 + .../styles/base16/black-metal-venom.min.css | 7 + .../styles/base16/black-metal.css | 163 + .../styles/base16/black-metal.min.css | 7 + .../highlight.js/styles/base16/brewer.css | 163 + .../highlight.js/styles/base16/brewer.min.css | 7 + .../highlight.js/styles/base16/bright.css | 163 + .../highlight.js/styles/base16/bright.min.css | 7 + .../highlight.js/styles/base16/brogrammer.css | 163 + .../styles/base16/brogrammer.min.css | 7 + .../styles/base16/brush-trees-dark.css | 163 + .../styles/base16/brush-trees-dark.min.css | 7 + .../styles/base16/brush-trees.css | 163 + .../styles/base16/brush-trees.min.css | 7 + .../highlight.js/styles/base16/chalk.css | 163 + .../highlight.js/styles/base16/chalk.min.css | 7 + .../highlight.js/styles/base16/circus.css | 163 + .../highlight.js/styles/base16/circus.min.css | 7 + .../styles/base16/classic-dark.css | 163 + .../styles/base16/classic-dark.min.css | 7 + .../styles/base16/classic-light.css | 163 + .../styles/base16/classic-light.min.css | 7 + .../highlight.js/styles/base16/codeschool.css | 163 + .../styles/base16/codeschool.min.css | 7 + .../highlight.js/styles/base16/colors.css | 163 + .../highlight.js/styles/base16/colors.min.css | 7 + .../highlight.js/styles/base16/cupcake.css | 163 + .../styles/base16/cupcake.min.css | 7 + .../highlight.js/styles/base16/cupertino.css | 163 + .../styles/base16/cupertino.min.css | 7 + .../highlight.js/styles/base16/danqing.css | 163 + .../styles/base16/danqing.min.css | 7 + .../highlight.js/styles/base16/darcula.css | 163 + .../styles/base16/darcula.min.css | 7 + .../styles/base16/dark-violet.css | 163 + .../styles/base16/dark-violet.min.css | 7 + .../highlight.js/styles/base16/darkmoss.css | 163 + .../styles/base16/darkmoss.min.css | 7 + .../highlight.js/styles/base16/darktooth.css | 163 + .../styles/base16/darktooth.min.css | 7 + .../highlight.js/styles/base16/decaf.css | 163 + .../highlight.js/styles/base16/decaf.min.css | 7 + .../styles/base16/default-dark.css | 163 + .../styles/base16/default-dark.min.css | 7 + .../styles/base16/default-light.css | 163 + .../styles/base16/default-light.min.css | 7 + .../highlight.js/styles/base16/dirtysea.css | 163 + .../styles/base16/dirtysea.min.css | 7 + .../highlight.js/styles/base16/dracula.css | 163 + .../styles/base16/dracula.min.css | 7 + .../highlight.js/styles/base16/edge-dark.css | 163 + .../styles/base16/edge-dark.min.css | 7 + .../highlight.js/styles/base16/edge-light.css | 163 + .../styles/base16/edge-light.min.css | 7 + .../highlight.js/styles/base16/eighties.css | 163 + .../styles/base16/eighties.min.css | 7 + .../highlight.js/styles/base16/embers.css | 163 + .../highlight.js/styles/base16/embers.min.css | 7 + .../styles/base16/equilibrium-dark.css | 163 + .../styles/base16/equilibrium-dark.min.css | 7 + .../styles/base16/equilibrium-gray-dark.css | 163 + .../base16/equilibrium-gray-dark.min.css | 7 + .../styles/base16/equilibrium-gray-light.css | 163 + .../base16/equilibrium-gray-light.min.css | 7 + .../styles/base16/equilibrium-light.css | 163 + .../styles/base16/equilibrium-light.min.css | 7 + .../highlight.js/styles/base16/espresso.css | 163 + .../styles/base16/espresso.min.css | 7 + .../highlight.js/styles/base16/eva-dim.css | 163 + .../styles/base16/eva-dim.min.css | 7 + .../highlight.js/styles/base16/eva.css | 163 + .../highlight.js/styles/base16/eva.min.css | 7 + .../highlight.js/styles/base16/flat.css | 163 + .../highlight.js/styles/base16/flat.min.css | 7 + .../highlight.js/styles/base16/framer.css | 163 + .../highlight.js/styles/base16/framer.min.css | 7 + .../highlight.js/styles/base16/fruit-soda.css | 163 + .../styles/base16/fruit-soda.min.css | 7 + .../highlight.js/styles/base16/gigavolt.css | 163 + .../styles/base16/gigavolt.min.css | 7 + .../highlight.js/styles/base16/github.css | 163 + .../highlight.js/styles/base16/github.min.css | 7 + .../styles/base16/google-dark.css | 163 + .../styles/base16/google-dark.min.css | 7 + .../styles/base16/google-light.css | 163 + .../styles/base16/google-light.min.css | 7 + .../styles/base16/grayscale-dark.css | 163 + .../styles/base16/grayscale-dark.min.css | 7 + .../styles/base16/grayscale-light.css | 163 + .../styles/base16/grayscale-light.min.css | 7 + .../styles/base16/green-screen.css | 163 + .../styles/base16/green-screen.min.css | 7 + .../styles/base16/gruvbox-dark-hard.css | 163 + .../styles/base16/gruvbox-dark-hard.min.css | 7 + .../styles/base16/gruvbox-dark-medium.css | 163 + .../styles/base16/gruvbox-dark-medium.min.css | 7 + .../styles/base16/gruvbox-dark-pale.css | 163 + .../styles/base16/gruvbox-dark-pale.min.css | 7 + .../styles/base16/gruvbox-dark-soft.css | 163 + .../styles/base16/gruvbox-dark-soft.min.css | 7 + .../styles/base16/gruvbox-light-hard.css | 163 + .../styles/base16/gruvbox-light-hard.min.css | 7 + .../styles/base16/gruvbox-light-medium.css | 163 + .../base16/gruvbox-light-medium.min.css | 7 + .../styles/base16/gruvbox-light-soft.css | 163 + .../styles/base16/gruvbox-light-soft.min.css | 7 + .../highlight.js/styles/base16/hardcore.css | 163 + .../styles/base16/hardcore.min.css | 7 + .../styles/base16/harmonic16-dark.css | 163 + .../styles/base16/harmonic16-dark.min.css | 7 + .../styles/base16/harmonic16-light.css | 163 + .../styles/base16/harmonic16-light.min.css | 7 + .../styles/base16/heetch-dark.css | 163 + .../styles/base16/heetch-dark.min.css | 7 + .../styles/base16/heetch-light.css | 163 + .../styles/base16/heetch-light.min.css | 7 + .../highlight.js/styles/base16/helios.css | 163 + .../highlight.js/styles/base16/helios.min.css | 7 + .../highlight.js/styles/base16/hopscotch.css | 163 + .../styles/base16/hopscotch.min.css | 7 + .../styles/base16/horizon-dark.css | 163 + .../styles/base16/horizon-dark.min.css | 7 + .../styles/base16/horizon-light.css | 163 + .../styles/base16/horizon-light.min.css | 7 + .../styles/base16/humanoid-dark.css | 163 + .../styles/base16/humanoid-dark.min.css | 7 + .../styles/base16/humanoid-light.css | 163 + .../styles/base16/humanoid-light.min.css | 7 + .../highlight.js/styles/base16/ia-dark.css | 163 + .../styles/base16/ia-dark.min.css | 7 + .../highlight.js/styles/base16/ia-light.css | 163 + .../styles/base16/ia-light.min.css | 7 + .../highlight.js/styles/base16/icy-dark.css | 163 + .../styles/base16/icy-dark.min.css | 7 + .../highlight.js/styles/base16/ir-black.css | 163 + .../styles/base16/ir-black.min.css | 7 + .../highlight.js/styles/base16/isotope.css | 163 + .../styles/base16/isotope.min.css | 7 + .../highlight.js/styles/base16/kimber.css | 163 + .../highlight.js/styles/base16/kimber.min.css | 7 + .../styles/base16/london-tube.css | 163 + .../styles/base16/london-tube.min.css | 7 + .../highlight.js/styles/base16/macintosh.css | 163 + .../styles/base16/macintosh.min.css | 7 + .../highlight.js/styles/base16/marrakesh.css | 163 + .../styles/base16/marrakesh.min.css | 7 + .../highlight.js/styles/base16/materia.css | 163 + .../styles/base16/materia.min.css | 7 + .../styles/base16/material-darker.css | 163 + .../styles/base16/material-darker.min.css | 7 + .../styles/base16/material-lighter.css | 163 + .../styles/base16/material-lighter.min.css | 7 + .../styles/base16/material-palenight.css | 163 + .../styles/base16/material-palenight.min.css | 7 + .../styles/base16/material-vivid.css | 163 + .../styles/base16/material-vivid.min.css | 7 + .../highlight.js/styles/base16/material.css | 163 + .../styles/base16/material.min.css | 7 + .../styles/base16/mellow-purple.css | 163 + .../styles/base16/mellow-purple.min.css | 7 + .../styles/base16/mexico-light.css | 163 + .../styles/base16/mexico-light.min.css | 7 + .../highlight.js/styles/base16/mocha.css | 163 + .../highlight.js/styles/base16/mocha.min.css | 7 + .../highlight.js/styles/base16/monokai.css | 163 + .../styles/base16/monokai.min.css | 7 + .../highlight.js/styles/base16/nebula.css | 163 + .../highlight.js/styles/base16/nebula.min.css | 7 + .../highlight.js/styles/base16/nord.css | 163 + .../highlight.js/styles/base16/nord.min.css | 7 + .../highlight.js/styles/base16/nova.css | 163 + .../highlight.js/styles/base16/nova.min.css | 7 + .../highlight.js/styles/base16/ocean.css | 163 + .../highlight.js/styles/base16/ocean.min.css | 7 + .../styles/base16/oceanicnext.css | 163 + .../styles/base16/oceanicnext.min.css | 7 + .../highlight.js/styles/base16/one-light.css | 163 + .../styles/base16/one-light.min.css | 7 + .../highlight.js/styles/base16/onedark.css | 163 + .../styles/base16/onedark.min.css | 7 + .../styles/base16/outrun-dark.css | 163 + .../styles/base16/outrun-dark.min.css | 7 + .../styles/base16/papercolor-dark.css | 163 + .../styles/base16/papercolor-dark.min.css | 7 + .../styles/base16/papercolor-light.css | 163 + .../styles/base16/papercolor-light.min.css | 7 + .../highlight.js/styles/base16/paraiso.css | 163 + .../styles/base16/paraiso.min.css | 7 + .../highlight.js/styles/base16/pasque.css | 163 + .../highlight.js/styles/base16/pasque.min.css | 7 + .../highlight.js/styles/base16/phd.css | 163 + .../highlight.js/styles/base16/phd.min.css | 7 + .../highlight.js/styles/base16/pico.css | 163 + .../highlight.js/styles/base16/pico.min.css | 7 + .../highlight.js/styles/base16/pop.css | 163 + .../highlight.js/styles/base16/pop.min.css | 7 + .../highlight.js/styles/base16/porple.css | 163 + .../highlight.js/styles/base16/porple.min.css | 7 + .../highlight.js/styles/base16/qualia.css | 163 + .../highlight.js/styles/base16/qualia.min.css | 7 + .../highlight.js/styles/base16/railscasts.css | 163 + .../styles/base16/railscasts.min.css | 7 + .../highlight.js/styles/base16/rebecca.css | 163 + .../styles/base16/rebecca.min.css | 7 + .../styles/base16/ros-pine-dawn.css | 163 + .../styles/base16/ros-pine-dawn.min.css | 7 + .../styles/base16/ros-pine-moon.css | 163 + .../styles/base16/ros-pine-moon.min.css | 7 + .../highlight.js/styles/base16/ros-pine.css | 163 + .../styles/base16/ros-pine.min.css | 7 + .../highlight.js/styles/base16/sagelight.css | 163 + .../styles/base16/sagelight.min.css | 7 + .../highlight.js/styles/base16/sandcastle.css | 163 + .../styles/base16/sandcastle.min.css | 7 + .../highlight.js/styles/base16/seti-ui.css | 163 + .../styles/base16/seti-ui.min.css | 7 + .../styles/base16/shapeshifter.css | 163 + .../styles/base16/shapeshifter.min.css | 7 + .../highlight.js/styles/base16/silk-dark.css | 163 + .../styles/base16/silk-dark.min.css | 7 + .../highlight.js/styles/base16/silk-light.css | 163 + .../styles/base16/silk-light.min.css | 7 + .../highlight.js/styles/base16/snazzy.css | 163 + .../highlight.js/styles/base16/snazzy.min.css | 7 + .../styles/base16/solar-flare-light.css | 163 + .../styles/base16/solar-flare-light.min.css | 7 + .../styles/base16/solar-flare.css | 163 + .../styles/base16/solar-flare.min.css | 7 + .../styles/base16/solarized-dark.css | 163 + .../styles/base16/solarized-dark.min.css | 7 + .../styles/base16/solarized-light.css | 163 + .../styles/base16/solarized-light.min.css | 7 + .../highlight.js/styles/base16/spacemacs.css | 163 + .../styles/base16/spacemacs.min.css | 7 + .../highlight.js/styles/base16/summercamp.css | 163 + .../styles/base16/summercamp.min.css | 7 + .../styles/base16/summerfruit-dark.css | 163 + .../styles/base16/summerfruit-dark.min.css | 7 + .../styles/base16/summerfruit-light.css | 163 + .../styles/base16/summerfruit-light.min.css | 7 + .../base16/synth-midnight-terminal-dark.css | 163 + .../synth-midnight-terminal-dark.min.css | 7 + .../base16/synth-midnight-terminal-light.css | 163 + .../synth-midnight-terminal-light.min.css | 7 + .../highlight.js/styles/base16/tango.css | 163 + .../highlight.js/styles/base16/tango.min.css | 7 + .../highlight.js/styles/base16/tender.css | 163 + .../highlight.js/styles/base16/tender.min.css | 7 + .../styles/base16/tomorrow-night.css | 163 + .../styles/base16/tomorrow-night.min.css | 7 + .../highlight.js/styles/base16/tomorrow.css | 163 + .../styles/base16/tomorrow.min.css | 7 + .../highlight.js/styles/base16/twilight.css | 163 + .../styles/base16/twilight.min.css | 7 + .../styles/base16/unikitty-dark.css | 163 + .../styles/base16/unikitty-dark.min.css | 7 + .../styles/base16/unikitty-light.css | 163 + .../styles/base16/unikitty-light.min.css | 7 + .../highlight.js/styles/base16/vulcan.css | 163 + .../highlight.js/styles/base16/vulcan.min.css | 7 + .../styles/base16/windows-10-light.css | 163 + .../styles/base16/windows-10-light.min.css | 7 + .../highlight.js/styles/base16/windows-10.css | 163 + .../styles/base16/windows-10.min.css | 7 + .../styles/base16/windows-95-light.css | 163 + .../styles/base16/windows-95-light.min.css | 7 + .../highlight.js/styles/base16/windows-95.css | 163 + .../styles/base16/windows-95.min.css | 7 + .../base16/windows-high-contrast-light.css | 163 + .../windows-high-contrast-light.min.css | 7 + .../styles/base16/windows-high-contrast.css | 163 + .../base16/windows-high-contrast.min.css | 7 + .../styles/base16/windows-nt-light.css | 163 + .../styles/base16/windows-nt-light.min.css | 7 + .../highlight.js/styles/base16/windows-nt.css | 163 + .../styles/base16/windows-nt.min.css | 7 + .../highlight.js/styles/base16/woodland.css | 163 + .../styles/base16/woodland.min.css | 7 + .../highlight.js/styles/base16/xcode-dusk.css | 163 + .../styles/base16/xcode-dusk.min.css | 7 + .../highlight.js/styles/base16/zenburn.css | 163 + .../styles/base16/zenburn.min.css | 7 + .../highlight.js/styles/brown-paper.css | 63 + .../highlight.js/styles/brown-paper.min.css | 1 + .../highlight.js/styles/brown-papersq.png | Bin 0 -> 18198 bytes .../highlight.js/styles/codepen-embed.css | 57 + .../highlight.js/styles/codepen-embed.min.css | 1 + .../highlight.js/styles/color-brewer.css | 66 + .../highlight.js/styles/color-brewer.min.css | 1 + .../highlight.js/styles/cybertopia-cherry.css | 103 + .../styles/cybertopia-cherry.min.css | 1 + .../highlight.js/styles/cybertopia-dimmer.css | 103 + .../styles/cybertopia-dimmer.min.css | 1 + .../highlight.js/styles/cybertopia-icecap.css | 103 + .../styles/cybertopia-icecap.min.css | 1 + .../styles/cybertopia-saturated.css | 103 + .../styles/cybertopia-saturated.min.css | 1 + .../node_modules/highlight.js/styles/dark.css | 62 + .../highlight.js/styles/dark.min.css | 1 + .../highlight.js/styles/default.css | 117 + .../highlight.js/styles/default.min.css | 9 + .../highlight.js/styles/devibeans.css | 90 + .../highlight.js/styles/devibeans.min.css | 7 + .../highlight.js/styles/docco.css | 83 + .../highlight.js/styles/docco.min.css | 1 + .../node_modules/highlight.js/styles/far.css | 67 + .../highlight.js/styles/far.min.css | 1 + .../highlight.js/styles/felipec.css | 94 + .../highlight.js/styles/felipec.min.css | 7 + .../highlight.js/styles/foundation.css | 80 + .../highlight.js/styles/foundation.min.css | 1 + .../styles/github-dark-dimmed.css | 117 + .../styles/github-dark-dimmed.min.css | 9 + .../highlight.js/styles/github-dark.css | 118 + .../highlight.js/styles/github-dark.min.css | 10 + .../highlight.js/styles/github.css | 118 + .../highlight.js/styles/github.min.css | 10 + .../node_modules/highlight.js/styles/gml.css | 72 + .../highlight.js/styles/gml.min.css | 1 + .../highlight.js/styles/googlecode.css | 79 + .../highlight.js/styles/googlecode.min.css | 1 + .../highlight.js/styles/gradient-dark.css | 90 + .../highlight.js/styles/gradient-dark.min.css | 1 + .../highlight.js/styles/gradient-light.css | 90 + .../styles/gradient-light.min.css | 1 + .../highlight.js/styles/grayscale.css | 89 + .../highlight.js/styles/grayscale.min.css | 1 + .../highlight.js/styles/hybrid.css | 88 + .../highlight.js/styles/hybrid.min.css | 1 + .../node_modules/highlight.js/styles/idea.css | 86 + .../highlight.js/styles/idea.min.css | 1 + .../highlight.js/styles/intellij-light.css | 107 + .../styles/intellij-light.min.css | 1 + .../highlight.js/styles/ir-black.css | 66 + .../highlight.js/styles/ir-black.min.css | 1 + .../highlight.js/styles/isbl-editor-dark.css | 94 + .../styles/isbl-editor-dark.min.css | 1 + .../highlight.js/styles/isbl-editor-light.css | 93 + .../styles/isbl-editor-light.min.css | 1 + .../highlight.js/styles/kimbie-dark.css | 69 + .../highlight.js/styles/kimbie-dark.min.css | 1 + .../highlight.js/styles/kimbie-light.css | 69 + .../highlight.js/styles/kimbie-light.min.css | 1 + .../highlight.js/styles/lightfair.css | 81 + .../highlight.js/styles/lightfair.min.css | 1 + .../highlight.js/styles/lioshi.css | 76 + .../highlight.js/styles/lioshi.min.css | 1 + .../highlight.js/styles/magula.css | 66 + .../highlight.js/styles/magula.min.css | 1 + .../highlight.js/styles/mono-blue.css | 56 + .../highlight.js/styles/mono-blue.min.css | 1 + .../highlight.js/styles/monokai-sublime.css | 76 + .../styles/monokai-sublime.min.css | 1 + .../highlight.js/styles/monokai.css | 70 + .../highlight.js/styles/monokai.min.css | 1 + .../highlight.js/styles/night-owl.css | 174 + .../highlight.js/styles/night-owl.min.css | 1 + .../highlight.js/styles/nnfx-dark.css | 104 + .../highlight.js/styles/nnfx-dark.min.css | 10 + .../highlight.js/styles/nnfx-light.css | 104 + .../highlight.js/styles/nnfx-light.min.css | 10 + .../node_modules/highlight.js/styles/nord.css | 275 + .../highlight.js/styles/nord.min.css | 1 + .../highlight.js/styles/obsidian.css | 79 + .../highlight.js/styles/obsidian.min.css | 1 + .../highlight.js/styles/panda-syntax-dark.css | 92 + .../styles/panda-syntax-dark.min.css | 1 + .../styles/panda-syntax-light.css | 89 + .../styles/panda-syntax-light.min.css | 1 + .../highlight.js/styles/paraiso-dark.css | 67 + .../highlight.js/styles/paraiso-dark.min.css | 1 + .../highlight.js/styles/paraiso-light.css | 67 + .../highlight.js/styles/paraiso-light.min.css | 1 + .../highlight.js/styles/pojoaque.css | 76 + .../highlight.js/styles/pojoaque.jpg | Bin 0 -> 1186 bytes .../highlight.js/styles/pojoaque.min.css | 1 + .../highlight.js/styles/purebasic.css | 103 + .../highlight.js/styles/purebasic.min.css | 1 + .../highlight.js/styles/qtcreator-dark.css | 76 + .../styles/qtcreator-dark.min.css | 1 + .../highlight.js/styles/qtcreator-light.css | 74 + .../styles/qtcreator-light.min.css | 1 + .../highlight.js/styles/rainbow.css | 77 + .../highlight.js/styles/rainbow.min.css | 1 + .../highlight.js/styles/rose-pine-dawn.css | 107 + .../styles/rose-pine-dawn.min.css | 4 + .../highlight.js/styles/rose-pine-moon.css | 109 + .../styles/rose-pine-moon.min.css | 4 + .../highlight.js/styles/rose-pine.css | 109 + .../highlight.js/styles/rose-pine.min.css | 4 + .../highlight.js/styles/routeros.css | 86 + .../highlight.js/styles/routeros.min.css | 1 + .../highlight.js/styles/school-book.css | 62 + .../highlight.js/styles/school-book.min.css | 1 + .../highlight.js/styles/shades-of-purple.css | 84 + .../styles/shades-of-purple.min.css | 1 + .../highlight.js/styles/srcery.css | 89 + .../highlight.js/styles/srcery.min.css | 1 + .../styles/stackoverflow-dark.css | 117 + .../styles/stackoverflow-dark.min.css | 13 + .../styles/stackoverflow-light.css | 117 + .../styles/stackoverflow-light.min.css | 13 + .../highlight.js/styles/sunburst.css | 89 + .../highlight.js/styles/sunburst.min.css | 1 + .../highlight.js/styles/tokyo-night-dark.css | 114 + .../styles/tokyo-night-dark.min.css | 8 + .../highlight.js/styles/tokyo-night-light.css | 114 + .../styles/tokyo-night-light.min.css | 8 + .../styles/tomorrow-night-blue.css | 69 + .../styles/tomorrow-night-blue.min.css | 1 + .../styles/tomorrow-night-bright.css | 68 + .../styles/tomorrow-night-bright.min.css | 1 + .../node_modules/highlight.js/styles/vs.css | 63 + .../highlight.js/styles/vs.min.css | 1 + .../highlight.js/styles/vs2015.css | 100 + .../highlight.js/styles/vs2015.min.css | 1 + .../highlight.js/styles/xcode.css | 90 + .../highlight.js/styles/xcode.min.css | 1 + .../highlight.js/styles/xt256.css | 79 + .../highlight.js/styles/xt256.min.css | 1 + .../highlight.js/types/index.d.ts | 274 + frontend/node_modules/htmlparser2/LICENSE | 18 + frontend/node_modules/htmlparser2/README.md | 171 + .../node_modules/htmlparser2/lib/Parser.d.ts | 198 + .../htmlparser2/lib/Parser.d.ts.map | 1 + .../node_modules/htmlparser2/lib/Parser.js | 519 + .../htmlparser2/lib/Parser.js.map | 1 + .../htmlparser2/lib/Tokenizer.d.ts | 126 + .../htmlparser2/lib/Tokenizer.d.ts.map | 1 + .../node_modules/htmlparser2/lib/Tokenizer.js | 791 + .../htmlparser2/lib/Tokenizer.js.map | 1 + .../htmlparser2/lib/WritableStream.d.ts | 17 + .../htmlparser2/lib/WritableStream.d.ts.map | 1 + .../htmlparser2/lib/WritableStream.js | 54 + .../htmlparser2/lib/WritableStream.js.map | 1 + .../htmlparser2/lib/esm/Parser.d.ts | 198 + .../htmlparser2/lib/esm/Parser.d.ts.map | 1 + .../htmlparser2/lib/esm/Parser.js | 490 + .../htmlparser2/lib/esm/Parser.js.map | 1 + .../htmlparser2/lib/esm/Tokenizer.d.ts | 126 + .../htmlparser2/lib/esm/Tokenizer.d.ts.map | 1 + .../htmlparser2/lib/esm/Tokenizer.js | 784 + .../htmlparser2/lib/esm/Tokenizer.js.map | 1 + .../htmlparser2/lib/esm/WritableStream.d.ts | 17 + .../lib/esm/WritableStream.d.ts.map | 1 + .../htmlparser2/lib/esm/WritableStream.js | 32 + .../htmlparser2/lib/esm/WritableStream.js.map | 1 + .../htmlparser2/lib/esm/index.d.ts | 54 + .../htmlparser2/lib/esm/index.d.ts.map | 1 + .../node_modules/htmlparser2/lib/esm/index.js | 74 + .../htmlparser2/lib/esm/index.js.map | 1 + .../htmlparser2/lib/esm/package.json | 1 + .../node_modules/htmlparser2/lib/index.d.ts | 54 + .../htmlparser2/lib/index.d.ts.map | 1 + .../node_modules/htmlparser2/lib/index.js | 114 + .../node_modules/htmlparser2/lib/index.js.map | 1 + .../node_modules/htmlparser2/package.json | 97 + .../iconv-lite/.github/dependabot.yml | 11 + .../iconv-lite/.idea/codeStyles/Project.xml | 47 + .../.idea/codeStyles/codeStyleConfig.xml | 5 + .../iconv-lite/.idea/iconv-lite.iml | 12 + .../inspectionProfiles/Project_Default.xml | 6 + .../node_modules/iconv-lite/.idea/modules.xml | 8 + .../node_modules/iconv-lite/.idea/vcs.xml | 6 + frontend/node_modules/iconv-lite/Changelog.md | 212 + frontend/node_modules/iconv-lite/LICENSE | 21 + frontend/node_modules/iconv-lite/README.md | 130 + .../iconv-lite/encodings/dbcs-codec.js | 597 + .../iconv-lite/encodings/dbcs-data.js | 188 + .../iconv-lite/encodings/index.js | 23 + .../iconv-lite/encodings/internal.js | 198 + .../iconv-lite/encodings/sbcs-codec.js | 72 + .../encodings/sbcs-data-generated.js | 451 + .../iconv-lite/encodings/sbcs-data.js | 179 + .../encodings/tables/big5-added.json | 122 + .../iconv-lite/encodings/tables/cp936.json | 264 + .../iconv-lite/encodings/tables/cp949.json | 273 + .../iconv-lite/encodings/tables/cp950.json | 177 + .../iconv-lite/encodings/tables/eucjp.json | 182 + .../encodings/tables/gb18030-ranges.json | 1 + .../encodings/tables/gbk-added.json | 56 + .../iconv-lite/encodings/tables/shiftjis.json | 125 + .../iconv-lite/encodings/utf16.js | 197 + .../iconv-lite/encodings/utf32.js | 319 + .../node_modules/iconv-lite/encodings/utf7.js | 290 + .../iconv-lite/lib/bom-handling.js | 52 + .../node_modules/iconv-lite/lib/index.d.ts | 41 + frontend/node_modules/iconv-lite/lib/index.js | 180 + .../node_modules/iconv-lite/lib/streams.js | 109 + frontend/node_modules/iconv-lite/package.json | 44 + frontend/node_modules/internmap/LICENSE | 13 + frontend/node_modules/internmap/README.md | 94 + .../node_modules/internmap/dist/internmap.js | 75 + .../internmap/dist/internmap.min.js | 2 + frontend/node_modules/internmap/package.json | 43 + frontend/node_modules/internmap/src/index.js | 61 + frontend/node_modules/katex/LICENSE | 21 + frontend/node_modules/katex/README.md | 125 + frontend/node_modules/katex/cli.js | 112 + .../katex/contrib/auto-render/README.md | 8 + .../katex/contrib/auto-render/auto-render.js | 142 + .../katex/contrib/auto-render/index.html | 56 + .../contrib/auto-render/splitAtDelimiters.js | 85 + .../auto-render/test/auto-render-spec.js | 363 + .../katex/contrib/copy-tex/README.md | 39 + .../katex/contrib/copy-tex/copy-tex.js | 51 + .../katex/contrib/copy-tex/index.html | 38 + .../katex/contrib/copy-tex/katex2tex.js | 61 + .../contrib/mathtex-script-type/README.md | 38 + .../mathtex-script-type.js | 22 + .../katex/contrib/mhchem/README.md | 23 + .../katex/contrib/mhchem/mhchem.js | 1695 ++ .../render-a11y-string/render-a11y-string.js | 746 + .../test/render-a11y-string-spec.js | 549 + frontend/node_modules/katex/dist/README.md | 125 + .../katex/dist/contrib/auto-render.js | 338 + .../katex/dist/contrib/auto-render.min.js | 1 + .../katex/dist/contrib/auto-render.mjs | 244 + .../katex/dist/contrib/copy-tex.js | 127 + .../katex/dist/contrib/copy-tex.min.js | 1 + .../katex/dist/contrib/copy-tex.mjs | 105 + .../katex/dist/contrib/mathtex-script-type.js | 109 + .../dist/contrib/mathtex-script-type.min.js | 1 + .../dist/contrib/mathtex-script-type.mjs | 24 + .../node_modules/katex/dist/contrib/mhchem.js | 3213 +++ .../katex/dist/contrib/mhchem.min.js | 1 + .../katex/dist/contrib/mhchem.mjs | 3109 +++ .../katex/dist/contrib/render-a11y-string.js | 887 + .../dist/contrib/render-a11y-string.min.js | 1 + .../katex/dist/contrib/render-a11y-string.mjs | 800 + .../katex/dist/fonts/KaTeX_AMS-Regular.ttf | Bin 0 -> 63632 bytes .../katex/dist/fonts/KaTeX_AMS-Regular.woff | Bin 0 -> 33516 bytes .../katex/dist/fonts/KaTeX_AMS-Regular.woff2 | Bin 0 -> 28076 bytes .../dist/fonts/KaTeX_Caligraphic-Bold.ttf | Bin 0 -> 12368 bytes .../dist/fonts/KaTeX_Caligraphic-Bold.woff | Bin 0 -> 7716 bytes .../dist/fonts/KaTeX_Caligraphic-Bold.woff2 | Bin 0 -> 6912 bytes .../dist/fonts/KaTeX_Caligraphic-Regular.ttf | Bin 0 -> 12344 bytes .../dist/fonts/KaTeX_Caligraphic-Regular.woff | Bin 0 -> 7656 bytes .../fonts/KaTeX_Caligraphic-Regular.woff2 | Bin 0 -> 6908 bytes .../katex/dist/fonts/KaTeX_Fraktur-Bold.ttf | Bin 0 -> 19584 bytes .../katex/dist/fonts/KaTeX_Fraktur-Bold.woff | Bin 0 -> 13296 bytes .../katex/dist/fonts/KaTeX_Fraktur-Bold.woff2 | Bin 0 -> 11348 bytes .../dist/fonts/KaTeX_Fraktur-Regular.ttf | Bin 0 -> 19572 bytes .../dist/fonts/KaTeX_Fraktur-Regular.woff | Bin 0 -> 13208 bytes .../dist/fonts/KaTeX_Fraktur-Regular.woff2 | Bin 0 -> 11316 bytes .../katex/dist/fonts/KaTeX_Main-Bold.ttf | Bin 0 -> 51336 bytes .../katex/dist/fonts/KaTeX_Main-Bold.woff | Bin 0 -> 29912 bytes .../katex/dist/fonts/KaTeX_Main-Bold.woff2 | Bin 0 -> 25324 bytes .../dist/fonts/KaTeX_Main-BoldItalic.ttf | Bin 0 -> 32968 bytes .../dist/fonts/KaTeX_Main-BoldItalic.woff | Bin 0 -> 19412 bytes .../dist/fonts/KaTeX_Main-BoldItalic.woff2 | Bin 0 -> 16780 bytes .../katex/dist/fonts/KaTeX_Main-Italic.ttf | Bin 0 -> 33580 bytes .../katex/dist/fonts/KaTeX_Main-Italic.woff | Bin 0 -> 19676 bytes .../katex/dist/fonts/KaTeX_Main-Italic.woff2 | Bin 0 -> 16988 bytes .../katex/dist/fonts/KaTeX_Main-Regular.ttf | Bin 0 -> 53580 bytes .../katex/dist/fonts/KaTeX_Main-Regular.woff | Bin 0 -> 30772 bytes .../katex/dist/fonts/KaTeX_Main-Regular.woff2 | Bin 0 -> 26272 bytes .../dist/fonts/KaTeX_Math-BoldItalic.ttf | Bin 0 -> 31196 bytes .../dist/fonts/KaTeX_Math-BoldItalic.woff | Bin 0 -> 18668 bytes .../dist/fonts/KaTeX_Math-BoldItalic.woff2 | Bin 0 -> 16400 bytes .../katex/dist/fonts/KaTeX_Math-Italic.ttf | Bin 0 -> 31308 bytes .../katex/dist/fonts/KaTeX_Math-Italic.woff | Bin 0 -> 18748 bytes .../katex/dist/fonts/KaTeX_Math-Italic.woff2 | Bin 0 -> 16440 bytes .../katex/dist/fonts/KaTeX_SansSerif-Bold.ttf | Bin 0 -> 24504 bytes .../dist/fonts/KaTeX_SansSerif-Bold.woff | Bin 0 -> 14408 bytes .../dist/fonts/KaTeX_SansSerif-Bold.woff2 | Bin 0 -> 12216 bytes .../dist/fonts/KaTeX_SansSerif-Italic.ttf | Bin 0 -> 22364 bytes .../dist/fonts/KaTeX_SansSerif-Italic.woff | Bin 0 -> 14112 bytes .../dist/fonts/KaTeX_SansSerif-Italic.woff2 | Bin 0 -> 12028 bytes .../dist/fonts/KaTeX_SansSerif-Regular.ttf | Bin 0 -> 19436 bytes .../dist/fonts/KaTeX_SansSerif-Regular.woff | Bin 0 -> 12316 bytes .../dist/fonts/KaTeX_SansSerif-Regular.woff2 | Bin 0 -> 10344 bytes .../katex/dist/fonts/KaTeX_Script-Regular.ttf | Bin 0 -> 16648 bytes .../dist/fonts/KaTeX_Script-Regular.woff | Bin 0 -> 10588 bytes .../dist/fonts/KaTeX_Script-Regular.woff2 | Bin 0 -> 9644 bytes .../katex/dist/fonts/KaTeX_Size1-Regular.ttf | Bin 0 -> 12228 bytes .../katex/dist/fonts/KaTeX_Size1-Regular.woff | Bin 0 -> 6496 bytes .../dist/fonts/KaTeX_Size1-Regular.woff2 | Bin 0 -> 5468 bytes .../katex/dist/fonts/KaTeX_Size2-Regular.ttf | Bin 0 -> 11508 bytes .../katex/dist/fonts/KaTeX_Size2-Regular.woff | Bin 0 -> 6188 bytes .../dist/fonts/KaTeX_Size2-Regular.woff2 | Bin 0 -> 5208 bytes .../katex/dist/fonts/KaTeX_Size3-Regular.ttf | Bin 0 -> 7588 bytes .../katex/dist/fonts/KaTeX_Size3-Regular.woff | Bin 0 -> 4420 bytes .../dist/fonts/KaTeX_Size3-Regular.woff2 | Bin 0 -> 3624 bytes .../katex/dist/fonts/KaTeX_Size4-Regular.ttf | Bin 0 -> 10364 bytes .../katex/dist/fonts/KaTeX_Size4-Regular.woff | Bin 0 -> 5980 bytes .../dist/fonts/KaTeX_Size4-Regular.woff2 | Bin 0 -> 4928 bytes .../dist/fonts/KaTeX_Typewriter-Regular.ttf | Bin 0 -> 27556 bytes .../dist/fonts/KaTeX_Typewriter-Regular.woff | Bin 0 -> 16028 bytes .../dist/fonts/KaTeX_Typewriter-Regular.woff2 | Bin 0 -> 13568 bytes frontend/node_modules/katex/dist/katex.css | 1210 + frontend/node_modules/katex/dist/katex.js | 19092 ++++++++++++++ .../node_modules/katex/dist/katex.min.css | 1 + frontend/node_modules/katex/dist/katex.min.js | 1 + frontend/node_modules/katex/dist/katex.mjs | 18549 ++++++++++++++ frontend/node_modules/katex/katex.js | 247 + frontend/node_modules/katex/package.json | 195 + frontend/node_modules/katex/src/Lexer.js | 122 + .../node_modules/katex/src/MacroExpander.js | 470 + frontend/node_modules/katex/src/Namespace.js | 129 + frontend/node_modules/katex/src/Options.js | 319 + frontend/node_modules/katex/src/ParseError.js | 86 + frontend/node_modules/katex/src/Parser.js | 1041 + frontend/node_modules/katex/src/Settings.js | 360 + .../node_modules/katex/src/SourceLocation.js | 42 + frontend/node_modules/katex/src/Style.js | 130 + frontend/node_modules/katex/src/Token.js | 47 + .../node_modules/katex/src/buildCommon.js | 784 + frontend/node_modules/katex/src/buildHTML.js | 406 + .../node_modules/katex/src/buildMathML.js | 322 + frontend/node_modules/katex/src/buildTree.js | 67 + .../katex/src/defineEnvironment.js | 117 + .../node_modules/katex/src/defineFunction.js | 223 + .../node_modules/katex/src/defineMacro.js | 125 + frontend/node_modules/katex/src/delimiter.js | 835 + frontend/node_modules/katex/src/domTree.js | 632 + .../node_modules/katex/src/environments.js | 9 + .../katex/src/environments/array.js | 1118 + .../node_modules/katex/src/environments/cd.js | 313 + .../node_modules/katex/src/fontMetrics.js | 282 + .../node_modules/katex/src/fontMetricsData.js | 2077 ++ .../node_modules/katex/src/fonts/Makefile | 139 + .../node_modules/katex/src/fonts/default.cfg | 20 + .../katex/src/fonts/generate_fonts.py | 58 + .../katex/src/fonts/lib/Extra.otf | Bin 0 -> 1332 bytes .../katex/src/fonts/lib/Space.ttx | 234 + .../node_modules/katex/src/fonts/makeBlacker | 49 + frontend/node_modules/katex/src/fonts/makeFF | 2005 ++ .../node_modules/katex/src/fonts/xbbold.mf | 182 + frontend/node_modules/katex/src/functions.js | 55 + .../katex/src/functions/accent.js | 284 + .../katex/src/functions/accentunder.js | 60 + .../node_modules/katex/src/functions/arrow.js | 144 + .../node_modules/katex/src/functions/char.js | 45 + .../node_modules/katex/src/functions/color.js | 88 + .../node_modules/katex/src/functions/cr.js | 61 + .../node_modules/katex/src/functions/def.js | 210 + .../katex/src/functions/delimsizing.js | 360 + .../katex/src/functions/enclose.js | 323 + .../katex/src/functions/environment.js | 62 + .../node_modules/katex/src/functions/font.js | 120 + .../katex/src/functions/genfrac.js | 510 + .../node_modules/katex/src/functions/hbox.js | 39 + .../katex/src/functions/horizBrace.js | 137 + .../node_modules/katex/src/functions/href.js | 93 + .../node_modules/katex/src/functions/html.js | 102 + .../katex/src/functions/htmlmathml.js | 34 + .../katex/src/functions/includegraphics.js | 151 + .../node_modules/katex/src/functions/kern.js | 56 + .../node_modules/katex/src/functions/lap.js | 74 + .../node_modules/katex/src/functions/math.js | 42 + .../katex/src/functions/mathchoice.js | 51 + .../katex/src/functions/mclass.js | 168 + .../node_modules/katex/src/functions/op.js | 334 + .../katex/src/functions/operatorname.js | 164 + .../katex/src/functions/ordgroup.js | 22 + .../katex/src/functions/overline.js | 59 + .../katex/src/functions/phantom.js | 117 + .../node_modules/katex/src/functions/pmb.js | 44 + .../katex/src/functions/raisebox.js | 46 + .../node_modules/katex/src/functions/relax.js | 18 + .../node_modules/katex/src/functions/rule.js | 77 + .../katex/src/functions/sizing.js | 91 + .../node_modules/katex/src/functions/smash.js | 110 + .../node_modules/katex/src/functions/sqrt.js | 125 + .../katex/src/functions/styling.js | 73 + .../katex/src/functions/supsub.js | 267 + .../katex/src/functions/symbolsOp.js | 34 + .../katex/src/functions/symbolsOrd.js | 62 + .../katex/src/functions/symbolsSpacing.js | 73 + .../node_modules/katex/src/functions/tag.js | 40 + .../node_modules/katex/src/functions/text.js | 76 + .../katex/src/functions/underline.js | 58 + .../src/functions/utils/assembleSupSub.js | 120 + .../katex/src/functions/vcenter.js | 44 + .../node_modules/katex/src/functions/verb.js | 58 + frontend/node_modules/katex/src/macros.js | 1033 + frontend/node_modules/katex/src/mathMLTree.js | 267 + .../node_modules/katex/src/metrics/README.md | 23 + .../katex/src/metrics/extract_tfms.py | 114 + .../katex/src/metrics/extract_ttfs.py | 122 + .../katex/src/metrics/format_json.py | 28 + .../node_modules/katex/src/metrics/mapping.pl | 1224 + .../katex/src/metrics/parse_tfm.py | 211 + frontend/node_modules/katex/src/parseNode.js | 524 + frontend/node_modules/katex/src/parseTree.js | 49 + .../node_modules/katex/src/spacingData.js | 108 + frontend/node_modules/katex/src/stretchy.js | 378 + .../node_modules/katex/src/styles/fonts.scss | 71 + .../node_modules/katex/src/styles/katex.scss | 664 + .../node_modules/katex/src/svgGeometry.js | 545 + frontend/node_modules/katex/src/symbols.js | 890 + frontend/node_modules/katex/src/tree.js | 78 + frontend/node_modules/katex/src/types.js | 36 + .../node_modules/katex/src/unicodeAccents.js | 18 + .../node_modules/katex/src/unicodeScripts.js | 126 + .../node_modules/katex/src/unicodeSupOrSub.js | 108 + .../node_modules/katex/src/unicodeSymbols.js | 32 + frontend/node_modules/katex/src/units.js | 106 + frontend/node_modules/katex/src/utils.js | 130 + .../node_modules/katex/src/wide-character.js | 111 + frontend/node_modules/katex/types/katex.d.ts | 258 + frontend/node_modules/linkify-it/LICENSE | 22 + frontend/node_modules/linkify-it/README.md | 196 + .../linkify-it/build/index.cjs.js | 832 + frontend/node_modules/linkify-it/index.mjs | 642 + frontend/node_modules/linkify-it/lib/re.mjs | 189 + frontend/node_modules/linkify-it/package.json | 58 + frontend/node_modules/markdown-it-ins/LICENSE | 22 + .../node_modules/markdown-it-ins/README.md | 40 + .../markdown-it-ins/dist/index.cjs.js | 113 + .../markdown-it-ins/dist/markdown-it-ins.js | 114 + .../dist/markdown-it-ins.min.js | 2 + .../node_modules/markdown-it-ins/index.mjs | 123 + .../node_modules/markdown-it-ins/package.json | 49 + .../node_modules/markdown-it-mark/LICENSE | 22 + .../node_modules/markdown-it-mark/README.md | 40 + .../markdown-it-mark/dist/index.cjs.js | 113 + .../markdown-it-mark/dist/markdown-it-mark.js | 114 + .../dist/markdown-it-mark.min.js | 2 + .../node_modules/markdown-it-mark/index.mjs | 123 + .../markdown-it-mark/package.json | 48 + frontend/node_modules/markdown-it-sub/LICENSE | 22 + .../node_modules/markdown-it-sub/README.md | 40 + .../markdown-it-sub/dist/index.cjs.js | 59 + .../markdown-it-sub/dist/markdown-it-sub.js | 60 + .../dist/markdown-it-sub.min.js | 2 + .../node_modules/markdown-it-sub/index.mjs | 60 + .../node_modules/markdown-it-sub/package.json | 49 + frontend/node_modules/markdown-it-sup/LICENSE | 22 + .../node_modules/markdown-it-sup/README.md | 40 + .../markdown-it-sup/dist/index.cjs.js | 59 + .../markdown-it-sup/dist/markdown-it-sup.js | 60 + .../dist/markdown-it-sup.min.js | 2 + .../node_modules/markdown-it-sup/index.mjs | 60 + .../node_modules/markdown-it-sup/package.json | 49 + frontend/node_modules/markdown-it/LICENSE | 22 + frontend/node_modules/markdown-it/README.md | 324 + .../markdown-it/bin/markdown-it.mjs | 107 + .../markdown-it/dist/index.cjs.js | 5540 +++++ .../markdown-it/dist/markdown-it.js | 6963 ++++++ .../markdown-it/dist/markdown-it.min.js | 2 + frontend/node_modules/markdown-it/index.mjs | 1 + .../markdown-it/lib/common/html_blocks.mjs | 67 + .../markdown-it/lib/common/html_re.mjs | 25 + .../markdown-it/lib/common/utils.mjs | 304 + .../markdown-it/lib/helpers/index.mjs | 11 + .../lib/helpers/parse_link_destination.mjs | 77 + .../lib/helpers/parse_link_label.mjs | 49 + .../lib/helpers/parse_link_title.mjs | 66 + .../node_modules/markdown-it/lib/index.mjs | 565 + .../markdown-it/lib/parser_block.mjs | 134 + .../markdown-it/lib/parser_core.mjs | 62 + .../markdown-it/lib/parser_inline.mjs | 197 + .../markdown-it/lib/presets/commonmark.mjs | 88 + .../markdown-it/lib/presets/default.mjs | 47 + .../markdown-it/lib/presets/zero.mjs | 70 + .../node_modules/markdown-it/lib/renderer.mjs | 322 + .../node_modules/markdown-it/lib/ruler.mjs | 340 + .../lib/rules_block/blockquote.mjs | 209 + .../markdown-it/lib/rules_block/code.mjs | 30 + .../markdown-it/lib/rules_block/fence.mjs | 94 + .../markdown-it/lib/rules_block/heading.mjs | 51 + .../markdown-it/lib/rules_block/hr.mjs | 40 + .../lib/rules_block/html_block.mjs | 69 + .../markdown-it/lib/rules_block/lheading.mjs | 82 + .../markdown-it/lib/rules_block/list.mjs | 331 + .../markdown-it/lib/rules_block/paragraph.mjs | 46 + .../markdown-it/lib/rules_block/reference.mjs | 212 + .../lib/rules_block/state_block.mjs | 220 + .../markdown-it/lib/rules_block/table.mjs | 228 + .../markdown-it/lib/rules_core/block.mjs | 13 + .../markdown-it/lib/rules_core/inline.mjs | 11 + .../markdown-it/lib/rules_core/linkify.mjs | 134 + .../markdown-it/lib/rules_core/normalize.mjs | 17 + .../lib/rules_core/replacements.mjs | 101 + .../lib/rules_core/smartquotes.mjs | 193 + .../markdown-it/lib/rules_core/state_core.mjs | 17 + .../markdown-it/lib/rules_core/text_join.mjs | 43 + .../markdown-it/lib/rules_inline/autolink.mjs | 72 + .../lib/rules_inline/backticks.mjs | 60 + .../lib/rules_inline/balance_pairs.mjs | 124 + .../markdown-it/lib/rules_inline/emphasis.mjs | 123 + .../markdown-it/lib/rules_inline/entity.mjs | 51 + .../markdown-it/lib/rules_inline/escape.mjs | 69 + .../lib/rules_inline/fragments_join.mjs | 38 + .../lib/rules_inline/html_inline.mjs | 50 + .../markdown-it/lib/rules_inline/image.mjs | 138 + .../markdown-it/lib/rules_inline/link.mjs | 139 + .../markdown-it/lib/rules_inline/linkify.mjs | 56 + .../markdown-it/lib/rules_inline/newline.mjs | 42 + .../lib/rules_inline/state_inline.mjs | 123 + .../lib/rules_inline/strikethrough.mjs | 127 + .../markdown-it/lib/rules_inline/text.mjs | 86 + .../node_modules/markdown-it/lib/token.mjs | 191 + .../node_modules/argparse/CHANGELOG.md | 216 + .../markdown-it/node_modules/argparse/LICENSE | 254 + .../node_modules/argparse/README.md | 84 + .../node_modules/argparse/argparse.js | 3707 +++ .../node_modules/argparse/lib/sub.js | 67 + .../node_modules/argparse/lib/textwrap.js | 440 + .../node_modules/argparse/package.json | 31 + .../node_modules/markdown-it/package.json | 92 + frontend/node_modules/markmap-common/LICENSE | 21 + .../node_modules/markmap-common/README.md | 3 + .../markmap-common/dist/hook.d.ts | 8 + .../markmap-common/dist/html.d.ts | 9 + .../markmap-common/dist/index.d.ts | 6 + .../node_modules/markmap-common/dist/index.js | 523 + .../markmap-common/dist/index.mjs | 523 + .../markmap-common/dist/loader.d.ts | 7 + .../markmap-common/dist/types/common.d.ts | 96 + .../markmap-common/dist/types/index.d.ts | 1 + .../markmap-common/dist/util.d.ts | 11 + .../node_modules/markmap-common/package.json | 38 + .../node_modules/markmap-html-parser/LICENSE | 21 + .../markmap-html-parser/README.md | 9 + .../markmap-html-parser/dist/index.d.ts | 48 + .../markmap-html-parser/dist/index.js | 6000 +++++ .../markmap-html-parser/dist/index.mjs | 6000 +++++ .../markmap-html-parser/package.json | 55 + frontend/node_modules/markmap-lib/LICENSE | 21 + frontend/node_modules/markmap-lib/README.md | 19 + .../markmap-lib/dist/browser/index.iife.js | 18702 ++++++++++++++ .../markmap-lib/dist/browser/index.mjs | 500 + .../node_modules/markmap-lib/dist/index.d.ts | 6 + .../node_modules/markmap-lib/dist/index.js | 132 + .../node_modules/markmap-lib/dist/index.mjs | 132 + .../markmap-lib/dist/index.no-plugins.js | 140 + .../markmap-lib/dist/index.no-plugins.mjs | 140 + .../markmap-lib/dist/markdown-it.d.ts | 2 + .../node_modules/markmap-lib/dist/plugins.js | 314 + .../node_modules/markmap-lib/dist/plugins.mjs | 314 + .../markmap-lib/dist/plugins/base.d.ts | 6 + .../dist/plugins/checkbox/index.d.ts | 2 + .../dist/plugins/frontmatter/index.d.ts | 2 + .../markmap-lib/dist/plugins/hljs/config.d.ts | 8 + .../dist/plugins/hljs/index.browser.d.ts | 2 + .../markmap-lib/dist/plugins/hljs/index.d.ts | 2 + .../markmap-lib/dist/plugins/index.d.ts | 9 + .../dist/plugins/katex/config.d.ts | 12 + .../dist/plugins/katex/index.browser.d.ts | 2 + .../markmap-lib/dist/plugins/katex/index.d.ts | 2 + .../dist/plugins/katex/vendor.d.ts | 2 + .../dist/plugins/npm-url/index.d.ts | 2 + .../dist/plugins/prism/config.d.ts | 8 + .../dist/plugins/prism/index.browser.d.ts | 2 + .../markmap-lib/dist/plugins/prism/index.d.ts | 2 + .../dist/plugins/source-lines/index.d.ts | 2 + .../markmap-lib/dist/plugins/util.d.ts | 4 + .../markmap-lib/dist/transform.d.ts | 24 + .../node_modules/markmap-lib/dist/types.d.ts | 77 + .../node_modules/markmap-lib/dist/util.d.ts | 3 + .../node_modules/markmap-lib/package.json | 85 + frontend/node_modules/markmap-view/LICENSE | 21 + frontend/node_modules/markmap-view/README.md | 11 + .../markmap-view/dist/browser/index.js | 1457 ++ .../markmap-view/dist/constants.d.ts | 6 + .../node_modules/markmap-view/dist/index.d.ts | 5 + .../node_modules/markmap-view/dist/index.js | 811 + .../node_modules/markmap-view/dist/types.d.ts | 61 + .../node_modules/markmap-view/dist/util.d.ts | 7 + .../node_modules/markmap-view/dist/view.d.ts | 74 + .../node_modules/markmap-view/package.json | 55 + frontend/node_modules/mdurl/LICENSE | 45 + frontend/node_modules/mdurl/README.md | 102 + .../node_modules/mdurl/build/index.cjs.js | 534 + frontend/node_modules/mdurl/index.mjs | 11 + frontend/node_modules/mdurl/lib/decode.mjs | 112 + frontend/node_modules/mdurl/lib/encode.mjs | 89 + frontend/node_modules/mdurl/lib/format.mjs | 21 + frontend/node_modules/mdurl/lib/parse.mjs | 308 + frontend/node_modules/mdurl/package.json | 37 + .../mind-elixir/dist/MindElixir.iife.js | 12 - .../mind-elixir/dist/MindElixir.js | 2364 -- .../mind-elixir/dist/MindElixirLite.iife.js | 10 - .../mind-elixir/dist/MindElixirLite.js | 1574 -- .../mind-elixir/dist/example.iife.js | 2 - .../node_modules/mind-elixir/dist/example.js | 272 - .../mind-elixir/dist/types/const.d.ts | 9 - .../mind-elixir/dist/types/customLink.d.ts | 34 - .../mind-elixir/dist/types/docs.d.ts | 6 - .../dist/types/exampleData/1.cn.d.ts | 126 - .../mind-elixir/dist/types/exampleData/1.d.ts | 3 - .../mind-elixir/dist/types/exampleData/2.d.ts | 3 - .../mind-elixir/dist/types/exampleData/3.d.ts | 3 - .../mind-elixir/dist/types/i18n.d.ts | 15 - .../mind-elixir/dist/types/index.d.ts | 111 - .../mind-elixir/dist/types/interact.d.ts | 142 - .../mind-elixir/dist/types/linkDiv.d.ts | 15 - .../mind-elixir/dist/types/methods.d.ts | 91 - .../mind-elixir/dist/types/mouse.d.ts | 2 - .../mind-elixir/dist/types/nodeOperation.d.ts | 156 - .../dist/types/plugin/contextMenu.d.ts | 3 - .../dist/types/plugin/exportImage.d.ts | 3 - .../dist/types/plugin/keypress.d.ts | 2 - .../dist/types/plugin/mobileMenu.d.ts | 3 - .../dist/types/plugin/nodeDraggable.d.ts | 2 - .../dist/types/plugin/operationHistory.d.ts | 2 - .../dist/types/plugin/selection.d.ts | 2 - .../dist/types/plugin/toolBar.d.ts | 3 - .../mind-elixir/dist/types/summary.d.ts | 18 - .../mind-elixir/dist/types/types/dom.d.ts | 50 - .../mind-elixir/dist/types/types/global.d.ts | 7 - .../mind-elixir/dist/types/types/index.d.ts | 164 - .../dist/types/utils/LinkDragMoveHelper.d.ts | 28 - .../mind-elixir/dist/types/utils/dom.d.ts | 18 - .../dist/types/utils/domManipulation.d.ts | 8 - .../dist/types/utils/dragMoveHelper.d.ts | 7 - .../mind-elixir/dist/types/utils/index.d.ts | 30 - .../mind-elixir/dist/types/utils/layout.d.ts | 4 - .../dist/types/utils/objectManipulation.d.ts | 10 - .../mind-elixir/dist/types/utils/pubsub.d.ts | 73 - .../mind-elixir/dist/types/utils/svg.d.ts | 8 - .../mind-elixir/dist/types/utils/theme.d.ts | 4 - .../node_modules/mind-elixir/readme.cn.md | 207 - frontend/node_modules/npm2url/LICENSE | 21 + frontend/node_modules/npm2url/README.md | 50 + frontend/node_modules/npm2url/dist/index.cjs | 75 + frontend/node_modules/npm2url/dist/index.d.ts | 20 + frontend/node_modules/npm2url/dist/index.mjs | 72 + frontend/node_modules/npm2url/package.json | 41 + frontend/node_modules/nth-check/LICENSE | 11 + frontend/node_modules/nth-check/README.md | 136 + .../node_modules/nth-check/lib/compile.d.ts | 55 + .../nth-check/lib/compile.d.ts.map | 1 + .../node_modules/nth-check/lib/compile.js | 121 + .../node_modules/nth-check/lib/compile.js.map | 1 + .../nth-check/lib/esm/compile.d.ts | 55 + .../nth-check/lib/esm/compile.d.ts.map | 1 + .../node_modules/nth-check/lib/esm/compile.js | 113 + .../nth-check/lib/esm/compile.js.map | 1 + .../node_modules/nth-check/lib/esm/index.d.ts | 59 + .../nth-check/lib/esm/index.d.ts.map | 1 + .../node_modules/nth-check/lib/esm/index.js | 63 + .../nth-check/lib/esm/index.js.map | 1 + .../nth-check/lib/esm/package.json | 1 + .../node_modules/nth-check/lib/esm/parse.d.ts | 9 + .../nth-check/lib/esm/parse.d.ts.map | 1 + .../node_modules/nth-check/lib/esm/parse.js | 73 + .../nth-check/lib/esm/parse.js.map | 1 + .../node_modules/nth-check/lib/index.d.ts | 59 + .../node_modules/nth-check/lib/index.d.ts.map | 1 + frontend/node_modules/nth-check/lib/index.js | 70 + .../node_modules/nth-check/lib/index.js.map | 1 + .../node_modules/nth-check/lib/parse.d.ts | 9 + .../node_modules/nth-check/lib/parse.d.ts.map | 1 + frontend/node_modules/nth-check/lib/parse.js | 77 + .../node_modules/nth-check/lib/parse.js.map | 1 + frontend/node_modules/nth-check/package.json | 78 + .../parse5-htmlparser2-tree-adapter/LICENSE | 19 + .../parse5-htmlparser2-tree-adapter/README.md | 34 + .../dist/cjs/index.d.ts | 6 + .../dist/cjs/index.js | 214 + .../dist/cjs/package.json | 1 + .../dist/index.d.ts | 6 + .../dist/index.js | 213 + .../package.json | 40 + .../node_modules/parse5-parser-stream/LICENSE | 19 + .../parse5-parser-stream/README.md | 34 + .../parse5-parser-stream/dist/cjs/index.d.ts | 85 + .../parse5-parser-stream/dist/cjs/index.js | 90 + .../dist/cjs/package.json | 1 + .../parse5-parser-stream/dist/index.d.ts | 85 + .../parse5-parser-stream/dist/index.js | 86 + .../parse5-parser-stream/package.json | 39 + frontend/node_modules/parse5/LICENSE | 19 + frontend/node_modules/parse5/README.md | 38 + .../parse5/dist/cjs/common/doctype.d.ts | 4 + .../parse5/dist/cjs/common/doctype.js | 118 + .../parse5/dist/cjs/common/error-codes.d.ts | 67 + .../parse5/dist/cjs/common/error-codes.js | 66 + .../dist/cjs/common/foreign-content.d.ts | 9 + .../parse5/dist/cjs/common/foreign-content.js | 237 + .../parse5/dist/cjs/common/html.d.ts | 289 + .../parse5/dist/cjs/common/html.js | 528 + .../parse5/dist/cjs/common/token.d.ts | 84 + .../parse5/dist/cjs/common/token.js | 24 + .../parse5/dist/cjs/common/unicode.d.ts | 42 + .../parse5/dist/cjs/common/unicode.js | 70 + .../node_modules/parse5/dist/cjs/index.d.ts | 71 + .../node_modules/parse5/dist/cjs/index.js | 54 + .../node_modules/parse5/dist/cjs/package.json | 1 + .../cjs/parser/formatting-element-list.d.ts | 36 + .../cjs/parser/formatting-element-list.js | 114 + .../parse5/dist/cjs/parser/index.d.ts | 221 + .../parse5/dist/cjs/parser/index.js | 3240 +++ .../dist/cjs/parser/open-element-stack.d.ts | 53 + .../dist/cjs/parser/open-element-stack.js | 328 + .../parse5/dist/cjs/serializer/index.d.ts | 60 + .../parse5/dist/cjs/serializer/index.js | 172 + .../parse5/dist/cjs/tokenizer/index.d.ts | 247 + .../parse5/dist/cjs/tokenizer/index.js | 2714 ++ .../dist/cjs/tokenizer/preprocessor.d.ts | 36 + .../parse5/dist/cjs/tokenizer/preprocessor.js | 200 + .../dist/cjs/tree-adapters/default.d.ts | 84 + .../parse5/dist/cjs/tree-adapters/default.js | 176 + .../dist/cjs/tree-adapters/interface.d.ts | 255 + .../dist/cjs/tree-adapters/interface.js | 2 + .../parse5/dist/common/doctype.d.ts | 4 + .../parse5/dist/common/doctype.js | 114 + .../parse5/dist/common/error-codes.d.ts | 67 + .../parse5/dist/common/error-codes.js | 63 + .../parse5/dist/common/foreign-content.d.ts | 9 + .../parse5/dist/common/foreign-content.js | 228 + .../node_modules/parse5/dist/common/html.d.ts | 289 + .../node_modules/parse5/dist/common/html.js | 523 + .../parse5/dist/common/token.d.ts | 84 + .../node_modules/parse5/dist/common/token.js | 20 + .../parse5/dist/common/unicode.d.ts | 42 + .../parse5/dist/common/unicode.js | 62 + frontend/node_modules/parse5/dist/index.d.ts | 71 + frontend/node_modules/parse5/dist/index.js | 42 + .../dist/parser/formatting-element-list.d.ts | 36 + .../dist/parser/formatting-element-list.js | 110 + .../parse5/dist/parser/index.d.ts | 221 + .../node_modules/parse5/dist/parser/index.js | 3245 +++ .../dist/parser/open-element-stack.d.ts | 53 + .../parse5/dist/parser/open-element-stack.js | 324 + .../parse5/dist/serializer/index.d.ts | 60 + .../parse5/dist/serializer/index.js | 168 + .../parse5/dist/tokenizer/index.d.ts | 247 + .../parse5/dist/tokenizer/index.js | 2710 ++ .../parse5/dist/tokenizer/preprocessor.d.ts | 36 + .../parse5/dist/tokenizer/preprocessor.js | 196 + .../parse5/dist/tree-adapters/default.d.ts | 84 + .../parse5/dist/tree-adapters/default.js | 173 + .../parse5/dist/tree-adapters/interface.d.ts | 255 + .../dist/tree-adapters/interface.js} | 0 .../parse5/node_modules/entities/LICENSE | 11 + .../parse5/node_modules/entities/decode.d.ts | 1 + .../parse5/node_modules/entities/decode.js | 3 + .../dist/commonjs/decode-codepoint.d.ts | 19 + .../dist/commonjs/decode-codepoint.d.ts.map | 1 + .../dist/commonjs/decode-codepoint.js | 77 + .../dist/commonjs/decode-codepoint.js.map | 1 + .../entities/dist/commonjs/decode.d.ts | 209 + .../entities/dist/commonjs/decode.d.ts.map | 1 + .../entities/dist/commonjs/decode.js | 511 + .../entities/dist/commonjs/decode.js.map | 1 + .../entities/dist/commonjs/encode.d.ts | 22 + .../entities/dist/commonjs/encode.d.ts.map | 1 + .../entities/dist/commonjs/encode.js | 73 + .../entities/dist/commonjs/encode.js.map | 1 + .../entities/dist/commonjs/escape.d.ts | 43 + .../entities/dist/commonjs/escape.d.ts.map | 1 + .../entities/dist/commonjs/escape.js | 121 + .../entities/dist/commonjs/escape.js.map | 1 + .../commonjs/generated/decode-data-html.d.ts | 2 + .../generated/decode-data-html.d.ts.map | 1 + .../commonjs/generated/decode-data-html.js | 10 + .../generated/decode-data-html.js.map | 1 + .../commonjs/generated/decode-data-xml.d.ts | 2 + .../generated/decode-data-xml.d.ts.map | 1 + .../commonjs/generated/decode-data-xml.js | 10 + .../commonjs/generated/decode-data-xml.js.map | 1 + .../dist/commonjs/generated/encode-html.d.ts | 8 + .../commonjs/generated/encode-html.d.ts.map | 1 + .../dist/commonjs/generated/encode-html.js | 13 + .../commonjs/generated/encode-html.js.map | 1 + .../entities/dist/commonjs/index.d.ts | 96 + .../entities/dist/commonjs/index.d.ts.map | 1 + .../entities/dist/commonjs/index.js | 131 + .../entities/dist/commonjs/index.js.map | 1 + .../entities/dist/commonjs/package.json | 3 + .../entities/dist/esm/decode-codepoint.d.ts | 19 + .../dist/esm/decode-codepoint.d.ts.map | 1 + .../entities/dist/esm/decode-codepoint.js | 72 + .../entities/dist/esm/decode-codepoint.js.map | 1 + .../entities/dist/esm/decode.d.ts | 209 + .../entities/dist/esm/decode.d.ts.map | 1 + .../node_modules/entities/dist/esm/decode.js | 497 + .../entities/dist/esm/decode.js.map | 1 + .../entities/dist/esm/encode.d.ts | 22 + .../entities/dist/esm/encode.d.ts.map | 1 + .../node_modules/entities/dist/esm/encode.js | 69 + .../entities/dist/esm/encode.js.map | 1 + .../entities/dist/esm/escape.d.ts | 43 + .../entities/dist/esm/escape.d.ts.map | 1 + .../node_modules/entities/dist/esm/escape.js | 117 + .../entities/dist/esm/escape.js.map | 1 + .../dist/esm/generated/decode-data-html.d.ts | 2 + .../esm/generated/decode-data-html.d.ts.map | 1 + .../dist/esm/generated/decode-data-html.js | 7 + .../esm/generated/decode-data-html.js.map | 1 + .../dist/esm/generated/decode-data-xml.d.ts | 2 + .../esm/generated/decode-data-xml.d.ts.map | 1 + .../dist/esm/generated/decode-data-xml.js | 7 + .../dist/esm/generated/decode-data-xml.js.map | 1 + .../dist/esm/generated/encode-html.d.ts | 8 + .../dist/esm/generated/encode-html.d.ts.map | 1 + .../dist/esm/generated/encode-html.js | 10 + .../dist/esm/generated/encode-html.js.map | 1 + .../node_modules/entities/dist/esm/index.d.ts | 96 + .../entities/dist/esm/index.d.ts.map | 1 + .../node_modules/entities/dist/esm/index.js | 107 + .../entities/dist/esm/index.js.map | 1 + .../entities/dist/esm/package.json | 3 + .../parse5/node_modules/entities/escape.d.ts | 1 + .../parse5/node_modules/entities/escape.js | 3 + .../parse5/node_modules/entities/package.json | 118 + .../parse5/node_modules/entities/readme.md | 122 + .../entities/src/decode-codepoint.ts | 81 + .../node_modules/entities/src/decode.spec.ts | 320 + .../node_modules/entities/src/decode.ts | 620 + .../node_modules/entities/src/encode.spec.ts | 78 + .../node_modules/entities/src/encode.ts | 77 + .../node_modules/entities/src/escape.spec.ts | 14 + .../node_modules/entities/src/escape.ts | 148 + .../entities/src/generated/.eslintrc.json | 10 + .../src/generated/decode-data-html.ts | 8 + .../entities/src/generated/decode-data-xml.ts | 8 + .../entities/src/generated/encode-html.ts | 17 + .../node_modules/entities/src/index.spec.ts | 125 + .../parse5/node_modules/entities/src/index.ts | 188 + frontend/node_modules/parse5/package.json | 50 + frontend/node_modules/prismjs/CHANGELOG.md | 3068 +++ frontend/node_modules/prismjs/LICENSE | 21 + frontend/node_modules/prismjs/README.md | 51 + frontend/node_modules/prismjs/_headers | 2 + frontend/node_modules/prismjs/components.js | 2 + frontend/node_modules/prismjs/components.json | 1766 ++ .../node_modules/prismjs/components/index.js | 56 + .../prismjs/components/prism-abap.js | 48 + .../prismjs/components/prism-abap.min.js | 1 + .../prismjs/components/prism-abnf.js | 54 + .../prismjs/components/prism-abnf.min.js | 1 + .../prismjs/components/prism-actionscript.js | 19 + .../components/prism-actionscript.min.js | 1 + .../prismjs/components/prism-ada.js | 22 + .../prismjs/components/prism-ada.min.js | 1 + .../prismjs/components/prism-agda.js | 24 + .../prismjs/components/prism-agda.min.js | 1 + .../prismjs/components/prism-al.js | 25 + .../prismjs/components/prism-al.min.js | 1 + .../prismjs/components/prism-antlr4.js | 65 + .../prismjs/components/prism-antlr4.min.js | 1 + .../prismjs/components/prism-apacheconf.js | 47 + .../components/prism-apacheconf.min.js | 1 + .../prismjs/components/prism-apex.js | 65 + .../prismjs/components/prism-apex.min.js | 1 + .../prismjs/components/prism-apl.js | 32 + .../prismjs/components/prism-apl.min.js | 1 + .../prismjs/components/prism-applescript.js | 17 + .../components/prism-applescript.min.js | 1 + .../prismjs/components/prism-aql.js | 49 + .../prismjs/components/prism-aql.min.js | 1 + .../prismjs/components/prism-arduino.js | 7 + .../prismjs/components/prism-arduino.min.js | 1 + .../prismjs/components/prism-arff.js | 10 + .../prismjs/components/prism-arff.min.js | 1 + .../prismjs/components/prism-armasm.js | 49 + .../prismjs/components/prism-armasm.min.js | 1 + .../prismjs/components/prism-arturo.js | 105 + .../prismjs/components/prism-arturo.min.js | 1 + .../prismjs/components/prism-asciidoc.js | 234 + .../prismjs/components/prism-asciidoc.min.js | 1 + .../prismjs/components/prism-asm6502.js | 29 + .../prismjs/components/prism-asm6502.min.js | 1 + .../prismjs/components/prism-asmatmel.js | 43 + .../prismjs/components/prism-asmatmel.min.js | 1 + .../prismjs/components/prism-aspnet.js | 48 + .../prismjs/components/prism-aspnet.min.js | 1 + .../prismjs/components/prism-autohotkey.js | 44 + .../components/prism-autohotkey.min.js | 1 + .../prismjs/components/prism-autoit.js | 34 + .../prismjs/components/prism-autoit.min.js | 1 + .../prismjs/components/prism-avisynth.js | 188 + .../prismjs/components/prism-avisynth.min.js | 1 + .../prismjs/components/prism-avro-idl.js | 50 + .../prismjs/components/prism-avro-idl.min.js | 1 + .../prismjs/components/prism-awk.js | 32 + .../prismjs/components/prism-awk.min.js | 1 + .../prismjs/components/prism-bash.js | 235 + .../prismjs/components/prism-bash.min.js | 1 + .../prismjs/components/prism-basic.js | 17 + .../prismjs/components/prism-basic.min.js | 1 + .../prismjs/components/prism-batch.js | 99 + .../prismjs/components/prism-batch.min.js | 1 + .../prismjs/components/prism-bbcode.js | 29 + .../prismjs/components/prism-bbcode.min.js | 1 + .../prismjs/components/prism-bbj.js | 19 + .../prismjs/components/prism-bbj.min.js | 1 + .../prismjs/components/prism-bicep.js | 77 + .../prismjs/components/prism-bicep.min.js | 1 + .../prismjs/components/prism-birb.js | 23 + .../prismjs/components/prism-birb.min.js | 1 + .../prismjs/components/prism-bison.js | 39 + .../prismjs/components/prism-bison.min.js | 1 + .../prismjs/components/prism-bnf.js | 21 + .../prismjs/components/prism-bnf.min.js | 1 + .../prismjs/components/prism-bqn.js | 63 + .../prismjs/components/prism-bqn.min.js | 1 + .../prismjs/components/prism-brainfuck.js | 20 + .../prismjs/components/prism-brainfuck.min.js | 1 + .../prismjs/components/prism-brightscript.js | 44 + .../components/prism-brightscript.min.js | 1 + .../prismjs/components/prism-bro.js | 37 + .../prismjs/components/prism-bro.min.js | 1 + .../prismjs/components/prism-bsl.js | 75 + .../prismjs/components/prism-bsl.min.js | 1 + .../prismjs/components/prism-c.js | 80 + .../prismjs/components/prism-c.min.js | 1 + .../prismjs/components/prism-cfscript.js | 44 + .../prismjs/components/prism-cfscript.min.js | 1 + .../prismjs/components/prism-chaiscript.js | 60 + .../components/prism-chaiscript.min.js | 1 + .../prismjs/components/prism-cil.js | 27 + .../prismjs/components/prism-cil.min.js | 1 + .../prismjs/components/prism-cilkc.js | 8 + .../prismjs/components/prism-cilkc.min.js | 1 + .../prismjs/components/prism-cilkcpp.js | 9 + .../prismjs/components/prism-cilkcpp.min.js | 1 + .../prismjs/components/prism-clike.js | 31 + .../prismjs/components/prism-clike.min.js | 1 + .../prismjs/components/prism-clojure.js | 31 + .../prismjs/components/prism-clojure.min.js | 1 + .../prismjs/components/prism-cmake.js | 29 + .../prismjs/components/prism-cmake.min.js | 1 + .../prismjs/components/prism-cobol.js | 53 + .../prismjs/components/prism-cobol.min.js | 1 + .../prismjs/components/prism-coffeescript.js | 96 + .../components/prism-coffeescript.min.js | 1 + .../prismjs/components/prism-concurnas.js | 61 + .../prismjs/components/prism-concurnas.min.js | 1 + .../prismjs/components/prism-cooklang.js | 146 + .../prismjs/components/prism-cooklang.min.js | 1 + .../prismjs/components/prism-coq.js | 54 + .../prismjs/components/prism-coq.min.js | 1 + .../prismjs/components/prism-core.js | 1263 + .../prismjs/components/prism-core.min.js | 1 + .../prismjs/components/prism-cpp.js | 99 + .../prismjs/components/prism-cpp.min.js | 1 + .../prismjs/components/prism-crystal.js | 57 + .../prismjs/components/prism-crystal.min.js | 1 + .../prismjs/components/prism-csharp.js | 366 + .../prismjs/components/prism-csharp.min.js | 1 + .../prismjs/components/prism-cshtml.js | 199 + .../prismjs/components/prism-cshtml.min.js | 1 + .../prismjs/components/prism-csp.js | 76 + .../prismjs/components/prism-csp.min.js | 1 + .../prismjs/components/prism-css-extras.js | 120 + .../components/prism-css-extras.min.js | 1 + .../prismjs/components/prism-css.js | 64 + .../prismjs/components/prism-css.min.js | 1 + .../prismjs/components/prism-csv.js | 6 + .../prismjs/components/prism-csv.min.js | 1 + .../prismjs/components/prism-cue.js | 84 + .../prismjs/components/prism-cue.min.js | 1 + .../prismjs/components/prism-cypher.js | 36 + .../prismjs/components/prism-cypher.min.js | 1 + .../prismjs/components/prism-d.js | 84 + .../prismjs/components/prism-d.min.js | 1 + .../prismjs/components/prism-dart.js | 79 + .../prismjs/components/prism-dart.min.js | 1 + .../prismjs/components/prism-dataweave.js | 41 + .../prismjs/components/prism-dataweave.min.js | 1 + .../prismjs/components/prism-dax.js | 27 + .../prismjs/components/prism-dax.min.js | 1 + .../prismjs/components/prism-dhall.js | 69 + .../prismjs/components/prism-dhall.min.js | 1 + .../prismjs/components/prism-diff.js | 64 + .../prismjs/components/prism-diff.min.js | 1 + .../prismjs/components/prism-django.js | 60 + .../prismjs/components/prism-django.min.js | 1 + .../prismjs/components/prism-dns-zone-file.js | 33 + .../components/prism-dns-zone-file.min.js | 1 + .../prismjs/components/prism-docker.js | 98 + .../prismjs/components/prism-docker.min.js | 1 + .../prismjs/components/prism-dot.js | 76 + .../prismjs/components/prism-dot.min.js | 1 + .../prismjs/components/prism-ebnf.js | 22 + .../prismjs/components/prism-ebnf.min.js | 1 + .../prismjs/components/prism-editorconfig.js | 26 + .../components/prism-editorconfig.min.js | 1 + .../prismjs/components/prism-eiffel.js | 34 + .../prismjs/components/prism-eiffel.min.js | 1 + .../prismjs/components/prism-ejs.js | 26 + .../prismjs/components/prism-ejs.min.js | 1 + .../prismjs/components/prism-elixir.js | 98 + .../prismjs/components/prism-elixir.min.js | 1 + .../prismjs/components/prism-elm.js | 45 + .../prismjs/components/prism-elm.min.js | 1 + .../prismjs/components/prism-erb.js | 25 + .../prismjs/components/prism-erb.min.js | 1 + .../prismjs/components/prism-erlang.js | 44 + .../prismjs/components/prism-erlang.min.js | 1 + .../prismjs/components/prism-etlua.js | 23 + .../prismjs/components/prism-etlua.min.js | 1 + .../prismjs/components/prism-excel-formula.js | 66 + .../components/prism-excel-formula.min.js | 1 + .../prismjs/components/prism-factor.js | 403 + .../prismjs/components/prism-factor.min.js | 1 + .../prismjs/components/prism-false.js | 32 + .../prismjs/components/prism-false.min.js | 1 + .../prism-firestore-security-rules.js | 35 + .../prism-firestore-security-rules.min.js | 1 + .../prismjs/components/prism-flow.js | 35 + .../prismjs/components/prism-flow.min.js | 1 + .../prismjs/components/prism-fortran.js | 40 + .../prismjs/components/prism-fortran.min.js | 1 + .../prismjs/components/prism-fsharp.js | 75 + .../prismjs/components/prism-fsharp.min.js | 1 + .../prismjs/components/prism-ftl.js | 98 + .../prismjs/components/prism-ftl.min.js | 1 + .../prismjs/components/prism-gap.js | 54 + .../prismjs/components/prism-gap.min.js | 1 + .../prismjs/components/prism-gcode.js | 16 + .../prismjs/components/prism-gcode.min.js | 1 + .../prismjs/components/prism-gdscript.js | 27 + .../prismjs/components/prism-gdscript.min.js | 1 + .../prismjs/components/prism-gedcom.js | 28 + .../prismjs/components/prism-gedcom.min.js | 1 + .../prismjs/components/prism-gettext.js | 43 + .../prismjs/components/prism-gettext.min.js | 1 + .../prismjs/components/prism-gherkin.js | 85 + .../prismjs/components/prism-gherkin.min.js | 1 + .../prismjs/components/prism-git.js | 68 + .../prismjs/components/prism-git.min.js | 1 + .../prismjs/components/prism-glsl.js | 3 + .../prismjs/components/prism-glsl.min.js | 1 + .../prismjs/components/prism-gml.js | 7 + .../prismjs/components/prism-gml.min.js | 1 + .../prismjs/components/prism-gn.js | 51 + .../prismjs/components/prism-gn.min.js | 1 + .../prismjs/components/prism-go-module.js | 24 + .../prismjs/components/prism-go-module.min.js | 1 + .../prismjs/components/prism-go.js | 28 + .../prismjs/components/prism-go.min.js | 1 + .../prismjs/components/prism-gradle.js | 63 + .../prismjs/components/prism-gradle.min.js | 1 + .../prismjs/components/prism-graphql.js | 211 + .../prismjs/components/prism-graphql.min.js | 1 + .../prismjs/components/prism-groovy.js | 65 + .../prismjs/components/prism-groovy.min.js | 1 + .../prismjs/components/prism-haml.js | 149 + .../prismjs/components/prism-haml.min.js | 1 + .../prismjs/components/prism-handlebars.js | 40 + .../components/prism-handlebars.min.js | 1 + .../prismjs/components/prism-haskell.js | 66 + .../prismjs/components/prism-haskell.min.js | 1 + .../prismjs/components/prism-haxe.js | 78 + .../prismjs/components/prism-haxe.min.js | 1 + .../prismjs/components/prism-hcl.js | 63 + .../prismjs/components/prism-hcl.min.js | 1 + .../prismjs/components/prism-hlsl.js | 20 + .../prismjs/components/prism-hlsl.min.js | 1 + .../prismjs/components/prism-hoon.js | 14 + .../prismjs/components/prism-hoon.min.js | 1 + .../prismjs/components/prism-hpkp.js | 14 + .../prismjs/components/prism-hpkp.min.js | 1 + .../prismjs/components/prism-hsts.js | 14 + .../prismjs/components/prism-hsts.min.js | 1 + .../prismjs/components/prism-http.js | 151 + .../prismjs/components/prism-http.min.js | 1 + .../prismjs/components/prism-ichigojam.js | 15 + .../prismjs/components/prism-ichigojam.min.js | 1 + .../prismjs/components/prism-icon.js | 20 + .../prismjs/components/prism-icon.min.js | 1 + .../components/prism-icu-message-format.js | 148 + .../prism-icu-message-format.min.js | 1 + .../prismjs/components/prism-idris.js | 19 + .../prismjs/components/prism-idris.min.js | 1 + .../prismjs/components/prism-iecst.js | 32 + .../prismjs/components/prism-iecst.min.js | 1 + .../prismjs/components/prism-ignore.js | 23 + .../prismjs/components/prism-ignore.min.js | 1 + .../prismjs/components/prism-inform7.js | 61 + .../prismjs/components/prism-inform7.min.js | 1 + .../prismjs/components/prism-ini.js | 42 + .../prismjs/components/prism-ini.min.js | 1 + .../prismjs/components/prism-io.js | 22 + .../prismjs/components/prism-io.min.js | 1 + .../prismjs/components/prism-j.js | 28 + .../prismjs/components/prism-j.min.js | 1 + .../prismjs/components/prism-java.js | 124 + .../prismjs/components/prism-java.min.js | 1 + .../prismjs/components/prism-javadoc.js | 82 + .../prismjs/components/prism-javadoc.min.js | 1 + .../prismjs/components/prism-javadoclike.js | 87 + .../components/prism-javadoclike.min.js | 1 + .../prismjs/components/prism-javascript.js | 172 + .../components/prism-javascript.min.js | 1 + .../components/prism-javastacktrace.js | 142 + .../components/prism-javastacktrace.min.js | 1 + .../prismjs/components/prism-jexl.js | 14 + .../prismjs/components/prism-jexl.min.js | 1 + .../prismjs/components/prism-jolie.js | 41 + .../prismjs/components/prism-jolie.min.js | 1 + .../prismjs/components/prism-jq.js | 69 + .../prismjs/components/prism-jq.min.js | 1 + .../prismjs/components/prism-js-extras.js | 135 + .../prismjs/components/prism-js-extras.min.js | 1 + .../prismjs/components/prism-js-templates.js | 349 + .../components/prism-js-templates.min.js | 1 + .../prismjs/components/prism-jsdoc.js | 78 + .../prismjs/components/prism-jsdoc.min.js | 1 + .../prismjs/components/prism-json.js | 27 + .../prismjs/components/prism-json.min.js | 1 + .../prismjs/components/prism-json5.js | 23 + .../prismjs/components/prism-json5.min.js | 1 + .../prismjs/components/prism-jsonp.js | 7 + .../prismjs/components/prism-jsonp.min.js | 1 + .../prismjs/components/prism-jsstacktrace.js | 49 + .../components/prism-jsstacktrace.min.js | 1 + .../prismjs/components/prism-jsx.js | 145 + .../prismjs/components/prism-jsx.min.js | 1 + .../prismjs/components/prism-julia.js | 35 + .../prismjs/components/prism-julia.min.js | 1 + .../prismjs/components/prism-keepalived.js | 51 + .../components/prism-keepalived.min.js | 1 + .../prismjs/components/prism-keyman.js | 44 + .../prismjs/components/prism-keyman.min.js | 1 + .../prismjs/components/prism-kotlin.js | 88 + .../prismjs/components/prism-kotlin.min.js | 1 + .../prismjs/components/prism-kumir.js | 106 + .../prismjs/components/prism-kumir.min.js | 1 + .../prismjs/components/prism-kusto.js | 44 + .../prismjs/components/prism-kusto.min.js | 1 + .../prismjs/components/prism-latex.js | 64 + .../prismjs/components/prism-latex.min.js | 1 + .../prismjs/components/prism-latte.js | 63 + .../prismjs/components/prism-latte.min.js | 1 + .../prismjs/components/prism-less.js | 54 + .../prismjs/components/prism-less.min.js | 1 + .../prismjs/components/prism-lilypond.js | 69 + .../prismjs/components/prism-lilypond.min.js | 1 + .../prismjs/components/prism-linker-script.js | 30 + .../components/prism-linker-script.min.js | 1 + .../prismjs/components/prism-liquid.js | 66 + .../prismjs/components/prism-liquid.min.js | 1 + .../prismjs/components/prism-lisp.js | 197 + .../prismjs/components/prism-lisp.min.js | 1 + .../prismjs/components/prism-livescript.js | 119 + .../components/prism-livescript.min.js | 1 + .../prismjs/components/prism-llvm.js | 19 + .../prismjs/components/prism-llvm.min.js | 1 + .../prismjs/components/prism-log.js | 120 + .../prismjs/components/prism-log.min.js | 1 + .../prismjs/components/prism-lolcode.js | 55 + .../prismjs/components/prism-lolcode.min.js | 1 + .../prismjs/components/prism-lua.js | 20 + .../prismjs/components/prism-lua.min.js | 1 + .../prismjs/components/prism-magma.js | 35 + .../prismjs/components/prism-magma.min.js | 1 + .../prismjs/components/prism-makefile.js | 34 + .../prismjs/components/prism-makefile.min.js | 1 + .../prismjs/components/prism-markdown.js | 415 + .../prismjs/components/prism-markdown.min.js | 1 + .../components/prism-markup-templating.js | 124 + .../components/prism-markup-templating.min.js | 1 + .../prismjs/components/prism-markup.js | 186 + .../prismjs/components/prism-markup.min.js | 1 + .../prismjs/components/prism-mata.js | 50 + .../prismjs/components/prism-mata.min.js | 1 + .../prismjs/components/prism-matlab.js | 16 + .../prismjs/components/prism-matlab.min.js | 1 + .../prismjs/components/prism-maxscript.js | 91 + .../prismjs/components/prism-maxscript.min.js | 1 + .../prismjs/components/prism-mel.js | 46 + .../prismjs/components/prism-mel.min.js | 1 + .../prismjs/components/prism-mermaid.js | 113 + .../prismjs/components/prism-mermaid.min.js | 1 + .../prismjs/components/prism-metafont.js | 84 + .../prismjs/components/prism-metafont.min.js | 1 + .../prismjs/components/prism-mizar.js | 12 + .../prismjs/components/prism-mizar.min.js | 1 + .../prismjs/components/prism-mongodb.js | 97 + .../prismjs/components/prism-mongodb.min.js | 1 + .../prismjs/components/prism-monkey.js | 29 + .../prismjs/components/prism-monkey.min.js | 1 + .../prismjs/components/prism-moonscript.js | 57 + .../components/prism-moonscript.min.js | 1 + .../prismjs/components/prism-n1ql.js | 24 + .../prismjs/components/prism-n1ql.min.js | 1 + .../prismjs/components/prism-n4js.js | 14 + .../prismjs/components/prism-n4js.min.js | 1 + .../components/prism-nand2tetris-hdl.js | 9 + .../components/prism-nand2tetris-hdl.min.js | 1 + .../prismjs/components/prism-naniscript.js | 170 + .../components/prism-naniscript.min.js | 1 + .../prismjs/components/prism-nasm.js | 24 + .../prismjs/components/prism-nasm.min.js | 1 + .../prismjs/components/prism-neon.js | 40 + .../prismjs/components/prism-neon.min.js | 1 + .../prismjs/components/prism-nevod.js | 125 + .../prismjs/components/prism-nevod.min.js | 1 + .../prismjs/components/prism-nginx.js | 54 + .../prismjs/components/prism-nginx.min.js | 1 + .../prismjs/components/prism-nim.js | 44 + .../prismjs/components/prism-nim.min.js | 1 + .../prismjs/components/prism-nix.js | 37 + .../prismjs/components/prism-nix.min.js | 1 + .../prismjs/components/prism-nsis.js | 30 + .../prismjs/components/prism-nsis.min.js | 1 + .../prismjs/components/prism-objectivec.js | 12 + .../components/prism-objectivec.min.js | 1 + .../prismjs/components/prism-ocaml.js | 58 + .../prismjs/components/prism-ocaml.min.js | 1 + .../prismjs/components/prism-odin.js | 99 + .../prismjs/components/prism-odin.min.js | 1 + .../prismjs/components/prism-opencl.js | 61 + .../prismjs/components/prism-opencl.min.js | 1 + .../prismjs/components/prism-openqasm.js | 23 + .../prismjs/components/prism-openqasm.min.js | 1 + .../prismjs/components/prism-oz.js | 28 + .../prismjs/components/prism-oz.min.js | 1 + .../prismjs/components/prism-parigp.js | 30 + .../prismjs/components/prism-parigp.min.js | 1 + .../prismjs/components/prism-parser.js | 73 + .../prismjs/components/prism-parser.min.js | 1 + .../prismjs/components/prism-pascal.js | 71 + .../prismjs/components/prism-pascal.min.js | 1 + .../prismjs/components/prism-pascaligo.js | 62 + .../prismjs/components/prism-pascaligo.min.js | 1 + .../prismjs/components/prism-pcaxis.js | 53 + .../prismjs/components/prism-pcaxis.min.js | 1 + .../prismjs/components/prism-peoplecode.js | 42 + .../components/prism-peoplecode.min.js | 1 + .../prismjs/components/prism-perl.js | 156 + .../prismjs/components/prism-perl.min.js | 1 + .../prismjs/components/prism-php-extras.js | 14 + .../components/prism-php-extras.min.js | 1 + .../prismjs/components/prism-php.js | 342 + .../prismjs/components/prism-php.min.js | 1 + .../prismjs/components/prism-phpdoc.js | 27 + .../prismjs/components/prism-phpdoc.min.js | 1 + .../prismjs/components/prism-plant-uml.js | 103 + .../prismjs/components/prism-plant-uml.min.js | 1 + .../prismjs/components/prism-plsql.js | 17 + .../prismjs/components/prism-plsql.min.js | 1 + .../prismjs/components/prism-powerquery.js | 55 + .../components/prism-powerquery.min.js | 1 + .../prismjs/components/prism-powershell.js | 58 + .../components/prism-powershell.min.js | 1 + .../prismjs/components/prism-processing.js | 15 + .../components/prism-processing.min.js | 1 + .../prismjs/components/prism-prolog.js | 19 + .../prismjs/components/prism-prolog.min.js | 1 + .../prismjs/components/prism-promql.js | 99 + .../prismjs/components/prism-promql.min.js | 1 + .../prismjs/components/prism-properties.js | 13 + .../components/prism-properties.min.js | 1 + .../prismjs/components/prism-protobuf.js | 43 + .../prismjs/components/prism-protobuf.min.js | 1 + .../prismjs/components/prism-psl.js | 35 + .../prismjs/components/prism-psl.min.js | 1 + .../prismjs/components/prism-pug.js | 188 + .../prismjs/components/prism-pug.min.js | 1 + .../prismjs/components/prism-puppet.js | 136 + .../prismjs/components/prism-puppet.min.js | 1 + .../prismjs/components/prism-pure.js | 82 + .../prismjs/components/prism-pure.min.js | 1 + .../prismjs/components/prism-purebasic.js | 70 + .../prismjs/components/prism-purebasic.min.js | 1 + .../prismjs/components/prism-purescript.js | 31 + .../components/prism-purescript.min.js | 1 + .../prismjs/components/prism-python.js | 65 + .../prismjs/components/prism-python.min.js | 1 + .../prismjs/components/prism-q.js | 51 + .../prismjs/components/prism-q.min.js | 1 + .../prismjs/components/prism-qml.js | 61 + .../prismjs/components/prism-qml.min.js | 1 + .../prismjs/components/prism-qore.js | 20 + .../prismjs/components/prism-qore.min.js | 1 + .../prismjs/components/prism-qsharp.js | 132 + .../prismjs/components/prism-qsharp.min.js | 1 + .../prismjs/components/prism-r.js | 22 + .../prismjs/components/prism-r.min.js | 1 + .../prismjs/components/prism-racket.js | 18 + .../prismjs/components/prism-racket.min.js | 1 + .../prismjs/components/prism-reason.js | 25 + .../prismjs/components/prism-reason.min.js | 1 + .../prismjs/components/prism-regex.js | 104 + .../prismjs/components/prism-regex.min.js | 1 + .../prismjs/components/prism-rego.js | 30 + .../prismjs/components/prism-rego.min.js | 1 + .../prismjs/components/prism-renpy.js | 29 + .../prismjs/components/prism-renpy.min.js | 1 + .../prismjs/components/prism-rescript.js | 60 + .../prismjs/components/prism-rescript.min.js | 1 + .../prismjs/components/prism-rest.js | 205 + .../prismjs/components/prism-rest.min.js | 1 + .../prismjs/components/prism-rip.js | 38 + .../prismjs/components/prism-rip.min.js | 1 + .../prismjs/components/prism-roboconf.js | 27 + .../prismjs/components/prism-roboconf.min.js | 1 + .../components/prism-robotframework.js | 104 + .../components/prism-robotframework.min.js | 1 + .../prismjs/components/prism-ruby.js | 189 + .../prismjs/components/prism-ruby.min.js | 1 + .../prismjs/components/prism-rust.js | 128 + .../prismjs/components/prism-rust.min.js | 1 + .../prismjs/components/prism-sas.js | 326 + .../prismjs/components/prism-sas.min.js | 1 + .../prismjs/components/prism-sass.js | 77 + .../prismjs/components/prism-sass.min.js | 1 + .../prismjs/components/prism-scala.js | 50 + .../prismjs/components/prism-scala.min.js | 1 + .../prismjs/components/prism-scheme.js | 120 + .../prismjs/components/prism-scheme.min.js | 1 + .../prismjs/components/prism-scss.js | 81 + .../prismjs/components/prism-scss.min.js | 1 + .../prismjs/components/prism-shell-session.js | 70 + .../components/prism-shell-session.min.js | 1 + .../prismjs/components/prism-smali.js | 87 + .../prismjs/components/prism-smali.min.js | 1 + .../prismjs/components/prism-smalltalk.js | 38 + .../prismjs/components/prism-smalltalk.min.js | 1 + .../prismjs/components/prism-smarty.js | 131 + .../prismjs/components/prism-smarty.min.js | 1 + .../prismjs/components/prism-sml.js | 68 + .../prismjs/components/prism-sml.min.js | 1 + .../prismjs/components/prism-solidity.js | 22 + .../prismjs/components/prism-solidity.min.js | 1 + .../prismjs/components/prism-solution-file.js | 51 + .../components/prism-solution-file.min.js | 1 + .../prismjs/components/prism-soy.js | 96 + .../prismjs/components/prism-soy.min.js | 1 + .../prismjs/components/prism-sparql.js | 18 + .../prismjs/components/prism-sparql.min.js | 1 + .../prismjs/components/prism-splunk-spl.js | 24 + .../components/prism-splunk-spl.min.js | 1 + .../prismjs/components/prism-sqf.js | 34 + .../prismjs/components/prism-sqf.min.js | 1 + .../prismjs/components/prism-sql.js | 32 + .../prismjs/components/prism-sql.min.js | 1 + .../prismjs/components/prism-squirrel.js | 47 + .../prismjs/components/prism-squirrel.min.js | 1 + .../prismjs/components/prism-stan.js | 65 + .../prismjs/components/prism-stan.min.js | 1 + .../prismjs/components/prism-stata.js | 76 + .../prismjs/components/prism-stata.min.js | 1 + .../prismjs/components/prism-stylus.js | 143 + .../prismjs/components/prism-stylus.min.js | 1 + .../prismjs/components/prism-supercollider.js | 36 + .../components/prism-supercollider.min.js | 1 + .../prismjs/components/prism-swift.js | 148 + .../prismjs/components/prism-swift.min.js | 1 + .../prismjs/components/prism-systemd.js | 74 + .../prismjs/components/prism-systemd.min.js | 1 + .../prismjs/components/prism-t4-cs.js | 1 + .../prismjs/components/prism-t4-cs.min.js | 1 + .../prismjs/components/prism-t4-templating.js | 49 + .../components/prism-t4-templating.min.js | 1 + .../prismjs/components/prism-t4-vb.js | 1 + .../prismjs/components/prism-t4-vb.min.js | 1 + .../prismjs/components/prism-tap.js | 22 + .../prismjs/components/prism-tap.min.js | 1 + .../prismjs/components/prism-tcl.js | 46 + .../prismjs/components/prism-tcl.min.js | 1 + .../prismjs/components/prism-textile.js | 286 + .../prismjs/components/prism-textile.min.js | 1 + .../prismjs/components/prism-toml.js | 49 + .../prismjs/components/prism-toml.min.js | 1 + .../prismjs/components/prism-tremor.js | 72 + .../prismjs/components/prism-tremor.min.js | 1 + .../prismjs/components/prism-tsx.js | 15 + .../prismjs/components/prism-tsx.min.js | 1 + .../prismjs/components/prism-tt2.js | 53 + .../prismjs/components/prism-tt2.min.js | 1 + .../prismjs/components/prism-turtle.js | 54 + .../prismjs/components/prism-turtle.min.js | 1 + .../prismjs/components/prism-twig.js | 44 + .../prismjs/components/prism-twig.min.js | 1 + .../prismjs/components/prism-typescript.js | 60 + .../components/prism-typescript.min.js | 1 + .../prismjs/components/prism-typoscript.js | 80 + .../components/prism-typoscript.min.js | 1 + .../prismjs/components/prism-unrealscript.js | 42 + .../components/prism-unrealscript.min.js | 1 + .../prismjs/components/prism-uorazor.js | 48 + .../prismjs/components/prism-uorazor.min.js | 1 + .../prismjs/components/prism-uri.js | 96 + .../prismjs/components/prism-uri.min.js | 1 + .../prismjs/components/prism-v.js | 81 + .../prismjs/components/prism-v.min.js | 1 + .../prismjs/components/prism-vala.js | 84 + .../prismjs/components/prism-vala.min.js | 1 + .../prismjs/components/prism-vbnet.js | 22 + .../prismjs/components/prism-vbnet.min.js | 1 + .../prismjs/components/prism-velocity.js | 72 + .../prismjs/components/prism-velocity.min.js | 1 + .../prismjs/components/prism-verilog.js | 26 + .../prismjs/components/prism-verilog.min.js | 1 + .../prismjs/components/prism-vhdl.js | 26 + .../prismjs/components/prism-vhdl.min.js | 1 + .../prismjs/components/prism-vim.js | 10 + .../prismjs/components/prism-vim.min.js | 1 + .../prismjs/components/prism-visual-basic.js | 29 + .../components/prism-visual-basic.min.js | 1 + .../prismjs/components/prism-warpscript.js | 21 + .../components/prism-warpscript.min.js | 1 + .../prismjs/components/prism-wasm.js | 31 + .../prismjs/components/prism-wasm.min.js | 1 + .../prismjs/components/prism-web-idl.js | 101 + .../prismjs/components/prism-web-idl.min.js | 1 + .../prismjs/components/prism-wgsl.js | 69 + .../prismjs/components/prism-wgsl.min.js | 1 + .../prismjs/components/prism-wiki.js | 82 + .../prismjs/components/prism-wiki.min.js | 1 + .../prismjs/components/prism-wolfram.js | 29 + .../prismjs/components/prism-wolfram.min.js | 1 + .../prismjs/components/prism-wren.js | 100 + .../prismjs/components/prism-wren.min.js | 1 + .../prismjs/components/prism-xeora.js | 114 + .../prismjs/components/prism-xeora.min.js | 1 + .../prismjs/components/prism-xml-doc.js | 40 + .../prismjs/components/prism-xml-doc.min.js | 1 + .../prismjs/components/prism-xojo.js | 21 + .../prismjs/components/prism-xojo.min.js | 1 + .../prismjs/components/prism-xquery.js | 162 + .../prismjs/components/prism-xquery.min.js | 1 + .../prismjs/components/prism-yaml.js | 83 + .../prismjs/components/prism-yaml.min.js | 1 + .../prismjs/components/prism-yang.js | 20 + .../prismjs/components/prism-yang.min.js | 1 + .../prismjs/components/prism-zig.js | 101 + .../prismjs/components/prism-zig.min.js | 1 + frontend/node_modules/prismjs/dependencies.js | 452 + frontend/node_modules/prismjs/package.json | 89 + .../plugins/autolinker/prism-autolinker.css | 3 + .../plugins/autolinker/prism-autolinker.js | 76 + .../autolinker/prism-autolinker.min.css | 1 + .../autolinker/prism-autolinker.min.js | 1 + .../plugins/autoloader/prism-autoloader.js | 541 + .../autoloader/prism-autoloader.min.js | 1 + .../command-line/prism-command-line.css | 43 + .../command-line/prism-command-line.js | 239 + .../command-line/prism-command-line.min.css | 1 + .../command-line/prism-command-line.min.js | 1 + .../prism-copy-to-clipboard.js | 160 + .../prism-copy-to-clipboard.min.js | 1 + .../custom-class/prism-custom-class.js | 110 + .../custom-class/prism-custom-class.min.js | 1 + .../prism-data-uri-highlight.js | 94 + .../prism-data-uri-highlight.min.js | 1 + .../diff-highlight/prism-diff-highlight.css | 13 + .../diff-highlight/prism-diff-highlight.js | 90 + .../prism-diff-highlight.min.css | 1 + .../prism-diff-highlight.min.js | 1 + .../download-button/prism-download-button.js | 20 + .../prism-download-button.min.js | 1 + .../file-highlight/prism-file-highlight.js | 195 + .../prism-file-highlight.min.js | 1 + .../prism-filter-highlight-all.js | 127 + .../prism-filter-highlight-all.min.js | 1 + .../prism-highlight-keywords.js | 14 + .../prism-highlight-keywords.min.js | 1 + .../inline-color/prism-inline-color.css | 33 + .../inline-color/prism-inline-color.js | 105 + .../inline-color/prism-inline-color.min.css | 1 + .../inline-color/prism-inline-color.min.js | 1 + .../jsonp-highlight/prism-jsonp-highlight.js | 303 + .../prism-jsonp-highlight.min.js | 1 + .../plugins/keep-markup/prism-keep-markup.js | 126 + .../keep-markup/prism-keep-markup.min.js | 1 + .../line-highlight/prism-line-highlight.css | 70 + .../line-highlight/prism-line-highlight.js | 346 + .../prism-line-highlight.min.css | 1 + .../prism-line-highlight.min.js | 1 + .../line-numbers/prism-line-numbers.css | 40 + .../line-numbers/prism-line-numbers.js | 252 + .../line-numbers/prism-line-numbers.min.css | 1 + .../line-numbers/prism-line-numbers.min.js | 1 + .../match-braces/prism-match-braces.css | 29 + .../match-braces/prism-match-braces.js | 190 + .../match-braces/prism-match-braces.min.css | 1 + .../match-braces/prism-match-braces.min.js | 1 + .../prism-normalize-whitespace.js | 229 + .../prism-normalize-whitespace.min.js | 1 + .../plugins/previewers/prism-previewers.css | 243 + .../plugins/previewers/prism-previewers.js | 712 + .../previewers/prism-previewers.min.css | 1 + .../previewers/prism-previewers.min.js | 1 + .../prism-remove-initial-line-feed.js | 21 + .../prism-remove-initial-line-feed.min.js | 1 + .../show-invisibles/prism-show-invisibles.css | 34 + .../show-invisibles/prism-show-invisibles.js | 83 + .../prism-show-invisibles.min.css | 1 + .../prism-show-invisibles.min.js | 1 + .../show-language/prism-show-language.js | 325 + .../show-language/prism-show-language.min.js | 1 + .../prismjs/plugins/toolbar/prism-toolbar.css | 65 + .../prismjs/plugins/toolbar/prism-toolbar.js | 179 + .../plugins/toolbar/prism-toolbar.min.css | 1 + .../plugins/toolbar/prism-toolbar.min.js | 1 + .../plugins/treeview/prism-treeview.css | 168 + .../plugins/treeview/prism-treeview.js | 70 + .../plugins/treeview/prism-treeview.min.css | 1 + .../plugins/treeview/prism-treeview.min.js | 1 + .../prism-unescaped-markup.css | 10 + .../prism-unescaped-markup.js | 62 + .../prism-unescaped-markup.min.css | 1 + .../prism-unescaped-markup.min.js | 1 + .../prismjs/plugins/wpd/prism-wpd.css | 11 + .../prismjs/plugins/wpd/prism-wpd.js | 154 + .../prismjs/plugins/wpd/prism-wpd.min.css | 1 + .../prismjs/plugins/wpd/prism-wpd.min.js | 1 + frontend/node_modules/prismjs/prism.js | 1946 ++ .../node_modules/prismjs/themes/prism-coy.css | 219 + .../prismjs/themes/prism-coy.min.css | 1 + .../prismjs/themes/prism-dark.css | 129 + .../prismjs/themes/prism-dark.min.css | 1 + .../prismjs/themes/prism-funky.css | 130 + .../prismjs/themes/prism-funky.min.css | 1 + .../prismjs/themes/prism-okaidia.css | 123 + .../prismjs/themes/prism-okaidia.min.css | 1 + .../prismjs/themes/prism-solarizedlight.css | 150 + .../themes/prism-solarizedlight.min.css | 1 + .../prismjs/themes/prism-tomorrow.css | 122 + .../prismjs/themes/prism-tomorrow.min.css | 1 + .../prismjs/themes/prism-twilight.css | 169 + .../prismjs/themes/prism-twilight.min.css | 1 + .../node_modules/prismjs/themes/prism.css | 140 + .../node_modules/prismjs/themes/prism.min.css | 1 + .../node_modules/punycode.js/LICENSE-MIT.txt | 20 + frontend/node_modules/punycode.js/README.md | 148 + .../node_modules/punycode.js/package.json | 58 + .../node_modules/punycode.js/punycode.es6.js | 444 + frontend/node_modules/punycode.js/punycode.js | 443 + .../node_modules/robust-predicates/LICENSE | 24 + .../node_modules/robust-predicates/README.md | 82 + .../robust-predicates/esm/incircle.js | 765 + .../robust-predicates/esm/insphere.js | 766 + .../robust-predicates/esm/orient2d.js | 184 + .../robust-predicates/esm/orient3d.js | 462 + .../robust-predicates/esm/util.js | 138 + .../node_modules/robust-predicates/index.d.ts | 49 + .../node_modules/robust-predicates/index.js | 5 + .../robust-predicates/package.json | 75 + .../robust-predicates/umd/incircle.js | 908 + .../robust-predicates/umd/incircle.min.js | 1 + .../robust-predicates/umd/insphere.js | 914 + .../robust-predicates/umd/insphere.min.js | 1 + .../robust-predicates/umd/orient2d.js | 280 + .../robust-predicates/umd/orient2d.min.js | 1 + .../robust-predicates/umd/orient3d.js | 601 + .../robust-predicates/umd/orient3d.min.js | 1 + .../robust-predicates/umd/predicates.js | 2328 ++ .../robust-predicates/umd/predicates.min.js | 1 + frontend/node_modules/rw/.eslintrc | 5 + frontend/node_modules/rw/.npmignore | 3 + frontend/node_modules/rw/LICENSE | 26 + frontend/node_modules/rw/README.md | 120 + frontend/node_modules/rw/index.js | 5 + frontend/node_modules/rw/lib/rw/dash.js | 14 + frontend/node_modules/rw/lib/rw/decode.js | 23 + frontend/node_modules/rw/lib/rw/encode.js | 7 + .../node_modules/rw/lib/rw/read-file-sync.js | 29 + frontend/node_modules/rw/lib/rw/read-file.js | 23 + .../node_modules/rw/lib/rw/write-file-sync.js | 32 + frontend/node_modules/rw/lib/rw/write-file.js | 22 + frontend/node_modules/rw/package.json | 32 + frontend/node_modules/rw/test/cat-async | 10 + frontend/node_modules/rw/test/cat-sync | 5 + .../node_modules/rw/test/encode-object-async | 7 + .../node_modules/rw/test/encode-object-sync | 5 + .../node_modules/rw/test/encode-string-async | 7 + .../node_modules/rw/test/encode-string-sync | 5 + frontend/node_modules/rw/test/encoding-async | 42 + frontend/node_modules/rw/test/encoding-sync | 20 + frontend/node_modules/rw/test/run-tests | 53 + frontend/node_modules/rw/test/utf8.txt | 1 + frontend/node_modules/rw/test/wc-async | 8 + frontend/node_modules/rw/test/wc-sync | 5 + frontend/node_modules/rw/test/write-async | 7 + frontend/node_modules/rw/test/write-sync | 5 + frontend/node_modules/safer-buffer/LICENSE | 21 + .../safer-buffer/Porting-Buffer.md | 268 + frontend/node_modules/safer-buffer/Readme.md | 156 + .../node_modules/safer-buffer/dangerous.js | 58 + .../node_modules/safer-buffer/package.json | 34 + frontend/node_modules/safer-buffer/safer.js | 77 + frontend/node_modules/safer-buffer/tests.js | 406 + frontend/node_modules/uc.micro/LICENSE.txt | 20 + frontend/node_modules/uc.micro/README.md | 14 + .../node_modules/uc.micro/build/index.cjs.js | 20 + .../uc.micro/categories/Cc/regex.mjs | 1 + .../uc.micro/categories/Cf/regex.mjs | 1 + .../uc.micro/categories/P/regex.mjs | 1 + .../uc.micro/categories/S/regex.mjs | 1 + .../uc.micro/categories/Z/regex.mjs | 1 + frontend/node_modules/uc.micro/index.mjs | 8 + frontend/node_modules/uc.micro/package.json | 37 + .../uc.micro/properties/Any/regex.mjs | 1 + frontend/node_modules/undici/LICENSE | 21 + frontend/node_modules/undici/README.md | 467 + .../undici/docs/docs/api/Agent.md | 80 + .../undici/docs/docs/api/BalancedPool.md | 99 + .../undici/docs/docs/api/CacheStorage.md | 30 + .../undici/docs/docs/api/Client.md | 274 + .../undici/docs/docs/api/Connector.md | 115 + .../undici/docs/docs/api/ContentType.md | 57 + .../undici/docs/docs/api/Cookies.md | 101 + .../undici/docs/docs/api/Debug.md | 62 + .../docs/docs/api/DiagnosticsChannel.md | 204 + .../docs/docs/api/DispatchInterceptor.md | 60 + .../undici/docs/docs/api/Dispatcher.md | 1347 + .../undici/docs/docs/api/EnvHttpProxyAgent.md | 162 + .../undici/docs/docs/api/Errors.md | 48 + .../undici/docs/docs/api/EventSource.md | 45 + .../undici/docs/docs/api/Fetch.md | 52 + .../undici/docs/docs/api/MockAgent.md | 540 + .../undici/docs/docs/api/MockClient.md | 77 + .../undici/docs/docs/api/MockErrors.md | 12 + .../undici/docs/docs/api/MockPool.md | 547 + .../node_modules/undici/docs/docs/api/Pool.md | 84 + .../undici/docs/docs/api/PoolStats.md | 35 + .../undici/docs/docs/api/ProxyAgent.md | 130 + .../undici/docs/docs/api/RedirectHandler.md | 96 + .../undici/docs/docs/api/RetryAgent.md | 45 + .../undici/docs/docs/api/RetryHandler.md | 117 + .../node_modules/undici/docs/docs/api/Util.md | 25 + .../undici/docs/docs/api/WebSocket.md | 43 + .../undici/docs/docs/api/api-lifecycle.md | 91 + .../docs/best-practices/client-certificate.md | 64 + .../docs/best-practices/mocking-request.md | 136 + .../undici/docs/docs/best-practices/proxy.md | 127 + .../docs/docs/best-practices/writing-tests.md | 20 + frontend/node_modules/undici/index-fetch.js | 32 + frontend/node_modules/undici/index.d.ts | 3 + frontend/node_modules/undici/index.js | 169 + .../undici/lib/api/abort-signal.js | 57 + .../undici/lib/api/api-connect.js | 108 + .../undici/lib/api/api-pipeline.js | 251 + .../undici/lib/api/api-request.js | 214 + .../node_modules/undici/lib/api/api-stream.js | 220 + .../undici/lib/api/api-upgrade.js | 108 + frontend/node_modules/undici/lib/api/index.js | 7 + .../node_modules/undici/lib/api/readable.js | 385 + frontend/node_modules/undici/lib/api/util.js | 93 + .../node_modules/undici/lib/core/connect.js | 240 + .../node_modules/undici/lib/core/constants.js | 118 + .../undici/lib/core/diagnostics.js | 202 + .../node_modules/undici/lib/core/errors.js | 244 + .../node_modules/undici/lib/core/request.js | 395 + .../node_modules/undici/lib/core/symbols.js | 67 + frontend/node_modules/undici/lib/core/tree.js | 152 + frontend/node_modules/undici/lib/core/util.js | 719 + .../undici/lib/dispatcher/agent.js | 129 + .../undici/lib/dispatcher/balanced-pool.js | 209 + .../undici/lib/dispatcher/client-h1.js | 1370 + .../undici/lib/dispatcher/client-h2.js | 744 + .../undici/lib/dispatcher/client.js | 622 + .../undici/lib/dispatcher/dispatcher-base.js | 190 + .../undici/lib/dispatcher/dispatcher.js | 65 + .../lib/dispatcher/env-http-proxy-agent.js | 160 + .../undici/lib/dispatcher/fixed-queue.js | 117 + .../undici/lib/dispatcher/pool-base.js | 194 + .../undici/lib/dispatcher/pool-stats.js | 34 + .../undici/lib/dispatcher/pool.js | 107 + .../undici/lib/dispatcher/proxy-agent.js | 192 + .../undici/lib/dispatcher/retry-agent.js | 35 + frontend/node_modules/undici/lib/global.js | 32 + .../undici/lib/handler/decorator-handler.js | 44 + .../undici/lib/handler/redirect-handler.js | 232 + .../undici/lib/handler/retry-handler.js | 374 + .../undici/lib/interceptor/dns.js | 375 + .../undici/lib/interceptor/dump.js | 123 + .../lib/interceptor/redirect-interceptor.js | 21 + .../undici/lib/interceptor/redirect.js | 24 + .../undici/lib/interceptor/response-error.js | 86 + .../undici/lib/interceptor/retry.js | 19 + .../node_modules/undici/lib/llhttp/.gitkeep | 0 .../undici/lib/llhttp/constants.js | 278 + .../undici/lib/llhttp/llhttp-wasm.js | 5 + .../undici/lib/llhttp/llhttp_simd-wasm.js | 5 + .../node_modules/undici/lib/llhttp/utils.js | 15 + .../undici/lib/mock/mock-agent.js | 160 + .../undici/lib/mock/mock-client.js | 59 + .../undici/lib/mock/mock-errors.js | 17 + .../undici/lib/mock/mock-interceptor.js | 207 + .../node_modules/undici/lib/mock/mock-pool.js | 59 + .../undici/lib/mock/mock-symbols.js | 23 + .../undici/lib/mock/mock-utils.js | 367 + .../mock/pending-interceptors-formatter.js | 43 + .../undici/lib/mock/pluralizer.js | 29 + .../node_modules/undici/lib/util/timers.js | 423 + .../undici/lib/web/cache/cache.js | 859 + .../undici/lib/web/cache/cachestorage.js | 152 + .../undici/lib/web/cache/symbols.js | 5 + .../node_modules/undici/lib/web/cache/util.js | 45 + .../undici/lib/web/cookies/constants.js | 12 + .../undici/lib/web/cookies/index.js | 184 + .../undici/lib/web/cookies/parse.js | 317 + .../undici/lib/web/cookies/util.js | 282 + .../lib/web/eventsource/eventsource-stream.js | 398 + .../undici/lib/web/eventsource/eventsource.js | 480 + .../undici/lib/web/eventsource/util.js | 37 + .../node_modules/undici/lib/web/fetch/LICENSE | 21 + .../node_modules/undici/lib/web/fetch/body.js | 533 + .../undici/lib/web/fetch/constants.js | 124 + .../undici/lib/web/fetch/data-url.js | 744 + .../lib/web/fetch/dispatcher-weakref.js | 46 + .../node_modules/undici/lib/web/fetch/file.js | 126 + .../undici/lib/web/fetch/formdata-parser.js | 474 + .../undici/lib/web/fetch/formdata.js | 252 + .../undici/lib/web/fetch/global.js | 40 + .../undici/lib/web/fetch/headers.js | 687 + .../undici/lib/web/fetch/index.js | 2266 ++ .../undici/lib/web/fetch/request.js | 1037 + .../undici/lib/web/fetch/response.js | 605 + .../undici/lib/web/fetch/symbols.js | 9 + .../node_modules/undici/lib/web/fetch/util.js | 1632 ++ .../undici/lib/web/fetch/webidl.js | 695 + .../undici/lib/web/fileapi/encoding.js | 290 + .../undici/lib/web/fileapi/filereader.js | 344 + .../undici/lib/web/fileapi/progressevent.js | 78 + .../undici/lib/web/fileapi/symbols.js | 10 + .../undici/lib/web/fileapi/util.js | 391 + .../undici/lib/web/websocket/connection.js | 371 + .../undici/lib/web/websocket/constants.js | 66 + .../undici/lib/web/websocket/events.js | 329 + .../undici/lib/web/websocket/frame.js | 96 + .../lib/web/websocket/permessage-deflate.js | 70 + .../undici/lib/web/websocket/receiver.js | 424 + .../undici/lib/web/websocket/sender.js | 104 + .../undici/lib/web/websocket/symbols.js | 12 + .../undici/lib/web/websocket/util.js | 314 + .../undici/lib/web/websocket/websocket.js | 588 + frontend/node_modules/undici/package.json | 160 + .../undici/scripts/strip-comments.js | 8 + frontend/node_modules/undici/types/README.md | 6 + frontend/node_modules/undici/types/agent.d.ts | 31 + frontend/node_modules/undici/types/api.d.ts | 43 + .../undici/types/balanced-pool.d.ts | 29 + frontend/node_modules/undici/types/cache.d.ts | 36 + .../node_modules/undici/types/client.d.ts | 108 + .../node_modules/undici/types/connector.d.ts | 34 + .../undici/types/content-type.d.ts | 21 + .../node_modules/undici/types/cookies.d.ts | 28 + .../undici/types/diagnostics-channel.d.ts | 66 + .../node_modules/undici/types/dispatcher.d.ts | 256 + .../undici/types/env-http-proxy-agent.d.ts | 21 + .../node_modules/undici/types/errors.d.ts | 149 + .../undici/types/eventsource.d.ts | 61 + frontend/node_modules/undici/types/fetch.d.ts | 209 + frontend/node_modules/undici/types/file.d.ts | 39 + .../node_modules/undici/types/filereader.d.ts | 54 + .../node_modules/undici/types/formdata.d.ts | 108 + .../undici/types/global-dispatcher.d.ts | 9 + .../undici/types/global-origin.d.ts | 7 + .../node_modules/undici/types/handlers.d.ts | 15 + .../node_modules/undici/types/header.d.ts | 4 + frontend/node_modules/undici/types/index.d.ts | 71 + .../undici/types/interceptors.d.ts | 32 + .../node_modules/undici/types/mock-agent.d.ts | 50 + .../undici/types/mock-client.d.ts | 25 + .../undici/types/mock-errors.d.ts | 12 + .../undici/types/mock-interceptor.d.ts | 93 + .../node_modules/undici/types/mock-pool.d.ts | 25 + frontend/node_modules/undici/types/patch.d.ts | 33 + .../node_modules/undici/types/pool-stats.d.ts | 19 + frontend/node_modules/undici/types/pool.d.ts | 39 + .../undici/types/proxy-agent.d.ts | 28 + .../node_modules/undici/types/readable.d.ts | 65 + .../undici/types/retry-agent.d.ts | 8 + .../undici/types/retry-handler.d.ts | 116 + frontend/node_modules/undici/types/util.d.ts | 18 + .../node_modules/undici/types/webidl.d.ts | 228 + .../node_modules/undici/types/websocket.d.ts | 150 + .../node_modules/whatwg-encoding/LICENSE.txt | 7 + .../node_modules/whatwg-encoding/README.md | 50 + .../whatwg-encoding/lib/labels-to-names.json | 217 + .../whatwg-encoding/lib/supported-names.json | 38 + .../whatwg-encoding/lib/whatwg-encoding.js | 60 + .../node_modules/whatwg-encoding/package.json | 32 + .../node_modules/whatwg-mimetype/LICENSE.txt | 7 + .../node_modules/whatwg-mimetype/README.md | 101 + .../lib/mime-type-parameters.js | 70 + .../whatwg-mimetype/lib/mime-type.js | 127 + .../whatwg-mimetype/lib/parser.js | 105 + .../whatwg-mimetype/lib/serializer.js | 25 + .../node_modules/whatwg-mimetype/lib/utils.js | 60 + .../node_modules/whatwg-mimetype/package.json | 45 + frontend/node_modules/yaml/LICENSE | 13 + frontend/node_modules/yaml/README.md | 172 + frontend/node_modules/yaml/bin.mjs | 11 + .../dist/compose/compose-collection.js | 88 + .../yaml/browser/dist/compose/compose-doc.js | 43 + .../yaml/browser/dist/compose/compose-node.js | 102 + .../browser/dist/compose/compose-scalar.js | 86 + .../yaml/browser/dist/compose/composer.js | 217 + .../browser/dist/compose/resolve-block-map.js | 115 + .../dist/compose/resolve-block-scalar.js | 198 + .../browser/dist/compose/resolve-block-seq.js | 49 + .../yaml/browser/dist/compose/resolve-end.js | 37 + .../dist/compose/resolve-flow-collection.js | 207 + .../dist/compose/resolve-flow-scalar.js | 223 + .../browser/dist/compose/resolve-props.js | 146 + .../dist/compose/util-contains-newline.js | 34 + .../compose/util-empty-scalar-position.js | 26 + .../dist/compose/util-flow-indent-check.js | 15 + .../browser/dist/compose/util-map-includes.js | 13 + .../yaml/browser/dist/doc/Document.js | 335 + .../yaml/browser/dist/doc/anchors.js | 71 + .../yaml/browser/dist/doc/applyReviver.js | 55 + .../yaml/browser/dist/doc/createNode.js | 88 + .../yaml/browser/dist/doc/directives.js | 176 + .../node_modules/yaml/browser/dist/errors.js | 57 + .../node_modules/yaml/browser/dist/index.js | 17 + .../node_modules/yaml/browser/dist/log.js | 11 + .../yaml/browser/dist/nodes/Alias.js | 114 + .../yaml/browser/dist/nodes/Collection.js | 147 + .../yaml/browser/dist/nodes/Node.js | 38 + .../yaml/browser/dist/nodes/Pair.js | 36 + .../yaml/browser/dist/nodes/Scalar.js | 24 + .../yaml/browser/dist/nodes/YAMLMap.js | 144 + .../yaml/browser/dist/nodes/YAMLSeq.js | 113 + .../yaml/browser/dist/nodes/addPairToJSMap.js | 63 + .../yaml/browser/dist/nodes/identity.js | 36 + .../yaml/browser/dist/nodes/toJS.js | 37 + .../yaml/browser/dist/parse/cst-scalar.js | 214 + .../yaml/browser/dist/parse/cst-stringify.js | 61 + .../yaml/browser/dist/parse/cst-visit.js | 97 + .../yaml/browser/dist/parse/cst.js | 98 + .../yaml/browser/dist/parse/lexer.js | 717 + .../yaml/browser/dist/parse/line-counter.js | 39 + .../yaml/browser/dist/parse/parser.js | 967 + .../yaml/browser/dist/public-api.js | 102 + .../yaml/browser/dist/schema/Schema.js | 37 + .../yaml/browser/dist/schema/common/map.js | 17 + .../yaml/browser/dist/schema/common/null.js | 15 + .../yaml/browser/dist/schema/common/seq.js | 17 + .../yaml/browser/dist/schema/common/string.js | 14 + .../yaml/browser/dist/schema/core/bool.js | 19 + .../yaml/browser/dist/schema/core/float.js | 43 + .../yaml/browser/dist/schema/core/int.js | 38 + .../yaml/browser/dist/schema/core/schema.js | 23 + .../yaml/browser/dist/schema/json/schema.js | 62 + .../yaml/browser/dist/schema/tags.js | 96 + .../browser/dist/schema/yaml-1.1/binary.js | 58 + .../yaml/browser/dist/schema/yaml-1.1/bool.js | 26 + .../browser/dist/schema/yaml-1.1/float.js | 46 + .../yaml/browser/dist/schema/yaml-1.1/int.js | 71 + .../browser/dist/schema/yaml-1.1/merge.js | 64 + .../yaml/browser/dist/schema/yaml-1.1/omap.js | 74 + .../browser/dist/schema/yaml-1.1/pairs.js | 78 + .../browser/dist/schema/yaml-1.1/schema.js | 39 + .../yaml/browser/dist/schema/yaml-1.1/set.js | 93 + .../browser/dist/schema/yaml-1.1/timestamp.js | 101 + .../browser/dist/stringify/foldFlowLines.js | 146 + .../yaml/browser/dist/stringify/stringify.js | 128 + .../dist/stringify/stringifyCollection.js | 143 + .../dist/stringify/stringifyComment.js | 20 + .../dist/stringify/stringifyDocument.js | 85 + .../browser/dist/stringify/stringifyNumber.js | 24 + .../browser/dist/stringify/stringifyPair.js | 150 + .../browser/dist/stringify/stringifyString.js | 336 + .../node_modules/yaml/browser/dist/util.js | 11 + .../node_modules/yaml/browser/dist/visit.js | 233 + frontend/node_modules/yaml/browser/index.js | 5 + .../node_modules/yaml/browser/package.json | 3 + frontend/node_modules/yaml/dist/cli.d.ts | 8 + frontend/node_modules/yaml/dist/cli.mjs | 201 + .../yaml/dist/compose/compose-collection.d.ts | 11 + .../yaml/dist/compose/compose-collection.js | 90 + .../yaml/dist/compose/compose-doc.d.ts | 7 + .../yaml/dist/compose/compose-doc.js | 45 + .../yaml/dist/compose/compose-node.d.ts | 29 + .../yaml/dist/compose/compose-node.js | 105 + .../yaml/dist/compose/compose-scalar.d.ts | 5 + .../yaml/dist/compose/compose-scalar.js | 88 + .../yaml/dist/compose/composer.d.ts | 63 + .../yaml/dist/compose/composer.js | 222 + .../yaml/dist/compose/resolve-block-map.d.ts | 6 + .../yaml/dist/compose/resolve-block-map.js | 117 + .../dist/compose/resolve-block-scalar.d.ts | 11 + .../yaml/dist/compose/resolve-block-scalar.js | 200 + .../yaml/dist/compose/resolve-block-seq.d.ts | 6 + .../yaml/dist/compose/resolve-block-seq.js | 51 + .../yaml/dist/compose/resolve-end.d.ts | 6 + .../yaml/dist/compose/resolve-end.js | 39 + .../dist/compose/resolve-flow-collection.d.ts | 7 + .../dist/compose/resolve-flow-collection.js | 209 + .../dist/compose/resolve-flow-scalar.d.ts | 10 + .../yaml/dist/compose/resolve-flow-scalar.js | 225 + .../yaml/dist/compose/resolve-props.d.ts | 23 + .../yaml/dist/compose/resolve-props.js | 148 + .../dist/compose/util-contains-newline.d.ts | 2 + .../dist/compose/util-contains-newline.js | 36 + .../compose/util-empty-scalar-position.d.ts | 2 + .../compose/util-empty-scalar-position.js | 28 + .../dist/compose/util-flow-indent-check.d.ts | 3 + .../dist/compose/util-flow-indent-check.js | 17 + .../yaml/dist/compose/util-map-includes.d.ts | 4 + .../yaml/dist/compose/util-map-includes.js | 15 + .../node_modules/yaml/dist/doc/Document.d.ts | 141 + .../node_modules/yaml/dist/doc/Document.js | 337 + .../node_modules/yaml/dist/doc/anchors.d.ts | 24 + .../node_modules/yaml/dist/doc/anchors.js | 76 + .../yaml/dist/doc/applyReviver.d.ts | 9 + .../yaml/dist/doc/applyReviver.js | 57 + .../yaml/dist/doc/createNode.d.ts | 17 + .../node_modules/yaml/dist/doc/createNode.js | 90 + .../yaml/dist/doc/directives.d.ts | 49 + .../node_modules/yaml/dist/doc/directives.js | 178 + frontend/node_modules/yaml/dist/errors.d.ts | 21 + frontend/node_modules/yaml/dist/errors.js | 62 + frontend/node_modules/yaml/dist/index.d.ts | 25 + frontend/node_modules/yaml/dist/index.js | 50 + frontend/node_modules/yaml/dist/log.d.ts | 3 + frontend/node_modules/yaml/dist/log.js | 19 + .../node_modules/yaml/dist/nodes/Alias.d.ts | 29 + .../node_modules/yaml/dist/nodes/Alias.js | 116 + .../yaml/dist/nodes/Collection.d.ts | 73 + .../yaml/dist/nodes/Collection.js | 151 + .../node_modules/yaml/dist/nodes/Node.d.ts | 53 + frontend/node_modules/yaml/dist/nodes/Node.js | 40 + .../node_modules/yaml/dist/nodes/Pair.d.ts | 22 + frontend/node_modules/yaml/dist/nodes/Pair.js | 39 + .../node_modules/yaml/dist/nodes/Scalar.d.ts | 43 + .../node_modules/yaml/dist/nodes/Scalar.js | 27 + .../node_modules/yaml/dist/nodes/YAMLMap.d.ts | 53 + .../node_modules/yaml/dist/nodes/YAMLMap.js | 147 + .../node_modules/yaml/dist/nodes/YAMLSeq.d.ts | 60 + .../node_modules/yaml/dist/nodes/YAMLSeq.js | 115 + .../yaml/dist/nodes/addPairToJSMap.d.ts | 4 + .../yaml/dist/nodes/addPairToJSMap.js | 65 + .../yaml/dist/nodes/identity.d.ts | 23 + .../node_modules/yaml/dist/nodes/identity.js | 53 + .../node_modules/yaml/dist/nodes/toJS.d.ts | 29 + frontend/node_modules/yaml/dist/nodes/toJS.js | 39 + frontend/node_modules/yaml/dist/options.d.ts | 344 + .../yaml/dist/parse/cst-scalar.d.ts | 64 + .../yaml/dist/parse/cst-scalar.js | 218 + .../yaml/dist/parse/cst-stringify.d.ts | 8 + .../yaml/dist/parse/cst-stringify.js | 63 + .../yaml/dist/parse/cst-visit.d.ts | 39 + .../node_modules/yaml/dist/parse/cst-visit.js | 99 + .../node_modules/yaml/dist/parse/cst.d.ts | 109 + frontend/node_modules/yaml/dist/parse/cst.js | 112 + .../node_modules/yaml/dist/parse/lexer.d.ts | 87 + .../node_modules/yaml/dist/parse/lexer.js | 719 + .../yaml/dist/parse/line-counter.d.ts | 22 + .../yaml/dist/parse/line-counter.js | 41 + .../node_modules/yaml/dist/parse/parser.d.ts | 84 + .../node_modules/yaml/dist/parse/parser.js | 972 + .../node_modules/yaml/dist/public-api.d.ts | 44 + frontend/node_modules/yaml/dist/public-api.js | 107 + .../node_modules/yaml/dist/schema/Schema.d.ts | 17 + .../node_modules/yaml/dist/schema/Schema.js | 39 + .../yaml/dist/schema/common/map.d.ts | 2 + .../yaml/dist/schema/common/map.js | 19 + .../yaml/dist/schema/common/null.d.ts | 4 + .../yaml/dist/schema/common/null.js | 17 + .../yaml/dist/schema/common/seq.d.ts | 2 + .../yaml/dist/schema/common/seq.js | 19 + .../yaml/dist/schema/common/string.d.ts | 2 + .../yaml/dist/schema/common/string.js | 16 + .../yaml/dist/schema/core/bool.d.ts | 4 + .../yaml/dist/schema/core/bool.js | 21 + .../yaml/dist/schema/core/float.d.ts | 4 + .../yaml/dist/schema/core/float.js | 47 + .../yaml/dist/schema/core/int.d.ts | 4 + .../node_modules/yaml/dist/schema/core/int.js | 42 + .../yaml/dist/schema/core/schema.d.ts | 1 + .../yaml/dist/schema/core/schema.js | 25 + .../yaml/dist/schema/json-schema.d.ts | 69 + .../yaml/dist/schema/json/schema.d.ts | 2 + .../yaml/dist/schema/json/schema.js | 64 + .../node_modules/yaml/dist/schema/tags.d.ts | 48 + .../node_modules/yaml/dist/schema/tags.js | 99 + .../node_modules/yaml/dist/schema/types.d.ts | 92 + .../yaml/dist/schema/yaml-1.1/binary.d.ts | 2 + .../yaml/dist/schema/yaml-1.1/binary.js | 70 + .../yaml/dist/schema/yaml-1.1/bool.d.ts | 7 + .../yaml/dist/schema/yaml-1.1/bool.js | 29 + .../yaml/dist/schema/yaml-1.1/float.d.ts | 4 + .../yaml/dist/schema/yaml-1.1/float.js | 50 + .../yaml/dist/schema/yaml-1.1/int.d.ts | 5 + .../yaml/dist/schema/yaml-1.1/int.js | 76 + .../yaml/dist/schema/yaml-1.1/merge.d.ts | 9 + .../yaml/dist/schema/yaml-1.1/merge.js | 68 + .../yaml/dist/schema/yaml-1.1/omap.d.ts | 22 + .../yaml/dist/schema/yaml-1.1/omap.js | 77 + .../yaml/dist/schema/yaml-1.1/pairs.d.ts | 10 + .../yaml/dist/schema/yaml-1.1/pairs.js | 82 + .../yaml/dist/schema/yaml-1.1/schema.d.ts | 1 + .../yaml/dist/schema/yaml-1.1/schema.js | 41 + .../yaml/dist/schema/yaml-1.1/set.d.ts | 28 + .../yaml/dist/schema/yaml-1.1/set.js | 96 + .../yaml/dist/schema/yaml-1.1/timestamp.d.ts | 6 + .../yaml/dist/schema/yaml-1.1/timestamp.js | 105 + .../yaml/dist/stringify/foldFlowLines.d.ts | 34 + .../yaml/dist/stringify/foldFlowLines.js | 151 + .../yaml/dist/stringify/stringify.d.ts | 21 + .../yaml/dist/stringify/stringify.js | 131 + .../dist/stringify/stringifyCollection.d.ts | 17 + .../dist/stringify/stringifyCollection.js | 145 + .../yaml/dist/stringify/stringifyComment.d.ts | 10 + .../yaml/dist/stringify/stringifyComment.js | 24 + .../dist/stringify/stringifyDocument.d.ts | 4 + .../yaml/dist/stringify/stringifyDocument.js | 87 + .../yaml/dist/stringify/stringifyNumber.d.ts | 2 + .../yaml/dist/stringify/stringifyNumber.js | 26 + .../yaml/dist/stringify/stringifyPair.d.ts | 3 + .../yaml/dist/stringify/stringifyPair.js | 152 + .../yaml/dist/stringify/stringifyString.d.ts | 9 + .../yaml/dist/stringify/stringifyString.js | 338 + .../node_modules/yaml/dist/test-events.d.ts | 4 + .../node_modules/yaml/dist/test-events.js | 134 + frontend/node_modules/yaml/dist/util.d.ts | 16 + frontend/node_modules/yaml/dist/util.js | 28 + frontend/node_modules/yaml/dist/visit.d.ts | 102 + frontend/node_modules/yaml/dist/visit.js | 236 + frontend/node_modules/yaml/package.json | 97 + frontend/node_modules/yaml/util.js | 2 + frontend/package-lock.json | 8 +- frontend/package.json | 2 +- frontend/src/App.vue | 5 +- frontend/src/components/AISidebar.vue | 170 +- frontend/src/components/MindMap.vue | 384 +- frontend/src/lib/mind-elixir/.eslintignore | 4 + frontend/src/lib/mind-elixir/.eslintrc.cjs | 16 + .../src/lib/mind-elixir/.github/FUNDING.yml | 12 + .../.github/ISSUE_TEMPLATE/bug_report.md | 38 + .../.github/ISSUE_TEMPLATE/feature_request.md | 20 + .../.github/workflows/npm-publish.yml | 60 + frontend/src/lib/mind-elixir/.gitignore | 32 + .../src/lib/mind-elixir/.husky/commit-msg | 4 + .../src/lib/mind-elixir/.husky/pre-commit | 4 + frontend/src/lib/mind-elixir/.husky/pre-push | 4 + frontend/src/lib/mind-elixir/.npmignore | 74 + frontend/src/lib/mind-elixir/.prettierrc.json | 9 + .../lib}/mind-elixir/LICENSE | 0 .../src/lib/mind-elixir/api-extractor.json | 396 + frontend/src/lib/mind-elixir/build.js | 47 + .../src/lib/mind-elixir/commitlint.config.js | 107 + frontend/src/lib/mind-elixir/images/logo.png | Bin 0 -> 19287 bytes frontend/src/lib/mind-elixir/images/logo2.png | Bin 0 -> 720485 bytes .../lib/mind-elixir/images/screenshot.cn.png | Bin 0 -> 338991 bytes .../src/lib/mind-elixir/images/screenshot.png | Bin 0 -> 310514 bytes .../lib/mind-elixir/images/screenshot2.png | Bin 0 -> 143312 bytes .../lib/mind-elixir/images/screenshot5.jpg | Bin 0 -> 214511 bytes frontend/src/lib/mind-elixir/index.css | 177 + frontend/src/lib/mind-elixir/index.html | 40 + frontend/src/lib/mind-elixir/katex.css | 1 + .../src/lib/mind-elixir/package-lock.json | 7715 ++++++ .../lib}/mind-elixir/package.json | 51 +- .../src/lib/mind-elixir/playwright.config.ts | 81 + frontend/src/lib/mind-elixir/pnpm-lock.yaml | 4550 ++++ frontend/src/lib/mind-elixir/readme.md | 432 + frontend/src/lib/mind-elixir/readme/es.md | 430 + frontend/src/lib/mind-elixir/readme/fr.md | 430 + frontend/src/lib/mind-elixir/readme/ja.md | 429 + .../lib/mind-elixir/readme/ko.md} | 214 +- frontend/src/lib/mind-elixir/readme/pt.md | 430 + frontend/src/lib/mind-elixir/readme/ru.md | 430 + frontend/src/lib/mind-elixir/readme/zh.md | 430 + .../mind-elixir/refs/scale-calc.excalidraw | 1720 ++ frontend/src/lib/mind-elixir/src/arrow.ts | 556 + frontend/src/lib/mind-elixir/src/const.ts | 62 + frontend/src/lib/mind-elixir/src/dev.dist.ts | 68 + frontend/src/lib/mind-elixir/src/dev.ts | 185 + frontend/src/lib/mind-elixir/src/docs.ts | 26 + .../lib/mind-elixir/src/exampleData/1.cn.ts | 544 + .../src/lib/mind-elixir/src/exampleData/1.ts | 623 + .../src/lib/mind-elixir/src/exampleData/2.ts | 114 + .../src/lib/mind-elixir/src/exampleData/3.ts | 2646 ++ .../mind-elixir/src/exampleData/htmlText.ts | 6 + frontend/src/lib/mind-elixir/src/i18n.ts | 165 + .../lib/mind-elixir/src/icons/add-circle.svg | 7 + .../src/lib/mind-elixir/src/icons/full.svg | 1 + .../src/lib/mind-elixir/src/icons/left.svg | 1 + .../src/lib/mind-elixir/src/icons/living.svg | 1 + .../mind-elixir/src/icons/minus-circle.svg | 7 + .../src/lib/mind-elixir/src/icons/right.svg | 1 + .../src/lib/mind-elixir/src/icons/side.svg | 1 + .../src/lib/mind-elixir/src/icons/zoomin.svg | 1 + .../src/lib/mind-elixir/src/icons/zoomout.svg | 1 + frontend/src/lib/mind-elixir/src/index.less | 320 + frontend/src/lib/mind-elixir/src/index.ts | 198 + frontend/src/lib/mind-elixir/src/interact.ts | 407 + frontend/src/lib/mind-elixir/src/linkDiv.ts | 107 + frontend/src/lib/mind-elixir/src/methods.ts | 131 + frontend/src/lib/mind-elixir/src/mouse.ts | 161 + .../src/lib/mind-elixir/src/nodeOperation.ts | 314 + .../mind-elixir/src/plugin/contextMenu.less | 66 + .../lib/mind-elixir/src/plugin/contextMenu.ts | 229 + .../lib/mind-elixir/src/plugin/exportImage.ts | 263 + .../lib/mind-elixir/src/plugin/keypress.ts | 242 + .../mind-elixir/src/plugin/nodeDraggable.ts | 174 + .../src/plugin/operationHistory.ts | 124 + .../lib/mind-elixir/src/plugin/selection.ts | 94 + .../lib/mind-elixir/src/plugin/toolBar.less | 40 + .../src/lib/mind-elixir/src/plugin/toolBar.ts | 85 + frontend/src/lib/mind-elixir/src/summary.ts | 241 + frontend/src/lib/mind-elixir/src/types/dom.ts | 61 + .../src/lib/mind-elixir/src/types/global.ts | 7 + .../src/lib/mind-elixir/src/types/index.ts | 249 + .../src/utils/LinkDragMoveHelper.ts | 61 + frontend/src/lib/mind-elixir/src/utils/dom.ts | 248 + .../mind-elixir/src/utils/domManipulation.ts | 62 + .../mind-elixir/src/utils/dragMoveHelper.ts | 19 + .../mind-elixir/src/utils/generateBranch.ts | 80 + .../src/lib/mind-elixir/src/utils/index.ts | 192 + .../lib/mind-elixir/src/utils/layout-ssr.ts | 321 + .../src/lib/mind-elixir/src/utils/layout.ts | 80 + .../src/utils/objectManipulation.ts | 77 + .../src/lib/mind-elixir/src/utils/pubsub.ts | 117 + frontend/src/lib/mind-elixir/src/utils/svg.ts | 189 + .../src/lib/mind-elixir/src/utils/theme.ts | 18 + .../src/lib/mind-elixir/src/vite-env.d.ts | 1 + frontend/src/lib/mind-elixir/test.html | 39 + .../mind-elixir/tests/MindElixirFixture.ts | 110 + .../src/lib/mind-elixir/tests/arrow.spec.ts | 729 + .../mind-elixir/tests/drag-and-drop.spec.ts | 58 + .../DnD-move-after-1-chromium-win32.png | Bin 0 -> 12961 bytes .../DnD-move-before-1-chromium-win32.png | Bin 0 -> 12903 bytes .../DnD-move-in-1-chromium-win32.png | Bin 0 -> 9136 bytes .../mind-elixir/tests/expand-collapse.spec.ts | 191 + .../lib/mind-elixir/tests/interaction.spec.ts | 103 + .../Add-Before-1-chromium-win32.png | Bin 0 -> 9602 bytes .../Add-Child-1-chromium-win32.png | Bin 0 -> 9000 bytes .../Add-Parent-1-chromium-win32.png | Bin 0 -> 8954 bytes .../Add-Sibling-1-chromium-win32.png | Bin 0 -> 9629 bytes .../Clear-and-reset-1-chromium-win32.png | Bin 0 -> 9301 bytes .../Copy-and-Paste-1-chromium-win32.png | Bin 0 -> 13194 bytes .../Edit-Node-1-chromium-win32.png | Bin 0 -> 10221 bytes .../Remove-Node-1-chromium-win32.png | Bin 0 -> 8226 bytes .../tests/keyboard-undo-redo.spec.ts | 235 + .../lib/mind-elixir/tests/mind-elixir-test.ts | 46 + .../tests/multiple-instance.spec.ts | 50 + ...ld-To-Data2-Correctly-1-chromium-win32.png | Bin 0 -> 24942 bytes .../mind-elixir/tests/multiple-node.spec.ts | 94 + .../Multiple-Copy-1-chromium-win32.png | Bin 0 -> 16093 bytes .../Multiple-Move-After-1-chromium-win32.png | Bin 0 -> 13398 bytes .../Multiple-Move-Before-1-chromium-win32.png | Bin 0 -> 13310 bytes .../Multiple-Move-In-1-chromium-win32.png | Bin 0 -> 13015 bytes .../tests/operation-history.spec.ts | 293 + .../tests/simple-undo-redo.spec.ts | 139 + .../src/lib/mind-elixir/tests/summary.spec.ts | 310 + .../mind-elixir/tests/topic-select.spec.ts | 85 + .../lib/mind-elixir/tests/undo-redo.spec.ts | 231 + frontend/src/lib/mind-elixir/tsconfig.json | 28 + frontend/src/lib/mind-elixir/vite.config.ts | 61 + frontend/src/utils/markdownRenderer.js | 165 +- frontend/test-enhanced-markdown.html | 261 + frontend/test-table-rendering.html | 127 + frontend/test-table.html | 120 + mind-elixir-core-master/.eslintignore | 4 + mind-elixir-core-master/.eslintrc.cjs | 16 + mind-elixir-core-master/.github/FUNDING.yml | 12 + .../.github/ISSUE_TEMPLATE/bug_report.md | 38 + .../.github/ISSUE_TEMPLATE/feature_request.md | 20 + .../.github/workflows/npm-publish.yml | 60 + mind-elixir-core-master/.gitignore | 32 + mind-elixir-core-master/.husky/commit-msg | 4 + mind-elixir-core-master/.husky/pre-commit | 4 + mind-elixir-core-master/.husky/pre-push | 4 + mind-elixir-core-master/.npmignore | 74 + mind-elixir-core-master/.prettierrc.json | 9 + mind-elixir-core-master/LICENSE | 21 + mind-elixir-core-master/api-extractor.json | 396 + mind-elixir-core-master/build.js | 47 + mind-elixir-core-master/commitlint.config.js | 107 + mind-elixir-core-master/images/logo.png | Bin 0 -> 19287 bytes mind-elixir-core-master/images/logo2.png | Bin 0 -> 720485 bytes .../images/screenshot.cn.png | Bin 0 -> 338991 bytes mind-elixir-core-master/images/screenshot.png | Bin 0 -> 310514 bytes .../images/screenshot2.png | Bin 0 -> 143312 bytes .../images/screenshot5.jpg | Bin 0 -> 214511 bytes mind-elixir-core-master/index.css | 177 + mind-elixir-core-master/index.html | 40 + mind-elixir-core-master/katex.css | 1 + mind-elixir-core-master/package.json | 108 + mind-elixir-core-master/playwright.config.ts | 81 + mind-elixir-core-master/pnpm-lock.yaml | 4550 ++++ mind-elixir-core-master/readme.md | 432 + mind-elixir-core-master/readme/es.md | 430 + mind-elixir-core-master/readme/fr.md | 430 + mind-elixir-core-master/readme/ja.md | 429 + mind-elixir-core-master/readme/ko.md | 430 + mind-elixir-core-master/readme/pt.md | 430 + mind-elixir-core-master/readme/ru.md | 430 + mind-elixir-core-master/readme/zh.md | 430 + .../refs/scale-calc.excalidraw | 1720 ++ mind-elixir-core-master/src/arrow.ts | 556 + mind-elixir-core-master/src/const.ts | 62 + mind-elixir-core-master/src/dev.dist.ts | 68 + mind-elixir-core-master/src/dev.ts | 185 + mind-elixir-core-master/src/docs.ts | 26 + .../src/exampleData/1.cn.ts | 544 + mind-elixir-core-master/src/exampleData/1.ts | 623 + mind-elixir-core-master/src/exampleData/2.ts | 114 + mind-elixir-core-master/src/exampleData/3.ts | 2646 ++ .../src/exampleData/htmlText.ts | 6 + mind-elixir-core-master/src/i18n.ts | 165 + .../src/icons/add-circle.svg | 7 + mind-elixir-core-master/src/icons/full.svg | 1 + mind-elixir-core-master/src/icons/left.svg | 1 + mind-elixir-core-master/src/icons/living.svg | 1 + .../src/icons/minus-circle.svg | 7 + mind-elixir-core-master/src/icons/right.svg | 1 + mind-elixir-core-master/src/icons/side.svg | 1 + mind-elixir-core-master/src/icons/zoomin.svg | 1 + mind-elixir-core-master/src/icons/zoomout.svg | 1 + mind-elixir-core-master/src/index.less | 320 + mind-elixir-core-master/src/index.ts | 198 + mind-elixir-core-master/src/interact.ts | 407 + mind-elixir-core-master/src/linkDiv.ts | 107 + mind-elixir-core-master/src/methods.ts | 131 + mind-elixir-core-master/src/mouse.ts | 161 + mind-elixir-core-master/src/nodeOperation.ts | 314 + .../src/plugin/contextMenu.less | 66 + .../src/plugin/contextMenu.ts | 229 + .../src/plugin/exportImage.ts | 263 + .../src/plugin/keypress.ts | 242 + .../src/plugin/nodeDraggable.ts | 174 + .../src/plugin/operationHistory.ts | 124 + .../src/plugin/selection.ts | 94 + .../src/plugin/toolBar.less | 40 + mind-elixir-core-master/src/plugin/toolBar.ts | 85 + mind-elixir-core-master/src/summary.ts | 241 + mind-elixir-core-master/src/types/dom.ts | 61 + mind-elixir-core-master/src/types/global.ts | 7 + mind-elixir-core-master/src/types/index.ts | 249 + .../src/utils/LinkDragMoveHelper.ts | 61 + mind-elixir-core-master/src/utils/dom.ts | 248 + .../src/utils/domManipulation.ts | 62 + .../src/utils/dragMoveHelper.ts | 19 + .../src/utils/generateBranch.ts | 80 + mind-elixir-core-master/src/utils/index.ts | 192 + .../src/utils/layout-ssr.ts | 321 + mind-elixir-core-master/src/utils/layout.ts | 80 + .../src/utils/objectManipulation.ts | 77 + mind-elixir-core-master/src/utils/pubsub.ts | 117 + mind-elixir-core-master/src/utils/svg.ts | 189 + mind-elixir-core-master/src/utils/theme.ts | 18 + mind-elixir-core-master/src/vite-env.d.ts | 1 + mind-elixir-core-master/test.html | 39 + .../tests/MindElixirFixture.ts | 110 + mind-elixir-core-master/tests/arrow.spec.ts | 729 + .../tests/drag-and-drop.spec.ts | 58 + .../DnD-move-after-1-chromium-win32.png | Bin 0 -> 12961 bytes .../DnD-move-before-1-chromium-win32.png | Bin 0 -> 12903 bytes .../DnD-move-in-1-chromium-win32.png | Bin 0 -> 9136 bytes .../tests/expand-collapse.spec.ts | 191 + .../tests/interaction.spec.ts | 103 + .../Add-Before-1-chromium-win32.png | Bin 0 -> 9602 bytes .../Add-Child-1-chromium-win32.png | Bin 0 -> 9000 bytes .../Add-Parent-1-chromium-win32.png | Bin 0 -> 8954 bytes .../Add-Sibling-1-chromium-win32.png | Bin 0 -> 9629 bytes .../Clear-and-reset-1-chromium-win32.png | Bin 0 -> 9301 bytes .../Copy-and-Paste-1-chromium-win32.png | Bin 0 -> 13194 bytes .../Edit-Node-1-chromium-win32.png | Bin 0 -> 10221 bytes .../Remove-Node-1-chromium-win32.png | Bin 0 -> 8226 bytes .../tests/keyboard-undo-redo.spec.ts | 235 + .../tests/mind-elixir-test.ts | 46 + .../tests/multiple-instance.spec.ts | 50 + ...ld-To-Data2-Correctly-1-chromium-win32.png | Bin 0 -> 24942 bytes .../tests/multiple-node.spec.ts | 94 + .../Multiple-Copy-1-chromium-win32.png | Bin 0 -> 16093 bytes .../Multiple-Move-After-1-chromium-win32.png | Bin 0 -> 13398 bytes .../Multiple-Move-Before-1-chromium-win32.png | Bin 0 -> 13310 bytes .../Multiple-Move-In-1-chromium-win32.png | Bin 0 -> 13015 bytes .../tests/operation-history.spec.ts | 293 + .../tests/simple-undo-redo.spec.ts | 139 + mind-elixir-core-master/tests/summary.spec.ts | 310 + .../tests/topic-select.spec.ts | 85 + .../tests/undo-redo.spec.ts | 231 + mind-elixir-core-master/tsconfig.json | 28 + mind-elixir-core-master/vite.config.ts | 61 + 5392 files changed, 677302 insertions(+), 8403 deletions(-) create mode 100644 frontend/debug-current-issue.html create mode 100644 frontend/debug-mindelixir-styles.html create mode 100644 frontend/debug-table-detection.html create mode 120000 frontend/node_modules/.bin/csv2json create mode 120000 frontend/node_modules/.bin/csv2tsv create mode 120000 frontend/node_modules/.bin/dsv2dsv create mode 120000 frontend/node_modules/.bin/dsv2json create mode 120000 frontend/node_modules/.bin/json2csv create mode 120000 frontend/node_modules/.bin/json2dsv create mode 120000 frontend/node_modules/.bin/json2tsv create mode 120000 frontend/node_modules/.bin/katex create mode 120000 frontend/node_modules/.bin/markdown-it create mode 120000 frontend/node_modules/.bin/tsv2csv create mode 120000 frontend/node_modules/.bin/tsv2json create mode 120000 frontend/node_modules/.bin/yaml delete mode 100644 frontend/node_modules/.vite/deps/mind-elixir.js delete mode 100644 frontend/node_modules/.vite/deps/mind-elixir.js.map create mode 100644 frontend/node_modules/.vite/deps/prismjs.js create mode 100644 frontend/node_modules/.vite/deps/prismjs.js.map create mode 100644 frontend/node_modules/.vite/deps/prismjs_components_prism-css.js create mode 100644 frontend/node_modules/.vite/deps/prismjs_components_prism-css.js.map create mode 100644 frontend/node_modules/.vite/deps/prismjs_components_prism-javascript.js create mode 100644 frontend/node_modules/.vite/deps/prismjs_components_prism-javascript.js.map create mode 100644 frontend/node_modules/.vite/deps/prismjs_components_prism-json.js create mode 100644 frontend/node_modules/.vite/deps/prismjs_components_prism-json.js.map create mode 100644 frontend/node_modules/.vite/deps/prismjs_components_prism-python.js create mode 100644 frontend/node_modules/.vite/deps/prismjs_components_prism-python.js.map create mode 100644 frontend/node_modules/.vite/deps/prismjs_components_prism-sql.js create mode 100644 frontend/node_modules/.vite/deps/prismjs_components_prism-sql.js.map create mode 100644 frontend/node_modules/@babel/runtime/LICENSE create mode 100644 frontend/node_modules/@babel/runtime/README.md create mode 100644 frontend/node_modules/@babel/runtime/helpers/AwaitValue.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/OverloadYield.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/applyDecoratedDescriptor.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/applyDecs.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/applyDecs2203.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/applyDecs2203R.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/applyDecs2301.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/applyDecs2305.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/applyDecs2311.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/arrayLikeToArray.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/arrayWithHoles.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/arrayWithoutHoles.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/assertClassBrand.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/assertThisInitialized.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/asyncGeneratorDelegate.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/asyncIterator.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/asyncToGenerator.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/awaitAsyncGenerator.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/callSuper.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/checkInRHS.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/checkPrivateRedeclaration.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classApplyDescriptorDestructureSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classApplyDescriptorGet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classApplyDescriptorSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classCallCheck.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classCheckPrivateStaticAccess.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classCheckPrivateStaticFieldDescriptor.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classExtractFieldDescriptor.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classNameTDZError.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateFieldDestructureSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateFieldGet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateFieldGet2.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateFieldInitSpec.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateFieldLooseBase.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateFieldLooseKey.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateFieldSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateFieldSet2.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateGetter.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateMethodGet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateMethodInitSpec.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateMethodSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classPrivateSetter.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classStaticPrivateFieldDestructureSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classStaticPrivateFieldSpecGet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classStaticPrivateFieldSpecSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classStaticPrivateMethodGet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/classStaticPrivateMethodSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/construct.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/createClass.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/createForOfIteratorHelper.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/createForOfIteratorHelperLoose.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/createSuper.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/decorate.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/defaults.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/defineAccessor.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/defineEnumerableProperties.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/defineProperty.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/dispose.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/AwaitValue.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/OverloadYield.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/applyDecoratedDescriptor.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/applyDecs.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/applyDecs2203.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/applyDecs2203R.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/applyDecs2301.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/applyDecs2305.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/applyDecs2311.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/arrayLikeToArray.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/arrayWithHoles.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/arrayWithoutHoles.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/assertClassBrand.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/assertThisInitialized.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/asyncGeneratorDelegate.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/asyncIterator.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/asyncToGenerator.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/awaitAsyncGenerator.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/callSuper.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/checkInRHS.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/checkPrivateRedeclaration.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classApplyDescriptorDestructureSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classApplyDescriptorGet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classApplyDescriptorSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classCallCheck.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classCheckPrivateStaticAccess.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classCheckPrivateStaticFieldDescriptor.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classExtractFieldDescriptor.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classNameTDZError.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateFieldDestructureSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateFieldGet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateFieldGet2.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateFieldInitSpec.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateFieldLooseBase.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateFieldLooseKey.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateFieldSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateFieldSet2.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateGetter.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateMethodGet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateMethodInitSpec.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateMethodSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classPrivateSetter.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classStaticPrivateFieldDestructureSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classStaticPrivateFieldSpecGet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classStaticPrivateFieldSpecSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classStaticPrivateMethodGet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/classStaticPrivateMethodSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/construct.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/createClass.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/createForOfIteratorHelper.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/createForOfIteratorHelperLoose.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/createSuper.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/decorate.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/defaults.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/defineAccessor.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/defineEnumerableProperties.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/defineProperty.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/dispose.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/extends.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/get.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/getPrototypeOf.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/identity.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/importDeferProxy.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/inherits.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/inheritsLoose.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/initializerDefineProperty.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/initializerWarningHelper.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/instanceof.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/interopRequireDefault.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/interopRequireWildcard.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/isNativeFunction.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/isNativeReflectConstruct.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/iterableToArray.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/iterableToArrayLimit.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/jsx.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/maybeArrayLike.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/newArrowCheck.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/nonIterableRest.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/nonIterableSpread.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/nullishReceiverError.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/objectDestructuringEmpty.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/objectSpread.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/objectSpread2.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/objectWithoutProperties.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/objectWithoutPropertiesLoose.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/package.json create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/possibleConstructorReturn.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/readOnlyError.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/regenerator.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/regeneratorAsync.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/regeneratorAsyncGen.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/regeneratorAsyncIterator.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/regeneratorDefine.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/regeneratorKeys.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/regeneratorRuntime.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/regeneratorValues.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/set.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/setFunctionName.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/setPrototypeOf.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/skipFirstGeneratorNext.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/slicedToArray.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/superPropBase.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/superPropGet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/superPropSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/taggedTemplateLiteral.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/taggedTemplateLiteralLoose.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/tdz.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/temporalRef.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/temporalUndefined.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/toArray.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/toConsumableArray.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/toPrimitive.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/toPropertyKey.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/toSetter.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/tsRewriteRelativeImportExtensions.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/typeof.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/unsupportedIterableToArray.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/using.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/usingCtx.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/wrapAsyncGenerator.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/wrapNativeSuper.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/wrapRegExp.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/esm/writeOnlyError.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/extends.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/get.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/getPrototypeOf.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/identity.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/importDeferProxy.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/inherits.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/inheritsLoose.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/initializerDefineProperty.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/initializerWarningHelper.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/instanceof.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/interopRequireDefault.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/interopRequireWildcard.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/isNativeFunction.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/isNativeReflectConstruct.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/iterableToArray.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/iterableToArrayLimit.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/jsx.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/maybeArrayLike.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/newArrowCheck.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/nonIterableRest.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/nonIterableSpread.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/nullishReceiverError.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/objectDestructuringEmpty.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/objectSpread.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/objectSpread2.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/objectWithoutProperties.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/objectWithoutPropertiesLoose.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/possibleConstructorReturn.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/readOnlyError.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/regenerator.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/regeneratorAsync.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/regeneratorAsyncGen.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/regeneratorAsyncIterator.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/regeneratorDefine.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/regeneratorKeys.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/regeneratorRuntime.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/regeneratorValues.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/set.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/setFunctionName.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/setPrototypeOf.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/skipFirstGeneratorNext.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/slicedToArray.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/superPropBase.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/superPropGet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/superPropSet.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/taggedTemplateLiteral.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/taggedTemplateLiteralLoose.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/tdz.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/temporalRef.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/temporalUndefined.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/toArray.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/toConsumableArray.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/toPrimitive.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/toPropertyKey.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/toSetter.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/tsRewriteRelativeImportExtensions.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/typeof.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/unsupportedIterableToArray.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/using.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/usingCtx.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/wrapAsyncGenerator.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/wrapNativeSuper.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/wrapRegExp.js create mode 100644 frontend/node_modules/@babel/runtime/helpers/writeOnlyError.js create mode 100644 frontend/node_modules/@babel/runtime/package.json create mode 100644 frontend/node_modules/@babel/runtime/regenerator/index.js create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/LICENSE create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/README.md create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/dist/index.cjs create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/dist/index.js create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/dist/index.mjs create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/jsx-runtime.d.ts create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/jsx-runtime.js create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/package.json create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/types/consts.d.ts create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/types/h.d.ts create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/types/index.d.ts create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/types/mount.d.ts create mode 100644 frontend/node_modules/@gera2ld/jsx-dom/types/types.d.ts create mode 100644 frontend/node_modules/@vscode/markdown-it-katex/LICENSE create mode 100644 frontend/node_modules/@vscode/markdown-it-katex/README.md create mode 100644 frontend/node_modules/@vscode/markdown-it-katex/dist/index.js create mode 100644 frontend/node_modules/@vscode/markdown-it-katex/package.json create mode 100644 frontend/node_modules/@vscode/markdown-it-katex/types.d.ts create mode 100644 frontend/node_modules/boolbase/README.md create mode 100644 frontend/node_modules/boolbase/index.js create mode 100644 frontend/node_modules/boolbase/package.json create mode 100644 frontend/node_modules/cheerio-select/LICENSE create mode 100644 frontend/node_modules/cheerio-select/README.md create mode 100644 frontend/node_modules/cheerio-select/lib/esm/helpers.d.ts create mode 100644 frontend/node_modules/cheerio-select/lib/esm/helpers.d.ts.map create mode 100644 frontend/node_modules/cheerio-select/lib/esm/helpers.js create mode 100644 frontend/node_modules/cheerio-select/lib/esm/helpers.js.map create mode 100644 frontend/node_modules/cheerio-select/lib/esm/index.d.ts create mode 100644 frontend/node_modules/cheerio-select/lib/esm/index.d.ts.map create mode 100644 frontend/node_modules/cheerio-select/lib/esm/index.js create mode 100644 frontend/node_modules/cheerio-select/lib/esm/index.js.map create mode 100644 frontend/node_modules/cheerio-select/lib/esm/package.json create mode 100644 frontend/node_modules/cheerio-select/lib/esm/positionals.d.ts create mode 100644 frontend/node_modules/cheerio-select/lib/esm/positionals.d.ts.map create mode 100644 frontend/node_modules/cheerio-select/lib/esm/positionals.js create mode 100644 frontend/node_modules/cheerio-select/lib/esm/positionals.js.map create mode 100644 frontend/node_modules/cheerio-select/lib/helpers.d.ts create mode 100644 frontend/node_modules/cheerio-select/lib/helpers.d.ts.map create mode 100644 frontend/node_modules/cheerio-select/lib/helpers.js create mode 100644 frontend/node_modules/cheerio-select/lib/helpers.js.map create mode 100644 frontend/node_modules/cheerio-select/lib/index.d.ts create mode 100644 frontend/node_modules/cheerio-select/lib/index.d.ts.map create mode 100644 frontend/node_modules/cheerio-select/lib/index.js create mode 100644 frontend/node_modules/cheerio-select/lib/index.js.map create mode 100644 frontend/node_modules/cheerio-select/lib/positionals.d.ts create mode 100644 frontend/node_modules/cheerio-select/lib/positionals.d.ts.map create mode 100644 frontend/node_modules/cheerio-select/lib/positionals.js create mode 100644 frontend/node_modules/cheerio-select/lib/positionals.js.map create mode 100644 frontend/node_modules/cheerio-select/package.json create mode 100644 frontend/node_modules/cheerio/LICENSE create mode 100644 frontend/node_modules/cheerio/Readme.md create mode 100644 frontend/node_modules/cheerio/dist/browser/api/attributes.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/api/attributes.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/api/attributes.js create mode 100644 frontend/node_modules/cheerio/dist/browser/api/attributes.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/api/css.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/api/css.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/api/css.js create mode 100644 frontend/node_modules/cheerio/dist/browser/api/css.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/api/extract.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/api/extract.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/api/extract.js create mode 100644 frontend/node_modules/cheerio/dist/browser/api/extract.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/api/forms.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/api/forms.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/api/forms.js create mode 100644 frontend/node_modules/cheerio/dist/browser/api/forms.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/api/manipulation.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/api/manipulation.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/api/manipulation.js create mode 100644 frontend/node_modules/cheerio/dist/browser/api/manipulation.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/api/traversing.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/api/traversing.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/api/traversing.js create mode 100644 frontend/node_modules/cheerio/dist/browser/api/traversing.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/cheerio.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/cheerio.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/cheerio.js create mode 100644 frontend/node_modules/cheerio/dist/browser/cheerio.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/index-browser.d.mts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/index-browser.mjs.map create mode 100644 frontend/node_modules/cheerio/dist/browser/index.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/index.js create mode 100644 frontend/node_modules/cheerio/dist/browser/load-parse.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/load-parse.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/load-parse.js create mode 100644 frontend/node_modules/cheerio/dist/browser/load-parse.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/load.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/load.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/load.js create mode 100644 frontend/node_modules/cheerio/dist/browser/load.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/options.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/options.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/options.js create mode 100644 frontend/node_modules/cheerio/dist/browser/options.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/package.json create mode 100644 frontend/node_modules/cheerio/dist/browser/parse.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/parse.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/parse.js create mode 100644 frontend/node_modules/cheerio/dist/browser/parse.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/parsers/parse5-adapter.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/parsers/parse5-adapter.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/parsers/parse5-adapter.js create mode 100644 frontend/node_modules/cheerio/dist/browser/parsers/parse5-adapter.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/slim.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/slim.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/slim.js create mode 100644 frontend/node_modules/cheerio/dist/browser/slim.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/static.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/static.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/static.js create mode 100644 frontend/node_modules/cheerio/dist/browser/static.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/types.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/types.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/types.js create mode 100644 frontend/node_modules/cheerio/dist/browser/types.js.map create mode 100644 frontend/node_modules/cheerio/dist/browser/utils.d.ts create mode 100644 frontend/node_modules/cheerio/dist/browser/utils.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/browser/utils.js create mode 100644 frontend/node_modules/cheerio/dist/browser/utils.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/attributes.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/attributes.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/attributes.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/attributes.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/css.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/css.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/css.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/css.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/extract.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/extract.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/extract.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/extract.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/forms.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/forms.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/forms.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/forms.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/manipulation.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/manipulation.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/manipulation.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/manipulation.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/traversing.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/traversing.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/traversing.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/api/traversing.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/cheerio.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/cheerio.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/cheerio.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/cheerio.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/index.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/index.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/index.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/index.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/load-parse.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/load-parse.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/load-parse.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/load-parse.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/load.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/load.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/load.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/load.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/options.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/options.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/options.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/options.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/package.json create mode 100644 frontend/node_modules/cheerio/dist/commonjs/parse.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/parse.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/parse.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/parse.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/parsers/parse5-adapter.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/parsers/parse5-adapter.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/parsers/parse5-adapter.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/parsers/parse5-adapter.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/slim.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/slim.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/slim.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/slim.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/static.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/static.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/static.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/static.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/types.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/types.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/types.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/types.js.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/utils.d.ts create mode 100644 frontend/node_modules/cheerio/dist/commonjs/utils.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/commonjs/utils.js create mode 100644 frontend/node_modules/cheerio/dist/commonjs/utils.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/api/attributes.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/api/attributes.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/api/attributes.js create mode 100644 frontend/node_modules/cheerio/dist/esm/api/attributes.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/api/css.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/api/css.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/api/css.js create mode 100644 frontend/node_modules/cheerio/dist/esm/api/css.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/api/extract.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/api/extract.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/api/extract.js create mode 100644 frontend/node_modules/cheerio/dist/esm/api/extract.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/api/forms.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/api/forms.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/api/forms.js create mode 100644 frontend/node_modules/cheerio/dist/esm/api/forms.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/api/manipulation.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/api/manipulation.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/api/manipulation.js create mode 100644 frontend/node_modules/cheerio/dist/esm/api/manipulation.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/api/traversing.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/api/traversing.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/api/traversing.js create mode 100644 frontend/node_modules/cheerio/dist/esm/api/traversing.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/cheerio.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/cheerio.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/cheerio.js create mode 100644 frontend/node_modules/cheerio/dist/esm/cheerio.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/index.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/index.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/index.js create mode 100644 frontend/node_modules/cheerio/dist/esm/index.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/load-parse.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/load-parse.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/load-parse.js create mode 100644 frontend/node_modules/cheerio/dist/esm/load-parse.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/load.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/load.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/load.js create mode 100644 frontend/node_modules/cheerio/dist/esm/load.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/options.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/options.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/options.js create mode 100644 frontend/node_modules/cheerio/dist/esm/options.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/package.json create mode 100644 frontend/node_modules/cheerio/dist/esm/parse.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/parse.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/parse.js create mode 100644 frontend/node_modules/cheerio/dist/esm/parse.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/parsers/parse5-adapter.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/parsers/parse5-adapter.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/parsers/parse5-adapter.js create mode 100644 frontend/node_modules/cheerio/dist/esm/parsers/parse5-adapter.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/slim.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/slim.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/slim.js create mode 100644 frontend/node_modules/cheerio/dist/esm/slim.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/static.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/static.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/static.js create mode 100644 frontend/node_modules/cheerio/dist/esm/static.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/types.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/types.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/types.js create mode 100644 frontend/node_modules/cheerio/dist/esm/types.js.map create mode 100644 frontend/node_modules/cheerio/dist/esm/utils.d.ts create mode 100644 frontend/node_modules/cheerio/dist/esm/utils.d.ts.map create mode 100644 frontend/node_modules/cheerio/dist/esm/utils.js create mode 100644 frontend/node_modules/cheerio/dist/esm/utils.js.map create mode 100644 frontend/node_modules/cheerio/package.json create mode 100644 frontend/node_modules/cheerio/src/__fixtures__/fixtures.ts create mode 100644 frontend/node_modules/cheerio/src/__tests__/deprecated.spec.ts create mode 100644 frontend/node_modules/cheerio/src/__tests__/xml.spec.ts create mode 100644 frontend/node_modules/cheerio/src/api/attributes.spec.ts create mode 100644 frontend/node_modules/cheerio/src/api/attributes.ts create mode 100644 frontend/node_modules/cheerio/src/api/css.spec.ts create mode 100644 frontend/node_modules/cheerio/src/api/css.ts create mode 100644 frontend/node_modules/cheerio/src/api/extract.spec.ts create mode 100644 frontend/node_modules/cheerio/src/api/extract.ts create mode 100644 frontend/node_modules/cheerio/src/api/forms.spec.ts create mode 100644 frontend/node_modules/cheerio/src/api/forms.ts create mode 100644 frontend/node_modules/cheerio/src/api/manipulation.spec.ts create mode 100644 frontend/node_modules/cheerio/src/api/manipulation.ts create mode 100644 frontend/node_modules/cheerio/src/api/traversing.spec.ts create mode 100644 frontend/node_modules/cheerio/src/api/traversing.ts create mode 100644 frontend/node_modules/cheerio/src/cheerio.spec.ts create mode 100644 frontend/node_modules/cheerio/src/cheerio.ts create mode 100644 frontend/node_modules/cheerio/src/index-browser.mts create mode 100644 frontend/node_modules/cheerio/src/index.spec.ts create mode 100644 frontend/node_modules/cheerio/src/index.ts create mode 100644 frontend/node_modules/cheerio/src/load-parse.ts create mode 100644 frontend/node_modules/cheerio/src/load.spec.ts create mode 100644 frontend/node_modules/cheerio/src/load.ts create mode 100644 frontend/node_modules/cheerio/src/options.ts create mode 100644 frontend/node_modules/cheerio/src/parse.spec.ts create mode 100644 frontend/node_modules/cheerio/src/parse.ts create mode 100644 frontend/node_modules/cheerio/src/parsers/parse5-adapter.ts create mode 100644 frontend/node_modules/cheerio/src/slim.ts create mode 100644 frontend/node_modules/cheerio/src/static.spec.ts create mode 100644 frontend/node_modules/cheerio/src/static.ts create mode 100644 frontend/node_modules/cheerio/src/types.ts create mode 100644 frontend/node_modules/cheerio/src/utils.spec.ts create mode 100644 frontend/node_modules/cheerio/src/utils.ts create mode 100644 frontend/node_modules/commander/LICENSE create mode 100644 frontend/node_modules/commander/Readme.md create mode 100644 frontend/node_modules/commander/esm.mjs create mode 100644 frontend/node_modules/commander/index.js create mode 100644 frontend/node_modules/commander/lib/argument.js create mode 100644 frontend/node_modules/commander/lib/command.js create mode 100644 frontend/node_modules/commander/lib/error.js create mode 100644 frontend/node_modules/commander/lib/help.js create mode 100644 frontend/node_modules/commander/lib/option.js create mode 100644 frontend/node_modules/commander/lib/suggestSimilar.js create mode 100644 frontend/node_modules/commander/package-support.json create mode 100644 frontend/node_modules/commander/package.json create mode 100644 frontend/node_modules/commander/typings/index.d.ts create mode 100644 frontend/node_modules/css-select/LICENSE create mode 100644 frontend/node_modules/css-select/README.md create mode 100644 frontend/node_modules/css-select/lib/attributes.d.ts create mode 100644 frontend/node_modules/css-select/lib/attributes.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/attributes.js create mode 100644 frontend/node_modules/css-select/lib/attributes.js.map create mode 100644 frontend/node_modules/css-select/lib/compile.d.ts create mode 100644 frontend/node_modules/css-select/lib/compile.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/compile.js create mode 100644 frontend/node_modules/css-select/lib/compile.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/attributes.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/attributes.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/attributes.js create mode 100644 frontend/node_modules/css-select/lib/esm/attributes.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/compile.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/compile.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/compile.js create mode 100644 frontend/node_modules/css-select/lib/esm/compile.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/general.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/general.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/general.js create mode 100644 frontend/node_modules/css-select/lib/esm/general.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/helpers/cache.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/helpers/cache.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/helpers/cache.js create mode 100644 frontend/node_modules/css-select/lib/esm/helpers/cache.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/helpers/querying.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/helpers/querying.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/helpers/querying.js create mode 100644 frontend/node_modules/css-select/lib/esm/helpers/querying.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/helpers/selectors.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/helpers/selectors.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/helpers/selectors.js create mode 100644 frontend/node_modules/css-select/lib/esm/helpers/selectors.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/index.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/index.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/index.js create mode 100644 frontend/node_modules/css-select/lib/esm/index.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/package.json create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/aliases.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/aliases.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/aliases.js create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/aliases.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/filters.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/filters.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/filters.js create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/filters.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/index.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/index.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/index.js create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/index.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/pseudos.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/pseudos.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/pseudos.js create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/pseudos.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/subselects.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/subselects.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/subselects.js create mode 100644 frontend/node_modules/css-select/lib/esm/pseudo-selectors/subselects.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/sort.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/sort.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/sort.js create mode 100644 frontend/node_modules/css-select/lib/esm/sort.js.map create mode 100644 frontend/node_modules/css-select/lib/esm/types.d.ts create mode 100644 frontend/node_modules/css-select/lib/esm/types.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/esm/types.js create mode 100644 frontend/node_modules/css-select/lib/esm/types.js.map create mode 100644 frontend/node_modules/css-select/lib/general.d.ts create mode 100644 frontend/node_modules/css-select/lib/general.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/general.js create mode 100644 frontend/node_modules/css-select/lib/general.js.map create mode 100644 frontend/node_modules/css-select/lib/helpers/cache.d.ts create mode 100644 frontend/node_modules/css-select/lib/helpers/cache.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/helpers/cache.js create mode 100644 frontend/node_modules/css-select/lib/helpers/cache.js.map create mode 100644 frontend/node_modules/css-select/lib/helpers/querying.d.ts create mode 100644 frontend/node_modules/css-select/lib/helpers/querying.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/helpers/querying.js create mode 100644 frontend/node_modules/css-select/lib/helpers/querying.js.map create mode 100644 frontend/node_modules/css-select/lib/helpers/selectors.d.ts create mode 100644 frontend/node_modules/css-select/lib/helpers/selectors.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/helpers/selectors.js create mode 100644 frontend/node_modules/css-select/lib/helpers/selectors.js.map create mode 100644 frontend/node_modules/css-select/lib/index.d.ts create mode 100644 frontend/node_modules/css-select/lib/index.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/index.js create mode 100644 frontend/node_modules/css-select/lib/index.js.map create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/aliases.d.ts create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/aliases.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/aliases.js create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/aliases.js.map create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/filters.d.ts create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/filters.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/filters.js create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/filters.js.map create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/index.d.ts create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/index.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/index.js create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/index.js.map create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/pseudos.d.ts create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/pseudos.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/pseudos.js create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/pseudos.js.map create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/subselects.d.ts create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/subselects.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/subselects.js create mode 100644 frontend/node_modules/css-select/lib/pseudo-selectors/subselects.js.map create mode 100644 frontend/node_modules/css-select/lib/sort.d.ts create mode 100644 frontend/node_modules/css-select/lib/sort.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/sort.js create mode 100644 frontend/node_modules/css-select/lib/sort.js.map create mode 100644 frontend/node_modules/css-select/lib/types.d.ts create mode 100644 frontend/node_modules/css-select/lib/types.d.ts.map create mode 100644 frontend/node_modules/css-select/lib/types.js create mode 100644 frontend/node_modules/css-select/lib/types.js.map create mode 100644 frontend/node_modules/css-select/package.json create mode 100644 frontend/node_modules/css-what/LICENSE create mode 100644 frontend/node_modules/css-what/lib/commonjs/index.d.ts create mode 100644 frontend/node_modules/css-what/lib/commonjs/index.d.ts.map create mode 100644 frontend/node_modules/css-what/lib/commonjs/index.js create mode 100644 frontend/node_modules/css-what/lib/commonjs/parse.d.ts create mode 100644 frontend/node_modules/css-what/lib/commonjs/parse.d.ts.map create mode 100644 frontend/node_modules/css-what/lib/commonjs/parse.js create mode 100644 frontend/node_modules/css-what/lib/commonjs/stringify.d.ts create mode 100644 frontend/node_modules/css-what/lib/commonjs/stringify.d.ts.map create mode 100644 frontend/node_modules/css-what/lib/commonjs/stringify.js create mode 100644 frontend/node_modules/css-what/lib/commonjs/types.d.ts create mode 100644 frontend/node_modules/css-what/lib/commonjs/types.d.ts.map create mode 100644 frontend/node_modules/css-what/lib/commonjs/types.js create mode 100644 frontend/node_modules/css-what/lib/es/index.d.ts create mode 100644 frontend/node_modules/css-what/lib/es/index.d.ts.map create mode 100644 frontend/node_modules/css-what/lib/es/index.js create mode 100644 frontend/node_modules/css-what/lib/es/parse.d.ts create mode 100644 frontend/node_modules/css-what/lib/es/parse.d.ts.map create mode 100644 frontend/node_modules/css-what/lib/es/parse.js create mode 100644 frontend/node_modules/css-what/lib/es/stringify.d.ts create mode 100644 frontend/node_modules/css-what/lib/es/stringify.d.ts.map create mode 100644 frontend/node_modules/css-what/lib/es/stringify.js create mode 100644 frontend/node_modules/css-what/lib/es/types.d.ts create mode 100644 frontend/node_modules/css-what/lib/es/types.d.ts.map create mode 100644 frontend/node_modules/css-what/lib/es/types.js create mode 100644 frontend/node_modules/css-what/package.json create mode 100644 frontend/node_modules/css-what/readme.md create mode 100644 frontend/node_modules/d3-array/LICENSE create mode 100644 frontend/node_modules/d3-array/README.md create mode 100644 frontend/node_modules/d3-array/dist/d3-array.js create mode 100644 frontend/node_modules/d3-array/dist/d3-array.min.js create mode 100644 frontend/node_modules/d3-array/package.json create mode 100644 frontend/node_modules/d3-array/src/array.js create mode 100644 frontend/node_modules/d3-array/src/ascending.js create mode 100644 frontend/node_modules/d3-array/src/bin.js create mode 100644 frontend/node_modules/d3-array/src/bisect.js create mode 100644 frontend/node_modules/d3-array/src/bisector.js create mode 100644 frontend/node_modules/d3-array/src/blur.js create mode 100644 frontend/node_modules/d3-array/src/constant.js create mode 100644 frontend/node_modules/d3-array/src/count.js create mode 100644 frontend/node_modules/d3-array/src/cross.js create mode 100644 frontend/node_modules/d3-array/src/cumsum.js create mode 100644 frontend/node_modules/d3-array/src/descending.js create mode 100644 frontend/node_modules/d3-array/src/deviation.js create mode 100644 frontend/node_modules/d3-array/src/difference.js create mode 100644 frontend/node_modules/d3-array/src/disjoint.js create mode 100644 frontend/node_modules/d3-array/src/every.js create mode 100644 frontend/node_modules/d3-array/src/extent.js create mode 100644 frontend/node_modules/d3-array/src/filter.js create mode 100644 frontend/node_modules/d3-array/src/fsum.js create mode 100644 frontend/node_modules/d3-array/src/greatest.js create mode 100644 frontend/node_modules/d3-array/src/greatestIndex.js create mode 100644 frontend/node_modules/d3-array/src/group.js create mode 100644 frontend/node_modules/d3-array/src/groupSort.js create mode 100644 frontend/node_modules/d3-array/src/identity.js create mode 100644 frontend/node_modules/d3-array/src/index.js create mode 100644 frontend/node_modules/d3-array/src/intersection.js create mode 100644 frontend/node_modules/d3-array/src/least.js create mode 100644 frontend/node_modules/d3-array/src/leastIndex.js create mode 100644 frontend/node_modules/d3-array/src/map.js create mode 100644 frontend/node_modules/d3-array/src/max.js create mode 100644 frontend/node_modules/d3-array/src/maxIndex.js create mode 100644 frontend/node_modules/d3-array/src/mean.js create mode 100644 frontend/node_modules/d3-array/src/median.js create mode 100644 frontend/node_modules/d3-array/src/merge.js create mode 100644 frontend/node_modules/d3-array/src/min.js create mode 100644 frontend/node_modules/d3-array/src/minIndex.js create mode 100644 frontend/node_modules/d3-array/src/mode.js create mode 100644 frontend/node_modules/d3-array/src/nice.js create mode 100644 frontend/node_modules/d3-array/src/number.js create mode 100644 frontend/node_modules/d3-array/src/pairs.js create mode 100644 frontend/node_modules/d3-array/src/permute.js create mode 100644 frontend/node_modules/d3-array/src/quantile.js create mode 100644 frontend/node_modules/d3-array/src/quickselect.js create mode 100644 frontend/node_modules/d3-array/src/range.js create mode 100644 frontend/node_modules/d3-array/src/rank.js create mode 100644 frontend/node_modules/d3-array/src/reduce.js create mode 100644 frontend/node_modules/d3-array/src/reverse.js create mode 100644 frontend/node_modules/d3-array/src/scan.js create mode 100644 frontend/node_modules/d3-array/src/shuffle.js create mode 100644 frontend/node_modules/d3-array/src/some.js create mode 100644 frontend/node_modules/d3-array/src/sort.js create mode 100644 frontend/node_modules/d3-array/src/subset.js create mode 100644 frontend/node_modules/d3-array/src/sum.js create mode 100644 frontend/node_modules/d3-array/src/superset.js create mode 100644 frontend/node_modules/d3-array/src/threshold/freedmanDiaconis.js create mode 100644 frontend/node_modules/d3-array/src/threshold/scott.js create mode 100644 frontend/node_modules/d3-array/src/threshold/sturges.js create mode 100644 frontend/node_modules/d3-array/src/ticks.js create mode 100644 frontend/node_modules/d3-array/src/transpose.js create mode 100644 frontend/node_modules/d3-array/src/union.js create mode 100644 frontend/node_modules/d3-array/src/variance.js create mode 100644 frontend/node_modules/d3-array/src/zip.js create mode 100644 frontend/node_modules/d3-axis/LICENSE create mode 100644 frontend/node_modules/d3-axis/README.md create mode 100644 frontend/node_modules/d3-axis/dist/d3-axis.js create mode 100644 frontend/node_modules/d3-axis/dist/d3-axis.min.js create mode 100644 frontend/node_modules/d3-axis/package.json create mode 100644 frontend/node_modules/d3-axis/src/axis.js create mode 100644 frontend/node_modules/d3-axis/src/identity.js create mode 100644 frontend/node_modules/d3-axis/src/index.js create mode 100644 frontend/node_modules/d3-brush/LICENSE create mode 100644 frontend/node_modules/d3-brush/README.md create mode 100644 frontend/node_modules/d3-brush/dist/d3-brush.js create mode 100644 frontend/node_modules/d3-brush/dist/d3-brush.min.js create mode 100644 frontend/node_modules/d3-brush/package.json create mode 100644 frontend/node_modules/d3-brush/src/brush.js create mode 100644 frontend/node_modules/d3-brush/src/constant.js create mode 100644 frontend/node_modules/d3-brush/src/event.js create mode 100644 frontend/node_modules/d3-brush/src/index.js create mode 100644 frontend/node_modules/d3-brush/src/noevent.js create mode 100644 frontend/node_modules/d3-chord/LICENSE create mode 100644 frontend/node_modules/d3-chord/README.md create mode 100644 frontend/node_modules/d3-chord/dist/d3-chord.js create mode 100644 frontend/node_modules/d3-chord/dist/d3-chord.min.js create mode 100644 frontend/node_modules/d3-chord/package.json create mode 100644 frontend/node_modules/d3-chord/src/array.js create mode 100644 frontend/node_modules/d3-chord/src/chord.js create mode 100644 frontend/node_modules/d3-chord/src/constant.js create mode 100644 frontend/node_modules/d3-chord/src/index.js create mode 100644 frontend/node_modules/d3-chord/src/math.js create mode 100644 frontend/node_modules/d3-chord/src/ribbon.js create mode 100644 frontend/node_modules/d3-color/LICENSE create mode 100644 frontend/node_modules/d3-color/README.md create mode 100644 frontend/node_modules/d3-color/dist/d3-color.js create mode 100644 frontend/node_modules/d3-color/dist/d3-color.min.js create mode 100644 frontend/node_modules/d3-color/package.json create mode 100644 frontend/node_modules/d3-color/src/color.js create mode 100644 frontend/node_modules/d3-color/src/cubehelix.js create mode 100644 frontend/node_modules/d3-color/src/define.js create mode 100644 frontend/node_modules/d3-color/src/index.js create mode 100644 frontend/node_modules/d3-color/src/lab.js create mode 100644 frontend/node_modules/d3-color/src/math.js create mode 100644 frontend/node_modules/d3-contour/LICENSE create mode 100644 frontend/node_modules/d3-contour/README.md create mode 100644 frontend/node_modules/d3-contour/dist/d3-contour.js create mode 100644 frontend/node_modules/d3-contour/dist/d3-contour.min.js create mode 100644 frontend/node_modules/d3-contour/package.json create mode 100644 frontend/node_modules/d3-contour/src/area.js create mode 100644 frontend/node_modules/d3-contour/src/array.js create mode 100644 frontend/node_modules/d3-contour/src/ascending.js create mode 100644 frontend/node_modules/d3-contour/src/constant.js create mode 100644 frontend/node_modules/d3-contour/src/contains.js create mode 100644 frontend/node_modules/d3-contour/src/contours.js create mode 100644 frontend/node_modules/d3-contour/src/density.js create mode 100644 frontend/node_modules/d3-contour/src/index.js create mode 100644 frontend/node_modules/d3-contour/src/noop.js create mode 100644 frontend/node_modules/d3-delaunay/LICENSE create mode 100644 frontend/node_modules/d3-delaunay/README.md create mode 100644 frontend/node_modules/d3-delaunay/dist/d3-delaunay.js create mode 100644 frontend/node_modules/d3-delaunay/dist/d3-delaunay.min.js create mode 100644 frontend/node_modules/d3-delaunay/package.json create mode 100644 frontend/node_modules/d3-delaunay/src/delaunay.js create mode 100644 frontend/node_modules/d3-delaunay/src/index.js create mode 100644 frontend/node_modules/d3-delaunay/src/path.js create mode 100644 frontend/node_modules/d3-delaunay/src/polygon.js create mode 100644 frontend/node_modules/d3-delaunay/src/voronoi.js create mode 100644 frontend/node_modules/d3-dispatch/LICENSE create mode 100644 frontend/node_modules/d3-dispatch/README.md create mode 100644 frontend/node_modules/d3-dispatch/dist/d3-dispatch.js create mode 100644 frontend/node_modules/d3-dispatch/dist/d3-dispatch.min.js create mode 100644 frontend/node_modules/d3-dispatch/package.json create mode 100644 frontend/node_modules/d3-dispatch/src/dispatch.js create mode 100644 frontend/node_modules/d3-dispatch/src/index.js create mode 100644 frontend/node_modules/d3-drag/LICENSE create mode 100644 frontend/node_modules/d3-drag/README.md create mode 100644 frontend/node_modules/d3-drag/dist/d3-drag.js create mode 100644 frontend/node_modules/d3-drag/dist/d3-drag.min.js create mode 100644 frontend/node_modules/d3-drag/package.json create mode 100644 frontend/node_modules/d3-drag/src/constant.js create mode 100644 frontend/node_modules/d3-drag/src/drag.js create mode 100644 frontend/node_modules/d3-drag/src/event.js create mode 100644 frontend/node_modules/d3-drag/src/index.js create mode 100644 frontend/node_modules/d3-drag/src/nodrag.js create mode 100644 frontend/node_modules/d3-drag/src/noevent.js create mode 100644 frontend/node_modules/d3-dsv/LICENSE create mode 100644 frontend/node_modules/d3-dsv/README.md create mode 100755 frontend/node_modules/d3-dsv/bin/dsv2dsv.js create mode 100755 frontend/node_modules/d3-dsv/bin/dsv2json.js create mode 100755 frontend/node_modules/d3-dsv/bin/json2dsv.js create mode 100644 frontend/node_modules/d3-dsv/dist/d3-dsv.js create mode 100644 frontend/node_modules/d3-dsv/dist/d3-dsv.min.js create mode 100644 frontend/node_modules/d3-dsv/node_modules/commander/CHANGELOG.md create mode 100644 frontend/node_modules/d3-dsv/node_modules/commander/LICENSE create mode 100644 frontend/node_modules/d3-dsv/node_modules/commander/Readme.md create mode 100644 frontend/node_modules/d3-dsv/node_modules/commander/esm.mjs create mode 100644 frontend/node_modules/d3-dsv/node_modules/commander/index.js create mode 100644 frontend/node_modules/d3-dsv/node_modules/commander/package-support.json create mode 100644 frontend/node_modules/d3-dsv/node_modules/commander/package.json create mode 100644 frontend/node_modules/d3-dsv/node_modules/commander/typings/index.d.ts create mode 100644 frontend/node_modules/d3-dsv/package.json create mode 100644 frontend/node_modules/d3-dsv/src/autoType.js create mode 100644 frontend/node_modules/d3-dsv/src/csv.js create mode 100644 frontend/node_modules/d3-dsv/src/dsv.js create mode 100644 frontend/node_modules/d3-dsv/src/index.js create mode 100644 frontend/node_modules/d3-dsv/src/tsv.js create mode 100644 frontend/node_modules/d3-ease/LICENSE create mode 100644 frontend/node_modules/d3-ease/README.md create mode 100644 frontend/node_modules/d3-ease/dist/d3-ease.js create mode 100644 frontend/node_modules/d3-ease/dist/d3-ease.min.js create mode 100644 frontend/node_modules/d3-ease/package.json create mode 100644 frontend/node_modules/d3-ease/src/back.js create mode 100644 frontend/node_modules/d3-ease/src/bounce.js create mode 100644 frontend/node_modules/d3-ease/src/circle.js create mode 100644 frontend/node_modules/d3-ease/src/cubic.js create mode 100644 frontend/node_modules/d3-ease/src/elastic.js create mode 100644 frontend/node_modules/d3-ease/src/exp.js create mode 100644 frontend/node_modules/d3-ease/src/index.js create mode 100644 frontend/node_modules/d3-ease/src/linear.js create mode 100644 frontend/node_modules/d3-ease/src/math.js create mode 100644 frontend/node_modules/d3-ease/src/poly.js create mode 100644 frontend/node_modules/d3-ease/src/quad.js create mode 100644 frontend/node_modules/d3-ease/src/sin.js create mode 100644 frontend/node_modules/d3-fetch/LICENSE create mode 100644 frontend/node_modules/d3-fetch/README.md create mode 100644 frontend/node_modules/d3-fetch/dist/d3-fetch.js create mode 100644 frontend/node_modules/d3-fetch/dist/d3-fetch.min.js create mode 100644 frontend/node_modules/d3-fetch/package.json create mode 100644 frontend/node_modules/d3-fetch/src/blob.js create mode 100644 frontend/node_modules/d3-fetch/src/buffer.js create mode 100644 frontend/node_modules/d3-fetch/src/dsv.js create mode 100644 frontend/node_modules/d3-fetch/src/image.js create mode 100644 frontend/node_modules/d3-fetch/src/index.js create mode 100644 frontend/node_modules/d3-fetch/src/json.js create mode 100644 frontend/node_modules/d3-fetch/src/text.js create mode 100644 frontend/node_modules/d3-fetch/src/xml.js create mode 100644 frontend/node_modules/d3-force/LICENSE create mode 100644 frontend/node_modules/d3-force/README.md create mode 100644 frontend/node_modules/d3-force/dist/d3-force.js create mode 100644 frontend/node_modules/d3-force/dist/d3-force.min.js create mode 100644 frontend/node_modules/d3-force/package.json create mode 100644 frontend/node_modules/d3-force/src/center.js create mode 100644 frontend/node_modules/d3-force/src/collide.js create mode 100644 frontend/node_modules/d3-force/src/constant.js create mode 100644 frontend/node_modules/d3-force/src/index.js create mode 100644 frontend/node_modules/d3-force/src/jiggle.js create mode 100644 frontend/node_modules/d3-force/src/lcg.js create mode 100644 frontend/node_modules/d3-force/src/link.js create mode 100644 frontend/node_modules/d3-force/src/manyBody.js create mode 100644 frontend/node_modules/d3-force/src/radial.js create mode 100644 frontend/node_modules/d3-force/src/simulation.js create mode 100644 frontend/node_modules/d3-force/src/x.js create mode 100644 frontend/node_modules/d3-force/src/y.js create mode 100644 frontend/node_modules/d3-format/LICENSE create mode 100644 frontend/node_modules/d3-format/README.md create mode 100644 frontend/node_modules/d3-format/dist/d3-format.js create mode 100644 frontend/node_modules/d3-format/dist/d3-format.min.js create mode 100644 frontend/node_modules/d3-format/locale/ar-001.json create mode 100644 frontend/node_modules/d3-format/locale/ar-AE.json create mode 100644 frontend/node_modules/d3-format/locale/ar-BH.json create mode 100644 frontend/node_modules/d3-format/locale/ar-DJ.json create mode 100644 frontend/node_modules/d3-format/locale/ar-DZ.json create mode 100644 frontend/node_modules/d3-format/locale/ar-EG.json create mode 100644 frontend/node_modules/d3-format/locale/ar-EH.json create mode 100644 frontend/node_modules/d3-format/locale/ar-ER.json create mode 100644 frontend/node_modules/d3-format/locale/ar-IL.json create mode 100644 frontend/node_modules/d3-format/locale/ar-IQ.json create mode 100644 frontend/node_modules/d3-format/locale/ar-JO.json create mode 100644 frontend/node_modules/d3-format/locale/ar-KM.json create mode 100644 frontend/node_modules/d3-format/locale/ar-KW.json create mode 100644 frontend/node_modules/d3-format/locale/ar-LB.json create mode 100644 frontend/node_modules/d3-format/locale/ar-LY.json create mode 100644 frontend/node_modules/d3-format/locale/ar-MA.json create mode 100644 frontend/node_modules/d3-format/locale/ar-MR.json create mode 100644 frontend/node_modules/d3-format/locale/ar-OM.json create mode 100644 frontend/node_modules/d3-format/locale/ar-PS.json create mode 100644 frontend/node_modules/d3-format/locale/ar-QA.json create mode 100644 frontend/node_modules/d3-format/locale/ar-SA.json create mode 100644 frontend/node_modules/d3-format/locale/ar-SD.json create mode 100644 frontend/node_modules/d3-format/locale/ar-SO.json create mode 100644 frontend/node_modules/d3-format/locale/ar-SS.json create mode 100644 frontend/node_modules/d3-format/locale/ar-SY.json create mode 100644 frontend/node_modules/d3-format/locale/ar-TD.json create mode 100644 frontend/node_modules/d3-format/locale/ar-TN.json create mode 100644 frontend/node_modules/d3-format/locale/ar-YE.json create mode 100644 frontend/node_modules/d3-format/locale/ca-ES.json create mode 100644 frontend/node_modules/d3-format/locale/cs-CZ.json create mode 100644 frontend/node_modules/d3-format/locale/da-DK.json create mode 100644 frontend/node_modules/d3-format/locale/de-CH.json create mode 100644 frontend/node_modules/d3-format/locale/de-DE.json create mode 100644 frontend/node_modules/d3-format/locale/en-CA.json create mode 100644 frontend/node_modules/d3-format/locale/en-GB.json create mode 100644 frontend/node_modules/d3-format/locale/en-IE.json create mode 100644 frontend/node_modules/d3-format/locale/en-IN.json create mode 100644 frontend/node_modules/d3-format/locale/en-US.json create mode 100644 frontend/node_modules/d3-format/locale/es-BO.json create mode 100644 frontend/node_modules/d3-format/locale/es-ES.json create mode 100644 frontend/node_modules/d3-format/locale/es-MX.json create mode 100644 frontend/node_modules/d3-format/locale/fi-FI.json create mode 100644 frontend/node_modules/d3-format/locale/fr-CA.json create mode 100644 frontend/node_modules/d3-format/locale/fr-FR.json create mode 100644 frontend/node_modules/d3-format/locale/he-IL.json create mode 100644 frontend/node_modules/d3-format/locale/hu-HU.json create mode 100644 frontend/node_modules/d3-format/locale/it-IT.json create mode 100644 frontend/node_modules/d3-format/locale/ja-JP.json create mode 100644 frontend/node_modules/d3-format/locale/ko-KR.json create mode 100644 frontend/node_modules/d3-format/locale/mk-MK.json create mode 100644 frontend/node_modules/d3-format/locale/nl-NL.json create mode 100644 frontend/node_modules/d3-format/locale/pl-PL.json create mode 100644 frontend/node_modules/d3-format/locale/pt-BR.json create mode 100644 frontend/node_modules/d3-format/locale/pt-PT.json create mode 100644 frontend/node_modules/d3-format/locale/ru-RU.json create mode 100644 frontend/node_modules/d3-format/locale/sl-SI.json create mode 100644 frontend/node_modules/d3-format/locale/sv-SE.json create mode 100644 frontend/node_modules/d3-format/locale/uk-UA.json create mode 100644 frontend/node_modules/d3-format/locale/zh-CN.json create mode 100644 frontend/node_modules/d3-format/package.json create mode 100644 frontend/node_modules/d3-format/src/defaultLocale.js create mode 100644 frontend/node_modules/d3-format/src/exponent.js create mode 100644 frontend/node_modules/d3-format/src/formatDecimal.js create mode 100644 frontend/node_modules/d3-format/src/formatGroup.js create mode 100644 frontend/node_modules/d3-format/src/formatNumerals.js create mode 100644 frontend/node_modules/d3-format/src/formatPrefixAuto.js create mode 100644 frontend/node_modules/d3-format/src/formatRounded.js create mode 100644 frontend/node_modules/d3-format/src/formatSpecifier.js create mode 100644 frontend/node_modules/d3-format/src/formatTrim.js create mode 100644 frontend/node_modules/d3-format/src/formatTypes.js create mode 100644 frontend/node_modules/d3-format/src/identity.js create mode 100644 frontend/node_modules/d3-format/src/index.js create mode 100644 frontend/node_modules/d3-format/src/locale.js create mode 100644 frontend/node_modules/d3-format/src/precisionFixed.js create mode 100644 frontend/node_modules/d3-format/src/precisionPrefix.js create mode 100644 frontend/node_modules/d3-format/src/precisionRound.js create mode 100644 frontend/node_modules/d3-geo/LICENSE create mode 100644 frontend/node_modules/d3-geo/README.md create mode 100644 frontend/node_modules/d3-geo/dist/d3-geo.js create mode 100644 frontend/node_modules/d3-geo/dist/d3-geo.min.js create mode 100644 frontend/node_modules/d3-geo/package.json create mode 100644 frontend/node_modules/d3-geo/src/area.js create mode 100644 frontend/node_modules/d3-geo/src/bounds.js create mode 100644 frontend/node_modules/d3-geo/src/cartesian.js create mode 100644 frontend/node_modules/d3-geo/src/centroid.js create mode 100644 frontend/node_modules/d3-geo/src/circle.js create mode 100644 frontend/node_modules/d3-geo/src/clip/antimeridian.js create mode 100644 frontend/node_modules/d3-geo/src/clip/buffer.js create mode 100644 frontend/node_modules/d3-geo/src/clip/circle.js create mode 100644 frontend/node_modules/d3-geo/src/clip/extent.js create mode 100644 frontend/node_modules/d3-geo/src/clip/index.js create mode 100644 frontend/node_modules/d3-geo/src/clip/line.js create mode 100644 frontend/node_modules/d3-geo/src/clip/rectangle.js create mode 100644 frontend/node_modules/d3-geo/src/clip/rejoin.js create mode 100644 frontend/node_modules/d3-geo/src/compose.js create mode 100644 frontend/node_modules/d3-geo/src/constant.js create mode 100644 frontend/node_modules/d3-geo/src/contains.js create mode 100644 frontend/node_modules/d3-geo/src/distance.js create mode 100644 frontend/node_modules/d3-geo/src/graticule.js create mode 100644 frontend/node_modules/d3-geo/src/identity.js create mode 100644 frontend/node_modules/d3-geo/src/index.js create mode 100644 frontend/node_modules/d3-geo/src/interpolate.js create mode 100644 frontend/node_modules/d3-geo/src/length.js create mode 100644 frontend/node_modules/d3-geo/src/math.js create mode 100644 frontend/node_modules/d3-geo/src/noop.js create mode 100644 frontend/node_modules/d3-geo/src/path/area.js create mode 100644 frontend/node_modules/d3-geo/src/path/bounds.js create mode 100644 frontend/node_modules/d3-geo/src/path/centroid.js create mode 100644 frontend/node_modules/d3-geo/src/path/context.js create mode 100644 frontend/node_modules/d3-geo/src/path/index.js create mode 100644 frontend/node_modules/d3-geo/src/path/measure.js create mode 100644 frontend/node_modules/d3-geo/src/path/string.js create mode 100644 frontend/node_modules/d3-geo/src/pointEqual.js create mode 100644 frontend/node_modules/d3-geo/src/polygonContains.js create mode 100644 frontend/node_modules/d3-geo/src/projection/albers.js create mode 100644 frontend/node_modules/d3-geo/src/projection/albersUsa.js create mode 100644 frontend/node_modules/d3-geo/src/projection/azimuthal.js create mode 100644 frontend/node_modules/d3-geo/src/projection/azimuthalEqualArea.js create mode 100644 frontend/node_modules/d3-geo/src/projection/azimuthalEquidistant.js create mode 100644 frontend/node_modules/d3-geo/src/projection/conic.js create mode 100644 frontend/node_modules/d3-geo/src/projection/conicConformal.js create mode 100644 frontend/node_modules/d3-geo/src/projection/conicEqualArea.js create mode 100644 frontend/node_modules/d3-geo/src/projection/conicEquidistant.js create mode 100644 frontend/node_modules/d3-geo/src/projection/cylindricalEqualArea.js create mode 100644 frontend/node_modules/d3-geo/src/projection/equalEarth.js create mode 100644 frontend/node_modules/d3-geo/src/projection/equirectangular.js create mode 100644 frontend/node_modules/d3-geo/src/projection/fit.js create mode 100644 frontend/node_modules/d3-geo/src/projection/gnomonic.js create mode 100644 frontend/node_modules/d3-geo/src/projection/identity.js create mode 100644 frontend/node_modules/d3-geo/src/projection/index.js create mode 100644 frontend/node_modules/d3-geo/src/projection/mercator.js create mode 100644 frontend/node_modules/d3-geo/src/projection/naturalEarth1.js create mode 100644 frontend/node_modules/d3-geo/src/projection/orthographic.js create mode 100644 frontend/node_modules/d3-geo/src/projection/resample.js create mode 100644 frontend/node_modules/d3-geo/src/projection/stereographic.js create mode 100644 frontend/node_modules/d3-geo/src/projection/transverseMercator.js create mode 100644 frontend/node_modules/d3-geo/src/rotation.js create mode 100644 frontend/node_modules/d3-geo/src/stream.js create mode 100644 frontend/node_modules/d3-geo/src/transform.js create mode 100644 frontend/node_modules/d3-hierarchy/LICENSE create mode 100644 frontend/node_modules/d3-hierarchy/README.md create mode 100644 frontend/node_modules/d3-hierarchy/dist/d3-hierarchy.js create mode 100644 frontend/node_modules/d3-hierarchy/dist/d3-hierarchy.min.js create mode 100644 frontend/node_modules/d3-hierarchy/package.json create mode 100644 frontend/node_modules/d3-hierarchy/src/accessors.js create mode 100644 frontend/node_modules/d3-hierarchy/src/array.js create mode 100644 frontend/node_modules/d3-hierarchy/src/cluster.js create mode 100644 frontend/node_modules/d3-hierarchy/src/constant.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/ancestors.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/count.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/descendants.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/each.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/eachAfter.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/eachBefore.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/find.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/index.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/iterator.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/leaves.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/links.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/path.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/sort.js create mode 100644 frontend/node_modules/d3-hierarchy/src/hierarchy/sum.js create mode 100644 frontend/node_modules/d3-hierarchy/src/index.js create mode 100644 frontend/node_modules/d3-hierarchy/src/lcg.js create mode 100644 frontend/node_modules/d3-hierarchy/src/pack/enclose.js create mode 100644 frontend/node_modules/d3-hierarchy/src/pack/index.js create mode 100644 frontend/node_modules/d3-hierarchy/src/pack/siblings.js create mode 100644 frontend/node_modules/d3-hierarchy/src/partition.js create mode 100644 frontend/node_modules/d3-hierarchy/src/stratify.js create mode 100644 frontend/node_modules/d3-hierarchy/src/tree.js create mode 100644 frontend/node_modules/d3-hierarchy/src/treemap/binary.js create mode 100644 frontend/node_modules/d3-hierarchy/src/treemap/dice.js create mode 100644 frontend/node_modules/d3-hierarchy/src/treemap/index.js create mode 100644 frontend/node_modules/d3-hierarchy/src/treemap/resquarify.js create mode 100644 frontend/node_modules/d3-hierarchy/src/treemap/round.js create mode 100644 frontend/node_modules/d3-hierarchy/src/treemap/slice.js create mode 100644 frontend/node_modules/d3-hierarchy/src/treemap/sliceDice.js create mode 100644 frontend/node_modules/d3-hierarchy/src/treemap/squarify.js create mode 100644 frontend/node_modules/d3-interpolate/LICENSE create mode 100644 frontend/node_modules/d3-interpolate/README.md create mode 100644 frontend/node_modules/d3-interpolate/dist/d3-interpolate.js create mode 100644 frontend/node_modules/d3-interpolate/dist/d3-interpolate.min.js create mode 100644 frontend/node_modules/d3-interpolate/package.json create mode 100644 frontend/node_modules/d3-interpolate/src/array.js create mode 100644 frontend/node_modules/d3-interpolate/src/basis.js create mode 100644 frontend/node_modules/d3-interpolate/src/basisClosed.js create mode 100644 frontend/node_modules/d3-interpolate/src/color.js create mode 100644 frontend/node_modules/d3-interpolate/src/constant.js create mode 100644 frontend/node_modules/d3-interpolate/src/cubehelix.js create mode 100644 frontend/node_modules/d3-interpolate/src/date.js create mode 100644 frontend/node_modules/d3-interpolate/src/discrete.js create mode 100644 frontend/node_modules/d3-interpolate/src/hcl.js create mode 100644 frontend/node_modules/d3-interpolate/src/hsl.js create mode 100644 frontend/node_modules/d3-interpolate/src/hue.js create mode 100644 frontend/node_modules/d3-interpolate/src/index.js create mode 100644 frontend/node_modules/d3-interpolate/src/lab.js create mode 100644 frontend/node_modules/d3-interpolate/src/number.js create mode 100644 frontend/node_modules/d3-interpolate/src/numberArray.js create mode 100644 frontend/node_modules/d3-interpolate/src/object.js create mode 100644 frontend/node_modules/d3-interpolate/src/piecewise.js create mode 100644 frontend/node_modules/d3-interpolate/src/quantize.js create mode 100644 frontend/node_modules/d3-interpolate/src/rgb.js create mode 100644 frontend/node_modules/d3-interpolate/src/round.js create mode 100644 frontend/node_modules/d3-interpolate/src/string.js create mode 100644 frontend/node_modules/d3-interpolate/src/transform/decompose.js create mode 100644 frontend/node_modules/d3-interpolate/src/transform/index.js create mode 100644 frontend/node_modules/d3-interpolate/src/transform/parse.js create mode 100644 frontend/node_modules/d3-interpolate/src/value.js create mode 100644 frontend/node_modules/d3-interpolate/src/zoom.js create mode 100644 frontend/node_modules/d3-path/LICENSE create mode 100644 frontend/node_modules/d3-path/README.md create mode 100644 frontend/node_modules/d3-path/dist/d3-path.js create mode 100644 frontend/node_modules/d3-path/dist/d3-path.min.js create mode 100644 frontend/node_modules/d3-path/package.json create mode 100644 frontend/node_modules/d3-path/src/index.js create mode 100644 frontend/node_modules/d3-path/src/path.js create mode 100644 frontend/node_modules/d3-polygon/LICENSE create mode 100644 frontend/node_modules/d3-polygon/README.md create mode 100644 frontend/node_modules/d3-polygon/dist/d3-polygon.js create mode 100644 frontend/node_modules/d3-polygon/dist/d3-polygon.min.js create mode 100644 frontend/node_modules/d3-polygon/package.json create mode 100644 frontend/node_modules/d3-polygon/src/area.js create mode 100644 frontend/node_modules/d3-polygon/src/centroid.js create mode 100644 frontend/node_modules/d3-polygon/src/contains.js create mode 100644 frontend/node_modules/d3-polygon/src/cross.js create mode 100644 frontend/node_modules/d3-polygon/src/hull.js create mode 100644 frontend/node_modules/d3-polygon/src/index.js create mode 100644 frontend/node_modules/d3-polygon/src/length.js create mode 100644 frontend/node_modules/d3-quadtree/LICENSE create mode 100644 frontend/node_modules/d3-quadtree/README.md create mode 100644 frontend/node_modules/d3-quadtree/dist/d3-quadtree.js create mode 100644 frontend/node_modules/d3-quadtree/dist/d3-quadtree.min.js create mode 100644 frontend/node_modules/d3-quadtree/package.json create mode 100644 frontend/node_modules/d3-quadtree/src/add.js create mode 100644 frontend/node_modules/d3-quadtree/src/cover.js create mode 100644 frontend/node_modules/d3-quadtree/src/data.js create mode 100644 frontend/node_modules/d3-quadtree/src/extent.js create mode 100644 frontend/node_modules/d3-quadtree/src/find.js create mode 100644 frontend/node_modules/d3-quadtree/src/index.js create mode 100644 frontend/node_modules/d3-quadtree/src/quad.js create mode 100644 frontend/node_modules/d3-quadtree/src/quadtree.js create mode 100644 frontend/node_modules/d3-quadtree/src/remove.js create mode 100644 frontend/node_modules/d3-quadtree/src/root.js create mode 100644 frontend/node_modules/d3-quadtree/src/size.js create mode 100644 frontend/node_modules/d3-quadtree/src/visit.js create mode 100644 frontend/node_modules/d3-quadtree/src/visitAfter.js create mode 100644 frontend/node_modules/d3-quadtree/src/x.js create mode 100644 frontend/node_modules/d3-quadtree/src/y.js create mode 100644 frontend/node_modules/d3-random/LICENSE create mode 100644 frontend/node_modules/d3-random/README.md create mode 100644 frontend/node_modules/d3-random/dist/d3-random.js create mode 100644 frontend/node_modules/d3-random/dist/d3-random.min.js create mode 100644 frontend/node_modules/d3-random/package.json create mode 100644 frontend/node_modules/d3-random/src/bates.js create mode 100644 frontend/node_modules/d3-random/src/bernoulli.js create mode 100644 frontend/node_modules/d3-random/src/beta.js create mode 100644 frontend/node_modules/d3-random/src/binomial.js create mode 100644 frontend/node_modules/d3-random/src/cauchy.js create mode 100644 frontend/node_modules/d3-random/src/defaultSource.js create mode 100644 frontend/node_modules/d3-random/src/exponential.js create mode 100644 frontend/node_modules/d3-random/src/gamma.js create mode 100644 frontend/node_modules/d3-random/src/geometric.js create mode 100644 frontend/node_modules/d3-random/src/index.js create mode 100644 frontend/node_modules/d3-random/src/int.js create mode 100644 frontend/node_modules/d3-random/src/irwinHall.js create mode 100644 frontend/node_modules/d3-random/src/lcg.js create mode 100644 frontend/node_modules/d3-random/src/logNormal.js create mode 100644 frontend/node_modules/d3-random/src/logistic.js create mode 100644 frontend/node_modules/d3-random/src/normal.js create mode 100644 frontend/node_modules/d3-random/src/pareto.js create mode 100644 frontend/node_modules/d3-random/src/poisson.js create mode 100644 frontend/node_modules/d3-random/src/uniform.js create mode 100644 frontend/node_modules/d3-random/src/weibull.js create mode 100644 frontend/node_modules/d3-scale-chromatic/LICENSE create mode 100644 frontend/node_modules/d3-scale-chromatic/README.md create mode 100644 frontend/node_modules/d3-scale-chromatic/dist/d3-scale-chromatic.js create mode 100644 frontend/node_modules/d3-scale-chromatic/dist/d3-scale-chromatic.min.js create mode 100644 frontend/node_modules/d3-scale-chromatic/package.json create mode 100644 frontend/node_modules/d3-scale-chromatic/src/categorical/Accent.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/categorical/Dark2.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/categorical/Paired.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/categorical/Pastel1.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/categorical/Pastel2.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/categorical/Set1.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/categorical/Set2.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/categorical/Set3.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/categorical/Tableau10.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/categorical/category10.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/categorical/observable10.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/colors.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/diverging/BrBG.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/diverging/PRGn.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/diverging/PiYG.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/diverging/PuOr.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/diverging/RdBu.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/diverging/RdGy.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/diverging/RdYlBu.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/diverging/RdYlGn.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/diverging/Spectral.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/index.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/ramp.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/rampClosed.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/BuGn.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/BuPu.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/GnBu.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/OrRd.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/PuBu.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/PuBuGn.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/PuRd.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/RdPu.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlGn.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlGnBu.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlOrBr.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlOrRd.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/cividis.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/cubehelix.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/rainbow.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/sinebow.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/turbo.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-multi/viridis.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-single/Blues.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-single/Greens.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-single/Greys.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-single/Oranges.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-single/Purples.js create mode 100644 frontend/node_modules/d3-scale-chromatic/src/sequential-single/Reds.js create mode 100644 frontend/node_modules/d3-scale/LICENSE create mode 100644 frontend/node_modules/d3-scale/README.md create mode 100644 frontend/node_modules/d3-scale/dist/d3-scale.js create mode 100644 frontend/node_modules/d3-scale/dist/d3-scale.min.js create mode 100644 frontend/node_modules/d3-scale/package.json create mode 100644 frontend/node_modules/d3-scale/src/band.js create mode 100644 frontend/node_modules/d3-scale/src/colors.js create mode 100644 frontend/node_modules/d3-scale/src/constant.js create mode 100644 frontend/node_modules/d3-scale/src/continuous.js create mode 100644 frontend/node_modules/d3-scale/src/diverging.js create mode 100644 frontend/node_modules/d3-scale/src/identity.js create mode 100644 frontend/node_modules/d3-scale/src/index.js create mode 100644 frontend/node_modules/d3-scale/src/init.js create mode 100644 frontend/node_modules/d3-scale/src/linear.js create mode 100644 frontend/node_modules/d3-scale/src/log.js create mode 100644 frontend/node_modules/d3-scale/src/nice.js create mode 100644 frontend/node_modules/d3-scale/src/number.js create mode 100644 frontend/node_modules/d3-scale/src/ordinal.js create mode 100644 frontend/node_modules/d3-scale/src/pow.js create mode 100644 frontend/node_modules/d3-scale/src/quantile.js create mode 100644 frontend/node_modules/d3-scale/src/quantize.js create mode 100644 frontend/node_modules/d3-scale/src/radial.js create mode 100644 frontend/node_modules/d3-scale/src/sequential.js create mode 100644 frontend/node_modules/d3-scale/src/sequentialQuantile.js create mode 100644 frontend/node_modules/d3-scale/src/symlog.js create mode 100644 frontend/node_modules/d3-scale/src/threshold.js create mode 100644 frontend/node_modules/d3-scale/src/tickFormat.js create mode 100644 frontend/node_modules/d3-scale/src/time.js create mode 100644 frontend/node_modules/d3-scale/src/utcTime.js create mode 100644 frontend/node_modules/d3-selection/LICENSE create mode 100644 frontend/node_modules/d3-selection/README.md create mode 100644 frontend/node_modules/d3-selection/dist/d3-selection.js create mode 100644 frontend/node_modules/d3-selection/dist/d3-selection.min.js create mode 100644 frontend/node_modules/d3-selection/package.json create mode 100644 frontend/node_modules/d3-selection/src/array.js create mode 100644 frontend/node_modules/d3-selection/src/constant.js create mode 100644 frontend/node_modules/d3-selection/src/create.js create mode 100644 frontend/node_modules/d3-selection/src/creator.js create mode 100644 frontend/node_modules/d3-selection/src/identity.js create mode 100644 frontend/node_modules/d3-selection/src/index.js create mode 100644 frontend/node_modules/d3-selection/src/local.js create mode 100644 frontend/node_modules/d3-selection/src/matcher.js create mode 100644 frontend/node_modules/d3-selection/src/namespace.js create mode 100644 frontend/node_modules/d3-selection/src/namespaces.js create mode 100644 frontend/node_modules/d3-selection/src/pointer.js create mode 100644 frontend/node_modules/d3-selection/src/pointers.js create mode 100644 frontend/node_modules/d3-selection/src/select.js create mode 100644 frontend/node_modules/d3-selection/src/selectAll.js create mode 100644 frontend/node_modules/d3-selection/src/selection/append.js create mode 100644 frontend/node_modules/d3-selection/src/selection/attr.js create mode 100644 frontend/node_modules/d3-selection/src/selection/call.js create mode 100644 frontend/node_modules/d3-selection/src/selection/classed.js create mode 100644 frontend/node_modules/d3-selection/src/selection/clone.js create mode 100644 frontend/node_modules/d3-selection/src/selection/data.js create mode 100644 frontend/node_modules/d3-selection/src/selection/datum.js create mode 100644 frontend/node_modules/d3-selection/src/selection/dispatch.js create mode 100644 frontend/node_modules/d3-selection/src/selection/each.js create mode 100644 frontend/node_modules/d3-selection/src/selection/empty.js create mode 100644 frontend/node_modules/d3-selection/src/selection/enter.js create mode 100644 frontend/node_modules/d3-selection/src/selection/exit.js create mode 100644 frontend/node_modules/d3-selection/src/selection/filter.js create mode 100644 frontend/node_modules/d3-selection/src/selection/html.js create mode 100644 frontend/node_modules/d3-selection/src/selection/index.js create mode 100644 frontend/node_modules/d3-selection/src/selection/insert.js create mode 100644 frontend/node_modules/d3-selection/src/selection/iterator.js create mode 100644 frontend/node_modules/d3-selection/src/selection/join.js create mode 100644 frontend/node_modules/d3-selection/src/selection/lower.js create mode 100644 frontend/node_modules/d3-selection/src/selection/merge.js create mode 100644 frontend/node_modules/d3-selection/src/selection/node.js create mode 100644 frontend/node_modules/d3-selection/src/selection/nodes.js create mode 100644 frontend/node_modules/d3-selection/src/selection/on.js create mode 100644 frontend/node_modules/d3-selection/src/selection/order.js create mode 100644 frontend/node_modules/d3-selection/src/selection/property.js create mode 100644 frontend/node_modules/d3-selection/src/selection/raise.js create mode 100644 frontend/node_modules/d3-selection/src/selection/remove.js create mode 100644 frontend/node_modules/d3-selection/src/selection/select.js create mode 100644 frontend/node_modules/d3-selection/src/selection/selectAll.js create mode 100644 frontend/node_modules/d3-selection/src/selection/selectChild.js create mode 100644 frontend/node_modules/d3-selection/src/selection/selectChildren.js create mode 100644 frontend/node_modules/d3-selection/src/selection/size.js create mode 100644 frontend/node_modules/d3-selection/src/selection/sort.js create mode 100644 frontend/node_modules/d3-selection/src/selection/sparse.js create mode 100644 frontend/node_modules/d3-selection/src/selection/style.js create mode 100644 frontend/node_modules/d3-selection/src/selection/text.js create mode 100644 frontend/node_modules/d3-selection/src/selector.js create mode 100644 frontend/node_modules/d3-selection/src/selectorAll.js create mode 100644 frontend/node_modules/d3-selection/src/sourceEvent.js create mode 100644 frontend/node_modules/d3-selection/src/window.js create mode 100644 frontend/node_modules/d3-shape/LICENSE create mode 100644 frontend/node_modules/d3-shape/README.md create mode 100644 frontend/node_modules/d3-shape/dist/d3-shape.js create mode 100644 frontend/node_modules/d3-shape/dist/d3-shape.min.js create mode 100644 frontend/node_modules/d3-shape/package.json create mode 100644 frontend/node_modules/d3-shape/src/arc.js create mode 100644 frontend/node_modules/d3-shape/src/area.js create mode 100644 frontend/node_modules/d3-shape/src/areaRadial.js create mode 100644 frontend/node_modules/d3-shape/src/array.js create mode 100644 frontend/node_modules/d3-shape/src/constant.js create mode 100644 frontend/node_modules/d3-shape/src/curve/basis.js create mode 100644 frontend/node_modules/d3-shape/src/curve/basisClosed.js create mode 100644 frontend/node_modules/d3-shape/src/curve/basisOpen.js create mode 100644 frontend/node_modules/d3-shape/src/curve/bump.js create mode 100644 frontend/node_modules/d3-shape/src/curve/bundle.js create mode 100644 frontend/node_modules/d3-shape/src/curve/cardinal.js create mode 100644 frontend/node_modules/d3-shape/src/curve/cardinalClosed.js create mode 100644 frontend/node_modules/d3-shape/src/curve/cardinalOpen.js create mode 100644 frontend/node_modules/d3-shape/src/curve/catmullRom.js create mode 100644 frontend/node_modules/d3-shape/src/curve/catmullRomClosed.js create mode 100644 frontend/node_modules/d3-shape/src/curve/catmullRomOpen.js create mode 100644 frontend/node_modules/d3-shape/src/curve/linear.js create mode 100644 frontend/node_modules/d3-shape/src/curve/linearClosed.js create mode 100644 frontend/node_modules/d3-shape/src/curve/monotone.js create mode 100644 frontend/node_modules/d3-shape/src/curve/natural.js create mode 100644 frontend/node_modules/d3-shape/src/curve/radial.js create mode 100644 frontend/node_modules/d3-shape/src/curve/step.js create mode 100644 frontend/node_modules/d3-shape/src/descending.js create mode 100644 frontend/node_modules/d3-shape/src/identity.js create mode 100644 frontend/node_modules/d3-shape/src/index.js create mode 100644 frontend/node_modules/d3-shape/src/line.js create mode 100644 frontend/node_modules/d3-shape/src/lineRadial.js create mode 100644 frontend/node_modules/d3-shape/src/link.js create mode 100644 frontend/node_modules/d3-shape/src/math.js create mode 100644 frontend/node_modules/d3-shape/src/noop.js create mode 100644 frontend/node_modules/d3-shape/src/offset/diverging.js create mode 100644 frontend/node_modules/d3-shape/src/offset/expand.js create mode 100644 frontend/node_modules/d3-shape/src/offset/none.js create mode 100644 frontend/node_modules/d3-shape/src/offset/silhouette.js create mode 100644 frontend/node_modules/d3-shape/src/offset/wiggle.js create mode 100644 frontend/node_modules/d3-shape/src/order/appearance.js create mode 100644 frontend/node_modules/d3-shape/src/order/ascending.js create mode 100644 frontend/node_modules/d3-shape/src/order/descending.js create mode 100644 frontend/node_modules/d3-shape/src/order/insideOut.js create mode 100644 frontend/node_modules/d3-shape/src/order/none.js create mode 100644 frontend/node_modules/d3-shape/src/order/reverse.js create mode 100644 frontend/node_modules/d3-shape/src/path.js create mode 100644 frontend/node_modules/d3-shape/src/pie.js create mode 100644 frontend/node_modules/d3-shape/src/point.js create mode 100644 frontend/node_modules/d3-shape/src/pointRadial.js create mode 100644 frontend/node_modules/d3-shape/src/stack.js create mode 100644 frontend/node_modules/d3-shape/src/symbol.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/asterisk.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/circle.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/cross.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/diamond.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/diamond2.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/plus.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/square.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/square2.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/star.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/times.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/triangle.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/triangle2.js create mode 100644 frontend/node_modules/d3-shape/src/symbol/wye.js create mode 100644 frontend/node_modules/d3-time-format/LICENSE create mode 100644 frontend/node_modules/d3-time-format/README.md create mode 100644 frontend/node_modules/d3-time-format/dist/d3-time-format.js create mode 100644 frontend/node_modules/d3-time-format/dist/d3-time-format.min.js create mode 100644 frontend/node_modules/d3-time-format/locale/ar-EG.json create mode 100644 frontend/node_modules/d3-time-format/locale/ar-SY.json create mode 100644 frontend/node_modules/d3-time-format/locale/ca-ES.json create mode 100644 frontend/node_modules/d3-time-format/locale/cs-CZ.json create mode 100644 frontend/node_modules/d3-time-format/locale/da-DK.json create mode 100644 frontend/node_modules/d3-time-format/locale/de-CH.json create mode 100644 frontend/node_modules/d3-time-format/locale/de-DE.json create mode 100644 frontend/node_modules/d3-time-format/locale/en-CA.json create mode 100644 frontend/node_modules/d3-time-format/locale/en-GB.json create mode 100644 frontend/node_modules/d3-time-format/locale/en-US.json create mode 100644 frontend/node_modules/d3-time-format/locale/es-ES.json create mode 100644 frontend/node_modules/d3-time-format/locale/es-MX.json create mode 100644 frontend/node_modules/d3-time-format/locale/fa-IR.json create mode 100644 frontend/node_modules/d3-time-format/locale/fi-FI.json create mode 100644 frontend/node_modules/d3-time-format/locale/fr-CA.json create mode 100644 frontend/node_modules/d3-time-format/locale/fr-FR.json create mode 100644 frontend/node_modules/d3-time-format/locale/he-IL.json create mode 100644 frontend/node_modules/d3-time-format/locale/hr-HR.json create mode 100644 frontend/node_modules/d3-time-format/locale/hu-HU.json create mode 100644 frontend/node_modules/d3-time-format/locale/it-IT.json create mode 100644 frontend/node_modules/d3-time-format/locale/ja-JP.json create mode 100644 frontend/node_modules/d3-time-format/locale/ko-KR.json create mode 100644 frontend/node_modules/d3-time-format/locale/mk-MK.json create mode 100644 frontend/node_modules/d3-time-format/locale/nb-NO.json create mode 100644 frontend/node_modules/d3-time-format/locale/nl-BE.json create mode 100644 frontend/node_modules/d3-time-format/locale/nl-NL.json create mode 100644 frontend/node_modules/d3-time-format/locale/pl-PL.json create mode 100644 frontend/node_modules/d3-time-format/locale/pt-BR.json create mode 100644 frontend/node_modules/d3-time-format/locale/ru-RU.json create mode 100644 frontend/node_modules/d3-time-format/locale/sv-SE.json create mode 100644 frontend/node_modules/d3-time-format/locale/tr-TR.json create mode 100644 frontend/node_modules/d3-time-format/locale/uk-UA.json create mode 100644 frontend/node_modules/d3-time-format/locale/zh-CN.json create mode 100644 frontend/node_modules/d3-time-format/locale/zh-TW.json create mode 100644 frontend/node_modules/d3-time-format/package.json create mode 100644 frontend/node_modules/d3-time-format/src/defaultLocale.js create mode 100644 frontend/node_modules/d3-time-format/src/index.js create mode 100644 frontend/node_modules/d3-time-format/src/isoFormat.js create mode 100644 frontend/node_modules/d3-time-format/src/isoParse.js create mode 100644 frontend/node_modules/d3-time-format/src/locale.js create mode 100644 frontend/node_modules/d3-time/LICENSE create mode 100644 frontend/node_modules/d3-time/README.md create mode 100644 frontend/node_modules/d3-time/dist/d3-time.js create mode 100644 frontend/node_modules/d3-time/dist/d3-time.min.js create mode 100644 frontend/node_modules/d3-time/package.json create mode 100644 frontend/node_modules/d3-time/src/day.js create mode 100644 frontend/node_modules/d3-time/src/duration.js create mode 100644 frontend/node_modules/d3-time/src/hour.js create mode 100644 frontend/node_modules/d3-time/src/index.js create mode 100644 frontend/node_modules/d3-time/src/interval.js create mode 100644 frontend/node_modules/d3-time/src/millisecond.js create mode 100644 frontend/node_modules/d3-time/src/minute.js create mode 100644 frontend/node_modules/d3-time/src/month.js create mode 100644 frontend/node_modules/d3-time/src/second.js create mode 100644 frontend/node_modules/d3-time/src/ticks.js create mode 100644 frontend/node_modules/d3-time/src/week.js create mode 100644 frontend/node_modules/d3-time/src/year.js create mode 100644 frontend/node_modules/d3-timer/LICENSE create mode 100644 frontend/node_modules/d3-timer/README.md create mode 100644 frontend/node_modules/d3-timer/dist/d3-timer.js create mode 100644 frontend/node_modules/d3-timer/dist/d3-timer.min.js create mode 100644 frontend/node_modules/d3-timer/package.json create mode 100644 frontend/node_modules/d3-timer/src/index.js create mode 100644 frontend/node_modules/d3-timer/src/interval.js create mode 100644 frontend/node_modules/d3-timer/src/timeout.js create mode 100644 frontend/node_modules/d3-timer/src/timer.js create mode 100644 frontend/node_modules/d3-transition/LICENSE create mode 100644 frontend/node_modules/d3-transition/README.md create mode 100644 frontend/node_modules/d3-transition/dist/d3-transition.js create mode 100644 frontend/node_modules/d3-transition/dist/d3-transition.min.js create mode 100644 frontend/node_modules/d3-transition/package.json create mode 100644 frontend/node_modules/d3-transition/src/active.js create mode 100644 frontend/node_modules/d3-transition/src/index.js create mode 100644 frontend/node_modules/d3-transition/src/interrupt.js create mode 100644 frontend/node_modules/d3-transition/src/selection/index.js create mode 100644 frontend/node_modules/d3-transition/src/selection/interrupt.js create mode 100644 frontend/node_modules/d3-transition/src/selection/transition.js create mode 100644 frontend/node_modules/d3-transition/src/transition/attr.js create mode 100644 frontend/node_modules/d3-transition/src/transition/attrTween.js create mode 100644 frontend/node_modules/d3-transition/src/transition/delay.js create mode 100644 frontend/node_modules/d3-transition/src/transition/duration.js create mode 100644 frontend/node_modules/d3-transition/src/transition/ease.js create mode 100644 frontend/node_modules/d3-transition/src/transition/easeVarying.js create mode 100644 frontend/node_modules/d3-transition/src/transition/end.js create mode 100644 frontend/node_modules/d3-transition/src/transition/filter.js create mode 100644 frontend/node_modules/d3-transition/src/transition/index.js create mode 100644 frontend/node_modules/d3-transition/src/transition/interpolate.js create mode 100644 frontend/node_modules/d3-transition/src/transition/merge.js create mode 100644 frontend/node_modules/d3-transition/src/transition/on.js create mode 100644 frontend/node_modules/d3-transition/src/transition/remove.js create mode 100644 frontend/node_modules/d3-transition/src/transition/schedule.js create mode 100644 frontend/node_modules/d3-transition/src/transition/select.js create mode 100644 frontend/node_modules/d3-transition/src/transition/selectAll.js create mode 100644 frontend/node_modules/d3-transition/src/transition/selection.js create mode 100644 frontend/node_modules/d3-transition/src/transition/style.js create mode 100644 frontend/node_modules/d3-transition/src/transition/styleTween.js create mode 100644 frontend/node_modules/d3-transition/src/transition/text.js create mode 100644 frontend/node_modules/d3-transition/src/transition/textTween.js create mode 100644 frontend/node_modules/d3-transition/src/transition/transition.js create mode 100644 frontend/node_modules/d3-transition/src/transition/tween.js create mode 100644 frontend/node_modules/d3-zoom/LICENSE create mode 100644 frontend/node_modules/d3-zoom/README.md create mode 100644 frontend/node_modules/d3-zoom/dist/d3-zoom.js create mode 100644 frontend/node_modules/d3-zoom/dist/d3-zoom.min.js create mode 100644 frontend/node_modules/d3-zoom/package.json create mode 100644 frontend/node_modules/d3-zoom/src/constant.js create mode 100644 frontend/node_modules/d3-zoom/src/event.js create mode 100644 frontend/node_modules/d3-zoom/src/index.js create mode 100644 frontend/node_modules/d3-zoom/src/noevent.js create mode 100644 frontend/node_modules/d3-zoom/src/transform.js create mode 100644 frontend/node_modules/d3-zoom/src/zoom.js create mode 100644 frontend/node_modules/d3/LICENSE create mode 100644 frontend/node_modules/d3/README.md create mode 100644 frontend/node_modules/d3/dist/d3.js create mode 100644 frontend/node_modules/d3/dist/d3.min.js create mode 100644 frontend/node_modules/d3/package.json create mode 100644 frontend/node_modules/d3/src/index.js create mode 100644 frontend/node_modules/delaunator/LICENSE create mode 100644 frontend/node_modules/delaunator/README.md create mode 100644 frontend/node_modules/delaunator/delaunator.js create mode 100644 frontend/node_modules/delaunator/delaunator.min.js create mode 100644 frontend/node_modules/delaunator/index.js create mode 100644 frontend/node_modules/delaunator/package.json create mode 100644 frontend/node_modules/dom-serializer/LICENSE create mode 100644 frontend/node_modules/dom-serializer/README.md create mode 100644 frontend/node_modules/dom-serializer/lib/esm/foreignNames.d.ts create mode 100644 frontend/node_modules/dom-serializer/lib/esm/foreignNames.d.ts.map create mode 100644 frontend/node_modules/dom-serializer/lib/esm/foreignNames.js create mode 100644 frontend/node_modules/dom-serializer/lib/esm/index.d.ts create mode 100644 frontend/node_modules/dom-serializer/lib/esm/index.d.ts.map create mode 100644 frontend/node_modules/dom-serializer/lib/esm/index.js create mode 100644 frontend/node_modules/dom-serializer/lib/esm/package.json create mode 100644 frontend/node_modules/dom-serializer/lib/foreignNames.d.ts create mode 100644 frontend/node_modules/dom-serializer/lib/foreignNames.d.ts.map create mode 100644 frontend/node_modules/dom-serializer/lib/foreignNames.js create mode 100644 frontend/node_modules/dom-serializer/lib/index.d.ts create mode 100644 frontend/node_modules/dom-serializer/lib/index.d.ts.map create mode 100644 frontend/node_modules/dom-serializer/lib/index.js create mode 100644 frontend/node_modules/dom-serializer/package.json create mode 100644 frontend/node_modules/domelementtype/LICENSE create mode 100644 frontend/node_modules/domelementtype/lib/esm/index.d.ts create mode 100644 frontend/node_modules/domelementtype/lib/esm/index.d.ts.map create mode 100644 frontend/node_modules/domelementtype/lib/esm/index.js create mode 100644 frontend/node_modules/domelementtype/lib/esm/package.json create mode 100644 frontend/node_modules/domelementtype/lib/index.d.ts create mode 100644 frontend/node_modules/domelementtype/lib/index.d.ts.map create mode 100644 frontend/node_modules/domelementtype/lib/index.js create mode 100644 frontend/node_modules/domelementtype/package.json create mode 100644 frontend/node_modules/domelementtype/readme.md create mode 100644 frontend/node_modules/domhandler/LICENSE create mode 100644 frontend/node_modules/domhandler/lib/esm/index.d.ts create mode 100644 frontend/node_modules/domhandler/lib/esm/index.d.ts.map create mode 100644 frontend/node_modules/domhandler/lib/esm/index.js create mode 100644 frontend/node_modules/domhandler/lib/esm/node.d.ts create mode 100644 frontend/node_modules/domhandler/lib/esm/node.d.ts.map create mode 100644 frontend/node_modules/domhandler/lib/esm/node.js create mode 100644 frontend/node_modules/domhandler/lib/esm/package.json create mode 100644 frontend/node_modules/domhandler/lib/index.d.ts create mode 100644 frontend/node_modules/domhandler/lib/index.d.ts.map create mode 100644 frontend/node_modules/domhandler/lib/index.js create mode 100644 frontend/node_modules/domhandler/lib/node.d.ts create mode 100644 frontend/node_modules/domhandler/lib/node.d.ts.map create mode 100644 frontend/node_modules/domhandler/lib/node.js create mode 100644 frontend/node_modules/domhandler/package.json create mode 100644 frontend/node_modules/domhandler/readme.md create mode 100644 frontend/node_modules/domutils/LICENSE create mode 100644 frontend/node_modules/domutils/lib/esm/feeds.d.ts create mode 100644 frontend/node_modules/domutils/lib/esm/feeds.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/esm/feeds.js create mode 100644 frontend/node_modules/domutils/lib/esm/feeds.js.map create mode 100644 frontend/node_modules/domutils/lib/esm/helpers.d.ts create mode 100644 frontend/node_modules/domutils/lib/esm/helpers.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/esm/helpers.js create mode 100644 frontend/node_modules/domutils/lib/esm/helpers.js.map create mode 100644 frontend/node_modules/domutils/lib/esm/index.d.ts create mode 100644 frontend/node_modules/domutils/lib/esm/index.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/esm/index.js create mode 100644 frontend/node_modules/domutils/lib/esm/index.js.map create mode 100644 frontend/node_modules/domutils/lib/esm/legacy.d.ts create mode 100644 frontend/node_modules/domutils/lib/esm/legacy.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/esm/legacy.js create mode 100644 frontend/node_modules/domutils/lib/esm/legacy.js.map create mode 100644 frontend/node_modules/domutils/lib/esm/manipulation.d.ts create mode 100644 frontend/node_modules/domutils/lib/esm/manipulation.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/esm/manipulation.js create mode 100644 frontend/node_modules/domutils/lib/esm/manipulation.js.map create mode 100644 frontend/node_modules/domutils/lib/esm/package.json create mode 100644 frontend/node_modules/domutils/lib/esm/querying.d.ts create mode 100644 frontend/node_modules/domutils/lib/esm/querying.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/esm/querying.js create mode 100644 frontend/node_modules/domutils/lib/esm/querying.js.map create mode 100644 frontend/node_modules/domutils/lib/esm/stringify.d.ts create mode 100644 frontend/node_modules/domutils/lib/esm/stringify.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/esm/stringify.js create mode 100644 frontend/node_modules/domutils/lib/esm/stringify.js.map create mode 100644 frontend/node_modules/domutils/lib/esm/traversal.d.ts create mode 100644 frontend/node_modules/domutils/lib/esm/traversal.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/esm/traversal.js create mode 100644 frontend/node_modules/domutils/lib/esm/traversal.js.map create mode 100644 frontend/node_modules/domutils/lib/feeds.d.ts create mode 100644 frontend/node_modules/domutils/lib/feeds.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/feeds.js create mode 100644 frontend/node_modules/domutils/lib/feeds.js.map create mode 100644 frontend/node_modules/domutils/lib/helpers.d.ts create mode 100644 frontend/node_modules/domutils/lib/helpers.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/helpers.js create mode 100644 frontend/node_modules/domutils/lib/helpers.js.map create mode 100644 frontend/node_modules/domutils/lib/index.d.ts create mode 100644 frontend/node_modules/domutils/lib/index.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/index.js create mode 100644 frontend/node_modules/domutils/lib/index.js.map create mode 100644 frontend/node_modules/domutils/lib/legacy.d.ts create mode 100644 frontend/node_modules/domutils/lib/legacy.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/legacy.js create mode 100644 frontend/node_modules/domutils/lib/legacy.js.map create mode 100644 frontend/node_modules/domutils/lib/manipulation.d.ts create mode 100644 frontend/node_modules/domutils/lib/manipulation.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/manipulation.js create mode 100644 frontend/node_modules/domutils/lib/manipulation.js.map create mode 100644 frontend/node_modules/domutils/lib/querying.d.ts create mode 100644 frontend/node_modules/domutils/lib/querying.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/querying.js create mode 100644 frontend/node_modules/domutils/lib/querying.js.map create mode 100644 frontend/node_modules/domutils/lib/stringify.d.ts create mode 100644 frontend/node_modules/domutils/lib/stringify.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/stringify.js create mode 100644 frontend/node_modules/domutils/lib/stringify.js.map create mode 100644 frontend/node_modules/domutils/lib/traversal.d.ts create mode 100644 frontend/node_modules/domutils/lib/traversal.d.ts.map create mode 100644 frontend/node_modules/domutils/lib/traversal.js create mode 100644 frontend/node_modules/domutils/lib/traversal.js.map create mode 100644 frontend/node_modules/domutils/package.json create mode 100644 frontend/node_modules/domutils/readme.md create mode 100644 frontend/node_modules/encoding-sniffer/LICENSE create mode 100644 frontend/node_modules/encoding-sniffer/README.md create mode 100644 frontend/node_modules/encoding-sniffer/dist/commonjs/index.d.ts create mode 100644 frontend/node_modules/encoding-sniffer/dist/commonjs/index.d.ts.map create mode 100644 frontend/node_modules/encoding-sniffer/dist/commonjs/index.js create mode 100644 frontend/node_modules/encoding-sniffer/dist/commonjs/index.js.map create mode 100644 frontend/node_modules/encoding-sniffer/dist/commonjs/package.json create mode 100644 frontend/node_modules/encoding-sniffer/dist/commonjs/sniffer.d.ts create mode 100644 frontend/node_modules/encoding-sniffer/dist/commonjs/sniffer.d.ts.map create mode 100644 frontend/node_modules/encoding-sniffer/dist/commonjs/sniffer.js create mode 100644 frontend/node_modules/encoding-sniffer/dist/commonjs/sniffer.js.map create mode 100644 frontend/node_modules/encoding-sniffer/dist/esm/index.d.ts create mode 100644 frontend/node_modules/encoding-sniffer/dist/esm/index.d.ts.map create mode 100644 frontend/node_modules/encoding-sniffer/dist/esm/index.js create mode 100644 frontend/node_modules/encoding-sniffer/dist/esm/index.js.map create mode 100644 frontend/node_modules/encoding-sniffer/dist/esm/package.json create mode 100644 frontend/node_modules/encoding-sniffer/dist/esm/sniffer.d.ts create mode 100644 frontend/node_modules/encoding-sniffer/dist/esm/sniffer.d.ts.map create mode 100644 frontend/node_modules/encoding-sniffer/dist/esm/sniffer.js create mode 100644 frontend/node_modules/encoding-sniffer/dist/esm/sniffer.js.map create mode 100644 frontend/node_modules/encoding-sniffer/package.json create mode 100644 frontend/node_modules/encoding-sniffer/sniffer.d.ts create mode 100644 frontend/node_modules/encoding-sniffer/sniffer.js create mode 100644 frontend/node_modules/highlight.js/CHANGES.md create mode 100644 frontend/node_modules/highlight.js/LICENSE create mode 100644 frontend/node_modules/highlight.js/README.md create mode 100644 frontend/node_modules/highlight.js/SECURITY.md create mode 100644 frontend/node_modules/highlight.js/SUPPORTED_LANGUAGES.md create mode 100644 frontend/node_modules/highlight.js/VERSION_10_UPGRADE.md create mode 100644 frontend/node_modules/highlight.js/VERSION_11_UPGRADE.md create mode 100644 frontend/node_modules/highlight.js/es/common.d.ts create mode 100644 frontend/node_modules/highlight.js/es/common.js create mode 100644 frontend/node_modules/highlight.js/es/core.d.ts create mode 100644 frontend/node_modules/highlight.js/es/core.js create mode 100644 frontend/node_modules/highlight.js/es/index.js create mode 100644 frontend/node_modules/highlight.js/es/languages/1c.js create mode 100644 frontend/node_modules/highlight.js/es/languages/1c.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/abnf.js create mode 100644 frontend/node_modules/highlight.js/es/languages/abnf.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/accesslog.js create mode 100644 frontend/node_modules/highlight.js/es/languages/accesslog.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/actionscript.js create mode 100644 frontend/node_modules/highlight.js/es/languages/actionscript.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ada.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ada.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/angelscript.js create mode 100644 frontend/node_modules/highlight.js/es/languages/angelscript.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/apache.js create mode 100644 frontend/node_modules/highlight.js/es/languages/apache.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/applescript.js create mode 100644 frontend/node_modules/highlight.js/es/languages/applescript.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/arcade.js create mode 100644 frontend/node_modules/highlight.js/es/languages/arcade.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/arduino.js create mode 100644 frontend/node_modules/highlight.js/es/languages/arduino.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/armasm.js create mode 100644 frontend/node_modules/highlight.js/es/languages/armasm.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/asciidoc.js create mode 100644 frontend/node_modules/highlight.js/es/languages/asciidoc.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/aspectj.js create mode 100644 frontend/node_modules/highlight.js/es/languages/aspectj.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/autohotkey.js create mode 100644 frontend/node_modules/highlight.js/es/languages/autohotkey.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/autoit.js create mode 100644 frontend/node_modules/highlight.js/es/languages/autoit.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/avrasm.js create mode 100644 frontend/node_modules/highlight.js/es/languages/avrasm.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/awk.js create mode 100644 frontend/node_modules/highlight.js/es/languages/awk.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/axapta.js create mode 100644 frontend/node_modules/highlight.js/es/languages/axapta.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/bash.js create mode 100644 frontend/node_modules/highlight.js/es/languages/bash.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/basic.js create mode 100644 frontend/node_modules/highlight.js/es/languages/basic.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/bnf.js create mode 100644 frontend/node_modules/highlight.js/es/languages/bnf.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/brainfuck.js create mode 100644 frontend/node_modules/highlight.js/es/languages/brainfuck.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/c.js create mode 100644 frontend/node_modules/highlight.js/es/languages/c.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/cal.js create mode 100644 frontend/node_modules/highlight.js/es/languages/cal.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/capnproto.js create mode 100644 frontend/node_modules/highlight.js/es/languages/capnproto.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ceylon.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ceylon.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/clean.js create mode 100644 frontend/node_modules/highlight.js/es/languages/clean.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/clojure-repl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/clojure-repl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/clojure.js create mode 100644 frontend/node_modules/highlight.js/es/languages/clojure.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/cmake.js create mode 100644 frontend/node_modules/highlight.js/es/languages/cmake.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/coffeescript.js create mode 100644 frontend/node_modules/highlight.js/es/languages/coffeescript.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/coq.js create mode 100644 frontend/node_modules/highlight.js/es/languages/coq.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/cos.js create mode 100644 frontend/node_modules/highlight.js/es/languages/cos.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/cpp.js create mode 100644 frontend/node_modules/highlight.js/es/languages/cpp.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/crmsh.js create mode 100644 frontend/node_modules/highlight.js/es/languages/crmsh.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/crystal.js create mode 100644 frontend/node_modules/highlight.js/es/languages/crystal.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/csharp.js create mode 100644 frontend/node_modules/highlight.js/es/languages/csharp.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/csp.js create mode 100644 frontend/node_modules/highlight.js/es/languages/csp.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/css.js create mode 100644 frontend/node_modules/highlight.js/es/languages/css.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/d.js create mode 100644 frontend/node_modules/highlight.js/es/languages/d.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dart.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dart.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/delphi.js create mode 100644 frontend/node_modules/highlight.js/es/languages/delphi.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/diff.js create mode 100644 frontend/node_modules/highlight.js/es/languages/diff.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/django.js create mode 100644 frontend/node_modules/highlight.js/es/languages/django.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dns.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dns.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dockerfile.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dockerfile.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dos.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dos.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dsconfig.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dsconfig.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dts.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dts.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dust.js create mode 100644 frontend/node_modules/highlight.js/es/languages/dust.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ebnf.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ebnf.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/elixir.js create mode 100644 frontend/node_modules/highlight.js/es/languages/elixir.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/elm.js create mode 100644 frontend/node_modules/highlight.js/es/languages/elm.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/erb.js create mode 100644 frontend/node_modules/highlight.js/es/languages/erb.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/erlang-repl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/erlang-repl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/erlang.js create mode 100644 frontend/node_modules/highlight.js/es/languages/erlang.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/excel.js create mode 100644 frontend/node_modules/highlight.js/es/languages/excel.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/fix.js create mode 100644 frontend/node_modules/highlight.js/es/languages/fix.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/flix.js create mode 100644 frontend/node_modules/highlight.js/es/languages/flix.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/fortran.js create mode 100644 frontend/node_modules/highlight.js/es/languages/fortran.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/fsharp.js create mode 100644 frontend/node_modules/highlight.js/es/languages/fsharp.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/gams.js create mode 100644 frontend/node_modules/highlight.js/es/languages/gams.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/gauss.js create mode 100644 frontend/node_modules/highlight.js/es/languages/gauss.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/gcode.js create mode 100644 frontend/node_modules/highlight.js/es/languages/gcode.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/gherkin.js create mode 100644 frontend/node_modules/highlight.js/es/languages/gherkin.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/glsl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/glsl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/gml.js create mode 100644 frontend/node_modules/highlight.js/es/languages/gml.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/go.js create mode 100644 frontend/node_modules/highlight.js/es/languages/go.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/golo.js create mode 100644 frontend/node_modules/highlight.js/es/languages/golo.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/gradle.js create mode 100644 frontend/node_modules/highlight.js/es/languages/gradle.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/graphql.js create mode 100644 frontend/node_modules/highlight.js/es/languages/graphql.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/groovy.js create mode 100644 frontend/node_modules/highlight.js/es/languages/groovy.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/haml.js create mode 100644 frontend/node_modules/highlight.js/es/languages/haml.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/handlebars.js create mode 100644 frontend/node_modules/highlight.js/es/languages/handlebars.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/haskell.js create mode 100644 frontend/node_modules/highlight.js/es/languages/haskell.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/haxe.js create mode 100644 frontend/node_modules/highlight.js/es/languages/haxe.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/hsp.js create mode 100644 frontend/node_modules/highlight.js/es/languages/hsp.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/http.js create mode 100644 frontend/node_modules/highlight.js/es/languages/http.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/hy.js create mode 100644 frontend/node_modules/highlight.js/es/languages/hy.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/inform7.js create mode 100644 frontend/node_modules/highlight.js/es/languages/inform7.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ini.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ini.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/irpf90.js create mode 100644 frontend/node_modules/highlight.js/es/languages/irpf90.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/isbl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/isbl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/java.js create mode 100644 frontend/node_modules/highlight.js/es/languages/java.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/javascript.js create mode 100644 frontend/node_modules/highlight.js/es/languages/javascript.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/jboss-cli.js create mode 100644 frontend/node_modules/highlight.js/es/languages/jboss-cli.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/json.js create mode 100644 frontend/node_modules/highlight.js/es/languages/json.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/julia-repl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/julia-repl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/julia.js create mode 100644 frontend/node_modules/highlight.js/es/languages/julia.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/kotlin.js create mode 100644 frontend/node_modules/highlight.js/es/languages/kotlin.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/lasso.js create mode 100644 frontend/node_modules/highlight.js/es/languages/lasso.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/latex.js create mode 100644 frontend/node_modules/highlight.js/es/languages/latex.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ldif.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ldif.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/leaf.js create mode 100644 frontend/node_modules/highlight.js/es/languages/leaf.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/less.js create mode 100644 frontend/node_modules/highlight.js/es/languages/less.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/lisp.js create mode 100644 frontend/node_modules/highlight.js/es/languages/lisp.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/livecodeserver.js create mode 100644 frontend/node_modules/highlight.js/es/languages/livecodeserver.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/livescript.js create mode 100644 frontend/node_modules/highlight.js/es/languages/livescript.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/llvm.js create mode 100644 frontend/node_modules/highlight.js/es/languages/llvm.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/lsl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/lsl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/lua.js create mode 100644 frontend/node_modules/highlight.js/es/languages/lua.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/makefile.js create mode 100644 frontend/node_modules/highlight.js/es/languages/makefile.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/markdown.js create mode 100644 frontend/node_modules/highlight.js/es/languages/markdown.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/mathematica.js create mode 100644 frontend/node_modules/highlight.js/es/languages/mathematica.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/matlab.js create mode 100644 frontend/node_modules/highlight.js/es/languages/matlab.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/maxima.js create mode 100644 frontend/node_modules/highlight.js/es/languages/maxima.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/mel.js create mode 100644 frontend/node_modules/highlight.js/es/languages/mel.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/mercury.js create mode 100644 frontend/node_modules/highlight.js/es/languages/mercury.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/mipsasm.js create mode 100644 frontend/node_modules/highlight.js/es/languages/mipsasm.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/mizar.js create mode 100644 frontend/node_modules/highlight.js/es/languages/mizar.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/mojolicious.js create mode 100644 frontend/node_modules/highlight.js/es/languages/mojolicious.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/monkey.js create mode 100644 frontend/node_modules/highlight.js/es/languages/monkey.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/moonscript.js create mode 100644 frontend/node_modules/highlight.js/es/languages/moonscript.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/n1ql.js create mode 100644 frontend/node_modules/highlight.js/es/languages/n1ql.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/nestedtext.js create mode 100644 frontend/node_modules/highlight.js/es/languages/nestedtext.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/nginx.js create mode 100644 frontend/node_modules/highlight.js/es/languages/nginx.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/nim.js create mode 100644 frontend/node_modules/highlight.js/es/languages/nim.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/nix.js create mode 100644 frontend/node_modules/highlight.js/es/languages/nix.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/node-repl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/node-repl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/nsis.js create mode 100644 frontend/node_modules/highlight.js/es/languages/nsis.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/objectivec.js create mode 100644 frontend/node_modules/highlight.js/es/languages/objectivec.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ocaml.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ocaml.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/openscad.js create mode 100644 frontend/node_modules/highlight.js/es/languages/openscad.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/oxygene.js create mode 100644 frontend/node_modules/highlight.js/es/languages/oxygene.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/parser3.js create mode 100644 frontend/node_modules/highlight.js/es/languages/parser3.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/perl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/perl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/pf.js create mode 100644 frontend/node_modules/highlight.js/es/languages/pf.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/pgsql.js create mode 100644 frontend/node_modules/highlight.js/es/languages/pgsql.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/php-template.js create mode 100644 frontend/node_modules/highlight.js/es/languages/php-template.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/php.js create mode 100644 frontend/node_modules/highlight.js/es/languages/php.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/plaintext.js create mode 100644 frontend/node_modules/highlight.js/es/languages/plaintext.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/pony.js create mode 100644 frontend/node_modules/highlight.js/es/languages/pony.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/powershell.js create mode 100644 frontend/node_modules/highlight.js/es/languages/powershell.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/processing.js create mode 100644 frontend/node_modules/highlight.js/es/languages/processing.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/profile.js create mode 100644 frontend/node_modules/highlight.js/es/languages/profile.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/prolog.js create mode 100644 frontend/node_modules/highlight.js/es/languages/prolog.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/properties.js create mode 100644 frontend/node_modules/highlight.js/es/languages/properties.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/protobuf.js create mode 100644 frontend/node_modules/highlight.js/es/languages/protobuf.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/puppet.js create mode 100644 frontend/node_modules/highlight.js/es/languages/puppet.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/purebasic.js create mode 100644 frontend/node_modules/highlight.js/es/languages/purebasic.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/python-repl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/python-repl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/python.js create mode 100644 frontend/node_modules/highlight.js/es/languages/python.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/q.js create mode 100644 frontend/node_modules/highlight.js/es/languages/q.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/qml.js create mode 100644 frontend/node_modules/highlight.js/es/languages/qml.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/r.js create mode 100644 frontend/node_modules/highlight.js/es/languages/r.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/reasonml.js create mode 100644 frontend/node_modules/highlight.js/es/languages/reasonml.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/rib.js create mode 100644 frontend/node_modules/highlight.js/es/languages/rib.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/roboconf.js create mode 100644 frontend/node_modules/highlight.js/es/languages/roboconf.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/routeros.js create mode 100644 frontend/node_modules/highlight.js/es/languages/routeros.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/rsl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/rsl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ruby.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ruby.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ruleslanguage.js create mode 100644 frontend/node_modules/highlight.js/es/languages/ruleslanguage.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/rust.js create mode 100644 frontend/node_modules/highlight.js/es/languages/rust.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/sas.js create mode 100644 frontend/node_modules/highlight.js/es/languages/sas.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/scala.js create mode 100644 frontend/node_modules/highlight.js/es/languages/scala.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/scheme.js create mode 100644 frontend/node_modules/highlight.js/es/languages/scheme.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/scilab.js create mode 100644 frontend/node_modules/highlight.js/es/languages/scilab.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/scss.js create mode 100644 frontend/node_modules/highlight.js/es/languages/scss.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/shell.js create mode 100644 frontend/node_modules/highlight.js/es/languages/shell.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/smali.js create mode 100644 frontend/node_modules/highlight.js/es/languages/smali.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/smalltalk.js create mode 100644 frontend/node_modules/highlight.js/es/languages/smalltalk.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/sml.js create mode 100644 frontend/node_modules/highlight.js/es/languages/sml.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/sqf.js create mode 100644 frontend/node_modules/highlight.js/es/languages/sqf.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/sql.js create mode 100644 frontend/node_modules/highlight.js/es/languages/sql.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/stan.js create mode 100644 frontend/node_modules/highlight.js/es/languages/stan.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/stata.js create mode 100644 frontend/node_modules/highlight.js/es/languages/stata.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/step21.js create mode 100644 frontend/node_modules/highlight.js/es/languages/step21.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/stylus.js create mode 100644 frontend/node_modules/highlight.js/es/languages/stylus.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/subunit.js create mode 100644 frontend/node_modules/highlight.js/es/languages/subunit.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/swift.js create mode 100644 frontend/node_modules/highlight.js/es/languages/swift.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/taggerscript.js create mode 100644 frontend/node_modules/highlight.js/es/languages/taggerscript.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/tap.js create mode 100644 frontend/node_modules/highlight.js/es/languages/tap.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/tcl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/tcl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/thrift.js create mode 100644 frontend/node_modules/highlight.js/es/languages/thrift.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/tp.js create mode 100644 frontend/node_modules/highlight.js/es/languages/tp.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/twig.js create mode 100644 frontend/node_modules/highlight.js/es/languages/twig.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/typescript.js create mode 100644 frontend/node_modules/highlight.js/es/languages/typescript.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/vala.js create mode 100644 frontend/node_modules/highlight.js/es/languages/vala.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/vbnet.js create mode 100644 frontend/node_modules/highlight.js/es/languages/vbnet.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/vbscript-html.js create mode 100644 frontend/node_modules/highlight.js/es/languages/vbscript-html.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/vbscript.js create mode 100644 frontend/node_modules/highlight.js/es/languages/vbscript.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/verilog.js create mode 100644 frontend/node_modules/highlight.js/es/languages/verilog.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/vhdl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/vhdl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/vim.js create mode 100644 frontend/node_modules/highlight.js/es/languages/vim.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/wasm.js create mode 100644 frontend/node_modules/highlight.js/es/languages/wasm.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/wren.js create mode 100644 frontend/node_modules/highlight.js/es/languages/wren.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/x86asm.js create mode 100644 frontend/node_modules/highlight.js/es/languages/x86asm.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/xl.js create mode 100644 frontend/node_modules/highlight.js/es/languages/xl.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/xml.js create mode 100644 frontend/node_modules/highlight.js/es/languages/xml.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/xquery.js create mode 100644 frontend/node_modules/highlight.js/es/languages/xquery.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/yaml.js create mode 100644 frontend/node_modules/highlight.js/es/languages/yaml.js.js create mode 100644 frontend/node_modules/highlight.js/es/languages/zephir.js create mode 100644 frontend/node_modules/highlight.js/es/languages/zephir.js.js create mode 100644 frontend/node_modules/highlight.js/es/package.json create mode 100644 frontend/node_modules/highlight.js/es/utils/regex.js create mode 100644 frontend/node_modules/highlight.js/lib/common.d.ts create mode 100644 frontend/node_modules/highlight.js/lib/common.js create mode 100644 frontend/node_modules/highlight.js/lib/core.d.ts create mode 100644 frontend/node_modules/highlight.js/lib/core.js create mode 100644 frontend/node_modules/highlight.js/lib/index.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/1c.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/1c.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/abnf.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/abnf.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/accesslog.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/accesslog.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/actionscript.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/actionscript.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ada.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ada.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/angelscript.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/angelscript.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/apache.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/apache.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/applescript.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/applescript.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/arcade.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/arcade.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/arduino.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/arduino.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/armasm.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/armasm.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/asciidoc.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/asciidoc.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/aspectj.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/aspectj.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/autohotkey.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/autohotkey.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/autoit.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/autoit.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/avrasm.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/avrasm.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/awk.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/awk.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/axapta.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/axapta.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/bash.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/bash.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/basic.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/basic.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/bnf.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/bnf.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/brainfuck.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/brainfuck.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/c.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/c.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/cal.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/cal.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/capnproto.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/capnproto.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ceylon.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ceylon.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/clean.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/clean.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/clojure-repl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/clojure-repl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/clojure.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/clojure.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/cmake.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/cmake.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/coffeescript.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/coffeescript.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/coq.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/coq.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/cos.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/cos.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/cpp.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/cpp.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/crmsh.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/crmsh.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/crystal.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/crystal.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/csharp.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/csharp.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/csp.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/csp.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/css.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/css.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/d.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/d.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dart.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dart.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/delphi.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/delphi.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/diff.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/diff.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/django.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/django.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dns.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dns.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dockerfile.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dockerfile.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dos.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dos.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dsconfig.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dsconfig.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dts.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dts.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dust.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/dust.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ebnf.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ebnf.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/elixir.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/elixir.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/elm.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/elm.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/erb.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/erb.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/erlang-repl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/erlang-repl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/erlang.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/erlang.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/excel.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/excel.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/fix.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/fix.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/flix.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/flix.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/fortran.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/fortran.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/fsharp.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/fsharp.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/gams.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/gams.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/gauss.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/gauss.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/gcode.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/gcode.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/gherkin.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/gherkin.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/glsl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/glsl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/gml.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/gml.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/go.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/go.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/golo.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/golo.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/gradle.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/gradle.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/graphql.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/graphql.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/groovy.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/groovy.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/haml.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/haml.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/handlebars.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/handlebars.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/haskell.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/haskell.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/haxe.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/haxe.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/hsp.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/hsp.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/http.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/http.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/hy.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/hy.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/inform7.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/inform7.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ini.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ini.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/irpf90.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/irpf90.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/isbl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/isbl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/java.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/java.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/javascript.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/javascript.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/jboss-cli.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/jboss-cli.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/json.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/json.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/julia-repl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/julia-repl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/julia.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/julia.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/kotlin.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/kotlin.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/lasso.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/lasso.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/latex.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/latex.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ldif.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ldif.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/leaf.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/leaf.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/less.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/less.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/lisp.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/lisp.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/livecodeserver.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/livecodeserver.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/livescript.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/livescript.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/llvm.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/llvm.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/lsl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/lsl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/lua.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/lua.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/makefile.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/makefile.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/markdown.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/markdown.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/mathematica.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/mathematica.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/matlab.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/matlab.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/maxima.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/maxima.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/mel.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/mel.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/mercury.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/mercury.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/mipsasm.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/mipsasm.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/mizar.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/mizar.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/mojolicious.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/mojolicious.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/monkey.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/monkey.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/moonscript.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/moonscript.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/n1ql.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/n1ql.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/nestedtext.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/nestedtext.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/nginx.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/nginx.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/nim.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/nim.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/nix.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/nix.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/node-repl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/node-repl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/nsis.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/nsis.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/objectivec.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/objectivec.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ocaml.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ocaml.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/openscad.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/openscad.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/oxygene.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/oxygene.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/parser3.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/parser3.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/perl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/perl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/pf.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/pf.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/pgsql.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/pgsql.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/php-template.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/php-template.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/php.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/php.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/plaintext.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/plaintext.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/pony.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/pony.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/powershell.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/powershell.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/processing.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/processing.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/profile.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/profile.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/prolog.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/prolog.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/properties.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/properties.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/protobuf.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/protobuf.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/puppet.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/puppet.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/purebasic.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/purebasic.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/python-repl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/python-repl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/python.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/python.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/q.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/q.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/qml.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/qml.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/r.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/r.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/reasonml.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/reasonml.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/rib.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/rib.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/roboconf.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/roboconf.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/routeros.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/routeros.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/rsl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/rsl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ruby.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ruby.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ruleslanguage.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/ruleslanguage.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/rust.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/rust.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/sas.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/sas.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/scala.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/scala.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/scheme.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/scheme.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/scilab.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/scilab.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/scss.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/scss.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/shell.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/shell.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/smali.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/smali.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/smalltalk.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/smalltalk.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/sml.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/sml.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/sqf.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/sqf.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/sql.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/sql.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/stan.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/stan.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/stata.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/stata.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/step21.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/step21.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/stylus.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/stylus.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/subunit.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/subunit.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/swift.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/swift.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/taggerscript.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/taggerscript.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/tap.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/tap.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/tcl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/tcl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/thrift.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/thrift.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/tp.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/tp.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/twig.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/twig.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/typescript.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/typescript.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/vala.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/vala.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/vbnet.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/vbnet.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/vbscript-html.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/vbscript-html.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/vbscript.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/vbscript.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/verilog.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/verilog.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/vhdl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/vhdl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/vim.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/vim.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/wasm.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/wasm.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/wren.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/wren.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/x86asm.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/x86asm.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/xl.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/xl.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/xml.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/xml.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/xquery.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/xquery.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/yaml.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/yaml.js.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/zephir.js create mode 100644 frontend/node_modules/highlight.js/lib/languages/zephir.js.js create mode 100644 frontend/node_modules/highlight.js/package.json create mode 100644 frontend/node_modules/highlight.js/scss/1c-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/a11y-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/a11y-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/agate.scss create mode 100644 frontend/node_modules/highlight.js/scss/an-old-hope.scss create mode 100644 frontend/node_modules/highlight.js/scss/androidstudio.scss create mode 100644 frontend/node_modules/highlight.js/scss/arduino-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/arta.scss create mode 100644 frontend/node_modules/highlight.js/scss/ascetic.scss create mode 100644 frontend/node_modules/highlight.js/scss/atom-one-dark-reasonable.scss create mode 100644 frontend/node_modules/highlight.js/scss/atom-one-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/atom-one-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/3024.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/apathy.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/apprentice.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/ashes.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-cave-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-cave.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-dune-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-dune.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-estuary-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-estuary.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-forest-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-forest.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-heath-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-heath.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-lakeside-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-lakeside.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-plateau-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-plateau.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-savanna-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-savanna.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-seaside-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-seaside.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-sulphurpool-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atelier-sulphurpool.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/atlas.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/bespin.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/black-metal-bathory.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/black-metal-burzum.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/black-metal-dark-funeral.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/black-metal-gorgoroth.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/black-metal-immortal.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/black-metal-khold.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/black-metal-marduk.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/black-metal-mayhem.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/black-metal-nile.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/black-metal-venom.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/black-metal.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/brewer.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/bright.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/brogrammer.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/brush-trees-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/brush-trees.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/chalk.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/circus.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/classic-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/classic-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/codeschool.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/colors.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/cupcake.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/cupertino.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/danqing.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/darcula.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/dark-violet.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/darkmoss.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/darktooth.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/decaf.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/default-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/default-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/dirtysea.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/dracula.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/edge-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/edge-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/eighties.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/embers.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/equilibrium-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/equilibrium-gray-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/equilibrium-gray-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/equilibrium-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/espresso.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/eva-dim.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/eva.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/flat.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/framer.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/fruit-soda.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/gigavolt.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/github.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/google-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/google-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/grayscale-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/grayscale-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/green-screen.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/gruvbox-dark-hard.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/gruvbox-dark-medium.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/gruvbox-dark-pale.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/gruvbox-dark-soft.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/gruvbox-light-hard.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/gruvbox-light-medium.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/gruvbox-light-soft.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/hardcore.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/harmonic16-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/harmonic16-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/heetch-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/heetch-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/helios.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/hopscotch.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/horizon-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/horizon-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/humanoid-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/humanoid-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/ia-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/ia-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/icy-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/ir-black.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/isotope.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/kimber.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/london-tube.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/macintosh.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/marrakesh.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/materia.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/material-darker.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/material-lighter.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/material-palenight.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/material-vivid.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/material.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/mellow-purple.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/mexico-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/mocha.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/monokai.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/nebula.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/nord.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/nova.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/ocean.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/oceanicnext.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/one-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/onedark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/outrun-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/papercolor-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/papercolor-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/paraiso.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/pasque.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/phd.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/pico.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/pop.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/porple.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/qualia.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/railscasts.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/rebecca.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/ros-pine-dawn.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/ros-pine-moon.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/ros-pine.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/sagelight.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/sandcastle.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/seti-ui.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/shapeshifter.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/silk-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/silk-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/snazzy.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/solar-flare-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/solar-flare.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/solarized-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/solarized-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/spacemacs.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/summercamp.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/summerfruit-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/summerfruit-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/synth-midnight-terminal-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/synth-midnight-terminal-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/tango.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/tender.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/tomorrow-night.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/tomorrow.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/twilight.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/unikitty-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/unikitty-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/vulcan.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/windows-10-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/windows-10.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/windows-95-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/windows-95.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/windows-high-contrast-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/windows-high-contrast.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/windows-nt-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/windows-nt.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/woodland.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/xcode-dusk.scss create mode 100644 frontend/node_modules/highlight.js/scss/base16/zenburn.scss create mode 100644 frontend/node_modules/highlight.js/scss/brown-paper.scss create mode 100644 frontend/node_modules/highlight.js/scss/codepen-embed.scss create mode 100644 frontend/node_modules/highlight.js/scss/color-brewer.scss create mode 100644 frontend/node_modules/highlight.js/scss/cybertopia-cherry.scss create mode 100644 frontend/node_modules/highlight.js/scss/cybertopia-dimmer.scss create mode 100644 frontend/node_modules/highlight.js/scss/cybertopia-icecap.scss create mode 100644 frontend/node_modules/highlight.js/scss/cybertopia-saturated.scss create mode 100644 frontend/node_modules/highlight.js/scss/dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/default.scss create mode 100644 frontend/node_modules/highlight.js/scss/devibeans.scss create mode 100644 frontend/node_modules/highlight.js/scss/docco.scss create mode 100644 frontend/node_modules/highlight.js/scss/far.scss create mode 100644 frontend/node_modules/highlight.js/scss/felipec.scss create mode 100644 frontend/node_modules/highlight.js/scss/foundation.scss create mode 100644 frontend/node_modules/highlight.js/scss/github-dark-dimmed.scss create mode 100644 frontend/node_modules/highlight.js/scss/github-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/github.scss create mode 100644 frontend/node_modules/highlight.js/scss/gml.scss create mode 100644 frontend/node_modules/highlight.js/scss/googlecode.scss create mode 100644 frontend/node_modules/highlight.js/scss/gradient-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/gradient-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/grayscale.scss create mode 100644 frontend/node_modules/highlight.js/scss/hybrid.scss create mode 100644 frontend/node_modules/highlight.js/scss/idea.scss create mode 100644 frontend/node_modules/highlight.js/scss/intellij-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/ir-black.scss create mode 100644 frontend/node_modules/highlight.js/scss/isbl-editor-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/isbl-editor-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/kimbie-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/kimbie-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/lightfair.scss create mode 100644 frontend/node_modules/highlight.js/scss/lioshi.scss create mode 100644 frontend/node_modules/highlight.js/scss/magula.scss create mode 100644 frontend/node_modules/highlight.js/scss/mono-blue.scss create mode 100644 frontend/node_modules/highlight.js/scss/monokai-sublime.scss create mode 100644 frontend/node_modules/highlight.js/scss/monokai.scss create mode 100644 frontend/node_modules/highlight.js/scss/night-owl.scss create mode 100644 frontend/node_modules/highlight.js/scss/nnfx-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/nnfx-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/nord.scss create mode 100644 frontend/node_modules/highlight.js/scss/obsidian.scss create mode 100644 frontend/node_modules/highlight.js/scss/panda-syntax-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/panda-syntax-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/paraiso-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/paraiso-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/pojoaque.scss create mode 100644 frontend/node_modules/highlight.js/scss/purebasic.scss create mode 100644 frontend/node_modules/highlight.js/scss/qtcreator-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/qtcreator-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/rainbow.scss create mode 100644 frontend/node_modules/highlight.js/scss/rose-pine-dawn.scss create mode 100644 frontend/node_modules/highlight.js/scss/rose-pine-moon.scss create mode 100644 frontend/node_modules/highlight.js/scss/rose-pine.scss create mode 100644 frontend/node_modules/highlight.js/scss/routeros.scss create mode 100644 frontend/node_modules/highlight.js/scss/school-book.scss create mode 100644 frontend/node_modules/highlight.js/scss/shades-of-purple.scss create mode 100644 frontend/node_modules/highlight.js/scss/srcery.scss create mode 100644 frontend/node_modules/highlight.js/scss/stackoverflow-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/stackoverflow-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/sunburst.scss create mode 100644 frontend/node_modules/highlight.js/scss/tokyo-night-dark.scss create mode 100644 frontend/node_modules/highlight.js/scss/tokyo-night-light.scss create mode 100644 frontend/node_modules/highlight.js/scss/tomorrow-night-blue.scss create mode 100644 frontend/node_modules/highlight.js/scss/tomorrow-night-bright.scss create mode 100644 frontend/node_modules/highlight.js/scss/vs.scss create mode 100644 frontend/node_modules/highlight.js/scss/vs2015.scss create mode 100644 frontend/node_modules/highlight.js/scss/xcode.scss create mode 100644 frontend/node_modules/highlight.js/scss/xt256.scss create mode 100644 frontend/node_modules/highlight.js/styles/1c-light.css create mode 100644 frontend/node_modules/highlight.js/styles/1c-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/a11y-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/a11y-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/a11y-light.css create mode 100644 frontend/node_modules/highlight.js/styles/a11y-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/agate.css create mode 100644 frontend/node_modules/highlight.js/styles/agate.min.css create mode 100644 frontend/node_modules/highlight.js/styles/an-old-hope.css create mode 100644 frontend/node_modules/highlight.js/styles/an-old-hope.min.css create mode 100644 frontend/node_modules/highlight.js/styles/androidstudio.css create mode 100644 frontend/node_modules/highlight.js/styles/androidstudio.min.css create mode 100644 frontend/node_modules/highlight.js/styles/arduino-light.css create mode 100644 frontend/node_modules/highlight.js/styles/arduino-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/arta.css create mode 100644 frontend/node_modules/highlight.js/styles/arta.min.css create mode 100644 frontend/node_modules/highlight.js/styles/ascetic.css create mode 100644 frontend/node_modules/highlight.js/styles/ascetic.min.css create mode 100644 frontend/node_modules/highlight.js/styles/atom-one-dark-reasonable.css create mode 100644 frontend/node_modules/highlight.js/styles/atom-one-dark-reasonable.min.css create mode 100644 frontend/node_modules/highlight.js/styles/atom-one-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/atom-one-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/atom-one-light.css create mode 100644 frontend/node_modules/highlight.js/styles/atom-one-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/3024.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/3024.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/apathy.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/apathy.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/apprentice.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/apprentice.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ashes.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ashes.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-cave-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-cave-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-cave.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-cave.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-dune-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-dune-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-dune.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-dune.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-estuary-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-estuary-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-estuary.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-estuary.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-forest-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-forest-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-forest.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-forest.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-heath-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-heath-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-heath.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-heath.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-lakeside-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-lakeside-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-lakeside.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-lakeside.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-plateau-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-plateau-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-plateau.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-plateau.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-savanna-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-savanna-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-savanna.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-savanna.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-seaside-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-seaside-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-seaside.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-seaside.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-sulphurpool-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-sulphurpool-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-sulphurpool.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atelier-sulphurpool.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atlas.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/atlas.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/bespin.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/bespin.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-bathory.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-bathory.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-burzum.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-burzum.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-dark-funeral.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-dark-funeral.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-gorgoroth.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-gorgoroth.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-immortal.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-immortal.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-khold.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-khold.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-marduk.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-marduk.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-mayhem.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-mayhem.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-nile.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-nile.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-venom.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal-venom.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/black-metal.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/brewer.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/brewer.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/bright.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/bright.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/brogrammer.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/brogrammer.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/brush-trees-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/brush-trees-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/brush-trees.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/brush-trees.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/chalk.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/chalk.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/circus.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/circus.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/classic-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/classic-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/classic-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/classic-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/codeschool.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/codeschool.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/colors.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/colors.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/cupcake.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/cupcake.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/cupertino.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/cupertino.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/danqing.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/danqing.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/darcula.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/darcula.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/dark-violet.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/dark-violet.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/darkmoss.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/darkmoss.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/darktooth.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/darktooth.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/decaf.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/decaf.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/default-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/default-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/default-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/default-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/dirtysea.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/dirtysea.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/dracula.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/dracula.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/edge-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/edge-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/edge-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/edge-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/eighties.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/eighties.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/embers.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/embers.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/equilibrium-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/equilibrium-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/equilibrium-gray-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/equilibrium-gray-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/equilibrium-gray-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/equilibrium-gray-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/equilibrium-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/equilibrium-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/espresso.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/espresso.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/eva-dim.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/eva-dim.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/eva.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/eva.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/flat.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/flat.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/framer.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/framer.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/fruit-soda.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/fruit-soda.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gigavolt.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gigavolt.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/github.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/github.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/google-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/google-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/google-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/google-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/grayscale-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/grayscale-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/grayscale-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/grayscale-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/green-screen.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/green-screen.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-dark-hard.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-dark-hard.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-dark-medium.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-dark-medium.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-dark-pale.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-dark-pale.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-dark-soft.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-dark-soft.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-light-hard.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-light-hard.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-light-medium.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-light-medium.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-light-soft.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/gruvbox-light-soft.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/hardcore.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/hardcore.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/harmonic16-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/harmonic16-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/harmonic16-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/harmonic16-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/heetch-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/heetch-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/heetch-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/heetch-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/helios.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/helios.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/hopscotch.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/hopscotch.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/horizon-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/horizon-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/horizon-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/horizon-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/humanoid-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/humanoid-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/humanoid-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/humanoid-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ia-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ia-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ia-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ia-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/icy-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/icy-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ir-black.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ir-black.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/isotope.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/isotope.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/kimber.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/kimber.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/london-tube.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/london-tube.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/macintosh.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/macintosh.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/marrakesh.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/marrakesh.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/materia.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/materia.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/material-darker.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/material-darker.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/material-lighter.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/material-lighter.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/material-palenight.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/material-palenight.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/material-vivid.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/material-vivid.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/material.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/material.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/mellow-purple.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/mellow-purple.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/mexico-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/mexico-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/mocha.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/mocha.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/monokai.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/monokai.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/nebula.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/nebula.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/nord.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/nord.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/nova.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/nova.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ocean.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ocean.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/oceanicnext.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/oceanicnext.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/one-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/one-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/onedark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/onedark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/outrun-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/outrun-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/papercolor-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/papercolor-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/papercolor-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/papercolor-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/paraiso.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/paraiso.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/pasque.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/pasque.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/phd.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/phd.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/pico.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/pico.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/pop.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/pop.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/porple.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/porple.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/qualia.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/qualia.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/railscasts.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/railscasts.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/rebecca.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/rebecca.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ros-pine-dawn.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ros-pine-dawn.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ros-pine-moon.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ros-pine-moon.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ros-pine.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/ros-pine.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/sagelight.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/sagelight.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/sandcastle.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/sandcastle.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/seti-ui.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/seti-ui.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/shapeshifter.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/shapeshifter.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/silk-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/silk-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/silk-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/silk-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/snazzy.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/snazzy.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/solar-flare-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/solar-flare-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/solar-flare.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/solar-flare.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/solarized-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/solarized-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/solarized-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/solarized-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/spacemacs.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/spacemacs.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/summercamp.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/summercamp.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/summerfruit-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/summerfruit-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/summerfruit-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/summerfruit-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/synth-midnight-terminal-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/synth-midnight-terminal-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/synth-midnight-terminal-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/synth-midnight-terminal-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/tango.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/tango.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/tender.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/tender.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/tomorrow-night.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/tomorrow-night.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/tomorrow.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/tomorrow.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/twilight.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/twilight.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/unikitty-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/unikitty-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/unikitty-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/unikitty-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/vulcan.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/vulcan.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-10-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-10-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-10.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-10.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-95-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-95-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-95.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-95.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-high-contrast-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-high-contrast-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-high-contrast.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-high-contrast.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-nt-light.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-nt-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-nt.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/windows-nt.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/woodland.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/woodland.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/xcode-dusk.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/xcode-dusk.min.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/zenburn.css create mode 100644 frontend/node_modules/highlight.js/styles/base16/zenburn.min.css create mode 100644 frontend/node_modules/highlight.js/styles/brown-paper.css create mode 100644 frontend/node_modules/highlight.js/styles/brown-paper.min.css create mode 100644 frontend/node_modules/highlight.js/styles/brown-papersq.png create mode 100644 frontend/node_modules/highlight.js/styles/codepen-embed.css create mode 100644 frontend/node_modules/highlight.js/styles/codepen-embed.min.css create mode 100644 frontend/node_modules/highlight.js/styles/color-brewer.css create mode 100644 frontend/node_modules/highlight.js/styles/color-brewer.min.css create mode 100644 frontend/node_modules/highlight.js/styles/cybertopia-cherry.css create mode 100644 frontend/node_modules/highlight.js/styles/cybertopia-cherry.min.css create mode 100644 frontend/node_modules/highlight.js/styles/cybertopia-dimmer.css create mode 100644 frontend/node_modules/highlight.js/styles/cybertopia-dimmer.min.css create mode 100644 frontend/node_modules/highlight.js/styles/cybertopia-icecap.css create mode 100644 frontend/node_modules/highlight.js/styles/cybertopia-icecap.min.css create mode 100644 frontend/node_modules/highlight.js/styles/cybertopia-saturated.css create mode 100644 frontend/node_modules/highlight.js/styles/cybertopia-saturated.min.css create mode 100644 frontend/node_modules/highlight.js/styles/dark.css create mode 100644 frontend/node_modules/highlight.js/styles/dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/default.css create mode 100644 frontend/node_modules/highlight.js/styles/default.min.css create mode 100644 frontend/node_modules/highlight.js/styles/devibeans.css create mode 100644 frontend/node_modules/highlight.js/styles/devibeans.min.css create mode 100644 frontend/node_modules/highlight.js/styles/docco.css create mode 100644 frontend/node_modules/highlight.js/styles/docco.min.css create mode 100644 frontend/node_modules/highlight.js/styles/far.css create mode 100644 frontend/node_modules/highlight.js/styles/far.min.css create mode 100644 frontend/node_modules/highlight.js/styles/felipec.css create mode 100644 frontend/node_modules/highlight.js/styles/felipec.min.css create mode 100644 frontend/node_modules/highlight.js/styles/foundation.css create mode 100644 frontend/node_modules/highlight.js/styles/foundation.min.css create mode 100644 frontend/node_modules/highlight.js/styles/github-dark-dimmed.css create mode 100644 frontend/node_modules/highlight.js/styles/github-dark-dimmed.min.css create mode 100644 frontend/node_modules/highlight.js/styles/github-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/github-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/github.css create mode 100644 frontend/node_modules/highlight.js/styles/github.min.css create mode 100644 frontend/node_modules/highlight.js/styles/gml.css create mode 100644 frontend/node_modules/highlight.js/styles/gml.min.css create mode 100644 frontend/node_modules/highlight.js/styles/googlecode.css create mode 100644 frontend/node_modules/highlight.js/styles/googlecode.min.css create mode 100644 frontend/node_modules/highlight.js/styles/gradient-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/gradient-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/gradient-light.css create mode 100644 frontend/node_modules/highlight.js/styles/gradient-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/grayscale.css create mode 100644 frontend/node_modules/highlight.js/styles/grayscale.min.css create mode 100644 frontend/node_modules/highlight.js/styles/hybrid.css create mode 100644 frontend/node_modules/highlight.js/styles/hybrid.min.css create mode 100644 frontend/node_modules/highlight.js/styles/idea.css create mode 100644 frontend/node_modules/highlight.js/styles/idea.min.css create mode 100644 frontend/node_modules/highlight.js/styles/intellij-light.css create mode 100644 frontend/node_modules/highlight.js/styles/intellij-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/ir-black.css create mode 100644 frontend/node_modules/highlight.js/styles/ir-black.min.css create mode 100644 frontend/node_modules/highlight.js/styles/isbl-editor-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/isbl-editor-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/isbl-editor-light.css create mode 100644 frontend/node_modules/highlight.js/styles/isbl-editor-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/kimbie-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/kimbie-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/kimbie-light.css create mode 100644 frontend/node_modules/highlight.js/styles/kimbie-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/lightfair.css create mode 100644 frontend/node_modules/highlight.js/styles/lightfair.min.css create mode 100644 frontend/node_modules/highlight.js/styles/lioshi.css create mode 100644 frontend/node_modules/highlight.js/styles/lioshi.min.css create mode 100644 frontend/node_modules/highlight.js/styles/magula.css create mode 100644 frontend/node_modules/highlight.js/styles/magula.min.css create mode 100644 frontend/node_modules/highlight.js/styles/mono-blue.css create mode 100644 frontend/node_modules/highlight.js/styles/mono-blue.min.css create mode 100644 frontend/node_modules/highlight.js/styles/monokai-sublime.css create mode 100644 frontend/node_modules/highlight.js/styles/monokai-sublime.min.css create mode 100644 frontend/node_modules/highlight.js/styles/monokai.css create mode 100644 frontend/node_modules/highlight.js/styles/monokai.min.css create mode 100644 frontend/node_modules/highlight.js/styles/night-owl.css create mode 100644 frontend/node_modules/highlight.js/styles/night-owl.min.css create mode 100644 frontend/node_modules/highlight.js/styles/nnfx-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/nnfx-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/nnfx-light.css create mode 100644 frontend/node_modules/highlight.js/styles/nnfx-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/nord.css create mode 100644 frontend/node_modules/highlight.js/styles/nord.min.css create mode 100644 frontend/node_modules/highlight.js/styles/obsidian.css create mode 100644 frontend/node_modules/highlight.js/styles/obsidian.min.css create mode 100644 frontend/node_modules/highlight.js/styles/panda-syntax-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/panda-syntax-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/panda-syntax-light.css create mode 100644 frontend/node_modules/highlight.js/styles/panda-syntax-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/paraiso-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/paraiso-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/paraiso-light.css create mode 100644 frontend/node_modules/highlight.js/styles/paraiso-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/pojoaque.css create mode 100644 frontend/node_modules/highlight.js/styles/pojoaque.jpg create mode 100644 frontend/node_modules/highlight.js/styles/pojoaque.min.css create mode 100644 frontend/node_modules/highlight.js/styles/purebasic.css create mode 100644 frontend/node_modules/highlight.js/styles/purebasic.min.css create mode 100644 frontend/node_modules/highlight.js/styles/qtcreator-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/qtcreator-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/qtcreator-light.css create mode 100644 frontend/node_modules/highlight.js/styles/qtcreator-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/rainbow.css create mode 100644 frontend/node_modules/highlight.js/styles/rainbow.min.css create mode 100644 frontend/node_modules/highlight.js/styles/rose-pine-dawn.css create mode 100644 frontend/node_modules/highlight.js/styles/rose-pine-dawn.min.css create mode 100644 frontend/node_modules/highlight.js/styles/rose-pine-moon.css create mode 100644 frontend/node_modules/highlight.js/styles/rose-pine-moon.min.css create mode 100644 frontend/node_modules/highlight.js/styles/rose-pine.css create mode 100644 frontend/node_modules/highlight.js/styles/rose-pine.min.css create mode 100644 frontend/node_modules/highlight.js/styles/routeros.css create mode 100644 frontend/node_modules/highlight.js/styles/routeros.min.css create mode 100644 frontend/node_modules/highlight.js/styles/school-book.css create mode 100644 frontend/node_modules/highlight.js/styles/school-book.min.css create mode 100644 frontend/node_modules/highlight.js/styles/shades-of-purple.css create mode 100644 frontend/node_modules/highlight.js/styles/shades-of-purple.min.css create mode 100644 frontend/node_modules/highlight.js/styles/srcery.css create mode 100644 frontend/node_modules/highlight.js/styles/srcery.min.css create mode 100644 frontend/node_modules/highlight.js/styles/stackoverflow-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/stackoverflow-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/stackoverflow-light.css create mode 100644 frontend/node_modules/highlight.js/styles/stackoverflow-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/sunburst.css create mode 100644 frontend/node_modules/highlight.js/styles/sunburst.min.css create mode 100644 frontend/node_modules/highlight.js/styles/tokyo-night-dark.css create mode 100644 frontend/node_modules/highlight.js/styles/tokyo-night-dark.min.css create mode 100644 frontend/node_modules/highlight.js/styles/tokyo-night-light.css create mode 100644 frontend/node_modules/highlight.js/styles/tokyo-night-light.min.css create mode 100644 frontend/node_modules/highlight.js/styles/tomorrow-night-blue.css create mode 100644 frontend/node_modules/highlight.js/styles/tomorrow-night-blue.min.css create mode 100644 frontend/node_modules/highlight.js/styles/tomorrow-night-bright.css create mode 100644 frontend/node_modules/highlight.js/styles/tomorrow-night-bright.min.css create mode 100644 frontend/node_modules/highlight.js/styles/vs.css create mode 100644 frontend/node_modules/highlight.js/styles/vs.min.css create mode 100644 frontend/node_modules/highlight.js/styles/vs2015.css create mode 100644 frontend/node_modules/highlight.js/styles/vs2015.min.css create mode 100644 frontend/node_modules/highlight.js/styles/xcode.css create mode 100644 frontend/node_modules/highlight.js/styles/xcode.min.css create mode 100644 frontend/node_modules/highlight.js/styles/xt256.css create mode 100644 frontend/node_modules/highlight.js/styles/xt256.min.css create mode 100644 frontend/node_modules/highlight.js/types/index.d.ts create mode 100644 frontend/node_modules/htmlparser2/LICENSE create mode 100644 frontend/node_modules/htmlparser2/README.md create mode 100644 frontend/node_modules/htmlparser2/lib/Parser.d.ts create mode 100644 frontend/node_modules/htmlparser2/lib/Parser.d.ts.map create mode 100644 frontend/node_modules/htmlparser2/lib/Parser.js create mode 100644 frontend/node_modules/htmlparser2/lib/Parser.js.map create mode 100644 frontend/node_modules/htmlparser2/lib/Tokenizer.d.ts create mode 100644 frontend/node_modules/htmlparser2/lib/Tokenizer.d.ts.map create mode 100644 frontend/node_modules/htmlparser2/lib/Tokenizer.js create mode 100644 frontend/node_modules/htmlparser2/lib/Tokenizer.js.map create mode 100644 frontend/node_modules/htmlparser2/lib/WritableStream.d.ts create mode 100644 frontend/node_modules/htmlparser2/lib/WritableStream.d.ts.map create mode 100644 frontend/node_modules/htmlparser2/lib/WritableStream.js create mode 100644 frontend/node_modules/htmlparser2/lib/WritableStream.js.map create mode 100644 frontend/node_modules/htmlparser2/lib/esm/Parser.d.ts create mode 100644 frontend/node_modules/htmlparser2/lib/esm/Parser.d.ts.map create mode 100644 frontend/node_modules/htmlparser2/lib/esm/Parser.js create mode 100644 frontend/node_modules/htmlparser2/lib/esm/Parser.js.map create mode 100644 frontend/node_modules/htmlparser2/lib/esm/Tokenizer.d.ts create mode 100644 frontend/node_modules/htmlparser2/lib/esm/Tokenizer.d.ts.map create mode 100644 frontend/node_modules/htmlparser2/lib/esm/Tokenizer.js create mode 100644 frontend/node_modules/htmlparser2/lib/esm/Tokenizer.js.map create mode 100644 frontend/node_modules/htmlparser2/lib/esm/WritableStream.d.ts create mode 100644 frontend/node_modules/htmlparser2/lib/esm/WritableStream.d.ts.map create mode 100644 frontend/node_modules/htmlparser2/lib/esm/WritableStream.js create mode 100644 frontend/node_modules/htmlparser2/lib/esm/WritableStream.js.map create mode 100644 frontend/node_modules/htmlparser2/lib/esm/index.d.ts create mode 100644 frontend/node_modules/htmlparser2/lib/esm/index.d.ts.map create mode 100644 frontend/node_modules/htmlparser2/lib/esm/index.js create mode 100644 frontend/node_modules/htmlparser2/lib/esm/index.js.map create mode 100644 frontend/node_modules/htmlparser2/lib/esm/package.json create mode 100644 frontend/node_modules/htmlparser2/lib/index.d.ts create mode 100644 frontend/node_modules/htmlparser2/lib/index.d.ts.map create mode 100644 frontend/node_modules/htmlparser2/lib/index.js create mode 100644 frontend/node_modules/htmlparser2/lib/index.js.map create mode 100644 frontend/node_modules/htmlparser2/package.json create mode 100644 frontend/node_modules/iconv-lite/.github/dependabot.yml create mode 100644 frontend/node_modules/iconv-lite/.idea/codeStyles/Project.xml create mode 100644 frontend/node_modules/iconv-lite/.idea/codeStyles/codeStyleConfig.xml create mode 100644 frontend/node_modules/iconv-lite/.idea/iconv-lite.iml create mode 100644 frontend/node_modules/iconv-lite/.idea/inspectionProfiles/Project_Default.xml create mode 100644 frontend/node_modules/iconv-lite/.idea/modules.xml create mode 100644 frontend/node_modules/iconv-lite/.idea/vcs.xml create mode 100644 frontend/node_modules/iconv-lite/Changelog.md create mode 100644 frontend/node_modules/iconv-lite/LICENSE create mode 100644 frontend/node_modules/iconv-lite/README.md create mode 100644 frontend/node_modules/iconv-lite/encodings/dbcs-codec.js create mode 100644 frontend/node_modules/iconv-lite/encodings/dbcs-data.js create mode 100644 frontend/node_modules/iconv-lite/encodings/index.js create mode 100644 frontend/node_modules/iconv-lite/encodings/internal.js create mode 100644 frontend/node_modules/iconv-lite/encodings/sbcs-codec.js create mode 100644 frontend/node_modules/iconv-lite/encodings/sbcs-data-generated.js create mode 100644 frontend/node_modules/iconv-lite/encodings/sbcs-data.js create mode 100644 frontend/node_modules/iconv-lite/encodings/tables/big5-added.json create mode 100644 frontend/node_modules/iconv-lite/encodings/tables/cp936.json create mode 100644 frontend/node_modules/iconv-lite/encodings/tables/cp949.json create mode 100644 frontend/node_modules/iconv-lite/encodings/tables/cp950.json create mode 100644 frontend/node_modules/iconv-lite/encodings/tables/eucjp.json create mode 100644 frontend/node_modules/iconv-lite/encodings/tables/gb18030-ranges.json create mode 100644 frontend/node_modules/iconv-lite/encodings/tables/gbk-added.json create mode 100644 frontend/node_modules/iconv-lite/encodings/tables/shiftjis.json create mode 100644 frontend/node_modules/iconv-lite/encodings/utf16.js create mode 100644 frontend/node_modules/iconv-lite/encodings/utf32.js create mode 100644 frontend/node_modules/iconv-lite/encodings/utf7.js create mode 100644 frontend/node_modules/iconv-lite/lib/bom-handling.js create mode 100644 frontend/node_modules/iconv-lite/lib/index.d.ts create mode 100644 frontend/node_modules/iconv-lite/lib/index.js create mode 100644 frontend/node_modules/iconv-lite/lib/streams.js create mode 100644 frontend/node_modules/iconv-lite/package.json create mode 100644 frontend/node_modules/internmap/LICENSE create mode 100644 frontend/node_modules/internmap/README.md create mode 100644 frontend/node_modules/internmap/dist/internmap.js create mode 100644 frontend/node_modules/internmap/dist/internmap.min.js create mode 100644 frontend/node_modules/internmap/package.json create mode 100644 frontend/node_modules/internmap/src/index.js create mode 100644 frontend/node_modules/katex/LICENSE create mode 100644 frontend/node_modules/katex/README.md create mode 100755 frontend/node_modules/katex/cli.js create mode 100644 frontend/node_modules/katex/contrib/auto-render/README.md create mode 100644 frontend/node_modules/katex/contrib/auto-render/auto-render.js create mode 100644 frontend/node_modules/katex/contrib/auto-render/index.html create mode 100644 frontend/node_modules/katex/contrib/auto-render/splitAtDelimiters.js create mode 100644 frontend/node_modules/katex/contrib/auto-render/test/auto-render-spec.js create mode 100644 frontend/node_modules/katex/contrib/copy-tex/README.md create mode 100644 frontend/node_modules/katex/contrib/copy-tex/copy-tex.js create mode 100644 frontend/node_modules/katex/contrib/copy-tex/index.html create mode 100644 frontend/node_modules/katex/contrib/copy-tex/katex2tex.js create mode 100644 frontend/node_modules/katex/contrib/mathtex-script-type/README.md create mode 100644 frontend/node_modules/katex/contrib/mathtex-script-type/mathtex-script-type.js create mode 100644 frontend/node_modules/katex/contrib/mhchem/README.md create mode 100644 frontend/node_modules/katex/contrib/mhchem/mhchem.js create mode 100644 frontend/node_modules/katex/contrib/render-a11y-string/render-a11y-string.js create mode 100644 frontend/node_modules/katex/contrib/render-a11y-string/test/render-a11y-string-spec.js create mode 100644 frontend/node_modules/katex/dist/README.md create mode 100644 frontend/node_modules/katex/dist/contrib/auto-render.js create mode 100644 frontend/node_modules/katex/dist/contrib/auto-render.min.js create mode 100644 frontend/node_modules/katex/dist/contrib/auto-render.mjs create mode 100644 frontend/node_modules/katex/dist/contrib/copy-tex.js create mode 100644 frontend/node_modules/katex/dist/contrib/copy-tex.min.js create mode 100644 frontend/node_modules/katex/dist/contrib/copy-tex.mjs create mode 100644 frontend/node_modules/katex/dist/contrib/mathtex-script-type.js create mode 100644 frontend/node_modules/katex/dist/contrib/mathtex-script-type.min.js create mode 100644 frontend/node_modules/katex/dist/contrib/mathtex-script-type.mjs create mode 100644 frontend/node_modules/katex/dist/contrib/mhchem.js create mode 100644 frontend/node_modules/katex/dist/contrib/mhchem.min.js create mode 100644 frontend/node_modules/katex/dist/contrib/mhchem.mjs create mode 100644 frontend/node_modules/katex/dist/contrib/render-a11y-string.js create mode 100644 frontend/node_modules/katex/dist/contrib/render-a11y-string.min.js create mode 100644 frontend/node_modules/katex/dist/contrib/render-a11y-string.mjs create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_AMS-Regular.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_AMS-Regular.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_AMS-Regular.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Caligraphic-Bold.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Caligraphic-Bold.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Caligraphic-Bold.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Caligraphic-Regular.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Caligraphic-Regular.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Caligraphic-Regular.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Fraktur-Bold.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Fraktur-Bold.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Fraktur-Bold.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Fraktur-Regular.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Fraktur-Regular.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Fraktur-Regular.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Main-Bold.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Main-Bold.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Main-Bold.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Main-BoldItalic.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Main-BoldItalic.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Main-BoldItalic.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Main-Italic.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Main-Italic.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Main-Italic.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Main-Regular.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Main-Regular.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Main-Regular.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Math-BoldItalic.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Math-BoldItalic.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Math-BoldItalic.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Math-Italic.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Math-Italic.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Math-Italic.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Bold.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Bold.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Bold.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Italic.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Italic.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Italic.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Regular.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Regular.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Regular.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Script-Regular.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Script-Regular.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Script-Regular.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Size1-Regular.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Size1-Regular.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Size1-Regular.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Size2-Regular.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Size2-Regular.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Size2-Regular.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Size3-Regular.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Size3-Regular.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Size3-Regular.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Size4-Regular.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Size4-Regular.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Size4-Regular.woff2 create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Typewriter-Regular.ttf create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Typewriter-Regular.woff create mode 100644 frontend/node_modules/katex/dist/fonts/KaTeX_Typewriter-Regular.woff2 create mode 100644 frontend/node_modules/katex/dist/katex.css create mode 100644 frontend/node_modules/katex/dist/katex.js create mode 100644 frontend/node_modules/katex/dist/katex.min.css create mode 100644 frontend/node_modules/katex/dist/katex.min.js create mode 100644 frontend/node_modules/katex/dist/katex.mjs create mode 100644 frontend/node_modules/katex/katex.js create mode 100644 frontend/node_modules/katex/package.json create mode 100644 frontend/node_modules/katex/src/Lexer.js create mode 100644 frontend/node_modules/katex/src/MacroExpander.js create mode 100644 frontend/node_modules/katex/src/Namespace.js create mode 100644 frontend/node_modules/katex/src/Options.js create mode 100644 frontend/node_modules/katex/src/ParseError.js create mode 100644 frontend/node_modules/katex/src/Parser.js create mode 100644 frontend/node_modules/katex/src/Settings.js create mode 100644 frontend/node_modules/katex/src/SourceLocation.js create mode 100644 frontend/node_modules/katex/src/Style.js create mode 100644 frontend/node_modules/katex/src/Token.js create mode 100644 frontend/node_modules/katex/src/buildCommon.js create mode 100644 frontend/node_modules/katex/src/buildHTML.js create mode 100644 frontend/node_modules/katex/src/buildMathML.js create mode 100644 frontend/node_modules/katex/src/buildTree.js create mode 100644 frontend/node_modules/katex/src/defineEnvironment.js create mode 100644 frontend/node_modules/katex/src/defineFunction.js create mode 100644 frontend/node_modules/katex/src/defineMacro.js create mode 100644 frontend/node_modules/katex/src/delimiter.js create mode 100644 frontend/node_modules/katex/src/domTree.js create mode 100644 frontend/node_modules/katex/src/environments.js create mode 100644 frontend/node_modules/katex/src/environments/array.js create mode 100644 frontend/node_modules/katex/src/environments/cd.js create mode 100644 frontend/node_modules/katex/src/fontMetrics.js create mode 100644 frontend/node_modules/katex/src/fontMetricsData.js create mode 100644 frontend/node_modules/katex/src/fonts/Makefile create mode 100644 frontend/node_modules/katex/src/fonts/default.cfg create mode 100755 frontend/node_modules/katex/src/fonts/generate_fonts.py create mode 100644 frontend/node_modules/katex/src/fonts/lib/Extra.otf create mode 100644 frontend/node_modules/katex/src/fonts/lib/Space.ttx create mode 100755 frontend/node_modules/katex/src/fonts/makeBlacker create mode 100755 frontend/node_modules/katex/src/fonts/makeFF create mode 100644 frontend/node_modules/katex/src/fonts/xbbold.mf create mode 100644 frontend/node_modules/katex/src/functions.js create mode 100644 frontend/node_modules/katex/src/functions/accent.js create mode 100644 frontend/node_modules/katex/src/functions/accentunder.js create mode 100644 frontend/node_modules/katex/src/functions/arrow.js create mode 100644 frontend/node_modules/katex/src/functions/char.js create mode 100644 frontend/node_modules/katex/src/functions/color.js create mode 100644 frontend/node_modules/katex/src/functions/cr.js create mode 100644 frontend/node_modules/katex/src/functions/def.js create mode 100644 frontend/node_modules/katex/src/functions/delimsizing.js create mode 100644 frontend/node_modules/katex/src/functions/enclose.js create mode 100644 frontend/node_modules/katex/src/functions/environment.js create mode 100644 frontend/node_modules/katex/src/functions/font.js create mode 100644 frontend/node_modules/katex/src/functions/genfrac.js create mode 100644 frontend/node_modules/katex/src/functions/hbox.js create mode 100644 frontend/node_modules/katex/src/functions/horizBrace.js create mode 100644 frontend/node_modules/katex/src/functions/href.js create mode 100644 frontend/node_modules/katex/src/functions/html.js create mode 100644 frontend/node_modules/katex/src/functions/htmlmathml.js create mode 100644 frontend/node_modules/katex/src/functions/includegraphics.js create mode 100644 frontend/node_modules/katex/src/functions/kern.js create mode 100644 frontend/node_modules/katex/src/functions/lap.js create mode 100644 frontend/node_modules/katex/src/functions/math.js create mode 100644 frontend/node_modules/katex/src/functions/mathchoice.js create mode 100644 frontend/node_modules/katex/src/functions/mclass.js create mode 100644 frontend/node_modules/katex/src/functions/op.js create mode 100644 frontend/node_modules/katex/src/functions/operatorname.js create mode 100644 frontend/node_modules/katex/src/functions/ordgroup.js create mode 100644 frontend/node_modules/katex/src/functions/overline.js create mode 100644 frontend/node_modules/katex/src/functions/phantom.js create mode 100644 frontend/node_modules/katex/src/functions/pmb.js create mode 100644 frontend/node_modules/katex/src/functions/raisebox.js create mode 100644 frontend/node_modules/katex/src/functions/relax.js create mode 100644 frontend/node_modules/katex/src/functions/rule.js create mode 100644 frontend/node_modules/katex/src/functions/sizing.js create mode 100644 frontend/node_modules/katex/src/functions/smash.js create mode 100644 frontend/node_modules/katex/src/functions/sqrt.js create mode 100644 frontend/node_modules/katex/src/functions/styling.js create mode 100644 frontend/node_modules/katex/src/functions/supsub.js create mode 100644 frontend/node_modules/katex/src/functions/symbolsOp.js create mode 100644 frontend/node_modules/katex/src/functions/symbolsOrd.js create mode 100644 frontend/node_modules/katex/src/functions/symbolsSpacing.js create mode 100644 frontend/node_modules/katex/src/functions/tag.js create mode 100644 frontend/node_modules/katex/src/functions/text.js create mode 100644 frontend/node_modules/katex/src/functions/underline.js create mode 100644 frontend/node_modules/katex/src/functions/utils/assembleSupSub.js create mode 100644 frontend/node_modules/katex/src/functions/vcenter.js create mode 100644 frontend/node_modules/katex/src/functions/verb.js create mode 100644 frontend/node_modules/katex/src/macros.js create mode 100644 frontend/node_modules/katex/src/mathMLTree.js create mode 100644 frontend/node_modules/katex/src/metrics/README.md create mode 100755 frontend/node_modules/katex/src/metrics/extract_tfms.py create mode 100755 frontend/node_modules/katex/src/metrics/extract_ttfs.py create mode 100755 frontend/node_modules/katex/src/metrics/format_json.py create mode 100755 frontend/node_modules/katex/src/metrics/mapping.pl create mode 100644 frontend/node_modules/katex/src/metrics/parse_tfm.py create mode 100644 frontend/node_modules/katex/src/parseNode.js create mode 100644 frontend/node_modules/katex/src/parseTree.js create mode 100644 frontend/node_modules/katex/src/spacingData.js create mode 100644 frontend/node_modules/katex/src/stretchy.js create mode 100644 frontend/node_modules/katex/src/styles/fonts.scss create mode 100644 frontend/node_modules/katex/src/styles/katex.scss create mode 100644 frontend/node_modules/katex/src/svgGeometry.js create mode 100644 frontend/node_modules/katex/src/symbols.js create mode 100644 frontend/node_modules/katex/src/tree.js create mode 100644 frontend/node_modules/katex/src/types.js create mode 100644 frontend/node_modules/katex/src/unicodeAccents.js create mode 100644 frontend/node_modules/katex/src/unicodeScripts.js create mode 100644 frontend/node_modules/katex/src/unicodeSupOrSub.js create mode 100644 frontend/node_modules/katex/src/unicodeSymbols.js create mode 100644 frontend/node_modules/katex/src/units.js create mode 100644 frontend/node_modules/katex/src/utils.js create mode 100644 frontend/node_modules/katex/src/wide-character.js create mode 100644 frontend/node_modules/katex/types/katex.d.ts create mode 100644 frontend/node_modules/linkify-it/LICENSE create mode 100644 frontend/node_modules/linkify-it/README.md create mode 100644 frontend/node_modules/linkify-it/build/index.cjs.js create mode 100644 frontend/node_modules/linkify-it/index.mjs create mode 100644 frontend/node_modules/linkify-it/lib/re.mjs create mode 100644 frontend/node_modules/linkify-it/package.json create mode 100644 frontend/node_modules/markdown-it-ins/LICENSE create mode 100644 frontend/node_modules/markdown-it-ins/README.md create mode 100644 frontend/node_modules/markdown-it-ins/dist/index.cjs.js create mode 100644 frontend/node_modules/markdown-it-ins/dist/markdown-it-ins.js create mode 100644 frontend/node_modules/markdown-it-ins/dist/markdown-it-ins.min.js create mode 100644 frontend/node_modules/markdown-it-ins/index.mjs create mode 100644 frontend/node_modules/markdown-it-ins/package.json create mode 100644 frontend/node_modules/markdown-it-mark/LICENSE create mode 100644 frontend/node_modules/markdown-it-mark/README.md create mode 100644 frontend/node_modules/markdown-it-mark/dist/index.cjs.js create mode 100644 frontend/node_modules/markdown-it-mark/dist/markdown-it-mark.js create mode 100644 frontend/node_modules/markdown-it-mark/dist/markdown-it-mark.min.js create mode 100644 frontend/node_modules/markdown-it-mark/index.mjs create mode 100644 frontend/node_modules/markdown-it-mark/package.json create mode 100644 frontend/node_modules/markdown-it-sub/LICENSE create mode 100644 frontend/node_modules/markdown-it-sub/README.md create mode 100644 frontend/node_modules/markdown-it-sub/dist/index.cjs.js create mode 100644 frontend/node_modules/markdown-it-sub/dist/markdown-it-sub.js create mode 100644 frontend/node_modules/markdown-it-sub/dist/markdown-it-sub.min.js create mode 100644 frontend/node_modules/markdown-it-sub/index.mjs create mode 100644 frontend/node_modules/markdown-it-sub/package.json create mode 100644 frontend/node_modules/markdown-it-sup/LICENSE create mode 100644 frontend/node_modules/markdown-it-sup/README.md create mode 100644 frontend/node_modules/markdown-it-sup/dist/index.cjs.js create mode 100644 frontend/node_modules/markdown-it-sup/dist/markdown-it-sup.js create mode 100644 frontend/node_modules/markdown-it-sup/dist/markdown-it-sup.min.js create mode 100644 frontend/node_modules/markdown-it-sup/index.mjs create mode 100644 frontend/node_modules/markdown-it-sup/package.json create mode 100644 frontend/node_modules/markdown-it/LICENSE create mode 100644 frontend/node_modules/markdown-it/README.md create mode 100755 frontend/node_modules/markdown-it/bin/markdown-it.mjs create mode 100644 frontend/node_modules/markdown-it/dist/index.cjs.js create mode 100644 frontend/node_modules/markdown-it/dist/markdown-it.js create mode 100644 frontend/node_modules/markdown-it/dist/markdown-it.min.js create mode 100644 frontend/node_modules/markdown-it/index.mjs create mode 100644 frontend/node_modules/markdown-it/lib/common/html_blocks.mjs create mode 100644 frontend/node_modules/markdown-it/lib/common/html_re.mjs create mode 100644 frontend/node_modules/markdown-it/lib/common/utils.mjs create mode 100644 frontend/node_modules/markdown-it/lib/helpers/index.mjs create mode 100644 frontend/node_modules/markdown-it/lib/helpers/parse_link_destination.mjs create mode 100644 frontend/node_modules/markdown-it/lib/helpers/parse_link_label.mjs create mode 100644 frontend/node_modules/markdown-it/lib/helpers/parse_link_title.mjs create mode 100644 frontend/node_modules/markdown-it/lib/index.mjs create mode 100644 frontend/node_modules/markdown-it/lib/parser_block.mjs create mode 100644 frontend/node_modules/markdown-it/lib/parser_core.mjs create mode 100644 frontend/node_modules/markdown-it/lib/parser_inline.mjs create mode 100644 frontend/node_modules/markdown-it/lib/presets/commonmark.mjs create mode 100644 frontend/node_modules/markdown-it/lib/presets/default.mjs create mode 100644 frontend/node_modules/markdown-it/lib/presets/zero.mjs create mode 100644 frontend/node_modules/markdown-it/lib/renderer.mjs create mode 100644 frontend/node_modules/markdown-it/lib/ruler.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_block/blockquote.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_block/code.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_block/fence.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_block/heading.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_block/hr.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_block/html_block.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_block/lheading.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_block/list.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_block/paragraph.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_block/reference.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_block/state_block.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_block/table.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_core/block.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_core/inline.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_core/linkify.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_core/normalize.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_core/replacements.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_core/smartquotes.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_core/state_core.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_core/text_join.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/autolink.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/backticks.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/balance_pairs.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/emphasis.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/entity.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/escape.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/fragments_join.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/html_inline.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/image.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/link.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/linkify.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/newline.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/state_inline.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/strikethrough.mjs create mode 100644 frontend/node_modules/markdown-it/lib/rules_inline/text.mjs create mode 100644 frontend/node_modules/markdown-it/lib/token.mjs create mode 100644 frontend/node_modules/markdown-it/node_modules/argparse/CHANGELOG.md create mode 100644 frontend/node_modules/markdown-it/node_modules/argparse/LICENSE create mode 100644 frontend/node_modules/markdown-it/node_modules/argparse/README.md create mode 100644 frontend/node_modules/markdown-it/node_modules/argparse/argparse.js create mode 100644 frontend/node_modules/markdown-it/node_modules/argparse/lib/sub.js create mode 100644 frontend/node_modules/markdown-it/node_modules/argparse/lib/textwrap.js create mode 100644 frontend/node_modules/markdown-it/node_modules/argparse/package.json create mode 100644 frontend/node_modules/markdown-it/package.json create mode 100644 frontend/node_modules/markmap-common/LICENSE create mode 100644 frontend/node_modules/markmap-common/README.md create mode 100644 frontend/node_modules/markmap-common/dist/hook.d.ts create mode 100644 frontend/node_modules/markmap-common/dist/html.d.ts create mode 100644 frontend/node_modules/markmap-common/dist/index.d.ts create mode 100644 frontend/node_modules/markmap-common/dist/index.js create mode 100644 frontend/node_modules/markmap-common/dist/index.mjs create mode 100644 frontend/node_modules/markmap-common/dist/loader.d.ts create mode 100644 frontend/node_modules/markmap-common/dist/types/common.d.ts create mode 100644 frontend/node_modules/markmap-common/dist/types/index.d.ts create mode 100644 frontend/node_modules/markmap-common/dist/util.d.ts create mode 100644 frontend/node_modules/markmap-common/package.json create mode 100644 frontend/node_modules/markmap-html-parser/LICENSE create mode 100644 frontend/node_modules/markmap-html-parser/README.md create mode 100644 frontend/node_modules/markmap-html-parser/dist/index.d.ts create mode 100644 frontend/node_modules/markmap-html-parser/dist/index.js create mode 100644 frontend/node_modules/markmap-html-parser/dist/index.mjs create mode 100644 frontend/node_modules/markmap-html-parser/package.json create mode 100644 frontend/node_modules/markmap-lib/LICENSE create mode 100644 frontend/node_modules/markmap-lib/README.md create mode 100644 frontend/node_modules/markmap-lib/dist/browser/index.iife.js create mode 100644 frontend/node_modules/markmap-lib/dist/browser/index.mjs create mode 100644 frontend/node_modules/markmap-lib/dist/index.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/index.js create mode 100644 frontend/node_modules/markmap-lib/dist/index.mjs create mode 100644 frontend/node_modules/markmap-lib/dist/index.no-plugins.js create mode 100644 frontend/node_modules/markmap-lib/dist/index.no-plugins.mjs create mode 100644 frontend/node_modules/markmap-lib/dist/markdown-it.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins.js create mode 100644 frontend/node_modules/markmap-lib/dist/plugins.mjs create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/base.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/checkbox/index.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/frontmatter/index.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/hljs/config.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/hljs/index.browser.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/hljs/index.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/index.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/katex/config.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/katex/index.browser.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/katex/index.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/katex/vendor.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/npm-url/index.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/prism/config.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/prism/index.browser.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/prism/index.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/source-lines/index.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/plugins/util.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/transform.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/types.d.ts create mode 100644 frontend/node_modules/markmap-lib/dist/util.d.ts create mode 100644 frontend/node_modules/markmap-lib/package.json create mode 100644 frontend/node_modules/markmap-view/LICENSE create mode 100644 frontend/node_modules/markmap-view/README.md create mode 100644 frontend/node_modules/markmap-view/dist/browser/index.js create mode 100644 frontend/node_modules/markmap-view/dist/constants.d.ts create mode 100644 frontend/node_modules/markmap-view/dist/index.d.ts create mode 100644 frontend/node_modules/markmap-view/dist/index.js create mode 100644 frontend/node_modules/markmap-view/dist/types.d.ts create mode 100644 frontend/node_modules/markmap-view/dist/util.d.ts create mode 100644 frontend/node_modules/markmap-view/dist/view.d.ts create mode 100644 frontend/node_modules/markmap-view/package.json create mode 100644 frontend/node_modules/mdurl/LICENSE create mode 100644 frontend/node_modules/mdurl/README.md create mode 100644 frontend/node_modules/mdurl/build/index.cjs.js create mode 100644 frontend/node_modules/mdurl/index.mjs create mode 100644 frontend/node_modules/mdurl/lib/decode.mjs create mode 100644 frontend/node_modules/mdurl/lib/encode.mjs create mode 100644 frontend/node_modules/mdurl/lib/format.mjs create mode 100644 frontend/node_modules/mdurl/lib/parse.mjs create mode 100644 frontend/node_modules/mdurl/package.json delete mode 100644 frontend/node_modules/mind-elixir/dist/MindElixir.iife.js delete mode 100644 frontend/node_modules/mind-elixir/dist/MindElixir.js delete mode 100644 frontend/node_modules/mind-elixir/dist/MindElixirLite.iife.js delete mode 100644 frontend/node_modules/mind-elixir/dist/MindElixirLite.js delete mode 100644 frontend/node_modules/mind-elixir/dist/example.iife.js delete mode 100644 frontend/node_modules/mind-elixir/dist/example.js delete mode 100644 frontend/node_modules/mind-elixir/dist/types/const.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/customLink.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/docs.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/exampleData/1.cn.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/exampleData/1.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/exampleData/2.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/exampleData/3.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/i18n.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/index.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/interact.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/linkDiv.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/methods.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/mouse.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/nodeOperation.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/plugin/contextMenu.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/plugin/exportImage.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/plugin/keypress.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/plugin/mobileMenu.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/plugin/nodeDraggable.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/plugin/operationHistory.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/plugin/selection.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/plugin/toolBar.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/summary.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/types/dom.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/types/global.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/types/index.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/utils/LinkDragMoveHelper.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/utils/dom.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/utils/domManipulation.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/utils/dragMoveHelper.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/utils/index.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/utils/layout.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/utils/objectManipulation.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/utils/pubsub.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/utils/svg.d.ts delete mode 100644 frontend/node_modules/mind-elixir/dist/types/utils/theme.d.ts delete mode 100644 frontend/node_modules/mind-elixir/readme.cn.md create mode 100644 frontend/node_modules/npm2url/LICENSE create mode 100644 frontend/node_modules/npm2url/README.md create mode 100644 frontend/node_modules/npm2url/dist/index.cjs create mode 100644 frontend/node_modules/npm2url/dist/index.d.ts create mode 100644 frontend/node_modules/npm2url/dist/index.mjs create mode 100644 frontend/node_modules/npm2url/package.json create mode 100644 frontend/node_modules/nth-check/LICENSE create mode 100644 frontend/node_modules/nth-check/README.md create mode 100644 frontend/node_modules/nth-check/lib/compile.d.ts create mode 100644 frontend/node_modules/nth-check/lib/compile.d.ts.map create mode 100644 frontend/node_modules/nth-check/lib/compile.js create mode 100644 frontend/node_modules/nth-check/lib/compile.js.map create mode 100644 frontend/node_modules/nth-check/lib/esm/compile.d.ts create mode 100644 frontend/node_modules/nth-check/lib/esm/compile.d.ts.map create mode 100644 frontend/node_modules/nth-check/lib/esm/compile.js create mode 100644 frontend/node_modules/nth-check/lib/esm/compile.js.map create mode 100644 frontend/node_modules/nth-check/lib/esm/index.d.ts create mode 100644 frontend/node_modules/nth-check/lib/esm/index.d.ts.map create mode 100644 frontend/node_modules/nth-check/lib/esm/index.js create mode 100644 frontend/node_modules/nth-check/lib/esm/index.js.map create mode 100644 frontend/node_modules/nth-check/lib/esm/package.json create mode 100644 frontend/node_modules/nth-check/lib/esm/parse.d.ts create mode 100644 frontend/node_modules/nth-check/lib/esm/parse.d.ts.map create mode 100644 frontend/node_modules/nth-check/lib/esm/parse.js create mode 100644 frontend/node_modules/nth-check/lib/esm/parse.js.map create mode 100644 frontend/node_modules/nth-check/lib/index.d.ts create mode 100644 frontend/node_modules/nth-check/lib/index.d.ts.map create mode 100644 frontend/node_modules/nth-check/lib/index.js create mode 100644 frontend/node_modules/nth-check/lib/index.js.map create mode 100644 frontend/node_modules/nth-check/lib/parse.d.ts create mode 100644 frontend/node_modules/nth-check/lib/parse.d.ts.map create mode 100644 frontend/node_modules/nth-check/lib/parse.js create mode 100644 frontend/node_modules/nth-check/lib/parse.js.map create mode 100644 frontend/node_modules/nth-check/package.json create mode 100644 frontend/node_modules/parse5-htmlparser2-tree-adapter/LICENSE create mode 100644 frontend/node_modules/parse5-htmlparser2-tree-adapter/README.md create mode 100644 frontend/node_modules/parse5-htmlparser2-tree-adapter/dist/cjs/index.d.ts create mode 100644 frontend/node_modules/parse5-htmlparser2-tree-adapter/dist/cjs/index.js create mode 100644 frontend/node_modules/parse5-htmlparser2-tree-adapter/dist/cjs/package.json create mode 100644 frontend/node_modules/parse5-htmlparser2-tree-adapter/dist/index.d.ts create mode 100644 frontend/node_modules/parse5-htmlparser2-tree-adapter/dist/index.js create mode 100644 frontend/node_modules/parse5-htmlparser2-tree-adapter/package.json create mode 100644 frontend/node_modules/parse5-parser-stream/LICENSE create mode 100644 frontend/node_modules/parse5-parser-stream/README.md create mode 100644 frontend/node_modules/parse5-parser-stream/dist/cjs/index.d.ts create mode 100644 frontend/node_modules/parse5-parser-stream/dist/cjs/index.js create mode 100644 frontend/node_modules/parse5-parser-stream/dist/cjs/package.json create mode 100644 frontend/node_modules/parse5-parser-stream/dist/index.d.ts create mode 100644 frontend/node_modules/parse5-parser-stream/dist/index.js create mode 100644 frontend/node_modules/parse5-parser-stream/package.json create mode 100644 frontend/node_modules/parse5/LICENSE create mode 100644 frontend/node_modules/parse5/README.md create mode 100644 frontend/node_modules/parse5/dist/cjs/common/doctype.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/common/doctype.js create mode 100644 frontend/node_modules/parse5/dist/cjs/common/error-codes.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/common/error-codes.js create mode 100644 frontend/node_modules/parse5/dist/cjs/common/foreign-content.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/common/foreign-content.js create mode 100644 frontend/node_modules/parse5/dist/cjs/common/html.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/common/html.js create mode 100644 frontend/node_modules/parse5/dist/cjs/common/token.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/common/token.js create mode 100644 frontend/node_modules/parse5/dist/cjs/common/unicode.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/common/unicode.js create mode 100644 frontend/node_modules/parse5/dist/cjs/index.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/index.js create mode 100644 frontend/node_modules/parse5/dist/cjs/package.json create mode 100644 frontend/node_modules/parse5/dist/cjs/parser/formatting-element-list.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/parser/formatting-element-list.js create mode 100644 frontend/node_modules/parse5/dist/cjs/parser/index.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/parser/index.js create mode 100644 frontend/node_modules/parse5/dist/cjs/parser/open-element-stack.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/parser/open-element-stack.js create mode 100644 frontend/node_modules/parse5/dist/cjs/serializer/index.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/serializer/index.js create mode 100644 frontend/node_modules/parse5/dist/cjs/tokenizer/index.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/tokenizer/index.js create mode 100644 frontend/node_modules/parse5/dist/cjs/tokenizer/preprocessor.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/tokenizer/preprocessor.js create mode 100644 frontend/node_modules/parse5/dist/cjs/tree-adapters/default.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/tree-adapters/default.js create mode 100644 frontend/node_modules/parse5/dist/cjs/tree-adapters/interface.d.ts create mode 100644 frontend/node_modules/parse5/dist/cjs/tree-adapters/interface.js create mode 100644 frontend/node_modules/parse5/dist/common/doctype.d.ts create mode 100644 frontend/node_modules/parse5/dist/common/doctype.js create mode 100644 frontend/node_modules/parse5/dist/common/error-codes.d.ts create mode 100644 frontend/node_modules/parse5/dist/common/error-codes.js create mode 100644 frontend/node_modules/parse5/dist/common/foreign-content.d.ts create mode 100644 frontend/node_modules/parse5/dist/common/foreign-content.js create mode 100644 frontend/node_modules/parse5/dist/common/html.d.ts create mode 100644 frontend/node_modules/parse5/dist/common/html.js create mode 100644 frontend/node_modules/parse5/dist/common/token.d.ts create mode 100644 frontend/node_modules/parse5/dist/common/token.js create mode 100644 frontend/node_modules/parse5/dist/common/unicode.d.ts create mode 100644 frontend/node_modules/parse5/dist/common/unicode.js create mode 100644 frontend/node_modules/parse5/dist/index.d.ts create mode 100644 frontend/node_modules/parse5/dist/index.js create mode 100644 frontend/node_modules/parse5/dist/parser/formatting-element-list.d.ts create mode 100644 frontend/node_modules/parse5/dist/parser/formatting-element-list.js create mode 100644 frontend/node_modules/parse5/dist/parser/index.d.ts create mode 100644 frontend/node_modules/parse5/dist/parser/index.js create mode 100644 frontend/node_modules/parse5/dist/parser/open-element-stack.d.ts create mode 100644 frontend/node_modules/parse5/dist/parser/open-element-stack.js create mode 100644 frontend/node_modules/parse5/dist/serializer/index.d.ts create mode 100644 frontend/node_modules/parse5/dist/serializer/index.js create mode 100644 frontend/node_modules/parse5/dist/tokenizer/index.d.ts create mode 100644 frontend/node_modules/parse5/dist/tokenizer/index.js create mode 100644 frontend/node_modules/parse5/dist/tokenizer/preprocessor.d.ts create mode 100644 frontend/node_modules/parse5/dist/tokenizer/preprocessor.js create mode 100644 frontend/node_modules/parse5/dist/tree-adapters/default.d.ts create mode 100644 frontend/node_modules/parse5/dist/tree-adapters/default.js create mode 100644 frontend/node_modules/parse5/dist/tree-adapters/interface.d.ts rename frontend/node_modules/{mind-elixir/dist/types/dev.d.ts => parse5/dist/tree-adapters/interface.js} (100%) create mode 100644 frontend/node_modules/parse5/node_modules/entities/LICENSE create mode 100644 frontend/node_modules/parse5/node_modules/entities/decode.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/decode.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/decode-codepoint.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/decode-codepoint.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/decode-codepoint.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/decode-codepoint.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/decode.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/decode.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/decode.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/decode.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/encode.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/encode.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/encode.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/encode.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/escape.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/escape.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/escape.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/escape.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/generated/decode-data-html.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/generated/decode-data-html.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/generated/decode-data-html.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/generated/decode-data-html.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/generated/decode-data-xml.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/generated/decode-data-xml.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/generated/decode-data-xml.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/generated/decode-data-xml.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/generated/encode-html.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/generated/encode-html.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/generated/encode-html.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/generated/encode-html.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/index.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/index.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/index.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/index.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/commonjs/package.json create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/decode-codepoint.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/decode-codepoint.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/decode-codepoint.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/decode-codepoint.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/decode.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/decode.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/decode.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/decode.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/encode.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/encode.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/encode.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/encode.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/escape.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/escape.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/escape.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/escape.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/generated/decode-data-html.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/generated/decode-data-html.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/generated/decode-data-html.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/generated/decode-data-html.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/generated/decode-data-xml.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/generated/decode-data-xml.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/generated/decode-data-xml.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/generated/decode-data-xml.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/generated/encode-html.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/generated/encode-html.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/generated/encode-html.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/generated/encode-html.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/index.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/index.d.ts.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/index.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/index.js.map create mode 100644 frontend/node_modules/parse5/node_modules/entities/dist/esm/package.json create mode 100644 frontend/node_modules/parse5/node_modules/entities/escape.d.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/escape.js create mode 100644 frontend/node_modules/parse5/node_modules/entities/package.json create mode 100644 frontend/node_modules/parse5/node_modules/entities/readme.md create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/decode-codepoint.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/decode.spec.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/decode.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/encode.spec.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/encode.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/escape.spec.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/escape.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/generated/.eslintrc.json create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/generated/decode-data-html.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/generated/decode-data-xml.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/generated/encode-html.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/index.spec.ts create mode 100644 frontend/node_modules/parse5/node_modules/entities/src/index.ts create mode 100644 frontend/node_modules/parse5/package.json create mode 100644 frontend/node_modules/prismjs/CHANGELOG.md create mode 100644 frontend/node_modules/prismjs/LICENSE create mode 100644 frontend/node_modules/prismjs/README.md create mode 100644 frontend/node_modules/prismjs/_headers create mode 100644 frontend/node_modules/prismjs/components.js create mode 100644 frontend/node_modules/prismjs/components.json create mode 100644 frontend/node_modules/prismjs/components/index.js create mode 100644 frontend/node_modules/prismjs/components/prism-abap.js create mode 100644 frontend/node_modules/prismjs/components/prism-abap.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-abnf.js create mode 100644 frontend/node_modules/prismjs/components/prism-abnf.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-actionscript.js create mode 100644 frontend/node_modules/prismjs/components/prism-actionscript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-ada.js create mode 100644 frontend/node_modules/prismjs/components/prism-ada.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-agda.js create mode 100644 frontend/node_modules/prismjs/components/prism-agda.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-al.js create mode 100644 frontend/node_modules/prismjs/components/prism-al.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-antlr4.js create mode 100644 frontend/node_modules/prismjs/components/prism-antlr4.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-apacheconf.js create mode 100644 frontend/node_modules/prismjs/components/prism-apacheconf.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-apex.js create mode 100644 frontend/node_modules/prismjs/components/prism-apex.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-apl.js create mode 100644 frontend/node_modules/prismjs/components/prism-apl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-applescript.js create mode 100644 frontend/node_modules/prismjs/components/prism-applescript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-aql.js create mode 100644 frontend/node_modules/prismjs/components/prism-aql.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-arduino.js create mode 100644 frontend/node_modules/prismjs/components/prism-arduino.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-arff.js create mode 100644 frontend/node_modules/prismjs/components/prism-arff.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-armasm.js create mode 100644 frontend/node_modules/prismjs/components/prism-armasm.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-arturo.js create mode 100644 frontend/node_modules/prismjs/components/prism-arturo.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-asciidoc.js create mode 100644 frontend/node_modules/prismjs/components/prism-asciidoc.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-asm6502.js create mode 100644 frontend/node_modules/prismjs/components/prism-asm6502.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-asmatmel.js create mode 100644 frontend/node_modules/prismjs/components/prism-asmatmel.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-aspnet.js create mode 100644 frontend/node_modules/prismjs/components/prism-aspnet.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-autohotkey.js create mode 100644 frontend/node_modules/prismjs/components/prism-autohotkey.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-autoit.js create mode 100644 frontend/node_modules/prismjs/components/prism-autoit.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-avisynth.js create mode 100644 frontend/node_modules/prismjs/components/prism-avisynth.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-avro-idl.js create mode 100644 frontend/node_modules/prismjs/components/prism-avro-idl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-awk.js create mode 100644 frontend/node_modules/prismjs/components/prism-awk.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-bash.js create mode 100644 frontend/node_modules/prismjs/components/prism-bash.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-basic.js create mode 100644 frontend/node_modules/prismjs/components/prism-basic.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-batch.js create mode 100644 frontend/node_modules/prismjs/components/prism-batch.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-bbcode.js create mode 100644 frontend/node_modules/prismjs/components/prism-bbcode.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-bbj.js create mode 100644 frontend/node_modules/prismjs/components/prism-bbj.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-bicep.js create mode 100644 frontend/node_modules/prismjs/components/prism-bicep.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-birb.js create mode 100644 frontend/node_modules/prismjs/components/prism-birb.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-bison.js create mode 100644 frontend/node_modules/prismjs/components/prism-bison.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-bnf.js create mode 100644 frontend/node_modules/prismjs/components/prism-bnf.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-bqn.js create mode 100644 frontend/node_modules/prismjs/components/prism-bqn.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-brainfuck.js create mode 100644 frontend/node_modules/prismjs/components/prism-brainfuck.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-brightscript.js create mode 100644 frontend/node_modules/prismjs/components/prism-brightscript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-bro.js create mode 100644 frontend/node_modules/prismjs/components/prism-bro.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-bsl.js create mode 100644 frontend/node_modules/prismjs/components/prism-bsl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-c.js create mode 100644 frontend/node_modules/prismjs/components/prism-c.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-cfscript.js create mode 100644 frontend/node_modules/prismjs/components/prism-cfscript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-chaiscript.js create mode 100644 frontend/node_modules/prismjs/components/prism-chaiscript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-cil.js create mode 100644 frontend/node_modules/prismjs/components/prism-cil.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-cilkc.js create mode 100644 frontend/node_modules/prismjs/components/prism-cilkc.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-cilkcpp.js create mode 100644 frontend/node_modules/prismjs/components/prism-cilkcpp.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-clike.js create mode 100644 frontend/node_modules/prismjs/components/prism-clike.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-clojure.js create mode 100644 frontend/node_modules/prismjs/components/prism-clojure.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-cmake.js create mode 100644 frontend/node_modules/prismjs/components/prism-cmake.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-cobol.js create mode 100644 frontend/node_modules/prismjs/components/prism-cobol.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-coffeescript.js create mode 100644 frontend/node_modules/prismjs/components/prism-coffeescript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-concurnas.js create mode 100644 frontend/node_modules/prismjs/components/prism-concurnas.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-cooklang.js create mode 100644 frontend/node_modules/prismjs/components/prism-cooklang.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-coq.js create mode 100644 frontend/node_modules/prismjs/components/prism-coq.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-core.js create mode 100644 frontend/node_modules/prismjs/components/prism-core.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-cpp.js create mode 100644 frontend/node_modules/prismjs/components/prism-cpp.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-crystal.js create mode 100644 frontend/node_modules/prismjs/components/prism-crystal.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-csharp.js create mode 100644 frontend/node_modules/prismjs/components/prism-csharp.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-cshtml.js create mode 100644 frontend/node_modules/prismjs/components/prism-cshtml.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-csp.js create mode 100644 frontend/node_modules/prismjs/components/prism-csp.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-css-extras.js create mode 100644 frontend/node_modules/prismjs/components/prism-css-extras.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-css.js create mode 100644 frontend/node_modules/prismjs/components/prism-css.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-csv.js create mode 100644 frontend/node_modules/prismjs/components/prism-csv.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-cue.js create mode 100644 frontend/node_modules/prismjs/components/prism-cue.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-cypher.js create mode 100644 frontend/node_modules/prismjs/components/prism-cypher.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-d.js create mode 100644 frontend/node_modules/prismjs/components/prism-d.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-dart.js create mode 100644 frontend/node_modules/prismjs/components/prism-dart.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-dataweave.js create mode 100644 frontend/node_modules/prismjs/components/prism-dataweave.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-dax.js create mode 100644 frontend/node_modules/prismjs/components/prism-dax.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-dhall.js create mode 100644 frontend/node_modules/prismjs/components/prism-dhall.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-diff.js create mode 100644 frontend/node_modules/prismjs/components/prism-diff.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-django.js create mode 100644 frontend/node_modules/prismjs/components/prism-django.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-dns-zone-file.js create mode 100644 frontend/node_modules/prismjs/components/prism-dns-zone-file.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-docker.js create mode 100644 frontend/node_modules/prismjs/components/prism-docker.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-dot.js create mode 100644 frontend/node_modules/prismjs/components/prism-dot.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-ebnf.js create mode 100644 frontend/node_modules/prismjs/components/prism-ebnf.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-editorconfig.js create mode 100644 frontend/node_modules/prismjs/components/prism-editorconfig.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-eiffel.js create mode 100644 frontend/node_modules/prismjs/components/prism-eiffel.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-ejs.js create mode 100644 frontend/node_modules/prismjs/components/prism-ejs.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-elixir.js create mode 100644 frontend/node_modules/prismjs/components/prism-elixir.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-elm.js create mode 100644 frontend/node_modules/prismjs/components/prism-elm.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-erb.js create mode 100644 frontend/node_modules/prismjs/components/prism-erb.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-erlang.js create mode 100644 frontend/node_modules/prismjs/components/prism-erlang.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-etlua.js create mode 100644 frontend/node_modules/prismjs/components/prism-etlua.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-excel-formula.js create mode 100644 frontend/node_modules/prismjs/components/prism-excel-formula.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-factor.js create mode 100644 frontend/node_modules/prismjs/components/prism-factor.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-false.js create mode 100644 frontend/node_modules/prismjs/components/prism-false.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-firestore-security-rules.js create mode 100644 frontend/node_modules/prismjs/components/prism-firestore-security-rules.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-flow.js create mode 100644 frontend/node_modules/prismjs/components/prism-flow.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-fortran.js create mode 100644 frontend/node_modules/prismjs/components/prism-fortran.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-fsharp.js create mode 100644 frontend/node_modules/prismjs/components/prism-fsharp.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-ftl.js create mode 100644 frontend/node_modules/prismjs/components/prism-ftl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-gap.js create mode 100644 frontend/node_modules/prismjs/components/prism-gap.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-gcode.js create mode 100644 frontend/node_modules/prismjs/components/prism-gcode.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-gdscript.js create mode 100644 frontend/node_modules/prismjs/components/prism-gdscript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-gedcom.js create mode 100644 frontend/node_modules/prismjs/components/prism-gedcom.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-gettext.js create mode 100644 frontend/node_modules/prismjs/components/prism-gettext.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-gherkin.js create mode 100644 frontend/node_modules/prismjs/components/prism-gherkin.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-git.js create mode 100644 frontend/node_modules/prismjs/components/prism-git.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-glsl.js create mode 100644 frontend/node_modules/prismjs/components/prism-glsl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-gml.js create mode 100644 frontend/node_modules/prismjs/components/prism-gml.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-gn.js create mode 100644 frontend/node_modules/prismjs/components/prism-gn.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-go-module.js create mode 100644 frontend/node_modules/prismjs/components/prism-go-module.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-go.js create mode 100644 frontend/node_modules/prismjs/components/prism-go.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-gradle.js create mode 100644 frontend/node_modules/prismjs/components/prism-gradle.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-graphql.js create mode 100644 frontend/node_modules/prismjs/components/prism-graphql.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-groovy.js create mode 100644 frontend/node_modules/prismjs/components/prism-groovy.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-haml.js create mode 100644 frontend/node_modules/prismjs/components/prism-haml.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-handlebars.js create mode 100644 frontend/node_modules/prismjs/components/prism-handlebars.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-haskell.js create mode 100644 frontend/node_modules/prismjs/components/prism-haskell.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-haxe.js create mode 100644 frontend/node_modules/prismjs/components/prism-haxe.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-hcl.js create mode 100644 frontend/node_modules/prismjs/components/prism-hcl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-hlsl.js create mode 100644 frontend/node_modules/prismjs/components/prism-hlsl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-hoon.js create mode 100644 frontend/node_modules/prismjs/components/prism-hoon.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-hpkp.js create mode 100644 frontend/node_modules/prismjs/components/prism-hpkp.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-hsts.js create mode 100644 frontend/node_modules/prismjs/components/prism-hsts.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-http.js create mode 100644 frontend/node_modules/prismjs/components/prism-http.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-ichigojam.js create mode 100644 frontend/node_modules/prismjs/components/prism-ichigojam.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-icon.js create mode 100644 frontend/node_modules/prismjs/components/prism-icon.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-icu-message-format.js create mode 100644 frontend/node_modules/prismjs/components/prism-icu-message-format.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-idris.js create mode 100644 frontend/node_modules/prismjs/components/prism-idris.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-iecst.js create mode 100644 frontend/node_modules/prismjs/components/prism-iecst.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-ignore.js create mode 100644 frontend/node_modules/prismjs/components/prism-ignore.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-inform7.js create mode 100644 frontend/node_modules/prismjs/components/prism-inform7.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-ini.js create mode 100644 frontend/node_modules/prismjs/components/prism-ini.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-io.js create mode 100644 frontend/node_modules/prismjs/components/prism-io.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-j.js create mode 100644 frontend/node_modules/prismjs/components/prism-j.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-java.js create mode 100644 frontend/node_modules/prismjs/components/prism-java.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-javadoc.js create mode 100644 frontend/node_modules/prismjs/components/prism-javadoc.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-javadoclike.js create mode 100644 frontend/node_modules/prismjs/components/prism-javadoclike.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-javascript.js create mode 100644 frontend/node_modules/prismjs/components/prism-javascript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-javastacktrace.js create mode 100644 frontend/node_modules/prismjs/components/prism-javastacktrace.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-jexl.js create mode 100644 frontend/node_modules/prismjs/components/prism-jexl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-jolie.js create mode 100644 frontend/node_modules/prismjs/components/prism-jolie.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-jq.js create mode 100644 frontend/node_modules/prismjs/components/prism-jq.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-js-extras.js create mode 100644 frontend/node_modules/prismjs/components/prism-js-extras.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-js-templates.js create mode 100644 frontend/node_modules/prismjs/components/prism-js-templates.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-jsdoc.js create mode 100644 frontend/node_modules/prismjs/components/prism-jsdoc.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-json.js create mode 100644 frontend/node_modules/prismjs/components/prism-json.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-json5.js create mode 100644 frontend/node_modules/prismjs/components/prism-json5.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-jsonp.js create mode 100644 frontend/node_modules/prismjs/components/prism-jsonp.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-jsstacktrace.js create mode 100644 frontend/node_modules/prismjs/components/prism-jsstacktrace.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-jsx.js create mode 100644 frontend/node_modules/prismjs/components/prism-jsx.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-julia.js create mode 100644 frontend/node_modules/prismjs/components/prism-julia.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-keepalived.js create mode 100644 frontend/node_modules/prismjs/components/prism-keepalived.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-keyman.js create mode 100644 frontend/node_modules/prismjs/components/prism-keyman.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-kotlin.js create mode 100644 frontend/node_modules/prismjs/components/prism-kotlin.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-kumir.js create mode 100644 frontend/node_modules/prismjs/components/prism-kumir.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-kusto.js create mode 100644 frontend/node_modules/prismjs/components/prism-kusto.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-latex.js create mode 100644 frontend/node_modules/prismjs/components/prism-latex.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-latte.js create mode 100644 frontend/node_modules/prismjs/components/prism-latte.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-less.js create mode 100644 frontend/node_modules/prismjs/components/prism-less.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-lilypond.js create mode 100644 frontend/node_modules/prismjs/components/prism-lilypond.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-linker-script.js create mode 100644 frontend/node_modules/prismjs/components/prism-linker-script.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-liquid.js create mode 100644 frontend/node_modules/prismjs/components/prism-liquid.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-lisp.js create mode 100644 frontend/node_modules/prismjs/components/prism-lisp.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-livescript.js create mode 100644 frontend/node_modules/prismjs/components/prism-livescript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-llvm.js create mode 100644 frontend/node_modules/prismjs/components/prism-llvm.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-log.js create mode 100644 frontend/node_modules/prismjs/components/prism-log.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-lolcode.js create mode 100644 frontend/node_modules/prismjs/components/prism-lolcode.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-lua.js create mode 100644 frontend/node_modules/prismjs/components/prism-lua.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-magma.js create mode 100644 frontend/node_modules/prismjs/components/prism-magma.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-makefile.js create mode 100644 frontend/node_modules/prismjs/components/prism-makefile.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-markdown.js create mode 100644 frontend/node_modules/prismjs/components/prism-markdown.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-markup-templating.js create mode 100644 frontend/node_modules/prismjs/components/prism-markup-templating.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-markup.js create mode 100644 frontend/node_modules/prismjs/components/prism-markup.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-mata.js create mode 100644 frontend/node_modules/prismjs/components/prism-mata.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-matlab.js create mode 100644 frontend/node_modules/prismjs/components/prism-matlab.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-maxscript.js create mode 100644 frontend/node_modules/prismjs/components/prism-maxscript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-mel.js create mode 100644 frontend/node_modules/prismjs/components/prism-mel.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-mermaid.js create mode 100644 frontend/node_modules/prismjs/components/prism-mermaid.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-metafont.js create mode 100644 frontend/node_modules/prismjs/components/prism-metafont.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-mizar.js create mode 100644 frontend/node_modules/prismjs/components/prism-mizar.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-mongodb.js create mode 100644 frontend/node_modules/prismjs/components/prism-mongodb.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-monkey.js create mode 100644 frontend/node_modules/prismjs/components/prism-monkey.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-moonscript.js create mode 100644 frontend/node_modules/prismjs/components/prism-moonscript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-n1ql.js create mode 100644 frontend/node_modules/prismjs/components/prism-n1ql.min.js create mode 100755 frontend/node_modules/prismjs/components/prism-n4js.js create mode 100755 frontend/node_modules/prismjs/components/prism-n4js.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-nand2tetris-hdl.js create mode 100644 frontend/node_modules/prismjs/components/prism-nand2tetris-hdl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-naniscript.js create mode 100644 frontend/node_modules/prismjs/components/prism-naniscript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-nasm.js create mode 100644 frontend/node_modules/prismjs/components/prism-nasm.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-neon.js create mode 100644 frontend/node_modules/prismjs/components/prism-neon.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-nevod.js create mode 100644 frontend/node_modules/prismjs/components/prism-nevod.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-nginx.js create mode 100644 frontend/node_modules/prismjs/components/prism-nginx.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-nim.js create mode 100644 frontend/node_modules/prismjs/components/prism-nim.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-nix.js create mode 100644 frontend/node_modules/prismjs/components/prism-nix.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-nsis.js create mode 100644 frontend/node_modules/prismjs/components/prism-nsis.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-objectivec.js create mode 100644 frontend/node_modules/prismjs/components/prism-objectivec.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-ocaml.js create mode 100644 frontend/node_modules/prismjs/components/prism-ocaml.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-odin.js create mode 100644 frontend/node_modules/prismjs/components/prism-odin.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-opencl.js create mode 100644 frontend/node_modules/prismjs/components/prism-opencl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-openqasm.js create mode 100644 frontend/node_modules/prismjs/components/prism-openqasm.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-oz.js create mode 100644 frontend/node_modules/prismjs/components/prism-oz.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-parigp.js create mode 100644 frontend/node_modules/prismjs/components/prism-parigp.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-parser.js create mode 100644 frontend/node_modules/prismjs/components/prism-parser.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-pascal.js create mode 100644 frontend/node_modules/prismjs/components/prism-pascal.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-pascaligo.js create mode 100644 frontend/node_modules/prismjs/components/prism-pascaligo.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-pcaxis.js create mode 100644 frontend/node_modules/prismjs/components/prism-pcaxis.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-peoplecode.js create mode 100644 frontend/node_modules/prismjs/components/prism-peoplecode.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-perl.js create mode 100644 frontend/node_modules/prismjs/components/prism-perl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-php-extras.js create mode 100644 frontend/node_modules/prismjs/components/prism-php-extras.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-php.js create mode 100644 frontend/node_modules/prismjs/components/prism-php.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-phpdoc.js create mode 100644 frontend/node_modules/prismjs/components/prism-phpdoc.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-plant-uml.js create mode 100644 frontend/node_modules/prismjs/components/prism-plant-uml.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-plsql.js create mode 100644 frontend/node_modules/prismjs/components/prism-plsql.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-powerquery.js create mode 100644 frontend/node_modules/prismjs/components/prism-powerquery.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-powershell.js create mode 100644 frontend/node_modules/prismjs/components/prism-powershell.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-processing.js create mode 100644 frontend/node_modules/prismjs/components/prism-processing.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-prolog.js create mode 100644 frontend/node_modules/prismjs/components/prism-prolog.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-promql.js create mode 100644 frontend/node_modules/prismjs/components/prism-promql.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-properties.js create mode 100644 frontend/node_modules/prismjs/components/prism-properties.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-protobuf.js create mode 100644 frontend/node_modules/prismjs/components/prism-protobuf.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-psl.js create mode 100644 frontend/node_modules/prismjs/components/prism-psl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-pug.js create mode 100644 frontend/node_modules/prismjs/components/prism-pug.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-puppet.js create mode 100644 frontend/node_modules/prismjs/components/prism-puppet.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-pure.js create mode 100644 frontend/node_modules/prismjs/components/prism-pure.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-purebasic.js create mode 100644 frontend/node_modules/prismjs/components/prism-purebasic.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-purescript.js create mode 100644 frontend/node_modules/prismjs/components/prism-purescript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-python.js create mode 100644 frontend/node_modules/prismjs/components/prism-python.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-q.js create mode 100644 frontend/node_modules/prismjs/components/prism-q.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-qml.js create mode 100644 frontend/node_modules/prismjs/components/prism-qml.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-qore.js create mode 100644 frontend/node_modules/prismjs/components/prism-qore.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-qsharp.js create mode 100644 frontend/node_modules/prismjs/components/prism-qsharp.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-r.js create mode 100644 frontend/node_modules/prismjs/components/prism-r.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-racket.js create mode 100644 frontend/node_modules/prismjs/components/prism-racket.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-reason.js create mode 100644 frontend/node_modules/prismjs/components/prism-reason.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-regex.js create mode 100644 frontend/node_modules/prismjs/components/prism-regex.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-rego.js create mode 100644 frontend/node_modules/prismjs/components/prism-rego.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-renpy.js create mode 100644 frontend/node_modules/prismjs/components/prism-renpy.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-rescript.js create mode 100644 frontend/node_modules/prismjs/components/prism-rescript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-rest.js create mode 100644 frontend/node_modules/prismjs/components/prism-rest.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-rip.js create mode 100644 frontend/node_modules/prismjs/components/prism-rip.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-roboconf.js create mode 100644 frontend/node_modules/prismjs/components/prism-roboconf.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-robotframework.js create mode 100644 frontend/node_modules/prismjs/components/prism-robotframework.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-ruby.js create mode 100644 frontend/node_modules/prismjs/components/prism-ruby.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-rust.js create mode 100644 frontend/node_modules/prismjs/components/prism-rust.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-sas.js create mode 100644 frontend/node_modules/prismjs/components/prism-sas.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-sass.js create mode 100644 frontend/node_modules/prismjs/components/prism-sass.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-scala.js create mode 100644 frontend/node_modules/prismjs/components/prism-scala.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-scheme.js create mode 100644 frontend/node_modules/prismjs/components/prism-scheme.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-scss.js create mode 100644 frontend/node_modules/prismjs/components/prism-scss.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-shell-session.js create mode 100644 frontend/node_modules/prismjs/components/prism-shell-session.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-smali.js create mode 100644 frontend/node_modules/prismjs/components/prism-smali.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-smalltalk.js create mode 100644 frontend/node_modules/prismjs/components/prism-smalltalk.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-smarty.js create mode 100644 frontend/node_modules/prismjs/components/prism-smarty.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-sml.js create mode 100644 frontend/node_modules/prismjs/components/prism-sml.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-solidity.js create mode 100644 frontend/node_modules/prismjs/components/prism-solidity.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-solution-file.js create mode 100644 frontend/node_modules/prismjs/components/prism-solution-file.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-soy.js create mode 100644 frontend/node_modules/prismjs/components/prism-soy.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-sparql.js create mode 100644 frontend/node_modules/prismjs/components/prism-sparql.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-splunk-spl.js create mode 100644 frontend/node_modules/prismjs/components/prism-splunk-spl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-sqf.js create mode 100644 frontend/node_modules/prismjs/components/prism-sqf.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-sql.js create mode 100644 frontend/node_modules/prismjs/components/prism-sql.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-squirrel.js create mode 100644 frontend/node_modules/prismjs/components/prism-squirrel.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-stan.js create mode 100644 frontend/node_modules/prismjs/components/prism-stan.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-stata.js create mode 100644 frontend/node_modules/prismjs/components/prism-stata.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-stylus.js create mode 100644 frontend/node_modules/prismjs/components/prism-stylus.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-supercollider.js create mode 100644 frontend/node_modules/prismjs/components/prism-supercollider.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-swift.js create mode 100644 frontend/node_modules/prismjs/components/prism-swift.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-systemd.js create mode 100644 frontend/node_modules/prismjs/components/prism-systemd.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-t4-cs.js create mode 100644 frontend/node_modules/prismjs/components/prism-t4-cs.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-t4-templating.js create mode 100644 frontend/node_modules/prismjs/components/prism-t4-templating.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-t4-vb.js create mode 100644 frontend/node_modules/prismjs/components/prism-t4-vb.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-tap.js create mode 100644 frontend/node_modules/prismjs/components/prism-tap.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-tcl.js create mode 100644 frontend/node_modules/prismjs/components/prism-tcl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-textile.js create mode 100644 frontend/node_modules/prismjs/components/prism-textile.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-toml.js create mode 100644 frontend/node_modules/prismjs/components/prism-toml.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-tremor.js create mode 100644 frontend/node_modules/prismjs/components/prism-tremor.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-tsx.js create mode 100644 frontend/node_modules/prismjs/components/prism-tsx.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-tt2.js create mode 100644 frontend/node_modules/prismjs/components/prism-tt2.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-turtle.js create mode 100644 frontend/node_modules/prismjs/components/prism-turtle.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-twig.js create mode 100644 frontend/node_modules/prismjs/components/prism-twig.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-typescript.js create mode 100644 frontend/node_modules/prismjs/components/prism-typescript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-typoscript.js create mode 100644 frontend/node_modules/prismjs/components/prism-typoscript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-unrealscript.js create mode 100644 frontend/node_modules/prismjs/components/prism-unrealscript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-uorazor.js create mode 100644 frontend/node_modules/prismjs/components/prism-uorazor.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-uri.js create mode 100644 frontend/node_modules/prismjs/components/prism-uri.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-v.js create mode 100644 frontend/node_modules/prismjs/components/prism-v.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-vala.js create mode 100644 frontend/node_modules/prismjs/components/prism-vala.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-vbnet.js create mode 100644 frontend/node_modules/prismjs/components/prism-vbnet.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-velocity.js create mode 100644 frontend/node_modules/prismjs/components/prism-velocity.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-verilog.js create mode 100644 frontend/node_modules/prismjs/components/prism-verilog.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-vhdl.js create mode 100644 frontend/node_modules/prismjs/components/prism-vhdl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-vim.js create mode 100644 frontend/node_modules/prismjs/components/prism-vim.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-visual-basic.js create mode 100644 frontend/node_modules/prismjs/components/prism-visual-basic.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-warpscript.js create mode 100644 frontend/node_modules/prismjs/components/prism-warpscript.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-wasm.js create mode 100644 frontend/node_modules/prismjs/components/prism-wasm.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-web-idl.js create mode 100644 frontend/node_modules/prismjs/components/prism-web-idl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-wgsl.js create mode 100644 frontend/node_modules/prismjs/components/prism-wgsl.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-wiki.js create mode 100644 frontend/node_modules/prismjs/components/prism-wiki.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-wolfram.js create mode 100644 frontend/node_modules/prismjs/components/prism-wolfram.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-wren.js create mode 100644 frontend/node_modules/prismjs/components/prism-wren.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-xeora.js create mode 100644 frontend/node_modules/prismjs/components/prism-xeora.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-xml-doc.js create mode 100644 frontend/node_modules/prismjs/components/prism-xml-doc.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-xojo.js create mode 100644 frontend/node_modules/prismjs/components/prism-xojo.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-xquery.js create mode 100644 frontend/node_modules/prismjs/components/prism-xquery.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-yaml.js create mode 100644 frontend/node_modules/prismjs/components/prism-yaml.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-yang.js create mode 100644 frontend/node_modules/prismjs/components/prism-yang.min.js create mode 100644 frontend/node_modules/prismjs/components/prism-zig.js create mode 100644 frontend/node_modules/prismjs/components/prism-zig.min.js create mode 100644 frontend/node_modules/prismjs/dependencies.js create mode 100644 frontend/node_modules/prismjs/package.json create mode 100644 frontend/node_modules/prismjs/plugins/autolinker/prism-autolinker.css create mode 100644 frontend/node_modules/prismjs/plugins/autolinker/prism-autolinker.js create mode 100644 frontend/node_modules/prismjs/plugins/autolinker/prism-autolinker.min.css create mode 100644 frontend/node_modules/prismjs/plugins/autolinker/prism-autolinker.min.js create mode 100644 frontend/node_modules/prismjs/plugins/autoloader/prism-autoloader.js create mode 100644 frontend/node_modules/prismjs/plugins/autoloader/prism-autoloader.min.js create mode 100644 frontend/node_modules/prismjs/plugins/command-line/prism-command-line.css create mode 100644 frontend/node_modules/prismjs/plugins/command-line/prism-command-line.js create mode 100644 frontend/node_modules/prismjs/plugins/command-line/prism-command-line.min.css create mode 100644 frontend/node_modules/prismjs/plugins/command-line/prism-command-line.min.js create mode 100644 frontend/node_modules/prismjs/plugins/copy-to-clipboard/prism-copy-to-clipboard.js create mode 100644 frontend/node_modules/prismjs/plugins/copy-to-clipboard/prism-copy-to-clipboard.min.js create mode 100644 frontend/node_modules/prismjs/plugins/custom-class/prism-custom-class.js create mode 100644 frontend/node_modules/prismjs/plugins/custom-class/prism-custom-class.min.js create mode 100644 frontend/node_modules/prismjs/plugins/data-uri-highlight/prism-data-uri-highlight.js create mode 100644 frontend/node_modules/prismjs/plugins/data-uri-highlight/prism-data-uri-highlight.min.js create mode 100644 frontend/node_modules/prismjs/plugins/diff-highlight/prism-diff-highlight.css create mode 100644 frontend/node_modules/prismjs/plugins/diff-highlight/prism-diff-highlight.js create mode 100644 frontend/node_modules/prismjs/plugins/diff-highlight/prism-diff-highlight.min.css create mode 100644 frontend/node_modules/prismjs/plugins/diff-highlight/prism-diff-highlight.min.js create mode 100644 frontend/node_modules/prismjs/plugins/download-button/prism-download-button.js create mode 100644 frontend/node_modules/prismjs/plugins/download-button/prism-download-button.min.js create mode 100644 frontend/node_modules/prismjs/plugins/file-highlight/prism-file-highlight.js create mode 100644 frontend/node_modules/prismjs/plugins/file-highlight/prism-file-highlight.min.js create mode 100644 frontend/node_modules/prismjs/plugins/filter-highlight-all/prism-filter-highlight-all.js create mode 100644 frontend/node_modules/prismjs/plugins/filter-highlight-all/prism-filter-highlight-all.min.js create mode 100644 frontend/node_modules/prismjs/plugins/highlight-keywords/prism-highlight-keywords.js create mode 100644 frontend/node_modules/prismjs/plugins/highlight-keywords/prism-highlight-keywords.min.js create mode 100644 frontend/node_modules/prismjs/plugins/inline-color/prism-inline-color.css create mode 100644 frontend/node_modules/prismjs/plugins/inline-color/prism-inline-color.js create mode 100644 frontend/node_modules/prismjs/plugins/inline-color/prism-inline-color.min.css create mode 100644 frontend/node_modules/prismjs/plugins/inline-color/prism-inline-color.min.js create mode 100644 frontend/node_modules/prismjs/plugins/jsonp-highlight/prism-jsonp-highlight.js create mode 100644 frontend/node_modules/prismjs/plugins/jsonp-highlight/prism-jsonp-highlight.min.js create mode 100644 frontend/node_modules/prismjs/plugins/keep-markup/prism-keep-markup.js create mode 100644 frontend/node_modules/prismjs/plugins/keep-markup/prism-keep-markup.min.js create mode 100644 frontend/node_modules/prismjs/plugins/line-highlight/prism-line-highlight.css create mode 100644 frontend/node_modules/prismjs/plugins/line-highlight/prism-line-highlight.js create mode 100644 frontend/node_modules/prismjs/plugins/line-highlight/prism-line-highlight.min.css create mode 100644 frontend/node_modules/prismjs/plugins/line-highlight/prism-line-highlight.min.js create mode 100644 frontend/node_modules/prismjs/plugins/line-numbers/prism-line-numbers.css create mode 100644 frontend/node_modules/prismjs/plugins/line-numbers/prism-line-numbers.js create mode 100644 frontend/node_modules/prismjs/plugins/line-numbers/prism-line-numbers.min.css create mode 100644 frontend/node_modules/prismjs/plugins/line-numbers/prism-line-numbers.min.js create mode 100644 frontend/node_modules/prismjs/plugins/match-braces/prism-match-braces.css create mode 100644 frontend/node_modules/prismjs/plugins/match-braces/prism-match-braces.js create mode 100644 frontend/node_modules/prismjs/plugins/match-braces/prism-match-braces.min.css create mode 100644 frontend/node_modules/prismjs/plugins/match-braces/prism-match-braces.min.js create mode 100644 frontend/node_modules/prismjs/plugins/normalize-whitespace/prism-normalize-whitespace.js create mode 100644 frontend/node_modules/prismjs/plugins/normalize-whitespace/prism-normalize-whitespace.min.js create mode 100644 frontend/node_modules/prismjs/plugins/previewers/prism-previewers.css create mode 100644 frontend/node_modules/prismjs/plugins/previewers/prism-previewers.js create mode 100644 frontend/node_modules/prismjs/plugins/previewers/prism-previewers.min.css create mode 100644 frontend/node_modules/prismjs/plugins/previewers/prism-previewers.min.js create mode 100644 frontend/node_modules/prismjs/plugins/remove-initial-line-feed/prism-remove-initial-line-feed.js create mode 100644 frontend/node_modules/prismjs/plugins/remove-initial-line-feed/prism-remove-initial-line-feed.min.js create mode 100644 frontend/node_modules/prismjs/plugins/show-invisibles/prism-show-invisibles.css create mode 100644 frontend/node_modules/prismjs/plugins/show-invisibles/prism-show-invisibles.js create mode 100644 frontend/node_modules/prismjs/plugins/show-invisibles/prism-show-invisibles.min.css create mode 100644 frontend/node_modules/prismjs/plugins/show-invisibles/prism-show-invisibles.min.js create mode 100644 frontend/node_modules/prismjs/plugins/show-language/prism-show-language.js create mode 100644 frontend/node_modules/prismjs/plugins/show-language/prism-show-language.min.js create mode 100644 frontend/node_modules/prismjs/plugins/toolbar/prism-toolbar.css create mode 100644 frontend/node_modules/prismjs/plugins/toolbar/prism-toolbar.js create mode 100644 frontend/node_modules/prismjs/plugins/toolbar/prism-toolbar.min.css create mode 100644 frontend/node_modules/prismjs/plugins/toolbar/prism-toolbar.min.js create mode 100644 frontend/node_modules/prismjs/plugins/treeview/prism-treeview.css create mode 100644 frontend/node_modules/prismjs/plugins/treeview/prism-treeview.js create mode 100644 frontend/node_modules/prismjs/plugins/treeview/prism-treeview.min.css create mode 100644 frontend/node_modules/prismjs/plugins/treeview/prism-treeview.min.js create mode 100644 frontend/node_modules/prismjs/plugins/unescaped-markup/prism-unescaped-markup.css create mode 100644 frontend/node_modules/prismjs/plugins/unescaped-markup/prism-unescaped-markup.js create mode 100644 frontend/node_modules/prismjs/plugins/unescaped-markup/prism-unescaped-markup.min.css create mode 100644 frontend/node_modules/prismjs/plugins/unescaped-markup/prism-unescaped-markup.min.js create mode 100644 frontend/node_modules/prismjs/plugins/wpd/prism-wpd.css create mode 100644 frontend/node_modules/prismjs/plugins/wpd/prism-wpd.js create mode 100644 frontend/node_modules/prismjs/plugins/wpd/prism-wpd.min.css create mode 100644 frontend/node_modules/prismjs/plugins/wpd/prism-wpd.min.js create mode 100644 frontend/node_modules/prismjs/prism.js create mode 100644 frontend/node_modules/prismjs/themes/prism-coy.css create mode 100644 frontend/node_modules/prismjs/themes/prism-coy.min.css create mode 100644 frontend/node_modules/prismjs/themes/prism-dark.css create mode 100644 frontend/node_modules/prismjs/themes/prism-dark.min.css create mode 100644 frontend/node_modules/prismjs/themes/prism-funky.css create mode 100644 frontend/node_modules/prismjs/themes/prism-funky.min.css create mode 100644 frontend/node_modules/prismjs/themes/prism-okaidia.css create mode 100644 frontend/node_modules/prismjs/themes/prism-okaidia.min.css create mode 100644 frontend/node_modules/prismjs/themes/prism-solarizedlight.css create mode 100644 frontend/node_modules/prismjs/themes/prism-solarizedlight.min.css create mode 100644 frontend/node_modules/prismjs/themes/prism-tomorrow.css create mode 100644 frontend/node_modules/prismjs/themes/prism-tomorrow.min.css create mode 100644 frontend/node_modules/prismjs/themes/prism-twilight.css create mode 100644 frontend/node_modules/prismjs/themes/prism-twilight.min.css create mode 100644 frontend/node_modules/prismjs/themes/prism.css create mode 100644 frontend/node_modules/prismjs/themes/prism.min.css create mode 100644 frontend/node_modules/punycode.js/LICENSE-MIT.txt create mode 100644 frontend/node_modules/punycode.js/README.md create mode 100644 frontend/node_modules/punycode.js/package.json create mode 100644 frontend/node_modules/punycode.js/punycode.es6.js create mode 100644 frontend/node_modules/punycode.js/punycode.js create mode 100644 frontend/node_modules/robust-predicates/LICENSE create mode 100644 frontend/node_modules/robust-predicates/README.md create mode 100644 frontend/node_modules/robust-predicates/esm/incircle.js create mode 100644 frontend/node_modules/robust-predicates/esm/insphere.js create mode 100644 frontend/node_modules/robust-predicates/esm/orient2d.js create mode 100644 frontend/node_modules/robust-predicates/esm/orient3d.js create mode 100644 frontend/node_modules/robust-predicates/esm/util.js create mode 100644 frontend/node_modules/robust-predicates/index.d.ts create mode 100644 frontend/node_modules/robust-predicates/index.js create mode 100644 frontend/node_modules/robust-predicates/package.json create mode 100644 frontend/node_modules/robust-predicates/umd/incircle.js create mode 100644 frontend/node_modules/robust-predicates/umd/incircle.min.js create mode 100644 frontend/node_modules/robust-predicates/umd/insphere.js create mode 100644 frontend/node_modules/robust-predicates/umd/insphere.min.js create mode 100644 frontend/node_modules/robust-predicates/umd/orient2d.js create mode 100644 frontend/node_modules/robust-predicates/umd/orient2d.min.js create mode 100644 frontend/node_modules/robust-predicates/umd/orient3d.js create mode 100644 frontend/node_modules/robust-predicates/umd/orient3d.min.js create mode 100644 frontend/node_modules/robust-predicates/umd/predicates.js create mode 100644 frontend/node_modules/robust-predicates/umd/predicates.min.js create mode 100644 frontend/node_modules/rw/.eslintrc create mode 100644 frontend/node_modules/rw/.npmignore create mode 100644 frontend/node_modules/rw/LICENSE create mode 100644 frontend/node_modules/rw/README.md create mode 100644 frontend/node_modules/rw/index.js create mode 100644 frontend/node_modules/rw/lib/rw/dash.js create mode 100644 frontend/node_modules/rw/lib/rw/decode.js create mode 100644 frontend/node_modules/rw/lib/rw/encode.js create mode 100644 frontend/node_modules/rw/lib/rw/read-file-sync.js create mode 100644 frontend/node_modules/rw/lib/rw/read-file.js create mode 100644 frontend/node_modules/rw/lib/rw/write-file-sync.js create mode 100644 frontend/node_modules/rw/lib/rw/write-file.js create mode 100644 frontend/node_modules/rw/package.json create mode 100755 frontend/node_modules/rw/test/cat-async create mode 100755 frontend/node_modules/rw/test/cat-sync create mode 100755 frontend/node_modules/rw/test/encode-object-async create mode 100755 frontend/node_modules/rw/test/encode-object-sync create mode 100755 frontend/node_modules/rw/test/encode-string-async create mode 100755 frontend/node_modules/rw/test/encode-string-sync create mode 100755 frontend/node_modules/rw/test/encoding-async create mode 100755 frontend/node_modules/rw/test/encoding-sync create mode 100755 frontend/node_modules/rw/test/run-tests create mode 100644 frontend/node_modules/rw/test/utf8.txt create mode 100755 frontend/node_modules/rw/test/wc-async create mode 100755 frontend/node_modules/rw/test/wc-sync create mode 100755 frontend/node_modules/rw/test/write-async create mode 100755 frontend/node_modules/rw/test/write-sync create mode 100644 frontend/node_modules/safer-buffer/LICENSE create mode 100644 frontend/node_modules/safer-buffer/Porting-Buffer.md create mode 100644 frontend/node_modules/safer-buffer/Readme.md create mode 100644 frontend/node_modules/safer-buffer/dangerous.js create mode 100644 frontend/node_modules/safer-buffer/package.json create mode 100644 frontend/node_modules/safer-buffer/safer.js create mode 100644 frontend/node_modules/safer-buffer/tests.js create mode 100644 frontend/node_modules/uc.micro/LICENSE.txt create mode 100644 frontend/node_modules/uc.micro/README.md create mode 100644 frontend/node_modules/uc.micro/build/index.cjs.js create mode 100644 frontend/node_modules/uc.micro/categories/Cc/regex.mjs create mode 100644 frontend/node_modules/uc.micro/categories/Cf/regex.mjs create mode 100644 frontend/node_modules/uc.micro/categories/P/regex.mjs create mode 100644 frontend/node_modules/uc.micro/categories/S/regex.mjs create mode 100644 frontend/node_modules/uc.micro/categories/Z/regex.mjs create mode 100644 frontend/node_modules/uc.micro/index.mjs create mode 100644 frontend/node_modules/uc.micro/package.json create mode 100644 frontend/node_modules/uc.micro/properties/Any/regex.mjs create mode 100644 frontend/node_modules/undici/LICENSE create mode 100644 frontend/node_modules/undici/README.md create mode 100644 frontend/node_modules/undici/docs/docs/api/Agent.md create mode 100644 frontend/node_modules/undici/docs/docs/api/BalancedPool.md create mode 100644 frontend/node_modules/undici/docs/docs/api/CacheStorage.md create mode 100644 frontend/node_modules/undici/docs/docs/api/Client.md create mode 100644 frontend/node_modules/undici/docs/docs/api/Connector.md create mode 100644 frontend/node_modules/undici/docs/docs/api/ContentType.md create mode 100644 frontend/node_modules/undici/docs/docs/api/Cookies.md create mode 100644 frontend/node_modules/undici/docs/docs/api/Debug.md create mode 100644 frontend/node_modules/undici/docs/docs/api/DiagnosticsChannel.md create mode 100644 frontend/node_modules/undici/docs/docs/api/DispatchInterceptor.md create mode 100644 frontend/node_modules/undici/docs/docs/api/Dispatcher.md create mode 100644 frontend/node_modules/undici/docs/docs/api/EnvHttpProxyAgent.md create mode 100644 frontend/node_modules/undici/docs/docs/api/Errors.md create mode 100644 frontend/node_modules/undici/docs/docs/api/EventSource.md create mode 100644 frontend/node_modules/undici/docs/docs/api/Fetch.md create mode 100644 frontend/node_modules/undici/docs/docs/api/MockAgent.md create mode 100644 frontend/node_modules/undici/docs/docs/api/MockClient.md create mode 100644 frontend/node_modules/undici/docs/docs/api/MockErrors.md create mode 100644 frontend/node_modules/undici/docs/docs/api/MockPool.md create mode 100644 frontend/node_modules/undici/docs/docs/api/Pool.md create mode 100644 frontend/node_modules/undici/docs/docs/api/PoolStats.md create mode 100644 frontend/node_modules/undici/docs/docs/api/ProxyAgent.md create mode 100644 frontend/node_modules/undici/docs/docs/api/RedirectHandler.md create mode 100644 frontend/node_modules/undici/docs/docs/api/RetryAgent.md create mode 100644 frontend/node_modules/undici/docs/docs/api/RetryHandler.md create mode 100644 frontend/node_modules/undici/docs/docs/api/Util.md create mode 100644 frontend/node_modules/undici/docs/docs/api/WebSocket.md create mode 100644 frontend/node_modules/undici/docs/docs/api/api-lifecycle.md create mode 100644 frontend/node_modules/undici/docs/docs/best-practices/client-certificate.md create mode 100644 frontend/node_modules/undici/docs/docs/best-practices/mocking-request.md create mode 100644 frontend/node_modules/undici/docs/docs/best-practices/proxy.md create mode 100644 frontend/node_modules/undici/docs/docs/best-practices/writing-tests.md create mode 100644 frontend/node_modules/undici/index-fetch.js create mode 100644 frontend/node_modules/undici/index.d.ts create mode 100644 frontend/node_modules/undici/index.js create mode 100644 frontend/node_modules/undici/lib/api/abort-signal.js create mode 100644 frontend/node_modules/undici/lib/api/api-connect.js create mode 100644 frontend/node_modules/undici/lib/api/api-pipeline.js create mode 100644 frontend/node_modules/undici/lib/api/api-request.js create mode 100644 frontend/node_modules/undici/lib/api/api-stream.js create mode 100644 frontend/node_modules/undici/lib/api/api-upgrade.js create mode 100644 frontend/node_modules/undici/lib/api/index.js create mode 100644 frontend/node_modules/undici/lib/api/readable.js create mode 100644 frontend/node_modules/undici/lib/api/util.js create mode 100644 frontend/node_modules/undici/lib/core/connect.js create mode 100644 frontend/node_modules/undici/lib/core/constants.js create mode 100644 frontend/node_modules/undici/lib/core/diagnostics.js create mode 100644 frontend/node_modules/undici/lib/core/errors.js create mode 100644 frontend/node_modules/undici/lib/core/request.js create mode 100644 frontend/node_modules/undici/lib/core/symbols.js create mode 100644 frontend/node_modules/undici/lib/core/tree.js create mode 100644 frontend/node_modules/undici/lib/core/util.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/agent.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/balanced-pool.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/client-h1.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/client-h2.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/client.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/dispatcher-base.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/dispatcher.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/env-http-proxy-agent.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/fixed-queue.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/pool-base.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/pool-stats.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/pool.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/proxy-agent.js create mode 100644 frontend/node_modules/undici/lib/dispatcher/retry-agent.js create mode 100644 frontend/node_modules/undici/lib/global.js create mode 100644 frontend/node_modules/undici/lib/handler/decorator-handler.js create mode 100644 frontend/node_modules/undici/lib/handler/redirect-handler.js create mode 100644 frontend/node_modules/undici/lib/handler/retry-handler.js create mode 100644 frontend/node_modules/undici/lib/interceptor/dns.js create mode 100644 frontend/node_modules/undici/lib/interceptor/dump.js create mode 100644 frontend/node_modules/undici/lib/interceptor/redirect-interceptor.js create mode 100644 frontend/node_modules/undici/lib/interceptor/redirect.js create mode 100644 frontend/node_modules/undici/lib/interceptor/response-error.js create mode 100644 frontend/node_modules/undici/lib/interceptor/retry.js create mode 100644 frontend/node_modules/undici/lib/llhttp/.gitkeep create mode 100644 frontend/node_modules/undici/lib/llhttp/constants.js create mode 100644 frontend/node_modules/undici/lib/llhttp/llhttp-wasm.js create mode 100644 frontend/node_modules/undici/lib/llhttp/llhttp_simd-wasm.js create mode 100644 frontend/node_modules/undici/lib/llhttp/utils.js create mode 100644 frontend/node_modules/undici/lib/mock/mock-agent.js create mode 100644 frontend/node_modules/undici/lib/mock/mock-client.js create mode 100644 frontend/node_modules/undici/lib/mock/mock-errors.js create mode 100644 frontend/node_modules/undici/lib/mock/mock-interceptor.js create mode 100644 frontend/node_modules/undici/lib/mock/mock-pool.js create mode 100644 frontend/node_modules/undici/lib/mock/mock-symbols.js create mode 100644 frontend/node_modules/undici/lib/mock/mock-utils.js create mode 100644 frontend/node_modules/undici/lib/mock/pending-interceptors-formatter.js create mode 100644 frontend/node_modules/undici/lib/mock/pluralizer.js create mode 100644 frontend/node_modules/undici/lib/util/timers.js create mode 100644 frontend/node_modules/undici/lib/web/cache/cache.js create mode 100644 frontend/node_modules/undici/lib/web/cache/cachestorage.js create mode 100644 frontend/node_modules/undici/lib/web/cache/symbols.js create mode 100644 frontend/node_modules/undici/lib/web/cache/util.js create mode 100644 frontend/node_modules/undici/lib/web/cookies/constants.js create mode 100644 frontend/node_modules/undici/lib/web/cookies/index.js create mode 100644 frontend/node_modules/undici/lib/web/cookies/parse.js create mode 100644 frontend/node_modules/undici/lib/web/cookies/util.js create mode 100644 frontend/node_modules/undici/lib/web/eventsource/eventsource-stream.js create mode 100644 frontend/node_modules/undici/lib/web/eventsource/eventsource.js create mode 100644 frontend/node_modules/undici/lib/web/eventsource/util.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/LICENSE create mode 100644 frontend/node_modules/undici/lib/web/fetch/body.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/constants.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/data-url.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/dispatcher-weakref.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/file.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/formdata-parser.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/formdata.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/global.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/headers.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/index.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/request.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/response.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/symbols.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/util.js create mode 100644 frontend/node_modules/undici/lib/web/fetch/webidl.js create mode 100644 frontend/node_modules/undici/lib/web/fileapi/encoding.js create mode 100644 frontend/node_modules/undici/lib/web/fileapi/filereader.js create mode 100644 frontend/node_modules/undici/lib/web/fileapi/progressevent.js create mode 100644 frontend/node_modules/undici/lib/web/fileapi/symbols.js create mode 100644 frontend/node_modules/undici/lib/web/fileapi/util.js create mode 100644 frontend/node_modules/undici/lib/web/websocket/connection.js create mode 100644 frontend/node_modules/undici/lib/web/websocket/constants.js create mode 100644 frontend/node_modules/undici/lib/web/websocket/events.js create mode 100644 frontend/node_modules/undici/lib/web/websocket/frame.js create mode 100644 frontend/node_modules/undici/lib/web/websocket/permessage-deflate.js create mode 100644 frontend/node_modules/undici/lib/web/websocket/receiver.js create mode 100644 frontend/node_modules/undici/lib/web/websocket/sender.js create mode 100644 frontend/node_modules/undici/lib/web/websocket/symbols.js create mode 100644 frontend/node_modules/undici/lib/web/websocket/util.js create mode 100644 frontend/node_modules/undici/lib/web/websocket/websocket.js create mode 100644 frontend/node_modules/undici/package.json create mode 100644 frontend/node_modules/undici/scripts/strip-comments.js create mode 100644 frontend/node_modules/undici/types/README.md create mode 100644 frontend/node_modules/undici/types/agent.d.ts create mode 100644 frontend/node_modules/undici/types/api.d.ts create mode 100644 frontend/node_modules/undici/types/balanced-pool.d.ts create mode 100644 frontend/node_modules/undici/types/cache.d.ts create mode 100644 frontend/node_modules/undici/types/client.d.ts create mode 100644 frontend/node_modules/undici/types/connector.d.ts create mode 100644 frontend/node_modules/undici/types/content-type.d.ts create mode 100644 frontend/node_modules/undici/types/cookies.d.ts create mode 100644 frontend/node_modules/undici/types/diagnostics-channel.d.ts create mode 100644 frontend/node_modules/undici/types/dispatcher.d.ts create mode 100644 frontend/node_modules/undici/types/env-http-proxy-agent.d.ts create mode 100644 frontend/node_modules/undici/types/errors.d.ts create mode 100644 frontend/node_modules/undici/types/eventsource.d.ts create mode 100644 frontend/node_modules/undici/types/fetch.d.ts create mode 100644 frontend/node_modules/undici/types/file.d.ts create mode 100644 frontend/node_modules/undici/types/filereader.d.ts create mode 100644 frontend/node_modules/undici/types/formdata.d.ts create mode 100644 frontend/node_modules/undici/types/global-dispatcher.d.ts create mode 100644 frontend/node_modules/undici/types/global-origin.d.ts create mode 100644 frontend/node_modules/undici/types/handlers.d.ts create mode 100644 frontend/node_modules/undici/types/header.d.ts create mode 100644 frontend/node_modules/undici/types/index.d.ts create mode 100644 frontend/node_modules/undici/types/interceptors.d.ts create mode 100644 frontend/node_modules/undici/types/mock-agent.d.ts create mode 100644 frontend/node_modules/undici/types/mock-client.d.ts create mode 100644 frontend/node_modules/undici/types/mock-errors.d.ts create mode 100644 frontend/node_modules/undici/types/mock-interceptor.d.ts create mode 100644 frontend/node_modules/undici/types/mock-pool.d.ts create mode 100644 frontend/node_modules/undici/types/patch.d.ts create mode 100644 frontend/node_modules/undici/types/pool-stats.d.ts create mode 100644 frontend/node_modules/undici/types/pool.d.ts create mode 100644 frontend/node_modules/undici/types/proxy-agent.d.ts create mode 100644 frontend/node_modules/undici/types/readable.d.ts create mode 100644 frontend/node_modules/undici/types/retry-agent.d.ts create mode 100644 frontend/node_modules/undici/types/retry-handler.d.ts create mode 100644 frontend/node_modules/undici/types/util.d.ts create mode 100644 frontend/node_modules/undici/types/webidl.d.ts create mode 100644 frontend/node_modules/undici/types/websocket.d.ts create mode 100644 frontend/node_modules/whatwg-encoding/LICENSE.txt create mode 100644 frontend/node_modules/whatwg-encoding/README.md create mode 100644 frontend/node_modules/whatwg-encoding/lib/labels-to-names.json create mode 100644 frontend/node_modules/whatwg-encoding/lib/supported-names.json create mode 100644 frontend/node_modules/whatwg-encoding/lib/whatwg-encoding.js create mode 100644 frontend/node_modules/whatwg-encoding/package.json create mode 100644 frontend/node_modules/whatwg-mimetype/LICENSE.txt create mode 100644 frontend/node_modules/whatwg-mimetype/README.md create mode 100644 frontend/node_modules/whatwg-mimetype/lib/mime-type-parameters.js create mode 100644 frontend/node_modules/whatwg-mimetype/lib/mime-type.js create mode 100644 frontend/node_modules/whatwg-mimetype/lib/parser.js create mode 100644 frontend/node_modules/whatwg-mimetype/lib/serializer.js create mode 100644 frontend/node_modules/whatwg-mimetype/lib/utils.js create mode 100644 frontend/node_modules/whatwg-mimetype/package.json create mode 100644 frontend/node_modules/yaml/LICENSE create mode 100644 frontend/node_modules/yaml/README.md create mode 100755 frontend/node_modules/yaml/bin.mjs create mode 100644 frontend/node_modules/yaml/browser/dist/compose/compose-collection.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/compose-doc.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/compose-node.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/compose-scalar.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/composer.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/resolve-block-map.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/resolve-block-scalar.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/resolve-block-seq.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/resolve-end.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/resolve-flow-collection.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/resolve-flow-scalar.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/resolve-props.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/util-contains-newline.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/util-empty-scalar-position.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/util-flow-indent-check.js create mode 100644 frontend/node_modules/yaml/browser/dist/compose/util-map-includes.js create mode 100644 frontend/node_modules/yaml/browser/dist/doc/Document.js create mode 100644 frontend/node_modules/yaml/browser/dist/doc/anchors.js create mode 100644 frontend/node_modules/yaml/browser/dist/doc/applyReviver.js create mode 100644 frontend/node_modules/yaml/browser/dist/doc/createNode.js create mode 100644 frontend/node_modules/yaml/browser/dist/doc/directives.js create mode 100644 frontend/node_modules/yaml/browser/dist/errors.js create mode 100644 frontend/node_modules/yaml/browser/dist/index.js create mode 100644 frontend/node_modules/yaml/browser/dist/log.js create mode 100644 frontend/node_modules/yaml/browser/dist/nodes/Alias.js create mode 100644 frontend/node_modules/yaml/browser/dist/nodes/Collection.js create mode 100644 frontend/node_modules/yaml/browser/dist/nodes/Node.js create mode 100644 frontend/node_modules/yaml/browser/dist/nodes/Pair.js create mode 100644 frontend/node_modules/yaml/browser/dist/nodes/Scalar.js create mode 100644 frontend/node_modules/yaml/browser/dist/nodes/YAMLMap.js create mode 100644 frontend/node_modules/yaml/browser/dist/nodes/YAMLSeq.js create mode 100644 frontend/node_modules/yaml/browser/dist/nodes/addPairToJSMap.js create mode 100644 frontend/node_modules/yaml/browser/dist/nodes/identity.js create mode 100644 frontend/node_modules/yaml/browser/dist/nodes/toJS.js create mode 100644 frontend/node_modules/yaml/browser/dist/parse/cst-scalar.js create mode 100644 frontend/node_modules/yaml/browser/dist/parse/cst-stringify.js create mode 100644 frontend/node_modules/yaml/browser/dist/parse/cst-visit.js create mode 100644 frontend/node_modules/yaml/browser/dist/parse/cst.js create mode 100644 frontend/node_modules/yaml/browser/dist/parse/lexer.js create mode 100644 frontend/node_modules/yaml/browser/dist/parse/line-counter.js create mode 100644 frontend/node_modules/yaml/browser/dist/parse/parser.js create mode 100644 frontend/node_modules/yaml/browser/dist/public-api.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/Schema.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/common/map.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/common/null.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/common/seq.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/common/string.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/core/bool.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/core/float.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/core/int.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/core/schema.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/json/schema.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/tags.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/yaml-1.1/binary.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/yaml-1.1/bool.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/yaml-1.1/float.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/yaml-1.1/int.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/yaml-1.1/merge.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/yaml-1.1/omap.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/yaml-1.1/pairs.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/yaml-1.1/schema.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/yaml-1.1/set.js create mode 100644 frontend/node_modules/yaml/browser/dist/schema/yaml-1.1/timestamp.js create mode 100644 frontend/node_modules/yaml/browser/dist/stringify/foldFlowLines.js create mode 100644 frontend/node_modules/yaml/browser/dist/stringify/stringify.js create mode 100644 frontend/node_modules/yaml/browser/dist/stringify/stringifyCollection.js create mode 100644 frontend/node_modules/yaml/browser/dist/stringify/stringifyComment.js create mode 100644 frontend/node_modules/yaml/browser/dist/stringify/stringifyDocument.js create mode 100644 frontend/node_modules/yaml/browser/dist/stringify/stringifyNumber.js create mode 100644 frontend/node_modules/yaml/browser/dist/stringify/stringifyPair.js create mode 100644 frontend/node_modules/yaml/browser/dist/stringify/stringifyString.js create mode 100644 frontend/node_modules/yaml/browser/dist/util.js create mode 100644 frontend/node_modules/yaml/browser/dist/visit.js create mode 100644 frontend/node_modules/yaml/browser/index.js create mode 100644 frontend/node_modules/yaml/browser/package.json create mode 100644 frontend/node_modules/yaml/dist/cli.d.ts create mode 100644 frontend/node_modules/yaml/dist/cli.mjs create mode 100644 frontend/node_modules/yaml/dist/compose/compose-collection.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/compose-collection.js create mode 100644 frontend/node_modules/yaml/dist/compose/compose-doc.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/compose-doc.js create mode 100644 frontend/node_modules/yaml/dist/compose/compose-node.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/compose-node.js create mode 100644 frontend/node_modules/yaml/dist/compose/compose-scalar.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/compose-scalar.js create mode 100644 frontend/node_modules/yaml/dist/compose/composer.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/composer.js create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-block-map.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-block-map.js create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-block-scalar.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-block-scalar.js create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-block-seq.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-block-seq.js create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-end.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-end.js create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-flow-collection.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-flow-collection.js create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-flow-scalar.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-flow-scalar.js create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-props.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/resolve-props.js create mode 100644 frontend/node_modules/yaml/dist/compose/util-contains-newline.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/util-contains-newline.js create mode 100644 frontend/node_modules/yaml/dist/compose/util-empty-scalar-position.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/util-empty-scalar-position.js create mode 100644 frontend/node_modules/yaml/dist/compose/util-flow-indent-check.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/util-flow-indent-check.js create mode 100644 frontend/node_modules/yaml/dist/compose/util-map-includes.d.ts create mode 100644 frontend/node_modules/yaml/dist/compose/util-map-includes.js create mode 100644 frontend/node_modules/yaml/dist/doc/Document.d.ts create mode 100644 frontend/node_modules/yaml/dist/doc/Document.js create mode 100644 frontend/node_modules/yaml/dist/doc/anchors.d.ts create mode 100644 frontend/node_modules/yaml/dist/doc/anchors.js create mode 100644 frontend/node_modules/yaml/dist/doc/applyReviver.d.ts create mode 100644 frontend/node_modules/yaml/dist/doc/applyReviver.js create mode 100644 frontend/node_modules/yaml/dist/doc/createNode.d.ts create mode 100644 frontend/node_modules/yaml/dist/doc/createNode.js create mode 100644 frontend/node_modules/yaml/dist/doc/directives.d.ts create mode 100644 frontend/node_modules/yaml/dist/doc/directives.js create mode 100644 frontend/node_modules/yaml/dist/errors.d.ts create mode 100644 frontend/node_modules/yaml/dist/errors.js create mode 100644 frontend/node_modules/yaml/dist/index.d.ts create mode 100644 frontend/node_modules/yaml/dist/index.js create mode 100644 frontend/node_modules/yaml/dist/log.d.ts create mode 100644 frontend/node_modules/yaml/dist/log.js create mode 100644 frontend/node_modules/yaml/dist/nodes/Alias.d.ts create mode 100644 frontend/node_modules/yaml/dist/nodes/Alias.js create mode 100644 frontend/node_modules/yaml/dist/nodes/Collection.d.ts create mode 100644 frontend/node_modules/yaml/dist/nodes/Collection.js create mode 100644 frontend/node_modules/yaml/dist/nodes/Node.d.ts create mode 100644 frontend/node_modules/yaml/dist/nodes/Node.js create mode 100644 frontend/node_modules/yaml/dist/nodes/Pair.d.ts create mode 100644 frontend/node_modules/yaml/dist/nodes/Pair.js create mode 100644 frontend/node_modules/yaml/dist/nodes/Scalar.d.ts create mode 100644 frontend/node_modules/yaml/dist/nodes/Scalar.js create mode 100644 frontend/node_modules/yaml/dist/nodes/YAMLMap.d.ts create mode 100644 frontend/node_modules/yaml/dist/nodes/YAMLMap.js create mode 100644 frontend/node_modules/yaml/dist/nodes/YAMLSeq.d.ts create mode 100644 frontend/node_modules/yaml/dist/nodes/YAMLSeq.js create mode 100644 frontend/node_modules/yaml/dist/nodes/addPairToJSMap.d.ts create mode 100644 frontend/node_modules/yaml/dist/nodes/addPairToJSMap.js create mode 100644 frontend/node_modules/yaml/dist/nodes/identity.d.ts create mode 100644 frontend/node_modules/yaml/dist/nodes/identity.js create mode 100644 frontend/node_modules/yaml/dist/nodes/toJS.d.ts create mode 100644 frontend/node_modules/yaml/dist/nodes/toJS.js create mode 100644 frontend/node_modules/yaml/dist/options.d.ts create mode 100644 frontend/node_modules/yaml/dist/parse/cst-scalar.d.ts create mode 100644 frontend/node_modules/yaml/dist/parse/cst-scalar.js create mode 100644 frontend/node_modules/yaml/dist/parse/cst-stringify.d.ts create mode 100644 frontend/node_modules/yaml/dist/parse/cst-stringify.js create mode 100644 frontend/node_modules/yaml/dist/parse/cst-visit.d.ts create mode 100644 frontend/node_modules/yaml/dist/parse/cst-visit.js create mode 100644 frontend/node_modules/yaml/dist/parse/cst.d.ts create mode 100644 frontend/node_modules/yaml/dist/parse/cst.js create mode 100644 frontend/node_modules/yaml/dist/parse/lexer.d.ts create mode 100644 frontend/node_modules/yaml/dist/parse/lexer.js create mode 100644 frontend/node_modules/yaml/dist/parse/line-counter.d.ts create mode 100644 frontend/node_modules/yaml/dist/parse/line-counter.js create mode 100644 frontend/node_modules/yaml/dist/parse/parser.d.ts create mode 100644 frontend/node_modules/yaml/dist/parse/parser.js create mode 100644 frontend/node_modules/yaml/dist/public-api.d.ts create mode 100644 frontend/node_modules/yaml/dist/public-api.js create mode 100644 frontend/node_modules/yaml/dist/schema/Schema.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/Schema.js create mode 100644 frontend/node_modules/yaml/dist/schema/common/map.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/common/map.js create mode 100644 frontend/node_modules/yaml/dist/schema/common/null.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/common/null.js create mode 100644 frontend/node_modules/yaml/dist/schema/common/seq.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/common/seq.js create mode 100644 frontend/node_modules/yaml/dist/schema/common/string.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/common/string.js create mode 100644 frontend/node_modules/yaml/dist/schema/core/bool.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/core/bool.js create mode 100644 frontend/node_modules/yaml/dist/schema/core/float.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/core/float.js create mode 100644 frontend/node_modules/yaml/dist/schema/core/int.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/core/int.js create mode 100644 frontend/node_modules/yaml/dist/schema/core/schema.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/core/schema.js create mode 100644 frontend/node_modules/yaml/dist/schema/json-schema.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/json/schema.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/json/schema.js create mode 100644 frontend/node_modules/yaml/dist/schema/tags.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/tags.js create mode 100644 frontend/node_modules/yaml/dist/schema/types.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/binary.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/binary.js create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/bool.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/bool.js create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/float.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/float.js create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/int.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/int.js create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/merge.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/merge.js create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/omap.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/omap.js create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/pairs.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/pairs.js create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/schema.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/schema.js create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/set.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/set.js create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/timestamp.d.ts create mode 100644 frontend/node_modules/yaml/dist/schema/yaml-1.1/timestamp.js create mode 100644 frontend/node_modules/yaml/dist/stringify/foldFlowLines.d.ts create mode 100644 frontend/node_modules/yaml/dist/stringify/foldFlowLines.js create mode 100644 frontend/node_modules/yaml/dist/stringify/stringify.d.ts create mode 100644 frontend/node_modules/yaml/dist/stringify/stringify.js create mode 100644 frontend/node_modules/yaml/dist/stringify/stringifyCollection.d.ts create mode 100644 frontend/node_modules/yaml/dist/stringify/stringifyCollection.js create mode 100644 frontend/node_modules/yaml/dist/stringify/stringifyComment.d.ts create mode 100644 frontend/node_modules/yaml/dist/stringify/stringifyComment.js create mode 100644 frontend/node_modules/yaml/dist/stringify/stringifyDocument.d.ts create mode 100644 frontend/node_modules/yaml/dist/stringify/stringifyDocument.js create mode 100644 frontend/node_modules/yaml/dist/stringify/stringifyNumber.d.ts create mode 100644 frontend/node_modules/yaml/dist/stringify/stringifyNumber.js create mode 100644 frontend/node_modules/yaml/dist/stringify/stringifyPair.d.ts create mode 100644 frontend/node_modules/yaml/dist/stringify/stringifyPair.js create mode 100644 frontend/node_modules/yaml/dist/stringify/stringifyString.d.ts create mode 100644 frontend/node_modules/yaml/dist/stringify/stringifyString.js create mode 100644 frontend/node_modules/yaml/dist/test-events.d.ts create mode 100644 frontend/node_modules/yaml/dist/test-events.js create mode 100644 frontend/node_modules/yaml/dist/util.d.ts create mode 100644 frontend/node_modules/yaml/dist/util.js create mode 100644 frontend/node_modules/yaml/dist/visit.d.ts create mode 100644 frontend/node_modules/yaml/dist/visit.js create mode 100644 frontend/node_modules/yaml/package.json create mode 100644 frontend/node_modules/yaml/util.js create mode 100644 frontend/src/lib/mind-elixir/.eslintignore create mode 100644 frontend/src/lib/mind-elixir/.eslintrc.cjs create mode 100644 frontend/src/lib/mind-elixir/.github/FUNDING.yml create mode 100644 frontend/src/lib/mind-elixir/.github/ISSUE_TEMPLATE/bug_report.md create mode 100644 frontend/src/lib/mind-elixir/.github/ISSUE_TEMPLATE/feature_request.md create mode 100644 frontend/src/lib/mind-elixir/.github/workflows/npm-publish.yml create mode 100644 frontend/src/lib/mind-elixir/.gitignore create mode 100644 frontend/src/lib/mind-elixir/.husky/commit-msg create mode 100644 frontend/src/lib/mind-elixir/.husky/pre-commit create mode 100644 frontend/src/lib/mind-elixir/.husky/pre-push create mode 100644 frontend/src/lib/mind-elixir/.npmignore create mode 100644 frontend/src/lib/mind-elixir/.prettierrc.json rename frontend/{node_modules => src/lib}/mind-elixir/LICENSE (100%) create mode 100644 frontend/src/lib/mind-elixir/api-extractor.json create mode 100644 frontend/src/lib/mind-elixir/build.js create mode 100644 frontend/src/lib/mind-elixir/commitlint.config.js create mode 100644 frontend/src/lib/mind-elixir/images/logo.png create mode 100644 frontend/src/lib/mind-elixir/images/logo2.png create mode 100644 frontend/src/lib/mind-elixir/images/screenshot.cn.png create mode 100644 frontend/src/lib/mind-elixir/images/screenshot.png create mode 100644 frontend/src/lib/mind-elixir/images/screenshot2.png create mode 100644 frontend/src/lib/mind-elixir/images/screenshot5.jpg create mode 100644 frontend/src/lib/mind-elixir/index.css create mode 100644 frontend/src/lib/mind-elixir/index.html create mode 100644 frontend/src/lib/mind-elixir/katex.css create mode 100644 frontend/src/lib/mind-elixir/package-lock.json rename frontend/{node_modules => src/lib}/mind-elixir/package.json (55%) create mode 100644 frontend/src/lib/mind-elixir/playwright.config.ts create mode 100644 frontend/src/lib/mind-elixir/pnpm-lock.yaml create mode 100644 frontend/src/lib/mind-elixir/readme.md create mode 100644 frontend/src/lib/mind-elixir/readme/es.md create mode 100644 frontend/src/lib/mind-elixir/readme/fr.md create mode 100644 frontend/src/lib/mind-elixir/readme/ja.md rename frontend/{node_modules/mind-elixir/readme.md => src/lib/mind-elixir/readme/ko.md} (59%) create mode 100644 frontend/src/lib/mind-elixir/readme/pt.md create mode 100644 frontend/src/lib/mind-elixir/readme/ru.md create mode 100644 frontend/src/lib/mind-elixir/readme/zh.md create mode 100644 frontend/src/lib/mind-elixir/refs/scale-calc.excalidraw create mode 100644 frontend/src/lib/mind-elixir/src/arrow.ts create mode 100644 frontend/src/lib/mind-elixir/src/const.ts create mode 100644 frontend/src/lib/mind-elixir/src/dev.dist.ts create mode 100644 frontend/src/lib/mind-elixir/src/dev.ts create mode 100644 frontend/src/lib/mind-elixir/src/docs.ts create mode 100644 frontend/src/lib/mind-elixir/src/exampleData/1.cn.ts create mode 100644 frontend/src/lib/mind-elixir/src/exampleData/1.ts create mode 100644 frontend/src/lib/mind-elixir/src/exampleData/2.ts create mode 100644 frontend/src/lib/mind-elixir/src/exampleData/3.ts create mode 100644 frontend/src/lib/mind-elixir/src/exampleData/htmlText.ts create mode 100644 frontend/src/lib/mind-elixir/src/i18n.ts create mode 100644 frontend/src/lib/mind-elixir/src/icons/add-circle.svg create mode 100644 frontend/src/lib/mind-elixir/src/icons/full.svg create mode 100644 frontend/src/lib/mind-elixir/src/icons/left.svg create mode 100644 frontend/src/lib/mind-elixir/src/icons/living.svg create mode 100644 frontend/src/lib/mind-elixir/src/icons/minus-circle.svg create mode 100644 frontend/src/lib/mind-elixir/src/icons/right.svg create mode 100644 frontend/src/lib/mind-elixir/src/icons/side.svg create mode 100644 frontend/src/lib/mind-elixir/src/icons/zoomin.svg create mode 100644 frontend/src/lib/mind-elixir/src/icons/zoomout.svg create mode 100644 frontend/src/lib/mind-elixir/src/index.less create mode 100644 frontend/src/lib/mind-elixir/src/index.ts create mode 100644 frontend/src/lib/mind-elixir/src/interact.ts create mode 100644 frontend/src/lib/mind-elixir/src/linkDiv.ts create mode 100644 frontend/src/lib/mind-elixir/src/methods.ts create mode 100644 frontend/src/lib/mind-elixir/src/mouse.ts create mode 100644 frontend/src/lib/mind-elixir/src/nodeOperation.ts create mode 100644 frontend/src/lib/mind-elixir/src/plugin/contextMenu.less create mode 100644 frontend/src/lib/mind-elixir/src/plugin/contextMenu.ts create mode 100644 frontend/src/lib/mind-elixir/src/plugin/exportImage.ts create mode 100644 frontend/src/lib/mind-elixir/src/plugin/keypress.ts create mode 100644 frontend/src/lib/mind-elixir/src/plugin/nodeDraggable.ts create mode 100644 frontend/src/lib/mind-elixir/src/plugin/operationHistory.ts create mode 100644 frontend/src/lib/mind-elixir/src/plugin/selection.ts create mode 100644 frontend/src/lib/mind-elixir/src/plugin/toolBar.less create mode 100644 frontend/src/lib/mind-elixir/src/plugin/toolBar.ts create mode 100644 frontend/src/lib/mind-elixir/src/summary.ts create mode 100644 frontend/src/lib/mind-elixir/src/types/dom.ts create mode 100644 frontend/src/lib/mind-elixir/src/types/global.ts create mode 100644 frontend/src/lib/mind-elixir/src/types/index.ts create mode 100644 frontend/src/lib/mind-elixir/src/utils/LinkDragMoveHelper.ts create mode 100644 frontend/src/lib/mind-elixir/src/utils/dom.ts create mode 100644 frontend/src/lib/mind-elixir/src/utils/domManipulation.ts create mode 100644 frontend/src/lib/mind-elixir/src/utils/dragMoveHelper.ts create mode 100644 frontend/src/lib/mind-elixir/src/utils/generateBranch.ts create mode 100644 frontend/src/lib/mind-elixir/src/utils/index.ts create mode 100644 frontend/src/lib/mind-elixir/src/utils/layout-ssr.ts create mode 100644 frontend/src/lib/mind-elixir/src/utils/layout.ts create mode 100644 frontend/src/lib/mind-elixir/src/utils/objectManipulation.ts create mode 100644 frontend/src/lib/mind-elixir/src/utils/pubsub.ts create mode 100644 frontend/src/lib/mind-elixir/src/utils/svg.ts create mode 100644 frontend/src/lib/mind-elixir/src/utils/theme.ts create mode 100644 frontend/src/lib/mind-elixir/src/vite-env.d.ts create mode 100644 frontend/src/lib/mind-elixir/test.html create mode 100644 frontend/src/lib/mind-elixir/tests/MindElixirFixture.ts create mode 100644 frontend/src/lib/mind-elixir/tests/arrow.spec.ts create mode 100644 frontend/src/lib/mind-elixir/tests/drag-and-drop.spec.ts create mode 100644 frontend/src/lib/mind-elixir/tests/drag-and-drop.spec.ts-snapshots/DnD-move-after-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/drag-and-drop.spec.ts-snapshots/DnD-move-before-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/drag-and-drop.spec.ts-snapshots/DnD-move-in-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/expand-collapse.spec.ts create mode 100644 frontend/src/lib/mind-elixir/tests/interaction.spec.ts create mode 100644 frontend/src/lib/mind-elixir/tests/interaction.spec.ts-snapshots/Add-Before-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/interaction.spec.ts-snapshots/Add-Child-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/interaction.spec.ts-snapshots/Add-Parent-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/interaction.spec.ts-snapshots/Add-Sibling-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/interaction.spec.ts-snapshots/Clear-and-reset-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/interaction.spec.ts-snapshots/Copy-and-Paste-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/interaction.spec.ts-snapshots/Edit-Node-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/interaction.spec.ts-snapshots/Remove-Node-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/keyboard-undo-redo.spec.ts create mode 100644 frontend/src/lib/mind-elixir/tests/mind-elixir-test.ts create mode 100644 frontend/src/lib/mind-elixir/tests/multiple-instance.spec.ts create mode 100644 frontend/src/lib/mind-elixir/tests/multiple-instance.spec.ts-snapshots/Add-Child-To-Data2-Correctly-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/multiple-node.spec.ts create mode 100644 frontend/src/lib/mind-elixir/tests/multiple-node.spec.ts-snapshots/Multiple-Copy-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/multiple-node.spec.ts-snapshots/Multiple-Move-After-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/multiple-node.spec.ts-snapshots/Multiple-Move-Before-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/multiple-node.spec.ts-snapshots/Multiple-Move-In-1-chromium-win32.png create mode 100644 frontend/src/lib/mind-elixir/tests/operation-history.spec.ts create mode 100644 frontend/src/lib/mind-elixir/tests/simple-undo-redo.spec.ts create mode 100644 frontend/src/lib/mind-elixir/tests/summary.spec.ts create mode 100644 frontend/src/lib/mind-elixir/tests/topic-select.spec.ts create mode 100644 frontend/src/lib/mind-elixir/tests/undo-redo.spec.ts create mode 100644 frontend/src/lib/mind-elixir/tsconfig.json create mode 100644 frontend/src/lib/mind-elixir/vite.config.ts create mode 100644 frontend/test-enhanced-markdown.html create mode 100644 frontend/test-table-rendering.html create mode 100644 frontend/test-table.html create mode 100644 mind-elixir-core-master/.eslintignore create mode 100644 mind-elixir-core-master/.eslintrc.cjs create mode 100644 mind-elixir-core-master/.github/FUNDING.yml create mode 100644 mind-elixir-core-master/.github/ISSUE_TEMPLATE/bug_report.md create mode 100644 mind-elixir-core-master/.github/ISSUE_TEMPLATE/feature_request.md create mode 100644 mind-elixir-core-master/.github/workflows/npm-publish.yml create mode 100644 mind-elixir-core-master/.gitignore create mode 100644 mind-elixir-core-master/.husky/commit-msg create mode 100644 mind-elixir-core-master/.husky/pre-commit create mode 100644 mind-elixir-core-master/.husky/pre-push create mode 100644 mind-elixir-core-master/.npmignore create mode 100644 mind-elixir-core-master/.prettierrc.json create mode 100644 mind-elixir-core-master/LICENSE create mode 100644 mind-elixir-core-master/api-extractor.json create mode 100644 mind-elixir-core-master/build.js create mode 100644 mind-elixir-core-master/commitlint.config.js create mode 100644 mind-elixir-core-master/images/logo.png create mode 100644 mind-elixir-core-master/images/logo2.png create mode 100644 mind-elixir-core-master/images/screenshot.cn.png create mode 100644 mind-elixir-core-master/images/screenshot.png create mode 100644 mind-elixir-core-master/images/screenshot2.png create mode 100644 mind-elixir-core-master/images/screenshot5.jpg create mode 100644 mind-elixir-core-master/index.css create mode 100644 mind-elixir-core-master/index.html create mode 100644 mind-elixir-core-master/katex.css create mode 100644 mind-elixir-core-master/package.json create mode 100644 mind-elixir-core-master/playwright.config.ts create mode 100644 mind-elixir-core-master/pnpm-lock.yaml create mode 100644 mind-elixir-core-master/readme.md create mode 100644 mind-elixir-core-master/readme/es.md create mode 100644 mind-elixir-core-master/readme/fr.md create mode 100644 mind-elixir-core-master/readme/ja.md create mode 100644 mind-elixir-core-master/readme/ko.md create mode 100644 mind-elixir-core-master/readme/pt.md create mode 100644 mind-elixir-core-master/readme/ru.md create mode 100644 mind-elixir-core-master/readme/zh.md create mode 100644 mind-elixir-core-master/refs/scale-calc.excalidraw create mode 100644 mind-elixir-core-master/src/arrow.ts create mode 100644 mind-elixir-core-master/src/const.ts create mode 100644 mind-elixir-core-master/src/dev.dist.ts create mode 100644 mind-elixir-core-master/src/dev.ts create mode 100644 mind-elixir-core-master/src/docs.ts create mode 100644 mind-elixir-core-master/src/exampleData/1.cn.ts create mode 100644 mind-elixir-core-master/src/exampleData/1.ts create mode 100644 mind-elixir-core-master/src/exampleData/2.ts create mode 100644 mind-elixir-core-master/src/exampleData/3.ts create mode 100644 mind-elixir-core-master/src/exampleData/htmlText.ts create mode 100644 mind-elixir-core-master/src/i18n.ts create mode 100644 mind-elixir-core-master/src/icons/add-circle.svg create mode 100644 mind-elixir-core-master/src/icons/full.svg create mode 100644 mind-elixir-core-master/src/icons/left.svg create mode 100644 mind-elixir-core-master/src/icons/living.svg create mode 100644 mind-elixir-core-master/src/icons/minus-circle.svg create mode 100644 mind-elixir-core-master/src/icons/right.svg create mode 100644 mind-elixir-core-master/src/icons/side.svg create mode 100644 mind-elixir-core-master/src/icons/zoomin.svg create mode 100644 mind-elixir-core-master/src/icons/zoomout.svg create mode 100644 mind-elixir-core-master/src/index.less create mode 100644 mind-elixir-core-master/src/index.ts create mode 100644 mind-elixir-core-master/src/interact.ts create mode 100644 mind-elixir-core-master/src/linkDiv.ts create mode 100644 mind-elixir-core-master/src/methods.ts create mode 100644 mind-elixir-core-master/src/mouse.ts create mode 100644 mind-elixir-core-master/src/nodeOperation.ts create mode 100644 mind-elixir-core-master/src/plugin/contextMenu.less create mode 100644 mind-elixir-core-master/src/plugin/contextMenu.ts create mode 100644 mind-elixir-core-master/src/plugin/exportImage.ts create mode 100644 mind-elixir-core-master/src/plugin/keypress.ts create mode 100644 mind-elixir-core-master/src/plugin/nodeDraggable.ts create mode 100644 mind-elixir-core-master/src/plugin/operationHistory.ts create mode 100644 mind-elixir-core-master/src/plugin/selection.ts create mode 100644 mind-elixir-core-master/src/plugin/toolBar.less create mode 100644 mind-elixir-core-master/src/plugin/toolBar.ts create mode 100644 mind-elixir-core-master/src/summary.ts create mode 100644 mind-elixir-core-master/src/types/dom.ts create mode 100644 mind-elixir-core-master/src/types/global.ts create mode 100644 mind-elixir-core-master/src/types/index.ts create mode 100644 mind-elixir-core-master/src/utils/LinkDragMoveHelper.ts create mode 100644 mind-elixir-core-master/src/utils/dom.ts create mode 100644 mind-elixir-core-master/src/utils/domManipulation.ts create mode 100644 mind-elixir-core-master/src/utils/dragMoveHelper.ts create mode 100644 mind-elixir-core-master/src/utils/generateBranch.ts create mode 100644 mind-elixir-core-master/src/utils/index.ts create mode 100644 mind-elixir-core-master/src/utils/layout-ssr.ts create mode 100644 mind-elixir-core-master/src/utils/layout.ts create mode 100644 mind-elixir-core-master/src/utils/objectManipulation.ts create mode 100644 mind-elixir-core-master/src/utils/pubsub.ts create mode 100644 mind-elixir-core-master/src/utils/svg.ts create mode 100644 mind-elixir-core-master/src/utils/theme.ts create mode 100644 mind-elixir-core-master/src/vite-env.d.ts create mode 100644 mind-elixir-core-master/test.html create mode 100644 mind-elixir-core-master/tests/MindElixirFixture.ts create mode 100644 mind-elixir-core-master/tests/arrow.spec.ts create mode 100644 mind-elixir-core-master/tests/drag-and-drop.spec.ts create mode 100644 mind-elixir-core-master/tests/drag-and-drop.spec.ts-snapshots/DnD-move-after-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/drag-and-drop.spec.ts-snapshots/DnD-move-before-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/drag-and-drop.spec.ts-snapshots/DnD-move-in-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/expand-collapse.spec.ts create mode 100644 mind-elixir-core-master/tests/interaction.spec.ts create mode 100644 mind-elixir-core-master/tests/interaction.spec.ts-snapshots/Add-Before-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/interaction.spec.ts-snapshots/Add-Child-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/interaction.spec.ts-snapshots/Add-Parent-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/interaction.spec.ts-snapshots/Add-Sibling-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/interaction.spec.ts-snapshots/Clear-and-reset-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/interaction.spec.ts-snapshots/Copy-and-Paste-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/interaction.spec.ts-snapshots/Edit-Node-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/interaction.spec.ts-snapshots/Remove-Node-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/keyboard-undo-redo.spec.ts create mode 100644 mind-elixir-core-master/tests/mind-elixir-test.ts create mode 100644 mind-elixir-core-master/tests/multiple-instance.spec.ts create mode 100644 mind-elixir-core-master/tests/multiple-instance.spec.ts-snapshots/Add-Child-To-Data2-Correctly-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/multiple-node.spec.ts create mode 100644 mind-elixir-core-master/tests/multiple-node.spec.ts-snapshots/Multiple-Copy-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/multiple-node.spec.ts-snapshots/Multiple-Move-After-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/multiple-node.spec.ts-snapshots/Multiple-Move-Before-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/multiple-node.spec.ts-snapshots/Multiple-Move-In-1-chromium-win32.png create mode 100644 mind-elixir-core-master/tests/operation-history.spec.ts create mode 100644 mind-elixir-core-master/tests/simple-undo-redo.spec.ts create mode 100644 mind-elixir-core-master/tests/summary.spec.ts create mode 100644 mind-elixir-core-master/tests/topic-select.spec.ts create mode 100644 mind-elixir-core-master/tests/undo-redo.spec.ts create mode 100644 mind-elixir-core-master/tsconfig.json create mode 100644 mind-elixir-core-master/vite.config.ts diff --git a/.DS_Store b/.DS_Store index ca044df5d4e649dc66d1c2116f052757efb1057a..522f33c5b03858971e4d5a2b85a81418f79e06dc 100644 GIT binary patch delta 163 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�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

bnT5(H^A`tVQY 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

|>N3W2a3XuqFg$1Snw1bhg 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 W+G|7-AM&|T9*-22amoIVxc>qWjLumA diff --git a/frontend/debug-current-issue.html b/frontend/debug-current-issue.html new file mode 100644 index 0000000..0a51807 --- /dev/null +++ b/frontend/debug-current-issue.html @@ -0,0 +1,182 @@ + + + + + + 当前问题调试 + + + + +

+ + + + diff --git a/frontend/debug-mindelixir-styles.html b/frontend/debug-mindelixir-styles.html new file mode 100644 index 0000000..96ad8b6 --- /dev/null +++ b/frontend/debug-mindelixir-styles.html @@ -0,0 +1,196 @@ + + + + + + Mind Elixir样式调试 + + + +
+

Mind Elixir样式调试

+ +

测试1:模拟Mind Elixir节点中的表格

+
+
+ + + + + + + + + + + + + + + + + + + + + + + +
评估维度权重评分标准计算公式
完整性0.3缺失值比例 < 5%完整性 = 1 - 缺失值数量/总数据量
准确性0.3误差率 < 3%准确性 = 1 - 错误记录数/总记录数
+
+
+ +

测试2:普通表格(对比)

+ + + + + + + + + + + + + + + + + + + + + + + +
评估维度权重评分标准计算公式
完整性0.3缺失值比例 < 5%完整性 = 1 - 缺失值数量/总数据量
准确性0.3误差率 < 3%准确性 = 1 - 错误记录数/总记录数
+ +

测试3:检查样式是否被覆盖

+
+
+ + + + diff --git a/frontend/debug-table-detection.html b/frontend/debug-table-detection.html new file mode 100644 index 0000000..a56ac41 --- /dev/null +++ b/frontend/debug-table-detection.html @@ -0,0 +1,123 @@ + + + + + + 表格检测调试 + + + +

表格检测调试

+
+ + + + diff --git a/frontend/node_modules/.bin/csv2json b/frontend/node_modules/.bin/csv2json new file mode 120000 index 0000000..7259b5b --- /dev/null +++ b/frontend/node_modules/.bin/csv2json @@ -0,0 +1 @@ +../d3-dsv/bin/dsv2json.js \ No newline at end of file diff --git a/frontend/node_modules/.bin/csv2tsv b/frontend/node_modules/.bin/csv2tsv new file mode 120000 index 0000000..e72cff7 --- /dev/null +++ b/frontend/node_modules/.bin/csv2tsv @@ -0,0 +1 @@ +../d3-dsv/bin/dsv2dsv.js \ No newline at end of file diff --git a/frontend/node_modules/.bin/dsv2dsv b/frontend/node_modules/.bin/dsv2dsv new file mode 120000 index 0000000..e72cff7 --- /dev/null +++ b/frontend/node_modules/.bin/dsv2dsv @@ -0,0 +1 @@ +../d3-dsv/bin/dsv2dsv.js \ No newline at end of file diff --git a/frontend/node_modules/.bin/dsv2json b/frontend/node_modules/.bin/dsv2json new file mode 120000 index 0000000..7259b5b --- /dev/null +++ b/frontend/node_modules/.bin/dsv2json @@ -0,0 +1 @@ +../d3-dsv/bin/dsv2json.js \ No newline at end of file diff --git a/frontend/node_modules/.bin/json2csv b/frontend/node_modules/.bin/json2csv new file mode 120000 index 0000000..f4d7de4 --- /dev/null +++ b/frontend/node_modules/.bin/json2csv @@ -0,0 +1 @@ +../d3-dsv/bin/json2dsv.js \ No newline at end of file diff --git a/frontend/node_modules/.bin/json2dsv b/frontend/node_modules/.bin/json2dsv new file mode 120000 index 0000000..f4d7de4 --- /dev/null +++ b/frontend/node_modules/.bin/json2dsv @@ -0,0 +1 @@ +../d3-dsv/bin/json2dsv.js \ No newline at end of file diff --git a/frontend/node_modules/.bin/json2tsv b/frontend/node_modules/.bin/json2tsv new file mode 120000 index 0000000..f4d7de4 --- /dev/null +++ b/frontend/node_modules/.bin/json2tsv @@ -0,0 +1 @@ +../d3-dsv/bin/json2dsv.js \ No newline at end of file diff --git a/frontend/node_modules/.bin/katex b/frontend/node_modules/.bin/katex new file mode 120000 index 0000000..891ac13 --- /dev/null +++ b/frontend/node_modules/.bin/katex @@ -0,0 +1 @@ +../katex/cli.js \ No newline at end of file diff --git a/frontend/node_modules/.bin/markdown-it b/frontend/node_modules/.bin/markdown-it new file mode 120000 index 0000000..8a64108 --- /dev/null +++ b/frontend/node_modules/.bin/markdown-it @@ -0,0 +1 @@ +../markdown-it/bin/markdown-it.mjs \ No newline at end of file diff --git a/frontend/node_modules/.bin/tsv2csv b/frontend/node_modules/.bin/tsv2csv new file mode 120000 index 0000000..e72cff7 --- /dev/null +++ b/frontend/node_modules/.bin/tsv2csv @@ -0,0 +1 @@ +../d3-dsv/bin/dsv2dsv.js \ No newline at end of file diff --git a/frontend/node_modules/.bin/tsv2json b/frontend/node_modules/.bin/tsv2json new file mode 120000 index 0000000..7259b5b --- /dev/null +++ b/frontend/node_modules/.bin/tsv2json @@ -0,0 +1 @@ +../d3-dsv/bin/dsv2json.js \ No newline at end of file diff --git a/frontend/node_modules/.bin/yaml b/frontend/node_modules/.bin/yaml new file mode 120000 index 0000000..0368324 --- /dev/null +++ b/frontend/node_modules/.bin/yaml @@ -0,0 +1 @@ +../yaml/bin.mjs \ No newline at end of file diff --git a/frontend/node_modules/.package-lock.json b/frontend/node_modules/.package-lock.json index 8505c68..c4b1025 100644 --- a/frontend/node_modules/.package-lock.json +++ b/frontend/node_modules/.package-lock.json @@ -37,6 +37,15 @@ "node": ">=6.0.0" } }, + "node_modules/@babel/runtime": { + "version": "7.28.4", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.28.4.tgz", + "integrity": "sha512-Q/N6JNWvIvPnLDvjlE1OUBLPQHH6l3CltCEsHIujp45zQUSSh8K+gHnaEX45yAT1nyngnINhvWtzN+Nb9D8RAQ==", + "license": "MIT", + "engines": { + "node": ">=6.9.0" + } + }, "node_modules/@babel/types": { "version": "7.28.2", "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.28.2.tgz", @@ -67,6 +76,16 @@ "node": ">=12" } }, + "node_modules/@gera2ld/jsx-dom": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/@gera2ld/jsx-dom/-/jsx-dom-2.2.2.tgz", + "integrity": "sha512-EOqf31IATRE6zS1W1EoWmXZhGfLAoO9FIlwTtHduSrBdud4npYBxYAkv8dZ5hudDPwJeeSjn40kbCL4wAzr8dA==", + "license": "ISC", + "peer": true, + "dependencies": { + "@babel/runtime": "^7.21.5" + } + }, "node_modules/@jridgewell/sourcemap-codec": { "version": "1.5.5", "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.5.tgz", @@ -128,6 +147,15 @@ "vue": "^3.2.25" } }, + "node_modules/@vscode/markdown-it-katex": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@vscode/markdown-it-katex/-/markdown-it-katex-1.1.2.tgz", + "integrity": "sha512-+4IIv5PgrmhKvW/3LpkpkGg257OViEhXkOOgCyj5KMsjsOfnRXkni8XAuuF9Ui5p3B8WnUovlDXAQNb8RJ/RaQ==", + "license": "MIT", + "dependencies": { + "katex": "^0.16.4" + } + }, "node_modules/@vue/compiler-core": { "version": "3.5.20", "resolved": "https://registry.npmjs.org/@vue/compiler-core/-/compiler-core-3.5.20.tgz", @@ -289,6 +317,12 @@ "integrity": "sha512-iD3898SR7sWVRHbiQv+sHUtHnMvC1o3nW5rAcqnq3uOn07DSAppZYUkIGslDz6gXC7HfunPe7YVBgoEJASPcHA==", "license": "MIT" }, + "node_modules/boolbase": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/boolbase/-/boolbase-1.0.0.tgz", + "integrity": "sha512-JZOSA7Mo9sNGB8+UjSgzdLtokWAky1zbztM3WRLCbZ70/3cTANmQmOdR7y2g+J0e2WXywy1yS468tY+IruqEww==", + "license": "ISC" + }, "node_modules/call-bind-apply-helpers": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz", @@ -302,6 +336,48 @@ "node": ">= 0.4" } }, + "node_modules/cheerio": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/cheerio/-/cheerio-1.0.0.tgz", + "integrity": "sha512-quS9HgjQpdaXOvsZz82Oz7uxtXiy6UIsIQcpBj7HRw2M63Skasm9qlDocAM7jNuaxdhpPU7c4kJN+gA5MCu4ww==", + "license": "MIT", + "dependencies": { + "cheerio-select": "^2.1.0", + "dom-serializer": "^2.0.0", + "domhandler": "^5.0.3", + "domutils": "^3.1.0", + "encoding-sniffer": "^0.2.0", + "htmlparser2": "^9.1.0", + "parse5": "^7.1.2", + "parse5-htmlparser2-tree-adapter": "^7.0.0", + "parse5-parser-stream": "^7.1.2", + "undici": "^6.19.5", + "whatwg-mimetype": "^4.0.0" + }, + "engines": { + "node": ">=18.17" + }, + "funding": { + "url": "https://github.com/cheeriojs/cheerio?sponsor=1" + } + }, + "node_modules/cheerio-select": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/cheerio-select/-/cheerio-select-2.1.0.tgz", + "integrity": "sha512-9v9kG0LvzrlcungtnJtpGNxY+fzECQKhK4EGJX2vByejiMX84MFNQw4UxPJl3bFbTMw+Dfs37XaIkCwTZfLh4g==", + "license": "BSD-2-Clause", + "dependencies": { + "boolbase": "^1.0.0", + "css-select": "^5.1.0", + "css-what": "^6.1.0", + "domelementtype": "^2.3.0", + "domhandler": "^5.0.3", + "domutils": "^3.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/fb55" + } + }, "node_modules/combined-stream": { "version": "1.0.8", "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", @@ -314,18 +390,474 @@ "node": ">= 0.8" } }, + "node_modules/commander": { + "version": "8.3.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-8.3.0.tgz", + "integrity": "sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww==", + "license": "MIT", + "engines": { + "node": ">= 12" + } + }, "node_modules/core-util-is": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz", "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==", "license": "MIT" }, + "node_modules/css-select": { + "version": "5.2.2", + "resolved": "https://registry.npmjs.org/css-select/-/css-select-5.2.2.tgz", + "integrity": "sha512-TizTzUddG/xYLA3NXodFM0fSbNizXjOKhqiQQwvhlspadZokn1KDy0NZFS0wuEubIYAV5/c1/lAr0TaaFXEXzw==", + "license": "BSD-2-Clause", + "dependencies": { + "boolbase": "^1.0.0", + "css-what": "^6.1.0", + "domhandler": "^5.0.2", + "domutils": "^3.0.1", + "nth-check": "^2.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/fb55" + } + }, + "node_modules/css-what": { + "version": "6.2.2", + "resolved": "https://registry.npmjs.org/css-what/-/css-what-6.2.2.tgz", + "integrity": "sha512-u/O3vwbptzhMs3L1fQE82ZSLHQQfto5gyZzwteVIEyeaY5Fc7R4dapF/BvRoSYFeqfBk4m0V1Vafq5Pjv25wvA==", + "license": "BSD-2-Clause", + "engines": { + "node": ">= 6" + }, + "funding": { + "url": "https://github.com/sponsors/fb55" + } + }, "node_modules/csstype": { "version": "3.1.3", "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.3.tgz", "integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==", "license": "MIT" }, + "node_modules/d3": { + "version": "7.9.0", + "resolved": "https://registry.npmjs.org/d3/-/d3-7.9.0.tgz", + "integrity": "sha512-e1U46jVP+w7Iut8Jt8ri1YsPOvFpg46k+K8TpCb0P+zjCkjkPnV7WzfDJzMHy1LnA+wj5pLT1wjO901gLXeEhA==", + "license": "ISC", + "dependencies": { + "d3-array": "3", + "d3-axis": "3", + "d3-brush": "3", + "d3-chord": "3", + "d3-color": "3", + "d3-contour": "4", + "d3-delaunay": "6", + "d3-dispatch": "3", + "d3-drag": "3", + "d3-dsv": "3", + "d3-ease": "3", + "d3-fetch": "3", + "d3-force": "3", + "d3-format": "3", + "d3-geo": "3", + "d3-hierarchy": "3", + "d3-interpolate": "3", + "d3-path": "3", + "d3-polygon": "3", + "d3-quadtree": "3", + "d3-random": "3", + "d3-scale": "4", + "d3-scale-chromatic": "3", + "d3-selection": "3", + "d3-shape": "3", + "d3-time": "3", + "d3-time-format": "4", + "d3-timer": "3", + "d3-transition": "3", + "d3-zoom": "3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-array": { + "version": "3.2.4", + "resolved": "https://registry.npmjs.org/d3-array/-/d3-array-3.2.4.tgz", + "integrity": "sha512-tdQAmyA18i4J7wprpYq8ClcxZy3SC31QMeByyCFyRt7BVHdREQZ5lpzoe5mFEYZUWe+oq8HBvk9JjpibyEV4Jg==", + "license": "ISC", + "dependencies": { + "internmap": "1 - 2" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-axis": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/d3-axis/-/d3-axis-3.0.0.tgz", + "integrity": "sha512-IH5tgjV4jE/GhHkRV0HiVYPDtvfjHQlQfJHs0usq7M30XcSBvOotpmH1IgkcXsO/5gEQZD43B//fc7SRT5S+xw==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-brush": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/d3-brush/-/d3-brush-3.0.0.tgz", + "integrity": "sha512-ALnjWlVYkXsVIGlOsuWH1+3udkYFI48Ljihfnh8FZPF2QS9o+PzGLBslO0PjzVoHLZ2KCVgAM8NVkXPJB2aNnQ==", + "license": "ISC", + "dependencies": { + "d3-dispatch": "1 - 3", + "d3-drag": "2 - 3", + "d3-interpolate": "1 - 3", + "d3-selection": "3", + "d3-transition": "3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-chord": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-chord/-/d3-chord-3.0.1.tgz", + "integrity": "sha512-VE5S6TNa+j8msksl7HwjxMHDM2yNK3XCkusIlpX5kwauBfXuyLAtNg9jCp/iHH61tgI4sb6R/EIMWCqEIdjT/g==", + "license": "ISC", + "dependencies": { + "d3-path": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-color": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-color/-/d3-color-3.1.0.tgz", + "integrity": "sha512-zg/chbXyeBtMQ1LbD/WSoW2DpC3I0mpmPdW+ynRTj/x2DAWYrIY7qeZIHidozwV24m4iavr15lNwIwLxRmOxhA==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-contour": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/d3-contour/-/d3-contour-4.0.2.tgz", + "integrity": "sha512-4EzFTRIikzs47RGmdxbeUvLWtGedDUNkTcmzoeyg4sP/dvCexO47AaQL7VKy/gul85TOxw+IBgA8US2xwbToNA==", + "license": "ISC", + "dependencies": { + "d3-array": "^3.2.0" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-delaunay": { + "version": "6.0.4", + "resolved": "https://registry.npmjs.org/d3-delaunay/-/d3-delaunay-6.0.4.tgz", + "integrity": "sha512-mdjtIZ1XLAM8bm/hx3WwjfHt6Sggek7qH043O8KEjDXN40xi3vx/6pYSVTwLjEgiXQTbvaouWKynLBiUZ6SK6A==", + "license": "ISC", + "dependencies": { + "delaunator": "5" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-dispatch": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-dispatch/-/d3-dispatch-3.0.1.tgz", + "integrity": "sha512-rzUyPU/S7rwUflMyLc1ETDeBj0NRuHKKAcvukozwhshr6g6c5d8zh4c2gQjY2bZ0dXeGLWc1PF174P2tVvKhfg==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-drag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/d3-drag/-/d3-drag-3.0.0.tgz", + "integrity": "sha512-pWbUJLdETVA8lQNJecMxoXfH6x+mO2UQo8rSmZ+QqxcbyA3hfeprFgIT//HW2nlHChWeIIMwS2Fq+gEARkhTkg==", + "license": "ISC", + "dependencies": { + "d3-dispatch": "1 - 3", + "d3-selection": "3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-dsv": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-dsv/-/d3-dsv-3.0.1.tgz", + "integrity": "sha512-UG6OvdI5afDIFP9w4G0mNq50dSOsXHJaRE8arAS5o9ApWnIElp8GZw1Dun8vP8OyHOZ/QJUKUJwxiiCCnUwm+Q==", + "license": "ISC", + "dependencies": { + "commander": "7", + "iconv-lite": "0.6", + "rw": "1" + }, + "bin": { + "csv2json": "bin/dsv2json.js", + "csv2tsv": "bin/dsv2dsv.js", + "dsv2dsv": "bin/dsv2dsv.js", + "dsv2json": "bin/dsv2json.js", + "json2csv": "bin/json2dsv.js", + "json2dsv": "bin/json2dsv.js", + "json2tsv": "bin/json2dsv.js", + "tsv2csv": "bin/dsv2dsv.js", + "tsv2json": "bin/dsv2json.js" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-dsv/node_modules/commander": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-7.2.0.tgz", + "integrity": "sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==", + "license": "MIT", + "engines": { + "node": ">= 10" + } + }, + "node_modules/d3-ease": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-ease/-/d3-ease-3.0.1.tgz", + "integrity": "sha512-wR/XK3D3XcLIZwpbvQwQ5fK+8Ykds1ip7A2Txe0yxncXSdq1L9skcG7blcedkOX+ZcgxGAmLX1FrRGbADwzi0w==", + "license": "BSD-3-Clause", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-fetch": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-fetch/-/d3-fetch-3.0.1.tgz", + "integrity": "sha512-kpkQIM20n3oLVBKGg6oHrUchHM3xODkTzjMoj7aWQFq5QEM+R6E4WkzT5+tojDY7yjez8KgCBRoj4aEr99Fdqw==", + "license": "ISC", + "dependencies": { + "d3-dsv": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-force": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/d3-force/-/d3-force-3.0.0.tgz", + "integrity": "sha512-zxV/SsA+U4yte8051P4ECydjD/S+qeYtnaIyAs9tgHCqfguma/aAQDjo85A9Z6EKhBirHRJHXIgJUlffT4wdLg==", + "license": "ISC", + "dependencies": { + "d3-dispatch": "1 - 3", + "d3-quadtree": "1 - 3", + "d3-timer": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-format": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-format/-/d3-format-3.1.0.tgz", + "integrity": "sha512-YyUI6AEuY/Wpt8KWLgZHsIU86atmikuoOmCfommt0LYHiQSPjvX2AcFc38PX0CBpr2RCyZhjex+NS/LPOv6YqA==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-geo": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/d3-geo/-/d3-geo-3.1.1.tgz", + "integrity": "sha512-637ln3gXKXOwhalDzinUgY83KzNWZRKbYubaG+fGVuc/dxO64RRljtCTnf5ecMyE1RIdtqpkVcq0IbtU2S8j2Q==", + "license": "ISC", + "dependencies": { + "d3-array": "2.5.0 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-hierarchy": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/d3-hierarchy/-/d3-hierarchy-3.1.2.tgz", + "integrity": "sha512-FX/9frcub54beBdugHjDCdikxThEqjnR93Qt7PvQTOHxyiNCAlvMrHhclk3cD5VeAaq9fxmfRp+CnWw9rEMBuA==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-interpolate": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-interpolate/-/d3-interpolate-3.0.1.tgz", + "integrity": "sha512-3bYs1rOD33uo8aqJfKP3JWPAibgw8Zm2+L9vBKEHJ2Rg+viTR7o5Mmv5mZcieN+FRYaAOWX5SJATX6k1PWz72g==", + "license": "ISC", + "dependencies": { + "d3-color": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-path": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-path/-/d3-path-3.1.0.tgz", + "integrity": "sha512-p3KP5HCf/bvjBSSKuXid6Zqijx7wIfNW+J/maPs+iwR35at5JCbLUT0LzF1cnjbCHWhqzQTIN2Jpe8pRebIEFQ==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-polygon": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-polygon/-/d3-polygon-3.0.1.tgz", + "integrity": "sha512-3vbA7vXYwfe1SYhED++fPUQlWSYTTGmFmQiany/gdbiWgU/iEyQzyymwL9SkJjFFuCS4902BSzewVGsHHmHtXg==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-quadtree": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-quadtree/-/d3-quadtree-3.0.1.tgz", + "integrity": "sha512-04xDrxQTDTCFwP5H6hRhsRcb9xxv2RzkcsygFzmkSIOJy3PeRJP7sNk3VRIbKXcog561P9oU0/rVH6vDROAgUw==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-random": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-random/-/d3-random-3.0.1.tgz", + "integrity": "sha512-FXMe9GfxTxqd5D6jFsQ+DJ8BJS4E/fT5mqqdjovykEB2oFbTMDVdg1MGFxfQW+FBOGoB++k8swBrgwSHT1cUXQ==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-scale": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/d3-scale/-/d3-scale-4.0.2.tgz", + "integrity": "sha512-GZW464g1SH7ag3Y7hXjf8RoUuAFIqklOAq3MRl4OaWabTFJY9PN/E1YklhXLh+OQ3fM9yS2nOkCoS+WLZ6kvxQ==", + "license": "ISC", + "dependencies": { + "d3-array": "2.10.0 - 3", + "d3-format": "1 - 3", + "d3-interpolate": "1.2.0 - 3", + "d3-time": "2.1.1 - 3", + "d3-time-format": "2 - 4" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-scale-chromatic": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-scale-chromatic/-/d3-scale-chromatic-3.1.0.tgz", + "integrity": "sha512-A3s5PWiZ9YCXFye1o246KoscMWqf8BsD9eRiJ3He7C9OBaxKhAd5TFCdEx/7VbKtxxTsu//1mMJFrEt572cEyQ==", + "license": "ISC", + "dependencies": { + "d3-color": "1 - 3", + "d3-interpolate": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-selection": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/d3-selection/-/d3-selection-3.0.0.tgz", + "integrity": "sha512-fmTRWbNMmsmWq6xJV8D19U/gw/bwrHfNXxrIN+HfZgnzqTHp9jOmKMhsTUjXOJnZOdZY9Q28y4yebKzqDKlxlQ==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-shape": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/d3-shape/-/d3-shape-3.2.0.tgz", + "integrity": "sha512-SaLBuwGm3MOViRq2ABk3eLoxwZELpH6zhl3FbAoJ7Vm1gofKx6El1Ib5z23NUEhF9AsGl7y+dzLe5Cw2AArGTA==", + "license": "ISC", + "dependencies": { + "d3-path": "^3.1.0" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-time": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/d3-time/-/d3-time-3.1.0.tgz", + "integrity": "sha512-VqKjzBLejbSMT4IgbmVgDjpkYrNWUYJnbCGo874u7MMKIWsILRX+OpX/gTk8MqjpT1A/c6HY2dCA77ZN0lkQ2Q==", + "license": "ISC", + "dependencies": { + "d3-array": "2 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-time-format": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/d3-time-format/-/d3-time-format-4.1.0.tgz", + "integrity": "sha512-dJxPBlzC7NugB2PDLwo9Q8JiTR3M3e4/XANkreKSUxF8vvXKqm1Yfq4Q5dl8budlunRVlUUaDUgFt7eA8D6NLg==", + "license": "ISC", + "dependencies": { + "d3-time": "1 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-timer": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-timer/-/d3-timer-3.0.1.tgz", + "integrity": "sha512-ndfJ/JxxMd3nw31uyKoY2naivF+r29V+Lc0svZxe1JvvIRmi8hUsrMvdOwgS1o6uBHmiz91geQ0ylPP0aj1VUA==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, + "node_modules/d3-transition": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/d3-transition/-/d3-transition-3.0.1.tgz", + "integrity": "sha512-ApKvfjsSR6tg06xrL434C0WydLr7JewBB3V+/39RMHsaXTOG0zmt/OAXeng5M5LBm0ojmxJrpomQVZ1aPvBL4w==", + "license": "ISC", + "dependencies": { + "d3-color": "1 - 3", + "d3-dispatch": "1 - 3", + "d3-ease": "1 - 3", + "d3-interpolate": "1 - 3", + "d3-timer": "1 - 3" + }, + "engines": { + "node": ">=12" + }, + "peerDependencies": { + "d3-selection": "2 - 3" + } + }, + "node_modules/d3-zoom": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/d3-zoom/-/d3-zoom-3.0.0.tgz", + "integrity": "sha512-b8AmV3kfQaqWAuacbPuNbL6vahnOJflOhexLzMMNLga62+/nh0JzvJ0aO/5a5MVgUFGS7Hu1P9P03o3fJkDCyw==", + "license": "ISC", + "dependencies": { + "d3-dispatch": "1 - 3", + "d3-drag": "2 - 3", + "d3-interpolate": "1 - 3", + "d3-selection": "2 - 3", + "d3-transition": "2 - 3" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/delaunator": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/delaunator/-/delaunator-5.0.1.tgz", + "integrity": "sha512-8nvh+XBe96aCESrGOqMp/84b13H9cdKbG5P2ejQCh4d4sK9RL4371qou9drQjMhvnPmhWl5hnmqbEE0fXr9Xnw==", + "license": "ISC", + "dependencies": { + "robust-predicates": "^3.0.2" + } + }, "node_modules/delayed-stream": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", @@ -341,6 +873,61 @@ "integrity": "sha512-98l0sW87ZT58pU4i61wa2OHwxbiYSbuxsCBozaVnYX2iCnr3bLM3fIes1/ej7h1YdOKuKt/MLs706TVnALA65w==", "license": "BSD-2-Clause" }, + "node_modules/dom-serializer": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-2.0.0.tgz", + "integrity": "sha512-wIkAryiqt/nV5EQKqQpo3SToSOV9J0DnbJqwK7Wv/Trc92zIAYZ4FlMu+JPFW1DfGFt81ZTCGgDEabffXeLyJg==", + "license": "MIT", + "dependencies": { + "domelementtype": "^2.3.0", + "domhandler": "^5.0.2", + "entities": "^4.2.0" + }, + "funding": { + "url": "https://github.com/cheeriojs/dom-serializer?sponsor=1" + } + }, + "node_modules/domelementtype": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-2.3.0.tgz", + "integrity": "sha512-OLETBj6w0OsagBwdXnPdN0cnMfF9opN69co+7ZrbfPGrdpPVNBUj02spi6B1N7wChLQiPn4CSH/zJvXw56gmHw==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/fb55" + } + ], + "license": "BSD-2-Clause" + }, + "node_modules/domhandler": { + "version": "5.0.3", + "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-5.0.3.tgz", + "integrity": "sha512-cgwlv/1iFQiFnU96XXgROh8xTeetsnJiDsTc7TYCLFd9+/WNkIqPTxiM/8pSd8VIrhXGTf1Ny1q1hquVqDJB5w==", + "license": "BSD-2-Clause", + "dependencies": { + "domelementtype": "^2.3.0" + }, + "engines": { + "node": ">= 4" + }, + "funding": { + "url": "https://github.com/fb55/domhandler?sponsor=1" + } + }, + "node_modules/domutils": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/domutils/-/domutils-3.2.2.tgz", + "integrity": "sha512-6kZKyUajlDuqlHKVX1w7gyslj9MPIXzIFiz/rGu35uC1wMi+kMhQwGhl4lt9unC9Vb9INnY9Z3/ZA3+FhASLaw==", + "license": "BSD-2-Clause", + "dependencies": { + "dom-serializer": "^2.0.0", + "domelementtype": "^2.3.0", + "domhandler": "^5.0.3" + }, + "funding": { + "url": "https://github.com/fb55/domutils?sponsor=1" + } + }, "node_modules/duck": { "version": "0.1.12", "resolved": "https://registry.npmjs.org/duck/-/duck-0.1.12.tgz", @@ -364,6 +951,19 @@ "node": ">= 0.4" } }, + "node_modules/encoding-sniffer": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/encoding-sniffer/-/encoding-sniffer-0.2.1.tgz", + "integrity": "sha512-5gvq20T6vfpekVtqrYQsSCFZ1wEg5+wW0/QaZMWkFr6BqD3NfKs0rLCx4rrVlSWJeZb5NBJgVLswK/w2MWU+Gw==", + "license": "MIT", + "dependencies": { + "iconv-lite": "^0.6.3", + "whatwg-encoding": "^3.1.1" + }, + "funding": { + "url": "https://github.com/fb55/encoding-sniffer?sponsor=1" + } + }, "node_modules/entities": { "version": "4.5.0", "resolved": "https://registry.npmjs.org/entities/-/entities-4.5.0.tgz", @@ -613,6 +1213,46 @@ "node": ">= 0.4" } }, + "node_modules/highlight.js": { + "version": "11.11.1", + "resolved": "https://registry.npmjs.org/highlight.js/-/highlight.js-11.11.1.tgz", + "integrity": "sha512-Xwwo44whKBVCYoliBQwaPvtd/2tYFkRQtXDWj1nackaV2JPXx3L0+Jvd8/qCJ2p+ML0/XVkJ2q+Mr+UVdpJK5w==", + "license": "BSD-3-Clause", + "engines": { + "node": ">=12.0.0" + } + }, + "node_modules/htmlparser2": { + "version": "9.1.0", + "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-9.1.0.tgz", + "integrity": "sha512-5zfg6mHUoaer/97TxnGpxmbR7zJtPwIYFMZ/H5ucTlPZhKvtum05yiPK3Mgai3a0DyVxv7qYqoweaEd2nrYQzQ==", + "funding": [ + "https://github.com/fb55/htmlparser2?sponsor=1", + { + "type": "github", + "url": "https://github.com/sponsors/fb55" + } + ], + "license": "MIT", + "dependencies": { + "domelementtype": "^2.3.0", + "domhandler": "^5.0.3", + "domutils": "^3.1.0", + "entities": "^4.5.0" + } + }, + "node_modules/iconv-lite": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", + "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", + "license": "MIT", + "dependencies": { + "safer-buffer": ">= 2.1.2 < 3.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/immediate": { "version": "3.0.6", "resolved": "https://registry.npmjs.org/immediate/-/immediate-3.0.6.tgz", @@ -625,6 +1265,15 @@ "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", "license": "ISC" }, + "node_modules/internmap": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/internmap/-/internmap-2.0.3.tgz", + "integrity": "sha512-5Hh7Y1wQbvY5ooGgPbDaL5iYLAPzMTUrjMulskHLH6wnv/A+1q5rgEaiuqEjB+oxGXIVZs1FF+R/KPN3ZSQYYg==", + "license": "ISC", + "engines": { + "node": ">=12" + } + }, "node_modules/isarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", @@ -643,6 +1292,22 @@ "setimmediate": "^1.0.5" } }, + "node_modules/katex": { + "version": "0.16.22", + "resolved": "https://registry.npmjs.org/katex/-/katex-0.16.22.tgz", + "integrity": "sha512-XCHRdUw4lf3SKBaJe4EvgqIuWwkPSo9XoeO8GjQW94Bp7TWv9hNhzZjZ+OH9yf1UmLygb7DIT5GSFQiyt16zYg==", + "funding": [ + "https://opencollective.com/katex", + "https://github.com/sponsors/katex" + ], + "license": "MIT", + "dependencies": { + "commander": "^8.3.0" + }, + "bin": { + "katex": "cli.js" + } + }, "node_modules/lie": { "version": "3.3.0", "resolved": "https://registry.npmjs.org/lie/-/lie-3.3.0.tgz", @@ -652,6 +1317,15 @@ "immediate": "~3.0.5" } }, + "node_modules/linkify-it": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/linkify-it/-/linkify-it-5.0.0.tgz", + "integrity": "sha512-5aHCbzQRADcdP+ATqnDuhhJ/MRIqDkZX5pyjFHRRysS8vZ5AbqGEoFIb6pYHPZ+L/OC2Lc+xT8uHVVR5CAK/wQ==", + "license": "MIT", + "dependencies": { + "uc.micro": "^2.0.0" + } + }, "node_modules/lop": { "version": "0.4.2", "resolved": "https://registry.npmjs.org/lop/-/lop-0.4.2.tgz", @@ -696,6 +1370,53 @@ "node": ">=12.0.0" } }, + "node_modules/markdown-it": { + "version": "14.1.0", + "resolved": "https://registry.npmjs.org/markdown-it/-/markdown-it-14.1.0.tgz", + "integrity": "sha512-a54IwgWPaeBCAAsv13YgmALOF1elABB08FxO9i+r4VFk5Vl4pKokRPeX8u5TCgSsPi6ec1otfLjdOpVcgbpshg==", + "license": "MIT", + "dependencies": { + "argparse": "^2.0.1", + "entities": "^4.4.0", + "linkify-it": "^5.0.0", + "mdurl": "^2.0.0", + "punycode.js": "^2.3.1", + "uc.micro": "^2.1.0" + }, + "bin": { + "markdown-it": "bin/markdown-it.mjs" + } + }, + "node_modules/markdown-it-ins": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/markdown-it-ins/-/markdown-it-ins-4.0.0.tgz", + "integrity": "sha512-sWbjK2DprrkINE4oYDhHdCijGT+MIDhEupjSHLXe5UXeVr5qmVxs/nTUVtgi0Oh/qtF+QKV0tNWDhQBEPxiMew==", + "license": "MIT" + }, + "node_modules/markdown-it-mark": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/markdown-it-mark/-/markdown-it-mark-4.0.0.tgz", + "integrity": "sha512-YLhzaOsU9THO/cal0lUjfMjrqSMPjjyjChYM7oyj4DnyaXEzA8gnW6cVJeyCrCVeyesrY2PlEdUYJSPFYL4Nkg==", + "license": "MIT" + }, + "node_modules/markdown-it-sub": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/markdown-it-sub/-/markdown-it-sub-2.0.0.tgz", + "integrity": "sha512-iCBKgwCkfQBRg2vApy9vx1C1Tu6D8XYo8NvevI3OlwzBRmiMtsJ2sXupBgEA7PPxiDwNni3qIUkhZ6j5wofDUA==", + "license": "MIT" + }, + "node_modules/markdown-it-sup": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/markdown-it-sup/-/markdown-it-sup-2.0.0.tgz", + "integrity": "sha512-5VgmdKlkBd8sgXuoDoxMpiU+BiEt3I49GItBzzw7Mxq9CxvnhE/k09HFli09zgfFDRixDQDfDxi0mgBCXtaTvA==", + "license": "MIT" + }, + "node_modules/markdown-it/node_modules/argparse": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", + "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==", + "license": "Python-2.0" + }, "node_modules/marked": { "version": "16.2.1", "resolved": "https://registry.npmjs.org/marked/-/marked-16.2.1.tgz", @@ -708,6 +1429,68 @@ "node": ">= 20" } }, + "node_modules/markmap-common": { + "version": "0.18.9", + "resolved": "https://registry.npmjs.org/markmap-common/-/markmap-common-0.18.9.tgz", + "integrity": "sha512-MV2HQO7IGIm3jWEJXSG8vmdpqf4WIDXcEyAEN52lrWR1qD53Zg5l81JwjXoZ2l0rY5mofKYqUFlmdM2fqTGMVg==", + "license": "MIT", + "peer": true, + "dependencies": { + "@babel/runtime": "^7.22.6", + "@gera2ld/jsx-dom": "^2.2.2", + "npm2url": "^0.2.4" + } + }, + "node_modules/markmap-html-parser": { + "version": "0.18.11", + "resolved": "https://registry.npmjs.org/markmap-html-parser/-/markmap-html-parser-0.18.11.tgz", + "integrity": "sha512-+kC5C4sCGntGUhGvTa5VIb5rtM75cSy/VCy3tzZoNAcn2qZGdgYvljN0WvjsOzrEzp+V6XKgwzO0u2TdzNAiOg==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.22.6", + "cheerio": "1.0.0" + }, + "peerDependencies": { + "markmap-common": "*" + } + }, + "node_modules/markmap-lib": { + "version": "0.18.12", + "resolved": "https://registry.npmjs.org/markmap-lib/-/markmap-lib-0.18.12.tgz", + "integrity": "sha512-WCA4OT+b71jYg0e4PS/6NRKqihod5OpPsvw1jEGHQwCtqQrY/yXXCeRyuL3axOS5cMy5pV8BSl4CwKfJU1LxJg==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.22.6", + "@vscode/markdown-it-katex": "^1.1.0", + "highlight.js": "^11.8.0", + "katex": "^0.16.8", + "markdown-it": "^14.1.0", + "markdown-it-ins": "^4.0.0", + "markdown-it-mark": "^4.0.0", + "markdown-it-sub": "^2.0.0", + "markdown-it-sup": "^2.0.0", + "markmap-html-parser": "0.18.11", + "markmap-view": "0.18.12", + "prismjs": "^1.29.0", + "yaml": "^2.5.1" + }, + "peerDependencies": { + "markmap-common": "*" + } + }, + "node_modules/markmap-view": { + "version": "0.18.12", + "resolved": "https://registry.npmjs.org/markmap-view/-/markmap-view-0.18.12.tgz", + "integrity": "sha512-D8bzT1YwIC/8rkbwm6WzigVUrpOAGv7ioEGTi1Lj+Oo8gO5sAm6hhli27jvTgUcZ9TwBeIWZ+dSUP+AupYUGlQ==", + "license": "MIT", + "dependencies": { + "@babel/runtime": "^7.22.6", + "d3": "^7.8.5" + }, + "peerDependencies": { + "markmap-common": "*" + } + }, "node_modules/math-intrinsics": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz", @@ -717,6 +1500,12 @@ "node": ">= 0.4" } }, + "node_modules/mdurl": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mdurl/-/mdurl-2.0.0.tgz", + "integrity": "sha512-Lf+9+2r+Tdp5wXDXC4PcIBjTDtq4UKjCPMQhKIuzpJNW0b96kVqSwW0bT7FhRSfmAiFYgP+SCRvdrDozfh0U5w==", + "license": "MIT" + }, "node_modules/mime-db": { "version": "1.52.0", "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", @@ -738,12 +1527,6 @@ "node": ">= 0.6" } }, - "node_modules/mind-elixir": { - "version": "3.3.2", - "resolved": "https://registry.npmjs.org/mind-elixir/-/mind-elixir-3.3.2.tgz", - "integrity": "sha512-SHHospQXT7ARaNMMnaZLFzBsOela9tc8rgSYHPhAPrV8Jxh6MCo1X8qQxJAvuqIVvN8uSGnXf+Po4nhzzSmWWQ==", - "license": "MIT" - }, "node_modules/nanoid": { "version": "3.3.11", "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.11.tgz", @@ -762,6 +1545,25 @@ "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" } }, + "node_modules/npm2url": { + "version": "0.2.4", + "resolved": "https://registry.npmjs.org/npm2url/-/npm2url-0.2.4.tgz", + "integrity": "sha512-arzGp/hQz0Ey+ZGhF64XVH7Xqwd+1Q/po5uGiBbzph8ebX6T0uvt3N7c1nBHQNsQVykQgHhqoRTX7JFcHecGuw==", + "license": "MIT", + "peer": true + }, + "node_modules/nth-check": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/nth-check/-/nth-check-2.1.1.tgz", + "integrity": "sha512-lqjrjmaOoAnWfMmBPL+XNnynZh2+swxiX3WUE0s4yEHI6m+AwrK2UZOimIRl3X/4QctVqS8AiZjFqyOGrMXb/w==", + "license": "BSD-2-Clause", + "dependencies": { + "boolbase": "^1.0.0" + }, + "funding": { + "url": "https://github.com/fb55/nth-check?sponsor=1" + } + }, "node_modules/option": { "version": "0.2.4", "resolved": "https://registry.npmjs.org/option/-/option-0.2.4.tgz", @@ -774,6 +1576,55 @@ "integrity": "sha512-4hLB8Py4zZce5s4yd9XzopqwVv/yGNhV1Bl8NTmCq1763HeK2+EwVTv+leGeL13Dnh2wfbqowVPXCIO0z4taYw==", "license": "(MIT AND Zlib)" }, + "node_modules/parse5": { + "version": "7.3.0", + "resolved": "https://registry.npmjs.org/parse5/-/parse5-7.3.0.tgz", + "integrity": "sha512-IInvU7fabl34qmi9gY8XOVxhYyMyuH2xUNpb2q8/Y+7552KlejkRvqvD19nMoUW/uQGGbqNpA6Tufu5FL5BZgw==", + "license": "MIT", + "dependencies": { + "entities": "^6.0.0" + }, + "funding": { + "url": "https://github.com/inikulin/parse5?sponsor=1" + } + }, + "node_modules/parse5-htmlparser2-tree-adapter": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/parse5-htmlparser2-tree-adapter/-/parse5-htmlparser2-tree-adapter-7.1.0.tgz", + "integrity": "sha512-ruw5xyKs6lrpo9x9rCZqZZnIUntICjQAd0Wsmp396Ul9lN/h+ifgVV1x1gZHi8euej6wTfpqX8j+BFQxF0NS/g==", + "license": "MIT", + "dependencies": { + "domhandler": "^5.0.3", + "parse5": "^7.0.0" + }, + "funding": { + "url": "https://github.com/inikulin/parse5?sponsor=1" + } + }, + "node_modules/parse5-parser-stream": { + "version": "7.1.2", + "resolved": "https://registry.npmjs.org/parse5-parser-stream/-/parse5-parser-stream-7.1.2.tgz", + "integrity": "sha512-JyeQc9iwFLn5TbvvqACIF/VXG6abODeB3Fwmv/TGdLk2LfbWkaySGY72at4+Ty7EkPZj854u4CrICqNk2qIbow==", + "license": "MIT", + "dependencies": { + "parse5": "^7.0.0" + }, + "funding": { + "url": "https://github.com/inikulin/parse5?sponsor=1" + } + }, + "node_modules/parse5/node_modules/entities": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/entities/-/entities-6.0.1.tgz", + "integrity": "sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g==", + "license": "BSD-2-Clause", + "engines": { + "node": ">=0.12" + }, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" + } + }, "node_modules/path-is-absolute": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", @@ -829,6 +1680,15 @@ "node": "^10 || ^12 || >=14" } }, + "node_modules/prismjs": { + "version": "1.30.0", + "resolved": "https://registry.npmjs.org/prismjs/-/prismjs-1.30.0.tgz", + "integrity": "sha512-DEvV2ZF2r2/63V+tK8hQvrR2ZGn10srHbXviTlcv7Kpzw8jWiNTqbVgjO3IY8RxrrOUF8VPMQQFysYYYv0YZxw==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/process-nextick-args": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", @@ -841,6 +1701,15 @@ "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==", "license": "MIT" }, + "node_modules/punycode.js": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/punycode.js/-/punycode.js-2.3.1.tgz", + "integrity": "sha512-uxFIHU0YlHYhDQtV4R9J6a52SLx28BCjT+4ieh7IGbgwVJWO+km431c4yRlREUAsAmt/uMjQUyQHNEPf0M39CA==", + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/readable-stream": { "version": "2.3.8", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz", @@ -856,6 +1725,12 @@ "util-deprecate": "~1.0.1" } }, + "node_modules/robust-predicates": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/robust-predicates/-/robust-predicates-3.0.2.tgz", + "integrity": "sha512-IXgzBWvWQwE6PrDI05OvmXUIruQTcoMDzRsOd5CDvHCVLcLHMTSYvOK5Cm46kWqlV3yAbuSpBZdJ5oP5OUoStg==", + "license": "Unlicense" + }, "node_modules/rollup": { "version": "3.29.5", "resolved": "https://registry.npmjs.org/rollup/-/rollup-3.29.5.tgz", @@ -873,12 +1748,24 @@ "fsevents": "~2.3.2" } }, + "node_modules/rw": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/rw/-/rw-1.3.3.tgz", + "integrity": "sha512-PdhdWy89SiZogBLaw42zdeqtRJ//zFd2PgQavcICDUgJT5oW10QCRKbJ6bg4r0/UY2M6BWd5tkxuGFRvCkgfHQ==", + "license": "BSD-3-Clause" + }, "node_modules/safe-buffer": { "version": "5.1.2", "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", "license": "MIT" }, + "node_modules/safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", + "license": "MIT" + }, "node_modules/setimmediate": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.5.tgz", @@ -909,12 +1796,27 @@ "safe-buffer": "~5.1.0" } }, + "node_modules/uc.micro": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/uc.micro/-/uc.micro-2.1.0.tgz", + "integrity": "sha512-ARDJmphmdvUk6Glw7y9DQ2bFkKBHwQHLi2lsaH6PPmz/Ka9sFOBsBluozhDltWmnv9u/cF6Rt87znRTPV+yp/A==", + "license": "MIT" + }, "node_modules/underscore": { "version": "1.13.7", "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.13.7.tgz", "integrity": "sha512-GMXzWtsc57XAtguZgaQViUOzs0KTkk8ojr3/xAxXLITqf/3EMwxC0inyETfDFjH/Krbhuep0HNbbjI9i/q3F3g==", "license": "MIT" }, + "node_modules/undici": { + "version": "6.21.3", + "resolved": "https://registry.npmjs.org/undici/-/undici-6.21.3.tgz", + "integrity": "sha512-gBLkYIlEnSp8pFbT64yFgGE6UIB9tAkhukC23PmMDCe5Nd+cRqKxSjw5y54MK2AZMgZfJWMaNE4nYUHgi1XEOw==", + "license": "MIT", + "engines": { + "node": ">=18.17" + } + }, "node_modules/util-deprecate": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", @@ -998,6 +1900,27 @@ } } }, + "node_modules/whatwg-encoding": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/whatwg-encoding/-/whatwg-encoding-3.1.1.tgz", + "integrity": "sha512-6qN4hJdMwfYBtE3YBTTHhoeuUrDBPZmbQaxWAqSALV/MeEnR5z1xd8UKud2RAkFoPkmB+hli1TZSnyi84xz1vQ==", + "license": "MIT", + "dependencies": { + "iconv-lite": "0.6.3" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/whatwg-mimetype": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/whatwg-mimetype/-/whatwg-mimetype-4.0.0.tgz", + "integrity": "sha512-QaKxh0eNIi2mE9p2vEdzfagOKHCcj1pJ56EEHGQOVxp8r9/iszLUUV7v89x9O1p/T+NlTM5W7jW6+cz4Fq1YVg==", + "license": "MIT", + "engines": { + "node": ">=18" + } + }, "node_modules/xmlbuilder": { "version": "10.1.1", "resolved": "https://registry.npmjs.org/xmlbuilder/-/xmlbuilder-10.1.1.tgz", @@ -1006,6 +1929,18 @@ "engines": { "node": ">=4.0" } + }, + "node_modules/yaml": { + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.8.1.tgz", + "integrity": "sha512-lcYcMxX2PO9XMGvAJkJ3OsNMw+/7FKes7/hgerGUYWIoWu5j/+YQqcZr5JnPZWzOsEBgMbSbiSTn/dv/69Mkpw==", + "license": "ISC", + "bin": { + "yaml": "bin.mjs" + }, + "engines": { + "node": ">= 14.6" + } } } } diff --git a/frontend/node_modules/.vite/deps/_metadata.json b/frontend/node_modules/.vite/deps/_metadata.json index a2c15c3..c6dcd26 100644 --- a/frontend/node_modules/.vite/deps/_metadata.json +++ b/frontend/node_modules/.vite/deps/_metadata.json @@ -1,41 +1,71 @@ { - "hash": "6a8d66df", - "browserHash": "ef50870a", + "hash": "1229e8fa", + "browserHash": "5c2510fa", "optimized": { "axios": { "src": "../../axios/index.js", "file": "axios.js", - "fileHash": "770c42d0", + "fileHash": "c14dff39", "needsInterop": false }, "mammoth": { "src": "../../mammoth/lib/index.js", "file": "mammoth.js", - "fileHash": "699a606e", + "fileHash": "9331e90f", "needsInterop": true }, "marked": { "src": "../../marked/lib/marked.esm.js", "file": "marked.js", - "fileHash": "f070c986", - "needsInterop": false - }, - "mind-elixir": { - "src": "../../mind-elixir/dist/MindElixir.js", - "file": "mind-elixir.js", - "fileHash": "b78327d7", + "fileHash": "d9459e29", "needsInterop": false }, "pdfjs-dist": { "src": "../../pdfjs-dist/build/pdf.mjs", "file": "pdfjs-dist.js", - "fileHash": "7c5f9c82", + "fileHash": "4db246e9", "needsInterop": false }, + "prismjs": { + "src": "../../prismjs/prism.js", + "file": "prismjs.js", + "fileHash": "e122bdaf", + "needsInterop": true + }, + "prismjs/components/prism-css": { + "src": "../../prismjs/components/prism-css.js", + "file": "prismjs_components_prism-css.js", + "fileHash": "b1805788", + "needsInterop": true + }, + "prismjs/components/prism-javascript": { + "src": "../../prismjs/components/prism-javascript.js", + "file": "prismjs_components_prism-javascript.js", + "fileHash": "c034dce0", + "needsInterop": true + }, + "prismjs/components/prism-json": { + "src": "../../prismjs/components/prism-json.js", + "file": "prismjs_components_prism-json.js", + "fileHash": "1379480f", + "needsInterop": true + }, + "prismjs/components/prism-python": { + "src": "../../prismjs/components/prism-python.js", + "file": "prismjs_components_prism-python.js", + "fileHash": "fa615091", + "needsInterop": true + }, + "prismjs/components/prism-sql": { + "src": "../../prismjs/components/prism-sql.js", + "file": "prismjs_components_prism-sql.js", + "fileHash": "31352c1e", + "needsInterop": true + }, "vue": { "src": "../../vue/dist/vue.runtime.esm-bundler.js", "file": "vue.js", - "fileHash": "73ad40f1", + "fileHash": "7f03e6bd", "needsInterop": false } }, diff --git a/frontend/node_modules/.vite/deps/mind-elixir.js b/frontend/node_modules/.vite/deps/mind-elixir.js deleted file mode 100644 index ba2065a..0000000 --- a/frontend/node_modules/.vite/deps/mind-elixir.js +++ /dev/null @@ -1,2501 +0,0 @@ -import "./chunk-FOSKEDPS.js"; - -// node_modules/mind-elixir/dist/MindElixir.js -(function() { - "use strict"; - try { - if (typeof document < "u") { - var i = document.createElement("style"); - i.appendChild(document.createTextNode(".mind-elixir{--gap: 30px;--root-radius: 30px;--main-radius: 20px;--root-color: #ffffff;--root-bgcolor: #4c4f69;--main-color: #444446;--main-bgcolor: #ffffff;--topic-padding: 3px;--color: #777777;--bgcolor: #f6f6f6;--selected: #4dc4ff;--panel-color: #444446;--panel-bgcolor: #ffffff;--panel-border-color: #eaeaea;position:relative;-webkit-tap-highlight-color:rgba(0,0,0,0);font-family:-apple-system,BlinkMacSystemFont,Helvetica Neue,PingFang SC,Microsoft YaHei,Source Han Sans SC,Noto Sans CJK SC,WenQuanYi Micro Hei,sans-serif}.mind-elixir .hyper-link{text-decoration:none;margin-left:.3em}.map-container{-webkit-user-select:none;user-select:none;height:100%;width:100%;overflow:scroll;font-size:15px}.map-container::-webkit-scrollbar{width:0px;height:0px}.map-container .selected{box-shadow:0 0 0 2px var(--selected)}.map-container .lhs{direction:rtl}.map-container .lhs me-tpc{direction:ltr}.map-container .map-canvas{height:20000px;width:20000px;position:relative;-webkit-user-select:none;user-select:none;transition:transform .3s;transform:scale(1);background-color:var(--bgcolor)}.map-container .map-canvas me-nodes{position:absolute;display:flex;justify-content:center;align-items:center;height:fit-content;width:fit-content}.map-container .map-canvas me-root{position:relative}.map-container .map-canvas me-root me-tpc{display:block;font-size:25px;line-height:1.2em;color:var(--root-color);padding:10px var(--gap);border-radius:var(--root-radius);white-space:pre-wrap;background-color:var(--root-bgcolor)}.map-container .map-canvas me-root me-tpc #input-box{padding:10px var(--gap)}.map-container me-main>me-wrapper{position:relative;margin:20px 65px}.map-container me-main>me-wrapper>me-parent{margin:var(--gap);padding:0}.map-container me-main>me-wrapper>me-parent>me-tpc{border-radius:var(--main-radius);background-color:var(--main-bgcolor);border:2px solid var(--main-color);color:var(--main-color);padding:8px var(--gap)}.map-container me-main>me-wrapper>me-parent>me-tpc #input-box{padding:8px var(--gap)}.map-container me-wrapper{display:block;pointer-events:none;width:fit-content}.map-container me-children,.map-container me-parent{display:inline-block;vertical-align:middle}.map-container me-parent{position:relative;cursor:pointer;padding:6px var(--gap);margin-top:10px}.map-container me-parent me-tpc{position:relative;display:block;border-radius:3px;color:var(--color);pointer-events:all;max-width:35em;white-space:pre-wrap;padding:var(--topic-padding);line-height:1.2em}.map-container me-parent me-tpc .insert-preview{position:absolute;width:100%;left:0;z-index:9}.map-container me-parent me-tpc .show{background:#7ad5ff;pointer-events:none;opacity:.7}.map-container me-parent me-tpc .before{height:14px;top:-14px}.map-container me-parent me-tpc .in{height:100%;top:0}.map-container me-parent me-tpc .after{height:14px;bottom:-14px}.map-container me-parent me-epd{position:absolute;height:18px;width:18px;opacity:.8;background-image:url(data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBzdGFuZGFsb25lPSJubyI/PjwhRE9DVFlQRSBzdmcgUFVCTElDICItLy9XM0MvL0RURCBTVkcgMS4xLy9FTiIgImh0dHA6Ly93d3cudzMub3JnL0dyYXBoaWNzL1NWRy8xLjEvRFREL3N2ZzExLmR0ZCI+CjxzdmcgdD0iMTY1NjY1NDcxNzI0MiIgY2xhc3M9Imljb24iIHZpZXdCb3g9IjAgMCAxMDI0IDEwMjQiIHZlcnNpb249IjEuMSIKICAgIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIKICAgIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB3aWR0aD0iMjAwIiBoZWlnaHQ9IjIwMCI+CiAgICA8cGF0aCBkPSJNNTEyIDc0LjY2NjY2N0MyNzAuOTMzMzMzIDc0LjY2NjY2NyA3NC42NjY2NjcgMjcwLjkzMzMzMyA3NC42NjY2NjcgNTEyUzI3MC45MzMzMzMgOTQ5LjMzMzMzMyA1MTIgOTQ5LjMzMzMzMyA5NDkuMzMzMzMzIDc1My4wNjY2NjcgOTQ5LjMzMzMzMyA1MTIgNzUzLjA2NjY2NyA3NC42NjY2NjcgNTEyIDc0LjY2NjY2N3oiIHN0cm9rZS13aWR0aD0iNTQiIHN0cm9rZT0nYmxhY2snIGZpbGw9J3doaXRlJyA+PC9wYXRoPgogICAgPHBhdGggZD0iTTY4Mi42NjY2NjcgNDgwaC0xMzguNjY2NjY3VjM0MS4zMzMzMzNjMC0xNy4wNjY2NjctMTQuOTMzMzMzLTMyLTMyLTMycy0zMiAxNC45MzMzMzMtMzIgMzJ2MTM4LjY2NjY2N0gzNDEuMzMzMzMzYy0xNy4wNjY2NjcgMC0zMiAxNC45MzMzMzMtMzIgMzJzMTQuOTMzMzMzIDMyIDMyIDMyaDEzOC42NjY2NjdWNjgyLjY2NjY2N2MwIDE3LjA2NjY2NyAxNC45MzMzMzMgMzIgMzIgMzJzMzItMTQuOTMzMzMzIDMyLTMydi0xMzguNjY2NjY3SDY4Mi42NjY2NjdjMTcuMDY2NjY3IDAgMzItMTQuOTMzMzMzIDMyLTMycy0xNC45MzMzMzMtMzItMzItMzJ6Ij48L3BhdGg+Cjwvc3ZnPg==);background-repeat:no-repeat;background-size:contain;background-position:center;pointer-events:all;z-index:9}.map-container me-parent me-epd.minus{background-image:url(data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBzdGFuZGFsb25lPSJubyI/PjwhRE9DVFlQRSBzdmcgUFVCTElDICItLy9XM0MvL0RURCBTVkcgMS4xLy9FTiIgImh0dHA6Ly93d3cudzMub3JnL0dyYXBoaWNzL1NWRy8xLjEvRFREL3N2ZzExLmR0ZCI+CjxzdmcgdD0iMTY1NjY1NTU2NDk4NSIgY2xhc3M9Imljb24iIHZpZXdCb3g9IjAgMCAxMDI0IDEwMjQiIHZlcnNpb249IjEuMSIKICAgIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIKICAgIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB3aWR0aD0iMjAwIiBoZWlnaHQ9IjIwMCI+CiAgICA8cGF0aCBkPSJNNTEyIDc0LjY2NjY2N0MyNzAuOTMzMzMzIDc0LjY2NjY2NyA3NC42NjY2NjcgMjcwLjkzMzMzMyA3NC42NjY2NjcgNTEyUzI3MC45MzMzMzMgOTQ5LjMzMzMzMyA1MTIgOTQ5LjMzMzMzMyA5NDkuMzMzMzMzIDc1My4wNjY2NjcgOTQ5LjMzMzMzMyA1MTIgNzUzLjA2NjY2NyA3NC42NjY2NjcgNTEyIDc0LjY2NjY2N3oiIHN0cm9rZS13aWR0aD0iNTQiIHN0cm9rZT0nYmxhY2snIGZpbGw9J3doaXRlJyA+PC9wYXRoPgogICAgPHBhdGggZD0iTTY4Mi42NjY2NjcgNTQ0SDM0MS4zMzMzMzNjLTE3LjA2NjY2NyAwLTMyLTE0LjkzMzMzMy0zMi0zMnMxNC45MzMzMzMtMzIgMzItMzJoMzQxLjMzMzMzNGMxNy4wNjY2NjcgMCAzMiAxNC45MzMzMzMgMzIgMzJzLTE0LjkzMzMzMyAzMi0zMiAzMnoiPjwvcGF0aD4KPC9zdmc+)!important;transition:opacity .3s;opacity:0}.map-container me-parent me-epd.minus:hover{opacity:.8}.map-container .icon{width:1em;height:1em;vertical-align:-.15em;fill:currentColor;overflow:hidden}.map-container .lines,.map-container .summary,.map-container .subLines,.map-container .topiclinks,.map-container .linkcontroller{position:absolute;height:102%;width:100%;top:0;left:0}.map-container .topiclinks,.map-container .linkcontroller,.map-container .summary{pointer-events:none}.map-container .topiclinks text,.map-container .linkcontroller text,.map-container .summary text{pointer-events:all}.map-container .topiclinks .selected,.map-container .linkcontroller .selected,.map-container .summary .selected{pointer-events:none}.map-container .lines,.map-container .subLines{pointer-events:none;z-index:-1}.map-container .topiclinks *,.map-container .linkcontroller *{z-index:100}.map-container .topiclinks g{cursor:pointer}.map-container #input-box{position:absolute;top:0;left:0;padding:var(--topic-padding);color:var(--color);background-color:var(--bgcolor);width:max-content;max-width:35em;z-index:11;direction:ltr;-webkit-user-select:auto;user-select:auto;pointer-events:all}.map-container me-tpc>div,.map-container me-tpc>span,.map-container me-tpc>img{pointer-events:none}.map-container me-tpc>img{display:block;margin-bottom:8px;object-fit:cover}.map-container me-tpc>.text{display:inline-block}.map-container .circle{position:absolute;height:10px;width:10px;margin-top:-5px;margin-left:-5px;border-radius:100%;background:#757575;border:2px solid #ffffff;cursor:pointer}.map-container .tags{direction:ltr}.map-container .tags span{display:inline-block;border-radius:3px;padding:2px 4px;background:#d6f0f8;color:#276f86;margin:2px 3px 0 0;font-size:12px;line-height:1.3em}.map-container .icons{display:inline-block;direction:ltr;margin-right:10px}.map-container .icons span{display:inline-block}.map-container .mind-elixir-ghost{position:fixed;top:-100%;left:-100%;box-sizing:content-box;opacity:.5;background-color:#f6f6f6;max-width:200px;width:fit-content;overflow:hidden;white-space:nowrap;text-overflow:ellipsis;padding:8px 16px;border-radius:6px;border:#666666 2px solid}.map-container .selection-area{background:#4f90f22d;border:1px solid #4f90f2}.mind-elixir .context-menu{position:fixed;top:0;left:0;width:100%;height:100%;z-index:99}.mind-elixir .context-menu .menu-list{position:fixed;list-style:none;margin:0;padding:0;font:300 15px Roboto,sans-serif;color:var(--panel-color);box-shadow:0 12px 15px #0003}.mind-elixir .context-menu .menu-list li{min-width:200px;overflow:hidden;white-space:nowrap;padding:10px 14px;background:var(--panel-bgcolor);border-bottom:1px solid var(--panel-border-color)}.mind-elixir .context-menu .menu-list li a{color:#333;text-decoration:none}.mind-elixir .context-menu .menu-list li.disabled{display:none;color:#5e5e5e;background-color:#f7f7f7}.mind-elixir .context-menu .menu-list li.disabled:hover{cursor:default;background-color:#f7f7f7}.mind-elixir .context-menu .menu-list li:hover{cursor:pointer;filter:brightness(.9)}.mind-elixir .context-menu .menu-list li:first-child{border-radius:5px 5px 0 0}.mind-elixir .context-menu .menu-list li:last-child{border-bottom:0;border-radius:0 0 5px 5px}.mind-elixir .context-menu .menu-list li span:last-child{float:right}.mind-elixir .tips{position:absolute;bottom:20px;left:50%;transform:translate(-50%);color:var(--panel-color);font-weight:bolder}.mind-elixir .mobile-menu{position:absolute;left:20px;bottom:70px;z-index:99;margin:0;padding:0;color:#333;border-radius:5px;box-shadow:0 12px 15px #0003;overflow:hidden}.mind-elixir .mobile-menu *{transition:color .4s,background-color .4s}.mind-elixir .mobile-menu div{float:left;text-align:center;width:30px;overflow:hidden;white-space:nowrap;padding:8px;background-color:#fff;border-bottom:1px solid #ecf0f1}.mind-elixir .mobile-menu div a{color:#333;text-decoration:none}.mind-elixir .mobile-menu div.disabled{color:#5e5e5e;background-color:#f7f7f7}.mind-elixir .mobile-menu div.disabled:hover{cursor:default;background-color:#f7f7f7}.mind-elixir .mobile-menu div:hover{cursor:pointer;background-color:#ecf0f1}.mind-elixir-toolbar{font-family:iconfont;position:absolute;color:var(--panel-color);background:var(--panel-bgcolor);padding:10px;border-radius:5px;box-shadow:0 1px 2px #0003}.mind-elixir-toolbar svg{display:inline-block}.mind-elixir-toolbar span:active{opacity:.5}.mind-elixir-toolbar.rb{right:20px;bottom:20px}.mind-elixir-toolbar.rb span+span{margin-left:10px}.mind-elixir-toolbar.lt{font-size:20px;left:20px;top:20px}.mind-elixir-toolbar.lt span{display:block}.mind-elixir-toolbar.lt span+span{margin-top:10px}")), document.head.appendChild(i); - } - } catch (e) { - console.error("vite-plugin-css-injected-by-js", e); - } -})(); -(function(e) { - var t, n, o, i, s, r, l = '', c = (c = document.getElementsByTagName("script"))[c.length - 1].getAttribute("data-injectcss"); - if (c && !e.__iconfont__svg__cssinject__) { - e.__iconfont__svg__cssinject__ = true; - try { - document.write( - "" - ); - } catch (a) { - console && console.log(a); - } - } - function h() { - s || (s = true, o()); - } - t = function() { - var a, u, d, p; - (p = document.createElement("div")).innerHTML = l, l = null, (d = p.getElementsByTagName("svg")[0]) && (d.setAttribute("aria-hidden", "true"), d.style.position = "absolute", d.style.width = 0, d.style.height = 0, d.style.overflow = "hidden", a = d, (u = document.body).firstChild ? (p = a, (d = u.firstChild).parentNode.insertBefore(p, d)) : u.appendChild(a)); - }, document.addEventListener ? ~["complete", "loaded", "interactive"].indexOf(document.readyState) ? setTimeout(t, 0) : (n = function() { - document.removeEventListener("DOMContentLoaded", n, false), t(); - }, document.addEventListener("DOMContentLoaded", n, false)) : document.attachEvent && (o = t, i = e.document, s = false, (r = function() { - try { - i.documentElement.doScroll("left"); - } catch { - return void setTimeout(r, 50); - } - h(); - })(), i.onreadystatechange = function() { - i.readyState == "complete" && (i.onreadystatechange = null, h()); - }); -})(window); -var L = 0; -var z = 1; -var X = 2; -var T = 30; -var M = 8; -var Le = { - name: "Latte", - palette: ["#dd7878", "#ea76cb", "#8839ef", "#e64553", "#fe640b", "#df8e1d", "#40a02b", "#209fb5", "#1e66f5", "#7287fd"], - cssVar: { - "--main-color": "#444446", - "--main-bgcolor": "#ffffff", - "--color": "#777777", - "--bgcolor": "#f6f6f6", - "--panel-color": "#444446", - "--panel-bgcolor": "#ffffff", - "--panel-border-color": "#eaeaea" - } -}; -var Me = { - name: "Dark", - palette: ["#848FA0", "#748BE9", "#D2F9FE", "#4145A5", "#789AFA", "#706CF4", "#EF987F", "#775DD5", "#FCEECF", "#DA7FBC"], - cssVar: { - "--main-color": "#ffffff", - "--main-bgcolor": "#4c4f69", - "--color": "#cccccc", - "--bgcolor": "#252526", - "--panel-color": "#ffffff", - "--panel-bgcolor": "#2d3748", - "--panel-border-color": "#696969" - } -}; -function ne(e) { - return e.replace(/&/g, "&").replace(/ /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent); -var oe = function(e, t) { - if (t.id === e) - return t; - if (t.children && t.children.length) { - for (let n = 0; n < t.children.length; n++) { - const o = oe(e, t.children[n]); - if (o) - return o; - } - return null; - } else - return null; -}; -var $ = (e, t) => { - if (e.parent = t, e.children) - for (let n = 0; n < e.children.length; n++) - $(e.children[n], e); -}; -function Te(e) { - if (e.id = J(), e.children) - for (let t = 0; t < e.children.length; t++) - Te(e.children[t]); -} -var Ge = (e, t) => { - let n = Date.now(); - return function(...o) { - Date.now() - n >= t && (e(...o), n = Date.now()); - }; -}; -function $e(e, t, n, o) { - const i = o - t, s = e - n; - let r = Math.atan(Math.abs(i) / Math.abs(s)) / 3.14 * 180; - s < 0 && i > 0 && (r = 180 - r), s < 0 && i < 0 && (r = 180 + r), s > 0 && i < 0 && (r = 360 - r); - const l = 15, c = 30, h = r + c, a = r - c; - return { - x1: n + Math.cos(Math.PI * h / 180) * l, - y1: o - Math.sin(Math.PI * h / 180) * l, - x2: n + Math.cos(Math.PI * a / 180) * l, - y2: o - Math.sin(Math.PI * a / 180) * l - }; -} -function J() { - return ((/* @__PURE__ */ new Date()).getTime().toString(16) + Math.random().toString(16).substr(2)).substr(2, 16); -} -var Xe = function() { - const e = J(); - return { - topic: this.newTopicName, - id: e - }; -}; -function Je(e, t) { - let n = true; - for (; t.parent; ) { - if (t.parent === e) { - n = false; - break; - } - t = t.parent; - } - return n; -} -function De(e) { - return JSON.parse( - JSON.stringify(e, (n, o) => { - if (n !== "parent") - return o; - }) - ); -} -var K = (e, t) => { - let n = 0, o = 0; - for (; t && t !== e; ) - n += t.offsetLeft, o += t.offsetTop, t = t.offsetParent; - return { offsetLeft: n, offsetTop: o }; -}; -var C = (e, t) => { - for (const n in t) - e.setAttribute(n, t[n]); -}; -var ae = (e) => e ? e.tagName === "ME-TPC" : false; -var S = { - moved: false, - // diffrentiate click and move - mousedown: false, - onMove(e, t) { - if (this.mousedown) { - this.moved = true; - const n = e.movementX, o = e.movementY; - t.scrollTo(t.scrollLeft - n, t.scrollTop - o); - } - }, - clear() { - this.moved = false, this.mousedown = false; - } -}; -function Qe(e) { - e.map.addEventListener("click", (t) => { - var o, i; - if (t.button !== 0) - return; - if ((o = e.helper1) != null && o.moved) { - e.helper1.clear(); - return; - } - if ((i = e.helper2) != null && i.moved) { - e.helper2.clear(); - return; - } - if (S.moved) { - S.clear(); - return; - } - e.unselectNode(), e.unselectNodes(), e.unselectSummary(), e.unselectLink(); - const n = t.target; - if (n.tagName === "ME-EPD") - e.expandNode(n.previousSibling); - else if (e.editable) - ae(n) ? e.selectNode(n, false, t) : n.tagName === "text" ? n.dataset.type === "custom-link" ? e.selectLink(n.parentElement) : e.selectSummary(n.parentElement) : n.className === "circle" || e.hideLinkController && e.hideLinkController(); - else - return; - }), e.map.addEventListener("dblclick", (t) => { - if (t.preventDefault(), !e.editable) - return; - const n = t.target; - ae(n) ? e.beginEdit(n) : n.tagName === "text" && (n.dataset.type === "custom-link" ? e.editCutsomLinkLabel(n.parentElement) : e.editSummary(n.parentElement)); - }), e.map.addEventListener("mousemove", (t) => { - t.target.contentEditable !== "true" && S.onMove(t, e.container); - }), e.map.addEventListener("mousedown", (t) => { - const n = e.mouseSelectionButton === 0 ? 2 : 0; - t.button === n && t.target.contentEditable !== "true" && (S.moved = false, S.mousedown = true); - }), e.map.addEventListener("mouseleave", (t) => { - const n = e.mouseSelectionButton === 0 ? 2 : 0; - t.button === n && S.clear(); - }), e.map.addEventListener("mouseup", (t) => { - const n = e.mouseSelectionButton === 0 ? 2 : 0; - t.button === n && S.clear(); - }), e.map.addEventListener("contextmenu", (t) => { - t.preventDefault(); - }); -} -var Ze = { - create() { - return { - handlers: {}, - showHandler: function() { - console.log(this.handlers); - }, - addListener: function(e, t) { - this.handlers[e] === void 0 && (this.handlers[e] = []), this.handlers[e].push(t); - }, - fire: function(e, ...t) { - if (this.handlers[e] instanceof Array) { - const n = this.handlers[e]; - for (let o = 0; o < n.length; o++) - n[o](...t); - } - }, - removeListener: function(e, t) { - if (!this.handlers[e]) - return; - const n = this.handlers[e]; - if (!t) - n.length = 0; - else if (n.length) - for (let o = 0; o < n.length; o++) - n[o] === t && this.handlers[e].splice(o, 1); - } - }; - } -}; -var ie = document; -var et = function() { - console.time("layout"), this.nodes.innerHTML = ""; - const e = this.createTopic(this.nodeData); - ue(e, this.nodeData), e.draggable = false; - const t = ie.createElement("me-root"); - t.appendChild(e); - const n = this.nodeData.children || []; - if (this.direction === X) { - let o = 0, i = 0; - n.map((s) => { - s.direction === L ? o += 1 : s.direction === z ? i += 1 : o <= i ? (s.direction = L, o += 1) : (s.direction = z, i += 1); - }); - } - tt(this, n, t), console.timeEnd("layout"); -}; -var tt = function(e, t, n) { - const o = ie.createElement("me-main"); - o.className = "lhs"; - const i = ie.createElement("me-main"); - i.className = "rhs"; - for (let s = 0; s < t.length; s++) { - const r = t[s], { grp: l } = e.createWrapper(r); - e.direction === X ? r.direction === L ? o.appendChild(l) : i.appendChild(l) : e.direction === L ? o.appendChild(l) : i.appendChild(l); - } - e.nodes.appendChild(o), e.nodes.appendChild(n), e.nodes.appendChild(i), e.nodes.appendChild(e.lines); -}; -var nt = function(e, t) { - const n = ie.createElement("me-children"); - for (let o = 0; o < t.length; o++) { - const i = t[o], { grp: s } = e.createWrapper(i); - n.appendChild(s); - } - return n; -}; -var k = document; -var N = (e, t) => { - const o = (t ? t.mindElixirBox : k).querySelector(`[data-nodeid=me${e}]`); - if (!o) - throw new Error(`FindEle: Node ${e} not found, maybe it's collapsed.`); - return o; -}; -var ue = function(e, t) { - if (e.innerHTML = "", t.style && (e.style.color = t.style.color || "", e.style.background = t.style.background || "", e.style.fontSize = t.style.fontSize + "px", e.style.fontWeight = t.style.fontWeight || "normal"), t.branchColor && (e.style.borderColor = t.branchColor), t.image) { - const n = t.image; - if (n.url && n.width && n.height) { - const o = k.createElement("img"); - o.src = n.url, o.style.width = n.width + "px", o.style.height = n.height + "px", e.appendChild(o), e.image = o; - } else - console.warn("image url/width/height are required"); - } else - e.image && (e.image = void 0); - { - const n = k.createElement("span"); - n.className = "text", n.textContent = t.topic, e.appendChild(n), e.text = n; - } - if (t.hyperLink) { - const n = k.createElement("a"); - n.className = "hyper-link", n.target = "_blank", n.innerText = "🔗", n.href = t.hyperLink, e.appendChild(n), e.linkContainer = n; - } else - e.linkContainer && (e.linkContainer = void 0); - if (t.icons && t.icons.length) { - const n = k.createElement("span"); - n.className = "icons", n.innerHTML = t.icons.map((o) => `${ne(o)}`).join(""), e.appendChild(n), e.icons = n; - } else - e.icons && (e.icons = void 0); - if (t.tags && t.tags.length) { - const n = k.createElement("div"); - n.className = "tags", n.innerHTML = t.tags.map((o) => `${ne(o)}`).join(""), e.appendChild(n), e.tags = n; - } else - e.tags && (e.tags = void 0); -}; -var ot = function(e, t) { - const n = k.createElement("me-wrapper"), { p: o, tpc: i } = this.createParent(e); - if (n.appendChild(o), !t && e.children && e.children.length > 0) { - const s = re(e.expanded); - if (o.appendChild(s), e.expanded !== false) { - const r = nt(this, e.children); - n.appendChild(r); - } - } - return { grp: n, top: o, tpc: i }; -}; -var it = function(e) { - const t = k.createElement("me-parent"), n = this.createTopic(e); - return ue(n, e), t.appendChild(n), { p: t, tpc: n }; -}; -var st = function(e) { - const t = k.createElement("me-children"); - return t.append(...e), t; -}; -var rt = function(e) { - const t = k.createElement("me-tpc"); - return t.nodeObj = e, t.dataset.nodeid = "me" + e.id, t.draggable = this.draggable, t; -}; -function je(e) { - const t = k.createRange(); - t.selectNodeContents(e); - const n = window.getSelection(); - n && (n.removeAllRanges(), n.addRange(t)); -} -var lt = function(e) { - if (console.time("editTopic"), !e) - return; - const t = k.createElement("div"), n = e.text.textContent; - e.appendChild(t), t.id = "input-box", t.textContent = n, t.contentEditable = "true", t.spellcheck = false, t.style.cssText = `min-width:${e.offsetWidth - 8}px;`, this.direction === L && (t.style.right = "0"), t.focus(), je(t), this.bus.fire("operation", { - name: "beginEdit", - obj: e.nodeObj - }), t.addEventListener("keydown", (o) => { - o.stopPropagation(); - const i = o.key; - if (i === "Enter" || i === "Tab") { - if (o.shiftKey) - return; - o.preventDefault(), t == null || t.blur(), this.map.focus(); - } - }), t.addEventListener("blur", () => { - var s; - if (!t) - return; - const o = e.nodeObj, i = ((s = t.textContent) == null ? void 0 : s.trim()) || ""; - console.log(i), i === "" ? o.topic = n : o.topic = i, t.remove(), i !== n && (e.text.textContent = o.topic, this.linkDiv(), this.bus.fire("operation", { - name: "finishEdit", - obj: o, - origin: n - })); - }), console.timeEnd("editTopic"); -}; -var re = function(e) { - const t = k.createElement("me-epd"); - return t.expanded = e !== false, t.className = e !== false ? "minus" : "", t; -}; -var q = document; -var F = "http://www.w3.org/2000/svg"; -var ct = function(e, t) { - const n = q.createElementNS(F, "path"); - return n.setAttribute("d", e), n.setAttribute("stroke", t || "#666"), n.setAttribute("fill", "none"), n.setAttribute("stroke-width", "3"), n; -}; -var G = function(e) { - const t = q.createElementNS(F, "svg"); - return t.setAttribute("class", e), t.setAttribute("overflow", "visible"), t; -}; -var pe = function() { - const e = q.createElementNS(F, "line"); - return e.setAttribute("stroke", "#bbb"), e.setAttribute("fill", "none"), e.setAttribute("stroke-width", "2"), e; -}; -var at = function(e, t) { - const n = q.createElementNS(F, "path"); - return n.setAttribute("d", e), n.setAttribute("stroke", t || "#555"), n.setAttribute("fill", "none"), n.setAttribute("stroke-linecap", "square"), n.setAttribute("stroke-width", "2"), n; -}; -var dt = function(e, t) { - const n = { - stroke: "rgb(235, 95, 82)", - fill: "none", - "stroke-linecap": "cap", - "stroke-width": "2" - }, o = q.createElementNS(F, "g"), i = q.createElementNS(F, "path"), s = q.createElementNS(F, "path"); - return C(s, { - d: t, - ...n - }), C(i, { - d: e, - ...n, - "stroke-dasharray": "8,2" - }), o.appendChild(i), o.appendChild(s), o; -}; -var Oe = function(e, t, n) { - if (console.time("editSummary"), !t) - return; - const o = document.createElement("div"); - e.nodes.appendChild(o); - const i = t.innerHTML; - o.id = "input-box", o.textContent = i, o.contentEditable = "true", o.spellcheck = false; - const s = t.getAttribute("x") + "px", r = t.getAttribute("y") + "px"; - o.style.cssText = `min-width:${100 - 8}px;position:absolute;left:${s};top:${r};`; - const l = t.getAttribute("text-anchor"); - l === "end" ? o.style.cssText += "transform: translate(-100%, -100%);" : l === "middle" ? o.style.cssText += "transform: translate(-50%, -100%);" : o.style.cssText += "transform: translate(0, -100%);", o.focus(), je(o), o.addEventListener("keydown", (c) => { - c.stopPropagation(); - const h = c.key; - if (h === "Enter" || h === "Tab") { - if (c.shiftKey) - return; - c.preventDefault(), o.blur(), e.map.focus(); - } - }), o.addEventListener("blur", () => { - o && n(o); - }), console.timeEnd("editSummary"); -}; -var Ae = He; -var ht = function(e) { - console.time("linkDiv"); - const t = this.map.querySelector("me-root"); - this.nodes.style.top = `${1e4 - this.nodes.offsetHeight / 2}px`, this.nodes.style.left = `${1e4 - t.offsetLeft - t.offsetWidth / 2}px`; - const n = this.map.querySelectorAll("me-main > me-wrapper"); - this.lines.innerHTML = "", Ae = this.subLinkStyle === 2 ? pt : He; - for (let o = 0; o < n.length; o++) { - const i = n[o], s = i.querySelector("me-tpc"), r = i.firstChild, l = i.parentNode.className; - let c = t.offsetLeft + t.offsetWidth / 2; - const h = t.offsetTop + t.offsetHeight / 2; - let a; - const u = this.theme.palette, d = s.nodeObj.branchColor || u[o % u.length], { offsetLeft: p, offsetTop: g } = K(this.nodes, r); - l === "lhs" ? a = p + r.offsetWidth : a = p; - const m = g + r.offsetHeight / 2; - let f = ""; - if (this.mainLinkStyle === 2) - this.direction === X && (l === "lhs" ? c = c - t.offsetWidth / 6 : c = c + t.offsetWidth / 6), f = ut({ x1: c, y1: h, x2: a, y2: m }); - else { - const b = (1 - Math.abs(m - i.parentElement.offsetTop - i.parentElement.offsetHeight / 2) / i.parentElement.offsetHeight) * 0.25 * (t.offsetWidth / 2); - l === "lhs" ? c = c - t.offsetWidth / 10 - b : c = c + t.offsetWidth / 10 + b, f = ft({ x1: c, y1: h, x2: a, y2: m }); - } - this.lines.appendChild(ct(f, d)); - const v = i.children[0].children[1]; - if (v && (v.style.top = (v.parentNode.offsetHeight - v.offsetHeight) / 2 + "px", l === "lhs" ? v.style.left = "-10px" : v.style.right = "-10px"), !(e && e !== i) && i.childElementCount) { - const y = G("subLines"), b = i.lastChild; - b.tagName === "svg" && b.remove(), i.appendChild(y); - const x = i.firstChild, w = i.children[1].children, _ = Pe(w, x, l, true); - y.appendChild(at(_, d)); - } - } - this.renderCustomLink(), this.renderSummary(), console.timeEnd("linkDiv"); -}; -var Pe = function(e, t, n, o) { - let i = ""; - const s = t.offsetTop, r = t.offsetLeft, l = t.offsetWidth, c = t.offsetHeight; - for (let h = 0; h < e.length; h++) { - const a = e[h], u = a.firstChild, d = u.offsetTop, p = u.offsetLeft, g = u.offsetWidth, m = u.offsetHeight; - i += Ae({ pT: s, pL: r, pW: l, pH: c, cT: d, cL: p, cW: g, cH: m, direction: n, isFirst: o }); - const f = u.children[1]; - if (f) { - if (f.style.bottom = -(f.offsetHeight / 2) + "px", n === "lhs" ? f.style.left = "10px" : n === "rhs" && (f.style.right = "10px"), !f.expanded) - continue; - } else - continue; - const v = a.children[1].children; - v.length > 0 && (i += Pe(v, u, n)); - } - return i; -}; -function ut({ x1: e, y1: t, x2: n, y2: o }) { - return `M ${e} ${t} V ${o > t ? o - 20 : o + 20} C ${e} ${o} ${e} ${o} ${n > e ? e + 20 : e - 20} ${o} H ${n}`; -} -function ft({ x1: e, y1: t, x2: n, y2: o }) { - return `M ${e} ${t} Q ${e} ${o} ${n} ${o}`; -} -function pt({ pT: e, pL: t, pW: n, pH: o, cT: i, cL: s, cW: r, cH: l, direction: c, isFirst: h }) { - let a; - h ? a = e + o / 2 : a = e + o; - const u = i + l; - let d = 0, p = 0, g = 0; - return c === "lhs" ? (d = t + T, p = s, g = s + r) : c === "rhs" && (d = t + n - T, p = s + r, g = s), u < a + 50 && u > a - 50 ? `M ${d} ${a} H ${g} V ${u} H ${p}` : u >= a ? `M ${d} ${a} H ${g} V ${u - M} A ${M} ${M} 0 0 ${d > p ? 1 : 0} ${d > p ? g - M : g + M} ${u} H ${p}` : `M ${d} ${a} H ${g} V ${u + M} A ${M} ${M} 0 0 ${d > p ? 0 : 1} ${d > p ? g - M : g + M} ${u} H ${p}`; -} -function He({ pT: e, pL: t, pW: n, pH: o, cT: i, cL: s, cW: r, cH: l, direction: c, isFirst: h }) { - let a = 0, u = 0; - h ? a = e + o / 2 : a = e + o; - const d = i + l; - let p = 0, g = 0, m = 0; - const f = Math.min(Math.abs(a - d) / 800, 1.2) * T; - return c === "lhs" ? (m = t, p = m + T, g = m - T, u = s + T, `M ${p} ${a} C ${m} ${a} ${m + f} ${d} ${g} ${d} H ${u}`) : (m = t + n, p = m - T, g = m + T, u = s + r - T, `M ${p} ${a} C ${m} ${a} ${m - f} ${d} ${g} ${d} H ${u}`); -} -var me = { - addChild: "插入子节点", - addParent: "插入父节点", - addSibling: "插入同级节点", - removeNode: "删除节点", - focus: "专注", - cancelFocus: "取消专注", - moveUp: "上移", - moveDown: "下移", - link: "连接", - clickTips: "请点击目标节点", - summary: "摘要" -}; -var ge = { - cn: me, - zh_CN: me, - zh_TW: { - addChild: "插入子節點", - addParent: "插入父節點", - addSibling: "插入同級節點", - removeNode: "刪除節點", - focus: "專注", - cancelFocus: "取消專注", - moveUp: "上移", - moveDown: "下移", - link: "連接", - clickTips: "請點擊目標節點", - summary: "摘要" - }, - en: { - addChild: "Add child", - addParent: "Add parent", - addSibling: "Add sibling", - removeNode: "Remove node", - focus: "Focus Mode", - cancelFocus: "Cancel Focus Mode", - moveUp: "Move up", - moveDown: "Move down", - link: "Link", - clickTips: "Please click the target node", - summary: "Summary" - }, - ru: { - addChild: "Добавить дочерний элемент", - addParent: "Добавить родительский элемент", - addSibling: "Добавить на этом уровне", - removeNode: "Удалить узел", - focus: "Режим фокусировки", - cancelFocus: "Отменить режим фокусировки", - moveUp: "Поднять выше", - moveDown: "Опустить ниже", - link: "Ссылка", - clickTips: "Пожалуйста, нажмите на целевой узел", - summary: "Описание" - }, - ja: { - addChild: "子ノードを追加する", - addParent: "親ノードを追加します", - addSibling: "兄弟ノードを追加する", - removeNode: "ノードを削除", - focus: "集中", - cancelFocus: "集中解除", - moveUp: "上へ移動", - moveDown: "下へ移動", - link: "コネクト", - clickTips: "ターゲットノードをクリックしてください", - summary: "概要" - }, - pt: { - addChild: "Adicionar item filho", - addParent: "Adicionar item pai", - addSibling: "Adicionar item irmao", - removeNode: "Remover item", - focus: "Modo Foco", - cancelFocus: "Cancelar Modo Foco", - moveUp: "Mover para cima", - moveDown: "Mover para baixo", - link: "Link", - clickTips: "Favor clicar no item alvo", - summary: "Resumo" - } -}; -function mt(e, t) { - const n = (b) => { - const x = document.createElement("div"); - return x.innerText = b, x.className = "tips", x; - }, o = (b, x, w) => { - const _ = document.createElement("li"); - return _.id = b, _.innerHTML = `${ne(x)}${ne(w)}`, _; - }, i = ge[e.locale] ? e.locale : "en", s = ge[i], r = o("cm-add_child", s.addChild, "tab"), l = o("cm-add_parent", s.addParent, ""), c = o("cm-add_sibling", s.addSibling, "enter"), h = o("cm-remove_child", s.removeNode, "delete"), a = o("cm-fucus", s.focus, ""), u = o("cm-unfucus", s.cancelFocus, ""), d = o("cm-up", s.moveUp, "PgUp"), p = o("cm-down", s.moveDown, "Pgdn"), g = o("cm-down", s.link, ""), m = o("cm-down", s.summary, ""), f = document.createElement("ul"); - if (f.className = "menu-list", f.appendChild(r), f.appendChild(l), f.appendChild(c), f.appendChild(h), (!t || t.focus) && (f.appendChild(a), f.appendChild(u)), f.appendChild(d), f.appendChild(p), f.appendChild(m), (!t || t.link) && f.appendChild(g), t && t.extend) - for (let b = 0; b < t.extend.length; b++) { - const x = t.extend[b], w = o(x.name, x.name, x.key || ""); - f.appendChild(w), w.onclick = (_) => { - x.onclick(_); - }; - } - const v = document.createElement("div"); - v.className = "context-menu", v.appendChild(f), v.hidden = true, e.container.append(v); - let y = true; - e.container.oncontextmenu = function(b) { - if (b.preventDefault(), !e.editable) - return; - const x = b.target; - if (ae(x)) { - x.parentElement.tagName === "ME-ROOT" ? y = true : y = false, y ? (a.className = "disabled", d.className = "disabled", p.className = "disabled", l.className = "disabled", c.className = "disabled", h.className = "disabled") : (a.className = "", d.className = "", p.className = "", l.className = "", c.className = "", h.className = ""), e.currentNodes || e.selectNode(x), v.hidden = false, S.mousedown && (S.mousedown = false), f.style.top = "", f.style.bottom = "", f.style.left = "", f.style.right = ""; - const w = f.getBoundingClientRect(), _ = f.offsetHeight, P = f.offsetWidth, U = b.clientY - w.top, H = b.clientX - w.left; - _ + U > window.innerHeight ? (f.style.top = "", f.style.bottom = "0px") : (f.style.bottom = "", f.style.top = U + 15 + "px"), P + H > window.innerWidth ? (f.style.left = "", f.style.right = "0px") : (f.style.right = "", f.style.left = H + 10 + "px"); - } - }, v.onclick = (b) => { - b.target === v && (v.hidden = true); - }, r.onclick = () => { - e.addChild(), v.hidden = true; - }, l.onclick = () => { - e.insertParent(), v.hidden = true; - }, c.onclick = () => { - y || (e.insertSibling(), v.hidden = true); - }, h.onclick = () => { - y || (e.removeNode(), v.hidden = true); - }, a.onclick = () => { - y || (e.focusNode(e.currentNode), v.hidden = true); - }, u.onclick = () => { - e.cancelFocus(), v.hidden = true; - }, d.onclick = () => { - y || (e.moveUpNode(), v.hidden = true); - }, p.onclick = () => { - y || (e.moveDownNode(), v.hidden = true); - }, g.onclick = () => { - v.hidden = true; - const b = e.currentNode, x = n(s.clickTips); - e.container.appendChild(x), e.map.addEventListener( - "click", - (w) => { - w.preventDefault(), x.remove(); - const _ = w.target; - _.parentElement.tagName === "ME-PARENT" || _.parentElement.tagName === "ME-ROOT" ? e.createLink(b, _) : console.log("link cancel"); - }, - { - once: true - } - ); - }, m.onclick = () => { - v.hidden = true, e.createSummary(), e.unselectNodes(); - }; -} -var gt = (e) => { - const t = e.map.querySelectorAll(".lhs>me-wrapper>me-parent>me-tpc"); - e.selectNode(t[Math.ceil(t.length / 2) - 1]); -}; -var vt = (e) => { - const t = e.map.querySelectorAll(".rhs>me-wrapper>me-parent>me-tpc"); - e.selectNode(t[Math.ceil(t.length / 2) - 1]); -}; -var ve = (e) => { - e.selectNode(e.map.querySelector("me-root>me-tpc")); -}; -function bt(e) { - const t = { - 13: (n) => { - n.shiftKey ? e.insertBefore() : e.insertSibling(); - }, - 9: () => { - e.addChild(); - }, - 112: () => { - e.toCenter(); - }, - 113: () => { - e.beginEdit(); - }, - 38: (n) => { - if (n.altKey) - e.moveUpNode(); - else { - if (n.metaKey || n.ctrlKey) - return e.initSide(); - e.selectPrevSibling(); - } - }, - 40: (n) => { - n.altKey ? e.moveDownNode() : e.selectNextSibling(); - }, - 37: (n) => { - var s; - if (n.metaKey || n.ctrlKey) - return e.initLeft(); - if (!e.currentNode) - return; - const o = e.currentNode.nodeObj, i = e.currentNode.offsetParent.offsetParent.parentElement; - e.currentNode.nodeObj.root ? gt(e) : i.className === "rhs" ? (s = o.parent) != null && s.root ? ve(e) : e.selectParent() : i.className === "lhs" && e.selectFirstChild(); - }, - 39: (n) => { - var s; - if (n.metaKey || n.ctrlKey) - return e.initRight(); - if (!e.currentNode) - return; - const o = e.currentNode.nodeObj, i = e.currentNode.offsetParent.offsetParent.parentElement; - o.root ? vt(e) : i.className === "lhs" ? (s = o.parent) != null && s.root ? ve(e) : e.selectParent() : i.className === "rhs" && e.selectFirstChild(); - }, - 33() { - e.moveUpNode(); - }, - 34() { - e.moveDownNode(); - }, - 67: (n) => { - (n.metaKey || n.ctrlKey) && (e.waitCopy = e.currentNode); - }, - 86: (n) => { - !e.waitCopy || !e.currentNode || (n.metaKey || n.ctrlKey) && (e.copyNode(e.waitCopy, e.currentNode), e.waitCopy = null); - }, - // ctrl + - 187: (n) => { - if (n.metaKey || n.ctrlKey) { - if (e.scaleVal > 1.6) - return; - e.scale(e.scaleVal += 0.2); - } - }, - // ctrl - - 189: (n) => { - if (n.metaKey || n.ctrlKey) { - if (e.scaleVal < 0.6) - return; - e.scale(e.scaleVal -= 0.2); - } - }, - // ctrl 0 - 48: (n) => { - (n.metaKey || n.ctrlKey) && e.scale(1); - } - }; - e.map.onkeydown = (n) => { - if (n.preventDefault(), !!e.editable && n.target === n.currentTarget) - if (n.keyCode === 8 || n.keyCode === 46) - e.currentLink ? e.removeLink() : e.currentSummary ? e.removeSummary(e.currentSummary.summaryObj.id) : e.currentNode ? e.removeNode() : e.currentNodes && e.removeNodes(e.currentNodes); - else { - const o = t[n.keyCode]; - o && o(n); - } - }; -} -function yt(e, t) { - const n = (d, p) => { - const g = document.createElement("div"); - return g.id = d, g.innerHTML = ``, g; - }, o = n("cm-add_child", "zijiedian"), i = n("cm-add_sibling", "tongjijiedian-"), s = n("cm-remove_child", "shanchu2"), r = n("cm-up", "rising"), l = n("cm-down", "falling"), c = n("cm-edit", "edit"), h = document.createElement("ul"); - if (h.className = "menu-list", t && t.extend) - for (let d = 0; d < t.extend.length; d++) { - const p = t.extend[d], g = n(p.name, p.name); - h.appendChild(g), g.onclick = (m) => { - p.onclick(m); - }; - } - const a = document.createElement("mmenu"); - a.className = "mobile-menu", a.appendChild(o), a.appendChild(i), a.appendChild(s), a.appendChild(r), a.appendChild(l), a.appendChild(c), a.hidden = true, e.container.append(a); - let u = true; - e.bus.addListener("unselectNode", function() { - a.hidden = true; - }), e.bus.addListener("selectNode", function(d) { - a.hidden = false, d.root ? u = true : u = false; - }), a.onclick = (d) => { - d.target === a && (a.hidden = true); - }, o.onclick = () => { - e.addChild(); - }, i.onclick = () => { - u || e.insertSibling(); - }, s.onclick = () => { - u || e.removeNode(); - }, r.onclick = (d) => { - u || e.moveUpNode(); - }, l.onclick = (d) => { - u || e.moveDownNode(); - }, c.onclick = (d) => { - e.beginEdit(); - }; -} -var de = document; -var xt = function(e, t) { - if (!t) - return he(e), e; - const n = e.getElementsByClassName("insert-preview"), o = `insert-preview ${t} show`; - if (n.length > 0) - n[0].className = o; - else { - const i = de.createElement("div"); - i.className = o, e.appendChild(i); - } - return e; -}; -var he = function(e) { - if (!e) - return; - const t = e.getElementsByClassName("insert-preview"); - for (const n of t || []) - n.remove(); -}; -var be = function(e, t) { - const n = t.parentElement.parentElement.contains(e); - return e && e.tagName === "ME-TPC" && e !== t && !n && e.nodeObj.root !== true; -}; -var wt = function(e) { - const t = document.createElement("div"); - return t.className = "mind-elixir-ghost", e.map.appendChild(t), t; -}; -function Et(e) { - let t = null, n = null, o = null; - const i = wt(e), s = 12; - e.map.addEventListener("dragstart", (r) => { - var c; - const l = r.target; - if ((l == null ? void 0 : l.tagName) !== "ME-TPC") { - r.preventDefault(); - return; - } - t = l, t.parentElement.parentElement.style.opacity = "0.5", i.innerHTML = t.innerHTML, (c = r.dataTransfer) == null || c.setDragImage(i, 0, 0), S.clear(); - }), e.map.addEventListener("dragend", async (r) => { - if (!t) - return; - t.parentElement.parentElement.style.opacity = "1"; - const l = r.target; - if (l.style.opacity = "", !o) - return; - he(o); - const c = t.nodeObj; - switch (n) { - case "before": - e.moveNodeBefore(t, o), e.selectNode(N(c.id)); - break; - case "after": - e.moveNodeAfter(t, o), e.selectNode(N(c.id)); - break; - case "in": - e.moveNode(t, o); - break; - } - t = null; - }), e.map.addEventListener( - "dragover", - Ge(function(r) { - if (!t) - return; - he(o); - const l = de.elementFromPoint(r.clientX, r.clientY - s); - if (be(l, t)) { - o = l; - const c = l.getBoundingClientRect().y; - r.clientY > c + l.clientHeight ? n = "after" : r.clientY > c + l.clientHeight / 2 && (n = "in"); - } else { - const c = de.elementFromPoint(r.clientX, r.clientY + s); - if (be(c, t)) { - o = c; - const h = c.getBoundingClientRect().y; - r.clientY < h ? n = "before" : r.clientY < h + c.clientHeight / 2 && (n = "in"); - } else - n = o = null; - } - o && xt(o, n); - }, 200) - ); -} -var Nt = function(e) { - return ["createSummary", "removeSummary", "finishEditSummary"].includes(e.name) ? { - type: "summary", - value: e.obj.id - } : ["createCustomLink", "removeCustomLink", "finishEditCustomLinkLabel"].includes(e.name) ? { - type: "customLink", - value: e.obj.id - } : ["removeNodes"].includes(e.name) ? { - type: "nodes", - value: e.objs.map((t) => t.id) - } : { - type: "node", - value: e.obj.id - }; -}; -function Ct(e) { - let t = [], n = -1, o = e.getData(); - e.bus.addListener("operation", (i) => { - if (i.name === "beginEdit") - return; - t = t.slice(0, n + 1); - const s = e.getData(); - t.push({ prev: o, currentObject: Nt(i), next: s }), o = s, n = t.length - 1; - }), e.undo = function() { - if (n > -1) { - const i = t[n]; - o = i.prev, e.refresh(i.prev), i.currentObject.type === "node" && e.selectNode(N(i.currentObject.value)), n--, console.log("current", o); - } - }, e.redo = function() { - if (n < t.length - 1) { - n++; - const i = t[n]; - o = i.next, e.refresh(i.next), i.currentObject.type === "node" && e.selectNode(N(i.currentObject.value)); - } - }, e.map.addEventListener("keydown", (i) => { - (i.metaKey || i.ctrlKey) && i.shiftKey && i.key === "Z" ? e.redo() : (i.metaKey || i.ctrlKey) && i.key === "z" && e.undo(); - }); -} -var R = (e, t) => { - const n = document.createElement("span"); - return n.id = e, n.innerHTML = ``, n; -}; -function _t(e) { - const t = document.createElement("div"), n = R("fullscreen", "full"), o = R("toCenter", "living"), i = R("zoomout", "move"), s = R("zoomin", "add"), r = document.createElement("span"); - return r.innerText = "100%", t.appendChild(n), t.appendChild(o), t.appendChild(i), t.appendChild(s), t.className = "mind-elixir-toolbar rb", n.onclick = () => { - e.container.requestFullscreen(); - }, o.onclick = () => { - e.toCenter(); - }, i.onclick = () => { - e.scaleVal < 0.6 || e.scale(e.scaleVal -= 0.2); - }, s.onclick = () => { - e.scaleVal > 1.6 || e.scale(e.scaleVal += 0.2); - }, t; -} -function kt(e) { - const t = document.createElement("div"), n = R("tbltl", "left"), o = R("tbltr", "right"), i = R("tblts", "side"); - return t.appendChild(n), t.appendChild(o), t.appendChild(i), t.className = "mind-elixir-toolbar lt", n.onclick = () => { - e.initLeft(); - }, o.onclick = () => { - e.initRight(); - }, i.onclick = () => { - e.initSide(); - }, t; -} -function St(e) { - e.container.append(_t(e)), e.container.append(kt(e)); -} -var Lt = Object.defineProperty; -var Mt = (e, t, n) => t in e ? Lt(e, t, { enumerable: true, configurable: true, writable: true, value: n }) : e[t] = n; -var E = (e, t, n) => (Mt(e, typeof t != "symbol" ? t + "" : t, n), n); -var Tt = class { - constructor() { - E(this, "_listeners", /* @__PURE__ */ new Map()), E(this, "on", this.addEventListener), E(this, "off", this.removeEventListener), E(this, "emit", this.dispatchEvent); - } - addEventListener(t, n) { - const o = this._listeners.get(t) ?? /* @__PURE__ */ new Set(); - return this._listeners.set(t, o), o.add(n), this; - } - removeEventListener(t, n) { - var o; - return (o = this._listeners.get(t)) == null || o.delete(n), this; - } - dispatchEvent(t, ...n) { - let o = true; - for (const i of this._listeners.get(t) ?? []) - o = i(...n) !== false && o; - return o; - } - unbindAllListeners() { - this._listeners.clear(); - } -}; -var ye = (e, t = "px") => typeof e == "number" ? e + t : e; -function j({ style: e }, t, n) { - if (typeof t == "object") - for (const [o, i] of Object.entries(t)) - i !== void 0 && (e[o] = ye(i)); - else - n !== void 0 && (e[t] = ye(n)); -} -function Be(e) { - return (t, n, o, i = {}) => { - t instanceof HTMLCollection || t instanceof NodeList ? t = Array.from(t) : Array.isArray(t) || (t = [t]), Array.isArray(n) || (n = [n]); - for (const s of t) - for (const r of n) - s[e](r, o, { capture: false, ...i }); - return [t, n, o, i]; - }; -} -var V = Be("addEventListener"); -var O = Be("removeEventListener"); -var ee = (e) => { - var t; - const { clientX: n, clientY: o, target: i } = ((t = e.touches) == null ? void 0 : t[0]) ?? e; - return { x: n, y: o, target: i }; -}; -function xe(e, t, n = "touch") { - switch (n) { - case "center": { - const o = t.left + t.width / 2, i = t.top + t.height / 2; - return o >= e.left && o <= e.right && i >= e.top && i <= e.bottom; - } - case "cover": - return t.left >= e.left && t.top >= e.top && t.right <= e.right && t.bottom <= e.bottom; - case "touch": - return e.right >= t.left && e.left <= t.right && e.bottom >= t.top && e.top <= t.bottom; - } -} -function W(e, t = document) { - const n = Array.isArray(e) ? e : [e]; - let o = []; - for (let i = 0, s = n.length; i < s; i++) { - const r = n[i]; - typeof r == "string" ? o = o.concat(Array.from(t.querySelectorAll(r))) : r instanceof Element && o.push(r); - } - return o; -} -var $t = () => matchMedia("(hover: none), (pointer: coarse)").matches; -var Dt = () => "safari" in window; -var jt = (e) => { - let t, n = -1, o = false; - return { - next(...i) { - t = i, o || (o = true, n = requestAnimationFrame(() => { - e(...t), o = false; - })); - }, - cancel() { - cancelAnimationFrame(n), o = false; - } - }; -}; -var { abs: B, max: we, min: Ee, ceil: Ne } = Math; -var ze = class extends Tt { - constructor(t) { - var n, o, i, s, r; - super(), E(this, "_options"), E(this, "_selection", { - stored: [], - selected: [], - touched: [], - changed: { - added: [], - // Added elements since last selection - removed: [] - // Removed elements since last selection - } - }), E(this, "_area"), E(this, "_clippingElement"), E(this, "_targetElement"), E(this, "_targetRect"), E(this, "_selectables", []), E(this, "_latestElement"), E(this, "_areaRect", new DOMRect()), E(this, "_areaLocation", { y1: 0, x2: 0, y2: 0, x1: 0 }), E(this, "_singleClick", true), E(this, "_frame"), E(this, "_scrollAvailable", true), E(this, "_scrollingActive", false), E(this, "_scrollSpeed", { x: 0, y: 0 }), E(this, "_scrollDelta", { x: 0, y: 0 }), E(this, "disable", this._bindStartEvents.bind(this, false)), E(this, "enable", this._bindStartEvents), this._options = { - selectionAreaClass: "selection-area", - selectionContainerClass: void 0, - selectables: [], - document: window.document, - startAreas: ["html"], - boundaries: ["html"], - container: "body", - ...t, - behaviour: { - overlap: "invert", - intersect: "touch", - ...t.behaviour, - startThreshold: (n = t.behaviour) != null && n.startThreshold ? typeof t.behaviour.startThreshold == "number" ? t.behaviour.startThreshold : { x: 10, y: 10, ...t.behaviour.startThreshold } : { x: 10, y: 10 }, - scrolling: { - speedDivider: 10, - manualSpeed: 750, - ...(o = t.behaviour) == null ? void 0 : o.scrolling, - startScrollMargins: { - x: 0, - y: 0, - ...(s = (i = t.behaviour) == null ? void 0 : i.scrolling) == null ? void 0 : s.startScrollMargins - } - } - }, - features: { - range: true, - touch: true, - ...t.features, - singleTap: { - allow: true, - intersect: "native", - ...(r = t.features) == null ? void 0 : r.singleTap - } - } - }; - for (const a of Object.getOwnPropertyNames(Object.getPrototypeOf(this))) - typeof this[a] == "function" && (this[a] = this[a].bind(this)); - const { document: l, selectionAreaClass: c, selectionContainerClass: h } = this._options; - this._area = l.createElement("div"), this._clippingElement = l.createElement("div"), this._clippingElement.appendChild(this._area), this._area.classList.add(c), h && this._clippingElement.classList.add(h), j(this._area, { - willChange: "top, left, bottom, right, width, height", - top: 0, - left: 0, - position: "fixed" - }), j(this._clippingElement, { - overflow: "hidden", - position: "fixed", - transform: "translate3d(0, 0, 0)", - // https://stackoverflow.com/a/38268846 - pointerEvents: "none", - zIndex: "1" - }), this._frame = jt((a) => { - this._recalculateSelectionAreaRect(), this._updateElementSelection(), this._emitEvent("move", a), this._redrawSelectionArea(); - }), this.enable(); - } - _bindStartEvents(t = true) { - const { document: n, features: o } = this._options, i = t ? V : O; - i(n, "mousedown", this._onTapStart), o.touch && i(n, "touchstart", this._onTapStart, { - passive: false - }); - } - _onTapStart(t, n = false) { - const { x: o, y: i, target: s } = ee(t), { _options: r } = this, { document: l } = this._options, c = s.getBoundingClientRect(), h = W(r.startAreas, r.document), a = W(r.boundaries, r.document); - this._targetElement = a.find( - (p) => xe(p.getBoundingClientRect(), c) - ); - const u = t.composedPath(); - if (!this._targetElement || !h.find((p) => u.includes(p)) || !a.find((p) => u.includes(p)) || !n && this._emitEvent("beforestart", t) === false) - return; - this._areaLocation = { x1: o, y1: i, x2: 0, y2: 0 }; - const d = l.scrollingElement ?? l.body; - this._scrollDelta = { x: d.scrollLeft, y: d.scrollTop }, this._singleClick = true, this.clearSelection(false, true), V(l, ["touchmove", "mousemove"], this._delayedTapMove, { passive: false }), V(l, ["mouseup", "touchcancel", "touchend"], this._onTapStop), V(l, "scroll", this._onScroll); - } - _onSingleTap(t) { - const { singleTap: { intersect: n }, range: o } = this._options.features, i = ee(t); - let s; - if (n === "native") - s = i.target; - else if (n === "touch") { - this.resolveSelectables(); - const { x: l, y: c } = i; - s = this._selectables.find((h) => { - const { right: a, left: u, top: d, bottom: p } = h.getBoundingClientRect(); - return l < a && l > u && c < p && c > d; - }); - } - if (!s) - return; - for (this.resolveSelectables(); !this._selectables.includes(s); ) { - if (!s.parentElement) - return; - s = s.parentElement; - } - const { stored: r } = this._selection; - if (this._emitEvent("start", t), t.shiftKey && o && this._latestElement) { - const l = this._latestElement, [c, h] = l.compareDocumentPosition(s) & 4 ? [s, l] : [l, s], a = [...this._selectables.filter( - (u) => u.compareDocumentPosition(c) & 4 && u.compareDocumentPosition(h) & 2 - ), c, h]; - this.select(a), this._latestElement = l; - } else - r.includes(s) && (r.length === 1 || t.ctrlKey || r.every((l) => this._selection.stored.includes(l))) ? this.deselect(s) : (this.select(s), this._latestElement = s); - this._emitEvent("stop", t); - } - _delayedTapMove(t) { - const { container: n, document: o, behaviour: { startThreshold: i } } = this._options, { x1: s, y1: r } = this._areaLocation, { x: l, y: c } = ee(t); - if ( - // Single number for both coordinates - typeof i == "number" && B(l + c - (s + r)) >= i || // Different x and y threshold - typeof i == "object" && B(l - s) >= i.x || B(c - r) >= i.y - ) { - if (O(o, ["mousemove", "touchmove"], this._delayedTapMove, { passive: false }), this._emitEvent("beforedrag", t) === false) { - O(o, ["mouseup", "touchcancel", "touchend"], this._onTapStop); - return; - } - V(o, ["mousemove", "touchmove"], this._onTapMove, { passive: false }), j(this._area, "display", "block"), W(n, o)[0].appendChild(this._clippingElement), this.resolveSelectables(), this._singleClick = false, this._targetRect = this._targetElement.getBoundingClientRect(), this._scrollAvailable = this._targetElement.scrollHeight !== this._targetElement.clientHeight || this._targetElement.scrollWidth !== this._targetElement.clientWidth, this._scrollAvailable && (V(o, "wheel", this._manualScroll, { passive: false }), this._selectables = this._selectables.filter((h) => this._targetElement.contains(h))), this._setupSelectionArea(), this._emitEvent("start", t), this._onTapMove(t); - } - this._handleMoveEvent(t); - } - _setupSelectionArea() { - const { _clippingElement: t, _targetElement: n, _area: o } = this, i = this._targetRect = n.getBoundingClientRect(); - this._scrollAvailable ? (j(t, { - top: i.top, - left: i.left, - width: i.width, - height: i.height - }), j(o, { - marginTop: -i.top, - marginLeft: -i.left - })) : (j(t, { - top: 0, - left: 0, - width: "100%", - height: "100%" - }), j(o, { - marginTop: 0, - marginLeft: 0 - })); - } - _onTapMove(t) { - const { x: n, y: o } = ee(t), { _scrollSpeed: i, _areaLocation: s, _options: r, _frame: l } = this, { speedDivider: c } = r.behaviour.scrolling, h = this._targetElement; - if (s.x2 = n, s.y2 = o, this._scrollAvailable && !this._scrollingActive && (i.y || i.x)) { - this._scrollingActive = true; - const a = () => { - if (!i.x && !i.y) { - this._scrollingActive = false; - return; - } - const { scrollTop: u, scrollLeft: d } = h; - i.y && (h.scrollTop += Ne(i.y / c), s.y1 -= h.scrollTop - u), i.x && (h.scrollLeft += Ne(i.x / c), s.x1 -= h.scrollLeft - d), l.next(t), requestAnimationFrame(a); - }; - requestAnimationFrame(a); - } else - l.next(t); - this._handleMoveEvent(t); - } - _handleMoveEvent(t) { - const { features: n } = this._options; - (n.touch && $t() || this._scrollAvailable && Dt()) && t.preventDefault(); - } - _onScroll() { - const { _scrollDelta: t, _options: { document: n } } = this, { scrollTop: o, scrollLeft: i } = n.scrollingElement ?? n.body; - this._areaLocation.x1 += t.x - i, this._areaLocation.y1 += t.y - o, t.x = i, t.y = o, this._setupSelectionArea(), this._frame.next(null); - } - _manualScroll(t) { - const { manualSpeed: n } = this._options.behaviour.scrolling, o = t.deltaY ? t.deltaY > 0 ? 1 : -1 : 0, i = t.deltaX ? t.deltaX > 0 ? 1 : -1 : 0; - this._scrollSpeed.y += o * n, this._scrollSpeed.x += i * n, this._onTapMove(t), t.preventDefault(); - } - _recalculateSelectionAreaRect() { - const { _scrollSpeed: t, _areaLocation: n, _areaRect: o, _targetElement: i, _options: s } = this, { scrollTop: r, scrollHeight: l, clientHeight: c, scrollLeft: h, scrollWidth: a, clientWidth: u } = i, d = this._targetRect, { x1: p, y1: g } = n; - let { x2: m, y2: f } = n; - const { behaviour: { scrolling: { startScrollMargins: v } } } = s; - m < d.left + v.x ? (t.x = h ? -B(d.left - m + v.x) : 0, m = m < d.left ? d.left : m) : m > d.right - v.x ? (t.x = a - h - u ? B(d.left + d.width - m - v.x) : 0, m = m > d.right ? d.right : m) : t.x = 0, f < d.top + v.y ? (t.y = r ? -B(d.top - f + v.y) : 0, f = f < d.top ? d.top : f) : f > d.bottom - v.y ? (t.y = l - r - c ? B(d.top + d.height - f - v.y) : 0, f = f > d.bottom ? d.bottom : f) : t.y = 0; - const y = Ee(p, m), b = Ee(g, f), x = we(p, m), w = we(g, f); - o.x = y, o.y = b, o.width = x - y, o.height = w - b; - } - _redrawSelectionArea() { - const { x: t, y: n, width: o, height: i } = this._areaRect, { style: s } = this._area; - s.left = `${t}px`, s.top = `${n}px`, s.width = `${o}px`, s.height = `${i}px`; - } - _onTapStop(t, n) { - var o; - const { document: i, features: s } = this._options, { _singleClick: r } = this; - O(i, ["mousemove", "touchmove"], this._delayedTapMove), O(i, ["touchmove", "mousemove"], this._onTapMove), O(i, ["mouseup", "touchcancel", "touchend"], this._onTapStop), O(i, "scroll", this._onScroll), this._keepSelection(), t && r && s.singleTap.allow ? this._onSingleTap(t) : !r && !n && (this._updateElementSelection(), this._emitEvent("stop", t)), this._scrollSpeed.x = 0, this._scrollSpeed.y = 0, this._scrollAvailable && O(i, "wheel", this._manualScroll, { passive: true }), this._clippingElement.remove(), (o = this._frame) == null || o.cancel(), j(this._area, "display", "none"); - } - _updateElementSelection() { - const { _selectables: t, _options: n, _selection: o, _areaRect: i } = this, { stored: s, selected: r, touched: l } = o, { intersect: c, overlap: h } = n.behaviour, a = h === "invert", u = [], d = [], p = []; - for (let m = 0; m < t.length; m++) { - const f = t[m]; - if (xe(i, f.getBoundingClientRect(), c)) { - if (r.includes(f)) - s.includes(f) && !l.includes(f) && l.push(f); - else if (a && s.includes(f)) { - p.push(f); - continue; - } else - d.push(f); - u.push(f); - } - } - a && d.push(...s.filter((m) => !r.includes(m))); - const g = h === "keep"; - for (let m = 0; m < r.length; m++) { - const f = r[m]; - !u.includes(f) && !// Check if user wants to keep previously selected elements, e.g. - // not make them part of the current selection as soon as they're touched. - (g && s.includes(f)) && p.push(f); - } - o.selected = u, o.changed = { added: d, removed: p }, this._latestElement = void 0; - } - _emitEvent(t, n) { - return this.emit(t, { - event: n, - store: this._selection, - selection: this - }); - } - _keepSelection() { - const { _options: t, _selection: n } = this, { selected: o, changed: i, touched: s, stored: r } = n, l = o.filter((c) => !r.includes(c)); - switch (t.behaviour.overlap) { - case "drop": { - n.stored = [ - ...l, - ...r.filter((c) => !s.includes(c)) - // Elements not touched - ]; - break; - } - case "invert": { - n.stored = [ - ...l, - ...r.filter((c) => !i.removed.includes(c)) - // Elements not removed from selection - ]; - break; - } - case "keep": { - n.stored = [ - ...r, - ...o.filter((c) => !r.includes(c)) - // Newly added - ]; - break; - } - } - } - /** - * Manually triggers the start of a selection - * @param evt A MouseEvent / TouchEvent -like object - * @param silent If beforestart should be fired, - */ - trigger(t, n = true) { - this._onTapStart(t, n); - } - /** - * Can be used if during a selection elements have been added. - * Will update everything which can be selected. - */ - resolveSelectables() { - this._selectables = W(this._options.selectables, this._options.document); - } - /** - * Same as deselect, but for all elements currently selected. - * @param includeStored If the store should also get cleared - * @param quiet If move / stop events should be fired - */ - clearSelection(t = true, n = false) { - const { selected: o, stored: i, changed: s } = this._selection; - s.added = [], s.removed.push( - ...o, - ...t ? i : [] - ), n || (this._emitEvent("move", null), this._emitEvent("stop", null)), this._selection = { - stored: t ? [] : i, - selected: [], - touched: [], - changed: { added: [], removed: [] } - }; - } - /** - * @returns {Array} Selected elements - */ - getSelection() { - return this._selection.stored; - } - /** - * @returns {HTMLElement} The selection area element - */ - getSelectionArea() { - return this._area; - } - /** - * Cancel the current selection process. - * @param keepEvent {boolean} true to fire a stop event after cancel. - */ - cancel(t = false) { - this._onTapStop(null, !t); - } - /** - * Unbinds all events and removes the area-element. - */ - destroy() { - this.cancel(), this.disable(), this._clippingElement.remove(), super.unbindAllListeners(); - } - /** - * Adds elements to the selection - * @param query - CSS Query, can be an array of queries - * @param quiet - If this should not trigger the move event - */ - select(t, n = false) { - const { changed: o, selected: i, stored: s } = this._selection, r = W(t, this._options.document).filter( - (l) => !i.includes(l) && !s.includes(l) - ); - return s.push(...r), i.push(...r), o.added.push(...r), o.removed = [], this._latestElement = void 0, n || (this._emitEvent("move", null), this._emitEvent("stop", null)), r; - } - /** - * Removes a particular element from the selection. - * @param query - CSS Query, can be an array of queries - * @param quiet - If this should not trigger the move event - */ - deselect(t, n = false) { - const { selected: o, stored: i, changed: s } = this._selection, r = W(t, this._options.document).filter( - (l) => o.includes(l) || i.includes(l) - ); - r.length && (this._selection.stored = i.filter((l) => !r.includes(l)), this._selection.selected = o.filter((l) => !r.includes(l)), this._selection.changed.added = [], this._selection.changed.removed.push( - ...r.filter((l) => !s.removed.includes(l)) - ), this._latestElement = void 0, n || (this._emitEvent("move", null), this._emitEvent("stop", null))); - } -}; -E(ze, "version", "3.3.1"); -function Ot(e) { - const t = new ze({ - selectables: [".map-container me-tpc"], - boundaries: [e.container], - container: "body", - behaviour: { - // Scroll configuration. - scrolling: { - // On scrollable areas the number on px per frame is devided by this amount. - // Default is 10 to provide a enjoyable scroll experience. - speedDivider: 10, - // Browsers handle mouse-wheel events differently, this number will be used as - // numerator to calculate the mount of px while scrolling manually: manualScrollSpeed / scrollSpeedDivider. - manualSpeed: 750, - // This property defines the virtual inset margins from the borders of the container - // component that, when crossed by the mouse/touch, trigger the scrolling. Useful for - // fullscreen containers. - startScrollMargins: { x: 10, y: 10 } - } - } - }).on("beforestart", ({ event: n }) => { - if (n.button !== e.mouseSelectionButton || n.target.tagName === "ME-TPC" || n.target.id === "input-box" || n.target.className === "circle") - return false; - const o = t.getSelectionArea(); - return o.style.background = "#4f90f22d", o.style.border = "1px solid #4f90f2", o.parentElement && (o.parentElement.style.zIndex = "9999"), true; - }).on("start", ({ event: n }) => { - !n.ctrlKey && !n.metaKey && (e.unselectNode(), e.unselectNodes(), e.unselectSummary(), e.unselectLink(), t.clearSelection(true, true)); - }).on( - "move", - ({ - store: { - changed: { added: n, removed: o } - } - }) => { - S.moved = true; - for (const i of n) - i.classList.add("selected"); - for (const i of o) - i.classList.remove("selected"); - } - ).on("stop", ({ store: { stored: n } }) => { - e.selectNodes(n); - }); - e.selection = t; -} -var At = function(e, t = true) { - this.theme = e; - const n = this.theme.cssVar, o = Object.keys(n); - for (let i = 0; i < o.length; i++) { - const s = o[i]; - this.mindElixirBox.style.setProperty(s, n[s]); - } - t && this.refresh(); -}; -function Re(e) { - return { - nodeData: e.isFocusMode ? e.nodeDataBackup : e.nodeData, - linkData: e.linkData, - summaries: e.summaries, - direction: e.direction, - theme: e.theme - }; -} -var Pt = function(e, t, n) { - if (e) { - if (console.time("selectNode"), typeof e == "string") { - const o = N(e); - return o ? this.selectNode(o) : void 0; - } - this.currentNode && (this.currentNode.className = ""), e.className = "selected", e.scrollIntoView({ block: "nearest", inline: "nearest" }), this.currentNode = e, t ? this.bus.fire("selectNewNode", e.nodeObj) : this.bus.fire("selectNode", e.nodeObj, n), console.timeEnd("selectNode"); - } -}; -var Ht = function() { - this.currentNode && (this.currentNode.className = ""), this.currentNode = null, this.bus.fire("unselectNode"); -}; -var Bt = function(e) { - if (e) { - console.time("selectNodes"); - for (const t of e) - t.className = "selected"; - this.currentNodes = e, this.bus.fire( - "selectNodes", - e.map((t) => t.nodeObj) - ), console.timeEnd("selectNodes"); - } -}; -var zt = function() { - if (this.currentNodes) - for (const e of this.currentNodes) - e.classList.remove("selected"); - this.currentNodes = null, this.bus.fire("unselectNodes"); -}; -var Rt = function() { - if (!this.currentNode || this.currentNode.dataset.nodeid === "meroot") - return false; - const e = this.currentNode.parentElement.parentElement.nextSibling; - let t; - if (e) - t = e.firstChild.firstChild; - else - return false; - return this.selectNode(t), true; -}; -var qt = function() { - if (!this.currentNode || this.currentNode.dataset.nodeid === "meroot") - return false; - const e = this.currentNode.parentElement.parentElement.previousSibling; - let t; - if (e) - t = e.firstChild.firstChild; - else - return false; - return this.selectNode(t), true; -}; -var Ft = function() { - if (!this.currentNode) - return; - const e = this.currentNode.parentElement.nextSibling; - if (e && e.firstChild) { - const t = e.firstChild.firstChild.firstChild; - this.selectNode(t); - } -}; -var Vt = function() { - if (!this.currentNode || this.currentNode.dataset.nodeid === "meroot") - return; - const e = this.currentNode.parentElement.parentElement.parentElement.previousSibling; - if (e) { - const t = e.firstChild; - this.selectNode(t); - } -}; -var Wt = function() { - const e = Re(this); - return JSON.stringify(e, (t, n) => { - if (!(t === "parent" && typeof n != "string")) - return n; - }); -}; -var It = function() { - return JSON.parse(this.getDataString()); -}; -var Kt = function() { - const e = Re(this).nodeData; - let t = "# " + e.topic + ` - -`; - function n(o, i) { - for (let s = 0; s < o.length; s++) - i <= 6 ? t += "".padStart(i, "#") + " " + o[s].topic + ` - -` : t += "".padStart(i - 7, " ") + "- " + o[s].topic + ` -`, o[s].children && n(o[s].children || [], i + 1); - } - return n(e.children || [], 2), t; -}; -var Ut = function() { - this.editable = true; -}; -var Yt = function() { - this.editable = false; -}; -var Gt = function(e) { - this.scaleVal = e, this.map.style.transform = "scale(" + e + ")"; -}; -var Xt = function() { - this.container.scrollTo(1e4 - this.container.offsetWidth / 2, 1e4 - this.container.offsetHeight / 2); -}; -var Jt = function(e) { - e(this); -}; -var Qt = function(e) { - e.nodeObj.root || (this.tempDirection === null && (this.tempDirection = this.direction), this.isFocusMode || (this.nodeDataBackup = this.nodeData, this.isFocusMode = true), this.nodeData = e.nodeObj, this.nodeData.root = true, this.initRight(), this.toCenter()); -}; -var Zt = function() { - this.isFocusMode = false, this.tempDirection !== null && (delete this.nodeData.root, this.nodeData = this.nodeDataBackup, this.direction = this.tempDirection, this.tempDirection = null, this.refresh(), this.toCenter()); -}; -var en = function() { - this.direction = 0, this.refresh(); -}; -var tn = function() { - this.direction = 1, this.refresh(); -}; -var nn = function() { - this.direction = 2, this.refresh(); -}; -var on = function(e) { - this.locale = e, this.refresh(); -}; -var sn = function(e, t) { - const n = e.nodeObj; - typeof t == "boolean" ? n.expanded = t : n.expanded !== false ? n.expanded = false : n.expanded = true, this.layout(), this.linkDiv(), this.bus.fire("expandNode", n); -}; -var rn = function(e) { - e && (e = JSON.parse(JSON.stringify(e)), this.nodeData = e.nodeData, this.linkData = e.linkData || {}, this.summaries = e.summaries || []), $(this.nodeData), this.layout(), this.linkDiv(); -}; -var ln = Object.freeze(Object.defineProperty({ - __proto__: null, - cancelFocus: Zt, - disableEdit: Yt, - enableEdit: Ut, - expandNode: sn, - focusNode: Qt, - getData: It, - getDataMd: Kt, - getDataString: Wt, - initLeft: en, - initRight: tn, - initSide: nn, - install: Jt, - refresh: rn, - scale: Gt, - selectFirstChild: Ft, - selectNextSibling: Rt, - selectNode: Pt, - selectNodes: Bt, - selectParent: Vt, - selectPrevSibling: qt, - setLocale: on, - toCenter: Xt, - unselectNode: Ht, - unselectNodes: zt -}, Symbol.toStringTag, { value: "Module" })); -var A = (e) => { - var o; - const t = (o = e.parent) == null ? void 0 : o.children, n = t.indexOf(e); - return { siblings: t, index: n }; -}; -function cn(e) { - const { siblings: t, index: n } = A(e), o = t[n]; - n === 0 ? (t[n] = t[t.length - 1], t[t.length - 1] = o) : (t[n] = t[n - 1], t[n - 1] = o); -} -function an(e) { - const { siblings: t, index: n } = A(e), o = t[n]; - n === t.length - 1 ? (t[n] = t[0], t[0] = o) : (t[n] = t[n + 1], t[n + 1] = o); -} -function Q(e) { - const { siblings: t, index: n } = A(e); - return t.splice(n, 1), t.length; -} -function dn(e, t) { - const { siblings: n, index: o } = A(e); - n.splice(o + 1, 0, t); -} -function hn(e, t) { - const { siblings: n, index: o } = A(e); - n.splice(o, 0, t); -} -function un(e, t) { - const { siblings: n, index: o } = A(e); - n[o] = t, t.children = [e]; -} -function fn(e, t) { - Q(e), t.children ? t.children.push(e) : t.children = [e]; -} -function pn(e, t) { - e.direction !== void 0 && (e.direction = t.direction), Q(e); - const { siblings: n, index: o } = A(t); - n.splice(o, 0, e); -} -function mn(e, t) { - e.direction !== void 0 && (e.direction = t.direction), Q(e); - const { siblings: n, index: o } = A(t); - n.splice(o + 1, 0, e); -} -var qe = function(e, t) { - var n, o; - if (e === L) - return L; - if (e === z) - return z; - if (e === X) { - const i = ((n = document.querySelector(".lhs")) == null ? void 0 : n.childElementCount) || 0, s = ((o = document.querySelector(".rhs")) == null ? void 0 : o.childElementCount) || 0; - return i <= s ? (t.direction = L, L) : (t.direction = z, z); - } -}; -var Fe = function(e, t) { - var l, c; - if (!e) - return null; - const n = e.nodeObj; - n.expanded === false && (this.expandNode(e, true), e = N(n.id)); - const o = t || this.generateNewObj(); - n.children ? n.children.push(o) : n.children = [o], $(this.nodeData); - const i = e.parentElement, { grp: s, top: r } = this.createWrapper(o); - if (i.tagName === "ME-PARENT") { - if (i.children[1]) - i.nextSibling.appendChild(s); - else { - const h = this.createChildren([s]); - i.appendChild(re(true)), i.insertAdjacentElement("afterend", h); - } - this.linkDiv(s.offsetParent); - } else - i.tagName === "ME-ROOT" && (qe(this.direction, o) === L ? (l = document.querySelector(".lhs")) == null || l.appendChild(s) : (c = document.querySelector(".rhs")) == null || c.appendChild(s), this.linkDiv()); - return { newTop: r, newNodeObj: o }; -}; -var Ve = function(e, t) { - const n = e.parentNode; - if (t === 0) { - const o = n.parentNode.parentNode; - o.tagName !== "ME-MAIN" && o.previousSibling.children[1].remove(); - } - n.parentNode.remove(); -}; -var le = function(e) { - const n = e.parentElement.parentElement.lastElementChild; - (n == null ? void 0 : n.tagName) === "svg" && (n == null || n.remove()); -}; -var gn = function(e, t) { - console.log(t); - const n = e.nodeObj, o = De(n); - o.style && t.style && (t.style = Object.assign(o.style, t.style)); - const i = Object.assign(n, t); - ue(e, i), this.linkDiv(), this.bus.fire("operation", { - name: "reshapeNode", - obj: i, - origin: o - }); -}; -var vn = function(e, t) { - var h, a, u; - const n = e || this.currentNode; - if (!n) - return; - const o = n.nodeObj; - if (o.root === true) { - this.addChild(); - return; - } else if (((h = o.parent) == null ? void 0 : h.root) === true && ((u = (a = o.parent) == null ? void 0 : a.children) == null ? void 0 : u.length) === 1) { - this.addChild(N(o.parent.id)); - return; - } - const i = t || this.generateNewObj(); - dn(o, i), $(this.nodeData); - const s = n.parentElement; - console.time("insertSibling_DOM"); - const { grp: r, top: l } = this.createWrapper(i); - s.parentNode.parentNode.insertBefore(r, s.parentNode.nextSibling), this.linkDiv(r.offsetParent), t || this.editTopic(l.firstChild), this.selectNode(l.firstChild, true), console.timeEnd("insertSibling_DOM"), this.bus.fire("operation", { - name: "insertSibling", - obj: i - }); -}; -var bn = function(e, t) { - const n = e || this.currentNode; - if (!n) - return; - const o = n.nodeObj; - if (o.root === true) { - this.addChild(); - return; - } - const i = t || this.generateNewObj(); - hn(o, i), $(this.nodeData); - const s = n.parentElement; - console.time("insertSibling_DOM"); - const { grp: r, top: l } = this.createWrapper(i); - s.parentNode.parentNode.insertBefore(r, s.parentNode), this.linkDiv(r.offsetParent), t || this.editTopic(l.firstChild), this.selectNode(l.firstChild, true), console.timeEnd("insertSibling_DOM"), this.bus.fire("operation", { - name: "insertBefore", - obj: i - }); -}; -var yn = function(e, t) { - const n = e || this.currentNode; - if (!n) - return; - le(n); - const o = n.nodeObj; - if (o.root === true) - return; - const i = t || this.generateNewObj(); - un(o, i), $(this.nodeData); - const s = n.parentElement.parentElement; - console.time("insertParent_DOM"); - const { grp: r, top: l } = this.createWrapper(i, true); - l.appendChild(re(true)), s.insertAdjacentElement("afterend", r); - const c = this.createChildren([s]); - l.insertAdjacentElement("afterend", c), this.linkDiv(), t || this.editTopic(l.firstChild), this.selectNode(l.firstChild, true), console.timeEnd("insertParent_DOM"), this.bus.fire("operation", { - name: "insertParent", - obj: i - }); -}; -var xn = function(e, t) { - console.time("addChild"); - const n = e || this.currentNode; - if (!n) - return; - const o = Fe.call(this, n, t); - if (!o) - return; - const { newTop: i, newNodeObj: s } = o; - this.bus.fire("operation", { - name: "addChild", - obj: s - }), console.timeEnd("addChild"), t || this.editTopic(i.firstChild), this.selectNode(i.firstChild, true); -}; -var wn = function(e, t) { - console.time("copyNode"); - const n = De(e.nodeObj); - Te(n); - const o = Fe.call(this, t, n); - if (!o) - return; - const { newNodeObj: i } = o; - console.timeEnd("copyNode"), this.bus.fire("operation", { - name: "copyNode", - obj: i - }); -}; -var En = function(e) { - const t = e || this.currentNode; - if (!t) - return; - const n = t.nodeObj; - cn(n); - const o = t.parentNode.parentNode; - o.parentNode.insertBefore(o, o.previousSibling), this.linkDiv(), this.bus.fire("operation", { - name: "moveUpNode", - obj: n - }); -}; -var Nn = function(e) { - const t = e || this.currentNode; - if (!t) - return; - const n = t.nodeObj; - an(n); - const o = t.parentNode.parentNode; - o.nextSibling ? o.nextSibling.insertAdjacentElement("afterend", o) : o.parentNode.prepend(o), this.linkDiv(), this.bus.fire("operation", { - name: "moveDownNode", - obj: n - }); -}; -var Cn = function(e) { - var r; - const t = e || this.currentNode; - if (!t) - return; - const n = t.nodeObj; - if (n.root === true) - throw new Error("Can not remove root node"); - const o = n.parent.children, i = o.findIndex((l) => l === n), s = Q(n); - if (Ve(t, s), o.length !== 0) { - const l = o[i] || o[i - 1]; - this.selectNode(N(l.id)); - } else - this.selectNode(N(n.parent.id)); - this.linkDiv(), this.bus.fire("operation", { - name: "removeNode", - obj: n, - originIndex: i, - originParentId: (r = n == null ? void 0 : n.parent) == null ? void 0 : r.id - }); -}; -var _n = function(e) { - for (const t of e) { - const n = t.nodeObj; - if (n.root === true) - continue; - const o = Q(n); - Ve(t, o); - } - this.linkDiv(), this.bus.fire("operation", { - name: "removeNodes", - objs: e.map((t) => t.nodeObj) - }); -}; -var kn = function(e, t) { - var l; - const n = e.nodeObj, o = t.nodeObj, i = (l = n == null ? void 0 : n.parent) == null ? void 0 : l.id; - if (o.expanded === false && (this.expandNode(t, true), e = N(n.id), t = N(o.id)), !Je(n, o)) { - console.warn("Invalid move"); - return; - } - console.time("moveNode"), fn(n, o), $(this.nodeData); - const s = e.parentElement, r = t.parentElement; - if (r.tagName === "ME-PARENT") - if (le(e), r.children[1]) - r.nextSibling.appendChild(s.parentElement); - else { - const c = this.createChildren([s.parentElement]); - r.appendChild(re(true)), r.parentElement.insertBefore(c, r.nextSibling); - } - else - r.tagName === "ME-ROOT" && (qe(this.direction, n), r.nextSibling.appendChild(s.parentElement)); - this.linkDiv(), this.bus.fire("operation", { - name: "moveNode", - obj: n, - toObj: o, - originParentId: i - }), console.timeEnd("moveNode"); -}; -var Sn = function(e, t) { - var l; - const n = e.nodeObj, o = t.nodeObj, i = (l = n.parent) == null ? void 0 : l.id; - pn(n, o), $(this.nodeData), le(e); - const s = e.parentElement.parentNode; - t.parentElement.parentNode.insertAdjacentElement("beforebegin", s), this.linkDiv(), this.bus.fire("operation", { - name: "moveNodeBefore", - obj: n, - toObj: o, - originParentId: i - }); -}; -var Ln = function(e, t) { - var l; - const n = e.nodeObj, o = t.nodeObj, i = (l = n.parent) == null ? void 0 : l.id; - mn(n, o), $(this.nodeData), le(e); - const s = e.parentElement.parentNode; - t.parentElement.parentNode.insertAdjacentElement("afterend", s), this.linkDiv(), this.bus.fire("operation", { - name: "moveNodeAfter", - obj: n, - toObj: o, - originParentId: i - }); -}; -var Mn = function(e) { - const t = e || this.currentNode; - t && this.editTopic(t); -}; -var Tn = function(e, t) { - e.text.textContent = t, e.nodeObj.topic = t, this.linkDiv(); -}; -var We = Object.freeze(Object.defineProperty({ - __proto__: null, - addChild: xn, - beginEdit: Mn, - copyNode: wn, - insertBefore: bn, - insertParent: yn, - insertSibling: vn, - moveDownNode: Nn, - moveNode: kn, - moveNodeAfter: Ln, - moveNodeBefore: Sn, - moveUpNode: En, - removeNode: Cn, - removeNodes: _n, - reshapeNode: gn, - setNodeTopic: Tn -}, Symbol.toStringTag, { value: "Module" })); -var $n = function(e) { - return { - dom: e, - moved: false, - // diffrentiate click and move - mousedown: false, - handleMouseMove(t) { - this.mousedown && (this.moved = true, this.cb && this.cb(t.movementX, t.movementY)); - }, - handleMouseDown(t) { - t.button === 0 && (this.mousedown = true); - }, - handleClear(t) { - this.mousedown = false; - }, - cb: null, - init(t, n) { - this.cb = n, this.handleClear = this.handleClear.bind(this), this.handleMouseMove = this.handleMouseMove.bind(this), this.handleMouseDown = this.handleMouseDown.bind(this), t.addEventListener("mousemove", this.handleMouseMove), t.addEventListener("mouseleave", this.handleClear), t.addEventListener("mouseup", this.handleClear), this.dom.addEventListener("mousedown", this.handleMouseDown); - }, - destory(t) { - t.removeEventListener("mousemove", this.handleMouseMove), t.removeEventListener("mouseleave", this.handleClear), t.removeEventListener("mouseup", this.handleClear), this.dom.removeEventListener("mousedown", this.handleMouseDown); - }, - clear() { - this.moved = false, this.mousedown = false; - } - }; -}; -var Ce = { - create: $n -}; -function se(e, t, n) { - const { offsetLeft: o, offsetTop: i } = K(e.nodes, t), s = t.offsetWidth, r = t.offsetHeight, l = o + s / 2, c = i + r / 2, h = l + n.x, a = c + n.y; - return { - w: s, - h: r, - cx: l, - cy: c, - ctrlX: h, - ctrlY: a - }; -} -function I(e) { - let t, n; - const o = (e.cy - e.ctrlY) / (e.ctrlX - e.cx); - return o > e.h / e.w || o < -e.h / e.w ? e.cy - e.ctrlY < 0 ? (t = e.cx - e.h / 2 / o, n = e.cy + e.h / 2) : (t = e.cx + e.h / 2 / o, n = e.cy - e.h / 2) : e.cx - e.ctrlX < 0 ? (t = e.cx + e.w / 2, n = e.cy - e.w * o / 2) : (t = e.cx - e.w / 2, n = e.cy + e.w * o / 2), { - x: t, - y: n - }; -} -var Dn = function(e, t, n, o) { - const i = document.createElementNS("http://www.w3.org/2000/svg", "text"); - return C(i, { - "text-anchor": "middle", - x: t + "", - y: n + "", - fill: o || "#666" - }), i.dataset.type = "custom-link", i.innerHTML = e, i; -}; -var jn = function(e, t, n, o) { - if (!e || !t) - return; - const i = performance.now(), s = se(this, e, n.delta1), r = se(this, t, n.delta2), { x: l, y: c } = I(s), { ctrlX: h, ctrlY: a } = s, { ctrlX: u, ctrlY: d } = r, { x: p, y: g } = I(r), m = $e(u, d, p, g), f = dt( - `M ${l} ${c} C ${h} ${a} ${u} ${d} ${p} ${g}`, - `M ${m.x1} ${m.y1} L ${p} ${g} L ${m.x2} ${m.y2}` - ), v = l / 8 + h * 3 / 8 + u * 3 / 8 + p / 8, y = c / 8 + a * 3 / 8 + d * 3 / 8 + g / 8, b = Dn(n.label, v, y, this.theme.cssVar["--color"]); - f.appendChild(b), f.linkObj = n, f.dataset.linkid = n.id, this.linkSvgGroup.appendChild(f), o || (this.linkData[n.id] = n, this.currentLink = f, this.showLinkController(n, s, r)); - const x = performance.now(); - console.log(`DrawCustomLink Execution time: ${x - i} ms`); -}; -var On = function(e, t) { - const n = { - id: J(), - label: "Custom Link", - from: e.nodeObj.id, - to: t.nodeObj.id, - delta1: { - x: 0, - y: -200 - }, - delta2: { - x: 0, - y: -200 - } - }; - this.drawCustomLink(e, t, n), this.bus.fire("operation", { - name: "createCustomLink", - obj: n - }); -}; -var An = function(e) { - let t; - if (e ? t = e : t = this.currentLink, !t) - return; - this.hideLinkController(); - const n = t.linkObj.id; - delete this.linkData[n], t.remove(), this.bus.fire("operation", { - name: "removeCustomLink", - obj: { - id: n - } - }); -}; -var Pn = function(e) { - this.currentLink = e; - const t = e.linkObj, n = N(t.from), o = N(t.to), i = se(this, n, t.delta1), s = se(this, o, t.delta2); - this.showLinkController(t, i, s); -}; -var Hn = function() { - this.currentLink = null, this.hideLinkController(); -}; -var Bn = function() { - this.linkController.style.display = "none", this.P2.style.display = "none", this.P3.style.display = "none"; -}; -var zn = function(e, t, n) { - var u; - this.linkController.style.display = "initial", this.P2.style.display = "initial", this.P3.style.display = "initial", this.nodes.appendChild(this.linkController), this.nodes.appendChild(this.P2), this.nodes.appendChild(this.P3); - let { x: o, y: i } = I(t), { ctrlX: s, ctrlY: r } = t, { ctrlX: l, ctrlY: c } = n, { x: h, y: a } = I(n); - this.P2.style.cssText = `top:${r}px;left:${s}px;`, this.P3.style.cssText = `top:${c}px;left:${l}px;`, C(this.line1, { - x1: o + "", - y1: i + "", - x2: s + "", - y2: r + "" - }), C(this.line2, { - x1: l + "", - y1: c + "", - x2: h + "", - y2: a + "" - }), this.helper1 && (this.helper1.destory(this.map), (u = this.helper2) == null || u.destory(this.map)), this.helper1 = Ce.create(this.P2), this.helper2 = Ce.create(this.P3), this.helper1.init(this.map, (d, p) => { - var v; - s = s + d / this.scaleVal, r = r + p / this.scaleVal; - const g = I({ ...t, ctrlX: s, ctrlY: r }); - o = g.x, i = g.y; - const m = o / 8 + s * 3 / 8 + l * 3 / 8 + h / 8, f = i / 8 + r * 3 / 8 + c * 3 / 8 + a / 8; - this.P2.style.top = r + "px", this.P2.style.left = s + "px", (v = this.currentLink) == null || v.children[0].setAttribute("d", `M ${o} ${i} C ${s} ${r} ${l} ${c} ${h} ${a}`), C(this.currentLink.children[2], { - x: m + "", - y: f + "" - }), C(this.line1, { - x1: o + "", - y1: i + "", - x2: s + "", - y2: r + "" - }), e.delta1.x = s - t.cx, e.delta1.y = r - t.cy; - }), this.helper2.init(this.map, (d, p) => { - var y, b; - l = l + d / this.scaleVal, c = c + p / this.scaleVal; - const g = I({ ...n, ctrlX: l, ctrlY: c }); - h = g.x, a = g.y; - const m = o / 8 + s * 3 / 8 + l * 3 / 8 + h / 8, f = i / 8 + r * 3 / 8 + c * 3 / 8 + a / 8, v = $e(l, c, h, a); - this.P3.style.top = c + "px", this.P3.style.left = l + "px", (y = this.currentLink) == null || y.children[0].setAttribute("d", `M ${o} ${i} C ${s} ${r} ${l} ${c} ${h} ${a}`), (b = this.currentLink) == null || b.children[1].setAttribute("d", `M ${v.x1} ${v.y1} L ${h} ${a} L ${v.x2} ${v.y2}`), C(this.currentLink.children[2], { - x: m + "", - y: f + "" - }), C(this.line2, { - x1: l + "", - y1: c + "", - x2: h + "", - y2: a + "" - }), e.delta2.x = l - n.cx, e.delta2.y = c - n.cy; - }); -}; -function Rn() { - this.linkSvgGroup.innerHTML = ""; - for (const e in this.linkData) { - const t = this.linkData[e]; - try { - this.drawCustomLink(N(t.from), N(t.to), t, true); - } catch { - console.warn("Node may not be expanded"); - } - } - this.nodes.appendChild(this.linkSvgGroup); -} -function qn(e) { - if (console.time("editSummary"), !e) - return; - const t = e.children[2]; - console.log(t, e), Oe(this, t, (n) => { - var s; - const o = e.linkObj, i = ((s = n.textContent) == null ? void 0 : s.trim()) || ""; - i === "" ? o.label = origin : o.label = i, n.remove(), i !== origin && (t.innerHTML = o.label, this.linkDiv(), this.bus.fire("operation", { - name: "finishEditCustomLinkLabel", - obj: o - })); - }), console.timeEnd("editSummary"); -} -function Fn() { - for (const e in this.linkData) { - const t = this.linkData[e]; - (!oe(t.from, this.nodeData) || !oe(t.to, this.nodeData)) && delete this.linkData[t.id]; - } -} -var Vn = Object.freeze(Object.defineProperty({ - __proto__: null, - createLink: On, - drawCustomLink: jn, - editCutsomLinkLabel: qn, - hideLinkController: Bn, - removeLink: An, - renderCustomLink: Rn, - selectLink: Pn, - showLinkController: zn, - tidyCustomLink: Fn, - unselectLink: Hn -}, Symbol.toStringTag, { value: "Module" })); -var Wn = function(e) { - var c, h; - if (e.length === 0) - throw new Error("No selected node."); - if (e.length === 1) { - const a = e[0].nodeObj, u = e[0].nodeObj.parent; - if (!u) - throw new Error("Can not select root node."); - const d = u.children.findIndex((p) => a === p); - return { - parent: u.id, - start: d, - end: d - }; - } - let t = 0; - const n = e.map((a) => { - let u = a.nodeObj; - const d = []; - for (; u.parent; ) { - const p = u.parent, g = p.children, m = g == null ? void 0 : g.indexOf(u); - u = p, d.unshift({ node: u, index: m }); - } - return d.length > t && (t = d.length), d; - }); - let o = 0; - e: - for (; o < t; o++) { - const a = (c = n[0][o]) == null ? void 0 : c.node; - for (let u = 1; u < n.length; u++) - if (((h = n[u][o]) == null ? void 0 : h.node) !== a) - break e; - } - if (!o) - throw new Error("Can not select root node."); - const i = n.map((a) => a[o - 1].index).sort(), s = i[0] || 0, r = i[i.length - 1] || 0, l = n[0][o - 1].node; - if (l.root) - throw new Error("Please select nodes in the same main topic."); - return { - parent: l.id, - start: s, - end: r - }; -}; -var In = function(e) { - const t = document.createElementNS("http://www.w3.org/2000/svg", "g"); - return t.setAttribute("id", e), t; -}; -var _e = function(e, t) { - const n = document.createElementNS("http://www.w3.org/2000/svg", "path"); - return C(n, { - d: e, - stroke: t || "#666", - fill: "none", - "stroke-linecap": "round", - "stroke-width": "2" - }), n; -}; -var ke = function(e, t, n, o, i) { - const s = document.createElementNS("http://www.w3.org/2000/svg", "text"); - return C(s, { - "text-anchor": o, - x: t + "", - y: n + "", - fill: i || "#666" - }), s.innerHTML = e, s; -}; -var Kn = (e) => N(e).parentElement.parentElement; -var Un = function({ parent: e, start: t }) { - var s, r; - const n = N(e), o = n.nodeObj; - let i; - return o.root === true ? i = (s = N(o.children[t].id).closest("me-main")) == null ? void 0 : s.className : i = (r = n.closest("me-main")) == null ? void 0 : r.className, i; -}; -var Ie = function(e, t) { - var _; - const { id: n, text: o, parent: i, start: s, end: r } = t, l = e.nodes, h = N(i).nodeObj, a = Un(t); - let u = 1 / 0, d = 0, p = 0, g = 0; - for (let P = s; P <= r; P++) { - const U = (_ = h.children) == null ? void 0 : _[P]; - if (!U) - return console.warn("Child not found"), e.removeSummary(n), null; - const H = Kn(U.id), { offsetLeft: Z, offsetTop: fe } = K(l, H); - P === s && (p = fe), P === r && (g = fe + H.offsetHeight), Z < u && (u = Z), H.offsetWidth + Z > d && (d = H.offsetWidth + Z); - } - let m, f; - const v = p + 10, y = g + 10, b = (v + y) / 2, x = e.theme.cssVar["--color"]; - a === "lhs" ? (m = _e(`M ${u + 10} ${v} c -5 0 -10 5 -10 10 L ${u} ${y - 10} c 0 5 5 10 10 10 M ${u} ${b} h -10`, x), f = ke(o, u - 20, b + 6, "end", x)) : (m = _e(`M ${d - 10} ${v} c 5 0 10 5 10 10 L ${d} ${y - 10} c 0 5 -5 10 -10 10 M ${d} ${b} h 10`, x), f = ke(o, d + 20, b + 6, "start", x)); - const w = In("s-" + n); - return w.appendChild(m), w.appendChild(f), w.summaryObj = t, e.summarySvg.appendChild(w), w; -}; -var Yn = function() { - let e = []; - this.currentNode ? e = [this.currentNode] : this.currentNodes && (e = this.currentNodes); - const { parent: t, start: n, end: o } = Wn(e), i = { id: J(), parent: t, start: n, end: o, text: "summary" }, s = Ie(this, i); - this.summaries.push(i), this.editSummary(s), this.bus.fire("operation", { - name: "createSummary", - obj: i - }); -}; -var Gn = function(e) { - var n; - const t = this.summaries.findIndex((o) => o.id === e); - t > -1 && (this.summaries.splice(t, 1), (n = document.querySelector("#s-" + e)) == null || n.remove()), this.bus.fire("operation", { - name: "removeSummary", - obj: { id: e } - }); -}; -var Xn = function(e) { - const t = e.children[1].getBBox(), n = 6, o = 3, i = document.createElementNS("http://www.w3.org/2000/svg", "rect"); - C(i, { - x: t.x - n + "", - y: t.y - n + "", - width: t.width + n * 2 + "", - height: t.height + n * 2 + "", - rx: o + "", - stroke: this.theme.cssVar["--selected"] || "#4dc4ff", - "stroke-width": "2", - fill: "none" - }), i.classList.add("selected"), e.appendChild(i), this.currentSummary = e; -}; -var Jn = function() { - var e, t; - (t = (e = this.currentSummary) == null ? void 0 : e.querySelector("rect")) == null || t.remove(), this.currentSummary = null; -}; -var Qn = function() { - this.summarySvg.innerHTML = "", this.summaries.forEach((e) => { - try { - Ie(this, e); - } catch { - console.warn("Node may not be expanded"); - } - }), this.nodes.insertAdjacentElement("beforeend", this.summarySvg); -}; -var Zn = function(e) { - if (console.time("editSummary"), !e) - return; - const t = e.childNodes[1]; - Oe(this, t, (n) => { - var s; - const o = e.summaryObj, i = ((s = n.textContent) == null ? void 0 : s.trim()) || ""; - i === "" ? o.text = origin : o.text = i, n.remove(), i !== origin && (t.innerHTML = o.text, this.linkDiv(), this.bus.fire("operation", { - name: "finishEditSummary", - obj: o - })); - }), console.timeEnd("editSummary"); -}; -var eo = Object.freeze(Object.defineProperty({ - __proto__: null, - createSummary: Yn, - editSummary: Zn, - removeSummary: Gn, - renderSummary: Qn, - selectSummary: Xn, - unselectSummary: Jn -}, Symbol.toStringTag, { value: "Module" })); -function to(e, t) { - const n = document.createElementNS("http://www.w3.org/2000/svg", "svg"); - return C(n, { - version: "1.1", - xmlns: "http://www.w3.org/2000/svg", - height: e, - width: t - }), n; -} -function no(e, t) { - return (parseInt(e) - parseInt(t)) / 2; -} -function oo(e, t, n, o) { - const i = document.createElementNS("http://www.w3.org/2000/svg", "g"); - let s = ""; - return e.text ? s = e.text.textContent : s = e.childNodes[0].textContent, s.split(` -`).forEach((l, c) => { - const h = document.createElementNS("http://www.w3.org/2000/svg", "text"); - C(h, { - x: n + parseInt(t.paddingLeft) + "", - y: o + parseInt(t.paddingTop) + no(t.lineHeight, t.fontSize) * (c + 1) + parseFloat(t.fontSize) * (c + 1) + "", - "text-anchor": "start", - "font-family": t.fontFamily, - "font-size": `${t.fontSize}`, - "font-weight": `${t.fontWeight}`, - fill: `${t.color}` - }), h.innerHTML = l, i.appendChild(h); - }), i; -} -function io(e, t, n, o) { - let i = ""; - e.text ? i = e.text.textContent : i = e.childNodes[0].textContent; - const s = document.createElementNS("http://www.w3.org/2000/svg", "foreignObject"); - C(s, { - x: n + parseInt(t.paddingLeft) + "", - y: o + parseInt(t.paddingTop) + "", - width: t.width, - height: t.height - }); - const r = document.createElement("div"); - return C(r, { - xmlns: "http://www.w3.org/1999/xhtml", - style: `font-family: ${t.fontFamily}; font-size: ${t.fontSize}; font-weight: ${t.fontWeight}; color: ${t.color}; white-space: pre-wrap;` - }), r.innerHTML = i, s.appendChild(r), s; -} -function ce(e, t, n = false) { - const o = getComputedStyle(t), { offsetLeft: i, offsetTop: s } = K(e.nodes, t), r = document.createElementNS("http://www.w3.org/2000/svg", "rect"); - C(r, { - x: i + "", - y: s + "", - rx: o.borderRadius, - ry: o.borderRadius, - width: o.width, - height: o.height, - fill: o.backgroundColor, - stroke: o.borderColor, - "stroke-width": o.borderWidth - }); - const l = document.createElementNS("http://www.w3.org/2000/svg", "g"); - l.appendChild(r); - let c; - return n ? c = io(t, o, i, s) : c = oo(t, o, i, s), l.appendChild(c), l; -} -function so(e, t) { - const n = getComputedStyle(t), { offsetLeft: o, offsetTop: i } = K(e.nodes, t), s = document.createElementNS("http://www.w3.org/2000/svg", "a"), r = document.createElementNS("http://www.w3.org/2000/svg", "text"); - return C(r, { - x: o + "", - y: i + parseInt(n.fontSize) + "", - "text-anchor": "start", - "font-family": n.fontFamily, - "font-size": `${n.fontSize}`, - "font-weight": `${n.fontWeight}`, - fill: `${n.color}` - }), r.innerHTML = t.textContent, s.appendChild(r), s.setAttribute("href", t.href), s; -} -var te = 100; -var ro = ''; -var Ke = (e, t = false) => { - var u, d, p; - const n = e.nodes, o = n.offsetHeight + te * 2, i = n.offsetWidth + te * 2, s = to(o + "px", i + "px"), r = document.createElementNS("http://www.w3.org/2000/svg", "svg"), l = document.createElementNS("http://www.w3.org/2000/svg", "rect"); - C(l, { - x: "0", - y: "0", - width: `${i}`, - height: `${o}`, - fill: e.theme.cssVar["--bgcolor"] - }), s.appendChild(l), n.querySelectorAll(".subLines").forEach((g) => { - const m = g.cloneNode(true), { offsetLeft: f, offsetTop: v } = K(n, g.parentElement); - m.setAttribute("x", `${f}`), m.setAttribute("y", `${v}`), r.appendChild(m); - }); - const c = (u = n.querySelector(".lines")) == null ? void 0 : u.cloneNode(true); - c && r.appendChild(c); - const h = (d = n.querySelector(".topiclinks")) == null ? void 0 : d.cloneNode(true); - h && r.appendChild(h); - const a = (p = n.querySelector(".summary")) == null ? void 0 : p.cloneNode(true); - return a && r.appendChild(a), n.querySelectorAll("me-tpc").forEach((g) => { - r.appendChild(ce(e, g, !t)); - }), n.querySelectorAll(".tags > span").forEach((g) => { - r.appendChild(ce(e, g)); - }), n.querySelectorAll(".icons > span").forEach((g) => { - r.appendChild(ce(e, g)); - }), n.querySelectorAll(".hyper-link").forEach((g) => { - r.appendChild(so(e, g)); - }), C(r, { - x: te + "", - y: te + "", - overflow: "visible" - }), s.appendChild(r), ro + s.outerHTML; -}; -function lo(e) { - return new Promise((t, n) => { - const o = new FileReader(); - o.onload = (i) => { - t(i.target.result); - }, o.onerror = (i) => { - n(i); - }, o.readAsDataURL(e); - }); -} -var co = function(e = false) { - const t = Ke(this, e); - return new Blob([t], { type: "image/svg+xml" }); -}; -var ao = async function(e = false) { - const t = Ke(this, e), n = new Blob([t], { type: "image/svg+xml" }), o = await lo(n); - return new Promise((i, s) => { - const r = new Image(); - r.setAttribute("crossOrigin", "anonymous"), r.onload = () => { - const l = document.createElement("canvas"); - l.width = r.width, l.height = r.height, l.getContext("2d").drawImage(r, 0, 0), l.toBlob(i, "image/png", 1); - }, r.src = o, r.onerror = s; - }); -}; -var ho = Object.freeze(Object.defineProperty({ - __proto__: null, - exportPng: ao, - exportSvg: co -}, Symbol.toStringTag, { value: "Module" })); -function uo(e, t) { - return async function(...n) { - const o = this.before[t]; - o && !await o.apply(this, n) || e.apply(this, n); - }; -} -var Se = Object.keys(We); -var Ue = {}; -for (let e = 0; e < Se.length; e++) { - const t = Se[e]; - Ue[t] = uo(We[t], t); -} -var fo = { - getObjById: oe, - generateNewObj: Xe, - layout: et, - linkDiv: ht, - editTopic: lt, - createWrapper: ot, - createParent: it, - createChildren: st, - createTopic: rt, - findEle: N, - changeTheme: At, - ...ln, - ...Ue, - ...Vn, - ...eo, - ...ho, - init(e) { - if (!e || !e.nodeData) - return new Error("MindElixir: `data` is required"); - e.direction !== void 0 && (this.direction = e.direction), this.changeTheme(e.theme || this.theme, false), this.nodeData = e.nodeData, $(this.nodeData), this.linkData = e.linkData || {}, this.summaries = e.summaries || [], this.tidyCustomLink(), this.toolBar && St(this), this.keypress && bt(this), this.editable && Ot(this), Ye() && this.mobileMenu ? yt(this) : this.contextMenu && mt(this, this.contextMenuOption), this.draggable && Et(this), this.allowUndo && Ct(this), this.toCenter(), this.layout(), this.linkDiv(); - } -}; -var Y = document; -function D({ - el: e, - direction: t, - locale: n, - draggable: o, - editable: i, - contextMenu: s, - contextMenuOption: r, - toolBar: l, - keypress: c, - mouseSelectionButton: h, - before: a, - newTopicName: u, - allowUndo: d, - mainLinkStyle: p, - subLinkStyle: g, - overflowHidden: m, - mobileMenu: f, - theme: v -}) { - console.log("ME_version " + D.version, this); - let y = null; - const b = Object.prototype.toString.call(e); - if (b === "[object HTMLDivElement]" ? y = e : b === "[object String]" && (y = document.querySelector(e)), !y) - throw new Error("MindElixir: el is not a valid element"); - y.className += " mind-elixir", y.innerHTML = "", y.style.setProperty("--gap", T + "px"), this.mindElixirBox = y, this.before = a || {}, this.locale = n || "en", this.contextMenuOption = r, this.contextMenu = s === void 0 ? true : s, this.toolBar = l === void 0 ? true : l, this.keypress = c === void 0 ? true : c, this.mouseSelectionButton = h || 0, this.mobileMenu = f || false, this.direction = typeof t == "number" ? t : 1, this.draggable = o === void 0 ? true : o, this.newTopicName = u || "new node", this.editable = i === void 0 ? true : i, this.allowUndo = d === void 0 ? false : d, this.currentNode = null, this.currentLink = null, this.scaleVal = 1, this.tempDirection = null, this.mainLinkStyle = p || 0, this.subLinkStyle = g || 0, this.overflowHidden = m || false, this.bus = Ze.create(), this.container = Y.createElement("div"), this.container.className = "map-container"; - const x = window.matchMedia("(prefers-color-scheme: dark)"); - this.theme = v || (x.matches ? Me : Le); - const w = Y.createElement("div"); - w.className = "map-canvas", this.map = w, this.map.setAttribute("tabindex", "0"), this.container.appendChild(this.map), this.mindElixirBox.appendChild(this.container), this.nodes = Y.createElement("me-nodes"), this.nodes.className = "main-node-container", this.lines = G("lines"), this.summarySvg = G("summary"), this.linkController = G("linkcontroller"), this.P2 = Y.createElement("div"), this.P3 = Y.createElement("div"), this.P2.className = this.P3.className = "circle", this.P2.style.display = this.P3.style.display = "none", this.line1 = pe(), this.line2 = pe(), this.linkController.appendChild(this.line1), this.linkController.appendChild(this.line2), this.linkSvgGroup = G("topiclinks"), this.map.appendChild(this.nodes), this.overflowHidden ? this.container.style.overflow = "hidden" : Qe(this); -} -D.prototype = fo; -D.LEFT = L; -D.RIGHT = z; -D.SIDE = X; -D.THEME = Le; -D.DARK_THEME = Me; -D.version = "3.3.2"; -D.E = N; -D.new = (e) => ({ - nodeData: { - id: J(), - topic: e || "new topic", - root: true, - children: [] - }, - linkData: {} -}); -export { - D as default -}; -/*! Bundled license information: - -mind-elixir/dist/MindElixir.js: - (*! @viselect/vanilla v3.3.1 MIT | https://github.com/Simonwep/selection/tree/master/packages/vanilla *) -*/ -//# sourceMappingURL=mind-elixir.js.map diff --git a/frontend/node_modules/.vite/deps/mind-elixir.js.map b/frontend/node_modules/.vite/deps/mind-elixir.js.map deleted file mode 100644 index 439329e..0000000 --- a/frontend/node_modules/.vite/deps/mind-elixir.js.map +++ /dev/null @@ -1,7 +0,0 @@ -{ - "version": 3, - "sources": ["../../mind-elixir/dist/MindElixir.js"], - "sourcesContent": ["(function(){\"use strict\";try{if(typeof document<\"u\"){var i=document.createElement(\"style\");i.appendChild(document.createTextNode(\".mind-elixir{--gap: 30px;--root-radius: 30px;--main-radius: 20px;--root-color: #ffffff;--root-bgcolor: #4c4f69;--main-color: #444446;--main-bgcolor: #ffffff;--topic-padding: 3px;--color: #777777;--bgcolor: #f6f6f6;--selected: #4dc4ff;--panel-color: #444446;--panel-bgcolor: #ffffff;--panel-border-color: #eaeaea;position:relative;-webkit-tap-highlight-color:rgba(0,0,0,0);font-family:-apple-system,BlinkMacSystemFont,Helvetica Neue,PingFang SC,Microsoft YaHei,Source Han Sans SC,Noto Sans CJK SC,WenQuanYi Micro Hei,sans-serif}.mind-elixir .hyper-link{text-decoration:none;margin-left:.3em}.map-container{-webkit-user-select:none;user-select:none;height:100%;width:100%;overflow:scroll;font-size:15px}.map-container::-webkit-scrollbar{width:0px;height:0px}.map-container .selected{box-shadow:0 0 0 2px var(--selected)}.map-container .lhs{direction:rtl}.map-container .lhs me-tpc{direction:ltr}.map-container .map-canvas{height:20000px;width:20000px;position:relative;-webkit-user-select:none;user-select:none;transition:transform .3s;transform:scale(1);background-color:var(--bgcolor)}.map-container .map-canvas me-nodes{position:absolute;display:flex;justify-content:center;align-items:center;height:fit-content;width:fit-content}.map-container .map-canvas me-root{position:relative}.map-container .map-canvas me-root me-tpc{display:block;font-size:25px;line-height:1.2em;color:var(--root-color);padding:10px var(--gap);border-radius:var(--root-radius);white-space:pre-wrap;background-color:var(--root-bgcolor)}.map-container .map-canvas me-root me-tpc #input-box{padding:10px var(--gap)}.map-container me-main>me-wrapper{position:relative;margin:20px 65px}.map-container me-main>me-wrapper>me-parent{margin:var(--gap);padding:0}.map-container me-main>me-wrapper>me-parent>me-tpc{border-radius:var(--main-radius);background-color:var(--main-bgcolor);border:2px solid var(--main-color);color:var(--main-color);padding:8px var(--gap)}.map-container me-main>me-wrapper>me-parent>me-tpc #input-box{padding:8px var(--gap)}.map-container me-wrapper{display:block;pointer-events:none;width:fit-content}.map-container me-children,.map-container me-parent{display:inline-block;vertical-align:middle}.map-container me-parent{position:relative;cursor:pointer;padding:6px var(--gap);margin-top:10px}.map-container me-parent me-tpc{position:relative;display:block;border-radius:3px;color:var(--color);pointer-events:all;max-width:35em;white-space:pre-wrap;padding:var(--topic-padding);line-height:1.2em}.map-container me-parent me-tpc .insert-preview{position:absolute;width:100%;left:0;z-index:9}.map-container me-parent me-tpc .show{background:#7ad5ff;pointer-events:none;opacity:.7}.map-container me-parent me-tpc .before{height:14px;top:-14px}.map-container me-parent me-tpc .in{height:100%;top:0}.map-container me-parent me-tpc .after{height:14px;bottom:-14px}.map-container me-parent me-epd{position:absolute;height:18px;width:18px;opacity:.8;background-image:url(data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBzdGFuZGFsb25lPSJubyI/PjwhRE9DVFlQRSBzdmcgUFVCTElDICItLy9XM0MvL0RURCBTVkcgMS4xLy9FTiIgImh0dHA6Ly93d3cudzMub3JnL0dyYXBoaWNzL1NWRy8xLjEvRFREL3N2ZzExLmR0ZCI+CjxzdmcgdD0iMTY1NjY1NDcxNzI0MiIgY2xhc3M9Imljb24iIHZpZXdCb3g9IjAgMCAxMDI0IDEwMjQiIHZlcnNpb249IjEuMSIKICAgIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIKICAgIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB3aWR0aD0iMjAwIiBoZWlnaHQ9IjIwMCI+CiAgICA8cGF0aCBkPSJNNTEyIDc0LjY2NjY2N0MyNzAuOTMzMzMzIDc0LjY2NjY2NyA3NC42NjY2NjcgMjcwLjkzMzMzMyA3NC42NjY2NjcgNTEyUzI3MC45MzMzMzMgOTQ5LjMzMzMzMyA1MTIgOTQ5LjMzMzMzMyA5NDkuMzMzMzMzIDc1My4wNjY2NjcgOTQ5LjMzMzMzMyA1MTIgNzUzLjA2NjY2NyA3NC42NjY2NjcgNTEyIDc0LjY2NjY2N3oiIHN0cm9rZS13aWR0aD0iNTQiIHN0cm9rZT0nYmxhY2snIGZpbGw9J3doaXRlJyA+PC9wYXRoPgogICAgPHBhdGggZD0iTTY4Mi42NjY2NjcgNDgwaC0xMzguNjY2NjY3VjM0MS4zMzMzMzNjMC0xNy4wNjY2NjctMTQuOTMzMzMzLTMyLTMyLTMycy0zMiAxNC45MzMzMzMtMzIgMzJ2MTM4LjY2NjY2N0gzNDEuMzMzMzMzYy0xNy4wNjY2NjcgMC0zMiAxNC45MzMzMzMtMzIgMzJzMTQuOTMzMzMzIDMyIDMyIDMyaDEzOC42NjY2NjdWNjgyLjY2NjY2N2MwIDE3LjA2NjY2NyAxNC45MzMzMzMgMzIgMzIgMzJzMzItMTQuOTMzMzMzIDMyLTMydi0xMzguNjY2NjY3SDY4Mi42NjY2NjdjMTcuMDY2NjY3IDAgMzItMTQuOTMzMzMzIDMyLTMycy0xNC45MzMzMzMtMzItMzItMzJ6Ij48L3BhdGg+Cjwvc3ZnPg==);background-repeat:no-repeat;background-size:contain;background-position:center;pointer-events:all;z-index:9}.map-container me-parent me-epd.minus{background-image:url(data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBzdGFuZGFsb25lPSJubyI/PjwhRE9DVFlQRSBzdmcgUFVCTElDICItLy9XM0MvL0RURCBTVkcgMS4xLy9FTiIgImh0dHA6Ly93d3cudzMub3JnL0dyYXBoaWNzL1NWRy8xLjEvRFREL3N2ZzExLmR0ZCI+CjxzdmcgdD0iMTY1NjY1NTU2NDk4NSIgY2xhc3M9Imljb24iIHZpZXdCb3g9IjAgMCAxMDI0IDEwMjQiIHZlcnNpb249IjEuMSIKICAgIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIKICAgIHhtbG5zOnhsaW5rPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiB3aWR0aD0iMjAwIiBoZWlnaHQ9IjIwMCI+CiAgICA8cGF0aCBkPSJNNTEyIDc0LjY2NjY2N0MyNzAuOTMzMzMzIDc0LjY2NjY2NyA3NC42NjY2NjcgMjcwLjkzMzMzMyA3NC42NjY2NjcgNTEyUzI3MC45MzMzMzMgOTQ5LjMzMzMzMyA1MTIgOTQ5LjMzMzMzMyA5NDkuMzMzMzMzIDc1My4wNjY2NjcgOTQ5LjMzMzMzMyA1MTIgNzUzLjA2NjY2NyA3NC42NjY2NjcgNTEyIDc0LjY2NjY2N3oiIHN0cm9rZS13aWR0aD0iNTQiIHN0cm9rZT0nYmxhY2snIGZpbGw9J3doaXRlJyA+PC9wYXRoPgogICAgPHBhdGggZD0iTTY4Mi42NjY2NjcgNTQ0SDM0MS4zMzMzMzNjLTE3LjA2NjY2NyAwLTMyLTE0LjkzMzMzMy0zMi0zMnMxNC45MzMzMzMtMzIgMzItMzJoMzQxLjMzMzMzNGMxNy4wNjY2NjcgMCAzMiAxNC45MzMzMzMgMzIgMzJzLTE0LjkzMzMzMyAzMi0zMiAzMnoiPjwvcGF0aD4KPC9zdmc+)!important;transition:opacity .3s;opacity:0}.map-container me-parent me-epd.minus:hover{opacity:.8}.map-container .icon{width:1em;height:1em;vertical-align:-.15em;fill:currentColor;overflow:hidden}.map-container .lines,.map-container .summary,.map-container .subLines,.map-container .topiclinks,.map-container .linkcontroller{position:absolute;height:102%;width:100%;top:0;left:0}.map-container .topiclinks,.map-container .linkcontroller,.map-container .summary{pointer-events:none}.map-container .topiclinks text,.map-container .linkcontroller text,.map-container .summary text{pointer-events:all}.map-container .topiclinks .selected,.map-container .linkcontroller .selected,.map-container .summary .selected{pointer-events:none}.map-container .lines,.map-container .subLines{pointer-events:none;z-index:-1}.map-container .topiclinks *,.map-container .linkcontroller *{z-index:100}.map-container .topiclinks g{cursor:pointer}.map-container #input-box{position:absolute;top:0;left:0;padding:var(--topic-padding);color:var(--color);background-color:var(--bgcolor);width:max-content;max-width:35em;z-index:11;direction:ltr;-webkit-user-select:auto;user-select:auto;pointer-events:all}.map-container me-tpc>div,.map-container me-tpc>span,.map-container me-tpc>img{pointer-events:none}.map-container me-tpc>img{display:block;margin-bottom:8px;object-fit:cover}.map-container me-tpc>.text{display:inline-block}.map-container .circle{position:absolute;height:10px;width:10px;margin-top:-5px;margin-left:-5px;border-radius:100%;background:#757575;border:2px solid #ffffff;cursor:pointer}.map-container .tags{direction:ltr}.map-container .tags span{display:inline-block;border-radius:3px;padding:2px 4px;background:#d6f0f8;color:#276f86;margin:2px 3px 0 0;font-size:12px;line-height:1.3em}.map-container .icons{display:inline-block;direction:ltr;margin-right:10px}.map-container .icons span{display:inline-block}.map-container .mind-elixir-ghost{position:fixed;top:-100%;left:-100%;box-sizing:content-box;opacity:.5;background-color:#f6f6f6;max-width:200px;width:fit-content;overflow:hidden;white-space:nowrap;text-overflow:ellipsis;padding:8px 16px;border-radius:6px;border:#666666 2px solid}.map-container .selection-area{background:#4f90f22d;border:1px solid #4f90f2}.mind-elixir .context-menu{position:fixed;top:0;left:0;width:100%;height:100%;z-index:99}.mind-elixir .context-menu .menu-list{position:fixed;list-style:none;margin:0;padding:0;font:300 15px Roboto,sans-serif;color:var(--panel-color);box-shadow:0 12px 15px #0003}.mind-elixir .context-menu .menu-list li{min-width:200px;overflow:hidden;white-space:nowrap;padding:10px 14px;background:var(--panel-bgcolor);border-bottom:1px solid var(--panel-border-color)}.mind-elixir .context-menu .menu-list li a{color:#333;text-decoration:none}.mind-elixir .context-menu .menu-list li.disabled{display:none;color:#5e5e5e;background-color:#f7f7f7}.mind-elixir .context-menu .menu-list li.disabled:hover{cursor:default;background-color:#f7f7f7}.mind-elixir .context-menu .menu-list li:hover{cursor:pointer;filter:brightness(.9)}.mind-elixir .context-menu .menu-list li:first-child{border-radius:5px 5px 0 0}.mind-elixir .context-menu .menu-list li:last-child{border-bottom:0;border-radius:0 0 5px 5px}.mind-elixir .context-menu .menu-list li span:last-child{float:right}.mind-elixir .tips{position:absolute;bottom:20px;left:50%;transform:translate(-50%);color:var(--panel-color);font-weight:bolder}.mind-elixir .mobile-menu{position:absolute;left:20px;bottom:70px;z-index:99;margin:0;padding:0;color:#333;border-radius:5px;box-shadow:0 12px 15px #0003;overflow:hidden}.mind-elixir .mobile-menu *{transition:color .4s,background-color .4s}.mind-elixir .mobile-menu div{float:left;text-align:center;width:30px;overflow:hidden;white-space:nowrap;padding:8px;background-color:#fff;border-bottom:1px solid #ecf0f1}.mind-elixir .mobile-menu div a{color:#333;text-decoration:none}.mind-elixir .mobile-menu div.disabled{color:#5e5e5e;background-color:#f7f7f7}.mind-elixir .mobile-menu div.disabled:hover{cursor:default;background-color:#f7f7f7}.mind-elixir .mobile-menu div:hover{cursor:pointer;background-color:#ecf0f1}.mind-elixir-toolbar{font-family:iconfont;position:absolute;color:var(--panel-color);background:var(--panel-bgcolor);padding:10px;border-radius:5px;box-shadow:0 1px 2px #0003}.mind-elixir-toolbar svg{display:inline-block}.mind-elixir-toolbar span:active{opacity:.5}.mind-elixir-toolbar.rb{right:20px;bottom:20px}.mind-elixir-toolbar.rb span+span{margin-left:10px}.mind-elixir-toolbar.lt{font-size:20px;left:20px;top:20px}.mind-elixir-toolbar.lt span{display:block}.mind-elixir-toolbar.lt span+span{margin-top:10px}\")),document.head.appendChild(i)}}catch(e){console.error(\"vite-plugin-css-injected-by-js\",e)}})();\n(function(e) {\n var t, n, o, i, s, r, l = '', c = (c = document.getElementsByTagName(\"script\"))[c.length - 1].getAttribute(\"data-injectcss\");\n if (c && !e.__iconfont__svg__cssinject__) {\n e.__iconfont__svg__cssinject__ = !0;\n try {\n document.write(\n \"\"\n );\n } catch (a) {\n console && console.log(a);\n }\n }\n function h() {\n s || (s = !0, o());\n }\n t = function() {\n var a, u, d, p;\n (p = document.createElement(\"div\")).innerHTML = l, l = null, (d = p.getElementsByTagName(\"svg\")[0]) && (d.setAttribute(\"aria-hidden\", \"true\"), d.style.position = \"absolute\", d.style.width = 0, d.style.height = 0, d.style.overflow = \"hidden\", a = d, (u = document.body).firstChild ? (p = a, (d = u.firstChild).parentNode.insertBefore(p, d)) : u.appendChild(a));\n }, document.addEventListener ? ~[\"complete\", \"loaded\", \"interactive\"].indexOf(document.readyState) ? setTimeout(t, 0) : (n = function() {\n document.removeEventListener(\"DOMContentLoaded\", n, !1), t();\n }, document.addEventListener(\"DOMContentLoaded\", n, !1)) : document.attachEvent && (o = t, i = e.document, s = !1, (r = function() {\n try {\n i.documentElement.doScroll(\"left\");\n } catch {\n return void setTimeout(r, 50);\n }\n h();\n })(), i.onreadystatechange = function() {\n i.readyState == \"complete\" && (i.onreadystatechange = null, h());\n });\n})(window);\nconst L = 0, z = 1, X = 2, T = 30, M = 8, Le = {\n name: \"Latte\",\n palette: [\"#dd7878\", \"#ea76cb\", \"#8839ef\", \"#e64553\", \"#fe640b\", \"#df8e1d\", \"#40a02b\", \"#209fb5\", \"#1e66f5\", \"#7287fd\"],\n cssVar: {\n \"--main-color\": \"#444446\",\n \"--main-bgcolor\": \"#ffffff\",\n \"--color\": \"#777777\",\n \"--bgcolor\": \"#f6f6f6\",\n \"--panel-color\": \"#444446\",\n \"--panel-bgcolor\": \"#ffffff\",\n \"--panel-border-color\": \"#eaeaea\"\n }\n}, Me = {\n name: \"Dark\",\n palette: [\"#848FA0\", \"#748BE9\", \"#D2F9FE\", \"#4145A5\", \"#789AFA\", \"#706CF4\", \"#EF987F\", \"#775DD5\", \"#FCEECF\", \"#DA7FBC\"],\n cssVar: {\n \"--main-color\": \"#ffffff\",\n \"--main-bgcolor\": \"#4c4f69\",\n \"--color\": \"#cccccc\",\n \"--bgcolor\": \"#252526\",\n \"--panel-color\": \"#ffffff\",\n \"--panel-bgcolor\": \"#2d3748\",\n \"--panel-border-color\": \"#696969\"\n }\n};\nfunction ne(e) {\n return e.replace(/&/g, \"&\").replace(/ /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent), oe = function(e, t) {\n if (t.id === e)\n return t;\n if (t.children && t.children.length) {\n for (let n = 0; n < t.children.length; n++) {\n const o = oe(e, t.children[n]);\n if (o)\n return o;\n }\n return null;\n } else\n return null;\n}, $ = (e, t) => {\n if (e.parent = t, e.children)\n for (let n = 0; n < e.children.length; n++)\n $(e.children[n], e);\n};\nfunction Te(e) {\n if (e.id = J(), e.children)\n for (let t = 0; t < e.children.length; t++)\n Te(e.children[t]);\n}\nconst Ge = (e, t) => {\n let n = Date.now();\n return function(...o) {\n Date.now() - n >= t && (e(...o), n = Date.now());\n };\n};\nfunction $e(e, t, n, o) {\n const i = o - t, s = e - n;\n let r = Math.atan(Math.abs(i) / Math.abs(s)) / 3.14 * 180;\n s < 0 && i > 0 && (r = 180 - r), s < 0 && i < 0 && (r = 180 + r), s > 0 && i < 0 && (r = 360 - r);\n const l = 15, c = 30, h = r + c, a = r - c;\n return {\n x1: n + Math.cos(Math.PI * h / 180) * l,\n y1: o - Math.sin(Math.PI * h / 180) * l,\n x2: n + Math.cos(Math.PI * a / 180) * l,\n y2: o - Math.sin(Math.PI * a / 180) * l\n };\n}\nfunction J() {\n return ((/* @__PURE__ */ new Date()).getTime().toString(16) + Math.random().toString(16).substr(2)).substr(2, 16);\n}\nconst Xe = function() {\n const e = J();\n return {\n topic: this.newTopicName,\n id: e\n };\n};\nfunction Je(e, t) {\n let n = !0;\n for (; t.parent; ) {\n if (t.parent === e) {\n n = !1;\n break;\n }\n t = t.parent;\n }\n return n;\n}\nfunction De(e) {\n return JSON.parse(\n JSON.stringify(e, (n, o) => {\n if (n !== \"parent\")\n return o;\n })\n );\n}\nconst K = (e, t) => {\n let n = 0, o = 0;\n for (; t && t !== e; )\n n += t.offsetLeft, o += t.offsetTop, t = t.offsetParent;\n return { offsetLeft: n, offsetTop: o };\n}, C = (e, t) => {\n for (const n in t)\n e.setAttribute(n, t[n]);\n}, ae = (e) => e ? e.tagName === \"ME-TPC\" : !1, S = {\n moved: !1,\n // diffrentiate click and move\n mousedown: !1,\n onMove(e, t) {\n if (this.mousedown) {\n this.moved = !0;\n const n = e.movementX, o = e.movementY;\n t.scrollTo(t.scrollLeft - n, t.scrollTop - o);\n }\n },\n clear() {\n this.moved = !1, this.mousedown = !1;\n }\n};\nfunction Qe(e) {\n e.map.addEventListener(\"click\", (t) => {\n var o, i;\n if (t.button !== 0)\n return;\n if ((o = e.helper1) != null && o.moved) {\n e.helper1.clear();\n return;\n }\n if ((i = e.helper2) != null && i.moved) {\n e.helper2.clear();\n return;\n }\n if (S.moved) {\n S.clear();\n return;\n }\n e.unselectNode(), e.unselectNodes(), e.unselectSummary(), e.unselectLink();\n const n = t.target;\n if (n.tagName === \"ME-EPD\")\n e.expandNode(n.previousSibling);\n else if (e.editable)\n ae(n) ? e.selectNode(n, !1, t) : n.tagName === \"text\" ? n.dataset.type === \"custom-link\" ? e.selectLink(n.parentElement) : e.selectSummary(n.parentElement) : n.className === \"circle\" || e.hideLinkController && e.hideLinkController();\n else\n return;\n }), e.map.addEventListener(\"dblclick\", (t) => {\n if (t.preventDefault(), !e.editable)\n return;\n const n = t.target;\n ae(n) ? e.beginEdit(n) : n.tagName === \"text\" && (n.dataset.type === \"custom-link\" ? e.editCutsomLinkLabel(n.parentElement) : e.editSummary(n.parentElement));\n }), e.map.addEventListener(\"mousemove\", (t) => {\n t.target.contentEditable !== \"true\" && S.onMove(t, e.container);\n }), e.map.addEventListener(\"mousedown\", (t) => {\n const n = e.mouseSelectionButton === 0 ? 2 : 0;\n t.button === n && t.target.contentEditable !== \"true\" && (S.moved = !1, S.mousedown = !0);\n }), e.map.addEventListener(\"mouseleave\", (t) => {\n const n = e.mouseSelectionButton === 0 ? 2 : 0;\n t.button === n && S.clear();\n }), e.map.addEventListener(\"mouseup\", (t) => {\n const n = e.mouseSelectionButton === 0 ? 2 : 0;\n t.button === n && S.clear();\n }), e.map.addEventListener(\"contextmenu\", (t) => {\n t.preventDefault();\n });\n}\nconst Ze = {\n create() {\n return {\n handlers: {},\n showHandler: function() {\n console.log(this.handlers);\n },\n addListener: function(e, t) {\n this.handlers[e] === void 0 && (this.handlers[e] = []), this.handlers[e].push(t);\n },\n fire: function(e, ...t) {\n if (this.handlers[e] instanceof Array) {\n const n = this.handlers[e];\n for (let o = 0; o < n.length; o++)\n n[o](...t);\n }\n },\n removeListener: function(e, t) {\n if (!this.handlers[e])\n return;\n const n = this.handlers[e];\n if (!t)\n n.length = 0;\n else if (n.length)\n for (let o = 0; o < n.length; o++)\n n[o] === t && this.handlers[e].splice(o, 1);\n }\n };\n }\n}, ie = document, et = function() {\n console.time(\"layout\"), this.nodes.innerHTML = \"\";\n const e = this.createTopic(this.nodeData);\n ue(e, this.nodeData), e.draggable = !1;\n const t = ie.createElement(\"me-root\");\n t.appendChild(e);\n const n = this.nodeData.children || [];\n if (this.direction === X) {\n let o = 0, i = 0;\n n.map((s) => {\n s.direction === L ? o += 1 : s.direction === z ? i += 1 : o <= i ? (s.direction = L, o += 1) : (s.direction = z, i += 1);\n });\n }\n tt(this, n, t), console.timeEnd(\"layout\");\n}, tt = function(e, t, n) {\n const o = ie.createElement(\"me-main\");\n o.className = \"lhs\";\n const i = ie.createElement(\"me-main\");\n i.className = \"rhs\";\n for (let s = 0; s < t.length; s++) {\n const r = t[s], { grp: l } = e.createWrapper(r);\n e.direction === X ? r.direction === L ? o.appendChild(l) : i.appendChild(l) : e.direction === L ? o.appendChild(l) : i.appendChild(l);\n }\n e.nodes.appendChild(o), e.nodes.appendChild(n), e.nodes.appendChild(i), e.nodes.appendChild(e.lines);\n}, nt = function(e, t) {\n const n = ie.createElement(\"me-children\");\n for (let o = 0; o < t.length; o++) {\n const i = t[o], { grp: s } = e.createWrapper(i);\n n.appendChild(s);\n }\n return n;\n}, k = document, N = (e, t) => {\n const o = (t ? t.mindElixirBox : k).querySelector(`[data-nodeid=me${e}]`);\n if (!o)\n throw new Error(`FindEle: Node ${e} not found, maybe it's collapsed.`);\n return o;\n}, ue = function(e, t) {\n if (e.innerHTML = \"\", t.style && (e.style.color = t.style.color || \"\", e.style.background = t.style.background || \"\", e.style.fontSize = t.style.fontSize + \"px\", e.style.fontWeight = t.style.fontWeight || \"normal\"), t.branchColor && (e.style.borderColor = t.branchColor), t.image) {\n const n = t.image;\n if (n.url && n.width && n.height) {\n const o = k.createElement(\"img\");\n o.src = n.url, o.style.width = n.width + \"px\", o.style.height = n.height + \"px\", e.appendChild(o), e.image = o;\n } else\n console.warn(\"image url/width/height are required\");\n } else\n e.image && (e.image = void 0);\n {\n const n = k.createElement(\"span\");\n n.className = \"text\", n.textContent = t.topic, e.appendChild(n), e.text = n;\n }\n if (t.hyperLink) {\n const n = k.createElement(\"a\");\n n.className = \"hyper-link\", n.target = \"_blank\", n.innerText = \"🔗\", n.href = t.hyperLink, e.appendChild(n), e.linkContainer = n;\n } else\n e.linkContainer && (e.linkContainer = void 0);\n if (t.icons && t.icons.length) {\n const n = k.createElement(\"span\");\n n.className = \"icons\", n.innerHTML = t.icons.map((o) => `${ne(o)}`).join(\"\"), e.appendChild(n), e.icons = n;\n } else\n e.icons && (e.icons = void 0);\n if (t.tags && t.tags.length) {\n const n = k.createElement(\"div\");\n n.className = \"tags\", n.innerHTML = t.tags.map((o) => `${ne(o)}`).join(\"\"), e.appendChild(n), e.tags = n;\n } else\n e.tags && (e.tags = void 0);\n}, ot = function(e, t) {\n const n = k.createElement(\"me-wrapper\"), { p: o, tpc: i } = this.createParent(e);\n if (n.appendChild(o), !t && e.children && e.children.length > 0) {\n const s = re(e.expanded);\n if (o.appendChild(s), e.expanded !== !1) {\n const r = nt(this, e.children);\n n.appendChild(r);\n }\n }\n return { grp: n, top: o, tpc: i };\n}, it = function(e) {\n const t = k.createElement(\"me-parent\"), n = this.createTopic(e);\n return ue(n, e), t.appendChild(n), { p: t, tpc: n };\n}, st = function(e) {\n const t = k.createElement(\"me-children\");\n return t.append(...e), t;\n}, rt = function(e) {\n const t = k.createElement(\"me-tpc\");\n return t.nodeObj = e, t.dataset.nodeid = \"me\" + e.id, t.draggable = this.draggable, t;\n};\nfunction je(e) {\n const t = k.createRange();\n t.selectNodeContents(e);\n const n = window.getSelection();\n n && (n.removeAllRanges(), n.addRange(t));\n}\nconst lt = function(e) {\n if (console.time(\"editTopic\"), !e)\n return;\n const t = k.createElement(\"div\"), n = e.text.textContent;\n e.appendChild(t), t.id = \"input-box\", t.textContent = n, t.contentEditable = \"true\", t.spellcheck = !1, t.style.cssText = `min-width:${e.offsetWidth - 8}px;`, this.direction === L && (t.style.right = \"0\"), t.focus(), je(t), this.bus.fire(\"operation\", {\n name: \"beginEdit\",\n obj: e.nodeObj\n }), t.addEventListener(\"keydown\", (o) => {\n o.stopPropagation();\n const i = o.key;\n if (i === \"Enter\" || i === \"Tab\") {\n if (o.shiftKey)\n return;\n o.preventDefault(), t == null || t.blur(), this.map.focus();\n }\n }), t.addEventListener(\"blur\", () => {\n var s;\n if (!t)\n return;\n const o = e.nodeObj, i = ((s = t.textContent) == null ? void 0 : s.trim()) || \"\";\n console.log(i), i === \"\" ? o.topic = n : o.topic = i, t.remove(), i !== n && (e.text.textContent = o.topic, this.linkDiv(), this.bus.fire(\"operation\", {\n name: \"finishEdit\",\n obj: o,\n origin: n\n }));\n }), console.timeEnd(\"editTopic\");\n}, re = function(e) {\n const t = k.createElement(\"me-epd\");\n return t.expanded = e !== !1, t.className = e !== !1 ? \"minus\" : \"\", t;\n}, q = document, F = \"http://www.w3.org/2000/svg\", ct = function(e, t) {\n const n = q.createElementNS(F, \"path\");\n return n.setAttribute(\"d\", e), n.setAttribute(\"stroke\", t || \"#666\"), n.setAttribute(\"fill\", \"none\"), n.setAttribute(\"stroke-width\", \"3\"), n;\n}, G = function(e) {\n const t = q.createElementNS(F, \"svg\");\n return t.setAttribute(\"class\", e), t.setAttribute(\"overflow\", \"visible\"), t;\n}, pe = function() {\n const e = q.createElementNS(F, \"line\");\n return e.setAttribute(\"stroke\", \"#bbb\"), e.setAttribute(\"fill\", \"none\"), e.setAttribute(\"stroke-width\", \"2\"), e;\n}, at = function(e, t) {\n const n = q.createElementNS(F, \"path\");\n return n.setAttribute(\"d\", e), n.setAttribute(\"stroke\", t || \"#555\"), n.setAttribute(\"fill\", \"none\"), n.setAttribute(\"stroke-linecap\", \"square\"), n.setAttribute(\"stroke-width\", \"2\"), n;\n}, dt = function(e, t) {\n const n = {\n stroke: \"rgb(235, 95, 82)\",\n fill: \"none\",\n \"stroke-linecap\": \"cap\",\n \"stroke-width\": \"2\"\n }, o = q.createElementNS(F, \"g\"), i = q.createElementNS(F, \"path\"), s = q.createElementNS(F, \"path\");\n return C(s, {\n d: t,\n ...n\n }), C(i, {\n d: e,\n ...n,\n \"stroke-dasharray\": \"8,2\"\n }), o.appendChild(i), o.appendChild(s), o;\n}, Oe = function(e, t, n) {\n if (console.time(\"editSummary\"), !t)\n return;\n const o = document.createElement(\"div\");\n e.nodes.appendChild(o);\n const i = t.innerHTML;\n o.id = \"input-box\", o.textContent = i, o.contentEditable = \"true\", o.spellcheck = !1;\n const s = t.getAttribute(\"x\") + \"px\", r = t.getAttribute(\"y\") + \"px\";\n o.style.cssText = `min-width:${100 - 8}px;position:absolute;left:${s};top:${r};`;\n const l = t.getAttribute(\"text-anchor\");\n l === \"end\" ? o.style.cssText += \"transform: translate(-100%, -100%);\" : l === \"middle\" ? o.style.cssText += \"transform: translate(-50%, -100%);\" : o.style.cssText += \"transform: translate(0, -100%);\", o.focus(), je(o), o.addEventListener(\"keydown\", (c) => {\n c.stopPropagation();\n const h = c.key;\n if (h === \"Enter\" || h === \"Tab\") {\n if (c.shiftKey)\n return;\n c.preventDefault(), o.blur(), e.map.focus();\n }\n }), o.addEventListener(\"blur\", () => {\n o && n(o);\n }), console.timeEnd(\"editSummary\");\n};\nlet Ae = He;\nconst ht = function(e) {\n console.time(\"linkDiv\");\n const t = this.map.querySelector(\"me-root\");\n this.nodes.style.top = `${1e4 - this.nodes.offsetHeight / 2}px`, this.nodes.style.left = `${1e4 - t.offsetLeft - t.offsetWidth / 2}px`;\n const n = this.map.querySelectorAll(\"me-main > me-wrapper\");\n this.lines.innerHTML = \"\", Ae = this.subLinkStyle === 2 ? pt : He;\n for (let o = 0; o < n.length; o++) {\n const i = n[o], s = i.querySelector(\"me-tpc\"), r = i.firstChild, l = i.parentNode.className;\n let c = t.offsetLeft + t.offsetWidth / 2;\n const h = t.offsetTop + t.offsetHeight / 2;\n let a;\n const u = this.theme.palette, d = s.nodeObj.branchColor || u[o % u.length], { offsetLeft: p, offsetTop: g } = K(this.nodes, r);\n l === \"lhs\" ? a = p + r.offsetWidth : a = p;\n const m = g + r.offsetHeight / 2;\n let f = \"\";\n if (this.mainLinkStyle === 2)\n this.direction === X && (l === \"lhs\" ? c = c - t.offsetWidth / 6 : c = c + t.offsetWidth / 6), f = ut({ x1: c, y1: h, x2: a, y2: m });\n else {\n const b = (1 - Math.abs(m - i.parentElement.offsetTop - i.parentElement.offsetHeight / 2) / i.parentElement.offsetHeight) * 0.25 * (t.offsetWidth / 2);\n l === \"lhs\" ? c = c - t.offsetWidth / 10 - b : c = c + t.offsetWidth / 10 + b, f = ft({ x1: c, y1: h, x2: a, y2: m });\n }\n this.lines.appendChild(ct(f, d));\n const v = i.children[0].children[1];\n if (v && (v.style.top = (v.parentNode.offsetHeight - v.offsetHeight) / 2 + \"px\", l === \"lhs\" ? v.style.left = \"-10px\" : v.style.right = \"-10px\"), !(e && e !== i) && i.childElementCount) {\n const y = G(\"subLines\"), b = i.lastChild;\n b.tagName === \"svg\" && b.remove(), i.appendChild(y);\n const x = i.firstChild, w = i.children[1].children, _ = Pe(w, x, l, !0);\n y.appendChild(at(_, d));\n }\n }\n this.renderCustomLink(), this.renderSummary(), console.timeEnd(\"linkDiv\");\n}, Pe = function(e, t, n, o) {\n let i = \"\";\n const s = t.offsetTop, r = t.offsetLeft, l = t.offsetWidth, c = t.offsetHeight;\n for (let h = 0; h < e.length; h++) {\n const a = e[h], u = a.firstChild, d = u.offsetTop, p = u.offsetLeft, g = u.offsetWidth, m = u.offsetHeight;\n i += Ae({ pT: s, pL: r, pW: l, pH: c, cT: d, cL: p, cW: g, cH: m, direction: n, isFirst: o });\n const f = u.children[1];\n if (f) {\n if (f.style.bottom = -(f.offsetHeight / 2) + \"px\", n === \"lhs\" ? f.style.left = \"10px\" : n === \"rhs\" && (f.style.right = \"10px\"), !f.expanded)\n continue;\n } else\n continue;\n const v = a.children[1].children;\n v.length > 0 && (i += Pe(v, u, n));\n }\n return i;\n};\nfunction ut({ x1: e, y1: t, x2: n, y2: o }) {\n return `M ${e} ${t} V ${o > t ? o - 20 : o + 20} C ${e} ${o} ${e} ${o} ${n > e ? e + 20 : e - 20} ${o} H ${n}`;\n}\nfunction ft({ x1: e, y1: t, x2: n, y2: o }) {\n return `M ${e} ${t} Q ${e} ${o} ${n} ${o}`;\n}\nfunction pt({ pT: e, pL: t, pW: n, pH: o, cT: i, cL: s, cW: r, cH: l, direction: c, isFirst: h }) {\n let a;\n h ? a = e + o / 2 : a = e + o;\n const u = i + l;\n let d = 0, p = 0, g = 0;\n return c === \"lhs\" ? (d = t + T, p = s, g = s + r) : c === \"rhs\" && (d = t + n - T, p = s + r, g = s), u < a + 50 && u > a - 50 ? `M ${d} ${a} H ${g} V ${u} H ${p}` : u >= a ? `M ${d} ${a} H ${g} V ${u - M} A ${M} ${M} 0 0 ${d > p ? 1 : 0} ${d > p ? g - M : g + M} ${u} H ${p}` : `M ${d} ${a} H ${g} V ${u + M} A ${M} ${M} 0 0 ${d > p ? 0 : 1} ${d > p ? g - M : g + M} ${u} H ${p}`;\n}\nfunction He({ pT: e, pL: t, pW: n, pH: o, cT: i, cL: s, cW: r, cH: l, direction: c, isFirst: h }) {\n let a = 0, u = 0;\n h ? a = e + o / 2 : a = e + o;\n const d = i + l;\n let p = 0, g = 0, m = 0;\n const f = Math.min(Math.abs(a - d) / 800, 1.2) * T;\n return c === \"lhs\" ? (m = t, p = m + T, g = m - T, u = s + T, `M ${p} ${a} C ${m} ${a} ${m + f} ${d} ${g} ${d} H ${u}`) : (m = t + n, p = m - T, g = m + T, u = s + r - T, `M ${p} ${a} C ${m} ${a} ${m - f} ${d} ${g} ${d} H ${u}`);\n}\nconst me = {\n addChild: \"插入子节点\",\n addParent: \"插入父节点\",\n addSibling: \"插入同级节点\",\n removeNode: \"删除节点\",\n focus: \"专注\",\n cancelFocus: \"取消专注\",\n moveUp: \"上移\",\n moveDown: \"下移\",\n link: \"连接\",\n clickTips: \"请点击目标节点\",\n summary: \"摘要\"\n}, ge = {\n cn: me,\n zh_CN: me,\n zh_TW: {\n addChild: \"插入子節點\",\n addParent: \"插入父節點\",\n addSibling: \"插入同級節點\",\n removeNode: \"刪除節點\",\n focus: \"專注\",\n cancelFocus: \"取消專注\",\n moveUp: \"上移\",\n moveDown: \"下移\",\n link: \"連接\",\n clickTips: \"請點擊目標節點\",\n summary: \"摘要\"\n },\n en: {\n addChild: \"Add child\",\n addParent: \"Add parent\",\n addSibling: \"Add sibling\",\n removeNode: \"Remove node\",\n focus: \"Focus Mode\",\n cancelFocus: \"Cancel Focus Mode\",\n moveUp: \"Move up\",\n moveDown: \"Move down\",\n link: \"Link\",\n clickTips: \"Please click the target node\",\n summary: \"Summary\"\n },\n ru: {\n addChild: \"Добавить дочерний элемент\",\n addParent: \"Добавить родительский элемент\",\n addSibling: \"Добавить на этом уровне\",\n removeNode: \"Удалить узел\",\n focus: \"Режим фокусировки\",\n cancelFocus: \"Отменить режим фокусировки\",\n moveUp: \"Поднять выше\",\n moveDown: \"Опустить ниже\",\n link: \"Ссылка\",\n clickTips: \"Пожалуйста, нажмите на целевой узел\",\n summary: \"Описание\"\n },\n ja: {\n addChild: \"子ノードを追加する\",\n addParent: \"親ノードを追加します\",\n addSibling: \"兄弟ノードを追加する\",\n removeNode: \"ノードを削除\",\n focus: \"集中\",\n cancelFocus: \"集中解除\",\n moveUp: \"上へ移動\",\n moveDown: \"下へ移動\",\n link: \"コネクト\",\n clickTips: \"ターゲットノードをクリックしてください\",\n summary: \"概要\"\n },\n pt: {\n addChild: \"Adicionar item filho\",\n addParent: \"Adicionar item pai\",\n addSibling: \"Adicionar item irmao\",\n removeNode: \"Remover item\",\n focus: \"Modo Foco\",\n cancelFocus: \"Cancelar Modo Foco\",\n moveUp: \"Mover para cima\",\n moveDown: \"Mover para baixo\",\n link: \"Link\",\n clickTips: \"Favor clicar no item alvo\",\n summary: \"Resumo\"\n }\n};\nfunction mt(e, t) {\n const n = (b) => {\n const x = document.createElement(\"div\");\n return x.innerText = b, x.className = \"tips\", x;\n }, o = (b, x, w) => {\n const _ = document.createElement(\"li\");\n return _.id = b, _.innerHTML = `${ne(x)}${ne(w)}`, _;\n }, i = ge[e.locale] ? e.locale : \"en\", s = ge[i], r = o(\"cm-add_child\", s.addChild, \"tab\"), l = o(\"cm-add_parent\", s.addParent, \"\"), c = o(\"cm-add_sibling\", s.addSibling, \"enter\"), h = o(\"cm-remove_child\", s.removeNode, \"delete\"), a = o(\"cm-fucus\", s.focus, \"\"), u = o(\"cm-unfucus\", s.cancelFocus, \"\"), d = o(\"cm-up\", s.moveUp, \"PgUp\"), p = o(\"cm-down\", s.moveDown, \"Pgdn\"), g = o(\"cm-down\", s.link, \"\"), m = o(\"cm-down\", s.summary, \"\"), f = document.createElement(\"ul\");\n if (f.className = \"menu-list\", f.appendChild(r), f.appendChild(l), f.appendChild(c), f.appendChild(h), (!t || t.focus) && (f.appendChild(a), f.appendChild(u)), f.appendChild(d), f.appendChild(p), f.appendChild(m), (!t || t.link) && f.appendChild(g), t && t.extend)\n for (let b = 0; b < t.extend.length; b++) {\n const x = t.extend[b], w = o(x.name, x.name, x.key || \"\");\n f.appendChild(w), w.onclick = (_) => {\n x.onclick(_);\n };\n }\n const v = document.createElement(\"div\");\n v.className = \"context-menu\", v.appendChild(f), v.hidden = !0, e.container.append(v);\n let y = !0;\n e.container.oncontextmenu = function(b) {\n if (b.preventDefault(), !e.editable)\n return;\n const x = b.target;\n if (ae(x)) {\n x.parentElement.tagName === \"ME-ROOT\" ? y = !0 : y = !1, y ? (a.className = \"disabled\", d.className = \"disabled\", p.className = \"disabled\", l.className = \"disabled\", c.className = \"disabled\", h.className = \"disabled\") : (a.className = \"\", d.className = \"\", p.className = \"\", l.className = \"\", c.className = \"\", h.className = \"\"), e.currentNodes || e.selectNode(x), v.hidden = !1, S.mousedown && (S.mousedown = !1), f.style.top = \"\", f.style.bottom = \"\", f.style.left = \"\", f.style.right = \"\";\n const w = f.getBoundingClientRect(), _ = f.offsetHeight, P = f.offsetWidth, U = b.clientY - w.top, H = b.clientX - w.left;\n _ + U > window.innerHeight ? (f.style.top = \"\", f.style.bottom = \"0px\") : (f.style.bottom = \"\", f.style.top = U + 15 + \"px\"), P + H > window.innerWidth ? (f.style.left = \"\", f.style.right = \"0px\") : (f.style.right = \"\", f.style.left = H + 10 + \"px\");\n }\n }, v.onclick = (b) => {\n b.target === v && (v.hidden = !0);\n }, r.onclick = () => {\n e.addChild(), v.hidden = !0;\n }, l.onclick = () => {\n e.insertParent(), v.hidden = !0;\n }, c.onclick = () => {\n y || (e.insertSibling(), v.hidden = !0);\n }, h.onclick = () => {\n y || (e.removeNode(), v.hidden = !0);\n }, a.onclick = () => {\n y || (e.focusNode(e.currentNode), v.hidden = !0);\n }, u.onclick = () => {\n e.cancelFocus(), v.hidden = !0;\n }, d.onclick = () => {\n y || (e.moveUpNode(), v.hidden = !0);\n }, p.onclick = () => {\n y || (e.moveDownNode(), v.hidden = !0);\n }, g.onclick = () => {\n v.hidden = !0;\n const b = e.currentNode, x = n(s.clickTips);\n e.container.appendChild(x), e.map.addEventListener(\n \"click\",\n (w) => {\n w.preventDefault(), x.remove();\n const _ = w.target;\n _.parentElement.tagName === \"ME-PARENT\" || _.parentElement.tagName === \"ME-ROOT\" ? e.createLink(b, _) : console.log(\"link cancel\");\n },\n {\n once: !0\n }\n );\n }, m.onclick = () => {\n v.hidden = !0, e.createSummary(), e.unselectNodes();\n };\n}\nconst gt = (e) => {\n const t = e.map.querySelectorAll(\".lhs>me-wrapper>me-parent>me-tpc\");\n e.selectNode(t[Math.ceil(t.length / 2) - 1]);\n}, vt = (e) => {\n const t = e.map.querySelectorAll(\".rhs>me-wrapper>me-parent>me-tpc\");\n e.selectNode(t[Math.ceil(t.length / 2) - 1]);\n}, ve = (e) => {\n e.selectNode(e.map.querySelector(\"me-root>me-tpc\"));\n};\nfunction bt(e) {\n const t = {\n 13: (n) => {\n n.shiftKey ? e.insertBefore() : e.insertSibling();\n },\n 9: () => {\n e.addChild();\n },\n 112: () => {\n e.toCenter();\n },\n 113: () => {\n e.beginEdit();\n },\n 38: (n) => {\n if (n.altKey)\n e.moveUpNode();\n else {\n if (n.metaKey || n.ctrlKey)\n return e.initSide();\n e.selectPrevSibling();\n }\n },\n 40: (n) => {\n n.altKey ? e.moveDownNode() : e.selectNextSibling();\n },\n 37: (n) => {\n var s;\n if (n.metaKey || n.ctrlKey)\n return e.initLeft();\n if (!e.currentNode)\n return;\n const o = e.currentNode.nodeObj, i = e.currentNode.offsetParent.offsetParent.parentElement;\n e.currentNode.nodeObj.root ? gt(e) : i.className === \"rhs\" ? (s = o.parent) != null && s.root ? ve(e) : e.selectParent() : i.className === \"lhs\" && e.selectFirstChild();\n },\n 39: (n) => {\n var s;\n if (n.metaKey || n.ctrlKey)\n return e.initRight();\n if (!e.currentNode)\n return;\n const o = e.currentNode.nodeObj, i = e.currentNode.offsetParent.offsetParent.parentElement;\n o.root ? vt(e) : i.className === \"lhs\" ? (s = o.parent) != null && s.root ? ve(e) : e.selectParent() : i.className === \"rhs\" && e.selectFirstChild();\n },\n 33() {\n e.moveUpNode();\n },\n 34() {\n e.moveDownNode();\n },\n 67: (n) => {\n (n.metaKey || n.ctrlKey) && (e.waitCopy = e.currentNode);\n },\n 86: (n) => {\n !e.waitCopy || !e.currentNode || (n.metaKey || n.ctrlKey) && (e.copyNode(e.waitCopy, e.currentNode), e.waitCopy = null);\n },\n // ctrl +\n 187: (n) => {\n if (n.metaKey || n.ctrlKey) {\n if (e.scaleVal > 1.6)\n return;\n e.scale(e.scaleVal += 0.2);\n }\n },\n // ctrl -\n 189: (n) => {\n if (n.metaKey || n.ctrlKey) {\n if (e.scaleVal < 0.6)\n return;\n e.scale(e.scaleVal -= 0.2);\n }\n },\n // ctrl 0\n 48: (n) => {\n (n.metaKey || n.ctrlKey) && e.scale(1);\n }\n };\n e.map.onkeydown = (n) => {\n if (n.preventDefault(), !!e.editable && n.target === n.currentTarget)\n if (n.keyCode === 8 || n.keyCode === 46)\n e.currentLink ? e.removeLink() : e.currentSummary ? e.removeSummary(e.currentSummary.summaryObj.id) : e.currentNode ? e.removeNode() : e.currentNodes && e.removeNodes(e.currentNodes);\n else {\n const o = t[n.keyCode];\n o && o(n);\n }\n };\n}\nfunction yt(e, t) {\n const n = (d, p) => {\n const g = document.createElement(\"div\");\n return g.id = d, g.innerHTML = `\n \n `, g;\n }, o = n(\"cm-add_child\", \"zijiedian\"), i = n(\"cm-add_sibling\", \"tongjijiedian-\"), s = n(\"cm-remove_child\", \"shanchu2\"), r = n(\"cm-up\", \"rising\"), l = n(\"cm-down\", \"falling\"), c = n(\"cm-edit\", \"edit\"), h = document.createElement(\"ul\");\n if (h.className = \"menu-list\", t && t.extend)\n for (let d = 0; d < t.extend.length; d++) {\n const p = t.extend[d], g = n(p.name, p.name);\n h.appendChild(g), g.onclick = (m) => {\n p.onclick(m);\n };\n }\n const a = document.createElement(\"mmenu\");\n a.className = \"mobile-menu\", a.appendChild(o), a.appendChild(i), a.appendChild(s), a.appendChild(r), a.appendChild(l), a.appendChild(c), a.hidden = !0, e.container.append(a);\n let u = !0;\n e.bus.addListener(\"unselectNode\", function() {\n a.hidden = !0;\n }), e.bus.addListener(\"selectNode\", function(d) {\n a.hidden = !1, d.root ? u = !0 : u = !1;\n }), a.onclick = (d) => {\n d.target === a && (a.hidden = !0);\n }, o.onclick = () => {\n e.addChild();\n }, i.onclick = () => {\n u || e.insertSibling();\n }, s.onclick = () => {\n u || e.removeNode();\n }, r.onclick = (d) => {\n u || e.moveUpNode();\n }, l.onclick = (d) => {\n u || e.moveDownNode();\n }, c.onclick = (d) => {\n e.beginEdit();\n };\n}\nconst de = document, xt = function(e, t) {\n if (!t)\n return he(e), e;\n const n = e.getElementsByClassName(\"insert-preview\"), o = `insert-preview ${t} show`;\n if (n.length > 0)\n n[0].className = o;\n else {\n const i = de.createElement(\"div\");\n i.className = o, e.appendChild(i);\n }\n return e;\n}, he = function(e) {\n if (!e)\n return;\n const t = e.getElementsByClassName(\"insert-preview\");\n for (const n of t || [])\n n.remove();\n}, be = function(e, t) {\n const n = t.parentElement.parentElement.contains(e);\n return e && e.tagName === \"ME-TPC\" && e !== t && !n && e.nodeObj.root !== !0;\n}, wt = function(e) {\n const t = document.createElement(\"div\");\n return t.className = \"mind-elixir-ghost\", e.map.appendChild(t), t;\n};\nfunction Et(e) {\n let t = null, n = null, o = null;\n const i = wt(e), s = 12;\n e.map.addEventListener(\"dragstart\", (r) => {\n var c;\n const l = r.target;\n if ((l == null ? void 0 : l.tagName) !== \"ME-TPC\") {\n r.preventDefault();\n return;\n }\n t = l, t.parentElement.parentElement.style.opacity = \"0.5\", i.innerHTML = t.innerHTML, (c = r.dataTransfer) == null || c.setDragImage(i, 0, 0), S.clear();\n }), e.map.addEventListener(\"dragend\", async (r) => {\n if (!t)\n return;\n t.parentElement.parentElement.style.opacity = \"1\";\n const l = r.target;\n if (l.style.opacity = \"\", !o)\n return;\n he(o);\n const c = t.nodeObj;\n switch (n) {\n case \"before\":\n e.moveNodeBefore(t, o), e.selectNode(N(c.id));\n break;\n case \"after\":\n e.moveNodeAfter(t, o), e.selectNode(N(c.id));\n break;\n case \"in\":\n e.moveNode(t, o);\n break;\n }\n t = null;\n }), e.map.addEventListener(\n \"dragover\",\n Ge(function(r) {\n if (!t)\n return;\n he(o);\n const l = de.elementFromPoint(r.clientX, r.clientY - s);\n if (be(l, t)) {\n o = l;\n const c = l.getBoundingClientRect().y;\n r.clientY > c + l.clientHeight ? n = \"after\" : r.clientY > c + l.clientHeight / 2 && (n = \"in\");\n } else {\n const c = de.elementFromPoint(r.clientX, r.clientY + s);\n if (be(c, t)) {\n o = c;\n const h = c.getBoundingClientRect().y;\n r.clientY < h ? n = \"before\" : r.clientY < h + c.clientHeight / 2 && (n = \"in\");\n } else\n n = o = null;\n }\n o && xt(o, n);\n }, 200)\n );\n}\nconst Nt = function(e) {\n return [\"createSummary\", \"removeSummary\", \"finishEditSummary\"].includes(e.name) ? {\n type: \"summary\",\n value: e.obj.id\n } : [\"createCustomLink\", \"removeCustomLink\", \"finishEditCustomLinkLabel\"].includes(e.name) ? {\n type: \"customLink\",\n value: e.obj.id\n } : [\"removeNodes\"].includes(e.name) ? {\n type: \"nodes\",\n value: e.objs.map((t) => t.id)\n } : {\n type: \"node\",\n value: e.obj.id\n };\n};\nfunction Ct(e) {\n let t = [], n = -1, o = e.getData();\n e.bus.addListener(\"operation\", (i) => {\n if (i.name === \"beginEdit\")\n return;\n t = t.slice(0, n + 1);\n const s = e.getData();\n t.push({ prev: o, currentObject: Nt(i), next: s }), o = s, n = t.length - 1;\n }), e.undo = function() {\n if (n > -1) {\n const i = t[n];\n o = i.prev, e.refresh(i.prev), i.currentObject.type === \"node\" && e.selectNode(N(i.currentObject.value)), n--, console.log(\"current\", o);\n }\n }, e.redo = function() {\n if (n < t.length - 1) {\n n++;\n const i = t[n];\n o = i.next, e.refresh(i.next), i.currentObject.type === \"node\" && e.selectNode(N(i.currentObject.value));\n }\n }, e.map.addEventListener(\"keydown\", (i) => {\n (i.metaKey || i.ctrlKey) && i.shiftKey && i.key === \"Z\" ? e.redo() : (i.metaKey || i.ctrlKey) && i.key === \"z\" && e.undo();\n });\n}\nconst R = (e, t) => {\n const n = document.createElement(\"span\");\n return n.id = e, n.innerHTML = `\n \n `, n;\n};\nfunction _t(e) {\n const t = document.createElement(\"div\"), n = R(\"fullscreen\", \"full\"), o = R(\"toCenter\", \"living\"), i = R(\"zoomout\", \"move\"), s = R(\"zoomin\", \"add\"), r = document.createElement(\"span\");\n return r.innerText = \"100%\", t.appendChild(n), t.appendChild(o), t.appendChild(i), t.appendChild(s), t.className = \"mind-elixir-toolbar rb\", n.onclick = () => {\n e.container.requestFullscreen();\n }, o.onclick = () => {\n e.toCenter();\n }, i.onclick = () => {\n e.scaleVal < 0.6 || e.scale(e.scaleVal -= 0.2);\n }, s.onclick = () => {\n e.scaleVal > 1.6 || e.scale(e.scaleVal += 0.2);\n }, t;\n}\nfunction kt(e) {\n const t = document.createElement(\"div\"), n = R(\"tbltl\", \"left\"), o = R(\"tbltr\", \"right\"), i = R(\"tblts\", \"side\");\n return t.appendChild(n), t.appendChild(o), t.appendChild(i), t.className = \"mind-elixir-toolbar lt\", n.onclick = () => {\n e.initLeft();\n }, o.onclick = () => {\n e.initRight();\n }, i.onclick = () => {\n e.initSide();\n }, t;\n}\nfunction St(e) {\n e.container.append(_t(e)), e.container.append(kt(e));\n}\n/*! @viselect/vanilla v3.3.1 MIT | https://github.com/Simonwep/selection/tree/master/packages/vanilla */\nvar Lt = Object.defineProperty, Mt = (e, t, n) => t in e ? Lt(e, t, { enumerable: !0, configurable: !0, writable: !0, value: n }) : e[t] = n, E = (e, t, n) => (Mt(e, typeof t != \"symbol\" ? t + \"\" : t, n), n);\nclass Tt {\n constructor() {\n E(this, \"_listeners\", /* @__PURE__ */ new Map()), E(this, \"on\", this.addEventListener), E(this, \"off\", this.removeEventListener), E(this, \"emit\", this.dispatchEvent);\n }\n addEventListener(t, n) {\n const o = this._listeners.get(t) ?? /* @__PURE__ */ new Set();\n return this._listeners.set(t, o), o.add(n), this;\n }\n removeEventListener(t, n) {\n var o;\n return (o = this._listeners.get(t)) == null || o.delete(n), this;\n }\n dispatchEvent(t, ...n) {\n let o = !0;\n for (const i of this._listeners.get(t) ?? [])\n o = i(...n) !== !1 && o;\n return o;\n }\n unbindAllListeners() {\n this._listeners.clear();\n }\n}\nconst ye = (e, t = \"px\") => typeof e == \"number\" ? e + t : e;\nfunction j({ style: e }, t, n) {\n if (typeof t == \"object\")\n for (const [o, i] of Object.entries(t))\n i !== void 0 && (e[o] = ye(i));\n else\n n !== void 0 && (e[t] = ye(n));\n}\nfunction Be(e) {\n return (t, n, o, i = {}) => {\n t instanceof HTMLCollection || t instanceof NodeList ? t = Array.from(t) : Array.isArray(t) || (t = [t]), Array.isArray(n) || (n = [n]);\n for (const s of t)\n for (const r of n)\n s[e](r, o, { capture: !1, ...i });\n return [t, n, o, i];\n };\n}\nconst V = Be(\"addEventListener\"), O = Be(\"removeEventListener\"), ee = (e) => {\n var t;\n const { clientX: n, clientY: o, target: i } = ((t = e.touches) == null ? void 0 : t[0]) ?? e;\n return { x: n, y: o, target: i };\n};\nfunction xe(e, t, n = \"touch\") {\n switch (n) {\n case \"center\": {\n const o = t.left + t.width / 2, i = t.top + t.height / 2;\n return o >= e.left && o <= e.right && i >= e.top && i <= e.bottom;\n }\n case \"cover\":\n return t.left >= e.left && t.top >= e.top && t.right <= e.right && t.bottom <= e.bottom;\n case \"touch\":\n return e.right >= t.left && e.left <= t.right && e.bottom >= t.top && e.top <= t.bottom;\n }\n}\nfunction W(e, t = document) {\n const n = Array.isArray(e) ? e : [e];\n let o = [];\n for (let i = 0, s = n.length; i < s; i++) {\n const r = n[i];\n typeof r == \"string\" ? o = o.concat(Array.from(t.querySelectorAll(r))) : r instanceof Element && o.push(r);\n }\n return o;\n}\nconst $t = () => matchMedia(\"(hover: none), (pointer: coarse)\").matches, Dt = () => \"safari\" in window, jt = (e) => {\n let t, n = -1, o = !1;\n return {\n next(...i) {\n t = i, o || (o = !0, n = requestAnimationFrame(() => {\n e(...t), o = !1;\n }));\n },\n cancel() {\n cancelAnimationFrame(n), o = !1;\n }\n };\n}, { abs: B, max: we, min: Ee, ceil: Ne } = Math;\nclass ze extends Tt {\n constructor(t) {\n var n, o, i, s, r;\n super(), E(this, \"_options\"), E(this, \"_selection\", {\n stored: [],\n selected: [],\n touched: [],\n changed: {\n added: [],\n // Added elements since last selection\n removed: []\n // Removed elements since last selection\n }\n }), E(this, \"_area\"), E(this, \"_clippingElement\"), E(this, \"_targetElement\"), E(this, \"_targetRect\"), E(this, \"_selectables\", []), E(this, \"_latestElement\"), E(this, \"_areaRect\", new DOMRect()), E(this, \"_areaLocation\", { y1: 0, x2: 0, y2: 0, x1: 0 }), E(this, \"_singleClick\", !0), E(this, \"_frame\"), E(this, \"_scrollAvailable\", !0), E(this, \"_scrollingActive\", !1), E(this, \"_scrollSpeed\", { x: 0, y: 0 }), E(this, \"_scrollDelta\", { x: 0, y: 0 }), E(this, \"disable\", this._bindStartEvents.bind(this, !1)), E(this, \"enable\", this._bindStartEvents), this._options = {\n selectionAreaClass: \"selection-area\",\n selectionContainerClass: void 0,\n selectables: [],\n document: window.document,\n startAreas: [\"html\"],\n boundaries: [\"html\"],\n container: \"body\",\n ...t,\n behaviour: {\n overlap: \"invert\",\n intersect: \"touch\",\n ...t.behaviour,\n startThreshold: (n = t.behaviour) != null && n.startThreshold ? typeof t.behaviour.startThreshold == \"number\" ? t.behaviour.startThreshold : { x: 10, y: 10, ...t.behaviour.startThreshold } : { x: 10, y: 10 },\n scrolling: {\n speedDivider: 10,\n manualSpeed: 750,\n ...(o = t.behaviour) == null ? void 0 : o.scrolling,\n startScrollMargins: {\n x: 0,\n y: 0,\n ...(s = (i = t.behaviour) == null ? void 0 : i.scrolling) == null ? void 0 : s.startScrollMargins\n }\n }\n },\n features: {\n range: !0,\n touch: !0,\n ...t.features,\n singleTap: {\n allow: !0,\n intersect: \"native\",\n ...(r = t.features) == null ? void 0 : r.singleTap\n }\n }\n };\n for (const a of Object.getOwnPropertyNames(Object.getPrototypeOf(this)))\n typeof this[a] == \"function\" && (this[a] = this[a].bind(this));\n const { document: l, selectionAreaClass: c, selectionContainerClass: h } = this._options;\n this._area = l.createElement(\"div\"), this._clippingElement = l.createElement(\"div\"), this._clippingElement.appendChild(this._area), this._area.classList.add(c), h && this._clippingElement.classList.add(h), j(this._area, {\n willChange: \"top, left, bottom, right, width, height\",\n top: 0,\n left: 0,\n position: \"fixed\"\n }), j(this._clippingElement, {\n overflow: \"hidden\",\n position: \"fixed\",\n transform: \"translate3d(0, 0, 0)\",\n // https://stackoverflow.com/a/38268846\n pointerEvents: \"none\",\n zIndex: \"1\"\n }), this._frame = jt((a) => {\n this._recalculateSelectionAreaRect(), this._updateElementSelection(), this._emitEvent(\"move\", a), this._redrawSelectionArea();\n }), this.enable();\n }\n _bindStartEvents(t = !0) {\n const { document: n, features: o } = this._options, i = t ? V : O;\n i(n, \"mousedown\", this._onTapStart), o.touch && i(n, \"touchstart\", this._onTapStart, {\n passive: !1\n });\n }\n _onTapStart(t, n = !1) {\n const { x: o, y: i, target: s } = ee(t), { _options: r } = this, { document: l } = this._options, c = s.getBoundingClientRect(), h = W(r.startAreas, r.document), a = W(r.boundaries, r.document);\n this._targetElement = a.find(\n (p) => xe(p.getBoundingClientRect(), c)\n );\n const u = t.composedPath();\n if (!this._targetElement || !h.find((p) => u.includes(p)) || !a.find((p) => u.includes(p)) || !n && this._emitEvent(\"beforestart\", t) === !1)\n return;\n this._areaLocation = { x1: o, y1: i, x2: 0, y2: 0 };\n const d = l.scrollingElement ?? l.body;\n this._scrollDelta = { x: d.scrollLeft, y: d.scrollTop }, this._singleClick = !0, this.clearSelection(!1, !0), V(l, [\"touchmove\", \"mousemove\"], this._delayedTapMove, { passive: !1 }), V(l, [\"mouseup\", \"touchcancel\", \"touchend\"], this._onTapStop), V(l, \"scroll\", this._onScroll);\n }\n _onSingleTap(t) {\n const { singleTap: { intersect: n }, range: o } = this._options.features, i = ee(t);\n let s;\n if (n === \"native\")\n s = i.target;\n else if (n === \"touch\") {\n this.resolveSelectables();\n const { x: l, y: c } = i;\n s = this._selectables.find((h) => {\n const { right: a, left: u, top: d, bottom: p } = h.getBoundingClientRect();\n return l < a && l > u && c < p && c > d;\n });\n }\n if (!s)\n return;\n for (this.resolveSelectables(); !this._selectables.includes(s); ) {\n if (!s.parentElement)\n return;\n s = s.parentElement;\n }\n const { stored: r } = this._selection;\n if (this._emitEvent(\"start\", t), t.shiftKey && o && this._latestElement) {\n const l = this._latestElement, [c, h] = l.compareDocumentPosition(s) & 4 ? [s, l] : [l, s], a = [...this._selectables.filter(\n (u) => u.compareDocumentPosition(c) & 4 && u.compareDocumentPosition(h) & 2\n ), c, h];\n this.select(a), this._latestElement = l;\n } else\n r.includes(s) && (r.length === 1 || t.ctrlKey || r.every((l) => this._selection.stored.includes(l))) ? this.deselect(s) : (this.select(s), this._latestElement = s);\n this._emitEvent(\"stop\", t);\n }\n _delayedTapMove(t) {\n const { container: n, document: o, behaviour: { startThreshold: i } } = this._options, { x1: s, y1: r } = this._areaLocation, { x: l, y: c } = ee(t);\n if (\n // Single number for both coordinates\n typeof i == \"number\" && B(l + c - (s + r)) >= i || // Different x and y threshold\n typeof i == \"object\" && B(l - s) >= i.x || B(c - r) >= i.y\n ) {\n if (O(o, [\"mousemove\", \"touchmove\"], this._delayedTapMove, { passive: !1 }), this._emitEvent(\"beforedrag\", t) === !1) {\n O(o, [\"mouseup\", \"touchcancel\", \"touchend\"], this._onTapStop);\n return;\n }\n V(o, [\"mousemove\", \"touchmove\"], this._onTapMove, { passive: !1 }), j(this._area, \"display\", \"block\"), W(n, o)[0].appendChild(this._clippingElement), this.resolveSelectables(), this._singleClick = !1, this._targetRect = this._targetElement.getBoundingClientRect(), this._scrollAvailable = this._targetElement.scrollHeight !== this._targetElement.clientHeight || this._targetElement.scrollWidth !== this._targetElement.clientWidth, this._scrollAvailable && (V(o, \"wheel\", this._manualScroll, { passive: !1 }), this._selectables = this._selectables.filter((h) => this._targetElement.contains(h))), this._setupSelectionArea(), this._emitEvent(\"start\", t), this._onTapMove(t);\n }\n this._handleMoveEvent(t);\n }\n _setupSelectionArea() {\n const { _clippingElement: t, _targetElement: n, _area: o } = this, i = this._targetRect = n.getBoundingClientRect();\n this._scrollAvailable ? (j(t, {\n top: i.top,\n left: i.left,\n width: i.width,\n height: i.height\n }), j(o, {\n marginTop: -i.top,\n marginLeft: -i.left\n })) : (j(t, {\n top: 0,\n left: 0,\n width: \"100%\",\n height: \"100%\"\n }), j(o, {\n marginTop: 0,\n marginLeft: 0\n }));\n }\n _onTapMove(t) {\n const { x: n, y: o } = ee(t), { _scrollSpeed: i, _areaLocation: s, _options: r, _frame: l } = this, { speedDivider: c } = r.behaviour.scrolling, h = this._targetElement;\n if (s.x2 = n, s.y2 = o, this._scrollAvailable && !this._scrollingActive && (i.y || i.x)) {\n this._scrollingActive = !0;\n const a = () => {\n if (!i.x && !i.y) {\n this._scrollingActive = !1;\n return;\n }\n const { scrollTop: u, scrollLeft: d } = h;\n i.y && (h.scrollTop += Ne(i.y / c), s.y1 -= h.scrollTop - u), i.x && (h.scrollLeft += Ne(i.x / c), s.x1 -= h.scrollLeft - d), l.next(t), requestAnimationFrame(a);\n };\n requestAnimationFrame(a);\n } else\n l.next(t);\n this._handleMoveEvent(t);\n }\n _handleMoveEvent(t) {\n const { features: n } = this._options;\n (n.touch && $t() || this._scrollAvailable && Dt()) && t.preventDefault();\n }\n _onScroll() {\n const { _scrollDelta: t, _options: { document: n } } = this, { scrollTop: o, scrollLeft: i } = n.scrollingElement ?? n.body;\n this._areaLocation.x1 += t.x - i, this._areaLocation.y1 += t.y - o, t.x = i, t.y = o, this._setupSelectionArea(), this._frame.next(null);\n }\n _manualScroll(t) {\n const { manualSpeed: n } = this._options.behaviour.scrolling, o = t.deltaY ? t.deltaY > 0 ? 1 : -1 : 0, i = t.deltaX ? t.deltaX > 0 ? 1 : -1 : 0;\n this._scrollSpeed.y += o * n, this._scrollSpeed.x += i * n, this._onTapMove(t), t.preventDefault();\n }\n _recalculateSelectionAreaRect() {\n const { _scrollSpeed: t, _areaLocation: n, _areaRect: o, _targetElement: i, _options: s } = this, { scrollTop: r, scrollHeight: l, clientHeight: c, scrollLeft: h, scrollWidth: a, clientWidth: u } = i, d = this._targetRect, { x1: p, y1: g } = n;\n let { x2: m, y2: f } = n;\n const { behaviour: { scrolling: { startScrollMargins: v } } } = s;\n m < d.left + v.x ? (t.x = h ? -B(d.left - m + v.x) : 0, m = m < d.left ? d.left : m) : m > d.right - v.x ? (t.x = a - h - u ? B(d.left + d.width - m - v.x) : 0, m = m > d.right ? d.right : m) : t.x = 0, f < d.top + v.y ? (t.y = r ? -B(d.top - f + v.y) : 0, f = f < d.top ? d.top : f) : f > d.bottom - v.y ? (t.y = l - r - c ? B(d.top + d.height - f - v.y) : 0, f = f > d.bottom ? d.bottom : f) : t.y = 0;\n const y = Ee(p, m), b = Ee(g, f), x = we(p, m), w = we(g, f);\n o.x = y, o.y = b, o.width = x - y, o.height = w - b;\n }\n _redrawSelectionArea() {\n const { x: t, y: n, width: o, height: i } = this._areaRect, { style: s } = this._area;\n s.left = `${t}px`, s.top = `${n}px`, s.width = `${o}px`, s.height = `${i}px`;\n }\n _onTapStop(t, n) {\n var o;\n const { document: i, features: s } = this._options, { _singleClick: r } = this;\n O(i, [\"mousemove\", \"touchmove\"], this._delayedTapMove), O(i, [\"touchmove\", \"mousemove\"], this._onTapMove), O(i, [\"mouseup\", \"touchcancel\", \"touchend\"], this._onTapStop), O(i, \"scroll\", this._onScroll), this._keepSelection(), t && r && s.singleTap.allow ? this._onSingleTap(t) : !r && !n && (this._updateElementSelection(), this._emitEvent(\"stop\", t)), this._scrollSpeed.x = 0, this._scrollSpeed.y = 0, this._scrollAvailable && O(i, \"wheel\", this._manualScroll, { passive: !0 }), this._clippingElement.remove(), (o = this._frame) == null || o.cancel(), j(this._area, \"display\", \"none\");\n }\n _updateElementSelection() {\n const { _selectables: t, _options: n, _selection: o, _areaRect: i } = this, { stored: s, selected: r, touched: l } = o, { intersect: c, overlap: h } = n.behaviour, a = h === \"invert\", u = [], d = [], p = [];\n for (let m = 0; m < t.length; m++) {\n const f = t[m];\n if (xe(i, f.getBoundingClientRect(), c)) {\n if (r.includes(f))\n s.includes(f) && !l.includes(f) && l.push(f);\n else if (a && s.includes(f)) {\n p.push(f);\n continue;\n } else\n d.push(f);\n u.push(f);\n }\n }\n a && d.push(...s.filter((m) => !r.includes(m)));\n const g = h === \"keep\";\n for (let m = 0; m < r.length; m++) {\n const f = r[m];\n !u.includes(f) && !// Check if user wants to keep previously selected elements, e.g.\n // not make them part of the current selection as soon as they're touched.\n (g && s.includes(f)) && p.push(f);\n }\n o.selected = u, o.changed = { added: d, removed: p }, this._latestElement = void 0;\n }\n _emitEvent(t, n) {\n return this.emit(t, {\n event: n,\n store: this._selection,\n selection: this\n });\n }\n _keepSelection() {\n const { _options: t, _selection: n } = this, { selected: o, changed: i, touched: s, stored: r } = n, l = o.filter((c) => !r.includes(c));\n switch (t.behaviour.overlap) {\n case \"drop\": {\n n.stored = [\n ...l,\n ...r.filter((c) => !s.includes(c))\n // Elements not touched\n ];\n break;\n }\n case \"invert\": {\n n.stored = [\n ...l,\n ...r.filter((c) => !i.removed.includes(c))\n // Elements not removed from selection\n ];\n break;\n }\n case \"keep\": {\n n.stored = [\n ...r,\n ...o.filter((c) => !r.includes(c))\n // Newly added\n ];\n break;\n }\n }\n }\n /**\n * Manually triggers the start of a selection\n * @param evt A MouseEvent / TouchEvent -like object\n * @param silent If beforestart should be fired,\n */\n trigger(t, n = !0) {\n this._onTapStart(t, n);\n }\n /**\n * Can be used if during a selection elements have been added.\n * Will update everything which can be selected.\n */\n resolveSelectables() {\n this._selectables = W(this._options.selectables, this._options.document);\n }\n /**\n * Same as deselect, but for all elements currently selected.\n * @param includeStored If the store should also get cleared\n * @param quiet If move / stop events should be fired\n */\n clearSelection(t = !0, n = !1) {\n const { selected: o, stored: i, changed: s } = this._selection;\n s.added = [], s.removed.push(\n ...o,\n ...t ? i : []\n ), n || (this._emitEvent(\"move\", null), this._emitEvent(\"stop\", null)), this._selection = {\n stored: t ? [] : i,\n selected: [],\n touched: [],\n changed: { added: [], removed: [] }\n };\n }\n /**\n * @returns {Array} Selected elements\n */\n getSelection() {\n return this._selection.stored;\n }\n /**\n * @returns {HTMLElement} The selection area element\n */\n getSelectionArea() {\n return this._area;\n }\n /**\n * Cancel the current selection process.\n * @param keepEvent {boolean} true to fire a stop event after cancel.\n */\n cancel(t = !1) {\n this._onTapStop(null, !t);\n }\n /**\n * Unbinds all events and removes the area-element.\n */\n destroy() {\n this.cancel(), this.disable(), this._clippingElement.remove(), super.unbindAllListeners();\n }\n /**\n * Adds elements to the selection\n * @param query - CSS Query, can be an array of queries\n * @param quiet - If this should not trigger the move event\n */\n select(t, n = !1) {\n const { changed: o, selected: i, stored: s } = this._selection, r = W(t, this._options.document).filter(\n (l) => !i.includes(l) && !s.includes(l)\n );\n return s.push(...r), i.push(...r), o.added.push(...r), o.removed = [], this._latestElement = void 0, n || (this._emitEvent(\"move\", null), this._emitEvent(\"stop\", null)), r;\n }\n /**\n * Removes a particular element from the selection.\n * @param query - CSS Query, can be an array of queries\n * @param quiet - If this should not trigger the move event\n */\n deselect(t, n = !1) {\n const { selected: o, stored: i, changed: s } = this._selection, r = W(t, this._options.document).filter(\n (l) => o.includes(l) || i.includes(l)\n );\n r.length && (this._selection.stored = i.filter((l) => !r.includes(l)), this._selection.selected = o.filter((l) => !r.includes(l)), this._selection.changed.added = [], this._selection.changed.removed.push(\n ...r.filter((l) => !s.removed.includes(l))\n ), this._latestElement = void 0, n || (this._emitEvent(\"move\", null), this._emitEvent(\"stop\", null)));\n }\n}\nE(ze, \"version\", \"3.3.1\");\nfunction Ot(e) {\n const t = new ze({\n selectables: [\".map-container me-tpc\"],\n boundaries: [e.container],\n container: \"body\",\n behaviour: {\n // Scroll configuration.\n scrolling: {\n // On scrollable areas the number on px per frame is devided by this amount.\n // Default is 10 to provide a enjoyable scroll experience.\n speedDivider: 10,\n // Browsers handle mouse-wheel events differently, this number will be used as\n // numerator to calculate the mount of px while scrolling manually: manualScrollSpeed / scrollSpeedDivider.\n manualSpeed: 750,\n // This property defines the virtual inset margins from the borders of the container\n // component that, when crossed by the mouse/touch, trigger the scrolling. Useful for\n // fullscreen containers.\n startScrollMargins: { x: 10, y: 10 }\n }\n }\n }).on(\"beforestart\", ({ event: n }) => {\n if (n.button !== e.mouseSelectionButton || n.target.tagName === \"ME-TPC\" || n.target.id === \"input-box\" || n.target.className === \"circle\")\n return !1;\n const o = t.getSelectionArea();\n return o.style.background = \"#4f90f22d\", o.style.border = \"1px solid #4f90f2\", o.parentElement && (o.parentElement.style.zIndex = \"9999\"), !0;\n }).on(\"start\", ({ event: n }) => {\n !n.ctrlKey && !n.metaKey && (e.unselectNode(), e.unselectNodes(), e.unselectSummary(), e.unselectLink(), t.clearSelection(!0, !0));\n }).on(\n \"move\",\n ({\n store: {\n changed: { added: n, removed: o }\n }\n }) => {\n S.moved = !0;\n for (const i of n)\n i.classList.add(\"selected\");\n for (const i of o)\n i.classList.remove(\"selected\");\n }\n ).on(\"stop\", ({ store: { stored: n } }) => {\n e.selectNodes(n);\n });\n e.selection = t;\n}\nconst At = function(e, t = !0) {\n this.theme = e;\n const n = this.theme.cssVar, o = Object.keys(n);\n for (let i = 0; i < o.length; i++) {\n const s = o[i];\n this.mindElixirBox.style.setProperty(s, n[s]);\n }\n t && this.refresh();\n};\nfunction Re(e) {\n return {\n nodeData: e.isFocusMode ? e.nodeDataBackup : e.nodeData,\n linkData: e.linkData,\n summaries: e.summaries,\n direction: e.direction,\n theme: e.theme\n };\n}\nconst Pt = function(e, t, n) {\n if (e) {\n if (console.time(\"selectNode\"), typeof e == \"string\") {\n const o = N(e);\n return o ? this.selectNode(o) : void 0;\n }\n this.currentNode && (this.currentNode.className = \"\"), e.className = \"selected\", e.scrollIntoView({ block: \"nearest\", inline: \"nearest\" }), this.currentNode = e, t ? this.bus.fire(\"selectNewNode\", e.nodeObj) : this.bus.fire(\"selectNode\", e.nodeObj, n), console.timeEnd(\"selectNode\");\n }\n}, Ht = function() {\n this.currentNode && (this.currentNode.className = \"\"), this.currentNode = null, this.bus.fire(\"unselectNode\");\n}, Bt = function(e) {\n if (e) {\n console.time(\"selectNodes\");\n for (const t of e)\n t.className = \"selected\";\n this.currentNodes = e, this.bus.fire(\n \"selectNodes\",\n e.map((t) => t.nodeObj)\n ), console.timeEnd(\"selectNodes\");\n }\n}, zt = function() {\n if (this.currentNodes)\n for (const e of this.currentNodes)\n e.classList.remove(\"selected\");\n this.currentNodes = null, this.bus.fire(\"unselectNodes\");\n}, Rt = function() {\n if (!this.currentNode || this.currentNode.dataset.nodeid === \"meroot\")\n return !1;\n const e = this.currentNode.parentElement.parentElement.nextSibling;\n let t;\n if (e)\n t = e.firstChild.firstChild;\n else\n return !1;\n return this.selectNode(t), !0;\n}, qt = function() {\n if (!this.currentNode || this.currentNode.dataset.nodeid === \"meroot\")\n return !1;\n const e = this.currentNode.parentElement.parentElement.previousSibling;\n let t;\n if (e)\n t = e.firstChild.firstChild;\n else\n return !1;\n return this.selectNode(t), !0;\n}, Ft = function() {\n if (!this.currentNode)\n return;\n const e = this.currentNode.parentElement.nextSibling;\n if (e && e.firstChild) {\n const t = e.firstChild.firstChild.firstChild;\n this.selectNode(t);\n }\n}, Vt = function() {\n if (!this.currentNode || this.currentNode.dataset.nodeid === \"meroot\")\n return;\n const e = this.currentNode.parentElement.parentElement.parentElement.previousSibling;\n if (e) {\n const t = e.firstChild;\n this.selectNode(t);\n }\n}, Wt = function() {\n const e = Re(this);\n return JSON.stringify(e, (t, n) => {\n if (!(t === \"parent\" && typeof n != \"string\"))\n return n;\n });\n}, It = function() {\n return JSON.parse(this.getDataString());\n}, Kt = function() {\n const e = Re(this).nodeData;\n let t = \"# \" + e.topic + `\n\n`;\n function n(o, i) {\n for (let s = 0; s < o.length; s++)\n i <= 6 ? t += \"\".padStart(i, \"#\") + \" \" + o[s].topic + `\n\n` : t += \"\".padStart(i - 7, \"\t\") + \"- \" + o[s].topic + `\n`, o[s].children && n(o[s].children || [], i + 1);\n }\n return n(e.children || [], 2), t;\n}, Ut = function() {\n this.editable = !0;\n}, Yt = function() {\n this.editable = !1;\n}, Gt = function(e) {\n this.scaleVal = e, this.map.style.transform = \"scale(\" + e + \")\";\n}, Xt = function() {\n this.container.scrollTo(1e4 - this.container.offsetWidth / 2, 1e4 - this.container.offsetHeight / 2);\n}, Jt = function(e) {\n e(this);\n}, Qt = function(e) {\n e.nodeObj.root || (this.tempDirection === null && (this.tempDirection = this.direction), this.isFocusMode || (this.nodeDataBackup = this.nodeData, this.isFocusMode = !0), this.nodeData = e.nodeObj, this.nodeData.root = !0, this.initRight(), this.toCenter());\n}, Zt = function() {\n this.isFocusMode = !1, this.tempDirection !== null && (delete this.nodeData.root, this.nodeData = this.nodeDataBackup, this.direction = this.tempDirection, this.tempDirection = null, this.refresh(), this.toCenter());\n}, en = function() {\n this.direction = 0, this.refresh();\n}, tn = function() {\n this.direction = 1, this.refresh();\n}, nn = function() {\n this.direction = 2, this.refresh();\n}, on = function(e) {\n this.locale = e, this.refresh();\n}, sn = function(e, t) {\n const n = e.nodeObj;\n typeof t == \"boolean\" ? n.expanded = t : n.expanded !== !1 ? n.expanded = !1 : n.expanded = !0, this.layout(), this.linkDiv(), this.bus.fire(\"expandNode\", n);\n}, rn = function(e) {\n e && (e = JSON.parse(JSON.stringify(e)), this.nodeData = e.nodeData, this.linkData = e.linkData || {}, this.summaries = e.summaries || []), $(this.nodeData), this.layout(), this.linkDiv();\n}, ln = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({\n __proto__: null,\n cancelFocus: Zt,\n disableEdit: Yt,\n enableEdit: Ut,\n expandNode: sn,\n focusNode: Qt,\n getData: It,\n getDataMd: Kt,\n getDataString: Wt,\n initLeft: en,\n initRight: tn,\n initSide: nn,\n install: Jt,\n refresh: rn,\n scale: Gt,\n selectFirstChild: Ft,\n selectNextSibling: Rt,\n selectNode: Pt,\n selectNodes: Bt,\n selectParent: Vt,\n selectPrevSibling: qt,\n setLocale: on,\n toCenter: Xt,\n unselectNode: Ht,\n unselectNodes: zt\n}, Symbol.toStringTag, { value: \"Module\" })), A = (e) => {\n var o;\n const t = (o = e.parent) == null ? void 0 : o.children, n = t.indexOf(e);\n return { siblings: t, index: n };\n};\nfunction cn(e) {\n const { siblings: t, index: n } = A(e), o = t[n];\n n === 0 ? (t[n] = t[t.length - 1], t[t.length - 1] = o) : (t[n] = t[n - 1], t[n - 1] = o);\n}\nfunction an(e) {\n const { siblings: t, index: n } = A(e), o = t[n];\n n === t.length - 1 ? (t[n] = t[0], t[0] = o) : (t[n] = t[n + 1], t[n + 1] = o);\n}\nfunction Q(e) {\n const { siblings: t, index: n } = A(e);\n return t.splice(n, 1), t.length;\n}\nfunction dn(e, t) {\n const { siblings: n, index: o } = A(e);\n n.splice(o + 1, 0, t);\n}\nfunction hn(e, t) {\n const { siblings: n, index: o } = A(e);\n n.splice(o, 0, t);\n}\nfunction un(e, t) {\n const { siblings: n, index: o } = A(e);\n n[o] = t, t.children = [e];\n}\nfunction fn(e, t) {\n Q(e), t.children ? t.children.push(e) : t.children = [e];\n}\nfunction pn(e, t) {\n e.direction !== void 0 && (e.direction = t.direction), Q(e);\n const { siblings: n, index: o } = A(t);\n n.splice(o, 0, e);\n}\nfunction mn(e, t) {\n e.direction !== void 0 && (e.direction = t.direction), Q(e);\n const { siblings: n, index: o } = A(t);\n n.splice(o + 1, 0, e);\n}\nconst qe = function(e, t) {\n var n, o;\n if (e === L)\n return L;\n if (e === z)\n return z;\n if (e === X) {\n const i = ((n = document.querySelector(\".lhs\")) == null ? void 0 : n.childElementCount) || 0, s = ((o = document.querySelector(\".rhs\")) == null ? void 0 : o.childElementCount) || 0;\n return i <= s ? (t.direction = L, L) : (t.direction = z, z);\n }\n}, Fe = function(e, t) {\n var l, c;\n if (!e)\n return null;\n const n = e.nodeObj;\n n.expanded === !1 && (this.expandNode(e, !0), e = N(n.id));\n const o = t || this.generateNewObj();\n n.children ? n.children.push(o) : n.children = [o], $(this.nodeData);\n const i = e.parentElement, { grp: s, top: r } = this.createWrapper(o);\n if (i.tagName === \"ME-PARENT\") {\n if (i.children[1])\n i.nextSibling.appendChild(s);\n else {\n const h = this.createChildren([s]);\n i.appendChild(re(!0)), i.insertAdjacentElement(\"afterend\", h);\n }\n this.linkDiv(s.offsetParent);\n } else\n i.tagName === \"ME-ROOT\" && (qe(this.direction, o) === L ? (l = document.querySelector(\".lhs\")) == null || l.appendChild(s) : (c = document.querySelector(\".rhs\")) == null || c.appendChild(s), this.linkDiv());\n return { newTop: r, newNodeObj: o };\n}, Ve = function(e, t) {\n const n = e.parentNode;\n if (t === 0) {\n const o = n.parentNode.parentNode;\n o.tagName !== \"ME-MAIN\" && o.previousSibling.children[1].remove();\n }\n n.parentNode.remove();\n}, le = function(e) {\n const n = e.parentElement.parentElement.lastElementChild;\n (n == null ? void 0 : n.tagName) === \"svg\" && (n == null || n.remove());\n}, gn = function(e, t) {\n console.log(t);\n const n = e.nodeObj, o = De(n);\n o.style && t.style && (t.style = Object.assign(o.style, t.style));\n const i = Object.assign(n, t);\n ue(e, i), this.linkDiv(), this.bus.fire(\"operation\", {\n name: \"reshapeNode\",\n obj: i,\n origin: o\n });\n}, vn = function(e, t) {\n var h, a, u;\n const n = e || this.currentNode;\n if (!n)\n return;\n const o = n.nodeObj;\n if (o.root === !0) {\n this.addChild();\n return;\n } else if (((h = o.parent) == null ? void 0 : h.root) === !0 && ((u = (a = o.parent) == null ? void 0 : a.children) == null ? void 0 : u.length) === 1) {\n this.addChild(N(o.parent.id));\n return;\n }\n const i = t || this.generateNewObj();\n dn(o, i), $(this.nodeData);\n const s = n.parentElement;\n console.time(\"insertSibling_DOM\");\n const { grp: r, top: l } = this.createWrapper(i);\n s.parentNode.parentNode.insertBefore(r, s.parentNode.nextSibling), this.linkDiv(r.offsetParent), t || this.editTopic(l.firstChild), this.selectNode(l.firstChild, !0), console.timeEnd(\"insertSibling_DOM\"), this.bus.fire(\"operation\", {\n name: \"insertSibling\",\n obj: i\n });\n}, bn = function(e, t) {\n const n = e || this.currentNode;\n if (!n)\n return;\n const o = n.nodeObj;\n if (o.root === !0) {\n this.addChild();\n return;\n }\n const i = t || this.generateNewObj();\n hn(o, i), $(this.nodeData);\n const s = n.parentElement;\n console.time(\"insertSibling_DOM\");\n const { grp: r, top: l } = this.createWrapper(i);\n s.parentNode.parentNode.insertBefore(r, s.parentNode), this.linkDiv(r.offsetParent), t || this.editTopic(l.firstChild), this.selectNode(l.firstChild, !0), console.timeEnd(\"insertSibling_DOM\"), this.bus.fire(\"operation\", {\n name: \"insertBefore\",\n obj: i\n });\n}, yn = function(e, t) {\n const n = e || this.currentNode;\n if (!n)\n return;\n le(n);\n const o = n.nodeObj;\n if (o.root === !0)\n return;\n const i = t || this.generateNewObj();\n un(o, i), $(this.nodeData);\n const s = n.parentElement.parentElement;\n console.time(\"insertParent_DOM\");\n const { grp: r, top: l } = this.createWrapper(i, !0);\n l.appendChild(re(!0)), s.insertAdjacentElement(\"afterend\", r);\n const c = this.createChildren([s]);\n l.insertAdjacentElement(\"afterend\", c), this.linkDiv(), t || this.editTopic(l.firstChild), this.selectNode(l.firstChild, !0), console.timeEnd(\"insertParent_DOM\"), this.bus.fire(\"operation\", {\n name: \"insertParent\",\n obj: i\n });\n}, xn = function(e, t) {\n console.time(\"addChild\");\n const n = e || this.currentNode;\n if (!n)\n return;\n const o = Fe.call(this, n, t);\n if (!o)\n return;\n const { newTop: i, newNodeObj: s } = o;\n this.bus.fire(\"operation\", {\n name: \"addChild\",\n obj: s\n }), console.timeEnd(\"addChild\"), t || this.editTopic(i.firstChild), this.selectNode(i.firstChild, !0);\n}, wn = function(e, t) {\n console.time(\"copyNode\");\n const n = De(e.nodeObj);\n Te(n);\n const o = Fe.call(this, t, n);\n if (!o)\n return;\n const { newNodeObj: i } = o;\n console.timeEnd(\"copyNode\"), this.bus.fire(\"operation\", {\n name: \"copyNode\",\n obj: i\n });\n}, En = function(e) {\n const t = e || this.currentNode;\n if (!t)\n return;\n const n = t.nodeObj;\n cn(n);\n const o = t.parentNode.parentNode;\n o.parentNode.insertBefore(o, o.previousSibling), this.linkDiv(), this.bus.fire(\"operation\", {\n name: \"moveUpNode\",\n obj: n\n });\n}, Nn = function(e) {\n const t = e || this.currentNode;\n if (!t)\n return;\n const n = t.nodeObj;\n an(n);\n const o = t.parentNode.parentNode;\n o.nextSibling ? o.nextSibling.insertAdjacentElement(\"afterend\", o) : o.parentNode.prepend(o), this.linkDiv(), this.bus.fire(\"operation\", {\n name: \"moveDownNode\",\n obj: n\n });\n}, Cn = function(e) {\n var r;\n const t = e || this.currentNode;\n if (!t)\n return;\n const n = t.nodeObj;\n if (n.root === !0)\n throw new Error(\"Can not remove root node\");\n const o = n.parent.children, i = o.findIndex((l) => l === n), s = Q(n);\n if (Ve(t, s), o.length !== 0) {\n const l = o[i] || o[i - 1];\n this.selectNode(N(l.id));\n } else\n this.selectNode(N(n.parent.id));\n this.linkDiv(), this.bus.fire(\"operation\", {\n name: \"removeNode\",\n obj: n,\n originIndex: i,\n originParentId: (r = n == null ? void 0 : n.parent) == null ? void 0 : r.id\n });\n}, _n = function(e) {\n for (const t of e) {\n const n = t.nodeObj;\n if (n.root === !0)\n continue;\n const o = Q(n);\n Ve(t, o);\n }\n this.linkDiv(), this.bus.fire(\"operation\", {\n name: \"removeNodes\",\n objs: e.map((t) => t.nodeObj)\n });\n}, kn = function(e, t) {\n var l;\n const n = e.nodeObj, o = t.nodeObj, i = (l = n == null ? void 0 : n.parent) == null ? void 0 : l.id;\n if (o.expanded === !1 && (this.expandNode(t, !0), e = N(n.id), t = N(o.id)), !Je(n, o)) {\n console.warn(\"Invalid move\");\n return;\n }\n console.time(\"moveNode\"), fn(n, o), $(this.nodeData);\n const s = e.parentElement, r = t.parentElement;\n if (r.tagName === \"ME-PARENT\")\n if (le(e), r.children[1])\n r.nextSibling.appendChild(s.parentElement);\n else {\n const c = this.createChildren([s.parentElement]);\n r.appendChild(re(!0)), r.parentElement.insertBefore(c, r.nextSibling);\n }\n else\n r.tagName === \"ME-ROOT\" && (qe(this.direction, n), r.nextSibling.appendChild(s.parentElement));\n this.linkDiv(), this.bus.fire(\"operation\", {\n name: \"moveNode\",\n obj: n,\n toObj: o,\n originParentId: i\n }), console.timeEnd(\"moveNode\");\n}, Sn = function(e, t) {\n var l;\n const n = e.nodeObj, o = t.nodeObj, i = (l = n.parent) == null ? void 0 : l.id;\n pn(n, o), $(this.nodeData), le(e);\n const s = e.parentElement.parentNode;\n t.parentElement.parentNode.insertAdjacentElement(\"beforebegin\", s), this.linkDiv(), this.bus.fire(\"operation\", {\n name: \"moveNodeBefore\",\n obj: n,\n toObj: o,\n originParentId: i\n });\n}, Ln = function(e, t) {\n var l;\n const n = e.nodeObj, o = t.nodeObj, i = (l = n.parent) == null ? void 0 : l.id;\n mn(n, o), $(this.nodeData), le(e);\n const s = e.parentElement.parentNode;\n t.parentElement.parentNode.insertAdjacentElement(\"afterend\", s), this.linkDiv(), this.bus.fire(\"operation\", {\n name: \"moveNodeAfter\",\n obj: n,\n toObj: o,\n originParentId: i\n });\n}, Mn = function(e) {\n const t = e || this.currentNode;\n t && this.editTopic(t);\n}, Tn = function(e, t) {\n e.text.textContent = t, e.nodeObj.topic = t, this.linkDiv();\n}, We = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({\n __proto__: null,\n addChild: xn,\n beginEdit: Mn,\n copyNode: wn,\n insertBefore: bn,\n insertParent: yn,\n insertSibling: vn,\n moveDownNode: Nn,\n moveNode: kn,\n moveNodeAfter: Ln,\n moveNodeBefore: Sn,\n moveUpNode: En,\n removeNode: Cn,\n removeNodes: _n,\n reshapeNode: gn,\n setNodeTopic: Tn\n}, Symbol.toStringTag, { value: \"Module\" })), $n = function(e) {\n return {\n dom: e,\n moved: !1,\n // diffrentiate click and move\n mousedown: !1,\n handleMouseMove(t) {\n this.mousedown && (this.moved = !0, this.cb && this.cb(t.movementX, t.movementY));\n },\n handleMouseDown(t) {\n t.button === 0 && (this.mousedown = !0);\n },\n handleClear(t) {\n this.mousedown = !1;\n },\n cb: null,\n init(t, n) {\n this.cb = n, this.handleClear = this.handleClear.bind(this), this.handleMouseMove = this.handleMouseMove.bind(this), this.handleMouseDown = this.handleMouseDown.bind(this), t.addEventListener(\"mousemove\", this.handleMouseMove), t.addEventListener(\"mouseleave\", this.handleClear), t.addEventListener(\"mouseup\", this.handleClear), this.dom.addEventListener(\"mousedown\", this.handleMouseDown);\n },\n destory(t) {\n t.removeEventListener(\"mousemove\", this.handleMouseMove), t.removeEventListener(\"mouseleave\", this.handleClear), t.removeEventListener(\"mouseup\", this.handleClear), this.dom.removeEventListener(\"mousedown\", this.handleMouseDown);\n },\n clear() {\n this.moved = !1, this.mousedown = !1;\n }\n };\n}, Ce = {\n create: $n\n};\nfunction se(e, t, n) {\n const { offsetLeft: o, offsetTop: i } = K(e.nodes, t), s = t.offsetWidth, r = t.offsetHeight, l = o + s / 2, c = i + r / 2, h = l + n.x, a = c + n.y;\n return {\n w: s,\n h: r,\n cx: l,\n cy: c,\n ctrlX: h,\n ctrlY: a\n };\n}\nfunction I(e) {\n let t, n;\n const o = (e.cy - e.ctrlY) / (e.ctrlX - e.cx);\n return o > e.h / e.w || o < -e.h / e.w ? e.cy - e.ctrlY < 0 ? (t = e.cx - e.h / 2 / o, n = e.cy + e.h / 2) : (t = e.cx + e.h / 2 / o, n = e.cy - e.h / 2) : e.cx - e.ctrlX < 0 ? (t = e.cx + e.w / 2, n = e.cy - e.w * o / 2) : (t = e.cx - e.w / 2, n = e.cy + e.w * o / 2), {\n x: t,\n y: n\n };\n}\nconst Dn = function(e, t, n, o) {\n const i = document.createElementNS(\"http://www.w3.org/2000/svg\", \"text\");\n return C(i, {\n \"text-anchor\": \"middle\",\n x: t + \"\",\n y: n + \"\",\n fill: o || \"#666\"\n }), i.dataset.type = \"custom-link\", i.innerHTML = e, i;\n}, jn = function(e, t, n, o) {\n if (!e || !t)\n return;\n const i = performance.now(), s = se(this, e, n.delta1), r = se(this, t, n.delta2), { x: l, y: c } = I(s), { ctrlX: h, ctrlY: a } = s, { ctrlX: u, ctrlY: d } = r, { x: p, y: g } = I(r), m = $e(u, d, p, g), f = dt(\n `M ${l} ${c} C ${h} ${a} ${u} ${d} ${p} ${g}`,\n `M ${m.x1} ${m.y1} L ${p} ${g} L ${m.x2} ${m.y2}`\n ), v = l / 8 + h * 3 / 8 + u * 3 / 8 + p / 8, y = c / 8 + a * 3 / 8 + d * 3 / 8 + g / 8, b = Dn(n.label, v, y, this.theme.cssVar[\"--color\"]);\n f.appendChild(b), f.linkObj = n, f.dataset.linkid = n.id, this.linkSvgGroup.appendChild(f), o || (this.linkData[n.id] = n, this.currentLink = f, this.showLinkController(n, s, r));\n const x = performance.now();\n console.log(`DrawCustomLink Execution time: ${x - i} ms`);\n}, On = function(e, t) {\n const n = {\n id: J(),\n label: \"Custom Link\",\n from: e.nodeObj.id,\n to: t.nodeObj.id,\n delta1: {\n x: 0,\n y: -200\n },\n delta2: {\n x: 0,\n y: -200\n }\n };\n this.drawCustomLink(e, t, n), this.bus.fire(\"operation\", {\n name: \"createCustomLink\",\n obj: n\n });\n}, An = function(e) {\n let t;\n if (e ? t = e : t = this.currentLink, !t)\n return;\n this.hideLinkController();\n const n = t.linkObj.id;\n delete this.linkData[n], t.remove(), this.bus.fire(\"operation\", {\n name: \"removeCustomLink\",\n obj: {\n id: n\n }\n });\n}, Pn = function(e) {\n this.currentLink = e;\n const t = e.linkObj, n = N(t.from), o = N(t.to), i = se(this, n, t.delta1), s = se(this, o, t.delta2);\n this.showLinkController(t, i, s);\n}, Hn = function() {\n this.currentLink = null, this.hideLinkController();\n}, Bn = function() {\n this.linkController.style.display = \"none\", this.P2.style.display = \"none\", this.P3.style.display = \"none\";\n}, zn = function(e, t, n) {\n var u;\n this.linkController.style.display = \"initial\", this.P2.style.display = \"initial\", this.P3.style.display = \"initial\", this.nodes.appendChild(this.linkController), this.nodes.appendChild(this.P2), this.nodes.appendChild(this.P3);\n let { x: o, y: i } = I(t), { ctrlX: s, ctrlY: r } = t, { ctrlX: l, ctrlY: c } = n, { x: h, y: a } = I(n);\n this.P2.style.cssText = `top:${r}px;left:${s}px;`, this.P3.style.cssText = `top:${c}px;left:${l}px;`, C(this.line1, {\n x1: o + \"\",\n y1: i + \"\",\n x2: s + \"\",\n y2: r + \"\"\n }), C(this.line2, {\n x1: l + \"\",\n y1: c + \"\",\n x2: h + \"\",\n y2: a + \"\"\n }), this.helper1 && (this.helper1.destory(this.map), (u = this.helper2) == null || u.destory(this.map)), this.helper1 = Ce.create(this.P2), this.helper2 = Ce.create(this.P3), this.helper1.init(this.map, (d, p) => {\n var v;\n s = s + d / this.scaleVal, r = r + p / this.scaleVal;\n const g = I({ ...t, ctrlX: s, ctrlY: r });\n o = g.x, i = g.y;\n const m = o / 8 + s * 3 / 8 + l * 3 / 8 + h / 8, f = i / 8 + r * 3 / 8 + c * 3 / 8 + a / 8;\n this.P2.style.top = r + \"px\", this.P2.style.left = s + \"px\", (v = this.currentLink) == null || v.children[0].setAttribute(\"d\", `M ${o} ${i} C ${s} ${r} ${l} ${c} ${h} ${a}`), C(this.currentLink.children[2], {\n x: m + \"\",\n y: f + \"\"\n }), C(this.line1, {\n x1: o + \"\",\n y1: i + \"\",\n x2: s + \"\",\n y2: r + \"\"\n }), e.delta1.x = s - t.cx, e.delta1.y = r - t.cy;\n }), this.helper2.init(this.map, (d, p) => {\n var y, b;\n l = l + d / this.scaleVal, c = c + p / this.scaleVal;\n const g = I({ ...n, ctrlX: l, ctrlY: c });\n h = g.x, a = g.y;\n const m = o / 8 + s * 3 / 8 + l * 3 / 8 + h / 8, f = i / 8 + r * 3 / 8 + c * 3 / 8 + a / 8, v = $e(l, c, h, a);\n this.P3.style.top = c + \"px\", this.P3.style.left = l + \"px\", (y = this.currentLink) == null || y.children[0].setAttribute(\"d\", `M ${o} ${i} C ${s} ${r} ${l} ${c} ${h} ${a}`), (b = this.currentLink) == null || b.children[1].setAttribute(\"d\", `M ${v.x1} ${v.y1} L ${h} ${a} L ${v.x2} ${v.y2}`), C(this.currentLink.children[2], {\n x: m + \"\",\n y: f + \"\"\n }), C(this.line2, {\n x1: l + \"\",\n y1: c + \"\",\n x2: h + \"\",\n y2: a + \"\"\n }), e.delta2.x = l - n.cx, e.delta2.y = c - n.cy;\n });\n};\nfunction Rn() {\n this.linkSvgGroup.innerHTML = \"\";\n for (const e in this.linkData) {\n const t = this.linkData[e];\n try {\n this.drawCustomLink(N(t.from), N(t.to), t, !0);\n } catch {\n console.warn(\"Node may not be expanded\");\n }\n }\n this.nodes.appendChild(this.linkSvgGroup);\n}\nfunction qn(e) {\n if (console.time(\"editSummary\"), !e)\n return;\n const t = e.children[2];\n console.log(t, e), Oe(this, t, (n) => {\n var s;\n const o = e.linkObj, i = ((s = n.textContent) == null ? void 0 : s.trim()) || \"\";\n i === \"\" ? o.label = origin : o.label = i, n.remove(), i !== origin && (t.innerHTML = o.label, this.linkDiv(), this.bus.fire(\"operation\", {\n name: \"finishEditCustomLinkLabel\",\n obj: o\n }));\n }), console.timeEnd(\"editSummary\");\n}\nfunction Fn() {\n for (const e in this.linkData) {\n const t = this.linkData[e];\n (!oe(t.from, this.nodeData) || !oe(t.to, this.nodeData)) && delete this.linkData[t.id];\n }\n}\nconst Vn = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({\n __proto__: null,\n createLink: On,\n drawCustomLink: jn,\n editCutsomLinkLabel: qn,\n hideLinkController: Bn,\n removeLink: An,\n renderCustomLink: Rn,\n selectLink: Pn,\n showLinkController: zn,\n tidyCustomLink: Fn,\n unselectLink: Hn\n}, Symbol.toStringTag, { value: \"Module\" })), Wn = function(e) {\n var c, h;\n if (e.length === 0)\n throw new Error(\"No selected node.\");\n if (e.length === 1) {\n const a = e[0].nodeObj, u = e[0].nodeObj.parent;\n if (!u)\n throw new Error(\"Can not select root node.\");\n const d = u.children.findIndex((p) => a === p);\n return {\n parent: u.id,\n start: d,\n end: d\n };\n }\n let t = 0;\n const n = e.map((a) => {\n let u = a.nodeObj;\n const d = [];\n for (; u.parent; ) {\n const p = u.parent, g = p.children, m = g == null ? void 0 : g.indexOf(u);\n u = p, d.unshift({ node: u, index: m });\n }\n return d.length > t && (t = d.length), d;\n });\n let o = 0;\n e:\n for (; o < t; o++) {\n const a = (c = n[0][o]) == null ? void 0 : c.node;\n for (let u = 1; u < n.length; u++)\n if (((h = n[u][o]) == null ? void 0 : h.node) !== a)\n break e;\n }\n if (!o)\n throw new Error(\"Can not select root node.\");\n const i = n.map((a) => a[o - 1].index).sort(), s = i[0] || 0, r = i[i.length - 1] || 0, l = n[0][o - 1].node;\n if (l.root)\n throw new Error(\"Please select nodes in the same main topic.\");\n return {\n parent: l.id,\n start: s,\n end: r\n };\n}, In = function(e) {\n const t = document.createElementNS(\"http://www.w3.org/2000/svg\", \"g\");\n return t.setAttribute(\"id\", e), t;\n}, _e = function(e, t) {\n const n = document.createElementNS(\"http://www.w3.org/2000/svg\", \"path\");\n return C(n, {\n d: e,\n stroke: t || \"#666\",\n fill: \"none\",\n \"stroke-linecap\": \"round\",\n \"stroke-width\": \"2\"\n }), n;\n}, ke = function(e, t, n, o, i) {\n const s = document.createElementNS(\"http://www.w3.org/2000/svg\", \"text\");\n return C(s, {\n \"text-anchor\": o,\n x: t + \"\",\n y: n + \"\",\n fill: i || \"#666\"\n }), s.innerHTML = e, s;\n}, Kn = (e) => N(e).parentElement.parentElement, Un = function({ parent: e, start: t }) {\n var s, r;\n const n = N(e), o = n.nodeObj;\n let i;\n return o.root === !0 ? i = (s = N(o.children[t].id).closest(\"me-main\")) == null ? void 0 : s.className : i = (r = n.closest(\"me-main\")) == null ? void 0 : r.className, i;\n}, Ie = function(e, t) {\n var _;\n const { id: n, text: o, parent: i, start: s, end: r } = t, l = e.nodes, h = N(i).nodeObj, a = Un(t);\n let u = 1 / 0, d = 0, p = 0, g = 0;\n for (let P = s; P <= r; P++) {\n const U = (_ = h.children) == null ? void 0 : _[P];\n if (!U)\n return console.warn(\"Child not found\"), e.removeSummary(n), null;\n const H = Kn(U.id), { offsetLeft: Z, offsetTop: fe } = K(l, H);\n P === s && (p = fe), P === r && (g = fe + H.offsetHeight), Z < u && (u = Z), H.offsetWidth + Z > d && (d = H.offsetWidth + Z);\n }\n let m, f;\n const v = p + 10, y = g + 10, b = (v + y) / 2, x = e.theme.cssVar[\"--color\"];\n a === \"lhs\" ? (m = _e(`M ${u + 10} ${v} c -5 0 -10 5 -10 10 L ${u} ${y - 10} c 0 5 5 10 10 10 M ${u} ${b} h -10`, x), f = ke(o, u - 20, b + 6, \"end\", x)) : (m = _e(`M ${d - 10} ${v} c 5 0 10 5 10 10 L ${d} ${y - 10} c 0 5 -5 10 -10 10 M ${d} ${b} h 10`, x), f = ke(o, d + 20, b + 6, \"start\", x));\n const w = In(\"s-\" + n);\n return w.appendChild(m), w.appendChild(f), w.summaryObj = t, e.summarySvg.appendChild(w), w;\n}, Yn = function() {\n let e = [];\n this.currentNode ? e = [this.currentNode] : this.currentNodes && (e = this.currentNodes);\n const { parent: t, start: n, end: o } = Wn(e), i = { id: J(), parent: t, start: n, end: o, text: \"summary\" }, s = Ie(this, i);\n this.summaries.push(i), this.editSummary(s), this.bus.fire(\"operation\", {\n name: \"createSummary\",\n obj: i\n });\n}, Gn = function(e) {\n var n;\n const t = this.summaries.findIndex((o) => o.id === e);\n t > -1 && (this.summaries.splice(t, 1), (n = document.querySelector(\"#s-\" + e)) == null || n.remove()), this.bus.fire(\"operation\", {\n name: \"removeSummary\",\n obj: { id: e }\n });\n}, Xn = function(e) {\n const t = e.children[1].getBBox(), n = 6, o = 3, i = document.createElementNS(\"http://www.w3.org/2000/svg\", \"rect\");\n C(i, {\n x: t.x - n + \"\",\n y: t.y - n + \"\",\n width: t.width + n * 2 + \"\",\n height: t.height + n * 2 + \"\",\n rx: o + \"\",\n stroke: this.theme.cssVar[\"--selected\"] || \"#4dc4ff\",\n \"stroke-width\": \"2\",\n fill: \"none\"\n }), i.classList.add(\"selected\"), e.appendChild(i), this.currentSummary = e;\n}, Jn = function() {\n var e, t;\n (t = (e = this.currentSummary) == null ? void 0 : e.querySelector(\"rect\")) == null || t.remove(), this.currentSummary = null;\n}, Qn = function() {\n this.summarySvg.innerHTML = \"\", this.summaries.forEach((e) => {\n try {\n Ie(this, e);\n } catch {\n console.warn(\"Node may not be expanded\");\n }\n }), this.nodes.insertAdjacentElement(\"beforeend\", this.summarySvg);\n}, Zn = function(e) {\n if (console.time(\"editSummary\"), !e)\n return;\n const t = e.childNodes[1];\n Oe(this, t, (n) => {\n var s;\n const o = e.summaryObj, i = ((s = n.textContent) == null ? void 0 : s.trim()) || \"\";\n i === \"\" ? o.text = origin : o.text = i, n.remove(), i !== origin && (t.innerHTML = o.text, this.linkDiv(), this.bus.fire(\"operation\", {\n name: \"finishEditSummary\",\n obj: o\n }));\n }), console.timeEnd(\"editSummary\");\n}, eo = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({\n __proto__: null,\n createSummary: Yn,\n editSummary: Zn,\n removeSummary: Gn,\n renderSummary: Qn,\n selectSummary: Xn,\n unselectSummary: Jn\n}, Symbol.toStringTag, { value: \"Module\" }));\nfunction to(e, t) {\n const n = document.createElementNS(\"http://www.w3.org/2000/svg\", \"svg\");\n return C(n, {\n version: \"1.1\",\n xmlns: \"http://www.w3.org/2000/svg\",\n height: e,\n width: t\n }), n;\n}\nfunction no(e, t) {\n return (parseInt(e) - parseInt(t)) / 2;\n}\nfunction oo(e, t, n, o) {\n const i = document.createElementNS(\"http://www.w3.org/2000/svg\", \"g\");\n let s = \"\";\n return e.text ? s = e.text.textContent : s = e.childNodes[0].textContent, s.split(`\n`).forEach((l, c) => {\n const h = document.createElementNS(\"http://www.w3.org/2000/svg\", \"text\");\n C(h, {\n x: n + parseInt(t.paddingLeft) + \"\",\n y: o + parseInt(t.paddingTop) + no(t.lineHeight, t.fontSize) * (c + 1) + parseFloat(t.fontSize) * (c + 1) + \"\",\n \"text-anchor\": \"start\",\n \"font-family\": t.fontFamily,\n \"font-size\": `${t.fontSize}`,\n \"font-weight\": `${t.fontWeight}`,\n fill: `${t.color}`\n }), h.innerHTML = l, i.appendChild(h);\n }), i;\n}\nfunction io(e, t, n, o) {\n let i = \"\";\n e.text ? i = e.text.textContent : i = e.childNodes[0].textContent;\n const s = document.createElementNS(\"http://www.w3.org/2000/svg\", \"foreignObject\");\n C(s, {\n x: n + parseInt(t.paddingLeft) + \"\",\n y: o + parseInt(t.paddingTop) + \"\",\n width: t.width,\n height: t.height\n });\n const r = document.createElement(\"div\");\n return C(r, {\n xmlns: \"http://www.w3.org/1999/xhtml\",\n style: `font-family: ${t.fontFamily}; font-size: ${t.fontSize}; font-weight: ${t.fontWeight}; color: ${t.color}; white-space: pre-wrap;`\n }), r.innerHTML = i, s.appendChild(r), s;\n}\nfunction ce(e, t, n = !1) {\n const o = getComputedStyle(t), { offsetLeft: i, offsetTop: s } = K(e.nodes, t), r = document.createElementNS(\"http://www.w3.org/2000/svg\", \"rect\");\n C(r, {\n x: i + \"\",\n y: s + \"\",\n rx: o.borderRadius,\n ry: o.borderRadius,\n width: o.width,\n height: o.height,\n fill: o.backgroundColor,\n stroke: o.borderColor,\n \"stroke-width\": o.borderWidth\n });\n const l = document.createElementNS(\"http://www.w3.org/2000/svg\", \"g\");\n l.appendChild(r);\n let c;\n return n ? c = io(t, o, i, s) : c = oo(t, o, i, s), l.appendChild(c), l;\n}\nfunction so(e, t) {\n const n = getComputedStyle(t), { offsetLeft: o, offsetTop: i } = K(e.nodes, t), s = document.createElementNS(\"http://www.w3.org/2000/svg\", \"a\"), r = document.createElementNS(\"http://www.w3.org/2000/svg\", \"text\");\n return C(r, {\n x: o + \"\",\n y: i + parseInt(n.fontSize) + \"\",\n \"text-anchor\": \"start\",\n \"font-family\": n.fontFamily,\n \"font-size\": `${n.fontSize}`,\n \"font-weight\": `${n.fontWeight}`,\n fill: `${n.color}`\n }), r.innerHTML = t.textContent, s.appendChild(r), s.setAttribute(\"href\", t.href), s;\n}\nconst te = 100, ro = '', Ke = (e, t = !1) => {\n var u, d, p;\n const n = e.nodes, o = n.offsetHeight + te * 2, i = n.offsetWidth + te * 2, s = to(o + \"px\", i + \"px\"), r = document.createElementNS(\"http://www.w3.org/2000/svg\", \"svg\"), l = document.createElementNS(\"http://www.w3.org/2000/svg\", \"rect\");\n C(l, {\n x: \"0\",\n y: \"0\",\n width: `${i}`,\n height: `${o}`,\n fill: e.theme.cssVar[\"--bgcolor\"]\n }), s.appendChild(l), n.querySelectorAll(\".subLines\").forEach((g) => {\n const m = g.cloneNode(!0), { offsetLeft: f, offsetTop: v } = K(n, g.parentElement);\n m.setAttribute(\"x\", `${f}`), m.setAttribute(\"y\", `${v}`), r.appendChild(m);\n });\n const c = (u = n.querySelector(\".lines\")) == null ? void 0 : u.cloneNode(!0);\n c && r.appendChild(c);\n const h = (d = n.querySelector(\".topiclinks\")) == null ? void 0 : d.cloneNode(!0);\n h && r.appendChild(h);\n const a = (p = n.querySelector(\".summary\")) == null ? void 0 : p.cloneNode(!0);\n return a && r.appendChild(a), n.querySelectorAll(\"me-tpc\").forEach((g) => {\n r.appendChild(ce(e, g, !t));\n }), n.querySelectorAll(\".tags > span\").forEach((g) => {\n r.appendChild(ce(e, g));\n }), n.querySelectorAll(\".icons > span\").forEach((g) => {\n r.appendChild(ce(e, g));\n }), n.querySelectorAll(\".hyper-link\").forEach((g) => {\n r.appendChild(so(e, g));\n }), C(r, {\n x: te + \"\",\n y: te + \"\",\n overflow: \"visible\"\n }), s.appendChild(r), ro + s.outerHTML;\n};\nfunction lo(e) {\n return new Promise((t, n) => {\n const o = new FileReader();\n o.onload = (i) => {\n t(i.target.result);\n }, o.onerror = (i) => {\n n(i);\n }, o.readAsDataURL(e);\n });\n}\nconst co = function(e = !1) {\n const t = Ke(this, e);\n return new Blob([t], { type: \"image/svg+xml\" });\n}, ao = async function(e = !1) {\n const t = Ke(this, e), n = new Blob([t], { type: \"image/svg+xml\" }), o = await lo(n);\n return new Promise((i, s) => {\n const r = new Image();\n r.setAttribute(\"crossOrigin\", \"anonymous\"), r.onload = () => {\n const l = document.createElement(\"canvas\");\n l.width = r.width, l.height = r.height, l.getContext(\"2d\").drawImage(r, 0, 0), l.toBlob(i, \"image/png\", 1);\n }, r.src = o, r.onerror = s;\n });\n}, ho = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({\n __proto__: null,\n exportPng: ao,\n exportSvg: co\n}, Symbol.toStringTag, { value: \"Module\" }));\nfunction uo(e, t) {\n return async function(...n) {\n const o = this.before[t];\n o && !await o.apply(this, n) || e.apply(this, n);\n };\n}\nconst Se = Object.keys(We), Ue = {};\nfor (let e = 0; e < Se.length; e++) {\n const t = Se[e];\n Ue[t] = uo(We[t], t);\n}\nconst fo = {\n getObjById: oe,\n generateNewObj: Xe,\n layout: et,\n linkDiv: ht,\n editTopic: lt,\n createWrapper: ot,\n createParent: it,\n createChildren: st,\n createTopic: rt,\n findEle: N,\n changeTheme: At,\n ...ln,\n ...Ue,\n ...Vn,\n ...eo,\n ...ho,\n init(e) {\n if (!e || !e.nodeData)\n return new Error(\"MindElixir: `data` is required\");\n e.direction !== void 0 && (this.direction = e.direction), this.changeTheme(e.theme || this.theme, !1), this.nodeData = e.nodeData, $(this.nodeData), this.linkData = e.linkData || {}, this.summaries = e.summaries || [], this.tidyCustomLink(), this.toolBar && St(this), this.keypress && bt(this), this.editable && Ot(this), Ye() && this.mobileMenu ? yt(this) : this.contextMenu && mt(this, this.contextMenuOption), this.draggable && Et(this), this.allowUndo && Ct(this), this.toCenter(), this.layout(), this.linkDiv();\n }\n}, Y = document;\nfunction D({\n el: e,\n direction: t,\n locale: n,\n draggable: o,\n editable: i,\n contextMenu: s,\n contextMenuOption: r,\n toolBar: l,\n keypress: c,\n mouseSelectionButton: h,\n before: a,\n newTopicName: u,\n allowUndo: d,\n mainLinkStyle: p,\n subLinkStyle: g,\n overflowHidden: m,\n mobileMenu: f,\n theme: v\n}) {\n console.log(\"ME_version \" + D.version, this);\n let y = null;\n const b = Object.prototype.toString.call(e);\n if (b === \"[object HTMLDivElement]\" ? y = e : b === \"[object String]\" && (y = document.querySelector(e)), !y)\n throw new Error(\"MindElixir: el is not a valid element\");\n y.className += \" mind-elixir\", y.innerHTML = \"\", y.style.setProperty(\"--gap\", T + \"px\"), this.mindElixirBox = y, this.before = a || {}, this.locale = n || \"en\", this.contextMenuOption = r, this.contextMenu = s === void 0 ? !0 : s, this.toolBar = l === void 0 ? !0 : l, this.keypress = c === void 0 ? !0 : c, this.mouseSelectionButton = h || 0, this.mobileMenu = f || !1, this.direction = typeof t == \"number\" ? t : 1, this.draggable = o === void 0 ? !0 : o, this.newTopicName = u || \"new node\", this.editable = i === void 0 ? !0 : i, this.allowUndo = d === void 0 ? !1 : d, this.currentNode = null, this.currentLink = null, this.scaleVal = 1, this.tempDirection = null, this.mainLinkStyle = p || 0, this.subLinkStyle = g || 0, this.overflowHidden = m || !1, this.bus = Ze.create(), this.container = Y.createElement(\"div\"), this.container.className = \"map-container\";\n const x = window.matchMedia(\"(prefers-color-scheme: dark)\");\n this.theme = v || (x.matches ? Me : Le);\n const w = Y.createElement(\"div\");\n w.className = \"map-canvas\", this.map = w, this.map.setAttribute(\"tabindex\", \"0\"), this.container.appendChild(this.map), this.mindElixirBox.appendChild(this.container), this.nodes = Y.createElement(\"me-nodes\"), this.nodes.className = \"main-node-container\", this.lines = G(\"lines\"), this.summarySvg = G(\"summary\"), this.linkController = G(\"linkcontroller\"), this.P2 = Y.createElement(\"div\"), this.P3 = Y.createElement(\"div\"), this.P2.className = this.P3.className = \"circle\", this.P2.style.display = this.P3.style.display = \"none\", this.line1 = pe(), this.line2 = pe(), this.linkController.appendChild(this.line1), this.linkController.appendChild(this.line2), this.linkSvgGroup = G(\"topiclinks\"), this.map.appendChild(this.nodes), this.overflowHidden ? this.container.style.overflow = \"hidden\" : Qe(this);\n}\nD.prototype = fo;\nD.LEFT = L;\nD.RIGHT = z;\nD.SIDE = X;\nD.THEME = Le;\nD.DARK_THEME = Me;\nD.version = \"3.3.2\";\nD.E = N;\nD.new = (e) => ({\n nodeData: {\n id: J(),\n topic: e || \"new topic\",\n root: !0,\n children: []\n },\n linkData: {}\n});\nexport {\n D as default\n};\n"], - "mappings": "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", - "names": [] -} diff --git a/frontend/node_modules/.vite/deps/prismjs.js b/frontend/node_modules/.vite/deps/prismjs.js new file mode 100644 index 0000000..9635fe0 --- /dev/null +++ b/frontend/node_modules/.vite/deps/prismjs.js @@ -0,0 +1,1466 @@ +import { + __commonJS +} from "./chunk-FOSKEDPS.js"; + +// node_modules/prismjs/prism.js +var require_prism = __commonJS({ + "node_modules/prismjs/prism.js"(exports, module) { + var _self = typeof window !== "undefined" ? window : typeof WorkerGlobalScope !== "undefined" && self instanceof WorkerGlobalScope ? self : {}; + var Prism = function(_self2) { + var lang = /(?:^|\s)lang(?:uage)?-([\w-]+)(?=\s|$)/i; + var uniqueId = 0; + var plainTextGrammar = {}; + var _ = { + /** + * By default, Prism will attempt to highlight all code elements (by calling {@link Prism.highlightAll}) on the + * current page after the page finished loading. This might be a problem if e.g. you wanted to asynchronously load + * additional languages or plugins yourself. + * + * By setting this value to `true`, Prism will not automatically highlight all code elements on the page. + * + * You obviously have to change this value before the automatic highlighting started. To do this, you can add an + * empty Prism object into the global scope before loading the Prism script like this: + * + * ```js + * window.Prism = window.Prism || {}; + * Prism.manual = true; + * // add a new ', + 'B', + '', +].join(''); + +export const mixedText = '
1TEXT2'; diff --git a/frontend/node_modules/cheerio/src/__tests__/deprecated.spec.ts b/frontend/node_modules/cheerio/src/__tests__/deprecated.spec.ts new file mode 100644 index 0000000..493b8c7 --- /dev/null +++ b/frontend/node_modules/cheerio/src/__tests__/deprecated.spec.ts @@ -0,0 +1,266 @@ +/** + * This file includes tests for deprecated APIs. The methods are expected to be + * removed in the next major release of Cheerio, but their stability should be + * maintained until that time. + */ +import { describe, it, expect, beforeEach } from 'vitest'; +import { cheerio, food, fruits } from '../__fixtures__/fixtures.js'; + +describe('deprecated APIs', () => { + describe('cheerio module', () => { + describe('.parseHTML', () => { + it('(html) : should preserve content', () => { + const html = '
test div
'; + expect(cheerio(cheerio.parseHTML(html)[0]).html()).toBe('test div'); + }); + }); + + describe('.merge', () => { + it('should be a function', () => { + expect(typeof cheerio.merge).toBe('function'); + }); + + // #1674 - merge, wont accept Cheerio object + it('should be a able merge array and cheerio object', () => { + const ret = cheerio.merge(cheerio(), ['elem1', 'elem2']); + expect(typeof ret).toBe('object'); + expect(ret).toHaveLength(2); + }); + + it('(arraylike, arraylike) : should modify the first array, but not the second', () => { + const arr1 = [1, 2, 3]; + const arr2 = [4, 5, 6]; + const ret = cheerio.merge(arr1, arr2); + + expect(typeof ret).toBe('object'); + expect(Array.isArray(ret)).toBe(true); + expect(ret).toBe(arr1); + expect(arr1).toHaveLength(6); + expect(arr2).toHaveLength(3); + }); + + it('(arraylike, arraylike) : should handle objects that arent arrays, but are arraylike', () => { + const arr1: ArrayLike = { + length: 3, + 0: 'a', + 1: 'b', + 2: 'c', + }; + const arr2 = { + length: 3, + 0: 'd', + 1: 'e', + 2: 'f', + }; + + cheerio.merge(arr1, arr2); + expect(arr1).toHaveLength(6); + expect(arr1[3]).toBe('d'); + expect(arr1[4]).toBe('e'); + expect(arr1[5]).toBe('f'); + expect(arr2).toHaveLength(3); + }); + + it('(?, ?) : should gracefully reject invalid inputs', () => { + expect(cheerio.merge([4], 3 as never)).toBeUndefined(); + expect(cheerio.merge({} as never, {} as never)).toBeUndefined(); + expect(cheerio.merge([], {} as never)).toBeUndefined(); + expect(cheerio.merge({} as never, [])).toBeUndefined(); + + const fakeArray = { length: 3, 0: 'a', 1: 'b', 3: 'd' }; + expect(cheerio.merge(fakeArray, [])).toBeUndefined(); + expect(cheerio.merge([], fakeArray)).toBeUndefined(); + + expect(cheerio.merge({ length: '7' } as never, [])).toBeUndefined(); + expect(cheerio.merge({ length: -1 }, [])).toBeUndefined(); + }); + + it('(?, ?) : should no-op on invalid inputs', () => { + const fakeArray1 = { length: 3, 0: 'a', 1: 'b', 3: 'd' }; + cheerio.merge(fakeArray1, []); + expect(fakeArray1).toHaveLength(3); + expect(fakeArray1[0]).toBe('a'); + expect(fakeArray1[1]).toBe('b'); + expect(fakeArray1[3]).toBe('d'); + cheerio.merge([], fakeArray1); + expect(fakeArray1).toHaveLength(3); + expect(fakeArray1[0]).toBe('a'); + expect(fakeArray1[1]).toBe('b'); + expect(fakeArray1[3]).toBe('d'); + }); + }); + + describe('.contains', () => { + let $: typeof cheerio; + + beforeEach(() => { + $ = cheerio.load(food); + }); + + it('(container, contained) : should correctly detect the provided element', () => { + const $food = $('#food'); + const $fruits = $('#fruits'); + const $apple = $('.apple'); + + expect(cheerio.contains($food[0], $fruits[0])).toBe(true); + expect(cheerio.contains($food[0], $apple[0])).toBe(true); + }); + + it('(container, other) : should not detect elements that are not contained', () => { + const $fruits = $('#fruits'); + const $vegetables = $('#vegetables'); + const $apple = $('.apple'); + + expect(cheerio.contains($vegetables[0], $apple[0])).toBe(false); + expect(cheerio.contains($fruits[0], $vegetables[0])).toBe(false); + expect(cheerio.contains($vegetables[0], $fruits[0])).toBe(false); + expect(cheerio.contains($fruits[0], $fruits[0])).toBe(false); + expect(cheerio.contains($vegetables[0], $vegetables[0])).toBe(false); + }); + }); + + describe('.root', () => { + it('returns an empty selection', () => { + const $empty = cheerio.root(); + expect($empty).toHaveLength(1); + expect($empty[0].children).toHaveLength(0); + }); + }); + }); + + describe('Cheerio function', () => { + it('.load', () => { + const $1 = cheerio.load(fruits); + const $2 = $1.load('

Some text.

'); + + expect($2('a')).toHaveLength(1); + }); + + /** + * The `.html` static method defined on the "loaded" Cheerio factory + * function is deprecated. + * + * In order to promote consistency with the jQuery library, users are + * encouraged to instead use the instance method of the same name. + * + * @example + * + * ```js + * const $ = cheerio.load('

Hello, world.

'); + * + * $('h1').html(); + * //=> '

Hello, world.' + * ``` + * + * @example To render the markup of an entire document, invoke the + * `html` function exported by the Cheerio module with a "root" + * selection. + * + * ```js + * cheerio.html($.root()); + * //=> '

Hello, world.

' + * ``` + */ + describe('.html - deprecated API', () => { + it('() : of empty cheerio object should return null', () => { + /* + * Note: the direct invocation of the Cheerio constructor function is + * also deprecated. + */ + const $ = cheerio(); + expect($.html()).toBe(null); + }); + + it('(selector) : should return the outerHTML of the selected element', () => { + const $ = cheerio.load(fruits); + expect($.html('.pear')).toBe('
  • Pear
  • '); + }); + }); + + /** + * The `.xml` static method defined on the "loaded" Cheerio factory function + * is deprecated. Users are encouraged to instead use the `xml` function + * exported by the Cheerio module. + * + * @example + * + * ```js + * cheerio.xml($.root()); + * ``` + */ + describe('.xml - deprecated API', () => { + it('() : renders XML', () => { + const $ = cheerio.load('', { xmlMode: true }); + expect($.xml()).toBe(''); + }); + }); + + /** + * The `.text` static method defined on the "loaded" Cheerio factory + * function is deprecated. + * + * In order to promote consistency with the jQuery library, users are + * encouraged to instead use the instance method of the same name. + * + * @example + * + * ```js + * const $ = cheerio.load('

    Hello, world.

    '); + * $('h1').text(); + * //=> 'Hello, world.' + * ``` + * + * @example To render the text content of an entire document, + * invoke the `text` function exported by the Cheerio module with a "root" + * selection. + * + * ```js + * cheerio.text($.root()); + * //=> 'Hello, world.' + * ``` + */ + describe('.text - deprecated API', () => { + it('(cheerio object) : should return the text contents of the specified elements', () => { + const $ = cheerio.load('This is content.'); + expect($.text($('a'))).toBe('This is content.'); + }); + + it('(cheerio object) : should omit comment nodes', () => { + const $ = cheerio.load( + 'This is not a comment.', + ); + expect($.text($('a'))).toBe('This is not a comment.'); + }); + + it('(cheerio object) : should include text contents of children recursively', () => { + const $ = cheerio.load( + 'This is
    a child with another child and not a comment followed by one last child and some final
    text.
    ', + ); + expect($.text($('a'))).toBe( + 'This is a child with another child and not a comment followed by one last child and some final text.', + ); + }); + + it('() : should return the rendered text content of the root', () => { + const $ = cheerio.load( + 'This is
    a child with another child and not a comment followed by one last child and some final
    text.
    ', + ); + expect($.text()).toBe( + 'This is a child with another child and not a comment followed by one last child and some final text.', + ); + }); + + it('(cheerio object) : should not omit script tags', () => { + const $ = cheerio.load(''); + expect($.text()).toBe('console.log("test")'); + }); + + it('(cheerio object) : should omit style tags', () => { + const $ = cheerio.load( + '', + ); + expect($.text()).toBe('.cf-hidden { display: none; }'); + }); + }); + }); +}); diff --git a/frontend/node_modules/cheerio/src/__tests__/xml.spec.ts b/frontend/node_modules/cheerio/src/__tests__/xml.spec.ts new file mode 100644 index 0000000..22d32fe --- /dev/null +++ b/frontend/node_modules/cheerio/src/__tests__/xml.spec.ts @@ -0,0 +1,66 @@ +import { describe, it, expect } from 'vitest'; +import { load } from '../index.js'; +import type { CheerioOptions } from '../options.js'; + +function xml(str: string, options?: CheerioOptions) { + options = { xml: true, ...options }; + const $ = load(str, options); + return $.xml(); +} + +function dom(str: string, options?: CheerioOptions) { + const $ = load('', options); + return $(str).html(); +} + +describe('render', () => { + describe('(xml)', () => { + it('should render tags correctly', () => { + const str = + ''; + expect(xml(str)).toBe( + '', + ); + }); + + it('should render tags (RSS) correctly', () => { + const str = 'http://www.github.com/'; + expect(xml(str)).toBe('http://www.github.com/'); + }); + + it('should escape entities', () => { + const str = ''; + expect(xml(str)).toBe(str); + }); + + it('should render HTML as XML', () => { + const $ = load('', null, false); + expect($.xml()).toBe(''); + }); + }); + + describe('(dom)', () => { + it('should not keep camelCase for new nodes', () => { + const str = 'hello'; + expect(dom(str, { xml: false })).toBe( + 'hello', + ); + }); + + it('should keep camelCase for new nodes', () => { + const str = 'hello'; + expect(dom(str, { xml: true })).toBe( + 'hello', + ); + }); + + it('should maintain the parsing options of distinct contexts independently', () => { + const str = 'hello'; + const $ = load('', { xml: false }); + + expect($(str).html()).toBe( + 'hello', + ); + }); + }); +}); diff --git a/frontend/node_modules/cheerio/src/api/attributes.spec.ts b/frontend/node_modules/cheerio/src/api/attributes.spec.ts new file mode 100644 index 0000000..9b1c64c --- /dev/null +++ b/frontend/node_modules/cheerio/src/api/attributes.spec.ts @@ -0,0 +1,1165 @@ +import { describe, it, expect, beforeEach } from 'vitest'; +import { load, type CheerioAPI, type Cheerio } from '../index.js'; +import type { Element } from 'domhandler'; +import { + cheerio, + script, + fruits, + vegetables, + food, + chocolates, + inputs, + mixedText, +} from '../__fixtures__/fixtures.js'; + +function withClass(attr: string) { + return cheerio(`
    `); +} + +describe('$(...)', () => { + describe('.attr', () => { + let $: CheerioAPI; + + beforeEach(() => { + $ = load(fruits); + }); + + it('() : should get all the attributes', () => { + const attrs = $('ul').attr(); + expect(attrs).toHaveProperty('id', 'fruits'); + }); + + it('(invalid key) : invalid attr should get undefined', () => { + const attr = $('.apple').attr('lol'); + expect(attr).toBeUndefined(); + }); + + it('(valid key) : valid attr should get value', () => { + const cls = $('.apple').attr('class'); + expect(cls).toBe('apple'); + }); + + it('(valid key) : valid attr should get name when boolean', () => { + const attr = $('').attr('autofocus'); + expect(attr).toBe('autofocus'); + }); + + it('(key, value) : should set one attr', () => { + const $pear = $('.pear').attr('id', 'pear'); + expect($('#pear')).toHaveLength(1); + expect($pear).toBeInstanceOf($); + }); + + it('(key, value) : should set multiple attr', () => { + const $el = cheerio('
    ').attr( + 'class', + 'pear', + ) as Cheerio; + + expect($el[0].attribs).toHaveProperty('class', 'pear'); + expect($el[1].attribs).toBeUndefined(); + expect($el[2].attribs).toHaveProperty('class', 'pear'); + }); + + it('(key, value) : should return an empty object for an empty object', () => { + const $src = $().attr('key', 'value'); + expect($src.length).toBe(0); + expect($src[0]).toBeUndefined(); + }); + + it('(map) : object map should set multiple attributes', () => { + $('.apple').attr({ + id: 'apple', + style: 'color:red;', + 'data-url': 'http://apple.com', + }); + const attrs = $('.apple').attr(); + expect(attrs).toHaveProperty('id', 'apple'); + expect(attrs).toHaveProperty('style', 'color:red;'); + expect(attrs).toHaveProperty('data-url', 'http://apple.com'); + }); + + it('(map, val) : should throw with wrong combination of arguments', () => { + expect(() => + $('.apple').attr( + { + id: 'apple', + style: 'color:red;', + 'data-url': 'http://apple.com', + } as never, + () => '', + ), + ).toThrow('Bad combination of arguments.'); + }); + + it('(key, function) : should call the function and update the attribute with the return value', () => { + const $fruits = $('#fruits'); + $fruits.attr('id', (index, value) => { + expect(index).toBe(0); + expect(value).toBe('fruits'); + return 'ninja'; + }); + const attrs = $fruits.attr(); + expect(attrs).toHaveProperty('id', 'ninja'); + }); + + it('(key, function) : should ignore text nodes', () => { + const $text = $(mixedText); + $text.attr('class', () => 'ninja'); + const className = $text.attr('class'); + expect(className).toBe('ninja'); + }); + + it('(key, value) : should correctly encode then decode unsafe values', () => { + const $apple = $('.apple'); + $apple.attr( + 'href', + 'http://github.com/">alert("XSS!")'); + }); + + it('(key, value) : should coerce values to a string', () => { + const $apple = $('.apple'); + $apple.attr('data-test', 1 as never); + expect($apple[0].attribs['data-test']).toBe('1'); + expect($apple.attr('data-test')).toBe('1'); + }); + + it('(key, value) : handle removed boolean attributes', () => { + const $apple = $('.apple'); + $apple.attr('autofocus', 'autofocus'); + expect($apple.attr('autofocus')).toBe('autofocus'); + $apple.removeAttr('autofocus'); + expect($apple.attr('autofocus')).toBeUndefined(); + }); + + it('(key, value) : should remove non-boolean attributes with names or values similar to boolean ones', () => { + const $apple = $('.apple'); + $apple.attr('data-autofocus', 'autofocus'); + expect($apple.attr('data-autofocus')).toBe('autofocus'); + $apple.removeAttr('data-autofocus'); + expect($apple.attr('data-autofocus')).toBeUndefined(); + }); + + it('(key, value) : should remove attributes when called with null value', () => { + const $pear = $('.pear').attr('autofocus', 'autofocus'); + expect($pear.attr('autofocus')).toBe('autofocus'); + $pear.attr('autofocus', null); + expect($pear.attr('autofocus')).toBeUndefined(); + }); + + it('(map) : should remove attributes with null values', () => { + const $pear = $('.pear').attr({ + autofocus: 'autofocus', + style: 'color:red', + }); + expect($pear.attr('autofocus')).toBe('autofocus'); + expect($pear.attr('style')).toBe('color:red'); + $pear.attr({ autofocus: null, style: 'color:blue' }); + expect($pear.attr('autofocus')).toBeUndefined(); + expect($pear.attr('style')).toBe('color:blue'); + }); + + it('(chaining) setting value and calling attr returns result', () => { + const pearAttr = $('.pear').attr('foo', 'bar').attr('foo'); + expect(pearAttr).toBe('bar'); + }); + + it('(chaining) setting attr to null returns a $', () => { + const $pear = $('.pear').attr('foo', null); + expect($pear).toBeInstanceOf($); + }); + + it('(chaining) setting attr to undefined returns a $', () => { + const $pear = $('.pear').attr('foo', undefined); + expect($('.pear')).toHaveLength(1); + expect($('.pear').attr('foo')).toBeUndefined(); + expect($pear).toBeInstanceOf($); + }); + + it("(bool) shouldn't treat boolean attributes differently in XML mode", () => { + const $xml = $.load(``, { + xml: true, + })('input'); + + expect($xml.attr('checked')).toBe('checked'); + expect($xml.attr('disabled')).toBe('yes'); + }); + }); + + describe('.prop', () => { + let $: CheerioAPI; + let checkbox: Cheerio; + + beforeEach(() => { + $ = load(inputs); + checkbox = $('input[name=checkbox_on]'); + }); + + it('(valid key) : valid prop should get value', () => { + expect(checkbox.prop('checked')).toBe(true); + checkbox.css('display', 'none'); + expect(checkbox.prop('style')).toHaveProperty('display', 'none'); + expect(checkbox.prop('style')).toHaveLength(1); + expect(checkbox.prop('style')).toContain('display'); + expect(checkbox.prop('tagName')).toBe('INPUT'); + expect(checkbox.prop('nodeName')).toBe('INPUT'); + }); + + it('(valid key) : should return on empty collection', () => { + expect($(undefined).prop('checked')).toBeUndefined(); + expect($(undefined).prop('style')).toBeUndefined(); + expect($(undefined).prop('tagName')).toBeUndefined(); + expect($(undefined).prop('nodeName')).toBeUndefined(); + }); + + it('(invalid key) : invalid prop should get undefined', () => { + expect(checkbox.prop('lol')).toBeUndefined(); + expect(checkbox.prop(4 as never)).toBeUndefined(); + expect(checkbox.prop(true as never)).toBeUndefined(); + }); + + it('(key, value) : should set prop', () => { + expect(checkbox.prop('checked')).toBe(true); + checkbox.prop('checked', false); + expect(checkbox.prop('checked')).toBe(false); + checkbox.prop('checked', true); + expect(checkbox.prop('checked')).toBe(true); + }); + + it('(key, value) : should update attribute', () => { + expect(checkbox.prop('checked')).toBe(true); + expect(checkbox.attr('checked')).toBe('checked'); + checkbox.prop('checked', false); + expect(checkbox.prop('checked')).toBe(false); + expect(checkbox.attr('checked')).toBeUndefined(); + checkbox.prop('checked', true); + expect(checkbox.prop('checked')).toBe(true); + expect(checkbox.attr('checked')).toBe('checked'); + }); + + it('(key, value) : should update namespace', () => { + const imgs = $('\n\n\n\n'); + const nsHtml = 'http://www.w3.org/1999/xhtml'; + imgs.prop('src', '#').prop('namespace', nsHtml); + expect(imgs.prop('namespace')).toBe(nsHtml); + imgs.prop('attribs', null); + expect(imgs.prop('src')).toBeUndefined(); + expect(imgs.prop('data-foo')).toBeUndefined(); + }); + + it('(key, value) : should ignore empty collection', () => { + expect($(undefined).prop('checked')).toBeUndefined(); + $(undefined).prop('checked', true); + expect($(undefined).prop('checked')).toBeUndefined(); + }); + + it('(map) : object map should set multiple props', () => { + checkbox.prop({ + id: 'check', + checked: false, + }); + expect(checkbox.prop('id')).toBe('check'); + expect(checkbox.prop('checked')).toBe(false); + }); + + it('(map, val) : should throw with wrong combination of arguments', () => { + expect(() => + $('.apple').prop( + { + id: 'check', + checked: false, + } as never, + () => '', + ), + ).toThrow('Bad combination of arguments.'); + }); + + it('(key, function) : should call the function and update the prop with the return value', () => { + checkbox.prop('checked', (index, value) => { + expect(index).toBe(0); + expect(value).toBe(true); + return false; + }); + expect(checkbox.prop('checked')).toBe(false); + }); + + it('(key, value) : should support chaining after setting props', () => { + expect(checkbox.prop('checked', false)).toBe(checkbox); + }); + + it('(invalid element/tag) : prop should return undefined', () => { + expect($(undefined).prop('prop')).toBeUndefined(); + expect($(null as never).prop('prop')).toBeUndefined(); + }); + + it('("href") : should resolve links with `baseURI`', () => { + const $ = load( + ` + example1 + example2 + example3 + example4 + `, + { baseURI: 'http://example.com/page/1' }, + ); + + expect($('#1').prop('href')).toBe('http://example.org/'); + expect($('#2').prop('href')).toBe('http://example.org/'); + expect($('#3').prop('href')).toBe('http://example.com/example.org'); + expect($('#4').prop('href')).toBe('http://example.com/page/example.org'); + + expect($(undefined).prop('href')).toBeUndefined(); + }); + + it('("src") : should resolve links with `baseURI`', () => { + const $ = load( + ` + + + + + `, + { baseURI: 'http://example.com/page/1' }, + ); + + expect($('#1').prop('src')).toBe('http://example.org/image.png'); + expect($('#2').prop('src')).toBe('http://example.org/page.html'); + expect($('#3').prop('src')).toBe( + 'http://example.com/example.org/song.mp3', + ); + expect($('#4').prop('src')).toBe( + 'http://example.com/page/example.org/image.png', + ); + + expect($(undefined).prop('src')).toBeUndefined(); + }); + + it('("outerHTML") : should render properly', () => { + const outerHtml = '
    '; + const $a = $(outerHtml); + + expect($a.prop('outerHTML')).toBe(outerHtml); + + expect($(undefined).prop('outerHTML')).toBeUndefined(); + }); + + it('("innerHTML") : should render properly', () => { + const $a = $('
    '); + + expect($a.prop('innerHTML')).toBe(''); + + expect($(undefined).prop('innerHTML')).toBeUndefined(); + }); + + it('("textContent") : should render properly', () => { + expect($('select').children().prop('textContent')).toBe( + 'Option not selected', + ); + + expect($(script).prop('textContent')).toBe('A var foo = "bar";B'); + + expect($(undefined).prop('textContent')).toBeUndefined(); + }); + + it('("textContent") : should include style and script tags', () => { + const $ = load( + 'Welcome
    Hello, testing text function,
    End of message', + ); + expect($('body').prop('textContent')).toBe( + 'Welcome Hello, testing text function,console.log("hello").cf-hidden { display: none; }End of message', + ); + expect($('style').prop('textContent')).toBe( + '.cf-hidden { display: none; }', + ); + expect($('script').prop('textContent')).toBe('console.log("hello")'); + }); + + it('("innerText") : should render properly', () => { + expect($('select').children().prop('innerText')).toBe( + 'Option not selected', + ); + + expect($(script).prop('innerText')).toBe('AB'); + + expect($(undefined).prop('innerText')).toBeUndefined(); + }); + + it('("innerText") : should omit style and script tags', () => { + const $ = load( + 'Welcome
    Hello, testing text function,
    End of message', + ); + expect($('body').prop('innerText')).toBe( + 'Welcome Hello, testing text function,End of message', + ); + expect($('style').prop('innerText')).toBe(''); + expect($('script').prop('innerText')).toBe(''); + }); + + it('(inherited properties) : prop should support inherited properties', () => { + expect($('select').prop('childNodes')).toBe($('select')[0].childNodes); + }); + + it('(key) : should skip text nodes', () => { + const $text = load(mixedText); + const $body = $text($text('body')[0].children); + + expect($text($body[1]).prop('tagName')).toBeUndefined(); + + $body.prop('test-name', () => 'tester'); + expect($text('body').html()).toBe( + '1TEXT2', + ); + }); + + it("(bool) shouldn't treat boolean attributes differently in XML mode", () => { + const $xml = $.load(``, { + xml: true, + })('input'); + + expect($xml.prop('checked')).toBe('checked'); + expect($xml.prop('disabled')).toBe('yes'); + }); + }); + + describe('.data', () => { + let $: CheerioAPI; + + beforeEach(() => { + $ = load(chocolates); + }); + + it('() : should get all data attributes initially declared in the markup', () => { + const data = $('.linth').data(); + expect(data).toStrictEqual({ + highlight: 'Lindor', + origin: 'swiss', + }); + }); + + it('() : should get all data set via `data`', () => { + const $el = cheerio('
    '); + $el.data('a', 1); + $el.data('b', 2); + + expect($el.data()).toStrictEqual({ + a: 1, + b: 2, + }); + }); + + it('() : should get all data attributes initially declared in the markup merged with all data additionally set via `data`', () => { + const $el = cheerio('
    '); + $el.data('b', 'b-modified'); + $el.data('c', 'c'); + + expect($el.data()).toStrictEqual({ + a: 'a', + b: 'b-modified', + c: 'c', + }); + }); + + it('() : no data attribute should return an empty object', () => { + const data = $('.cailler').data(); + expect(Object.keys(data)).toHaveLength(0); + expect($('.free').data()).toBeUndefined(); + }); + + it('(invalid key) : invalid data attribute should return `undefined`', () => { + const data = $('.frey').data('lol'); + expect(data).toBeUndefined(); + }); + + it('(valid key) : valid data attribute should get value', () => { + const highlight = $('.linth').data('highlight'); + const origin = $('.linth').data('origin'); + + expect(highlight).toBe('Lindor'); + expect(origin).toBe('swiss'); + }); + + it('(key) : should translate camel-cased key values to hyphen-separated versions', () => { + const $el = cheerio( + '
    ', + ); + + expect($el.data('ThreeWordAttribute')).toBe('a'); + expect($el.data('fooBar_baz-')).toBe('b'); + }); + + it('(key) : should retrieve object values', () => { + const data = {}; + const $el = cheerio('
    '); + + $el.data('test', data); + + expect($el.data('test')).toBe(data); + }); + + it('(key) : should parse JSON data derived from the markup', () => { + const $el = cheerio('
    '); + + expect($el.data('json')).toStrictEqual([1, 2, 3]); + }); + + it('(key) : should not parse JSON data set via the `data` API', () => { + const $el = cheerio('
    '); + $el.data('json', '[1, 2, 3]'); + + expect($el.data('json')).toBe('[1, 2, 3]'); + }); + + // See https://api.jquery.com/data/ and https://bugs.jquery.com/ticket/14523 + it('(key) : should ignore the markup value after the first access', () => { + const $el = cheerio('
    '); + + expect($el.data('test')).toBe('a'); + + $el.attr('data-test', 'b'); + + expect($el.data('test')).toBe('a'); + }); + + it('(key) : should recover from malformed JSON', () => { + const $el = cheerio('
    '); + + expect($el.data('custom')).toBe('{{templatevar}}'); + }); + + it('("") : should accept the empty string as a name', () => { + const $el = cheerio('
    '); + + expect($el.data('')).toBe('a'); + }); + + it('(hyphen key) : data addribute with hyphen should be camelized ;-)', () => { + const data = $('.frey').data(); + expect(data).toStrictEqual({ + taste: 'sweet', + bestCollection: 'Mahony', + }); + }); + + it('(key, value) : should set data attribute', () => { + // Adding as object. + const a = $('.frey').data({ + balls: 'giandor', + }); + // Adding as string. + const b = $('.linth').data('snack', 'chocoletti'); + + expect(() => { + a.data(4 as never, 'throw'); + }).not.toThrow(); + expect(a.data('balls')).toStrictEqual('giandor'); + expect(b.data('snack')).toStrictEqual('chocoletti'); + }); + + it('(key, value) : should set data for all elements in the selection', () => { + $('li').data('foo', 'bar'); + + expect($('li').eq(0).data('foo')).toStrictEqual('bar'); + expect($('li').eq(1).data('foo')).toStrictEqual('bar'); + expect($('li').eq(2).data('foo')).toStrictEqual('bar'); + }); + + it('(map) : object map should set multiple data attributes', () => { + const { data } = $('.linth').data({ + id: 'Cailler', + flop: 'Pippilotti Rist', + top: 'Frigor', + url: 'http://www.cailler.ch/', + })[0] as never; + + expect(data).toHaveProperty('id', 'Cailler'); + expect(data).toHaveProperty('flop', 'Pippilotti Rist'); + expect(data).toHaveProperty('top', 'Frigor'); + expect(data).toHaveProperty('url', 'http://www.cailler.ch/'); + }); + + describe('(attr) : data-* attribute type coercion :', () => { + it('boolean', () => { + const $el = cheerio('
    '); + expect($el.data('bool')).toBe(true); + }); + + it('number', () => { + const $el = cheerio('
    '); + expect($el.data('number')).toBe(23); + }); + + it('number (scientific notation is not coerced)', () => { + const $el = cheerio('
    '); + expect($el.data('sci')).toBe('1E10'); + }); + + it('null', () => { + const $el = cheerio('
    '); + expect($el.data('null')).toBe(null); + }); + + it('object', () => { + const $el = cheerio('
    '); + expect($el.data('obj')).toStrictEqual({ a: 45 }); + }); + + it('array', () => { + const $el = cheerio('
    '); + expect($el.data('array')).toStrictEqual([1, 2, 3]); + }); + }); + + it('(key, value) : should skip text nodes', () => { + const $text = load(mixedText); + const $body = $text($text('body')[0].children); + + $body.data('snack', 'chocoletti'); + + expect($text('b').data('snack')).toBe('chocoletti'); + }); + }); + + describe('.val', () => { + let $: CheerioAPI; + + beforeEach(() => { + $ = load(inputs); + }); + + it('(): on div should get undefined', () => { + expect($('
    ').val()).toBeUndefined(); + }); + + it('(): on select should get value', () => { + const val = $('select#one').val(); + expect(val).toBe('option_selected'); + }); + it('(): on select with no value should get text', () => { + const val = $('select#one-valueless').val(); + expect(val).toBe('Option selected'); + }); + it('(): on select with no value should get converted HTML', () => { + const val = $('select#one-html-entity').val(); + expect(val).toBe('Option '); + }); + it('(): on select with no value should get text content', () => { + const val = $('select#one-nested').val(); + expect(val).toBe('Option selected'); + }); + it('(): on option should get value', () => { + const val = $('select#one option').eq(0).val(); + expect(val).toBe('option_not_selected'); + }); + it('(): on text input should get value', () => { + const val = $('input[type="text"]').val(); + expect(val).toBe('input_text'); + }); + it('(): on checked checkbox should get value', () => { + const val = $('input[name="checkbox_on"]').val(); + expect(val).toBe('on'); + }); + it('(): on unchecked checkbox should get value', () => { + const val = $('input[name="checkbox_off"]').val(); + expect(val).toBe('off'); + }); + it('(): on valueless checkbox should get value', () => { + const val = $('input[name="checkbox_valueless"]').val(); + expect(val).toBe('on'); + }); + it('(): on radio should get value', () => { + const val = $('input[type="radio"]').val(); + expect(val).toBe('off'); + }); + it('(): on valueless radio should get value', () => { + const val = $('input[name="radio_valueless"]').val(); + expect(val).toBe('on'); + }); + it('(): on multiple select should get an array of values', () => { + const val = $('select#multi').val(); + expect(val).toStrictEqual(['2', '3']); + }); + it('(): on multiple select with no value attribute should get an array of text content', () => { + const val = $('select#multi-valueless').val(); + expect(val).toStrictEqual(['2', '3']); + }); + it('(): with no selector matches should return nothing', () => { + const val = $('.nasty').val(); + expect(val).toBeUndefined(); + }); + it('(invalid value): should only handle arrays when it has the attribute multiple', () => { + const val = $('select#one').val([]); + expect(val).not.toBeUndefined(); + }); + it('(value): on empty set should get `this`', () => { + const $empty = $([]); + expect($empty.val('test')).toBe($empty); + }); + it('(value): on input text should set value', () => { + const element = $('input[type="text"]').val('test'); + expect(element.val()).toBe('test'); + }); + it('(value): on select should set value', () => { + const element = $('select#one').val('option_not_selected'); + expect(element.val()).toBe('option_not_selected'); + }); + it('(value): on option should set value', () => { + const element = $('select#one option').eq(0).val('option_changed'); + expect(element.val()).toBe('option_changed'); + }); + it('(value): on radio should set value', () => { + const element = $('input[name="radio"]').val('off'); + expect(element.val()).toBe('off'); + }); + it('(value): on radio with special characters should set value', () => { + const element = $('input[name="radio[brackets]"]').val('off'); + expect(element.val()).toBe('off'); + }); + it('(values): on multiple select should set multiple values', () => { + const element = $('select#multi').val(['1', '3', '4']); + expect(element.val()).toHaveLength(3); + }); + }); + + describe('.removeAttr', () => { + let $: CheerioAPI; + + beforeEach(() => { + $ = load(fruits); + }); + + it('(key) : should remove a single attr', () => { + const $fruits = $('#fruits'); + expect($fruits.attr('id')).not.toBeUndefined(); + $fruits.removeAttr('id'); + expect($fruits.attr('id')).toBeUndefined(); + }); + + it('(key key) : should remove multiple attrs', () => { + const $apple = $('.apple'); + $apple.attr('id', 'favorite'); + $apple.attr('size', 'small'); + + expect($apple.attr('id')).toBe('favorite'); + expect($apple.attr('class')).toBe('apple'); + expect($apple.attr('size')).toBe('small'); + $apple.removeAttr('id class'); + expect($apple.attr('id')).toBeUndefined(); + expect($apple.attr('class')).toBeUndefined(); + expect($apple.attr('size')).toBe('small'); + }); + + it('(key) : should return cheerio object', () => { + const obj = $('ul').removeAttr('id'); + expect(obj).toBeInstanceOf($); + }); + + it('(key) : should skip text nodes', () => { + const $text = load(mixedText); + const $body = $text($text('body')[0].children); + + $body.addClass(() => 'test'); + + expect($text('body').html()).toBe( + '1TEXT2', + ); + + $body.removeAttr('class'); + + expect($text('body').html()).toBe(mixedText); + }); + }); + + describe('.hasClass', () => { + let $: CheerioAPI; + + beforeEach(() => { + $ = load(fruits); + }); + + it('(valid class) : should return true', () => { + const cls = $('.apple').hasClass('apple'); + expect(cls).toBe(true); + + expect(withClass('foo').hasClass('foo')).toBe(true); + expect(withClass('foo bar').hasClass('foo')).toBe(true); + expect(withClass('bar foo').hasClass('foo')).toBe(true); + expect(withClass('bar foo bar').hasClass('foo')).toBe(true); + }); + + it('(invalid class) : should return false', () => { + const cls = $('#fruits').hasClass('fruits'); + expect(cls).toBe(false); + expect(withClass('foo-bar').hasClass('foo')).toBe(false); + expect(withClass('foo-bar').hasClass('foo')).toBe(false); + expect(withClass('foo-bar').hasClass('foo-ba')).toBe(false); + }); + + it('should check multiple classes', () => { + // Add a class + $('.apple').addClass('red'); + expect($('.apple').hasClass('apple')).toBe(true); + expect($('.apple').hasClass('red')).toBe(true); + + // Remove one and test again + $('.apple').removeClass('apple'); + expect($('li').eq(0).hasClass('apple')).toBe(false); + }); + + it('(empty string argument) : should return false', () => { + expect(withClass('foo').hasClass('')).toBe(false); + expect(withClass('foo bar').hasClass('')).toBe(false); + expect(withClass('foo bar').removeClass('foo').hasClass('')).toBe(false); + }); + }); + + describe('.addClass', () => { + let $: CheerioAPI; + + beforeEach(() => { + $ = load(fruits); + }); + + it('(first class) : should add the class to the element', () => { + const $fruits = $('#fruits'); + $fruits.addClass('fruits'); + const cls = $fruits.hasClass('fruits'); + expect(cls).toBe(true); + }); + + it('(single class) : should add the class to the element', () => { + $('.apple').addClass('fruit'); + const cls = $('.apple').hasClass('fruit'); + expect(cls).toBe(true); + }); + + it('(class): adds classes to many selected items', () => { + $('li').addClass('fruit'); + expect($('.apple').hasClass('fruit')).toBe(true); + expect($('.orange').hasClass('fruit')).toBe(true); + expect($('.pear').hasClass('fruit')).toBe(true); + + // Mixed with text nodes + const $red = $('\n
      \n
    \t').addClass('red'); + expect($red).toHaveLength(3); + expect($red[0].type).toBe('text'); + expect($red[1].type).toBe('tag'); + expect($red[2].type).toBe('text'); + expect($red.hasClass('red')).toBe(true); + }); + + it('(class class class) : should add multiple classes to the element', () => { + $('.apple').addClass('fruit red tasty'); + expect($('.apple').hasClass('apple')).toBe(true); + expect($('.apple').hasClass('fruit')).toBe(true); + expect($('.apple').hasClass('red')).toBe(true); + expect($('.apple').hasClass('tasty')).toBe(true); + }); + + it('(fn) : should add classes returned from the function', () => { + const $fruits = $('#fruits').children().add($('#fruits')); + const args: [i: number, className: string][] = []; + const thisVals: Element[] = []; + const toAdd = ['main', 'apple red', '', undefined]; + + $fruits.addClass(function (...myArgs) { + args.push(myArgs); + thisVals.push(this); + return toAdd[myArgs[0]]; + }); + + expect(args).toStrictEqual([ + [0, ''], + [1, 'apple'], + [2, 'orange'], + [3, 'pear'], + ]); + expect(thisVals).toStrictEqual([ + $fruits[0], + $fruits[1], + $fruits[2], + $fruits[3], + ]); + expect($fruits.eq(0).hasClass('main')).toBe(true); + expect($fruits.eq(0).hasClass('apple')).toBe(false); + expect($fruits.eq(1).hasClass('apple')).toBe(true); + expect($fruits.eq(1).hasClass('red')).toBe(true); + expect($fruits.eq(2).hasClass('orange')).toBe(true); + expect($fruits.eq(3).hasClass('pear')).toBe(true); + }); + }); + + describe('.removeClass', () => { + let $: CheerioAPI; + + beforeEach(() => { + $ = load(fruits); + }); + + it('() : should remove all the classes', () => { + $('.pear').addClass('fruit'); + $('.pear').removeClass(); + expect($('.pear').attr('class')).toBeUndefined(); + }); + + it('("") : should not modify class list', () => { + const $fruits = $('#fruits'); + $fruits.children().removeClass(''); + expect($('.apple')).toHaveLength(1); + }); + + it('(invalid class) : should not remove anything', () => { + $('.pear').removeClass('fruit'); + expect($('.pear').hasClass('pear')).toBe(true); + }); + + it('(no class attribute) : should not throw an exception', () => { + const $vegetables = cheerio(vegetables); + + expect(() => { + $('li', $vegetables).removeClass('vegetable'); + }).not.toThrow(); + }); + + it('(single class) : should remove a single class from the element', () => { + $('.pear').addClass('fruit'); + expect($('.pear').hasClass('fruit')).toBe(true); + $('.pear').removeClass('fruit'); + expect($('.pear').hasClass('fruit')).toBe(false); + expect($('.pear').hasClass('pear')).toBe(true); + + // Remove one class from set + const $li = $('li').removeClass('orange'); + expect($li.eq(0).attr('class')).toBe('apple'); + expect($li.eq(1).attr('class')).toBe(''); + expect($li.eq(2).attr('class')).toBe('pear'); + + // Mixed with text nodes + const $red = $('\n
      \n
    \t').removeClass( + 'one', + ); + expect($red).toHaveLength(3); + expect($red[0].type).toBe('text'); + expect($red[1].type).toBe('tag'); + expect($red[2].type).toBe('text'); + expect($red.eq(1).attr('class')).toBe(''); + expect($red.eq(1).prop('tagName')).toBe('UL'); + }); + + it('(single class) : should remove a single class from multiple classes on the element', () => { + $('.pear').addClass('fruit green tasty'); + expect($('.pear').hasClass('fruit')).toBe(true); + expect($('.pear').hasClass('green')).toBe(true); + expect($('.pear').hasClass('tasty')).toBe(true); + + $('.pear').removeClass('green'); + expect($('.pear').hasClass('fruit')).toBe(true); + expect($('.pear').hasClass('green')).toBe(false); + expect($('.pear').hasClass('tasty')).toBe(true); + }); + + it('(class class class) : should remove multiple classes from the element', () => { + $('.apple').addClass('fruit red tasty'); + expect($('.apple').hasClass('apple')).toBe(true); + expect($('.apple').hasClass('fruit')).toBe(true); + expect($('.apple').hasClass('red')).toBe(true); + expect($('.apple').hasClass('tasty')).toBe(true); + + $('.apple').removeClass('apple red tasty'); + expect($('.fruit').hasClass('apple')).toBe(false); + expect($('.fruit').hasClass('red')).toBe(false); + expect($('.fruit').hasClass('tasty')).toBe(false); + expect($('.fruit').hasClass('fruit')).toBe(true); + }); + + it('(class) : should remove all occurrences of a class name', () => { + const $div = cheerio('
    '); + expect($div.removeClass('x').hasClass('x')).toBe(false); + }); + + it('(fn) : should remove classes returned from the function', () => { + const $fruits = $('#fruits').children(); + const args: [number, string][] = []; + const thisVals: Element[] = []; + const toAdd = ['apple red', '', undefined]; + + $fruits.removeClass(function (...myArgs) { + args.push(myArgs); + thisVals.push(this); + return toAdd[myArgs[0]]; + }); + + expect(args).toStrictEqual([ + [0, 'apple'], + [1, 'orange'], + [2, 'pear'], + ]); + expect(thisVals).toStrictEqual([$fruits[0], $fruits[1], $fruits[2]]); + expect($fruits.eq(0).hasClass('apple')).toBe(false); + expect($fruits.eq(0).hasClass('red')).toBe(false); + expect($fruits.eq(1).hasClass('orange')).toBe(true); + expect($fruits.eq(2).hasClass('pear')).toBe(true); + }); + + it('(fn) : should no op elements without attributes', () => { + const $inputs = $(inputs); + const val = $inputs.removeClass(() => 'tasty'); + expect(val).toHaveLength(15); + }); + + it('(fn) : should skip text nodes', () => { + const $text = load(mixedText); + const $body = $text($text('body')[0].children); + + $body.addClass(() => 'test'); + + expect($text('body').html()).toBe( + '1TEXT2', + ); + + $body.removeClass(() => 'test'); + + expect($text('body').html()).toBe( + '1TEXT2', + ); + }); + }); + + describe('.toggleClass', () => { + let $: CheerioAPI; + + beforeEach(() => { + $ = load(fruits); + }); + + it('(class class) : should toggle multiple classes from the element', () => { + $('.apple').addClass('fruit'); + expect($('.apple').hasClass('apple')).toBe(true); + expect($('.apple').hasClass('fruit')).toBe(true); + expect($('.apple').hasClass('red')).toBe(false); + + $('.apple').toggleClass('apple red'); + expect($('.fruit').hasClass('apple')).toBe(false); + expect($('.fruit').hasClass('red')).toBe(true); + expect($('.fruit').hasClass('fruit')).toBe(true); + + // Mixed with text nodes + const $red = $('\n
      \n
    \t').toggleClass( + 'red', + ); + expect($red).toHaveLength(3); + expect($red.hasClass('red')).toBe(true); + expect($red.hasClass('one')).toBe(true); + $red.toggleClass('one'); + expect($red.hasClass('red')).toBe(true); + expect($red.hasClass('one')).toBe(false); + }); + + it('(class class, true) : should add multiple classes to the element', () => { + $('.apple').addClass('fruit'); + expect($('.apple').hasClass('apple')).toBe(true); + expect($('.apple').hasClass('fruit')).toBe(true); + expect($('.apple').hasClass('red')).toBe(false); + + $('.apple').toggleClass('apple red', true); + expect($('.fruit').hasClass('apple')).toBe(true); + expect($('.fruit').hasClass('red')).toBe(true); + expect($('.fruit').hasClass('fruit')).toBe(true); + }); + + it('(class true) : should add only one instance of class', () => { + $('.apple').toggleClass('tasty', true); + $('.apple').toggleClass('tasty', true); + expect($('.apple').attr('class')).toMatch(/tasty/g); + }); + + it('(class class, false) : should remove multiple classes from the element', () => { + $('.apple').addClass('fruit'); + expect($('.apple').hasClass('apple')).toBe(true); + expect($('.apple').hasClass('fruit')).toBe(true); + expect($('.apple').hasClass('red')).toBe(false); + + $('.apple').toggleClass('apple red', false); + expect($('.fruit').hasClass('apple')).toBe(false); + expect($('.fruit').hasClass('red')).toBe(false); + expect($('.fruit').hasClass('fruit')).toBe(true); + }); + + it('(fn) : should toggle classes returned from the function', () => { + const $ = load(food); + + $('.apple').addClass('fruit'); + $('.carrot').addClass('vegetable'); + expect($('.apple').hasClass('fruit')).toBe(true); + expect($('.apple').hasClass('vegetable')).toBe(false); + expect($('.orange').hasClass('fruit')).toBe(false); + expect($('.orange').hasClass('vegetable')).toBe(false); + expect($('.carrot').hasClass('fruit')).toBe(false); + expect($('.carrot').hasClass('vegetable')).toBe(true); + expect($('.sweetcorn').hasClass('fruit')).toBe(false); + expect($('.sweetcorn').hasClass('vegetable')).toBe(false); + + $('li').toggleClass(function () { + return $(this).parent().is('#fruits') ? 'fruit' : 'vegetable'; + }); + expect($('.apple').hasClass('fruit')).toBe(false); + expect($('.apple').hasClass('vegetable')).toBe(false); + expect($('.orange').hasClass('fruit')).toBe(true); + expect($('.orange').hasClass('vegetable')).toBe(false); + expect($('.carrot').hasClass('fruit')).toBe(false); + expect($('.carrot').hasClass('vegetable')).toBe(false); + expect($('.sweetcorn').hasClass('fruit')).toBe(false); + expect($('.sweetcorn').hasClass('vegetable')).toBe(true); + }); + + it('(fn) : should work with no initial class attribute', () => { + const $inputs = load(inputs); + $inputs('input, select').toggleClass(function () { + // eslint-disable-next-line @typescript-eslint/no-non-null-assertion -- `get` should never return undefined here. + return $inputs(this).get(0)!.tagName === 'select' + ? 'selectable' + : 'inputable'; + }); + expect($inputs('.selectable')).toHaveLength(6); + expect($inputs('.inputable')).toHaveLength(9); + }); + + it('(fn) : should skip text nodes', () => { + const $text = load(mixedText); + const $body = $text($text('body')[0].children); + + $body.toggleClass(() => 'test'); + + expect($text('body').html()).toBe( + '1TEXT2', + ); + + $body.toggleClass(() => 'test'); + + expect($text('body').html()).toBe( + '1TEXT2', + ); + }); + + it('(invalid) : should be a no-op for invalid inputs', () => { + const original = $('.apple'); + const testAgainst = original.attr('class'); + expect(original.toggleClass().attr('class')).toStrictEqual(testAgainst); + + for (const value of [undefined, true, false, null, 0, 1, {}]) { + expect( + original.toggleClass(value as never).attr('class'), + ).toStrictEqual(testAgainst); + } + }); + }); +}); diff --git a/frontend/node_modules/cheerio/src/api/attributes.ts b/frontend/node_modules/cheerio/src/api/attributes.ts new file mode 100644 index 0000000..db246e6 --- /dev/null +++ b/frontend/node_modules/cheerio/src/api/attributes.ts @@ -0,0 +1,1130 @@ +/** + * Methods for getting and modifying attributes. + * + * @module cheerio/attributes + */ + +import { text } from '../static.js'; +import { domEach, camelCase, cssCase } from '../utils.js'; +import { isTag, type AnyNode, type Element } from 'domhandler'; +import type { Cheerio } from '../cheerio.js'; +import { innerText, textContent } from 'domutils'; +const hasOwn = Object.prototype.hasOwnProperty; +const rspace = /\s+/; +const dataAttrPrefix = 'data-'; + +// Attributes that are booleans +const rboolean = + /^(?:autofocus|autoplay|async|checked|controls|defer|disabled|hidden|loop|multiple|open|readonly|required|scoped|selected)$/i; +// Matches strings that look like JSON objects or arrays +const rbrace = /^{[^]*}$|^\[[^]*]$/; + +/** + * Gets a node's attribute. For boolean attributes, it will return the value's + * name should it be set. + * + * Also supports getting the `value` of several form elements. + * + * @private + * @category Attributes + * @param elem - Element to get the attribute of. + * @param name - Name of the attribute. + * @param xmlMode - Disable handling of special HTML attributes. + * @returns The attribute's value. + */ +function getAttr( + elem: AnyNode, + name: undefined, + xmlMode?: boolean, +): Record | undefined; +function getAttr( + elem: AnyNode, + name: string, + xmlMode?: boolean, +): string | undefined; +function getAttr( + elem: AnyNode, + name: string | undefined, + xmlMode?: boolean, +): Record | string | undefined { + if (!elem || !isTag(elem)) return undefined; + + elem.attribs ??= {}; + + // Return the entire attribs object if no attribute specified + if (!name) { + return elem.attribs; + } + + if (hasOwn.call(elem.attribs, name)) { + // Get the (decoded) attribute + return !xmlMode && rboolean.test(name) ? name : elem.attribs[name]; + } + + // Mimic the DOM and return text content as value for `option's` + if (elem.name === 'option' && name === 'value') { + return text(elem.children); + } + + // Mimic DOM with default value for radios/checkboxes + if ( + elem.name === 'input' && + (elem.attribs['type'] === 'radio' || elem.attribs['type'] === 'checkbox') && + name === 'value' + ) { + return 'on'; + } + + return undefined; +} + +/** + * Sets the value of an attribute. The attribute will be deleted if the value is + * `null`. + * + * @private + * @param el - The element to set the attribute on. + * @param name - The attribute's name. + * @param value - The attribute's value. + */ +function setAttr(el: Element, name: string, value: string | null) { + if (value === null) { + removeAttribute(el, name); + } else { + el.attribs[name] = `${value}`; + } +} + +/** + * Method for getting attributes. Gets the attribute value for only the first + * element in the matched set. + * + * @category Attributes + * @example + * + * ```js + * $('ul').attr('id'); + * //=> fruits + * ``` + * + * @param name - Name of the attribute. + * @returns The attribute's value. + * @see {@link https://api.jquery.com/attr/} + */ +export function attr( + this: Cheerio, + name: string, +): string | undefined; +/** + * Method for getting all attributes and their values of the first element in + * the matched set. + * + * @category Attributes + * @example + * + * ```js + * $('ul').attr(); + * //=> { id: 'fruits' } + * ``` + * + * @returns The attribute's values. + * @see {@link https://api.jquery.com/attr/} + */ +export function attr( + this: Cheerio, +): Record | undefined; +/** + * Method for setting attributes. Sets the attribute value for only the first + * element in the matched set. If you set an attribute's value to `null`, you + * remove that attribute. You may also pass a `map` and `function`. + * + * @category Attributes + * @example + * + * ```js + * $('.apple').attr('id', 'favorite').html(); + * //=>
  • Apple
  • + * ``` + * + * @param name - Name of the attribute. + * @param value - The new value of the attribute. + * @returns The instance itself. + * @see {@link https://api.jquery.com/attr/} + */ +export function attr( + this: Cheerio, + name: string, + value?: + | string + | null + | ((this: Element, i: number, attrib: string) => string | null), +): Cheerio; +/** + * Method for setting multiple attributes at once. Sets the attribute value for + * only the first element in the matched set. If you set an attribute's value to + * `null`, you remove that attribute. + * + * @category Attributes + * @example + * + * ```js + * $('.apple').attr({ id: 'favorite' }).html(); + * //=>
  • Apple
  • + * ``` + * + * @param values - Map of attribute names and values. + * @returns The instance itself. + * @see {@link https://api.jquery.com/attr/} + */ +export function attr( + this: Cheerio, + values: Record, +): Cheerio; +export function attr( + this: Cheerio, + name?: string | Record, + value?: + | string + | null + | ((this: Element, i: number, attrib: string) => string | null), +): string | Cheerio | undefined | Record { + // Set the value (with attr map support) + if (typeof name === 'object' || value !== undefined) { + if (typeof value === 'function') { + if (typeof name !== 'string') { + { + throw new Error('Bad combination of arguments.'); + } + } + return domEach(this, (el, i) => { + if (isTag(el)) setAttr(el, name, value.call(el, i, el.attribs[name])); + }); + } + return domEach(this, (el) => { + if (!isTag(el)) return; + + if (typeof name === 'object') { + for (const objName of Object.keys(name)) { + const objValue = name[objName]; + setAttr(el, objName, objValue); + } + } else { + setAttr(el, name as string, value as string); + } + }); + } + + return arguments.length > 1 + ? this + : getAttr(this[0], name as string, this.options.xmlMode); +} + +/** + * Gets a node's prop. + * + * @private + * @category Attributes + * @param el - Element to get the prop of. + * @param name - Name of the prop. + * @param xmlMode - Disable handling of special HTML attributes. + * @returns The prop's value. + */ +function getProp( + el: Element, + name: string, + xmlMode?: boolean, +): string | undefined | Element[keyof Element] { + return name in el + ? // @ts-expect-error TS doesn't like us accessing the value directly here. + el[name] + : !xmlMode && rboolean.test(name) + ? getAttr(el, name, false) !== undefined + : getAttr(el, name, xmlMode); +} + +/** + * Sets the value of a prop. + * + * @private + * @param el - The element to set the prop on. + * @param name - The prop's name. + * @param value - The prop's value. + * @param xmlMode - Disable handling of special HTML attributes. + */ +function setProp(el: Element, name: string, value: unknown, xmlMode?: boolean) { + if (name in el) { + // @ts-expect-error Overriding value + el[name] = value; + } else { + setAttr( + el, + name, + !xmlMode && rboolean.test(name) ? (value ? '' : null) : `${value}`, + ); + } +} + +interface StyleProp { + length: number; + [key: string]: string | number; + [index: number]: string; +} + +/** + * Method for getting and setting properties. Gets the property value for only + * the first element in the matched set. + * + * @category Attributes + * @example + * + * ```js + * $('input[type="checkbox"]').prop('checked'); + * //=> false + * + * $('input[type="checkbox"]').prop('checked', true).val(); + * //=> ok + * ``` + * + * @param name - Name of the property. + * @returns If `value` is specified the instance itself, otherwise the prop's + * value. + * @see {@link https://api.jquery.com/prop/} + */ +export function prop( + this: Cheerio, + name: 'tagName' | 'nodeName', +): string | undefined; +export function prop( + this: Cheerio, + name: 'innerHTML' | 'outerHTML' | 'innerText' | 'textContent', +): string | null; +/** + * Get a parsed CSS style object. + * + * @param name - Name of the property. + * @returns The style object, or `undefined` if the element has no `style` + * attribute. + */ +export function prop( + this: Cheerio, + name: 'style', +): StyleProp | undefined; +/** + * Resolve `href` or `src` of supported elements. Requires the `baseURI` option + * to be set, and a global `URL` object to be part of the environment. + * + * @example With `baseURI` set to `'https://example.com'`: + * + * ```js + * $('').prop('src'); + * //=> 'https://example.com/image.png' + * ``` + * + * @param name - Name of the property. + * @returns The resolved URL, or `undefined` if the element is not supported. + */ +export function prop( + this: Cheerio, + name: 'href' | 'src', +): string | undefined; +/** + * Get a property of an element. + * + * @param name - Name of the property. + * @returns The property's value. + */ +export function prop( + this: Cheerio, + name: K, +): Element[K]; +/** + * Set a property of an element. + * + * @param name - Name of the property. + * @param value - Value to set the property to. + * @returns The instance itself. + */ +export function prop( + this: Cheerio, + name: K, + value: + | Element[K] + | ((this: Element, i: number, prop: K) => Element[keyof Element]), +): Cheerio; +/** + * Set multiple properties of an element. + * + * @example + * + * ```js + * $('input[type="checkbox"]').prop({ + * checked: true, + * disabled: false, + * }); + * ``` + * + * @param map - Object of properties to set. + * @returns The instance itself. + */ +export function prop( + this: Cheerio, + map: Record, +): Cheerio; +/** + * Set a property of an element. + * + * @param name - Name of the property. + * @param value - Value to set the property to. + * @returns The instance itself. + */ +export function prop( + this: Cheerio, + name: string, + value: + | string + | boolean + | null + | ((this: Element, i: number, prop: string) => string | boolean), +): Cheerio; +/** + * Get a property of an element. + * + * @param name - The property's name. + * @returns The property's value. + */ +export function prop(this: Cheerio, name: string): string; +export function prop( + this: Cheerio, + name: string | Record, + value?: + | (( + this: Element, + i: number, + prop: string | undefined, + ) => string | Element[keyof Element] | boolean) + | unknown, +): Cheerio | string | undefined | null | Element[keyof Element] | StyleProp { + if (typeof name === 'string' && value === undefined) { + const el = this[0]; + + if (!el || !isTag(el)) return undefined; + + switch (name) { + case 'style': { + const property = this.css() as StyleProp; + const keys = Object.keys(property); + for (let i = 0; i < keys.length; i++) { + property[i] = keys[i]; + } + + property.length = keys.length; + + return property; + } + case 'tagName': + case 'nodeName': { + return el.name.toUpperCase(); + } + + case 'href': + case 'src': { + const prop = el.attribs?.[name]; + + if ( + typeof URL !== 'undefined' && + ((name === 'href' && (el.tagName === 'a' || el.tagName === 'link')) || + (name === 'src' && + (el.tagName === 'img' || + el.tagName === 'iframe' || + el.tagName === 'audio' || + el.tagName === 'video' || + el.tagName === 'source'))) && + prop !== undefined && + this.options.baseURI + ) { + return new URL(prop, this.options.baseURI).href; + } + + return prop; + } + + case 'innerText': { + return innerText(el); + } + + case 'textContent': { + return textContent(el); + } + + case 'outerHTML': { + return this.clone().wrap('').parent().html(); + } + + case 'innerHTML': { + return this.html(); + } + + default: { + return getProp(el, name, this.options.xmlMode); + } + } + } + + if (typeof name === 'object' || value !== undefined) { + if (typeof value === 'function') { + if (typeof name === 'object') { + throw new TypeError('Bad combination of arguments.'); + } + return domEach(this, (el, i) => { + if (isTag(el)) { + setProp( + el, + name, + value.call(el, i, getProp(el, name, this.options.xmlMode)), + this.options.xmlMode, + ); + } + }); + } + + return domEach(this, (el) => { + if (!isTag(el)) return; + + if (typeof name === 'object') { + for (const key of Object.keys(name)) { + const val = name[key]; + setProp(el, key, val, this.options.xmlMode); + } + } else { + setProp(el, name, value, this.options.xmlMode); + } + }); + } + + return undefined; +} + +/** + * An element with a data attribute. + * + * @private + */ +interface DataElement extends Element { + /** The data attribute. */ + data?: Record; +} + +/** + * Sets the value of a data attribute. + * + * @private + * @param elem - The element to set the data attribute on. + * @param name - The data attribute's name. + * @param value - The data attribute's value. + */ +function setData( + elem: DataElement, + name: string | Record, + value?: unknown, +) { + elem.data ??= {}; + + if (typeof name === 'object') Object.assign(elem.data, name); + else if (typeof name === 'string' && value !== undefined) { + elem.data[name] = value; + } +} + +/** + * Read _all_ HTML5 `data-*` attributes from the equivalent HTML5 `data-*` + * attribute, and cache the value in the node's internal data store. + * + * @private + * @category Attributes + * @param el - Element to get the data attribute of. + * @returns A map with all of the data attributes. + */ +function readAllData(el: DataElement): unknown { + for (const domName of Object.keys(el.attribs)) { + if (!domName.startsWith(dataAttrPrefix)) { + continue; + } + + const jsName = camelCase(domName.slice(dataAttrPrefix.length)); + + if (!hasOwn.call(el.data, jsName)) { + el.data![jsName] = parseDataValue(el.attribs[domName]); + } + } + + return el.data; +} + +/** + * Read the specified attribute from the equivalent HTML5 `data-*` attribute, + * and (if present) cache the value in the node's internal data store. + * + * @private + * @category Attributes + * @param el - Element to get the data attribute of. + * @param name - Name of the data attribute. + * @returns The data attribute's value. + */ +function readData(el: DataElement, name: string): unknown { + const domName = dataAttrPrefix + cssCase(name); + const data = el.data!; + + if (hasOwn.call(data, name)) { + return data[name]; + } + + if (hasOwn.call(el.attribs, domName)) { + return (data[name] = parseDataValue(el.attribs[domName])); + } + + return undefined; +} + +/** + * Coerce string data-* attributes to their corresponding JavaScript primitives. + * + * @private + * @category Attributes + * @param value - The value to parse. + * @returns The parsed value. + */ +function parseDataValue(value: string): unknown { + if (value === 'null') return null; + if (value === 'true') return true; + if (value === 'false') return false; + const num = Number(value); + if (value === String(num)) return num; + if (rbrace.test(value)) { + try { + return JSON.parse(value); + } catch { + /* Ignore */ + } + } + return value; +} + +/** + * Method for getting data attributes, for only the first element in the matched + * set. + * + * @category Attributes + * @example + * + * ```js + * $('
    ').data('apple-color'); + * //=> 'red' + * ``` + * + * @param name - Name of the data attribute. + * @returns The data attribute's value, or `undefined` if the attribute does not + * exist. + * @see {@link https://api.jquery.com/data/} + */ +export function data( + this: Cheerio, + name: string, +): unknown | undefined; +/** + * Method for getting all of an element's data attributes, for only the first + * element in the matched set. + * + * @category Attributes + * @example + * + * ```js + * $('
    ').data(); + * //=> { appleColor: 'red' } + * ``` + * + * @returns A map with all of the data attributes. + * @see {@link https://api.jquery.com/data/} + */ +export function data( + this: Cheerio, +): Record; +/** + * Method for setting data attributes, for only the first element in the matched + * set. + * + * @category Attributes + * @example + * + * ```js + * const apple = $('.apple').data('kind', 'mac'); + * + * apple.data('kind'); + * //=> 'mac' + * ``` + * + * @param name - Name of the data attribute. + * @param value - The new value. + * @returns The instance itself. + * @see {@link https://api.jquery.com/data/} + */ +export function data( + this: Cheerio, + name: string, + value: unknown, +): Cheerio; +/** + * Method for setting multiple data attributes at once, for only the first + * element in the matched set. + * + * @category Attributes + * @example + * + * ```js + * const apple = $('.apple').data({ kind: 'mac' }); + * + * apple.data('kind'); + * //=> 'mac' + * ``` + * + * @param values - Map of names to values. + * @returns The instance itself. + * @see {@link https://api.jquery.com/data/} + */ +export function data( + this: Cheerio, + values: Record, +): Cheerio; +export function data( + this: Cheerio, + name?: string | Record, + value?: unknown, +): unknown | Cheerio | undefined | Record { + const elem = this[0]; + + if (!elem || !isTag(elem)) return; + + const dataEl: DataElement = elem; + dataEl.data ??= {}; + + // Return the entire data object if no data specified + if (name == null) { + return readAllData(dataEl); + } + + // Set the value (with attr map support) + if (typeof name === 'object' || value !== undefined) { + domEach(this, (el) => { + if (isTag(el)) { + if (typeof name === 'object') setData(el, name); + else setData(el, name, value as unknown); + } + }); + return this; + } + + return readData(dataEl, name); +} + +/** + * Method for getting the value of input, select, and textarea. Note: Support + * for `map`, and `function` has not been added yet. + * + * @category Attributes + * @example + * + * ```js + * $('input[type="text"]').val(); + * //=> input_text + * ``` + * + * @returns The value. + * @see {@link https://api.jquery.com/val/} + */ +export function val( + this: Cheerio, +): string | undefined | string[]; +/** + * Method for setting the value of input, select, and textarea. Note: Support + * for `map`, and `function` has not been added yet. + * + * @category Attributes + * @example + * + * ```js + * $('input[type="text"]').val('test').html(); + * //=> + * ``` + * + * @param value - The new value. + * @returns The instance itself. + * @see {@link https://api.jquery.com/val/} + */ +export function val( + this: Cheerio, + value: string | string[], +): Cheerio; +export function val( + this: Cheerio, + value?: string | string[], +): string | string[] | Cheerio | undefined { + const querying = arguments.length === 0; + const element = this[0]; + + if (!element || !isTag(element)) return querying ? undefined : this; + + switch (element.name) { + case 'textarea': { + return this.text(value as string); + } + case 'select': { + const option = this.find('option:selected'); + if (!querying) { + if (this.attr('multiple') == null && typeof value === 'object') { + return this; + } + + this.find('option').removeAttr('selected'); + + const values = typeof value === 'object' ? value : [value]; + for (const val of values) { + this.find(`option[value="${val}"]`).attr('selected', ''); + } + + return this; + } + + return this.attr('multiple') + ? option.toArray().map((el) => text(el.children)) + : option.attr('value'); + } + case 'input': + case 'option': { + return querying + ? this.attr('value') + : this.attr('value', value as string); + } + } + + return undefined; +} + +/** + * Remove an attribute. + * + * @private + * @param elem - Node to remove attribute from. + * @param name - Name of the attribute to remove. + */ +function removeAttribute(elem: Element, name: string) { + if (!elem.attribs || !hasOwn.call(elem.attribs, name)) return; + + delete elem.attribs[name]; +} + +/** + * Splits a space-separated list of names to individual names. + * + * @category Attributes + * @param names - Names to split. + * @returns - Split names. + */ +function splitNames(names?: string): string[] { + return names ? names.trim().split(rspace) : []; +} + +/** + * Method for removing attributes by `name`. + * + * @category Attributes + * @example + * + * ```js + * $('.pear').removeAttr('class').html(); + * //=>
  • Pear
  • + * + * $('.apple').attr('id', 'favorite'); + * $('.apple').removeAttr('id class').html(); + * //=>
  • Apple
  • + * ``` + * + * @param name - Name of the attribute. + * @returns The instance itself. + * @see {@link https://api.jquery.com/removeAttr/} + */ +export function removeAttr( + this: Cheerio, + name: string, +): Cheerio { + const attrNames = splitNames(name); + + for (const attrName of attrNames) { + domEach(this, (elem) => { + if (isTag(elem)) removeAttribute(elem, attrName); + }); + } + + return this; +} + +/** + * Check to see if _any_ of the matched elements have the given `className`. + * + * @category Attributes + * @example + * + * ```js + * $('.pear').hasClass('pear'); + * //=> true + * + * $('apple').hasClass('fruit'); + * //=> false + * + * $('li').hasClass('pear'); + * //=> true + * ``` + * + * @param className - Name of the class. + * @returns Indicates if an element has the given `className`. + * @see {@link https://api.jquery.com/hasClass/} + */ +export function hasClass( + this: Cheerio, + className: string, +): boolean { + return this.toArray().some((elem) => { + const clazz = isTag(elem) && elem.attribs['class']; + let idx = -1; + + if (clazz && className.length > 0) { + while ((idx = clazz.indexOf(className, idx + 1)) > -1) { + const end = idx + className.length; + + if ( + (idx === 0 || rspace.test(clazz[idx - 1])) && + (end === clazz.length || rspace.test(clazz[end])) + ) { + return true; + } + } + } + + return false; + }); +} + +/** + * Adds class(es) to all of the matched elements. Also accepts a `function`. + * + * @category Attributes + * @example + * + * ```js + * $('.pear').addClass('fruit').html(); + * //=>
  • Pear
  • + * + * $('.apple').addClass('fruit red').html(); + * //=>
  • Apple
  • + * ``` + * + * @param value - Name of new class. + * @returns The instance itself. + * @see {@link https://api.jquery.com/addClass/} + */ +export function addClass>( + this: R, + value?: + | string + | ((this: Element, i: number, className: string) => string | undefined), +): R { + // Support functions + if (typeof value === 'function') { + return domEach(this, (el, i) => { + if (isTag(el)) { + const className = el.attribs['class'] || ''; + addClass.call([el], value.call(el, i, className)); + } + }); + } + + // Return if no value or not a string or function + if (!value || typeof value !== 'string') return this; + + const classNames = value.split(rspace); + const numElements = this.length; + + for (let i = 0; i < numElements; i++) { + const el = this[i]; + // If selected element isn't a tag, move on + if (!isTag(el)) continue; + + // If we don't already have classes — always set xmlMode to false here, as it doesn't matter for classes + const className = getAttr(el, 'class', false); + + if (className) { + let setClass = ` ${className} `; + + // Check if class already exists + for (const cn of classNames) { + const appendClass = `${cn} `; + if (!setClass.includes(` ${appendClass}`)) setClass += appendClass; + } + + setAttr(el, 'class', setClass.trim()); + } else { + setAttr(el, 'class', classNames.join(' ').trim()); + } + } + + return this; +} + +/** + * Removes one or more space-separated classes from the selected elements. If no + * `className` is defined, all classes will be removed. Also accepts a + * `function`. + * + * @category Attributes + * @example + * + * ```js + * $('.pear').removeClass('pear').html(); + * //=>
  • Pear
  • + * + * $('.apple').addClass('red').removeClass().html(); + * //=>
  • Apple
  • + * ``` + * + * @param name - Name of the class. If not specified, removes all elements. + * @returns The instance itself. + * @see {@link https://api.jquery.com/removeClass/} + */ +export function removeClass>( + this: R, + name?: + | string + | ((this: Element, i: number, className: string) => string | undefined), +): R { + // Handle if value is a function + if (typeof name === 'function') { + return domEach(this, (el, i) => { + if (isTag(el)) { + removeClass.call([el], name.call(el, i, el.attribs['class'] || '')); + } + }); + } + + const classes = splitNames(name); + const numClasses = classes.length; + const removeAll = arguments.length === 0; + + return domEach(this, (el) => { + if (!isTag(el)) return; + + if (removeAll) { + // Short circuit the remove all case as this is the nice one + el.attribs['class'] = ''; + } else { + const elClasses = splitNames(el.attribs['class']); + let changed = false; + + for (let j = 0; j < numClasses; j++) { + const index = elClasses.indexOf(classes[j]); + + if (index >= 0) { + elClasses.splice(index, 1); + changed = true; + + /* + * We have to do another pass to ensure that there are not duplicate + * classes listed + */ + j--; + } + } + if (changed) { + el.attribs['class'] = elClasses.join(' '); + } + } + }); +} + +/** + * Add or remove class(es) from the matched elements, depending on either the + * class's presence or the value of the switch argument. Also accepts a + * `function`. + * + * @category Attributes + * @example + * + * ```js + * $('.apple.green').toggleClass('fruit green red').html(); + * //=>
  • Apple
  • + * + * $('.apple.green').toggleClass('fruit green red', true).html(); + * //=>
  • Apple
  • + * ``` + * + * @param value - Name of the class. Can also be a function. + * @param stateVal - If specified the state of the class. + * @returns The instance itself. + * @see {@link https://api.jquery.com/toggleClass/} + */ +export function toggleClass>( + this: R, + value?: + | string + | (( + this: Element, + i: number, + className: string, + stateVal?: boolean, + ) => string), + stateVal?: boolean, +): R { + // Support functions + if (typeof value === 'function') { + return domEach(this, (el, i) => { + if (isTag(el)) { + toggleClass.call( + [el], + value.call(el, i, el.attribs['class'] || '', stateVal), + stateVal, + ); + } + }); + } + + // Return if no value or not a string or function + if (!value || typeof value !== 'string') return this; + + const classNames = value.split(rspace); + const numClasses = classNames.length; + const state = typeof stateVal === 'boolean' ? (stateVal ? 1 : -1) : 0; + const numElements = this.length; + + for (let i = 0; i < numElements; i++) { + const el = this[i]; + // If selected element isn't a tag, move on + if (!isTag(el)) continue; + + const elementClasses = splitNames(el.attribs['class']); + + // Check if class already exists + for (let j = 0; j < numClasses; j++) { + // Check if the class name is currently defined + const index = elementClasses.indexOf(classNames[j]); + + // Add if stateValue === true or we are toggling and there is no value + if (state >= 0 && index < 0) { + elementClasses.push(classNames[j]); + } else if (state <= 0 && index >= 0) { + // Otherwise remove but only if the item exists + elementClasses.splice(index, 1); + } + } + + el.attribs['class'] = elementClasses.join(' '); + } + + return this; +} diff --git a/frontend/node_modules/cheerio/src/api/css.spec.ts b/frontend/node_modules/cheerio/src/api/css.spec.ts new file mode 100644 index 0000000..f6455c2 --- /dev/null +++ b/frontend/node_modules/cheerio/src/api/css.spec.ts @@ -0,0 +1,138 @@ +import { describe, it, expect, beforeEach } from 'vitest'; +import { load, type Cheerio } from '../index.js'; +import type { Element } from 'domhandler'; +import { cheerio, mixedText } from '../__fixtures__/fixtures.js'; + +describe('$(...)', () => { + describe('.css', () => { + it('(prop): should return a css property value', () => { + const el = cheerio('
  • '); + expect(el.css('hai')).toBe('there'); + }); + + it('([prop1, prop2]): should return the specified property values as an object', () => { + const el = cheerio( + '
  • ', + ); + expect(el.css(['margin', 'color'])).toStrictEqual({ + margin: '1px', + color: 'blue', + }); + }); + + it('(prop, val): should set a css property', () => { + const el = cheerio('
  • '); + el.css('color', 'red'); + expect(el.attr('style')).toBe('margin: 0; color: red;'); + expect(el.eq(1).attr('style')).toBe('color: red;'); + }); + + it('(prop, val) : should skip text nodes', () => { + const $text = load(mixedText); + const $body = $text($text('body')[0].children); + + $body.css('test', 'value'); + + expect($text('body').html()).toBe( + '1TEXT2', + ); + }); + + it('(prop, ""): should unset a css property', () => { + const el = cheerio('
  • '); + el.css('padding', ''); + expect(el.attr('style')).toBe('margin: 0;'); + }); + + it('(any, val): should ignore unsupported prop types', () => { + const el = cheerio('
  • '); + el.css(123 as never, 'test'); + expect(el.attr('style')).toBe('padding: 1px;'); + }); + + it('(prop): should not mangle embedded urls', () => { + const el = cheerio( + '
  • ', + ); + expect(el.css('background-image')).toBe( + 'url(http://example.com/img.png)', + ); + }); + + it('(prop): should ignore blank properties', () => { + const el = cheerio('
  • '); + expect(el.css()).toStrictEqual({ color: '#aaa' }); + }); + + it('(prop): should ignore blank values', () => { + const el = cheerio('
  • '); + expect(el.css()).toStrictEqual({ position: 'absolute' }); + }); + + it('(prop): should return undefined for unmatched elements', () => { + const $ = load('
  • '); + expect($('ul').css('background-image')).toBeUndefined(); + }); + + it('(prop): should return undefined for unmatched styles', () => { + const el = cheerio('
  • '); + expect(el.css('margin')).toBeUndefined(); + }); + + describe('(prop, function):', () => { + let $el: Cheerio; + beforeEach(() => { + const $ = load( + '
    ', + ); + $el = $('div'); + }); + + it('should iterate over the selection', () => { + let count = 0; + $el.css('margin', function (idx, value) { + expect(idx).toBe(count); + expect(value).toBe(`${count}px`); + expect(this).toBe($el[count]); + count++; + return undefined; + }); + expect(count).toBe(3); + }); + + it('should set each attribute independently', () => { + const values = ['4px', '', undefined]; + $el.css('margin', (idx) => values[idx]); + expect($el.eq(0).attr('style')).toBe('margin: 4px;'); + expect($el.eq(1).attr('style')).toBe(''); + expect($el.eq(2).attr('style')).toBe('margin: 2px;'); + }); + }); + + it('(obj): should set each key and val', () => { + const el = cheerio('
  • '); + el.css({ foo: 0 } as never); + expect(el.eq(0).attr('style')).toBe('padding: 0; foo: 0;'); + expect(el.eq(1).attr('style')).toBe('foo: 0;'); + }); + + describe('parser', () => { + it('should allow any whitespace between declarations', () => { + const el = cheerio('
  • '); + expect(el.css(['one', 'two', 'five'])).toStrictEqual({ + one: '0', + two: '1', + }); + }); + + it('should add malformed values to previous field (#1134)', () => { + const el = cheerio( + '', + ); + expect(el.css('background-image')).toStrictEqual( + 'url(data:image/png;base64,iVBORw0KGgo)', + ); + }); + }); + }); +}); diff --git a/frontend/node_modules/cheerio/src/api/css.ts b/frontend/node_modules/cheerio/src/api/css.ts new file mode 100644 index 0000000..9a1564a --- /dev/null +++ b/frontend/node_modules/cheerio/src/api/css.ts @@ -0,0 +1,224 @@ +import { domEach } from '../utils.js'; +import { isTag, type Element, type AnyNode } from 'domhandler'; +import type { Cheerio } from '../cheerio.js'; + +/** + * Get the value of a style property for the first element in the set of matched + * elements. + * + * @category CSS + * @param names - Optionally the names of the properties of interest. + * @returns A map of all of the style properties. + * @see {@link https://api.jquery.com/css/} + */ +export function css( + this: Cheerio, + names?: string[], +): Record | undefined; +/** + * Get the value of a style property for the first element in the set of matched + * elements. + * + * @category CSS + * @param name - The name of the property. + * @returns The property value for the given name. + * @see {@link https://api.jquery.com/css/} + */ +export function css( + this: Cheerio, + name: string, +): string | undefined; +/** + * Set one CSS property for every matched element. + * + * @category CSS + * @param prop - The name of the property. + * @param val - The new value. + * @returns The instance itself. + * @see {@link https://api.jquery.com/css/} + */ +export function css( + this: Cheerio, + prop: string, + val: + | string + | ((this: Element, i: number, style: string) => string | undefined), +): Cheerio; +/** + * Set multiple CSS properties for every matched element. + * + * @category CSS + * @param map - A map of property names and values. + * @returns The instance itself. + * @see {@link https://api.jquery.com/css/} + */ +export function css( + this: Cheerio, + map: Record, +): Cheerio; +/** + * Set multiple CSS properties for every matched element. + * + * @category CSS + * @param prop - The names of the properties. + * @param val - The new values. + * @returns The instance itself. + * @see {@link https://api.jquery.com/css/} + */ +export function css( + this: Cheerio, + prop?: string | string[] | Record, + val?: + | string + | ((this: Element, i: number, style: string) => string | undefined), +): Cheerio | Record | string | undefined { + if ( + (prop != null && val != null) || + // When `prop` is a "plain" object + (typeof prop === 'object' && !Array.isArray(prop)) + ) { + return domEach(this, (el, i) => { + if (isTag(el)) { + // `prop` can't be an array here anymore. + setCss(el, prop as string, val, i); + } + }); + } + + if (this.length === 0) { + return undefined; + } + + return getCss(this[0], prop as string); +} + +/** + * Set styles of all elements. + * + * @private + * @param el - Element to set style of. + * @param prop - Name of property. + * @param value - Value to set property to. + * @param idx - Optional index within the selection. + */ +function setCss( + el: Element, + prop: string | Record, + value: + | string + | ((this: Element, i: number, style: string) => string | undefined) + | undefined, + idx: number, +) { + if (typeof prop === 'string') { + const styles = getCss(el); + + const val = + typeof value === 'function' ? value.call(el, idx, styles[prop]) : value; + + if (val === '') { + delete styles[prop]; + } else if (val != null) { + styles[prop] = val; + } + + el.attribs['style'] = stringify(styles); + } else if (typeof prop === 'object') { + const keys = Object.keys(prop); + for (let i = 0; i < keys.length; i++) { + const k = keys[i]; + setCss(el, k, prop[k], i); + } + } +} + +/** + * Get the parsed styles of the first element. + * + * @private + * @category CSS + * @param el - Element to get styles from. + * @param props - Optionally the names of the properties of interest. + * @returns The parsed styles. + */ +function getCss(el: AnyNode, props?: string[]): Record; +/** + * Get a property from the parsed styles of the first element. + * + * @private + * @category CSS + * @param el - Element to get styles from. + * @param prop - Name of the prop. + * @returns The value of the property. + */ +function getCss(el: AnyNode, prop: string): string | undefined; +function getCss( + el: AnyNode, + prop?: string | string[], +): Record | string | undefined { + if (!el || !isTag(el)) return; + + const styles = parse(el.attribs['style']); + if (typeof prop === 'string') { + return styles[prop]; + } + if (Array.isArray(prop)) { + const newStyles: Record = {}; + for (const item of prop) { + if (styles[item] != null) { + newStyles[item] = styles[item]; + } + } + return newStyles; + } + return styles; +} + +/** + * Stringify `obj` to styles. + * + * @private + * @category CSS + * @param obj - Object to stringify. + * @returns The serialized styles. + */ +function stringify(obj: Record): string { + return Object.keys(obj).reduce( + (str, prop) => `${str}${str ? ' ' : ''}${prop}: ${obj[prop]};`, + '', + ); +} + +/** + * Parse `styles`. + * + * @private + * @category CSS + * @param styles - Styles to be parsed. + * @returns The parsed styles. + */ +function parse(styles: string): Record { + styles = (styles || '').trim(); + + if (!styles) return {}; + + const obj: Record = {}; + + let key: string | undefined; + + for (const str of styles.split(';')) { + const n = str.indexOf(':'); + // If there is no :, or if it is the first/last character, add to the previous item's value + if (n < 1 || n === str.length - 1) { + const trimmed = str.trimEnd(); + if (trimmed.length > 0 && key !== undefined) { + obj[key] += `;${trimmed}`; + } + } else { + key = str.slice(0, n).trim(); + obj[key] = str.slice(n + 1).trim(); + } + } + + return obj; +} diff --git a/frontend/node_modules/cheerio/src/api/extract.spec.ts b/frontend/node_modules/cheerio/src/api/extract.spec.ts new file mode 100644 index 0000000..b243212 --- /dev/null +++ b/frontend/node_modules/cheerio/src/api/extract.spec.ts @@ -0,0 +1,121 @@ +import { describe, it, expect } from 'vitest'; +import * as fixtures from '../__fixtures__/fixtures.js'; +import { load } from '../load-parse.js'; + +interface RedSelObject { + red: string | undefined; + sel: string | undefined; +} + +interface RedSelMultipleObject { + red: string[]; + sel: string[]; +} + +describe('$.extract', () => { + it('() : should extract values for selectors', () => { + const $ = load(fixtures.eleven); + const $root = load(fixtures.eleven).root(); + // An empty object should lead to an empty extraction. + + // $ExpectType ExtractedMap<{}> + const emptyExtract = $root.extract({}); + expect(emptyExtract).toStrictEqual({}); + // Non-existent values should be undefined. + + // $ExpectType ExtractedMap<{ foo: string; }> + const simpleExtract = $root.extract({ foo: 'bar' }); + expect(simpleExtract).toStrictEqual({ foo: undefined }); + + // Existing values should be extracted. + expect<{ red: string | undefined }>( + $root.extract({ red: '.red' }), + ).toStrictEqual({ + red: 'Four', + }); + expect( + $root.extract({ red: '.red', sel: '.sel' }), + ).toStrictEqual({ + red: 'Four', + sel: 'Three', + }); + // Descriptors for extractions should be supported + expect( + $root.extract({ + red: { selector: '.red' }, + sel: { selector: '.sel' }, + }), + ).toStrictEqual({ red: 'Four', sel: 'Three' }); + // Should support extraction of multiple values. + + // $ExpectType ExtractedMap<{ red: [string]; sel: [string]; }> + const multipleExtract = $root.extract({ + red: ['.red'], + sel: ['.sel'], + }); + expect(multipleExtract).toStrictEqual({ + red: ['Four', 'Five', 'Nine'], + sel: ['Three', 'Nine', 'Eleven'], + }); + // Should support custom `prop`s. + expect( + $root.extract({ + red: { selector: '.red', value: 'outerHTML' }, + sel: { selector: '.sel', value: 'tagName' }, + }), + ).toStrictEqual({ red: '
  • Four
  • ', sel: 'LI' }); + // Should support custom `prop`s for multiple values. + expect<{ red: string[] }>( + $root.extract({ + red: [{ selector: '.red', value: 'outerHTML' }], + }), + ).toStrictEqual({ + red: [ + '
  • Four
  • ', + '
  • Five
  • ', + '
  • Nine
  • ', + ], + }); + // Should support custom extraction functions. + expect<{ red: string | undefined }>( + $root.extract({ + red: { + selector: '.red', + value: (el, key) => `${key}=${$(el).text()}`, + }, + }), + ).toStrictEqual({ red: 'red=Four' }); + // Should support custom extraction functions for multiple values. + expect<{ red: string[] }>( + $root.extract({ + red: [ + { + selector: '.red', + value: (el, key) => `${key}=${$(el).text()}`, + }, + ], + }), + ).toStrictEqual({ red: ['red=Four', 'red=Five', 'red=Nine'] }); + // Should support extraction objects + + // $ExpectType ExtractedMap<{ section: { selector: string; value: { red: string; sel: string; }; }; }> + const subExtractObject = $root.extract({ + section: { + selector: 'ul:nth(1)', + value: { + red: '.red', + sel: '.blue', + }, + }, + }); + + expect<{ section: RedSelObject | undefined }>( + subExtractObject, + ).toStrictEqual({ + section: { + red: 'Five', + sel: 'Seven', + }, + }); + }); +}); diff --git a/frontend/node_modules/cheerio/src/api/extract.ts b/frontend/node_modules/cheerio/src/api/extract.ts new file mode 100644 index 0000000..10bd529 --- /dev/null +++ b/frontend/node_modules/cheerio/src/api/extract.ts @@ -0,0 +1,92 @@ +import type { AnyNode, Element } from 'domhandler'; +import type { Cheerio } from '../cheerio.js'; +import type { prop } from './attributes.js'; + +type ExtractDescriptorFn = ( + el: Element, + key: string, + // TODO: This could be typed with ExtractedMap + obj: Record, +) => unknown; + +interface ExtractDescriptor { + selector: string; + value?: string | ExtractDescriptorFn | ExtractMap; +} + +type ExtractValue = string | ExtractDescriptor | [string | ExtractDescriptor]; + +export interface ExtractMap { + [key: string]: ExtractValue; +} + +type ExtractedValue = V extends [ + string | ExtractDescriptor, +] + ? NonNullable>[] + : V extends string + ? string | undefined + : V extends ExtractDescriptor + ? V['value'] extends ExtractMap + ? ExtractedMap | undefined + : V['value'] extends ExtractDescriptorFn + ? ReturnType | undefined + : ReturnType | undefined + : never; + +export type ExtractedMap = { + [key in keyof M]: ExtractedValue; +}; + +function getExtractDescr( + descr: string | ExtractDescriptor, +): Required { + if (typeof descr === 'string') { + return { selector: descr, value: 'textContent' }; + } + + return { + selector: descr.selector, + value: descr.value ?? 'textContent', + }; +} + +/** + * Extract multiple values from a document, and store them in an object. + * + * @param map - An object containing key-value pairs. The keys are the names of + * the properties to be created on the object, and the values are the + * selectors to be used to extract the values. + * @returns An object containing the extracted values. + */ +export function extract( + this: Cheerio, + map: M, +): ExtractedMap { + const ret: Record = {}; + + for (const key in map) { + const descr = map[key]; + const isArray = Array.isArray(descr); + + const { selector, value } = getExtractDescr(isArray ? descr[0] : descr); + + const fn: ExtractDescriptorFn = + typeof value === 'function' + ? value + : typeof value === 'string' + ? (el: Element) => this._make(el).prop(value) + : (el: Element) => this._make(el).extract(value); + + if (isArray) { + ret[key] = this._findBySelector(selector, Number.POSITIVE_INFINITY) + .map((_, el) => fn(el, key, ret)) + .get(); + } else { + const $ = this._findBySelector(selector, 1); + ret[key] = $.length > 0 ? fn($[0], key, ret) : undefined; + } + } + + return ret as ExtractedMap; +} diff --git a/frontend/node_modules/cheerio/src/api/forms.spec.ts b/frontend/node_modules/cheerio/src/api/forms.spec.ts new file mode 100644 index 0000000..ddd3d75 --- /dev/null +++ b/frontend/node_modules/cheerio/src/api/forms.spec.ts @@ -0,0 +1,155 @@ +import { describe, it, expect, beforeEach } from 'vitest'; +import { type CheerioAPI } from '../index.js'; +import { cheerio, forms } from '../__fixtures__/fixtures.js'; + +describe('$(...)', () => { + let $: CheerioAPI; + + beforeEach(() => { + $ = cheerio.load(forms); + }); + + describe('.serializeArray', () => { + it('() : should get form controls', () => { + expect($('form#simple').serializeArray()).toStrictEqual([ + { + name: 'fruit', + value: 'Apple', + }, + ]); + }); + + it('() : should get nested form controls', () => { + expect($('form#nested').serializeArray()).toHaveLength(2); + const data = $('form#nested').serializeArray(); + data.sort((a, b) => (a.value > b.value ? 1 : -1)); + expect(data).toStrictEqual([ + { + name: 'fruit', + value: 'Apple', + }, + { + name: 'vegetable', + value: 'Carrot', + }, + ]); + }); + + it('() : should not get disabled form controls', () => { + expect($('form#disabled').serializeArray()).toStrictEqual([]); + }); + + it('() : should not get form controls with the wrong type', () => { + expect($('form#submit').serializeArray()).toStrictEqual([ + { + name: 'fruit', + value: 'Apple', + }, + ]); + }); + + it('() : should get selected options', () => { + expect($('form#select').serializeArray()).toStrictEqual([ + { + name: 'fruit', + value: 'Orange', + }, + ]); + }); + + it('() : should not get unnamed form controls', () => { + expect($('form#unnamed').serializeArray()).toStrictEqual([ + { + name: 'fruit', + value: 'Apple', + }, + ]); + }); + + it('() : should get multiple selected options', () => { + expect($('form#multiple').serializeArray()).toHaveLength(2); + const data = $('form#multiple').serializeArray(); + data.sort((a, b) => (a.value > b.value ? 1 : -1)); + expect(data).toStrictEqual([ + { + name: 'fruit', + value: 'Apple', + }, + { + name: 'fruit', + value: 'Orange', + }, + ]); + }); + + it('() : should get individually selected elements', () => { + const data = $('form#nested input').serializeArray(); + data.sort((a, b) => (a.value > b.value ? 1 : -1)); + expect(data).toStrictEqual([ + { + name: 'fruit', + value: 'Apple', + }, + { + name: 'vegetable', + value: 'Carrot', + }, + ]); + }); + + it('() : should standardize line breaks', () => { + expect($('form#textarea').serializeArray()).toStrictEqual([ + { + name: 'fruits', + value: 'Apple\r\nOrange', + }, + ]); + }); + + it("() : shouldn't serialize the empty string", () => { + expect($('').serializeArray()).toStrictEqual([]); + expect( + $('').serializeArray(), + ).toStrictEqual([]); + expect( + $('').serializeArray(), + ).toStrictEqual([ + { + name: 'fruit', + value: 'pineapple', + }, + ]); + }); + + it('() : should serialize inputs without value attributes', () => { + expect($('').serializeArray()).toStrictEqual([ + { + name: 'fruit', + value: '', + }, + ]); + }); + }); + + describe('.serialize', () => { + it('() : should get form controls', () => { + expect($('form#simple').serialize()).toBe('fruit=Apple'); + }); + + it('() : should get nested form controls', () => { + expect($('form#nested').serialize()).toBe('fruit=Apple&vegetable=Carrot'); + }); + + it('() : should not get disabled form controls', () => { + expect($('form#disabled').serialize()).toBe(''); + }); + + it('() : should get multiple selected options', () => { + expect($('form#multiple').serialize()).toBe('fruit=Apple&fruit=Orange'); + }); + + it("() : should encode spaces as +'s", () => { + expect($('form#spaces').serialize()).toBe('fruit=Blood+orange'); + }); + }); +}); diff --git a/frontend/node_modules/cheerio/src/api/forms.ts b/frontend/node_modules/cheerio/src/api/forms.ts new file mode 100644 index 0000000..902f919 --- /dev/null +++ b/frontend/node_modules/cheerio/src/api/forms.ts @@ -0,0 +1,103 @@ +import { isTag, type AnyNode } from 'domhandler'; +import type { Cheerio } from '../cheerio.js'; + +/* + * https://github.com/jquery/jquery/blob/2.1.3/src/manipulation/var/rcheckableType.js + * https://github.com/jquery/jquery/blob/2.1.3/src/serialize.js + */ +const submittableSelector = 'input,select,textarea,keygen'; +const r20 = /%20/g; +const rCRLF = /\r?\n/g; + +/** + * Encode a set of form elements as a string for submission. + * + * @category Forms + * @example + * + * ```js + * $('
    ').serialize(); + * //=> 'foo=bar' + * ``` + * + * @returns The serialized form. + * @see {@link https://api.jquery.com/serialize/} + */ +export function serialize(this: Cheerio): string { + // Convert form elements into name/value objects + const arr = this.serializeArray(); + + // Serialize each element into a key/value string + const retArr = arr.map( + (data) => + `${encodeURIComponent(data.name)}=${encodeURIComponent(data.value)}`, + ); + + // Return the resulting serialization + return retArr.join('&').replace(r20, '+'); +} + +/** + * Encode a set of form elements as an array of names and values. + * + * @category Forms + * @example + * + * ```js + * $('
    ').serializeArray(); + * //=> [ { name: 'foo', value: 'bar' } ] + * ``` + * + * @returns The serialized form. + * @see {@link https://api.jquery.com/serializeArray/} + */ +export function serializeArray( + this: Cheerio, +): { + name: string; + value: string; +}[] { + // Resolve all form elements from either forms or collections of form elements + return this.map((_, elem) => { + const $elem = this._make(elem); + if (isTag(elem) && elem.name === 'form') { + return $elem.find(submittableSelector).toArray(); + } + return $elem.filter(submittableSelector).toArray(); + }) + .filter( + // Verify elements have a name (`attr.name`) and are not disabled (`:enabled`) + '[name!=""]:enabled' + + // And cannot be clicked (`[type=submit]`) or are used in `x-www-form-urlencoded` (`[type=file]`) + ':not(:submit, :button, :image, :reset, :file)' + + // And are either checked/don't have a checkable state + ':matches([checked], :not(:checkbox, :radio))', + // Convert each of the elements to its value(s) + ) + .map< + AnyNode, + { + name: string; + value: string; + } + >((_, elem) => { + const $elem = this._make(elem); + const name = $elem.attr('name') as string; // We have filtered for elements with a name before. + // If there is no value set (e.g. `undefined`, `null`), then default value to empty + const value = $elem.val() ?? ''; + + // If we have an array of values (e.g. `'; + +// Comments +const comment = ''; +const conditional = + ''; + +// Text +const text = 'lorem ipsum'; + +// Script +const script = ''; +const scriptEmpty = ''; + +// Style +const style = ''; +const styleEmpty = ''; + +// Directives +const directive = ''; + +function rootTest(root: Document) { + expect(root).toHaveProperty('type', 'root'); + + expect(root.nextSibling).toBe(null); + expect(root.previousSibling).toBe(null); + expect(root.parentNode).toBe(null); + + const child = root.childNodes[0]; + expect(child.parentNode).toBe(root); +} + +describe('parse', () => { + describe('evaluate', () => { + it(`should parse basic empty tags: ${basic}`, () => { + const [tag] = parse(basic, defaultOpts, true, null).children as Element[]; + expect(tag.type).toBe('tag'); + expect(tag.tagName).toBe('html'); + expect(tag.childNodes).toHaveLength(2); + }); + + it(`should handle sibling tags: ${siblings}`, () => { + const dom = parse(siblings, defaultOpts, false, null) + .children as Element[]; + const [h2, p] = dom; + + expect(dom).toHaveLength(2); + expect(h2.tagName).toBe('h2'); + expect(p.tagName).toBe('p'); + }); + + it(`should handle single tags: ${single}`, () => { + const [tag] = parse(single, defaultOpts, false, null) + .children as Element[]; + expect(tag.type).toBe('tag'); + expect(tag.tagName).toBe('br'); + expect(tag.childNodes).toHaveLength(0); + }); + + it(`should handle malformatted single tags: ${singleWrong}`, () => { + const [tag] = parse(singleWrong, defaultOpts, false, null) + .children as Element[]; + expect(tag.type).toBe('tag'); + expect(tag.tagName).toBe('br'); + expect(tag.childNodes).toHaveLength(0); + }); + + it(`should handle tags with children: ${children}`, () => { + const [tag] = parse(children, defaultOpts, true, null) + .children as Element[]; + expect(tag.type).toBe('tag'); + expect(tag.tagName).toBe('html'); + expect(tag.childNodes).toBeTruthy(); + expect(tag.childNodes[1]).toHaveProperty('tagName', 'body'); + expect((tag.childNodes[1] as Element).childNodes).toHaveLength(1); + }); + + it(`should handle tags with children: ${li}`, () => { + const [tag] = parse(li, defaultOpts, false, null).children as Element[]; + expect(tag.childNodes).toHaveLength(1); + expect(tag.childNodes[0]).toHaveProperty('data', 'Durian'); + }); + + it(`should handle tags with attributes: ${attributes}`, () => { + const attrs = parse(attributes, defaultOpts, false, null) + .children[0] as Element; + expect(attrs.attribs).toBeTruthy(); + expect(attrs.attribs).toHaveProperty('src', 'hello.png'); + expect(attrs.attribs).toHaveProperty('alt', 'man waving'); + }); + + it(`should handle value-less attributes: ${noValueAttribute}`, () => { + const attrs = parse(noValueAttribute, defaultOpts, false, null) + .children[0] as Element; + expect(attrs.attribs).toBeTruthy(); + expect(attrs.attribs).toHaveProperty('disabled', ''); + }); + + it(`should handle comments: ${comment}`, () => { + const elem = parse(comment, defaultOpts, false, null).children[0]; + expect(elem.type).toBe('comment'); + expect(elem).toHaveProperty('data', ' sexy '); + }); + + it(`should handle conditional comments: ${conditional}`, () => { + const elem = parse(conditional, defaultOpts, false, null).children[0]; + expect(elem.type).toBe('comment'); + expect(elem).toHaveProperty( + 'data', + conditional.replace('', ''), + ); + }); + + it(`should handle text: ${text}`, () => { + const text_ = parse(text, defaultOpts, false, null).children[0]; + expect(text_.type).toBe('text'); + expect(text_).toHaveProperty('data', 'lorem ipsum'); + }); + + it(`should handle script tags: ${script}`, () => { + const script_ = parse(script, defaultOpts, false, null) + .children[0] as Element; + expect(script_.type).toBe('script'); + expect(script_.tagName).toBe('script'); + expect(script_.attribs).toHaveProperty('type', 'text/javascript'); + expect(script_.childNodes).toHaveLength(1); + expect(script_.childNodes[0].type).toBe('text'); + expect(script_.childNodes[0]).toHaveProperty( + 'data', + 'alert("hi world!");', + ); + }); + + it(`should handle style tags: ${style}`, () => { + const style_ = parse(style, defaultOpts, false, null) + .children[0] as Element; + expect(style_.type).toBe('style'); + expect(style_.tagName).toBe('style'); + expect(style_.attribs).toHaveProperty('type', 'text/css'); + expect(style_.childNodes).toHaveLength(1); + expect(style_.childNodes[0].type).toBe('text'); + expect(style_.childNodes[0]).toHaveProperty( + 'data', + ' h2 { color:blue; } ', + ); + }); + + it(`should handle directives: ${directive}`, () => { + const elem = parse(directive, defaultOpts, true, null).children[0]; + expect(elem.type).toBe('directive'); + expect(elem).toHaveProperty('data', '!DOCTYPE html'); + expect(elem).toHaveProperty('name', '!doctype'); + }); + }); + + describe('.parse', () => { + // Root test utility + + it(`should add root to: ${basic}`, () => { + const root = parse(basic, defaultOpts, true, null); + rootTest(root); + expect(root.childNodes).toHaveLength(1); + expect(root.childNodes[0]).toHaveProperty('tagName', 'html'); + }); + + it(`should add root to: ${siblings}`, () => { + const root = parse(siblings, defaultOpts, false, null); + rootTest(root); + expect(root.childNodes).toHaveLength(2); + expect(root.childNodes[0]).toHaveProperty('tagName', 'h2'); + expect(root.childNodes[1]).toHaveProperty('tagName', 'p'); + expect(root.childNodes[1].parent).toBe(root); + }); + + it(`should add root to: ${comment}`, () => { + const root = parse(comment, defaultOpts, false, null); + rootTest(root); + expect(root.childNodes).toHaveLength(1); + expect(root.childNodes[0].type).toBe('comment'); + }); + + it(`should add root to: ${text}`, () => { + const root = parse(text, defaultOpts, false, null); + rootTest(root); + expect(root.childNodes).toHaveLength(1); + expect(root.childNodes[0].type).toBe('text'); + }); + + it(`should add root to: ${scriptEmpty}`, () => { + const root = parse(scriptEmpty, defaultOpts, false, null); + rootTest(root); + expect(root.childNodes).toHaveLength(1); + expect(root.childNodes[0].type).toBe('script'); + }); + + it(`should add root to: ${styleEmpty}`, () => { + const root = parse(styleEmpty, defaultOpts, false, null); + rootTest(root); + expect(root.childNodes).toHaveLength(1); + expect(root.childNodes[0].type).toBe('style'); + }); + + it(`should add root to: ${directive}`, () => { + const root = parse(directive, defaultOpts, true, null); + rootTest(root); + expect(root.childNodes).toHaveLength(2); + expect(root.childNodes[0].type).toBe('directive'); + }); + + it('should simply return root', () => { + const oldroot = parse(basic, defaultOpts, true, null); + const root = parse(oldroot, defaultOpts, true, null); + expect(root).toBe(oldroot); + rootTest(root); + expect(root.childNodes).toHaveLength(1); + expect(root.childNodes[0]).toHaveProperty('tagName', 'html'); + }); + + it('should expose the DOM level 1 API', () => { + const root = parse( + '

    ', + defaultOpts, + false, + null, + ).childNodes[0] as Element; + const childNodes = root.childNodes as Element[]; + + expect(childNodes).toHaveLength(3); + + expect(root.tagName).toBe('div'); + expect(root.firstChild).toBe(childNodes[0]); + expect(root.lastChild).toBe(childNodes[2]); + + expect(childNodes[0].tagName).toBe('a'); + expect(childNodes[0].previousSibling).toBe(null); + expect(childNodes[0].nextSibling).toBe(childNodes[1]); + expect(childNodes[0].parentNode).toBe(root); + expect((childNodes[0] as Element).childNodes).toHaveLength(0); + expect(childNodes[0].firstChild).toBe(null); + expect(childNodes[0].lastChild).toBe(null); + + expect(childNodes[1].tagName).toBe('span'); + expect(childNodes[1].previousSibling).toBe(childNodes[0]); + expect(childNodes[1].nextSibling).toBe(childNodes[2]); + expect(childNodes[1].parentNode).toBe(root); + expect(childNodes[1].childNodes).toHaveLength(0); + expect(childNodes[1].firstChild).toBe(null); + expect(childNodes[1].lastChild).toBe(null); + + expect(childNodes[2].tagName).toBe('p'); + expect(childNodes[2].previousSibling).toBe(childNodes[1]); + expect(childNodes[2].nextSibling).toBe(null); + expect(childNodes[2].parentNode).toBe(root); + expect(childNodes[2].childNodes).toHaveLength(0); + expect(childNodes[2].firstChild).toBe(null); + expect(childNodes[2].lastChild).toBe(null); + }); + + it('Should parse less than or equal sign sign', () => { + const root = parse('A<=B', defaultOpts, false, null); + const { childNodes } = root; + + expect(childNodes[0]).toHaveProperty('tagName', 'i'); + expect((childNodes[0] as Element).childNodes[0]).toHaveProperty( + 'data', + 'A', + ); + expect(childNodes[1]).toHaveProperty('data', '<='); + expect(childNodes[2]).toHaveProperty('tagName', 'i'); + expect((childNodes[2] as Element).childNodes[0]).toHaveProperty( + 'data', + 'B', + ); + }); + + it('Should ignore unclosed CDATA', () => { + const root = parse( + '', + defaultOpts, + false, + null, + ); + const childNodes = root.childNodes as Element[]; + + expect(childNodes[0].tagName).toBe('a'); + expect(childNodes[1].tagName).toBe('script'); + expect(childNodes[1].childNodes[0]).toHaveProperty( + 'data', + 'foo // to documents', () => { + const root = parse('', defaultOpts, true, null); + const childNodes = root.childNodes as Element[]; + + expect(childNodes[0].tagName).toBe('html'); + expect(childNodes[0].childNodes[0]).toHaveProperty('tagName', 'head'); + }); + + it('Should implicitly create around ', () => { + const root = parse( + '
    bar
    ', + defaultOpts, + false, + null, + ); + const childNodes = root.childNodes as Element[]; + + expect(childNodes[0].tagName).toBe('table'); + expect(childNodes[0].childNodes.length).toBe(1); + expect(childNodes[0].childNodes[0]).toHaveProperty('tagName', 'tbody'); + expect((childNodes[0] as any).childNodes[0].childNodes[0]).toHaveProperty( + 'tagName', + 'tr', + ); + expect( + (childNodes[0] as any).childNodes[0].childNodes[0].childNodes[0] + .tagName, + ).toBe('td'); + expect( + (childNodes[0] as any).childNodes[0].childNodes[0].childNodes[0] + .childNodes[0].data, + ).toBe('bar'); + }); + + it('Should parse custom tag ', () => { + const root = parse('test', defaultOpts, false, null); + const childNodes = root.childNodes as Element[]; + + expect(childNodes.length).toBe(1); + expect(childNodes[0].tagName).toBe('line'); + expect(childNodes[0].childNodes[0]).toHaveProperty('data', 'test'); + }); + + it('Should properly parse misnested table tags', () => { + const root = parse( + 'i1i2i3', + defaultOpts, + false, + null, + ); + const childNodes = root.childNodes as Element[]; + + expect(childNodes.length).toBe(3); + + for (let i = 0; i < childNodes.length; i++) { + const child = childNodes[i]; + expect(child.tagName).toBe('tr'); + expect(child.childNodes[0]).toHaveProperty('tagName', 'td'); + expect((child.childNodes[0] as Element).childNodes[0]).toHaveProperty( + 'data', + `i${i + 1}`, + ); + } + }); + + it('Should correctly parse data url attributes', () => { + const html = + '
    '; + const expectedAttr = + 'font-family:"butcherman-caps"; src:url(data:font/opentype;base64,AAEA...);'; + const root = parse(html, defaultOpts, false, null); + const childNodes = root.childNodes as Element[]; + + expect(childNodes[0].attribs).toHaveProperty('style', expectedAttr); + }); + + it('Should treat tag content as text', () => { + const root = parse('<xmp><h2>', defaultOpts, false, null); + const childNodes = root.childNodes as Element[]; + + expect(childNodes[0].childNodes[0]).toHaveProperty('data', '

    '); + }); + + it('Should correctly parse malformed numbered entities', () => { + const root = parse('

    z&#

    ', defaultOpts, false, null); + const childNodes = root.childNodes as Element[]; + + expect(childNodes[0].childNodes[0]).toHaveProperty('data', 'z&#'); + }); + + it('Should correctly parse mismatched headings', () => { + const root = parse('

    Test

    ', defaultOpts, false, null); + const { childNodes } = root; + + expect(childNodes.length).toBe(2); + expect(childNodes[0]).toHaveProperty('tagName', 'h2'); + expect(childNodes[1]).toHaveProperty('tagName', 'div'); + }); + + it('Should correctly parse tricky
     content', () => {
    +      const root = parse(
    +        '
    \nA <- factor(A, levels = c("c","a","b"))\n
    ', + defaultOpts, + false, + null, + ); + const childNodes = root.childNodes as Element[]; + + expect(childNodes.length).toBe(1); + expect(childNodes[0].tagName).toBe('pre'); + expect(childNodes[0].childNodes[0]).toHaveProperty( + 'data', + 'A <- factor(A, levels = c("c","a","b"))\n', + ); + }); + + it('should pass the options for including the location info to parse5', () => { + const root = parse( + '

    Hello

    ', + { ...defaultOpts, sourceCodeLocationInfo: true }, + false, + null, + ); + const location = root.children[0].sourceCodeLocation; + + expect(typeof location).toBe('object'); + expect(location?.endOffset).toBe(12); + }); + }); +}); diff --git a/frontend/node_modules/cheerio/src/parse.ts b/frontend/node_modules/cheerio/src/parse.ts new file mode 100644 index 0000000..5706f14 --- /dev/null +++ b/frontend/node_modules/cheerio/src/parse.ts @@ -0,0 +1,105 @@ +import { removeElement } from 'domutils'; +import { + type AnyNode, + Document, + type ParentNode, + isDocument as checkIsDocument, +} from 'domhandler'; +import type { InternalOptions } from './options.js'; + +/** + * Get the parse function with options. + * + * @param parser - The parser function. + * @returns The parse function with options. + */ +export function getParse( + parser: ( + content: string, + options: InternalOptions, + isDocument: boolean, + context: ParentNode | null, + ) => Document, +) { + /** + * Parse a HTML string or a node. + * + * @param content - The HTML string or node. + * @param options - The parser options. + * @param isDocument - If `content` is a document. + * @param context - The context node in the DOM tree. + * @returns The parsed document node. + */ + return function parse( + content: string | Document | AnyNode | AnyNode[] | Buffer, + options: InternalOptions, + isDocument: boolean, + context: ParentNode | null, + ): Document { + if (typeof Buffer !== 'undefined' && Buffer.isBuffer(content)) { + content = content.toString(); + } + + if (typeof content === 'string') { + return parser(content, options, isDocument, context); + } + + const doc = content as AnyNode | AnyNode[] | Document; + + if (!Array.isArray(doc) && checkIsDocument(doc)) { + // If `doc` is already a root, just return it + return doc; + } + + // Add conent to new root element + const root = new Document([]); + + // Update the DOM using the root + update(doc, root); + + return root; + }; +} + +/** + * Update the dom structure, for one changed layer. + * + * @param newChilds - The new children. + * @param parent - The new parent. + * @returns The parent node. + */ +export function update( + newChilds: AnyNode[] | AnyNode, + parent: ParentNode | null, +): ParentNode | null { + // Normalize + const arr = Array.isArray(newChilds) ? newChilds : [newChilds]; + + // Update parent + if (parent) { + parent.children = arr; + } else { + parent = null; + } + + // Update neighbors + for (let i = 0; i < arr.length; i++) { + const node = arr[i]; + + // Cleanly remove existing nodes from their previous structures. + if (node.parent && node.parent.children !== arr) { + removeElement(node); + } + + if (parent) { + node.prev = arr[i - 1] || null; + node.next = arr[i + 1] || null; + } else { + node.prev = node.next = null; + } + + node.parent = parent; + } + + return parent; +} diff --git a/frontend/node_modules/cheerio/src/parsers/parse5-adapter.ts b/frontend/node_modules/cheerio/src/parsers/parse5-adapter.ts new file mode 100644 index 0000000..ca0d861 --- /dev/null +++ b/frontend/node_modules/cheerio/src/parsers/parse5-adapter.ts @@ -0,0 +1,66 @@ +import { + type AnyNode, + type Document, + type ParentNode, + isDocument, +} from 'domhandler'; +import { parse as parseDocument, parseFragment, serializeOuter } from 'parse5'; +import { adapter as htmlparser2Adapter } from 'parse5-htmlparser2-tree-adapter'; +import type { InternalOptions } from '../options.js'; + +/** + * Parse the content with `parse5` in the context of the given `ParentNode`. + * + * @param content - The content to parse. + * @param options - A set of options to use to parse. + * @param isDocument - Whether to parse the content as a full HTML document. + * @param context - The context in which to parse the content. + * @returns The parsed content. + */ +export function parseWithParse5( + content: string, + options: InternalOptions, + isDocument: boolean, + context: ParentNode | null, +): Document { + options.treeAdapter ??= htmlparser2Adapter; + + if (options.scriptingEnabled !== false) { + options.scriptingEnabled = true; + } + + return isDocument + ? parseDocument(content, options) + : parseFragment(context, content, options); +} + +const renderOpts = { treeAdapter: htmlparser2Adapter }; + +/** + * Renders the given DOM tree with `parse5` and returns the result as a string. + * + * @param dom - The DOM tree to render. + * @returns The rendered document. + */ +export function renderWithParse5(dom: AnyNode | ArrayLike): string { + /* + * `dom-serializer` passes over the special "root" node and renders the + * node's children in its place. To mimic this behavior with `parse5`, an + * equivalent operation must be applied to the input array. + */ + const nodes = 'length' in dom ? dom : [dom]; + for (let index = 0; index < nodes.length; index += 1) { + const node = nodes[index]; + if (isDocument(node)) { + Array.prototype.splice.call(nodes, index, 1, ...node.children); + } + } + + let result = ''; + for (let index = 0; index < nodes.length; index += 1) { + const node = nodes[index]; + result += serializeOuter(node, renderOpts); + } + + return result; +} diff --git a/frontend/node_modules/cheerio/src/slim.ts b/frontend/node_modules/cheerio/src/slim.ts new file mode 100644 index 0000000..440d0a6 --- /dev/null +++ b/frontend/node_modules/cheerio/src/slim.ts @@ -0,0 +1,33 @@ +/** + * @file Alternative entry point for Cheerio that always uses htmlparser2. This + * way, parse5 won't be loaded, saving some memory. + */ +import { type CheerioAPI, getLoad } from './load.js'; +import { type CheerioOptions } from './options.js'; +import { getParse } from './parse.js'; +import type { AnyNode } from 'domhandler'; +import render from 'dom-serializer'; +import { parseDocument } from 'htmlparser2'; + +export { contains, merge } from './static.js'; +export type * from './types.js'; +export type { Cheerio } from './cheerio.js'; +export type { CheerioOptions, HTMLParser2Options } from './options.js'; +export type { CheerioAPI } from './load.js'; + +/** + * Create a querying function, bound to a document created from the provided + * markup. + * + * @param content - Markup to be loaded. + * @param options - Options for the created instance. + * @param isDocument - Always `false` here, as we are always using + * `htmlparser2`. + * @returns The loaded document. + * @see {@link https://cheerio.js.org#loading} for additional usage information. + */ +export const load: ( + content: string | AnyNode | AnyNode[] | Buffer, + options?: CheerioOptions | null, + isDocument?: boolean, +) => CheerioAPI = getLoad(getParse(parseDocument), render); diff --git a/frontend/node_modules/cheerio/src/static.spec.ts b/frontend/node_modules/cheerio/src/static.spec.ts new file mode 100644 index 0000000..3f27234 --- /dev/null +++ b/frontend/node_modules/cheerio/src/static.spec.ts @@ -0,0 +1,325 @@ +import { describe, it, expect, beforeEach } from 'vitest'; +import { cheerio, food, eleven } from './__fixtures__/fixtures.js'; +import { type CheerioAPI } from './index.js'; + +describe('cheerio', () => { + describe('.html', () => { + it('() : should return innerHTML; $.html(obj) should return outerHTML', () => { + const $div = cheerio( + 'div', + '
    foobar
    ', + ); + const span = $div.children()[1]; + expect(cheerio(span).html()).toBe('bar'); + expect(cheerio.html(span)).toBe('bar'); + }); + + it('() : should accept an object, an array, or a cheerio object', () => { + const $span = cheerio('foo'); + expect(cheerio.html($span[0])).toBe('foo'); + expect(cheerio.html($span)).toBe('foo'); + }); + + it('() : should be able to set to an empty string', () => { + const $elem = cheerio('foo').html(''); + expect(cheerio.html($elem)).toBe(''); + }); + + it('() : does not render the root element', () => { + const $ = cheerio.load(''); + expect(cheerio.html($.root())).toBe( + '', + ); + }); + + it('(, , ) : does not render the root element', () => { + const $ = cheerio.load('
    a div
    a span'); + const $collection = $('div').add($.root()).add('span'); + const expected = + '
    a div
    a span
    a div
    a span'; + expect(cheerio.html($collection)).toBe(expected); + }); + + it('() : does not crash with `null` as `this` value', () => { + const { html } = cheerio; + expect(html.call(null as never)).toBe(''); + expect(html.call(null as never, '#nothing')).toBe(''); + }); + }); + + describe('.text', () => { + it('(cheerio object) : should return the text contents of the specified elements', () => { + const $ = cheerio.load('This is content.'); + expect(cheerio.text($('a'))).toBe('This is content.'); + }); + + it('(cheerio object) : should omit comment nodes', () => { + const $ = cheerio.load( + 'This is not a comment.', + ); + expect(cheerio.text($('a'))).toBe('This is not a comment.'); + }); + + it('(cheerio object) : should include text contents of children recursively', () => { + const $ = cheerio.load( + 'This is
    a child with another child and not a comment followed by one last child and some final
    text.
    ', + ); + expect(cheerio.text($('a'))).toBe( + 'This is a child with another child and not a comment followed by one last child and some final text.', + ); + }); + + it('() : should return the rendered text content of the root', () => { + const $ = cheerio.load( + 'This is
    a child with another child and not a comment followed by one last child and some final
    text.
    ', + ); + expect(cheerio.text($.root())).toBe( + 'This is a child with another child and not a comment followed by one last child and some final text.', + ); + }); + + it('(cheerio object) : should not omit script tags', () => { + const $ = cheerio.load(''); + expect(cheerio.text($.root())).toBe('console.log("test")'); + }); + + it('(cheerio object) : should omit style tags', () => { + const $ = cheerio.load( + '', + ); + expect($.text()).toBe('.cf-hidden { display: none; }'); + }); + + it('() : does not crash with `null` as `this` value', () => { + const { text } = cheerio; + expect(text.call(null as never)).toBe(''); + }); + }); + + describe('.parseHTML', () => { + const $ = cheerio.load(''); + + it('() : returns null', () => { + expect($.parseHTML()).toBe(null); + }); + + it('(null) : returns null', () => { + expect($.parseHTML(null)).toBe(null); + }); + + it('("") : returns null', () => { + expect($.parseHTML('')).toBe(null); + }); + + it('(largeHtmlString) : parses large HTML strings', () => { + const html = '
    '.repeat(10); + const nodes = $.parseHTML(html); + + expect(nodes.length).toBe(10); + expect(nodes).toBeInstanceOf(Array); + }); + + it('("'; + expect($.parseHTML(html)).toHaveLength(0); + }); + + it('("'; + expect($.parseHTML(html, true)[0]).toHaveProperty('tagName', 'script'); + }); + + it('("scriptAndNonScript) : preserves non-script nodes', () => { + const html = '
    '; + expect($.parseHTML(html)[0]).toHaveProperty('tagName', 'div'); + }); + + it('(scriptAndNonScript, true) : Preserves script position', () => { + const html = '
    '; + expect($.parseHTML(html, true)[0]).toHaveProperty('tagName', 'script'); + }); + + it('(text) : returns a text node', () => { + expect($.parseHTML('text')[0].type).toBe('text'); + }); + + it('(>text) : preserves leading whitespace', () => { + expect($.parseHTML('\t
    ')[0]).toHaveProperty('data', '\t'); + }); + + it('( text) : Leading spaces are treated as text nodes', () => { + expect($.parseHTML('
    ')[0].type).toBe('text'); + }); + + it('(html) : should preserve content', () => { + const html = '
    test div
    '; + expect(cheerio($.parseHTML(html)[0]).html()).toBe('test div'); + }); + + it('(malformedHtml) : should not break', () => { + expect($.parseHTML('')).toHaveLength(1); + }); + + it('(garbageInput) : should not cause an error', () => { + expect( + $.parseHTML('<#if>

    This is a test.

    <#/if>'), + ).toBeTruthy(); + }); + + it('(text) : should return an array that is not effected by DOM manipulation methods', () => { + const $div = cheerio.load('
    '); + const elems = $div.parseHTML(''); + + $div('div').append(elems); + + expect(elems).toHaveLength(2); + }); + + it('(html, context) : should ignore context argument', () => { + const $div = cheerio.load('
    '); + const elems = $div.parseHTML('', { foo: 123 }); + + $div('div').append(elems); + + expect(elems).toHaveLength(1); + }); + + it('(html, context, keepScripts) : should ignore context argument', () => { + const $div = cheerio.load('
    '); + const elems = $div.parseHTML( + '', + { foo: 123 }, + true, + ); + + $div('div').append(elems); + + expect(elems).toHaveLength(2); + }); + }); + + describe('.merge', () => { + const $ = cheerio.load(''); + + it('should be a function', () => { + expect(typeof $.merge).toBe('function'); + }); + + it('(arraylike, arraylike) : should modify the first array, but not the second', () => { + const arr1 = [1, 2, 3]; + const arr2 = [4, 5, 6]; + + const ret = $.merge(arr1, arr2); + expect(typeof ret).toBe('object'); + expect(Array.isArray(ret)).toBe(true); + expect(ret).toBe(arr1); + expect(arr1).toHaveLength(6); + expect(arr2).toHaveLength(3); + }); + + it('(arraylike, arraylike) : should handle objects that arent arrays, but are arraylike', () => { + const arr1: ArrayLike = { + length: 3, + 0: 'a', + 1: 'b', + 2: 'c', + }; + const arr2 = { + length: 3, + 0: 'd', + 1: 'e', + 2: 'f', + }; + + $.merge(arr1, arr2); + expect(arr1).toHaveLength(6); + expect(arr1[3]).toBe('d'); + expect(arr1[4]).toBe('e'); + expect(arr1[5]).toBe('f'); + expect(arr2).toHaveLength(3); + }); + + it('(?, ?) : should gracefully reject invalid inputs', () => { + expect($.merge([4], 3 as never)).toBeFalsy(); + expect($.merge({} as never, {} as never)).toBeFalsy(); + expect($.merge([], {} as never)).toBeFalsy(); + expect($.merge({} as never, [])).toBeFalsy(); + const fakeArray1 = { length: 3, 0: 'a', 1: 'b', 3: 'd' }; + expect($.merge(fakeArray1, [])).toBeFalsy(); + expect($.merge([], fakeArray1)).toBeFalsy(); + expect($.merge({ length: '7' } as never, [])).toBeFalsy(); + expect($.merge({ length: -1 }, [])).toBeFalsy(); + }); + + it('(?, ?) : should no-op on invalid inputs', () => { + const fakeArray1 = { length: 3, 0: 'a', 1: 'b', 3: 'd' }; + $.merge(fakeArray1, []); + expect(fakeArray1).toHaveLength(3); + expect(fakeArray1[0]).toBe('a'); + expect(fakeArray1[1]).toBe('b'); + expect(fakeArray1[3]).toBe('d'); + $.merge([], fakeArray1); + expect(fakeArray1).toHaveLength(3); + expect(fakeArray1[0]).toBe('a'); + expect(fakeArray1[1]).toBe('b'); + expect(fakeArray1[3]).toBe('d'); + }); + }); + + describe('.contains', () => { + let $: CheerioAPI; + + beforeEach(() => { + $ = cheerio.load(food); + }); + + it('(container, contained) : should correctly detect the provided element', () => { + const $food = $('#food'); + const $fruits = $('#fruits'); + const $apple = $('.apple'); + + expect($.contains($food[0], $fruits[0])).toBe(true); + expect($.contains($food[0], $apple[0])).toBe(true); + }); + + it('(container, other) : should not detect elements that are not contained', () => { + const $fruits = $('#fruits'); + const $vegetables = $('#vegetables'); + const $apple = $('.apple'); + + expect($.contains($vegetables[0], $apple[0])).toBe(false); + expect($.contains($fruits[0], $vegetables[0])).toBe(false); + expect($.contains($vegetables[0], $fruits[0])).toBe(false); + expect($.contains($fruits[0], $fruits[0])).toBe(false); + expect($.contains($vegetables[0], $vegetables[0])).toBe(false); + }); + }); + + describe('.root', () => { + it('() : should return a cheerio-wrapped root object', () => { + const $ = cheerio.load('foo'); + $.root().append('
    '); + expect($.html()).toBe( + 'foo
    ', + ); + }); + }); + + describe('.extract', () => { + it('() : should extract values for selectors', () => { + const $ = cheerio.load(eleven); + + expect( + $.extract({ + red: [{ selector: '.red', value: 'outerHTML' }], + }), + ).toStrictEqual({ + red: [ + '
  • Four
  • ', + '
  • Five
  • ', + '
  • Nine
  • ', + ], + }); + }); + }); +}); diff --git a/frontend/node_modules/cheerio/src/static.ts b/frontend/node_modules/cheerio/src/static.ts new file mode 100644 index 0000000..b26f213 --- /dev/null +++ b/frontend/node_modules/cheerio/src/static.ts @@ -0,0 +1,312 @@ +import type { BasicAcceptedElems } from './types.js'; +import type { CheerioAPI } from './load.js'; +import type { Cheerio } from './cheerio.js'; +import type { AnyNode, Document } from 'domhandler'; +import { textContent } from 'domutils'; +import { + type InternalOptions, + type CheerioOptions, + flattenOptions as flattenOptions, +} from './options.js'; +import type { ExtractedMap, ExtractMap } from './api/extract.js'; + +/** + * Helper function to render a DOM. + * + * @param that - Cheerio instance to render. + * @param dom - The DOM to render. Defaults to `that`'s root. + * @param options - Options for rendering. + * @returns The rendered document. + */ +function render( + that: CheerioAPI, + dom: BasicAcceptedElems | undefined, + options: InternalOptions, +): string { + if (!that) return ''; + + return that(dom ?? that._root.children, null, undefined, options).toString(); +} + +/** + * Checks if a passed object is an options object. + * + * @param dom - Object to check if it is an options object. + * @param options - Options object. + * @returns Whether the object is an options object. + */ +function isOptions( + dom?: BasicAcceptedElems | CheerioOptions | null, + options?: CheerioOptions, +): dom is CheerioOptions { + return ( + !options && + typeof dom === 'object' && + dom != null && + !('length' in dom) && + !('type' in dom) + ); +} + +/** + * Renders the document. + * + * @category Static + * @param options - Options for the renderer. + * @returns The rendered document. + */ +export function html(this: CheerioAPI, options?: CheerioOptions): string; +/** + * Renders the document. + * + * @category Static + * @param dom - Element to render. + * @param options - Options for the renderer. + * @returns The rendered document. + */ +export function html( + this: CheerioAPI, + dom?: BasicAcceptedElems, + options?: CheerioOptions, +): string; +export function html( + this: CheerioAPI, + dom?: BasicAcceptedElems | CheerioOptions, + options?: CheerioOptions, +): string { + /* + * Be flexible about parameters, sometimes we call html(), + * with options as only parameter + * check dom argument for dom element specific properties + * assume there is no 'length' or 'type' properties in the options object + */ + const toRender = isOptions(dom) ? ((options = dom), undefined) : dom; + + /* + * Sometimes `$.html()` is used without preloading html, + * so fallback non-existing options to the default ones. + */ + const opts = { + ...this?._options, + ...flattenOptions(options), + }; + + return render(this, toRender, opts); +} + +/** + * Render the document as XML. + * + * @category Static + * @param dom - Element to render. + * @returns THe rendered document. + */ +export function xml( + this: CheerioAPI, + dom?: BasicAcceptedElems, +): string { + const options = { ...this._options, xmlMode: true }; + + return render(this, dom, options); +} + +/** + * Render the document as text. + * + * This returns the `textContent` of the passed elements. The result will + * include the contents of ` +``` + +For legacy environments, you can load d3-array’s UMD bundle; a `d3` global is exported: + +```html + + +``` + +## API Reference + +* [Statistics](#statistics) +* [Search](#search) +* [Transformations](#transformations) +* [Iterables](#iterables) +* [Sets](#sets) +* [Bins](#bins) +* [Interning](#interning) + +### Statistics + +Methods for computing basic summary statistics. + +
    # d3.min(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/min.js), [Examples](https://observablehq.com/@d3/d3-extent) + +Returns the minimum value in the given *iterable* using natural order. If the iterable contains no comparable values, returns undefined. An optional *accessor* function may be specified, which is equivalent to calling Array.from before computing the minimum value. + +Unlike the built-in [Math.min](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Math/min), this method ignores undefined, null and NaN values; this is useful for ignoring missing data. In addition, elements are compared using natural order rather than numeric order. For example, the minimum of the strings [“20”, “3”] is “20”, while the minimum of the numbers [20, 3] is 3. + +See also [extent](#extent). + +# d3.minIndex(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/minIndex.js), [Examples](https://observablehq.com/@d3/d3-extent) + +Returns the index of the minimum value in the given *iterable* using natural order. If the iterable contains no comparable values, returns -1. An optional *accessor* function may be specified, which is equivalent to calling Array.from before computing the minimum value. + +Unlike the built-in [Math.min](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Math/min), this method ignores undefined, null and NaN values; this is useful for ignoring missing data. In addition, elements are compared using natural order rather than numeric order. For example, the minimum of the strings [“20”, “3”] is “20”, while the minimum of the numbers [20, 3] is 3. + +# d3.max(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/max.js), [Examples](https://observablehq.com/@d3/d3-extent) + +Returns the maximum value in the given *iterable* using natural order. If the iterable contains no comparable values, returns undefined. An optional *accessor* function may be specified, which is equivalent to calling Array.from before computing the maximum value. + +Unlike the built-in [Math.max](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Math/max), this method ignores undefined values; this is useful for ignoring missing data. In addition, elements are compared using natural order rather than numeric order. For example, the maximum of the strings [“20”, “3”] is “3”, while the maximum of the numbers [20, 3] is 20. + +See also [extent](#extent). + +# d3.maxIndex(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/maxIndex.js), [Examples](https://observablehq.com/@d3/d3-extent) + +Returns the index of the maximum value in the given *iterable* using natural order. If the iterable contains no comparable values, returns -1. An optional *accessor* function may be specified, which is equivalent to calling Array.from before computing the maximum value. + +Unlike the built-in [Math.max](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Math/max), this method ignores undefined values; this is useful for ignoring missing data. In addition, elements are compared using natural order rather than numeric order. For example, the maximum of the strings [“20”, “3”] is “3”, while the maximum of the numbers [20, 3] is 20. + +# d3.extent(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/extent.js), [Examples](https://observablehq.com/@d3/d3-extent) + +Returns the [minimum](#min) and [maximum](#max) value in the given *iterable* using natural order. If the iterable contains no comparable values, returns [undefined, undefined]. An optional *accessor* function may be specified, which is equivalent to calling Array.from before computing the extent. + +# d3.mode(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/mode.js), [Examples](https://observablehq.com/@d3/d3-mode) + +Returns the mode of the given *iterable*, *i.e.* the value which appears the most often. In case of equality, returns the first of the relevant values. If the iterable contains no comparable values, returns undefined. An optional *accessor* function may be specified, which is equivalent to calling Array.from before computing the mode. This method ignores undefined, null and NaN values; this is useful for ignoring missing data. + +# d3.sum(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/sum.js), [Examples](https://observablehq.com/@d3/d3-sum) + +Returns the sum of the given *iterable* of numbers. If the iterable contains no numbers, returns 0. An optional *accessor* function may be specified, which is equivalent to calling Array.from before computing the sum. This method ignores undefined and NaN values; this is useful for ignoring missing data. + +# d3.mean(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/mean.js), [Examples](https://observablehq.com/@d3/d3-mean-d3-median-and-friends) + +Returns the mean of the given *iterable* of numbers. If the iterable contains no numbers, returns undefined. An optional *accessor* function may be specified, which is equivalent to calling Array.from before computing the mean. This method ignores undefined and NaN values; this is useful for ignoring missing data. + +# d3.median(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/median.js), [Examples](https://observablehq.com/@d3/d3-mean-d3-median-and-friends) + +Returns the median of the given *iterable* of numbers using the [R-7 method](https://en.wikipedia.org/wiki/Quantile#Estimating_quantiles_from_a_sample). If the iterable contains no numbers, returns undefined. An optional *accessor* function may be specified, which is equivalent to calling Array.from before computing the median. This method ignores undefined and NaN values; this is useful for ignoring missing data. + +# d3.medianIndex(array[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/median.js) + +Similar to *median*, but returns the index of the element to the left of the median. + +# d3.cumsum(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/cumsum.js), [Examples](https://observablehq.com/@d3/d3-cumsum) + +Returns the cumulative sum of the given *iterable* of numbers, as a Float64Array of the same length. If the iterable contains no numbers, returns zeros. An optional *accessor* function may be specified, which is equivalent to calling Array.from before computing the cumulative sum. This method ignores undefined and NaN values; this is useful for ignoring missing data. + +# d3.quantile(iterable, p[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/quantile.js), [Examples](https://observablehq.com/@d3/d3-mean-d3-median-and-friends) + +Returns the *p*-quantile of the given *iterable* of numbers, where *p* is a number in the range [0, 1]. For example, the median can be computed using *p* = 0.5, the first quartile at *p* = 0.25, and the third quartile at *p* = 0.75. This particular implementation uses the [R-7 method](http://en.wikipedia.org/wiki/Quantile#Quantiles_of_a_population), which is the default for the R programming language and Excel. For example: + +```js +var a = [0, 10, 30]; +d3.quantile(a, 0); // 0 +d3.quantile(a, 0.5); // 10 +d3.quantile(a, 1); // 30 +d3.quantile(a, 0.25); // 5 +d3.quantile(a, 0.75); // 20 +d3.quantile(a, 0.1); // 2 +``` + +An optional *accessor* function may be specified, which is equivalent to calling *array*.map(*accessor*) before computing the quantile. + +# d3.quantileIndex(array, p[, accessor]) [Source](https://github.com/d3/d3-array/blob/main/src/quantile.js "Source") + +Similar to *quantile*, but returns the index to the left of *p*. + +# d3.quantileSorted(array, p[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/quantile.js), [Examples](https://observablehq.com/@d3/d3-mean-d3-median-and-friends) + +Similar to *quantile*, but expects the input to be a **sorted** *array* of values. In contrast with *quantile*, the accessor is only called on the elements needed to compute the quantile. + +# d3.rank(iterable[, comparator]) · [Source](https://github.com/d3/d3-array/blob/main/src/rank.js), [Examples](https://observablehq.com/@d3/rank) +
    # d3.rank(iterable[, accessor]) + +Returns an array with the rank of each value in the *iterable*, *i.e.* the zero-based index of the value when the iterable is sorted. Nullish values are sorted to the end and ranked NaN. An optional *comparator* or *accessor* function may be specified; the latter is equivalent to calling *array*.map(*accessor*) before computing the ranks. If *comparator* is not specified, it defaults to [ascending](#ascending). Ties (equivalent values) all get the same rank, defined as the first time the value is found. + +```js +d3.rank([{x: 1}, {}, {x: 2}, {x: 0}], d => d.x); // [1, NaN, 2, 0] +d3.rank(["b", "c", "b", "a"]); // [1, 3, 1, 0] +d3.rank([1, 2, 3], d3.descending); // [2, 1, 0] +``` + +# d3.variance(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/variance.js), [Examples](https://observablehq.com/@d3/d3-mean-d3-median-and-friends) + +Returns an [unbiased estimator of the population variance](http://mathworld.wolfram.com/SampleVariance.html) of the given *iterable* of numbers using [Welford’s algorithm](https://en.wikipedia.org/wiki/Algorithms_for_calculating_variance#Welford's_online_algorithm). If the iterable has fewer than two numbers, returns undefined. An optional *accessor* function may be specified, which is equivalent to calling Array.from before computing the variance. This method ignores undefined and NaN values; this is useful for ignoring missing data. + +# d3.deviation(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/deviation.js), [Examples](https://observablehq.com/@d3/d3-mean-d3-median-and-friends) + +Returns the standard deviation, defined as the square root of the [bias-corrected variance](#variance), of the given *iterable* of numbers. If the iterable has fewer than two numbers, returns undefined. An optional *accessor* function may be specified, which is equivalent to calling Array.from before computing the standard deviation. This method ignores undefined and NaN values; this is useful for ignoring missing data. + +# d3.fsum([values][, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/fsum.js), [Examples](https://observablehq.com/@d3/d3-fsum) + +Returns a full precision summation of the given *values*. + +```js +d3.fsum([.1, .1, .1, .1, .1, .1, .1, .1, .1, .1]); // 1 +d3.sum([.1, .1, .1, .1, .1, .1, .1, .1, .1, .1]); // 0.9999999999999999 +``` + +Although slower, d3.fsum can replace d3.sum wherever greater precision is needed. Uses d3.Adder. + +# d3.fcumsum([values][, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/fsum.js), [Examples](https://observablehq.com/@d3/d3-fcumsum) + +Returns a full precision cumulative sum of the given *values*. + +```js +d3.fcumsum([1, 1e-14, -1]); // [1, 1.00000000000001, 1e-14] +d3.cumsum([1, 1e-14, -1]); // [1, 1.00000000000001, 9.992e-15] +``` + +Although slower, d3.fcumsum can replace d3.cumsum when greater precision is needed. Uses d3.Adder. + +# new d3.Adder() + +Creates a full precision adder for [IEEE 754](https://en.wikipedia.org/wiki/IEEE_754) floating point numbers, setting its initial value to 0. + +# *adder*.add(number) + +Adds the specified *number* to the adder’s current value and returns the adder. + +# *adder*.valueOf() + +Returns the IEEE 754 double precision representation of the adder’s current value. Most useful as the short-hand notation `+adder`. + +### Search + +Methods for searching arrays for a specific element. + +# d3.least(iterable[, comparator]) · [Source](https://github.com/d3/d3-array/blob/main/src/least.js), [Examples](https://observablehq.com/@d3/d3-least) +
    # d3.least(iterable[, accessor]) + +Returns the least element of the specified *iterable* according to the specified *comparator* or *accessor*. If the given *iterable* contains no comparable elements (*i.e.*, the comparator returns NaN when comparing each element to itself), returns undefined. If *comparator* is not specified, it defaults to [ascending](#ascending). For example: + +```js +const array = [{foo: 42}, {foo: 91}]; +d3.least(array, (a, b) => a.foo - b.foo); // {foo: 42} +d3.least(array, (a, b) => b.foo - a.foo); // {foo: 91} +d3.least(array, a => a.foo); // {foo: 42} +``` + +This function is similar to [min](#min), except it allows the use of a comparator rather than an accessor. + +# d3.leastIndex(iterable[, comparator]) · [Source](https://github.com/d3/d3-array/blob/main/src/leastIndex.js), [Examples](https://observablehq.com/@d3/d3-least) +
    # d3.leastIndex(iterable[, accessor]) + +Returns the index of the least element of the specified *iterable* according to the specified *comparator* or *accessor*. If the given *iterable* contains no comparable elements (*i.e.*, the comparator returns NaN when comparing each element to itself), returns -1. If *comparator* is not specified, it defaults to [ascending](#ascending). For example: + +```js +const array = [{foo: 42}, {foo: 91}]; +d3.leastIndex(array, (a, b) => a.foo - b.foo); // 0 +d3.leastIndex(array, (a, b) => b.foo - a.foo); // 1 +d3.leastIndex(array, a => a.foo); // 0 +``` + +This function is similar to [minIndex](#minIndex), except it allows the use of a comparator rather than an accessor. + +# d3.greatest(iterable[, comparator]) · [Source](https://github.com/d3/d3-array/blob/main/src/greatest.js), [Examples](https://observablehq.com/@d3/d3-least) +
    # d3.greatest(iterable[, accessor]) + +Returns the greatest element of the specified *iterable* according to the specified *comparator* or *accessor*. If the given *iterable* contains no comparable elements (*i.e.*, the comparator returns NaN when comparing each element to itself), returns undefined. If *comparator* is not specified, it defaults to [ascending](#ascending). For example: + +```js +const array = [{foo: 42}, {foo: 91}]; +d3.greatest(array, (a, b) => a.foo - b.foo); // {foo: 91} +d3.greatest(array, (a, b) => b.foo - a.foo); // {foo: 42} +d3.greatest(array, a => a.foo); // {foo: 91} +``` + +This function is similar to [max](#max), except it allows the use of a comparator rather than an accessor. + +# d3.greatestIndex(iterable[, comparator]) · [Source](https://github.com/d3/d3-array/blob/main/src/greatestIndex.js), [Examples](https://observablehq.com/@d3/d3-least) +
    # d3.greatestIndex(iterable[, accessor]) + +Returns the index of the greatest element of the specified *iterable* according to the specified *comparator* or *accessor*. If the given *iterable* contains no comparable elements (*i.e.*, the comparator returns NaN when comparing each element to itself), returns -1. If *comparator* is not specified, it defaults to [ascending](#ascending). For example: + +```js +const array = [{foo: 42}, {foo: 91}]; +d3.greatestIndex(array, (a, b) => a.foo - b.foo); // 1 +d3.greatestIndex(array, (a, b) => b.foo - a.foo); // 0 +d3.greatestIndex(array, a => a.foo); // 1 +``` + +This function is similar to [maxIndex](#maxIndex), except it allows the use of a comparator rather than an accessor. + +# d3.bisectLeft(array, x[, lo[, hi]]) · [Source](https://github.com/d3/d3-array/blob/main/src/bisect.js) + +Returns the insertion point for *x* in *array* to maintain sorted order. The arguments *lo* and *hi* may be used to specify a subset of the array which should be considered; by default the entire array is used. If *x* is already present in *array*, the insertion point will be before (to the left of) any existing entries. The return value is suitable for use as the first argument to [splice](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Array/splice) assuming that *array* is already sorted. The returned insertion point *i* partitions the *array* into two halves so that all *v* < *x* for *v* in *array*.slice(*lo*, *i*) for the left side and all *v* >= *x* for *v* in *array*.slice(*i*, *hi*) for the right side. + +# d3.bisect(array, x[, lo[, hi]]) · [Source](https://github.com/d3/d3-array/blob/main/src/bisect.js), [Examples](https://observablehq.com/@d3/d3-bisect) +
    # d3.bisectRight(array, x[, lo[, hi]]) + +Similar to [bisectLeft](#bisectLeft), but returns an insertion point which comes after (to the right of) any existing entries of *x* in *array*. The returned insertion point *i* partitions the *array* into two halves so that all *v* <= *x* for *v* in *array*.slice(*lo*, *i*) for the left side and all *v* > *x* for *v* in *array*.slice(*i*, *hi*) for the right side. + +# d3.bisectCenter(array, x[, lo[, hi]]) · [Source](https://github.com/d3/d3-array/blob/main/src/bisect.js), [Examples](https://observablehq.com/@d3/multi-line-chart) + +Returns the index of the value closest to *x* in the given *array* of numbers. The arguments *lo* (inclusive) and *hi* (exclusive) may be used to specify a subset of the array which should be considered; by default the entire array is used. + +See [*bisector*.center](#bisector_center). + +# d3.bisector(accessor) · [Source](https://github.com/d3/d3-array/blob/main/src/bisector.js) +
    # d3.bisector(comparator) + +Returns a new bisector using the specified *accessor* or *comparator* function. This method can be used to bisect arrays of objects instead of being limited to simple arrays of primitives. For example, given the following array of objects: + +```js +var data = [ + {date: new Date(2011, 1, 1), value: 0.5}, + {date: new Date(2011, 2, 1), value: 0.6}, + {date: new Date(2011, 3, 1), value: 0.7}, + {date: new Date(2011, 4, 1), value: 0.8} +]; +``` + +A suitable bisect function could be constructed as: + +```js +var bisectDate = d3.bisector(function(d) { return d.date; }).right; +``` + +This is equivalent to specifying a comparator: + +```js +var bisectDate = d3.bisector(function(d, x) { return d.date - x; }).right; +``` + +And then applied as *bisectDate*(*array*, *date*), returning an index. Note that the comparator is always passed the search value *x* as the second argument. Use a comparator rather than an accessor if you want values to be sorted in an order different than natural order, such as in descending rather than ascending order. + +# bisector.left(array, x[, lo[, hi]]) · [Source](https://github.com/d3/d3-array/blob/main/src/bisector.js) + +Equivalent to [bisectLeft](#bisectLeft), but uses this bisector’s associated comparator. + +# bisector.right(array, x[, lo[, hi]]) · [Source](https://github.com/d3/d3-array/blob/main/src/bisector.js) + +Equivalent to [bisectRight](#bisectRight), but uses this bisector’s associated comparator. + +# bisector.center(array, x[, lo[, hi]]) · [Source](https://github.com/d3/d3-array/blob/main/src/bisector.js) + +Returns the index of the closest value to *x* in the given sorted *array*. This expects that the bisector’s associated accessor returns a quantitative value, or that the bisector’s associated comparator returns a signed distance; otherwise, this method is equivalent to *bisector*.left. + +# d3.quickselect(array, k, left = 0, right = array.length - 1, compare = ascending) · [Source](https://github.com/d3/d3-array/blob/main/src/quickselect.js), [Examples](https://observablehq.com/@d3/d3-quickselect) + +See [mourner/quickselect](https://github.com/mourner/quickselect/blob/master/README.md). + +# d3.ascending(a, b) · [Source](https://github.com/d3/d3-array/blob/main/src/ascending.js), [Examples](https://observablehq.com/@d3/d3-ascending) + +Returns -1 if *a* is less than *b*, or 1 if *a* is greater than *b*, or 0. This is the comparator function for natural order, and can be used in conjunction with the built-in [*array*.sort](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Array/sort) method to arrange elements in ascending order. It is implemented as: + +```js +function ascending(a, b) { + return a == null || b == null ? NaN : a < b ? -1 : a > b ? 1 : a >= b ? 0 : NaN; +} +``` + +Note that if no comparator function is specified to the built-in sort method, the default order is lexicographic (alphabetical), not natural! This can lead to surprising behavior when sorting an array of numbers. + +# d3.descending(a, b) · [Source](https://github.com/d3/d3-array/blob/main/src/descending.js), [Examples](https://observablehq.com/@d3/d3-ascending) + +Returns -1 if *a* is greater than *b*, or 1 if *a* is less than *b*, or 0. This is the comparator function for reverse natural order, and can be used in conjunction with the built-in array sort method to arrange elements in descending order. It is implemented as: + +```js +function descending(a, b) { + return a == null || b == null ? NaN : b < a ? -1 : b > a ? 1 : b >= a ? 0 : NaN; +} +``` + +Note that if no comparator function is specified to the built-in sort method, the default order is lexicographic (alphabetical), not natural! This can lead to surprising behavior when sorting an array of numbers. + +### Transformations + +Methods for transforming arrays and for generating new arrays. + +# d3.group(iterable, ...keys) · [Source](https://github.com/d3/d3-array/blob/main/src/group.js), [Examples](https://observablehq.com/@d3/d3-group-d3-rollup) + +Groups the specified *iterable* of values into an [InternMap](#InternMap) from *key* to array of value. For example, given some data: + +```js +data = [ + {name: "jim", amount: "34.0", date: "11/12/2015"}, + {name: "carl", amount: "120.11", date: "11/12/2015"}, + {name: "stacy", amount: "12.01", date: "01/04/2016"}, + {name: "stacy", amount: "34.05", date: "01/04/2016"} +] +``` + +To group the data by name: + +```js +d3.group(data, d => d.name) +``` + +This produces: + +```js +Map(3) { + "jim" => Array(1) + "carl" => Array(1) + "stacy" => Array(2) +} +``` + +If more than one *key* is specified, a nested InternMap is returned. For example: + +```js +d3.group(data, d => d.name, d => d.date) +``` + +This produces: + +```js +Map(3) { + "jim" => Map(1) { + "11/12/2015" => Array(1) + } + "carl" => Map(1) { + "11/12/2015" => Array(1) + } + "stacy" => Map(1) { + "01/04/2016" => Array(2) + } +} +``` + +To convert a Map to an Array, use [Array.from](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/from). For example: + +```js +Array.from(d3.group(data, d => d.name)) +``` + +This produces: + +```js +[ + ["jim", Array(1)], + ["carl", Array(1)], + ["stacy", Array(2)] +] +``` + +You can also simultaneously convert the [*key*, *value*] to some other representation by passing a map function to Array.from: + +```js +Array.from(d3.group(data, d => d.name), ([key, value]) => ({key, value})) +``` + +This produces: + +```js +[ + {key: "jim", value: Array(1)}, + {key: "carl", value: Array(1)}, + {key: "stacy", value: Array(2)} +] +``` + +[*selection*.data](https://github.com/d3/d3-selection/blob/main/README.md#selection_data) accepts iterables directly, meaning that you can use a Map (or Set or other iterable) to perform a data join without first needing to convert to an array. + +# d3.groups(iterable, ...keys) · [Source](https://github.com/d3/d3-array/blob/main/src/group.js), [Examples](https://observablehq.com/@d3/d3-group-d3-rollup) + +Equivalent to [group](#group), but returns nested arrays instead of nested maps. + +# d3.flatGroup(iterable, ...keys) · [Source](https://github.com/d3/d3-array/blob/main/src/group.js), [Examples](https://observablehq.com/@d3/d3-flatgroup) + +Equivalent to [group](#group), but returns a flat array of [*key0*, *key1*, …, *values*] instead of nested maps. + +# d3.index(iterable, ...keys) · [Source](https://github.com/d3/d3-array/blob/main/src/group.js), [Examples](https://observablehq.com/@d3/d3-group) + +Equivalent to [group](#group) but returns a unique value per compound key instead of an array, throwing if the key is not unique. + +For example, given the data defined above, + +```js +d3.index(data, d => d.amount) +``` + +returns + +```js +Map(4) { + "34.0" => Object {name: "jim", amount: "34.0", date: "11/12/2015"} + "120.11" => Object {name: "carl", amount: "120.11", date: "11/12/2015"} + "12.01" => Object {name: "stacy", amount: "12.01", date: "01/04/2016"} + "34.05" => Object {name: "stacy", amount: "34.05", date: "01/04/2016"} +} +``` + +On the other hand, + +```js +d3.index(data, d => d.name) +``` + +throws an error because two objects share the same name. + +# d3.indexes(iterable, ...keys) · [Source](https://github.com/d3/d3-array/blob/main/src/group.js), [Examples](https://observablehq.com/@d3/d3-group) + +Equivalent to [index](#index), but returns nested arrays instead of nested maps. + +# d3.rollup(iterable, reduce, ...keys) · [Source](https://github.com/d3/d3-array/blob/main/src/group.js), [Examples](https://observablehq.com/@d3/d3-group-d3-rollup) + +[Groups](#group) and reduces the specified *iterable* of values into an InternMap from *key* to value. For example, given some data: + +```js +data = [ + {name: "jim", amount: "34.0", date: "11/12/2015"}, + {name: "carl", amount: "120.11", date: "11/12/2015"}, + {name: "stacy", amount: "12.01", date: "01/04/2016"}, + {name: "stacy", amount: "34.05", date: "01/04/2016"} +] +``` + +To count the number of elements by name: + +```js +d3.rollup(data, v => v.length, d => d.name) +``` + +This produces: + +```js +Map(3) { + "jim" => 1 + "carl" => 1 + "stacy" => 2 +} +``` + +If more than one *key* is specified, a nested Map is returned. For example: + +```js +d3.rollup(data, v => v.length, d => d.name, d => d.date) +``` + +This produces: + +```js +Map(3) { + "jim" => Map(1) { + "11/12/2015" => 1 + } + "carl" => Map(1) { + "11/12/2015" => 1 + } + "stacy" => Map(1) { + "01/04/2016" => 2 + } +} +``` + +To convert a Map to an Array, use [Array.from](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/from). See [d3.group](#group) for examples. + +# d3.rollups(iterable, reduce, ...keys) · [Source](https://github.com/d3/d3-array/blob/main/src/group.js), [Examples](https://observablehq.com/@d3/d3-group-d3-rollup) + +Equivalent to [rollup](#rollup), but returns nested arrays instead of nested maps. + +# d3.flatRollup(iterable, reduce, ...keys) · [Source](https://github.com/d3/d3-array/blob/main/src/group.js), [Examples](https://observablehq.com/@d3/d3-flatgroup) + +Equivalent to [rollup](#rollup), but returns a flat array of [*key0*, *key1*, …, *value*] instead of nested maps. + +# d3.groupSort(iterable, comparator, key) · [Source](https://github.com/d3/d3-array/blob/main/src/groupSort.js), [Examples](https://observablehq.com/@d3/d3-groupsort) +
    # d3.groupSort(iterable, accessor, key) + +Groups the specified *iterable* of elements according to the specified *key* function, sorts the groups according to the specified *comparator*, and then returns an array of keys in sorted order. For example, if you had a table of barley yields for different varieties, sites, and years, to sort the barley varieties by ascending median yield: + +```js +d3.groupSort(barley, g => d3.median(g, d => d.yield), d => d.variety) +``` + +For descending order, negate the group value: + +```js +d3.groupSort(barley, g => -d3.median(g, d => d.yield), d => d.variety) +``` + +If a *comparator* is passed instead of an *accessor* (i.e., if the second argument is a function that takes exactly two arguments), it will be asked to compare two groups *a* and *b* and should return a negative value if *a* should be before *b*, a positive value if *a* should be after *b*, or zero for a partial ordering. + +# d3.count(iterable[, accessor]) · [Source](https://github.com/d3/d3-array/blob/main/src/count.js), [Examples](https://observablehq.com/@d3/d3-count) + +Returns the number of valid number values (*i.e.*, not null, NaN, or undefined) in the specified *iterable*; accepts an accessor. + +For example: + +```js +d3.count([{n: "Alice", age: NaN}, {n: "Bob", age: 18}, {n: "Other"}], d => d.age) // 1 +``` +# d3.cross(...iterables[, reducer]) · [Source](https://github.com/d3/d3-array/blob/main/src/cross.js), [Examples](https://observablehq.com/@d3/d3-cross) + +Returns the [Cartesian product](https://en.wikipedia.org/wiki/Cartesian_product) of the specified *iterables*. For example, if two iterables *a* and *b* are specified, for each element *i* in the iterable *a* and each element *j* in the iterable *b*, in order, invokes the specified *reducer* function passing the element *i* and element *j*. If a *reducer* is not specified, it defaults to a function which creates a two-element array for each pair: + +```js +function pair(a, b) { + return [a, b]; +} +``` + +For example: + +```js +d3.cross([1, 2], ["x", "y"]); // returns [[1, "x"], [1, "y"], [2, "x"], [2, "y"]] +d3.cross([1, 2], ["x", "y"], (a, b) => a + b); // returns ["1x", "1y", "2x", "2y"] +``` + +# d3.merge(iterables) · [Source](https://github.com/d3/d3-array/blob/main/src/merge.js), [Examples](https://observablehq.com/@d3/d3-merge) + +Merges the specified iterable of *iterables* into a single array. This method is similar to the built-in array concat method; the only difference is that it is more convenient when you have an array of arrays. + +```js +d3.merge([[1], [2, 3]]); // returns [1, 2, 3] +``` + +# d3.pairs(iterable[, reducer]) · [Source](https://github.com/d3/d3-array/blob/main/src/pairs.js), [Examples](https://observablehq.com/@d3/d3-pairs) + +For each adjacent pair of elements in the specified *iterable*, in order, invokes the specified *reducer* function passing the element *i* and element *i* - 1. If a *reducer* is not specified, it defaults to a function which creates a two-element array for each pair: + +```js +function pair(a, b) { + return [a, b]; +} +``` + +For example: + +```js +d3.pairs([1, 2, 3, 4]); // returns [[1, 2], [2, 3], [3, 4]] +d3.pairs([1, 2, 3, 4], (a, b) => b - a); // returns [1, 1, 1]; +``` + +If the specified iterable has fewer than two elements, returns the empty array. + +# d3.permute(source, keys) · [Source](https://github.com/d3/d3-array/blob/main/src/permute.js), [Examples](https://observablehq.com/@d3/d3-permute) + +Returns a permutation of the specified *source* object (or array) using the specified iterable of *keys*. The returned array contains the corresponding property of the source object for each key in *keys*, in order. For example: + +```js +permute(["a", "b", "c"], [1, 2, 0]); // returns ["b", "c", "a"] +``` + +It is acceptable to have more keys than source elements, and for keys to be duplicated or omitted. + +This method can also be used to extract the values from an object into an array with a stable order. Extracting keyed values in order can be useful for generating data arrays in nested selections. For example: + +```js +let object = {yield: 27, variety: "Manchuria", year: 1931, site: "University Farm"}; +let fields = ["site", "variety", "yield"]; + +d3.permute(object, fields); // returns ["University Farm", "Manchuria", 27] +``` + +# d3.shuffle(array[, start[, stop]]) · [Source](https://github.com/d3/d3-array/blob/main/src/shuffle.js), [Examples](https://observablehq.com/@d3/d3-shuffle) + +Randomizes the order of the specified *array* in-place using the [Fisher–Yates shuffle](https://bost.ocks.org/mike/shuffle/) and returns the *array*. If *start* is specified, it is the starting index (inclusive) of the *array* to shuffle; if *start* is not specified, it defaults to zero. If *stop* is specified, it is the ending index (exclusive) of the *array* to shuffle; if *stop* is not specified, it defaults to *array*.length. For example, to shuffle the first ten elements of the *array*: shuffle(*array*, 0, 10). + +# d3.shuffler(random) · [Source](https://github.com/d3/d3-array/blob/main/src/shuffle.js) + +Returns a [shuffle function](#shuffle) given the specified random source. For example, using [d3.randomLcg](https://github.com/d3/d3-random/blob/main/README.md#randomLcg): + +```js +const random = d3.randomLcg(0.9051667019185816); +const shuffle = d3.shuffler(random); + +shuffle([0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); // returns [7, 4, 5, 3, 9, 0, 6, 1, 2, 8] +``` + +# d3.ticks(start, stop, count) · [Source](https://github.com/d3/d3-array/blob/main/src/ticks.js), [Examples](https://observablehq.com/@d3/d3-ticks) + +Returns an array of approximately *count* + 1 uniformly-spaced, nicely-rounded values between *start* and *stop* (inclusive). Each value is a power of ten multiplied by 1, 2 or 5. See also [d3.tickIncrement](#tickIncrement), [d3.tickStep](#tickStep) and [*linear*.ticks](https://github.com/d3/d3-scale/blob/main/README.md#linear_ticks). + +Ticks are inclusive in the sense that they may include the specified *start* and *stop* values if (and only if) they are exact, nicely-rounded values consistent with the inferred [step](#tickStep). More formally, each returned tick *t* satisfies *start* ≤ *t* and *t* ≤ *stop*. + +# d3.tickIncrement(start, stop, count) · [Source](https://github.com/d3/d3-array/blob/main/src/ticks.js), [Examples](https://observablehq.com/@d3/d3-ticks) + +Like [d3.tickStep](#tickStep), except requires that *start* is always less than or equal to *stop*, and if the tick step for the given *start*, *stop* and *count* would be less than one, returns the negative inverse tick step instead. This method is always guaranteed to return an integer, and is used by [d3.ticks](#ticks) to guarantee that the returned tick values are represented as precisely as possible in IEEE 754 floating point. + +# d3.tickStep(start, stop, count) · [Source](https://github.com/d3/d3-array/blob/main/src/ticks.js), [Examples](https://observablehq.com/@d3/d3-ticks) + +Returns the difference between adjacent tick values if the same arguments were passed to [d3.ticks](#ticks): a nicely-rounded value that is a power of ten multiplied by 1, 2 or 5. Note that due to the limited precision of IEEE 754 floating point, the returned value may not be exact decimals; use [d3-format](https://github.com/d3/d3-format) to format numbers for human consumption. + +# d3.nice(start, stop, count) · [Source](https://github.com/d3/d3-array/blob/main/src/nice.js) + +Returns a new interval [*niceStart*, *niceStop*] covering the given interval [*start*, *stop*] and where *niceStart* and *niceStop* are guaranteed to align with the corresponding [tick step](#tickStep). Like [d3.tickIncrement](#tickIncrement), this requires that *start* is less than or equal to *stop*. + +# d3.range([start, ]stop[, step]) · [Source](https://github.com/d3/d3-array/blob/main/src/range.js), [Examples](https://observablehq.com/@d3/d3-range) + +Returns an array containing an arithmetic progression, similar to the Python built-in [range](http://docs.python.org/library/functions.html#range). This method is often used to iterate over a sequence of uniformly-spaced numeric values, such as the indexes of an array or the ticks of a linear scale. (See also [d3.ticks](#ticks) for nicely-rounded values.) + +If *step* is omitted, it defaults to 1. If *start* is omitted, it defaults to 0. The *stop* value is exclusive; it is not included in the result. If *step* is positive, the last element is the largest *start* + *i* \* *step* less than *stop*; if *step* is negative, the last element is the smallest *start* + *i* \* *step* greater than *stop*. If the returned array would contain an infinite number of values, an empty range is returned. + +The arguments are not required to be integers; however, the results are more predictable if they are. The values in the returned array are defined as *start* + *i* \* *step*, where *i* is an integer from zero to one minus the total number of elements in the returned array. For example: + +```js +d3.range(0, 1, 0.2) // [0, 0.2, 0.4, 0.6000000000000001, 0.8] +``` + +This unexpected behavior is due to IEEE 754 double-precision floating point, which defines 0.2 * 3 = 0.6000000000000001. Use [d3-format](https://github.com/d3/d3-format) to format numbers for human consumption with appropriate rounding; see also [linear.tickFormat](https://github.com/d3/d3-scale/blob/main/README.md#linear_tickFormat) in [d3-scale](https://github.com/d3/d3-scale). + +Likewise, if the returned array should have a specific length, consider using [array.map](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Array/map) on an integer range. For example: + +```js +d3.range(0, 1, 1 / 49); // BAD: returns 50 elements! +d3.range(49).map(function(d) { return d / 49; }); // GOOD: returns 49 elements. +``` + +# d3.transpose(matrix) · [Source](https://github.com/d3/d3-array/blob/main/src/transpose.js), [Examples](https://observablehq.com/@d3/d3-transpose) + +Uses the [zip](#zip) operator as a two-dimensional [matrix transpose](http://en.wikipedia.org/wiki/Transpose). + +# d3.zip(arrays…) · [Source](https://github.com/d3/d3-array/blob/main/src/zip.js), [Examples](https://observablehq.com/@d3/d3-transpose) + +Returns an array of arrays, where the *i*th array contains the *i*th element from each of the argument *arrays*. The returned array is truncated in length to the shortest array in *arrays*. If *arrays* contains only a single array, the returned array contains one-element arrays. With no arguments, the returned array is empty. + +```js +d3.zip([1, 2], [3, 4]); // returns [[1, 3], [2, 4]] +``` + +#### Blur + +# d3.blur(*data*, *radius*) · [Source](https://github.com/d3/d3-array/blob/main/src/blur.js), [Examples](https://observablehq.com/@d3/d3-blur) + +Blurs an array of *data* in-place by applying three iterations of a moving average transform, for a fast approximation of a gaussian kernel of the given *radius*, a non-negative number, and returns the array. + +```js +const randomWalk = d3.cumsum({length: 1000}, () => Math.random() - 0.5); +blur(randomWalk, 5); +``` + +Copy the data if you don’t want to smooth it in-place: +```js +const smoothed = blur(randomWalk.slice(), 5); +``` + +# d3.blur2({*data*, *width*[, *height*]}, *rx*[, *ry*]) · [Source](https://github.com/d3/d3-array/blob/main/src/blur.js), [Examples](https://observablehq.com/@d3/d3-blur) + +Blurs a matrix of the given *width* and *height* in-place, by applying an horizontal blur of radius *rx* and a vertical blur or radius *ry* (which defaults to *rx*). The matrix *data* is stored in a flat array, used to determine the *height* if it is not specified. Returns the blurred {data, width, height}. + +```js +data = [ + 1, 0, 0, + 0, 0, 0, + 0, 0, 1 +]; +blur2({data, width: 3}, 1); +``` + +# d3.blurImage(*imageData*, *rx*[, *ry*]) · [Source](https://github.com/d3/d3-array/blob/main/src/blur.js), [Examples](https://observablehq.com/@d3/d3-blurimage) + +Blurs an [ImageData](https://developer.mozilla.org/en-US/docs/Web/API/ImageData) structure in-place, blurring each of the RGBA layers independently by applying an horizontal blur of radius *rx* and a vertical blur or radius *ry* (which defaults to *rx*). Returns the blurred ImageData. + +```js +const imData = context.getImageData(0, 0, width, height); +blurImage(imData, 5); +``` + +### Iterables + +These are equivalent to built-in array methods, but work with any iterable including Map, Set, and Generator. + +# d3.every(iterable, test) · [Source](https://github.com/d3/d3-array/blob/main/src/every.js) + +Returns true if the given *test* function returns true for every value in the given *iterable*. This method returns as soon as *test* returns a non-truthy value or all values are iterated over. Equivalent to [*array*.every](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/every): + +```js +d3.every(new Set([1, 3, 5, 7]), x => x & 1) // true +``` + +# d3.some(iterable, test) · [Source](https://github.com/d3/d3-array/blob/main/src/some.js) + +Returns true if the given *test* function returns true for any value in the given *iterable*. This method returns as soon as *test* returns a truthy value or all values are iterated over. Equivalent to [*array*.some](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/some): + +```js +d3.some(new Set([0, 2, 3, 4]), x => x & 1) // true +``` + +# d3.filter(iterable, test) · [Source](https://github.com/d3/d3-array/blob/main/src/filter.js) + +Returns a new array containing the values from *iterable*, in order, for which the given *test* function returns true. Equivalent to [*array*.filter](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/filter): + +```js +d3.filter(new Set([0, 2, 3, 4]), x => x & 1) // [3] +``` + +# d3.map(iterable, mapper) · [Source](https://github.com/d3/d3-array/blob/main/src/map.js) + +Returns a new array containing the mapped values from *iterable*, in order, as defined by given *mapper* function. Equivalent to [*array*.map](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/map) and [Array.from](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/from): + +```js +d3.map(new Set([0, 2, 3, 4]), x => x & 1) // [0, 0, 1, 0] +``` + +# d3.reduce(iterable, reducer[, initialValue]) · [Source](https://github.com/d3/d3-array/blob/main/src/reduce.js) + +Returns the reduced value defined by given *reducer* function, which is repeatedly invoked for each value in *iterable*, being passed the current reduced value and the next value. Equivalent to [*array*.reduce](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/reduce): + +```js +d3.reduce(new Set([0, 2, 3, 4]), (p, v) => p + v, 0) // 9 +``` + +# d3.reverse(iterable) · [Source](https://github.com/d3/d3-array/blob/main/src/reverse.js) + +Returns an array containing the values in the given *iterable* in reverse order. Equivalent to [*array*.reverse](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/reverse), except that it does not mutate the given *iterable*: + +```js +d3.reverse(new Set([0, 2, 3, 1])) // [1, 3, 2, 0] +``` + +# d3.sort(iterable, comparator = d3.ascending) · [Source](https://github.com/d3/d3-array/blob/main/src/sort.js) +
    # d3.sort(iterable, ...accessors) + +Returns an array containing the values in the given *iterable* in the sorted order defined by the given *comparator* or *accessor* function. If *comparator* is not specified, it defaults to [d3.ascending](#ascending). Equivalent to [*array*.sort](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/sort), except that it does not mutate the given *iterable*, and the comparator defaults to natural order instead of lexicographic order: + +```js +d3.sort(new Set([0, 2, 3, 1])) // [0, 1, 2, 3] +``` + +If an *accessor* (a function that does not take exactly two arguments) is specified, + +```js +d3.sort(data, d => d.value) +``` + +it is equivalent to a *comparator* using [natural order](#ascending): + +```js +d3.sort(data, (a, b) => d3.ascending(a.value, b.value)) +``` + +The *accessor* is only invoked once per element, and thus the returned sorted order is consistent even if the accessor is nondeterministic. + +Multiple accessors may be specified to break ties: + +```js +d3.sort(points, ({x}) => x, ({y}) => y) +``` + +This is equivalent to: + +```js +d3.sort(data, (a, b) => d3.ascending(a.x, b.x) || d3.ascending(a.y, b.y)) +``` + +### Sets + +This methods implement basic set operations for any iterable. + +# d3.difference(iterable, ...others) · [Source](https://github.com/d3/d3-array/blob/main/src/difference.js) + +Returns a new InternSet containing every value in *iterable* that is not in any of the *others* iterables. + +```js +d3.difference([0, 1, 2, 0], [1]) // Set {0, 2} +``` + +# d3.union(...iterables) · [Source](https://github.com/d3/d3-array/blob/main/src/union.js) + +Returns a new InternSet containing every (distinct) value that appears in any of the given *iterables*. The order of values in the returned set is based on their first occurrence in the given *iterables*. + +```js +d3.union([0, 2, 1, 0], [1, 3]) // Set {0, 2, 1, 3} +``` + +# d3.intersection(...iterables) · [Source](https://github.com/d3/d3-array/blob/main/src/intersection.js) + +Returns a new InternSet containing every (distinct) value that appears in all of the given *iterables*. The order of values in the returned set is based on their first occurrence in the given *iterables*. + +```js +d3.intersection([0, 2, 1, 0], [1, 3]) // Set {1} +``` + +# d3.superset(a, b) · [Source](https://github.com/d3/d3-array/blob/main/src/superset.js) + +Returns true if *a* is a superset of *b*: if every value in the given iterable *b* is also in the given iterable *a*. + +```js +d3.superset([0, 2, 1, 3, 0], [1, 3]) // true +``` + +# d3.subset(a, b) · [Source](https://github.com/d3/d3-array/blob/main/src/subset.js) + +Returns true if *a* is a subset of *b*: if every value in the given iterable *a* is also in the given iterable *b*. + +```js +d3.subset([1, 3], [0, 2, 1, 3, 0]) // true +``` + +# d3.disjoint(a, b) · [Source](https://github.com/d3/d3-array/blob/main/src/disjoint.js) + +Returns true if *a* and *b* are disjoint: if *a* and *b* contain no shared value. + +```js +d3.disjoint([1, 3], [2, 4]) // true +``` + +### Bins + +[Histogram](http://bl.ocks.org/mbostock/3048450) + +Binning groups discrete samples into a smaller number of consecutive, non-overlapping intervals. They are often used to visualize the distribution of numerical data as histograms. + +# d3.bin() · [Source](https://github.com/d3/d3-array/blob/main/src/bin.js), [Examples](https://observablehq.com/@d3/d3-bin) + +Constructs a new bin generator with the default settings. + +# bin(data) · [Source](https://github.com/d3/d3-array/blob/main/src/bin.js), [Examples](https://observablehq.com/@d3/d3-bin) + +Bins the given iterable of *data* samples. Returns an array of bins, where each bin is an array containing the associated elements from the input *data*. Thus, the `length` of the bin is the number of elements in that bin. Each bin has two additional attributes: + +* `x0` - the lower bound of the bin (inclusive). +* `x1` - the upper bound of the bin (exclusive, except for the last bin). + +Any null or non-comparable values in the given *data*, or those outside the [domain](#bin_domain), are ignored. + +# bin.value([value]) · [Source](https://github.com/d3/d3-array/blob/main/src/bin.js), [Examples](https://observablehq.com/@d3/d3-bin) + +If *value* is specified, sets the value accessor to the specified function or constant and returns this bin generator. If *value* is not specified, returns the current value accessor, which defaults to the identity function. + +When bins are [generated](#_bin), the value accessor will be invoked for each element in the input data array, being passed the element `d`, the index `i`, and the array `data` as three arguments. The default value accessor assumes that the input data are orderable (comparable), such as numbers or dates. If your data are not, then you should specify an accessor that returns the corresponding orderable value for a given datum. + +This is similar to mapping your data to values before invoking the bin generator, but has the benefit that the input data remains associated with the returned bins, thereby making it easier to access other fields of the data. + +# bin.domain([domain]) · [Source](https://github.com/d3/d3-array/blob/main/src/bin.js), [Examples](https://observablehq.com/@d3/d3-bin) + +If *domain* is specified, sets the domain accessor to the specified function or array and returns this bin generator. If *domain* is not specified, returns the current domain accessor, which defaults to [extent](#extent). The bin domain is defined as an array [*min*, *max*], where *min* is the minimum observable value and *max* is the maximum observable value; both values are inclusive. Any value outside of this domain will be ignored when the bins are [generated](#_bin). + +For example, if you are using the bin generator in conjunction with a [linear scale](https://github.com/d3/d3-scale/blob/main/README.md#linear-scales) `x`, you might say: + +```js +var bin = d3.bin() + .domain(x.domain()) + .thresholds(x.ticks(20)); +``` + +You can then compute the bins from an array of numbers like so: + +```js +var bins = bin(numbers); +``` + +If the default [extent](#extent) domain is used and the [thresholds](#bin_thresholds) are specified as a count (rather than explicit values), then the computed domain will be [niced](#nice) such that all bins are uniform width. + +Note that the domain accessor is invoked on the materialized array of [values](#bin_value), not on the input data array. + +# bin.thresholds([count]) · [Source](https://github.com/d3/d3-array/blob/main/src/bin.js), [Examples](https://observablehq.com/@d3/d3-bin) +
    # bin.thresholds([thresholds]) + +If *thresholds* is specified, sets the [threshold generator](#bin-thresholds) to the specified function or array and returns this bin generator. If *thresholds* is not specified, returns the current threshold generator, which by default implements [Sturges’ formula](#thresholdSturges). (Thus by default, the values to be binned must be numbers!) Thresholds are defined as an array of values [*x0*, *x1*, …]. Any value less than *x0* will be placed in the first bin; any value greater than or equal to *x0* but less than *x1* will be placed in the second bin; and so on. Thus, the [generated bins](#_bin) will have *thresholds*.length + 1 bins. See [bin thresholds](#bin-thresholds) for more information. + +Any threshold values outside the [domain](#bin_domain) are ignored. The first *bin*.x0 is always equal to the minimum domain value, and the last *bin*.x1 is always equal to the maximum domain value. + +If a *count* is specified instead of an array of *thresholds*, then the [domain](#bin_domain) will be uniformly divided into approximately *count* bins; see [ticks](#ticks). + +#### Bin Thresholds + +These functions are typically not used directly; instead, pass them to [*bin*.thresholds](#bin_thresholds). + +# d3.thresholdFreedmanDiaconis(values, min, max) · [Source](https://github.com/d3/d3-array/blob/main/src/threshold/freedmanDiaconis.js), [Examples](https://observablehq.com/@d3/d3-bin) + +Returns the number of bins according to the [Freedman–Diaconis rule](https://en.wikipedia.org/wiki/Histogram#Mathematical_definition); the input *values* must be numbers. + +# d3.thresholdScott(values, min, max) · [Source](https://github.com/d3/d3-array/blob/main/src/threshold/scott.js), [Examples](https://observablehq.com/@d3/d3-bin) + +Returns the number of bins according to [Scott’s normal reference rule](https://en.wikipedia.org/wiki/Histogram#Mathematical_definition); the input *values* must be numbers. + +# d3.thresholdSturges(values) · [Source](https://github.com/d3/d3-array/blob/main/src/threshold/sturges.js), [Examples](https://observablehq.com/@d3/d3-bin) + +Returns the number of bins according to [Sturges’ formula](https://en.wikipedia.org/wiki/Histogram#Mathematical_definition); the input *values* must be numbers. + +You may also implement your own threshold generator taking three arguments: the array of input [*values*](#bin_value) derived from the data, and the [observable domain](#bin_domain) represented as *min* and *max*. The generator may then return either the array of numeric thresholds or the *count* of bins; in the latter case the domain is divided uniformly into approximately *count* bins; see [ticks](#ticks). + +For instance, when binning date values, you might want to use the ticks from a time scale ([Example](https://observablehq.com/@d3/d3-bin-time-thresholds)). + +### Interning + +# new d3.InternMap([iterable][, key]) · [Source](https://github.com/mbostock/internmap/blob/main/src/index.js), [Examples](https://observablehq.com/d/d4c5f6ad343866b9) +
    # new d3.InternSet([iterable][, key]) · [Source](https://github.com/mbostock/internmap/blob/main/src/index.js), [Examples](https://observablehq.com/d/d4c5f6ad343866b9) + +The [InternMap and InternSet](https://github.com/mbostock/internmap) classes extend the native JavaScript Map and Set classes, respectively, allowing Dates and other non-primitive keys by bypassing the [SameValueZero algorithm](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Equality_comparisons_and_sameness) when determining key equality. d3.group, d3.rollup and d3.index use an InternMap rather than a native Map. These two classes are exported for convenience. diff --git a/frontend/node_modules/d3-array/dist/d3-array.js b/frontend/node_modules/d3-array/dist/d3-array.js new file mode 100644 index 0000000..0644ded --- /dev/null +++ b/frontend/node_modules/d3-array/dist/d3-array.js @@ -0,0 +1,1455 @@ +// https://d3js.org/d3-array/ v3.2.4 Copyright 2010-2023 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +})(this, (function (exports) { 'use strict'; + +function ascending(a, b) { + return a == null || b == null ? NaN : a < b ? -1 : a > b ? 1 : a >= b ? 0 : NaN; +} + +function descending(a, b) { + return a == null || b == null ? NaN + : b < a ? -1 + : b > a ? 1 + : b >= a ? 0 + : NaN; +} + +function bisector(f) { + let compare1, compare2, delta; + + // If an accessor is specified, promote it to a comparator. In this case we + // can test whether the search value is (self-) comparable. We can’t do this + // for a comparator (except for specific, known comparators) because we can’t + // tell if the comparator is symmetric, and an asymmetric comparator can’t be + // used to test whether a single value is comparable. + if (f.length !== 2) { + compare1 = ascending; + compare2 = (d, x) => ascending(f(d), x); + delta = (d, x) => f(d) - x; + } else { + compare1 = f === ascending || f === descending ? f : zero; + compare2 = f; + delta = f; + } + + function left(a, x, lo = 0, hi = a.length) { + if (lo < hi) { + if (compare1(x, x) !== 0) return hi; + do { + const mid = (lo + hi) >>> 1; + if (compare2(a[mid], x) < 0) lo = mid + 1; + else hi = mid; + } while (lo < hi); + } + return lo; + } + + function right(a, x, lo = 0, hi = a.length) { + if (lo < hi) { + if (compare1(x, x) !== 0) return hi; + do { + const mid = (lo + hi) >>> 1; + if (compare2(a[mid], x) <= 0) lo = mid + 1; + else hi = mid; + } while (lo < hi); + } + return lo; + } + + function center(a, x, lo = 0, hi = a.length) { + const i = left(a, x, lo, hi - 1); + return i > lo && delta(a[i - 1], x) > -delta(a[i], x) ? i - 1 : i; + } + + return {left, center, right}; +} + +function zero() { + return 0; +} + +function number(x) { + return x === null ? NaN : +x; +} + +function* numbers(values, valueof) { + if (valueof === undefined) { + for (let value of values) { + if (value != null && (value = +value) >= value) { + yield value; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && (value = +value) >= value) { + yield value; + } + } + } +} + +const ascendingBisect = bisector(ascending); +const bisectRight = ascendingBisect.right; +const bisectLeft = ascendingBisect.left; +const bisectCenter = bisector(number).center; +var bisect = bisectRight; + +function blur(values, r) { + if (!((r = +r) >= 0)) throw new RangeError("invalid r"); + let length = values.length; + if (!((length = Math.floor(length)) >= 0)) throw new RangeError("invalid length"); + if (!length || !r) return values; + const blur = blurf(r); + const temp = values.slice(); + blur(values, temp, 0, length, 1); + blur(temp, values, 0, length, 1); + blur(values, temp, 0, length, 1); + return values; +} + +const blur2 = Blur2(blurf); + +const blurImage = Blur2(blurfImage); + +function Blur2(blur) { + return function(data, rx, ry = rx) { + if (!((rx = +rx) >= 0)) throw new RangeError("invalid rx"); + if (!((ry = +ry) >= 0)) throw new RangeError("invalid ry"); + let {data: values, width, height} = data; + if (!((width = Math.floor(width)) >= 0)) throw new RangeError("invalid width"); + if (!((height = Math.floor(height !== undefined ? height : values.length / width)) >= 0)) throw new RangeError("invalid height"); + if (!width || !height || (!rx && !ry)) return data; + const blurx = rx && blur(rx); + const blury = ry && blur(ry); + const temp = values.slice(); + if (blurx && blury) { + blurh(blurx, temp, values, width, height); + blurh(blurx, values, temp, width, height); + blurh(blurx, temp, values, width, height); + blurv(blury, values, temp, width, height); + blurv(blury, temp, values, width, height); + blurv(blury, values, temp, width, height); + } else if (blurx) { + blurh(blurx, values, temp, width, height); + blurh(blurx, temp, values, width, height); + blurh(blurx, values, temp, width, height); + } else if (blury) { + blurv(blury, values, temp, width, height); + blurv(blury, temp, values, width, height); + blurv(blury, values, temp, width, height); + } + return data; + }; +} + +function blurh(blur, T, S, w, h) { + for (let y = 0, n = w * h; y < n;) { + blur(T, S, y, y += w, 1); + } +} + +function blurv(blur, T, S, w, h) { + for (let x = 0, n = w * h; x < w; ++x) { + blur(T, S, x, x + n, w); + } +} + +function blurfImage(radius) { + const blur = blurf(radius); + return (T, S, start, stop, step) => { + start <<= 2, stop <<= 2, step <<= 2; + blur(T, S, start + 0, stop + 0, step); + blur(T, S, start + 1, stop + 1, step); + blur(T, S, start + 2, stop + 2, step); + blur(T, S, start + 3, stop + 3, step); + }; +} + +// Given a target array T, a source array S, sets each value T[i] to the average +// of {S[i - r], …, S[i], …, S[i + r]}, where r = ⌊radius⌋, start <= i < stop, +// for each i, i + step, i + 2 * step, etc., and where S[j] is clamped between +// S[start] (inclusive) and S[stop] (exclusive). If the given radius is not an +// integer, S[i - r - 1] and S[i + r + 1] are added to the sum, each weighted +// according to r - ⌊radius⌋. +function blurf(radius) { + const radius0 = Math.floor(radius); + if (radius0 === radius) return bluri(radius); + const t = radius - radius0; + const w = 2 * radius + 1; + return (T, S, start, stop, step) => { // stop must be aligned! + if (!((stop -= step) >= start)) return; // inclusive stop + let sum = radius0 * S[start]; + const s0 = step * radius0; + const s1 = s0 + step; + for (let i = start, j = start + s0; i < j; i += step) { + sum += S[Math.min(stop, i)]; + } + for (let i = start, j = stop; i <= j; i += step) { + sum += S[Math.min(stop, i + s0)]; + T[i] = (sum + t * (S[Math.max(start, i - s1)] + S[Math.min(stop, i + s1)])) / w; + sum -= S[Math.max(start, i - s0)]; + } + }; +} + +// Like blurf, but optimized for integer radius. +function bluri(radius) { + const w = 2 * radius + 1; + return (T, S, start, stop, step) => { // stop must be aligned! + if (!((stop -= step) >= start)) return; // inclusive stop + let sum = radius * S[start]; + const s = step * radius; + for (let i = start, j = start + s; i < j; i += step) { + sum += S[Math.min(stop, i)]; + } + for (let i = start, j = stop; i <= j; i += step) { + sum += S[Math.min(stop, i + s)]; + T[i] = sum / w; + sum -= S[Math.max(start, i - s)]; + } + }; +} + +function count(values, valueof) { + let count = 0; + if (valueof === undefined) { + for (let value of values) { + if (value != null && (value = +value) >= value) { + ++count; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && (value = +value) >= value) { + ++count; + } + } + } + return count; +} + +function length$1(array) { + return array.length | 0; +} + +function empty(length) { + return !(length > 0); +} + +function arrayify(values) { + return typeof values !== "object" || "length" in values ? values : Array.from(values); +} + +function reducer(reduce) { + return values => reduce(...values); +} + +function cross(...values) { + const reduce = typeof values[values.length - 1] === "function" && reducer(values.pop()); + values = values.map(arrayify); + const lengths = values.map(length$1); + const j = values.length - 1; + const index = new Array(j + 1).fill(0); + const product = []; + if (j < 0 || lengths.some(empty)) return product; + while (true) { + product.push(index.map((j, i) => values[i][j])); + let i = j; + while (++index[i] === lengths[i]) { + if (i === 0) return reduce ? product.map(reduce) : product; + index[i--] = 0; + } + } +} + +function cumsum(values, valueof) { + var sum = 0, index = 0; + return Float64Array.from(values, valueof === undefined + ? v => (sum += +v || 0) + : v => (sum += +valueof(v, index++, values) || 0)); +} + +function variance(values, valueof) { + let count = 0; + let delta; + let mean = 0; + let sum = 0; + if (valueof === undefined) { + for (let value of values) { + if (value != null && (value = +value) >= value) { + delta = value - mean; + mean += delta / ++count; + sum += delta * (value - mean); + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && (value = +value) >= value) { + delta = value - mean; + mean += delta / ++count; + sum += delta * (value - mean); + } + } + } + if (count > 1) return sum / (count - 1); +} + +function deviation(values, valueof) { + const v = variance(values, valueof); + return v ? Math.sqrt(v) : v; +} + +function extent(values, valueof) { + let min; + let max; + if (valueof === undefined) { + for (const value of values) { + if (value != null) { + if (min === undefined) { + if (value >= value) min = max = value; + } else { + if (min > value) min = value; + if (max < value) max = value; + } + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null) { + if (min === undefined) { + if (value >= value) min = max = value; + } else { + if (min > value) min = value; + if (max < value) max = value; + } + } + } + } + return [min, max]; +} + +// https://github.com/python/cpython/blob/a74eea238f5baba15797e2e8b570d153bc8690a7/Modules/mathmodule.c#L1423 +class Adder { + constructor() { + this._partials = new Float64Array(32); + this._n = 0; + } + add(x) { + const p = this._partials; + let i = 0; + for (let j = 0; j < this._n && j < 32; j++) { + const y = p[j], + hi = x + y, + lo = Math.abs(x) < Math.abs(y) ? x - (hi - y) : y - (hi - x); + if (lo) p[i++] = lo; + x = hi; + } + p[i] = x; + this._n = i + 1; + return this; + } + valueOf() { + const p = this._partials; + let n = this._n, x, y, lo, hi = 0; + if (n > 0) { + hi = p[--n]; + while (n > 0) { + x = hi; + y = p[--n]; + hi = x + y; + lo = y - (hi - x); + if (lo) break; + } + if (n > 0 && ((lo < 0 && p[n - 1] < 0) || (lo > 0 && p[n - 1] > 0))) { + y = lo * 2; + x = hi + y; + if (y == x - hi) hi = x; + } + } + return hi; + } +} + +function fsum(values, valueof) { + const adder = new Adder(); + if (valueof === undefined) { + for (let value of values) { + if (value = +value) { + adder.add(value); + } + } + } else { + let index = -1; + for (let value of values) { + if (value = +valueof(value, ++index, values)) { + adder.add(value); + } + } + } + return +adder; +} + +function fcumsum(values, valueof) { + const adder = new Adder(); + let index = -1; + return Float64Array.from(values, valueof === undefined + ? v => adder.add(+v || 0) + : v => adder.add(+valueof(v, ++index, values) || 0) + ); +} + +class InternMap extends Map { + constructor(entries, key = keyof) { + super(); + Object.defineProperties(this, {_intern: {value: new Map()}, _key: {value: key}}); + if (entries != null) for (const [key, value] of entries) this.set(key, value); + } + get(key) { + return super.get(intern_get(this, key)); + } + has(key) { + return super.has(intern_get(this, key)); + } + set(key, value) { + return super.set(intern_set(this, key), value); + } + delete(key) { + return super.delete(intern_delete(this, key)); + } +} + +class InternSet extends Set { + constructor(values, key = keyof) { + super(); + Object.defineProperties(this, {_intern: {value: new Map()}, _key: {value: key}}); + if (values != null) for (const value of values) this.add(value); + } + has(value) { + return super.has(intern_get(this, value)); + } + add(value) { + return super.add(intern_set(this, value)); + } + delete(value) { + return super.delete(intern_delete(this, value)); + } +} + +function intern_get({_intern, _key}, value) { + const key = _key(value); + return _intern.has(key) ? _intern.get(key) : value; +} + +function intern_set({_intern, _key}, value) { + const key = _key(value); + if (_intern.has(key)) return _intern.get(key); + _intern.set(key, value); + return value; +} + +function intern_delete({_intern, _key}, value) { + const key = _key(value); + if (_intern.has(key)) { + value = _intern.get(key); + _intern.delete(key); + } + return value; +} + +function keyof(value) { + return value !== null && typeof value === "object" ? value.valueOf() : value; +} + +function identity(x) { + return x; +} + +function group(values, ...keys) { + return nest(values, identity, identity, keys); +} + +function groups(values, ...keys) { + return nest(values, Array.from, identity, keys); +} + +function flatten$1(groups, keys) { + for (let i = 1, n = keys.length; i < n; ++i) { + groups = groups.flatMap(g => g.pop().map(([key, value]) => [...g, key, value])); + } + return groups; +} + +function flatGroup(values, ...keys) { + return flatten$1(groups(values, ...keys), keys); +} + +function flatRollup(values, reduce, ...keys) { + return flatten$1(rollups(values, reduce, ...keys), keys); +} + +function rollup(values, reduce, ...keys) { + return nest(values, identity, reduce, keys); +} + +function rollups(values, reduce, ...keys) { + return nest(values, Array.from, reduce, keys); +} + +function index(values, ...keys) { + return nest(values, identity, unique, keys); +} + +function indexes(values, ...keys) { + return nest(values, Array.from, unique, keys); +} + +function unique(values) { + if (values.length !== 1) throw new Error("duplicate key"); + return values[0]; +} + +function nest(values, map, reduce, keys) { + return (function regroup(values, i) { + if (i >= keys.length) return reduce(values); + const groups = new InternMap(); + const keyof = keys[i++]; + let index = -1; + for (const value of values) { + const key = keyof(value, ++index, values); + const group = groups.get(key); + if (group) group.push(value); + else groups.set(key, [value]); + } + for (const [key, values] of groups) { + groups.set(key, regroup(values, i)); + } + return map(groups); + })(values, 0); +} + +function permute(source, keys) { + return Array.from(keys, key => source[key]); +} + +function sort(values, ...F) { + if (typeof values[Symbol.iterator] !== "function") throw new TypeError("values is not iterable"); + values = Array.from(values); + let [f] = F; + if ((f && f.length !== 2) || F.length > 1) { + const index = Uint32Array.from(values, (d, i) => i); + if (F.length > 1) { + F = F.map(f => values.map(f)); + index.sort((i, j) => { + for (const f of F) { + const c = ascendingDefined(f[i], f[j]); + if (c) return c; + } + }); + } else { + f = values.map(f); + index.sort((i, j) => ascendingDefined(f[i], f[j])); + } + return permute(values, index); + } + return values.sort(compareDefined(f)); +} + +function compareDefined(compare = ascending) { + if (compare === ascending) return ascendingDefined; + if (typeof compare !== "function") throw new TypeError("compare is not a function"); + return (a, b) => { + const x = compare(a, b); + if (x || x === 0) return x; + return (compare(b, b) === 0) - (compare(a, a) === 0); + }; +} + +function ascendingDefined(a, b) { + return (a == null || !(a >= a)) - (b == null || !(b >= b)) || (a < b ? -1 : a > b ? 1 : 0); +} + +function groupSort(values, reduce, key) { + return (reduce.length !== 2 + ? sort(rollup(values, reduce, key), (([ak, av], [bk, bv]) => ascending(av, bv) || ascending(ak, bk))) + : sort(group(values, key), (([ak, av], [bk, bv]) => reduce(av, bv) || ascending(ak, bk)))) + .map(([key]) => key); +} + +var array = Array.prototype; + +var slice = array.slice; + +function constant(x) { + return () => x; +} + +const e10 = Math.sqrt(50), + e5 = Math.sqrt(10), + e2 = Math.sqrt(2); + +function tickSpec(start, stop, count) { + const step = (stop - start) / Math.max(0, count), + power = Math.floor(Math.log10(step)), + error = step / Math.pow(10, power), + factor = error >= e10 ? 10 : error >= e5 ? 5 : error >= e2 ? 2 : 1; + let i1, i2, inc; + if (power < 0) { + inc = Math.pow(10, -power) / factor; + i1 = Math.round(start * inc); + i2 = Math.round(stop * inc); + if (i1 / inc < start) ++i1; + if (i2 / inc > stop) --i2; + inc = -inc; + } else { + inc = Math.pow(10, power) * factor; + i1 = Math.round(start / inc); + i2 = Math.round(stop / inc); + if (i1 * inc < start) ++i1; + if (i2 * inc > stop) --i2; + } + if (i2 < i1 && 0.5 <= count && count < 2) return tickSpec(start, stop, count * 2); + return [i1, i2, inc]; +} + +function ticks(start, stop, count) { + stop = +stop, start = +start, count = +count; + if (!(count > 0)) return []; + if (start === stop) return [start]; + const reverse = stop < start, [i1, i2, inc] = reverse ? tickSpec(stop, start, count) : tickSpec(start, stop, count); + if (!(i2 >= i1)) return []; + const n = i2 - i1 + 1, ticks = new Array(n); + if (reverse) { + if (inc < 0) for (let i = 0; i < n; ++i) ticks[i] = (i2 - i) / -inc; + else for (let i = 0; i < n; ++i) ticks[i] = (i2 - i) * inc; + } else { + if (inc < 0) for (let i = 0; i < n; ++i) ticks[i] = (i1 + i) / -inc; + else for (let i = 0; i < n; ++i) ticks[i] = (i1 + i) * inc; + } + return ticks; +} + +function tickIncrement(start, stop, count) { + stop = +stop, start = +start, count = +count; + return tickSpec(start, stop, count)[2]; +} + +function tickStep(start, stop, count) { + stop = +stop, start = +start, count = +count; + const reverse = stop < start, inc = reverse ? tickIncrement(stop, start, count) : tickIncrement(start, stop, count); + return (reverse ? -1 : 1) * (inc < 0 ? 1 / -inc : inc); +} + +function nice(start, stop, count) { + let prestep; + while (true) { + const step = tickIncrement(start, stop, count); + if (step === prestep || step === 0 || !isFinite(step)) { + return [start, stop]; + } else if (step > 0) { + start = Math.floor(start / step) * step; + stop = Math.ceil(stop / step) * step; + } else if (step < 0) { + start = Math.ceil(start * step) / step; + stop = Math.floor(stop * step) / step; + } + prestep = step; + } +} + +function thresholdSturges(values) { + return Math.max(1, Math.ceil(Math.log(count(values)) / Math.LN2) + 1); +} + +function bin() { + var value = identity, + domain = extent, + threshold = thresholdSturges; + + function histogram(data) { + if (!Array.isArray(data)) data = Array.from(data); + + var i, + n = data.length, + x, + step, + values = new Array(n); + + for (i = 0; i < n; ++i) { + values[i] = value(data[i], i, data); + } + + var xz = domain(values), + x0 = xz[0], + x1 = xz[1], + tz = threshold(values, x0, x1); + + // Convert number of thresholds into uniform thresholds, and nice the + // default domain accordingly. + if (!Array.isArray(tz)) { + const max = x1, tn = +tz; + if (domain === extent) [x0, x1] = nice(x0, x1, tn); + tz = ticks(x0, x1, tn); + + // If the domain is aligned with the first tick (which it will by + // default), then we can use quantization rather than bisection to bin + // values, which is substantially faster. + if (tz[0] <= x0) step = tickIncrement(x0, x1, tn); + + // If the last threshold is coincident with the domain’s upper bound, the + // last bin will be zero-width. If the default domain is used, and this + // last threshold is coincident with the maximum input value, we can + // extend the niced upper bound by one tick to ensure uniform bin widths; + // otherwise, we simply remove the last threshold. Note that we don’t + // coerce values or the domain to numbers, and thus must be careful to + // compare order (>=) rather than strict equality (===)! + if (tz[tz.length - 1] >= x1) { + if (max >= x1 && domain === extent) { + const step = tickIncrement(x0, x1, tn); + if (isFinite(step)) { + if (step > 0) { + x1 = (Math.floor(x1 / step) + 1) * step; + } else if (step < 0) { + x1 = (Math.ceil(x1 * -step) + 1) / -step; + } + } + } else { + tz.pop(); + } + } + } + + // Remove any thresholds outside the domain. + // Be careful not to mutate an array owned by the user! + var m = tz.length, a = 0, b = m; + while (tz[a] <= x0) ++a; + while (tz[b - 1] > x1) --b; + if (a || b < m) tz = tz.slice(a, b), m = b - a; + + var bins = new Array(m + 1), + bin; + + // Initialize bins. + for (i = 0; i <= m; ++i) { + bin = bins[i] = []; + bin.x0 = i > 0 ? tz[i - 1] : x0; + bin.x1 = i < m ? tz[i] : x1; + } + + // Assign data to bins by value, ignoring any outside the domain. + if (isFinite(step)) { + if (step > 0) { + for (i = 0; i < n; ++i) { + if ((x = values[i]) != null && x0 <= x && x <= x1) { + bins[Math.min(m, Math.floor((x - x0) / step))].push(data[i]); + } + } + } else if (step < 0) { + for (i = 0; i < n; ++i) { + if ((x = values[i]) != null && x0 <= x && x <= x1) { + const j = Math.floor((x0 - x) * step); + bins[Math.min(m, j + (tz[j] <= x))].push(data[i]); // handle off-by-one due to rounding + } + } + } + } else { + for (i = 0; i < n; ++i) { + if ((x = values[i]) != null && x0 <= x && x <= x1) { + bins[bisect(tz, x, 0, m)].push(data[i]); + } + } + } + + return bins; + } + + histogram.value = function(_) { + return arguments.length ? (value = typeof _ === "function" ? _ : constant(_), histogram) : value; + }; + + histogram.domain = function(_) { + return arguments.length ? (domain = typeof _ === "function" ? _ : constant([_[0], _[1]]), histogram) : domain; + }; + + histogram.thresholds = function(_) { + return arguments.length ? (threshold = typeof _ === "function" ? _ : constant(Array.isArray(_) ? slice.call(_) : _), histogram) : threshold; + }; + + return histogram; +} + +function max(values, valueof) { + let max; + if (valueof === undefined) { + for (const value of values) { + if (value != null + && (max < value || (max === undefined && value >= value))) { + max = value; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null + && (max < value || (max === undefined && value >= value))) { + max = value; + } + } + } + return max; +} + +function maxIndex(values, valueof) { + let max; + let maxIndex = -1; + let index = -1; + if (valueof === undefined) { + for (const value of values) { + ++index; + if (value != null + && (max < value || (max === undefined && value >= value))) { + max = value, maxIndex = index; + } + } + } else { + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null + && (max < value || (max === undefined && value >= value))) { + max = value, maxIndex = index; + } + } + } + return maxIndex; +} + +function min(values, valueof) { + let min; + if (valueof === undefined) { + for (const value of values) { + if (value != null + && (min > value || (min === undefined && value >= value))) { + min = value; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null + && (min > value || (min === undefined && value >= value))) { + min = value; + } + } + } + return min; +} + +function minIndex(values, valueof) { + let min; + let minIndex = -1; + let index = -1; + if (valueof === undefined) { + for (const value of values) { + ++index; + if (value != null + && (min > value || (min === undefined && value >= value))) { + min = value, minIndex = index; + } + } + } else { + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null + && (min > value || (min === undefined && value >= value))) { + min = value, minIndex = index; + } + } + } + return minIndex; +} + +// Based on https://github.com/mourner/quickselect +// ISC license, Copyright 2018 Vladimir Agafonkin. +function quickselect(array, k, left = 0, right = Infinity, compare) { + k = Math.floor(k); + left = Math.floor(Math.max(0, left)); + right = Math.floor(Math.min(array.length - 1, right)); + + if (!(left <= k && k <= right)) return array; + + compare = compare === undefined ? ascendingDefined : compareDefined(compare); + + while (right > left) { + if (right - left > 600) { + const n = right - left + 1; + const m = k - left + 1; + const z = Math.log(n); + const s = 0.5 * Math.exp(2 * z / 3); + const sd = 0.5 * Math.sqrt(z * s * (n - s) / n) * (m - n / 2 < 0 ? -1 : 1); + const newLeft = Math.max(left, Math.floor(k - m * s / n + sd)); + const newRight = Math.min(right, Math.floor(k + (n - m) * s / n + sd)); + quickselect(array, k, newLeft, newRight, compare); + } + + const t = array[k]; + let i = left; + let j = right; + + swap(array, left, k); + if (compare(array[right], t) > 0) swap(array, left, right); + + while (i < j) { + swap(array, i, j), ++i, --j; + while (compare(array[i], t) < 0) ++i; + while (compare(array[j], t) > 0) --j; + } + + if (compare(array[left], t) === 0) swap(array, left, j); + else ++j, swap(array, j, right); + + if (j <= k) left = j + 1; + if (k <= j) right = j - 1; + } + + return array; +} + +function swap(array, i, j) { + const t = array[i]; + array[i] = array[j]; + array[j] = t; +} + +function greatest(values, compare = ascending) { + let max; + let defined = false; + if (compare.length === 1) { + let maxValue; + for (const element of values) { + const value = compare(element); + if (defined + ? ascending(value, maxValue) > 0 + : ascending(value, value) === 0) { + max = element; + maxValue = value; + defined = true; + } + } + } else { + for (const value of values) { + if (defined + ? compare(value, max) > 0 + : compare(value, value) === 0) { + max = value; + defined = true; + } + } + } + return max; +} + +function quantile(values, p, valueof) { + values = Float64Array.from(numbers(values, valueof)); + if (!(n = values.length) || isNaN(p = +p)) return; + if (p <= 0 || n < 2) return min(values); + if (p >= 1) return max(values); + var n, + i = (n - 1) * p, + i0 = Math.floor(i), + value0 = max(quickselect(values, i0).subarray(0, i0 + 1)), + value1 = min(values.subarray(i0 + 1)); + return value0 + (value1 - value0) * (i - i0); +} + +function quantileSorted(values, p, valueof = number) { + if (!(n = values.length) || isNaN(p = +p)) return; + if (p <= 0 || n < 2) return +valueof(values[0], 0, values); + if (p >= 1) return +valueof(values[n - 1], n - 1, values); + var n, + i = (n - 1) * p, + i0 = Math.floor(i), + value0 = +valueof(values[i0], i0, values), + value1 = +valueof(values[i0 + 1], i0 + 1, values); + return value0 + (value1 - value0) * (i - i0); +} + +function quantileIndex(values, p, valueof = number) { + if (isNaN(p = +p)) return; + numbers = Float64Array.from(values, (_, i) => number(valueof(values[i], i, values))); + if (p <= 0) return minIndex(numbers); + if (p >= 1) return maxIndex(numbers); + var numbers, + index = Uint32Array.from(values, (_, i) => i), + j = numbers.length - 1, + i = Math.floor(j * p); + quickselect(index, i, 0, j, (i, j) => ascendingDefined(numbers[i], numbers[j])); + i = greatest(index.subarray(0, i + 1), (i) => numbers[i]); + return i >= 0 ? i : -1; +} + +function thresholdFreedmanDiaconis(values, min, max) { + const c = count(values), d = quantile(values, 0.75) - quantile(values, 0.25); + return c && d ? Math.ceil((max - min) / (2 * d * Math.pow(c, -1 / 3))) : 1; +} + +function thresholdScott(values, min, max) { + const c = count(values), d = deviation(values); + return c && d ? Math.ceil((max - min) * Math.cbrt(c) / (3.49 * d)) : 1; +} + +function mean(values, valueof) { + let count = 0; + let sum = 0; + if (valueof === undefined) { + for (let value of values) { + if (value != null && (value = +value) >= value) { + ++count, sum += value; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && (value = +value) >= value) { + ++count, sum += value; + } + } + } + if (count) return sum / count; +} + +function median(values, valueof) { + return quantile(values, 0.5, valueof); +} + +function medianIndex(values, valueof) { + return quantileIndex(values, 0.5, valueof); +} + +function* flatten(arrays) { + for (const array of arrays) { + yield* array; + } +} + +function merge(arrays) { + return Array.from(flatten(arrays)); +} + +function mode(values, valueof) { + const counts = new InternMap(); + if (valueof === undefined) { + for (let value of values) { + if (value != null && value >= value) { + counts.set(value, (counts.get(value) || 0) + 1); + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && value >= value) { + counts.set(value, (counts.get(value) || 0) + 1); + } + } + } + let modeValue; + let modeCount = 0; + for (const [value, count] of counts) { + if (count > modeCount) { + modeCount = count; + modeValue = value; + } + } + return modeValue; +} + +function pairs(values, pairof = pair) { + const pairs = []; + let previous; + let first = false; + for (const value of values) { + if (first) pairs.push(pairof(previous, value)); + previous = value; + first = true; + } + return pairs; +} + +function pair(a, b) { + return [a, b]; +} + +function range(start, stop, step) { + start = +start, stop = +stop, step = (n = arguments.length) < 2 ? (stop = start, start = 0, 1) : n < 3 ? 1 : +step; + + var i = -1, + n = Math.max(0, Math.ceil((stop - start) / step)) | 0, + range = new Array(n); + + while (++i < n) { + range[i] = start + i * step; + } + + return range; +} + +function rank(values, valueof = ascending) { + if (typeof values[Symbol.iterator] !== "function") throw new TypeError("values is not iterable"); + let V = Array.from(values); + const R = new Float64Array(V.length); + if (valueof.length !== 2) V = V.map(valueof), valueof = ascending; + const compareIndex = (i, j) => valueof(V[i], V[j]); + let k, r; + values = Uint32Array.from(V, (_, i) => i); + // Risky chaining due to Safari 14 https://github.com/d3/d3-array/issues/123 + values.sort(valueof === ascending ? (i, j) => ascendingDefined(V[i], V[j]) : compareDefined(compareIndex)); + values.forEach((j, i) => { + const c = compareIndex(j, k === undefined ? j : k); + if (c >= 0) { + if (k === undefined || c > 0) k = j, r = i; + R[j] = r; + } else { + R[j] = NaN; + } + }); + return R; +} + +function least(values, compare = ascending) { + let min; + let defined = false; + if (compare.length === 1) { + let minValue; + for (const element of values) { + const value = compare(element); + if (defined + ? ascending(value, minValue) < 0 + : ascending(value, value) === 0) { + min = element; + minValue = value; + defined = true; + } + } + } else { + for (const value of values) { + if (defined + ? compare(value, min) < 0 + : compare(value, value) === 0) { + min = value; + defined = true; + } + } + } + return min; +} + +function leastIndex(values, compare = ascending) { + if (compare.length === 1) return minIndex(values, compare); + let minValue; + let min = -1; + let index = -1; + for (const value of values) { + ++index; + if (min < 0 + ? compare(value, value) === 0 + : compare(value, minValue) < 0) { + minValue = value; + min = index; + } + } + return min; +} + +function greatestIndex(values, compare = ascending) { + if (compare.length === 1) return maxIndex(values, compare); + let maxValue; + let max = -1; + let index = -1; + for (const value of values) { + ++index; + if (max < 0 + ? compare(value, value) === 0 + : compare(value, maxValue) > 0) { + maxValue = value; + max = index; + } + } + return max; +} + +function scan(values, compare) { + const index = leastIndex(values, compare); + return index < 0 ? undefined : index; +} + +var shuffle = shuffler(Math.random); + +function shuffler(random) { + return function shuffle(array, i0 = 0, i1 = array.length) { + let m = i1 - (i0 = +i0); + while (m) { + const i = random() * m-- | 0, t = array[m + i0]; + array[m + i0] = array[i + i0]; + array[i + i0] = t; + } + return array; + }; +} + +function sum(values, valueof) { + let sum = 0; + if (valueof === undefined) { + for (let value of values) { + if (value = +value) { + sum += value; + } + } + } else { + let index = -1; + for (let value of values) { + if (value = +valueof(value, ++index, values)) { + sum += value; + } + } + } + return sum; +} + +function transpose(matrix) { + if (!(n = matrix.length)) return []; + for (var i = -1, m = min(matrix, length), transpose = new Array(m); ++i < m;) { + for (var j = -1, n, row = transpose[i] = new Array(n); ++j < n;) { + row[j] = matrix[j][i]; + } + } + return transpose; +} + +function length(d) { + return d.length; +} + +function zip() { + return transpose(arguments); +} + +function every(values, test) { + if (typeof test !== "function") throw new TypeError("test is not a function"); + let index = -1; + for (const value of values) { + if (!test(value, ++index, values)) { + return false; + } + } + return true; +} + +function some(values, test) { + if (typeof test !== "function") throw new TypeError("test is not a function"); + let index = -1; + for (const value of values) { + if (test(value, ++index, values)) { + return true; + } + } + return false; +} + +function filter(values, test) { + if (typeof test !== "function") throw new TypeError("test is not a function"); + const array = []; + let index = -1; + for (const value of values) { + if (test(value, ++index, values)) { + array.push(value); + } + } + return array; +} + +function map(values, mapper) { + if (typeof values[Symbol.iterator] !== "function") throw new TypeError("values is not iterable"); + if (typeof mapper !== "function") throw new TypeError("mapper is not a function"); + return Array.from(values, (value, index) => mapper(value, index, values)); +} + +function reduce(values, reducer, value) { + if (typeof reducer !== "function") throw new TypeError("reducer is not a function"); + const iterator = values[Symbol.iterator](); + let done, next, index = -1; + if (arguments.length < 3) { + ({done, value} = iterator.next()); + if (done) return; + ++index; + } + while (({done, value: next} = iterator.next()), !done) { + value = reducer(value, next, ++index, values); + } + return value; +} + +function reverse(values) { + if (typeof values[Symbol.iterator] !== "function") throw new TypeError("values is not iterable"); + return Array.from(values).reverse(); +} + +function difference(values, ...others) { + values = new InternSet(values); + for (const other of others) { + for (const value of other) { + values.delete(value); + } + } + return values; +} + +function disjoint(values, other) { + const iterator = other[Symbol.iterator](), set = new InternSet(); + for (const v of values) { + if (set.has(v)) return false; + let value, done; + while (({value, done} = iterator.next())) { + if (done) break; + if (Object.is(v, value)) return false; + set.add(value); + } + } + return true; +} + +function intersection(values, ...others) { + values = new InternSet(values); + others = others.map(set); + out: for (const value of values) { + for (const other of others) { + if (!other.has(value)) { + values.delete(value); + continue out; + } + } + } + return values; +} + +function set(values) { + return values instanceof InternSet ? values : new InternSet(values); +} + +function superset(values, other) { + const iterator = values[Symbol.iterator](), set = new Set(); + for (const o of other) { + const io = intern(o); + if (set.has(io)) continue; + let value, done; + while (({value, done} = iterator.next())) { + if (done) return false; + const ivalue = intern(value); + set.add(ivalue); + if (Object.is(io, ivalue)) break; + } + } + return true; +} + +function intern(value) { + return value !== null && typeof value === "object" ? value.valueOf() : value; +} + +function subset(values, other) { + return superset(other, values); +} + +function union(...others) { + const set = new InternSet(); + for (const other of others) { + for (const o of other) { + set.add(o); + } + } + return set; +} + +exports.Adder = Adder; +exports.InternMap = InternMap; +exports.InternSet = InternSet; +exports.ascending = ascending; +exports.bin = bin; +exports.bisect = bisect; +exports.bisectCenter = bisectCenter; +exports.bisectLeft = bisectLeft; +exports.bisectRight = bisectRight; +exports.bisector = bisector; +exports.blur = blur; +exports.blur2 = blur2; +exports.blurImage = blurImage; +exports.count = count; +exports.cross = cross; +exports.cumsum = cumsum; +exports.descending = descending; +exports.deviation = deviation; +exports.difference = difference; +exports.disjoint = disjoint; +exports.every = every; +exports.extent = extent; +exports.fcumsum = fcumsum; +exports.filter = filter; +exports.flatGroup = flatGroup; +exports.flatRollup = flatRollup; +exports.fsum = fsum; +exports.greatest = greatest; +exports.greatestIndex = greatestIndex; +exports.group = group; +exports.groupSort = groupSort; +exports.groups = groups; +exports.histogram = bin; +exports.index = index; +exports.indexes = indexes; +exports.intersection = intersection; +exports.least = least; +exports.leastIndex = leastIndex; +exports.map = map; +exports.max = max; +exports.maxIndex = maxIndex; +exports.mean = mean; +exports.median = median; +exports.medianIndex = medianIndex; +exports.merge = merge; +exports.min = min; +exports.minIndex = minIndex; +exports.mode = mode; +exports.nice = nice; +exports.pairs = pairs; +exports.permute = permute; +exports.quantile = quantile; +exports.quantileIndex = quantileIndex; +exports.quantileSorted = quantileSorted; +exports.quickselect = quickselect; +exports.range = range; +exports.rank = rank; +exports.reduce = reduce; +exports.reverse = reverse; +exports.rollup = rollup; +exports.rollups = rollups; +exports.scan = scan; +exports.shuffle = shuffle; +exports.shuffler = shuffler; +exports.some = some; +exports.sort = sort; +exports.subset = subset; +exports.sum = sum; +exports.superset = superset; +exports.thresholdFreedmanDiaconis = thresholdFreedmanDiaconis; +exports.thresholdScott = thresholdScott; +exports.thresholdSturges = thresholdSturges; +exports.tickIncrement = tickIncrement; +exports.tickStep = tickStep; +exports.ticks = ticks; +exports.transpose = transpose; +exports.union = union; +exports.variance = variance; +exports.zip = zip; + +})); diff --git a/frontend/node_modules/d3-array/dist/d3-array.min.js b/frontend/node_modules/d3-array/dist/d3-array.min.js new file mode 100644 index 0000000..8ac3c09 --- /dev/null +++ b/frontend/node_modules/d3-array/dist/d3-array.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-array/ v3.2.4 Copyright 2010-2023 Mike Bostock +!function(t,n){"object"==typeof exports&&"undefined"!=typeof module?n(exports):"function"==typeof define&&define.amd?define(["exports"],n):n((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{})}(this,(function(t){"use strict";function n(t,n){return null==t||null==n?NaN:tn?1:t>=n?0:NaN}function r(t,n){return null==t||null==n?NaN:nt?1:n>=t?0:NaN}function e(t){let e,f,i;function u(t,n,r=0,o=t.length){if(r>>1;f(t[e],n)<0?r=e+1:o=e}while(rn(t(r),e),i=(n,r)=>t(n)-r):(e=t===n||t===r?t:o,f=t,i=t),{left:u,center:function(t,n,r=0,e=t.length){const o=u(t,n,r,e-1);return o>r&&i(t[o-1],n)>-i(t[o],n)?o-1:o},right:function(t,n,r=0,o=t.length){if(r>>1;f(t[e],n)<=0?r=e+1:o=e}while(r{n(t,r,(e<<=2)+0,(o<<=2)+0,f<<=2),n(t,r,e+1,o+1,f),n(t,r,e+2,o+2,f),n(t,r,e+3,o+3,f)}}));function d(t){return function(n,r,e=r){if(!((r=+r)>=0))throw new RangeError("invalid rx");if(!((e=+e)>=0))throw new RangeError("invalid ry");let{data:o,width:f,height:i}=n;if(!((f=Math.floor(f))>=0))throw new RangeError("invalid width");if(!((i=Math.floor(void 0!==i?i:o.length/f))>=0))throw new RangeError("invalid height");if(!f||!i||!r&&!e)return n;const u=r&&t(r),l=e&&t(e),c=o.slice();return u&&l?(p(u,c,o,f,i),p(u,o,c,f,i),p(u,c,o,f,i),y(l,o,c,f,i),y(l,c,o,f,i),y(l,o,c,f,i)):u?(p(u,o,c,f,i),p(u,c,o,f,i),p(u,o,c,f,i)):l&&(y(l,o,c,f,i),y(l,c,o,f,i),y(l,o,c,f,i)),n}}function p(t,n,r,e,o){for(let f=0,i=e*o;f{if(!((f-=i)>=o))return;let u=t*e[o];const l=i*t;for(let t=o,n=o+l;t{if(!((i-=u)>=f))return;let l=n*o[f];const c=u*n,s=c+u;for(let t=f,n=f+c;t=n&&++r;else{let e=-1;for(let o of t)null!=(o=n(o,++e,t))&&(o=+o)>=o&&++r}return r}function v(t){return 0|t.length}function M(t){return!(t>0)}function w(t){return"object"!=typeof t||"length"in t?t:Array.from(t)}function b(t,n){let r,e=0,o=0,f=0;if(void 0===n)for(let n of t)null!=n&&(n=+n)>=n&&(r=n-o,o+=r/++e,f+=r*(n-o));else{let i=-1;for(let u of t)null!=(u=n(u,++i,t))&&(u=+u)>=u&&(r=u-o,o+=r/++e,f+=r*(u-o))}if(e>1)return f/(e-1)}function A(t,n){const r=b(t,n);return r?Math.sqrt(r):r}function x(t,n){let r,e;if(void 0===n)for(const n of t)null!=n&&(void 0===r?n>=n&&(r=e=n):(r>n&&(r=n),e=f&&(r=e=f):(r>f&&(r=f),e0){for(f=t[--o];o>0&&(n=f,r=t[--o],f=n+r,e=r-(f-n),!e););o>0&&(e<0&&t[o-1]<0||e>0&&t[o-1]>0)&&(r=2*e,n=f+r,r==n-f&&(f=n))}return f}}class InternMap extends Map{constructor(t,n=k){if(super(),Object.defineProperties(this,{_intern:{value:new Map},_key:{value:n}}),null!=t)for(const[n,r]of t)this.set(n,r)}get(t){return super.get(E(this,t))}has(t){return super.has(E(this,t))}set(t,n){return super.set(_(this,t),n)}delete(t){return super.delete(S(this,t))}}class InternSet extends Set{constructor(t,n=k){if(super(),Object.defineProperties(this,{_intern:{value:new Map},_key:{value:n}}),null!=t)for(const n of t)this.add(n)}has(t){return super.has(E(this,t))}add(t){return super.add(_(this,t))}delete(t){return super.delete(S(this,t))}}function E({_intern:t,_key:n},r){const e=n(r);return t.has(e)?t.get(e):r}function _({_intern:t,_key:n},r){const e=n(r);return t.has(e)?t.get(e):(t.set(e,r),r)}function S({_intern:t,_key:n},r){const e=n(r);return t.has(e)&&(r=t.get(e),t.delete(e)),r}function k(t){return null!==t&&"object"==typeof t?t.valueOf():t}function T(t){return t}function F(t,...n){return U(t,T,T,n)}function I(t,...n){return U(t,Array.from,T,n)}function j(t,n){for(let r=1,e=n.length;rt.pop().map((([n,r])=>[...t,n,r]))));return t}function q(t,n,...r){return U(t,T,n,r)}function R(t,n,...r){return U(t,Array.from,n,r)}function O(t){if(1!==t.length)throw new Error("duplicate key");return t[0]}function U(t,n,r,e){return function t(o,f){if(f>=e.length)return r(o);const i=new InternMap,u=e[f++];let l=-1;for(const t of o){const n=u(t,++l,o),r=i.get(n);r?r.push(t):i.set(n,[t])}for(const[n,r]of i)i.set(n,t(r,f));return n(i)}(t,0)}function L(t,n){return Array.from(n,(n=>t[n]))}function P(t,...n){if("function"!=typeof t[Symbol.iterator])throw new TypeError("values is not iterable");t=Array.from(t);let[r]=n;if(r&&2!==r.length||n.length>1){const e=Uint32Array.from(t,((t,n)=>n));return n.length>1?(n=n.map((n=>t.map(n))),e.sort(((t,r)=>{for(const e of n){const n=C(e[t],e[r]);if(n)return n}}))):(r=t.map(r),e.sort(((t,n)=>C(r[t],r[n])))),L(t,e)}return t.sort(z(r))}function z(t=n){if(t===n)return C;if("function"!=typeof t)throw new TypeError("compare is not a function");return(n,r)=>{const e=t(n,r);return e||0===e?e:(0===t(r,r))-(0===t(n,n))}}function C(t,n){return(null==t||!(t>=t))-(null==n||!(n>=n))||(tn?1:0)}var D=Array.prototype.slice;function G(t){return()=>t}const B=Math.sqrt(50),H=Math.sqrt(10),J=Math.sqrt(2);function K(t,n,r){const e=(n-t)/Math.max(0,r),o=Math.floor(Math.log10(e)),f=e/Math.pow(10,o),i=f>=B?10:f>=H?5:f>=J?2:1;let u,l,c;return o<0?(c=Math.pow(10,-o)/i,u=Math.round(t*c),l=Math.round(n*c),u/cn&&--l,c=-c):(c=Math.pow(10,o)*i,u=Math.round(t/c),l=Math.round(n/c),u*cn&&--l),l0))return[];if((t=+t)===(n=+n))return[t];const e=n=o))return[];const u=f-o+1,l=new Array(u);if(e)if(i<0)for(let t=0;t0?(t=Math.floor(t/o)*o,n=Math.ceil(n/o)*o):o<0&&(t=Math.ceil(t*o)/o,n=Math.floor(n*o)/o),e=o}}function X(t){return Math.max(1,Math.ceil(Math.log(g(t))/Math.LN2)+1)}function Y(){var t=T,n=x,r=X;function e(e){Array.isArray(e)||(e=Array.from(e));var o,f,i,u=e.length,l=new Array(u);for(o=0;o=h)if(t>=h&&n===x){const t=V(a,h,r);isFinite(t)&&(t>0?h=(Math.floor(h/t)+1)*t:t<0&&(h=(Math.ceil(h*-t)+1)/-t))}else d.pop()}for(var p=d.length,y=0,m=p;d[y]<=a;)++y;for(;d[m-1]>h;)--m;(y||m0?d[o-1]:a,g.x1=o0)for(o=0;o=n)&&(r=n);else{let e=-1;for(let o of t)null!=(o=n(o,++e,t))&&(r=o)&&(r=o)}return r}function $(t,n){let r,e=-1,o=-1;if(void 0===n)for(const n of t)++o,null!=n&&(r=n)&&(r=n,e=o);else for(let f of t)null!=(f=n(f,++o,t))&&(r=f)&&(r=f,e=o);return e}function tt(t,n){let r;if(void 0===n)for(const n of t)null!=n&&(r>n||void 0===r&&n>=n)&&(r=n);else{let e=-1;for(let o of t)null!=(o=n(o,++e,t))&&(r>o||void 0===r&&o>=o)&&(r=o)}return r}function nt(t,n){let r,e=-1,o=-1;if(void 0===n)for(const n of t)++o,null!=n&&(r>n||void 0===r&&n>=n)&&(r=n,e=o);else for(let f of t)null!=(f=n(f,++o,t))&&(r>f||void 0===r&&f>=f)&&(r=f,e=o);return e}function rt(t,n,r=0,e=1/0,o){if(n=Math.floor(n),r=Math.floor(Math.max(0,r)),e=Math.floor(Math.min(t.length-1,e)),!(r<=n&&n<=e))return t;for(o=void 0===o?C:z(o);e>r;){if(e-r>600){const f=e-r+1,i=n-r+1,u=Math.log(f),l=.5*Math.exp(2*u/3),c=.5*Math.sqrt(u*l*(f-l)/f)*(i-f/2<0?-1:1);rt(t,n,Math.max(r,Math.floor(n-i*l/f+c)),Math.min(e,Math.floor(n+(f-i)*l/f+c)),o)}const f=t[n];let i=r,u=e;for(et(t,r,n),o(t[e],f)>0&&et(t,r,e);i0;)--u}0===o(t[r],f)?et(t,r,u):(++u,et(t,u,e)),u<=n&&(r=u+1),n<=u&&(e=u-1)}return t}function et(t,n,r){const e=t[n];t[n]=t[r],t[r]=e}function ot(t,r=n){let e,o=!1;if(1===r.length){let f;for(const i of t){const t=r(i);(o?n(t,f)>0:0===n(t,t))&&(e=i,f=t,o=!0)}}else for(const n of t)(o?r(n,e)>0:0===r(n,n))&&(e=n,o=!0);return e}function ft(t,n,r){if(t=Float64Array.from(function*(t,n){if(void 0===n)for(let n of t)null!=n&&(n=+n)>=n&&(yield n);else{let r=-1;for(let e of t)null!=(e=n(e,++r,t))&&(e=+e)>=e&&(yield e)}}(t,r)),(e=t.length)&&!isNaN(n=+n)){if(n<=0||e<2)return tt(t);if(n>=1)return Z(t);var e,o=(e-1)*n,f=Math.floor(o),i=Z(rt(t,f).subarray(0,f+1));return i+(tt(t.subarray(f+1))-i)*(o-f)}}function it(t,n,r=f){if(!isNaN(n=+n)){if(e=Float64Array.from(t,((n,e)=>f(r(t[e],e,t)))),n<=0)return nt(e);if(n>=1)return $(e);var e,o=Uint32Array.from(t,((t,n)=>n)),i=e.length-1,u=Math.floor(i*n);return rt(o,u,0,i,((t,n)=>C(e[t],e[n]))),(u=ot(o.subarray(0,u+1),(t=>e[t])))>=0?u:-1}}function ut(t,n){return[t,n]}function lt(t,r=n){if(1===r.length)return nt(t,r);let e,o=-1,f=-1;for(const n of t)++f,(o<0?0===r(n,n):r(n,e)<0)&&(e=n,o=f);return o}var ct=st(Math.random);function st(t){return function(n,r=0,e=n.length){let o=e-(r=+r);for(;o;){const e=t()*o--|0,f=n[o+r];n[o+r]=n[e+r],n[e+r]=f}return n}}function at(t){if(!(o=t.length))return[];for(var n=-1,r=tt(t,ht),e=new Array(r);++n=0))throw new RangeError("invalid r");let r=t.length;if(!((r=Math.floor(r))>=0))throw new RangeError("invalid length");if(!r||!n)return t;const e=m(n),o=t.slice();return e(t,o,0,r,1),e(o,t,0,r,1),e(t,o,0,r,1),t},t.blur2=a,t.blurImage=h,t.count=g,t.cross=function(...t){const n="function"==typeof t[t.length-1]&&function(t){return n=>t(...n)}(t.pop()),r=(t=t.map(w)).map(v),e=t.length-1,o=new Array(e+1).fill(0),f=[];if(e<0||r.some(M))return f;for(;;){f.push(o.map(((n,r)=>t[r][n])));let i=e;for(;++o[i]===r[i];){if(0===i)return n?f.map(n):f;o[i--]=0}}},t.cumsum=function(t,n){var r=0,e=0;return Float64Array.from(t,void 0===n?t=>r+=+t||0:o=>r+=+n(o,e++,t)||0)},t.descending=r,t.deviation=A,t.difference=function(t,...n){t=new InternSet(t);for(const r of n)for(const n of r)t.delete(n);return t},t.disjoint=function(t,n){const r=n[Symbol.iterator](),e=new InternSet;for(const n of t){if(e.has(n))return!1;let t,o;for(;({value:t,done:o}=r.next())&&!o;){if(Object.is(n,t))return!1;e.add(t)}}return!0},t.every=function(t,n){if("function"!=typeof n)throw new TypeError("test is not a function");let r=-1;for(const e of t)if(!n(e,++r,t))return!1;return!0},t.extent=x,t.fcumsum=function(t,n){const r=new N;let e=-1;return Float64Array.from(t,void 0===n?t=>r.add(+t||0):o=>r.add(+n(o,++e,t)||0))},t.filter=function(t,n){if("function"!=typeof n)throw new TypeError("test is not a function");const r=[];let e=-1;for(const o of t)n(o,++e,t)&&r.push(o);return r},t.flatGroup=function(t,...n){return j(I(t,...n),n)},t.flatRollup=function(t,n,...r){return j(R(t,n,...r),r)},t.fsum=function(t,n){const r=new N;if(void 0===n)for(let n of t)(n=+n)&&r.add(n);else{let e=-1;for(let o of t)(o=+n(o,++e,t))&&r.add(o)}return+r},t.greatest=ot,t.greatestIndex=function(t,r=n){if(1===r.length)return $(t,r);let e,o=-1,f=-1;for(const n of t)++f,(o<0?0===r(n,n):r(n,e)>0)&&(e=n,o=f);return o},t.group=F,t.groupSort=function(t,r,e){return(2!==r.length?P(q(t,r,e),(([t,r],[e,o])=>n(r,o)||n(t,e))):P(F(t,e),(([t,e],[o,f])=>r(e,f)||n(t,o)))).map((([t])=>t))},t.groups=I,t.histogram=Y,t.index=function(t,...n){return U(t,T,O,n)},t.indexes=function(t,...n){return U(t,Array.from,O,n)},t.intersection=function(t,...n){t=new InternSet(t),n=n.map(dt);t:for(const r of t)for(const e of n)if(!e.has(r)){t.delete(r);continue t}return t},t.least=function(t,r=n){let e,o=!1;if(1===r.length){let f;for(const i of t){const t=r(i);(o?n(t,f)<0:0===n(t,t))&&(e=i,f=t,o=!0)}}else for(const n of t)(o?r(n,e)<0:0===r(n,n))&&(e=n,o=!0);return e},t.leastIndex=lt,t.map=function(t,n){if("function"!=typeof t[Symbol.iterator])throw new TypeError("values is not iterable");if("function"!=typeof n)throw new TypeError("mapper is not a function");return Array.from(t,((r,e)=>n(r,e,t)))},t.max=Z,t.maxIndex=$,t.mean=function(t,n){let r=0,e=0;if(void 0===n)for(let n of t)null!=n&&(n=+n)>=n&&(++r,e+=n);else{let o=-1;for(let f of t)null!=(f=n(f,++o,t))&&(f=+f)>=f&&(++r,e+=f)}if(r)return e/r},t.median=function(t,n){return ft(t,.5,n)},t.medianIndex=function(t,n){return it(t,.5,n)},t.merge=function(t){return Array.from(function*(t){for(const n of t)yield*n}(t))},t.min=tt,t.minIndex=nt,t.mode=function(t,n){const r=new InternMap;if(void 0===n)for(let n of t)null!=n&&n>=n&&r.set(n,(r.get(n)||0)+1);else{let e=-1;for(let o of t)null!=(o=n(o,++e,t))&&o>=o&&r.set(o,(r.get(o)||0)+1)}let e,o=0;for(const[t,n]of r)n>o&&(o=n,e=t);return e},t.nice=W,t.pairs=function(t,n=ut){const r=[];let e,o=!1;for(const f of t)o&&r.push(n(e,f)),e=f,o=!0;return r},t.permute=L,t.quantile=ft,t.quantileIndex=it,t.quantileSorted=function(t,n,r=f){if((e=t.length)&&!isNaN(n=+n)){if(n<=0||e<2)return+r(t[0],0,t);if(n>=1)return+r(t[e-1],e-1,t);var e,o=(e-1)*n,i=Math.floor(o),u=+r(t[i],i,t);return u+(+r(t[i+1],i+1,t)-u)*(o-i)}},t.quickselect=rt,t.range=function(t,n,r){t=+t,n=+n,r=(o=arguments.length)<2?(n=t,t=0,1):o<3?1:+r;for(var e=-1,o=0|Math.max(0,Math.ceil((n-t)/r)),f=new Array(o);++er(e[t],e[n]);let i,u;return(t=Uint32Array.from(e,((t,n)=>n))).sort(r===n?(t,n)=>C(e[t],e[n]):z(f)),t.forEach(((t,n)=>{const r=f(t,void 0===i?t:i);r>=0?((void 0===i||r>0)&&(i=t,u=n),o[t]=u):o[t]=NaN})),o},t.reduce=function(t,n,r){if("function"!=typeof n)throw new TypeError("reducer is not a function");const e=t[Symbol.iterator]();let o,f,i=-1;if(arguments.length<3){if(({done:o,value:r}=e.next()),o)return;++i}for(;({done:o,value:f}=e.next()),!o;)r=n(r,f,++i,t);return r},t.reverse=function(t){if("function"!=typeof t[Symbol.iterator])throw new TypeError("values is not iterable");return Array.from(t).reverse()},t.rollup=q,t.rollups=R,t.scan=function(t,n){const r=lt(t,n);return r<0?void 0:r},t.shuffle=ct,t.shuffler=st,t.some=function(t,n){if("function"!=typeof n)throw new TypeError("test is not a function");let r=-1;for(const e of t)if(n(e,++r,t))return!0;return!1},t.sort=P,t.subset=function(t,n){return pt(n,t)},t.sum=function(t,n){let r=0;if(void 0===n)for(let n of t)(n=+n)&&(r+=n);else{let e=-1;for(let o of t)(o=+n(o,++e,t))&&(r+=o)}return r},t.superset=pt,t.thresholdFreedmanDiaconis=function(t,n,r){const e=g(t),o=ft(t,.75)-ft(t,.25);return e&&o?Math.ceil((r-n)/(2*o*Math.pow(e,-1/3))):1},t.thresholdScott=function(t,n,r){const e=g(t),o=A(t);return e&&o?Math.ceil((r-n)*Math.cbrt(e)/(3.49*o)):1},t.thresholdSturges=X,t.tickIncrement=V,t.tickStep=function(t,n,r){r=+r;const e=(n=+n)<(t=+t),o=e?V(n,t,r):V(t,n,r);return(e?-1:1)*(o<0?1/-o:o)},t.ticks=Q,t.transpose=at,t.union=function(...t){const n=new InternSet;for(const r of t)for(const t of r)n.add(t);return n},t.variance=b,t.zip=function(){return at(arguments)}})); diff --git a/frontend/node_modules/d3-array/package.json b/frontend/node_modules/d3-array/package.json new file mode 100644 index 0000000..d0c54ee --- /dev/null +++ b/frontend/node_modules/d3-array/package.json @@ -0,0 +1,61 @@ +{ + "name": "d3-array", + "version": "3.2.4", + "description": "Array manipulation, ordering, searching, summarizing, etc.", + "homepage": "https://d3js.org/d3-array/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-array.git" + }, + "keywords": [ + "d3", + "d3-module", + "histogram", + "bisect", + "shuffle", + "statistics", + "search", + "sort", + "array" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "http://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-array.min.js", + "unpkg": "dist/d3-array.min.js", + "exports": { + "umd": "./dist/d3-array.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "dependencies": { + "internmap": "1 - 2" + }, + "devDependencies": { + "@rollup/plugin-node-resolve": "15", + "d3-dsv": "3", + "d3-random": "2 - 3", + "eslint": "8", + "jsdom": "21", + "mocha": "10", + "rollup": "3", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-array/src/array.js b/frontend/node_modules/d3-array/src/array.js new file mode 100644 index 0000000..8008403 --- /dev/null +++ b/frontend/node_modules/d3-array/src/array.js @@ -0,0 +1,4 @@ +var array = Array.prototype; + +export var slice = array.slice; +export var map = array.map; diff --git a/frontend/node_modules/d3-array/src/ascending.js b/frontend/node_modules/d3-array/src/ascending.js new file mode 100644 index 0000000..7527ea7 --- /dev/null +++ b/frontend/node_modules/d3-array/src/ascending.js @@ -0,0 +1,3 @@ +export default function ascending(a, b) { + return a == null || b == null ? NaN : a < b ? -1 : a > b ? 1 : a >= b ? 0 : NaN; +} diff --git a/frontend/node_modules/d3-array/src/bin.js b/frontend/node_modules/d3-array/src/bin.js new file mode 100644 index 0000000..4557e10 --- /dev/null +++ b/frontend/node_modules/d3-array/src/bin.js @@ -0,0 +1,125 @@ +import {slice} from "./array.js"; +import bisect from "./bisect.js"; +import constant from "./constant.js"; +import extent from "./extent.js"; +import identity from "./identity.js"; +import nice from "./nice.js"; +import ticks, {tickIncrement} from "./ticks.js"; +import sturges from "./threshold/sturges.js"; + +export default function bin() { + var value = identity, + domain = extent, + threshold = sturges; + + function histogram(data) { + if (!Array.isArray(data)) data = Array.from(data); + + var i, + n = data.length, + x, + step, + values = new Array(n); + + for (i = 0; i < n; ++i) { + values[i] = value(data[i], i, data); + } + + var xz = domain(values), + x0 = xz[0], + x1 = xz[1], + tz = threshold(values, x0, x1); + + // Convert number of thresholds into uniform thresholds, and nice the + // default domain accordingly. + if (!Array.isArray(tz)) { + const max = x1, tn = +tz; + if (domain === extent) [x0, x1] = nice(x0, x1, tn); + tz = ticks(x0, x1, tn); + + // If the domain is aligned with the first tick (which it will by + // default), then we can use quantization rather than bisection to bin + // values, which is substantially faster. + if (tz[0] <= x0) step = tickIncrement(x0, x1, tn); + + // If the last threshold is coincident with the domain’s upper bound, the + // last bin will be zero-width. If the default domain is used, and this + // last threshold is coincident with the maximum input value, we can + // extend the niced upper bound by one tick to ensure uniform bin widths; + // otherwise, we simply remove the last threshold. Note that we don’t + // coerce values or the domain to numbers, and thus must be careful to + // compare order (>=) rather than strict equality (===)! + if (tz[tz.length - 1] >= x1) { + if (max >= x1 && domain === extent) { + const step = tickIncrement(x0, x1, tn); + if (isFinite(step)) { + if (step > 0) { + x1 = (Math.floor(x1 / step) + 1) * step; + } else if (step < 0) { + x1 = (Math.ceil(x1 * -step) + 1) / -step; + } + } + } else { + tz.pop(); + } + } + } + + // Remove any thresholds outside the domain. + // Be careful not to mutate an array owned by the user! + var m = tz.length, a = 0, b = m; + while (tz[a] <= x0) ++a; + while (tz[b - 1] > x1) --b; + if (a || b < m) tz = tz.slice(a, b), m = b - a; + + var bins = new Array(m + 1), + bin; + + // Initialize bins. + for (i = 0; i <= m; ++i) { + bin = bins[i] = []; + bin.x0 = i > 0 ? tz[i - 1] : x0; + bin.x1 = i < m ? tz[i] : x1; + } + + // Assign data to bins by value, ignoring any outside the domain. + if (isFinite(step)) { + if (step > 0) { + for (i = 0; i < n; ++i) { + if ((x = values[i]) != null && x0 <= x && x <= x1) { + bins[Math.min(m, Math.floor((x - x0) / step))].push(data[i]); + } + } + } else if (step < 0) { + for (i = 0; i < n; ++i) { + if ((x = values[i]) != null && x0 <= x && x <= x1) { + const j = Math.floor((x0 - x) * step); + bins[Math.min(m, j + (tz[j] <= x))].push(data[i]); // handle off-by-one due to rounding + } + } + } + } else { + for (i = 0; i < n; ++i) { + if ((x = values[i]) != null && x0 <= x && x <= x1) { + bins[bisect(tz, x, 0, m)].push(data[i]); + } + } + } + + return bins; + } + + histogram.value = function(_) { + return arguments.length ? (value = typeof _ === "function" ? _ : constant(_), histogram) : value; + }; + + histogram.domain = function(_) { + return arguments.length ? (domain = typeof _ === "function" ? _ : constant([_[0], _[1]]), histogram) : domain; + }; + + histogram.thresholds = function(_) { + return arguments.length ? (threshold = typeof _ === "function" ? _ : constant(Array.isArray(_) ? slice.call(_) : _), histogram) : threshold; + }; + + return histogram; +} diff --git a/frontend/node_modules/d3-array/src/bisect.js b/frontend/node_modules/d3-array/src/bisect.js new file mode 100644 index 0000000..333a7e4 --- /dev/null +++ b/frontend/node_modules/d3-array/src/bisect.js @@ -0,0 +1,9 @@ +import ascending from "./ascending.js"; +import bisector from "./bisector.js"; +import number from "./number.js"; + +const ascendingBisect = bisector(ascending); +export const bisectRight = ascendingBisect.right; +export const bisectLeft = ascendingBisect.left; +export const bisectCenter = bisector(number).center; +export default bisectRight; diff --git a/frontend/node_modules/d3-array/src/bisector.js b/frontend/node_modules/d3-array/src/bisector.js new file mode 100644 index 0000000..07e4c34 --- /dev/null +++ b/frontend/node_modules/d3-array/src/bisector.js @@ -0,0 +1,56 @@ +import ascending from "./ascending.js"; +import descending from "./descending.js"; + +export default function bisector(f) { + let compare1, compare2, delta; + + // If an accessor is specified, promote it to a comparator. In this case we + // can test whether the search value is (self-) comparable. We can’t do this + // for a comparator (except for specific, known comparators) because we can’t + // tell if the comparator is symmetric, and an asymmetric comparator can’t be + // used to test whether a single value is comparable. + if (f.length !== 2) { + compare1 = ascending; + compare2 = (d, x) => ascending(f(d), x); + delta = (d, x) => f(d) - x; + } else { + compare1 = f === ascending || f === descending ? f : zero; + compare2 = f; + delta = f; + } + + function left(a, x, lo = 0, hi = a.length) { + if (lo < hi) { + if (compare1(x, x) !== 0) return hi; + do { + const mid = (lo + hi) >>> 1; + if (compare2(a[mid], x) < 0) lo = mid + 1; + else hi = mid; + } while (lo < hi); + } + return lo; + } + + function right(a, x, lo = 0, hi = a.length) { + if (lo < hi) { + if (compare1(x, x) !== 0) return hi; + do { + const mid = (lo + hi) >>> 1; + if (compare2(a[mid], x) <= 0) lo = mid + 1; + else hi = mid; + } while (lo < hi); + } + return lo; + } + + function center(a, x, lo = 0, hi = a.length) { + const i = left(a, x, lo, hi - 1); + return i > lo && delta(a[i - 1], x) > -delta(a[i], x) ? i - 1 : i; + } + + return {left, center, right}; +} + +function zero() { + return 0; +} diff --git a/frontend/node_modules/d3-array/src/blur.js b/frontend/node_modules/d3-array/src/blur.js new file mode 100644 index 0000000..7021cbf --- /dev/null +++ b/frontend/node_modules/d3-array/src/blur.js @@ -0,0 +1,115 @@ +export function blur(values, r) { + if (!((r = +r) >= 0)) throw new RangeError("invalid r"); + let length = values.length; + if (!((length = Math.floor(length)) >= 0)) throw new RangeError("invalid length"); + if (!length || !r) return values; + const blur = blurf(r); + const temp = values.slice(); + blur(values, temp, 0, length, 1); + blur(temp, values, 0, length, 1); + blur(values, temp, 0, length, 1); + return values; +} + +export const blur2 = Blur2(blurf); + +export const blurImage = Blur2(blurfImage); + +function Blur2(blur) { + return function(data, rx, ry = rx) { + if (!((rx = +rx) >= 0)) throw new RangeError("invalid rx"); + if (!((ry = +ry) >= 0)) throw new RangeError("invalid ry"); + let {data: values, width, height} = data; + if (!((width = Math.floor(width)) >= 0)) throw new RangeError("invalid width"); + if (!((height = Math.floor(height !== undefined ? height : values.length / width)) >= 0)) throw new RangeError("invalid height"); + if (!width || !height || (!rx && !ry)) return data; + const blurx = rx && blur(rx); + const blury = ry && blur(ry); + const temp = values.slice(); + if (blurx && blury) { + blurh(blurx, temp, values, width, height); + blurh(blurx, values, temp, width, height); + blurh(blurx, temp, values, width, height); + blurv(blury, values, temp, width, height); + blurv(blury, temp, values, width, height); + blurv(blury, values, temp, width, height); + } else if (blurx) { + blurh(blurx, values, temp, width, height); + blurh(blurx, temp, values, width, height); + blurh(blurx, values, temp, width, height); + } else if (blury) { + blurv(blury, values, temp, width, height); + blurv(blury, temp, values, width, height); + blurv(blury, values, temp, width, height); + } + return data; + }; +} + +function blurh(blur, T, S, w, h) { + for (let y = 0, n = w * h; y < n;) { + blur(T, S, y, y += w, 1); + } +} + +function blurv(blur, T, S, w, h) { + for (let x = 0, n = w * h; x < w; ++x) { + blur(T, S, x, x + n, w); + } +} + +function blurfImage(radius) { + const blur = blurf(radius); + return (T, S, start, stop, step) => { + start <<= 2, stop <<= 2, step <<= 2; + blur(T, S, start + 0, stop + 0, step); + blur(T, S, start + 1, stop + 1, step); + blur(T, S, start + 2, stop + 2, step); + blur(T, S, start + 3, stop + 3, step); + }; +} + +// Given a target array T, a source array S, sets each value T[i] to the average +// of {S[i - r], …, S[i], …, S[i + r]}, where r = ⌊radius⌋, start <= i < stop, +// for each i, i + step, i + 2 * step, etc., and where S[j] is clamped between +// S[start] (inclusive) and S[stop] (exclusive). If the given radius is not an +// integer, S[i - r - 1] and S[i + r + 1] are added to the sum, each weighted +// according to r - ⌊radius⌋. +function blurf(radius) { + const radius0 = Math.floor(radius); + if (radius0 === radius) return bluri(radius); + const t = radius - radius0; + const w = 2 * radius + 1; + return (T, S, start, stop, step) => { // stop must be aligned! + if (!((stop -= step) >= start)) return; // inclusive stop + let sum = radius0 * S[start]; + const s0 = step * radius0; + const s1 = s0 + step; + for (let i = start, j = start + s0; i < j; i += step) { + sum += S[Math.min(stop, i)]; + } + for (let i = start, j = stop; i <= j; i += step) { + sum += S[Math.min(stop, i + s0)]; + T[i] = (sum + t * (S[Math.max(start, i - s1)] + S[Math.min(stop, i + s1)])) / w; + sum -= S[Math.max(start, i - s0)]; + } + }; +} + +// Like blurf, but optimized for integer radius. +function bluri(radius) { + const w = 2 * radius + 1; + return (T, S, start, stop, step) => { // stop must be aligned! + if (!((stop -= step) >= start)) return; // inclusive stop + let sum = radius * S[start]; + const s = step * radius; + for (let i = start, j = start + s; i < j; i += step) { + sum += S[Math.min(stop, i)]; + } + for (let i = start, j = stop; i <= j; i += step) { + sum += S[Math.min(stop, i + s)]; + T[i] = sum / w; + sum -= S[Math.max(start, i - s)]; + } + }; +} diff --git a/frontend/node_modules/d3-array/src/constant.js b/frontend/node_modules/d3-array/src/constant.js new file mode 100644 index 0000000..bb0ec86 --- /dev/null +++ b/frontend/node_modules/d3-array/src/constant.js @@ -0,0 +1,3 @@ +export default function constant(x) { + return () => x; +} diff --git a/frontend/node_modules/d3-array/src/count.js b/frontend/node_modules/d3-array/src/count.js new file mode 100644 index 0000000..b8783f0 --- /dev/null +++ b/frontend/node_modules/d3-array/src/count.js @@ -0,0 +1,18 @@ +export default function count(values, valueof) { + let count = 0; + if (valueof === undefined) { + for (let value of values) { + if (value != null && (value = +value) >= value) { + ++count; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && (value = +value) >= value) { + ++count; + } + } + } + return count; +} diff --git a/frontend/node_modules/d3-array/src/cross.js b/frontend/node_modules/d3-array/src/cross.js new file mode 100644 index 0000000..7efdbe3 --- /dev/null +++ b/frontend/node_modules/d3-array/src/cross.js @@ -0,0 +1,33 @@ +function length(array) { + return array.length | 0; +} + +function empty(length) { + return !(length > 0); +} + +function arrayify(values) { + return typeof values !== "object" || "length" in values ? values : Array.from(values); +} + +function reducer(reduce) { + return values => reduce(...values); +} + +export default function cross(...values) { + const reduce = typeof values[values.length - 1] === "function" && reducer(values.pop()); + values = values.map(arrayify); + const lengths = values.map(length); + const j = values.length - 1; + const index = new Array(j + 1).fill(0); + const product = []; + if (j < 0 || lengths.some(empty)) return product; + while (true) { + product.push(index.map((j, i) => values[i][j])); + let i = j; + while (++index[i] === lengths[i]) { + if (i === 0) return reduce ? product.map(reduce) : product; + index[i--] = 0; + } + } +} diff --git a/frontend/node_modules/d3-array/src/cumsum.js b/frontend/node_modules/d3-array/src/cumsum.js new file mode 100644 index 0000000..86fb052 --- /dev/null +++ b/frontend/node_modules/d3-array/src/cumsum.js @@ -0,0 +1,6 @@ +export default function cumsum(values, valueof) { + var sum = 0, index = 0; + return Float64Array.from(values, valueof === undefined + ? v => (sum += +v || 0) + : v => (sum += +valueof(v, index++, values) || 0)); +} \ No newline at end of file diff --git a/frontend/node_modules/d3-array/src/descending.js b/frontend/node_modules/d3-array/src/descending.js new file mode 100644 index 0000000..215f81e --- /dev/null +++ b/frontend/node_modules/d3-array/src/descending.js @@ -0,0 +1,7 @@ +export default function descending(a, b) { + return a == null || b == null ? NaN + : b < a ? -1 + : b > a ? 1 + : b >= a ? 0 + : NaN; +} diff --git a/frontend/node_modules/d3-array/src/deviation.js b/frontend/node_modules/d3-array/src/deviation.js new file mode 100644 index 0000000..d5dbe7a --- /dev/null +++ b/frontend/node_modules/d3-array/src/deviation.js @@ -0,0 +1,6 @@ +import variance from "./variance.js"; + +export default function deviation(values, valueof) { + const v = variance(values, valueof); + return v ? Math.sqrt(v) : v; +} diff --git a/frontend/node_modules/d3-array/src/difference.js b/frontend/node_modules/d3-array/src/difference.js new file mode 100644 index 0000000..c19ba78 --- /dev/null +++ b/frontend/node_modules/d3-array/src/difference.js @@ -0,0 +1,11 @@ +import {InternSet} from "internmap"; + +export default function difference(values, ...others) { + values = new InternSet(values); + for (const other of others) { + for (const value of other) { + values.delete(value); + } + } + return values; +} diff --git a/frontend/node_modules/d3-array/src/disjoint.js b/frontend/node_modules/d3-array/src/disjoint.js new file mode 100644 index 0000000..d62a670 --- /dev/null +++ b/frontend/node_modules/d3-array/src/disjoint.js @@ -0,0 +1,15 @@ +import {InternSet} from "internmap"; + +export default function disjoint(values, other) { + const iterator = other[Symbol.iterator](), set = new InternSet(); + for (const v of values) { + if (set.has(v)) return false; + let value, done; + while (({value, done} = iterator.next())) { + if (done) break; + if (Object.is(v, value)) return false; + set.add(value); + } + } + return true; +} diff --git a/frontend/node_modules/d3-array/src/every.js b/frontend/node_modules/d3-array/src/every.js new file mode 100644 index 0000000..484cac2 --- /dev/null +++ b/frontend/node_modules/d3-array/src/every.js @@ -0,0 +1,10 @@ +export default function every(values, test) { + if (typeof test !== "function") throw new TypeError("test is not a function"); + let index = -1; + for (const value of values) { + if (!test(value, ++index, values)) { + return false; + } + } + return true; +} diff --git a/frontend/node_modules/d3-array/src/extent.js b/frontend/node_modules/d3-array/src/extent.js new file mode 100644 index 0000000..580171f --- /dev/null +++ b/frontend/node_modules/d3-array/src/extent.js @@ -0,0 +1,29 @@ +export default function extent(values, valueof) { + let min; + let max; + if (valueof === undefined) { + for (const value of values) { + if (value != null) { + if (min === undefined) { + if (value >= value) min = max = value; + } else { + if (min > value) min = value; + if (max < value) max = value; + } + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null) { + if (min === undefined) { + if (value >= value) min = max = value; + } else { + if (min > value) min = value; + if (max < value) max = value; + } + } + } + } + return [min, max]; +} diff --git a/frontend/node_modules/d3-array/src/filter.js b/frontend/node_modules/d3-array/src/filter.js new file mode 100644 index 0000000..d653392 --- /dev/null +++ b/frontend/node_modules/d3-array/src/filter.js @@ -0,0 +1,11 @@ +export default function filter(values, test) { + if (typeof test !== "function") throw new TypeError("test is not a function"); + const array = []; + let index = -1; + for (const value of values) { + if (test(value, ++index, values)) { + array.push(value); + } + } + return array; +} diff --git a/frontend/node_modules/d3-array/src/fsum.js b/frontend/node_modules/d3-array/src/fsum.js new file mode 100644 index 0000000..4a8e1cf --- /dev/null +++ b/frontend/node_modules/d3-array/src/fsum.js @@ -0,0 +1,69 @@ +// https://github.com/python/cpython/blob/a74eea238f5baba15797e2e8b570d153bc8690a7/Modules/mathmodule.c#L1423 +export class Adder { + constructor() { + this._partials = new Float64Array(32); + this._n = 0; + } + add(x) { + const p = this._partials; + let i = 0; + for (let j = 0; j < this._n && j < 32; j++) { + const y = p[j], + hi = x + y, + lo = Math.abs(x) < Math.abs(y) ? x - (hi - y) : y - (hi - x); + if (lo) p[i++] = lo; + x = hi; + } + p[i] = x; + this._n = i + 1; + return this; + } + valueOf() { + const p = this._partials; + let n = this._n, x, y, lo, hi = 0; + if (n > 0) { + hi = p[--n]; + while (n > 0) { + x = hi; + y = p[--n]; + hi = x + y; + lo = y - (hi - x); + if (lo) break; + } + if (n > 0 && ((lo < 0 && p[n - 1] < 0) || (lo > 0 && p[n - 1] > 0))) { + y = lo * 2; + x = hi + y; + if (y == x - hi) hi = x; + } + } + return hi; + } +} + +export function fsum(values, valueof) { + const adder = new Adder(); + if (valueof === undefined) { + for (let value of values) { + if (value = +value) { + adder.add(value); + } + } + } else { + let index = -1; + for (let value of values) { + if (value = +valueof(value, ++index, values)) { + adder.add(value); + } + } + } + return +adder; +} + +export function fcumsum(values, valueof) { + const adder = new Adder(); + let index = -1; + return Float64Array.from(values, valueof === undefined + ? v => adder.add(+v || 0) + : v => adder.add(+valueof(v, ++index, values) || 0) + ); +} diff --git a/frontend/node_modules/d3-array/src/greatest.js b/frontend/node_modules/d3-array/src/greatest.js new file mode 100644 index 0000000..521f4f5 --- /dev/null +++ b/frontend/node_modules/d3-array/src/greatest.js @@ -0,0 +1,29 @@ +import ascending from "./ascending.js"; + +export default function greatest(values, compare = ascending) { + let max; + let defined = false; + if (compare.length === 1) { + let maxValue; + for (const element of values) { + const value = compare(element); + if (defined + ? ascending(value, maxValue) > 0 + : ascending(value, value) === 0) { + max = element; + maxValue = value; + defined = true; + } + } + } else { + for (const value of values) { + if (defined + ? compare(value, max) > 0 + : compare(value, value) === 0) { + max = value; + defined = true; + } + } + } + return max; +} diff --git a/frontend/node_modules/d3-array/src/greatestIndex.js b/frontend/node_modules/d3-array/src/greatestIndex.js new file mode 100644 index 0000000..2f390e5 --- /dev/null +++ b/frontend/node_modules/d3-array/src/greatestIndex.js @@ -0,0 +1,19 @@ +import ascending from "./ascending.js"; +import maxIndex from "./maxIndex.js"; + +export default function greatestIndex(values, compare = ascending) { + if (compare.length === 1) return maxIndex(values, compare); + let maxValue; + let max = -1; + let index = -1; + for (const value of values) { + ++index; + if (max < 0 + ? compare(value, value) === 0 + : compare(value, maxValue) > 0) { + maxValue = value; + max = index; + } + } + return max; +} diff --git a/frontend/node_modules/d3-array/src/group.js b/frontend/node_modules/d3-array/src/group.js new file mode 100644 index 0000000..0c30d7e --- /dev/null +++ b/frontend/node_modules/d3-array/src/group.js @@ -0,0 +1,65 @@ +import {InternMap} from "internmap"; +import identity from "./identity.js"; + +export default function group(values, ...keys) { + return nest(values, identity, identity, keys); +} + +export function groups(values, ...keys) { + return nest(values, Array.from, identity, keys); +} + +function flatten(groups, keys) { + for (let i = 1, n = keys.length; i < n; ++i) { + groups = groups.flatMap(g => g.pop().map(([key, value]) => [...g, key, value])); + } + return groups; +} + +export function flatGroup(values, ...keys) { + return flatten(groups(values, ...keys), keys); +} + +export function flatRollup(values, reduce, ...keys) { + return flatten(rollups(values, reduce, ...keys), keys); +} + +export function rollup(values, reduce, ...keys) { + return nest(values, identity, reduce, keys); +} + +export function rollups(values, reduce, ...keys) { + return nest(values, Array.from, reduce, keys); +} + +export function index(values, ...keys) { + return nest(values, identity, unique, keys); +} + +export function indexes(values, ...keys) { + return nest(values, Array.from, unique, keys); +} + +function unique(values) { + if (values.length !== 1) throw new Error("duplicate key"); + return values[0]; +} + +function nest(values, map, reduce, keys) { + return (function regroup(values, i) { + if (i >= keys.length) return reduce(values); + const groups = new InternMap(); + const keyof = keys[i++]; + let index = -1; + for (const value of values) { + const key = keyof(value, ++index, values); + const group = groups.get(key); + if (group) group.push(value); + else groups.set(key, [value]); + } + for (const [key, values] of groups) { + groups.set(key, regroup(values, i)); + } + return map(groups); + })(values, 0); +} diff --git a/frontend/node_modules/d3-array/src/groupSort.js b/frontend/node_modules/d3-array/src/groupSort.js new file mode 100644 index 0000000..2d56ccf --- /dev/null +++ b/frontend/node_modules/d3-array/src/groupSort.js @@ -0,0 +1,10 @@ +import ascending from "./ascending.js"; +import group, {rollup} from "./group.js"; +import sort from "./sort.js"; + +export default function groupSort(values, reduce, key) { + return (reduce.length !== 2 + ? sort(rollup(values, reduce, key), (([ak, av], [bk, bv]) => ascending(av, bv) || ascending(ak, bk))) + : sort(group(values, key), (([ak, av], [bk, bv]) => reduce(av, bv) || ascending(ak, bk)))) + .map(([key]) => key); +} diff --git a/frontend/node_modules/d3-array/src/identity.js b/frontend/node_modules/d3-array/src/identity.js new file mode 100644 index 0000000..0c86fdf --- /dev/null +++ b/frontend/node_modules/d3-array/src/identity.js @@ -0,0 +1,3 @@ +export default function identity(x) { + return x; +} diff --git a/frontend/node_modules/d3-array/src/index.js b/frontend/node_modules/d3-array/src/index.js new file mode 100644 index 0000000..7759f6d --- /dev/null +++ b/frontend/node_modules/d3-array/src/index.js @@ -0,0 +1,57 @@ +export {default as bisect, bisectRight, bisectLeft, bisectCenter} from "./bisect.js"; +export {default as ascending} from "./ascending.js"; +export {default as bisector} from "./bisector.js"; +export {blur, blur2, blurImage} from "./blur.js"; +export {default as count} from "./count.js"; +export {default as cross} from "./cross.js"; +export {default as cumsum} from "./cumsum.js"; +export {default as descending} from "./descending.js"; +export {default as deviation} from "./deviation.js"; +export {default as extent} from "./extent.js"; +export {Adder, fsum, fcumsum} from "./fsum.js"; +export {default as group, flatGroup, flatRollup, groups, index, indexes, rollup, rollups} from "./group.js"; +export {default as groupSort} from "./groupSort.js"; +export {default as bin, default as histogram} from "./bin.js"; // Deprecated; use bin. +export {default as thresholdFreedmanDiaconis} from "./threshold/freedmanDiaconis.js"; +export {default as thresholdScott} from "./threshold/scott.js"; +export {default as thresholdSturges} from "./threshold/sturges.js"; +export {default as max} from "./max.js"; +export {default as maxIndex} from "./maxIndex.js"; +export {default as mean} from "./mean.js"; +export {default as median, medianIndex} from "./median.js"; +export {default as merge} from "./merge.js"; +export {default as min} from "./min.js"; +export {default as minIndex} from "./minIndex.js"; +export {default as mode} from "./mode.js"; +export {default as nice} from "./nice.js"; +export {default as pairs} from "./pairs.js"; +export {default as permute} from "./permute.js"; +export {default as quantile, quantileIndex, quantileSorted} from "./quantile.js"; +export {default as quickselect} from "./quickselect.js"; +export {default as range} from "./range.js"; +export {default as rank} from "./rank.js"; +export {default as least} from "./least.js"; +export {default as leastIndex} from "./leastIndex.js"; +export {default as greatest} from "./greatest.js"; +export {default as greatestIndex} from "./greatestIndex.js"; +export {default as scan} from "./scan.js"; // Deprecated; use leastIndex. +export {default as shuffle, shuffler} from "./shuffle.js"; +export {default as sum} from "./sum.js"; +export {default as ticks, tickIncrement, tickStep} from "./ticks.js"; +export {default as transpose} from "./transpose.js"; +export {default as variance} from "./variance.js"; +export {default as zip} from "./zip.js"; +export {default as every} from "./every.js"; +export {default as some} from "./some.js"; +export {default as filter} from "./filter.js"; +export {default as map} from "./map.js"; +export {default as reduce} from "./reduce.js"; +export {default as reverse} from "./reverse.js"; +export {default as sort} from "./sort.js"; +export {default as difference} from "./difference.js"; +export {default as disjoint} from "./disjoint.js"; +export {default as intersection} from "./intersection.js"; +export {default as subset} from "./subset.js"; +export {default as superset} from "./superset.js"; +export {default as union} from "./union.js"; +export {InternMap, InternSet} from "internmap"; diff --git a/frontend/node_modules/d3-array/src/intersection.js b/frontend/node_modules/d3-array/src/intersection.js new file mode 100644 index 0000000..43aff39 --- /dev/null +++ b/frontend/node_modules/d3-array/src/intersection.js @@ -0,0 +1,19 @@ +import {InternSet} from "internmap"; + +export default function intersection(values, ...others) { + values = new InternSet(values); + others = others.map(set); + out: for (const value of values) { + for (const other of others) { + if (!other.has(value)) { + values.delete(value); + continue out; + } + } + } + return values; +} + +function set(values) { + return values instanceof InternSet ? values : new InternSet(values); +} diff --git a/frontend/node_modules/d3-array/src/least.js b/frontend/node_modules/d3-array/src/least.js new file mode 100644 index 0000000..a756abf --- /dev/null +++ b/frontend/node_modules/d3-array/src/least.js @@ -0,0 +1,29 @@ +import ascending from "./ascending.js"; + +export default function least(values, compare = ascending) { + let min; + let defined = false; + if (compare.length === 1) { + let minValue; + for (const element of values) { + const value = compare(element); + if (defined + ? ascending(value, minValue) < 0 + : ascending(value, value) === 0) { + min = element; + minValue = value; + defined = true; + } + } + } else { + for (const value of values) { + if (defined + ? compare(value, min) < 0 + : compare(value, value) === 0) { + min = value; + defined = true; + } + } + } + return min; +} diff --git a/frontend/node_modules/d3-array/src/leastIndex.js b/frontend/node_modules/d3-array/src/leastIndex.js new file mode 100644 index 0000000..ee3542b --- /dev/null +++ b/frontend/node_modules/d3-array/src/leastIndex.js @@ -0,0 +1,19 @@ +import ascending from "./ascending.js"; +import minIndex from "./minIndex.js"; + +export default function leastIndex(values, compare = ascending) { + if (compare.length === 1) return minIndex(values, compare); + let minValue; + let min = -1; + let index = -1; + for (const value of values) { + ++index; + if (min < 0 + ? compare(value, value) === 0 + : compare(value, minValue) < 0) { + minValue = value; + min = index; + } + } + return min; +} diff --git a/frontend/node_modules/d3-array/src/map.js b/frontend/node_modules/d3-array/src/map.js new file mode 100644 index 0000000..4e56819 --- /dev/null +++ b/frontend/node_modules/d3-array/src/map.js @@ -0,0 +1,5 @@ +export default function map(values, mapper) { + if (typeof values[Symbol.iterator] !== "function") throw new TypeError("values is not iterable"); + if (typeof mapper !== "function") throw new TypeError("mapper is not a function"); + return Array.from(values, (value, index) => mapper(value, index, values)); +} diff --git a/frontend/node_modules/d3-array/src/max.js b/frontend/node_modules/d3-array/src/max.js new file mode 100644 index 0000000..ce28736 --- /dev/null +++ b/frontend/node_modules/d3-array/src/max.js @@ -0,0 +1,20 @@ +export default function max(values, valueof) { + let max; + if (valueof === undefined) { + for (const value of values) { + if (value != null + && (max < value || (max === undefined && value >= value))) { + max = value; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null + && (max < value || (max === undefined && value >= value))) { + max = value; + } + } + } + return max; +} diff --git a/frontend/node_modules/d3-array/src/maxIndex.js b/frontend/node_modules/d3-array/src/maxIndex.js new file mode 100644 index 0000000..87da1a2 --- /dev/null +++ b/frontend/node_modules/d3-array/src/maxIndex.js @@ -0,0 +1,22 @@ +export default function maxIndex(values, valueof) { + let max; + let maxIndex = -1; + let index = -1; + if (valueof === undefined) { + for (const value of values) { + ++index; + if (value != null + && (max < value || (max === undefined && value >= value))) { + max = value, maxIndex = index; + } + } + } else { + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null + && (max < value || (max === undefined && value >= value))) { + max = value, maxIndex = index; + } + } + } + return maxIndex; +} diff --git a/frontend/node_modules/d3-array/src/mean.js b/frontend/node_modules/d3-array/src/mean.js new file mode 100644 index 0000000..ff6fc46 --- /dev/null +++ b/frontend/node_modules/d3-array/src/mean.js @@ -0,0 +1,19 @@ +export default function mean(values, valueof) { + let count = 0; + let sum = 0; + if (valueof === undefined) { + for (let value of values) { + if (value != null && (value = +value) >= value) { + ++count, sum += value; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && (value = +value) >= value) { + ++count, sum += value; + } + } + } + if (count) return sum / count; +} diff --git a/frontend/node_modules/d3-array/src/median.js b/frontend/node_modules/d3-array/src/median.js new file mode 100644 index 0000000..2604df8 --- /dev/null +++ b/frontend/node_modules/d3-array/src/median.js @@ -0,0 +1,9 @@ +import quantile, {quantileIndex} from "./quantile.js"; + +export default function median(values, valueof) { + return quantile(values, 0.5, valueof); +} + +export function medianIndex(values, valueof) { + return quantileIndex(values, 0.5, valueof); +} diff --git a/frontend/node_modules/d3-array/src/merge.js b/frontend/node_modules/d3-array/src/merge.js new file mode 100644 index 0000000..a368002 --- /dev/null +++ b/frontend/node_modules/d3-array/src/merge.js @@ -0,0 +1,9 @@ +function* flatten(arrays) { + for (const array of arrays) { + yield* array; + } +} + +export default function merge(arrays) { + return Array.from(flatten(arrays)); +} diff --git a/frontend/node_modules/d3-array/src/min.js b/frontend/node_modules/d3-array/src/min.js new file mode 100644 index 0000000..df88bfb --- /dev/null +++ b/frontend/node_modules/d3-array/src/min.js @@ -0,0 +1,20 @@ +export default function min(values, valueof) { + let min; + if (valueof === undefined) { + for (const value of values) { + if (value != null + && (min > value || (min === undefined && value >= value))) { + min = value; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null + && (min > value || (min === undefined && value >= value))) { + min = value; + } + } + } + return min; +} diff --git a/frontend/node_modules/d3-array/src/minIndex.js b/frontend/node_modules/d3-array/src/minIndex.js new file mode 100644 index 0000000..5c07d1e --- /dev/null +++ b/frontend/node_modules/d3-array/src/minIndex.js @@ -0,0 +1,22 @@ +export default function minIndex(values, valueof) { + let min; + let minIndex = -1; + let index = -1; + if (valueof === undefined) { + for (const value of values) { + ++index; + if (value != null + && (min > value || (min === undefined && value >= value))) { + min = value, minIndex = index; + } + } + } else { + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null + && (min > value || (min === undefined && value >= value))) { + min = value, minIndex = index; + } + } + } + return minIndex; +} diff --git a/frontend/node_modules/d3-array/src/mode.js b/frontend/node_modules/d3-array/src/mode.js new file mode 100644 index 0000000..386be57 --- /dev/null +++ b/frontend/node_modules/d3-array/src/mode.js @@ -0,0 +1,28 @@ +import {InternMap} from "internmap"; + +export default function mode(values, valueof) { + const counts = new InternMap(); + if (valueof === undefined) { + for (let value of values) { + if (value != null && value >= value) { + counts.set(value, (counts.get(value) || 0) + 1); + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && value >= value) { + counts.set(value, (counts.get(value) || 0) + 1); + } + } + } + let modeValue; + let modeCount = 0; + for (const [value, count] of counts) { + if (count > modeCount) { + modeCount = count; + modeValue = value; + } + } + return modeValue; +} diff --git a/frontend/node_modules/d3-array/src/nice.js b/frontend/node_modules/d3-array/src/nice.js new file mode 100644 index 0000000..579b418 --- /dev/null +++ b/frontend/node_modules/d3-array/src/nice.js @@ -0,0 +1,18 @@ +import {tickIncrement} from "./ticks.js"; + +export default function nice(start, stop, count) { + let prestep; + while (true) { + const step = tickIncrement(start, stop, count); + if (step === prestep || step === 0 || !isFinite(step)) { + return [start, stop]; + } else if (step > 0) { + start = Math.floor(start / step) * step; + stop = Math.ceil(stop / step) * step; + } else if (step < 0) { + start = Math.ceil(start * step) / step; + stop = Math.floor(stop * step) / step; + } + prestep = step; + } +} diff --git a/frontend/node_modules/d3-array/src/number.js b/frontend/node_modules/d3-array/src/number.js new file mode 100644 index 0000000..f282cdf --- /dev/null +++ b/frontend/node_modules/d3-array/src/number.js @@ -0,0 +1,20 @@ +export default function number(x) { + return x === null ? NaN : +x; +} + +export function* numbers(values, valueof) { + if (valueof === undefined) { + for (let value of values) { + if (value != null && (value = +value) >= value) { + yield value; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && (value = +value) >= value) { + yield value; + } + } + } +} diff --git a/frontend/node_modules/d3-array/src/pairs.js b/frontend/node_modules/d3-array/src/pairs.js new file mode 100644 index 0000000..bfaafec --- /dev/null +++ b/frontend/node_modules/d3-array/src/pairs.js @@ -0,0 +1,15 @@ +export default function pairs(values, pairof = pair) { + const pairs = []; + let previous; + let first = false; + for (const value of values) { + if (first) pairs.push(pairof(previous, value)); + previous = value; + first = true; + } + return pairs; +} + +export function pair(a, b) { + return [a, b]; +} diff --git a/frontend/node_modules/d3-array/src/permute.js b/frontend/node_modules/d3-array/src/permute.js new file mode 100644 index 0000000..f050865 --- /dev/null +++ b/frontend/node_modules/d3-array/src/permute.js @@ -0,0 +1,3 @@ +export default function permute(source, keys) { + return Array.from(keys, key => source[key]); +} diff --git a/frontend/node_modules/d3-array/src/quantile.js b/frontend/node_modules/d3-array/src/quantile.js new file mode 100644 index 0000000..75d9726 --- /dev/null +++ b/frontend/node_modules/d3-array/src/quantile.js @@ -0,0 +1,47 @@ +import max from "./max.js"; +import maxIndex from "./maxIndex.js"; +import min from "./min.js"; +import minIndex from "./minIndex.js"; +import quickselect from "./quickselect.js"; +import number, {numbers} from "./number.js"; +import {ascendingDefined} from "./sort.js"; +import greatest from "./greatest.js"; + +export default function quantile(values, p, valueof) { + values = Float64Array.from(numbers(values, valueof)); + if (!(n = values.length) || isNaN(p = +p)) return; + if (p <= 0 || n < 2) return min(values); + if (p >= 1) return max(values); + var n, + i = (n - 1) * p, + i0 = Math.floor(i), + value0 = max(quickselect(values, i0).subarray(0, i0 + 1)), + value1 = min(values.subarray(i0 + 1)); + return value0 + (value1 - value0) * (i - i0); +} + +export function quantileSorted(values, p, valueof = number) { + if (!(n = values.length) || isNaN(p = +p)) return; + if (p <= 0 || n < 2) return +valueof(values[0], 0, values); + if (p >= 1) return +valueof(values[n - 1], n - 1, values); + var n, + i = (n - 1) * p, + i0 = Math.floor(i), + value0 = +valueof(values[i0], i0, values), + value1 = +valueof(values[i0 + 1], i0 + 1, values); + return value0 + (value1 - value0) * (i - i0); +} + +export function quantileIndex(values, p, valueof = number) { + if (isNaN(p = +p)) return; + numbers = Float64Array.from(values, (_, i) => number(valueof(values[i], i, values))); + if (p <= 0) return minIndex(numbers); + if (p >= 1) return maxIndex(numbers); + var numbers, + index = Uint32Array.from(values, (_, i) => i), + j = numbers.length - 1, + i = Math.floor(j * p); + quickselect(index, i, 0, j, (i, j) => ascendingDefined(numbers[i], numbers[j])); + i = greatest(index.subarray(0, i + 1), (i) => numbers[i]); + return i >= 0 ? i : -1; +} diff --git a/frontend/node_modules/d3-array/src/quickselect.js b/frontend/node_modules/d3-array/src/quickselect.js new file mode 100644 index 0000000..19dbb46 --- /dev/null +++ b/frontend/node_modules/d3-array/src/quickselect.js @@ -0,0 +1,53 @@ +import {ascendingDefined, compareDefined} from "./sort.js"; + +// Based on https://github.com/mourner/quickselect +// ISC license, Copyright 2018 Vladimir Agafonkin. +export default function quickselect(array, k, left = 0, right = Infinity, compare) { + k = Math.floor(k); + left = Math.floor(Math.max(0, left)); + right = Math.floor(Math.min(array.length - 1, right)); + + if (!(left <= k && k <= right)) return array; + + compare = compare === undefined ? ascendingDefined : compareDefined(compare); + + while (right > left) { + if (right - left > 600) { + const n = right - left + 1; + const m = k - left + 1; + const z = Math.log(n); + const s = 0.5 * Math.exp(2 * z / 3); + const sd = 0.5 * Math.sqrt(z * s * (n - s) / n) * (m - n / 2 < 0 ? -1 : 1); + const newLeft = Math.max(left, Math.floor(k - m * s / n + sd)); + const newRight = Math.min(right, Math.floor(k + (n - m) * s / n + sd)); + quickselect(array, k, newLeft, newRight, compare); + } + + const t = array[k]; + let i = left; + let j = right; + + swap(array, left, k); + if (compare(array[right], t) > 0) swap(array, left, right); + + while (i < j) { + swap(array, i, j), ++i, --j; + while (compare(array[i], t) < 0) ++i; + while (compare(array[j], t) > 0) --j; + } + + if (compare(array[left], t) === 0) swap(array, left, j); + else ++j, swap(array, j, right); + + if (j <= k) left = j + 1; + if (k <= j) right = j - 1; + } + + return array; +} + +function swap(array, i, j) { + const t = array[i]; + array[i] = array[j]; + array[j] = t; +} diff --git a/frontend/node_modules/d3-array/src/range.js b/frontend/node_modules/d3-array/src/range.js new file mode 100644 index 0000000..5b86b56 --- /dev/null +++ b/frontend/node_modules/d3-array/src/range.js @@ -0,0 +1,13 @@ +export default function range(start, stop, step) { + start = +start, stop = +stop, step = (n = arguments.length) < 2 ? (stop = start, start = 0, 1) : n < 3 ? 1 : +step; + + var i = -1, + n = Math.max(0, Math.ceil((stop - start) / step)) | 0, + range = new Array(n); + + while (++i < n) { + range[i] = start + i * step; + } + + return range; +} diff --git a/frontend/node_modules/d3-array/src/rank.js b/frontend/node_modules/d3-array/src/rank.js new file mode 100644 index 0000000..44fb675 --- /dev/null +++ b/frontend/node_modules/d3-array/src/rank.js @@ -0,0 +1,24 @@ +import ascending from "./ascending.js"; +import {ascendingDefined, compareDefined} from "./sort.js"; + +export default function rank(values, valueof = ascending) { + if (typeof values[Symbol.iterator] !== "function") throw new TypeError("values is not iterable"); + let V = Array.from(values); + const R = new Float64Array(V.length); + if (valueof.length !== 2) V = V.map(valueof), valueof = ascending; + const compareIndex = (i, j) => valueof(V[i], V[j]); + let k, r; + values = Uint32Array.from(V, (_, i) => i); + // Risky chaining due to Safari 14 https://github.com/d3/d3-array/issues/123 + values.sort(valueof === ascending ? (i, j) => ascendingDefined(V[i], V[j]) : compareDefined(compareIndex)); + values.forEach((j, i) => { + const c = compareIndex(j, k === undefined ? j : k); + if (c >= 0) { + if (k === undefined || c > 0) k = j, r = i; + R[j] = r; + } else { + R[j] = NaN; + } + }); + return R; +} diff --git a/frontend/node_modules/d3-array/src/reduce.js b/frontend/node_modules/d3-array/src/reduce.js new file mode 100644 index 0000000..3b49cf5 --- /dev/null +++ b/frontend/node_modules/d3-array/src/reduce.js @@ -0,0 +1,14 @@ +export default function reduce(values, reducer, value) { + if (typeof reducer !== "function") throw new TypeError("reducer is not a function"); + const iterator = values[Symbol.iterator](); + let done, next, index = -1; + if (arguments.length < 3) { + ({done, value} = iterator.next()); + if (done) return; + ++index; + } + while (({done, value: next} = iterator.next()), !done) { + value = reducer(value, next, ++index, values); + } + return value; +} diff --git a/frontend/node_modules/d3-array/src/reverse.js b/frontend/node_modules/d3-array/src/reverse.js new file mode 100644 index 0000000..da6742c --- /dev/null +++ b/frontend/node_modules/d3-array/src/reverse.js @@ -0,0 +1,4 @@ +export default function reverse(values) { + if (typeof values[Symbol.iterator] !== "function") throw new TypeError("values is not iterable"); + return Array.from(values).reverse(); +} diff --git a/frontend/node_modules/d3-array/src/scan.js b/frontend/node_modules/d3-array/src/scan.js new file mode 100644 index 0000000..9c538f8 --- /dev/null +++ b/frontend/node_modules/d3-array/src/scan.js @@ -0,0 +1,6 @@ +import leastIndex from "./leastIndex.js"; + +export default function scan(values, compare) { + const index = leastIndex(values, compare); + return index < 0 ? undefined : index; +} diff --git a/frontend/node_modules/d3-array/src/shuffle.js b/frontend/node_modules/d3-array/src/shuffle.js new file mode 100644 index 0000000..426cdac --- /dev/null +++ b/frontend/node_modules/d3-array/src/shuffle.js @@ -0,0 +1,13 @@ +export default shuffler(Math.random); + +export function shuffler(random) { + return function shuffle(array, i0 = 0, i1 = array.length) { + let m = i1 - (i0 = +i0); + while (m) { + const i = random() * m-- | 0, t = array[m + i0]; + array[m + i0] = array[i + i0]; + array[i + i0] = t; + } + return array; + }; +} diff --git a/frontend/node_modules/d3-array/src/some.js b/frontend/node_modules/d3-array/src/some.js new file mode 100644 index 0000000..0b8f98b --- /dev/null +++ b/frontend/node_modules/d3-array/src/some.js @@ -0,0 +1,10 @@ +export default function some(values, test) { + if (typeof test !== "function") throw new TypeError("test is not a function"); + let index = -1; + for (const value of values) { + if (test(value, ++index, values)) { + return true; + } + } + return false; +} diff --git a/frontend/node_modules/d3-array/src/sort.js b/frontend/node_modules/d3-array/src/sort.js new file mode 100644 index 0000000..14541be --- /dev/null +++ b/frontend/node_modules/d3-array/src/sort.js @@ -0,0 +1,39 @@ +import ascending from "./ascending.js"; +import permute from "./permute.js"; + +export default function sort(values, ...F) { + if (typeof values[Symbol.iterator] !== "function") throw new TypeError("values is not iterable"); + values = Array.from(values); + let [f] = F; + if ((f && f.length !== 2) || F.length > 1) { + const index = Uint32Array.from(values, (d, i) => i); + if (F.length > 1) { + F = F.map(f => values.map(f)); + index.sort((i, j) => { + for (const f of F) { + const c = ascendingDefined(f[i], f[j]); + if (c) return c; + } + }); + } else { + f = values.map(f); + index.sort((i, j) => ascendingDefined(f[i], f[j])); + } + return permute(values, index); + } + return values.sort(compareDefined(f)); +} + +export function compareDefined(compare = ascending) { + if (compare === ascending) return ascendingDefined; + if (typeof compare !== "function") throw new TypeError("compare is not a function"); + return (a, b) => { + const x = compare(a, b); + if (x || x === 0) return x; + return (compare(b, b) === 0) - (compare(a, a) === 0); + }; +} + +export function ascendingDefined(a, b) { + return (a == null || !(a >= a)) - (b == null || !(b >= b)) || (a < b ? -1 : a > b ? 1 : 0); +} diff --git a/frontend/node_modules/d3-array/src/subset.js b/frontend/node_modules/d3-array/src/subset.js new file mode 100644 index 0000000..8a1c564 --- /dev/null +++ b/frontend/node_modules/d3-array/src/subset.js @@ -0,0 +1,5 @@ +import superset from "./superset.js"; + +export default function subset(values, other) { + return superset(other, values); +} diff --git a/frontend/node_modules/d3-array/src/sum.js b/frontend/node_modules/d3-array/src/sum.js new file mode 100644 index 0000000..0720e2a --- /dev/null +++ b/frontend/node_modules/d3-array/src/sum.js @@ -0,0 +1,18 @@ +export default function sum(values, valueof) { + let sum = 0; + if (valueof === undefined) { + for (let value of values) { + if (value = +value) { + sum += value; + } + } + } else { + let index = -1; + for (let value of values) { + if (value = +valueof(value, ++index, values)) { + sum += value; + } + } + } + return sum; +} diff --git a/frontend/node_modules/d3-array/src/superset.js b/frontend/node_modules/d3-array/src/superset.js new file mode 100644 index 0000000..d178e9c --- /dev/null +++ b/frontend/node_modules/d3-array/src/superset.js @@ -0,0 +1,19 @@ +export default function superset(values, other) { + const iterator = values[Symbol.iterator](), set = new Set(); + for (const o of other) { + const io = intern(o); + if (set.has(io)) continue; + let value, done; + while (({value, done} = iterator.next())) { + if (done) return false; + const ivalue = intern(value); + set.add(ivalue); + if (Object.is(io, ivalue)) break; + } + } + return true; +} + +function intern(value) { + return value !== null && typeof value === "object" ? value.valueOf() : value; +} diff --git a/frontend/node_modules/d3-array/src/threshold/freedmanDiaconis.js b/frontend/node_modules/d3-array/src/threshold/freedmanDiaconis.js new file mode 100644 index 0000000..c78cff4 --- /dev/null +++ b/frontend/node_modules/d3-array/src/threshold/freedmanDiaconis.js @@ -0,0 +1,7 @@ +import count from "../count.js"; +import quantile from "../quantile.js"; + +export default function thresholdFreedmanDiaconis(values, min, max) { + const c = count(values), d = quantile(values, 0.75) - quantile(values, 0.25); + return c && d ? Math.ceil((max - min) / (2 * d * Math.pow(c, -1 / 3))) : 1; +} diff --git a/frontend/node_modules/d3-array/src/threshold/scott.js b/frontend/node_modules/d3-array/src/threshold/scott.js new file mode 100644 index 0000000..2541d2d --- /dev/null +++ b/frontend/node_modules/d3-array/src/threshold/scott.js @@ -0,0 +1,7 @@ +import count from "../count.js"; +import deviation from "../deviation.js"; + +export default function thresholdScott(values, min, max) { + const c = count(values), d = deviation(values); + return c && d ? Math.ceil((max - min) * Math.cbrt(c) / (3.49 * d)) : 1; +} diff --git a/frontend/node_modules/d3-array/src/threshold/sturges.js b/frontend/node_modules/d3-array/src/threshold/sturges.js new file mode 100644 index 0000000..3370968 --- /dev/null +++ b/frontend/node_modules/d3-array/src/threshold/sturges.js @@ -0,0 +1,5 @@ +import count from "../count.js"; + +export default function thresholdSturges(values) { + return Math.max(1, Math.ceil(Math.log(count(values)) / Math.LN2) + 1); +} diff --git a/frontend/node_modules/d3-array/src/ticks.js b/frontend/node_modules/d3-array/src/ticks.js new file mode 100644 index 0000000..5868d8d --- /dev/null +++ b/frontend/node_modules/d3-array/src/ticks.js @@ -0,0 +1,55 @@ +const e10 = Math.sqrt(50), + e5 = Math.sqrt(10), + e2 = Math.sqrt(2); + +function tickSpec(start, stop, count) { + const step = (stop - start) / Math.max(0, count), + power = Math.floor(Math.log10(step)), + error = step / Math.pow(10, power), + factor = error >= e10 ? 10 : error >= e5 ? 5 : error >= e2 ? 2 : 1; + let i1, i2, inc; + if (power < 0) { + inc = Math.pow(10, -power) / factor; + i1 = Math.round(start * inc); + i2 = Math.round(stop * inc); + if (i1 / inc < start) ++i1; + if (i2 / inc > stop) --i2; + inc = -inc; + } else { + inc = Math.pow(10, power) * factor; + i1 = Math.round(start / inc); + i2 = Math.round(stop / inc); + if (i1 * inc < start) ++i1; + if (i2 * inc > stop) --i2; + } + if (i2 < i1 && 0.5 <= count && count < 2) return tickSpec(start, stop, count * 2); + return [i1, i2, inc]; +} + +export default function ticks(start, stop, count) { + stop = +stop, start = +start, count = +count; + if (!(count > 0)) return []; + if (start === stop) return [start]; + const reverse = stop < start, [i1, i2, inc] = reverse ? tickSpec(stop, start, count) : tickSpec(start, stop, count); + if (!(i2 >= i1)) return []; + const n = i2 - i1 + 1, ticks = new Array(n); + if (reverse) { + if (inc < 0) for (let i = 0; i < n; ++i) ticks[i] = (i2 - i) / -inc; + else for (let i = 0; i < n; ++i) ticks[i] = (i2 - i) * inc; + } else { + if (inc < 0) for (let i = 0; i < n; ++i) ticks[i] = (i1 + i) / -inc; + else for (let i = 0; i < n; ++i) ticks[i] = (i1 + i) * inc; + } + return ticks; +} + +export function tickIncrement(start, stop, count) { + stop = +stop, start = +start, count = +count; + return tickSpec(start, stop, count)[2]; +} + +export function tickStep(start, stop, count) { + stop = +stop, start = +start, count = +count; + const reverse = stop < start, inc = reverse ? tickIncrement(stop, start, count) : tickIncrement(start, stop, count); + return (reverse ? -1 : 1) * (inc < 0 ? 1 / -inc : inc); +} diff --git a/frontend/node_modules/d3-array/src/transpose.js b/frontend/node_modules/d3-array/src/transpose.js new file mode 100644 index 0000000..de6caeb --- /dev/null +++ b/frontend/node_modules/d3-array/src/transpose.js @@ -0,0 +1,15 @@ +import min from "./min.js"; + +export default function transpose(matrix) { + if (!(n = matrix.length)) return []; + for (var i = -1, m = min(matrix, length), transpose = new Array(m); ++i < m;) { + for (var j = -1, n, row = transpose[i] = new Array(n); ++j < n;) { + row[j] = matrix[j][i]; + } + } + return transpose; +} + +function length(d) { + return d.length; +} diff --git a/frontend/node_modules/d3-array/src/union.js b/frontend/node_modules/d3-array/src/union.js new file mode 100644 index 0000000..57c20b1 --- /dev/null +++ b/frontend/node_modules/d3-array/src/union.js @@ -0,0 +1,11 @@ +import {InternSet} from "internmap"; + +export default function union(...others) { + const set = new InternSet(); + for (const other of others) { + for (const o of other) { + set.add(o); + } + } + return set; +} diff --git a/frontend/node_modules/d3-array/src/variance.js b/frontend/node_modules/d3-array/src/variance.js new file mode 100644 index 0000000..2428bf8 --- /dev/null +++ b/frontend/node_modules/d3-array/src/variance.js @@ -0,0 +1,25 @@ +export default function variance(values, valueof) { + let count = 0; + let delta; + let mean = 0; + let sum = 0; + if (valueof === undefined) { + for (let value of values) { + if (value != null && (value = +value) >= value) { + delta = value - mean; + mean += delta / ++count; + sum += delta * (value - mean); + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && (value = +value) >= value) { + delta = value - mean; + mean += delta / ++count; + sum += delta * (value - mean); + } + } + } + if (count > 1) return sum / (count - 1); +} diff --git a/frontend/node_modules/d3-array/src/zip.js b/frontend/node_modules/d3-array/src/zip.js new file mode 100644 index 0000000..48cfb42 --- /dev/null +++ b/frontend/node_modules/d3-array/src/zip.js @@ -0,0 +1,5 @@ +import transpose from "./transpose.js"; + +export default function zip() { + return transpose(arguments); +} diff --git a/frontend/node_modules/d3-axis/LICENSE b/frontend/node_modules/d3-axis/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-axis/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-axis/README.md b/frontend/node_modules/d3-axis/README.md new file mode 100644 index 0000000..6c65e82 --- /dev/null +++ b/frontend/node_modules/d3-axis/README.md @@ -0,0 +1,210 @@ +# d3-axis + +The axis component renders human-readable reference marks for [scales](https://github.com/d3/d3-scale). This alleviates one of the more tedious tasks in visualizing data. + +## Installing + +If you use npm, `npm install d3-axis`. You can also download the [latest release on GitHub](https://github.com/d3/d3-axis/releases/latest). For vanilla HTML in modern browsers, import d3-axis from Skypack: + +```html + +``` + +For legacy environments, you can load d3-axis’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +[Try d3-axis in your browser.](https://observablehq.com/collection/@d3/d3-axis) + +## API Reference + +Regardless of orientation, axes are always rendered at the origin. To change the position of the axis with respect to the chart, specify a [transform attribute](http://www.w3.org/TR/SVG/coords.html#TransformAttribute) on the containing element. For example: + +```js +d3.select("body").append("svg") + .attr("width", 1440) + .attr("height", 30) + .append("g") + .attr("transform", "translate(0,30)") + .call(axis); +``` + +The elements created by the axis are considered part of its public API. You can apply external stylesheets or modify the generated axis elements to [customize the axis appearance](https://observablehq.com/@d3/styled-axes). + +[Custom Axis](https://observablehq.com/@d3/styled-axes) + +An axis consists of a [path element](https://www.w3.org/TR/SVG/paths.html#PathElement) of class “domain” representing the extent of the scale’s domain, followed by transformed [g elements](https://www.w3.org/TR/SVG/struct.html#Groups) of class “tick” representing each of the scale’s ticks. Each tick has a [line element](https://www.w3.org/TR/SVG/shapes.html#LineElement) to draw the tick line, and a [text element](https://www.w3.org/TR/SVG/text.html#TextElement) for the tick label. For example, here is a typical bottom-oriented axis: + +```html + + + + + 0.0 + + + + 0.2 + + + + 0.4 + + + + 0.6 + + + + 0.8 + + + + 1.0 + + +``` + +The orientation of an axis is fixed; to change the orientation, remove the old axis and create a new axis. + +# d3.axisTop(scale) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +Constructs a new top-oriented axis generator for the given [scale](https://github.com/d3/d3-scale), with empty [tick arguments](#axis_ticks), a [tick size](#axis_tickSize) of 6 and [padding](#axis_tickPadding) of 3. In this orientation, ticks are drawn above the horizontal domain path. + +# d3.axisRight(scale) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +Constructs a new right-oriented axis generator for the given [scale](https://github.com/d3/d3-scale), with empty [tick arguments](#axis_ticks), a [tick size](#axis_tickSize) of 6 and [padding](#axis_tickPadding) of 3. In this orientation, ticks are drawn to the right of the vertical domain path. + +# d3.axisBottom(scale) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +Constructs a new bottom-oriented axis generator for the given [scale](https://github.com/d3/d3-scale), with empty [tick arguments](#axis_ticks), a [tick size](#axis_tickSize) of 6 and [padding](#axis_tickPadding) of 3. In this orientation, ticks are drawn below the horizontal domain path. + +# d3.axisLeft(scale) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +Constructs a new left-oriented axis generator for the given [scale](https://github.com/d3/d3-scale), with empty [tick arguments](#axis_ticks), a [tick size](#axis_tickSize) of 6 and [padding](#axis_tickPadding) of 3. In this orientation, ticks are drawn to the left of the vertical domain path. + +# axis(context) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +Render the axis to the given *context*, which may be either a [selection](https://github.com/d3/d3-selection) of SVG containers (either SVG or G elements) or a corresponding [transition](https://github.com/d3/d3-transition). + +# axis.scale([scale]) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +If *scale* is specified, sets the [scale](https://github.com/d3/d3-scale) and returns the axis. If *scale* is not specified, returns the current scale. + +# axis.ticks(arguments…) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) +
    # axis.ticks([count[, specifier]]) +
    # axis.ticks([interval[, specifier]]) + +Sets the *arguments* that will be passed to [*scale*.ticks](https://github.com/d3/d3-scale/blob/master/README.md#continuous_ticks) and [*scale*.tickFormat](https://github.com/d3/d3-scale/blob/master/README.md#continuous_tickFormat) when the axis is [rendered](#_axis), and returns the axis generator. The meaning of the *arguments* depends on the [axis’ scale](#axis_scale) type: most commonly, the arguments are a suggested *count* for the number of ticks (or a [time *interval*](https://github.com/d3/d3-time) for time scales), and an optional [format *specifier*](https://github.com/d3/d3-format) to customize how the tick values are formatted. + +This method has no effect if the scale does not implement *scale*.ticks, as with [band](https://github.com/d3/d3-scale/blob/master/README.md#band-scales) and [point](https://github.com/d3/d3-scale/blob/master/README.md#point-scales) scales. To set the tick values explicitly, use [*axis*.tickValues](#axis_tickValues). To set the tick format explicitly, use [*axis*.tickFormat](#axis_tickFormat). + +For example, to generate twenty ticks with SI-prefix formatting on a linear scale, say: + +```js +axis.ticks(20, "s"); +``` + +To generate ticks every fifteen minutes with a time scale, say: + +```js +axis.ticks(d3.timeMinute.every(15)); +``` + +This method is also a convenience function for [*axis*.tickArguments](#axis_tickArguments). For example, this: + +```js +axis.ticks(10); +``` + +Is equivalent to: + +```js +axis.tickArguments([10]); +``` + +To generate tick values directly, use [*scale*.ticks](https://github.com/d3/d3-scale/blob/master/README.md#continuous_ticks). + +# axis.tickArguments([arguments]) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +If *arguments* is specified, sets the *arguments* that will be passed to [*scale*.ticks](https://github.com/d3/d3-scale/blob/master/README.md#continuous_ticks) and [*scale*.tickFormat](https://github.com/d3/d3-scale/blob/master/README.md#continuous_tickFormat) when the axis is [rendered](#_axis), and returns the axis generator. The meaning of the *arguments* depends on the [axis’ scale](#axis_scale) type: most commonly, the arguments are a suggested *count* for the number of ticks (or a [time *interval*](https://github.com/d3/d3-time) for time scales), and an optional [format *specifier*](https://github.com/d3/d3-format) to customize how the tick values are formatted. + +If *arguments* is specified, this method has no effect if the scale does not implement *scale*.ticks, as with [band](https://github.com/d3/d3-scale/blob/master/README.md#band-scales) and [point](https://github.com/d3/d3-scale/blob/master/README.md#point-scales) scales. To set the tick values explicitly, use [*axis*.tickValues](#axis_tickValues). To set the tick format explicitly, use [*axis*.tickFormat](#axis_tickFormat). + +If *arguments* is not specified, returns the current tick arguments, which defaults to the empty array. + +For example, to generate twenty ticks with SI-prefix formatting on a linear scale, say: + +```js +axis.tickArguments([20, "s"]); +``` + +To generate ticks every fifteen minutes with a time scale, say: + +```js +axis.tickArguments([d3.timeMinute.every(15)]); +``` + +See also [*axis*.ticks](#axis_ticks). + +# axis.tickValues([values]) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +If a *values* iterable is specified, the specified values are used for ticks rather than using the scale’s automatic tick generator. If *values* is null, clears any previously-set explicit tick values and reverts back to the scale’s tick generator. If *values* is not specified, returns the current tick values, which defaults to null. For example, to generate ticks at specific values: + +```js +var xAxis = d3.axisBottom(x) + .tickValues([1, 2, 3, 5, 8, 13, 21]); +``` + +The explicit tick values take precedent over the tick arguments set by [*axis*.tickArguments](#axis_tickArguments). However, any tick arguments will still be passed to the scale’s [tickFormat](#axis_tickFormat) function if a tick format is not also set. + +# axis.tickFormat([format]) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +If *format* is specified, sets the tick format function and returns the axis. If *format* is not specified, returns the current format function, which defaults to null. A null format indicates that the scale’s default formatter should be used, which is generated by calling [*scale*.tickFormat](https://github.com/d3/d3-scale/blob/master/README.md#continuous_tickFormat). In this case, the arguments specified by [*axis*.tickArguments](#axis_tickArguments) are likewise passed to *scale*.tickFormat. + +See [d3-format](https://github.com/d3/d3-format) and [d3-time-format](https://github.com/d3/d3-time-format) for help creating formatters. For example, to display integers with comma-grouping for thousands: + +```js +axis.tickFormat(d3.format(",.0f")); +``` + +More commonly, a format specifier is passed to [*axis*.ticks](#axis_ticks): + +```js +axis.ticks(10, ",f"); +``` + +This has the advantage of setting the format precision automatically based on the tick interval. + +# axis.tickSize([size]) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +If *size* is specified, sets the [inner](#axis_tickSizeInner) and [outer](#axis_tickSizeOuter) tick size to the specified value and returns the axis. If *size* is not specified, returns the current inner tick size, which defaults to 6. + +# axis.tickSizeInner([size]) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +If *size* is specified, sets the inner tick size to the specified value and returns the axis. If *size* is not specified, returns the current inner tick size, which defaults to 6. The inner tick size controls the length of the tick lines, offset from the native position of the axis. + +# axis.tickSizeOuter([size]) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +If *size* is specified, sets the outer tick size to the specified value and returns the axis. If *size* is not specified, returns the current outer tick size, which defaults to 6. The outer tick size controls the length of the square ends of the domain path, offset from the native position of the axis. Thus, the “outer ticks” are not actually ticks but part of the domain path, and their position is determined by the associated scale’s domain extent. Thus, outer ticks may overlap with the first or last inner tick. An outer tick size of 0 suppresses the square ends of the domain path, instead producing a straight line. + +# axis.tickPadding([padding]) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +If *padding* is specified, sets the padding to the specified value in pixels and returns the axis. If *padding* is not specified, returns the current padding which defaults to 3 pixels. + +# axis.offset([offset]) · [Source](https://github.com/d3/d3-axis/blob/master/src/axis.js) + +If *offset* is specified, sets the offset to the specified value in pixels and returns the axis. If *offset* is not specified, returns the current offset which defaults to 0 on devices with a [devicePixelRatio](https://developer.mozilla.org/en-US/docs/Web/API/Window/devicePixelRatio) greater than 1, and 0.5px otherwise. This default offset ensures crisp edges on low-resolution devices. diff --git a/frontend/node_modules/d3-axis/dist/d3-axis.js b/frontend/node_modules/d3-axis/dist/d3-axis.js new file mode 100644 index 0000000..effae89 --- /dev/null +++ b/frontend/node_modules/d3-axis/dist/d3-axis.js @@ -0,0 +1,192 @@ +// https://d3js.org/d3-axis/ v3.0.0 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +}(this, (function (exports) { 'use strict'; + +function identity(x) { + return x; +} + +var top = 1, + right = 2, + bottom = 3, + left = 4, + epsilon = 1e-6; + +function translateX(x) { + return "translate(" + x + ",0)"; +} + +function translateY(y) { + return "translate(0," + y + ")"; +} + +function number(scale) { + return d => +scale(d); +} + +function center(scale, offset) { + offset = Math.max(0, scale.bandwidth() - offset * 2) / 2; + if (scale.round()) offset = Math.round(offset); + return d => +scale(d) + offset; +} + +function entering() { + return !this.__axis; +} + +function axis(orient, scale) { + var tickArguments = [], + tickValues = null, + tickFormat = null, + tickSizeInner = 6, + tickSizeOuter = 6, + tickPadding = 3, + offset = typeof window !== "undefined" && window.devicePixelRatio > 1 ? 0 : 0.5, + k = orient === top || orient === left ? -1 : 1, + x = orient === left || orient === right ? "x" : "y", + transform = orient === top || orient === bottom ? translateX : translateY; + + function axis(context) { + var values = tickValues == null ? (scale.ticks ? scale.ticks.apply(scale, tickArguments) : scale.domain()) : tickValues, + format = tickFormat == null ? (scale.tickFormat ? scale.tickFormat.apply(scale, tickArguments) : identity) : tickFormat, + spacing = Math.max(tickSizeInner, 0) + tickPadding, + range = scale.range(), + range0 = +range[0] + offset, + range1 = +range[range.length - 1] + offset, + position = (scale.bandwidth ? center : number)(scale.copy(), offset), + selection = context.selection ? context.selection() : context, + path = selection.selectAll(".domain").data([null]), + tick = selection.selectAll(".tick").data(values, scale).order(), + tickExit = tick.exit(), + tickEnter = tick.enter().append("g").attr("class", "tick"), + line = tick.select("line"), + text = tick.select("text"); + + path = path.merge(path.enter().insert("path", ".tick") + .attr("class", "domain") + .attr("stroke", "currentColor")); + + tick = tick.merge(tickEnter); + + line = line.merge(tickEnter.append("line") + .attr("stroke", "currentColor") + .attr(x + "2", k * tickSizeInner)); + + text = text.merge(tickEnter.append("text") + .attr("fill", "currentColor") + .attr(x, k * spacing) + .attr("dy", orient === top ? "0em" : orient === bottom ? "0.71em" : "0.32em")); + + if (context !== selection) { + path = path.transition(context); + tick = tick.transition(context); + line = line.transition(context); + text = text.transition(context); + + tickExit = tickExit.transition(context) + .attr("opacity", epsilon) + .attr("transform", function(d) { return isFinite(d = position(d)) ? transform(d + offset) : this.getAttribute("transform"); }); + + tickEnter + .attr("opacity", epsilon) + .attr("transform", function(d) { var p = this.parentNode.__axis; return transform((p && isFinite(p = p(d)) ? p : position(d)) + offset); }); + } + + tickExit.remove(); + + path + .attr("d", orient === left || orient === right + ? (tickSizeOuter ? "M" + k * tickSizeOuter + "," + range0 + "H" + offset + "V" + range1 + "H" + k * tickSizeOuter : "M" + offset + "," + range0 + "V" + range1) + : (tickSizeOuter ? "M" + range0 + "," + k * tickSizeOuter + "V" + offset + "H" + range1 + "V" + k * tickSizeOuter : "M" + range0 + "," + offset + "H" + range1)); + + tick + .attr("opacity", 1) + .attr("transform", function(d) { return transform(position(d) + offset); }); + + line + .attr(x + "2", k * tickSizeInner); + + text + .attr(x, k * spacing) + .text(format); + + selection.filter(entering) + .attr("fill", "none") + .attr("font-size", 10) + .attr("font-family", "sans-serif") + .attr("text-anchor", orient === right ? "start" : orient === left ? "end" : "middle"); + + selection + .each(function() { this.__axis = position; }); + } + + axis.scale = function(_) { + return arguments.length ? (scale = _, axis) : scale; + }; + + axis.ticks = function() { + return tickArguments = Array.from(arguments), axis; + }; + + axis.tickArguments = function(_) { + return arguments.length ? (tickArguments = _ == null ? [] : Array.from(_), axis) : tickArguments.slice(); + }; + + axis.tickValues = function(_) { + return arguments.length ? (tickValues = _ == null ? null : Array.from(_), axis) : tickValues && tickValues.slice(); + }; + + axis.tickFormat = function(_) { + return arguments.length ? (tickFormat = _, axis) : tickFormat; + }; + + axis.tickSize = function(_) { + return arguments.length ? (tickSizeInner = tickSizeOuter = +_, axis) : tickSizeInner; + }; + + axis.tickSizeInner = function(_) { + return arguments.length ? (tickSizeInner = +_, axis) : tickSizeInner; + }; + + axis.tickSizeOuter = function(_) { + return arguments.length ? (tickSizeOuter = +_, axis) : tickSizeOuter; + }; + + axis.tickPadding = function(_) { + return arguments.length ? (tickPadding = +_, axis) : tickPadding; + }; + + axis.offset = function(_) { + return arguments.length ? (offset = +_, axis) : offset; + }; + + return axis; +} + +function axisTop(scale) { + return axis(top, scale); +} + +function axisRight(scale) { + return axis(right, scale); +} + +function axisBottom(scale) { + return axis(bottom, scale); +} + +function axisLeft(scale) { + return axis(left, scale); +} + +exports.axisBottom = axisBottom; +exports.axisLeft = axisLeft; +exports.axisRight = axisRight; +exports.axisTop = axisTop; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-axis/dist/d3-axis.min.js b/frontend/node_modules/d3-axis/dist/d3-axis.min.js new file mode 100644 index 0000000..03e6c97 --- /dev/null +++ b/frontend/node_modules/d3-axis/dist/d3-axis.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-axis/ v3.0.0 Copyright 2010-2021 Mike Bostock +!function(t,n){"object"==typeof exports&&"undefined"!=typeof module?n(exports):"function"==typeof define&&define.amd?define(["exports"],n):n((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{})}(this,(function(t){"use strict";function n(t){return t}var e=1e-6;function r(t){return"translate("+t+",0)"}function i(t){return"translate(0,"+t+")"}function a(t){return n=>+t(n)}function o(t,n){return n=Math.max(0,t.bandwidth()-2*n)/2,t.round()&&(n=Math.round(n)),e=>+t(e)+n}function u(){return!this.__axis}function c(t,c){var l=[],s=null,f=null,d=6,m=6,h=3,p="undefined"!=typeof window&&window.devicePixelRatio>1?0:.5,g=1===t||4===t?-1:1,x=4===t||2===t?"x":"y",y=1===t||3===t?r:i;function k(r){var i=null==s?c.ticks?c.ticks.apply(c,l):c.domain():s,k=null==f?c.tickFormat?c.tickFormat.apply(c,l):n:f,M=Math.max(d,0)+h,_=c.range(),b=+_[0]+p,v=+_[_.length-1]+p,A=(c.bandwidth?o:a)(c.copy(),p),w=r.selection?r.selection():r,F=w.selectAll(".domain").data([null]),V=w.selectAll(".tick").data(i,c).order(),z=V.exit(),H=V.enter().append("g").attr("class","tick"),C=V.select("line"),P=V.select("text");F=F.merge(F.enter().insert("path",".tick").attr("class","domain").attr("stroke","currentColor")),V=V.merge(H),C=C.merge(H.append("line").attr("stroke","currentColor").attr(x+"2",g*d)),P=P.merge(H.append("text").attr("fill","currentColor").attr(x,g*M).attr("dy",1===t?"0em":3===t?"0.71em":"0.32em")),r!==w&&(F=F.transition(r),V=V.transition(r),C=C.transition(r),P=P.transition(r),z=z.transition(r).attr("opacity",e).attr("transform",(function(t){return isFinite(t=A(t))?y(t+p):this.getAttribute("transform")})),H.attr("opacity",e).attr("transform",(function(t){var n=this.parentNode.__axis;return y((n&&isFinite(n=n(t))?n:A(t))+p)}))),z.remove(),F.attr("d",4===t||2===t?m?"M"+g*m+","+b+"H"+p+"V"+v+"H"+g*m:"M"+p+","+b+"V"+v:m?"M"+b+","+g*m+"V"+p+"H"+v+"V"+g*m:"M"+b+","+p+"H"+v),V.attr("opacity",1).attr("transform",(function(t){return y(A(t)+p)})),C.attr(x+"2",g*d),P.attr(x,g*M).text(k),w.filter(u).attr("fill","none").attr("font-size",10).attr("font-family","sans-serif").attr("text-anchor",2===t?"start":4===t?"end":"middle"),w.each((function(){this.__axis=A}))}return k.scale=function(t){return arguments.length?(c=t,k):c},k.ticks=function(){return l=Array.from(arguments),k},k.tickArguments=function(t){return arguments.length?(l=null==t?[]:Array.from(t),k):l.slice()},k.tickValues=function(t){return arguments.length?(s=null==t?null:Array.from(t),k):s&&s.slice()},k.tickFormat=function(t){return arguments.length?(f=t,k):f},k.tickSize=function(t){return arguments.length?(d=m=+t,k):d},k.tickSizeInner=function(t){return arguments.length?(d=+t,k):d},k.tickSizeOuter=function(t){return arguments.length?(m=+t,k):m},k.tickPadding=function(t){return arguments.length?(h=+t,k):h},k.offset=function(t){return arguments.length?(p=+t,k):p},k}t.axisBottom=function(t){return c(3,t)},t.axisLeft=function(t){return c(4,t)},t.axisRight=function(t){return c(2,t)},t.axisTop=function(t){return c(1,t)},Object.defineProperty(t,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-axis/package.json b/frontend/node_modules/d3-axis/package.json new file mode 100644 index 0000000..249f9dc --- /dev/null +++ b/frontend/node_modules/d3-axis/package.json @@ -0,0 +1,54 @@ +{ + "name": "d3-axis", + "version": "3.0.0", + "description": "Displays automatic reference lines for scales.", + "homepage": "https://d3js.org/d3-axis/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-axis.git" + }, + "keywords": [ + "d3", + "d3-module", + "axis", + "scale", + "visualization" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "https://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-axis.min.js", + "unpkg": "dist/d3-axis.min.js", + "exports": { + "umd": "./dist/d3-axis.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "devDependencies": { + "d3-scale": "2 - 4", + "d3-selection": "1 - 3", + "eslint": "7", + "js-beautify": "1", + "jsdom": "16", + "mocha": "9", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c && git push", + "postpublish": "git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-axis/src/axis.js b/frontend/node_modules/d3-axis/src/axis.js new file mode 100644 index 0000000..78e1bcb --- /dev/null +++ b/frontend/node_modules/d3-axis/src/axis.js @@ -0,0 +1,174 @@ +import identity from "./identity.js"; + +var top = 1, + right = 2, + bottom = 3, + left = 4, + epsilon = 1e-6; + +function translateX(x) { + return "translate(" + x + ",0)"; +} + +function translateY(y) { + return "translate(0," + y + ")"; +} + +function number(scale) { + return d => +scale(d); +} + +function center(scale, offset) { + offset = Math.max(0, scale.bandwidth() - offset * 2) / 2; + if (scale.round()) offset = Math.round(offset); + return d => +scale(d) + offset; +} + +function entering() { + return !this.__axis; +} + +function axis(orient, scale) { + var tickArguments = [], + tickValues = null, + tickFormat = null, + tickSizeInner = 6, + tickSizeOuter = 6, + tickPadding = 3, + offset = typeof window !== "undefined" && window.devicePixelRatio > 1 ? 0 : 0.5, + k = orient === top || orient === left ? -1 : 1, + x = orient === left || orient === right ? "x" : "y", + transform = orient === top || orient === bottom ? translateX : translateY; + + function axis(context) { + var values = tickValues == null ? (scale.ticks ? scale.ticks.apply(scale, tickArguments) : scale.domain()) : tickValues, + format = tickFormat == null ? (scale.tickFormat ? scale.tickFormat.apply(scale, tickArguments) : identity) : tickFormat, + spacing = Math.max(tickSizeInner, 0) + tickPadding, + range = scale.range(), + range0 = +range[0] + offset, + range1 = +range[range.length - 1] + offset, + position = (scale.bandwidth ? center : number)(scale.copy(), offset), + selection = context.selection ? context.selection() : context, + path = selection.selectAll(".domain").data([null]), + tick = selection.selectAll(".tick").data(values, scale).order(), + tickExit = tick.exit(), + tickEnter = tick.enter().append("g").attr("class", "tick"), + line = tick.select("line"), + text = tick.select("text"); + + path = path.merge(path.enter().insert("path", ".tick") + .attr("class", "domain") + .attr("stroke", "currentColor")); + + tick = tick.merge(tickEnter); + + line = line.merge(tickEnter.append("line") + .attr("stroke", "currentColor") + .attr(x + "2", k * tickSizeInner)); + + text = text.merge(tickEnter.append("text") + .attr("fill", "currentColor") + .attr(x, k * spacing) + .attr("dy", orient === top ? "0em" : orient === bottom ? "0.71em" : "0.32em")); + + if (context !== selection) { + path = path.transition(context); + tick = tick.transition(context); + line = line.transition(context); + text = text.transition(context); + + tickExit = tickExit.transition(context) + .attr("opacity", epsilon) + .attr("transform", function(d) { return isFinite(d = position(d)) ? transform(d + offset) : this.getAttribute("transform"); }); + + tickEnter + .attr("opacity", epsilon) + .attr("transform", function(d) { var p = this.parentNode.__axis; return transform((p && isFinite(p = p(d)) ? p : position(d)) + offset); }); + } + + tickExit.remove(); + + path + .attr("d", orient === left || orient === right + ? (tickSizeOuter ? "M" + k * tickSizeOuter + "," + range0 + "H" + offset + "V" + range1 + "H" + k * tickSizeOuter : "M" + offset + "," + range0 + "V" + range1) + : (tickSizeOuter ? "M" + range0 + "," + k * tickSizeOuter + "V" + offset + "H" + range1 + "V" + k * tickSizeOuter : "M" + range0 + "," + offset + "H" + range1)); + + tick + .attr("opacity", 1) + .attr("transform", function(d) { return transform(position(d) + offset); }); + + line + .attr(x + "2", k * tickSizeInner); + + text + .attr(x, k * spacing) + .text(format); + + selection.filter(entering) + .attr("fill", "none") + .attr("font-size", 10) + .attr("font-family", "sans-serif") + .attr("text-anchor", orient === right ? "start" : orient === left ? "end" : "middle"); + + selection + .each(function() { this.__axis = position; }); + } + + axis.scale = function(_) { + return arguments.length ? (scale = _, axis) : scale; + }; + + axis.ticks = function() { + return tickArguments = Array.from(arguments), axis; + }; + + axis.tickArguments = function(_) { + return arguments.length ? (tickArguments = _ == null ? [] : Array.from(_), axis) : tickArguments.slice(); + }; + + axis.tickValues = function(_) { + return arguments.length ? (tickValues = _ == null ? null : Array.from(_), axis) : tickValues && tickValues.slice(); + }; + + axis.tickFormat = function(_) { + return arguments.length ? (tickFormat = _, axis) : tickFormat; + }; + + axis.tickSize = function(_) { + return arguments.length ? (tickSizeInner = tickSizeOuter = +_, axis) : tickSizeInner; + }; + + axis.tickSizeInner = function(_) { + return arguments.length ? (tickSizeInner = +_, axis) : tickSizeInner; + }; + + axis.tickSizeOuter = function(_) { + return arguments.length ? (tickSizeOuter = +_, axis) : tickSizeOuter; + }; + + axis.tickPadding = function(_) { + return arguments.length ? (tickPadding = +_, axis) : tickPadding; + }; + + axis.offset = function(_) { + return arguments.length ? (offset = +_, axis) : offset; + }; + + return axis; +} + +export function axisTop(scale) { + return axis(top, scale); +} + +export function axisRight(scale) { + return axis(right, scale); +} + +export function axisBottom(scale) { + return axis(bottom, scale); +} + +export function axisLeft(scale) { + return axis(left, scale); +} diff --git a/frontend/node_modules/d3-axis/src/identity.js b/frontend/node_modules/d3-axis/src/identity.js new file mode 100644 index 0000000..b2f94b2 --- /dev/null +++ b/frontend/node_modules/d3-axis/src/identity.js @@ -0,0 +1,3 @@ +export default function(x) { + return x; +} diff --git a/frontend/node_modules/d3-axis/src/index.js b/frontend/node_modules/d3-axis/src/index.js new file mode 100644 index 0000000..d870043 --- /dev/null +++ b/frontend/node_modules/d3-axis/src/index.js @@ -0,0 +1,6 @@ +export { + axisTop, + axisRight, + axisBottom, + axisLeft +} from "./axis.js"; diff --git a/frontend/node_modules/d3-brush/LICENSE b/frontend/node_modules/d3-brush/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-brush/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-brush/README.md b/frontend/node_modules/d3-brush/README.md new file mode 100644 index 0000000..2ba014c --- /dev/null +++ b/frontend/node_modules/d3-brush/README.md @@ -0,0 +1,185 @@ +# d3-brush + +Brushing is the interactive specification a one- or two-dimensional selected region using a pointing gesture, such as by clicking and dragging the mouse. Brushing is often used to select discrete elements, such as dots in a scatterplot or files on a desktop. It can also be used to zoom-in to a region of interest, or to select continuous regions for [cross-filtering data](http://square.github.io/crossfilter/) or live histograms: + +[Mona Lisa Histogram](https://observablehq.com/@d3/mona-lisa-histogram) + +The d3-brush module implements brushing for mouse and touch events using [SVG](https://www.w3.org/TR/SVG/). Click and drag on the brush selection to translate the selection. Click and drag on one of the selection handles to move the corresponding edge (or edges) of the selection. Click and drag on the invisible overlay to define a new brush selection, or click anywhere within the brushable region while holding down the META (⌘) key. Holding down the ALT (⌥) key while moving the brush causes it to reposition around its center, while holding down SPACE locks the current brush size, allowing only translation. + +Brushes also support programmatic control. For example, you can listen to [*end* events](#brush-events), and then initiate a transition with [*brush*.move](#brush_move) to snap the brush selection to semantic boundaries: + +[Brush Snapping](https://observablehq.com/@d3/brush-snapping-transitions) + +Or you can have the brush recenter when you click outside the current selection: + +[Click-to-Recenter](https://observablehq.com/@d3/click-to-recenter-brush) + +## Installing + +If you use npm, `npm install d3-brush`. You can also download the [latest release on GitHub](https://github.com/d3/d3-brush/releases/latest). For vanilla HTML in modern browsers, import d3-brush from Skypack: + +```html + +``` + +For legacy environments, you can load d3-brush’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + + + + + + + + + +``` + + +[Try d3-brush in your browser.](https://observablehq.com/collection/@d3/d3-brush) + +## API Reference + +# d3.brush() · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js), [Examples](https://observablehq.com/@d3/brushable-scatterplot) + +Creates a new two-dimensional brush. + +# d3.brushX() · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js), [Examples](https://observablehq.com/@d3/focus-context) + +Creates a new one-dimensional brush along the *x*-dimension. + +# d3.brushY() · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js) + +Creates a new one-dimensional brush along the *y*-dimension. + +# brush(group) · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js), [Examples](https://observablehq.com/@d3/brushable-scatterplot-matrix) + +Applies the brush to the specified *group*, which must be a [selection](https://github.com/d3/d3-selection) of SVG [G elements](https://www.w3.org/TR/SVG/struct.html#Groups). This function is typically not invoked directly, and is instead invoked via [*selection*.call](https://github.com/d3/d3-selection#selection_call). For example, to render a brush: + +```js +svg.append("g") + .attr("class", "brush") + .call(d3.brush().on("brush", brushed)); +``` + +Internally, the brush uses [*selection*.on](https://github.com/d3/d3-selection#selection_on) to bind the necessary event listeners for dragging. The listeners use the name `.brush`, so you can subsequently unbind the brush event listeners as follows: + +```js +group.on(".brush", null); +``` + +The brush also creates the SVG elements necessary to display the brush selection and to receive input events for interaction. You can add, remove or modify these elements as desired to change the brush appearance; you can also apply stylesheets to modify the brush appearance. The structure of a two-dimensional brush is as follows: + +```html + + + + + + + + + + + + +``` + +The overlay rect covers the brushable area defined by [*brush*.extent](#brush_extent). The selection rect covers the area defined by the current [brush selection](#brushSelection). The handle rects cover the edges and corners of the brush selection, allowing the corresponding value in the brush selection to be modified interactively. To modify the brush selection programmatically, use [*brush*.move](#brush_move). + +# brush.move(group, selection[, event]) · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js), [Examples](https://observablehq.com/d/93b91f86f9ebc9b9) + +Sets the active *selection* of the brush on the specified *group*, which must be a [selection](https://github.com/d3/d3-selection) or a [transition](https://github.com/d3/d3-transition) of SVG [G elements](https://www.w3.org/TR/SVG/struct.html#Groups). The *selection* must be defined as an array of numbers, or null to clear the brush selection. For a [two-dimensional brush](#brush), it must be defined as [[*x0*, *y0*], [*x1*, *y1*]], where *x0* is the minimum *x*-value, *y0* is the minimum *y*-value, *x1* is the maximum *x*-value, and *y1* is the maximum *y*-value. For an [*x*-brush](#brushX), it must be defined as [*x0*, *x1*]; for a [*y*-brush](#brushY), it must be defined as [*y0*, *y1*]. The selection may also be specified as a function which returns such an array; if a function, it is invoked for each selected element, being passed the current datum `d` and index `i`, with the `this` context as the current DOM element. The returned array defines the brush selection for that element. + +# brush.clear(group[, event]) · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js), [Examples](https://observablehq.com/@d3/double-click-brush-clear) + +An alias for [*brush*.move](#brush_move) with the null selection. + +# brush.extent([extent]) · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js), [Examples](https://observablehq.com/@d3/brush-snapping) + +If *extent* is specified, sets the brushable extent to the specified array of points [[*x0*, *y0*], [*x1*, *y1*]], where [*x0*, *y0*] is the top-left corner and [*x1*, *y1*] is the bottom-right corner, and returns this brush. The *extent* may also be specified as a function which returns such an array; if a function, it is invoked for each selected element, being passed the current datum `d` and index `i`, with the `this` context as the current DOM element. If *extent* is not specified, returns the current extent accessor, which defaults to: + +```js +function defaultExtent() { + var svg = this.ownerSVGElement || this; + if (svg.hasAttribute("viewBox")) { + svg = svg.viewBox.baseVal; + return [[svg.x, svg.y], [svg.x + svg.width, svg.y + svg.height]]; + } + return [[0, 0], [svg.width.baseVal.value, svg.height.baseVal.value]]; +} +``` + +This default implementation requires that the owner SVG element have a defined [viewBox](https://www.w3.org/TR/SVG/coords.html#ViewBoxAttribute), or [width](https://www.w3.org/TR/SVG/struct.html#SVGElementWidthAttribute) and [height](https://www.w3.org/TR/SVG/struct.html#SVGElementHeightAttribute) attributes. Alternatively, consider using [*element*.getBoundingClientRect](https://developer.mozilla.org/en-US/docs/Web/API/Element/getBoundingClientRect). (In Firefox, [*element*.clientWidth](https://developer.mozilla.org/en-US/docs/Web/API/Element/clientWidth) and [*element*.clientHeight](https://developer.mozilla.org/en-US/docs/Web/API/Element/clientHeight) is zero for SVG elements!) + +The brush extent determines the size of the invisible overlay and also constrains the brush selection; the brush selection cannot go outside the brush extent. + +# brush.filter([filter]) · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js), [Examples](https://observablehq.com/@d3/brush-filter) + +If *filter* is specified, sets the filter to the specified function and returns the brush. If *filter* is not specified, returns the current filter, which defaults to: + +```js +function filter(event) { + return !event.ctrlKey && !event.button; +} +``` + +If the filter returns falsey, the initiating event is ignored and no brush gesture is started. Thus, the filter determines which input events are ignored. The default filter ignores mousedown events on secondary buttons, since those buttons are typically intended for other purposes, such as the context menu. + +# brush.touchable([touchable]) · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js) + +If *touchable* is specified, sets the touch support detector to the specified function and returns the brush. If *touchable* is not specified, returns the current touch support detector, which defaults to: + +```js +function touchable() { + return navigator.maxTouchPoints || ("ontouchstart" in this); +} +``` + +Touch event listeners are only registered if the detector returns truthy for the corresponding element when the brush is [applied](#_brush). The default detector works well for most browsers that are capable of touch input, but not all; Chrome’s mobile device emulator, for example, fails detection. + +# brush.keyModifiers([modifiers]) · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js) + +If *modifiers* is specified, sets whether the brush listens to key events during brushing and returns the brush. If *modifiers* is not specified, returns the current behavior, which defaults to true. + +# brush.handleSize([size]) · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js) + +If *size* is specified, sets the size of the brush handles to the specified number and returns the brush. If *size* is not specified, returns the current handle size, which defaults to six. This method must be called before [applying the brush](#_brush) to a selection; changing the handle size does not affect brushes that were previously rendered. + +# brush.on(typenames[, listener]) · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js) + +If *listener* is specified, sets the event *listener* for the specified *typenames* and returns the brush. If an event listener was already registered for the same type and name, the existing listener is removed before the new listener is added. If *listener* is null, removes the current event listeners for the specified *typenames*, if any. If *listener* is not specified, returns the first currently-assigned listener matching the specified *typenames*, if any. When a specified event is dispatched, each *listener* will be invoked with the same context and arguments as [*selection*.on](https://github.com/d3/d3-selection#selection_on) listeners: the current event `event` and datum `d`, with the `this` context as the current DOM element. + +The *typenames* is a string containing one or more *typename* separated by whitespace. Each *typename* is a *type*, optionally followed by a period (`.`) and a *name*, such as `brush.foo` and `brush.bar`; the name allows multiple listeners to be registered for the same *type*. The *type* must be one of the following: + +* `start` - at the start of a brush gesture, such as on mousedown. +* `brush` - when the brush moves, such as on mousemove. +* `end` - at the end of a brush gesture, such as on mouseup. + +See [*dispatch*.on](https://github.com/d3/d3-dispatch#dispatch_on) and [Brush Events](#brush-events) for more. + +# d3.brushSelection(node) · [Source](https://github.com/d3/d3-brush/blob/master/src/brush.js), [Examples](https://observablehq.com/@d3/double-click-brush-clear) + +Returns the current brush selection for the specified *node*. Internally, an element’s brush state is stored as *element*.\_\_brush; however, you should use this method rather than accessing it directly. If the given *node* has no selection, returns null. Otherwise, the *selection* is defined as an array of numbers. For a [two-dimensional brush](#brush), it is [[*x0*, *y0*], [*x1*, *y1*]], where *x0* is the minimum *x*-value, *y0* is the minimum *y*-value, *x1* is the maximum *x*-value, and *y1* is the maximum *y*-value. For an [*x*-brush](#brushX), it is [*x0*, *x1*]; for a [*y*-brush](#brushY), it is [*y0*, *y1*]. + +### Brush Events + +When a [brush event listener](#brush_on) is invoked, it receives the current brush event. The *event* object exposes several fields: + +* `target` - the associated [brush behavior](#brush). +* `type` - the string “start”, “brush” or “end”; see [*brush*.on](#brush_on). +* `selection` - the current [brush selection](#brushSelection). +* `sourceEvent` - the underlying input event, such as mousemove or touchmove. +* `mode` - the string “drag”, “space”, “handle” or “center”; the mode of the brush. diff --git a/frontend/node_modules/d3-brush/dist/d3-brush.js b/frontend/node_modules/d3-brush/dist/d3-brush.js new file mode 100644 index 0000000..b1a9afc --- /dev/null +++ b/frontend/node_modules/d3-brush/dist/d3-brush.js @@ -0,0 +1,656 @@ +// https://d3js.org/d3-brush/ v3.0.0 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-dispatch'), require('d3-drag'), require('d3-interpolate'), require('d3-selection'), require('d3-transition')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-dispatch', 'd3-drag', 'd3-interpolate', 'd3-selection', 'd3-transition'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3, global.d3, global.d3, global.d3, global.d3)); +}(this, (function (exports, d3Dispatch, d3Drag, d3Interpolate, d3Selection, d3Transition) { 'use strict'; + +var constant = x => () => x; + +function BrushEvent(type, { + sourceEvent, + target, + selection, + mode, + dispatch +}) { + Object.defineProperties(this, { + type: {value: type, enumerable: true, configurable: true}, + sourceEvent: {value: sourceEvent, enumerable: true, configurable: true}, + target: {value: target, enumerable: true, configurable: true}, + selection: {value: selection, enumerable: true, configurable: true}, + mode: {value: mode, enumerable: true, configurable: true}, + _: {value: dispatch} + }); +} + +function nopropagation(event) { + event.stopImmediatePropagation(); +} + +function noevent(event) { + event.preventDefault(); + event.stopImmediatePropagation(); +} + +var MODE_DRAG = {name: "drag"}, + MODE_SPACE = {name: "space"}, + MODE_HANDLE = {name: "handle"}, + MODE_CENTER = {name: "center"}; + +const {abs, max, min} = Math; + +function number1(e) { + return [+e[0], +e[1]]; +} + +function number2(e) { + return [number1(e[0]), number1(e[1])]; +} + +var X = { + name: "x", + handles: ["w", "e"].map(type), + input: function(x, e) { return x == null ? null : [[+x[0], e[0][1]], [+x[1], e[1][1]]]; }, + output: function(xy) { return xy && [xy[0][0], xy[1][0]]; } +}; + +var Y = { + name: "y", + handles: ["n", "s"].map(type), + input: function(y, e) { return y == null ? null : [[e[0][0], +y[0]], [e[1][0], +y[1]]]; }, + output: function(xy) { return xy && [xy[0][1], xy[1][1]]; } +}; + +var XY = { + name: "xy", + handles: ["n", "w", "e", "s", "nw", "ne", "sw", "se"].map(type), + input: function(xy) { return xy == null ? null : number2(xy); }, + output: function(xy) { return xy; } +}; + +var cursors = { + overlay: "crosshair", + selection: "move", + n: "ns-resize", + e: "ew-resize", + s: "ns-resize", + w: "ew-resize", + nw: "nwse-resize", + ne: "nesw-resize", + se: "nwse-resize", + sw: "nesw-resize" +}; + +var flipX = { + e: "w", + w: "e", + nw: "ne", + ne: "nw", + se: "sw", + sw: "se" +}; + +var flipY = { + n: "s", + s: "n", + nw: "sw", + ne: "se", + se: "ne", + sw: "nw" +}; + +var signsX = { + overlay: +1, + selection: +1, + n: null, + e: +1, + s: null, + w: -1, + nw: -1, + ne: +1, + se: +1, + sw: -1 +}; + +var signsY = { + overlay: +1, + selection: +1, + n: -1, + e: null, + s: +1, + w: null, + nw: -1, + ne: -1, + se: +1, + sw: +1 +}; + +function type(t) { + return {type: t}; +} + +// Ignore right-click, since that should open the context menu. +function defaultFilter(event) { + return !event.ctrlKey && !event.button; +} + +function defaultExtent() { + var svg = this.ownerSVGElement || this; + if (svg.hasAttribute("viewBox")) { + svg = svg.viewBox.baseVal; + return [[svg.x, svg.y], [svg.x + svg.width, svg.y + svg.height]]; + } + return [[0, 0], [svg.width.baseVal.value, svg.height.baseVal.value]]; +} + +function defaultTouchable() { + return navigator.maxTouchPoints || ("ontouchstart" in this); +} + +// Like d3.local, but with the name “__brush” rather than auto-generated. +function local(node) { + while (!node.__brush) if (!(node = node.parentNode)) return; + return node.__brush; +} + +function empty(extent) { + return extent[0][0] === extent[1][0] + || extent[0][1] === extent[1][1]; +} + +function brushSelection(node) { + var state = node.__brush; + return state ? state.dim.output(state.selection) : null; +} + +function brushX() { + return brush$1(X); +} + +function brushY() { + return brush$1(Y); +} + +function brush() { + return brush$1(XY); +} + +function brush$1(dim) { + var extent = defaultExtent, + filter = defaultFilter, + touchable = defaultTouchable, + keys = true, + listeners = d3Dispatch.dispatch("start", "brush", "end"), + handleSize = 6, + touchending; + + function brush(group) { + var overlay = group + .property("__brush", initialize) + .selectAll(".overlay") + .data([type("overlay")]); + + overlay.enter().append("rect") + .attr("class", "overlay") + .attr("pointer-events", "all") + .attr("cursor", cursors.overlay) + .merge(overlay) + .each(function() { + var extent = local(this).extent; + d3Selection.select(this) + .attr("x", extent[0][0]) + .attr("y", extent[0][1]) + .attr("width", extent[1][0] - extent[0][0]) + .attr("height", extent[1][1] - extent[0][1]); + }); + + group.selectAll(".selection") + .data([type("selection")]) + .enter().append("rect") + .attr("class", "selection") + .attr("cursor", cursors.selection) + .attr("fill", "#777") + .attr("fill-opacity", 0.3) + .attr("stroke", "#fff") + .attr("shape-rendering", "crispEdges"); + + var handle = group.selectAll(".handle") + .data(dim.handles, function(d) { return d.type; }); + + handle.exit().remove(); + + handle.enter().append("rect") + .attr("class", function(d) { return "handle handle--" + d.type; }) + .attr("cursor", function(d) { return cursors[d.type]; }); + + group + .each(redraw) + .attr("fill", "none") + .attr("pointer-events", "all") + .on("mousedown.brush", started) + .filter(touchable) + .on("touchstart.brush", started) + .on("touchmove.brush", touchmoved) + .on("touchend.brush touchcancel.brush", touchended) + .style("touch-action", "none") + .style("-webkit-tap-highlight-color", "rgba(0,0,0,0)"); + } + + brush.move = function(group, selection, event) { + if (group.tween) { + group + .on("start.brush", function(event) { emitter(this, arguments).beforestart().start(event); }) + .on("interrupt.brush end.brush", function(event) { emitter(this, arguments).end(event); }) + .tween("brush", function() { + var that = this, + state = that.__brush, + emit = emitter(that, arguments), + selection0 = state.selection, + selection1 = dim.input(typeof selection === "function" ? selection.apply(this, arguments) : selection, state.extent), + i = d3Interpolate.interpolate(selection0, selection1); + + function tween(t) { + state.selection = t === 1 && selection1 === null ? null : i(t); + redraw.call(that); + emit.brush(); + } + + return selection0 !== null && selection1 !== null ? tween : tween(1); + }); + } else { + group + .each(function() { + var that = this, + args = arguments, + state = that.__brush, + selection1 = dim.input(typeof selection === "function" ? selection.apply(that, args) : selection, state.extent), + emit = emitter(that, args).beforestart(); + + d3Transition.interrupt(that); + state.selection = selection1 === null ? null : selection1; + redraw.call(that); + emit.start(event).brush(event).end(event); + }); + } + }; + + brush.clear = function(group, event) { + brush.move(group, null, event); + }; + + function redraw() { + var group = d3Selection.select(this), + selection = local(this).selection; + + if (selection) { + group.selectAll(".selection") + .style("display", null) + .attr("x", selection[0][0]) + .attr("y", selection[0][1]) + .attr("width", selection[1][0] - selection[0][0]) + .attr("height", selection[1][1] - selection[0][1]); + + group.selectAll(".handle") + .style("display", null) + .attr("x", function(d) { return d.type[d.type.length - 1] === "e" ? selection[1][0] - handleSize / 2 : selection[0][0] - handleSize / 2; }) + .attr("y", function(d) { return d.type[0] === "s" ? selection[1][1] - handleSize / 2 : selection[0][1] - handleSize / 2; }) + .attr("width", function(d) { return d.type === "n" || d.type === "s" ? selection[1][0] - selection[0][0] + handleSize : handleSize; }) + .attr("height", function(d) { return d.type === "e" || d.type === "w" ? selection[1][1] - selection[0][1] + handleSize : handleSize; }); + } + + else { + group.selectAll(".selection,.handle") + .style("display", "none") + .attr("x", null) + .attr("y", null) + .attr("width", null) + .attr("height", null); + } + } + + function emitter(that, args, clean) { + var emit = that.__brush.emitter; + return emit && (!clean || !emit.clean) ? emit : new Emitter(that, args, clean); + } + + function Emitter(that, args, clean) { + this.that = that; + this.args = args; + this.state = that.__brush; + this.active = 0; + this.clean = clean; + } + + Emitter.prototype = { + beforestart: function() { + if (++this.active === 1) this.state.emitter = this, this.starting = true; + return this; + }, + start: function(event, mode) { + if (this.starting) this.starting = false, this.emit("start", event, mode); + else this.emit("brush", event); + return this; + }, + brush: function(event, mode) { + this.emit("brush", event, mode); + return this; + }, + end: function(event, mode) { + if (--this.active === 0) delete this.state.emitter, this.emit("end", event, mode); + return this; + }, + emit: function(type, event, mode) { + var d = d3Selection.select(this.that).datum(); + listeners.call( + type, + this.that, + new BrushEvent(type, { + sourceEvent: event, + target: brush, + selection: dim.output(this.state.selection), + mode, + dispatch: listeners + }), + d + ); + } + }; + + function started(event) { + if (touchending && !event.touches) return; + if (!filter.apply(this, arguments)) return; + + var that = this, + type = event.target.__data__.type, + mode = (keys && event.metaKey ? type = "overlay" : type) === "selection" ? MODE_DRAG : (keys && event.altKey ? MODE_CENTER : MODE_HANDLE), + signX = dim === Y ? null : signsX[type], + signY = dim === X ? null : signsY[type], + state = local(that), + extent = state.extent, + selection = state.selection, + W = extent[0][0], w0, w1, + N = extent[0][1], n0, n1, + E = extent[1][0], e0, e1, + S = extent[1][1], s0, s1, + dx = 0, + dy = 0, + moving, + shifting = signX && signY && keys && event.shiftKey, + lockX, + lockY, + points = Array.from(event.touches || [event], t => { + const i = t.identifier; + t = d3Selection.pointer(t, that); + t.point0 = t.slice(); + t.identifier = i; + return t; + }); + + d3Transition.interrupt(that); + var emit = emitter(that, arguments, true).beforestart(); + + if (type === "overlay") { + if (selection) moving = true; + const pts = [points[0], points[1] || points[0]]; + state.selection = selection = [[ + w0 = dim === Y ? W : min(pts[0][0], pts[1][0]), + n0 = dim === X ? N : min(pts[0][1], pts[1][1]) + ], [ + e0 = dim === Y ? E : max(pts[0][0], pts[1][0]), + s0 = dim === X ? S : max(pts[0][1], pts[1][1]) + ]]; + if (points.length > 1) move(event); + } else { + w0 = selection[0][0]; + n0 = selection[0][1]; + e0 = selection[1][0]; + s0 = selection[1][1]; + } + + w1 = w0; + n1 = n0; + e1 = e0; + s1 = s0; + + var group = d3Selection.select(that) + .attr("pointer-events", "none"); + + var overlay = group.selectAll(".overlay") + .attr("cursor", cursors[type]); + + if (event.touches) { + emit.moved = moved; + emit.ended = ended; + } else { + var view = d3Selection.select(event.view) + .on("mousemove.brush", moved, true) + .on("mouseup.brush", ended, true); + if (keys) view + .on("keydown.brush", keydowned, true) + .on("keyup.brush", keyupped, true); + + d3Drag.dragDisable(event.view); + } + + redraw.call(that); + emit.start(event, mode.name); + + function moved(event) { + for (const p of event.changedTouches || [event]) { + for (const d of points) + if (d.identifier === p.identifier) d.cur = d3Selection.pointer(p, that); + } + if (shifting && !lockX && !lockY && points.length === 1) { + const point = points[0]; + if (abs(point.cur[0] - point[0]) > abs(point.cur[1] - point[1])) + lockY = true; + else + lockX = true; + } + for (const point of points) + if (point.cur) point[0] = point.cur[0], point[1] = point.cur[1]; + moving = true; + noevent(event); + move(event); + } + + function move(event) { + const point = points[0], point0 = point.point0; + var t; + + dx = point[0] - point0[0]; + dy = point[1] - point0[1]; + + switch (mode) { + case MODE_SPACE: + case MODE_DRAG: { + if (signX) dx = max(W - w0, min(E - e0, dx)), w1 = w0 + dx, e1 = e0 + dx; + if (signY) dy = max(N - n0, min(S - s0, dy)), n1 = n0 + dy, s1 = s0 + dy; + break; + } + case MODE_HANDLE: { + if (points[1]) { + if (signX) w1 = max(W, min(E, points[0][0])), e1 = max(W, min(E, points[1][0])), signX = 1; + if (signY) n1 = max(N, min(S, points[0][1])), s1 = max(N, min(S, points[1][1])), signY = 1; + } else { + if (signX < 0) dx = max(W - w0, min(E - w0, dx)), w1 = w0 + dx, e1 = e0; + else if (signX > 0) dx = max(W - e0, min(E - e0, dx)), w1 = w0, e1 = e0 + dx; + if (signY < 0) dy = max(N - n0, min(S - n0, dy)), n1 = n0 + dy, s1 = s0; + else if (signY > 0) dy = max(N - s0, min(S - s0, dy)), n1 = n0, s1 = s0 + dy; + } + break; + } + case MODE_CENTER: { + if (signX) w1 = max(W, min(E, w0 - dx * signX)), e1 = max(W, min(E, e0 + dx * signX)); + if (signY) n1 = max(N, min(S, n0 - dy * signY)), s1 = max(N, min(S, s0 + dy * signY)); + break; + } + } + + if (e1 < w1) { + signX *= -1; + t = w0, w0 = e0, e0 = t; + t = w1, w1 = e1, e1 = t; + if (type in flipX) overlay.attr("cursor", cursors[type = flipX[type]]); + } + + if (s1 < n1) { + signY *= -1; + t = n0, n0 = s0, s0 = t; + t = n1, n1 = s1, s1 = t; + if (type in flipY) overlay.attr("cursor", cursors[type = flipY[type]]); + } + + if (state.selection) selection = state.selection; // May be set by brush.move! + if (lockX) w1 = selection[0][0], e1 = selection[1][0]; + if (lockY) n1 = selection[0][1], s1 = selection[1][1]; + + if (selection[0][0] !== w1 + || selection[0][1] !== n1 + || selection[1][0] !== e1 + || selection[1][1] !== s1) { + state.selection = [[w1, n1], [e1, s1]]; + redraw.call(that); + emit.brush(event, mode.name); + } + } + + function ended(event) { + nopropagation(event); + if (event.touches) { + if (event.touches.length) return; + if (touchending) clearTimeout(touchending); + touchending = setTimeout(function() { touchending = null; }, 500); // Ghost clicks are delayed! + } else { + d3Drag.dragEnable(event.view, moving); + view.on("keydown.brush keyup.brush mousemove.brush mouseup.brush", null); + } + group.attr("pointer-events", "all"); + overlay.attr("cursor", cursors.overlay); + if (state.selection) selection = state.selection; // May be set by brush.move (on start)! + if (empty(selection)) state.selection = null, redraw.call(that); + emit.end(event, mode.name); + } + + function keydowned(event) { + switch (event.keyCode) { + case 16: { // SHIFT + shifting = signX && signY; + break; + } + case 18: { // ALT + if (mode === MODE_HANDLE) { + if (signX) e0 = e1 - dx * signX, w0 = w1 + dx * signX; + if (signY) s0 = s1 - dy * signY, n0 = n1 + dy * signY; + mode = MODE_CENTER; + move(event); + } + break; + } + case 32: { // SPACE; takes priority over ALT + if (mode === MODE_HANDLE || mode === MODE_CENTER) { + if (signX < 0) e0 = e1 - dx; else if (signX > 0) w0 = w1 - dx; + if (signY < 0) s0 = s1 - dy; else if (signY > 0) n0 = n1 - dy; + mode = MODE_SPACE; + overlay.attr("cursor", cursors.selection); + move(event); + } + break; + } + default: return; + } + noevent(event); + } + + function keyupped(event) { + switch (event.keyCode) { + case 16: { // SHIFT + if (shifting) { + lockX = lockY = shifting = false; + move(event); + } + break; + } + case 18: { // ALT + if (mode === MODE_CENTER) { + if (signX < 0) e0 = e1; else if (signX > 0) w0 = w1; + if (signY < 0) s0 = s1; else if (signY > 0) n0 = n1; + mode = MODE_HANDLE; + move(event); + } + break; + } + case 32: { // SPACE + if (mode === MODE_SPACE) { + if (event.altKey) { + if (signX) e0 = e1 - dx * signX, w0 = w1 + dx * signX; + if (signY) s0 = s1 - dy * signY, n0 = n1 + dy * signY; + mode = MODE_CENTER; + } else { + if (signX < 0) e0 = e1; else if (signX > 0) w0 = w1; + if (signY < 0) s0 = s1; else if (signY > 0) n0 = n1; + mode = MODE_HANDLE; + } + overlay.attr("cursor", cursors[type]); + move(event); + } + break; + } + default: return; + } + noevent(event); + } + } + + function touchmoved(event) { + emitter(this, arguments).moved(event); + } + + function touchended(event) { + emitter(this, arguments).ended(event); + } + + function initialize() { + var state = this.__brush || {selection: null}; + state.extent = number2(extent.apply(this, arguments)); + state.dim = dim; + return state; + } + + brush.extent = function(_) { + return arguments.length ? (extent = typeof _ === "function" ? _ : constant(number2(_)), brush) : extent; + }; + + brush.filter = function(_) { + return arguments.length ? (filter = typeof _ === "function" ? _ : constant(!!_), brush) : filter; + }; + + brush.touchable = function(_) { + return arguments.length ? (touchable = typeof _ === "function" ? _ : constant(!!_), brush) : touchable; + }; + + brush.handleSize = function(_) { + return arguments.length ? (handleSize = +_, brush) : handleSize; + }; + + brush.keyModifiers = function(_) { + return arguments.length ? (keys = !!_, brush) : keys; + }; + + brush.on = function() { + var value = listeners.on.apply(listeners, arguments); + return value === listeners ? brush : value; + }; + + return brush; +} + +exports.brush = brush; +exports.brushSelection = brushSelection; +exports.brushX = brushX; +exports.brushY = brushY; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-brush/dist/d3-brush.min.js b/frontend/node_modules/d3-brush/dist/d3-brush.min.js new file mode 100644 index 0000000..c1e496d --- /dev/null +++ b/frontend/node_modules/d3-brush/dist/d3-brush.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-brush/ v3.0.0 Copyright 2010-2021 Mike Bostock +!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports,require("d3-dispatch"),require("d3-drag"),require("d3-interpolate"),require("d3-selection"),require("d3-transition")):"function"==typeof define&&define.amd?define(["exports","d3-dispatch","d3-drag","d3-interpolate","d3-selection","d3-transition"],t):t((e="undefined"!=typeof globalThis?globalThis:e||self).d3=e.d3||{},e.d3,e.d3,e.d3,e.d3,e.d3)}(this,(function(e,t,n,r,i,s){"use strict";var u=e=>()=>e;function o(e,{sourceEvent:t,target:n,selection:r,mode:i,dispatch:s}){Object.defineProperties(this,{type:{value:e,enumerable:!0,configurable:!0},sourceEvent:{value:t,enumerable:!0,configurable:!0},target:{value:n,enumerable:!0,configurable:!0},selection:{value:r,enumerable:!0,configurable:!0},mode:{value:i,enumerable:!0,configurable:!0},_:{value:s}})}function a(e){e.stopImmediatePropagation()}function l(e){e.preventDefault(),e.stopImmediatePropagation()}var c={name:"drag"},h={name:"space"},f={name:"handle"},d={name:"center"};const{abs:p,max:b,min:y}=Math;function v(e){return[+e[0],+e[1]]}function m(e){return[v(e[0]),v(e[1])]}var w={name:"x",handles:["w","e"].map(T),input:function(e,t){return null==e?null:[[+e[0],t[0][1]],[+e[1],t[1][1]]]},output:function(e){return e&&[e[0][0],e[1][0]]}},g={name:"y",handles:["n","s"].map(T),input:function(e,t){return null==e?null:[[t[0][0],+e[0]],[t[1][0],+e[1]]]},output:function(e){return e&&[e[0][1],e[1][1]]}},_={name:"xy",handles:["n","w","e","s","nw","ne","sw","se"].map(T),input:function(e){return null==e?null:m(e)},output:function(e){return e}},x={overlay:"crosshair",selection:"move",n:"ns-resize",e:"ew-resize",s:"ns-resize",w:"ew-resize",nw:"nwse-resize",ne:"nesw-resize",se:"nwse-resize",sw:"nesw-resize"},k={e:"w",w:"e",nw:"ne",ne:"nw",se:"sw",sw:"se"},z={n:"s",s:"n",nw:"sw",ne:"se",se:"ne",sw:"nw"},A={overlay:1,selection:1,n:null,e:1,s:null,w:-1,nw:-1,ne:1,se:1,sw:-1},E={overlay:1,selection:1,n:-1,e:null,s:1,w:null,nw:-1,ne:-1,se:1,sw:1};function T(e){return{type:e}}function q(e){return!e.ctrlKey&&!e.button}function K(){var e=this.ownerSVGElement||this;return e.hasAttribute("viewBox")?[[(e=e.viewBox.baseVal).x,e.y],[e.x+e.width,e.y+e.height]]:[[0,0],[e.width.baseVal.value,e.height.baseVal.value]]}function P(){return navigator.maxTouchPoints||"ontouchstart"in this}function V(e){for(;!e.__brush;)if(!(e=e.parentNode))return;return e.__brush}function j(e){return e[0][0]===e[1][0]||e[0][1]===e[1][1]}function M(e){var v,_=K,M=q,S=P,B=!0,C=t.dispatch("start","brush","end"),D=6;function I(t){var n=t.property("__brush",H).selectAll(".overlay").data([T("overlay")]);n.enter().append("rect").attr("class","overlay").attr("pointer-events","all").attr("cursor",x.overlay).merge(n).each((function(){var e=V(this).extent;i.select(this).attr("x",e[0][0]).attr("y",e[0][1]).attr("width",e[1][0]-e[0][0]).attr("height",e[1][1]-e[0][1])})),t.selectAll(".selection").data([T("selection")]).enter().append("rect").attr("class","selection").attr("cursor",x.selection).attr("fill","#777").attr("fill-opacity",.3).attr("stroke","#fff").attr("shape-rendering","crispEdges");var r=t.selectAll(".handle").data(e.handles,(function(e){return e.type}));r.exit().remove(),r.enter().append("rect").attr("class",(function(e){return"handle handle--"+e.type})).attr("cursor",(function(e){return x[e.type]})),t.each(O).attr("fill","none").attr("pointer-events","all").on("mousedown.brush",X).filter(S).on("touchstart.brush",X).on("touchmove.brush",Y).on("touchend.brush touchcancel.brush",F).style("touch-action","none").style("-webkit-tap-highlight-color","rgba(0,0,0,0)")}function O(){var e=i.select(this),t=V(this).selection;t?(e.selectAll(".selection").style("display",null).attr("x",t[0][0]).attr("y",t[0][1]).attr("width",t[1][0]-t[0][0]).attr("height",t[1][1]-t[0][1]),e.selectAll(".handle").style("display",null).attr("x",(function(e){return"e"===e.type[e.type.length-1]?t[1][0]-D/2:t[0][0]-D/2})).attr("y",(function(e){return"s"===e.type[0]?t[1][1]-D/2:t[0][1]-D/2})).attr("width",(function(e){return"n"===e.type||"s"===e.type?t[1][0]-t[0][0]+D:D})).attr("height",(function(e){return"e"===e.type||"w"===e.type?t[1][1]-t[0][1]+D:D}))):e.selectAll(".selection,.handle").style("display","none").attr("x",null).attr("y",null).attr("width",null).attr("height",null)}function G(e,t,n){var r=e.__brush.emitter;return!r||n&&r.clean?new N(e,t,n):r}function N(e,t,n){this.that=e,this.args=t,this.state=e.__brush,this.active=0,this.clean=n}function X(t){if((!v||t.touches)&&M.apply(this,arguments)){var r,u,o,m,_,T,q,K,P,S,C,D=this,I=t.target.__data__.type,N="selection"===(B&&t.metaKey?I="overlay":I)?c:B&&t.altKey?d:f,X=e===g?null:A[I],Y=e===w?null:E[I],F=V(D),H=F.extent,J=F.selection,L=H[0][0],Q=H[0][1],R=H[1][0],U=H[1][1],W=0,Z=0,$=X&&Y&&B&&t.shiftKey,ee=Array.from(t.touches||[t],(e=>{const t=e.identifier;return(e=i.pointer(e,D)).point0=e.slice(),e.identifier=t,e}));s.interrupt(D);var te=G(D,arguments,!0).beforestart();if("overlay"===I){J&&(P=!0);const n=[ee[0],ee[1]||ee[0]];F.selection=J=[[r=e===g?L:y(n[0][0],n[1][0]),o=e===w?Q:y(n[0][1],n[1][1])],[_=e===g?R:b(n[0][0],n[1][0]),q=e===w?U:b(n[0][1],n[1][1])]],ee.length>1&&ue(t)}else r=J[0][0],o=J[0][1],_=J[1][0],q=J[1][1];u=r,m=o,T=_,K=q;var ne=i.select(D).attr("pointer-events","none"),re=ne.selectAll(".overlay").attr("cursor",x[I]);if(t.touches)te.moved=se,te.ended=oe;else{var ie=i.select(t.view).on("mousemove.brush",se,!0).on("mouseup.brush",oe,!0);B&&ie.on("keydown.brush",ae,!0).on("keyup.brush",le,!0),n.dragDisable(t.view)}O.call(D),te.start(t,N.name)}function se(e){for(const t of e.changedTouches||[e])for(const e of ee)e.identifier===t.identifier&&(e.cur=i.pointer(t,D));if($&&!S&&!C&&1===ee.length){const e=ee[0];p(e.cur[0]-e[0])>p(e.cur[1]-e[1])?C=!0:S=!0}for(const e of ee)e.cur&&(e[0]=e.cur[0],e[1]=e.cur[1]);P=!0,l(e),ue(e)}function ue(e){const t=ee[0],n=t.point0;var i;switch(W=t[0]-n[0],Z=t[1]-n[1],N){case h:case c:X&&(W=b(L-r,y(R-_,W)),u=r+W,T=_+W),Y&&(Z=b(Q-o,y(U-q,Z)),m=o+Z,K=q+Z);break;case f:ee[1]?(X&&(u=b(L,y(R,ee[0][0])),T=b(L,y(R,ee[1][0])),X=1),Y&&(m=b(Q,y(U,ee[0][1])),K=b(Q,y(U,ee[1][1])),Y=1)):(X<0?(W=b(L-r,y(R-r,W)),u=r+W,T=_):X>0&&(W=b(L-_,y(R-_,W)),u=r,T=_+W),Y<0?(Z=b(Q-o,y(U-o,Z)),m=o+Z,K=q):Y>0&&(Z=b(Q-q,y(U-q,Z)),m=o,K=q+Z));break;case d:X&&(u=b(L,y(R,r-W*X)),T=b(L,y(R,_+W*X))),Y&&(m=b(Q,y(U,o-Z*Y)),K=b(Q,y(U,q+Z*Y)))}T0&&(r=u-W),Y<0?q=K-Z:Y>0&&(o=m-Z),N=h,re.attr("cursor",x.selection),ue(e));break;default:return}l(e)}function le(e){switch(e.keyCode){case 16:$&&(S=C=$=!1,ue(e));break;case 18:N===d&&(X<0?_=T:X>0&&(r=u),Y<0?q=K:Y>0&&(o=m),N=f,ue(e));break;case 32:N===h&&(e.altKey?(X&&(_=T-W*X,r=u+W*X),Y&&(q=K-Z*Y,o=m+Z*Y),N=d):(X<0?_=T:X>0&&(r=u),Y<0?q=K:Y>0&&(o=m),N=f),re.attr("cursor",x[I]),ue(e));break;default:return}l(e)}}function Y(e){G(this,arguments).moved(e)}function F(e){G(this,arguments).ended(e)}function H(){var t=this.__brush||{selection:null};return t.extent=m(_.apply(this,arguments)),t.dim=e,t}return I.move=function(t,n,i){t.tween?t.on("start.brush",(function(e){G(this,arguments).beforestart().start(e)})).on("interrupt.brush end.brush",(function(e){G(this,arguments).end(e)})).tween("brush",(function(){var t=this,i=t.__brush,s=G(t,arguments),u=i.selection,o=e.input("function"==typeof n?n.apply(this,arguments):n,i.extent),a=r.interpolate(u,o);function l(e){i.selection=1===e&&null===o?null:a(e),O.call(t),s.brush()}return null!==u&&null!==o?l:l(1)})):t.each((function(){var t=this,r=arguments,u=t.__brush,o=e.input("function"==typeof n?n.apply(t,r):n,u.extent),a=G(t,r).beforestart();s.interrupt(t),u.selection=null===o?null:o,O.call(t),a.start(i).brush(i).end(i)}))},I.clear=function(e,t){I.move(e,null,t)},N.prototype={beforestart:function(){return 1==++this.active&&(this.state.emitter=this,this.starting=!0),this},start:function(e,t){return this.starting?(this.starting=!1,this.emit("start",e,t)):this.emit("brush",e),this},brush:function(e,t){return this.emit("brush",e,t),this},end:function(e,t){return 0==--this.active&&(delete this.state.emitter,this.emit("end",e,t)),this},emit:function(t,n,r){var s=i.select(this.that).datum();C.call(t,this.that,new o(t,{sourceEvent:n,target:I,selection:e.output(this.state.selection),mode:r,dispatch:C}),s)}},I.extent=function(e){return arguments.length?(_="function"==typeof e?e:u(m(e)),I):_},I.filter=function(e){return arguments.length?(M="function"==typeof e?e:u(!!e),I):M},I.touchable=function(e){return arguments.length?(S="function"==typeof e?e:u(!!e),I):S},I.handleSize=function(e){return arguments.length?(D=+e,I):D},I.keyModifiers=function(e){return arguments.length?(B=!!e,I):B},I.on=function(){var e=C.on.apply(C,arguments);return e===C?I:e},I}e.brush=function(){return M(_)},e.brushSelection=function(e){var t=e.__brush;return t?t.dim.output(t.selection):null},e.brushX=function(){return M(w)},e.brushY=function(){return M(g)},Object.defineProperty(e,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-brush/package.json b/frontend/node_modules/d3-brush/package.json new file mode 100644 index 0000000..f234774 --- /dev/null +++ b/frontend/node_modules/d3-brush/package.json @@ -0,0 +1,55 @@ +{ + "name": "d3-brush", + "version": "3.0.0", + "description": "Select a one- or two-dimensional region using the mouse or touch.", + "homepage": "https://d3js.org/d3-brush/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-brush.git" + }, + "keywords": [ + "d3", + "d3-module", + "brush", + "interaction" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "https://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-brush.min.js", + "unpkg": "dist/d3-brush.min.js", + "exports": { + "umd": "./dist/d3-brush.min.js", + "default": "./src/index.js" + }, + "dependencies": { + "d3-dispatch": "1 - 3", + "d3-drag": "2 - 3", + "d3-interpolate": "1 - 3", + "d3-selection": "3", + "d3-transition": "3" + }, + "devDependencies": { + "eslint": "7", + "mocha": "9", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c && git push", + "postpublish": "git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-brush/src/brush.js b/frontend/node_modules/d3-brush/src/brush.js new file mode 100644 index 0000000..eb5a687 --- /dev/null +++ b/frontend/node_modules/d3-brush/src/brush.js @@ -0,0 +1,621 @@ +import {dispatch} from "d3-dispatch"; +import {dragDisable, dragEnable} from "d3-drag"; +import {interpolate} from "d3-interpolate"; +import {pointer, select} from "d3-selection"; +import {interrupt} from "d3-transition"; +import constant from "./constant.js"; +import BrushEvent from "./event.js"; +import noevent, {nopropagation} from "./noevent.js"; + +var MODE_DRAG = {name: "drag"}, + MODE_SPACE = {name: "space"}, + MODE_HANDLE = {name: "handle"}, + MODE_CENTER = {name: "center"}; + +const {abs, max, min} = Math; + +function number1(e) { + return [+e[0], +e[1]]; +} + +function number2(e) { + return [number1(e[0]), number1(e[1])]; +} + +var X = { + name: "x", + handles: ["w", "e"].map(type), + input: function(x, e) { return x == null ? null : [[+x[0], e[0][1]], [+x[1], e[1][1]]]; }, + output: function(xy) { return xy && [xy[0][0], xy[1][0]]; } +}; + +var Y = { + name: "y", + handles: ["n", "s"].map(type), + input: function(y, e) { return y == null ? null : [[e[0][0], +y[0]], [e[1][0], +y[1]]]; }, + output: function(xy) { return xy && [xy[0][1], xy[1][1]]; } +}; + +var XY = { + name: "xy", + handles: ["n", "w", "e", "s", "nw", "ne", "sw", "se"].map(type), + input: function(xy) { return xy == null ? null : number2(xy); }, + output: function(xy) { return xy; } +}; + +var cursors = { + overlay: "crosshair", + selection: "move", + n: "ns-resize", + e: "ew-resize", + s: "ns-resize", + w: "ew-resize", + nw: "nwse-resize", + ne: "nesw-resize", + se: "nwse-resize", + sw: "nesw-resize" +}; + +var flipX = { + e: "w", + w: "e", + nw: "ne", + ne: "nw", + se: "sw", + sw: "se" +}; + +var flipY = { + n: "s", + s: "n", + nw: "sw", + ne: "se", + se: "ne", + sw: "nw" +}; + +var signsX = { + overlay: +1, + selection: +1, + n: null, + e: +1, + s: null, + w: -1, + nw: -1, + ne: +1, + se: +1, + sw: -1 +}; + +var signsY = { + overlay: +1, + selection: +1, + n: -1, + e: null, + s: +1, + w: null, + nw: -1, + ne: -1, + se: +1, + sw: +1 +}; + +function type(t) { + return {type: t}; +} + +// Ignore right-click, since that should open the context menu. +function defaultFilter(event) { + return !event.ctrlKey && !event.button; +} + +function defaultExtent() { + var svg = this.ownerSVGElement || this; + if (svg.hasAttribute("viewBox")) { + svg = svg.viewBox.baseVal; + return [[svg.x, svg.y], [svg.x + svg.width, svg.y + svg.height]]; + } + return [[0, 0], [svg.width.baseVal.value, svg.height.baseVal.value]]; +} + +function defaultTouchable() { + return navigator.maxTouchPoints || ("ontouchstart" in this); +} + +// Like d3.local, but with the name “__brush” rather than auto-generated. +function local(node) { + while (!node.__brush) if (!(node = node.parentNode)) return; + return node.__brush; +} + +function empty(extent) { + return extent[0][0] === extent[1][0] + || extent[0][1] === extent[1][1]; +} + +export function brushSelection(node) { + var state = node.__brush; + return state ? state.dim.output(state.selection) : null; +} + +export function brushX() { + return brush(X); +} + +export function brushY() { + return brush(Y); +} + +export default function() { + return brush(XY); +} + +function brush(dim) { + var extent = defaultExtent, + filter = defaultFilter, + touchable = defaultTouchable, + keys = true, + listeners = dispatch("start", "brush", "end"), + handleSize = 6, + touchending; + + function brush(group) { + var overlay = group + .property("__brush", initialize) + .selectAll(".overlay") + .data([type("overlay")]); + + overlay.enter().append("rect") + .attr("class", "overlay") + .attr("pointer-events", "all") + .attr("cursor", cursors.overlay) + .merge(overlay) + .each(function() { + var extent = local(this).extent; + select(this) + .attr("x", extent[0][0]) + .attr("y", extent[0][1]) + .attr("width", extent[1][0] - extent[0][0]) + .attr("height", extent[1][1] - extent[0][1]); + }); + + group.selectAll(".selection") + .data([type("selection")]) + .enter().append("rect") + .attr("class", "selection") + .attr("cursor", cursors.selection) + .attr("fill", "#777") + .attr("fill-opacity", 0.3) + .attr("stroke", "#fff") + .attr("shape-rendering", "crispEdges"); + + var handle = group.selectAll(".handle") + .data(dim.handles, function(d) { return d.type; }); + + handle.exit().remove(); + + handle.enter().append("rect") + .attr("class", function(d) { return "handle handle--" + d.type; }) + .attr("cursor", function(d) { return cursors[d.type]; }); + + group + .each(redraw) + .attr("fill", "none") + .attr("pointer-events", "all") + .on("mousedown.brush", started) + .filter(touchable) + .on("touchstart.brush", started) + .on("touchmove.brush", touchmoved) + .on("touchend.brush touchcancel.brush", touchended) + .style("touch-action", "none") + .style("-webkit-tap-highlight-color", "rgba(0,0,0,0)"); + } + + brush.move = function(group, selection, event) { + if (group.tween) { + group + .on("start.brush", function(event) { emitter(this, arguments).beforestart().start(event); }) + .on("interrupt.brush end.brush", function(event) { emitter(this, arguments).end(event); }) + .tween("brush", function() { + var that = this, + state = that.__brush, + emit = emitter(that, arguments), + selection0 = state.selection, + selection1 = dim.input(typeof selection === "function" ? selection.apply(this, arguments) : selection, state.extent), + i = interpolate(selection0, selection1); + + function tween(t) { + state.selection = t === 1 && selection1 === null ? null : i(t); + redraw.call(that); + emit.brush(); + } + + return selection0 !== null && selection1 !== null ? tween : tween(1); + }); + } else { + group + .each(function() { + var that = this, + args = arguments, + state = that.__brush, + selection1 = dim.input(typeof selection === "function" ? selection.apply(that, args) : selection, state.extent), + emit = emitter(that, args).beforestart(); + + interrupt(that); + state.selection = selection1 === null ? null : selection1; + redraw.call(that); + emit.start(event).brush(event).end(event); + }); + } + }; + + brush.clear = function(group, event) { + brush.move(group, null, event); + }; + + function redraw() { + var group = select(this), + selection = local(this).selection; + + if (selection) { + group.selectAll(".selection") + .style("display", null) + .attr("x", selection[0][0]) + .attr("y", selection[0][1]) + .attr("width", selection[1][0] - selection[0][0]) + .attr("height", selection[1][1] - selection[0][1]); + + group.selectAll(".handle") + .style("display", null) + .attr("x", function(d) { return d.type[d.type.length - 1] === "e" ? selection[1][0] - handleSize / 2 : selection[0][0] - handleSize / 2; }) + .attr("y", function(d) { return d.type[0] === "s" ? selection[1][1] - handleSize / 2 : selection[0][1] - handleSize / 2; }) + .attr("width", function(d) { return d.type === "n" || d.type === "s" ? selection[1][0] - selection[0][0] + handleSize : handleSize; }) + .attr("height", function(d) { return d.type === "e" || d.type === "w" ? selection[1][1] - selection[0][1] + handleSize : handleSize; }); + } + + else { + group.selectAll(".selection,.handle") + .style("display", "none") + .attr("x", null) + .attr("y", null) + .attr("width", null) + .attr("height", null); + } + } + + function emitter(that, args, clean) { + var emit = that.__brush.emitter; + return emit && (!clean || !emit.clean) ? emit : new Emitter(that, args, clean); + } + + function Emitter(that, args, clean) { + this.that = that; + this.args = args; + this.state = that.__brush; + this.active = 0; + this.clean = clean; + } + + Emitter.prototype = { + beforestart: function() { + if (++this.active === 1) this.state.emitter = this, this.starting = true; + return this; + }, + start: function(event, mode) { + if (this.starting) this.starting = false, this.emit("start", event, mode); + else this.emit("brush", event); + return this; + }, + brush: function(event, mode) { + this.emit("brush", event, mode); + return this; + }, + end: function(event, mode) { + if (--this.active === 0) delete this.state.emitter, this.emit("end", event, mode); + return this; + }, + emit: function(type, event, mode) { + var d = select(this.that).datum(); + listeners.call( + type, + this.that, + new BrushEvent(type, { + sourceEvent: event, + target: brush, + selection: dim.output(this.state.selection), + mode, + dispatch: listeners + }), + d + ); + } + }; + + function started(event) { + if (touchending && !event.touches) return; + if (!filter.apply(this, arguments)) return; + + var that = this, + type = event.target.__data__.type, + mode = (keys && event.metaKey ? type = "overlay" : type) === "selection" ? MODE_DRAG : (keys && event.altKey ? MODE_CENTER : MODE_HANDLE), + signX = dim === Y ? null : signsX[type], + signY = dim === X ? null : signsY[type], + state = local(that), + extent = state.extent, + selection = state.selection, + W = extent[0][0], w0, w1, + N = extent[0][1], n0, n1, + E = extent[1][0], e0, e1, + S = extent[1][1], s0, s1, + dx = 0, + dy = 0, + moving, + shifting = signX && signY && keys && event.shiftKey, + lockX, + lockY, + points = Array.from(event.touches || [event], t => { + const i = t.identifier; + t = pointer(t, that); + t.point0 = t.slice(); + t.identifier = i; + return t; + }); + + interrupt(that); + var emit = emitter(that, arguments, true).beforestart(); + + if (type === "overlay") { + if (selection) moving = true; + const pts = [points[0], points[1] || points[0]]; + state.selection = selection = [[ + w0 = dim === Y ? W : min(pts[0][0], pts[1][0]), + n0 = dim === X ? N : min(pts[0][1], pts[1][1]) + ], [ + e0 = dim === Y ? E : max(pts[0][0], pts[1][0]), + s0 = dim === X ? S : max(pts[0][1], pts[1][1]) + ]]; + if (points.length > 1) move(event); + } else { + w0 = selection[0][0]; + n0 = selection[0][1]; + e0 = selection[1][0]; + s0 = selection[1][1]; + } + + w1 = w0; + n1 = n0; + e1 = e0; + s1 = s0; + + var group = select(that) + .attr("pointer-events", "none"); + + var overlay = group.selectAll(".overlay") + .attr("cursor", cursors[type]); + + if (event.touches) { + emit.moved = moved; + emit.ended = ended; + } else { + var view = select(event.view) + .on("mousemove.brush", moved, true) + .on("mouseup.brush", ended, true); + if (keys) view + .on("keydown.brush", keydowned, true) + .on("keyup.brush", keyupped, true) + + dragDisable(event.view); + } + + redraw.call(that); + emit.start(event, mode.name); + + function moved(event) { + for (const p of event.changedTouches || [event]) { + for (const d of points) + if (d.identifier === p.identifier) d.cur = pointer(p, that); + } + if (shifting && !lockX && !lockY && points.length === 1) { + const point = points[0]; + if (abs(point.cur[0] - point[0]) > abs(point.cur[1] - point[1])) + lockY = true; + else + lockX = true; + } + for (const point of points) + if (point.cur) point[0] = point.cur[0], point[1] = point.cur[1]; + moving = true; + noevent(event); + move(event); + } + + function move(event) { + const point = points[0], point0 = point.point0; + var t; + + dx = point[0] - point0[0]; + dy = point[1] - point0[1]; + + switch (mode) { + case MODE_SPACE: + case MODE_DRAG: { + if (signX) dx = max(W - w0, min(E - e0, dx)), w1 = w0 + dx, e1 = e0 + dx; + if (signY) dy = max(N - n0, min(S - s0, dy)), n1 = n0 + dy, s1 = s0 + dy; + break; + } + case MODE_HANDLE: { + if (points[1]) { + if (signX) w1 = max(W, min(E, points[0][0])), e1 = max(W, min(E, points[1][0])), signX = 1; + if (signY) n1 = max(N, min(S, points[0][1])), s1 = max(N, min(S, points[1][1])), signY = 1; + } else { + if (signX < 0) dx = max(W - w0, min(E - w0, dx)), w1 = w0 + dx, e1 = e0; + else if (signX > 0) dx = max(W - e0, min(E - e0, dx)), w1 = w0, e1 = e0 + dx; + if (signY < 0) dy = max(N - n0, min(S - n0, dy)), n1 = n0 + dy, s1 = s0; + else if (signY > 0) dy = max(N - s0, min(S - s0, dy)), n1 = n0, s1 = s0 + dy; + } + break; + } + case MODE_CENTER: { + if (signX) w1 = max(W, min(E, w0 - dx * signX)), e1 = max(W, min(E, e0 + dx * signX)); + if (signY) n1 = max(N, min(S, n0 - dy * signY)), s1 = max(N, min(S, s0 + dy * signY)); + break; + } + } + + if (e1 < w1) { + signX *= -1; + t = w0, w0 = e0, e0 = t; + t = w1, w1 = e1, e1 = t; + if (type in flipX) overlay.attr("cursor", cursors[type = flipX[type]]); + } + + if (s1 < n1) { + signY *= -1; + t = n0, n0 = s0, s0 = t; + t = n1, n1 = s1, s1 = t; + if (type in flipY) overlay.attr("cursor", cursors[type = flipY[type]]); + } + + if (state.selection) selection = state.selection; // May be set by brush.move! + if (lockX) w1 = selection[0][0], e1 = selection[1][0]; + if (lockY) n1 = selection[0][1], s1 = selection[1][1]; + + if (selection[0][0] !== w1 + || selection[0][1] !== n1 + || selection[1][0] !== e1 + || selection[1][1] !== s1) { + state.selection = [[w1, n1], [e1, s1]]; + redraw.call(that); + emit.brush(event, mode.name); + } + } + + function ended(event) { + nopropagation(event); + if (event.touches) { + if (event.touches.length) return; + if (touchending) clearTimeout(touchending); + touchending = setTimeout(function() { touchending = null; }, 500); // Ghost clicks are delayed! + } else { + dragEnable(event.view, moving); + view.on("keydown.brush keyup.brush mousemove.brush mouseup.brush", null); + } + group.attr("pointer-events", "all"); + overlay.attr("cursor", cursors.overlay); + if (state.selection) selection = state.selection; // May be set by brush.move (on start)! + if (empty(selection)) state.selection = null, redraw.call(that); + emit.end(event, mode.name); + } + + function keydowned(event) { + switch (event.keyCode) { + case 16: { // SHIFT + shifting = signX && signY; + break; + } + case 18: { // ALT + if (mode === MODE_HANDLE) { + if (signX) e0 = e1 - dx * signX, w0 = w1 + dx * signX; + if (signY) s0 = s1 - dy * signY, n0 = n1 + dy * signY; + mode = MODE_CENTER; + move(event); + } + break; + } + case 32: { // SPACE; takes priority over ALT + if (mode === MODE_HANDLE || mode === MODE_CENTER) { + if (signX < 0) e0 = e1 - dx; else if (signX > 0) w0 = w1 - dx; + if (signY < 0) s0 = s1 - dy; else if (signY > 0) n0 = n1 - dy; + mode = MODE_SPACE; + overlay.attr("cursor", cursors.selection); + move(event); + } + break; + } + default: return; + } + noevent(event); + } + + function keyupped(event) { + switch (event.keyCode) { + case 16: { // SHIFT + if (shifting) { + lockX = lockY = shifting = false; + move(event); + } + break; + } + case 18: { // ALT + if (mode === MODE_CENTER) { + if (signX < 0) e0 = e1; else if (signX > 0) w0 = w1; + if (signY < 0) s0 = s1; else if (signY > 0) n0 = n1; + mode = MODE_HANDLE; + move(event); + } + break; + } + case 32: { // SPACE + if (mode === MODE_SPACE) { + if (event.altKey) { + if (signX) e0 = e1 - dx * signX, w0 = w1 + dx * signX; + if (signY) s0 = s1 - dy * signY, n0 = n1 + dy * signY; + mode = MODE_CENTER; + } else { + if (signX < 0) e0 = e1; else if (signX > 0) w0 = w1; + if (signY < 0) s0 = s1; else if (signY > 0) n0 = n1; + mode = MODE_HANDLE; + } + overlay.attr("cursor", cursors[type]); + move(event); + } + break; + } + default: return; + } + noevent(event); + } + } + + function touchmoved(event) { + emitter(this, arguments).moved(event); + } + + function touchended(event) { + emitter(this, arguments).ended(event); + } + + function initialize() { + var state = this.__brush || {selection: null}; + state.extent = number2(extent.apply(this, arguments)); + state.dim = dim; + return state; + } + + brush.extent = function(_) { + return arguments.length ? (extent = typeof _ === "function" ? _ : constant(number2(_)), brush) : extent; + }; + + brush.filter = function(_) { + return arguments.length ? (filter = typeof _ === "function" ? _ : constant(!!_), brush) : filter; + }; + + brush.touchable = function(_) { + return arguments.length ? (touchable = typeof _ === "function" ? _ : constant(!!_), brush) : touchable; + }; + + brush.handleSize = function(_) { + return arguments.length ? (handleSize = +_, brush) : handleSize; + }; + + brush.keyModifiers = function(_) { + return arguments.length ? (keys = !!_, brush) : keys; + }; + + brush.on = function() { + var value = listeners.on.apply(listeners, arguments); + return value === listeners ? brush : value; + }; + + return brush; +} diff --git a/frontend/node_modules/d3-brush/src/constant.js b/frontend/node_modules/d3-brush/src/constant.js new file mode 100644 index 0000000..3487c0d --- /dev/null +++ b/frontend/node_modules/d3-brush/src/constant.js @@ -0,0 +1 @@ +export default x => () => x; diff --git a/frontend/node_modules/d3-brush/src/event.js b/frontend/node_modules/d3-brush/src/event.js new file mode 100644 index 0000000..78deba1 --- /dev/null +++ b/frontend/node_modules/d3-brush/src/event.js @@ -0,0 +1,16 @@ +export default function BrushEvent(type, { + sourceEvent, + target, + selection, + mode, + dispatch +}) { + Object.defineProperties(this, { + type: {value: type, enumerable: true, configurable: true}, + sourceEvent: {value: sourceEvent, enumerable: true, configurable: true}, + target: {value: target, enumerable: true, configurable: true}, + selection: {value: selection, enumerable: true, configurable: true}, + mode: {value: mode, enumerable: true, configurable: true}, + _: {value: dispatch} + }); +} diff --git a/frontend/node_modules/d3-brush/src/index.js b/frontend/node_modules/d3-brush/src/index.js new file mode 100644 index 0000000..2c55476 --- /dev/null +++ b/frontend/node_modules/d3-brush/src/index.js @@ -0,0 +1,6 @@ +export { + default as brush, + brushX, + brushY, + brushSelection +} from "./brush.js"; diff --git a/frontend/node_modules/d3-brush/src/noevent.js b/frontend/node_modules/d3-brush/src/noevent.js new file mode 100644 index 0000000..b32552d --- /dev/null +++ b/frontend/node_modules/d3-brush/src/noevent.js @@ -0,0 +1,8 @@ +export function nopropagation(event) { + event.stopImmediatePropagation(); +} + +export default function(event) { + event.preventDefault(); + event.stopImmediatePropagation(); +} diff --git a/frontend/node_modules/d3-chord/LICENSE b/frontend/node_modules/d3-chord/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-chord/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-chord/README.md b/frontend/node_modules/d3-chord/README.md new file mode 100644 index 0000000..5344a53 --- /dev/null +++ b/frontend/node_modules/d3-chord/README.md @@ -0,0 +1,234 @@ +# d3-chord + +Visualize relationships or network flow with an aesthetically-pleasing circular layout. + +[Chord Diagram](https://observablehq.com/@d3/chord-diagram) + +## Installing + +If you use npm, `npm install d3-chord`. You can also download the [latest release on GitHub](https://github.com/d3/d3-chord/releases/latest). For vanilla HTML in modern browsers, import d3-chord from Skypack: + +```html + +``` + +For legacy environments, you can load d3-chord’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + + +``` + +## API Reference + +# d3.chord() · [Source](https://github.com/d3/d3-chord/blob/master/src/chord.js) + +Constructs a new chord layout with the default settings. + +# chord(matrix) · [Source](https://github.com/d3/d3-chord/blob/master/src/chord.js) + +Computes the chord layout for the specified square *matrix* of size *n*×*n*, where the *matrix* represents the directed flow amongst a network (a complete digraph) of *n* nodes. The given *matrix* must be an array of length *n*, where each element *matrix*[*i*] is an array of *n* numbers, where each *matrix*[*i*][*j*] represents the flow from the *i*th node in the network to the *j*th node. Each number *matrix*[*i*][*j*] must be nonnegative, though it can be zero if there is no flow from node *i* to node *j*. From the [Circos tableviewer example](http://mkweb.bcgsc.ca/circos/guide/tables/): + +```js +const matrix = [ + [11975, 5871, 8916, 2868], + [ 1951, 10048, 2060, 6171], + [ 8010, 16145, 8090, 8045], + [ 1013, 990, 940, 6907] +]; +``` + +The return value of *chord*(*matrix*) is an array of *chords*, where each chord represents the combined bidirectional flow between two nodes *i* and *j* (where *i* may be equal to *j*) and is an object with the following properties: + +* `source` - the source subgroup +* `target` - the target subgroup + +Each source and target subgroup is also an object with the following properties: + +* `startAngle` - the start angle in radians +* `endAngle` - the end angle in radians +* `value` - the flow value *matrix*[*i*][*j*] +* `index` - the node index *i* + +The chords are typically passed to [d3.ribbon](#ribbon) to display the network relationships. The returned array includes only chord objects for which the value *matrix*[*i*][*j*] or *matrix*[*j*][*i*] is non-zero. Furthermore, the returned array only contains unique chords: a given chord *ij* represents the bidirectional flow from *i* to *j* *and* from *j* to *i*, and does not contain a duplicate chord *ji*; *i* and *j* are chosen such that the chord’s source always represents the larger of *matrix*[*i*][*j*] and *matrix*[*j*][*i*]. + +The *chords* array also defines a secondary array of length *n*, *chords*.groups, where each group represents the combined outflow for node *i*, corresponding to the elements *matrix*[*i*][0 … *n* - 1], and is an object with the following properties: + +* `startAngle` - the start angle in radians +* `endAngle` - the end angle in radians +* `value` - the total outgoing flow value for node *i* +* `index` - the node index *i* + +The groups are typically passed to [d3.arc](https://github.com/d3/d3-shape#arc) to produce a donut chart around the circumference of the chord layout. + +# chord.padAngle([angle]) · [Source](https://github.com/d3/d3-chord/blob/master/src/chord.js) + +If *angle* is specified, sets the pad angle between adjacent groups to the specified number in radians and returns this chord layout. If *angle* is not specified, returns the current pad angle, which defaults to zero. + +# chord.sortGroups([compare]) · [Source](https://github.com/d3/d3-chord/blob/master/src/chord.js) + +If *compare* is specified, sets the group comparator to the specified function or null and returns this chord layout. If *compare* is not specified, returns the current group comparator, which defaults to null. If the group comparator is non-null, it is used to sort the groups by their total outflow. See also [d3.ascending](https://github.com/d3/d3-array/blob/master/README.md#ascending) and [d3.descending](https://github.com/d3/d3-array/blob/master/README.md#descending). + +# chord.sortSubgroups([compare]) · [Source](https://github.com/d3/d3-chord/blob/master/src/chord.js) + +If *compare* is specified, sets the subgroup comparator to the specified function or null and returns this chord layout. If *compare* is not specified, returns the current subgroup comparator, which defaults to null. If the subgroup comparator is non-null, it is used to sort the subgroups corresponding to *matrix*[*i*][0 … *n* - 1] for a given group *i* by their total outflow. See also [d3.ascending](https://github.com/d3/d3-array/blob/master/README.md#ascending) and [d3.descending](https://github.com/d3/d3-array/blob/master/README.md#descending). + +# chord.sortChords([compare]) · [Source](https://github.com/d3/d3-chord/blob/master/src/chord.js) + +If *compare* is specified, sets the chord comparator to the specified function or null and returns this chord layout. If *compare* is not specified, returns the current chord comparator, which defaults to null. If the chord comparator is non-null, it is used to sort the [chords](#_chord) by their combined flow; this only affects the *z*-order of the chords. See also [d3.ascending](https://github.com/d3/d3-array/blob/master/README.md#ascending) and [d3.descending](https://github.com/d3/d3-array/blob/master/README.md#descending). + +# d3.chordDirected() · [Source](https://github.com/d3/d3-chord/blob/master/src/chord.js), [Examples](https://observablehq.com/@d3/directed-chord-diagram) + +A chord layout for directional flows. The chord from *i* to *j* is generated from the value in *matrix*[*i*][*j*] only. + +# d3.chordTranspose() · [Source](https://github.com/d3/d3-chord/blob/master/src/chord.js) + +A transposed chord layout. Useful to highlight outgoing (rather than incoming) flows. + +# d3.ribbon() · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +Creates a new ribbon generator with the default settings. + +# ribbon(arguments…) · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +Generates a ribbon for the given *arguments*. The *arguments* are arbitrary; they are simply propagated to the ribbon generator’s accessor functions along with the `this` object. For example, with the default settings, a [chord object](#_chord) expected: + +```js +const ribbon = d3.ribbon(); + +ribbon({ + source: {startAngle: 0.7524114, endAngle: 1.1212972, radius: 240}, + target: {startAngle: 1.8617078, endAngle: 1.9842927, radius: 240} +}); // "M164.0162810494058,-175.21032946354026A240,240,0,0,1,216.1595644740915,-104.28347273835429Q0,0,229.9158815306728,68.8381247563705A240,240,0,0,1,219.77316791012538,96.43523560788266Q0,0,164.0162810494058,-175.21032946354026Z" +``` + +Or equivalently if the radius is instead defined as a constant: + +```js +const ribbon = d3.ribbon() + .radius(240); + +ribbon({ + source: {startAngle: 0.7524114, endAngle: 1.1212972}, + target: {startAngle: 1.8617078, endAngle: 1.9842927} +}); // "M164.0162810494058,-175.21032946354026A240,240,0,0,1,216.1595644740915,-104.28347273835429Q0,0,229.9158815306728,68.8381247563705A240,240,0,0,1,219.77316791012538,96.43523560788266Q0,0,164.0162810494058,-175.21032946354026Z" +``` + +If the ribbon generator has a context, then the ribbon is rendered to this context as a sequence of path method calls and this function returns void. Otherwise, a path data string is returned. + +# ribbon.source([source]) · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +If *source* is specified, sets the source accessor to the specified function and returns this ribbon generator. If *source* is not specified, returns the current source accessor, which defaults to: + +```js +function source(d) { + return d.source; +} +``` + +# ribbon.target([target]) · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +If *target* is specified, sets the target accessor to the specified function and returns this ribbon generator. If *target* is not specified, returns the current target accessor, which defaults to: + +```js +function target(d) { + return d.target; +} +``` + +# ribbon.radius([radius]) · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +If *radius* is specified, sets the source and target radius accessor to the specified function and returns this ribbon generator. If *radius* is not specified, returns the current source radius accessor, which defaults to: + +```js +function radius(d) { + return d.radius; +} +``` + +# ribbon.sourceRadius([radius]) · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +If *radius* is specified, sets the source radius accessor to the specified function and returns this ribbon generator. If *radius* is not specified, returns the current source radius accessor, which defaults to: + +```js +function radius(d) { + return d.radius; +} +``` + +# ribbon.targetRadius([radius]) · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +If *radius* is specified, sets the target radius accessor to the specified function and returns this ribbon generator. If *radius* is not specified, returns the current target radius accessor, which defaults to: + +```js +function radius(d) { + return d.radius; +} +``` + +By convention, the target radius in asymmetric chord diagrams is typically inset from the source radius, resulting in a gap between the end of the directed link and its associated group arc. + +# ribbon.startAngle([angle]) · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +If *angle* is specified, sets the start angle accessor to the specified function and returns this ribbon generator. If *angle* is not specified, returns the current start angle accessor, which defaults to: + +```js +function startAngle(d) { + return d.startAngle; +} +``` + +The *angle* is specified in radians, with 0 at -*y* (12 o’clock) and positive angles proceeding clockwise. + +# ribbon.endAngle([angle]) · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +If *angle* is specified, sets the end angle accessor to the specified function and returns this ribbon generator. If *angle* is not specified, returns the current end angle accessor, which defaults to: + +```js +function endAngle(d) { + return d.endAngle; +} +``` + +The *angle* is specified in radians, with 0 at -*y* (12 o’clock) and positive angles proceeding clockwise. + +# ribbon.padAngle([angle]) · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +If *angle* is specified, sets the pad angle accessor to the specified function and returns this ribbon generator. If *angle* is not specified, returns the current pad angle accessor, which defaults to: + +```js +function padAngle() { + return 0; +} +``` + +The pad angle specifies the angular gap between adjacent ribbons. + +# ribbon.context([context]) · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +If *context* is specified, sets the context and returns this ribbon generator. If *context* is not specified, returns the current context, which defaults to null. If the context is not null, then the [generated ribbon](#_ribbon) is rendered to this context as a sequence of [path method](http://www.w3.org/TR/2dcontext/#canvaspathmethods) calls. Otherwise, a [path data](http://www.w3.org/TR/SVG/paths.html#PathData) string representing the generated ribbon is returned. See also [d3-path](https://github.com/d3/d3-path). + +# d3.ribbonArrow() · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +Creates a new arrow ribbon generator with the default settings. + +# ribbonArrow.headRadius([radius]) · [Source](https://github.com/d3/d3-chord/blob/master/src/ribbon.js) + +If *radius* is specified, sets the arrowhead radius accessor to the specified function and returns this ribbon generator. If *radius* is not specified, returns the current arrowhead radius accessor, which defaults to: + +```js +function headRadius() { + return 10; +} +``` diff --git a/frontend/node_modules/d3-chord/dist/d3-chord.js b/frontend/node_modules/d3-chord/dist/d3-chord.js new file mode 100644 index 0000000..39bc819 --- /dev/null +++ b/frontend/node_modules/d3-chord/dist/d3-chord.js @@ -0,0 +1,284 @@ +// https://d3js.org/d3-chord/ v3.0.1 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-path')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-path'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3)); +}(this, (function (exports, d3Path) { 'use strict'; + +var abs = Math.abs; +var cos = Math.cos; +var sin = Math.sin; +var pi = Math.PI; +var halfPi = pi / 2; +var tau = pi * 2; +var max = Math.max; +var epsilon = 1e-12; + +function range(i, j) { + return Array.from({length: j - i}, (_, k) => i + k); +} + +function compareValue(compare) { + return function(a, b) { + return compare( + a.source.value + a.target.value, + b.source.value + b.target.value + ); + }; +} + +function chord() { + return chord$1(false, false); +} + +function chordTranspose() { + return chord$1(false, true); +} + +function chordDirected() { + return chord$1(true, false); +} + +function chord$1(directed, transpose) { + var padAngle = 0, + sortGroups = null, + sortSubgroups = null, + sortChords = null; + + function chord(matrix) { + var n = matrix.length, + groupSums = new Array(n), + groupIndex = range(0, n), + chords = new Array(n * n), + groups = new Array(n), + k = 0, dx; + + matrix = Float64Array.from({length: n * n}, transpose + ? (_, i) => matrix[i % n][i / n | 0] + : (_, i) => matrix[i / n | 0][i % n]); + + // Compute the scaling factor from value to angle in [0, 2pi]. + for (let i = 0; i < n; ++i) { + let x = 0; + for (let j = 0; j < n; ++j) x += matrix[i * n + j] + directed * matrix[j * n + i]; + k += groupSums[i] = x; + } + k = max(0, tau - padAngle * n) / k; + dx = k ? padAngle : tau / n; + + // Compute the angles for each group and constituent chord. + { + let x = 0; + if (sortGroups) groupIndex.sort((a, b) => sortGroups(groupSums[a], groupSums[b])); + for (const i of groupIndex) { + const x0 = x; + if (directed) { + const subgroupIndex = range(~n + 1, n).filter(j => j < 0 ? matrix[~j * n + i] : matrix[i * n + j]); + if (sortSubgroups) subgroupIndex.sort((a, b) => sortSubgroups(a < 0 ? -matrix[~a * n + i] : matrix[i * n + a], b < 0 ? -matrix[~b * n + i] : matrix[i * n + b])); + for (const j of subgroupIndex) { + if (j < 0) { + const chord = chords[~j * n + i] || (chords[~j * n + i] = {source: null, target: null}); + chord.target = {index: i, startAngle: x, endAngle: x += matrix[~j * n + i] * k, value: matrix[~j * n + i]}; + } else { + const chord = chords[i * n + j] || (chords[i * n + j] = {source: null, target: null}); + chord.source = {index: i, startAngle: x, endAngle: x += matrix[i * n + j] * k, value: matrix[i * n + j]}; + } + } + groups[i] = {index: i, startAngle: x0, endAngle: x, value: groupSums[i]}; + } else { + const subgroupIndex = range(0, n).filter(j => matrix[i * n + j] || matrix[j * n + i]); + if (sortSubgroups) subgroupIndex.sort((a, b) => sortSubgroups(matrix[i * n + a], matrix[i * n + b])); + for (const j of subgroupIndex) { + let chord; + if (i < j) { + chord = chords[i * n + j] || (chords[i * n + j] = {source: null, target: null}); + chord.source = {index: i, startAngle: x, endAngle: x += matrix[i * n + j] * k, value: matrix[i * n + j]}; + } else { + chord = chords[j * n + i] || (chords[j * n + i] = {source: null, target: null}); + chord.target = {index: i, startAngle: x, endAngle: x += matrix[i * n + j] * k, value: matrix[i * n + j]}; + if (i === j) chord.source = chord.target; + } + if (chord.source && chord.target && chord.source.value < chord.target.value) { + const source = chord.source; + chord.source = chord.target; + chord.target = source; + } + } + groups[i] = {index: i, startAngle: x0, endAngle: x, value: groupSums[i]}; + } + x += dx; + } + } + + // Remove empty chords. + chords = Object.values(chords); + chords.groups = groups; + return sortChords ? chords.sort(sortChords) : chords; + } + + chord.padAngle = function(_) { + return arguments.length ? (padAngle = max(0, _), chord) : padAngle; + }; + + chord.sortGroups = function(_) { + return arguments.length ? (sortGroups = _, chord) : sortGroups; + }; + + chord.sortSubgroups = function(_) { + return arguments.length ? (sortSubgroups = _, chord) : sortSubgroups; + }; + + chord.sortChords = function(_) { + return arguments.length ? (_ == null ? sortChords = null : (sortChords = compareValue(_))._ = _, chord) : sortChords && sortChords._; + }; + + return chord; +} + +var slice = Array.prototype.slice; + +function constant(x) { + return function() { + return x; + }; +} + +function defaultSource(d) { + return d.source; +} + +function defaultTarget(d) { + return d.target; +} + +function defaultRadius(d) { + return d.radius; +} + +function defaultStartAngle(d) { + return d.startAngle; +} + +function defaultEndAngle(d) { + return d.endAngle; +} + +function defaultPadAngle() { + return 0; +} + +function defaultArrowheadRadius() { + return 10; +} + +function ribbon(headRadius) { + var source = defaultSource, + target = defaultTarget, + sourceRadius = defaultRadius, + targetRadius = defaultRadius, + startAngle = defaultStartAngle, + endAngle = defaultEndAngle, + padAngle = defaultPadAngle, + context = null; + + function ribbon() { + var buffer, + s = source.apply(this, arguments), + t = target.apply(this, arguments), + ap = padAngle.apply(this, arguments) / 2, + argv = slice.call(arguments), + sr = +sourceRadius.apply(this, (argv[0] = s, argv)), + sa0 = startAngle.apply(this, argv) - halfPi, + sa1 = endAngle.apply(this, argv) - halfPi, + tr = +targetRadius.apply(this, (argv[0] = t, argv)), + ta0 = startAngle.apply(this, argv) - halfPi, + ta1 = endAngle.apply(this, argv) - halfPi; + + if (!context) context = buffer = d3Path.path(); + + if (ap > epsilon) { + if (abs(sa1 - sa0) > ap * 2 + epsilon) sa1 > sa0 ? (sa0 += ap, sa1 -= ap) : (sa0 -= ap, sa1 += ap); + else sa0 = sa1 = (sa0 + sa1) / 2; + if (abs(ta1 - ta0) > ap * 2 + epsilon) ta1 > ta0 ? (ta0 += ap, ta1 -= ap) : (ta0 -= ap, ta1 += ap); + else ta0 = ta1 = (ta0 + ta1) / 2; + } + + context.moveTo(sr * cos(sa0), sr * sin(sa0)); + context.arc(0, 0, sr, sa0, sa1); + if (sa0 !== ta0 || sa1 !== ta1) { + if (headRadius) { + var hr = +headRadius.apply(this, arguments), tr2 = tr - hr, ta2 = (ta0 + ta1) / 2; + context.quadraticCurveTo(0, 0, tr2 * cos(ta0), tr2 * sin(ta0)); + context.lineTo(tr * cos(ta2), tr * sin(ta2)); + context.lineTo(tr2 * cos(ta1), tr2 * sin(ta1)); + } else { + context.quadraticCurveTo(0, 0, tr * cos(ta0), tr * sin(ta0)); + context.arc(0, 0, tr, ta0, ta1); + } + } + context.quadraticCurveTo(0, 0, sr * cos(sa0), sr * sin(sa0)); + context.closePath(); + + if (buffer) return context = null, buffer + "" || null; + } + + if (headRadius) ribbon.headRadius = function(_) { + return arguments.length ? (headRadius = typeof _ === "function" ? _ : constant(+_), ribbon) : headRadius; + }; + + ribbon.radius = function(_) { + return arguments.length ? (sourceRadius = targetRadius = typeof _ === "function" ? _ : constant(+_), ribbon) : sourceRadius; + }; + + ribbon.sourceRadius = function(_) { + return arguments.length ? (sourceRadius = typeof _ === "function" ? _ : constant(+_), ribbon) : sourceRadius; + }; + + ribbon.targetRadius = function(_) { + return arguments.length ? (targetRadius = typeof _ === "function" ? _ : constant(+_), ribbon) : targetRadius; + }; + + ribbon.startAngle = function(_) { + return arguments.length ? (startAngle = typeof _ === "function" ? _ : constant(+_), ribbon) : startAngle; + }; + + ribbon.endAngle = function(_) { + return arguments.length ? (endAngle = typeof _ === "function" ? _ : constant(+_), ribbon) : endAngle; + }; + + ribbon.padAngle = function(_) { + return arguments.length ? (padAngle = typeof _ === "function" ? _ : constant(+_), ribbon) : padAngle; + }; + + ribbon.source = function(_) { + return arguments.length ? (source = _, ribbon) : source; + }; + + ribbon.target = function(_) { + return arguments.length ? (target = _, ribbon) : target; + }; + + ribbon.context = function(_) { + return arguments.length ? ((context = _ == null ? null : _), ribbon) : context; + }; + + return ribbon; +} + +function ribbon$1() { + return ribbon(); +} + +function ribbonArrow() { + return ribbon(defaultArrowheadRadius); +} + +exports.chord = chord; +exports.chordDirected = chordDirected; +exports.chordTranspose = chordTranspose; +exports.ribbon = ribbon$1; +exports.ribbonArrow = ribbonArrow; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-chord/dist/d3-chord.min.js b/frontend/node_modules/d3-chord/dist/d3-chord.min.js new file mode 100644 index 0000000..d686adc --- /dev/null +++ b/frontend/node_modules/d3-chord/dist/d3-chord.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-chord/ v3.0.1 Copyright 2010-2021 Mike Bostock +!function(n,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports,require("d3-path")):"function"==typeof define&&define.amd?define(["exports","d3-path"],t):t((n="undefined"!=typeof globalThis?globalThis:n||self).d3=n.d3||{},n.d3)}(this,(function(n,t){"use strict";var e=Math.abs,r=Math.cos,u=Math.sin,o=Math.PI,l=o/2,i=2*o,a=Math.max,c=1e-12;function f(n,t){return Array.from({length:t-n},((t,e)=>n+e))}function s(n){return function(t,e){return n(t.source.value+t.target.value,e.source.value+e.target.value)}}function g(n,t){var e=0,r=null,u=null,o=null;function l(l){var c,s=l.length,g=new Array(s),d=f(0,s),p=new Array(s*s),h=new Array(s),y=0;l=Float64Array.from({length:s*s},t?(n,t)=>l[t%s][t/s|0]:(n,t)=>l[t/s|0][t%s]);for(let t=0;tr(g[n],g[t])));for(const e of d){const r=t;if(n){const n=f(1+~s,s).filter((n=>n<0?l[~n*s+e]:l[e*s+n]));u&&n.sort(((n,t)=>u(n<0?-l[~n*s+e]:l[e*s+n],t<0?-l[~t*s+e]:l[e*s+t])));for(const r of n)if(r<0){(p[~r*s+e]||(p[~r*s+e]={source:null,target:null})).target={index:e,startAngle:t,endAngle:t+=l[~r*s+e]*y,value:l[~r*s+e]}}else{(p[e*s+r]||(p[e*s+r]={source:null,target:null})).source={index:e,startAngle:t,endAngle:t+=l[e*s+r]*y,value:l[e*s+r]}}h[e]={index:e,startAngle:r,endAngle:t,value:g[e]}}else{const n=f(0,s).filter((n=>l[e*s+n]||l[n*s+e]));u&&n.sort(((n,t)=>u(l[e*s+n],l[e*s+t])));for(const r of n){let n;if(ec&&(e(M-x)>2*v+c?M>x?(x+=v,M-=v):(x-=v,M+=v):x=M=(x+M)/2,e(C-w)>2*v+c?C>w?(w+=v,C-=v):(w-=v,C+=v):w=C=(w+C)/2),m.moveTo(b*r(x),b*u(x)),m.arc(0,0,b,x,M),x!==w||M!==C)if(n){var _=+n.apply(this,arguments),j=q-_,P=(w+C)/2;m.quadraticCurveTo(0,0,j*r(w),j*u(w)),m.lineTo(q*r(P),q*u(P)),m.lineTo(j*r(C),j*u(C))}else m.quadraticCurveTo(0,0,q*r(w),q*u(w)),m.arc(0,0,q,w,C);if(m.quadraticCurveTo(0,0,b*r(x),b*u(x)),m.closePath(),p)return m=null,p+""||null}return n&&(M.headRadius=function(t){return arguments.length?(n="function"==typeof t?t:p(+t),M):n}),M.radius=function(n){return arguments.length?(a=f="function"==typeof n?n:p(+n),M):a},M.sourceRadius=function(n){return arguments.length?(a="function"==typeof n?n:p(+n),M):a},M.targetRadius=function(n){return arguments.length?(f="function"==typeof n?n:p(+n),M):f},M.startAngle=function(n){return arguments.length?(s="function"==typeof n?n:p(+n),M):s},M.endAngle=function(n){return arguments.length?(g="function"==typeof n?n:p(+n),M):g},M.padAngle=function(n){return arguments.length?(T="function"==typeof n?n:p(+n),M):T},M.source=function(n){return arguments.length?(o=n,M):o},M.target=function(n){return arguments.length?(i=n,M):i},M.context=function(n){return arguments.length?(m=null==n?null:n,M):m},M}n.chord=function(){return g(!1,!1)},n.chordDirected=function(){return g(!0,!1)},n.chordTranspose=function(){return g(!1,!0)},n.ribbon=function(){return m()},n.ribbonArrow=function(){return m(T)},Object.defineProperty(n,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-chord/package.json b/frontend/node_modules/d3-chord/package.json new file mode 100644 index 0000000..a391a6c --- /dev/null +++ b/frontend/node_modules/d3-chord/package.json @@ -0,0 +1,54 @@ +{ + "name": "d3-chord", + "version": "3.0.1", + "description": "Visualize relationships or network flow with an aesthetically-pleasing circular layout.", + "homepage": "https://d3js.org/d3-chord/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-chord.git" + }, + "keywords": [ + "d3", + "d3-module", + "chord", + "radial", + "network", + "flow" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "http://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-chord.min.js", + "unpkg": "dist/d3-chord.min.js", + "exports": { + "umd": "./dist/d3-chord.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "dependencies": { + "d3-path": "1 - 3" + }, + "devDependencies": { + "eslint": "7", + "mocha": "8", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-chord/src/array.js b/frontend/node_modules/d3-chord/src/array.js new file mode 100644 index 0000000..8eeac16 --- /dev/null +++ b/frontend/node_modules/d3-chord/src/array.js @@ -0,0 +1 @@ +export var slice = Array.prototype.slice; diff --git a/frontend/node_modules/d3-chord/src/chord.js b/frontend/node_modules/d3-chord/src/chord.js new file mode 100644 index 0000000..f9f1a98 --- /dev/null +++ b/frontend/node_modules/d3-chord/src/chord.js @@ -0,0 +1,122 @@ +import {max, tau} from "./math.js"; + +function range(i, j) { + return Array.from({length: j - i}, (_, k) => i + k); +} + +function compareValue(compare) { + return function(a, b) { + return compare( + a.source.value + a.target.value, + b.source.value + b.target.value + ); + }; +} + +export default function() { + return chord(false, false); +} + +export function chordTranspose() { + return chord(false, true); +} + +export function chordDirected() { + return chord(true, false); +} + +function chord(directed, transpose) { + var padAngle = 0, + sortGroups = null, + sortSubgroups = null, + sortChords = null; + + function chord(matrix) { + var n = matrix.length, + groupSums = new Array(n), + groupIndex = range(0, n), + chords = new Array(n * n), + groups = new Array(n), + k = 0, dx; + + matrix = Float64Array.from({length: n * n}, transpose + ? (_, i) => matrix[i % n][i / n | 0] + : (_, i) => matrix[i / n | 0][i % n]); + + // Compute the scaling factor from value to angle in [0, 2pi]. + for (let i = 0; i < n; ++i) { + let x = 0; + for (let j = 0; j < n; ++j) x += matrix[i * n + j] + directed * matrix[j * n + i]; + k += groupSums[i] = x; + } + k = max(0, tau - padAngle * n) / k; + dx = k ? padAngle : tau / n; + + // Compute the angles for each group and constituent chord. + { + let x = 0; + if (sortGroups) groupIndex.sort((a, b) => sortGroups(groupSums[a], groupSums[b])); + for (const i of groupIndex) { + const x0 = x; + if (directed) { + const subgroupIndex = range(~n + 1, n).filter(j => j < 0 ? matrix[~j * n + i] : matrix[i * n + j]); + if (sortSubgroups) subgroupIndex.sort((a, b) => sortSubgroups(a < 0 ? -matrix[~a * n + i] : matrix[i * n + a], b < 0 ? -matrix[~b * n + i] : matrix[i * n + b])); + for (const j of subgroupIndex) { + if (j < 0) { + const chord = chords[~j * n + i] || (chords[~j * n + i] = {source: null, target: null}); + chord.target = {index: i, startAngle: x, endAngle: x += matrix[~j * n + i] * k, value: matrix[~j * n + i]}; + } else { + const chord = chords[i * n + j] || (chords[i * n + j] = {source: null, target: null}); + chord.source = {index: i, startAngle: x, endAngle: x += matrix[i * n + j] * k, value: matrix[i * n + j]}; + } + } + groups[i] = {index: i, startAngle: x0, endAngle: x, value: groupSums[i]}; + } else { + const subgroupIndex = range(0, n).filter(j => matrix[i * n + j] || matrix[j * n + i]); + if (sortSubgroups) subgroupIndex.sort((a, b) => sortSubgroups(matrix[i * n + a], matrix[i * n + b])); + for (const j of subgroupIndex) { + let chord; + if (i < j) { + chord = chords[i * n + j] || (chords[i * n + j] = {source: null, target: null}); + chord.source = {index: i, startAngle: x, endAngle: x += matrix[i * n + j] * k, value: matrix[i * n + j]}; + } else { + chord = chords[j * n + i] || (chords[j * n + i] = {source: null, target: null}); + chord.target = {index: i, startAngle: x, endAngle: x += matrix[i * n + j] * k, value: matrix[i * n + j]}; + if (i === j) chord.source = chord.target; + } + if (chord.source && chord.target && chord.source.value < chord.target.value) { + const source = chord.source; + chord.source = chord.target; + chord.target = source; + } + } + groups[i] = {index: i, startAngle: x0, endAngle: x, value: groupSums[i]}; + } + x += dx; + } + } + + // Remove empty chords. + chords = Object.values(chords); + chords.groups = groups; + return sortChords ? chords.sort(sortChords) : chords; + } + + chord.padAngle = function(_) { + return arguments.length ? (padAngle = max(0, _), chord) : padAngle; + }; + + chord.sortGroups = function(_) { + return arguments.length ? (sortGroups = _, chord) : sortGroups; + }; + + chord.sortSubgroups = function(_) { + return arguments.length ? (sortSubgroups = _, chord) : sortSubgroups; + }; + + chord.sortChords = function(_) { + return arguments.length ? (_ == null ? sortChords = null : (sortChords = compareValue(_))._ = _, chord) : sortChords && sortChords._; + }; + + return chord; +} diff --git a/frontend/node_modules/d3-chord/src/constant.js b/frontend/node_modules/d3-chord/src/constant.js new file mode 100644 index 0000000..b7d42e7 --- /dev/null +++ b/frontend/node_modules/d3-chord/src/constant.js @@ -0,0 +1,5 @@ +export default function(x) { + return function() { + return x; + }; +} diff --git a/frontend/node_modules/d3-chord/src/index.js b/frontend/node_modules/d3-chord/src/index.js new file mode 100644 index 0000000..adec603 --- /dev/null +++ b/frontend/node_modules/d3-chord/src/index.js @@ -0,0 +1,2 @@ +export {default as chord, chordTranspose, chordDirected} from "./chord.js"; +export {default as ribbon, ribbonArrow} from "./ribbon.js"; diff --git a/frontend/node_modules/d3-chord/src/math.js b/frontend/node_modules/d3-chord/src/math.js new file mode 100644 index 0000000..9ad579e --- /dev/null +++ b/frontend/node_modules/d3-chord/src/math.js @@ -0,0 +1,8 @@ +export var abs = Math.abs; +export var cos = Math.cos; +export var sin = Math.sin; +export var pi = Math.PI; +export var halfPi = pi / 2; +export var tau = pi * 2; +export var max = Math.max; +export var epsilon = 1e-12; diff --git a/frontend/node_modules/d3-chord/src/ribbon.js b/frontend/node_modules/d3-chord/src/ribbon.js new file mode 100644 index 0000000..bcd75b8 --- /dev/null +++ b/frontend/node_modules/d3-chord/src/ribbon.js @@ -0,0 +1,134 @@ +import {path} from "d3-path"; +import {slice} from "./array.js"; +import constant from "./constant.js"; +import {abs, cos, epsilon, halfPi, sin} from "./math.js"; + +function defaultSource(d) { + return d.source; +} + +function defaultTarget(d) { + return d.target; +} + +function defaultRadius(d) { + return d.radius; +} + +function defaultStartAngle(d) { + return d.startAngle; +} + +function defaultEndAngle(d) { + return d.endAngle; +} + +function defaultPadAngle() { + return 0; +} + +function defaultArrowheadRadius() { + return 10; +} + +function ribbon(headRadius) { + var source = defaultSource, + target = defaultTarget, + sourceRadius = defaultRadius, + targetRadius = defaultRadius, + startAngle = defaultStartAngle, + endAngle = defaultEndAngle, + padAngle = defaultPadAngle, + context = null; + + function ribbon() { + var buffer, + s = source.apply(this, arguments), + t = target.apply(this, arguments), + ap = padAngle.apply(this, arguments) / 2, + argv = slice.call(arguments), + sr = +sourceRadius.apply(this, (argv[0] = s, argv)), + sa0 = startAngle.apply(this, argv) - halfPi, + sa1 = endAngle.apply(this, argv) - halfPi, + tr = +targetRadius.apply(this, (argv[0] = t, argv)), + ta0 = startAngle.apply(this, argv) - halfPi, + ta1 = endAngle.apply(this, argv) - halfPi; + + if (!context) context = buffer = path(); + + if (ap > epsilon) { + if (abs(sa1 - sa0) > ap * 2 + epsilon) sa1 > sa0 ? (sa0 += ap, sa1 -= ap) : (sa0 -= ap, sa1 += ap); + else sa0 = sa1 = (sa0 + sa1) / 2; + if (abs(ta1 - ta0) > ap * 2 + epsilon) ta1 > ta0 ? (ta0 += ap, ta1 -= ap) : (ta0 -= ap, ta1 += ap); + else ta0 = ta1 = (ta0 + ta1) / 2; + } + + context.moveTo(sr * cos(sa0), sr * sin(sa0)); + context.arc(0, 0, sr, sa0, sa1); + if (sa0 !== ta0 || sa1 !== ta1) { + if (headRadius) { + var hr = +headRadius.apply(this, arguments), tr2 = tr - hr, ta2 = (ta0 + ta1) / 2; + context.quadraticCurveTo(0, 0, tr2 * cos(ta0), tr2 * sin(ta0)); + context.lineTo(tr * cos(ta2), tr * sin(ta2)); + context.lineTo(tr2 * cos(ta1), tr2 * sin(ta1)); + } else { + context.quadraticCurveTo(0, 0, tr * cos(ta0), tr * sin(ta0)); + context.arc(0, 0, tr, ta0, ta1); + } + } + context.quadraticCurveTo(0, 0, sr * cos(sa0), sr * sin(sa0)); + context.closePath(); + + if (buffer) return context = null, buffer + "" || null; + } + + if (headRadius) ribbon.headRadius = function(_) { + return arguments.length ? (headRadius = typeof _ === "function" ? _ : constant(+_), ribbon) : headRadius; + }; + + ribbon.radius = function(_) { + return arguments.length ? (sourceRadius = targetRadius = typeof _ === "function" ? _ : constant(+_), ribbon) : sourceRadius; + }; + + ribbon.sourceRadius = function(_) { + return arguments.length ? (sourceRadius = typeof _ === "function" ? _ : constant(+_), ribbon) : sourceRadius; + }; + + ribbon.targetRadius = function(_) { + return arguments.length ? (targetRadius = typeof _ === "function" ? _ : constant(+_), ribbon) : targetRadius; + }; + + ribbon.startAngle = function(_) { + return arguments.length ? (startAngle = typeof _ === "function" ? _ : constant(+_), ribbon) : startAngle; + }; + + ribbon.endAngle = function(_) { + return arguments.length ? (endAngle = typeof _ === "function" ? _ : constant(+_), ribbon) : endAngle; + }; + + ribbon.padAngle = function(_) { + return arguments.length ? (padAngle = typeof _ === "function" ? _ : constant(+_), ribbon) : padAngle; + }; + + ribbon.source = function(_) { + return arguments.length ? (source = _, ribbon) : source; + }; + + ribbon.target = function(_) { + return arguments.length ? (target = _, ribbon) : target; + }; + + ribbon.context = function(_) { + return arguments.length ? ((context = _ == null ? null : _), ribbon) : context; + }; + + return ribbon; +} + +export default function() { + return ribbon(); +} + +export function ribbonArrow() { + return ribbon(defaultArrowheadRadius); +} diff --git a/frontend/node_modules/d3-color/LICENSE b/frontend/node_modules/d3-color/LICENSE new file mode 100644 index 0000000..fbe44bd --- /dev/null +++ b/frontend/node_modules/d3-color/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2022 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-color/README.md b/frontend/node_modules/d3-color/README.md new file mode 100644 index 0000000..a7f2d52 --- /dev/null +++ b/frontend/node_modules/d3-color/README.md @@ -0,0 +1,203 @@ +# d3-color + +Even though your browser understands a lot about colors, it doesn’t offer much help in manipulating colors through JavaScript. The d3-color module therefore provides representations for various color spaces, allowing specification, conversion and manipulation. (Also see [d3-interpolate](https://github.com/d3/d3-interpolate) for color interpolation.) + +For example, take the color named “steelblue”: + +```js +const c = d3.color("steelblue"); // {r: 70, g: 130, b: 180, opacity: 1} +``` + +Let’s try converting it to HSL: + +```js +const c = d3.hsl("steelblue"); // {h: 207.27…, s: 0.44, l: 0.4902…, opacity: 1} +``` + +Now rotate the hue by 90°, bump up the saturation, and format as a string for CSS: + +```js +c.h += 90; +c.s += 0.2; +c + ""; // rgb(198, 45, 205) +``` + +To fade the color slightly: + +```js +c.opacity = 0.8; +c + ""; // rgba(198, 45, 205, 0.8) +``` + +In addition to the ubiquitous and machine-friendly [RGB](#rgb) and [HSL](#hsl) color space, d3-color supports color spaces that are designed for humans: + +* [CIELAB](#lab) (*a.k.a.* “Lab”) +* [CIELChab](#lch) (*a.k.a.* “LCh” or “HCL”) +* Dave Green’s [Cubehelix](#cubehelix) + +Cubehelix features monotonic lightness, while CIELAB and its polar form CIELChab are perceptually uniform. + +## Extensions + +For additional color spaces, see: + +* [d3-cam16](https://github.com/d3/d3-cam16) +* [d3-cam02](https://github.com/connorgr/d3-cam02) +* [d3-hsv](https://github.com/d3/d3-hsv) +* [d3-hcg](https://github.com/d3/d3-hcg) +* [d3-hsluv](https://github.com/petulla/d3-hsluv) + +To measure color differences, see: + +* [d3-color-difference](https://github.com/Evercoder/d3-color-difference) + +## Installing + +If you use npm, `npm install d3-color`. You can also download the [latest release on GitHub](https://github.com/d3/d3-color/releases/latest). For vanilla HTML in modern browsers, import d3-color from Skypack: + +```html + +``` + +For legacy environments, you can load d3-color’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +[Try d3-color in your browser.](https://observablehq.com/collection/@d3/d3-color) + +## API Reference + +# d3.color(specifier) [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source") + +Parses the specified [CSS Color Module Level 3](http://www.w3.org/TR/css3-color/#colorunits) *specifier* string, returning an [RGB](#rgb) or [HSL](#hsl) color, along with [CSS Color Module Level 4 hex](https://www.w3.org/TR/css-color-4/#hex-notation) *specifier* strings. If the specifier was not valid, null is returned. Some examples: + +* `rgb(255, 255, 255)` +* `rgb(10%, 20%, 30%)` +* `rgba(255, 255, 255, 0.4)` +* `rgba(10%, 20%, 30%, 0.4)` +* `hsl(120, 50%, 20%)` +* `hsla(120, 50%, 20%, 0.4)` +* `#ffeeaa` +* `#fea` +* `#ffeeaa22` +* `#fea2` +* `steelblue` + +The list of supported [named colors](http://www.w3.org/TR/SVG/types.html#ColorKeywords) is specified by CSS. + +Note: this function may also be used with `instanceof` to test if an object is a color instance. The same is true of color subclasses, allowing you to test whether a color is in a particular color space. + +# *color*.opacity + +This color’s opacity, typically in the range [0, 1]. + +# *color*.rgb() [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source") + +Returns the [RGB equivalent](#rgb) of this color. For RGB colors, that’s `this`. + +# color.copy([values]) [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source") + +Returns a copy of this color. If *values* is specified, any enumerable own properties of *values* are assigned to the new returned color. For example, to derive a copy of a *color* with opacity 0.5, say + +```js +color.copy({opacity: 0.5}) +``` + +# *color*.brighter([k]) [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source") + +Returns a brighter copy of this color. If *k* is specified, it controls how much brighter the returned color should be. If *k* is not specified, it defaults to 1. The behavior of this method is dependent on the implementing color space. + +# *color*.darker([k]) [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source") + +Returns a darker copy of this color. If *k* is specified, it controls how much darker the returned color should be. If *k* is not specified, it defaults to 1. The behavior of this method is dependent on the implementing color space. + +# *color*.displayable() [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source") + +Returns true if and only if the color is displayable on standard hardware. For example, this returns false for an RGB color if any channel value is less than zero or greater than 255 when rounded, or if the opacity is not in the range [0, 1]. + +# *color*.formatHex() [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source") + +Returns a hexadecimal string representing this color in RGB space, such as `#f7eaba`. If this color is not displayable, a suitable displayable color is returned instead. For example, RGB channel values greater than 255 are clamped to 255. + +# *color*.formatHsl() [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source") + +Returns a string representing this color according to the [CSS Color Module Level 3 specification](https://www.w3.org/TR/css-color-3/#hsl-color), such as `hsl(257, 50%, 80%)` or `hsla(257, 50%, 80%, 0.2)`. If this color is not displayable, a suitable displayable color is returned instead by clamping S and L channel values to the interval [0, 100]. + +# *color*.formatRgb() [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source") + +Returns a string representing this color according to the [CSS Object Model specification](https://drafts.csswg.org/cssom/#serialize-a-css-component-value), such as `rgb(247, 234, 186)` or `rgba(247, 234, 186, 0.2)`. If this color is not displayable, a suitable displayable color is returned instead by clamping RGB channel values to the interval [0, 255]. + +# *color*.toString() [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source") + +An alias for [*color*.formatRgb](#color_formatRgb). + +# d3.rgb(r, g, b[, opacity]) [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source")
    +# d3.rgb(specifier)
    +# d3.rgb(color)
    + +Constructs a new [RGB](https://en.wikipedia.org/wiki/RGB_color_model) color. The channel values are exposed as `r`, `g` and `b` properties on the returned instance. Use the [RGB color picker](http://bl.ocks.org/mbostock/78d64ca7ef013b4dcf8f) to explore this color space. + +If *r*, *g* and *b* are specified, these represent the channel values of the returned color; an *opacity* may also be specified. If a CSS Color Module Level 3 *specifier* string is specified, it is parsed and then converted to the RGB color space. See [color](#color) for examples. If a [*color*](#color) instance is specified, it is converted to the RGB color space using [*color*.rgb](#color_rgb). Note that unlike [*color*.rgb](#color_rgb) this method *always* returns a new instance, even if *color* is already an RGB color. + +# *rgb*.clamp() [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source") + +Returns a new RGB color where the `r`, `g`, and `b` channels are clamped to the range [0, 255] and rounded to the nearest integer value, and the `opacity` is clamped to the range [0, 1]. + +# d3.hsl(h, s, l[, opacity]) [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source")
    +# d3.hsl(specifier)
    +# d3.hsl(color)
    + +Constructs a new [HSL](https://en.wikipedia.org/wiki/HSL_and_HSV) color. The channel values are exposed as `h`, `s` and `l` properties on the returned instance. Use the [HSL color picker](http://bl.ocks.org/mbostock/debaad4fcce9bcee14cf) to explore this color space. + +If *h*, *s* and *l* are specified, these represent the channel values of the returned color; an *opacity* may also be specified. If a CSS Color Module Level 3 *specifier* string is specified, it is parsed and then converted to the HSL color space. See [color](#color) for examples. If a [*color*](#color) instance is specified, it is converted to the RGB color space using [*color*.rgb](#color_rgb) and then converted to HSL. (Colors already in the HSL color space skip the conversion to RGB.) + +# *hsl*.clamp() [<>](https://github.com/d3/d3-color/blob/master/src/color.js "Source") + +Returns a new HSL color where the `h` channel is clamped to the range [0, 360), and the `s`, `l`, and `opacity` channels are clamped to the range [0, 1]. + +# d3.lab(l, a, b[, opacity]) [<>](https://github.com/d3/d3-color/blob/master/src/lab.js "Source")
    +# d3.lab(specifier)
    +# d3.lab(color)
    + +Constructs a new [CIELAB](https://en.wikipedia.org/wiki/Lab_color_space#CIELAB) color. The channel values are exposed as `l`, `a` and `b` properties on the returned instance. Use the [CIELAB color picker](http://bl.ocks.org/mbostock/9f37cc207c0cb166921b) to explore this color space. The value of *l* is typically in the range [0, 100], while *a* and *b* are typically in [-160, +160]. + +If *l*, *a* and *b* are specified, these represent the channel values of the returned color; an *opacity* may also be specified. If a CSS Color Module Level 3 *specifier* string is specified, it is parsed and then converted to the CIELAB color space. See [color](#color) for examples. If a [*color*](#color) instance is specified, it is converted to the RGB color space using [*color*.rgb](#color_rgb) and then converted to CIELAB. (Colors already in the CIELAB color space skip the conversion to RGB, and colors in the HCL color space are converted directly to CIELAB.) + +# d3.gray(l[, opacity]) [<>](https://github.com/d3/d3-color/blob/master/src/lab.js "Source")
    + +Constructs a new [CIELAB](#lab) color with the specified *l* value and *a* = *b* = 0. + +# d3.hcl(h, c, l[, opacity]) [<>](https://github.com/d3/d3-color/blob/master/src/lab.js "Source")
    +# d3.hcl(specifier)
    +# d3.hcl(color)
    + +Equivalent to [d3.lch](#lch), but with reversed argument order. + +# d3.lch(l, c, h[, opacity]) [<>](https://github.com/d3/d3-color/blob/master/src/lab.js "Source")
    +# d3.lch(specifier)
    +# d3.lch(color)
    + +Constructs a new [CIELChab](https://en.wikipedia.org/wiki/CIELAB_color_space#Cylindrical_representation:_CIELCh_or_CIEHLC) color. The channel values are exposed as `l`, `c` and `h` properties on the returned instance. Use the [CIELChab color picker](http://bl.ocks.org/mbostock/3e115519a1b495e0bd95) to explore this color space. The value of *l* is typically in the range [0, 100], *c* is typically in [0, 230], and *h* is typically in [0, 360). + +If *l*, *c*, and *h* are specified, these represent the channel values of the returned color; an *opacity* may also be specified. If a CSS Color Module Level 3 *specifier* string is specified, it is parsed and then converted to CIELChab color space. See [color](#color) for examples. If a [*color*](#color) instance is specified, it is converted to the RGB color space using [*color*.rgb](#color_rgb) and then converted to CIELChab. (Colors already in CIELChab color space skip the conversion to RGB, and colors in CIELAB color space are converted directly to CIELChab.) + +# d3.cubehelix(h, s, l[, opacity]) [<>](https://github.com/d3/d3-color/blob/master/src/cubehelix.js "Source")
    +# d3.cubehelix(specifier)
    +# d3.cubehelix(color)
    + +Constructs a new [Cubehelix](http://www.mrao.cam.ac.uk/~dag/CUBEHELIX/) color. The channel values are exposed as `h`, `s` and `l` properties on the returned instance. Use the [Cubehelix color picker](http://bl.ocks.org/mbostock/ba8d75e45794c27168b5) to explore this color space. + +If *h*, *s* and *l* are specified, these represent the channel values of the returned color; an *opacity* may also be specified. If a CSS Color Module Level 3 *specifier* string is specified, it is parsed and then converted to the Cubehelix color space. See [color](#color) for examples. If a [*color*](#color) instance is specified, it is converted to the RGB color space using [*color*.rgb](#color_rgb) and then converted to Cubehelix. (Colors already in the Cubehelix color space skip the conversion to RGB.) diff --git a/frontend/node_modules/d3-color/dist/d3-color.js b/frontend/node_modules/d3-color/dist/d3-color.js new file mode 100644 index 0000000..a4ad54e --- /dev/null +++ b/frontend/node_modules/d3-color/dist/d3-color.js @@ -0,0 +1,606 @@ +// https://d3js.org/d3-color/ v3.1.0 Copyright 2010-2022 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +})(this, (function (exports) { 'use strict'; + +function define(constructor, factory, prototype) { + constructor.prototype = factory.prototype = prototype; + prototype.constructor = constructor; +} + +function extend(parent, definition) { + var prototype = Object.create(parent.prototype); + for (var key in definition) prototype[key] = definition[key]; + return prototype; +} + +function Color() {} + +var darker = 0.7; +var brighter = 1 / darker; + +var reI = "\\s*([+-]?\\d+)\\s*", + reN = "\\s*([+-]?(?:\\d*\\.)?\\d+(?:[eE][+-]?\\d+)?)\\s*", + reP = "\\s*([+-]?(?:\\d*\\.)?\\d+(?:[eE][+-]?\\d+)?)%\\s*", + reHex = /^#([0-9a-f]{3,8})$/, + reRgbInteger = new RegExp(`^rgb\\(${reI},${reI},${reI}\\)$`), + reRgbPercent = new RegExp(`^rgb\\(${reP},${reP},${reP}\\)$`), + reRgbaInteger = new RegExp(`^rgba\\(${reI},${reI},${reI},${reN}\\)$`), + reRgbaPercent = new RegExp(`^rgba\\(${reP},${reP},${reP},${reN}\\)$`), + reHslPercent = new RegExp(`^hsl\\(${reN},${reP},${reP}\\)$`), + reHslaPercent = new RegExp(`^hsla\\(${reN},${reP},${reP},${reN}\\)$`); + +var named = { + aliceblue: 0xf0f8ff, + antiquewhite: 0xfaebd7, + aqua: 0x00ffff, + aquamarine: 0x7fffd4, + azure: 0xf0ffff, + beige: 0xf5f5dc, + bisque: 0xffe4c4, + black: 0x000000, + blanchedalmond: 0xffebcd, + blue: 0x0000ff, + blueviolet: 0x8a2be2, + brown: 0xa52a2a, + burlywood: 0xdeb887, + cadetblue: 0x5f9ea0, + chartreuse: 0x7fff00, + chocolate: 0xd2691e, + coral: 0xff7f50, + cornflowerblue: 0x6495ed, + cornsilk: 0xfff8dc, + crimson: 0xdc143c, + cyan: 0x00ffff, + darkblue: 0x00008b, + darkcyan: 0x008b8b, + darkgoldenrod: 0xb8860b, + darkgray: 0xa9a9a9, + darkgreen: 0x006400, + darkgrey: 0xa9a9a9, + darkkhaki: 0xbdb76b, + darkmagenta: 0x8b008b, + darkolivegreen: 0x556b2f, + darkorange: 0xff8c00, + darkorchid: 0x9932cc, + darkred: 0x8b0000, + darksalmon: 0xe9967a, + darkseagreen: 0x8fbc8f, + darkslateblue: 0x483d8b, + darkslategray: 0x2f4f4f, + darkslategrey: 0x2f4f4f, + darkturquoise: 0x00ced1, + darkviolet: 0x9400d3, + deeppink: 0xff1493, + deepskyblue: 0x00bfff, + dimgray: 0x696969, + dimgrey: 0x696969, + dodgerblue: 0x1e90ff, + firebrick: 0xb22222, + floralwhite: 0xfffaf0, + forestgreen: 0x228b22, + fuchsia: 0xff00ff, + gainsboro: 0xdcdcdc, + ghostwhite: 0xf8f8ff, + gold: 0xffd700, + goldenrod: 0xdaa520, + gray: 0x808080, + green: 0x008000, + greenyellow: 0xadff2f, + grey: 0x808080, + honeydew: 0xf0fff0, + hotpink: 0xff69b4, + indianred: 0xcd5c5c, + indigo: 0x4b0082, + ivory: 0xfffff0, + khaki: 0xf0e68c, + lavender: 0xe6e6fa, + lavenderblush: 0xfff0f5, + lawngreen: 0x7cfc00, + lemonchiffon: 0xfffacd, + lightblue: 0xadd8e6, + lightcoral: 0xf08080, + lightcyan: 0xe0ffff, + lightgoldenrodyellow: 0xfafad2, + lightgray: 0xd3d3d3, + lightgreen: 0x90ee90, + lightgrey: 0xd3d3d3, + lightpink: 0xffb6c1, + lightsalmon: 0xffa07a, + lightseagreen: 0x20b2aa, + lightskyblue: 0x87cefa, + lightslategray: 0x778899, + lightslategrey: 0x778899, + lightsteelblue: 0xb0c4de, + lightyellow: 0xffffe0, + lime: 0x00ff00, + limegreen: 0x32cd32, + linen: 0xfaf0e6, + magenta: 0xff00ff, + maroon: 0x800000, + mediumaquamarine: 0x66cdaa, + mediumblue: 0x0000cd, + mediumorchid: 0xba55d3, + mediumpurple: 0x9370db, + mediumseagreen: 0x3cb371, + mediumslateblue: 0x7b68ee, + mediumspringgreen: 0x00fa9a, + mediumturquoise: 0x48d1cc, + mediumvioletred: 0xc71585, + midnightblue: 0x191970, + mintcream: 0xf5fffa, + mistyrose: 0xffe4e1, + moccasin: 0xffe4b5, + navajowhite: 0xffdead, + navy: 0x000080, + oldlace: 0xfdf5e6, + olive: 0x808000, + olivedrab: 0x6b8e23, + orange: 0xffa500, + orangered: 0xff4500, + orchid: 0xda70d6, + palegoldenrod: 0xeee8aa, + palegreen: 0x98fb98, + paleturquoise: 0xafeeee, + palevioletred: 0xdb7093, + papayawhip: 0xffefd5, + peachpuff: 0xffdab9, + peru: 0xcd853f, + pink: 0xffc0cb, + plum: 0xdda0dd, + powderblue: 0xb0e0e6, + purple: 0x800080, + rebeccapurple: 0x663399, + red: 0xff0000, + rosybrown: 0xbc8f8f, + royalblue: 0x4169e1, + saddlebrown: 0x8b4513, + salmon: 0xfa8072, + sandybrown: 0xf4a460, + seagreen: 0x2e8b57, + seashell: 0xfff5ee, + sienna: 0xa0522d, + silver: 0xc0c0c0, + skyblue: 0x87ceeb, + slateblue: 0x6a5acd, + slategray: 0x708090, + slategrey: 0x708090, + snow: 0xfffafa, + springgreen: 0x00ff7f, + steelblue: 0x4682b4, + tan: 0xd2b48c, + teal: 0x008080, + thistle: 0xd8bfd8, + tomato: 0xff6347, + turquoise: 0x40e0d0, + violet: 0xee82ee, + wheat: 0xf5deb3, + white: 0xffffff, + whitesmoke: 0xf5f5f5, + yellow: 0xffff00, + yellowgreen: 0x9acd32 +}; + +define(Color, color, { + copy(channels) { + return Object.assign(new this.constructor, this, channels); + }, + displayable() { + return this.rgb().displayable(); + }, + hex: color_formatHex, // Deprecated! Use color.formatHex. + formatHex: color_formatHex, + formatHex8: color_formatHex8, + formatHsl: color_formatHsl, + formatRgb: color_formatRgb, + toString: color_formatRgb +}); + +function color_formatHex() { + return this.rgb().formatHex(); +} + +function color_formatHex8() { + return this.rgb().formatHex8(); +} + +function color_formatHsl() { + return hslConvert(this).formatHsl(); +} + +function color_formatRgb() { + return this.rgb().formatRgb(); +} + +function color(format) { + var m, l; + format = (format + "").trim().toLowerCase(); + return (m = reHex.exec(format)) ? (l = m[1].length, m = parseInt(m[1], 16), l === 6 ? rgbn(m) // #ff0000 + : l === 3 ? new Rgb((m >> 8 & 0xf) | (m >> 4 & 0xf0), (m >> 4 & 0xf) | (m & 0xf0), ((m & 0xf) << 4) | (m & 0xf), 1) // #f00 + : l === 8 ? rgba(m >> 24 & 0xff, m >> 16 & 0xff, m >> 8 & 0xff, (m & 0xff) / 0xff) // #ff000000 + : l === 4 ? rgba((m >> 12 & 0xf) | (m >> 8 & 0xf0), (m >> 8 & 0xf) | (m >> 4 & 0xf0), (m >> 4 & 0xf) | (m & 0xf0), (((m & 0xf) << 4) | (m & 0xf)) / 0xff) // #f000 + : null) // invalid hex + : (m = reRgbInteger.exec(format)) ? new Rgb(m[1], m[2], m[3], 1) // rgb(255, 0, 0) + : (m = reRgbPercent.exec(format)) ? new Rgb(m[1] * 255 / 100, m[2] * 255 / 100, m[3] * 255 / 100, 1) // rgb(100%, 0%, 0%) + : (m = reRgbaInteger.exec(format)) ? rgba(m[1], m[2], m[3], m[4]) // rgba(255, 0, 0, 1) + : (m = reRgbaPercent.exec(format)) ? rgba(m[1] * 255 / 100, m[2] * 255 / 100, m[3] * 255 / 100, m[4]) // rgb(100%, 0%, 0%, 1) + : (m = reHslPercent.exec(format)) ? hsla(m[1], m[2] / 100, m[3] / 100, 1) // hsl(120, 50%, 50%) + : (m = reHslaPercent.exec(format)) ? hsla(m[1], m[2] / 100, m[3] / 100, m[4]) // hsla(120, 50%, 50%, 1) + : named.hasOwnProperty(format) ? rgbn(named[format]) // eslint-disable-line no-prototype-builtins + : format === "transparent" ? new Rgb(NaN, NaN, NaN, 0) + : null; +} + +function rgbn(n) { + return new Rgb(n >> 16 & 0xff, n >> 8 & 0xff, n & 0xff, 1); +} + +function rgba(r, g, b, a) { + if (a <= 0) r = g = b = NaN; + return new Rgb(r, g, b, a); +} + +function rgbConvert(o) { + if (!(o instanceof Color)) o = color(o); + if (!o) return new Rgb; + o = o.rgb(); + return new Rgb(o.r, o.g, o.b, o.opacity); +} + +function rgb(r, g, b, opacity) { + return arguments.length === 1 ? rgbConvert(r) : new Rgb(r, g, b, opacity == null ? 1 : opacity); +} + +function Rgb(r, g, b, opacity) { + this.r = +r; + this.g = +g; + this.b = +b; + this.opacity = +opacity; +} + +define(Rgb, rgb, extend(Color, { + brighter(k) { + k = k == null ? brighter : Math.pow(brighter, k); + return new Rgb(this.r * k, this.g * k, this.b * k, this.opacity); + }, + darker(k) { + k = k == null ? darker : Math.pow(darker, k); + return new Rgb(this.r * k, this.g * k, this.b * k, this.opacity); + }, + rgb() { + return this; + }, + clamp() { + return new Rgb(clampi(this.r), clampi(this.g), clampi(this.b), clampa(this.opacity)); + }, + displayable() { + return (-0.5 <= this.r && this.r < 255.5) + && (-0.5 <= this.g && this.g < 255.5) + && (-0.5 <= this.b && this.b < 255.5) + && (0 <= this.opacity && this.opacity <= 1); + }, + hex: rgb_formatHex, // Deprecated! Use color.formatHex. + formatHex: rgb_formatHex, + formatHex8: rgb_formatHex8, + formatRgb: rgb_formatRgb, + toString: rgb_formatRgb +})); + +function rgb_formatHex() { + return `#${hex(this.r)}${hex(this.g)}${hex(this.b)}`; +} + +function rgb_formatHex8() { + return `#${hex(this.r)}${hex(this.g)}${hex(this.b)}${hex((isNaN(this.opacity) ? 1 : this.opacity) * 255)}`; +} + +function rgb_formatRgb() { + const a = clampa(this.opacity); + return `${a === 1 ? "rgb(" : "rgba("}${clampi(this.r)}, ${clampi(this.g)}, ${clampi(this.b)}${a === 1 ? ")" : `, ${a})`}`; +} + +function clampa(opacity) { + return isNaN(opacity) ? 1 : Math.max(0, Math.min(1, opacity)); +} + +function clampi(value) { + return Math.max(0, Math.min(255, Math.round(value) || 0)); +} + +function hex(value) { + value = clampi(value); + return (value < 16 ? "0" : "") + value.toString(16); +} + +function hsla(h, s, l, a) { + if (a <= 0) h = s = l = NaN; + else if (l <= 0 || l >= 1) h = s = NaN; + else if (s <= 0) h = NaN; + return new Hsl(h, s, l, a); +} + +function hslConvert(o) { + if (o instanceof Hsl) return new Hsl(o.h, o.s, o.l, o.opacity); + if (!(o instanceof Color)) o = color(o); + if (!o) return new Hsl; + if (o instanceof Hsl) return o; + o = o.rgb(); + var r = o.r / 255, + g = o.g / 255, + b = o.b / 255, + min = Math.min(r, g, b), + max = Math.max(r, g, b), + h = NaN, + s = max - min, + l = (max + min) / 2; + if (s) { + if (r === max) h = (g - b) / s + (g < b) * 6; + else if (g === max) h = (b - r) / s + 2; + else h = (r - g) / s + 4; + s /= l < 0.5 ? max + min : 2 - max - min; + h *= 60; + } else { + s = l > 0 && l < 1 ? 0 : h; + } + return new Hsl(h, s, l, o.opacity); +} + +function hsl(h, s, l, opacity) { + return arguments.length === 1 ? hslConvert(h) : new Hsl(h, s, l, opacity == null ? 1 : opacity); +} + +function Hsl(h, s, l, opacity) { + this.h = +h; + this.s = +s; + this.l = +l; + this.opacity = +opacity; +} + +define(Hsl, hsl, extend(Color, { + brighter(k) { + k = k == null ? brighter : Math.pow(brighter, k); + return new Hsl(this.h, this.s, this.l * k, this.opacity); + }, + darker(k) { + k = k == null ? darker : Math.pow(darker, k); + return new Hsl(this.h, this.s, this.l * k, this.opacity); + }, + rgb() { + var h = this.h % 360 + (this.h < 0) * 360, + s = isNaN(h) || isNaN(this.s) ? 0 : this.s, + l = this.l, + m2 = l + (l < 0.5 ? l : 1 - l) * s, + m1 = 2 * l - m2; + return new Rgb( + hsl2rgb(h >= 240 ? h - 240 : h + 120, m1, m2), + hsl2rgb(h, m1, m2), + hsl2rgb(h < 120 ? h + 240 : h - 120, m1, m2), + this.opacity + ); + }, + clamp() { + return new Hsl(clamph(this.h), clampt(this.s), clampt(this.l), clampa(this.opacity)); + }, + displayable() { + return (0 <= this.s && this.s <= 1 || isNaN(this.s)) + && (0 <= this.l && this.l <= 1) + && (0 <= this.opacity && this.opacity <= 1); + }, + formatHsl() { + const a = clampa(this.opacity); + return `${a === 1 ? "hsl(" : "hsla("}${clamph(this.h)}, ${clampt(this.s) * 100}%, ${clampt(this.l) * 100}%${a === 1 ? ")" : `, ${a})`}`; + } +})); + +function clamph(value) { + value = (value || 0) % 360; + return value < 0 ? value + 360 : value; +} + +function clampt(value) { + return Math.max(0, Math.min(1, value || 0)); +} + +/* From FvD 13.37, CSS Color Module Level 3 */ +function hsl2rgb(h, m1, m2) { + return (h < 60 ? m1 + (m2 - m1) * h / 60 + : h < 180 ? m2 + : h < 240 ? m1 + (m2 - m1) * (240 - h) / 60 + : m1) * 255; +} + +const radians = Math.PI / 180; +const degrees = 180 / Math.PI; + +// https://observablehq.com/@mbostock/lab-and-rgb +const K = 18, + Xn = 0.96422, + Yn = 1, + Zn = 0.82521, + t0 = 4 / 29, + t1 = 6 / 29, + t2 = 3 * t1 * t1, + t3 = t1 * t1 * t1; + +function labConvert(o) { + if (o instanceof Lab) return new Lab(o.l, o.a, o.b, o.opacity); + if (o instanceof Hcl) return hcl2lab(o); + if (!(o instanceof Rgb)) o = rgbConvert(o); + var r = rgb2lrgb(o.r), + g = rgb2lrgb(o.g), + b = rgb2lrgb(o.b), + y = xyz2lab((0.2225045 * r + 0.7168786 * g + 0.0606169 * b) / Yn), x, z; + if (r === g && g === b) x = z = y; else { + x = xyz2lab((0.4360747 * r + 0.3850649 * g + 0.1430804 * b) / Xn); + z = xyz2lab((0.0139322 * r + 0.0971045 * g + 0.7141733 * b) / Zn); + } + return new Lab(116 * y - 16, 500 * (x - y), 200 * (y - z), o.opacity); +} + +function gray(l, opacity) { + return new Lab(l, 0, 0, opacity == null ? 1 : opacity); +} + +function lab(l, a, b, opacity) { + return arguments.length === 1 ? labConvert(l) : new Lab(l, a, b, opacity == null ? 1 : opacity); +} + +function Lab(l, a, b, opacity) { + this.l = +l; + this.a = +a; + this.b = +b; + this.opacity = +opacity; +} + +define(Lab, lab, extend(Color, { + brighter(k) { + return new Lab(this.l + K * (k == null ? 1 : k), this.a, this.b, this.opacity); + }, + darker(k) { + return new Lab(this.l - K * (k == null ? 1 : k), this.a, this.b, this.opacity); + }, + rgb() { + var y = (this.l + 16) / 116, + x = isNaN(this.a) ? y : y + this.a / 500, + z = isNaN(this.b) ? y : y - this.b / 200; + x = Xn * lab2xyz(x); + y = Yn * lab2xyz(y); + z = Zn * lab2xyz(z); + return new Rgb( + lrgb2rgb( 3.1338561 * x - 1.6168667 * y - 0.4906146 * z), + lrgb2rgb(-0.9787684 * x + 1.9161415 * y + 0.0334540 * z), + lrgb2rgb( 0.0719453 * x - 0.2289914 * y + 1.4052427 * z), + this.opacity + ); + } +})); + +function xyz2lab(t) { + return t > t3 ? Math.pow(t, 1 / 3) : t / t2 + t0; +} + +function lab2xyz(t) { + return t > t1 ? t * t * t : t2 * (t - t0); +} + +function lrgb2rgb(x) { + return 255 * (x <= 0.0031308 ? 12.92 * x : 1.055 * Math.pow(x, 1 / 2.4) - 0.055); +} + +function rgb2lrgb(x) { + return (x /= 255) <= 0.04045 ? x / 12.92 : Math.pow((x + 0.055) / 1.055, 2.4); +} + +function hclConvert(o) { + if (o instanceof Hcl) return new Hcl(o.h, o.c, o.l, o.opacity); + if (!(o instanceof Lab)) o = labConvert(o); + if (o.a === 0 && o.b === 0) return new Hcl(NaN, 0 < o.l && o.l < 100 ? 0 : NaN, o.l, o.opacity); + var h = Math.atan2(o.b, o.a) * degrees; + return new Hcl(h < 0 ? h + 360 : h, Math.sqrt(o.a * o.a + o.b * o.b), o.l, o.opacity); +} + +function lch(l, c, h, opacity) { + return arguments.length === 1 ? hclConvert(l) : new Hcl(h, c, l, opacity == null ? 1 : opacity); +} + +function hcl(h, c, l, opacity) { + return arguments.length === 1 ? hclConvert(h) : new Hcl(h, c, l, opacity == null ? 1 : opacity); +} + +function Hcl(h, c, l, opacity) { + this.h = +h; + this.c = +c; + this.l = +l; + this.opacity = +opacity; +} + +function hcl2lab(o) { + if (isNaN(o.h)) return new Lab(o.l, 0, 0, o.opacity); + var h = o.h * radians; + return new Lab(o.l, Math.cos(h) * o.c, Math.sin(h) * o.c, o.opacity); +} + +define(Hcl, hcl, extend(Color, { + brighter(k) { + return new Hcl(this.h, this.c, this.l + K * (k == null ? 1 : k), this.opacity); + }, + darker(k) { + return new Hcl(this.h, this.c, this.l - K * (k == null ? 1 : k), this.opacity); + }, + rgb() { + return hcl2lab(this).rgb(); + } +})); + +var A = -0.14861, + B = +1.78277, + C = -0.29227, + D = -0.90649, + E = +1.97294, + ED = E * D, + EB = E * B, + BC_DA = B * C - D * A; + +function cubehelixConvert(o) { + if (o instanceof Cubehelix) return new Cubehelix(o.h, o.s, o.l, o.opacity); + if (!(o instanceof Rgb)) o = rgbConvert(o); + var r = o.r / 255, + g = o.g / 255, + b = o.b / 255, + l = (BC_DA * b + ED * r - EB * g) / (BC_DA + ED - EB), + bl = b - l, + k = (E * (g - l) - C * bl) / D, + s = Math.sqrt(k * k + bl * bl) / (E * l * (1 - l)), // NaN if l=0 or l=1 + h = s ? Math.atan2(k, bl) * degrees - 120 : NaN; + return new Cubehelix(h < 0 ? h + 360 : h, s, l, o.opacity); +} + +function cubehelix(h, s, l, opacity) { + return arguments.length === 1 ? cubehelixConvert(h) : new Cubehelix(h, s, l, opacity == null ? 1 : opacity); +} + +function Cubehelix(h, s, l, opacity) { + this.h = +h; + this.s = +s; + this.l = +l; + this.opacity = +opacity; +} + +define(Cubehelix, cubehelix, extend(Color, { + brighter(k) { + k = k == null ? brighter : Math.pow(brighter, k); + return new Cubehelix(this.h, this.s, this.l * k, this.opacity); + }, + darker(k) { + k = k == null ? darker : Math.pow(darker, k); + return new Cubehelix(this.h, this.s, this.l * k, this.opacity); + }, + rgb() { + var h = isNaN(this.h) ? 0 : (this.h + 120) * radians, + l = +this.l, + a = isNaN(this.s) ? 0 : this.s * l * (1 - l), + cosh = Math.cos(h), + sinh = Math.sin(h); + return new Rgb( + 255 * (l + a * (A * cosh + B * sinh)), + 255 * (l + a * (C * cosh + D * sinh)), + 255 * (l + a * (E * cosh)), + this.opacity + ); + } +})); + +exports.color = color; +exports.cubehelix = cubehelix; +exports.gray = gray; +exports.hcl = hcl; +exports.hsl = hsl; +exports.lab = lab; +exports.lch = lch; +exports.rgb = rgb; + +Object.defineProperty(exports, '__esModule', { value: true }); + +})); diff --git a/frontend/node_modules/d3-color/dist/d3-color.min.js b/frontend/node_modules/d3-color/dist/d3-color.min.js new file mode 100644 index 0000000..dfe24a3 --- /dev/null +++ b/frontend/node_modules/d3-color/dist/d3-color.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-color/ v3.1.0 Copyright 2010-2022 Mike Bostock +!function(t,e){"object"==typeof exports&&"undefined"!=typeof module?e(exports):"function"==typeof define&&define.amd?define(["exports"],e):e((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{})}(this,(function(t){"use strict";function e(t,e,i){t.prototype=e.prototype=i,i.constructor=t}function i(t,e){var i=Object.create(t.prototype);for(var n in e)i[n]=e[n];return i}function n(){}var r=.7,a=1/r,s="\\s*([+-]?\\d+)\\s*",h="\\s*([+-]?(?:\\d*\\.)?\\d+(?:[eE][+-]?\\d+)?)\\s*",o="\\s*([+-]?(?:\\d*\\.)?\\d+(?:[eE][+-]?\\d+)?)%\\s*",l=/^#([0-9a-f]{3,8})$/,u=new RegExp(`^rgb\\(${s},${s},${s}\\)$`),c=new RegExp(`^rgb\\(${o},${o},${o}\\)$`),g=new RegExp(`^rgba\\(${s},${s},${s},${h}\\)$`),p=new RegExp(`^rgba\\(${o},${o},${o},${h}\\)$`),f=new RegExp(`^hsl\\(${h},${o},${o}\\)$`),d=new RegExp(`^hsla\\(${h},${o},${o},${h}\\)$`),b={aliceblue:15792383,antiquewhite:16444375,aqua:65535,aquamarine:8388564,azure:15794175,beige:16119260,bisque:16770244,black:0,blanchedalmond:16772045,blue:255,blueviolet:9055202,brown:10824234,burlywood:14596231,cadetblue:6266528,chartreuse:8388352,chocolate:13789470,coral:16744272,cornflowerblue:6591981,cornsilk:16775388,crimson:14423100,cyan:65535,darkblue:139,darkcyan:35723,darkgoldenrod:12092939,darkgray:11119017,darkgreen:25600,darkgrey:11119017,darkkhaki:12433259,darkmagenta:9109643,darkolivegreen:5597999,darkorange:16747520,darkorchid:10040012,darkred:9109504,darksalmon:15308410,darkseagreen:9419919,darkslateblue:4734347,darkslategray:3100495,darkslategrey:3100495,darkturquoise:52945,darkviolet:9699539,deeppink:16716947,deepskyblue:49151,dimgray:6908265,dimgrey:6908265,dodgerblue:2003199,firebrick:11674146,floralwhite:16775920,forestgreen:2263842,fuchsia:16711935,gainsboro:14474460,ghostwhite:16316671,gold:16766720,goldenrod:14329120,gray:8421504,green:32768,greenyellow:11403055,grey:8421504,honeydew:15794160,hotpink:16738740,indianred:13458524,indigo:4915330,ivory:16777200,khaki:15787660,lavender:15132410,lavenderblush:16773365,lawngreen:8190976,lemonchiffon:16775885,lightblue:11393254,lightcoral:15761536,lightcyan:14745599,lightgoldenrodyellow:16448210,lightgray:13882323,lightgreen:9498256,lightgrey:13882323,lightpink:16758465,lightsalmon:16752762,lightseagreen:2142890,lightskyblue:8900346,lightslategray:7833753,lightslategrey:7833753,lightsteelblue:11584734,lightyellow:16777184,lime:65280,limegreen:3329330,linen:16445670,magenta:16711935,maroon:8388608,mediumaquamarine:6737322,mediumblue:205,mediumorchid:12211667,mediumpurple:9662683,mediumseagreen:3978097,mediumslateblue:8087790,mediumspringgreen:64154,mediumturquoise:4772300,mediumvioletred:13047173,midnightblue:1644912,mintcream:16121850,mistyrose:16770273,moccasin:16770229,navajowhite:16768685,navy:128,oldlace:16643558,olive:8421376,olivedrab:7048739,orange:16753920,orangered:16729344,orchid:14315734,palegoldenrod:15657130,palegreen:10025880,paleturquoise:11529966,palevioletred:14381203,papayawhip:16773077,peachpuff:16767673,peru:13468991,pink:16761035,plum:14524637,powderblue:11591910,purple:8388736,rebeccapurple:6697881,red:16711680,rosybrown:12357519,royalblue:4286945,saddlebrown:9127187,salmon:16416882,sandybrown:16032864,seagreen:3050327,seashell:16774638,sienna:10506797,silver:12632256,skyblue:8900331,slateblue:6970061,slategray:7372944,slategrey:7372944,snow:16775930,springgreen:65407,steelblue:4620980,tan:13808780,teal:32896,thistle:14204888,tomato:16737095,turquoise:4251856,violet:15631086,wheat:16113331,white:16777215,whitesmoke:16119285,yellow:16776960,yellowgreen:10145074};function y(){return this.rgb().formatHex()}function w(){return this.rgb().formatRgb()}function m(t){var e,i;return t=(t+"").trim().toLowerCase(),(e=l.exec(t))?(i=e[1].length,e=parseInt(e[1],16),6===i?$(e):3===i?new M(e>>8&15|e>>4&240,e>>4&15|240&e,(15&e)<<4|15&e,1):8===i?N(e>>24&255,e>>16&255,e>>8&255,(255&e)/255):4===i?N(e>>12&15|e>>8&240,e>>8&15|e>>4&240,e>>4&15|240&e,((15&e)<<4|15&e)/255):null):(e=u.exec(t))?new M(e[1],e[2],e[3],1):(e=c.exec(t))?new M(255*e[1]/100,255*e[2]/100,255*e[3]/100,1):(e=g.exec(t))?N(e[1],e[2],e[3],e[4]):(e=p.exec(t))?N(255*e[1]/100,255*e[2]/100,255*e[3]/100,e[4]):(e=f.exec(t))?j(e[1],e[2]/100,e[3]/100,1):(e=d.exec(t))?j(e[1],e[2]/100,e[3]/100,e[4]):b.hasOwnProperty(t)?$(b[t]):"transparent"===t?new M(NaN,NaN,NaN,0):null}function $(t){return new M(t>>16&255,t>>8&255,255&t,1)}function N(t,e,i,n){return n<=0&&(t=e=i=NaN),new M(t,e,i,n)}function k(t){return t instanceof n||(t=m(t)),t?new M((t=t.rgb()).r,t.g,t.b,t.opacity):new M}function x(t,e,i,n){return 1===arguments.length?k(t):new M(t,e,i,null==n?1:n)}function M(t,e,i,n){this.r=+t,this.g=+e,this.b=+i,this.opacity=+n}function v(){return`#${E(this.r)}${E(this.g)}${E(this.b)}`}function q(){const t=H(this.opacity);return`${1===t?"rgb(":"rgba("}${R(this.r)}, ${R(this.g)}, ${R(this.b)}${1===t?")":`, ${t})`}`}function H(t){return isNaN(t)?1:Math.max(0,Math.min(1,t))}function R(t){return Math.max(0,Math.min(255,Math.round(t)||0))}function E(t){return((t=R(t))<16?"0":"")+t.toString(16)}function j(t,e,i,n){return n<=0?t=e=i=NaN:i<=0||i>=1?t=e=NaN:e<=0&&(t=NaN),new I(t,e,i,n)}function O(t){if(t instanceof I)return new I(t.h,t.s,t.l,t.opacity);if(t instanceof n||(t=m(t)),!t)return new I;if(t instanceof I)return t;var e=(t=t.rgb()).r/255,i=t.g/255,r=t.b/255,a=Math.min(e,i,r),s=Math.max(e,i,r),h=NaN,o=s-a,l=(s+a)/2;return o?(h=e===s?(i-r)/o+6*(i0&&l<1?0:h,new I(h,o,l,t.opacity)}function P(t,e,i,n){return 1===arguments.length?O(t):new I(t,e,i,null==n?1:n)}function I(t,e,i,n){this.h=+t,this.s=+e,this.l=+i,this.opacity=+n}function S(t){return(t=(t||0)%360)<0?t+360:t}function T(t){return Math.max(0,Math.min(1,t||0))}function _(t,e,i){return 255*(t<60?e+(i-e)*t/60:t<180?i:t<240?e+(i-e)*(240-t)/60:e)}e(n,m,{copy(t){return Object.assign(new this.constructor,this,t)},displayable(){return this.rgb().displayable()},hex:y,formatHex:y,formatHex8:function(){return this.rgb().formatHex8()},formatHsl:function(){return O(this).formatHsl()},formatRgb:w,toString:w}),e(M,x,i(n,{brighter(t){return t=null==t?a:Math.pow(a,t),new M(this.r*t,this.g*t,this.b*t,this.opacity)},darker(t){return t=null==t?r:Math.pow(r,t),new M(this.r*t,this.g*t,this.b*t,this.opacity)},rgb(){return this},clamp(){return new M(R(this.r),R(this.g),R(this.b),H(this.opacity))},displayable(){return-.5<=this.r&&this.r<255.5&&-.5<=this.g&&this.g<255.5&&-.5<=this.b&&this.b<255.5&&0<=this.opacity&&this.opacity<=1},hex:v,formatHex:v,formatHex8:function(){return`#${E(this.r)}${E(this.g)}${E(this.b)}${E(255*(isNaN(this.opacity)?1:this.opacity))}`},formatRgb:q,toString:q})),e(I,P,i(n,{brighter(t){return t=null==t?a:Math.pow(a,t),new I(this.h,this.s,this.l*t,this.opacity)},darker(t){return t=null==t?r:Math.pow(r,t),new I(this.h,this.s,this.l*t,this.opacity)},rgb(){var t=this.h%360+360*(this.h<0),e=isNaN(t)||isNaN(this.s)?0:this.s,i=this.l,n=i+(i<.5?i:1-i)*e,r=2*i-n;return new M(_(t>=240?t-240:t+120,r,n),_(t,r,n),_(t<120?t+240:t-120,r,n),this.opacity)},clamp(){return new I(S(this.h),T(this.s),T(this.l),H(this.opacity))},displayable(){return(0<=this.s&&this.s<=1||isNaN(this.s))&&0<=this.l&&this.l<=1&&0<=this.opacity&&this.opacity<=1},formatHsl(){const t=H(this.opacity);return`${1===t?"hsl(":"hsla("}${S(this.h)}, ${100*T(this.s)}%, ${100*T(this.l)}%${1===t?")":`, ${t})`}`}}));const z=Math.PI/180,C=180/Math.PI,L=.96422,A=.82521,B=4/29,D=6/29,F=3*D*D;function G(t){if(t instanceof K)return new K(t.l,t.a,t.b,t.opacity);if(t instanceof Z)return tt(t);t instanceof M||(t=k(t));var e,i,n=W(t.r),r=W(t.g),a=W(t.b),s=Q((.2225045*n+.7168786*r+.0606169*a)/1);return n===r&&r===a?e=i=s:(e=Q((.4360747*n+.3850649*r+.1430804*a)/L),i=Q((.0139322*n+.0971045*r+.7141733*a)/A)),new K(116*s-16,500*(e-s),200*(s-i),t.opacity)}function J(t,e,i,n){return 1===arguments.length?G(t):new K(t,e,i,null==n?1:n)}function K(t,e,i,n){this.l=+t,this.a=+e,this.b=+i,this.opacity=+n}function Q(t){return t>.008856451679035631?Math.pow(t,1/3):t/F+B}function U(t){return t>D?t*t*t:F*(t-B)}function V(t){return 255*(t<=.0031308?12.92*t:1.055*Math.pow(t,1/2.4)-.055)}function W(t){return(t/=255)<=.04045?t/12.92:Math.pow((t+.055)/1.055,2.4)}function X(t){if(t instanceof Z)return new Z(t.h,t.c,t.l,t.opacity);if(t instanceof K||(t=G(t)),0===t.a&&0===t.b)return new Z(NaN,0=12" + } +} diff --git a/frontend/node_modules/d3-color/src/color.js b/frontend/node_modules/d3-color/src/color.js new file mode 100644 index 0000000..75b68b4 --- /dev/null +++ b/frontend/node_modules/d3-color/src/color.js @@ -0,0 +1,396 @@ +import define, {extend} from "./define.js"; + +export function Color() {} + +export var darker = 0.7; +export var brighter = 1 / darker; + +var reI = "\\s*([+-]?\\d+)\\s*", + reN = "\\s*([+-]?(?:\\d*\\.)?\\d+(?:[eE][+-]?\\d+)?)\\s*", + reP = "\\s*([+-]?(?:\\d*\\.)?\\d+(?:[eE][+-]?\\d+)?)%\\s*", + reHex = /^#([0-9a-f]{3,8})$/, + reRgbInteger = new RegExp(`^rgb\\(${reI},${reI},${reI}\\)$`), + reRgbPercent = new RegExp(`^rgb\\(${reP},${reP},${reP}\\)$`), + reRgbaInteger = new RegExp(`^rgba\\(${reI},${reI},${reI},${reN}\\)$`), + reRgbaPercent = new RegExp(`^rgba\\(${reP},${reP},${reP},${reN}\\)$`), + reHslPercent = new RegExp(`^hsl\\(${reN},${reP},${reP}\\)$`), + reHslaPercent = new RegExp(`^hsla\\(${reN},${reP},${reP},${reN}\\)$`); + +var named = { + aliceblue: 0xf0f8ff, + antiquewhite: 0xfaebd7, + aqua: 0x00ffff, + aquamarine: 0x7fffd4, + azure: 0xf0ffff, + beige: 0xf5f5dc, + bisque: 0xffe4c4, + black: 0x000000, + blanchedalmond: 0xffebcd, + blue: 0x0000ff, + blueviolet: 0x8a2be2, + brown: 0xa52a2a, + burlywood: 0xdeb887, + cadetblue: 0x5f9ea0, + chartreuse: 0x7fff00, + chocolate: 0xd2691e, + coral: 0xff7f50, + cornflowerblue: 0x6495ed, + cornsilk: 0xfff8dc, + crimson: 0xdc143c, + cyan: 0x00ffff, + darkblue: 0x00008b, + darkcyan: 0x008b8b, + darkgoldenrod: 0xb8860b, + darkgray: 0xa9a9a9, + darkgreen: 0x006400, + darkgrey: 0xa9a9a9, + darkkhaki: 0xbdb76b, + darkmagenta: 0x8b008b, + darkolivegreen: 0x556b2f, + darkorange: 0xff8c00, + darkorchid: 0x9932cc, + darkred: 0x8b0000, + darksalmon: 0xe9967a, + darkseagreen: 0x8fbc8f, + darkslateblue: 0x483d8b, + darkslategray: 0x2f4f4f, + darkslategrey: 0x2f4f4f, + darkturquoise: 0x00ced1, + darkviolet: 0x9400d3, + deeppink: 0xff1493, + deepskyblue: 0x00bfff, + dimgray: 0x696969, + dimgrey: 0x696969, + dodgerblue: 0x1e90ff, + firebrick: 0xb22222, + floralwhite: 0xfffaf0, + forestgreen: 0x228b22, + fuchsia: 0xff00ff, + gainsboro: 0xdcdcdc, + ghostwhite: 0xf8f8ff, + gold: 0xffd700, + goldenrod: 0xdaa520, + gray: 0x808080, + green: 0x008000, + greenyellow: 0xadff2f, + grey: 0x808080, + honeydew: 0xf0fff0, + hotpink: 0xff69b4, + indianred: 0xcd5c5c, + indigo: 0x4b0082, + ivory: 0xfffff0, + khaki: 0xf0e68c, + lavender: 0xe6e6fa, + lavenderblush: 0xfff0f5, + lawngreen: 0x7cfc00, + lemonchiffon: 0xfffacd, + lightblue: 0xadd8e6, + lightcoral: 0xf08080, + lightcyan: 0xe0ffff, + lightgoldenrodyellow: 0xfafad2, + lightgray: 0xd3d3d3, + lightgreen: 0x90ee90, + lightgrey: 0xd3d3d3, + lightpink: 0xffb6c1, + lightsalmon: 0xffa07a, + lightseagreen: 0x20b2aa, + lightskyblue: 0x87cefa, + lightslategray: 0x778899, + lightslategrey: 0x778899, + lightsteelblue: 0xb0c4de, + lightyellow: 0xffffe0, + lime: 0x00ff00, + limegreen: 0x32cd32, + linen: 0xfaf0e6, + magenta: 0xff00ff, + maroon: 0x800000, + mediumaquamarine: 0x66cdaa, + mediumblue: 0x0000cd, + mediumorchid: 0xba55d3, + mediumpurple: 0x9370db, + mediumseagreen: 0x3cb371, + mediumslateblue: 0x7b68ee, + mediumspringgreen: 0x00fa9a, + mediumturquoise: 0x48d1cc, + mediumvioletred: 0xc71585, + midnightblue: 0x191970, + mintcream: 0xf5fffa, + mistyrose: 0xffe4e1, + moccasin: 0xffe4b5, + navajowhite: 0xffdead, + navy: 0x000080, + oldlace: 0xfdf5e6, + olive: 0x808000, + olivedrab: 0x6b8e23, + orange: 0xffa500, + orangered: 0xff4500, + orchid: 0xda70d6, + palegoldenrod: 0xeee8aa, + palegreen: 0x98fb98, + paleturquoise: 0xafeeee, + palevioletred: 0xdb7093, + papayawhip: 0xffefd5, + peachpuff: 0xffdab9, + peru: 0xcd853f, + pink: 0xffc0cb, + plum: 0xdda0dd, + powderblue: 0xb0e0e6, + purple: 0x800080, + rebeccapurple: 0x663399, + red: 0xff0000, + rosybrown: 0xbc8f8f, + royalblue: 0x4169e1, + saddlebrown: 0x8b4513, + salmon: 0xfa8072, + sandybrown: 0xf4a460, + seagreen: 0x2e8b57, + seashell: 0xfff5ee, + sienna: 0xa0522d, + silver: 0xc0c0c0, + skyblue: 0x87ceeb, + slateblue: 0x6a5acd, + slategray: 0x708090, + slategrey: 0x708090, + snow: 0xfffafa, + springgreen: 0x00ff7f, + steelblue: 0x4682b4, + tan: 0xd2b48c, + teal: 0x008080, + thistle: 0xd8bfd8, + tomato: 0xff6347, + turquoise: 0x40e0d0, + violet: 0xee82ee, + wheat: 0xf5deb3, + white: 0xffffff, + whitesmoke: 0xf5f5f5, + yellow: 0xffff00, + yellowgreen: 0x9acd32 +}; + +define(Color, color, { + copy(channels) { + return Object.assign(new this.constructor, this, channels); + }, + displayable() { + return this.rgb().displayable(); + }, + hex: color_formatHex, // Deprecated! Use color.formatHex. + formatHex: color_formatHex, + formatHex8: color_formatHex8, + formatHsl: color_formatHsl, + formatRgb: color_formatRgb, + toString: color_formatRgb +}); + +function color_formatHex() { + return this.rgb().formatHex(); +} + +function color_formatHex8() { + return this.rgb().formatHex8(); +} + +function color_formatHsl() { + return hslConvert(this).formatHsl(); +} + +function color_formatRgb() { + return this.rgb().formatRgb(); +} + +export default function color(format) { + var m, l; + format = (format + "").trim().toLowerCase(); + return (m = reHex.exec(format)) ? (l = m[1].length, m = parseInt(m[1], 16), l === 6 ? rgbn(m) // #ff0000 + : l === 3 ? new Rgb((m >> 8 & 0xf) | (m >> 4 & 0xf0), (m >> 4 & 0xf) | (m & 0xf0), ((m & 0xf) << 4) | (m & 0xf), 1) // #f00 + : l === 8 ? rgba(m >> 24 & 0xff, m >> 16 & 0xff, m >> 8 & 0xff, (m & 0xff) / 0xff) // #ff000000 + : l === 4 ? rgba((m >> 12 & 0xf) | (m >> 8 & 0xf0), (m >> 8 & 0xf) | (m >> 4 & 0xf0), (m >> 4 & 0xf) | (m & 0xf0), (((m & 0xf) << 4) | (m & 0xf)) / 0xff) // #f000 + : null) // invalid hex + : (m = reRgbInteger.exec(format)) ? new Rgb(m[1], m[2], m[3], 1) // rgb(255, 0, 0) + : (m = reRgbPercent.exec(format)) ? new Rgb(m[1] * 255 / 100, m[2] * 255 / 100, m[3] * 255 / 100, 1) // rgb(100%, 0%, 0%) + : (m = reRgbaInteger.exec(format)) ? rgba(m[1], m[2], m[3], m[4]) // rgba(255, 0, 0, 1) + : (m = reRgbaPercent.exec(format)) ? rgba(m[1] * 255 / 100, m[2] * 255 / 100, m[3] * 255 / 100, m[4]) // rgb(100%, 0%, 0%, 1) + : (m = reHslPercent.exec(format)) ? hsla(m[1], m[2] / 100, m[3] / 100, 1) // hsl(120, 50%, 50%) + : (m = reHslaPercent.exec(format)) ? hsla(m[1], m[2] / 100, m[3] / 100, m[4]) // hsla(120, 50%, 50%, 1) + : named.hasOwnProperty(format) ? rgbn(named[format]) // eslint-disable-line no-prototype-builtins + : format === "transparent" ? new Rgb(NaN, NaN, NaN, 0) + : null; +} + +function rgbn(n) { + return new Rgb(n >> 16 & 0xff, n >> 8 & 0xff, n & 0xff, 1); +} + +function rgba(r, g, b, a) { + if (a <= 0) r = g = b = NaN; + return new Rgb(r, g, b, a); +} + +export function rgbConvert(o) { + if (!(o instanceof Color)) o = color(o); + if (!o) return new Rgb; + o = o.rgb(); + return new Rgb(o.r, o.g, o.b, o.opacity); +} + +export function rgb(r, g, b, opacity) { + return arguments.length === 1 ? rgbConvert(r) : new Rgb(r, g, b, opacity == null ? 1 : opacity); +} + +export function Rgb(r, g, b, opacity) { + this.r = +r; + this.g = +g; + this.b = +b; + this.opacity = +opacity; +} + +define(Rgb, rgb, extend(Color, { + brighter(k) { + k = k == null ? brighter : Math.pow(brighter, k); + return new Rgb(this.r * k, this.g * k, this.b * k, this.opacity); + }, + darker(k) { + k = k == null ? darker : Math.pow(darker, k); + return new Rgb(this.r * k, this.g * k, this.b * k, this.opacity); + }, + rgb() { + return this; + }, + clamp() { + return new Rgb(clampi(this.r), clampi(this.g), clampi(this.b), clampa(this.opacity)); + }, + displayable() { + return (-0.5 <= this.r && this.r < 255.5) + && (-0.5 <= this.g && this.g < 255.5) + && (-0.5 <= this.b && this.b < 255.5) + && (0 <= this.opacity && this.opacity <= 1); + }, + hex: rgb_formatHex, // Deprecated! Use color.formatHex. + formatHex: rgb_formatHex, + formatHex8: rgb_formatHex8, + formatRgb: rgb_formatRgb, + toString: rgb_formatRgb +})); + +function rgb_formatHex() { + return `#${hex(this.r)}${hex(this.g)}${hex(this.b)}`; +} + +function rgb_formatHex8() { + return `#${hex(this.r)}${hex(this.g)}${hex(this.b)}${hex((isNaN(this.opacity) ? 1 : this.opacity) * 255)}`; +} + +function rgb_formatRgb() { + const a = clampa(this.opacity); + return `${a === 1 ? "rgb(" : "rgba("}${clampi(this.r)}, ${clampi(this.g)}, ${clampi(this.b)}${a === 1 ? ")" : `, ${a})`}`; +} + +function clampa(opacity) { + return isNaN(opacity) ? 1 : Math.max(0, Math.min(1, opacity)); +} + +function clampi(value) { + return Math.max(0, Math.min(255, Math.round(value) || 0)); +} + +function hex(value) { + value = clampi(value); + return (value < 16 ? "0" : "") + value.toString(16); +} + +function hsla(h, s, l, a) { + if (a <= 0) h = s = l = NaN; + else if (l <= 0 || l >= 1) h = s = NaN; + else if (s <= 0) h = NaN; + return new Hsl(h, s, l, a); +} + +export function hslConvert(o) { + if (o instanceof Hsl) return new Hsl(o.h, o.s, o.l, o.opacity); + if (!(o instanceof Color)) o = color(o); + if (!o) return new Hsl; + if (o instanceof Hsl) return o; + o = o.rgb(); + var r = o.r / 255, + g = o.g / 255, + b = o.b / 255, + min = Math.min(r, g, b), + max = Math.max(r, g, b), + h = NaN, + s = max - min, + l = (max + min) / 2; + if (s) { + if (r === max) h = (g - b) / s + (g < b) * 6; + else if (g === max) h = (b - r) / s + 2; + else h = (r - g) / s + 4; + s /= l < 0.5 ? max + min : 2 - max - min; + h *= 60; + } else { + s = l > 0 && l < 1 ? 0 : h; + } + return new Hsl(h, s, l, o.opacity); +} + +export function hsl(h, s, l, opacity) { + return arguments.length === 1 ? hslConvert(h) : new Hsl(h, s, l, opacity == null ? 1 : opacity); +} + +function Hsl(h, s, l, opacity) { + this.h = +h; + this.s = +s; + this.l = +l; + this.opacity = +opacity; +} + +define(Hsl, hsl, extend(Color, { + brighter(k) { + k = k == null ? brighter : Math.pow(brighter, k); + return new Hsl(this.h, this.s, this.l * k, this.opacity); + }, + darker(k) { + k = k == null ? darker : Math.pow(darker, k); + return new Hsl(this.h, this.s, this.l * k, this.opacity); + }, + rgb() { + var h = this.h % 360 + (this.h < 0) * 360, + s = isNaN(h) || isNaN(this.s) ? 0 : this.s, + l = this.l, + m2 = l + (l < 0.5 ? l : 1 - l) * s, + m1 = 2 * l - m2; + return new Rgb( + hsl2rgb(h >= 240 ? h - 240 : h + 120, m1, m2), + hsl2rgb(h, m1, m2), + hsl2rgb(h < 120 ? h + 240 : h - 120, m1, m2), + this.opacity + ); + }, + clamp() { + return new Hsl(clamph(this.h), clampt(this.s), clampt(this.l), clampa(this.opacity)); + }, + displayable() { + return (0 <= this.s && this.s <= 1 || isNaN(this.s)) + && (0 <= this.l && this.l <= 1) + && (0 <= this.opacity && this.opacity <= 1); + }, + formatHsl() { + const a = clampa(this.opacity); + return `${a === 1 ? "hsl(" : "hsla("}${clamph(this.h)}, ${clampt(this.s) * 100}%, ${clampt(this.l) * 100}%${a === 1 ? ")" : `, ${a})`}`; + } +})); + +function clamph(value) { + value = (value || 0) % 360; + return value < 0 ? value + 360 : value; +} + +function clampt(value) { + return Math.max(0, Math.min(1, value || 0)); +} + +/* From FvD 13.37, CSS Color Module Level 3 */ +function hsl2rgb(h, m1, m2) { + return (h < 60 ? m1 + (m2 - m1) * h / 60 + : h < 180 ? m2 + : h < 240 ? m1 + (m2 - m1) * (240 - h) / 60 + : m1) * 255; +} diff --git a/frontend/node_modules/d3-color/src/cubehelix.js b/frontend/node_modules/d3-color/src/cubehelix.js new file mode 100644 index 0000000..b3cf696 --- /dev/null +++ b/frontend/node_modules/d3-color/src/cubehelix.js @@ -0,0 +1,61 @@ +import define, {extend} from "./define.js"; +import {Color, rgbConvert, Rgb, darker, brighter} from "./color.js"; +import {degrees, radians} from "./math.js"; + +var A = -0.14861, + B = +1.78277, + C = -0.29227, + D = -0.90649, + E = +1.97294, + ED = E * D, + EB = E * B, + BC_DA = B * C - D * A; + +function cubehelixConvert(o) { + if (o instanceof Cubehelix) return new Cubehelix(o.h, o.s, o.l, o.opacity); + if (!(o instanceof Rgb)) o = rgbConvert(o); + var r = o.r / 255, + g = o.g / 255, + b = o.b / 255, + l = (BC_DA * b + ED * r - EB * g) / (BC_DA + ED - EB), + bl = b - l, + k = (E * (g - l) - C * bl) / D, + s = Math.sqrt(k * k + bl * bl) / (E * l * (1 - l)), // NaN if l=0 or l=1 + h = s ? Math.atan2(k, bl) * degrees - 120 : NaN; + return new Cubehelix(h < 0 ? h + 360 : h, s, l, o.opacity); +} + +export default function cubehelix(h, s, l, opacity) { + return arguments.length === 1 ? cubehelixConvert(h) : new Cubehelix(h, s, l, opacity == null ? 1 : opacity); +} + +export function Cubehelix(h, s, l, opacity) { + this.h = +h; + this.s = +s; + this.l = +l; + this.opacity = +opacity; +} + +define(Cubehelix, cubehelix, extend(Color, { + brighter(k) { + k = k == null ? brighter : Math.pow(brighter, k); + return new Cubehelix(this.h, this.s, this.l * k, this.opacity); + }, + darker(k) { + k = k == null ? darker : Math.pow(darker, k); + return new Cubehelix(this.h, this.s, this.l * k, this.opacity); + }, + rgb() { + var h = isNaN(this.h) ? 0 : (this.h + 120) * radians, + l = +this.l, + a = isNaN(this.s) ? 0 : this.s * l * (1 - l), + cosh = Math.cos(h), + sinh = Math.sin(h); + return new Rgb( + 255 * (l + a * (A * cosh + B * sinh)), + 255 * (l + a * (C * cosh + D * sinh)), + 255 * (l + a * (E * cosh)), + this.opacity + ); + } +})); diff --git a/frontend/node_modules/d3-color/src/define.js b/frontend/node_modules/d3-color/src/define.js new file mode 100644 index 0000000..2bba2d3 --- /dev/null +++ b/frontend/node_modules/d3-color/src/define.js @@ -0,0 +1,10 @@ +export default function(constructor, factory, prototype) { + constructor.prototype = factory.prototype = prototype; + prototype.constructor = constructor; +} + +export function extend(parent, definition) { + var prototype = Object.create(parent.prototype); + for (var key in definition) prototype[key] = definition[key]; + return prototype; +} diff --git a/frontend/node_modules/d3-color/src/index.js b/frontend/node_modules/d3-color/src/index.js new file mode 100644 index 0000000..831cf52 --- /dev/null +++ b/frontend/node_modules/d3-color/src/index.js @@ -0,0 +1,3 @@ +export {default as color, rgb, hsl} from "./color.js"; +export {default as lab, hcl, lch, gray} from "./lab.js"; +export {default as cubehelix} from "./cubehelix.js"; diff --git a/frontend/node_modules/d3-color/src/lab.js b/frontend/node_modules/d3-color/src/lab.js new file mode 100644 index 0000000..88c46e8 --- /dev/null +++ b/frontend/node_modules/d3-color/src/lab.js @@ -0,0 +1,123 @@ +import define, {extend} from "./define.js"; +import {Color, rgbConvert, Rgb} from "./color.js"; +import {degrees, radians} from "./math.js"; + +// https://observablehq.com/@mbostock/lab-and-rgb +const K = 18, + Xn = 0.96422, + Yn = 1, + Zn = 0.82521, + t0 = 4 / 29, + t1 = 6 / 29, + t2 = 3 * t1 * t1, + t3 = t1 * t1 * t1; + +function labConvert(o) { + if (o instanceof Lab) return new Lab(o.l, o.a, o.b, o.opacity); + if (o instanceof Hcl) return hcl2lab(o); + if (!(o instanceof Rgb)) o = rgbConvert(o); + var r = rgb2lrgb(o.r), + g = rgb2lrgb(o.g), + b = rgb2lrgb(o.b), + y = xyz2lab((0.2225045 * r + 0.7168786 * g + 0.0606169 * b) / Yn), x, z; + if (r === g && g === b) x = z = y; else { + x = xyz2lab((0.4360747 * r + 0.3850649 * g + 0.1430804 * b) / Xn); + z = xyz2lab((0.0139322 * r + 0.0971045 * g + 0.7141733 * b) / Zn); + } + return new Lab(116 * y - 16, 500 * (x - y), 200 * (y - z), o.opacity); +} + +export function gray(l, opacity) { + return new Lab(l, 0, 0, opacity == null ? 1 : opacity); +} + +export default function lab(l, a, b, opacity) { + return arguments.length === 1 ? labConvert(l) : new Lab(l, a, b, opacity == null ? 1 : opacity); +} + +export function Lab(l, a, b, opacity) { + this.l = +l; + this.a = +a; + this.b = +b; + this.opacity = +opacity; +} + +define(Lab, lab, extend(Color, { + brighter(k) { + return new Lab(this.l + K * (k == null ? 1 : k), this.a, this.b, this.opacity); + }, + darker(k) { + return new Lab(this.l - K * (k == null ? 1 : k), this.a, this.b, this.opacity); + }, + rgb() { + var y = (this.l + 16) / 116, + x = isNaN(this.a) ? y : y + this.a / 500, + z = isNaN(this.b) ? y : y - this.b / 200; + x = Xn * lab2xyz(x); + y = Yn * lab2xyz(y); + z = Zn * lab2xyz(z); + return new Rgb( + lrgb2rgb( 3.1338561 * x - 1.6168667 * y - 0.4906146 * z), + lrgb2rgb(-0.9787684 * x + 1.9161415 * y + 0.0334540 * z), + lrgb2rgb( 0.0719453 * x - 0.2289914 * y + 1.4052427 * z), + this.opacity + ); + } +})); + +function xyz2lab(t) { + return t > t3 ? Math.pow(t, 1 / 3) : t / t2 + t0; +} + +function lab2xyz(t) { + return t > t1 ? t * t * t : t2 * (t - t0); +} + +function lrgb2rgb(x) { + return 255 * (x <= 0.0031308 ? 12.92 * x : 1.055 * Math.pow(x, 1 / 2.4) - 0.055); +} + +function rgb2lrgb(x) { + return (x /= 255) <= 0.04045 ? x / 12.92 : Math.pow((x + 0.055) / 1.055, 2.4); +} + +function hclConvert(o) { + if (o instanceof Hcl) return new Hcl(o.h, o.c, o.l, o.opacity); + if (!(o instanceof Lab)) o = labConvert(o); + if (o.a === 0 && o.b === 0) return new Hcl(NaN, 0 < o.l && o.l < 100 ? 0 : NaN, o.l, o.opacity); + var h = Math.atan2(o.b, o.a) * degrees; + return new Hcl(h < 0 ? h + 360 : h, Math.sqrt(o.a * o.a + o.b * o.b), o.l, o.opacity); +} + +export function lch(l, c, h, opacity) { + return arguments.length === 1 ? hclConvert(l) : new Hcl(h, c, l, opacity == null ? 1 : opacity); +} + +export function hcl(h, c, l, opacity) { + return arguments.length === 1 ? hclConvert(h) : new Hcl(h, c, l, opacity == null ? 1 : opacity); +} + +export function Hcl(h, c, l, opacity) { + this.h = +h; + this.c = +c; + this.l = +l; + this.opacity = +opacity; +} + +function hcl2lab(o) { + if (isNaN(o.h)) return new Lab(o.l, 0, 0, o.opacity); + var h = o.h * radians; + return new Lab(o.l, Math.cos(h) * o.c, Math.sin(h) * o.c, o.opacity); +} + +define(Hcl, hcl, extend(Color, { + brighter(k) { + return new Hcl(this.h, this.c, this.l + K * (k == null ? 1 : k), this.opacity); + }, + darker(k) { + return new Hcl(this.h, this.c, this.l - K * (k == null ? 1 : k), this.opacity); + }, + rgb() { + return hcl2lab(this).rgb(); + } +})); diff --git a/frontend/node_modules/d3-color/src/math.js b/frontend/node_modules/d3-color/src/math.js new file mode 100644 index 0000000..66b172e --- /dev/null +++ b/frontend/node_modules/d3-color/src/math.js @@ -0,0 +1,2 @@ +export const radians = Math.PI / 180; +export const degrees = 180 / Math.PI; diff --git a/frontend/node_modules/d3-contour/LICENSE b/frontend/node_modules/d3-contour/LICENSE new file mode 100644 index 0000000..fa068a4 --- /dev/null +++ b/frontend/node_modules/d3-contour/LICENSE @@ -0,0 +1,13 @@ +Copyright 2012-2023 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-contour/README.md b/frontend/node_modules/d3-contour/README.md new file mode 100644 index 0000000..a40ac45 --- /dev/null +++ b/frontend/node_modules/d3-contour/README.md @@ -0,0 +1,187 @@ +# d3-contour + +This library computes contour polygons by applying [marching squares](https://en.wikipedia.org/wiki/Marching_squares) to a rectangular array of numeric values. For example, here is Maungawhau’s topology (the classic `volcano` dataset and `terrain.colors` from R): + +[Volcano Contours](https://observablehq.com/@d3/volcano-contours) + +For each [threshold value](#contours_thresholds), the [contour generator](#_contours) constructs a GeoJSON MultiPolygon geometry object representing the area where the input values are greater than or equal to the threshold value. The geometry is in planar coordinates, where ⟨i + 0.5, j + 0.5⟩ corresponds to element i + jn in the input values array. Here is an example that loads a GeoTIFF of surface temperatures, and another that blurs a noisy monochrome PNG to produce smooth contours of cloud fraction: + +[GeoTiff Contours](https://observablehq.com/@d3/geotiff-contours) +[Cloud Contours](https://observablehq.com/@d3/cloud-contours) + +Since the contour polygons are GeoJSON, you can transform and display them using standard tools; see [d3.geoPath](https://github.com/d3/d3-geo/blob/main/README.md#geoPath), [d3.geoProject](https://github.com/d3/d3-geo-projection/blob/main/README.md#geoProject) and [d3.geoStitch](https://github.com/d3/d3-geo-projection/blob/main/README.md#geoStitch), for example. Here the above contours of surface temperature are displayed in the Natural Earth projection: + +[GeoTiff Contours II](https://observablehq.com/@d3/geotiff-contours-ii) + +Contour plots can also visualize continuous functions by sampling. Here is the Goldstein–Price function (a test function for global optimization) and a trippy animation of *sin*(*x* + *y*)*sin*(*x* - *y*): + +[Contours](https://observablehq.com/@d3/contours) +[Animated Contours](https://observablehq.com/@d3/animated-contours) + +Contours can also show the [estimated density](#density-estimation) of point clouds, which is especially useful to avoid overplotting in large datasets. This library implements fast two-dimensional kernel density estimation; see [d3.contourDensity](#contourDensity). Here is a scatterplot showing the relationship between the idle duration and eruption duration for Old Faithful: + +[Density Contours](https://observablehq.com/@d3/density-contours) + +And here is a density contour plot showing the relationship between the weight and price of 53,940 diamonds: + +[Density Contours](https://observablehq.com/@d3/density-contours) + +## Installing + +If you use npm, `npm install d3-contour`. You can also download the [latest release on GitHub](https://github.com/d3/d3-contour/releases/latest). For vanilla HTML in modern browsers, import d3-contour from jsDelivr: + +```html + +``` + +For legacy environments, you can load d3-contour’s UMD bundle; a `d3` global is exported: + +```html + + + +``` + +## API Reference + +# d3.contours() · [Source](./src/contours.js), [Examples](https://observablehq.com/collection/@d3/d3-contour) + +Constructs a new contour generator with the default settings. + +# contours(values) · [Source](./src/contours.js) + +Computes the contours for the given array of *values*, returning an array of [GeoJSON](http://geojson.org/geojson-spec.html) [MultiPolygon](http://geojson.org/geojson-spec.html#multipolygon) [geometry objects](http://geojson.org/geojson-spec.html#geometry-objects). Each geometry object represents the area where the input values are greater than or equal to the corresponding [threshold value](#contours_thresholds); the threshold value for each geometry object is exposed as geometry.value. + +The input *values* must be an array of length n×m where [n, m] is the contour generator’s [size](#contours_size); furthermore, each values[i + jn] must represent the value at the position ⟨i, j⟩. For example, to construct a 256×256 grid for the [Goldstein–Price function](https://en.wikipedia.org/wiki/Test_functions_for_optimization) where -2 ≤ x ≤ 2 and -2 ≤ y ≤ 1: + +```js +var n = 256, m = 256, values = new Array(n * m); +for (var j = 0.5, k = 0; j < m; ++j) { + for (var i = 0.5; i < n; ++i, ++k) { + values[k] = goldsteinPrice(i / n * 4 - 2, 1 - j / m * 3); + } +} + +function goldsteinPrice(x, y) { + return (1 + Math.pow(x + y + 1, 2) * (19 - 14 * x + 3 * x * x - 14 * y + 6 * x * x + 3 * y * y)) + * (30 + Math.pow(2 * x - 3 * y, 2) * (18 - 32 * x + 12 * x * x + 48 * y - 36 * x * y + 27 * y * y)); +} +``` + +The returned geometry objects are typically passed to [d3.geoPath](https://github.com/d3/d3-geo/blob/main/README.md#geoPath) to display, using null or [d3.geoIdentity](https://github.com/d3/d3-geo/blob/main/README.md#geoIdentity) as the associated projection. + +# contours.contour(values, threshold) · [Source](./src/contours.js), [Examples](https://observablehq.com/@d3/animated-contours) + +Computes a single contour, returning a [GeoJSON](http://geojson.org/geojson-spec.html) [MultiPolygon](http://geojson.org/geojson-spec.html#multipolygon) [geometry object](http://geojson.org/geojson-spec.html#geometry-objects) representing the area where the input values are greater than or equal to the given [*threshold* value](#contours_thresholds); the threshold value for each geometry object is exposed as geometry.value. + +The input *values* must be an array of length n×m where [n, m] is the contour generator’s [size](#contours_size); furthermore, each values[i + jn] must represent the value at the position ⟨i, j⟩. See [*contours*](#_contours) for an example. + +# contours.size([size]) · [Source](./src/contours.js), [Examples](https://observablehq.com/@d3/animated-contours) + +If *size* is specified, sets the expected size of the input *values* grid to the [contour generator](#_contour) and returns the contour generator. The *size* is specified as an array \[n, m\] where n is the number of columns in the grid and m is the number of rows; *n* and *m* must be positive integers. If *size* is not specified, returns the current size which defaults to [1, 1]. + +# contours.smooth([smooth]) · [Source](./src/contours.js), [Examples](https://observablehq.com/@d3/contours-smooth) + +If *smooth* is specified, sets whether or not the generated contour polygons are smoothed using linear interpolation. If *smooth* is not specified, returns the current smoothing flag, which defaults to true. + +# contours.thresholds([thresholds]) · [Source](./src/contours.js), [Examples](https://observablehq.com/@d3/volcano-contours) + +If *thresholds* is specified, sets the threshold generator to the specified function or array and returns this contour generator. If *thresholds* is not specified, returns the current threshold generator, which by default implements [Sturges’ formula](https://github.com/d3/d3-array/blob/main/README.md#thresholdSturges). + +Thresholds are defined as an array of values [*x0*, *x1*, …]. The first [generated contour](#_contour) corresponds to the area where the input values are greater than or equal to *x0*; the second contour corresponds to the area where the input values are greater than or equal to *x1*, and so on. Thus, there is exactly one generated MultiPolygon geometry object for each specified threshold value; the threshold value is exposed as geometry.value. + +If a *count* is specified instead of an array of *thresholds*, then the input values’ [extent](https://github.com/d3/d3-array/blob/main/README.md#extent) will be uniformly divided into approximately *count* bins; see [d3.ticks](https://github.com/d3/d3-array/blob/main/README.md#ticks). + +### Density Estimation + +# d3.contourDensity() · [Source](./src/density.js), [Examples](https://observablehq.com/@d3/density-contours) + +Constructs a new density estimator with the default settings. + +# density(data) · [Source](./src/density.js) + +Estimates the density contours for the given array of *data*, returning an array of [GeoJSON](http://geojson.org/geojson-spec.html) [MultiPolygon](http://geojson.org/geojson-spec.html#multipolygon) [geometry objects](http://geojson.org/geojson-spec.html#geometry-objects). Each geometry object represents the area where the estimated number of points per square pixel is greater than or equal to the corresponding [threshold value](#density_thresholds); the threshold value for each geometry object is exposed as geometry.value. The returned geometry objects are typically passed to [d3.geoPath](https://github.com/d3/d3-geo/blob/main/README.md#geoPath) to display, using null or [d3.geoIdentity](https://github.com/d3/d3-geo/blob/main/README.md#geoIdentity) as the associated projection. See also [d3.contours](#contours). + +The *x*- and *y*-coordinate for each data point are computed using [*density*.x](#density_x) and [*density*.y](#density_y). In addition, [*density*.weight](#density_weight) indicates the relative contribution of each data point (default 1). The generated contours are only accurate within the estimator’s [defined size](#density_size). + +# density.x([x]) · [Source](./src/density.js), [Examples](https://observablehq.com/@d3/density-contours) + +If *x* is specified, sets the *x*-coordinate accessor. If *x* is not specified, returns the current *x*-coordinate accessor, which defaults to: + +```js +function x(d) { + return d[0]; +} +``` + +# density.y([y]) · [Source](./src/density.js), [Examples](https://observablehq.com/@d3/density-contours) + +If *y* is specified, sets the *y*-coordinate accessor. If *y* is not specified, returns the current *y*-coordinate accessor, which defaults to: + +```js +function y(d) { + return d[1]; +} +``` + +# density.weight([weight]) · [Source](./src/density.js) + +If *weight* is specified, sets the accessor for point weights. If *weight* is not specified, returns the current point weight accessor, which defaults to: + +```js +function weight() { + return 1; +} +``` + +# density.size([size]) · [Source](./src/density.js), [Examples](https://observablehq.com/@d3/density-contours) + +If *size* is specified, sets the size of the density estimator to the specified bounds and returns the estimator. The *size* is specified as an array \[width, height\], where width is the maximum *x*-value and height is the maximum *y*-value. If *size* is not specified, returns the current size which defaults to [960, 500]. The [estimated density contours](#_density) are only accurate within the defined size. + +# density.cellSize([cellSize]) · [Source](./src/density.js) + +If *cellSize* is specified, sets the size of individual cells in the underlying bin grid to the specified positive integer and returns the estimator. If *cellSize* is not specified, returns the current cell size, which defaults to 4. The cell size is rounded down to the nearest power of two. Smaller cells produce more detailed contour polygons, but are more expensive to compute. + +# density.thresholds([thresholds]) · [Source](./src/density.js), [Examples](https://observablehq.com/@d3/density-contours) + +If *thresholds* is specified, sets the threshold generator to the specified function or array and returns this contour generator. If *thresholds* is not specified, returns the current threshold generator, which by default generates about twenty nicely-rounded density thresholds. + +Thresholds are defined as an array of values [*x0*, *x1*, …]. The first [generated density contour](#_density) corresponds to the area where the estimated density is greater than or equal to *x0*; the second contour corresponds to the area where the estimated density is greater than or equal to *x1*, and so on. Thus, there is exactly one generated MultiPolygon geometry object for each specified threshold value; the threshold value is exposed as geometry.value. The first value *x0* should typically be greater than zero. + +If a *count* is specified instead of an array of *thresholds*, then approximately *count* uniformly-spaced nicely-rounded thresholds will be generated; see [d3.ticks](https://github.com/d3/d3-array/blob/main/README.md#ticks). + +# density.bandwidth([bandwidth]) · [Source](./src/density.js), [Examples](https://observablehq.com/@d3/density-contours) + +If *bandwidth* is specified, sets the bandwidth (the standard deviation) of the Gaussian kernel and returns the estimate. If *bandwidth* is not specified, returns the current bandwidth, which defaults to 20.4939…. The specified *bandwidth* is currently rounded to the nearest supported value by this implementation, and must be nonnegative. + +# density.contours(data) · [Source](./src/density.js), [Examples](https://observablehq.com/@d3/density-contours-data) + +Return a *contour*(*value*) function that can be used to compute an arbitrary contour on the given data without needing to recompute the underlying grid. The returned *contour* function also exposes a *contour*.max value which represents the maximum density of the grid. diff --git a/frontend/node_modules/d3-contour/dist/d3-contour.js b/frontend/node_modules/d3-contour/dist/d3-contour.js new file mode 100644 index 0000000..9b19050 --- /dev/null +++ b/frontend/node_modules/d3-contour/dist/d3-contour.js @@ -0,0 +1,420 @@ +// https://d3js.org/d3-contour/ v4.0.2 Copyright 2012-2023 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-array')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-array'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3)); +})(this, (function (exports, d3Array) { 'use strict'; + +var array = Array.prototype; + +var slice = array.slice; + +function ascending(a, b) { + return a - b; +} + +function area(ring) { + var i = 0, n = ring.length, area = ring[n - 1][1] * ring[0][0] - ring[n - 1][0] * ring[0][1]; + while (++i < n) area += ring[i - 1][1] * ring[i][0] - ring[i - 1][0] * ring[i][1]; + return area; +} + +var constant = x => () => x; + +function contains(ring, hole) { + var i = -1, n = hole.length, c; + while (++i < n) if (c = ringContains(ring, hole[i])) return c; + return 0; +} + +function ringContains(ring, point) { + var x = point[0], y = point[1], contains = -1; + for (var i = 0, n = ring.length, j = n - 1; i < n; j = i++) { + var pi = ring[i], xi = pi[0], yi = pi[1], pj = ring[j], xj = pj[0], yj = pj[1]; + if (segmentContains(pi, pj, point)) return 0; + if (((yi > y) !== (yj > y)) && ((x < (xj - xi) * (y - yi) / (yj - yi) + xi))) contains = -contains; + } + return contains; +} + +function segmentContains(a, b, c) { + var i; return collinear(a, b, c) && within(a[i = +(a[0] === b[0])], c[i], b[i]); +} + +function collinear(a, b, c) { + return (b[0] - a[0]) * (c[1] - a[1]) === (c[0] - a[0]) * (b[1] - a[1]); +} + +function within(p, q, r) { + return p <= q && q <= r || r <= q && q <= p; +} + +function noop() {} + +var cases = [ + [], + [[[1.0, 1.5], [0.5, 1.0]]], + [[[1.5, 1.0], [1.0, 1.5]]], + [[[1.5, 1.0], [0.5, 1.0]]], + [[[1.0, 0.5], [1.5, 1.0]]], + [[[1.0, 1.5], [0.5, 1.0]], [[1.0, 0.5], [1.5, 1.0]]], + [[[1.0, 0.5], [1.0, 1.5]]], + [[[1.0, 0.5], [0.5, 1.0]]], + [[[0.5, 1.0], [1.0, 0.5]]], + [[[1.0, 1.5], [1.0, 0.5]]], + [[[0.5, 1.0], [1.0, 0.5]], [[1.5, 1.0], [1.0, 1.5]]], + [[[1.5, 1.0], [1.0, 0.5]]], + [[[0.5, 1.0], [1.5, 1.0]]], + [[[1.0, 1.5], [1.5, 1.0]]], + [[[0.5, 1.0], [1.0, 1.5]]], + [] +]; + +function Contours() { + var dx = 1, + dy = 1, + threshold = d3Array.thresholdSturges, + smooth = smoothLinear; + + function contours(values) { + var tz = threshold(values); + + // Convert number of thresholds into uniform thresholds. + if (!Array.isArray(tz)) { + const e = d3Array.extent(values, finite); + tz = d3Array.ticks(...d3Array.nice(e[0], e[1], tz), tz); + while (tz[tz.length - 1] >= e[1]) tz.pop(); + while (tz[1] < e[0]) tz.shift(); + } else { + tz = tz.slice().sort(ascending); + } + + return tz.map(value => contour(values, value)); + } + + // Accumulate, smooth contour rings, assign holes to exterior rings. + // Based on https://github.com/mbostock/shapefile/blob/v0.6.2/shp/polygon.js + function contour(values, value) { + const v = value == null ? NaN : +value; + if (isNaN(v)) throw new Error(`invalid value: ${value}`); + + var polygons = [], + holes = []; + + isorings(values, v, function(ring) { + smooth(ring, values, v); + if (area(ring) > 0) polygons.push([ring]); + else holes.push(ring); + }); + + holes.forEach(function(hole) { + for (var i = 0, n = polygons.length, polygon; i < n; ++i) { + if (contains((polygon = polygons[i])[0], hole) !== -1) { + polygon.push(hole); + return; + } + } + }); + + return { + type: "MultiPolygon", + value: value, + coordinates: polygons + }; + } + + // Marching squares with isolines stitched into rings. + // Based on https://github.com/topojson/topojson-client/blob/v3.0.0/src/stitch.js + function isorings(values, value, callback) { + var fragmentByStart = new Array, + fragmentByEnd = new Array, + x, y, t0, t1, t2, t3; + + // Special case for the first row (y = -1, t2 = t3 = 0). + x = y = -1; + t1 = above(values[0], value); + cases[t1 << 1].forEach(stitch); + while (++x < dx - 1) { + t0 = t1, t1 = above(values[x + 1], value); + cases[t0 | t1 << 1].forEach(stitch); + } + cases[t1 << 0].forEach(stitch); + + // General case for the intermediate rows. + while (++y < dy - 1) { + x = -1; + t1 = above(values[y * dx + dx], value); + t2 = above(values[y * dx], value); + cases[t1 << 1 | t2 << 2].forEach(stitch); + while (++x < dx - 1) { + t0 = t1, t1 = above(values[y * dx + dx + x + 1], value); + t3 = t2, t2 = above(values[y * dx + x + 1], value); + cases[t0 | t1 << 1 | t2 << 2 | t3 << 3].forEach(stitch); + } + cases[t1 | t2 << 3].forEach(stitch); + } + + // Special case for the last row (y = dy - 1, t0 = t1 = 0). + x = -1; + t2 = values[y * dx] >= value; + cases[t2 << 2].forEach(stitch); + while (++x < dx - 1) { + t3 = t2, t2 = above(values[y * dx + x + 1], value); + cases[t2 << 2 | t3 << 3].forEach(stitch); + } + cases[t2 << 3].forEach(stitch); + + function stitch(line) { + var start = [line[0][0] + x, line[0][1] + y], + end = [line[1][0] + x, line[1][1] + y], + startIndex = index(start), + endIndex = index(end), + f, g; + if (f = fragmentByEnd[startIndex]) { + if (g = fragmentByStart[endIndex]) { + delete fragmentByEnd[f.end]; + delete fragmentByStart[g.start]; + if (f === g) { + f.ring.push(end); + callback(f.ring); + } else { + fragmentByStart[f.start] = fragmentByEnd[g.end] = {start: f.start, end: g.end, ring: f.ring.concat(g.ring)}; + } + } else { + delete fragmentByEnd[f.end]; + f.ring.push(end); + fragmentByEnd[f.end = endIndex] = f; + } + } else if (f = fragmentByStart[endIndex]) { + if (g = fragmentByEnd[startIndex]) { + delete fragmentByStart[f.start]; + delete fragmentByEnd[g.end]; + if (f === g) { + f.ring.push(end); + callback(f.ring); + } else { + fragmentByStart[g.start] = fragmentByEnd[f.end] = {start: g.start, end: f.end, ring: g.ring.concat(f.ring)}; + } + } else { + delete fragmentByStart[f.start]; + f.ring.unshift(start); + fragmentByStart[f.start = startIndex] = f; + } + } else { + fragmentByStart[startIndex] = fragmentByEnd[endIndex] = {start: startIndex, end: endIndex, ring: [start, end]}; + } + } + } + + function index(point) { + return point[0] * 2 + point[1] * (dx + 1) * 4; + } + + function smoothLinear(ring, values, value) { + ring.forEach(function(point) { + var x = point[0], + y = point[1], + xt = x | 0, + yt = y | 0, + v1 = valid(values[yt * dx + xt]); + if (x > 0 && x < dx && xt === x) { + point[0] = smooth1(x, valid(values[yt * dx + xt - 1]), v1, value); + } + if (y > 0 && y < dy && yt === y) { + point[1] = smooth1(y, valid(values[(yt - 1) * dx + xt]), v1, value); + } + }); + } + + contours.contour = contour; + + contours.size = function(_) { + if (!arguments.length) return [dx, dy]; + var _0 = Math.floor(_[0]), _1 = Math.floor(_[1]); + if (!(_0 >= 0 && _1 >= 0)) throw new Error("invalid size"); + return dx = _0, dy = _1, contours; + }; + + contours.thresholds = function(_) { + return arguments.length ? (threshold = typeof _ === "function" ? _ : Array.isArray(_) ? constant(slice.call(_)) : constant(_), contours) : threshold; + }; + + contours.smooth = function(_) { + return arguments.length ? (smooth = _ ? smoothLinear : noop, contours) : smooth === smoothLinear; + }; + + return contours; +} + +// When computing the extent, ignore infinite values (as well as invalid ones). +function finite(x) { + return isFinite(x) ? x : NaN; +} + +// Is the (possibly invalid) x greater than or equal to the (known valid) value? +// Treat any invalid value as below negative infinity. +function above(x, value) { + return x == null ? false : +x >= value; +} + +// During smoothing, treat any invalid value as negative infinity. +function valid(v) { + return v == null || isNaN(v = +v) ? -Infinity : v; +} + +function smooth1(x, v0, v1, value) { + const a = value - v0; + const b = v1 - v0; + const d = isFinite(a) || isFinite(b) ? a / b : Math.sign(a) / Math.sign(b); + return isNaN(d) ? x : x + d - 0.5; +} + +function defaultX(d) { + return d[0]; +} + +function defaultY(d) { + return d[1]; +} + +function defaultWeight() { + return 1; +} + +function density() { + var x = defaultX, + y = defaultY, + weight = defaultWeight, + dx = 960, + dy = 500, + r = 20, // blur radius + k = 2, // log2(grid cell size) + o = r * 3, // grid offset, to pad for blur + n = (dx + o * 2) >> k, // grid width + m = (dy + o * 2) >> k, // grid height + threshold = constant(20); + + function grid(data) { + var values = new Float32Array(n * m), + pow2k = Math.pow(2, -k), + i = -1; + + for (const d of data) { + var xi = (x(d, ++i, data) + o) * pow2k, + yi = (y(d, i, data) + o) * pow2k, + wi = +weight(d, i, data); + if (wi && xi >= 0 && xi < n && yi >= 0 && yi < m) { + var x0 = Math.floor(xi), + y0 = Math.floor(yi), + xt = xi - x0 - 0.5, + yt = yi - y0 - 0.5; + values[x0 + y0 * n] += (1 - xt) * (1 - yt) * wi; + values[x0 + 1 + y0 * n] += xt * (1 - yt) * wi; + values[x0 + 1 + (y0 + 1) * n] += xt * yt * wi; + values[x0 + (y0 + 1) * n] += (1 - xt) * yt * wi; + } + } + + d3Array.blur2({data: values, width: n, height: m}, r * pow2k); + return values; + } + + function density(data) { + var values = grid(data), + tz = threshold(values), + pow4k = Math.pow(2, 2 * k); + + // Convert number of thresholds into uniform thresholds. + if (!Array.isArray(tz)) { + tz = d3Array.ticks(Number.MIN_VALUE, d3Array.max(values) / pow4k, tz); + } + + return Contours() + .size([n, m]) + .thresholds(tz.map(d => d * pow4k)) + (values) + .map((c, i) => (c.value = +tz[i], transform(c))); + } + + density.contours = function(data) { + var values = grid(data), + contours = Contours().size([n, m]), + pow4k = Math.pow(2, 2 * k), + contour = value => { + value = +value; + var c = transform(contours.contour(values, value * pow4k)); + c.value = value; // preserve exact threshold value + return c; + }; + Object.defineProperty(contour, "max", {get: () => d3Array.max(values) / pow4k}); + return contour; + }; + + function transform(geometry) { + geometry.coordinates.forEach(transformPolygon); + return geometry; + } + + function transformPolygon(coordinates) { + coordinates.forEach(transformRing); + } + + function transformRing(coordinates) { + coordinates.forEach(transformPoint); + } + + // TODO Optimize. + function transformPoint(coordinates) { + coordinates[0] = coordinates[0] * Math.pow(2, k) - o; + coordinates[1] = coordinates[1] * Math.pow(2, k) - o; + } + + function resize() { + o = r * 3; + n = (dx + o * 2) >> k; + m = (dy + o * 2) >> k; + return density; + } + + density.x = function(_) { + return arguments.length ? (x = typeof _ === "function" ? _ : constant(+_), density) : x; + }; + + density.y = function(_) { + return arguments.length ? (y = typeof _ === "function" ? _ : constant(+_), density) : y; + }; + + density.weight = function(_) { + return arguments.length ? (weight = typeof _ === "function" ? _ : constant(+_), density) : weight; + }; + + density.size = function(_) { + if (!arguments.length) return [dx, dy]; + var _0 = +_[0], _1 = +_[1]; + if (!(_0 >= 0 && _1 >= 0)) throw new Error("invalid size"); + return dx = _0, dy = _1, resize(); + }; + + density.cellSize = function(_) { + if (!arguments.length) return 1 << k; + if (!((_ = +_) >= 1)) throw new Error("invalid cell size"); + return k = Math.floor(Math.log(_) / Math.LN2), resize(); + }; + + density.thresholds = function(_) { + return arguments.length ? (threshold = typeof _ === "function" ? _ : Array.isArray(_) ? constant(slice.call(_)) : constant(_), density) : threshold; + }; + + density.bandwidth = function(_) { + if (!arguments.length) return Math.sqrt(r * (r + 1)); + if (!((_ = +_) >= 0)) throw new Error("invalid bandwidth"); + return r = (Math.sqrt(4 * _ * _ + 1) - 1) / 2, resize(); + }; + + return density; +} + +exports.contourDensity = density; +exports.contours = Contours; + +})); diff --git a/frontend/node_modules/d3-contour/dist/d3-contour.min.js b/frontend/node_modules/d3-contour/dist/d3-contour.min.js new file mode 100644 index 0000000..2388601 --- /dev/null +++ b/frontend/node_modules/d3-contour/dist/d3-contour.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-contour/ v4.0.2 Copyright 2012-2023 Mike Bostock +!function(r,n){"object"==typeof exports&&"undefined"!=typeof module?n(exports,require("d3-array")):"function"==typeof define&&define.amd?define(["exports","d3-array"],n):n((r="undefined"!=typeof globalThis?globalThis:r||self).d3=r.d3||{},r.d3)}(this,(function(r,n){"use strict";var t=Array.prototype.slice;function e(r,n){return r-n}var o=r=>()=>r;function i(r,n){for(var t,e=-1,o=n.length;++ee!=g>e&&t<(d-h)*(e-s)/(g-s)+h&&(o=-o)}return o}function a(r,n,t){var e,o,i,u;return function(r,n,t){return(n[0]-r[0])*(t[1]-r[1])==(t[0]-r[0])*(n[1]-r[1])}(r,n,t)&&(o=r[e=+(r[0]===n[0])],i=t[e],u=n[e],o<=i&&i<=u||u<=i&&i<=o)}function f(){}var c=[[],[[[1,1.5],[.5,1]]],[[[1.5,1],[1,1.5]]],[[[1.5,1],[.5,1]]],[[[1,.5],[1.5,1]]],[[[1,1.5],[.5,1]],[[1,.5],[1.5,1]]],[[[1,.5],[1,1.5]]],[[[1,.5],[.5,1]]],[[[.5,1],[1,.5]]],[[[1,1.5],[1,.5]]],[[[.5,1],[1,.5]],[[1.5,1],[1,1.5]]],[[[1.5,1],[1,.5]]],[[[.5,1],[1.5,1]]],[[[1,1.5],[1.5,1]]],[[[.5,1],[1,1.5]]],[]];function h(){var r=1,u=1,a=n.thresholdSturges,h=w;function v(r){var t=a(r);if(Array.isArray(t))t=t.slice().sort(e);else{const e=n.extent(r,s);for(t=n.ticks(...n.nice(e[0],e[1],t),t);t[t.length-1]>=e[1];)t.pop();for(;t[1]p(r,n)))}function p(n,t){const e=null==t?NaN:+t;if(isNaN(e))throw new Error(`invalid value: ${t}`);var o=[],a=[];return function(n,t,e){var o,i,a,f,h,s,d=new Array,g=new Array;o=i=-1,f=l(n[0],t),c[f<<1].forEach(v);for(;++o=t,c[h<<2].forEach(v);for(;++o0?o.push([r]):a.push(r)})),a.forEach((function(r){for(var n,t=0,e=o.length;t0&&o0&&i=0&&e>=0))throw new Error("invalid size");return r=t,u=e,v},v.thresholds=function(r){return arguments.length?(a="function"==typeof r?r:Array.isArray(r)?o(t.call(r)):o(r),v):a},v.smooth=function(r){return arguments.length?(h=r?w:f,v):h===w},v}function s(r){return isFinite(r)?r:NaN}function l(r,n){return null!=r&&+r>=n}function d(r){return null==r||isNaN(r=+r)?-1/0:r}function g(r,n,t,e){const o=e-n,i=t-n,u=isFinite(o)||isFinite(i)?o/i:Math.sign(o)/Math.sign(i);return isNaN(u)?r:r+u-.5}function v(r){return r[0]}function p(r){return r[1]}function y(){return 1}r.contourDensity=function(){var r=v,e=p,i=y,u=960,a=500,f=20,c=2,s=3*f,l=u+2*s>>c,d=a+2*s>>c,g=o(20);function w(t){var o=new Float32Array(l*d),u=Math.pow(2,-c),a=-1;for(const n of t){var h=(r(n,++a,t)+s)*u,g=(e(n,a,t)+s)*u,v=+i(n,a,t);if(v&&h>=0&&h=0&&gr*o)))(t).map(((r,n)=>(r.value=+e[n],M(r))))}function M(r){return r.coordinates.forEach(A),r}function A(r){r.forEach(N)}function N(r){r.forEach(m)}function m(r){r[0]=r[0]*Math.pow(2,c)-s,r[1]=r[1]*Math.pow(2,c)-s}function b(){return l=u+2*(s=3*f)>>c,d=a+2*s>>c,E}return E.contours=function(r){var t=w(r),e=h().size([l,d]),o=Math.pow(2,2*c),i=r=>{r=+r;var n=M(e.contour(t,r*o));return n.value=r,n};return Object.defineProperty(i,"max",{get:()=>n.max(t)/o}),i},E.x=function(n){return arguments.length?(r="function"==typeof n?n:o(+n),E):r},E.y=function(r){return arguments.length?(e="function"==typeof r?r:o(+r),E):e},E.weight=function(r){return arguments.length?(i="function"==typeof r?r:o(+r),E):i},E.size=function(r){if(!arguments.length)return[u,a];var n=+r[0],t=+r[1];if(!(n>=0&&t>=0))throw new Error("invalid size");return u=n,a=t,b()},E.cellSize=function(r){if(!arguments.length)return 1<=1))throw new Error("invalid cell size");return c=Math.floor(Math.log(r)/Math.LN2),b()},E.thresholds=function(r){return arguments.length?(g="function"==typeof r?r:Array.isArray(r)?o(t.call(r)):o(r),E):g},E.bandwidth=function(r){if(!arguments.length)return Math.sqrt(f*(f+1));if(!((r=+r)>=0))throw new Error("invalid bandwidth");return f=(Math.sqrt(4*r*r+1)-1)/2,b()},E},r.contours=h})); diff --git a/frontend/node_modules/d3-contour/package.json b/frontend/node_modules/d3-contour/package.json new file mode 100644 index 0000000..4197216 --- /dev/null +++ b/frontend/node_modules/d3-contour/package.json @@ -0,0 +1,66 @@ +{ + "name": "d3-contour", + "version": "4.0.2", + "description": "Compute contour polygons using marching squares.", + "homepage": "https://d3js.org/d3-contour/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-contour.git" + }, + "keywords": [ + "d3", + "d3-module", + "contour", + "isoline" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "http://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-contour.min.js", + "unpkg": "dist/d3-contour.min.js", + "exports": { + "umd": "./dist/d3-contour.min.js", + "default": "./src/index.js" + }, + "_moduleAliases": { + "d3-contour": "./src/index.js" + }, + "sideEffects": false, + "dependencies": { + "d3-array": "^3.2.0" + }, + "devDependencies": { + "d3-axis": "3", + "d3-dsv": "3", + "d3-fetch": "3", + "d3-geo": "3", + "d3-polygon": "3", + "d3-scale": "4", + "d3-selection": "3", + "eslint": "8", + "htl": "^0.3.1", + "js-beautify": "1", + "jsdom": "20", + "mocha": "10", + "module-alias": "2", + "rollup": "3", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mkdir -p test/output && mocha -r module-alias/register 'test/**/*-test.js' test/snapshot.js && eslint src test", + "prepublishOnly": "rm -rf dist && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-contour/src/area.js b/frontend/node_modules/d3-contour/src/area.js new file mode 100644 index 0000000..2157a7e --- /dev/null +++ b/frontend/node_modules/d3-contour/src/area.js @@ -0,0 +1,5 @@ +export default function(ring) { + var i = 0, n = ring.length, area = ring[n - 1][1] * ring[0][0] - ring[n - 1][0] * ring[0][1]; + while (++i < n) area += ring[i - 1][1] * ring[i][0] - ring[i - 1][0] * ring[i][1]; + return area; +} diff --git a/frontend/node_modules/d3-contour/src/array.js b/frontend/node_modules/d3-contour/src/array.js new file mode 100644 index 0000000..d236135 --- /dev/null +++ b/frontend/node_modules/d3-contour/src/array.js @@ -0,0 +1,3 @@ +var array = Array.prototype; + +export var slice = array.slice; diff --git a/frontend/node_modules/d3-contour/src/ascending.js b/frontend/node_modules/d3-contour/src/ascending.js new file mode 100644 index 0000000..8939af7 --- /dev/null +++ b/frontend/node_modules/d3-contour/src/ascending.js @@ -0,0 +1,3 @@ +export default function(a, b) { + return a - b; +} diff --git a/frontend/node_modules/d3-contour/src/constant.js b/frontend/node_modules/d3-contour/src/constant.js new file mode 100644 index 0000000..3487c0d --- /dev/null +++ b/frontend/node_modules/d3-contour/src/constant.js @@ -0,0 +1 @@ +export default x => () => x; diff --git a/frontend/node_modules/d3-contour/src/contains.js b/frontend/node_modules/d3-contour/src/contains.js new file mode 100644 index 0000000..f364b35 --- /dev/null +++ b/frontend/node_modules/d3-contour/src/contains.js @@ -0,0 +1,27 @@ +export default function(ring, hole) { + var i = -1, n = hole.length, c; + while (++i < n) if (c = ringContains(ring, hole[i])) return c; + return 0; +} + +function ringContains(ring, point) { + var x = point[0], y = point[1], contains = -1; + for (var i = 0, n = ring.length, j = n - 1; i < n; j = i++) { + var pi = ring[i], xi = pi[0], yi = pi[1], pj = ring[j], xj = pj[0], yj = pj[1]; + if (segmentContains(pi, pj, point)) return 0; + if (((yi > y) !== (yj > y)) && ((x < (xj - xi) * (y - yi) / (yj - yi) + xi))) contains = -contains; + } + return contains; +} + +function segmentContains(a, b, c) { + var i; return collinear(a, b, c) && within(a[i = +(a[0] === b[0])], c[i], b[i]); +} + +function collinear(a, b, c) { + return (b[0] - a[0]) * (c[1] - a[1]) === (c[0] - a[0]) * (b[1] - a[1]); +} + +function within(p, q, r) { + return p <= q && q <= r || r <= q && q <= p; +} diff --git a/frontend/node_modules/d3-contour/src/contours.js b/frontend/node_modules/d3-contour/src/contours.js new file mode 100644 index 0000000..90faf82 --- /dev/null +++ b/frontend/node_modules/d3-contour/src/contours.js @@ -0,0 +1,225 @@ +import {extent, nice, thresholdSturges, ticks} from "d3-array"; +import {slice} from "./array.js"; +import ascending from "./ascending.js"; +import area from "./area.js"; +import constant from "./constant.js"; +import contains from "./contains.js"; +import noop from "./noop.js"; + +var cases = [ + [], + [[[1.0, 1.5], [0.5, 1.0]]], + [[[1.5, 1.0], [1.0, 1.5]]], + [[[1.5, 1.0], [0.5, 1.0]]], + [[[1.0, 0.5], [1.5, 1.0]]], + [[[1.0, 1.5], [0.5, 1.0]], [[1.0, 0.5], [1.5, 1.0]]], + [[[1.0, 0.5], [1.0, 1.5]]], + [[[1.0, 0.5], [0.5, 1.0]]], + [[[0.5, 1.0], [1.0, 0.5]]], + [[[1.0, 1.5], [1.0, 0.5]]], + [[[0.5, 1.0], [1.0, 0.5]], [[1.5, 1.0], [1.0, 1.5]]], + [[[1.5, 1.0], [1.0, 0.5]]], + [[[0.5, 1.0], [1.5, 1.0]]], + [[[1.0, 1.5], [1.5, 1.0]]], + [[[0.5, 1.0], [1.0, 1.5]]], + [] +]; + +export default function() { + var dx = 1, + dy = 1, + threshold = thresholdSturges, + smooth = smoothLinear; + + function contours(values) { + var tz = threshold(values); + + // Convert number of thresholds into uniform thresholds. + if (!Array.isArray(tz)) { + const e = extent(values, finite); + tz = ticks(...nice(e[0], e[1], tz), tz); + while (tz[tz.length - 1] >= e[1]) tz.pop(); + while (tz[1] < e[0]) tz.shift(); + } else { + tz = tz.slice().sort(ascending); + } + + return tz.map(value => contour(values, value)); + } + + // Accumulate, smooth contour rings, assign holes to exterior rings. + // Based on https://github.com/mbostock/shapefile/blob/v0.6.2/shp/polygon.js + function contour(values, value) { + const v = value == null ? NaN : +value; + if (isNaN(v)) throw new Error(`invalid value: ${value}`); + + var polygons = [], + holes = []; + + isorings(values, v, function(ring) { + smooth(ring, values, v); + if (area(ring) > 0) polygons.push([ring]); + else holes.push(ring); + }); + + holes.forEach(function(hole) { + for (var i = 0, n = polygons.length, polygon; i < n; ++i) { + if (contains((polygon = polygons[i])[0], hole) !== -1) { + polygon.push(hole); + return; + } + } + }); + + return { + type: "MultiPolygon", + value: value, + coordinates: polygons + }; + } + + // Marching squares with isolines stitched into rings. + // Based on https://github.com/topojson/topojson-client/blob/v3.0.0/src/stitch.js + function isorings(values, value, callback) { + var fragmentByStart = new Array, + fragmentByEnd = new Array, + x, y, t0, t1, t2, t3; + + // Special case for the first row (y = -1, t2 = t3 = 0). + x = y = -1; + t1 = above(values[0], value); + cases[t1 << 1].forEach(stitch); + while (++x < dx - 1) { + t0 = t1, t1 = above(values[x + 1], value); + cases[t0 | t1 << 1].forEach(stitch); + } + cases[t1 << 0].forEach(stitch); + + // General case for the intermediate rows. + while (++y < dy - 1) { + x = -1; + t1 = above(values[y * dx + dx], value); + t2 = above(values[y * dx], value); + cases[t1 << 1 | t2 << 2].forEach(stitch); + while (++x < dx - 1) { + t0 = t1, t1 = above(values[y * dx + dx + x + 1], value); + t3 = t2, t2 = above(values[y * dx + x + 1], value); + cases[t0 | t1 << 1 | t2 << 2 | t3 << 3].forEach(stitch); + } + cases[t1 | t2 << 3].forEach(stitch); + } + + // Special case for the last row (y = dy - 1, t0 = t1 = 0). + x = -1; + t2 = values[y * dx] >= value; + cases[t2 << 2].forEach(stitch); + while (++x < dx - 1) { + t3 = t2, t2 = above(values[y * dx + x + 1], value); + cases[t2 << 2 | t3 << 3].forEach(stitch); + } + cases[t2 << 3].forEach(stitch); + + function stitch(line) { + var start = [line[0][0] + x, line[0][1] + y], + end = [line[1][0] + x, line[1][1] + y], + startIndex = index(start), + endIndex = index(end), + f, g; + if (f = fragmentByEnd[startIndex]) { + if (g = fragmentByStart[endIndex]) { + delete fragmentByEnd[f.end]; + delete fragmentByStart[g.start]; + if (f === g) { + f.ring.push(end); + callback(f.ring); + } else { + fragmentByStart[f.start] = fragmentByEnd[g.end] = {start: f.start, end: g.end, ring: f.ring.concat(g.ring)}; + } + } else { + delete fragmentByEnd[f.end]; + f.ring.push(end); + fragmentByEnd[f.end = endIndex] = f; + } + } else if (f = fragmentByStart[endIndex]) { + if (g = fragmentByEnd[startIndex]) { + delete fragmentByStart[f.start]; + delete fragmentByEnd[g.end]; + if (f === g) { + f.ring.push(end); + callback(f.ring); + } else { + fragmentByStart[g.start] = fragmentByEnd[f.end] = {start: g.start, end: f.end, ring: g.ring.concat(f.ring)}; + } + } else { + delete fragmentByStart[f.start]; + f.ring.unshift(start); + fragmentByStart[f.start = startIndex] = f; + } + } else { + fragmentByStart[startIndex] = fragmentByEnd[endIndex] = {start: startIndex, end: endIndex, ring: [start, end]}; + } + } + } + + function index(point) { + return point[0] * 2 + point[1] * (dx + 1) * 4; + } + + function smoothLinear(ring, values, value) { + ring.forEach(function(point) { + var x = point[0], + y = point[1], + xt = x | 0, + yt = y | 0, + v1 = valid(values[yt * dx + xt]); + if (x > 0 && x < dx && xt === x) { + point[0] = smooth1(x, valid(values[yt * dx + xt - 1]), v1, value); + } + if (y > 0 && y < dy && yt === y) { + point[1] = smooth1(y, valid(values[(yt - 1) * dx + xt]), v1, value); + } + }); + } + + contours.contour = contour; + + contours.size = function(_) { + if (!arguments.length) return [dx, dy]; + var _0 = Math.floor(_[0]), _1 = Math.floor(_[1]); + if (!(_0 >= 0 && _1 >= 0)) throw new Error("invalid size"); + return dx = _0, dy = _1, contours; + }; + + contours.thresholds = function(_) { + return arguments.length ? (threshold = typeof _ === "function" ? _ : Array.isArray(_) ? constant(slice.call(_)) : constant(_), contours) : threshold; + }; + + contours.smooth = function(_) { + return arguments.length ? (smooth = _ ? smoothLinear : noop, contours) : smooth === smoothLinear; + }; + + return contours; +} + +// When computing the extent, ignore infinite values (as well as invalid ones). +function finite(x) { + return isFinite(x) ? x : NaN; +} + +// Is the (possibly invalid) x greater than or equal to the (known valid) value? +// Treat any invalid value as below negative infinity. +function above(x, value) { + return x == null ? false : +x >= value; +} + +// During smoothing, treat any invalid value as negative infinity. +function valid(v) { + return v == null || isNaN(v = +v) ? -Infinity : v; +} + +function smooth1(x, v0, v1, value) { + const a = value - v0; + const b = v1 - v0; + const d = isFinite(a) || isFinite(b) ? a / b : Math.sign(a) / Math.sign(b); + return isNaN(d) ? x : x + d - 0.5; +} diff --git a/frontend/node_modules/d3-contour/src/density.js b/frontend/node_modules/d3-contour/src/density.js new file mode 100644 index 0000000..6d6b86b --- /dev/null +++ b/frontend/node_modules/d3-contour/src/density.js @@ -0,0 +1,149 @@ +import {blur2, max, ticks} from "d3-array"; +import {slice} from "./array.js"; +import constant from "./constant.js"; +import Contours from "./contours.js"; + +function defaultX(d) { + return d[0]; +} + +function defaultY(d) { + return d[1]; +} + +function defaultWeight() { + return 1; +} + +export default function() { + var x = defaultX, + y = defaultY, + weight = defaultWeight, + dx = 960, + dy = 500, + r = 20, // blur radius + k = 2, // log2(grid cell size) + o = r * 3, // grid offset, to pad for blur + n = (dx + o * 2) >> k, // grid width + m = (dy + o * 2) >> k, // grid height + threshold = constant(20); + + function grid(data) { + var values = new Float32Array(n * m), + pow2k = Math.pow(2, -k), + i = -1; + + for (const d of data) { + var xi = (x(d, ++i, data) + o) * pow2k, + yi = (y(d, i, data) + o) * pow2k, + wi = +weight(d, i, data); + if (wi && xi >= 0 && xi < n && yi >= 0 && yi < m) { + var x0 = Math.floor(xi), + y0 = Math.floor(yi), + xt = xi - x0 - 0.5, + yt = yi - y0 - 0.5; + values[x0 + y0 * n] += (1 - xt) * (1 - yt) * wi; + values[x0 + 1 + y0 * n] += xt * (1 - yt) * wi; + values[x0 + 1 + (y0 + 1) * n] += xt * yt * wi; + values[x0 + (y0 + 1) * n] += (1 - xt) * yt * wi; + } + } + + blur2({data: values, width: n, height: m}, r * pow2k); + return values; + } + + function density(data) { + var values = grid(data), + tz = threshold(values), + pow4k = Math.pow(2, 2 * k); + + // Convert number of thresholds into uniform thresholds. + if (!Array.isArray(tz)) { + tz = ticks(Number.MIN_VALUE, max(values) / pow4k, tz); + } + + return Contours() + .size([n, m]) + .thresholds(tz.map(d => d * pow4k)) + (values) + .map((c, i) => (c.value = +tz[i], transform(c))); + } + + density.contours = function(data) { + var values = grid(data), + contours = Contours().size([n, m]), + pow4k = Math.pow(2, 2 * k), + contour = value => { + value = +value; + var c = transform(contours.contour(values, value * pow4k)); + c.value = value; // preserve exact threshold value + return c; + }; + Object.defineProperty(contour, "max", {get: () => max(values) / pow4k}); + return contour; + }; + + function transform(geometry) { + geometry.coordinates.forEach(transformPolygon); + return geometry; + } + + function transformPolygon(coordinates) { + coordinates.forEach(transformRing); + } + + function transformRing(coordinates) { + coordinates.forEach(transformPoint); + } + + // TODO Optimize. + function transformPoint(coordinates) { + coordinates[0] = coordinates[0] * Math.pow(2, k) - o; + coordinates[1] = coordinates[1] * Math.pow(2, k) - o; + } + + function resize() { + o = r * 3; + n = (dx + o * 2) >> k; + m = (dy + o * 2) >> k; + return density; + } + + density.x = function(_) { + return arguments.length ? (x = typeof _ === "function" ? _ : constant(+_), density) : x; + }; + + density.y = function(_) { + return arguments.length ? (y = typeof _ === "function" ? _ : constant(+_), density) : y; + }; + + density.weight = function(_) { + return arguments.length ? (weight = typeof _ === "function" ? _ : constant(+_), density) : weight; + }; + + density.size = function(_) { + if (!arguments.length) return [dx, dy]; + var _0 = +_[0], _1 = +_[1]; + if (!(_0 >= 0 && _1 >= 0)) throw new Error("invalid size"); + return dx = _0, dy = _1, resize(); + }; + + density.cellSize = function(_) { + if (!arguments.length) return 1 << k; + if (!((_ = +_) >= 1)) throw new Error("invalid cell size"); + return k = Math.floor(Math.log(_) / Math.LN2), resize(); + }; + + density.thresholds = function(_) { + return arguments.length ? (threshold = typeof _ === "function" ? _ : Array.isArray(_) ? constant(slice.call(_)) : constant(_), density) : threshold; + }; + + density.bandwidth = function(_) { + if (!arguments.length) return Math.sqrt(r * (r + 1)); + if (!((_ = +_) >= 0)) throw new Error("invalid bandwidth"); + return r = (Math.sqrt(4 * _ * _ + 1) - 1) / 2, resize(); + }; + + return density; +} diff --git a/frontend/node_modules/d3-contour/src/index.js b/frontend/node_modules/d3-contour/src/index.js new file mode 100644 index 0000000..8e6b5f0 --- /dev/null +++ b/frontend/node_modules/d3-contour/src/index.js @@ -0,0 +1,2 @@ +export {default as contours} from "./contours.js"; +export {default as contourDensity} from "./density.js"; diff --git a/frontend/node_modules/d3-contour/src/noop.js b/frontend/node_modules/d3-contour/src/noop.js new file mode 100644 index 0000000..6ab80bc --- /dev/null +++ b/frontend/node_modules/d3-contour/src/noop.js @@ -0,0 +1 @@ +export default function() {} diff --git a/frontend/node_modules/d3-delaunay/LICENSE b/frontend/node_modules/d3-delaunay/LICENSE new file mode 100644 index 0000000..3a6ada6 --- /dev/null +++ b/frontend/node_modules/d3-delaunay/LICENSE @@ -0,0 +1,14 @@ +Copyright 2018-2021 Observable, Inc. +Copyright 2021 Mapbox + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-delaunay/README.md b/frontend/node_modules/d3-delaunay/README.md new file mode 100644 index 0000000..01dbfee --- /dev/null +++ b/frontend/node_modules/d3-delaunay/README.md @@ -0,0 +1,216 @@ +# d3-delaunay + +

    +

    Georgy “The Voronator” Voronoy + +This is a fast library for computing the [Voronoi diagram](https://en.wikipedia.org/wiki/Voronoi_diagram) of a set of two-dimensional points. It is based on [Delaunator](https://github.com/mapbox/delaunator), a fast library for computing the [Delaunay triangulation](https://en.wikipedia.org/wiki/Delaunay_triangulation) using [sweep algorithms](https://github.com/mapbox/delaunator/blob/master/README.md#papers). The Voronoi diagram is constructed by connecting the circumcenters of adjacent triangles in the Delaunay triangulation. + +For an interactive explanation of how this library works, see [The Delaunay’s Dual](https://observablehq.com/@mbostock/the-delaunays-dual). + +## Installing + +If you use npm, `npm install d3-delaunay`. You can also download the [latest release on GitHub](https://github.com/d3/d3-delaunay/releases/latest). For vanilla HTML in modern browsers, import d3-delaunay from Skypack: + +```html + +``` + +For legacy environments, you can load d3-delaunay’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + + +## API Reference + +### Delaunay + +# new Delaunay(points) [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +Returns the Delaunay triangulation for the given flat array [*x0*, *y0*, *x1*, *y1*, …] of *points*. + +```js +const delaunay = new Delaunay(Float64Array.of(0, 0, 0, 1, 1, 0, 1, 1)); +``` + +# Delaunay.from(points[, fx[, fy[, that]]]) [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +Returns the Delaunay triangulation for the given array or iterable of *points*. If *fx* and *fy* are not specified, then *points* is assumed to be an array of two-element arrays of numbers: [[*x0*, *y0*], [*x1*, *y1*], …]. Otherwise, *fx* and *fy* are functions that are invoked for each element in the *points* array in order, and must return the respective *x*- and *y*-coordinate for each point. If *that* is specified, the functions *fx* and *fy* are invoked with *that* as *this*. (See [Array.from](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Array/from) for reference.) + +```js +const delaunay = Delaunay.from([[0, 0], [0, 1], [1, 0], [1, 1]]); +``` + +# delaunay.points + +The coordinates of the points as an array [*x0*, *y0*, *x1*, *y1*, …]. Typically, this is a Float64Array, however you can use any array-like type in the [constructor](#new_Delaunay). + +# delaunay.halfedges + +The halfedge indexes as an Int32Array [*j0*, *j1*, …]. For each index 0 ≤ *i* < *halfedges*.length, there is a halfedge from triangle vertex *j* = *halfedges*[*i*] to triangle vertex *i*. Equivalently, this means that triangle ⌊*i* / 3⌋ is adjacent to triangle ⌊*j* / 3⌋. If *j* is negative, then triangle ⌊*i* / 3⌋ is an exterior triangle on the [convex hull](#delaunay_hull). For example, to render the internal edges of the Delaunay triangulation: + +```js +const {points, halfedges, triangles} = delaunay; +for (let i = 0, n = halfedges.length; i < n; ++i) { + const j = halfedges[i]; + if (j < i) continue; + const ti = triangles[i]; + const tj = triangles[j]; + context.moveTo(points[ti * 2], points[ti * 2 + 1]); + context.lineTo(points[tj * 2], points[tj * 2 + 1]); +} +``` + +See also [*delaunay*.render](#delaunay_render). + +# delaunay.hull + +An Int32Array of point indexes that form the convex hull in counterclockwise order. If the points are collinear, returns them ordered. + +See also [*delaunay*.renderHull](#delaunay_renderHull). + +# delaunay.triangles + +The triangle vertex indexes as an Uint32Array [*i0*, *j0*, *k0*, *i1*, *j1*, *k1*, …]. Each contiguous triplet of indexes *i*, *j*, *k* forms a counterclockwise triangle. The coordinates of the triangle’s points can be found by going through [*delaunay*.points](#delaunay_points). For example, to render triangle *i*: + +```js +const {points, triangles} = delaunay; +const t0 = triangles[i * 3 + 0]; +const t1 = triangles[i * 3 + 1]; +const t2 = triangles[i * 3 + 2]; +context.moveTo(points[t0 * 2], points[t0 * 2 + 1]); +context.lineTo(points[t1 * 2], points[t1 * 2 + 1]); +context.lineTo(points[t2 * 2], points[t2 * 2 + 1]); +context.closePath(); +``` + +See also [*delaunay*.renderTriangle](#delaunay_renderTriangle). + +# delaunay.inedges + +The incoming halfedge indexes as a Int32Array [*e0*, *e1*, *e2*, …]. For each point *i*, *inedges*[*i*] is the halfedge index *e* of an incoming halfedge. For coincident points, the halfedge index is -1; for points on the convex hull, the incoming halfedge is on the convex hull; for other points, the choice of incoming halfedge is arbitrary. The *inedges* table can be used to traverse the Delaunay triangulation; see also [*delaunay*.neighbors](#delaunay_neighbors). + +# delaunay.find(x, y[, i]) [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +Returns the index of the input point that is closest to the specified point ⟨*x*, *y*⟩. The search is started at the specified point *i*. If *i* is not specified, it defaults to zero. + +# delaunay.neighbors(i) [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +Returns an iterable over the indexes of the neighboring points to the specified point *i*. The iterable is empty if *i* is a coincident point. + +# delaunay.render([context]) [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +delaunay.render + +Renders the edges of the Delaunay triangulation to the specified *context*. The specified *context* must implement the *context*.moveTo and *context*.lineTo methods from the [CanvasPathMethods API](https://www.w3.org/TR/2dcontext/#canvaspathmethods). If a *context* is not specified, an SVG path string is returned instead. + +# delaunay.renderHull([context]) [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +delaunay.renderHull + +Renders the convex hull of the Delaunay triangulation to the specified *context*. The specified *context* must implement the *context*.moveTo and *context*.lineTo methods from the [CanvasPathMethods API](https://www.w3.org/TR/2dcontext/#canvaspathmethods). If a *context* is not specified, an SVG path string is returned instead. + +# delaunay.renderTriangle(i[, context]) [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +delaunay.renderTriangle + +Renders triangle *i* of the Delaunay triangulation to the specified *context*. The specified *context* must implement the *context*.moveTo, *context*.lineTo and *context*.closePath methods from the [CanvasPathMethods API](https://www.w3.org/TR/2dcontext/#canvaspathmethods). If a *context* is not specified, an SVG path string is returned instead. + +# delaunay.renderPoints(\[context\]\[, radius\]) [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +Renders the input points of the Delaunay triangulation to the specified *context* as circles with the specified *radius*. If *radius* is not specified, it defaults to 2. The specified *context* must implement the *context*.moveTo and *context*.arc methods from the [CanvasPathMethods API](https://www.w3.org/TR/2dcontext/#canvaspathmethods). If a *context* is not specified, an SVG path string is returned instead. + +# delaunay.hullPolygon() [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +Returns the closed polygon [[*x0*, *y0*], [*x1*, *y1*], …, [*x0*, *y0*]] representing the convex hull. + +# delaunay.trianglePolygons() [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +Returns an iterable over the [polygons for each triangle](#delaunay_trianglePolygon), in order. + +# delaunay.trianglePolygon(i) [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +Returns the closed polygon [[*x0*, *y0*], [*x1*, *y1*], [*x2*, *y2*], [*x0*, *y0*]] representing the triangle *i*. + +# delaunay.update() [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +Updates the triangulation after the points have been modified in-place. + +# delaunay.voronoi([bounds]) [<>](https://github.com/d3/d3-delaunay/blob/master/src/delaunay.js "Source") + +Returns the [Voronoi diagram](#voronoi) for the associated [points](#delaunay_points). When rendering, the diagram will be clipped to the specified *bounds* = [*xmin*, *ymin*, *xmax*, *ymax*]. If *bounds* is not specified, it defaults to [0, 0, 960, 500]. See [To Infinity and Back Again](https://observablehq.com/@mbostock/to-infinity-and-back-again) for an interactive explanation of Voronoi cell clipping. + +The Voronoi diagram is returned even in degenerate cases where no triangulation exists — namely 0, 1 or 2 points, and collinear points. + +### Voronoi + +# voronoi.delaunay + +The Voronoi diagram’s associated [Delaunay triangulation](#delaunay). + +# voronoi.circumcenters + +The [circumcenters](http://mathworld.wolfram.com/Circumcenter.html) of the Delaunay triangles as a Float64Array [*cx0*, *cy0*, *cx1*, *cy1*, …]. Each contiguous pair of coordinates *cx*, *cy* is the circumcenter for the corresponding triangle. These circumcenters form the coordinates of the Voronoi cell polygons. + +# voronoi.vectors + +A Float64Array [*vx0*, *vy0*, *wx0*, *wy0*, …] where each non-zero quadruple describes an open (infinite) cell on the outer hull, giving the directions of two open half-lines. + +# voronoi.xmin
    +# voronoi.ymin
    +# voronoi.xmax
    +# voronoi.ymax
    + +The bounds of the viewport [*xmin*, *ymin*, *xmax*, *ymax*] for rendering the Voronoi diagram. These values only affect the rendering methods ([*voronoi*.render](#voronoi_render), [*voronoi*.renderBounds](#voronoi_renderBounds), [*cell*.render](#cell_render)). + +# voronoi.contains(i, x, y) [<>](https://github.com/d3/d3-delaunay/blob/master/src/cell.js "Source") + +Returns true if the cell with the specified index *i* contains the specified point ⟨*x*, *y*⟩. (This method is not affected by the associated Voronoi diagram’s viewport [bounds](#voronoi_xmin).) + +# voronoi.neighbors(i) [<>](https://github.com/d3/d3-delaunay/blob/master/src/voronoi.js "Source") + +Returns an iterable over the indexes of the cells that share a common edge with the specified cell *i*. Voronoi neighbors are always neighbors on the Delaunay graph, but the converse is false when the common edge has been clipped out by the Voronoi diagram’s viewport. + +# voronoi.render([context]) [<>](https://github.com/d3/d3-delaunay/blob/master/src/voronoi.js "Source") + +voronoi.render + +Renders the mesh of Voronoi cells to the specified *context*. The specified *context* must implement the *context*.moveTo and *context*.lineTo methods from the [CanvasPathMethods API](https://www.w3.org/TR/2dcontext/#canvaspathmethods). If a *context* is not specified, an SVG path string is returned instead. + +# voronoi.renderBounds([context]) [<>](https://github.com/d3/d3-delaunay/blob/master/src/voronoi.js "Source") + +voronoi.renderBounds + +Renders the viewport extent to the specified *context*. The specified *context* must implement the *context*.rect method from the [CanvasPathMethods API](https://www.w3.org/TR/2dcontext/#canvaspathmethods). Equivalent to *context*.rect(*voronoi*.xmin, *voronoi*.ymin, *voronoi*.xmax - *voronoi*.xmin, *voronoi*.ymax - *voronoi*.ymin). If a *context* is not specified, an SVG path string is returned instead. + +# voronoi.renderCell(i[, context]) [<>](https://github.com/d3/d3-delaunay/blob/master/src/voronoi.js "Source") + +cell.render + +Renders the cell with the specified index *i* to the specified *context*. The specified *context* must implement the *context*.moveTo , *context*.lineTo and *context*.closePath methods from the [CanvasPathMethods API](https://www.w3.org/TR/2dcontext/#canvaspathmethods). If a *context* is not specified, an SVG path string is returned instead. + +# voronoi.cellPolygons() [<>](https://github.com/d3/d3-delaunay/blob/master/src/voronoi.js "Source") + +Returns an iterable over the non-empty [polygons for each cell](#voronoi_cellPolygon), with the cell index as property. + +# voronoi.cellPolygon(i) [<>](https://github.com/d3/d3-delaunay/blob/master/src/voronoi.js "Source") + +Returns the convex, closed polygon [[*x0*, *y0*], [*x1*, *y1*], …, [*x0*, *y0*]] representing the cell for the specified point *i*. + +# voronoi.update() [<>](https://github.com/d3/d3-delaunay/blob/master/src/voronoi.js "Source") + +Updates the Voronoi diagram and underlying triangulation after the points have been modified in-place — useful for Lloyd’s relaxation. diff --git a/frontend/node_modules/d3-delaunay/dist/d3-delaunay.js b/frontend/node_modules/d3-delaunay/dist/d3-delaunay.js new file mode 100644 index 0000000..a001223 --- /dev/null +++ b/frontend/node_modules/d3-delaunay/dist/d3-delaunay.js @@ -0,0 +1,1391 @@ +// https://github.com/d3/d3-delaunay v6.0.4 Copyright 2018-2021 Observable, Inc., 2021 Mapbox +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +}(this, (function (exports) { 'use strict'; + +const epsilon$1 = 1.1102230246251565e-16; +const splitter = 134217729; +const resulterrbound = (3 + 8 * epsilon$1) * epsilon$1; + +// fast_expansion_sum_zeroelim routine from oritinal code +function sum(elen, e, flen, f, h) { + let Q, Qnew, hh, bvirt; + let enow = e[0]; + let fnow = f[0]; + let eindex = 0; + let findex = 0; + if ((fnow > enow) === (fnow > -enow)) { + Q = enow; + enow = e[++eindex]; + } else { + Q = fnow; + fnow = f[++findex]; + } + let hindex = 0; + if (eindex < elen && findex < flen) { + if ((fnow > enow) === (fnow > -enow)) { + Qnew = enow + Q; + hh = Q - (Qnew - enow); + enow = e[++eindex]; + } else { + Qnew = fnow + Q; + hh = Q - (Qnew - fnow); + fnow = f[++findex]; + } + Q = Qnew; + if (hh !== 0) { + h[hindex++] = hh; + } + while (eindex < elen && findex < flen) { + if ((fnow > enow) === (fnow > -enow)) { + Qnew = Q + enow; + bvirt = Qnew - Q; + hh = Q - (Qnew - bvirt) + (enow - bvirt); + enow = e[++eindex]; + } else { + Qnew = Q + fnow; + bvirt = Qnew - Q; + hh = Q - (Qnew - bvirt) + (fnow - bvirt); + fnow = f[++findex]; + } + Q = Qnew; + if (hh !== 0) { + h[hindex++] = hh; + } + } + } + while (eindex < elen) { + Qnew = Q + enow; + bvirt = Qnew - Q; + hh = Q - (Qnew - bvirt) + (enow - bvirt); + enow = e[++eindex]; + Q = Qnew; + if (hh !== 0) { + h[hindex++] = hh; + } + } + while (findex < flen) { + Qnew = Q + fnow; + bvirt = Qnew - Q; + hh = Q - (Qnew - bvirt) + (fnow - bvirt); + fnow = f[++findex]; + Q = Qnew; + if (hh !== 0) { + h[hindex++] = hh; + } + } + if (Q !== 0 || hindex === 0) { + h[hindex++] = Q; + } + return hindex; +} + +function estimate(elen, e) { + let Q = e[0]; + for (let i = 1; i < elen; i++) Q += e[i]; + return Q; +} + +function vec(n) { + return new Float64Array(n); +} + +const ccwerrboundA = (3 + 16 * epsilon$1) * epsilon$1; +const ccwerrboundB = (2 + 12 * epsilon$1) * epsilon$1; +const ccwerrboundC = (9 + 64 * epsilon$1) * epsilon$1 * epsilon$1; + +const B = vec(4); +const C1 = vec(8); +const C2 = vec(12); +const D = vec(16); +const u = vec(4); + +function orient2dadapt(ax, ay, bx, by, cx, cy, detsum) { + let acxtail, acytail, bcxtail, bcytail; + let bvirt, c, ahi, alo, bhi, blo, _i, _j, _0, s1, s0, t1, t0, u3; + + const acx = ax - cx; + const bcx = bx - cx; + const acy = ay - cy; + const bcy = by - cy; + + s1 = acx * bcy; + c = splitter * acx; + ahi = c - (c - acx); + alo = acx - ahi; + c = splitter * bcy; + bhi = c - (c - bcy); + blo = bcy - bhi; + s0 = alo * blo - (s1 - ahi * bhi - alo * bhi - ahi * blo); + t1 = acy * bcx; + c = splitter * acy; + ahi = c - (c - acy); + alo = acy - ahi; + c = splitter * bcx; + bhi = c - (c - bcx); + blo = bcx - bhi; + t0 = alo * blo - (t1 - ahi * bhi - alo * bhi - ahi * blo); + _i = s0 - t0; + bvirt = s0 - _i; + B[0] = s0 - (_i + bvirt) + (bvirt - t0); + _j = s1 + _i; + bvirt = _j - s1; + _0 = s1 - (_j - bvirt) + (_i - bvirt); + _i = _0 - t1; + bvirt = _0 - _i; + B[1] = _0 - (_i + bvirt) + (bvirt - t1); + u3 = _j + _i; + bvirt = u3 - _j; + B[2] = _j - (u3 - bvirt) + (_i - bvirt); + B[3] = u3; + + let det = estimate(4, B); + let errbound = ccwerrboundB * detsum; + if (det >= errbound || -det >= errbound) { + return det; + } + + bvirt = ax - acx; + acxtail = ax - (acx + bvirt) + (bvirt - cx); + bvirt = bx - bcx; + bcxtail = bx - (bcx + bvirt) + (bvirt - cx); + bvirt = ay - acy; + acytail = ay - (acy + bvirt) + (bvirt - cy); + bvirt = by - bcy; + bcytail = by - (bcy + bvirt) + (bvirt - cy); + + if (acxtail === 0 && acytail === 0 && bcxtail === 0 && bcytail === 0) { + return det; + } + + errbound = ccwerrboundC * detsum + resulterrbound * Math.abs(det); + det += (acx * bcytail + bcy * acxtail) - (acy * bcxtail + bcx * acytail); + if (det >= errbound || -det >= errbound) return det; + + s1 = acxtail * bcy; + c = splitter * acxtail; + ahi = c - (c - acxtail); + alo = acxtail - ahi; + c = splitter * bcy; + bhi = c - (c - bcy); + blo = bcy - bhi; + s0 = alo * blo - (s1 - ahi * bhi - alo * bhi - ahi * blo); + t1 = acytail * bcx; + c = splitter * acytail; + ahi = c - (c - acytail); + alo = acytail - ahi; + c = splitter * bcx; + bhi = c - (c - bcx); + blo = bcx - bhi; + t0 = alo * blo - (t1 - ahi * bhi - alo * bhi - ahi * blo); + _i = s0 - t0; + bvirt = s0 - _i; + u[0] = s0 - (_i + bvirt) + (bvirt - t0); + _j = s1 + _i; + bvirt = _j - s1; + _0 = s1 - (_j - bvirt) + (_i - bvirt); + _i = _0 - t1; + bvirt = _0 - _i; + u[1] = _0 - (_i + bvirt) + (bvirt - t1); + u3 = _j + _i; + bvirt = u3 - _j; + u[2] = _j - (u3 - bvirt) + (_i - bvirt); + u[3] = u3; + const C1len = sum(4, B, 4, u, C1); + + s1 = acx * bcytail; + c = splitter * acx; + ahi = c - (c - acx); + alo = acx - ahi; + c = splitter * bcytail; + bhi = c - (c - bcytail); + blo = bcytail - bhi; + s0 = alo * blo - (s1 - ahi * bhi - alo * bhi - ahi * blo); + t1 = acy * bcxtail; + c = splitter * acy; + ahi = c - (c - acy); + alo = acy - ahi; + c = splitter * bcxtail; + bhi = c - (c - bcxtail); + blo = bcxtail - bhi; + t0 = alo * blo - (t1 - ahi * bhi - alo * bhi - ahi * blo); + _i = s0 - t0; + bvirt = s0 - _i; + u[0] = s0 - (_i + bvirt) + (bvirt - t0); + _j = s1 + _i; + bvirt = _j - s1; + _0 = s1 - (_j - bvirt) + (_i - bvirt); + _i = _0 - t1; + bvirt = _0 - _i; + u[1] = _0 - (_i + bvirt) + (bvirt - t1); + u3 = _j + _i; + bvirt = u3 - _j; + u[2] = _j - (u3 - bvirt) + (_i - bvirt); + u[3] = u3; + const C2len = sum(C1len, C1, 4, u, C2); + + s1 = acxtail * bcytail; + c = splitter * acxtail; + ahi = c - (c - acxtail); + alo = acxtail - ahi; + c = splitter * bcytail; + bhi = c - (c - bcytail); + blo = bcytail - bhi; + s0 = alo * blo - (s1 - ahi * bhi - alo * bhi - ahi * blo); + t1 = acytail * bcxtail; + c = splitter * acytail; + ahi = c - (c - acytail); + alo = acytail - ahi; + c = splitter * bcxtail; + bhi = c - (c - bcxtail); + blo = bcxtail - bhi; + t0 = alo * blo - (t1 - ahi * bhi - alo * bhi - ahi * blo); + _i = s0 - t0; + bvirt = s0 - _i; + u[0] = s0 - (_i + bvirt) + (bvirt - t0); + _j = s1 + _i; + bvirt = _j - s1; + _0 = s1 - (_j - bvirt) + (_i - bvirt); + _i = _0 - t1; + bvirt = _0 - _i; + u[1] = _0 - (_i + bvirt) + (bvirt - t1); + u3 = _j + _i; + bvirt = u3 - _j; + u[2] = _j - (u3 - bvirt) + (_i - bvirt); + u[3] = u3; + const Dlen = sum(C2len, C2, 4, u, D); + + return D[Dlen - 1]; +} + +function orient2d(ax, ay, bx, by, cx, cy) { + const detleft = (ay - cy) * (bx - cx); + const detright = (ax - cx) * (by - cy); + const det = detleft - detright; + + if (detleft === 0 || detright === 0 || (detleft > 0) !== (detright > 0)) return det; + + const detsum = Math.abs(detleft + detright); + if (Math.abs(det) >= ccwerrboundA * detsum) return det; + + return -orient2dadapt(ax, ay, bx, by, cx, cy, detsum); +} + +const EPSILON = Math.pow(2, -52); +const EDGE_STACK = new Uint32Array(512); + +class Delaunator { + + static from(points, getX = defaultGetX, getY = defaultGetY) { + const n = points.length; + const coords = new Float64Array(n * 2); + + for (let i = 0; i < n; i++) { + const p = points[i]; + coords[2 * i] = getX(p); + coords[2 * i + 1] = getY(p); + } + + return new Delaunator(coords); + } + + constructor(coords) { + const n = coords.length >> 1; + if (n > 0 && typeof coords[0] !== 'number') throw new Error('Expected coords to contain numbers.'); + + this.coords = coords; + + // arrays that will store the triangulation graph + const maxTriangles = Math.max(2 * n - 5, 0); + this._triangles = new Uint32Array(maxTriangles * 3); + this._halfedges = new Int32Array(maxTriangles * 3); + + // temporary arrays for tracking the edges of the advancing convex hull + this._hashSize = Math.ceil(Math.sqrt(n)); + this._hullPrev = new Uint32Array(n); // edge to prev edge + this._hullNext = new Uint32Array(n); // edge to next edge + this._hullTri = new Uint32Array(n); // edge to adjacent triangle + this._hullHash = new Int32Array(this._hashSize).fill(-1); // angular edge hash + + // temporary arrays for sorting points + this._ids = new Uint32Array(n); + this._dists = new Float64Array(n); + + this.update(); + } + + update() { + const {coords, _hullPrev: hullPrev, _hullNext: hullNext, _hullTri: hullTri, _hullHash: hullHash} = this; + const n = coords.length >> 1; + + // populate an array of point indices; calculate input data bbox + let minX = Infinity; + let minY = Infinity; + let maxX = -Infinity; + let maxY = -Infinity; + + for (let i = 0; i < n; i++) { + const x = coords[2 * i]; + const y = coords[2 * i + 1]; + if (x < minX) minX = x; + if (y < minY) minY = y; + if (x > maxX) maxX = x; + if (y > maxY) maxY = y; + this._ids[i] = i; + } + const cx = (minX + maxX) / 2; + const cy = (minY + maxY) / 2; + + let minDist = Infinity; + let i0, i1, i2; + + // pick a seed point close to the center + for (let i = 0; i < n; i++) { + const d = dist(cx, cy, coords[2 * i], coords[2 * i + 1]); + if (d < minDist) { + i0 = i; + minDist = d; + } + } + const i0x = coords[2 * i0]; + const i0y = coords[2 * i0 + 1]; + + minDist = Infinity; + + // find the point closest to the seed + for (let i = 0; i < n; i++) { + if (i === i0) continue; + const d = dist(i0x, i0y, coords[2 * i], coords[2 * i + 1]); + if (d < minDist && d > 0) { + i1 = i; + minDist = d; + } + } + let i1x = coords[2 * i1]; + let i1y = coords[2 * i1 + 1]; + + let minRadius = Infinity; + + // find the third point which forms the smallest circumcircle with the first two + for (let i = 0; i < n; i++) { + if (i === i0 || i === i1) continue; + const r = circumradius(i0x, i0y, i1x, i1y, coords[2 * i], coords[2 * i + 1]); + if (r < minRadius) { + i2 = i; + minRadius = r; + } + } + let i2x = coords[2 * i2]; + let i2y = coords[2 * i2 + 1]; + + if (minRadius === Infinity) { + // order collinear points by dx (or dy if all x are identical) + // and return the list as a hull + for (let i = 0; i < n; i++) { + this._dists[i] = (coords[2 * i] - coords[0]) || (coords[2 * i + 1] - coords[1]); + } + quicksort(this._ids, this._dists, 0, n - 1); + const hull = new Uint32Array(n); + let j = 0; + for (let i = 0, d0 = -Infinity; i < n; i++) { + const id = this._ids[i]; + if (this._dists[id] > d0) { + hull[j++] = id; + d0 = this._dists[id]; + } + } + this.hull = hull.subarray(0, j); + this.triangles = new Uint32Array(0); + this.halfedges = new Uint32Array(0); + return; + } + + // swap the order of the seed points for counter-clockwise orientation + if (orient2d(i0x, i0y, i1x, i1y, i2x, i2y) < 0) { + const i = i1; + const x = i1x; + const y = i1y; + i1 = i2; + i1x = i2x; + i1y = i2y; + i2 = i; + i2x = x; + i2y = y; + } + + const center = circumcenter(i0x, i0y, i1x, i1y, i2x, i2y); + this._cx = center.x; + this._cy = center.y; + + for (let i = 0; i < n; i++) { + this._dists[i] = dist(coords[2 * i], coords[2 * i + 1], center.x, center.y); + } + + // sort the points by distance from the seed triangle circumcenter + quicksort(this._ids, this._dists, 0, n - 1); + + // set up the seed triangle as the starting hull + this._hullStart = i0; + let hullSize = 3; + + hullNext[i0] = hullPrev[i2] = i1; + hullNext[i1] = hullPrev[i0] = i2; + hullNext[i2] = hullPrev[i1] = i0; + + hullTri[i0] = 0; + hullTri[i1] = 1; + hullTri[i2] = 2; + + hullHash.fill(-1); + hullHash[this._hashKey(i0x, i0y)] = i0; + hullHash[this._hashKey(i1x, i1y)] = i1; + hullHash[this._hashKey(i2x, i2y)] = i2; + + this.trianglesLen = 0; + this._addTriangle(i0, i1, i2, -1, -1, -1); + + for (let k = 0, xp, yp; k < this._ids.length; k++) { + const i = this._ids[k]; + const x = coords[2 * i]; + const y = coords[2 * i + 1]; + + // skip near-duplicate points + if (k > 0 && Math.abs(x - xp) <= EPSILON && Math.abs(y - yp) <= EPSILON) continue; + xp = x; + yp = y; + + // skip seed triangle points + if (i === i0 || i === i1 || i === i2) continue; + + // find a visible edge on the convex hull using edge hash + let start = 0; + for (let j = 0, key = this._hashKey(x, y); j < this._hashSize; j++) { + start = hullHash[(key + j) % this._hashSize]; + if (start !== -1 && start !== hullNext[start]) break; + } + + start = hullPrev[start]; + let e = start, q; + while (q = hullNext[e], orient2d(x, y, coords[2 * e], coords[2 * e + 1], coords[2 * q], coords[2 * q + 1]) >= 0) { + e = q; + if (e === start) { + e = -1; + break; + } + } + if (e === -1) continue; // likely a near-duplicate point; skip it + + // add the first triangle from the point + let t = this._addTriangle(e, i, hullNext[e], -1, -1, hullTri[e]); + + // recursively flip triangles from the point until they satisfy the Delaunay condition + hullTri[i] = this._legalize(t + 2); + hullTri[e] = t; // keep track of boundary triangles on the hull + hullSize++; + + // walk forward through the hull, adding more triangles and flipping recursively + let n = hullNext[e]; + while (q = hullNext[n], orient2d(x, y, coords[2 * n], coords[2 * n + 1], coords[2 * q], coords[2 * q + 1]) < 0) { + t = this._addTriangle(n, i, q, hullTri[i], -1, hullTri[n]); + hullTri[i] = this._legalize(t + 2); + hullNext[n] = n; // mark as removed + hullSize--; + n = q; + } + + // walk backward from the other side, adding more triangles and flipping + if (e === start) { + while (q = hullPrev[e], orient2d(x, y, coords[2 * q], coords[2 * q + 1], coords[2 * e], coords[2 * e + 1]) < 0) { + t = this._addTriangle(q, i, e, -1, hullTri[e], hullTri[q]); + this._legalize(t + 2); + hullTri[q] = t; + hullNext[e] = e; // mark as removed + hullSize--; + e = q; + } + } + + // update the hull indices + this._hullStart = hullPrev[i] = e; + hullNext[e] = hullPrev[n] = i; + hullNext[i] = n; + + // save the two new edges in the hash table + hullHash[this._hashKey(x, y)] = i; + hullHash[this._hashKey(coords[2 * e], coords[2 * e + 1])] = e; + } + + this.hull = new Uint32Array(hullSize); + for (let i = 0, e = this._hullStart; i < hullSize; i++) { + this.hull[i] = e; + e = hullNext[e]; + } + + // trim typed triangle mesh arrays + this.triangles = this._triangles.subarray(0, this.trianglesLen); + this.halfedges = this._halfedges.subarray(0, this.trianglesLen); + } + + _hashKey(x, y) { + return Math.floor(pseudoAngle(x - this._cx, y - this._cy) * this._hashSize) % this._hashSize; + } + + _legalize(a) { + const {_triangles: triangles, _halfedges: halfedges, coords} = this; + + let i = 0; + let ar = 0; + + // recursion eliminated with a fixed-size stack + while (true) { + const b = halfedges[a]; + + /* if the pair of triangles doesn't satisfy the Delaunay condition + * (p1 is inside the circumcircle of [p0, pl, pr]), flip them, + * then do the same check/flip recursively for the new pair of triangles + * + * pl pl + * /||\ / \ + * al/ || \bl al/ \a + * / || \ / \ + * / a||b \ flip /___ar___\ + * p0\ || /p1 => p0\---bl---/p1 + * \ || / \ / + * ar\ || /br b\ /br + * \||/ \ / + * pr pr + */ + const a0 = a - a % 3; + ar = a0 + (a + 2) % 3; + + if (b === -1) { // convex hull edge + if (i === 0) break; + a = EDGE_STACK[--i]; + continue; + } + + const b0 = b - b % 3; + const al = a0 + (a + 1) % 3; + const bl = b0 + (b + 2) % 3; + + const p0 = triangles[ar]; + const pr = triangles[a]; + const pl = triangles[al]; + const p1 = triangles[bl]; + + const illegal = inCircle( + coords[2 * p0], coords[2 * p0 + 1], + coords[2 * pr], coords[2 * pr + 1], + coords[2 * pl], coords[2 * pl + 1], + coords[2 * p1], coords[2 * p1 + 1]); + + if (illegal) { + triangles[a] = p1; + triangles[b] = p0; + + const hbl = halfedges[bl]; + + // edge swapped on the other side of the hull (rare); fix the halfedge reference + if (hbl === -1) { + let e = this._hullStart; + do { + if (this._hullTri[e] === bl) { + this._hullTri[e] = a; + break; + } + e = this._hullPrev[e]; + } while (e !== this._hullStart); + } + this._link(a, hbl); + this._link(b, halfedges[ar]); + this._link(ar, bl); + + const br = b0 + (b + 1) % 3; + + // don't worry about hitting the cap: it can only happen on extremely degenerate input + if (i < EDGE_STACK.length) { + EDGE_STACK[i++] = br; + } + } else { + if (i === 0) break; + a = EDGE_STACK[--i]; + } + } + + return ar; + } + + _link(a, b) { + this._halfedges[a] = b; + if (b !== -1) this._halfedges[b] = a; + } + + // add a new triangle given vertex indices and adjacent half-edge ids + _addTriangle(i0, i1, i2, a, b, c) { + const t = this.trianglesLen; + + this._triangles[t] = i0; + this._triangles[t + 1] = i1; + this._triangles[t + 2] = i2; + + this._link(t, a); + this._link(t + 1, b); + this._link(t + 2, c); + + this.trianglesLen += 3; + + return t; + } +} + +// monotonically increases with real angle, but doesn't need expensive trigonometry +function pseudoAngle(dx, dy) { + const p = dx / (Math.abs(dx) + Math.abs(dy)); + return (dy > 0 ? 3 - p : 1 + p) / 4; // [0..1] +} + +function dist(ax, ay, bx, by) { + const dx = ax - bx; + const dy = ay - by; + return dx * dx + dy * dy; +} + +function inCircle(ax, ay, bx, by, cx, cy, px, py) { + const dx = ax - px; + const dy = ay - py; + const ex = bx - px; + const ey = by - py; + const fx = cx - px; + const fy = cy - py; + + const ap = dx * dx + dy * dy; + const bp = ex * ex + ey * ey; + const cp = fx * fx + fy * fy; + + return dx * (ey * cp - bp * fy) - + dy * (ex * cp - bp * fx) + + ap * (ex * fy - ey * fx) < 0; +} + +function circumradius(ax, ay, bx, by, cx, cy) { + const dx = bx - ax; + const dy = by - ay; + const ex = cx - ax; + const ey = cy - ay; + + const bl = dx * dx + dy * dy; + const cl = ex * ex + ey * ey; + const d = 0.5 / (dx * ey - dy * ex); + + const x = (ey * bl - dy * cl) * d; + const y = (dx * cl - ex * bl) * d; + + return x * x + y * y; +} + +function circumcenter(ax, ay, bx, by, cx, cy) { + const dx = bx - ax; + const dy = by - ay; + const ex = cx - ax; + const ey = cy - ay; + + const bl = dx * dx + dy * dy; + const cl = ex * ex + ey * ey; + const d = 0.5 / (dx * ey - dy * ex); + + const x = ax + (ey * bl - dy * cl) * d; + const y = ay + (dx * cl - ex * bl) * d; + + return {x, y}; +} + +function quicksort(ids, dists, left, right) { + if (right - left <= 20) { + for (let i = left + 1; i <= right; i++) { + const temp = ids[i]; + const tempDist = dists[temp]; + let j = i - 1; + while (j >= left && dists[ids[j]] > tempDist) ids[j + 1] = ids[j--]; + ids[j + 1] = temp; + } + } else { + const median = (left + right) >> 1; + let i = left + 1; + let j = right; + swap(ids, median, i); + if (dists[ids[left]] > dists[ids[right]]) swap(ids, left, right); + if (dists[ids[i]] > dists[ids[right]]) swap(ids, i, right); + if (dists[ids[left]] > dists[ids[i]]) swap(ids, left, i); + + const temp = ids[i]; + const tempDist = dists[temp]; + while (true) { + do i++; while (dists[ids[i]] < tempDist); + do j--; while (dists[ids[j]] > tempDist); + if (j < i) break; + swap(ids, i, j); + } + ids[left + 1] = ids[j]; + ids[j] = temp; + + if (right - i + 1 >= j - left) { + quicksort(ids, dists, i, right); + quicksort(ids, dists, left, j - 1); + } else { + quicksort(ids, dists, left, j - 1); + quicksort(ids, dists, i, right); + } + } +} + +function swap(arr, i, j) { + const tmp = arr[i]; + arr[i] = arr[j]; + arr[j] = tmp; +} + +function defaultGetX(p) { + return p[0]; +} +function defaultGetY(p) { + return p[1]; +} + +const epsilon = 1e-6; + +class Path { + constructor() { + this._x0 = this._y0 = // start of current subpath + this._x1 = this._y1 = null; // end of current subpath + this._ = ""; + } + moveTo(x, y) { + this._ += `M${this._x0 = this._x1 = +x},${this._y0 = this._y1 = +y}`; + } + closePath() { + if (this._x1 !== null) { + this._x1 = this._x0, this._y1 = this._y0; + this._ += "Z"; + } + } + lineTo(x, y) { + this._ += `L${this._x1 = +x},${this._y1 = +y}`; + } + arc(x, y, r) { + x = +x, y = +y, r = +r; + const x0 = x + r; + const y0 = y; + if (r < 0) throw new Error("negative radius"); + if (this._x1 === null) this._ += `M${x0},${y0}`; + else if (Math.abs(this._x1 - x0) > epsilon || Math.abs(this._y1 - y0) > epsilon) this._ += "L" + x0 + "," + y0; + if (!r) return; + this._ += `A${r},${r},0,1,1,${x - r},${y}A${r},${r},0,1,1,${this._x1 = x0},${this._y1 = y0}`; + } + rect(x, y, w, h) { + this._ += `M${this._x0 = this._x1 = +x},${this._y0 = this._y1 = +y}h${+w}v${+h}h${-w}Z`; + } + value() { + return this._ || null; + } +} + +class Polygon { + constructor() { + this._ = []; + } + moveTo(x, y) { + this._.push([x, y]); + } + closePath() { + this._.push(this._[0].slice()); + } + lineTo(x, y) { + this._.push([x, y]); + } + value() { + return this._.length ? this._ : null; + } +} + +class Voronoi { + constructor(delaunay, [xmin, ymin, xmax, ymax] = [0, 0, 960, 500]) { + if (!((xmax = +xmax) >= (xmin = +xmin)) || !((ymax = +ymax) >= (ymin = +ymin))) throw new Error("invalid bounds"); + this.delaunay = delaunay; + this._circumcenters = new Float64Array(delaunay.points.length * 2); + this.vectors = new Float64Array(delaunay.points.length * 2); + this.xmax = xmax, this.xmin = xmin; + this.ymax = ymax, this.ymin = ymin; + this._init(); + } + update() { + this.delaunay.update(); + this._init(); + return this; + } + _init() { + const {delaunay: {points, hull, triangles}, vectors} = this; + let bx, by; // lazily computed barycenter of the hull + + // Compute circumcenters. + const circumcenters = this.circumcenters = this._circumcenters.subarray(0, triangles.length / 3 * 2); + for (let i = 0, j = 0, n = triangles.length, x, y; i < n; i += 3, j += 2) { + const t1 = triangles[i] * 2; + const t2 = triangles[i + 1] * 2; + const t3 = triangles[i + 2] * 2; + const x1 = points[t1]; + const y1 = points[t1 + 1]; + const x2 = points[t2]; + const y2 = points[t2 + 1]; + const x3 = points[t3]; + const y3 = points[t3 + 1]; + + const dx = x2 - x1; + const dy = y2 - y1; + const ex = x3 - x1; + const ey = y3 - y1; + const ab = (dx * ey - dy * ex) * 2; + + if (Math.abs(ab) < 1e-9) { + // For a degenerate triangle, the circumcenter is at the infinity, in a + // direction orthogonal to the halfedge and away from the “center” of + // the diagram , defined as the hull’s barycenter. + if (bx === undefined) { + bx = by = 0; + for (const i of hull) bx += points[i * 2], by += points[i * 2 + 1]; + bx /= hull.length, by /= hull.length; + } + const a = 1e9 * Math.sign((bx - x1) * ey - (by - y1) * ex); + x = (x1 + x3) / 2 - a * ey; + y = (y1 + y3) / 2 + a * ex; + } else { + const d = 1 / ab; + const bl = dx * dx + dy * dy; + const cl = ex * ex + ey * ey; + x = x1 + (ey * bl - dy * cl) * d; + y = y1 + (dx * cl - ex * bl) * d; + } + circumcenters[j] = x; + circumcenters[j + 1] = y; + } + + // Compute exterior cell rays. + let h = hull[hull.length - 1]; + let p0, p1 = h * 4; + let x0, x1 = points[2 * h]; + let y0, y1 = points[2 * h + 1]; + vectors.fill(0); + for (let i = 0; i < hull.length; ++i) { + h = hull[i]; + p0 = p1, x0 = x1, y0 = y1; + p1 = h * 4, x1 = points[2 * h], y1 = points[2 * h + 1]; + vectors[p0 + 2] = vectors[p1] = y0 - y1; + vectors[p0 + 3] = vectors[p1 + 1] = x1 - x0; + } + } + render(context) { + const buffer = context == null ? context = new Path : undefined; + const {delaunay: {halfedges, inedges, hull}, circumcenters, vectors} = this; + if (hull.length <= 1) return null; + for (let i = 0, n = halfedges.length; i < n; ++i) { + const j = halfedges[i]; + if (j < i) continue; + const ti = Math.floor(i / 3) * 2; + const tj = Math.floor(j / 3) * 2; + const xi = circumcenters[ti]; + const yi = circumcenters[ti + 1]; + const xj = circumcenters[tj]; + const yj = circumcenters[tj + 1]; + this._renderSegment(xi, yi, xj, yj, context); + } + let h0, h1 = hull[hull.length - 1]; + for (let i = 0; i < hull.length; ++i) { + h0 = h1, h1 = hull[i]; + const t = Math.floor(inedges[h1] / 3) * 2; + const x = circumcenters[t]; + const y = circumcenters[t + 1]; + const v = h0 * 4; + const p = this._project(x, y, vectors[v + 2], vectors[v + 3]); + if (p) this._renderSegment(x, y, p[0], p[1], context); + } + return buffer && buffer.value(); + } + renderBounds(context) { + const buffer = context == null ? context = new Path : undefined; + context.rect(this.xmin, this.ymin, this.xmax - this.xmin, this.ymax - this.ymin); + return buffer && buffer.value(); + } + renderCell(i, context) { + const buffer = context == null ? context = new Path : undefined; + const points = this._clip(i); + if (points === null || !points.length) return; + context.moveTo(points[0], points[1]); + let n = points.length; + while (points[0] === points[n-2] && points[1] === points[n-1] && n > 1) n -= 2; + for (let i = 2; i < n; i += 2) { + if (points[i] !== points[i-2] || points[i+1] !== points[i-1]) + context.lineTo(points[i], points[i + 1]); + } + context.closePath(); + return buffer && buffer.value(); + } + *cellPolygons() { + const {delaunay: {points}} = this; + for (let i = 0, n = points.length / 2; i < n; ++i) { + const cell = this.cellPolygon(i); + if (cell) cell.index = i, yield cell; + } + } + cellPolygon(i) { + const polygon = new Polygon; + this.renderCell(i, polygon); + return polygon.value(); + } + _renderSegment(x0, y0, x1, y1, context) { + let S; + const c0 = this._regioncode(x0, y0); + const c1 = this._regioncode(x1, y1); + if (c0 === 0 && c1 === 0) { + context.moveTo(x0, y0); + context.lineTo(x1, y1); + } else if (S = this._clipSegment(x0, y0, x1, y1, c0, c1)) { + context.moveTo(S[0], S[1]); + context.lineTo(S[2], S[3]); + } + } + contains(i, x, y) { + if ((x = +x, x !== x) || (y = +y, y !== y)) return false; + return this.delaunay._step(i, x, y) === i; + } + *neighbors(i) { + const ci = this._clip(i); + if (ci) for (const j of this.delaunay.neighbors(i)) { + const cj = this._clip(j); + // find the common edge + if (cj) loop: for (let ai = 0, li = ci.length; ai < li; ai += 2) { + for (let aj = 0, lj = cj.length; aj < lj; aj += 2) { + if (ci[ai] === cj[aj] + && ci[ai + 1] === cj[aj + 1] + && ci[(ai + 2) % li] === cj[(aj + lj - 2) % lj] + && ci[(ai + 3) % li] === cj[(aj + lj - 1) % lj]) { + yield j; + break loop; + } + } + } + } + } + _cell(i) { + const {circumcenters, delaunay: {inedges, halfedges, triangles}} = this; + const e0 = inedges[i]; + if (e0 === -1) return null; // coincident point + const points = []; + let e = e0; + do { + const t = Math.floor(e / 3); + points.push(circumcenters[t * 2], circumcenters[t * 2 + 1]); + e = e % 3 === 2 ? e - 2 : e + 1; + if (triangles[e] !== i) break; // bad triangulation + e = halfedges[e]; + } while (e !== e0 && e !== -1); + return points; + } + _clip(i) { + // degenerate case (1 valid point: return the box) + if (i === 0 && this.delaunay.hull.length === 1) { + return [this.xmax, this.ymin, this.xmax, this.ymax, this.xmin, this.ymax, this.xmin, this.ymin]; + } + const points = this._cell(i); + if (points === null) return null; + const {vectors: V} = this; + const v = i * 4; + return this._simplify(V[v] || V[v + 1] + ? this._clipInfinite(i, points, V[v], V[v + 1], V[v + 2], V[v + 3]) + : this._clipFinite(i, points)); + } + _clipFinite(i, points) { + const n = points.length; + let P = null; + let x0, y0, x1 = points[n - 2], y1 = points[n - 1]; + let c0, c1 = this._regioncode(x1, y1); + let e0, e1 = 0; + for (let j = 0; j < n; j += 2) { + x0 = x1, y0 = y1, x1 = points[j], y1 = points[j + 1]; + c0 = c1, c1 = this._regioncode(x1, y1); + if (c0 === 0 && c1 === 0) { + e0 = e1, e1 = 0; + if (P) P.push(x1, y1); + else P = [x1, y1]; + } else { + let S, sx0, sy0, sx1, sy1; + if (c0 === 0) { + if ((S = this._clipSegment(x0, y0, x1, y1, c0, c1)) === null) continue; + [sx0, sy0, sx1, sy1] = S; + } else { + if ((S = this._clipSegment(x1, y1, x0, y0, c1, c0)) === null) continue; + [sx1, sy1, sx0, sy0] = S; + e0 = e1, e1 = this._edgecode(sx0, sy0); + if (e0 && e1) this._edge(i, e0, e1, P, P.length); + if (P) P.push(sx0, sy0); + else P = [sx0, sy0]; + } + e0 = e1, e1 = this._edgecode(sx1, sy1); + if (e0 && e1) this._edge(i, e0, e1, P, P.length); + if (P) P.push(sx1, sy1); + else P = [sx1, sy1]; + } + } + if (P) { + e0 = e1, e1 = this._edgecode(P[0], P[1]); + if (e0 && e1) this._edge(i, e0, e1, P, P.length); + } else if (this.contains(i, (this.xmin + this.xmax) / 2, (this.ymin + this.ymax) / 2)) { + return [this.xmax, this.ymin, this.xmax, this.ymax, this.xmin, this.ymax, this.xmin, this.ymin]; + } + return P; + } + _clipSegment(x0, y0, x1, y1, c0, c1) { + // for more robustness, always consider the segment in the same order + const flip = c0 < c1; + if (flip) [x0, y0, x1, y1, c0, c1] = [x1, y1, x0, y0, c1, c0]; + while (true) { + if (c0 === 0 && c1 === 0) return flip ? [x1, y1, x0, y0] : [x0, y0, x1, y1]; + if (c0 & c1) return null; + let x, y, c = c0 || c1; + if (c & 0b1000) x = x0 + (x1 - x0) * (this.ymax - y0) / (y1 - y0), y = this.ymax; + else if (c & 0b0100) x = x0 + (x1 - x0) * (this.ymin - y0) / (y1 - y0), y = this.ymin; + else if (c & 0b0010) y = y0 + (y1 - y0) * (this.xmax - x0) / (x1 - x0), x = this.xmax; + else y = y0 + (y1 - y0) * (this.xmin - x0) / (x1 - x0), x = this.xmin; + if (c0) x0 = x, y0 = y, c0 = this._regioncode(x0, y0); + else x1 = x, y1 = y, c1 = this._regioncode(x1, y1); + } + } + _clipInfinite(i, points, vx0, vy0, vxn, vyn) { + let P = Array.from(points), p; + if (p = this._project(P[0], P[1], vx0, vy0)) P.unshift(p[0], p[1]); + if (p = this._project(P[P.length - 2], P[P.length - 1], vxn, vyn)) P.push(p[0], p[1]); + if (P = this._clipFinite(i, P)) { + for (let j = 0, n = P.length, c0, c1 = this._edgecode(P[n - 2], P[n - 1]); j < n; j += 2) { + c0 = c1, c1 = this._edgecode(P[j], P[j + 1]); + if (c0 && c1) j = this._edge(i, c0, c1, P, j), n = P.length; + } + } else if (this.contains(i, (this.xmin + this.xmax) / 2, (this.ymin + this.ymax) / 2)) { + P = [this.xmin, this.ymin, this.xmax, this.ymin, this.xmax, this.ymax, this.xmin, this.ymax]; + } + return P; + } + _edge(i, e0, e1, P, j) { + while (e0 !== e1) { + let x, y; + switch (e0) { + case 0b0101: e0 = 0b0100; continue; // top-left + case 0b0100: e0 = 0b0110, x = this.xmax, y = this.ymin; break; // top + case 0b0110: e0 = 0b0010; continue; // top-right + case 0b0010: e0 = 0b1010, x = this.xmax, y = this.ymax; break; // right + case 0b1010: e0 = 0b1000; continue; // bottom-right + case 0b1000: e0 = 0b1001, x = this.xmin, y = this.ymax; break; // bottom + case 0b1001: e0 = 0b0001; continue; // bottom-left + case 0b0001: e0 = 0b0101, x = this.xmin, y = this.ymin; break; // left + } + // Note: this implicitly checks for out of bounds: if P[j] or P[j+1] are + // undefined, the conditional statement will be executed. + if ((P[j] !== x || P[j + 1] !== y) && this.contains(i, x, y)) { + P.splice(j, 0, x, y), j += 2; + } + } + return j; + } + _project(x0, y0, vx, vy) { + let t = Infinity, c, x, y; + if (vy < 0) { // top + if (y0 <= this.ymin) return null; + if ((c = (this.ymin - y0) / vy) < t) y = this.ymin, x = x0 + (t = c) * vx; + } else if (vy > 0) { // bottom + if (y0 >= this.ymax) return null; + if ((c = (this.ymax - y0) / vy) < t) y = this.ymax, x = x0 + (t = c) * vx; + } + if (vx > 0) { // right + if (x0 >= this.xmax) return null; + if ((c = (this.xmax - x0) / vx) < t) x = this.xmax, y = y0 + (t = c) * vy; + } else if (vx < 0) { // left + if (x0 <= this.xmin) return null; + if ((c = (this.xmin - x0) / vx) < t) x = this.xmin, y = y0 + (t = c) * vy; + } + return [x, y]; + } + _edgecode(x, y) { + return (x === this.xmin ? 0b0001 + : x === this.xmax ? 0b0010 : 0b0000) + | (y === this.ymin ? 0b0100 + : y === this.ymax ? 0b1000 : 0b0000); + } + _regioncode(x, y) { + return (x < this.xmin ? 0b0001 + : x > this.xmax ? 0b0010 : 0b0000) + | (y < this.ymin ? 0b0100 + : y > this.ymax ? 0b1000 : 0b0000); + } + _simplify(P) { + if (P && P.length > 4) { + for (let i = 0; i < P.length; i+= 2) { + const j = (i + 2) % P.length, k = (i + 4) % P.length; + if (P[i] === P[j] && P[j] === P[k] || P[i + 1] === P[j + 1] && P[j + 1] === P[k + 1]) { + P.splice(j, 2), i -= 2; + } + } + if (!P.length) P = null; + } + return P; + } +} + +const tau = 2 * Math.PI, pow = Math.pow; + +function pointX(p) { + return p[0]; +} + +function pointY(p) { + return p[1]; +} + +// A triangulation is collinear if all its triangles have a non-null area +function collinear(d) { + const {triangles, coords} = d; + for (let i = 0; i < triangles.length; i += 3) { + const a = 2 * triangles[i], + b = 2 * triangles[i + 1], + c = 2 * triangles[i + 2], + cross = (coords[c] - coords[a]) * (coords[b + 1] - coords[a + 1]) + - (coords[b] - coords[a]) * (coords[c + 1] - coords[a + 1]); + if (cross > 1e-10) return false; + } + return true; +} + +function jitter(x, y, r) { + return [x + Math.sin(x + y) * r, y + Math.cos(x - y) * r]; +} + +class Delaunay { + static from(points, fx = pointX, fy = pointY, that) { + return new Delaunay("length" in points + ? flatArray(points, fx, fy, that) + : Float64Array.from(flatIterable(points, fx, fy, that))); + } + constructor(points) { + this._delaunator = new Delaunator(points); + this.inedges = new Int32Array(points.length / 2); + this._hullIndex = new Int32Array(points.length / 2); + this.points = this._delaunator.coords; + this._init(); + } + update() { + this._delaunator.update(); + this._init(); + return this; + } + _init() { + const d = this._delaunator, points = this.points; + + // check for collinear + if (d.hull && d.hull.length > 2 && collinear(d)) { + this.collinear = Int32Array.from({length: points.length/2}, (_,i) => i) + .sort((i, j) => points[2 * i] - points[2 * j] || points[2 * i + 1] - points[2 * j + 1]); // for exact neighbors + const e = this.collinear[0], f = this.collinear[this.collinear.length - 1], + bounds = [ points[2 * e], points[2 * e + 1], points[2 * f], points[2 * f + 1] ], + r = 1e-8 * Math.hypot(bounds[3] - bounds[1], bounds[2] - bounds[0]); + for (let i = 0, n = points.length / 2; i < n; ++i) { + const p = jitter(points[2 * i], points[2 * i + 1], r); + points[2 * i] = p[0]; + points[2 * i + 1] = p[1]; + } + this._delaunator = new Delaunator(points); + } else { + delete this.collinear; + } + + const halfedges = this.halfedges = this._delaunator.halfedges; + const hull = this.hull = this._delaunator.hull; + const triangles = this.triangles = this._delaunator.triangles; + const inedges = this.inedges.fill(-1); + const hullIndex = this._hullIndex.fill(-1); + + // Compute an index from each point to an (arbitrary) incoming halfedge + // Used to give the first neighbor of each point; for this reason, + // on the hull we give priority to exterior halfedges + for (let e = 0, n = halfedges.length; e < n; ++e) { + const p = triangles[e % 3 === 2 ? e - 2 : e + 1]; + if (halfedges[e] === -1 || inedges[p] === -1) inedges[p] = e; + } + for (let i = 0, n = hull.length; i < n; ++i) { + hullIndex[hull[i]] = i; + } + + // degenerate case: 1 or 2 (distinct) points + if (hull.length <= 2 && hull.length > 0) { + this.triangles = new Int32Array(3).fill(-1); + this.halfedges = new Int32Array(3).fill(-1); + this.triangles[0] = hull[0]; + inedges[hull[0]] = 1; + if (hull.length === 2) { + inedges[hull[1]] = 0; + this.triangles[1] = hull[1]; + this.triangles[2] = hull[1]; + } + } + } + voronoi(bounds) { + return new Voronoi(this, bounds); + } + *neighbors(i) { + const {inedges, hull, _hullIndex, halfedges, triangles, collinear} = this; + + // degenerate case with several collinear points + if (collinear) { + const l = collinear.indexOf(i); + if (l > 0) yield collinear[l - 1]; + if (l < collinear.length - 1) yield collinear[l + 1]; + return; + } + + const e0 = inedges[i]; + if (e0 === -1) return; // coincident point + let e = e0, p0 = -1; + do { + yield p0 = triangles[e]; + e = e % 3 === 2 ? e - 2 : e + 1; + if (triangles[e] !== i) return; // bad triangulation + e = halfedges[e]; + if (e === -1) { + const p = hull[(_hullIndex[i] + 1) % hull.length]; + if (p !== p0) yield p; + return; + } + } while (e !== e0); + } + find(x, y, i = 0) { + if ((x = +x, x !== x) || (y = +y, y !== y)) return -1; + const i0 = i; + let c; + while ((c = this._step(i, x, y)) >= 0 && c !== i && c !== i0) i = c; + return c; + } + _step(i, x, y) { + const {inedges, hull, _hullIndex, halfedges, triangles, points} = this; + if (inedges[i] === -1 || !points.length) return (i + 1) % (points.length >> 1); + let c = i; + let dc = pow(x - points[i * 2], 2) + pow(y - points[i * 2 + 1], 2); + const e0 = inedges[i]; + let e = e0; + do { + let t = triangles[e]; + const dt = pow(x - points[t * 2], 2) + pow(y - points[t * 2 + 1], 2); + if (dt < dc) dc = dt, c = t; + e = e % 3 === 2 ? e - 2 : e + 1; + if (triangles[e] !== i) break; // bad triangulation + e = halfedges[e]; + if (e === -1) { + e = hull[(_hullIndex[i] + 1) % hull.length]; + if (e !== t) { + if (pow(x - points[e * 2], 2) + pow(y - points[e * 2 + 1], 2) < dc) return e; + } + break; + } + } while (e !== e0); + return c; + } + render(context) { + const buffer = context == null ? context = new Path : undefined; + const {points, halfedges, triangles} = this; + for (let i = 0, n = halfedges.length; i < n; ++i) { + const j = halfedges[i]; + if (j < i) continue; + const ti = triangles[i] * 2; + const tj = triangles[j] * 2; + context.moveTo(points[ti], points[ti + 1]); + context.lineTo(points[tj], points[tj + 1]); + } + this.renderHull(context); + return buffer && buffer.value(); + } + renderPoints(context, r) { + if (r === undefined && (!context || typeof context.moveTo !== "function")) r = context, context = null; + r = r == undefined ? 2 : +r; + const buffer = context == null ? context = new Path : undefined; + const {points} = this; + for (let i = 0, n = points.length; i < n; i += 2) { + const x = points[i], y = points[i + 1]; + context.moveTo(x + r, y); + context.arc(x, y, r, 0, tau); + } + return buffer && buffer.value(); + } + renderHull(context) { + const buffer = context == null ? context = new Path : undefined; + const {hull, points} = this; + const h = hull[0] * 2, n = hull.length; + context.moveTo(points[h], points[h + 1]); + for (let i = 1; i < n; ++i) { + const h = 2 * hull[i]; + context.lineTo(points[h], points[h + 1]); + } + context.closePath(); + return buffer && buffer.value(); + } + hullPolygon() { + const polygon = new Polygon; + this.renderHull(polygon); + return polygon.value(); + } + renderTriangle(i, context) { + const buffer = context == null ? context = new Path : undefined; + const {points, triangles} = this; + const t0 = triangles[i *= 3] * 2; + const t1 = triangles[i + 1] * 2; + const t2 = triangles[i + 2] * 2; + context.moveTo(points[t0], points[t0 + 1]); + context.lineTo(points[t1], points[t1 + 1]); + context.lineTo(points[t2], points[t2 + 1]); + context.closePath(); + return buffer && buffer.value(); + } + *trianglePolygons() { + const {triangles} = this; + for (let i = 0, n = triangles.length / 3; i < n; ++i) { + yield this.trianglePolygon(i); + } + } + trianglePolygon(i) { + const polygon = new Polygon; + this.renderTriangle(i, polygon); + return polygon.value(); + } +} + +function flatArray(points, fx, fy, that) { + const n = points.length; + const array = new Float64Array(n * 2); + for (let i = 0; i < n; ++i) { + const p = points[i]; + array[i * 2] = fx.call(that, p, i, points); + array[i * 2 + 1] = fy.call(that, p, i, points); + } + return array; +} + +function* flatIterable(points, fx, fy, that) { + let i = 0; + for (const p of points) { + yield fx.call(that, p, i, points); + yield fy.call(that, p, i, points); + ++i; + } +} + +exports.Delaunay = Delaunay; +exports.Voronoi = Voronoi; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-delaunay/dist/d3-delaunay.min.js b/frontend/node_modules/d3-delaunay/dist/d3-delaunay.min.js new file mode 100644 index 0000000..b9f76af --- /dev/null +++ b/frontend/node_modules/d3-delaunay/dist/d3-delaunay.min.js @@ -0,0 +1,2 @@ +// https://github.com/d3/d3-delaunay v6.0.4 Copyright 2018-2021 Observable, Inc., 2021 Mapbox +!function(t,i){"object"==typeof exports&&"undefined"!=typeof module?i(exports):"function"==typeof define&&define.amd?define(["exports"],i):i((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{})}(this,(function(t){"use strict";const i=134217729;function e(t,i,e,n,s){let l,h,r,o,a=i[0],c=n[0],u=0,f=0;c>a==c>-a?(l=a,a=i[++u]):(l=c,c=n[++f]);let _=0;if(ua==c>-a?(h=a+l,r=l-(h-a),a=i[++u]):(h=c+l,r=l-(h-c),c=n[++f]),l=h,0!==r&&(s[_++]=r);ua==c>-a?(h=l+a,o=h-l,r=l-(h-o)+(a-o),a=i[++u]):(h=l+c,o=h-l,r=l-(h-o)+(c-o),c=n[++f]),l=h,0!==r&&(s[_++]=r);for(;u0!=d>0)return g;const y=Math.abs(_+d);return Math.abs(g)>=33306690738754716e-32*y?g:-function(t,n,a,c,u,f,_){let d,g,y,m,x,p,w,v,b,T,M,A,k,$,P,S,I,z;const F=t-u,U=a-u,K=n-f,L=c-f;$=F*L,p=i*F,w=p-(p-F),v=F-w,p=i*L,b=p-(p-L),T=L-b,P=v*T-($-w*b-v*b-w*T),S=K*U,p=i*K,w=p-(p-K),v=K-w,p=i*U,b=p-(p-U),T=U-b,I=v*T-(S-w*b-v*b-w*T),M=P-I,x=P-M,s[0]=P-(M+x)+(x-I),A=$+M,x=A-$,k=$-(A-x)+(M-x),M=k-S,x=k-M,s[1]=k-(M+x)+(x-S),z=A+M,x=z-A,s[2]=A-(z-x)+(M-x),s[3]=z;let j=function(t,i){let e=i[0];for(let n=1;n=H||-j>=H)return j;if(x=t-F,d=t-(F+x)+(x-u),x=a-U,y=a-(U+x)+(x-u),x=n-K,g=n-(K+x)+(x-f),x=c-L,m=c-(L+x)+(x-f),0===d&&0===g&&0===y&&0===m)return j;if(H=11093356479670487e-47*_+33306690738754706e-32*Math.abs(j),j+=F*m+L*d-(K*y+U*g),j>=H||-j>=H)return j;$=d*L,p=i*d,w=p-(p-d),v=d-w,p=i*L,b=p-(p-L),T=L-b,P=v*T-($-w*b-v*b-w*T),S=g*U,p=i*g,w=p-(p-g),v=g-w,p=i*U,b=p-(p-U),T=U-b,I=v*T-(S-w*b-v*b-w*T),M=P-I,x=P-M,o[0]=P-(M+x)+(x-I),A=$+M,x=A-$,k=$-(A-x)+(M-x),M=k-S,x=k-M,o[1]=k-(M+x)+(x-S),z=A+M,x=z-A,o[2]=A-(z-x)+(M-x),o[3]=z;const E=e(4,s,4,o,l);$=F*m,p=i*F,w=p-(p-F),v=F-w,p=i*m,b=p-(p-m),T=m-b,P=v*T-($-w*b-v*b-w*T),S=K*y,p=i*K,w=p-(p-K),v=K-w,p=i*y,b=p-(p-y),T=y-b,I=v*T-(S-w*b-v*b-w*T),M=P-I,x=P-M,o[0]=P-(M+x)+(x-I),A=$+M,x=A-$,k=$-(A-x)+(M-x),M=k-S,x=k-M,o[1]=k-(M+x)+(x-S),z=A+M,x=z-A,o[2]=A-(z-x)+(M-x),o[3]=z;const C=e(E,l,4,o,h);$=d*m,p=i*d,w=p-(p-d),v=d-w,p=i*m,b=p-(p-m),T=m-b,P=v*T-($-w*b-v*b-w*T),S=g*y,p=i*g,w=p-(p-g),v=g-w,p=i*y,b=p-(p-y),T=y-b,I=v*T-(S-w*b-v*b-w*T),M=P-I,x=P-M,o[0]=P-(M+x)+(x-I),A=$+M,x=A-$,k=$-(A-x)+(M-x),M=k-S,x=k-M,o[1]=k-(M+x)+(x-S),z=A+M,x=z-A,o[2]=A-(z-x)+(M-x),o[3]=z;const N=e(C,h,4,o,r);return r[N-1]}(t,n,a,c,u,f,y)}const c=Math.pow(2,-52),u=new Uint32Array(512);class f{static from(t,i=x,e=p){const n=t.length,s=new Float64Array(2*n);for(let l=0;l>1;if(i>0&&"number"!=typeof t[0])throw new Error("Expected coords to contain numbers.");this.coords=t;const e=Math.max(2*i-5,0);this._triangles=new Uint32Array(3*e),this._halfedges=new Int32Array(3*e),this._hashSize=Math.ceil(Math.sqrt(i)),this._hullPrev=new Uint32Array(i),this._hullNext=new Uint32Array(i),this._hullTri=new Uint32Array(i),this._hullHash=new Int32Array(this._hashSize).fill(-1),this._ids=new Uint32Array(i),this._dists=new Float64Array(i),this.update()}update(){const{coords:t,_hullPrev:i,_hullNext:e,_hullTri:n,_hullHash:s}=this,l=t.length>>1;let h=1/0,r=1/0,o=-1/0,u=-1/0;for(let i=0;io&&(o=e),n>u&&(u=n),this._ids[i]=i}const f=(h+o)/2,d=(r+u)/2;let m,x,p,w=1/0;for(let i=0;i0&&(x=i,w=e)}let T=t[2*x],M=t[2*x+1],A=1/0;for(let i=0;in&&(i[e++]=s,n=this._dists[s])}return this.hull=i.subarray(0,e),this.triangles=new Uint32Array(0),void(this.halfedges=new Uint32Array(0))}if(a(v,b,T,M,k,$)<0){const t=x,i=T,e=M;x=p,T=k,M=$,p=t,k=i,$=e}const P=function(t,i,e,n,s,l){const h=e-t,r=n-i,o=s-t,a=l-i,c=h*h+r*r,u=o*o+a*a,f=.5/(h*a-r*o);return{x:t+(a*c-r*u)*f,y:i+(h*u-o*c)*f}}(v,b,T,M,k,$);this._cx=P.x,this._cy=P.y;for(let i=0;i0&&Math.abs(u-l)<=c&&Math.abs(f-h)<=c)continue;if(l=u,h=f,o===m||o===x||o===p)continue;let _=0;for(let t=0,i=this._hashKey(u,f);t=0;)if(g=d,g===_){g=-1;break}if(-1===g)continue;let y=this._addTriangle(g,o,e[g],-1,-1,n[g]);n[o]=this._legalize(y+2),n[g]=y,S++;let w=e[g];for(;d=e[w],a(u,f,t[2*w],t[2*w+1],t[2*d],t[2*d+1])<0;)y=this._addTriangle(w,o,d,n[o],-1,n[w]),n[o]=this._legalize(y+2),e[w]=w,S--,w=d;if(g===_)for(;d=i[g],a(u,f,t[2*d],t[2*d+1],t[2*g],t[2*g+1])<0;)y=this._addTriangle(d,o,g,-1,n[g],n[d]),this._legalize(y+2),n[d]=y,e[g]=g,S--,g=d;this._hullStart=i[o]=g,e[g]=i[w]=o,e[o]=w,s[this._hashKey(u,f)]=o,s[this._hashKey(t[2*g],t[2*g+1])]=g}this.hull=new Uint32Array(S);for(let t=0,i=this._hullStart;t0?3-e:1+e)/4}(t-this._cx,i-this._cy)*this._hashSize)%this._hashSize}_legalize(t){const{_triangles:i,_halfedges:e,coords:n}=this;let s=0,l=0;for(;;){const h=e[t],r=t-t%3;if(l=r+(t+2)%3,-1===h){if(0===s)break;t=u[--s];continue}const o=h-h%3,a=r+(t+1)%3,c=o+(h+2)%3,f=i[l],_=i[t],g=i[a],y=i[c];if(d(n[2*f],n[2*f+1],n[2*_],n[2*_+1],n[2*g],n[2*g+1],n[2*y],n[2*y+1])){i[t]=y,i[h]=f;const n=e[c];if(-1===n){let i=this._hullStart;do{if(this._hullTri[i]===c){this._hullTri[i]=t;break}i=this._hullPrev[i]}while(i!==this._hullStart)}this._link(t,n),this._link(h,e[l]),this._link(l,c);const r=o+(h+1)%3;s=e&&i[t[h]]>l;)t[h+1]=t[h--];t[h+1]=n}else{let s=e+1,l=n;m(t,e+n>>1,s),i[t[e]]>i[t[n]]&&m(t,e,n),i[t[s]]>i[t[n]]&&m(t,s,n),i[t[e]]>i[t[s]]&&m(t,e,s);const h=t[s],r=i[h];for(;;){do{s++}while(i[t[s]]r);if(l=l-e?(y(t,i,s,n),y(t,i,e,l-1)):(y(t,i,e,l-1),y(t,i,s,n))}}function m(t,i,e){const n=t[i];t[i]=t[e],t[e]=n}function x(t){return t[0]}function p(t){return t[1]}const w=1e-6;class v{constructor(){this._x0=this._y0=this._x1=this._y1=null,this._=""}moveTo(t,i){this._+=`M${this._x0=this._x1=+t},${this._y0=this._y1=+i}`}closePath(){null!==this._x1&&(this._x1=this._x0,this._y1=this._y0,this._+="Z")}lineTo(t,i){this._+=`L${this._x1=+t},${this._y1=+i}`}arc(t,i,e){const n=(t=+t)+(e=+e),s=i=+i;if(e<0)throw new Error("negative radius");null===this._x1?this._+=`M${n},${s}`:(Math.abs(this._x1-n)>w||Math.abs(this._y1-s)>w)&&(this._+="L"+n+","+s),e&&(this._+=`A${e},${e},0,1,1,${t-e},${i}A${e},${e},0,1,1,${this._x1=n},${this._y1=s}`)}rect(t,i,e,n){this._+=`M${this._x0=this._x1=+t},${this._y0=this._y1=+i}h${+e}v${+n}h${-e}Z`}value(){return this._||null}}class b{constructor(){this._=[]}moveTo(t,i){this._.push([t,i])}closePath(){this._.push(this._[0].slice())}lineTo(t,i){this._.push([t,i])}value(){return this._.length?this._:null}}class T{constructor(t,[i,e,n,s]=[0,0,960,500]){if(!((n=+n)>=(i=+i)&&(s=+s)>=(e=+e)))throw new Error("invalid bounds");this.delaunay=t,this._circumcenters=new Float64Array(2*t.points.length),this.vectors=new Float64Array(2*t.points.length),this.xmax=n,this.xmin=i,this.ymax=s,this.ymin=e,this._init()}update(){return this.delaunay.update(),this._init(),this}_init(){const{delaunay:{points:t,hull:i,triangles:e},vectors:n}=this;let s,l;const h=this.circumcenters=this._circumcenters.subarray(0,e.length/3*2);for(let n,r,o=0,a=0,c=e.length;o1;)s-=2;for(let t=2;t0){if(i>=this.ymax)return null;(s=(this.ymax-i)/n)0){if(t>=this.xmax)return null;(s=(this.xmax-t)/e)this.xmax?2:0)|(ithis.ymax?8:0)}_simplify(t){if(t&&t.length>4){for(let i=0;i2&&function(t){const{triangles:i,coords:e}=t;for(let t=0;t1e-10)return!1}return!0}(t)){this.collinear=Int32Array.from({length:i.length/2},((t,i)=>i)).sort(((t,e)=>i[2*t]-i[2*e]||i[2*t+1]-i[2*e+1]));const t=this.collinear[0],e=this.collinear[this.collinear.length-1],n=[i[2*t],i[2*t+1],i[2*e],i[2*e+1]],s=1e-8*Math.hypot(n[3]-n[1],n[2]-n[0]);for(let t=0,e=i.length/2;t0&&(this.triangles=new Int32Array(3).fill(-1),this.halfedges=new Int32Array(3).fill(-1),this.triangles[0]=n[0],l[n[0]]=1,2===n.length&&(l[n[1]]=0,this.triangles[1]=n[1],this.triangles[2]=n[1]))}voronoi(t){return new T(this,t)}*neighbors(t){const{inedges:i,hull:e,_hullIndex:n,halfedges:s,triangles:l,collinear:h}=this;if(h){const i=h.indexOf(t);return i>0&&(yield h[i-1]),void(i=0&&s!==e&&s!==n;)e=s;return s}_step(t,i,e){const{inedges:n,hull:s,_hullIndex:l,halfedges:h,triangles:r,points:o}=this;if(-1===n[t]||!o.length)return(t+1)%(o.length>>1);let a=t,c=A(i-o[2*t],2)+A(e-o[2*t+1],2);const u=n[t];let f=u;do{let n=r[f];const u=A(i-o[2*n],2)+A(e-o[2*n+1],2);if(u=12" + } +} diff --git a/frontend/node_modules/d3-delaunay/src/delaunay.js b/frontend/node_modules/d3-delaunay/src/delaunay.js new file mode 100644 index 0000000..fcb9d24 --- /dev/null +++ b/frontend/node_modules/d3-delaunay/src/delaunay.js @@ -0,0 +1,248 @@ +import Delaunator from "delaunator"; +import Path from "./path.js"; +import Polygon from "./polygon.js"; +import Voronoi from "./voronoi.js"; + +const tau = 2 * Math.PI, pow = Math.pow; + +function pointX(p) { + return p[0]; +} + +function pointY(p) { + return p[1]; +} + +// A triangulation is collinear if all its triangles have a non-null area +function collinear(d) { + const {triangles, coords} = d; + for (let i = 0; i < triangles.length; i += 3) { + const a = 2 * triangles[i], + b = 2 * triangles[i + 1], + c = 2 * triangles[i + 2], + cross = (coords[c] - coords[a]) * (coords[b + 1] - coords[a + 1]) + - (coords[b] - coords[a]) * (coords[c + 1] - coords[a + 1]); + if (cross > 1e-10) return false; + } + return true; +} + +function jitter(x, y, r) { + return [x + Math.sin(x + y) * r, y + Math.cos(x - y) * r]; +} + +export default class Delaunay { + static from(points, fx = pointX, fy = pointY, that) { + return new Delaunay("length" in points + ? flatArray(points, fx, fy, that) + : Float64Array.from(flatIterable(points, fx, fy, that))); + } + constructor(points) { + this._delaunator = new Delaunator(points); + this.inedges = new Int32Array(points.length / 2); + this._hullIndex = new Int32Array(points.length / 2); + this.points = this._delaunator.coords; + this._init(); + } + update() { + this._delaunator.update(); + this._init(); + return this; + } + _init() { + const d = this._delaunator, points = this.points; + + // check for collinear + if (d.hull && d.hull.length > 2 && collinear(d)) { + this.collinear = Int32Array.from({length: points.length/2}, (_,i) => i) + .sort((i, j) => points[2 * i] - points[2 * j] || points[2 * i + 1] - points[2 * j + 1]); // for exact neighbors + const e = this.collinear[0], f = this.collinear[this.collinear.length - 1], + bounds = [ points[2 * e], points[2 * e + 1], points[2 * f], points[2 * f + 1] ], + r = 1e-8 * Math.hypot(bounds[3] - bounds[1], bounds[2] - bounds[0]); + for (let i = 0, n = points.length / 2; i < n; ++i) { + const p = jitter(points[2 * i], points[2 * i + 1], r); + points[2 * i] = p[0]; + points[2 * i + 1] = p[1]; + } + this._delaunator = new Delaunator(points); + } else { + delete this.collinear; + } + + const halfedges = this.halfedges = this._delaunator.halfedges; + const hull = this.hull = this._delaunator.hull; + const triangles = this.triangles = this._delaunator.triangles; + const inedges = this.inedges.fill(-1); + const hullIndex = this._hullIndex.fill(-1); + + // Compute an index from each point to an (arbitrary) incoming halfedge + // Used to give the first neighbor of each point; for this reason, + // on the hull we give priority to exterior halfedges + for (let e = 0, n = halfedges.length; e < n; ++e) { + const p = triangles[e % 3 === 2 ? e - 2 : e + 1]; + if (halfedges[e] === -1 || inedges[p] === -1) inedges[p] = e; + } + for (let i = 0, n = hull.length; i < n; ++i) { + hullIndex[hull[i]] = i; + } + + // degenerate case: 1 or 2 (distinct) points + if (hull.length <= 2 && hull.length > 0) { + this.triangles = new Int32Array(3).fill(-1); + this.halfedges = new Int32Array(3).fill(-1); + this.triangles[0] = hull[0]; + inedges[hull[0]] = 1; + if (hull.length === 2) { + inedges[hull[1]] = 0; + this.triangles[1] = hull[1]; + this.triangles[2] = hull[1]; + } + } + } + voronoi(bounds) { + return new Voronoi(this, bounds); + } + *neighbors(i) { + const {inedges, hull, _hullIndex, halfedges, triangles, collinear} = this; + + // degenerate case with several collinear points + if (collinear) { + const l = collinear.indexOf(i); + if (l > 0) yield collinear[l - 1]; + if (l < collinear.length - 1) yield collinear[l + 1]; + return; + } + + const e0 = inedges[i]; + if (e0 === -1) return; // coincident point + let e = e0, p0 = -1; + do { + yield p0 = triangles[e]; + e = e % 3 === 2 ? e - 2 : e + 1; + if (triangles[e] !== i) return; // bad triangulation + e = halfedges[e]; + if (e === -1) { + const p = hull[(_hullIndex[i] + 1) % hull.length]; + if (p !== p0) yield p; + return; + } + } while (e !== e0); + } + find(x, y, i = 0) { + if ((x = +x, x !== x) || (y = +y, y !== y)) return -1; + const i0 = i; + let c; + while ((c = this._step(i, x, y)) >= 0 && c !== i && c !== i0) i = c; + return c; + } + _step(i, x, y) { + const {inedges, hull, _hullIndex, halfedges, triangles, points} = this; + if (inedges[i] === -1 || !points.length) return (i + 1) % (points.length >> 1); + let c = i; + let dc = pow(x - points[i * 2], 2) + pow(y - points[i * 2 + 1], 2); + const e0 = inedges[i]; + let e = e0; + do { + let t = triangles[e]; + const dt = pow(x - points[t * 2], 2) + pow(y - points[t * 2 + 1], 2); + if (dt < dc) dc = dt, c = t; + e = e % 3 === 2 ? e - 2 : e + 1; + if (triangles[e] !== i) break; // bad triangulation + e = halfedges[e]; + if (e === -1) { + e = hull[(_hullIndex[i] + 1) % hull.length]; + if (e !== t) { + if (pow(x - points[e * 2], 2) + pow(y - points[e * 2 + 1], 2) < dc) return e; + } + break; + } + } while (e !== e0); + return c; + } + render(context) { + const buffer = context == null ? context = new Path : undefined; + const {points, halfedges, triangles} = this; + for (let i = 0, n = halfedges.length; i < n; ++i) { + const j = halfedges[i]; + if (j < i) continue; + const ti = triangles[i] * 2; + const tj = triangles[j] * 2; + context.moveTo(points[ti], points[ti + 1]); + context.lineTo(points[tj], points[tj + 1]); + } + this.renderHull(context); + return buffer && buffer.value(); + } + renderPoints(context, r) { + if (r === undefined && (!context || typeof context.moveTo !== "function")) r = context, context = null; + r = r == undefined ? 2 : +r; + const buffer = context == null ? context = new Path : undefined; + const {points} = this; + for (let i = 0, n = points.length; i < n; i += 2) { + const x = points[i], y = points[i + 1]; + context.moveTo(x + r, y); + context.arc(x, y, r, 0, tau); + } + return buffer && buffer.value(); + } + renderHull(context) { + const buffer = context == null ? context = new Path : undefined; + const {hull, points} = this; + const h = hull[0] * 2, n = hull.length; + context.moveTo(points[h], points[h + 1]); + for (let i = 1; i < n; ++i) { + const h = 2 * hull[i]; + context.lineTo(points[h], points[h + 1]); + } + context.closePath(); + return buffer && buffer.value(); + } + hullPolygon() { + const polygon = new Polygon; + this.renderHull(polygon); + return polygon.value(); + } + renderTriangle(i, context) { + const buffer = context == null ? context = new Path : undefined; + const {points, triangles} = this; + const t0 = triangles[i *= 3] * 2; + const t1 = triangles[i + 1] * 2; + const t2 = triangles[i + 2] * 2; + context.moveTo(points[t0], points[t0 + 1]); + context.lineTo(points[t1], points[t1 + 1]); + context.lineTo(points[t2], points[t2 + 1]); + context.closePath(); + return buffer && buffer.value(); + } + *trianglePolygons() { + const {triangles} = this; + for (let i = 0, n = triangles.length / 3; i < n; ++i) { + yield this.trianglePolygon(i); + } + } + trianglePolygon(i) { + const polygon = new Polygon; + this.renderTriangle(i, polygon); + return polygon.value(); + } +} + +function flatArray(points, fx, fy, that) { + const n = points.length; + const array = new Float64Array(n * 2); + for (let i = 0; i < n; ++i) { + const p = points[i]; + array[i * 2] = fx.call(that, p, i, points); + array[i * 2 + 1] = fy.call(that, p, i, points); + } + return array; +} + +function* flatIterable(points, fx, fy, that) { + let i = 0; + for (const p of points) { + yield fx.call(that, p, i, points); + yield fy.call(that, p, i, points); + ++i; + } +} diff --git a/frontend/node_modules/d3-delaunay/src/index.js b/frontend/node_modules/d3-delaunay/src/index.js new file mode 100644 index 0000000..dc9022e --- /dev/null +++ b/frontend/node_modules/d3-delaunay/src/index.js @@ -0,0 +1,2 @@ +export {default as Delaunay} from "./delaunay.js"; +export {default as Voronoi} from "./voronoi.js"; diff --git a/frontend/node_modules/d3-delaunay/src/path.js b/frontend/node_modules/d3-delaunay/src/path.js new file mode 100644 index 0000000..0eaa69e --- /dev/null +++ b/frontend/node_modules/d3-delaunay/src/path.js @@ -0,0 +1,37 @@ +const epsilon = 1e-6; + +export default class Path { + constructor() { + this._x0 = this._y0 = // start of current subpath + this._x1 = this._y1 = null; // end of current subpath + this._ = ""; + } + moveTo(x, y) { + this._ += `M${this._x0 = this._x1 = +x},${this._y0 = this._y1 = +y}`; + } + closePath() { + if (this._x1 !== null) { + this._x1 = this._x0, this._y1 = this._y0; + this._ += "Z"; + } + } + lineTo(x, y) { + this._ += `L${this._x1 = +x},${this._y1 = +y}`; + } + arc(x, y, r) { + x = +x, y = +y, r = +r; + const x0 = x + r; + const y0 = y; + if (r < 0) throw new Error("negative radius"); + if (this._x1 === null) this._ += `M${x0},${y0}`; + else if (Math.abs(this._x1 - x0) > epsilon || Math.abs(this._y1 - y0) > epsilon) this._ += "L" + x0 + "," + y0; + if (!r) return; + this._ += `A${r},${r},0,1,1,${x - r},${y}A${r},${r},0,1,1,${this._x1 = x0},${this._y1 = y0}`; + } + rect(x, y, w, h) { + this._ += `M${this._x0 = this._x1 = +x},${this._y0 = this._y1 = +y}h${+w}v${+h}h${-w}Z`; + } + value() { + return this._ || null; + } +} diff --git a/frontend/node_modules/d3-delaunay/src/polygon.js b/frontend/node_modules/d3-delaunay/src/polygon.js new file mode 100644 index 0000000..bdbbdc3 --- /dev/null +++ b/frontend/node_modules/d3-delaunay/src/polygon.js @@ -0,0 +1,17 @@ +export default class Polygon { + constructor() { + this._ = []; + } + moveTo(x, y) { + this._.push([x, y]); + } + closePath() { + this._.push(this._[0].slice()); + } + lineTo(x, y) { + this._.push([x, y]); + } + value() { + return this._.length ? this._ : null; + } +} diff --git a/frontend/node_modules/d3-delaunay/src/voronoi.js b/frontend/node_modules/d3-delaunay/src/voronoi.js new file mode 100644 index 0000000..4918036 --- /dev/null +++ b/frontend/node_modules/d3-delaunay/src/voronoi.js @@ -0,0 +1,332 @@ +import Path from "./path.js"; +import Polygon from "./polygon.js"; + +export default class Voronoi { + constructor(delaunay, [xmin, ymin, xmax, ymax] = [0, 0, 960, 500]) { + if (!((xmax = +xmax) >= (xmin = +xmin)) || !((ymax = +ymax) >= (ymin = +ymin))) throw new Error("invalid bounds"); + this.delaunay = delaunay; + this._circumcenters = new Float64Array(delaunay.points.length * 2); + this.vectors = new Float64Array(delaunay.points.length * 2); + this.xmax = xmax, this.xmin = xmin; + this.ymax = ymax, this.ymin = ymin; + this._init(); + } + update() { + this.delaunay.update(); + this._init(); + return this; + } + _init() { + const {delaunay: {points, hull, triangles}, vectors} = this; + let bx, by; // lazily computed barycenter of the hull + + // Compute circumcenters. + const circumcenters = this.circumcenters = this._circumcenters.subarray(0, triangles.length / 3 * 2); + for (let i = 0, j = 0, n = triangles.length, x, y; i < n; i += 3, j += 2) { + const t1 = triangles[i] * 2; + const t2 = triangles[i + 1] * 2; + const t3 = triangles[i + 2] * 2; + const x1 = points[t1]; + const y1 = points[t1 + 1]; + const x2 = points[t2]; + const y2 = points[t2 + 1]; + const x3 = points[t3]; + const y3 = points[t3 + 1]; + + const dx = x2 - x1; + const dy = y2 - y1; + const ex = x3 - x1; + const ey = y3 - y1; + const ab = (dx * ey - dy * ex) * 2; + + if (Math.abs(ab) < 1e-9) { + // For a degenerate triangle, the circumcenter is at the infinity, in a + // direction orthogonal to the halfedge and away from the “center” of + // the diagram , defined as the hull’s barycenter. + if (bx === undefined) { + bx = by = 0; + for (const i of hull) bx += points[i * 2], by += points[i * 2 + 1]; + bx /= hull.length, by /= hull.length; + } + const a = 1e9 * Math.sign((bx - x1) * ey - (by - y1) * ex); + x = (x1 + x3) / 2 - a * ey; + y = (y1 + y3) / 2 + a * ex; + } else { + const d = 1 / ab; + const bl = dx * dx + dy * dy; + const cl = ex * ex + ey * ey; + x = x1 + (ey * bl - dy * cl) * d; + y = y1 + (dx * cl - ex * bl) * d; + } + circumcenters[j] = x; + circumcenters[j + 1] = y; + } + + // Compute exterior cell rays. + let h = hull[hull.length - 1]; + let p0, p1 = h * 4; + let x0, x1 = points[2 * h]; + let y0, y1 = points[2 * h + 1]; + vectors.fill(0); + for (let i = 0; i < hull.length; ++i) { + h = hull[i]; + p0 = p1, x0 = x1, y0 = y1; + p1 = h * 4, x1 = points[2 * h], y1 = points[2 * h + 1]; + vectors[p0 + 2] = vectors[p1] = y0 - y1; + vectors[p0 + 3] = vectors[p1 + 1] = x1 - x0; + } + } + render(context) { + const buffer = context == null ? context = new Path : undefined; + const {delaunay: {halfedges, inedges, hull}, circumcenters, vectors} = this; + if (hull.length <= 1) return null; + for (let i = 0, n = halfedges.length; i < n; ++i) { + const j = halfedges[i]; + if (j < i) continue; + const ti = Math.floor(i / 3) * 2; + const tj = Math.floor(j / 3) * 2; + const xi = circumcenters[ti]; + const yi = circumcenters[ti + 1]; + const xj = circumcenters[tj]; + const yj = circumcenters[tj + 1]; + this._renderSegment(xi, yi, xj, yj, context); + } + let h0, h1 = hull[hull.length - 1]; + for (let i = 0; i < hull.length; ++i) { + h0 = h1, h1 = hull[i]; + const t = Math.floor(inedges[h1] / 3) * 2; + const x = circumcenters[t]; + const y = circumcenters[t + 1]; + const v = h0 * 4; + const p = this._project(x, y, vectors[v + 2], vectors[v + 3]); + if (p) this._renderSegment(x, y, p[0], p[1], context); + } + return buffer && buffer.value(); + } + renderBounds(context) { + const buffer = context == null ? context = new Path : undefined; + context.rect(this.xmin, this.ymin, this.xmax - this.xmin, this.ymax - this.ymin); + return buffer && buffer.value(); + } + renderCell(i, context) { + const buffer = context == null ? context = new Path : undefined; + const points = this._clip(i); + if (points === null || !points.length) return; + context.moveTo(points[0], points[1]); + let n = points.length; + while (points[0] === points[n-2] && points[1] === points[n-1] && n > 1) n -= 2; + for (let i = 2; i < n; i += 2) { + if (points[i] !== points[i-2] || points[i+1] !== points[i-1]) + context.lineTo(points[i], points[i + 1]); + } + context.closePath(); + return buffer && buffer.value(); + } + *cellPolygons() { + const {delaunay: {points}} = this; + for (let i = 0, n = points.length / 2; i < n; ++i) { + const cell = this.cellPolygon(i); + if (cell) cell.index = i, yield cell; + } + } + cellPolygon(i) { + const polygon = new Polygon; + this.renderCell(i, polygon); + return polygon.value(); + } + _renderSegment(x0, y0, x1, y1, context) { + let S; + const c0 = this._regioncode(x0, y0); + const c1 = this._regioncode(x1, y1); + if (c0 === 0 && c1 === 0) { + context.moveTo(x0, y0); + context.lineTo(x1, y1); + } else if (S = this._clipSegment(x0, y0, x1, y1, c0, c1)) { + context.moveTo(S[0], S[1]); + context.lineTo(S[2], S[3]); + } + } + contains(i, x, y) { + if ((x = +x, x !== x) || (y = +y, y !== y)) return false; + return this.delaunay._step(i, x, y) === i; + } + *neighbors(i) { + const ci = this._clip(i); + if (ci) for (const j of this.delaunay.neighbors(i)) { + const cj = this._clip(j); + // find the common edge + if (cj) loop: for (let ai = 0, li = ci.length; ai < li; ai += 2) { + for (let aj = 0, lj = cj.length; aj < lj; aj += 2) { + if (ci[ai] === cj[aj] + && ci[ai + 1] === cj[aj + 1] + && ci[(ai + 2) % li] === cj[(aj + lj - 2) % lj] + && ci[(ai + 3) % li] === cj[(aj + lj - 1) % lj]) { + yield j; + break loop; + } + } + } + } + } + _cell(i) { + const {circumcenters, delaunay: {inedges, halfedges, triangles}} = this; + const e0 = inedges[i]; + if (e0 === -1) return null; // coincident point + const points = []; + let e = e0; + do { + const t = Math.floor(e / 3); + points.push(circumcenters[t * 2], circumcenters[t * 2 + 1]); + e = e % 3 === 2 ? e - 2 : e + 1; + if (triangles[e] !== i) break; // bad triangulation + e = halfedges[e]; + } while (e !== e0 && e !== -1); + return points; + } + _clip(i) { + // degenerate case (1 valid point: return the box) + if (i === 0 && this.delaunay.hull.length === 1) { + return [this.xmax, this.ymin, this.xmax, this.ymax, this.xmin, this.ymax, this.xmin, this.ymin]; + } + const points = this._cell(i); + if (points === null) return null; + const {vectors: V} = this; + const v = i * 4; + return this._simplify(V[v] || V[v + 1] + ? this._clipInfinite(i, points, V[v], V[v + 1], V[v + 2], V[v + 3]) + : this._clipFinite(i, points)); + } + _clipFinite(i, points) { + const n = points.length; + let P = null; + let x0, y0, x1 = points[n - 2], y1 = points[n - 1]; + let c0, c1 = this._regioncode(x1, y1); + let e0, e1 = 0; + for (let j = 0; j < n; j += 2) { + x0 = x1, y0 = y1, x1 = points[j], y1 = points[j + 1]; + c0 = c1, c1 = this._regioncode(x1, y1); + if (c0 === 0 && c1 === 0) { + e0 = e1, e1 = 0; + if (P) P.push(x1, y1); + else P = [x1, y1]; + } else { + let S, sx0, sy0, sx1, sy1; + if (c0 === 0) { + if ((S = this._clipSegment(x0, y0, x1, y1, c0, c1)) === null) continue; + [sx0, sy0, sx1, sy1] = S; + } else { + if ((S = this._clipSegment(x1, y1, x0, y0, c1, c0)) === null) continue; + [sx1, sy1, sx0, sy0] = S; + e0 = e1, e1 = this._edgecode(sx0, sy0); + if (e0 && e1) this._edge(i, e0, e1, P, P.length); + if (P) P.push(sx0, sy0); + else P = [sx0, sy0]; + } + e0 = e1, e1 = this._edgecode(sx1, sy1); + if (e0 && e1) this._edge(i, e0, e1, P, P.length); + if (P) P.push(sx1, sy1); + else P = [sx1, sy1]; + } + } + if (P) { + e0 = e1, e1 = this._edgecode(P[0], P[1]); + if (e0 && e1) this._edge(i, e0, e1, P, P.length); + } else if (this.contains(i, (this.xmin + this.xmax) / 2, (this.ymin + this.ymax) / 2)) { + return [this.xmax, this.ymin, this.xmax, this.ymax, this.xmin, this.ymax, this.xmin, this.ymin]; + } + return P; + } + _clipSegment(x0, y0, x1, y1, c0, c1) { + // for more robustness, always consider the segment in the same order + const flip = c0 < c1; + if (flip) [x0, y0, x1, y1, c0, c1] = [x1, y1, x0, y0, c1, c0]; + while (true) { + if (c0 === 0 && c1 === 0) return flip ? [x1, y1, x0, y0] : [x0, y0, x1, y1]; + if (c0 & c1) return null; + let x, y, c = c0 || c1; + if (c & 0b1000) x = x0 + (x1 - x0) * (this.ymax - y0) / (y1 - y0), y = this.ymax; + else if (c & 0b0100) x = x0 + (x1 - x0) * (this.ymin - y0) / (y1 - y0), y = this.ymin; + else if (c & 0b0010) y = y0 + (y1 - y0) * (this.xmax - x0) / (x1 - x0), x = this.xmax; + else y = y0 + (y1 - y0) * (this.xmin - x0) / (x1 - x0), x = this.xmin; + if (c0) x0 = x, y0 = y, c0 = this._regioncode(x0, y0); + else x1 = x, y1 = y, c1 = this._regioncode(x1, y1); + } + } + _clipInfinite(i, points, vx0, vy0, vxn, vyn) { + let P = Array.from(points), p; + if (p = this._project(P[0], P[1], vx0, vy0)) P.unshift(p[0], p[1]); + if (p = this._project(P[P.length - 2], P[P.length - 1], vxn, vyn)) P.push(p[0], p[1]); + if (P = this._clipFinite(i, P)) { + for (let j = 0, n = P.length, c0, c1 = this._edgecode(P[n - 2], P[n - 1]); j < n; j += 2) { + c0 = c1, c1 = this._edgecode(P[j], P[j + 1]); + if (c0 && c1) j = this._edge(i, c0, c1, P, j), n = P.length; + } + } else if (this.contains(i, (this.xmin + this.xmax) / 2, (this.ymin + this.ymax) / 2)) { + P = [this.xmin, this.ymin, this.xmax, this.ymin, this.xmax, this.ymax, this.xmin, this.ymax]; + } + return P; + } + _edge(i, e0, e1, P, j) { + while (e0 !== e1) { + let x, y; + switch (e0) { + case 0b0101: e0 = 0b0100; continue; // top-left + case 0b0100: e0 = 0b0110, x = this.xmax, y = this.ymin; break; // top + case 0b0110: e0 = 0b0010; continue; // top-right + case 0b0010: e0 = 0b1010, x = this.xmax, y = this.ymax; break; // right + case 0b1010: e0 = 0b1000; continue; // bottom-right + case 0b1000: e0 = 0b1001, x = this.xmin, y = this.ymax; break; // bottom + case 0b1001: e0 = 0b0001; continue; // bottom-left + case 0b0001: e0 = 0b0101, x = this.xmin, y = this.ymin; break; // left + } + // Note: this implicitly checks for out of bounds: if P[j] or P[j+1] are + // undefined, the conditional statement will be executed. + if ((P[j] !== x || P[j + 1] !== y) && this.contains(i, x, y)) { + P.splice(j, 0, x, y), j += 2; + } + } + return j; + } + _project(x0, y0, vx, vy) { + let t = Infinity, c, x, y; + if (vy < 0) { // top + if (y0 <= this.ymin) return null; + if ((c = (this.ymin - y0) / vy) < t) y = this.ymin, x = x0 + (t = c) * vx; + } else if (vy > 0) { // bottom + if (y0 >= this.ymax) return null; + if ((c = (this.ymax - y0) / vy) < t) y = this.ymax, x = x0 + (t = c) * vx; + } + if (vx > 0) { // right + if (x0 >= this.xmax) return null; + if ((c = (this.xmax - x0) / vx) < t) x = this.xmax, y = y0 + (t = c) * vy; + } else if (vx < 0) { // left + if (x0 <= this.xmin) return null; + if ((c = (this.xmin - x0) / vx) < t) x = this.xmin, y = y0 + (t = c) * vy; + } + return [x, y]; + } + _edgecode(x, y) { + return (x === this.xmin ? 0b0001 + : x === this.xmax ? 0b0010 : 0b0000) + | (y === this.ymin ? 0b0100 + : y === this.ymax ? 0b1000 : 0b0000); + } + _regioncode(x, y) { + return (x < this.xmin ? 0b0001 + : x > this.xmax ? 0b0010 : 0b0000) + | (y < this.ymin ? 0b0100 + : y > this.ymax ? 0b1000 : 0b0000); + } + _simplify(P) { + if (P && P.length > 4) { + for (let i = 0; i < P.length; i+= 2) { + const j = (i + 2) % P.length, k = (i + 4) % P.length; + if (P[i] === P[j] && P[j] === P[k] || P[i + 1] === P[j + 1] && P[j + 1] === P[k + 1]) { + P.splice(j, 2), i -= 2; + } + } + if (!P.length) P = null; + } + return P; + } +} diff --git a/frontend/node_modules/d3-dispatch/LICENSE b/frontend/node_modules/d3-dispatch/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-dispatch/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-dispatch/README.md b/frontend/node_modules/d3-dispatch/README.md new file mode 100644 index 0000000..9963a84 --- /dev/null +++ b/frontend/node_modules/d3-dispatch/README.md @@ -0,0 +1,94 @@ +# d3-dispatch + +Dispatching is a convenient mechanism for separating concerns with loosely-coupled code: register named callbacks and then call them with arbitrary arguments. A variety of D3 components, such as [d3-drag](https://github.com/d3/d3-drag), use this mechanism to emit events to listeners. Think of this like Node’s [EventEmitter](https://nodejs.org/api/events.html), except every listener has a well-defined name so it’s easy to remove or replace them. + +For example, to create a dispatch for *start* and *end* events: + +```js +const dispatch = d3.dispatch("start", "end"); +``` + +You can then register callbacks for these events using [*dispatch*.on](#dispatch_on): + +```js +dispatch.on("start", callback1); +dispatch.on("start.foo", callback2); +dispatch.on("end", callback3); +``` + +Then, you can invoke all the *start* callbacks using [*dispatch*.call](#dispatch_call) or [*dispatch*.apply](#dispatch_apply): + +```js +dispatch.call("start"); +``` + +Like *function*.call, you may also specify the `this` context and any arguments: + +```js +dispatch.call("start", {about: "I am a context object"}, "I am an argument"); +``` + +Want a more involved example? See how to use [d3-dispatch for coordinated views](http://bl.ocks.org/mbostock/5872848). + +## Installing + +If you use npm, `npm install d3-dispatch`. You can also download the [latest release on GitHub](https://github.com/d3/d3-dispatch/releases/latest). For vanilla HTML in modern browsers, import d3-dispatch from Skypack: + +```html + +``` + +For legacy environments, you can load d3-dispatch’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +[Try d3-dispatch in your browser.](https://observablehq.com/collection/@d3/d3-dispatch) + +## API Reference + +# d3.dispatch(types…) · [Source](https://github.com/d3/d3-dispatch/blob/master/src/dispatch.js) + +Creates a new dispatch for the specified event *types*. Each *type* is a string, such as `"start"` or `"end"`. + +# *dispatch*.on(typenames[, callback]) · [Source](https://github.com/d3/d3-dispatch/blob/master/src/dispatch.js) + +Adds, removes or gets the *callback* for the specified *typenames*. If a *callback* function is specified, it is registered for the specified (fully-qualified) *typenames*. If a callback was already registered for the given *typenames*, the existing callback is removed before the new callback is added. + +The specified *typenames* is a string, such as `start` or `end.foo`. The type may be optionally followed by a period (`.`) and a name; the optional name allows multiple callbacks to be registered to receive events of the same type, such as `start.foo` and `start.bar`. To specify multiple typenames, separate typenames with spaces, such as `start end` or `start.foo start.bar`. + +To remove all callbacks for a given name `foo`, say `dispatch.on(".foo", null)`. + +If *callback* is not specified, returns the current callback for the specified *typenames*, if any. If multiple typenames are specified, the first matching callback is returned. + +# *dispatch*.copy() · [Source](https://github.com/d3/d3-dispatch/blob/master/src/dispatch.js) + +Returns a copy of this dispatch object. Changes to this dispatch do not affect the returned copy and vice versa. + +# *dispatch*.call(type[, that[, arguments…]]) · [Source](https://github.com/d3/d3-dispatch/blob/master/src/dispatch.js) + +Like [*function*.call](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Function/call), invokes each registered callback for the specified *type*, passing the callback the specified *arguments*, with *that* as the `this` context. See [*dispatch*.apply](#dispatch_apply) for more information. + +# *dispatch*.apply(type[, that[, arguments]]) · [Source](https://github.com/d3/d3-dispatch/blob/master/src/dispatch.js) + +Like [*function*.apply](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Function/call), invokes each registered callback for the specified *type*, passing the callback the specified *arguments*, with *that* as the `this` context. For example, if you wanted to dispatch your *custom* callbacks after handling a native *click* event, while preserving the current `this` context and arguments, you could say: + +```js +selection.on("click", function() { + dispatch.apply("custom", this, arguments); +}); +``` + +You can pass whatever arguments you want to callbacks; most commonly, you might create an object that represents an event, or pass the current datum (*d*) and index (*i*). See [function.call](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Function/Call) and [function.apply](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Function/Apply) for further information. diff --git a/frontend/node_modules/d3-dispatch/dist/d3-dispatch.js b/frontend/node_modules/d3-dispatch/dist/d3-dispatch.js new file mode 100644 index 0000000..178c7c9 --- /dev/null +++ b/frontend/node_modules/d3-dispatch/dist/d3-dispatch.js @@ -0,0 +1,95 @@ +// https://d3js.org/d3-dispatch/ v3.0.1 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +}(this, (function (exports) { 'use strict'; + +var noop = {value: () => {}}; + +function dispatch() { + for (var i = 0, n = arguments.length, _ = {}, t; i < n; ++i) { + if (!(t = arguments[i] + "") || (t in _) || /[\s.]/.test(t)) throw new Error("illegal type: " + t); + _[t] = []; + } + return new Dispatch(_); +} + +function Dispatch(_) { + this._ = _; +} + +function parseTypenames(typenames, types) { + return typenames.trim().split(/^|\s+/).map(function(t) { + var name = "", i = t.indexOf("."); + if (i >= 0) name = t.slice(i + 1), t = t.slice(0, i); + if (t && !types.hasOwnProperty(t)) throw new Error("unknown type: " + t); + return {type: t, name: name}; + }); +} + +Dispatch.prototype = dispatch.prototype = { + constructor: Dispatch, + on: function(typename, callback) { + var _ = this._, + T = parseTypenames(typename + "", _), + t, + i = -1, + n = T.length; + + // If no callback was specified, return the callback of the given type and name. + if (arguments.length < 2) { + while (++i < n) if ((t = (typename = T[i]).type) && (t = get(_[t], typename.name))) return t; + return; + } + + // If a type was specified, set the callback for the given type and name. + // Otherwise, if a null callback was specified, remove callbacks of the given name. + if (callback != null && typeof callback !== "function") throw new Error("invalid callback: " + callback); + while (++i < n) { + if (t = (typename = T[i]).type) _[t] = set(_[t], typename.name, callback); + else if (callback == null) for (t in _) _[t] = set(_[t], typename.name, null); + } + + return this; + }, + copy: function() { + var copy = {}, _ = this._; + for (var t in _) copy[t] = _[t].slice(); + return new Dispatch(copy); + }, + call: function(type, that) { + if ((n = arguments.length - 2) > 0) for (var args = new Array(n), i = 0, n, t; i < n; ++i) args[i] = arguments[i + 2]; + if (!this._.hasOwnProperty(type)) throw new Error("unknown type: " + type); + for (t = this._[type], i = 0, n = t.length; i < n; ++i) t[i].value.apply(that, args); + }, + apply: function(type, that, args) { + if (!this._.hasOwnProperty(type)) throw new Error("unknown type: " + type); + for (var t = this._[type], i = 0, n = t.length; i < n; ++i) t[i].value.apply(that, args); + } +}; + +function get(type, name) { + for (var i = 0, n = type.length, c; i < n; ++i) { + if ((c = type[i]).name === name) { + return c.value; + } + } +} + +function set(type, name, callback) { + for (var i = 0, n = type.length; i < n; ++i) { + if (type[i].name === name) { + type[i] = noop, type = type.slice(0, i).concat(type.slice(i + 1)); + break; + } + } + if (callback != null) type.push({name: name, value: callback}); + return type; +} + +exports.dispatch = dispatch; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-dispatch/dist/d3-dispatch.min.js b/frontend/node_modules/d3-dispatch/dist/d3-dispatch.min.js new file mode 100644 index 0000000..608d2f7 --- /dev/null +++ b/frontend/node_modules/d3-dispatch/dist/d3-dispatch.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-dispatch/ v3.0.1 Copyright 2010-2021 Mike Bostock +!function(n,e){"object"==typeof exports&&"undefined"!=typeof module?e(exports):"function"==typeof define&&define.amd?define(["exports"],e):e((n="undefined"!=typeof globalThis?globalThis:n||self).d3=n.d3||{})}(this,(function(n){"use strict";var e={value:()=>{}};function t(){for(var n,e=0,t=arguments.length,o={};e=0&&(t=n.slice(r+1),n=n.slice(0,r)),n&&!e.hasOwnProperty(n))throw new Error("unknown type: "+n);return{type:n,name:t}}))}function i(n,e){for(var t,r=0,o=n.length;r0)for(var t,r,o=new Array(t),i=0;i=12" + } +} diff --git a/frontend/node_modules/d3-dispatch/src/dispatch.js b/frontend/node_modules/d3-dispatch/src/dispatch.js new file mode 100644 index 0000000..c93ac4f --- /dev/null +++ b/frontend/node_modules/d3-dispatch/src/dispatch.js @@ -0,0 +1,84 @@ +var noop = {value: () => {}}; + +function dispatch() { + for (var i = 0, n = arguments.length, _ = {}, t; i < n; ++i) { + if (!(t = arguments[i] + "") || (t in _) || /[\s.]/.test(t)) throw new Error("illegal type: " + t); + _[t] = []; + } + return new Dispatch(_); +} + +function Dispatch(_) { + this._ = _; +} + +function parseTypenames(typenames, types) { + return typenames.trim().split(/^|\s+/).map(function(t) { + var name = "", i = t.indexOf("."); + if (i >= 0) name = t.slice(i + 1), t = t.slice(0, i); + if (t && !types.hasOwnProperty(t)) throw new Error("unknown type: " + t); + return {type: t, name: name}; + }); +} + +Dispatch.prototype = dispatch.prototype = { + constructor: Dispatch, + on: function(typename, callback) { + var _ = this._, + T = parseTypenames(typename + "", _), + t, + i = -1, + n = T.length; + + // If no callback was specified, return the callback of the given type and name. + if (arguments.length < 2) { + while (++i < n) if ((t = (typename = T[i]).type) && (t = get(_[t], typename.name))) return t; + return; + } + + // If a type was specified, set the callback for the given type and name. + // Otherwise, if a null callback was specified, remove callbacks of the given name. + if (callback != null && typeof callback !== "function") throw new Error("invalid callback: " + callback); + while (++i < n) { + if (t = (typename = T[i]).type) _[t] = set(_[t], typename.name, callback); + else if (callback == null) for (t in _) _[t] = set(_[t], typename.name, null); + } + + return this; + }, + copy: function() { + var copy = {}, _ = this._; + for (var t in _) copy[t] = _[t].slice(); + return new Dispatch(copy); + }, + call: function(type, that) { + if ((n = arguments.length - 2) > 0) for (var args = new Array(n), i = 0, n, t; i < n; ++i) args[i] = arguments[i + 2]; + if (!this._.hasOwnProperty(type)) throw new Error("unknown type: " + type); + for (t = this._[type], i = 0, n = t.length; i < n; ++i) t[i].value.apply(that, args); + }, + apply: function(type, that, args) { + if (!this._.hasOwnProperty(type)) throw new Error("unknown type: " + type); + for (var t = this._[type], i = 0, n = t.length; i < n; ++i) t[i].value.apply(that, args); + } +}; + +function get(type, name) { + for (var i = 0, n = type.length, c; i < n; ++i) { + if ((c = type[i]).name === name) { + return c.value; + } + } +} + +function set(type, name, callback) { + for (var i = 0, n = type.length; i < n; ++i) { + if (type[i].name === name) { + type[i] = noop, type = type.slice(0, i).concat(type.slice(i + 1)); + break; + } + } + if (callback != null) type.push({name: name, value: callback}); + return type; +} + +export default dispatch; diff --git a/frontend/node_modules/d3-dispatch/src/index.js b/frontend/node_modules/d3-dispatch/src/index.js new file mode 100644 index 0000000..4b8d3bd --- /dev/null +++ b/frontend/node_modules/d3-dispatch/src/index.js @@ -0,0 +1 @@ +export {default as dispatch} from "./dispatch.js"; diff --git a/frontend/node_modules/d3-drag/LICENSE b/frontend/node_modules/d3-drag/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-drag/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-drag/README.md b/frontend/node_modules/d3-drag/README.md new file mode 100644 index 0000000..f0f4d7c --- /dev/null +++ b/frontend/node_modules/d3-drag/README.md @@ -0,0 +1,248 @@ +# d3-drag + +[Drag-and-drop](https://en.wikipedia.org/wiki/Drag_and_drop) is a popular and easy-to-learn pointing gesture: move the pointer to an object, press and hold to grab it, “drag” the object to a new location, and release to “drop”. D3’s [drag behavior](#api-reference) provides a convenient but flexible abstraction for enabling drag-and-drop interaction on [selections](https://github.com/d3/d3-selection). For example, you can use d3-drag to facilitate interaction with a [force-directed graph](https://github.com/d3/d3-force), or a simulation of colliding circles: + +[Force-Directed Graph](https://observablehq.com/@d3/force-directed-graph)[Force Dragging II](https://observablehq.com/d/c55a5839a5bb7c73) + +You can also use d3-drag to implement custom user interface elements, such as a slider. But the drag behavior isn’t just for moving elements around; there are a variety of ways to respond to a drag gesture. For example, you can use it to lasso elements in a scatterplot, or to paint lines on a canvas: + +[Line Drawing](https://observablehq.com/@d3/draw-me) + +The drag behavior can be combined with other behaviors, such as [d3-zoom](https://github.com/d3/d3-zoom) for zooming. + +[Drag & Zoom II](https://observablehq.com/@d3/drag-zoom) + +The drag behavior is agnostic about the DOM, so you can use it with SVG, HTML or even Canvas! And you can extend it with advanced selection techniques, such as a Voronoi overlay or a closest-target search: + +[Circle Dragging IV](https://observablehq.com/@d3/circle-dragging-iii)[Circle Dragging II](https://observablehq.com/@d3/circle-dragging-ii) + +Best of all, the drag behavior automatically unifies mouse and touch input, and avoids browser idiosyncrasies. When [Pointer Events](https://www.w3.org/TR/pointerevents/) are more widely available, the drag behavior will support those, too. + +## Installing + +If you use npm, `npm install d3-drag`. You can also download the [latest release on GitHub](https://github.com/d3/d3-drag/releases/latest). For vanilla HTML in modern browsers, import d3-drag from Skypack: + +```html + +``` + +For legacy environments, you can load d3-drag’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + + + +``` + +[Try d3-drag in your browser.](https://observablehq.com/collection/@d3/d3-drag) + +## API Reference + +This table describes how the drag behavior interprets native events: + +| Event | Listening Element | Drag Event | Default Prevented? | +| ------------ | ----------------- | ---------- | ------------------ | +| mousedown⁵ | selection | start | no¹ | +| mousemove² | window¹ | drag | yes | +| mouseup² | window¹ | end | yes | +| dragstart² | window | - | yes | +| selectstart² | window | - | yes | +| click³ | window | - | yes | +| touchstart | selection | start | no⁴ | +| touchmove | selection | drag | yes | +| touchend | selection | end | no⁴ | +| touchcancel | selection | end | no⁴ | + +The propagation of all consumed events is [immediately stopped](https://dom.spec.whatwg.org/#dom-event-stopimmediatepropagation). If you want to prevent some events from initiating a drag gesture, use [*drag*.filter](#drag_filter). + +¹ Necessary to capture events outside an iframe; see [#9](https://github.com/d3/d3-drag/issues/9). +
    ² Only applies during an active, mouse-based gesture; see [#9](https://github.com/d3/d3-drag/issues/9). +
    ³ Only applies immediately after some mouse-based gestures; see [*drag*.clickDistance](#drag_clickDistance). +
    ⁴ Necessary to allow [click emulation](https://developer.apple.com/library/ios/documentation/AppleApplications/Reference/SafariWebContent/HandlingEvents/HandlingEvents.html#//apple_ref/doc/uid/TP40006511-SW7) on touch input; see [#9](https://github.com/d3/d3-drag/issues/9). +
    ⁵ Ignored if within 500ms of a touch gesture ending; assumes [click emulation](https://developer.apple.com/library/ios/documentation/AppleApplications/Reference/SafariWebContent/HandlingEvents/HandlingEvents.html#//apple_ref/doc/uid/TP40006511-SW7). + +# d3.drag() · [Source](https://github.com/d3/d3-drag/blob/master/src/drag.js), [Examples](https://observablehq.com/collection/@d3/d3-drag) + +Creates a new drag behavior. The returned behavior, [*drag*](#_drag), is both an object and a function, and is typically applied to selected elements via [*selection*.call](https://github.com/d3/d3-selection#selection_call). + +# drag(selection) · [Source](https://github.com/d3/d3-drag/blob/master/src/drag.js), [Examples](https://observablehq.com/collection/@d3/d3-drag) + +Applies this drag behavior to the specified [*selection*](https://github.com/d3/d3-selection). This function is typically not invoked directly, and is instead invoked via [*selection*.call](https://github.com/d3/d3-selection#selection_call). For example, to instantiate a drag behavior and apply it to a selection: + +```js +d3.selectAll(".node").call(d3.drag().on("start", started)); +``` + +Internally, the drag behavior uses [*selection*.on](https://github.com/d3/d3-selection#selection_on) to bind the necessary event listeners for dragging. The listeners use the name `.drag`, so you can subsequently unbind the drag behavior as follows: + +```js +selection.on(".drag", null); +``` + +Applying the drag behavior also sets the [-webkit-tap-highlight-color](https://developer.apple.com/library/mac/documentation/AppleApplications/Reference/SafariWebContent/AdjustingtheTextSize/AdjustingtheTextSize.html#//apple_ref/doc/uid/TP40006510-SW5) style to transparent, disabling the tap highlight on iOS. If you want a different tap highlight color, remove or re-apply this style after applying the drag behavior. + +# drag.container([container]) · [Source](https://github.com/d3/d3-drag/blob/master/src/drag.js), [Examples](https://observablehq.com/collection/@d3/d3-drag) + +If *container* is specified, sets the container accessor to the specified object or function and returns the drag behavior. If *container* is not specified, returns the current container accessor, which defaults to: + +```js +function container() { + return this.parentNode; +} +``` + +The *container* of a drag gesture determines the coordinate system of subsequent [drag events](#drag-events), affecting *event*.x and *event*.y. The element returned by the container accessor is subsequently passed to [d3.pointer](https://github.com/d3/d3-selection#pointer) to determine the local coordinates of the pointer. + +The default container accessor returns the parent node of the element in the originating selection (see [*drag*](#_drag)) that received the initiating input event. This is often appropriate when dragging SVG or HTML elements, since those elements are typically positioned relative to a parent. For dragging graphical elements with a Canvas, however, you may want to redefine the container as the initiating element itself: + +```js +function container() { + return this; +} +``` + +Alternatively, the container may be specified as the element directly, such as `drag.container(canvas)`. + + +# drag.filter([filter]) · [Source](https://github.com/d3/d3-drag/blob/master/src/drag.js), [Examples](https://observablehq.com/d/c55a5839a5bb7c73) + +If *filter* is specified, sets the event filter to the specified function and returns the drag behavior. If *filter* is not specified, returns the current filter, which defaults to: + +```js +function filter(event) { + return !event.ctrlKey && !event.button; +} +``` + +If the filter returns falsey, the initiating event is ignored and no drag gestures are started. Thus, the filter determines which input events are ignored; the default filter ignores mousedown events on secondary buttons, since those buttons are typically intended for other purposes, such as the context menu. + +# drag.touchable([touchable]) · [Source](https://github.com/d3/d3-drag/blob/master/src/drag.js), [Examples](https://observablehq.com/d/c55a5839a5bb7c73) + +If *touchable* is specified, sets the touch support detector to the specified function and returns the drag behavior. If *touchable* is not specified, returns the current touch support detector, which defaults to: + +```js +function touchable() { + return navigator.maxTouchPoints || ("ontouchstart" in this); +} +``` + +Touch event listeners are only registered if the detector returns truthy for the corresponding element when the drag behavior is [applied](#_drag). The default detector works well for most browsers that are capable of touch input, but not all; Chrome’s mobile device emulator, for example, fails detection. + +# drag.subject([subject]) · [Source](https://github.com/d3/d3-drag/blob/master/src/drag.js), [Examples](https://observablehq.com/collection/@d3/d3-drag) + +If *subject* is specified, sets the subject accessor to the specified object or function and returns the drag behavior. If *subject* is not specified, returns the current subject accessor, which defaults to: + +```js +function subject(event, d) { + return d == null ? {x: event.x, y: event.y} : d; +} +``` + +The *subject* of a drag gesture represents *the thing being dragged*. It is computed when an initiating input event is received, such as a mousedown or touchstart, immediately before the drag gesture starts. The subject is then exposed as *event*.subject on subsequent [drag events](#drag-events) for this gesture. + +The default subject is the [datum](https://github.com/d3/d3-selection#selection_datum) of the element in the originating selection (see [*drag*](#_drag)) that received the initiating input event; if this datum is undefined, an object representing the coordinates of the pointer is created. When dragging circle elements in SVG, the default subject is thus the datum of the circle being dragged. With [Canvas](https://html.spec.whatwg.org/multipage/scripting.html#the-canvas-element), the default subject is the canvas element’s datum (regardless of where on the canvas you click). In this case, a custom subject accessor would be more appropriate, such as one that picks the closest circle to the mouse within a given search *radius*: + +```js +function subject(event) { + let n = circles.length, + i, + dx, + dy, + d2, + s2 = radius * radius, + circle, + subject; + + for (i = 0; i < n; ++i) { + circle = circles[i]; + dx = event.x - circle.x; + dy = event.y - circle.y; + d2 = dx * dx + dy * dy; + if (d2 < s2) subject = circle, s2 = d2; + } + + return subject; +} +``` + +(If necessary, the above can be accelerated using [*quadtree*.find](https://github.com/d3/d3-quadtree/blob/master/README.md#quadtree_find), [*simulation*.find](https://github.com/d3/d3-force/blob/master/README.md#simulation_find) or [*delaunay*.find](https://github.com/d3/d3-delaunay/blob/master/README.md#delaunay_find).) + +The returned subject should be an object that exposes `x` and `y` properties, so that the relative position of the subject and the pointer can be preserved during the drag gesture. If the subject is null or undefined, no drag gesture is started for this pointer; however, other starting touches may yet start drag gestures. See also [*drag*.filter](#drag_filter). + +The subject of a drag gesture may not be changed after the gesture starts. The subject accessor is invoked with the same context and arguments as [*selection*.on](https://github.com/d3/d3-selection#selection_on) listeners: the current event (`event`) and datum `d`, with the `this` context as the current DOM element. During the evaluation of the subject accessor, `event` is a beforestart [drag event](#drag-events). Use *event*.sourceEvent to access the initiating input event and *event*.identifier to access the touch identifier. The *event*.x and *event*.y are relative to the [container](#drag_container), and are computed using [d3.pointer](https://github.com/d3/d3-selection#pointer). + +# drag.clickDistance([distance]) · [Source](https://github.com/d3/d3-drag/blob/master/src/drag.js) + +If *distance* is specified, sets the maximum distance that the mouse can move between mousedown and mouseup that will trigger a subsequent click event. If at any point between mousedown and mouseup the mouse is greater than or equal to *distance* from its position on mousedown, the click event following mouseup will be suppressed. If *distance* is not specified, returns the current distance threshold, which defaults to zero. The distance threshold is measured in client coordinates ([*event*.clientX](https://developer.mozilla.org/en-US/docs/Web/API/MouseEvent/clientX) and [*event*.clientY](https://developer.mozilla.org/en-US/docs/Web/API/MouseEvent/clientY)). + +# drag.on(typenames, [listener]) · [Source](https://github.com/d3/d3-drag/blob/master/src/drag.js) + +If *listener* is specified, sets the event *listener* for the specified *typenames* and returns the drag behavior. If an event listener was already registered for the same type and name, the existing listener is removed before the new listener is added. If *listener* is null, removes the current event listeners for the specified *typenames*, if any. If *listener* is not specified, returns the first currently-assigned listener matching the specified *typenames*, if any. When a specified event is dispatched, each *listener* will be invoked with the same context and arguments as [*selection*.on](https://github.com/d3/d3-selection#selection_on) listeners: the current event (`event`) and datum `d`, with the `this` context as the current DOM element. + +The *typenames* is a string containing one or more *typename* separated by whitespace. Each *typename* is a *type*, optionally followed by a period (`.`) and a *name*, such as `drag.foo` and `drag.bar`; the name allows multiple listeners to be registered for the same *type*. The *type* must be one of the following: + +* `start` - after a new pointer becomes active (on mousedown or touchstart). +* `drag` - after an active pointer moves (on mousemove or touchmove). +* `end` - after an active pointer becomes inactive (on mouseup, touchend or touchcancel). + +See [*dispatch*.on](https://github.com/d3/d3-dispatch#dispatch_on) for more. + +Changes to registered listeners via *drag*.on during a drag gesture *do not affect* the current drag gesture. Instead, you must use [*event*.on](#event_on), which also allows you to register temporary event listeners for the current drag gesture. **Separate events are dispatched for each active pointer** during a drag gesture. For example, if simultaneously dragging multiple subjects with multiple fingers, a start event is dispatched for each finger, even if both fingers start touching simultaneously. See [Drag Events](#drag-events) for more. + +# d3.dragDisable(window) · [Source](https://github.com/d3/d3-drag/blob/master/src/nodrag.js) + +Prevents native drag-and-drop and text selection on the specified *window*. As an alternative to preventing the default action of mousedown events (see [#9](https://github.com/d3/d3-drag/issues/9)), this method prevents undesirable default actions following mousedown. In supported browsers, this means capturing dragstart and selectstart events, preventing the associated default actions, and immediately stopping their propagation. In browsers that do not support selection events, the user-select CSS property is set to none on the document element. This method is intended to be called on mousedown, followed by [d3.dragEnable](#dragEnable) on mouseup. + +# d3.dragEnable(window[, noclick]) · [Source](https://github.com/d3/d3-drag/blob/master/src/nodrag.js) + +Allows native drag-and-drop and text selection on the specified *window*; undoes the effect of [d3.dragDisable](#dragDisable). This method is intended to be called on mouseup, preceded by [d3.dragDisable](#dragDisable) on mousedown. If *noclick* is true, this method also temporarily suppresses click events. The suppression of click events expires after a zero-millisecond timeout, such that it only suppress the click event that would immediately follow the current mouseup event, if any. + +### Drag Events + +When a [drag event listener](#drag_on) is invoked, it receives the current drag event as its first argument. The *event* object exposes several fields: + +* `target` - the associated [drag behavior](#drag). +* `type` - the string “start”, “drag” or “end”; see [*drag*.on](#drag_on). +* `subject` - the drag subject, defined by [*drag*.subject](#drag_subject). +* `x` - the new *x*-coordinate of the subject; see [*drag*.container](#drag_container). +* `y` - the new *y*-coordinate of the subject; see [*drag*.container](#drag_container). +* `dx` - the change in *x*-coordinate since the previous drag event. +* `dy` - the change in *y*-coordinate since the previous drag event. +* `identifier` - the string “mouse”, or a numeric [touch identifier](https://www.w3.org/TR/touch-events/#widl-Touch-identifier). +* `active` - the number of currently active drag gestures (on start and end, not including this one). +* `sourceEvent` - the underlying input event, such as mousemove or touchmove. + +The *event*.active field is useful for detecting the first start event and the last end event in a sequence of concurrent drag gestures: it is zero when the first drag gesture starts, and zero when the last drag gesture ends. + +The *event* object also exposes the [*event*.on](#event_on) method. + +# event.on(typenames, [listener]) · [Source](https://github.com/d3/d3-drag/blob/master/src/event.js) + +Equivalent to [*drag*.on](#drag_on), but only applies to the current drag gesture. Before the drag gesture starts, a [copy](https://github.com/d3/d3-dispatch#dispatch_copy) of the current drag [event listeners](#drag_on) is made. This copy is bound to the current drag gesture and modified by *event*.on. This is useful for temporary listeners that only receive events for the current drag gesture. For example, this start event listener registers temporary drag and end event listeners as closures: + +```js +function started(event) { + const circle = d3.select(this).classed("dragging", true); + + event.on("drag", dragged).on("end", ended); + + function dragged(event, d) { + circle.raise().attr("cx", d.x = event.x).attr("cy", d.y = event.y); + } + + function ended() { + circle.classed("dragging", false); + } +} +``` diff --git a/frontend/node_modules/d3-drag/dist/d3-drag.js b/frontend/node_modules/d3-drag/dist/d3-drag.js new file mode 100644 index 0000000..98cbbb9 --- /dev/null +++ b/frontend/node_modules/d3-drag/dist/d3-drag.js @@ -0,0 +1,273 @@ +// https://d3js.org/d3-drag/ v3.0.0 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-dispatch'), require('d3-selection')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-dispatch', 'd3-selection'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3, global.d3)); +}(this, (function (exports, d3Dispatch, d3Selection) { 'use strict'; + +// These are typically used in conjunction with noevent to ensure that we can +// preventDefault on the event. +const nonpassive = {passive: false}; +const nonpassivecapture = {capture: true, passive: false}; + +function nopropagation(event) { + event.stopImmediatePropagation(); +} + +function noevent(event) { + event.preventDefault(); + event.stopImmediatePropagation(); +} + +function nodrag(view) { + var root = view.document.documentElement, + selection = d3Selection.select(view).on("dragstart.drag", noevent, nonpassivecapture); + if ("onselectstart" in root) { + selection.on("selectstart.drag", noevent, nonpassivecapture); + } else { + root.__noselect = root.style.MozUserSelect; + root.style.MozUserSelect = "none"; + } +} + +function yesdrag(view, noclick) { + var root = view.document.documentElement, + selection = d3Selection.select(view).on("dragstart.drag", null); + if (noclick) { + selection.on("click.drag", noevent, nonpassivecapture); + setTimeout(function() { selection.on("click.drag", null); }, 0); + } + if ("onselectstart" in root) { + selection.on("selectstart.drag", null); + } else { + root.style.MozUserSelect = root.__noselect; + delete root.__noselect; + } +} + +var constant = x => () => x; + +function DragEvent(type, { + sourceEvent, + subject, + target, + identifier, + active, + x, y, dx, dy, + dispatch +}) { + Object.defineProperties(this, { + type: {value: type, enumerable: true, configurable: true}, + sourceEvent: {value: sourceEvent, enumerable: true, configurable: true}, + subject: {value: subject, enumerable: true, configurable: true}, + target: {value: target, enumerable: true, configurable: true}, + identifier: {value: identifier, enumerable: true, configurable: true}, + active: {value: active, enumerable: true, configurable: true}, + x: {value: x, enumerable: true, configurable: true}, + y: {value: y, enumerable: true, configurable: true}, + dx: {value: dx, enumerable: true, configurable: true}, + dy: {value: dy, enumerable: true, configurable: true}, + _: {value: dispatch} + }); +} + +DragEvent.prototype.on = function() { + var value = this._.on.apply(this._, arguments); + return value === this._ ? this : value; +}; + +// Ignore right-click, since that should open the context menu. +function defaultFilter(event) { + return !event.ctrlKey && !event.button; +} + +function defaultContainer() { + return this.parentNode; +} + +function defaultSubject(event, d) { + return d == null ? {x: event.x, y: event.y} : d; +} + +function defaultTouchable() { + return navigator.maxTouchPoints || ("ontouchstart" in this); +} + +function drag() { + var filter = defaultFilter, + container = defaultContainer, + subject = defaultSubject, + touchable = defaultTouchable, + gestures = {}, + listeners = d3Dispatch.dispatch("start", "drag", "end"), + active = 0, + mousedownx, + mousedowny, + mousemoving, + touchending, + clickDistance2 = 0; + + function drag(selection) { + selection + .on("mousedown.drag", mousedowned) + .filter(touchable) + .on("touchstart.drag", touchstarted) + .on("touchmove.drag", touchmoved, nonpassive) + .on("touchend.drag touchcancel.drag", touchended) + .style("touch-action", "none") + .style("-webkit-tap-highlight-color", "rgba(0,0,0,0)"); + } + + function mousedowned(event, d) { + if (touchending || !filter.call(this, event, d)) return; + var gesture = beforestart(this, container.call(this, event, d), event, d, "mouse"); + if (!gesture) return; + d3Selection.select(event.view) + .on("mousemove.drag", mousemoved, nonpassivecapture) + .on("mouseup.drag", mouseupped, nonpassivecapture); + nodrag(event.view); + nopropagation(event); + mousemoving = false; + mousedownx = event.clientX; + mousedowny = event.clientY; + gesture("start", event); + } + + function mousemoved(event) { + noevent(event); + if (!mousemoving) { + var dx = event.clientX - mousedownx, dy = event.clientY - mousedowny; + mousemoving = dx * dx + dy * dy > clickDistance2; + } + gestures.mouse("drag", event); + } + + function mouseupped(event) { + d3Selection.select(event.view).on("mousemove.drag mouseup.drag", null); + yesdrag(event.view, mousemoving); + noevent(event); + gestures.mouse("end", event); + } + + function touchstarted(event, d) { + if (!filter.call(this, event, d)) return; + var touches = event.changedTouches, + c = container.call(this, event, d), + n = touches.length, i, gesture; + + for (i = 0; i < n; ++i) { + if (gesture = beforestart(this, c, event, d, touches[i].identifier, touches[i])) { + nopropagation(event); + gesture("start", event, touches[i]); + } + } + } + + function touchmoved(event) { + var touches = event.changedTouches, + n = touches.length, i, gesture; + + for (i = 0; i < n; ++i) { + if (gesture = gestures[touches[i].identifier]) { + noevent(event); + gesture("drag", event, touches[i]); + } + } + } + + function touchended(event) { + var touches = event.changedTouches, + n = touches.length, i, gesture; + + if (touchending) clearTimeout(touchending); + touchending = setTimeout(function() { touchending = null; }, 500); // Ghost clicks are delayed! + for (i = 0; i < n; ++i) { + if (gesture = gestures[touches[i].identifier]) { + nopropagation(event); + gesture("end", event, touches[i]); + } + } + } + + function beforestart(that, container, event, d, identifier, touch) { + var dispatch = listeners.copy(), + p = d3Selection.pointer(touch || event, container), dx, dy, + s; + + if ((s = subject.call(that, new DragEvent("beforestart", { + sourceEvent: event, + target: drag, + identifier, + active, + x: p[0], + y: p[1], + dx: 0, + dy: 0, + dispatch + }), d)) == null) return; + + dx = s.x - p[0] || 0; + dy = s.y - p[1] || 0; + + return function gesture(type, event, touch) { + var p0 = p, n; + switch (type) { + case "start": gestures[identifier] = gesture, n = active++; break; + case "end": delete gestures[identifier], --active; // falls through + case "drag": p = d3Selection.pointer(touch || event, container), n = active; break; + } + dispatch.call( + type, + that, + new DragEvent(type, { + sourceEvent: event, + subject: s, + target: drag, + identifier, + active: n, + x: p[0] + dx, + y: p[1] + dy, + dx: p[0] - p0[0], + dy: p[1] - p0[1], + dispatch + }), + d + ); + }; + } + + drag.filter = function(_) { + return arguments.length ? (filter = typeof _ === "function" ? _ : constant(!!_), drag) : filter; + }; + + drag.container = function(_) { + return arguments.length ? (container = typeof _ === "function" ? _ : constant(_), drag) : container; + }; + + drag.subject = function(_) { + return arguments.length ? (subject = typeof _ === "function" ? _ : constant(_), drag) : subject; + }; + + drag.touchable = function(_) { + return arguments.length ? (touchable = typeof _ === "function" ? _ : constant(!!_), drag) : touchable; + }; + + drag.on = function() { + var value = listeners.on.apply(listeners, arguments); + return value === listeners ? drag : value; + }; + + drag.clickDistance = function(_) { + return arguments.length ? (clickDistance2 = (_ = +_) * _, drag) : Math.sqrt(clickDistance2); + }; + + return drag; +} + +exports.drag = drag; +exports.dragDisable = nodrag; +exports.dragEnable = yesdrag; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-drag/dist/d3-drag.min.js b/frontend/node_modules/d3-drag/dist/d3-drag.min.js new file mode 100644 index 0000000..1c8bcc3 --- /dev/null +++ b/frontend/node_modules/d3-drag/dist/d3-drag.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-drag/ v3.0.0 Copyright 2010-2021 Mike Bostock +!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports,require("d3-dispatch"),require("d3-selection")):"function"==typeof define&&define.amd?define(["exports","d3-dispatch","d3-selection"],t):t((e="undefined"!=typeof globalThis?globalThis:e||self).d3=e.d3||{},e.d3,e.d3)}(this,(function(e,t,n){"use strict";const o={passive:!1},r={capture:!0,passive:!1};function i(e){e.stopImmediatePropagation()}function a(e){e.preventDefault(),e.stopImmediatePropagation()}function u(e){var t=e.document.documentElement,o=n.select(e).on("dragstart.drag",a,r);"onselectstart"in t?o.on("selectstart.drag",a,r):(t.__noselect=t.style.MozUserSelect,t.style.MozUserSelect="none")}function c(e,t){var o=e.document.documentElement,i=n.select(e).on("dragstart.drag",null);t&&(i.on("click.drag",a,r),setTimeout((function(){i.on("click.drag",null)}),0)),"onselectstart"in o?i.on("selectstart.drag",null):(o.style.MozUserSelect=o.__noselect,delete o.__noselect)}var l=e=>()=>e;function s(e,{sourceEvent:t,subject:n,target:o,identifier:r,active:i,x:a,y:u,dx:c,dy:l,dispatch:s}){Object.defineProperties(this,{type:{value:e,enumerable:!0,configurable:!0},sourceEvent:{value:t,enumerable:!0,configurable:!0},subject:{value:n,enumerable:!0,configurable:!0},target:{value:o,enumerable:!0,configurable:!0},identifier:{value:r,enumerable:!0,configurable:!0},active:{value:i,enumerable:!0,configurable:!0},x:{value:a,enumerable:!0,configurable:!0},y:{value:u,enumerable:!0,configurable:!0},dx:{value:c,enumerable:!0,configurable:!0},dy:{value:l,enumerable:!0,configurable:!0},_:{value:s}})}function d(e){return!e.ctrlKey&&!e.button}function f(){return this.parentNode}function g(e,t){return null==t?{x:e.x,y:e.y}:t}function h(){return navigator.maxTouchPoints||"ontouchstart"in this}s.prototype.on=function(){var e=this._.on.apply(this._,arguments);return e===this._?this:e},e.drag=function(){var e,v,p,b,m=d,y=f,x=g,_=h,w={},T=t.dispatch("start","drag","end"),j=0,E=0;function k(e){e.on("mousedown.drag",M).filter(_).on("touchstart.drag",z).on("touchmove.drag",D,o).on("touchend.drag touchcancel.drag",S).style("touch-action","none").style("-webkit-tap-highlight-color","rgba(0,0,0,0)")}function M(t,o){if(!b&&m.call(this,t,o)){var a=U(this,y.call(this,t,o),t,o,"mouse");a&&(n.select(t.view).on("mousemove.drag",P,r).on("mouseup.drag",q,r),u(t.view),i(t),p=!1,e=t.clientX,v=t.clientY,a("start",t))}}function P(t){if(a(t),!p){var n=t.clientX-e,o=t.clientY-v;p=n*n+o*o>E}w.mouse("drag",t)}function q(e){n.select(e.view).on("mousemove.drag mouseup.drag",null),c(e.view,p),a(e),w.mouse("end",e)}function z(e,t){if(m.call(this,e,t)){var n,o,r=e.changedTouches,a=y.call(this,e,t),u=r.length;for(n=0;n=12" + } +} diff --git a/frontend/node_modules/d3-drag/src/constant.js b/frontend/node_modules/d3-drag/src/constant.js new file mode 100644 index 0000000..3487c0d --- /dev/null +++ b/frontend/node_modules/d3-drag/src/constant.js @@ -0,0 +1 @@ +export default x => () => x; diff --git a/frontend/node_modules/d3-drag/src/drag.js b/frontend/node_modules/d3-drag/src/drag.js new file mode 100644 index 0000000..790d9c7 --- /dev/null +++ b/frontend/node_modules/d3-drag/src/drag.js @@ -0,0 +1,194 @@ +import {dispatch} from "d3-dispatch"; +import {select, pointer} from "d3-selection"; +import nodrag, {yesdrag} from "./nodrag.js"; +import noevent, {nonpassive, nonpassivecapture, nopropagation} from "./noevent.js"; +import constant from "./constant.js"; +import DragEvent from "./event.js"; + +// Ignore right-click, since that should open the context menu. +function defaultFilter(event) { + return !event.ctrlKey && !event.button; +} + +function defaultContainer() { + return this.parentNode; +} + +function defaultSubject(event, d) { + return d == null ? {x: event.x, y: event.y} : d; +} + +function defaultTouchable() { + return navigator.maxTouchPoints || ("ontouchstart" in this); +} + +export default function() { + var filter = defaultFilter, + container = defaultContainer, + subject = defaultSubject, + touchable = defaultTouchable, + gestures = {}, + listeners = dispatch("start", "drag", "end"), + active = 0, + mousedownx, + mousedowny, + mousemoving, + touchending, + clickDistance2 = 0; + + function drag(selection) { + selection + .on("mousedown.drag", mousedowned) + .filter(touchable) + .on("touchstart.drag", touchstarted) + .on("touchmove.drag", touchmoved, nonpassive) + .on("touchend.drag touchcancel.drag", touchended) + .style("touch-action", "none") + .style("-webkit-tap-highlight-color", "rgba(0,0,0,0)"); + } + + function mousedowned(event, d) { + if (touchending || !filter.call(this, event, d)) return; + var gesture = beforestart(this, container.call(this, event, d), event, d, "mouse"); + if (!gesture) return; + select(event.view) + .on("mousemove.drag", mousemoved, nonpassivecapture) + .on("mouseup.drag", mouseupped, nonpassivecapture); + nodrag(event.view); + nopropagation(event); + mousemoving = false; + mousedownx = event.clientX; + mousedowny = event.clientY; + gesture("start", event); + } + + function mousemoved(event) { + noevent(event); + if (!mousemoving) { + var dx = event.clientX - mousedownx, dy = event.clientY - mousedowny; + mousemoving = dx * dx + dy * dy > clickDistance2; + } + gestures.mouse("drag", event); + } + + function mouseupped(event) { + select(event.view).on("mousemove.drag mouseup.drag", null); + yesdrag(event.view, mousemoving); + noevent(event); + gestures.mouse("end", event); + } + + function touchstarted(event, d) { + if (!filter.call(this, event, d)) return; + var touches = event.changedTouches, + c = container.call(this, event, d), + n = touches.length, i, gesture; + + for (i = 0; i < n; ++i) { + if (gesture = beforestart(this, c, event, d, touches[i].identifier, touches[i])) { + nopropagation(event); + gesture("start", event, touches[i]); + } + } + } + + function touchmoved(event) { + var touches = event.changedTouches, + n = touches.length, i, gesture; + + for (i = 0; i < n; ++i) { + if (gesture = gestures[touches[i].identifier]) { + noevent(event); + gesture("drag", event, touches[i]); + } + } + } + + function touchended(event) { + var touches = event.changedTouches, + n = touches.length, i, gesture; + + if (touchending) clearTimeout(touchending); + touchending = setTimeout(function() { touchending = null; }, 500); // Ghost clicks are delayed! + for (i = 0; i < n; ++i) { + if (gesture = gestures[touches[i].identifier]) { + nopropagation(event); + gesture("end", event, touches[i]); + } + } + } + + function beforestart(that, container, event, d, identifier, touch) { + var dispatch = listeners.copy(), + p = pointer(touch || event, container), dx, dy, + s; + + if ((s = subject.call(that, new DragEvent("beforestart", { + sourceEvent: event, + target: drag, + identifier, + active, + x: p[0], + y: p[1], + dx: 0, + dy: 0, + dispatch + }), d)) == null) return; + + dx = s.x - p[0] || 0; + dy = s.y - p[1] || 0; + + return function gesture(type, event, touch) { + var p0 = p, n; + switch (type) { + case "start": gestures[identifier] = gesture, n = active++; break; + case "end": delete gestures[identifier], --active; // falls through + case "drag": p = pointer(touch || event, container), n = active; break; + } + dispatch.call( + type, + that, + new DragEvent(type, { + sourceEvent: event, + subject: s, + target: drag, + identifier, + active: n, + x: p[0] + dx, + y: p[1] + dy, + dx: p[0] - p0[0], + dy: p[1] - p0[1], + dispatch + }), + d + ); + }; + } + + drag.filter = function(_) { + return arguments.length ? (filter = typeof _ === "function" ? _ : constant(!!_), drag) : filter; + }; + + drag.container = function(_) { + return arguments.length ? (container = typeof _ === "function" ? _ : constant(_), drag) : container; + }; + + drag.subject = function(_) { + return arguments.length ? (subject = typeof _ === "function" ? _ : constant(_), drag) : subject; + }; + + drag.touchable = function(_) { + return arguments.length ? (touchable = typeof _ === "function" ? _ : constant(!!_), drag) : touchable; + }; + + drag.on = function() { + var value = listeners.on.apply(listeners, arguments); + return value === listeners ? drag : value; + }; + + drag.clickDistance = function(_) { + return arguments.length ? (clickDistance2 = (_ = +_) * _, drag) : Math.sqrt(clickDistance2); + }; + + return drag; +} diff --git a/frontend/node_modules/d3-drag/src/event.js b/frontend/node_modules/d3-drag/src/event.js new file mode 100644 index 0000000..5f246fe --- /dev/null +++ b/frontend/node_modules/d3-drag/src/event.js @@ -0,0 +1,28 @@ +export default function DragEvent(type, { + sourceEvent, + subject, + target, + identifier, + active, + x, y, dx, dy, + dispatch +}) { + Object.defineProperties(this, { + type: {value: type, enumerable: true, configurable: true}, + sourceEvent: {value: sourceEvent, enumerable: true, configurable: true}, + subject: {value: subject, enumerable: true, configurable: true}, + target: {value: target, enumerable: true, configurable: true}, + identifier: {value: identifier, enumerable: true, configurable: true}, + active: {value: active, enumerable: true, configurable: true}, + x: {value: x, enumerable: true, configurable: true}, + y: {value: y, enumerable: true, configurable: true}, + dx: {value: dx, enumerable: true, configurable: true}, + dy: {value: dy, enumerable: true, configurable: true}, + _: {value: dispatch} + }); +} + +DragEvent.prototype.on = function() { + var value = this._.on.apply(this._, arguments); + return value === this._ ? this : value; +}; diff --git a/frontend/node_modules/d3-drag/src/index.js b/frontend/node_modules/d3-drag/src/index.js new file mode 100644 index 0000000..d2dd601 --- /dev/null +++ b/frontend/node_modules/d3-drag/src/index.js @@ -0,0 +1,2 @@ +export {default as drag} from "./drag.js"; +export {default as dragDisable, yesdrag as dragEnable} from "./nodrag.js"; diff --git a/frontend/node_modules/d3-drag/src/nodrag.js b/frontend/node_modules/d3-drag/src/nodrag.js new file mode 100644 index 0000000..6076694 --- /dev/null +++ b/frontend/node_modules/d3-drag/src/nodrag.js @@ -0,0 +1,28 @@ +import {select} from "d3-selection"; +import noevent, {nonpassivecapture} from "./noevent.js"; + +export default function(view) { + var root = view.document.documentElement, + selection = select(view).on("dragstart.drag", noevent, nonpassivecapture); + if ("onselectstart" in root) { + selection.on("selectstart.drag", noevent, nonpassivecapture); + } else { + root.__noselect = root.style.MozUserSelect; + root.style.MozUserSelect = "none"; + } +} + +export function yesdrag(view, noclick) { + var root = view.document.documentElement, + selection = select(view).on("dragstart.drag", null); + if (noclick) { + selection.on("click.drag", noevent, nonpassivecapture); + setTimeout(function() { selection.on("click.drag", null); }, 0); + } + if ("onselectstart" in root) { + selection.on("selectstart.drag", null); + } else { + root.style.MozUserSelect = root.__noselect; + delete root.__noselect; + } +} diff --git a/frontend/node_modules/d3-drag/src/noevent.js b/frontend/node_modules/d3-drag/src/noevent.js new file mode 100644 index 0000000..173c250 --- /dev/null +++ b/frontend/node_modules/d3-drag/src/noevent.js @@ -0,0 +1,13 @@ +// These are typically used in conjunction with noevent to ensure that we can +// preventDefault on the event. +export const nonpassive = {passive: false}; +export const nonpassivecapture = {capture: true, passive: false}; + +export function nopropagation(event) { + event.stopImmediatePropagation(); +} + +export default function(event) { + event.preventDefault(); + event.stopImmediatePropagation(); +} diff --git a/frontend/node_modules/d3-dsv/LICENSE b/frontend/node_modules/d3-dsv/LICENSE new file mode 100644 index 0000000..5cb4fc7 --- /dev/null +++ b/frontend/node_modules/d3-dsv/LICENSE @@ -0,0 +1,13 @@ +Copyright 2013-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-dsv/README.md b/frontend/node_modules/d3-dsv/README.md new file mode 100644 index 0000000..a373221 --- /dev/null +++ b/frontend/node_modules/d3-dsv/README.md @@ -0,0 +1,492 @@ +# d3-dsv + +This module provides a parser and formatter for delimiter-separated values, most commonly [comma-](https://en.wikipedia.org/wiki/Comma-separated_values) (CSV) or tab-separated values (TSV). These tabular formats are popular with spreadsheet programs such as Microsoft Excel, and are often more space-efficient than JSON. This implementation is based on [RFC 4180](http://tools.ietf.org/html/rfc4180). + +Comma (CSV) and tab (TSV) delimiters are built-in. For example, to parse: + +```js +d3.csvParse("foo,bar\n1,2"); // [{foo: "1", bar: "2"}, columns: ["foo", "bar"]] +d3.tsvParse("foo\tbar\n1\t2"); // [{foo: "1", bar: "2"}, columns: ["foo", "bar"]] +``` + +Or to format: + +```js +d3.csvFormat([{foo: "1", bar: "2"}]); // "foo,bar\n1,2" +d3.tsvFormat([{foo: "1", bar: "2"}]); // "foo\tbar\n1\t2" +``` + +To use a different delimiter, such as “|” for pipe-separated values, use [d3.dsvFormat](#dsvFormat): + +```js +const psv = d3.dsvFormat("|"); + +console.log(psv.parse("foo|bar\n1|2")); // [{foo: "1", bar: "2"}, columns: ["foo", "bar"]] +``` + +For easy loading of DSV files in a browser, see [d3-fetch](https://github.com/d3/d3-fetch)’s [d3.csv](https://github.com/d3/d3-fetch/blob/master/README.md#csv), [d3.tsv](https://github.com/d3/d3-fetch/blob/master/README.md#tsv) and [d3.dsv](https://github.com/d3/d3-fetch/blob/master/README.md#dsv) methods. + +## Installing + +If you use npm, `npm install d3-dsv`. You can also download the [latest release on GitHub](https://github.com/d3/d3-dsv/releases/latest). For vanilla HTML in modern browsers, import d3-dsv from Skypack: + +```html + +``` + +For legacy environments, you can load d3-dsv’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +## API Reference + +# d3.csvParse(string[, row]) [<>](https://github.com/d3/d3-dsv/blob/master/src/csv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)(",").[parse](#dsv_parse). Note: requires unsafe-eval [content security policy](#content-security-policy). + +# d3.csvParseRows(string[, row]) [<>](https://github.com/d3/d3-dsv/blob/master/src/csv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)(",").[parseRows](#dsv_parseRows). + +# d3.csvFormat(rows[, columns]) [<>](https://github.com/d3/d3-dsv/blob/master/src/csv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)(",").[format](#dsv_format). + +# d3.csvFormatBody(rows[, columns]) [<>](https://github.com/d3/d3-dsv/blob/master/src/csv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)(",").[formatBody](#dsv_formatBody). + +# d3.csvFormatRows(rows) [<>](https://github.com/d3/d3-dsv/blob/master/src/csv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)(",").[formatRows](#dsv_formatRows). + +# d3.csvFormatRow(row) [<>](https://github.com/d3/d3-dsv/blob/master/src/csv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)(",").[formatRow](#dsv_formatRow). + +# d3.csvFormatValue(value) [<>](https://github.com/d3/d3-dsv/blob/master/src/csv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)(",").[formatValue](#dsv_formatValue). + +# d3.tsvParse(string[, row]) [<>](https://github.com/d3/d3-dsv/blob/master/src/tsv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)("\t").[parse](#dsv_parse). Note: requires unsafe-eval [content security policy](#content-security-policy). + +# d3.tsvParseRows(string[, row]) [<>](https://github.com/d3/d3-dsv/blob/master/src/tsv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)("\t").[parseRows](#dsv_parseRows). + +# d3.tsvFormat(rows[, columns]) [<>](https://github.com/d3/d3-dsv/blob/master/src/tsv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)("\t").[format](#dsv_format). + +# d3.tsvFormatBody(rows[, columns]) [<>](https://github.com/d3/d3-dsv/blob/master/src/tsv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)("\t").[formatBody](#dsv_formatBody). + +# d3.tsvFormatRows(rows) [<>](https://github.com/d3/d3-dsv/blob/master/src/tsv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)("\t").[formatRows](#dsv_formatRows). + +# d3.tsvFormatRow(row) [<>](https://github.com/d3/d3-dsv/blob/master/src/tsv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)("\t").[formatRow](#dsv_formatRow). + +# d3.tsvFormatValue(value) [<>](https://github.com/d3/d3-dsv/blob/master/src/tsv.js "Source") + +Equivalent to [dsvFormat](#dsvFormat)("\t").[formatValue](#dsv_formatValue). + +# d3.dsvFormat(delimiter) [<>](https://github.com/d3/d3-dsv/blob/master/src/dsv.js) + +Constructs a new DSV parser and formatter for the specified *delimiter*. The *delimiter* must be a single character (*i.e.*, a single 16-bit code unit); so, ASCII delimiters are fine, but emoji delimiters are not. + +# *dsv*.parse(string[, row]) [<>](https://github.com/d3/d3-dsv/blob/master/src/dsv.js "Source") + +Parses the specified *string*, which must be in the delimiter-separated values format with the appropriate delimiter, returning an array of objects representing the parsed rows. + +Unlike [*dsv*.parseRows](#dsv_parseRows), this method requires that the first line of the DSV content contains a delimiter-separated list of column names; these column names become the attributes on the returned objects. For example, consider the following CSV file: + +``` +Year,Make,Model,Length +1997,Ford,E350,2.34 +2000,Mercury,Cougar,2.38 +``` + +The resulting JavaScript array is: + +```js +[ + {"Year": "1997", "Make": "Ford", "Model": "E350", "Length": "2.34"}, + {"Year": "2000", "Make": "Mercury", "Model": "Cougar", "Length": "2.38"} +] +``` + +The returned array also exposes a `columns` property containing the column names in input order (in contrast to Object.keys, whose iteration order is arbitrary). For example: + +```js +data.columns; // ["Year", "Make", "Model", "Length"] +``` + +If the column names are not unique, only the last value is returned for each name; to access all values, use [*dsv*.parseRows](#dsv_parseRows) instead (see [example](https://observablehq.com/@d3/parse-csv-with-duplicate-column-names)). + +If a *row* conversion function is not specified, field values are strings. For safety, there is no automatic conversion to numbers, dates, or other types. In some cases, JavaScript may coerce strings to numbers for you automatically (for example, using the `+` operator), but better is to specify a *row* conversion function. See [d3.autoType](#autoType) for a convenient *row* conversion function that infers and coerces common types like numbers and strings. + +If a *row* conversion function is specified, the specified function is invoked for each row, being passed an object representing the current row (`d`), the index (`i`) starting at zero for the first non-header row, and the array of column names. If the returned value is null or undefined, the row is skipped and will be omitted from the array returned by *dsv*.parse; otherwise, the returned value defines the corresponding row object. For example: + +```js +const data = d3.csvParse(string, (d) => { + return { + year: new Date(+d.Year, 0, 1), // lowercase and convert "Year" to Date + make: d.Make, // lowercase + model: d.Model, // lowercase + length: +d.Length // lowercase and convert "Length" to number + }; +}); +``` + +Note: using `+` rather than [parseInt](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/parseInt) or [parseFloat](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/parseFloat) is typically faster, though more restrictive. For example, `"30px"` when coerced using `+` returns `NaN`, while parseInt and parseFloat return `30`. + +Note: requires unsafe-eval [content security policy](#content-security-policy). + +# dsv.parseRows(string[, row]) [<>](https://github.com/d3/d3-dsv/blob/master/src/dsv.js "Source") + +Parses the specified *string*, which must be in the delimiter-separated values format with the appropriate delimiter, returning an array of arrays representing the parsed rows. + +Unlike [*dsv*.parse](#dsv_parse), this method treats the header line as a standard row, and should be used whenever DSV content does not contain a header. Each row is represented as an array rather than an object. Rows may have variable length. For example, consider the following CSV file, which notably lacks a header line: + +``` +1997,Ford,E350,2.34 +2000,Mercury,Cougar,2.38 +``` + +The resulting JavaScript array is: + +```js +[ + ["1997", "Ford", "E350", "2.34"], + ["2000", "Mercury", "Cougar", "2.38"] +] +``` + +If a *row* conversion function is not specified, field values are strings. For safety, there is no automatic conversion to numbers, dates, or other types. In some cases, JavaScript may coerce strings to numbers for you automatically (for example, using the `+` operator), but better is to specify a *row* conversion function. See [d3.autoType](#autoType) for a convenient *row* conversion function that infers and coerces common types like numbers and strings. + +If a *row* conversion function is specified, the specified function is invoked for each row, being passed an array representing the current row (`d`), the index (`i`) starting at zero for the first row, and the array of column names. If the returned value is null or undefined, the row is skipped and will be omitted from the array returned by *dsv*.parse; otherwise, the returned value defines the corresponding row object. For example: + +```js +const data = d3.csvParseRows(string, (d, i) => { + return { + year: new Date(+d[0], 0, 1), // convert first colum column to Date + make: d[1], + model: d[2], + length: +d[3] // convert fourth column to number + }; +}); +``` + +In effect, *row* is similar to applying a [map](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/map) and [filter](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/filter) operator to the returned rows. + +# dsv.format(rows[, columns]) [<>](https://github.com/d3/d3-dsv/blob/master/src/dsv.js "Source") + +Formats the specified array of object *rows* as delimiter-separated values, returning a string. This operation is the inverse of [*dsv*.parse](#dsv_parse). Each row will be separated by a newline (`\n`), and each column within each row will be separated by the delimiter (such as a comma, `,`). Values that contain either the delimiter, a double-quote (`"`) or a newline will be escaped using double-quotes. + +If *columns* is not specified, the list of column names that forms the header row is determined by the union of all properties on all objects in *rows*; the order of columns is nondeterministic. If *columns* is specified, it is an array of strings representing the column names. For example: + +```js +const string = d3.csvFormat(data, ["year", "make", "model", "length"]); +``` + +All fields on each row object will be coerced to strings. If the field value is null or undefined, the empty string is used. If the field value is a Date, the [ECMAScript date-time string format](https://www.ecma-international.org/ecma-262/9.0/index.html#sec-date-time-string-format) (a subset of ISO 8601) is used: for example, dates at UTC midnight are formatted as `YYYY-MM-DD`. For more control over which and how fields are formatted, first map *rows* to an array of array of string, and then use [*dsv*.formatRows](#dsv_formatRows). + +# dsv.formatBody(rows[, columns]) [<>](https://github.com/d3/d3-dsv/blob/master/src/dsv.js "Source") + +Equivalent to [*dsv*.format](#dsv_format), but omits the header row. This is useful, for example, when appending rows to an existing file. + +# dsv.formatRows(rows) [<>](https://github.com/d3/d3-dsv/blob/master/src/dsv.js "Source") + +Formats the specified array of array of string *rows* as delimiter-separated values, returning a string. This operation is the reverse of [*dsv*.parseRows](#dsv_parseRows). Each row will be separated by a newline (`\n`), and each column within each row will be separated by the delimiter (such as a comma, `,`). Values that contain either the delimiter, a double-quote (") or a newline will be escaped using double-quotes. + +To convert an array of objects to an array of arrays while explicitly specifying the columns, use [*array*.map](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/map). For example: + +```js +const string = d3.csvFormatRows(data.map((d, i) => { + return [ + d.year.getFullYear(), // Assuming d.year is a Date object. + d.make, + d.model, + d.length + ]; +})); +``` + +If you like, you can also [*array*.concat](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/concat) this result with an array of column names to generate the first row: + +```js +const string = d3.csvFormatRows([[ + "year", + "make", + "model", + "length" + ]].concat(data.map((d, i) => { + return [ + d.year.getFullYear(), // Assuming d.year is a Date object. + d.make, + d.model, + d.length + ]; +}))); +``` + +# dsv.formatRow(row) [<>](https://github.com/d3/d3-dsv/blob/master/src/dsv.js "Source") + +Formats a single array *row* of strings as delimiter-separated values, returning a string. Each column within the row will be separated by the delimiter (such as a comma, `,`). Values that contain either the delimiter, a double-quote (") or a newline will be escaped using double-quotes. + +# dsv.formatValue(value) [<>](https://github.com/d3/d3-dsv/blob/master/src/dsv.js "Source") + +Format a single *value* or string as a delimiter-separated value, returning a string. A value that contains either the delimiter, a double-quote (") or a newline will be escaped using double-quotes. + +# d3.autoType(object) [<>](https://github.com/d3/d3-dsv/blob/master/src/autoType.js "Source") + +Given an *object* (or array) representing a parsed row, infers the types of values on the *object* and coerces them accordingly, returning the mutated *object*. This function is intended to be used as a *row* accessor function in conjunction with [*dsv*.parse](#dsv_parse) and [*dsv*.parseRows](#dsv_parseRow). For example, consider the following CSV file: + +``` +Year,Make,Model,Length +1997,Ford,E350,2.34 +2000,Mercury,Cougar,2.38 +``` + +When used with [d3.csvParse](#csvParse), + +```js +d3.csvParse(string, d3.autoType) +``` + +the resulting JavaScript array is: + +```js +[ + {"Year": 1997, "Make": "Ford", "Model": "E350", "Length": 2.34}, + {"Year": 2000, "Make": "Mercury", "Model": "Cougar", "Length": 2.38} +] +``` + +Type inference works as follows. For each *value* in the given *object*, the [trimmed](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/Trim) value is computed; the value is then re-assigned as follows: + +1. If empty, then `null`. +1. If exactly `"true"`, then `true`. +1. If exactly `"false"`, then `false`. +1. If exactly `"NaN"`, then `NaN`. +1. Otherwise, if [coercible to a number](https://www.ecma-international.org/ecma-262/9.0/index.html#sec-tonumber-applied-to-the-string-type), then a number. +1. Otherwise, if a [date-only or date-time string](https://www.ecma-international.org/ecma-262/9.0/index.html#sec-date-time-string-format), then a Date. +1. Otherwise, a string (the original untrimmed value). + +Values with leading zeroes may be coerced to numbers; for example `"08904"` coerces to `8904`. However, extra characters such as commas or units (*e.g.*, `"$1.00"`, `"(123)"`, `"1,234"` or `"32px"`) will prevent number coercion, resulting in a string. + +Date strings must be in ECMAScript’s subset of the [ISO 8601 format](https://en.wikipedia.org/wiki/ISO_8601). When a date-only string such as YYYY-MM-DD is specified, the inferred time is midnight UTC; however, if a date-time string such as YYYY-MM-DDTHH:MM is specified without a time zone, it is assumed to be local time. + +Automatic type inference is primarily intended to provide safe, predictable behavior in conjunction with [*dsv*.format](#dsv_format) and [*dsv*.formatRows](#dsv_formatRows) for common JavaScript types. If you need different behavior, you should implement your own row accessor function. + +For more, see [the d3.autoType notebook](https://observablehq.com/@d3/d3-autotype). + +### Content Security Policy + +If a [content security policy](http://www.w3.org/TR/CSP/) is in place, note that [*dsv*.parse](#dsv_parse) requires `unsafe-eval` in the `script-src` directive, due to the (safe) use of dynamic code generation for fast parsing. (See [source](https://github.com/d3/d3-dsv/blob/master/src/dsv.js).) Alternatively, use [*dsv*.parseRows](#dsv_parseRows). + +### Byte-Order Marks + +DSV files sometimes begin with a [byte order mark (BOM)](https://en.wikipedia.org/wiki/Byte_order_mark); saving a spreadsheet in CSV UTF-8 format from Microsoft Excel, for example, will include a BOM. On the web this is not usually a problem because the [UTF-8 decode algorithm](https://encoding.spec.whatwg.org/#utf-8-decode) specified in the Encoding standard removes the BOM. Node.js, on the other hand, [does not remove the BOM](https://github.com/nodejs/node-v0.x-archive/issues/1918) when decoding UTF-8. + +If the BOM is not removed, the first character of the text is a zero-width non-breaking space. So if a CSV file with a BOM is parsed by [d3.csvParse](#csvParse), the first column’s name will begin with a zero-width non-breaking space. This can be hard to spot since this character is usually invisible when printed. + +To remove the BOM before parsing, consider using [strip-bom](https://www.npmjs.com/package/strip-bom). + +## Command Line Reference + +### dsv2dsv + +# dsv2dsv [options…] [file] + +Converts the specified DSV input *file* to DSV (typically with a different delimiter or encoding). If *file* is not specified, defaults to reading from stdin. For example, to convert to CSV to TSV: + +``` +csv2tsv < example.csv > example.tsv +``` + +To convert windows-1252 CSV to utf-8 CSV: + +``` +dsv2dsv --input-encoding windows-1252 < latin1.csv > utf8.csv +``` + +# dsv2dsv -h +
    # dsv2dsv --help + +Output usage information. + +# dsv2dsv -V +
    # dsv2dsv --version + +Output the version number. + +# dsv2dsv -o file +
    # dsv2dsv --out file + +Specify the output file name. Defaults to “-” for stdout. + +# dsv2dsv -r delimiter +
    # dsv2dsv --input-delimiter delimiter + +Specify the input delimiter character. Defaults to “,” for reading CSV. (You can enter a tab on the command line by typing ⌃V.) + +# dsv2dsv --input-encoding encoding + +Specify the input character encoding. Defaults to “utf8”. + +# dsv2dsv -w delimiter +
    # dsv2dsv --output-delimiter delimiter + +Specify the output delimiter character. Defaults to “,” for writing CSV. (You can enter a tab on the command line by typing ⌃V.) + +# dsv2dsv --output-encoding encoding + +Specify the output character encoding. Defaults to “utf8”. + +# csv2tsv [options…] [file] + +Equivalent to [dsv2dsv](#dsv2dsv), but the [output delimiter](#dsv2dsv_output_delimiter) defaults to the tab character (\t). + +# tsv2csv [options…] [file] + +Equivalent to [dsv2dsv](#dsv2dsv), but the [input delimiter](#dsv2dsv_output_delimiter) defaults to the tab character (\t). + +### dsv2json + +# dsv2json [options…] [file] + +Converts the specified DSV input *file* to JSON. If *file* is not specified, defaults to reading from stdin. For example, to convert to CSV to JSON: + +``` +csv2json < example.csv > example.json +``` + +Or to convert CSV to a newline-delimited JSON stream: + +``` +csv2json -n < example.csv > example.ndjson +``` + +# dsv2json -h +
    # dsv2json --help + +Output usage information. + +# dsv2json -V +
    # dsv2json --version + +Output the version number. + +# dsv2json -o file +
    # dsv2json --out file + +Specify the output file name. Defaults to “-” for stdout. + +# dsv2json -a +
    # dsv2json --auto-type + +Use type inference when parsing rows. See d3.autoType for how it works. + +# dsv2json -r delimiter +
    # dsv2json --input-delimiter delimiter + +Specify the input delimiter character. Defaults to “,” for reading CSV. (You can enter a tab on the command line by typing ⌃V.) + +# dsv2json --input-encoding encoding + +Specify the input character encoding. Defaults to “utf8”. + +# dsv2json -r encoding +
    # dsv2json --output-encoding encoding + +Specify the output character encoding. Defaults to “utf8”. + +# dsv2json -n +
    # dsv2json --newline-delimited + +Output [newline-delimited JSON](https://github.com/mbostock/ndjson-cli) instead of a single JSON array. + +# csv2json [options…] [file] + +Equivalent to [dsv2json](#dsv2json). + +# tsv2json [options…] [file] + +Equivalent to [dsv2json](#dsv2json), but the [input delimiter](#dsv2json_input_delimiter) defaults to the tab character (\t). + +### json2dsv + +# json2dsv [options…] [file] + +Converts the specified JSON input *file* to DSV. If *file* is not specified, defaults to reading from stdin. For example, to convert to JSON to CSV: + +``` +json2csv < example.json > example.csv +``` + +Or to convert a newline-delimited JSON stream to CSV: + +``` +json2csv -n < example.ndjson > example.csv +``` + +# json2dsv -h +
    # json2dsv --help + +Output usage information. + +# json2dsv -V +
    # json2dsv --version + +Output the version number. + +# json2dsv -o file +
    # json2dsv --out file + +Specify the output file name. Defaults to “-” for stdout. + +# json2dsv --input-encoding encoding + +Specify the input character encoding. Defaults to “utf8”. + +# json2dsv -w delimiter +
    # json2dsv --output-delimiter delimiter + +Specify the output delimiter character. Defaults to “,” for writing CSV. (You can enter a tab on the command line by typing ⌃V.) + +# json2dsv --output-encoding encoding + +Specify the output character encoding. Defaults to “utf8”. + +# json2dsv -n +
    # json2dsv --newline-delimited + +Read [newline-delimited JSON](https://github.com/mbostock/ndjson-cli) instead of a single JSON array. + +# json2csv [options…] [file] + +Equivalent to [json2dsv](#json2dsv). + +# json2tsv [options…] [file] + +Equivalent to [json2dsv](#json2dsv), but the [output delimiter](#json2dsv_output_delimiter) defaults to the tab character (\t). diff --git a/frontend/node_modules/d3-dsv/bin/dsv2dsv.js b/frontend/node_modules/d3-dsv/bin/dsv2dsv.js new file mode 100755 index 0000000..0dd38ba --- /dev/null +++ b/frontend/node_modules/d3-dsv/bin/dsv2dsv.js @@ -0,0 +1,35 @@ +#!/usr/bin/env node + +import {EOL} from "os"; +import {basename, dirname, resolve} from "path"; +import {readFileSync} from "fs"; +import {fileURLToPath} from "url"; +import rw from "rw"; +import {program} from "commander"; +import iconv from "iconv-lite"; +import {dsvFormat} from "../src/index.js"; + +const progname = basename(process.argv[1]); +const defaultInDelimiter = progname.slice(0, 3) === "tsv" ? "\t" : ","; +const defaultOutDelimiter = progname.slice(-3) === "tsv" ? "\t" : ","; + +const options = program + .version(JSON.parse(readFileSync(resolve(dirname(fileURLToPath(import.meta.url)), "../package.json"))).version) + .usage("[options] [file]") + .option("-o, --out ", "output file name; defaults to “-” for stdout", "-") + .option("-r, --input-delimiter ", "input delimiter character", defaultInDelimiter) + .option("-w, --output-delimiter ", "output delimiter character", defaultOutDelimiter) + .option("--input-encoding ", "input character encoding; defaults to “utf8”", "utf8") + .option("--output-encoding ", "output character encoding; defaults to “utf8”", "utf8") + .parse(process.argv) + .opts(); + +const inFormat = dsvFormat(options.inputDelimiter); +const outFormat = dsvFormat(options.outputDelimiter); + +rw.dash.readFile(program.args[0] || "-", (error, text) => { + if (error) throw error; + rw.dash.writeFile("-", iconv.encode(outFormat.format(inFormat.parse(iconv.decode(text, options.inputEncoding))) + EOL, options.outputEncoding), (error) => { + if (error) throw error; + }); +}); diff --git a/frontend/node_modules/d3-dsv/bin/dsv2json.js b/frontend/node_modules/d3-dsv/bin/dsv2json.js new file mode 100755 index 0000000..c2a447f --- /dev/null +++ b/frontend/node_modules/d3-dsv/bin/dsv2json.js @@ -0,0 +1,38 @@ +#!/usr/bin/env node + +import {EOL} from "os"; +import {basename, dirname, resolve} from "path"; +import {readFileSync} from "fs"; +import {fileURLToPath} from "url"; +import rw from "rw"; +import {program} from "commander"; +import iconv from "iconv-lite"; +import {dsvFormat} from "../src/index.js"; + +const progname = basename(process.argv[1]); +const defaultInDelimiter = progname.slice(0, 3) === "tsv" ? "\t" : ","; + +const options = program + .version(JSON.parse(readFileSync(resolve(dirname(fileURLToPath(import.meta.url)), "../package.json"))).version) + .usage("[options] [file]") + .option("-o, --out ", "output file name; defaults to “-” for stdout", "-") + .option("-r, --input-delimiter ", "input delimiter character", defaultInDelimiter) + .option("-a, --auto-type", "parse rows with type inference (see d3.autoType)") + .option("-n, --newline-delimited", "output newline-delimited JSON") + .option("--input-encoding ", "input character encoding; defaults to “utf8”", "utf8") + .option("--output-encoding ", "output character encoding; defaults to “utf8”", "utf8") + .parse(process.argv) + .opts(); + +const inFormat = dsvFormat(options.inputDelimiter); + +rw.dash.readFile(program.args[0] || "-", (error, text) => { + if (error) throw error; + const rowConverter = options.autoType ? dsv.autoType : null + const rows = inFormat.parse(iconv.decode(text, options.inputEncoding), rowConverter); + rw.dash.writeFile(options.out, iconv.encode(options.newlineDelimited + ? rows.map((row) => JSON.stringify(row)).join("\n") + "\n" + : JSON.stringify(rows) + EOL, options.outputEncoding), (error) => { + if (error) throw error; + }); +}); diff --git a/frontend/node_modules/d3-dsv/bin/json2dsv.js b/frontend/node_modules/d3-dsv/bin/json2dsv.js new file mode 100755 index 0000000..75606b8 --- /dev/null +++ b/frontend/node_modules/d3-dsv/bin/json2dsv.js @@ -0,0 +1,36 @@ +#!/usr/bin/env node + +import {EOL} from "os"; +import {basename, dirname, resolve} from "path"; +import {readFileSync} from "fs"; +import {fileURLToPath} from "url"; +import rw from "rw"; +import {program} from "commander"; +import iconv from "iconv-lite"; +import {dsvFormat} from "../src/index.js"; + +const progname = basename(process.argv[1]); +const defaultOutDelimiter = progname.slice(-3) === "tsv" ? "\t" : ","; + +const options = program + .version(JSON.parse(readFileSync(resolve(dirname(fileURLToPath(import.meta.url)), "../package.json"))).version) + .usage("[options] [file]") + .option("-o, --out ", "output file name; defaults to “-” for stdout", "-") + .option("-w, --output-delimiter ", "output delimiter character", defaultOutDelimiter) + .option("-n, --newline-delimited", "accept newline-delimited JSON") + .option("--input-encoding ", "input character encoding; defaults to “utf8”", "utf8") + .option("--output-encoding ", "output character encoding; defaults to “utf8”", "utf8") + .parse(process.argv) + .opts(); + +const outFormat = dsvFormat(options.outputDelimiter); + +rw.dash.readFile(program.args[0] || "-", (error, text) => { + if (error) throw error; + text = iconv.decode(text, options.inputEncoding); + rw.dash.writeFile(options.out, iconv.encode(outFormat.format(options.newlineDelimited + ? text.trim().split(/\r?\n/g).map((line) => JSON.parse(line)) + : JSON.parse(text)) + EOL, options.outputEncoding), (error) => { + if (error) throw error; + }); +}); diff --git a/frontend/node_modules/d3-dsv/dist/d3-dsv.js b/frontend/node_modules/d3-dsv/dist/d3-dsv.js new file mode 100644 index 0000000..2b58579 --- /dev/null +++ b/frontend/node_modules/d3-dsv/dist/d3-dsv.js @@ -0,0 +1,233 @@ +// https://d3js.org/d3-dsv/ v3.0.1 Copyright 2013-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +}(this, (function (exports) { 'use strict'; + +var EOL = {}, + EOF = {}, + QUOTE = 34, + NEWLINE = 10, + RETURN = 13; + +function objectConverter(columns) { + return new Function("d", "return {" + columns.map(function(name, i) { + return JSON.stringify(name) + ": d[" + i + "] || \"\""; + }).join(",") + "}"); +} + +function customConverter(columns, f) { + var object = objectConverter(columns); + return function(row, i) { + return f(object(row), i, columns); + }; +} + +// Compute unique columns in order of discovery. +function inferColumns(rows) { + var columnSet = Object.create(null), + columns = []; + + rows.forEach(function(row) { + for (var column in row) { + if (!(column in columnSet)) { + columns.push(columnSet[column] = column); + } + } + }); + + return columns; +} + +function pad(value, width) { + var s = value + "", length = s.length; + return length < width ? new Array(width - length + 1).join(0) + s : s; +} + +function formatYear(year) { + return year < 0 ? "-" + pad(-year, 6) + : year > 9999 ? "+" + pad(year, 6) + : pad(year, 4); +} + +function formatDate(date) { + var hours = date.getUTCHours(), + minutes = date.getUTCMinutes(), + seconds = date.getUTCSeconds(), + milliseconds = date.getUTCMilliseconds(); + return isNaN(date) ? "Invalid Date" + : formatYear(date.getUTCFullYear()) + "-" + pad(date.getUTCMonth() + 1, 2) + "-" + pad(date.getUTCDate(), 2) + + (milliseconds ? "T" + pad(hours, 2) + ":" + pad(minutes, 2) + ":" + pad(seconds, 2) + "." + pad(milliseconds, 3) + "Z" + : seconds ? "T" + pad(hours, 2) + ":" + pad(minutes, 2) + ":" + pad(seconds, 2) + "Z" + : minutes || hours ? "T" + pad(hours, 2) + ":" + pad(minutes, 2) + "Z" + : ""); +} + +function dsv(delimiter) { + var reFormat = new RegExp("[\"" + delimiter + "\n\r]"), + DELIMITER = delimiter.charCodeAt(0); + + function parse(text, f) { + var convert, columns, rows = parseRows(text, function(row, i) { + if (convert) return convert(row, i - 1); + columns = row, convert = f ? customConverter(row, f) : objectConverter(row); + }); + rows.columns = columns || []; + return rows; + } + + function parseRows(text, f) { + var rows = [], // output rows + N = text.length, + I = 0, // current character index + n = 0, // current line number + t, // current token + eof = N <= 0, // current token followed by EOF? + eol = false; // current token followed by EOL? + + // Strip the trailing newline. + if (text.charCodeAt(N - 1) === NEWLINE) --N; + if (text.charCodeAt(N - 1) === RETURN) --N; + + function token() { + if (eof) return EOF; + if (eol) return eol = false, EOL; + + // Unescape quotes. + var i, j = I, c; + if (text.charCodeAt(j) === QUOTE) { + while (I++ < N && text.charCodeAt(I) !== QUOTE || text.charCodeAt(++I) === QUOTE); + if ((i = I) >= N) eof = true; + else if ((c = text.charCodeAt(I++)) === NEWLINE) eol = true; + else if (c === RETURN) { eol = true; if (text.charCodeAt(I) === NEWLINE) ++I; } + return text.slice(j + 1, i - 1).replace(/""/g, "\""); + } + + // Find next delimiter or newline. + while (I < N) { + if ((c = text.charCodeAt(i = I++)) === NEWLINE) eol = true; + else if (c === RETURN) { eol = true; if (text.charCodeAt(I) === NEWLINE) ++I; } + else if (c !== DELIMITER) continue; + return text.slice(j, i); + } + + // Return last token before EOF. + return eof = true, text.slice(j, N); + } + + while ((t = token()) !== EOF) { + var row = []; + while (t !== EOL && t !== EOF) row.push(t), t = token(); + if (f && (row = f(row, n++)) == null) continue; + rows.push(row); + } + + return rows; + } + + function preformatBody(rows, columns) { + return rows.map(function(row) { + return columns.map(function(column) { + return formatValue(row[column]); + }).join(delimiter); + }); + } + + function format(rows, columns) { + if (columns == null) columns = inferColumns(rows); + return [columns.map(formatValue).join(delimiter)].concat(preformatBody(rows, columns)).join("\n"); + } + + function formatBody(rows, columns) { + if (columns == null) columns = inferColumns(rows); + return preformatBody(rows, columns).join("\n"); + } + + function formatRows(rows) { + return rows.map(formatRow).join("\n"); + } + + function formatRow(row) { + return row.map(formatValue).join(delimiter); + } + + function formatValue(value) { + return value == null ? "" + : value instanceof Date ? formatDate(value) + : reFormat.test(value += "") ? "\"" + value.replace(/"/g, "\"\"") + "\"" + : value; + } + + return { + parse: parse, + parseRows: parseRows, + format: format, + formatBody: formatBody, + formatRows: formatRows, + formatRow: formatRow, + formatValue: formatValue + }; +} + +var csv = dsv(","); + +var csvParse = csv.parse; +var csvParseRows = csv.parseRows; +var csvFormat = csv.format; +var csvFormatBody = csv.formatBody; +var csvFormatRows = csv.formatRows; +var csvFormatRow = csv.formatRow; +var csvFormatValue = csv.formatValue; + +var tsv = dsv("\t"); + +var tsvParse = tsv.parse; +var tsvParseRows = tsv.parseRows; +var tsvFormat = tsv.format; +var tsvFormatBody = tsv.formatBody; +var tsvFormatRows = tsv.formatRows; +var tsvFormatRow = tsv.formatRow; +var tsvFormatValue = tsv.formatValue; + +function autoType(object) { + for (var key in object) { + var value = object[key].trim(), number, m; + if (!value) value = null; + else if (value === "true") value = true; + else if (value === "false") value = false; + else if (value === "NaN") value = NaN; + else if (!isNaN(number = +value)) value = number; + else if (m = value.match(/^([-+]\d{2})?\d{4}(-\d{2}(-\d{2})?)?(T\d{2}:\d{2}(:\d{2}(\.\d{3})?)?(Z|[-+]\d{2}:\d{2})?)?$/)) { + if (fixtz && !!m[4] && !m[7]) value = value.replace(/-/g, "/").replace(/T/, " "); + value = new Date(value); + } + else continue; + object[key] = value; + } + return object; +} + +// https://github.com/d3/d3-dsv/issues/45 +const fixtz = new Date("2019-01-01T00:00").getHours() || new Date("2019-07-01T00:00").getHours(); + +exports.autoType = autoType; +exports.csvFormat = csvFormat; +exports.csvFormatBody = csvFormatBody; +exports.csvFormatRow = csvFormatRow; +exports.csvFormatRows = csvFormatRows; +exports.csvFormatValue = csvFormatValue; +exports.csvParse = csvParse; +exports.csvParseRows = csvParseRows; +exports.dsvFormat = dsv; +exports.tsvFormat = tsvFormat; +exports.tsvFormatBody = tsvFormatBody; +exports.tsvFormatRow = tsvFormatRow; +exports.tsvFormatRows = tsvFormatRows; +exports.tsvFormatValue = tsvFormatValue; +exports.tsvParse = tsvParse; +exports.tsvParseRows = tsvParseRows; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-dsv/dist/d3-dsv.min.js b/frontend/node_modules/d3-dsv/dist/d3-dsv.min.js new file mode 100644 index 0000000..eb8de3b --- /dev/null +++ b/frontend/node_modules/d3-dsv/dist/d3-dsv.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-dsv/ v3.0.1 Copyright 2013-2021 Mike Bostock +!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports):"function"==typeof define&&define.amd?define(["exports"],t):t((e="undefined"!=typeof globalThis?globalThis:e||self).d3=e.d3||{})}(this,(function(e){"use strict";var t={},r={};function n(e){return new Function("d","return {"+e.map((function(e,t){return JSON.stringify(e)+": d["+t+'] || ""'})).join(",")+"}")}function o(e){var t=Object.create(null),r=[];return e.forEach((function(e){for(var n in e)n in t||r.push(t[n]=n)})),r}function a(e,t){var r=e+"",n=r.length;return n9999?"+"+a(t,6):a(t,4))+"-"+a(e.getUTCMonth()+1,2)+"-"+a(e.getUTCDate(),2)+(u?"T"+a(r,2)+":"+a(n,2)+":"+a(o,2)+"."+a(u,3)+"Z":o?"T"+a(r,2)+":"+a(n,2)+":"+a(o,2)+"Z":n||r?"T"+a(r,2)+":"+a(n,2)+"Z":"")}function i(e){var a=new RegExp('["'+e+"\n\r]"),i=e.charCodeAt(0);function f(e,n){var o,a=[],u=e.length,f=0,s=0,c=u<=0,l=!1;function d(){if(c)return r;if(l)return l=!1,t;var n,o,a=f;if(34===e.charCodeAt(a)){for(;f++=u?c=!0:10===(o=e.charCodeAt(f++))?l=!0:13===o&&(l=!0,10===e.charCodeAt(f)&&++f),e.slice(a+1,n-1).replace(/""/g,'"')}for(;f + + +## [7.2.0] (2021-03-26) + +### Added + +- TypeScript typing for `parent` property on `Command` ([#1475]) +- TypeScript typing for `.attributeName()` on `Option` ([#1483]) +- support information in package ([#1477]) + +### Changed + +- improvements to error messages, README, and tests +- update dependencies + +## [7.1.0] (2021-02-15) + +### Added + +- support for named imports from ECMAScript modules ([#1440]) +- add `.cjs` to list of expected script file extensions ([#1449]) +- allow using option choices and variadic together ([#1454]) + +### Fixed + +- replace use of deprecated `process.mainModule` ([#1448]) +- regression for legacy `command('*')` and call when command line includes options ([#1464]) +- regression for `on('command:*', ...)` and call when command line includes unknown options ([#1464]) +- display best error for combination of unknown command and unknown option (i.e. unknown command) ([#1464]) + +### Changed + +- make TypeScript typings tests stricter ([#1453]) +- improvements to README and tests + +## [7.0.0] (2021-01-15) + +### Added + +- `.enablePositionalOptions()` to let program and subcommand reuse same option ([#1427]) +- `.passThroughOptions()` to pass options through to other programs without needing `--` ([#1427]) +- `.allowExcessArguments(false)` to show an error message if there are too many command-arguments on command line for the action handler ([#1409]) +- `.configureOutput()` to modify use of stdout and stderr or customise display of errors ([#1387]) +- use `.addHelpText()` to add text before or after the built-in help, for just current command or also for all subcommands ([#1296]) +- enhance Option class ([#1331]) + - allow hiding options from help + - allow restricting option arguments to a list of choices + - allow setting how default value is shown in help +- `.createOption()` to support subclassing of automatically created options (like `.createCommand()`) ([#1380]) +- refactor the code generating the help into a separate public Help class ([#1365]) + - support sorting subcommands and options in help + - support specifying wrap width (columns) + - allow subclassing Help class + - allow configuring Help class without subclassing + +### Changed + +- *Breaking:* options are stored safely by default, not as properties on the command ([#1409]) + - this especially affects accessing options on program, use `program.opts()` + - revert behaviour with `.storeOptionsAsProperties()` +- *Breaking:* action handlers are passed options and command separately ([#1409]) +- deprecated callback parameter to `.help()` and `.outputHelp()` (removed from README) ([#1296]) +- *Breaking:* errors now displayed using `process.stderr.write()` instead of `console.error()` +- deprecate `.on('--help')` (removed from README) ([#1296]) +- initialise the command description to empty string (previously undefined) ([#1365]) +- document and annotate deprecated routines ([#1349]) + +### Fixed + +- wrapping bugs in help ([#1365]) + - first line of command description was wrapping two characters early + - pad width calculation was not including help option and help command + - pad width calculation was including hidden options and commands +- improve backwards compatibility for custom command event listeners ([#1403]) + +### Deleted + +- *Breaking:* `.passCommandToAction()` ([#1409]) + - no longer needed as action handler is passed options and command +- *Breaking:* "extra arguments" parameter to action handler ([#1409]) + - if being used to detect excess arguments, there is now an error available by setting `.allowExcessArguments(false)` + +### Migration Tips + +The biggest change is the parsed option values. Previously the options were stored by default as properties on the command object, and now the options are stored separately. + +If you wish to restore the old behaviour and get running quickly you can call `.storeOptionsAsProperties()`. +To allow you to move to the new code patterns incrementally, the action handler will be passed the command _twice_, +to match the new "options" and "command" parameters (see below). + +**program options** + +Use the `.opts()` method to access the options. This is available on any command but is used most with the program. + +```js +program.option('-d, --debug'); +program.parse(); +// Old code before Commander 7 +if (program.debug) console.log(`Program name is ${program.name()}`); +``` + +```js +// New code +const options = program.opts(); +if (options.debug) console.log(`Program name is ${program.name()}`); +``` + +**action handler** + +The action handler gets passed a parameter for each command-argument you declared. Previously by default the next parameter was the command object with the options as properties. Now the next two parameters are instead the options and the command. If you +only accessed the options there may be no code changes required. + +```js +program + .command('compress ') + .option('-t, --trace') + // Old code before Commander 7 + .action((filename, cmd)) => { + if (cmd.trace) console.log(`Command name is ${cmd.name()}`); + }); +``` + +```js + // New code + .action((filename, options, command)) => { + if (options.trace) console.log(`Command name is ${command.name()}`); + }); +``` + +If you already set `.storeOptionsAsProperties(false)` you may still need to adjust your code. + +```js +program + .command('compress ') + .storeOptionsAsProperties(false) + .option('-t, --trace') + // Old code before Commander 7 + .action((filename, command)) => { + if (command.opts().trace) console.log(`Command name is ${command.name()}`); + }); +``` + +```js + // New code + .action((filename, options, command)) => { + if (command.opts().trace) console.log(`Command name is ${command.name()}`); + }); +``` + +## [7.0.0-2] (2020-12-14) + +(Released in 7.0.0) + +## [7.0.0-1] (2020-11-21) + +(Released in 7.0.0) + +## [7.0.0-0] (2020-10-25) + +(Released in 7.0.0) + +## [6.2.1] (2020-12-13) + +### Fixed + +- some tests failed if directory path included a space ([1390]) + +## [6.2.0] (2020-10-25) + +### Added + +- added 'tsx' file extension for stand-alone executable subcommands ([#1368]) +- documented second parameter to `.description()` to describe command arguments ([#1353]) +- documentation of special cases with options taking varying numbers of option-arguments ([#1332]) +- documentation for terminology ([#1361]) + +### Fixed + +- add missing TypeScript definition for `.addHelpCommand()' ([#1375]) +- removed blank line after "Arguments:" in help, to match "Options:" and "Commands:" ([#1360]) + +### Changed + +- update dependencies + +## [6.1.0] (2020-08-28) + +### Added + +- include URL to relevant section of README for error for potential conflict between Command properties and option values ([#1306]) +- `.combineFlagAndOptionalValue(false)` to ease upgrade path from older versions of Commander ([#1326]) +- allow disabling the built-in help option using `.helpOption(false)` ([#1325]) +- allow just some arguments in `argumentDescription` to `.description()` ([#1323]) + +### Changed + +- tidy async test and remove lint override ([#1312]) + +### Fixed + +- executable subcommand launching when script path not known ([#1322]) + +## [6.0.0] (2020-07-21) + +### Added + +- add support for variadic options ([#1250]) +- allow options to be added with just a short flag ([#1256]) + - *Breaking* the option property has same case as flag. e.g. flag `-n` accessed as `opts().n` (previously uppercase) +- *Breaking* throw an error if there might be a clash between option name and a Command property, with advice on how to resolve ([#1275]) + +### Fixed + +- Options which contain -no- in the middle of the option flag should not be treated as negatable. ([#1301]) + +## [6.0.0-0] (2020-06-20) + +(Released in 6.0.0) + +## [5.1.0] (2020-04-25) + +### Added + +- support for multiple command aliases, the first of which is shown in the auto-generated help ([#531], [#1236]) +- configuration support in `addCommand()` for `hidden` and `isDefault` ([#1232]) + +### Fixed + +- omit masked help flags from the displayed help ([#645], [#1247]) +- remove old short help flag when change help flags using `helpOption` ([#1248]) + +### Changed + +- remove use of `arguments` to improve auto-generated help in editors ([#1235]) +- rename `.command()` configuration `noHelp` to `hidden` (but not remove old support) ([#1232]) +- improvements to documentation +- update dependencies +- update tested versions of node +- eliminate lint errors in TypeScript ([#1208]) + +## [5.0.0] (2020-03-14) + +### Added + +* support for nested commands with action-handlers ([#1] [#764] [#1149]) +* `.addCommand()` for adding a separately configured command ([#764] [#1149]) +* allow a non-executable to be set as the default command ([#742] [#1149]) +* implicit help command when there are subcommands (previously only if executables) ([#1149]) +* customise implicit help command with `.addHelpCommand()` ([#1149]) +* display error message for unknown subcommand, by default ([#432] [#1088] [#1149]) +* display help for missing subcommand, by default ([#1088] [#1149]) +* combined short options as single argument may include boolean flags and value flag and value (e.g. `-a -b -p 80` can be written as `-abp80`) ([#1145]) +* `.parseOption()` includes short flag and long flag expansions ([#1145]) +* `.helpInformation()` returns help text as a string, previously a private routine ([#1169]) +* `.parse()` implicitly uses `process.argv` if arguments not specified ([#1172]) +* optionally specify where `.parse()` arguments "from", if not following node conventions ([#512] [#1172]) +* suggest help option along with unknown command error ([#1179]) +* TypeScript definition for `commands` property of `Command` ([#1184]) +* export `program` property ([#1195]) +* `createCommand` factory method to simplify subclassing ([#1191]) + +### Fixed + +* preserve argument order in subcommands ([#508] [#962] [#1138]) +* do not emit `command:*` for executable subcommands ([#809] [#1149]) +* action handler called whether or not there are non-option arguments ([#1062] [#1149]) +* combining option short flag and value in single argument now works for subcommands ([#1145]) +* only add implicit help command when it will not conflict with other uses of argument ([#1153] [#1149]) +* implicit help command works with command aliases ([#948] [#1149]) +* options are validated whether or not there is an action handler ([#1149]) + +### Changed + +* *Breaking* `.args` contains command arguments with just recognised options removed ([#1032] [#1138]) +* *Breaking* display error if required argument for command is missing ([#995] [#1149]) +* tighten TypeScript definition of custom option processing function passed to `.option()` ([#1119]) +* *Breaking* `.allowUnknownOption()` ([#802] [#1138]) + * unknown options included in arguments passed to command action handler + * unknown options included in `.args` +* only recognised option short flags and long flags are expanded (e.g. `-ab` or `--foo=bar`) ([#1145]) +* *Breaking* `.parseOptions()` ([#1138]) + * `args` in returned result renamed `operands` and does not include anything after first unknown option + * `unknown` in returned result has arguments after first unknown option including operands, not just options and values +* *Breaking* `.on('command:*', callback)` and other command events passed (changed) results from `.parseOptions`, i.e. operands and unknown ([#1138]) +* refactor Option from prototype to class ([#1133]) +* refactor Command from prototype to class ([#1159]) +* changes to error handling ([#1165]) + * throw for author error, not just display message + * preflight for variadic error + * add tips to missing subcommand executable +* TypeScript fluent return types changed to be more subclass friendly, return `this` rather than `Command` ([#1180]) +* `.parseAsync` returns `Promise` to be consistent with `.parse()` ([#1180]) +* update dependencies + +### Removed + +* removed EventEmitter from TypeScript definition for Command, eliminating implicit peer dependency on `@types/node` ([#1146]) +* removed private function `normalize` (the functionality has been integrated into `parseOptions`) ([#1145]) +* `parseExpectedArgs` is now private ([#1149]) + +### Migration Tips + +If you use `.on('command:*')` or more complicated tests to detect an unrecognised subcommand, you may be able to delete the code and rely on the default behaviour. + +If you use `program.args` or more complicated tests to detect a missing subcommand, you may be able to delete the code and rely on the default behaviour. + +If you use `.command('*')` to add a default command, you may be be able to switch to `isDefault:true` with a named command. + +If you want to continue combining short options with optional values as though they were boolean flags, set `combineFlagAndOptionalValue(false)` +to expand `-fb` to `-f -b` rather than `-f b`. + +## [5.0.0-4] (2020-03-03) + +(Released in 5.0.0) + +## [5.0.0-3] (2020-02-20) + +(Released in 5.0.0) + +## [5.0.0-2] (2020-02-10) + +(Released in 5.0.0) + +## [5.0.0-1] (2020-02-08) + +(Released in 5.0.0) + +## [5.0.0-0] (2020-02-02) + +(Released in 5.0.0) + +## Older versions + +* [4.x](./changelogs/CHANGELOG-4.md) +* [3.x](./changelogs/CHANGELOG-3.md) +* [2.x](./changelogs/CHANGELOG-2.md) +* [1.x](./changelogs/CHANGELOG-1.md) +* [0.x](./changelogs/CHANGELOG-0.md) + +[#1]: https://github.com/tj/commander.js/issues/1 +[#432]: https://github.com/tj/commander.js/issues/432 +[#508]: https://github.com/tj/commander.js/issues/508 +[#512]: https://github.com/tj/commander.js/issues/512 +[#531]: https://github.com/tj/commander.js/issues/531 +[#645]: https://github.com/tj/commander.js/issues/645 +[#742]: https://github.com/tj/commander.js/issues/742 +[#764]: https://github.com/tj/commander.js/issues/764 +[#802]: https://github.com/tj/commander.js/issues/802 +[#809]: https://github.com/tj/commander.js/issues/809 +[#948]: https://github.com/tj/commander.js/issues/948 +[#962]: https://github.com/tj/commander.js/issues/962 +[#995]: https://github.com/tj/commander.js/issues/995 +[#1032]: https://github.com/tj/commander.js/issues/1032 +[#1062]: https://github.com/tj/commander.js/pull/1062 +[#1088]: https://github.com/tj/commander.js/issues/1088 +[#1119]: https://github.com/tj/commander.js/pull/1119 +[#1133]: https://github.com/tj/commander.js/pull/1133 +[#1138]: https://github.com/tj/commander.js/pull/1138 +[#1145]: https://github.com/tj/commander.js/pull/1145 +[#1146]: https://github.com/tj/commander.js/pull/1146 +[#1149]: https://github.com/tj/commander.js/pull/1149 +[#1153]: https://github.com/tj/commander.js/issues/1153 +[#1159]: https://github.com/tj/commander.js/pull/1159 +[#1165]: https://github.com/tj/commander.js/pull/1165 +[#1169]: https://github.com/tj/commander.js/pull/1169 +[#1172]: https://github.com/tj/commander.js/pull/1172 +[#1179]: https://github.com/tj/commander.js/pull/1179 +[#1180]: https://github.com/tj/commander.js/pull/1180 +[#1184]: https://github.com/tj/commander.js/pull/1184 +[#1191]: https://github.com/tj/commander.js/pull/1191 +[#1195]: https://github.com/tj/commander.js/pull/1195 +[#1208]: https://github.com/tj/commander.js/pull/1208 +[#1232]: https://github.com/tj/commander.js/pull/1232 +[#1235]: https://github.com/tj/commander.js/pull/1235 +[#1236]: https://github.com/tj/commander.js/pull/1236 +[#1247]: https://github.com/tj/commander.js/pull/1247 +[#1248]: https://github.com/tj/commander.js/pull/1248 +[#1250]: https://github.com/tj/commander.js/pull/1250 +[#1256]: https://github.com/tj/commander.js/pull/1256 +[#1275]: https://github.com/tj/commander.js/pull/1275 +[#1296]: https://github.com/tj/commander.js/pull/1296 +[#1301]: https://github.com/tj/commander.js/issues/1301 +[#1306]: https://github.com/tj/commander.js/pull/1306 +[#1312]: https://github.com/tj/commander.js/pull/1312 +[#1322]: https://github.com/tj/commander.js/pull/1322 +[#1323]: https://github.com/tj/commander.js/pull/1323 +[#1325]: https://github.com/tj/commander.js/pull/1325 +[#1326]: https://github.com/tj/commander.js/pull/1326 +[#1331]: https://github.com/tj/commander.js/pull/1331 +[#1332]: https://github.com/tj/commander.js/pull/1332 +[#1349]: https://github.com/tj/commander.js/pull/1349 +[#1353]: https://github.com/tj/commander.js/pull/1353 +[#1360]: https://github.com/tj/commander.js/pull/1360 +[#1361]: https://github.com/tj/commander.js/pull/1361 +[#1365]: https://github.com/tj/commander.js/pull/1365 +[#1368]: https://github.com/tj/commander.js/pull/1368 +[#1375]: https://github.com/tj/commander.js/pull/1375 +[#1380]: https://github.com/tj/commander.js/pull/1380 +[#1387]: https://github.com/tj/commander.js/pull/1387 +[#1390]: https://github.com/tj/commander.js/pull/1390 +[#1403]: https://github.com/tj/commander.js/pull/1403 +[#1409]: https://github.com/tj/commander.js/pull/1409 +[#1427]: https://github.com/tj/commander.js/pull/1427 +[#1440]: https://github.com/tj/commander.js/pull/1440 +[#1448]: https://github.com/tj/commander.js/pull/1448 +[#1449]: https://github.com/tj/commander.js/pull/1449 +[#1453]: https://github.com/tj/commander.js/pull/1453 +[#1454]: https://github.com/tj/commander.js/pull/1454 +[#1464]: https://github.com/tj/commander.js/pull/1464 +[#1475]: https://github.com/tj/commander.js/pull/1475 +[#1477]: https://github.com/tj/commander.js/pull/1477 +[#1483]: https://github.com/tj/commander.js/pull/1483 + +[Unreleased]: https://github.com/tj/commander.js/compare/master...develop +[7.2.0]: https://github.com/tj/commander.js/compare/v7.1.0...v7.2.0 +[7.1.0]: https://github.com/tj/commander.js/compare/v7.0.0...v7.1.0 +[7.0.0]: https://github.com/tj/commander.js/compare/v6.2.1...v7.0.0 +[7.0.0-2]: https://github.com/tj/commander.js/compare/v7.0.0-1...v7.0.0-2 +[7.0.0-1]: https://github.com/tj/commander.js/compare/v7.0.0-0...v7.0.0-1 +[7.0.0-0]: https://github.com/tj/commander.js/compare/v6.2.0...v7.0.0-0 +[6.2.1]: https://github.com/tj/commander.js/compare/v6.2.0..v6.2.1 +[6.2.0]: https://github.com/tj/commander.js/compare/v6.1.0..v6.2.0 +[6.1.0]: https://github.com/tj/commander.js/compare/v6.0.0..v6.1.0 +[6.0.0]: https://github.com/tj/commander.js/compare/v5.1.0..v6.0.0 +[6.0.0-0]: https://github.com/tj/commander.js/compare/v5.1.0..v6.0.0-0 +[5.1.0]: https://github.com/tj/commander.js/compare/v5.0.0..v5.1.0 +[5.0.0]: https://github.com/tj/commander.js/compare/v4.1.1..v5.0.0 +[5.0.0-4]: https://github.com/tj/commander.js/compare/v5.0.0-3..v5.0.0-4 +[5.0.0-3]: https://github.com/tj/commander.js/compare/v5.0.0-2..v5.0.0-3 +[5.0.0-2]: https://github.com/tj/commander.js/compare/v5.0.0-1..v5.0.0-2 +[5.0.0-1]: https://github.com/tj/commander.js/compare/v5.0.0-0..v5.0.0-1 +[5.0.0-0]: https://github.com/tj/commander.js/compare/v4.1.1..v5.0.0-0 diff --git a/frontend/node_modules/d3-dsv/node_modules/commander/LICENSE b/frontend/node_modules/d3-dsv/node_modules/commander/LICENSE new file mode 100644 index 0000000..10f997a --- /dev/null +++ b/frontend/node_modules/d3-dsv/node_modules/commander/LICENSE @@ -0,0 +1,22 @@ +(The MIT License) + +Copyright (c) 2011 TJ Holowaychuk + +Permission is hereby granted, free of charge, to any person obtaining +a copy of this software and associated documentation files (the +'Software'), to deal in the Software without restriction, including +without limitation the rights to use, copy, modify, merge, publish, +distribute, sublicense, and/or sell copies of the Software, and to +permit persons to whom the Software is furnished to do so, subject to +the following conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY +CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, +TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE +SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/frontend/node_modules/d3-dsv/node_modules/commander/Readme.md b/frontend/node_modules/d3-dsv/node_modules/commander/Readme.md new file mode 100644 index 0000000..d2a88a7 --- /dev/null +++ b/frontend/node_modules/d3-dsv/node_modules/commander/Readme.md @@ -0,0 +1,917 @@ +# Commander.js + +[![Build Status](https://github.com/tj/commander.js/workflows/build/badge.svg)](https://github.com/tj/commander.js/actions?query=workflow%3A%22build%22) +[![NPM Version](http://img.shields.io/npm/v/commander.svg?style=flat)](https://www.npmjs.org/package/commander) +[![NPM Downloads](https://img.shields.io/npm/dm/commander.svg?style=flat)](https://npmcharts.com/compare/commander?minimal=true) +[![Install Size](https://packagephobia.now.sh/badge?p=commander)](https://packagephobia.now.sh/result?p=commander) + +The complete solution for [node.js](http://nodejs.org) command-line interfaces. + +Read this in other languages: English | [简体中文](./Readme_zh-CN.md) + +- [Commander.js](#commanderjs) + - [Installation](#installation) + - [Declaring _program_ variable](#declaring-program-variable) + - [Options](#options) + - [Common option types, boolean and value](#common-option-types-boolean-and-value) + - [Default option value](#default-option-value) + - [Other option types, negatable boolean and boolean|value](#other-option-types-negatable-boolean-and-booleanvalue) + - [Required option](#required-option) + - [Variadic option](#variadic-option) + - [Version option](#version-option) + - [More configuration](#more-configuration) + - [Custom option processing](#custom-option-processing) + - [Commands](#commands) + - [Specify the argument syntax](#specify-the-argument-syntax) + - [Action handler](#action-handler) + - [Stand-alone executable (sub)commands](#stand-alone-executable-subcommands) + - [Automated help](#automated-help) + - [Custom help](#custom-help) + - [Display help from code](#display-help-from-code) + - [.usage and .name](#usage-and-name) + - [.helpOption(flags, description)](#helpoptionflags-description) + - [.addHelpCommand()](#addhelpcommand) + - [More configuration](#more-configuration-1) + - [Custom event listeners](#custom-event-listeners) + - [Bits and pieces](#bits-and-pieces) + - [.parse() and .parseAsync()](#parse-and-parseasync) + - [Parsing Configuration](#parsing-configuration) + - [Legacy options as properties](#legacy-options-as-properties) + - [TypeScript](#typescript) + - [createCommand()](#createcommand) + - [Node options such as `--harmony`](#node-options-such-as---harmony) + - [Debugging stand-alone executable subcommands](#debugging-stand-alone-executable-subcommands) + - [Override exit and output handling](#override-exit-and-output-handling) + - [Additional documentation](#additional-documentation) + - [Examples](#examples) + - [Support](#support) + - [Commander for enterprise](#commander-for-enterprise) + +For information about terms used in this document see: [terminology](./docs/terminology.md) + +## Installation + +```bash +npm install commander +``` + +## Declaring _program_ variable + +Commander exports a global object which is convenient for quick programs. +This is used in the examples in this README for brevity. + +```js +const { program } = require('commander'); +program.version('0.0.1'); +``` + +For larger programs which may use commander in multiple ways, including unit testing, it is better to create a local Command object to use. + +```js +const { Command } = require('commander'); +const program = new Command(); +program.version('0.0.1'); +``` + +For named imports in ECMAScript modules, import from `commander/esm.mjs`. + +```js +// index.mjs +import { Command } from 'commander/esm.mjs'; +const program = new Command(); +``` + +And in TypeScript: + +```ts +// index.ts +import { Command } from 'commander'; +const program = new Command(); +``` + + +## Options + +Options are defined with the `.option()` method, also serving as documentation for the options. Each option can have a short flag (single character) and a long name, separated by a comma or space or vertical bar ('|'). + +The parsed options can be accessed by calling `.opts()` on a `Command` object, and are passed to the action handler. Multi-word options such as "--template-engine" are camel-cased, becoming `program.opts().templateEngine` etc. + +Multiple short flags may optionally be combined in a single argument following the dash: boolean flags, followed by a single option taking a value (possibly followed by the value). +For example `-a -b -p 80` may be written as `-ab -p80` or even `-abp80`. + +You can use `--` to indicate the end of the options, and any remaining arguments will be used without being interpreted. + +By default options on the command line are not positional, and can be specified before or after other arguments. + +### Common option types, boolean and value + +The two most used option types are a boolean option, and an option which takes its value +from the following argument (declared with angle brackets like `--expect `). Both are `undefined` unless specified on command line. + +Example file: [options-common.js](./examples/options-common.js) + +```js +program + .option('-d, --debug', 'output extra debugging') + .option('-s, --small', 'small pizza size') + .option('-p, --pizza-type ', 'flavour of pizza'); + +program.parse(process.argv); + +const options = program.opts(); +if (options.debug) console.log(options); +console.log('pizza details:'); +if (options.small) console.log('- small pizza size'); +if (options.pizzaType) console.log(`- ${options.pizzaType}`); +``` + +```bash +$ pizza-options -d +{ debug: true, small: undefined, pizzaType: undefined } +pizza details: +$ pizza-options -p +error: option '-p, --pizza-type ' argument missing +$ pizza-options -ds -p vegetarian +{ debug: true, small: true, pizzaType: 'vegetarian' } +pizza details: +- small pizza size +- vegetarian +$ pizza-options --pizza-type=cheese +pizza details: +- cheese +``` + +`program.parse(arguments)` processes the arguments, leaving any args not consumed by the program options in the `program.args` array. The parameter is optional and defaults to `process.argv`. + +### Default option value + +You can specify a default value for an option which takes a value. + +Example file: [options-defaults.js](./examples/options-defaults.js) + +```js +program + .option('-c, --cheese ', 'add the specified type of cheese', 'blue'); + +program.parse(); + +console.log(`cheese: ${program.opts().cheese}`); +``` + +```bash +$ pizza-options +cheese: blue +$ pizza-options --cheese stilton +cheese: stilton +``` + +### Other option types, negatable boolean and boolean|value + +You can define a boolean option long name with a leading `no-` to set the option value to false when used. +Defined alone this also makes the option true by default. + +If you define `--foo` first, adding `--no-foo` does not change the default value from what it would +otherwise be. You can specify a default boolean value for a boolean option and it can be overridden on command line. + +Example file: [options-negatable.js](./examples/options-negatable.js) + +```js +program + .option('--no-sauce', 'Remove sauce') + .option('--cheese ', 'cheese flavour', 'mozzarella') + .option('--no-cheese', 'plain with no cheese') + .parse(); + +const options = program.opts(); +const sauceStr = options.sauce ? 'sauce' : 'no sauce'; +const cheeseStr = (options.cheese === false) ? 'no cheese' : `${options.cheese} cheese`; +console.log(`You ordered a pizza with ${sauceStr} and ${cheeseStr}`); +``` + +```bash +$ pizza-options +You ordered a pizza with sauce and mozzarella cheese +$ pizza-options --sauce +error: unknown option '--sauce' +$ pizza-options --cheese=blue +You ordered a pizza with sauce and blue cheese +$ pizza-options --no-sauce --no-cheese +You ordered a pizza with no sauce and no cheese +``` + +You can specify an option which may be used as a boolean option but may optionally take an option-argument +(declared with square brackets like `--optional [value]`). + +Example file: [options-boolean-or-value.js](./examples/options-boolean-or-value.js) + +```js +program + .option('-c, --cheese [type]', 'Add cheese with optional type'); + +program.parse(process.argv); + +const options = program.opts(); +if (options.cheese === undefined) console.log('no cheese'); +else if (options.cheese === true) console.log('add cheese'); +else console.log(`add cheese type ${options.cheese}`); +``` + +```bash +$ pizza-options +no cheese +$ pizza-options --cheese +add cheese +$ pizza-options --cheese mozzarella +add cheese type mozzarella +``` + +For information about possible ambiguous cases, see [options taking varying arguments](./docs/options-taking-varying-arguments.md). + +### Required option + +You may specify a required (mandatory) option using `.requiredOption`. The option must have a value after parsing, usually specified on the command line, or perhaps from a default value (say from environment). The method is otherwise the same as `.option` in format, taking flags and description, and optional default value or custom processing. + +Example file: [options-required.js](./examples/options-required.js) + +```js +program + .requiredOption('-c, --cheese ', 'pizza must have cheese'); + +program.parse(); +``` + +```bash +$ pizza +error: required option '-c, --cheese ' not specified +``` + +### Variadic option + +You may make an option variadic by appending `...` to the value placeholder when declaring the option. On the command line you +can then specify multiple option-arguments, and the parsed option value will be an array. The extra arguments +are read until the first argument starting with a dash. The special argument `--` stops option processing entirely. If a value +is specified in the same argument as the option then no further values are read. + +Example file: [options-variadic.js](./examples/options-variadic.js) + +```js +program + .option('-n, --number ', 'specify numbers') + .option('-l, --letter [letters...]', 'specify letters'); + +program.parse(); + +console.log('Options: ', program.opts()); +console.log('Remaining arguments: ', program.args); +``` + +```bash +$ collect -n 1 2 3 --letter a b c +Options: { number: [ '1', '2', '3' ], letter: [ 'a', 'b', 'c' ] } +Remaining arguments: [] +$ collect --letter=A -n80 operand +Options: { number: [ '80' ], letter: [ 'A' ] } +Remaining arguments: [ 'operand' ] +$ collect --letter -n 1 -n 2 3 -- operand +Options: { number: [ '1', '2', '3' ], letter: true } +Remaining arguments: [ 'operand' ] +``` + +For information about possible ambiguous cases, see [options taking varying arguments](./docs/options-taking-varying-arguments.md). + +### Version option + +The optional `version` method adds handling for displaying the command version. The default option flags are `-V` and `--version`, and when present the command prints the version number and exits. + +```js +program.version('0.0.1'); +``` + +```bash +$ ./examples/pizza -V +0.0.1 +``` + +You may change the flags and description by passing additional parameters to the `version` method, using +the same syntax for flags as the `option` method. + +```js +program.version('0.0.1', '-v, --vers', 'output the current version'); +``` + +### More configuration + +You can add most options using the `.option()` method, but there are some additional features available +by constructing an `Option` explicitly for less common cases. + +Example file: [options-extra.js](./examples/options-extra.js) + +```js +program + .addOption(new Option('-s, --secret').hideHelp()) + .addOption(new Option('-t, --timeout ', 'timeout in seconds').default(60, 'one minute')) + .addOption(new Option('-d, --drink ', 'drink size').choices(['small', 'medium', 'large'])); +``` + +```bash +$ extra --help +Usage: help [options] + +Options: + -t, --timeout timeout in seconds (default: one minute) + -d, --drink drink cup size (choices: "small", "medium", "large") + -h, --help display help for command + +$ extra --drink huge +error: option '-d, --drink ' argument 'huge' is invalid. Allowed choices are small, medium, large. +``` + +### Custom option processing + +You may specify a function to do custom processing of option-arguments. The callback function receives two parameters, +the user specified option-argument and the previous value for the option. It returns the new value for the option. + +This allows you to coerce the option-argument to the desired type, or accumulate values, or do entirely custom processing. + +You can optionally specify the default/starting value for the option after the function parameter. + +Example file: [options-custom-processing.js](./examples/options-custom-processing.js) + +```js +function myParseInt(value, dummyPrevious) { + // parseInt takes a string and a radix + const parsedValue = parseInt(value, 10); + if (isNaN(parsedValue)) { + throw new commander.InvalidOptionArgumentError('Not a number.'); + } + return parsedValue; +} + +function increaseVerbosity(dummyValue, previous) { + return previous + 1; +} + +function collect(value, previous) { + return previous.concat([value]); +} + +function commaSeparatedList(value, dummyPrevious) { + return value.split(','); +} + +program + .option('-f, --float ', 'float argument', parseFloat) + .option('-i, --integer ', 'integer argument', myParseInt) + .option('-v, --verbose', 'verbosity that can be increased', increaseVerbosity, 0) + .option('-c, --collect ', 'repeatable value', collect, []) + .option('-l, --list ', 'comma separated list', commaSeparatedList) +; + +program.parse(); + +const options = program.opts(); +if (options.float !== undefined) console.log(`float: ${options.float}`); +if (options.integer !== undefined) console.log(`integer: ${options.integer}`); +if (options.verbose > 0) console.log(`verbosity: ${options.verbose}`); +if (options.collect.length > 0) console.log(options.collect); +if (options.list !== undefined) console.log(options.list); +``` + +```bash +$ custom -f 1e2 +float: 100 +$ custom --integer 2 +integer: 2 +$ custom -v -v -v +verbose: 3 +$ custom -c a -c b -c c +[ 'a', 'b', 'c' ] +$ custom --list x,y,z +[ 'x', 'y', 'z' ] +``` + +## Commands + +You can specify (sub)commands using `.command()` or `.addCommand()`. There are two ways these can be implemented: using an action handler attached to the command, or as a stand-alone executable file (described in more detail later). The subcommands may be nested ([example](./examples/nestedCommands.js)). + +In the first parameter to `.command()` you specify the command name and any command-arguments. The arguments may be `` or `[optional]`, and the last argument may also be `variadic...`. + +You can use `.addCommand()` to add an already configured subcommand to the program. + +For example: + +```js +// Command implemented using action handler (description is supplied separately to `.command`) +// Returns new command for configuring. +program + .command('clone [destination]') + .description('clone a repository into a newly created directory') + .action((source, destination) => { + console.log('clone command called'); + }); + +// Command implemented using stand-alone executable file (description is second parameter to `.command`) +// Returns `this` for adding more commands. +program + .command('start ', 'start named service') + .command('stop [service]', 'stop named service, or all if no name supplied'); + +// Command prepared separately. +// Returns `this` for adding more commands. +program + .addCommand(build.makeBuildCommand()); +``` + +Configuration options can be passed with the call to `.command()` and `.addCommand()`. Specifying `hidden: true` will +remove the command from the generated help output. Specifying `isDefault: true` will run the subcommand if no other +subcommand is specified ([example](./examples/defaultCommand.js)). + +### Specify the argument syntax + +You use `.arguments` to specify the expected command-arguments for the top-level command, and for subcommands they are usually +included in the `.command` call. Angled brackets (e.g. ``) indicate required command-arguments. +Square brackets (e.g. `[optional]`) indicate optional command-arguments. +You can optionally describe the arguments in the help by supplying a hash as second parameter to `.description()`. + +Example file: [arguments.js](./examples/arguments.js) + +```js +program + .version('0.1.0') + .arguments(' [password]') + .description('test command', { + username: 'user to login', + password: 'password for user, if required' + }) + .action((username, password) => { + console.log('username:', username); + console.log('environment:', password || 'no password given'); + }); +``` + + The last argument of a command can be variadic, and only the last argument. To make an argument variadic you + append `...` to the argument name. For example: + +```js +program + .version('0.1.0') + .command('rmdir ') + .action(function (dirs) { + dirs.forEach((dir) => { + console.log('rmdir %s', dir); + }); + }); +``` + +The variadic argument is passed to the action handler as an array. + +### Action handler + +The action handler gets passed a parameter for each command-argument you declared, and two additional parameters +which are the parsed options and the command object itself. + +Example file: [thank.js](./examples/thank.js) + +```js +program + .arguments('') + .option('-t, --title ', 'title to use before name') + .option('-d, --debug', 'display some debugging') + .action((name, options, command) => { + if (options.debug) { + console.error('Called %s with options %o', command.name(), options); + } + const title = options.title ? `${options.title} ` : ''; + console.log(`Thank-you ${title}${name}`); + }); +``` + +You may supply an `async` action handler, in which case you call `.parseAsync` rather than `.parse`. + +```js +async function run() { /* code goes here */ } + +async function main() { + program + .command('run') + .action(run); + await program.parseAsync(process.argv); +} +``` + +A command's options and arguments on the command line are validated when the command is used. Any unknown options or missing arguments will be reported as an error. You can suppress the unknown option checks with `.allowUnknownOption()`. By default it is not an error to +pass more arguments than declared, but you can make this an error with `.allowExcessArguments(false)`. + +### Stand-alone executable (sub)commands + +When `.command()` is invoked with a description argument, this tells Commander that you're going to use stand-alone executables for subcommands. +Commander will search the executables in the directory of the entry script (like `./examples/pm`) with the name `program-subcommand`, like `pm-install`, `pm-search`. +You can specify a custom name with the `executableFile` configuration option. + +You handle the options for an executable (sub)command in the executable, and don't declare them at the top-level. + +Example file: [pm](./examples/pm) + +```js +program + .version('0.1.0') + .command('install [name]', 'install one or more packages') + .command('search [query]', 'search with optional query') + .command('update', 'update installed packages', { executableFile: 'myUpdateSubCommand' }) + .command('list', 'list packages installed', { isDefault: true }); + +program.parse(process.argv); +``` + +If the program is designed to be installed globally, make sure the executables have proper modes, like `755`. + +## Automated help + +The help information is auto-generated based on the information commander already knows about your program. The default +help option is `-h,--help`. + +Example file: [pizza](./examples/pizza) + +```bash +$ node ./examples/pizza --help +Usage: pizza [options] + +An application for pizza ordering + +Options: + -p, --peppers Add peppers + -c, --cheese Add the specified type of cheese (default: "marble") + -C, --no-cheese You do not want any cheese + -h, --help display help for command +``` + +A `help` command is added by default if your command has subcommands. It can be used alone, or with a subcommand name to show +further help for the subcommand. These are effectively the same if the `shell` program has implicit help: + +```bash +shell help +shell --help + +shell help spawn +shell spawn --help +``` + +### Custom help + +You can add extra text to be displayed along with the built-in help. + +Example file: [custom-help](./examples/custom-help) + +```js +program + .option('-f, --foo', 'enable some foo'); + +program.addHelpText('after', ` + +Example call: + $ custom-help --help`); +``` + +Yields the following help output: + +```Text +Usage: custom-help [options] + +Options: + -f, --foo enable some foo + -h, --help display help for command + +Example call: + $ custom-help --help +``` + +The positions in order displayed are: + +- `beforeAll`: add to the program for a global banner or header +- `before`: display extra information before built-in help +- `after`: display extra information after built-in help +- `afterAll`: add to the program for a global footer (epilog) + +The positions "beforeAll" and "afterAll" apply to the command and all its subcommands. + +The second parameter can be a string, or a function returning a string. The function is passed a context object for your convenience. The properties are: + +- error: a boolean for whether the help is being displayed due to a usage error +- command: the Command which is displaying the help + +### Display help from code + +`.help()`: display help information and exit immediately. You can optionally pass `{ error: true }` to display on stderr and exit with an error status. + +`.outputHelp()`: output help information without exiting. You can optionally pass `{ error: true }` to display on stderr. + +`.helpInformation()`: get the built-in command help information as a string for processing or displaying yourself. + +### .usage and .name + +These allow you to customise the usage description in the first line of the help. The name is otherwise +deduced from the (full) program arguments. Given: + +```js +program + .name("my-command") + .usage("[global options] command") +``` + +The help will start with: + +```Text +Usage: my-command [global options] command +``` + +### .helpOption(flags, description) + +By default every command has a help option. Override the default help flags and description. Pass false to disable the built-in help option. + +```js +program + .helpOption('-e, --HELP', 'read more information'); +``` + +### .addHelpCommand() + +A help command is added by default if your command has subcommands. You can explicitly turn on or off the implicit help command with `.addHelpCommand()` and `.addHelpCommand(false)`. + +You can both turn on and customise the help command by supplying the name and description: + +```js +program.addHelpCommand('assist [command]', 'show assistance'); +``` + +### More configuration + +The built-in help is formatted using the Help class. +You can configure the Help behaviour by modifying data properties and methods using `.configureHelp()`, or by subclassing using `.createHelp()` if you prefer. + +The data properties are: + +- `helpWidth`: specify the wrap width, useful for unit tests +- `sortSubcommands`: sort the subcommands alphabetically +- `sortOptions`: sort the options alphabetically + +There are methods getting the visible lists of arguments, options, and subcommands. There are methods for formatting the items in the lists, with each item having a _term_ and _description_. Take a look at `.formatHelp()` to see how they are used. + +Example file: [configure-help.js](./examples/configure-help.js) + +``` +program.configureHelp({ + sortSubcommands: true, + subcommandTerm: (cmd) => cmd.name() // Just show the name, instead of short usage. +}); +``` + +## Custom event listeners + +You can execute custom actions by listening to command and option events. + +```js +program.on('option:verbose', function () { + process.env.VERBOSE = this.opts().verbose; +}); + +program.on('command:*', function (operands) { + console.error(`error: unknown command '${operands[0]}'`); + const availableCommands = program.commands.map(cmd => cmd.name()); + mySuggestBestMatch(operands[0], availableCommands); + process.exitCode = 1; +}); +``` + +## Bits and pieces + +### .parse() and .parseAsync() + +The first argument to `.parse` is the array of strings to parse. You may omit the parameter to implicitly use `process.argv`. + +If the arguments follow different conventions than node you can pass a `from` option in the second parameter: + +- 'node': default, `argv[0]` is the application and `argv[1]` is the script being run, with user parameters after that +- 'electron': `argv[1]` varies depending on whether the electron application is packaged +- 'user': all of the arguments from the user + +For example: + +```js +program.parse(process.argv); // Explicit, node conventions +program.parse(); // Implicit, and auto-detect electron +program.parse(['-f', 'filename'], { from: 'user' }); +``` + +### Parsing Configuration + +If the default parsing does not suit your needs, there are some behaviours to support other usage patterns. + +By default program options are recognised before and after subcommands. To only look for program options before subcommands, use `.enablePositionalOptions()`. This lets you use +an option for a different purpose in subcommands. + +Example file: [positional-options.js](./examples/positional-options.js) + +With positional options, the `-b` is a program option in the first line and a subcommand option in the second line: + +```sh +program -b subcommand +program subcommand -b +``` + +By default options are recognised before and after command-arguments. To only process options that come +before the command-arguments, use `.passThroughOptions()`. This lets you pass the arguments and following options through to another program +without needing to use `--` to end the option processing. +To use pass through options in a subcommand, the program needs to enable positional options. + +Example file: [pass-through-options.js](./examples/pass-through-options.js) + +With pass through options, the `--port=80` is a program option in the first line and passed through as a command-argument in the second line: + +```sh +program --port=80 arg +program arg --port=80 +``` + +By default the option processing shows an error for an unknown option. To have an unknown option treated as an ordinary command-argument and continue looking for options, use `.allowUnknownOption()`. This lets you mix known and unknown options. + +By default the argument processing does not display an error for more command-arguments than expected. +To display an error for excess arguments, use`.allowExcessArguments(false)`. + +### Legacy options as properties + +Before Commander 7, the option values were stored as properties on the command. +This was convenient to code but the downside was possible clashes with +existing properties of `Command`. You can revert to the old behaviour to run unmodified legacy code by using `.storeOptionsAsProperties()`. + +```js +program + .storeOptionsAsProperties() + .option('-d, --debug') + .action((commandAndOptions) => { + if (commandAndOptions.debug) { + console.error(`Called ${commandAndOptions.name()}`); + } + }); +``` + +### TypeScript + +If you use `ts-node` and stand-alone executable subcommands written as `.ts` files, you need to call your program through node to get the subcommands called correctly. e.g. + +```bash +node -r ts-node/register pm.ts +``` + +### createCommand() + +This factory function creates a new command. It is exported and may be used instead of using `new`, like: + +```js +const { createCommand } = require('commander'); +const program = createCommand(); +``` + +`createCommand` is also a method of the Command object, and creates a new command rather than a subcommand. This gets used internally +when creating subcommands using `.command()`, and you may override it to +customise the new subcommand (example file [custom-command-class.js](./examples/custom-command-class.js)). + +### Node options such as `--harmony` + +You can enable `--harmony` option in two ways: + +- Use `#! /usr/bin/env node --harmony` in the subcommands scripts. (Note Windows does not support this pattern.) +- Use the `--harmony` option when call the command, like `node --harmony examples/pm publish`. The `--harmony` option will be preserved when spawning subcommand process. + +### Debugging stand-alone executable subcommands + +An executable subcommand is launched as a separate child process. + +If you are using the node inspector for [debugging](https://nodejs.org/en/docs/guides/debugging-getting-started/) executable subcommands using `node --inspect` et al, +the inspector port is incremented by 1 for the spawned subcommand. + +If you are using VSCode to debug executable subcommands you need to set the `"autoAttachChildProcesses": true` flag in your launch.json configuration. + +### Override exit and output handling + +By default Commander calls `process.exit` when it detects errors, or after displaying the help or version. You can override +this behaviour and optionally supply a callback. The default override throws a `CommanderError`. + +The override callback is passed a `CommanderError` with properties `exitCode` number, `code` string, and `message`. The default override behaviour is to throw the error, except for async handling of executable subcommand completion which carries on. The normal display of error messages or version or help +is not affected by the override which is called after the display. + +```js +program.exitOverride(); + +try { + program.parse(process.argv); +} catch (err) { + // custom processing... +} +``` + +By default Commander is configured for a command-line application and writes to stdout and stderr. +You can modify this behaviour for custom applications. In addition, you can modify the display of error messages. + +Example file: [configure-output.js](./examples/configure-output.js) + + +```js +function errorColor(str) { + // Add ANSI escape codes to display text in red. + return `\x1b[31m${str}\x1b[0m`; +} + +program + .configureOutput({ + // Visibly override write routines as example! + writeOut: (str) => process.stdout.write(`[OUT] ${str}`), + writeErr: (str) => process.stdout.write(`[ERR] ${str}`), + // Highlight errors in color. + outputError: (str, write) => write(errorColor(str)) + }); +``` + +### Additional documentation + +There is more information available about: + +- [deprecated](./docs/deprecated.md) features still supported for backwards compatibility +- [options taking varying arguments](./docs/options-taking-varying-arguments.md) + +## Examples + +In a single command program, you might not need an action handler. + +Example file: [pizza](./examples/pizza) + +```js +const { program } = require('commander'); + +program + .description('An application for pizza ordering') + .option('-p, --peppers', 'Add peppers') + .option('-c, --cheese ', 'Add the specified type of cheese', 'marble') + .option('-C, --no-cheese', 'You do not want any cheese'); + +program.parse(); + +const options = program.opts(); +console.log('you ordered a pizza with:'); +if (options.peppers) console.log(' - peppers'); +const cheese = !options.cheese ? 'no' : options.cheese; +console.log(' - %s cheese', cheese); +``` + +In a multi-command program, you will have action handlers for each command (or stand-alone executables for the commands). + +Example file: [deploy](./examples/deploy) + +```js +const { Command } = require('commander'); +const program = new Command(); + +program + .version('0.0.1') + .option('-c, --config ', 'set config path', './deploy.conf'); + +program + .command('setup [env]') + .description('run setup commands for all envs') + .option('-s, --setup_mode ', 'Which setup mode to use', 'normal') + .action((env, options) => { + env = env || 'all'; + console.log('read config from %s', program.opts().config); + console.log('setup for %s env(s) with %s mode', env, options.setup_mode); + }); + +program + .command('exec +``` + +For legacy environments, you can load d3-ease’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +[Try d3-ease in your browser.](https://observablehq.com/@d3/easing-animations) + +## API Reference + +# ease(t) + +Given the specified normalized time *t*, typically in the range [0,1], returns the “eased” time *tʹ*, also typically in [0,1]. 0 represents the start of the animation and 1 represents the end. A good implementation returns 0 if *t* = 0 and 1 if *t* = 1. See the [easing explorer](https://observablehq.com/@d3/easing) for a visual demonstration. For example, to apply [cubic](#easeCubic) easing: + +```js +const te = d3.easeCubic(t); +``` + +Similarly, to apply custom [elastic](#easeElastic) easing: + +```js +// Before the animation starts, create your easing function. +const customElastic = d3.easeElastic.period(0.4); + +// During the animation, apply the easing function. +const te = customElastic(t); +``` + +# d3.easeLinear(t) [<>](https://github.com/d3/d3-ease/blob/master/src/linear.js "Source") + +Linear easing; the identity function; *linear*(*t*) returns *t*. + +[linear](https://observablehq.com/@d3/easing#linear) + +# d3.easePolyIn(t) [<>](https://github.com/d3/d3-ease/blob/master/src/poly.js#L3 "Source") + +Polynomial easing; raises *t* to the specified [exponent](#poly_exponent). If the exponent is not specified, it defaults to 3, equivalent to [cubicIn](#easeCubicIn). + +[polyIn](https://observablehq.com/@d3/easing#polyIn) + +# d3.easePolyOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/poly.js#L15 "Source") + +Reverse polynomial easing; equivalent to 1 - [polyIn](#easePolyIn)(1 - *t*). If the [exponent](#poly_exponent) is not specified, it defaults to 3, equivalent to [cubicOut](#easeCubicOut). + +[polyOut](https://observablehq.com/@d3/easing#polyOut) + +# d3.easePoly(t) [<>](https://github.com/d3/d3-ease/blob/master/src/poly.js "Source") +
    # d3.easePolyInOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/poly.js#L27 "Source") + +Symmetric polynomial easing; scales [polyIn](#easePolyIn) for *t* in [0, 0.5] and [polyOut](#easePolyOut) for *t* in [0.5, 1]. If the [exponent](#poly_exponent) is not specified, it defaults to 3, equivalent to [cubic](#easeCubic). + +[polyInOut](https://observablehq.com/@d3/easing#polyInOut) + +# poly.exponent(e) [<>](https://github.com/d3/d3-ease/blob/master/src/poly.js#L1 "Source") + +Returns a new polynomial easing with the specified exponent *e*. For example, to create equivalents of [linear](#easeLinear), [quad](#easeQuad), and [cubic](#easeCubic): + +```js +const linear = d3.easePoly.exponent(1); +const quad = d3.easePoly.exponent(2); +const cubic = d3.easePoly.exponent(3); +``` + +# d3.easeQuadIn(t) [<>](https://github.com/d3/d3-ease/blob/master/src/quad.js#L1 "Source") + +Quadratic easing; equivalent to [polyIn](#easePolyIn).[exponent](#poly_exponent)(2). + +[quadIn](https://observablehq.com/@d3/easing#quadIn) + +# d3.easeQuadOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/quad.js#L5 "Source") + +Reverse quadratic easing; equivalent to 1 - [quadIn](#easeQuadIn)(1 - *t*). Also equivalent to [polyOut](#easePolyOut).[exponent](#poly_exponent)(2). + +[quadOut](https://observablehq.com/@d3/easing#quadOut) + +# d3.easeQuad(t) [<>](https://github.com/d3/d3-ease/blob/master/src/quad.js "Source") +
    # d3.easeQuadInOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/quad.js#L9 "Source") + +Symmetric quadratic easing; scales [quadIn](#easeQuadIn) for *t* in [0, 0.5] and [quadOut](#easeQuadOut) for *t* in [0.5, 1]. Also equivalent to [poly](#easePoly).[exponent](#poly_exponent)(2). + +[quadInOut](https://observablehq.com/@d3/easing#quadInOut) + +# d3.easeCubicIn(t) [<>](https://github.com/d3/d3-ease/blob/master/src/cubic.js#L1 "Source") + +Cubic easing; equivalent to [polyIn](#easePolyIn).[exponent](#poly_exponent)(3). + +[cubicIn](https://observablehq.com/@d3/easing#cubicIn) + +# d3.easeCubicOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/cubic.js#L5 "Source") + +Reverse cubic easing; equivalent to 1 - [cubicIn](#easeCubicIn)(1 - *t*). Also equivalent to [polyOut](#easePolyOut).[exponent](#poly_exponent)(3). + +[cubicOut](https://observablehq.com/@d3/easing#cubicOut) + +# d3.easeCubic(t) [<>](https://github.com/d3/d3-ease/blob/master/src/cubic.js "Source") +
    # d3.easeCubicInOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/cubic.js#L9 "Source") + +Symmetric cubic easing; scales [cubicIn](#easeCubicIn) for *t* in [0, 0.5] and [cubicOut](#easeCubicOut) for *t* in [0.5, 1]. Also equivalent to [poly](#easePoly).[exponent](#poly_exponent)(3). + +[cubicInOut](https://observablehq.com/@d3/easing#cubicInOut) + +# d3.easeSinIn(t) [<>](https://github.com/d3/d3-ease/blob/master/src/sin.js#L4 "Source") + +Sinusoidal easing; returns sin(*t*). + +[sinIn](https://observablehq.com/@d3/easing#sinIn) + +# d3.easeSinOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/sin.js#L8 "Source") + +Reverse sinusoidal easing; equivalent to 1 - [sinIn](#easeSinIn)(1 - *t*). + +[sinOut](https://observablehq.com/@d3/easing#sinOut) + +# d3.easeSin(t) [<>](https://github.com/d3/d3-ease/blob/master/src/sin.js "Source") +
    # d3.easeSinInOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/sin.js#L12 "Source") + +Symmetric sinusoidal easing; scales [sinIn](#easeSinIn) for *t* in [0, 0.5] and [sinOut](#easeSinOut) for *t* in [0.5, 1]. + +[sinInOut](https://observablehq.com/@d3/easing#sinInOut) + +# d3.easeExpIn(t) [<>](https://github.com/d3/d3-ease/blob/master/src/exp.js#L1 "Source") + +Exponential easing; raises 2 to the exponent 10 \* (*t* - 1). + +[expIn](https://observablehq.com/@d3/easing#expIn) + +# d3.easeExpOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/exp.js#L5 "Source") + +Reverse exponential easing; equivalent to 1 - [expIn](#easeExpIn)(1 - *t*). + +[expOut](https://observablehq.com/@d3/easing#expOut) + +# d3.easeExp(t) [<>](https://github.com/d3/d3-ease/blob/master/src/exp.js "Source") +
    # d3.easeExpInOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/exp.js#L9 "Source") + +Symmetric exponential easing; scales [expIn](#easeExpIn) for *t* in [0, 0.5] and [expOut](#easeExpOut) for *t* in [0.5, 1]. + +[expInOut](https://observablehq.com/@d3/easing#expInOut) + +# d3.easeCircleIn(t) [<>](https://github.com/d3/d3-ease/blob/master/src/circle.js#L1 "Source") + +Circular easing. + +[circleIn](https://observablehq.com/@d3/easing#circleIn) + +# d3.easeCircleOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/circle.js#L5 "Source") + +Reverse circular easing; equivalent to 1 - [circleIn](#easeCircleIn)(1 - *t*). + +[circleOut](https://observablehq.com/@d3/easing#circleOut) + +# d3.easeCircle(t) [<>](https://github.com/d3/d3-ease/blob/master/src/circle.js "Source") +
    # d3.easeCircleInOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/circle.js#L9 "Source") + +Symmetric circular easing; scales [circleIn](#easeCircleIn) for *t* in [0, 0.5] and [circleOut](#easeCircleOut) for *t* in [0.5, 1]. + +[circleInOut](https://observablehq.com/@d3/easing#circleInOut) + +# d3.easeElasticIn(t) [<>](https://github.com/d3/d3-ease/blob/master/src/elastic.js#L5 "Source") + +Elastic easing, like a rubber band. The [amplitude](#elastic_amplitude) and [period](#elastic_period) of the oscillation are configurable; if not specified, they default to 1 and 0.3, respectively. + +[elasticIn](https://observablehq.com/@d3/easing#elasticIn) + +# d3.easeElastic(t) [<>](https://github.com/d3/d3-ease/blob/master/src/elastic.js "Source") +
    # d3.easeElasticOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/elastic.js#L18 "Source") + +Reverse elastic easing; equivalent to 1 - [elasticIn](#easeElasticIn)(1 - *t*). + +[elasticOut](https://observablehq.com/@d3/easing#elasticOut) + +# d3.easeElasticInOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/elastic.js#L31 "Source") + +Symmetric elastic easing; scales [elasticIn](#easeElasticIn) for *t* in [0, 0.5] and [elasticOut](#easeElasticOut) for *t* in [0.5, 1]. + +[elasticInOut](https://observablehq.com/@d3/easing#elasticInOut) + +# elastic.amplitude(a) [<>](https://github.com/d3/d3-ease/blob/master/src/elastic.js#L40 "Source") + +Returns a new elastic easing with the specified amplitude *a*. + +# elastic.period(p) [<>](https://github.com/d3/d3-ease/blob/master/src/elastic.js#L41 "Source") + +Returns a new elastic easing with the specified period *p*. + +# d3.easeBackIn(t) [<>](https://github.com/d3/d3-ease/blob/master/src/back.js#L3 "Source") + +[Anticipatory](https://en.wikipedia.org/wiki/12_basic_principles_of_animation#Anticipation) easing, like a dancer bending his knees before jumping off the floor. The degree of [overshoot](#back_overshoot) is configurable; if not specified, it defaults to 1.70158. + +[backIn](https://observablehq.com/@d3/easing#backIn) + +# d3.easeBackOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/back.js#L15 "Source") + +Reverse anticipatory easing; equivalent to 1 - [backIn](#easeBackIn)(1 - *t*). + +[backOut](https://observablehq.com/@d3/easing#backOut) + +# d3.easeBack(t) [<>](https://github.com/d3/d3-ease/blob/master/src/back.js "Source") +
    # d3.easeBackInOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/back.js#L27 "Source") + +Symmetric anticipatory easing; scales [backIn](#easeBackIn) for *t* in [0, 0.5] and [backOut](#easeBackOut) for *t* in [0.5, 1]. + +[backInOut](https://observablehq.com/@d3/easing#backInOut) + +# back.overshoot(s) [<>](https://github.com/d3/d3-ease/blob/master/src/back.js#L1 "Source") + +Returns a new back easing with the specified overshoot *s*. + +# d3.easeBounceIn(t) [<>](https://github.com/d3/d3-ease/blob/master/src/bounce.js#L12 "Source") + +Bounce easing, like a rubber ball. + +[bounceIn](https://observablehq.com/@d3/easing#bounceIn) + +# d3.easeBounce(t) [<>](https://github.com/d3/d3-ease/blob/master/src/bounce.js "Source") +
    # d3.easeBounceOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/bounce.js#L16 "Source") + +Reverse bounce easing; equivalent to 1 - [bounceIn](#easeBounceIn)(1 - *t*). + +[bounceOut](https://observablehq.com/@d3/easing#bounceOut) + +# d3.easeBounceInOut(t) [<>](https://github.com/d3/d3-ease/blob/master/src/bounce.js#L20 "Source") + +Symmetric bounce easing; scales [bounceIn](#easeBounceIn) for *t* in [0, 0.5] and [bounceOut](#easeBounceOut) for *t* in [0.5, 1]. + +[bounceInOut](https://observablehq.com/@d3/easing#bounceInOut) diff --git a/frontend/node_modules/d3-ease/dist/d3-ease.js b/frontend/node_modules/d3-ease/dist/d3-ease.js new file mode 100644 index 0000000..8e5e545 --- /dev/null +++ b/frontend/node_modules/d3-ease/dist/d3-ease.js @@ -0,0 +1,262 @@ +// https://d3js.org/d3-ease/ v3.0.1 Copyright 2010-2021 Mike Bostock, 2001 Robert Penner +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +}(this, (function (exports) { 'use strict'; + +const linear = t => +t; + +function quadIn(t) { + return t * t; +} + +function quadOut(t) { + return t * (2 - t); +} + +function quadInOut(t) { + return ((t *= 2) <= 1 ? t * t : --t * (2 - t) + 1) / 2; +} + +function cubicIn(t) { + return t * t * t; +} + +function cubicOut(t) { + return --t * t * t + 1; +} + +function cubicInOut(t) { + return ((t *= 2) <= 1 ? t * t * t : (t -= 2) * t * t + 2) / 2; +} + +var exponent = 3; + +var polyIn = (function custom(e) { + e = +e; + + function polyIn(t) { + return Math.pow(t, e); + } + + polyIn.exponent = custom; + + return polyIn; +})(exponent); + +var polyOut = (function custom(e) { + e = +e; + + function polyOut(t) { + return 1 - Math.pow(1 - t, e); + } + + polyOut.exponent = custom; + + return polyOut; +})(exponent); + +var polyInOut = (function custom(e) { + e = +e; + + function polyInOut(t) { + return ((t *= 2) <= 1 ? Math.pow(t, e) : 2 - Math.pow(2 - t, e)) / 2; + } + + polyInOut.exponent = custom; + + return polyInOut; +})(exponent); + +var pi = Math.PI, + halfPi = pi / 2; + +function sinIn(t) { + return (+t === 1) ? 1 : 1 - Math.cos(t * halfPi); +} + +function sinOut(t) { + return Math.sin(t * halfPi); +} + +function sinInOut(t) { + return (1 - Math.cos(pi * t)) / 2; +} + +// tpmt is two power minus ten times t scaled to [0,1] +function tpmt(x) { + return (Math.pow(2, -10 * x) - 0.0009765625) * 1.0009775171065494; +} + +function expIn(t) { + return tpmt(1 - +t); +} + +function expOut(t) { + return 1 - tpmt(t); +} + +function expInOut(t) { + return ((t *= 2) <= 1 ? tpmt(1 - t) : 2 - tpmt(t - 1)) / 2; +} + +function circleIn(t) { + return 1 - Math.sqrt(1 - t * t); +} + +function circleOut(t) { + return Math.sqrt(1 - --t * t); +} + +function circleInOut(t) { + return ((t *= 2) <= 1 ? 1 - Math.sqrt(1 - t * t) : Math.sqrt(1 - (t -= 2) * t) + 1) / 2; +} + +var b1 = 4 / 11, + b2 = 6 / 11, + b3 = 8 / 11, + b4 = 3 / 4, + b5 = 9 / 11, + b6 = 10 / 11, + b7 = 15 / 16, + b8 = 21 / 22, + b9 = 63 / 64, + b0 = 1 / b1 / b1; + +function bounceIn(t) { + return 1 - bounceOut(1 - t); +} + +function bounceOut(t) { + return (t = +t) < b1 ? b0 * t * t : t < b3 ? b0 * (t -= b2) * t + b4 : t < b6 ? b0 * (t -= b5) * t + b7 : b0 * (t -= b8) * t + b9; +} + +function bounceInOut(t) { + return ((t *= 2) <= 1 ? 1 - bounceOut(1 - t) : bounceOut(t - 1) + 1) / 2; +} + +var overshoot = 1.70158; + +var backIn = (function custom(s) { + s = +s; + + function backIn(t) { + return (t = +t) * t * (s * (t - 1) + t); + } + + backIn.overshoot = custom; + + return backIn; +})(overshoot); + +var backOut = (function custom(s) { + s = +s; + + function backOut(t) { + return --t * t * ((t + 1) * s + t) + 1; + } + + backOut.overshoot = custom; + + return backOut; +})(overshoot); + +var backInOut = (function custom(s) { + s = +s; + + function backInOut(t) { + return ((t *= 2) < 1 ? t * t * ((s + 1) * t - s) : (t -= 2) * t * ((s + 1) * t + s) + 2) / 2; + } + + backInOut.overshoot = custom; + + return backInOut; +})(overshoot); + +var tau = 2 * Math.PI, + amplitude = 1, + period = 0.3; + +var elasticIn = (function custom(a, p) { + var s = Math.asin(1 / (a = Math.max(1, a))) * (p /= tau); + + function elasticIn(t) { + return a * tpmt(-(--t)) * Math.sin((s - t) / p); + } + + elasticIn.amplitude = function(a) { return custom(a, p * tau); }; + elasticIn.period = function(p) { return custom(a, p); }; + + return elasticIn; +})(amplitude, period); + +var elasticOut = (function custom(a, p) { + var s = Math.asin(1 / (a = Math.max(1, a))) * (p /= tau); + + function elasticOut(t) { + return 1 - a * tpmt(t = +t) * Math.sin((t + s) / p); + } + + elasticOut.amplitude = function(a) { return custom(a, p * tau); }; + elasticOut.period = function(p) { return custom(a, p); }; + + return elasticOut; +})(amplitude, period); + +var elasticInOut = (function custom(a, p) { + var s = Math.asin(1 / (a = Math.max(1, a))) * (p /= tau); + + function elasticInOut(t) { + return ((t = t * 2 - 1) < 0 + ? a * tpmt(-t) * Math.sin((s - t) / p) + : 2 - a * tpmt(t) * Math.sin((s + t) / p)) / 2; + } + + elasticInOut.amplitude = function(a) { return custom(a, p * tau); }; + elasticInOut.period = function(p) { return custom(a, p); }; + + return elasticInOut; +})(amplitude, period); + +exports.easeBack = backInOut; +exports.easeBackIn = backIn; +exports.easeBackInOut = backInOut; +exports.easeBackOut = backOut; +exports.easeBounce = bounceOut; +exports.easeBounceIn = bounceIn; +exports.easeBounceInOut = bounceInOut; +exports.easeBounceOut = bounceOut; +exports.easeCircle = circleInOut; +exports.easeCircleIn = circleIn; +exports.easeCircleInOut = circleInOut; +exports.easeCircleOut = circleOut; +exports.easeCubic = cubicInOut; +exports.easeCubicIn = cubicIn; +exports.easeCubicInOut = cubicInOut; +exports.easeCubicOut = cubicOut; +exports.easeElastic = elasticOut; +exports.easeElasticIn = elasticIn; +exports.easeElasticInOut = elasticInOut; +exports.easeElasticOut = elasticOut; +exports.easeExp = expInOut; +exports.easeExpIn = expIn; +exports.easeExpInOut = expInOut; +exports.easeExpOut = expOut; +exports.easeLinear = linear; +exports.easePoly = polyInOut; +exports.easePolyIn = polyIn; +exports.easePolyInOut = polyInOut; +exports.easePolyOut = polyOut; +exports.easeQuad = quadInOut; +exports.easeQuadIn = quadIn; +exports.easeQuadInOut = quadInOut; +exports.easeQuadOut = quadOut; +exports.easeSin = sinInOut; +exports.easeSinIn = sinIn; +exports.easeSinInOut = sinInOut; +exports.easeSinOut = sinOut; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-ease/dist/d3-ease.min.js b/frontend/node_modules/d3-ease/dist/d3-ease.min.js new file mode 100644 index 0000000..f34b0dd --- /dev/null +++ b/frontend/node_modules/d3-ease/dist/d3-ease.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-ease/ v3.0.1 Copyright 2010-2021 Mike Bostock, 2001 Robert Penner +!function(n,e){"object"==typeof exports&&"undefined"!=typeof module?e(exports):"function"==typeof define&&define.amd?define(["exports"],e):e((n="undefined"!=typeof globalThis?globalThis:n||self).d3=n.d3||{})}(this,(function(n){"use strict";function e(n){return((n*=2)<=1?n*n:--n*(2-n)+1)/2}function t(n){return((n*=2)<=1?n*n*n:(n-=2)*n*n+2)/2}var u=function n(e){function t(n){return Math.pow(n,e)}return e=+e,t.exponent=n,t}(3),r=function n(e){function t(n){return 1-Math.pow(1-n,e)}return e=+e,t.exponent=n,t}(3),a=function n(e){function t(n){return((n*=2)<=1?Math.pow(n,e):2-Math.pow(2-n,e))/2}return e=+e,t.exponent=n,t}(3),o=Math.PI,i=o/2;function c(n){return(1-Math.cos(o*n))/2}function s(n){return 1.0009775171065494*(Math.pow(2,-10*n)-.0009765625)}function f(n){return((n*=2)<=1?s(1-n):2-s(n-1))/2}function h(n){return((n*=2)<=1?1-Math.sqrt(1-n*n):Math.sqrt(1-(n-=2)*n)+1)/2}var p=4/11,M=7.5625;function d(n){return(n=+n)+n,n.easePoly=a,n.easePolyIn=u,n.easePolyInOut=a,n.easePolyOut=r,n.easeQuad=e,n.easeQuadIn=function(n){return n*n},n.easeQuadInOut=e,n.easeQuadOut=function(n){return n*(2-n)},n.easeSin=c,n.easeSinIn=function(n){return 1==+n?1:1-Math.cos(n*i)},n.easeSinInOut=c,n.easeSinOut=function(n){return Math.sin(n*i)},Object.defineProperty(n,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-ease/package.json b/frontend/node_modules/d3-ease/package.json new file mode 100644 index 0000000..2ff544c --- /dev/null +++ b/frontend/node_modules/d3-ease/package.json @@ -0,0 +1,51 @@ +{ + "name": "d3-ease", + "version": "3.0.1", + "description": "Easing functions for smooth animation.", + "homepage": "https://d3js.org/d3-ease/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-ease.git" + }, + "keywords": [ + "d3", + "d3-module", + "ease", + "easing", + "animation", + "transition" + ], + "license": "BSD-3-Clause", + "author": { + "name": "Mike Bostock", + "url": "http://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-ease.min.js", + "unpkg": "dist/d3-ease.min.js", + "exports": { + "umd": "./dist/d3-ease.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "devDependencies": { + "eslint": "7", + "mocha": "8", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-ease/src/back.js b/frontend/node_modules/d3-ease/src/back.js new file mode 100644 index 0000000..b9c1bcc --- /dev/null +++ b/frontend/node_modules/d3-ease/src/back.js @@ -0,0 +1,37 @@ +var overshoot = 1.70158; + +export var backIn = (function custom(s) { + s = +s; + + function backIn(t) { + return (t = +t) * t * (s * (t - 1) + t); + } + + backIn.overshoot = custom; + + return backIn; +})(overshoot); + +export var backOut = (function custom(s) { + s = +s; + + function backOut(t) { + return --t * t * ((t + 1) * s + t) + 1; + } + + backOut.overshoot = custom; + + return backOut; +})(overshoot); + +export var backInOut = (function custom(s) { + s = +s; + + function backInOut(t) { + return ((t *= 2) < 1 ? t * t * ((s + 1) * t - s) : (t -= 2) * t * ((s + 1) * t + s) + 2) / 2; + } + + backInOut.overshoot = custom; + + return backInOut; +})(overshoot); diff --git a/frontend/node_modules/d3-ease/src/bounce.js b/frontend/node_modules/d3-ease/src/bounce.js new file mode 100644 index 0000000..d2d81ca --- /dev/null +++ b/frontend/node_modules/d3-ease/src/bounce.js @@ -0,0 +1,22 @@ +var b1 = 4 / 11, + b2 = 6 / 11, + b3 = 8 / 11, + b4 = 3 / 4, + b5 = 9 / 11, + b6 = 10 / 11, + b7 = 15 / 16, + b8 = 21 / 22, + b9 = 63 / 64, + b0 = 1 / b1 / b1; + +export function bounceIn(t) { + return 1 - bounceOut(1 - t); +} + +export function bounceOut(t) { + return (t = +t) < b1 ? b0 * t * t : t < b3 ? b0 * (t -= b2) * t + b4 : t < b6 ? b0 * (t -= b5) * t + b7 : b0 * (t -= b8) * t + b9; +} + +export function bounceInOut(t) { + return ((t *= 2) <= 1 ? 1 - bounceOut(1 - t) : bounceOut(t - 1) + 1) / 2; +} diff --git a/frontend/node_modules/d3-ease/src/circle.js b/frontend/node_modules/d3-ease/src/circle.js new file mode 100644 index 0000000..8b9bb1d --- /dev/null +++ b/frontend/node_modules/d3-ease/src/circle.js @@ -0,0 +1,11 @@ +export function circleIn(t) { + return 1 - Math.sqrt(1 - t * t); +} + +export function circleOut(t) { + return Math.sqrt(1 - --t * t); +} + +export function circleInOut(t) { + return ((t *= 2) <= 1 ? 1 - Math.sqrt(1 - t * t) : Math.sqrt(1 - (t -= 2) * t) + 1) / 2; +} diff --git a/frontend/node_modules/d3-ease/src/cubic.js b/frontend/node_modules/d3-ease/src/cubic.js new file mode 100644 index 0000000..bad3a7c --- /dev/null +++ b/frontend/node_modules/d3-ease/src/cubic.js @@ -0,0 +1,11 @@ +export function cubicIn(t) { + return t * t * t; +} + +export function cubicOut(t) { + return --t * t * t + 1; +} + +export function cubicInOut(t) { + return ((t *= 2) <= 1 ? t * t * t : (t -= 2) * t * t + 2) / 2; +} diff --git a/frontend/node_modules/d3-ease/src/elastic.js b/frontend/node_modules/d3-ease/src/elastic.js new file mode 100644 index 0000000..48ca673 --- /dev/null +++ b/frontend/node_modules/d3-ease/src/elastic.js @@ -0,0 +1,46 @@ +import {tpmt} from "./math.js"; + +var tau = 2 * Math.PI, + amplitude = 1, + period = 0.3; + +export var elasticIn = (function custom(a, p) { + var s = Math.asin(1 / (a = Math.max(1, a))) * (p /= tau); + + function elasticIn(t) { + return a * tpmt(-(--t)) * Math.sin((s - t) / p); + } + + elasticIn.amplitude = function(a) { return custom(a, p * tau); }; + elasticIn.period = function(p) { return custom(a, p); }; + + return elasticIn; +})(amplitude, period); + +export var elasticOut = (function custom(a, p) { + var s = Math.asin(1 / (a = Math.max(1, a))) * (p /= tau); + + function elasticOut(t) { + return 1 - a * tpmt(t = +t) * Math.sin((t + s) / p); + } + + elasticOut.amplitude = function(a) { return custom(a, p * tau); }; + elasticOut.period = function(p) { return custom(a, p); }; + + return elasticOut; +})(amplitude, period); + +export var elasticInOut = (function custom(a, p) { + var s = Math.asin(1 / (a = Math.max(1, a))) * (p /= tau); + + function elasticInOut(t) { + return ((t = t * 2 - 1) < 0 + ? a * tpmt(-t) * Math.sin((s - t) / p) + : 2 - a * tpmt(t) * Math.sin((s + t) / p)) / 2; + } + + elasticInOut.amplitude = function(a) { return custom(a, p * tau); }; + elasticInOut.period = function(p) { return custom(a, p); }; + + return elasticInOut; +})(amplitude, period); diff --git a/frontend/node_modules/d3-ease/src/exp.js b/frontend/node_modules/d3-ease/src/exp.js new file mode 100644 index 0000000..f3c1cf0 --- /dev/null +++ b/frontend/node_modules/d3-ease/src/exp.js @@ -0,0 +1,13 @@ +import {tpmt} from "./math.js"; + +export function expIn(t) { + return tpmt(1 - +t); +} + +export function expOut(t) { + return 1 - tpmt(t); +} + +export function expInOut(t) { + return ((t *= 2) <= 1 ? tpmt(1 - t) : 2 - tpmt(t - 1)) / 2; +} diff --git a/frontend/node_modules/d3-ease/src/index.js b/frontend/node_modules/d3-ease/src/index.js new file mode 100644 index 0000000..710d3df --- /dev/null +++ b/frontend/node_modules/d3-ease/src/index.js @@ -0,0 +1,66 @@ +export { + linear as easeLinear +} from "./linear.js"; + +export { + quadInOut as easeQuad, + quadIn as easeQuadIn, + quadOut as easeQuadOut, + quadInOut as easeQuadInOut +} from "./quad.js"; + +export { + cubicInOut as easeCubic, + cubicIn as easeCubicIn, + cubicOut as easeCubicOut, + cubicInOut as easeCubicInOut +} from "./cubic.js"; + +export { + polyInOut as easePoly, + polyIn as easePolyIn, + polyOut as easePolyOut, + polyInOut as easePolyInOut +} from "./poly.js"; + +export { + sinInOut as easeSin, + sinIn as easeSinIn, + sinOut as easeSinOut, + sinInOut as easeSinInOut +} from "./sin.js"; + +export { + expInOut as easeExp, + expIn as easeExpIn, + expOut as easeExpOut, + expInOut as easeExpInOut +} from "./exp.js"; + +export { + circleInOut as easeCircle, + circleIn as easeCircleIn, + circleOut as easeCircleOut, + circleInOut as easeCircleInOut +} from "./circle.js"; + +export { + bounceOut as easeBounce, + bounceIn as easeBounceIn, + bounceOut as easeBounceOut, + bounceInOut as easeBounceInOut +} from "./bounce.js"; + +export { + backInOut as easeBack, + backIn as easeBackIn, + backOut as easeBackOut, + backInOut as easeBackInOut +} from "./back.js"; + +export { + elasticOut as easeElastic, + elasticIn as easeElasticIn, + elasticOut as easeElasticOut, + elasticInOut as easeElasticInOut +} from "./elastic.js"; diff --git a/frontend/node_modules/d3-ease/src/linear.js b/frontend/node_modules/d3-ease/src/linear.js new file mode 100644 index 0000000..7b7d2c1 --- /dev/null +++ b/frontend/node_modules/d3-ease/src/linear.js @@ -0,0 +1 @@ +export const linear = t => +t; diff --git a/frontend/node_modules/d3-ease/src/math.js b/frontend/node_modules/d3-ease/src/math.js new file mode 100644 index 0000000..d342db1 --- /dev/null +++ b/frontend/node_modules/d3-ease/src/math.js @@ -0,0 +1,4 @@ +// tpmt is two power minus ten times t scaled to [0,1] +export function tpmt(x) { + return (Math.pow(2, -10 * x) - 0.0009765625) * 1.0009775171065494; +} diff --git a/frontend/node_modules/d3-ease/src/poly.js b/frontend/node_modules/d3-ease/src/poly.js new file mode 100644 index 0000000..827cf87 --- /dev/null +++ b/frontend/node_modules/d3-ease/src/poly.js @@ -0,0 +1,37 @@ +var exponent = 3; + +export var polyIn = (function custom(e) { + e = +e; + + function polyIn(t) { + return Math.pow(t, e); + } + + polyIn.exponent = custom; + + return polyIn; +})(exponent); + +export var polyOut = (function custom(e) { + e = +e; + + function polyOut(t) { + return 1 - Math.pow(1 - t, e); + } + + polyOut.exponent = custom; + + return polyOut; +})(exponent); + +export var polyInOut = (function custom(e) { + e = +e; + + function polyInOut(t) { + return ((t *= 2) <= 1 ? Math.pow(t, e) : 2 - Math.pow(2 - t, e)) / 2; + } + + polyInOut.exponent = custom; + + return polyInOut; +})(exponent); diff --git a/frontend/node_modules/d3-ease/src/quad.js b/frontend/node_modules/d3-ease/src/quad.js new file mode 100644 index 0000000..df65bc2 --- /dev/null +++ b/frontend/node_modules/d3-ease/src/quad.js @@ -0,0 +1,11 @@ +export function quadIn(t) { + return t * t; +} + +export function quadOut(t) { + return t * (2 - t); +} + +export function quadInOut(t) { + return ((t *= 2) <= 1 ? t * t : --t * (2 - t) + 1) / 2; +} diff --git a/frontend/node_modules/d3-ease/src/sin.js b/frontend/node_modules/d3-ease/src/sin.js new file mode 100644 index 0000000..d8e09b8 --- /dev/null +++ b/frontend/node_modules/d3-ease/src/sin.js @@ -0,0 +1,14 @@ +var pi = Math.PI, + halfPi = pi / 2; + +export function sinIn(t) { + return (+t === 1) ? 1 : 1 - Math.cos(t * halfPi); +} + +export function sinOut(t) { + return Math.sin(t * halfPi); +} + +export function sinInOut(t) { + return (1 - Math.cos(pi * t)) / 2; +} diff --git a/frontend/node_modules/d3-fetch/LICENSE b/frontend/node_modules/d3-fetch/LICENSE new file mode 100644 index 0000000..ff79401 --- /dev/null +++ b/frontend/node_modules/d3-fetch/LICENSE @@ -0,0 +1,13 @@ +Copyright 2016-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-fetch/README.md b/frontend/node_modules/d3-fetch/README.md new file mode 100644 index 0000000..a9451a1 --- /dev/null +++ b/frontend/node_modules/d3-fetch/README.md @@ -0,0 +1,111 @@ +# d3-fetch + +This module provides convenient parsing on top of [Fetch](https://fetch.spec.whatwg.org/). For example, to load a text file: + +```js +const text = await d3.text("/path/to/file.txt"); +console.log(text); // Hello, world! +``` + +To load and parse a CSV file: + +```js +const data = await d3.csv("/path/to/file.csv"); +console.log(data); // [{"Hello": "world"}, …] +``` + +This module has built-in support for parsing [JSON](#json), [CSV](#csv), and [TSV](#tsv). You can parse additional formats by using [text](#text) directly. (This module replaced [d3-request](https://github.com/d3/d3-request).) + +## Installing + +If you use npm, `npm install d3-fetch`. You can also download the [latest release on GitHub](https://github.com/d3/d3-fetch/releases/latest). For vanilla HTML in modern browsers, import d3-fetch from Skypack: + +```html + +``` + +For legacy environments, you can load d3-fetch’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +## API Reference + +# d3.blob(input[, init]) · [Source](https://github.com/d3/d3-fetch/blob/master/src/blob.js "Source") + +Fetches the binary file at the specified *input* URL as a Blob. If *init* is specified, it is passed along to the underlying call to [fetch](https://fetch.spec.whatwg.org/#fetch-method); see [RequestInit](https://fetch.spec.whatwg.org/#requestinit) for allowed fields. + +# d3.buffer(input[, init]) · [Source](https://github.com/d3/d3-fetch/blob/master/src/buffer.js "Source") + +Fetches the binary file at the specified *input* URL as an ArrayBuffer. If *init* is specified, it is passed along to the underlying call to [fetch](https://fetch.spec.whatwg.org/#fetch-method); see [RequestInit](https://fetch.spec.whatwg.org/#requestinit) for allowed fields. + +# d3.csv(input[, init][, row]) · [Source](https://github.com/d3/d3-fetch/blob/master/src/dsv.js "Source") + +Equivalent to [d3.dsv](#dsv) with the comma character as the delimiter. + +# d3.dsv(delimiter, input[, init][, row]) · [Source](https://github.com/d3/d3-fetch/blob/master/src/dsv.js "Source") + +Fetches the [DSV](https://github.com/d3/d3-dsv) file at the specified *input* URL. If *init* is specified, it is passed along to the underlying call to [fetch](https://fetch.spec.whatwg.org/#fetch-method); see [RequestInit](https://fetch.spec.whatwg.org/#requestinit) for allowed fields. An optional *row* conversion function may be specified to map and filter row objects to a more-specific representation; see [*dsv*.parse](https://github.com/d3/d3-dsv#dsv_parse) for details. For example: + +```js +const data = await d3.dsv(",", "test.csv", (d) => { + return { + year: new Date(+d.Year, 0, 1), // convert "Year" column to Date + make: d.Make, + model: d.Model, + length: +d.Length // convert "Length" column to number + }; +}); +``` + +If only one of *init* and *row* is specified, it is interpreted as the *row* conversion function if it is a function, and otherwise an *init* object. + +See also [d3.csv](#csv) and [d3.tsv](#tsv). + +# d3.html(input[, init]) · [Source](https://github.com/d3/d3-fetch/blob/master/src/xml.js "Source") + +Fetches the file at the specified *input* URL as [text](#text) and then [parses it](https://developer.mozilla.org/docs/Web/API/DOMParser) as HTML. If *init* is specified, it is passed along to the underlying call to [fetch](https://fetch.spec.whatwg.org/#fetch-method); see [RequestInit](https://fetch.spec.whatwg.org/#requestinit) for allowed fields. + +# d3.image(input[, init]) · [Source](https://github.com/d3/d3-fetch/blob/master/src/image.js "Source") + +Fetches the image at the specified *input* URL. If *init* is specified, sets any additional properties on the image before loading. For example, to enable an anonymous [cross-origin request](https://developer.mozilla.org/en-US/docs/Web/HTML/CORS_enabled_image): + +```js +const img = await d3.image("https://example.com/test.png", {crossOrigin: "anonymous"}); +``` + +# d3.json(input[, init]) · [Source](https://github.com/d3/d3-fetch/blob/master/src/json.js "Source") + +Fetches the [JSON](http://json.org) file at the specified *input* URL. If *init* is specified, it is passed along to the underlying call to [fetch](https://fetch.spec.whatwg.org/#fetch-method); see [RequestInit](https://fetch.spec.whatwg.org/#requestinit) for allowed fields. If the server returns a status code of [204 No Content](https://developer.mozilla.org/docs/Web/HTTP/Status/204) or [205 Reset Content](https://developer.mozilla.org/docs/Web/HTTP/Status/205), the promise resolves to `undefined`. + +# d3.svg(input[, init]) · [Source](https://github.com/d3/d3-fetch/blob/master/src/xml.js "Source") + +Fetches the file at the specified *input* URL as [text](#text) and then [parses it](https://developer.mozilla.org/docs/Web/API/DOMParser) as SVG. If *init* is specified, it is passed along to the underlying call to [fetch](https://fetch.spec.whatwg.org/#fetch-method); see [RequestInit](https://fetch.spec.whatwg.org/#requestinit) for allowed fields. + +# d3.text(input[, init]) · [Source](https://github.com/d3/d3-fetch/blob/master/src/text.js "Source") + +Fetches the text file at the specified *input* URL. If *init* is specified, it is passed along to the underlying call to [fetch](https://fetch.spec.whatwg.org/#fetch-method); see [RequestInit](https://fetch.spec.whatwg.org/#requestinit) for allowed fields. + +# d3.tsv(input[, init][, row]) · [Source](https://github.com/d3/d3-fetch/blob/master/src/dsv.js "Source") + +Equivalent to [d3.dsv](#dsv) with the tab character as the delimiter. + +# d3.xml(input[, init]) · [Source](https://github.com/d3/d3-fetch/blob/master/src/xml.js "Source") + +Fetches the file at the specified *input* URL as [text](#text) and then [parses it](https://developer.mozilla.org/docs/Web/API/DOMParser) as XML. If *init* is specified, it is passed along to the underlying call to [fetch](https://fetch.spec.whatwg.org/#fetch-method); see [RequestInit](https://fetch.spec.whatwg.org/#requestinit) for allowed fields. diff --git a/frontend/node_modules/d3-fetch/dist/d3-fetch.js b/frontend/node_modules/d3-fetch/dist/d3-fetch.js new file mode 100644 index 0000000..a50bf0e --- /dev/null +++ b/frontend/node_modules/d3-fetch/dist/d3-fetch.js @@ -0,0 +1,100 @@ +// https://d3js.org/d3-fetch/ v3.0.1 Copyright 2016-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-dsv')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-dsv'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3)); +}(this, (function (exports, d3Dsv) { 'use strict'; + +function responseBlob(response) { + if (!response.ok) throw new Error(response.status + " " + response.statusText); + return response.blob(); +} + +function blob(input, init) { + return fetch(input, init).then(responseBlob); +} + +function responseArrayBuffer(response) { + if (!response.ok) throw new Error(response.status + " " + response.statusText); + return response.arrayBuffer(); +} + +function buffer(input, init) { + return fetch(input, init).then(responseArrayBuffer); +} + +function responseText(response) { + if (!response.ok) throw new Error(response.status + " " + response.statusText); + return response.text(); +} + +function text(input, init) { + return fetch(input, init).then(responseText); +} + +function dsvParse(parse) { + return function(input, init, row) { + if (arguments.length === 2 && typeof init === "function") row = init, init = undefined; + return text(input, init).then(function(response) { + return parse(response, row); + }); + }; +} + +function dsv(delimiter, input, init, row) { + if (arguments.length === 3 && typeof init === "function") row = init, init = undefined; + var format = d3Dsv.dsvFormat(delimiter); + return text(input, init).then(function(response) { + return format.parse(response, row); + }); +} + +var csv = dsvParse(d3Dsv.csvParse); +var tsv = dsvParse(d3Dsv.tsvParse); + +function image(input, init) { + return new Promise(function(resolve, reject) { + var image = new Image; + for (var key in init) image[key] = init[key]; + image.onerror = reject; + image.onload = function() { resolve(image); }; + image.src = input; + }); +} + +function responseJson(response) { + if (!response.ok) throw new Error(response.status + " " + response.statusText); + if (response.status === 204 || response.status === 205) return; + return response.json(); +} + +function json(input, init) { + return fetch(input, init).then(responseJson); +} + +function parser(type) { + return (input, init) => text(input, init) + .then(text => (new DOMParser).parseFromString(text, type)); +} + +var xml = parser("application/xml"); + +var html = parser("text/html"); + +var svg = parser("image/svg+xml"); + +exports.blob = blob; +exports.buffer = buffer; +exports.csv = csv; +exports.dsv = dsv; +exports.html = html; +exports.image = image; +exports.json = json; +exports.svg = svg; +exports.text = text; +exports.tsv = tsv; +exports.xml = xml; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-fetch/dist/d3-fetch.min.js b/frontend/node_modules/d3-fetch/dist/d3-fetch.min.js new file mode 100644 index 0000000..18eed2f --- /dev/null +++ b/frontend/node_modules/d3-fetch/dist/d3-fetch.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-fetch/ v3.0.1 Copyright 2016-2021 Mike Bostock +!function(t,n){"object"==typeof exports&&"undefined"!=typeof module?n(exports,require("d3-dsv")):"function"==typeof define&&define.amd?define(["exports","d3-dsv"],n):n((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{},t.d3)}(this,(function(t,n){"use strict";function e(t){if(!t.ok)throw new Error(t.status+" "+t.statusText);return t.blob()}function r(t){if(!t.ok)throw new Error(t.status+" "+t.statusText);return t.arrayBuffer()}function o(t){if(!t.ok)throw new Error(t.status+" "+t.statusText);return t.text()}function u(t,n){return fetch(t,n).then(o)}function f(t){return function(n,e,r){return 2===arguments.length&&"function"==typeof e&&(r=e,e=void 0),u(n,e).then((function(n){return t(n,r)}))}}var s=f(n.csvParse),i=f(n.tsvParse);function a(t){if(!t.ok)throw new Error(t.status+" "+t.statusText);if(204!==t.status&&205!==t.status)return t.json()}function c(t){return(n,e)=>u(n,e).then((n=>(new DOMParser).parseFromString(n,t)))}var d=c("application/xml"),h=c("text/html"),l=c("image/svg+xml");t.blob=function(t,n){return fetch(t,n).then(e)},t.buffer=function(t,n){return fetch(t,n).then(r)},t.csv=s,t.dsv=function(t,e,r,o){3===arguments.length&&"function"==typeof r&&(o=r,r=void 0);var f=n.dsvFormat(t);return u(e,r).then((function(t){return f.parse(t,o)}))},t.html=h,t.image=function(t,n){return new Promise((function(e,r){var o=new Image;for(var u in n)o[u]=n[u];o.onerror=r,o.onload=function(){e(o)},o.src=t}))},t.json=function(t,n){return fetch(t,n).then(a)},t.svg=l,t.text=u,t.tsv=i,t.xml=d,Object.defineProperty(t,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-fetch/package.json b/frontend/node_modules/d3-fetch/package.json new file mode 100644 index 0000000..fa30c4f --- /dev/null +++ b/frontend/node_modules/d3-fetch/package.json @@ -0,0 +1,53 @@ +{ + "name": "d3-fetch", + "version": "3.0.1", + "description": "Convenient parsing for Fetch.", + "homepage": "https://d3js.org/d3-fetch/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-fetch.git" + }, + "keywords": [ + "d3", + "d3-module", + "fetch", + "ajax", + "XMLHttpRequest" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "http://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-fetch.min.js", + "unpkg": "dist/d3-fetch.min.js", + "exports": { + "umd": "./dist/d3-fetch.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "dependencies": { + "d3-dsv": "1 - 3" + }, + "devDependencies": { + "eslint": "7", + "mocha": "8", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-fetch/src/blob.js b/frontend/node_modules/d3-fetch/src/blob.js new file mode 100644 index 0000000..646664c --- /dev/null +++ b/frontend/node_modules/d3-fetch/src/blob.js @@ -0,0 +1,8 @@ +function responseBlob(response) { + if (!response.ok) throw new Error(response.status + " " + response.statusText); + return response.blob(); +} + +export default function(input, init) { + return fetch(input, init).then(responseBlob); +} diff --git a/frontend/node_modules/d3-fetch/src/buffer.js b/frontend/node_modules/d3-fetch/src/buffer.js new file mode 100644 index 0000000..f776a94 --- /dev/null +++ b/frontend/node_modules/d3-fetch/src/buffer.js @@ -0,0 +1,8 @@ +function responseArrayBuffer(response) { + if (!response.ok) throw new Error(response.status + " " + response.statusText); + return response.arrayBuffer(); +} + +export default function(input, init) { + return fetch(input, init).then(responseArrayBuffer); +} diff --git a/frontend/node_modules/d3-fetch/src/dsv.js b/frontend/node_modules/d3-fetch/src/dsv.js new file mode 100644 index 0000000..99d7bc3 --- /dev/null +++ b/frontend/node_modules/d3-fetch/src/dsv.js @@ -0,0 +1,22 @@ +import {csvParse, dsvFormat, tsvParse} from "d3-dsv"; +import text from "./text.js"; + +function dsvParse(parse) { + return function(input, init, row) { + if (arguments.length === 2 && typeof init === "function") row = init, init = undefined; + return text(input, init).then(function(response) { + return parse(response, row); + }); + }; +} + +export default function dsv(delimiter, input, init, row) { + if (arguments.length === 3 && typeof init === "function") row = init, init = undefined; + var format = dsvFormat(delimiter); + return text(input, init).then(function(response) { + return format.parse(response, row); + }); +} + +export var csv = dsvParse(csvParse); +export var tsv = dsvParse(tsvParse); diff --git a/frontend/node_modules/d3-fetch/src/image.js b/frontend/node_modules/d3-fetch/src/image.js new file mode 100644 index 0000000..c80a74b --- /dev/null +++ b/frontend/node_modules/d3-fetch/src/image.js @@ -0,0 +1,9 @@ +export default function(input, init) { + return new Promise(function(resolve, reject) { + var image = new Image; + for (var key in init) image[key] = init[key]; + image.onerror = reject; + image.onload = function() { resolve(image); }; + image.src = input; + }); +} diff --git a/frontend/node_modules/d3-fetch/src/index.js b/frontend/node_modules/d3-fetch/src/index.js new file mode 100644 index 0000000..f3ac0f9 --- /dev/null +++ b/frontend/node_modules/d3-fetch/src/index.js @@ -0,0 +1,7 @@ +export {default as blob} from "./blob.js"; +export {default as buffer} from "./buffer.js"; +export {default as dsv, csv, tsv} from "./dsv.js"; +export {default as image} from "./image.js"; +export {default as json} from "./json.js"; +export {default as text} from "./text.js"; +export {default as xml, html, svg} from "./xml.js"; diff --git a/frontend/node_modules/d3-fetch/src/json.js b/frontend/node_modules/d3-fetch/src/json.js new file mode 100644 index 0000000..25e9798 --- /dev/null +++ b/frontend/node_modules/d3-fetch/src/json.js @@ -0,0 +1,9 @@ +function responseJson(response) { + if (!response.ok) throw new Error(response.status + " " + response.statusText); + if (response.status === 204 || response.status === 205) return; + return response.json(); +} + +export default function(input, init) { + return fetch(input, init).then(responseJson); +} diff --git a/frontend/node_modules/d3-fetch/src/text.js b/frontend/node_modules/d3-fetch/src/text.js new file mode 100644 index 0000000..8ea18f8 --- /dev/null +++ b/frontend/node_modules/d3-fetch/src/text.js @@ -0,0 +1,8 @@ +function responseText(response) { + if (!response.ok) throw new Error(response.status + " " + response.statusText); + return response.text(); +} + +export default function(input, init) { + return fetch(input, init).then(responseText); +} diff --git a/frontend/node_modules/d3-fetch/src/xml.js b/frontend/node_modules/d3-fetch/src/xml.js new file mode 100644 index 0000000..5628280 --- /dev/null +++ b/frontend/node_modules/d3-fetch/src/xml.js @@ -0,0 +1,12 @@ +import text from "./text.js"; + +function parser(type) { + return (input, init) => text(input, init) + .then(text => (new DOMParser).parseFromString(text, type)); +} + +export default parser("application/xml"); + +export var html = parser("text/html"); + +export var svg = parser("image/svg+xml"); diff --git a/frontend/node_modules/d3-force/LICENSE b/frontend/node_modules/d3-force/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-force/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-force/README.md b/frontend/node_modules/d3-force/README.md new file mode 100644 index 0000000..d81dc1d --- /dev/null +++ b/frontend/node_modules/d3-force/README.md @@ -0,0 +1,480 @@ +# d3-force + +This module implements a [velocity Verlet](https://en.wikipedia.org/wiki/Verlet_integration) numerical integrator for simulating physical forces on particles. The simulation is simplified: it assumes a constant unit time step Δ*t* = 1 for each step, and a constant unit mass *m* = 1 for all particles. As a result, a force *F* acting on a particle is equivalent to a constant acceleration *a* over the time interval Δ*t*, and can be simulated simply by adding to the particle’s velocity, which is then added to the particle’s position. + +In the domain of information visualization, physical simulations are useful for studying [networks](https://observablehq.com/@d3/force-directed-graph) and [hierarchies](https://observablehq.com/@d3/force-directed-tree)! + +[Force-Directed Graph](https://observablehq.com/@d3/force-directed-graph)[Force-Directed Tree](https://observablehq.com/@d3/force-directed-tree) + +You can also simulate circles (disks) with collision, such as for [bubble charts](http://www.nytimes.com/interactive/2012/09/06/us/politics/convention-word-counts.html) or [beeswarm plots](https://observablehq.com/@d3/beeswarm): + +[Collision Detection](https://observablehq.com/@d3/collision-detection)[Beeswarm](https://observablehq.com/@d3/beeswarm) + +You can even use it as a rudimentary physics engine, say to simulate cloth: + +[Force-Directed Lattice](https://observablehq.com/@d3/force-directed-lattice) + +To use this module, create a [simulation](#simulation) for an array of [nodes](#simulation_nodes), and compose the desired [forces](#simulation_force). Then [listen](#simulation_on) for tick events to render the nodes as they update in your preferred graphics system, such as Canvas or SVG. + +## Installing + +If you use npm, `npm install d3-force`. You can also download the [latest release on GitHub](https://github.com/d3/d3-force/releases/latest). For vanilla HTML in modern browsers, import d3-force from Skypack: + +```html + +``` + +For legacy environments, you can load d3-force’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + + + + +``` + +[Try d3-force in your browser.](https://observablehq.com/collection/@d3/d3-force) + +## API Reference + +### Simulation + +# d3.forceSimulation([nodes]) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +Creates a new simulation with the specified array of [*nodes*](#simulation_nodes) and no [forces](#simulation_force). If *nodes* is not specified, it defaults to the empty array. The simulator [starts](#simulation_restart) automatically; use [*simulation*.on](#simulation_on) to listen for tick events as the simulation runs. If you wish to run the simulation manually instead, call [*simulation*.stop](#simulation_stop), and then call [*simulation*.tick](#simulation_tick) as desired. + +# simulation.restart() · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +Restarts the simulation’s internal timer and returns the simulation. In conjunction with [*simulation*.alphaTarget](#simulation_alphaTarget) or [*simulation*.alpha](#simulation_alpha), this method can be used to “reheat” the simulation during interaction, such as when dragging a node, or to resume the simulation after temporarily pausing it with [*simulation*.stop](#simulation_stop). + +# simulation.stop() · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +Stops the simulation’s internal timer, if it is running, and returns the simulation. If the timer is already stopped, this method does nothing. This method is useful for running the simulation manually; see [*simulation*.tick](#simulation_tick). + +# simulation.tick([iterations]) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +Manually steps the simulation by the specified number of *iterations*, and returns the simulation. If *iterations* is not specified, it defaults to 1 (single step). + +For each iteration, it increments the current [*alpha*](#simulation_alpha) by ([*alphaTarget*](#simulation_alphaTarget) - *alpha*) × [*alphaDecay*](#simulation_alphaDecay); then invokes each registered [force](#simulation_force), passing the new *alpha*; then decrements each [node](#simulation_nodes)’s velocity by *velocity* × [*velocityDecay*](#simulation_velocityDecay); lastly increments each node’s position by *velocity*. + +This method does not dispatch [events](#simulation_on); events are only dispatched by the internal timer when the simulation is started automatically upon [creation](#forceSimulation) or by calling [*simulation*.restart](#simulation_restart). The natural number of ticks when the simulation is started is ⌈*log*([*alphaMin*](#simulation_alphaMin)) / *log*(1 - [*alphaDecay*](#simulation_alphaDecay))⌉; by default, this is 300. + +This method can be used in conjunction with [*simulation*.stop](#simulation_stop) to compute a [static force layout](https://bl.ocks.org/mbostock/1667139). For large graphs, static layouts should be computed [in a web worker](https://bl.ocks.org/mbostock/01ab2e85e8727d6529d20391c0fd9a16) to avoid freezing the user interface. + +# simulation.nodes([nodes]) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +If *nodes* is specified, sets the simulation’s nodes to the specified array of objects, initializing their positions and velocities if necessary, and then [re-initializes](#force_initialize) any bound [forces](#simulation_force); returns the simulation. If *nodes* is not specified, returns the simulation’s array of nodes as specified to the [constructor](#forceSimulation). + +Each *node* must be an object. The following properties are assigned by the simulation: + +* `index` - the node’s zero-based index into *nodes* +* `x` - the node’s current *x*-position +* `y` - the node’s current *y*-position +* `vx` - the node’s current *x*-velocity +* `vy` - the node’s current *y*-velocity + +The position ⟨*x*,*y*⟩ and velocity ⟨*vx*,*vy*⟩ may be subsequently modified by [forces](#forces) and by the simulation. If either *vx* or *vy* is NaN, the velocity is initialized to ⟨0,0⟩. If either *x* or *y* is NaN, the position is initialized in a [phyllotaxis arrangement](https://observablehq.com/@d3/force-layout-phyllotaxis), so chosen to ensure a deterministic, uniform distribution. + +To fix a node in a given position, you may specify two additional properties: + +* `fx` - the node’s fixed *x*-position +* `fy` - the node’s fixed *y*-position + +At the end of each [tick](#simulation_tick), after the application of any forces, a node with a defined *node*.fx has *node*.x reset to this value and *node*.vx set to zero; likewise, a node with a defined *node*.fy has *node*.y reset to this value and *node*.vy set to zero. To unfix a node that was previously fixed, set *node*.fx and *node*.fy to null, or delete these properties. + +If the specified array of *nodes* is modified, such as when nodes are added to or removed from the simulation, this method must be called again with the new (or changed) array to notify the simulation and bound forces of the change; the simulation does not make a defensive copy of the specified array. + +# simulation.alpha([alpha]) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +*alpha* is roughly analogous to temperature in [simulated annealing](https://en.wikipedia.org/wiki/Simulated_annealing#Overview). It decreases over time as the simulation “cools down”. When *alpha* reaches *alphaMin*, the simulation stops; see [*simulation*.restart](#simulation_restart). + +If *alpha* is specified, sets the current alpha to the specified number in the range [0,1] and returns this simulation. If *alpha* is not specified, returns the current alpha value, which defaults to 1. + +# simulation.alphaMin([min]) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +If *min* is specified, sets the minimum *alpha* to the specified number in the range [0,1] and returns this simulation. If *min* is not specified, returns the current minimum *alpha* value, which defaults to 0.001. The simulation’s internal timer stops when the current [*alpha*](#simulation_alpha) is less than the minimum *alpha*. The default [alpha decay rate](#simulation_alphaDecay) of ~0.0228 corresponds to 300 iterations. + +# simulation.alphaDecay([decay]) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +If *decay* is specified, sets the [*alpha*](#simulation_alpha) decay rate to the specified number in the range [0,1] and returns this simulation. If *decay* is not specified, returns the current *alpha* decay rate, which defaults to 0.0228… = 1 - *pow*(0.001, 1 / 300) where 0.001 is the default [minimum *alpha*](#simulation_alphaMin). + +The alpha decay rate determines how quickly the current alpha interpolates towards the desired [target *alpha*](#simulation_alphaTarget); since the default target *alpha* is zero, by default this controls how quickly the simulation cools. Higher decay rates cause the simulation to stabilize more quickly, but risk getting stuck in a local minimum; lower values cause the simulation to take longer to run, but typically converge on a better layout. To have the simulation run forever at the current *alpha*, set the *decay* rate to zero; alternatively, set a [target *alpha*](#simulation_alphaTarget) greater than the [minimum *alpha*](#simulation_alphaMin). + +# simulation.alphaTarget([target]) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +If *target* is specified, sets the current target [*alpha*](#simulation_alpha) to the specified number in the range [0,1] and returns this simulation. If *target* is not specified, returns the current target alpha value, which defaults to 0. + +# simulation.velocityDecay([decay]) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +If *decay* is specified, sets the velocity decay factor to the specified number in the range [0,1] and returns this simulation. If *decay* is not specified, returns the current velocity decay factor, which defaults to 0.4. The decay factor is akin to atmospheric friction; after the application of any forces during a [tick](#simulation_tick), each node’s velocity is multiplied by 1 - *decay*. As with lowering the [alpha decay rate](#simulation_alphaDecay), less velocity decay may converge on a better solution, but risks numerical instabilities and oscillation. + +# simulation.force(name[, force]) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +If *force* is specified, assigns the [force](#forces) for the specified *name* and returns this simulation. If *force* is not specified, returns the force with the specified name, or undefined if there is no such force. (By default, new simulations have no forces.) For example, to create a new simulation to layout a graph, you might say: + +```js +var simulation = d3.forceSimulation(nodes) + .force("charge", d3.forceManyBody()) + .force("link", d3.forceLink(links)) + .force("center", d3.forceCenter()); +``` + +To remove the force with the given *name*, pass null as the *force*. For example, to remove the charge force: + +```js +simulation.force("charge", null); +``` + +# simulation.find(x, y[, radius]) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +Returns the node closest to the position ⟨*x*,*y*⟩ with the given search *radius*. If *radius* is not specified, it defaults to infinity. If there is no node within the search area, returns undefined. + +# simulation.randomSource([source]) [<>](https://github.com/d3/d3-force/blob/master/src/simulation.js "Source")) + +If *source* is specified, sets the function used to generate random numbers; this should be a function that returns a number between 0 (inclusive) and 1 (exclusive). If *source* is not specified, returns this simulation’s current random source which defaults to a fixed-seed [linear congruential generator](https://en.wikipedia.org/wiki/Linear_congruential_generator). See also [*random*.source](https://github.com/d3/d3-random/blob/master/README.md#random_source). + +# simulation.on(typenames, [listener]) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +If *listener* is specified, sets the event *listener* for the specified *typenames* and returns this simulation. If an event listener was already registered for the same type and name, the existing listener is removed before the new listener is added. If *listener* is null, removes the current event listeners for the specified *typenames*, if any. If *listener* is not specified, returns the first currently-assigned listener matching the specified *typenames*, if any. When a specified event is dispatched, each *listener* will be invoked with the `this` context as the simulation. + +The *typenames* is a string containing one or more *typename* separated by whitespace. Each *typename* is a *type*, optionally followed by a period (`.`) and a *name*, such as `tick.foo` and `tick.bar`; the name allows multiple listeners to be registered for the same *type*. The *type* must be one of the following: + +* `tick` - after each tick of the simulation’s internal timer. +* `end` - after the simulation’s timer stops when *alpha* < [*alphaMin*](#simulation_alphaMin). + +Note that *tick* events are not dispatched when [*simulation*.tick](#simulation_tick) is called manually; events are only dispatched by the internal timer and are intended for interactive rendering of the simulation. To affect the simulation, register [forces](#simulation_force) instead of modifying nodes’ positions or velocities inside a tick event listener. + +See [*dispatch*.on](https://github.com/d3/d3-dispatch#dispatch_on) for details. + +### Forces + +A *force* is simply a function that modifies nodes’ positions or velocities; in this context, a *force* can apply a classical physical force such as electrical charge or gravity, or it can resolve a geometric constraint, such as keeping nodes within a bounding box or keeping linked nodes a fixed distance apart. For example, a simple positioning force that moves nodes towards the origin ⟨0,0⟩ might be implemented as: + +```js +function force(alpha) { + for (var i = 0, n = nodes.length, node, k = alpha * 0.1; i < n; ++i) { + node = nodes[i]; + node.vx -= node.x * k; + node.vy -= node.y * k; + } +} +``` + +Forces typically read the node’s current position ⟨*x*,*y*⟩ and then add to (or subtract from) the node’s velocity ⟨*vx*,*vy*⟩. However, forces may also “peek ahead” to the anticipated next position of the node, ⟨*x* + *vx*,*y* + *vy*⟩; this is necessary for resolving geometric constraints through [iterative relaxation](https://en.wikipedia.org/wiki/Relaxation_\(iterative_method\)). Forces may also modify the position directly, which is sometimes useful to avoid adding energy to the simulation, such as when recentering the simulation in the viewport. + +Simulations typically compose multiple forces as desired. This module provides several for your enjoyment: + +* [Centering](#centering) +* [Collision](#collision) +* [Links](#links) +* [Many-Body](#many-body) +* [Positioning](#positioning) + +Forces may optionally implement [*force*.initialize](#force_initialize) to receive the simulation’s array of nodes. + +# force(alpha) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +Applies this force, optionally observing the specified *alpha*. Typically, the force is applied to the array of nodes previously passed to [*force*.initialize](#force_initialize), however, some forces may apply to a subset of nodes, or behave differently. For example, [d3.forceLink](#links) applies to the source and target of each link. + +# force.initialize(nodes) · [Source](https://github.com/d3/d3-force/blob/master/src/simulation.js) + +Supplies the array of *nodes* and *random* source to this force. This method is called when a force is bound to a simulation via [*simulation*.force](#simulation_force) and when the simulation’s nodes change via [*simulation*.nodes](#simulation_nodes). A force may perform necessary work during initialization, such as evaluating per-node parameters, to avoid repeatedly performing work during each application of the force. + +#### Centering + +The centering force translates nodes uniformly so that the mean position of all nodes (the center of mass if all nodes have equal weight) is at the given position ⟨[*x*](#center_x),[*y*](#center_y)⟩. This force modifies the positions of nodes on each application; it does not modify velocities, as doing so would typically cause the nodes to overshoot and oscillate around the desired center. This force helps keeps nodes in the center of the viewport, and unlike the [positioning force](#positioning), it does not distort their relative positions. + +# d3.forceCenter([x, y]) · [Source](https://github.com/d3/d3-force/blob/master/src/center.js) + +Creates a new centering force with the specified [*x*-](#center_x) and [*y*-](#center_y) coordinates. If *x* and *y* are not specified, they default to ⟨0,0⟩. + +# center.x([x]) · [Source](https://github.com/d3/d3-force/blob/master/src/center.js) + +If *x* is specified, sets the *x*-coordinate of the centering position to the specified number and returns this force. If *x* is not specified, returns the current *x*-coordinate, which defaults to zero. + +# center.y([y]) · [Source](https://github.com/d3/d3-force/blob/master/src/center.js) + +If *y* is specified, sets the *y*-coordinate of the centering position to the specified number and returns this force. If *y* is not specified, returns the current *y*-coordinate, which defaults to zero. + +# center.strength([strength]) · [Source](https://github.com/d3/d3-force/blob/master/src/center.js), [Examples](https://observablehq.com/@d3/forcecenter-strength) + +If *strength* is specified, sets the centering force’s strength. A reduced strength of e.g. 0.05 softens the movements on interactive graphs in which new nodes enter or exit the graph. If *strength* is not specified, returns the force’s current strength, which defaults to 1. + +#### Collision + +The collision force treats nodes as circles with a given [radius](#collide_radius), rather than points, and prevents nodes from overlapping. More formally, two nodes *a* and *b* are separated so that the distance between *a* and *b* is at least *radius*(*a*) + *radius*(*b*). To reduce jitter, this is by default a “soft” constraint with a configurable [strength](#collide_strength) and [iteration count](#collide_iterations). + +# d3.forceCollide([radius]) · [Source](https://github.com/d3/d3-force/blob/master/src/collide.js) + +Creates a new circle collision force with the specified [*radius*](#collide_radius). If *radius* is not specified, it defaults to the constant one for all nodes. + +# collide.radius([radius]) · [Source](https://github.com/d3/d3-force/blob/master/src/collide.js) + +If *radius* is specified, sets the radius accessor to the specified number or function, re-evaluates the radius accessor for each node, and returns this force. If *radius* is not specified, returns the current radius accessor, which defaults to: + +```js +function radius() { + return 1; +} +``` + +The radius accessor is invoked for each [node](#simulation_nodes) in the simulation, being passed the *node* and its zero-based *index*. The resulting number is then stored internally, such that the radius of each node is only recomputed when the force is initialized or when this method is called with a new *radius*, and not on every application of the force. + +# collide.strength([strength]) · [Source](https://github.com/d3/d3-force/blob/master/src/collide.js) + +If *strength* is specified, sets the force strength to the specified number in the range [0,1] and returns this force. If *strength* is not specified, returns the current strength which defaults to 1. + +Overlapping nodes are resolved through iterative relaxation. For each node, the other nodes that are anticipated to overlap at the next tick (using the anticipated positions ⟨*x* + *vx*,*y* + *vy*⟩) are determined; the node’s velocity is then modified to push the node out of each overlapping node. The change in velocity is dampened by the force’s strength such that the resolution of simultaneous overlaps can be blended together to find a stable solution. + +# collide.iterations([iterations]) · [Source](https://github.com/d3/d3-force/blob/master/src/collide.js) + +If *iterations* is specified, sets the number of iterations per application to the specified number and returns this force. If *iterations* is not specified, returns the current iteration count which defaults to 1. Increasing the number of iterations greatly increases the rigidity of the constraint and avoids partial overlap of nodes, but also increases the runtime cost to evaluate the force. + +#### Links + +The link force pushes linked nodes together or apart according to the desired [link distance](#link_distance). The strength of the force is proportional to the difference between the linked nodes’ distance and the target distance, similar to a spring force. + +# d3.forceLink([links]) · [Source](https://github.com/d3/d3-force/blob/master/src/link.js) + +Creates a new link force with the specified *links* and default parameters. If *links* is not specified, it defaults to the empty array. + +# link.links([links]) · [Source](https://github.com/d3/d3-force/blob/master/src/link.js) + +If *links* is specified, sets the array of links associated with this force, recomputes the [distance](#link_distance) and [strength](#link_strength) parameters for each link, and returns this force. If *links* is not specified, returns the current array of links, which defaults to the empty array. + +Each link is an object with the following properties: + +* `source` - the link’s source node; see [*simulation*.nodes](#simulation_nodes) +* `target` - the link’s target node; see [*simulation*.nodes](#simulation_nodes) +* `index` - the zero-based index into *links*, assigned by this method + +For convenience, a link’s source and target properties may be initialized using numeric or string identifiers rather than object references; see [*link*.id](#link_id). When the link force is [initialized](#force_initialize) (or re-initialized, as when the nodes or links change), any *link*.source or *link*.target property which is *not* an object is replaced by an object reference to the corresponding *node* with the given identifier. + +If the specified array of *links* is modified, such as when links are added to or removed from the simulation, this method must be called again with the new (or changed) array to notify the force of the change; the force does not make a defensive copy of the specified array. + +# link.id([id]) · [Source](https://github.com/d3/d3-force/blob/master/src/link.js) + +If *id* is specified, sets the node id accessor to the specified function and returns this force. If *id* is not specified, returns the current node id accessor, which defaults to the numeric *node*.index: + +```js +function id(d) { + return d.index; +} +``` + +The default id accessor allows each link’s source and target to be specified as a zero-based index into the [nodes](#simulation_nodes) array. For example: + +```js +var nodes = [ + {"id": "Alice"}, + {"id": "Bob"}, + {"id": "Carol"} +]; + +var links = [ + {"source": 0, "target": 1}, // Alice → Bob + {"source": 1, "target": 2} // Bob → Carol +]; +``` + +Now consider a different id accessor that returns a string: + +```js +function id(d) { + return d.id; +} +``` + +With this accessor, you can use named sources and targets: + +```js +var nodes = [ + {"id": "Alice"}, + {"id": "Bob"}, + {"id": "Carol"} +]; + +var links = [ + {"source": "Alice", "target": "Bob"}, + {"source": "Bob", "target": "Carol"} +]; +``` + +This is particularly useful when representing graphs in JSON, as JSON does not allow references. See [this example](https://bl.ocks.org/mbostock/f584aa36df54c451c94a9d0798caed35). + +The id accessor is invoked for each node whenever the force is initialized, as when the [nodes](#simulation_nodes) or [links](#link_links) change, being passed the node and its zero-based index. + +# link.distance([distance]) · [Source](https://github.com/d3/d3-force/blob/master/src/link.js) + +If *distance* is specified, sets the distance accessor to the specified number or function, re-evaluates the distance accessor for each link, and returns this force. If *distance* is not specified, returns the current distance accessor, which defaults to: + +```js +function distance() { + return 30; +} +``` + +The distance accessor is invoked for each [link](#link_links), being passed the *link* and its zero-based *index*. The resulting number is then stored internally, such that the distance of each link is only recomputed when the force is initialized or when this method is called with a new *distance*, and not on every application of the force. + +# link.strength([strength]) · [Source](https://github.com/d3/d3-force/blob/master/src/link.js) + +If *strength* is specified, sets the strength accessor to the specified number or function, re-evaluates the strength accessor for each link, and returns this force. If *strength* is not specified, returns the current strength accessor, which defaults to: + +```js +function strength(link) { + return 1 / Math.min(count(link.source), count(link.target)); +} +``` + +Where *count*(*node*) is a function that returns the number of links with the given node as a source or target. This default was chosen because it automatically reduces the strength of links connected to heavily-connected nodes, improving stability. + +The strength accessor is invoked for each [link](#link_links), being passed the *link* and its zero-based *index*. The resulting number is then stored internally, such that the strength of each link is only recomputed when the force is initialized or when this method is called with a new *strength*, and not on every application of the force. + +# link.iterations([iterations]) · [Source](https://github.com/d3/d3-force/blob/master/src/link.js) + +If *iterations* is specified, sets the number of iterations per application to the specified number and returns this force. If *iterations* is not specified, returns the current iteration count which defaults to 1. Increasing the number of iterations greatly increases the rigidity of the constraint and is useful for [complex structures such as lattices](https://observablehq.com/@d3/force-directed-lattice), but also increases the runtime cost to evaluate the force. + +#### Many-Body + +The many-body (or *n*-body) force applies mutually amongst all [nodes](#simulation_nodes). It can be used to simulate gravity (attraction) if the [strength](#manyBody_strength) is positive, or electrostatic charge (repulsion) if the strength is negative. This implementation uses quadtrees and the [Barnes–Hut approximation](https://en.wikipedia.org/wiki/Barnes–Hut_simulation) to greatly improve performance; the accuracy can be customized using the [theta](#manyBody_theta) parameter. + +Unlike links, which only affect two linked nodes, the charge force is global: every node affects every other node, even if they are on disconnected subgraphs. + +# d3.forceManyBody() · [Source](https://github.com/d3/d3-force/blob/master/src/manyBody.js) + +Creates a new many-body force with the default parameters. + +# manyBody.strength([strength]) · [Source](https://github.com/d3/d3-force/blob/master/src/manyBody.js) + +If *strength* is specified, sets the strength accessor to the specified number or function, re-evaluates the strength accessor for each node, and returns this force. A positive value causes nodes to attract each other, similar to gravity, while a negative value causes nodes to repel each other, similar to electrostatic charge. If *strength* is not specified, returns the current strength accessor, which defaults to: + +```js +function strength() { + return -30; +} +``` + +The strength accessor is invoked for each [node](#simulation_nodes) in the simulation, being passed the *node* and its zero-based *index*. The resulting number is then stored internally, such that the strength of each node is only recomputed when the force is initialized or when this method is called with a new *strength*, and not on every application of the force. + +# manyBody.theta([theta]) · [Source](https://github.com/d3/d3-force/blob/master/src/manyBody.js) + +If *theta* is specified, sets the Barnes–Hut approximation criterion to the specified number and returns this force. If *theta* is not specified, returns the current value, which defaults to 0.9. + +To accelerate computation, this force implements the [Barnes–Hut approximation](http://en.wikipedia.org/wiki/Barnes–Hut_simulation) which takes O(*n* log *n*) per application where *n* is the number of [nodes](#simulation_nodes). For each application, a [quadtree](https://github.com/d3/d3-quadtree) stores the current node positions; then for each node, the combined force of all other nodes on the given node is computed. For a cluster of nodes that is far away, the charge force can be approximated by treating the cluster as a single, larger node. The *theta* parameter determines the accuracy of the approximation: if the ratio *w* / *l* of the width *w* of the quadtree cell to the distance *l* from the node to the cell’s center of mass is less than *theta*, all nodes in the given cell are treated as a single node rather than individually. + +# manyBody.distanceMin([distance]) · [Source](https://github.com/d3/d3-force/blob/master/src/manyBody.js) + +If *distance* is specified, sets the minimum distance between nodes over which this force is considered. If *distance* is not specified, returns the current minimum distance, which defaults to 1. A minimum distance establishes an upper bound on the strength of the force between two nearby nodes, avoiding instability. In particular, it avoids an infinitely-strong force if two nodes are exactly coincident; in this case, the direction of the force is random. + +# manyBody.distanceMax([distance]) · [Source](https://github.com/d3/d3-force/blob/master/src/manyBody.js) + +If *distance* is specified, sets the maximum distance between nodes over which this force is considered. If *distance* is not specified, returns the current maximum distance, which defaults to infinity. Specifying a finite maximum distance improves performance and produces a more localized layout. + +#### Positioning + +The [*x*](#forceX)- and [*y*](#forceY)-positioning forces push nodes towards a desired position along the given dimension with a configurable strength. The [*radial*](#forceRadial) force is similar, except it pushes nodes towards the closest point on a given circle. The strength of the force is proportional to the one-dimensional distance between the node’s position and the target position. While these forces can be used to position individual nodes, they are intended primarily for global forces that apply to all (or most) nodes. + +# d3.forceX([x]) · [Source](https://github.com/d3/d3-force/blob/master/src/x.js) + +Creates a new positioning force along the *x*-axis towards the given position [*x*](#x_x). If *x* is not specified, it defaults to 0. + +# x.strength([strength]) · [Source](https://github.com/d3/d3-force/blob/master/src/x.js) + +If *strength* is specified, sets the strength accessor to the specified number or function, re-evaluates the strength accessor for each node, and returns this force. The *strength* determines how much to increment the node’s *x*-velocity: ([*x*](#x_x) - *node*.x) × *strength*. For example, a value of 0.1 indicates that the node should move a tenth of the way from its current *x*-position to the target *x*-position with each application. Higher values moves nodes more quickly to the target position, often at the expense of other forces or constraints. A value outside the range [0,1] is not recommended. + +If *strength* is not specified, returns the current strength accessor, which defaults to: + +```js +function strength() { + return 0.1; +} +``` + +The strength accessor is invoked for each [node](#simulation_nodes) in the simulation, being passed the *node* and its zero-based *index*. The resulting number is then stored internally, such that the strength of each node is only recomputed when the force is initialized or when this method is called with a new *strength*, and not on every application of the force. + +# x.x([x]) · [Source](https://github.com/d3/d3-force/blob/master/src/x.js) + +If *x* is specified, sets the *x*-coordinate accessor to the specified number or function, re-evaluates the *x*-accessor for each node, and returns this force. If *x* is not specified, returns the current *x*-accessor, which defaults to: + +```js +function x() { + return 0; +} +``` + +The *x*-accessor is invoked for each [node](#simulation_nodes) in the simulation, being passed the *node* and its zero-based *index*. The resulting number is then stored internally, such that the target *x*-coordinate of each node is only recomputed when the force is initialized or when this method is called with a new *x*, and not on every application of the force. + +# d3.forceY([y]) · [Source](https://github.com/d3/d3-force/blob/master/src/y.js) + +Creates a new positioning force along the *y*-axis towards the given position [*y*](#y_y). If *y* is not specified, it defaults to 0. + +# y.strength([strength]) · [Source](https://github.com/d3/d3-force/blob/master/src/y.js) + +If *strength* is specified, sets the strength accessor to the specified number or function, re-evaluates the strength accessor for each node, and returns this force. The *strength* determines how much to increment the node’s *y*-velocity: ([*y*](#y_y) - *node*.y) × *strength*. For example, a value of 0.1 indicates that the node should move a tenth of the way from its current *y*-position to the target *y*-position with each application. Higher values moves nodes more quickly to the target position, often at the expense of other forces or constraints. A value outside the range [0,1] is not recommended. + +If *strength* is not specified, returns the current strength accessor, which defaults to: + +```js +function strength() { + return 0.1; +} +``` + +The strength accessor is invoked for each [node](#simulation_nodes) in the simulation, being passed the *node* and its zero-based *index*. The resulting number is then stored internally, such that the strength of each node is only recomputed when the force is initialized or when this method is called with a new *strength*, and not on every application of the force. + +# y.y([y]) · [Source](https://github.com/d3/d3-force/blob/master/src/y.js) + +If *y* is specified, sets the *y*-coordinate accessor to the specified number or function, re-evaluates the *y*-accessor for each node, and returns this force. If *y* is not specified, returns the current *y*-accessor, which defaults to: + +```js +function y() { + return 0; +} +``` + +The *y*-accessor is invoked for each [node](#simulation_nodes) in the simulation, being passed the *node* and its zero-based *index*. The resulting number is then stored internally, such that the target *y*-coordinate of each node is only recomputed when the force is initialized or when this method is called with a new *y*, and not on every application of the force. + +# d3.forceRadial(radius[, x][, y]) · [Source](https://github.com/d3/d3-force/blob/master/src/radial.js) + +[Radial Force](https://bl.ocks.org/mbostock/cd98bf52e9067e26945edd95e8cf6ef9) + +Creates a new positioning force towards a circle of the specified [*radius*](#radial_radius) centered at ⟨[*x*](#radial_x),[*y*](#radial_y)⟩. If *x* and *y* are not specified, they default to ⟨0,0⟩. + +# radial.strength([strength]) · [Source](https://github.com/d3/d3-force/blob/master/src/radial.js) + +If *strength* is specified, sets the strength accessor to the specified number or function, re-evaluates the strength accessor for each node, and returns this force. The *strength* determines how much to increment the node’s *x*- and *y*-velocity. For example, a value of 0.1 indicates that the node should move a tenth of the way from its current position to the closest point on the circle with each application. Higher values moves nodes more quickly to the target position, often at the expense of other forces or constraints. A value outside the range [0,1] is not recommended. + +If *strength* is not specified, returns the current strength accessor, which defaults to: + +```js +function strength() { + return 0.1; +} +``` + +The strength accessor is invoked for each [node](#simulation_nodes) in the simulation, being passed the *node* and its zero-based *index*. The resulting number is then stored internally, such that the strength of each node is only recomputed when the force is initialized or when this method is called with a new *strength*, and not on every application of the force. + +# radial.radius([radius]) · [Source](https://github.com/d3/d3-force/blob/master/src/radial.js) + +If *radius* is specified, sets the circle *radius* to the specified number or function, re-evaluates the *radius* accessor for each node, and returns this force. If *radius* is not specified, returns the current *radius* accessor. + +The *radius* accessor is invoked for each [node](#simulation_nodes) in the simulation, being passed the *node* and its zero-based *index*. The resulting number is then stored internally, such that the target radius of each node is only recomputed when the force is initialized or when this method is called with a new *radius*, and not on every application of the force. + +# radial.x([x]) · [Source](https://github.com/d3/d3-force/blob/master/src/radial.js) + +If *x* is specified, sets the *x*-coordinate of the circle center to the specified number and returns this force. If *x* is not specified, returns the current *x*-coordinate of the center, which defaults to zero. + +# radial.y([y]) · [Source](https://github.com/d3/d3-force/blob/master/src/radial.js) + +If *y* is specified, sets the *y*-coordinate of the circle center to the specified number and returns this force. If *y* is not specified, returns the current *y*-coordinate of the center, which defaults to zero. diff --git a/frontend/node_modules/d3-force/dist/d3-force.js b/frontend/node_modules/d3-force/dist/d3-force.js new file mode 100644 index 0000000..71976dc --- /dev/null +++ b/frontend/node_modules/d3-force/dist/d3-force.js @@ -0,0 +1,693 @@ +// https://d3js.org/d3-force/ v3.0.0 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-quadtree'), require('d3-dispatch'), require('d3-timer')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-quadtree', 'd3-dispatch', 'd3-timer'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3, global.d3, global.d3)); +}(this, (function (exports, d3Quadtree, d3Dispatch, d3Timer) { 'use strict'; + +function center(x, y) { + var nodes, strength = 1; + + if (x == null) x = 0; + if (y == null) y = 0; + + function force() { + var i, + n = nodes.length, + node, + sx = 0, + sy = 0; + + for (i = 0; i < n; ++i) { + node = nodes[i], sx += node.x, sy += node.y; + } + + for (sx = (sx / n - x) * strength, sy = (sy / n - y) * strength, i = 0; i < n; ++i) { + node = nodes[i], node.x -= sx, node.y -= sy; + } + } + + force.initialize = function(_) { + nodes = _; + }; + + force.x = function(_) { + return arguments.length ? (x = +_, force) : x; + }; + + force.y = function(_) { + return arguments.length ? (y = +_, force) : y; + }; + + force.strength = function(_) { + return arguments.length ? (strength = +_, force) : strength; + }; + + return force; +} + +function constant(x) { + return function() { + return x; + }; +} + +function jiggle(random) { + return (random() - 0.5) * 1e-6; +} + +function x$2(d) { + return d.x + d.vx; +} + +function y$2(d) { + return d.y + d.vy; +} + +function collide(radius) { + var nodes, + radii, + random, + strength = 1, + iterations = 1; + + if (typeof radius !== "function") radius = constant(radius == null ? 1 : +radius); + + function force() { + var i, n = nodes.length, + tree, + node, + xi, + yi, + ri, + ri2; + + for (var k = 0; k < iterations; ++k) { + tree = d3Quadtree.quadtree(nodes, x$2, y$2).visitAfter(prepare); + for (i = 0; i < n; ++i) { + node = nodes[i]; + ri = radii[node.index], ri2 = ri * ri; + xi = node.x + node.vx; + yi = node.y + node.vy; + tree.visit(apply); + } + } + + function apply(quad, x0, y0, x1, y1) { + var data = quad.data, rj = quad.r, r = ri + rj; + if (data) { + if (data.index > node.index) { + var x = xi - data.x - data.vx, + y = yi - data.y - data.vy, + l = x * x + y * y; + if (l < r * r) { + if (x === 0) x = jiggle(random), l += x * x; + if (y === 0) y = jiggle(random), l += y * y; + l = (r - (l = Math.sqrt(l))) / l * strength; + node.vx += (x *= l) * (r = (rj *= rj) / (ri2 + rj)); + node.vy += (y *= l) * r; + data.vx -= x * (r = 1 - r); + data.vy -= y * r; + } + } + return; + } + return x0 > xi + r || x1 < xi - r || y0 > yi + r || y1 < yi - r; + } + } + + function prepare(quad) { + if (quad.data) return quad.r = radii[quad.data.index]; + for (var i = quad.r = 0; i < 4; ++i) { + if (quad[i] && quad[i].r > quad.r) { + quad.r = quad[i].r; + } + } + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length, node; + radii = new Array(n); + for (i = 0; i < n; ++i) node = nodes[i], radii[node.index] = +radius(node, i, nodes); + } + + force.initialize = function(_nodes, _random) { + nodes = _nodes; + random = _random; + initialize(); + }; + + force.iterations = function(_) { + return arguments.length ? (iterations = +_, force) : iterations; + }; + + force.strength = function(_) { + return arguments.length ? (strength = +_, force) : strength; + }; + + force.radius = function(_) { + return arguments.length ? (radius = typeof _ === "function" ? _ : constant(+_), initialize(), force) : radius; + }; + + return force; +} + +function index(d) { + return d.index; +} + +function find(nodeById, nodeId) { + var node = nodeById.get(nodeId); + if (!node) throw new Error("node not found: " + nodeId); + return node; +} + +function link(links) { + var id = index, + strength = defaultStrength, + strengths, + distance = constant(30), + distances, + nodes, + count, + bias, + random, + iterations = 1; + + if (links == null) links = []; + + function defaultStrength(link) { + return 1 / Math.min(count[link.source.index], count[link.target.index]); + } + + function force(alpha) { + for (var k = 0, n = links.length; k < iterations; ++k) { + for (var i = 0, link, source, target, x, y, l, b; i < n; ++i) { + link = links[i], source = link.source, target = link.target; + x = target.x + target.vx - source.x - source.vx || jiggle(random); + y = target.y + target.vy - source.y - source.vy || jiggle(random); + l = Math.sqrt(x * x + y * y); + l = (l - distances[i]) / l * alpha * strengths[i]; + x *= l, y *= l; + target.vx -= x * (b = bias[i]); + target.vy -= y * b; + source.vx += x * (b = 1 - b); + source.vy += y * b; + } + } + } + + function initialize() { + if (!nodes) return; + + var i, + n = nodes.length, + m = links.length, + nodeById = new Map(nodes.map((d, i) => [id(d, i, nodes), d])), + link; + + for (i = 0, count = new Array(n); i < m; ++i) { + link = links[i], link.index = i; + if (typeof link.source !== "object") link.source = find(nodeById, link.source); + if (typeof link.target !== "object") link.target = find(nodeById, link.target); + count[link.source.index] = (count[link.source.index] || 0) + 1; + count[link.target.index] = (count[link.target.index] || 0) + 1; + } + + for (i = 0, bias = new Array(m); i < m; ++i) { + link = links[i], bias[i] = count[link.source.index] / (count[link.source.index] + count[link.target.index]); + } + + strengths = new Array(m), initializeStrength(); + distances = new Array(m), initializeDistance(); + } + + function initializeStrength() { + if (!nodes) return; + + for (var i = 0, n = links.length; i < n; ++i) { + strengths[i] = +strength(links[i], i, links); + } + } + + function initializeDistance() { + if (!nodes) return; + + for (var i = 0, n = links.length; i < n; ++i) { + distances[i] = +distance(links[i], i, links); + } + } + + force.initialize = function(_nodes, _random) { + nodes = _nodes; + random = _random; + initialize(); + }; + + force.links = function(_) { + return arguments.length ? (links = _, initialize(), force) : links; + }; + + force.id = function(_) { + return arguments.length ? (id = _, force) : id; + }; + + force.iterations = function(_) { + return arguments.length ? (iterations = +_, force) : iterations; + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant(+_), initializeStrength(), force) : strength; + }; + + force.distance = function(_) { + return arguments.length ? (distance = typeof _ === "function" ? _ : constant(+_), initializeDistance(), force) : distance; + }; + + return force; +} + +// https://en.wikipedia.org/wiki/Linear_congruential_generator#Parameters_in_common_use +const a = 1664525; +const c = 1013904223; +const m = 4294967296; // 2^32 + +function lcg() { + let s = 1; + return () => (s = (a * s + c) % m) / m; +} + +function x$1(d) { + return d.x; +} + +function y$1(d) { + return d.y; +} + +var initialRadius = 10, + initialAngle = Math.PI * (3 - Math.sqrt(5)); + +function simulation(nodes) { + var simulation, + alpha = 1, + alphaMin = 0.001, + alphaDecay = 1 - Math.pow(alphaMin, 1 / 300), + alphaTarget = 0, + velocityDecay = 0.6, + forces = new Map(), + stepper = d3Timer.timer(step), + event = d3Dispatch.dispatch("tick", "end"), + random = lcg(); + + if (nodes == null) nodes = []; + + function step() { + tick(); + event.call("tick", simulation); + if (alpha < alphaMin) { + stepper.stop(); + event.call("end", simulation); + } + } + + function tick(iterations) { + var i, n = nodes.length, node; + + if (iterations === undefined) iterations = 1; + + for (var k = 0; k < iterations; ++k) { + alpha += (alphaTarget - alpha) * alphaDecay; + + forces.forEach(function(force) { + force(alpha); + }); + + for (i = 0; i < n; ++i) { + node = nodes[i]; + if (node.fx == null) node.x += node.vx *= velocityDecay; + else node.x = node.fx, node.vx = 0; + if (node.fy == null) node.y += node.vy *= velocityDecay; + else node.y = node.fy, node.vy = 0; + } + } + + return simulation; + } + + function initializeNodes() { + for (var i = 0, n = nodes.length, node; i < n; ++i) { + node = nodes[i], node.index = i; + if (node.fx != null) node.x = node.fx; + if (node.fy != null) node.y = node.fy; + if (isNaN(node.x) || isNaN(node.y)) { + var radius = initialRadius * Math.sqrt(0.5 + i), angle = i * initialAngle; + node.x = radius * Math.cos(angle); + node.y = radius * Math.sin(angle); + } + if (isNaN(node.vx) || isNaN(node.vy)) { + node.vx = node.vy = 0; + } + } + } + + function initializeForce(force) { + if (force.initialize) force.initialize(nodes, random); + return force; + } + + initializeNodes(); + + return simulation = { + tick: tick, + + restart: function() { + return stepper.restart(step), simulation; + }, + + stop: function() { + return stepper.stop(), simulation; + }, + + nodes: function(_) { + return arguments.length ? (nodes = _, initializeNodes(), forces.forEach(initializeForce), simulation) : nodes; + }, + + alpha: function(_) { + return arguments.length ? (alpha = +_, simulation) : alpha; + }, + + alphaMin: function(_) { + return arguments.length ? (alphaMin = +_, simulation) : alphaMin; + }, + + alphaDecay: function(_) { + return arguments.length ? (alphaDecay = +_, simulation) : +alphaDecay; + }, + + alphaTarget: function(_) { + return arguments.length ? (alphaTarget = +_, simulation) : alphaTarget; + }, + + velocityDecay: function(_) { + return arguments.length ? (velocityDecay = 1 - _, simulation) : 1 - velocityDecay; + }, + + randomSource: function(_) { + return arguments.length ? (random = _, forces.forEach(initializeForce), simulation) : random; + }, + + force: function(name, _) { + return arguments.length > 1 ? ((_ == null ? forces.delete(name) : forces.set(name, initializeForce(_))), simulation) : forces.get(name); + }, + + find: function(x, y, radius) { + var i = 0, + n = nodes.length, + dx, + dy, + d2, + node, + closest; + + if (radius == null) radius = Infinity; + else radius *= radius; + + for (i = 0; i < n; ++i) { + node = nodes[i]; + dx = x - node.x; + dy = y - node.y; + d2 = dx * dx + dy * dy; + if (d2 < radius) closest = node, radius = d2; + } + + return closest; + }, + + on: function(name, _) { + return arguments.length > 1 ? (event.on(name, _), simulation) : event.on(name); + } + }; +} + +function manyBody() { + var nodes, + node, + random, + alpha, + strength = constant(-30), + strengths, + distanceMin2 = 1, + distanceMax2 = Infinity, + theta2 = 0.81; + + function force(_) { + var i, n = nodes.length, tree = d3Quadtree.quadtree(nodes, x$1, y$1).visitAfter(accumulate); + for (alpha = _, i = 0; i < n; ++i) node = nodes[i], tree.visit(apply); + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length, node; + strengths = new Array(n); + for (i = 0; i < n; ++i) node = nodes[i], strengths[node.index] = +strength(node, i, nodes); + } + + function accumulate(quad) { + var strength = 0, q, c, weight = 0, x, y, i; + + // For internal nodes, accumulate forces from child quadrants. + if (quad.length) { + for (x = y = i = 0; i < 4; ++i) { + if ((q = quad[i]) && (c = Math.abs(q.value))) { + strength += q.value, weight += c, x += c * q.x, y += c * q.y; + } + } + quad.x = x / weight; + quad.y = y / weight; + } + + // For leaf nodes, accumulate forces from coincident quadrants. + else { + q = quad; + q.x = q.data.x; + q.y = q.data.y; + do strength += strengths[q.data.index]; + while (q = q.next); + } + + quad.value = strength; + } + + function apply(quad, x1, _, x2) { + if (!quad.value) return true; + + var x = quad.x - node.x, + y = quad.y - node.y, + w = x2 - x1, + l = x * x + y * y; + + // Apply the Barnes-Hut approximation if possible. + // Limit forces for very close nodes; randomize direction if coincident. + if (w * w / theta2 < l) { + if (l < distanceMax2) { + if (x === 0) x = jiggle(random), l += x * x; + if (y === 0) y = jiggle(random), l += y * y; + if (l < distanceMin2) l = Math.sqrt(distanceMin2 * l); + node.vx += x * quad.value * alpha / l; + node.vy += y * quad.value * alpha / l; + } + return true; + } + + // Otherwise, process points directly. + else if (quad.length || l >= distanceMax2) return; + + // Limit forces for very close nodes; randomize direction if coincident. + if (quad.data !== node || quad.next) { + if (x === 0) x = jiggle(random), l += x * x; + if (y === 0) y = jiggle(random), l += y * y; + if (l < distanceMin2) l = Math.sqrt(distanceMin2 * l); + } + + do if (quad.data !== node) { + w = strengths[quad.data.index] * alpha / l; + node.vx += x * w; + node.vy += y * w; + } while (quad = quad.next); + } + + force.initialize = function(_nodes, _random) { + nodes = _nodes; + random = _random; + initialize(); + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant(+_), initialize(), force) : strength; + }; + + force.distanceMin = function(_) { + return arguments.length ? (distanceMin2 = _ * _, force) : Math.sqrt(distanceMin2); + }; + + force.distanceMax = function(_) { + return arguments.length ? (distanceMax2 = _ * _, force) : Math.sqrt(distanceMax2); + }; + + force.theta = function(_) { + return arguments.length ? (theta2 = _ * _, force) : Math.sqrt(theta2); + }; + + return force; +} + +function radial(radius, x, y) { + var nodes, + strength = constant(0.1), + strengths, + radiuses; + + if (typeof radius !== "function") radius = constant(+radius); + if (x == null) x = 0; + if (y == null) y = 0; + + function force(alpha) { + for (var i = 0, n = nodes.length; i < n; ++i) { + var node = nodes[i], + dx = node.x - x || 1e-6, + dy = node.y - y || 1e-6, + r = Math.sqrt(dx * dx + dy * dy), + k = (radiuses[i] - r) * strengths[i] * alpha / r; + node.vx += dx * k; + node.vy += dy * k; + } + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length; + strengths = new Array(n); + radiuses = new Array(n); + for (i = 0; i < n; ++i) { + radiuses[i] = +radius(nodes[i], i, nodes); + strengths[i] = isNaN(radiuses[i]) ? 0 : +strength(nodes[i], i, nodes); + } + } + + force.initialize = function(_) { + nodes = _, initialize(); + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant(+_), initialize(), force) : strength; + }; + + force.radius = function(_) { + return arguments.length ? (radius = typeof _ === "function" ? _ : constant(+_), initialize(), force) : radius; + }; + + force.x = function(_) { + return arguments.length ? (x = +_, force) : x; + }; + + force.y = function(_) { + return arguments.length ? (y = +_, force) : y; + }; + + return force; +} + +function x(x) { + var strength = constant(0.1), + nodes, + strengths, + xz; + + if (typeof x !== "function") x = constant(x == null ? 0 : +x); + + function force(alpha) { + for (var i = 0, n = nodes.length, node; i < n; ++i) { + node = nodes[i], node.vx += (xz[i] - node.x) * strengths[i] * alpha; + } + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length; + strengths = new Array(n); + xz = new Array(n); + for (i = 0; i < n; ++i) { + strengths[i] = isNaN(xz[i] = +x(nodes[i], i, nodes)) ? 0 : +strength(nodes[i], i, nodes); + } + } + + force.initialize = function(_) { + nodes = _; + initialize(); + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant(+_), initialize(), force) : strength; + }; + + force.x = function(_) { + return arguments.length ? (x = typeof _ === "function" ? _ : constant(+_), initialize(), force) : x; + }; + + return force; +} + +function y(y) { + var strength = constant(0.1), + nodes, + strengths, + yz; + + if (typeof y !== "function") y = constant(y == null ? 0 : +y); + + function force(alpha) { + for (var i = 0, n = nodes.length, node; i < n; ++i) { + node = nodes[i], node.vy += (yz[i] - node.y) * strengths[i] * alpha; + } + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length; + strengths = new Array(n); + yz = new Array(n); + for (i = 0; i < n; ++i) { + strengths[i] = isNaN(yz[i] = +y(nodes[i], i, nodes)) ? 0 : +strength(nodes[i], i, nodes); + } + } + + force.initialize = function(_) { + nodes = _; + initialize(); + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant(+_), initialize(), force) : strength; + }; + + force.y = function(_) { + return arguments.length ? (y = typeof _ === "function" ? _ : constant(+_), initialize(), force) : y; + }; + + return force; +} + +exports.forceCenter = center; +exports.forceCollide = collide; +exports.forceLink = link; +exports.forceManyBody = manyBody; +exports.forceRadial = radial; +exports.forceSimulation = simulation; +exports.forceX = x; +exports.forceY = y; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-force/dist/d3-force.min.js b/frontend/node_modules/d3-force/dist/d3-force.min.js new file mode 100644 index 0000000..09ab9fb --- /dev/null +++ b/frontend/node_modules/d3-force/dist/d3-force.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-force/ v3.0.0 Copyright 2010-2021 Mike Bostock +!function(n,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports,require("d3-quadtree"),require("d3-dispatch"),require("d3-timer")):"function"==typeof define&&define.amd?define(["exports","d3-quadtree","d3-dispatch","d3-timer"],t):t((n="undefined"!=typeof globalThis?globalThis:n||self).d3=n.d3||{},n.d3,n.d3,n.d3)}(this,(function(n,t,e,r){"use strict";function i(n){return function(){return n}}function u(n){return 1e-6*(n()-.5)}function o(n){return n.x+n.vx}function f(n){return n.y+n.vy}function a(n){return n.index}function c(n,t){var e=n.get(t);if(!e)throw new Error("node not found: "+t);return e}const l=4294967296;function h(n){return n.x}function v(n){return n.y}var y=Math.PI*(3-Math.sqrt(5));n.forceCenter=function(n,t){var e,r=1;function i(){var i,u,o=e.length,f=0,a=0;for(i=0;iy+l||rd+l||ih.index){var v=y-o.x-o.vx,s=d-o.y-o.vy,p=v*v+s*s;pn.r&&(n.r=n[t].r)}function y(){if(e){var t,i,u=e.length;for(r=new Array(u),t=0;t[h(n,t,r),n])));for(i=0,o=new Array(a);i=l)){(n.data!==e||n.next)&&(0===h&&(g+=(h=u(r))*h),0===v&&(g+=(v=u(r))*v),g(n=(1664525*n+1013904223)%l)/l}();function g(){x(),v.call("tick",t),i1?(null==e?c.delete(n):c.set(n,p(e)),t):c.get(n)},find:function(t,e,r){var i,u,o,f,a,c=0,l=n.length;for(null==r?r=1/0:r*=r,c=0;c1?(v.on(n,e),t):v.on(n)}}},n.forceX=function(n){var t,e,r,u=i(.1);function o(n){for(var i,u=0,o=t.length;u=12" + } +} diff --git a/frontend/node_modules/d3-force/src/center.js b/frontend/node_modules/d3-force/src/center.js new file mode 100644 index 0000000..280d3e4 --- /dev/null +++ b/frontend/node_modules/d3-force/src/center.js @@ -0,0 +1,40 @@ +export default function(x, y) { + var nodes, strength = 1; + + if (x == null) x = 0; + if (y == null) y = 0; + + function force() { + var i, + n = nodes.length, + node, + sx = 0, + sy = 0; + + for (i = 0; i < n; ++i) { + node = nodes[i], sx += node.x, sy += node.y; + } + + for (sx = (sx / n - x) * strength, sy = (sy / n - y) * strength, i = 0; i < n; ++i) { + node = nodes[i], node.x -= sx, node.y -= sy; + } + } + + force.initialize = function(_) { + nodes = _; + }; + + force.x = function(_) { + return arguments.length ? (x = +_, force) : x; + }; + + force.y = function(_) { + return arguments.length ? (y = +_, force) : y; + }; + + force.strength = function(_) { + return arguments.length ? (strength = +_, force) : strength; + }; + + return force; +} diff --git a/frontend/node_modules/d3-force/src/collide.js b/frontend/node_modules/d3-force/src/collide.js new file mode 100644 index 0000000..8ebd8d9 --- /dev/null +++ b/frontend/node_modules/d3-force/src/collide.js @@ -0,0 +1,100 @@ +import {quadtree} from "d3-quadtree"; +import constant from "./constant.js"; +import jiggle from "./jiggle.js"; + +function x(d) { + return d.x + d.vx; +} + +function y(d) { + return d.y + d.vy; +} + +export default function(radius) { + var nodes, + radii, + random, + strength = 1, + iterations = 1; + + if (typeof radius !== "function") radius = constant(radius == null ? 1 : +radius); + + function force() { + var i, n = nodes.length, + tree, + node, + xi, + yi, + ri, + ri2; + + for (var k = 0; k < iterations; ++k) { + tree = quadtree(nodes, x, y).visitAfter(prepare); + for (i = 0; i < n; ++i) { + node = nodes[i]; + ri = radii[node.index], ri2 = ri * ri; + xi = node.x + node.vx; + yi = node.y + node.vy; + tree.visit(apply); + } + } + + function apply(quad, x0, y0, x1, y1) { + var data = quad.data, rj = quad.r, r = ri + rj; + if (data) { + if (data.index > node.index) { + var x = xi - data.x - data.vx, + y = yi - data.y - data.vy, + l = x * x + y * y; + if (l < r * r) { + if (x === 0) x = jiggle(random), l += x * x; + if (y === 0) y = jiggle(random), l += y * y; + l = (r - (l = Math.sqrt(l))) / l * strength; + node.vx += (x *= l) * (r = (rj *= rj) / (ri2 + rj)); + node.vy += (y *= l) * r; + data.vx -= x * (r = 1 - r); + data.vy -= y * r; + } + } + return; + } + return x0 > xi + r || x1 < xi - r || y0 > yi + r || y1 < yi - r; + } + } + + function prepare(quad) { + if (quad.data) return quad.r = radii[quad.data.index]; + for (var i = quad.r = 0; i < 4; ++i) { + if (quad[i] && quad[i].r > quad.r) { + quad.r = quad[i].r; + } + } + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length, node; + radii = new Array(n); + for (i = 0; i < n; ++i) node = nodes[i], radii[node.index] = +radius(node, i, nodes); + } + + force.initialize = function(_nodes, _random) { + nodes = _nodes; + random = _random; + initialize(); + }; + + force.iterations = function(_) { + return arguments.length ? (iterations = +_, force) : iterations; + }; + + force.strength = function(_) { + return arguments.length ? (strength = +_, force) : strength; + }; + + force.radius = function(_) { + return arguments.length ? (radius = typeof _ === "function" ? _ : constant(+_), initialize(), force) : radius; + }; + + return force; +} diff --git a/frontend/node_modules/d3-force/src/constant.js b/frontend/node_modules/d3-force/src/constant.js new file mode 100644 index 0000000..b7d42e7 --- /dev/null +++ b/frontend/node_modules/d3-force/src/constant.js @@ -0,0 +1,5 @@ +export default function(x) { + return function() { + return x; + }; +} diff --git a/frontend/node_modules/d3-force/src/index.js b/frontend/node_modules/d3-force/src/index.js new file mode 100644 index 0000000..a76c1c4 --- /dev/null +++ b/frontend/node_modules/d3-force/src/index.js @@ -0,0 +1,8 @@ +export {default as forceCenter} from "./center.js"; +export {default as forceCollide} from "./collide.js"; +export {default as forceLink} from "./link.js"; +export {default as forceManyBody} from "./manyBody.js"; +export {default as forceRadial} from "./radial.js"; +export {default as forceSimulation} from "./simulation.js"; +export {default as forceX} from "./x.js"; +export {default as forceY} from "./y.js"; diff --git a/frontend/node_modules/d3-force/src/jiggle.js b/frontend/node_modules/d3-force/src/jiggle.js new file mode 100644 index 0000000..00752b9 --- /dev/null +++ b/frontend/node_modules/d3-force/src/jiggle.js @@ -0,0 +1,3 @@ +export default function(random) { + return (random() - 0.5) * 1e-6; +} diff --git a/frontend/node_modules/d3-force/src/lcg.js b/frontend/node_modules/d3-force/src/lcg.js new file mode 100644 index 0000000..a13cf79 --- /dev/null +++ b/frontend/node_modules/d3-force/src/lcg.js @@ -0,0 +1,9 @@ +// https://en.wikipedia.org/wiki/Linear_congruential_generator#Parameters_in_common_use +const a = 1664525; +const c = 1013904223; +const m = 4294967296; // 2^32 + +export default function() { + let s = 1; + return () => (s = (a * s + c) % m) / m; +} diff --git a/frontend/node_modules/d3-force/src/link.js b/frontend/node_modules/d3-force/src/link.js new file mode 100644 index 0000000..df6afa6 --- /dev/null +++ b/frontend/node_modules/d3-force/src/link.js @@ -0,0 +1,117 @@ +import constant from "./constant.js"; +import jiggle from "./jiggle.js"; + +function index(d) { + return d.index; +} + +function find(nodeById, nodeId) { + var node = nodeById.get(nodeId); + if (!node) throw new Error("node not found: " + nodeId); + return node; +} + +export default function(links) { + var id = index, + strength = defaultStrength, + strengths, + distance = constant(30), + distances, + nodes, + count, + bias, + random, + iterations = 1; + + if (links == null) links = []; + + function defaultStrength(link) { + return 1 / Math.min(count[link.source.index], count[link.target.index]); + } + + function force(alpha) { + for (var k = 0, n = links.length; k < iterations; ++k) { + for (var i = 0, link, source, target, x, y, l, b; i < n; ++i) { + link = links[i], source = link.source, target = link.target; + x = target.x + target.vx - source.x - source.vx || jiggle(random); + y = target.y + target.vy - source.y - source.vy || jiggle(random); + l = Math.sqrt(x * x + y * y); + l = (l - distances[i]) / l * alpha * strengths[i]; + x *= l, y *= l; + target.vx -= x * (b = bias[i]); + target.vy -= y * b; + source.vx += x * (b = 1 - b); + source.vy += y * b; + } + } + } + + function initialize() { + if (!nodes) return; + + var i, + n = nodes.length, + m = links.length, + nodeById = new Map(nodes.map((d, i) => [id(d, i, nodes), d])), + link; + + for (i = 0, count = new Array(n); i < m; ++i) { + link = links[i], link.index = i; + if (typeof link.source !== "object") link.source = find(nodeById, link.source); + if (typeof link.target !== "object") link.target = find(nodeById, link.target); + count[link.source.index] = (count[link.source.index] || 0) + 1; + count[link.target.index] = (count[link.target.index] || 0) + 1; + } + + for (i = 0, bias = new Array(m); i < m; ++i) { + link = links[i], bias[i] = count[link.source.index] / (count[link.source.index] + count[link.target.index]); + } + + strengths = new Array(m), initializeStrength(); + distances = new Array(m), initializeDistance(); + } + + function initializeStrength() { + if (!nodes) return; + + for (var i = 0, n = links.length; i < n; ++i) { + strengths[i] = +strength(links[i], i, links); + } + } + + function initializeDistance() { + if (!nodes) return; + + for (var i = 0, n = links.length; i < n; ++i) { + distances[i] = +distance(links[i], i, links); + } + } + + force.initialize = function(_nodes, _random) { + nodes = _nodes; + random = _random; + initialize(); + }; + + force.links = function(_) { + return arguments.length ? (links = _, initialize(), force) : links; + }; + + force.id = function(_) { + return arguments.length ? (id = _, force) : id; + }; + + force.iterations = function(_) { + return arguments.length ? (iterations = +_, force) : iterations; + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant(+_), initializeStrength(), force) : strength; + }; + + force.distance = function(_) { + return arguments.length ? (distance = typeof _ === "function" ? _ : constant(+_), initializeDistance(), force) : distance; + }; + + return force; +} diff --git a/frontend/node_modules/d3-force/src/manyBody.js b/frontend/node_modules/d3-force/src/manyBody.js new file mode 100644 index 0000000..746a0d0 --- /dev/null +++ b/frontend/node_modules/d3-force/src/manyBody.js @@ -0,0 +1,116 @@ +import {quadtree} from "d3-quadtree"; +import constant from "./constant.js"; +import jiggle from "./jiggle.js"; +import {x, y} from "./simulation.js"; + +export default function() { + var nodes, + node, + random, + alpha, + strength = constant(-30), + strengths, + distanceMin2 = 1, + distanceMax2 = Infinity, + theta2 = 0.81; + + function force(_) { + var i, n = nodes.length, tree = quadtree(nodes, x, y).visitAfter(accumulate); + for (alpha = _, i = 0; i < n; ++i) node = nodes[i], tree.visit(apply); + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length, node; + strengths = new Array(n); + for (i = 0; i < n; ++i) node = nodes[i], strengths[node.index] = +strength(node, i, nodes); + } + + function accumulate(quad) { + var strength = 0, q, c, weight = 0, x, y, i; + + // For internal nodes, accumulate forces from child quadrants. + if (quad.length) { + for (x = y = i = 0; i < 4; ++i) { + if ((q = quad[i]) && (c = Math.abs(q.value))) { + strength += q.value, weight += c, x += c * q.x, y += c * q.y; + } + } + quad.x = x / weight; + quad.y = y / weight; + } + + // For leaf nodes, accumulate forces from coincident quadrants. + else { + q = quad; + q.x = q.data.x; + q.y = q.data.y; + do strength += strengths[q.data.index]; + while (q = q.next); + } + + quad.value = strength; + } + + function apply(quad, x1, _, x2) { + if (!quad.value) return true; + + var x = quad.x - node.x, + y = quad.y - node.y, + w = x2 - x1, + l = x * x + y * y; + + // Apply the Barnes-Hut approximation if possible. + // Limit forces for very close nodes; randomize direction if coincident. + if (w * w / theta2 < l) { + if (l < distanceMax2) { + if (x === 0) x = jiggle(random), l += x * x; + if (y === 0) y = jiggle(random), l += y * y; + if (l < distanceMin2) l = Math.sqrt(distanceMin2 * l); + node.vx += x * quad.value * alpha / l; + node.vy += y * quad.value * alpha / l; + } + return true; + } + + // Otherwise, process points directly. + else if (quad.length || l >= distanceMax2) return; + + // Limit forces for very close nodes; randomize direction if coincident. + if (quad.data !== node || quad.next) { + if (x === 0) x = jiggle(random), l += x * x; + if (y === 0) y = jiggle(random), l += y * y; + if (l < distanceMin2) l = Math.sqrt(distanceMin2 * l); + } + + do if (quad.data !== node) { + w = strengths[quad.data.index] * alpha / l; + node.vx += x * w; + node.vy += y * w; + } while (quad = quad.next); + } + + force.initialize = function(_nodes, _random) { + nodes = _nodes; + random = _random; + initialize(); + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant(+_), initialize(), force) : strength; + }; + + force.distanceMin = function(_) { + return arguments.length ? (distanceMin2 = _ * _, force) : Math.sqrt(distanceMin2); + }; + + force.distanceMax = function(_) { + return arguments.length ? (distanceMax2 = _ * _, force) : Math.sqrt(distanceMax2); + }; + + force.theta = function(_) { + return arguments.length ? (theta2 = _ * _, force) : Math.sqrt(theta2); + }; + + return force; +} diff --git a/frontend/node_modules/d3-force/src/radial.js b/frontend/node_modules/d3-force/src/radial.js new file mode 100644 index 0000000..609516b --- /dev/null +++ b/frontend/node_modules/d3-force/src/radial.js @@ -0,0 +1,57 @@ +import constant from "./constant.js"; + +export default function(radius, x, y) { + var nodes, + strength = constant(0.1), + strengths, + radiuses; + + if (typeof radius !== "function") radius = constant(+radius); + if (x == null) x = 0; + if (y == null) y = 0; + + function force(alpha) { + for (var i = 0, n = nodes.length; i < n; ++i) { + var node = nodes[i], + dx = node.x - x || 1e-6, + dy = node.y - y || 1e-6, + r = Math.sqrt(dx * dx + dy * dy), + k = (radiuses[i] - r) * strengths[i] * alpha / r; + node.vx += dx * k; + node.vy += dy * k; + } + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length; + strengths = new Array(n); + radiuses = new Array(n); + for (i = 0; i < n; ++i) { + radiuses[i] = +radius(nodes[i], i, nodes); + strengths[i] = isNaN(radiuses[i]) ? 0 : +strength(nodes[i], i, nodes); + } + } + + force.initialize = function(_) { + nodes = _, initialize(); + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant(+_), initialize(), force) : strength; + }; + + force.radius = function(_) { + return arguments.length ? (radius = typeof _ === "function" ? _ : constant(+_), initialize(), force) : radius; + }; + + force.x = function(_) { + return arguments.length ? (x = +_, force) : x; + }; + + force.y = function(_) { + return arguments.length ? (y = +_, force) : y; + }; + + return force; +} diff --git a/frontend/node_modules/d3-force/src/simulation.js b/frontend/node_modules/d3-force/src/simulation.js new file mode 100644 index 0000000..7a1ff82 --- /dev/null +++ b/frontend/node_modules/d3-force/src/simulation.js @@ -0,0 +1,156 @@ +import {dispatch} from "d3-dispatch"; +import {timer} from "d3-timer"; +import lcg from "./lcg.js"; + +export function x(d) { + return d.x; +} + +export function y(d) { + return d.y; +} + +var initialRadius = 10, + initialAngle = Math.PI * (3 - Math.sqrt(5)); + +export default function(nodes) { + var simulation, + alpha = 1, + alphaMin = 0.001, + alphaDecay = 1 - Math.pow(alphaMin, 1 / 300), + alphaTarget = 0, + velocityDecay = 0.6, + forces = new Map(), + stepper = timer(step), + event = dispatch("tick", "end"), + random = lcg(); + + if (nodes == null) nodes = []; + + function step() { + tick(); + event.call("tick", simulation); + if (alpha < alphaMin) { + stepper.stop(); + event.call("end", simulation); + } + } + + function tick(iterations) { + var i, n = nodes.length, node; + + if (iterations === undefined) iterations = 1; + + for (var k = 0; k < iterations; ++k) { + alpha += (alphaTarget - alpha) * alphaDecay; + + forces.forEach(function(force) { + force(alpha); + }); + + for (i = 0; i < n; ++i) { + node = nodes[i]; + if (node.fx == null) node.x += node.vx *= velocityDecay; + else node.x = node.fx, node.vx = 0; + if (node.fy == null) node.y += node.vy *= velocityDecay; + else node.y = node.fy, node.vy = 0; + } + } + + return simulation; + } + + function initializeNodes() { + for (var i = 0, n = nodes.length, node; i < n; ++i) { + node = nodes[i], node.index = i; + if (node.fx != null) node.x = node.fx; + if (node.fy != null) node.y = node.fy; + if (isNaN(node.x) || isNaN(node.y)) { + var radius = initialRadius * Math.sqrt(0.5 + i), angle = i * initialAngle; + node.x = radius * Math.cos(angle); + node.y = radius * Math.sin(angle); + } + if (isNaN(node.vx) || isNaN(node.vy)) { + node.vx = node.vy = 0; + } + } + } + + function initializeForce(force) { + if (force.initialize) force.initialize(nodes, random); + return force; + } + + initializeNodes(); + + return simulation = { + tick: tick, + + restart: function() { + return stepper.restart(step), simulation; + }, + + stop: function() { + return stepper.stop(), simulation; + }, + + nodes: function(_) { + return arguments.length ? (nodes = _, initializeNodes(), forces.forEach(initializeForce), simulation) : nodes; + }, + + alpha: function(_) { + return arguments.length ? (alpha = +_, simulation) : alpha; + }, + + alphaMin: function(_) { + return arguments.length ? (alphaMin = +_, simulation) : alphaMin; + }, + + alphaDecay: function(_) { + return arguments.length ? (alphaDecay = +_, simulation) : +alphaDecay; + }, + + alphaTarget: function(_) { + return arguments.length ? (alphaTarget = +_, simulation) : alphaTarget; + }, + + velocityDecay: function(_) { + return arguments.length ? (velocityDecay = 1 - _, simulation) : 1 - velocityDecay; + }, + + randomSource: function(_) { + return arguments.length ? (random = _, forces.forEach(initializeForce), simulation) : random; + }, + + force: function(name, _) { + return arguments.length > 1 ? ((_ == null ? forces.delete(name) : forces.set(name, initializeForce(_))), simulation) : forces.get(name); + }, + + find: function(x, y, radius) { + var i = 0, + n = nodes.length, + dx, + dy, + d2, + node, + closest; + + if (radius == null) radius = Infinity; + else radius *= radius; + + for (i = 0; i < n; ++i) { + node = nodes[i]; + dx = x - node.x; + dy = y - node.y; + d2 = dx * dx + dy * dy; + if (d2 < radius) closest = node, radius = d2; + } + + return closest; + }, + + on: function(name, _) { + return arguments.length > 1 ? (event.on(name, _), simulation) : event.on(name); + } + }; +} diff --git a/frontend/node_modules/d3-force/src/x.js b/frontend/node_modules/d3-force/src/x.js new file mode 100644 index 0000000..2e7a821 --- /dev/null +++ b/frontend/node_modules/d3-force/src/x.js @@ -0,0 +1,41 @@ +import constant from "./constant.js"; + +export default function(x) { + var strength = constant(0.1), + nodes, + strengths, + xz; + + if (typeof x !== "function") x = constant(x == null ? 0 : +x); + + function force(alpha) { + for (var i = 0, n = nodes.length, node; i < n; ++i) { + node = nodes[i], node.vx += (xz[i] - node.x) * strengths[i] * alpha; + } + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length; + strengths = new Array(n); + xz = new Array(n); + for (i = 0; i < n; ++i) { + strengths[i] = isNaN(xz[i] = +x(nodes[i], i, nodes)) ? 0 : +strength(nodes[i], i, nodes); + } + } + + force.initialize = function(_) { + nodes = _; + initialize(); + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant(+_), initialize(), force) : strength; + }; + + force.x = function(_) { + return arguments.length ? (x = typeof _ === "function" ? _ : constant(+_), initialize(), force) : x; + }; + + return force; +} diff --git a/frontend/node_modules/d3-force/src/y.js b/frontend/node_modules/d3-force/src/y.js new file mode 100644 index 0000000..5fcde67 --- /dev/null +++ b/frontend/node_modules/d3-force/src/y.js @@ -0,0 +1,41 @@ +import constant from "./constant.js"; + +export default function(y) { + var strength = constant(0.1), + nodes, + strengths, + yz; + + if (typeof y !== "function") y = constant(y == null ? 0 : +y); + + function force(alpha) { + for (var i = 0, n = nodes.length, node; i < n; ++i) { + node = nodes[i], node.vy += (yz[i] - node.y) * strengths[i] * alpha; + } + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length; + strengths = new Array(n); + yz = new Array(n); + for (i = 0; i < n; ++i) { + strengths[i] = isNaN(yz[i] = +y(nodes[i], i, nodes)) ? 0 : +strength(nodes[i], i, nodes); + } + } + + force.initialize = function(_) { + nodes = _; + initialize(); + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant(+_), initialize(), force) : strength; + }; + + force.y = function(_) { + return arguments.length ? (y = typeof _ === "function" ? _ : constant(+_), initialize(), force) : y; + }; + + return force; +} diff --git a/frontend/node_modules/d3-format/LICENSE b/frontend/node_modules/d3-format/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-format/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-format/README.md b/frontend/node_modules/d3-format/README.md new file mode 100644 index 0000000..9c7e904 --- /dev/null +++ b/frontend/node_modules/d3-format/README.md @@ -0,0 +1,350 @@ +# d3-format + +Ever noticed how sometimes JavaScript doesn’t display numbers the way you expect? Like, you tried to print tenths with a simple loop: + +```js +for (let i = 0; i < 10; ++i) { + console.log(0.1 * i); +} +``` + +And you got this: + +```js +0 +0.1 +0.2 +0.30000000000000004 +0.4 +0.5 +0.6000000000000001 +0.7000000000000001 +0.8 +0.9 +``` + +Welcome to [binary floating point](https://en.wikipedia.org/wiki/Double-precision_floating-point_format)! ಠ_ಠ + +Yet rounding error is not the only reason to customize number formatting. A table of numbers should be formatted consistently for comparison; above, 0.0 would be better than 0. Large numbers should have grouped digits (e.g., 42,000) or be in scientific or metric notation (4.2e+4, 42k). Currencies should have fixed precision ($3.50). Reported numerical results should be rounded to significant digits (4021 becomes 4000). Number formats should appropriate to the reader’s locale (42.000,00 or 42,000.00). The list goes on. + +Formatting numbers for human consumption is the purpose of d3-format, which is modeled after Python 3’s [format specification mini-language](https://docs.python.org/3/library/string.html#format-specification-mini-language) ([PEP 3101](https://www.python.org/dev/peps/pep-3101/)). Revisiting the example above: + +```js +const f = d3.format(".1f"); +for (let i = 0; i < 10; ++i) { + console.log(f(0.1 * i)); +} +``` + +Now you get this: + +```js +0.0 +0.1 +0.2 +0.3 +0.4 +0.5 +0.6 +0.7 +0.8 +0.9 +``` + +But d3-format is much more than an alias for [number.toFixed](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Number/toFixed)! A few more examples: + +```js +d3.format(".0%")(0.123); // rounded percentage, "12%" +d3.format("($.2f")(-3.5); // localized fixed-point currency, "(£3.50)" +d3.format("+20")(42); // space-filled and signed, " +42" +d3.format(".^20")(42); // dot-filled and centered, ".........42........." +d3.format(".2s")(42e6); // SI-prefix with two significant digits, "42M" +d3.format("#x")(48879); // prefixed lowercase hexadecimal, "0xbeef" +d3.format(",.2r")(4223); // grouped thousands with two significant digits, "4,200" +``` + +See [*locale*.format](#locale_format) for a detailed specification, and try running [d3.formatSpecifier](#formatSpecifier) on the above formats to decode their meaning. + +## Installing + +If you use npm, `npm install d3-format`. You can also download the [latest release on GitHub](https://github.com/d3/d3-format/releases/latest). In modern browsers, you can import d3-format from Skypack: + +```html + +``` + +For legacy environments, you can load d3-format’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +Locale files are published to npm and can be loaded using [d3.json](https://github.com/d3/d3-fetch/blob/master/README.md#json). For example, to set Russian as the default locale: + +```js +const locale = await d3.json("https://cdn.jsdelivr.net/npm/d3-format@3/locale/ru-RU.json"); +d3.formatDefaultLocale(locale); +const f = d3.format("$,"); +console.log(f(1234.56)); // 1 234,56 руб. +``` + +[Try d3-format in your browser.](https://observablehq.com/@d3/d3-format) + +## API Reference + +# d3.format(specifier) [<>](https://github.com/d3/d3-format/blob/main/src/defaultLocale.js#L4 "Source") + +An alias for [*locale*.format](#locale_format) on the [default locale](#formatDefaultLocale). + +# d3.formatPrefix(specifier, value) [<>](https://github.com/d3/d3-format/blob/main/src/defaultLocale.js#L5 "Source") + +An alias for [*locale*.formatPrefix](#locale_formatPrefix) on the [default locale](#formatDefaultLocale). + +# locale.format(specifier) [<>](https://github.com/d3/d3-format/blob/main/src/locale.js#L18 "Source") + +Returns a new format function for the given string *specifier*. The returned function takes a number as the only argument, and returns a string representing the formatted number. The general form of a specifier is: + +``` +[​[fill]align][sign][symbol][0][width][,][.precision][~][type] +``` + +The *fill* can be any character. The presence of a fill character is signaled by the *align* character following it, which must be one of the following: + +* `>` - Forces the field to be right-aligned within the available space. (Default behavior). +* `<` - Forces the field to be left-aligned within the available space. +* `^` - Forces the field to be centered within the available space. +* `=` - like `>`, but with any sign and symbol to the left of any padding. + +The *sign* can be: + +* `-` - nothing for zero or positive and a minus sign for negative. (Default behavior.) +* `+` - a plus sign for zero or positive and a minus sign for negative. +* `(` - nothing for zero or positive and parentheses for negative. +* ` ` (space) - a space for zero or positive and a minus sign for negative. + +The *symbol* can be: + +* `$` - apply currency symbols per the locale definition. +* `#` - for binary, octal, or hexadecimal notation, prefix by `0b`, `0o`, or `0x`, respectively. + +The *zero* (`0`) option enables zero-padding; this implicitly sets *fill* to `0` and *align* to `=`. The *width* defines the minimum field width; if not specified, then the width will be determined by the content. The *comma* (`,`) option enables the use of a group separator, such as a comma for thousands. + +Depending on the *type*, the *precision* either indicates the number of digits that follow the decimal point (types `f` and `%`), or the number of significant digits (types `​`, `e`, `g`, `r`, `s` and `p`). If the precision is not specified, it defaults to 6 for all types except `​` (none), which defaults to 12. Precision is ignored for integer formats (types `b`, `o`, `d`, `x`, and `X`) and character data (type `c`). See [precisionFixed](#precisionFixed) and [precisionRound](#precisionRound) for help picking an appropriate precision. + +The `~` option trims insignificant trailing zeros across all format types. This is most commonly used in conjunction with types `r`, `e`, `s` and `%`. For example: + +```js +d3.format("s")(1500); // "1.50000k" +d3.format("~s")(1500); // "1.5k" +``` + +The available *type* values are: + +* `e` - exponent notation. +* `f` - fixed point notation. +* `g` - either decimal or exponent notation, rounded to significant digits. +* `r` - decimal notation, rounded to significant digits. +* `s` - decimal notation with an [SI prefix](#locale_formatPrefix), rounded to significant digits. +* `%` - multiply by 100, and then decimal notation with a percent sign. +* `p` - multiply by 100, round to significant digits, and then decimal notation with a percent sign. +* `b` - binary notation, rounded to integer. +* `o` - octal notation, rounded to integer. +* `d` - decimal notation, rounded to integer. +* `x` - hexadecimal notation, using lower-case letters, rounded to integer. +* `X` - hexadecimal notation, using upper-case letters, rounded to integer. +* `c` - character data, for a string of text. + +The type `​` (none) is also supported as shorthand for `~g` (with a default precision of 12 instead of 6), and the type `n` is shorthand for `,g`. For the `g`, `n` and `​` (none) types, decimal notation is used if the resulting string would have *precision* or fewer digits; otherwise, exponent notation is used. For example: + +```js +d3.format(".2")(42); // "42" +d3.format(".2")(4.2); // "4.2" +d3.format(".1")(42); // "4e+1" +d3.format(".1")(4.2); // "4" +``` + +# locale.formatPrefix(specifier, value) [<>](https://github.com/d3/d3-format/blob/main/src/locale.js#L127 "Source") + +Equivalent to [*locale*.format](#locale_format), except the returned function will convert values to the units of the appropriate [SI prefix](https://en.wikipedia.org/wiki/Metric_prefix#List_of_SI_prefixes) for the specified numeric reference *value* before formatting in fixed point notation. The following prefixes are supported: + +* `y` - yocto, 10⁻²⁴ +* `z` - zepto, 10⁻²¹ +* `a` - atto, 10⁻¹⁸ +* `f` - femto, 10⁻¹⁵ +* `p` - pico, 10⁻¹² +* `n` - nano, 10⁻⁹ +* `µ` - micro, 10⁻⁶ +* `m` - milli, 10⁻³ +* `​` (none) - 10⁰ +* `k` - kilo, 10³ +* `M` - mega, 10⁶ +* `G` - giga, 10⁹ +* `T` - tera, 10¹² +* `P` - peta, 10¹⁵ +* `E` - exa, 10¹⁸ +* `Z` - zetta, 10²¹ +* `Y` - yotta, 10²⁴ + +Unlike [*locale*.format](#locale_format) with the `s` format type, this method returns a formatter with a consistent SI prefix, rather than computing the prefix dynamically for each number. In addition, the *precision* for the given *specifier* represents the number of digits past the decimal point (as with `f` fixed point notation), not the number of significant digits. For example: + +```js +const f = d3.formatPrefix(",.0", 1e-6); +f(0.00042); // "420µ" +f(0.0042); // "4,200µ" +``` + +This method is useful when formatting multiple numbers in the same units for easy comparison. See [precisionPrefix](#precisionPrefix) for help picking an appropriate precision, and [bl.ocks.org/9764126](http://bl.ocks.org/mbostock/9764126) for an example. + +# d3.formatSpecifier(specifier) [<>](https://github.com/d3/d3-format/blob/main/src/formatSpecifier.js "Source") + +Parses the specified *specifier*, returning an object with exposed fields that correspond to the [format specification mini-language](#locale_format) and a toString method that reconstructs the specifier. For example, `formatSpecifier("s")` returns: + +```js +FormatSpecifier { + "fill": " ", + "align": ">", + "sign": "-", + "symbol": "", + "zero": false, + "width": undefined, + "comma": false, + "precision": undefined, + "trim": false, + "type": "s" +} +``` + +This method is useful for understanding how format specifiers are parsed and for deriving new specifiers. For example, you might compute an appropriate precision based on the numbers you want to format using [precisionFixed](#precisionFixed) and then create a new format: + +```js +const s = d3.formatSpecifier("f"); +s.precision = d3.precisionFixed(0.01); +const f = d3.format(s); +f(42); // "42.00"; +``` + +# new d3.FormatSpecifier(specifier) [<>](https://github.com/d3/d3-format/blob/main/src/formatSpecifier.js "Source") + +Given the specified *specifier* object, returning an object with exposed fields that correspond to the [format specification mini-language](#locale_format) and a toString method that reconstructs the specifier. For example, `new FormatSpecifier({type: "s"})` returns: + +```js +FormatSpecifier { + "fill": " ", + "align": ">", + "sign": "-", + "symbol": "", + "zero": false, + "width": undefined, + "comma": false, + "precision": undefined, + "trim": false, + "type": "s" +} +``` + +# d3.precisionFixed(step) [<>](https://github.com/d3/d3-format/blob/main/src/precisionFixed.js "Source") + +Returns a suggested decimal precision for fixed point notation given the specified numeric *step* value. The *step* represents the minimum absolute difference between values that will be formatted. (This assumes that the values to be formatted are also multiples of *step*.) For example, given the numbers 1, 1.5, and 2, the *step* should be 0.5 and the suggested precision is 1: + +```js +const p = d3.precisionFixed(0.5); +const f = d3.format("." + p + "f"); +f(1); // "1.0" +f(1.5); // "1.5" +f(2); // "2.0" +``` + +Whereas for the numbers 1, 2 and 3, the *step* should be 1 and the suggested precision is 0: + +```js +const p = d3.precisionFixed(1); +const f = d3.format("." + p + "f"); +f(1); // "1" +f(2); // "2" +f(3); // "3" +``` + +Note: for the `%` format type, subtract two: + +```js +const p = Math.max(0, d3.precisionFixed(0.05) - 2); +const f = d3.format("." + p + "%"); +f(0.45); // "45%" +f(0.50); // "50%" +f(0.55); // "55%" +``` + +# d3.precisionPrefix(step, value) [<>](https://github.com/d3/d3-format/blob/main/src/precisionPrefix.js "Source") + +Returns a suggested decimal precision for use with [*locale*.formatPrefix](#locale_formatPrefix) given the specified numeric *step* and reference *value*. The *step* represents the minimum absolute difference between values that will be formatted, and *value* determines which SI prefix will be used. (This assumes that the values to be formatted are also multiples of *step*.) For example, given the numbers 1.1e6, 1.2e6, and 1.3e6, the *step* should be 1e5, the *value* could be 1.3e6, and the suggested precision is 1: + +```js +const p = d3.precisionPrefix(1e5, 1.3e6); +const f = d3.formatPrefix("." + p, 1.3e6); +f(1.1e6); // "1.1M" +f(1.2e6); // "1.2M" +f(1.3e6); // "1.3M" +``` + +# d3.precisionRound(step, max) [<>](https://github.com/d3/d3-format/blob/main/src/precisionRound.js "Source") + +Returns a suggested decimal precision for format types that round to significant digits given the specified numeric *step* and *max* values. The *step* represents the minimum absolute difference between values that will be formatted, and the *max* represents the largest absolute value that will be formatted. (This assumes that the values to be formatted are also multiples of *step*.) For example, given the numbers 0.99, 1.0, and 1.01, the *step* should be 0.01, the *max* should be 1.01, and the suggested precision is 3: + +```js +const p = d3.precisionRound(0.01, 1.01); +const f = d3.format("." + p + "r"); +f(0.99); // "0.990" +f(1.0); // "1.00" +f(1.01); // "1.01" +``` + +Whereas for the numbers 0.9, 1.0, and 1.1, the *step* should be 0.1, the *max* should be 1.1, and the suggested precision is 2: + +```js +const p = d3.precisionRound(0.1, 1.1); +const f = d3.format("." + p + "r"); +f(0.9); // "0.90" +f(1.0); // "1.0" +f(1.1); // "1.1" +``` + +Note: for the `e` format type, subtract one: + +```js +const p = Math.max(0, d3.precisionRound(0.01, 1.01) - 1); +const f = d3.format("." + p + "e"); +f(0.01); // "1.00e-2" +f(1.01); // "1.01e+0" +``` + +### Locales + +# d3.formatLocale(definition) [<>](https://github.com/d3/d3-format/blob/main/src/locale.js "Source") + +Returns a *locale* object for the specified *definition* with [*locale*.format](#locale_format) and [*locale*.formatPrefix](#locale_formatPrefix) methods. The *definition* must include the following properties: + +* `decimal` - the decimal point (e.g., `"."`). +* `thousands` - the group separator (e.g., `","`). +* `grouping` - the array of group sizes (e.g., `[3]`), cycled as needed. +* `currency` - the currency prefix and suffix (e.g., `["$", ""]`). +* `numerals` - optional; an array of ten strings to replace the numerals 0-9. +* `percent` - optional; the percent sign (defaults to `"%"`). +* `minus` - optional; the minus sign (defaults to `"−"`). +* `nan` - optional; the not-a-number value (defaults `"NaN"`). + +Note that the *thousands* property is a misnomer, as the grouping definition allows groups other than thousands. + +# d3.formatDefaultLocale(definition) [<>](https://github.com/d3/d3-format/blob/main/src/defaultLocale.js "Source") + +Equivalent to [d3.formatLocale](#formatLocale), except it also redefines [d3.format](#format) and [d3.formatPrefix](#formatPrefix) to the new locale’s [*locale*.format](#locale_format) and [*locale*.formatPrefix](#locale_formatPrefix). If you do not set a default locale, it defaults to [U.S. English](https://github.com/d3/d3-format/blob/main/locale/en-US.json). diff --git a/frontend/node_modules/d3-format/dist/d3-format.js b/frontend/node_modules/d3-format/dist/d3-format.js new file mode 100644 index 0000000..9740235 --- /dev/null +++ b/frontend/node_modules/d3-format/dist/d3-format.js @@ -0,0 +1,345 @@ +// https://d3js.org/d3-format/ v3.1.0 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +})(this, (function (exports) { 'use strict'; + +function formatDecimal(x) { + return Math.abs(x = Math.round(x)) >= 1e21 + ? x.toLocaleString("en").replace(/,/g, "") + : x.toString(10); +} + +// Computes the decimal coefficient and exponent of the specified number x with +// significant digits p, where x is positive and p is in [1, 21] or undefined. +// For example, formatDecimalParts(1.23) returns ["123", 0]. +function formatDecimalParts(x, p) { + if ((i = (x = p ? x.toExponential(p - 1) : x.toExponential()).indexOf("e")) < 0) return null; // NaN, ±Infinity + var i, coefficient = x.slice(0, i); + + // The string returned by toExponential either has the form \d\.\d+e[-+]\d+ + // (e.g., 1.2e+3) or the form \de[-+]\d+ (e.g., 1e+3). + return [ + coefficient.length > 1 ? coefficient[0] + coefficient.slice(2) : coefficient, + +x.slice(i + 1) + ]; +} + +function exponent(x) { + return x = formatDecimalParts(Math.abs(x)), x ? x[1] : NaN; +} + +function formatGroup(grouping, thousands) { + return function(value, width) { + var i = value.length, + t = [], + j = 0, + g = grouping[0], + length = 0; + + while (i > 0 && g > 0) { + if (length + g + 1 > width) g = Math.max(1, width - length); + t.push(value.substring(i -= g, i + g)); + if ((length += g + 1) > width) break; + g = grouping[j = (j + 1) % grouping.length]; + } + + return t.reverse().join(thousands); + }; +} + +function formatNumerals(numerals) { + return function(value) { + return value.replace(/[0-9]/g, function(i) { + return numerals[+i]; + }); + }; +} + +// [[fill]align][sign][symbol][0][width][,][.precision][~][type] +var re = /^(?:(.)?([<>=^]))?([+\-( ])?([$#])?(0)?(\d+)?(,)?(\.\d+)?(~)?([a-z%])?$/i; + +function formatSpecifier(specifier) { + if (!(match = re.exec(specifier))) throw new Error("invalid format: " + specifier); + var match; + return new FormatSpecifier({ + fill: match[1], + align: match[2], + sign: match[3], + symbol: match[4], + zero: match[5], + width: match[6], + comma: match[7], + precision: match[8] && match[8].slice(1), + trim: match[9], + type: match[10] + }); +} + +formatSpecifier.prototype = FormatSpecifier.prototype; // instanceof + +function FormatSpecifier(specifier) { + this.fill = specifier.fill === undefined ? " " : specifier.fill + ""; + this.align = specifier.align === undefined ? ">" : specifier.align + ""; + this.sign = specifier.sign === undefined ? "-" : specifier.sign + ""; + this.symbol = specifier.symbol === undefined ? "" : specifier.symbol + ""; + this.zero = !!specifier.zero; + this.width = specifier.width === undefined ? undefined : +specifier.width; + this.comma = !!specifier.comma; + this.precision = specifier.precision === undefined ? undefined : +specifier.precision; + this.trim = !!specifier.trim; + this.type = specifier.type === undefined ? "" : specifier.type + ""; +} + +FormatSpecifier.prototype.toString = function() { + return this.fill + + this.align + + this.sign + + this.symbol + + (this.zero ? "0" : "") + + (this.width === undefined ? "" : Math.max(1, this.width | 0)) + + (this.comma ? "," : "") + + (this.precision === undefined ? "" : "." + Math.max(0, this.precision | 0)) + + (this.trim ? "~" : "") + + this.type; +}; + +// Trims insignificant zeros, e.g., replaces 1.2000k with 1.2k. +function formatTrim(s) { + out: for (var n = s.length, i = 1, i0 = -1, i1; i < n; ++i) { + switch (s[i]) { + case ".": i0 = i1 = i; break; + case "0": if (i0 === 0) i0 = i; i1 = i; break; + default: if (!+s[i]) break out; if (i0 > 0) i0 = 0; break; + } + } + return i0 > 0 ? s.slice(0, i0) + s.slice(i1 + 1) : s; +} + +var prefixExponent; + +function formatPrefixAuto(x, p) { + var d = formatDecimalParts(x, p); + if (!d) return x + ""; + var coefficient = d[0], + exponent = d[1], + i = exponent - (prefixExponent = Math.max(-8, Math.min(8, Math.floor(exponent / 3))) * 3) + 1, + n = coefficient.length; + return i === n ? coefficient + : i > n ? coefficient + new Array(i - n + 1).join("0") + : i > 0 ? coefficient.slice(0, i) + "." + coefficient.slice(i) + : "0." + new Array(1 - i).join("0") + formatDecimalParts(x, Math.max(0, p + i - 1))[0]; // less than 1y! +} + +function formatRounded(x, p) { + var d = formatDecimalParts(x, p); + if (!d) return x + ""; + var coefficient = d[0], + exponent = d[1]; + return exponent < 0 ? "0." + new Array(-exponent).join("0") + coefficient + : coefficient.length > exponent + 1 ? coefficient.slice(0, exponent + 1) + "." + coefficient.slice(exponent + 1) + : coefficient + new Array(exponent - coefficient.length + 2).join("0"); +} + +var formatTypes = { + "%": (x, p) => (x * 100).toFixed(p), + "b": (x) => Math.round(x).toString(2), + "c": (x) => x + "", + "d": formatDecimal, + "e": (x, p) => x.toExponential(p), + "f": (x, p) => x.toFixed(p), + "g": (x, p) => x.toPrecision(p), + "o": (x) => Math.round(x).toString(8), + "p": (x, p) => formatRounded(x * 100, p), + "r": formatRounded, + "s": formatPrefixAuto, + "X": (x) => Math.round(x).toString(16).toUpperCase(), + "x": (x) => Math.round(x).toString(16) +}; + +function identity(x) { + return x; +} + +var map = Array.prototype.map, + prefixes = ["y","z","a","f","p","n","µ","m","","k","M","G","T","P","E","Z","Y"]; + +function formatLocale(locale) { + var group = locale.grouping === undefined || locale.thousands === undefined ? identity : formatGroup(map.call(locale.grouping, Number), locale.thousands + ""), + currencyPrefix = locale.currency === undefined ? "" : locale.currency[0] + "", + currencySuffix = locale.currency === undefined ? "" : locale.currency[1] + "", + decimal = locale.decimal === undefined ? "." : locale.decimal + "", + numerals = locale.numerals === undefined ? identity : formatNumerals(map.call(locale.numerals, String)), + percent = locale.percent === undefined ? "%" : locale.percent + "", + minus = locale.minus === undefined ? "−" : locale.minus + "", + nan = locale.nan === undefined ? "NaN" : locale.nan + ""; + + function newFormat(specifier) { + specifier = formatSpecifier(specifier); + + var fill = specifier.fill, + align = specifier.align, + sign = specifier.sign, + symbol = specifier.symbol, + zero = specifier.zero, + width = specifier.width, + comma = specifier.comma, + precision = specifier.precision, + trim = specifier.trim, + type = specifier.type; + + // The "n" type is an alias for ",g". + if (type === "n") comma = true, type = "g"; + + // The "" type, and any invalid type, is an alias for ".12~g". + else if (!formatTypes[type]) precision === undefined && (precision = 12), trim = true, type = "g"; + + // If zero fill is specified, padding goes after sign and before digits. + if (zero || (fill === "0" && align === "=")) zero = true, fill = "0", align = "="; + + // Compute the prefix and suffix. + // For SI-prefix, the suffix is lazily computed. + var prefix = symbol === "$" ? currencyPrefix : symbol === "#" && /[boxX]/.test(type) ? "0" + type.toLowerCase() : "", + suffix = symbol === "$" ? currencySuffix : /[%p]/.test(type) ? percent : ""; + + // What format function should we use? + // Is this an integer type? + // Can this type generate exponential notation? + var formatType = formatTypes[type], + maybeSuffix = /[defgprs%]/.test(type); + + // Set the default precision if not specified, + // or clamp the specified precision to the supported range. + // For significant precision, it must be in [1, 21]. + // For fixed precision, it must be in [0, 20]. + precision = precision === undefined ? 6 + : /[gprs]/.test(type) ? Math.max(1, Math.min(21, precision)) + : Math.max(0, Math.min(20, precision)); + + function format(value) { + var valuePrefix = prefix, + valueSuffix = suffix, + i, n, c; + + if (type === "c") { + valueSuffix = formatType(value) + valueSuffix; + value = ""; + } else { + value = +value; + + // Determine the sign. -0 is not less than 0, but 1 / -0 is! + var valueNegative = value < 0 || 1 / value < 0; + + // Perform the initial formatting. + value = isNaN(value) ? nan : formatType(Math.abs(value), precision); + + // Trim insignificant zeros. + if (trim) value = formatTrim(value); + + // If a negative value rounds to zero after formatting, and no explicit positive sign is requested, hide the sign. + if (valueNegative && +value === 0 && sign !== "+") valueNegative = false; + + // Compute the prefix and suffix. + valuePrefix = (valueNegative ? (sign === "(" ? sign : minus) : sign === "-" || sign === "(" ? "" : sign) + valuePrefix; + valueSuffix = (type === "s" ? prefixes[8 + prefixExponent / 3] : "") + valueSuffix + (valueNegative && sign === "(" ? ")" : ""); + + // Break the formatted value into the integer “value” part that can be + // grouped, and fractional or exponential “suffix” part that is not. + if (maybeSuffix) { + i = -1, n = value.length; + while (++i < n) { + if (c = value.charCodeAt(i), 48 > c || c > 57) { + valueSuffix = (c === 46 ? decimal + value.slice(i + 1) : value.slice(i)) + valueSuffix; + value = value.slice(0, i); + break; + } + } + } + } + + // If the fill character is not "0", grouping is applied before padding. + if (comma && !zero) value = group(value, Infinity); + + // Compute the padding. + var length = valuePrefix.length + value.length + valueSuffix.length, + padding = length < width ? new Array(width - length + 1).join(fill) : ""; + + // If the fill character is "0", grouping is applied after padding. + if (comma && zero) value = group(padding + value, padding.length ? width - valueSuffix.length : Infinity), padding = ""; + + // Reconstruct the final output based on the desired alignment. + switch (align) { + case "<": value = valuePrefix + value + valueSuffix + padding; break; + case "=": value = valuePrefix + padding + value + valueSuffix; break; + case "^": value = padding.slice(0, length = padding.length >> 1) + valuePrefix + value + valueSuffix + padding.slice(length); break; + default: value = padding + valuePrefix + value + valueSuffix; break; + } + + return numerals(value); + } + + format.toString = function() { + return specifier + ""; + }; + + return format; + } + + function formatPrefix(specifier, value) { + var f = newFormat((specifier = formatSpecifier(specifier), specifier.type = "f", specifier)), + e = Math.max(-8, Math.min(8, Math.floor(exponent(value) / 3))) * 3, + k = Math.pow(10, -e), + prefix = prefixes[8 + e / 3]; + return function(value) { + return f(k * value) + prefix; + }; + } + + return { + format: newFormat, + formatPrefix: formatPrefix + }; +} + +var locale; +exports.format = void 0; +exports.formatPrefix = void 0; + +defaultLocale({ + thousands: ",", + grouping: [3], + currency: ["$", ""] +}); + +function defaultLocale(definition) { + locale = formatLocale(definition); + exports.format = locale.format; + exports.formatPrefix = locale.formatPrefix; + return locale; +} + +function precisionFixed(step) { + return Math.max(0, -exponent(Math.abs(step))); +} + +function precisionPrefix(step, value) { + return Math.max(0, Math.max(-8, Math.min(8, Math.floor(exponent(value) / 3))) * 3 - exponent(Math.abs(step))); +} + +function precisionRound(step, max) { + step = Math.abs(step), max = Math.abs(max) - step; + return Math.max(0, exponent(max) - exponent(step)) + 1; +} + +exports.FormatSpecifier = FormatSpecifier; +exports.formatDefaultLocale = defaultLocale; +exports.formatLocale = formatLocale; +exports.formatSpecifier = formatSpecifier; +exports.precisionFixed = precisionFixed; +exports.precisionPrefix = precisionPrefix; +exports.precisionRound = precisionRound; + +Object.defineProperty(exports, '__esModule', { value: true }); + +})); diff --git a/frontend/node_modules/d3-format/dist/d3-format.min.js b/frontend/node_modules/d3-format/dist/d3-format.min.js new file mode 100644 index 0000000..192cea8 --- /dev/null +++ b/frontend/node_modules/d3-format/dist/d3-format.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-format/ v3.1.0 Copyright 2010-2021 Mike Bostock +!function(t,i){"object"==typeof exports&&"undefined"!=typeof module?i(exports):"function"==typeof define&&define.amd?define(["exports"],i):i((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{})}(this,(function(t){"use strict";function i(t,i){if((r=(t=i?t.toExponential(i-1):t.toExponential()).indexOf("e"))<0)return null;var r,n=t.slice(0,r);return[n.length>1?n[0]+n.slice(2):n,+t.slice(r+1)]}function r(t){return(t=i(Math.abs(t)))?t[1]:NaN}var n,e=/^(?:(.)?([<>=^]))?([+\-( ])?([$#])?(0)?(\d+)?(,)?(\.\d+)?(~)?([a-z%])?$/i;function o(t){if(!(i=e.exec(t)))throw new Error("invalid format: "+t);var i;return new a({fill:i[1],align:i[2],sign:i[3],symbol:i[4],zero:i[5],width:i[6],comma:i[7],precision:i[8]&&i[8].slice(1),trim:i[9],type:i[10]})}function a(t){this.fill=void 0===t.fill?" ":t.fill+"",this.align=void 0===t.align?">":t.align+"",this.sign=void 0===t.sign?"-":t.sign+"",this.symbol=void 0===t.symbol?"":t.symbol+"",this.zero=!!t.zero,this.width=void 0===t.width?void 0:+t.width,this.comma=!!t.comma,this.precision=void 0===t.precision?void 0:+t.precision,this.trim=!!t.trim,this.type=void 0===t.type?"":t.type+""}function s(t,r){var n=i(t,r);if(!n)return t+"";var e=n[0],o=n[1];return o<0?"0."+new Array(-o).join("0")+e:e.length>o+1?e.slice(0,o+1)+"."+e.slice(o+1):e+new Array(o-e.length+2).join("0")}o.prototype=a.prototype,a.prototype.toString=function(){return this.fill+this.align+this.sign+this.symbol+(this.zero?"0":"")+(void 0===this.width?"":Math.max(1,0|this.width))+(this.comma?",":"")+(void 0===this.precision?"":"."+Math.max(0,0|this.precision))+(this.trim?"~":"")+this.type};var c={"%":(t,i)=>(100*t).toFixed(i),b:t=>Math.round(t).toString(2),c:t=>t+"",d:function(t){return Math.abs(t=Math.round(t))>=1e21?t.toLocaleString("en").replace(/,/g,""):t.toString(10)},e:(t,i)=>t.toExponential(i),f:(t,i)=>t.toFixed(i),g:(t,i)=>t.toPrecision(i),o:t=>Math.round(t).toString(8),p:(t,i)=>s(100*t,i),r:s,s:function(t,r){var e=i(t,r);if(!e)return t+"";var o=e[0],a=e[1],s=a-(n=3*Math.max(-8,Math.min(8,Math.floor(a/3))))+1,c=o.length;return s===c?o:s>c?o+new Array(s-c+1).join("0"):s>0?o.slice(0,s)+"."+o.slice(s):"0."+new Array(1-s).join("0")+i(t,Math.max(0,r+s-1))[0]},X:t=>Math.round(t).toString(16).toUpperCase(),x:t=>Math.round(t).toString(16)};function h(t){return t}var l,u=Array.prototype.map,f=["y","z","a","f","p","n","µ","m","","k","M","G","T","P","E","Z","Y"];function d(t){var i,e,a=void 0===t.grouping||void 0===t.thousands?h:(i=u.call(t.grouping,Number),e=t.thousands+"",function(t,r){for(var n=t.length,o=[],a=0,s=i[0],c=0;n>0&&s>0&&(c+s+1>r&&(s=Math.max(1,r-c)),o.push(t.substring(n-=s,n+s)),!((c+=s+1)>r));)s=i[a=(a+1)%i.length];return o.reverse().join(e)}),s=void 0===t.currency?"":t.currency[0]+"",l=void 0===t.currency?"":t.currency[1]+"",d=void 0===t.decimal?".":t.decimal+"",m=void 0===t.numerals?h:function(t){return function(i){return i.replace(/[0-9]/g,(function(i){return t[+i]}))}}(u.call(t.numerals,String)),p=void 0===t.percent?"%":t.percent+"",g=void 0===t.minus?"−":t.minus+"",v=void 0===t.nan?"NaN":t.nan+"";function M(t){var i=(t=o(t)).fill,r=t.align,e=t.sign,h=t.symbol,u=t.zero,M=t.width,y=t.comma,x=t.precision,b=t.trim,w=t.type;"n"===w?(y=!0,w="g"):c[w]||(void 0===x&&(x=12),b=!0,w="g"),(u||"0"===i&&"="===r)&&(u=!0,i="0",r="=");var S="$"===h?s:"#"===h&&/[boxX]/.test(w)?"0"+w.toLowerCase():"",j="$"===h?l:/[%p]/.test(w)?p:"",k=c[w],P=/[defgprs%]/.test(w);function z(t){var o,s,c,h=S,l=j;if("c"===w)l=k(t)+l,t="";else{var p=(t=+t)<0||1/t<0;if(t=isNaN(t)?v:k(Math.abs(t),x),b&&(t=function(t){t:for(var i,r=t.length,n=1,e=-1;n0&&(e=0)}return e>0?t.slice(0,e)+t.slice(i+1):t}(t)),p&&0==+t&&"+"!==e&&(p=!1),h=(p?"("===e?e:g:"-"===e||"("===e?"":e)+h,l=("s"===w?f[8+n/3]:"")+l+(p&&"("===e?")":""),P)for(o=-1,s=t.length;++o(c=t.charCodeAt(o))||c>57){l=(46===c?d+t.slice(o+1):t.slice(o))+l,t=t.slice(0,o);break}}y&&!u&&(t=a(t,1/0));var z=h.length+t.length+l.length,A=z>1)+h+t+l+A.slice(z);break;default:t=A+h+t+l}return m(t)}return x=void 0===x?6:/[gprs]/.test(w)?Math.max(1,Math.min(21,x)):Math.max(0,Math.min(20,x)),z.toString=function(){return t+""},z}return{format:M,formatPrefix:function(t,i){var n=M(((t=o(t)).type="f",t)),e=3*Math.max(-8,Math.min(8,Math.floor(r(i)/3))),a=Math.pow(10,-e),s=f[8+e/3];return function(t){return n(a*t)+s}}}}function m(i){return l=d(i),t.format=l.format,t.formatPrefix=l.formatPrefix,l}t.format=void 0,t.formatPrefix=void 0,m({thousands:",",grouping:[3],currency:["$",""]}),t.FormatSpecifier=a,t.formatDefaultLocale=m,t.formatLocale=d,t.formatSpecifier=o,t.precisionFixed=function(t){return Math.max(0,-r(Math.abs(t)))},t.precisionPrefix=function(t,i){return Math.max(0,3*Math.max(-8,Math.min(8,Math.floor(r(i)/3)))-r(Math.abs(t)))},t.precisionRound=function(t,i){return t=Math.abs(t),i=Math.abs(i)-t,Math.max(0,r(i)-r(t))+1},Object.defineProperty(t,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-format/locale/ar-001.json b/frontend/node_modules/d3-format/locale/ar-001.json new file mode 100644 index 0000000..0376eb9 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-001.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", ""], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-AE.json b/frontend/node_modules/d3-format/locale/ar-AE.json new file mode 100644 index 0000000..a827308 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-AE.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u062f\u002e\u0625\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-BH.json b/frontend/node_modules/d3-format/locale/ar-BH.json new file mode 100644 index 0000000..5f4e5dd --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-BH.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u062f\u002e\u0628\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-DJ.json b/frontend/node_modules/d3-format/locale/ar-DJ.json new file mode 100644 index 0000000..b893ff0 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-DJ.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["\u200f\u0046\u0064\u006a ", ""], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-DZ.json b/frontend/node_modules/d3-format/locale/ar-DZ.json new file mode 100644 index 0000000..e1438af --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-DZ.json @@ -0,0 +1,6 @@ +{ + "decimal": "\u002c", + "thousands": "\u002e", + "grouping": [3], + "currency": ["\u062f\u002e\u062c\u002e ", ""] +} diff --git a/frontend/node_modules/d3-format/locale/ar-EG.json b/frontend/node_modules/d3-format/locale/ar-EG.json new file mode 100644 index 0000000..2b1ff3a --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-EG.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u062c\u002e\u0645\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-EH.json b/frontend/node_modules/d3-format/locale/ar-EH.json new file mode 100644 index 0000000..b33c32a --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-EH.json @@ -0,0 +1,6 @@ +{ + "decimal": "\u002e", + "thousands": "\u002c", + "grouping": [3], + "currency": ["\u062f\u002e\u0645\u002e ", ""] +} diff --git a/frontend/node_modules/d3-format/locale/ar-ER.json b/frontend/node_modules/d3-format/locale/ar-ER.json new file mode 100644 index 0000000..b0f82bb --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-ER.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["\u004e\u0066\u006b ", ""], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-IL.json b/frontend/node_modules/d3-format/locale/ar-IL.json new file mode 100644 index 0000000..ce15fb4 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-IL.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["\u20aa ", ""], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-IQ.json b/frontend/node_modules/d3-format/locale/ar-IQ.json new file mode 100644 index 0000000..a6c9b3f --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-IQ.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u062f\u002e\u0639\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-JO.json b/frontend/node_modules/d3-format/locale/ar-JO.json new file mode 100644 index 0000000..94df180 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-JO.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u062f\u002e\u0623\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-KM.json b/frontend/node_modules/d3-format/locale/ar-KM.json new file mode 100644 index 0000000..84dd81a --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-KM.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u0641\u002e\u062c\u002e\u0642\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-KW.json b/frontend/node_modules/d3-format/locale/ar-KW.json new file mode 100644 index 0000000..b4018ab --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-KW.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u062f\u002e\u0643\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-LB.json b/frontend/node_modules/d3-format/locale/ar-LB.json new file mode 100644 index 0000000..c732df3 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-LB.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u0644\u002e\u0644\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-LY.json b/frontend/node_modules/d3-format/locale/ar-LY.json new file mode 100644 index 0000000..431f230 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-LY.json @@ -0,0 +1,6 @@ +{ + "decimal": "\u002c", + "thousands": "\u002e", + "grouping": [3], + "currency": ["\u062f\u002e\u0644\u002e ", ""] +} diff --git a/frontend/node_modules/d3-format/locale/ar-MA.json b/frontend/node_modules/d3-format/locale/ar-MA.json new file mode 100644 index 0000000..abc0663 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-MA.json @@ -0,0 +1,6 @@ +{ + "decimal": "\u002c", + "thousands": "\u002e", + "grouping": [3], + "currency": ["\u062f\u002e\u0645\u002e ", ""] +} diff --git a/frontend/node_modules/d3-format/locale/ar-MR.json b/frontend/node_modules/d3-format/locale/ar-MR.json new file mode 100644 index 0000000..8d1f8c2 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-MR.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u0623\u002e\u0645\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-OM.json b/frontend/node_modules/d3-format/locale/ar-OM.json new file mode 100644 index 0000000..04ad53a --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-OM.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u0631\u002e\u0639\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-PS.json b/frontend/node_modules/d3-format/locale/ar-PS.json new file mode 100644 index 0000000..ce15fb4 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-PS.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["\u20aa ", ""], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-QA.json b/frontend/node_modules/d3-format/locale/ar-QA.json new file mode 100644 index 0000000..94aef29 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-QA.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u0631\u002e\u0642\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-SA.json b/frontend/node_modules/d3-format/locale/ar-SA.json new file mode 100644 index 0000000..4d64227 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-SA.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u0631\u002e\u0633\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-SD.json b/frontend/node_modules/d3-format/locale/ar-SD.json new file mode 100644 index 0000000..1ae41ae --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-SD.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u062c\u002e\u0633\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-SO.json b/frontend/node_modules/d3-format/locale/ar-SO.json new file mode 100644 index 0000000..143b46f --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-SO.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["\u200f\u0053 ", ""], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-SS.json b/frontend/node_modules/d3-format/locale/ar-SS.json new file mode 100644 index 0000000..03ca5b4 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-SS.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["\u00a3 ", ""], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-SY.json b/frontend/node_modules/d3-format/locale/ar-SY.json new file mode 100644 index 0000000..40263fb --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-SY.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u0644\u002e\u0633\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-TD.json b/frontend/node_modules/d3-format/locale/ar-TD.json new file mode 100644 index 0000000..7bc3646 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-TD.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["\u200f\u0046\u0043\u0046\u0041 ", ""], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ar-TN.json b/frontend/node_modules/d3-format/locale/ar-TN.json new file mode 100644 index 0000000..16829aa --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-TN.json @@ -0,0 +1,6 @@ +{ + "decimal": "\u002c", + "thousands": "\u002e", + "grouping": [3], + "currency": ["\u062f\u002e\u062a\u002e ", ""] +} diff --git a/frontend/node_modules/d3-format/locale/ar-YE.json b/frontend/node_modules/d3-format/locale/ar-YE.json new file mode 100644 index 0000000..ed9f48e --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ar-YE.json @@ -0,0 +1,7 @@ +{ + "decimal": "\u066b", + "thousands": "\u066c", + "grouping": [3], + "currency": ["", " \u0631\u002e\u0649\u002e"], + "numerals" : ["\u0660", "\u0661", "\u0662", "\u0663", "\u0664", "\u0665", "\u0666", "\u0667", "\u0668", "\u0669"] +} diff --git a/frontend/node_modules/d3-format/locale/ca-ES.json b/frontend/node_modules/d3-format/locale/ca-ES.json new file mode 100644 index 0000000..a249762 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ca-ES.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": ".", + "grouping": [3], + "currency": ["", "\u00a0€"] +} diff --git a/frontend/node_modules/d3-format/locale/cs-CZ.json b/frontend/node_modules/d3-format/locale/cs-CZ.json new file mode 100644 index 0000000..7ff40eb --- /dev/null +++ b/frontend/node_modules/d3-format/locale/cs-CZ.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": "\u00a0", + "grouping": [3], + "currency": ["", "\u00a0Kč"] +} diff --git a/frontend/node_modules/d3-format/locale/da-DK.json b/frontend/node_modules/d3-format/locale/da-DK.json new file mode 100644 index 0000000..991a81c --- /dev/null +++ b/frontend/node_modules/d3-format/locale/da-DK.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": ".", + "grouping": [3], + "currency": ["", " kr"] +} diff --git a/frontend/node_modules/d3-format/locale/de-CH.json b/frontend/node_modules/d3-format/locale/de-CH.json new file mode 100644 index 0000000..874bb56 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/de-CH.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": "'", + "grouping": [3], + "currency": ["", "\u00a0CHF"] +} diff --git a/frontend/node_modules/d3-format/locale/de-DE.json b/frontend/node_modules/d3-format/locale/de-DE.json new file mode 100644 index 0000000..a249762 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/de-DE.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": ".", + "grouping": [3], + "currency": ["", "\u00a0€"] +} diff --git a/frontend/node_modules/d3-format/locale/en-CA.json b/frontend/node_modules/d3-format/locale/en-CA.json new file mode 100644 index 0000000..f075b86 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/en-CA.json @@ -0,0 +1,6 @@ +{ + "decimal": ".", + "thousands": ",", + "grouping": [3], + "currency": ["$", ""] +} diff --git a/frontend/node_modules/d3-format/locale/en-GB.json b/frontend/node_modules/d3-format/locale/en-GB.json new file mode 100644 index 0000000..3d22d7a --- /dev/null +++ b/frontend/node_modules/d3-format/locale/en-GB.json @@ -0,0 +1,6 @@ +{ + "decimal": ".", + "thousands": ",", + "grouping": [3], + "currency": ["£", ""] +} diff --git a/frontend/node_modules/d3-format/locale/en-IE.json b/frontend/node_modules/d3-format/locale/en-IE.json new file mode 100644 index 0000000..7d64415 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/en-IE.json @@ -0,0 +1,6 @@ +{ + "decimal": ".", + "thousands": ",", + "grouping": [3], + "currency": ["€", ""] +} diff --git a/frontend/node_modules/d3-format/locale/en-IN.json b/frontend/node_modules/d3-format/locale/en-IN.json new file mode 100644 index 0000000..ada1510 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/en-IN.json @@ -0,0 +1,6 @@ +{ + "decimal": ".", + "thousands": ",", + "grouping": [3, 2, 2, 2, 2, 2, 2, 2, 2, 2], + "currency": ["₹", ""] +} diff --git a/frontend/node_modules/d3-format/locale/en-US.json b/frontend/node_modules/d3-format/locale/en-US.json new file mode 100644 index 0000000..f075b86 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/en-US.json @@ -0,0 +1,6 @@ +{ + "decimal": ".", + "thousands": ",", + "grouping": [3], + "currency": ["$", ""] +} diff --git a/frontend/node_modules/d3-format/locale/es-BO.json b/frontend/node_modules/d3-format/locale/es-BO.json new file mode 100644 index 0000000..98fe646 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/es-BO.json @@ -0,0 +1,7 @@ +{ + "decimal": ",", + "thousands": ".", + "grouping": [3], + "currency": ["Bs\u00a0", ""], + "percent": "\u202f%" +} diff --git a/frontend/node_modules/d3-format/locale/es-ES.json b/frontend/node_modules/d3-format/locale/es-ES.json new file mode 100644 index 0000000..a249762 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/es-ES.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": ".", + "grouping": [3], + "currency": ["", "\u00a0€"] +} diff --git a/frontend/node_modules/d3-format/locale/es-MX.json b/frontend/node_modules/d3-format/locale/es-MX.json new file mode 100644 index 0000000..f075b86 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/es-MX.json @@ -0,0 +1,6 @@ +{ + "decimal": ".", + "thousands": ",", + "grouping": [3], + "currency": ["$", ""] +} diff --git a/frontend/node_modules/d3-format/locale/fi-FI.json b/frontend/node_modules/d3-format/locale/fi-FI.json new file mode 100644 index 0000000..e2218ec --- /dev/null +++ b/frontend/node_modules/d3-format/locale/fi-FI.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": "\u00a0", + "grouping": [3], + "currency": ["", "\u00a0€"] +} diff --git a/frontend/node_modules/d3-format/locale/fr-CA.json b/frontend/node_modules/d3-format/locale/fr-CA.json new file mode 100644 index 0000000..0d927b9 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/fr-CA.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": "\u00a0", + "grouping": [3], + "currency": ["", "$"] +} diff --git a/frontend/node_modules/d3-format/locale/fr-FR.json b/frontend/node_modules/d3-format/locale/fr-FR.json new file mode 100644 index 0000000..e0cf89d --- /dev/null +++ b/frontend/node_modules/d3-format/locale/fr-FR.json @@ -0,0 +1,7 @@ +{ + "decimal": ",", + "thousands": "\u00a0", + "grouping": [3], + "currency": ["", "\u00a0€"], + "percent": "\u202f%" +} diff --git a/frontend/node_modules/d3-format/locale/he-IL.json b/frontend/node_modules/d3-format/locale/he-IL.json new file mode 100644 index 0000000..23926cb --- /dev/null +++ b/frontend/node_modules/d3-format/locale/he-IL.json @@ -0,0 +1,6 @@ +{ + "decimal": ".", + "thousands": ",", + "grouping": [3], + "currency": ["₪", ""] +} diff --git a/frontend/node_modules/d3-format/locale/hu-HU.json b/frontend/node_modules/d3-format/locale/hu-HU.json new file mode 100644 index 0000000..1baff74 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/hu-HU.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": "\u00a0", + "grouping": [3], + "currency": ["", "\u00a0Ft"] +} diff --git a/frontend/node_modules/d3-format/locale/it-IT.json b/frontend/node_modules/d3-format/locale/it-IT.json new file mode 100644 index 0000000..564ed46 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/it-IT.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": ".", + "grouping": [3], + "currency": ["€", ""] +} diff --git a/frontend/node_modules/d3-format/locale/ja-JP.json b/frontend/node_modules/d3-format/locale/ja-JP.json new file mode 100644 index 0000000..fdcba6c --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ja-JP.json @@ -0,0 +1,6 @@ +{ + "decimal": ".", + "thousands": ",", + "grouping": [3], + "currency": ["", "円"] +} diff --git a/frontend/node_modules/d3-format/locale/ko-KR.json b/frontend/node_modules/d3-format/locale/ko-KR.json new file mode 100644 index 0000000..d1d882c --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ko-KR.json @@ -0,0 +1,6 @@ +{ + "decimal": ".", + "thousands": ",", + "grouping": [3], + "currency": ["₩", ""] +} diff --git a/frontend/node_modules/d3-format/locale/mk-MK.json b/frontend/node_modules/d3-format/locale/mk-MK.json new file mode 100644 index 0000000..33528b8 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/mk-MK.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": ".", + "grouping": [3], + "currency": ["", "\u00a0ден."] +} diff --git a/frontend/node_modules/d3-format/locale/nl-NL.json b/frontend/node_modules/d3-format/locale/nl-NL.json new file mode 100644 index 0000000..7176b37 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/nl-NL.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": ".", + "grouping": [3], + "currency": ["€\u00a0", ""] +} diff --git a/frontend/node_modules/d3-format/locale/pl-PL.json b/frontend/node_modules/d3-format/locale/pl-PL.json new file mode 100644 index 0000000..12c673f --- /dev/null +++ b/frontend/node_modules/d3-format/locale/pl-PL.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": ".", + "grouping": [3], + "currency": ["", "zł"] +} diff --git a/frontend/node_modules/d3-format/locale/pt-BR.json b/frontend/node_modules/d3-format/locale/pt-BR.json new file mode 100644 index 0000000..e6705f1 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/pt-BR.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": ".", + "grouping": [3], + "currency": ["R$", ""] +} diff --git a/frontend/node_modules/d3-format/locale/pt-PT.json b/frontend/node_modules/d3-format/locale/pt-PT.json new file mode 100644 index 0000000..e2218ec --- /dev/null +++ b/frontend/node_modules/d3-format/locale/pt-PT.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": "\u00a0", + "grouping": [3], + "currency": ["", "\u00a0€"] +} diff --git a/frontend/node_modules/d3-format/locale/ru-RU.json b/frontend/node_modules/d3-format/locale/ru-RU.json new file mode 100644 index 0000000..1babec3 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/ru-RU.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": "\u00a0", + "grouping": [3], + "currency": ["", "\u00a0\u20bd"] +} diff --git a/frontend/node_modules/d3-format/locale/sl-SI.json b/frontend/node_modules/d3-format/locale/sl-SI.json new file mode 100644 index 0000000..a249762 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/sl-SI.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": ".", + "grouping": [3], + "currency": ["", "\u00a0€"] +} diff --git a/frontend/node_modules/d3-format/locale/sv-SE.json b/frontend/node_modules/d3-format/locale/sv-SE.json new file mode 100644 index 0000000..870eba3 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/sv-SE.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": "\u00a0", + "grouping": [3], + "currency": ["", " kr"] +} diff --git a/frontend/node_modules/d3-format/locale/uk-UA.json b/frontend/node_modules/d3-format/locale/uk-UA.json new file mode 100644 index 0000000..75cee2d --- /dev/null +++ b/frontend/node_modules/d3-format/locale/uk-UA.json @@ -0,0 +1,6 @@ +{ + "decimal": ",", + "thousands": "\u00a0", + "grouping": [3], + "currency": ["", "\u00a0₴."] +} diff --git a/frontend/node_modules/d3-format/locale/zh-CN.json b/frontend/node_modules/d3-format/locale/zh-CN.json new file mode 100644 index 0000000..1ffc7b6 --- /dev/null +++ b/frontend/node_modules/d3-format/locale/zh-CN.json @@ -0,0 +1,6 @@ +{ + "decimal": ".", + "thousands": ",", + "grouping": [3], + "currency": ["¥", ""] +} diff --git a/frontend/node_modules/d3-format/package.json b/frontend/node_modules/d3-format/package.json new file mode 100644 index 0000000..8865d58 --- /dev/null +++ b/frontend/node_modules/d3-format/package.json @@ -0,0 +1,55 @@ +{ + "name": "d3-format", + "version": "3.1.0", + "description": "Format numbers for human consumption.", + "homepage": "https://d3js.org/d3-format/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-format.git" + }, + "keywords": [ + "d3", + "d3-module", + "format", + "localization" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "http://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js", + "locale/*.json" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-format.min.js", + "unpkg": "dist/d3-format.min.js", + "exports": { + ".": { + "umd": "./dist/d3-format.min.js", + "default": "./src/index.js" + }, + "./locale/*": "./locale/*.json" + }, + "sideEffects": [ + "./src/defaultLocale.js" + ], + "devDependencies": { + "eslint": "8", + "mocha": "9", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-format/src/defaultLocale.js b/frontend/node_modules/d3-format/src/defaultLocale.js new file mode 100644 index 0000000..2fab057 --- /dev/null +++ b/frontend/node_modules/d3-format/src/defaultLocale.js @@ -0,0 +1,18 @@ +import formatLocale from "./locale.js"; + +var locale; +export var format; +export var formatPrefix; + +defaultLocale({ + thousands: ",", + grouping: [3], + currency: ["$", ""] +}); + +export default function defaultLocale(definition) { + locale = formatLocale(definition); + format = locale.format; + formatPrefix = locale.formatPrefix; + return locale; +} diff --git a/frontend/node_modules/d3-format/src/exponent.js b/frontend/node_modules/d3-format/src/exponent.js new file mode 100644 index 0000000..79b67e3 --- /dev/null +++ b/frontend/node_modules/d3-format/src/exponent.js @@ -0,0 +1,5 @@ +import {formatDecimalParts} from "./formatDecimal.js"; + +export default function(x) { + return x = formatDecimalParts(Math.abs(x)), x ? x[1] : NaN; +} diff --git a/frontend/node_modules/d3-format/src/formatDecimal.js b/frontend/node_modules/d3-format/src/formatDecimal.js new file mode 100644 index 0000000..4b34192 --- /dev/null +++ b/frontend/node_modules/d3-format/src/formatDecimal.js @@ -0,0 +1,20 @@ +export default function(x) { + return Math.abs(x = Math.round(x)) >= 1e21 + ? x.toLocaleString("en").replace(/,/g, "") + : x.toString(10); +} + +// Computes the decimal coefficient and exponent of the specified number x with +// significant digits p, where x is positive and p is in [1, 21] or undefined. +// For example, formatDecimalParts(1.23) returns ["123", 0]. +export function formatDecimalParts(x, p) { + if ((i = (x = p ? x.toExponential(p - 1) : x.toExponential()).indexOf("e")) < 0) return null; // NaN, ±Infinity + var i, coefficient = x.slice(0, i); + + // The string returned by toExponential either has the form \d\.\d+e[-+]\d+ + // (e.g., 1.2e+3) or the form \de[-+]\d+ (e.g., 1e+3). + return [ + coefficient.length > 1 ? coefficient[0] + coefficient.slice(2) : coefficient, + +x.slice(i + 1) + ]; +} diff --git a/frontend/node_modules/d3-format/src/formatGroup.js b/frontend/node_modules/d3-format/src/formatGroup.js new file mode 100644 index 0000000..ae603d3 --- /dev/null +++ b/frontend/node_modules/d3-format/src/formatGroup.js @@ -0,0 +1,18 @@ +export default function(grouping, thousands) { + return function(value, width) { + var i = value.length, + t = [], + j = 0, + g = grouping[0], + length = 0; + + while (i > 0 && g > 0) { + if (length + g + 1 > width) g = Math.max(1, width - length); + t.push(value.substring(i -= g, i + g)); + if ((length += g + 1) > width) break; + g = grouping[j = (j + 1) % grouping.length]; + } + + return t.reverse().join(thousands); + }; +} diff --git a/frontend/node_modules/d3-format/src/formatNumerals.js b/frontend/node_modules/d3-format/src/formatNumerals.js new file mode 100644 index 0000000..046317e --- /dev/null +++ b/frontend/node_modules/d3-format/src/formatNumerals.js @@ -0,0 +1,7 @@ +export default function(numerals) { + return function(value) { + return value.replace(/[0-9]/g, function(i) { + return numerals[+i]; + }); + }; +} diff --git a/frontend/node_modules/d3-format/src/formatPrefixAuto.js b/frontend/node_modules/d3-format/src/formatPrefixAuto.js new file mode 100644 index 0000000..907742a --- /dev/null +++ b/frontend/node_modules/d3-format/src/formatPrefixAuto.js @@ -0,0 +1,16 @@ +import {formatDecimalParts} from "./formatDecimal.js"; + +export var prefixExponent; + +export default function(x, p) { + var d = formatDecimalParts(x, p); + if (!d) return x + ""; + var coefficient = d[0], + exponent = d[1], + i = exponent - (prefixExponent = Math.max(-8, Math.min(8, Math.floor(exponent / 3))) * 3) + 1, + n = coefficient.length; + return i === n ? coefficient + : i > n ? coefficient + new Array(i - n + 1).join("0") + : i > 0 ? coefficient.slice(0, i) + "." + coefficient.slice(i) + : "0." + new Array(1 - i).join("0") + formatDecimalParts(x, Math.max(0, p + i - 1))[0]; // less than 1y! +} diff --git a/frontend/node_modules/d3-format/src/formatRounded.js b/frontend/node_modules/d3-format/src/formatRounded.js new file mode 100644 index 0000000..ea5e10d --- /dev/null +++ b/frontend/node_modules/d3-format/src/formatRounded.js @@ -0,0 +1,11 @@ +import {formatDecimalParts} from "./formatDecimal.js"; + +export default function(x, p) { + var d = formatDecimalParts(x, p); + if (!d) return x + ""; + var coefficient = d[0], + exponent = d[1]; + return exponent < 0 ? "0." + new Array(-exponent).join("0") + coefficient + : coefficient.length > exponent + 1 ? coefficient.slice(0, exponent + 1) + "." + coefficient.slice(exponent + 1) + : coefficient + new Array(exponent - coefficient.length + 2).join("0"); +} diff --git a/frontend/node_modules/d3-format/src/formatSpecifier.js b/frontend/node_modules/d3-format/src/formatSpecifier.js new file mode 100644 index 0000000..2dabb2f --- /dev/null +++ b/frontend/node_modules/d3-format/src/formatSpecifier.js @@ -0,0 +1,47 @@ +// [[fill]align][sign][symbol][0][width][,][.precision][~][type] +var re = /^(?:(.)?([<>=^]))?([+\-( ])?([$#])?(0)?(\d+)?(,)?(\.\d+)?(~)?([a-z%])?$/i; + +export default function formatSpecifier(specifier) { + if (!(match = re.exec(specifier))) throw new Error("invalid format: " + specifier); + var match; + return new FormatSpecifier({ + fill: match[1], + align: match[2], + sign: match[3], + symbol: match[4], + zero: match[5], + width: match[6], + comma: match[7], + precision: match[8] && match[8].slice(1), + trim: match[9], + type: match[10] + }); +} + +formatSpecifier.prototype = FormatSpecifier.prototype; // instanceof + +export function FormatSpecifier(specifier) { + this.fill = specifier.fill === undefined ? " " : specifier.fill + ""; + this.align = specifier.align === undefined ? ">" : specifier.align + ""; + this.sign = specifier.sign === undefined ? "-" : specifier.sign + ""; + this.symbol = specifier.symbol === undefined ? "" : specifier.symbol + ""; + this.zero = !!specifier.zero; + this.width = specifier.width === undefined ? undefined : +specifier.width; + this.comma = !!specifier.comma; + this.precision = specifier.precision === undefined ? undefined : +specifier.precision; + this.trim = !!specifier.trim; + this.type = specifier.type === undefined ? "" : specifier.type + ""; +} + +FormatSpecifier.prototype.toString = function() { + return this.fill + + this.align + + this.sign + + this.symbol + + (this.zero ? "0" : "") + + (this.width === undefined ? "" : Math.max(1, this.width | 0)) + + (this.comma ? "," : "") + + (this.precision === undefined ? "" : "." + Math.max(0, this.precision | 0)) + + (this.trim ? "~" : "") + + this.type; +}; diff --git a/frontend/node_modules/d3-format/src/formatTrim.js b/frontend/node_modules/d3-format/src/formatTrim.js new file mode 100644 index 0000000..b0d647b --- /dev/null +++ b/frontend/node_modules/d3-format/src/formatTrim.js @@ -0,0 +1,11 @@ +// Trims insignificant zeros, e.g., replaces 1.2000k with 1.2k. +export default function(s) { + out: for (var n = s.length, i = 1, i0 = -1, i1; i < n; ++i) { + switch (s[i]) { + case ".": i0 = i1 = i; break; + case "0": if (i0 === 0) i0 = i; i1 = i; break; + default: if (!+s[i]) break out; if (i0 > 0) i0 = 0; break; + } + } + return i0 > 0 ? s.slice(0, i0) + s.slice(i1 + 1) : s; +} diff --git a/frontend/node_modules/d3-format/src/formatTypes.js b/frontend/node_modules/d3-format/src/formatTypes.js new file mode 100644 index 0000000..007db36 --- /dev/null +++ b/frontend/node_modules/d3-format/src/formatTypes.js @@ -0,0 +1,19 @@ +import formatDecimal from "./formatDecimal.js"; +import formatPrefixAuto from "./formatPrefixAuto.js"; +import formatRounded from "./formatRounded.js"; + +export default { + "%": (x, p) => (x * 100).toFixed(p), + "b": (x) => Math.round(x).toString(2), + "c": (x) => x + "", + "d": formatDecimal, + "e": (x, p) => x.toExponential(p), + "f": (x, p) => x.toFixed(p), + "g": (x, p) => x.toPrecision(p), + "o": (x) => Math.round(x).toString(8), + "p": (x, p) => formatRounded(x * 100, p), + "r": formatRounded, + "s": formatPrefixAuto, + "X": (x) => Math.round(x).toString(16).toUpperCase(), + "x": (x) => Math.round(x).toString(16) +}; diff --git a/frontend/node_modules/d3-format/src/identity.js b/frontend/node_modules/d3-format/src/identity.js new file mode 100644 index 0000000..b2f94b2 --- /dev/null +++ b/frontend/node_modules/d3-format/src/identity.js @@ -0,0 +1,3 @@ +export default function(x) { + return x; +} diff --git a/frontend/node_modules/d3-format/src/index.js b/frontend/node_modules/d3-format/src/index.js new file mode 100644 index 0000000..22ae6b2 --- /dev/null +++ b/frontend/node_modules/d3-format/src/index.js @@ -0,0 +1,6 @@ +export {default as formatDefaultLocale, format, formatPrefix} from "./defaultLocale.js"; +export {default as formatLocale} from "./locale.js"; +export {default as formatSpecifier, FormatSpecifier} from "./formatSpecifier.js"; +export {default as precisionFixed} from "./precisionFixed.js"; +export {default as precisionPrefix} from "./precisionPrefix.js"; +export {default as precisionRound} from "./precisionRound.js"; diff --git a/frontend/node_modules/d3-format/src/locale.js b/frontend/node_modules/d3-format/src/locale.js new file mode 100644 index 0000000..404f941 --- /dev/null +++ b/frontend/node_modules/d3-format/src/locale.js @@ -0,0 +1,148 @@ +import exponent from "./exponent.js"; +import formatGroup from "./formatGroup.js"; +import formatNumerals from "./formatNumerals.js"; +import formatSpecifier from "./formatSpecifier.js"; +import formatTrim from "./formatTrim.js"; +import formatTypes from "./formatTypes.js"; +import {prefixExponent} from "./formatPrefixAuto.js"; +import identity from "./identity.js"; + +var map = Array.prototype.map, + prefixes = ["y","z","a","f","p","n","µ","m","","k","M","G","T","P","E","Z","Y"]; + +export default function(locale) { + var group = locale.grouping === undefined || locale.thousands === undefined ? identity : formatGroup(map.call(locale.grouping, Number), locale.thousands + ""), + currencyPrefix = locale.currency === undefined ? "" : locale.currency[0] + "", + currencySuffix = locale.currency === undefined ? "" : locale.currency[1] + "", + decimal = locale.decimal === undefined ? "." : locale.decimal + "", + numerals = locale.numerals === undefined ? identity : formatNumerals(map.call(locale.numerals, String)), + percent = locale.percent === undefined ? "%" : locale.percent + "", + minus = locale.minus === undefined ? "−" : locale.minus + "", + nan = locale.nan === undefined ? "NaN" : locale.nan + ""; + + function newFormat(specifier) { + specifier = formatSpecifier(specifier); + + var fill = specifier.fill, + align = specifier.align, + sign = specifier.sign, + symbol = specifier.symbol, + zero = specifier.zero, + width = specifier.width, + comma = specifier.comma, + precision = specifier.precision, + trim = specifier.trim, + type = specifier.type; + + // The "n" type is an alias for ",g". + if (type === "n") comma = true, type = "g"; + + // The "" type, and any invalid type, is an alias for ".12~g". + else if (!formatTypes[type]) precision === undefined && (precision = 12), trim = true, type = "g"; + + // If zero fill is specified, padding goes after sign and before digits. + if (zero || (fill === "0" && align === "=")) zero = true, fill = "0", align = "="; + + // Compute the prefix and suffix. + // For SI-prefix, the suffix is lazily computed. + var prefix = symbol === "$" ? currencyPrefix : symbol === "#" && /[boxX]/.test(type) ? "0" + type.toLowerCase() : "", + suffix = symbol === "$" ? currencySuffix : /[%p]/.test(type) ? percent : ""; + + // What format function should we use? + // Is this an integer type? + // Can this type generate exponential notation? + var formatType = formatTypes[type], + maybeSuffix = /[defgprs%]/.test(type); + + // Set the default precision if not specified, + // or clamp the specified precision to the supported range. + // For significant precision, it must be in [1, 21]. + // For fixed precision, it must be in [0, 20]. + precision = precision === undefined ? 6 + : /[gprs]/.test(type) ? Math.max(1, Math.min(21, precision)) + : Math.max(0, Math.min(20, precision)); + + function format(value) { + var valuePrefix = prefix, + valueSuffix = suffix, + i, n, c; + + if (type === "c") { + valueSuffix = formatType(value) + valueSuffix; + value = ""; + } else { + value = +value; + + // Determine the sign. -0 is not less than 0, but 1 / -0 is! + var valueNegative = value < 0 || 1 / value < 0; + + // Perform the initial formatting. + value = isNaN(value) ? nan : formatType(Math.abs(value), precision); + + // Trim insignificant zeros. + if (trim) value = formatTrim(value); + + // If a negative value rounds to zero after formatting, and no explicit positive sign is requested, hide the sign. + if (valueNegative && +value === 0 && sign !== "+") valueNegative = false; + + // Compute the prefix and suffix. + valuePrefix = (valueNegative ? (sign === "(" ? sign : minus) : sign === "-" || sign === "(" ? "" : sign) + valuePrefix; + valueSuffix = (type === "s" ? prefixes[8 + prefixExponent / 3] : "") + valueSuffix + (valueNegative && sign === "(" ? ")" : ""); + + // Break the formatted value into the integer “value” part that can be + // grouped, and fractional or exponential “suffix” part that is not. + if (maybeSuffix) { + i = -1, n = value.length; + while (++i < n) { + if (c = value.charCodeAt(i), 48 > c || c > 57) { + valueSuffix = (c === 46 ? decimal + value.slice(i + 1) : value.slice(i)) + valueSuffix; + value = value.slice(0, i); + break; + } + } + } + } + + // If the fill character is not "0", grouping is applied before padding. + if (comma && !zero) value = group(value, Infinity); + + // Compute the padding. + var length = valuePrefix.length + value.length + valueSuffix.length, + padding = length < width ? new Array(width - length + 1).join(fill) : ""; + + // If the fill character is "0", grouping is applied after padding. + if (comma && zero) value = group(padding + value, padding.length ? width - valueSuffix.length : Infinity), padding = ""; + + // Reconstruct the final output based on the desired alignment. + switch (align) { + case "<": value = valuePrefix + value + valueSuffix + padding; break; + case "=": value = valuePrefix + padding + value + valueSuffix; break; + case "^": value = padding.slice(0, length = padding.length >> 1) + valuePrefix + value + valueSuffix + padding.slice(length); break; + default: value = padding + valuePrefix + value + valueSuffix; break; + } + + return numerals(value); + } + + format.toString = function() { + return specifier + ""; + }; + + return format; + } + + function formatPrefix(specifier, value) { + var f = newFormat((specifier = formatSpecifier(specifier), specifier.type = "f", specifier)), + e = Math.max(-8, Math.min(8, Math.floor(exponent(value) / 3))) * 3, + k = Math.pow(10, -e), + prefix = prefixes[8 + e / 3]; + return function(value) { + return f(k * value) + prefix; + }; + } + + return { + format: newFormat, + formatPrefix: formatPrefix + }; +} diff --git a/frontend/node_modules/d3-format/src/precisionFixed.js b/frontend/node_modules/d3-format/src/precisionFixed.js new file mode 100644 index 0000000..237f53f --- /dev/null +++ b/frontend/node_modules/d3-format/src/precisionFixed.js @@ -0,0 +1,5 @@ +import exponent from "./exponent.js"; + +export default function(step) { + return Math.max(0, -exponent(Math.abs(step))); +} diff --git a/frontend/node_modules/d3-format/src/precisionPrefix.js b/frontend/node_modules/d3-format/src/precisionPrefix.js new file mode 100644 index 0000000..fd6af84 --- /dev/null +++ b/frontend/node_modules/d3-format/src/precisionPrefix.js @@ -0,0 +1,5 @@ +import exponent from "./exponent.js"; + +export default function(step, value) { + return Math.max(0, Math.max(-8, Math.min(8, Math.floor(exponent(value) / 3))) * 3 - exponent(Math.abs(step))); +} diff --git a/frontend/node_modules/d3-format/src/precisionRound.js b/frontend/node_modules/d3-format/src/precisionRound.js new file mode 100644 index 0000000..5c70437 --- /dev/null +++ b/frontend/node_modules/d3-format/src/precisionRound.js @@ -0,0 +1,6 @@ +import exponent from "./exponent.js"; + +export default function(step, max) { + step = Math.abs(step), max = Math.abs(max) - step; + return Math.max(0, exponent(max) - exponent(step)) + 1; +} diff --git a/frontend/node_modules/d3-geo/LICENSE b/frontend/node_modules/d3-geo/LICENSE new file mode 100644 index 0000000..7286c02 --- /dev/null +++ b/frontend/node_modules/d3-geo/LICENSE @@ -0,0 +1,34 @@ +Copyright 2010-2024 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. + +This license applies to GeographicLib, versions 1.12 and later. + +Copyright 2008-2012 Charles Karney + +Permission is hereby granted, free of charge, to any person obtaining a copy of +this software and associated documentation files (the "Software"), to deal in +the Software without restriction, including without limitation the rights to +use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of +the Software, and to permit persons to whom the Software is furnished to do so, +subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS +FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR +COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER +IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN +CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/frontend/node_modules/d3-geo/README.md b/frontend/node_modules/d3-geo/README.md new file mode 100644 index 0000000..4d4ca58 --- /dev/null +++ b/frontend/node_modules/d3-geo/README.md @@ -0,0 +1,12 @@ +# d3-geo + + + +This module uses spherical [GeoJSON](http://geojson.org/geojson-spec.html) to represent geographic features in JavaScript. D3 supports a wide variety of common and [unusual](https://github.com/d3/d3-geo-projection) map projections. And because D3 uses spherical geometry to represent data, you can apply any aspect to any projection by rotating geometry. + +## Resources + +- [Documentation](https://d3js.org/d3-geo) +- [Examples](https://observablehq.com/collection/@d3/d3-geo) +- [Releases](https://github.com/d3/d3-geo/releases) +- [Getting help](https://d3js.org/community) diff --git a/frontend/node_modules/d3-geo/dist/d3-geo.js b/frontend/node_modules/d3-geo/dist/d3-geo.js new file mode 100644 index 0000000..6ad02fa --- /dev/null +++ b/frontend/node_modules/d3-geo/dist/d3-geo.js @@ -0,0 +1,3167 @@ +// https://d3js.org/d3-geo/ v3.1.1 Copyright 2010-2024 Mike Bostock, 2008-2012 Charles Karney +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-array')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-array'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3)); +})(this, (function (exports, d3Array) { 'use strict'; + +var epsilon = 1e-6; +var epsilon2 = 1e-12; +var pi = Math.PI; +var halfPi = pi / 2; +var quarterPi = pi / 4; +var tau = pi * 2; + +var degrees = 180 / pi; +var radians = pi / 180; + +var abs = Math.abs; +var atan = Math.atan; +var atan2 = Math.atan2; +var cos = Math.cos; +var ceil = Math.ceil; +var exp = Math.exp; +var hypot = Math.hypot; +var log = Math.log; +var pow = Math.pow; +var sin = Math.sin; +var sign = Math.sign || function(x) { return x > 0 ? 1 : x < 0 ? -1 : 0; }; +var sqrt = Math.sqrt; +var tan = Math.tan; + +function acos(x) { + return x > 1 ? 0 : x < -1 ? pi : Math.acos(x); +} + +function asin(x) { + return x > 1 ? halfPi : x < -1 ? -halfPi : Math.asin(x); +} + +function haversin(x) { + return (x = sin(x / 2)) * x; +} + +function noop() {} + +function streamGeometry(geometry, stream) { + if (geometry && streamGeometryType.hasOwnProperty(geometry.type)) { + streamGeometryType[geometry.type](geometry, stream); + } +} + +var streamObjectType = { + Feature: function(object, stream) { + streamGeometry(object.geometry, stream); + }, + FeatureCollection: function(object, stream) { + var features = object.features, i = -1, n = features.length; + while (++i < n) streamGeometry(features[i].geometry, stream); + } +}; + +var streamGeometryType = { + Sphere: function(object, stream) { + stream.sphere(); + }, + Point: function(object, stream) { + object = object.coordinates; + stream.point(object[0], object[1], object[2]); + }, + MultiPoint: function(object, stream) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) object = coordinates[i], stream.point(object[0], object[1], object[2]); + }, + LineString: function(object, stream) { + streamLine(object.coordinates, stream, 0); + }, + MultiLineString: function(object, stream) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) streamLine(coordinates[i], stream, 0); + }, + Polygon: function(object, stream) { + streamPolygon(object.coordinates, stream); + }, + MultiPolygon: function(object, stream) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) streamPolygon(coordinates[i], stream); + }, + GeometryCollection: function(object, stream) { + var geometries = object.geometries, i = -1, n = geometries.length; + while (++i < n) streamGeometry(geometries[i], stream); + } +}; + +function streamLine(coordinates, stream, closed) { + var i = -1, n = coordinates.length - closed, coordinate; + stream.lineStart(); + while (++i < n) coordinate = coordinates[i], stream.point(coordinate[0], coordinate[1], coordinate[2]); + stream.lineEnd(); +} + +function streamPolygon(coordinates, stream) { + var i = -1, n = coordinates.length; + stream.polygonStart(); + while (++i < n) streamLine(coordinates[i], stream, 1); + stream.polygonEnd(); +} + +function geoStream(object, stream) { + if (object && streamObjectType.hasOwnProperty(object.type)) { + streamObjectType[object.type](object, stream); + } else { + streamGeometry(object, stream); + } +} + +var areaRingSum$1 = new d3Array.Adder(); + +// hello? + +var areaSum$1 = new d3Array.Adder(), + lambda00$2, + phi00$2, + lambda0$2, + cosPhi0$1, + sinPhi0$1; + +var areaStream$1 = { + point: noop, + lineStart: noop, + lineEnd: noop, + polygonStart: function() { + areaRingSum$1 = new d3Array.Adder(); + areaStream$1.lineStart = areaRingStart$1; + areaStream$1.lineEnd = areaRingEnd$1; + }, + polygonEnd: function() { + var areaRing = +areaRingSum$1; + areaSum$1.add(areaRing < 0 ? tau + areaRing : areaRing); + this.lineStart = this.lineEnd = this.point = noop; + }, + sphere: function() { + areaSum$1.add(tau); + } +}; + +function areaRingStart$1() { + areaStream$1.point = areaPointFirst$1; +} + +function areaRingEnd$1() { + areaPoint$1(lambda00$2, phi00$2); +} + +function areaPointFirst$1(lambda, phi) { + areaStream$1.point = areaPoint$1; + lambda00$2 = lambda, phi00$2 = phi; + lambda *= radians, phi *= radians; + lambda0$2 = lambda, cosPhi0$1 = cos(phi = phi / 2 + quarterPi), sinPhi0$1 = sin(phi); +} + +function areaPoint$1(lambda, phi) { + lambda *= radians, phi *= radians; + phi = phi / 2 + quarterPi; // half the angular distance from south pole + + // Spherical excess E for a spherical triangle with vertices: south pole, + // previous point, current point. Uses a formula derived from Cagnoli’s + // theorem. See Todhunter, Spherical Trig. (1871), Sec. 103, Eq. (2). + var dLambda = lambda - lambda0$2, + sdLambda = dLambda >= 0 ? 1 : -1, + adLambda = sdLambda * dLambda, + cosPhi = cos(phi), + sinPhi = sin(phi), + k = sinPhi0$1 * sinPhi, + u = cosPhi0$1 * cosPhi + k * cos(adLambda), + v = k * sdLambda * sin(adLambda); + areaRingSum$1.add(atan2(v, u)); + + // Advance the previous points. + lambda0$2 = lambda, cosPhi0$1 = cosPhi, sinPhi0$1 = sinPhi; +} + +function area(object) { + areaSum$1 = new d3Array.Adder(); + geoStream(object, areaStream$1); + return areaSum$1 * 2; +} + +function spherical(cartesian) { + return [atan2(cartesian[1], cartesian[0]), asin(cartesian[2])]; +} + +function cartesian(spherical) { + var lambda = spherical[0], phi = spherical[1], cosPhi = cos(phi); + return [cosPhi * cos(lambda), cosPhi * sin(lambda), sin(phi)]; +} + +function cartesianDot(a, b) { + return a[0] * b[0] + a[1] * b[1] + a[2] * b[2]; +} + +function cartesianCross(a, b) { + return [a[1] * b[2] - a[2] * b[1], a[2] * b[0] - a[0] * b[2], a[0] * b[1] - a[1] * b[0]]; +} + +// TODO return a +function cartesianAddInPlace(a, b) { + a[0] += b[0], a[1] += b[1], a[2] += b[2]; +} + +function cartesianScale(vector, k) { + return [vector[0] * k, vector[1] * k, vector[2] * k]; +} + +// TODO return d +function cartesianNormalizeInPlace(d) { + var l = sqrt(d[0] * d[0] + d[1] * d[1] + d[2] * d[2]); + d[0] /= l, d[1] /= l, d[2] /= l; +} + +var lambda0$1, phi0, lambda1, phi1, // bounds + lambda2, // previous lambda-coordinate + lambda00$1, phi00$1, // first point + p0, // previous 3D point + deltaSum, + ranges, + range; + +var boundsStream$1 = { + point: boundsPoint$1, + lineStart: boundsLineStart, + lineEnd: boundsLineEnd, + polygonStart: function() { + boundsStream$1.point = boundsRingPoint; + boundsStream$1.lineStart = boundsRingStart; + boundsStream$1.lineEnd = boundsRingEnd; + deltaSum = new d3Array.Adder(); + areaStream$1.polygonStart(); + }, + polygonEnd: function() { + areaStream$1.polygonEnd(); + boundsStream$1.point = boundsPoint$1; + boundsStream$1.lineStart = boundsLineStart; + boundsStream$1.lineEnd = boundsLineEnd; + if (areaRingSum$1 < 0) lambda0$1 = -(lambda1 = 180), phi0 = -(phi1 = 90); + else if (deltaSum > epsilon) phi1 = 90; + else if (deltaSum < -epsilon) phi0 = -90; + range[0] = lambda0$1, range[1] = lambda1; + }, + sphere: function() { + lambda0$1 = -(lambda1 = 180), phi0 = -(phi1 = 90); + } +}; + +function boundsPoint$1(lambda, phi) { + ranges.push(range = [lambda0$1 = lambda, lambda1 = lambda]); + if (phi < phi0) phi0 = phi; + if (phi > phi1) phi1 = phi; +} + +function linePoint(lambda, phi) { + var p = cartesian([lambda * radians, phi * radians]); + if (p0) { + var normal = cartesianCross(p0, p), + equatorial = [normal[1], -normal[0], 0], + inflection = cartesianCross(equatorial, normal); + cartesianNormalizeInPlace(inflection); + inflection = spherical(inflection); + var delta = lambda - lambda2, + sign = delta > 0 ? 1 : -1, + lambdai = inflection[0] * degrees * sign, + phii, + antimeridian = abs(delta) > 180; + if (antimeridian ^ (sign * lambda2 < lambdai && lambdai < sign * lambda)) { + phii = inflection[1] * degrees; + if (phii > phi1) phi1 = phii; + } else if (lambdai = (lambdai + 360) % 360 - 180, antimeridian ^ (sign * lambda2 < lambdai && lambdai < sign * lambda)) { + phii = -inflection[1] * degrees; + if (phii < phi0) phi0 = phii; + } else { + if (phi < phi0) phi0 = phi; + if (phi > phi1) phi1 = phi; + } + if (antimeridian) { + if (lambda < lambda2) { + if (angle(lambda0$1, lambda) > angle(lambda0$1, lambda1)) lambda1 = lambda; + } else { + if (angle(lambda, lambda1) > angle(lambda0$1, lambda1)) lambda0$1 = lambda; + } + } else { + if (lambda1 >= lambda0$1) { + if (lambda < lambda0$1) lambda0$1 = lambda; + if (lambda > lambda1) lambda1 = lambda; + } else { + if (lambda > lambda2) { + if (angle(lambda0$1, lambda) > angle(lambda0$1, lambda1)) lambda1 = lambda; + } else { + if (angle(lambda, lambda1) > angle(lambda0$1, lambda1)) lambda0$1 = lambda; + } + } + } + } else { + ranges.push(range = [lambda0$1 = lambda, lambda1 = lambda]); + } + if (phi < phi0) phi0 = phi; + if (phi > phi1) phi1 = phi; + p0 = p, lambda2 = lambda; +} + +function boundsLineStart() { + boundsStream$1.point = linePoint; +} + +function boundsLineEnd() { + range[0] = lambda0$1, range[1] = lambda1; + boundsStream$1.point = boundsPoint$1; + p0 = null; +} + +function boundsRingPoint(lambda, phi) { + if (p0) { + var delta = lambda - lambda2; + deltaSum.add(abs(delta) > 180 ? delta + (delta > 0 ? 360 : -360) : delta); + } else { + lambda00$1 = lambda, phi00$1 = phi; + } + areaStream$1.point(lambda, phi); + linePoint(lambda, phi); +} + +function boundsRingStart() { + areaStream$1.lineStart(); +} + +function boundsRingEnd() { + boundsRingPoint(lambda00$1, phi00$1); + areaStream$1.lineEnd(); + if (abs(deltaSum) > epsilon) lambda0$1 = -(lambda1 = 180); + range[0] = lambda0$1, range[1] = lambda1; + p0 = null; +} + +// Finds the left-right distance between two longitudes. +// This is almost the same as (lambda1 - lambda0 + 360°) % 360°, except that we want +// the distance between ±180° to be 360°. +function angle(lambda0, lambda1) { + return (lambda1 -= lambda0) < 0 ? lambda1 + 360 : lambda1; +} + +function rangeCompare(a, b) { + return a[0] - b[0]; +} + +function rangeContains(range, x) { + return range[0] <= range[1] ? range[0] <= x && x <= range[1] : x < range[0] || range[1] < x; +} + +function bounds(feature) { + var i, n, a, b, merged, deltaMax, delta; + + phi1 = lambda1 = -(lambda0$1 = phi0 = Infinity); + ranges = []; + geoStream(feature, boundsStream$1); + + // First, sort ranges by their minimum longitudes. + if (n = ranges.length) { + ranges.sort(rangeCompare); + + // Then, merge any ranges that overlap. + for (i = 1, a = ranges[0], merged = [a]; i < n; ++i) { + b = ranges[i]; + if (rangeContains(a, b[0]) || rangeContains(a, b[1])) { + if (angle(a[0], b[1]) > angle(a[0], a[1])) a[1] = b[1]; + if (angle(b[0], a[1]) > angle(a[0], a[1])) a[0] = b[0]; + } else { + merged.push(a = b); + } + } + + // Finally, find the largest gap between the merged ranges. + // The final bounding box will be the inverse of this gap. + for (deltaMax = -Infinity, n = merged.length - 1, i = 0, a = merged[n]; i <= n; a = b, ++i) { + b = merged[i]; + if ((delta = angle(a[1], b[0])) > deltaMax) deltaMax = delta, lambda0$1 = b[0], lambda1 = a[1]; + } + } + + ranges = range = null; + + return lambda0$1 === Infinity || phi0 === Infinity + ? [[NaN, NaN], [NaN, NaN]] + : [[lambda0$1, phi0], [lambda1, phi1]]; +} + +var W0, W1, + X0$1, Y0$1, Z0$1, + X1$1, Y1$1, Z1$1, + X2$1, Y2$1, Z2$1, + lambda00, phi00, // first point + x0$4, y0$4, z0; // previous point + +var centroidStream$1 = { + sphere: noop, + point: centroidPoint$1, + lineStart: centroidLineStart$1, + lineEnd: centroidLineEnd$1, + polygonStart: function() { + centroidStream$1.lineStart = centroidRingStart$1; + centroidStream$1.lineEnd = centroidRingEnd$1; + }, + polygonEnd: function() { + centroidStream$1.lineStart = centroidLineStart$1; + centroidStream$1.lineEnd = centroidLineEnd$1; + } +}; + +// Arithmetic mean of Cartesian vectors. +function centroidPoint$1(lambda, phi) { + lambda *= radians, phi *= radians; + var cosPhi = cos(phi); + centroidPointCartesian(cosPhi * cos(lambda), cosPhi * sin(lambda), sin(phi)); +} + +function centroidPointCartesian(x, y, z) { + ++W0; + X0$1 += (x - X0$1) / W0; + Y0$1 += (y - Y0$1) / W0; + Z0$1 += (z - Z0$1) / W0; +} + +function centroidLineStart$1() { + centroidStream$1.point = centroidLinePointFirst; +} + +function centroidLinePointFirst(lambda, phi) { + lambda *= radians, phi *= radians; + var cosPhi = cos(phi); + x0$4 = cosPhi * cos(lambda); + y0$4 = cosPhi * sin(lambda); + z0 = sin(phi); + centroidStream$1.point = centroidLinePoint; + centroidPointCartesian(x0$4, y0$4, z0); +} + +function centroidLinePoint(lambda, phi) { + lambda *= radians, phi *= radians; + var cosPhi = cos(phi), + x = cosPhi * cos(lambda), + y = cosPhi * sin(lambda), + z = sin(phi), + w = atan2(sqrt((w = y0$4 * z - z0 * y) * w + (w = z0 * x - x0$4 * z) * w + (w = x0$4 * y - y0$4 * x) * w), x0$4 * x + y0$4 * y + z0 * z); + W1 += w; + X1$1 += w * (x0$4 + (x0$4 = x)); + Y1$1 += w * (y0$4 + (y0$4 = y)); + Z1$1 += w * (z0 + (z0 = z)); + centroidPointCartesian(x0$4, y0$4, z0); +} + +function centroidLineEnd$1() { + centroidStream$1.point = centroidPoint$1; +} + +// See J. E. Brock, The Inertia Tensor for a Spherical Triangle, +// J. Applied Mechanics 42, 239 (1975). +function centroidRingStart$1() { + centroidStream$1.point = centroidRingPointFirst; +} + +function centroidRingEnd$1() { + centroidRingPoint(lambda00, phi00); + centroidStream$1.point = centroidPoint$1; +} + +function centroidRingPointFirst(lambda, phi) { + lambda00 = lambda, phi00 = phi; + lambda *= radians, phi *= radians; + centroidStream$1.point = centroidRingPoint; + var cosPhi = cos(phi); + x0$4 = cosPhi * cos(lambda); + y0$4 = cosPhi * sin(lambda); + z0 = sin(phi); + centroidPointCartesian(x0$4, y0$4, z0); +} + +function centroidRingPoint(lambda, phi) { + lambda *= radians, phi *= radians; + var cosPhi = cos(phi), + x = cosPhi * cos(lambda), + y = cosPhi * sin(lambda), + z = sin(phi), + cx = y0$4 * z - z0 * y, + cy = z0 * x - x0$4 * z, + cz = x0$4 * y - y0$4 * x, + m = hypot(cx, cy, cz), + w = asin(m), // line weight = angle + v = m && -w / m; // area weight multiplier + X2$1.add(v * cx); + Y2$1.add(v * cy); + Z2$1.add(v * cz); + W1 += w; + X1$1 += w * (x0$4 + (x0$4 = x)); + Y1$1 += w * (y0$4 + (y0$4 = y)); + Z1$1 += w * (z0 + (z0 = z)); + centroidPointCartesian(x0$4, y0$4, z0); +} + +function centroid(object) { + W0 = W1 = + X0$1 = Y0$1 = Z0$1 = + X1$1 = Y1$1 = Z1$1 = 0; + X2$1 = new d3Array.Adder(); + Y2$1 = new d3Array.Adder(); + Z2$1 = new d3Array.Adder(); + geoStream(object, centroidStream$1); + + var x = +X2$1, + y = +Y2$1, + z = +Z2$1, + m = hypot(x, y, z); + + // If the area-weighted ccentroid is undefined, fall back to length-weighted ccentroid. + if (m < epsilon2) { + x = X1$1, y = Y1$1, z = Z1$1; + // If the feature has zero length, fall back to arithmetic mean of point vectors. + if (W1 < epsilon) x = X0$1, y = Y0$1, z = Z0$1; + m = hypot(x, y, z); + // If the feature still has an undefined ccentroid, then return. + if (m < epsilon2) return [NaN, NaN]; + } + + return [atan2(y, x) * degrees, asin(z / m) * degrees]; +} + +function constant(x) { + return function() { + return x; + }; +} + +function compose(a, b) { + + function compose(x, y) { + return x = a(x, y), b(x[0], x[1]); + } + + if (a.invert && b.invert) compose.invert = function(x, y) { + return x = b.invert(x, y), x && a.invert(x[0], x[1]); + }; + + return compose; +} + +function rotationIdentity(lambda, phi) { + if (abs(lambda) > pi) lambda -= Math.round(lambda / tau) * tau; + return [lambda, phi]; +} + +rotationIdentity.invert = rotationIdentity; + +function rotateRadians(deltaLambda, deltaPhi, deltaGamma) { + return (deltaLambda %= tau) ? (deltaPhi || deltaGamma ? compose(rotationLambda(deltaLambda), rotationPhiGamma(deltaPhi, deltaGamma)) + : rotationLambda(deltaLambda)) + : (deltaPhi || deltaGamma ? rotationPhiGamma(deltaPhi, deltaGamma) + : rotationIdentity); +} + +function forwardRotationLambda(deltaLambda) { + return function(lambda, phi) { + lambda += deltaLambda; + if (abs(lambda) > pi) lambda -= Math.round(lambda / tau) * tau; + return [lambda, phi]; + }; +} + +function rotationLambda(deltaLambda) { + var rotation = forwardRotationLambda(deltaLambda); + rotation.invert = forwardRotationLambda(-deltaLambda); + return rotation; +} + +function rotationPhiGamma(deltaPhi, deltaGamma) { + var cosDeltaPhi = cos(deltaPhi), + sinDeltaPhi = sin(deltaPhi), + cosDeltaGamma = cos(deltaGamma), + sinDeltaGamma = sin(deltaGamma); + + function rotation(lambda, phi) { + var cosPhi = cos(phi), + x = cos(lambda) * cosPhi, + y = sin(lambda) * cosPhi, + z = sin(phi), + k = z * cosDeltaPhi + x * sinDeltaPhi; + return [ + atan2(y * cosDeltaGamma - k * sinDeltaGamma, x * cosDeltaPhi - z * sinDeltaPhi), + asin(k * cosDeltaGamma + y * sinDeltaGamma) + ]; + } + + rotation.invert = function(lambda, phi) { + var cosPhi = cos(phi), + x = cos(lambda) * cosPhi, + y = sin(lambda) * cosPhi, + z = sin(phi), + k = z * cosDeltaGamma - y * sinDeltaGamma; + return [ + atan2(y * cosDeltaGamma + z * sinDeltaGamma, x * cosDeltaPhi + k * sinDeltaPhi), + asin(k * cosDeltaPhi - x * sinDeltaPhi) + ]; + }; + + return rotation; +} + +function rotation(rotate) { + rotate = rotateRadians(rotate[0] * radians, rotate[1] * radians, rotate.length > 2 ? rotate[2] * radians : 0); + + function forward(coordinates) { + coordinates = rotate(coordinates[0] * radians, coordinates[1] * radians); + return coordinates[0] *= degrees, coordinates[1] *= degrees, coordinates; + } + + forward.invert = function(coordinates) { + coordinates = rotate.invert(coordinates[0] * radians, coordinates[1] * radians); + return coordinates[0] *= degrees, coordinates[1] *= degrees, coordinates; + }; + + return forward; +} + +// Generates a circle centered at [0°, 0°], with a given radius and precision. +function circleStream(stream, radius, delta, direction, t0, t1) { + if (!delta) return; + var cosRadius = cos(radius), + sinRadius = sin(radius), + step = direction * delta; + if (t0 == null) { + t0 = radius + direction * tau; + t1 = radius - step / 2; + } else { + t0 = circleRadius(cosRadius, t0); + t1 = circleRadius(cosRadius, t1); + if (direction > 0 ? t0 < t1 : t0 > t1) t0 += direction * tau; + } + for (var point, t = t0; direction > 0 ? t > t1 : t < t1; t -= step) { + point = spherical([cosRadius, -sinRadius * cos(t), -sinRadius * sin(t)]); + stream.point(point[0], point[1]); + } +} + +// Returns the signed angle of a cartesian point relative to [cosRadius, 0, 0]. +function circleRadius(cosRadius, point) { + point = cartesian(point), point[0] -= cosRadius; + cartesianNormalizeInPlace(point); + var radius = acos(-point[1]); + return ((-point[2] < 0 ? -radius : radius) + tau - epsilon) % tau; +} + +function circle() { + var center = constant([0, 0]), + radius = constant(90), + precision = constant(2), + ring, + rotate, + stream = {point: point}; + + function point(x, y) { + ring.push(x = rotate(x, y)); + x[0] *= degrees, x[1] *= degrees; + } + + function circle() { + var c = center.apply(this, arguments), + r = radius.apply(this, arguments) * radians, + p = precision.apply(this, arguments) * radians; + ring = []; + rotate = rotateRadians(-c[0] * radians, -c[1] * radians, 0).invert; + circleStream(stream, r, p, 1); + c = {type: "Polygon", coordinates: [ring]}; + ring = rotate = null; + return c; + } + + circle.center = function(_) { + return arguments.length ? (center = typeof _ === "function" ? _ : constant([+_[0], +_[1]]), circle) : center; + }; + + circle.radius = function(_) { + return arguments.length ? (radius = typeof _ === "function" ? _ : constant(+_), circle) : radius; + }; + + circle.precision = function(_) { + return arguments.length ? (precision = typeof _ === "function" ? _ : constant(+_), circle) : precision; + }; + + return circle; +} + +function clipBuffer() { + var lines = [], + line; + return { + point: function(x, y, m) { + line.push([x, y, m]); + }, + lineStart: function() { + lines.push(line = []); + }, + lineEnd: noop, + rejoin: function() { + if (lines.length > 1) lines.push(lines.pop().concat(lines.shift())); + }, + result: function() { + var result = lines; + lines = []; + line = null; + return result; + } + }; +} + +function pointEqual(a, b) { + return abs(a[0] - b[0]) < epsilon && abs(a[1] - b[1]) < epsilon; +} + +function Intersection(point, points, other, entry) { + this.x = point; + this.z = points; + this.o = other; // another intersection + this.e = entry; // is an entry? + this.v = false; // visited + this.n = this.p = null; // next & previous +} + +// A generalized polygon clipping algorithm: given a polygon that has been cut +// into its visible line segments, and rejoins the segments by interpolating +// along the clip edge. +function clipRejoin(segments, compareIntersection, startInside, interpolate, stream) { + var subject = [], + clip = [], + i, + n; + + segments.forEach(function(segment) { + if ((n = segment.length - 1) <= 0) return; + var n, p0 = segment[0], p1 = segment[n], x; + + if (pointEqual(p0, p1)) { + if (!p0[2] && !p1[2]) { + stream.lineStart(); + for (i = 0; i < n; ++i) stream.point((p0 = segment[i])[0], p0[1]); + stream.lineEnd(); + return; + } + // handle degenerate cases by moving the point + p1[0] += 2 * epsilon; + } + + subject.push(x = new Intersection(p0, segment, null, true)); + clip.push(x.o = new Intersection(p0, null, x, false)); + subject.push(x = new Intersection(p1, segment, null, false)); + clip.push(x.o = new Intersection(p1, null, x, true)); + }); + + if (!subject.length) return; + + clip.sort(compareIntersection); + link(subject); + link(clip); + + for (i = 0, n = clip.length; i < n; ++i) { + clip[i].e = startInside = !startInside; + } + + var start = subject[0], + points, + point; + + while (1) { + // Find first unvisited intersection. + var current = start, + isSubject = true; + while (current.v) if ((current = current.n) === start) return; + points = current.z; + stream.lineStart(); + do { + current.v = current.o.v = true; + if (current.e) { + if (isSubject) { + for (i = 0, n = points.length; i < n; ++i) stream.point((point = points[i])[0], point[1]); + } else { + interpolate(current.x, current.n.x, 1, stream); + } + current = current.n; + } else { + if (isSubject) { + points = current.p.z; + for (i = points.length - 1; i >= 0; --i) stream.point((point = points[i])[0], point[1]); + } else { + interpolate(current.x, current.p.x, -1, stream); + } + current = current.p; + } + current = current.o; + points = current.z; + isSubject = !isSubject; + } while (!current.v); + stream.lineEnd(); + } +} + +function link(array) { + if (!(n = array.length)) return; + var n, + i = 0, + a = array[0], + b; + while (++i < n) { + a.n = b = array[i]; + b.p = a; + a = b; + } + a.n = b = array[0]; + b.p = a; +} + +function longitude(point) { + return abs(point[0]) <= pi ? point[0] : sign(point[0]) * ((abs(point[0]) + pi) % tau - pi); +} + +function polygonContains(polygon, point) { + var lambda = longitude(point), + phi = point[1], + sinPhi = sin(phi), + normal = [sin(lambda), -cos(lambda), 0], + angle = 0, + winding = 0; + + var sum = new d3Array.Adder(); + + if (sinPhi === 1) phi = halfPi + epsilon; + else if (sinPhi === -1) phi = -halfPi - epsilon; + + for (var i = 0, n = polygon.length; i < n; ++i) { + if (!(m = (ring = polygon[i]).length)) continue; + var ring, + m, + point0 = ring[m - 1], + lambda0 = longitude(point0), + phi0 = point0[1] / 2 + quarterPi, + sinPhi0 = sin(phi0), + cosPhi0 = cos(phi0); + + for (var j = 0; j < m; ++j, lambda0 = lambda1, sinPhi0 = sinPhi1, cosPhi0 = cosPhi1, point0 = point1) { + var point1 = ring[j], + lambda1 = longitude(point1), + phi1 = point1[1] / 2 + quarterPi, + sinPhi1 = sin(phi1), + cosPhi1 = cos(phi1), + delta = lambda1 - lambda0, + sign = delta >= 0 ? 1 : -1, + absDelta = sign * delta, + antimeridian = absDelta > pi, + k = sinPhi0 * sinPhi1; + + sum.add(atan2(k * sign * sin(absDelta), cosPhi0 * cosPhi1 + k * cos(absDelta))); + angle += antimeridian ? delta + sign * tau : delta; + + // Are the longitudes either side of the point’s meridian (lambda), + // and are the latitudes smaller than the parallel (phi)? + if (antimeridian ^ lambda0 >= lambda ^ lambda1 >= lambda) { + var arc = cartesianCross(cartesian(point0), cartesian(point1)); + cartesianNormalizeInPlace(arc); + var intersection = cartesianCross(normal, arc); + cartesianNormalizeInPlace(intersection); + var phiArc = (antimeridian ^ delta >= 0 ? -1 : 1) * asin(intersection[2]); + if (phi > phiArc || phi === phiArc && (arc[0] || arc[1])) { + winding += antimeridian ^ delta >= 0 ? 1 : -1; + } + } + } + } + + // First, determine whether the South pole is inside or outside: + // + // It is inside if: + // * the polygon winds around it in a clockwise direction. + // * the polygon does not (cumulatively) wind around it, but has a negative + // (counter-clockwise) area. + // + // Second, count the (signed) number of times a segment crosses a lambda + // from the point to the South pole. If it is zero, then the point is the + // same side as the South pole. + + return (angle < -epsilon || angle < epsilon && sum < -epsilon2) ^ (winding & 1); +} + +function clip(pointVisible, clipLine, interpolate, start) { + return function(sink) { + var line = clipLine(sink), + ringBuffer = clipBuffer(), + ringSink = clipLine(ringBuffer), + polygonStarted = false, + polygon, + segments, + ring; + + var clip = { + point: point, + lineStart: lineStart, + lineEnd: lineEnd, + polygonStart: function() { + clip.point = pointRing; + clip.lineStart = ringStart; + clip.lineEnd = ringEnd; + segments = []; + polygon = []; + }, + polygonEnd: function() { + clip.point = point; + clip.lineStart = lineStart; + clip.lineEnd = lineEnd; + segments = d3Array.merge(segments); + var startInside = polygonContains(polygon, start); + if (segments.length) { + if (!polygonStarted) sink.polygonStart(), polygonStarted = true; + clipRejoin(segments, compareIntersection, startInside, interpolate, sink); + } else if (startInside) { + if (!polygonStarted) sink.polygonStart(), polygonStarted = true; + sink.lineStart(); + interpolate(null, null, 1, sink); + sink.lineEnd(); + } + if (polygonStarted) sink.polygonEnd(), polygonStarted = false; + segments = polygon = null; + }, + sphere: function() { + sink.polygonStart(); + sink.lineStart(); + interpolate(null, null, 1, sink); + sink.lineEnd(); + sink.polygonEnd(); + } + }; + + function point(lambda, phi) { + if (pointVisible(lambda, phi)) sink.point(lambda, phi); + } + + function pointLine(lambda, phi) { + line.point(lambda, phi); + } + + function lineStart() { + clip.point = pointLine; + line.lineStart(); + } + + function lineEnd() { + clip.point = point; + line.lineEnd(); + } + + function pointRing(lambda, phi) { + ring.push([lambda, phi]); + ringSink.point(lambda, phi); + } + + function ringStart() { + ringSink.lineStart(); + ring = []; + } + + function ringEnd() { + pointRing(ring[0][0], ring[0][1]); + ringSink.lineEnd(); + + var clean = ringSink.clean(), + ringSegments = ringBuffer.result(), + i, n = ringSegments.length, m, + segment, + point; + + ring.pop(); + polygon.push(ring); + ring = null; + + if (!n) return; + + // No intersections. + if (clean & 1) { + segment = ringSegments[0]; + if ((m = segment.length - 1) > 0) { + if (!polygonStarted) sink.polygonStart(), polygonStarted = true; + sink.lineStart(); + for (i = 0; i < m; ++i) sink.point((point = segment[i])[0], point[1]); + sink.lineEnd(); + } + return; + } + + // Rejoin connected segments. + // TODO reuse ringBuffer.rejoin()? + if (n > 1 && clean & 2) ringSegments.push(ringSegments.pop().concat(ringSegments.shift())); + + segments.push(ringSegments.filter(validSegment)); + } + + return clip; + }; +} + +function validSegment(segment) { + return segment.length > 1; +} + +// Intersections are sorted along the clip edge. For both antimeridian cutting +// and circle clipping, the same comparison is used. +function compareIntersection(a, b) { + return ((a = a.x)[0] < 0 ? a[1] - halfPi - epsilon : halfPi - a[1]) + - ((b = b.x)[0] < 0 ? b[1] - halfPi - epsilon : halfPi - b[1]); +} + +var clipAntimeridian = clip( + function() { return true; }, + clipAntimeridianLine, + clipAntimeridianInterpolate, + [-pi, -halfPi] +); + +// Takes a line and cuts into visible segments. Return values: 0 - there were +// intersections or the line was empty; 1 - no intersections; 2 - there were +// intersections, and the first and last segments should be rejoined. +function clipAntimeridianLine(stream) { + var lambda0 = NaN, + phi0 = NaN, + sign0 = NaN, + clean; // no intersections + + return { + lineStart: function() { + stream.lineStart(); + clean = 1; + }, + point: function(lambda1, phi1) { + var sign1 = lambda1 > 0 ? pi : -pi, + delta = abs(lambda1 - lambda0); + if (abs(delta - pi) < epsilon) { // line crosses a pole + stream.point(lambda0, phi0 = (phi0 + phi1) / 2 > 0 ? halfPi : -halfPi); + stream.point(sign0, phi0); + stream.lineEnd(); + stream.lineStart(); + stream.point(sign1, phi0); + stream.point(lambda1, phi0); + clean = 0; + } else if (sign0 !== sign1 && delta >= pi) { // line crosses antimeridian + if (abs(lambda0 - sign0) < epsilon) lambda0 -= sign0 * epsilon; // handle degeneracies + if (abs(lambda1 - sign1) < epsilon) lambda1 -= sign1 * epsilon; + phi0 = clipAntimeridianIntersect(lambda0, phi0, lambda1, phi1); + stream.point(sign0, phi0); + stream.lineEnd(); + stream.lineStart(); + stream.point(sign1, phi0); + clean = 0; + } + stream.point(lambda0 = lambda1, phi0 = phi1); + sign0 = sign1; + }, + lineEnd: function() { + stream.lineEnd(); + lambda0 = phi0 = NaN; + }, + clean: function() { + return 2 - clean; // if intersections, rejoin first and last segments + } + }; +} + +function clipAntimeridianIntersect(lambda0, phi0, lambda1, phi1) { + var cosPhi0, + cosPhi1, + sinLambda0Lambda1 = sin(lambda0 - lambda1); + return abs(sinLambda0Lambda1) > epsilon + ? atan((sin(phi0) * (cosPhi1 = cos(phi1)) * sin(lambda1) + - sin(phi1) * (cosPhi0 = cos(phi0)) * sin(lambda0)) + / (cosPhi0 * cosPhi1 * sinLambda0Lambda1)) + : (phi0 + phi1) / 2; +} + +function clipAntimeridianInterpolate(from, to, direction, stream) { + var phi; + if (from == null) { + phi = direction * halfPi; + stream.point(-pi, phi); + stream.point(0, phi); + stream.point(pi, phi); + stream.point(pi, 0); + stream.point(pi, -phi); + stream.point(0, -phi); + stream.point(-pi, -phi); + stream.point(-pi, 0); + stream.point(-pi, phi); + } else if (abs(from[0] - to[0]) > epsilon) { + var lambda = from[0] < to[0] ? pi : -pi; + phi = direction * lambda / 2; + stream.point(-lambda, phi); + stream.point(0, phi); + stream.point(lambda, phi); + } else { + stream.point(to[0], to[1]); + } +} + +function clipCircle(radius) { + var cr = cos(radius), + delta = 2 * radians, + smallRadius = cr > 0, + notHemisphere = abs(cr) > epsilon; // TODO optimise for this common case + + function interpolate(from, to, direction, stream) { + circleStream(stream, radius, delta, direction, from, to); + } + + function visible(lambda, phi) { + return cos(lambda) * cos(phi) > cr; + } + + // Takes a line and cuts into visible segments. Return values used for polygon + // clipping: 0 - there were intersections or the line was empty; 1 - no + // intersections 2 - there were intersections, and the first and last segments + // should be rejoined. + function clipLine(stream) { + var point0, // previous point + c0, // code for previous point + v0, // visibility of previous point + v00, // visibility of first point + clean; // no intersections + return { + lineStart: function() { + v00 = v0 = false; + clean = 1; + }, + point: function(lambda, phi) { + var point1 = [lambda, phi], + point2, + v = visible(lambda, phi), + c = smallRadius + ? v ? 0 : code(lambda, phi) + : v ? code(lambda + (lambda < 0 ? pi : -pi), phi) : 0; + if (!point0 && (v00 = v0 = v)) stream.lineStart(); + if (v !== v0) { + point2 = intersect(point0, point1); + if (!point2 || pointEqual(point0, point2) || pointEqual(point1, point2)) + point1[2] = 1; + } + if (v !== v0) { + clean = 0; + if (v) { + // outside going in + stream.lineStart(); + point2 = intersect(point1, point0); + stream.point(point2[0], point2[1]); + } else { + // inside going out + point2 = intersect(point0, point1); + stream.point(point2[0], point2[1], 2); + stream.lineEnd(); + } + point0 = point2; + } else if (notHemisphere && point0 && smallRadius ^ v) { + var t; + // If the codes for two points are different, or are both zero, + // and there this segment intersects with the small circle. + if (!(c & c0) && (t = intersect(point1, point0, true))) { + clean = 0; + if (smallRadius) { + stream.lineStart(); + stream.point(t[0][0], t[0][1]); + stream.point(t[1][0], t[1][1]); + stream.lineEnd(); + } else { + stream.point(t[1][0], t[1][1]); + stream.lineEnd(); + stream.lineStart(); + stream.point(t[0][0], t[0][1], 3); + } + } + } + if (v && (!point0 || !pointEqual(point0, point1))) { + stream.point(point1[0], point1[1]); + } + point0 = point1, v0 = v, c0 = c; + }, + lineEnd: function() { + if (v0) stream.lineEnd(); + point0 = null; + }, + // Rejoin first and last segments if there were intersections and the first + // and last points were visible. + clean: function() { + return clean | ((v00 && v0) << 1); + } + }; + } + + // Intersects the great circle between a and b with the clip circle. + function intersect(a, b, two) { + var pa = cartesian(a), + pb = cartesian(b); + + // We have two planes, n1.p = d1 and n2.p = d2. + // Find intersection line p(t) = c1 n1 + c2 n2 + t (n1 ⨯ n2). + var n1 = [1, 0, 0], // normal + n2 = cartesianCross(pa, pb), + n2n2 = cartesianDot(n2, n2), + n1n2 = n2[0], // cartesianDot(n1, n2), + determinant = n2n2 - n1n2 * n1n2; + + // Two polar points. + if (!determinant) return !two && a; + + var c1 = cr * n2n2 / determinant, + c2 = -cr * n1n2 / determinant, + n1xn2 = cartesianCross(n1, n2), + A = cartesianScale(n1, c1), + B = cartesianScale(n2, c2); + cartesianAddInPlace(A, B); + + // Solve |p(t)|^2 = 1. + var u = n1xn2, + w = cartesianDot(A, u), + uu = cartesianDot(u, u), + t2 = w * w - uu * (cartesianDot(A, A) - 1); + + if (t2 < 0) return; + + var t = sqrt(t2), + q = cartesianScale(u, (-w - t) / uu); + cartesianAddInPlace(q, A); + q = spherical(q); + + if (!two) return q; + + // Two intersection points. + var lambda0 = a[0], + lambda1 = b[0], + phi0 = a[1], + phi1 = b[1], + z; + + if (lambda1 < lambda0) z = lambda0, lambda0 = lambda1, lambda1 = z; + + var delta = lambda1 - lambda0, + polar = abs(delta - pi) < epsilon, + meridian = polar || delta < epsilon; + + if (!polar && phi1 < phi0) z = phi0, phi0 = phi1, phi1 = z; + + // Check that the first point is between a and b. + if (meridian + ? polar + ? phi0 + phi1 > 0 ^ q[1] < (abs(q[0] - lambda0) < epsilon ? phi0 : phi1) + : phi0 <= q[1] && q[1] <= phi1 + : delta > pi ^ (lambda0 <= q[0] && q[0] <= lambda1)) { + var q1 = cartesianScale(u, (-w + t) / uu); + cartesianAddInPlace(q1, A); + return [q, spherical(q1)]; + } + } + + // Generates a 4-bit vector representing the location of a point relative to + // the small circle's bounding box. + function code(lambda, phi) { + var r = smallRadius ? radius : pi - radius, + code = 0; + if (lambda < -r) code |= 1; // left + else if (lambda > r) code |= 2; // right + if (phi < -r) code |= 4; // below + else if (phi > r) code |= 8; // above + return code; + } + + return clip(visible, clipLine, interpolate, smallRadius ? [0, -radius] : [-pi, radius - pi]); +} + +function clipLine(a, b, x0, y0, x1, y1) { + var ax = a[0], + ay = a[1], + bx = b[0], + by = b[1], + t0 = 0, + t1 = 1, + dx = bx - ax, + dy = by - ay, + r; + + r = x0 - ax; + if (!dx && r > 0) return; + r /= dx; + if (dx < 0) { + if (r < t0) return; + if (r < t1) t1 = r; + } else if (dx > 0) { + if (r > t1) return; + if (r > t0) t0 = r; + } + + r = x1 - ax; + if (!dx && r < 0) return; + r /= dx; + if (dx < 0) { + if (r > t1) return; + if (r > t0) t0 = r; + } else if (dx > 0) { + if (r < t0) return; + if (r < t1) t1 = r; + } + + r = y0 - ay; + if (!dy && r > 0) return; + r /= dy; + if (dy < 0) { + if (r < t0) return; + if (r < t1) t1 = r; + } else if (dy > 0) { + if (r > t1) return; + if (r > t0) t0 = r; + } + + r = y1 - ay; + if (!dy && r < 0) return; + r /= dy; + if (dy < 0) { + if (r > t1) return; + if (r > t0) t0 = r; + } else if (dy > 0) { + if (r < t0) return; + if (r < t1) t1 = r; + } + + if (t0 > 0) a[0] = ax + t0 * dx, a[1] = ay + t0 * dy; + if (t1 < 1) b[0] = ax + t1 * dx, b[1] = ay + t1 * dy; + return true; +} + +var clipMax = 1e9, clipMin = -clipMax; + +// TODO Use d3-polygon’s polygonContains here for the ring check? +// TODO Eliminate duplicate buffering in clipBuffer and polygon.push? + +function clipRectangle(x0, y0, x1, y1) { + + function visible(x, y) { + return x0 <= x && x <= x1 && y0 <= y && y <= y1; + } + + function interpolate(from, to, direction, stream) { + var a = 0, a1 = 0; + if (from == null + || (a = corner(from, direction)) !== (a1 = corner(to, direction)) + || comparePoint(from, to) < 0 ^ direction > 0) { + do stream.point(a === 0 || a === 3 ? x0 : x1, a > 1 ? y1 : y0); + while ((a = (a + direction + 4) % 4) !== a1); + } else { + stream.point(to[0], to[1]); + } + } + + function corner(p, direction) { + return abs(p[0] - x0) < epsilon ? direction > 0 ? 0 : 3 + : abs(p[0] - x1) < epsilon ? direction > 0 ? 2 : 1 + : abs(p[1] - y0) < epsilon ? direction > 0 ? 1 : 0 + : direction > 0 ? 3 : 2; // abs(p[1] - y1) < epsilon + } + + function compareIntersection(a, b) { + return comparePoint(a.x, b.x); + } + + function comparePoint(a, b) { + var ca = corner(a, 1), + cb = corner(b, 1); + return ca !== cb ? ca - cb + : ca === 0 ? b[1] - a[1] + : ca === 1 ? a[0] - b[0] + : ca === 2 ? a[1] - b[1] + : b[0] - a[0]; + } + + return function(stream) { + var activeStream = stream, + bufferStream = clipBuffer(), + segments, + polygon, + ring, + x__, y__, v__, // first point + x_, y_, v_, // previous point + first, + clean; + + var clipStream = { + point: point, + lineStart: lineStart, + lineEnd: lineEnd, + polygonStart: polygonStart, + polygonEnd: polygonEnd + }; + + function point(x, y) { + if (visible(x, y)) activeStream.point(x, y); + } + + function polygonInside() { + var winding = 0; + + for (var i = 0, n = polygon.length; i < n; ++i) { + for (var ring = polygon[i], j = 1, m = ring.length, point = ring[0], a0, a1, b0 = point[0], b1 = point[1]; j < m; ++j) { + a0 = b0, a1 = b1, point = ring[j], b0 = point[0], b1 = point[1]; + if (a1 <= y1) { if (b1 > y1 && (b0 - a0) * (y1 - a1) > (b1 - a1) * (x0 - a0)) ++winding; } + else { if (b1 <= y1 && (b0 - a0) * (y1 - a1) < (b1 - a1) * (x0 - a0)) --winding; } + } + } + + return winding; + } + + // Buffer geometry within a polygon and then clip it en masse. + function polygonStart() { + activeStream = bufferStream, segments = [], polygon = [], clean = true; + } + + function polygonEnd() { + var startInside = polygonInside(), + cleanInside = clean && startInside, + visible = (segments = d3Array.merge(segments)).length; + if (cleanInside || visible) { + stream.polygonStart(); + if (cleanInside) { + stream.lineStart(); + interpolate(null, null, 1, stream); + stream.lineEnd(); + } + if (visible) { + clipRejoin(segments, compareIntersection, startInside, interpolate, stream); + } + stream.polygonEnd(); + } + activeStream = stream, segments = polygon = ring = null; + } + + function lineStart() { + clipStream.point = linePoint; + if (polygon) polygon.push(ring = []); + first = true; + v_ = false; + x_ = y_ = NaN; + } + + // TODO rather than special-case polygons, simply handle them separately. + // Ideally, coincident intersection points should be jittered to avoid + // clipping issues. + function lineEnd() { + if (segments) { + linePoint(x__, y__); + if (v__ && v_) bufferStream.rejoin(); + segments.push(bufferStream.result()); + } + clipStream.point = point; + if (v_) activeStream.lineEnd(); + } + + function linePoint(x, y) { + var v = visible(x, y); + if (polygon) ring.push([x, y]); + if (first) { + x__ = x, y__ = y, v__ = v; + first = false; + if (v) { + activeStream.lineStart(); + activeStream.point(x, y); + } + } else { + if (v && v_) activeStream.point(x, y); + else { + var a = [x_ = Math.max(clipMin, Math.min(clipMax, x_)), y_ = Math.max(clipMin, Math.min(clipMax, y_))], + b = [x = Math.max(clipMin, Math.min(clipMax, x)), y = Math.max(clipMin, Math.min(clipMax, y))]; + if (clipLine(a, b, x0, y0, x1, y1)) { + if (!v_) { + activeStream.lineStart(); + activeStream.point(a[0], a[1]); + } + activeStream.point(b[0], b[1]); + if (!v) activeStream.lineEnd(); + clean = false; + } else if (v) { + activeStream.lineStart(); + activeStream.point(x, y); + clean = false; + } + } + } + x_ = x, y_ = y, v_ = v; + } + + return clipStream; + }; +} + +function extent() { + var x0 = 0, + y0 = 0, + x1 = 960, + y1 = 500, + cache, + cacheStream, + clip; + + return clip = { + stream: function(stream) { + return cache && cacheStream === stream ? cache : cache = clipRectangle(x0, y0, x1, y1)(cacheStream = stream); + }, + extent: function(_) { + return arguments.length ? (x0 = +_[0][0], y0 = +_[0][1], x1 = +_[1][0], y1 = +_[1][1], cache = cacheStream = null, clip) : [[x0, y0], [x1, y1]]; + } + }; +} + +var lengthSum$1, + lambda0, + sinPhi0, + cosPhi0; + +var lengthStream$1 = { + sphere: noop, + point: noop, + lineStart: lengthLineStart, + lineEnd: noop, + polygonStart: noop, + polygonEnd: noop +}; + +function lengthLineStart() { + lengthStream$1.point = lengthPointFirst$1; + lengthStream$1.lineEnd = lengthLineEnd; +} + +function lengthLineEnd() { + lengthStream$1.point = lengthStream$1.lineEnd = noop; +} + +function lengthPointFirst$1(lambda, phi) { + lambda *= radians, phi *= radians; + lambda0 = lambda, sinPhi0 = sin(phi), cosPhi0 = cos(phi); + lengthStream$1.point = lengthPoint$1; +} + +function lengthPoint$1(lambda, phi) { + lambda *= radians, phi *= radians; + var sinPhi = sin(phi), + cosPhi = cos(phi), + delta = abs(lambda - lambda0), + cosDelta = cos(delta), + sinDelta = sin(delta), + x = cosPhi * sinDelta, + y = cosPhi0 * sinPhi - sinPhi0 * cosPhi * cosDelta, + z = sinPhi0 * sinPhi + cosPhi0 * cosPhi * cosDelta; + lengthSum$1.add(atan2(sqrt(x * x + y * y), z)); + lambda0 = lambda, sinPhi0 = sinPhi, cosPhi0 = cosPhi; +} + +function length(object) { + lengthSum$1 = new d3Array.Adder(); + geoStream(object, lengthStream$1); + return +lengthSum$1; +} + +var coordinates = [null, null], + object = {type: "LineString", coordinates: coordinates}; + +function distance(a, b) { + coordinates[0] = a; + coordinates[1] = b; + return length(object); +} + +var containsObjectType = { + Feature: function(object, point) { + return containsGeometry(object.geometry, point); + }, + FeatureCollection: function(object, point) { + var features = object.features, i = -1, n = features.length; + while (++i < n) if (containsGeometry(features[i].geometry, point)) return true; + return false; + } +}; + +var containsGeometryType = { + Sphere: function() { + return true; + }, + Point: function(object, point) { + return containsPoint(object.coordinates, point); + }, + MultiPoint: function(object, point) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) if (containsPoint(coordinates[i], point)) return true; + return false; + }, + LineString: function(object, point) { + return containsLine(object.coordinates, point); + }, + MultiLineString: function(object, point) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) if (containsLine(coordinates[i], point)) return true; + return false; + }, + Polygon: function(object, point) { + return containsPolygon(object.coordinates, point); + }, + MultiPolygon: function(object, point) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) if (containsPolygon(coordinates[i], point)) return true; + return false; + }, + GeometryCollection: function(object, point) { + var geometries = object.geometries, i = -1, n = geometries.length; + while (++i < n) if (containsGeometry(geometries[i], point)) return true; + return false; + } +}; + +function containsGeometry(geometry, point) { + return geometry && containsGeometryType.hasOwnProperty(geometry.type) + ? containsGeometryType[geometry.type](geometry, point) + : false; +} + +function containsPoint(coordinates, point) { + return distance(coordinates, point) === 0; +} + +function containsLine(coordinates, point) { + var ao, bo, ab; + for (var i = 0, n = coordinates.length; i < n; i++) { + bo = distance(coordinates[i], point); + if (bo === 0) return true; + if (i > 0) { + ab = distance(coordinates[i], coordinates[i - 1]); + if ( + ab > 0 && + ao <= ab && + bo <= ab && + (ao + bo - ab) * (1 - Math.pow((ao - bo) / ab, 2)) < epsilon2 * ab + ) + return true; + } + ao = bo; + } + return false; +} + +function containsPolygon(coordinates, point) { + return !!polygonContains(coordinates.map(ringRadians), pointRadians(point)); +} + +function ringRadians(ring) { + return ring = ring.map(pointRadians), ring.pop(), ring; +} + +function pointRadians(point) { + return [point[0] * radians, point[1] * radians]; +} + +function contains(object, point) { + return (object && containsObjectType.hasOwnProperty(object.type) + ? containsObjectType[object.type] + : containsGeometry)(object, point); +} + +function graticuleX(y0, y1, dy) { + var y = d3Array.range(y0, y1 - epsilon, dy).concat(y1); + return function(x) { return y.map(function(y) { return [x, y]; }); }; +} + +function graticuleY(x0, x1, dx) { + var x = d3Array.range(x0, x1 - epsilon, dx).concat(x1); + return function(y) { return x.map(function(x) { return [x, y]; }); }; +} + +function graticule() { + var x1, x0, X1, X0, + y1, y0, Y1, Y0, + dx = 10, dy = dx, DX = 90, DY = 360, + x, y, X, Y, + precision = 2.5; + + function graticule() { + return {type: "MultiLineString", coordinates: lines()}; + } + + function lines() { + return d3Array.range(ceil(X0 / DX) * DX, X1, DX).map(X) + .concat(d3Array.range(ceil(Y0 / DY) * DY, Y1, DY).map(Y)) + .concat(d3Array.range(ceil(x0 / dx) * dx, x1, dx).filter(function(x) { return abs(x % DX) > epsilon; }).map(x)) + .concat(d3Array.range(ceil(y0 / dy) * dy, y1, dy).filter(function(y) { return abs(y % DY) > epsilon; }).map(y)); + } + + graticule.lines = function() { + return lines().map(function(coordinates) { return {type: "LineString", coordinates: coordinates}; }); + }; + + graticule.outline = function() { + return { + type: "Polygon", + coordinates: [ + X(X0).concat( + Y(Y1).slice(1), + X(X1).reverse().slice(1), + Y(Y0).reverse().slice(1)) + ] + }; + }; + + graticule.extent = function(_) { + if (!arguments.length) return graticule.extentMinor(); + return graticule.extentMajor(_).extentMinor(_); + }; + + graticule.extentMajor = function(_) { + if (!arguments.length) return [[X0, Y0], [X1, Y1]]; + X0 = +_[0][0], X1 = +_[1][0]; + Y0 = +_[0][1], Y1 = +_[1][1]; + if (X0 > X1) _ = X0, X0 = X1, X1 = _; + if (Y0 > Y1) _ = Y0, Y0 = Y1, Y1 = _; + return graticule.precision(precision); + }; + + graticule.extentMinor = function(_) { + if (!arguments.length) return [[x0, y0], [x1, y1]]; + x0 = +_[0][0], x1 = +_[1][0]; + y0 = +_[0][1], y1 = +_[1][1]; + if (x0 > x1) _ = x0, x0 = x1, x1 = _; + if (y0 > y1) _ = y0, y0 = y1, y1 = _; + return graticule.precision(precision); + }; + + graticule.step = function(_) { + if (!arguments.length) return graticule.stepMinor(); + return graticule.stepMajor(_).stepMinor(_); + }; + + graticule.stepMajor = function(_) { + if (!arguments.length) return [DX, DY]; + DX = +_[0], DY = +_[1]; + return graticule; + }; + + graticule.stepMinor = function(_) { + if (!arguments.length) return [dx, dy]; + dx = +_[0], dy = +_[1]; + return graticule; + }; + + graticule.precision = function(_) { + if (!arguments.length) return precision; + precision = +_; + x = graticuleX(y0, y1, 90); + y = graticuleY(x0, x1, precision); + X = graticuleX(Y0, Y1, 90); + Y = graticuleY(X0, X1, precision); + return graticule; + }; + + return graticule + .extentMajor([[-180, -90 + epsilon], [180, 90 - epsilon]]) + .extentMinor([[-180, -80 - epsilon], [180, 80 + epsilon]]); +} + +function graticule10() { + return graticule()(); +} + +function interpolate(a, b) { + var x0 = a[0] * radians, + y0 = a[1] * radians, + x1 = b[0] * radians, + y1 = b[1] * radians, + cy0 = cos(y0), + sy0 = sin(y0), + cy1 = cos(y1), + sy1 = sin(y1), + kx0 = cy0 * cos(x0), + ky0 = cy0 * sin(x0), + kx1 = cy1 * cos(x1), + ky1 = cy1 * sin(x1), + d = 2 * asin(sqrt(haversin(y1 - y0) + cy0 * cy1 * haversin(x1 - x0))), + k = sin(d); + + var interpolate = d ? function(t) { + var B = sin(t *= d) / k, + A = sin(d - t) / k, + x = A * kx0 + B * kx1, + y = A * ky0 + B * ky1, + z = A * sy0 + B * sy1; + return [ + atan2(y, x) * degrees, + atan2(z, sqrt(x * x + y * y)) * degrees + ]; + } : function() { + return [x0 * degrees, y0 * degrees]; + }; + + interpolate.distance = d; + + return interpolate; +} + +var identity$1 = x => x; + +var areaSum = new d3Array.Adder(), + areaRingSum = new d3Array.Adder(), + x00$2, + y00$2, + x0$3, + y0$3; + +var areaStream = { + point: noop, + lineStart: noop, + lineEnd: noop, + polygonStart: function() { + areaStream.lineStart = areaRingStart; + areaStream.lineEnd = areaRingEnd; + }, + polygonEnd: function() { + areaStream.lineStart = areaStream.lineEnd = areaStream.point = noop; + areaSum.add(abs(areaRingSum)); + areaRingSum = new d3Array.Adder(); + }, + result: function() { + var area = areaSum / 2; + areaSum = new d3Array.Adder(); + return area; + } +}; + +function areaRingStart() { + areaStream.point = areaPointFirst; +} + +function areaPointFirst(x, y) { + areaStream.point = areaPoint; + x00$2 = x0$3 = x, y00$2 = y0$3 = y; +} + +function areaPoint(x, y) { + areaRingSum.add(y0$3 * x - x0$3 * y); + x0$3 = x, y0$3 = y; +} + +function areaRingEnd() { + areaPoint(x00$2, y00$2); +} + +var x0$2 = Infinity, + y0$2 = x0$2, + x1 = -x0$2, + y1 = x1; + +var boundsStream = { + point: boundsPoint, + lineStart: noop, + lineEnd: noop, + polygonStart: noop, + polygonEnd: noop, + result: function() { + var bounds = [[x0$2, y0$2], [x1, y1]]; + x1 = y1 = -(y0$2 = x0$2 = Infinity); + return bounds; + } +}; + +function boundsPoint(x, y) { + if (x < x0$2) x0$2 = x; + if (x > x1) x1 = x; + if (y < y0$2) y0$2 = y; + if (y > y1) y1 = y; +} + +// TODO Enforce positive area for exterior, negative area for interior? + +var X0 = 0, + Y0 = 0, + Z0 = 0, + X1 = 0, + Y1 = 0, + Z1 = 0, + X2 = 0, + Y2 = 0, + Z2 = 0, + x00$1, + y00$1, + x0$1, + y0$1; + +var centroidStream = { + point: centroidPoint, + lineStart: centroidLineStart, + lineEnd: centroidLineEnd, + polygonStart: function() { + centroidStream.lineStart = centroidRingStart; + centroidStream.lineEnd = centroidRingEnd; + }, + polygonEnd: function() { + centroidStream.point = centroidPoint; + centroidStream.lineStart = centroidLineStart; + centroidStream.lineEnd = centroidLineEnd; + }, + result: function() { + var centroid = Z2 ? [X2 / Z2, Y2 / Z2] + : Z1 ? [X1 / Z1, Y1 / Z1] + : Z0 ? [X0 / Z0, Y0 / Z0] + : [NaN, NaN]; + X0 = Y0 = Z0 = + X1 = Y1 = Z1 = + X2 = Y2 = Z2 = 0; + return centroid; + } +}; + +function centroidPoint(x, y) { + X0 += x; + Y0 += y; + ++Z0; +} + +function centroidLineStart() { + centroidStream.point = centroidPointFirstLine; +} + +function centroidPointFirstLine(x, y) { + centroidStream.point = centroidPointLine; + centroidPoint(x0$1 = x, y0$1 = y); +} + +function centroidPointLine(x, y) { + var dx = x - x0$1, dy = y - y0$1, z = sqrt(dx * dx + dy * dy); + X1 += z * (x0$1 + x) / 2; + Y1 += z * (y0$1 + y) / 2; + Z1 += z; + centroidPoint(x0$1 = x, y0$1 = y); +} + +function centroidLineEnd() { + centroidStream.point = centroidPoint; +} + +function centroidRingStart() { + centroidStream.point = centroidPointFirstRing; +} + +function centroidRingEnd() { + centroidPointRing(x00$1, y00$1); +} + +function centroidPointFirstRing(x, y) { + centroidStream.point = centroidPointRing; + centroidPoint(x00$1 = x0$1 = x, y00$1 = y0$1 = y); +} + +function centroidPointRing(x, y) { + var dx = x - x0$1, + dy = y - y0$1, + z = sqrt(dx * dx + dy * dy); + + X1 += z * (x0$1 + x) / 2; + Y1 += z * (y0$1 + y) / 2; + Z1 += z; + + z = y0$1 * x - x0$1 * y; + X2 += z * (x0$1 + x); + Y2 += z * (y0$1 + y); + Z2 += z * 3; + centroidPoint(x0$1 = x, y0$1 = y); +} + +function PathContext(context) { + this._context = context; +} + +PathContext.prototype = { + _radius: 4.5, + pointRadius: function(_) { + return this._radius = _, this; + }, + polygonStart: function() { + this._line = 0; + }, + polygonEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._point = 0; + }, + lineEnd: function() { + if (this._line === 0) this._context.closePath(); + this._point = NaN; + }, + point: function(x, y) { + switch (this._point) { + case 0: { + this._context.moveTo(x, y); + this._point = 1; + break; + } + case 1: { + this._context.lineTo(x, y); + break; + } + default: { + this._context.moveTo(x + this._radius, y); + this._context.arc(x, y, this._radius, 0, tau); + break; + } + } + }, + result: noop +}; + +var lengthSum = new d3Array.Adder(), + lengthRing, + x00, + y00, + x0, + y0; + +var lengthStream = { + point: noop, + lineStart: function() { + lengthStream.point = lengthPointFirst; + }, + lineEnd: function() { + if (lengthRing) lengthPoint(x00, y00); + lengthStream.point = noop; + }, + polygonStart: function() { + lengthRing = true; + }, + polygonEnd: function() { + lengthRing = null; + }, + result: function() { + var length = +lengthSum; + lengthSum = new d3Array.Adder(); + return length; + } +}; + +function lengthPointFirst(x, y) { + lengthStream.point = lengthPoint; + x00 = x0 = x, y00 = y0 = y; +} + +function lengthPoint(x, y) { + x0 -= x, y0 -= y; + lengthSum.add(sqrt(x0 * x0 + y0 * y0)); + x0 = x, y0 = y; +} + +// Simple caching for constant-radius points. +let cacheDigits, cacheAppend, cacheRadius, cacheCircle; + +class PathString { + constructor(digits) { + this._append = digits == null ? append : appendRound(digits); + this._radius = 4.5; + this._ = ""; + } + pointRadius(_) { + this._radius = +_; + return this; + } + polygonStart() { + this._line = 0; + } + polygonEnd() { + this._line = NaN; + } + lineStart() { + this._point = 0; + } + lineEnd() { + if (this._line === 0) this._ += "Z"; + this._point = NaN; + } + point(x, y) { + switch (this._point) { + case 0: { + this._append`M${x},${y}`; + this._point = 1; + break; + } + case 1: { + this._append`L${x},${y}`; + break; + } + default: { + this._append`M${x},${y}`; + if (this._radius !== cacheRadius || this._append !== cacheAppend) { + const r = this._radius; + const s = this._; + this._ = ""; // stash the old string so we can cache the circle path fragment + this._append`m0,${r}a${r},${r} 0 1,1 0,${-2 * r}a${r},${r} 0 1,1 0,${2 * r}z`; + cacheRadius = r; + cacheAppend = this._append; + cacheCircle = this._; + this._ = s; + } + this._ += cacheCircle; + break; + } + } + } + result() { + const result = this._; + this._ = ""; + return result.length ? result : null; + } +} + +function append(strings) { + let i = 1; + this._ += strings[0]; + for (const j = strings.length; i < j; ++i) { + this._ += arguments[i] + strings[i]; + } +} + +function appendRound(digits) { + const d = Math.floor(digits); + if (!(d >= 0)) throw new RangeError(`invalid digits: ${digits}`); + if (d > 15) return append; + if (d !== cacheDigits) { + const k = 10 ** d; + cacheDigits = d; + cacheAppend = function append(strings) { + let i = 1; + this._ += strings[0]; + for (const j = strings.length; i < j; ++i) { + this._ += Math.round(arguments[i] * k) / k + strings[i]; + } + }; + } + return cacheAppend; +} + +function index(projection, context) { + let digits = 3, + pointRadius = 4.5, + projectionStream, + contextStream; + + function path(object) { + if (object) { + if (typeof pointRadius === "function") contextStream.pointRadius(+pointRadius.apply(this, arguments)); + geoStream(object, projectionStream(contextStream)); + } + return contextStream.result(); + } + + path.area = function(object) { + geoStream(object, projectionStream(areaStream)); + return areaStream.result(); + }; + + path.measure = function(object) { + geoStream(object, projectionStream(lengthStream)); + return lengthStream.result(); + }; + + path.bounds = function(object) { + geoStream(object, projectionStream(boundsStream)); + return boundsStream.result(); + }; + + path.centroid = function(object) { + geoStream(object, projectionStream(centroidStream)); + return centroidStream.result(); + }; + + path.projection = function(_) { + if (!arguments.length) return projection; + projectionStream = _ == null ? (projection = null, identity$1) : (projection = _).stream; + return path; + }; + + path.context = function(_) { + if (!arguments.length) return context; + contextStream = _ == null ? (context = null, new PathString(digits)) : new PathContext(context = _); + if (typeof pointRadius !== "function") contextStream.pointRadius(pointRadius); + return path; + }; + + path.pointRadius = function(_) { + if (!arguments.length) return pointRadius; + pointRadius = typeof _ === "function" ? _ : (contextStream.pointRadius(+_), +_); + return path; + }; + + path.digits = function(_) { + if (!arguments.length) return digits; + if (_ == null) digits = null; + else { + const d = Math.floor(_); + if (!(d >= 0)) throw new RangeError(`invalid digits: ${_}`); + digits = d; + } + if (context === null) contextStream = new PathString(digits); + return path; + }; + + return path.projection(projection).digits(digits).context(context); +} + +function transform(methods) { + return { + stream: transformer(methods) + }; +} + +function transformer(methods) { + return function(stream) { + var s = new TransformStream; + for (var key in methods) s[key] = methods[key]; + s.stream = stream; + return s; + }; +} + +function TransformStream() {} + +TransformStream.prototype = { + constructor: TransformStream, + point: function(x, y) { this.stream.point(x, y); }, + sphere: function() { this.stream.sphere(); }, + lineStart: function() { this.stream.lineStart(); }, + lineEnd: function() { this.stream.lineEnd(); }, + polygonStart: function() { this.stream.polygonStart(); }, + polygonEnd: function() { this.stream.polygonEnd(); } +}; + +function fit(projection, fitBounds, object) { + var clip = projection.clipExtent && projection.clipExtent(); + projection.scale(150).translate([0, 0]); + if (clip != null) projection.clipExtent(null); + geoStream(object, projection.stream(boundsStream)); + fitBounds(boundsStream.result()); + if (clip != null) projection.clipExtent(clip); + return projection; +} + +function fitExtent(projection, extent, object) { + return fit(projection, function(b) { + var w = extent[1][0] - extent[0][0], + h = extent[1][1] - extent[0][1], + k = Math.min(w / (b[1][0] - b[0][0]), h / (b[1][1] - b[0][1])), + x = +extent[0][0] + (w - k * (b[1][0] + b[0][0])) / 2, + y = +extent[0][1] + (h - k * (b[1][1] + b[0][1])) / 2; + projection.scale(150 * k).translate([x, y]); + }, object); +} + +function fitSize(projection, size, object) { + return fitExtent(projection, [[0, 0], size], object); +} + +function fitWidth(projection, width, object) { + return fit(projection, function(b) { + var w = +width, + k = w / (b[1][0] - b[0][0]), + x = (w - k * (b[1][0] + b[0][0])) / 2, + y = -k * b[0][1]; + projection.scale(150 * k).translate([x, y]); + }, object); +} + +function fitHeight(projection, height, object) { + return fit(projection, function(b) { + var h = +height, + k = h / (b[1][1] - b[0][1]), + x = -k * b[0][0], + y = (h - k * (b[1][1] + b[0][1])) / 2; + projection.scale(150 * k).translate([x, y]); + }, object); +} + +var maxDepth = 16, // maximum depth of subdivision + cosMinDistance = cos(30 * radians); // cos(minimum angular distance) + +function resample(project, delta2) { + return +delta2 ? resample$1(project, delta2) : resampleNone(project); +} + +function resampleNone(project) { + return transformer({ + point: function(x, y) { + x = project(x, y); + this.stream.point(x[0], x[1]); + } + }); +} + +function resample$1(project, delta2) { + + function resampleLineTo(x0, y0, lambda0, a0, b0, c0, x1, y1, lambda1, a1, b1, c1, depth, stream) { + var dx = x1 - x0, + dy = y1 - y0, + d2 = dx * dx + dy * dy; + if (d2 > 4 * delta2 && depth--) { + var a = a0 + a1, + b = b0 + b1, + c = c0 + c1, + m = sqrt(a * a + b * b + c * c), + phi2 = asin(c /= m), + lambda2 = abs(abs(c) - 1) < epsilon || abs(lambda0 - lambda1) < epsilon ? (lambda0 + lambda1) / 2 : atan2(b, a), + p = project(lambda2, phi2), + x2 = p[0], + y2 = p[1], + dx2 = x2 - x0, + dy2 = y2 - y0, + dz = dy * dx2 - dx * dy2; + if (dz * dz / d2 > delta2 // perpendicular projected distance + || abs((dx * dx2 + dy * dy2) / d2 - 0.5) > 0.3 // midpoint close to an end + || a0 * a1 + b0 * b1 + c0 * c1 < cosMinDistance) { // angular distance + resampleLineTo(x0, y0, lambda0, a0, b0, c0, x2, y2, lambda2, a /= m, b /= m, c, depth, stream); + stream.point(x2, y2); + resampleLineTo(x2, y2, lambda2, a, b, c, x1, y1, lambda1, a1, b1, c1, depth, stream); + } + } + } + return function(stream) { + var lambda00, x00, y00, a00, b00, c00, // first point + lambda0, x0, y0, a0, b0, c0; // previous point + + var resampleStream = { + point: point, + lineStart: lineStart, + lineEnd: lineEnd, + polygonStart: function() { stream.polygonStart(); resampleStream.lineStart = ringStart; }, + polygonEnd: function() { stream.polygonEnd(); resampleStream.lineStart = lineStart; } + }; + + function point(x, y) { + x = project(x, y); + stream.point(x[0], x[1]); + } + + function lineStart() { + x0 = NaN; + resampleStream.point = linePoint; + stream.lineStart(); + } + + function linePoint(lambda, phi) { + var c = cartesian([lambda, phi]), p = project(lambda, phi); + resampleLineTo(x0, y0, lambda0, a0, b0, c0, x0 = p[0], y0 = p[1], lambda0 = lambda, a0 = c[0], b0 = c[1], c0 = c[2], maxDepth, stream); + stream.point(x0, y0); + } + + function lineEnd() { + resampleStream.point = point; + stream.lineEnd(); + } + + function ringStart() { + lineStart(); + resampleStream.point = ringPoint; + resampleStream.lineEnd = ringEnd; + } + + function ringPoint(lambda, phi) { + linePoint(lambda00 = lambda, phi), x00 = x0, y00 = y0, a00 = a0, b00 = b0, c00 = c0; + resampleStream.point = linePoint; + } + + function ringEnd() { + resampleLineTo(x0, y0, lambda0, a0, b0, c0, x00, y00, lambda00, a00, b00, c00, maxDepth, stream); + resampleStream.lineEnd = lineEnd; + lineEnd(); + } + + return resampleStream; + }; +} + +var transformRadians = transformer({ + point: function(x, y) { + this.stream.point(x * radians, y * radians); + } +}); + +function transformRotate(rotate) { + return transformer({ + point: function(x, y) { + var r = rotate(x, y); + return this.stream.point(r[0], r[1]); + } + }); +} + +function scaleTranslate(k, dx, dy, sx, sy) { + function transform(x, y) { + x *= sx; y *= sy; + return [dx + k * x, dy - k * y]; + } + transform.invert = function(x, y) { + return [(x - dx) / k * sx, (dy - y) / k * sy]; + }; + return transform; +} + +function scaleTranslateRotate(k, dx, dy, sx, sy, alpha) { + if (!alpha) return scaleTranslate(k, dx, dy, sx, sy); + var cosAlpha = cos(alpha), + sinAlpha = sin(alpha), + a = cosAlpha * k, + b = sinAlpha * k, + ai = cosAlpha / k, + bi = sinAlpha / k, + ci = (sinAlpha * dy - cosAlpha * dx) / k, + fi = (sinAlpha * dx + cosAlpha * dy) / k; + function transform(x, y) { + x *= sx; y *= sy; + return [a * x - b * y + dx, dy - b * x - a * y]; + } + transform.invert = function(x, y) { + return [sx * (ai * x - bi * y + ci), sy * (fi - bi * x - ai * y)]; + }; + return transform; +} + +function projection(project) { + return projectionMutator(function() { return project; })(); +} + +function projectionMutator(projectAt) { + var project, + k = 150, // scale + x = 480, y = 250, // translate + lambda = 0, phi = 0, // center + deltaLambda = 0, deltaPhi = 0, deltaGamma = 0, rotate, // pre-rotate + alpha = 0, // post-rotate angle + sx = 1, // reflectX + sy = 1, // reflectX + theta = null, preclip = clipAntimeridian, // pre-clip angle + x0 = null, y0, x1, y1, postclip = identity$1, // post-clip extent + delta2 = 0.5, // precision + projectResample, + projectTransform, + projectRotateTransform, + cache, + cacheStream; + + function projection(point) { + return projectRotateTransform(point[0] * radians, point[1] * radians); + } + + function invert(point) { + point = projectRotateTransform.invert(point[0], point[1]); + return point && [point[0] * degrees, point[1] * degrees]; + } + + projection.stream = function(stream) { + return cache && cacheStream === stream ? cache : cache = transformRadians(transformRotate(rotate)(preclip(projectResample(postclip(cacheStream = stream))))); + }; + + projection.preclip = function(_) { + return arguments.length ? (preclip = _, theta = undefined, reset()) : preclip; + }; + + projection.postclip = function(_) { + return arguments.length ? (postclip = _, x0 = y0 = x1 = y1 = null, reset()) : postclip; + }; + + projection.clipAngle = function(_) { + return arguments.length ? (preclip = +_ ? clipCircle(theta = _ * radians) : (theta = null, clipAntimeridian), reset()) : theta * degrees; + }; + + projection.clipExtent = function(_) { + return arguments.length ? (postclip = _ == null ? (x0 = y0 = x1 = y1 = null, identity$1) : clipRectangle(x0 = +_[0][0], y0 = +_[0][1], x1 = +_[1][0], y1 = +_[1][1]), reset()) : x0 == null ? null : [[x0, y0], [x1, y1]]; + }; + + projection.scale = function(_) { + return arguments.length ? (k = +_, recenter()) : k; + }; + + projection.translate = function(_) { + return arguments.length ? (x = +_[0], y = +_[1], recenter()) : [x, y]; + }; + + projection.center = function(_) { + return arguments.length ? (lambda = _[0] % 360 * radians, phi = _[1] % 360 * radians, recenter()) : [lambda * degrees, phi * degrees]; + }; + + projection.rotate = function(_) { + return arguments.length ? (deltaLambda = _[0] % 360 * radians, deltaPhi = _[1] % 360 * radians, deltaGamma = _.length > 2 ? _[2] % 360 * radians : 0, recenter()) : [deltaLambda * degrees, deltaPhi * degrees, deltaGamma * degrees]; + }; + + projection.angle = function(_) { + return arguments.length ? (alpha = _ % 360 * radians, recenter()) : alpha * degrees; + }; + + projection.reflectX = function(_) { + return arguments.length ? (sx = _ ? -1 : 1, recenter()) : sx < 0; + }; + + projection.reflectY = function(_) { + return arguments.length ? (sy = _ ? -1 : 1, recenter()) : sy < 0; + }; + + projection.precision = function(_) { + return arguments.length ? (projectResample = resample(projectTransform, delta2 = _ * _), reset()) : sqrt(delta2); + }; + + projection.fitExtent = function(extent, object) { + return fitExtent(projection, extent, object); + }; + + projection.fitSize = function(size, object) { + return fitSize(projection, size, object); + }; + + projection.fitWidth = function(width, object) { + return fitWidth(projection, width, object); + }; + + projection.fitHeight = function(height, object) { + return fitHeight(projection, height, object); + }; + + function recenter() { + var center = scaleTranslateRotate(k, 0, 0, sx, sy, alpha).apply(null, project(lambda, phi)), + transform = scaleTranslateRotate(k, x - center[0], y - center[1], sx, sy, alpha); + rotate = rotateRadians(deltaLambda, deltaPhi, deltaGamma); + projectTransform = compose(project, transform); + projectRotateTransform = compose(rotate, projectTransform); + projectResample = resample(projectTransform, delta2); + return reset(); + } + + function reset() { + cache = cacheStream = null; + return projection; + } + + return function() { + project = projectAt.apply(this, arguments); + projection.invert = project.invert && invert; + return recenter(); + }; +} + +function conicProjection(projectAt) { + var phi0 = 0, + phi1 = pi / 3, + m = projectionMutator(projectAt), + p = m(phi0, phi1); + + p.parallels = function(_) { + return arguments.length ? m(phi0 = _[0] * radians, phi1 = _[1] * radians) : [phi0 * degrees, phi1 * degrees]; + }; + + return p; +} + +function cylindricalEqualAreaRaw(phi0) { + var cosPhi0 = cos(phi0); + + function forward(lambda, phi) { + return [lambda * cosPhi0, sin(phi) / cosPhi0]; + } + + forward.invert = function(x, y) { + return [x / cosPhi0, asin(y * cosPhi0)]; + }; + + return forward; +} + +function conicEqualAreaRaw(y0, y1) { + var sy0 = sin(y0), n = (sy0 + sin(y1)) / 2; + + // Are the parallels symmetrical around the Equator? + if (abs(n) < epsilon) return cylindricalEqualAreaRaw(y0); + + var c = 1 + sy0 * (2 * n - sy0), r0 = sqrt(c) / n; + + function project(x, y) { + var r = sqrt(c - 2 * n * sin(y)) / n; + return [r * sin(x *= n), r0 - r * cos(x)]; + } + + project.invert = function(x, y) { + var r0y = r0 - y, + l = atan2(x, abs(r0y)) * sign(r0y); + if (r0y * n < 0) + l -= pi * sign(x) * sign(r0y); + return [l / n, asin((c - (x * x + r0y * r0y) * n * n) / (2 * n))]; + }; + + return project; +} + +function conicEqualArea() { + return conicProjection(conicEqualAreaRaw) + .scale(155.424) + .center([0, 33.6442]); +} + +function albers() { + return conicEqualArea() + .parallels([29.5, 45.5]) + .scale(1070) + .translate([480, 250]) + .rotate([96, 0]) + .center([-0.6, 38.7]); +} + +// The projections must have mutually exclusive clip regions on the sphere, +// as this will avoid emitting interleaving lines and polygons. +function multiplex(streams) { + var n = streams.length; + return { + point: function(x, y) { var i = -1; while (++i < n) streams[i].point(x, y); }, + sphere: function() { var i = -1; while (++i < n) streams[i].sphere(); }, + lineStart: function() { var i = -1; while (++i < n) streams[i].lineStart(); }, + lineEnd: function() { var i = -1; while (++i < n) streams[i].lineEnd(); }, + polygonStart: function() { var i = -1; while (++i < n) streams[i].polygonStart(); }, + polygonEnd: function() { var i = -1; while (++i < n) streams[i].polygonEnd(); } + }; +} + +// A composite projection for the United States, configured by default for +// 960×500. The projection also works quite well at 960×600 if you change the +// scale to 1285 and adjust the translate accordingly. The set of standard +// parallels for each region comes from USGS, which is published here: +// http://egsc.usgs.gov/isb/pubs/MapProjections/projections.html#albers +function albersUsa() { + var cache, + cacheStream, + lower48 = albers(), lower48Point, + alaska = conicEqualArea().rotate([154, 0]).center([-2, 58.5]).parallels([55, 65]), alaskaPoint, // EPSG:3338 + hawaii = conicEqualArea().rotate([157, 0]).center([-3, 19.9]).parallels([8, 18]), hawaiiPoint, // ESRI:102007 + point, pointStream = {point: function(x, y) { point = [x, y]; }}; + + function albersUsa(coordinates) { + var x = coordinates[0], y = coordinates[1]; + return point = null, + (lower48Point.point(x, y), point) + || (alaskaPoint.point(x, y), point) + || (hawaiiPoint.point(x, y), point); + } + + albersUsa.invert = function(coordinates) { + var k = lower48.scale(), + t = lower48.translate(), + x = (coordinates[0] - t[0]) / k, + y = (coordinates[1] - t[1]) / k; + return (y >= 0.120 && y < 0.234 && x >= -0.425 && x < -0.214 ? alaska + : y >= 0.166 && y < 0.234 && x >= -0.214 && x < -0.115 ? hawaii + : lower48).invert(coordinates); + }; + + albersUsa.stream = function(stream) { + return cache && cacheStream === stream ? cache : cache = multiplex([lower48.stream(cacheStream = stream), alaska.stream(stream), hawaii.stream(stream)]); + }; + + albersUsa.precision = function(_) { + if (!arguments.length) return lower48.precision(); + lower48.precision(_), alaska.precision(_), hawaii.precision(_); + return reset(); + }; + + albersUsa.scale = function(_) { + if (!arguments.length) return lower48.scale(); + lower48.scale(_), alaska.scale(_ * 0.35), hawaii.scale(_); + return albersUsa.translate(lower48.translate()); + }; + + albersUsa.translate = function(_) { + if (!arguments.length) return lower48.translate(); + var k = lower48.scale(), x = +_[0], y = +_[1]; + + lower48Point = lower48 + .translate(_) + .clipExtent([[x - 0.455 * k, y - 0.238 * k], [x + 0.455 * k, y + 0.238 * k]]) + .stream(pointStream); + + alaskaPoint = alaska + .translate([x - 0.307 * k, y + 0.201 * k]) + .clipExtent([[x - 0.425 * k + epsilon, y + 0.120 * k + epsilon], [x - 0.214 * k - epsilon, y + 0.234 * k - epsilon]]) + .stream(pointStream); + + hawaiiPoint = hawaii + .translate([x - 0.205 * k, y + 0.212 * k]) + .clipExtent([[x - 0.214 * k + epsilon, y + 0.166 * k + epsilon], [x - 0.115 * k - epsilon, y + 0.234 * k - epsilon]]) + .stream(pointStream); + + return reset(); + }; + + albersUsa.fitExtent = function(extent, object) { + return fitExtent(albersUsa, extent, object); + }; + + albersUsa.fitSize = function(size, object) { + return fitSize(albersUsa, size, object); + }; + + albersUsa.fitWidth = function(width, object) { + return fitWidth(albersUsa, width, object); + }; + + albersUsa.fitHeight = function(height, object) { + return fitHeight(albersUsa, height, object); + }; + + function reset() { + cache = cacheStream = null; + return albersUsa; + } + + return albersUsa.scale(1070); +} + +function azimuthalRaw(scale) { + return function(x, y) { + var cx = cos(x), + cy = cos(y), + k = scale(cx * cy); + if (k === Infinity) return [2, 0]; + return [ + k * cy * sin(x), + k * sin(y) + ]; + } +} + +function azimuthalInvert(angle) { + return function(x, y) { + var z = sqrt(x * x + y * y), + c = angle(z), + sc = sin(c), + cc = cos(c); + return [ + atan2(x * sc, z * cc), + asin(z && y * sc / z) + ]; + } +} + +var azimuthalEqualAreaRaw = azimuthalRaw(function(cxcy) { + return sqrt(2 / (1 + cxcy)); +}); + +azimuthalEqualAreaRaw.invert = azimuthalInvert(function(z) { + return 2 * asin(z / 2); +}); + +function azimuthalEqualArea() { + return projection(azimuthalEqualAreaRaw) + .scale(124.75) + .clipAngle(180 - 1e-3); +} + +var azimuthalEquidistantRaw = azimuthalRaw(function(c) { + return (c = acos(c)) && c / sin(c); +}); + +azimuthalEquidistantRaw.invert = azimuthalInvert(function(z) { + return z; +}); + +function azimuthalEquidistant() { + return projection(azimuthalEquidistantRaw) + .scale(79.4188) + .clipAngle(180 - 1e-3); +} + +function mercatorRaw(lambda, phi) { + return [lambda, log(tan((halfPi + phi) / 2))]; +} + +mercatorRaw.invert = function(x, y) { + return [x, 2 * atan(exp(y)) - halfPi]; +}; + +function mercator() { + return mercatorProjection(mercatorRaw) + .scale(961 / tau); +} + +function mercatorProjection(project) { + var m = projection(project), + center = m.center, + scale = m.scale, + translate = m.translate, + clipExtent = m.clipExtent, + x0 = null, y0, x1, y1; // clip extent + + m.scale = function(_) { + return arguments.length ? (scale(_), reclip()) : scale(); + }; + + m.translate = function(_) { + return arguments.length ? (translate(_), reclip()) : translate(); + }; + + m.center = function(_) { + return arguments.length ? (center(_), reclip()) : center(); + }; + + m.clipExtent = function(_) { + return arguments.length ? ((_ == null ? x0 = y0 = x1 = y1 = null : (x0 = +_[0][0], y0 = +_[0][1], x1 = +_[1][0], y1 = +_[1][1])), reclip()) : x0 == null ? null : [[x0, y0], [x1, y1]]; + }; + + function reclip() { + var k = pi * scale(), + t = m(rotation(m.rotate()).invert([0, 0])); + return clipExtent(x0 == null + ? [[t[0] - k, t[1] - k], [t[0] + k, t[1] + k]] : project === mercatorRaw + ? [[Math.max(t[0] - k, x0), y0], [Math.min(t[0] + k, x1), y1]] + : [[x0, Math.max(t[1] - k, y0)], [x1, Math.min(t[1] + k, y1)]]); + } + + return reclip(); +} + +function tany(y) { + return tan((halfPi + y) / 2); +} + +function conicConformalRaw(y0, y1) { + var cy0 = cos(y0), + n = y0 === y1 ? sin(y0) : log(cy0 / cos(y1)) / log(tany(y1) / tany(y0)), + f = cy0 * pow(tany(y0), n) / n; + + if (!n) return mercatorRaw; + + function project(x, y) { + if (f > 0) { if (y < -halfPi + epsilon) y = -halfPi + epsilon; } + else { if (y > halfPi - epsilon) y = halfPi - epsilon; } + var r = f / pow(tany(y), n); + return [r * sin(n * x), f - r * cos(n * x)]; + } + + project.invert = function(x, y) { + var fy = f - y, r = sign(n) * sqrt(x * x + fy * fy), + l = atan2(x, abs(fy)) * sign(fy); + if (fy * n < 0) + l -= pi * sign(x) * sign(fy); + return [l / n, 2 * atan(pow(f / r, 1 / n)) - halfPi]; + }; + + return project; +} + +function conicConformal() { + return conicProjection(conicConformalRaw) + .scale(109.5) + .parallels([30, 30]); +} + +function equirectangularRaw(lambda, phi) { + return [lambda, phi]; +} + +equirectangularRaw.invert = equirectangularRaw; + +function equirectangular() { + return projection(equirectangularRaw) + .scale(152.63); +} + +function conicEquidistantRaw(y0, y1) { + var cy0 = cos(y0), + n = y0 === y1 ? sin(y0) : (cy0 - cos(y1)) / (y1 - y0), + g = cy0 / n + y0; + + if (abs(n) < epsilon) return equirectangularRaw; + + function project(x, y) { + var gy = g - y, nx = n * x; + return [gy * sin(nx), g - gy * cos(nx)]; + } + + project.invert = function(x, y) { + var gy = g - y, + l = atan2(x, abs(gy)) * sign(gy); + if (gy * n < 0) + l -= pi * sign(x) * sign(gy); + return [l / n, g - sign(n) * sqrt(x * x + gy * gy)]; + }; + + return project; +} + +function conicEquidistant() { + return conicProjection(conicEquidistantRaw) + .scale(131.154) + .center([0, 13.9389]); +} + +var A1 = 1.340264, + A2 = -0.081106, + A3 = 0.000893, + A4 = 0.003796, + M = sqrt(3) / 2, + iterations = 12; + +function equalEarthRaw(lambda, phi) { + var l = asin(M * sin(phi)), l2 = l * l, l6 = l2 * l2 * l2; + return [ + lambda * cos(l) / (M * (A1 + 3 * A2 * l2 + l6 * (7 * A3 + 9 * A4 * l2))), + l * (A1 + A2 * l2 + l6 * (A3 + A4 * l2)) + ]; +} + +equalEarthRaw.invert = function(x, y) { + var l = y, l2 = l * l, l6 = l2 * l2 * l2; + for (var i = 0, delta, fy, fpy; i < iterations; ++i) { + fy = l * (A1 + A2 * l2 + l6 * (A3 + A4 * l2)) - y; + fpy = A1 + 3 * A2 * l2 + l6 * (7 * A3 + 9 * A4 * l2); + l -= delta = fy / fpy, l2 = l * l, l6 = l2 * l2 * l2; + if (abs(delta) < epsilon2) break; + } + return [ + M * x * (A1 + 3 * A2 * l2 + l6 * (7 * A3 + 9 * A4 * l2)) / cos(l), + asin(sin(l) / M) + ]; +}; + +function equalEarth() { + return projection(equalEarthRaw) + .scale(177.158); +} + +function gnomonicRaw(x, y) { + var cy = cos(y), k = cos(x) * cy; + return [cy * sin(x) / k, sin(y) / k]; +} + +gnomonicRaw.invert = azimuthalInvert(atan); + +function gnomonic() { + return projection(gnomonicRaw) + .scale(144.049) + .clipAngle(60); +} + +function identity() { + var k = 1, tx = 0, ty = 0, sx = 1, sy = 1, // scale, translate and reflect + alpha = 0, ca, sa, // angle + x0 = null, y0, x1, y1, // clip extent + kx = 1, ky = 1, + transform = transformer({ + point: function(x, y) { + var p = projection([x, y]); + this.stream.point(p[0], p[1]); + } + }), + postclip = identity$1, + cache, + cacheStream; + + function reset() { + kx = k * sx; + ky = k * sy; + cache = cacheStream = null; + return projection; + } + + function projection (p) { + var x = p[0] * kx, y = p[1] * ky; + if (alpha) { + var t = y * ca - x * sa; + x = x * ca + y * sa; + y = t; + } + return [x + tx, y + ty]; + } + projection.invert = function(p) { + var x = p[0] - tx, y = p[1] - ty; + if (alpha) { + var t = y * ca + x * sa; + x = x * ca - y * sa; + y = t; + } + return [x / kx, y / ky]; + }; + projection.stream = function(stream) { + return cache && cacheStream === stream ? cache : cache = transform(postclip(cacheStream = stream)); + }; + projection.postclip = function(_) { + return arguments.length ? (postclip = _, x0 = y0 = x1 = y1 = null, reset()) : postclip; + }; + projection.clipExtent = function(_) { + return arguments.length ? (postclip = _ == null ? (x0 = y0 = x1 = y1 = null, identity$1) : clipRectangle(x0 = +_[0][0], y0 = +_[0][1], x1 = +_[1][0], y1 = +_[1][1]), reset()) : x0 == null ? null : [[x0, y0], [x1, y1]]; + }; + projection.scale = function(_) { + return arguments.length ? (k = +_, reset()) : k; + }; + projection.translate = function(_) { + return arguments.length ? (tx = +_[0], ty = +_[1], reset()) : [tx, ty]; + }; + projection.angle = function(_) { + return arguments.length ? (alpha = _ % 360 * radians, sa = sin(alpha), ca = cos(alpha), reset()) : alpha * degrees; + }; + projection.reflectX = function(_) { + return arguments.length ? (sx = _ ? -1 : 1, reset()) : sx < 0; + }; + projection.reflectY = function(_) { + return arguments.length ? (sy = _ ? -1 : 1, reset()) : sy < 0; + }; + projection.fitExtent = function(extent, object) { + return fitExtent(projection, extent, object); + }; + projection.fitSize = function(size, object) { + return fitSize(projection, size, object); + }; + projection.fitWidth = function(width, object) { + return fitWidth(projection, width, object); + }; + projection.fitHeight = function(height, object) { + return fitHeight(projection, height, object); + }; + + return projection; +} + +function naturalEarth1Raw(lambda, phi) { + var phi2 = phi * phi, phi4 = phi2 * phi2; + return [ + lambda * (0.8707 - 0.131979 * phi2 + phi4 * (-0.013791 + phi4 * (0.003971 * phi2 - 0.001529 * phi4))), + phi * (1.007226 + phi2 * (0.015085 + phi4 * (-0.044475 + 0.028874 * phi2 - 0.005916 * phi4))) + ]; +} + +naturalEarth1Raw.invert = function(x, y) { + var phi = y, i = 25, delta; + do { + var phi2 = phi * phi, phi4 = phi2 * phi2; + phi -= delta = (phi * (1.007226 + phi2 * (0.015085 + phi4 * (-0.044475 + 0.028874 * phi2 - 0.005916 * phi4))) - y) / + (1.007226 + phi2 * (0.015085 * 3 + phi4 * (-0.044475 * 7 + 0.028874 * 9 * phi2 - 0.005916 * 11 * phi4))); + } while (abs(delta) > epsilon && --i > 0); + return [ + x / (0.8707 + (phi2 = phi * phi) * (-0.131979 + phi2 * (-0.013791 + phi2 * phi2 * phi2 * (0.003971 - 0.001529 * phi2)))), + phi + ]; +}; + +function naturalEarth1() { + return projection(naturalEarth1Raw) + .scale(175.295); +} + +function orthographicRaw(x, y) { + return [cos(y) * sin(x), sin(y)]; +} + +orthographicRaw.invert = azimuthalInvert(asin); + +function orthographic() { + return projection(orthographicRaw) + .scale(249.5) + .clipAngle(90 + epsilon); +} + +function stereographicRaw(x, y) { + var cy = cos(y), k = 1 + cos(x) * cy; + return [cy * sin(x) / k, sin(y) / k]; +} + +stereographicRaw.invert = azimuthalInvert(function(z) { + return 2 * atan(z); +}); + +function stereographic() { + return projection(stereographicRaw) + .scale(250) + .clipAngle(142); +} + +function transverseMercatorRaw(lambda, phi) { + return [log(tan((halfPi + phi) / 2)), -lambda]; +} + +transverseMercatorRaw.invert = function(x, y) { + return [-y, 2 * atan(exp(x)) - halfPi]; +}; + +function transverseMercator() { + var m = mercatorProjection(transverseMercatorRaw), + center = m.center, + rotate = m.rotate; + + m.center = function(_) { + return arguments.length ? center([-_[1], _[0]]) : (_ = center(), [_[1], -_[0]]); + }; + + m.rotate = function(_) { + return arguments.length ? rotate([_[0], _[1], _.length > 2 ? _[2] + 90 : 90]) : (_ = rotate(), [_[0], _[1], _[2] - 90]); + }; + + return rotate([0, 0, 90]) + .scale(159.155); +} + +exports.geoAlbers = albers; +exports.geoAlbersUsa = albersUsa; +exports.geoArea = area; +exports.geoAzimuthalEqualArea = azimuthalEqualArea; +exports.geoAzimuthalEqualAreaRaw = azimuthalEqualAreaRaw; +exports.geoAzimuthalEquidistant = azimuthalEquidistant; +exports.geoAzimuthalEquidistantRaw = azimuthalEquidistantRaw; +exports.geoBounds = bounds; +exports.geoCentroid = centroid; +exports.geoCircle = circle; +exports.geoClipAntimeridian = clipAntimeridian; +exports.geoClipCircle = clipCircle; +exports.geoClipExtent = extent; +exports.geoClipRectangle = clipRectangle; +exports.geoConicConformal = conicConformal; +exports.geoConicConformalRaw = conicConformalRaw; +exports.geoConicEqualArea = conicEqualArea; +exports.geoConicEqualAreaRaw = conicEqualAreaRaw; +exports.geoConicEquidistant = conicEquidistant; +exports.geoConicEquidistantRaw = conicEquidistantRaw; +exports.geoContains = contains; +exports.geoDistance = distance; +exports.geoEqualEarth = equalEarth; +exports.geoEqualEarthRaw = equalEarthRaw; +exports.geoEquirectangular = equirectangular; +exports.geoEquirectangularRaw = equirectangularRaw; +exports.geoGnomonic = gnomonic; +exports.geoGnomonicRaw = gnomonicRaw; +exports.geoGraticule = graticule; +exports.geoGraticule10 = graticule10; +exports.geoIdentity = identity; +exports.geoInterpolate = interpolate; +exports.geoLength = length; +exports.geoMercator = mercator; +exports.geoMercatorRaw = mercatorRaw; +exports.geoNaturalEarth1 = naturalEarth1; +exports.geoNaturalEarth1Raw = naturalEarth1Raw; +exports.geoOrthographic = orthographic; +exports.geoOrthographicRaw = orthographicRaw; +exports.geoPath = index; +exports.geoProjection = projection; +exports.geoProjectionMutator = projectionMutator; +exports.geoRotation = rotation; +exports.geoStereographic = stereographic; +exports.geoStereographicRaw = stereographicRaw; +exports.geoStream = geoStream; +exports.geoTransform = transform; +exports.geoTransverseMercator = transverseMercator; +exports.geoTransverseMercatorRaw = transverseMercatorRaw; + +})); diff --git a/frontend/node_modules/d3-geo/dist/d3-geo.min.js b/frontend/node_modules/d3-geo/dist/d3-geo.min.js new file mode 100644 index 0000000..d70a0df --- /dev/null +++ b/frontend/node_modules/d3-geo/dist/d3-geo.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-geo/ v3.1.1 Copyright 2010-2024 Mike Bostock, 2008-2012 Charles Karney +!function(n,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports,require("d3-array")):"function"==typeof define&&define.amd?define(["exports","d3-array"],t):t((n="undefined"!=typeof globalThis?globalThis:n||self).d3=n.d3||{},n.d3)}(this,(function(n,t){"use strict";var r=1e-6,e=1e-12,i=Math.PI,o=i/2,u=i/4,a=2*i,c=180/i,l=i/180,f=Math.abs,p=Math.atan,s=Math.atan2,h=Math.cos,g=Math.ceil,d=Math.exp,v=Math.hypot,E=Math.log,y=Math.pow,S=Math.sin,m=Math.sign||function(n){return n>0?1:n<0?-1:0},M=Math.sqrt,w=Math.tan;function x(n){return n>1?0:n<-1?i:Math.acos(n)}function _(n){return n>1?o:n<-1?-o:Math.asin(n)}function N(n){return(n=S(n/2))*n}function A(){}function R(n,t){n&&P.hasOwnProperty(n.type)&&P[n.type](n,t)}var C={Feature:function(n,t){R(n.geometry,t)},FeatureCollection:function(n,t){for(var r=n.features,e=-1,i=r.length;++e=0?1:-1,i=e*r,o=h(t=(t*=l)/2+u),a=S(t),c=G*a,f=T*o+c*h(i),p=c*e*S(i);Z.add(s(p,f)),L=n,T=o,G=a}function rn(n){return[s(n[1],n[0]),_(n[2])]}function en(n){var t=n[0],r=n[1],e=h(r);return[e*h(t),e*S(t),S(r)]}function on(n,t){return n[0]*t[0]+n[1]*t[1]+n[2]*t[2]}function un(n,t){return[n[1]*t[2]-n[2]*t[1],n[2]*t[0]-n[0]*t[2],n[0]*t[1]-n[1]*t[0]]}function an(n,t){n[0]+=t[0],n[1]+=t[1],n[2]+=t[2]}function cn(n,t){return[n[0]*t,n[1]*t,n[2]*t]}function ln(n){var t=M(n[0]*n[0]+n[1]*n[1]+n[2]*n[2]);n[0]/=t,n[1]/=t,n[2]/=t}var fn,pn,sn,hn,gn,dn,vn,En,yn,Sn,mn,Mn,wn,xn,_n,Nn,An={point:Rn,lineStart:Pn,lineEnd:$n,polygonStart:function(){An.point=qn,An.lineStart=jn,An.lineEnd=zn,B=new t.Adder,K.polygonStart()},polygonEnd:function(){K.polygonEnd(),An.point=Rn,An.lineStart=Pn,An.lineEnd=$n,Z<0?(O=-(F=180),k=-(H=90)):B>r?H=90:B<-r&&(k=-90),U[0]=O,U[1]=F},sphere:function(){O=-(F=180),k=-(H=90)}};function Rn(n,t){D.push(U=[O=n,F=n]),tH&&(H=t)}function Cn(n,t){var r=en([n*l,t*l]);if(Y){var e=un(Y,r),i=un([e[1],-e[0],0],e);ln(i),i=rn(i);var o,u=n-I,a=u>0?1:-1,p=i[0]*c*a,s=f(u)>180;s^(a*IH&&(H=o):s^(a*I<(p=(p+360)%360-180)&&pH&&(H=t)),s?nbn(O,F)&&(F=n):bn(n,F)>bn(O,F)&&(O=n):F>=O?(nF&&(F=n)):n>I?bn(O,n)>bn(O,F)&&(F=n):bn(n,F)>bn(O,F)&&(O=n)}else D.push(U=[O=n,F=n]);tH&&(H=t),Y=r,I=n}function Pn(){An.point=Cn}function $n(){U[0]=O,U[1]=F,An.point=Rn,Y=null}function qn(n,t){if(Y){var r=n-I;B.add(f(r)>180?r+(r>0?360:-360):r)}else W=n,X=t;K.point(n,t),Cn(n,t)}function jn(){K.lineStart()}function zn(){qn(W,X),K.lineEnd(),f(B)>r&&(O=-(F=180)),U[0]=O,U[1]=F,Y=null}function bn(n,t){return(t-=n)<0?t+360:t}function Ln(n,t){return n[0]-t[0]}function Tn(n,t){return n[0]<=n[1]?n[0]<=t&&t<=n[1]:ti&&(n-=Math.round(n/a)*a),[n,t]}function Kn(n,t,r){return(n%=a)?t||r?Zn(Vn(n),nt(t,r)):Vn(n):t||r?nt(t,r):Jn}function Qn(n){return function(t,r){return f(t+=n)>i&&(t-=Math.round(t/a)*a),[t,r]}}function Vn(n){var t=Qn(n);return t.invert=Qn(-n),t}function nt(n,t){var r=h(n),e=S(n),i=h(t),o=S(t);function u(n,t){var u=h(t),a=h(n)*u,c=S(n)*u,l=S(t),f=l*r+a*e;return[s(c*i-f*o,a*r-l*e),_(f*i+c*o)]}return u.invert=function(n,t){var u=h(t),a=h(n)*u,c=S(n)*u,l=S(t),f=l*i-c*o;return[s(c*i+l*o,a*r+f*e),_(f*r-a*e)]},u}function tt(n){function t(t){return(t=n(t[0]*l,t[1]*l))[0]*=c,t[1]*=c,t}return n=Kn(n[0]*l,n[1]*l,n.length>2?n[2]*l:0),t.invert=function(t){return(t=n.invert(t[0]*l,t[1]*l))[0]*=c,t[1]*=c,t},t}function rt(n,t,r,e,i,o){if(r){var u=h(t),c=S(t),l=e*r;null==i?(i=t+e*a,o=t-l/2):(i=et(u,i),o=et(u,o),(e>0?io)&&(i+=e*a));for(var f,p=i;e>0?p>o:p1&&t.push(t.pop().concat(t.shift()))},result:function(){var r=t;return t=[],n=null,r}}}function ot(n,t){return f(n[0]-t[0])=0;--u)o.point((p=f[u])[0],p[1]);else i(h.x,h.p.x,-1,o);h=h.p}f=(h=h.o).z,g=!g}while(!h.v);o.lineEnd()}}}function ct(n){if(t=n.length){for(var t,r,e=0,i=n[0];++e=0?1:-1,G=T*L,O=G>i,k=R*z;if(E.add(s(k*T*S(G),C*b+k*h(G))),d+=O?L+T*a:L,O^N>=l^q>=l){var F=un(en(x),en($));ln(F);var H=un(g,F);ln(H);var I=(O^L>=0?-1:1)*_(H[2]);(f>I||f===I&&(F[0]||F[1]))&&(v+=O^L>=0?1:-1)}}return(d<-r||d0){for(s||(o.polygonStart(),s=!0),o.lineStart(),n=0;n1&&2&i&&l.push(l.pop().concat(l.shift())),a.push(l.filter(st))}return h}}function st(n){return n.length>1}function ht(n,t){return((n=n.x)[0]<0?n[1]-o-r:o-n[1])-((t=t.x)[0]<0?t[1]-o-r:o-t[1])}Jn.invert=Jn;var gt=pt((function(){return!0}),(function(n){var t,e=NaN,u=NaN,a=NaN;return{lineStart:function(){n.lineStart(),t=1},point:function(c,l){var s=c>0?i:-i,g=f(c-e);f(g-i)0?o:-o),n.point(a,u),n.lineEnd(),n.lineStart(),n.point(s,u),n.point(c,u),t=0):a!==s&&g>=i&&(f(e-a)r?p((S(t)*(u=h(i))*S(e)-S(i)*(o=h(t))*S(n))/(o*u*a)):(t+i)/2}(e,u,c,l),n.point(a,u),n.lineEnd(),n.lineStart(),n.point(s,u),t=0),n.point(e=c,u=l),a=s},lineEnd:function(){n.lineEnd(),e=u=NaN},clean:function(){return 2-t}}}),(function(n,t,e,u){var a;if(null==n)a=e*o,u.point(-i,a),u.point(0,a),u.point(i,a),u.point(i,0),u.point(i,-a),u.point(0,-a),u.point(-i,-a),u.point(-i,0),u.point(-i,a);else if(f(n[0]-t[0])>r){var c=n[0]0,u=f(t)>r;function a(n,r){return h(n)*h(r)>t}function c(n,e,o){var u=[1,0,0],a=un(en(n),en(e)),c=on(a,a),l=a[0],p=c-l*l;if(!p)return!o&&n;var s=t*c/p,h=-t*l/p,g=un(u,a),d=cn(u,s);an(d,cn(a,h));var v=g,E=on(d,v),y=on(v,v),S=E*E-y*(on(d,d)-1);if(!(S<0)){var m=M(S),w=cn(v,(-E-m)/y);if(an(w,d),w=rn(w),!o)return w;var x,_=n[0],N=e[0],A=n[1],R=e[1];N<_&&(x=_,_=N,N=x);var C=N-_,P=f(C-i)0^w[1]<(f(w[0]-_)i^(_<=w[0]&&w[0]<=N)){var $=cn(v,(-E+m)/y);return an($,d),[w,rn($)]}}}function p(t,r){var e=o?n:i-n,u=0;return t<-e?u|=1:t>e&&(u|=2),r<-e?u|=4:r>e&&(u|=8),u}return pt(a,(function(n){var t,r,e,l,f;return{lineStart:function(){l=e=!1,f=1},point:function(s,h){var g,d=[s,h],v=a(s,h),E=o?v?0:p(s,h):v?p(s+(s<0?i:-i),h):0;if(!t&&(l=e=v)&&n.lineStart(),v!==e&&(!(g=c(t,d))||ot(t,g)||ot(d,g))&&(d[2]=1),v!==e)f=0,v?(n.lineStart(),g=c(d,t),n.point(g[0],g[1])):(g=c(t,d),n.point(g[0],g[1],2),n.lineEnd()),t=g;else if(u&&t&&o^v){var y;E&r||!(y=c(d,t,!0))||(f=0,o?(n.lineStart(),n.point(y[0][0],y[0][1]),n.point(y[1][0],y[1][1]),n.lineEnd()):(n.point(y[1][0],y[1][1]),n.lineEnd(),n.lineStart(),n.point(y[0][0],y[0][1],3)))}!v||t&&ot(t,d)||n.point(d[0],d[1]),t=d,e=v,r=E},lineEnd:function(){e&&n.lineEnd(),t=null},clean:function(){return f|(l&&e)<<1}}}),(function(t,r,i,o){rt(o,n,e,i,t,r)}),o?[0,-n]:[-i,n-i])}var vt,Et,yt,St,mt=1e9,Mt=-mt;function wt(n,e,i,o){function u(t,r){return n<=t&&t<=i&&e<=r&&r<=o}function a(t,r,u,a){var l=0,f=0;if(null==t||(l=c(t,u))!==(f=c(r,u))||p(t,r)<0^u>0)do{a.point(0===l||3===l?n:i,l>1?o:e)}while((l=(l+u+4)%4)!==f);else a.point(r[0],r[1])}function c(t,o){return f(t[0]-n)0?0:3:f(t[0]-i)0?2:1:f(t[1]-e)0?1:0:o>0?3:2}function l(n,t){return p(n.x,t.x)}function p(n,t){var r=c(n,1),e=c(t,1);return r!==e?r-e:0===r?t[1]-n[1]:1===r?n[0]-t[0]:2===r?n[1]-t[1]:t[0]-n[0]}return function(r){var c,f,p,s,h,g,d,v,E,y,S,m=r,M=it(),w={point:x,lineStart:function(){w.point=_,f&&f.push(p=[]);y=!0,E=!1,d=v=NaN},lineEnd:function(){c&&(_(s,h),g&&E&&M.rejoin(),c.push(M.result()));w.point=x,E&&m.lineEnd()},polygonStart:function(){m=M,c=[],f=[],S=!0},polygonEnd:function(){var e=function(){for(var t=0,r=0,e=f.length;ro&&(s-i)*(o-u)>(h-u)*(n-i)&&++t:h<=o&&(s-i)*(o-u)<(h-u)*(n-i)&&--t;return t}(),i=S&&e,u=(c=t.merge(c)).length;(i||u)&&(r.polygonStart(),i&&(r.lineStart(),a(null,null,1,r),r.lineEnd()),u&&at(c,l,e,a,r),r.polygonEnd());m=r,c=f=p=null}};function x(n,t){u(n,t)&&m.point(n,t)}function _(t,r){var a=u(t,r);if(f&&p.push([t,r]),y)s=t,h=r,g=a,y=!1,a&&(m.lineStart(),m.point(t,r));else if(a&&E)m.point(t,r);else{var c=[d=Math.max(Mt,Math.min(mt,d)),v=Math.max(Mt,Math.min(mt,v))],l=[t=Math.max(Mt,Math.min(mt,t)),r=Math.max(Mt,Math.min(mt,r))];!function(n,t,r,e,i,o){var u,a=n[0],c=n[1],l=0,f=1,p=t[0]-a,s=t[1]-c;if(u=r-a,p||!(u>0)){if(u/=p,p<0){if(u0){if(u>f)return;u>l&&(l=u)}if(u=i-a,p||!(u<0)){if(u/=p,p<0){if(u>f)return;u>l&&(l=u)}else if(p>0){if(u0)){if(u/=s,s<0){if(u0){if(u>f)return;u>l&&(l=u)}if(u=o-c,s||!(u<0)){if(u/=s,s<0){if(u>f)return;u>l&&(l=u)}else if(s>0){if(u0&&(n[0]=a+l*p,n[1]=c+l*s),f<1&&(t[0]=a+f*p,t[1]=c+f*s),!0}}}}}(c,l,n,e,i,o)?a&&(m.lineStart(),m.point(t,r),S=!1):(E||(m.lineStart(),m.point(c[0],c[1])),m.point(l[0],l[1]),a||m.lineEnd(),S=!1)}d=t,v=r,E=a}return w}}var xt={sphere:A,point:A,lineStart:function(){xt.point=Nt,xt.lineEnd=_t},lineEnd:A,polygonStart:A,polygonEnd:A};function _t(){xt.point=xt.lineEnd=A}function Nt(n,t){Et=n*=l,yt=S(t*=l),St=h(t),xt.point=At}function At(n,t){n*=l;var r=S(t*=l),e=h(t),i=f(n-Et),o=h(i),u=e*S(i),a=St*r-yt*e*o,c=yt*r+St*e*o;vt.add(s(M(u*u+a*a),c)),Et=n,yt=r,St=e}function Rt(n){return vt=new t.Adder,j(n,xt),+vt}var Ct=[null,null],Pt={type:"LineString",coordinates:Ct};function $t(n,t){return Ct[0]=n,Ct[1]=t,Rt(Pt)}var qt={Feature:function(n,t){return zt(n.geometry,t)},FeatureCollection:function(n,t){for(var r=n.features,e=-1,i=r.length;++e0&&(o=$t(n[u],n[u-1]))>0&&r<=o&&i<=o&&(r+i-o)*(1-Math.pow((r-i)/o,2))r})).map(p)).concat(t.range(g(a/E)*E,u,E).filter((function(n){return f(n%S)>r})).map(s))}return M.lines=function(){return w().map((function(n){return{type:"LineString",coordinates:n}}))},M.outline=function(){return{type:"Polygon",coordinates:[h(o).concat(d(c).slice(1),h(i).reverse().slice(1),d(l).reverse().slice(1))]}},M.extent=function(n){return arguments.length?M.extentMajor(n).extentMinor(n):M.extentMinor()},M.extentMajor=function(n){return arguments.length?(o=+n[0][0],i=+n[1][0],l=+n[0][1],c=+n[1][1],o>i&&(n=o,o=i,i=n),l>c&&(n=l,l=c,c=n),M.precision(m)):[[o,l],[i,c]]},M.extentMinor=function(t){return arguments.length?(e=+t[0][0],n=+t[1][0],a=+t[0][1],u=+t[1][1],e>n&&(t=e,e=n,n=t),a>u&&(t=a,a=u,u=t),M.precision(m)):[[e,a],[n,u]]},M.step=function(n){return arguments.length?M.stepMajor(n).stepMinor(n):M.stepMinor()},M.stepMajor=function(n){return arguments.length?(y=+n[0],S=+n[1],M):[y,S]},M.stepMinor=function(n){return arguments.length?(v=+n[0],E=+n[1],M):[v,E]},M.precision=function(t){return arguments.length?(m=+t,p=kt(a,u,90),s=Ft(e,n,m),h=kt(l,c,90),d=Ft(o,i,m),M):m},M.extentMajor([[-180,-90+r],[180,90-r]]).extentMinor([[-180,-80-r],[180,80+r]])}var It,Wt,Xt,Yt,Bt=n=>n,Dt=new t.Adder,Ut=new t.Adder,Zt={point:A,lineStart:A,lineEnd:A,polygonStart:function(){Zt.lineStart=Jt,Zt.lineEnd=Vt},polygonEnd:function(){Zt.lineStart=Zt.lineEnd=Zt.point=A,Dt.add(f(Ut)),Ut=new t.Adder},result:function(){var n=Dt/2;return Dt=new t.Adder,n}};function Jt(){Zt.point=Kt}function Kt(n,t){Zt.point=Qt,It=Xt=n,Wt=Yt=t}function Qt(n,t){Ut.add(Yt*n-Xt*t),Xt=n,Yt=t}function Vt(){Qt(It,Wt)}var nr=1/0,tr=nr,rr=-nr,er=rr,ir={point:function(n,t){nrr&&(rr=n);ter&&(er=t)},lineStart:A,lineEnd:A,polygonStart:A,polygonEnd:A,result:function(){var n=[[nr,tr],[rr,er]];return rr=er=-(tr=nr=1/0),n}};var or,ur,ar,cr,lr=0,fr=0,pr=0,sr=0,hr=0,gr=0,dr=0,vr=0,Er=0,yr={point:Sr,lineStart:mr,lineEnd:xr,polygonStart:function(){yr.lineStart=_r,yr.lineEnd=Nr},polygonEnd:function(){yr.point=Sr,yr.lineStart=mr,yr.lineEnd=xr},result:function(){var n=Er?[dr/Er,vr/Er]:gr?[sr/gr,hr/gr]:pr?[lr/pr,fr/pr]:[NaN,NaN];return lr=fr=pr=sr=hr=gr=dr=vr=Er=0,n}};function Sr(n,t){lr+=n,fr+=t,++pr}function mr(){yr.point=Mr}function Mr(n,t){yr.point=wr,Sr(ar=n,cr=t)}function wr(n,t){var r=n-ar,e=t-cr,i=M(r*r+e*e);sr+=i*(ar+n)/2,hr+=i*(cr+t)/2,gr+=i,Sr(ar=n,cr=t)}function xr(){yr.point=Sr}function _r(){yr.point=Ar}function Nr(){Rr(or,ur)}function Ar(n,t){yr.point=Rr,Sr(or=ar=n,ur=cr=t)}function Rr(n,t){var r=n-ar,e=t-cr,i=M(r*r+e*e);sr+=i*(ar+n)/2,hr+=i*(cr+t)/2,gr+=i,dr+=(i=cr*n-ar*t)*(ar+n),vr+=i*(cr+t),Er+=3*i,Sr(ar=n,cr=t)}function Cr(n){this._context=n}Cr.prototype={_radius:4.5,pointRadius:function(n){return this._radius=n,this},polygonStart:function(){this._line=0},polygonEnd:function(){this._line=NaN},lineStart:function(){this._point=0},lineEnd:function(){0===this._line&&this._context.closePath(),this._point=NaN},point:function(n,t){switch(this._point){case 0:this._context.moveTo(n,t),this._point=1;break;case 1:this._context.lineTo(n,t);break;default:this._context.moveTo(n+this._radius,t),this._context.arc(n,t,this._radius,0,a)}},result:A};var Pr,$r,qr,jr,zr,br=new t.Adder,Lr={point:A,lineStart:function(){Lr.point=Tr},lineEnd:function(){Pr&&Gr($r,qr),Lr.point=A},polygonStart:function(){Pr=!0},polygonEnd:function(){Pr=null},result:function(){var n=+br;return br=new t.Adder,n}};function Tr(n,t){Lr.point=Gr,$r=jr=n,qr=zr=t}function Gr(n,t){jr-=n,zr-=t,br.add(M(jr*jr+zr*zr)),jr=n,zr=t}let Or,kr,Fr,Hr;class Ir{constructor(n){this._append=null==n?Wr:function(n){const t=Math.floor(n);if(!(t>=0))throw new RangeError(`invalid digits: ${n}`);if(t>15)return Wr;if(t!==Or){const n=10**t;Or=t,kr=function(t){let r=1;this._+=t[0];for(const e=t.length;r4*t&&y--){var N=a+d,A=c+v,R=l+E,C=M(N*N+A*A+R*R),P=_(R/=C),$=f(f(R)-1)t||f((m*b+w*L)/x-.5)>.3||a*d+c*v+l*E2?n[2]%360*l:0,j()):[y*c,S*c,m*c]},$.angle=function(n){return arguments.length?(w=n%360*l,j()):w*c},$.reflectX=function(n){return arguments.length?(x=n?-1:1,j()):x<0},$.reflectY=function(n){return arguments.length?(_=n?-1:1,j()):_<0},$.precision=function(n){return arguments.length?(u=Vr(a,P=n*n),z()):M(P)},$.fitExtent=function(n,t){return Dr($,n,t)},$.fitSize=function(n,t){return Ur($,n,t)},$.fitWidth=function(n,t){return Zr($,n,t)},$.fitHeight=function(n,t){return Jr($,n,t)},function(){return t=n.apply(this,arguments),$.invert=t.invert&&q,j()}}function ie(n){var t=0,r=i/3,e=ee(n),o=e(t,r);return o.parallels=function(n){return arguments.length?e(t=n[0]*l,r=n[1]*l):[t*c,r*c]},o}function oe(n,t){var e=S(n),o=(e+S(t))/2;if(f(o)0?t<-o+r&&(t=-o+r):t>o-r&&(t=o-r);var e=a/y(ge(t),u);return[e*S(u*n),a-e*h(u*n)]}return c.invert=function(n,t){var r=a-t,e=m(u)*M(n*n+r*r),c=s(n,f(r))*m(r);return r*u<0&&(c-=i*m(n)*m(r)),[c/u,2*p(y(a/e,1/u))-o]},c}function ve(n,t){return[n,t]}function Ee(n,t){var e=h(n),o=n===t?S(n):(e-h(t))/(t-n),u=e/o+n;if(f(o)r&&--o>0);return[n/(.8707+(u=i*i)*(u*(u*u*u*(.003971-.001529*u)-.013791)-.131979)),i]},Ae.invert=le(_),Re.invert=le((function(n){return 2*p(n)})),Ce.invert=function(n,t){return[-t,2*p(d(n))-o]},n.geoAlbers=ae,n.geoAlbersUsa=function(){var n,t,e,i,o,u,a=ae(),c=ue().rotate([154,0]).center([-2,58.5]).parallels([55,65]),l=ue().rotate([157,0]).center([-3,19.9]).parallels([8,18]),f={point:function(n,t){u=[n,t]}};function p(n){var t=n[0],r=n[1];return u=null,e.point(t,r),u||(i.point(t,r),u)||(o.point(t,r),u)}function s(){return n=t=null,p}return p.invert=function(n){var t=a.scale(),r=a.translate(),e=(n[0]-r[0])/t,i=(n[1]-r[1])/t;return(i>=.12&&i<.234&&e>=-.425&&e<-.214?c:i>=.166&&i<.234&&e>=-.214&&e<-.115?l:a).invert(n)},p.stream=function(r){return n&&t===r?n:(e=[a.stream(t=r),c.stream(r),l.stream(r)],i=e.length,n={point:function(n,t){for(var r=-1;++rbn(e[0],e[1])&&(e[1]=i[1]),bn(i[0],e[1])>bn(e[0],e[1])&&(e[0]=i[0])):o.push(e=i);for(u=-1/0,t=0,e=o[r=o.length-1];t<=r;e=i,++t)i=o[t],(a=bn(e[1],i[0]))>u&&(u=a,O=i[0],F=e[1])}return D=U=null,O===1/0||k===1/0?[[NaN,NaN],[NaN,NaN]]:[[O,k],[F,H]]},n.geoCentroid=function(n){fn=pn=sn=hn=gn=dn=vn=En=0,yn=new t.Adder,Sn=new t.Adder,mn=new t.Adder,j(n,Gn);var i=+yn,o=+Sn,u=+mn,a=v(i,o,u);return a=0))throw new RangeError(`invalid digits: ${n}`);i=t}return null===t&&(e=new Ir(i)),u},u.projection(n).digits(i).context(t)},n.geoProjection=re,n.geoProjectionMutator=ee,n.geoRotation=tt,n.geoStereographic=function(){return re(Re).scale(250).clipAngle(142)},n.geoStereographicRaw=Re,n.geoStream=j,n.geoTransform=function(n){return{stream:Xr(n)}},n.geoTransverseMercator=function(){var n=he(Ce),t=n.center,r=n.rotate;return n.center=function(n){return arguments.length?t([-n[1],n[0]]):[(n=t())[1],-n[0]]},n.rotate=function(n){return arguments.length?r([n[0],n[1],n.length>2?n[2]+90:90]):[(n=r())[0],n[1],n[2]-90]},r([0,0,90]).scale(159.155)},n.geoTransverseMercatorRaw=Ce})); diff --git a/frontend/node_modules/d3-geo/package.json b/frontend/node_modules/d3-geo/package.json new file mode 100644 index 0000000..9144d9e --- /dev/null +++ b/frontend/node_modules/d3-geo/package.json @@ -0,0 +1,59 @@ +{ + "name": "d3-geo", + "version": "3.1.1", + "description": "Shapes and calculators for spherical coordinates.", + "homepage": "https://d3js.org/d3-geo/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-geo.git" + }, + "keywords": [ + "d3", + "d3-module", + "geo", + "maps", + "cartography" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "https://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-geo.min.js", + "unpkg": "dist/d3-geo.min.js", + "exports": { + "umd": "./dist/d3-geo.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "dependencies": { + "d3-array": "2.5.0 - 3" + }, + "devDependencies": { + "@rollup/plugin-terser": "0.4", + "canvas": "2", + "d3-format": "1 - 3", + "eslint": "8", + "mocha": "10", + "pixelmatch": "5", + "pngjs": "6", + "rollup": "3", + "topojson-client": "3", + "world-atlas": "1" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-geo/src/area.js b/frontend/node_modules/d3-geo/src/area.js new file mode 100644 index 0000000..df91640 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/area.js @@ -0,0 +1,76 @@ +import {Adder} from "d3-array"; +import {atan2, cos, quarterPi, radians, sin, tau} from "./math.js"; +import noop from "./noop.js"; +import stream from "./stream.js"; + +export var areaRingSum = new Adder(); + +// hello? + +var areaSum = new Adder(), + lambda00, + phi00, + lambda0, + cosPhi0, + sinPhi0; + +export var areaStream = { + point: noop, + lineStart: noop, + lineEnd: noop, + polygonStart: function() { + areaRingSum = new Adder(); + areaStream.lineStart = areaRingStart; + areaStream.lineEnd = areaRingEnd; + }, + polygonEnd: function() { + var areaRing = +areaRingSum; + areaSum.add(areaRing < 0 ? tau + areaRing : areaRing); + this.lineStart = this.lineEnd = this.point = noop; + }, + sphere: function() { + areaSum.add(tau); + } +}; + +function areaRingStart() { + areaStream.point = areaPointFirst; +} + +function areaRingEnd() { + areaPoint(lambda00, phi00); +} + +function areaPointFirst(lambda, phi) { + areaStream.point = areaPoint; + lambda00 = lambda, phi00 = phi; + lambda *= radians, phi *= radians; + lambda0 = lambda, cosPhi0 = cos(phi = phi / 2 + quarterPi), sinPhi0 = sin(phi); +} + +function areaPoint(lambda, phi) { + lambda *= radians, phi *= radians; + phi = phi / 2 + quarterPi; // half the angular distance from south pole + + // Spherical excess E for a spherical triangle with vertices: south pole, + // previous point, current point. Uses a formula derived from Cagnoli’s + // theorem. See Todhunter, Spherical Trig. (1871), Sec. 103, Eq. (2). + var dLambda = lambda - lambda0, + sdLambda = dLambda >= 0 ? 1 : -1, + adLambda = sdLambda * dLambda, + cosPhi = cos(phi), + sinPhi = sin(phi), + k = sinPhi0 * sinPhi, + u = cosPhi0 * cosPhi + k * cos(adLambda), + v = k * sdLambda * sin(adLambda); + areaRingSum.add(atan2(v, u)); + + // Advance the previous points. + lambda0 = lambda, cosPhi0 = cosPhi, sinPhi0 = sinPhi; +} + +export default function(object) { + areaSum = new Adder(); + stream(object, areaStream); + return areaSum * 2; +} diff --git a/frontend/node_modules/d3-geo/src/bounds.js b/frontend/node_modules/d3-geo/src/bounds.js new file mode 100644 index 0000000..0b398ac --- /dev/null +++ b/frontend/node_modules/d3-geo/src/bounds.js @@ -0,0 +1,179 @@ +import {Adder} from "d3-array"; +import {areaStream, areaRingSum} from "./area.js"; +import {cartesian, cartesianCross, cartesianNormalizeInPlace, spherical} from "./cartesian.js"; +import {abs, degrees, epsilon, radians} from "./math.js"; +import stream from "./stream.js"; + +var lambda0, phi0, lambda1, phi1, // bounds + lambda2, // previous lambda-coordinate + lambda00, phi00, // first point + p0, // previous 3D point + deltaSum, + ranges, + range; + +var boundsStream = { + point: boundsPoint, + lineStart: boundsLineStart, + lineEnd: boundsLineEnd, + polygonStart: function() { + boundsStream.point = boundsRingPoint; + boundsStream.lineStart = boundsRingStart; + boundsStream.lineEnd = boundsRingEnd; + deltaSum = new Adder(); + areaStream.polygonStart(); + }, + polygonEnd: function() { + areaStream.polygonEnd(); + boundsStream.point = boundsPoint; + boundsStream.lineStart = boundsLineStart; + boundsStream.lineEnd = boundsLineEnd; + if (areaRingSum < 0) lambda0 = -(lambda1 = 180), phi0 = -(phi1 = 90); + else if (deltaSum > epsilon) phi1 = 90; + else if (deltaSum < -epsilon) phi0 = -90; + range[0] = lambda0, range[1] = lambda1; + }, + sphere: function() { + lambda0 = -(lambda1 = 180), phi0 = -(phi1 = 90); + } +}; + +function boundsPoint(lambda, phi) { + ranges.push(range = [lambda0 = lambda, lambda1 = lambda]); + if (phi < phi0) phi0 = phi; + if (phi > phi1) phi1 = phi; +} + +function linePoint(lambda, phi) { + var p = cartesian([lambda * radians, phi * radians]); + if (p0) { + var normal = cartesianCross(p0, p), + equatorial = [normal[1], -normal[0], 0], + inflection = cartesianCross(equatorial, normal); + cartesianNormalizeInPlace(inflection); + inflection = spherical(inflection); + var delta = lambda - lambda2, + sign = delta > 0 ? 1 : -1, + lambdai = inflection[0] * degrees * sign, + phii, + antimeridian = abs(delta) > 180; + if (antimeridian ^ (sign * lambda2 < lambdai && lambdai < sign * lambda)) { + phii = inflection[1] * degrees; + if (phii > phi1) phi1 = phii; + } else if (lambdai = (lambdai + 360) % 360 - 180, antimeridian ^ (sign * lambda2 < lambdai && lambdai < sign * lambda)) { + phii = -inflection[1] * degrees; + if (phii < phi0) phi0 = phii; + } else { + if (phi < phi0) phi0 = phi; + if (phi > phi1) phi1 = phi; + } + if (antimeridian) { + if (lambda < lambda2) { + if (angle(lambda0, lambda) > angle(lambda0, lambda1)) lambda1 = lambda; + } else { + if (angle(lambda, lambda1) > angle(lambda0, lambda1)) lambda0 = lambda; + } + } else { + if (lambda1 >= lambda0) { + if (lambda < lambda0) lambda0 = lambda; + if (lambda > lambda1) lambda1 = lambda; + } else { + if (lambda > lambda2) { + if (angle(lambda0, lambda) > angle(lambda0, lambda1)) lambda1 = lambda; + } else { + if (angle(lambda, lambda1) > angle(lambda0, lambda1)) lambda0 = lambda; + } + } + } + } else { + ranges.push(range = [lambda0 = lambda, lambda1 = lambda]); + } + if (phi < phi0) phi0 = phi; + if (phi > phi1) phi1 = phi; + p0 = p, lambda2 = lambda; +} + +function boundsLineStart() { + boundsStream.point = linePoint; +} + +function boundsLineEnd() { + range[0] = lambda0, range[1] = lambda1; + boundsStream.point = boundsPoint; + p0 = null; +} + +function boundsRingPoint(lambda, phi) { + if (p0) { + var delta = lambda - lambda2; + deltaSum.add(abs(delta) > 180 ? delta + (delta > 0 ? 360 : -360) : delta); + } else { + lambda00 = lambda, phi00 = phi; + } + areaStream.point(lambda, phi); + linePoint(lambda, phi); +} + +function boundsRingStart() { + areaStream.lineStart(); +} + +function boundsRingEnd() { + boundsRingPoint(lambda00, phi00); + areaStream.lineEnd(); + if (abs(deltaSum) > epsilon) lambda0 = -(lambda1 = 180); + range[0] = lambda0, range[1] = lambda1; + p0 = null; +} + +// Finds the left-right distance between two longitudes. +// This is almost the same as (lambda1 - lambda0 + 360°) % 360°, except that we want +// the distance between ±180° to be 360°. +function angle(lambda0, lambda1) { + return (lambda1 -= lambda0) < 0 ? lambda1 + 360 : lambda1; +} + +function rangeCompare(a, b) { + return a[0] - b[0]; +} + +function rangeContains(range, x) { + return range[0] <= range[1] ? range[0] <= x && x <= range[1] : x < range[0] || range[1] < x; +} + +export default function(feature) { + var i, n, a, b, merged, deltaMax, delta; + + phi1 = lambda1 = -(lambda0 = phi0 = Infinity); + ranges = []; + stream(feature, boundsStream); + + // First, sort ranges by their minimum longitudes. + if (n = ranges.length) { + ranges.sort(rangeCompare); + + // Then, merge any ranges that overlap. + for (i = 1, a = ranges[0], merged = [a]; i < n; ++i) { + b = ranges[i]; + if (rangeContains(a, b[0]) || rangeContains(a, b[1])) { + if (angle(a[0], b[1]) > angle(a[0], a[1])) a[1] = b[1]; + if (angle(b[0], a[1]) > angle(a[0], a[1])) a[0] = b[0]; + } else { + merged.push(a = b); + } + } + + // Finally, find the largest gap between the merged ranges. + // The final bounding box will be the inverse of this gap. + for (deltaMax = -Infinity, n = merged.length - 1, i = 0, a = merged[n]; i <= n; a = b, ++i) { + b = merged[i]; + if ((delta = angle(a[1], b[0])) > deltaMax) deltaMax = delta, lambda0 = b[0], lambda1 = a[1]; + } + } + + ranges = range = null; + + return lambda0 === Infinity || phi0 === Infinity + ? [[NaN, NaN], [NaN, NaN]] + : [[lambda0, phi0], [lambda1, phi1]]; +} diff --git a/frontend/node_modules/d3-geo/src/cartesian.js b/frontend/node_modules/d3-geo/src/cartesian.js new file mode 100644 index 0000000..73790a6 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/cartesian.js @@ -0,0 +1,33 @@ +import {asin, atan2, cos, sin, sqrt} from "./math.js"; + +export function spherical(cartesian) { + return [atan2(cartesian[1], cartesian[0]), asin(cartesian[2])]; +} + +export function cartesian(spherical) { + var lambda = spherical[0], phi = spherical[1], cosPhi = cos(phi); + return [cosPhi * cos(lambda), cosPhi * sin(lambda), sin(phi)]; +} + +export function cartesianDot(a, b) { + return a[0] * b[0] + a[1] * b[1] + a[2] * b[2]; +} + +export function cartesianCross(a, b) { + return [a[1] * b[2] - a[2] * b[1], a[2] * b[0] - a[0] * b[2], a[0] * b[1] - a[1] * b[0]]; +} + +// TODO return a +export function cartesianAddInPlace(a, b) { + a[0] += b[0], a[1] += b[1], a[2] += b[2]; +} + +export function cartesianScale(vector, k) { + return [vector[0] * k, vector[1] * k, vector[2] * k]; +} + +// TODO return d +export function cartesianNormalizeInPlace(d) { + var l = sqrt(d[0] * d[0] + d[1] * d[1] + d[2] * d[2]); + d[0] /= l, d[1] /= l, d[2] /= l; +} diff --git a/frontend/node_modules/d3-geo/src/centroid.js b/frontend/node_modules/d3-geo/src/centroid.js new file mode 100644 index 0000000..6b1eede --- /dev/null +++ b/frontend/node_modules/d3-geo/src/centroid.js @@ -0,0 +1,143 @@ +import {Adder} from "d3-array"; +import {asin, atan2, cos, degrees, epsilon, epsilon2, hypot, radians, sin, sqrt} from "./math.js"; +import noop from "./noop.js"; +import stream from "./stream.js"; + +var W0, W1, + X0, Y0, Z0, + X1, Y1, Z1, + X2, Y2, Z2, + lambda00, phi00, // first point + x0, y0, z0; // previous point + +var centroidStream = { + sphere: noop, + point: centroidPoint, + lineStart: centroidLineStart, + lineEnd: centroidLineEnd, + polygonStart: function() { + centroidStream.lineStart = centroidRingStart; + centroidStream.lineEnd = centroidRingEnd; + }, + polygonEnd: function() { + centroidStream.lineStart = centroidLineStart; + centroidStream.lineEnd = centroidLineEnd; + } +}; + +// Arithmetic mean of Cartesian vectors. +function centroidPoint(lambda, phi) { + lambda *= radians, phi *= radians; + var cosPhi = cos(phi); + centroidPointCartesian(cosPhi * cos(lambda), cosPhi * sin(lambda), sin(phi)); +} + +function centroidPointCartesian(x, y, z) { + ++W0; + X0 += (x - X0) / W0; + Y0 += (y - Y0) / W0; + Z0 += (z - Z0) / W0; +} + +function centroidLineStart() { + centroidStream.point = centroidLinePointFirst; +} + +function centroidLinePointFirst(lambda, phi) { + lambda *= radians, phi *= radians; + var cosPhi = cos(phi); + x0 = cosPhi * cos(lambda); + y0 = cosPhi * sin(lambda); + z0 = sin(phi); + centroidStream.point = centroidLinePoint; + centroidPointCartesian(x0, y0, z0); +} + +function centroidLinePoint(lambda, phi) { + lambda *= radians, phi *= radians; + var cosPhi = cos(phi), + x = cosPhi * cos(lambda), + y = cosPhi * sin(lambda), + z = sin(phi), + w = atan2(sqrt((w = y0 * z - z0 * y) * w + (w = z0 * x - x0 * z) * w + (w = x0 * y - y0 * x) * w), x0 * x + y0 * y + z0 * z); + W1 += w; + X1 += w * (x0 + (x0 = x)); + Y1 += w * (y0 + (y0 = y)); + Z1 += w * (z0 + (z0 = z)); + centroidPointCartesian(x0, y0, z0); +} + +function centroidLineEnd() { + centroidStream.point = centroidPoint; +} + +// See J. E. Brock, The Inertia Tensor for a Spherical Triangle, +// J. Applied Mechanics 42, 239 (1975). +function centroidRingStart() { + centroidStream.point = centroidRingPointFirst; +} + +function centroidRingEnd() { + centroidRingPoint(lambda00, phi00); + centroidStream.point = centroidPoint; +} + +function centroidRingPointFirst(lambda, phi) { + lambda00 = lambda, phi00 = phi; + lambda *= radians, phi *= radians; + centroidStream.point = centroidRingPoint; + var cosPhi = cos(phi); + x0 = cosPhi * cos(lambda); + y0 = cosPhi * sin(lambda); + z0 = sin(phi); + centroidPointCartesian(x0, y0, z0); +} + +function centroidRingPoint(lambda, phi) { + lambda *= radians, phi *= radians; + var cosPhi = cos(phi), + x = cosPhi * cos(lambda), + y = cosPhi * sin(lambda), + z = sin(phi), + cx = y0 * z - z0 * y, + cy = z0 * x - x0 * z, + cz = x0 * y - y0 * x, + m = hypot(cx, cy, cz), + w = asin(m), // line weight = angle + v = m && -w / m; // area weight multiplier + X2.add(v * cx); + Y2.add(v * cy); + Z2.add(v * cz); + W1 += w; + X1 += w * (x0 + (x0 = x)); + Y1 += w * (y0 + (y0 = y)); + Z1 += w * (z0 + (z0 = z)); + centroidPointCartesian(x0, y0, z0); +} + +export default function(object) { + W0 = W1 = + X0 = Y0 = Z0 = + X1 = Y1 = Z1 = 0; + X2 = new Adder(); + Y2 = new Adder(); + Z2 = new Adder(); + stream(object, centroidStream); + + var x = +X2, + y = +Y2, + z = +Z2, + m = hypot(x, y, z); + + // If the area-weighted ccentroid is undefined, fall back to length-weighted ccentroid. + if (m < epsilon2) { + x = X1, y = Y1, z = Z1; + // If the feature has zero length, fall back to arithmetic mean of point vectors. + if (W1 < epsilon) x = X0, y = Y0, z = Z0; + m = hypot(x, y, z); + // If the feature still has an undefined ccentroid, then return. + if (m < epsilon2) return [NaN, NaN]; + } + + return [atan2(y, x) * degrees, asin(z / m) * degrees]; +} diff --git a/frontend/node_modules/d3-geo/src/circle.js b/frontend/node_modules/d3-geo/src/circle.js new file mode 100644 index 0000000..2b86270 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/circle.js @@ -0,0 +1,72 @@ +import {cartesian, cartesianNormalizeInPlace, spherical} from "./cartesian.js"; +import constant from "./constant.js"; +import {acos, cos, degrees, epsilon, radians, sin, tau} from "./math.js"; +import {rotateRadians} from "./rotation.js"; + +// Generates a circle centered at [0°, 0°], with a given radius and precision. +export function circleStream(stream, radius, delta, direction, t0, t1) { + if (!delta) return; + var cosRadius = cos(radius), + sinRadius = sin(radius), + step = direction * delta; + if (t0 == null) { + t0 = radius + direction * tau; + t1 = radius - step / 2; + } else { + t0 = circleRadius(cosRadius, t0); + t1 = circleRadius(cosRadius, t1); + if (direction > 0 ? t0 < t1 : t0 > t1) t0 += direction * tau; + } + for (var point, t = t0; direction > 0 ? t > t1 : t < t1; t -= step) { + point = spherical([cosRadius, -sinRadius * cos(t), -sinRadius * sin(t)]); + stream.point(point[0], point[1]); + } +} + +// Returns the signed angle of a cartesian point relative to [cosRadius, 0, 0]. +function circleRadius(cosRadius, point) { + point = cartesian(point), point[0] -= cosRadius; + cartesianNormalizeInPlace(point); + var radius = acos(-point[1]); + return ((-point[2] < 0 ? -radius : radius) + tau - epsilon) % tau; +} + +export default function() { + var center = constant([0, 0]), + radius = constant(90), + precision = constant(2), + ring, + rotate, + stream = {point: point}; + + function point(x, y) { + ring.push(x = rotate(x, y)); + x[0] *= degrees, x[1] *= degrees; + } + + function circle() { + var c = center.apply(this, arguments), + r = radius.apply(this, arguments) * radians, + p = precision.apply(this, arguments) * radians; + ring = []; + rotate = rotateRadians(-c[0] * radians, -c[1] * radians, 0).invert; + circleStream(stream, r, p, 1); + c = {type: "Polygon", coordinates: [ring]}; + ring = rotate = null; + return c; + } + + circle.center = function(_) { + return arguments.length ? (center = typeof _ === "function" ? _ : constant([+_[0], +_[1]]), circle) : center; + }; + + circle.radius = function(_) { + return arguments.length ? (radius = typeof _ === "function" ? _ : constant(+_), circle) : radius; + }; + + circle.precision = function(_) { + return arguments.length ? (precision = typeof _ === "function" ? _ : constant(+_), circle) : precision; + }; + + return circle; +} diff --git a/frontend/node_modules/d3-geo/src/clip/antimeridian.js b/frontend/node_modules/d3-geo/src/clip/antimeridian.js new file mode 100644 index 0000000..7ed32d4 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/clip/antimeridian.js @@ -0,0 +1,92 @@ +import clip from "./index.js"; +import {abs, atan, cos, epsilon, halfPi, pi, sin} from "../math.js"; + +export default clip( + function() { return true; }, + clipAntimeridianLine, + clipAntimeridianInterpolate, + [-pi, -halfPi] +); + +// Takes a line and cuts into visible segments. Return values: 0 - there were +// intersections or the line was empty; 1 - no intersections; 2 - there were +// intersections, and the first and last segments should be rejoined. +function clipAntimeridianLine(stream) { + var lambda0 = NaN, + phi0 = NaN, + sign0 = NaN, + clean; // no intersections + + return { + lineStart: function() { + stream.lineStart(); + clean = 1; + }, + point: function(lambda1, phi1) { + var sign1 = lambda1 > 0 ? pi : -pi, + delta = abs(lambda1 - lambda0); + if (abs(delta - pi) < epsilon) { // line crosses a pole + stream.point(lambda0, phi0 = (phi0 + phi1) / 2 > 0 ? halfPi : -halfPi); + stream.point(sign0, phi0); + stream.lineEnd(); + stream.lineStart(); + stream.point(sign1, phi0); + stream.point(lambda1, phi0); + clean = 0; + } else if (sign0 !== sign1 && delta >= pi) { // line crosses antimeridian + if (abs(lambda0 - sign0) < epsilon) lambda0 -= sign0 * epsilon; // handle degeneracies + if (abs(lambda1 - sign1) < epsilon) lambda1 -= sign1 * epsilon; + phi0 = clipAntimeridianIntersect(lambda0, phi0, lambda1, phi1); + stream.point(sign0, phi0); + stream.lineEnd(); + stream.lineStart(); + stream.point(sign1, phi0); + clean = 0; + } + stream.point(lambda0 = lambda1, phi0 = phi1); + sign0 = sign1; + }, + lineEnd: function() { + stream.lineEnd(); + lambda0 = phi0 = NaN; + }, + clean: function() { + return 2 - clean; // if intersections, rejoin first and last segments + } + }; +} + +function clipAntimeridianIntersect(lambda0, phi0, lambda1, phi1) { + var cosPhi0, + cosPhi1, + sinLambda0Lambda1 = sin(lambda0 - lambda1); + return abs(sinLambda0Lambda1) > epsilon + ? atan((sin(phi0) * (cosPhi1 = cos(phi1)) * sin(lambda1) + - sin(phi1) * (cosPhi0 = cos(phi0)) * sin(lambda0)) + / (cosPhi0 * cosPhi1 * sinLambda0Lambda1)) + : (phi0 + phi1) / 2; +} + +function clipAntimeridianInterpolate(from, to, direction, stream) { + var phi; + if (from == null) { + phi = direction * halfPi; + stream.point(-pi, phi); + stream.point(0, phi); + stream.point(pi, phi); + stream.point(pi, 0); + stream.point(pi, -phi); + stream.point(0, -phi); + stream.point(-pi, -phi); + stream.point(-pi, 0); + stream.point(-pi, phi); + } else if (abs(from[0] - to[0]) > epsilon) { + var lambda = from[0] < to[0] ? pi : -pi; + phi = direction * lambda / 2; + stream.point(-lambda, phi); + stream.point(0, phi); + stream.point(lambda, phi); + } else { + stream.point(to[0], to[1]); + } +} diff --git a/frontend/node_modules/d3-geo/src/clip/buffer.js b/frontend/node_modules/d3-geo/src/clip/buffer.js new file mode 100644 index 0000000..f5e1ece --- /dev/null +++ b/frontend/node_modules/d3-geo/src/clip/buffer.js @@ -0,0 +1,24 @@ +import noop from "../noop.js"; + +export default function() { + var lines = [], + line; + return { + point: function(x, y, m) { + line.push([x, y, m]); + }, + lineStart: function() { + lines.push(line = []); + }, + lineEnd: noop, + rejoin: function() { + if (lines.length > 1) lines.push(lines.pop().concat(lines.shift())); + }, + result: function() { + var result = lines; + lines = []; + line = null; + return result; + } + }; +} diff --git a/frontend/node_modules/d3-geo/src/clip/circle.js b/frontend/node_modules/d3-geo/src/clip/circle.js new file mode 100644 index 0000000..de11999 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/clip/circle.js @@ -0,0 +1,177 @@ +import {cartesian, cartesianAddInPlace, cartesianCross, cartesianDot, cartesianScale, spherical} from "../cartesian.js"; +import {circleStream} from "../circle.js"; +import {abs, cos, epsilon, pi, radians, sqrt} from "../math.js"; +import pointEqual from "../pointEqual.js"; +import clip from "./index.js"; + +export default function(radius) { + var cr = cos(radius), + delta = 2 * radians, + smallRadius = cr > 0, + notHemisphere = abs(cr) > epsilon; // TODO optimise for this common case + + function interpolate(from, to, direction, stream) { + circleStream(stream, radius, delta, direction, from, to); + } + + function visible(lambda, phi) { + return cos(lambda) * cos(phi) > cr; + } + + // Takes a line and cuts into visible segments. Return values used for polygon + // clipping: 0 - there were intersections or the line was empty; 1 - no + // intersections 2 - there were intersections, and the first and last segments + // should be rejoined. + function clipLine(stream) { + var point0, // previous point + c0, // code for previous point + v0, // visibility of previous point + v00, // visibility of first point + clean; // no intersections + return { + lineStart: function() { + v00 = v0 = false; + clean = 1; + }, + point: function(lambda, phi) { + var point1 = [lambda, phi], + point2, + v = visible(lambda, phi), + c = smallRadius + ? v ? 0 : code(lambda, phi) + : v ? code(lambda + (lambda < 0 ? pi : -pi), phi) : 0; + if (!point0 && (v00 = v0 = v)) stream.lineStart(); + if (v !== v0) { + point2 = intersect(point0, point1); + if (!point2 || pointEqual(point0, point2) || pointEqual(point1, point2)) + point1[2] = 1; + } + if (v !== v0) { + clean = 0; + if (v) { + // outside going in + stream.lineStart(); + point2 = intersect(point1, point0); + stream.point(point2[0], point2[1]); + } else { + // inside going out + point2 = intersect(point0, point1); + stream.point(point2[0], point2[1], 2); + stream.lineEnd(); + } + point0 = point2; + } else if (notHemisphere && point0 && smallRadius ^ v) { + var t; + // If the codes for two points are different, or are both zero, + // and there this segment intersects with the small circle. + if (!(c & c0) && (t = intersect(point1, point0, true))) { + clean = 0; + if (smallRadius) { + stream.lineStart(); + stream.point(t[0][0], t[0][1]); + stream.point(t[1][0], t[1][1]); + stream.lineEnd(); + } else { + stream.point(t[1][0], t[1][1]); + stream.lineEnd(); + stream.lineStart(); + stream.point(t[0][0], t[0][1], 3); + } + } + } + if (v && (!point0 || !pointEqual(point0, point1))) { + stream.point(point1[0], point1[1]); + } + point0 = point1, v0 = v, c0 = c; + }, + lineEnd: function() { + if (v0) stream.lineEnd(); + point0 = null; + }, + // Rejoin first and last segments if there were intersections and the first + // and last points were visible. + clean: function() { + return clean | ((v00 && v0) << 1); + } + }; + } + + // Intersects the great circle between a and b with the clip circle. + function intersect(a, b, two) { + var pa = cartesian(a), + pb = cartesian(b); + + // We have two planes, n1.p = d1 and n2.p = d2. + // Find intersection line p(t) = c1 n1 + c2 n2 + t (n1 ⨯ n2). + var n1 = [1, 0, 0], // normal + n2 = cartesianCross(pa, pb), + n2n2 = cartesianDot(n2, n2), + n1n2 = n2[0], // cartesianDot(n1, n2), + determinant = n2n2 - n1n2 * n1n2; + + // Two polar points. + if (!determinant) return !two && a; + + var c1 = cr * n2n2 / determinant, + c2 = -cr * n1n2 / determinant, + n1xn2 = cartesianCross(n1, n2), + A = cartesianScale(n1, c1), + B = cartesianScale(n2, c2); + cartesianAddInPlace(A, B); + + // Solve |p(t)|^2 = 1. + var u = n1xn2, + w = cartesianDot(A, u), + uu = cartesianDot(u, u), + t2 = w * w - uu * (cartesianDot(A, A) - 1); + + if (t2 < 0) return; + + var t = sqrt(t2), + q = cartesianScale(u, (-w - t) / uu); + cartesianAddInPlace(q, A); + q = spherical(q); + + if (!two) return q; + + // Two intersection points. + var lambda0 = a[0], + lambda1 = b[0], + phi0 = a[1], + phi1 = b[1], + z; + + if (lambda1 < lambda0) z = lambda0, lambda0 = lambda1, lambda1 = z; + + var delta = lambda1 - lambda0, + polar = abs(delta - pi) < epsilon, + meridian = polar || delta < epsilon; + + if (!polar && phi1 < phi0) z = phi0, phi0 = phi1, phi1 = z; + + // Check that the first point is between a and b. + if (meridian + ? polar + ? phi0 + phi1 > 0 ^ q[1] < (abs(q[0] - lambda0) < epsilon ? phi0 : phi1) + : phi0 <= q[1] && q[1] <= phi1 + : delta > pi ^ (lambda0 <= q[0] && q[0] <= lambda1)) { + var q1 = cartesianScale(u, (-w + t) / uu); + cartesianAddInPlace(q1, A); + return [q, spherical(q1)]; + } + } + + // Generates a 4-bit vector representing the location of a point relative to + // the small circle's bounding box. + function code(lambda, phi) { + var r = smallRadius ? radius : pi - radius, + code = 0; + if (lambda < -r) code |= 1; // left + else if (lambda > r) code |= 2; // right + if (phi < -r) code |= 4; // below + else if (phi > r) code |= 8; // above + return code; + } + + return clip(visible, clipLine, interpolate, smallRadius ? [0, -radius] : [-pi, radius - pi]); +} diff --git a/frontend/node_modules/d3-geo/src/clip/extent.js b/frontend/node_modules/d3-geo/src/clip/extent.js new file mode 100644 index 0000000..5ff06ee --- /dev/null +++ b/frontend/node_modules/d3-geo/src/clip/extent.js @@ -0,0 +1,20 @@ +import clipRectangle from "./rectangle.js"; + +export default function() { + var x0 = 0, + y0 = 0, + x1 = 960, + y1 = 500, + cache, + cacheStream, + clip; + + return clip = { + stream: function(stream) { + return cache && cacheStream === stream ? cache : cache = clipRectangle(x0, y0, x1, y1)(cacheStream = stream); + }, + extent: function(_) { + return arguments.length ? (x0 = +_[0][0], y0 = +_[0][1], x1 = +_[1][0], y1 = +_[1][1], cache = cacheStream = null, clip) : [[x0, y0], [x1, y1]]; + } + }; +} diff --git a/frontend/node_modules/d3-geo/src/clip/index.js b/frontend/node_modules/d3-geo/src/clip/index.js new file mode 100644 index 0000000..af7ac91 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/clip/index.js @@ -0,0 +1,131 @@ +import clipBuffer from "./buffer.js"; +import clipRejoin from "./rejoin.js"; +import {epsilon, halfPi} from "../math.js"; +import polygonContains from "../polygonContains.js"; +import {merge} from "d3-array"; + +export default function(pointVisible, clipLine, interpolate, start) { + return function(sink) { + var line = clipLine(sink), + ringBuffer = clipBuffer(), + ringSink = clipLine(ringBuffer), + polygonStarted = false, + polygon, + segments, + ring; + + var clip = { + point: point, + lineStart: lineStart, + lineEnd: lineEnd, + polygonStart: function() { + clip.point = pointRing; + clip.lineStart = ringStart; + clip.lineEnd = ringEnd; + segments = []; + polygon = []; + }, + polygonEnd: function() { + clip.point = point; + clip.lineStart = lineStart; + clip.lineEnd = lineEnd; + segments = merge(segments); + var startInside = polygonContains(polygon, start); + if (segments.length) { + if (!polygonStarted) sink.polygonStart(), polygonStarted = true; + clipRejoin(segments, compareIntersection, startInside, interpolate, sink); + } else if (startInside) { + if (!polygonStarted) sink.polygonStart(), polygonStarted = true; + sink.lineStart(); + interpolate(null, null, 1, sink); + sink.lineEnd(); + } + if (polygonStarted) sink.polygonEnd(), polygonStarted = false; + segments = polygon = null; + }, + sphere: function() { + sink.polygonStart(); + sink.lineStart(); + interpolate(null, null, 1, sink); + sink.lineEnd(); + sink.polygonEnd(); + } + }; + + function point(lambda, phi) { + if (pointVisible(lambda, phi)) sink.point(lambda, phi); + } + + function pointLine(lambda, phi) { + line.point(lambda, phi); + } + + function lineStart() { + clip.point = pointLine; + line.lineStart(); + } + + function lineEnd() { + clip.point = point; + line.lineEnd(); + } + + function pointRing(lambda, phi) { + ring.push([lambda, phi]); + ringSink.point(lambda, phi); + } + + function ringStart() { + ringSink.lineStart(); + ring = []; + } + + function ringEnd() { + pointRing(ring[0][0], ring[0][1]); + ringSink.lineEnd(); + + var clean = ringSink.clean(), + ringSegments = ringBuffer.result(), + i, n = ringSegments.length, m, + segment, + point; + + ring.pop(); + polygon.push(ring); + ring = null; + + if (!n) return; + + // No intersections. + if (clean & 1) { + segment = ringSegments[0]; + if ((m = segment.length - 1) > 0) { + if (!polygonStarted) sink.polygonStart(), polygonStarted = true; + sink.lineStart(); + for (i = 0; i < m; ++i) sink.point((point = segment[i])[0], point[1]); + sink.lineEnd(); + } + return; + } + + // Rejoin connected segments. + // TODO reuse ringBuffer.rejoin()? + if (n > 1 && clean & 2) ringSegments.push(ringSegments.pop().concat(ringSegments.shift())); + + segments.push(ringSegments.filter(validSegment)); + } + + return clip; + }; +} + +function validSegment(segment) { + return segment.length > 1; +} + +// Intersections are sorted along the clip edge. For both antimeridian cutting +// and circle clipping, the same comparison is used. +function compareIntersection(a, b) { + return ((a = a.x)[0] < 0 ? a[1] - halfPi - epsilon : halfPi - a[1]) + - ((b = b.x)[0] < 0 ? b[1] - halfPi - epsilon : halfPi - b[1]); +} diff --git a/frontend/node_modules/d3-geo/src/clip/line.js b/frontend/node_modules/d3-geo/src/clip/line.js new file mode 100644 index 0000000..3b173d7 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/clip/line.js @@ -0,0 +1,59 @@ +export default function(a, b, x0, y0, x1, y1) { + var ax = a[0], + ay = a[1], + bx = b[0], + by = b[1], + t0 = 0, + t1 = 1, + dx = bx - ax, + dy = by - ay, + r; + + r = x0 - ax; + if (!dx && r > 0) return; + r /= dx; + if (dx < 0) { + if (r < t0) return; + if (r < t1) t1 = r; + } else if (dx > 0) { + if (r > t1) return; + if (r > t0) t0 = r; + } + + r = x1 - ax; + if (!dx && r < 0) return; + r /= dx; + if (dx < 0) { + if (r > t1) return; + if (r > t0) t0 = r; + } else if (dx > 0) { + if (r < t0) return; + if (r < t1) t1 = r; + } + + r = y0 - ay; + if (!dy && r > 0) return; + r /= dy; + if (dy < 0) { + if (r < t0) return; + if (r < t1) t1 = r; + } else if (dy > 0) { + if (r > t1) return; + if (r > t0) t0 = r; + } + + r = y1 - ay; + if (!dy && r < 0) return; + r /= dy; + if (dy < 0) { + if (r > t1) return; + if (r > t0) t0 = r; + } else if (dy > 0) { + if (r < t0) return; + if (r < t1) t1 = r; + } + + if (t0 > 0) a[0] = ax + t0 * dx, a[1] = ay + t0 * dy; + if (t1 < 1) b[0] = ax + t1 * dx, b[1] = ay + t1 * dy; + return true; +} diff --git a/frontend/node_modules/d3-geo/src/clip/rectangle.js b/frontend/node_modules/d3-geo/src/clip/rectangle.js new file mode 100644 index 0000000..4767626 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/clip/rectangle.js @@ -0,0 +1,168 @@ +import {abs, epsilon} from "../math.js"; +import clipBuffer from "./buffer.js"; +import clipLine from "./line.js"; +import clipRejoin from "./rejoin.js"; +import {merge} from "d3-array"; + +var clipMax = 1e9, clipMin = -clipMax; + +// TODO Use d3-polygon’s polygonContains here for the ring check? +// TODO Eliminate duplicate buffering in clipBuffer and polygon.push? + +export default function clipRectangle(x0, y0, x1, y1) { + + function visible(x, y) { + return x0 <= x && x <= x1 && y0 <= y && y <= y1; + } + + function interpolate(from, to, direction, stream) { + var a = 0, a1 = 0; + if (from == null + || (a = corner(from, direction)) !== (a1 = corner(to, direction)) + || comparePoint(from, to) < 0 ^ direction > 0) { + do stream.point(a === 0 || a === 3 ? x0 : x1, a > 1 ? y1 : y0); + while ((a = (a + direction + 4) % 4) !== a1); + } else { + stream.point(to[0], to[1]); + } + } + + function corner(p, direction) { + return abs(p[0] - x0) < epsilon ? direction > 0 ? 0 : 3 + : abs(p[0] - x1) < epsilon ? direction > 0 ? 2 : 1 + : abs(p[1] - y0) < epsilon ? direction > 0 ? 1 : 0 + : direction > 0 ? 3 : 2; // abs(p[1] - y1) < epsilon + } + + function compareIntersection(a, b) { + return comparePoint(a.x, b.x); + } + + function comparePoint(a, b) { + var ca = corner(a, 1), + cb = corner(b, 1); + return ca !== cb ? ca - cb + : ca === 0 ? b[1] - a[1] + : ca === 1 ? a[0] - b[0] + : ca === 2 ? a[1] - b[1] + : b[0] - a[0]; + } + + return function(stream) { + var activeStream = stream, + bufferStream = clipBuffer(), + segments, + polygon, + ring, + x__, y__, v__, // first point + x_, y_, v_, // previous point + first, + clean; + + var clipStream = { + point: point, + lineStart: lineStart, + lineEnd: lineEnd, + polygonStart: polygonStart, + polygonEnd: polygonEnd + }; + + function point(x, y) { + if (visible(x, y)) activeStream.point(x, y); + } + + function polygonInside() { + var winding = 0; + + for (var i = 0, n = polygon.length; i < n; ++i) { + for (var ring = polygon[i], j = 1, m = ring.length, point = ring[0], a0, a1, b0 = point[0], b1 = point[1]; j < m; ++j) { + a0 = b0, a1 = b1, point = ring[j], b0 = point[0], b1 = point[1]; + if (a1 <= y1) { if (b1 > y1 && (b0 - a0) * (y1 - a1) > (b1 - a1) * (x0 - a0)) ++winding; } + else { if (b1 <= y1 && (b0 - a0) * (y1 - a1) < (b1 - a1) * (x0 - a0)) --winding; } + } + } + + return winding; + } + + // Buffer geometry within a polygon and then clip it en masse. + function polygonStart() { + activeStream = bufferStream, segments = [], polygon = [], clean = true; + } + + function polygonEnd() { + var startInside = polygonInside(), + cleanInside = clean && startInside, + visible = (segments = merge(segments)).length; + if (cleanInside || visible) { + stream.polygonStart(); + if (cleanInside) { + stream.lineStart(); + interpolate(null, null, 1, stream); + stream.lineEnd(); + } + if (visible) { + clipRejoin(segments, compareIntersection, startInside, interpolate, stream); + } + stream.polygonEnd(); + } + activeStream = stream, segments = polygon = ring = null; + } + + function lineStart() { + clipStream.point = linePoint; + if (polygon) polygon.push(ring = []); + first = true; + v_ = false; + x_ = y_ = NaN; + } + + // TODO rather than special-case polygons, simply handle them separately. + // Ideally, coincident intersection points should be jittered to avoid + // clipping issues. + function lineEnd() { + if (segments) { + linePoint(x__, y__); + if (v__ && v_) bufferStream.rejoin(); + segments.push(bufferStream.result()); + } + clipStream.point = point; + if (v_) activeStream.lineEnd(); + } + + function linePoint(x, y) { + var v = visible(x, y); + if (polygon) ring.push([x, y]); + if (first) { + x__ = x, y__ = y, v__ = v; + first = false; + if (v) { + activeStream.lineStart(); + activeStream.point(x, y); + } + } else { + if (v && v_) activeStream.point(x, y); + else { + var a = [x_ = Math.max(clipMin, Math.min(clipMax, x_)), y_ = Math.max(clipMin, Math.min(clipMax, y_))], + b = [x = Math.max(clipMin, Math.min(clipMax, x)), y = Math.max(clipMin, Math.min(clipMax, y))]; + if (clipLine(a, b, x0, y0, x1, y1)) { + if (!v_) { + activeStream.lineStart(); + activeStream.point(a[0], a[1]); + } + activeStream.point(b[0], b[1]); + if (!v) activeStream.lineEnd(); + clean = false; + } else if (v) { + activeStream.lineStart(); + activeStream.point(x, y); + clean = false; + } + } + } + x_ = x, y_ = y, v_ = v; + } + + return clipStream; + }; +} diff --git a/frontend/node_modules/d3-geo/src/clip/rejoin.js b/frontend/node_modules/d3-geo/src/clip/rejoin.js new file mode 100644 index 0000000..37e0241 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/clip/rejoin.js @@ -0,0 +1,103 @@ +import pointEqual from "../pointEqual.js"; +import {epsilon} from "../math.js"; + +function Intersection(point, points, other, entry) { + this.x = point; + this.z = points; + this.o = other; // another intersection + this.e = entry; // is an entry? + this.v = false; // visited + this.n = this.p = null; // next & previous +} + +// A generalized polygon clipping algorithm: given a polygon that has been cut +// into its visible line segments, and rejoins the segments by interpolating +// along the clip edge. +export default function(segments, compareIntersection, startInside, interpolate, stream) { + var subject = [], + clip = [], + i, + n; + + segments.forEach(function(segment) { + if ((n = segment.length - 1) <= 0) return; + var n, p0 = segment[0], p1 = segment[n], x; + + if (pointEqual(p0, p1)) { + if (!p0[2] && !p1[2]) { + stream.lineStart(); + for (i = 0; i < n; ++i) stream.point((p0 = segment[i])[0], p0[1]); + stream.lineEnd(); + return; + } + // handle degenerate cases by moving the point + p1[0] += 2 * epsilon; + } + + subject.push(x = new Intersection(p0, segment, null, true)); + clip.push(x.o = new Intersection(p0, null, x, false)); + subject.push(x = new Intersection(p1, segment, null, false)); + clip.push(x.o = new Intersection(p1, null, x, true)); + }); + + if (!subject.length) return; + + clip.sort(compareIntersection); + link(subject); + link(clip); + + for (i = 0, n = clip.length; i < n; ++i) { + clip[i].e = startInside = !startInside; + } + + var start = subject[0], + points, + point; + + while (1) { + // Find first unvisited intersection. + var current = start, + isSubject = true; + while (current.v) if ((current = current.n) === start) return; + points = current.z; + stream.lineStart(); + do { + current.v = current.o.v = true; + if (current.e) { + if (isSubject) { + for (i = 0, n = points.length; i < n; ++i) stream.point((point = points[i])[0], point[1]); + } else { + interpolate(current.x, current.n.x, 1, stream); + } + current = current.n; + } else { + if (isSubject) { + points = current.p.z; + for (i = points.length - 1; i >= 0; --i) stream.point((point = points[i])[0], point[1]); + } else { + interpolate(current.x, current.p.x, -1, stream); + } + current = current.p; + } + current = current.o; + points = current.z; + isSubject = !isSubject; + } while (!current.v); + stream.lineEnd(); + } +} + +function link(array) { + if (!(n = array.length)) return; + var n, + i = 0, + a = array[0], + b; + while (++i < n) { + a.n = b = array[i]; + b.p = a; + a = b; + } + a.n = b = array[0]; + b.p = a; +} diff --git a/frontend/node_modules/d3-geo/src/compose.js b/frontend/node_modules/d3-geo/src/compose.js new file mode 100644 index 0000000..f6a967a --- /dev/null +++ b/frontend/node_modules/d3-geo/src/compose.js @@ -0,0 +1,12 @@ +export default function(a, b) { + + function compose(x, y) { + return x = a(x, y), b(x[0], x[1]); + } + + if (a.invert && b.invert) compose.invert = function(x, y) { + return x = b.invert(x, y), x && a.invert(x[0], x[1]); + }; + + return compose; +} diff --git a/frontend/node_modules/d3-geo/src/constant.js b/frontend/node_modules/d3-geo/src/constant.js new file mode 100644 index 0000000..b7d42e7 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/constant.js @@ -0,0 +1,5 @@ +export default function(x) { + return function() { + return x; + }; +} diff --git a/frontend/node_modules/d3-geo/src/contains.js b/frontend/node_modules/d3-geo/src/contains.js new file mode 100644 index 0000000..923f4d4 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/contains.js @@ -0,0 +1,97 @@ +import {default as polygonContains} from "./polygonContains.js"; +import {default as distance} from "./distance.js"; +import {epsilon2, radians} from "./math.js"; + +var containsObjectType = { + Feature: function(object, point) { + return containsGeometry(object.geometry, point); + }, + FeatureCollection: function(object, point) { + var features = object.features, i = -1, n = features.length; + while (++i < n) if (containsGeometry(features[i].geometry, point)) return true; + return false; + } +}; + +var containsGeometryType = { + Sphere: function() { + return true; + }, + Point: function(object, point) { + return containsPoint(object.coordinates, point); + }, + MultiPoint: function(object, point) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) if (containsPoint(coordinates[i], point)) return true; + return false; + }, + LineString: function(object, point) { + return containsLine(object.coordinates, point); + }, + MultiLineString: function(object, point) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) if (containsLine(coordinates[i], point)) return true; + return false; + }, + Polygon: function(object, point) { + return containsPolygon(object.coordinates, point); + }, + MultiPolygon: function(object, point) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) if (containsPolygon(coordinates[i], point)) return true; + return false; + }, + GeometryCollection: function(object, point) { + var geometries = object.geometries, i = -1, n = geometries.length; + while (++i < n) if (containsGeometry(geometries[i], point)) return true; + return false; + } +}; + +function containsGeometry(geometry, point) { + return geometry && containsGeometryType.hasOwnProperty(geometry.type) + ? containsGeometryType[geometry.type](geometry, point) + : false; +} + +function containsPoint(coordinates, point) { + return distance(coordinates, point) === 0; +} + +function containsLine(coordinates, point) { + var ao, bo, ab; + for (var i = 0, n = coordinates.length; i < n; i++) { + bo = distance(coordinates[i], point); + if (bo === 0) return true; + if (i > 0) { + ab = distance(coordinates[i], coordinates[i - 1]); + if ( + ab > 0 && + ao <= ab && + bo <= ab && + (ao + bo - ab) * (1 - Math.pow((ao - bo) / ab, 2)) < epsilon2 * ab + ) + return true; + } + ao = bo; + } + return false; +} + +function containsPolygon(coordinates, point) { + return !!polygonContains(coordinates.map(ringRadians), pointRadians(point)); +} + +function ringRadians(ring) { + return ring = ring.map(pointRadians), ring.pop(), ring; +} + +function pointRadians(point) { + return [point[0] * radians, point[1] * radians]; +} + +export default function(object, point) { + return (object && containsObjectType.hasOwnProperty(object.type) + ? containsObjectType[object.type] + : containsGeometry)(object, point); +} diff --git a/frontend/node_modules/d3-geo/src/distance.js b/frontend/node_modules/d3-geo/src/distance.js new file mode 100644 index 0000000..0cd23db --- /dev/null +++ b/frontend/node_modules/d3-geo/src/distance.js @@ -0,0 +1,10 @@ +import length from "./length.js"; + +var coordinates = [null, null], + object = {type: "LineString", coordinates: coordinates}; + +export default function(a, b) { + coordinates[0] = a; + coordinates[1] = b; + return length(object); +} diff --git a/frontend/node_modules/d3-geo/src/graticule.js b/frontend/node_modules/d3-geo/src/graticule.js new file mode 100644 index 0000000..dc8daaf --- /dev/null +++ b/frontend/node_modules/d3-geo/src/graticule.js @@ -0,0 +1,105 @@ +import {range} from "d3-array"; +import {abs, ceil, epsilon} from "./math.js"; + +function graticuleX(y0, y1, dy) { + var y = range(y0, y1 - epsilon, dy).concat(y1); + return function(x) { return y.map(function(y) { return [x, y]; }); }; +} + +function graticuleY(x0, x1, dx) { + var x = range(x0, x1 - epsilon, dx).concat(x1); + return function(y) { return x.map(function(x) { return [x, y]; }); }; +} + +export default function graticule() { + var x1, x0, X1, X0, + y1, y0, Y1, Y0, + dx = 10, dy = dx, DX = 90, DY = 360, + x, y, X, Y, + precision = 2.5; + + function graticule() { + return {type: "MultiLineString", coordinates: lines()}; + } + + function lines() { + return range(ceil(X0 / DX) * DX, X1, DX).map(X) + .concat(range(ceil(Y0 / DY) * DY, Y1, DY).map(Y)) + .concat(range(ceil(x0 / dx) * dx, x1, dx).filter(function(x) { return abs(x % DX) > epsilon; }).map(x)) + .concat(range(ceil(y0 / dy) * dy, y1, dy).filter(function(y) { return abs(y % DY) > epsilon; }).map(y)); + } + + graticule.lines = function() { + return lines().map(function(coordinates) { return {type: "LineString", coordinates: coordinates}; }); + }; + + graticule.outline = function() { + return { + type: "Polygon", + coordinates: [ + X(X0).concat( + Y(Y1).slice(1), + X(X1).reverse().slice(1), + Y(Y0).reverse().slice(1)) + ] + }; + }; + + graticule.extent = function(_) { + if (!arguments.length) return graticule.extentMinor(); + return graticule.extentMajor(_).extentMinor(_); + }; + + graticule.extentMajor = function(_) { + if (!arguments.length) return [[X0, Y0], [X1, Y1]]; + X0 = +_[0][0], X1 = +_[1][0]; + Y0 = +_[0][1], Y1 = +_[1][1]; + if (X0 > X1) _ = X0, X0 = X1, X1 = _; + if (Y0 > Y1) _ = Y0, Y0 = Y1, Y1 = _; + return graticule.precision(precision); + }; + + graticule.extentMinor = function(_) { + if (!arguments.length) return [[x0, y0], [x1, y1]]; + x0 = +_[0][0], x1 = +_[1][0]; + y0 = +_[0][1], y1 = +_[1][1]; + if (x0 > x1) _ = x0, x0 = x1, x1 = _; + if (y0 > y1) _ = y0, y0 = y1, y1 = _; + return graticule.precision(precision); + }; + + graticule.step = function(_) { + if (!arguments.length) return graticule.stepMinor(); + return graticule.stepMajor(_).stepMinor(_); + }; + + graticule.stepMajor = function(_) { + if (!arguments.length) return [DX, DY]; + DX = +_[0], DY = +_[1]; + return graticule; + }; + + graticule.stepMinor = function(_) { + if (!arguments.length) return [dx, dy]; + dx = +_[0], dy = +_[1]; + return graticule; + }; + + graticule.precision = function(_) { + if (!arguments.length) return precision; + precision = +_; + x = graticuleX(y0, y1, 90); + y = graticuleY(x0, x1, precision); + X = graticuleX(Y0, Y1, 90); + Y = graticuleY(X0, X1, precision); + return graticule; + }; + + return graticule + .extentMajor([[-180, -90 + epsilon], [180, 90 - epsilon]]) + .extentMinor([[-180, -80 - epsilon], [180, 80 + epsilon]]); +} + +export function graticule10() { + return graticule()(); +} diff --git a/frontend/node_modules/d3-geo/src/identity.js b/frontend/node_modules/d3-geo/src/identity.js new file mode 100644 index 0000000..9a80059 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/identity.js @@ -0,0 +1 @@ +export default x => x; diff --git a/frontend/node_modules/d3-geo/src/index.js b/frontend/node_modules/d3-geo/src/index.js new file mode 100644 index 0000000..9a36976 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/index.js @@ -0,0 +1,34 @@ +export {default as geoArea} from "./area.js"; +export {default as geoBounds} from "./bounds.js"; +export {default as geoCentroid} from "./centroid.js"; +export {default as geoCircle} from "./circle.js"; +export {default as geoClipAntimeridian} from "./clip/antimeridian.js"; +export {default as geoClipCircle} from "./clip/circle.js"; +export {default as geoClipExtent} from "./clip/extent.js"; // DEPRECATED! Use d3.geoIdentity().clipExtent(…). +export {default as geoClipRectangle} from "./clip/rectangle.js"; +export {default as geoContains} from "./contains.js"; +export {default as geoDistance} from "./distance.js"; +export {default as geoGraticule, graticule10 as geoGraticule10} from "./graticule.js"; +export {default as geoInterpolate} from "./interpolate.js"; +export {default as geoLength} from "./length.js"; +export {default as geoPath} from "./path/index.js"; +export {default as geoAlbers} from "./projection/albers.js"; +export {default as geoAlbersUsa} from "./projection/albersUsa.js"; +export {default as geoAzimuthalEqualArea, azimuthalEqualAreaRaw as geoAzimuthalEqualAreaRaw} from "./projection/azimuthalEqualArea.js"; +export {default as geoAzimuthalEquidistant, azimuthalEquidistantRaw as geoAzimuthalEquidistantRaw} from "./projection/azimuthalEquidistant.js"; +export {default as geoConicConformal, conicConformalRaw as geoConicConformalRaw} from "./projection/conicConformal.js"; +export {default as geoConicEqualArea, conicEqualAreaRaw as geoConicEqualAreaRaw} from "./projection/conicEqualArea.js"; +export {default as geoConicEquidistant, conicEquidistantRaw as geoConicEquidistantRaw} from "./projection/conicEquidistant.js"; +export {default as geoEqualEarth, equalEarthRaw as geoEqualEarthRaw} from "./projection/equalEarth.js"; +export {default as geoEquirectangular, equirectangularRaw as geoEquirectangularRaw} from "./projection/equirectangular.js"; +export {default as geoGnomonic, gnomonicRaw as geoGnomonicRaw} from "./projection/gnomonic.js"; +export {default as geoIdentity} from "./projection/identity.js"; +export {default as geoProjection, projectionMutator as geoProjectionMutator} from "./projection/index.js"; +export {default as geoMercator, mercatorRaw as geoMercatorRaw} from "./projection/mercator.js"; +export {default as geoNaturalEarth1, naturalEarth1Raw as geoNaturalEarth1Raw} from "./projection/naturalEarth1.js"; +export {default as geoOrthographic, orthographicRaw as geoOrthographicRaw} from "./projection/orthographic.js"; +export {default as geoStereographic, stereographicRaw as geoStereographicRaw} from "./projection/stereographic.js"; +export {default as geoTransverseMercator, transverseMercatorRaw as geoTransverseMercatorRaw} from "./projection/transverseMercator.js"; +export {default as geoRotation} from "./rotation.js"; +export {default as geoStream} from "./stream.js"; +export {default as geoTransform} from "./transform.js"; diff --git a/frontend/node_modules/d3-geo/src/interpolate.js b/frontend/node_modules/d3-geo/src/interpolate.js new file mode 100644 index 0000000..b19fbba --- /dev/null +++ b/frontend/node_modules/d3-geo/src/interpolate.js @@ -0,0 +1,36 @@ +import {asin, atan2, cos, degrees, haversin, radians, sin, sqrt} from "./math.js"; + +export default function(a, b) { + var x0 = a[0] * radians, + y0 = a[1] * radians, + x1 = b[0] * radians, + y1 = b[1] * radians, + cy0 = cos(y0), + sy0 = sin(y0), + cy1 = cos(y1), + sy1 = sin(y1), + kx0 = cy0 * cos(x0), + ky0 = cy0 * sin(x0), + kx1 = cy1 * cos(x1), + ky1 = cy1 * sin(x1), + d = 2 * asin(sqrt(haversin(y1 - y0) + cy0 * cy1 * haversin(x1 - x0))), + k = sin(d); + + var interpolate = d ? function(t) { + var B = sin(t *= d) / k, + A = sin(d - t) / k, + x = A * kx0 + B * kx1, + y = A * ky0 + B * ky1, + z = A * sy0 + B * sy1; + return [ + atan2(y, x) * degrees, + atan2(z, sqrt(x * x + y * y)) * degrees + ]; + } : function() { + return [x0 * degrees, y0 * degrees]; + }; + + interpolate.distance = d; + + return interpolate; +} diff --git a/frontend/node_modules/d3-geo/src/length.js b/frontend/node_modules/d3-geo/src/length.js new file mode 100644 index 0000000..7899e05 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/length.js @@ -0,0 +1,53 @@ +import {Adder} from "d3-array"; +import {abs, atan2, cos, radians, sin, sqrt} from "./math.js"; +import noop from "./noop.js"; +import stream from "./stream.js"; + +var lengthSum, + lambda0, + sinPhi0, + cosPhi0; + +var lengthStream = { + sphere: noop, + point: noop, + lineStart: lengthLineStart, + lineEnd: noop, + polygonStart: noop, + polygonEnd: noop +}; + +function lengthLineStart() { + lengthStream.point = lengthPointFirst; + lengthStream.lineEnd = lengthLineEnd; +} + +function lengthLineEnd() { + lengthStream.point = lengthStream.lineEnd = noop; +} + +function lengthPointFirst(lambda, phi) { + lambda *= radians, phi *= radians; + lambda0 = lambda, sinPhi0 = sin(phi), cosPhi0 = cos(phi); + lengthStream.point = lengthPoint; +} + +function lengthPoint(lambda, phi) { + lambda *= radians, phi *= radians; + var sinPhi = sin(phi), + cosPhi = cos(phi), + delta = abs(lambda - lambda0), + cosDelta = cos(delta), + sinDelta = sin(delta), + x = cosPhi * sinDelta, + y = cosPhi0 * sinPhi - sinPhi0 * cosPhi * cosDelta, + z = sinPhi0 * sinPhi + cosPhi0 * cosPhi * cosDelta; + lengthSum.add(atan2(sqrt(x * x + y * y), z)); + lambda0 = lambda, sinPhi0 = sinPhi, cosPhi0 = cosPhi; +} + +export default function(object) { + lengthSum = new Adder(); + stream(object, lengthStream); + return +lengthSum; +} diff --git a/frontend/node_modules/d3-geo/src/math.js b/frontend/node_modules/d3-geo/src/math.js new file mode 100644 index 0000000..ace500f --- /dev/null +++ b/frontend/node_modules/d3-geo/src/math.js @@ -0,0 +1,36 @@ +export var epsilon = 1e-6; +export var epsilon2 = 1e-12; +export var pi = Math.PI; +export var halfPi = pi / 2; +export var quarterPi = pi / 4; +export var tau = pi * 2; + +export var degrees = 180 / pi; +export var radians = pi / 180; + +export var abs = Math.abs; +export var atan = Math.atan; +export var atan2 = Math.atan2; +export var cos = Math.cos; +export var ceil = Math.ceil; +export var exp = Math.exp; +export var floor = Math.floor; +export var hypot = Math.hypot; +export var log = Math.log; +export var pow = Math.pow; +export var sin = Math.sin; +export var sign = Math.sign || function(x) { return x > 0 ? 1 : x < 0 ? -1 : 0; }; +export var sqrt = Math.sqrt; +export var tan = Math.tan; + +export function acos(x) { + return x > 1 ? 0 : x < -1 ? pi : Math.acos(x); +} + +export function asin(x) { + return x > 1 ? halfPi : x < -1 ? -halfPi : Math.asin(x); +} + +export function haversin(x) { + return (x = sin(x / 2)) * x; +} diff --git a/frontend/node_modules/d3-geo/src/noop.js b/frontend/node_modules/d3-geo/src/noop.js new file mode 100644 index 0000000..ca6a744 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/noop.js @@ -0,0 +1 @@ +export default function noop() {} diff --git a/frontend/node_modules/d3-geo/src/path/area.js b/frontend/node_modules/d3-geo/src/path/area.js new file mode 100644 index 0000000..bb38b19 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/path/area.js @@ -0,0 +1,50 @@ +import {Adder} from "d3-array"; +import {abs} from "../math.js"; +import noop from "../noop.js"; + +var areaSum = new Adder(), + areaRingSum = new Adder(), + x00, + y00, + x0, + y0; + +var areaStream = { + point: noop, + lineStart: noop, + lineEnd: noop, + polygonStart: function() { + areaStream.lineStart = areaRingStart; + areaStream.lineEnd = areaRingEnd; + }, + polygonEnd: function() { + areaStream.lineStart = areaStream.lineEnd = areaStream.point = noop; + areaSum.add(abs(areaRingSum)); + areaRingSum = new Adder(); + }, + result: function() { + var area = areaSum / 2; + areaSum = new Adder(); + return area; + } +}; + +function areaRingStart() { + areaStream.point = areaPointFirst; +} + +function areaPointFirst(x, y) { + areaStream.point = areaPoint; + x00 = x0 = x, y00 = y0 = y; +} + +function areaPoint(x, y) { + areaRingSum.add(y0 * x - x0 * y); + x0 = x, y0 = y; +} + +function areaRingEnd() { + areaPoint(x00, y00); +} + +export default areaStream; diff --git a/frontend/node_modules/d3-geo/src/path/bounds.js b/frontend/node_modules/d3-geo/src/path/bounds.js new file mode 100644 index 0000000..0c83258 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/path/bounds.js @@ -0,0 +1,28 @@ +import noop from "../noop.js"; + +var x0 = Infinity, + y0 = x0, + x1 = -x0, + y1 = x1; + +var boundsStream = { + point: boundsPoint, + lineStart: noop, + lineEnd: noop, + polygonStart: noop, + polygonEnd: noop, + result: function() { + var bounds = [[x0, y0], [x1, y1]]; + x1 = y1 = -(y0 = x0 = Infinity); + return bounds; + } +}; + +function boundsPoint(x, y) { + if (x < x0) x0 = x; + if (x > x1) x1 = x; + if (y < y0) y0 = y; + if (y > y1) y1 = y; +} + +export default boundsStream; diff --git a/frontend/node_modules/d3-geo/src/path/centroid.js b/frontend/node_modules/d3-geo/src/path/centroid.js new file mode 100644 index 0000000..852ef76 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/path/centroid.js @@ -0,0 +1,100 @@ +import {sqrt} from "../math.js"; + +// TODO Enforce positive area for exterior, negative area for interior? + +var X0 = 0, + Y0 = 0, + Z0 = 0, + X1 = 0, + Y1 = 0, + Z1 = 0, + X2 = 0, + Y2 = 0, + Z2 = 0, + x00, + y00, + x0, + y0; + +var centroidStream = { + point: centroidPoint, + lineStart: centroidLineStart, + lineEnd: centroidLineEnd, + polygonStart: function() { + centroidStream.lineStart = centroidRingStart; + centroidStream.lineEnd = centroidRingEnd; + }, + polygonEnd: function() { + centroidStream.point = centroidPoint; + centroidStream.lineStart = centroidLineStart; + centroidStream.lineEnd = centroidLineEnd; + }, + result: function() { + var centroid = Z2 ? [X2 / Z2, Y2 / Z2] + : Z1 ? [X1 / Z1, Y1 / Z1] + : Z0 ? [X0 / Z0, Y0 / Z0] + : [NaN, NaN]; + X0 = Y0 = Z0 = + X1 = Y1 = Z1 = + X2 = Y2 = Z2 = 0; + return centroid; + } +}; + +function centroidPoint(x, y) { + X0 += x; + Y0 += y; + ++Z0; +} + +function centroidLineStart() { + centroidStream.point = centroidPointFirstLine; +} + +function centroidPointFirstLine(x, y) { + centroidStream.point = centroidPointLine; + centroidPoint(x0 = x, y0 = y); +} + +function centroidPointLine(x, y) { + var dx = x - x0, dy = y - y0, z = sqrt(dx * dx + dy * dy); + X1 += z * (x0 + x) / 2; + Y1 += z * (y0 + y) / 2; + Z1 += z; + centroidPoint(x0 = x, y0 = y); +} + +function centroidLineEnd() { + centroidStream.point = centroidPoint; +} + +function centroidRingStart() { + centroidStream.point = centroidPointFirstRing; +} + +function centroidRingEnd() { + centroidPointRing(x00, y00); +} + +function centroidPointFirstRing(x, y) { + centroidStream.point = centroidPointRing; + centroidPoint(x00 = x0 = x, y00 = y0 = y); +} + +function centroidPointRing(x, y) { + var dx = x - x0, + dy = y - y0, + z = sqrt(dx * dx + dy * dy); + + X1 += z * (x0 + x) / 2; + Y1 += z * (y0 + y) / 2; + Z1 += z; + + z = y0 * x - x0 * y; + X2 += z * (x0 + x); + Y2 += z * (y0 + y); + Z2 += z * 3; + centroidPoint(x0 = x, y0 = y); +} + +export default centroidStream; diff --git a/frontend/node_modules/d3-geo/src/path/context.js b/frontend/node_modules/d3-geo/src/path/context.js new file mode 100644 index 0000000..5137fc9 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/path/context.js @@ -0,0 +1,45 @@ +import {tau} from "../math.js"; +import noop from "../noop.js"; + +export default function PathContext(context) { + this._context = context; +} + +PathContext.prototype = { + _radius: 4.5, + pointRadius: function(_) { + return this._radius = _, this; + }, + polygonStart: function() { + this._line = 0; + }, + polygonEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._point = 0; + }, + lineEnd: function() { + if (this._line === 0) this._context.closePath(); + this._point = NaN; + }, + point: function(x, y) { + switch (this._point) { + case 0: { + this._context.moveTo(x, y); + this._point = 1; + break; + } + case 1: { + this._context.lineTo(x, y); + break; + } + default: { + this._context.moveTo(x + this._radius, y); + this._context.arc(x, y, this._radius, 0, tau); + break; + } + } + }, + result: noop +}; diff --git a/frontend/node_modules/d3-geo/src/path/index.js b/frontend/node_modules/d3-geo/src/path/index.js new file mode 100644 index 0000000..e8292bc --- /dev/null +++ b/frontend/node_modules/d3-geo/src/path/index.js @@ -0,0 +1,76 @@ +import identity from "../identity.js"; +import stream from "../stream.js"; +import pathArea from "./area.js"; +import pathBounds from "./bounds.js"; +import pathCentroid from "./centroid.js"; +import PathContext from "./context.js"; +import pathMeasure from "./measure.js"; +import PathString from "./string.js"; + +export default function(projection, context) { + let digits = 3, + pointRadius = 4.5, + projectionStream, + contextStream; + + function path(object) { + if (object) { + if (typeof pointRadius === "function") contextStream.pointRadius(+pointRadius.apply(this, arguments)); + stream(object, projectionStream(contextStream)); + } + return contextStream.result(); + } + + path.area = function(object) { + stream(object, projectionStream(pathArea)); + return pathArea.result(); + }; + + path.measure = function(object) { + stream(object, projectionStream(pathMeasure)); + return pathMeasure.result(); + }; + + path.bounds = function(object) { + stream(object, projectionStream(pathBounds)); + return pathBounds.result(); + }; + + path.centroid = function(object) { + stream(object, projectionStream(pathCentroid)); + return pathCentroid.result(); + }; + + path.projection = function(_) { + if (!arguments.length) return projection; + projectionStream = _ == null ? (projection = null, identity) : (projection = _).stream; + return path; + }; + + path.context = function(_) { + if (!arguments.length) return context; + contextStream = _ == null ? (context = null, new PathString(digits)) : new PathContext(context = _); + if (typeof pointRadius !== "function") contextStream.pointRadius(pointRadius); + return path; + }; + + path.pointRadius = function(_) { + if (!arguments.length) return pointRadius; + pointRadius = typeof _ === "function" ? _ : (contextStream.pointRadius(+_), +_); + return path; + }; + + path.digits = function(_) { + if (!arguments.length) return digits; + if (_ == null) digits = null; + else { + const d = Math.floor(_); + if (!(d >= 0)) throw new RangeError(`invalid digits: ${_}`); + digits = d; + } + if (context === null) contextStream = new PathString(digits); + return path; + }; + + return path.projection(projection).digits(digits).context(context); +} diff --git a/frontend/node_modules/d3-geo/src/path/measure.js b/frontend/node_modules/d3-geo/src/path/measure.js new file mode 100644 index 0000000..ad4177a --- /dev/null +++ b/frontend/node_modules/d3-geo/src/path/measure.js @@ -0,0 +1,45 @@ +import {Adder} from "d3-array"; +import {sqrt} from "../math.js"; +import noop from "../noop.js"; + +var lengthSum = new Adder(), + lengthRing, + x00, + y00, + x0, + y0; + +var lengthStream = { + point: noop, + lineStart: function() { + lengthStream.point = lengthPointFirst; + }, + lineEnd: function() { + if (lengthRing) lengthPoint(x00, y00); + lengthStream.point = noop; + }, + polygonStart: function() { + lengthRing = true; + }, + polygonEnd: function() { + lengthRing = null; + }, + result: function() { + var length = +lengthSum; + lengthSum = new Adder(); + return length; + } +}; + +function lengthPointFirst(x, y) { + lengthStream.point = lengthPoint; + x00 = x0 = x, y00 = y0 = y; +} + +function lengthPoint(x, y) { + x0 -= x, y0 -= y; + lengthSum.add(sqrt(x0 * x0 + y0 * y0)); + x0 = x, y0 = y; +} + +export default lengthStream; diff --git a/frontend/node_modules/d3-geo/src/path/string.js b/frontend/node_modules/d3-geo/src/path/string.js new file mode 100644 index 0000000..d9efbfc --- /dev/null +++ b/frontend/node_modules/d3-geo/src/path/string.js @@ -0,0 +1,86 @@ +// Simple caching for constant-radius points. +let cacheDigits, cacheAppend, cacheRadius, cacheCircle; + +export default class PathString { + constructor(digits) { + this._append = digits == null ? append : appendRound(digits); + this._radius = 4.5; + this._ = ""; + } + pointRadius(_) { + this._radius = +_; + return this; + } + polygonStart() { + this._line = 0; + } + polygonEnd() { + this._line = NaN; + } + lineStart() { + this._point = 0; + } + lineEnd() { + if (this._line === 0) this._ += "Z"; + this._point = NaN; + } + point(x, y) { + switch (this._point) { + case 0: { + this._append`M${x},${y}`; + this._point = 1; + break; + } + case 1: { + this._append`L${x},${y}`; + break; + } + default: { + this._append`M${x},${y}`; + if (this._radius !== cacheRadius || this._append !== cacheAppend) { + const r = this._radius; + const s = this._; + this._ = ""; // stash the old string so we can cache the circle path fragment + this._append`m0,${r}a${r},${r} 0 1,1 0,${-2 * r}a${r},${r} 0 1,1 0,${2 * r}z`; + cacheRadius = r; + cacheAppend = this._append; + cacheCircle = this._; + this._ = s; + } + this._ += cacheCircle; + break; + } + } + } + result() { + const result = this._; + this._ = ""; + return result.length ? result : null; + } +} + +function append(strings) { + let i = 1; + this._ += strings[0]; + for (const j = strings.length; i < j; ++i) { + this._ += arguments[i] + strings[i]; + } +} + +function appendRound(digits) { + const d = Math.floor(digits); + if (!(d >= 0)) throw new RangeError(`invalid digits: ${digits}`); + if (d > 15) return append; + if (d !== cacheDigits) { + const k = 10 ** d; + cacheDigits = d; + cacheAppend = function append(strings) { + let i = 1; + this._ += strings[0]; + for (const j = strings.length; i < j; ++i) { + this._ += Math.round(arguments[i] * k) / k + strings[i]; + } + }; + } + return cacheAppend; +} diff --git a/frontend/node_modules/d3-geo/src/pointEqual.js b/frontend/node_modules/d3-geo/src/pointEqual.js new file mode 100644 index 0000000..d25aa11 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/pointEqual.js @@ -0,0 +1,5 @@ +import {abs, epsilon} from "./math.js"; + +export default function(a, b) { + return abs(a[0] - b[0]) < epsilon && abs(a[1] - b[1]) < epsilon; +} diff --git a/frontend/node_modules/d3-geo/src/polygonContains.js b/frontend/node_modules/d3-geo/src/polygonContains.js new file mode 100644 index 0000000..59baee7 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/polygonContains.js @@ -0,0 +1,74 @@ +import {Adder} from "d3-array"; +import {cartesian, cartesianCross, cartesianNormalizeInPlace} from "./cartesian.js"; +import {abs, asin, atan2, cos, epsilon, epsilon2, halfPi, pi, quarterPi, sign, sin, tau} from "./math.js"; + +function longitude(point) { + return abs(point[0]) <= pi ? point[0] : sign(point[0]) * ((abs(point[0]) + pi) % tau - pi); +} + +export default function(polygon, point) { + var lambda = longitude(point), + phi = point[1], + sinPhi = sin(phi), + normal = [sin(lambda), -cos(lambda), 0], + angle = 0, + winding = 0; + + var sum = new Adder(); + + if (sinPhi === 1) phi = halfPi + epsilon; + else if (sinPhi === -1) phi = -halfPi - epsilon; + + for (var i = 0, n = polygon.length; i < n; ++i) { + if (!(m = (ring = polygon[i]).length)) continue; + var ring, + m, + point0 = ring[m - 1], + lambda0 = longitude(point0), + phi0 = point0[1] / 2 + quarterPi, + sinPhi0 = sin(phi0), + cosPhi0 = cos(phi0); + + for (var j = 0; j < m; ++j, lambda0 = lambda1, sinPhi0 = sinPhi1, cosPhi0 = cosPhi1, point0 = point1) { + var point1 = ring[j], + lambda1 = longitude(point1), + phi1 = point1[1] / 2 + quarterPi, + sinPhi1 = sin(phi1), + cosPhi1 = cos(phi1), + delta = lambda1 - lambda0, + sign = delta >= 0 ? 1 : -1, + absDelta = sign * delta, + antimeridian = absDelta > pi, + k = sinPhi0 * sinPhi1; + + sum.add(atan2(k * sign * sin(absDelta), cosPhi0 * cosPhi1 + k * cos(absDelta))); + angle += antimeridian ? delta + sign * tau : delta; + + // Are the longitudes either side of the point’s meridian (lambda), + // and are the latitudes smaller than the parallel (phi)? + if (antimeridian ^ lambda0 >= lambda ^ lambda1 >= lambda) { + var arc = cartesianCross(cartesian(point0), cartesian(point1)); + cartesianNormalizeInPlace(arc); + var intersection = cartesianCross(normal, arc); + cartesianNormalizeInPlace(intersection); + var phiArc = (antimeridian ^ delta >= 0 ? -1 : 1) * asin(intersection[2]); + if (phi > phiArc || phi === phiArc && (arc[0] || arc[1])) { + winding += antimeridian ^ delta >= 0 ? 1 : -1; + } + } + } + } + + // First, determine whether the South pole is inside or outside: + // + // It is inside if: + // * the polygon winds around it in a clockwise direction. + // * the polygon does not (cumulatively) wind around it, but has a negative + // (counter-clockwise) area. + // + // Second, count the (signed) number of times a segment crosses a lambda + // from the point to the South pole. If it is zero, then the point is the + // same side as the South pole. + + return (angle < -epsilon || angle < epsilon && sum < -epsilon2) ^ (winding & 1); +} diff --git a/frontend/node_modules/d3-geo/src/projection/albers.js b/frontend/node_modules/d3-geo/src/projection/albers.js new file mode 100644 index 0000000..180425d --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/albers.js @@ -0,0 +1,10 @@ +import conicEqualArea from "./conicEqualArea.js"; + +export default function() { + return conicEqualArea() + .parallels([29.5, 45.5]) + .scale(1070) + .translate([480, 250]) + .rotate([96, 0]) + .center([-0.6, 38.7]); +} diff --git a/frontend/node_modules/d3-geo/src/projection/albersUsa.js b/frontend/node_modules/d3-geo/src/projection/albersUsa.js new file mode 100644 index 0000000..fd295ed --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/albersUsa.js @@ -0,0 +1,111 @@ +import {epsilon} from "../math.js"; +import albers from "./albers.js"; +import conicEqualArea from "./conicEqualArea.js"; +import {fitExtent, fitSize, fitWidth, fitHeight} from "./fit.js"; + +// The projections must have mutually exclusive clip regions on the sphere, +// as this will avoid emitting interleaving lines and polygons. +function multiplex(streams) { + var n = streams.length; + return { + point: function(x, y) { var i = -1; while (++i < n) streams[i].point(x, y); }, + sphere: function() { var i = -1; while (++i < n) streams[i].sphere(); }, + lineStart: function() { var i = -1; while (++i < n) streams[i].lineStart(); }, + lineEnd: function() { var i = -1; while (++i < n) streams[i].lineEnd(); }, + polygonStart: function() { var i = -1; while (++i < n) streams[i].polygonStart(); }, + polygonEnd: function() { var i = -1; while (++i < n) streams[i].polygonEnd(); } + }; +} + +// A composite projection for the United States, configured by default for +// 960×500. The projection also works quite well at 960×600 if you change the +// scale to 1285 and adjust the translate accordingly. The set of standard +// parallels for each region comes from USGS, which is published here: +// http://egsc.usgs.gov/isb/pubs/MapProjections/projections.html#albers +export default function() { + var cache, + cacheStream, + lower48 = albers(), lower48Point, + alaska = conicEqualArea().rotate([154, 0]).center([-2, 58.5]).parallels([55, 65]), alaskaPoint, // EPSG:3338 + hawaii = conicEqualArea().rotate([157, 0]).center([-3, 19.9]).parallels([8, 18]), hawaiiPoint, // ESRI:102007 + point, pointStream = {point: function(x, y) { point = [x, y]; }}; + + function albersUsa(coordinates) { + var x = coordinates[0], y = coordinates[1]; + return point = null, + (lower48Point.point(x, y), point) + || (alaskaPoint.point(x, y), point) + || (hawaiiPoint.point(x, y), point); + } + + albersUsa.invert = function(coordinates) { + var k = lower48.scale(), + t = lower48.translate(), + x = (coordinates[0] - t[0]) / k, + y = (coordinates[1] - t[1]) / k; + return (y >= 0.120 && y < 0.234 && x >= -0.425 && x < -0.214 ? alaska + : y >= 0.166 && y < 0.234 && x >= -0.214 && x < -0.115 ? hawaii + : lower48).invert(coordinates); + }; + + albersUsa.stream = function(stream) { + return cache && cacheStream === stream ? cache : cache = multiplex([lower48.stream(cacheStream = stream), alaska.stream(stream), hawaii.stream(stream)]); + }; + + albersUsa.precision = function(_) { + if (!arguments.length) return lower48.precision(); + lower48.precision(_), alaska.precision(_), hawaii.precision(_); + return reset(); + }; + + albersUsa.scale = function(_) { + if (!arguments.length) return lower48.scale(); + lower48.scale(_), alaska.scale(_ * 0.35), hawaii.scale(_); + return albersUsa.translate(lower48.translate()); + }; + + albersUsa.translate = function(_) { + if (!arguments.length) return lower48.translate(); + var k = lower48.scale(), x = +_[0], y = +_[1]; + + lower48Point = lower48 + .translate(_) + .clipExtent([[x - 0.455 * k, y - 0.238 * k], [x + 0.455 * k, y + 0.238 * k]]) + .stream(pointStream); + + alaskaPoint = alaska + .translate([x - 0.307 * k, y + 0.201 * k]) + .clipExtent([[x - 0.425 * k + epsilon, y + 0.120 * k + epsilon], [x - 0.214 * k - epsilon, y + 0.234 * k - epsilon]]) + .stream(pointStream); + + hawaiiPoint = hawaii + .translate([x - 0.205 * k, y + 0.212 * k]) + .clipExtent([[x - 0.214 * k + epsilon, y + 0.166 * k + epsilon], [x - 0.115 * k - epsilon, y + 0.234 * k - epsilon]]) + .stream(pointStream); + + return reset(); + }; + + albersUsa.fitExtent = function(extent, object) { + return fitExtent(albersUsa, extent, object); + }; + + albersUsa.fitSize = function(size, object) { + return fitSize(albersUsa, size, object); + }; + + albersUsa.fitWidth = function(width, object) { + return fitWidth(albersUsa, width, object); + }; + + albersUsa.fitHeight = function(height, object) { + return fitHeight(albersUsa, height, object); + }; + + function reset() { + cache = cacheStream = null; + return albersUsa; + } + + return albersUsa.scale(1070); +} diff --git a/frontend/node_modules/d3-geo/src/projection/azimuthal.js b/frontend/node_modules/d3-geo/src/projection/azimuthal.js new file mode 100644 index 0000000..22dffe7 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/azimuthal.js @@ -0,0 +1,27 @@ +import {asin, atan2, cos, sin, sqrt} from "../math.js"; + +export function azimuthalRaw(scale) { + return function(x, y) { + var cx = cos(x), + cy = cos(y), + k = scale(cx * cy); + if (k === Infinity) return [2, 0]; + return [ + k * cy * sin(x), + k * sin(y) + ]; + } +} + +export function azimuthalInvert(angle) { + return function(x, y) { + var z = sqrt(x * x + y * y), + c = angle(z), + sc = sin(c), + cc = cos(c); + return [ + atan2(x * sc, z * cc), + asin(z && y * sc / z) + ]; + } +} diff --git a/frontend/node_modules/d3-geo/src/projection/azimuthalEqualArea.js b/frontend/node_modules/d3-geo/src/projection/azimuthalEqualArea.js new file mode 100644 index 0000000..795d4c7 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/azimuthalEqualArea.js @@ -0,0 +1,17 @@ +import {asin, sqrt} from "../math.js"; +import {azimuthalRaw, azimuthalInvert} from "./azimuthal.js"; +import projection from "./index.js"; + +export var azimuthalEqualAreaRaw = azimuthalRaw(function(cxcy) { + return sqrt(2 / (1 + cxcy)); +}); + +azimuthalEqualAreaRaw.invert = azimuthalInvert(function(z) { + return 2 * asin(z / 2); +}); + +export default function() { + return projection(azimuthalEqualAreaRaw) + .scale(124.75) + .clipAngle(180 - 1e-3); +} diff --git a/frontend/node_modules/d3-geo/src/projection/azimuthalEquidistant.js b/frontend/node_modules/d3-geo/src/projection/azimuthalEquidistant.js new file mode 100644 index 0000000..9b89eb9 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/azimuthalEquidistant.js @@ -0,0 +1,17 @@ +import {acos, sin} from "../math.js"; +import {azimuthalRaw, azimuthalInvert} from "./azimuthal.js"; +import projection from "./index.js"; + +export var azimuthalEquidistantRaw = azimuthalRaw(function(c) { + return (c = acos(c)) && c / sin(c); +}); + +azimuthalEquidistantRaw.invert = azimuthalInvert(function(z) { + return z; +}); + +export default function() { + return projection(azimuthalEquidistantRaw) + .scale(79.4188) + .clipAngle(180 - 1e-3); +} diff --git a/frontend/node_modules/d3-geo/src/projection/conic.js b/frontend/node_modules/d3-geo/src/projection/conic.js new file mode 100644 index 0000000..81c5744 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/conic.js @@ -0,0 +1,15 @@ +import {degrees, pi, radians} from "../math.js"; +import {projectionMutator} from "./index.js"; + +export function conicProjection(projectAt) { + var phi0 = 0, + phi1 = pi / 3, + m = projectionMutator(projectAt), + p = m(phi0, phi1); + + p.parallels = function(_) { + return arguments.length ? m(phi0 = _[0] * radians, phi1 = _[1] * radians) : [phi0 * degrees, phi1 * degrees]; + }; + + return p; +} diff --git a/frontend/node_modules/d3-geo/src/projection/conicConformal.js b/frontend/node_modules/d3-geo/src/projection/conicConformal.js new file mode 100644 index 0000000..adf73da --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/conicConformal.js @@ -0,0 +1,38 @@ +import {abs, atan, atan2, cos, epsilon, halfPi, log, pi, pow, sign, sin, sqrt, tan} from "../math.js"; +import {conicProjection} from "./conic.js"; +import {mercatorRaw} from "./mercator.js"; + +function tany(y) { + return tan((halfPi + y) / 2); +} + +export function conicConformalRaw(y0, y1) { + var cy0 = cos(y0), + n = y0 === y1 ? sin(y0) : log(cy0 / cos(y1)) / log(tany(y1) / tany(y0)), + f = cy0 * pow(tany(y0), n) / n; + + if (!n) return mercatorRaw; + + function project(x, y) { + if (f > 0) { if (y < -halfPi + epsilon) y = -halfPi + epsilon; } + else { if (y > halfPi - epsilon) y = halfPi - epsilon; } + var r = f / pow(tany(y), n); + return [r * sin(n * x), f - r * cos(n * x)]; + } + + project.invert = function(x, y) { + var fy = f - y, r = sign(n) * sqrt(x * x + fy * fy), + l = atan2(x, abs(fy)) * sign(fy); + if (fy * n < 0) + l -= pi * sign(x) * sign(fy); + return [l / n, 2 * atan(pow(f / r, 1 / n)) - halfPi]; + }; + + return project; +} + +export default function() { + return conicProjection(conicConformalRaw) + .scale(109.5) + .parallels([30, 30]); +} diff --git a/frontend/node_modules/d3-geo/src/projection/conicEqualArea.js b/frontend/node_modules/d3-geo/src/projection/conicEqualArea.js new file mode 100644 index 0000000..b4238e4 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/conicEqualArea.js @@ -0,0 +1,33 @@ +import {abs, asin, atan2, cos, epsilon, pi, sign, sin, sqrt} from "../math.js"; +import {conicProjection} from "./conic.js"; +import {cylindricalEqualAreaRaw} from "./cylindricalEqualArea.js"; + +export function conicEqualAreaRaw(y0, y1) { + var sy0 = sin(y0), n = (sy0 + sin(y1)) / 2; + + // Are the parallels symmetrical around the Equator? + if (abs(n) < epsilon) return cylindricalEqualAreaRaw(y0); + + var c = 1 + sy0 * (2 * n - sy0), r0 = sqrt(c) / n; + + function project(x, y) { + var r = sqrt(c - 2 * n * sin(y)) / n; + return [r * sin(x *= n), r0 - r * cos(x)]; + } + + project.invert = function(x, y) { + var r0y = r0 - y, + l = atan2(x, abs(r0y)) * sign(r0y); + if (r0y * n < 0) + l -= pi * sign(x) * sign(r0y); + return [l / n, asin((c - (x * x + r0y * r0y) * n * n) / (2 * n))]; + }; + + return project; +} + +export default function() { + return conicProjection(conicEqualAreaRaw) + .scale(155.424) + .center([0, 33.6442]); +} diff --git a/frontend/node_modules/d3-geo/src/projection/conicEquidistant.js b/frontend/node_modules/d3-geo/src/projection/conicEquidistant.js new file mode 100644 index 0000000..796710e --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/conicEquidistant.js @@ -0,0 +1,32 @@ +import {abs, atan2, cos, epsilon, pi, sign, sin, sqrt} from "../math.js"; +import {conicProjection} from "./conic.js"; +import {equirectangularRaw} from "./equirectangular.js"; + +export function conicEquidistantRaw(y0, y1) { + var cy0 = cos(y0), + n = y0 === y1 ? sin(y0) : (cy0 - cos(y1)) / (y1 - y0), + g = cy0 / n + y0; + + if (abs(n) < epsilon) return equirectangularRaw; + + function project(x, y) { + var gy = g - y, nx = n * x; + return [gy * sin(nx), g - gy * cos(nx)]; + } + + project.invert = function(x, y) { + var gy = g - y, + l = atan2(x, abs(gy)) * sign(gy); + if (gy * n < 0) + l -= pi * sign(x) * sign(gy); + return [l / n, g - sign(n) * sqrt(x * x + gy * gy)]; + }; + + return project; +} + +export default function() { + return conicProjection(conicEquidistantRaw) + .scale(131.154) + .center([0, 13.9389]); +} diff --git a/frontend/node_modules/d3-geo/src/projection/cylindricalEqualArea.js b/frontend/node_modules/d3-geo/src/projection/cylindricalEqualArea.js new file mode 100644 index 0000000..1d38b40 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/cylindricalEqualArea.js @@ -0,0 +1,15 @@ +import {asin, cos, sin} from "../math.js"; + +export function cylindricalEqualAreaRaw(phi0) { + var cosPhi0 = cos(phi0); + + function forward(lambda, phi) { + return [lambda * cosPhi0, sin(phi) / cosPhi0]; + } + + forward.invert = function(x, y) { + return [x / cosPhi0, asin(y * cosPhi0)]; + }; + + return forward; +} diff --git a/frontend/node_modules/d3-geo/src/projection/equalEarth.js b/frontend/node_modules/d3-geo/src/projection/equalEarth.js new file mode 100644 index 0000000..dc5ce2c --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/equalEarth.js @@ -0,0 +1,36 @@ +import projection from "./index.js"; +import {abs, asin, cos, epsilon2, sin, sqrt} from "../math.js"; + +var A1 = 1.340264, + A2 = -0.081106, + A3 = 0.000893, + A4 = 0.003796, + M = sqrt(3) / 2, + iterations = 12; + +export function equalEarthRaw(lambda, phi) { + var l = asin(M * sin(phi)), l2 = l * l, l6 = l2 * l2 * l2; + return [ + lambda * cos(l) / (M * (A1 + 3 * A2 * l2 + l6 * (7 * A3 + 9 * A4 * l2))), + l * (A1 + A2 * l2 + l6 * (A3 + A4 * l2)) + ]; +} + +equalEarthRaw.invert = function(x, y) { + var l = y, l2 = l * l, l6 = l2 * l2 * l2; + for (var i = 0, delta, fy, fpy; i < iterations; ++i) { + fy = l * (A1 + A2 * l2 + l6 * (A3 + A4 * l2)) - y; + fpy = A1 + 3 * A2 * l2 + l6 * (7 * A3 + 9 * A4 * l2); + l -= delta = fy / fpy, l2 = l * l, l6 = l2 * l2 * l2; + if (abs(delta) < epsilon2) break; + } + return [ + M * x * (A1 + 3 * A2 * l2 + l6 * (7 * A3 + 9 * A4 * l2)) / cos(l), + asin(sin(l) / M) + ]; +}; + +export default function() { + return projection(equalEarthRaw) + .scale(177.158); +} diff --git a/frontend/node_modules/d3-geo/src/projection/equirectangular.js b/frontend/node_modules/d3-geo/src/projection/equirectangular.js new file mode 100644 index 0000000..d47065c --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/equirectangular.js @@ -0,0 +1,12 @@ +import projection from "./index.js"; + +export function equirectangularRaw(lambda, phi) { + return [lambda, phi]; +} + +equirectangularRaw.invert = equirectangularRaw; + +export default function() { + return projection(equirectangularRaw) + .scale(152.63); +} diff --git a/frontend/node_modules/d3-geo/src/projection/fit.js b/frontend/node_modules/d3-geo/src/projection/fit.js new file mode 100644 index 0000000..d496d0f --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/fit.js @@ -0,0 +1,47 @@ +import {default as geoStream} from "../stream.js"; +import boundsStream from "../path/bounds.js"; + +function fit(projection, fitBounds, object) { + var clip = projection.clipExtent && projection.clipExtent(); + projection.scale(150).translate([0, 0]); + if (clip != null) projection.clipExtent(null); + geoStream(object, projection.stream(boundsStream)); + fitBounds(boundsStream.result()); + if (clip != null) projection.clipExtent(clip); + return projection; +} + +export function fitExtent(projection, extent, object) { + return fit(projection, function(b) { + var w = extent[1][0] - extent[0][0], + h = extent[1][1] - extent[0][1], + k = Math.min(w / (b[1][0] - b[0][0]), h / (b[1][1] - b[0][1])), + x = +extent[0][0] + (w - k * (b[1][0] + b[0][0])) / 2, + y = +extent[0][1] + (h - k * (b[1][1] + b[0][1])) / 2; + projection.scale(150 * k).translate([x, y]); + }, object); +} + +export function fitSize(projection, size, object) { + return fitExtent(projection, [[0, 0], size], object); +} + +export function fitWidth(projection, width, object) { + return fit(projection, function(b) { + var w = +width, + k = w / (b[1][0] - b[0][0]), + x = (w - k * (b[1][0] + b[0][0])) / 2, + y = -k * b[0][1]; + projection.scale(150 * k).translate([x, y]); + }, object); +} + +export function fitHeight(projection, height, object) { + return fit(projection, function(b) { + var h = +height, + k = h / (b[1][1] - b[0][1]), + x = -k * b[0][0], + y = (h - k * (b[1][1] + b[0][1])) / 2; + projection.scale(150 * k).translate([x, y]); + }, object); +} diff --git a/frontend/node_modules/d3-geo/src/projection/gnomonic.js b/frontend/node_modules/d3-geo/src/projection/gnomonic.js new file mode 100644 index 0000000..5da1cc7 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/gnomonic.js @@ -0,0 +1,16 @@ +import {atan, cos, sin} from "../math.js"; +import {azimuthalInvert} from "./azimuthal.js"; +import projection from "./index.js"; + +export function gnomonicRaw(x, y) { + var cy = cos(y), k = cos(x) * cy; + return [cy * sin(x) / k, sin(y) / k]; +} + +gnomonicRaw.invert = azimuthalInvert(atan); + +export default function() { + return projection(gnomonicRaw) + .scale(144.049) + .clipAngle(60); +} diff --git a/frontend/node_modules/d3-geo/src/projection/identity.js b/frontend/node_modules/d3-geo/src/projection/identity.js new file mode 100644 index 0000000..cc439d8 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/identity.js @@ -0,0 +1,85 @@ +import clipRectangle from "../clip/rectangle.js"; +import identity from "../identity.js"; +import {transformer} from "../transform.js"; +import {fitExtent, fitSize, fitWidth, fitHeight} from "./fit.js"; +import {cos, degrees, radians, sin} from "../math.js"; + +export default function() { + var k = 1, tx = 0, ty = 0, sx = 1, sy = 1, // scale, translate and reflect + alpha = 0, ca, sa, // angle + x0 = null, y0, x1, y1, // clip extent + kx = 1, ky = 1, + transform = transformer({ + point: function(x, y) { + var p = projection([x, y]) + this.stream.point(p[0], p[1]); + } + }), + postclip = identity, + cache, + cacheStream; + + function reset() { + kx = k * sx; + ky = k * sy; + cache = cacheStream = null; + return projection; + } + + function projection (p) { + var x = p[0] * kx, y = p[1] * ky; + if (alpha) { + var t = y * ca - x * sa; + x = x * ca + y * sa; + y = t; + } + return [x + tx, y + ty]; + } + projection.invert = function(p) { + var x = p[0] - tx, y = p[1] - ty; + if (alpha) { + var t = y * ca + x * sa; + x = x * ca - y * sa; + y = t; + } + return [x / kx, y / ky]; + }; + projection.stream = function(stream) { + return cache && cacheStream === stream ? cache : cache = transform(postclip(cacheStream = stream)); + }; + projection.postclip = function(_) { + return arguments.length ? (postclip = _, x0 = y0 = x1 = y1 = null, reset()) : postclip; + }; + projection.clipExtent = function(_) { + return arguments.length ? (postclip = _ == null ? (x0 = y0 = x1 = y1 = null, identity) : clipRectangle(x0 = +_[0][0], y0 = +_[0][1], x1 = +_[1][0], y1 = +_[1][1]), reset()) : x0 == null ? null : [[x0, y0], [x1, y1]]; + }; + projection.scale = function(_) { + return arguments.length ? (k = +_, reset()) : k; + }; + projection.translate = function(_) { + return arguments.length ? (tx = +_[0], ty = +_[1], reset()) : [tx, ty]; + } + projection.angle = function(_) { + return arguments.length ? (alpha = _ % 360 * radians, sa = sin(alpha), ca = cos(alpha), reset()) : alpha * degrees; + }; + projection.reflectX = function(_) { + return arguments.length ? (sx = _ ? -1 : 1, reset()) : sx < 0; + }; + projection.reflectY = function(_) { + return arguments.length ? (sy = _ ? -1 : 1, reset()) : sy < 0; + }; + projection.fitExtent = function(extent, object) { + return fitExtent(projection, extent, object); + }; + projection.fitSize = function(size, object) { + return fitSize(projection, size, object); + }; + projection.fitWidth = function(width, object) { + return fitWidth(projection, width, object); + }; + projection.fitHeight = function(height, object) { + return fitHeight(projection, height, object); + }; + + return projection; +} diff --git a/frontend/node_modules/d3-geo/src/projection/index.js b/frontend/node_modules/d3-geo/src/projection/index.js new file mode 100644 index 0000000..8ea64bc --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/index.js @@ -0,0 +1,177 @@ +import clipAntimeridian from "../clip/antimeridian.js"; +import clipCircle from "../clip/circle.js"; +import clipRectangle from "../clip/rectangle.js"; +import compose from "../compose.js"; +import identity from "../identity.js"; +import {cos, degrees, radians, sin, sqrt} from "../math.js"; +import {rotateRadians} from "../rotation.js"; +import {transformer} from "../transform.js"; +import {fitExtent, fitSize, fitWidth, fitHeight} from "./fit.js"; +import resample from "./resample.js"; + +var transformRadians = transformer({ + point: function(x, y) { + this.stream.point(x * radians, y * radians); + } +}); + +function transformRotate(rotate) { + return transformer({ + point: function(x, y) { + var r = rotate(x, y); + return this.stream.point(r[0], r[1]); + } + }); +} + +function scaleTranslate(k, dx, dy, sx, sy) { + function transform(x, y) { + x *= sx; y *= sy; + return [dx + k * x, dy - k * y]; + } + transform.invert = function(x, y) { + return [(x - dx) / k * sx, (dy - y) / k * sy]; + }; + return transform; +} + +function scaleTranslateRotate(k, dx, dy, sx, sy, alpha) { + if (!alpha) return scaleTranslate(k, dx, dy, sx, sy); + var cosAlpha = cos(alpha), + sinAlpha = sin(alpha), + a = cosAlpha * k, + b = sinAlpha * k, + ai = cosAlpha / k, + bi = sinAlpha / k, + ci = (sinAlpha * dy - cosAlpha * dx) / k, + fi = (sinAlpha * dx + cosAlpha * dy) / k; + function transform(x, y) { + x *= sx; y *= sy; + return [a * x - b * y + dx, dy - b * x - a * y]; + } + transform.invert = function(x, y) { + return [sx * (ai * x - bi * y + ci), sy * (fi - bi * x - ai * y)]; + }; + return transform; +} + +export default function projection(project) { + return projectionMutator(function() { return project; })(); +} + +export function projectionMutator(projectAt) { + var project, + k = 150, // scale + x = 480, y = 250, // translate + lambda = 0, phi = 0, // center + deltaLambda = 0, deltaPhi = 0, deltaGamma = 0, rotate, // pre-rotate + alpha = 0, // post-rotate angle + sx = 1, // reflectX + sy = 1, // reflectX + theta = null, preclip = clipAntimeridian, // pre-clip angle + x0 = null, y0, x1, y1, postclip = identity, // post-clip extent + delta2 = 0.5, // precision + projectResample, + projectTransform, + projectRotateTransform, + cache, + cacheStream; + + function projection(point) { + return projectRotateTransform(point[0] * radians, point[1] * radians); + } + + function invert(point) { + point = projectRotateTransform.invert(point[0], point[1]); + return point && [point[0] * degrees, point[1] * degrees]; + } + + projection.stream = function(stream) { + return cache && cacheStream === stream ? cache : cache = transformRadians(transformRotate(rotate)(preclip(projectResample(postclip(cacheStream = stream))))); + }; + + projection.preclip = function(_) { + return arguments.length ? (preclip = _, theta = undefined, reset()) : preclip; + }; + + projection.postclip = function(_) { + return arguments.length ? (postclip = _, x0 = y0 = x1 = y1 = null, reset()) : postclip; + }; + + projection.clipAngle = function(_) { + return arguments.length ? (preclip = +_ ? clipCircle(theta = _ * radians) : (theta = null, clipAntimeridian), reset()) : theta * degrees; + }; + + projection.clipExtent = function(_) { + return arguments.length ? (postclip = _ == null ? (x0 = y0 = x1 = y1 = null, identity) : clipRectangle(x0 = +_[0][0], y0 = +_[0][1], x1 = +_[1][0], y1 = +_[1][1]), reset()) : x0 == null ? null : [[x0, y0], [x1, y1]]; + }; + + projection.scale = function(_) { + return arguments.length ? (k = +_, recenter()) : k; + }; + + projection.translate = function(_) { + return arguments.length ? (x = +_[0], y = +_[1], recenter()) : [x, y]; + }; + + projection.center = function(_) { + return arguments.length ? (lambda = _[0] % 360 * radians, phi = _[1] % 360 * radians, recenter()) : [lambda * degrees, phi * degrees]; + }; + + projection.rotate = function(_) { + return arguments.length ? (deltaLambda = _[0] % 360 * radians, deltaPhi = _[1] % 360 * radians, deltaGamma = _.length > 2 ? _[2] % 360 * radians : 0, recenter()) : [deltaLambda * degrees, deltaPhi * degrees, deltaGamma * degrees]; + }; + + projection.angle = function(_) { + return arguments.length ? (alpha = _ % 360 * radians, recenter()) : alpha * degrees; + }; + + projection.reflectX = function(_) { + return arguments.length ? (sx = _ ? -1 : 1, recenter()) : sx < 0; + }; + + projection.reflectY = function(_) { + return arguments.length ? (sy = _ ? -1 : 1, recenter()) : sy < 0; + }; + + projection.precision = function(_) { + return arguments.length ? (projectResample = resample(projectTransform, delta2 = _ * _), reset()) : sqrt(delta2); + }; + + projection.fitExtent = function(extent, object) { + return fitExtent(projection, extent, object); + }; + + projection.fitSize = function(size, object) { + return fitSize(projection, size, object); + }; + + projection.fitWidth = function(width, object) { + return fitWidth(projection, width, object); + }; + + projection.fitHeight = function(height, object) { + return fitHeight(projection, height, object); + }; + + function recenter() { + var center = scaleTranslateRotate(k, 0, 0, sx, sy, alpha).apply(null, project(lambda, phi)), + transform = scaleTranslateRotate(k, x - center[0], y - center[1], sx, sy, alpha); + rotate = rotateRadians(deltaLambda, deltaPhi, deltaGamma); + projectTransform = compose(project, transform); + projectRotateTransform = compose(rotate, projectTransform); + projectResample = resample(projectTransform, delta2); + return reset(); + } + + function reset() { + cache = cacheStream = null; + return projection; + } + + return function() { + project = projectAt.apply(this, arguments); + projection.invert = project.invert && invert; + return recenter(); + }; +} diff --git a/frontend/node_modules/d3-geo/src/projection/mercator.js b/frontend/node_modules/d3-geo/src/projection/mercator.js new file mode 100644 index 0000000..be975a9 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/mercator.js @@ -0,0 +1,52 @@ +import {atan, exp, halfPi, log, pi, tan, tau} from "../math.js"; +import rotation from "../rotation.js"; +import projection from "./index.js"; + +export function mercatorRaw(lambda, phi) { + return [lambda, log(tan((halfPi + phi) / 2))]; +} + +mercatorRaw.invert = function(x, y) { + return [x, 2 * atan(exp(y)) - halfPi]; +}; + +export default function() { + return mercatorProjection(mercatorRaw) + .scale(961 / tau); +} + +export function mercatorProjection(project) { + var m = projection(project), + center = m.center, + scale = m.scale, + translate = m.translate, + clipExtent = m.clipExtent, + x0 = null, y0, x1, y1; // clip extent + + m.scale = function(_) { + return arguments.length ? (scale(_), reclip()) : scale(); + }; + + m.translate = function(_) { + return arguments.length ? (translate(_), reclip()) : translate(); + }; + + m.center = function(_) { + return arguments.length ? (center(_), reclip()) : center(); + }; + + m.clipExtent = function(_) { + return arguments.length ? ((_ == null ? x0 = y0 = x1 = y1 = null : (x0 = +_[0][0], y0 = +_[0][1], x1 = +_[1][0], y1 = +_[1][1])), reclip()) : x0 == null ? null : [[x0, y0], [x1, y1]]; + }; + + function reclip() { + var k = pi * scale(), + t = m(rotation(m.rotate()).invert([0, 0])); + return clipExtent(x0 == null + ? [[t[0] - k, t[1] - k], [t[0] + k, t[1] + k]] : project === mercatorRaw + ? [[Math.max(t[0] - k, x0), y0], [Math.min(t[0] + k, x1), y1]] + : [[x0, Math.max(t[1] - k, y0)], [x1, Math.min(t[1] + k, y1)]]); + } + + return reclip(); +} diff --git a/frontend/node_modules/d3-geo/src/projection/naturalEarth1.js b/frontend/node_modules/d3-geo/src/projection/naturalEarth1.js new file mode 100644 index 0000000..fe5ed31 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/naturalEarth1.js @@ -0,0 +1,28 @@ +import projection from "./index.js"; +import {abs, epsilon} from "../math.js"; + +export function naturalEarth1Raw(lambda, phi) { + var phi2 = phi * phi, phi4 = phi2 * phi2; + return [ + lambda * (0.8707 - 0.131979 * phi2 + phi4 * (-0.013791 + phi4 * (0.003971 * phi2 - 0.001529 * phi4))), + phi * (1.007226 + phi2 * (0.015085 + phi4 * (-0.044475 + 0.028874 * phi2 - 0.005916 * phi4))) + ]; +} + +naturalEarth1Raw.invert = function(x, y) { + var phi = y, i = 25, delta; + do { + var phi2 = phi * phi, phi4 = phi2 * phi2; + phi -= delta = (phi * (1.007226 + phi2 * (0.015085 + phi4 * (-0.044475 + 0.028874 * phi2 - 0.005916 * phi4))) - y) / + (1.007226 + phi2 * (0.015085 * 3 + phi4 * (-0.044475 * 7 + 0.028874 * 9 * phi2 - 0.005916 * 11 * phi4))); + } while (abs(delta) > epsilon && --i > 0); + return [ + x / (0.8707 + (phi2 = phi * phi) * (-0.131979 + phi2 * (-0.013791 + phi2 * phi2 * phi2 * (0.003971 - 0.001529 * phi2)))), + phi + ]; +}; + +export default function() { + return projection(naturalEarth1Raw) + .scale(175.295); +} diff --git a/frontend/node_modules/d3-geo/src/projection/orthographic.js b/frontend/node_modules/d3-geo/src/projection/orthographic.js new file mode 100644 index 0000000..b5a8351 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/orthographic.js @@ -0,0 +1,15 @@ +import {asin, cos, epsilon, sin} from "../math.js"; +import {azimuthalInvert} from "./azimuthal.js"; +import projection from "./index.js"; + +export function orthographicRaw(x, y) { + return [cos(y) * sin(x), sin(y)]; +} + +orthographicRaw.invert = azimuthalInvert(asin); + +export default function() { + return projection(orthographicRaw) + .scale(249.5) + .clipAngle(90 + epsilon); +} diff --git a/frontend/node_modules/d3-geo/src/projection/resample.js b/frontend/node_modules/d3-geo/src/projection/resample.js new file mode 100644 index 0000000..268fc44 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/resample.js @@ -0,0 +1,102 @@ +import {cartesian} from "../cartesian.js"; +import {abs, asin, atan2, cos, epsilon, radians, sqrt} from "../math.js"; +import {transformer} from "../transform.js"; + +var maxDepth = 16, // maximum depth of subdivision + cosMinDistance = cos(30 * radians); // cos(minimum angular distance) + +export default function(project, delta2) { + return +delta2 ? resample(project, delta2) : resampleNone(project); +} + +function resampleNone(project) { + return transformer({ + point: function(x, y) { + x = project(x, y); + this.stream.point(x[0], x[1]); + } + }); +} + +function resample(project, delta2) { + + function resampleLineTo(x0, y0, lambda0, a0, b0, c0, x1, y1, lambda1, a1, b1, c1, depth, stream) { + var dx = x1 - x0, + dy = y1 - y0, + d2 = dx * dx + dy * dy; + if (d2 > 4 * delta2 && depth--) { + var a = a0 + a1, + b = b0 + b1, + c = c0 + c1, + m = sqrt(a * a + b * b + c * c), + phi2 = asin(c /= m), + lambda2 = abs(abs(c) - 1) < epsilon || abs(lambda0 - lambda1) < epsilon ? (lambda0 + lambda1) / 2 : atan2(b, a), + p = project(lambda2, phi2), + x2 = p[0], + y2 = p[1], + dx2 = x2 - x0, + dy2 = y2 - y0, + dz = dy * dx2 - dx * dy2; + if (dz * dz / d2 > delta2 // perpendicular projected distance + || abs((dx * dx2 + dy * dy2) / d2 - 0.5) > 0.3 // midpoint close to an end + || a0 * a1 + b0 * b1 + c0 * c1 < cosMinDistance) { // angular distance + resampleLineTo(x0, y0, lambda0, a0, b0, c0, x2, y2, lambda2, a /= m, b /= m, c, depth, stream); + stream.point(x2, y2); + resampleLineTo(x2, y2, lambda2, a, b, c, x1, y1, lambda1, a1, b1, c1, depth, stream); + } + } + } + return function(stream) { + var lambda00, x00, y00, a00, b00, c00, // first point + lambda0, x0, y0, a0, b0, c0; // previous point + + var resampleStream = { + point: point, + lineStart: lineStart, + lineEnd: lineEnd, + polygonStart: function() { stream.polygonStart(); resampleStream.lineStart = ringStart; }, + polygonEnd: function() { stream.polygonEnd(); resampleStream.lineStart = lineStart; } + }; + + function point(x, y) { + x = project(x, y); + stream.point(x[0], x[1]); + } + + function lineStart() { + x0 = NaN; + resampleStream.point = linePoint; + stream.lineStart(); + } + + function linePoint(lambda, phi) { + var c = cartesian([lambda, phi]), p = project(lambda, phi); + resampleLineTo(x0, y0, lambda0, a0, b0, c0, x0 = p[0], y0 = p[1], lambda0 = lambda, a0 = c[0], b0 = c[1], c0 = c[2], maxDepth, stream); + stream.point(x0, y0); + } + + function lineEnd() { + resampleStream.point = point; + stream.lineEnd(); + } + + function ringStart() { + lineStart(); + resampleStream.point = ringPoint; + resampleStream.lineEnd = ringEnd; + } + + function ringPoint(lambda, phi) { + linePoint(lambda00 = lambda, phi), x00 = x0, y00 = y0, a00 = a0, b00 = b0, c00 = c0; + resampleStream.point = linePoint; + } + + function ringEnd() { + resampleLineTo(x0, y0, lambda0, a0, b0, c0, x00, y00, lambda00, a00, b00, c00, maxDepth, stream); + resampleStream.lineEnd = lineEnd; + lineEnd(); + } + + return resampleStream; + }; +} diff --git a/frontend/node_modules/d3-geo/src/projection/stereographic.js b/frontend/node_modules/d3-geo/src/projection/stereographic.js new file mode 100644 index 0000000..5f9694a --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/stereographic.js @@ -0,0 +1,18 @@ +import {atan, cos, sin} from "../math.js"; +import {azimuthalInvert} from "./azimuthal.js"; +import projection from "./index.js"; + +export function stereographicRaw(x, y) { + var cy = cos(y), k = 1 + cos(x) * cy; + return [cy * sin(x) / k, sin(y) / k]; +} + +stereographicRaw.invert = azimuthalInvert(function(z) { + return 2 * atan(z); +}); + +export default function() { + return projection(stereographicRaw) + .scale(250) + .clipAngle(142); +} diff --git a/frontend/node_modules/d3-geo/src/projection/transverseMercator.js b/frontend/node_modules/d3-geo/src/projection/transverseMercator.js new file mode 100644 index 0000000..bedd1c3 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/projection/transverseMercator.js @@ -0,0 +1,27 @@ +import {atan, exp, halfPi, log, tan} from "../math.js"; +import {mercatorProjection} from "./mercator.js"; + +export function transverseMercatorRaw(lambda, phi) { + return [log(tan((halfPi + phi) / 2)), -lambda]; +} + +transverseMercatorRaw.invert = function(x, y) { + return [-y, 2 * atan(exp(x)) - halfPi]; +}; + +export default function() { + var m = mercatorProjection(transverseMercatorRaw), + center = m.center, + rotate = m.rotate; + + m.center = function(_) { + return arguments.length ? center([-_[1], _[0]]) : (_ = center(), [_[1], -_[0]]); + }; + + m.rotate = function(_) { + return arguments.length ? rotate([_[0], _[1], _.length > 2 ? _[2] + 90 : 90]) : (_ = rotate(), [_[0], _[1], _[2] - 90]); + }; + + return rotate([0, 0, 90]) + .scale(159.155); +} diff --git a/frontend/node_modules/d3-geo/src/rotation.js b/frontend/node_modules/d3-geo/src/rotation.js new file mode 100644 index 0000000..dc1b068 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/rotation.js @@ -0,0 +1,79 @@ +import compose from "./compose.js"; +import {abs, asin, atan2, cos, degrees, pi, radians, sin, tau} from "./math.js"; + +function rotationIdentity(lambda, phi) { + if (abs(lambda) > pi) lambda -= Math.round(lambda / tau) * tau; + return [lambda, phi]; +} + +rotationIdentity.invert = rotationIdentity; + +export function rotateRadians(deltaLambda, deltaPhi, deltaGamma) { + return (deltaLambda %= tau) ? (deltaPhi || deltaGamma ? compose(rotationLambda(deltaLambda), rotationPhiGamma(deltaPhi, deltaGamma)) + : rotationLambda(deltaLambda)) + : (deltaPhi || deltaGamma ? rotationPhiGamma(deltaPhi, deltaGamma) + : rotationIdentity); +} + +function forwardRotationLambda(deltaLambda) { + return function(lambda, phi) { + lambda += deltaLambda; + if (abs(lambda) > pi) lambda -= Math.round(lambda / tau) * tau; + return [lambda, phi]; + }; +} + +function rotationLambda(deltaLambda) { + var rotation = forwardRotationLambda(deltaLambda); + rotation.invert = forwardRotationLambda(-deltaLambda); + return rotation; +} + +function rotationPhiGamma(deltaPhi, deltaGamma) { + var cosDeltaPhi = cos(deltaPhi), + sinDeltaPhi = sin(deltaPhi), + cosDeltaGamma = cos(deltaGamma), + sinDeltaGamma = sin(deltaGamma); + + function rotation(lambda, phi) { + var cosPhi = cos(phi), + x = cos(lambda) * cosPhi, + y = sin(lambda) * cosPhi, + z = sin(phi), + k = z * cosDeltaPhi + x * sinDeltaPhi; + return [ + atan2(y * cosDeltaGamma - k * sinDeltaGamma, x * cosDeltaPhi - z * sinDeltaPhi), + asin(k * cosDeltaGamma + y * sinDeltaGamma) + ]; + } + + rotation.invert = function(lambda, phi) { + var cosPhi = cos(phi), + x = cos(lambda) * cosPhi, + y = sin(lambda) * cosPhi, + z = sin(phi), + k = z * cosDeltaGamma - y * sinDeltaGamma; + return [ + atan2(y * cosDeltaGamma + z * sinDeltaGamma, x * cosDeltaPhi + k * sinDeltaPhi), + asin(k * cosDeltaPhi - x * sinDeltaPhi) + ]; + }; + + return rotation; +} + +export default function(rotate) { + rotate = rotateRadians(rotate[0] * radians, rotate[1] * radians, rotate.length > 2 ? rotate[2] * radians : 0); + + function forward(coordinates) { + coordinates = rotate(coordinates[0] * radians, coordinates[1] * radians); + return coordinates[0] *= degrees, coordinates[1] *= degrees, coordinates; + } + + forward.invert = function(coordinates) { + coordinates = rotate.invert(coordinates[0] * radians, coordinates[1] * radians); + return coordinates[0] *= degrees, coordinates[1] *= degrees, coordinates; + }; + + return forward; +} diff --git a/frontend/node_modules/d3-geo/src/stream.js b/frontend/node_modules/d3-geo/src/stream.js new file mode 100644 index 0000000..ee994ae --- /dev/null +++ b/frontend/node_modules/d3-geo/src/stream.js @@ -0,0 +1,69 @@ +function streamGeometry(geometry, stream) { + if (geometry && streamGeometryType.hasOwnProperty(geometry.type)) { + streamGeometryType[geometry.type](geometry, stream); + } +} + +var streamObjectType = { + Feature: function(object, stream) { + streamGeometry(object.geometry, stream); + }, + FeatureCollection: function(object, stream) { + var features = object.features, i = -1, n = features.length; + while (++i < n) streamGeometry(features[i].geometry, stream); + } +}; + +var streamGeometryType = { + Sphere: function(object, stream) { + stream.sphere(); + }, + Point: function(object, stream) { + object = object.coordinates; + stream.point(object[0], object[1], object[2]); + }, + MultiPoint: function(object, stream) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) object = coordinates[i], stream.point(object[0], object[1], object[2]); + }, + LineString: function(object, stream) { + streamLine(object.coordinates, stream, 0); + }, + MultiLineString: function(object, stream) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) streamLine(coordinates[i], stream, 0); + }, + Polygon: function(object, stream) { + streamPolygon(object.coordinates, stream); + }, + MultiPolygon: function(object, stream) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) streamPolygon(coordinates[i], stream); + }, + GeometryCollection: function(object, stream) { + var geometries = object.geometries, i = -1, n = geometries.length; + while (++i < n) streamGeometry(geometries[i], stream); + } +}; + +function streamLine(coordinates, stream, closed) { + var i = -1, n = coordinates.length - closed, coordinate; + stream.lineStart(); + while (++i < n) coordinate = coordinates[i], stream.point(coordinate[0], coordinate[1], coordinate[2]); + stream.lineEnd(); +} + +function streamPolygon(coordinates, stream) { + var i = -1, n = coordinates.length; + stream.polygonStart(); + while (++i < n) streamLine(coordinates[i], stream, 1); + stream.polygonEnd(); +} + +export default function(object, stream) { + if (object && streamObjectType.hasOwnProperty(object.type)) { + streamObjectType[object.type](object, stream); + } else { + streamGeometry(object, stream); + } +} diff --git a/frontend/node_modules/d3-geo/src/transform.js b/frontend/node_modules/d3-geo/src/transform.js new file mode 100644 index 0000000..a954bc5 --- /dev/null +++ b/frontend/node_modules/d3-geo/src/transform.js @@ -0,0 +1,26 @@ +export default function(methods) { + return { + stream: transformer(methods) + }; +} + +export function transformer(methods) { + return function(stream) { + var s = new TransformStream; + for (var key in methods) s[key] = methods[key]; + s.stream = stream; + return s; + }; +} + +function TransformStream() {} + +TransformStream.prototype = { + constructor: TransformStream, + point: function(x, y) { this.stream.point(x, y); }, + sphere: function() { this.stream.sphere(); }, + lineStart: function() { this.stream.lineStart(); }, + lineEnd: function() { this.stream.lineEnd(); }, + polygonStart: function() { this.stream.polygonStart(); }, + polygonEnd: function() { this.stream.polygonEnd(); } +}; diff --git a/frontend/node_modules/d3-hierarchy/LICENSE b/frontend/node_modules/d3-hierarchy/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-hierarchy/README.md b/frontend/node_modules/d3-hierarchy/README.md new file mode 100644 index 0000000..69e4f7e --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/README.md @@ -0,0 +1,592 @@ +# d3-hierarchy + +Many datasets are intrinsically hierarchical. Consider [geographic entities](https://www.census.gov/programs-surveys/geography/guidance/hierarchy.html), such as census blocks, census tracts, counties and states; the command structure of businesses and governments; file systems and software packages. And even non-hierarchical data may be arranged empirically into a hierarchy, as with [*k*-means clustering](https://en.wikipedia.org/wiki/K-means_clustering) or [phylogenetic trees](https://observablehq.com/@mbostock/tree-of-life). + +This module implements several popular techniques for visualizing hierarchical data: + +**Node-link diagrams** show topology using discrete marks for nodes and links, such as a circle for each node and a line connecting each parent and child. The [“tidy” tree](#tree) is delightfully compact, while the [dendrogram](#cluster) places leaves at the same level. (These have both polar and Cartesian forms.) [Indented trees](https://observablehq.com/@d3/indented-tree) are useful for interactive browsing. + +**Adjacency diagrams** show topology through the relative placement of nodes. They may also encode a quantitative dimension in the area of each node, for example to show revenue or file size. The [“icicle” diagram](#partition) uses rectangles, while the “sunburst” uses annular segments. + +**Enclosure diagrams** also use an area encoding, but show topology through containment. A [treemap](#treemap) recursively subdivides area into rectangles. [Circle-packing](#pack) tightly nests circles; this is not as space-efficient as a treemap, but perhaps more readily shows topology. + +A good hierarchical visualization facilitates rapid multiscale inference: micro-observations of individual elements and macro-observations of large groups. + +## Installing + +If you use npm, `npm install d3-hierarchy`. You can also download the [latest release on GitHub](https://github.com/d3/d3-hierarchy/releases/latest). For vanilla HTML in modern browsers, import d3-hierarchy from Skypack: + +```html + +``` + +For legacy environments, you can load d3-hierarchy’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +## API Reference + +* [Hierarchy](#hierarchy) ([Stratify](#stratify)) +* [Cluster](#cluster) +* [Tree](#tree) +* [Treemap](#treemap) ([Treemap Tiling](#treemap-tiling)) +* [Partition](#partition) +* [Pack](#pack) + +### Hierarchy + +Before you can compute a hierarchical layout, you need a root node. If your data is already in a hierarchical format, such as JSON, you can pass it directly to [d3.hierarchy](#hierarchy); otherwise, you can rearrange tabular data, such as comma-separated values (CSV), into a hierarchy using [d3.stratify](#stratify). + +# d3.hierarchy(data[, children]) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/index.js), [Examples](https://observablehq.com/@d3/d3-hierarchy) + +Constructs a root node from the specified hierarchical *data*. The specified *data* must be an object representing the root node. For example: + +```json +{ + "name": "Eve", + "children": [ + { + "name": "Cain" + }, + { + "name": "Seth", + "children": [ + { + "name": "Enos" + }, + { + "name": "Noam" + } + ] + }, + { + "name": "Abel" + }, + { + "name": "Awan", + "children": [ + { + "name": "Enoch" + } + ] + }, + { + "name": "Azura" + } + ] +} +``` + +The specified *children* accessor function is invoked for each datum, starting with the root *data*, and must return an iterable of data representing the children, if any. If the children accessor is not specified, it defaults to: + +```js +function children(d) { + return d.children; +} +``` + +If *data* is a Map, it is implicitly converted to the entry [undefined, *data*], and the children accessor instead defaults to: + +```js +function children(d) { + return Array.isArray(d) ? d[1] : null; +} +``` + +This allows you to pass the result of [d3.group](https://github.com/d3/d3-array/blob/main/README.md#group) or [d3.rollup](https://github.com/d3/d3-array/blob/main/README.md#rollup) to d3.hierarchy. + +The returned node and each descendant has the following properties: + +* *node*.data - the associated data, as specified to the [constructor](#hierarchy). +* *node*.depth - zero for the root node, and increasing by one for each descendant generation. +* *node*.height - zero for leaf nodes, and the greatest distance from any descendant leaf for internal nodes. +* *node*.parent - the parent node, or null for the root node. +* *node*.children - an array of child nodes, if any; undefined for leaf nodes. +* *node*.value - the summed value of the node and its [descendants](#node_descendants); optional, see [*node*.sum](#node_sum) and [*node*.count](#node_count). + +This method can also be used to test if a node is an `instanceof d3.hierarchy` and to extend the node prototype. + +# node.ancestors() · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/ancestors.js), [Examples](https://observablehq.com/@d3/d3-hierarchy) + +Returns the array of ancestors nodes, starting with this node, then followed by each parent up to the root. + +# node.descendants() · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/descendants.js), [Examples](https://observablehq.com/@d3/d3-hierarchy) + +Returns the array of descendant nodes, starting with this node, then followed by each child in topological order. + +# node.leaves() · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/leaves.js), [Examples](https://observablehq.com/@d3/d3-hierarchy) + +Returns the array of leaf nodes in traversal order; leaves are nodes with no children. + +# node.find(filter) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/find.js) + +Returns the first node in the hierarchy from this *node* for which the specified *filter* returns a truthy value. undefined if no such node is found. + +# node.path(target) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/path.js), [Examples](https://observablehq.com/@d3/d3-hierarchy) + +Returns the shortest path through the hierarchy from this *node* to the specified *target* node. The path starts at this *node*, ascends to the least common ancestor of this *node* and the *target* node, and then descends to the *target* node. This is particularly useful for [hierarchical edge bundling](https://observablehq.com/@d3/hierarchical-edge-bundling). + +# node.links() · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/links.js), [Examples](https://observablehq.com/@d3/d3-hierarchy) + +Returns an array of links for this *node* and its descendants, where each *link* is an object that defines source and target properties. The source of each link is the parent node, and the target is a child node. + +# node.sum(value) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/sum.js), [Examples](https://observablehq.com/@d3/visiting-a-d3-hierarchy) + +Evaluates the specified *value* function for this *node* and each descendant in [post-order traversal](#node_eachAfter), and returns this *node*. The *node*.value property of each node is set to the numeric value returned by the specified function plus the combined value of all children. The function is passed the node’s data, and must return a non-negative number. The *value* accessor is evaluated for *node* and every descendant, including internal nodes; if you only want leaf nodes to have internal value, then return zero for any node with children. [For example](https://observablehq.com/@d3/treemap-by-count), as an alternative to [*node*.count](#node_count): + +```js +root.sum(function(d) { return d.value ? 1 : 0; }); +``` + +You must call *node*.sum or [*node*.count](#node_count) before invoking a hierarchical layout that requires *node*.value, such as [d3.treemap](#treemap). Since the API supports [method chaining](https://en.wikipedia.org/wiki/Method_chaining), you can invoke *node*.sum and [*node*.sort](#node_sort) before computing the layout, and then subsequently generate an array of all [descendant nodes](#node_descendants) like so: + +```js +var treemap = d3.treemap() + .size([width, height]) + .padding(2); + +var nodes = treemap(root + .sum(function(d) { return d.value; }) + .sort(function(a, b) { return b.height - a.height || b.value - a.value; })) + .descendants(); +``` + +This example assumes that the node data has a value field. + +# node.count() · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/count.js), [Examples](https://observablehq.com/@d3/visiting-a-d3-hierarchy) + +Computes the number of leaves under this *node* and assigns it to *node*.value, and similarly for every descendant of *node*. If this *node* is a leaf, its count is one. Returns this *node*. See also [*node*.sum](#node_sum). + +# node.sort(compare) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/sort.js), [Examples](https://observablehq.com/@d3/visiting-a-d3-hierarchy) + +Sorts the children of this *node*, if any, and each of this *node*’s descendants’ children, in [pre-order traversal](#node_eachBefore) using the specified *compare* function, and returns this *node*. The specified function is passed two nodes *a* and *b* to compare. If *a* should be before *b*, the function must return a value less than zero; if *b* should be before *a*, the function must return a value greater than zero; otherwise, the relative order of *a* and *b* are not specified. See [*array*.sort](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/sort) for more. + +Unlike [*node*.sum](#node_sum), the *compare* function is passed two [nodes](#hierarchy) rather than two nodes’ data. For example, if the data has a value property, this sorts nodes by the descending aggregate value of the node and all its descendants, as is recommended for [circle-packing](#pack): + +```js +root + .sum(function(d) { return d.value; }) + .sort(function(a, b) { return b.value - a.value; }); +`````` + +Similarly, to sort nodes by descending height (greatest distance from any descendant leaf) and then descending value, as is recommended for [treemaps](#treemap) and [icicles](#partition): + +```js +root + .sum(function(d) { return d.value; }) + .sort(function(a, b) { return b.height - a.height || b.value - a.value; }); +``` + +To sort nodes by descending height and then ascending id, as is recommended for [trees](#tree) and [dendrograms](#cluster): + +```js +root + .sum(function(d) { return d.value; }) + .sort(function(a, b) { return b.height - a.height || a.id.localeCompare(b.id); }); +``` + +You must call *node*.sort before invoking a hierarchical layout if you want the new sort order to affect the layout; see [*node*.sum](#node_sum) for an example. + +# node\[Symbol.iterator\]() [<>](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/iterator.js "Source") + +Returns an iterator over the *node*’s descendants in breadth-first order. For example: + +```js +for (const descendant of node) { + console.log(descendant); +} +``` + +# node.each(function[, that]) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/each.js), [Examples](https://observablehq.com/@d3/visiting-a-d3-hierarchy) + +Invokes the specified *function* for *node* and each descendant in [breadth-first order](https://en.wikipedia.org/wiki/Breadth-first_search), such that a given *node* is only visited if all nodes of lesser depth have already been visited, as well as all preceding nodes of the same depth. The specified function is passed the current *descendant*, the zero-based traversal *index*, and this *node*. If *that* is specified, it is the this context of the callback. + +# node.eachAfter(function[, that]) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/eachAfter.js), [Examples](https://observablehq.com/@d3/visiting-a-d3-hierarchy) + +Invokes the specified *function* for *node* and each descendant in [post-order traversal](https://en.wikipedia.org/wiki/Tree_traversal#Post-order), such that a given *node* is only visited after all of its descendants have already been visited. The specified function is passed the current *descendant*, the zero-based traversal *index*, and this *node*. If *that* is specified, it is the this context of the callback. + +# node.eachBefore(function[, that]) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/eachBefore.js), [Examples](https://observablehq.com/@d3/visiting-a-d3-hierarchy) + +Invokes the specified *function* for *node* and each descendant in [pre-order traversal](https://en.wikipedia.org/wiki/Tree_traversal#Pre-order), such that a given *node* is only visited after all of its ancestors have already been visited. The specified function is passed the current *descendant*, the zero-based traversal *index*, and this *node*. If *that* is specified, it is the this context of the callback. + +# node.copy() · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/hierarchy/index.js), [Examples](https://observablehq.com/@d3/d3-hierarchy) + +Return a deep copy of the subtree starting at this *node*. (The returned deep copy shares the same data, however.) The returned node is the root of a new tree; the returned node’s parent is always null and its depth is always zero. + +#### Stratify + +Consider the following table of relationships: + +Name | Parent +------|-------- +Eve | +Cain | Eve +Seth | Eve +Enos | Seth +Noam | Seth +Abel | Eve +Awan | Eve +Enoch | Awan +Azura | Eve + +These names are conveniently unique, so we can unambiguously represent the hierarchy as a CSV file: + +``` +name,parent +Eve, +Cain,Eve +Seth,Eve +Enos,Seth +Noam,Seth +Abel,Eve +Awan,Eve +Enoch,Awan +Azura,Eve +``` + +To parse the CSV using [d3.csvParse](https://github.com/d3/d3-dsv#csvParse): + +```js +var table = d3.csvParse(text); +``` + +This returns: + +```json +[ + {"name": "Eve", "parent": ""}, + {"name": "Cain", "parent": "Eve"}, + {"name": "Seth", "parent": "Eve"}, + {"name": "Enos", "parent": "Seth"}, + {"name": "Noam", "parent": "Seth"}, + {"name": "Abel", "parent": "Eve"}, + {"name": "Awan", "parent": "Eve"}, + {"name": "Enoch", "parent": "Awan"}, + {"name": "Azura", "parent": "Eve"} +] +``` + +To convert to a hierarchy: + +```js +var root = d3.stratify() + .id(function(d) { return d.name; }) + .parentId(function(d) { return d.parent; }) + (table); +``` + +This returns: + +[Stratify](https://runkit.com/mbostock/56fed33d8630b01300f72daa) + +This hierarchy can now be passed to a hierarchical layout, such as [d3.tree](#_tree), for visualization. + +# d3.stratify() · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/stratify.js), [Examples](https://observablehq.com/@d3/d3-stratify) + +Constructs a new stratify operator with the default settings. + +# stratify(data) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/stratify.js), [Examples](https://observablehq.com/@d3/d3-stratify) + +Generates a new hierarchy from the specified tabular *data*. + +# stratify.id([id]) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/stratify.js), [Examples](https://observablehq.com/@d3/d3-stratify) + +If *id* is specified, sets the id accessor to the given function and returns this stratify operator. Otherwise, returns the current id accessor, which defaults to: + +```js +function id(d) { + return d.id; +} +``` + +The id accessor is invoked for each element in the input data passed to the [stratify operator](#_stratify), being passed the current datum (*d*) and the current index (*i*). The returned string is then used to identify the node’s relationships in conjunction with the [parent id](#stratify_parentId). For leaf nodes, the id may be undefined; otherwise, the id must be unique. (Null and the empty string are equivalent to undefined.) + +# stratify.parentId([parentId]) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/stratify.js), [Examples](https://observablehq.com/@d3/d3-stratify) + +If *parentId* is specified, sets the parent id accessor to the given function and returns this stratify operator. Otherwise, returns the current parent id accessor, which defaults to: + +```js +function parentId(d) { + return d.parentId; +} +``` + +The parent id accessor is invoked for each element in the input data passed to the [stratify operator](#_stratify), being passed the current datum (*d*) and the current index (*i*). The returned string is then used to identify the node’s relationships in conjunction with the [id](#stratify_id). For the root node, the parent id should be undefined. (Null and the empty string are equivalent to undefined.) There must be exactly one root node in the input data, and no circular relationships. + +# stratify.path([path]) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/stratify.js), [Examples](https://observablehq.com/@d3/d3-stratify) + +If *path* is specified, sets the path accessor to the given function and returns this stratify operator. Otherwise, returns the current path accessor, which defaults to undefined. If a path accessor is set, the id and parentId arguments are ignored, and a unix-like hierarchy is computed on the slash-delimited strings returned by the path accessor, imputing parent nodes and ids as necessary. + +```js +d3.stratify().path(d => d)(["a/b", "a/c"]); // nodes with id "/a", "/a/b", "/a/c" +``` + +### Cluster + +[Dendrogram](https://observablehq.com/@d3/cluster-dendrogram) + +The **cluster layout** produces [dendrograms](http://en.wikipedia.org/wiki/Dendrogram): node-link diagrams that place leaf nodes of the tree at the same depth. Dendrograms are typically less compact than [tidy trees](#tree), but are useful when all the leaves should be at the same level, such as for hierarchical clustering or [phylogenetic tree diagrams](https://observablehq.com/@mbostock/tree-of-life). + +# d3.cluster() · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/cluster.js), [Examples](https://observablehq.com/@d3/cluster-dendrogram) + +Creates a new cluster layout with default settings. + +# cluster(root) + +Lays out the specified *root* [hierarchy](#hierarchy), assigning the following properties on *root* and its descendants: + +* *node*.x - the *x*-coordinate of the node +* *node*.y - the *y*-coordinate of the node + +The coordinates *x* and *y* represent an arbitrary coordinate system; for example, you can treat *x* as an angle and *y* as a radius to produce a [radial layout](https://observablehq.com/@d3/radial-dendrogram). You may want to call [*root*.sort](#node_sort) before passing the hierarchy to the cluster layout. + +# cluster.size([size]) + +If *size* is specified, sets this cluster layout’s size to the specified two-element array of numbers [*width*, *height*] and returns this cluster layout. If *size* is not specified, returns the current layout size, which defaults to [1, 1]. A layout size of null indicates that a [node size](#cluster_nodeSize) will be used instead. The coordinates *x* and *y* represent an arbitrary coordinate system; for example, to produce a [radial layout](https://observablehq.com/@d3/radial-dendrogram), a size of [360, *radius*] corresponds to a breadth of 360° and a depth of *radius*. + +# cluster.nodeSize([size]) + +If *size* is specified, sets this cluster layout’s node size to the specified two-element array of numbers [*width*, *height*] and returns this cluster layout. If *size* is not specified, returns the current node size, which defaults to null. A node size of null indicates that a [layout size](#cluster_size) will be used instead. When a node size is specified, the root node is always positioned at ⟨0, 0⟩. + +# cluster.separation([separation]) + +If *separation* is specified, sets the separation accessor to the specified function and returns this cluster layout. If *separation* is not specified, returns the current separation accessor, which defaults to: + +```js +function separation(a, b) { + return a.parent == b.parent ? 1 : 2; +} +``` + +The separation accessor is used to separate neighboring leaves. The separation function is passed two leaves *a* and *b*, and must return the desired separation. The nodes are typically siblings, though the nodes may be more distantly related if the layout decides to place such nodes adjacent. + +### Tree + +[Tidy Tree](https://observablehq.com/@d3/tidy-tree) + +The **tree** layout produces tidy node-link diagrams of trees using the [Reingold–Tilford “tidy” algorithm](http://reingold.co/tidier-drawings.pdf), improved to run in linear time by [Buchheim *et al.*](http://dirk.jivas.de/papers/buchheim02improving.pdf) Tidy trees are typically more compact than [dendrograms](#cluster). + +# d3.tree() · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/tree.js), [Examples](https://observablehq.com/@d3/tidy-tree) + +Creates a new tree layout with default settings. + +# tree(root) + +Lays out the specified *root* [hierarchy](#hierarchy), assigning the following properties on *root* and its descendants: + +* *node*.x - the *x*-coordinate of the node +* *node*.y - the *y*-coordinate of the node + +The coordinates *x* and *y* represent an arbitrary coordinate system; for example, you can treat *x* as an angle and *y* as a radius to produce a [radial layout](https://observablehq.com/@d3/radial-tidy-tree). You may want to call [*root*.sort](#node_sort) before passing the hierarchy to the tree layout. + +# tree.size([size]) + +If *size* is specified, sets this tree layout’s size to the specified two-element array of numbers [*width*, *height*] and returns this tree layout. If *size* is not specified, returns the current layout size, which defaults to [1, 1]. A layout size of null indicates that a [node size](#tree_nodeSize) will be used instead. The coordinates *x* and *y* represent an arbitrary coordinate system; for example, to produce a [radial layout](https://observablehq.com/@d3/radial-tidy-tree), a size of [360, *radius*] corresponds to a breadth of 360° and a depth of *radius*. + +# tree.nodeSize([size]) + +If *size* is specified, sets this tree layout’s node size to the specified two-element array of numbers [*width*, *height*] and returns this tree layout. If *size* is not specified, returns the current node size, which defaults to null. A node size of null indicates that a [layout size](#tree_size) will be used instead. When a node size is specified, the root node is always positioned at ⟨0, 0⟩. + +# tree.separation([separation]) + +If *separation* is specified, sets the separation accessor to the specified function and returns this tree layout. If *separation* is not specified, returns the current separation accessor, which defaults to: + +```js +function separation(a, b) { + return a.parent == b.parent ? 1 : 2; +} +``` + +A variation that is more appropriate for radial layouts reduces the separation gap proportionally to the radius: + +```js +function separation(a, b) { + return (a.parent == b.parent ? 1 : 2) / a.depth; +} +``` + +The separation accessor is used to separate neighboring nodes. The separation function is passed two nodes *a* and *b*, and must return the desired separation. The nodes are typically siblings, though the nodes may be more distantly related if the layout decides to place such nodes adjacent. + +### Treemap + +[Treemap](https://observablehq.com/@d3/treemap) + +Introduced by [Ben Shneiderman](http://www.cs.umd.edu/hcil/treemap-history/) in 1991, a **treemap** recursively subdivides area into rectangles according to each node’s associated value. D3’s treemap implementation supports an extensible [tiling method](#treemap_tile): the default [squarified](#treemapSquarify) method seeks to generate rectangles with a [golden](https://en.wikipedia.org/wiki/Golden_ratio) aspect ratio; this offers better readability and size estimation than [slice-and-dice](#treemapSliceDice), which simply alternates between horizontal and vertical subdivision by depth. + +# d3.treemap() · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/treemap/index.js), [Examples](https://observablehq.com/@d3/treemap) + +Creates a new treemap layout with default settings. + +# treemap(root) + +Lays out the specified *root* [hierarchy](#hierarchy), assigning the following properties on *root* and its descendants: + +* *node*.x0 - the left edge of the rectangle +* *node*.y0 - the top edge of the rectangle +* *node*.x1 - the right edge of the rectangle +* *node*.y1 - the bottom edge of the rectangle + +You must call [*root*.sum](#node_sum) before passing the hierarchy to the treemap layout. You probably also want to call [*root*.sort](#node_sort) to order the hierarchy before computing the layout. + +# treemap.tile([tile]) + +If *tile* is specified, sets the [tiling method](#treemap-tiling) to the specified function and returns this treemap layout. If *tile* is not specified, returns the current tiling method, which defaults to [d3.treemapSquarify](#treemapSquarify) with the golden ratio. + +# treemap.size([size]) + +If *size* is specified, sets this treemap layout’s size to the specified two-element array of numbers [*width*, *height*] and returns this treemap layout. If *size* is not specified, returns the current size, which defaults to [1, 1]. + +# treemap.round([round]) + +If *round* is specified, enables or disables rounding according to the given boolean and returns this treemap layout. If *round* is not specified, returns the current rounding state, which defaults to false. + +# treemap.padding([padding]) + +If *padding* is specified, sets the [inner](#treemap_paddingInner) and [outer](#treemap_paddingOuter) padding to the specified number or function and returns this treemap layout. If *padding* is not specified, returns the current inner padding function. + +# treemap.paddingInner([padding]) + +If *padding* is specified, sets the inner padding to the specified number or function and returns this treemap layout. If *padding* is not specified, returns the current inner padding function, which defaults to the constant zero. If *padding* is a function, it is invoked for each node with children, being passed the current node. The inner padding is used to separate a node’s adjacent children. + +# treemap.paddingOuter([padding]) + +If *padding* is specified, sets the [top](#treemap_paddingTop), [right](#treemap_paddingRight), [bottom](#treemap_paddingBottom) and [left](#treemap_paddingLeft) padding to the specified number or function and returns this treemap layout. If *padding* is not specified, returns the current top padding function. + +# treemap.paddingTop([padding]) + +If *padding* is specified, sets the top padding to the specified number or function and returns this treemap layout. If *padding* is not specified, returns the current top padding function, which defaults to the constant zero. If *padding* is a function, it is invoked for each node with children, being passed the current node. The top padding is used to separate the top edge of a node from its children. + +# treemap.paddingRight([padding]) + +If *padding* is specified, sets the right padding to the specified number or function and returns this treemap layout. If *padding* is not specified, returns the current right padding function, which defaults to the constant zero. If *padding* is a function, it is invoked for each node with children, being passed the current node. The right padding is used to separate the right edge of a node from its children. + +# treemap.paddingBottom([padding]) + +If *padding* is specified, sets the bottom padding to the specified number or function and returns this treemap layout. If *padding* is not specified, returns the current bottom padding function, which defaults to the constant zero. If *padding* is a function, it is invoked for each node with children, being passed the current node. The bottom padding is used to separate the bottom edge of a node from its children. + +# treemap.paddingLeft([padding]) + +If *padding* is specified, sets the left padding to the specified number or function and returns this treemap layout. If *padding* is not specified, returns the current left padding function, which defaults to the constant zero. If *padding* is a function, it is invoked for each node with children, being passed the current node. The left padding is used to separate the left edge of a node from its children. + +#### Treemap Tiling + +Several built-in tiling methods are provided for use with [*treemap*.tile](#treemap_tile). + +# d3.treemapBinary(node, x0, y0, x1, y1) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/treemap/binary.js), [Examples](https://observablehq.com/@d3/treemap) + +Recursively partitions the specified *nodes* into an approximately-balanced binary tree, choosing horizontal partitioning for wide rectangles and vertical partitioning for tall rectangles. + +# d3.treemapDice(node, x0, y0, x1, y1) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/treemap/dice.js), [Examples](https://observablehq.com/@d3/treemap) + +Divides the rectangular area specified by *x0*, *y0*, *x1*, *y1* horizontally according the value of each of the specified *node*’s children. The children are positioned in order, starting with the left edge (*x0*) of the given rectangle. If the sum of the children’s values is less than the specified *node*’s value (*i.e.*, if the specified *node* has a non-zero internal value), the remaining empty space will be positioned on the right edge (*x1*) of the given rectangle. + +# d3.treemapSlice(node, x0, y0, x1, y1) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/treemap/slice.js), [Examples](https://observablehq.com/@d3/treemap) + +Divides the rectangular area specified by *x0*, *y0*, *x1*, *y1* vertically according the value of each of the specified *node*’s children. The children are positioned in order, starting with the top edge (*y0*) of the given rectangle. If the sum of the children’s values is less than the specified *node*’s value (*i.e.*, if the specified *node* has a non-zero internal value), the remaining empty space will be positioned on the bottom edge (*y1*) of the given rectangle. + +# d3.treemapSliceDice(node, x0, y0, x1, y1) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/treemap/sliceDice.js), [Examples](https://observablehq.com/@d3/treemap) + +If the specified *node* has odd depth, delegates to [treemapSlice](#treemapSlice); otherwise delegates to [treemapDice](#treemapDice). + +# d3.treemapSquarify(node, x0, y0, x1, y1) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/treemap/squarify.js), [Examples](https://observablehq.com/@d3/treemap) + +Implements the [squarified treemap](https://www.win.tue.nl/~vanwijk/stm.pdf) algorithm by Bruls *et al.*, which seeks to produce rectangles of a given [aspect ratio](#squarify_ratio). + +# d3.treemapResquarify(node, x0, y0, x1, y1) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/treemap/resquarify.js), [Examples](https://observablehq.com/@d3/animated-treemap) + +Like [d3.treemapSquarify](#treemapSquarify), except preserves the topology (node adjacencies) of the previous layout computed by d3.treemapResquarify, if there is one and it used the same [target aspect ratio](#squarify_ratio). This tiling method is good for animating changes to treemaps because it only changes node sizes and not their relative positions, thus avoiding distracting shuffling and occlusion. The downside of a stable update, however, is a suboptimal layout for subsequent updates: only the first layout uses the Bruls *et al.* squarified algorithm. + +# squarify.ratio(ratio) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/treemap/squarify.js), [Examples](https://observablehq.com/@d3/treemap) + +Specifies the desired aspect ratio of the generated rectangles. The *ratio* must be specified as a number greater than or equal to one. Note that the orientation of the generated rectangles (tall or wide) is not implied by the ratio; for example, a ratio of two will attempt to produce a mixture of rectangles whose *width*:*height* ratio is either 2:1 or 1:2. (However, you can approximately achieve this result by generating a square treemap at different dimensions, and then [stretching the treemap](https://observablehq.com/@d3/stretched-treemap) to the desired aspect ratio.) Furthermore, the specified *ratio* is merely a hint to the tiling algorithm; the rectangles are not guaranteed to have the specified aspect ratio. If not specified, the aspect ratio defaults to the golden ratio, φ = (1 + sqrt(5)) / 2, per [Kong *et al.*](http://vis.stanford.edu/papers/perception-treemaps) + +### Partition + +[Partition](https://observablehq.com/@d3/icicle) + +The **partition layout** produces adjacency diagrams: a space-filling variant of a node-link tree diagram. Rather than drawing a link between parent and child in the hierarchy, nodes are drawn as solid areas (either arcs or rectangles), and their placement relative to other nodes reveals their position in the hierarchy. The size of the nodes encodes a quantitative dimension that would be difficult to show in a node-link diagram. + +# d3.partition() · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/partition.js), [Examples](https://observablehq.com/@d3/icicle) + +Creates a new partition layout with the default settings. + +# partition(root) + +Lays out the specified *root* [hierarchy](#hierarchy), assigning the following properties on *root* and its descendants: + +* *node*.x0 - the left edge of the rectangle +* *node*.y0 - the top edge of the rectangle +* *node*.x1 - the right edge of the rectangle +* *node*.y1 - the bottom edge of the rectangle + +You must call [*root*.sum](#node_sum) before passing the hierarchy to the partition layout. You probably also want to call [*root*.sort](#node_sort) to order the hierarchy before computing the layout. + +# partition.size([size]) + +If *size* is specified, sets this partition layout’s size to the specified two-element array of numbers [*width*, *height*] and returns this partition layout. If *size* is not specified, returns the current size, which defaults to [1, 1]. + +# partition.round([round]) + +If *round* is specified, enables or disables rounding according to the given boolean and returns this partition layout. If *round* is not specified, returns the current rounding state, which defaults to false. + +# partition.padding([padding]) + +If *padding* is specified, sets the padding to the specified number and returns this partition layout. If *padding* is not specified, returns the current padding, which defaults to zero. The padding is used to separate a node’s adjacent children. + +### Pack + +[Circle-Packing](https://observablehq.com/@d3/circle-packing) + +Enclosure diagrams use containment (nesting) to represent a hierarchy. The size of the leaf circles encodes a quantitative dimension of the data. The enclosing circles show the approximate cumulative size of each subtree, but due to wasted space there is some distortion; only the leaf nodes can be compared accurately. Although [circle packing](http://en.wikipedia.org/wiki/Circle_packing) does not use space as efficiently as a [treemap](#treemap), the “wasted” space more prominently reveals the hierarchical structure. + +# d3.pack() · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/pack/index.js), [Examples](https://observablehq.com/@d3/circle-packing) + +Creates a new pack layout with the default settings. + +# pack(root) + +Lays out the specified *root* [hierarchy](#hierarchy), assigning the following properties on *root* and its descendants: + +* *node*.x - the *x*-coordinate of the circle’s center +* *node*.y - the *y*-coordinate of the circle’s center +* *node*.r - the radius of the circle + +You must call [*root*.sum](#node_sum) before passing the hierarchy to the pack layout. You probably also want to call [*root*.sort](#node_sort) to order the hierarchy before computing the layout. + +# pack.radius([radius]) + +If *radius* is specified, sets the pack layout’s radius accessor to the specified function and returns this pack layout. If *radius* is not specified, returns the current radius accessor, which defaults to null. If the radius accessor is null, the radius of each leaf circle is derived from the leaf *node*.value (computed by [*node*.sum](#node_sum)); the radii are then scaled proportionally to fit the [layout size](#pack_size). If the radius accessor is not null, the radius of each leaf circle is specified exactly by the function. + +# pack.size([size]) + +If *size* is specified, sets this pack layout’s size to the specified two-element array of numbers [*width*, *height*] and returns this pack layout. If *size* is not specified, returns the current size, which defaults to [1, 1]. + +# pack.padding([padding]) + +If *padding* is specified, sets this pack layout’s padding accessor to the specified number or function and returns this pack layout. If *padding* is not specified, returns the current padding accessor, which defaults to the constant zero. When siblings are packed, tangent siblings will be separated by approximately the specified padding; the enclosing parent circle will also be separated from its children by approximately the specified padding. If an [explicit radius](#pack_radius) is not specified, the padding is approximate because a two-pass algorithm is needed to fit within the [layout size](#pack_size): the circles are first packed without padding; a scaling factor is computed and applied to the specified padding; and lastly the circles are re-packed with padding. + +# d3.packSiblings(circles) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/pack/siblings.js) + +Packs the specified array of *circles*, each of which must have a *circle*.r property specifying the circle’s radius. Assigns the following properties to each circle: + +* *circle*.x - the *x*-coordinate of the circle’s center +* *circle*.y - the *y*-coordinate of the circle’s center + +The circles are positioned according to the front-chain packing algorithm by [Wang *et al.*](https://dl.acm.org/citation.cfm?id=1124851) + +# d3.packEnclose(circles) · [Source](https://github.com/d3/d3-hierarchy/blob/main/src/pack/enclose.js), [Examples](https://observablehq.com/@d3/d3-packenclose) + +Computes the [smallest circle](https://en.wikipedia.org/wiki/Smallest-circle_problem) that encloses the specified array of *circles*, each of which must have a *circle*.r property specifying the circle’s radius, and *circle*.x and *circle*.y properties specifying the circle’s center. The enclosing circle is computed using the [Matoušek-Sharir-Welzl algorithm](http://www.inf.ethz.ch/personal/emo/PublFiles/SubexLinProg_ALG16_96.pdf). (See also [Apollonius’ Problem](https://bl.ocks.org/mbostock/751fdd637f4bc2e3f08b).) diff --git a/frontend/node_modules/d3-hierarchy/dist/d3-hierarchy.js b/frontend/node_modules/d3-hierarchy/dist/d3-hierarchy.js new file mode 100644 index 0000000..5896e3e --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/dist/d3-hierarchy.js @@ -0,0 +1,1410 @@ +// https://d3js.org/d3-hierarchy/ v3.1.2 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +})(this, (function (exports) { 'use strict'; + +function defaultSeparation$1(a, b) { + return a.parent === b.parent ? 1 : 2; +} + +function meanX(children) { + return children.reduce(meanXReduce, 0) / children.length; +} + +function meanXReduce(x, c) { + return x + c.x; +} + +function maxY(children) { + return 1 + children.reduce(maxYReduce, 0); +} + +function maxYReduce(y, c) { + return Math.max(y, c.y); +} + +function leafLeft(node) { + var children; + while (children = node.children) node = children[0]; + return node; +} + +function leafRight(node) { + var children; + while (children = node.children) node = children[children.length - 1]; + return node; +} + +function cluster() { + var separation = defaultSeparation$1, + dx = 1, + dy = 1, + nodeSize = false; + + function cluster(root) { + var previousNode, + x = 0; + + // First walk, computing the initial x & y values. + root.eachAfter(function(node) { + var children = node.children; + if (children) { + node.x = meanX(children); + node.y = maxY(children); + } else { + node.x = previousNode ? x += separation(node, previousNode) : 0; + node.y = 0; + previousNode = node; + } + }); + + var left = leafLeft(root), + right = leafRight(root), + x0 = left.x - separation(left, right) / 2, + x1 = right.x + separation(right, left) / 2; + + // Second walk, normalizing x & y to the desired size. + return root.eachAfter(nodeSize ? function(node) { + node.x = (node.x - root.x) * dx; + node.y = (root.y - node.y) * dy; + } : function(node) { + node.x = (node.x - x0) / (x1 - x0) * dx; + node.y = (1 - (root.y ? node.y / root.y : 1)) * dy; + }); + } + + cluster.separation = function(x) { + return arguments.length ? (separation = x, cluster) : separation; + }; + + cluster.size = function(x) { + return arguments.length ? (nodeSize = false, dx = +x[0], dy = +x[1], cluster) : (nodeSize ? null : [dx, dy]); + }; + + cluster.nodeSize = function(x) { + return arguments.length ? (nodeSize = true, dx = +x[0], dy = +x[1], cluster) : (nodeSize ? [dx, dy] : null); + }; + + return cluster; +} + +function count(node) { + var sum = 0, + children = node.children, + i = children && children.length; + if (!i) sum = 1; + else while (--i >= 0) sum += children[i].value; + node.value = sum; +} + +function node_count() { + return this.eachAfter(count); +} + +function node_each(callback, that) { + let index = -1; + for (const node of this) { + callback.call(that, node, ++index, this); + } + return this; +} + +function node_eachBefore(callback, that) { + var node = this, nodes = [node], children, i, index = -1; + while (node = nodes.pop()) { + callback.call(that, node, ++index, this); + if (children = node.children) { + for (i = children.length - 1; i >= 0; --i) { + nodes.push(children[i]); + } + } + } + return this; +} + +function node_eachAfter(callback, that) { + var node = this, nodes = [node], next = [], children, i, n, index = -1; + while (node = nodes.pop()) { + next.push(node); + if (children = node.children) { + for (i = 0, n = children.length; i < n; ++i) { + nodes.push(children[i]); + } + } + } + while (node = next.pop()) { + callback.call(that, node, ++index, this); + } + return this; +} + +function node_find(callback, that) { + let index = -1; + for (const node of this) { + if (callback.call(that, node, ++index, this)) { + return node; + } + } +} + +function node_sum(value) { + return this.eachAfter(function(node) { + var sum = +value(node.data) || 0, + children = node.children, + i = children && children.length; + while (--i >= 0) sum += children[i].value; + node.value = sum; + }); +} + +function node_sort(compare) { + return this.eachBefore(function(node) { + if (node.children) { + node.children.sort(compare); + } + }); +} + +function node_path(end) { + var start = this, + ancestor = leastCommonAncestor(start, end), + nodes = [start]; + while (start !== ancestor) { + start = start.parent; + nodes.push(start); + } + var k = nodes.length; + while (end !== ancestor) { + nodes.splice(k, 0, end); + end = end.parent; + } + return nodes; +} + +function leastCommonAncestor(a, b) { + if (a === b) return a; + var aNodes = a.ancestors(), + bNodes = b.ancestors(), + c = null; + a = aNodes.pop(); + b = bNodes.pop(); + while (a === b) { + c = a; + a = aNodes.pop(); + b = bNodes.pop(); + } + return c; +} + +function node_ancestors() { + var node = this, nodes = [node]; + while (node = node.parent) { + nodes.push(node); + } + return nodes; +} + +function node_descendants() { + return Array.from(this); +} + +function node_leaves() { + var leaves = []; + this.eachBefore(function(node) { + if (!node.children) { + leaves.push(node); + } + }); + return leaves; +} + +function node_links() { + var root = this, links = []; + root.each(function(node) { + if (node !== root) { // Don’t include the root’s parent, if any. + links.push({source: node.parent, target: node}); + } + }); + return links; +} + +function* node_iterator() { + var node = this, current, next = [node], children, i, n; + do { + current = next.reverse(), next = []; + while (node = current.pop()) { + yield node; + if (children = node.children) { + for (i = 0, n = children.length; i < n; ++i) { + next.push(children[i]); + } + } + } + } while (next.length); +} + +function hierarchy(data, children) { + if (data instanceof Map) { + data = [undefined, data]; + if (children === undefined) children = mapChildren; + } else if (children === undefined) { + children = objectChildren; + } + + var root = new Node$1(data), + node, + nodes = [root], + child, + childs, + i, + n; + + while (node = nodes.pop()) { + if ((childs = children(node.data)) && (n = (childs = Array.from(childs)).length)) { + node.children = childs; + for (i = n - 1; i >= 0; --i) { + nodes.push(child = childs[i] = new Node$1(childs[i])); + child.parent = node; + child.depth = node.depth + 1; + } + } + } + + return root.eachBefore(computeHeight); +} + +function node_copy() { + return hierarchy(this).eachBefore(copyData); +} + +function objectChildren(d) { + return d.children; +} + +function mapChildren(d) { + return Array.isArray(d) ? d[1] : null; +} + +function copyData(node) { + if (node.data.value !== undefined) node.value = node.data.value; + node.data = node.data.data; +} + +function computeHeight(node) { + var height = 0; + do node.height = height; + while ((node = node.parent) && (node.height < ++height)); +} + +function Node$1(data) { + this.data = data; + this.depth = + this.height = 0; + this.parent = null; +} + +Node$1.prototype = hierarchy.prototype = { + constructor: Node$1, + count: node_count, + each: node_each, + eachAfter: node_eachAfter, + eachBefore: node_eachBefore, + find: node_find, + sum: node_sum, + sort: node_sort, + path: node_path, + ancestors: node_ancestors, + descendants: node_descendants, + leaves: node_leaves, + links: node_links, + copy: node_copy, + [Symbol.iterator]: node_iterator +}; + +function optional(f) { + return f == null ? null : required(f); +} + +function required(f) { + if (typeof f !== "function") throw new Error; + return f; +} + +function constantZero() { + return 0; +} + +function constant(x) { + return function() { + return x; + }; +} + +// https://en.wikipedia.org/wiki/Linear_congruential_generator#Parameters_in_common_use +const a = 1664525; +const c = 1013904223; +const m = 4294967296; // 2^32 + +function lcg() { + let s = 1; + return () => (s = (a * s + c) % m) / m; +} + +function array(x) { + return typeof x === "object" && "length" in x + ? x // Array, TypedArray, NodeList, array-like + : Array.from(x); // Map, Set, iterable, string, or anything else +} + +function shuffle(array, random) { + let m = array.length, + t, + i; + + while (m) { + i = random() * m-- | 0; + t = array[m]; + array[m] = array[i]; + array[i] = t; + } + + return array; +} + +function enclose(circles) { + return packEncloseRandom(circles, lcg()); +} + +function packEncloseRandom(circles, random) { + var i = 0, n = (circles = shuffle(Array.from(circles), random)).length, B = [], p, e; + + while (i < n) { + p = circles[i]; + if (e && enclosesWeak(e, p)) ++i; + else e = encloseBasis(B = extendBasis(B, p)), i = 0; + } + + return e; +} + +function extendBasis(B, p) { + var i, j; + + if (enclosesWeakAll(p, B)) return [p]; + + // If we get here then B must have at least one element. + for (i = 0; i < B.length; ++i) { + if (enclosesNot(p, B[i]) + && enclosesWeakAll(encloseBasis2(B[i], p), B)) { + return [B[i], p]; + } + } + + // If we get here then B must have at least two elements. + for (i = 0; i < B.length - 1; ++i) { + for (j = i + 1; j < B.length; ++j) { + if (enclosesNot(encloseBasis2(B[i], B[j]), p) + && enclosesNot(encloseBasis2(B[i], p), B[j]) + && enclosesNot(encloseBasis2(B[j], p), B[i]) + && enclosesWeakAll(encloseBasis3(B[i], B[j], p), B)) { + return [B[i], B[j], p]; + } + } + } + + // If we get here then something is very wrong. + throw new Error; +} + +function enclosesNot(a, b) { + var dr = a.r - b.r, dx = b.x - a.x, dy = b.y - a.y; + return dr < 0 || dr * dr < dx * dx + dy * dy; +} + +function enclosesWeak(a, b) { + var dr = a.r - b.r + Math.max(a.r, b.r, 1) * 1e-9, dx = b.x - a.x, dy = b.y - a.y; + return dr > 0 && dr * dr > dx * dx + dy * dy; +} + +function enclosesWeakAll(a, B) { + for (var i = 0; i < B.length; ++i) { + if (!enclosesWeak(a, B[i])) { + return false; + } + } + return true; +} + +function encloseBasis(B) { + switch (B.length) { + case 1: return encloseBasis1(B[0]); + case 2: return encloseBasis2(B[0], B[1]); + case 3: return encloseBasis3(B[0], B[1], B[2]); + } +} + +function encloseBasis1(a) { + return { + x: a.x, + y: a.y, + r: a.r + }; +} + +function encloseBasis2(a, b) { + var x1 = a.x, y1 = a.y, r1 = a.r, + x2 = b.x, y2 = b.y, r2 = b.r, + x21 = x2 - x1, y21 = y2 - y1, r21 = r2 - r1, + l = Math.sqrt(x21 * x21 + y21 * y21); + return { + x: (x1 + x2 + x21 / l * r21) / 2, + y: (y1 + y2 + y21 / l * r21) / 2, + r: (l + r1 + r2) / 2 + }; +} + +function encloseBasis3(a, b, c) { + var x1 = a.x, y1 = a.y, r1 = a.r, + x2 = b.x, y2 = b.y, r2 = b.r, + x3 = c.x, y3 = c.y, r3 = c.r, + a2 = x1 - x2, + a3 = x1 - x3, + b2 = y1 - y2, + b3 = y1 - y3, + c2 = r2 - r1, + c3 = r3 - r1, + d1 = x1 * x1 + y1 * y1 - r1 * r1, + d2 = d1 - x2 * x2 - y2 * y2 + r2 * r2, + d3 = d1 - x3 * x3 - y3 * y3 + r3 * r3, + ab = a3 * b2 - a2 * b3, + xa = (b2 * d3 - b3 * d2) / (ab * 2) - x1, + xb = (b3 * c2 - b2 * c3) / ab, + ya = (a3 * d2 - a2 * d3) / (ab * 2) - y1, + yb = (a2 * c3 - a3 * c2) / ab, + A = xb * xb + yb * yb - 1, + B = 2 * (r1 + xa * xb + ya * yb), + C = xa * xa + ya * ya - r1 * r1, + r = -(Math.abs(A) > 1e-6 ? (B + Math.sqrt(B * B - 4 * A * C)) / (2 * A) : C / B); + return { + x: x1 + xa + xb * r, + y: y1 + ya + yb * r, + r: r + }; +} + +function place(b, a, c) { + var dx = b.x - a.x, x, a2, + dy = b.y - a.y, y, b2, + d2 = dx * dx + dy * dy; + if (d2) { + a2 = a.r + c.r, a2 *= a2; + b2 = b.r + c.r, b2 *= b2; + if (a2 > b2) { + x = (d2 + b2 - a2) / (2 * d2); + y = Math.sqrt(Math.max(0, b2 / d2 - x * x)); + c.x = b.x - x * dx - y * dy; + c.y = b.y - x * dy + y * dx; + } else { + x = (d2 + a2 - b2) / (2 * d2); + y = Math.sqrt(Math.max(0, a2 / d2 - x * x)); + c.x = a.x + x * dx - y * dy; + c.y = a.y + x * dy + y * dx; + } + } else { + c.x = a.x + c.r; + c.y = a.y; + } +} + +function intersects(a, b) { + var dr = a.r + b.r - 1e-6, dx = b.x - a.x, dy = b.y - a.y; + return dr > 0 && dr * dr > dx * dx + dy * dy; +} + +function score(node) { + var a = node._, + b = node.next._, + ab = a.r + b.r, + dx = (a.x * b.r + b.x * a.r) / ab, + dy = (a.y * b.r + b.y * a.r) / ab; + return dx * dx + dy * dy; +} + +function Node(circle) { + this._ = circle; + this.next = null; + this.previous = null; +} + +function packSiblingsRandom(circles, random) { + if (!(n = (circles = array(circles)).length)) return 0; + + var a, b, c, n, aa, ca, i, j, k, sj, sk; + + // Place the first circle. + a = circles[0], a.x = 0, a.y = 0; + if (!(n > 1)) return a.r; + + // Place the second circle. + b = circles[1], a.x = -b.r, b.x = a.r, b.y = 0; + if (!(n > 2)) return a.r + b.r; + + // Place the third circle. + place(b, a, c = circles[2]); + + // Initialize the front-chain using the first three circles a, b and c. + a = new Node(a), b = new Node(b), c = new Node(c); + a.next = c.previous = b; + b.next = a.previous = c; + c.next = b.previous = a; + + // Attempt to place each remaining circle… + pack: for (i = 3; i < n; ++i) { + place(a._, b._, c = circles[i]), c = new Node(c); + + // Find the closest intersecting circle on the front-chain, if any. + // “Closeness” is determined by linear distance along the front-chain. + // “Ahead” or “behind” is likewise determined by linear distance. + j = b.next, k = a.previous, sj = b._.r, sk = a._.r; + do { + if (sj <= sk) { + if (intersects(j._, c._)) { + b = j, a.next = b, b.previous = a, --i; + continue pack; + } + sj += j._.r, j = j.next; + } else { + if (intersects(k._, c._)) { + a = k, a.next = b, b.previous = a, --i; + continue pack; + } + sk += k._.r, k = k.previous; + } + } while (j !== k.next); + + // Success! Insert the new circle c between a and b. + c.previous = a, c.next = b, a.next = b.previous = b = c; + + // Compute the new closest circle pair to the centroid. + aa = score(a); + while ((c = c.next) !== b) { + if ((ca = score(c)) < aa) { + a = c, aa = ca; + } + } + b = a.next; + } + + // Compute the enclosing circle of the front chain. + a = [b._], c = b; while ((c = c.next) !== b) a.push(c._); c = packEncloseRandom(a, random); + + // Translate the circles to put the enclosing circle around the origin. + for (i = 0; i < n; ++i) a = circles[i], a.x -= c.x, a.y -= c.y; + + return c.r; +} + +function siblings(circles) { + packSiblingsRandom(circles, lcg()); + return circles; +} + +function defaultRadius(d) { + return Math.sqrt(d.value); +} + +function index$1() { + var radius = null, + dx = 1, + dy = 1, + padding = constantZero; + + function pack(root) { + const random = lcg(); + root.x = dx / 2, root.y = dy / 2; + if (radius) { + root.eachBefore(radiusLeaf(radius)) + .eachAfter(packChildrenRandom(padding, 0.5, random)) + .eachBefore(translateChild(1)); + } else { + root.eachBefore(radiusLeaf(defaultRadius)) + .eachAfter(packChildrenRandom(constantZero, 1, random)) + .eachAfter(packChildrenRandom(padding, root.r / Math.min(dx, dy), random)) + .eachBefore(translateChild(Math.min(dx, dy) / (2 * root.r))); + } + return root; + } + + pack.radius = function(x) { + return arguments.length ? (radius = optional(x), pack) : radius; + }; + + pack.size = function(x) { + return arguments.length ? (dx = +x[0], dy = +x[1], pack) : [dx, dy]; + }; + + pack.padding = function(x) { + return arguments.length ? (padding = typeof x === "function" ? x : constant(+x), pack) : padding; + }; + + return pack; +} + +function radiusLeaf(radius) { + return function(node) { + if (!node.children) { + node.r = Math.max(0, +radius(node) || 0); + } + }; +} + +function packChildrenRandom(padding, k, random) { + return function(node) { + if (children = node.children) { + var children, + i, + n = children.length, + r = padding(node) * k || 0, + e; + + if (r) for (i = 0; i < n; ++i) children[i].r += r; + e = packSiblingsRandom(children, random); + if (r) for (i = 0; i < n; ++i) children[i].r -= r; + node.r = e + r; + } + }; +} + +function translateChild(k) { + return function(node) { + var parent = node.parent; + node.r *= k; + if (parent) { + node.x = parent.x + k * node.x; + node.y = parent.y + k * node.y; + } + }; +} + +function roundNode(node) { + node.x0 = Math.round(node.x0); + node.y0 = Math.round(node.y0); + node.x1 = Math.round(node.x1); + node.y1 = Math.round(node.y1); +} + +function treemapDice(parent, x0, y0, x1, y1) { + var nodes = parent.children, + node, + i = -1, + n = nodes.length, + k = parent.value && (x1 - x0) / parent.value; + + while (++i < n) { + node = nodes[i], node.y0 = y0, node.y1 = y1; + node.x0 = x0, node.x1 = x0 += node.value * k; + } +} + +function partition() { + var dx = 1, + dy = 1, + padding = 0, + round = false; + + function partition(root) { + var n = root.height + 1; + root.x0 = + root.y0 = padding; + root.x1 = dx; + root.y1 = dy / n; + root.eachBefore(positionNode(dy, n)); + if (round) root.eachBefore(roundNode); + return root; + } + + function positionNode(dy, n) { + return function(node) { + if (node.children) { + treemapDice(node, node.x0, dy * (node.depth + 1) / n, node.x1, dy * (node.depth + 2) / n); + } + var x0 = node.x0, + y0 = node.y0, + x1 = node.x1 - padding, + y1 = node.y1 - padding; + if (x1 < x0) x0 = x1 = (x0 + x1) / 2; + if (y1 < y0) y0 = y1 = (y0 + y1) / 2; + node.x0 = x0; + node.y0 = y0; + node.x1 = x1; + node.y1 = y1; + }; + } + + partition.round = function(x) { + return arguments.length ? (round = !!x, partition) : round; + }; + + partition.size = function(x) { + return arguments.length ? (dx = +x[0], dy = +x[1], partition) : [dx, dy]; + }; + + partition.padding = function(x) { + return arguments.length ? (padding = +x, partition) : padding; + }; + + return partition; +} + +var preroot = {depth: -1}, + ambiguous = {}, + imputed = {}; + +function defaultId(d) { + return d.id; +} + +function defaultParentId(d) { + return d.parentId; +} + +function stratify() { + var id = defaultId, + parentId = defaultParentId, + path; + + function stratify(data) { + var nodes = Array.from(data), + currentId = id, + currentParentId = parentId, + n, + d, + i, + root, + parent, + node, + nodeId, + nodeKey, + nodeByKey = new Map; + + if (path != null) { + const I = nodes.map((d, i) => normalize(path(d, i, data))); + const P = I.map(parentof); + const S = new Set(I).add(""); + for (const i of P) { + if (!S.has(i)) { + S.add(i); + I.push(i); + P.push(parentof(i)); + nodes.push(imputed); + } + } + currentId = (_, i) => I[i]; + currentParentId = (_, i) => P[i]; + } + + for (i = 0, n = nodes.length; i < n; ++i) { + d = nodes[i], node = nodes[i] = new Node$1(d); + if ((nodeId = currentId(d, i, data)) != null && (nodeId += "")) { + nodeKey = node.id = nodeId; + nodeByKey.set(nodeKey, nodeByKey.has(nodeKey) ? ambiguous : node); + } + if ((nodeId = currentParentId(d, i, data)) != null && (nodeId += "")) { + node.parent = nodeId; + } + } + + for (i = 0; i < n; ++i) { + node = nodes[i]; + if (nodeId = node.parent) { + parent = nodeByKey.get(nodeId); + if (!parent) throw new Error("missing: " + nodeId); + if (parent === ambiguous) throw new Error("ambiguous: " + nodeId); + if (parent.children) parent.children.push(node); + else parent.children = [node]; + node.parent = parent; + } else { + if (root) throw new Error("multiple roots"); + root = node; + } + } + + if (!root) throw new Error("no root"); + + // When imputing internal nodes, only introduce roots if needed. + // Then replace the imputed marker data with null. + if (path != null) { + while (root.data === imputed && root.children.length === 1) { + root = root.children[0], --n; + } + for (let i = nodes.length - 1; i >= 0; --i) { + node = nodes[i]; + if (node.data !== imputed) break; + node.data = null; + } + } + + root.parent = preroot; + root.eachBefore(function(node) { node.depth = node.parent.depth + 1; --n; }).eachBefore(computeHeight); + root.parent = null; + if (n > 0) throw new Error("cycle"); + + return root; + } + + stratify.id = function(x) { + return arguments.length ? (id = optional(x), stratify) : id; + }; + + stratify.parentId = function(x) { + return arguments.length ? (parentId = optional(x), stratify) : parentId; + }; + + stratify.path = function(x) { + return arguments.length ? (path = optional(x), stratify) : path; + }; + + return stratify; +} + +// To normalize a path, we coerce to a string, strip the trailing slash if any +// (as long as the trailing slash is not immediately preceded by another slash), +// and add leading slash if missing. +function normalize(path) { + path = `${path}`; + let i = path.length; + if (slash(path, i - 1) && !slash(path, i - 2)) path = path.slice(0, -1); + return path[0] === "/" ? path : `/${path}`; +} + +// Walk backwards to find the first slash that is not the leading slash, e.g.: +// "/foo/bar" ⇥ "/foo", "/foo" ⇥ "/", "/" ↦ "". (The root is special-cased +// because the id of the root must be a truthy value.) +function parentof(path) { + let i = path.length; + if (i < 2) return ""; + while (--i > 1) if (slash(path, i)) break; + return path.slice(0, i); +} + +// Slashes can be escaped; to determine whether a slash is a path delimiter, we +// count the number of preceding backslashes escaping the forward slash: an odd +// number indicates an escaped forward slash. +function slash(path, i) { + if (path[i] === "/") { + let k = 0; + while (i > 0 && path[--i] === "\\") ++k; + if ((k & 1) === 0) return true; + } + return false; +} + +function defaultSeparation(a, b) { + return a.parent === b.parent ? 1 : 2; +} + +// function radialSeparation(a, b) { +// return (a.parent === b.parent ? 1 : 2) / a.depth; +// } + +// This function is used to traverse the left contour of a subtree (or +// subforest). It returns the successor of v on this contour. This successor is +// either given by the leftmost child of v or by the thread of v. The function +// returns null if and only if v is on the highest level of its subtree. +function nextLeft(v) { + var children = v.children; + return children ? children[0] : v.t; +} + +// This function works analogously to nextLeft. +function nextRight(v) { + var children = v.children; + return children ? children[children.length - 1] : v.t; +} + +// Shifts the current subtree rooted at w+. This is done by increasing +// prelim(w+) and mod(w+) by shift. +function moveSubtree(wm, wp, shift) { + var change = shift / (wp.i - wm.i); + wp.c -= change; + wp.s += shift; + wm.c += change; + wp.z += shift; + wp.m += shift; +} + +// All other shifts, applied to the smaller subtrees between w- and w+, are +// performed by this function. To prepare the shifts, we have to adjust +// change(w+), shift(w+), and change(w-). +function executeShifts(v) { + var shift = 0, + change = 0, + children = v.children, + i = children.length, + w; + while (--i >= 0) { + w = children[i]; + w.z += shift; + w.m += shift; + shift += w.s + (change += w.c); + } +} + +// If vi-’s ancestor is a sibling of v, returns vi-’s ancestor. Otherwise, +// returns the specified (default) ancestor. +function nextAncestor(vim, v, ancestor) { + return vim.a.parent === v.parent ? vim.a : ancestor; +} + +function TreeNode(node, i) { + this._ = node; + this.parent = null; + this.children = null; + this.A = null; // default ancestor + this.a = this; // ancestor + this.z = 0; // prelim + this.m = 0; // mod + this.c = 0; // change + this.s = 0; // shift + this.t = null; // thread + this.i = i; // number +} + +TreeNode.prototype = Object.create(Node$1.prototype); + +function treeRoot(root) { + var tree = new TreeNode(root, 0), + node, + nodes = [tree], + child, + children, + i, + n; + + while (node = nodes.pop()) { + if (children = node._.children) { + node.children = new Array(n = children.length); + for (i = n - 1; i >= 0; --i) { + nodes.push(child = node.children[i] = new TreeNode(children[i], i)); + child.parent = node; + } + } + } + + (tree.parent = new TreeNode(null, 0)).children = [tree]; + return tree; +} + +// Node-link tree diagram using the Reingold-Tilford "tidy" algorithm +function tree() { + var separation = defaultSeparation, + dx = 1, + dy = 1, + nodeSize = null; + + function tree(root) { + var t = treeRoot(root); + + // Compute the layout using Buchheim et al.’s algorithm. + t.eachAfter(firstWalk), t.parent.m = -t.z; + t.eachBefore(secondWalk); + + // If a fixed node size is specified, scale x and y. + if (nodeSize) root.eachBefore(sizeNode); + + // If a fixed tree size is specified, scale x and y based on the extent. + // Compute the left-most, right-most, and depth-most nodes for extents. + else { + var left = root, + right = root, + bottom = root; + root.eachBefore(function(node) { + if (node.x < left.x) left = node; + if (node.x > right.x) right = node; + if (node.depth > bottom.depth) bottom = node; + }); + var s = left === right ? 1 : separation(left, right) / 2, + tx = s - left.x, + kx = dx / (right.x + s + tx), + ky = dy / (bottom.depth || 1); + root.eachBefore(function(node) { + node.x = (node.x + tx) * kx; + node.y = node.depth * ky; + }); + } + + return root; + } + + // Computes a preliminary x-coordinate for v. Before that, FIRST WALK is + // applied recursively to the children of v, as well as the function + // APPORTION. After spacing out the children by calling EXECUTE SHIFTS, the + // node v is placed to the midpoint of its outermost children. + function firstWalk(v) { + var children = v.children, + siblings = v.parent.children, + w = v.i ? siblings[v.i - 1] : null; + if (children) { + executeShifts(v); + var midpoint = (children[0].z + children[children.length - 1].z) / 2; + if (w) { + v.z = w.z + separation(v._, w._); + v.m = v.z - midpoint; + } else { + v.z = midpoint; + } + } else if (w) { + v.z = w.z + separation(v._, w._); + } + v.parent.A = apportion(v, w, v.parent.A || siblings[0]); + } + + // Computes all real x-coordinates by summing up the modifiers recursively. + function secondWalk(v) { + v._.x = v.z + v.parent.m; + v.m += v.parent.m; + } + + // The core of the algorithm. Here, a new subtree is combined with the + // previous subtrees. Threads are used to traverse the inside and outside + // contours of the left and right subtree up to the highest common level. The + // vertices used for the traversals are vi+, vi-, vo-, and vo+, where the + // superscript o means outside and i means inside, the subscript - means left + // subtree and + means right subtree. For summing up the modifiers along the + // contour, we use respective variables si+, si-, so-, and so+. Whenever two + // nodes of the inside contours conflict, we compute the left one of the + // greatest uncommon ancestors using the function ANCESTOR and call MOVE + // SUBTREE to shift the subtree and prepare the shifts of smaller subtrees. + // Finally, we add a new thread (if necessary). + function apportion(v, w, ancestor) { + if (w) { + var vip = v, + vop = v, + vim = w, + vom = vip.parent.children[0], + sip = vip.m, + sop = vop.m, + sim = vim.m, + som = vom.m, + shift; + while (vim = nextRight(vim), vip = nextLeft(vip), vim && vip) { + vom = nextLeft(vom); + vop = nextRight(vop); + vop.a = v; + shift = vim.z + sim - vip.z - sip + separation(vim._, vip._); + if (shift > 0) { + moveSubtree(nextAncestor(vim, v, ancestor), v, shift); + sip += shift; + sop += shift; + } + sim += vim.m; + sip += vip.m; + som += vom.m; + sop += vop.m; + } + if (vim && !nextRight(vop)) { + vop.t = vim; + vop.m += sim - sop; + } + if (vip && !nextLeft(vom)) { + vom.t = vip; + vom.m += sip - som; + ancestor = v; + } + } + return ancestor; + } + + function sizeNode(node) { + node.x *= dx; + node.y = node.depth * dy; + } + + tree.separation = function(x) { + return arguments.length ? (separation = x, tree) : separation; + }; + + tree.size = function(x) { + return arguments.length ? (nodeSize = false, dx = +x[0], dy = +x[1], tree) : (nodeSize ? null : [dx, dy]); + }; + + tree.nodeSize = function(x) { + return arguments.length ? (nodeSize = true, dx = +x[0], dy = +x[1], tree) : (nodeSize ? [dx, dy] : null); + }; + + return tree; +} + +function treemapSlice(parent, x0, y0, x1, y1) { + var nodes = parent.children, + node, + i = -1, + n = nodes.length, + k = parent.value && (y1 - y0) / parent.value; + + while (++i < n) { + node = nodes[i], node.x0 = x0, node.x1 = x1; + node.y0 = y0, node.y1 = y0 += node.value * k; + } +} + +var phi = (1 + Math.sqrt(5)) / 2; + +function squarifyRatio(ratio, parent, x0, y0, x1, y1) { + var rows = [], + nodes = parent.children, + row, + nodeValue, + i0 = 0, + i1 = 0, + n = nodes.length, + dx, dy, + value = parent.value, + sumValue, + minValue, + maxValue, + newRatio, + minRatio, + alpha, + beta; + + while (i0 < n) { + dx = x1 - x0, dy = y1 - y0; + + // Find the next non-empty node. + do sumValue = nodes[i1++].value; while (!sumValue && i1 < n); + minValue = maxValue = sumValue; + alpha = Math.max(dy / dx, dx / dy) / (value * ratio); + beta = sumValue * sumValue * alpha; + minRatio = Math.max(maxValue / beta, beta / minValue); + + // Keep adding nodes while the aspect ratio maintains or improves. + for (; i1 < n; ++i1) { + sumValue += nodeValue = nodes[i1].value; + if (nodeValue < minValue) minValue = nodeValue; + if (nodeValue > maxValue) maxValue = nodeValue; + beta = sumValue * sumValue * alpha; + newRatio = Math.max(maxValue / beta, beta / minValue); + if (newRatio > minRatio) { sumValue -= nodeValue; break; } + minRatio = newRatio; + } + + // Position and record the row orientation. + rows.push(row = {value: sumValue, dice: dx < dy, children: nodes.slice(i0, i1)}); + if (row.dice) treemapDice(row, x0, y0, x1, value ? y0 += dy * sumValue / value : y1); + else treemapSlice(row, x0, y0, value ? x0 += dx * sumValue / value : x1, y1); + value -= sumValue, i0 = i1; + } + + return rows; +} + +var squarify = (function custom(ratio) { + + function squarify(parent, x0, y0, x1, y1) { + squarifyRatio(ratio, parent, x0, y0, x1, y1); + } + + squarify.ratio = function(x) { + return custom((x = +x) > 1 ? x : 1); + }; + + return squarify; +})(phi); + +function index() { + var tile = squarify, + round = false, + dx = 1, + dy = 1, + paddingStack = [0], + paddingInner = constantZero, + paddingTop = constantZero, + paddingRight = constantZero, + paddingBottom = constantZero, + paddingLeft = constantZero; + + function treemap(root) { + root.x0 = + root.y0 = 0; + root.x1 = dx; + root.y1 = dy; + root.eachBefore(positionNode); + paddingStack = [0]; + if (round) root.eachBefore(roundNode); + return root; + } + + function positionNode(node) { + var p = paddingStack[node.depth], + x0 = node.x0 + p, + y0 = node.y0 + p, + x1 = node.x1 - p, + y1 = node.y1 - p; + if (x1 < x0) x0 = x1 = (x0 + x1) / 2; + if (y1 < y0) y0 = y1 = (y0 + y1) / 2; + node.x0 = x0; + node.y0 = y0; + node.x1 = x1; + node.y1 = y1; + if (node.children) { + p = paddingStack[node.depth + 1] = paddingInner(node) / 2; + x0 += paddingLeft(node) - p; + y0 += paddingTop(node) - p; + x1 -= paddingRight(node) - p; + y1 -= paddingBottom(node) - p; + if (x1 < x0) x0 = x1 = (x0 + x1) / 2; + if (y1 < y0) y0 = y1 = (y0 + y1) / 2; + tile(node, x0, y0, x1, y1); + } + } + + treemap.round = function(x) { + return arguments.length ? (round = !!x, treemap) : round; + }; + + treemap.size = function(x) { + return arguments.length ? (dx = +x[0], dy = +x[1], treemap) : [dx, dy]; + }; + + treemap.tile = function(x) { + return arguments.length ? (tile = required(x), treemap) : tile; + }; + + treemap.padding = function(x) { + return arguments.length ? treemap.paddingInner(x).paddingOuter(x) : treemap.paddingInner(); + }; + + treemap.paddingInner = function(x) { + return arguments.length ? (paddingInner = typeof x === "function" ? x : constant(+x), treemap) : paddingInner; + }; + + treemap.paddingOuter = function(x) { + return arguments.length ? treemap.paddingTop(x).paddingRight(x).paddingBottom(x).paddingLeft(x) : treemap.paddingTop(); + }; + + treemap.paddingTop = function(x) { + return arguments.length ? (paddingTop = typeof x === "function" ? x : constant(+x), treemap) : paddingTop; + }; + + treemap.paddingRight = function(x) { + return arguments.length ? (paddingRight = typeof x === "function" ? x : constant(+x), treemap) : paddingRight; + }; + + treemap.paddingBottom = function(x) { + return arguments.length ? (paddingBottom = typeof x === "function" ? x : constant(+x), treemap) : paddingBottom; + }; + + treemap.paddingLeft = function(x) { + return arguments.length ? (paddingLeft = typeof x === "function" ? x : constant(+x), treemap) : paddingLeft; + }; + + return treemap; +} + +function binary(parent, x0, y0, x1, y1) { + var nodes = parent.children, + i, n = nodes.length, + sum, sums = new Array(n + 1); + + for (sums[0] = sum = i = 0; i < n; ++i) { + sums[i + 1] = sum += nodes[i].value; + } + + partition(0, n, parent.value, x0, y0, x1, y1); + + function partition(i, j, value, x0, y0, x1, y1) { + if (i >= j - 1) { + var node = nodes[i]; + node.x0 = x0, node.y0 = y0; + node.x1 = x1, node.y1 = y1; + return; + } + + var valueOffset = sums[i], + valueTarget = (value / 2) + valueOffset, + k = i + 1, + hi = j - 1; + + while (k < hi) { + var mid = k + hi >>> 1; + if (sums[mid] < valueTarget) k = mid + 1; + else hi = mid; + } + + if ((valueTarget - sums[k - 1]) < (sums[k] - valueTarget) && i + 1 < k) --k; + + var valueLeft = sums[k] - valueOffset, + valueRight = value - valueLeft; + + if ((x1 - x0) > (y1 - y0)) { + var xk = value ? (x0 * valueRight + x1 * valueLeft) / value : x1; + partition(i, k, valueLeft, x0, y0, xk, y1); + partition(k, j, valueRight, xk, y0, x1, y1); + } else { + var yk = value ? (y0 * valueRight + y1 * valueLeft) / value : y1; + partition(i, k, valueLeft, x0, y0, x1, yk); + partition(k, j, valueRight, x0, yk, x1, y1); + } + } +} + +function sliceDice(parent, x0, y0, x1, y1) { + (parent.depth & 1 ? treemapSlice : treemapDice)(parent, x0, y0, x1, y1); +} + +var resquarify = (function custom(ratio) { + + function resquarify(parent, x0, y0, x1, y1) { + if ((rows = parent._squarify) && (rows.ratio === ratio)) { + var rows, + row, + nodes, + i, + j = -1, + n, + m = rows.length, + value = parent.value; + + while (++j < m) { + row = rows[j], nodes = row.children; + for (i = row.value = 0, n = nodes.length; i < n; ++i) row.value += nodes[i].value; + if (row.dice) treemapDice(row, x0, y0, x1, value ? y0 += (y1 - y0) * row.value / value : y1); + else treemapSlice(row, x0, y0, value ? x0 += (x1 - x0) * row.value / value : x1, y1); + value -= row.value; + } + } else { + parent._squarify = rows = squarifyRatio(ratio, parent, x0, y0, x1, y1); + rows.ratio = ratio; + } + } + + resquarify.ratio = function(x) { + return custom((x = +x) > 1 ? x : 1); + }; + + return resquarify; +})(phi); + +exports.Node = Node$1; +exports.cluster = cluster; +exports.hierarchy = hierarchy; +exports.pack = index$1; +exports.packEnclose = enclose; +exports.packSiblings = siblings; +exports.partition = partition; +exports.stratify = stratify; +exports.tree = tree; +exports.treemap = index; +exports.treemapBinary = binary; +exports.treemapDice = treemapDice; +exports.treemapResquarify = resquarify; +exports.treemapSlice = treemapSlice; +exports.treemapSliceDice = sliceDice; +exports.treemapSquarify = squarify; + +Object.defineProperty(exports, '__esModule', { value: true }); + +})); diff --git a/frontend/node_modules/d3-hierarchy/dist/d3-hierarchy.min.js b/frontend/node_modules/d3-hierarchy/dist/d3-hierarchy.min.js new file mode 100644 index 0000000..d91fffb --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/dist/d3-hierarchy.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-hierarchy/ v3.1.2 Copyright 2010-2021 Mike Bostock +!function(n,r){"object"==typeof exports&&"undefined"!=typeof module?r(exports):"function"==typeof define&&define.amd?define(["exports"],r):r((n="undefined"!=typeof globalThis?globalThis:n||self).d3=n.d3||{})}(this,(function(n){"use strict";function r(n,r){return n.parent===r.parent?1:2}function t(n,r){return n+r.x}function e(n,r){return Math.max(n,r.y)}function i(n){var r=0,t=n.children,e=t&&t.length;if(e)for(;--e>=0;)r+=t[e].value;else r=1;n.value=r}function u(n,r){n instanceof Map?(n=[void 0,n],void 0===r&&(r=f)):void 0===r&&(r=o);for(var t,e,i,u,a,l=new h(n),p=[l];t=p.pop();)if((i=r(t.data))&&(a=(i=Array.from(i)).length))for(t.children=i,u=a-1;u>=0;--u)p.push(e=i[u]=new h(i[u])),e.parent=t,e.depth=t.depth+1;return l.eachBefore(c)}function o(n){return n.children}function f(n){return Array.isArray(n)?n[1]:null}function a(n){void 0!==n.data.value&&(n.value=n.data.value),n.data=n.data.data}function c(n){var r=0;do{n.height=r}while((n=n.parent)&&n.height<++r)}function h(n){this.data=n,this.depth=this.height=0,this.parent=null}function l(n){return null==n?null:p(n)}function p(n){if("function"!=typeof n)throw new Error;return n}function d(){return 0}function s(n){return function(){return n}}h.prototype=u.prototype={constructor:h,count:function(){return this.eachAfter(i)},each:function(n,r){let t=-1;for(const e of this)n.call(r,e,++t,this);return this},eachAfter:function(n,r){for(var t,e,i,u=this,o=[u],f=[],a=-1;u=o.pop();)if(f.push(u),t=u.children)for(e=0,i=t.length;e=0;--e)u.push(t[e]);return this},find:function(n,r){let t=-1;for(const e of this)if(n.call(r,e,++t,this))return e},sum:function(n){return this.eachAfter((function(r){for(var t=+n(r.data)||0,e=r.children,i=e&&e.length;--i>=0;)t+=e[i].value;r.value=t}))},sort:function(n){return this.eachBefore((function(r){r.children&&r.children.sort(n)}))},path:function(n){for(var r=this,t=function(n,r){if(n===r)return n;var t=n.ancestors(),e=r.ancestors(),i=null;n=t.pop(),r=e.pop();for(;n===r;)i=n,n=t.pop(),r=e.pop();return i}(r,n),e=[r];r!==t;)r=r.parent,e.push(r);for(var i=e.length;n!==t;)e.splice(i,0,n),n=n.parent;return e},ancestors:function(){for(var n=this,r=[n];n=n.parent;)r.push(n);return r},descendants:function(){return Array.from(this)},leaves:function(){var n=[];return this.eachBefore((function(r){r.children||n.push(r)})),n},links:function(){var n=this,r=[];return n.each((function(t){t!==n&&r.push({source:t.parent,target:t})})),r},copy:function(){return u(this).eachBefore(a)},[Symbol.iterator]:function*(){var n,r,t,e,i=this,u=[i];do{for(n=u.reverse(),u=[];i=n.pop();)if(yield i,r=i.children)for(t=0,e=r.length;t(n=(1664525*n+1013904223)%v)/v}function y(n,r){for(var t,e,i=0,u=(n=function(n,r){let t,e,i=n.length;for(;i;)e=r()*i--|0,t=n[i],n[i]=n[e],n[e]=t;return n}(Array.from(n),r)).length,o=[];i0&&t*t>e*e+i*i}function _(n,r){for(var t=0;t1e-6?(q+Math.sqrt(q*q-4*b*E))/(2*b):E/q);return{x:e+M+z*S,y:i+B+A*S,r:S}}function A(n,r,t){var e,i,u,o,f=n.x-r.x,a=n.y-r.y,c=f*f+a*a;c?(i=r.r+t.r,i*=i,o=n.r+t.r,i>(o*=o)?(e=(c+o-i)/(2*c),u=Math.sqrt(Math.max(0,o/c-e*e)),t.x=n.x-e*f-u*a,t.y=n.y-e*a+u*f):(e=(c+i-o)/(2*c),u=Math.sqrt(Math.max(0,i/c-e*e)),t.x=r.x+e*f-u*a,t.y=r.y+e*a+u*f)):(t.x=r.x+t.r,t.y=r.y)}function b(n,r){var t=n.r+r.r-1e-6,e=r.x-n.x,i=r.y-n.y;return t>0&&t*t>e*e+i*i}function q(n){var r=n._,t=n.next._,e=r.r+t.r,i=(r.x*t.r+t.x*r.r)/e,u=(r.y*t.r+t.y*r.r)/e;return i*i+u*u}function Node(n){this._=n,this.next=null,this.previous=null}function E(n,r){if(!(o=(t=n,n="object"==typeof t&&"length"in t?t:Array.from(t)).length))return 0;var t,e,i,u,o,f,a,c,h,l,p,d;if((e=n[0]).x=0,e.y=0,!(o>1))return e.r;if(i=n[1],e.x=-i.r,i.x=e.r,i.y=0,!(o>2))return e.r+i.r;A(i,e,u=n[2]),e=new Node(e),i=new Node(i),u=new Node(u),e.next=u.previous=i,i.next=e.previous=u,u.next=i.previous=e;n:for(c=3;c1&&!C(n,r););return n.slice(0,r)}function C(n,r){if("/"===n[r]){let t=0;for(;r>0&&"\\"===n[--r];)++t;if(0==(1&t))return!0}return!1}function F(n,r){return n.parent===r.parent?1:2}function G(n){var r=n.children;return r?r[0]:n.t}function H(n){var r=n.children;return r?r[r.length-1]:n.t}function J(n,r,t){var e=t/(r.i-n.i);r.c-=e,r.s+=t,n.c+=e,r.z+=t,r.m+=t}function K(n,r,t){return n.a.parent===r.parent?n.a:t}function Q(n,r){this._=n,this.parent=null,this.children=null,this.A=null,this.a=this,this.z=0,this.m=0,this.c=0,this.s=0,this.t=null,this.i=r}function U(n,r,t,e,i){for(var u,o=n.children,f=-1,a=o.length,c=n.value&&(i-t)/n.value;++fp&&(p=f),x=h*h*v,(d=Math.max(p/x,x/l))>s){h-=f;break}s=d}y.push(o={value:h,dice:a1?r:1)},t}(V);var Y=function n(r){function t(n,t,e,i,u){if((o=n._squarify)&&o.ratio===r)for(var o,f,a,c,h,l=-1,p=o.length,d=n.value;++l1?r:1)},t}(V);n.Node=h,n.cluster=function(){var n=r,i=1,u=1,o=!1;function f(r){var f,a=0;r.eachAfter((function(r){var i=r.children;i?(r.x=function(n){return n.reduce(t,0)/n.length}(i),r.y=function(n){return 1+n.reduce(e,0)}(i)):(r.x=f?a+=n(r,f):0,r.y=0,f=r)}));var c=function(n){for(var r;r=n.children;)n=r[0];return n}(r),h=function(n){for(var r;r=n.children;)n=r[r.length-1];return n}(r),l=c.x-n(c,h)/2,p=h.x+n(h,c)/2;return r.eachAfter(o?function(n){n.x=(n.x-r.x)*i,n.y=(r.y-n.y)*u}:function(n){n.x=(n.x-l)/(p-l)*i,n.y=(1-(r.y?n.y/r.y:1))*u})}return f.separation=function(r){return arguments.length?(n=r,f):n},f.size=function(n){return arguments.length?(o=!1,i=+n[0],u=+n[1],f):o?null:[i,u]},f.nodeSize=function(n){return arguments.length?(o=!0,i=+n[0],u=+n[1],f):o?[i,u]:null},f},n.hierarchy=u,n.pack=function(){var n=null,r=1,t=1,e=d;function i(i){const u=x();return i.x=r/2,i.y=t/2,n?i.eachBefore(k(n)).eachAfter(I(e,.5,u)).eachBefore(T(1)):i.eachBefore(k(S)).eachAfter(I(d,1,u)).eachAfter(I(e,i.r/Math.min(r,t),u)).eachBefore(T(Math.min(r,t)/(2*i.r))),i}return i.radius=function(r){return arguments.length?(n=l(r),i):n},i.size=function(n){return arguments.length?(r=+n[0],t=+n[1],i):[r,t]},i.padding=function(n){return arguments.length?(e="function"==typeof n?n:s(+n),i):e},i},n.packEnclose=function(n){return y(n,x())},n.packSiblings=function(n){return E(n,x()),n},n.partition=function(){var n=1,r=1,t=0,e=!1;function i(i){var u=i.height+1;return i.x0=i.y0=t,i.x1=n,i.y1=r/u,i.eachBefore(function(n,r){return function(e){e.children&&O(e,e.x0,n*(e.depth+1)/r,e.x1,n*(e.depth+2)/r);var i=e.x0,u=e.y0,o=e.x1-t,f=e.y1-t;ofunction(n){let r=(n=`${n}`).length;C(n,r-1)&&!C(n,r-2)&&(n=n.slice(0,-1));return"/"===n[0]?n:`/${n}`}(n(r,t,e)))),t=r.map(P),i=new Set(r).add("");for(const n of t)i.has(n)||(i.add(n),r.push(n),t.push(P(n)),s.push(L));v=(n,t)=>r[t],x=(n,r)=>t[r]}for(o=0,i=s.length;o=0&&(l=s[n],l.data===L);--n)l.data=null}if(f.parent=R,f.eachBefore((function(n){n.depth=n.parent.depth+1,--i})).eachBefore(c),f.parent=null,i>0)throw new Error("cycle");return f}return e.id=function(n){return arguments.length?(r=l(n),e):r},e.parentId=function(n){return arguments.length?(t=l(n),e):t},e.path=function(r){return arguments.length?(n=l(r),e):n},e},n.tree=function(){var n=F,r=1,t=1,e=null;function i(i){var a=function(n){for(var r,t,e,i,u,o=new Q(n,0),f=[o];r=f.pop();)if(e=r._.children)for(r.children=new Array(u=e.length),i=u-1;i>=0;--i)f.push(t=r.children[i]=new Q(e[i],i)),t.parent=r;return(o.parent=new Q(null,0)).children=[o],o}(i);if(a.eachAfter(u),a.parent.m=-a.z,a.eachBefore(o),e)i.eachBefore(f);else{var c=i,h=i,l=i;i.eachBefore((function(n){n.xh.x&&(h=n),n.depth>l.depth&&(l=n)}));var p=c===h?1:n(c,h)/2,d=p-c.x,s=r/(h.x+p+d),v=t/(l.depth||1);i.eachBefore((function(n){n.x=(n.x+d)*s,n.y=n.depth*v}))}return i}function u(r){var t=r.children,e=r.parent.children,i=r.i?e[r.i-1]:null;if(t){!function(n){for(var r,t=0,e=0,i=n.children,u=i.length;--u>=0;)(r=i[u]).z+=t,r.m+=t,t+=r.s+(e+=r.c)}(r);var u=(t[0].z+t[t.length-1].z)/2;i?(r.z=i.z+n(r._,i._),r.m=r.z-u):r.z=u}else i&&(r.z=i.z+n(r._,i._));r.parent.A=function(r,t,e){if(t){for(var i,u=r,o=r,f=t,a=u.parent.children[0],c=u.m,h=o.m,l=f.m,p=a.m;f=H(f),u=G(u),f&&u;)a=G(a),(o=H(o)).a=r,(i=f.z+l-u.z-c+n(f._,u._))>0&&(J(K(f,r,e),r,i),c+=i,h+=i),l+=f.m,c+=u.m,p+=a.m,h+=o.m;f&&!H(o)&&(o.t=f,o.m+=l-h),u&&!G(a)&&(a.t=u,a.m+=c-p,e=r)}return e}(r,i,r.parent.A||e[0])}function o(n){n._.x=n.z+n.parent.m,n.m+=n.parent.m}function f(n){n.x*=r,n.y=n.depth*t}return i.separation=function(r){return arguments.length?(n=r,i):n},i.size=function(n){return arguments.length?(e=!1,r=+n[0],t=+n[1],i):e?null:[r,t]},i.nodeSize=function(n){return arguments.length?(e=!0,r=+n[0],t=+n[1],i):e?[r,t]:null},i},n.treemap=function(){var n=X,r=!1,t=1,e=1,i=[0],u=d,o=d,f=d,a=d,c=d;function h(n){return n.x0=n.y0=0,n.x1=t,n.y1=e,n.eachBefore(l),i=[0],r&&n.eachBefore(j),n}function l(r){var t=i[r.depth],e=r.x0+t,h=r.y0+t,l=r.x1-t,p=r.y1-t;l=t-1){var h=f[r];return h.x0=i,h.y0=u,h.x1=o,void(h.y1=a)}var l=c[r],p=e/2+l,d=r+1,s=t-1;for(;d>>1;c[v]a-u){var g=e?(i*y+o*x)/e:o;n(r,d,x,i,u,g,a),n(d,t,y,g,u,o,a)}else{var m=e?(u*y+a*x)/e:a;n(r,d,x,i,u,o,m),n(d,t,y,i,m,o,a)}}(0,a,n.value,r,t,e,i)},n.treemapDice=O,n.treemapResquarify=Y,n.treemapSlice=U,n.treemapSliceDice=function(n,r,t,e,i){(1&n.depth?U:O)(n,r,t,e,i)},n.treemapSquarify=X,Object.defineProperty(n,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-hierarchy/package.json b/frontend/node_modules/d3-hierarchy/package.json new file mode 100644 index 0000000..3b4e0b6 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/package.json @@ -0,0 +1,56 @@ +{ + "name": "d3-hierarchy", + "version": "3.1.2", + "description": "Layout algorithms for visualizing hierarchical data.", + "homepage": "https://d3js.org/d3-hierarchy/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-hierarchy.git" + }, + "keywords": [ + "d3", + "d3-module", + "layout", + "tree", + "treemap", + "hierarchy", + "infovis" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "http://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-hierarchy.min.js", + "unpkg": "dist/d3-hierarchy.min.js", + "exports": { + "umd": "./dist/d3-hierarchy.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "devDependencies": { + "benchmark": "2", + "d3-array": "1.2.0 - 3", + "d3-dsv": "1 - 3", + "d3-random": "1.1.0 - 3", + "eslint": "8", + "mocha": "9", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-hierarchy/src/accessors.js b/frontend/node_modules/d3-hierarchy/src/accessors.js new file mode 100644 index 0000000..369c414 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/accessors.js @@ -0,0 +1,8 @@ +export function optional(f) { + return f == null ? null : required(f); +} + +export function required(f) { + if (typeof f !== "function") throw new Error; + return f; +} diff --git a/frontend/node_modules/d3-hierarchy/src/array.js b/frontend/node_modules/d3-hierarchy/src/array.js new file mode 100644 index 0000000..b46d1b9 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/array.js @@ -0,0 +1,20 @@ +export default function(x) { + return typeof x === "object" && "length" in x + ? x // Array, TypedArray, NodeList, array-like + : Array.from(x); // Map, Set, iterable, string, or anything else +} + +export function shuffle(array, random) { + let m = array.length, + t, + i; + + while (m) { + i = random() * m-- | 0; + t = array[m]; + array[m] = array[i]; + array[i] = t; + } + + return array; +} diff --git a/frontend/node_modules/d3-hierarchy/src/cluster.js b/frontend/node_modules/d3-hierarchy/src/cluster.js new file mode 100644 index 0000000..f5a280e --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/cluster.js @@ -0,0 +1,84 @@ +function defaultSeparation(a, b) { + return a.parent === b.parent ? 1 : 2; +} + +function meanX(children) { + return children.reduce(meanXReduce, 0) / children.length; +} + +function meanXReduce(x, c) { + return x + c.x; +} + +function maxY(children) { + return 1 + children.reduce(maxYReduce, 0); +} + +function maxYReduce(y, c) { + return Math.max(y, c.y); +} + +function leafLeft(node) { + var children; + while (children = node.children) node = children[0]; + return node; +} + +function leafRight(node) { + var children; + while (children = node.children) node = children[children.length - 1]; + return node; +} + +export default function() { + var separation = defaultSeparation, + dx = 1, + dy = 1, + nodeSize = false; + + function cluster(root) { + var previousNode, + x = 0; + + // First walk, computing the initial x & y values. + root.eachAfter(function(node) { + var children = node.children; + if (children) { + node.x = meanX(children); + node.y = maxY(children); + } else { + node.x = previousNode ? x += separation(node, previousNode) : 0; + node.y = 0; + previousNode = node; + } + }); + + var left = leafLeft(root), + right = leafRight(root), + x0 = left.x - separation(left, right) / 2, + x1 = right.x + separation(right, left) / 2; + + // Second walk, normalizing x & y to the desired size. + return root.eachAfter(nodeSize ? function(node) { + node.x = (node.x - root.x) * dx; + node.y = (root.y - node.y) * dy; + } : function(node) { + node.x = (node.x - x0) / (x1 - x0) * dx; + node.y = (1 - (root.y ? node.y / root.y : 1)) * dy; + }); + } + + cluster.separation = function(x) { + return arguments.length ? (separation = x, cluster) : separation; + }; + + cluster.size = function(x) { + return arguments.length ? (nodeSize = false, dx = +x[0], dy = +x[1], cluster) : (nodeSize ? null : [dx, dy]); + }; + + cluster.nodeSize = function(x) { + return arguments.length ? (nodeSize = true, dx = +x[0], dy = +x[1], cluster) : (nodeSize ? [dx, dy] : null); + }; + + return cluster; +} diff --git a/frontend/node_modules/d3-hierarchy/src/constant.js b/frontend/node_modules/d3-hierarchy/src/constant.js new file mode 100644 index 0000000..1d947c4 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/constant.js @@ -0,0 +1,9 @@ +export function constantZero() { + return 0; +} + +export default function(x) { + return function() { + return x; + }; +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/ancestors.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/ancestors.js new file mode 100644 index 0000000..f70c726 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/ancestors.js @@ -0,0 +1,7 @@ +export default function() { + var node = this, nodes = [node]; + while (node = node.parent) { + nodes.push(node); + } + return nodes; +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/count.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/count.js new file mode 100644 index 0000000..0b90f1b --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/count.js @@ -0,0 +1,12 @@ +function count(node) { + var sum = 0, + children = node.children, + i = children && children.length; + if (!i) sum = 1; + else while (--i >= 0) sum += children[i].value; + node.value = sum; +} + +export default function() { + return this.eachAfter(count); +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/descendants.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/descendants.js new file mode 100644 index 0000000..7f38090 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/descendants.js @@ -0,0 +1,3 @@ +export default function() { + return Array.from(this); +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/each.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/each.js new file mode 100644 index 0000000..af911cc --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/each.js @@ -0,0 +1,7 @@ +export default function(callback, that) { + let index = -1; + for (const node of this) { + callback.call(that, node, ++index, this); + } + return this; +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/eachAfter.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/eachAfter.js new file mode 100644 index 0000000..a3f0a2c --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/eachAfter.js @@ -0,0 +1,15 @@ +export default function(callback, that) { + var node = this, nodes = [node], next = [], children, i, n, index = -1; + while (node = nodes.pop()) { + next.push(node); + if (children = node.children) { + for (i = 0, n = children.length; i < n; ++i) { + nodes.push(children[i]); + } + } + } + while (node = next.pop()) { + callback.call(that, node, ++index, this); + } + return this; +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/eachBefore.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/eachBefore.js new file mode 100644 index 0000000..f3cd524 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/eachBefore.js @@ -0,0 +1,12 @@ +export default function(callback, that) { + var node = this, nodes = [node], children, i, index = -1; + while (node = nodes.pop()) { + callback.call(that, node, ++index, this); + if (children = node.children) { + for (i = children.length - 1; i >= 0; --i) { + nodes.push(children[i]); + } + } + } + return this; +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/find.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/find.js new file mode 100644 index 0000000..f4ed8c6 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/find.js @@ -0,0 +1,8 @@ +export default function(callback, that) { + let index = -1; + for (const node of this) { + if (callback.call(that, node, ++index, this)) { + return node; + } + } +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/index.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/index.js new file mode 100644 index 0000000..b9c1026 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/index.js @@ -0,0 +1,91 @@ +import node_count from "./count.js"; +import node_each from "./each.js"; +import node_eachBefore from "./eachBefore.js"; +import node_eachAfter from "./eachAfter.js"; +import node_find from "./find.js"; +import node_sum from "./sum.js"; +import node_sort from "./sort.js"; +import node_path from "./path.js"; +import node_ancestors from "./ancestors.js"; +import node_descendants from "./descendants.js"; +import node_leaves from "./leaves.js"; +import node_links from "./links.js"; +import node_iterator from "./iterator.js"; + +export default function hierarchy(data, children) { + if (data instanceof Map) { + data = [undefined, data]; + if (children === undefined) children = mapChildren; + } else if (children === undefined) { + children = objectChildren; + } + + var root = new Node(data), + node, + nodes = [root], + child, + childs, + i, + n; + + while (node = nodes.pop()) { + if ((childs = children(node.data)) && (n = (childs = Array.from(childs)).length)) { + node.children = childs; + for (i = n - 1; i >= 0; --i) { + nodes.push(child = childs[i] = new Node(childs[i])); + child.parent = node; + child.depth = node.depth + 1; + } + } + } + + return root.eachBefore(computeHeight); +} + +function node_copy() { + return hierarchy(this).eachBefore(copyData); +} + +function objectChildren(d) { + return d.children; +} + +function mapChildren(d) { + return Array.isArray(d) ? d[1] : null; +} + +function copyData(node) { + if (node.data.value !== undefined) node.value = node.data.value; + node.data = node.data.data; +} + +export function computeHeight(node) { + var height = 0; + do node.height = height; + while ((node = node.parent) && (node.height < ++height)); +} + +export function Node(data) { + this.data = data; + this.depth = + this.height = 0; + this.parent = null; +} + +Node.prototype = hierarchy.prototype = { + constructor: Node, + count: node_count, + each: node_each, + eachAfter: node_eachAfter, + eachBefore: node_eachBefore, + find: node_find, + sum: node_sum, + sort: node_sort, + path: node_path, + ancestors: node_ancestors, + descendants: node_descendants, + leaves: node_leaves, + links: node_links, + copy: node_copy, + [Symbol.iterator]: node_iterator +}; diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/iterator.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/iterator.js new file mode 100644 index 0000000..7e06b62 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/iterator.js @@ -0,0 +1,14 @@ +export default function*() { + var node = this, current, next = [node], children, i, n; + do { + current = next.reverse(), next = []; + while (node = current.pop()) { + yield node; + if (children = node.children) { + for (i = 0, n = children.length; i < n; ++i) { + next.push(children[i]); + } + } + } + } while (next.length); +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/leaves.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/leaves.js new file mode 100644 index 0000000..401c5b5 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/leaves.js @@ -0,0 +1,9 @@ +export default function() { + var leaves = []; + this.eachBefore(function(node) { + if (!node.children) { + leaves.push(node); + } + }); + return leaves; +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/links.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/links.js new file mode 100644 index 0000000..6fcb82f --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/links.js @@ -0,0 +1,9 @@ +export default function() { + var root = this, links = []; + root.each(function(node) { + if (node !== root) { // Don’t include the root’s parent, if any. + links.push({source: node.parent, target: node}); + } + }); + return links; +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/path.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/path.js new file mode 100644 index 0000000..9958913 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/path.js @@ -0,0 +1,30 @@ +export default function(end) { + var start = this, + ancestor = leastCommonAncestor(start, end), + nodes = [start]; + while (start !== ancestor) { + start = start.parent; + nodes.push(start); + } + var k = nodes.length; + while (end !== ancestor) { + nodes.splice(k, 0, end); + end = end.parent; + } + return nodes; +} + +function leastCommonAncestor(a, b) { + if (a === b) return a; + var aNodes = a.ancestors(), + bNodes = b.ancestors(), + c = null; + a = aNodes.pop(); + b = bNodes.pop(); + while (a === b) { + c = a; + a = aNodes.pop(); + b = bNodes.pop(); + } + return c; +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/sort.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/sort.js new file mode 100644 index 0000000..5d0426d --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/sort.js @@ -0,0 +1,7 @@ +export default function(compare) { + return this.eachBefore(function(node) { + if (node.children) { + node.children.sort(compare); + } + }); +} diff --git a/frontend/node_modules/d3-hierarchy/src/hierarchy/sum.js b/frontend/node_modules/d3-hierarchy/src/hierarchy/sum.js new file mode 100644 index 0000000..350a965 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/hierarchy/sum.js @@ -0,0 +1,9 @@ +export default function(value) { + return this.eachAfter(function(node) { + var sum = +value(node.data) || 0, + children = node.children, + i = children && children.length; + while (--i >= 0) sum += children[i].value; + node.value = sum; + }); +} diff --git a/frontend/node_modules/d3-hierarchy/src/index.js b/frontend/node_modules/d3-hierarchy/src/index.js new file mode 100644 index 0000000..e5952b1 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/index.js @@ -0,0 +1,15 @@ +export {default as cluster} from "./cluster.js"; +export {default as hierarchy, Node} from "./hierarchy/index.js"; +export {default as pack} from "./pack/index.js"; +export {default as packSiblings} from "./pack/siblings.js"; +export {default as packEnclose} from "./pack/enclose.js"; +export {default as partition} from "./partition.js"; +export {default as stratify} from "./stratify.js"; +export {default as tree} from "./tree.js"; +export {default as treemap} from "./treemap/index.js"; +export {default as treemapBinary} from "./treemap/binary.js"; +export {default as treemapDice} from "./treemap/dice.js"; +export {default as treemapSlice} from "./treemap/slice.js"; +export {default as treemapSliceDice} from "./treemap/sliceDice.js"; +export {default as treemapSquarify} from "./treemap/squarify.js"; +export {default as treemapResquarify} from "./treemap/resquarify.js"; diff --git a/frontend/node_modules/d3-hierarchy/src/lcg.js b/frontend/node_modules/d3-hierarchy/src/lcg.js new file mode 100644 index 0000000..a13cf79 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/lcg.js @@ -0,0 +1,9 @@ +// https://en.wikipedia.org/wiki/Linear_congruential_generator#Parameters_in_common_use +const a = 1664525; +const c = 1013904223; +const m = 4294967296; // 2^32 + +export default function() { + let s = 1; + return () => (s = (a * s + c) % m) / m; +} diff --git a/frontend/node_modules/d3-hierarchy/src/pack/enclose.js b/frontend/node_modules/d3-hierarchy/src/pack/enclose.js new file mode 100644 index 0000000..f6eb67f --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/pack/enclose.js @@ -0,0 +1,123 @@ +import {shuffle} from "../array.js"; +import lcg from "../lcg.js"; + +export default function(circles) { + return packEncloseRandom(circles, lcg()); +} + +export function packEncloseRandom(circles, random) { + var i = 0, n = (circles = shuffle(Array.from(circles), random)).length, B = [], p, e; + + while (i < n) { + p = circles[i]; + if (e && enclosesWeak(e, p)) ++i; + else e = encloseBasis(B = extendBasis(B, p)), i = 0; + } + + return e; +} + +function extendBasis(B, p) { + var i, j; + + if (enclosesWeakAll(p, B)) return [p]; + + // If we get here then B must have at least one element. + for (i = 0; i < B.length; ++i) { + if (enclosesNot(p, B[i]) + && enclosesWeakAll(encloseBasis2(B[i], p), B)) { + return [B[i], p]; + } + } + + // If we get here then B must have at least two elements. + for (i = 0; i < B.length - 1; ++i) { + for (j = i + 1; j < B.length; ++j) { + if (enclosesNot(encloseBasis2(B[i], B[j]), p) + && enclosesNot(encloseBasis2(B[i], p), B[j]) + && enclosesNot(encloseBasis2(B[j], p), B[i]) + && enclosesWeakAll(encloseBasis3(B[i], B[j], p), B)) { + return [B[i], B[j], p]; + } + } + } + + // If we get here then something is very wrong. + throw new Error; +} + +function enclosesNot(a, b) { + var dr = a.r - b.r, dx = b.x - a.x, dy = b.y - a.y; + return dr < 0 || dr * dr < dx * dx + dy * dy; +} + +function enclosesWeak(a, b) { + var dr = a.r - b.r + Math.max(a.r, b.r, 1) * 1e-9, dx = b.x - a.x, dy = b.y - a.y; + return dr > 0 && dr * dr > dx * dx + dy * dy; +} + +function enclosesWeakAll(a, B) { + for (var i = 0; i < B.length; ++i) { + if (!enclosesWeak(a, B[i])) { + return false; + } + } + return true; +} + +function encloseBasis(B) { + switch (B.length) { + case 1: return encloseBasis1(B[0]); + case 2: return encloseBasis2(B[0], B[1]); + case 3: return encloseBasis3(B[0], B[1], B[2]); + } +} + +function encloseBasis1(a) { + return { + x: a.x, + y: a.y, + r: a.r + }; +} + +function encloseBasis2(a, b) { + var x1 = a.x, y1 = a.y, r1 = a.r, + x2 = b.x, y2 = b.y, r2 = b.r, + x21 = x2 - x1, y21 = y2 - y1, r21 = r2 - r1, + l = Math.sqrt(x21 * x21 + y21 * y21); + return { + x: (x1 + x2 + x21 / l * r21) / 2, + y: (y1 + y2 + y21 / l * r21) / 2, + r: (l + r1 + r2) / 2 + }; +} + +function encloseBasis3(a, b, c) { + var x1 = a.x, y1 = a.y, r1 = a.r, + x2 = b.x, y2 = b.y, r2 = b.r, + x3 = c.x, y3 = c.y, r3 = c.r, + a2 = x1 - x2, + a3 = x1 - x3, + b2 = y1 - y2, + b3 = y1 - y3, + c2 = r2 - r1, + c3 = r3 - r1, + d1 = x1 * x1 + y1 * y1 - r1 * r1, + d2 = d1 - x2 * x2 - y2 * y2 + r2 * r2, + d3 = d1 - x3 * x3 - y3 * y3 + r3 * r3, + ab = a3 * b2 - a2 * b3, + xa = (b2 * d3 - b3 * d2) / (ab * 2) - x1, + xb = (b3 * c2 - b2 * c3) / ab, + ya = (a3 * d2 - a2 * d3) / (ab * 2) - y1, + yb = (a2 * c3 - a3 * c2) / ab, + A = xb * xb + yb * yb - 1, + B = 2 * (r1 + xa * xb + ya * yb), + C = xa * xa + ya * ya - r1 * r1, + r = -(Math.abs(A) > 1e-6 ? (B + Math.sqrt(B * B - 4 * A * C)) / (2 * A) : C / B); + return { + x: x1 + xa + xb * r, + y: y1 + ya + yb * r, + r: r + }; +} diff --git a/frontend/node_modules/d3-hierarchy/src/pack/index.js b/frontend/node_modules/d3-hierarchy/src/pack/index.js new file mode 100644 index 0000000..8b710b3 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/pack/index.js @@ -0,0 +1,81 @@ +import {optional} from "../accessors.js"; +import constant, {constantZero} from "../constant.js"; +import lcg from "../lcg.js"; +import {packSiblingsRandom} from "./siblings.js"; + +function defaultRadius(d) { + return Math.sqrt(d.value); +} + +export default function() { + var radius = null, + dx = 1, + dy = 1, + padding = constantZero; + + function pack(root) { + const random = lcg(); + root.x = dx / 2, root.y = dy / 2; + if (radius) { + root.eachBefore(radiusLeaf(radius)) + .eachAfter(packChildrenRandom(padding, 0.5, random)) + .eachBefore(translateChild(1)); + } else { + root.eachBefore(radiusLeaf(defaultRadius)) + .eachAfter(packChildrenRandom(constantZero, 1, random)) + .eachAfter(packChildrenRandom(padding, root.r / Math.min(dx, dy), random)) + .eachBefore(translateChild(Math.min(dx, dy) / (2 * root.r))); + } + return root; + } + + pack.radius = function(x) { + return arguments.length ? (radius = optional(x), pack) : radius; + }; + + pack.size = function(x) { + return arguments.length ? (dx = +x[0], dy = +x[1], pack) : [dx, dy]; + }; + + pack.padding = function(x) { + return arguments.length ? (padding = typeof x === "function" ? x : constant(+x), pack) : padding; + }; + + return pack; +} + +function radiusLeaf(radius) { + return function(node) { + if (!node.children) { + node.r = Math.max(0, +radius(node) || 0); + } + }; +} + +function packChildrenRandom(padding, k, random) { + return function(node) { + if (children = node.children) { + var children, + i, + n = children.length, + r = padding(node) * k || 0, + e; + + if (r) for (i = 0; i < n; ++i) children[i].r += r; + e = packSiblingsRandom(children, random); + if (r) for (i = 0; i < n; ++i) children[i].r -= r; + node.r = e + r; + } + }; +} + +function translateChild(k) { + return function(node) { + var parent = node.parent; + node.r *= k; + if (parent) { + node.x = parent.x + k * node.x; + node.y = parent.y + k * node.y; + } + }; +} diff --git a/frontend/node_modules/d3-hierarchy/src/pack/siblings.js b/frontend/node_modules/d3-hierarchy/src/pack/siblings.js new file mode 100644 index 0000000..e7f5df4 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/pack/siblings.js @@ -0,0 +1,120 @@ +import array from "../array.js"; +import lcg from "../lcg.js"; +import {packEncloseRandom} from "./enclose.js"; + +function place(b, a, c) { + var dx = b.x - a.x, x, a2, + dy = b.y - a.y, y, b2, + d2 = dx * dx + dy * dy; + if (d2) { + a2 = a.r + c.r, a2 *= a2; + b2 = b.r + c.r, b2 *= b2; + if (a2 > b2) { + x = (d2 + b2 - a2) / (2 * d2); + y = Math.sqrt(Math.max(0, b2 / d2 - x * x)); + c.x = b.x - x * dx - y * dy; + c.y = b.y - x * dy + y * dx; + } else { + x = (d2 + a2 - b2) / (2 * d2); + y = Math.sqrt(Math.max(0, a2 / d2 - x * x)); + c.x = a.x + x * dx - y * dy; + c.y = a.y + x * dy + y * dx; + } + } else { + c.x = a.x + c.r; + c.y = a.y; + } +} + +function intersects(a, b) { + var dr = a.r + b.r - 1e-6, dx = b.x - a.x, dy = b.y - a.y; + return dr > 0 && dr * dr > dx * dx + dy * dy; +} + +function score(node) { + var a = node._, + b = node.next._, + ab = a.r + b.r, + dx = (a.x * b.r + b.x * a.r) / ab, + dy = (a.y * b.r + b.y * a.r) / ab; + return dx * dx + dy * dy; +} + +function Node(circle) { + this._ = circle; + this.next = null; + this.previous = null; +} + +export function packSiblingsRandom(circles, random) { + if (!(n = (circles = array(circles)).length)) return 0; + + var a, b, c, n, aa, ca, i, j, k, sj, sk; + + // Place the first circle. + a = circles[0], a.x = 0, a.y = 0; + if (!(n > 1)) return a.r; + + // Place the second circle. + b = circles[1], a.x = -b.r, b.x = a.r, b.y = 0; + if (!(n > 2)) return a.r + b.r; + + // Place the third circle. + place(b, a, c = circles[2]); + + // Initialize the front-chain using the first three circles a, b and c. + a = new Node(a), b = new Node(b), c = new Node(c); + a.next = c.previous = b; + b.next = a.previous = c; + c.next = b.previous = a; + + // Attempt to place each remaining circle… + pack: for (i = 3; i < n; ++i) { + place(a._, b._, c = circles[i]), c = new Node(c); + + // Find the closest intersecting circle on the front-chain, if any. + // “Closeness” is determined by linear distance along the front-chain. + // “Ahead” or “behind” is likewise determined by linear distance. + j = b.next, k = a.previous, sj = b._.r, sk = a._.r; + do { + if (sj <= sk) { + if (intersects(j._, c._)) { + b = j, a.next = b, b.previous = a, --i; + continue pack; + } + sj += j._.r, j = j.next; + } else { + if (intersects(k._, c._)) { + a = k, a.next = b, b.previous = a, --i; + continue pack; + } + sk += k._.r, k = k.previous; + } + } while (j !== k.next); + + // Success! Insert the new circle c between a and b. + c.previous = a, c.next = b, a.next = b.previous = b = c; + + // Compute the new closest circle pair to the centroid. + aa = score(a); + while ((c = c.next) !== b) { + if ((ca = score(c)) < aa) { + a = c, aa = ca; + } + } + b = a.next; + } + + // Compute the enclosing circle of the front chain. + a = [b._], c = b; while ((c = c.next) !== b) a.push(c._); c = packEncloseRandom(a, random); + + // Translate the circles to put the enclosing circle around the origin. + for (i = 0; i < n; ++i) a = circles[i], a.x -= c.x, a.y -= c.y; + + return c.r; +} + +export default function(circles) { + packSiblingsRandom(circles, lcg()); + return circles; +} diff --git a/frontend/node_modules/d3-hierarchy/src/partition.js b/frontend/node_modules/d3-hierarchy/src/partition.js new file mode 100644 index 0000000..0165ef7 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/partition.js @@ -0,0 +1,52 @@ +import roundNode from "./treemap/round.js"; +import treemapDice from "./treemap/dice.js"; + +export default function() { + var dx = 1, + dy = 1, + padding = 0, + round = false; + + function partition(root) { + var n = root.height + 1; + root.x0 = + root.y0 = padding; + root.x1 = dx; + root.y1 = dy / n; + root.eachBefore(positionNode(dy, n)); + if (round) root.eachBefore(roundNode); + return root; + } + + function positionNode(dy, n) { + return function(node) { + if (node.children) { + treemapDice(node, node.x0, dy * (node.depth + 1) / n, node.x1, dy * (node.depth + 2) / n); + } + var x0 = node.x0, + y0 = node.y0, + x1 = node.x1 - padding, + y1 = node.y1 - padding; + if (x1 < x0) x0 = x1 = (x0 + x1) / 2; + if (y1 < y0) y0 = y1 = (y0 + y1) / 2; + node.x0 = x0; + node.y0 = y0; + node.x1 = x1; + node.y1 = y1; + }; + } + + partition.round = function(x) { + return arguments.length ? (round = !!x, partition) : round; + }; + + partition.size = function(x) { + return arguments.length ? (dx = +x[0], dy = +x[1], partition) : [dx, dy]; + }; + + partition.padding = function(x) { + return arguments.length ? (padding = +x, partition) : padding; + }; + + return partition; +} diff --git a/frontend/node_modules/d3-hierarchy/src/stratify.js b/frontend/node_modules/d3-hierarchy/src/stratify.js new file mode 100644 index 0000000..d113100 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/stratify.js @@ -0,0 +1,145 @@ +import {optional} from "./accessors.js"; +import {Node, computeHeight} from "./hierarchy/index.js"; + +var preroot = {depth: -1}, + ambiguous = {}, + imputed = {}; + +function defaultId(d) { + return d.id; +} + +function defaultParentId(d) { + return d.parentId; +} + +export default function() { + var id = defaultId, + parentId = defaultParentId, + path; + + function stratify(data) { + var nodes = Array.from(data), + currentId = id, + currentParentId = parentId, + n, + d, + i, + root, + parent, + node, + nodeId, + nodeKey, + nodeByKey = new Map; + + if (path != null) { + const I = nodes.map((d, i) => normalize(path(d, i, data))); + const P = I.map(parentof); + const S = new Set(I).add(""); + for (const i of P) { + if (!S.has(i)) { + S.add(i); + I.push(i); + P.push(parentof(i)); + nodes.push(imputed); + } + } + currentId = (_, i) => I[i]; + currentParentId = (_, i) => P[i]; + } + + for (i = 0, n = nodes.length; i < n; ++i) { + d = nodes[i], node = nodes[i] = new Node(d); + if ((nodeId = currentId(d, i, data)) != null && (nodeId += "")) { + nodeKey = node.id = nodeId; + nodeByKey.set(nodeKey, nodeByKey.has(nodeKey) ? ambiguous : node); + } + if ((nodeId = currentParentId(d, i, data)) != null && (nodeId += "")) { + node.parent = nodeId; + } + } + + for (i = 0; i < n; ++i) { + node = nodes[i]; + if (nodeId = node.parent) { + parent = nodeByKey.get(nodeId); + if (!parent) throw new Error("missing: " + nodeId); + if (parent === ambiguous) throw new Error("ambiguous: " + nodeId); + if (parent.children) parent.children.push(node); + else parent.children = [node]; + node.parent = parent; + } else { + if (root) throw new Error("multiple roots"); + root = node; + } + } + + if (!root) throw new Error("no root"); + + // When imputing internal nodes, only introduce roots if needed. + // Then replace the imputed marker data with null. + if (path != null) { + while (root.data === imputed && root.children.length === 1) { + root = root.children[0], --n; + } + for (let i = nodes.length - 1; i >= 0; --i) { + node = nodes[i]; + if (node.data !== imputed) break; + node.data = null; + } + } + + root.parent = preroot; + root.eachBefore(function(node) { node.depth = node.parent.depth + 1; --n; }).eachBefore(computeHeight); + root.parent = null; + if (n > 0) throw new Error("cycle"); + + return root; + } + + stratify.id = function(x) { + return arguments.length ? (id = optional(x), stratify) : id; + }; + + stratify.parentId = function(x) { + return arguments.length ? (parentId = optional(x), stratify) : parentId; + }; + + stratify.path = function(x) { + return arguments.length ? (path = optional(x), stratify) : path; + }; + + return stratify; +} + +// To normalize a path, we coerce to a string, strip the trailing slash if any +// (as long as the trailing slash is not immediately preceded by another slash), +// and add leading slash if missing. +function normalize(path) { + path = `${path}`; + let i = path.length; + if (slash(path, i - 1) && !slash(path, i - 2)) path = path.slice(0, -1); + return path[0] === "/" ? path : `/${path}`; +} + +// Walk backwards to find the first slash that is not the leading slash, e.g.: +// "/foo/bar" ⇥ "/foo", "/foo" ⇥ "/", "/" ↦ "". (The root is special-cased +// because the id of the root must be a truthy value.) +function parentof(path) { + let i = path.length; + if (i < 2) return ""; + while (--i > 1) if (slash(path, i)) break; + return path.slice(0, i); +} + +// Slashes can be escaped; to determine whether a slash is a path delimiter, we +// count the number of preceding backslashes escaping the forward slash: an odd +// number indicates an escaped forward slash. +function slash(path, i) { + if (path[i] === "/") { + let k = 0; + while (i > 0 && path[--i] === "\\") ++k; + if ((k & 1) === 0) return true; + } + return false; +} diff --git a/frontend/node_modules/d3-hierarchy/src/tree.js b/frontend/node_modules/d3-hierarchy/src/tree.js new file mode 100644 index 0000000..dc4275e --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/tree.js @@ -0,0 +1,237 @@ +import {Node} from "./hierarchy/index.js"; + +function defaultSeparation(a, b) { + return a.parent === b.parent ? 1 : 2; +} + +// function radialSeparation(a, b) { +// return (a.parent === b.parent ? 1 : 2) / a.depth; +// } + +// This function is used to traverse the left contour of a subtree (or +// subforest). It returns the successor of v on this contour. This successor is +// either given by the leftmost child of v or by the thread of v. The function +// returns null if and only if v is on the highest level of its subtree. +function nextLeft(v) { + var children = v.children; + return children ? children[0] : v.t; +} + +// This function works analogously to nextLeft. +function nextRight(v) { + var children = v.children; + return children ? children[children.length - 1] : v.t; +} + +// Shifts the current subtree rooted at w+. This is done by increasing +// prelim(w+) and mod(w+) by shift. +function moveSubtree(wm, wp, shift) { + var change = shift / (wp.i - wm.i); + wp.c -= change; + wp.s += shift; + wm.c += change; + wp.z += shift; + wp.m += shift; +} + +// All other shifts, applied to the smaller subtrees between w- and w+, are +// performed by this function. To prepare the shifts, we have to adjust +// change(w+), shift(w+), and change(w-). +function executeShifts(v) { + var shift = 0, + change = 0, + children = v.children, + i = children.length, + w; + while (--i >= 0) { + w = children[i]; + w.z += shift; + w.m += shift; + shift += w.s + (change += w.c); + } +} + +// If vi-’s ancestor is a sibling of v, returns vi-’s ancestor. Otherwise, +// returns the specified (default) ancestor. +function nextAncestor(vim, v, ancestor) { + return vim.a.parent === v.parent ? vim.a : ancestor; +} + +function TreeNode(node, i) { + this._ = node; + this.parent = null; + this.children = null; + this.A = null; // default ancestor + this.a = this; // ancestor + this.z = 0; // prelim + this.m = 0; // mod + this.c = 0; // change + this.s = 0; // shift + this.t = null; // thread + this.i = i; // number +} + +TreeNode.prototype = Object.create(Node.prototype); + +function treeRoot(root) { + var tree = new TreeNode(root, 0), + node, + nodes = [tree], + child, + children, + i, + n; + + while (node = nodes.pop()) { + if (children = node._.children) { + node.children = new Array(n = children.length); + for (i = n - 1; i >= 0; --i) { + nodes.push(child = node.children[i] = new TreeNode(children[i], i)); + child.parent = node; + } + } + } + + (tree.parent = new TreeNode(null, 0)).children = [tree]; + return tree; +} + +// Node-link tree diagram using the Reingold-Tilford "tidy" algorithm +export default function() { + var separation = defaultSeparation, + dx = 1, + dy = 1, + nodeSize = null; + + function tree(root) { + var t = treeRoot(root); + + // Compute the layout using Buchheim et al.’s algorithm. + t.eachAfter(firstWalk), t.parent.m = -t.z; + t.eachBefore(secondWalk); + + // If a fixed node size is specified, scale x and y. + if (nodeSize) root.eachBefore(sizeNode); + + // If a fixed tree size is specified, scale x and y based on the extent. + // Compute the left-most, right-most, and depth-most nodes for extents. + else { + var left = root, + right = root, + bottom = root; + root.eachBefore(function(node) { + if (node.x < left.x) left = node; + if (node.x > right.x) right = node; + if (node.depth > bottom.depth) bottom = node; + }); + var s = left === right ? 1 : separation(left, right) / 2, + tx = s - left.x, + kx = dx / (right.x + s + tx), + ky = dy / (bottom.depth || 1); + root.eachBefore(function(node) { + node.x = (node.x + tx) * kx; + node.y = node.depth * ky; + }); + } + + return root; + } + + // Computes a preliminary x-coordinate for v. Before that, FIRST WALK is + // applied recursively to the children of v, as well as the function + // APPORTION. After spacing out the children by calling EXECUTE SHIFTS, the + // node v is placed to the midpoint of its outermost children. + function firstWalk(v) { + var children = v.children, + siblings = v.parent.children, + w = v.i ? siblings[v.i - 1] : null; + if (children) { + executeShifts(v); + var midpoint = (children[0].z + children[children.length - 1].z) / 2; + if (w) { + v.z = w.z + separation(v._, w._); + v.m = v.z - midpoint; + } else { + v.z = midpoint; + } + } else if (w) { + v.z = w.z + separation(v._, w._); + } + v.parent.A = apportion(v, w, v.parent.A || siblings[0]); + } + + // Computes all real x-coordinates by summing up the modifiers recursively. + function secondWalk(v) { + v._.x = v.z + v.parent.m; + v.m += v.parent.m; + } + + // The core of the algorithm. Here, a new subtree is combined with the + // previous subtrees. Threads are used to traverse the inside and outside + // contours of the left and right subtree up to the highest common level. The + // vertices used for the traversals are vi+, vi-, vo-, and vo+, where the + // superscript o means outside and i means inside, the subscript - means left + // subtree and + means right subtree. For summing up the modifiers along the + // contour, we use respective variables si+, si-, so-, and so+. Whenever two + // nodes of the inside contours conflict, we compute the left one of the + // greatest uncommon ancestors using the function ANCESTOR and call MOVE + // SUBTREE to shift the subtree and prepare the shifts of smaller subtrees. + // Finally, we add a new thread (if necessary). + function apportion(v, w, ancestor) { + if (w) { + var vip = v, + vop = v, + vim = w, + vom = vip.parent.children[0], + sip = vip.m, + sop = vop.m, + sim = vim.m, + som = vom.m, + shift; + while (vim = nextRight(vim), vip = nextLeft(vip), vim && vip) { + vom = nextLeft(vom); + vop = nextRight(vop); + vop.a = v; + shift = vim.z + sim - vip.z - sip + separation(vim._, vip._); + if (shift > 0) { + moveSubtree(nextAncestor(vim, v, ancestor), v, shift); + sip += shift; + sop += shift; + } + sim += vim.m; + sip += vip.m; + som += vom.m; + sop += vop.m; + } + if (vim && !nextRight(vop)) { + vop.t = vim; + vop.m += sim - sop; + } + if (vip && !nextLeft(vom)) { + vom.t = vip; + vom.m += sip - som; + ancestor = v; + } + } + return ancestor; + } + + function sizeNode(node) { + node.x *= dx; + node.y = node.depth * dy; + } + + tree.separation = function(x) { + return arguments.length ? (separation = x, tree) : separation; + }; + + tree.size = function(x) { + return arguments.length ? (nodeSize = false, dx = +x[0], dy = +x[1], tree) : (nodeSize ? null : [dx, dy]); + }; + + tree.nodeSize = function(x) { + return arguments.length ? (nodeSize = true, dx = +x[0], dy = +x[1], tree) : (nodeSize ? [dx, dy] : null); + }; + + return tree; +} diff --git a/frontend/node_modules/d3-hierarchy/src/treemap/binary.js b/frontend/node_modules/d3-hierarchy/src/treemap/binary.js new file mode 100644 index 0000000..a9395dc --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/treemap/binary.js @@ -0,0 +1,46 @@ +export default function(parent, x0, y0, x1, y1) { + var nodes = parent.children, + i, n = nodes.length, + sum, sums = new Array(n + 1); + + for (sums[0] = sum = i = 0; i < n; ++i) { + sums[i + 1] = sum += nodes[i].value; + } + + partition(0, n, parent.value, x0, y0, x1, y1); + + function partition(i, j, value, x0, y0, x1, y1) { + if (i >= j - 1) { + var node = nodes[i]; + node.x0 = x0, node.y0 = y0; + node.x1 = x1, node.y1 = y1; + return; + } + + var valueOffset = sums[i], + valueTarget = (value / 2) + valueOffset, + k = i + 1, + hi = j - 1; + + while (k < hi) { + var mid = k + hi >>> 1; + if (sums[mid] < valueTarget) k = mid + 1; + else hi = mid; + } + + if ((valueTarget - sums[k - 1]) < (sums[k] - valueTarget) && i + 1 < k) --k; + + var valueLeft = sums[k] - valueOffset, + valueRight = value - valueLeft; + + if ((x1 - x0) > (y1 - y0)) { + var xk = value ? (x0 * valueRight + x1 * valueLeft) / value : x1; + partition(i, k, valueLeft, x0, y0, xk, y1); + partition(k, j, valueRight, xk, y0, x1, y1); + } else { + var yk = value ? (y0 * valueRight + y1 * valueLeft) / value : y1; + partition(i, k, valueLeft, x0, y0, x1, yk); + partition(k, j, valueRight, x0, yk, x1, y1); + } + } +} diff --git a/frontend/node_modules/d3-hierarchy/src/treemap/dice.js b/frontend/node_modules/d3-hierarchy/src/treemap/dice.js new file mode 100644 index 0000000..605c1f6 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/treemap/dice.js @@ -0,0 +1,12 @@ +export default function(parent, x0, y0, x1, y1) { + var nodes = parent.children, + node, + i = -1, + n = nodes.length, + k = parent.value && (x1 - x0) / parent.value; + + while (++i < n) { + node = nodes[i], node.y0 = y0, node.y1 = y1; + node.x0 = x0, node.x1 = x0 += node.value * k; + } +} diff --git a/frontend/node_modules/d3-hierarchy/src/treemap/index.js b/frontend/node_modules/d3-hierarchy/src/treemap/index.js new file mode 100644 index 0000000..ccc42c9 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/treemap/index.js @@ -0,0 +1,94 @@ +import roundNode from "./round.js"; +import squarify from "./squarify.js"; +import {required} from "../accessors.js"; +import constant, {constantZero} from "../constant.js"; + +export default function() { + var tile = squarify, + round = false, + dx = 1, + dy = 1, + paddingStack = [0], + paddingInner = constantZero, + paddingTop = constantZero, + paddingRight = constantZero, + paddingBottom = constantZero, + paddingLeft = constantZero; + + function treemap(root) { + root.x0 = + root.y0 = 0; + root.x1 = dx; + root.y1 = dy; + root.eachBefore(positionNode); + paddingStack = [0]; + if (round) root.eachBefore(roundNode); + return root; + } + + function positionNode(node) { + var p = paddingStack[node.depth], + x0 = node.x0 + p, + y0 = node.y0 + p, + x1 = node.x1 - p, + y1 = node.y1 - p; + if (x1 < x0) x0 = x1 = (x0 + x1) / 2; + if (y1 < y0) y0 = y1 = (y0 + y1) / 2; + node.x0 = x0; + node.y0 = y0; + node.x1 = x1; + node.y1 = y1; + if (node.children) { + p = paddingStack[node.depth + 1] = paddingInner(node) / 2; + x0 += paddingLeft(node) - p; + y0 += paddingTop(node) - p; + x1 -= paddingRight(node) - p; + y1 -= paddingBottom(node) - p; + if (x1 < x0) x0 = x1 = (x0 + x1) / 2; + if (y1 < y0) y0 = y1 = (y0 + y1) / 2; + tile(node, x0, y0, x1, y1); + } + } + + treemap.round = function(x) { + return arguments.length ? (round = !!x, treemap) : round; + }; + + treemap.size = function(x) { + return arguments.length ? (dx = +x[0], dy = +x[1], treemap) : [dx, dy]; + }; + + treemap.tile = function(x) { + return arguments.length ? (tile = required(x), treemap) : tile; + }; + + treemap.padding = function(x) { + return arguments.length ? treemap.paddingInner(x).paddingOuter(x) : treemap.paddingInner(); + }; + + treemap.paddingInner = function(x) { + return arguments.length ? (paddingInner = typeof x === "function" ? x : constant(+x), treemap) : paddingInner; + }; + + treemap.paddingOuter = function(x) { + return arguments.length ? treemap.paddingTop(x).paddingRight(x).paddingBottom(x).paddingLeft(x) : treemap.paddingTop(); + }; + + treemap.paddingTop = function(x) { + return arguments.length ? (paddingTop = typeof x === "function" ? x : constant(+x), treemap) : paddingTop; + }; + + treemap.paddingRight = function(x) { + return arguments.length ? (paddingRight = typeof x === "function" ? x : constant(+x), treemap) : paddingRight; + }; + + treemap.paddingBottom = function(x) { + return arguments.length ? (paddingBottom = typeof x === "function" ? x : constant(+x), treemap) : paddingBottom; + }; + + treemap.paddingLeft = function(x) { + return arguments.length ? (paddingLeft = typeof x === "function" ? x : constant(+x), treemap) : paddingLeft; + }; + + return treemap; +} diff --git a/frontend/node_modules/d3-hierarchy/src/treemap/resquarify.js b/frontend/node_modules/d3-hierarchy/src/treemap/resquarify.js new file mode 100644 index 0000000..de72047 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/treemap/resquarify.js @@ -0,0 +1,36 @@ +import treemapDice from "./dice.js"; +import treemapSlice from "./slice.js"; +import {phi, squarifyRatio} from "./squarify.js"; + +export default (function custom(ratio) { + + function resquarify(parent, x0, y0, x1, y1) { + if ((rows = parent._squarify) && (rows.ratio === ratio)) { + var rows, + row, + nodes, + i, + j = -1, + n, + m = rows.length, + value = parent.value; + + while (++j < m) { + row = rows[j], nodes = row.children; + for (i = row.value = 0, n = nodes.length; i < n; ++i) row.value += nodes[i].value; + if (row.dice) treemapDice(row, x0, y0, x1, value ? y0 += (y1 - y0) * row.value / value : y1); + else treemapSlice(row, x0, y0, value ? x0 += (x1 - x0) * row.value / value : x1, y1); + value -= row.value; + } + } else { + parent._squarify = rows = squarifyRatio(ratio, parent, x0, y0, x1, y1); + rows.ratio = ratio; + } + } + + resquarify.ratio = function(x) { + return custom((x = +x) > 1 ? x : 1); + }; + + return resquarify; +})(phi); diff --git a/frontend/node_modules/d3-hierarchy/src/treemap/round.js b/frontend/node_modules/d3-hierarchy/src/treemap/round.js new file mode 100644 index 0000000..7ac45ec --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/treemap/round.js @@ -0,0 +1,6 @@ +export default function(node) { + node.x0 = Math.round(node.x0); + node.y0 = Math.round(node.y0); + node.x1 = Math.round(node.x1); + node.y1 = Math.round(node.y1); +} diff --git a/frontend/node_modules/d3-hierarchy/src/treemap/slice.js b/frontend/node_modules/d3-hierarchy/src/treemap/slice.js new file mode 100644 index 0000000..1022bfa --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/treemap/slice.js @@ -0,0 +1,12 @@ +export default function(parent, x0, y0, x1, y1) { + var nodes = parent.children, + node, + i = -1, + n = nodes.length, + k = parent.value && (y1 - y0) / parent.value; + + while (++i < n) { + node = nodes[i], node.x0 = x0, node.x1 = x1; + node.y0 = y0, node.y1 = y0 += node.value * k; + } +} diff --git a/frontend/node_modules/d3-hierarchy/src/treemap/sliceDice.js b/frontend/node_modules/d3-hierarchy/src/treemap/sliceDice.js new file mode 100644 index 0000000..545ad42 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/treemap/sliceDice.js @@ -0,0 +1,6 @@ +import dice from "./dice.js"; +import slice from "./slice.js"; + +export default function(parent, x0, y0, x1, y1) { + (parent.depth & 1 ? slice : dice)(parent, x0, y0, x1, y1); +} diff --git a/frontend/node_modules/d3-hierarchy/src/treemap/squarify.js b/frontend/node_modules/d3-hierarchy/src/treemap/squarify.js new file mode 100644 index 0000000..f801070 --- /dev/null +++ b/frontend/node_modules/d3-hierarchy/src/treemap/squarify.js @@ -0,0 +1,66 @@ +import treemapDice from "./dice.js"; +import treemapSlice from "./slice.js"; + +export var phi = (1 + Math.sqrt(5)) / 2; + +export function squarifyRatio(ratio, parent, x0, y0, x1, y1) { + var rows = [], + nodes = parent.children, + row, + nodeValue, + i0 = 0, + i1 = 0, + n = nodes.length, + dx, dy, + value = parent.value, + sumValue, + minValue, + maxValue, + newRatio, + minRatio, + alpha, + beta; + + while (i0 < n) { + dx = x1 - x0, dy = y1 - y0; + + // Find the next non-empty node. + do sumValue = nodes[i1++].value; while (!sumValue && i1 < n); + minValue = maxValue = sumValue; + alpha = Math.max(dy / dx, dx / dy) / (value * ratio); + beta = sumValue * sumValue * alpha; + minRatio = Math.max(maxValue / beta, beta / minValue); + + // Keep adding nodes while the aspect ratio maintains or improves. + for (; i1 < n; ++i1) { + sumValue += nodeValue = nodes[i1].value; + if (nodeValue < minValue) minValue = nodeValue; + if (nodeValue > maxValue) maxValue = nodeValue; + beta = sumValue * sumValue * alpha; + newRatio = Math.max(maxValue / beta, beta / minValue); + if (newRatio > minRatio) { sumValue -= nodeValue; break; } + minRatio = newRatio; + } + + // Position and record the row orientation. + rows.push(row = {value: sumValue, dice: dx < dy, children: nodes.slice(i0, i1)}); + if (row.dice) treemapDice(row, x0, y0, x1, value ? y0 += dy * sumValue / value : y1); + else treemapSlice(row, x0, y0, value ? x0 += dx * sumValue / value : x1, y1); + value -= sumValue, i0 = i1; + } + + return rows; +} + +export default (function custom(ratio) { + + function squarify(parent, x0, y0, x1, y1) { + squarifyRatio(ratio, parent, x0, y0, x1, y1); + } + + squarify.ratio = function(x) { + return custom((x = +x) > 1 ? x : 1); + }; + + return squarify; +})(phi); diff --git a/frontend/node_modules/d3-interpolate/LICENSE b/frontend/node_modules/d3-interpolate/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-interpolate/README.md b/frontend/node_modules/d3-interpolate/README.md new file mode 100644 index 0000000..f5d82e7 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/README.md @@ -0,0 +1,268 @@ +# d3-interpolate + +This module provides a variety of interpolation methods for blending between two values. Values may be numbers, colors, strings, arrays, or even deeply-nested objects. For example: + +```js +const i = d3.interpolateNumber(10, 20); +i(0.0); // 10 +i(0.2); // 12 +i(0.5); // 15 +i(1.0); // 20 +``` + +The returned function `i` is called an *interpolator*. Given a starting value *a* and an ending value *b*, it takes a parameter *t* in the domain [0, 1] and returns the corresponding interpolated value between *a* and *b*. An interpolator typically returns a value equivalent to *a* at *t* = 0 and a value equivalent to *b* at *t* = 1. + +You can interpolate more than just numbers. To find the perceptual midpoint between steelblue and brown: + +```js +d3.interpolateLab("steelblue", "brown")(0.5); // "rgb(142, 92, 109)" +``` + +Here’s a more elaborate example demonstrating type inference used by [interpolate](#interpolate): + +```js +const i = d3.interpolate({colors: ["red", "blue"]}, {colors: ["white", "black"]}); +i(0.0); // {colors: ["rgb(255, 0, 0)", "rgb(0, 0, 255)"]} +i(0.5); // {colors: ["rgb(255, 128, 128)", "rgb(0, 0, 128)"]} +i(1.0); // {colors: ["rgb(255, 255, 255)", "rgb(0, 0, 0)"]} +``` + +Note that the generic value interpolator detects not only nested objects and arrays, but also color strings and numbers embedded in strings! + +## Installing + +If you use npm, `npm install d3-interpolate`. You can also download the [latest release on GitHub](https://github.com/d3/d3-interpolate/releases/latest). For vanilla HTML in modern browsers, import d3-interpolate from Skypack: + +```html + +``` + +For legacy environments, you can load d3-interpolate’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported. (If using [color interpolation](#color-spaces), also load [d3-color](https://github.com/d3/d3-color).) + +```html + + + +``` + +## API Reference + +# d3.interpolate(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/value.js), [Examples](https://observablehq.com/@d3/d3-interpolate) + +Returns an interpolator between the two arbitrary values *a* and *b*. The interpolator implementation is based on the type of the end value *b*, using the following algorithm: + +1. If *b* is null, undefined or a boolean, use the constant *b*. +2. If *b* is a number, use [interpolateNumber](#interpolateNumber). +3. If *b* is a [color](https://github.com/d3/d3-color/blob/master/README.md#color) or a string coercible to a color, use [interpolateRgb](#interpolateRgb). +4. If *b* is a [date](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date), use [interpolateDate](#interpolateDate). +5. If *b* is a string, use [interpolateString](#interpolateString). +6. If *b* is a [typed array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/TypedArray) of numbers, use [interpolateNumberArray](#interpolateNumberArray). +7. If *b* is a generic [array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/isArray), use [interpolateArray](#interpolateArray). +8. If *b* is coercible to a number, use [interpolateNumber](#interpolateNumber). +9. Use [interpolateObject](#interpolateObject). + +Based on the chosen interpolator, *a* is coerced to the suitable corresponding type. + +# d3.interpolateNumber(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/number.js), [Examples](https://observablehq.com/@d3/d3-interpolatenumber) + +Returns an interpolator between the two numbers *a* and *b*. The returned interpolator is equivalent to: + +```js +function interpolator(t) { + return a * (1 - t) + b * t; +} +``` + +Caution: avoid interpolating to or from the number zero when the interpolator is used to generate a string. When very small values are stringified, they may be converted to scientific notation, which is an invalid attribute or style property value in older browsers. For example, the number `0.0000001` is converted to the string `"1e-7"`. This is particularly noticeable with interpolating opacity. To avoid scientific notation, start or end the transition at 1e-6: the smallest value that is not stringified in scientific notation. + +# d3.interpolateRound(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/round.js), [Examples](https://observablehq.com/@d3/d3-interpolatenumber) + +Returns an interpolator between the two numbers *a* and *b*; the interpolator is similar to [interpolateNumber](#interpolateNumber), except it will round the resulting value to the nearest integer. + +# d3.interpolateString(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/string.js), [Examples](https://observablehq.com/@d3/d3-interpolatestring) + +Returns an interpolator between the two strings *a* and *b*. The string interpolator finds numbers embedded in *a* and *b*, where each number is of the form understood by JavaScript. A few examples of numbers that will be detected within a string: `-1`, `42`, `3.14159`, and `6.0221413e+23`. + +For each number embedded in *b*, the interpolator will attempt to find a corresponding number in *a*. If a corresponding number is found, a numeric interpolator is created using [interpolateNumber](#interpolateNumber). The remaining parts of the string *b* are used as a template: the static parts of the string *b* remain constant for the interpolation, with the interpolated numeric values embedded in the template. + +For example, if *a* is `"300 12px sans-serif"`, and *b* is `"500 36px Comic-Sans"`, two embedded numbers are found. The remaining static parts (of string *b*) are a space between the two numbers (`" "`), and the suffix (`"px Comic-Sans"`). The result of the interpolator at *t* = 0.5 is `"400 24px Comic-Sans"`. + +# d3.interpolateDate(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/date.js), [Examples](https://observablehq.com/@d3/d3-interpolatedate) + +Returns an interpolator between the two [dates](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date) *a* and *b*. + +Note: **no defensive copy** of the returned date is created; the same Date instance is returned for every evaluation of the interpolator. No copy is made for performance reasons; interpolators are often part of the inner loop of [animated transitions](https://github.com/d3/d3-transition). + +# d3.interpolateArray(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/array.js), [Examples](https://observablehq.com/@d3/d3-interpolateobject) + +Returns an interpolator between the two arrays *a* and *b*. If *b* is a typed array (e.g., Float64Array), [interpolateNumberArray](#interpolateNumberArray) is called instead. + +Internally, an array template is created that is the same length as *b*. For each element in *b*, if there exists a corresponding element in *a*, a generic interpolator is created for the two elements using [interpolate](#interpolate). If there is no such element, the static value from *b* is used in the template. Then, for the given parameter *t*, the template’s embedded interpolators are evaluated. The updated array template is then returned. + +For example, if *a* is the array `[0, 1]` and *b* is the array `[1, 10, 100]`, then the result of the interpolator for *t* = 0.5 is the array `[0.5, 5.5, 100]`. + +Note: **no defensive copy** of the template array is created; modifications of the returned array may adversely affect subsequent evaluation of the interpolator. No copy is made for performance reasons; interpolators are often part of the inner loop of [animated transitions](https://github.com/d3/d3-transition). + +# d3.interpolateNumberArray(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/numberArray.js), [Examples](https://observablehq.com/@d3/d3-interpolatenumberarray) + +Returns an interpolator between the two arrays of numbers *a* and *b*. Internally, an array template is created that is the same type and length as *b*. For each element in *b*, if there exists a corresponding element in *a*, the values are directly interpolated in the array template. If there is no such element, the static value from *b* is copied. The updated array template is then returned. + +Note: For performance reasons, **no defensive copy** is made of the template array and the arguments *a* and *b*; modifications of these arrays may affect subsequent evaluation of the interpolator. + +# d3.interpolateObject(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/object.js), [Examples](https://observablehq.com/@d3/d3-interpolateobject) + +Returns an interpolator between the two objects *a* and *b*. Internally, an object template is created that has the same properties as *b*. For each property in *b*, if there exists a corresponding property in *a*, a generic interpolator is created for the two elements using [interpolate](#interpolate). If there is no such property, the static value from *b* is used in the template. Then, for the given parameter *t*, the template's embedded interpolators are evaluated and the updated object template is then returned. + +For example, if *a* is the object `{x: 0, y: 1}` and *b* is the object `{x: 1, y: 10, z: 100}`, the result of the interpolator for *t* = 0.5 is the object `{x: 0.5, y: 5.5, z: 100}`. + +Object interpolation is particularly useful for *dataspace interpolation*, where data is interpolated rather than attribute values. For example, you can interpolate an object which describes an arc in a pie chart, and then use [d3.arc](https://github.com/d3/d3-shape/blob/master/README.md#arc) to compute the new SVG path data. + +Note: **no defensive copy** of the template object is created; modifications of the returned object may adversely affect subsequent evaluation of the interpolator. No copy is made for performance reasons; interpolators are often part of the inner loop of [animated transitions](https://github.com/d3/d3-transition). + +# d3.interpolateTransformCss(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/transform/index.js#L62), [Examples](https://observablehq.com/@d3/d3-interpolatetransformcss) + +Returns an interpolator between the two 2D CSS transforms represented by *a* and *b*. Each transform is decomposed to a standard representation of translate, rotate, *x*-skew and scale; these component transformations are then interpolated. This behavior is standardized by CSS: see [matrix decomposition for animation](http://www.w3.org/TR/css3-2d-transforms/#matrix-decomposition). + +# d3.interpolateTransformSvg(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/transform/index.js#L63), [Examples](https://observablehq.com/@d3/d3-interpolatetransformcss) + +Returns an interpolator between the two 2D SVG transforms represented by *a* and *b*. Each transform is decomposed to a standard representation of translate, rotate, *x*-skew and scale; these component transformations are then interpolated. This behavior is standardized by CSS: see [matrix decomposition for animation](http://www.w3.org/TR/css3-2d-transforms/#matrix-decomposition). + +# d3.interpolateZoom(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/zoom.js), [Examples](https://observablehq.com/@d3/d3-interpolatezoom) + +Returns an interpolator between the two views *a* and *b* of a two-dimensional plane, based on [“Smooth and efficient zooming and panning”](http://www.win.tue.nl/~vanwijk/zoompan.pdf) by Jarke J. van Wijk and Wim A.A. Nuij. Each view is defined as an array of three numbers: *cx*, *cy* and *width*. The first two coordinates *cx*, *cy* represent the center of the viewport; the last coordinate *width* represents the size of the viewport. + +The returned interpolator exposes a *duration* property which encodes the recommended transition duration in milliseconds. This duration is based on the path length of the curved trajectory through *x,y* space. If you want a slower or faster transition, multiply this by an arbitrary scale factor (V as described in the original paper). + +# *interpolateZoom*.rho(rho) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/zoom.js) + +Given a [zoom interpolator](#interpolateZoom), returns a new zoom interpolator using the specified curvature *rho*. When *rho* is close to 0, the interpolator is almost linear. The default curvature is sqrt(2). + +# d3.interpolateDiscrete(values) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/discrete.js), [Examples](https://observablehq.com/@d3/d3-interpolatediscrete) + +Returns a discrete interpolator for the given array of *values*. The returned interpolator maps *t* in [0, 1 / *n*) to *values*[0], *t* in [1 / *n*, 2 / *n*) to *values*[1], and so on, where *n* = *values*.length. In effect, this is a lightweight [quantize scale](https://github.com/d3/d3-scale/blob/master/README.md#quantize-scales) with a fixed domain of [0, 1]. + +### Sampling + +# d3.quantize(interpolator, n) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/quantize.js), [Examples](https://observablehq.com/@d3/d3-quantize) + +Returns *n* uniformly-spaced samples from the specified *interpolator*, where *n* is an integer greater than one. The first sample is always at *t* = 0, and the last sample is always at *t* = 1. This can be useful in generating a fixed number of samples from a given interpolator, such as to derive the range of a [quantize scale](https://github.com/d3/d3-scale/blob/master/README.md#quantize-scales) from a [continuous interpolator](https://github.com/d3/d3-scale-chromatic/blob/master/README.md#interpolateWarm). + +Caution: this method will not work with interpolators that do not return defensive copies of their output, such as [d3.interpolateArray](#interpolateArray), [d3.interpolateDate](#interpolateDate) and [d3.interpolateObject](#interpolateObject). For those interpolators, you must wrap the interpolator and create a copy for each returned value. + +### Color Spaces + +# d3.interpolateRgb(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/rgb.js), [Examples](https://observablehq.com/@d3/working-with-color) + +rgb + +Or, with a corrected [gamma](#interpolate_gamma) of 2.2: + +rgbGamma + +Returns an RGB color space interpolator between the two colors *a* and *b* with a configurable [gamma](#interpolate_gamma). If the gamma is not specified, it defaults to 1.0. The colors *a* and *b* need not be in RGB; they will be converted to RGB using [d3.rgb](https://github.com/d3/d3-color/blob/master/README.md#rgb). The return value of the interpolator is an RGB string. + +# d3.interpolateRgbBasis(colors) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/rgb.js#L54), [Examples](https://observablehq.com/@d3/working-with-color) + +Returns a uniform nonrational B-spline interpolator through the specified array of *colors*, which are converted to [RGB color space](https://github.com/d3/d3-color/blob/master/README.md#rgb). Implicit control points are generated such that the interpolator returns *colors*[0] at *t* = 0 and *colors*[*colors*.length - 1] at *t* = 1. Opacity interpolation is not currently supported. See also [d3.interpolateBasis](#interpolateBasis), and see [d3-scale-chromatic](https://github.com/d3/d3-scale-chromatic) for examples. + +# d3.interpolateRgbBasisClosed(colors) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/rgb.js#L55), [Examples](https://observablehq.com/@d3/working-with-color) + +Returns a uniform nonrational B-spline interpolator through the specified array of *colors*, which are converted to [RGB color space](https://github.com/d3/d3-color/blob/master/README.md#rgb). The control points are implicitly repeated such that the resulting spline has cyclical C² continuity when repeated around *t* in [0,1]; this is useful, for example, to create cyclical color scales. Opacity interpolation is not currently supported. See also [d3.interpolateBasisClosed](#interpolateBasisClosed), and see [d3-scale-chromatic](https://github.com/d3/d3-scale-chromatic) for examples. + +# d3.interpolateHsl(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/hsl.js), [Examples](https://observablehq.com/@d3/working-with-color) + +hsl + +Returns an HSL color space interpolator between the two colors *a* and *b*. The colors *a* and *b* need not be in HSL; they will be converted to HSL using [d3.hsl](https://github.com/d3/d3-color/blob/master/README.md#hsl). If either color’s hue or saturation is NaN, the opposing color’s channel value is used. The shortest path between hues is used. The return value of the interpolator is an RGB string. + +# d3.interpolateHslLong(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/hsl.js#L21), [Examples](https://observablehq.com/@d3/working-with-color) + +hslLong + +Like [interpolateHsl](#interpolateHsl), but does not use the shortest path between hues. + +# d3.interpolateLab(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/lab.js), [Examples](https://observablehq.com/@d3/working-with-color) + +lab + +Returns a [CIELAB color space](https://en.wikipedia.org/wiki/Lab_color_space#CIELAB) interpolator between the two colors *a* and *b*. The colors *a* and *b* need not be in CIELAB; they will be converted to CIELAB using [d3.lab](https://github.com/d3/d3-color/blob/master/README.md#lab). The return value of the interpolator is an RGB string. + +# d3.interpolateHcl(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/hcl.js), [Examples](https://observablehq.com/@d3/working-with-color) + +hcl + +Returns a [CIELChab color space](https://en.wikipedia.org/wiki/CIELAB_color_space#Cylindrical_representation:_CIELCh_or_CIEHLC) interpolator between the two colors *a* and *b*. The colors *a* and *b* need not be in CIELChab; they will be converted to CIELChab using [d3.hcl](https://github.com/d3/d3-color/blob/master/README.md#hcl). If either color’s hue or chroma is NaN, the opposing color’s channel value is used. The shortest path between hues is used. The return value of the interpolator is an RGB string. + +# d3.interpolateHclLong(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/hcl.js#L21), [Examples](https://observablehq.com/@d3/working-with-color) + +hclLong + +Like [interpolateHcl](#interpolateHcl), but does not use the shortest path between hues. + +# d3.interpolateCubehelix(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/cubehelix.js), [Examples](https://observablehq.com/@d3/working-with-color) + +cubehelix + +Or, with a [gamma](#interpolate_gamma) of 3.0 to emphasize high-intensity values: + +cubehelixGamma + +Returns a Cubehelix color space interpolator between the two colors *a* and *b* using a configurable [gamma](#interpolate_gamma). If the gamma is not specified, it defaults to 1.0. The colors *a* and *b* need not be in Cubehelix; they will be converted to Cubehelix using [d3.cubehelix](https://github.com/d3/d3-color/blob/master/README.md#cubehelix). If either color’s hue or saturation is NaN, the opposing color’s channel value is used. The shortest path between hues is used. The return value of the interpolator is an RGB string. + +# d3.interpolateCubehelixLong(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/cubehelix.js#L29), [Examples](https://observablehq.com/@d3/working-with-color) + +cubehelixLong + +Or, with a [gamma](#interpolate_gamma) of 3.0 to emphasize high-intensity values: + +cubehelixGammaLong + +Like [interpolateCubehelix](#interpolateCubehelix), but does not use the shortest path between hues. + +# interpolate.gamma(gamma) + +Given that *interpolate* is one of [interpolateRgb](#interpolateRgb), [interpolateCubehelix](#interpolateCubehelix) or [interpolateCubehelixLong](#interpolateCubehelixLong), returns a new interpolator factory of the same type using the specified *gamma*. For example, to interpolate from purple to orange with a gamma of 2.2 in RGB space: + +```js +const interpolator = d3.interpolateRgb.gamma(2.2)("purple", "orange"); +``` + +See Eric Brasseur’s article, [Gamma error in picture scaling](http://www.ericbrasseur.org/gamma.html), for more on gamma correction. + +# d3.interpolateHue(a, b) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/hue.js), [Examples](https://observablehq.com/@d3/working-with-color) + +Returns an interpolator between the two hue angles *a* and *b*. If either hue is NaN, the opposing value is used. The shortest path between hues is used. The return value of the interpolator is a number in [0, 360). + +### Splines + +Whereas standard interpolators blend from a starting value *a* at *t* = 0 to an ending value *b* at *t* = 1, spline interpolators smoothly blend multiple input values for *t* in [0,1] using piecewise polynomial functions. Only cubic uniform nonrational [B-splines](https://en.wikipedia.org/wiki/B-spline) are currently supported, also known as basis splines. + +# d3.interpolateBasis(values) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/basis.js), [Examples](https://observablehq.com/@d3/d3-interpolatebasis) + +Returns a uniform nonrational B-spline interpolator through the specified array of *values*, which must be numbers. Implicit control points are generated such that the interpolator returns *values*[0] at *t* = 0 and *values*[*values*.length - 1] at *t* = 1. See also [d3.curveBasis](https://github.com/d3/d3-shape/blob/master/README.md#curveBasis). + +# d3.interpolateBasisClosed(values) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/basisClosed.js), [Examples](https://observablehq.com/@d3/d3-interpolatebasis) + +Returns a uniform nonrational B-spline interpolator through the specified array of *values*, which must be numbers. The control points are implicitly repeated such that the resulting one-dimensional spline has cyclical C² continuity when repeated around *t* in [0,1]. See also [d3.curveBasisClosed](https://github.com/d3/d3-shape/blob/master/README.md#curveBasisClosed). + +### Piecewise + +# d3.piecewise([interpolate, ]values) · [Source](https://github.com/d3/d3-interpolate/blob/master/src/piecewise.js), [Examples](https://observablehq.com/@d3/d3-piecewise) + +Returns a piecewise interpolator, composing interpolators for each adjacent pair of *values*. The returned interpolator maps *t* in [0, 1 / (*n* - 1)] to *interpolate*(*values*[0], *values*[1]), *t* in [1 / (*n* - 1), 2 / (*n* - 1)] to *interpolate*(*values*[1], *values*[2]), and so on, where *n* = *values*.length. In effect, this is a lightweight [linear scale](https://github.com/d3/d3-scale/blob/master/README.md#linear-scales). For example, to blend through red, green and blue: + +```js +const interpolate = d3.piecewise(d3.interpolateRgb.gamma(2.2), ["red", "green", "blue"]); +``` + +If *interpolate* is not specified, defaults to [d3.interpolate](#interpolate). diff --git a/frontend/node_modules/d3-interpolate/dist/d3-interpolate.js b/frontend/node_modules/d3-interpolate/dist/d3-interpolate.js new file mode 100644 index 0000000..a374eed --- /dev/null +++ b/frontend/node_modules/d3-interpolate/dist/d3-interpolate.js @@ -0,0 +1,590 @@ +// https://d3js.org/d3-interpolate/ v3.0.1 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-color')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-color'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3)); +}(this, (function (exports, d3Color) { 'use strict'; + +function basis(t1, v0, v1, v2, v3) { + var t2 = t1 * t1, t3 = t2 * t1; + return ((1 - 3 * t1 + 3 * t2 - t3) * v0 + + (4 - 6 * t2 + 3 * t3) * v1 + + (1 + 3 * t1 + 3 * t2 - 3 * t3) * v2 + + t3 * v3) / 6; +} + +function basis$1(values) { + var n = values.length - 1; + return function(t) { + var i = t <= 0 ? (t = 0) : t >= 1 ? (t = 1, n - 1) : Math.floor(t * n), + v1 = values[i], + v2 = values[i + 1], + v0 = i > 0 ? values[i - 1] : 2 * v1 - v2, + v3 = i < n - 1 ? values[i + 2] : 2 * v2 - v1; + return basis((t - i / n) * n, v0, v1, v2, v3); + }; +} + +function basisClosed(values) { + var n = values.length; + return function(t) { + var i = Math.floor(((t %= 1) < 0 ? ++t : t) * n), + v0 = values[(i + n - 1) % n], + v1 = values[i % n], + v2 = values[(i + 1) % n], + v3 = values[(i + 2) % n]; + return basis((t - i / n) * n, v0, v1, v2, v3); + }; +} + +var constant = x => () => x; + +function linear(a, d) { + return function(t) { + return a + t * d; + }; +} + +function exponential(a, b, y) { + return a = Math.pow(a, y), b = Math.pow(b, y) - a, y = 1 / y, function(t) { + return Math.pow(a + t * b, y); + }; +} + +function hue$1(a, b) { + var d = b - a; + return d ? linear(a, d > 180 || d < -180 ? d - 360 * Math.round(d / 360) : d) : constant(isNaN(a) ? b : a); +} + +function gamma(y) { + return (y = +y) === 1 ? nogamma : function(a, b) { + return b - a ? exponential(a, b, y) : constant(isNaN(a) ? b : a); + }; +} + +function nogamma(a, b) { + var d = b - a; + return d ? linear(a, d) : constant(isNaN(a) ? b : a); +} + +var rgb = (function rgbGamma(y) { + var color = gamma(y); + + function rgb(start, end) { + var r = color((start = d3Color.rgb(start)).r, (end = d3Color.rgb(end)).r), + g = color(start.g, end.g), + b = color(start.b, end.b), + opacity = nogamma(start.opacity, end.opacity); + return function(t) { + start.r = r(t); + start.g = g(t); + start.b = b(t); + start.opacity = opacity(t); + return start + ""; + }; + } + + rgb.gamma = rgbGamma; + + return rgb; +})(1); + +function rgbSpline(spline) { + return function(colors) { + var n = colors.length, + r = new Array(n), + g = new Array(n), + b = new Array(n), + i, color; + for (i = 0; i < n; ++i) { + color = d3Color.rgb(colors[i]); + r[i] = color.r || 0; + g[i] = color.g || 0; + b[i] = color.b || 0; + } + r = spline(r); + g = spline(g); + b = spline(b); + color.opacity = 1; + return function(t) { + color.r = r(t); + color.g = g(t); + color.b = b(t); + return color + ""; + }; + }; +} + +var rgbBasis = rgbSpline(basis$1); +var rgbBasisClosed = rgbSpline(basisClosed); + +function numberArray(a, b) { + if (!b) b = []; + var n = a ? Math.min(b.length, a.length) : 0, + c = b.slice(), + i; + return function(t) { + for (i = 0; i < n; ++i) c[i] = a[i] * (1 - t) + b[i] * t; + return c; + }; +} + +function isNumberArray(x) { + return ArrayBuffer.isView(x) && !(x instanceof DataView); +} + +function array(a, b) { + return (isNumberArray(b) ? numberArray : genericArray)(a, b); +} + +function genericArray(a, b) { + var nb = b ? b.length : 0, + na = a ? Math.min(nb, a.length) : 0, + x = new Array(na), + c = new Array(nb), + i; + + for (i = 0; i < na; ++i) x[i] = value(a[i], b[i]); + for (; i < nb; ++i) c[i] = b[i]; + + return function(t) { + for (i = 0; i < na; ++i) c[i] = x[i](t); + return c; + }; +} + +function date(a, b) { + var d = new Date; + return a = +a, b = +b, function(t) { + return d.setTime(a * (1 - t) + b * t), d; + }; +} + +function number(a, b) { + return a = +a, b = +b, function(t) { + return a * (1 - t) + b * t; + }; +} + +function object(a, b) { + var i = {}, + c = {}, + k; + + if (a === null || typeof a !== "object") a = {}; + if (b === null || typeof b !== "object") b = {}; + + for (k in b) { + if (k in a) { + i[k] = value(a[k], b[k]); + } else { + c[k] = b[k]; + } + } + + return function(t) { + for (k in i) c[k] = i[k](t); + return c; + }; +} + +var reA = /[-+]?(?:\d+\.?\d*|\.?\d+)(?:[eE][-+]?\d+)?/g, + reB = new RegExp(reA.source, "g"); + +function zero(b) { + return function() { + return b; + }; +} + +function one(b) { + return function(t) { + return b(t) + ""; + }; +} + +function string(a, b) { + var bi = reA.lastIndex = reB.lastIndex = 0, // scan index for next number in b + am, // current match in a + bm, // current match in b + bs, // string preceding current number in b, if any + i = -1, // index in s + s = [], // string constants and placeholders + q = []; // number interpolators + + // Coerce inputs to strings. + a = a + "", b = b + ""; + + // Interpolate pairs of numbers in a & b. + while ((am = reA.exec(a)) + && (bm = reB.exec(b))) { + if ((bs = bm.index) > bi) { // a string precedes the next number in b + bs = b.slice(bi, bs); + if (s[i]) s[i] += bs; // coalesce with previous string + else s[++i] = bs; + } + if ((am = am[0]) === (bm = bm[0])) { // numbers in a & b match + if (s[i]) s[i] += bm; // coalesce with previous string + else s[++i] = bm; + } else { // interpolate non-matching numbers + s[++i] = null; + q.push({i: i, x: number(am, bm)}); + } + bi = reB.lastIndex; + } + + // Add remains of b. + if (bi < b.length) { + bs = b.slice(bi); + if (s[i]) s[i] += bs; // coalesce with previous string + else s[++i] = bs; + } + + // Special optimization for only a single match. + // Otherwise, interpolate each of the numbers and rejoin the string. + return s.length < 2 ? (q[0] + ? one(q[0].x) + : zero(b)) + : (b = q.length, function(t) { + for (var i = 0, o; i < b; ++i) s[(o = q[i]).i] = o.x(t); + return s.join(""); + }); +} + +function value(a, b) { + var t = typeof b, c; + return b == null || t === "boolean" ? constant(b) + : (t === "number" ? number + : t === "string" ? ((c = d3Color.color(b)) ? (b = c, rgb) : string) + : b instanceof d3Color.color ? rgb + : b instanceof Date ? date + : isNumberArray(b) ? numberArray + : Array.isArray(b) ? genericArray + : typeof b.valueOf !== "function" && typeof b.toString !== "function" || isNaN(b) ? object + : number)(a, b); +} + +function discrete(range) { + var n = range.length; + return function(t) { + return range[Math.max(0, Math.min(n - 1, Math.floor(t * n)))]; + }; +} + +function hue(a, b) { + var i = hue$1(+a, +b); + return function(t) { + var x = i(t); + return x - 360 * Math.floor(x / 360); + }; +} + +function round(a, b) { + return a = +a, b = +b, function(t) { + return Math.round(a * (1 - t) + b * t); + }; +} + +var degrees = 180 / Math.PI; + +var identity = { + translateX: 0, + translateY: 0, + rotate: 0, + skewX: 0, + scaleX: 1, + scaleY: 1 +}; + +function decompose(a, b, c, d, e, f) { + var scaleX, scaleY, skewX; + if (scaleX = Math.sqrt(a * a + b * b)) a /= scaleX, b /= scaleX; + if (skewX = a * c + b * d) c -= a * skewX, d -= b * skewX; + if (scaleY = Math.sqrt(c * c + d * d)) c /= scaleY, d /= scaleY, skewX /= scaleY; + if (a * d < b * c) a = -a, b = -b, skewX = -skewX, scaleX = -scaleX; + return { + translateX: e, + translateY: f, + rotate: Math.atan2(b, a) * degrees, + skewX: Math.atan(skewX) * degrees, + scaleX: scaleX, + scaleY: scaleY + }; +} + +var svgNode; + +/* eslint-disable no-undef */ +function parseCss(value) { + const m = new (typeof DOMMatrix === "function" ? DOMMatrix : WebKitCSSMatrix)(value + ""); + return m.isIdentity ? identity : decompose(m.a, m.b, m.c, m.d, m.e, m.f); +} + +function parseSvg(value) { + if (value == null) return identity; + if (!svgNode) svgNode = document.createElementNS("http://www.w3.org/2000/svg", "g"); + svgNode.setAttribute("transform", value); + if (!(value = svgNode.transform.baseVal.consolidate())) return identity; + value = value.matrix; + return decompose(value.a, value.b, value.c, value.d, value.e, value.f); +} + +function interpolateTransform(parse, pxComma, pxParen, degParen) { + + function pop(s) { + return s.length ? s.pop() + " " : ""; + } + + function translate(xa, ya, xb, yb, s, q) { + if (xa !== xb || ya !== yb) { + var i = s.push("translate(", null, pxComma, null, pxParen); + q.push({i: i - 4, x: number(xa, xb)}, {i: i - 2, x: number(ya, yb)}); + } else if (xb || yb) { + s.push("translate(" + xb + pxComma + yb + pxParen); + } + } + + function rotate(a, b, s, q) { + if (a !== b) { + if (a - b > 180) b += 360; else if (b - a > 180) a += 360; // shortest path + q.push({i: s.push(pop(s) + "rotate(", null, degParen) - 2, x: number(a, b)}); + } else if (b) { + s.push(pop(s) + "rotate(" + b + degParen); + } + } + + function skewX(a, b, s, q) { + if (a !== b) { + q.push({i: s.push(pop(s) + "skewX(", null, degParen) - 2, x: number(a, b)}); + } else if (b) { + s.push(pop(s) + "skewX(" + b + degParen); + } + } + + function scale(xa, ya, xb, yb, s, q) { + if (xa !== xb || ya !== yb) { + var i = s.push(pop(s) + "scale(", null, ",", null, ")"); + q.push({i: i - 4, x: number(xa, xb)}, {i: i - 2, x: number(ya, yb)}); + } else if (xb !== 1 || yb !== 1) { + s.push(pop(s) + "scale(" + xb + "," + yb + ")"); + } + } + + return function(a, b) { + var s = [], // string constants and placeholders + q = []; // number interpolators + a = parse(a), b = parse(b); + translate(a.translateX, a.translateY, b.translateX, b.translateY, s, q); + rotate(a.rotate, b.rotate, s, q); + skewX(a.skewX, b.skewX, s, q); + scale(a.scaleX, a.scaleY, b.scaleX, b.scaleY, s, q); + a = b = null; // gc + return function(t) { + var i = -1, n = q.length, o; + while (++i < n) s[(o = q[i]).i] = o.x(t); + return s.join(""); + }; + }; +} + +var interpolateTransformCss = interpolateTransform(parseCss, "px, ", "px)", "deg)"); +var interpolateTransformSvg = interpolateTransform(parseSvg, ", ", ")", ")"); + +var epsilon2 = 1e-12; + +function cosh(x) { + return ((x = Math.exp(x)) + 1 / x) / 2; +} + +function sinh(x) { + return ((x = Math.exp(x)) - 1 / x) / 2; +} + +function tanh(x) { + return ((x = Math.exp(2 * x)) - 1) / (x + 1); +} + +var zoom = (function zoomRho(rho, rho2, rho4) { + + // p0 = [ux0, uy0, w0] + // p1 = [ux1, uy1, w1] + function zoom(p0, p1) { + var ux0 = p0[0], uy0 = p0[1], w0 = p0[2], + ux1 = p1[0], uy1 = p1[1], w1 = p1[2], + dx = ux1 - ux0, + dy = uy1 - uy0, + d2 = dx * dx + dy * dy, + i, + S; + + // Special case for u0 ≅ u1. + if (d2 < epsilon2) { + S = Math.log(w1 / w0) / rho; + i = function(t) { + return [ + ux0 + t * dx, + uy0 + t * dy, + w0 * Math.exp(rho * t * S) + ]; + }; + } + + // General case. + else { + var d1 = Math.sqrt(d2), + b0 = (w1 * w1 - w0 * w0 + rho4 * d2) / (2 * w0 * rho2 * d1), + b1 = (w1 * w1 - w0 * w0 - rho4 * d2) / (2 * w1 * rho2 * d1), + r0 = Math.log(Math.sqrt(b0 * b0 + 1) - b0), + r1 = Math.log(Math.sqrt(b1 * b1 + 1) - b1); + S = (r1 - r0) / rho; + i = function(t) { + var s = t * S, + coshr0 = cosh(r0), + u = w0 / (rho2 * d1) * (coshr0 * tanh(rho * s + r0) - sinh(r0)); + return [ + ux0 + u * dx, + uy0 + u * dy, + w0 * coshr0 / cosh(rho * s + r0) + ]; + }; + } + + i.duration = S * 1000 * rho / Math.SQRT2; + + return i; + } + + zoom.rho = function(_) { + var _1 = Math.max(1e-3, +_), _2 = _1 * _1, _4 = _2 * _2; + return zoomRho(_1, _2, _4); + }; + + return zoom; +})(Math.SQRT2, 2, 4); + +function hsl(hue) { + return function(start, end) { + var h = hue((start = d3Color.hsl(start)).h, (end = d3Color.hsl(end)).h), + s = nogamma(start.s, end.s), + l = nogamma(start.l, end.l), + opacity = nogamma(start.opacity, end.opacity); + return function(t) { + start.h = h(t); + start.s = s(t); + start.l = l(t); + start.opacity = opacity(t); + return start + ""; + }; + } +} + +var hsl$1 = hsl(hue$1); +var hslLong = hsl(nogamma); + +function lab(start, end) { + var l = nogamma((start = d3Color.lab(start)).l, (end = d3Color.lab(end)).l), + a = nogamma(start.a, end.a), + b = nogamma(start.b, end.b), + opacity = nogamma(start.opacity, end.opacity); + return function(t) { + start.l = l(t); + start.a = a(t); + start.b = b(t); + start.opacity = opacity(t); + return start + ""; + }; +} + +function hcl(hue) { + return function(start, end) { + var h = hue((start = d3Color.hcl(start)).h, (end = d3Color.hcl(end)).h), + c = nogamma(start.c, end.c), + l = nogamma(start.l, end.l), + opacity = nogamma(start.opacity, end.opacity); + return function(t) { + start.h = h(t); + start.c = c(t); + start.l = l(t); + start.opacity = opacity(t); + return start + ""; + }; + } +} + +var hcl$1 = hcl(hue$1); +var hclLong = hcl(nogamma); + +function cubehelix(hue) { + return (function cubehelixGamma(y) { + y = +y; + + function cubehelix(start, end) { + var h = hue((start = d3Color.cubehelix(start)).h, (end = d3Color.cubehelix(end)).h), + s = nogamma(start.s, end.s), + l = nogamma(start.l, end.l), + opacity = nogamma(start.opacity, end.opacity); + return function(t) { + start.h = h(t); + start.s = s(t); + start.l = l(Math.pow(t, y)); + start.opacity = opacity(t); + return start + ""; + }; + } + + cubehelix.gamma = cubehelixGamma; + + return cubehelix; + })(1); +} + +var cubehelix$1 = cubehelix(hue$1); +var cubehelixLong = cubehelix(nogamma); + +function piecewise(interpolate, values) { + if (values === undefined) values = interpolate, interpolate = value; + var i = 0, n = values.length - 1, v = values[0], I = new Array(n < 0 ? 0 : n); + while (i < n) I[i] = interpolate(v, v = values[++i]); + return function(t) { + var i = Math.max(0, Math.min(n - 1, Math.floor(t *= n))); + return I[i](t - i); + }; +} + +function quantize(interpolator, n) { + var samples = new Array(n); + for (var i = 0; i < n; ++i) samples[i] = interpolator(i / (n - 1)); + return samples; +} + +exports.interpolate = value; +exports.interpolateArray = array; +exports.interpolateBasis = basis$1; +exports.interpolateBasisClosed = basisClosed; +exports.interpolateCubehelix = cubehelix$1; +exports.interpolateCubehelixLong = cubehelixLong; +exports.interpolateDate = date; +exports.interpolateDiscrete = discrete; +exports.interpolateHcl = hcl$1; +exports.interpolateHclLong = hclLong; +exports.interpolateHsl = hsl$1; +exports.interpolateHslLong = hslLong; +exports.interpolateHue = hue; +exports.interpolateLab = lab; +exports.interpolateNumber = number; +exports.interpolateNumberArray = numberArray; +exports.interpolateObject = object; +exports.interpolateRgb = rgb; +exports.interpolateRgbBasis = rgbBasis; +exports.interpolateRgbBasisClosed = rgbBasisClosed; +exports.interpolateRound = round; +exports.interpolateString = string; +exports.interpolateTransformCss = interpolateTransformCss; +exports.interpolateTransformSvg = interpolateTransformSvg; +exports.interpolateZoom = zoom; +exports.piecewise = piecewise; +exports.quantize = quantize; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-interpolate/dist/d3-interpolate.min.js b/frontend/node_modules/d3-interpolate/dist/d3-interpolate.min.js new file mode 100644 index 0000000..d1b6263 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/dist/d3-interpolate.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-interpolate/ v3.0.1 Copyright 2010-2021 Mike Bostock +!function(t,n){"object"==typeof exports&&"undefined"!=typeof module?n(exports,require("d3-color")):"function"==typeof define&&define.amd?define(["exports","d3-color"],n):n((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{},t.d3)}(this,(function(t,n){"use strict";function r(t,n,r,e,a){var o=t*t,u=o*t;return((1-3*t+3*o-u)*n+(4-6*o+3*u)*r+(1+3*t+3*o-3*u)*e+u*a)/6}function e(t){var n=t.length-1;return function(e){var a=e<=0?e=0:e>=1?(e=1,n-1):Math.floor(e*n),o=t[a],u=t[a+1],i=a>0?t[a-1]:2*o-u,c=a()=>t;function u(t,n){return function(r){return t+r*n}}function i(t,n){var r=n-t;return r?u(t,r>180||r<-180?r-360*Math.round(r/360):r):o(isNaN(t)?n:t)}function c(t){return 1==(t=+t)?l:function(n,r){return r-n?function(t,n,r){return t=Math.pow(t,r),n=Math.pow(n,r)-t,r=1/r,function(e){return Math.pow(t+e*n,r)}}(n,r,t):o(isNaN(n)?r:n)}}function l(t,n){var r=n-t;return r?u(t,r):o(isNaN(t)?n:t)}var f=function t(r){var e=c(r);function a(t,r){var a=e((t=n.rgb(t)).r,(r=n.rgb(r)).r),o=e(t.g,r.g),u=e(t.b,r.b),i=l(t.opacity,r.opacity);return function(n){return t.r=a(n),t.g=o(n),t.b=u(n),t.opacity=i(n),t+""}}return a.gamma=t,a}(1);function s(t){return function(r){var e,a,o=r.length,u=new Array(o),i=new Array(o),c=new Array(o);for(e=0;eo&&(a=n.slice(o,a),i[u]?i[u]+=a:i[++u]=a),(r=r[0])===(e=e[0])?i[u]?i[u]+=e:i[++u]=e:(i[++u]=null,c.push({i:u,x:b(r,e)})),o=w.lastIndex;return o180?n+=360:n-t>180&&(t+=360),o.push({i:r.push(a(r)+"rotate(",null,e)-2,x:b(t,n)})):n&&r.push(a(r)+"rotate("+n+e)}(o.rotate,u.rotate,i,c),function(t,n,r,o){t!==n?o.push({i:r.push(a(r)+"skewX(",null,e)-2,x:b(t,n)}):n&&r.push(a(r)+"skewX("+n+e)}(o.skewX,u.skewX,i,c),function(t,n,r,e,o,u){if(t!==r||n!==e){var i=o.push(a(o)+"scale(",null,",",null,")");u.push({i:i-4,x:b(t,r)},{i:i-2,x:b(n,e)})}else 1===r&&1===e||o.push(a(o)+"scale("+r+","+e+")")}(o.scaleX,o.scaleY,u.scaleX,u.scaleY,i,c),o=u=null,function(t){for(var n,r=-1,e=c.length;++r=12" + } +} diff --git a/frontend/node_modules/d3-interpolate/src/array.js b/frontend/node_modules/d3-interpolate/src/array.js new file mode 100644 index 0000000..89f7722 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/array.js @@ -0,0 +1,22 @@ +import value from "./value.js"; +import numberArray, {isNumberArray} from "./numberArray.js"; + +export default function(a, b) { + return (isNumberArray(b) ? numberArray : genericArray)(a, b); +} + +export function genericArray(a, b) { + var nb = b ? b.length : 0, + na = a ? Math.min(nb, a.length) : 0, + x = new Array(na), + c = new Array(nb), + i; + + for (i = 0; i < na; ++i) x[i] = value(a[i], b[i]); + for (; i < nb; ++i) c[i] = b[i]; + + return function(t) { + for (i = 0; i < na; ++i) c[i] = x[i](t); + return c; + }; +} diff --git a/frontend/node_modules/d3-interpolate/src/basis.js b/frontend/node_modules/d3-interpolate/src/basis.js new file mode 100644 index 0000000..0d853f0 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/basis.js @@ -0,0 +1,19 @@ +export function basis(t1, v0, v1, v2, v3) { + var t2 = t1 * t1, t3 = t2 * t1; + return ((1 - 3 * t1 + 3 * t2 - t3) * v0 + + (4 - 6 * t2 + 3 * t3) * v1 + + (1 + 3 * t1 + 3 * t2 - 3 * t3) * v2 + + t3 * v3) / 6; +} + +export default function(values) { + var n = values.length - 1; + return function(t) { + var i = t <= 0 ? (t = 0) : t >= 1 ? (t = 1, n - 1) : Math.floor(t * n), + v1 = values[i], + v2 = values[i + 1], + v0 = i > 0 ? values[i - 1] : 2 * v1 - v2, + v3 = i < n - 1 ? values[i + 2] : 2 * v2 - v1; + return basis((t - i / n) * n, v0, v1, v2, v3); + }; +} diff --git a/frontend/node_modules/d3-interpolate/src/basisClosed.js b/frontend/node_modules/d3-interpolate/src/basisClosed.js new file mode 100644 index 0000000..2639d92 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/basisClosed.js @@ -0,0 +1,13 @@ +import {basis} from "./basis.js"; + +export default function(values) { + var n = values.length; + return function(t) { + var i = Math.floor(((t %= 1) < 0 ? ++t : t) * n), + v0 = values[(i + n - 1) % n], + v1 = values[i % n], + v2 = values[(i + 1) % n], + v3 = values[(i + 2) % n]; + return basis((t - i / n) * n, v0, v1, v2, v3); + }; +} diff --git a/frontend/node_modules/d3-interpolate/src/color.js b/frontend/node_modules/d3-interpolate/src/color.js new file mode 100644 index 0000000..4630fb2 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/color.js @@ -0,0 +1,29 @@ +import constant from "./constant.js"; + +function linear(a, d) { + return function(t) { + return a + t * d; + }; +} + +function exponential(a, b, y) { + return a = Math.pow(a, y), b = Math.pow(b, y) - a, y = 1 / y, function(t) { + return Math.pow(a + t * b, y); + }; +} + +export function hue(a, b) { + var d = b - a; + return d ? linear(a, d > 180 || d < -180 ? d - 360 * Math.round(d / 360) : d) : constant(isNaN(a) ? b : a); +} + +export function gamma(y) { + return (y = +y) === 1 ? nogamma : function(a, b) { + return b - a ? exponential(a, b, y) : constant(isNaN(a) ? b : a); + }; +} + +export default function nogamma(a, b) { + var d = b - a; + return d ? linear(a, d) : constant(isNaN(a) ? b : a); +} diff --git a/frontend/node_modules/d3-interpolate/src/constant.js b/frontend/node_modules/d3-interpolate/src/constant.js new file mode 100644 index 0000000..3487c0d --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/constant.js @@ -0,0 +1 @@ +export default x => () => x; diff --git a/frontend/node_modules/d3-interpolate/src/cubehelix.js b/frontend/node_modules/d3-interpolate/src/cubehelix.js new file mode 100644 index 0000000..2c4f64b --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/cubehelix.js @@ -0,0 +1,29 @@ +import {cubehelix as colorCubehelix} from "d3-color"; +import color, {hue} from "./color.js"; + +function cubehelix(hue) { + return (function cubehelixGamma(y) { + y = +y; + + function cubehelix(start, end) { + var h = hue((start = colorCubehelix(start)).h, (end = colorCubehelix(end)).h), + s = color(start.s, end.s), + l = color(start.l, end.l), + opacity = color(start.opacity, end.opacity); + return function(t) { + start.h = h(t); + start.s = s(t); + start.l = l(Math.pow(t, y)); + start.opacity = opacity(t); + return start + ""; + }; + } + + cubehelix.gamma = cubehelixGamma; + + return cubehelix; + })(1); +} + +export default cubehelix(hue); +export var cubehelixLong = cubehelix(color); diff --git a/frontend/node_modules/d3-interpolate/src/date.js b/frontend/node_modules/d3-interpolate/src/date.js new file mode 100644 index 0000000..cdfbea7 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/date.js @@ -0,0 +1,6 @@ +export default function(a, b) { + var d = new Date; + return a = +a, b = +b, function(t) { + return d.setTime(a * (1 - t) + b * t), d; + }; +} diff --git a/frontend/node_modules/d3-interpolate/src/discrete.js b/frontend/node_modules/d3-interpolate/src/discrete.js new file mode 100644 index 0000000..b3d1e3b --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/discrete.js @@ -0,0 +1,6 @@ +export default function(range) { + var n = range.length; + return function(t) { + return range[Math.max(0, Math.min(n - 1, Math.floor(t * n)))]; + }; +} diff --git a/frontend/node_modules/d3-interpolate/src/hcl.js b/frontend/node_modules/d3-interpolate/src/hcl.js new file mode 100644 index 0000000..0312580 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/hcl.js @@ -0,0 +1,21 @@ +import {hcl as colorHcl} from "d3-color"; +import color, {hue} from "./color.js"; + +function hcl(hue) { + return function(start, end) { + var h = hue((start = colorHcl(start)).h, (end = colorHcl(end)).h), + c = color(start.c, end.c), + l = color(start.l, end.l), + opacity = color(start.opacity, end.opacity); + return function(t) { + start.h = h(t); + start.c = c(t); + start.l = l(t); + start.opacity = opacity(t); + return start + ""; + }; + } +} + +export default hcl(hue); +export var hclLong = hcl(color); diff --git a/frontend/node_modules/d3-interpolate/src/hsl.js b/frontend/node_modules/d3-interpolate/src/hsl.js new file mode 100644 index 0000000..2f78a90 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/hsl.js @@ -0,0 +1,21 @@ +import {hsl as colorHsl} from "d3-color"; +import color, {hue} from "./color.js"; + +function hsl(hue) { + return function(start, end) { + var h = hue((start = colorHsl(start)).h, (end = colorHsl(end)).h), + s = color(start.s, end.s), + l = color(start.l, end.l), + opacity = color(start.opacity, end.opacity); + return function(t) { + start.h = h(t); + start.s = s(t); + start.l = l(t); + start.opacity = opacity(t); + return start + ""; + }; + } +} + +export default hsl(hue); +export var hslLong = hsl(color); diff --git a/frontend/node_modules/d3-interpolate/src/hue.js b/frontend/node_modules/d3-interpolate/src/hue.js new file mode 100644 index 0000000..5d8d4b9 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/hue.js @@ -0,0 +1,9 @@ +import {hue} from "./color.js"; + +export default function(a, b) { + var i = hue(+a, +b); + return function(t) { + var x = i(t); + return x - 360 * Math.floor(x / 360); + }; +} diff --git a/frontend/node_modules/d3-interpolate/src/index.js b/frontend/node_modules/d3-interpolate/src/index.js new file mode 100644 index 0000000..b4dce7d --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/index.js @@ -0,0 +1,21 @@ +export {default as interpolate} from "./value.js"; +export {default as interpolateArray} from "./array.js"; +export {default as interpolateBasis} from "./basis.js"; +export {default as interpolateBasisClosed} from "./basisClosed.js"; +export {default as interpolateDate} from "./date.js"; +export {default as interpolateDiscrete} from "./discrete.js"; +export {default as interpolateHue} from "./hue.js"; +export {default as interpolateNumber} from "./number.js"; +export {default as interpolateNumberArray} from "./numberArray.js"; +export {default as interpolateObject} from "./object.js"; +export {default as interpolateRound} from "./round.js"; +export {default as interpolateString} from "./string.js"; +export {interpolateTransformCss, interpolateTransformSvg} from "./transform/index.js"; +export {default as interpolateZoom} from "./zoom.js"; +export {default as interpolateRgb, rgbBasis as interpolateRgbBasis, rgbBasisClosed as interpolateRgbBasisClosed} from "./rgb.js"; +export {default as interpolateHsl, hslLong as interpolateHslLong} from "./hsl.js"; +export {default as interpolateLab} from "./lab.js"; +export {default as interpolateHcl, hclLong as interpolateHclLong} from "./hcl.js"; +export {default as interpolateCubehelix, cubehelixLong as interpolateCubehelixLong} from "./cubehelix.js"; +export {default as piecewise} from "./piecewise.js"; +export {default as quantize} from "./quantize.js"; diff --git a/frontend/node_modules/d3-interpolate/src/lab.js b/frontend/node_modules/d3-interpolate/src/lab.js new file mode 100644 index 0000000..8fbf7f3 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/lab.js @@ -0,0 +1,16 @@ +import {lab as colorLab} from "d3-color"; +import color from "./color.js"; + +export default function lab(start, end) { + var l = color((start = colorLab(start)).l, (end = colorLab(end)).l), + a = color(start.a, end.a), + b = color(start.b, end.b), + opacity = color(start.opacity, end.opacity); + return function(t) { + start.l = l(t); + start.a = a(t); + start.b = b(t); + start.opacity = opacity(t); + return start + ""; + }; +} diff --git a/frontend/node_modules/d3-interpolate/src/number.js b/frontend/node_modules/d3-interpolate/src/number.js new file mode 100644 index 0000000..837b13d --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/number.js @@ -0,0 +1,5 @@ +export default function(a, b) { + return a = +a, b = +b, function(t) { + return a * (1 - t) + b * t; + }; +} diff --git a/frontend/node_modules/d3-interpolate/src/numberArray.js b/frontend/node_modules/d3-interpolate/src/numberArray.js new file mode 100644 index 0000000..4081086 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/numberArray.js @@ -0,0 +1,14 @@ +export default function(a, b) { + if (!b) b = []; + var n = a ? Math.min(b.length, a.length) : 0, + c = b.slice(), + i; + return function(t) { + for (i = 0; i < n; ++i) c[i] = a[i] * (1 - t) + b[i] * t; + return c; + }; +} + +export function isNumberArray(x) { + return ArrayBuffer.isView(x) && !(x instanceof DataView); +} diff --git a/frontend/node_modules/d3-interpolate/src/object.js b/frontend/node_modules/d3-interpolate/src/object.js new file mode 100644 index 0000000..b521c33 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/object.js @@ -0,0 +1,23 @@ +import value from "./value.js"; + +export default function(a, b) { + var i = {}, + c = {}, + k; + + if (a === null || typeof a !== "object") a = {}; + if (b === null || typeof b !== "object") b = {}; + + for (k in b) { + if (k in a) { + i[k] = value(a[k], b[k]); + } else { + c[k] = b[k]; + } + } + + return function(t) { + for (k in i) c[k] = i[k](t); + return c; + }; +} diff --git a/frontend/node_modules/d3-interpolate/src/piecewise.js b/frontend/node_modules/d3-interpolate/src/piecewise.js new file mode 100644 index 0000000..8b568c5 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/piecewise.js @@ -0,0 +1,11 @@ +import {default as value} from "./value.js"; + +export default function piecewise(interpolate, values) { + if (values === undefined) values = interpolate, interpolate = value; + var i = 0, n = values.length - 1, v = values[0], I = new Array(n < 0 ? 0 : n); + while (i < n) I[i] = interpolate(v, v = values[++i]); + return function(t) { + var i = Math.max(0, Math.min(n - 1, Math.floor(t *= n))); + return I[i](t - i); + }; +} diff --git a/frontend/node_modules/d3-interpolate/src/quantize.js b/frontend/node_modules/d3-interpolate/src/quantize.js new file mode 100644 index 0000000..d7c23e6 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/quantize.js @@ -0,0 +1,5 @@ +export default function(interpolator, n) { + var samples = new Array(n); + for (var i = 0; i < n; ++i) samples[i] = interpolator(i / (n - 1)); + return samples; +} diff --git a/frontend/node_modules/d3-interpolate/src/rgb.js b/frontend/node_modules/d3-interpolate/src/rgb.js new file mode 100644 index 0000000..495c1f8 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/rgb.js @@ -0,0 +1,55 @@ +import {rgb as colorRgb} from "d3-color"; +import basis from "./basis.js"; +import basisClosed from "./basisClosed.js"; +import nogamma, {gamma} from "./color.js"; + +export default (function rgbGamma(y) { + var color = gamma(y); + + function rgb(start, end) { + var r = color((start = colorRgb(start)).r, (end = colorRgb(end)).r), + g = color(start.g, end.g), + b = color(start.b, end.b), + opacity = nogamma(start.opacity, end.opacity); + return function(t) { + start.r = r(t); + start.g = g(t); + start.b = b(t); + start.opacity = opacity(t); + return start + ""; + }; + } + + rgb.gamma = rgbGamma; + + return rgb; +})(1); + +function rgbSpline(spline) { + return function(colors) { + var n = colors.length, + r = new Array(n), + g = new Array(n), + b = new Array(n), + i, color; + for (i = 0; i < n; ++i) { + color = colorRgb(colors[i]); + r[i] = color.r || 0; + g[i] = color.g || 0; + b[i] = color.b || 0; + } + r = spline(r); + g = spline(g); + b = spline(b); + color.opacity = 1; + return function(t) { + color.r = r(t); + color.g = g(t); + color.b = b(t); + return color + ""; + }; + }; +} + +export var rgbBasis = rgbSpline(basis); +export var rgbBasisClosed = rgbSpline(basisClosed); diff --git a/frontend/node_modules/d3-interpolate/src/round.js b/frontend/node_modules/d3-interpolate/src/round.js new file mode 100644 index 0000000..2635d28 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/round.js @@ -0,0 +1,5 @@ +export default function(a, b) { + return a = +a, b = +b, function(t) { + return Math.round(a * (1 - t) + b * t); + }; +} diff --git a/frontend/node_modules/d3-interpolate/src/string.js b/frontend/node_modules/d3-interpolate/src/string.js new file mode 100644 index 0000000..7f04d2d --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/string.js @@ -0,0 +1,64 @@ +import number from "./number.js"; + +var reA = /[-+]?(?:\d+\.?\d*|\.?\d+)(?:[eE][-+]?\d+)?/g, + reB = new RegExp(reA.source, "g"); + +function zero(b) { + return function() { + return b; + }; +} + +function one(b) { + return function(t) { + return b(t) + ""; + }; +} + +export default function(a, b) { + var bi = reA.lastIndex = reB.lastIndex = 0, // scan index for next number in b + am, // current match in a + bm, // current match in b + bs, // string preceding current number in b, if any + i = -1, // index in s + s = [], // string constants and placeholders + q = []; // number interpolators + + // Coerce inputs to strings. + a = a + "", b = b + ""; + + // Interpolate pairs of numbers in a & b. + while ((am = reA.exec(a)) + && (bm = reB.exec(b))) { + if ((bs = bm.index) > bi) { // a string precedes the next number in b + bs = b.slice(bi, bs); + if (s[i]) s[i] += bs; // coalesce with previous string + else s[++i] = bs; + } + if ((am = am[0]) === (bm = bm[0])) { // numbers in a & b match + if (s[i]) s[i] += bm; // coalesce with previous string + else s[++i] = bm; + } else { // interpolate non-matching numbers + s[++i] = null; + q.push({i: i, x: number(am, bm)}); + } + bi = reB.lastIndex; + } + + // Add remains of b. + if (bi < b.length) { + bs = b.slice(bi); + if (s[i]) s[i] += bs; // coalesce with previous string + else s[++i] = bs; + } + + // Special optimization for only a single match. + // Otherwise, interpolate each of the numbers and rejoin the string. + return s.length < 2 ? (q[0] + ? one(q[0].x) + : zero(b)) + : (b = q.length, function(t) { + for (var i = 0, o; i < b; ++i) s[(o = q[i]).i] = o.x(t); + return s.join(""); + }); +} diff --git a/frontend/node_modules/d3-interpolate/src/transform/decompose.js b/frontend/node_modules/d3-interpolate/src/transform/decompose.js new file mode 100644 index 0000000..3535f23 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/transform/decompose.js @@ -0,0 +1,26 @@ +var degrees = 180 / Math.PI; + +export var identity = { + translateX: 0, + translateY: 0, + rotate: 0, + skewX: 0, + scaleX: 1, + scaleY: 1 +}; + +export default function(a, b, c, d, e, f) { + var scaleX, scaleY, skewX; + if (scaleX = Math.sqrt(a * a + b * b)) a /= scaleX, b /= scaleX; + if (skewX = a * c + b * d) c -= a * skewX, d -= b * skewX; + if (scaleY = Math.sqrt(c * c + d * d)) c /= scaleY, d /= scaleY, skewX /= scaleY; + if (a * d < b * c) a = -a, b = -b, skewX = -skewX, scaleX = -scaleX; + return { + translateX: e, + translateY: f, + rotate: Math.atan2(b, a) * degrees, + skewX: Math.atan(skewX) * degrees, + scaleX: scaleX, + scaleY: scaleY + }; +} diff --git a/frontend/node_modules/d3-interpolate/src/transform/index.js b/frontend/node_modules/d3-interpolate/src/transform/index.js new file mode 100644 index 0000000..5383d5f --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/transform/index.js @@ -0,0 +1,63 @@ +import number from "../number.js"; +import {parseCss, parseSvg} from "./parse.js"; + +function interpolateTransform(parse, pxComma, pxParen, degParen) { + + function pop(s) { + return s.length ? s.pop() + " " : ""; + } + + function translate(xa, ya, xb, yb, s, q) { + if (xa !== xb || ya !== yb) { + var i = s.push("translate(", null, pxComma, null, pxParen); + q.push({i: i - 4, x: number(xa, xb)}, {i: i - 2, x: number(ya, yb)}); + } else if (xb || yb) { + s.push("translate(" + xb + pxComma + yb + pxParen); + } + } + + function rotate(a, b, s, q) { + if (a !== b) { + if (a - b > 180) b += 360; else if (b - a > 180) a += 360; // shortest path + q.push({i: s.push(pop(s) + "rotate(", null, degParen) - 2, x: number(a, b)}); + } else if (b) { + s.push(pop(s) + "rotate(" + b + degParen); + } + } + + function skewX(a, b, s, q) { + if (a !== b) { + q.push({i: s.push(pop(s) + "skewX(", null, degParen) - 2, x: number(a, b)}); + } else if (b) { + s.push(pop(s) + "skewX(" + b + degParen); + } + } + + function scale(xa, ya, xb, yb, s, q) { + if (xa !== xb || ya !== yb) { + var i = s.push(pop(s) + "scale(", null, ",", null, ")"); + q.push({i: i - 4, x: number(xa, xb)}, {i: i - 2, x: number(ya, yb)}); + } else if (xb !== 1 || yb !== 1) { + s.push(pop(s) + "scale(" + xb + "," + yb + ")"); + } + } + + return function(a, b) { + var s = [], // string constants and placeholders + q = []; // number interpolators + a = parse(a), b = parse(b); + translate(a.translateX, a.translateY, b.translateX, b.translateY, s, q); + rotate(a.rotate, b.rotate, s, q); + skewX(a.skewX, b.skewX, s, q); + scale(a.scaleX, a.scaleY, b.scaleX, b.scaleY, s, q); + a = b = null; // gc + return function(t) { + var i = -1, n = q.length, o; + while (++i < n) s[(o = q[i]).i] = o.x(t); + return s.join(""); + }; + }; +} + +export var interpolateTransformCss = interpolateTransform(parseCss, "px, ", "px)", "deg)"); +export var interpolateTransformSvg = interpolateTransform(parseSvg, ", ", ")", ")"); diff --git a/frontend/node_modules/d3-interpolate/src/transform/parse.js b/frontend/node_modules/d3-interpolate/src/transform/parse.js new file mode 100644 index 0000000..c62088e --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/transform/parse.js @@ -0,0 +1,18 @@ +import decompose, {identity} from "./decompose.js"; + +var svgNode; + +/* eslint-disable no-undef */ +export function parseCss(value) { + const m = new (typeof DOMMatrix === "function" ? DOMMatrix : WebKitCSSMatrix)(value + ""); + return m.isIdentity ? identity : decompose(m.a, m.b, m.c, m.d, m.e, m.f); +} + +export function parseSvg(value) { + if (value == null) return identity; + if (!svgNode) svgNode = document.createElementNS("http://www.w3.org/2000/svg", "g"); + svgNode.setAttribute("transform", value); + if (!(value = svgNode.transform.baseVal.consolidate())) return identity; + value = value.matrix; + return decompose(value.a, value.b, value.c, value.d, value.e, value.f); +} diff --git a/frontend/node_modules/d3-interpolate/src/value.js b/frontend/node_modules/d3-interpolate/src/value.js new file mode 100644 index 0000000..6a67ac4 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/value.js @@ -0,0 +1,22 @@ +import {color} from "d3-color"; +import rgb from "./rgb.js"; +import {genericArray} from "./array.js"; +import date from "./date.js"; +import number from "./number.js"; +import object from "./object.js"; +import string from "./string.js"; +import constant from "./constant.js"; +import numberArray, {isNumberArray} from "./numberArray.js"; + +export default function(a, b) { + var t = typeof b, c; + return b == null || t === "boolean" ? constant(b) + : (t === "number" ? number + : t === "string" ? ((c = color(b)) ? (b = c, rgb) : string) + : b instanceof color ? rgb + : b instanceof Date ? date + : isNumberArray(b) ? numberArray + : Array.isArray(b) ? genericArray + : typeof b.valueOf !== "function" && typeof b.toString !== "function" || isNaN(b) ? object + : number)(a, b); +} diff --git a/frontend/node_modules/d3-interpolate/src/zoom.js b/frontend/node_modules/d3-interpolate/src/zoom.js new file mode 100644 index 0000000..f275602 --- /dev/null +++ b/frontend/node_modules/d3-interpolate/src/zoom.js @@ -0,0 +1,71 @@ +var epsilon2 = 1e-12; + +function cosh(x) { + return ((x = Math.exp(x)) + 1 / x) / 2; +} + +function sinh(x) { + return ((x = Math.exp(x)) - 1 / x) / 2; +} + +function tanh(x) { + return ((x = Math.exp(2 * x)) - 1) / (x + 1); +} + +export default (function zoomRho(rho, rho2, rho4) { + + // p0 = [ux0, uy0, w0] + // p1 = [ux1, uy1, w1] + function zoom(p0, p1) { + var ux0 = p0[0], uy0 = p0[1], w0 = p0[2], + ux1 = p1[0], uy1 = p1[1], w1 = p1[2], + dx = ux1 - ux0, + dy = uy1 - uy0, + d2 = dx * dx + dy * dy, + i, + S; + + // Special case for u0 ≅ u1. + if (d2 < epsilon2) { + S = Math.log(w1 / w0) / rho; + i = function(t) { + return [ + ux0 + t * dx, + uy0 + t * dy, + w0 * Math.exp(rho * t * S) + ]; + } + } + + // General case. + else { + var d1 = Math.sqrt(d2), + b0 = (w1 * w1 - w0 * w0 + rho4 * d2) / (2 * w0 * rho2 * d1), + b1 = (w1 * w1 - w0 * w0 - rho4 * d2) / (2 * w1 * rho2 * d1), + r0 = Math.log(Math.sqrt(b0 * b0 + 1) - b0), + r1 = Math.log(Math.sqrt(b1 * b1 + 1) - b1); + S = (r1 - r0) / rho; + i = function(t) { + var s = t * S, + coshr0 = cosh(r0), + u = w0 / (rho2 * d1) * (coshr0 * tanh(rho * s + r0) - sinh(r0)); + return [ + ux0 + u * dx, + uy0 + u * dy, + w0 * coshr0 / cosh(rho * s + r0) + ]; + } + } + + i.duration = S * 1000 * rho / Math.SQRT2; + + return i; + } + + zoom.rho = function(_) { + var _1 = Math.max(1e-3, +_), _2 = _1 * _1, _4 = _2 * _2; + return zoomRho(_1, _2, _4); + }; + + return zoom; +})(Math.SQRT2, 2, 4); diff --git a/frontend/node_modules/d3-path/LICENSE b/frontend/node_modules/d3-path/LICENSE new file mode 100644 index 0000000..ed25746 --- /dev/null +++ b/frontend/node_modules/d3-path/LICENSE @@ -0,0 +1,13 @@ +Copyright 2015-2022 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-path/README.md b/frontend/node_modules/d3-path/README.md new file mode 100644 index 0000000..344f686 --- /dev/null +++ b/frontend/node_modules/d3-path/README.md @@ -0,0 +1,94 @@ +# d3-path + +Say you have some code that draws to a 2D canvas: + +```js +function drawCircle(context, radius) { + context.moveTo(radius, 0); + context.arc(0, 0, radius, 0, 2 * Math.PI); +} +``` + +The d3-path module lets you take this exact code and additionally render to [SVG](http://www.w3.org/TR/SVG/paths.html). It works by [serializing](#path_toString) [CanvasPathMethods](http://www.w3.org/TR/2dcontext/#canvaspathmethods) calls to [SVG path data](http://www.w3.org/TR/SVG/paths.html#PathData). For example: + +```js +const context = d3.path(); +drawCircle(context, 40); +pathElement.setAttribute("d", context.toString()); +``` + +Now code you write once can be used with both Canvas (for performance) and SVG (for convenience). For a practical example, see [d3-shape](https://github.com/d3/d3-shape). + +## Installing + +If you use npm, `npm install d3-path`. You can also download the [latest release on GitHub](https://github.com/d3/d3-path/releases/latest). In modern browsers, you can import d3-path from jsDelivr: + +```html + +``` + +For legacy environments, you can load d3-path’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +## API Reference + +# d3.path() · [Source](https://github.com/d3/d3-path/blob/master/src/path.js), [Examples](https://observablehq.com/@d3/d3-path) + +Constructs a new path serializer that implements [CanvasPathMethods](http://www.w3.org/TR/2dcontext/#canvaspathmethods). + +# path.moveTo(x, y) + +Move to the specified point ⟨*x*, *y*⟩. Equivalent to [*context*.moveTo](http://www.w3.org/TR/2dcontext/#dom-context-2d-moveto) and SVG’s [“moveto” command](http://www.w3.org/TR/SVG/paths.html#PathDataMovetoCommands). + +# path.closePath() + +Ends the current subpath and causes an automatic straight line to be drawn from the current point to the initial point of the current subpath. Equivalent to [*context*.closePath](http://www.w3.org/TR/2dcontext/#dom-context-2d-closepath) and SVG’s [“closepath” command](http://www.w3.org/TR/SVG/paths.html#PathDataClosePathCommand). + +# path.lineTo(x, y) + +Draws a straight line from the current point to the specified point ⟨*x*, *y*⟩. Equivalent to [*context*.lineTo](http://www.w3.org/TR/2dcontext/#dom-context-2d-lineto) and SVG’s [“lineto” command](http://www.w3.org/TR/SVG/paths.html#PathDataLinetoCommands). + +# path.quadraticCurveTo(cpx, cpy, x, y) + +Draws a quadratic Bézier segment from the current point to the specified point ⟨*x*, *y*⟩, with the specified control point ⟨*cpx*, *cpy*⟩. Equivalent to [*context*.quadraticCurveTo](http://www.w3.org/TR/2dcontext/#dom-context-2d-quadraticcurveto) and SVG’s [quadratic Bézier curve commands](http://www.w3.org/TR/SVG/paths.html#PathDataQuadraticBezierCommands). + +# path.bezierCurveTo(cpx1, cpy1, cpx2, cpy2, x, y) + +Draws a cubic Bézier segment from the current point to the specified point ⟨*x*, *y*⟩, with the specified control points ⟨*cpx1*, *cpy1*⟩ and ⟨*cpx2*, *cpy2*⟩. Equivalent to [*context*.bezierCurveTo](http://www.w3.org/TR/2dcontext/#dom-context-2d-beziercurveto) and SVG’s [cubic Bézier curve commands](http://www.w3.org/TR/SVG/paths.html#PathDataCubicBezierCommands). + +# path.arcTo(x1, y1, x2, y2, radius) + +Draws a circular arc segment with the specified *radius* that starts tangent to the line between the current point and the specified point ⟨*x1*, *y1*⟩ and ends tangent to the line between the specified points ⟨*x1*, *y1*⟩ and ⟨*x2*, *y2*⟩. If the first tangent point is not equal to the current point, a straight line is drawn between the current point and the first tangent point. Equivalent to [*context*.arcTo](http://www.w3.org/TR/2dcontext/#dom-context-2d-arcto) and uses SVG’s [elliptical arc curve commands](http://www.w3.org/TR/SVG/paths.html#PathDataEllipticalArcCommands). + +# path.arc(x, y, radius, startAngle, endAngle[, anticlockwise]) + +Draws a circular arc segment with the specified center ⟨*x*, *y*⟩, *radius*, *startAngle* and *endAngle*. If *anticlockwise* is true, the arc is drawn in the anticlockwise direction; otherwise, it is drawn in the clockwise direction. If the current point is not equal to the starting point of the arc, a straight line is drawn from the current point to the start of the arc. Equivalent to [*context*.arc](http://www.w3.org/TR/2dcontext/#dom-context-2d-arc) and uses SVG’s [elliptical arc curve commands](http://www.w3.org/TR/SVG/paths.html#PathDataEllipticalArcCommands). + +# path.rect(x, y, w, h) + +Creates a new subpath containing just the four points ⟨*x*, *y*⟩, ⟨*x* + *w*, *y*⟩, ⟨*x* + *w*, *y* + *h*⟩, ⟨*x*, *y* + *h*⟩, with those four points connected by straight lines, and then marks the subpath as closed. Equivalent to [*context*.rect](http://www.w3.org/TR/2dcontext/#dom-context-2d-rect) and uses SVG’s [“lineto” commands](http://www.w3.org/TR/SVG/paths.html#PathDataLinetoCommands). + +# path.toString() + +Returns the string representation of this *path* according to SVG’s [path data specification](http://www.w3.org/TR/SVG/paths.html#PathData). + +# d3.pathRound(*digits* = 3) · [Source](https://github.com/d3/d3-path/blob/master/src/path.js), [Examples](https://observablehq.com/@d3/d3-path) + +Like [d3.path](#path), except limits the digits after the decimal to the specified number of *digits*. diff --git a/frontend/node_modules/d3-path/dist/d3-path.js b/frontend/node_modules/d3-path/dist/d3-path.js new file mode 100644 index 0000000..22957bf --- /dev/null +++ b/frontend/node_modules/d3-path/dist/d3-path.js @@ -0,0 +1,169 @@ +// https://d3js.org/d3-path/ v3.1.0 Copyright 2015-2022 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +})(this, (function (exports) { 'use strict'; + +const pi = Math.PI, + tau = 2 * pi, + epsilon = 1e-6, + tauEpsilon = tau - epsilon; + +function append(strings) { + this._ += strings[0]; + for (let i = 1, n = strings.length; i < n; ++i) { + this._ += arguments[i] + strings[i]; + } +} + +function appendRound(digits) { + let d = Math.floor(digits); + if (!(d >= 0)) throw new Error(`invalid digits: ${digits}`); + if (d > 15) return append; + const k = 10 ** d; + return function(strings) { + this._ += strings[0]; + for (let i = 1, n = strings.length; i < n; ++i) { + this._ += Math.round(arguments[i] * k) / k + strings[i]; + } + }; +} + +class Path { + constructor(digits) { + this._x0 = this._y0 = // start of current subpath + this._x1 = this._y1 = null; // end of current subpath + this._ = ""; + this._append = digits == null ? append : appendRound(digits); + } + moveTo(x, y) { + this._append`M${this._x0 = this._x1 = +x},${this._y0 = this._y1 = +y}`; + } + closePath() { + if (this._x1 !== null) { + this._x1 = this._x0, this._y1 = this._y0; + this._append`Z`; + } + } + lineTo(x, y) { + this._append`L${this._x1 = +x},${this._y1 = +y}`; + } + quadraticCurveTo(x1, y1, x, y) { + this._append`Q${+x1},${+y1},${this._x1 = +x},${this._y1 = +y}`; + } + bezierCurveTo(x1, y1, x2, y2, x, y) { + this._append`C${+x1},${+y1},${+x2},${+y2},${this._x1 = +x},${this._y1 = +y}`; + } + arcTo(x1, y1, x2, y2, r) { + x1 = +x1, y1 = +y1, x2 = +x2, y2 = +y2, r = +r; + + // Is the radius negative? Error. + if (r < 0) throw new Error(`negative radius: ${r}`); + + let x0 = this._x1, + y0 = this._y1, + x21 = x2 - x1, + y21 = y2 - y1, + x01 = x0 - x1, + y01 = y0 - y1, + l01_2 = x01 * x01 + y01 * y01; + + // Is this path empty? Move to (x1,y1). + if (this._x1 === null) { + this._append`M${this._x1 = x1},${this._y1 = y1}`; + } + + // Or, is (x1,y1) coincident with (x0,y0)? Do nothing. + else if (!(l01_2 > epsilon)); + + // Or, are (x0,y0), (x1,y1) and (x2,y2) collinear? + // Equivalently, is (x1,y1) coincident with (x2,y2)? + // Or, is the radius zero? Line to (x1,y1). + else if (!(Math.abs(y01 * x21 - y21 * x01) > epsilon) || !r) { + this._append`L${this._x1 = x1},${this._y1 = y1}`; + } + + // Otherwise, draw an arc! + else { + let x20 = x2 - x0, + y20 = y2 - y0, + l21_2 = x21 * x21 + y21 * y21, + l20_2 = x20 * x20 + y20 * y20, + l21 = Math.sqrt(l21_2), + l01 = Math.sqrt(l01_2), + l = r * Math.tan((pi - Math.acos((l21_2 + l01_2 - l20_2) / (2 * l21 * l01))) / 2), + t01 = l / l01, + t21 = l / l21; + + // If the start tangent is not coincident with (x0,y0), line to. + if (Math.abs(t01 - 1) > epsilon) { + this._append`L${x1 + t01 * x01},${y1 + t01 * y01}`; + } + + this._append`A${r},${r},0,0,${+(y01 * x20 > x01 * y20)},${this._x1 = x1 + t21 * x21},${this._y1 = y1 + t21 * y21}`; + } + } + arc(x, y, r, a0, a1, ccw) { + x = +x, y = +y, r = +r, ccw = !!ccw; + + // Is the radius negative? Error. + if (r < 0) throw new Error(`negative radius: ${r}`); + + let dx = r * Math.cos(a0), + dy = r * Math.sin(a0), + x0 = x + dx, + y0 = y + dy, + cw = 1 ^ ccw, + da = ccw ? a0 - a1 : a1 - a0; + + // Is this path empty? Move to (x0,y0). + if (this._x1 === null) { + this._append`M${x0},${y0}`; + } + + // Or, is (x0,y0) not coincident with the previous point? Line to (x0,y0). + else if (Math.abs(this._x1 - x0) > epsilon || Math.abs(this._y1 - y0) > epsilon) { + this._append`L${x0},${y0}`; + } + + // Is this arc empty? We’re done. + if (!r) return; + + // Does the angle go the wrong way? Flip the direction. + if (da < 0) da = da % tau + tau; + + // Is this a complete circle? Draw two arcs to complete the circle. + if (da > tauEpsilon) { + this._append`A${r},${r},0,1,${cw},${x - dx},${y - dy}A${r},${r},0,1,${cw},${this._x1 = x0},${this._y1 = y0}`; + } + + // Is this arc non-empty? Draw an arc! + else if (da > epsilon) { + this._append`A${r},${r},0,${+(da >= pi)},${cw},${this._x1 = x + r * Math.cos(a1)},${this._y1 = y + r * Math.sin(a1)}`; + } + } + rect(x, y, w, h) { + this._append`M${this._x0 = this._x1 = +x},${this._y0 = this._y1 = +y}h${w = +w}v${+h}h${-w}Z`; + } + toString() { + return this._; + } +} + +function path() { + return new Path; +} + +// Allow instanceof d3.path +path.prototype = Path.prototype; + +function pathRound(digits = 3) { + return new Path(+digits); +} + +exports.Path = Path; +exports.path = path; +exports.pathRound = pathRound; + +})); diff --git a/frontend/node_modules/d3-path/dist/d3-path.min.js b/frontend/node_modules/d3-path/dist/d3-path.min.js new file mode 100644 index 0000000..db2e96b --- /dev/null +++ b/frontend/node_modules/d3-path/dist/d3-path.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-path/ v3.1.0 Copyright 2015-2022 Mike Bostock +!function(t,i){"object"==typeof exports&&"undefined"!=typeof module?i(exports):"function"==typeof define&&define.amd?define(["exports"],i):i((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{})}(this,(function(t){"use strict";const i=Math.PI,s=2*i,h=1e-6,e=s-h;function n(t){this._+=t[0];for(let i=1,s=t.length;i=0))throw new Error(`invalid digits: ${t}`);if(i>15)return n;const s=10**i;return function(t){this._+=t[0];for(let i=1,h=t.length;ih)if(Math.abs(d*o-r*p)>h&&_){let u=e-a,f=n-$,x=o*o+r*r,y=u*u+f*f,c=Math.sqrt(x),M=Math.sqrt(l),b=_*Math.tan((i-Math.acos((x+l-y)/(2*c*M)))/2),g=b/M,w=b/c;Math.abs(g-1)>h&&this._append`L${t+g*p},${s+g*d}`,this._append`A${_},${_},0,0,${+(d*u>p*f)},${this._x1=t+w*o},${this._y1=s+w*r}`}else this._append`L${this._x1=t},${this._y1=s}`;else;}arc(t,n,_,a,$,o){if(t=+t,n=+n,o=!!o,(_=+_)<0)throw new Error(`negative radius: ${_}`);let r=_*Math.cos(a),p=_*Math.sin(a),d=t+r,l=n+p,u=1^o,f=o?a-$:$-a;null===this._x1?this._append`M${d},${l}`:(Math.abs(this._x1-d)>h||Math.abs(this._y1-l)>h)&&this._append`L${d},${l}`,_&&(f<0&&(f=f%s+s),f>e?this._append`A${_},${_},0,1,${u},${t-r},${n-p}A${_},${_},0,1,${u},${this._x1=d},${this._y1=l}`:f>h&&this._append`A${_},${_},0,${+(f>=i)},${u},${this._x1=t+_*Math.cos($)},${this._y1=n+_*Math.sin($)}`)}rect(t,i,s,h){this._append`M${this._x0=this._x1=+t},${this._y0=this._y1=+i}h${s=+s}v${+h}h${-s}Z`}toString(){return this._}}function a(){return new _}a.prototype=_.prototype,t.Path=_,t.path=a,t.pathRound=function(t=3){return new _(+t)}})); diff --git a/frontend/node_modules/d3-path/package.json b/frontend/node_modules/d3-path/package.json new file mode 100644 index 0000000..e254f9c --- /dev/null +++ b/frontend/node_modules/d3-path/package.json @@ -0,0 +1,54 @@ +{ + "name": "d3-path", + "version": "3.1.0", + "description": "Serialize Canvas path commands to SVG.", + "homepage": "https://d3js.org/d3-path/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-path.git" + }, + "keywords": [ + "d3", + "d3-module", + "canvas", + "path", + "svg", + "graphics", + "CanvasRenderingContext2D", + "CanvasPathMethods", + "Path2D" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "http://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-path.min.js", + "unpkg": "dist/d3-path.min.js", + "exports": { + "umd": "./dist/d3-path.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "devDependencies": { + "eslint": "8", + "mocha": "10", + "rollup": "3", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-path/src/index.js b/frontend/node_modules/d3-path/src/index.js new file mode 100644 index 0000000..389003f --- /dev/null +++ b/frontend/node_modules/d3-path/src/index.js @@ -0,0 +1 @@ +export {Path, path, pathRound} from "./path.js"; diff --git a/frontend/node_modules/d3-path/src/path.js b/frontend/node_modules/d3-path/src/path.js new file mode 100644 index 0000000..e0b35cb --- /dev/null +++ b/frontend/node_modules/d3-path/src/path.js @@ -0,0 +1,156 @@ +const pi = Math.PI, + tau = 2 * pi, + epsilon = 1e-6, + tauEpsilon = tau - epsilon; + +function append(strings) { + this._ += strings[0]; + for (let i = 1, n = strings.length; i < n; ++i) { + this._ += arguments[i] + strings[i]; + } +} + +function appendRound(digits) { + let d = Math.floor(digits); + if (!(d >= 0)) throw new Error(`invalid digits: ${digits}`); + if (d > 15) return append; + const k = 10 ** d; + return function(strings) { + this._ += strings[0]; + for (let i = 1, n = strings.length; i < n; ++i) { + this._ += Math.round(arguments[i] * k) / k + strings[i]; + } + }; +} + +export class Path { + constructor(digits) { + this._x0 = this._y0 = // start of current subpath + this._x1 = this._y1 = null; // end of current subpath + this._ = ""; + this._append = digits == null ? append : appendRound(digits); + } + moveTo(x, y) { + this._append`M${this._x0 = this._x1 = +x},${this._y0 = this._y1 = +y}`; + } + closePath() { + if (this._x1 !== null) { + this._x1 = this._x0, this._y1 = this._y0; + this._append`Z`; + } + } + lineTo(x, y) { + this._append`L${this._x1 = +x},${this._y1 = +y}`; + } + quadraticCurveTo(x1, y1, x, y) { + this._append`Q${+x1},${+y1},${this._x1 = +x},${this._y1 = +y}`; + } + bezierCurveTo(x1, y1, x2, y2, x, y) { + this._append`C${+x1},${+y1},${+x2},${+y2},${this._x1 = +x},${this._y1 = +y}`; + } + arcTo(x1, y1, x2, y2, r) { + x1 = +x1, y1 = +y1, x2 = +x2, y2 = +y2, r = +r; + + // Is the radius negative? Error. + if (r < 0) throw new Error(`negative radius: ${r}`); + + let x0 = this._x1, + y0 = this._y1, + x21 = x2 - x1, + y21 = y2 - y1, + x01 = x0 - x1, + y01 = y0 - y1, + l01_2 = x01 * x01 + y01 * y01; + + // Is this path empty? Move to (x1,y1). + if (this._x1 === null) { + this._append`M${this._x1 = x1},${this._y1 = y1}`; + } + + // Or, is (x1,y1) coincident with (x0,y0)? Do nothing. + else if (!(l01_2 > epsilon)); + + // Or, are (x0,y0), (x1,y1) and (x2,y2) collinear? + // Equivalently, is (x1,y1) coincident with (x2,y2)? + // Or, is the radius zero? Line to (x1,y1). + else if (!(Math.abs(y01 * x21 - y21 * x01) > epsilon) || !r) { + this._append`L${this._x1 = x1},${this._y1 = y1}`; + } + + // Otherwise, draw an arc! + else { + let x20 = x2 - x0, + y20 = y2 - y0, + l21_2 = x21 * x21 + y21 * y21, + l20_2 = x20 * x20 + y20 * y20, + l21 = Math.sqrt(l21_2), + l01 = Math.sqrt(l01_2), + l = r * Math.tan((pi - Math.acos((l21_2 + l01_2 - l20_2) / (2 * l21 * l01))) / 2), + t01 = l / l01, + t21 = l / l21; + + // If the start tangent is not coincident with (x0,y0), line to. + if (Math.abs(t01 - 1) > epsilon) { + this._append`L${x1 + t01 * x01},${y1 + t01 * y01}`; + } + + this._append`A${r},${r},0,0,${+(y01 * x20 > x01 * y20)},${this._x1 = x1 + t21 * x21},${this._y1 = y1 + t21 * y21}`; + } + } + arc(x, y, r, a0, a1, ccw) { + x = +x, y = +y, r = +r, ccw = !!ccw; + + // Is the radius negative? Error. + if (r < 0) throw new Error(`negative radius: ${r}`); + + let dx = r * Math.cos(a0), + dy = r * Math.sin(a0), + x0 = x + dx, + y0 = y + dy, + cw = 1 ^ ccw, + da = ccw ? a0 - a1 : a1 - a0; + + // Is this path empty? Move to (x0,y0). + if (this._x1 === null) { + this._append`M${x0},${y0}`; + } + + // Or, is (x0,y0) not coincident with the previous point? Line to (x0,y0). + else if (Math.abs(this._x1 - x0) > epsilon || Math.abs(this._y1 - y0) > epsilon) { + this._append`L${x0},${y0}`; + } + + // Is this arc empty? We’re done. + if (!r) return; + + // Does the angle go the wrong way? Flip the direction. + if (da < 0) da = da % tau + tau; + + // Is this a complete circle? Draw two arcs to complete the circle. + if (da > tauEpsilon) { + this._append`A${r},${r},0,1,${cw},${x - dx},${y - dy}A${r},${r},0,1,${cw},${this._x1 = x0},${this._y1 = y0}`; + } + + // Is this arc non-empty? Draw an arc! + else if (da > epsilon) { + this._append`A${r},${r},0,${+(da >= pi)},${cw},${this._x1 = x + r * Math.cos(a1)},${this._y1 = y + r * Math.sin(a1)}`; + } + } + rect(x, y, w, h) { + this._append`M${this._x0 = this._x1 = +x},${this._y0 = this._y1 = +y}h${w = +w}v${+h}h${-w}Z`; + } + toString() { + return this._; + } +} + +export function path() { + return new Path; +} + +// Allow instanceof d3.path +path.prototype = Path.prototype; + +export function pathRound(digits = 3) { + return new Path(+digits); +} diff --git a/frontend/node_modules/d3-polygon/LICENSE b/frontend/node_modules/d3-polygon/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-polygon/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-polygon/README.md b/frontend/node_modules/d3-polygon/README.md new file mode 100644 index 0000000..ecdc791 --- /dev/null +++ b/frontend/node_modules/d3-polygon/README.md @@ -0,0 +1,52 @@ +# d3-polygon + +This module provides a few basic geometric operations for two-dimensional polygons. Each polygon is represented as an array of two-element arrays [​[x1, y1], [x2, y2], …], and may either be closed (wherein the first and last point are the same) or open (wherein they are not). Typically polygons are in counterclockwise order, assuming a coordinate system where the origin ⟨0,0⟩ is in the top-left corner. + +## Installing + +If you use npm, `npm install d3-polygon`. You can also download the [latest release on GitHub](https://github.com/d3/d3-polygon/releases/latest). For vanilla HTML in modern browsers, import d3-polygon from Skypack: + +```html + +``` + +For legacy environments, you can load d3-polygon’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +## API Reference + +# d3.polygonArea(polygon) [<>](https://github.com/d3/d3-polygon/blob/master/src/area.js "Source Code") + +Returns the signed area of the specified *polygon*. If the vertices of the polygon are in counterclockwise order (assuming a coordinate system where the origin ⟨0,0⟩ is in the top-left corner), the returned area is positive; otherwise it is negative, or zero. + +# d3.polygonCentroid(polygon) [<>](https://github.com/d3/d3-polygon/blob/master/src/centroid.js "Source Code") + +Returns the [centroid](https://en.wikipedia.org/wiki/Centroid) of the specified *polygon*. + +# d3.polygonHull(points) [<>](https://github.com/d3/d3-polygon/blob/master/src/hull.js#L23 "Source Code") + + + +Returns the [convex hull](https://en.wikipedia.org/wiki/Convex_hull) of the specified *points* using [Andrew’s monotone chain algorithm](http://en.wikibooks.org/wiki/Algorithm_Implementation/Geometry/Convex_hull/Monotone_chain). The returned hull is represented as an array containing a subset of the input *points* arranged in counterclockwise order. Returns null if *points* has fewer than three elements. + +# d3.polygonContains(polygon, point) [<>](https://github.com/d3/d3-polygon/blob/master/src/contains.js "Source Code") + +Returns true if and only if the specified *point* is inside the specified *polygon*. + +# d3.polygonLength(polygon) [<>](https://github.com/d3/d3-polygon/blob/master/src/length.js "Source Code") + +Returns the length of the perimeter of the specified *polygon*. diff --git a/frontend/node_modules/d3-polygon/dist/d3-polygon.js b/frontend/node_modules/d3-polygon/dist/d3-polygon.js new file mode 100644 index 0000000..33ba08b --- /dev/null +++ b/frontend/node_modules/d3-polygon/dist/d3-polygon.js @@ -0,0 +1,150 @@ +// https://d3js.org/d3-polygon/ v3.0.1 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +}(this, (function (exports) { 'use strict'; + +function area(polygon) { + var i = -1, + n = polygon.length, + a, + b = polygon[n - 1], + area = 0; + + while (++i < n) { + a = b; + b = polygon[i]; + area += a[1] * b[0] - a[0] * b[1]; + } + + return area / 2; +} + +function centroid(polygon) { + var i = -1, + n = polygon.length, + x = 0, + y = 0, + a, + b = polygon[n - 1], + c, + k = 0; + + while (++i < n) { + a = b; + b = polygon[i]; + k += c = a[0] * b[1] - b[0] * a[1]; + x += (a[0] + b[0]) * c; + y += (a[1] + b[1]) * c; + } + + return k *= 3, [x / k, y / k]; +} + +// Returns the 2D cross product of AB and AC vectors, i.e., the z-component of +// the 3D cross product in a quadrant I Cartesian coordinate system (+x is +// right, +y is up). Returns a positive value if ABC is counter-clockwise, +// negative if clockwise, and zero if the points are collinear. +function cross(a, b, c) { + return (b[0] - a[0]) * (c[1] - a[1]) - (b[1] - a[1]) * (c[0] - a[0]); +} + +function lexicographicOrder(a, b) { + return a[0] - b[0] || a[1] - b[1]; +} + +// Computes the upper convex hull per the monotone chain algorithm. +// Assumes points.length >= 3, is sorted by x, unique in y. +// Returns an array of indices into points in left-to-right order. +function computeUpperHullIndexes(points) { + const n = points.length, + indexes = [0, 1]; + let size = 2, i; + + for (i = 2; i < n; ++i) { + while (size > 1 && cross(points[indexes[size - 2]], points[indexes[size - 1]], points[i]) <= 0) --size; + indexes[size++] = i; + } + + return indexes.slice(0, size); // remove popped points +} + +function hull(points) { + if ((n = points.length) < 3) return null; + + var i, + n, + sortedPoints = new Array(n), + flippedPoints = new Array(n); + + for (i = 0; i < n; ++i) sortedPoints[i] = [+points[i][0], +points[i][1], i]; + sortedPoints.sort(lexicographicOrder); + for (i = 0; i < n; ++i) flippedPoints[i] = [sortedPoints[i][0], -sortedPoints[i][1]]; + + var upperIndexes = computeUpperHullIndexes(sortedPoints), + lowerIndexes = computeUpperHullIndexes(flippedPoints); + + // Construct the hull polygon, removing possible duplicate endpoints. + var skipLeft = lowerIndexes[0] === upperIndexes[0], + skipRight = lowerIndexes[lowerIndexes.length - 1] === upperIndexes[upperIndexes.length - 1], + hull = []; + + // Add upper hull in right-to-l order. + // Then add lower hull in left-to-right order. + for (i = upperIndexes.length - 1; i >= 0; --i) hull.push(points[sortedPoints[upperIndexes[i]][2]]); + for (i = +skipLeft; i < lowerIndexes.length - skipRight; ++i) hull.push(points[sortedPoints[lowerIndexes[i]][2]]); + + return hull; +} + +function contains(polygon, point) { + var n = polygon.length, + p = polygon[n - 1], + x = point[0], y = point[1], + x0 = p[0], y0 = p[1], + x1, y1, + inside = false; + + for (var i = 0; i < n; ++i) { + p = polygon[i], x1 = p[0], y1 = p[1]; + if (((y1 > y) !== (y0 > y)) && (x < (x0 - x1) * (y - y1) / (y0 - y1) + x1)) inside = !inside; + x0 = x1, y0 = y1; + } + + return inside; +} + +function length(polygon) { + var i = -1, + n = polygon.length, + b = polygon[n - 1], + xa, + ya, + xb = b[0], + yb = b[1], + perimeter = 0; + + while (++i < n) { + xa = xb; + ya = yb; + b = polygon[i]; + xb = b[0]; + yb = b[1]; + xa -= xb; + ya -= yb; + perimeter += Math.hypot(xa, ya); + } + + return perimeter; +} + +exports.polygonArea = area; +exports.polygonCentroid = centroid; +exports.polygonContains = contains; +exports.polygonHull = hull; +exports.polygonLength = length; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-polygon/dist/d3-polygon.min.js b/frontend/node_modules/d3-polygon/dist/d3-polygon.min.js new file mode 100644 index 0000000..38fcfc3 --- /dev/null +++ b/frontend/node_modules/d3-polygon/dist/d3-polygon.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-polygon/ v3.0.1 Copyright 2010-2021 Mike Bostock +!function(n,e){"object"==typeof exports&&"undefined"!=typeof module?e(exports):"function"==typeof define&&define.amd?define(["exports"],e):e((n="undefined"!=typeof globalThis?globalThis:n||self).d3=n.d3||{})}(this,(function(n){"use strict";function e(n,e){return n[0]-e[0]||n[1]-e[1]}function t(n){const e=n.length,t=[0,1];let o,r=2;for(o=2;o1&&(f=n[t[r-2]],l=n[t[r-1]],u=n[o],(l[0]-f[0])*(u[1]-f[1])-(l[1]-f[1])*(u[0]-f[0])<=0);)--r;t[r++]=o}var f,l,u;return t.slice(0,r)}n.polygonArea=function(n){for(var e,t=-1,o=n.length,r=n[o-1],f=0;++tu!=g>u&&l<(i-t)*(u-o)/(g-o)+t&&(h=!h),i=t,g=o;return h},n.polygonHull=function(n){if((r=n.length)<3)return null;var o,r,f=new Array(r),l=new Array(r);for(o=0;o=0;--o)a.push(n[f[u[o]][2]]);for(o=+g;o=12" + } +} diff --git a/frontend/node_modules/d3-polygon/src/area.js b/frontend/node_modules/d3-polygon/src/area.js new file mode 100644 index 0000000..109efb4 --- /dev/null +++ b/frontend/node_modules/d3-polygon/src/area.js @@ -0,0 +1,15 @@ +export default function(polygon) { + var i = -1, + n = polygon.length, + a, + b = polygon[n - 1], + area = 0; + + while (++i < n) { + a = b; + b = polygon[i]; + area += a[1] * b[0] - a[0] * b[1]; + } + + return area / 2; +} diff --git a/frontend/node_modules/d3-polygon/src/centroid.js b/frontend/node_modules/d3-polygon/src/centroid.js new file mode 100644 index 0000000..6c8ece1 --- /dev/null +++ b/frontend/node_modules/d3-polygon/src/centroid.js @@ -0,0 +1,20 @@ +export default function(polygon) { + var i = -1, + n = polygon.length, + x = 0, + y = 0, + a, + b = polygon[n - 1], + c, + k = 0; + + while (++i < n) { + a = b; + b = polygon[i]; + k += c = a[0] * b[1] - b[0] * a[1]; + x += (a[0] + b[0]) * c; + y += (a[1] + b[1]) * c; + } + + return k *= 3, [x / k, y / k]; +} diff --git a/frontend/node_modules/d3-polygon/src/contains.js b/frontend/node_modules/d3-polygon/src/contains.js new file mode 100644 index 0000000..a0beabc --- /dev/null +++ b/frontend/node_modules/d3-polygon/src/contains.js @@ -0,0 +1,16 @@ +export default function(polygon, point) { + var n = polygon.length, + p = polygon[n - 1], + x = point[0], y = point[1], + x0 = p[0], y0 = p[1], + x1, y1, + inside = false; + + for (var i = 0; i < n; ++i) { + p = polygon[i], x1 = p[0], y1 = p[1]; + if (((y1 > y) !== (y0 > y)) && (x < (x0 - x1) * (y - y1) / (y0 - y1) + x1)) inside = !inside; + x0 = x1, y0 = y1; + } + + return inside; +} diff --git a/frontend/node_modules/d3-polygon/src/cross.js b/frontend/node_modules/d3-polygon/src/cross.js new file mode 100644 index 0000000..11a6df0 --- /dev/null +++ b/frontend/node_modules/d3-polygon/src/cross.js @@ -0,0 +1,7 @@ +// Returns the 2D cross product of AB and AC vectors, i.e., the z-component of +// the 3D cross product in a quadrant I Cartesian coordinate system (+x is +// right, +y is up). Returns a positive value if ABC is counter-clockwise, +// negative if clockwise, and zero if the points are collinear. +export default function(a, b, c) { + return (b[0] - a[0]) * (c[1] - a[1]) - (b[1] - a[1]) * (c[0] - a[0]); +} diff --git a/frontend/node_modules/d3-polygon/src/hull.js b/frontend/node_modules/d3-polygon/src/hull.js new file mode 100644 index 0000000..daaf9a5 --- /dev/null +++ b/frontend/node_modules/d3-polygon/src/hull.js @@ -0,0 +1,49 @@ +import cross from "./cross.js"; + +function lexicographicOrder(a, b) { + return a[0] - b[0] || a[1] - b[1]; +} + +// Computes the upper convex hull per the monotone chain algorithm. +// Assumes points.length >= 3, is sorted by x, unique in y. +// Returns an array of indices into points in left-to-right order. +function computeUpperHullIndexes(points) { + const n = points.length, + indexes = [0, 1]; + let size = 2, i; + + for (i = 2; i < n; ++i) { + while (size > 1 && cross(points[indexes[size - 2]], points[indexes[size - 1]], points[i]) <= 0) --size; + indexes[size++] = i; + } + + return indexes.slice(0, size); // remove popped points +} + +export default function(points) { + if ((n = points.length) < 3) return null; + + var i, + n, + sortedPoints = new Array(n), + flippedPoints = new Array(n); + + for (i = 0; i < n; ++i) sortedPoints[i] = [+points[i][0], +points[i][1], i]; + sortedPoints.sort(lexicographicOrder); + for (i = 0; i < n; ++i) flippedPoints[i] = [sortedPoints[i][0], -sortedPoints[i][1]]; + + var upperIndexes = computeUpperHullIndexes(sortedPoints), + lowerIndexes = computeUpperHullIndexes(flippedPoints); + + // Construct the hull polygon, removing possible duplicate endpoints. + var skipLeft = lowerIndexes[0] === upperIndexes[0], + skipRight = lowerIndexes[lowerIndexes.length - 1] === upperIndexes[upperIndexes.length - 1], + hull = []; + + // Add upper hull in right-to-l order. + // Then add lower hull in left-to-right order. + for (i = upperIndexes.length - 1; i >= 0; --i) hull.push(points[sortedPoints[upperIndexes[i]][2]]); + for (i = +skipLeft; i < lowerIndexes.length - skipRight; ++i) hull.push(points[sortedPoints[lowerIndexes[i]][2]]); + + return hull; +} diff --git a/frontend/node_modules/d3-polygon/src/index.js b/frontend/node_modules/d3-polygon/src/index.js new file mode 100644 index 0000000..e774be9 --- /dev/null +++ b/frontend/node_modules/d3-polygon/src/index.js @@ -0,0 +1,5 @@ +export {default as polygonArea} from "./area.js"; +export {default as polygonCentroid} from "./centroid.js"; +export {default as polygonHull} from "./hull.js"; +export {default as polygonContains} from "./contains.js"; +export {default as polygonLength} from "./length.js"; diff --git a/frontend/node_modules/d3-polygon/src/length.js b/frontend/node_modules/d3-polygon/src/length.js new file mode 100644 index 0000000..8e4da5e --- /dev/null +++ b/frontend/node_modules/d3-polygon/src/length.js @@ -0,0 +1,23 @@ +export default function(polygon) { + var i = -1, + n = polygon.length, + b = polygon[n - 1], + xa, + ya, + xb = b[0], + yb = b[1], + perimeter = 0; + + while (++i < n) { + xa = xb; + ya = yb; + b = polygon[i]; + xb = b[0]; + yb = b[1]; + xa -= xb; + ya -= yb; + perimeter += Math.hypot(xa, ya); + } + + return perimeter; +} diff --git a/frontend/node_modules/d3-quadtree/LICENSE b/frontend/node_modules/d3-quadtree/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-quadtree/README.md b/frontend/node_modules/d3-quadtree/README.md new file mode 100644 index 0000000..0a930a2 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/README.md @@ -0,0 +1,181 @@ +# d3-quadtree + +A [quadtree](https://en.wikipedia.org/wiki/Quadtree) recursively partitions two-dimensional space into squares, dividing each square into four equally-sized squares. Each distinct point exists in a unique leaf [node](#nodes); coincident points are represented by a linked list. Quadtrees can accelerate various spatial operations, such as the [Barnes–Hut approximation](https://en.wikipedia.org/wiki/Barnes–Hut_simulation) for computing many-body forces, collision detection, and searching for nearby points. + + + + +## Installing + +If you use npm, `npm install d3-quadtree`. You can also download the [latest release on GitHub](https://github.com/d3/d3-quadtree/releases/latest). For vanilla HTML in modern browsers, import d3-quadtree from Skypack: + +```html + +``` + +For legacy environments, you can load d3-quadtree’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +## API Reference + +# d3.quadtree([data[, x, y]]) [<>](https://github.com/d3/d3-quadtree/blob/master/src/quadtree.js "Source") + +Creates a new, empty quadtree with an empty [extent](#quadtree_extent) and the default [*x*-](#quadtree_x) and [*y*-](#quadtree_y)accessors. If *data* is specified, [adds](#quadtree_addAll) the specified array of data to the quadtree. This is equivalent to: + +```js +const tree = d3.quadtree() + .addAll(data); +``` + +If *x* and *y* are also specified, sets the [*x*-](#quadtree_x) and [*y*-](#quadtree_y) accessors to the specified functions before adding the specified array of data to the quadtree, equivalent to: + +```js +const tree = d3.quadtree() + .x(x) + .y(y) + .addAll(data); +``` + +# quadtree.x([x]) [<>](https://github.com/d3/d3-quadtree/blob/master/src/x.js "Source") + +If *x* is specified, sets the current *x*-coordinate accessor and returns the quadtree. If *x* is not specified, returns the current *x*-accessor, which defaults to: + +```js +function x(d) { + return d[0]; +} +``` + +The *x*-acccessor is used to derive the *x*-coordinate of data when [adding](#quadtree_add) to and [removing](#quadtree_remove) from the tree. It is also used when [finding](#quadtree_find) to re-access the coordinates of data previously added to the tree; therefore, the *x*- and *y*-accessors must be consistent, returning the same value given the same input. + +# quadtree.y([y]) [<>](https://github.com/d3/d3-quadtree/blob/master/src/y.js "Source") + +If *y* is specified, sets the current *y*-coordinate accessor and returns the quadtree. If *y* is not specified, returns the current *y*-accessor, which defaults to: + +```js +function y(d) { + return d[1]; +} +``` + +The *y*-acccessor is used to derive the *y*-coordinate of data when [adding](#quadtree_add) to and [removing](#quadtree_remove) from the tree. It is also used when [finding](#quadtree_find) to re-access the coordinates of data previously added to the tree; therefore, the *x*- and *y*-accessors must be consistent, returning the same value given the same input. + +# quadtree.extent([*extent*]) [<>](https://github.com/d3/d3-quadtree/blob/master/src/extent.js "Source") + +If *extent* is specified, expands the quadtree to [cover](#quadtree_cover) the specified points [[*x0*, *y0*], [*x1*, *y1*]] and returns the quadtree. If *extent* is not specified, returns the quadtree’s current extent [[*x0*, *y0*], [*x1*, *y1*]], where *x0* and *y0* are the inclusive lower bounds and *x1* and *y1* are the inclusive upper bounds, or undefined if the quadtree has no extent. The extent may also be expanded by calling [*quadtree*.cover](#quadtree_cover) or [*quadtree*.add](#quadtree_add). + +# quadtree.cover(x, y) [<>](https://github.com/d3/d3-quadtree/blob/master/src/cover.js "Source") + +Expands the quadtree to cover the specified point ⟨*x*,*y*⟩, and returns the quadtree. If the quadtree’s extent already covers the specified point, this method does nothing. If the quadtree has an extent, the extent is repeatedly doubled to cover the specified point, wrapping the [root](#quadtree_root) [node](#nodes) as necessary; if the quadtree is empty, the extent is initialized to the extent [[⌊*x*⌋, ⌊*y*⌋], [⌈*x*⌉, ⌈*y*⌉]]. (Rounding is necessary such that if the extent is later doubled, the boundaries of existing quadrants do not change due to floating point error.) + +# quadtree.add(datum) [<>](https://github.com/d3/d3-quadtree/blob/master/src/add.js "Source") + +Adds the specified *datum* to the quadtree, deriving its coordinates ⟨*x*,*y*⟩ using the current [*x*-](#quadtree_x) and [*y*-](#quadtree_y)accessors, and returns the quadtree. If the new point is outside the current [extent](#quadtree_extent) of the quadtree, the quadtree is automatically expanded to [cover](#quadtree_cover) the new point. + +# quadtree.addAll(data) [<>](https://github.com/d3/d3-quadtree/blob/master/src/add.js "Source") + +Adds the specified array of *data* to the quadtree, deriving each element’s coordinates ⟨*x*,*y*⟩ using the current [*x*-](#quadtree_x) and [*y*-](#quadtree_y)accessors, and return this quadtree. This is approximately equivalent to calling [*quadtree*.add](#quadtree_add) repeatedly: + +```js +for (let i = 0, n = data.length; i < n; ++i) { + quadtree.add(data[i]); +} +``` + +However, this method results in a more compact quadtree because the extent of the *data* is computed first before adding the data. + +# quadtree.remove(datum) [<>](https://github.com/d3/d3-quadtree/blob/master/src/remove.js "Source") + +Removes the specified *datum* from the quadtree, deriving its coordinates ⟨*x*,*y*⟩ using the current [*x*-](#quadtree_x) and [*y*-](#quadtree_y)accessors, and returns the quadtree. If the specified *datum* does not exist in this quadtree, this method does nothing. + +# quadtree.removeAll(data) [<>](https://github.com/d3/d3-quadtree/blob/master/src/remove.js "Source") + +Removes the specified *data* from the quadtree, deriving their coordinates ⟨*x*,*y*⟩ using the current [*x*-](#quadtree_x) and [*y*-](#quadtree_y)accessors, and returns the quadtree. If a specified datum does not exist in this quadtree, it is ignored. + +# quadtree.copy() + +Returns a copy of the quadtree. All [nodes](#nodes) in the returned quadtree are identical copies of the corresponding node in the quadtree; however, any data in the quadtree is shared by reference and not copied. + +# quadtree.root() [<>](https://github.com/d3/d3-quadtree/blob/master/src/root.js "Source") + +Returns the root [node](#nodes) of the quadtree. + +# quadtree.data() [<>](https://github.com/d3/d3-quadtree/blob/master/src/data.js "Source") + +Returns an array of all data in the quadtree. + +# quadtree.size() [<>](https://github.com/d3/d3-quadtree/blob/master/src/size.js "Source") + +Returns the total number of data in the quadtree. + +# quadtree.find(x, y[, radius]) [<>](https://github.com/d3/d3-quadtree/blob/master/src/find.js "Source") + +Returns the datum closest to the position ⟨*x*,*y*⟩ with the given search *radius*. If *radius* is not specified, it defaults to infinity. If there is no datum within the search area, returns undefined. + +# quadtree.visit(callback) [<>](https://github.com/d3/d3-quadtree/blob/master/src/visit.js "Source") + +Visits each [node](#nodes) in the quadtree in pre-order traversal, invoking the specified *callback* with arguments *node*, *x0*, *y0*, *x1*, *y1* for each node, where *node* is the node being visited, ⟨*x0*, *y0*⟩ are the lower bounds of the node, and ⟨*x1*, *y1*⟩ are the upper bounds, and returns the quadtree. (Assuming that positive *x* is right and positive *y* is down, as is typically the case in Canvas and SVG, ⟨*x0*, *y0*⟩ is the top-left corner and ⟨*x1*, *y1*⟩ is the lower-right corner; however, the coordinate system is arbitrary, so more formally *x0* <= *x1* and *y0* <= *y1*.) + +If the *callback* returns true for a given node, then the children of that node are not visited; otherwise, all child nodes are visited. This can be used to quickly visit only parts of the tree, for example when using the [Barnes–Hut approximation](https://en.wikipedia.org/wiki/Barnes–Hut_simulation). Note, however, that child quadrants are always visited in sibling order: top-left, top-right, bottom-left, bottom-right. In cases such as [search](#quadtree_find), visiting siblings in a specific order may be faster. + +As an example, the following visits the quadtree and returns all the nodes within a rectangular extent [xmin, ymin, xmax, ymax], ignoring quads that cannot possibly contain any such node: + +```js +function search(quadtree, xmin, ymin, xmax, ymax) { + const results = []; + quadtree.visit((node, x1, y1, x2, y2) => { + if (!node.length) { + do { + let d = node.data; + if (d[0] >= xmin && d[0] < xmax && d[1] >= ymin && d[1] < ymax) { + results.push(d); + } + } while (node = node.next); + } + return x1 >= xmax || y1 >= ymax || x2 < xmin || y2 < ymin; + }); + return results; +} +``` + +# quadtree.visitAfter(callback) [<>](https://github.com/d3/d3-quadtree/blob/master/src/visitAfter.js "Source") + +Visits each [node](#nodes) in the quadtree in post-order traversal, invoking the specified *callback* with arguments *node*, *x0*, *y0*, *x1*, *y1* for each node, where *node* is the node being visited, ⟨*x0*, *y0*⟩ are the lower bounds of the node, and ⟨*x1*, *y1*⟩ are the upper bounds, and returns the quadtree. (Assuming that positive *x* is right and positive *y* is down, as is typically the case in Canvas and SVG, ⟨*x0*, *y0*⟩ is the top-left corner and ⟨*x1*, *y1*⟩ is the lower-right corner; however, the coordinate system is arbitrary, so more formally *x0* <= *x1* and *y0* <= *y1*.) Returns *root*. + +### Nodes + +Internal nodes of the quadtree are represented as four-element arrays in left-to-right, top-to-bottom order: + +* `0` - the top-left quadrant, if any. +* `1` - the top-right quadrant, if any. +* `2` - the bottom-left quadrant, if any. +* `3` - the bottom-right quadrant, if any. + +A child quadrant may be undefined if it is empty. + +Leaf nodes are represented as objects with the following properties: + +* `data` - the data associated with this point, as passed to [*quadtree*.add](#quadtree_add). +* `next` - the next datum in this leaf, if any. + +The `length` property may be used to distinguish leaf nodes from internal nodes: it is undefined for leaf nodes, and 4 for internal nodes. For example, to iterate over all data in a leaf node: + +```js +if (!node.length) do console.log(node.data); while (node = node.next); +``` + +The point’s *x*- and *y*-coordinates **must not be modified** while the point is in the quadtree. To update a point’s position, [remove](#quadtree_remove) the point and then re-[add](#quadtree_add) it to the quadtree at the new position. Alternatively, you may discard the existing quadtree entirely and create a new one from scratch; this may be more efficient if many of the points have moved. diff --git a/frontend/node_modules/d3-quadtree/dist/d3-quadtree.js b/frontend/node_modules/d3-quadtree/dist/d3-quadtree.js new file mode 100644 index 0000000..e2afa70 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/dist/d3-quadtree.js @@ -0,0 +1,419 @@ +// https://d3js.org/d3-quadtree/ v3.0.1 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +}(this, (function (exports) { 'use strict'; + +function tree_add(d) { + const x = +this._x.call(null, d), + y = +this._y.call(null, d); + return add(this.cover(x, y), x, y, d); +} + +function add(tree, x, y, d) { + if (isNaN(x) || isNaN(y)) return tree; // ignore invalid points + + var parent, + node = tree._root, + leaf = {data: d}, + x0 = tree._x0, + y0 = tree._y0, + x1 = tree._x1, + y1 = tree._y1, + xm, + ym, + xp, + yp, + right, + bottom, + i, + j; + + // If the tree is empty, initialize the root as a leaf. + if (!node) return tree._root = leaf, tree; + + // Find the existing leaf for the new point, or add it. + while (node.length) { + if (right = x >= (xm = (x0 + x1) / 2)) x0 = xm; else x1 = xm; + if (bottom = y >= (ym = (y0 + y1) / 2)) y0 = ym; else y1 = ym; + if (parent = node, !(node = node[i = bottom << 1 | right])) return parent[i] = leaf, tree; + } + + // Is the new point is exactly coincident with the existing point? + xp = +tree._x.call(null, node.data); + yp = +tree._y.call(null, node.data); + if (x === xp && y === yp) return leaf.next = node, parent ? parent[i] = leaf : tree._root = leaf, tree; + + // Otherwise, split the leaf node until the old and new point are separated. + do { + parent = parent ? parent[i] = new Array(4) : tree._root = new Array(4); + if (right = x >= (xm = (x0 + x1) / 2)) x0 = xm; else x1 = xm; + if (bottom = y >= (ym = (y0 + y1) / 2)) y0 = ym; else y1 = ym; + } while ((i = bottom << 1 | right) === (j = (yp >= ym) << 1 | (xp >= xm))); + return parent[j] = node, parent[i] = leaf, tree; +} + +function addAll(data) { + var d, i, n = data.length, + x, + y, + xz = new Array(n), + yz = new Array(n), + x0 = Infinity, + y0 = Infinity, + x1 = -Infinity, + y1 = -Infinity; + + // Compute the points and their extent. + for (i = 0; i < n; ++i) { + if (isNaN(x = +this._x.call(null, d = data[i])) || isNaN(y = +this._y.call(null, d))) continue; + xz[i] = x; + yz[i] = y; + if (x < x0) x0 = x; + if (x > x1) x1 = x; + if (y < y0) y0 = y; + if (y > y1) y1 = y; + } + + // If there were no (valid) points, abort. + if (x0 > x1 || y0 > y1) return this; + + // Expand the tree to cover the new points. + this.cover(x0, y0).cover(x1, y1); + + // Add the new points. + for (i = 0; i < n; ++i) { + add(this, xz[i], yz[i], data[i]); + } + + return this; +} + +function tree_cover(x, y) { + if (isNaN(x = +x) || isNaN(y = +y)) return this; // ignore invalid points + + var x0 = this._x0, + y0 = this._y0, + x1 = this._x1, + y1 = this._y1; + + // If the quadtree has no extent, initialize them. + // Integer extent are necessary so that if we later double the extent, + // the existing quadrant boundaries don’t change due to floating point error! + if (isNaN(x0)) { + x1 = (x0 = Math.floor(x)) + 1; + y1 = (y0 = Math.floor(y)) + 1; + } + + // Otherwise, double repeatedly to cover. + else { + var z = x1 - x0 || 1, + node = this._root, + parent, + i; + + while (x0 > x || x >= x1 || y0 > y || y >= y1) { + i = (y < y0) << 1 | (x < x0); + parent = new Array(4), parent[i] = node, node = parent, z *= 2; + switch (i) { + case 0: x1 = x0 + z, y1 = y0 + z; break; + case 1: x0 = x1 - z, y1 = y0 + z; break; + case 2: x1 = x0 + z, y0 = y1 - z; break; + case 3: x0 = x1 - z, y0 = y1 - z; break; + } + } + + if (this._root && this._root.length) this._root = node; + } + + this._x0 = x0; + this._y0 = y0; + this._x1 = x1; + this._y1 = y1; + return this; +} + +function tree_data() { + var data = []; + this.visit(function(node) { + if (!node.length) do data.push(node.data); while (node = node.next) + }); + return data; +} + +function tree_extent(_) { + return arguments.length + ? this.cover(+_[0][0], +_[0][1]).cover(+_[1][0], +_[1][1]) + : isNaN(this._x0) ? undefined : [[this._x0, this._y0], [this._x1, this._y1]]; +} + +function Quad(node, x0, y0, x1, y1) { + this.node = node; + this.x0 = x0; + this.y0 = y0; + this.x1 = x1; + this.y1 = y1; +} + +function tree_find(x, y, radius) { + var data, + x0 = this._x0, + y0 = this._y0, + x1, + y1, + x2, + y2, + x3 = this._x1, + y3 = this._y1, + quads = [], + node = this._root, + q, + i; + + if (node) quads.push(new Quad(node, x0, y0, x3, y3)); + if (radius == null) radius = Infinity; + else { + x0 = x - radius, y0 = y - radius; + x3 = x + radius, y3 = y + radius; + radius *= radius; + } + + while (q = quads.pop()) { + + // Stop searching if this quadrant can’t contain a closer node. + if (!(node = q.node) + || (x1 = q.x0) > x3 + || (y1 = q.y0) > y3 + || (x2 = q.x1) < x0 + || (y2 = q.y1) < y0) continue; + + // Bisect the current quadrant. + if (node.length) { + var xm = (x1 + x2) / 2, + ym = (y1 + y2) / 2; + + quads.push( + new Quad(node[3], xm, ym, x2, y2), + new Quad(node[2], x1, ym, xm, y2), + new Quad(node[1], xm, y1, x2, ym), + new Quad(node[0], x1, y1, xm, ym) + ); + + // Visit the closest quadrant first. + if (i = (y >= ym) << 1 | (x >= xm)) { + q = quads[quads.length - 1]; + quads[quads.length - 1] = quads[quads.length - 1 - i]; + quads[quads.length - 1 - i] = q; + } + } + + // Visit this point. (Visiting coincident points isn’t necessary!) + else { + var dx = x - +this._x.call(null, node.data), + dy = y - +this._y.call(null, node.data), + d2 = dx * dx + dy * dy; + if (d2 < radius) { + var d = Math.sqrt(radius = d2); + x0 = x - d, y0 = y - d; + x3 = x + d, y3 = y + d; + data = node.data; + } + } + } + + return data; +} + +function tree_remove(d) { + if (isNaN(x = +this._x.call(null, d)) || isNaN(y = +this._y.call(null, d))) return this; // ignore invalid points + + var parent, + node = this._root, + retainer, + previous, + next, + x0 = this._x0, + y0 = this._y0, + x1 = this._x1, + y1 = this._y1, + x, + y, + xm, + ym, + right, + bottom, + i, + j; + + // If the tree is empty, initialize the root as a leaf. + if (!node) return this; + + // Find the leaf node for the point. + // While descending, also retain the deepest parent with a non-removed sibling. + if (node.length) while (true) { + if (right = x >= (xm = (x0 + x1) / 2)) x0 = xm; else x1 = xm; + if (bottom = y >= (ym = (y0 + y1) / 2)) y0 = ym; else y1 = ym; + if (!(parent = node, node = node[i = bottom << 1 | right])) return this; + if (!node.length) break; + if (parent[(i + 1) & 3] || parent[(i + 2) & 3] || parent[(i + 3) & 3]) retainer = parent, j = i; + } + + // Find the point to remove. + while (node.data !== d) if (!(previous = node, node = node.next)) return this; + if (next = node.next) delete node.next; + + // If there are multiple coincident points, remove just the point. + if (previous) return (next ? previous.next = next : delete previous.next), this; + + // If this is the root point, remove it. + if (!parent) return this._root = next, this; + + // Remove this leaf. + next ? parent[i] = next : delete parent[i]; + + // If the parent now contains exactly one leaf, collapse superfluous parents. + if ((node = parent[0] || parent[1] || parent[2] || parent[3]) + && node === (parent[3] || parent[2] || parent[1] || parent[0]) + && !node.length) { + if (retainer) retainer[j] = node; + else this._root = node; + } + + return this; +} + +function removeAll(data) { + for (var i = 0, n = data.length; i < n; ++i) this.remove(data[i]); + return this; +} + +function tree_root() { + return this._root; +} + +function tree_size() { + var size = 0; + this.visit(function(node) { + if (!node.length) do ++size; while (node = node.next) + }); + return size; +} + +function tree_visit(callback) { + var quads = [], q, node = this._root, child, x0, y0, x1, y1; + if (node) quads.push(new Quad(node, this._x0, this._y0, this._x1, this._y1)); + while (q = quads.pop()) { + if (!callback(node = q.node, x0 = q.x0, y0 = q.y0, x1 = q.x1, y1 = q.y1) && node.length) { + var xm = (x0 + x1) / 2, ym = (y0 + y1) / 2; + if (child = node[3]) quads.push(new Quad(child, xm, ym, x1, y1)); + if (child = node[2]) quads.push(new Quad(child, x0, ym, xm, y1)); + if (child = node[1]) quads.push(new Quad(child, xm, y0, x1, ym)); + if (child = node[0]) quads.push(new Quad(child, x0, y0, xm, ym)); + } + } + return this; +} + +function tree_visitAfter(callback) { + var quads = [], next = [], q; + if (this._root) quads.push(new Quad(this._root, this._x0, this._y0, this._x1, this._y1)); + while (q = quads.pop()) { + var node = q.node; + if (node.length) { + var child, x0 = q.x0, y0 = q.y0, x1 = q.x1, y1 = q.y1, xm = (x0 + x1) / 2, ym = (y0 + y1) / 2; + if (child = node[0]) quads.push(new Quad(child, x0, y0, xm, ym)); + if (child = node[1]) quads.push(new Quad(child, xm, y0, x1, ym)); + if (child = node[2]) quads.push(new Quad(child, x0, ym, xm, y1)); + if (child = node[3]) quads.push(new Quad(child, xm, ym, x1, y1)); + } + next.push(q); + } + while (q = next.pop()) { + callback(q.node, q.x0, q.y0, q.x1, q.y1); + } + return this; +} + +function defaultX(d) { + return d[0]; +} + +function tree_x(_) { + return arguments.length ? (this._x = _, this) : this._x; +} + +function defaultY(d) { + return d[1]; +} + +function tree_y(_) { + return arguments.length ? (this._y = _, this) : this._y; +} + +function quadtree(nodes, x, y) { + var tree = new Quadtree(x == null ? defaultX : x, y == null ? defaultY : y, NaN, NaN, NaN, NaN); + return nodes == null ? tree : tree.addAll(nodes); +} + +function Quadtree(x, y, x0, y0, x1, y1) { + this._x = x; + this._y = y; + this._x0 = x0; + this._y0 = y0; + this._x1 = x1; + this._y1 = y1; + this._root = undefined; +} + +function leaf_copy(leaf) { + var copy = {data: leaf.data}, next = copy; + while (leaf = leaf.next) next = next.next = {data: leaf.data}; + return copy; +} + +var treeProto = quadtree.prototype = Quadtree.prototype; + +treeProto.copy = function() { + var copy = new Quadtree(this._x, this._y, this._x0, this._y0, this._x1, this._y1), + node = this._root, + nodes, + child; + + if (!node) return copy; + + if (!node.length) return copy._root = leaf_copy(node), copy; + + nodes = [{source: node, target: copy._root = new Array(4)}]; + while (node = nodes.pop()) { + for (var i = 0; i < 4; ++i) { + if (child = node.source[i]) { + if (child.length) nodes.push({source: child, target: node.target[i] = new Array(4)}); + else node.target[i] = leaf_copy(child); + } + } + } + + return copy; +}; + +treeProto.add = tree_add; +treeProto.addAll = addAll; +treeProto.cover = tree_cover; +treeProto.data = tree_data; +treeProto.extent = tree_extent; +treeProto.find = tree_find; +treeProto.remove = tree_remove; +treeProto.removeAll = removeAll; +treeProto.root = tree_root; +treeProto.size = tree_size; +treeProto.visit = tree_visit; +treeProto.visitAfter = tree_visitAfter; +treeProto.x = tree_x; +treeProto.y = tree_y; + +exports.quadtree = quadtree; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-quadtree/dist/d3-quadtree.min.js b/frontend/node_modules/d3-quadtree/dist/d3-quadtree.min.js new file mode 100644 index 0000000..670fa61 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/dist/d3-quadtree.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-quadtree/ v3.0.1 Copyright 2010-2021 Mike Bostock +!function(t,i){"object"==typeof exports&&"undefined"!=typeof module?i(exports):"function"==typeof define&&define.amd?define(["exports"],i):i((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{})}(this,(function(t){"use strict";function i(t,i,e,n){if(isNaN(i)||isNaN(e))return t;var r,s,h,o,a,u,l,_,f,c=t._root,x={data:n},y=t._x0,d=t._y0,p=t._x1,v=t._y1;if(!c)return t._root=x,t;for(;c.length;)if((u=i>=(s=(y+p)/2))?y=s:p=s,(l=e>=(h=(d+v)/2))?d=h:v=h,r=c,!(c=c[_=l<<1|u]))return r[_]=x,t;if(o=+t._x.call(null,c.data),a=+t._y.call(null,c.data),i===o&&e===a)return x.next=c,r?r[_]=x:t._root=x,t;do{r=r?r[_]=new Array(4):t._root=new Array(4),(u=i>=(s=(y+p)/2))?y=s:p=s,(l=e>=(h=(d+v)/2))?d=h:v=h}while((_=l<<1|u)==(f=(a>=h)<<1|o>=s));return r[f]=c,r[_]=x,t}function e(t,i,e,n,r){this.node=t,this.x0=i,this.y0=e,this.x1=n,this.y1=r}function n(t){return t[0]}function r(t){return t[1]}function s(t,i,e){var s=new h(null==i?n:i,null==e?r:e,NaN,NaN,NaN,NaN);return null==t?s:s.addAll(t)}function h(t,i,e,n,r,s){this._x=t,this._y=i,this._x0=e,this._y0=n,this._x1=r,this._y1=s,this._root=void 0}function o(t){for(var i={data:t.data},e=i;t=t.next;)e=e.next={data:t.data};return i}var a=s.prototype=h.prototype;a.copy=function(){var t,i,e=new h(this._x,this._y,this._x0,this._y0,this._x1,this._y1),n=this._root;if(!n)return e;if(!n.length)return e._root=o(n),e;for(t=[{source:n,target:e._root=new Array(4)}];n=t.pop();)for(var r=0;r<4;++r)(i=n.source[r])&&(i.length?t.push({source:i,target:n.target[r]=new Array(4)}):n.target[r]=o(i));return e},a.add=function(t){const e=+this._x.call(null,t),n=+this._y.call(null,t);return i(this.cover(e,n),e,n,t)},a.addAll=function(t){var e,n,r,s,h=t.length,o=new Array(h),a=new Array(h),u=1/0,l=1/0,_=-1/0,f=-1/0;for(n=0;n_&&(_=r),sf&&(f=s));if(u>_||l>f)return this;for(this.cover(u,l).cover(_,f),n=0;nt||t>=r||n>i||i>=s;)switch(o=(ic||(h=u.y0)>x||(o=u.x1)<_||(a=u.y1)=v)<<1|t>=p)&&(u=y[y.length-1],y[y.length-1]=y[y.length-1-l],y[y.length-1-l]=u)}else{var w=t-+this._x.call(null,d.data),N=i-+this._y.call(null,d.data),g=w*w+N*N;if(g=(o=(x+d)/2))?x=o:d=o,(l=h>=(a=(y+p)/2))?y=a:p=a,i=c,!(c=c[_=l<<1|u]))return this;if(!c.length)break;(i[_+1&3]||i[_+2&3]||i[_+3&3])&&(e=i,f=_)}for(;c.data!==t;)if(n=c,!(c=c.next))return this;return(r=c.next)&&delete c.next,n?(r?n.next=r:delete n.next,this):i?(r?i[_]=r:delete i[_],(c=i[0]||i[1]||i[2]||i[3])&&c===(i[3]||i[2]||i[1]||i[0])&&!c.length&&(e?e[f]=c:this._root=c),this):(this._root=r,this)},a.removeAll=function(t){for(var i=0,e=t.length;i=12" + } +} diff --git a/frontend/node_modules/d3-quadtree/src/add.js b/frontend/node_modules/d3-quadtree/src/add.js new file mode 100644 index 0000000..985adfc --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/add.js @@ -0,0 +1,84 @@ +export default function(d) { + const x = +this._x.call(null, d), + y = +this._y.call(null, d); + return add(this.cover(x, y), x, y, d); +} + +function add(tree, x, y, d) { + if (isNaN(x) || isNaN(y)) return tree; // ignore invalid points + + var parent, + node = tree._root, + leaf = {data: d}, + x0 = tree._x0, + y0 = tree._y0, + x1 = tree._x1, + y1 = tree._y1, + xm, + ym, + xp, + yp, + right, + bottom, + i, + j; + + // If the tree is empty, initialize the root as a leaf. + if (!node) return tree._root = leaf, tree; + + // Find the existing leaf for the new point, or add it. + while (node.length) { + if (right = x >= (xm = (x0 + x1) / 2)) x0 = xm; else x1 = xm; + if (bottom = y >= (ym = (y0 + y1) / 2)) y0 = ym; else y1 = ym; + if (parent = node, !(node = node[i = bottom << 1 | right])) return parent[i] = leaf, tree; + } + + // Is the new point is exactly coincident with the existing point? + xp = +tree._x.call(null, node.data); + yp = +tree._y.call(null, node.data); + if (x === xp && y === yp) return leaf.next = node, parent ? parent[i] = leaf : tree._root = leaf, tree; + + // Otherwise, split the leaf node until the old and new point are separated. + do { + parent = parent ? parent[i] = new Array(4) : tree._root = new Array(4); + if (right = x >= (xm = (x0 + x1) / 2)) x0 = xm; else x1 = xm; + if (bottom = y >= (ym = (y0 + y1) / 2)) y0 = ym; else y1 = ym; + } while ((i = bottom << 1 | right) === (j = (yp >= ym) << 1 | (xp >= xm))); + return parent[j] = node, parent[i] = leaf, tree; +} + +export function addAll(data) { + var d, i, n = data.length, + x, + y, + xz = new Array(n), + yz = new Array(n), + x0 = Infinity, + y0 = Infinity, + x1 = -Infinity, + y1 = -Infinity; + + // Compute the points and their extent. + for (i = 0; i < n; ++i) { + if (isNaN(x = +this._x.call(null, d = data[i])) || isNaN(y = +this._y.call(null, d))) continue; + xz[i] = x; + yz[i] = y; + if (x < x0) x0 = x; + if (x > x1) x1 = x; + if (y < y0) y0 = y; + if (y > y1) y1 = y; + } + + // If there were no (valid) points, abort. + if (x0 > x1 || y0 > y1) return this; + + // Expand the tree to cover the new points. + this.cover(x0, y0).cover(x1, y1); + + // Add the new points. + for (i = 0; i < n; ++i) { + add(this, xz[i], yz[i], data[i]); + } + + return this; +} diff --git a/frontend/node_modules/d3-quadtree/src/cover.js b/frontend/node_modules/d3-quadtree/src/cover.js new file mode 100644 index 0000000..e1d47cd --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/cover.js @@ -0,0 +1,43 @@ +export default function(x, y) { + if (isNaN(x = +x) || isNaN(y = +y)) return this; // ignore invalid points + + var x0 = this._x0, + y0 = this._y0, + x1 = this._x1, + y1 = this._y1; + + // If the quadtree has no extent, initialize them. + // Integer extent are necessary so that if we later double the extent, + // the existing quadrant boundaries don’t change due to floating point error! + if (isNaN(x0)) { + x1 = (x0 = Math.floor(x)) + 1; + y1 = (y0 = Math.floor(y)) + 1; + } + + // Otherwise, double repeatedly to cover. + else { + var z = x1 - x0 || 1, + node = this._root, + parent, + i; + + while (x0 > x || x >= x1 || y0 > y || y >= y1) { + i = (y < y0) << 1 | (x < x0); + parent = new Array(4), parent[i] = node, node = parent, z *= 2; + switch (i) { + case 0: x1 = x0 + z, y1 = y0 + z; break; + case 1: x0 = x1 - z, y1 = y0 + z; break; + case 2: x1 = x0 + z, y0 = y1 - z; break; + case 3: x0 = x1 - z, y0 = y1 - z; break; + } + } + + if (this._root && this._root.length) this._root = node; + } + + this._x0 = x0; + this._y0 = y0; + this._x1 = x1; + this._y1 = y1; + return this; +} diff --git a/frontend/node_modules/d3-quadtree/src/data.js b/frontend/node_modules/d3-quadtree/src/data.js new file mode 100644 index 0000000..e934fa9 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/data.js @@ -0,0 +1,7 @@ +export default function() { + var data = []; + this.visit(function(node) { + if (!node.length) do data.push(node.data); while (node = node.next) + }); + return data; +} diff --git a/frontend/node_modules/d3-quadtree/src/extent.js b/frontend/node_modules/d3-quadtree/src/extent.js new file mode 100644 index 0000000..9e65a90 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/extent.js @@ -0,0 +1,5 @@ +export default function(_) { + return arguments.length + ? this.cover(+_[0][0], +_[0][1]).cover(+_[1][0], +_[1][1]) + : isNaN(this._x0) ? undefined : [[this._x0, this._y0], [this._x1, this._y1]]; +} diff --git a/frontend/node_modules/d3-quadtree/src/find.js b/frontend/node_modules/d3-quadtree/src/find.js new file mode 100644 index 0000000..e9db6c4 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/find.js @@ -0,0 +1,70 @@ +import Quad from "./quad.js"; + +export default function(x, y, radius) { + var data, + x0 = this._x0, + y0 = this._y0, + x1, + y1, + x2, + y2, + x3 = this._x1, + y3 = this._y1, + quads = [], + node = this._root, + q, + i; + + if (node) quads.push(new Quad(node, x0, y0, x3, y3)); + if (radius == null) radius = Infinity; + else { + x0 = x - radius, y0 = y - radius; + x3 = x + radius, y3 = y + radius; + radius *= radius; + } + + while (q = quads.pop()) { + + // Stop searching if this quadrant can’t contain a closer node. + if (!(node = q.node) + || (x1 = q.x0) > x3 + || (y1 = q.y0) > y3 + || (x2 = q.x1) < x0 + || (y2 = q.y1) < y0) continue; + + // Bisect the current quadrant. + if (node.length) { + var xm = (x1 + x2) / 2, + ym = (y1 + y2) / 2; + + quads.push( + new Quad(node[3], xm, ym, x2, y2), + new Quad(node[2], x1, ym, xm, y2), + new Quad(node[1], xm, y1, x2, ym), + new Quad(node[0], x1, y1, xm, ym) + ); + + // Visit the closest quadrant first. + if (i = (y >= ym) << 1 | (x >= xm)) { + q = quads[quads.length - 1]; + quads[quads.length - 1] = quads[quads.length - 1 - i]; + quads[quads.length - 1 - i] = q; + } + } + + // Visit this point. (Visiting coincident points isn’t necessary!) + else { + var dx = x - +this._x.call(null, node.data), + dy = y - +this._y.call(null, node.data), + d2 = dx * dx + dy * dy; + if (d2 < radius) { + var d = Math.sqrt(radius = d2); + x0 = x - d, y0 = y - d; + x3 = x + d, y3 = y + d; + data = node.data; + } + } + } + + return data; +} diff --git a/frontend/node_modules/d3-quadtree/src/index.js b/frontend/node_modules/d3-quadtree/src/index.js new file mode 100644 index 0000000..e2b2c31 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/index.js @@ -0,0 +1 @@ +export {default as quadtree} from "./quadtree.js"; diff --git a/frontend/node_modules/d3-quadtree/src/quad.js b/frontend/node_modules/d3-quadtree/src/quad.js new file mode 100644 index 0000000..6f714db --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/quad.js @@ -0,0 +1,7 @@ +export default function(node, x0, y0, x1, y1) { + this.node = node; + this.x0 = x0; + this.y0 = y0; + this.x1 = x1; + this.y1 = y1; +} diff --git a/frontend/node_modules/d3-quadtree/src/quadtree.js b/frontend/node_modules/d3-quadtree/src/quadtree.js new file mode 100644 index 0000000..5d58593 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/quadtree.js @@ -0,0 +1,73 @@ +import tree_add, {addAll as tree_addAll} from "./add.js"; +import tree_cover from "./cover.js"; +import tree_data from "./data.js"; +import tree_extent from "./extent.js"; +import tree_find from "./find.js"; +import tree_remove, {removeAll as tree_removeAll} from "./remove.js"; +import tree_root from "./root.js"; +import tree_size from "./size.js"; +import tree_visit from "./visit.js"; +import tree_visitAfter from "./visitAfter.js"; +import tree_x, {defaultX} from "./x.js"; +import tree_y, {defaultY} from "./y.js"; + +export default function quadtree(nodes, x, y) { + var tree = new Quadtree(x == null ? defaultX : x, y == null ? defaultY : y, NaN, NaN, NaN, NaN); + return nodes == null ? tree : tree.addAll(nodes); +} + +function Quadtree(x, y, x0, y0, x1, y1) { + this._x = x; + this._y = y; + this._x0 = x0; + this._y0 = y0; + this._x1 = x1; + this._y1 = y1; + this._root = undefined; +} + +function leaf_copy(leaf) { + var copy = {data: leaf.data}, next = copy; + while (leaf = leaf.next) next = next.next = {data: leaf.data}; + return copy; +} + +var treeProto = quadtree.prototype = Quadtree.prototype; + +treeProto.copy = function() { + var copy = new Quadtree(this._x, this._y, this._x0, this._y0, this._x1, this._y1), + node = this._root, + nodes, + child; + + if (!node) return copy; + + if (!node.length) return copy._root = leaf_copy(node), copy; + + nodes = [{source: node, target: copy._root = new Array(4)}]; + while (node = nodes.pop()) { + for (var i = 0; i < 4; ++i) { + if (child = node.source[i]) { + if (child.length) nodes.push({source: child, target: node.target[i] = new Array(4)}); + else node.target[i] = leaf_copy(child); + } + } + } + + return copy; +}; + +treeProto.add = tree_add; +treeProto.addAll = tree_addAll; +treeProto.cover = tree_cover; +treeProto.data = tree_data; +treeProto.extent = tree_extent; +treeProto.find = tree_find; +treeProto.remove = tree_remove; +treeProto.removeAll = tree_removeAll; +treeProto.root = tree_root; +treeProto.size = tree_size; +treeProto.visit = tree_visit; +treeProto.visitAfter = tree_visitAfter; +treeProto.x = tree_x; +treeProto.y = tree_y; diff --git a/frontend/node_modules/d3-quadtree/src/remove.js b/frontend/node_modules/d3-quadtree/src/remove.js new file mode 100644 index 0000000..0ba27ab --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/remove.js @@ -0,0 +1,62 @@ +export default function(d) { + if (isNaN(x = +this._x.call(null, d)) || isNaN(y = +this._y.call(null, d))) return this; // ignore invalid points + + var parent, + node = this._root, + retainer, + previous, + next, + x0 = this._x0, + y0 = this._y0, + x1 = this._x1, + y1 = this._y1, + x, + y, + xm, + ym, + right, + bottom, + i, + j; + + // If the tree is empty, initialize the root as a leaf. + if (!node) return this; + + // Find the leaf node for the point. + // While descending, also retain the deepest parent with a non-removed sibling. + if (node.length) while (true) { + if (right = x >= (xm = (x0 + x1) / 2)) x0 = xm; else x1 = xm; + if (bottom = y >= (ym = (y0 + y1) / 2)) y0 = ym; else y1 = ym; + if (!(parent = node, node = node[i = bottom << 1 | right])) return this; + if (!node.length) break; + if (parent[(i + 1) & 3] || parent[(i + 2) & 3] || parent[(i + 3) & 3]) retainer = parent, j = i; + } + + // Find the point to remove. + while (node.data !== d) if (!(previous = node, node = node.next)) return this; + if (next = node.next) delete node.next; + + // If there are multiple coincident points, remove just the point. + if (previous) return (next ? previous.next = next : delete previous.next), this; + + // If this is the root point, remove it. + if (!parent) return this._root = next, this; + + // Remove this leaf. + next ? parent[i] = next : delete parent[i]; + + // If the parent now contains exactly one leaf, collapse superfluous parents. + if ((node = parent[0] || parent[1] || parent[2] || parent[3]) + && node === (parent[3] || parent[2] || parent[1] || parent[0]) + && !node.length) { + if (retainer) retainer[j] = node; + else this._root = node; + } + + return this; +} + +export function removeAll(data) { + for (var i = 0, n = data.length; i < n; ++i) this.remove(data[i]); + return this; +} diff --git a/frontend/node_modules/d3-quadtree/src/root.js b/frontend/node_modules/d3-quadtree/src/root.js new file mode 100644 index 0000000..c32889f --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/root.js @@ -0,0 +1,3 @@ +export default function() { + return this._root; +} diff --git a/frontend/node_modules/d3-quadtree/src/size.js b/frontend/node_modules/d3-quadtree/src/size.js new file mode 100644 index 0000000..d2d5ab6 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/size.js @@ -0,0 +1,7 @@ +export default function() { + var size = 0; + this.visit(function(node) { + if (!node.length) do ++size; while (node = node.next) + }); + return size; +} diff --git a/frontend/node_modules/d3-quadtree/src/visit.js b/frontend/node_modules/d3-quadtree/src/visit.js new file mode 100644 index 0000000..941ab88 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/visit.js @@ -0,0 +1,16 @@ +import Quad from "./quad.js"; + +export default function(callback) { + var quads = [], q, node = this._root, child, x0, y0, x1, y1; + if (node) quads.push(new Quad(node, this._x0, this._y0, this._x1, this._y1)); + while (q = quads.pop()) { + if (!callback(node = q.node, x0 = q.x0, y0 = q.y0, x1 = q.x1, y1 = q.y1) && node.length) { + var xm = (x0 + x1) / 2, ym = (y0 + y1) / 2; + if (child = node[3]) quads.push(new Quad(child, xm, ym, x1, y1)); + if (child = node[2]) quads.push(new Quad(child, x0, ym, xm, y1)); + if (child = node[1]) quads.push(new Quad(child, xm, y0, x1, ym)); + if (child = node[0]) quads.push(new Quad(child, x0, y0, xm, ym)); + } + } + return this; +} diff --git a/frontend/node_modules/d3-quadtree/src/visitAfter.js b/frontend/node_modules/d3-quadtree/src/visitAfter.js new file mode 100644 index 0000000..2096655 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/visitAfter.js @@ -0,0 +1,21 @@ +import Quad from "./quad.js"; + +export default function(callback) { + var quads = [], next = [], q; + if (this._root) quads.push(new Quad(this._root, this._x0, this._y0, this._x1, this._y1)); + while (q = quads.pop()) { + var node = q.node; + if (node.length) { + var child, x0 = q.x0, y0 = q.y0, x1 = q.x1, y1 = q.y1, xm = (x0 + x1) / 2, ym = (y0 + y1) / 2; + if (child = node[0]) quads.push(new Quad(child, x0, y0, xm, ym)); + if (child = node[1]) quads.push(new Quad(child, xm, y0, x1, ym)); + if (child = node[2]) quads.push(new Quad(child, x0, ym, xm, y1)); + if (child = node[3]) quads.push(new Quad(child, xm, ym, x1, y1)); + } + next.push(q); + } + while (q = next.pop()) { + callback(q.node, q.x0, q.y0, q.x1, q.y1); + } + return this; +} diff --git a/frontend/node_modules/d3-quadtree/src/x.js b/frontend/node_modules/d3-quadtree/src/x.js new file mode 100644 index 0000000..ffea507 --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/x.js @@ -0,0 +1,7 @@ +export function defaultX(d) { + return d[0]; +} + +export default function(_) { + return arguments.length ? (this._x = _, this) : this._x; +} diff --git a/frontend/node_modules/d3-quadtree/src/y.js b/frontend/node_modules/d3-quadtree/src/y.js new file mode 100644 index 0000000..d2d29cb --- /dev/null +++ b/frontend/node_modules/d3-quadtree/src/y.js @@ -0,0 +1,7 @@ +export function defaultY(d) { + return d[1]; +} + +export default function(_) { + return arguments.length ? (this._y = _, this) : this._y; +} diff --git a/frontend/node_modules/d3-random/LICENSE b/frontend/node_modules/d3-random/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-random/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-random/README.md b/frontend/node_modules/d3-random/README.md new file mode 100644 index 0000000..1e67488 --- /dev/null +++ b/frontend/node_modules/d3-random/README.md @@ -0,0 +1,133 @@ +# d3-random + +Generate random numbers from various distributions. + +See the [d3-random collection on Observable](https://observablehq.com/collection/@d3/d3-random) for examples. + +## Installing + +If you use npm, `npm install d3-random`. You can also download the [latest release on GitHub](https://github.com/d3/d3-random/releases/latest). For vanilla HTML in modern browsers, import d3-random from Skypack: + +```html + +``` + +For legacy environments, you can load d3-random’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +## API Reference + +# d3.randomUniform([min, ][max]) · [Source](https://github.com/d3/d3-random/blob/master/src/uniform.js), [Examples](https://observablehq.com/@d3/d3-random#uniform) + +Returns a function for generating random numbers with a [uniform distribution](https://en.wikipedia.org/wiki/Uniform_distribution_\(continuous\)). The minimum allowed value of a returned number is *min* (inclusive), and the maximum is *max* (exclusive). If *min* is not specified, it defaults to 0; if *max* is not specified, it defaults to 1. For example: + +```js +d3.randomUniform(6)(); // Returns a number greater than or equal to 0 and less than 6. +d3.randomUniform(1, 5)(); // Returns a number greater than or equal to 1 and less than 5. +``` + +# d3.randomInt([min, ][max]) · [Source](https://github.com/d3/d3-random/blob/master/src/int.js), [Examples](https://observablehq.com/@d3/d3-random#int) + +Returns a function for generating random integers with a [uniform distribution](https://en.wikipedia.org/wiki/Uniform_distribution_\(continuous\)). The minimum allowed value of a returned number is ⌊*min*⌋ (inclusive), and the maximum is ⌊*max* - 1⌋ (inclusive). If *min* is not specified, it defaults to 0. For example: + +```js +d3.randomInt(6)(); // Returns an integer greater than or equal to 0 and less than 6. +d3.randomInt(1, 5)(); // Returns an integer greater than or equal to 1 and less than 5. +``` + +# d3.randomNormal([mu][, sigma]) · [Source](https://github.com/d3/d3-random/blob/master/src/normal.js), [Examples](https://observablehq.com/@d3/d3-random#normal) + +Returns a function for generating random numbers with a [normal (Gaussian) distribution](https://en.wikipedia.org/wiki/Normal_distribution). The expected value of the generated numbers is *mu*, with the given standard deviation *sigma*. If *mu* is not specified, it defaults to 0; if *sigma* is not specified, it defaults to 1. + +# d3.randomLogNormal([mu][, sigma]) · [Source](https://github.com/d3/d3-random/blob/master/src/logNormal.js), [Examples](https://observablehq.com/@d3/d3-random#logNormal) + +Returns a function for generating random numbers with a [log-normal distribution](https://en.wikipedia.org/wiki/Log-normal_distribution). The expected value of the random variable’s natural logarithm is *mu*, with the given standard deviation *sigma*. If *mu* is not specified, it defaults to 0; if *sigma* is not specified, it defaults to 1. + +# d3.randomBates(n) · [Source](https://github.com/d3/d3-random/blob/master/src/bates.js), [Examples](https://observablehq.com/@d3/d3-random#bates) + +Returns a function for generating random numbers with a [Bates distribution](https://en.wikipedia.org/wiki/Bates_distribution) with *n* independent variables. The case of fractional *n* is handled as with d3.randomIrwinHall, and d3.randomBates(0) is equivalent to d3.randomUniform(). + +# d3.randomIrwinHall(n) · [Source](https://github.com/d3/d3-random/blob/master/src/irwinHall.js), [Examples](https://observablehq.com/@d3/d3-random#irwinHall) + +Returns a function for generating random numbers with an [Irwin–Hall distribution](https://en.wikipedia.org/wiki/Irwin–Hall_distribution) with *n* independent variables. If the fractional part of *n* is non-zero, this is treated as adding d3.randomUniform() times that fractional part to the integral part. + +# d3.randomExponential(lambda) · [Source](https://github.com/d3/d3-random/blob/master/src/exponential.js), [Examples](https://observablehq.com/@d3/d3-random#exponential) + +Returns a function for generating random numbers with an [exponential distribution](https://en.wikipedia.org/wiki/Exponential_distribution) with the rate *lambda*; equivalent to time between events in a [Poisson process](https://en.wikipedia.org/wiki/Poisson_point_process) with a mean of 1 / *lambda*. For example, exponential(1/40) generates random times between events where, on average, one event occurs every 40 units of time. + +# d3.randomPareto(alpha) · [Source](https://github.com/d3/d3-random/blob/master/src/pareto.js), [Examples](https://observablehq.com/@d3/d3-random#pareto) + +Returns a function for generating random numbers with a [Pareto distribution](https://en.wikipedia.org/wiki/Pareto_distribution) with the shape *alpha*. The value *alpha* must be a positive value. + +# d3.randomBernoulli(p) · [Source](https://github.com/d3/d3-random/blob/master/src/bernoulli.js), [Examples](https://observablehq.com/@d3/d3-random#bernoulli) + +Returns a function for generating either 1 or 0 according to a [Bernoulli distribution](https://en.wikipedia.org/wiki/Binomial_distribution) with 1 being returned with success probability *p* and 0 with failure probability *q* = 1 - *p*. The value *p* is in the range [0, 1]. + +# d3.randomGeometric(p) · [Source](https://github.com/d3/d3-random/blob/master/src/geometric.js), [Examples](https://observablehq.com/@d3/d3-random#geometric) + +Returns a function for generating numbers with a [geometric distribution](https://en.wikipedia.org/wiki/Geometric_distribution) with success probability *p*. The value *p* is in the range [0, 1]. + +# d3.randomBinomial(n, p) · [Source](https://github.com/d3/d3-random/blob/master/src/binomial.js), [Examples](https://observablehq.com/@d3/d3-random#binomial) + +Returns a function for generating random numbers with a [binomial distribution](https://en.wikipedia.org/wiki/Binomial_distribution) with *n* the number of trials and *p* the probability of success in each trial. The value *n* is greater or equal to 0, and the value *p* is in the range [0, 1]. + +# d3.randomGamma(k, [theta]) · [Source](https://github.com/d3/d3-random/blob/master/src/gamma.js), [Examples](https://observablehq.com/@parcly-taxel/the-gamma-and-beta-distributions) + +Returns a function for generating random numbers with a [gamma distribution](https://en.wikipedia.org/wiki/Gamma_distribution) with *k* the shape parameter and *theta* the scale parameter. The value *k* must be a positive value; if *theta* is not specified, it defaults to 1. + +# d3.randomBeta(alpha, beta) · [Source](https://github.com/d3/d3-random/blob/master/src/beta.js), [Examples](https://observablehq.com/@parcly-taxel/the-gamma-and-beta-distributions) + +Returns a function for generating random numbers with a [beta distribution](https://en.wikipedia.org/wiki/Beta_distribution) with *alpha* and *beta* shape parameters, which must both be positive. + +# d3.randomWeibull(k, [a], [b]) · [Source](https://github.com/d3/d3-random/blob/master/src/weibull.js), [Examples](https://observablehq.com/@parcly-taxel/frechet-gumbel-weibull) + +Returns a function for generating random numbers with one of the [generalized extreme value distributions](https://en.wikipedia.org/wiki/Generalized_extreme_value_distribution), depending on *k*: + +* If *k* is positive, the [Weibull distribution](https://en.wikipedia.org/wiki/Weibull_distribution) with shape parameter *k* +* If *k* is zero, the [Gumbel distribution](https://en.wikipedia.org/wiki/Gumbel_distribution) +* If *k* is negative, the [Fréchet distribution](https://en.wikipedia.org/wiki/Fréchet_distribution) with shape parameter −*k* + +In all three cases, *a* is the location parameter and *b* is the scale parameter. If *a* is not specified, it defaults to 0; if *b* is not specified, it defaults to 1. + +# d3.randomCauchy([a], [b]) · [Source](https://github.com/d3/d3-random/blob/master/src/cauchy.js), [Examples](https://observablehq.com/@parcly-taxel/cauchy-and-logistic-distributions) + +Returns a function for generating random numbers with a [Cauchy distribution](https://en.wikipedia.org/wiki/Cauchy_distribution). *a* and *b* have the same meanings and default values as in d3.randomWeibull. + +# d3.randomLogistic([a], [b]) · [Source](https://github.com/d3/d3-random/blob/master/src/logistic.js), [Examples](https://observablehq.com/@parcly-taxel/cauchy-and-logistic-distributions) + +Returns a function for generating random numbers with a [logistic distribution](https://en.wikipedia.org/wiki/Logistic_distribution). *a* and *b* have the same meanings and default values as in d3.randomWeibull. + +# d3.randomPoisson(lambda) · [Source](https://github.com/d3/d3-random/blob/master/src/poisson.js), [Examples](https://observablehq.com/@parcly-taxel/the-poisson-distribution) + +Returns a function for generating random numbers with a [Poisson distribution](https://en.wikipedia.org/wiki/Poisson_distribution) with mean *lambda*. + +# random.source(source) · [Examples](https://observablehq.com/@d3/random-source) + +Returns the same type of function for generating random numbers but where the given random number generator *source* is used as the source of randomness instead of Math.random. The given random number generator must implement the same interface as Math.random and only return values in the range [0, 1). This is useful when a seeded random number generator is preferable to Math.random. For example: + +```js +import {randomLcg, randomNumber} from "d3-random"; + +const seed = 0.44871573888282423; // any number in [0, 1) +const random = randomNormal.source(randomLcg(seed))(0, 1); + +random(); // -0.6253955998897069 +``` + +# d3.randomLcg([seed]) · [Source](https://github.com/d3/d3-random/blob/master/src/lcg.js), [Examples](https://observablehq.com/@d3/d3-randomlcg) + +Returns a [linear congruential generator](https://en.wikipedia.org/wiki/Linear_congruential_generator); this function can be called repeatedly to obtain pseudorandom values well-distributed on the interval [0,1) and with a long period (up to 1 billion numbers), similar to Math.random. A *seed* can be specified as a real number in the interval [0,1) or as any integer. In the latter case, only the lower 32 bits are considered. Two generators instanced with the same seed generate the same sequence, allowing to create reproducible pseudo-random experiments. If the *seed* is not specified, one is chosen using Math.random. diff --git a/frontend/node_modules/d3-random/dist/d3-random.js b/frontend/node_modules/d3-random/dist/d3-random.js new file mode 100644 index 0000000..e4b6eaa --- /dev/null +++ b/frontend/node_modules/d3-random/dist/d3-random.js @@ -0,0 +1,358 @@ +// https://d3js.org/d3-random/ v3.0.1 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +}(this, (function (exports) { 'use strict'; + +var defaultSource = Math.random; + +var uniform = (function sourceRandomUniform(source) { + function randomUniform(min, max) { + min = min == null ? 0 : +min; + max = max == null ? 1 : +max; + if (arguments.length === 1) max = min, min = 0; + else max -= min; + return function() { + return source() * max + min; + }; + } + + randomUniform.source = sourceRandomUniform; + + return randomUniform; +})(defaultSource); + +var int = (function sourceRandomInt(source) { + function randomInt(min, max) { + if (arguments.length < 2) max = min, min = 0; + min = Math.floor(min); + max = Math.floor(max) - min; + return function() { + return Math.floor(source() * max + min); + }; + } + + randomInt.source = sourceRandomInt; + + return randomInt; +})(defaultSource); + +var normal = (function sourceRandomNormal(source) { + function randomNormal(mu, sigma) { + var x, r; + mu = mu == null ? 0 : +mu; + sigma = sigma == null ? 1 : +sigma; + return function() { + var y; + + // If available, use the second previously-generated uniform random. + if (x != null) y = x, x = null; + + // Otherwise, generate a new x and y. + else do { + x = source() * 2 - 1; + y = source() * 2 - 1; + r = x * x + y * y; + } while (!r || r > 1); + + return mu + sigma * y * Math.sqrt(-2 * Math.log(r) / r); + }; + } + + randomNormal.source = sourceRandomNormal; + + return randomNormal; +})(defaultSource); + +var logNormal = (function sourceRandomLogNormal(source) { + var N = normal.source(source); + + function randomLogNormal() { + var randomNormal = N.apply(this, arguments); + return function() { + return Math.exp(randomNormal()); + }; + } + + randomLogNormal.source = sourceRandomLogNormal; + + return randomLogNormal; +})(defaultSource); + +var irwinHall = (function sourceRandomIrwinHall(source) { + function randomIrwinHall(n) { + if ((n = +n) <= 0) return () => 0; + return function() { + for (var sum = 0, i = n; i > 1; --i) sum += source(); + return sum + i * source(); + }; + } + + randomIrwinHall.source = sourceRandomIrwinHall; + + return randomIrwinHall; +})(defaultSource); + +var bates = (function sourceRandomBates(source) { + var I = irwinHall.source(source); + + function randomBates(n) { + // use limiting distribution at n === 0 + if ((n = +n) === 0) return source; + var randomIrwinHall = I(n); + return function() { + return randomIrwinHall() / n; + }; + } + + randomBates.source = sourceRandomBates; + + return randomBates; +})(defaultSource); + +var exponential = (function sourceRandomExponential(source) { + function randomExponential(lambda) { + return function() { + return -Math.log1p(-source()) / lambda; + }; + } + + randomExponential.source = sourceRandomExponential; + + return randomExponential; +})(defaultSource); + +var pareto = (function sourceRandomPareto(source) { + function randomPareto(alpha) { + if ((alpha = +alpha) < 0) throw new RangeError("invalid alpha"); + alpha = 1 / -alpha; + return function() { + return Math.pow(1 - source(), alpha); + }; + } + + randomPareto.source = sourceRandomPareto; + + return randomPareto; +})(defaultSource); + +var bernoulli = (function sourceRandomBernoulli(source) { + function randomBernoulli(p) { + if ((p = +p) < 0 || p > 1) throw new RangeError("invalid p"); + return function() { + return Math.floor(source() + p); + }; + } + + randomBernoulli.source = sourceRandomBernoulli; + + return randomBernoulli; +})(defaultSource); + +var geometric = (function sourceRandomGeometric(source) { + function randomGeometric(p) { + if ((p = +p) < 0 || p > 1) throw new RangeError("invalid p"); + if (p === 0) return () => Infinity; + if (p === 1) return () => 1; + p = Math.log1p(-p); + return function() { + return 1 + Math.floor(Math.log1p(-source()) / p); + }; + } + + randomGeometric.source = sourceRandomGeometric; + + return randomGeometric; +})(defaultSource); + +var gamma = (function sourceRandomGamma(source) { + var randomNormal = normal.source(source)(); + + function randomGamma(k, theta) { + if ((k = +k) < 0) throw new RangeError("invalid k"); + // degenerate distribution if k === 0 + if (k === 0) return () => 0; + theta = theta == null ? 1 : +theta; + // exponential distribution if k === 1 + if (k === 1) return () => -Math.log1p(-source()) * theta; + + var d = (k < 1 ? k + 1 : k) - 1 / 3, + c = 1 / (3 * Math.sqrt(d)), + multiplier = k < 1 ? () => Math.pow(source(), 1 / k) : () => 1; + return function() { + do { + do { + var x = randomNormal(), + v = 1 + c * x; + } while (v <= 0); + v *= v * v; + var u = 1 - source(); + } while (u >= 1 - 0.0331 * x * x * x * x && Math.log(u) >= 0.5 * x * x + d * (1 - v + Math.log(v))); + return d * v * multiplier() * theta; + }; + } + + randomGamma.source = sourceRandomGamma; + + return randomGamma; +})(defaultSource); + +var beta = (function sourceRandomBeta(source) { + var G = gamma.source(source); + + function randomBeta(alpha, beta) { + var X = G(alpha), + Y = G(beta); + return function() { + var x = X(); + return x === 0 ? 0 : x / (x + Y()); + }; + } + + randomBeta.source = sourceRandomBeta; + + return randomBeta; +})(defaultSource); + +var binomial = (function sourceRandomBinomial(source) { + var G = geometric.source(source), + B = beta.source(source); + + function randomBinomial(n, p) { + n = +n; + if ((p = +p) >= 1) return () => n; + if (p <= 0) return () => 0; + return function() { + var acc = 0, nn = n, pp = p; + while (nn * pp > 16 && nn * (1 - pp) > 16) { + var i = Math.floor((nn + 1) * pp), + y = B(i, nn - i + 1)(); + if (y <= pp) { + acc += i; + nn -= i; + pp = (pp - y) / (1 - y); + } else { + nn = i - 1; + pp /= y; + } + } + var sign = pp < 0.5, + pFinal = sign ? pp : 1 - pp, + g = G(pFinal); + for (var s = g(), k = 0; s <= nn; ++k) s += g(); + return acc + (sign ? k : nn - k); + }; + } + + randomBinomial.source = sourceRandomBinomial; + + return randomBinomial; +})(defaultSource); + +var weibull = (function sourceRandomWeibull(source) { + function randomWeibull(k, a, b) { + var outerFunc; + if ((k = +k) === 0) { + outerFunc = x => -Math.log(x); + } else { + k = 1 / k; + outerFunc = x => Math.pow(x, k); + } + a = a == null ? 0 : +a; + b = b == null ? 1 : +b; + return function() { + return a + b * outerFunc(-Math.log1p(-source())); + }; + } + + randomWeibull.source = sourceRandomWeibull; + + return randomWeibull; +})(defaultSource); + +var cauchy = (function sourceRandomCauchy(source) { + function randomCauchy(a, b) { + a = a == null ? 0 : +a; + b = b == null ? 1 : +b; + return function() { + return a + b * Math.tan(Math.PI * source()); + }; + } + + randomCauchy.source = sourceRandomCauchy; + + return randomCauchy; +})(defaultSource); + +var logistic = (function sourceRandomLogistic(source) { + function randomLogistic(a, b) { + a = a == null ? 0 : +a; + b = b == null ? 1 : +b; + return function() { + var u = source(); + return a + b * Math.log(u / (1 - u)); + }; + } + + randomLogistic.source = sourceRandomLogistic; + + return randomLogistic; +})(defaultSource); + +var poisson = (function sourceRandomPoisson(source) { + var G = gamma.source(source), + B = binomial.source(source); + + function randomPoisson(lambda) { + return function() { + var acc = 0, l = lambda; + while (l > 16) { + var n = Math.floor(0.875 * l), + t = G(n)(); + if (t > l) return acc + B(n - 1, l / t)(); + acc += n; + l -= t; + } + for (var s = -Math.log1p(-source()), k = 0; s <= l; ++k) s -= Math.log1p(-source()); + return acc + k; + }; + } + + randomPoisson.source = sourceRandomPoisson; + + return randomPoisson; +})(defaultSource); + +// https://en.wikipedia.org/wiki/Linear_congruential_generator#Parameters_in_common_use +const mul = 0x19660D; +const inc = 0x3C6EF35F; +const eps = 1 / 0x100000000; + +function lcg(seed = Math.random()) { + let state = (0 <= seed && seed < 1 ? seed / eps : Math.abs(seed)) | 0; + return () => (state = mul * state + inc | 0, eps * (state >>> 0)); +} + +exports.randomBates = bates; +exports.randomBernoulli = bernoulli; +exports.randomBeta = beta; +exports.randomBinomial = binomial; +exports.randomCauchy = cauchy; +exports.randomExponential = exponential; +exports.randomGamma = gamma; +exports.randomGeometric = geometric; +exports.randomInt = int; +exports.randomIrwinHall = irwinHall; +exports.randomLcg = lcg; +exports.randomLogNormal = logNormal; +exports.randomLogistic = logistic; +exports.randomNormal = normal; +exports.randomPareto = pareto; +exports.randomPoisson = poisson; +exports.randomUniform = uniform; +exports.randomWeibull = weibull; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-random/dist/d3-random.min.js b/frontend/node_modules/d3-random/dist/d3-random.min.js new file mode 100644 index 0000000..d83f671 --- /dev/null +++ b/frontend/node_modules/d3-random/dist/d3-random.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-random/ v3.0.1 Copyright 2010-2021 Mike Bostock +!function(n,r){"object"==typeof exports&&"undefined"!=typeof module?r(exports):"function"==typeof define&&define.amd?define(["exports"],r):r((n="undefined"!=typeof globalThis?globalThis:n||self).d3=n.d3||{})}(this,(function(n){"use strict";var r=Math.random,t=function n(r){function t(n,t){return n=null==n?0:+n,t=null==t?1:+t,1===arguments.length?(t=n,n=0):t-=n,function(){return r()*t+n}}return t.source=n,t}(r),o=function n(r){function t(n,t){return arguments.length<2&&(t=n,n=0),n=Math.floor(n),t=Math.floor(t)-n,function(){return Math.floor(r()*t+n)}}return t.source=n,t}(r),u=function n(r){function t(n,t){var o,u;return n=null==n?0:+n,t=null==t?1:+t,function(){var e;if(null!=o)e=o,o=null;else do{o=2*r()-1,e=2*r()-1,u=o*o+e*e}while(!u||u>1);return n+t*e*Math.sqrt(-2*Math.log(u)/u)}}return t.source=n,t}(r),e=function n(r){var t=u.source(r);function o(){var n=t.apply(this,arguments);return function(){return Math.exp(n())}}return o.source=n,o}(r),a=function n(r){function t(n){return(n=+n)<=0?()=>0:function(){for(var t=0,o=n;o>1;--o)t+=r();return t+o*r()}}return t.source=n,t}(r),i=function n(r){var t=a.source(r);function o(n){if(0==(n=+n))return r;var o=t(n);return function(){return o()/n}}return o.source=n,o}(r),c=function n(r){function t(n){return function(){return-Math.log1p(-r())/n}}return t.source=n,t}(r),f=function n(r){function t(n){if((n=+n)<0)throw new RangeError("invalid alpha");return n=1/-n,function(){return Math.pow(1-r(),n)}}return t.source=n,t}(r),l=function n(r){function t(n){if((n=+n)<0||n>1)throw new RangeError("invalid p");return function(){return Math.floor(r()+n)}}return t.source=n,t}(r),h=function n(r){function t(n){if((n=+n)<0||n>1)throw new RangeError("invalid p");return 0===n?()=>1/0:1===n?()=>1:(n=Math.log1p(-n),function(){return 1+Math.floor(Math.log1p(-r())/n)})}return t.source=n,t}(r),s=function n(r){var t=u.source(r)();function o(n,o){if((n=+n)<0)throw new RangeError("invalid k");if(0===n)return()=>0;if(o=null==o?1:+o,1===n)return()=>-Math.log1p(-r())*o;var u=(n<1?n+1:n)-1/3,e=1/(3*Math.sqrt(u)),a=n<1?()=>Math.pow(r(),1/n):()=>1;return function(){do{do{var n=t(),i=1+e*n}while(i<=0);i*=i*i;var c=1-r()}while(c>=1-.0331*n*n*n*n&&Math.log(c)>=.5*n*n+u*(1-i+Math.log(i)));return u*i*a()*o}}return o.source=n,o}(r),d=function n(r){var t=s.source(r);function o(n,r){var o=t(n),u=t(r);return function(){var n=o();return 0===n?0:n/(n+u())}}return o.source=n,o}(r),M=function n(r){var t=h.source(r),o=d.source(r);function u(n,r){return n=+n,(r=+r)>=1?()=>n:r<=0?()=>0:function(){for(var u=0,e=n,a=r;e*a>16&&e*(1-a)>16;){var i=Math.floor((e+1)*a),c=o(i,e-i+1)();c<=a?(u+=i,e-=i,a=(a-c)/(1-c)):(e=i-1,a/=c)}for(var f=a<.5,l=t(f?a:1-a),h=l(),s=0;h<=e;++s)h+=l();return u+(f?s:e-s)}}return u.source=n,u}(r),v=function n(r){function t(n,t,o){var u;return 0==(n=+n)?u=n=>-Math.log(n):(n=1/n,u=r=>Math.pow(r,n)),t=null==t?0:+t,o=null==o?1:+o,function(){return t+o*u(-Math.log1p(-r()))}}return t.source=n,t}(r),m=function n(r){function t(n,t){return n=null==n?0:+n,t=null==t?1:+t,function(){return n+t*Math.tan(Math.PI*r())}}return t.source=n,t}(r),p=function n(r){function t(n,t){return n=null==n?0:+n,t=null==t?1:+t,function(){var o=r();return n+t*Math.log(o/(1-o))}}return t.source=n,t}(r),g=function n(r){var t=s.source(r),o=M.source(r);function u(n){return function(){for(var u=0,e=n;e>16;){var a=Math.floor(.875*e),i=t(a)();if(i>e)return u+o(a-1,e/i)();u+=a,e-=i}for(var c=-Math.log1p(-r()),f=0;c<=e;++f)c-=Math.log1p(-r());return u+f}}return u.source=n,u}(r);const w=1/4294967296;n.randomBates=i,n.randomBernoulli=l,n.randomBeta=d,n.randomBinomial=M,n.randomCauchy=m,n.randomExponential=c,n.randomGamma=s,n.randomGeometric=h,n.randomInt=o,n.randomIrwinHall=a,n.randomLcg=function(n=Math.random()){let r=0|(0<=n&&n<1?n/w:Math.abs(n));return()=>(r=1664525*r+1013904223|0,w*(r>>>0))},n.randomLogNormal=e,n.randomLogistic=p,n.randomNormal=u,n.randomPareto=f,n.randomPoisson=g,n.randomUniform=t,n.randomWeibull=v,Object.defineProperty(n,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-random/package.json b/frontend/node_modules/d3-random/package.json new file mode 100644 index 0000000..1644fc6 --- /dev/null +++ b/frontend/node_modules/d3-random/package.json @@ -0,0 +1,51 @@ +{ + "name": "d3-random", + "version": "3.0.1", + "description": "Generate random numbers from various distributions.", + "homepage": "https://d3js.org/d3-random/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-random.git" + }, + "keywords": [ + "d3", + "d3-module", + "random", + "rng" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "http://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-random.min.js", + "unpkg": "dist/d3-random.min.js", + "exports": { + "umd": "./dist/d3-random.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "devDependencies": { + "d3-array": "1 - 2", + "eslint": "7", + "jsdom": "16", + "mocha": "8", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-random/src/bates.js b/frontend/node_modules/d3-random/src/bates.js new file mode 100644 index 0000000..6bafddd --- /dev/null +++ b/frontend/node_modules/d3-random/src/bates.js @@ -0,0 +1,19 @@ +import defaultSource from "./defaultSource.js"; +import irwinHall from "./irwinHall.js"; + +export default (function sourceRandomBates(source) { + var I = irwinHall.source(source); + + function randomBates(n) { + // use limiting distribution at n === 0 + if ((n = +n) === 0) return source; + var randomIrwinHall = I(n); + return function() { + return randomIrwinHall() / n; + }; + } + + randomBates.source = sourceRandomBates; + + return randomBates; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/bernoulli.js b/frontend/node_modules/d3-random/src/bernoulli.js new file mode 100644 index 0000000..8751b43 --- /dev/null +++ b/frontend/node_modules/d3-random/src/bernoulli.js @@ -0,0 +1,14 @@ +import defaultSource from "./defaultSource.js"; + +export default (function sourceRandomBernoulli(source) { + function randomBernoulli(p) { + if ((p = +p) < 0 || p > 1) throw new RangeError("invalid p"); + return function() { + return Math.floor(source() + p); + }; + } + + randomBernoulli.source = sourceRandomBernoulli; + + return randomBernoulli; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/beta.js b/frontend/node_modules/d3-random/src/beta.js new file mode 100644 index 0000000..15bb2b3 --- /dev/null +++ b/frontend/node_modules/d3-random/src/beta.js @@ -0,0 +1,19 @@ +import defaultSource from "./defaultSource.js"; +import gamma from "./gamma.js"; + +export default (function sourceRandomBeta(source) { + var G = gamma.source(source); + + function randomBeta(alpha, beta) { + var X = G(alpha), + Y = G(beta); + return function() { + var x = X(); + return x === 0 ? 0 : x / (x + Y()); + }; + } + + randomBeta.source = sourceRandomBeta; + + return randomBeta; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/binomial.js b/frontend/node_modules/d3-random/src/binomial.js new file mode 100644 index 0000000..3213b4a --- /dev/null +++ b/frontend/node_modules/d3-random/src/binomial.js @@ -0,0 +1,38 @@ +import defaultSource from "./defaultSource.js"; +import beta from "./beta.js"; +import geometric from "./geometric.js"; + +export default (function sourceRandomBinomial(source) { + var G = geometric.source(source), + B = beta.source(source); + + function randomBinomial(n, p) { + n = +n; + if ((p = +p) >= 1) return () => n; + if (p <= 0) return () => 0; + return function() { + var acc = 0, nn = n, pp = p; + while (nn * pp > 16 && nn * (1 - pp) > 16) { + var i = Math.floor((nn + 1) * pp), + y = B(i, nn - i + 1)(); + if (y <= pp) { + acc += i; + nn -= i; + pp = (pp - y) / (1 - y); + } else { + nn = i - 1; + pp /= y; + } + } + var sign = pp < 0.5, + pFinal = sign ? pp : 1 - pp, + g = G(pFinal); + for (var s = g(), k = 0; s <= nn; ++k) s += g(); + return acc + (sign ? k : nn - k); + }; + } + + randomBinomial.source = sourceRandomBinomial; + + return randomBinomial; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/cauchy.js b/frontend/node_modules/d3-random/src/cauchy.js new file mode 100644 index 0000000..95c15ca --- /dev/null +++ b/frontend/node_modules/d3-random/src/cauchy.js @@ -0,0 +1,15 @@ +import defaultSource from "./defaultSource.js"; + +export default (function sourceRandomCauchy(source) { + function randomCauchy(a, b) { + a = a == null ? 0 : +a; + b = b == null ? 1 : +b; + return function() { + return a + b * Math.tan(Math.PI * source()); + }; + } + + randomCauchy.source = sourceRandomCauchy; + + return randomCauchy; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/defaultSource.js b/frontend/node_modules/d3-random/src/defaultSource.js new file mode 100644 index 0000000..ef54f3d --- /dev/null +++ b/frontend/node_modules/d3-random/src/defaultSource.js @@ -0,0 +1 @@ +export default Math.random; diff --git a/frontend/node_modules/d3-random/src/exponential.js b/frontend/node_modules/d3-random/src/exponential.js new file mode 100644 index 0000000..0d4304c --- /dev/null +++ b/frontend/node_modules/d3-random/src/exponential.js @@ -0,0 +1,13 @@ +import defaultSource from "./defaultSource.js"; + +export default (function sourceRandomExponential(source) { + function randomExponential(lambda) { + return function() { + return -Math.log1p(-source()) / lambda; + }; + } + + randomExponential.source = sourceRandomExponential; + + return randomExponential; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/gamma.js b/frontend/node_modules/d3-random/src/gamma.js new file mode 100644 index 0000000..48bf706 --- /dev/null +++ b/frontend/node_modules/d3-random/src/gamma.js @@ -0,0 +1,34 @@ +import defaultSource from "./defaultSource.js"; +import normal from "./normal.js"; + +export default (function sourceRandomGamma(source) { + var randomNormal = normal.source(source)(); + + function randomGamma(k, theta) { + if ((k = +k) < 0) throw new RangeError("invalid k"); + // degenerate distribution if k === 0 + if (k === 0) return () => 0; + theta = theta == null ? 1 : +theta; + // exponential distribution if k === 1 + if (k === 1) return () => -Math.log1p(-source()) * theta; + + var d = (k < 1 ? k + 1 : k) - 1 / 3, + c = 1 / (3 * Math.sqrt(d)), + multiplier = k < 1 ? () => Math.pow(source(), 1 / k) : () => 1; + return function() { + do { + do { + var x = randomNormal(), + v = 1 + c * x; + } while (v <= 0); + v *= v * v; + var u = 1 - source(); + } while (u >= 1 - 0.0331 * x * x * x * x && Math.log(u) >= 0.5 * x * x + d * (1 - v + Math.log(v))); + return d * v * multiplier() * theta; + }; + } + + randomGamma.source = sourceRandomGamma; + + return randomGamma; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/geometric.js b/frontend/node_modules/d3-random/src/geometric.js new file mode 100644 index 0000000..2cae2cc --- /dev/null +++ b/frontend/node_modules/d3-random/src/geometric.js @@ -0,0 +1,17 @@ +import defaultSource from "./defaultSource.js"; + +export default (function sourceRandomGeometric(source) { + function randomGeometric(p) { + if ((p = +p) < 0 || p > 1) throw new RangeError("invalid p"); + if (p === 0) return () => Infinity; + if (p === 1) return () => 1; + p = Math.log1p(-p); + return function() { + return 1 + Math.floor(Math.log1p(-source()) / p); + }; + } + + randomGeometric.source = sourceRandomGeometric; + + return randomGeometric; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/index.js b/frontend/node_modules/d3-random/src/index.js new file mode 100644 index 0000000..033891e --- /dev/null +++ b/frontend/node_modules/d3-random/src/index.js @@ -0,0 +1,18 @@ +export {default as randomUniform} from "./uniform.js"; +export {default as randomInt} from "./int.js"; +export {default as randomNormal} from "./normal.js"; +export {default as randomLogNormal} from "./logNormal.js"; +export {default as randomBates} from "./bates.js"; +export {default as randomIrwinHall} from "./irwinHall.js"; +export {default as randomExponential} from "./exponential.js"; +export {default as randomPareto} from "./pareto.js"; +export {default as randomBernoulli} from "./bernoulli.js"; +export {default as randomGeometric} from "./geometric.js"; +export {default as randomBinomial} from "./binomial.js"; +export {default as randomGamma} from "./gamma.js"; +export {default as randomBeta} from "./beta.js"; +export {default as randomWeibull} from "./weibull.js"; +export {default as randomCauchy} from "./cauchy.js"; +export {default as randomLogistic} from "./logistic.js"; +export {default as randomPoisson} from "./poisson.js"; +export {default as randomLcg} from "./lcg.js"; diff --git a/frontend/node_modules/d3-random/src/int.js b/frontend/node_modules/d3-random/src/int.js new file mode 100644 index 0000000..a47249b --- /dev/null +++ b/frontend/node_modules/d3-random/src/int.js @@ -0,0 +1,16 @@ +import defaultSource from "./defaultSource.js"; + +export default (function sourceRandomInt(source) { + function randomInt(min, max) { + if (arguments.length < 2) max = min, min = 0; + min = Math.floor(min); + max = Math.floor(max) - min; + return function() { + return Math.floor(source() * max + min); + }; + } + + randomInt.source = sourceRandomInt; + + return randomInt; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/irwinHall.js b/frontend/node_modules/d3-random/src/irwinHall.js new file mode 100644 index 0000000..4db5dcc --- /dev/null +++ b/frontend/node_modules/d3-random/src/irwinHall.js @@ -0,0 +1,15 @@ +import defaultSource from "./defaultSource.js"; + +export default (function sourceRandomIrwinHall(source) { + function randomIrwinHall(n) { + if ((n = +n) <= 0) return () => 0; + return function() { + for (var sum = 0, i = n; i > 1; --i) sum += source(); + return sum + i * source(); + }; + } + + randomIrwinHall.source = sourceRandomIrwinHall; + + return randomIrwinHall; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/lcg.js b/frontend/node_modules/d3-random/src/lcg.js new file mode 100644 index 0000000..fb05878 --- /dev/null +++ b/frontend/node_modules/d3-random/src/lcg.js @@ -0,0 +1,9 @@ +// https://en.wikipedia.org/wiki/Linear_congruential_generator#Parameters_in_common_use +const mul = 0x19660D; +const inc = 0x3C6EF35F; +const eps = 1 / 0x100000000; + +export default function lcg(seed = Math.random()) { + let state = (0 <= seed && seed < 1 ? seed / eps : Math.abs(seed)) | 0; + return () => (state = mul * state + inc | 0, eps * (state >>> 0)); +} diff --git a/frontend/node_modules/d3-random/src/logNormal.js b/frontend/node_modules/d3-random/src/logNormal.js new file mode 100644 index 0000000..3465fba --- /dev/null +++ b/frontend/node_modules/d3-random/src/logNormal.js @@ -0,0 +1,17 @@ +import defaultSource from "./defaultSource.js"; +import normal from "./normal.js"; + +export default (function sourceRandomLogNormal(source) { + var N = normal.source(source); + + function randomLogNormal() { + var randomNormal = N.apply(this, arguments); + return function() { + return Math.exp(randomNormal()); + }; + } + + randomLogNormal.source = sourceRandomLogNormal; + + return randomLogNormal; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/logistic.js b/frontend/node_modules/d3-random/src/logistic.js new file mode 100644 index 0000000..b2cda2a --- /dev/null +++ b/frontend/node_modules/d3-random/src/logistic.js @@ -0,0 +1,16 @@ +import defaultSource from "./defaultSource.js"; + +export default (function sourceRandomLogistic(source) { + function randomLogistic(a, b) { + a = a == null ? 0 : +a; + b = b == null ? 1 : +b; + return function() { + var u = source(); + return a + b * Math.log(u / (1 - u)); + }; + } + + randomLogistic.source = sourceRandomLogistic; + + return randomLogistic; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/normal.js b/frontend/node_modules/d3-random/src/normal.js new file mode 100644 index 0000000..b6838d6 --- /dev/null +++ b/frontend/node_modules/d3-random/src/normal.js @@ -0,0 +1,28 @@ +import defaultSource from "./defaultSource.js"; + +export default (function sourceRandomNormal(source) { + function randomNormal(mu, sigma) { + var x, r; + mu = mu == null ? 0 : +mu; + sigma = sigma == null ? 1 : +sigma; + return function() { + var y; + + // If available, use the second previously-generated uniform random. + if (x != null) y = x, x = null; + + // Otherwise, generate a new x and y. + else do { + x = source() * 2 - 1; + y = source() * 2 - 1; + r = x * x + y * y; + } while (!r || r > 1); + + return mu + sigma * y * Math.sqrt(-2 * Math.log(r) / r); + }; + } + + randomNormal.source = sourceRandomNormal; + + return randomNormal; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/pareto.js b/frontend/node_modules/d3-random/src/pareto.js new file mode 100644 index 0000000..e5496f0 --- /dev/null +++ b/frontend/node_modules/d3-random/src/pareto.js @@ -0,0 +1,15 @@ +import defaultSource from "./defaultSource.js"; + +export default (function sourceRandomPareto(source) { + function randomPareto(alpha) { + if ((alpha = +alpha) < 0) throw new RangeError("invalid alpha"); + alpha = 1 / -alpha; + return function() { + return Math.pow(1 - source(), alpha); + }; + } + + randomPareto.source = sourceRandomPareto; + + return randomPareto; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/poisson.js b/frontend/node_modules/d3-random/src/poisson.js new file mode 100644 index 0000000..da93995 --- /dev/null +++ b/frontend/node_modules/d3-random/src/poisson.js @@ -0,0 +1,27 @@ +import defaultSource from "./defaultSource.js"; +import binomial from "./binomial.js"; +import gamma from "./gamma.js"; + +export default (function sourceRandomPoisson(source) { + var G = gamma.source(source), + B = binomial.source(source); + + function randomPoisson(lambda) { + return function() { + var acc = 0, l = lambda; + while (l > 16) { + var n = Math.floor(0.875 * l), + t = G(n)(); + if (t > l) return acc + B(n - 1, l / t)(); + acc += n; + l -= t; + } + for (var s = -Math.log1p(-source()), k = 0; s <= l; ++k) s -= Math.log1p(-source()); + return acc + k; + }; + } + + randomPoisson.source = sourceRandomPoisson; + + return randomPoisson; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/uniform.js b/frontend/node_modules/d3-random/src/uniform.js new file mode 100644 index 0000000..a2bc468 --- /dev/null +++ b/frontend/node_modules/d3-random/src/uniform.js @@ -0,0 +1,17 @@ +import defaultSource from "./defaultSource.js"; + +export default (function sourceRandomUniform(source) { + function randomUniform(min, max) { + min = min == null ? 0 : +min; + max = max == null ? 1 : +max; + if (arguments.length === 1) max = min, min = 0; + else max -= min; + return function() { + return source() * max + min; + }; + } + + randomUniform.source = sourceRandomUniform; + + return randomUniform; +})(defaultSource); diff --git a/frontend/node_modules/d3-random/src/weibull.js b/frontend/node_modules/d3-random/src/weibull.js new file mode 100644 index 0000000..b7d796c --- /dev/null +++ b/frontend/node_modules/d3-random/src/weibull.js @@ -0,0 +1,22 @@ +import defaultSource from "./defaultSource.js"; + +export default (function sourceRandomWeibull(source) { + function randomWeibull(k, a, b) { + var outerFunc; + if ((k = +k) === 0) { + outerFunc = x => -Math.log(x); + } else { + k = 1 / k; + outerFunc = x => Math.pow(x, k); + } + a = a == null ? 0 : +a; + b = b == null ? 1 : +b; + return function() { + return a + b * outerFunc(-Math.log1p(-source())); + }; + } + + randomWeibull.source = sourceRandomWeibull; + + return randomWeibull; +})(defaultSource); diff --git a/frontend/node_modules/d3-scale-chromatic/LICENSE b/frontend/node_modules/d3-scale-chromatic/LICENSE new file mode 100644 index 0000000..2d33881 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/LICENSE @@ -0,0 +1,28 @@ +Copyright 2010-2024 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. + +Apache-Style Software License for ColorBrewer software and ColorBrewer Color Schemes + +Copyright 2002 Cynthia Brewer, Mark Harrower, and The Pennsylvania State University + +Licensed under the Apache License, Version 2.0 (the "License"); you may not use +this file except in compliance with the License. You may obtain a copy of the +License at + +http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software distributed +under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR +CONDITIONS OF ANY KIND, either express or implied. See the License for the +specific language governing permissions and limitations under the License. diff --git a/frontend/node_modules/d3-scale-chromatic/README.md b/frontend/node_modules/d3-scale-chromatic/README.md new file mode 100644 index 0000000..74cbd8e --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/README.md @@ -0,0 +1,12 @@ +# d3-scale-chromatic + + + +This module provides sequential, diverging and categorical color schemes designed to work with [d3-scale](https://github.com/d3/d3-scale)’s scaleOrdinal and scaleSequential. Most of these schemes are derived from Cynthia A. Brewer’s [ColorBrewer](http://colorbrewer2.org). Since ColorBrewer publishes only discrete color schemes, the sequential and diverging scales are interpolated using [uniform B-splines](https://observablehq.com/@d3/colorbrewer-splines). + +## Resources + +- [Documentation](https://d3js.org/d3-scale-chromatic) +- [Examples](https://observablehq.com/collection/@d3/d3-scale-chromatic) +- [Releases](https://github.com/d3/d3-scale-chromatic/releases) +- [Getting help](https://d3js.org/community) diff --git a/frontend/node_modules/d3-scale-chromatic/dist/d3-scale-chromatic.js b/frontend/node_modules/d3-scale-chromatic/dist/d3-scale-chromatic.js new file mode 100644 index 0000000..e4431d2 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/dist/d3-scale-chromatic.js @@ -0,0 +1,522 @@ +// https://d3js.org/d3-scale-chromatic/ v3.1.0 Copyright 2010-2024 Mike Bostock; 2002 Cynthia Brewer, Mark Harrower, and The Pennsylvania State University +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-interpolate'), require('d3-color')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-interpolate', 'd3-color'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3, global.d3)); +})(this, (function (exports, d3Interpolate, d3Color) { 'use strict'; + +function colors(specifier) { + var n = specifier.length / 6 | 0, colors = new Array(n), i = 0; + while (i < n) colors[i] = "#" + specifier.slice(i * 6, ++i * 6); + return colors; +} + +var category10 = colors("1f77b4ff7f0e2ca02cd627289467bd8c564be377c27f7f7fbcbd2217becf"); + +var Accent = colors("7fc97fbeaed4fdc086ffff99386cb0f0027fbf5b17666666"); + +var Dark2 = colors("1b9e77d95f027570b3e7298a66a61ee6ab02a6761d666666"); + +var observable10 = colors("4269d0efb118ff725c6cc5b03ca951ff8ab7a463f297bbf59c6b4e9498a0"); + +var Paired = colors("a6cee31f78b4b2df8a33a02cfb9a99e31a1cfdbf6fff7f00cab2d66a3d9affff99b15928"); + +var Pastel1 = colors("fbb4aeb3cde3ccebc5decbe4fed9a6ffffcce5d8bdfddaecf2f2f2"); + +var Pastel2 = colors("b3e2cdfdcdaccbd5e8f4cae4e6f5c9fff2aef1e2cccccccc"); + +var Set1 = colors("e41a1c377eb84daf4a984ea3ff7f00ffff33a65628f781bf999999"); + +var Set2 = colors("66c2a5fc8d628da0cbe78ac3a6d854ffd92fe5c494b3b3b3"); + +var Set3 = colors("8dd3c7ffffb3bebadafb807280b1d3fdb462b3de69fccde5d9d9d9bc80bdccebc5ffed6f"); + +var Tableau10 = colors("4e79a7f28e2ce1575976b7b259a14fedc949af7aa1ff9da79c755fbab0ab"); + +var ramp$1 = scheme => d3Interpolate.interpolateRgbBasis(scheme[scheme.length - 1]); + +var scheme$q = new Array(3).concat( + "d8b365f5f5f55ab4ac", + "a6611adfc27d80cdc1018571", + "a6611adfc27df5f5f580cdc1018571", + "8c510ad8b365f6e8c3c7eae55ab4ac01665e", + "8c510ad8b365f6e8c3f5f5f5c7eae55ab4ac01665e", + "8c510abf812ddfc27df6e8c3c7eae580cdc135978f01665e", + "8c510abf812ddfc27df6e8c3f5f5f5c7eae580cdc135978f01665e", + "5430058c510abf812ddfc27df6e8c3c7eae580cdc135978f01665e003c30", + "5430058c510abf812ddfc27df6e8c3f5f5f5c7eae580cdc135978f01665e003c30" +).map(colors); + +var BrBG = ramp$1(scheme$q); + +var scheme$p = new Array(3).concat( + "af8dc3f7f7f77fbf7b", + "7b3294c2a5cfa6dba0008837", + "7b3294c2a5cff7f7f7a6dba0008837", + "762a83af8dc3e7d4e8d9f0d37fbf7b1b7837", + "762a83af8dc3e7d4e8f7f7f7d9f0d37fbf7b1b7837", + "762a839970abc2a5cfe7d4e8d9f0d3a6dba05aae611b7837", + "762a839970abc2a5cfe7d4e8f7f7f7d9f0d3a6dba05aae611b7837", + "40004b762a839970abc2a5cfe7d4e8d9f0d3a6dba05aae611b783700441b", + "40004b762a839970abc2a5cfe7d4e8f7f7f7d9f0d3a6dba05aae611b783700441b" +).map(colors); + +var PRGn = ramp$1(scheme$p); + +var scheme$o = new Array(3).concat( + "e9a3c9f7f7f7a1d76a", + "d01c8bf1b6dab8e1864dac26", + "d01c8bf1b6daf7f7f7b8e1864dac26", + "c51b7de9a3c9fde0efe6f5d0a1d76a4d9221", + "c51b7de9a3c9fde0eff7f7f7e6f5d0a1d76a4d9221", + "c51b7dde77aef1b6dafde0efe6f5d0b8e1867fbc414d9221", + "c51b7dde77aef1b6dafde0eff7f7f7e6f5d0b8e1867fbc414d9221", + "8e0152c51b7dde77aef1b6dafde0efe6f5d0b8e1867fbc414d9221276419", + "8e0152c51b7dde77aef1b6dafde0eff7f7f7e6f5d0b8e1867fbc414d9221276419" +).map(colors); + +var PiYG = ramp$1(scheme$o); + +var scheme$n = new Array(3).concat( + "998ec3f7f7f7f1a340", + "5e3c99b2abd2fdb863e66101", + "5e3c99b2abd2f7f7f7fdb863e66101", + "542788998ec3d8daebfee0b6f1a340b35806", + "542788998ec3d8daebf7f7f7fee0b6f1a340b35806", + "5427888073acb2abd2d8daebfee0b6fdb863e08214b35806", + "5427888073acb2abd2d8daebf7f7f7fee0b6fdb863e08214b35806", + "2d004b5427888073acb2abd2d8daebfee0b6fdb863e08214b358067f3b08", + "2d004b5427888073acb2abd2d8daebf7f7f7fee0b6fdb863e08214b358067f3b08" +).map(colors); + +var PuOr = ramp$1(scheme$n); + +var scheme$m = new Array(3).concat( + "ef8a62f7f7f767a9cf", + "ca0020f4a58292c5de0571b0", + "ca0020f4a582f7f7f792c5de0571b0", + "b2182bef8a62fddbc7d1e5f067a9cf2166ac", + "b2182bef8a62fddbc7f7f7f7d1e5f067a9cf2166ac", + "b2182bd6604df4a582fddbc7d1e5f092c5de4393c32166ac", + "b2182bd6604df4a582fddbc7f7f7f7d1e5f092c5de4393c32166ac", + "67001fb2182bd6604df4a582fddbc7d1e5f092c5de4393c32166ac053061", + "67001fb2182bd6604df4a582fddbc7f7f7f7d1e5f092c5de4393c32166ac053061" +).map(colors); + +var RdBu = ramp$1(scheme$m); + +var scheme$l = new Array(3).concat( + "ef8a62ffffff999999", + "ca0020f4a582bababa404040", + "ca0020f4a582ffffffbababa404040", + "b2182bef8a62fddbc7e0e0e09999994d4d4d", + "b2182bef8a62fddbc7ffffffe0e0e09999994d4d4d", + "b2182bd6604df4a582fddbc7e0e0e0bababa8787874d4d4d", + "b2182bd6604df4a582fddbc7ffffffe0e0e0bababa8787874d4d4d", + "67001fb2182bd6604df4a582fddbc7e0e0e0bababa8787874d4d4d1a1a1a", + "67001fb2182bd6604df4a582fddbc7ffffffe0e0e0bababa8787874d4d4d1a1a1a" +).map(colors); + +var RdGy = ramp$1(scheme$l); + +var scheme$k = new Array(3).concat( + "fc8d59ffffbf91bfdb", + "d7191cfdae61abd9e92c7bb6", + "d7191cfdae61ffffbfabd9e92c7bb6", + "d73027fc8d59fee090e0f3f891bfdb4575b4", + "d73027fc8d59fee090ffffbfe0f3f891bfdb4575b4", + "d73027f46d43fdae61fee090e0f3f8abd9e974add14575b4", + "d73027f46d43fdae61fee090ffffbfe0f3f8abd9e974add14575b4", + "a50026d73027f46d43fdae61fee090e0f3f8abd9e974add14575b4313695", + "a50026d73027f46d43fdae61fee090ffffbfe0f3f8abd9e974add14575b4313695" +).map(colors); + +var RdYlBu = ramp$1(scheme$k); + +var scheme$j = new Array(3).concat( + "fc8d59ffffbf91cf60", + "d7191cfdae61a6d96a1a9641", + "d7191cfdae61ffffbfa6d96a1a9641", + "d73027fc8d59fee08bd9ef8b91cf601a9850", + "d73027fc8d59fee08bffffbfd9ef8b91cf601a9850", + "d73027f46d43fdae61fee08bd9ef8ba6d96a66bd631a9850", + "d73027f46d43fdae61fee08bffffbfd9ef8ba6d96a66bd631a9850", + "a50026d73027f46d43fdae61fee08bd9ef8ba6d96a66bd631a9850006837", + "a50026d73027f46d43fdae61fee08bffffbfd9ef8ba6d96a66bd631a9850006837" +).map(colors); + +var RdYlGn = ramp$1(scheme$j); + +var scheme$i = new Array(3).concat( + "fc8d59ffffbf99d594", + "d7191cfdae61abdda42b83ba", + "d7191cfdae61ffffbfabdda42b83ba", + "d53e4ffc8d59fee08be6f59899d5943288bd", + "d53e4ffc8d59fee08bffffbfe6f59899d5943288bd", + "d53e4ff46d43fdae61fee08be6f598abdda466c2a53288bd", + "d53e4ff46d43fdae61fee08bffffbfe6f598abdda466c2a53288bd", + "9e0142d53e4ff46d43fdae61fee08be6f598abdda466c2a53288bd5e4fa2", + "9e0142d53e4ff46d43fdae61fee08bffffbfe6f598abdda466c2a53288bd5e4fa2" +).map(colors); + +var Spectral = ramp$1(scheme$i); + +var scheme$h = new Array(3).concat( + "e5f5f999d8c92ca25f", + "edf8fbb2e2e266c2a4238b45", + "edf8fbb2e2e266c2a42ca25f006d2c", + "edf8fbccece699d8c966c2a42ca25f006d2c", + "edf8fbccece699d8c966c2a441ae76238b45005824", + "f7fcfde5f5f9ccece699d8c966c2a441ae76238b45005824", + "f7fcfde5f5f9ccece699d8c966c2a441ae76238b45006d2c00441b" +).map(colors); + +var BuGn = ramp$1(scheme$h); + +var scheme$g = new Array(3).concat( + "e0ecf49ebcda8856a7", + "edf8fbb3cde38c96c688419d", + "edf8fbb3cde38c96c68856a7810f7c", + "edf8fbbfd3e69ebcda8c96c68856a7810f7c", + "edf8fbbfd3e69ebcda8c96c68c6bb188419d6e016b", + "f7fcfde0ecf4bfd3e69ebcda8c96c68c6bb188419d6e016b", + "f7fcfde0ecf4bfd3e69ebcda8c96c68c6bb188419d810f7c4d004b" +).map(colors); + +var BuPu = ramp$1(scheme$g); + +var scheme$f = new Array(3).concat( + "e0f3dba8ddb543a2ca", + "f0f9e8bae4bc7bccc42b8cbe", + "f0f9e8bae4bc7bccc443a2ca0868ac", + "f0f9e8ccebc5a8ddb57bccc443a2ca0868ac", + "f0f9e8ccebc5a8ddb57bccc44eb3d32b8cbe08589e", + "f7fcf0e0f3dbccebc5a8ddb57bccc44eb3d32b8cbe08589e", + "f7fcf0e0f3dbccebc5a8ddb57bccc44eb3d32b8cbe0868ac084081" +).map(colors); + +var GnBu = ramp$1(scheme$f); + +var scheme$e = new Array(3).concat( + "fee8c8fdbb84e34a33", + "fef0d9fdcc8afc8d59d7301f", + "fef0d9fdcc8afc8d59e34a33b30000", + "fef0d9fdd49efdbb84fc8d59e34a33b30000", + "fef0d9fdd49efdbb84fc8d59ef6548d7301f990000", + "fff7ecfee8c8fdd49efdbb84fc8d59ef6548d7301f990000", + "fff7ecfee8c8fdd49efdbb84fc8d59ef6548d7301fb300007f0000" +).map(colors); + +var OrRd = ramp$1(scheme$e); + +var scheme$d = new Array(3).concat( + "ece2f0a6bddb1c9099", + "f6eff7bdc9e167a9cf02818a", + "f6eff7bdc9e167a9cf1c9099016c59", + "f6eff7d0d1e6a6bddb67a9cf1c9099016c59", + "f6eff7d0d1e6a6bddb67a9cf3690c002818a016450", + "fff7fbece2f0d0d1e6a6bddb67a9cf3690c002818a016450", + "fff7fbece2f0d0d1e6a6bddb67a9cf3690c002818a016c59014636" +).map(colors); + +var PuBuGn = ramp$1(scheme$d); + +var scheme$c = new Array(3).concat( + "ece7f2a6bddb2b8cbe", + "f1eef6bdc9e174a9cf0570b0", + "f1eef6bdc9e174a9cf2b8cbe045a8d", + "f1eef6d0d1e6a6bddb74a9cf2b8cbe045a8d", + "f1eef6d0d1e6a6bddb74a9cf3690c00570b0034e7b", + "fff7fbece7f2d0d1e6a6bddb74a9cf3690c00570b0034e7b", + "fff7fbece7f2d0d1e6a6bddb74a9cf3690c00570b0045a8d023858" +).map(colors); + +var PuBu = ramp$1(scheme$c); + +var scheme$b = new Array(3).concat( + "e7e1efc994c7dd1c77", + "f1eef6d7b5d8df65b0ce1256", + "f1eef6d7b5d8df65b0dd1c77980043", + "f1eef6d4b9dac994c7df65b0dd1c77980043", + "f1eef6d4b9dac994c7df65b0e7298ace125691003f", + "f7f4f9e7e1efd4b9dac994c7df65b0e7298ace125691003f", + "f7f4f9e7e1efd4b9dac994c7df65b0e7298ace125698004367001f" +).map(colors); + +var PuRd = ramp$1(scheme$b); + +var scheme$a = new Array(3).concat( + "fde0ddfa9fb5c51b8a", + "feebe2fbb4b9f768a1ae017e", + "feebe2fbb4b9f768a1c51b8a7a0177", + "feebe2fcc5c0fa9fb5f768a1c51b8a7a0177", + "feebe2fcc5c0fa9fb5f768a1dd3497ae017e7a0177", + "fff7f3fde0ddfcc5c0fa9fb5f768a1dd3497ae017e7a0177", + "fff7f3fde0ddfcc5c0fa9fb5f768a1dd3497ae017e7a017749006a" +).map(colors); + +var RdPu = ramp$1(scheme$a); + +var scheme$9 = new Array(3).concat( + "edf8b17fcdbb2c7fb8", + "ffffcca1dab441b6c4225ea8", + "ffffcca1dab441b6c42c7fb8253494", + "ffffccc7e9b47fcdbb41b6c42c7fb8253494", + "ffffccc7e9b47fcdbb41b6c41d91c0225ea80c2c84", + "ffffd9edf8b1c7e9b47fcdbb41b6c41d91c0225ea80c2c84", + "ffffd9edf8b1c7e9b47fcdbb41b6c41d91c0225ea8253494081d58" +).map(colors); + +var YlGnBu = ramp$1(scheme$9); + +var scheme$8 = new Array(3).concat( + "f7fcb9addd8e31a354", + "ffffccc2e69978c679238443", + "ffffccc2e69978c67931a354006837", + "ffffccd9f0a3addd8e78c67931a354006837", + "ffffccd9f0a3addd8e78c67941ab5d238443005a32", + "ffffe5f7fcb9d9f0a3addd8e78c67941ab5d238443005a32", + "ffffe5f7fcb9d9f0a3addd8e78c67941ab5d238443006837004529" +).map(colors); + +var YlGn = ramp$1(scheme$8); + +var scheme$7 = new Array(3).concat( + "fff7bcfec44fd95f0e", + "ffffd4fed98efe9929cc4c02", + "ffffd4fed98efe9929d95f0e993404", + "ffffd4fee391fec44ffe9929d95f0e993404", + "ffffd4fee391fec44ffe9929ec7014cc4c028c2d04", + "ffffe5fff7bcfee391fec44ffe9929ec7014cc4c028c2d04", + "ffffe5fff7bcfee391fec44ffe9929ec7014cc4c02993404662506" +).map(colors); + +var YlOrBr = ramp$1(scheme$7); + +var scheme$6 = new Array(3).concat( + "ffeda0feb24cf03b20", + "ffffb2fecc5cfd8d3ce31a1c", + "ffffb2fecc5cfd8d3cf03b20bd0026", + "ffffb2fed976feb24cfd8d3cf03b20bd0026", + "ffffb2fed976feb24cfd8d3cfc4e2ae31a1cb10026", + "ffffccffeda0fed976feb24cfd8d3cfc4e2ae31a1cb10026", + "ffffccffeda0fed976feb24cfd8d3cfc4e2ae31a1cbd0026800026" +).map(colors); + +var YlOrRd = ramp$1(scheme$6); + +var scheme$5 = new Array(3).concat( + "deebf79ecae13182bd", + "eff3ffbdd7e76baed62171b5", + "eff3ffbdd7e76baed63182bd08519c", + "eff3ffc6dbef9ecae16baed63182bd08519c", + "eff3ffc6dbef9ecae16baed64292c62171b5084594", + "f7fbffdeebf7c6dbef9ecae16baed64292c62171b5084594", + "f7fbffdeebf7c6dbef9ecae16baed64292c62171b508519c08306b" +).map(colors); + +var Blues = ramp$1(scheme$5); + +var scheme$4 = new Array(3).concat( + "e5f5e0a1d99b31a354", + "edf8e9bae4b374c476238b45", + "edf8e9bae4b374c47631a354006d2c", + "edf8e9c7e9c0a1d99b74c47631a354006d2c", + "edf8e9c7e9c0a1d99b74c47641ab5d238b45005a32", + "f7fcf5e5f5e0c7e9c0a1d99b74c47641ab5d238b45005a32", + "f7fcf5e5f5e0c7e9c0a1d99b74c47641ab5d238b45006d2c00441b" +).map(colors); + +var Greens = ramp$1(scheme$4); + +var scheme$3 = new Array(3).concat( + "f0f0f0bdbdbd636363", + "f7f7f7cccccc969696525252", + "f7f7f7cccccc969696636363252525", + "f7f7f7d9d9d9bdbdbd969696636363252525", + "f7f7f7d9d9d9bdbdbd969696737373525252252525", + "fffffff0f0f0d9d9d9bdbdbd969696737373525252252525", + "fffffff0f0f0d9d9d9bdbdbd969696737373525252252525000000" +).map(colors); + +var Greys = ramp$1(scheme$3); + +var scheme$2 = new Array(3).concat( + "efedf5bcbddc756bb1", + "f2f0f7cbc9e29e9ac86a51a3", + "f2f0f7cbc9e29e9ac8756bb154278f", + "f2f0f7dadaebbcbddc9e9ac8756bb154278f", + "f2f0f7dadaebbcbddc9e9ac8807dba6a51a34a1486", + "fcfbfdefedf5dadaebbcbddc9e9ac8807dba6a51a34a1486", + "fcfbfdefedf5dadaebbcbddc9e9ac8807dba6a51a354278f3f007d" +).map(colors); + +var Purples = ramp$1(scheme$2); + +var scheme$1 = new Array(3).concat( + "fee0d2fc9272de2d26", + "fee5d9fcae91fb6a4acb181d", + "fee5d9fcae91fb6a4ade2d26a50f15", + "fee5d9fcbba1fc9272fb6a4ade2d26a50f15", + "fee5d9fcbba1fc9272fb6a4aef3b2ccb181d99000d", + "fff5f0fee0d2fcbba1fc9272fb6a4aef3b2ccb181d99000d", + "fff5f0fee0d2fcbba1fc9272fb6a4aef3b2ccb181da50f1567000d" +).map(colors); + +var Reds = ramp$1(scheme$1); + +var scheme = new Array(3).concat( + "fee6cefdae6be6550d", + "feeddefdbe85fd8d3cd94701", + "feeddefdbe85fd8d3ce6550da63603", + "feeddefdd0a2fdae6bfd8d3ce6550da63603", + "feeddefdd0a2fdae6bfd8d3cf16913d948018c2d04", + "fff5ebfee6cefdd0a2fdae6bfd8d3cf16913d948018c2d04", + "fff5ebfee6cefdd0a2fdae6bfd8d3cf16913d94801a636037f2704" +).map(colors); + +var Oranges = ramp$1(scheme); + +function cividis(t) { + t = Math.max(0, Math.min(1, t)); + return "rgb(" + + Math.max(0, Math.min(255, Math.round(-4.54 - t * (35.34 - t * (2381.73 - t * (6402.7 - t * (7024.72 - t * 2710.57))))))) + ", " + + Math.max(0, Math.min(255, Math.round(32.49 + t * (170.73 + t * (52.82 - t * (131.46 - t * (176.58 - t * 67.37))))))) + ", " + + Math.max(0, Math.min(255, Math.round(81.24 + t * (442.36 - t * (2482.43 - t * (6167.24 - t * (6614.94 - t * 2475.67))))))) + + ")"; +} + +var cubehelix = d3Interpolate.interpolateCubehelixLong(d3Color.cubehelix(300, 0.5, 0.0), d3Color.cubehelix(-240, 0.5, 1.0)); + +var warm = d3Interpolate.interpolateCubehelixLong(d3Color.cubehelix(-100, 0.75, 0.35), d3Color.cubehelix(80, 1.50, 0.8)); + +var cool = d3Interpolate.interpolateCubehelixLong(d3Color.cubehelix(260, 0.75, 0.35), d3Color.cubehelix(80, 1.50, 0.8)); + +var c$1 = d3Color.cubehelix(); + +function rainbow(t) { + if (t < 0 || t > 1) t -= Math.floor(t); + var ts = Math.abs(t - 0.5); + c$1.h = 360 * t - 100; + c$1.s = 1.5 - 1.5 * ts; + c$1.l = 0.8 - 0.9 * ts; + return c$1 + ""; +} + +var c = d3Color.rgb(), + pi_1_3 = Math.PI / 3, + pi_2_3 = Math.PI * 2 / 3; + +function sinebow(t) { + var x; + t = (0.5 - t) * Math.PI; + c.r = 255 * (x = Math.sin(t)) * x; + c.g = 255 * (x = Math.sin(t + pi_1_3)) * x; + c.b = 255 * (x = Math.sin(t + pi_2_3)) * x; + return c + ""; +} + +function turbo(t) { + t = Math.max(0, Math.min(1, t)); + return "rgb(" + + Math.max(0, Math.min(255, Math.round(34.61 + t * (1172.33 - t * (10793.56 - t * (33300.12 - t * (38394.49 - t * 14825.05))))))) + ", " + + Math.max(0, Math.min(255, Math.round(23.31 + t * (557.33 + t * (1225.33 - t * (3574.96 - t * (1073.77 + t * 707.56))))))) + ", " + + Math.max(0, Math.min(255, Math.round(27.2 + t * (3211.1 - t * (15327.97 - t * (27814 - t * (22569.18 - t * 6838.66))))))) + + ")"; +} + +function ramp(range) { + var n = range.length; + return function(t) { + return range[Math.max(0, Math.min(n - 1, Math.floor(t * n)))]; + }; +} + +var viridis = ramp(colors("44015444025645045745055946075a46085c460a5d460b5e470d60470e6147106347116447136548146748166848176948186a481a6c481b6d481c6e481d6f481f70482071482173482374482475482576482677482878482979472a7a472c7a472d7b472e7c472f7d46307e46327e46337f463480453581453781453882443983443a83443b84433d84433e85423f854240864241864142874144874045884046883f47883f48893e49893e4a893e4c8a3d4d8a3d4e8a3c4f8a3c508b3b518b3b528b3a538b3a548c39558c39568c38588c38598c375a8c375b8d365c8d365d8d355e8d355f8d34608d34618d33628d33638d32648e32658e31668e31678e31688e30698e306a8e2f6b8e2f6c8e2e6d8e2e6e8e2e6f8e2d708e2d718e2c718e2c728e2c738e2b748e2b758e2a768e2a778e2a788e29798e297a8e297b8e287c8e287d8e277e8e277f8e27808e26818e26828e26828e25838e25848e25858e24868e24878e23888e23898e238a8d228b8d228c8d228d8d218e8d218f8d21908d21918c20928c20928c20938c1f948c1f958b1f968b1f978b1f988b1f998a1f9a8a1e9b8a1e9c891e9d891f9e891f9f881fa0881fa1881fa1871fa28720a38620a48621a58521a68522a78522a88423a98324aa8325ab8225ac8226ad8127ad8128ae8029af7f2ab07f2cb17e2db27d2eb37c2fb47c31b57b32b67a34b67935b77937b87838b9773aba763bbb753dbc743fbc7340bd7242be7144bf7046c06f48c16e4ac16d4cc26c4ec36b50c46a52c56954c56856c66758c7655ac8645cc8635ec96260ca6063cb5f65cb5e67cc5c69cd5b6ccd5a6ece5870cf5773d05675d05477d1537ad1517cd2507fd34e81d34d84d44b86d54989d5488bd6468ed64590d74393d74195d84098d83e9bd93c9dd93ba0da39a2da37a5db36a8db34aadc32addc30b0dd2fb2dd2db5de2bb8de29bade28bddf26c0df25c2df23c5e021c8e020cae11fcde11dd0e11cd2e21bd5e21ad8e219dae319dde318dfe318e2e418e5e419e7e419eae51aece51befe51cf1e51df4e61ef6e620f8e621fbe723fde725")); + +var magma = ramp(colors("00000401000501010601010802010902020b02020d03030f03031204041405041606051806051a07061c08071e0907200a08220b09240c09260d0a290e0b2b100b2d110c2f120d31130d34140e36150e38160f3b180f3d19103f1a10421c10441d11471e114920114b21114e22115024125325125527125829115a2a115c2c115f2d11612f116331116533106734106936106b38106c390f6e3b0f703d0f713f0f72400f74420f75440f764510774710784910784a10794c117a4e117b4f127b51127c52137c54137d56147d57157e59157e5a167e5c167f5d177f5f187f601880621980641a80651a80671b80681c816a1c816b1d816d1d816e1e81701f81721f817320817521817621817822817922827b23827c23827e24828025828125818326818426818627818827818928818b29818c29818e2a81902a81912b81932b80942c80962c80982d80992d809b2e7f9c2e7f9e2f7fa02f7fa1307ea3307ea5317ea6317da8327daa337dab337cad347cae347bb0357bb2357bb3367ab5367ab73779b83779ba3878bc3978bd3977bf3a77c03a76c23b75c43c75c53c74c73d73c83e73ca3e72cc3f71cd4071cf4070d0416fd2426fd3436ed5446dd6456cd8456cd9466bdb476adc4869de4968df4a68e04c67e24d66e34e65e44f64e55064e75263e85362e95462ea5661eb5760ec5860ed5a5fee5b5eef5d5ef05f5ef1605df2625df2645cf3655cf4675cf4695cf56b5cf66c5cf66e5cf7705cf7725cf8745cf8765cf9785df9795df97b5dfa7d5efa7f5efa815ffb835ffb8560fb8761fc8961fc8a62fc8c63fc8e64fc9065fd9266fd9467fd9668fd9869fd9a6afd9b6bfe9d6cfe9f6dfea16efea36ffea571fea772fea973feaa74feac76feae77feb078feb27afeb47bfeb67cfeb77efeb97ffebb81febd82febf84fec185fec287fec488fec68afec88cfeca8dfecc8ffecd90fecf92fed194fed395fed597fed799fed89afdda9cfddc9efddea0fde0a1fde2a3fde3a5fde5a7fde7a9fde9aafdebacfcecaefceeb0fcf0b2fcf2b4fcf4b6fcf6b8fcf7b9fcf9bbfcfbbdfcfdbf")); + +var inferno = ramp(colors("00000401000501010601010802010a02020c02020e03021004031204031405041706041907051b08051d09061f0a07220b07240c08260d08290e092b10092d110a30120a32140b34150b37160b39180c3c190c3e1b0c411c0c431e0c451f0c48210c4a230c4c240c4f260c51280b53290b552b0b572d0b592f0a5b310a5c320a5e340a5f3609613809623909633b09643d09653e0966400a67420a68440a68450a69470b6a490b6a4a0c6b4c0c6b4d0d6c4f0d6c510e6c520e6d540f6d550f6d57106e59106e5a116e5c126e5d126e5f136e61136e62146e64156e65156e67166e69166e6a176e6c186e6d186e6f196e71196e721a6e741a6e751b6e771c6d781c6d7a1d6d7c1d6d7d1e6d7f1e6c801f6c82206c84206b85216b87216b88226a8a226a8c23698d23698f24699025689225689326679526679727669827669a28659b29649d29649f2a63a02a63a22b62a32c61a52c60a62d60a82e5fa92e5eab2f5ead305dae305cb0315bb1325ab3325ab43359b63458b73557b93556ba3655bc3754bd3853bf3952c03a51c13a50c33b4fc43c4ec63d4dc73e4cc83f4bca404acb4149cc4248ce4347cf4446d04545d24644d34743d44842d54a41d74b3fd84c3ed94d3dda4e3cdb503bdd513ade5238df5337e05536e15635e25734e35933e45a31e55c30e65d2fe75e2ee8602de9612bea632aeb6429eb6628ec6726ed6925ee6a24ef6c23ef6e21f06f20f1711ff1731df2741cf3761bf37819f47918f57b17f57d15f67e14f68013f78212f78410f8850ff8870ef8890cf98b0bf98c0af98e09fa9008fa9207fa9407fb9606fb9706fb9906fb9b06fb9d07fc9f07fca108fca309fca50afca60cfca80dfcaa0ffcac11fcae12fcb014fcb216fcb418fbb61afbb81dfbba1ffbbc21fbbe23fac026fac228fac42afac62df9c72ff9c932f9cb35f8cd37f8cf3af7d13df7d340f6d543f6d746f5d949f5db4cf4dd4ff4df53f4e156f3e35af3e55df2e661f2e865f2ea69f1ec6df1ed71f1ef75f1f179f2f27df2f482f3f586f3f68af4f88ef5f992f6fa96f8fb9af9fc9dfafda1fcffa4")); + +var plasma = ramp(colors("0d088710078813078916078a19068c1b068d1d068e20068f2206902406912605912805922a05932c05942e05952f059631059733059735049837049938049a3a049a3c049b3e049c3f049c41049d43039e44039e46039f48039f4903a04b03a14c02a14e02a25002a25102a35302a35502a45601a45801a45901a55b01a55c01a65e01a66001a66100a76300a76400a76600a76700a86900a86a00a86c00a86e00a86f00a87100a87201a87401a87501a87701a87801a87a02a87b02a87d03a87e03a88004a88104a78305a78405a78606a68707a68808a68a09a58b0aa58d0ba58e0ca48f0da4910ea3920fa39410a29511a19613a19814a099159f9a169f9c179e9d189d9e199da01a9ca11b9ba21d9aa31e9aa51f99a62098a72197a82296aa2395ab2494ac2694ad2793ae2892b02991b12a90b22b8fb32c8eb42e8db52f8cb6308bb7318ab83289ba3388bb3488bc3587bd3786be3885bf3984c03a83c13b82c23c81c33d80c43e7fc5407ec6417dc7427cc8437bc9447aca457acb4679cc4778cc4977cd4a76ce4b75cf4c74d04d73d14e72d24f71d35171d45270d5536fd5546ed6556dd7566cd8576bd9586ada5a6ada5b69db5c68dc5d67dd5e66de5f65de6164df6263e06363e16462e26561e26660e3685fe4695ee56a5de56b5de66c5ce76e5be76f5ae87059e97158e97257ea7457eb7556eb7655ec7754ed7953ed7a52ee7b51ef7c51ef7e50f07f4ff0804ef1814df1834cf2844bf3854bf3874af48849f48948f58b47f58c46f68d45f68f44f79044f79143f79342f89441f89540f9973ff9983ef99a3efa9b3dfa9c3cfa9e3bfb9f3afba139fba238fca338fca537fca636fca835fca934fdab33fdac33fdae32fdaf31fdb130fdb22ffdb42ffdb52efeb72dfeb82cfeba2cfebb2bfebd2afebe2afec029fdc229fdc328fdc527fdc627fdc827fdca26fdcb26fccd25fcce25fcd025fcd225fbd324fbd524fbd724fad824fada24f9dc24f9dd25f8df25f8e125f7e225f7e425f6e626f6e826f5e926f5eb27f4ed27f3ee27f3f027f2f227f1f426f1f525f0f724f0f921")); + +exports.interpolateBlues = Blues; +exports.interpolateBrBG = BrBG; +exports.interpolateBuGn = BuGn; +exports.interpolateBuPu = BuPu; +exports.interpolateCividis = cividis; +exports.interpolateCool = cool; +exports.interpolateCubehelixDefault = cubehelix; +exports.interpolateGnBu = GnBu; +exports.interpolateGreens = Greens; +exports.interpolateGreys = Greys; +exports.interpolateInferno = inferno; +exports.interpolateMagma = magma; +exports.interpolateOrRd = OrRd; +exports.interpolateOranges = Oranges; +exports.interpolatePRGn = PRGn; +exports.interpolatePiYG = PiYG; +exports.interpolatePlasma = plasma; +exports.interpolatePuBu = PuBu; +exports.interpolatePuBuGn = PuBuGn; +exports.interpolatePuOr = PuOr; +exports.interpolatePuRd = PuRd; +exports.interpolatePurples = Purples; +exports.interpolateRainbow = rainbow; +exports.interpolateRdBu = RdBu; +exports.interpolateRdGy = RdGy; +exports.interpolateRdPu = RdPu; +exports.interpolateRdYlBu = RdYlBu; +exports.interpolateRdYlGn = RdYlGn; +exports.interpolateReds = Reds; +exports.interpolateSinebow = sinebow; +exports.interpolateSpectral = Spectral; +exports.interpolateTurbo = turbo; +exports.interpolateViridis = viridis; +exports.interpolateWarm = warm; +exports.interpolateYlGn = YlGn; +exports.interpolateYlGnBu = YlGnBu; +exports.interpolateYlOrBr = YlOrBr; +exports.interpolateYlOrRd = YlOrRd; +exports.schemeAccent = Accent; +exports.schemeBlues = scheme$5; +exports.schemeBrBG = scheme$q; +exports.schemeBuGn = scheme$h; +exports.schemeBuPu = scheme$g; +exports.schemeCategory10 = category10; +exports.schemeDark2 = Dark2; +exports.schemeGnBu = scheme$f; +exports.schemeGreens = scheme$4; +exports.schemeGreys = scheme$3; +exports.schemeObservable10 = observable10; +exports.schemeOrRd = scheme$e; +exports.schemeOranges = scheme; +exports.schemePRGn = scheme$p; +exports.schemePaired = Paired; +exports.schemePastel1 = Pastel1; +exports.schemePastel2 = Pastel2; +exports.schemePiYG = scheme$o; +exports.schemePuBu = scheme$c; +exports.schemePuBuGn = scheme$d; +exports.schemePuOr = scheme$n; +exports.schemePuRd = scheme$b; +exports.schemePurples = scheme$2; +exports.schemeRdBu = scheme$m; +exports.schemeRdGy = scheme$l; +exports.schemeRdPu = scheme$a; +exports.schemeRdYlBu = scheme$k; +exports.schemeRdYlGn = scheme$j; +exports.schemeReds = scheme$1; +exports.schemeSet1 = Set1; +exports.schemeSet2 = Set2; +exports.schemeSet3 = Set3; +exports.schemeSpectral = scheme$i; +exports.schemeTableau10 = Tableau10; +exports.schemeYlGn = scheme$8; +exports.schemeYlGnBu = scheme$9; +exports.schemeYlOrBr = scheme$7; +exports.schemeYlOrRd = scheme$6; + +Object.defineProperty(exports, '__esModule', { value: true }); + +})); diff --git a/frontend/node_modules/d3-scale-chromatic/dist/d3-scale-chromatic.min.js b/frontend/node_modules/d3-scale-chromatic/dist/d3-scale-chromatic.min.js new file mode 100644 index 0000000..a01daea --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/dist/d3-scale-chromatic.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-scale-chromatic/ v3.1.0 Copyright 2010-2024 Mike Bostock; 2002 Cynthia Brewer, Mark Harrower, and The Pennsylvania State University +!function(f,e){"object"==typeof exports&&"undefined"!=typeof module?e(exports,require("d3-interpolate"),require("d3-color")):"function"==typeof define&&define.amd?define(["exports","d3-interpolate","d3-color"],e):e((f="undefined"!=typeof globalThis?globalThis:f||self).d3=f.d3||{},f.d3,f.d3)}(this,(function(f,e,d){"use strict";function a(f){for(var e=f.length/6|0,d=new Array(e),a=0;ae.interpolateRgbBasis(f[f.length-1]),s=new Array(3).concat("d8b365f5f5f55ab4ac","a6611adfc27d80cdc1018571","a6611adfc27df5f5f580cdc1018571","8c510ad8b365f6e8c3c7eae55ab4ac01665e","8c510ad8b365f6e8c3f5f5f5c7eae55ab4ac01665e","8c510abf812ddfc27df6e8c3c7eae580cdc135978f01665e","8c510abf812ddfc27df6e8c3f5f5f5c7eae580cdc135978f01665e","5430058c510abf812ddfc27df6e8c3c7eae580cdc135978f01665e003c30","5430058c510abf812ddfc27df6e8c3f5f5f5c7eae580cdc135978f01665e003c30").map(a),y=u(s),M=new Array(3).concat("af8dc3f7f7f77fbf7b","7b3294c2a5cfa6dba0008837","7b3294c2a5cff7f7f7a6dba0008837","762a83af8dc3e7d4e8d9f0d37fbf7b1b7837","762a83af8dc3e7d4e8f7f7f7d9f0d37fbf7b1b7837","762a839970abc2a5cfe7d4e8d9f0d3a6dba05aae611b7837","762a839970abc2a5cfe7d4e8f7f7f7d9f0d3a6dba05aae611b7837","40004b762a839970abc2a5cfe7d4e8d9f0d3a6dba05aae611b783700441b","40004b762a839970abc2a5cfe7d4e8f7f7f7d9f0d3a6dba05aae611b783700441b").map(a),w=u(M),A=new Array(3).concat("e9a3c9f7f7f7a1d76a","d01c8bf1b6dab8e1864dac26","d01c8bf1b6daf7f7f7b8e1864dac26","c51b7de9a3c9fde0efe6f5d0a1d76a4d9221","c51b7de9a3c9fde0eff7f7f7e6f5d0a1d76a4d9221","c51b7dde77aef1b6dafde0efe6f5d0b8e1867fbc414d9221","c51b7dde77aef1b6dafde0eff7f7f7e6f5d0b8e1867fbc414d9221","8e0152c51b7dde77aef1b6dafde0efe6f5d0b8e1867fbc414d9221276419","8e0152c51b7dde77aef1b6dafde0eff7f7f7e6f5d0b8e1867fbc414d9221276419").map(a),P=u(A),B=new Array(3).concat("998ec3f7f7f7f1a340","5e3c99b2abd2fdb863e66101","5e3c99b2abd2f7f7f7fdb863e66101","542788998ec3d8daebfee0b6f1a340b35806","542788998ec3d8daebf7f7f7fee0b6f1a340b35806","5427888073acb2abd2d8daebfee0b6fdb863e08214b35806","5427888073acb2abd2d8daebf7f7f7fee0b6fdb863e08214b35806","2d004b5427888073acb2abd2d8daebfee0b6fdb863e08214b358067f3b08","2d004b5427888073acb2abd2d8daebf7f7f7fee0b6fdb863e08214b358067f3b08").map(a),G=u(B),x=new Array(3).concat("ef8a62f7f7f767a9cf","ca0020f4a58292c5de0571b0","ca0020f4a582f7f7f792c5de0571b0","b2182bef8a62fddbc7d1e5f067a9cf2166ac","b2182bef8a62fddbc7f7f7f7d1e5f067a9cf2166ac","b2182bd6604df4a582fddbc7d1e5f092c5de4393c32166ac","b2182bd6604df4a582fddbc7f7f7f7d1e5f092c5de4393c32166ac","67001fb2182bd6604df4a582fddbc7d1e5f092c5de4393c32166ac053061","67001fb2182bd6604df4a582fddbc7f7f7f7d1e5f092c5de4393c32166ac053061").map(a),R=u(x),g=new Array(3).concat("ef8a62ffffff999999","ca0020f4a582bababa404040","ca0020f4a582ffffffbababa404040","b2182bef8a62fddbc7e0e0e09999994d4d4d","b2182bef8a62fddbc7ffffffe0e0e09999994d4d4d","b2182bd6604df4a582fddbc7e0e0e0bababa8787874d4d4d","b2182bd6604df4a582fddbc7ffffffe0e0e0bababa8787874d4d4d","67001fb2182bd6604df4a582fddbc7e0e0e0bababa8787874d4d4d1a1a1a","67001fb2182bd6604df4a582fddbc7ffffffe0e0e0bababa8787874d4d4d1a1a1a").map(a),Y=u(g),O=new Array(3).concat("fc8d59ffffbf91bfdb","d7191cfdae61abd9e92c7bb6","d7191cfdae61ffffbfabd9e92c7bb6","d73027fc8d59fee090e0f3f891bfdb4575b4","d73027fc8d59fee090ffffbfe0f3f891bfdb4575b4","d73027f46d43fdae61fee090e0f3f8abd9e974add14575b4","d73027f46d43fdae61fee090ffffbfe0f3f8abd9e974add14575b4","a50026d73027f46d43fdae61fee090e0f3f8abd9e974add14575b4313695","a50026d73027f46d43fdae61fee090ffffbfe0f3f8abd9e974add14575b4313695").map(a),v=u(O),C=new Array(3).concat("fc8d59ffffbf91cf60","d7191cfdae61a6d96a1a9641","d7191cfdae61ffffbfa6d96a1a9641","d73027fc8d59fee08bd9ef8b91cf601a9850","d73027fc8d59fee08bffffbfd9ef8b91cf601a9850","d73027f46d43fdae61fee08bd9ef8ba6d96a66bd631a9850","d73027f46d43fdae61fee08bffffbfd9ef8ba6d96a66bd631a9850","a50026d73027f46d43fdae61fee08bd9ef8ba6d96a66bd631a9850006837","a50026d73027f46d43fdae61fee08bffffbfd9ef8ba6d96a66bd631a9850006837").map(a),S=u(C),I=new Array(3).concat("fc8d59ffffbf99d594","d7191cfdae61abdda42b83ba","d7191cfdae61ffffbfabdda42b83ba","d53e4ffc8d59fee08be6f59899d5943288bd","d53e4ffc8d59fee08bffffbfe6f59899d5943288bd","d53e4ff46d43fdae61fee08be6f598abdda466c2a53288bd","d53e4ff46d43fdae61fee08bffffbfe6f598abdda466c2a53288bd","9e0142d53e4ff46d43fdae61fee08be6f598abdda466c2a53288bd5e4fa2","9e0142d53e4ff46d43fdae61fee08bffffbfe6f598abdda466c2a53288bd5e4fa2").map(a),T=u(I),L=new Array(3).concat("e5f5f999d8c92ca25f","edf8fbb2e2e266c2a4238b45","edf8fbb2e2e266c2a42ca25f006d2c","edf8fbccece699d8c966c2a42ca25f006d2c","edf8fbccece699d8c966c2a441ae76238b45005824","f7fcfde5f5f9ccece699d8c966c2a441ae76238b45005824","f7fcfde5f5f9ccece699d8c966c2a441ae76238b45006d2c00441b").map(a),j=u(L),q=new Array(3).concat("e0ecf49ebcda8856a7","edf8fbb3cde38c96c688419d","edf8fbb3cde38c96c68856a7810f7c","edf8fbbfd3e69ebcda8c96c68856a7810f7c","edf8fbbfd3e69ebcda8c96c68c6bb188419d6e016b","f7fcfde0ecf4bfd3e69ebcda8c96c68c6bb188419d6e016b","f7fcfde0ecf4bfd3e69ebcda8c96c68c6bb188419d810f7c4d004b").map(a),D=u(q),_=new Array(3).concat("e0f3dba8ddb543a2ca","f0f9e8bae4bc7bccc42b8cbe","f0f9e8bae4bc7bccc443a2ca0868ac","f0f9e8ccebc5a8ddb57bccc443a2ca0868ac","f0f9e8ccebc5a8ddb57bccc44eb3d32b8cbe08589e","f7fcf0e0f3dbccebc5a8ddb57bccc44eb3d32b8cbe08589e","f7fcf0e0f3dbccebc5a8ddb57bccc44eb3d32b8cbe0868ac084081").map(a),k=u(_),V=new Array(3).concat("fee8c8fdbb84e34a33","fef0d9fdcc8afc8d59d7301f","fef0d9fdcc8afc8d59e34a33b30000","fef0d9fdd49efdbb84fc8d59e34a33b30000","fef0d9fdd49efdbb84fc8d59ef6548d7301f990000","fff7ecfee8c8fdd49efdbb84fc8d59ef6548d7301f990000","fff7ecfee8c8fdd49efdbb84fc8d59ef6548d7301fb300007f0000").map(a),W=u(V),z=new Array(3).concat("ece2f0a6bddb1c9099","f6eff7bdc9e167a9cf02818a","f6eff7bdc9e167a9cf1c9099016c59","f6eff7d0d1e6a6bddb67a9cf1c9099016c59","f6eff7d0d1e6a6bddb67a9cf3690c002818a016450","fff7fbece2f0d0d1e6a6bddb67a9cf3690c002818a016450","fff7fbece2f0d0d1e6a6bddb67a9cf3690c002818a016c59014636").map(a),E=u(z),F=new Array(3).concat("ece7f2a6bddb2b8cbe","f1eef6bdc9e174a9cf0570b0","f1eef6bdc9e174a9cf2b8cbe045a8d","f1eef6d0d1e6a6bddb74a9cf2b8cbe045a8d","f1eef6d0d1e6a6bddb74a9cf3690c00570b0034e7b","fff7fbece7f2d0d1e6a6bddb74a9cf3690c00570b0034e7b","fff7fbece7f2d0d1e6a6bddb74a9cf3690c00570b0045a8d023858").map(a),H=u(F),J=new Array(3).concat("e7e1efc994c7dd1c77","f1eef6d7b5d8df65b0ce1256","f1eef6d7b5d8df65b0dd1c77980043","f1eef6d4b9dac994c7df65b0dd1c77980043","f1eef6d4b9dac994c7df65b0e7298ace125691003f","f7f4f9e7e1efd4b9dac994c7df65b0e7298ace125691003f","f7f4f9e7e1efd4b9dac994c7df65b0e7298ace125698004367001f").map(a),K=u(J),N=new Array(3).concat("fde0ddfa9fb5c51b8a","feebe2fbb4b9f768a1ae017e","feebe2fbb4b9f768a1c51b8a7a0177","feebe2fcc5c0fa9fb5f768a1c51b8a7a0177","feebe2fcc5c0fa9fb5f768a1dd3497ae017e7a0177","fff7f3fde0ddfcc5c0fa9fb5f768a1dd3497ae017e7a0177","fff7f3fde0ddfcc5c0fa9fb5f768a1dd3497ae017e7a017749006a").map(a),Q=u(N),U=new Array(3).concat("edf8b17fcdbb2c7fb8","ffffcca1dab441b6c4225ea8","ffffcca1dab441b6c42c7fb8253494","ffffccc7e9b47fcdbb41b6c42c7fb8253494","ffffccc7e9b47fcdbb41b6c41d91c0225ea80c2c84","ffffd9edf8b1c7e9b47fcdbb41b6c41d91c0225ea80c2c84","ffffd9edf8b1c7e9b47fcdbb41b6c41d91c0225ea8253494081d58").map(a),X=u(U),Z=new Array(3).concat("f7fcb9addd8e31a354","ffffccc2e69978c679238443","ffffccc2e69978c67931a354006837","ffffccd9f0a3addd8e78c67931a354006837","ffffccd9f0a3addd8e78c67941ab5d238443005a32","ffffe5f7fcb9d9f0a3addd8e78c67941ab5d238443005a32","ffffe5f7fcb9d9f0a3addd8e78c67941ab5d238443006837004529").map(a),$=u(Z),ff=new Array(3).concat("fff7bcfec44fd95f0e","ffffd4fed98efe9929cc4c02","ffffd4fed98efe9929d95f0e993404","ffffd4fee391fec44ffe9929d95f0e993404","ffffd4fee391fec44ffe9929ec7014cc4c028c2d04","ffffe5fff7bcfee391fec44ffe9929ec7014cc4c028c2d04","ffffe5fff7bcfee391fec44ffe9929ec7014cc4c02993404662506").map(a),ef=u(ff),df=new Array(3).concat("ffeda0feb24cf03b20","ffffb2fecc5cfd8d3ce31a1c","ffffb2fecc5cfd8d3cf03b20bd0026","ffffb2fed976feb24cfd8d3cf03b20bd0026","ffffb2fed976feb24cfd8d3cfc4e2ae31a1cb10026","ffffccffeda0fed976feb24cfd8d3cfc4e2ae31a1cb10026","ffffccffeda0fed976feb24cfd8d3cfc4e2ae31a1cbd0026800026").map(a),af=u(df),cf=new Array(3).concat("deebf79ecae13182bd","eff3ffbdd7e76baed62171b5","eff3ffbdd7e76baed63182bd08519c","eff3ffc6dbef9ecae16baed63182bd08519c","eff3ffc6dbef9ecae16baed64292c62171b5084594","f7fbffdeebf7c6dbef9ecae16baed64292c62171b5084594","f7fbffdeebf7c6dbef9ecae16baed64292c62171b508519c08306b").map(a),bf=u(cf),tf=new Array(3).concat("e5f5e0a1d99b31a354","edf8e9bae4b374c476238b45","edf8e9bae4b374c47631a354006d2c","edf8e9c7e9c0a1d99b74c47631a354006d2c","edf8e9c7e9c0a1d99b74c47641ab5d238b45005a32","f7fcf5e5f5e0c7e9c0a1d99b74c47641ab5d238b45005a32","f7fcf5e5f5e0c7e9c0a1d99b74c47641ab5d238b45006d2c00441b").map(a),nf=u(tf),rf=new Array(3).concat("f0f0f0bdbdbd636363","f7f7f7cccccc969696525252","f7f7f7cccccc969696636363252525","f7f7f7d9d9d9bdbdbd969696636363252525","f7f7f7d9d9d9bdbdbd969696737373525252252525","fffffff0f0f0d9d9d9bdbdbd969696737373525252252525","fffffff0f0f0d9d9d9bdbdbd969696737373525252252525000000").map(a),of=u(rf),lf=new Array(3).concat("efedf5bcbddc756bb1","f2f0f7cbc9e29e9ac86a51a3","f2f0f7cbc9e29e9ac8756bb154278f","f2f0f7dadaebbcbddc9e9ac8756bb154278f","f2f0f7dadaebbcbddc9e9ac8807dba6a51a34a1486","fcfbfdefedf5dadaebbcbddc9e9ac8807dba6a51a34a1486","fcfbfdefedf5dadaebbcbddc9e9ac8807dba6a51a354278f3f007d").map(a),hf=u(lf),mf=new Array(3).concat("fee0d2fc9272de2d26","fee5d9fcae91fb6a4acb181d","fee5d9fcae91fb6a4ade2d26a50f15","fee5d9fcbba1fc9272fb6a4ade2d26a50f15","fee5d9fcbba1fc9272fb6a4aef3b2ccb181d99000d","fff5f0fee0d2fcbba1fc9272fb6a4aef3b2ccb181d99000d","fff5f0fee0d2fcbba1fc9272fb6a4aef3b2ccb181da50f1567000d").map(a),pf=u(mf),uf=new Array(3).concat("fee6cefdae6be6550d","feeddefdbe85fd8d3cd94701","feeddefdbe85fd8d3ce6550da63603","feeddefdd0a2fdae6bfd8d3ce6550da63603","feeddefdd0a2fdae6bfd8d3cf16913d948018c2d04","fff5ebfee6cefdd0a2fdae6bfd8d3cf16913d948018c2d04","fff5ebfee6cefdd0a2fdae6bfd8d3cf16913d94801a636037f2704").map(a),sf=u(uf);var yf=e.interpolateCubehelixLong(d.cubehelix(300,.5,0),d.cubehelix(-240,.5,1)),Mf=e.interpolateCubehelixLong(d.cubehelix(-100,.75,.35),d.cubehelix(80,1.5,.8)),wf=e.interpolateCubehelixLong(d.cubehelix(260,.75,.35),d.cubehelix(80,1.5,.8)),Af=d.cubehelix();var Pf=d.rgb(),Bf=Math.PI/3,Gf=2*Math.PI/3;function xf(f){var e=f.length;return function(d){return f[Math.max(0,Math.min(e-1,Math.floor(d*e)))]}}var Rf=xf(a("44015444025645045745055946075a46085c460a5d460b5e470d60470e6147106347116447136548146748166848176948186a481a6c481b6d481c6e481d6f481f70482071482173482374482475482576482677482878482979472a7a472c7a472d7b472e7c472f7d46307e46327e46337f463480453581453781453882443983443a83443b84433d84433e85423f854240864241864142874144874045884046883f47883f48893e49893e4a893e4c8a3d4d8a3d4e8a3c4f8a3c508b3b518b3b528b3a538b3a548c39558c39568c38588c38598c375a8c375b8d365c8d365d8d355e8d355f8d34608d34618d33628d33638d32648e32658e31668e31678e31688e30698e306a8e2f6b8e2f6c8e2e6d8e2e6e8e2e6f8e2d708e2d718e2c718e2c728e2c738e2b748e2b758e2a768e2a778e2a788e29798e297a8e297b8e287c8e287d8e277e8e277f8e27808e26818e26828e26828e25838e25848e25858e24868e24878e23888e23898e238a8d228b8d228c8d228d8d218e8d218f8d21908d21918c20928c20928c20938c1f948c1f958b1f968b1f978b1f988b1f998a1f9a8a1e9b8a1e9c891e9d891f9e891f9f881fa0881fa1881fa1871fa28720a38620a48621a58521a68522a78522a88423a98324aa8325ab8225ac8226ad8127ad8128ae8029af7f2ab07f2cb17e2db27d2eb37c2fb47c31b57b32b67a34b67935b77937b87838b9773aba763bbb753dbc743fbc7340bd7242be7144bf7046c06f48c16e4ac16d4cc26c4ec36b50c46a52c56954c56856c66758c7655ac8645cc8635ec96260ca6063cb5f65cb5e67cc5c69cd5b6ccd5a6ece5870cf5773d05675d05477d1537ad1517cd2507fd34e81d34d84d44b86d54989d5488bd6468ed64590d74393d74195d84098d83e9bd93c9dd93ba0da39a2da37a5db36a8db34aadc32addc30b0dd2fb2dd2db5de2bb8de29bade28bddf26c0df25c2df23c5e021c8e020cae11fcde11dd0e11cd2e21bd5e21ad8e219dae319dde318dfe318e2e418e5e419e7e419eae51aece51befe51cf1e51df4e61ef6e620f8e621fbe723fde725")),gf=xf(a("00000401000501010601010802010902020b02020d03030f03031204041405041606051806051a07061c08071e0907200a08220b09240c09260d0a290e0b2b100b2d110c2f120d31130d34140e36150e38160f3b180f3d19103f1a10421c10441d11471e114920114b21114e22115024125325125527125829115a2a115c2c115f2d11612f116331116533106734106936106b38106c390f6e3b0f703d0f713f0f72400f74420f75440f764510774710784910784a10794c117a4e117b4f127b51127c52137c54137d56147d57157e59157e5a167e5c167f5d177f5f187f601880621980641a80651a80671b80681c816a1c816b1d816d1d816e1e81701f81721f817320817521817621817822817922827b23827c23827e24828025828125818326818426818627818827818928818b29818c29818e2a81902a81912b81932b80942c80962c80982d80992d809b2e7f9c2e7f9e2f7fa02f7fa1307ea3307ea5317ea6317da8327daa337dab337cad347cae347bb0357bb2357bb3367ab5367ab73779b83779ba3878bc3978bd3977bf3a77c03a76c23b75c43c75c53c74c73d73c83e73ca3e72cc3f71cd4071cf4070d0416fd2426fd3436ed5446dd6456cd8456cd9466bdb476adc4869de4968df4a68e04c67e24d66e34e65e44f64e55064e75263e85362e95462ea5661eb5760ec5860ed5a5fee5b5eef5d5ef05f5ef1605df2625df2645cf3655cf4675cf4695cf56b5cf66c5cf66e5cf7705cf7725cf8745cf8765cf9785df9795df97b5dfa7d5efa7f5efa815ffb835ffb8560fb8761fc8961fc8a62fc8c63fc8e64fc9065fd9266fd9467fd9668fd9869fd9a6afd9b6bfe9d6cfe9f6dfea16efea36ffea571fea772fea973feaa74feac76feae77feb078feb27afeb47bfeb67cfeb77efeb97ffebb81febd82febf84fec185fec287fec488fec68afec88cfeca8dfecc8ffecd90fecf92fed194fed395fed597fed799fed89afdda9cfddc9efddea0fde0a1fde2a3fde3a5fde5a7fde7a9fde9aafdebacfcecaefceeb0fcf0b2fcf2b4fcf4b6fcf6b8fcf7b9fcf9bbfcfbbdfcfdbf")),Yf=xf(a("00000401000501010601010802010a02020c02020e03021004031204031405041706041907051b08051d09061f0a07220b07240c08260d08290e092b10092d110a30120a32140b34150b37160b39180c3c190c3e1b0c411c0c431e0c451f0c48210c4a230c4c240c4f260c51280b53290b552b0b572d0b592f0a5b310a5c320a5e340a5f3609613809623909633b09643d09653e0966400a67420a68440a68450a69470b6a490b6a4a0c6b4c0c6b4d0d6c4f0d6c510e6c520e6d540f6d550f6d57106e59106e5a116e5c126e5d126e5f136e61136e62146e64156e65156e67166e69166e6a176e6c186e6d186e6f196e71196e721a6e741a6e751b6e771c6d781c6d7a1d6d7c1d6d7d1e6d7f1e6c801f6c82206c84206b85216b87216b88226a8a226a8c23698d23698f24699025689225689326679526679727669827669a28659b29649d29649f2a63a02a63a22b62a32c61a52c60a62d60a82e5fa92e5eab2f5ead305dae305cb0315bb1325ab3325ab43359b63458b73557b93556ba3655bc3754bd3853bf3952c03a51c13a50c33b4fc43c4ec63d4dc73e4cc83f4bca404acb4149cc4248ce4347cf4446d04545d24644d34743d44842d54a41d74b3fd84c3ed94d3dda4e3cdb503bdd513ade5238df5337e05536e15635e25734e35933e45a31e55c30e65d2fe75e2ee8602de9612bea632aeb6429eb6628ec6726ed6925ee6a24ef6c23ef6e21f06f20f1711ff1731df2741cf3761bf37819f47918f57b17f57d15f67e14f68013f78212f78410f8850ff8870ef8890cf98b0bf98c0af98e09fa9008fa9207fa9407fb9606fb9706fb9906fb9b06fb9d07fc9f07fca108fca309fca50afca60cfca80dfcaa0ffcac11fcae12fcb014fcb216fcb418fbb61afbb81dfbba1ffbbc21fbbe23fac026fac228fac42afac62df9c72ff9c932f9cb35f8cd37f8cf3af7d13df7d340f6d543f6d746f5d949f5db4cf4dd4ff4df53f4e156f3e35af3e55df2e661f2e865f2ea69f1ec6df1ed71f1ef75f1f179f2f27df2f482f3f586f3f68af4f88ef5f992f6fa96f8fb9af9fc9dfafda1fcffa4")),Of=xf(a("0d088710078813078916078a19068c1b068d1d068e20068f2206902406912605912805922a05932c05942e05952f059631059733059735049837049938049a3a049a3c049b3e049c3f049c41049d43039e44039e46039f48039f4903a04b03a14c02a14e02a25002a25102a35302a35502a45601a45801a45901a55b01a55c01a65e01a66001a66100a76300a76400a76600a76700a86900a86a00a86c00a86e00a86f00a87100a87201a87401a87501a87701a87801a87a02a87b02a87d03a87e03a88004a88104a78305a78405a78606a68707a68808a68a09a58b0aa58d0ba58e0ca48f0da4910ea3920fa39410a29511a19613a19814a099159f9a169f9c179e9d189d9e199da01a9ca11b9ba21d9aa31e9aa51f99a62098a72197a82296aa2395ab2494ac2694ad2793ae2892b02991b12a90b22b8fb32c8eb42e8db52f8cb6308bb7318ab83289ba3388bb3488bc3587bd3786be3885bf3984c03a83c13b82c23c81c33d80c43e7fc5407ec6417dc7427cc8437bc9447aca457acb4679cc4778cc4977cd4a76ce4b75cf4c74d04d73d14e72d24f71d35171d45270d5536fd5546ed6556dd7566cd8576bd9586ada5a6ada5b69db5c68dc5d67dd5e66de5f65de6164df6263e06363e16462e26561e26660e3685fe4695ee56a5de56b5de66c5ce76e5be76f5ae87059e97158e97257ea7457eb7556eb7655ec7754ed7953ed7a52ee7b51ef7c51ef7e50f07f4ff0804ef1814df1834cf2844bf3854bf3874af48849f48948f58b47f58c46f68d45f68f44f79044f79143f79342f89441f89540f9973ff9983ef99a3efa9b3dfa9c3cfa9e3bfb9f3afba139fba238fca338fca537fca636fca835fca934fdab33fdac33fdae32fdaf31fdb130fdb22ffdb42ffdb52efeb72dfeb82cfeba2cfebb2bfebd2afebe2afec029fdc229fdc328fdc527fdc627fdc827fdca26fdcb26fccd25fcce25fcd025fcd225fbd324fbd524fbd724fad824fada24f9dc24f9dd25f8df25f8e125f7e225f7e425f6e626f6e826f5e926f5eb27f4ed27f3ee27f3f027f2f227f1f426f1f525f0f724f0f921"));f.interpolateBlues=bf,f.interpolateBrBG=y,f.interpolateBuGn=j,f.interpolateBuPu=D,f.interpolateCividis=function(f){return f=Math.max(0,Math.min(1,f)),"rgb("+Math.max(0,Math.min(255,Math.round(-4.54-f*(35.34-f*(2381.73-f*(6402.7-f*(7024.72-2710.57*f)))))))+", "+Math.max(0,Math.min(255,Math.round(32.49+f*(170.73+f*(52.82-f*(131.46-f*(176.58-67.37*f)))))))+", "+Math.max(0,Math.min(255,Math.round(81.24+f*(442.36-f*(2482.43-f*(6167.24-f*(6614.94-2475.67*f)))))))+")"},f.interpolateCool=wf,f.interpolateCubehelixDefault=yf,f.interpolateGnBu=k,f.interpolateGreens=nf,f.interpolateGreys=of,f.interpolateInferno=Yf,f.interpolateMagma=gf,f.interpolateOrRd=W,f.interpolateOranges=sf,f.interpolatePRGn=w,f.interpolatePiYG=P,f.interpolatePlasma=Of,f.interpolatePuBu=H,f.interpolatePuBuGn=E,f.interpolatePuOr=G,f.interpolatePuRd=K,f.interpolatePurples=hf,f.interpolateRainbow=function(f){(f<0||f>1)&&(f-=Math.floor(f));var e=Math.abs(f-.5);return Af.h=360*f-100,Af.s=1.5-1.5*e,Af.l=.8-.9*e,Af+""},f.interpolateRdBu=R,f.interpolateRdGy=Y,f.interpolateRdPu=Q,f.interpolateRdYlBu=v,f.interpolateRdYlGn=S,f.interpolateReds=pf,f.interpolateSinebow=function(f){var e;return f=(.5-f)*Math.PI,Pf.r=255*(e=Math.sin(f))*e,Pf.g=255*(e=Math.sin(f+Bf))*e,Pf.b=255*(e=Math.sin(f+Gf))*e,Pf+""},f.interpolateSpectral=T,f.interpolateTurbo=function(f){return f=Math.max(0,Math.min(1,f)),"rgb("+Math.max(0,Math.min(255,Math.round(34.61+f*(1172.33-f*(10793.56-f*(33300.12-f*(38394.49-14825.05*f)))))))+", "+Math.max(0,Math.min(255,Math.round(23.31+f*(557.33+f*(1225.33-f*(3574.96-f*(1073.77+707.56*f)))))))+", "+Math.max(0,Math.min(255,Math.round(27.2+f*(3211.1-f*(15327.97-f*(27814-f*(22569.18-6838.66*f)))))))+")"},f.interpolateViridis=Rf,f.interpolateWarm=Mf,f.interpolateYlGn=$,f.interpolateYlGnBu=X,f.interpolateYlOrBr=ef,f.interpolateYlOrRd=af,f.schemeAccent=b,f.schemeBlues=cf,f.schemeBrBG=s,f.schemeBuGn=L,f.schemeBuPu=q,f.schemeCategory10=c,f.schemeDark2=t,f.schemeGnBu=_,f.schemeGreens=tf,f.schemeGreys=rf,f.schemeObservable10=n,f.schemeOrRd=V,f.schemeOranges=uf,f.schemePRGn=M,f.schemePaired=r,f.schemePastel1=o,f.schemePastel2=i,f.schemePiYG=A,f.schemePuBu=F,f.schemePuBuGn=z,f.schemePuOr=B,f.schemePuRd=J,f.schemePurples=lf,f.schemeRdBu=x,f.schemeRdGy=g,f.schemeRdPu=N,f.schemeRdYlBu=O,f.schemeRdYlGn=C,f.schemeReds=mf,f.schemeSet1=l,f.schemeSet2=h,f.schemeSet3=m,f.schemeSpectral=I,f.schemeTableau10=p,f.schemeYlGn=Z,f.schemeYlGnBu=U,f.schemeYlOrBr=ff,f.schemeYlOrRd=df,Object.defineProperty(f,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-scale-chromatic/package.json b/frontend/node_modules/d3-scale-chromatic/package.json new file mode 100644 index 0000000..f6e8da2 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/package.json @@ -0,0 +1,55 @@ +{ + "name": "d3-scale-chromatic", + "version": "3.1.0", + "description": "Sequential, diverging and categorical color schemes.", + "homepage": "https://d3js.org/d3-scale-chromatic/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-scale-chromatic.git" + }, + "keywords": [ + "d3", + "d3-module", + "color", + "scale", + "sequential", + "colorbrewer" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "https://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-scale-chromatic.min.js", + "unpkg": "dist/d3-scale-chromatic.min.js", + "exports": { + "umd": "./dist/d3-scale-chromatic.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "dependencies": { + "d3-color": "1 - 3", + "d3-interpolate": "1 - 3" + }, + "devDependencies": { + "eslint": "7", + "mocha": "8", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-scale-chromatic/src/categorical/Accent.js b/frontend/node_modules/d3-scale-chromatic/src/categorical/Accent.js new file mode 100644 index 0000000..3a1a9fd --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/categorical/Accent.js @@ -0,0 +1,3 @@ +import colors from "../colors.js"; + +export default colors("7fc97fbeaed4fdc086ffff99386cb0f0027fbf5b17666666"); diff --git a/frontend/node_modules/d3-scale-chromatic/src/categorical/Dark2.js b/frontend/node_modules/d3-scale-chromatic/src/categorical/Dark2.js new file mode 100644 index 0000000..1fe995d --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/categorical/Dark2.js @@ -0,0 +1,3 @@ +import colors from "../colors.js"; + +export default colors("1b9e77d95f027570b3e7298a66a61ee6ab02a6761d666666"); diff --git a/frontend/node_modules/d3-scale-chromatic/src/categorical/Paired.js b/frontend/node_modules/d3-scale-chromatic/src/categorical/Paired.js new file mode 100644 index 0000000..831fba3 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/categorical/Paired.js @@ -0,0 +1,3 @@ +import colors from "../colors.js"; + +export default colors("a6cee31f78b4b2df8a33a02cfb9a99e31a1cfdbf6fff7f00cab2d66a3d9affff99b15928"); diff --git a/frontend/node_modules/d3-scale-chromatic/src/categorical/Pastel1.js b/frontend/node_modules/d3-scale-chromatic/src/categorical/Pastel1.js new file mode 100644 index 0000000..d39c803 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/categorical/Pastel1.js @@ -0,0 +1,3 @@ +import colors from "../colors.js"; + +export default colors("fbb4aeb3cde3ccebc5decbe4fed9a6ffffcce5d8bdfddaecf2f2f2"); diff --git a/frontend/node_modules/d3-scale-chromatic/src/categorical/Pastel2.js b/frontend/node_modules/d3-scale-chromatic/src/categorical/Pastel2.js new file mode 100644 index 0000000..342e3ce --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/categorical/Pastel2.js @@ -0,0 +1,3 @@ +import colors from "../colors.js"; + +export default colors("b3e2cdfdcdaccbd5e8f4cae4e6f5c9fff2aef1e2cccccccc"); diff --git a/frontend/node_modules/d3-scale-chromatic/src/categorical/Set1.js b/frontend/node_modules/d3-scale-chromatic/src/categorical/Set1.js new file mode 100644 index 0000000..408887b --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/categorical/Set1.js @@ -0,0 +1,3 @@ +import colors from "../colors.js"; + +export default colors("e41a1c377eb84daf4a984ea3ff7f00ffff33a65628f781bf999999"); diff --git a/frontend/node_modules/d3-scale-chromatic/src/categorical/Set2.js b/frontend/node_modules/d3-scale-chromatic/src/categorical/Set2.js new file mode 100644 index 0000000..9aa8030 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/categorical/Set2.js @@ -0,0 +1,3 @@ +import colors from "../colors.js"; + +export default colors("66c2a5fc8d628da0cbe78ac3a6d854ffd92fe5c494b3b3b3"); diff --git a/frontend/node_modules/d3-scale-chromatic/src/categorical/Set3.js b/frontend/node_modules/d3-scale-chromatic/src/categorical/Set3.js new file mode 100644 index 0000000..d3b9b27 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/categorical/Set3.js @@ -0,0 +1,3 @@ +import colors from "../colors.js"; + +export default colors("8dd3c7ffffb3bebadafb807280b1d3fdb462b3de69fccde5d9d9d9bc80bdccebc5ffed6f"); diff --git a/frontend/node_modules/d3-scale-chromatic/src/categorical/Tableau10.js b/frontend/node_modules/d3-scale-chromatic/src/categorical/Tableau10.js new file mode 100644 index 0000000..370c950 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/categorical/Tableau10.js @@ -0,0 +1,3 @@ +import colors from "../colors.js"; + +export default colors("4e79a7f28e2ce1575976b7b259a14fedc949af7aa1ff9da79c755fbab0ab"); diff --git a/frontend/node_modules/d3-scale-chromatic/src/categorical/category10.js b/frontend/node_modules/d3-scale-chromatic/src/categorical/category10.js new file mode 100644 index 0000000..9adcd01 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/categorical/category10.js @@ -0,0 +1,3 @@ +import colors from "../colors.js"; + +export default colors("1f77b4ff7f0e2ca02cd627289467bd8c564be377c27f7f7fbcbd2217becf"); diff --git a/frontend/node_modules/d3-scale-chromatic/src/categorical/observable10.js b/frontend/node_modules/d3-scale-chromatic/src/categorical/observable10.js new file mode 100644 index 0000000..ada2815 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/categorical/observable10.js @@ -0,0 +1,3 @@ +import colors from "../colors.js"; + +export default colors("4269d0efb118ff725c6cc5b03ca951ff8ab7a463f297bbf59c6b4e9498a0"); diff --git a/frontend/node_modules/d3-scale-chromatic/src/colors.js b/frontend/node_modules/d3-scale-chromatic/src/colors.js new file mode 100644 index 0000000..aeedad5 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/colors.js @@ -0,0 +1,5 @@ +export default function(specifier) { + var n = specifier.length / 6 | 0, colors = new Array(n), i = 0; + while (i < n) colors[i] = "#" + specifier.slice(i * 6, ++i * 6); + return colors; +} diff --git a/frontend/node_modules/d3-scale-chromatic/src/diverging/BrBG.js b/frontend/node_modules/d3-scale-chromatic/src/diverging/BrBG.js new file mode 100644 index 0000000..6a467f7 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/diverging/BrBG.js @@ -0,0 +1,16 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "d8b365f5f5f55ab4ac", + "a6611adfc27d80cdc1018571", + "a6611adfc27df5f5f580cdc1018571", + "8c510ad8b365f6e8c3c7eae55ab4ac01665e", + "8c510ad8b365f6e8c3f5f5f5c7eae55ab4ac01665e", + "8c510abf812ddfc27df6e8c3c7eae580cdc135978f01665e", + "8c510abf812ddfc27df6e8c3f5f5f5c7eae580cdc135978f01665e", + "5430058c510abf812ddfc27df6e8c3c7eae580cdc135978f01665e003c30", + "5430058c510abf812ddfc27df6e8c3f5f5f5c7eae580cdc135978f01665e003c30" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/diverging/PRGn.js b/frontend/node_modules/d3-scale-chromatic/src/diverging/PRGn.js new file mode 100644 index 0000000..dd278aa --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/diverging/PRGn.js @@ -0,0 +1,16 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "af8dc3f7f7f77fbf7b", + "7b3294c2a5cfa6dba0008837", + "7b3294c2a5cff7f7f7a6dba0008837", + "762a83af8dc3e7d4e8d9f0d37fbf7b1b7837", + "762a83af8dc3e7d4e8f7f7f7d9f0d37fbf7b1b7837", + "762a839970abc2a5cfe7d4e8d9f0d3a6dba05aae611b7837", + "762a839970abc2a5cfe7d4e8f7f7f7d9f0d3a6dba05aae611b7837", + "40004b762a839970abc2a5cfe7d4e8d9f0d3a6dba05aae611b783700441b", + "40004b762a839970abc2a5cfe7d4e8f7f7f7d9f0d3a6dba05aae611b783700441b" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/diverging/PiYG.js b/frontend/node_modules/d3-scale-chromatic/src/diverging/PiYG.js new file mode 100644 index 0000000..43ef32d --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/diverging/PiYG.js @@ -0,0 +1,16 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "e9a3c9f7f7f7a1d76a", + "d01c8bf1b6dab8e1864dac26", + "d01c8bf1b6daf7f7f7b8e1864dac26", + "c51b7de9a3c9fde0efe6f5d0a1d76a4d9221", + "c51b7de9a3c9fde0eff7f7f7e6f5d0a1d76a4d9221", + "c51b7dde77aef1b6dafde0efe6f5d0b8e1867fbc414d9221", + "c51b7dde77aef1b6dafde0eff7f7f7e6f5d0b8e1867fbc414d9221", + "8e0152c51b7dde77aef1b6dafde0efe6f5d0b8e1867fbc414d9221276419", + "8e0152c51b7dde77aef1b6dafde0eff7f7f7e6f5d0b8e1867fbc414d9221276419" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/diverging/PuOr.js b/frontend/node_modules/d3-scale-chromatic/src/diverging/PuOr.js new file mode 100644 index 0000000..770ef90 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/diverging/PuOr.js @@ -0,0 +1,16 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "998ec3f7f7f7f1a340", + "5e3c99b2abd2fdb863e66101", + "5e3c99b2abd2f7f7f7fdb863e66101", + "542788998ec3d8daebfee0b6f1a340b35806", + "542788998ec3d8daebf7f7f7fee0b6f1a340b35806", + "5427888073acb2abd2d8daebfee0b6fdb863e08214b35806", + "5427888073acb2abd2d8daebf7f7f7fee0b6fdb863e08214b35806", + "2d004b5427888073acb2abd2d8daebfee0b6fdb863e08214b358067f3b08", + "2d004b5427888073acb2abd2d8daebf7f7f7fee0b6fdb863e08214b358067f3b08" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/diverging/RdBu.js b/frontend/node_modules/d3-scale-chromatic/src/diverging/RdBu.js new file mode 100644 index 0000000..703d61c --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/diverging/RdBu.js @@ -0,0 +1,16 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "ef8a62f7f7f767a9cf", + "ca0020f4a58292c5de0571b0", + "ca0020f4a582f7f7f792c5de0571b0", + "b2182bef8a62fddbc7d1e5f067a9cf2166ac", + "b2182bef8a62fddbc7f7f7f7d1e5f067a9cf2166ac", + "b2182bd6604df4a582fddbc7d1e5f092c5de4393c32166ac", + "b2182bd6604df4a582fddbc7f7f7f7d1e5f092c5de4393c32166ac", + "67001fb2182bd6604df4a582fddbc7d1e5f092c5de4393c32166ac053061", + "67001fb2182bd6604df4a582fddbc7f7f7f7d1e5f092c5de4393c32166ac053061" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/diverging/RdGy.js b/frontend/node_modules/d3-scale-chromatic/src/diverging/RdGy.js new file mode 100644 index 0000000..b4deb6a --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/diverging/RdGy.js @@ -0,0 +1,16 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "ef8a62ffffff999999", + "ca0020f4a582bababa404040", + "ca0020f4a582ffffffbababa404040", + "b2182bef8a62fddbc7e0e0e09999994d4d4d", + "b2182bef8a62fddbc7ffffffe0e0e09999994d4d4d", + "b2182bd6604df4a582fddbc7e0e0e0bababa8787874d4d4d", + "b2182bd6604df4a582fddbc7ffffffe0e0e0bababa8787874d4d4d", + "67001fb2182bd6604df4a582fddbc7e0e0e0bababa8787874d4d4d1a1a1a", + "67001fb2182bd6604df4a582fddbc7ffffffe0e0e0bababa8787874d4d4d1a1a1a" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/diverging/RdYlBu.js b/frontend/node_modules/d3-scale-chromatic/src/diverging/RdYlBu.js new file mode 100644 index 0000000..ad1a412 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/diverging/RdYlBu.js @@ -0,0 +1,16 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "fc8d59ffffbf91bfdb", + "d7191cfdae61abd9e92c7bb6", + "d7191cfdae61ffffbfabd9e92c7bb6", + "d73027fc8d59fee090e0f3f891bfdb4575b4", + "d73027fc8d59fee090ffffbfe0f3f891bfdb4575b4", + "d73027f46d43fdae61fee090e0f3f8abd9e974add14575b4", + "d73027f46d43fdae61fee090ffffbfe0f3f8abd9e974add14575b4", + "a50026d73027f46d43fdae61fee090e0f3f8abd9e974add14575b4313695", + "a50026d73027f46d43fdae61fee090ffffbfe0f3f8abd9e974add14575b4313695" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/diverging/RdYlGn.js b/frontend/node_modules/d3-scale-chromatic/src/diverging/RdYlGn.js new file mode 100644 index 0000000..3cd897e --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/diverging/RdYlGn.js @@ -0,0 +1,16 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "fc8d59ffffbf91cf60", + "d7191cfdae61a6d96a1a9641", + "d7191cfdae61ffffbfa6d96a1a9641", + "d73027fc8d59fee08bd9ef8b91cf601a9850", + "d73027fc8d59fee08bffffbfd9ef8b91cf601a9850", + "d73027f46d43fdae61fee08bd9ef8ba6d96a66bd631a9850", + "d73027f46d43fdae61fee08bffffbfd9ef8ba6d96a66bd631a9850", + "a50026d73027f46d43fdae61fee08bd9ef8ba6d96a66bd631a9850006837", + "a50026d73027f46d43fdae61fee08bffffbfd9ef8ba6d96a66bd631a9850006837" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/diverging/Spectral.js b/frontend/node_modules/d3-scale-chromatic/src/diverging/Spectral.js new file mode 100644 index 0000000..cd1e108 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/diverging/Spectral.js @@ -0,0 +1,16 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "fc8d59ffffbf99d594", + "d7191cfdae61abdda42b83ba", + "d7191cfdae61ffffbfabdda42b83ba", + "d53e4ffc8d59fee08be6f59899d5943288bd", + "d53e4ffc8d59fee08bffffbfe6f59899d5943288bd", + "d53e4ff46d43fdae61fee08be6f598abdda466c2a53288bd", + "d53e4ff46d43fdae61fee08bffffbfe6f598abdda466c2a53288bd", + "9e0142d53e4ff46d43fdae61fee08be6f598abdda466c2a53288bd5e4fa2", + "9e0142d53e4ff46d43fdae61fee08bffffbfe6f598abdda466c2a53288bd5e4fa2" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/index.js b/frontend/node_modules/d3-scale-chromatic/src/index.js new file mode 100644 index 0000000..65eb00d --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/index.js @@ -0,0 +1,44 @@ +export {default as schemeCategory10} from "./categorical/category10.js"; +export {default as schemeAccent} from "./categorical/Accent.js"; +export {default as schemeDark2} from "./categorical/Dark2.js"; +export {default as schemeObservable10} from "./categorical/observable10.js"; +export {default as schemePaired} from "./categorical/Paired.js"; +export {default as schemePastel1} from "./categorical/Pastel1.js"; +export {default as schemePastel2} from "./categorical/Pastel2.js"; +export {default as schemeSet1} from "./categorical/Set1.js"; +export {default as schemeSet2} from "./categorical/Set2.js"; +export {default as schemeSet3} from "./categorical/Set3.js"; +export {default as schemeTableau10} from "./categorical/Tableau10.js"; +export {default as interpolateBrBG, scheme as schemeBrBG} from "./diverging/BrBG.js"; +export {default as interpolatePRGn, scheme as schemePRGn} from "./diverging/PRGn.js"; +export {default as interpolatePiYG, scheme as schemePiYG} from "./diverging/PiYG.js"; +export {default as interpolatePuOr, scheme as schemePuOr} from "./diverging/PuOr.js"; +export {default as interpolateRdBu, scheme as schemeRdBu} from "./diverging/RdBu.js"; +export {default as interpolateRdGy, scheme as schemeRdGy} from "./diverging/RdGy.js"; +export {default as interpolateRdYlBu, scheme as schemeRdYlBu} from "./diverging/RdYlBu.js"; +export {default as interpolateRdYlGn, scheme as schemeRdYlGn} from "./diverging/RdYlGn.js"; +export {default as interpolateSpectral, scheme as schemeSpectral} from "./diverging/Spectral.js"; +export {default as interpolateBuGn, scheme as schemeBuGn} from "./sequential-multi/BuGn.js"; +export {default as interpolateBuPu, scheme as schemeBuPu} from "./sequential-multi/BuPu.js"; +export {default as interpolateGnBu, scheme as schemeGnBu} from "./sequential-multi/GnBu.js"; +export {default as interpolateOrRd, scheme as schemeOrRd} from "./sequential-multi/OrRd.js"; +export {default as interpolatePuBuGn, scheme as schemePuBuGn} from "./sequential-multi/PuBuGn.js"; +export {default as interpolatePuBu, scheme as schemePuBu} from "./sequential-multi/PuBu.js"; +export {default as interpolatePuRd, scheme as schemePuRd} from "./sequential-multi/PuRd.js"; +export {default as interpolateRdPu, scheme as schemeRdPu} from "./sequential-multi/RdPu.js"; +export {default as interpolateYlGnBu, scheme as schemeYlGnBu} from "./sequential-multi/YlGnBu.js"; +export {default as interpolateYlGn, scheme as schemeYlGn} from "./sequential-multi/YlGn.js"; +export {default as interpolateYlOrBr, scheme as schemeYlOrBr} from "./sequential-multi/YlOrBr.js"; +export {default as interpolateYlOrRd, scheme as schemeYlOrRd} from "./sequential-multi/YlOrRd.js"; +export {default as interpolateBlues, scheme as schemeBlues} from "./sequential-single/Blues.js"; +export {default as interpolateGreens, scheme as schemeGreens} from "./sequential-single/Greens.js"; +export {default as interpolateGreys, scheme as schemeGreys} from "./sequential-single/Greys.js"; +export {default as interpolatePurples, scheme as schemePurples} from "./sequential-single/Purples.js"; +export {default as interpolateReds, scheme as schemeReds} from "./sequential-single/Reds.js"; +export {default as interpolateOranges, scheme as schemeOranges} from "./sequential-single/Oranges.js"; +export {default as interpolateCividis} from "./sequential-multi/cividis.js"; +export {default as interpolateCubehelixDefault} from "./sequential-multi/cubehelix.js"; +export {default as interpolateRainbow, warm as interpolateWarm, cool as interpolateCool} from "./sequential-multi/rainbow.js"; +export {default as interpolateSinebow} from "./sequential-multi/sinebow.js"; +export {default as interpolateTurbo} from "./sequential-multi/turbo.js"; +export {default as interpolateViridis, magma as interpolateMagma, inferno as interpolateInferno, plasma as interpolatePlasma} from "./sequential-multi/viridis.js"; diff --git a/frontend/node_modules/d3-scale-chromatic/src/ramp.js b/frontend/node_modules/d3-scale-chromatic/src/ramp.js new file mode 100644 index 0000000..14f4050 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/ramp.js @@ -0,0 +1,3 @@ +import {interpolateRgbBasis} from "d3-interpolate"; + +export default scheme => interpolateRgbBasis(scheme[scheme.length - 1]); diff --git a/frontend/node_modules/d3-scale-chromatic/src/rampClosed.js b/frontend/node_modules/d3-scale-chromatic/src/rampClosed.js new file mode 100644 index 0000000..217d502 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/rampClosed.js @@ -0,0 +1,9 @@ +import {scaleSequential} from "d3-scale"; +import {interpolateRgbBasisClosed} from "d3-interpolate"; +import colors from "./colors.js"; + +export default function(range) { + var s = scaleSequential(interpolateRgbBasisClosed(colors(range))).clamp(true); + delete s.clamp; + return s; +} diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/BuGn.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/BuGn.js new file mode 100644 index 0000000..bfd4ff4 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/BuGn.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "e5f5f999d8c92ca25f", + "edf8fbb2e2e266c2a4238b45", + "edf8fbb2e2e266c2a42ca25f006d2c", + "edf8fbccece699d8c966c2a42ca25f006d2c", + "edf8fbccece699d8c966c2a441ae76238b45005824", + "f7fcfde5f5f9ccece699d8c966c2a441ae76238b45005824", + "f7fcfde5f5f9ccece699d8c966c2a441ae76238b45006d2c00441b" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/BuPu.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/BuPu.js new file mode 100644 index 0000000..7b6b7cc --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/BuPu.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "e0ecf49ebcda8856a7", + "edf8fbb3cde38c96c688419d", + "edf8fbb3cde38c96c68856a7810f7c", + "edf8fbbfd3e69ebcda8c96c68856a7810f7c", + "edf8fbbfd3e69ebcda8c96c68c6bb188419d6e016b", + "f7fcfde0ecf4bfd3e69ebcda8c96c68c6bb188419d6e016b", + "f7fcfde0ecf4bfd3e69ebcda8c96c68c6bb188419d810f7c4d004b" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/GnBu.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/GnBu.js new file mode 100644 index 0000000..0e1a31c --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/GnBu.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "e0f3dba8ddb543a2ca", + "f0f9e8bae4bc7bccc42b8cbe", + "f0f9e8bae4bc7bccc443a2ca0868ac", + "f0f9e8ccebc5a8ddb57bccc443a2ca0868ac", + "f0f9e8ccebc5a8ddb57bccc44eb3d32b8cbe08589e", + "f7fcf0e0f3dbccebc5a8ddb57bccc44eb3d32b8cbe08589e", + "f7fcf0e0f3dbccebc5a8ddb57bccc44eb3d32b8cbe0868ac084081" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/OrRd.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/OrRd.js new file mode 100644 index 0000000..6726f75 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/OrRd.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "fee8c8fdbb84e34a33", + "fef0d9fdcc8afc8d59d7301f", + "fef0d9fdcc8afc8d59e34a33b30000", + "fef0d9fdd49efdbb84fc8d59e34a33b30000", + "fef0d9fdd49efdbb84fc8d59ef6548d7301f990000", + "fff7ecfee8c8fdd49efdbb84fc8d59ef6548d7301f990000", + "fff7ecfee8c8fdd49efdbb84fc8d59ef6548d7301fb300007f0000" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/PuBu.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/PuBu.js new file mode 100644 index 0000000..4a63281 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/PuBu.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "ece7f2a6bddb2b8cbe", + "f1eef6bdc9e174a9cf0570b0", + "f1eef6bdc9e174a9cf2b8cbe045a8d", + "f1eef6d0d1e6a6bddb74a9cf2b8cbe045a8d", + "f1eef6d0d1e6a6bddb74a9cf3690c00570b0034e7b", + "fff7fbece7f2d0d1e6a6bddb74a9cf3690c00570b0034e7b", + "fff7fbece7f2d0d1e6a6bddb74a9cf3690c00570b0045a8d023858" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/PuBuGn.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/PuBuGn.js new file mode 100644 index 0000000..11a60d4 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/PuBuGn.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "ece2f0a6bddb1c9099", + "f6eff7bdc9e167a9cf02818a", + "f6eff7bdc9e167a9cf1c9099016c59", + "f6eff7d0d1e6a6bddb67a9cf1c9099016c59", + "f6eff7d0d1e6a6bddb67a9cf3690c002818a016450", + "fff7fbece2f0d0d1e6a6bddb67a9cf3690c002818a016450", + "fff7fbece2f0d0d1e6a6bddb67a9cf3690c002818a016c59014636" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/PuRd.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/PuRd.js new file mode 100644 index 0000000..2d9e143 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/PuRd.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "e7e1efc994c7dd1c77", + "f1eef6d7b5d8df65b0ce1256", + "f1eef6d7b5d8df65b0dd1c77980043", + "f1eef6d4b9dac994c7df65b0dd1c77980043", + "f1eef6d4b9dac994c7df65b0e7298ace125691003f", + "f7f4f9e7e1efd4b9dac994c7df65b0e7298ace125691003f", + "f7f4f9e7e1efd4b9dac994c7df65b0e7298ace125698004367001f" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/RdPu.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/RdPu.js new file mode 100644 index 0000000..680a5b1 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/RdPu.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "fde0ddfa9fb5c51b8a", + "feebe2fbb4b9f768a1ae017e", + "feebe2fbb4b9f768a1c51b8a7a0177", + "feebe2fcc5c0fa9fb5f768a1c51b8a7a0177", + "feebe2fcc5c0fa9fb5f768a1dd3497ae017e7a0177", + "fff7f3fde0ddfcc5c0fa9fb5f768a1dd3497ae017e7a0177", + "fff7f3fde0ddfcc5c0fa9fb5f768a1dd3497ae017e7a017749006a" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlGn.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlGn.js new file mode 100644 index 0000000..883ce59 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlGn.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "f7fcb9addd8e31a354", + "ffffccc2e69978c679238443", + "ffffccc2e69978c67931a354006837", + "ffffccd9f0a3addd8e78c67931a354006837", + "ffffccd9f0a3addd8e78c67941ab5d238443005a32", + "ffffe5f7fcb9d9f0a3addd8e78c67941ab5d238443005a32", + "ffffe5f7fcb9d9f0a3addd8e78c67941ab5d238443006837004529" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlGnBu.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlGnBu.js new file mode 100644 index 0000000..d002b3d --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlGnBu.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "edf8b17fcdbb2c7fb8", + "ffffcca1dab441b6c4225ea8", + "ffffcca1dab441b6c42c7fb8253494", + "ffffccc7e9b47fcdbb41b6c42c7fb8253494", + "ffffccc7e9b47fcdbb41b6c41d91c0225ea80c2c84", + "ffffd9edf8b1c7e9b47fcdbb41b6c41d91c0225ea80c2c84", + "ffffd9edf8b1c7e9b47fcdbb41b6c41d91c0225ea8253494081d58" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlOrBr.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlOrBr.js new file mode 100644 index 0000000..cb32c44 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlOrBr.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "fff7bcfec44fd95f0e", + "ffffd4fed98efe9929cc4c02", + "ffffd4fed98efe9929d95f0e993404", + "ffffd4fee391fec44ffe9929d95f0e993404", + "ffffd4fee391fec44ffe9929ec7014cc4c028c2d04", + "ffffe5fff7bcfee391fec44ffe9929ec7014cc4c028c2d04", + "ffffe5fff7bcfee391fec44ffe9929ec7014cc4c02993404662506" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlOrRd.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlOrRd.js new file mode 100644 index 0000000..6c314ba --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/YlOrRd.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "ffeda0feb24cf03b20", + "ffffb2fecc5cfd8d3ce31a1c", + "ffffb2fecc5cfd8d3cf03b20bd0026", + "ffffb2fed976feb24cfd8d3cf03b20bd0026", + "ffffb2fed976feb24cfd8d3cfc4e2ae31a1cb10026", + "ffffccffeda0fed976feb24cfd8d3cfc4e2ae31a1cb10026", + "ffffccffeda0fed976feb24cfd8d3cfc4e2ae31a1cbd0026800026" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/cividis.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/cividis.js new file mode 100644 index 0000000..46da9ab --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/cividis.js @@ -0,0 +1,8 @@ +export default function(t) { + t = Math.max(0, Math.min(1, t)); + return "rgb(" + + Math.max(0, Math.min(255, Math.round(-4.54 - t * (35.34 - t * (2381.73 - t * (6402.7 - t * (7024.72 - t * 2710.57))))))) + ", " + + Math.max(0, Math.min(255, Math.round(32.49 + t * (170.73 + t * (52.82 - t * (131.46 - t * (176.58 - t * 67.37))))))) + ", " + + Math.max(0, Math.min(255, Math.round(81.24 + t * (442.36 - t * (2482.43 - t * (6167.24 - t * (6614.94 - t * 2475.67))))))) + + ")"; +} diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/cubehelix.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/cubehelix.js new file mode 100644 index 0000000..7e9be12 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/cubehelix.js @@ -0,0 +1,4 @@ +import {cubehelix} from "d3-color"; +import {interpolateCubehelixLong} from "d3-interpolate"; + +export default interpolateCubehelixLong(cubehelix(300, 0.5, 0.0), cubehelix(-240, 0.5, 1.0)); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/rainbow.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/rainbow.js new file mode 100644 index 0000000..b33cd35 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/rainbow.js @@ -0,0 +1,17 @@ +import {cubehelix} from "d3-color"; +import {interpolateCubehelixLong} from "d3-interpolate"; + +export var warm = interpolateCubehelixLong(cubehelix(-100, 0.75, 0.35), cubehelix(80, 1.50, 0.8)); + +export var cool = interpolateCubehelixLong(cubehelix(260, 0.75, 0.35), cubehelix(80, 1.50, 0.8)); + +var c = cubehelix(); + +export default function(t) { + if (t < 0 || t > 1) t -= Math.floor(t); + var ts = Math.abs(t - 0.5); + c.h = 360 * t - 100; + c.s = 1.5 - 1.5 * ts; + c.l = 0.8 - 0.9 * ts; + return c + ""; +} diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/sinebow.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/sinebow.js new file mode 100644 index 0000000..09eb2de --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/sinebow.js @@ -0,0 +1,14 @@ +import {rgb} from "d3-color"; + +var c = rgb(), + pi_1_3 = Math.PI / 3, + pi_2_3 = Math.PI * 2 / 3; + +export default function(t) { + var x; + t = (0.5 - t) * Math.PI; + c.r = 255 * (x = Math.sin(t)) * x; + c.g = 255 * (x = Math.sin(t + pi_1_3)) * x; + c.b = 255 * (x = Math.sin(t + pi_2_3)) * x; + return c + ""; +} diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/turbo.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/turbo.js new file mode 100644 index 0000000..31ae8a4 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/turbo.js @@ -0,0 +1,8 @@ +export default function(t) { + t = Math.max(0, Math.min(1, t)); + return "rgb(" + + Math.max(0, Math.min(255, Math.round(34.61 + t * (1172.33 - t * (10793.56 - t * (33300.12 - t * (38394.49 - t * 14825.05))))))) + ", " + + Math.max(0, Math.min(255, Math.round(23.31 + t * (557.33 + t * (1225.33 - t * (3574.96 - t * (1073.77 + t * 707.56))))))) + ", " + + Math.max(0, Math.min(255, Math.round(27.2 + t * (3211.1 - t * (15327.97 - t * (27814 - t * (22569.18 - t * 6838.66))))))) + + ")"; +} diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/viridis.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/viridis.js new file mode 100644 index 0000000..2eeb758 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-multi/viridis.js @@ -0,0 +1,16 @@ +import colors from "../colors.js"; + +function ramp(range) { + var n = range.length; + return function(t) { + return range[Math.max(0, Math.min(n - 1, Math.floor(t * n)))]; + }; +} + +export default ramp(colors("44015444025645045745055946075a46085c460a5d460b5e470d60470e6147106347116447136548146748166848176948186a481a6c481b6d481c6e481d6f481f70482071482173482374482475482576482677482878482979472a7a472c7a472d7b472e7c472f7d46307e46327e46337f463480453581453781453882443983443a83443b84433d84433e85423f854240864241864142874144874045884046883f47883f48893e49893e4a893e4c8a3d4d8a3d4e8a3c4f8a3c508b3b518b3b528b3a538b3a548c39558c39568c38588c38598c375a8c375b8d365c8d365d8d355e8d355f8d34608d34618d33628d33638d32648e32658e31668e31678e31688e30698e306a8e2f6b8e2f6c8e2e6d8e2e6e8e2e6f8e2d708e2d718e2c718e2c728e2c738e2b748e2b758e2a768e2a778e2a788e29798e297a8e297b8e287c8e287d8e277e8e277f8e27808e26818e26828e26828e25838e25848e25858e24868e24878e23888e23898e238a8d228b8d228c8d228d8d218e8d218f8d21908d21918c20928c20928c20938c1f948c1f958b1f968b1f978b1f988b1f998a1f9a8a1e9b8a1e9c891e9d891f9e891f9f881fa0881fa1881fa1871fa28720a38620a48621a58521a68522a78522a88423a98324aa8325ab8225ac8226ad8127ad8128ae8029af7f2ab07f2cb17e2db27d2eb37c2fb47c31b57b32b67a34b67935b77937b87838b9773aba763bbb753dbc743fbc7340bd7242be7144bf7046c06f48c16e4ac16d4cc26c4ec36b50c46a52c56954c56856c66758c7655ac8645cc8635ec96260ca6063cb5f65cb5e67cc5c69cd5b6ccd5a6ece5870cf5773d05675d05477d1537ad1517cd2507fd34e81d34d84d44b86d54989d5488bd6468ed64590d74393d74195d84098d83e9bd93c9dd93ba0da39a2da37a5db36a8db34aadc32addc30b0dd2fb2dd2db5de2bb8de29bade28bddf26c0df25c2df23c5e021c8e020cae11fcde11dd0e11cd2e21bd5e21ad8e219dae319dde318dfe318e2e418e5e419e7e419eae51aece51befe51cf1e51df4e61ef6e620f8e621fbe723fde725")); + +export var magma = ramp(colors("00000401000501010601010802010902020b02020d03030f03031204041405041606051806051a07061c08071e0907200a08220b09240c09260d0a290e0b2b100b2d110c2f120d31130d34140e36150e38160f3b180f3d19103f1a10421c10441d11471e114920114b21114e22115024125325125527125829115a2a115c2c115f2d11612f116331116533106734106936106b38106c390f6e3b0f703d0f713f0f72400f74420f75440f764510774710784910784a10794c117a4e117b4f127b51127c52137c54137d56147d57157e59157e5a167e5c167f5d177f5f187f601880621980641a80651a80671b80681c816a1c816b1d816d1d816e1e81701f81721f817320817521817621817822817922827b23827c23827e24828025828125818326818426818627818827818928818b29818c29818e2a81902a81912b81932b80942c80962c80982d80992d809b2e7f9c2e7f9e2f7fa02f7fa1307ea3307ea5317ea6317da8327daa337dab337cad347cae347bb0357bb2357bb3367ab5367ab73779b83779ba3878bc3978bd3977bf3a77c03a76c23b75c43c75c53c74c73d73c83e73ca3e72cc3f71cd4071cf4070d0416fd2426fd3436ed5446dd6456cd8456cd9466bdb476adc4869de4968df4a68e04c67e24d66e34e65e44f64e55064e75263e85362e95462ea5661eb5760ec5860ed5a5fee5b5eef5d5ef05f5ef1605df2625df2645cf3655cf4675cf4695cf56b5cf66c5cf66e5cf7705cf7725cf8745cf8765cf9785df9795df97b5dfa7d5efa7f5efa815ffb835ffb8560fb8761fc8961fc8a62fc8c63fc8e64fc9065fd9266fd9467fd9668fd9869fd9a6afd9b6bfe9d6cfe9f6dfea16efea36ffea571fea772fea973feaa74feac76feae77feb078feb27afeb47bfeb67cfeb77efeb97ffebb81febd82febf84fec185fec287fec488fec68afec88cfeca8dfecc8ffecd90fecf92fed194fed395fed597fed799fed89afdda9cfddc9efddea0fde0a1fde2a3fde3a5fde5a7fde7a9fde9aafdebacfcecaefceeb0fcf0b2fcf2b4fcf4b6fcf6b8fcf7b9fcf9bbfcfbbdfcfdbf")); + +export var inferno = ramp(colors("00000401000501010601010802010a02020c02020e03021004031204031405041706041907051b08051d09061f0a07220b07240c08260d08290e092b10092d110a30120a32140b34150b37160b39180c3c190c3e1b0c411c0c431e0c451f0c48210c4a230c4c240c4f260c51280b53290b552b0b572d0b592f0a5b310a5c320a5e340a5f3609613809623909633b09643d09653e0966400a67420a68440a68450a69470b6a490b6a4a0c6b4c0c6b4d0d6c4f0d6c510e6c520e6d540f6d550f6d57106e59106e5a116e5c126e5d126e5f136e61136e62146e64156e65156e67166e69166e6a176e6c186e6d186e6f196e71196e721a6e741a6e751b6e771c6d781c6d7a1d6d7c1d6d7d1e6d7f1e6c801f6c82206c84206b85216b87216b88226a8a226a8c23698d23698f24699025689225689326679526679727669827669a28659b29649d29649f2a63a02a63a22b62a32c61a52c60a62d60a82e5fa92e5eab2f5ead305dae305cb0315bb1325ab3325ab43359b63458b73557b93556ba3655bc3754bd3853bf3952c03a51c13a50c33b4fc43c4ec63d4dc73e4cc83f4bca404acb4149cc4248ce4347cf4446d04545d24644d34743d44842d54a41d74b3fd84c3ed94d3dda4e3cdb503bdd513ade5238df5337e05536e15635e25734e35933e45a31e55c30e65d2fe75e2ee8602de9612bea632aeb6429eb6628ec6726ed6925ee6a24ef6c23ef6e21f06f20f1711ff1731df2741cf3761bf37819f47918f57b17f57d15f67e14f68013f78212f78410f8850ff8870ef8890cf98b0bf98c0af98e09fa9008fa9207fa9407fb9606fb9706fb9906fb9b06fb9d07fc9f07fca108fca309fca50afca60cfca80dfcaa0ffcac11fcae12fcb014fcb216fcb418fbb61afbb81dfbba1ffbbc21fbbe23fac026fac228fac42afac62df9c72ff9c932f9cb35f8cd37f8cf3af7d13df7d340f6d543f6d746f5d949f5db4cf4dd4ff4df53f4e156f3e35af3e55df2e661f2e865f2ea69f1ec6df1ed71f1ef75f1f179f2f27df2f482f3f586f3f68af4f88ef5f992f6fa96f8fb9af9fc9dfafda1fcffa4")); + +export var plasma = ramp(colors("0d088710078813078916078a19068c1b068d1d068e20068f2206902406912605912805922a05932c05942e05952f059631059733059735049837049938049a3a049a3c049b3e049c3f049c41049d43039e44039e46039f48039f4903a04b03a14c02a14e02a25002a25102a35302a35502a45601a45801a45901a55b01a55c01a65e01a66001a66100a76300a76400a76600a76700a86900a86a00a86c00a86e00a86f00a87100a87201a87401a87501a87701a87801a87a02a87b02a87d03a87e03a88004a88104a78305a78405a78606a68707a68808a68a09a58b0aa58d0ba58e0ca48f0da4910ea3920fa39410a29511a19613a19814a099159f9a169f9c179e9d189d9e199da01a9ca11b9ba21d9aa31e9aa51f99a62098a72197a82296aa2395ab2494ac2694ad2793ae2892b02991b12a90b22b8fb32c8eb42e8db52f8cb6308bb7318ab83289ba3388bb3488bc3587bd3786be3885bf3984c03a83c13b82c23c81c33d80c43e7fc5407ec6417dc7427cc8437bc9447aca457acb4679cc4778cc4977cd4a76ce4b75cf4c74d04d73d14e72d24f71d35171d45270d5536fd5546ed6556dd7566cd8576bd9586ada5a6ada5b69db5c68dc5d67dd5e66de5f65de6164df6263e06363e16462e26561e26660e3685fe4695ee56a5de56b5de66c5ce76e5be76f5ae87059e97158e97257ea7457eb7556eb7655ec7754ed7953ed7a52ee7b51ef7c51ef7e50f07f4ff0804ef1814df1834cf2844bf3854bf3874af48849f48948f58b47f58c46f68d45f68f44f79044f79143f79342f89441f89540f9973ff9983ef99a3efa9b3dfa9c3cfa9e3bfb9f3afba139fba238fca338fca537fca636fca835fca934fdab33fdac33fdae32fdaf31fdb130fdb22ffdb42ffdb52efeb72dfeb82cfeba2cfebb2bfebd2afebe2afec029fdc229fdc328fdc527fdc627fdc827fdca26fdcb26fccd25fcce25fcd025fcd225fbd324fbd524fbd724fad824fada24f9dc24f9dd25f8df25f8e125f7e225f7e425f6e626f6e826f5e926f5eb27f4ed27f3ee27f3f027f2f227f1f426f1f525f0f724f0f921")); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Blues.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Blues.js new file mode 100644 index 0000000..7acfdd3 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Blues.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "deebf79ecae13182bd", + "eff3ffbdd7e76baed62171b5", + "eff3ffbdd7e76baed63182bd08519c", + "eff3ffc6dbef9ecae16baed63182bd08519c", + "eff3ffc6dbef9ecae16baed64292c62171b5084594", + "f7fbffdeebf7c6dbef9ecae16baed64292c62171b5084594", + "f7fbffdeebf7c6dbef9ecae16baed64292c62171b508519c08306b" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Greens.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Greens.js new file mode 100644 index 0000000..48eb102 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Greens.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "e5f5e0a1d99b31a354", + "edf8e9bae4b374c476238b45", + "edf8e9bae4b374c47631a354006d2c", + "edf8e9c7e9c0a1d99b74c47631a354006d2c", + "edf8e9c7e9c0a1d99b74c47641ab5d238b45005a32", + "f7fcf5e5f5e0c7e9c0a1d99b74c47641ab5d238b45005a32", + "f7fcf5e5f5e0c7e9c0a1d99b74c47641ab5d238b45006d2c00441b" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Greys.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Greys.js new file mode 100644 index 0000000..315ca0a --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Greys.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "f0f0f0bdbdbd636363", + "f7f7f7cccccc969696525252", + "f7f7f7cccccc969696636363252525", + "f7f7f7d9d9d9bdbdbd969696636363252525", + "f7f7f7d9d9d9bdbdbd969696737373525252252525", + "fffffff0f0f0d9d9d9bdbdbd969696737373525252252525", + "fffffff0f0f0d9d9d9bdbdbd969696737373525252252525000000" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Oranges.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Oranges.js new file mode 100644 index 0000000..392bf23 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Oranges.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "fee6cefdae6be6550d", + "feeddefdbe85fd8d3cd94701", + "feeddefdbe85fd8d3ce6550da63603", + "feeddefdd0a2fdae6bfd8d3ce6550da63603", + "feeddefdd0a2fdae6bfd8d3cf16913d948018c2d04", + "fff5ebfee6cefdd0a2fdae6bfd8d3cf16913d948018c2d04", + "fff5ebfee6cefdd0a2fdae6bfd8d3cf16913d94801a636037f2704" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Purples.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Purples.js new file mode 100644 index 0000000..f4b22a5 --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Purples.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "efedf5bcbddc756bb1", + "f2f0f7cbc9e29e9ac86a51a3", + "f2f0f7cbc9e29e9ac8756bb154278f", + "f2f0f7dadaebbcbddc9e9ac8756bb154278f", + "f2f0f7dadaebbcbddc9e9ac8807dba6a51a34a1486", + "fcfbfdefedf5dadaebbcbddc9e9ac8807dba6a51a34a1486", + "fcfbfdefedf5dadaebbcbddc9e9ac8807dba6a51a354278f3f007d" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Reds.js b/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Reds.js new file mode 100644 index 0000000..35a048f --- /dev/null +++ b/frontend/node_modules/d3-scale-chromatic/src/sequential-single/Reds.js @@ -0,0 +1,14 @@ +import colors from "../colors.js"; +import ramp from "../ramp.js"; + +export var scheme = new Array(3).concat( + "fee0d2fc9272de2d26", + "fee5d9fcae91fb6a4acb181d", + "fee5d9fcae91fb6a4ade2d26a50f15", + "fee5d9fcbba1fc9272fb6a4ade2d26a50f15", + "fee5d9fcbba1fc9272fb6a4aef3b2ccb181d99000d", + "fff5f0fee0d2fcbba1fc9272fb6a4aef3b2ccb181d99000d", + "fff5f0fee0d2fcbba1fc9272fb6a4aef3b2ccb181da50f1567000d" +).map(colors); + +export default ramp(scheme); diff --git a/frontend/node_modules/d3-scale/LICENSE b/frontend/node_modules/d3-scale/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-scale/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-scale/README.md b/frontend/node_modules/d3-scale/README.md new file mode 100644 index 0000000..9024eaf --- /dev/null +++ b/frontend/node_modules/d3-scale/README.md @@ -0,0 +1,1003 @@ +# d3-scale + +Scales are a convenient abstraction for a fundamental task in visualization: mapping a dimension of abstract data to a visual representation. Although most often used for position-encoding quantitative data, such as mapping a measurement in meters to a position in pixels for dots in a scatterplot, scales can represent virtually any visual encoding, such as diverging colors, stroke widths, or symbol size. Scales can also be used with virtually any type of data, such as named categorical data or discrete data that requires sensible breaks. + +For [continuous](#continuous-scales) quantitative data, you typically want a [linear scale](#linear-scales). (For time series data, a [time scale](#time-scales).) If the distribution calls for it, consider transforming data using a [power](#power-scales) or [log](#log-scales) scale. A [quantize scale](#quantize-scales) may aid differentiation by rounding continuous data to a fixed set of discrete values; similarly, a [quantile scale](#quantile-scales) computes quantiles from a sample population, and a [threshold scale](#threshold-scales) allows you to specify arbitrary breaks in continuous data. + +For discrete ordinal (ordered) or categorical (unordered) data, an [ordinal scale](#ordinal-scales) specifies an explicit mapping from a set of data values to a corresponding set of visual attributes (such as colors). The related [band](#band-scales) and [point](#point-scales) scales are useful for position-encoding ordinal data, such as bars in a bar chart or dots in an categorical scatterplot. + +This repository does not provide color schemes; see [d3-scale-chromatic](https://github.com/d3/d3-scale-chromatic) for color schemes designed to work with d3-scale. + +Scales have no intrinsic visual representation. However, most scales can [generate](#continuous_ticks) and [format](#continuous_tickFormat) ticks for reference marks to aid in the construction of axes. + +For a longer introduction, see these recommended tutorials: + +* [Introducing d3-scale](https://medium.com/@mbostock/introducing-d3-scale-61980c51545f) by Mike Bostock + +* Chapter 7. Scales of [*Interactive Data Visualization for the Web*](http://alignedleft.com/work/d3-book) by Scott Murray + +* [d3: scales, and color.](https://jckr.github.io/blog/2011/08/11/d3-scales-and-color/) by Jérôme Cukier + +## Installing + +If you use npm, `npm install d3-scale`. You can also download the [latest release on GitHub](https://github.com/d3/d3-scale/releases/latest). For vanilla HTML in modern browsers, import d3-scale from Skypack: + +```html + +``` + +For legacy environments, you can load d3-scale’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + + + + + + + +``` + +(You can omit d3-time and d3-time-format if you’re not using [d3.scaleTime](#scaleTime) or [d3.scaleUtc](#scaleUtc).) + +## API Reference + +* [Continuous](#continuous-scales) ([Linear](#linear-scales), [Power](#power-scales), [Log](#log-scales), [Identity](#identity-scales), [Time](#time-scales), [Radial](#radial-scales)) +* [Sequential](#sequential-scales) +* [Diverging](#diverging-scales) +* [Quantize](#quantize-scales) +* [Quantile](#quantile-scales) +* [Threshold](#threshold-scales) +* [Ordinal](#ordinal-scales) ([Band](#band-scales), [Point](#point-scales)) + +### Continuous Scales + +Continuous scales map a continuous, quantitative input [domain](#continuous_domain) to a continuous output [range](#continuous_range). If the range is also numeric, the mapping may be [inverted](#continuous_invert). A continuous scale is not constructed directly; instead, try a [linear](#linear-scales), [power](#power-scales), [log](#log-scales), [identity](#identity-scales), [radial](#radial-scales), [time](#time-scales) or [sequential color](#sequential-scales) scale. + +# continuous(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/continuous.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +Given a *value* from the [domain](#continuous_domain), returns the corresponding value from the [range](#continuous_range). If the given *value* is outside the domain, and [clamping](#continuous_clamp) is not enabled, the mapping may be extrapolated such that the returned value is outside the range. For example, to apply a position encoding: + +```js +var x = d3.scaleLinear() + .domain([10, 130]) + .range([0, 960]); + +x(20); // 80 +x(50); // 320 +``` + +Or to apply a color encoding: + +```js +var color = d3.scaleLinear() + .domain([10, 100]) + .range(["brown", "steelblue"]); + +color(20); // "#9a3439" +color(50); // "#7b5167" +``` + +Or, in shorthand: + +```js +var x = d3.scaleLinear([10, 130], [0, 960]); +var color = d3.scaleLinear([10, 100], ["brown", "steelblue"]); +``` + +# continuous.invert(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/continuous.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +Given a *value* from the [range](#continuous_range), returns the corresponding value from the [domain](#continuous_domain). Inversion is useful for interaction, say to determine the data value corresponding to the position of the mouse. For example, to invert a position encoding: + +```js +var x = d3.scaleLinear() + .domain([10, 130]) + .range([0, 960]); + +x.invert(80); // 20 +x.invert(320); // 50 +``` + +If the given *value* is outside the range, and [clamping](#continuous_clamp) is not enabled, the mapping may be extrapolated such that the returned value is outside the domain. This method is only supported if the range is numeric. If the range is not numeric, returns NaN. + +For a valid value *y* in the range, continuous(continuous.invert(y)) approximately equals *y*; similarly, for a valid value *x* in the domain, continuous.invert(continuous(x)) approximately equals *x*. The scale and its inverse may not be exact due to the limitations of floating point precision. + +# continuous.domain([domain]) · [Source](https://github.com/d3/d3-scale/blob/master/src/continuous.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +If *domain* is specified, sets the scale’s domain to the specified array of numbers. The array must contain two or more elements. If the elements in the given array are not numbers, they will be coerced to numbers. If *domain* is not specified, returns a copy of the scale’s current domain. + +Although continuous scales typically have two values each in their domain and range, specifying more than two values produces a piecewise scale. For example, to create a [diverging color scale](#diverging-scales) that interpolates between white and red for negative values, and white and green for positive values, say: + +```js +var color = d3.scaleLinear() + .domain([-1, 0, 1]) + .range(["red", "white", "green"]); + +color(-0.5); // "rgb(255, 128, 128)" +color(+0.5); // "rgb(128, 192, 128)" +``` + +Internally, a piecewise scale performs a [binary search](https://github.com/d3/d3-array/blob/master/README.md#bisect) for the range interpolator corresponding to the given domain value. Thus, the domain must be in ascending or descending order. If the domain and range have different lengths *N* and *M*, only the first *min(N,M)* elements in each are observed. + +# continuous.range([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/continuous.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +If *range* is specified, sets the scale’s range to the specified array of values. The array must contain two or more elements. Unlike the [domain](#continuous_domain), elements in the given array need not be numbers; any value that is supported by the underlying [interpolator](#continuous_interpolate) will work, though note that numeric ranges are required for [invert](#continuous_invert). If *range* is not specified, returns a copy of the scale’s current range. See [*continuous*.interpolate](#continuous_interpolate) for more examples. + +# continuous.rangeRound([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/continuous.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +Sets the scale’s [*range*](#continuous_range) to the specified array of values while also setting the scale’s [interpolator](#continuous_interpolate) to [interpolateRound](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolateRound). This is a convenience method equivalent to: + +```js +continuous + .range(range) + .interpolate(d3.interpolateRound); +``` + +The rounding interpolator is sometimes useful for avoiding antialiasing artifacts, though also consider the [shape-rendering](https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/shape-rendering) “crispEdges” styles. Note that this interpolator can only be used with numeric ranges. + +# continuous.clamp(clamp) · [Source](https://github.com/d3/d3-scale/blob/master/src/continuous.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +If *clamp* is specified, enables or disables clamping accordingly. If clamping is disabled and the scale is passed a value outside the [domain](#continuous_domain), the scale may return a value outside the [range](#continuous_range) through extrapolation. If clamping is enabled, the return value of the scale is always within the scale’s range. Clamping similarly applies to [*continuous*.invert](#continuous_invert). For example: + +```js +var x = d3.scaleLinear() + .domain([10, 130]) + .range([0, 960]); + +x(-10); // -160, outside range +x.invert(-160); // -10, outside domain + +x.clamp(true); +x(-10); // 0, clamped to range +x.invert(-160); // 10, clamped to domain +``` + +If *clamp* is not specified, returns whether or not the scale currently clamps values to within the range. + +# continuous.unknown([value]) · [Source](https://github.com/d3/d3-scale/blob/master/src/continuous.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +If *value* is specified, sets the output value of the scale for undefined (or NaN) input values and returns this scale. If *value* is not specified, returns the current unknown value, which defaults to undefined. + +# continuous.interpolate(interpolate) · [Source](https://github.com/d3/d3-scale/blob/master/src/continuous.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +If *interpolate* is specified, sets the scale’s [range](#continuous_range) interpolator factory. This interpolator factory is used to create interpolators for each adjacent pair of values from the range; these interpolators then map a normalized domain parameter *t* in [0, 1] to the corresponding value in the range. If *factory* is not specified, returns the scale’s current interpolator factory, which defaults to [d3.interpolate](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolate). See [d3-interpolate](https://github.com/d3/d3-interpolate) for more interpolators. + +For example, consider a diverging color scale with three colors in the range: + +```js +var color = d3.scaleLinear() + .domain([-100, 0, +100]) + .range(["red", "white", "green"]); +``` + +Two interpolators are created internally by the scale, equivalent to: + +```js +var i0 = d3.interpolate("red", "white"), + i1 = d3.interpolate("white", "green"); +``` + +A common reason to specify a custom interpolator is to change the color space of interpolation. For example, to use [HCL](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolateHcl): + +```js +var color = d3.scaleLinear() + .domain([10, 100]) + .range(["brown", "steelblue"]) + .interpolate(d3.interpolateHcl); +``` + +Or for [Cubehelix](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolateCubehelix) with a custom gamma: + +```js +var color = d3.scaleLinear() + .domain([10, 100]) + .range(["brown", "steelblue"]) + .interpolate(d3.interpolateCubehelix.gamma(3)); +``` + +Note: the [default interpolator](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolate) **may reuse return values**. For example, if the range values are objects, then the value interpolator always returns the same object, modifying it in-place. If the scale is used to set an attribute or style, this is typically acceptable (and desirable for performance); however, if you need to store the scale’s return value, you must specify your own interpolator or make a copy as appropriate. + +# continuous.ticks([count]) + +Returns approximately *count* representative values from the scale’s [domain](#continuous_domain). If *count* is not specified, it defaults to 10. The returned tick values are uniformly spaced, have human-readable values (such as multiples of powers of 10), and are guaranteed to be within the extent of the domain. Ticks are often used to display reference lines, or tick marks, in conjunction with the visualized data. The specified *count* is only a hint; the scale may return more or fewer values depending on the domain. See also d3-array’s [ticks](https://github.com/d3/d3-array/blob/master/README.md#ticks). + +# continuous.tickFormat([count[, specifier]]) · [Source](https://github.com/d3/d3-scale/blob/master/src/tickFormat.js), [Examples](https://observablehq.com/@d3/scale-ticks) + +Returns a [number format](https://github.com/d3/d3-format) function suitable for displaying a tick value, automatically computing the appropriate precision based on the fixed interval between tick values. The specified *count* should have the same value as the count that is used to generate the [tick values](#continuous_ticks). + +An optional *specifier* allows a [custom format](https://github.com/d3/d3-format/blob/master/README.md#locale_format) where the precision of the format is automatically set by the scale as appropriate for the tick interval. For example, to format percentage change, you might say: + +```js +var x = d3.scaleLinear() + .domain([-1, 1]) + .range([0, 960]); + +var ticks = x.ticks(5), + tickFormat = x.tickFormat(5, "+%"); + +ticks.map(tickFormat); // ["-100%", "-50%", "+0%", "+50%", "+100%"] +``` + +If *specifier* uses the format type `s`, the scale will return a [SI-prefix format](https://github.com/d3/d3-format/blob/master/README.md#locale_formatPrefix) based on the largest value in the domain. If the *specifier* already specifies a precision, this method is equivalent to [*locale*.format](https://github.com/d3/d3-format/blob/master/README.md#locale_format). + +See also [d3.tickFormat](#tickFormat). + +# continuous.nice([count]) · [Source](https://github.com/d3/d3-scale/blob/master/src/nice.js), [Examples](https://observablehq.com/@d3/d3-scalelinear) + +Extends the [domain](#continuous_domain) so that it starts and ends on nice round values. This method typically modifies the scale’s domain, and may only extend the bounds to the nearest round value. An optional tick *count* argument allows greater control over the step size used to extend the bounds, guaranteeing that the returned [ticks](#continuous_ticks) will exactly cover the domain. Nicing is useful if the domain is computed from data, say using [extent](https://github.com/d3/d3-array/blob/master/README.md#extent), and may be irregular. For example, for a domain of [0.201479…, 0.996679…], a nice domain might be [0.2, 1.0]. If the domain has more than two values, nicing the domain only affects the first and last value. See also d3-array’s [tickStep](https://github.com/d3/d3-array/blob/master/README.md#tickStep). + +Nicing a scale only modifies the current domain; it does not automatically nice domains that are subsequently set using [*continuous*.domain](#continuous_domain). You must re-nice the scale after setting the new domain, if desired. + +# continuous.copy() · [Source](https://github.com/d3/d3-scale/blob/master/src/continuous.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +Returns an exact copy of this scale. Changes to this scale will not affect the returned scale, and vice versa. + +# d3.tickFormat(start, stop, count[, specifier]) · [Source](https://github.com/d3/d3-scale/blob/master/src/tickFormat.js), [Examples](https://observablehq.com/@d3/scale-ticks) + +Returns a [number format](https://github.com/d3/d3-format) function suitable for displaying a tick value, automatically computing the appropriate precision based on the fixed interval between tick values, as determined by [d3.tickStep](https://github.com/d3/d3-array/blob/master/README.md#tickStep). + +An optional *specifier* allows a [custom format](https://github.com/d3/d3-format/blob/master/README.md#locale_format) where the precision of the format is automatically set by the scale as appropriate for the tick interval. For example, to format percentage change, you might say: + +```js +var tickFormat = d3.tickFormat(-1, 1, 5, "+%"); + +tickFormat(-0.5); // "-50%" +``` + +If *specifier* uses the format type `s`, the scale will return a [SI-prefix format](https://github.com/d3/d3-format/blob/master/README.md#locale_formatPrefix) based on the larger absolute value of *start* and *stop*. If the *specifier* already specifies a precision, this method is equivalent to [*locale*.format](https://github.com/d3/d3-format/blob/master/README.md#locale_format). + +#### Linear Scales + +# d3.scaleLinear([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/linear.js), [Examples](https://observablehq.com/@d3/d3-scalelinear) + +Constructs a new [continuous scale](#continuous-scales) with the specified [domain](#continuous_domain) and [range](#continuous_range), the [default](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolate) [interpolator](#continuous_interpolate) and [clamping](#continuous_clamp) disabled. If either *domain* or *range* are not specified, each defaults to [0, 1]. Linear scales are a good default choice for continuous quantitative data because they preserve proportional differences. Each range value *y* can be expressed as a function of the domain value *x*: *y* = *mx* + *b*. + +#### Power Scales + +Power scales are similar to [linear scales](#linear-scales), except an exponential transform is applied to the input domain value before the output range value is computed. Each range value *y* can be expressed as a function of the domain value *x*: *y* = *mx^k* + *b*, where *k* is the [exponent](#pow_exponent) value. Power scales also support negative domain values, in which case the input value and the resulting output value are multiplied by -1. + +# d3.scalePow([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +Constructs a new [continuous scale](#continuous-scales) with the specified [domain](#continuous_domain) and [range](#continuous_range), the [exponent](#pow_exponent) 1, the [default](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolate) [interpolator](#continuous_interpolate) and [clamping](#continuous_clamp) disabled. If either *domain* or *range* are not specified, each defaults to [0, 1]. (Note that this is effectively a [linear](#linear-scales) scale until you set a different exponent.) + +# pow(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*](#_continuous). + +# pow.invert(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.invert](#continuous_invert). + +# pow.exponent([exponent]) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +If *exponent* is specified, sets the current exponent to the given numeric value. If *exponent* is not specified, returns the current exponent, which defaults to 1. (Note that this is effectively a [linear](#linear-scales) scale until you set a different exponent.) + +# pow.domain([domain]) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.domain](#continuous_domain). + +# pow.range([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.range](#continuous_range). + +# pow.rangeRound([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.rangeRound](#continuous_rangeRound). + +# pow.clamp(clamp) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.clamp](#continuous_clamp). + +# pow.interpolate(interpolate) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.interpolate](#continuous_interpolate). + +# pow.ticks([count]) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/scale-ticks) + +See [*continuous*.ticks](#continuous_ticks). + +# pow.tickFormat([count[, specifier]]) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/scale-ticks) + +See [*continuous*.tickFormat](#continuous_tickFormat). + +# pow.nice([count]) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.nice](#continuous_nice). + +# pow.copy() · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.copy](#continuous_copy). + +# d3.scaleSqrt([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/pow.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +Constructs a new [continuous](#continuous-scales) [power scale](#power-scales) with the specified [domain](#continuous_domain) and [range](#continuous_range), the [exponent](#pow_exponent) 0.5, the [default](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolate) [interpolator](#continuous_interpolate) and [clamping](#continuous_clamp) disabled. If either *domain* or *range* are not specified, each defaults to [0, 1]. This is a convenience method equivalent to `d3.scalePow(…).exponent(0.5)`. + +#### Log Scales + +Log scales are similar to [linear scales](#linear-scales), except a logarithmic transform is applied to the input domain value before the output range value is computed. The mapping to the range value *y* can be expressed as a function of the domain value *x*: *y* = *m* log(x) + *b*. + +As log(0) = -∞, a log scale domain must be **strictly-positive or strictly-negative**; the domain must not include or cross zero. A log scale with a positive domain has a well-defined behavior for positive values, and a log scale with a negative domain has a well-defined behavior for negative values. (For a negative domain, input and output values are implicitly multiplied by -1.) The behavior of the scale is undefined if you pass a negative value to a log scale with a positive domain or vice versa. + +# d3.scaleLog([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/log.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +Constructs a new [continuous scale](#continuous-scales) with the specified [domain](#log_domain) and [range](#log_range), the [base](#log_base) 10, the [default](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolate) [interpolator](#log_interpolate) and [clamping](#log_clamp) disabled. If *domain* is not specified, it defaults to [1, 10]. If *range* is not specified, it defaults to [0, 1]. + +# log(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/log.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*](#_continuous). + +# log.invert(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/log.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.invert](#continuous_invert). + +# log.base([base]) · [Source](https://github.com/d3/d3-scale/blob/master/src/log.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +If *base* is specified, sets the base for this logarithmic scale to the specified value. If *base* is not specified, returns the current base, which defaults to 10. + +# log.domain([domain]) · [Source](https://github.com/d3/d3-scale/blob/master/src/log.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.domain](#continuous_domain). + +# log.range([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/continuous.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.range](#continuous_range). + +# log.rangeRound([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/log.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.rangeRound](#continuous_rangeRound). + +# log.clamp(clamp) · [Source](https://github.com/d3/d3-scale/blob/master/src/log.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.clamp](#continuous_clamp). + +# log.interpolate(interpolate) · [Source](https://github.com/d3/d3-scale/blob/master/src/log.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.interpolate](#continuous_interpolate). + +# log.ticks([count]) · [Source](https://github.com/d3/d3-scale/blob/master/src/log.js), [Examples](https://observablehq.com/@d3/scale-ticks) + +Like [*continuous*.ticks](#continuous_ticks), but customized for a log scale. If the [base](#log_base) is an integer, the returned ticks are uniformly spaced within each integer power of base; otherwise, one tick per power of base is returned. The returned ticks are guaranteed to be within the extent of the domain. If the orders of magnitude in the [domain](#log_domain) is greater than *count*, then at most one tick per power is returned. Otherwise, the tick values are unfiltered, but note that you can use [*log*.tickFormat](#log_tickFormat) to filter the display of tick labels. If *count* is not specified, it defaults to 10. + +# log.tickFormat([count[, specifier]]) · [Source](https://github.com/d3/d3-scale/blob/master/src/log.js), [Examples](https://observablehq.com/@d3/scale-ticks) + +Like [*continuous*.tickFormat](#continuous_tickFormat), but customized for a log scale. The specified *count* typically has the same value as the count that is used to generate the [tick values](#continuous_ticks). If there are too many ticks, the formatter may return the empty string for some of the tick labels; however, note that the ticks are still shown. To disable filtering, specify a *count* of Infinity. When specifying a count, you may also provide a format *specifier* or format function. For example, to get a tick formatter that will display 20 ticks of a currency, say `log.tickFormat(20, "$,f")`. If the specifier does not have a defined precision, the precision will be set automatically by the scale, returning the appropriate format. This provides a convenient way of specifying a format whose precision will be automatically set by the scale. + +# log.nice() · [Source](https://github.com/d3/d3-scale/blob/master/src/log.js), [Examples](https://observablehq.com/@d3/d3-scalelinear) + +Like [*continuous*.nice](#continuous_nice), except extends the domain to integer powers of [base](#log_base). For example, for a domain of [0.201479…, 0.996679…], and base 10, the nice domain is [0.1, 1]. If the domain has more than two values, nicing the domain only affects the first and last value. + +# log.copy() · [Source](https://github.com/d3/d3-scale/blob/master/src/log.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +See [*continuous*.copy](#continuous_copy). + +#### Symlog Scales + +See [A bi-symmetric log transformation for wide-range data](https://www.researchgate.net/profile/John_Webber4/publication/233967063_A_bi-symmetric_log_transformation_for_wide-range_data/links/0fcfd50d791c85082e000000.pdf) by Webber for more. + +# d3.scaleSymlog([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/symlog.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +Constructs a new [continuous scale](#continuous-scales) with the specified [domain](#continuous_domain) and [range](#continuous_range), the [constant](#symlog_constant) 1, the [default](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolate) [interpolator](#continuous_interpolate) and [clamping](#continuous_clamp) disabled. If *domain* is not specified, it defaults to [0, 1]. If *range* is not specified, it defaults to [0, 1]. + +# symlog.constant([constant]) · [Source](https://github.com/d3/d3-scale/blob/master/src/symlog.js), [Examples](https://observablehq.com/@d3/continuous-scales) + +If *constant* is specified, sets the symlog constant to the specified number and returns this scale; otherwise returns the current value of the symlog constant, which defaults to 1. See “A bi-symmetric log transformation for wide-range data” by Webber for more. + +#### Identity Scales + +Identity scales are a special case of [linear scales](#linear-scales) where the domain and range are identical; the scale and its invert method are thus the identity function. These scales are occasionally useful when working with pixel coordinates, say in conjunction with an axis. Identity scales do not support [rangeRound](#continuous_rangeRound), [clamp](#continuous_clamp) or [interpolate](#continuous_interpolate). + +# d3.scaleIdentity([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/identity.js), [Examples](https://observablehq.com/@d3/d3-scalelinear) + +Constructs a new identity scale with the specified [domain](#continuous_domain) and [range](#continuous_range). If *range* is not specified, it defaults to [0, 1]. + +#### Radial Scales + +Radial scales are a variant of [linear scales](#linear-scales) where the range is internally squared so that an input value corresponds linearly to the squared output value. These scales are useful when you want the input value to correspond to the area of a graphical mark and the mark is specified by radius, as in a radial bar chart. Radial scales do not support [interpolate](#continuous_interpolate). + +# d3.scaleRadial([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/radial.js), [Examples](https://observablehq.com/@d3/radial-stacked-bar-chart) + +Constructs a new radial scale with the specified [domain](#continuous_domain) and [range](#continuous_range). If *domain* or *range* is not specified, each defaults to [0, 1]. + +#### Time Scales + +Time scales are a variant of [linear scales](#linear-scales) that have a temporal domain: domain values are coerced to [dates](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Date) rather than numbers, and [invert](#continuous_invert) likewise returns a date. Time scales implement [ticks](#time_ticks) based on [calendar intervals](https://github.com/d3/d3-time), taking the pain out of generating axes for temporal domains. + +For example, to create a position encoding: + +```js +var x = d3.scaleTime() + .domain([new Date(2000, 0, 1), new Date(2000, 0, 2)]) + .range([0, 960]); + +x(new Date(2000, 0, 1, 5)); // 200 +x(new Date(2000, 0, 1, 16)); // 640 +x.invert(200); // Sat Jan 01 2000 05:00:00 GMT-0800 (PST) +x.invert(640); // Sat Jan 01 2000 16:00:00 GMT-0800 (PST) +``` + +For a valid value *y* in the range, time(time.invert(y)) equals *y*; similarly, for a valid value *x* in the domain, time.invert(time(x)) equals *x*. The invert method is useful for interaction, say to determine the value in the domain that corresponds to the pixel location under the mouse. + +# d3.scaleTime([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/time.js), [Examples](https://observablehq.com/@d3/d3-scaletime) + +Constructs a new time scale with the specified [domain](#time_domain) and [range](#time_range), the [default](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolate) [interpolator](#time_interpolate) and [clamping](#time_clamp) disabled. If *domain* is not specified, it defaults to [2000-01-01, 2000-01-02]. If *range* is not specified, it defaults to [0, 1]. + +# time(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/time.js), [Examples](https://observablehq.com/@d3/d3-scaletime) + +See [*continuous*](#_continuous). + +# time.invert(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/time.js), [Examples](https://observablehq.com/@d3/d3-scaletime) + +See [*continuous*.invert](#continuous_invert). + +# time.domain([domain]) · [Source](https://github.com/d3/d3-scale/blob/master/src/time.js), [Examples](https://observablehq.com/@d3/d3-scaletime) + +See [*continuous*.domain](#continuous_domain). + +# time.range([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/time.js), [Examples](https://observablehq.com/@d3/d3-scaletime) + +See [*continuous*.range](#continuous_range). + +# time.rangeRound([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/time.js), [Examples](https://observablehq.com/@d3/d3-scaletime) + +See [*continuous*.rangeRound](#continuous_rangeRound). + +# time.clamp(clamp) · [Source](https://github.com/d3/d3-scale/blob/master/src/time.js), [Examples](https://observablehq.com/@d3/d3-scaletime) + +See [*continuous*.clamp](#continuous_clamp). + +# time.interpolate(interpolate) · [Source](https://github.com/d3/d3-scale/blob/master/src/time.js), [Examples](https://observablehq.com/@d3/d3-scaletime) + +See [*continuous*.interpolate](#continuous_interpolate). + +# time.ticks([count]) · [Source](https://github.com/d3/d3-scale/blob/master/src/time.js), [Examples](https://observablehq.com/@d3/d3-scaletime) +
    # time.ticks([interval]) + +Returns representative dates from the scale’s [domain](#time_domain). The returned tick values are uniformly-spaced (mostly), have sensible values (such as every day at midnight), and are guaranteed to be within the extent of the domain. Ticks are often used to display reference lines, or tick marks, in conjunction with the visualized data. + +An optional *count* may be specified to affect how many ticks are generated. If *count* is not specified, it defaults to 10. The specified *count* is only a hint; the scale may return more or fewer values depending on the domain. For example, to create ten default ticks, say: + +```js +var x = d3.scaleTime(); + +x.ticks(10); +// [Sat Jan 01 2000 00:00:00 GMT-0800 (PST), +// Sat Jan 01 2000 03:00:00 GMT-0800 (PST), +// Sat Jan 01 2000 06:00:00 GMT-0800 (PST), +// Sat Jan 01 2000 09:00:00 GMT-0800 (PST), +// Sat Jan 01 2000 12:00:00 GMT-0800 (PST), +// Sat Jan 01 2000 15:00:00 GMT-0800 (PST), +// Sat Jan 01 2000 18:00:00 GMT-0800 (PST), +// Sat Jan 01 2000 21:00:00 GMT-0800 (PST), +// Sun Jan 02 2000 00:00:00 GMT-0800 (PST)] +``` + +The following time intervals are considered for automatic ticks: + +* 1-, 5-, 15- and 30-second. +* 1-, 5-, 15- and 30-minute. +* 1-, 3-, 6- and 12-hour. +* 1- and 2-day. +* 1-week. +* 1- and 3-month. +* 1-year. + +In lieu of a *count*, a [time *interval*](https://github.com/d3/d3-time/blob/master/README.md#intervals) may be explicitly specified. To prune the generated ticks for a given time *interval*, use [*interval*.every](https://github.com/d3/d3-time/blob/master/README.md#interval_every). For example, to generate ticks at 15-[minute](https://github.com/d3/d3-time/blob/master/README.md#minute) intervals: + +```js +var x = d3.scaleTime() + .domain([new Date(2000, 0, 1, 0), new Date(2000, 0, 1, 2)]); + +x.ticks(d3.timeMinute.every(15)); +// [Sat Jan 01 2000 00:00:00 GMT-0800 (PST), +// Sat Jan 01 2000 00:15:00 GMT-0800 (PST), +// Sat Jan 01 2000 00:30:00 GMT-0800 (PST), +// Sat Jan 01 2000 00:45:00 GMT-0800 (PST), +// Sat Jan 01 2000 01:00:00 GMT-0800 (PST), +// Sat Jan 01 2000 01:15:00 GMT-0800 (PST), +// Sat Jan 01 2000 01:30:00 GMT-0800 (PST), +// Sat Jan 01 2000 01:45:00 GMT-0800 (PST), +// Sat Jan 01 2000 02:00:00 GMT-0800 (PST)] +``` + +Alternatively, pass a test function to [*interval*.filter](https://github.com/d3/d3-time/blob/master/README.md#interval_filter): + +```js +x.ticks(d3.timeMinute.filter(function(d) { + return d.getMinutes() % 15 === 0; +})); +``` + +Note: in some cases, such as with day ticks, specifying a *step* can result in irregular spacing of ticks because time intervals have varying length. + +# time.tickFormat([count[, specifier]]) · [Source](https://github.com/d3/d3-scale/blob/master/src/time.js), [Examples](https://observablehq.com/@d3/scale-ticks) +
    # time.tickFormat([interval[, specifier]]) + +Returns a time format function suitable for displaying [tick](#time_ticks) values. The specified *count* or *interval* is currently ignored, but is accepted for consistency with other scales such as [*continuous*.tickFormat](#continuous_tickFormat). If a format *specifier* is specified, this method is equivalent to [format](https://github.com/d3/d3-time-format/blob/master/README.md#format). If *specifier* is not specified, the default time format is returned. The default multi-scale time format chooses a human-readable representation based on the specified date as follows: + +* `%Y` - for year boundaries, such as `2011`. +* `%B` - for month boundaries, such as `February`. +* `%b %d` - for week boundaries, such as `Feb 06`. +* `%a %d` - for day boundaries, such as `Mon 07`. +* `%I %p` - for hour boundaries, such as `01 AM`. +* `%I:%M` - for minute boundaries, such as `01:23`. +* `:%S` - for second boundaries, such as `:45`. +* `.%L` - milliseconds for all other times, such as `.012`. + +Although somewhat unusual, this default behavior has the benefit of providing both local and global context: for example, formatting a sequence of ticks as [11 PM, Mon 07, 01 AM] reveals information about hours, dates, and day simultaneously, rather than just the hours [11 PM, 12 AM, 01 AM]. See [d3-time-format](https://github.com/d3/d3-time-format) if you’d like to roll your own conditional time format. + +# time.nice([count]) · [Source](https://github.com/d3/d3-scale/blob/master/src/time.js), [Examples](https://observablehq.com/@d3/d3-scaletime) +
    # time.nice([interval]) + +Extends the [domain](#time_domain) so that it starts and ends on nice round values. This method typically modifies the scale’s domain, and may only extend the bounds to the nearest round value. See [*continuous*.nice](#continuous_nice) for more. + +An optional tick *count* argument allows greater control over the step size used to extend the bounds, guaranteeing that the returned [ticks](#time_ticks) will exactly cover the domain. Alternatively, a [time *interval*](https://github.com/d3/d3-time/blob/master/README.md#intervals) may be specified to explicitly set the ticks. If an *interval* is specified, an optional *step* may also be specified to skip some ticks. For example, `time.nice(d3.timeSecond.every(10))` will extend the domain to an even ten seconds (0, 10, 20, etc.). See [*time*.ticks](#time_ticks) and [*interval*.every](https://github.com/d3/d3-time/blob/master/README.md#interval_every) for further detail. + +Nicing is useful if the domain is computed from data, say using [extent](https://github.com/d3/d3-array/blob/master/README.md#extent), and may be irregular. For example, for a domain of [2009-07-13T00:02, 2009-07-13T23:48], the nice domain is [2009-07-13, 2009-07-14]. If the domain has more than two values, nicing the domain only affects the first and last value. + +# time.copy() · [Source](https://github.com/d3/d3-scale/blob/master/src/time.js), [Examples](https://observablehq.com/@d3/d3-scaletime) + +See [*continuous*.copy](#continuous_copy). + +# d3.scaleUtc([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/utcTime.js), [Examples](https://observablehq.com/@d3/d3-scaletime) + +Equivalent to [scaleTime](#scaleTime), but the returned time scale operates in [Coordinated Universal Time](https://en.wikipedia.org/wiki/Coordinated_Universal_Time) rather than local time. + +### Sequential Scales + +Sequential scales, like [diverging scales](#diverging-scales), are similar to [continuous scales](#continuous-scales) in that they map a continuous, numeric input domain to a continuous output range. However, unlike continuous scales, the input domain and output range of a sequential scale always has exactly two elements, and the output range is typically specified as an interpolator rather than an array of values. These scales do not expose [invert](#continuous_invert) and [interpolate](#continuous_interpolate) methods. + +# d3.scaleSequential([[domain, ]interpolator]) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequential.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +Constructs a new sequential scale with the specified [*domain*](#sequential_domain) and [*interpolator*](#sequential_interpolator) function or array. If *domain* is not specified, it defaults to [0, 1]. If *interpolator* is not specified, it defaults to the identity function. When the scale is [applied](#_sequential), the interpolator will be invoked with a value typically in the range [0, 1], where 0 represents the minimum value and 1 represents the maximum value. For example, to implement the ill-advised [HSL](https://github.com/d3/d3-color/blob/master/README.md#hsl) rainbow scale: + +```js +var rainbow = d3.scaleSequential(function(t) { + return d3.hsl(t * 360, 1, 0.5) + ""; +}); +``` + +A more aesthetically-pleasing and perceptually-effective cyclical hue encoding is to use [d3.interpolateRainbow](https://github.com/d3/d3-scale-chromatic/blob/master/README.md#interpolateRainbow): + +```js +var rainbow = d3.scaleSequential(d3.interpolateRainbow); +``` + +If *interpolator* is an array, it represents the scale’s two-element output range and is converted to an interpolator function using [d3.interpolate](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolate). + +# sequential(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequential.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +See [*continuous*](#_continuous). + +# sequential.domain([domain]) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequential.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +See [*continuous*.domain](#continuous_domain). Note that a sequential scale’s domain must be numeric and must contain exactly two values. + +# sequential.clamp([clamp]) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequential.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +See [*continuous*.clamp](#continuous_clamp). + +# sequential.interpolator([interpolator]) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequential.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +If *interpolator* is specified, sets the scale’s interpolator to the specified function. If *interpolator* is not specified, returns the scale’s current interpolator. + +# sequential.range([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequential.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +See [*continuous*.range](#continuous_range). If *range* is specified, the given two-element array is converted to an interpolator function using [d3.interpolate](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolate). + +# sequential.rangeRound([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequential.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +See [*continuous*.rangeRound](#continuous_rangeRound). If *range* is specified, implicitly uses [d3.interpolateRound](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolateRound) as the interpolator. + +# sequential.copy() · [Source](https://github.com/d3/d3-scale/blob/master/src/sequential.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +See [*continuous*.copy](#continuous_copy). + +# d3.scaleSequentialLog([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequential.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +A [sequential scale](#sequential-scales) with a logarithmic transform, analogous to a [log scale](#log-scales). + +# d3.scaleSequentialPow([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequential.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +A [sequential scale](#sequential-scales) with an exponential transform, analogous to a [power scale](#pow-scales). + +# d3.scaleSequentialSqrt([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequential.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +A [sequential scale](#sequential-scales) with a square-root transform, analogous to a [d3.scaleSqrt](#scaleSqrt). + +# d3.scaleSequentialSymlog([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequential.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +A [sequential scale](#sequential-scales) with a symmetric logarithmic transform, analogous to a [symlog scale](#symlog-scales). + +# d3.scaleSequentialQuantile([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequentialQuantile.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +A [sequential scale](#sequential-scales) using a *p*-quantile transform, analogous to a [quantile scale](#quantile-scales). + +# sequentialQuantile.quantiles(n) · [Source](https://github.com/d3/d3-scale/blob/master/src/sequentialQuantile.js), [Examples](https://observablehq.com/@d3/sequential-scales) + +Returns an array of *n* + 1 quantiles. For example, if *n* = 4, returns an array of five numbers: the minimum value, the first quartile, the median, the third quartile, and the maximum. + +### Diverging Scales + +Diverging scales, like [sequential scales](#sequential-scales), are similar to [continuous scales](#continuous-scales) in that they map a continuous, numeric input domain to a continuous output range. However, unlike continuous scales, the input domain and output range of a diverging scale always has exactly three elements, and the output range is typically specified as an interpolator rather than an array of values. These scales do not expose [invert](#continuous_invert) and [interpolate](#continuous_interpolate) methods. + +# d3.scaleDiverging([[domain, ]interpolator]) · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +Constructs a new diverging scale with the specified [*domain*](#diverging_domain) and [*interpolator*](#diverging_interpolator) function or array. If *domain* is not specified, it defaults to [0, 0.5, 1]. If *interpolator* is not specified, it defaults to the identity function. When the scale is [applied](#_diverging), the interpolator will be invoked with a value typically in the range [0, 1], where 0 represents the extreme negative value, 0.5 represents the neutral value, and 1 represents the extreme positive value. For example, using [d3.interpolateSpectral](https://github.com/d3/d3-scale-chromatic/blob/master/README.md#interpolateSpectral): + +```js +var spectral = d3.scaleDiverging(d3.interpolateSpectral); +``` + +If *interpolator* is an array, it represents the scale’s three-element output range and is converted to an interpolator function using [d3.interpolate](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolate) and [d3.piecewise](https://github.com/d3/d3-interpolate/blob/master/README.md#piecewise). + +# diverging(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +See [*continuous*](#_continuous). + +# diverging.domain([domain]) · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +See [*continuous*.domain](#continuous_domain). Note that a diverging scale’s domain must be numeric and must contain exactly three values. The default domain is [0, 0.5, 1]. + +# diverging.clamp([clamp]) · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +See [*continuous*.clamp](#continuous_clamp). + +# diverging.interpolator([interpolator]) · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +If *interpolator* is specified, sets the scale’s interpolator to the specified function. If *interpolator* is not specified, returns the scale’s current interpolator. + +# diverging.range([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +See [*continuous*.range](#continuous_range). If *range* is specified, the given three-element array is converted to an interpolator function using [d3.interpolate](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolate) and [d3.piecewise](https://github.com/d3/d3-interpolate/blob/master/README.md#piecewise). + +# diverging.rangeRound([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +See [*continuous*.range](#continuous_rangeRound). If *range* is specified, implicitly uses [d3.interpolateRound](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolateRound) as the interpolator. + +# diverging.copy() · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +See [*continuous*.copy](#continuous_copy). + +# diverging.unknown() · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +See [*continuous*.unknown](#continuous_unknown). + +# d3.scaleDivergingLog([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +A [diverging scale](#diverging-scales) with a logarithmic transform, analogous to a [log scale](#log-scales). + +# d3.scaleDivergingPow([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +A [diverging scale](#diverging-scales) with an exponential transform, analogous to a [power scale](#pow-scales). + +# d3.scaleDivergingSqrt([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +A [diverging scale](#diverging-scales) with a square-root transform, analogous to a [d3.scaleSqrt](#scaleSqrt). + +# d3.scaleDivergingSymlog([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/diverging.js), [Examples](https://observablehq.com/@d3/diverging-scales) + +A [diverging scale](#diverging-scales) with a symmetric logarithmic transform, analogous to a [symlog scale](#symlog-scales). + +### Quantize Scales + +Quantize scales are similar to [linear scales](#linear-scales), except they use a discrete rather than continuous range. The continuous input domain is divided into uniform segments based on the number of values in (*i.e.*, the cardinality of) the output range. Each range value *y* can be expressed as a quantized linear function of the domain value *x*: *y* = *m round(x)* + *b*. See [this choropleth](https://observablehq.com/@d3/choropleth) for an example. + +# d3.scaleQuantize([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/quantize.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Constructs a new quantize scale with the specified [*domain*](#quantize_domain) and [*range*](#quantize_range). If either *domain* or *range* is not specified, each defaults to [0, 1]. Thus, the default quantize scale is equivalent to the [Math.round](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Math/round) function. + +# quantize(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/quantize.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Given a *value* in the input [domain](#quantize_domain), returns the corresponding value in the output [range](#quantize_range). For example, to apply a color encoding: + +```js +var color = d3.scaleQuantize() + .domain([0, 1]) + .range(["brown", "steelblue"]); + +color(0.49); // "brown" +color(0.51); // "steelblue" +``` + +Or dividing the domain into three equally-sized parts with different range values to compute an appropriate stroke width: + +```js +var width = d3.scaleQuantize() + .domain([10, 100]) + .range([1, 2, 4]); + +width(20); // 1 +width(50); // 2 +width(80); // 4 +``` + +# quantize.invertExtent(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/quantize.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Returns the extent of values in the [domain](#quantize_domain) [x0, x1] for the corresponding *value* in the [range](#quantize_range): the inverse of [*quantize*](#_quantize). This method is useful for interaction, say to determine the value in the domain that corresponds to the pixel location under the mouse. + +```js +var width = d3.scaleQuantize() + .domain([10, 100]) + .range([1, 2, 4]); + +width.invertExtent(2); // [40, 70] +``` + +# quantize.domain([domain]) · [Source](https://github.com/d3/d3-scale/blob/master/src/quantize.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +If *domain* is specified, sets the scale’s domain to the specified two-element array of numbers. If the elements in the given array are not numbers, they will be coerced to numbers. The numbers must be in ascending order or the behavior of the scale is undefined. If *domain* is not specified, returns the scale’s current domain. + +# quantize.range([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/quantize.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +If *range* is specified, sets the scale’s range to the specified array of values. The array may contain any number of discrete values. The elements in the given array need not be numbers; any value or type will work. If *range* is not specified, returns the scale’s current range. + +# quantize.ticks([count]) · [Source](https://github.com/d3/d3-scale/blob/master/src/quantize.js), [Examples](https://observablehq.com/@d3/scale-ticks) + +Equivalent to [*continuous*.ticks](#continuous_ticks). + +# quantize.tickFormat([count[, specifier]]) · [Source](https://github.com/d3/d3-scale/blob/master/src/linear.js), [Examples](https://observablehq.com/@d3/scale-ticks) + +Equivalent to [*continuous*.tickFormat](#continuous_tickFormat). + +# quantize.nice() · [Source](https://github.com/d3/d3-scale/blob/master/src/quantize.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Equivalent to [*continuous*.nice](#continuous_nice). + +# quantize.thresholds() · [Source](https://github.com/d3/d3-scale/blob/master/src/quantize.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Returns the array of computed thresholds within the [domain](#quantize_domain). + +# quantize.copy() · [Source](https://github.com/d3/d3-scale/blob/master/src/quantize.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Returns an exact copy of this scale. Changes to this scale will not affect the returned scale, and vice versa. + +### Quantile Scales + +Quantile scales map a sampled input domain to a discrete range. The domain is considered continuous and thus the scale will accept any reasonable input value; however, the domain is specified as a discrete set of sample values. The number of values in (the cardinality of) the output range determines the number of quantiles that will be computed from the domain. To compute the quantiles, the domain is sorted, and treated as a [population of discrete values](https://en.wikipedia.org/wiki/Quantile#Quantiles_of_a_population); see d3-array’s [quantile](https://github.com/d3/d3-array/blob/master/README.md#quantile). See [this quantile choropleth](https://observablehq.com/@d3/quantile-choropleth) for an example. + +# d3.scaleQuantile([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/quantile.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Constructs a new quantile scale with the specified [*domain*](#quantile_domain) and [*range*](#quantile_range). If either *domain* or *range* is not specified, each defaults to the empty array. The quantile scale is invalid until both a domain and range are specified. + +# quantile(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/quantile.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Given a *value* in the input [domain](#quantile_domain), returns the corresponding value in the output [range](#quantile_range). + +# quantile.invertExtent(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/quantile.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Returns the extent of values in the [domain](#quantile_domain) [x0, x1] for the corresponding *value* in the [range](#quantile_range): the inverse of [*quantile*](#_quantile). This method is useful for interaction, say to determine the value in the domain that corresponds to the pixel location under the mouse. + +# quantile.domain([domain]) · [Source](https://github.com/d3/d3-scale/blob/master/src/quantile.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +If *domain* is specified, sets the domain of the quantile scale to the specified set of discrete numeric values. The array must not be empty, and must contain at least one numeric value; NaN, null and undefined values are ignored and not considered part of the sample population. If the elements in the given array are not numbers, they will be coerced to numbers. A copy of the input array is sorted and stored internally. If *domain* is not specified, returns the scale’s current domain. + +# quantile.range([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/quantile.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +If *range* is specified, sets the discrete values in the range. The array must not be empty, and may contain any type of value. The number of values in (the cardinality, or length, of) the *range* array determines the number of quantiles that are computed. For example, to compute quartiles, *range* must be an array of four elements such as [0, 1, 2, 3]. If *range* is not specified, returns the current range. + +# quantile.quantiles() · [Source](https://github.com/d3/d3-scale/blob/master/src/quantile.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Returns the quantile thresholds. If the [range](#quantile_range) contains *n* discrete values, the returned array will contain *n* - 1 thresholds. Values less than the first threshold are considered in the first quantile; values greater than or equal to the first threshold but less than the second threshold are in the second quantile, and so on. Internally, the thresholds array is used with [bisect](https://github.com/d3/d3-array/blob/master/README.md#bisect) to find the output quantile associated with the given input value. + +# quantile.copy() · [Source](https://github.com/d3/d3-scale/blob/master/src/quantile.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Returns an exact copy of this scale. Changes to this scale will not affect the returned scale, and vice versa. + +### Threshold Scales + +Threshold scales are similar to [quantize scales](#quantize-scales), except they allow you to map arbitrary subsets of the domain to discrete values in the range. The input domain is still continuous, and divided into slices based on a set of threshold values. See [this choropleth](https://observablehq.com/@d3/threshold-choropleth) for an example. + +# d3.scaleThreshold([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/threshold.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Constructs a new threshold scale with the specified [*domain*](#threshold_domain) and [*range*](#threshold_range). If *domain* is not specified, it defaults to [0.5]. If *range* is not specified, it defaults to [0, 1]. Thus, the default threshold scale is equivalent to the [Math.round](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Math/round) function for numbers; for example threshold(0.49) returns 0, and threshold(0.51) returns 1. + +# threshold(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/threshold.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Given a *value* in the input [domain](#threshold_domain), returns the corresponding value in the output [range](#threshold_range). For example: + +```js +var color = d3.scaleThreshold() + .domain([0, 1]) + .range(["red", "white", "green"]); + +color(-1); // "red" +color(0); // "white" +color(0.5); // "white" +color(1); // "green" +color(1000); // "green" +``` + +# threshold.invertExtent(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/threshold.js), [Examples](https://observablehq.com/@d3/choropleth) + +Returns the extent of values in the [domain](#threshold_domain) [x0, x1] for the corresponding *value* in the [range](#threshold_range), representing the inverse mapping from range to domain. This method is useful for interaction, say to determine the value in the domain that corresponds to the pixel location under the mouse. For example: + +```js +var color = d3.scaleThreshold() + .domain([0, 1]) + .range(["red", "white", "green"]); + +color.invertExtent("red"); // [undefined, 0] +color.invertExtent("white"); // [0, 1] +color.invertExtent("green"); // [1, undefined] +``` + +# threshold.domain([domain]) · [Source](https://github.com/d3/d3-scale/blob/master/src/threshold.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +If *domain* is specified, sets the scale’s domain to the specified array of values. The values must be in ascending order or the behavior of the scale is undefined. The values are typically numbers, but any naturally ordered values (such as strings) will work; a threshold scale can be used to encode any type that is ordered. If the number of values in the scale’s range is N+1, the number of values in the scale’s domain must be N. If there are fewer than N elements in the domain, the additional values in the range are ignored. If there are more than N elements in the domain, the scale may return undefined for some inputs. If *domain* is not specified, returns the scale’s current domain. + +# threshold.range([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/threshold.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +If *range* is specified, sets the scale’s range to the specified array of values. If the number of values in the scale’s domain is N, the number of values in the scale’s range must be N+1. If there are fewer than N+1 elements in the range, the scale may return undefined for some inputs. If there are more than N+1 elements in the range, the additional values are ignored. The elements in the given array need not be numbers; any value or type will work. If *range* is not specified, returns the scale’s current range. + +# threshold.copy() · [Source](https://github.com/d3/d3-scale/blob/master/src/threshold.js), [Examples](https://observablehq.com/@d3/quantile-quantize-and-threshold-scales) + +Returns an exact copy of this scale. Changes to this scale will not affect the returned scale, and vice versa. + +### Ordinal Scales + +Unlike [continuous scales](#continuous-scales), ordinal scales have a discrete domain and range. For example, an ordinal scale might map a set of named categories to a set of colors, or determine the horizontal positions of columns in a column chart. + +# d3.scaleOrdinal([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/ordinal.js), [Examples](https://observablehq.com/@d3/d3-scaleordinal) + +Constructs a new ordinal scale with the specified [*domain*](#ordinal_domain) and [*range*](#ordinal_range). If *domain* is not specified, it defaults to the empty array. If *range* is not specified, it defaults to the empty array; an ordinal scale always returns undefined until a non-empty range is defined. + +# ordinal(value) · [Source](https://github.com/d3/d3-scale/blob/master/src/ordinal.js), [Examples](https://observablehq.com/@d3/d3-scaleordinal) + +Given a *value* in the input [domain](#ordinal_domain), returns the corresponding value in the output [range](#ordinal_range). If the given *value* is not in the scale’s [domain](#ordinal_domain), returns the [unknown](#ordinal_unknown); or, if the unknown value is [implicit](#scaleImplicit) (the default), then the *value* is implicitly added to the domain and the next-available value in the range is assigned to *value*, such that this and subsequent invocations of the scale given the same input *value* return the same output value. + +# ordinal.domain([domain]) · [Source](https://github.com/d3/d3-scale/blob/master/src/ordinal.js), [Examples](https://observablehq.com/@d3/d3-scaleordinal) + +If *domain* is specified, sets the domain to the specified array of values. The first element in *domain* will be mapped to the first element in the range, the second domain value to the second range value, and so on. Domain values are stored internally in an [InternMap](https://github.com/mbostock/internmap) from primitive value to index; the resulting index is then used to retrieve a value from the range. Thus, an ordinal scale’s values must be coercible to a primitive value, and the primitive domain value uniquely identifies the corresponding range value. If *domain* is not specified, this method returns the current domain. + +Setting the domain on an ordinal scale is optional if the [unknown value](#ordinal_unknown) is [implicit](#scaleImplicit) (the default). In this case, the domain will be inferred implicitly from usage by assigning each unique value passed to the scale a new value from the range. Note that an explicit domain is recommended to ensure deterministic behavior, as inferring the domain from usage will be dependent on ordering. + +# ordinal.range([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/ordinal.js), [Examples](https://observablehq.com/@d3/d3-scaleordinal) + +If *range* is specified, sets the range of the ordinal scale to the specified array of values. The first element in the domain will be mapped to the first element in *range*, the second domain value to the second range value, and so on. If there are fewer elements in the range than in the domain, the scale will reuse values from the start of the range. If *range* is not specified, this method returns the current range. + +# ordinal.unknown([value]) · [Source](https://github.com/d3/d3-scale/blob/master/src/ordinal.js), [Examples](https://observablehq.com/@d3/d3-scaleordinal) + +If *value* is specified, sets the output value of the scale for unknown input values and returns this scale. If *value* is not specified, returns the current unknown value, which defaults to [implicit](#scaleImplicit). The implicit value enables implicit domain construction; see [*ordinal*.domain](#ordinal_domain). + +# ordinal.copy() · [Source](https://github.com/d3/d3-scale/blob/master/src/ordinal.js), [Examples](https://observablehq.com/@d3/d3-scaleordinal) + +Returns an exact copy of this ordinal scale. Changes to this scale will not affect the returned scale, and vice versa. + +# d3.scaleImplicit · [Source](https://github.com/d3/d3-scale/blob/master/src/ordinal.js), [Examples](https://observablehq.com/@d3/d3-scaleordinal) + +A special value for [*ordinal*.unknown](#ordinal_unknown) that enables implicit domain construction: unknown values are implicitly added to the domain. + +#### Band Scales + +Band scales are like [ordinal scales](#ordinal-scales) except the output range is continuous and numeric. Discrete output values are automatically computed by the scale by dividing the continuous range into uniform bands. Band scales are typically used for bar charts with an ordinal or categorical dimension. The [unknown value](#ordinal_unknown) of a band scale is effectively undefined: they do not allow implicit domain construction. + +band + +# d3.scaleBand([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +Constructs a new band scale with the specified [*domain*](#band_domain) and [*range*](#band_range), no [padding](#band_padding), no [rounding](#band_round) and center [alignment](#band_align). If *domain* is not specified, it defaults to the empty domain. If *range* is not specified, it defaults to the unit range [0, 1]. + +# band(*value*) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +Given a *value* in the input [domain](#band_domain), returns the start of the corresponding band derived from the output [range](#band_range). If the given *value* is not in the scale’s domain, returns undefined. + +# band.domain([domain]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +If *domain* is specified, sets the domain to the specified array of values. The first element in *domain* will be mapped to the first band, the second domain value to the second band, and so on. Domain values are stored internally in an [InternMap](https://github.com/mbostock/internmap) from primitive value to index; the resulting index is then used to determine the band. Thus, a band scale’s values must be coercible to a primitive value, and the primitive domain value uniquely identifies the corresponding band. If *domain* is not specified, this method returns the current domain. + +# band.range([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +If *range* is specified, sets the scale’s range to the specified two-element array of numbers. If the elements in the given array are not numbers, they will be coerced to numbers. If *range* is not specified, returns the scale’s current range, which defaults to [0, 1]. + +# band.rangeRound([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +Sets the scale’s [*range*](#band_range) to the specified two-element array of numbers while also enabling [rounding](#band_round). This is a convenience method equivalent to: + +```js +band + .range(range) + .round(true); +``` + +Rounding is sometimes useful for avoiding antialiasing artifacts, though also consider the [shape-rendering](https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/shape-rendering) “crispEdges” styles. + +# band.round([round]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +If *round* is specified, enables or disables rounding accordingly. If rounding is enabled, the start and stop of each band will be integers. Rounding is sometimes useful for avoiding antialiasing artifacts, though also consider the [shape-rendering](https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/shape-rendering) “crispEdges” styles. Note that if the width of the domain is not a multiple of the cardinality of the range, there may be leftover unused space, even without padding! Use [*band*.align](#band_align) to specify how the leftover space is distributed. + +# band.paddingInner([padding]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +If *padding* is specified, sets the inner padding to the specified number which must be less than or equal to 1. If *padding* is not specified, returns the current inner padding which defaults to 0. The inner padding specifies the proportion of the range that is reserved for blank space between bands; a value of 0 means no blank space between bands, and a value of 1 means a [bandwidth](#band_bandwidth) of zero. + +# band.paddingOuter([padding]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +If *padding* is specified, sets the outer padding to the specified number which is typically in the range [0, 1]. If *padding* is not specified, returns the current outer padding which defaults to 0. The outer padding specifies the amount of blank space, in terms of multiples of the [step](#band_step), to reserve before the first band and after the last band. + +# band.padding([padding]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +A convenience method for setting the [inner](#band_paddingInner) and [outer](#band_paddingOuter) padding to the same *padding* value. If *padding* is not specified, returns the inner padding. + +# band.align([align]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +If *align* is specified, sets the alignment to the specified value which must be in the range [0, 1]. If *align* is not specified, returns the current alignment which defaults to 0.5. The alignment specifies how outer padding is distributed in the range. A value of 0.5 indicates that the outer padding should be equally distributed before the first band and after the last band; *i.e.*, the bands should be centered within the range. A value of 0 or 1 may be used to shift the bands to one side, say to position them adjacent to an axis. For more, [see this explainer](https://observablehq.com/@d3/band-align). + +# band.bandwidth() · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +Returns the width of each band. + +# band.step() · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +Returns the distance between the starts of adjacent bands. + +# band.copy() · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scaleband) + +Returns an exact copy of this scale. Changes to this scale will not affect the returned scale, and vice versa. + +#### Point Scales + +Point scales are a variant of [band scales](#band-scales) with the bandwidth fixed to zero. Point scales are typically used for scatterplots with an ordinal or categorical dimension. The [unknown value](#ordinal_unknown) of a point scale is always undefined: they do not allow implicit domain construction. + +point + +# d3.scalePoint([[domain, ]range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scalepoint) + +Constructs a new point scale with the specified [*domain*](#point_domain) and [*range*](#point_range), no [padding](#point_padding), no [rounding](#point_round) and center [alignment](#point_align). If *domain* is not specified, it defaults to the empty domain. If *range* is not specified, it defaults to the unit range [0, 1]. + +# point(*value*) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scalepoint) + +Given a *value* in the input [domain](#point_domain), returns the corresponding point derived from the output [range](#point_range). If the given *value* is not in the scale’s domain, returns undefined. + +# point.domain([domain]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scalepoint) + +If *domain* is specified, sets the domain to the specified array of values. The first element in *domain* will be mapped to the first point, the second domain value to the second point, and so on. Domain values are stored internally in an [InternMap](https://github.com/mbostock/internmap) from primitive value to index; the resulting index is then used to determine the point. Thus, a point scale’s values must be coercible to a primitive value, and the primitive domain value uniquely identifies the corresponding point. If *domain* is not specified, this method returns the current domain. + +# point.range([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scalepoint) + +If *range* is specified, sets the scale’s range to the specified two-element array of numbers. If the elements in the given array are not numbers, they will be coerced to numbers. If *range* is not specified, returns the scale’s current range, which defaults to [0, 1]. + +# point.rangeRound([range]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scalepoint) + +Sets the scale’s [*range*](#point_range) to the specified two-element array of numbers while also enabling [rounding](#point_round). This is a convenience method equivalent to: + +```js +point + .range(range) + .round(true); +``` + +Rounding is sometimes useful for avoiding antialiasing artifacts, though also consider the [shape-rendering](https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/shape-rendering) “crispEdges” styles. + +# point.round([round]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scalepoint) + +If *round* is specified, enables or disables rounding accordingly. If rounding is enabled, the position of each point will be integers. Rounding is sometimes useful for avoiding antialiasing artifacts, though also consider the [shape-rendering](https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/shape-rendering) “crispEdges” styles. Note that if the width of the domain is not a multiple of the cardinality of the range, there may be leftover unused space, even without padding! Use [*point*.align](#point_align) to specify how the leftover space is distributed. + +# point.padding([padding]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scalepoint) + +If *padding* is specified, sets the outer padding to the specified number which is typically in the range [0, 1]. If *padding* is not specified, returns the current outer padding which defaults to 0. The outer padding specifies the amount of blank space, in terms of multiples of the [step](#band_step), to reserve before the first point and after the last point. Equivalent to [*band*.paddingOuter](#band_paddingOuter). + +# point.align([align]) · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scalepoint) + +If *align* is specified, sets the alignment to the specified value which must be in the range [0, 1]. If *align* is not specified, returns the current alignment which defaults to 0.5. The alignment specifies how any leftover unused space in the range is distributed. A value of 0.5 indicates that the leftover space should be equally distributed before the first point and after the last point; *i.e.*, the points should be centered within the range. A value of 0 or 1 may be used to shift the points to one side, say to position them adjacent to an axis. + +# point.bandwidth() · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scalepoint) + +Returns zero. + +# point.step() · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scalepoint) + +Returns the distance between the starts of adjacent points. + +# point.copy() · [Source](https://github.com/d3/d3-scale/blob/master/src/band.js), [Examples](https://observablehq.com/@d3/d3-scalepoint) + +Returns an exact copy of this scale. Changes to this scale will not affect the returned scale, and vice versa. diff --git a/frontend/node_modules/d3-scale/dist/d3-scale.js b/frontend/node_modules/d3-scale/dist/d3-scale.js new file mode 100644 index 0000000..408d927 --- /dev/null +++ b/frontend/node_modules/d3-scale/dist/d3-scale.js @@ -0,0 +1,1196 @@ +// https://d3js.org/d3-scale/ v4.0.2 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-array'), require('d3-interpolate'), require('d3-format'), require('d3-time'), require('d3-time-format')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-array', 'd3-interpolate', 'd3-format', 'd3-time', 'd3-time-format'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3, global.d3, global.d3, global.d3, global.d3)); +})(this, (function (exports, d3Array, d3Interpolate, d3Format, d3Time, d3TimeFormat) { 'use strict'; + +function initRange(domain, range) { + switch (arguments.length) { + case 0: break; + case 1: this.range(domain); break; + default: this.range(range).domain(domain); break; + } + return this; +} + +function initInterpolator(domain, interpolator) { + switch (arguments.length) { + case 0: break; + case 1: { + if (typeof domain === "function") this.interpolator(domain); + else this.range(domain); + break; + } + default: { + this.domain(domain); + if (typeof interpolator === "function") this.interpolator(interpolator); + else this.range(interpolator); + break; + } + } + return this; +} + +const implicit = Symbol("implicit"); + +function ordinal() { + var index = new d3Array.InternMap(), + domain = [], + range = [], + unknown = implicit; + + function scale(d) { + let i = index.get(d); + if (i === undefined) { + if (unknown !== implicit) return unknown; + index.set(d, i = domain.push(d) - 1); + } + return range[i % range.length]; + } + + scale.domain = function(_) { + if (!arguments.length) return domain.slice(); + domain = [], index = new d3Array.InternMap(); + for (const value of _) { + if (index.has(value)) continue; + index.set(value, domain.push(value) - 1); + } + return scale; + }; + + scale.range = function(_) { + return arguments.length ? (range = Array.from(_), scale) : range.slice(); + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.copy = function() { + return ordinal(domain, range).unknown(unknown); + }; + + initRange.apply(scale, arguments); + + return scale; +} + +function band() { + var scale = ordinal().unknown(undefined), + domain = scale.domain, + ordinalRange = scale.range, + r0 = 0, + r1 = 1, + step, + bandwidth, + round = false, + paddingInner = 0, + paddingOuter = 0, + align = 0.5; + + delete scale.unknown; + + function rescale() { + var n = domain().length, + reverse = r1 < r0, + start = reverse ? r1 : r0, + stop = reverse ? r0 : r1; + step = (stop - start) / Math.max(1, n - paddingInner + paddingOuter * 2); + if (round) step = Math.floor(step); + start += (stop - start - step * (n - paddingInner)) * align; + bandwidth = step * (1 - paddingInner); + if (round) start = Math.round(start), bandwidth = Math.round(bandwidth); + var values = d3Array.range(n).map(function(i) { return start + step * i; }); + return ordinalRange(reverse ? values.reverse() : values); + } + + scale.domain = function(_) { + return arguments.length ? (domain(_), rescale()) : domain(); + }; + + scale.range = function(_) { + return arguments.length ? ([r0, r1] = _, r0 = +r0, r1 = +r1, rescale()) : [r0, r1]; + }; + + scale.rangeRound = function(_) { + return [r0, r1] = _, r0 = +r0, r1 = +r1, round = true, rescale(); + }; + + scale.bandwidth = function() { + return bandwidth; + }; + + scale.step = function() { + return step; + }; + + scale.round = function(_) { + return arguments.length ? (round = !!_, rescale()) : round; + }; + + scale.padding = function(_) { + return arguments.length ? (paddingInner = Math.min(1, paddingOuter = +_), rescale()) : paddingInner; + }; + + scale.paddingInner = function(_) { + return arguments.length ? (paddingInner = Math.min(1, _), rescale()) : paddingInner; + }; + + scale.paddingOuter = function(_) { + return arguments.length ? (paddingOuter = +_, rescale()) : paddingOuter; + }; + + scale.align = function(_) { + return arguments.length ? (align = Math.max(0, Math.min(1, _)), rescale()) : align; + }; + + scale.copy = function() { + return band(domain(), [r0, r1]) + .round(round) + .paddingInner(paddingInner) + .paddingOuter(paddingOuter) + .align(align); + }; + + return initRange.apply(rescale(), arguments); +} + +function pointish(scale) { + var copy = scale.copy; + + scale.padding = scale.paddingOuter; + delete scale.paddingInner; + delete scale.paddingOuter; + + scale.copy = function() { + return pointish(copy()); + }; + + return scale; +} + +function point() { + return pointish(band.apply(null, arguments).paddingInner(1)); +} + +function constants(x) { + return function() { + return x; + }; +} + +function number$1(x) { + return +x; +} + +var unit = [0, 1]; + +function identity$1(x) { + return x; +} + +function normalize(a, b) { + return (b -= (a = +a)) + ? function(x) { return (x - a) / b; } + : constants(isNaN(b) ? NaN : 0.5); +} + +function clamper(a, b) { + var t; + if (a > b) t = a, a = b, b = t; + return function(x) { return Math.max(a, Math.min(b, x)); }; +} + +// normalize(a, b)(x) takes a domain value x in [a,b] and returns the corresponding parameter t in [0,1]. +// interpolate(a, b)(t) takes a parameter t in [0,1] and returns the corresponding range value x in [a,b]. +function bimap(domain, range, interpolate) { + var d0 = domain[0], d1 = domain[1], r0 = range[0], r1 = range[1]; + if (d1 < d0) d0 = normalize(d1, d0), r0 = interpolate(r1, r0); + else d0 = normalize(d0, d1), r0 = interpolate(r0, r1); + return function(x) { return r0(d0(x)); }; +} + +function polymap(domain, range, interpolate) { + var j = Math.min(domain.length, range.length) - 1, + d = new Array(j), + r = new Array(j), + i = -1; + + // Reverse descending domains. + if (domain[j] < domain[0]) { + domain = domain.slice().reverse(); + range = range.slice().reverse(); + } + + while (++i < j) { + d[i] = normalize(domain[i], domain[i + 1]); + r[i] = interpolate(range[i], range[i + 1]); + } + + return function(x) { + var i = d3Array.bisect(domain, x, 1, j) - 1; + return r[i](d[i](x)); + }; +} + +function copy$1(source, target) { + return target + .domain(source.domain()) + .range(source.range()) + .interpolate(source.interpolate()) + .clamp(source.clamp()) + .unknown(source.unknown()); +} + +function transformer$2() { + var domain = unit, + range = unit, + interpolate = d3Interpolate.interpolate, + transform, + untransform, + unknown, + clamp = identity$1, + piecewise, + output, + input; + + function rescale() { + var n = Math.min(domain.length, range.length); + if (clamp !== identity$1) clamp = clamper(domain[0], domain[n - 1]); + piecewise = n > 2 ? polymap : bimap; + output = input = null; + return scale; + } + + function scale(x) { + return x == null || isNaN(x = +x) ? unknown : (output || (output = piecewise(domain.map(transform), range, interpolate)))(transform(clamp(x))); + } + + scale.invert = function(y) { + return clamp(untransform((input || (input = piecewise(range, domain.map(transform), d3Interpolate.interpolateNumber)))(y))); + }; + + scale.domain = function(_) { + return arguments.length ? (domain = Array.from(_, number$1), rescale()) : domain.slice(); + }; + + scale.range = function(_) { + return arguments.length ? (range = Array.from(_), rescale()) : range.slice(); + }; + + scale.rangeRound = function(_) { + return range = Array.from(_), interpolate = d3Interpolate.interpolateRound, rescale(); + }; + + scale.clamp = function(_) { + return arguments.length ? (clamp = _ ? true : identity$1, rescale()) : clamp !== identity$1; + }; + + scale.interpolate = function(_) { + return arguments.length ? (interpolate = _, rescale()) : interpolate; + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + return function(t, u) { + transform = t, untransform = u; + return rescale(); + }; +} + +function continuous() { + return transformer$2()(identity$1, identity$1); +} + +function tickFormat(start, stop, count, specifier) { + var step = d3Array.tickStep(start, stop, count), + precision; + specifier = d3Format.formatSpecifier(specifier == null ? ",f" : specifier); + switch (specifier.type) { + case "s": { + var value = Math.max(Math.abs(start), Math.abs(stop)); + if (specifier.precision == null && !isNaN(precision = d3Format.precisionPrefix(step, value))) specifier.precision = precision; + return d3Format.formatPrefix(specifier, value); + } + case "": + case "e": + case "g": + case "p": + case "r": { + if (specifier.precision == null && !isNaN(precision = d3Format.precisionRound(step, Math.max(Math.abs(start), Math.abs(stop))))) specifier.precision = precision - (specifier.type === "e"); + break; + } + case "f": + case "%": { + if (specifier.precision == null && !isNaN(precision = d3Format.precisionFixed(step))) specifier.precision = precision - (specifier.type === "%") * 2; + break; + } + } + return d3Format.format(specifier); +} + +function linearish(scale) { + var domain = scale.domain; + + scale.ticks = function(count) { + var d = domain(); + return d3Array.ticks(d[0], d[d.length - 1], count == null ? 10 : count); + }; + + scale.tickFormat = function(count, specifier) { + var d = domain(); + return tickFormat(d[0], d[d.length - 1], count == null ? 10 : count, specifier); + }; + + scale.nice = function(count) { + if (count == null) count = 10; + + var d = domain(); + var i0 = 0; + var i1 = d.length - 1; + var start = d[i0]; + var stop = d[i1]; + var prestep; + var step; + var maxIter = 10; + + if (stop < start) { + step = start, start = stop, stop = step; + step = i0, i0 = i1, i1 = step; + } + + while (maxIter-- > 0) { + step = d3Array.tickIncrement(start, stop, count); + if (step === prestep) { + d[i0] = start; + d[i1] = stop; + return domain(d); + } else if (step > 0) { + start = Math.floor(start / step) * step; + stop = Math.ceil(stop / step) * step; + } else if (step < 0) { + start = Math.ceil(start * step) / step; + stop = Math.floor(stop * step) / step; + } else { + break; + } + prestep = step; + } + + return scale; + }; + + return scale; +} + +function linear() { + var scale = continuous(); + + scale.copy = function() { + return copy$1(scale, linear()); + }; + + initRange.apply(scale, arguments); + + return linearish(scale); +} + +function identity(domain) { + var unknown; + + function scale(x) { + return x == null || isNaN(x = +x) ? unknown : x; + } + + scale.invert = scale; + + scale.domain = scale.range = function(_) { + return arguments.length ? (domain = Array.from(_, number$1), scale) : domain.slice(); + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.copy = function() { + return identity(domain).unknown(unknown); + }; + + domain = arguments.length ? Array.from(domain, number$1) : [0, 1]; + + return linearish(scale); +} + +function nice(domain, interval) { + domain = domain.slice(); + + var i0 = 0, + i1 = domain.length - 1, + x0 = domain[i0], + x1 = domain[i1], + t; + + if (x1 < x0) { + t = i0, i0 = i1, i1 = t; + t = x0, x0 = x1, x1 = t; + } + + domain[i0] = interval.floor(x0); + domain[i1] = interval.ceil(x1); + return domain; +} + +function transformLog(x) { + return Math.log(x); +} + +function transformExp(x) { + return Math.exp(x); +} + +function transformLogn(x) { + return -Math.log(-x); +} + +function transformExpn(x) { + return -Math.exp(-x); +} + +function pow10(x) { + return isFinite(x) ? +("1e" + x) : x < 0 ? 0 : x; +} + +function powp(base) { + return base === 10 ? pow10 + : base === Math.E ? Math.exp + : x => Math.pow(base, x); +} + +function logp(base) { + return base === Math.E ? Math.log + : base === 10 && Math.log10 + || base === 2 && Math.log2 + || (base = Math.log(base), x => Math.log(x) / base); +} + +function reflect(f) { + return (x, k) => -f(-x, k); +} + +function loggish(transform) { + const scale = transform(transformLog, transformExp); + const domain = scale.domain; + let base = 10; + let logs; + let pows; + + function rescale() { + logs = logp(base), pows = powp(base); + if (domain()[0] < 0) { + logs = reflect(logs), pows = reflect(pows); + transform(transformLogn, transformExpn); + } else { + transform(transformLog, transformExp); + } + return scale; + } + + scale.base = function(_) { + return arguments.length ? (base = +_, rescale()) : base; + }; + + scale.domain = function(_) { + return arguments.length ? (domain(_), rescale()) : domain(); + }; + + scale.ticks = count => { + const d = domain(); + let u = d[0]; + let v = d[d.length - 1]; + const r = v < u; + + if (r) ([u, v] = [v, u]); + + let i = logs(u); + let j = logs(v); + let k; + let t; + const n = count == null ? 10 : +count; + let z = []; + + if (!(base % 1) && j - i < n) { + i = Math.floor(i), j = Math.ceil(j); + if (u > 0) for (; i <= j; ++i) { + for (k = 1; k < base; ++k) { + t = i < 0 ? k / pows(-i) : k * pows(i); + if (t < u) continue; + if (t > v) break; + z.push(t); + } + } else for (; i <= j; ++i) { + for (k = base - 1; k >= 1; --k) { + t = i > 0 ? k / pows(-i) : k * pows(i); + if (t < u) continue; + if (t > v) break; + z.push(t); + } + } + if (z.length * 2 < n) z = d3Array.ticks(u, v, n); + } else { + z = d3Array.ticks(i, j, Math.min(j - i, n)).map(pows); + } + return r ? z.reverse() : z; + }; + + scale.tickFormat = (count, specifier) => { + if (count == null) count = 10; + if (specifier == null) specifier = base === 10 ? "s" : ","; + if (typeof specifier !== "function") { + if (!(base % 1) && (specifier = d3Format.formatSpecifier(specifier)).precision == null) specifier.trim = true; + specifier = d3Format.format(specifier); + } + if (count === Infinity) return specifier; + const k = Math.max(1, base * count / scale.ticks().length); // TODO fast estimate? + return d => { + let i = d / pows(Math.round(logs(d))); + if (i * base < base - 0.5) i *= base; + return i <= k ? specifier(d) : ""; + }; + }; + + scale.nice = () => { + return domain(nice(domain(), { + floor: x => pows(Math.floor(logs(x))), + ceil: x => pows(Math.ceil(logs(x))) + })); + }; + + return scale; +} + +function log() { + const scale = loggish(transformer$2()).domain([1, 10]); + scale.copy = () => copy$1(scale, log()).base(scale.base()); + initRange.apply(scale, arguments); + return scale; +} + +function transformSymlog(c) { + return function(x) { + return Math.sign(x) * Math.log1p(Math.abs(x / c)); + }; +} + +function transformSymexp(c) { + return function(x) { + return Math.sign(x) * Math.expm1(Math.abs(x)) * c; + }; +} + +function symlogish(transform) { + var c = 1, scale = transform(transformSymlog(c), transformSymexp(c)); + + scale.constant = function(_) { + return arguments.length ? transform(transformSymlog(c = +_), transformSymexp(c)) : c; + }; + + return linearish(scale); +} + +function symlog() { + var scale = symlogish(transformer$2()); + + scale.copy = function() { + return copy$1(scale, symlog()).constant(scale.constant()); + }; + + return initRange.apply(scale, arguments); +} + +function transformPow(exponent) { + return function(x) { + return x < 0 ? -Math.pow(-x, exponent) : Math.pow(x, exponent); + }; +} + +function transformSqrt(x) { + return x < 0 ? -Math.sqrt(-x) : Math.sqrt(x); +} + +function transformSquare(x) { + return x < 0 ? -x * x : x * x; +} + +function powish(transform) { + var scale = transform(identity$1, identity$1), + exponent = 1; + + function rescale() { + return exponent === 1 ? transform(identity$1, identity$1) + : exponent === 0.5 ? transform(transformSqrt, transformSquare) + : transform(transformPow(exponent), transformPow(1 / exponent)); + } + + scale.exponent = function(_) { + return arguments.length ? (exponent = +_, rescale()) : exponent; + }; + + return linearish(scale); +} + +function pow() { + var scale = powish(transformer$2()); + + scale.copy = function() { + return copy$1(scale, pow()).exponent(scale.exponent()); + }; + + initRange.apply(scale, arguments); + + return scale; +} + +function sqrt() { + return pow.apply(null, arguments).exponent(0.5); +} + +function square(x) { + return Math.sign(x) * x * x; +} + +function unsquare(x) { + return Math.sign(x) * Math.sqrt(Math.abs(x)); +} + +function radial() { + var squared = continuous(), + range = [0, 1], + round = false, + unknown; + + function scale(x) { + var y = unsquare(squared(x)); + return isNaN(y) ? unknown : round ? Math.round(y) : y; + } + + scale.invert = function(y) { + return squared.invert(square(y)); + }; + + scale.domain = function(_) { + return arguments.length ? (squared.domain(_), scale) : squared.domain(); + }; + + scale.range = function(_) { + return arguments.length ? (squared.range((range = Array.from(_, number$1)).map(square)), scale) : range.slice(); + }; + + scale.rangeRound = function(_) { + return scale.range(_).round(true); + }; + + scale.round = function(_) { + return arguments.length ? (round = !!_, scale) : round; + }; + + scale.clamp = function(_) { + return arguments.length ? (squared.clamp(_), scale) : squared.clamp(); + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.copy = function() { + return radial(squared.domain(), range) + .round(round) + .clamp(squared.clamp()) + .unknown(unknown); + }; + + initRange.apply(scale, arguments); + + return linearish(scale); +} + +function quantile() { + var domain = [], + range = [], + thresholds = [], + unknown; + + function rescale() { + var i = 0, n = Math.max(1, range.length); + thresholds = new Array(n - 1); + while (++i < n) thresholds[i - 1] = d3Array.quantileSorted(domain, i / n); + return scale; + } + + function scale(x) { + return x == null || isNaN(x = +x) ? unknown : range[d3Array.bisect(thresholds, x)]; + } + + scale.invertExtent = function(y) { + var i = range.indexOf(y); + return i < 0 ? [NaN, NaN] : [ + i > 0 ? thresholds[i - 1] : domain[0], + i < thresholds.length ? thresholds[i] : domain[domain.length - 1] + ]; + }; + + scale.domain = function(_) { + if (!arguments.length) return domain.slice(); + domain = []; + for (let d of _) if (d != null && !isNaN(d = +d)) domain.push(d); + domain.sort(d3Array.ascending); + return rescale(); + }; + + scale.range = function(_) { + return arguments.length ? (range = Array.from(_), rescale()) : range.slice(); + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.quantiles = function() { + return thresholds.slice(); + }; + + scale.copy = function() { + return quantile() + .domain(domain) + .range(range) + .unknown(unknown); + }; + + return initRange.apply(scale, arguments); +} + +function quantize() { + var x0 = 0, + x1 = 1, + n = 1, + domain = [0.5], + range = [0, 1], + unknown; + + function scale(x) { + return x != null && x <= x ? range[d3Array.bisect(domain, x, 0, n)] : unknown; + } + + function rescale() { + var i = -1; + domain = new Array(n); + while (++i < n) domain[i] = ((i + 1) * x1 - (i - n) * x0) / (n + 1); + return scale; + } + + scale.domain = function(_) { + return arguments.length ? ([x0, x1] = _, x0 = +x0, x1 = +x1, rescale()) : [x0, x1]; + }; + + scale.range = function(_) { + return arguments.length ? (n = (range = Array.from(_)).length - 1, rescale()) : range.slice(); + }; + + scale.invertExtent = function(y) { + var i = range.indexOf(y); + return i < 0 ? [NaN, NaN] + : i < 1 ? [x0, domain[0]] + : i >= n ? [domain[n - 1], x1] + : [domain[i - 1], domain[i]]; + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : scale; + }; + + scale.thresholds = function() { + return domain.slice(); + }; + + scale.copy = function() { + return quantize() + .domain([x0, x1]) + .range(range) + .unknown(unknown); + }; + + return initRange.apply(linearish(scale), arguments); +} + +function threshold() { + var domain = [0.5], + range = [0, 1], + unknown, + n = 1; + + function scale(x) { + return x != null && x <= x ? range[d3Array.bisect(domain, x, 0, n)] : unknown; + } + + scale.domain = function(_) { + return arguments.length ? (domain = Array.from(_), n = Math.min(domain.length, range.length - 1), scale) : domain.slice(); + }; + + scale.range = function(_) { + return arguments.length ? (range = Array.from(_), n = Math.min(domain.length, range.length - 1), scale) : range.slice(); + }; + + scale.invertExtent = function(y) { + var i = range.indexOf(y); + return [domain[i - 1], domain[i]]; + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.copy = function() { + return threshold() + .domain(domain) + .range(range) + .unknown(unknown); + }; + + return initRange.apply(scale, arguments); +} + +function date(t) { + return new Date(t); +} + +function number(t) { + return t instanceof Date ? +t : +new Date(+t); +} + +function calendar(ticks, tickInterval, year, month, week, day, hour, minute, second, format) { + var scale = continuous(), + invert = scale.invert, + domain = scale.domain; + + var formatMillisecond = format(".%L"), + formatSecond = format(":%S"), + formatMinute = format("%I:%M"), + formatHour = format("%I %p"), + formatDay = format("%a %d"), + formatWeek = format("%b %d"), + formatMonth = format("%B"), + formatYear = format("%Y"); + + function tickFormat(date) { + return (second(date) < date ? formatMillisecond + : minute(date) < date ? formatSecond + : hour(date) < date ? formatMinute + : day(date) < date ? formatHour + : month(date) < date ? (week(date) < date ? formatDay : formatWeek) + : year(date) < date ? formatMonth + : formatYear)(date); + } + + scale.invert = function(y) { + return new Date(invert(y)); + }; + + scale.domain = function(_) { + return arguments.length ? domain(Array.from(_, number)) : domain().map(date); + }; + + scale.ticks = function(interval) { + var d = domain(); + return ticks(d[0], d[d.length - 1], interval == null ? 10 : interval); + }; + + scale.tickFormat = function(count, specifier) { + return specifier == null ? tickFormat : format(specifier); + }; + + scale.nice = function(interval) { + var d = domain(); + if (!interval || typeof interval.range !== "function") interval = tickInterval(d[0], d[d.length - 1], interval == null ? 10 : interval); + return interval ? domain(nice(d, interval)) : scale; + }; + + scale.copy = function() { + return copy$1(scale, calendar(ticks, tickInterval, year, month, week, day, hour, minute, second, format)); + }; + + return scale; +} + +function time() { + return initRange.apply(calendar(d3Time.timeTicks, d3Time.timeTickInterval, d3Time.timeYear, d3Time.timeMonth, d3Time.timeWeek, d3Time.timeDay, d3Time.timeHour, d3Time.timeMinute, d3Time.timeSecond, d3TimeFormat.timeFormat).domain([new Date(2000, 0, 1), new Date(2000, 0, 2)]), arguments); +} + +function utcTime() { + return initRange.apply(calendar(d3Time.utcTicks, d3Time.utcTickInterval, d3Time.utcYear, d3Time.utcMonth, d3Time.utcWeek, d3Time.utcDay, d3Time.utcHour, d3Time.utcMinute, d3Time.utcSecond, d3TimeFormat.utcFormat).domain([Date.UTC(2000, 0, 1), Date.UTC(2000, 0, 2)]), arguments); +} + +function transformer$1() { + var x0 = 0, + x1 = 1, + t0, + t1, + k10, + transform, + interpolator = identity$1, + clamp = false, + unknown; + + function scale(x) { + return x == null || isNaN(x = +x) ? unknown : interpolator(k10 === 0 ? 0.5 : (x = (transform(x) - t0) * k10, clamp ? Math.max(0, Math.min(1, x)) : x)); + } + + scale.domain = function(_) { + return arguments.length ? ([x0, x1] = _, t0 = transform(x0 = +x0), t1 = transform(x1 = +x1), k10 = t0 === t1 ? 0 : 1 / (t1 - t0), scale) : [x0, x1]; + }; + + scale.clamp = function(_) { + return arguments.length ? (clamp = !!_, scale) : clamp; + }; + + scale.interpolator = function(_) { + return arguments.length ? (interpolator = _, scale) : interpolator; + }; + + function range(interpolate) { + return function(_) { + var r0, r1; + return arguments.length ? ([r0, r1] = _, interpolator = interpolate(r0, r1), scale) : [interpolator(0), interpolator(1)]; + }; + } + + scale.range = range(d3Interpolate.interpolate); + + scale.rangeRound = range(d3Interpolate.interpolateRound); + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + return function(t) { + transform = t, t0 = t(x0), t1 = t(x1), k10 = t0 === t1 ? 0 : 1 / (t1 - t0); + return scale; + }; +} + +function copy(source, target) { + return target + .domain(source.domain()) + .interpolator(source.interpolator()) + .clamp(source.clamp()) + .unknown(source.unknown()); +} + +function sequential() { + var scale = linearish(transformer$1()(identity$1)); + + scale.copy = function() { + return copy(scale, sequential()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function sequentialLog() { + var scale = loggish(transformer$1()).domain([1, 10]); + + scale.copy = function() { + return copy(scale, sequentialLog()).base(scale.base()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function sequentialSymlog() { + var scale = symlogish(transformer$1()); + + scale.copy = function() { + return copy(scale, sequentialSymlog()).constant(scale.constant()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function sequentialPow() { + var scale = powish(transformer$1()); + + scale.copy = function() { + return copy(scale, sequentialPow()).exponent(scale.exponent()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function sequentialSqrt() { + return sequentialPow.apply(null, arguments).exponent(0.5); +} + +function sequentialQuantile() { + var domain = [], + interpolator = identity$1; + + function scale(x) { + if (x != null && !isNaN(x = +x)) return interpolator((d3Array.bisect(domain, x, 1) - 1) / (domain.length - 1)); + } + + scale.domain = function(_) { + if (!arguments.length) return domain.slice(); + domain = []; + for (let d of _) if (d != null && !isNaN(d = +d)) domain.push(d); + domain.sort(d3Array.ascending); + return scale; + }; + + scale.interpolator = function(_) { + return arguments.length ? (interpolator = _, scale) : interpolator; + }; + + scale.range = function() { + return domain.map((d, i) => interpolator(i / (domain.length - 1))); + }; + + scale.quantiles = function(n) { + return Array.from({length: n + 1}, (_, i) => d3Array.quantile(domain, i / n)); + }; + + scale.copy = function() { + return sequentialQuantile(interpolator).domain(domain); + }; + + return initInterpolator.apply(scale, arguments); +} + +function transformer() { + var x0 = 0, + x1 = 0.5, + x2 = 1, + s = 1, + t0, + t1, + t2, + k10, + k21, + interpolator = identity$1, + transform, + clamp = false, + unknown; + + function scale(x) { + return isNaN(x = +x) ? unknown : (x = 0.5 + ((x = +transform(x)) - t1) * (s * x < s * t1 ? k10 : k21), interpolator(clamp ? Math.max(0, Math.min(1, x)) : x)); + } + + scale.domain = function(_) { + return arguments.length ? ([x0, x1, x2] = _, t0 = transform(x0 = +x0), t1 = transform(x1 = +x1), t2 = transform(x2 = +x2), k10 = t0 === t1 ? 0 : 0.5 / (t1 - t0), k21 = t1 === t2 ? 0 : 0.5 / (t2 - t1), s = t1 < t0 ? -1 : 1, scale) : [x0, x1, x2]; + }; + + scale.clamp = function(_) { + return arguments.length ? (clamp = !!_, scale) : clamp; + }; + + scale.interpolator = function(_) { + return arguments.length ? (interpolator = _, scale) : interpolator; + }; + + function range(interpolate) { + return function(_) { + var r0, r1, r2; + return arguments.length ? ([r0, r1, r2] = _, interpolator = d3Interpolate.piecewise(interpolate, [r0, r1, r2]), scale) : [interpolator(0), interpolator(0.5), interpolator(1)]; + }; + } + + scale.range = range(d3Interpolate.interpolate); + + scale.rangeRound = range(d3Interpolate.interpolateRound); + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + return function(t) { + transform = t, t0 = t(x0), t1 = t(x1), t2 = t(x2), k10 = t0 === t1 ? 0 : 0.5 / (t1 - t0), k21 = t1 === t2 ? 0 : 0.5 / (t2 - t1), s = t1 < t0 ? -1 : 1; + return scale; + }; +} + +function diverging() { + var scale = linearish(transformer()(identity$1)); + + scale.copy = function() { + return copy(scale, diverging()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function divergingLog() { + var scale = loggish(transformer()).domain([0.1, 1, 10]); + + scale.copy = function() { + return copy(scale, divergingLog()).base(scale.base()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function divergingSymlog() { + var scale = symlogish(transformer()); + + scale.copy = function() { + return copy(scale, divergingSymlog()).constant(scale.constant()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function divergingPow() { + var scale = powish(transformer()); + + scale.copy = function() { + return copy(scale, divergingPow()).exponent(scale.exponent()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function divergingSqrt() { + return divergingPow.apply(null, arguments).exponent(0.5); +} + +exports.scaleBand = band; +exports.scaleDiverging = diverging; +exports.scaleDivergingLog = divergingLog; +exports.scaleDivergingPow = divergingPow; +exports.scaleDivergingSqrt = divergingSqrt; +exports.scaleDivergingSymlog = divergingSymlog; +exports.scaleIdentity = identity; +exports.scaleImplicit = implicit; +exports.scaleLinear = linear; +exports.scaleLog = log; +exports.scaleOrdinal = ordinal; +exports.scalePoint = point; +exports.scalePow = pow; +exports.scaleQuantile = quantile; +exports.scaleQuantize = quantize; +exports.scaleRadial = radial; +exports.scaleSequential = sequential; +exports.scaleSequentialLog = sequentialLog; +exports.scaleSequentialPow = sequentialPow; +exports.scaleSequentialQuantile = sequentialQuantile; +exports.scaleSequentialSqrt = sequentialSqrt; +exports.scaleSequentialSymlog = sequentialSymlog; +exports.scaleSqrt = sqrt; +exports.scaleSymlog = symlog; +exports.scaleThreshold = threshold; +exports.scaleTime = time; +exports.scaleUtc = utcTime; +exports.tickFormat = tickFormat; + +Object.defineProperty(exports, '__esModule', { value: true }); + +})); diff --git a/frontend/node_modules/d3-scale/dist/d3-scale.min.js b/frontend/node_modules/d3-scale/dist/d3-scale.min.js new file mode 100644 index 0000000..1612ea9 --- /dev/null +++ b/frontend/node_modules/d3-scale/dist/d3-scale.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-scale/ v4.0.2 Copyright 2010-2021 Mike Bostock +!function(n,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports,require("d3-array"),require("d3-interpolate"),require("d3-format"),require("d3-time"),require("d3-time-format")):"function"==typeof define&&define.amd?define(["exports","d3-array","d3-interpolate","d3-format","d3-time","d3-time-format"],t):t((n="undefined"!=typeof globalThis?globalThis:n||self).d3=n.d3||{},n.d3,n.d3,n.d3,n.d3,n.d3)}(this,(function(n,t,r,e,u,i){"use strict";function o(n,t){switch(arguments.length){case 0:break;case 1:this.range(n);break;default:this.range(t).domain(n)}return this}function a(n,t){switch(arguments.length){case 0:break;case 1:"function"==typeof n?this.interpolator(n):this.range(n);break;default:this.domain(n),"function"==typeof t?this.interpolator(t):this.range(t)}return this}const c=Symbol("implicit");function l(){var n=new t.InternMap,r=[],e=[],u=c;function i(t){let i=n.get(t);if(void 0===i){if(u!==c)return u;n.set(t,i=r.push(t)-1)}return e[i%e.length]}return i.domain=function(e){if(!arguments.length)return r.slice();r=[],n=new t.InternMap;for(const t of e)n.has(t)||n.set(t,r.push(t)-1);return i},i.range=function(n){return arguments.length?(e=Array.from(n),i):e.slice()},i.unknown=function(n){return arguments.length?(u=n,i):u},i.copy=function(){return l(r,e).unknown(u)},o.apply(i,arguments),i}function f(){var n,r,e=l().unknown(void 0),u=e.domain,i=e.range,a=0,c=1,s=!1,p=0,h=0,g=.5;function m(){var e=u().length,o=ct&&(r=n,n=t,t=r),f=function(r){return Math.max(n,Math.min(t,r))}),u=e>2?y:d,i=o=null,m}function m(t){return null==t||isNaN(t=+t)?e:(i||(i=u(a.map(n),c,l)))(n(f(t)))}return m.invert=function(e){return f(t((o||(o=u(c,a.map(n),r.interpolateNumber)))(e)))},m.domain=function(n){return arguments.length?(a=Array.from(n,p),s()):a.slice()},m.range=function(n){return arguments.length?(c=Array.from(n),s()):c.slice()},m.rangeRound=function(n){return c=Array.from(n),l=r.interpolateRound,s()},m.clamp=function(n){return arguments.length?(f=!!n||g,s()):f!==g},m.interpolate=function(n){return arguments.length?(l=n,s()):l},m.unknown=function(n){return arguments.length?(e=n,m):e},function(r,e){return n=r,t=e,s()}}function k(){return M()(g,g)}function w(n,r,u,i){var o,a=t.tickStep(n,r,u);switch((i=e.formatSpecifier(null==i?",f":i)).type){case"s":var c=Math.max(Math.abs(n),Math.abs(r));return null!=i.precision||isNaN(o=e.precisionPrefix(a,c))||(i.precision=o),e.formatPrefix(i,c);case"":case"e":case"g":case"p":case"r":null!=i.precision||isNaN(o=e.precisionRound(a,Math.max(Math.abs(n),Math.abs(r))))||(i.precision=o-("e"===i.type));break;case"f":case"%":null!=i.precision||isNaN(o=e.precisionFixed(a))||(i.precision=o-2*("%"===i.type))}return e.format(i)}function N(n){var r=n.domain;return n.ticks=function(n){var e=r();return t.ticks(e[0],e[e.length-1],null==n?10:n)},n.tickFormat=function(n,t){var e=r();return w(e[0],e[e.length-1],null==n?10:n,t)},n.nice=function(e){null==e&&(e=10);var u,i,o=r(),a=0,c=o.length-1,l=o[a],f=o[c],s=10;for(f0;){if((i=t.tickIncrement(l,f,e))===u)return o[a]=l,o[c]=f,r(o);if(i>0)l=Math.floor(l/i)*i,f=Math.ceil(f/i)*i;else{if(!(i<0))break;l=Math.ceil(l*i)/i,f=Math.floor(f*i)/i}u=i}return n},n}function b(n,t){var r,e=0,u=(n=n.slice()).length-1,i=n[e],o=n[u];return o-n(-t,r)}function R(n){const r=n(x,q),u=r.domain;let i,o,a=10;function c(){return i=function(n){return n===Math.E?Math.log:10===n&&Math.log10||2===n&&Math.log2||(n=Math.log(n),t=>Math.log(t)/n)}(a),o=function(n){return 10===n?D:n===Math.E?Math.exp:t=>Math.pow(n,t)}(a),u()[0]<0?(i=I(i),o=I(o),n(S,A)):n(x,q),r}return r.base=function(n){return arguments.length?(a=+n,c()):a},r.domain=function(n){return arguments.length?(u(n),c()):u()},r.ticks=n=>{const r=u();let e=r[0],c=r[r.length-1];const l=c0){for(;p<=h;++p)for(f=1;fc)break;m.push(s)}}else for(;p<=h;++p)for(f=a-1;f>=1;--f)if(s=p>0?f/o(-p):f*o(p),!(sc)break;m.push(s)}2*m.length{if(null==n&&(n=10),null==t&&(t=10===a?"s":","),"function"!=typeof t&&(a%1||null!=(t=e.formatSpecifier(t)).precision||(t.trim=!0),t=e.format(t)),n===1/0)return t;const u=Math.max(1,a*n/r.ticks().length);return n=>{let r=n/o(Math.round(i(n)));return r*au(b(u(),{floor:n=>o(Math.floor(i(n))),ceil:n=>o(Math.ceil(i(n)))})),r}function T(n){return function(t){return Math.sign(t)*Math.log1p(Math.abs(t/n))}}function O(n){return function(t){return Math.sign(t)*Math.expm1(Math.abs(t))*n}}function F(n){var t=1,r=n(T(t),O(t));return r.constant=function(r){return arguments.length?n(T(t=+r),O(t)):t},N(r)}function P(n){return function(t){return t<0?-Math.pow(-t,n):Math.pow(t,n)}}function E(n){return n<0?-Math.sqrt(-n):Math.sqrt(n)}function L(n){return n<0?-n*n:n*n}function Q(n){var t=n(g,g),r=1;function e(){return 1===r?n(g,g):.5===r?n(E,L):n(P(r),P(1/r))}return t.exponent=function(n){return arguments.length?(r=+n,e()):r},N(t)}function U(){var n=Q(M());return n.copy=function(){return v(n,U()).exponent(n.exponent())},o.apply(n,arguments),n}function Y(n){return Math.sign(n)*n*n}function j(n){return Math.sign(n)*Math.sqrt(Math.abs(n))}function B(n){return new Date(n)}function C(n){return n instanceof Date?+n:+new Date(+n)}function H(n,t,r,e,u,i,o,a,c,l){var f=k(),s=f.invert,p=f.domain,h=l(".%L"),g=l(":%S"),m=l("%I:%M"),d=l("%I %p"),y=l("%a %d"),M=l("%b %d"),w=l("%B"),N=l("%Y");function x(n){return(c(n)v(t,n()).base(t.base()),o.apply(t,arguments),t},n.scaleOrdinal=l,n.scalePoint=function(){return s(f.apply(null,arguments).paddingInner(1))},n.scalePow=U,n.scaleQuantile=function n(){var r,e=[],u=[],i=[];function a(){var n=0,r=Math.max(1,u.length);for(i=new Array(r-1);++n0?i[t-1]:e[0],t=i?[a[i-1],u]:[a[t-1],a[t]]},l.unknown=function(n){return arguments.length?(r=n,l):l},l.thresholds=function(){return a.slice()},l.copy=function(){return n().domain([e,u]).range(c).unknown(r)},o.apply(N(l),arguments)},n.scaleRadial=function n(){var t,r=k(),e=[0,1],u=!1;function i(n){var e=j(r(n));return isNaN(e)?t:u?Math.round(e):e}return i.invert=function(n){return r.invert(Y(n))},i.domain=function(n){return arguments.length?(r.domain(n),i):r.domain()},i.range=function(n){return arguments.length?(r.range((e=Array.from(n,p)).map(Y)),i):e.slice()},i.rangeRound=function(n){return i.range(n).round(!0)},i.round=function(n){return arguments.length?(u=!!n,i):u},i.clamp=function(n){return arguments.length?(r.clamp(n),i):r.clamp()},i.unknown=function(n){return arguments.length?(t=n,i):t},i.copy=function(){return n(r.domain(),e).round(u).clamp(r.clamp()).unknown(t)},o.apply(i,arguments),N(i)},n.scaleSequential=function n(){var t=N(W()(g));return t.copy=function(){return _(t,n())},a.apply(t,arguments)},n.scaleSequentialLog=function n(){var t=R(W()).domain([1,10]);return t.copy=function(){return _(t,n()).base(t.base())},a.apply(t,arguments)},n.scaleSequentialPow=z,n.scaleSequentialQuantile=function n(){var r=[],e=g;function u(n){if(null!=n&&!isNaN(n=+n))return e((t.bisect(r,n,1)-1)/(r.length-1))}return u.domain=function(n){if(!arguments.length)return r.slice();r=[];for(let t of n)null==t||isNaN(t=+t)||r.push(t);return r.sort(t.ascending),u},u.interpolator=function(n){return arguments.length?(e=n,u):e},u.range=function(){return r.map(((n,t)=>e(t/(r.length-1))))},u.quantiles=function(n){return Array.from({length:n+1},((e,u)=>t.quantile(r,u/n)))},u.copy=function(){return n(e).domain(r)},a.apply(u,arguments)},n.scaleSequentialSqrt=function(){return z.apply(null,arguments).exponent(.5)},n.scaleSequentialSymlog=function n(){var t=F(W());return t.copy=function(){return _(t,n()).constant(t.constant())},a.apply(t,arguments)},n.scaleSqrt=function(){return U.apply(null,arguments).exponent(.5)},n.scaleSymlog=function n(){var t=F(M());return t.copy=function(){return v(t,n()).constant(t.constant())},o.apply(t,arguments)},n.scaleThreshold=function n(){var r,e=[.5],u=[0,1],i=1;function a(n){return null!=n&&n<=n?u[t.bisect(e,n,0,i)]:r}return a.domain=function(n){return arguments.length?(e=Array.from(n),i=Math.min(e.length,u.length-1),a):e.slice()},a.range=function(n){return arguments.length?(u=Array.from(n),i=Math.min(e.length,u.length-1),a):u.slice()},a.invertExtent=function(n){var t=u.indexOf(n);return[e[t-1],e[t]]},a.unknown=function(n){return arguments.length?(r=n,a):r},a.copy=function(){return n().domain(e).range(u).unknown(r)},o.apply(a,arguments)},n.scaleTime=function(){return o.apply(H(u.timeTicks,u.timeTickInterval,u.timeYear,u.timeMonth,u.timeWeek,u.timeDay,u.timeHour,u.timeMinute,u.timeSecond,i.timeFormat).domain([new Date(2e3,0,1),new Date(2e3,0,2)]),arguments)},n.scaleUtc=function(){return o.apply(H(u.utcTicks,u.utcTickInterval,u.utcYear,u.utcMonth,u.utcWeek,u.utcDay,u.utcHour,u.utcMinute,u.utcSecond,i.utcFormat).domain([Date.UTC(2e3,0,1),Date.UTC(2e3,0,2)]),arguments)},n.tickFormat=w,Object.defineProperty(n,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-scale/package.json b/frontend/node_modules/d3-scale/package.json new file mode 100644 index 0000000..cd77039 --- /dev/null +++ b/frontend/node_modules/d3-scale/package.json @@ -0,0 +1,57 @@ +{ + "name": "d3-scale", + "version": "4.0.2", + "description": "Encodings that map abstract data to visual representation.", + "homepage": "https://d3js.org/d3-scale/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-scale.git" + }, + "keywords": [ + "d3", + "d3-module", + "scale", + "visualization" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "https://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-scale.min.js", + "unpkg": "dist/d3-scale.min.js", + "exports": { + "umd": "./dist/d3-scale.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "dependencies": { + "d3-array": "2.10.0 - 3", + "d3-format": "1 - 3", + "d3-interpolate": "1.2.0 - 3", + "d3-time": "2.1.1 - 3", + "d3-time-format": "2 - 4" + }, + "devDependencies": { + "d3-color": "1 - 3", + "eslint": "7", + "mocha": "9", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "TZ=America/Los_Angeles mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-scale/src/band.js b/frontend/node_modules/d3-scale/src/band.js new file mode 100644 index 0000000..88e1fbd --- /dev/null +++ b/frontend/node_modules/d3-scale/src/band.js @@ -0,0 +1,101 @@ +import {range as sequence} from "d3-array"; +import {initRange} from "./init.js"; +import ordinal from "./ordinal.js"; + +export default function band() { + var scale = ordinal().unknown(undefined), + domain = scale.domain, + ordinalRange = scale.range, + r0 = 0, + r1 = 1, + step, + bandwidth, + round = false, + paddingInner = 0, + paddingOuter = 0, + align = 0.5; + + delete scale.unknown; + + function rescale() { + var n = domain().length, + reverse = r1 < r0, + start = reverse ? r1 : r0, + stop = reverse ? r0 : r1; + step = (stop - start) / Math.max(1, n - paddingInner + paddingOuter * 2); + if (round) step = Math.floor(step); + start += (stop - start - step * (n - paddingInner)) * align; + bandwidth = step * (1 - paddingInner); + if (round) start = Math.round(start), bandwidth = Math.round(bandwidth); + var values = sequence(n).map(function(i) { return start + step * i; }); + return ordinalRange(reverse ? values.reverse() : values); + } + + scale.domain = function(_) { + return arguments.length ? (domain(_), rescale()) : domain(); + }; + + scale.range = function(_) { + return arguments.length ? ([r0, r1] = _, r0 = +r0, r1 = +r1, rescale()) : [r0, r1]; + }; + + scale.rangeRound = function(_) { + return [r0, r1] = _, r0 = +r0, r1 = +r1, round = true, rescale(); + }; + + scale.bandwidth = function() { + return bandwidth; + }; + + scale.step = function() { + return step; + }; + + scale.round = function(_) { + return arguments.length ? (round = !!_, rescale()) : round; + }; + + scale.padding = function(_) { + return arguments.length ? (paddingInner = Math.min(1, paddingOuter = +_), rescale()) : paddingInner; + }; + + scale.paddingInner = function(_) { + return arguments.length ? (paddingInner = Math.min(1, _), rescale()) : paddingInner; + }; + + scale.paddingOuter = function(_) { + return arguments.length ? (paddingOuter = +_, rescale()) : paddingOuter; + }; + + scale.align = function(_) { + return arguments.length ? (align = Math.max(0, Math.min(1, _)), rescale()) : align; + }; + + scale.copy = function() { + return band(domain(), [r0, r1]) + .round(round) + .paddingInner(paddingInner) + .paddingOuter(paddingOuter) + .align(align); + }; + + return initRange.apply(rescale(), arguments); +} + +function pointish(scale) { + var copy = scale.copy; + + scale.padding = scale.paddingOuter; + delete scale.paddingInner; + delete scale.paddingOuter; + + scale.copy = function() { + return pointish(copy()); + }; + + return scale; +} + +export function point() { + return pointish(band.apply(null, arguments).paddingInner(1)); +} diff --git a/frontend/node_modules/d3-scale/src/colors.js b/frontend/node_modules/d3-scale/src/colors.js new file mode 100644 index 0000000..b344ddb --- /dev/null +++ b/frontend/node_modules/d3-scale/src/colors.js @@ -0,0 +1,5 @@ +export default function colors(s) { + return s.match(/.{6}/g).map(function(x) { + return "#" + x; + }); +} diff --git a/frontend/node_modules/d3-scale/src/constant.js b/frontend/node_modules/d3-scale/src/constant.js new file mode 100644 index 0000000..be84fee --- /dev/null +++ b/frontend/node_modules/d3-scale/src/constant.js @@ -0,0 +1,5 @@ +export default function constants(x) { + return function() { + return x; + }; +} diff --git a/frontend/node_modules/d3-scale/src/continuous.js b/frontend/node_modules/d3-scale/src/continuous.js new file mode 100644 index 0000000..d932095 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/continuous.js @@ -0,0 +1,125 @@ +import {bisect} from "d3-array"; +import {interpolate as interpolateValue, interpolateNumber, interpolateRound} from "d3-interpolate"; +import constant from "./constant.js"; +import number from "./number.js"; + +var unit = [0, 1]; + +export function identity(x) { + return x; +} + +function normalize(a, b) { + return (b -= (a = +a)) + ? function(x) { return (x - a) / b; } + : constant(isNaN(b) ? NaN : 0.5); +} + +function clamper(a, b) { + var t; + if (a > b) t = a, a = b, b = t; + return function(x) { return Math.max(a, Math.min(b, x)); }; +} + +// normalize(a, b)(x) takes a domain value x in [a,b] and returns the corresponding parameter t in [0,1]. +// interpolate(a, b)(t) takes a parameter t in [0,1] and returns the corresponding range value x in [a,b]. +function bimap(domain, range, interpolate) { + var d0 = domain[0], d1 = domain[1], r0 = range[0], r1 = range[1]; + if (d1 < d0) d0 = normalize(d1, d0), r0 = interpolate(r1, r0); + else d0 = normalize(d0, d1), r0 = interpolate(r0, r1); + return function(x) { return r0(d0(x)); }; +} + +function polymap(domain, range, interpolate) { + var j = Math.min(domain.length, range.length) - 1, + d = new Array(j), + r = new Array(j), + i = -1; + + // Reverse descending domains. + if (domain[j] < domain[0]) { + domain = domain.slice().reverse(); + range = range.slice().reverse(); + } + + while (++i < j) { + d[i] = normalize(domain[i], domain[i + 1]); + r[i] = interpolate(range[i], range[i + 1]); + } + + return function(x) { + var i = bisect(domain, x, 1, j) - 1; + return r[i](d[i](x)); + }; +} + +export function copy(source, target) { + return target + .domain(source.domain()) + .range(source.range()) + .interpolate(source.interpolate()) + .clamp(source.clamp()) + .unknown(source.unknown()); +} + +export function transformer() { + var domain = unit, + range = unit, + interpolate = interpolateValue, + transform, + untransform, + unknown, + clamp = identity, + piecewise, + output, + input; + + function rescale() { + var n = Math.min(domain.length, range.length); + if (clamp !== identity) clamp = clamper(domain[0], domain[n - 1]); + piecewise = n > 2 ? polymap : bimap; + output = input = null; + return scale; + } + + function scale(x) { + return x == null || isNaN(x = +x) ? unknown : (output || (output = piecewise(domain.map(transform), range, interpolate)))(transform(clamp(x))); + } + + scale.invert = function(y) { + return clamp(untransform((input || (input = piecewise(range, domain.map(transform), interpolateNumber)))(y))); + }; + + scale.domain = function(_) { + return arguments.length ? (domain = Array.from(_, number), rescale()) : domain.slice(); + }; + + scale.range = function(_) { + return arguments.length ? (range = Array.from(_), rescale()) : range.slice(); + }; + + scale.rangeRound = function(_) { + return range = Array.from(_), interpolate = interpolateRound, rescale(); + }; + + scale.clamp = function(_) { + return arguments.length ? (clamp = _ ? true : identity, rescale()) : clamp !== identity; + }; + + scale.interpolate = function(_) { + return arguments.length ? (interpolate = _, rescale()) : interpolate; + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + return function(t, u) { + transform = t, untransform = u; + return rescale(); + }; +} + +export default function continuous() { + return transformer()(identity, identity); +} diff --git a/frontend/node_modules/d3-scale/src/diverging.js b/frontend/node_modules/d3-scale/src/diverging.js new file mode 100644 index 0000000..f590748 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/diverging.js @@ -0,0 +1,104 @@ +import {interpolate, interpolateRound, piecewise} from "d3-interpolate"; +import {identity} from "./continuous.js"; +import {initInterpolator} from "./init.js"; +import {linearish} from "./linear.js"; +import {loggish} from "./log.js"; +import {copy} from "./sequential.js"; +import {symlogish} from "./symlog.js"; +import {powish} from "./pow.js"; + +function transformer() { + var x0 = 0, + x1 = 0.5, + x2 = 1, + s = 1, + t0, + t1, + t2, + k10, + k21, + interpolator = identity, + transform, + clamp = false, + unknown; + + function scale(x) { + return isNaN(x = +x) ? unknown : (x = 0.5 + ((x = +transform(x)) - t1) * (s * x < s * t1 ? k10 : k21), interpolator(clamp ? Math.max(0, Math.min(1, x)) : x)); + } + + scale.domain = function(_) { + return arguments.length ? ([x0, x1, x2] = _, t0 = transform(x0 = +x0), t1 = transform(x1 = +x1), t2 = transform(x2 = +x2), k10 = t0 === t1 ? 0 : 0.5 / (t1 - t0), k21 = t1 === t2 ? 0 : 0.5 / (t2 - t1), s = t1 < t0 ? -1 : 1, scale) : [x0, x1, x2]; + }; + + scale.clamp = function(_) { + return arguments.length ? (clamp = !!_, scale) : clamp; + }; + + scale.interpolator = function(_) { + return arguments.length ? (interpolator = _, scale) : interpolator; + }; + + function range(interpolate) { + return function(_) { + var r0, r1, r2; + return arguments.length ? ([r0, r1, r2] = _, interpolator = piecewise(interpolate, [r0, r1, r2]), scale) : [interpolator(0), interpolator(0.5), interpolator(1)]; + }; + } + + scale.range = range(interpolate); + + scale.rangeRound = range(interpolateRound); + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + return function(t) { + transform = t, t0 = t(x0), t1 = t(x1), t2 = t(x2), k10 = t0 === t1 ? 0 : 0.5 / (t1 - t0), k21 = t1 === t2 ? 0 : 0.5 / (t2 - t1), s = t1 < t0 ? -1 : 1; + return scale; + }; +} + +export default function diverging() { + var scale = linearish(transformer()(identity)); + + scale.copy = function() { + return copy(scale, diverging()); + }; + + return initInterpolator.apply(scale, arguments); +} + +export function divergingLog() { + var scale = loggish(transformer()).domain([0.1, 1, 10]); + + scale.copy = function() { + return copy(scale, divergingLog()).base(scale.base()); + }; + + return initInterpolator.apply(scale, arguments); +} + +export function divergingSymlog() { + var scale = symlogish(transformer()); + + scale.copy = function() { + return copy(scale, divergingSymlog()).constant(scale.constant()); + }; + + return initInterpolator.apply(scale, arguments); +} + +export function divergingPow() { + var scale = powish(transformer()); + + scale.copy = function() { + return copy(scale, divergingPow()).exponent(scale.exponent()); + }; + + return initInterpolator.apply(scale, arguments); +} + +export function divergingSqrt() { + return divergingPow.apply(null, arguments).exponent(0.5); +} diff --git a/frontend/node_modules/d3-scale/src/identity.js b/frontend/node_modules/d3-scale/src/identity.js new file mode 100644 index 0000000..e1d1da7 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/identity.js @@ -0,0 +1,28 @@ +import {linearish} from "./linear.js"; +import number from "./number.js"; + +export default function identity(domain) { + var unknown; + + function scale(x) { + return x == null || isNaN(x = +x) ? unknown : x; + } + + scale.invert = scale; + + scale.domain = scale.range = function(_) { + return arguments.length ? (domain = Array.from(_, number), scale) : domain.slice(); + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.copy = function() { + return identity(domain).unknown(unknown); + }; + + domain = arguments.length ? Array.from(domain, number) : [0, 1]; + + return linearish(scale); +} diff --git a/frontend/node_modules/d3-scale/src/index.js b/frontend/node_modules/d3-scale/src/index.js new file mode 100644 index 0000000..510103c --- /dev/null +++ b/frontend/node_modules/d3-scale/src/index.js @@ -0,0 +1,78 @@ +export { + default as scaleBand, + point as scalePoint +} from "./band.js"; + +export { + default as scaleIdentity +} from "./identity.js"; + +export { + default as scaleLinear +} from "./linear.js"; + +export { + default as scaleLog +} from "./log.js"; + +export { + default as scaleSymlog +} from "./symlog.js"; + +export { + default as scaleOrdinal, + implicit as scaleImplicit +} from "./ordinal.js"; + +export { + default as scalePow, + sqrt as scaleSqrt +} from "./pow.js"; + +export { + default as scaleRadial +} from "./radial.js"; + +export { + default as scaleQuantile +} from "./quantile.js"; + +export { + default as scaleQuantize +} from "./quantize.js"; + +export { + default as scaleThreshold +} from "./threshold.js"; + +export { + default as scaleTime +} from "./time.js"; + +export { + default as scaleUtc +} from "./utcTime.js"; + +export { + default as scaleSequential, + sequentialLog as scaleSequentialLog, + sequentialPow as scaleSequentialPow, + sequentialSqrt as scaleSequentialSqrt, + sequentialSymlog as scaleSequentialSymlog +} from "./sequential.js"; + +export { + default as scaleSequentialQuantile +} from "./sequentialQuantile.js"; + +export { + default as scaleDiverging, + divergingLog as scaleDivergingLog, + divergingPow as scaleDivergingPow, + divergingSqrt as scaleDivergingSqrt, + divergingSymlog as scaleDivergingSymlog +} from "./diverging.js"; + +export { + default as tickFormat +} from "./tickFormat.js"; diff --git a/frontend/node_modules/d3-scale/src/init.js b/frontend/node_modules/d3-scale/src/init.js new file mode 100644 index 0000000..61f51a0 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/init.js @@ -0,0 +1,26 @@ +export function initRange(domain, range) { + switch (arguments.length) { + case 0: break; + case 1: this.range(domain); break; + default: this.range(range).domain(domain); break; + } + return this; +} + +export function initInterpolator(domain, interpolator) { + switch (arguments.length) { + case 0: break; + case 1: { + if (typeof domain === "function") this.interpolator(domain); + else this.range(domain); + break; + } + default: { + this.domain(domain); + if (typeof interpolator === "function") this.interpolator(interpolator); + else this.range(interpolator); + break; + } + } + return this; +} diff --git a/frontend/node_modules/d3-scale/src/linear.js b/frontend/node_modules/d3-scale/src/linear.js new file mode 100644 index 0000000..3617d32 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/linear.js @@ -0,0 +1,70 @@ +import {ticks, tickIncrement} from "d3-array"; +import continuous, {copy} from "./continuous.js"; +import {initRange} from "./init.js"; +import tickFormat from "./tickFormat.js"; + +export function linearish(scale) { + var domain = scale.domain; + + scale.ticks = function(count) { + var d = domain(); + return ticks(d[0], d[d.length - 1], count == null ? 10 : count); + }; + + scale.tickFormat = function(count, specifier) { + var d = domain(); + return tickFormat(d[0], d[d.length - 1], count == null ? 10 : count, specifier); + }; + + scale.nice = function(count) { + if (count == null) count = 10; + + var d = domain(); + var i0 = 0; + var i1 = d.length - 1; + var start = d[i0]; + var stop = d[i1]; + var prestep; + var step; + var maxIter = 10; + + if (stop < start) { + step = start, start = stop, stop = step; + step = i0, i0 = i1, i1 = step; + } + + while (maxIter-- > 0) { + step = tickIncrement(start, stop, count); + if (step === prestep) { + d[i0] = start + d[i1] = stop + return domain(d); + } else if (step > 0) { + start = Math.floor(start / step) * step; + stop = Math.ceil(stop / step) * step; + } else if (step < 0) { + start = Math.ceil(start * step) / step; + stop = Math.floor(stop * step) / step; + } else { + break; + } + prestep = step; + } + + return scale; + }; + + return scale; +} + +export default function linear() { + var scale = continuous(); + + scale.copy = function() { + return copy(scale, linear()); + }; + + initRange.apply(scale, arguments); + + return linearish(scale); +} diff --git a/frontend/node_modules/d3-scale/src/log.js b/frontend/node_modules/d3-scale/src/log.js new file mode 100644 index 0000000..170cd69 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/log.js @@ -0,0 +1,140 @@ +import {ticks} from "d3-array"; +import {format, formatSpecifier} from "d3-format"; +import nice from "./nice.js"; +import {copy, transformer} from "./continuous.js"; +import {initRange} from "./init.js"; + +function transformLog(x) { + return Math.log(x); +} + +function transformExp(x) { + return Math.exp(x); +} + +function transformLogn(x) { + return -Math.log(-x); +} + +function transformExpn(x) { + return -Math.exp(-x); +} + +function pow10(x) { + return isFinite(x) ? +("1e" + x) : x < 0 ? 0 : x; +} + +function powp(base) { + return base === 10 ? pow10 + : base === Math.E ? Math.exp + : x => Math.pow(base, x); +} + +function logp(base) { + return base === Math.E ? Math.log + : base === 10 && Math.log10 + || base === 2 && Math.log2 + || (base = Math.log(base), x => Math.log(x) / base); +} + +function reflect(f) { + return (x, k) => -f(-x, k); +} + +export function loggish(transform) { + const scale = transform(transformLog, transformExp); + const domain = scale.domain; + let base = 10; + let logs; + let pows; + + function rescale() { + logs = logp(base), pows = powp(base); + if (domain()[0] < 0) { + logs = reflect(logs), pows = reflect(pows); + transform(transformLogn, transformExpn); + } else { + transform(transformLog, transformExp); + } + return scale; + } + + scale.base = function(_) { + return arguments.length ? (base = +_, rescale()) : base; + }; + + scale.domain = function(_) { + return arguments.length ? (domain(_), rescale()) : domain(); + }; + + scale.ticks = count => { + const d = domain(); + let u = d[0]; + let v = d[d.length - 1]; + const r = v < u; + + if (r) ([u, v] = [v, u]); + + let i = logs(u); + let j = logs(v); + let k; + let t; + const n = count == null ? 10 : +count; + let z = []; + + if (!(base % 1) && j - i < n) { + i = Math.floor(i), j = Math.ceil(j); + if (u > 0) for (; i <= j; ++i) { + for (k = 1; k < base; ++k) { + t = i < 0 ? k / pows(-i) : k * pows(i); + if (t < u) continue; + if (t > v) break; + z.push(t); + } + } else for (; i <= j; ++i) { + for (k = base - 1; k >= 1; --k) { + t = i > 0 ? k / pows(-i) : k * pows(i); + if (t < u) continue; + if (t > v) break; + z.push(t); + } + } + if (z.length * 2 < n) z = ticks(u, v, n); + } else { + z = ticks(i, j, Math.min(j - i, n)).map(pows); + } + return r ? z.reverse() : z; + }; + + scale.tickFormat = (count, specifier) => { + if (count == null) count = 10; + if (specifier == null) specifier = base === 10 ? "s" : ","; + if (typeof specifier !== "function") { + if (!(base % 1) && (specifier = formatSpecifier(specifier)).precision == null) specifier.trim = true; + specifier = format(specifier); + } + if (count === Infinity) return specifier; + const k = Math.max(1, base * count / scale.ticks().length); // TODO fast estimate? + return d => { + let i = d / pows(Math.round(logs(d))); + if (i * base < base - 0.5) i *= base; + return i <= k ? specifier(d) : ""; + }; + }; + + scale.nice = () => { + return domain(nice(domain(), { + floor: x => pows(Math.floor(logs(x))), + ceil: x => pows(Math.ceil(logs(x))) + })); + }; + + return scale; +} + +export default function log() { + const scale = loggish(transformer()).domain([1, 10]); + scale.copy = () => copy(scale, log()).base(scale.base()); + initRange.apply(scale, arguments); + return scale; +} diff --git a/frontend/node_modules/d3-scale/src/nice.js b/frontend/node_modules/d3-scale/src/nice.js new file mode 100644 index 0000000..a44e601 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/nice.js @@ -0,0 +1,18 @@ +export default function nice(domain, interval) { + domain = domain.slice(); + + var i0 = 0, + i1 = domain.length - 1, + x0 = domain[i0], + x1 = domain[i1], + t; + + if (x1 < x0) { + t = i0, i0 = i1, i1 = t; + t = x0, x0 = x1, x1 = t; + } + + domain[i0] = interval.floor(x0); + domain[i1] = interval.ceil(x1); + return domain; +} diff --git a/frontend/node_modules/d3-scale/src/number.js b/frontend/node_modules/d3-scale/src/number.js new file mode 100644 index 0000000..d185907 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/number.js @@ -0,0 +1,3 @@ +export default function number(x) { + return +x; +} diff --git a/frontend/node_modules/d3-scale/src/ordinal.js b/frontend/node_modules/d3-scale/src/ordinal.js new file mode 100644 index 0000000..7415280 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/ordinal.js @@ -0,0 +1,46 @@ +import {InternMap} from "d3-array"; +import {initRange} from "./init.js"; + +export const implicit = Symbol("implicit"); + +export default function ordinal() { + var index = new InternMap(), + domain = [], + range = [], + unknown = implicit; + + function scale(d) { + let i = index.get(d); + if (i === undefined) { + if (unknown !== implicit) return unknown; + index.set(d, i = domain.push(d) - 1); + } + return range[i % range.length]; + } + + scale.domain = function(_) { + if (!arguments.length) return domain.slice(); + domain = [], index = new InternMap(); + for (const value of _) { + if (index.has(value)) continue; + index.set(value, domain.push(value) - 1); + } + return scale; + }; + + scale.range = function(_) { + return arguments.length ? (range = Array.from(_), scale) : range.slice(); + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.copy = function() { + return ordinal(domain, range).unknown(unknown); + }; + + initRange.apply(scale, arguments); + + return scale; +} diff --git a/frontend/node_modules/d3-scale/src/pow.js b/frontend/node_modules/d3-scale/src/pow.js new file mode 100644 index 0000000..8146f1c --- /dev/null +++ b/frontend/node_modules/d3-scale/src/pow.js @@ -0,0 +1,50 @@ +import {linearish} from "./linear.js"; +import {copy, identity, transformer} from "./continuous.js"; +import {initRange} from "./init.js"; + +function transformPow(exponent) { + return function(x) { + return x < 0 ? -Math.pow(-x, exponent) : Math.pow(x, exponent); + }; +} + +function transformSqrt(x) { + return x < 0 ? -Math.sqrt(-x) : Math.sqrt(x); +} + +function transformSquare(x) { + return x < 0 ? -x * x : x * x; +} + +export function powish(transform) { + var scale = transform(identity, identity), + exponent = 1; + + function rescale() { + return exponent === 1 ? transform(identity, identity) + : exponent === 0.5 ? transform(transformSqrt, transformSquare) + : transform(transformPow(exponent), transformPow(1 / exponent)); + } + + scale.exponent = function(_) { + return arguments.length ? (exponent = +_, rescale()) : exponent; + }; + + return linearish(scale); +} + +export default function pow() { + var scale = powish(transformer()); + + scale.copy = function() { + return copy(scale, pow()).exponent(scale.exponent()); + }; + + initRange.apply(scale, arguments); + + return scale; +} + +export function sqrt() { + return pow.apply(null, arguments).exponent(0.5); +} diff --git a/frontend/node_modules/d3-scale/src/quantile.js b/frontend/node_modules/d3-scale/src/quantile.js new file mode 100644 index 0000000..303f935 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/quantile.js @@ -0,0 +1,57 @@ +import {ascending, bisect, quantileSorted as threshold} from "d3-array"; +import {initRange} from "./init.js"; + +export default function quantile() { + var domain = [], + range = [], + thresholds = [], + unknown; + + function rescale() { + var i = 0, n = Math.max(1, range.length); + thresholds = new Array(n - 1); + while (++i < n) thresholds[i - 1] = threshold(domain, i / n); + return scale; + } + + function scale(x) { + return x == null || isNaN(x = +x) ? unknown : range[bisect(thresholds, x)]; + } + + scale.invertExtent = function(y) { + var i = range.indexOf(y); + return i < 0 ? [NaN, NaN] : [ + i > 0 ? thresholds[i - 1] : domain[0], + i < thresholds.length ? thresholds[i] : domain[domain.length - 1] + ]; + }; + + scale.domain = function(_) { + if (!arguments.length) return domain.slice(); + domain = []; + for (let d of _) if (d != null && !isNaN(d = +d)) domain.push(d); + domain.sort(ascending); + return rescale(); + }; + + scale.range = function(_) { + return arguments.length ? (range = Array.from(_), rescale()) : range.slice(); + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.quantiles = function() { + return thresholds.slice(); + }; + + scale.copy = function() { + return quantile() + .domain(domain) + .range(range) + .unknown(unknown); + }; + + return initRange.apply(scale, arguments); +} diff --git a/frontend/node_modules/d3-scale/src/quantize.js b/frontend/node_modules/d3-scale/src/quantize.js new file mode 100644 index 0000000..0f54003 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/quantize.js @@ -0,0 +1,56 @@ +import {bisect} from "d3-array"; +import {linearish} from "./linear.js"; +import {initRange} from "./init.js"; + +export default function quantize() { + var x0 = 0, + x1 = 1, + n = 1, + domain = [0.5], + range = [0, 1], + unknown; + + function scale(x) { + return x != null && x <= x ? range[bisect(domain, x, 0, n)] : unknown; + } + + function rescale() { + var i = -1; + domain = new Array(n); + while (++i < n) domain[i] = ((i + 1) * x1 - (i - n) * x0) / (n + 1); + return scale; + } + + scale.domain = function(_) { + return arguments.length ? ([x0, x1] = _, x0 = +x0, x1 = +x1, rescale()) : [x0, x1]; + }; + + scale.range = function(_) { + return arguments.length ? (n = (range = Array.from(_)).length - 1, rescale()) : range.slice(); + }; + + scale.invertExtent = function(y) { + var i = range.indexOf(y); + return i < 0 ? [NaN, NaN] + : i < 1 ? [x0, domain[0]] + : i >= n ? [domain[n - 1], x1] + : [domain[i - 1], domain[i]]; + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : scale; + }; + + scale.thresholds = function() { + return domain.slice(); + }; + + scale.copy = function() { + return quantize() + .domain([x0, x1]) + .range(range) + .unknown(unknown); + }; + + return initRange.apply(linearish(scale), arguments); +} diff --git a/frontend/node_modules/d3-scale/src/radial.js b/frontend/node_modules/d3-scale/src/radial.js new file mode 100644 index 0000000..5c00cc6 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/radial.js @@ -0,0 +1,63 @@ +import continuous from "./continuous.js"; +import {initRange} from "./init.js"; +import {linearish} from "./linear.js"; +import number from "./number.js"; + +function square(x) { + return Math.sign(x) * x * x; +} + +function unsquare(x) { + return Math.sign(x) * Math.sqrt(Math.abs(x)); +} + +export default function radial() { + var squared = continuous(), + range = [0, 1], + round = false, + unknown; + + function scale(x) { + var y = unsquare(squared(x)); + return isNaN(y) ? unknown : round ? Math.round(y) : y; + } + + scale.invert = function(y) { + return squared.invert(square(y)); + }; + + scale.domain = function(_) { + return arguments.length ? (squared.domain(_), scale) : squared.domain(); + }; + + scale.range = function(_) { + return arguments.length ? (squared.range((range = Array.from(_, number)).map(square)), scale) : range.slice(); + }; + + scale.rangeRound = function(_) { + return scale.range(_).round(true); + }; + + scale.round = function(_) { + return arguments.length ? (round = !!_, scale) : round; + }; + + scale.clamp = function(_) { + return arguments.length ? (squared.clamp(_), scale) : squared.clamp(); + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.copy = function() { + return radial(squared.domain(), range) + .round(round) + .clamp(squared.clamp()) + .unknown(unknown); + }; + + initRange.apply(scale, arguments); + + return linearish(scale); +} diff --git a/frontend/node_modules/d3-scale/src/sequential.js b/frontend/node_modules/d3-scale/src/sequential.js new file mode 100644 index 0000000..547dc40 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/sequential.js @@ -0,0 +1,107 @@ +import {interpolate, interpolateRound} from "d3-interpolate"; +import {identity} from "./continuous.js"; +import {initInterpolator} from "./init.js"; +import {linearish} from "./linear.js"; +import {loggish} from "./log.js"; +import {symlogish} from "./symlog.js"; +import {powish} from "./pow.js"; + +function transformer() { + var x0 = 0, + x1 = 1, + t0, + t1, + k10, + transform, + interpolator = identity, + clamp = false, + unknown; + + function scale(x) { + return x == null || isNaN(x = +x) ? unknown : interpolator(k10 === 0 ? 0.5 : (x = (transform(x) - t0) * k10, clamp ? Math.max(0, Math.min(1, x)) : x)); + } + + scale.domain = function(_) { + return arguments.length ? ([x0, x1] = _, t0 = transform(x0 = +x0), t1 = transform(x1 = +x1), k10 = t0 === t1 ? 0 : 1 / (t1 - t0), scale) : [x0, x1]; + }; + + scale.clamp = function(_) { + return arguments.length ? (clamp = !!_, scale) : clamp; + }; + + scale.interpolator = function(_) { + return arguments.length ? (interpolator = _, scale) : interpolator; + }; + + function range(interpolate) { + return function(_) { + var r0, r1; + return arguments.length ? ([r0, r1] = _, interpolator = interpolate(r0, r1), scale) : [interpolator(0), interpolator(1)]; + }; + } + + scale.range = range(interpolate); + + scale.rangeRound = range(interpolateRound); + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + return function(t) { + transform = t, t0 = t(x0), t1 = t(x1), k10 = t0 === t1 ? 0 : 1 / (t1 - t0); + return scale; + }; +} + +export function copy(source, target) { + return target + .domain(source.domain()) + .interpolator(source.interpolator()) + .clamp(source.clamp()) + .unknown(source.unknown()); +} + +export default function sequential() { + var scale = linearish(transformer()(identity)); + + scale.copy = function() { + return copy(scale, sequential()); + }; + + return initInterpolator.apply(scale, arguments); +} + +export function sequentialLog() { + var scale = loggish(transformer()).domain([1, 10]); + + scale.copy = function() { + return copy(scale, sequentialLog()).base(scale.base()); + }; + + return initInterpolator.apply(scale, arguments); +} + +export function sequentialSymlog() { + var scale = symlogish(transformer()); + + scale.copy = function() { + return copy(scale, sequentialSymlog()).constant(scale.constant()); + }; + + return initInterpolator.apply(scale, arguments); +} + +export function sequentialPow() { + var scale = powish(transformer()); + + scale.copy = function() { + return copy(scale, sequentialPow()).exponent(scale.exponent()); + }; + + return initInterpolator.apply(scale, arguments); +} + +export function sequentialSqrt() { + return sequentialPow.apply(null, arguments).exponent(0.5); +} diff --git a/frontend/node_modules/d3-scale/src/sequentialQuantile.js b/frontend/node_modules/d3-scale/src/sequentialQuantile.js new file mode 100644 index 0000000..7437e55 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/sequentialQuantile.js @@ -0,0 +1,38 @@ +import {ascending, bisect, quantile} from "d3-array"; +import {identity} from "./continuous.js"; +import {initInterpolator} from "./init.js"; + +export default function sequentialQuantile() { + var domain = [], + interpolator = identity; + + function scale(x) { + if (x != null && !isNaN(x = +x)) return interpolator((bisect(domain, x, 1) - 1) / (domain.length - 1)); + } + + scale.domain = function(_) { + if (!arguments.length) return domain.slice(); + domain = []; + for (let d of _) if (d != null && !isNaN(d = +d)) domain.push(d); + domain.sort(ascending); + return scale; + }; + + scale.interpolator = function(_) { + return arguments.length ? (interpolator = _, scale) : interpolator; + }; + + scale.range = function() { + return domain.map((d, i) => interpolator(i / (domain.length - 1))); + }; + + scale.quantiles = function(n) { + return Array.from({length: n + 1}, (_, i) => quantile(domain, i / n)); + }; + + scale.copy = function() { + return sequentialQuantile(interpolator).domain(domain); + }; + + return initInterpolator.apply(scale, arguments); +} diff --git a/frontend/node_modules/d3-scale/src/symlog.js b/frontend/node_modules/d3-scale/src/symlog.js new file mode 100644 index 0000000..125fa7b --- /dev/null +++ b/frontend/node_modules/d3-scale/src/symlog.js @@ -0,0 +1,35 @@ +import {linearish} from "./linear.js"; +import {copy, transformer} from "./continuous.js"; +import {initRange} from "./init.js"; + +function transformSymlog(c) { + return function(x) { + return Math.sign(x) * Math.log1p(Math.abs(x / c)); + }; +} + +function transformSymexp(c) { + return function(x) { + return Math.sign(x) * Math.expm1(Math.abs(x)) * c; + }; +} + +export function symlogish(transform) { + var c = 1, scale = transform(transformSymlog(c), transformSymexp(c)); + + scale.constant = function(_) { + return arguments.length ? transform(transformSymlog(c = +_), transformSymexp(c)) : c; + }; + + return linearish(scale); +} + +export default function symlog() { + var scale = symlogish(transformer()); + + scale.copy = function() { + return copy(scale, symlog()).constant(scale.constant()); + }; + + return initRange.apply(scale, arguments); +} diff --git a/frontend/node_modules/d3-scale/src/threshold.js b/frontend/node_modules/d3-scale/src/threshold.js new file mode 100644 index 0000000..bbdbe39 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/threshold.js @@ -0,0 +1,39 @@ +import {bisect} from "d3-array"; +import {initRange} from "./init.js"; + +export default function threshold() { + var domain = [0.5], + range = [0, 1], + unknown, + n = 1; + + function scale(x) { + return x != null && x <= x ? range[bisect(domain, x, 0, n)] : unknown; + } + + scale.domain = function(_) { + return arguments.length ? (domain = Array.from(_), n = Math.min(domain.length, range.length - 1), scale) : domain.slice(); + }; + + scale.range = function(_) { + return arguments.length ? (range = Array.from(_), n = Math.min(domain.length, range.length - 1), scale) : range.slice(); + }; + + scale.invertExtent = function(y) { + var i = range.indexOf(y); + return [domain[i - 1], domain[i]]; + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.copy = function() { + return threshold() + .domain(domain) + .range(range) + .unknown(unknown); + }; + + return initRange.apply(scale, arguments); +} diff --git a/frontend/node_modules/d3-scale/src/tickFormat.js b/frontend/node_modules/d3-scale/src/tickFormat.js new file mode 100644 index 0000000..15fc54e --- /dev/null +++ b/frontend/node_modules/d3-scale/src/tickFormat.js @@ -0,0 +1,29 @@ +import {tickStep} from "d3-array"; +import {format, formatPrefix, formatSpecifier, precisionFixed, precisionPrefix, precisionRound} from "d3-format"; + +export default function tickFormat(start, stop, count, specifier) { + var step = tickStep(start, stop, count), + precision; + specifier = formatSpecifier(specifier == null ? ",f" : specifier); + switch (specifier.type) { + case "s": { + var value = Math.max(Math.abs(start), Math.abs(stop)); + if (specifier.precision == null && !isNaN(precision = precisionPrefix(step, value))) specifier.precision = precision; + return formatPrefix(specifier, value); + } + case "": + case "e": + case "g": + case "p": + case "r": { + if (specifier.precision == null && !isNaN(precision = precisionRound(step, Math.max(Math.abs(start), Math.abs(stop))))) specifier.precision = precision - (specifier.type === "e"); + break; + } + case "f": + case "%": { + if (specifier.precision == null && !isNaN(precision = precisionFixed(step))) specifier.precision = precision - (specifier.type === "%") * 2; + break; + } + } + return format(specifier); +} diff --git a/frontend/node_modules/d3-scale/src/time.js b/frontend/node_modules/d3-scale/src/time.js new file mode 100644 index 0000000..d1ea678 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/time.js @@ -0,0 +1,71 @@ +import {timeYear, timeMonth, timeWeek, timeDay, timeHour, timeMinute, timeSecond, timeTicks, timeTickInterval} from "d3-time"; +import {timeFormat} from "d3-time-format"; +import continuous, {copy} from "./continuous.js"; +import {initRange} from "./init.js"; +import nice from "./nice.js"; + +function date(t) { + return new Date(t); +} + +function number(t) { + return t instanceof Date ? +t : +new Date(+t); +} + +export function calendar(ticks, tickInterval, year, month, week, day, hour, minute, second, format) { + var scale = continuous(), + invert = scale.invert, + domain = scale.domain; + + var formatMillisecond = format(".%L"), + formatSecond = format(":%S"), + formatMinute = format("%I:%M"), + formatHour = format("%I %p"), + formatDay = format("%a %d"), + formatWeek = format("%b %d"), + formatMonth = format("%B"), + formatYear = format("%Y"); + + function tickFormat(date) { + return (second(date) < date ? formatMillisecond + : minute(date) < date ? formatSecond + : hour(date) < date ? formatMinute + : day(date) < date ? formatHour + : month(date) < date ? (week(date) < date ? formatDay : formatWeek) + : year(date) < date ? formatMonth + : formatYear)(date); + } + + scale.invert = function(y) { + return new Date(invert(y)); + }; + + scale.domain = function(_) { + return arguments.length ? domain(Array.from(_, number)) : domain().map(date); + }; + + scale.ticks = function(interval) { + var d = domain(); + return ticks(d[0], d[d.length - 1], interval == null ? 10 : interval); + }; + + scale.tickFormat = function(count, specifier) { + return specifier == null ? tickFormat : format(specifier); + }; + + scale.nice = function(interval) { + var d = domain(); + if (!interval || typeof interval.range !== "function") interval = tickInterval(d[0], d[d.length - 1], interval == null ? 10 : interval); + return interval ? domain(nice(d, interval)) : scale; + }; + + scale.copy = function() { + return copy(scale, calendar(ticks, tickInterval, year, month, week, day, hour, minute, second, format)); + }; + + return scale; +} + +export default function time() { + return initRange.apply(calendar(timeTicks, timeTickInterval, timeYear, timeMonth, timeWeek, timeDay, timeHour, timeMinute, timeSecond, timeFormat).domain([new Date(2000, 0, 1), new Date(2000, 0, 2)]), arguments); +} diff --git a/frontend/node_modules/d3-scale/src/utcTime.js b/frontend/node_modules/d3-scale/src/utcTime.js new file mode 100644 index 0000000..9741716 --- /dev/null +++ b/frontend/node_modules/d3-scale/src/utcTime.js @@ -0,0 +1,8 @@ +import {utcYear, utcMonth, utcWeek, utcDay, utcHour, utcMinute, utcSecond, utcTicks, utcTickInterval} from "d3-time"; +import {utcFormat} from "d3-time-format"; +import {calendar} from "./time.js"; +import {initRange} from "./init.js"; + +export default function utcTime() { + return initRange.apply(calendar(utcTicks, utcTickInterval, utcYear, utcMonth, utcWeek, utcDay, utcHour, utcMinute, utcSecond, utcFormat).domain([Date.UTC(2000, 0, 1), Date.UTC(2000, 0, 2)]), arguments); +} diff --git a/frontend/node_modules/d3-selection/LICENSE b/frontend/node_modules/d3-selection/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-selection/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-selection/README.md b/frontend/node_modules/d3-selection/README.md new file mode 100644 index 0000000..b8513c6 --- /dev/null +++ b/frontend/node_modules/d3-selection/README.md @@ -0,0 +1,863 @@ +# d3-selection + +Selections allow powerful data-driven transformation of the document object model (DOM): set [attributes](#selection_attr), [styles](#selection_style), [properties](#selection_property), [HTML](#selection_html) or [text](#selection_text) content, and more. Using the [data join](#joining-data)’s [enter](#selection_enter) and [exit](#selection_enter) selections, you can also [add](#selection_append) or [remove](#selection_remove) elements to correspond to data. + +Selection methods typically return the current selection, or a new selection, allowing the concise application of multiple operations on a given selection via method chaining. For example, to set the class and color style of all paragraph elements in the current document: + +```js +d3.selectAll("p") + .attr("class", "graf") + .style("color", "red"); +``` + +This is equivalent to: + +```js +const p = d3.selectAll("p"); +p.attr("class", "graf"); +p.style("color", "red"); +``` + +By convention, selection methods that return the current selection use *four* spaces of indent, while methods that return a new selection use only *two*. This helps reveal changes of context by making them stick out of the chain: + +```js +d3.select("body") + .append("svg") + .attr("width", 960) + .attr("height", 500) + .append("g") + .attr("transform", "translate(20,20)") + .append("rect") + .attr("width", 920) + .attr("height", 460); +``` + +Selections are immutable. All selection methods that affect which elements are selected (or their order) return a new selection rather than modifying the current selection. However, note that elements are necessarily mutable, as selections drive transformations of the document! + +For more, see [the d3-selection collection on Observable](https://observablehq.com/collection/@d3/d3-selection). + +## Installing + +If you use npm, `npm install d3-selection`. You can also download the [latest release on GitHub](https://github.com/d3/d3-selection/releases/latest). For vanilla HTML in modern browsers, import d3-selection from Skypack: + +```html + +``` + +For legacy environments, you can load d3-selection’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +[Try d3-selection in your browser.](https://observablehq.com/collection/@d3/d3-selection) + +## API Reference + +* [Selecting Elements](#selecting-elements) +* [Modifying Elements](#modifying-elements) +* [Joining Data](#joining-data) +* [Handling Events](#handling-events) +* [Control Flow](#control-flow) +* [Local Variables](#local-variables) +* [Namespaces](#namespaces) + +### Selecting Elements + +Selection methods accept [W3C selector strings](http://www.w3.org/TR/selectors-api/) such as `.fancy` to select elements with the class *fancy*, or `div` to select DIV elements. Selection methods come in two forms: select and selectAll: the former selects only the first matching element, while the latter selects all matching elements in document order. The top-level selection methods, [d3.select](#select) and [d3.selectAll](#selectAll), query the entire document; the subselection methods, [*selection*.select](#selection_select) and [*selection*.selectAll](#selection_selectAll), restrict selection to descendants of the selected elements. + +# d3.selection() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/index.js) + +[Selects](#select) the root element, `document.documentElement`. This function can also be used to test for selections (`instanceof d3.selection`) or to extend the selection prototype. For example, to add a method to check checkboxes: + +```js +d3.selection.prototype.checked = function(value) { + return arguments.length < 1 + ? this.property("checked") + : this.property("checked", !!value); +}; +``` + +And then to use: + +```js +d3.selectAll("input[type=checkbox]").checked(true); +``` + +# d3.select(selector) · [Source](https://github.com/d3/d3-selection/blob/master/src/select.js) + +Selects the first element that matches the specified *selector* string. If no elements match the *selector*, returns an empty selection. If multiple elements match the *selector*, only the first matching element (in document order) will be selected. For example, to select the first anchor element: + +```js +const anchor = d3.select("a"); +``` + +If the *selector* is not a string, instead selects the specified node; this is useful if you already have a reference to a node, such as `this` within an event listener or a global such as `document.body`. For example, to make a clicked paragraph red: + +```js +d3.selectAll("p").on("click", function(event) { + d3.select(this).style("color", "red"); +}); +``` + +# d3.selectAll(selector) · [Source](https://github.com/d3/d3-selection/blob/master/src/selectAll.js) + +Selects all elements that match the specified *selector* string. The elements will be selected in document order (top-to-bottom). If no elements in the document match the *selector*, or if the *selector* is null or undefined, returns an empty selection. For example, to select all paragraphs: + +```js +const paragraph = d3.selectAll("p"); +``` + +If the *selector* is not a string, instead selects the specified array of nodes; this is useful if you already have a reference to nodes, such as `this.childNodes` within an event listener or a global such as `document.links`. The nodes may instead be an iterable, or a pseudo-array such as a NodeList. For example, to color all links red: + +```js +d3.selectAll(document.links).style("color", "red"); +``` + +# selection.select(selector) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/select.js) + +For each selected element, selects the first descendant element that matches the specified *selector* string. If no element matches the specified selector for the current element, the element at the current index will be null in the returned selection. (If the *selector* is null, every element in the returned selection will be null, resulting in an empty selection.) If the current element has associated data, this data is propagated to the corresponding selected element. If multiple elements match the selector, only the first matching element in document order is selected. For example, to select the first bold element in every paragraph: + +```js +const b = d3.selectAll("p").select("b"); +``` + +If the *selector* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). It must return an element, or null if there is no matching element. For example, to select the previous sibling of each paragraph: + +```js +const previous = d3.selectAll("p").select(function() { + return this.previousElementSibling; +}); +``` + +Unlike [*selection*.selectAll](#selection_selectAll), *selection*.select does not affect grouping: it preserves the existing group structure and indexes, and propagates data (if any) to selected children. Grouping plays an important role in the [data join](#joining-data). See [Nested Selections](http://bost.ocks.org/mike/nest/) and [How Selections Work](http://bost.ocks.org/mike/selection/) for more on this topic. + +# selection.selectAll(selector) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/selectAll.js) + +For each selected element, selects the descendant elements that match the specified *selector* string. The elements in the returned selection are grouped by their corresponding parent node in this selection. If no element matches the specified selector for the current element, or if the *selector* is null, the group at the current index will be empty. The selected elements do not inherit data from this selection; use [*selection*.data](#selection_data) to propagate data to children. For example, to select the bold elements in every paragraph: + +```js +const b = d3.selectAll("p").selectAll("b"); +``` + +If the *selector* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). It must return an array of elements (or an iterable, or a pseudo-array such as a NodeList), or the empty array if there are no matching elements. For example, to select the previous and next siblings of each paragraph: + +```js +const sibling = d3.selectAll("p").selectAll(function() { + return [ + this.previousElementSibling, + this.nextElementSibling + ]; +}); +``` + +Unlike [*selection*.select](#selection_select), *selection*.selectAll does affect grouping: each selected descendant is grouped by the parent element in the originating selection. Grouping plays an important role in the [data join](#joining-data). See [Nested Selections](http://bost.ocks.org/mike/nest/) and [How Selections Work](http://bost.ocks.org/mike/selection/) for more on this topic. + +# selection.filter(filter) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/filter.js) + +Filters the selection, returning a new selection that contains only the elements for which the specified *filter* is true. The *filter* may be specified either as a selector string or a function. If the *filter* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). + +For example, to filter a selection of table rows to contain only even rows: + +```js +const even = d3.selectAll("tr").filter(":nth-child(even)"); +``` + +This is approximately equivalent to using [d3.selectAll](#selectAll) directly, although the indexes may be different: + +```js +const even = d3.selectAll("tr:nth-child(even)"); +``` + +Similarly, using a function: + +```js +const even = d3.selectAll("tr").filter((d, i) => i & 1); +``` + +Or using [*selection*.select](#selection_select) (and avoiding an arrow function, since *this* is needed to refer to the current element): + +```js +const even = d3.selectAll("tr").select(function(d, i) { return i & 1 ? this : null; }); +``` + +Note that the `:nth-child` pseudo-class is a one-based index rather than a zero-based index. Also, the above filter functions do not have precisely the same meaning as `:nth-child`; they rely on the selection index rather than the number of preceding sibling elements in the DOM. + +The returned filtered selection preserves the parents of this selection, but like [*array*.filter](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/filter), it does not preserve indexes as some elements may be removed; use [*selection*.select](#selection_select) to preserve the index, if needed. + +# selection.merge(other) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/merge.js) + +Returns a new selection merging this selection with the specified *other* selection or transition. The returned selection has the same number of groups and the same parents as this selection. Any missing (null) elements in this selection are filled with the corresponding element, if present (not null), from the specified *selection*. (If the *other* selection has additional groups or parents, they are ignored.) + +This method is used internally by [*selection*.join](#selection_join) to merge the [enter](#selection_enter) and [update](#selection_data) selections after [binding data](#joining-data). You can also merge explicitly, although note that since merging is based on element index, you should use operations that preserve index, such as [*selection*.select](#selection_select) instead of [*selection*.filter](#selection_filter). For example: + +```js +const odd = selection.select(function(d, i) { return i & 1 ? this : null; )); +const even = selection.select(function(d, i) { return i & 1 ? null : this; )); +const merged = odd.merge(even); +``` + +See [*selection*.data](#selection_data) for more. + +This method is not intended for concatenating arbitrary selections, however: if both this selection and the specified *other* selection have (non-null) elements at the same index, this selection’s element is returned in the merge and the *other* selection’s element is ignored. + +# selection.selectChild([selector]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/selectChild.js) + +Returns a new selection with the (first) child of each element of the current selection matching the *selector*. If no *selector* is specified, selects the first child (if any). If the *selector* is specified as a string, selects the first child that matches (if any). If the *selector* is a function, it is evaluated for each of the children nodes, in order, being passed the child (*child*), the child’s index (*i*), and the list of children (*children*); the method selects the first child for which the selector return truthy, if any. + +# selection.selectChildren([selector]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/selectChildren.js) + +Returns a new selection with the children of each element of the current selection matching the *selector*. If no *selector* is specified, selects all the children. If the *selector* is specified as a string, selects the children that match (if any). If the *selector* is a function, it is evaluated for each of the children nodes, in order, being passed the child (*child*), the child’s index (*i*), and the list of children (*children*); the method selects all children for which the selector return truthy. + +# selection.selection() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/index.js) + +Returns the selection (for symmetry with [transition.selection](https://github.com/d3/d3-transition/blob/master/README.md#transition_selection)). + +# d3.matcher(selector) · [Source](https://github.com/d3/d3-selection/blob/master/src/matcher.js) + +Given the specified *selector*, returns a function which returns true if `this` element [matches](https://developer.mozilla.org/en-US/docs/Web/API/Element/matches) the specified selector. This method is used internally by [*selection*.filter](#selection_filter). For example, this: + +```js +const div = selection.filter("div"); +``` + +Is equivalent to: + +```js +const div = selection.filter(d3.matcher("div")); +``` + +(Although D3 is not a compatibility layer, this implementation does support vendor-prefixed implementations due to the recent standardization of *element*.matches.) + +# d3.selector(selector) · [Source](https://github.com/d3/d3-selection/blob/master/src/selector.js) + +Given the specified *selector*, returns a function which returns the first descendant of `this` element that matches the specified selector. This method is used internally by [*selection*.select](#selection_select). For example, this: + +```js +const div = selection.select("div"); +``` + +Is equivalent to: + +```js +const div = selection.select(d3.selector("div")); +``` + +# d3.selectorAll(selector) · [Source](https://github.com/d3/d3-selection/blob/master/src/selectAll.js) + +Given the specified *selector*, returns a function which returns all descendants of `this` element that match the specified selector. This method is used internally by [*selection*.selectAll](#selection_selectAll). For example, this: + +```js +const div = selection.selectAll("div"); +``` + +Is equivalent to: + +```js +const div = selection.selectAll(d3.selectorAll("div")); +``` + +# d3.window(node) · [Source](https://github.com/d3/d3-selection/blob/master/src/window.js) + +Returns the owner window for the specified *node*. If *node* is a node, returns the owner document’s default view; if *node* is a document, returns its default view; otherwise returns the *node*. + +# d3.style(node, name) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/style.js) + +Returns the value of the style property with the specified *name* for the specified *node*. If the *node* has an inline style with the specified *name*, its value is returned; otherwise, the [computed property value](https://developer.mozilla.org/en-US/docs/Web/CSS/computed_value) is returned. See also [*selection*.style](#selection_style). + +### Modifying Elements + +After selecting elements, use the selection’s transformation methods to affect document content. For example, to set the name attribute and color style of an anchor element: + +```js +d3.select("a") + .attr("name", "fred") + .style("color", "red"); +``` + +To experiment with selections, visit [d3js.org](https://d3js.org) and open your browser’s developer console! (In Chrome, open the console with ⌥⌘J.) Select elements and then inspect the returned selection to see which elements are selected and how they are grouped. Call selection methods and see how the page content changes. + +# selection.attr(name[, value]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/attr.js) + +If a *value* is specified, sets the attribute with the specified *name* to the specified value on the selected elements and returns this selection. If the *value* is a constant, all elements are given the same attribute value; otherwise, if the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function’s return value is then used to set each element’s attribute. A null value will remove the specified attribute. + +If a *value* is not specified, returns the current value of the specified attribute for the first (non-null) element in the selection. This is generally useful only if you know that the selection contains exactly one element. + +The specified *name* may have a namespace prefix, such as `xlink:href` to specify the `href` attribute in the XLink namespace. See [namespaces](#namespaces) for the map of supported namespaces; additional namespaces can be registered by adding to the map. + +# selection.classed(names[, value]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/classed.js) + +If a *value* is specified, assigns or unassigns the specified CSS class *names* on the selected elements by setting the `class` attribute or modifying the `classList` property and returns this selection. The specified *names* is a string of space-separated class names. For example, to assign the classes `foo` and `bar` to the selected elements: + +```js +selection.classed("foo bar", true); +``` + +If the *value* is truthy, then all elements are assigned the specified classes; otherwise, the classes are unassigned. If the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function’s return value is then used to assign or unassign classes on each element. For example, to randomly associate the class *foo* with on average half the selected elements: + +```js +selection.classed("foo", () => Math.random() > 0.5); +``` + +If a *value* is not specified, returns true if and only if the first (non-null) selected element has the specified *classes*. This is generally useful only if you know the selection contains exactly one element. + +# selection.style(name[, value[, priority]]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/style.js) + +If a *value* is specified, sets the style property with the specified *name* to the specified value on the selected elements and returns this selection. If the *value* is a constant, then all elements are given the same style property value; otherwise, if the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function’s return value is then used to set each element’s style property. A null value will remove the style property. An optional *priority* may also be specified, either as null or the string `important` (without the exclamation point). + +If a *value* is not specified, returns the current value of the specified style property for the first (non-null) element in the selection. The current value is defined as the element’s inline value, if present, and otherwise its [computed value](https://developer.mozilla.org/en-US/docs/Web/CSS/computed_value). Accessing the current style value is generally useful only if you know the selection contains exactly one element. + +Caution: unlike many SVG attributes, CSS styles typically have associated units. For example, `3px` is a valid stroke-width property value, while `3` is not. Some browsers implicitly assign the `px` (pixel) unit to numeric values, but not all browsers do: IE, for example, throws an “invalid arguments” error! + +# selection.property(name[, value]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/property.js) + +Some HTML elements have special properties that are not addressable using attributes or styles, such as a form field’s text `value` and a checkbox’s `checked` boolean. Use this method to get or set these properties. + +If a *value* is specified, sets the property with the specified *name* to the specified value on selected elements. If the *value* is a constant, then all elements are given the same property value; otherwise, if the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function’s return value is then used to set each element’s property. A null value will delete the specified property. + +If a *value* is not specified, returns the value of the specified property for the first (non-null) element in the selection. This is generally useful only if you know the selection contains exactly one element. + +# selection.text([value]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/text.js) + +If a *value* is specified, sets the [text content](http://www.w3.org/TR/DOM-Level-3-Core/core.html#Node3-textContent) to the specified value on all selected elements, replacing any existing child elements. If the *value* is a constant, then all elements are given the same text content; otherwise, if the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function’s return value is then used to set each element’s text content. A null value will clear the content. + +If a *value* is not specified, returns the text content for the first (non-null) element in the selection. This is generally useful only if you know the selection contains exactly one element. + +# selection.html([value]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/html.js) + +If a *value* is specified, sets the [inner HTML](http://dev.w3.org/html5/spec-LC/apis-in-html-documents.html#innerhtml) to the specified value on all selected elements, replacing any existing child elements. If the *value* is a constant, then all elements are given the same inner HTML; otherwise, if the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function’s return value is then used to set each element’s inner HTML. A null value will clear the content. + +If a *value* is not specified, returns the inner HTML for the first (non-null) element in the selection. This is generally useful only if you know the selection contains exactly one element. + +Use [*selection*.append](#selection_append) or [*selection*.insert](#selection_insert) instead to create data-driven content; this method is intended for when you want a little bit of HTML, say for rich formatting. Also, *selection*.html is only supported on HTML elements. SVG elements and other non-HTML elements do not support the innerHTML property, and thus are incompatible with *selection*.html. Consider using [XMLSerializer](https://developer.mozilla.org/en-US/docs/XMLSerializer) to convert a DOM subtree to text. See also the [innersvg polyfill](https://code.google.com/p/innersvg/), which provides a shim to support the innerHTML property on SVG elements. + +# selection.append(type) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/append.js) + +If the specified *type* is a string, appends a new element of this type (tag name) as the last child of each selected element, or before the next following sibling in the update selection if this is an [enter selection](#selection_enter). The latter behavior for enter selections allows you to insert elements into the DOM in an order consistent with the new bound data; however, note that [*selection*.order](#selection_order) may still be required if updating elements change order (*i.e.*, if the order of new data is inconsistent with old data). + +If the specified *type* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). This function should return an element to be appended. (The function typically creates a new element, but it may instead return an existing element.) For example, to append a paragraph to each DIV element: + +```js +d3.selectAll("div").append("p"); +``` + +This is equivalent to: + +```js +d3.selectAll("div").append(() => document.createElement("p")); +``` + +Which is equivalent to: + +```js +d3.selectAll("div").select(function() { + return this.appendChild(document.createElement("p")); +}); +``` + +In both cases, this method returns a new selection containing the appended elements. Each new element inherits the data of the current elements, if any, in the same manner as [*selection*.select](#selection_select). + +The specified *name* may have a namespace prefix, such as `svg:text` to specify a `text` attribute in the SVG namespace. See [namespaces](#namespaces) for the map of supported namespaces; additional namespaces can be registered by adding to the map. If no namespace is specified, the namespace will be inherited from the parent element; or, if the name is one of the known prefixes, the corresponding namespace will be used (for example, `svg` implies `svg:svg`). + +# selection.insert(type[, before]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/insert.js) + +If the specified *type* is a string, inserts a new element of this type (tag name) before the first element matching the specified *before* selector for each selected element. For example, a *before* selector `:first-child` will prepend nodes before the first child. If *before* is not specified, it defaults to null. (To append elements in an order consistent with [bound data](#joining-data), use [*selection*.append](#selection_append).) + +Both *type* and *before* may instead be specified as functions which are evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The *type* function should return an element to be inserted; the *before* function should return the child element before which the element should be inserted. For example, to append a paragraph to each DIV element: + +```js +d3.selectAll("div").insert("p"); +``` + +This is equivalent to: + +```js +d3.selectAll("div").insert(() => document.createElement("p")); +``` + +Which is equivalent to: + +```js +d3.selectAll("div").select(function() { + return this.insertBefore(document.createElement("p"), null); +}); +``` + +In both cases, this method returns a new selection containing the appended elements. Each new element inherits the data of the current elements, if any, in the same manner as [*selection*.select](#selection_select). + +The specified *name* may have a namespace prefix, such as `svg:text` to specify a `text` attribute in the SVG namespace. See [namespaces](#namespaces) for the map of supported namespaces; additional namespaces can be registered by adding to the map. If no namespace is specified, the namespace will be inherited from the parent element; or, if the name is one of the known prefixes, the corresponding namespace will be used (for example, `svg` implies `svg:svg`). + +# selection.remove() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/remove.js) + +Removes the selected elements from the document. Returns this selection (the removed elements) which are now detached from the DOM. There is not currently a dedicated API to add removed elements back to the document; however, you can pass a function to [*selection*.append](#selection_append) or [*selection*.insert](#selection_insert) to re-add elements. + +# selection.clone([deep]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/clone.js) + +Inserts clones of the selected elements immediately following the selected elements and returns a selection of the newly added clones. If *deep* is truthy, the descendant nodes of the selected elements will be cloned as well. Otherwise, only the elements themselves will be cloned. Equivalent to: + +```js +selection.select(function() { + return this.parentNode.insertBefore(this.cloneNode(deep), this.nextSibling); +}); +``` + +# selection.sort(compare) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/sort.js) + +Returns a new selection that contains a copy of each group in this selection sorted according to the *compare* function. After sorting, re-inserts elements to match the resulting order (per [*selection*.order](#selection_order)). + +The compare function, which defaults to [ascending](https://github.com/d3/d3-array#ascending), is passed two elements’ data *a* and *b* to compare. It should return either a negative, positive, or zero value. If negative, then *a* should be before *b*; if positive, then *a* should be after *b*; otherwise, *a* and *b* are considered equal and the order is arbitrary. + +Note that sorting is not guaranteed to be stable; however, it is guaranteed to have the same behavior as your browser’s built-in [sort](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/sort) method on arrays. + +# selection.order() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/order.js) + +Re-inserts elements into the document such that the document order of each group matches the selection order. This is equivalent to calling [*selection*.sort](#selection_sort) if the data is already sorted, but much faster. + +# selection.raise() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/raise.js) + +Re-inserts each selected element, in order, as the last child of its parent. Equivalent to: + +```js +selection.each(function() { + this.parentNode.appendChild(this); +}); +``` + +# selection.lower() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/lower.js) + +Re-inserts each selected element, in order, as the first child of its parent. Equivalent to: + +```js +selection.each(function() { + this.parentNode.insertBefore(this, this.parentNode.firstChild); +}); +``` + +# d3.create(name) · [Source](https://github.com/d3/d3-selection/blob/master/src/create.js) + +Given the specified element *name*, returns a single-element selection containing a detached element of the given name in the current document. This method assumes the HTML namespace, so you must specify a namespace explicitly when creating SVG or other non-HTML elements; see [namespace](#namespace) for details on supported namespace prefixes. + +```js +d3.create("svg") // equivalent to svg:svg +d3.create("svg:svg") // more explicitly +d3.create("svg:g") // an SVG G element +d3.create("g") // an HTML G (unknown) element +``` + +# d3.creator(name) · [Source](https://github.com/d3/d3-selection/blob/master/src/creator.js) + +Given the specified element *name*, returns a function which creates an element of the given name, assuming that `this` is the parent element. This method is used internally by [*selection*.append](#selection_append) and [*selection*.insert](#selection_insert) to create new elements. For example, this: + +```js +selection.append("div"); +``` + +Is equivalent to: + +```js +selection.append(d3.creator("div")); +``` + +See [namespace](#namespace) for details on supported namespace prefixes, such as for SVG elements. + +### Joining Data + +For an introduction to D3’s data joins, see the [*selection*.join notebook](https://observablehq.com/@d3/selection-join). Also see [Thinking With Joins](http://bost.ocks.org/mike/join/). + +# selection.data([data[, key]]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/data.js), [Examples](https://observablehq.com/@d3/brushable-scatterplot) + +Binds the specified array of *data* with the selected elements, returning a new selection that represents the *update* selection: the elements successfully bound to data. Also defines the [enter](#selection_enter) and [exit](#selection_exit) selections on the returned selection, which can be used to add or remove elements to correspond to the new data. The specified *data* is an array of arbitrary values (*e.g.*, numbers or objects), or a function that returns an array of values for each group. When data is assigned to an element, it is stored in the property `__data__`, thus making the data “sticky” and available on re-selection. + +The *data* is specified **for each group** in the selection. If the selection has multiple groups (such as [d3.selectAll](#selectAll) followed by [*selection*.selectAll](#selection_selectAll)), then *data* should typically be specified as a function. This function will be evaluated for each group in order, being passed the group’s parent datum (*d*, which may be undefined), the group index (*i*), and the selection’s parent nodes (*nodes*), with *this* as the group’s parent element. + +In conjunction with [*selection*.join](#selection_join) (or more explicitly with [*selection*.enter](#selection_enter), [*selection*.exit](#selection_exit), [*selection*.append](#selection_append) and [*selection*.remove](#selection_remove)), *selection*.data can be used to enter, update and exit elements to match data. For example, to create an HTML table from a matrix of numbers: + +```js +const matrix = [ + [11975, 5871, 8916, 2868], + [ 1951, 10048, 2060, 6171], + [ 8010, 16145, 8090, 8045], + [ 1013, 990, 940, 6907] +]; + +d3.select("body") + .append("table") + .selectAll("tr") + .data(matrix) + .join("tr") + .selectAll("td") + .data(d => d) + .join("td") + .text(d => d); +``` + +In this example the *data* function is the identity function: for each table row, it returns the corresponding row from the data matrix. + +If a *key* function is not specified, then the first datum in *data* is assigned to the first selected element, the second datum to the second selected element, and so on. A *key* function may be specified to control which datum is assigned to which element, replacing the default join-by-index, by computing a string identifier for each datum and element. This key function is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]); the returned string is the element’s key. The key function is then also evaluated for each new datum in *data*, being passed the current datum (*d*), the current index (*i*), and the group’s new *data*, with *this* as the group’s parent DOM element; the returned string is the datum’s key. The datum for a given key is assigned to the element with the matching key. If multiple elements have the same key, the duplicate elements are put into the exit selection; if multiple data have the same key, the duplicate data are put into the enter selection. + +For example, given this document: + +```html +

    +
    +
    +
    +
    +
    +``` + +You could join data by key as follows: + + +```js +const data = [ + {name: "Locke", number: 4}, + {name: "Reyes", number: 8}, + {name: "Ford", number: 15}, + {name: "Jarrah", number: 16}, + {name: "Shephard", number: 23}, + {name: "Kwon", number: 42} +]; + +d3.selectAll("div") + .data(data, function(d) { return d ? d.name : this.id; }) + .text(d => d.number); +``` + +This example key function uses the datum *d* if present, and otherwise falls back to the element’s id property. Since these elements were not previously bound to data, the datum *d* is null when the key function is evaluated on selected elements, and non-null when the key function is evaluated on the new data. + +The *update* and *enter* selections are returned in data order, while the *exit* selection preserves the selection order prior to the join. If a key function is specified, the order of elements in the selection may not match their order in the document; use [*selection*.order](#selection_order) or [*selection*.sort](#selection_sort) as needed. For more on how the key function affects the join, see [A Bar Chart, Part 2](http://bost.ocks.org/mike/bar/2/) and [Object Constancy](http://bost.ocks.org/mike/constancy/). + +If *data* is not specified, this method returns the array of data for the selected elements. + +This method cannot be used to clear bound data; use [*selection*.datum](#selection_datum) instead. + +# selection.join(enter[, update][, exit]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/join.js) + +Appends, removes and reorders elements as necessary to match the data that was previously bound by [*selection*.data](#selection_data), returning the [merged](#selection_merge) enter and update selection. This method is a convenient alternative to the explicit [general update pattern](https://bl.ocks.org/mbostock/3808218), replacing [*selection*.enter](#selection_enter), [*selection*.exit](#selection_exit), [*selection*.append](#selection_append), [*selection*.remove](#selection_remove), and [*selection*.order](#selection_order). For example: + +```js +svg.selectAll("circle") + .data(data) + .join("circle") + .attr("fill", "none") + .attr("stroke", "black"); +``` + +The *enter* function may be specified as a string shorthand, as above, which is equivalent to [*selection*.append](#selection_append) with the given element name. Likewise, optional *update* and *exit* functions may be specified, which default to the identity function and calling [*selection*.remove](#selection_remove), respectively. The shorthand above is thus equivalent to: + +```js +svg.selectAll("circle") + .data(data) + .join( + enter => enter.append("circle"), + update => update, + exit => exit.remove() + ) + .attr("fill", "none") + .attr("stroke", "black"); +```` + +By passing separate functions on enter, update and exit, you have greater control over what happens. And by specifying a key function to [*selection*.data](#selection_data), you can minimize changes to the DOM to optimize performance. For example, to set different fill colors for enter and update: + +```js +svg.selectAll("circle") + .data(data) + .join( + enter => enter.append("circle").attr("fill", "green"), + update => update.attr("fill", "blue") + ) + .attr("stroke", "black"); +``` + +The selections returned by the *enter* and *update* functions are merged and then returned by *selection*.join. + +You can animate enter, update and exit by creating transitions inside the *enter*, *update* and *exit* functions. If the *enter* and *update* functions return transitions, their underlying selections are merged and then returned by *selection*.join. The return value of the *exit* function is not used. + +For more, see the [*selection*.join notebook](https://observablehq.com/@d3/selection-join). + +# selection.enter() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/enter.js) + +Returns the enter selection: placeholder nodes for each datum that had no corresponding DOM element in the selection. (The enter selection is empty for selections not returned by [*selection*.data](#selection_data).) + +The enter selection is typically used to create “missing” elements corresponding to new data. For example, to create DIV elements from an array of numbers: + +```js +const div = d3.select("body") + .selectAll("div") + .data([4, 8, 15, 16, 23, 42]) + .enter().append("div") + .text(d => d); +``` + +If the body is initially empty, the above code will create six new DIV elements, append them to the body in-order, and assign their text content as the associated (string-coerced) number: + +```html +
    4
    +
    8
    +
    15
    +
    16
    +
    23
    +
    42
    +``` + +Conceptually, the enter selection’s placeholders are pointers to the parent element (in this example, the document body). The enter selection is typically only used transiently to append elements, and is often [merged](#selection_merge) with the update selection after appending, such that modifications can be applied to both entering and updating elements. + +# selection.exit() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/exit.js) + +Returns the exit selection: existing DOM elements in the selection for which no new datum was found. (The exit selection is empty for selections not returned by [*selection*.data](#selection_data).) + +The exit selection is typically used to remove “superfluous” elements corresponding to old data. For example, to update the DIV elements created previously with a new array of numbers: + +```js +div = div.data([1, 2, 4, 8, 16, 32], d => d); +``` + +Since a key function was specified (as the identity function), and the new data contains the numbers [4, 8, 16] which match existing elements in the document, the update selection contains three DIV elements. Leaving those elements as-is, we can append new elements for [1, 2, 32] using the enter selection: + +```js +div.enter().append("div").text(d => d); +``` + +Likewise, to remove the exiting elements [15, 23, 42]: + +```js +div.exit().remove(); +``` + +Now the document body looks like this: + +```html +
    1
    +
    2
    +
    4
    +
    8
    +
    16
    +
    32
    +``` + +The order of the DOM elements matches the order of the data because the old data’s order and the new data’s order were consistent. If the new data’s order is different, use [*selection*.order](#selection_order) to reorder the elements in the DOM. See the [General Update Pattern](http://bl.ocks.org/mbostock/3808218) example thread for more on data joins. + +# selection.datum([value]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/datum.js) + +Gets or sets the bound data for each selected element. Unlike [*selection*.data](#selection_data), this method does not compute a join and does not affect indexes or the enter and exit selections. + +If a *value* is specified, sets the element’s bound data to the specified value on all selected elements. If the *value* is a constant, all elements are given the same datum; otherwise, if the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function is then used to set each element’s new data. A null value will delete the bound data. + +If a *value* is not specified, returns the bound datum for the first (non-null) element in the selection. This is generally useful only if you know the selection contains exactly one element. + +This method is useful for accessing HTML5 [custom data attributes](http://www.w3.org/TR/html5/dom.html#custom-data-attribute). For example, given the following elements: + +```html +
      +
    • Shawn Allen
    • +
    • Mike Bostock
    • +
    +``` + +You can expose the custom data attributes by setting each element’s data as the built-in [dataset](http://www.w3.org/TR/html5/dom.html#dom-dataset) property: + +```js +selection.datum(function() { return this.dataset; }) +``` + +### Handling Events + +For interaction, selections allow listening for and dispatching of events. + +# selection.on(typenames[, listener[, options]]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/on.js) + +Adds or removes a *listener* to each selected element for the specified event *typenames*. The *typenames* is a string event type, such as `click`, `mouseover`, or `submit`; any [DOM event type](https://developer.mozilla.org/en-US/docs/Web/Events#Standard_events) supported by your browser may be used. The type may be optionally followed by a period (`.`) and a name; the optional name allows multiple callbacks to be registered to receive events of the same type, such as `click.foo` and `click.bar`. To specify multiple typenames, separate typenames with spaces, such as `input change` or `click.foo click.bar`. + +When a specified event is dispatched on a selected element, the specified *listener* will be evaluated for the element, being passed the current event (*event*) and the current datum (*d*), with *this* as the current DOM element (*event*.currentTarget). Listeners always see the latest datum for their element. Note: while you can use [*event*.pageX](https://developer.mozilla.org/en/DOM/event.pageX) and [*event*.pageY](https://developer.mozilla.org/en/DOM/event.pageY) directly, it is often convenient to transform the event position to the local coordinate system of the element that received the event using [d3.pointer](#pointer). + +If an event listener was previously registered for the same *typename* on a selected element, the old listener is removed before the new listener is added. To remove a listener, pass null as the *listener*. To remove all listeners for a given name, pass null as the *listener* and `.foo` as the *typename*, where `foo` is the name; to remove all listeners with no name, specify `.` as the *typename*. + +An optional *options* object may specify characteristics about the event listener, such as whether it is capturing or passive; see [*element*.addEventListener](https://developer.mozilla.org/en-US/docs/Web/API/EventTarget/addEventListener). + +If a *listener* is not specified, returns the currently-assigned listener for the specified event *typename* on the first (non-null) selected element, if any. If multiple typenames are specified, the first matching listener is returned. + +# selection.dispatch(type[, parameters]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/dispatch.js) + +Dispatches a [custom event](http://www.w3.org/TR/dom/#interface-customevent) of the specified *type* to each selected element, in order. An optional *parameters* map may be specified to set additional properties of the event. It may contain the following fields: + +* [`bubbles`](https://www.w3.org/TR/dom/#dom-event-bubbles) - if true, the event is dispatched to ancestors in reverse tree order. +* [`cancelable`](https://www.w3.org/TR/dom/#dom-event-cancelable) - if true, *event*.preventDefault is allowed. +* [`detail`](https://www.w3.org/TR/dom/#dom-customevent-detail) - any custom data associated with the event. + +If *parameters* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). It must return the parameters map for the current element. + +# d3.pointer(event[, target]) · [Source](https://github.com/d3/d3-selection/blob/master/src/pointer.js) + +Returns a two-element array of numbers [*x*, *y*] representing the coordinates of the specified *event* relative to the specified *target*. *event* can be a [MouseEvent](https://developer.mozilla.org/en-US/docs/Web/API/MouseEvent), a [PointerEvent](https://developer.mozilla.org/en-US/docs/Web/API/PointerEvent), a [Touch](https://www.w3.org/TR/touch-events/#touch-interface), or a custom event holding a UIEvent as *event*.sourceEvent. + +If *target* is not specified, it defaults to the source event’s currentTarget property, if available. If the *target* is an SVG element, the event’s coordinates are transformed using the [inverse](https://www.w3.org/TR/geometry-1/#dom-dommatrixreadonly-inverse) of the [screen coordinate transformation matrix](https://www.w3.org/TR/SVG/types.html#__svg__SVGGraphicsElement__getScreenCTM). If the *target* is an HTML element, the event’s coordinates are translated relative to the top-left corner of the *target*’s [bounding client rectangle](https://developer.mozilla.org/en-US/docs/Web/API/Element/getBoundingClientRect). (As such, the coordinate system can only be translated relative to the client coordinates. See also [GeometryUtils](https://www.w3.org/TR/cssom-view-1/#the-geometryutils-interface).) Otherwise, [*event*.pageX, *event*.pageY] is returned. + +# d3.pointers(event[, target]) · [Source](https://github.com/d3/d3-selection/blob/master/src/pointers.js) + +Returns an array [[*x0*, *y0*], [*x1*, *y1*]…] of coordinates of the specified *event*’s pointer locations relative to the specified *target*. For touch events, the returned array of positions corresponds to the *event*.touches array; for other events, returns a single-element array. + +If *target* is not specified, it defaults to the source event’s currentTarget property, if any. + +### Control Flow + +For advanced usage, selections provide methods for custom control flow. + +# selection.each(function) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/each.js) + +Invokes the specified *function* for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). This method can be used to invoke arbitrary code for each selected element, and is useful for creating a context to access parent and child data simultaneously, such as: + +```js +parent.each(function(p, j) { + d3.select(this) + .selectAll(".child") + .text(d => `child ${d.name} of ${p.name}`); +}); +``` + +See [Sized Donut Multiples](http://bl.ocks.org/mbostock/4c5fad723c87d2fd8273) for an example. + +# selection.call(function[, arguments…]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/call.js) + +Invokes the specified *function* exactly once, passing in this selection along with any optional *arguments*. Returns this selection. This is equivalent to invoking the function by hand but facilitates method chaining. For example, to set several styles in a reusable function: + +```js +function name(selection, first, last) { + selection + .attr("first-name", first) + .attr("last-name", last); +} +``` + +Now say: + +```js +d3.selectAll("div").call(name, "John", "Snow"); +``` + +This is roughly equivalent to: + +```js +name(d3.selectAll("div"), "John", "Snow"); +``` + +The only difference is that *selection*.call always returns the *selection* and not the return value of the called *function*, `name`. + +# selection.empty() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/empty.js) + +Returns true if this selection contains no (non-null) elements. + +# selection.nodes() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/nodes.js) + +Returns an array of all (non-null) elements in this selection. Equivalent to: + +```js +const elements = Array.from(selection); +```` + +See also [*selection*[Symbol.iterator]](#selection_iterator). + +# selection.node() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/node.js) + +Returns the first (non-null) element in this selection. If the selection is empty, returns null. + +# selection.size() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/size.js) + +Returns the total number of (non-null) elements in this selection. + +# selection\[Symbol.iterator\]() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/iterator.js) + +Returns an iterator over the selected (non-null) elements. For example, to iterate over the selected elements: + +```js +for (const element of selection) { + console.log(element); +} +``` + +To flatten the selection to an array: + +```js +const elements = [...selection]; +```` + +### Local Variables + +D3 locals allow you to define local state independent of data. For instance, when rendering [small multiples](http://bl.ocks.org/mbostock/e1192fe405703d8321a5187350910e08) of time-series data, you might want the same *x*-scale for all charts but distinct *y*-scales to compare the relative performance of each metric. D3 locals are scoped by DOM elements: on set, the value is stored on the given element; on get, the value is retrieved from given element or the nearest ancestor that defines it. + +# d3.local() · [Source](https://github.com/d3/d3-selection/blob/master/src/local.js) + +Declares a new local variable. For example: + +```js +const foo = d3.local(); +``` + +Like `var`, each local is a distinct symbolic reference; unlike `var`, the value of each local is also scoped by the DOM. + +# local.set(node, value) · [Source](https://github.com/d3/d3-selection/blob/master/src/local.js) + +Sets the value of this local on the specified *node* to the *value*, and returns the specified *value*. This is often performed using [*selection*.each](#selection_each): + +```js +selection.each(function(d) { foo.set(this, d.value); }); +``` + +If you are just setting a single variable, consider using [*selection*.property](#selection_property): + +```js +selection.property(foo, d => d.value); +``` + +# local.get(node) · [Source](https://github.com/d3/d3-selection/blob/master/src/local.js) + +Returns the value of this local on the specified *node*. If the *node* does not define this local, returns the value from the nearest ancestor that defines it. Returns undefined if no ancestor defines this local. + +# local.remove(node) · [Source](https://github.com/d3/d3-selection/blob/master/src/local.js) + +Deletes this local’s value from the specified *node*. Returns true if the *node* defined this local prior to removal, and false otherwise. If ancestors also define this local, those definitions are unaffected, and thus [*local*.get](#local_get) will still return the inherited value. + +# local.toString() · [Source](https://github.com/d3/d3-selection/blob/master/src/local.js) + +Returns the automatically-generated identifier for this local. This is the name of the property that is used to store the local’s value on elements, and thus you can also set or get the local’s value using *element*[*local*] or by using [*selection*.property](#selection_property). + +### Namespaces + +XML namespaces are fun! Right? Fortunately you can mostly ignore them. + +# d3.namespace(name) · [Source](https://github.com/d3/d3-selection/blob/master/src/namespace.js) + +Qualifies the specified *name*, which may or may not have a namespace prefix. If the name contains a colon (`:`), the substring before the colon is interpreted as the namespace prefix, which must be registered in [d3.namespaces](#namespaces). Returns an object `space` and `local` attributes describing the full namespace URL and the local name. For example: + +```js +d3.namespace("svg:text"); // {space: "http://www.w3.org/2000/svg", local: "text"} +``` + +If the name does not contain a colon, this function merely returns the input name. + +# d3.namespaces · [Source](https://github.com/d3/d3-selection/blob/master/src/namespaces.js) + +The map of registered namespace prefixes. The initial value is: + +```js +{ + svg: "http://www.w3.org/2000/svg", + xhtml: "http://www.w3.org/1999/xhtml", + xlink: "http://www.w3.org/1999/xlink", + xml: "http://www.w3.org/XML/1998/namespace", + xmlns: "http://www.w3.org/2000/xmlns/" +} +``` + +Additional prefixes may be assigned as needed to create elements or attributes in other namespaces. diff --git a/frontend/node_modules/d3-selection/dist/d3-selection.js b/frontend/node_modules/d3-selection/dist/d3-selection.js new file mode 100644 index 0000000..9ffc1e8 --- /dev/null +++ b/frontend/node_modules/d3-selection/dist/d3-selection.js @@ -0,0 +1,1022 @@ +// https://d3js.org/d3-selection/ v3.0.0 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +}(this, (function (exports) { 'use strict'; + +var xhtml = "http://www.w3.org/1999/xhtml"; + +var namespaces = { + svg: "http://www.w3.org/2000/svg", + xhtml: xhtml, + xlink: "http://www.w3.org/1999/xlink", + xml: "http://www.w3.org/XML/1998/namespace", + xmlns: "http://www.w3.org/2000/xmlns/" +}; + +function namespace(name) { + var prefix = name += "", i = prefix.indexOf(":"); + if (i >= 0 && (prefix = name.slice(0, i)) !== "xmlns") name = name.slice(i + 1); + return namespaces.hasOwnProperty(prefix) ? {space: namespaces[prefix], local: name} : name; // eslint-disable-line no-prototype-builtins +} + +function creatorInherit(name) { + return function() { + var document = this.ownerDocument, + uri = this.namespaceURI; + return uri === xhtml && document.documentElement.namespaceURI === xhtml + ? document.createElement(name) + : document.createElementNS(uri, name); + }; +} + +function creatorFixed(fullname) { + return function() { + return this.ownerDocument.createElementNS(fullname.space, fullname.local); + }; +} + +function creator(name) { + var fullname = namespace(name); + return (fullname.local + ? creatorFixed + : creatorInherit)(fullname); +} + +function none() {} + +function selector(selector) { + return selector == null ? none : function() { + return this.querySelector(selector); + }; +} + +function selection_select(select) { + if (typeof select !== "function") select = selector(select); + + for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, subgroup = subgroups[j] = new Array(n), node, subnode, i = 0; i < n; ++i) { + if ((node = group[i]) && (subnode = select.call(node, node.__data__, i, group))) { + if ("__data__" in node) subnode.__data__ = node.__data__; + subgroup[i] = subnode; + } + } + } + + return new Selection(subgroups, this._parents); +} + +// Given something array like (or null), returns something that is strictly an +// array. This is used to ensure that array-like objects passed to d3.selectAll +// or selection.selectAll are converted into proper arrays when creating a +// selection; we don’t ever want to create a selection backed by a live +// HTMLCollection or NodeList. However, note that selection.selectAll will use a +// static NodeList as a group, since it safely derived from querySelectorAll. +function array(x) { + return x == null ? [] : Array.isArray(x) ? x : Array.from(x); +} + +function empty() { + return []; +} + +function selectorAll(selector) { + return selector == null ? empty : function() { + return this.querySelectorAll(selector); + }; +} + +function arrayAll(select) { + return function() { + return array(select.apply(this, arguments)); + }; +} + +function selection_selectAll(select) { + if (typeof select === "function") select = arrayAll(select); + else select = selectorAll(select); + + for (var groups = this._groups, m = groups.length, subgroups = [], parents = [], j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) { + if (node = group[i]) { + subgroups.push(select.call(node, node.__data__, i, group)); + parents.push(node); + } + } + } + + return new Selection(subgroups, parents); +} + +function matcher(selector) { + return function() { + return this.matches(selector); + }; +} + +function childMatcher(selector) { + return function(node) { + return node.matches(selector); + }; +} + +var find = Array.prototype.find; + +function childFind(match) { + return function() { + return find.call(this.children, match); + }; +} + +function childFirst() { + return this.firstElementChild; +} + +function selection_selectChild(match) { + return this.select(match == null ? childFirst + : childFind(typeof match === "function" ? match : childMatcher(match))); +} + +var filter = Array.prototype.filter; + +function children() { + return Array.from(this.children); +} + +function childrenFilter(match) { + return function() { + return filter.call(this.children, match); + }; +} + +function selection_selectChildren(match) { + return this.selectAll(match == null ? children + : childrenFilter(typeof match === "function" ? match : childMatcher(match))); +} + +function selection_filter(match) { + if (typeof match !== "function") match = matcher(match); + + for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, subgroup = subgroups[j] = [], node, i = 0; i < n; ++i) { + if ((node = group[i]) && match.call(node, node.__data__, i, group)) { + subgroup.push(node); + } + } + } + + return new Selection(subgroups, this._parents); +} + +function sparse(update) { + return new Array(update.length); +} + +function selection_enter() { + return new Selection(this._enter || this._groups.map(sparse), this._parents); +} + +function EnterNode(parent, datum) { + this.ownerDocument = parent.ownerDocument; + this.namespaceURI = parent.namespaceURI; + this._next = null; + this._parent = parent; + this.__data__ = datum; +} + +EnterNode.prototype = { + constructor: EnterNode, + appendChild: function(child) { return this._parent.insertBefore(child, this._next); }, + insertBefore: function(child, next) { return this._parent.insertBefore(child, next); }, + querySelector: function(selector) { return this._parent.querySelector(selector); }, + querySelectorAll: function(selector) { return this._parent.querySelectorAll(selector); } +}; + +function constant(x) { + return function() { + return x; + }; +} + +function bindIndex(parent, group, enter, update, exit, data) { + var i = 0, + node, + groupLength = group.length, + dataLength = data.length; + + // Put any non-null nodes that fit into update. + // Put any null nodes into enter. + // Put any remaining data into enter. + for (; i < dataLength; ++i) { + if (node = group[i]) { + node.__data__ = data[i]; + update[i] = node; + } else { + enter[i] = new EnterNode(parent, data[i]); + } + } + + // Put any non-null nodes that don’t fit into exit. + for (; i < groupLength; ++i) { + if (node = group[i]) { + exit[i] = node; + } + } +} + +function bindKey(parent, group, enter, update, exit, data, key) { + var i, + node, + nodeByKeyValue = new Map, + groupLength = group.length, + dataLength = data.length, + keyValues = new Array(groupLength), + keyValue; + + // Compute the key for each node. + // If multiple nodes have the same key, the duplicates are added to exit. + for (i = 0; i < groupLength; ++i) { + if (node = group[i]) { + keyValues[i] = keyValue = key.call(node, node.__data__, i, group) + ""; + if (nodeByKeyValue.has(keyValue)) { + exit[i] = node; + } else { + nodeByKeyValue.set(keyValue, node); + } + } + } + + // Compute the key for each datum. + // If there a node associated with this key, join and add it to update. + // If there is not (or the key is a duplicate), add it to enter. + for (i = 0; i < dataLength; ++i) { + keyValue = key.call(parent, data[i], i, data) + ""; + if (node = nodeByKeyValue.get(keyValue)) { + update[i] = node; + node.__data__ = data[i]; + nodeByKeyValue.delete(keyValue); + } else { + enter[i] = new EnterNode(parent, data[i]); + } + } + + // Add any remaining nodes that were not bound to data to exit. + for (i = 0; i < groupLength; ++i) { + if ((node = group[i]) && (nodeByKeyValue.get(keyValues[i]) === node)) { + exit[i] = node; + } + } +} + +function datum(node) { + return node.__data__; +} + +function selection_data(value, key) { + if (!arguments.length) return Array.from(this, datum); + + var bind = key ? bindKey : bindIndex, + parents = this._parents, + groups = this._groups; + + if (typeof value !== "function") value = constant(value); + + for (var m = groups.length, update = new Array(m), enter = new Array(m), exit = new Array(m), j = 0; j < m; ++j) { + var parent = parents[j], + group = groups[j], + groupLength = group.length, + data = arraylike(value.call(parent, parent && parent.__data__, j, parents)), + dataLength = data.length, + enterGroup = enter[j] = new Array(dataLength), + updateGroup = update[j] = new Array(dataLength), + exitGroup = exit[j] = new Array(groupLength); + + bind(parent, group, enterGroup, updateGroup, exitGroup, data, key); + + // Now connect the enter nodes to their following update node, such that + // appendChild can insert the materialized enter node before this node, + // rather than at the end of the parent node. + for (var i0 = 0, i1 = 0, previous, next; i0 < dataLength; ++i0) { + if (previous = enterGroup[i0]) { + if (i0 >= i1) i1 = i0 + 1; + while (!(next = updateGroup[i1]) && ++i1 < dataLength); + previous._next = next || null; + } + } + } + + update = new Selection(update, parents); + update._enter = enter; + update._exit = exit; + return update; +} + +// Given some data, this returns an array-like view of it: an object that +// exposes a length property and allows numeric indexing. Note that unlike +// selectAll, this isn’t worried about “live” collections because the resulting +// array will only be used briefly while data is being bound. (It is possible to +// cause the data to change while iterating by using a key function, but please +// don’t; we’d rather avoid a gratuitous copy.) +function arraylike(data) { + return typeof data === "object" && "length" in data + ? data // Array, TypedArray, NodeList, array-like + : Array.from(data); // Map, Set, iterable, string, or anything else +} + +function selection_exit() { + return new Selection(this._exit || this._groups.map(sparse), this._parents); +} + +function selection_join(onenter, onupdate, onexit) { + var enter = this.enter(), update = this, exit = this.exit(); + if (typeof onenter === "function") { + enter = onenter(enter); + if (enter) enter = enter.selection(); + } else { + enter = enter.append(onenter + ""); + } + if (onupdate != null) { + update = onupdate(update); + if (update) update = update.selection(); + } + if (onexit == null) exit.remove(); else onexit(exit); + return enter && update ? enter.merge(update).order() : update; +} + +function selection_merge(context) { + var selection = context.selection ? context.selection() : context; + + for (var groups0 = this._groups, groups1 = selection._groups, m0 = groups0.length, m1 = groups1.length, m = Math.min(m0, m1), merges = new Array(m0), j = 0; j < m; ++j) { + for (var group0 = groups0[j], group1 = groups1[j], n = group0.length, merge = merges[j] = new Array(n), node, i = 0; i < n; ++i) { + if (node = group0[i] || group1[i]) { + merge[i] = node; + } + } + } + + for (; j < m0; ++j) { + merges[j] = groups0[j]; + } + + return new Selection(merges, this._parents); +} + +function selection_order() { + + for (var groups = this._groups, j = -1, m = groups.length; ++j < m;) { + for (var group = groups[j], i = group.length - 1, next = group[i], node; --i >= 0;) { + if (node = group[i]) { + if (next && node.compareDocumentPosition(next) ^ 4) next.parentNode.insertBefore(node, next); + next = node; + } + } + } + + return this; +} + +function selection_sort(compare) { + if (!compare) compare = ascending; + + function compareNode(a, b) { + return a && b ? compare(a.__data__, b.__data__) : !a - !b; + } + + for (var groups = this._groups, m = groups.length, sortgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, sortgroup = sortgroups[j] = new Array(n), node, i = 0; i < n; ++i) { + if (node = group[i]) { + sortgroup[i] = node; + } + } + sortgroup.sort(compareNode); + } + + return new Selection(sortgroups, this._parents).order(); +} + +function ascending(a, b) { + return a < b ? -1 : a > b ? 1 : a >= b ? 0 : NaN; +} + +function selection_call() { + var callback = arguments[0]; + arguments[0] = this; + callback.apply(null, arguments); + return this; +} + +function selection_nodes() { + return Array.from(this); +} + +function selection_node() { + + for (var groups = this._groups, j = 0, m = groups.length; j < m; ++j) { + for (var group = groups[j], i = 0, n = group.length; i < n; ++i) { + var node = group[i]; + if (node) return node; + } + } + + return null; +} + +function selection_size() { + let size = 0; + for (const node of this) ++size; // eslint-disable-line no-unused-vars + return size; +} + +function selection_empty() { + return !this.node(); +} + +function selection_each(callback) { + + for (var groups = this._groups, j = 0, m = groups.length; j < m; ++j) { + for (var group = groups[j], i = 0, n = group.length, node; i < n; ++i) { + if (node = group[i]) callback.call(node, node.__data__, i, group); + } + } + + return this; +} + +function attrRemove(name) { + return function() { + this.removeAttribute(name); + }; +} + +function attrRemoveNS(fullname) { + return function() { + this.removeAttributeNS(fullname.space, fullname.local); + }; +} + +function attrConstant(name, value) { + return function() { + this.setAttribute(name, value); + }; +} + +function attrConstantNS(fullname, value) { + return function() { + this.setAttributeNS(fullname.space, fullname.local, value); + }; +} + +function attrFunction(name, value) { + return function() { + var v = value.apply(this, arguments); + if (v == null) this.removeAttribute(name); + else this.setAttribute(name, v); + }; +} + +function attrFunctionNS(fullname, value) { + return function() { + var v = value.apply(this, arguments); + if (v == null) this.removeAttributeNS(fullname.space, fullname.local); + else this.setAttributeNS(fullname.space, fullname.local, v); + }; +} + +function selection_attr(name, value) { + var fullname = namespace(name); + + if (arguments.length < 2) { + var node = this.node(); + return fullname.local + ? node.getAttributeNS(fullname.space, fullname.local) + : node.getAttribute(fullname); + } + + return this.each((value == null + ? (fullname.local ? attrRemoveNS : attrRemove) : (typeof value === "function" + ? (fullname.local ? attrFunctionNS : attrFunction) + : (fullname.local ? attrConstantNS : attrConstant)))(fullname, value)); +} + +function defaultView(node) { + return (node.ownerDocument && node.ownerDocument.defaultView) // node is a Node + || (node.document && node) // node is a Window + || node.defaultView; // node is a Document +} + +function styleRemove(name) { + return function() { + this.style.removeProperty(name); + }; +} + +function styleConstant(name, value, priority) { + return function() { + this.style.setProperty(name, value, priority); + }; +} + +function styleFunction(name, value, priority) { + return function() { + var v = value.apply(this, arguments); + if (v == null) this.style.removeProperty(name); + else this.style.setProperty(name, v, priority); + }; +} + +function selection_style(name, value, priority) { + return arguments.length > 1 + ? this.each((value == null + ? styleRemove : typeof value === "function" + ? styleFunction + : styleConstant)(name, value, priority == null ? "" : priority)) + : styleValue(this.node(), name); +} + +function styleValue(node, name) { + return node.style.getPropertyValue(name) + || defaultView(node).getComputedStyle(node, null).getPropertyValue(name); +} + +function propertyRemove(name) { + return function() { + delete this[name]; + }; +} + +function propertyConstant(name, value) { + return function() { + this[name] = value; + }; +} + +function propertyFunction(name, value) { + return function() { + var v = value.apply(this, arguments); + if (v == null) delete this[name]; + else this[name] = v; + }; +} + +function selection_property(name, value) { + return arguments.length > 1 + ? this.each((value == null + ? propertyRemove : typeof value === "function" + ? propertyFunction + : propertyConstant)(name, value)) + : this.node()[name]; +} + +function classArray(string) { + return string.trim().split(/^|\s+/); +} + +function classList(node) { + return node.classList || new ClassList(node); +} + +function ClassList(node) { + this._node = node; + this._names = classArray(node.getAttribute("class") || ""); +} + +ClassList.prototype = { + add: function(name) { + var i = this._names.indexOf(name); + if (i < 0) { + this._names.push(name); + this._node.setAttribute("class", this._names.join(" ")); + } + }, + remove: function(name) { + var i = this._names.indexOf(name); + if (i >= 0) { + this._names.splice(i, 1); + this._node.setAttribute("class", this._names.join(" ")); + } + }, + contains: function(name) { + return this._names.indexOf(name) >= 0; + } +}; + +function classedAdd(node, names) { + var list = classList(node), i = -1, n = names.length; + while (++i < n) list.add(names[i]); +} + +function classedRemove(node, names) { + var list = classList(node), i = -1, n = names.length; + while (++i < n) list.remove(names[i]); +} + +function classedTrue(names) { + return function() { + classedAdd(this, names); + }; +} + +function classedFalse(names) { + return function() { + classedRemove(this, names); + }; +} + +function classedFunction(names, value) { + return function() { + (value.apply(this, arguments) ? classedAdd : classedRemove)(this, names); + }; +} + +function selection_classed(name, value) { + var names = classArray(name + ""); + + if (arguments.length < 2) { + var list = classList(this.node()), i = -1, n = names.length; + while (++i < n) if (!list.contains(names[i])) return false; + return true; + } + + return this.each((typeof value === "function" + ? classedFunction : value + ? classedTrue + : classedFalse)(names, value)); +} + +function textRemove() { + this.textContent = ""; +} + +function textConstant(value) { + return function() { + this.textContent = value; + }; +} + +function textFunction(value) { + return function() { + var v = value.apply(this, arguments); + this.textContent = v == null ? "" : v; + }; +} + +function selection_text(value) { + return arguments.length + ? this.each(value == null + ? textRemove : (typeof value === "function" + ? textFunction + : textConstant)(value)) + : this.node().textContent; +} + +function htmlRemove() { + this.innerHTML = ""; +} + +function htmlConstant(value) { + return function() { + this.innerHTML = value; + }; +} + +function htmlFunction(value) { + return function() { + var v = value.apply(this, arguments); + this.innerHTML = v == null ? "" : v; + }; +} + +function selection_html(value) { + return arguments.length + ? this.each(value == null + ? htmlRemove : (typeof value === "function" + ? htmlFunction + : htmlConstant)(value)) + : this.node().innerHTML; +} + +function raise() { + if (this.nextSibling) this.parentNode.appendChild(this); +} + +function selection_raise() { + return this.each(raise); +} + +function lower() { + if (this.previousSibling) this.parentNode.insertBefore(this, this.parentNode.firstChild); +} + +function selection_lower() { + return this.each(lower); +} + +function selection_append(name) { + var create = typeof name === "function" ? name : creator(name); + return this.select(function() { + return this.appendChild(create.apply(this, arguments)); + }); +} + +function constantNull() { + return null; +} + +function selection_insert(name, before) { + var create = typeof name === "function" ? name : creator(name), + select = before == null ? constantNull : typeof before === "function" ? before : selector(before); + return this.select(function() { + return this.insertBefore(create.apply(this, arguments), select.apply(this, arguments) || null); + }); +} + +function remove() { + var parent = this.parentNode; + if (parent) parent.removeChild(this); +} + +function selection_remove() { + return this.each(remove); +} + +function selection_cloneShallow() { + var clone = this.cloneNode(false), parent = this.parentNode; + return parent ? parent.insertBefore(clone, this.nextSibling) : clone; +} + +function selection_cloneDeep() { + var clone = this.cloneNode(true), parent = this.parentNode; + return parent ? parent.insertBefore(clone, this.nextSibling) : clone; +} + +function selection_clone(deep) { + return this.select(deep ? selection_cloneDeep : selection_cloneShallow); +} + +function selection_datum(value) { + return arguments.length + ? this.property("__data__", value) + : this.node().__data__; +} + +function contextListener(listener) { + return function(event) { + listener.call(this, event, this.__data__); + }; +} + +function parseTypenames(typenames) { + return typenames.trim().split(/^|\s+/).map(function(t) { + var name = "", i = t.indexOf("."); + if (i >= 0) name = t.slice(i + 1), t = t.slice(0, i); + return {type: t, name: name}; + }); +} + +function onRemove(typename) { + return function() { + var on = this.__on; + if (!on) return; + for (var j = 0, i = -1, m = on.length, o; j < m; ++j) { + if (o = on[j], (!typename.type || o.type === typename.type) && o.name === typename.name) { + this.removeEventListener(o.type, o.listener, o.options); + } else { + on[++i] = o; + } + } + if (++i) on.length = i; + else delete this.__on; + }; +} + +function onAdd(typename, value, options) { + return function() { + var on = this.__on, o, listener = contextListener(value); + if (on) for (var j = 0, m = on.length; j < m; ++j) { + if ((o = on[j]).type === typename.type && o.name === typename.name) { + this.removeEventListener(o.type, o.listener, o.options); + this.addEventListener(o.type, o.listener = listener, o.options = options); + o.value = value; + return; + } + } + this.addEventListener(typename.type, listener, options); + o = {type: typename.type, name: typename.name, value: value, listener: listener, options: options}; + if (!on) this.__on = [o]; + else on.push(o); + }; +} + +function selection_on(typename, value, options) { + var typenames = parseTypenames(typename + ""), i, n = typenames.length, t; + + if (arguments.length < 2) { + var on = this.node().__on; + if (on) for (var j = 0, m = on.length, o; j < m; ++j) { + for (i = 0, o = on[j]; i < n; ++i) { + if ((t = typenames[i]).type === o.type && t.name === o.name) { + return o.value; + } + } + } + return; + } + + on = value ? onAdd : onRemove; + for (i = 0; i < n; ++i) this.each(on(typenames[i], value, options)); + return this; +} + +function dispatchEvent(node, type, params) { + var window = defaultView(node), + event = window.CustomEvent; + + if (typeof event === "function") { + event = new event(type, params); + } else { + event = window.document.createEvent("Event"); + if (params) event.initEvent(type, params.bubbles, params.cancelable), event.detail = params.detail; + else event.initEvent(type, false, false); + } + + node.dispatchEvent(event); +} + +function dispatchConstant(type, params) { + return function() { + return dispatchEvent(this, type, params); + }; +} + +function dispatchFunction(type, params) { + return function() { + return dispatchEvent(this, type, params.apply(this, arguments)); + }; +} + +function selection_dispatch(type, params) { + return this.each((typeof params === "function" + ? dispatchFunction + : dispatchConstant)(type, params)); +} + +function* selection_iterator() { + for (var groups = this._groups, j = 0, m = groups.length; j < m; ++j) { + for (var group = groups[j], i = 0, n = group.length, node; i < n; ++i) { + if (node = group[i]) yield node; + } + } +} + +var root = [null]; + +function Selection(groups, parents) { + this._groups = groups; + this._parents = parents; +} + +function selection() { + return new Selection([[document.documentElement]], root); +} + +function selection_selection() { + return this; +} + +Selection.prototype = selection.prototype = { + constructor: Selection, + select: selection_select, + selectAll: selection_selectAll, + selectChild: selection_selectChild, + selectChildren: selection_selectChildren, + filter: selection_filter, + data: selection_data, + enter: selection_enter, + exit: selection_exit, + join: selection_join, + merge: selection_merge, + selection: selection_selection, + order: selection_order, + sort: selection_sort, + call: selection_call, + nodes: selection_nodes, + node: selection_node, + size: selection_size, + empty: selection_empty, + each: selection_each, + attr: selection_attr, + style: selection_style, + property: selection_property, + classed: selection_classed, + text: selection_text, + html: selection_html, + raise: selection_raise, + lower: selection_lower, + append: selection_append, + insert: selection_insert, + remove: selection_remove, + clone: selection_clone, + datum: selection_datum, + on: selection_on, + dispatch: selection_dispatch, + [Symbol.iterator]: selection_iterator +}; + +function select(selector) { + return typeof selector === "string" + ? new Selection([[document.querySelector(selector)]], [document.documentElement]) + : new Selection([[selector]], root); +} + +function create(name) { + return select(creator(name).call(document.documentElement)); +} + +var nextId = 0; + +function local() { + return new Local; +} + +function Local() { + this._ = "@" + (++nextId).toString(36); +} + +Local.prototype = local.prototype = { + constructor: Local, + get: function(node) { + var id = this._; + while (!(id in node)) if (!(node = node.parentNode)) return; + return node[id]; + }, + set: function(node, value) { + return node[this._] = value; + }, + remove: function(node) { + return this._ in node && delete node[this._]; + }, + toString: function() { + return this._; + } +}; + +function sourceEvent(event) { + let sourceEvent; + while (sourceEvent = event.sourceEvent) event = sourceEvent; + return event; +} + +function pointer(event, node) { + event = sourceEvent(event); + if (node === undefined) node = event.currentTarget; + if (node) { + var svg = node.ownerSVGElement || node; + if (svg.createSVGPoint) { + var point = svg.createSVGPoint(); + point.x = event.clientX, point.y = event.clientY; + point = point.matrixTransform(node.getScreenCTM().inverse()); + return [point.x, point.y]; + } + if (node.getBoundingClientRect) { + var rect = node.getBoundingClientRect(); + return [event.clientX - rect.left - node.clientLeft, event.clientY - rect.top - node.clientTop]; + } + } + return [event.pageX, event.pageY]; +} + +function pointers(events, node) { + if (events.target) { // i.e., instanceof Event, not TouchList or iterable + events = sourceEvent(events); + if (node === undefined) node = events.currentTarget; + events = events.touches || [events]; + } + return Array.from(events, event => pointer(event, node)); +} + +function selectAll(selector) { + return typeof selector === "string" + ? new Selection([document.querySelectorAll(selector)], [document.documentElement]) + : new Selection([array(selector)], root); +} + +exports.create = create; +exports.creator = creator; +exports.local = local; +exports.matcher = matcher; +exports.namespace = namespace; +exports.namespaces = namespaces; +exports.pointer = pointer; +exports.pointers = pointers; +exports.select = select; +exports.selectAll = selectAll; +exports.selection = selection; +exports.selector = selector; +exports.selectorAll = selectorAll; +exports.style = styleValue; +exports.window = defaultView; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-selection/dist/d3-selection.min.js b/frontend/node_modules/d3-selection/dist/d3-selection.min.js new file mode 100644 index 0000000..37a5707 --- /dev/null +++ b/frontend/node_modules/d3-selection/dist/d3-selection.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-selection/ v3.0.0 Copyright 2010-2021 Mike Bostock +!function(t,n){"object"==typeof exports&&"undefined"!=typeof module?n(exports):"function"==typeof define&&define.amd?define(["exports"],n):n((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{})}(this,(function(t){"use strict";var n="http://www.w3.org/1999/xhtml",e={svg:"http://www.w3.org/2000/svg",xhtml:n,xlink:"http://www.w3.org/1999/xlink",xml:"http://www.w3.org/XML/1998/namespace",xmlns:"http://www.w3.org/2000/xmlns/"};function r(t){var n=t+="",r=n.indexOf(":");return r>=0&&"xmlns"!==(n=t.slice(0,r))&&(t=t.slice(r+1)),e.hasOwnProperty(n)?{space:e[n],local:t}:t}function i(t){return function(){var e=this.ownerDocument,r=this.namespaceURI;return r===n&&e.documentElement.namespaceURI===n?e.createElement(t):e.createElementNS(r,t)}}function o(t){return function(){return this.ownerDocument.createElementNS(t.space,t.local)}}function u(t){var n=r(t);return(n.local?o:i)(n)}function s(){}function c(t){return null==t?s:function(){return this.querySelector(t)}}function l(t){return null==t?[]:Array.isArray(t)?t:Array.from(t)}function a(){return[]}function f(t){return null==t?a:function(){return this.querySelectorAll(t)}}function h(t){return function(){return this.matches(t)}}function p(t){return function(n){return n.matches(t)}}var _=Array.prototype.find;function d(){return this.firstElementChild}var y=Array.prototype.filter;function m(){return Array.from(this.children)}function v(t){return new Array(t.length)}function g(t,n){this.ownerDocument=t.ownerDocument,this.namespaceURI=t.namespaceURI,this._next=null,this._parent=t,this.__data__=n}function w(t){return function(){return t}}function A(t,n,e,r,i,o){for(var u,s=0,c=n.length,l=o.length;sn?1:t>=n?0:NaN}function N(t){return function(){this.removeAttribute(t)}}function C(t){return function(){this.removeAttributeNS(t.space,t.local)}}function L(t,n){return function(){this.setAttribute(t,n)}}function P(t,n){return function(){this.setAttributeNS(t.space,t.local,n)}}function T(t,n){return function(){var e=n.apply(this,arguments);null==e?this.removeAttribute(t):this.setAttribute(t,e)}}function B(t,n){return function(){var e=n.apply(this,arguments);null==e?this.removeAttributeNS(t.space,t.local):this.setAttributeNS(t.space,t.local,e)}}function M(t){return t.ownerDocument&&t.ownerDocument.defaultView||t.document&&t||t.defaultView}function q(t){return function(){this.style.removeProperty(t)}}function D(t,n,e){return function(){this.style.setProperty(t,n,e)}}function O(t,n,e){return function(){var r=n.apply(this,arguments);null==r?this.style.removeProperty(t):this.style.setProperty(t,r,e)}}function V(t,n){return t.style.getPropertyValue(n)||M(t).getComputedStyle(t,null).getPropertyValue(n)}function j(t){return function(){delete this[t]}}function R(t,n){return function(){this[t]=n}}function H(t,n){return function(){var e=n.apply(this,arguments);null==e?delete this[t]:this[t]=e}}function I(t){return t.trim().split(/^|\s+/)}function U(t){return t.classList||new X(t)}function X(t){this._node=t,this._names=I(t.getAttribute("class")||"")}function G(t,n){for(var e=U(t),r=-1,i=n.length;++r=0&&(n=t.slice(e+1),t=t.slice(0,e)),{type:t,name:n}}))}function st(t){return function(){var n=this.__on;if(n){for(var e,r=0,i=-1,o=n.length;r=0&&(this._names.splice(n,1),this._node.setAttribute("class",this._names.join(" ")))},contains:function(t){return this._names.indexOf(t)>=0}};var ht=[null];function pt(t,n){this._groups=t,this._parents=n}function _t(){return new pt([[document.documentElement]],ht)}function dt(t){return"string"==typeof t?new pt([[document.querySelector(t)]],[document.documentElement]):new pt([[t]],ht)}pt.prototype=_t.prototype={constructor:pt,select:function(t){"function"!=typeof t&&(t=c(t));for(var n=this._groups,e=n.length,r=new Array(e),i=0;i=N&&(N=E+1);!(g=y[N])&&++N<_;);v._next=g||null}}return(u=new pt(u,r))._enter=s,u._exit=c,u},enter:function(){return new pt(this._enter||this._groups.map(v),this._parents)},exit:function(){return new pt(this._exit||this._groups.map(v),this._parents)},join:function(t,n,e){var r=this.enter(),i=this,o=this.exit();return"function"==typeof t?(r=t(r))&&(r=r.selection()):r=r.append(t+""),null!=n&&(i=n(i))&&(i=i.selection()),null==e?o.remove():e(o),r&&i?r.merge(i).order():i},merge:function(t){for(var n=t.selection?t.selection():t,e=this._groups,r=n._groups,i=e.length,o=r.length,u=Math.min(i,o),s=new Array(i),c=0;c=0;)(r=i[o])&&(u&&4^r.compareDocumentPosition(u)&&u.parentNode.insertBefore(r,u),u=r);return this},sort:function(t){function n(n,e){return n&&e?t(n.__data__,e.__data__):!n-!e}t||(t=E);for(var e=this._groups,r=e.length,i=new Array(r),o=0;o1?this.each((null==n?q:"function"==typeof n?O:D)(t,n,null==e?"":e)):V(this.node(),t)},property:function(t,n){return arguments.length>1?this.each((null==n?j:"function"==typeof n?H:R)(t,n)):this.node()[t]},classed:function(t,n){var e=I(t+"");if(arguments.length<2){for(var r=U(this.node()),i=-1,o=e.length;++iwt(t,n)))},t.select=dt,t.selectAll=function(t){return"string"==typeof t?new pt([document.querySelectorAll(t)],[document.documentElement]):new pt([l(t)],ht)},t.selection=_t,t.selector=c,t.selectorAll=f,t.style=V,t.window=M,Object.defineProperty(t,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-selection/package.json b/frontend/node_modules/d3-selection/package.json new file mode 100644 index 0000000..2f6af45 --- /dev/null +++ b/frontend/node_modules/d3-selection/package.json @@ -0,0 +1,51 @@ +{ + "name": "d3-selection", + "version": "3.0.0", + "description": "Data-driven DOM manipulation: select elements and join them to data.", + "homepage": "https://d3js.org/d3-selection/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-selection.git" + }, + "keywords": [ + "d3", + "d3-module", + "dom", + "selection", + "data-join" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "https://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-selection.min.js", + "unpkg": "dist/d3-selection.min.js", + "exports": { + "umd": "./dist/d3-selection.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "devDependencies": { + "eslint": "7", + "jsdom": "16", + "mocha": "9", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-selection/src/array.js b/frontend/node_modules/d3-selection/src/array.js new file mode 100644 index 0000000..978c22a --- /dev/null +++ b/frontend/node_modules/d3-selection/src/array.js @@ -0,0 +1,9 @@ +// Given something array like (or null), returns something that is strictly an +// array. This is used to ensure that array-like objects passed to d3.selectAll +// or selection.selectAll are converted into proper arrays when creating a +// selection; we don’t ever want to create a selection backed by a live +// HTMLCollection or NodeList. However, note that selection.selectAll will use a +// static NodeList as a group, since it safely derived from querySelectorAll. +export default function array(x) { + return x == null ? [] : Array.isArray(x) ? x : Array.from(x); +} diff --git a/frontend/node_modules/d3-selection/src/constant.js b/frontend/node_modules/d3-selection/src/constant.js new file mode 100644 index 0000000..b7d42e7 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/constant.js @@ -0,0 +1,5 @@ +export default function(x) { + return function() { + return x; + }; +} diff --git a/frontend/node_modules/d3-selection/src/create.js b/frontend/node_modules/d3-selection/src/create.js new file mode 100644 index 0000000..077a6a3 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/create.js @@ -0,0 +1,6 @@ +import creator from "./creator.js"; +import select from "./select.js"; + +export default function(name) { + return select(creator(name).call(document.documentElement)); +} diff --git a/frontend/node_modules/d3-selection/src/creator.js b/frontend/node_modules/d3-selection/src/creator.js new file mode 100644 index 0000000..4f1b162 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/creator.js @@ -0,0 +1,25 @@ +import namespace from "./namespace.js"; +import {xhtml} from "./namespaces.js"; + +function creatorInherit(name) { + return function() { + var document = this.ownerDocument, + uri = this.namespaceURI; + return uri === xhtml && document.documentElement.namespaceURI === xhtml + ? document.createElement(name) + : document.createElementNS(uri, name); + }; +} + +function creatorFixed(fullname) { + return function() { + return this.ownerDocument.createElementNS(fullname.space, fullname.local); + }; +} + +export default function(name) { + var fullname = namespace(name); + return (fullname.local + ? creatorFixed + : creatorInherit)(fullname); +} diff --git a/frontend/node_modules/d3-selection/src/identity.js b/frontend/node_modules/d3-selection/src/identity.js new file mode 100644 index 0000000..b2f94b2 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/identity.js @@ -0,0 +1,3 @@ +export default function(x) { + return x; +} diff --git a/frontend/node_modules/d3-selection/src/index.js b/frontend/node_modules/d3-selection/src/index.js new file mode 100644 index 0000000..dc51a3b --- /dev/null +++ b/frontend/node_modules/d3-selection/src/index.js @@ -0,0 +1,15 @@ +export {default as create} from "./create.js"; +export {default as creator} from "./creator.js"; +export {default as local} from "./local.js"; +export {default as matcher} from "./matcher.js"; +export {default as namespace} from "./namespace.js"; +export {default as namespaces} from "./namespaces.js"; +export {default as pointer} from "./pointer.js"; +export {default as pointers} from "./pointers.js"; +export {default as select} from "./select.js"; +export {default as selectAll} from "./selectAll.js"; +export {default as selection} from "./selection/index.js"; +export {default as selector} from "./selector.js"; +export {default as selectorAll} from "./selectorAll.js"; +export {styleValue as style} from "./selection/style.js"; +export {default as window} from "./window.js"; diff --git a/frontend/node_modules/d3-selection/src/local.js b/frontend/node_modules/d3-selection/src/local.js new file mode 100644 index 0000000..ab4c20f --- /dev/null +++ b/frontend/node_modules/d3-selection/src/local.js @@ -0,0 +1,27 @@ +var nextId = 0; + +export default function local() { + return new Local; +} + +function Local() { + this._ = "@" + (++nextId).toString(36); +} + +Local.prototype = local.prototype = { + constructor: Local, + get: function(node) { + var id = this._; + while (!(id in node)) if (!(node = node.parentNode)) return; + return node[id]; + }, + set: function(node, value) { + return node[this._] = value; + }, + remove: function(node) { + return this._ in node && delete node[this._]; + }, + toString: function() { + return this._; + } +}; diff --git a/frontend/node_modules/d3-selection/src/matcher.js b/frontend/node_modules/d3-selection/src/matcher.js new file mode 100644 index 0000000..854b0d9 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/matcher.js @@ -0,0 +1,12 @@ +export default function(selector) { + return function() { + return this.matches(selector); + }; +} + +export function childMatcher(selector) { + return function(node) { + return node.matches(selector); + }; +} + diff --git a/frontend/node_modules/d3-selection/src/namespace.js b/frontend/node_modules/d3-selection/src/namespace.js new file mode 100644 index 0000000..72db9df --- /dev/null +++ b/frontend/node_modules/d3-selection/src/namespace.js @@ -0,0 +1,7 @@ +import namespaces from "./namespaces.js"; + +export default function(name) { + var prefix = name += "", i = prefix.indexOf(":"); + if (i >= 0 && (prefix = name.slice(0, i)) !== "xmlns") name = name.slice(i + 1); + return namespaces.hasOwnProperty(prefix) ? {space: namespaces[prefix], local: name} : name; // eslint-disable-line no-prototype-builtins +} diff --git a/frontend/node_modules/d3-selection/src/namespaces.js b/frontend/node_modules/d3-selection/src/namespaces.js new file mode 100644 index 0000000..01749bd --- /dev/null +++ b/frontend/node_modules/d3-selection/src/namespaces.js @@ -0,0 +1,9 @@ +export var xhtml = "http://www.w3.org/1999/xhtml"; + +export default { + svg: "http://www.w3.org/2000/svg", + xhtml: xhtml, + xlink: "http://www.w3.org/1999/xlink", + xml: "http://www.w3.org/XML/1998/namespace", + xmlns: "http://www.w3.org/2000/xmlns/" +}; diff --git a/frontend/node_modules/d3-selection/src/pointer.js b/frontend/node_modules/d3-selection/src/pointer.js new file mode 100644 index 0000000..3e2298f --- /dev/null +++ b/frontend/node_modules/d3-selection/src/pointer.js @@ -0,0 +1,20 @@ +import sourceEvent from "./sourceEvent.js"; + +export default function(event, node) { + event = sourceEvent(event); + if (node === undefined) node = event.currentTarget; + if (node) { + var svg = node.ownerSVGElement || node; + if (svg.createSVGPoint) { + var point = svg.createSVGPoint(); + point.x = event.clientX, point.y = event.clientY; + point = point.matrixTransform(node.getScreenCTM().inverse()); + return [point.x, point.y]; + } + if (node.getBoundingClientRect) { + var rect = node.getBoundingClientRect(); + return [event.clientX - rect.left - node.clientLeft, event.clientY - rect.top - node.clientTop]; + } + } + return [event.pageX, event.pageY]; +} diff --git a/frontend/node_modules/d3-selection/src/pointers.js b/frontend/node_modules/d3-selection/src/pointers.js new file mode 100644 index 0000000..43d17d1 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/pointers.js @@ -0,0 +1,11 @@ +import pointer from "./pointer.js"; +import sourceEvent from "./sourceEvent.js"; + +export default function(events, node) { + if (events.target) { // i.e., instanceof Event, not TouchList or iterable + events = sourceEvent(events); + if (node === undefined) node = events.currentTarget; + events = events.touches || [events]; + } + return Array.from(events, event => pointer(event, node)); +} diff --git a/frontend/node_modules/d3-selection/src/select.js b/frontend/node_modules/d3-selection/src/select.js new file mode 100644 index 0000000..dcea22e --- /dev/null +++ b/frontend/node_modules/d3-selection/src/select.js @@ -0,0 +1,7 @@ +import {Selection, root} from "./selection/index.js"; + +export default function(selector) { + return typeof selector === "string" + ? new Selection([[document.querySelector(selector)]], [document.documentElement]) + : new Selection([[selector]], root); +} diff --git a/frontend/node_modules/d3-selection/src/selectAll.js b/frontend/node_modules/d3-selection/src/selectAll.js new file mode 100644 index 0000000..b6ecc3d --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selectAll.js @@ -0,0 +1,8 @@ +import array from "./array.js"; +import {Selection, root} from "./selection/index.js"; + +export default function(selector) { + return typeof selector === "string" + ? new Selection([document.querySelectorAll(selector)], [document.documentElement]) + : new Selection([array(selector)], root); +} diff --git a/frontend/node_modules/d3-selection/src/selection/append.js b/frontend/node_modules/d3-selection/src/selection/append.js new file mode 100644 index 0000000..3333633 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/append.js @@ -0,0 +1,8 @@ +import creator from "../creator.js"; + +export default function(name) { + var create = typeof name === "function" ? name : creator(name); + return this.select(function() { + return this.appendChild(create.apply(this, arguments)); + }); +} diff --git a/frontend/node_modules/d3-selection/src/selection/attr.js b/frontend/node_modules/d3-selection/src/selection/attr.js new file mode 100644 index 0000000..5e93353 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/attr.js @@ -0,0 +1,57 @@ +import namespace from "../namespace.js"; + +function attrRemove(name) { + return function() { + this.removeAttribute(name); + }; +} + +function attrRemoveNS(fullname) { + return function() { + this.removeAttributeNS(fullname.space, fullname.local); + }; +} + +function attrConstant(name, value) { + return function() { + this.setAttribute(name, value); + }; +} + +function attrConstantNS(fullname, value) { + return function() { + this.setAttributeNS(fullname.space, fullname.local, value); + }; +} + +function attrFunction(name, value) { + return function() { + var v = value.apply(this, arguments); + if (v == null) this.removeAttribute(name); + else this.setAttribute(name, v); + }; +} + +function attrFunctionNS(fullname, value) { + return function() { + var v = value.apply(this, arguments); + if (v == null) this.removeAttributeNS(fullname.space, fullname.local); + else this.setAttributeNS(fullname.space, fullname.local, v); + }; +} + +export default function(name, value) { + var fullname = namespace(name); + + if (arguments.length < 2) { + var node = this.node(); + return fullname.local + ? node.getAttributeNS(fullname.space, fullname.local) + : node.getAttribute(fullname); + } + + return this.each((value == null + ? (fullname.local ? attrRemoveNS : attrRemove) : (typeof value === "function" + ? (fullname.local ? attrFunctionNS : attrFunction) + : (fullname.local ? attrConstantNS : attrConstant)))(fullname, value)); +} diff --git a/frontend/node_modules/d3-selection/src/selection/call.js b/frontend/node_modules/d3-selection/src/selection/call.js new file mode 100644 index 0000000..2c41eee --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/call.js @@ -0,0 +1,6 @@ +export default function() { + var callback = arguments[0]; + arguments[0] = this; + callback.apply(null, arguments); + return this; +} diff --git a/frontend/node_modules/d3-selection/src/selection/classed.js b/frontend/node_modules/d3-selection/src/selection/classed.js new file mode 100644 index 0000000..b356373 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/classed.js @@ -0,0 +1,75 @@ +function classArray(string) { + return string.trim().split(/^|\s+/); +} + +function classList(node) { + return node.classList || new ClassList(node); +} + +function ClassList(node) { + this._node = node; + this._names = classArray(node.getAttribute("class") || ""); +} + +ClassList.prototype = { + add: function(name) { + var i = this._names.indexOf(name); + if (i < 0) { + this._names.push(name); + this._node.setAttribute("class", this._names.join(" ")); + } + }, + remove: function(name) { + var i = this._names.indexOf(name); + if (i >= 0) { + this._names.splice(i, 1); + this._node.setAttribute("class", this._names.join(" ")); + } + }, + contains: function(name) { + return this._names.indexOf(name) >= 0; + } +}; + +function classedAdd(node, names) { + var list = classList(node), i = -1, n = names.length; + while (++i < n) list.add(names[i]); +} + +function classedRemove(node, names) { + var list = classList(node), i = -1, n = names.length; + while (++i < n) list.remove(names[i]); +} + +function classedTrue(names) { + return function() { + classedAdd(this, names); + }; +} + +function classedFalse(names) { + return function() { + classedRemove(this, names); + }; +} + +function classedFunction(names, value) { + return function() { + (value.apply(this, arguments) ? classedAdd : classedRemove)(this, names); + }; +} + +export default function(name, value) { + var names = classArray(name + ""); + + if (arguments.length < 2) { + var list = classList(this.node()), i = -1, n = names.length; + while (++i < n) if (!list.contains(names[i])) return false; + return true; + } + + return this.each((typeof value === "function" + ? classedFunction : value + ? classedTrue + : classedFalse)(names, value)); +} diff --git a/frontend/node_modules/d3-selection/src/selection/clone.js b/frontend/node_modules/d3-selection/src/selection/clone.js new file mode 100644 index 0000000..5e273bf --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/clone.js @@ -0,0 +1,13 @@ +function selection_cloneShallow() { + var clone = this.cloneNode(false), parent = this.parentNode; + return parent ? parent.insertBefore(clone, this.nextSibling) : clone; +} + +function selection_cloneDeep() { + var clone = this.cloneNode(true), parent = this.parentNode; + return parent ? parent.insertBefore(clone, this.nextSibling) : clone; +} + +export default function(deep) { + return this.select(deep ? selection_cloneDeep : selection_cloneShallow); +} diff --git a/frontend/node_modules/d3-selection/src/selection/data.js b/frontend/node_modules/d3-selection/src/selection/data.js new file mode 100644 index 0000000..8eb0713 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/data.js @@ -0,0 +1,128 @@ +import {Selection} from "./index.js"; +import {EnterNode} from "./enter.js"; +import constant from "../constant.js"; + +function bindIndex(parent, group, enter, update, exit, data) { + var i = 0, + node, + groupLength = group.length, + dataLength = data.length; + + // Put any non-null nodes that fit into update. + // Put any null nodes into enter. + // Put any remaining data into enter. + for (; i < dataLength; ++i) { + if (node = group[i]) { + node.__data__ = data[i]; + update[i] = node; + } else { + enter[i] = new EnterNode(parent, data[i]); + } + } + + // Put any non-null nodes that don’t fit into exit. + for (; i < groupLength; ++i) { + if (node = group[i]) { + exit[i] = node; + } + } +} + +function bindKey(parent, group, enter, update, exit, data, key) { + var i, + node, + nodeByKeyValue = new Map, + groupLength = group.length, + dataLength = data.length, + keyValues = new Array(groupLength), + keyValue; + + // Compute the key for each node. + // If multiple nodes have the same key, the duplicates are added to exit. + for (i = 0; i < groupLength; ++i) { + if (node = group[i]) { + keyValues[i] = keyValue = key.call(node, node.__data__, i, group) + ""; + if (nodeByKeyValue.has(keyValue)) { + exit[i] = node; + } else { + nodeByKeyValue.set(keyValue, node); + } + } + } + + // Compute the key for each datum. + // If there a node associated with this key, join and add it to update. + // If there is not (or the key is a duplicate), add it to enter. + for (i = 0; i < dataLength; ++i) { + keyValue = key.call(parent, data[i], i, data) + ""; + if (node = nodeByKeyValue.get(keyValue)) { + update[i] = node; + node.__data__ = data[i]; + nodeByKeyValue.delete(keyValue); + } else { + enter[i] = new EnterNode(parent, data[i]); + } + } + + // Add any remaining nodes that were not bound to data to exit. + for (i = 0; i < groupLength; ++i) { + if ((node = group[i]) && (nodeByKeyValue.get(keyValues[i]) === node)) { + exit[i] = node; + } + } +} + +function datum(node) { + return node.__data__; +} + +export default function(value, key) { + if (!arguments.length) return Array.from(this, datum); + + var bind = key ? bindKey : bindIndex, + parents = this._parents, + groups = this._groups; + + if (typeof value !== "function") value = constant(value); + + for (var m = groups.length, update = new Array(m), enter = new Array(m), exit = new Array(m), j = 0; j < m; ++j) { + var parent = parents[j], + group = groups[j], + groupLength = group.length, + data = arraylike(value.call(parent, parent && parent.__data__, j, parents)), + dataLength = data.length, + enterGroup = enter[j] = new Array(dataLength), + updateGroup = update[j] = new Array(dataLength), + exitGroup = exit[j] = new Array(groupLength); + + bind(parent, group, enterGroup, updateGroup, exitGroup, data, key); + + // Now connect the enter nodes to their following update node, such that + // appendChild can insert the materialized enter node before this node, + // rather than at the end of the parent node. + for (var i0 = 0, i1 = 0, previous, next; i0 < dataLength; ++i0) { + if (previous = enterGroup[i0]) { + if (i0 >= i1) i1 = i0 + 1; + while (!(next = updateGroup[i1]) && ++i1 < dataLength); + previous._next = next || null; + } + } + } + + update = new Selection(update, parents); + update._enter = enter; + update._exit = exit; + return update; +} + +// Given some data, this returns an array-like view of it: an object that +// exposes a length property and allows numeric indexing. Note that unlike +// selectAll, this isn’t worried about “live” collections because the resulting +// array will only be used briefly while data is being bound. (It is possible to +// cause the data to change while iterating by using a key function, but please +// don’t; we’d rather avoid a gratuitous copy.) +function arraylike(data) { + return typeof data === "object" && "length" in data + ? data // Array, TypedArray, NodeList, array-like + : Array.from(data); // Map, Set, iterable, string, or anything else +} diff --git a/frontend/node_modules/d3-selection/src/selection/datum.js b/frontend/node_modules/d3-selection/src/selection/datum.js new file mode 100644 index 0000000..5de4e58 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/datum.js @@ -0,0 +1,5 @@ +export default function(value) { + return arguments.length + ? this.property("__data__", value) + : this.node().__data__; +} diff --git a/frontend/node_modules/d3-selection/src/selection/dispatch.js b/frontend/node_modules/d3-selection/src/selection/dispatch.js new file mode 100644 index 0000000..8f57915 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/dispatch.js @@ -0,0 +1,34 @@ +import defaultView from "../window.js"; + +function dispatchEvent(node, type, params) { + var window = defaultView(node), + event = window.CustomEvent; + + if (typeof event === "function") { + event = new event(type, params); + } else { + event = window.document.createEvent("Event"); + if (params) event.initEvent(type, params.bubbles, params.cancelable), event.detail = params.detail; + else event.initEvent(type, false, false); + } + + node.dispatchEvent(event); +} + +function dispatchConstant(type, params) { + return function() { + return dispatchEvent(this, type, params); + }; +} + +function dispatchFunction(type, params) { + return function() { + return dispatchEvent(this, type, params.apply(this, arguments)); + }; +} + +export default function(type, params) { + return this.each((typeof params === "function" + ? dispatchFunction + : dispatchConstant)(type, params)); +} diff --git a/frontend/node_modules/d3-selection/src/selection/each.js b/frontend/node_modules/d3-selection/src/selection/each.js new file mode 100644 index 0000000..260af8f --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/each.js @@ -0,0 +1,10 @@ +export default function(callback) { + + for (var groups = this._groups, j = 0, m = groups.length; j < m; ++j) { + for (var group = groups[j], i = 0, n = group.length, node; i < n; ++i) { + if (node = group[i]) callback.call(node, node.__data__, i, group); + } + } + + return this; +} diff --git a/frontend/node_modules/d3-selection/src/selection/empty.js b/frontend/node_modules/d3-selection/src/selection/empty.js new file mode 100644 index 0000000..4e2cf42 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/empty.js @@ -0,0 +1,3 @@ +export default function() { + return !this.node(); +} diff --git a/frontend/node_modules/d3-selection/src/selection/enter.js b/frontend/node_modules/d3-selection/src/selection/enter.js new file mode 100644 index 0000000..83a3ed4 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/enter.js @@ -0,0 +1,22 @@ +import sparse from "./sparse.js"; +import {Selection} from "./index.js"; + +export default function() { + return new Selection(this._enter || this._groups.map(sparse), this._parents); +} + +export function EnterNode(parent, datum) { + this.ownerDocument = parent.ownerDocument; + this.namespaceURI = parent.namespaceURI; + this._next = null; + this._parent = parent; + this.__data__ = datum; +} + +EnterNode.prototype = { + constructor: EnterNode, + appendChild: function(child) { return this._parent.insertBefore(child, this._next); }, + insertBefore: function(child, next) { return this._parent.insertBefore(child, next); }, + querySelector: function(selector) { return this._parent.querySelector(selector); }, + querySelectorAll: function(selector) { return this._parent.querySelectorAll(selector); } +}; diff --git a/frontend/node_modules/d3-selection/src/selection/exit.js b/frontend/node_modules/d3-selection/src/selection/exit.js new file mode 100644 index 0000000..f5d7b45 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/exit.js @@ -0,0 +1,6 @@ +import sparse from "./sparse.js"; +import {Selection} from "./index.js"; + +export default function() { + return new Selection(this._exit || this._groups.map(sparse), this._parents); +} diff --git a/frontend/node_modules/d3-selection/src/selection/filter.js b/frontend/node_modules/d3-selection/src/selection/filter.js new file mode 100644 index 0000000..74b3d6f --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/filter.js @@ -0,0 +1,16 @@ +import {Selection} from "./index.js"; +import matcher from "../matcher.js"; + +export default function(match) { + if (typeof match !== "function") match = matcher(match); + + for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, subgroup = subgroups[j] = [], node, i = 0; i < n; ++i) { + if ((node = group[i]) && match.call(node, node.__data__, i, group)) { + subgroup.push(node); + } + } + } + + return new Selection(subgroups, this._parents); +} diff --git a/frontend/node_modules/d3-selection/src/selection/html.js b/frontend/node_modules/d3-selection/src/selection/html.js new file mode 100644 index 0000000..df27442 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/html.js @@ -0,0 +1,25 @@ +function htmlRemove() { + this.innerHTML = ""; +} + +function htmlConstant(value) { + return function() { + this.innerHTML = value; + }; +} + +function htmlFunction(value) { + return function() { + var v = value.apply(this, arguments); + this.innerHTML = v == null ? "" : v; + }; +} + +export default function(value) { + return arguments.length + ? this.each(value == null + ? htmlRemove : (typeof value === "function" + ? htmlFunction + : htmlConstant)(value)) + : this.node().innerHTML; +} diff --git a/frontend/node_modules/d3-selection/src/selection/index.js b/frontend/node_modules/d3-selection/src/selection/index.js new file mode 100644 index 0000000..a593a21 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/index.js @@ -0,0 +1,90 @@ +import selection_select from "./select.js"; +import selection_selectAll from "./selectAll.js"; +import selection_selectChild from "./selectChild.js"; +import selection_selectChildren from "./selectChildren.js"; +import selection_filter from "./filter.js"; +import selection_data from "./data.js"; +import selection_enter from "./enter.js"; +import selection_exit from "./exit.js"; +import selection_join from "./join.js"; +import selection_merge from "./merge.js"; +import selection_order from "./order.js"; +import selection_sort from "./sort.js"; +import selection_call from "./call.js"; +import selection_nodes from "./nodes.js"; +import selection_node from "./node.js"; +import selection_size from "./size.js"; +import selection_empty from "./empty.js"; +import selection_each from "./each.js"; +import selection_attr from "./attr.js"; +import selection_style from "./style.js"; +import selection_property from "./property.js"; +import selection_classed from "./classed.js"; +import selection_text from "./text.js"; +import selection_html from "./html.js"; +import selection_raise from "./raise.js"; +import selection_lower from "./lower.js"; +import selection_append from "./append.js"; +import selection_insert from "./insert.js"; +import selection_remove from "./remove.js"; +import selection_clone from "./clone.js"; +import selection_datum from "./datum.js"; +import selection_on from "./on.js"; +import selection_dispatch from "./dispatch.js"; +import selection_iterator from "./iterator.js"; + +export var root = [null]; + +export function Selection(groups, parents) { + this._groups = groups; + this._parents = parents; +} + +function selection() { + return new Selection([[document.documentElement]], root); +} + +function selection_selection() { + return this; +} + +Selection.prototype = selection.prototype = { + constructor: Selection, + select: selection_select, + selectAll: selection_selectAll, + selectChild: selection_selectChild, + selectChildren: selection_selectChildren, + filter: selection_filter, + data: selection_data, + enter: selection_enter, + exit: selection_exit, + join: selection_join, + merge: selection_merge, + selection: selection_selection, + order: selection_order, + sort: selection_sort, + call: selection_call, + nodes: selection_nodes, + node: selection_node, + size: selection_size, + empty: selection_empty, + each: selection_each, + attr: selection_attr, + style: selection_style, + property: selection_property, + classed: selection_classed, + text: selection_text, + html: selection_html, + raise: selection_raise, + lower: selection_lower, + append: selection_append, + insert: selection_insert, + remove: selection_remove, + clone: selection_clone, + datum: selection_datum, + on: selection_on, + dispatch: selection_dispatch, + [Symbol.iterator]: selection_iterator +}; + +export default selection; diff --git a/frontend/node_modules/d3-selection/src/selection/insert.js b/frontend/node_modules/d3-selection/src/selection/insert.js new file mode 100644 index 0000000..1733de5 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/insert.js @@ -0,0 +1,14 @@ +import creator from "../creator.js"; +import selector from "../selector.js"; + +function constantNull() { + return null; +} + +export default function(name, before) { + var create = typeof name === "function" ? name : creator(name), + select = before == null ? constantNull : typeof before === "function" ? before : selector(before); + return this.select(function() { + return this.insertBefore(create.apply(this, arguments), select.apply(this, arguments) || null); + }); +} diff --git a/frontend/node_modules/d3-selection/src/selection/iterator.js b/frontend/node_modules/d3-selection/src/selection/iterator.js new file mode 100644 index 0000000..5872819 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/iterator.js @@ -0,0 +1,7 @@ +export default function*() { + for (var groups = this._groups, j = 0, m = groups.length; j < m; ++j) { + for (var group = groups[j], i = 0, n = group.length, node; i < n; ++i) { + if (node = group[i]) yield node; + } + } +} diff --git a/frontend/node_modules/d3-selection/src/selection/join.js b/frontend/node_modules/d3-selection/src/selection/join.js new file mode 100644 index 0000000..8b47281 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/join.js @@ -0,0 +1,15 @@ +export default function(onenter, onupdate, onexit) { + var enter = this.enter(), update = this, exit = this.exit(); + if (typeof onenter === "function") { + enter = onenter(enter); + if (enter) enter = enter.selection(); + } else { + enter = enter.append(onenter + ""); + } + if (onupdate != null) { + update = onupdate(update); + if (update) update = update.selection(); + } + if (onexit == null) exit.remove(); else onexit(exit); + return enter && update ? enter.merge(update).order() : update; +} diff --git a/frontend/node_modules/d3-selection/src/selection/lower.js b/frontend/node_modules/d3-selection/src/selection/lower.js new file mode 100644 index 0000000..d724713 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/lower.js @@ -0,0 +1,7 @@ +function lower() { + if (this.previousSibling) this.parentNode.insertBefore(this, this.parentNode.firstChild); +} + +export default function() { + return this.each(lower); +} diff --git a/frontend/node_modules/d3-selection/src/selection/merge.js b/frontend/node_modules/d3-selection/src/selection/merge.js new file mode 100644 index 0000000..fd68d6c --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/merge.js @@ -0,0 +1,19 @@ +import {Selection} from "./index.js"; + +export default function(context) { + var selection = context.selection ? context.selection() : context; + + for (var groups0 = this._groups, groups1 = selection._groups, m0 = groups0.length, m1 = groups1.length, m = Math.min(m0, m1), merges = new Array(m0), j = 0; j < m; ++j) { + for (var group0 = groups0[j], group1 = groups1[j], n = group0.length, merge = merges[j] = new Array(n), node, i = 0; i < n; ++i) { + if (node = group0[i] || group1[i]) { + merge[i] = node; + } + } + } + + for (; j < m0; ++j) { + merges[j] = groups0[j]; + } + + return new Selection(merges, this._parents); +} diff --git a/frontend/node_modules/d3-selection/src/selection/node.js b/frontend/node_modules/d3-selection/src/selection/node.js new file mode 100644 index 0000000..0691cbc --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/node.js @@ -0,0 +1,11 @@ +export default function() { + + for (var groups = this._groups, j = 0, m = groups.length; j < m; ++j) { + for (var group = groups[j], i = 0, n = group.length; i < n; ++i) { + var node = group[i]; + if (node) return node; + } + } + + return null; +} diff --git a/frontend/node_modules/d3-selection/src/selection/nodes.js b/frontend/node_modules/d3-selection/src/selection/nodes.js new file mode 100644 index 0000000..7f38090 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/nodes.js @@ -0,0 +1,3 @@ +export default function() { + return Array.from(this); +} diff --git a/frontend/node_modules/d3-selection/src/selection/on.js b/frontend/node_modules/d3-selection/src/selection/on.js new file mode 100644 index 0000000..7906c8c --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/on.js @@ -0,0 +1,67 @@ +function contextListener(listener) { + return function(event) { + listener.call(this, event, this.__data__); + }; +} + +function parseTypenames(typenames) { + return typenames.trim().split(/^|\s+/).map(function(t) { + var name = "", i = t.indexOf("."); + if (i >= 0) name = t.slice(i + 1), t = t.slice(0, i); + return {type: t, name: name}; + }); +} + +function onRemove(typename) { + return function() { + var on = this.__on; + if (!on) return; + for (var j = 0, i = -1, m = on.length, o; j < m; ++j) { + if (o = on[j], (!typename.type || o.type === typename.type) && o.name === typename.name) { + this.removeEventListener(o.type, o.listener, o.options); + } else { + on[++i] = o; + } + } + if (++i) on.length = i; + else delete this.__on; + }; +} + +function onAdd(typename, value, options) { + return function() { + var on = this.__on, o, listener = contextListener(value); + if (on) for (var j = 0, m = on.length; j < m; ++j) { + if ((o = on[j]).type === typename.type && o.name === typename.name) { + this.removeEventListener(o.type, o.listener, o.options); + this.addEventListener(o.type, o.listener = listener, o.options = options); + o.value = value; + return; + } + } + this.addEventListener(typename.type, listener, options); + o = {type: typename.type, name: typename.name, value: value, listener: listener, options: options}; + if (!on) this.__on = [o]; + else on.push(o); + }; +} + +export default function(typename, value, options) { + var typenames = parseTypenames(typename + ""), i, n = typenames.length, t; + + if (arguments.length < 2) { + var on = this.node().__on; + if (on) for (var j = 0, m = on.length, o; j < m; ++j) { + for (i = 0, o = on[j]; i < n; ++i) { + if ((t = typenames[i]).type === o.type && t.name === o.name) { + return o.value; + } + } + } + return; + } + + on = value ? onAdd : onRemove; + for (i = 0; i < n; ++i) this.each(on(typenames[i], value, options)); + return this; +} diff --git a/frontend/node_modules/d3-selection/src/selection/order.js b/frontend/node_modules/d3-selection/src/selection/order.js new file mode 100644 index 0000000..f8c52b4 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/order.js @@ -0,0 +1,13 @@ +export default function() { + + for (var groups = this._groups, j = -1, m = groups.length; ++j < m;) { + for (var group = groups[j], i = group.length - 1, next = group[i], node; --i >= 0;) { + if (node = group[i]) { + if (next && node.compareDocumentPosition(next) ^ 4) next.parentNode.insertBefore(node, next); + next = node; + } + } + } + + return this; +} diff --git a/frontend/node_modules/d3-selection/src/selection/property.js b/frontend/node_modules/d3-selection/src/selection/property.js new file mode 100644 index 0000000..3b7efd3 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/property.js @@ -0,0 +1,28 @@ +function propertyRemove(name) { + return function() { + delete this[name]; + }; +} + +function propertyConstant(name, value) { + return function() { + this[name] = value; + }; +} + +function propertyFunction(name, value) { + return function() { + var v = value.apply(this, arguments); + if (v == null) delete this[name]; + else this[name] = v; + }; +} + +export default function(name, value) { + return arguments.length > 1 + ? this.each((value == null + ? propertyRemove : typeof value === "function" + ? propertyFunction + : propertyConstant)(name, value)) + : this.node()[name]; +} diff --git a/frontend/node_modules/d3-selection/src/selection/raise.js b/frontend/node_modules/d3-selection/src/selection/raise.js new file mode 100644 index 0000000..3e9e1c9 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/raise.js @@ -0,0 +1,7 @@ +function raise() { + if (this.nextSibling) this.parentNode.appendChild(this); +} + +export default function() { + return this.each(raise); +} diff --git a/frontend/node_modules/d3-selection/src/selection/remove.js b/frontend/node_modules/d3-selection/src/selection/remove.js new file mode 100644 index 0000000..12a8106 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/remove.js @@ -0,0 +1,8 @@ +function remove() { + var parent = this.parentNode; + if (parent) parent.removeChild(this); +} + +export default function() { + return this.each(remove); +} diff --git a/frontend/node_modules/d3-selection/src/selection/select.js b/frontend/node_modules/d3-selection/src/selection/select.js new file mode 100644 index 0000000..223cc24 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/select.js @@ -0,0 +1,17 @@ +import {Selection} from "./index.js"; +import selector from "../selector.js"; + +export default function(select) { + if (typeof select !== "function") select = selector(select); + + for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, subgroup = subgroups[j] = new Array(n), node, subnode, i = 0; i < n; ++i) { + if ((node = group[i]) && (subnode = select.call(node, node.__data__, i, group))) { + if ("__data__" in node) subnode.__data__ = node.__data__; + subgroup[i] = subnode; + } + } + } + + return new Selection(subgroups, this._parents); +} diff --git a/frontend/node_modules/d3-selection/src/selection/selectAll.js b/frontend/node_modules/d3-selection/src/selection/selectAll.js new file mode 100644 index 0000000..2a87a27 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/selectAll.js @@ -0,0 +1,25 @@ +import {Selection} from "./index.js"; +import array from "../array.js"; +import selectorAll from "../selectorAll.js"; + +function arrayAll(select) { + return function() { + return array(select.apply(this, arguments)); + }; +} + +export default function(select) { + if (typeof select === "function") select = arrayAll(select); + else select = selectorAll(select); + + for (var groups = this._groups, m = groups.length, subgroups = [], parents = [], j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) { + if (node = group[i]) { + subgroups.push(select.call(node, node.__data__, i, group)); + parents.push(node); + } + } + } + + return new Selection(subgroups, parents); +} diff --git a/frontend/node_modules/d3-selection/src/selection/selectChild.js b/frontend/node_modules/d3-selection/src/selection/selectChild.js new file mode 100644 index 0000000..d042794 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/selectChild.js @@ -0,0 +1,18 @@ +import {childMatcher} from "../matcher.js"; + +var find = Array.prototype.find; + +function childFind(match) { + return function() { + return find.call(this.children, match); + }; +} + +function childFirst() { + return this.firstElementChild; +} + +export default function(match) { + return this.select(match == null ? childFirst + : childFind(typeof match === "function" ? match : childMatcher(match))); +} diff --git a/frontend/node_modules/d3-selection/src/selection/selectChildren.js b/frontend/node_modules/d3-selection/src/selection/selectChildren.js new file mode 100644 index 0000000..d514d3b --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/selectChildren.js @@ -0,0 +1,18 @@ +import {childMatcher} from "../matcher.js"; + +var filter = Array.prototype.filter; + +function children() { + return Array.from(this.children); +} + +function childrenFilter(match) { + return function() { + return filter.call(this.children, match); + }; +} + +export default function(match) { + return this.selectAll(match == null ? children + : childrenFilter(typeof match === "function" ? match : childMatcher(match))); +} diff --git a/frontend/node_modules/d3-selection/src/selection/size.js b/frontend/node_modules/d3-selection/src/selection/size.js new file mode 100644 index 0000000..e07eaa4 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/size.js @@ -0,0 +1,5 @@ +export default function() { + let size = 0; + for (const node of this) ++size; // eslint-disable-line no-unused-vars + return size; +} diff --git a/frontend/node_modules/d3-selection/src/selection/sort.js b/frontend/node_modules/d3-selection/src/selection/sort.js new file mode 100644 index 0000000..336760f --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/sort.js @@ -0,0 +1,24 @@ +import {Selection} from "./index.js"; + +export default function(compare) { + if (!compare) compare = ascending; + + function compareNode(a, b) { + return a && b ? compare(a.__data__, b.__data__) : !a - !b; + } + + for (var groups = this._groups, m = groups.length, sortgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, sortgroup = sortgroups[j] = new Array(n), node, i = 0; i < n; ++i) { + if (node = group[i]) { + sortgroup[i] = node; + } + } + sortgroup.sort(compareNode); + } + + return new Selection(sortgroups, this._parents).order(); +} + +function ascending(a, b) { + return a < b ? -1 : a > b ? 1 : a >= b ? 0 : NaN; +} diff --git a/frontend/node_modules/d3-selection/src/selection/sparse.js b/frontend/node_modules/d3-selection/src/selection/sparse.js new file mode 100644 index 0000000..7b261ad --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/sparse.js @@ -0,0 +1,3 @@ +export default function(update) { + return new Array(update.length); +} diff --git a/frontend/node_modules/d3-selection/src/selection/style.js b/frontend/node_modules/d3-selection/src/selection/style.js new file mode 100644 index 0000000..7e0f058 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/style.js @@ -0,0 +1,35 @@ +import defaultView from "../window.js"; + +function styleRemove(name) { + return function() { + this.style.removeProperty(name); + }; +} + +function styleConstant(name, value, priority) { + return function() { + this.style.setProperty(name, value, priority); + }; +} + +function styleFunction(name, value, priority) { + return function() { + var v = value.apply(this, arguments); + if (v == null) this.style.removeProperty(name); + else this.style.setProperty(name, v, priority); + }; +} + +export default function(name, value, priority) { + return arguments.length > 1 + ? this.each((value == null + ? styleRemove : typeof value === "function" + ? styleFunction + : styleConstant)(name, value, priority == null ? "" : priority)) + : styleValue(this.node(), name); +} + +export function styleValue(node, name) { + return node.style.getPropertyValue(name) + || defaultView(node).getComputedStyle(node, null).getPropertyValue(name); +} diff --git a/frontend/node_modules/d3-selection/src/selection/text.js b/frontend/node_modules/d3-selection/src/selection/text.js new file mode 100644 index 0000000..a902980 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selection/text.js @@ -0,0 +1,25 @@ +function textRemove() { + this.textContent = ""; +} + +function textConstant(value) { + return function() { + this.textContent = value; + }; +} + +function textFunction(value) { + return function() { + var v = value.apply(this, arguments); + this.textContent = v == null ? "" : v; + }; +} + +export default function(value) { + return arguments.length + ? this.each(value == null + ? textRemove : (typeof value === "function" + ? textFunction + : textConstant)(value)) + : this.node().textContent; +} diff --git a/frontend/node_modules/d3-selection/src/selector.js b/frontend/node_modules/d3-selection/src/selector.js new file mode 100644 index 0000000..058bd73 --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selector.js @@ -0,0 +1,7 @@ +function none() {} + +export default function(selector) { + return selector == null ? none : function() { + return this.querySelector(selector); + }; +} diff --git a/frontend/node_modules/d3-selection/src/selectorAll.js b/frontend/node_modules/d3-selection/src/selectorAll.js new file mode 100644 index 0000000..ea42ffa --- /dev/null +++ b/frontend/node_modules/d3-selection/src/selectorAll.js @@ -0,0 +1,9 @@ +function empty() { + return []; +} + +export default function(selector) { + return selector == null ? empty : function() { + return this.querySelectorAll(selector); + }; +} diff --git a/frontend/node_modules/d3-selection/src/sourceEvent.js b/frontend/node_modules/d3-selection/src/sourceEvent.js new file mode 100644 index 0000000..8ab130e --- /dev/null +++ b/frontend/node_modules/d3-selection/src/sourceEvent.js @@ -0,0 +1,5 @@ +export default function(event) { + let sourceEvent; + while (sourceEvent = event.sourceEvent) event = sourceEvent; + return event; +} diff --git a/frontend/node_modules/d3-selection/src/window.js b/frontend/node_modules/d3-selection/src/window.js new file mode 100644 index 0000000..ca1105b --- /dev/null +++ b/frontend/node_modules/d3-selection/src/window.js @@ -0,0 +1,5 @@ +export default function(node) { + return (node.ownerDocument && node.ownerDocument.defaultView) // node is a Node + || (node.document && node) // node is a Window + || node.defaultView; // node is a Document +} diff --git a/frontend/node_modules/d3-shape/LICENSE b/frontend/node_modules/d3-shape/LICENSE new file mode 100644 index 0000000..fbe44bd --- /dev/null +++ b/frontend/node_modules/d3-shape/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2022 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-shape/README.md b/frontend/node_modules/d3-shape/README.md new file mode 100644 index 0000000..2eba5c1 --- /dev/null +++ b/frontend/node_modules/d3-shape/README.md @@ -0,0 +1,1227 @@ +# d3-shape + +Visualizations typically consist of discrete graphical marks, such as [symbols](#symbols), [arcs](#arcs), [lines](#lines) and [areas](#areas). While the rectangles of a bar chart may be easy enough to generate directly using [SVG](http://www.w3.org/TR/SVG/paths.html#PathData) or [Canvas](http://www.w3.org/TR/2dcontext/#canvaspathmethods), other shapes are complex, such as rounded annular sectors and centripetal Catmull–Rom splines. This module provides a variety of shape generators for your convenience. + +As with other aspects of D3, these shapes are driven by data: each shape generator exposes accessors that control how the input data are mapped to a visual representation. For example, you might define a line generator for a time series by [scaling](https://github.com/d3/d3-scale) fields of your data to fit the chart: + +```js +const line = d3.line() + .x(d => x(d.date)) + .y(d => y(d.value)); +``` + +This line generator can then be used to compute the `d` attribute of an SVG path element: + +```js +path.datum(data).attr("d", line); +``` + +Or you can use it to render to a Canvas 2D context: + +```js +line.context(context)(data); +``` + +For more, read [Introducing d3-shape](https://medium.com/@mbostock/introducing-d3-shape-73f8367e6d12). + +## Installing + +If you use npm, `npm install d3-shape`. You can also download the [latest release on GitHub](https://github.com/d3/d3-shape/releases/latest). For vanilla HTML in modern browsers, import d3-shape from jsDelivr: + +```html + +``` + +For legacy environments, you can load d3-shape’s UMD bundle; a `d3` global is exported: + +```html + + + +``` + +## API Reference + +* [Arcs](#arcs) +* [Pies](#pies) +* [Lines](#lines) +* [Areas](#areas) +* [Curves](#curves) +* [Custom Curves](#custom-curves) +* [Links](#links) +* [Symbols](#symbols) +* [Custom Symbol Types](#custom-symbol-types) +* [Stacks](#stacks) + +Note: all the methods that accept arrays also accept iterables and convert them to arrays internally. + +### Arcs + +[Pie Chart](https://observablehq.com/@d3/pie-chart)[Donut Chart](https://observablehq.com/@d3/donut-chart) + +The arc generator produces a [circular](https://en.wikipedia.org/wiki/Circular_sector) or [annular](https://en.wikipedia.org/wiki/Annulus_\(mathematics\)) sector, as in a pie or donut chart. If the absolute difference between the [start](#arc_startAngle) and [end](#arc_endAngle) angles (the *angular span*) is greater than [τ](https://en.wikipedia.org/wiki/Turn_\(geometry\)#Tau_proposal), the arc generator will produce a complete circle or annulus. If it is less than τ, the arc’s angular length will be equal to the absolute difference between the two angles (going clockwise if the signed difference is positive and anticlockwise if it is negative). If the absolute difference is less than τ, the arc may have [rounded corners](#arc_cornerRadius) and [angular padding](#arc_padAngle). Arcs are always centered at ⟨0,0⟩; use a transform (see: [SVG](http://www.w3.org/TR/SVG/coords.html#TransformAttribute), [Canvas](http://www.w3.org/TR/2dcontext/#transformations)) to move the arc to a different position. + +See also the [pie generator](#pies), which computes the necessary angles to represent an array of data as a pie or donut chart; these angles can then be passed to an arc generator. + +# d3.arc() · [Source](https://github.com/d3/d3-shape/blob/main/src/arc.js) + +Constructs a new arc generator with the default settings. + +# arc(arguments…) · [Source](https://github.com/d3/d3-shape/blob/main/src/arc.js) + +Generates an arc for the given *arguments*. The *arguments* are arbitrary; they are simply propagated to the arc generator’s accessor functions along with the `this` object. For example, with the default settings, an object with radii and angles is expected: + +```js +const arc = d3.arc(); + +arc({ + innerRadius: 0, + outerRadius: 100, + startAngle: 0, + endAngle: Math.PI / 2 +}); // "M0,-100A100,100,0,0,1,100,0L0,0Z" +``` + +If the radii and angles are instead defined as constants, you can generate an arc without any arguments: + +```js +const arc = d3.arc() + .innerRadius(0) + .outerRadius(100) + .startAngle(0) + .endAngle(Math.PI / 2); + +arc(); // "M0,-100A100,100,0,0,1,100,0L0,0Z" +``` + +If the arc generator has a [context](#arc_context), then the arc is rendered to this context as a sequence of [path method](http://www.w3.org/TR/2dcontext/#canvaspathmethods) calls and this function returns void. Otherwise, a [path data](http://www.w3.org/TR/SVG/paths.html#PathData) string is returned. + +# arc.centroid(arguments…) · [Source](https://github.com/d3/d3-shape/blob/main/src/arc.js) + +Computes the midpoint [*x*, *y*] of the center line of the arc that would be [generated](#_arc) by the given *arguments*. The *arguments* are arbitrary; they are simply propagated to the arc generator’s accessor functions along with the `this` object. To be consistent with the generated arc, the accessors must be deterministic, *i.e.*, return the same value given the same arguments. The midpoint is defined as ([startAngle](#arc_startAngle) + [endAngle](#arc_endAngle)) / 2 and ([innerRadius](#arc_innerRadius) + [outerRadius](#arc_outerRadius)) / 2. For example: + +[Circular Sector Centroids](https://observablehq.com/@d3/pie-settings)[Annular Sector Centroids](https://observablehq.com/@d3/pie-settings) + +Note that this is **not the geometric center** of the arc, which may be outside the arc; this method is merely a convenience for positioning labels. + +# arc.innerRadius([radius]) · [Source](https://github.com/d3/d3-shape/blob/main/src/arc.js) + +If *radius* is specified, sets the inner radius to the specified function or number and returns this arc generator. If *radius* is not specified, returns the current inner radius accessor, which defaults to: + +```js +function innerRadius(d) { + return d.innerRadius; +} +``` + +Specifying the inner radius as a function is useful for constructing a stacked polar bar chart, often in conjunction with a [sqrt scale](https://github.com/d3/d3-scale#sqrt). More commonly, a constant inner radius is used for a donut or pie chart. If the outer radius is smaller than the inner radius, the inner and outer radii are swapped. A negative value is treated as zero. + +# arc.outerRadius([radius]) · [Source](https://github.com/d3/d3-shape/blob/main/src/arc.js) + +If *radius* is specified, sets the outer radius to the specified function or number and returns this arc generator. If *radius* is not specified, returns the current outer radius accessor, which defaults to: + +```js +function outerRadius(d) { + return d.outerRadius; +} +``` + +Specifying the outer radius as a function is useful for constructing a coxcomb or polar bar chart, often in conjunction with a [sqrt scale](https://github.com/d3/d3-scale#sqrt). More commonly, a constant outer radius is used for a pie or donut chart. If the outer radius is smaller than the inner radius, the inner and outer radii are swapped. A negative value is treated as zero. + +# arc.cornerRadius([radius]) · [Source](https://github.com/d3/d3-shape/blob/main/src/arc.js) + +If *radius* is specified, sets the corner radius to the specified function or number and returns this arc generator. If *radius* is not specified, returns the current corner radius accessor, which defaults to: + +```js +function cornerRadius() { + return 0; +} +``` + +If the corner radius is greater than zero, the corners of the arc are rounded using circles of the given radius. For a circular sector, the two outer corners are rounded; for an annular sector, all four corners are rounded. The corner circles are shown in this diagram: + +[Rounded Circular Sectors](https://observablehq.com/@d3/pie-settings)[Rounded Annular Sectors](https://observablehq.com/@d3/pie-settings) + +The corner radius may not be larger than ([outerRadius](#arc_outerRadius) - [innerRadius](#arc_innerRadius)) / 2. In addition, for arcs whose angular span is less than π, the corner radius may be reduced as two adjacent rounded corners intersect. This is occurs more often with the inner corners. See the [arc corners animation](https://observablehq.com/@d3/arc-corners) for illustration. + +# arc.startAngle([angle]) · [Source](https://github.com/d3/d3-shape/blob/main/src/arc.js) + +If *angle* is specified, sets the start angle to the specified function or number and returns this arc generator. If *angle* is not specified, returns the current start angle accessor, which defaults to: + +```js +function startAngle(d) { + return d.startAngle; +} +``` + +The *angle* is specified in radians, with 0 at -*y* (12 o’clock) and positive angles proceeding clockwise. If |endAngle - startAngle| ≥ τ, a complete circle or annulus is generated rather than a sector. + +# arc.endAngle([angle]) · [Source](https://github.com/d3/d3-shape/blob/main/src/arc.js) + +If *angle* is specified, sets the end angle to the specified function or number and returns this arc generator. If *angle* is not specified, returns the current end angle accessor, which defaults to: + +```js +function endAngle(d) { + return d.endAngle; +} +``` + +The *angle* is specified in radians, with 0 at -*y* (12 o’clock) and positive angles proceeding clockwise. If |endAngle - startAngle| ≥ τ, a complete circle or annulus is generated rather than a sector. + +# arc.padAngle([angle]) · [Source](https://github.com/d3/d3-shape/blob/main/src/arc.js) + +If *angle* is specified, sets the pad angle to the specified function or number and returns this arc generator. If *angle* is not specified, returns the current pad angle accessor, which defaults to: + +```js +function padAngle() { + return d && d.padAngle; +} +``` + +The pad angle is converted to a fixed linear distance separating adjacent arcs, defined as [padRadius](#arc_padRadius) * padAngle. This distance is subtracted equally from the [start](#arc_startAngle) and [end](#arc_endAngle) of the arc. If the arc forms a complete circle or annulus, as when |endAngle - startAngle| ≥ τ, the pad angle is ignored. + +If the [inner radius](#arc_innerRadius) or angular span is small relative to the pad angle, it may not be possible to maintain parallel edges between adjacent arcs. In this case, the inner edge of the arc may collapse to a point, similar to a circular sector. For this reason, padding is typically only applied to annular sectors (*i.e.*, when innerRadius is positive), as shown in this diagram: + +[Padded Circular Sectors](https://observablehq.com/@d3/pie-settings)[Padded Annular Sectors](https://observablehq.com/@d3/pie-settings) + +The recommended minimum inner radius when using padding is outerRadius \* padAngle / sin(θ), where θ is the angular span of the smallest arc before padding. For example, if the outer radius is 200 pixels and the pad angle is 0.02 radians, a reasonable θ is 0.04 radians, and a reasonable inner radius is 100 pixels. See the [arc padding animation](https://observablehq.com/@d3/arc-pad-angle) for illustration. + +Often, the pad angle is not set directly on the arc generator, but is instead computed by the [pie generator](#pies) so as to ensure that the area of padded arcs is proportional to their value; see [*pie*.padAngle](#pie_padAngle). See the [pie padding animation](https://observablehq.com/@d3/arc-pad-angle) for illustration. If you apply a constant pad angle to the arc generator directly, it tends to subtract disproportionately from smaller arcs, introducing distortion. + +# arc.padRadius([radius]) · [Source](https://github.com/d3/d3-shape/blob/main/src/arc.js) + +If *radius* is specified, sets the pad radius to the specified function or number and returns this arc generator. If *radius* is not specified, returns the current pad radius accessor, which defaults to null, indicating that the pad radius should be automatically computed as sqrt([innerRadius](#arc_innerRadius) * innerRadius + [outerRadius](#arc_outerRadius) * outerRadius). The pad radius determines the fixed linear distance separating adjacent arcs, defined as padRadius * [padAngle](#arc_padAngle). + +# arc.context([context]) · [Source](https://github.com/d3/d3-shape/blob/main/src/arc.js) + +If *context* is specified, sets the context and returns this arc generator. If *context* is not specified, returns the current context, which defaults to null. If the context is not null, then the [generated arc](#_arc) is rendered to this context as a sequence of [path method](http://www.w3.org/TR/2dcontext/#canvaspathmethods) calls. Otherwise, a [path data](http://www.w3.org/TR/SVG/paths.html#PathData) string representing the generated arc is returned. + +# arc.digits([digits]) · [Source](https://github.com/d3/d3-shape/blob/main/src/arc.js) + +If *digits* is specified, sets the maximum number of digits after the decimal separator and returns this arc generator. If *digits* is not specified, returns the current maximum fraction digits, which defaults to 3. This option only applies when the associated [*context*](#arc_context) is null, as when this arc generator is used to produce [path data](http://www.w3.org/TR/SVG/paths.html#PathData). + +### Pies + +The pie generator does not produce a shape directly, but instead computes the necessary angles to represent a tabular dataset as a pie or donut chart; these angles can then be passed to an [arc generator](#arcs). + +# d3.pie() · [Source](https://github.com/d3/d3-shape/blob/main/src/pie.js) + +Constructs a new pie generator with the default settings. + +# pie(data[, arguments…]) · [Source](https://github.com/d3/d3-shape/blob/main/src/pie.js) + +Generates a pie for the given array of *data*, returning an array of objects representing each datum’s arc angles. Any additional *arguments* are arbitrary; they are simply propagated to the pie generator’s accessor functions along with the `this` object. The length of the returned array is the same as *data*, and each element *i* in the returned array corresponds to the element *i* in the input data. Each object in the returned array has the following properties: + +* `data` - the input datum; the corresponding element in the input data array. +* `value` - the numeric [value](#pie_value) of the arc. +* `index` - the zero-based [sorted index](#pie_sort) of the arc. +* `startAngle` - the [start angle](#pie_startAngle) of the arc. +* `endAngle` - the [end angle](#pie_endAngle) of the arc. +* `padAngle` - the [pad angle](#pie_padAngle) of the arc. + +This representation is designed to work with the arc generator’s default [startAngle](#arc_startAngle), [endAngle](#arc_endAngle) and [padAngle](#arc_padAngle) accessors. The angular units are arbitrary, but if you plan to use the pie generator in conjunction with an [arc generator](#arcs), you should specify angles in radians, with 0 at -*y* (12 o’clock) and positive angles proceeding clockwise. + +Given a small dataset of numbers, here is how to compute the arc angles to render this data as a pie chart: + +```js +const data = [1, 1, 2, 3, 5, 8, 13, 21]; +const arcs = d3.pie()(data); +``` + +The first pair of parens, `pie()`, [constructs](#pie) a default pie generator. The second, `pie()(data)`, [invokes](#_pie) this generator on the dataset, returning an array of objects: + +```json +[ + {"data": 1, "value": 1, "index": 6, "startAngle": 6.050474740247008, "endAngle": 6.166830023713296, "padAngle": 0}, + {"data": 1, "value": 1, "index": 7, "startAngle": 6.166830023713296, "endAngle": 6.283185307179584, "padAngle": 0}, + {"data": 2, "value": 2, "index": 5, "startAngle": 5.817764173314431, "endAngle": 6.050474740247008, "padAngle": 0}, + {"data": 3, "value": 3, "index": 4, "startAngle": 5.468698322915565, "endAngle": 5.817764173314431, "padAngle": 0}, + {"data": 5, "value": 5, "index": 3, "startAngle": 4.886921905584122, "endAngle": 5.468698322915565, "padAngle": 0}, + {"data": 8, "value": 8, "index": 2, "startAngle": 3.956079637853813, "endAngle": 4.886921905584122, "padAngle": 0}, + {"data": 13, "value": 13, "index": 1, "startAngle": 2.443460952792061, "endAngle": 3.956079637853813, "padAngle": 0}, + {"data": 21, "value": 21, "index": 0, "startAngle": 0.000000000000000, "endAngle": 2.443460952792061, "padAngle": 0} +] +``` + +Note that the returned array is in the same order as the data, even though this pie chart is [sorted](#pie_sortValues) by descending value, starting with the arc for the last datum (value 21) at 12 o’clock. + +# pie.value([value]) · [Source](https://github.com/d3/d3-shape/blob/main/src/pie.js) + +If *value* is specified, sets the value accessor to the specified function or number and returns this pie generator. If *value* is not specified, returns the current value accessor, which defaults to: + +```js +function value(d) { + return d; +} +``` + +When a pie is [generated](#_pie), the value accessor will be invoked for each element in the input data array, being passed the element `d`, the index `i`, and the array `data` as three arguments. The default value accessor assumes that the input data are numbers, or that they are coercible to numbers using [valueOf](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/valueOf). If your data are not simply numbers, then you should specify an accessor that returns the corresponding numeric value for a given datum. For example: + +```js +const data = [ + {"number": 4, "name": "Locke"}, + {"number": 8, "name": "Reyes"}, + {"number": 15, "name": "Ford"}, + {"number": 16, "name": "Jarrah"}, + {"number": 23, "name": "Shephard"}, + {"number": 42, "name": "Kwon"} +]; + +const arcs = d3.pie() + .value(d => d.number) + (data); +``` + +This is similar to [mapping](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/map) your data to values before invoking the pie generator: + +```js +const arcs = d3.pie()(data.map(d => d.number)); +``` + +The benefit of an accessor is that the input data remains associated with the returned objects, thereby making it easier to access other fields of the data, for example to set the color or to add text labels. + +# pie.sort([compare]) · [Source](https://github.com/d3/d3-shape/blob/main/src/pie.js) + +If *compare* is specified, sets the data comparator to the specified function and returns this pie generator. If *compare* is not specified, returns the current data comparator, which defaults to null. If both the data comparator and the value comparator are null, then arcs are positioned in the original input order. Otherwise, the data is sorted according to the data comparator, and the resulting order is used. Setting the data comparator implicitly sets the [value comparator](#pie_sortValues) to null. + +The *compare* function takes two arguments *a* and *b*, each elements from the input data array. If the arc for *a* should be before the arc for *b*, then the comparator must return a number less than zero; if the arc for *a* should be after the arc for *b*, then the comparator must return a number greater than zero; returning zero means that the relative order of *a* and *b* is unspecified. For example, to sort arcs by their associated name: + +```js +pie.sort((a, b) => a.name.localeCompare(b.name)); +``` + +Sorting does not affect the order of the [generated arc array](#_pie) which is always in the same order as the input data array; it merely affects the computed angles of each arc. The first arc starts at the [start angle](#pie_startAngle) and the last arc ends at the [end angle](#pie_endAngle). + +# pie.sortValues([compare]) · [Source](https://github.com/d3/d3-shape/blob/main/src/pie.js) + +If *compare* is specified, sets the value comparator to the specified function and returns this pie generator. If *compare* is not specified, returns the current value comparator, which defaults to descending value. The default value comparator is implemented as: + +```js +function compare(a, b) { + return b - a; +} +``` + +If both the data comparator and the value comparator are null, then arcs are positioned in the original input order. Otherwise, the data is sorted according to the data comparator, and the resulting order is used. Setting the value comparator implicitly sets the [data comparator](#pie_sort) to null. + +The value comparator is similar to the [data comparator](#pie_sort), except the two arguments *a* and *b* are values derived from the input data array using the [value accessor](#pie_value), not the data elements. If the arc for *a* should be before the arc for *b*, then the comparator must return a number less than zero; if the arc for *a* should be after the arc for *b*, then the comparator must return a number greater than zero; returning zero means that the relative order of *a* and *b* is unspecified. For example, to sort arcs by ascending value: + +```js +pie.sortValues((a, b) => a - b); +``` + +Sorting does not affect the order of the [generated arc array](#_pie) which is always in the same order as the input data array; it merely affects the computed angles of each arc. The first arc starts at the [start angle](#pie_startAngle) and the last arc ends at the [end angle](#pie_endAngle). + +# pie.startAngle([angle]) · [Source](https://github.com/d3/d3-shape/blob/main/src/pie.js) + +If *angle* is specified, sets the overall start angle of the pie to the specified function or number and returns this pie generator. If *angle* is not specified, returns the current start angle accessor, which defaults to: + +```js +function startAngle() { + return 0; +} +``` + +The start angle here means the *overall* start angle of the pie, *i.e.*, the start angle of the first arc. The start angle accessor is invoked once, being passed the same arguments and `this` context as the [pie generator](#_pie). The units of *angle* are arbitrary, but if you plan to use the pie generator in conjunction with an [arc generator](#arcs), you should specify an angle in radians, with 0 at -*y* (12 o’clock) and positive angles proceeding clockwise. + +# pie.endAngle([angle]) · [Source](https://github.com/d3/d3-shape/blob/main/src/pie.js) + +If *angle* is specified, sets the overall end angle of the pie to the specified function or number and returns this pie generator. If *angle* is not specified, returns the current end angle accessor, which defaults to: + +```js +function endAngle() { + return 2 * Math.PI; +} +``` + +The end angle here means the *overall* end angle of the pie, *i.e.*, the end angle of the last arc. The end angle accessor is invoked once, being passed the same arguments and `this` context as the [pie generator](#_pie). The units of *angle* are arbitrary, but if you plan to use the pie generator in conjunction with an [arc generator](#arcs), you should specify an angle in radians, with 0 at -*y* (12 o’clock) and positive angles proceeding clockwise. + +The value of the end angle is constrained to [startAngle](#pie_startAngle) ± τ, such that |endAngle - startAngle| ≤ τ. + +# pie.padAngle([angle]) · [Source](https://github.com/d3/d3-shape/blob/main/src/pie.js) + +If *angle* is specified, sets the pad angle to the specified function or number and returns this pie generator. If *angle* is not specified, returns the current pad angle accessor, which defaults to: + +```js +function padAngle() { + return 0; +} +``` + +The pad angle here means the angular separation between each adjacent arc. The total amount of padding reserved is the specified *angle* times the number of elements in the input data array, and at most |endAngle - startAngle|; the remaining space is then divided proportionally by [value](#pie_value) such that the relative area of each arc is preserved. See the [pie padding animation](https://observablehq.com/@d3/arc-pad-angle) for illustration. The pad angle accessor is invoked once, being passed the same arguments and `this` context as the [pie generator](#_pie). The units of *angle* are arbitrary, but if you plan to use the pie generator in conjunction with an [arc generator](#arcs), you should specify an angle in radians. + +### Lines + +[Line Chart](https://observablehq.com/@d3/line-chart) + +The line generator produces a [spline](https://en.wikipedia.org/wiki/Spline_\(mathematics\)) or [polyline](https://en.wikipedia.org/wiki/Polygonal_chain), as in a line chart. Lines also appear in many other visualization types, such as the links in [hierarchical edge bundling](https://observablehq.com/@d3/hierarchical-edge-bundling). + +# d3.line([x][, y]) · [Source](https://github.com/d3/d3-shape/blob/main/src/line.js), [Examples](https://observablehq.com/@d3/d3-line) + +Constructs a new line generator with the default settings. If *x* or *y* are specified, sets the corresponding accessors to the specified function or number and returns this line generator. + +# line(data) · [Source](https://github.com/d3/d3-shape/blob/main/src/line.js), [Examples](https://observablehq.com/@d3/d3-line) + +Generates a line for the given array of *data*. Depending on this line generator’s associated [curve](#line_curve), the given input *data* may need to be sorted by *x*-value before being passed to the line generator. If the line generator has a [context](#line_context), then the line is rendered to this context as a sequence of [path method](http://www.w3.org/TR/2dcontext/#canvaspathmethods) calls and this function returns void. Otherwise, a [path data](http://www.w3.org/TR/SVG/paths.html#PathData) string is returned. + +# line.x([x]) · [Source](https://github.com/d3/d3-shape/blob/main/src/line.js), [Examples](https://observablehq.com/@d3/d3-line) + +If *x* is specified, sets the x accessor to the specified function or number and returns this line generator. If *x* is not specified, returns the current x accessor, which defaults to: + +```js +function x(d) { + return d[0]; +} +``` + +When a line is [generated](#_line), the x accessor will be invoked for each [defined](#line_defined) element in the input data array, being passed the element `d`, the index `i`, and the array `data` as three arguments. The default x accessor assumes that the input data are two-element arrays of numbers. If your data are in a different format, or if you wish to transform the data before rendering, then you should specify a custom accessor. For example, if `x` is a [time scale](https://github.com/d3/d3-scale#time-scales) and `y` is a [linear scale](https://github.com/d3/d3-scale#linear-scales): + +```js +const data = [ + {date: new Date(2007, 3, 24), value: 93.24}, + {date: new Date(2007, 3, 25), value: 95.35}, + {date: new Date(2007, 3, 26), value: 98.84}, + {date: new Date(2007, 3, 27), value: 99.92}, + {date: new Date(2007, 3, 30), value: 99.80}, + {date: new Date(2007, 4, 1), value: 99.47}, + … +]; + +const line = d3.line() + .x(d => x(d.date)) + .y(d => y(d.value)); +``` + +# line.y([y]) · [Source](https://github.com/d3/d3-shape/blob/main/src/line.js), [Examples](https://observablehq.com/@d3/d3-line) + +If *y* is specified, sets the y accessor to the specified function or number and returns this line generator. If *y* is not specified, returns the current y accessor, which defaults to: + +```js +function y(d) { + return d[1]; +} +``` + +When a line is [generated](#_line), the y accessor will be invoked for each [defined](#line_defined) element in the input data array, being passed the element `d`, the index `i`, and the array `data` as three arguments. The default y accessor assumes that the input data are two-element arrays of numbers. See [*line*.x](#line_x) for more information. + +# line.defined([defined]) · [Source](https://github.com/d3/d3-shape/blob/main/src/line.js), [Examples](https://observablehq.com/@d3/d3-line) + +If *defined* is specified, sets the defined accessor to the specified function or boolean and returns this line generator. If *defined* is not specified, returns the current defined accessor, which defaults to: + +```js +function defined() { + return true; +} +``` + +The default accessor thus assumes that the input data is always defined. When a line is [generated](#_line), the defined accessor will be invoked for each element in the input data array, being passed the element `d`, the index `i`, and the array `data` as three arguments. If the given element is defined (*i.e.*, if the defined accessor returns a truthy value for this element), the [x](#line_x) and [y](#line_y) accessors will subsequently be evaluated and the point will be added to the current line segment. Otherwise, the element will be skipped, the current line segment will be ended, and a new line segment will be generated for the next defined point. As a result, the generated line may have several discrete segments. For example: + +[Line with Missing Data](https://observablehq.com/@d3/line-with-missing-data) + +Note that if a line segment consists of only a single point, it may appear invisible unless rendered with rounded or square [line caps](https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/stroke-linecap). In addition, some curves such as [curveCardinalOpen](#curveCardinalOpen) only render a visible segment if it contains multiple points. + +# line.curve([curve]) · [Source](https://github.com/d3/d3-shape/blob/main/src/line.js), [Examples](https://observablehq.com/@d3/d3-line) + +If *curve* is specified, sets the [curve factory](#curves) and returns this line generator. If *curve* is not specified, returns the current curve factory, which defaults to [curveLinear](#curveLinear). + +# line.context([context]) · [Source](https://github.com/d3/d3-shape/blob/main/src/line.js), [Examples](https://observablehq.com/@d3/d3-line) + +If *context* is specified, sets the context and returns this line generator. If *context* is not specified, returns the current context, which defaults to null. If the context is not null, then the [generated line](#_line) is rendered to this context as a sequence of [path method](http://www.w3.org/TR/2dcontext/#canvaspathmethods) calls. Otherwise, a [path data](http://www.w3.org/TR/SVG/paths.html#PathData) string representing the generated line is returned. + +# line.digits([digits]) · [Source](https://github.com/d3/d3-shape/blob/main/src/line.js) + +If *digits* is specified, sets the maximum number of digits after the decimal separator and returns this line generator. If *digits* is not specified, returns the current maximum fraction digits, which defaults to 3. This option only applies when the associated [*context*](#line_context) is null, as when this line generator is used to produce [path data](http://www.w3.org/TR/SVG/paths.html#PathData). + +# d3.lineRadial() · [Source](https://github.com/d3/d3-shape/blob/main/src/lineRadial.js), [Examples](https://observablehq.com/@d3/d3-lineradial) + +Radial Line + +Constructs a new radial line generator with the default settings. A radial line generator is equivalent to the standard Cartesian [line generator](#line), except the [x](#line_x) and [y](#line_y) accessors are replaced with [angle](#lineRadial_angle) and [radius](#lineRadial_radius) accessors. Radial lines are always positioned relative to ⟨0,0⟩; use a transform (see: [SVG](http://www.w3.org/TR/SVG/coords.html#TransformAttribute), [Canvas](http://www.w3.org/TR/2dcontext/#transformations)) to change the origin. + +# lineRadial(data) · [Source](https://github.com/d3/d3-shape/blob/main/src/lineRadial.js#L4), [Examples](https://observablehq.com/@d3/d3-lineradial) + +Equivalent to [*line*](#_line). + +# lineRadial.angle([angle]) · [Source](https://github.com/d3/d3-shape/blob/main/src/lineRadial.js#L7), [Examples](https://observablehq.com/@d3/d3-lineradial) + +Equivalent to [*line*.x](#line_x), except the accessor returns the angle in radians, with 0 at -*y* (12 o’clock). + +# lineRadial.radius([radius]) · [Source](https://github.com/d3/d3-shape/blob/main/src/lineRadial.js#L8), [Examples](https://observablehq.com/@d3/d3-lineradial) + +Equivalent to [*line*.y](#line_y), except the accessor returns the radius: the distance from the origin ⟨0,0⟩. + +# lineRadial.defined([defined]) + +Equivalent to [*line*.defined](#line_defined). + +# lineRadial.curve([curve]) · [Source](https://github.com/d3/d3-shape/blob/main/src/lineRadial.js), [Examples](https://observablehq.com/@d3/d3-lineradial) + +Equivalent to [*line*.curve](#line_curve). Note that [curveMonotoneX](#curveMonotoneX) or [curveMonotoneY](#curveMonotoneY) are not recommended for radial lines because they assume that the data is monotonic in *x* or *y*, which is typically untrue of radial lines. + +# lineRadial.context([context]) + +Equivalent to [*line*.context](#line_context). + +### Areas + +[Area Chart](https://observablehq.com/@d3/area-chart)[Stacked Area Chart](https://observablehq.com/@d3/stacked-area-chart)[Difference Chart](https://observablehq.com/@d3/difference-chart) + +The area generator produces an area, as in an area chart. An area is defined by two bounding [lines](#lines), either splines or polylines. Typically, the two lines share the same [*x*-values](#area_x) ([x0](#area_x0) = [x1](#area_x1)), differing only in *y*-value ([y0](#area_y0) and [y1](#area_y1)); most commonly, y0 is defined as a constant representing [zero](http://www.vox.com/2015/11/19/9758062/y-axis-zero-chart). The first line (the topline) is defined by x1 and y1 and is rendered first; the second line (the baseline) is defined by x0 and y0 and is rendered second, with the points in reverse order. With a [curveLinear](#curveLinear) [curve](#area_curve), this produces a clockwise polygon. + +# d3.area([x][, y0][, y1]) · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +Constructs a new area generator with the default settings. If *x*, *y0* or *y1* are specified, sets the corresponding accessors to the specified function or number and returns this area generator. + +# area(data) · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +Generates an area for the given array of *data*. Depending on this area generator’s associated [curve](#area_curve), the given input *data* may need to be sorted by *x*-value before being passed to the area generator. If the area generator has a [context](#line_context), then the area is rendered to this context as a sequence of [path method](http://www.w3.org/TR/2dcontext/#canvaspathmethods) calls and this function returns void. Otherwise, a [path data](http://www.w3.org/TR/SVG/paths.html#PathData) string is returned. + +# area.x([x]) · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +If *x* is specified, sets [x0](#area_x0) to *x* and [x1](#area_x1) to null and returns this area generator. If *x* is not specified, returns the current x0 accessor. + +# area.x0([x]) · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +If *x* is specified, sets the x0 accessor to the specified function or number and returns this area generator. If *x* is not specified, returns the current x0 accessor, which defaults to: + +```js +function x(d) { + return d[0]; +} +``` + +When an area is [generated](#_area), the x0 accessor will be invoked for each [defined](#area_defined) element in the input data array, being passed the element `d`, the index `i`, and the array `data` as three arguments. The default x0 accessor assumes that the input data are two-element arrays of numbers. If your data are in a different format, or if you wish to transform the data before rendering, then you should specify a custom accessor. For example, if `x` is a [time scale](https://github.com/d3/d3-scale#time-scales) and `y` is a [linear scale](https://github.com/d3/d3-scale#linear-scales): + +```js +const data = [ + {date: new Date(2007, 3, 24), value: 93.24}, + {date: new Date(2007, 3, 25), value: 95.35}, + {date: new Date(2007, 3, 26), value: 98.84}, + {date: new Date(2007, 3, 27), value: 99.92}, + {date: new Date(2007, 3, 30), value: 99.80}, + {date: new Date(2007, 4, 1), value: 99.47}, + … +]; + +const area = d3.area() + .x(d => x(d.date)) + .y1(d => y(d.value)) + .y0(y(0)); +``` + +# area.x1([x]) · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +If *x* is specified, sets the x1 accessor to the specified function or number and returns this area generator. If *x* is not specified, returns the current x1 accessor, which defaults to null, indicating that the previously-computed [x0](#area_x0) value should be reused for the x1 value. + +When an area is [generated](#_area), the x1 accessor will be invoked for each [defined](#area_defined) element in the input data array, being passed the element `d`, the index `i`, and the array `data` as three arguments. See [*area*.x0](#area_x0) for more information. + +# area.y([y]) · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +If *y* is specified, sets [y0](#area_y0) to *y* and [y1](#area_y1) to null and returns this area generator. If *y* is not specified, returns the current y0 accessor. + +# area.y0([y]) · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +If *y* is specified, sets the y0 accessor to the specified function or number and returns this area generator. If *y* is not specified, returns the current y0 accessor, which defaults to: + +```js +function y() { + return 0; +} +``` + +When an area is [generated](#_area), the y0 accessor will be invoked for each [defined](#area_defined) element in the input data array, being passed the element `d`, the index `i`, and the array `data` as three arguments. See [*area*.x0](#area_x0) for more information. + +# area.y1([y]) · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +If *y* is specified, sets the y1 accessor to the specified function or number and returns this area generator. If *y* is not specified, returns the current y1 accessor, which defaults to: + +```js +function y(d) { + return d[1]; +} +``` + +A null accessor is also allowed, indicating that the previously-computed [y0](#area_y0) value should be reused for the y1 value. When an area is [generated](#_area), the y1 accessor will be invoked for each [defined](#area_defined) element in the input data array, being passed the element `d`, the index `i`, and the array `data` as three arguments. See [*area*.x0](#area_x0) for more information. + +# area.defined([defined]) · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +If *defined* is specified, sets the defined accessor to the specified function or boolean and returns this area generator. If *defined* is not specified, returns the current defined accessor, which defaults to: + +```js +function defined() { + return true; +} +``` + +The default accessor thus assumes that the input data is always defined. When an area is [generated](#_area), the defined accessor will be invoked for each element in the input data array, being passed the element `d`, the index `i`, and the array `data` as three arguments. If the given element is defined (*i.e.*, if the defined accessor returns a truthy value for this element), the [x0](#area_x0), [x1](#area_x1), [y0](#area_y0) and [y1](#area_y1) accessors will subsequently be evaluated and the point will be added to the current area segment. Otherwise, the element will be skipped, the current area segment will be ended, and a new area segment will be generated for the next defined point. As a result, the generated area may have several discrete segments. For example: + +[Area with Missing Data](https://observablehq.com/@d3/area-with-missing-data) + +Note that if an area segment consists of only a single point, it may appear invisible unless rendered with rounded or square [line caps](https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/stroke-linecap). In addition, some curves such as [curveCardinalOpen](#curveCardinalOpen) only render a visible segment if it contains multiple points. + +# area.curve([curve]) · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +If *curve* is specified, sets the [curve factory](#curves) and returns this area generator. If *curve* is not specified, returns the current curve factory, which defaults to [curveLinear](#curveLinear). + +# area.context([context]) · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +If *context* is specified, sets the context and returns this area generator. If *context* is not specified, returns the current context, which defaults to null. If the context is not null, then the [generated area](#_area) is rendered to this context as a sequence of [path method](http://www.w3.org/TR/2dcontext/#canvaspathmethods) calls. Otherwise, a [path data](http://www.w3.org/TR/SVG/paths.html#PathData) string representing the generated area is returned. + +# area.digits([digits]) · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +If *digits* is specified, sets the maximum number of digits after the decimal separator and returns this area generator. If *digits* is not specified, returns the current maximum fraction digits, which defaults to 3. This option only applies when the associated [*context*](#area_context) is null, as when this area generator is used to produce [path data](http://www.w3.org/TR/SVG/paths.html#PathData). + +# area.lineX0() · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) +
    # area.lineY0() · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +Returns a new [line generator](#lines) that has this area generator’s current [defined accessor](#area_defined), [curve](#area_curve) and [context](#area_context). The line’s [*x*-accessor](#line_x) is this area’s [*x0*-accessor](#area_x0), and the line’s [*y*-accessor](#line_y) is this area’s [*y0*-accessor](#area_y0). + +# area.lineX1() · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +Returns a new [line generator](#lines) that has this area generator’s current [defined accessor](#area_defined), [curve](#area_curve) and [context](#area_context). The line’s [*x*-accessor](#line_x) is this area’s [*x1*-accessor](#area_x1), and the line’s [*y*-accessor](#line_y) is this area’s [*y0*-accessor](#area_y0). + +# area.lineY1() · [Source](https://github.com/d3/d3-shape/blob/main/src/area.js) + +Returns a new [line generator](#lines) that has this area generator’s current [defined accessor](#area_defined), [curve](#area_curve) and [context](#area_context). The line’s [*x*-accessor](#line_x) is this area’s [*x0*-accessor](#area_x0), and the line’s [*y*-accessor](#line_y) is this area’s [*y1*-accessor](#area_y1). + +# d3.areaRadial() · [Source](https://github.com/d3/d3-shape/blob/main/src/areaRadial.js) + +Radial Area + +Constructs a new radial area generator with the default settings. A radial area generator is equivalent to the standard Cartesian [area generator](#area), except the [x](#area_x) and [y](#area_y) accessors are replaced with [angle](#areaRadial_angle) and [radius](#areaRadial_radius) accessors. Radial areas are always positioned relative to ⟨0,0⟩; use a transform (see: [SVG](http://www.w3.org/TR/SVG/coords.html#TransformAttribute), [Canvas](http://www.w3.org/TR/2dcontext/#transformations)) to change the origin. + +# areaRadial(data) + +Equivalent to [*area*](#_area). + +# areaRadial.angle([angle]) · [Source](https://github.com/d3/d3-shape/blob/main/src/areaRadial.js) + +Equivalent to [*area*.x](#area_x), except the accessor returns the angle in radians, with 0 at -*y* (12 o’clock). + +# areaRadial.startAngle([angle]) · [Source](https://github.com/d3/d3-shape/blob/main/src/areaRadial.js) + +Equivalent to [*area*.x0](#area_x0), except the accessor returns the angle in radians, with 0 at -*y* (12 o’clock). Note: typically [angle](#areaRadial_angle) is used instead of setting separate start and end angles. + +# areaRadial.endAngle([angle]) · [Source](https://github.com/d3/d3-shape/blob/main/src/areaRadial.js) + +Equivalent to [*area*.x1](#area_x1), except the accessor returns the angle in radians, with 0 at -*y* (12 o’clock). Note: typically [angle](#areaRadial_angle) is used instead of setting separate start and end angles. + +# areaRadial.radius([radius]) · [Source](https://github.com/d3/d3-shape/blob/main/src/areaRadial.js) + +Equivalent to [*area*.y](#area_y), except the accessor returns the radius: the distance from the origin ⟨0,0⟩. + +# areaRadial.innerRadius([radius]) · [Source](https://github.com/d3/d3-shape/blob/main/src/areaRadial.js) + +Equivalent to [*area*.y0](#area_y0), except the accessor returns the radius: the distance from the origin ⟨0,0⟩. + +# areaRadial.outerRadius([radius]) · [Source](https://github.com/d3/d3-shape/blob/main/src/areaRadial.js) + +Equivalent to [*area*.y1](#area_y1), except the accessor returns the radius: the distance from the origin ⟨0,0⟩. + +# areaRadial.defined([defined]) + +Equivalent to [*area*.defined](#area_defined). + +# areaRadial.curve([curve]) · [Source](https://github.com/d3/d3-shape/blob/main/src/areaRadial.js) + +Equivalent to [*area*.curve](#area_curve). Note that [curveMonotoneX](#curveMonotoneX) or [curveMonotoneY](#curveMonotoneY) are not recommended for radial areas because they assume that the data is monotonic in *x* or *y*, which is typically untrue of radial areas. + +# areaRadial.context([context]) + +Equivalent to [*line*.context](#line_context). + +# areaRadial.lineStartAngle() · [Source](https://github.com/d3/d3-shape/blob/main/src/areaRadial.js) +
    # areaRadial.lineInnerRadius() · [Source](https://github.com/d3/d3-shape/blob/main/src/areaRadial.js) + +Returns a new [radial line generator](#lineRadial) that has this radial area generator’s current [defined accessor](#areaRadial_defined), [curve](#areaRadial_curve) and [context](#areaRadial_context). The line’s [angle accessor](#lineRadial_angle) is this area’s [start angle accessor](#areaRadial_startAngle), and the line’s [radius accessor](#lineRadial_radius) is this area’s [inner radius accessor](#areaRadial_innerRadius). + +# areaRadial.lineEndAngle() · [Source](https://github.com/d3/d3-shape/blob/main/src/areaRadial.js) + +Returns a new [radial line generator](#lineRadial) that has this radial area generator’s current [defined accessor](#areaRadial_defined), [curve](#areaRadial_curve) and [context](#areaRadial_context). The line’s [angle accessor](#lineRadial_angle) is this area’s [end angle accessor](#areaRadial_endAngle), and the line’s [radius accessor](#lineRadial_radius) is this area’s [inner radius accessor](#areaRadial_innerRadius). + +# areaRadial.lineOuterRadius() · [Source](https://github.com/d3/d3-shape/blob/main/src/areaRadial.js) + +Returns a new [radial line generator](#lineRadial) that has this radial area generator’s current [defined accessor](#areaRadial_defined), [curve](#areaRadial_curve) and [context](#areaRadial_context). The line’s [angle accessor](#lineRadial_angle) is this area’s [start angle accessor](#areaRadial_startAngle), and the line’s [radius accessor](#lineRadial_radius) is this area’s [outer radius accessor](#areaRadial_outerRadius). + +### Curves + +While [lines](#lines) are defined as a sequence of two-dimensional [*x*, *y*] points, and [areas](#areas) are similarly defined by a topline and a baseline, there remains the task of transforming this discrete representation into a continuous shape: *i.e.*, how to interpolate between the points. A variety of curves are provided for this purpose. + +Curves are typically not constructed or used directly, instead being passed to [*line*.curve](#line_curve) and [*area*.curve](#area_curve). For example: + +```js +const line = d3.line(d => d.date, d => d.value) + .curve(d3.curveCatmullRom.alpha(0.5)); +``` + +# d3.curveBasis(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/basis.js) + +basis + +Produces a cubic [basis spline](https://en.wikipedia.org/wiki/B-spline) using the specified control points. The first and last points are triplicated such that the spline starts at the first point and ends at the last point, and is tangent to the line between the first and second points, and to the line between the penultimate and last points. + +# d3.curveBasisClosed(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/basisClosed.js) + +basisClosed + +Produces a closed cubic [basis spline](https://en.wikipedia.org/wiki/B-spline) using the specified control points. When a line segment ends, the first three control points are repeated, producing a closed loop with C2 continuity. + +# d3.curveBasisOpen(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/basisOpen.js) + +basisOpen + +Produces a cubic [basis spline](https://en.wikipedia.org/wiki/B-spline) using the specified control points. Unlike [basis](#basis), the first and last points are not repeated, and thus the curve typically does not intersect these points. + +# d3.curveBumpX(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/bump.js) + +bumpX + +Produces a Bézier curve between each pair of points, with horizontal tangents at each point. + +# d3.curveBumpY(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/bump.js) + +bumpY + +Produces a Bézier curve between each pair of points, with vertical tangents at each point. + +# d3.curveBundle(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/bundle.js) + +bundle + +Produces a straightened cubic [basis spline](https://en.wikipedia.org/wiki/B-spline) using the specified control points, with the spline straightened according to the curve’s [*beta*](#curveBundle_beta), which defaults to 0.85. This curve is typically used in [hierarchical edge bundling](https://observablehq.com/@d3/hierarchical-edge-bundling) to disambiguate connections, as proposed by [Danny Holten](https://www.win.tue.nl/vis1/home/dholten/) in [Hierarchical Edge Bundles: Visualization of Adjacency Relations in Hierarchical Data](https://www.win.tue.nl/vis1/home/dholten/papers/bundles_infovis.pdf). This curve does not implement [*curve*.areaStart](#curve_areaStart) and [*curve*.areaEnd](#curve_areaEnd); it is intended to work with [d3.line](#lines), not [d3.area](#areas). + +# bundle.beta(beta) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/bundle.js) + +Returns a bundle curve with the specified *beta* in the range [0, 1], representing the bundle strength. If *beta* equals zero, a straight line between the first and last point is produced; if *beta* equals one, a standard [basis](#basis) spline is produced. For example: + +```js +const line = d3.line().curve(d3.curveBundle.beta(0.5)); +``` + +# d3.curveCardinal(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/cardinal.js) + +cardinal + +Produces a cubic [cardinal spline](https://en.wikipedia.org/wiki/Cubic_Hermite_spline#Cardinal_spline) using the specified control points, with one-sided differences used for the first and last piece. The default [tension](#curveCardinal_tension) is 0. + +# d3.curveCardinalClosed(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/cardinalClosed.js) + +cardinalClosed + +Produces a closed cubic [cardinal spline](https://en.wikipedia.org/wiki/Cubic_Hermite_spline#Cardinal_spline) using the specified control points. When a line segment ends, the first three control points are repeated, producing a closed loop. The default [tension](#curveCardinal_tension) is 0. + +# d3.curveCardinalOpen(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/cardinalOpen.js) + +cardinalOpen + +Produces a cubic [cardinal spline](https://en.wikipedia.org/wiki/Cubic_Hermite_spline#Cardinal_spline) using the specified control points. Unlike [curveCardinal](#curveCardinal), one-sided differences are not used for the first and last piece, and thus the curve starts at the second point and ends at the penultimate point. The default [tension](#curveCardinal_tension) is 0. + +# cardinal.tension(tension) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/cardinalOpen.js) + +Returns a cardinal curve with the specified *tension* in the range [0, 1]. The *tension* determines the length of the tangents: a *tension* of one yields all zero tangents, equivalent to [curveLinear](#curveLinear); a *tension* of zero produces a uniform [Catmull–Rom](#curveCatmullRom) spline. For example: + +```js +const line = d3.line().curve(d3.curveCardinal.tension(0.5)); +``` + +# d3.curveCatmullRom(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/catmullRom.js) + +catmullRom + +Produces a cubic Catmull–Rom spline using the specified control points and the parameter [*alpha*](#curveCatmullRom_alpha), which defaults to 0.5, as proposed by Yuksel et al. in [On the Parameterization of Catmull–Rom Curves](http://www.cemyuksel.com/research/catmullrom_param/), with one-sided differences used for the first and last piece. + +# d3.curveCatmullRomClosed(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/catmullRomClosed.js) + +catmullRomClosed + +Produces a closed cubic Catmull–Rom spline using the specified control points and the parameter [*alpha*](#curveCatmullRom_alpha), which defaults to 0.5, as proposed by Yuksel et al. When a line segment ends, the first three control points are repeated, producing a closed loop. + +# d3.curveCatmullRomOpen(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/catmullRomOpen.js) + +catmullRomOpen + +Produces a cubic Catmull–Rom spline using the specified control points and the parameter [*alpha*](#curveCatmullRom_alpha), which defaults to 0.5, as proposed by Yuksel et al. Unlike [curveCatmullRom](#curveCatmullRom), one-sided differences are not used for the first and last piece, and thus the curve starts at the second point and ends at the penultimate point. + +# catmullRom.alpha(alpha) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/catmullRom.js) + +Returns a cubic Catmull–Rom curve with the specified *alpha* in the range [0, 1]. If *alpha* is zero, produces a uniform spline, equivalent to [curveCardinal](#curveCardinal) with a tension of zero; if *alpha* is one, produces a chordal spline; if *alpha* is 0.5, produces a [centripetal spline](https://en.wikipedia.org/wiki/Centripetal_Catmull–Rom_spline). Centripetal splines are recommended to avoid self-intersections and overshoot. For example: + +```js +const line = d3.line().curve(d3.curveCatmullRom.alpha(0.5)); +``` + +# d3.curveLinear(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/linear.js) + +linear + +Produces a polyline through the specified points. + +# d3.curveLinearClosed(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/linearClosed.js) + +linearClosed + +Produces a closed polyline through the specified points by repeating the first point when the line segment ends. + +# d3.curveMonotoneX(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/monotone.js) + +monotoneX + +Produces a cubic spline that [preserves monotonicity](https://en.wikipedia.org/wiki/Monotone_cubic_interpolation) in *y*, assuming monotonicity in *x*, as proposed by Steffen in [A simple method for monotonic interpolation in one dimension](http://adsabs.harvard.edu/full/1990A%26A...239..443S): “a smooth curve with continuous first-order derivatives that passes through any given set of data points without spurious oscillations. Local extrema can occur only at grid points where they are given by the data, but not in between two adjacent grid points.” + +# d3.curveMonotoneY(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/monotone.js) + +monotoneY + +Produces a cubic spline that [preserves monotonicity](https://en.wikipedia.org/wiki/Monotone_cubic_interpolation) in *x*, assuming monotonicity in *y*, as proposed by Steffen in [A simple method for monotonic interpolation in one dimension](http://adsabs.harvard.edu/full/1990A%26A...239..443S): “a smooth curve with continuous first-order derivatives that passes through any given set of data points without spurious oscillations. Local extrema can occur only at grid points where they are given by the data, but not in between two adjacent grid points.” + +# d3.curveNatural(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/natural.js) + +natural + +Produces a [natural](https://en.wikipedia.org/wiki/Spline_interpolation) [cubic spline](http://mathworld.wolfram.com/CubicSpline.html) with the second derivative of the spline set to zero at the endpoints. + +# d3.curveStep(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/step.js) + +step + +Produces a piecewise constant function (a [step function](https://en.wikipedia.org/wiki/Step_function)) consisting of alternating horizontal and vertical lines. The *y*-value changes at the midpoint of each pair of adjacent *x*-values. + +# d3.curveStepAfter(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/step.js) + +stepAfter + +Produces a piecewise constant function (a [step function](https://en.wikipedia.org/wiki/Step_function)) consisting of alternating horizontal and vertical lines. The *y*-value changes after the *x*-value. + +# d3.curveStepBefore(context) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/step.js) + +stepBefore + +Produces a piecewise constant function (a [step function](https://en.wikipedia.org/wiki/Step_function)) consisting of alternating horizontal and vertical lines. The *y*-value changes before the *x*-value. + +### Custom Curves + +Curves are typically not used directly, instead being passed to [*line*.curve](#line_curve) and [*area*.curve](#area_curve). However, you can define your own curve implementation should none of the built-in curves satisfy your needs using the following interface. You can also use this low-level interface with a built-in curve type as an alternative to the line and area generators. + +# curve.areaStart() · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/step.js#L7) + +Indicates the start of a new area segment. Each area segment consists of exactly two [line segments](#curve_lineStart): the topline, followed by the baseline, with the baseline points in reverse order. + +# curve.areaEnd() · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/step.js) + +Indicates the end of the current area segment. + +# curve.lineStart() · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/step.js) + +Indicates the start of a new line segment. Zero or more [points](#curve_point) will follow. + +# curve.lineEnd() · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/step.js) + +Indicates the end of the current line segment. + +# curve.point(x, y) · [Source](https://github.com/d3/d3-shape/blob/main/src/curve/step.js) + +Indicates a new point in the current line segment with the given *x*- and *y*-values. + +### Links + +[Tidy Tree](https://observablehq.com/@d3/tidy-tree) + +The **link** shape generates a smooth cubic Bézier curve from a source point to a target point. The tangents of the curve at the start and end are either [vertical](#linkVertical), [horizontal](#linkHorizontal) or [radial](#linkRadial). + +# d3.link(curve) · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +Returns a new [link generator](#_link) using the specified curve. For example, to visualize [links](https://github.com/d3/d3-hierarchy/blob/master/README.md#node_links) in a [tree diagram](https://github.com/d3/d3-hierarchy/blob/master/README.md#tree) rooted on the top edge of the display, you might say: + +```js +const link = d3.link(d3.curveBumpY) + .x(d => d.x) + .y(d => d.y); +``` + +# d3.linkVertical() · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +Shorthand for [d3.link](#link) with [d3.curveBumpY](#curveBumpY); suitable for visualizing [links](https://github.com/d3/d3-hierarchy/blob/master/README.md#node_links) in a [tree diagram](https://github.com/d3/d3-hierarchy/blob/master/README.md#tree) rooted on the top edge of the display. Equivalent to: + +```js +const link = d3.link(d3.curveBumpY); +``` + +# d3.linkHorizontal() · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +Shorthand for [d3.link](#link) with [d3.curveBumpX](#curveBumpX); suitable for visualizing [links](https://github.com/d3/d3-hierarchy/blob/master/README.md#node_links) in a [tree diagram](https://github.com/d3/d3-hierarchy/blob/master/README.md#tree) rooted on the left edge of the display. Equivalent to: + +```js +const link = d3.link(d3.curveBumpX); +``` + +# link(arguments…) · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +Generates a link for the given *arguments*. The *arguments* are arbitrary; they are simply propagated to the link generator’s accessor functions along with the `this` object. For example, with the default settings, an object expected: + +```js +link({ + source: [100, 100], + target: [300, 300] +}); +``` + +# link.source([source]) · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +If *source* is specified, sets the source accessor to the specified function and returns this link generator. If *source* is not specified, returns the current source accessor, which defaults to: + +```js +function source(d) { + return d.source; +} +``` + +# link.target([target]) · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +If *target* is specified, sets the target accessor to the specified function and returns this link generator. If *target* is not specified, returns the current target accessor, which defaults to: + +```js +function target(d) { + return d.target; +} +``` + +# link.x([x]) · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +If *x* is specified, sets the *x*-accessor to the specified function or number and returns this link generator. If *x* is not specified, returns the current *x*-accessor, which defaults to: + +```js +function x(d) { + return d[0]; +} +``` + +# link.y([y]) · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +If *y* is specified, sets the *y*-accessor to the specified function or number and returns this link generator. If *y* is not specified, returns the current *y*-accessor, which defaults to: + +```js +function y(d) { + return d[1]; +} +``` + +# link.context([context]) · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +If *context* is specified, sets the context and returns this link generator. If *context* is not specified, returns the current context, which defaults to null. If the context is not null, then the [generated link](#_link) is rendered to this context as a sequence of [path method](http://www.w3.org/TR/2dcontext/#canvaspathmethods) calls. Otherwise, a [path data](http://www.w3.org/TR/SVG/paths.html#PathData) string representing the generated link is returned. See also [d3-path](https://github.com/d3/d3-path). + +# link.digits([digits]) · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +If *digits* is specified, sets the maximum number of digits after the decimal separator and returns this link generator. If *digits* is not specified, returns the current maximum fraction digits, which defaults to 3. This option only applies when the associated [*context*](#link_context) is null, as when this link generator is used to produce [path data](http://www.w3.org/TR/SVG/paths.html#PathData). + +# d3.linkRadial() · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +Returns a new [link generator](#_link) with radial tangents. For example, to visualize [links](https://github.com/d3/d3-hierarchy/blob/master/README.md#node_links) in a [tree diagram](https://github.com/d3/d3-hierarchy/blob/master/README.md#tree) rooted in the center of the display, you might say: + +```js +const link = d3.linkRadial() + .angle(d => d.x) + .radius(d => d.y); +``` + +# linkRadial.angle([angle]) · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +Equivalent to [*link*.x](#link_x), except the accessor returns the angle in radians, with 0 at -*y* (12 o’clock). + +# linkRadial.radius([radius]) · [Source](https://github.com/d3/d3-shape/blob/main/src/link.js) + +Equivalent to [*link*.y](#link_y), except the accessor returns the radius: the distance from the origin ⟨0,0⟩. + +### Symbols + +Symbols provide a categorical shape encoding as is commonly used in scatterplots. Symbols are always centered at ⟨0,0⟩; use a transform (see: [SVG](http://www.w3.org/TR/SVG/coords.html#TransformAttribute), [Canvas](http://www.w3.org/TR/2dcontext/#transformations)) to move the symbol to a different position. + +# d3.symbol([type][, size]) · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol.js), [Examples](https://observablehq.com/@d3/fitted-symbols) + +Constructs a new symbol generator of the specified [type](#symbol_type) and [size](#symbol_size). If not specified, *type* defaults to a circle, and *size* defaults to 64. + +# symbol(arguments…) · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol.js) + +Generates a symbol for the given *arguments*. The *arguments* are arbitrary; they are simply propagated to the symbol generator’s accessor functions along with the `this` object. For example, with the default settings, no arguments are needed to produce a circle with area 64 square pixels. If the symbol generator has a [context](#symbol_context), then the symbol is rendered to this context as a sequence of [path method](http://www.w3.org/TR/2dcontext/#canvaspathmethods) calls and this function returns void. Otherwise, a [path data](http://www.w3.org/TR/SVG/paths.html#PathData) string is returned. + +# symbol.type([type]) · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol.js) + +If *type* is specified, sets the symbol type to the specified function or symbol type and returns this symbol generator. If *type* is a function, the symbol generator’s arguments and *this* are passed through. (See [*selection*.attr](https://github.com/d3/d3-selection/blob/master/README.md#selection_attr) if you are using d3-selection.) If *type* is not specified, returns the current symbol type accessor, which defaults to: + +```js +function type() { + return circle; +} +``` + +See [symbolsFill](#symbolsFill) and [symbolsStroke](#symbolsStroke) for built-in symbol types. To implement a custom symbol type, pass an object that implements [*symbolType*.draw](#symbolType_draw). + +# symbol.size([size]) · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol.js) + +If *size* is specified, sets the size to the specified function or number and returns this symbol generator. If *size* is a function, the symbol generator’s arguments and *this* are passed through. (See [*selection*.attr](https://github.com/d3/d3-selection/blob/master/README.md#selection_attr) if you are using d3-selection.) If *size* is not specified, returns the current size accessor, which defaults to: + +```js +function size() { + return 64; +} +``` + +Specifying the size as a function is useful for constructing a scatterplot with a size encoding. If you wish to scale the symbol to fit a given bounding box, rather than by area, try [SVG’s getBBox](https://observablehq.com/d/1fac2626b9e1b65f). + +# symbol.context([context]) · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol.js) + +If *context* is specified, sets the context and returns this symbol generator. If *context* is not specified, returns the current context, which defaults to null. If the context is not null, then the [generated symbol](#_symbol) is rendered to this context as a sequence of [path method](http://www.w3.org/TR/2dcontext/#canvaspathmethods) calls. Otherwise, a [path data](http://www.w3.org/TR/SVG/paths.html#PathData) string representing the generated symbol is returned. + +# symbol.digits([digits]) · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol.js) + +If *digits* is specified, sets the maximum number of digits after the decimal separator and returns this symbol generator. If *digits* is not specified, returns the current maximum fraction digits, which defaults to 3. This option only applies when the associated [*context*](#symbol_context) is null, as when this symbol generator is used to produce [path data](http://www.w3.org/TR/SVG/paths.html#PathData). + +# d3.symbolsFill · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol.js) + + + +An array containing a set of symbol types designed for filling: [circle](#symbolCircle), [cross](#symbolCross), [diamond](#symbolDiamond), [square](#symbolSquare), [star](#symbolStar), [triangle](#symbolTriangle), and [wye](#symbolWye). Useful for constructing the range of an [ordinal scale](https://github.com/d3/d3-scale#ordinal-scales) should you wish to use a shape encoding for categorical data. + +# d3.symbolsStroke · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol.js) + +An array containing a set of symbol types designed for stroking: [circle](#symbolCircle), [plus](#symbolPlus), [times](#symbolTimes), [triangle2](#symbolTriangle2), [asterisk](#symbolAsterisk), [square2](#symbolSquare2), and [diamond2](#symbolDiamond2). Useful for constructing the range of an [ordinal scale](https://github.com/d3/d3-scale#ordinal-scales) should you wish to use a shape encoding for categorical data. + +# d3.symbolAsterisk · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/asterisk.js) + +The asterisk symbol type; intended for stroking. + +# d3.symbolCircle · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/circle.js) + +The circle symbol type; intended for either filling or stroking. + +# d3.symbolCross · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/cross.js) + +The Greek cross symbol type, with arms of equal length; intended for filling. + +# d3.symbolDiamond · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/diamond.js) + +The rhombus symbol type; intended for filling. + +# d3.symbolDiamond2 · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/diamond.js) + +The rotated square symbol type; intended for stroking. + +# d3.symbolPlus · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/plus.js) + +The plus symbol type; intended for stroking. + +# d3.symbolSquare · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/square.js) + +The square symbol type; intended for filling. + +# d3.symbolSquare2 · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/square2.js) + +The square2 symbol type; intended for stroking. + +# d3.symbolStar · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/star.js) + +The pentagonal star (pentagram) symbol type; intended for filling. + +# d3.symbolTriangle · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/triangle.js) + +The up-pointing triangle symbol type; intended for filling. + +# d3.symbolTriangle2 · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/triangle2.js) + +The up-pointing triangle symbol type; intended for stroking. + +# d3.symbolWye · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/wye.js) + +The Y-shape symbol type; intended for filling. + +# d3.symbolTimes · [Source](https://github.com/d3/d3-shape/blob/main/src/symbol/times.js) + +The X-shape symbol type; intended for stroking. + +# d3.pointRadial(angle, radius) · [Source](https://github.com/d3/d3-shape/blob/main/src/pointRadial.js), [Examples](https://observablehq.com/@d3/radial-area-chart) + +Returns the point [x, y] for the given *angle* in radians, with 0 at -*y* (12 o’clock) and positive angles proceeding clockwise, and the given *radius*. + +### Custom Symbol Types + +Symbol types are typically not used directly, instead being passed to [*symbol*.type](#symbol_type). However, you can define your own symbol type implementation should none of the built-in types satisfy your needs using the following interface. You can also use this low-level interface with a built-in symbol type as an alternative to the symbol generator. + +# symbolType.draw(context, size) + +Renders this symbol type to the specified *context* with the specified *size* in square pixels. The *context* implements the [CanvasPathMethods](http://www.w3.org/TR/2dcontext/#canvaspathmethods) interface. (Note that this is a subset of the CanvasRenderingContext2D interface!) + +### Stacks + +[Stacked Bar Chart](https://observablehq.com/@d3/stacked-bar-chart)[Streamgraph](https://observablehq.com/@mbostock/streamgraph-transitions) + +Some shape types can be stacked, placing one shape adjacent to another. For example, a bar chart of monthly sales might be broken down into a multi-series bar chart by product category, stacking bars vertically. This is equivalent to subdividing a bar chart by an ordinal dimension (such as product category) and applying a color encoding. + +Stacked charts can show overall value and per-category value simultaneously; however, it is typically harder to compare across categories, as only the bottom layer of the stack is aligned. So, chose the [stack order](#stack_order) carefully, and consider a [streamgraph](#stackOffsetWiggle). (See also [grouped charts](https://observablehq.com/@d3/grouped-bar-chart).) + +Like the [pie generator](#pies), the stack generator does not produce a shape directly. Instead it computes positions which you can then pass to an [area generator](#areas) or use directly, say to position bars. + +# d3.stack() · [Source](https://github.com/d3/d3-shape/blob/main/src/stack.js) + +Constructs a new stack generator with the default settings. + +# stack(data[, arguments…]) · [Source](https://github.com/d3/d3-shape/blob/main/src/stack.js) + +Generates a stack for the given array of *data*, returning an array representing each series. Any additional *arguments* are arbitrary; they are simply propagated to accessors along with the `this` object. + +The series are determined by the [keys accessor](#stack_keys); each series *i* in the returned array corresponds to the *i*th key. Each series is an array of points, where each point *j* corresponds to the *j*th element in the input *data*. Lastly, each point is represented as an array [*y0*, *y1*] where *y0* is the lower value (baseline) and *y1* is the upper value (topline); the difference between *y0* and *y1* corresponds to the computed [value](#stack_value) for this point. The key for each series is available as *series*.key, and the [index](#stack_order) as *series*.index. The input data element for each point is available as *point*.data. + +For example, consider the following table representing monthly sales of fruits: + +Month | Apples | Bananas | Cherries | Durians +--------|--------|---------|----------|--------- + 1/2015 | 3840 | 1920 | 960 | 400 + 2/2015 | 1600 | 1440 | 960 | 400 + 3/2015 | 640 | 960 | 640 | 400 + 4/2015 | 320 | 480 | 640 | 400 + +This might be represented in JavaScript as an array of objects: + +```js +const data = [ + {month: new Date(2015, 0, 1), apples: 3840, bananas: 1920, cherries: 960, durians: 400}, + {month: new Date(2015, 1, 1), apples: 1600, bananas: 1440, cherries: 960, durians: 400}, + {month: new Date(2015, 2, 1), apples: 640, bananas: 960, cherries: 640, durians: 400}, + {month: new Date(2015, 3, 1), apples: 320, bananas: 480, cherries: 640, durians: 400} +]; +``` + +To produce a stack for this data: + +```js +const stack = d3.stack() + .keys(["apples", "bananas", "cherries", "durians"]) + .order(d3.stackOrderNone) + .offset(d3.stackOffsetNone); + +const series = stack(data); +``` + +The resulting array has one element per *series*. Each series has one point per month, and each point has a lower and upper value defining the baseline and topline: + +```js +[ + [[ 0, 3840], [ 0, 1600], [ 0, 640], [ 0, 320]], // apples + [[3840, 5760], [1600, 3040], [ 640, 1600], [ 320, 800]], // bananas + [[5760, 6720], [3040, 4000], [1600, 2240], [ 800, 1440]], // cherries + [[6720, 7120], [4000, 4400], [2240, 2640], [1440, 1840]], // durians +] +``` + +Each series in then typically passed to an [area generator](#areas) to render an area chart, or used to construct rectangles for a bar chart. + +# stack.keys([keys]) · [Source](https://github.com/d3/d3-shape/blob/main/src/stack.js) + +If *keys* is specified, sets the keys accessor to the specified function or array and returns this stack generator. If *keys* is not specified, returns the current keys accessor, which defaults to the empty array. A series (layer) is [generated](#_stack) for each key. Keys are typically strings, but they may be arbitrary values. The series’ key is passed to the [value accessor](#stack_value), along with each data point, to compute the point’s value. + +# stack.value([value]) · [Source](https://github.com/d3/d3-shape/blob/main/src/stack.js) + +If *value* is specified, sets the value accessor to the specified function or number and returns this stack generator. If *value* is not specified, returns the current value accessor, which defaults to: + +```js +function value(d, key) { + return d[key]; +} +``` + +Thus, by default the stack generator assumes that the input data is an array of objects, with each object exposing named properties with numeric values; see [*stack*](#_stack) for an example. + +# stack.order([order]) · [Source](https://github.com/d3/d3-shape/blob/main/src/stack.js) + +If *order* is specified, sets the order accessor to the specified function or array and returns this stack generator. If *order* is not specified, returns the current order accessor, which defaults to [stackOrderNone](#stackOrderNone); this uses the order given by the [key accessor](#stack_key). See [stack orders](#stack-orders) for the built-in orders. + +If *order* is a function, it is passed the generated series array and must return an array of numeric indexes representing the stack order. For example, the default order is defined as: + +```js +function orderNone(series) { + let n = series.length; + const o = new Array(n); + while (--n >= 0) o[n] = n; + return o; +} +``` + +The stack order is computed prior to the [offset](#stack_offset); thus, the lower value for all points is zero at the time the order is computed. The index attribute for each series is also not set until after the order is computed. + +# stack.offset([offset]) · [Source](https://github.com/d3/d3-shape/blob/main/src/stack.js) + +If *offset* is specified, sets the offset accessor to the specified function and returns this stack generator. If *offset* is not specified, returns the current offset acccesor, which defaults to [stackOffsetNone](#stackOffsetNone); this uses a zero baseline. See [stack offsets](#stack-offsets) for the built-in offsets. + +The offset function is passed the generated series array and the order index array; it is then responsible for updating the lower and upper values in the series array. For example, the default offset is defined as: + +```js +function offsetNone(series, order) { + if (!((n = series.length) > 1)) return; + for (let i = 1, s0, s1 = series[order[0]], n, m = s1.length; i < n; ++i) { + s0 = s1, s1 = series[order[i]]; + for (let j = 0; j < m; ++j) { + s1[j][1] += s1[j][0] = s0[j][1]; + } + } +} +``` + +### Stack Orders + +Stack orders are typically not used directly, but are instead passed to [*stack*.order](#stack_order). + +# d3.stackOrderAppearance(series) · [Source](https://github.com/d3/d3-shape/blob/main/src/order/appearance.js) + +Returns a series order such that the earliest series (according to the maximum value) is at the bottom. + +# d3.stackOrderAscending(series) · [Source](https://github.com/d3/d3-shape/blob/main/src/order/ascending.js) + +Returns a series order such that the smallest series (according to the sum of values) is at the bottom. + +# d3.stackOrderDescending(series) · [Source](https://github.com/d3/d3-shape/blob/main/src/order/descending.js) + +Returns a series order such that the largest series (according to the sum of values) is at the bottom. + +# d3.stackOrderInsideOut(series) · [Source](https://github.com/d3/d3-shape/blob/main/src/order/insideOut.js) + +Returns a series order such that the earliest series (according to the maximum value) are on the inside and the later series are on the outside. This order is recommended for streamgraphs in conjunction with the [wiggle offset](#stackOffsetWiggle). See [Stacked Graphs—Geometry & Aesthetics](http://leebyron.com/streamgraph/) by Byron & Wattenberg for more information. + +# d3.stackOrderNone(series) · [Source](https://github.com/d3/d3-shape/blob/main/src/order/none.js) + +Returns the given series order [0, 1, … *n* - 1] where *n* is the number of elements in *series*. Thus, the stack order is given by the [key accessor](#stack_keys). + +# d3.stackOrderReverse(series) · [Source](https://github.com/d3/d3-shape/blob/main/src/order/reverse.js) + +Returns the reverse of the given series order [*n* - 1, *n* - 2, … 0] where *n* is the number of elements in *series*. Thus, the stack order is given by the reverse of the [key accessor](#stack_keys). + +### Stack Offsets + +Stack offsets are typically not used directly, but are instead passed to [*stack*.offset](#stack_offset). + +# d3.stackOffsetExpand(series, order) · [Source](https://github.com/d3/d3-shape/blob/main/src/offset/expand.js) + +Applies a zero baseline and normalizes the values for each point such that the topline is always one. + +# d3.stackOffsetDiverging(series, order) · [Source](https://github.com/d3/d3-shape/blob/main/src/offset/diverging.js) + +Positive values are stacked above zero, negative values are [stacked below zero](https://observablehq.com/@d3/diverging-stacked-bar-chart), and zero values are stacked at zero. + +# d3.stackOffsetNone(series, order) · [Source](https://github.com/d3/d3-shape/blob/main/src/offset/none.js) + +Applies a zero baseline. + +# d3.stackOffsetSilhouette(series, order) · [Source](https://github.com/d3/d3-shape/blob/main/src/offset/silhouette.js) + +Shifts the baseline down such that the center of the streamgraph is always at zero. + +# d3.stackOffsetWiggle(series, order) · [Source](https://github.com/d3/d3-shape/blob/main/src/offset/wiggle.js) + +Shifts the baseline so as to minimize the weighted wiggle of layers. This offset is recommended for streamgraphs in conjunction with the [inside-out order](#stackOrderInsideOut). See [Stacked Graphs—Geometry & Aesthetics](http://leebyron.com/streamgraph/) by Bryon & Wattenberg for more information. diff --git a/frontend/node_modules/d3-shape/dist/d3-shape.js b/frontend/node_modules/d3-shape/dist/d3-shape.js new file mode 100644 index 0000000..62e76d0 --- /dev/null +++ b/frontend/node_modules/d3-shape/dist/d3-shape.js @@ -0,0 +1,2141 @@ +// https://d3js.org/d3-shape/ v3.2.0 Copyright 2010-2022 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-path')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-path'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3)); +})(this, (function (exports, d3Path) { 'use strict'; + +function constant(x) { + return function constant() { + return x; + }; +} + +const abs = Math.abs; +const atan2 = Math.atan2; +const cos = Math.cos; +const max = Math.max; +const min = Math.min; +const sin = Math.sin; +const sqrt = Math.sqrt; + +const epsilon = 1e-12; +const pi = Math.PI; +const halfPi = pi / 2; +const tau = 2 * pi; + +function acos(x) { + return x > 1 ? 0 : x < -1 ? pi : Math.acos(x); +} + +function asin(x) { + return x >= 1 ? halfPi : x <= -1 ? -halfPi : Math.asin(x); +} + +function withPath(shape) { + let digits = 3; + + shape.digits = function(_) { + if (!arguments.length) return digits; + if (_ == null) { + digits = null; + } else { + const d = Math.floor(_); + if (!(d >= 0)) throw new RangeError(`invalid digits: ${_}`); + digits = d; + } + return shape; + }; + + return () => new d3Path.Path(digits); +} + +function arcInnerRadius(d) { + return d.innerRadius; +} + +function arcOuterRadius(d) { + return d.outerRadius; +} + +function arcStartAngle(d) { + return d.startAngle; +} + +function arcEndAngle(d) { + return d.endAngle; +} + +function arcPadAngle(d) { + return d && d.padAngle; // Note: optional! +} + +function intersect(x0, y0, x1, y1, x2, y2, x3, y3) { + var x10 = x1 - x0, y10 = y1 - y0, + x32 = x3 - x2, y32 = y3 - y2, + t = y32 * x10 - x32 * y10; + if (t * t < epsilon) return; + t = (x32 * (y0 - y2) - y32 * (x0 - x2)) / t; + return [x0 + t * x10, y0 + t * y10]; +} + +// Compute perpendicular offset line of length rc. +// http://mathworld.wolfram.com/Circle-LineIntersection.html +function cornerTangents(x0, y0, x1, y1, r1, rc, cw) { + var x01 = x0 - x1, + y01 = y0 - y1, + lo = (cw ? rc : -rc) / sqrt(x01 * x01 + y01 * y01), + ox = lo * y01, + oy = -lo * x01, + x11 = x0 + ox, + y11 = y0 + oy, + x10 = x1 + ox, + y10 = y1 + oy, + x00 = (x11 + x10) / 2, + y00 = (y11 + y10) / 2, + dx = x10 - x11, + dy = y10 - y11, + d2 = dx * dx + dy * dy, + r = r1 - rc, + D = x11 * y10 - x10 * y11, + d = (dy < 0 ? -1 : 1) * sqrt(max(0, r * r * d2 - D * D)), + cx0 = (D * dy - dx * d) / d2, + cy0 = (-D * dx - dy * d) / d2, + cx1 = (D * dy + dx * d) / d2, + cy1 = (-D * dx + dy * d) / d2, + dx0 = cx0 - x00, + dy0 = cy0 - y00, + dx1 = cx1 - x00, + dy1 = cy1 - y00; + + // Pick the closer of the two intersection points. + // TODO Is there a faster way to determine which intersection to use? + if (dx0 * dx0 + dy0 * dy0 > dx1 * dx1 + dy1 * dy1) cx0 = cx1, cy0 = cy1; + + return { + cx: cx0, + cy: cy0, + x01: -ox, + y01: -oy, + x11: cx0 * (r1 / r - 1), + y11: cy0 * (r1 / r - 1) + }; +} + +function arc() { + var innerRadius = arcInnerRadius, + outerRadius = arcOuterRadius, + cornerRadius = constant(0), + padRadius = null, + startAngle = arcStartAngle, + endAngle = arcEndAngle, + padAngle = arcPadAngle, + context = null, + path = withPath(arc); + + function arc() { + var buffer, + r, + r0 = +innerRadius.apply(this, arguments), + r1 = +outerRadius.apply(this, arguments), + a0 = startAngle.apply(this, arguments) - halfPi, + a1 = endAngle.apply(this, arguments) - halfPi, + da = abs(a1 - a0), + cw = a1 > a0; + + if (!context) context = buffer = path(); + + // Ensure that the outer radius is always larger than the inner radius. + if (r1 < r0) r = r1, r1 = r0, r0 = r; + + // Is it a point? + if (!(r1 > epsilon)) context.moveTo(0, 0); + + // Or is it a circle or annulus? + else if (da > tau - epsilon) { + context.moveTo(r1 * cos(a0), r1 * sin(a0)); + context.arc(0, 0, r1, a0, a1, !cw); + if (r0 > epsilon) { + context.moveTo(r0 * cos(a1), r0 * sin(a1)); + context.arc(0, 0, r0, a1, a0, cw); + } + } + + // Or is it a circular or annular sector? + else { + var a01 = a0, + a11 = a1, + a00 = a0, + a10 = a1, + da0 = da, + da1 = da, + ap = padAngle.apply(this, arguments) / 2, + rp = (ap > epsilon) && (padRadius ? +padRadius.apply(this, arguments) : sqrt(r0 * r0 + r1 * r1)), + rc = min(abs(r1 - r0) / 2, +cornerRadius.apply(this, arguments)), + rc0 = rc, + rc1 = rc, + t0, + t1; + + // Apply padding? Note that since r1 ≥ r0, da1 ≥ da0. + if (rp > epsilon) { + var p0 = asin(rp / r0 * sin(ap)), + p1 = asin(rp / r1 * sin(ap)); + if ((da0 -= p0 * 2) > epsilon) p0 *= (cw ? 1 : -1), a00 += p0, a10 -= p0; + else da0 = 0, a00 = a10 = (a0 + a1) / 2; + if ((da1 -= p1 * 2) > epsilon) p1 *= (cw ? 1 : -1), a01 += p1, a11 -= p1; + else da1 = 0, a01 = a11 = (a0 + a1) / 2; + } + + var x01 = r1 * cos(a01), + y01 = r1 * sin(a01), + x10 = r0 * cos(a10), + y10 = r0 * sin(a10); + + // Apply rounded corners? + if (rc > epsilon) { + var x11 = r1 * cos(a11), + y11 = r1 * sin(a11), + x00 = r0 * cos(a00), + y00 = r0 * sin(a00), + oc; + + // Restrict the corner radius according to the sector angle. If this + // intersection fails, it’s probably because the arc is too small, so + // disable the corner radius entirely. + if (da < pi) { + if (oc = intersect(x01, y01, x00, y00, x11, y11, x10, y10)) { + var ax = x01 - oc[0], + ay = y01 - oc[1], + bx = x11 - oc[0], + by = y11 - oc[1], + kc = 1 / sin(acos((ax * bx + ay * by) / (sqrt(ax * ax + ay * ay) * sqrt(bx * bx + by * by))) / 2), + lc = sqrt(oc[0] * oc[0] + oc[1] * oc[1]); + rc0 = min(rc, (r0 - lc) / (kc - 1)); + rc1 = min(rc, (r1 - lc) / (kc + 1)); + } else { + rc0 = rc1 = 0; + } + } + } + + // Is the sector collapsed to a line? + if (!(da1 > epsilon)) context.moveTo(x01, y01); + + // Does the sector’s outer ring have rounded corners? + else if (rc1 > epsilon) { + t0 = cornerTangents(x00, y00, x01, y01, r1, rc1, cw); + t1 = cornerTangents(x11, y11, x10, y10, r1, rc1, cw); + + context.moveTo(t0.cx + t0.x01, t0.cy + t0.y01); + + // Have the corners merged? + if (rc1 < rc) context.arc(t0.cx, t0.cy, rc1, atan2(t0.y01, t0.x01), atan2(t1.y01, t1.x01), !cw); + + // Otherwise, draw the two corners and the ring. + else { + context.arc(t0.cx, t0.cy, rc1, atan2(t0.y01, t0.x01), atan2(t0.y11, t0.x11), !cw); + context.arc(0, 0, r1, atan2(t0.cy + t0.y11, t0.cx + t0.x11), atan2(t1.cy + t1.y11, t1.cx + t1.x11), !cw); + context.arc(t1.cx, t1.cy, rc1, atan2(t1.y11, t1.x11), atan2(t1.y01, t1.x01), !cw); + } + } + + // Or is the outer ring just a circular arc? + else context.moveTo(x01, y01), context.arc(0, 0, r1, a01, a11, !cw); + + // Is there no inner ring, and it’s a circular sector? + // Or perhaps it’s an annular sector collapsed due to padding? + if (!(r0 > epsilon) || !(da0 > epsilon)) context.lineTo(x10, y10); + + // Does the sector’s inner ring (or point) have rounded corners? + else if (rc0 > epsilon) { + t0 = cornerTangents(x10, y10, x11, y11, r0, -rc0, cw); + t1 = cornerTangents(x01, y01, x00, y00, r0, -rc0, cw); + + context.lineTo(t0.cx + t0.x01, t0.cy + t0.y01); + + // Have the corners merged? + if (rc0 < rc) context.arc(t0.cx, t0.cy, rc0, atan2(t0.y01, t0.x01), atan2(t1.y01, t1.x01), !cw); + + // Otherwise, draw the two corners and the ring. + else { + context.arc(t0.cx, t0.cy, rc0, atan2(t0.y01, t0.x01), atan2(t0.y11, t0.x11), !cw); + context.arc(0, 0, r0, atan2(t0.cy + t0.y11, t0.cx + t0.x11), atan2(t1.cy + t1.y11, t1.cx + t1.x11), cw); + context.arc(t1.cx, t1.cy, rc0, atan2(t1.y11, t1.x11), atan2(t1.y01, t1.x01), !cw); + } + } + + // Or is the inner ring just a circular arc? + else context.arc(0, 0, r0, a10, a00, cw); + } + + context.closePath(); + + if (buffer) return context = null, buffer + "" || null; + } + + arc.centroid = function() { + var r = (+innerRadius.apply(this, arguments) + +outerRadius.apply(this, arguments)) / 2, + a = (+startAngle.apply(this, arguments) + +endAngle.apply(this, arguments)) / 2 - pi / 2; + return [cos(a) * r, sin(a) * r]; + }; + + arc.innerRadius = function(_) { + return arguments.length ? (innerRadius = typeof _ === "function" ? _ : constant(+_), arc) : innerRadius; + }; + + arc.outerRadius = function(_) { + return arguments.length ? (outerRadius = typeof _ === "function" ? _ : constant(+_), arc) : outerRadius; + }; + + arc.cornerRadius = function(_) { + return arguments.length ? (cornerRadius = typeof _ === "function" ? _ : constant(+_), arc) : cornerRadius; + }; + + arc.padRadius = function(_) { + return arguments.length ? (padRadius = _ == null ? null : typeof _ === "function" ? _ : constant(+_), arc) : padRadius; + }; + + arc.startAngle = function(_) { + return arguments.length ? (startAngle = typeof _ === "function" ? _ : constant(+_), arc) : startAngle; + }; + + arc.endAngle = function(_) { + return arguments.length ? (endAngle = typeof _ === "function" ? _ : constant(+_), arc) : endAngle; + }; + + arc.padAngle = function(_) { + return arguments.length ? (padAngle = typeof _ === "function" ? _ : constant(+_), arc) : padAngle; + }; + + arc.context = function(_) { + return arguments.length ? ((context = _ == null ? null : _), arc) : context; + }; + + return arc; +} + +var slice = Array.prototype.slice; + +function array(x) { + return typeof x === "object" && "length" in x + ? x // Array, TypedArray, NodeList, array-like + : Array.from(x); // Map, Set, iterable, string, or anything else +} + +function Linear(context) { + this._context = context; +} + +Linear.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._point = 0; + }, + lineEnd: function() { + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; // falls through + default: this._context.lineTo(x, y); break; + } + } +}; + +function curveLinear(context) { + return new Linear(context); +} + +function x(p) { + return p[0]; +} + +function y(p) { + return p[1]; +} + +function line(x$1, y$1) { + var defined = constant(true), + context = null, + curve = curveLinear, + output = null, + path = withPath(line); + + x$1 = typeof x$1 === "function" ? x$1 : (x$1 === undefined) ? x : constant(x$1); + y$1 = typeof y$1 === "function" ? y$1 : (y$1 === undefined) ? y : constant(y$1); + + function line(data) { + var i, + n = (data = array(data)).length, + d, + defined0 = false, + buffer; + + if (context == null) output = curve(buffer = path()); + + for (i = 0; i <= n; ++i) { + if (!(i < n && defined(d = data[i], i, data)) === defined0) { + if (defined0 = !defined0) output.lineStart(); + else output.lineEnd(); + } + if (defined0) output.point(+x$1(d, i, data), +y$1(d, i, data)); + } + + if (buffer) return output = null, buffer + "" || null; + } + + line.x = function(_) { + return arguments.length ? (x$1 = typeof _ === "function" ? _ : constant(+_), line) : x$1; + }; + + line.y = function(_) { + return arguments.length ? (y$1 = typeof _ === "function" ? _ : constant(+_), line) : y$1; + }; + + line.defined = function(_) { + return arguments.length ? (defined = typeof _ === "function" ? _ : constant(!!_), line) : defined; + }; + + line.curve = function(_) { + return arguments.length ? (curve = _, context != null && (output = curve(context)), line) : curve; + }; + + line.context = function(_) { + return arguments.length ? (_ == null ? context = output = null : output = curve(context = _), line) : context; + }; + + return line; +} + +function area(x0, y0, y1) { + var x1 = null, + defined = constant(true), + context = null, + curve = curveLinear, + output = null, + path = withPath(area); + + x0 = typeof x0 === "function" ? x0 : (x0 === undefined) ? x : constant(+x0); + y0 = typeof y0 === "function" ? y0 : (y0 === undefined) ? constant(0) : constant(+y0); + y1 = typeof y1 === "function" ? y1 : (y1 === undefined) ? y : constant(+y1); + + function area(data) { + var i, + j, + k, + n = (data = array(data)).length, + d, + defined0 = false, + buffer, + x0z = new Array(n), + y0z = new Array(n); + + if (context == null) output = curve(buffer = path()); + + for (i = 0; i <= n; ++i) { + if (!(i < n && defined(d = data[i], i, data)) === defined0) { + if (defined0 = !defined0) { + j = i; + output.areaStart(); + output.lineStart(); + } else { + output.lineEnd(); + output.lineStart(); + for (k = i - 1; k >= j; --k) { + output.point(x0z[k], y0z[k]); + } + output.lineEnd(); + output.areaEnd(); + } + } + if (defined0) { + x0z[i] = +x0(d, i, data), y0z[i] = +y0(d, i, data); + output.point(x1 ? +x1(d, i, data) : x0z[i], y1 ? +y1(d, i, data) : y0z[i]); + } + } + + if (buffer) return output = null, buffer + "" || null; + } + + function arealine() { + return line().defined(defined).curve(curve).context(context); + } + + area.x = function(_) { + return arguments.length ? (x0 = typeof _ === "function" ? _ : constant(+_), x1 = null, area) : x0; + }; + + area.x0 = function(_) { + return arguments.length ? (x0 = typeof _ === "function" ? _ : constant(+_), area) : x0; + }; + + area.x1 = function(_) { + return arguments.length ? (x1 = _ == null ? null : typeof _ === "function" ? _ : constant(+_), area) : x1; + }; + + area.y = function(_) { + return arguments.length ? (y0 = typeof _ === "function" ? _ : constant(+_), y1 = null, area) : y0; + }; + + area.y0 = function(_) { + return arguments.length ? (y0 = typeof _ === "function" ? _ : constant(+_), area) : y0; + }; + + area.y1 = function(_) { + return arguments.length ? (y1 = _ == null ? null : typeof _ === "function" ? _ : constant(+_), area) : y1; + }; + + area.lineX0 = + area.lineY0 = function() { + return arealine().x(x0).y(y0); + }; + + area.lineY1 = function() { + return arealine().x(x0).y(y1); + }; + + area.lineX1 = function() { + return arealine().x(x1).y(y0); + }; + + area.defined = function(_) { + return arguments.length ? (defined = typeof _ === "function" ? _ : constant(!!_), area) : defined; + }; + + area.curve = function(_) { + return arguments.length ? (curve = _, context != null && (output = curve(context)), area) : curve; + }; + + area.context = function(_) { + return arguments.length ? (_ == null ? context = output = null : output = curve(context = _), area) : context; + }; + + return area; +} + +function descending$1(a, b) { + return b < a ? -1 : b > a ? 1 : b >= a ? 0 : NaN; +} + +function identity(d) { + return d; +} + +function pie() { + var value = identity, + sortValues = descending$1, + sort = null, + startAngle = constant(0), + endAngle = constant(tau), + padAngle = constant(0); + + function pie(data) { + var i, + n = (data = array(data)).length, + j, + k, + sum = 0, + index = new Array(n), + arcs = new Array(n), + a0 = +startAngle.apply(this, arguments), + da = Math.min(tau, Math.max(-tau, endAngle.apply(this, arguments) - a0)), + a1, + p = Math.min(Math.abs(da) / n, padAngle.apply(this, arguments)), + pa = p * (da < 0 ? -1 : 1), + v; + + for (i = 0; i < n; ++i) { + if ((v = arcs[index[i] = i] = +value(data[i], i, data)) > 0) { + sum += v; + } + } + + // Optionally sort the arcs by previously-computed values or by data. + if (sortValues != null) index.sort(function(i, j) { return sortValues(arcs[i], arcs[j]); }); + else if (sort != null) index.sort(function(i, j) { return sort(data[i], data[j]); }); + + // Compute the arcs! They are stored in the original data's order. + for (i = 0, k = sum ? (da - n * pa) / sum : 0; i < n; ++i, a0 = a1) { + j = index[i], v = arcs[j], a1 = a0 + (v > 0 ? v * k : 0) + pa, arcs[j] = { + data: data[j], + index: i, + value: v, + startAngle: a0, + endAngle: a1, + padAngle: p + }; + } + + return arcs; + } + + pie.value = function(_) { + return arguments.length ? (value = typeof _ === "function" ? _ : constant(+_), pie) : value; + }; + + pie.sortValues = function(_) { + return arguments.length ? (sortValues = _, sort = null, pie) : sortValues; + }; + + pie.sort = function(_) { + return arguments.length ? (sort = _, sortValues = null, pie) : sort; + }; + + pie.startAngle = function(_) { + return arguments.length ? (startAngle = typeof _ === "function" ? _ : constant(+_), pie) : startAngle; + }; + + pie.endAngle = function(_) { + return arguments.length ? (endAngle = typeof _ === "function" ? _ : constant(+_), pie) : endAngle; + }; + + pie.padAngle = function(_) { + return arguments.length ? (padAngle = typeof _ === "function" ? _ : constant(+_), pie) : padAngle; + }; + + return pie; +} + +var curveRadialLinear = curveRadial(curveLinear); + +function Radial(curve) { + this._curve = curve; +} + +Radial.prototype = { + areaStart: function() { + this._curve.areaStart(); + }, + areaEnd: function() { + this._curve.areaEnd(); + }, + lineStart: function() { + this._curve.lineStart(); + }, + lineEnd: function() { + this._curve.lineEnd(); + }, + point: function(a, r) { + this._curve.point(r * Math.sin(a), r * -Math.cos(a)); + } +}; + +function curveRadial(curve) { + + function radial(context) { + return new Radial(curve(context)); + } + + radial._curve = curve; + + return radial; +} + +function lineRadial(l) { + var c = l.curve; + + l.angle = l.x, delete l.x; + l.radius = l.y, delete l.y; + + l.curve = function(_) { + return arguments.length ? c(curveRadial(_)) : c()._curve; + }; + + return l; +} + +function lineRadial$1() { + return lineRadial(line().curve(curveRadialLinear)); +} + +function areaRadial() { + var a = area().curve(curveRadialLinear), + c = a.curve, + x0 = a.lineX0, + x1 = a.lineX1, + y0 = a.lineY0, + y1 = a.lineY1; + + a.angle = a.x, delete a.x; + a.startAngle = a.x0, delete a.x0; + a.endAngle = a.x1, delete a.x1; + a.radius = a.y, delete a.y; + a.innerRadius = a.y0, delete a.y0; + a.outerRadius = a.y1, delete a.y1; + a.lineStartAngle = function() { return lineRadial(x0()); }, delete a.lineX0; + a.lineEndAngle = function() { return lineRadial(x1()); }, delete a.lineX1; + a.lineInnerRadius = function() { return lineRadial(y0()); }, delete a.lineY0; + a.lineOuterRadius = function() { return lineRadial(y1()); }, delete a.lineY1; + + a.curve = function(_) { + return arguments.length ? c(curveRadial(_)) : c()._curve; + }; + + return a; +} + +function pointRadial(x, y) { + return [(y = +y) * Math.cos(x -= Math.PI / 2), y * Math.sin(x)]; +} + +class Bump { + constructor(context, x) { + this._context = context; + this._x = x; + } + areaStart() { + this._line = 0; + } + areaEnd() { + this._line = NaN; + } + lineStart() { + this._point = 0; + } + lineEnd() { + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + } + point(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: { + this._point = 1; + if (this._line) this._context.lineTo(x, y); + else this._context.moveTo(x, y); + break; + } + case 1: this._point = 2; // falls through + default: { + if (this._x) this._context.bezierCurveTo(this._x0 = (this._x0 + x) / 2, this._y0, this._x0, y, x, y); + else this._context.bezierCurveTo(this._x0, this._y0 = (this._y0 + y) / 2, x, this._y0, x, y); + break; + } + } + this._x0 = x, this._y0 = y; + } +} + +class BumpRadial { + constructor(context) { + this._context = context; + } + lineStart() { + this._point = 0; + } + lineEnd() {} + point(x, y) { + x = +x, y = +y; + if (this._point === 0) { + this._point = 1; + } else { + const p0 = pointRadial(this._x0, this._y0); + const p1 = pointRadial(this._x0, this._y0 = (this._y0 + y) / 2); + const p2 = pointRadial(x, this._y0); + const p3 = pointRadial(x, y); + this._context.moveTo(...p0); + this._context.bezierCurveTo(...p1, ...p2, ...p3); + } + this._x0 = x, this._y0 = y; + } +} + +function bumpX(context) { + return new Bump(context, true); +} + +function bumpY(context) { + return new Bump(context, false); +} + +function bumpRadial(context) { + return new BumpRadial(context); +} + +function linkSource(d) { + return d.source; +} + +function linkTarget(d) { + return d.target; +} + +function link(curve) { + let source = linkSource, + target = linkTarget, + x$1 = x, + y$1 = y, + context = null, + output = null, + path = withPath(link); + + function link() { + let buffer; + const argv = slice.call(arguments); + const s = source.apply(this, argv); + const t = target.apply(this, argv); + if (context == null) output = curve(buffer = path()); + output.lineStart(); + argv[0] = s, output.point(+x$1.apply(this, argv), +y$1.apply(this, argv)); + argv[0] = t, output.point(+x$1.apply(this, argv), +y$1.apply(this, argv)); + output.lineEnd(); + if (buffer) return output = null, buffer + "" || null; + } + + link.source = function(_) { + return arguments.length ? (source = _, link) : source; + }; + + link.target = function(_) { + return arguments.length ? (target = _, link) : target; + }; + + link.x = function(_) { + return arguments.length ? (x$1 = typeof _ === "function" ? _ : constant(+_), link) : x$1; + }; + + link.y = function(_) { + return arguments.length ? (y$1 = typeof _ === "function" ? _ : constant(+_), link) : y$1; + }; + + link.context = function(_) { + return arguments.length ? (_ == null ? context = output = null : output = curve(context = _), link) : context; + }; + + return link; +} + +function linkHorizontal() { + return link(bumpX); +} + +function linkVertical() { + return link(bumpY); +} + +function linkRadial() { + const l = link(bumpRadial); + l.angle = l.x, delete l.x; + l.radius = l.y, delete l.y; + return l; +} + +const sqrt3$2 = sqrt(3); + +var asterisk = { + draw(context, size) { + const r = sqrt(size + min(size / 28, 0.75)) * 0.59436; + const t = r / 2; + const u = t * sqrt3$2; + context.moveTo(0, r); + context.lineTo(0, -r); + context.moveTo(-u, -t); + context.lineTo(u, t); + context.moveTo(-u, t); + context.lineTo(u, -t); + } +}; + +var circle = { + draw(context, size) { + const r = sqrt(size / pi); + context.moveTo(r, 0); + context.arc(0, 0, r, 0, tau); + } +}; + +var cross = { + draw(context, size) { + const r = sqrt(size / 5) / 2; + context.moveTo(-3 * r, -r); + context.lineTo(-r, -r); + context.lineTo(-r, -3 * r); + context.lineTo(r, -3 * r); + context.lineTo(r, -r); + context.lineTo(3 * r, -r); + context.lineTo(3 * r, r); + context.lineTo(r, r); + context.lineTo(r, 3 * r); + context.lineTo(-r, 3 * r); + context.lineTo(-r, r); + context.lineTo(-3 * r, r); + context.closePath(); + } +}; + +const tan30 = sqrt(1 / 3); +const tan30_2 = tan30 * 2; + +var diamond = { + draw(context, size) { + const y = sqrt(size / tan30_2); + const x = y * tan30; + context.moveTo(0, -y); + context.lineTo(x, 0); + context.lineTo(0, y); + context.lineTo(-x, 0); + context.closePath(); + } +}; + +var diamond2 = { + draw(context, size) { + const r = sqrt(size) * 0.62625; + context.moveTo(0, -r); + context.lineTo(r, 0); + context.lineTo(0, r); + context.lineTo(-r, 0); + context.closePath(); + } +}; + +var plus = { + draw(context, size) { + const r = sqrt(size - min(size / 7, 2)) * 0.87559; + context.moveTo(-r, 0); + context.lineTo(r, 0); + context.moveTo(0, r); + context.lineTo(0, -r); + } +}; + +var square = { + draw(context, size) { + const w = sqrt(size); + const x = -w / 2; + context.rect(x, x, w, w); + } +}; + +var square2 = { + draw(context, size) { + const r = sqrt(size) * 0.4431; + context.moveTo(r, r); + context.lineTo(r, -r); + context.lineTo(-r, -r); + context.lineTo(-r, r); + context.closePath(); + } +}; + +const ka = 0.89081309152928522810; +const kr = sin(pi / 10) / sin(7 * pi / 10); +const kx = sin(tau / 10) * kr; +const ky = -cos(tau / 10) * kr; + +var star = { + draw(context, size) { + const r = sqrt(size * ka); + const x = kx * r; + const y = ky * r; + context.moveTo(0, -r); + context.lineTo(x, y); + for (let i = 1; i < 5; ++i) { + const a = tau * i / 5; + const c = cos(a); + const s = sin(a); + context.lineTo(s * r, -c * r); + context.lineTo(c * x - s * y, s * x + c * y); + } + context.closePath(); + } +}; + +const sqrt3$1 = sqrt(3); + +var triangle = { + draw(context, size) { + const y = -sqrt(size / (sqrt3$1 * 3)); + context.moveTo(0, y * 2); + context.lineTo(-sqrt3$1 * y, -y); + context.lineTo(sqrt3$1 * y, -y); + context.closePath(); + } +}; + +const sqrt3 = sqrt(3); + +var triangle2 = { + draw(context, size) { + const s = sqrt(size) * 0.6824; + const t = s / 2; + const u = (s * sqrt3) / 2; // cos(Math.PI / 6) + context.moveTo(0, -s); + context.lineTo(u, t); + context.lineTo(-u, t); + context.closePath(); + } +}; + +const c = -0.5; +const s = sqrt(3) / 2; +const k = 1 / sqrt(12); +const a = (k / 2 + 1) * 3; + +var wye = { + draw(context, size) { + const r = sqrt(size / a); + const x0 = r / 2, y0 = r * k; + const x1 = x0, y1 = r * k + r; + const x2 = -x1, y2 = y1; + context.moveTo(x0, y0); + context.lineTo(x1, y1); + context.lineTo(x2, y2); + context.lineTo(c * x0 - s * y0, s * x0 + c * y0); + context.lineTo(c * x1 - s * y1, s * x1 + c * y1); + context.lineTo(c * x2 - s * y2, s * x2 + c * y2); + context.lineTo(c * x0 + s * y0, c * y0 - s * x0); + context.lineTo(c * x1 + s * y1, c * y1 - s * x1); + context.lineTo(c * x2 + s * y2, c * y2 - s * x2); + context.closePath(); + } +}; + +var times = { + draw(context, size) { + const r = sqrt(size - min(size / 6, 1.7)) * 0.6189; + context.moveTo(-r, -r); + context.lineTo(r, r); + context.moveTo(-r, r); + context.lineTo(r, -r); + } +}; + +// These symbols are designed to be filled. +const symbolsFill = [ + circle, + cross, + diamond, + square, + star, + triangle, + wye +]; + +// These symbols are designed to be stroked (with a width of 1.5px and round caps). +const symbolsStroke = [ + circle, + plus, + times, + triangle2, + asterisk, + square2, + diamond2 +]; + +function Symbol(type, size) { + let context = null, + path = withPath(symbol); + + type = typeof type === "function" ? type : constant(type || circle); + size = typeof size === "function" ? size : constant(size === undefined ? 64 : +size); + + function symbol() { + let buffer; + if (!context) context = buffer = path(); + type.apply(this, arguments).draw(context, +size.apply(this, arguments)); + if (buffer) return context = null, buffer + "" || null; + } + + symbol.type = function(_) { + return arguments.length ? (type = typeof _ === "function" ? _ : constant(_), symbol) : type; + }; + + symbol.size = function(_) { + return arguments.length ? (size = typeof _ === "function" ? _ : constant(+_), symbol) : size; + }; + + symbol.context = function(_) { + return arguments.length ? (context = _ == null ? null : _, symbol) : context; + }; + + return symbol; +} + +function noop() {} + +function point$3(that, x, y) { + that._context.bezierCurveTo( + (2 * that._x0 + that._x1) / 3, + (2 * that._y0 + that._y1) / 3, + (that._x0 + 2 * that._x1) / 3, + (that._y0 + 2 * that._y1) / 3, + (that._x0 + 4 * that._x1 + x) / 6, + (that._y0 + 4 * that._y1 + y) / 6 + ); +} + +function Basis(context) { + this._context = context; +} + +Basis.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = + this._y0 = this._y1 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 3: point$3(this, this._x1, this._y1); // falls through + case 2: this._context.lineTo(this._x1, this._y1); break; + } + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; break; + case 2: this._point = 3; this._context.lineTo((5 * this._x0 + this._x1) / 6, (5 * this._y0 + this._y1) / 6); // falls through + default: point$3(this, x, y); break; + } + this._x0 = this._x1, this._x1 = x; + this._y0 = this._y1, this._y1 = y; + } +}; + +function basis(context) { + return new Basis(context); +} + +function BasisClosed(context) { + this._context = context; +} + +BasisClosed.prototype = { + areaStart: noop, + areaEnd: noop, + lineStart: function() { + this._x0 = this._x1 = this._x2 = this._x3 = this._x4 = + this._y0 = this._y1 = this._y2 = this._y3 = this._y4 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 1: { + this._context.moveTo(this._x2, this._y2); + this._context.closePath(); + break; + } + case 2: { + this._context.moveTo((this._x2 + 2 * this._x3) / 3, (this._y2 + 2 * this._y3) / 3); + this._context.lineTo((this._x3 + 2 * this._x2) / 3, (this._y3 + 2 * this._y2) / 3); + this._context.closePath(); + break; + } + case 3: { + this.point(this._x2, this._y2); + this.point(this._x3, this._y3); + this.point(this._x4, this._y4); + break; + } + } + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._x2 = x, this._y2 = y; break; + case 1: this._point = 2; this._x3 = x, this._y3 = y; break; + case 2: this._point = 3; this._x4 = x, this._y4 = y; this._context.moveTo((this._x0 + 4 * this._x1 + x) / 6, (this._y0 + 4 * this._y1 + y) / 6); break; + default: point$3(this, x, y); break; + } + this._x0 = this._x1, this._x1 = x; + this._y0 = this._y1, this._y1 = y; + } +}; + +function basisClosed(context) { + return new BasisClosed(context); +} + +function BasisOpen(context) { + this._context = context; +} + +BasisOpen.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = + this._y0 = this._y1 = NaN; + this._point = 0; + }, + lineEnd: function() { + if (this._line || (this._line !== 0 && this._point === 3)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; break; + case 1: this._point = 2; break; + case 2: this._point = 3; var x0 = (this._x0 + 4 * this._x1 + x) / 6, y0 = (this._y0 + 4 * this._y1 + y) / 6; this._line ? this._context.lineTo(x0, y0) : this._context.moveTo(x0, y0); break; + case 3: this._point = 4; // falls through + default: point$3(this, x, y); break; + } + this._x0 = this._x1, this._x1 = x; + this._y0 = this._y1, this._y1 = y; + } +}; + +function basisOpen(context) { + return new BasisOpen(context); +} + +function Bundle(context, beta) { + this._basis = new Basis(context); + this._beta = beta; +} + +Bundle.prototype = { + lineStart: function() { + this._x = []; + this._y = []; + this._basis.lineStart(); + }, + lineEnd: function() { + var x = this._x, + y = this._y, + j = x.length - 1; + + if (j > 0) { + var x0 = x[0], + y0 = y[0], + dx = x[j] - x0, + dy = y[j] - y0, + i = -1, + t; + + while (++i <= j) { + t = i / j; + this._basis.point( + this._beta * x[i] + (1 - this._beta) * (x0 + t * dx), + this._beta * y[i] + (1 - this._beta) * (y0 + t * dy) + ); + } + } + + this._x = this._y = null; + this._basis.lineEnd(); + }, + point: function(x, y) { + this._x.push(+x); + this._y.push(+y); + } +}; + +var bundle = (function custom(beta) { + + function bundle(context) { + return beta === 1 ? new Basis(context) : new Bundle(context, beta); + } + + bundle.beta = function(beta) { + return custom(+beta); + }; + + return bundle; +})(0.85); + +function point$2(that, x, y) { + that._context.bezierCurveTo( + that._x1 + that._k * (that._x2 - that._x0), + that._y1 + that._k * (that._y2 - that._y0), + that._x2 + that._k * (that._x1 - x), + that._y2 + that._k * (that._y1 - y), + that._x2, + that._y2 + ); +} + +function Cardinal(context, tension) { + this._context = context; + this._k = (1 - tension) / 6; +} + +Cardinal.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = this._x2 = + this._y0 = this._y1 = this._y2 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 2: this._context.lineTo(this._x2, this._y2); break; + case 3: point$2(this, this._x1, this._y1); break; + } + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; this._x1 = x, this._y1 = y; break; + case 2: this._point = 3; // falls through + default: point$2(this, x, y); break; + } + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +var cardinal = (function custom(tension) { + + function cardinal(context) { + return new Cardinal(context, tension); + } + + cardinal.tension = function(tension) { + return custom(+tension); + }; + + return cardinal; +})(0); + +function CardinalClosed(context, tension) { + this._context = context; + this._k = (1 - tension) / 6; +} + +CardinalClosed.prototype = { + areaStart: noop, + areaEnd: noop, + lineStart: function() { + this._x0 = this._x1 = this._x2 = this._x3 = this._x4 = this._x5 = + this._y0 = this._y1 = this._y2 = this._y3 = this._y4 = this._y5 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 1: { + this._context.moveTo(this._x3, this._y3); + this._context.closePath(); + break; + } + case 2: { + this._context.lineTo(this._x3, this._y3); + this._context.closePath(); + break; + } + case 3: { + this.point(this._x3, this._y3); + this.point(this._x4, this._y4); + this.point(this._x5, this._y5); + break; + } + } + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._x3 = x, this._y3 = y; break; + case 1: this._point = 2; this._context.moveTo(this._x4 = x, this._y4 = y); break; + case 2: this._point = 3; this._x5 = x, this._y5 = y; break; + default: point$2(this, x, y); break; + } + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +var cardinalClosed = (function custom(tension) { + + function cardinal(context) { + return new CardinalClosed(context, tension); + } + + cardinal.tension = function(tension) { + return custom(+tension); + }; + + return cardinal; +})(0); + +function CardinalOpen(context, tension) { + this._context = context; + this._k = (1 - tension) / 6; +} + +CardinalOpen.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = this._x2 = + this._y0 = this._y1 = this._y2 = NaN; + this._point = 0; + }, + lineEnd: function() { + if (this._line || (this._line !== 0 && this._point === 3)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; break; + case 1: this._point = 2; break; + case 2: this._point = 3; this._line ? this._context.lineTo(this._x2, this._y2) : this._context.moveTo(this._x2, this._y2); break; + case 3: this._point = 4; // falls through + default: point$2(this, x, y); break; + } + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +var cardinalOpen = (function custom(tension) { + + function cardinal(context) { + return new CardinalOpen(context, tension); + } + + cardinal.tension = function(tension) { + return custom(+tension); + }; + + return cardinal; +})(0); + +function point$1(that, x, y) { + var x1 = that._x1, + y1 = that._y1, + x2 = that._x2, + y2 = that._y2; + + if (that._l01_a > epsilon) { + var a = 2 * that._l01_2a + 3 * that._l01_a * that._l12_a + that._l12_2a, + n = 3 * that._l01_a * (that._l01_a + that._l12_a); + x1 = (x1 * a - that._x0 * that._l12_2a + that._x2 * that._l01_2a) / n; + y1 = (y1 * a - that._y0 * that._l12_2a + that._y2 * that._l01_2a) / n; + } + + if (that._l23_a > epsilon) { + var b = 2 * that._l23_2a + 3 * that._l23_a * that._l12_a + that._l12_2a, + m = 3 * that._l23_a * (that._l23_a + that._l12_a); + x2 = (x2 * b + that._x1 * that._l23_2a - x * that._l12_2a) / m; + y2 = (y2 * b + that._y1 * that._l23_2a - y * that._l12_2a) / m; + } + + that._context.bezierCurveTo(x1, y1, x2, y2, that._x2, that._y2); +} + +function CatmullRom(context, alpha) { + this._context = context; + this._alpha = alpha; +} + +CatmullRom.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = this._x2 = + this._y0 = this._y1 = this._y2 = NaN; + this._l01_a = this._l12_a = this._l23_a = + this._l01_2a = this._l12_2a = this._l23_2a = + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 2: this._context.lineTo(this._x2, this._y2); break; + case 3: this.point(this._x2, this._y2); break; + } + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + + if (this._point) { + var x23 = this._x2 - x, + y23 = this._y2 - y; + this._l23_a = Math.sqrt(this._l23_2a = Math.pow(x23 * x23 + y23 * y23, this._alpha)); + } + + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; break; + case 2: this._point = 3; // falls through + default: point$1(this, x, y); break; + } + + this._l01_a = this._l12_a, this._l12_a = this._l23_a; + this._l01_2a = this._l12_2a, this._l12_2a = this._l23_2a; + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +var catmullRom = (function custom(alpha) { + + function catmullRom(context) { + return alpha ? new CatmullRom(context, alpha) : new Cardinal(context, 0); + } + + catmullRom.alpha = function(alpha) { + return custom(+alpha); + }; + + return catmullRom; +})(0.5); + +function CatmullRomClosed(context, alpha) { + this._context = context; + this._alpha = alpha; +} + +CatmullRomClosed.prototype = { + areaStart: noop, + areaEnd: noop, + lineStart: function() { + this._x0 = this._x1 = this._x2 = this._x3 = this._x4 = this._x5 = + this._y0 = this._y1 = this._y2 = this._y3 = this._y4 = this._y5 = NaN; + this._l01_a = this._l12_a = this._l23_a = + this._l01_2a = this._l12_2a = this._l23_2a = + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 1: { + this._context.moveTo(this._x3, this._y3); + this._context.closePath(); + break; + } + case 2: { + this._context.lineTo(this._x3, this._y3); + this._context.closePath(); + break; + } + case 3: { + this.point(this._x3, this._y3); + this.point(this._x4, this._y4); + this.point(this._x5, this._y5); + break; + } + } + }, + point: function(x, y) { + x = +x, y = +y; + + if (this._point) { + var x23 = this._x2 - x, + y23 = this._y2 - y; + this._l23_a = Math.sqrt(this._l23_2a = Math.pow(x23 * x23 + y23 * y23, this._alpha)); + } + + switch (this._point) { + case 0: this._point = 1; this._x3 = x, this._y3 = y; break; + case 1: this._point = 2; this._context.moveTo(this._x4 = x, this._y4 = y); break; + case 2: this._point = 3; this._x5 = x, this._y5 = y; break; + default: point$1(this, x, y); break; + } + + this._l01_a = this._l12_a, this._l12_a = this._l23_a; + this._l01_2a = this._l12_2a, this._l12_2a = this._l23_2a; + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +var catmullRomClosed = (function custom(alpha) { + + function catmullRom(context) { + return alpha ? new CatmullRomClosed(context, alpha) : new CardinalClosed(context, 0); + } + + catmullRom.alpha = function(alpha) { + return custom(+alpha); + }; + + return catmullRom; +})(0.5); + +function CatmullRomOpen(context, alpha) { + this._context = context; + this._alpha = alpha; +} + +CatmullRomOpen.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = this._x2 = + this._y0 = this._y1 = this._y2 = NaN; + this._l01_a = this._l12_a = this._l23_a = + this._l01_2a = this._l12_2a = this._l23_2a = + this._point = 0; + }, + lineEnd: function() { + if (this._line || (this._line !== 0 && this._point === 3)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + + if (this._point) { + var x23 = this._x2 - x, + y23 = this._y2 - y; + this._l23_a = Math.sqrt(this._l23_2a = Math.pow(x23 * x23 + y23 * y23, this._alpha)); + } + + switch (this._point) { + case 0: this._point = 1; break; + case 1: this._point = 2; break; + case 2: this._point = 3; this._line ? this._context.lineTo(this._x2, this._y2) : this._context.moveTo(this._x2, this._y2); break; + case 3: this._point = 4; // falls through + default: point$1(this, x, y); break; + } + + this._l01_a = this._l12_a, this._l12_a = this._l23_a; + this._l01_2a = this._l12_2a, this._l12_2a = this._l23_2a; + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +var catmullRomOpen = (function custom(alpha) { + + function catmullRom(context) { + return alpha ? new CatmullRomOpen(context, alpha) : new CardinalOpen(context, 0); + } + + catmullRom.alpha = function(alpha) { + return custom(+alpha); + }; + + return catmullRom; +})(0.5); + +function LinearClosed(context) { + this._context = context; +} + +LinearClosed.prototype = { + areaStart: noop, + areaEnd: noop, + lineStart: function() { + this._point = 0; + }, + lineEnd: function() { + if (this._point) this._context.closePath(); + }, + point: function(x, y) { + x = +x, y = +y; + if (this._point) this._context.lineTo(x, y); + else this._point = 1, this._context.moveTo(x, y); + } +}; + +function linearClosed(context) { + return new LinearClosed(context); +} + +function sign(x) { + return x < 0 ? -1 : 1; +} + +// Calculate the slopes of the tangents (Hermite-type interpolation) based on +// the following paper: Steffen, M. 1990. A Simple Method for Monotonic +// Interpolation in One Dimension. Astronomy and Astrophysics, Vol. 239, NO. +// NOV(II), P. 443, 1990. +function slope3(that, x2, y2) { + var h0 = that._x1 - that._x0, + h1 = x2 - that._x1, + s0 = (that._y1 - that._y0) / (h0 || h1 < 0 && -0), + s1 = (y2 - that._y1) / (h1 || h0 < 0 && -0), + p = (s0 * h1 + s1 * h0) / (h0 + h1); + return (sign(s0) + sign(s1)) * Math.min(Math.abs(s0), Math.abs(s1), 0.5 * Math.abs(p)) || 0; +} + +// Calculate a one-sided slope. +function slope2(that, t) { + var h = that._x1 - that._x0; + return h ? (3 * (that._y1 - that._y0) / h - t) / 2 : t; +} + +// According to https://en.wikipedia.org/wiki/Cubic_Hermite_spline#Representations +// "you can express cubic Hermite interpolation in terms of cubic Bézier curves +// with respect to the four values p0, p0 + m0 / 3, p1 - m1 / 3, p1". +function point(that, t0, t1) { + var x0 = that._x0, + y0 = that._y0, + x1 = that._x1, + y1 = that._y1, + dx = (x1 - x0) / 3; + that._context.bezierCurveTo(x0 + dx, y0 + dx * t0, x1 - dx, y1 - dx * t1, x1, y1); +} + +function MonotoneX(context) { + this._context = context; +} + +MonotoneX.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = + this._y0 = this._y1 = + this._t0 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 2: this._context.lineTo(this._x1, this._y1); break; + case 3: point(this, this._t0, slope2(this, this._t0)); break; + } + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + var t1 = NaN; + + x = +x, y = +y; + if (x === this._x1 && y === this._y1) return; // Ignore coincident points. + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; break; + case 2: this._point = 3; point(this, slope2(this, t1 = slope3(this, x, y)), t1); break; + default: point(this, this._t0, t1 = slope3(this, x, y)); break; + } + + this._x0 = this._x1, this._x1 = x; + this._y0 = this._y1, this._y1 = y; + this._t0 = t1; + } +}; + +function MonotoneY(context) { + this._context = new ReflectContext(context); +} + +(MonotoneY.prototype = Object.create(MonotoneX.prototype)).point = function(x, y) { + MonotoneX.prototype.point.call(this, y, x); +}; + +function ReflectContext(context) { + this._context = context; +} + +ReflectContext.prototype = { + moveTo: function(x, y) { this._context.moveTo(y, x); }, + closePath: function() { this._context.closePath(); }, + lineTo: function(x, y) { this._context.lineTo(y, x); }, + bezierCurveTo: function(x1, y1, x2, y2, x, y) { this._context.bezierCurveTo(y1, x1, y2, x2, y, x); } +}; + +function monotoneX(context) { + return new MonotoneX(context); +} + +function monotoneY(context) { + return new MonotoneY(context); +} + +function Natural(context) { + this._context = context; +} + +Natural.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x = []; + this._y = []; + }, + lineEnd: function() { + var x = this._x, + y = this._y, + n = x.length; + + if (n) { + this._line ? this._context.lineTo(x[0], y[0]) : this._context.moveTo(x[0], y[0]); + if (n === 2) { + this._context.lineTo(x[1], y[1]); + } else { + var px = controlPoints(x), + py = controlPoints(y); + for (var i0 = 0, i1 = 1; i1 < n; ++i0, ++i1) { + this._context.bezierCurveTo(px[0][i0], py[0][i0], px[1][i0], py[1][i0], x[i1], y[i1]); + } + } + } + + if (this._line || (this._line !== 0 && n === 1)) this._context.closePath(); + this._line = 1 - this._line; + this._x = this._y = null; + }, + point: function(x, y) { + this._x.push(+x); + this._y.push(+y); + } +}; + +// See https://www.particleincell.com/2012/bezier-splines/ for derivation. +function controlPoints(x) { + var i, + n = x.length - 1, + m, + a = new Array(n), + b = new Array(n), + r = new Array(n); + a[0] = 0, b[0] = 2, r[0] = x[0] + 2 * x[1]; + for (i = 1; i < n - 1; ++i) a[i] = 1, b[i] = 4, r[i] = 4 * x[i] + 2 * x[i + 1]; + a[n - 1] = 2, b[n - 1] = 7, r[n - 1] = 8 * x[n - 1] + x[n]; + for (i = 1; i < n; ++i) m = a[i] / b[i - 1], b[i] -= m, r[i] -= m * r[i - 1]; + a[n - 1] = r[n - 1] / b[n - 1]; + for (i = n - 2; i >= 0; --i) a[i] = (r[i] - a[i + 1]) / b[i]; + b[n - 1] = (x[n] + a[n - 1]) / 2; + for (i = 0; i < n - 1; ++i) b[i] = 2 * x[i + 1] - a[i + 1]; + return [a, b]; +} + +function natural(context) { + return new Natural(context); +} + +function Step(context, t) { + this._context = context; + this._t = t; +} + +Step.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x = this._y = NaN; + this._point = 0; + }, + lineEnd: function() { + if (0 < this._t && this._t < 1 && this._point === 2) this._context.lineTo(this._x, this._y); + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + if (this._line >= 0) this._t = 1 - this._t, this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; // falls through + default: { + if (this._t <= 0) { + this._context.lineTo(this._x, y); + this._context.lineTo(x, y); + } else { + var x1 = this._x * (1 - this._t) + x * this._t; + this._context.lineTo(x1, this._y); + this._context.lineTo(x1, y); + } + break; + } + } + this._x = x, this._y = y; + } +}; + +function step(context) { + return new Step(context, 0.5); +} + +function stepBefore(context) { + return new Step(context, 0); +} + +function stepAfter(context) { + return new Step(context, 1); +} + +function none$1(series, order) { + if (!((n = series.length) > 1)) return; + for (var i = 1, j, s0, s1 = series[order[0]], n, m = s1.length; i < n; ++i) { + s0 = s1, s1 = series[order[i]]; + for (j = 0; j < m; ++j) { + s1[j][1] += s1[j][0] = isNaN(s0[j][1]) ? s0[j][0] : s0[j][1]; + } + } +} + +function none(series) { + var n = series.length, o = new Array(n); + while (--n >= 0) o[n] = n; + return o; +} + +function stackValue(d, key) { + return d[key]; +} + +function stackSeries(key) { + const series = []; + series.key = key; + return series; +} + +function stack() { + var keys = constant([]), + order = none, + offset = none$1, + value = stackValue; + + function stack(data) { + var sz = Array.from(keys.apply(this, arguments), stackSeries), + i, n = sz.length, j = -1, + oz; + + for (const d of data) { + for (i = 0, ++j; i < n; ++i) { + (sz[i][j] = [0, +value(d, sz[i].key, j, data)]).data = d; + } + } + + for (i = 0, oz = array(order(sz)); i < n; ++i) { + sz[oz[i]].index = i; + } + + offset(sz, oz); + return sz; + } + + stack.keys = function(_) { + return arguments.length ? (keys = typeof _ === "function" ? _ : constant(Array.from(_)), stack) : keys; + }; + + stack.value = function(_) { + return arguments.length ? (value = typeof _ === "function" ? _ : constant(+_), stack) : value; + }; + + stack.order = function(_) { + return arguments.length ? (order = _ == null ? none : typeof _ === "function" ? _ : constant(Array.from(_)), stack) : order; + }; + + stack.offset = function(_) { + return arguments.length ? (offset = _ == null ? none$1 : _, stack) : offset; + }; + + return stack; +} + +function expand(series, order) { + if (!((n = series.length) > 0)) return; + for (var i, n, j = 0, m = series[0].length, y; j < m; ++j) { + for (y = i = 0; i < n; ++i) y += series[i][j][1] || 0; + if (y) for (i = 0; i < n; ++i) series[i][j][1] /= y; + } + none$1(series, order); +} + +function diverging(series, order) { + if (!((n = series.length) > 0)) return; + for (var i, j = 0, d, dy, yp, yn, n, m = series[order[0]].length; j < m; ++j) { + for (yp = yn = 0, i = 0; i < n; ++i) { + if ((dy = (d = series[order[i]][j])[1] - d[0]) > 0) { + d[0] = yp, d[1] = yp += dy; + } else if (dy < 0) { + d[1] = yn, d[0] = yn += dy; + } else { + d[0] = 0, d[1] = dy; + } + } + } +} + +function silhouette(series, order) { + if (!((n = series.length) > 0)) return; + for (var j = 0, s0 = series[order[0]], n, m = s0.length; j < m; ++j) { + for (var i = 0, y = 0; i < n; ++i) y += series[i][j][1] || 0; + s0[j][1] += s0[j][0] = -y / 2; + } + none$1(series, order); +} + +function wiggle(series, order) { + if (!((n = series.length) > 0) || !((m = (s0 = series[order[0]]).length) > 0)) return; + for (var y = 0, j = 1, s0, m, n; j < m; ++j) { + for (var i = 0, s1 = 0, s2 = 0; i < n; ++i) { + var si = series[order[i]], + sij0 = si[j][1] || 0, + sij1 = si[j - 1][1] || 0, + s3 = (sij0 - sij1) / 2; + for (var k = 0; k < i; ++k) { + var sk = series[order[k]], + skj0 = sk[j][1] || 0, + skj1 = sk[j - 1][1] || 0; + s3 += skj0 - skj1; + } + s1 += sij0, s2 += s3 * sij0; + } + s0[j - 1][1] += s0[j - 1][0] = y; + if (s1) y -= s2 / s1; + } + s0[j - 1][1] += s0[j - 1][0] = y; + none$1(series, order); +} + +function appearance(series) { + var peaks = series.map(peak); + return none(series).sort(function(a, b) { return peaks[a] - peaks[b]; }); +} + +function peak(series) { + var i = -1, j = 0, n = series.length, vi, vj = -Infinity; + while (++i < n) if ((vi = +series[i][1]) > vj) vj = vi, j = i; + return j; +} + +function ascending(series) { + var sums = series.map(sum); + return none(series).sort(function(a, b) { return sums[a] - sums[b]; }); +} + +function sum(series) { + var s = 0, i = -1, n = series.length, v; + while (++i < n) if (v = +series[i][1]) s += v; + return s; +} + +function descending(series) { + return ascending(series).reverse(); +} + +function insideOut(series) { + var n = series.length, + i, + j, + sums = series.map(sum), + order = appearance(series), + top = 0, + bottom = 0, + tops = [], + bottoms = []; + + for (i = 0; i < n; ++i) { + j = order[i]; + if (top < bottom) { + top += sums[j]; + tops.push(j); + } else { + bottom += sums[j]; + bottoms.push(j); + } + } + + return bottoms.reverse().concat(tops); +} + +function reverse(series) { + return none(series).reverse(); +} + +exports.arc = arc; +exports.area = area; +exports.areaRadial = areaRadial; +exports.curveBasis = basis; +exports.curveBasisClosed = basisClosed; +exports.curveBasisOpen = basisOpen; +exports.curveBumpX = bumpX; +exports.curveBumpY = bumpY; +exports.curveBundle = bundle; +exports.curveCardinal = cardinal; +exports.curveCardinalClosed = cardinalClosed; +exports.curveCardinalOpen = cardinalOpen; +exports.curveCatmullRom = catmullRom; +exports.curveCatmullRomClosed = catmullRomClosed; +exports.curveCatmullRomOpen = catmullRomOpen; +exports.curveLinear = curveLinear; +exports.curveLinearClosed = linearClosed; +exports.curveMonotoneX = monotoneX; +exports.curveMonotoneY = monotoneY; +exports.curveNatural = natural; +exports.curveStep = step; +exports.curveStepAfter = stepAfter; +exports.curveStepBefore = stepBefore; +exports.line = line; +exports.lineRadial = lineRadial$1; +exports.link = link; +exports.linkHorizontal = linkHorizontal; +exports.linkRadial = linkRadial; +exports.linkVertical = linkVertical; +exports.pie = pie; +exports.pointRadial = pointRadial; +exports.radialArea = areaRadial; +exports.radialLine = lineRadial$1; +exports.stack = stack; +exports.stackOffsetDiverging = diverging; +exports.stackOffsetExpand = expand; +exports.stackOffsetNone = none$1; +exports.stackOffsetSilhouette = silhouette; +exports.stackOffsetWiggle = wiggle; +exports.stackOrderAppearance = appearance; +exports.stackOrderAscending = ascending; +exports.stackOrderDescending = descending; +exports.stackOrderInsideOut = insideOut; +exports.stackOrderNone = none; +exports.stackOrderReverse = reverse; +exports.symbol = Symbol; +exports.symbolAsterisk = asterisk; +exports.symbolCircle = circle; +exports.symbolCross = cross; +exports.symbolDiamond = diamond; +exports.symbolDiamond2 = diamond2; +exports.symbolPlus = plus; +exports.symbolSquare = square; +exports.symbolSquare2 = square2; +exports.symbolStar = star; +exports.symbolTimes = times; +exports.symbolTriangle = triangle; +exports.symbolTriangle2 = triangle2; +exports.symbolWye = wye; +exports.symbolX = times; +exports.symbols = symbolsFill; +exports.symbolsFill = symbolsFill; +exports.symbolsStroke = symbolsStroke; + +})); diff --git a/frontend/node_modules/d3-shape/dist/d3-shape.min.js b/frontend/node_modules/d3-shape/dist/d3-shape.min.js new file mode 100644 index 0000000..7cc2038 --- /dev/null +++ b/frontend/node_modules/d3-shape/dist/d3-shape.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-shape/ v3.2.0 Copyright 2010-2022 Mike Bostock +!function(t,n){"object"==typeof exports&&"undefined"!=typeof module?n(exports,require("d3-path")):"function"==typeof define&&define.amd?define(["exports","d3-path"],n):n((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{},t.d3)}(this,(function(t,n){"use strict";function i(t){return function(){return t}}const e=Math.abs,s=Math.atan2,o=Math.cos,h=Math.max,_=Math.min,r=Math.sin,a=Math.sqrt,l=1e-12,c=Math.PI,u=c/2,f=2*c;function y(t){return t>1?0:t<-1?c:Math.acos(t)}function x(t){return t>=1?u:t<=-1?-u:Math.asin(t)}function p(t){let i=3;return t.digits=function(n){if(!arguments.length)return i;if(null==n)i=null;else{const t=Math.floor(n);if(!(t>=0))throw new RangeError(`invalid digits: ${n}`);i=t}return t},()=>new n.Path(i)}function v(t){return t.innerRadius}function d(t){return t.outerRadius}function T(t){return t.startAngle}function g(t){return t.endAngle}function m(t){return t&&t.padAngle}function b(t,n,i,e,s,o,h,_){var r=i-t,a=e-n,c=h-s,u=_-o,f=u*r-c*a;if(!(f*fR*R+O*O&&(S=A,E=P),{cx:S,cy:E,x01:-u,y01:-f,x11:S*(s/w-1),y11:E*(s/w-1)}}var k=Array.prototype.slice;function N(t){return"object"==typeof t&&"length"in t?t:Array.from(t)}function S(t){this._context=t}function E(t){return new S(t)}function A(t){return t[0]}function P(t){return t[1]}function M(t,n){var e=i(!0),s=null,o=E,h=null,_=p(r);function r(i){var r,a,l,c=(i=N(i)).length,u=!1;for(null==s&&(h=o(l=_())),r=0;r<=c;++r)!(r=c;--u)r.point(v[u],d[u]);r.lineEnd(),r.areaEnd()}p&&(v[l]=+t(f,l,i),d[l]=+n(f,l,i),r.point(s?+s(f,l,i):v[l],e?+e(f,l,i):d[l]))}if(y)return r=null,y+""||null}function c(){return M().defined(o).curve(_).context(h)}return t="function"==typeof t?t:void 0===t?A:i(+t),n="function"==typeof n?n:i(void 0===n?0:+n),e="function"==typeof e?e:void 0===e?P:i(+e),l.x=function(n){return arguments.length?(t="function"==typeof n?n:i(+n),s=null,l):t},l.x0=function(n){return arguments.length?(t="function"==typeof n?n:i(+n),l):t},l.x1=function(t){return arguments.length?(s=null==t?null:"function"==typeof t?t:i(+t),l):s},l.y=function(t){return arguments.length?(n="function"==typeof t?t:i(+t),e=null,l):n},l.y0=function(t){return arguments.length?(n="function"==typeof t?t:i(+t),l):n},l.y1=function(t){return arguments.length?(e=null==t?null:"function"==typeof t?t:i(+t),l):e},l.lineX0=l.lineY0=function(){return c().x(t).y(n)},l.lineY1=function(){return c().x(t).y(e)},l.lineX1=function(){return c().x(s).y(n)},l.defined=function(t){return arguments.length?(o="function"==typeof t?t:i(!!t),l):o},l.curve=function(t){return arguments.length?(_=t,null!=h&&(r=_(h)),l):_},l.context=function(t){return arguments.length?(null==t?h=r=null:r=_(h=t),l):h},l}function R(t,n){return nt?1:n>=t?0:NaN}function O(t){return t}S.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._point=0},lineEnd:function(){(this._line||0!==this._line&&1===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._line?this._context.lineTo(t,n):this._context.moveTo(t,n);break;case 1:this._point=2;default:this._context.lineTo(t,n)}}};var z=Y(E);function X(t){this._curve=t}function Y(t){function n(n){return new X(t(n))}return n._curve=t,n}function q(t){var n=t.curve;return t.angle=t.x,delete t.x,t.radius=t.y,delete t.y,t.curve=function(t){return arguments.length?n(Y(t)):n()._curve},t}function B(){return q(M().curve(z))}function D(){var t=C().curve(z),n=t.curve,i=t.lineX0,e=t.lineX1,s=t.lineY0,o=t.lineY1;return t.angle=t.x,delete t.x,t.startAngle=t.x0,delete t.x0,t.endAngle=t.x1,delete t.x1,t.radius=t.y,delete t.y,t.innerRadius=t.y0,delete t.y0,t.outerRadius=t.y1,delete t.y1,t.lineStartAngle=function(){return q(i())},delete t.lineX0,t.lineEndAngle=function(){return q(e())},delete t.lineX1,t.lineInnerRadius=function(){return q(s())},delete t.lineY0,t.lineOuterRadius=function(){return q(o())},delete t.lineY1,t.curve=function(t){return arguments.length?n(Y(t)):n()._curve},t}function I(t,n){return[(n=+n)*Math.cos(t-=Math.PI/2),n*Math.sin(t)]}X.prototype={areaStart:function(){this._curve.areaStart()},areaEnd:function(){this._curve.areaEnd()},lineStart:function(){this._curve.lineStart()},lineEnd:function(){this._curve.lineEnd()},point:function(t,n){this._curve.point(n*Math.sin(t),n*-Math.cos(t))}};class j{constructor(t,n){this._context=t,this._x=n}areaStart(){this._line=0}areaEnd(){this._line=NaN}lineStart(){this._point=0}lineEnd(){(this._line||0!==this._line&&1===this._point)&&this._context.closePath(),this._line=1-this._line}point(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._line?this._context.lineTo(t,n):this._context.moveTo(t,n);break;case 1:this._point=2;default:this._x?this._context.bezierCurveTo(this._x0=(this._x0+t)/2,this._y0,this._x0,n,t,n):this._context.bezierCurveTo(this._x0,this._y0=(this._y0+n)/2,t,this._y0,t,n)}this._x0=t,this._y0=n}}class L{constructor(t){this._context=t}lineStart(){this._point=0}lineEnd(){}point(t,n){if(t=+t,n=+n,0===this._point)this._point=1;else{const i=I(this._x0,this._y0),e=I(this._x0,this._y0=(this._y0+n)/2),s=I(t,this._y0),o=I(t,n);this._context.moveTo(...i),this._context.bezierCurveTo(...e,...s,...o)}this._x0=t,this._y0=n}}function V(t){return new j(t,!0)}function W(t){return new j(t,!1)}function F(t){return new L(t)}function H(t){return t.source}function $(t){return t.target}function G(t){let n=H,e=$,s=A,o=P,h=null,_=null,r=p(a);function a(){let i;const a=k.call(arguments),l=n.apply(this,a),c=e.apply(this,a);if(null==h&&(_=t(i=r())),_.lineStart(),a[0]=l,_.point(+s.apply(this,a),+o.apply(this,a)),a[0]=c,_.point(+s.apply(this,a),+o.apply(this,a)),_.lineEnd(),i)return _=null,i+""||null}return a.source=function(t){return arguments.length?(n=t,a):n},a.target=function(t){return arguments.length?(e=t,a):e},a.x=function(t){return arguments.length?(s="function"==typeof t?t:i(+t),a):s},a.y=function(t){return arguments.length?(o="function"==typeof t?t:i(+t),a):o},a.context=function(n){return arguments.length?(null==n?h=_=null:_=t(h=n),a):h},a}const J=a(3);var K={draw(t,n){const i=.59436*a(n+_(n/28,.75)),e=i/2,s=e*J;t.moveTo(0,i),t.lineTo(0,-i),t.moveTo(-s,-e),t.lineTo(s,e),t.moveTo(-s,e),t.lineTo(s,-e)}},Q={draw(t,n){const i=a(n/c);t.moveTo(i,0),t.arc(0,0,i,0,f)}},U={draw(t,n){const i=a(n/5)/2;t.moveTo(-3*i,-i),t.lineTo(-i,-i),t.lineTo(-i,-3*i),t.lineTo(i,-3*i),t.lineTo(i,-i),t.lineTo(3*i,-i),t.lineTo(3*i,i),t.lineTo(i,i),t.lineTo(i,3*i),t.lineTo(-i,3*i),t.lineTo(-i,i),t.lineTo(-3*i,i),t.closePath()}};const Z=a(1/3),tt=2*Z;var nt={draw(t,n){const i=a(n/tt),e=i*Z;t.moveTo(0,-i),t.lineTo(e,0),t.lineTo(0,i),t.lineTo(-e,0),t.closePath()}},it={draw(t,n){const i=.62625*a(n);t.moveTo(0,-i),t.lineTo(i,0),t.lineTo(0,i),t.lineTo(-i,0),t.closePath()}},et={draw(t,n){const i=.87559*a(n-_(n/7,2));t.moveTo(-i,0),t.lineTo(i,0),t.moveTo(0,i),t.lineTo(0,-i)}},st={draw(t,n){const i=a(n),e=-i/2;t.rect(e,e,i,i)}},ot={draw(t,n){const i=.4431*a(n);t.moveTo(i,i),t.lineTo(i,-i),t.lineTo(-i,-i),t.lineTo(-i,i),t.closePath()}};const ht=r(c/10)/r(7*c/10),_t=r(f/10)*ht,rt=-o(f/10)*ht;var at={draw(t,n){const i=a(.8908130915292852*n),e=_t*i,s=rt*i;t.moveTo(0,-i),t.lineTo(e,s);for(let n=1;n<5;++n){const h=f*n/5,_=o(h),a=r(h);t.lineTo(a*i,-_*i),t.lineTo(_*e-a*s,a*e+_*s)}t.closePath()}};const lt=a(3);var ct={draw(t,n){const i=-a(n/(3*lt));t.moveTo(0,2*i),t.lineTo(-lt*i,-i),t.lineTo(lt*i,-i),t.closePath()}};const ut=a(3);var ft={draw(t,n){const i=.6824*a(n),e=i/2,s=i*ut/2;t.moveTo(0,-i),t.lineTo(s,e),t.lineTo(-s,e),t.closePath()}};const yt=-.5,xt=a(3)/2,pt=1/a(12),vt=3*(pt/2+1);var dt={draw(t,n){const i=a(n/vt),e=i/2,s=i*pt,o=e,h=i*pt+i,_=-o,r=h;t.moveTo(e,s),t.lineTo(o,h),t.lineTo(_,r),t.lineTo(yt*e-xt*s,xt*e+yt*s),t.lineTo(yt*o-xt*h,xt*o+yt*h),t.lineTo(yt*_-xt*r,xt*_+yt*r),t.lineTo(yt*e+xt*s,yt*s-xt*e),t.lineTo(yt*o+xt*h,yt*h-xt*o),t.lineTo(yt*_+xt*r,yt*r-xt*_),t.closePath()}},Tt={draw(t,n){const i=.6189*a(n-_(n/6,1.7));t.moveTo(-i,-i),t.lineTo(i,i),t.moveTo(-i,i),t.lineTo(i,-i)}};const gt=[Q,U,nt,st,at,ct,dt],mt=[Q,et,Tt,ft,K,ot,it];function bt(){}function wt(t,n,i){t._context.bezierCurveTo((2*t._x0+t._x1)/3,(2*t._y0+t._y1)/3,(t._x0+2*t._x1)/3,(t._y0+2*t._y1)/3,(t._x0+4*t._x1+n)/6,(t._y0+4*t._y1+i)/6)}function kt(t){this._context=t}function Nt(t){this._context=t}function St(t){this._context=t}function Et(t,n){this._basis=new kt(t),this._beta=n}kt.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._x0=this._x1=this._y0=this._y1=NaN,this._point=0},lineEnd:function(){switch(this._point){case 3:wt(this,this._x1,this._y1);case 2:this._context.lineTo(this._x1,this._y1)}(this._line||0!==this._line&&1===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._line?this._context.lineTo(t,n):this._context.moveTo(t,n);break;case 1:this._point=2;break;case 2:this._point=3,this._context.lineTo((5*this._x0+this._x1)/6,(5*this._y0+this._y1)/6);default:wt(this,t,n)}this._x0=this._x1,this._x1=t,this._y0=this._y1,this._y1=n}},Nt.prototype={areaStart:bt,areaEnd:bt,lineStart:function(){this._x0=this._x1=this._x2=this._x3=this._x4=this._y0=this._y1=this._y2=this._y3=this._y4=NaN,this._point=0},lineEnd:function(){switch(this._point){case 1:this._context.moveTo(this._x2,this._y2),this._context.closePath();break;case 2:this._context.moveTo((this._x2+2*this._x3)/3,(this._y2+2*this._y3)/3),this._context.lineTo((this._x3+2*this._x2)/3,(this._y3+2*this._y2)/3),this._context.closePath();break;case 3:this.point(this._x2,this._y2),this.point(this._x3,this._y3),this.point(this._x4,this._y4)}},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._x2=t,this._y2=n;break;case 1:this._point=2,this._x3=t,this._y3=n;break;case 2:this._point=3,this._x4=t,this._y4=n,this._context.moveTo((this._x0+4*this._x1+t)/6,(this._y0+4*this._y1+n)/6);break;default:wt(this,t,n)}this._x0=this._x1,this._x1=t,this._y0=this._y1,this._y1=n}},St.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._x0=this._x1=this._y0=this._y1=NaN,this._point=0},lineEnd:function(){(this._line||0!==this._line&&3===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1;break;case 1:this._point=2;break;case 2:this._point=3;var i=(this._x0+4*this._x1+t)/6,e=(this._y0+4*this._y1+n)/6;this._line?this._context.lineTo(i,e):this._context.moveTo(i,e);break;case 3:this._point=4;default:wt(this,t,n)}this._x0=this._x1,this._x1=t,this._y0=this._y1,this._y1=n}},Et.prototype={lineStart:function(){this._x=[],this._y=[],this._basis.lineStart()},lineEnd:function(){var t=this._x,n=this._y,i=t.length-1;if(i>0)for(var e,s=t[0],o=n[0],h=t[i]-s,_=n[i]-o,r=-1;++r<=i;)e=r/i,this._basis.point(this._beta*t[r]+(1-this._beta)*(s+e*h),this._beta*n[r]+(1-this._beta)*(o+e*_));this._x=this._y=null,this._basis.lineEnd()},point:function(t,n){this._x.push(+t),this._y.push(+n)}};var At=function t(n){function i(t){return 1===n?new kt(t):new Et(t,n)}return i.beta=function(n){return t(+n)},i}(.85);function Pt(t,n,i){t._context.bezierCurveTo(t._x1+t._k*(t._x2-t._x0),t._y1+t._k*(t._y2-t._y0),t._x2+t._k*(t._x1-n),t._y2+t._k*(t._y1-i),t._x2,t._y2)}function Mt(t,n){this._context=t,this._k=(1-n)/6}Mt.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._x0=this._x1=this._x2=this._y0=this._y1=this._y2=NaN,this._point=0},lineEnd:function(){switch(this._point){case 2:this._context.lineTo(this._x2,this._y2);break;case 3:Pt(this,this._x1,this._y1)}(this._line||0!==this._line&&1===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._line?this._context.lineTo(t,n):this._context.moveTo(t,n);break;case 1:this._point=2,this._x1=t,this._y1=n;break;case 2:this._point=3;default:Pt(this,t,n)}this._x0=this._x1,this._x1=this._x2,this._x2=t,this._y0=this._y1,this._y1=this._y2,this._y2=n}};var Ct=function t(n){function i(t){return new Mt(t,n)}return i.tension=function(n){return t(+n)},i}(0);function Rt(t,n){this._context=t,this._k=(1-n)/6}Rt.prototype={areaStart:bt,areaEnd:bt,lineStart:function(){this._x0=this._x1=this._x2=this._x3=this._x4=this._x5=this._y0=this._y1=this._y2=this._y3=this._y4=this._y5=NaN,this._point=0},lineEnd:function(){switch(this._point){case 1:this._context.moveTo(this._x3,this._y3),this._context.closePath();break;case 2:this._context.lineTo(this._x3,this._y3),this._context.closePath();break;case 3:this.point(this._x3,this._y3),this.point(this._x4,this._y4),this.point(this._x5,this._y5)}},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._x3=t,this._y3=n;break;case 1:this._point=2,this._context.moveTo(this._x4=t,this._y4=n);break;case 2:this._point=3,this._x5=t,this._y5=n;break;default:Pt(this,t,n)}this._x0=this._x1,this._x1=this._x2,this._x2=t,this._y0=this._y1,this._y1=this._y2,this._y2=n}};var Ot=function t(n){function i(t){return new Rt(t,n)}return i.tension=function(n){return t(+n)},i}(0);function zt(t,n){this._context=t,this._k=(1-n)/6}zt.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._x0=this._x1=this._x2=this._y0=this._y1=this._y2=NaN,this._point=0},lineEnd:function(){(this._line||0!==this._line&&3===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1;break;case 1:this._point=2;break;case 2:this._point=3,this._line?this._context.lineTo(this._x2,this._y2):this._context.moveTo(this._x2,this._y2);break;case 3:this._point=4;default:Pt(this,t,n)}this._x0=this._x1,this._x1=this._x2,this._x2=t,this._y0=this._y1,this._y1=this._y2,this._y2=n}};var Xt=function t(n){function i(t){return new zt(t,n)}return i.tension=function(n){return t(+n)},i}(0);function Yt(t,n,i){var e=t._x1,s=t._y1,o=t._x2,h=t._y2;if(t._l01_a>l){var _=2*t._l01_2a+3*t._l01_a*t._l12_a+t._l12_2a,r=3*t._l01_a*(t._l01_a+t._l12_a);e=(e*_-t._x0*t._l12_2a+t._x2*t._l01_2a)/r,s=(s*_-t._y0*t._l12_2a+t._y2*t._l01_2a)/r}if(t._l23_a>l){var a=2*t._l23_2a+3*t._l23_a*t._l12_a+t._l12_2a,c=3*t._l23_a*(t._l23_a+t._l12_a);o=(o*a+t._x1*t._l23_2a-n*t._l12_2a)/c,h=(h*a+t._y1*t._l23_2a-i*t._l12_2a)/c}t._context.bezierCurveTo(e,s,o,h,t._x2,t._y2)}function qt(t,n){this._context=t,this._alpha=n}qt.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._x0=this._x1=this._x2=this._y0=this._y1=this._y2=NaN,this._l01_a=this._l12_a=this._l23_a=this._l01_2a=this._l12_2a=this._l23_2a=this._point=0},lineEnd:function(){switch(this._point){case 2:this._context.lineTo(this._x2,this._y2);break;case 3:this.point(this._x2,this._y2)}(this._line||0!==this._line&&1===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){if(t=+t,n=+n,this._point){var i=this._x2-t,e=this._y2-n;this._l23_a=Math.sqrt(this._l23_2a=Math.pow(i*i+e*e,this._alpha))}switch(this._point){case 0:this._point=1,this._line?this._context.lineTo(t,n):this._context.moveTo(t,n);break;case 1:this._point=2;break;case 2:this._point=3;default:Yt(this,t,n)}this._l01_a=this._l12_a,this._l12_a=this._l23_a,this._l01_2a=this._l12_2a,this._l12_2a=this._l23_2a,this._x0=this._x1,this._x1=this._x2,this._x2=t,this._y0=this._y1,this._y1=this._y2,this._y2=n}};var Bt=function t(n){function i(t){return n?new qt(t,n):new Mt(t,0)}return i.alpha=function(n){return t(+n)},i}(.5);function Dt(t,n){this._context=t,this._alpha=n}Dt.prototype={areaStart:bt,areaEnd:bt,lineStart:function(){this._x0=this._x1=this._x2=this._x3=this._x4=this._x5=this._y0=this._y1=this._y2=this._y3=this._y4=this._y5=NaN,this._l01_a=this._l12_a=this._l23_a=this._l01_2a=this._l12_2a=this._l23_2a=this._point=0},lineEnd:function(){switch(this._point){case 1:this._context.moveTo(this._x3,this._y3),this._context.closePath();break;case 2:this._context.lineTo(this._x3,this._y3),this._context.closePath();break;case 3:this.point(this._x3,this._y3),this.point(this._x4,this._y4),this.point(this._x5,this._y5)}},point:function(t,n){if(t=+t,n=+n,this._point){var i=this._x2-t,e=this._y2-n;this._l23_a=Math.sqrt(this._l23_2a=Math.pow(i*i+e*e,this._alpha))}switch(this._point){case 0:this._point=1,this._x3=t,this._y3=n;break;case 1:this._point=2,this._context.moveTo(this._x4=t,this._y4=n);break;case 2:this._point=3,this._x5=t,this._y5=n;break;default:Yt(this,t,n)}this._l01_a=this._l12_a,this._l12_a=this._l23_a,this._l01_2a=this._l12_2a,this._l12_2a=this._l23_2a,this._x0=this._x1,this._x1=this._x2,this._x2=t,this._y0=this._y1,this._y1=this._y2,this._y2=n}};var It=function t(n){function i(t){return n?new Dt(t,n):new Rt(t,0)}return i.alpha=function(n){return t(+n)},i}(.5);function jt(t,n){this._context=t,this._alpha=n}jt.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._x0=this._x1=this._x2=this._y0=this._y1=this._y2=NaN,this._l01_a=this._l12_a=this._l23_a=this._l01_2a=this._l12_2a=this._l23_2a=this._point=0},lineEnd:function(){(this._line||0!==this._line&&3===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){if(t=+t,n=+n,this._point){var i=this._x2-t,e=this._y2-n;this._l23_a=Math.sqrt(this._l23_2a=Math.pow(i*i+e*e,this._alpha))}switch(this._point){case 0:this._point=1;break;case 1:this._point=2;break;case 2:this._point=3,this._line?this._context.lineTo(this._x2,this._y2):this._context.moveTo(this._x2,this._y2);break;case 3:this._point=4;default:Yt(this,t,n)}this._l01_a=this._l12_a,this._l12_a=this._l23_a,this._l01_2a=this._l12_2a,this._l12_2a=this._l23_2a,this._x0=this._x1,this._x1=this._x2,this._x2=t,this._y0=this._y1,this._y1=this._y2,this._y2=n}};var Lt=function t(n){function i(t){return n?new jt(t,n):new zt(t,0)}return i.alpha=function(n){return t(+n)},i}(.5);function Vt(t){this._context=t}function Wt(t){return t<0?-1:1}function Ft(t,n,i){var e=t._x1-t._x0,s=n-t._x1,o=(t._y1-t._y0)/(e||s<0&&-0),h=(i-t._y1)/(s||e<0&&-0),_=(o*s+h*e)/(e+s);return(Wt(o)+Wt(h))*Math.min(Math.abs(o),Math.abs(h),.5*Math.abs(_))||0}function Ht(t,n){var i=t._x1-t._x0;return i?(3*(t._y1-t._y0)/i-n)/2:n}function $t(t,n,i){var e=t._x0,s=t._y0,o=t._x1,h=t._y1,_=(o-e)/3;t._context.bezierCurveTo(e+_,s+_*n,o-_,h-_*i,o,h)}function Gt(t){this._context=t}function Jt(t){this._context=new Kt(t)}function Kt(t){this._context=t}function Qt(t){this._context=t}function Ut(t){var n,i,e=t.length-1,s=new Array(e),o=new Array(e),h=new Array(e);for(s[0]=0,o[0]=2,h[0]=t[0]+2*t[1],n=1;n=0;--n)s[n]=(h[n]-s[n+1])/o[n];for(o[e-1]=(t[e]+s[e-1])/2,n=0;n1)for(var i,e,s,o=1,h=t[n[0]],_=h.length;o=0;)i[n]=n;return i}function en(t,n){return t[n]}function sn(t){const n=[];return n.key=t,n}function on(t){var n=t.map(hn);return nn(t).sort((function(t,i){return n[t]-n[i]}))}function hn(t){for(var n,i=-1,e=0,s=t.length,o=-1/0;++io&&(o=n,e=i);return e}function _n(t){var n=t.map(rn);return nn(t).sort((function(t,i){return n[t]-n[i]}))}function rn(t){for(var n,i=0,e=-1,s=t.length;++e=0&&(this._t=1-this._t,this._line=1-this._line)},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._line?this._context.lineTo(t,n):this._context.moveTo(t,n);break;case 1:this._point=2;default:if(this._t<=0)this._context.lineTo(this._x,n),this._context.lineTo(t,n);else{var i=this._x*(1-this._t)+t*this._t;this._context.lineTo(i,this._y),this._context.lineTo(i,n)}}this._x=t,this._y=n}},t.arc=function(){var t=v,n=d,h=i(0),k=null,N=T,S=g,E=m,A=null,P=p(M);function M(){var i,p,v=+t.apply(this,arguments),d=+n.apply(this,arguments),T=N.apply(this,arguments)-u,g=S.apply(this,arguments)-u,m=e(g-T),M=g>T;if(A||(A=i=P()),dl)if(m>f-l)A.moveTo(d*o(T),d*r(T)),A.arc(0,0,d,T,g,!M),v>l&&(A.moveTo(v*o(g),v*r(g)),A.arc(0,0,v,g,T,M));else{var C,R,O=T,z=g,X=T,Y=g,q=m,B=m,D=E.apply(this,arguments)/2,I=D>l&&(k?+k.apply(this,arguments):a(v*v+d*d)),j=_(e(d-v)/2,+h.apply(this,arguments)),L=j,V=j;if(I>l){var W=x(I/v*r(D)),F=x(I/d*r(D));(q-=2*W)>l?(X+=W*=M?1:-1,Y-=W):(q=0,X=Y=(T+g)/2),(B-=2*F)>l?(O+=F*=M?1:-1,z-=F):(B=0,O=z=(T+g)/2)}var H=d*o(O),$=d*r(O),G=v*o(Y),J=v*r(Y);if(j>l){var K,Q=d*o(z),U=d*r(z),Z=v*o(X),tt=v*r(X);if(ml?V>l?(C=w(Z,tt,H,$,d,V,M),R=w(Q,U,G,J,d,V,M),A.moveTo(C.cx+C.x01,C.cy+C.y01),Vl&&q>l?L>l?(C=w(G,J,Q,U,v,-L,M),R=w(H,$,Z,tt,v,-L,M),A.lineTo(C.cx+C.x01,C.cy+C.y01),L0&&(y+=c);for(null!=n?x.sort((function(t,i){return n(p[t],p[i])})):null!=e&&x.sort((function(t,n){return e(i[t],i[n])})),_=0,a=y?(d-u*g)/y:0;_0?c*a:0)+g,p[r]={data:i[r],index:_,value:c,startAngle:v,endAngle:l,padAngle:T};return p}return _.value=function(n){return arguments.length?(t="function"==typeof n?n:i(+n),_):t},_.sortValues=function(t){return arguments.length?(n=t,e=null,_):n},_.sort=function(t){return arguments.length?(e=t,n=null,_):e},_.startAngle=function(t){return arguments.length?(s="function"==typeof t?t:i(+t),_):s},_.endAngle=function(t){return arguments.length?(o="function"==typeof t?t:i(+t),_):o},_.padAngle=function(t){return arguments.length?(h="function"==typeof t?t:i(+t),_):h},_},t.pointRadial=I,t.radialArea=D,t.radialLine=B,t.stack=function(){var t=i([]),n=nn,e=tn,s=en;function o(i){var o,h,_=Array.from(t.apply(this,arguments),sn),r=_.length,a=-1;for(const t of i)for(o=0,++a;o0)for(var i,e,s,o,h,_,r=0,a=t[n[0]].length;r0?(e[0]=o,e[1]=o+=s):s<0?(e[1]=h,e[0]=h+=s):(e[0]=0,e[1]=s)},t.stackOffsetExpand=function(t,n){if((e=t.length)>0){for(var i,e,s,o=0,h=t[0].length;o0){for(var i,e=0,s=t[n[0]],o=s.length;e0&&(e=(i=t[n[0]]).length)>0){for(var i,e,s,o=0,h=1;h=12" + } +} diff --git a/frontend/node_modules/d3-shape/src/arc.js b/frontend/node_modules/d3-shape/src/arc.js new file mode 100644 index 0000000..f98e420 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/arc.js @@ -0,0 +1,268 @@ +import constant from "./constant.js"; +import {abs, acos, asin, atan2, cos, epsilon, halfPi, max, min, pi, sin, sqrt, tau} from "./math.js"; +import {withPath} from "./path.js"; + +function arcInnerRadius(d) { + return d.innerRadius; +} + +function arcOuterRadius(d) { + return d.outerRadius; +} + +function arcStartAngle(d) { + return d.startAngle; +} + +function arcEndAngle(d) { + return d.endAngle; +} + +function arcPadAngle(d) { + return d && d.padAngle; // Note: optional! +} + +function intersect(x0, y0, x1, y1, x2, y2, x3, y3) { + var x10 = x1 - x0, y10 = y1 - y0, + x32 = x3 - x2, y32 = y3 - y2, + t = y32 * x10 - x32 * y10; + if (t * t < epsilon) return; + t = (x32 * (y0 - y2) - y32 * (x0 - x2)) / t; + return [x0 + t * x10, y0 + t * y10]; +} + +// Compute perpendicular offset line of length rc. +// http://mathworld.wolfram.com/Circle-LineIntersection.html +function cornerTangents(x0, y0, x1, y1, r1, rc, cw) { + var x01 = x0 - x1, + y01 = y0 - y1, + lo = (cw ? rc : -rc) / sqrt(x01 * x01 + y01 * y01), + ox = lo * y01, + oy = -lo * x01, + x11 = x0 + ox, + y11 = y0 + oy, + x10 = x1 + ox, + y10 = y1 + oy, + x00 = (x11 + x10) / 2, + y00 = (y11 + y10) / 2, + dx = x10 - x11, + dy = y10 - y11, + d2 = dx * dx + dy * dy, + r = r1 - rc, + D = x11 * y10 - x10 * y11, + d = (dy < 0 ? -1 : 1) * sqrt(max(0, r * r * d2 - D * D)), + cx0 = (D * dy - dx * d) / d2, + cy0 = (-D * dx - dy * d) / d2, + cx1 = (D * dy + dx * d) / d2, + cy1 = (-D * dx + dy * d) / d2, + dx0 = cx0 - x00, + dy0 = cy0 - y00, + dx1 = cx1 - x00, + dy1 = cy1 - y00; + + // Pick the closer of the two intersection points. + // TODO Is there a faster way to determine which intersection to use? + if (dx0 * dx0 + dy0 * dy0 > dx1 * dx1 + dy1 * dy1) cx0 = cx1, cy0 = cy1; + + return { + cx: cx0, + cy: cy0, + x01: -ox, + y01: -oy, + x11: cx0 * (r1 / r - 1), + y11: cy0 * (r1 / r - 1) + }; +} + +export default function() { + var innerRadius = arcInnerRadius, + outerRadius = arcOuterRadius, + cornerRadius = constant(0), + padRadius = null, + startAngle = arcStartAngle, + endAngle = arcEndAngle, + padAngle = arcPadAngle, + context = null, + path = withPath(arc); + + function arc() { + var buffer, + r, + r0 = +innerRadius.apply(this, arguments), + r1 = +outerRadius.apply(this, arguments), + a0 = startAngle.apply(this, arguments) - halfPi, + a1 = endAngle.apply(this, arguments) - halfPi, + da = abs(a1 - a0), + cw = a1 > a0; + + if (!context) context = buffer = path(); + + // Ensure that the outer radius is always larger than the inner radius. + if (r1 < r0) r = r1, r1 = r0, r0 = r; + + // Is it a point? + if (!(r1 > epsilon)) context.moveTo(0, 0); + + // Or is it a circle or annulus? + else if (da > tau - epsilon) { + context.moveTo(r1 * cos(a0), r1 * sin(a0)); + context.arc(0, 0, r1, a0, a1, !cw); + if (r0 > epsilon) { + context.moveTo(r0 * cos(a1), r0 * sin(a1)); + context.arc(0, 0, r0, a1, a0, cw); + } + } + + // Or is it a circular or annular sector? + else { + var a01 = a0, + a11 = a1, + a00 = a0, + a10 = a1, + da0 = da, + da1 = da, + ap = padAngle.apply(this, arguments) / 2, + rp = (ap > epsilon) && (padRadius ? +padRadius.apply(this, arguments) : sqrt(r0 * r0 + r1 * r1)), + rc = min(abs(r1 - r0) / 2, +cornerRadius.apply(this, arguments)), + rc0 = rc, + rc1 = rc, + t0, + t1; + + // Apply padding? Note that since r1 ≥ r0, da1 ≥ da0. + if (rp > epsilon) { + var p0 = asin(rp / r0 * sin(ap)), + p1 = asin(rp / r1 * sin(ap)); + if ((da0 -= p0 * 2) > epsilon) p0 *= (cw ? 1 : -1), a00 += p0, a10 -= p0; + else da0 = 0, a00 = a10 = (a0 + a1) / 2; + if ((da1 -= p1 * 2) > epsilon) p1 *= (cw ? 1 : -1), a01 += p1, a11 -= p1; + else da1 = 0, a01 = a11 = (a0 + a1) / 2; + } + + var x01 = r1 * cos(a01), + y01 = r1 * sin(a01), + x10 = r0 * cos(a10), + y10 = r0 * sin(a10); + + // Apply rounded corners? + if (rc > epsilon) { + var x11 = r1 * cos(a11), + y11 = r1 * sin(a11), + x00 = r0 * cos(a00), + y00 = r0 * sin(a00), + oc; + + // Restrict the corner radius according to the sector angle. If this + // intersection fails, it’s probably because the arc is too small, so + // disable the corner radius entirely. + if (da < pi) { + if (oc = intersect(x01, y01, x00, y00, x11, y11, x10, y10)) { + var ax = x01 - oc[0], + ay = y01 - oc[1], + bx = x11 - oc[0], + by = y11 - oc[1], + kc = 1 / sin(acos((ax * bx + ay * by) / (sqrt(ax * ax + ay * ay) * sqrt(bx * bx + by * by))) / 2), + lc = sqrt(oc[0] * oc[0] + oc[1] * oc[1]); + rc0 = min(rc, (r0 - lc) / (kc - 1)); + rc1 = min(rc, (r1 - lc) / (kc + 1)); + } else { + rc0 = rc1 = 0; + } + } + } + + // Is the sector collapsed to a line? + if (!(da1 > epsilon)) context.moveTo(x01, y01); + + // Does the sector’s outer ring have rounded corners? + else if (rc1 > epsilon) { + t0 = cornerTangents(x00, y00, x01, y01, r1, rc1, cw); + t1 = cornerTangents(x11, y11, x10, y10, r1, rc1, cw); + + context.moveTo(t0.cx + t0.x01, t0.cy + t0.y01); + + // Have the corners merged? + if (rc1 < rc) context.arc(t0.cx, t0.cy, rc1, atan2(t0.y01, t0.x01), atan2(t1.y01, t1.x01), !cw); + + // Otherwise, draw the two corners and the ring. + else { + context.arc(t0.cx, t0.cy, rc1, atan2(t0.y01, t0.x01), atan2(t0.y11, t0.x11), !cw); + context.arc(0, 0, r1, atan2(t0.cy + t0.y11, t0.cx + t0.x11), atan2(t1.cy + t1.y11, t1.cx + t1.x11), !cw); + context.arc(t1.cx, t1.cy, rc1, atan2(t1.y11, t1.x11), atan2(t1.y01, t1.x01), !cw); + } + } + + // Or is the outer ring just a circular arc? + else context.moveTo(x01, y01), context.arc(0, 0, r1, a01, a11, !cw); + + // Is there no inner ring, and it’s a circular sector? + // Or perhaps it’s an annular sector collapsed due to padding? + if (!(r0 > epsilon) || !(da0 > epsilon)) context.lineTo(x10, y10); + + // Does the sector’s inner ring (or point) have rounded corners? + else if (rc0 > epsilon) { + t0 = cornerTangents(x10, y10, x11, y11, r0, -rc0, cw); + t1 = cornerTangents(x01, y01, x00, y00, r0, -rc0, cw); + + context.lineTo(t0.cx + t0.x01, t0.cy + t0.y01); + + // Have the corners merged? + if (rc0 < rc) context.arc(t0.cx, t0.cy, rc0, atan2(t0.y01, t0.x01), atan2(t1.y01, t1.x01), !cw); + + // Otherwise, draw the two corners and the ring. + else { + context.arc(t0.cx, t0.cy, rc0, atan2(t0.y01, t0.x01), atan2(t0.y11, t0.x11), !cw); + context.arc(0, 0, r0, atan2(t0.cy + t0.y11, t0.cx + t0.x11), atan2(t1.cy + t1.y11, t1.cx + t1.x11), cw); + context.arc(t1.cx, t1.cy, rc0, atan2(t1.y11, t1.x11), atan2(t1.y01, t1.x01), !cw); + } + } + + // Or is the inner ring just a circular arc? + else context.arc(0, 0, r0, a10, a00, cw); + } + + context.closePath(); + + if (buffer) return context = null, buffer + "" || null; + } + + arc.centroid = function() { + var r = (+innerRadius.apply(this, arguments) + +outerRadius.apply(this, arguments)) / 2, + a = (+startAngle.apply(this, arguments) + +endAngle.apply(this, arguments)) / 2 - pi / 2; + return [cos(a) * r, sin(a) * r]; + }; + + arc.innerRadius = function(_) { + return arguments.length ? (innerRadius = typeof _ === "function" ? _ : constant(+_), arc) : innerRadius; + }; + + arc.outerRadius = function(_) { + return arguments.length ? (outerRadius = typeof _ === "function" ? _ : constant(+_), arc) : outerRadius; + }; + + arc.cornerRadius = function(_) { + return arguments.length ? (cornerRadius = typeof _ === "function" ? _ : constant(+_), arc) : cornerRadius; + }; + + arc.padRadius = function(_) { + return arguments.length ? (padRadius = _ == null ? null : typeof _ === "function" ? _ : constant(+_), arc) : padRadius; + }; + + arc.startAngle = function(_) { + return arguments.length ? (startAngle = typeof _ === "function" ? _ : constant(+_), arc) : startAngle; + }; + + arc.endAngle = function(_) { + return arguments.length ? (endAngle = typeof _ === "function" ? _ : constant(+_), arc) : endAngle; + }; + + arc.padAngle = function(_) { + return arguments.length ? (padAngle = typeof _ === "function" ? _ : constant(+_), arc) : padAngle; + }; + + arc.context = function(_) { + return arguments.length ? ((context = _ == null ? null : _), arc) : context; + }; + + return arc; +} diff --git a/frontend/node_modules/d3-shape/src/area.js b/frontend/node_modules/d3-shape/src/area.js new file mode 100644 index 0000000..7129f14 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/area.js @@ -0,0 +1,112 @@ +import array from "./array.js"; +import constant from "./constant.js"; +import curveLinear from "./curve/linear.js"; +import line from "./line.js"; +import {withPath} from "./path.js"; +import {x as pointX, y as pointY} from "./point.js"; + +export default function(x0, y0, y1) { + var x1 = null, + defined = constant(true), + context = null, + curve = curveLinear, + output = null, + path = withPath(area); + + x0 = typeof x0 === "function" ? x0 : (x0 === undefined) ? pointX : constant(+x0); + y0 = typeof y0 === "function" ? y0 : (y0 === undefined) ? constant(0) : constant(+y0); + y1 = typeof y1 === "function" ? y1 : (y1 === undefined) ? pointY : constant(+y1); + + function area(data) { + var i, + j, + k, + n = (data = array(data)).length, + d, + defined0 = false, + buffer, + x0z = new Array(n), + y0z = new Array(n); + + if (context == null) output = curve(buffer = path()); + + for (i = 0; i <= n; ++i) { + if (!(i < n && defined(d = data[i], i, data)) === defined0) { + if (defined0 = !defined0) { + j = i; + output.areaStart(); + output.lineStart(); + } else { + output.lineEnd(); + output.lineStart(); + for (k = i - 1; k >= j; --k) { + output.point(x0z[k], y0z[k]); + } + output.lineEnd(); + output.areaEnd(); + } + } + if (defined0) { + x0z[i] = +x0(d, i, data), y0z[i] = +y0(d, i, data); + output.point(x1 ? +x1(d, i, data) : x0z[i], y1 ? +y1(d, i, data) : y0z[i]); + } + } + + if (buffer) return output = null, buffer + "" || null; + } + + function arealine() { + return line().defined(defined).curve(curve).context(context); + } + + area.x = function(_) { + return arguments.length ? (x0 = typeof _ === "function" ? _ : constant(+_), x1 = null, area) : x0; + }; + + area.x0 = function(_) { + return arguments.length ? (x0 = typeof _ === "function" ? _ : constant(+_), area) : x0; + }; + + area.x1 = function(_) { + return arguments.length ? (x1 = _ == null ? null : typeof _ === "function" ? _ : constant(+_), area) : x1; + }; + + area.y = function(_) { + return arguments.length ? (y0 = typeof _ === "function" ? _ : constant(+_), y1 = null, area) : y0; + }; + + area.y0 = function(_) { + return arguments.length ? (y0 = typeof _ === "function" ? _ : constant(+_), area) : y0; + }; + + area.y1 = function(_) { + return arguments.length ? (y1 = _ == null ? null : typeof _ === "function" ? _ : constant(+_), area) : y1; + }; + + area.lineX0 = + area.lineY0 = function() { + return arealine().x(x0).y(y0); + }; + + area.lineY1 = function() { + return arealine().x(x0).y(y1); + }; + + area.lineX1 = function() { + return arealine().x(x1).y(y0); + }; + + area.defined = function(_) { + return arguments.length ? (defined = typeof _ === "function" ? _ : constant(!!_), area) : defined; + }; + + area.curve = function(_) { + return arguments.length ? (curve = _, context != null && (output = curve(context)), area) : curve; + }; + + area.context = function(_) { + return arguments.length ? (_ == null ? context = output = null : output = curve(context = _), area) : context; + }; + + return area; +} diff --git a/frontend/node_modules/d3-shape/src/areaRadial.js b/frontend/node_modules/d3-shape/src/areaRadial.js new file mode 100644 index 0000000..61e01d7 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/areaRadial.js @@ -0,0 +1,29 @@ +import curveRadial, {curveRadialLinear} from "./curve/radial.js"; +import area from "./area.js"; +import {lineRadial} from "./lineRadial.js"; + +export default function() { + var a = area().curve(curveRadialLinear), + c = a.curve, + x0 = a.lineX0, + x1 = a.lineX1, + y0 = a.lineY0, + y1 = a.lineY1; + + a.angle = a.x, delete a.x; + a.startAngle = a.x0, delete a.x0; + a.endAngle = a.x1, delete a.x1; + a.radius = a.y, delete a.y; + a.innerRadius = a.y0, delete a.y0; + a.outerRadius = a.y1, delete a.y1; + a.lineStartAngle = function() { return lineRadial(x0()); }, delete a.lineX0; + a.lineEndAngle = function() { return lineRadial(x1()); }, delete a.lineX1; + a.lineInnerRadius = function() { return lineRadial(y0()); }, delete a.lineY0; + a.lineOuterRadius = function() { return lineRadial(y1()); }, delete a.lineY1; + + a.curve = function(_) { + return arguments.length ? c(curveRadial(_)) : c()._curve; + }; + + return a; +} diff --git a/frontend/node_modules/d3-shape/src/array.js b/frontend/node_modules/d3-shape/src/array.js new file mode 100644 index 0000000..90808ff --- /dev/null +++ b/frontend/node_modules/d3-shape/src/array.js @@ -0,0 +1,7 @@ +export var slice = Array.prototype.slice; + +export default function(x) { + return typeof x === "object" && "length" in x + ? x // Array, TypedArray, NodeList, array-like + : Array.from(x); // Map, Set, iterable, string, or anything else +} diff --git a/frontend/node_modules/d3-shape/src/constant.js b/frontend/node_modules/d3-shape/src/constant.js new file mode 100644 index 0000000..6fa95b7 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/constant.js @@ -0,0 +1,5 @@ +export default function(x) { + return function constant() { + return x; + }; +} diff --git a/frontend/node_modules/d3-shape/src/curve/basis.js b/frontend/node_modules/d3-shape/src/curve/basis.js new file mode 100644 index 0000000..e6b1ea3 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/basis.js @@ -0,0 +1,51 @@ +export function point(that, x, y) { + that._context.bezierCurveTo( + (2 * that._x0 + that._x1) / 3, + (2 * that._y0 + that._y1) / 3, + (that._x0 + 2 * that._x1) / 3, + (that._y0 + 2 * that._y1) / 3, + (that._x0 + 4 * that._x1 + x) / 6, + (that._y0 + 4 * that._y1 + y) / 6 + ); +} + +export function Basis(context) { + this._context = context; +} + +Basis.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = + this._y0 = this._y1 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 3: point(this, this._x1, this._y1); // falls through + case 2: this._context.lineTo(this._x1, this._y1); break; + } + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; break; + case 2: this._point = 3; this._context.lineTo((5 * this._x0 + this._x1) / 6, (5 * this._y0 + this._y1) / 6); // falls through + default: point(this, x, y); break; + } + this._x0 = this._x1, this._x1 = x; + this._y0 = this._y1, this._y1 = y; + } +}; + +export default function(context) { + return new Basis(context); +} diff --git a/frontend/node_modules/d3-shape/src/curve/basisClosed.js b/frontend/node_modules/d3-shape/src/curve/basisClosed.js new file mode 100644 index 0000000..535df90 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/basisClosed.js @@ -0,0 +1,52 @@ +import noop from "../noop.js"; +import {point} from "./basis.js"; + +function BasisClosed(context) { + this._context = context; +} + +BasisClosed.prototype = { + areaStart: noop, + areaEnd: noop, + lineStart: function() { + this._x0 = this._x1 = this._x2 = this._x3 = this._x4 = + this._y0 = this._y1 = this._y2 = this._y3 = this._y4 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 1: { + this._context.moveTo(this._x2, this._y2); + this._context.closePath(); + break; + } + case 2: { + this._context.moveTo((this._x2 + 2 * this._x3) / 3, (this._y2 + 2 * this._y3) / 3); + this._context.lineTo((this._x3 + 2 * this._x2) / 3, (this._y3 + 2 * this._y2) / 3); + this._context.closePath(); + break; + } + case 3: { + this.point(this._x2, this._y2); + this.point(this._x3, this._y3); + this.point(this._x4, this._y4); + break; + } + } + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._x2 = x, this._y2 = y; break; + case 1: this._point = 2; this._x3 = x, this._y3 = y; break; + case 2: this._point = 3; this._x4 = x, this._y4 = y; this._context.moveTo((this._x0 + 4 * this._x1 + x) / 6, (this._y0 + 4 * this._y1 + y) / 6); break; + default: point(this, x, y); break; + } + this._x0 = this._x1, this._x1 = x; + this._y0 = this._y1, this._y1 = y; + } +}; + +export default function(context) { + return new BasisClosed(context); +} diff --git a/frontend/node_modules/d3-shape/src/curve/basisOpen.js b/frontend/node_modules/d3-shape/src/curve/basisOpen.js new file mode 100644 index 0000000..4ef5343 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/basisOpen.js @@ -0,0 +1,39 @@ +import {point} from "./basis.js"; + +function BasisOpen(context) { + this._context = context; +} + +BasisOpen.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = + this._y0 = this._y1 = NaN; + this._point = 0; + }, + lineEnd: function() { + if (this._line || (this._line !== 0 && this._point === 3)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; break; + case 1: this._point = 2; break; + case 2: this._point = 3; var x0 = (this._x0 + 4 * this._x1 + x) / 6, y0 = (this._y0 + 4 * this._y1 + y) / 6; this._line ? this._context.lineTo(x0, y0) : this._context.moveTo(x0, y0); break; + case 3: this._point = 4; // falls through + default: point(this, x, y); break; + } + this._x0 = this._x1, this._x1 = x; + this._y0 = this._y1, this._y1 = y; + } +}; + +export default function(context) { + return new BasisOpen(context); +} diff --git a/frontend/node_modules/d3-shape/src/curve/bump.js b/frontend/node_modules/d3-shape/src/curve/bump.js new file mode 100644 index 0000000..9b960cf --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/bump.js @@ -0,0 +1,75 @@ +import pointRadial from "../pointRadial.js"; + +class Bump { + constructor(context, x) { + this._context = context; + this._x = x; + } + areaStart() { + this._line = 0; + } + areaEnd() { + this._line = NaN; + } + lineStart() { + this._point = 0; + } + lineEnd() { + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + } + point(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: { + this._point = 1; + if (this._line) this._context.lineTo(x, y); + else this._context.moveTo(x, y); + break; + } + case 1: this._point = 2; // falls through + default: { + if (this._x) this._context.bezierCurveTo(this._x0 = (this._x0 + x) / 2, this._y0, this._x0, y, x, y); + else this._context.bezierCurveTo(this._x0, this._y0 = (this._y0 + y) / 2, x, this._y0, x, y); + break; + } + } + this._x0 = x, this._y0 = y; + } +} + +class BumpRadial { + constructor(context) { + this._context = context; + } + lineStart() { + this._point = 0; + } + lineEnd() {} + point(x, y) { + x = +x, y = +y; + if (this._point === 0) { + this._point = 1; + } else { + const p0 = pointRadial(this._x0, this._y0); + const p1 = pointRadial(this._x0, this._y0 = (this._y0 + y) / 2); + const p2 = pointRadial(x, this._y0); + const p3 = pointRadial(x, y); + this._context.moveTo(...p0); + this._context.bezierCurveTo(...p1, ...p2, ...p3); + } + this._x0 = x, this._y0 = y; + } +} + +export function bumpX(context) { + return new Bump(context, true); +} + +export function bumpY(context) { + return new Bump(context, false); +} + +export function bumpRadial(context) { + return new BumpRadial(context); +} diff --git a/frontend/node_modules/d3-shape/src/curve/bundle.js b/frontend/node_modules/d3-shape/src/curve/bundle.js new file mode 100644 index 0000000..ac1014e --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/bundle.js @@ -0,0 +1,56 @@ +import {Basis} from "./basis.js"; + +function Bundle(context, beta) { + this._basis = new Basis(context); + this._beta = beta; +} + +Bundle.prototype = { + lineStart: function() { + this._x = []; + this._y = []; + this._basis.lineStart(); + }, + lineEnd: function() { + var x = this._x, + y = this._y, + j = x.length - 1; + + if (j > 0) { + var x0 = x[0], + y0 = y[0], + dx = x[j] - x0, + dy = y[j] - y0, + i = -1, + t; + + while (++i <= j) { + t = i / j; + this._basis.point( + this._beta * x[i] + (1 - this._beta) * (x0 + t * dx), + this._beta * y[i] + (1 - this._beta) * (y0 + t * dy) + ); + } + } + + this._x = this._y = null; + this._basis.lineEnd(); + }, + point: function(x, y) { + this._x.push(+x); + this._y.push(+y); + } +}; + +export default (function custom(beta) { + + function bundle(context) { + return beta === 1 ? new Basis(context) : new Bundle(context, beta); + } + + bundle.beta = function(beta) { + return custom(+beta); + }; + + return bundle; +})(0.85); diff --git a/frontend/node_modules/d3-shape/src/curve/cardinal.js b/frontend/node_modules/d3-shape/src/curve/cardinal.js new file mode 100644 index 0000000..7e64c14 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/cardinal.js @@ -0,0 +1,61 @@ +export function point(that, x, y) { + that._context.bezierCurveTo( + that._x1 + that._k * (that._x2 - that._x0), + that._y1 + that._k * (that._y2 - that._y0), + that._x2 + that._k * (that._x1 - x), + that._y2 + that._k * (that._y1 - y), + that._x2, + that._y2 + ); +} + +export function Cardinal(context, tension) { + this._context = context; + this._k = (1 - tension) / 6; +} + +Cardinal.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = this._x2 = + this._y0 = this._y1 = this._y2 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 2: this._context.lineTo(this._x2, this._y2); break; + case 3: point(this, this._x1, this._y1); break; + } + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; this._x1 = x, this._y1 = y; break; + case 2: this._point = 3; // falls through + default: point(this, x, y); break; + } + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +export default (function custom(tension) { + + function cardinal(context) { + return new Cardinal(context, tension); + } + + cardinal.tension = function(tension) { + return custom(+tension); + }; + + return cardinal; +})(0); diff --git a/frontend/node_modules/d3-shape/src/curve/cardinalClosed.js b/frontend/node_modules/d3-shape/src/curve/cardinalClosed.js new file mode 100644 index 0000000..acef52e --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/cardinalClosed.js @@ -0,0 +1,61 @@ +import noop from "../noop.js"; +import {point} from "./cardinal.js"; + +export function CardinalClosed(context, tension) { + this._context = context; + this._k = (1 - tension) / 6; +} + +CardinalClosed.prototype = { + areaStart: noop, + areaEnd: noop, + lineStart: function() { + this._x0 = this._x1 = this._x2 = this._x3 = this._x4 = this._x5 = + this._y0 = this._y1 = this._y2 = this._y3 = this._y4 = this._y5 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 1: { + this._context.moveTo(this._x3, this._y3); + this._context.closePath(); + break; + } + case 2: { + this._context.lineTo(this._x3, this._y3); + this._context.closePath(); + break; + } + case 3: { + this.point(this._x3, this._y3); + this.point(this._x4, this._y4); + this.point(this._x5, this._y5); + break; + } + } + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._x3 = x, this._y3 = y; break; + case 1: this._point = 2; this._context.moveTo(this._x4 = x, this._y4 = y); break; + case 2: this._point = 3; this._x5 = x, this._y5 = y; break; + default: point(this, x, y); break; + } + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +export default (function custom(tension) { + + function cardinal(context) { + return new CardinalClosed(context, tension); + } + + cardinal.tension = function(tension) { + return custom(+tension); + }; + + return cardinal; +})(0); diff --git a/frontend/node_modules/d3-shape/src/curve/cardinalOpen.js b/frontend/node_modules/d3-shape/src/curve/cardinalOpen.js new file mode 100644 index 0000000..f73ac8b --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/cardinalOpen.js @@ -0,0 +1,49 @@ +import {point} from "./cardinal.js"; + +export function CardinalOpen(context, tension) { + this._context = context; + this._k = (1 - tension) / 6; +} + +CardinalOpen.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = this._x2 = + this._y0 = this._y1 = this._y2 = NaN; + this._point = 0; + }, + lineEnd: function() { + if (this._line || (this._line !== 0 && this._point === 3)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; break; + case 1: this._point = 2; break; + case 2: this._point = 3; this._line ? this._context.lineTo(this._x2, this._y2) : this._context.moveTo(this._x2, this._y2); break; + case 3: this._point = 4; // falls through + default: point(this, x, y); break; + } + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +export default (function custom(tension) { + + function cardinal(context) { + return new CardinalOpen(context, tension); + } + + cardinal.tension = function(tension) { + return custom(+tension); + }; + + return cardinal; +})(0); diff --git a/frontend/node_modules/d3-shape/src/curve/catmullRom.js b/frontend/node_modules/d3-shape/src/curve/catmullRom.js new file mode 100644 index 0000000..3a4b1a7 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/catmullRom.js @@ -0,0 +1,88 @@ +import {epsilon} from "../math.js"; +import {Cardinal} from "./cardinal.js"; + +export function point(that, x, y) { + var x1 = that._x1, + y1 = that._y1, + x2 = that._x2, + y2 = that._y2; + + if (that._l01_a > epsilon) { + var a = 2 * that._l01_2a + 3 * that._l01_a * that._l12_a + that._l12_2a, + n = 3 * that._l01_a * (that._l01_a + that._l12_a); + x1 = (x1 * a - that._x0 * that._l12_2a + that._x2 * that._l01_2a) / n; + y1 = (y1 * a - that._y0 * that._l12_2a + that._y2 * that._l01_2a) / n; + } + + if (that._l23_a > epsilon) { + var b = 2 * that._l23_2a + 3 * that._l23_a * that._l12_a + that._l12_2a, + m = 3 * that._l23_a * (that._l23_a + that._l12_a); + x2 = (x2 * b + that._x1 * that._l23_2a - x * that._l12_2a) / m; + y2 = (y2 * b + that._y1 * that._l23_2a - y * that._l12_2a) / m; + } + + that._context.bezierCurveTo(x1, y1, x2, y2, that._x2, that._y2); +} + +function CatmullRom(context, alpha) { + this._context = context; + this._alpha = alpha; +} + +CatmullRom.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = this._x2 = + this._y0 = this._y1 = this._y2 = NaN; + this._l01_a = this._l12_a = this._l23_a = + this._l01_2a = this._l12_2a = this._l23_2a = + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 2: this._context.lineTo(this._x2, this._y2); break; + case 3: this.point(this._x2, this._y2); break; + } + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + + if (this._point) { + var x23 = this._x2 - x, + y23 = this._y2 - y; + this._l23_a = Math.sqrt(this._l23_2a = Math.pow(x23 * x23 + y23 * y23, this._alpha)); + } + + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; break; + case 2: this._point = 3; // falls through + default: point(this, x, y); break; + } + + this._l01_a = this._l12_a, this._l12_a = this._l23_a; + this._l01_2a = this._l12_2a, this._l12_2a = this._l23_2a; + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +export default (function custom(alpha) { + + function catmullRom(context) { + return alpha ? new CatmullRom(context, alpha) : new Cardinal(context, 0); + } + + catmullRom.alpha = function(alpha) { + return custom(+alpha); + }; + + return catmullRom; +})(0.5); diff --git a/frontend/node_modules/d3-shape/src/curve/catmullRomClosed.js b/frontend/node_modules/d3-shape/src/curve/catmullRomClosed.js new file mode 100644 index 0000000..6c6b965 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/catmullRomClosed.js @@ -0,0 +1,74 @@ +import {CardinalClosed} from "./cardinalClosed.js"; +import noop from "../noop.js"; +import {point} from "./catmullRom.js"; + +function CatmullRomClosed(context, alpha) { + this._context = context; + this._alpha = alpha; +} + +CatmullRomClosed.prototype = { + areaStart: noop, + areaEnd: noop, + lineStart: function() { + this._x0 = this._x1 = this._x2 = this._x3 = this._x4 = this._x5 = + this._y0 = this._y1 = this._y2 = this._y3 = this._y4 = this._y5 = NaN; + this._l01_a = this._l12_a = this._l23_a = + this._l01_2a = this._l12_2a = this._l23_2a = + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 1: { + this._context.moveTo(this._x3, this._y3); + this._context.closePath(); + break; + } + case 2: { + this._context.lineTo(this._x3, this._y3); + this._context.closePath(); + break; + } + case 3: { + this.point(this._x3, this._y3); + this.point(this._x4, this._y4); + this.point(this._x5, this._y5); + break; + } + } + }, + point: function(x, y) { + x = +x, y = +y; + + if (this._point) { + var x23 = this._x2 - x, + y23 = this._y2 - y; + this._l23_a = Math.sqrt(this._l23_2a = Math.pow(x23 * x23 + y23 * y23, this._alpha)); + } + + switch (this._point) { + case 0: this._point = 1; this._x3 = x, this._y3 = y; break; + case 1: this._point = 2; this._context.moveTo(this._x4 = x, this._y4 = y); break; + case 2: this._point = 3; this._x5 = x, this._y5 = y; break; + default: point(this, x, y); break; + } + + this._l01_a = this._l12_a, this._l12_a = this._l23_a; + this._l01_2a = this._l12_2a, this._l12_2a = this._l23_2a; + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +export default (function custom(alpha) { + + function catmullRom(context) { + return alpha ? new CatmullRomClosed(context, alpha) : new CardinalClosed(context, 0); + } + + catmullRom.alpha = function(alpha) { + return custom(+alpha); + }; + + return catmullRom; +})(0.5); diff --git a/frontend/node_modules/d3-shape/src/curve/catmullRomOpen.js b/frontend/node_modules/d3-shape/src/curve/catmullRomOpen.js new file mode 100644 index 0000000..a372a70 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/catmullRomOpen.js @@ -0,0 +1,62 @@ +import {CardinalOpen} from "./cardinalOpen.js"; +import {point} from "./catmullRom.js"; + +function CatmullRomOpen(context, alpha) { + this._context = context; + this._alpha = alpha; +} + +CatmullRomOpen.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = this._x2 = + this._y0 = this._y1 = this._y2 = NaN; + this._l01_a = this._l12_a = this._l23_a = + this._l01_2a = this._l12_2a = this._l23_2a = + this._point = 0; + }, + lineEnd: function() { + if (this._line || (this._line !== 0 && this._point === 3)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + + if (this._point) { + var x23 = this._x2 - x, + y23 = this._y2 - y; + this._l23_a = Math.sqrt(this._l23_2a = Math.pow(x23 * x23 + y23 * y23, this._alpha)); + } + + switch (this._point) { + case 0: this._point = 1; break; + case 1: this._point = 2; break; + case 2: this._point = 3; this._line ? this._context.lineTo(this._x2, this._y2) : this._context.moveTo(this._x2, this._y2); break; + case 3: this._point = 4; // falls through + default: point(this, x, y); break; + } + + this._l01_a = this._l12_a, this._l12_a = this._l23_a; + this._l01_2a = this._l12_2a, this._l12_2a = this._l23_2a; + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +export default (function custom(alpha) { + + function catmullRom(context) { + return alpha ? new CatmullRomOpen(context, alpha) : new CardinalOpen(context, 0); + } + + catmullRom.alpha = function(alpha) { + return custom(+alpha); + }; + + return catmullRom; +})(0.5); diff --git a/frontend/node_modules/d3-shape/src/curve/linear.js b/frontend/node_modules/d3-shape/src/curve/linear.js new file mode 100644 index 0000000..68e169a --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/linear.js @@ -0,0 +1,31 @@ +function Linear(context) { + this._context = context; +} + +Linear.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._point = 0; + }, + lineEnd: function() { + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; // falls through + default: this._context.lineTo(x, y); break; + } + } +}; + +export default function(context) { + return new Linear(context); +} diff --git a/frontend/node_modules/d3-shape/src/curve/linearClosed.js b/frontend/node_modules/d3-shape/src/curve/linearClosed.js new file mode 100644 index 0000000..e25606f --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/linearClosed.js @@ -0,0 +1,25 @@ +import noop from "../noop.js"; + +function LinearClosed(context) { + this._context = context; +} + +LinearClosed.prototype = { + areaStart: noop, + areaEnd: noop, + lineStart: function() { + this._point = 0; + }, + lineEnd: function() { + if (this._point) this._context.closePath(); + }, + point: function(x, y) { + x = +x, y = +y; + if (this._point) this._context.lineTo(x, y); + else this._point = 1, this._context.moveTo(x, y); + } +}; + +export default function(context) { + return new LinearClosed(context); +} diff --git a/frontend/node_modules/d3-shape/src/curve/monotone.js b/frontend/node_modules/d3-shape/src/curve/monotone.js new file mode 100644 index 0000000..2599031 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/monotone.js @@ -0,0 +1,104 @@ +function sign(x) { + return x < 0 ? -1 : 1; +} + +// Calculate the slopes of the tangents (Hermite-type interpolation) based on +// the following paper: Steffen, M. 1990. A Simple Method for Monotonic +// Interpolation in One Dimension. Astronomy and Astrophysics, Vol. 239, NO. +// NOV(II), P. 443, 1990. +function slope3(that, x2, y2) { + var h0 = that._x1 - that._x0, + h1 = x2 - that._x1, + s0 = (that._y1 - that._y0) / (h0 || h1 < 0 && -0), + s1 = (y2 - that._y1) / (h1 || h0 < 0 && -0), + p = (s0 * h1 + s1 * h0) / (h0 + h1); + return (sign(s0) + sign(s1)) * Math.min(Math.abs(s0), Math.abs(s1), 0.5 * Math.abs(p)) || 0; +} + +// Calculate a one-sided slope. +function slope2(that, t) { + var h = that._x1 - that._x0; + return h ? (3 * (that._y1 - that._y0) / h - t) / 2 : t; +} + +// According to https://en.wikipedia.org/wiki/Cubic_Hermite_spline#Representations +// "you can express cubic Hermite interpolation in terms of cubic Bézier curves +// with respect to the four values p0, p0 + m0 / 3, p1 - m1 / 3, p1". +function point(that, t0, t1) { + var x0 = that._x0, + y0 = that._y0, + x1 = that._x1, + y1 = that._y1, + dx = (x1 - x0) / 3; + that._context.bezierCurveTo(x0 + dx, y0 + dx * t0, x1 - dx, y1 - dx * t1, x1, y1); +} + +function MonotoneX(context) { + this._context = context; +} + +MonotoneX.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = + this._y0 = this._y1 = + this._t0 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 2: this._context.lineTo(this._x1, this._y1); break; + case 3: point(this, this._t0, slope2(this, this._t0)); break; + } + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + var t1 = NaN; + + x = +x, y = +y; + if (x === this._x1 && y === this._y1) return; // Ignore coincident points. + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; break; + case 2: this._point = 3; point(this, slope2(this, t1 = slope3(this, x, y)), t1); break; + default: point(this, this._t0, t1 = slope3(this, x, y)); break; + } + + this._x0 = this._x1, this._x1 = x; + this._y0 = this._y1, this._y1 = y; + this._t0 = t1; + } +} + +function MonotoneY(context) { + this._context = new ReflectContext(context); +} + +(MonotoneY.prototype = Object.create(MonotoneX.prototype)).point = function(x, y) { + MonotoneX.prototype.point.call(this, y, x); +}; + +function ReflectContext(context) { + this._context = context; +} + +ReflectContext.prototype = { + moveTo: function(x, y) { this._context.moveTo(y, x); }, + closePath: function() { this._context.closePath(); }, + lineTo: function(x, y) { this._context.lineTo(y, x); }, + bezierCurveTo: function(x1, y1, x2, y2, x, y) { this._context.bezierCurveTo(y1, x1, y2, x2, y, x); } +}; + +export function monotoneX(context) { + return new MonotoneX(context); +} + +export function monotoneY(context) { + return new MonotoneY(context); +} diff --git a/frontend/node_modules/d3-shape/src/curve/natural.js b/frontend/node_modules/d3-shape/src/curve/natural.js new file mode 100644 index 0000000..d51eb51 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/natural.js @@ -0,0 +1,65 @@ +function Natural(context) { + this._context = context; +} + +Natural.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x = []; + this._y = []; + }, + lineEnd: function() { + var x = this._x, + y = this._y, + n = x.length; + + if (n) { + this._line ? this._context.lineTo(x[0], y[0]) : this._context.moveTo(x[0], y[0]); + if (n === 2) { + this._context.lineTo(x[1], y[1]); + } else { + var px = controlPoints(x), + py = controlPoints(y); + for (var i0 = 0, i1 = 1; i1 < n; ++i0, ++i1) { + this._context.bezierCurveTo(px[0][i0], py[0][i0], px[1][i0], py[1][i0], x[i1], y[i1]); + } + } + } + + if (this._line || (this._line !== 0 && n === 1)) this._context.closePath(); + this._line = 1 - this._line; + this._x = this._y = null; + }, + point: function(x, y) { + this._x.push(+x); + this._y.push(+y); + } +}; + +// See https://www.particleincell.com/2012/bezier-splines/ for derivation. +function controlPoints(x) { + var i, + n = x.length - 1, + m, + a = new Array(n), + b = new Array(n), + r = new Array(n); + a[0] = 0, b[0] = 2, r[0] = x[0] + 2 * x[1]; + for (i = 1; i < n - 1; ++i) a[i] = 1, b[i] = 4, r[i] = 4 * x[i] + 2 * x[i + 1]; + a[n - 1] = 2, b[n - 1] = 7, r[n - 1] = 8 * x[n - 1] + x[n]; + for (i = 1; i < n; ++i) m = a[i] / b[i - 1], b[i] -= m, r[i] -= m * r[i - 1]; + a[n - 1] = r[n - 1] / b[n - 1]; + for (i = n - 2; i >= 0; --i) a[i] = (r[i] - a[i + 1]) / b[i]; + b[n - 1] = (x[n] + a[n - 1]) / 2; + for (i = 0; i < n - 1; ++i) b[i] = 2 * x[i + 1] - a[i + 1]; + return [a, b]; +} + +export default function(context) { + return new Natural(context); +} diff --git a/frontend/node_modules/d3-shape/src/curve/radial.js b/frontend/node_modules/d3-shape/src/curve/radial.js new file mode 100644 index 0000000..730c989 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/radial.js @@ -0,0 +1,36 @@ +import curveLinear from "./linear.js"; + +export var curveRadialLinear = curveRadial(curveLinear); + +function Radial(curve) { + this._curve = curve; +} + +Radial.prototype = { + areaStart: function() { + this._curve.areaStart(); + }, + areaEnd: function() { + this._curve.areaEnd(); + }, + lineStart: function() { + this._curve.lineStart(); + }, + lineEnd: function() { + this._curve.lineEnd(); + }, + point: function(a, r) { + this._curve.point(r * Math.sin(a), r * -Math.cos(a)); + } +}; + +export default function curveRadial(curve) { + + function radial(context) { + return new Radial(curve(context)); + } + + radial._curve = curve; + + return radial; +} diff --git a/frontend/node_modules/d3-shape/src/curve/step.js b/frontend/node_modules/d3-shape/src/curve/step.js new file mode 100644 index 0000000..6f6aa05 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/curve/step.js @@ -0,0 +1,53 @@ +function Step(context, t) { + this._context = context; + this._t = t; +} + +Step.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x = this._y = NaN; + this._point = 0; + }, + lineEnd: function() { + if (0 < this._t && this._t < 1 && this._point === 2) this._context.lineTo(this._x, this._y); + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + if (this._line >= 0) this._t = 1 - this._t, this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; // falls through + default: { + if (this._t <= 0) { + this._context.lineTo(this._x, y); + this._context.lineTo(x, y); + } else { + var x1 = this._x * (1 - this._t) + x * this._t; + this._context.lineTo(x1, this._y); + this._context.lineTo(x1, y); + } + break; + } + } + this._x = x, this._y = y; + } +}; + +export default function(context) { + return new Step(context, 0.5); +} + +export function stepBefore(context) { + return new Step(context, 0); +} + +export function stepAfter(context) { + return new Step(context, 1); +} diff --git a/frontend/node_modules/d3-shape/src/descending.js b/frontend/node_modules/d3-shape/src/descending.js new file mode 100644 index 0000000..a4e2d7f --- /dev/null +++ b/frontend/node_modules/d3-shape/src/descending.js @@ -0,0 +1,3 @@ +export default function(a, b) { + return b < a ? -1 : b > a ? 1 : b >= a ? 0 : NaN; +} diff --git a/frontend/node_modules/d3-shape/src/identity.js b/frontend/node_modules/d3-shape/src/identity.js new file mode 100644 index 0000000..ca161ab --- /dev/null +++ b/frontend/node_modules/d3-shape/src/identity.js @@ -0,0 +1,3 @@ +export default function(d) { + return d; +} diff --git a/frontend/node_modules/d3-shape/src/index.js b/frontend/node_modules/d3-shape/src/index.js new file mode 100644 index 0000000..988d401 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/index.js @@ -0,0 +1,53 @@ +export {default as arc} from "./arc.js"; +export {default as area} from "./area.js"; +export {default as line} from "./line.js"; +export {default as pie} from "./pie.js"; +export {default as areaRadial, default as radialArea} from "./areaRadial.js"; // Note: radialArea is deprecated! +export {default as lineRadial, default as radialLine} from "./lineRadial.js"; // Note: radialLine is deprecated! +export {default as pointRadial} from "./pointRadial.js"; +export {link, linkHorizontal, linkVertical, linkRadial} from "./link.js"; + +export {default as symbol, symbolsStroke, symbolsFill, symbolsFill as symbols} from "./symbol.js"; +export {default as symbolAsterisk} from "./symbol/asterisk.js"; +export {default as symbolCircle} from "./symbol/circle.js"; +export {default as symbolCross} from "./symbol/cross.js"; +export {default as symbolDiamond} from "./symbol/diamond.js"; +export {default as symbolDiamond2} from "./symbol/diamond2.js"; +export {default as symbolPlus} from "./symbol/plus.js"; +export {default as symbolSquare} from "./symbol/square.js"; +export {default as symbolSquare2} from "./symbol/square2.js"; +export {default as symbolStar} from "./symbol/star.js"; +export {default as symbolTriangle} from "./symbol/triangle.js"; +export {default as symbolTriangle2} from "./symbol/triangle2.js"; +export {default as symbolWye} from "./symbol/wye.js"; +export {default as symbolTimes, default as symbolX} from "./symbol/times.js"; + +export {default as curveBasisClosed} from "./curve/basisClosed.js"; +export {default as curveBasisOpen} from "./curve/basisOpen.js"; +export {default as curveBasis} from "./curve/basis.js"; +export {bumpX as curveBumpX, bumpY as curveBumpY} from "./curve/bump.js"; +export {default as curveBundle} from "./curve/bundle.js"; +export {default as curveCardinalClosed} from "./curve/cardinalClosed.js"; +export {default as curveCardinalOpen} from "./curve/cardinalOpen.js"; +export {default as curveCardinal} from "./curve/cardinal.js"; +export {default as curveCatmullRomClosed} from "./curve/catmullRomClosed.js"; +export {default as curveCatmullRomOpen} from "./curve/catmullRomOpen.js"; +export {default as curveCatmullRom} from "./curve/catmullRom.js"; +export {default as curveLinearClosed} from "./curve/linearClosed.js"; +export {default as curveLinear} from "./curve/linear.js"; +export {monotoneX as curveMonotoneX, monotoneY as curveMonotoneY} from "./curve/monotone.js"; +export {default as curveNatural} from "./curve/natural.js"; +export {default as curveStep, stepAfter as curveStepAfter, stepBefore as curveStepBefore} from "./curve/step.js"; + +export {default as stack} from "./stack.js"; +export {default as stackOffsetExpand} from "./offset/expand.js"; +export {default as stackOffsetDiverging} from "./offset/diverging.js"; +export {default as stackOffsetNone} from "./offset/none.js"; +export {default as stackOffsetSilhouette} from "./offset/silhouette.js"; +export {default as stackOffsetWiggle} from "./offset/wiggle.js"; +export {default as stackOrderAppearance} from "./order/appearance.js"; +export {default as stackOrderAscending} from "./order/ascending.js"; +export {default as stackOrderDescending} from "./order/descending.js"; +export {default as stackOrderInsideOut} from "./order/insideOut.js"; +export {default as stackOrderNone} from "./order/none.js"; +export {default as stackOrderReverse} from "./order/reverse.js"; diff --git a/frontend/node_modules/d3-shape/src/line.js b/frontend/node_modules/d3-shape/src/line.js new file mode 100644 index 0000000..84bfb26 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/line.js @@ -0,0 +1,58 @@ +import array from "./array.js"; +import constant from "./constant.js"; +import curveLinear from "./curve/linear.js"; +import {withPath} from "./path.js"; +import {x as pointX, y as pointY} from "./point.js"; + +export default function(x, y) { + var defined = constant(true), + context = null, + curve = curveLinear, + output = null, + path = withPath(line); + + x = typeof x === "function" ? x : (x === undefined) ? pointX : constant(x); + y = typeof y === "function" ? y : (y === undefined) ? pointY : constant(y); + + function line(data) { + var i, + n = (data = array(data)).length, + d, + defined0 = false, + buffer; + + if (context == null) output = curve(buffer = path()); + + for (i = 0; i <= n; ++i) { + if (!(i < n && defined(d = data[i], i, data)) === defined0) { + if (defined0 = !defined0) output.lineStart(); + else output.lineEnd(); + } + if (defined0) output.point(+x(d, i, data), +y(d, i, data)); + } + + if (buffer) return output = null, buffer + "" || null; + } + + line.x = function(_) { + return arguments.length ? (x = typeof _ === "function" ? _ : constant(+_), line) : x; + }; + + line.y = function(_) { + return arguments.length ? (y = typeof _ === "function" ? _ : constant(+_), line) : y; + }; + + line.defined = function(_) { + return arguments.length ? (defined = typeof _ === "function" ? _ : constant(!!_), line) : defined; + }; + + line.curve = function(_) { + return arguments.length ? (curve = _, context != null && (output = curve(context)), line) : curve; + }; + + line.context = function(_) { + return arguments.length ? (_ == null ? context = output = null : output = curve(context = _), line) : context; + }; + + return line; +} diff --git a/frontend/node_modules/d3-shape/src/lineRadial.js b/frontend/node_modules/d3-shape/src/lineRadial.js new file mode 100644 index 0000000..beaf577 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/lineRadial.js @@ -0,0 +1,19 @@ +import curveRadial, {curveRadialLinear} from "./curve/radial.js"; +import line from "./line.js"; + +export function lineRadial(l) { + var c = l.curve; + + l.angle = l.x, delete l.x; + l.radius = l.y, delete l.y; + + l.curve = function(_) { + return arguments.length ? c(curveRadial(_)) : c()._curve; + }; + + return l; +} + +export default function() { + return lineRadial(line().curve(curveRadialLinear)); +} diff --git a/frontend/node_modules/d3-shape/src/link.js b/frontend/node_modules/d3-shape/src/link.js new file mode 100644 index 0000000..a1c7a8f --- /dev/null +++ b/frontend/node_modules/d3-shape/src/link.js @@ -0,0 +1,73 @@ +import {slice} from "./array.js"; +import constant from "./constant.js"; +import {bumpX, bumpY, bumpRadial} from "./curve/bump.js"; +import {withPath} from "./path.js"; +import {x as pointX, y as pointY} from "./point.js"; + +function linkSource(d) { + return d.source; +} + +function linkTarget(d) { + return d.target; +} + +export function link(curve) { + let source = linkSource, + target = linkTarget, + x = pointX, + y = pointY, + context = null, + output = null, + path = withPath(link); + + function link() { + let buffer; + const argv = slice.call(arguments); + const s = source.apply(this, argv); + const t = target.apply(this, argv); + if (context == null) output = curve(buffer = path()); + output.lineStart(); + argv[0] = s, output.point(+x.apply(this, argv), +y.apply(this, argv)); + argv[0] = t, output.point(+x.apply(this, argv), +y.apply(this, argv)); + output.lineEnd(); + if (buffer) return output = null, buffer + "" || null; + } + + link.source = function(_) { + return arguments.length ? (source = _, link) : source; + }; + + link.target = function(_) { + return arguments.length ? (target = _, link) : target; + }; + + link.x = function(_) { + return arguments.length ? (x = typeof _ === "function" ? _ : constant(+_), link) : x; + }; + + link.y = function(_) { + return arguments.length ? (y = typeof _ === "function" ? _ : constant(+_), link) : y; + }; + + link.context = function(_) { + return arguments.length ? (_ == null ? context = output = null : output = curve(context = _), link) : context; + }; + + return link; +} + +export function linkHorizontal() { + return link(bumpX); +} + +export function linkVertical() { + return link(bumpY); +} + +export function linkRadial() { + const l = link(bumpRadial); + l.angle = l.x, delete l.x; + l.radius = l.y, delete l.y; + return l; +} diff --git a/frontend/node_modules/d3-shape/src/math.js b/frontend/node_modules/d3-shape/src/math.js new file mode 100644 index 0000000..272303d --- /dev/null +++ b/frontend/node_modules/d3-shape/src/math.js @@ -0,0 +1,20 @@ +export const abs = Math.abs; +export const atan2 = Math.atan2; +export const cos = Math.cos; +export const max = Math.max; +export const min = Math.min; +export const sin = Math.sin; +export const sqrt = Math.sqrt; + +export const epsilon = 1e-12; +export const pi = Math.PI; +export const halfPi = pi / 2; +export const tau = 2 * pi; + +export function acos(x) { + return x > 1 ? 0 : x < -1 ? pi : Math.acos(x); +} + +export function asin(x) { + return x >= 1 ? halfPi : x <= -1 ? -halfPi : Math.asin(x); +} diff --git a/frontend/node_modules/d3-shape/src/noop.js b/frontend/node_modules/d3-shape/src/noop.js new file mode 100644 index 0000000..6ab80bc --- /dev/null +++ b/frontend/node_modules/d3-shape/src/noop.js @@ -0,0 +1 @@ +export default function() {} diff --git a/frontend/node_modules/d3-shape/src/offset/diverging.js b/frontend/node_modules/d3-shape/src/offset/diverging.js new file mode 100644 index 0000000..45a5fff --- /dev/null +++ b/frontend/node_modules/d3-shape/src/offset/diverging.js @@ -0,0 +1,14 @@ +export default function(series, order) { + if (!((n = series.length) > 0)) return; + for (var i, j = 0, d, dy, yp, yn, n, m = series[order[0]].length; j < m; ++j) { + for (yp = yn = 0, i = 0; i < n; ++i) { + if ((dy = (d = series[order[i]][j])[1] - d[0]) > 0) { + d[0] = yp, d[1] = yp += dy; + } else if (dy < 0) { + d[1] = yn, d[0] = yn += dy; + } else { + d[0] = 0, d[1] = dy; + } + } + } +} diff --git a/frontend/node_modules/d3-shape/src/offset/expand.js b/frontend/node_modules/d3-shape/src/offset/expand.js new file mode 100644 index 0000000..965bea1 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/offset/expand.js @@ -0,0 +1,10 @@ +import none from "./none.js"; + +export default function(series, order) { + if (!((n = series.length) > 0)) return; + for (var i, n, j = 0, m = series[0].length, y; j < m; ++j) { + for (y = i = 0; i < n; ++i) y += series[i][j][1] || 0; + if (y) for (i = 0; i < n; ++i) series[i][j][1] /= y; + } + none(series, order); +} diff --git a/frontend/node_modules/d3-shape/src/offset/none.js b/frontend/node_modules/d3-shape/src/offset/none.js new file mode 100644 index 0000000..d8e11dc --- /dev/null +++ b/frontend/node_modules/d3-shape/src/offset/none.js @@ -0,0 +1,9 @@ +export default function(series, order) { + if (!((n = series.length) > 1)) return; + for (var i = 1, j, s0, s1 = series[order[0]], n, m = s1.length; i < n; ++i) { + s0 = s1, s1 = series[order[i]]; + for (j = 0; j < m; ++j) { + s1[j][1] += s1[j][0] = isNaN(s0[j][1]) ? s0[j][0] : s0[j][1]; + } + } +} diff --git a/frontend/node_modules/d3-shape/src/offset/silhouette.js b/frontend/node_modules/d3-shape/src/offset/silhouette.js new file mode 100644 index 0000000..87829be --- /dev/null +++ b/frontend/node_modules/d3-shape/src/offset/silhouette.js @@ -0,0 +1,10 @@ +import none from "./none.js"; + +export default function(series, order) { + if (!((n = series.length) > 0)) return; + for (var j = 0, s0 = series[order[0]], n, m = s0.length; j < m; ++j) { + for (var i = 0, y = 0; i < n; ++i) y += series[i][j][1] || 0; + s0[j][1] += s0[j][0] = -y / 2; + } + none(series, order); +} diff --git a/frontend/node_modules/d3-shape/src/offset/wiggle.js b/frontend/node_modules/d3-shape/src/offset/wiggle.js new file mode 100644 index 0000000..8db717c --- /dev/null +++ b/frontend/node_modules/d3-shape/src/offset/wiggle.js @@ -0,0 +1,24 @@ +import none from "./none.js"; + +export default function(series, order) { + if (!((n = series.length) > 0) || !((m = (s0 = series[order[0]]).length) > 0)) return; + for (var y = 0, j = 1, s0, m, n; j < m; ++j) { + for (var i = 0, s1 = 0, s2 = 0; i < n; ++i) { + var si = series[order[i]], + sij0 = si[j][1] || 0, + sij1 = si[j - 1][1] || 0, + s3 = (sij0 - sij1) / 2; + for (var k = 0; k < i; ++k) { + var sk = series[order[k]], + skj0 = sk[j][1] || 0, + skj1 = sk[j - 1][1] || 0; + s3 += skj0 - skj1; + } + s1 += sij0, s2 += s3 * sij0; + } + s0[j - 1][1] += s0[j - 1][0] = y; + if (s1) y -= s2 / s1; + } + s0[j - 1][1] += s0[j - 1][0] = y; + none(series, order); +} diff --git a/frontend/node_modules/d3-shape/src/order/appearance.js b/frontend/node_modules/d3-shape/src/order/appearance.js new file mode 100644 index 0000000..e052924 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/order/appearance.js @@ -0,0 +1,12 @@ +import none from "./none.js"; + +export default function(series) { + var peaks = series.map(peak); + return none(series).sort(function(a, b) { return peaks[a] - peaks[b]; }); +} + +function peak(series) { + var i = -1, j = 0, n = series.length, vi, vj = -Infinity; + while (++i < n) if ((vi = +series[i][1]) > vj) vj = vi, j = i; + return j; +} diff --git a/frontend/node_modules/d3-shape/src/order/ascending.js b/frontend/node_modules/d3-shape/src/order/ascending.js new file mode 100644 index 0000000..e0d28e3 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/order/ascending.js @@ -0,0 +1,12 @@ +import none from "./none.js"; + +export default function(series) { + var sums = series.map(sum); + return none(series).sort(function(a, b) { return sums[a] - sums[b]; }); +} + +export function sum(series) { + var s = 0, i = -1, n = series.length, v; + while (++i < n) if (v = +series[i][1]) s += v; + return s; +} diff --git a/frontend/node_modules/d3-shape/src/order/descending.js b/frontend/node_modules/d3-shape/src/order/descending.js new file mode 100644 index 0000000..dd27201 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/order/descending.js @@ -0,0 +1,5 @@ +import ascending from "./ascending.js"; + +export default function(series) { + return ascending(series).reverse(); +} diff --git a/frontend/node_modules/d3-shape/src/order/insideOut.js b/frontend/node_modules/d3-shape/src/order/insideOut.js new file mode 100644 index 0000000..b0b2abd --- /dev/null +++ b/frontend/node_modules/d3-shape/src/order/insideOut.js @@ -0,0 +1,27 @@ +import appearance from "./appearance.js"; +import {sum} from "./ascending.js"; + +export default function(series) { + var n = series.length, + i, + j, + sums = series.map(sum), + order = appearance(series), + top = 0, + bottom = 0, + tops = [], + bottoms = []; + + for (i = 0; i < n; ++i) { + j = order[i]; + if (top < bottom) { + top += sums[j]; + tops.push(j); + } else { + bottom += sums[j]; + bottoms.push(j); + } + } + + return bottoms.reverse().concat(tops); +} diff --git a/frontend/node_modules/d3-shape/src/order/none.js b/frontend/node_modules/d3-shape/src/order/none.js new file mode 100644 index 0000000..b0d7d6f --- /dev/null +++ b/frontend/node_modules/d3-shape/src/order/none.js @@ -0,0 +1,5 @@ +export default function(series) { + var n = series.length, o = new Array(n); + while (--n >= 0) o[n] = n; + return o; +} diff --git a/frontend/node_modules/d3-shape/src/order/reverse.js b/frontend/node_modules/d3-shape/src/order/reverse.js new file mode 100644 index 0000000..8380ca0 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/order/reverse.js @@ -0,0 +1,5 @@ +import none from "./none.js"; + +export default function(series) { + return none(series).reverse(); +} diff --git a/frontend/node_modules/d3-shape/src/path.js b/frontend/node_modules/d3-shape/src/path.js new file mode 100644 index 0000000..a1c68e6 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/path.js @@ -0,0 +1,19 @@ +import {Path} from "d3-path"; + +export function withPath(shape) { + let digits = 3; + + shape.digits = function(_) { + if (!arguments.length) return digits; + if (_ == null) { + digits = null; + } else { + const d = Math.floor(_); + if (!(d >= 0)) throw new RangeError(`invalid digits: ${_}`); + digits = d; + } + return shape; + }; + + return () => new Path(digits); +} diff --git a/frontend/node_modules/d3-shape/src/pie.js b/frontend/node_modules/d3-shape/src/pie.js new file mode 100644 index 0000000..6748f45 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/pie.js @@ -0,0 +1,80 @@ +import array from "./array.js"; +import constant from "./constant.js"; +import descending from "./descending.js"; +import identity from "./identity.js"; +import {tau} from "./math.js"; + +export default function() { + var value = identity, + sortValues = descending, + sort = null, + startAngle = constant(0), + endAngle = constant(tau), + padAngle = constant(0); + + function pie(data) { + var i, + n = (data = array(data)).length, + j, + k, + sum = 0, + index = new Array(n), + arcs = new Array(n), + a0 = +startAngle.apply(this, arguments), + da = Math.min(tau, Math.max(-tau, endAngle.apply(this, arguments) - a0)), + a1, + p = Math.min(Math.abs(da) / n, padAngle.apply(this, arguments)), + pa = p * (da < 0 ? -1 : 1), + v; + + for (i = 0; i < n; ++i) { + if ((v = arcs[index[i] = i] = +value(data[i], i, data)) > 0) { + sum += v; + } + } + + // Optionally sort the arcs by previously-computed values or by data. + if (sortValues != null) index.sort(function(i, j) { return sortValues(arcs[i], arcs[j]); }); + else if (sort != null) index.sort(function(i, j) { return sort(data[i], data[j]); }); + + // Compute the arcs! They are stored in the original data's order. + for (i = 0, k = sum ? (da - n * pa) / sum : 0; i < n; ++i, a0 = a1) { + j = index[i], v = arcs[j], a1 = a0 + (v > 0 ? v * k : 0) + pa, arcs[j] = { + data: data[j], + index: i, + value: v, + startAngle: a0, + endAngle: a1, + padAngle: p + }; + } + + return arcs; + } + + pie.value = function(_) { + return arguments.length ? (value = typeof _ === "function" ? _ : constant(+_), pie) : value; + }; + + pie.sortValues = function(_) { + return arguments.length ? (sortValues = _, sort = null, pie) : sortValues; + }; + + pie.sort = function(_) { + return arguments.length ? (sort = _, sortValues = null, pie) : sort; + }; + + pie.startAngle = function(_) { + return arguments.length ? (startAngle = typeof _ === "function" ? _ : constant(+_), pie) : startAngle; + }; + + pie.endAngle = function(_) { + return arguments.length ? (endAngle = typeof _ === "function" ? _ : constant(+_), pie) : endAngle; + }; + + pie.padAngle = function(_) { + return arguments.length ? (padAngle = typeof _ === "function" ? _ : constant(+_), pie) : padAngle; + }; + + return pie; +} diff --git a/frontend/node_modules/d3-shape/src/point.js b/frontend/node_modules/d3-shape/src/point.js new file mode 100644 index 0000000..c345257 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/point.js @@ -0,0 +1,7 @@ +export function x(p) { + return p[0]; +} + +export function y(p) { + return p[1]; +} diff --git a/frontend/node_modules/d3-shape/src/pointRadial.js b/frontend/node_modules/d3-shape/src/pointRadial.js new file mode 100644 index 0000000..1cccb70 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/pointRadial.js @@ -0,0 +1,3 @@ +export default function(x, y) { + return [(y = +y) * Math.cos(x -= Math.PI / 2), y * Math.sin(x)]; +} diff --git a/frontend/node_modules/d3-shape/src/stack.js b/frontend/node_modules/d3-shape/src/stack.js new file mode 100644 index 0000000..c4d30b1 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/stack.js @@ -0,0 +1,58 @@ +import array from "./array.js"; +import constant from "./constant.js"; +import offsetNone from "./offset/none.js"; +import orderNone from "./order/none.js"; + +function stackValue(d, key) { + return d[key]; +} + +function stackSeries(key) { + const series = []; + series.key = key; + return series; +} + +export default function() { + var keys = constant([]), + order = orderNone, + offset = offsetNone, + value = stackValue; + + function stack(data) { + var sz = Array.from(keys.apply(this, arguments), stackSeries), + i, n = sz.length, j = -1, + oz; + + for (const d of data) { + for (i = 0, ++j; i < n; ++i) { + (sz[i][j] = [0, +value(d, sz[i].key, j, data)]).data = d; + } + } + + for (i = 0, oz = array(order(sz)); i < n; ++i) { + sz[oz[i]].index = i; + } + + offset(sz, oz); + return sz; + } + + stack.keys = function(_) { + return arguments.length ? (keys = typeof _ === "function" ? _ : constant(Array.from(_)), stack) : keys; + }; + + stack.value = function(_) { + return arguments.length ? (value = typeof _ === "function" ? _ : constant(+_), stack) : value; + }; + + stack.order = function(_) { + return arguments.length ? (order = _ == null ? orderNone : typeof _ === "function" ? _ : constant(Array.from(_)), stack) : order; + }; + + stack.offset = function(_) { + return arguments.length ? (offset = _ == null ? offsetNone : _, stack) : offset; + }; + + return stack; +} diff --git a/frontend/node_modules/d3-shape/src/symbol.js b/frontend/node_modules/d3-shape/src/symbol.js new file mode 100644 index 0000000..f6e6d7b --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol.js @@ -0,0 +1,66 @@ +import constant from "./constant.js"; +import {withPath} from "./path.js"; +import asterisk from "./symbol/asterisk.js"; +import circle from "./symbol/circle.js"; +import cross from "./symbol/cross.js"; +import diamond from "./symbol/diamond.js"; +import diamond2 from "./symbol/diamond2.js"; +import plus from "./symbol/plus.js"; +import square from "./symbol/square.js"; +import square2 from "./symbol/square2.js"; +import star from "./symbol/star.js"; +import triangle from "./symbol/triangle.js"; +import triangle2 from "./symbol/triangle2.js"; +import wye from "./symbol/wye.js"; +import times from "./symbol/times.js"; + +// These symbols are designed to be filled. +export const symbolsFill = [ + circle, + cross, + diamond, + square, + star, + triangle, + wye +]; + +// These symbols are designed to be stroked (with a width of 1.5px and round caps). +export const symbolsStroke = [ + circle, + plus, + times, + triangle2, + asterisk, + square2, + diamond2 +]; + +export default function Symbol(type, size) { + let context = null, + path = withPath(symbol); + + type = typeof type === "function" ? type : constant(type || circle); + size = typeof size === "function" ? size : constant(size === undefined ? 64 : +size); + + function symbol() { + let buffer; + if (!context) context = buffer = path(); + type.apply(this, arguments).draw(context, +size.apply(this, arguments)); + if (buffer) return context = null, buffer + "" || null; + } + + symbol.type = function(_) { + return arguments.length ? (type = typeof _ === "function" ? _ : constant(_), symbol) : type; + }; + + symbol.size = function(_) { + return arguments.length ? (size = typeof _ === "function" ? _ : constant(+_), symbol) : size; + }; + + symbol.context = function(_) { + return arguments.length ? (context = _ == null ? null : _, symbol) : context; + }; + + return symbol; +} diff --git a/frontend/node_modules/d3-shape/src/symbol/asterisk.js b/frontend/node_modules/d3-shape/src/symbol/asterisk.js new file mode 100644 index 0000000..05eb9a2 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/asterisk.js @@ -0,0 +1,17 @@ +import {min, sqrt} from "../math.js"; + +const sqrt3 = sqrt(3); + +export default { + draw(context, size) { + const r = sqrt(size + min(size / 28, 0.75)) * 0.59436; + const t = r / 2; + const u = t * sqrt3; + context.moveTo(0, r); + context.lineTo(0, -r); + context.moveTo(-u, -t); + context.lineTo(u, t); + context.moveTo(-u, t); + context.lineTo(u, -t); + } +}; diff --git a/frontend/node_modules/d3-shape/src/symbol/circle.js b/frontend/node_modules/d3-shape/src/symbol/circle.js new file mode 100644 index 0000000..485e06c --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/circle.js @@ -0,0 +1,9 @@ +import {pi, sqrt, tau} from "../math.js"; + +export default { + draw(context, size) { + const r = sqrt(size / pi); + context.moveTo(r, 0); + context.arc(0, 0, r, 0, tau); + } +}; diff --git a/frontend/node_modules/d3-shape/src/symbol/cross.js b/frontend/node_modules/d3-shape/src/symbol/cross.js new file mode 100644 index 0000000..5e586e9 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/cross.js @@ -0,0 +1,20 @@ +import {sqrt} from "../math.js"; + +export default { + draw(context, size) { + const r = sqrt(size / 5) / 2; + context.moveTo(-3 * r, -r); + context.lineTo(-r, -r); + context.lineTo(-r, -3 * r); + context.lineTo(r, -3 * r); + context.lineTo(r, -r); + context.lineTo(3 * r, -r); + context.lineTo(3 * r, r); + context.lineTo(r, r); + context.lineTo(r, 3 * r); + context.lineTo(-r, 3 * r); + context.lineTo(-r, r); + context.lineTo(-3 * r, r); + context.closePath(); + } +}; diff --git a/frontend/node_modules/d3-shape/src/symbol/diamond.js b/frontend/node_modules/d3-shape/src/symbol/diamond.js new file mode 100644 index 0000000..7f4d60a --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/diamond.js @@ -0,0 +1,16 @@ +import {sqrt} from "../math.js"; + +const tan30 = sqrt(1 / 3); +const tan30_2 = tan30 * 2; + +export default { + draw(context, size) { + const y = sqrt(size / tan30_2); + const x = y * tan30; + context.moveTo(0, -y); + context.lineTo(x, 0); + context.lineTo(0, y); + context.lineTo(-x, 0); + context.closePath(); + } +}; diff --git a/frontend/node_modules/d3-shape/src/symbol/diamond2.js b/frontend/node_modules/d3-shape/src/symbol/diamond2.js new file mode 100644 index 0000000..f4df0b3 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/diamond2.js @@ -0,0 +1,12 @@ +import {sqrt} from "../math.js"; + +export default { + draw(context, size) { + const r = sqrt(size) * 0.62625; + context.moveTo(0, -r); + context.lineTo(r, 0); + context.lineTo(0, r); + context.lineTo(-r, 0); + context.closePath(); + } +}; diff --git a/frontend/node_modules/d3-shape/src/symbol/plus.js b/frontend/node_modules/d3-shape/src/symbol/plus.js new file mode 100644 index 0000000..bbb7741 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/plus.js @@ -0,0 +1,11 @@ +import {min, sqrt} from "../math.js"; + +export default { + draw(context, size) { + const r = sqrt(size - min(size / 7, 2)) * 0.87559; + context.moveTo(-r, 0); + context.lineTo(r, 0); + context.moveTo(0, r); + context.lineTo(0, -r); + } +}; diff --git a/frontend/node_modules/d3-shape/src/symbol/square.js b/frontend/node_modules/d3-shape/src/symbol/square.js new file mode 100644 index 0000000..6a8d5dd --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/square.js @@ -0,0 +1,9 @@ +import {sqrt} from "../math.js"; + +export default { + draw(context, size) { + const w = sqrt(size); + const x = -w / 2; + context.rect(x, x, w, w); + } +}; diff --git a/frontend/node_modules/d3-shape/src/symbol/square2.js b/frontend/node_modules/d3-shape/src/symbol/square2.js new file mode 100644 index 0000000..508d504 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/square2.js @@ -0,0 +1,12 @@ +import {sqrt} from "../math.js"; + +export default { + draw(context, size) { + const r = sqrt(size) * 0.4431; + context.moveTo(r, r); + context.lineTo(r, -r); + context.lineTo(-r, -r); + context.lineTo(-r, r); + context.closePath(); + } +}; diff --git a/frontend/node_modules/d3-shape/src/symbol/star.js b/frontend/node_modules/d3-shape/src/symbol/star.js new file mode 100644 index 0000000..e5000d9 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/star.js @@ -0,0 +1,24 @@ +import {sin, cos, sqrt, pi, tau} from "../math.js"; + +const ka = 0.89081309152928522810; +const kr = sin(pi / 10) / sin(7 * pi / 10); +const kx = sin(tau / 10) * kr; +const ky = -cos(tau / 10) * kr; + +export default { + draw(context, size) { + const r = sqrt(size * ka); + const x = kx * r; + const y = ky * r; + context.moveTo(0, -r); + context.lineTo(x, y); + for (let i = 1; i < 5; ++i) { + const a = tau * i / 5; + const c = cos(a); + const s = sin(a); + context.lineTo(s * r, -c * r); + context.lineTo(c * x - s * y, s * x + c * y); + } + context.closePath(); + } +}; diff --git a/frontend/node_modules/d3-shape/src/symbol/times.js b/frontend/node_modules/d3-shape/src/symbol/times.js new file mode 100644 index 0000000..1d8c829 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/times.js @@ -0,0 +1,11 @@ +import {min, sqrt} from "../math.js"; + +export default { + draw(context, size) { + const r = sqrt(size - min(size / 6, 1.7)) * 0.6189; + context.moveTo(-r, -r); + context.lineTo(r, r); + context.moveTo(-r, r); + context.lineTo(r, -r); + } +}; diff --git a/frontend/node_modules/d3-shape/src/symbol/triangle.js b/frontend/node_modules/d3-shape/src/symbol/triangle.js new file mode 100644 index 0000000..023e824 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/triangle.js @@ -0,0 +1,13 @@ +import {sqrt} from "../math.js"; + +const sqrt3 = sqrt(3); + +export default { + draw(context, size) { + const y = -sqrt(size / (sqrt3 * 3)); + context.moveTo(0, y * 2); + context.lineTo(-sqrt3 * y, -y); + context.lineTo(sqrt3 * y, -y); + context.closePath(); + } +}; diff --git a/frontend/node_modules/d3-shape/src/symbol/triangle2.js b/frontend/node_modules/d3-shape/src/symbol/triangle2.js new file mode 100644 index 0000000..6b189e4 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/triangle2.js @@ -0,0 +1,15 @@ +import {sqrt} from "../math.js"; + +const sqrt3 = sqrt(3); + +export default { + draw(context, size) { + const s = sqrt(size) * 0.6824; + const t = s / 2; + const u = (s * sqrt3) / 2; // cos(Math.PI / 6) + context.moveTo(0, -s); + context.lineTo(u, t); + context.lineTo(-u, t); + context.closePath(); + } +}; diff --git a/frontend/node_modules/d3-shape/src/symbol/wye.js b/frontend/node_modules/d3-shape/src/symbol/wye.js new file mode 100644 index 0000000..b8fad35 --- /dev/null +++ b/frontend/node_modules/d3-shape/src/symbol/wye.js @@ -0,0 +1,25 @@ +import {sqrt} from "../math.js"; + +const c = -0.5; +const s = sqrt(3) / 2; +const k = 1 / sqrt(12); +const a = (k / 2 + 1) * 3; + +export default { + draw(context, size) { + const r = sqrt(size / a); + const x0 = r / 2, y0 = r * k; + const x1 = x0, y1 = r * k + r; + const x2 = -x1, y2 = y1; + context.moveTo(x0, y0); + context.lineTo(x1, y1); + context.lineTo(x2, y2); + context.lineTo(c * x0 - s * y0, s * x0 + c * y0); + context.lineTo(c * x1 - s * y1, s * x1 + c * y1); + context.lineTo(c * x2 - s * y2, s * x2 + c * y2); + context.lineTo(c * x0 + s * y0, c * y0 - s * x0); + context.lineTo(c * x1 + s * y1, c * y1 - s * x1); + context.lineTo(c * x2 + s * y2, c * y2 - s * x2); + context.closePath(); + } +}; diff --git a/frontend/node_modules/d3-time-format/LICENSE b/frontend/node_modules/d3-time-format/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-time-format/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-time-format/README.md b/frontend/node_modules/d3-time-format/README.md new file mode 100644 index 0000000..6388cc1 --- /dev/null +++ b/frontend/node_modules/d3-time-format/README.md @@ -0,0 +1,209 @@ +# d3-time-format + +This module provides a JavaScript implementation of the venerable [strptime](http://pubs.opengroup.org/onlinepubs/009695399/functions/strptime.html) and [strftime](http://pubs.opengroup.org/onlinepubs/007908799/xsh/strftime.html) functions from the C standard library, and can be used to parse or format [dates](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date) in a variety of locale-specific representations. To format a date, create a [formatter](#locale_format) from a specifier (a string with the desired format *directives*, indicated by `%`); then pass a date to the formatter, which returns a string. For example, to convert the current date to a human-readable string: + +```js +const formatTime = d3.timeFormat("%B %d, %Y"); +formatTime(new Date); // "June 30, 2015" +``` + +Likewise, to convert a string back to a date, create a [parser](#locale_parse): + +```js +const parseTime = d3.timeParse("%B %d, %Y"); +parseTime("June 30, 2015"); // Tue Jun 30 2015 00:00:00 GMT-0700 (PDT) +``` + +You can implement more elaborate conditional time formats, too. For example, here’s a [multi-scale time format](https://bl.ocks.org/mbostock/4149176) using [time intervals](https://github.com/d3/d3-time): + +```js +const formatMillisecond = d3.timeFormat(".%L"), + formatSecond = d3.timeFormat(":%S"), + formatMinute = d3.timeFormat("%I:%M"), + formatHour = d3.timeFormat("%I %p"), + formatDay = d3.timeFormat("%a %d"), + formatWeek = d3.timeFormat("%b %d"), + formatMonth = d3.timeFormat("%B"), + formatYear = d3.timeFormat("%Y"); + +function multiFormat(date) { + return (d3.timeSecond(date) < date ? formatMillisecond + : d3.timeMinute(date) < date ? formatSecond + : d3.timeHour(date) < date ? formatMinute + : d3.timeDay(date) < date ? formatHour + : d3.timeMonth(date) < date ? (d3.timeWeek(date) < date ? formatDay : formatWeek) + : d3.timeYear(date) < date ? formatMonth + : formatYear)(date); +} +``` + +This module is used by D3 [time scales](https://github.com/d3/d3-scale/blob/main/README.md#time-scales) to generate human-readable ticks. + +## Installing + +If you use npm, `npm install d3-time-format`. You can also download the [latest release on GitHub](https://github.com/d3/d3-time-format/releases/latest). For vanilla HTML in modern browsers, import d3-time-format from Skypack: + +```html + +``` + +For legacy environments, you can load d3-time-format’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + + + + +Locale files are published to npm and can be loaded using [d3.json](https://github.com/d3/d3-fetch/blob/main/README.md#json). For example, to set Russian as the default locale: + +```js +d3.json("https://cdn.jsdelivr.net/npm/d3-time-format@3/locale/ru-RU.json").then(locale => { + d3.timeFormatDefaultLocale(locale); + + const format = d3.timeFormat("%c"); + + console.log(format(new Date)); // понедельник, 5 декабря 2016 г. 10:31:59 +}); +``` + +## API Reference + +# d3.timeFormat(specifier) · [Source](https://github.com/d3/d3-time-format/blob/main/src/defaultLocale.js) + +An alias for [*locale*.format](#locale_format) on the [default locale](#timeFormatDefaultLocale). + +# d3.timeParse(specifier) · [Source](https://github.com/d3/d3-time-format/blob/main/src/defaultLocale.js) + +An alias for [*locale*.parse](#locale_parse) on the [default locale](#timeFormatDefaultLocale). + +# d3.utcFormat(specifier) · [Source](https://github.com/d3/d3-time-format/blob/main/src/defaultLocale.js) + +An alias for [*locale*.utcFormat](#locale_utcFormat) on the [default locale](#timeFormatDefaultLocale). + +# d3.utcParse(specifier) · [Source](https://github.com/d3/d3-time-format/blob/main/src/defaultLocale.js) + +An alias for [*locale*.utcParse](#locale_utcParse) on the [default locale](#timeFormatDefaultLocale). + +# d3.isoFormat · [Source](https://github.com/d3/d3-time-format/blob/main/src/isoFormat.js) + +The full [ISO 8601](https://en.wikipedia.org/wiki/ISO_8601) UTC time formatter. Where available, this method will use [Date.toISOString](https://developer.mozilla.org/en-US/docs/JavaScript/Reference/Global_Objects/Date/toISOString) to format. + +# d3.isoParse · [Source](https://github.com/d3/d3-time-format/blob/main/src/isoParse.js) + +The full [ISO 8601](https://en.wikipedia.org/wiki/ISO_8601) UTC time parser. Where available, this method will use the [Date constructor](https://developer.mozilla.org/en-US/docs/JavaScript/Reference/Global_Objects/Date) to parse strings. If you depend on strict validation of the input format according to ISO 8601, you should construct a [UTC parser function](#utcParse): + +```js +const strictIsoParse = d3.utcParse("%Y-%m-%dT%H:%M:%S.%LZ"); +``` + +# locale.format(specifier) · [Source](https://github.com/d3/d3-time-format/blob/main/src/locale.js) + +Returns a new formatter for the given string *specifier*. The specifier string may contain the following directives: + +* `%a` - abbreviated weekday name.* +* `%A` - full weekday name.* +* `%b` - abbreviated month name.* +* `%B` - full month name.* +* `%c` - the locale’s date and time, such as `%x, %X`.* +* `%d` - zero-padded day of the month as a decimal number [01,31]. +* `%e` - space-padded day of the month as a decimal number [ 1,31]; equivalent to `%_d`. +* `%f` - microseconds as a decimal number [000000, 999999]. +* `%g` - ISO 8601 week-based year without century as a decimal number [00,99]. +* `%G` - ISO 8601 week-based year with century as a decimal number. +* `%H` - hour (24-hour clock) as a decimal number [00,23]. +* `%I` - hour (12-hour clock) as a decimal number [01,12]. +* `%j` - day of the year as a decimal number [001,366]. +* `%m` - month as a decimal number [01,12]. +* `%M` - minute as a decimal number [00,59]. +* `%L` - milliseconds as a decimal number [000, 999]. +* `%p` - either AM or PM.* +* `%q` - quarter of the year as a decimal number [1,4]. +* `%Q` - milliseconds since UNIX epoch. +* `%s` - seconds since UNIX epoch. +* `%S` - second as a decimal number [00,61]. +* `%u` - Monday-based (ISO 8601) weekday as a decimal number [1,7]. +* `%U` - Sunday-based week of the year as a decimal number [00,53]. +* `%V` - ISO 8601 week of the year as a decimal number [01, 53]. +* `%w` - Sunday-based weekday as a decimal number [0,6]. +* `%W` - Monday-based week of the year as a decimal number [00,53]. +* `%x` - the locale’s date, such as `%-m/%-d/%Y`.* +* `%X` - the locale’s time, such as `%-I:%M:%S %p`.* +* `%y` - year without century as a decimal number [00,99]. +* `%Y` - year with century as a decimal number, such as `1999`. +* `%Z` - time zone offset, such as `-0700`, `-07:00`, `-07`, or `Z`. +* `%%` - a literal percent sign (`%`). + +Directives marked with an asterisk (\*) may be affected by the [locale definition](#locales). + +For `%U`, all days in a new year preceding the first Sunday are considered to be in week 0. For `%W`, all days in a new year preceding the first Monday are considered to be in week 0. Week numbers are computed using [*interval*.count](https://github.com/d3/d3-time/blob/main/README.md#interval_count). For example, 2015-52 and 2016-00 represent Monday, December 28, 2015, while 2015-53 and 2016-01 represent Monday, January 4, 2016. This differs from the [ISO week date](https://en.wikipedia.org/wiki/ISO_week_date) specification (`%V`), which uses a more complicated definition! + +For `%V`,`%g` and `%G`, per the [strftime man page](http://man7.org/linux/man-pages/man3/strftime.3.html): + +> In this system, weeks start on a Monday, and are numbered from 01, for the first week, up to 52 or 53, for the last week. Week 1 is the first week where four or more days fall within the new year (or, synonymously, week 01 is: the first week of the year that contains a Thursday; or, the week that has 4 January in it). If the ISO week number belongs to the previous or next year, that year is used instead. + +The `%` sign indicating a directive may be immediately followed by a padding modifier: + +* `0` - zero-padding +* `_` - space-padding +* `-` - disable padding + +If no padding modifier is specified, the default is `0` for all directives except `%e`, which defaults to `_`. (In some implementations of strftime and strptime, a directive may include an optional field width or precision; this feature is not yet implemented.) + +The returned function formats a specified *[date](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Date)*, returning the corresponding string. + +```js +const formatMonth = d3.timeFormat("%B"), + formatDay = d3.timeFormat("%A"), + date = new Date(2014, 4, 1); // Thu May 01 2014 00:00:00 GMT-0700 (PDT) + +formatMonth(date); // "May" +formatDay(date); // "Thursday" +``` + +# locale.parse(specifier) · [Source](https://github.com/d3/d3-time-format/blob/main/src/locale.js) + +Returns a new parser for the given string *specifier*. The specifier string may contain the same directives as [*locale*.format](#locale_format). The `%d` and `%e` directives are considered equivalent for parsing. + +The returned function parses a specified *string*, returning the corresponding [date](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Date) or null if the string could not be parsed according to this format’s specifier. Parsing is strict: if the specified string does not exactly match the associated specifier, this method returns null. For example, if the associated specifier is `%Y-%m-%dT%H:%M:%SZ`, then the string `"2011-07-01T19:15:28Z"` will be parsed as expected, but `"2011-07-01T19:15:28"`, `"2011-07-01 19:15:28"` and `"2011-07-01"` will return null. (Note that the literal `Z` here is different from the time zone offset directive `%Z`.) If a more flexible parser is desired, try multiple formats sequentially until one returns non-null. + +# locale.utcFormat(specifier) · [Source](https://github.com/d3/d3-time-format/blob/main/src/locale.js) + +Equivalent to [*locale*.format](#locale_format), except all directives are interpreted as [Coordinated Universal Time (UTC)](https://en.wikipedia.org/wiki/Coordinated_Universal_Time) rather than local time. + +# locale.utcParse(specifier) · [Source](https://github.com/d3/d3-time-format/blob/main/src/locale.js) + +Equivalent to [*locale*.parse](#locale_parse), except all directives are interpreted as [Coordinated Universal Time (UTC)](https://en.wikipedia.org/wiki/Coordinated_Universal_Time) rather than local time. + +### Locales + +# d3.timeFormatLocale(definition) · [Source](https://github.com/d3/d3-time-format/blob/main/src/locale.js) + +Returns a *locale* object for the specified *definition* with [*locale*.format](#locale_format), [*locale*.parse](#locale_parse), [*locale*.utcFormat](#locale_utcFormat), [*locale*.utcParse](#locale_utcParse) methods. The *definition* must include the following properties: + +* `dateTime` - the date and time (`%c`) format specifier (e.g., `"%a %b %e %X %Y"`). +* `date` - the date (`%x`) format specifier (e.g., `"%m/%d/%Y"`). +* `time` - the time (`%X`) format specifier (e.g., `"%H:%M:%S"`). +* `periods` - the A.M. and P.M. equivalents (e.g., `["AM", "PM"]`). +* `days` - the full names of the weekdays, starting with Sunday. +* `shortDays` - the abbreviated names of the weekdays, starting with Sunday. +* `months` - the full names of the months (starting with January). +* `shortMonths` - the abbreviated names of the months (starting with January). + +For an example, see [Localized Time Axis II](https://bl.ocks.org/mbostock/805115ebaa574e771db1875a6d828949). + +# d3.timeFormatDefaultLocale(definition) · [Source](https://github.com/d3/d3-time-format/blob/main/src/defaultLocale.js) + +Equivalent to [d3.timeFormatLocale](#timeFormatLocale), except it also redefines [d3.timeFormat](#timeFormat), [d3.timeParse](#timeParse), [d3.utcFormat](#utcFormat) and [d3.utcParse](#utcParse) to the new locale’s [*locale*.format](#locale_format), [*locale*.parse](#locale_parse), [*locale*.utcFormat](#locale_utcFormat) and [*locale*.utcParse](#locale_utcParse). If you do not set a default locale, it defaults to [U.S. English](https://github.com/d3/d3-time-format/blob/main/locale/en-US.json). + +For an example, see [Localized Time Axis](https://bl.ocks.org/mbostock/6f1cc065d4d172bcaf322e399aa8d62f). diff --git a/frontend/node_modules/d3-time-format/dist/d3-time-format.js b/frontend/node_modules/d3-time-format/dist/d3-time-format.js new file mode 100644 index 0000000..8fc0998 --- /dev/null +++ b/frontend/node_modules/d3-time-format/dist/d3-time-format.js @@ -0,0 +1,745 @@ +// https://d3js.org/d3-time-format/ v4.1.0 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-time')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-time'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3)); +})(this, (function (exports, d3Time) { 'use strict'; + +function localDate(d) { + if (0 <= d.y && d.y < 100) { + var date = new Date(-1, d.m, d.d, d.H, d.M, d.S, d.L); + date.setFullYear(d.y); + return date; + } + return new Date(d.y, d.m, d.d, d.H, d.M, d.S, d.L); +} + +function utcDate(d) { + if (0 <= d.y && d.y < 100) { + var date = new Date(Date.UTC(-1, d.m, d.d, d.H, d.M, d.S, d.L)); + date.setUTCFullYear(d.y); + return date; + } + return new Date(Date.UTC(d.y, d.m, d.d, d.H, d.M, d.S, d.L)); +} + +function newDate(y, m, d) { + return {y: y, m: m, d: d, H: 0, M: 0, S: 0, L: 0}; +} + +function formatLocale(locale) { + var locale_dateTime = locale.dateTime, + locale_date = locale.date, + locale_time = locale.time, + locale_periods = locale.periods, + locale_weekdays = locale.days, + locale_shortWeekdays = locale.shortDays, + locale_months = locale.months, + locale_shortMonths = locale.shortMonths; + + var periodRe = formatRe(locale_periods), + periodLookup = formatLookup(locale_periods), + weekdayRe = formatRe(locale_weekdays), + weekdayLookup = formatLookup(locale_weekdays), + shortWeekdayRe = formatRe(locale_shortWeekdays), + shortWeekdayLookup = formatLookup(locale_shortWeekdays), + monthRe = formatRe(locale_months), + monthLookup = formatLookup(locale_months), + shortMonthRe = formatRe(locale_shortMonths), + shortMonthLookup = formatLookup(locale_shortMonths); + + var formats = { + "a": formatShortWeekday, + "A": formatWeekday, + "b": formatShortMonth, + "B": formatMonth, + "c": null, + "d": formatDayOfMonth, + "e": formatDayOfMonth, + "f": formatMicroseconds, + "g": formatYearISO, + "G": formatFullYearISO, + "H": formatHour24, + "I": formatHour12, + "j": formatDayOfYear, + "L": formatMilliseconds, + "m": formatMonthNumber, + "M": formatMinutes, + "p": formatPeriod, + "q": formatQuarter, + "Q": formatUnixTimestamp, + "s": formatUnixTimestampSeconds, + "S": formatSeconds, + "u": formatWeekdayNumberMonday, + "U": formatWeekNumberSunday, + "V": formatWeekNumberISO, + "w": formatWeekdayNumberSunday, + "W": formatWeekNumberMonday, + "x": null, + "X": null, + "y": formatYear, + "Y": formatFullYear, + "Z": formatZone, + "%": formatLiteralPercent + }; + + var utcFormats = { + "a": formatUTCShortWeekday, + "A": formatUTCWeekday, + "b": formatUTCShortMonth, + "B": formatUTCMonth, + "c": null, + "d": formatUTCDayOfMonth, + "e": formatUTCDayOfMonth, + "f": formatUTCMicroseconds, + "g": formatUTCYearISO, + "G": formatUTCFullYearISO, + "H": formatUTCHour24, + "I": formatUTCHour12, + "j": formatUTCDayOfYear, + "L": formatUTCMilliseconds, + "m": formatUTCMonthNumber, + "M": formatUTCMinutes, + "p": formatUTCPeriod, + "q": formatUTCQuarter, + "Q": formatUnixTimestamp, + "s": formatUnixTimestampSeconds, + "S": formatUTCSeconds, + "u": formatUTCWeekdayNumberMonday, + "U": formatUTCWeekNumberSunday, + "V": formatUTCWeekNumberISO, + "w": formatUTCWeekdayNumberSunday, + "W": formatUTCWeekNumberMonday, + "x": null, + "X": null, + "y": formatUTCYear, + "Y": formatUTCFullYear, + "Z": formatUTCZone, + "%": formatLiteralPercent + }; + + var parses = { + "a": parseShortWeekday, + "A": parseWeekday, + "b": parseShortMonth, + "B": parseMonth, + "c": parseLocaleDateTime, + "d": parseDayOfMonth, + "e": parseDayOfMonth, + "f": parseMicroseconds, + "g": parseYear, + "G": parseFullYear, + "H": parseHour24, + "I": parseHour24, + "j": parseDayOfYear, + "L": parseMilliseconds, + "m": parseMonthNumber, + "M": parseMinutes, + "p": parsePeriod, + "q": parseQuarter, + "Q": parseUnixTimestamp, + "s": parseUnixTimestampSeconds, + "S": parseSeconds, + "u": parseWeekdayNumberMonday, + "U": parseWeekNumberSunday, + "V": parseWeekNumberISO, + "w": parseWeekdayNumberSunday, + "W": parseWeekNumberMonday, + "x": parseLocaleDate, + "X": parseLocaleTime, + "y": parseYear, + "Y": parseFullYear, + "Z": parseZone, + "%": parseLiteralPercent + }; + + // These recursive directive definitions must be deferred. + formats.x = newFormat(locale_date, formats); + formats.X = newFormat(locale_time, formats); + formats.c = newFormat(locale_dateTime, formats); + utcFormats.x = newFormat(locale_date, utcFormats); + utcFormats.X = newFormat(locale_time, utcFormats); + utcFormats.c = newFormat(locale_dateTime, utcFormats); + + function newFormat(specifier, formats) { + return function(date) { + var string = [], + i = -1, + j = 0, + n = specifier.length, + c, + pad, + format; + + if (!(date instanceof Date)) date = new Date(+date); + + while (++i < n) { + if (specifier.charCodeAt(i) === 37) { + string.push(specifier.slice(j, i)); + if ((pad = pads[c = specifier.charAt(++i)]) != null) c = specifier.charAt(++i); + else pad = c === "e" ? " " : "0"; + if (format = formats[c]) c = format(date, pad); + string.push(c); + j = i + 1; + } + } + + string.push(specifier.slice(j, i)); + return string.join(""); + }; + } + + function newParse(specifier, Z) { + return function(string) { + var d = newDate(1900, undefined, 1), + i = parseSpecifier(d, specifier, string += "", 0), + week, day; + if (i != string.length) return null; + + // If a UNIX timestamp is specified, return it. + if ("Q" in d) return new Date(d.Q); + if ("s" in d) return new Date(d.s * 1000 + ("L" in d ? d.L : 0)); + + // If this is utcParse, never use the local timezone. + if (Z && !("Z" in d)) d.Z = 0; + + // The am-pm flag is 0 for AM, and 1 for PM. + if ("p" in d) d.H = d.H % 12 + d.p * 12; + + // If the month was not specified, inherit from the quarter. + if (d.m === undefined) d.m = "q" in d ? d.q : 0; + + // Convert day-of-week and week-of-year to day-of-year. + if ("V" in d) { + if (d.V < 1 || d.V > 53) return null; + if (!("w" in d)) d.w = 1; + if ("Z" in d) { + week = utcDate(newDate(d.y, 0, 1)), day = week.getUTCDay(); + week = day > 4 || day === 0 ? d3Time.utcMonday.ceil(week) : d3Time.utcMonday(week); + week = d3Time.utcDay.offset(week, (d.V - 1) * 7); + d.y = week.getUTCFullYear(); + d.m = week.getUTCMonth(); + d.d = week.getUTCDate() + (d.w + 6) % 7; + } else { + week = localDate(newDate(d.y, 0, 1)), day = week.getDay(); + week = day > 4 || day === 0 ? d3Time.timeMonday.ceil(week) : d3Time.timeMonday(week); + week = d3Time.timeDay.offset(week, (d.V - 1) * 7); + d.y = week.getFullYear(); + d.m = week.getMonth(); + d.d = week.getDate() + (d.w + 6) % 7; + } + } else if ("W" in d || "U" in d) { + if (!("w" in d)) d.w = "u" in d ? d.u % 7 : "W" in d ? 1 : 0; + day = "Z" in d ? utcDate(newDate(d.y, 0, 1)).getUTCDay() : localDate(newDate(d.y, 0, 1)).getDay(); + d.m = 0; + d.d = "W" in d ? (d.w + 6) % 7 + d.W * 7 - (day + 5) % 7 : d.w + d.U * 7 - (day + 6) % 7; + } + + // If a time zone is specified, all fields are interpreted as UTC and then + // offset according to the specified time zone. + if ("Z" in d) { + d.H += d.Z / 100 | 0; + d.M += d.Z % 100; + return utcDate(d); + } + + // Otherwise, all fields are in local time. + return localDate(d); + }; + } + + function parseSpecifier(d, specifier, string, j) { + var i = 0, + n = specifier.length, + m = string.length, + c, + parse; + + while (i < n) { + if (j >= m) return -1; + c = specifier.charCodeAt(i++); + if (c === 37) { + c = specifier.charAt(i++); + parse = parses[c in pads ? specifier.charAt(i++) : c]; + if (!parse || ((j = parse(d, string, j)) < 0)) return -1; + } else if (c != string.charCodeAt(j++)) { + return -1; + } + } + + return j; + } + + function parsePeriod(d, string, i) { + var n = periodRe.exec(string.slice(i)); + return n ? (d.p = periodLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseShortWeekday(d, string, i) { + var n = shortWeekdayRe.exec(string.slice(i)); + return n ? (d.w = shortWeekdayLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseWeekday(d, string, i) { + var n = weekdayRe.exec(string.slice(i)); + return n ? (d.w = weekdayLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseShortMonth(d, string, i) { + var n = shortMonthRe.exec(string.slice(i)); + return n ? (d.m = shortMonthLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseMonth(d, string, i) { + var n = monthRe.exec(string.slice(i)); + return n ? (d.m = monthLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseLocaleDateTime(d, string, i) { + return parseSpecifier(d, locale_dateTime, string, i); + } + + function parseLocaleDate(d, string, i) { + return parseSpecifier(d, locale_date, string, i); + } + + function parseLocaleTime(d, string, i) { + return parseSpecifier(d, locale_time, string, i); + } + + function formatShortWeekday(d) { + return locale_shortWeekdays[d.getDay()]; + } + + function formatWeekday(d) { + return locale_weekdays[d.getDay()]; + } + + function formatShortMonth(d) { + return locale_shortMonths[d.getMonth()]; + } + + function formatMonth(d) { + return locale_months[d.getMonth()]; + } + + function formatPeriod(d) { + return locale_periods[+(d.getHours() >= 12)]; + } + + function formatQuarter(d) { + return 1 + ~~(d.getMonth() / 3); + } + + function formatUTCShortWeekday(d) { + return locale_shortWeekdays[d.getUTCDay()]; + } + + function formatUTCWeekday(d) { + return locale_weekdays[d.getUTCDay()]; + } + + function formatUTCShortMonth(d) { + return locale_shortMonths[d.getUTCMonth()]; + } + + function formatUTCMonth(d) { + return locale_months[d.getUTCMonth()]; + } + + function formatUTCPeriod(d) { + return locale_periods[+(d.getUTCHours() >= 12)]; + } + + function formatUTCQuarter(d) { + return 1 + ~~(d.getUTCMonth() / 3); + } + + return { + format: function(specifier) { + var f = newFormat(specifier += "", formats); + f.toString = function() { return specifier; }; + return f; + }, + parse: function(specifier) { + var p = newParse(specifier += "", false); + p.toString = function() { return specifier; }; + return p; + }, + utcFormat: function(specifier) { + var f = newFormat(specifier += "", utcFormats); + f.toString = function() { return specifier; }; + return f; + }, + utcParse: function(specifier) { + var p = newParse(specifier += "", true); + p.toString = function() { return specifier; }; + return p; + } + }; +} + +var pads = {"-": "", "_": " ", "0": "0"}, + numberRe = /^\s*\d+/, // note: ignores next directive + percentRe = /^%/, + requoteRe = /[\\^$*+?|[\]().{}]/g; + +function pad(value, fill, width) { + var sign = value < 0 ? "-" : "", + string = (sign ? -value : value) + "", + length = string.length; + return sign + (length < width ? new Array(width - length + 1).join(fill) + string : string); +} + +function requote(s) { + return s.replace(requoteRe, "\\$&"); +} + +function formatRe(names) { + return new RegExp("^(?:" + names.map(requote).join("|") + ")", "i"); +} + +function formatLookup(names) { + return new Map(names.map((name, i) => [name.toLowerCase(), i])); +} + +function parseWeekdayNumberSunday(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 1)); + return n ? (d.w = +n[0], i + n[0].length) : -1; +} + +function parseWeekdayNumberMonday(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 1)); + return n ? (d.u = +n[0], i + n[0].length) : -1; +} + +function parseWeekNumberSunday(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.U = +n[0], i + n[0].length) : -1; +} + +function parseWeekNumberISO(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.V = +n[0], i + n[0].length) : -1; +} + +function parseWeekNumberMonday(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.W = +n[0], i + n[0].length) : -1; +} + +function parseFullYear(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 4)); + return n ? (d.y = +n[0], i + n[0].length) : -1; +} + +function parseYear(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.y = +n[0] + (+n[0] > 68 ? 1900 : 2000), i + n[0].length) : -1; +} + +function parseZone(d, string, i) { + var n = /^(Z)|([+-]\d\d)(?::?(\d\d))?/.exec(string.slice(i, i + 6)); + return n ? (d.Z = n[1] ? 0 : -(n[2] + (n[3] || "00")), i + n[0].length) : -1; +} + +function parseQuarter(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 1)); + return n ? (d.q = n[0] * 3 - 3, i + n[0].length) : -1; +} + +function parseMonthNumber(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.m = n[0] - 1, i + n[0].length) : -1; +} + +function parseDayOfMonth(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.d = +n[0], i + n[0].length) : -1; +} + +function parseDayOfYear(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 3)); + return n ? (d.m = 0, d.d = +n[0], i + n[0].length) : -1; +} + +function parseHour24(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.H = +n[0], i + n[0].length) : -1; +} + +function parseMinutes(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.M = +n[0], i + n[0].length) : -1; +} + +function parseSeconds(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.S = +n[0], i + n[0].length) : -1; +} + +function parseMilliseconds(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 3)); + return n ? (d.L = +n[0], i + n[0].length) : -1; +} + +function parseMicroseconds(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 6)); + return n ? (d.L = Math.floor(n[0] / 1000), i + n[0].length) : -1; +} + +function parseLiteralPercent(d, string, i) { + var n = percentRe.exec(string.slice(i, i + 1)); + return n ? i + n[0].length : -1; +} + +function parseUnixTimestamp(d, string, i) { + var n = numberRe.exec(string.slice(i)); + return n ? (d.Q = +n[0], i + n[0].length) : -1; +} + +function parseUnixTimestampSeconds(d, string, i) { + var n = numberRe.exec(string.slice(i)); + return n ? (d.s = +n[0], i + n[0].length) : -1; +} + +function formatDayOfMonth(d, p) { + return pad(d.getDate(), p, 2); +} + +function formatHour24(d, p) { + return pad(d.getHours(), p, 2); +} + +function formatHour12(d, p) { + return pad(d.getHours() % 12 || 12, p, 2); +} + +function formatDayOfYear(d, p) { + return pad(1 + d3Time.timeDay.count(d3Time.timeYear(d), d), p, 3); +} + +function formatMilliseconds(d, p) { + return pad(d.getMilliseconds(), p, 3); +} + +function formatMicroseconds(d, p) { + return formatMilliseconds(d, p) + "000"; +} + +function formatMonthNumber(d, p) { + return pad(d.getMonth() + 1, p, 2); +} + +function formatMinutes(d, p) { + return pad(d.getMinutes(), p, 2); +} + +function formatSeconds(d, p) { + return pad(d.getSeconds(), p, 2); +} + +function formatWeekdayNumberMonday(d) { + var day = d.getDay(); + return day === 0 ? 7 : day; +} + +function formatWeekNumberSunday(d, p) { + return pad(d3Time.timeSunday.count(d3Time.timeYear(d) - 1, d), p, 2); +} + +function dISO(d) { + var day = d.getDay(); + return (day >= 4 || day === 0) ? d3Time.timeThursday(d) : d3Time.timeThursday.ceil(d); +} + +function formatWeekNumberISO(d, p) { + d = dISO(d); + return pad(d3Time.timeThursday.count(d3Time.timeYear(d), d) + (d3Time.timeYear(d).getDay() === 4), p, 2); +} + +function formatWeekdayNumberSunday(d) { + return d.getDay(); +} + +function formatWeekNumberMonday(d, p) { + return pad(d3Time.timeMonday.count(d3Time.timeYear(d) - 1, d), p, 2); +} + +function formatYear(d, p) { + return pad(d.getFullYear() % 100, p, 2); +} + +function formatYearISO(d, p) { + d = dISO(d); + return pad(d.getFullYear() % 100, p, 2); +} + +function formatFullYear(d, p) { + return pad(d.getFullYear() % 10000, p, 4); +} + +function formatFullYearISO(d, p) { + var day = d.getDay(); + d = (day >= 4 || day === 0) ? d3Time.timeThursday(d) : d3Time.timeThursday.ceil(d); + return pad(d.getFullYear() % 10000, p, 4); +} + +function formatZone(d) { + var z = d.getTimezoneOffset(); + return (z > 0 ? "-" : (z *= -1, "+")) + + pad(z / 60 | 0, "0", 2) + + pad(z % 60, "0", 2); +} + +function formatUTCDayOfMonth(d, p) { + return pad(d.getUTCDate(), p, 2); +} + +function formatUTCHour24(d, p) { + return pad(d.getUTCHours(), p, 2); +} + +function formatUTCHour12(d, p) { + return pad(d.getUTCHours() % 12 || 12, p, 2); +} + +function formatUTCDayOfYear(d, p) { + return pad(1 + d3Time.utcDay.count(d3Time.utcYear(d), d), p, 3); +} + +function formatUTCMilliseconds(d, p) { + return pad(d.getUTCMilliseconds(), p, 3); +} + +function formatUTCMicroseconds(d, p) { + return formatUTCMilliseconds(d, p) + "000"; +} + +function formatUTCMonthNumber(d, p) { + return pad(d.getUTCMonth() + 1, p, 2); +} + +function formatUTCMinutes(d, p) { + return pad(d.getUTCMinutes(), p, 2); +} + +function formatUTCSeconds(d, p) { + return pad(d.getUTCSeconds(), p, 2); +} + +function formatUTCWeekdayNumberMonday(d) { + var dow = d.getUTCDay(); + return dow === 0 ? 7 : dow; +} + +function formatUTCWeekNumberSunday(d, p) { + return pad(d3Time.utcSunday.count(d3Time.utcYear(d) - 1, d), p, 2); +} + +function UTCdISO(d) { + var day = d.getUTCDay(); + return (day >= 4 || day === 0) ? d3Time.utcThursday(d) : d3Time.utcThursday.ceil(d); +} + +function formatUTCWeekNumberISO(d, p) { + d = UTCdISO(d); + return pad(d3Time.utcThursday.count(d3Time.utcYear(d), d) + (d3Time.utcYear(d).getUTCDay() === 4), p, 2); +} + +function formatUTCWeekdayNumberSunday(d) { + return d.getUTCDay(); +} + +function formatUTCWeekNumberMonday(d, p) { + return pad(d3Time.utcMonday.count(d3Time.utcYear(d) - 1, d), p, 2); +} + +function formatUTCYear(d, p) { + return pad(d.getUTCFullYear() % 100, p, 2); +} + +function formatUTCYearISO(d, p) { + d = UTCdISO(d); + return pad(d.getUTCFullYear() % 100, p, 2); +} + +function formatUTCFullYear(d, p) { + return pad(d.getUTCFullYear() % 10000, p, 4); +} + +function formatUTCFullYearISO(d, p) { + var day = d.getUTCDay(); + d = (day >= 4 || day === 0) ? d3Time.utcThursday(d) : d3Time.utcThursday.ceil(d); + return pad(d.getUTCFullYear() % 10000, p, 4); +} + +function formatUTCZone() { + return "+0000"; +} + +function formatLiteralPercent() { + return "%"; +} + +function formatUnixTimestamp(d) { + return +d; +} + +function formatUnixTimestampSeconds(d) { + return Math.floor(+d / 1000); +} + +var locale; +exports.timeFormat = void 0; +exports.timeParse = void 0; +exports.utcFormat = void 0; +exports.utcParse = void 0; + +defaultLocale({ + dateTime: "%x, %X", + date: "%-m/%-d/%Y", + time: "%-I:%M:%S %p", + periods: ["AM", "PM"], + days: ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"], + shortDays: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"], + months: ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"], + shortMonths: ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"] +}); + +function defaultLocale(definition) { + locale = formatLocale(definition); + exports.timeFormat = locale.format; + exports.timeParse = locale.parse; + exports.utcFormat = locale.utcFormat; + exports.utcParse = locale.utcParse; + return locale; +} + +var isoSpecifier = "%Y-%m-%dT%H:%M:%S.%LZ"; + +function formatIsoNative(date) { + return date.toISOString(); +} + +var formatIso = Date.prototype.toISOString + ? formatIsoNative + : exports.utcFormat(isoSpecifier); + +function parseIsoNative(string) { + var date = new Date(string); + return isNaN(date) ? null : date; +} + +var parseIso = +new Date("2000-01-01T00:00:00.000Z") + ? parseIsoNative + : exports.utcParse(isoSpecifier); + +exports.isoFormat = formatIso; +exports.isoParse = parseIso; +exports.timeFormatDefaultLocale = defaultLocale; +exports.timeFormatLocale = formatLocale; + +Object.defineProperty(exports, '__esModule', { value: true }); + +})); diff --git a/frontend/node_modules/d3-time-format/dist/d3-time-format.min.js b/frontend/node_modules/d3-time-format/dist/d3-time-format.min.js new file mode 100644 index 0000000..816bce2 --- /dev/null +++ b/frontend/node_modules/d3-time-format/dist/d3-time-format.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-time-format/ v4.1.0 Copyright 2010-2021 Mike Bostock +!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports,require("d3-time")):"function"==typeof define&&define.amd?define(["exports","d3-time"],t):t((e="undefined"!=typeof globalThis?globalThis:e||self).d3=e.d3||{},e.d3)}(this,(function(e,t){"use strict";function n(e){if(0<=e.y&&e.y<100){var t=new Date(-1,e.m,e.d,e.H,e.M,e.S,e.L);return t.setFullYear(e.y),t}return new Date(e.y,e.m,e.d,e.H,e.M,e.S,e.L)}function r(e){if(0<=e.y&&e.y<100){var t=new Date(Date.UTC(-1,e.m,e.d,e.H,e.M,e.S,e.L));return t.setUTCFullYear(e.y),t}return new Date(Date.UTC(e.y,e.m,e.d,e.H,e.M,e.S,e.L))}function u(e,t,n){return{y:e,m:t,d:n,H:0,M:0,S:0,L:0}}function i(e){var i=e.dateTime,c=e.date,a=e.time,f=e.periods,l=e.days,s=e.shortDays,g=e.months,G=e.shortMonths,ge=d(f),pe=y(f),we=d(l),Se=y(l),Ye=d(s),Fe=y(s),Le=d(g),He=y(g),Ae=d(G),Ze=y(G),be={a:function(e){return s[e.getDay()]},A:function(e){return l[e.getDay()]},b:function(e){return G[e.getMonth()]},B:function(e){return g[e.getMonth()]},c:null,d:W,e:W,f:J,g:R,G:K,H:V,I:j,j:q,L:I,m:O,M:Q,p:function(e){return f[+(e.getHours()>=12)]},q:function(e){return 1+~~(e.getMonth()/3)},Q:Ue,s:xe,S:X,u:N,U:B,V:_,w:$,W:z,x:null,X:null,y:E,Y:k,Z:ee,"%":Ce},Pe={a:function(e){return s[e.getUTCDay()]},A:function(e){return l[e.getUTCDay()]},b:function(e){return G[e.getUTCMonth()]},B:function(e){return g[e.getUTCMonth()]},c:null,d:te,e:te,f:ce,g:ve,G:Me,H:ne,I:re,j:ue,L:ie,m:oe,M:ae,p:function(e){return f[+(e.getUTCHours()>=12)]},q:function(e){return 1+~~(e.getUTCMonth()/3)},Q:Ue,s:xe,S:fe,u:le,U:se,V:de,w:ye,W:he,x:null,X:null,y:me,Y:Te,Z:De,"%":Ce},We={a:function(e,t,n){var r=Ye.exec(t.slice(n));return r?(e.w=Fe.get(r[0].toLowerCase()),n+r[0].length):-1},A:function(e,t,n){var r=we.exec(t.slice(n));return r?(e.w=Se.get(r[0].toLowerCase()),n+r[0].length):-1},b:function(e,t,n){var r=Ae.exec(t.slice(n));return r?(e.m=Ze.get(r[0].toLowerCase()),n+r[0].length):-1},B:function(e,t,n){var r=Le.exec(t.slice(n));return r?(e.m=He.get(r[0].toLowerCase()),n+r[0].length):-1},c:function(e,t,n){return qe(e,i,t,n)},d:w,e:w,f:A,g:C,G:D,H:Y,I:Y,j:S,L:H,m:p,M:F,p:function(e,t,n){var r=ge.exec(t.slice(n));return r?(e.p=pe.get(r[0].toLowerCase()),n+r[0].length):-1},q:x,Q:b,s:P,S:L,u:m,U:v,V:T,w:h,W:M,x:function(e,t,n){return qe(e,c,t,n)},X:function(e,t,n){return qe(e,a,t,n)},y:C,Y:D,Z:U,"%":Z};function Ve(e,t){return function(n){var r,u,i,c=[],a=-1,f=0,l=e.length;for(n instanceof Date||(n=new Date(+n));++a53)return null;"w"in f||(f.w=1),"Z"in f?(a=(o=r(u(f.y,0,1))).getUTCDay(),o=a>4||0===a?t.utcMonday.ceil(o):t.utcMonday(o),o=t.utcDay.offset(o,7*(f.V-1)),f.y=o.getUTCFullYear(),f.m=o.getUTCMonth(),f.d=o.getUTCDate()+(f.w+6)%7):(a=(o=n(u(f.y,0,1))).getDay(),o=a>4||0===a?t.timeMonday.ceil(o):t.timeMonday(o),o=t.timeDay.offset(o,7*(f.V-1)),f.y=o.getFullYear(),f.m=o.getMonth(),f.d=o.getDate()+(f.w+6)%7)}else("W"in f||"U"in f)&&("w"in f||(f.w="u"in f?f.u%7:"W"in f?1:0),a="Z"in f?r(u(f.y,0,1)).getUTCDay():n(u(f.y,0,1)).getDay(),f.m=0,f.d="W"in f?(f.w+6)%7+7*f.W-(a+5)%7:f.w+7*f.U-(a+6)%7);return"Z"in f?(f.H+=f.Z/100|0,f.M+=f.Z%100,r(f)):n(f)}}function qe(e,t,n,r){for(var u,i,c=0,a=t.length,f=n.length;c=f)return-1;if(37===(u=t.charCodeAt(c++))){if(u=t.charAt(c++),!(i=We[u in o?t.charAt(c++):u])||(r=i(e,n,r))<0)return-1}else if(u!=n.charCodeAt(r++))return-1}return r}return be.x=Ve(c,be),be.X=Ve(a,be),be.c=Ve(i,be),Pe.x=Ve(c,Pe),Pe.X=Ve(a,Pe),Pe.c=Ve(i,Pe),{format:function(e){var t=Ve(e+="",be);return t.toString=function(){return e},t},parse:function(e){var t=je(e+="",!1);return t.toString=function(){return e},t},utcFormat:function(e){var t=Ve(e+="",Pe);return t.toString=function(){return e},t},utcParse:function(e){var t=je(e+="",!0);return t.toString=function(){return e},t}}}var c,o={"-":"",_:" ",0:"0"},a=/^\s*\d+/,f=/^%/,l=/[\\^$*+?|[\]().{}]/g;function s(e,t,n){var r=e<0?"-":"",u=(r?-e:e)+"",i=u.length;return r+(i[e.toLowerCase(),t])))}function h(e,t,n){var r=a.exec(t.slice(n,n+1));return r?(e.w=+r[0],n+r[0].length):-1}function m(e,t,n){var r=a.exec(t.slice(n,n+1));return r?(e.u=+r[0],n+r[0].length):-1}function v(e,t,n){var r=a.exec(t.slice(n,n+2));return r?(e.U=+r[0],n+r[0].length):-1}function T(e,t,n){var r=a.exec(t.slice(n,n+2));return r?(e.V=+r[0],n+r[0].length):-1}function M(e,t,n){var r=a.exec(t.slice(n,n+2));return r?(e.W=+r[0],n+r[0].length):-1}function D(e,t,n){var r=a.exec(t.slice(n,n+4));return r?(e.y=+r[0],n+r[0].length):-1}function C(e,t,n){var r=a.exec(t.slice(n,n+2));return r?(e.y=+r[0]+(+r[0]>68?1900:2e3),n+r[0].length):-1}function U(e,t,n){var r=/^(Z)|([+-]\d\d)(?::?(\d\d))?/.exec(t.slice(n,n+6));return r?(e.Z=r[1]?0:-(r[2]+(r[3]||"00")),n+r[0].length):-1}function x(e,t,n){var r=a.exec(t.slice(n,n+1));return r?(e.q=3*r[0]-3,n+r[0].length):-1}function p(e,t,n){var r=a.exec(t.slice(n,n+2));return r?(e.m=r[0]-1,n+r[0].length):-1}function w(e,t,n){var r=a.exec(t.slice(n,n+2));return r?(e.d=+r[0],n+r[0].length):-1}function S(e,t,n){var r=a.exec(t.slice(n,n+3));return r?(e.m=0,e.d=+r[0],n+r[0].length):-1}function Y(e,t,n){var r=a.exec(t.slice(n,n+2));return r?(e.H=+r[0],n+r[0].length):-1}function F(e,t,n){var r=a.exec(t.slice(n,n+2));return r?(e.M=+r[0],n+r[0].length):-1}function L(e,t,n){var r=a.exec(t.slice(n,n+2));return r?(e.S=+r[0],n+r[0].length):-1}function H(e,t,n){var r=a.exec(t.slice(n,n+3));return r?(e.L=+r[0],n+r[0].length):-1}function A(e,t,n){var r=a.exec(t.slice(n,n+6));return r?(e.L=Math.floor(r[0]/1e3),n+r[0].length):-1}function Z(e,t,n){var r=f.exec(t.slice(n,n+1));return r?n+r[0].length:-1}function b(e,t,n){var r=a.exec(t.slice(n));return r?(e.Q=+r[0],n+r[0].length):-1}function P(e,t,n){var r=a.exec(t.slice(n));return r?(e.s=+r[0],n+r[0].length):-1}function W(e,t){return s(e.getDate(),t,2)}function V(e,t){return s(e.getHours(),t,2)}function j(e,t){return s(e.getHours()%12||12,t,2)}function q(e,n){return s(1+t.timeDay.count(t.timeYear(e),e),n,3)}function I(e,t){return s(e.getMilliseconds(),t,3)}function J(e,t){return I(e,t)+"000"}function O(e,t){return s(e.getMonth()+1,t,2)}function Q(e,t){return s(e.getMinutes(),t,2)}function X(e,t){return s(e.getSeconds(),t,2)}function N(e){var t=e.getDay();return 0===t?7:t}function B(e,n){return s(t.timeSunday.count(t.timeYear(e)-1,e),n,2)}function G(e){var n=e.getDay();return n>=4||0===n?t.timeThursday(e):t.timeThursday.ceil(e)}function _(e,n){return e=G(e),s(t.timeThursday.count(t.timeYear(e),e)+(4===t.timeYear(e).getDay()),n,2)}function $(e){return e.getDay()}function z(e,n){return s(t.timeMonday.count(t.timeYear(e)-1,e),n,2)}function E(e,t){return s(e.getFullYear()%100,t,2)}function R(e,t){return s((e=G(e)).getFullYear()%100,t,2)}function k(e,t){return s(e.getFullYear()%1e4,t,4)}function K(e,n){var r=e.getDay();return s((e=r>=4||0===r?t.timeThursday(e):t.timeThursday.ceil(e)).getFullYear()%1e4,n,4)}function ee(e){var t=e.getTimezoneOffset();return(t>0?"-":(t*=-1,"+"))+s(t/60|0,"0",2)+s(t%60,"0",2)}function te(e,t){return s(e.getUTCDate(),t,2)}function ne(e,t){return s(e.getUTCHours(),t,2)}function re(e,t){return s(e.getUTCHours()%12||12,t,2)}function ue(e,n){return s(1+t.utcDay.count(t.utcYear(e),e),n,3)}function ie(e,t){return s(e.getUTCMilliseconds(),t,3)}function ce(e,t){return ie(e,t)+"000"}function oe(e,t){return s(e.getUTCMonth()+1,t,2)}function ae(e,t){return s(e.getUTCMinutes(),t,2)}function fe(e,t){return s(e.getUTCSeconds(),t,2)}function le(e){var t=e.getUTCDay();return 0===t?7:t}function se(e,n){return s(t.utcSunday.count(t.utcYear(e)-1,e),n,2)}function ge(e){var n=e.getUTCDay();return n>=4||0===n?t.utcThursday(e):t.utcThursday.ceil(e)}function de(e,n){return e=ge(e),s(t.utcThursday.count(t.utcYear(e),e)+(4===t.utcYear(e).getUTCDay()),n,2)}function ye(e){return e.getUTCDay()}function he(e,n){return s(t.utcMonday.count(t.utcYear(e)-1,e),n,2)}function me(e,t){return s(e.getUTCFullYear()%100,t,2)}function ve(e,t){return s((e=ge(e)).getUTCFullYear()%100,t,2)}function Te(e,t){return s(e.getUTCFullYear()%1e4,t,4)}function Me(e,n){var r=e.getUTCDay();return s((e=r>=4||0===r?t.utcThursday(e):t.utcThursday.ceil(e)).getUTCFullYear()%1e4,n,4)}function De(){return"+0000"}function Ce(){return"%"}function Ue(e){return+e}function xe(e){return Math.floor(+e/1e3)}function pe(t){return c=i(t),e.timeFormat=c.format,e.timeParse=c.parse,e.utcFormat=c.utcFormat,e.utcParse=c.utcParse,c}e.timeFormat=void 0,e.timeParse=void 0,e.utcFormat=void 0,e.utcParse=void 0,pe({dateTime:"%x, %X",date:"%-m/%-d/%Y",time:"%-I:%M:%S %p",periods:["AM","PM"],days:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],shortDays:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],months:["January","February","March","April","May","June","July","August","September","October","November","December"],shortMonths:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"]});var we="%Y-%m-%dT%H:%M:%S.%LZ";var Se=Date.prototype.toISOString?function(e){return e.toISOString()}:e.utcFormat(we);var Ye=+new Date("2000-01-01T00:00:00.000Z")?function(e){var t=new Date(e);return isNaN(t)?null:t}:e.utcParse(we);e.isoFormat=Se,e.isoParse=Ye,e.timeFormatDefaultLocale=pe,e.timeFormatLocale=i,Object.defineProperty(e,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-time-format/locale/ar-EG.json b/frontend/node_modules/d3-time-format/locale/ar-EG.json new file mode 100644 index 0000000..8ac0265 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/ar-EG.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%x, %X", + "date": "%-d/%-m/%Y", + "time": "%-I:%M:%S %p", + "periods": ["ص", "م"], + "days": ["الأحد", "الإثنين", "الثلاثاء", "الأربعاء", "الخميس", "الجمعة", "السبت"], + "shortDays": ["أحد", "إثنين", "ثلاثاء", "أربعاء", "خميس", "جمعة", "سبت"], + "months": ["يناير", "فبراير", "مارس", "أبريل", "مايو", "يونيو", "يوليو", "أغسطس", "سبتمبر", "أكتوبر", "نوفمبر", "ديسمبر"], + "shortMonths": ["يناير", "فبراير", "مارس", "أبريل", "مايو", "يونيو", "يوليو", "أغسطس", "سبتمبر", "أكتوبر", "نوفمبر", "ديسمبر"] +} diff --git a/frontend/node_modules/d3-time-format/locale/ar-SY.json b/frontend/node_modules/d3-time-format/locale/ar-SY.json new file mode 100644 index 0000000..866fa5e --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/ar-SY.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%x, %X", + "date": "%-d/%-m/%Y", + "time": "%-I:%M:%S %p", + "periods": ["ص", "م"], + "days": ["الأحد", "الإثنين", "الثلاثاء", "الأربعاء", "الخميس", "الجمعة", "السبت"], + "shortDays": ["أحد", "إثنين", "ثلاثاء", "أربعاء", "خميس", "جمعة", "سبت"], + "months": ["كانون الثاني", "شباط", "آذار", "نيسان", "أيار", "حزيران", "تموز", "آب", "أيلول", "تشرين الأول", "تشرين الثاني", "كانون الأول"], + "shortMonths": ["ك٢", "شباط", "آذار", "نيسان", "أيار", "حزيران", "تموز", "آب", "أيلول", "ت١", "ت٢", "ك١"] +} diff --git a/frontend/node_modules/d3-time-format/locale/ca-ES.json b/frontend/node_modules/d3-time-format/locale/ca-ES.json new file mode 100644 index 0000000..a270873 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/ca-ES.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A, %e de %B de %Y, %X", + "date": "%d/%m/%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["diumenge", "dilluns", "dimarts", "dimecres", "dijous", "divendres", "dissabte"], + "shortDays": ["dg.", "dl.", "dt.", "dc.", "dj.", "dv.", "ds."], + "months": ["gener", "febrer", "març", "abril", "maig", "juny", "juliol", "agost", "setembre", "octubre", "novembre", "desembre"], + "shortMonths": ["gen.", "febr.", "març", "abr.", "maig", "juny", "jul.", "ag.", "set.", "oct.", "nov.", "des."] +} diff --git a/frontend/node_modules/d3-time-format/locale/cs-CZ.json b/frontend/node_modules/d3-time-format/locale/cs-CZ.json new file mode 100644 index 0000000..ced34ea --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/cs-CZ.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A,%e.%B %Y, %X", + "date": "%-d.%-m.%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["neděle", "pondělí", "úterý", "středa", "čvrtek", "pátek", "sobota"], + "shortDays": ["ne.", "po.", "út.", "st.", "čt.", "pá.", "so."], + "months": ["leden", "únor", "březen", "duben", "květen", "červen", "červenec", "srpen", "září", "říjen", "listopad", "prosinec"], + "shortMonths": ["led", "úno", "břez", "dub", "kvě", "čer", "červ", "srp", "zář", "říj", "list", "pros"] +} diff --git a/frontend/node_modules/d3-time-format/locale/da-DK.json b/frontend/node_modules/d3-time-format/locale/da-DK.json new file mode 100644 index 0000000..f0c2349 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/da-DK.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A den %d %B %Y %X", + "date": "%d-%m-%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["søndag", "mandag", "tirsdag", "onsdag", "torsdag", "fredag", "lørdag"], + "shortDays": ["søn", "man", "tir", "ons", "tor", "fre", "lør"], + "months": ["januar", "februar", "marts", "april", "maj", "juni", "juli", "august", "september", "oktober", "november", "december"], + "shortMonths": ["jan", "feb", "mar", "apr", "maj", "jun", "jul", "aug", "sep", "okt", "nov", "dec"] +} diff --git a/frontend/node_modules/d3-time-format/locale/de-CH.json b/frontend/node_modules/d3-time-format/locale/de-CH.json new file mode 100644 index 0000000..466b749 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/de-CH.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A, der %e. %B %Y, %X", + "date": "%d.%m.%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["Sonntag", "Montag", "Dienstag", "Mittwoch", "Donnerstag", "Freitag", "Samstag"], + "shortDays": ["So", "Mo", "Di", "Mi", "Do", "Fr", "Sa"], + "months": ["Januar", "Februar", "März", "April", "Mai", "Juni", "Juli", "August", "September", "Oktober", "November", "Dezember"], + "shortMonths": ["Jan", "Feb", "Mrz", "Apr", "Mai", "Jun", "Jul", "Aug", "Sep", "Okt", "Nov", "Dez"] +} diff --git a/frontend/node_modules/d3-time-format/locale/de-DE.json b/frontend/node_modules/d3-time-format/locale/de-DE.json new file mode 100644 index 0000000..466b749 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/de-DE.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A, der %e. %B %Y, %X", + "date": "%d.%m.%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["Sonntag", "Montag", "Dienstag", "Mittwoch", "Donnerstag", "Freitag", "Samstag"], + "shortDays": ["So", "Mo", "Di", "Mi", "Do", "Fr", "Sa"], + "months": ["Januar", "Februar", "März", "April", "Mai", "Juni", "Juli", "August", "September", "Oktober", "November", "Dezember"], + "shortMonths": ["Jan", "Feb", "Mrz", "Apr", "Mai", "Jun", "Jul", "Aug", "Sep", "Okt", "Nov", "Dez"] +} diff --git a/frontend/node_modules/d3-time-format/locale/en-CA.json b/frontend/node_modules/d3-time-format/locale/en-CA.json new file mode 100644 index 0000000..5c13ae3 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/en-CA.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%a %b %e %X %Y", + "date": "%Y-%m-%d", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"], + "shortDays": ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"], + "months": ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"], + "shortMonths": ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"] +} diff --git a/frontend/node_modules/d3-time-format/locale/en-GB.json b/frontend/node_modules/d3-time-format/locale/en-GB.json new file mode 100644 index 0000000..9f651c5 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/en-GB.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%a %e %b %X %Y", + "date": "%d/%m/%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"], + "shortDays": ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"], + "months": ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"], + "shortMonths": ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"] +} diff --git a/frontend/node_modules/d3-time-format/locale/en-US.json b/frontend/node_modules/d3-time-format/locale/en-US.json new file mode 100644 index 0000000..a7ac951 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/en-US.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%x, %X", + "date": "%-m/%-d/%Y", + "time": "%-I:%M:%S %p", + "periods": ["AM", "PM"], + "days": ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"], + "shortDays": ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"], + "months": ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"], + "shortMonths": ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"] +} diff --git a/frontend/node_modules/d3-time-format/locale/es-ES.json b/frontend/node_modules/d3-time-format/locale/es-ES.json new file mode 100644 index 0000000..8c5f754 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/es-ES.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A, %e de %B de %Y, %X", + "date": "%d/%m/%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["domingo", "lunes", "martes", "miércoles", "jueves", "viernes", "sábado"], + "shortDays": ["dom", "lun", "mar", "mié", "jue", "vie", "sáb"], + "months": ["enero", "febrero", "marzo", "abril", "mayo", "junio", "julio", "agosto", "septiembre", "octubre", "noviembre", "diciembre"], + "shortMonths": ["ene", "feb", "mar", "abr", "may", "jun", "jul", "ago", "sep", "oct", "nov", "dic"] +} diff --git a/frontend/node_modules/d3-time-format/locale/es-MX.json b/frontend/node_modules/d3-time-format/locale/es-MX.json new file mode 100644 index 0000000..4dc2077 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/es-MX.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%x, %X", + "date": "%d/%m/%Y", + "time": "%-I:%M:%S %p", + "periods": ["AM", "PM"], + "days": ["domingo", "lunes", "martes", "miércoles", "jueves", "viernes", "sábado"], + "shortDays": ["dom", "lun", "mar", "mié", "jue", "vie", "sáb"], + "months": ["enero", "febrero", "marzo", "abril", "mayo", "junio", "julio", "agosto", "septiembre", "octubre", "noviembre", "diciembre"], + "shortMonths": ["ene", "feb", "mar", "abr", "may", "jun", "jul", "ago", "sep", "oct", "nov", "dic"] +} diff --git a/frontend/node_modules/d3-time-format/locale/fa-IR.json b/frontend/node_modules/d3-time-format/locale/fa-IR.json new file mode 100644 index 0000000..badff07 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/fa-IR.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%x, %X", + "date": "%-d/%-m/%Y", + "time": "%-I:%M:%S %p", + "periods": ["صبح", "عصر"], + "days": ["یکشنبه", "دوشنبه", "سه شنبه", "چهارشنبه", "پنجشنبه", "جمعه", "شنبه"], + "shortDays": ["یکشنبه", "دوشنبه", "سه شنبه", "چهارشنبه", "پنجشنبه", "جمعه", "شنبه"], + "months": ["ژانویه", "فوریه", "مارس", "آوریل", "مه", "ژوئن", "ژوئیه", "اوت", "سپتامبر", "اکتبر", "نوامبر", "دسامبر"], + "shortMonths": ["ژانویه", "فوریه", "مارس", "آوریل", "مه", "ژوئن", "ژوئیه", "اوت", "سپتامبر", "اکتبر", "نوامبر", "دسامبر"] +} diff --git a/frontend/node_modules/d3-time-format/locale/fi-FI.json b/frontend/node_modules/d3-time-format/locale/fi-FI.json new file mode 100644 index 0000000..2422199 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/fi-FI.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A, %-d. %Bta %Y klo %X", + "date": "%-d.%-m.%Y", + "time": "%H:%M:%S", + "periods": ["a.m.", "p.m."], + "days": ["sunnuntai", "maanantai", "tiistai", "keskiviikko", "torstai", "perjantai", "lauantai"], + "shortDays": ["Su", "Ma", "Ti", "Ke", "To", "Pe", "La"], + "months": ["tammikuu", "helmikuu", "maaliskuu", "huhtikuu", "toukokuu", "kesäkuu", "heinäkuu", "elokuu", "syyskuu", "lokakuu", "marraskuu", "joulukuu"], + "shortMonths": ["Tammi", "Helmi", "Maalis", "Huhti", "Touko", "Kesä", "Heinä", "Elo", "Syys", "Loka", "Marras", "Joulu"] +} diff --git a/frontend/node_modules/d3-time-format/locale/fr-CA.json b/frontend/node_modules/d3-time-format/locale/fr-CA.json new file mode 100644 index 0000000..1300cab --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/fr-CA.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%a %e %b %Y %X", + "date": "%Y-%m-%d", + "time": "%H:%M:%S", + "periods": ["", ""], + "days": ["dimanche", "lundi", "mardi", "mercredi", "jeudi", "vendredi", "samedi"], + "shortDays": ["dim", "lun", "mar", "mer", "jeu", "ven", "sam"], + "months": ["janvier", "février", "mars", "avril", "mai", "juin", "juillet", "août", "septembre", "octobre", "novembre", "décembre"], + "shortMonths": ["jan", "fév", "mar", "avr", "mai", "jui", "jul", "aoû", "sep", "oct", "nov", "déc"] +} diff --git a/frontend/node_modules/d3-time-format/locale/fr-FR.json b/frontend/node_modules/d3-time-format/locale/fr-FR.json new file mode 100644 index 0000000..6ac05ee --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/fr-FR.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A %e %B %Y à %X", + "date": "%d/%m/%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["dimanche", "lundi", "mardi", "mercredi", "jeudi", "vendredi", "samedi"], + "shortDays": ["dim.", "lun.", "mar.", "mer.", "jeu.", "ven.", "sam."], + "months": ["janvier", "février", "mars", "avril", "mai", "juin", "juillet", "août", "septembre", "octobre", "novembre", "décembre"], + "shortMonths": ["janv.", "févr.", "mars", "avr.", "mai", "juin", "juil.", "août", "sept.", "oct.", "nov.", "déc."] +} diff --git a/frontend/node_modules/d3-time-format/locale/he-IL.json b/frontend/node_modules/d3-time-format/locale/he-IL.json new file mode 100644 index 0000000..0ce27cd --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/he-IL.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A, %e ב%B %Y %X", + "date": "%d.%m.%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["ראשון", "שני", "שלישי", "רביעי", "חמישי", "שישי", "שבת"], + "shortDays": ["א׳", "ב׳", "ג׳", "ד׳", "ה׳", "ו׳", "ש׳"], + "months": ["ינואר", "פברואר", "מרץ", "אפריל", "מאי", "יוני", "יולי", "אוגוסט", "ספטמבר", "אוקטובר", "נובמבר", "דצמבר"], + "shortMonths": ["ינו׳", "פבר׳", "מרץ", "אפר׳", "מאי", "יוני", "יולי", "אוג׳", "ספט׳", "אוק׳", "נוב׳", "דצמ׳"] +} diff --git a/frontend/node_modules/d3-time-format/locale/hr-HR.json b/frontend/node_modules/d3-time-format/locale/hr-HR.json new file mode 100644 index 0000000..b82dea6 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/hr-HR.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A, %e. %B %Y., %X", + "date": "%d. %m. %Y.", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["Nedjelja", "Ponedjeljak", "Utorak", "Srijeda", "Četvtrak", "Petak", "Subota"], + "shortDays": ["Ne", "Po", "Ut", "Sr", "Če", "Pe", "Su"], + "months": ["Siječanj", "Veljača", "Ožujak", "Travanj", "Svibanj", "Lipanj", "Srpanj", "Kolovoz", "Rujan", "Listopad", "Studeni", "Prosinac"], + "shortMonths": ["Sij", "Velj", "Ožu", "Tra", "Svi", "Lip", "Srp", "Kol", "Ruj", "Lis", "Stu", "Pro"] +} diff --git a/frontend/node_modules/d3-time-format/locale/hu-HU.json b/frontend/node_modules/d3-time-format/locale/hu-HU.json new file mode 100644 index 0000000..d81acf2 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/hu-HU.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%Y. %B %-e., %A %X", + "date": "%Y. %m. %d.", + "time": "%H:%M:%S", + "periods": ["de.", "du."], + "days": ["vasárnap", "hétfő", "kedd", "szerda", "csütörtök", "péntek", "szombat"], + "shortDays": ["V", "H", "K", "Sze", "Cs", "P", "Szo"], + "months": ["január", "február", "március", "április", "május", "június", "július", "augusztus", "szeptember", "október", "november", "december"], + "shortMonths": ["jan.", "feb.", "már.", "ápr.", "máj.", "jún.", "júl.", "aug.", "szept.", "okt.", "nov.", "dec."] +} diff --git a/frontend/node_modules/d3-time-format/locale/it-IT.json b/frontend/node_modules/d3-time-format/locale/it-IT.json new file mode 100644 index 0000000..0fc08e0 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/it-IT.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A %e %B %Y, %X", + "date": "%d/%m/%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["Domenica", "Lunedì", "Martedì", "Mercoledì", "Giovedì", "Venerdì", "Sabato"], + "shortDays": ["Dom", "Lun", "Mar", "Mer", "Gio", "Ven", "Sab"], + "months": ["Gennaio", "Febbraio", "Marzo", "Aprile", "Maggio", "Giugno", "Luglio", "Agosto", "Settembre", "Ottobre", "Novembre", "Dicembre"], + "shortMonths": ["Gen", "Feb", "Mar", "Apr", "Mag", "Giu", "Lug", "Ago", "Set", "Ott", "Nov", "Dic"] +} diff --git a/frontend/node_modules/d3-time-format/locale/ja-JP.json b/frontend/node_modules/d3-time-format/locale/ja-JP.json new file mode 100644 index 0000000..72c460d --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/ja-JP.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%x %a %X", + "date": "%Y/%m/%d", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["日曜日", "月曜日", "火曜日", "水曜日", "木曜日", "金曜日", "土曜日"], + "shortDays": ["日", "月", "火", "水", "木", "金", "土"], + "months": ["1月", "2月", "3月", "4月", "5月", "6月", "7月", "8月", "9月", "10月", "11月", "12月"], + "shortMonths": ["1月", "2月", "3月", "4月", "5月", "6月", "7月", "8月", "9月", "10月", "11月", "12月"] +} diff --git a/frontend/node_modules/d3-time-format/locale/ko-KR.json b/frontend/node_modules/d3-time-format/locale/ko-KR.json new file mode 100644 index 0000000..7055666 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/ko-KR.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%Y/%m/%d %a %X", + "date": "%Y/%m/%d", + "time": "%H:%M:%S", + "periods": ["오전", "오후"], + "days": ["일요일", "월요일", "화요일", "수요일", "목요일", "금요일", "토요일"], + "shortDays": ["일", "월", "화", "수", "목", "금", "토"], + "months": ["1월", "2월", "3월", "4월", "5월", "6월", "7월", "8월", "9월", "10월", "11월", "12월"], + "shortMonths": ["1월", "2월", "3월", "4월", "5월", "6월", "7월", "8월", "9월", "10월", "11월", "12월"] +} diff --git a/frontend/node_modules/d3-time-format/locale/mk-MK.json b/frontend/node_modules/d3-time-format/locale/mk-MK.json new file mode 100644 index 0000000..4a47fd1 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/mk-MK.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A, %e %B %Y г. %X", + "date": "%d.%m.%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["недела", "понеделник", "вторник", "среда", "четврток", "петок", "сабота"], + "shortDays": ["нед", "пон", "вто", "сре", "чет", "пет", "саб"], + "months": ["јануари", "февруари", "март", "април", "мај", "јуни", "јули", "август", "септември", "октомври", "ноември", "декември"], + "shortMonths": ["јан", "фев", "мар", "апр", "мај", "јун", "јул", "авг", "сеп", "окт", "ное", "дек"] +} diff --git a/frontend/node_modules/d3-time-format/locale/nb-NO.json b/frontend/node_modules/d3-time-format/locale/nb-NO.json new file mode 100644 index 0000000..a8bfd20 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/nb-NO.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A den %d. %B %Y %X", + "date": "%d.%m.%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["søndag", "mandag", "tirsdag", "onsdag", "torsdag", "fredag", "lørdag"], + "shortDays": ["søn", "man", "tir", "ons", "tor", "fre", "lør"], + "months": ["januar", "februar", "mars", "april", "mai", "juni", "juli", "august", "september", "oktober", "november", "desember"], + "shortMonths": ["jan", "feb", "mars", "apr", "mai", "juni", "juli", "aug", "sep", "okt", "nov", "des"] +} diff --git a/frontend/node_modules/d3-time-format/locale/nl-BE.json b/frontend/node_modules/d3-time-format/locale/nl-BE.json new file mode 100644 index 0000000..69d587e --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/nl-BE.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%a %e %B %Y %X", + "date": "%d/%m/%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["zondag", "maandag", "dinsdag", "woensdag", "donderdag", "vrijdag", "zaterdag"], + "shortDays": ["zo", "ma", "di", "wo", "do", "vr", "za"], + "months": ["januari", "februari", "maart", "april", "mei", "juni", "juli", "augustus", "september", "oktober", "november", "december"], + "shortMonths": ["jan", "feb", "mrt", "apr", "mei", "jun", "jul", "aug", "sep", "okt", "nov", "dec"] +} diff --git a/frontend/node_modules/d3-time-format/locale/nl-NL.json b/frontend/node_modules/d3-time-format/locale/nl-NL.json new file mode 100644 index 0000000..375b0fe --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/nl-NL.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%a %e %B %Y %X", + "date": "%d-%m-%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["zondag", "maandag", "dinsdag", "woensdag", "donderdag", "vrijdag", "zaterdag"], + "shortDays": ["zo", "ma", "di", "wo", "do", "vr", "za"], + "months": ["januari", "februari", "maart", "april", "mei", "juni", "juli", "augustus", "september", "oktober", "november", "december"], + "shortMonths": ["jan", "feb", "mrt", "apr", "mei", "jun", "jul", "aug", "sep", "okt", "nov", "dec"] +} diff --git a/frontend/node_modules/d3-time-format/locale/pl-PL.json b/frontend/node_modules/d3-time-format/locale/pl-PL.json new file mode 100644 index 0000000..616b4cd --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/pl-PL.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A, %e %B %Y, %X", + "date": "%d/%m/%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["Niedziela", "Poniedziałek", "Wtorek", "Środa", "Czwartek", "Piątek", "Sobota"], + "shortDays": ["Niedz.", "Pon.", "Wt.", "Śr.", "Czw.", "Pt.", "Sob."], + "months": ["Styczeń", "Luty", "Marzec", "Kwiecień", "Maj", "Czerwiec", "Lipiec", "Sierpień", "Wrzesień", "Październik", "Listopad", "Grudzień"], + "shortMonths": ["Stycz.", "Luty", "Marz.", "Kwie.", "Maj", "Czerw.", "Lipc.", "Sierp.", "Wrz.", "Paźdz.", "Listop.", "Grudz."] +} diff --git a/frontend/node_modules/d3-time-format/locale/pt-BR.json b/frontend/node_modules/d3-time-format/locale/pt-BR.json new file mode 100644 index 0000000..4e9ff89 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/pt-BR.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A, %e de %B de %Y. %X", + "date": "%d/%m/%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["Domingo", "Segunda", "Terça", "Quarta", "Quinta", "Sexta", "Sábado"], + "shortDays": ["Dom", "Seg", "Ter", "Qua", "Qui", "Sex", "Sáb"], + "months": ["Janeiro", "Fevereiro", "Março", "Abril", "Maio", "Junho", "Julho", "Agosto", "Setembro", "Outubro", "Novembro", "Dezembro"], + "shortMonths": ["Jan", "Fev", "Mar", "Abr", "Mai", "Jun", "Jul", "Ago", "Set", "Out", "Nov", "Dez"] +} diff --git a/frontend/node_modules/d3-time-format/locale/ru-RU.json b/frontend/node_modules/d3-time-format/locale/ru-RU.json new file mode 100644 index 0000000..c042318 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/ru-RU.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A, %e %B %Y г. %X", + "date": "%d.%m.%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["воскресенье", "понедельник", "вторник", "среда", "четверг", "пятница", "суббота"], + "shortDays": ["вс", "пн", "вт", "ср", "чт", "пт", "сб"], + "months": ["января", "февраля", "марта", "апреля", "мая", "июня", "июля", "августа", "сентября", "октября", "ноября", "декабря"], + "shortMonths": ["янв", "фев", "мар", "апр", "май", "июн", "июл", "авг", "сен", "окт", "ноя", "дек"] +} diff --git a/frontend/node_modules/d3-time-format/locale/sv-SE.json b/frontend/node_modules/d3-time-format/locale/sv-SE.json new file mode 100644 index 0000000..2318388 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/sv-SE.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A den %d %B %Y %X", + "date": "%Y-%m-%d", + "time": "%H:%M:%S", + "periods": ["fm", "em"], + "days": ["Söndag", "Måndag", "Tisdag", "Onsdag", "Torsdag", "Fredag", "Lördag"], + "shortDays": ["Sön", "Mån", "Tis", "Ons", "Tor", "Fre", "Lör"], + "months": ["Januari", "Februari", "Mars", "April", "Maj", "Juni", "Juli", "Augusti", "September", "Oktober", "November", "December"], + "shortMonths": ["Jan", "Feb", "Mar", "Apr", "Maj", "Jun", "Jul", "Aug", "Sep", "Okt", "Nov", "Dec"] +} diff --git a/frontend/node_modules/d3-time-format/locale/tr-TR.json b/frontend/node_modules/d3-time-format/locale/tr-TR.json new file mode 100644 index 0000000..ea0557e --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/tr-TR.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%a %e %b %X %Y", + "date": "%d/%m/%Y", + "time": "%H:%M:%S", + "periods": ["AM", "PM"], + "days": ["Pazar", "Pazartesi", "Salı", "Çarşamba", "Perşembe", "Cuma", "Cumartesi"], + "shortDays": ["Paz", "Pzt", "Sal", "Çar", "Per", "Cum", "Cmt"], + "months": ["Ocak", "Şubat", "Mart", "Nisan", "Mayıs", "Haziran", "Temmuz", "Ağustos", "Eylül", "Ekim", "Kasım", "Aralık"], + "shortMonths": ["Oca", "Şub", "Mar", "Nis", "May", "Haz", "Tem", "Ağu", "Eyl", "Eki", "Kas", "Ara"] +} diff --git a/frontend/node_modules/d3-time-format/locale/uk-UA.json b/frontend/node_modules/d3-time-format/locale/uk-UA.json new file mode 100644 index 0000000..555eed4 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/uk-UA.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%A, %e %B %Y р. %X", + "date": "%d.%m.%Y", + "time": "%H:%M:%S", + "periods": ["дп", "пп"], + "days": ["неділя", "понеділок", "вівторок", "середа", "четвер", "п'ятниця", "субота"], + "shortDays": ["нд", "пн", "вт", "ср", "чт", "пт", "сб"], + "months": ["січня", "лютого", "березня", "квітня", "травня", "червня", "липня", "серпня", "вересня", "жовтня", "листопада", "грудня"], + "shortMonths": ["січ.", "лют.", "бер.", "квіт.", "трав.", "черв.", "лип.", "серп.", "вер.", "жовт.", "лист.", "груд."] +} diff --git a/frontend/node_modules/d3-time-format/locale/zh-CN.json b/frontend/node_modules/d3-time-format/locale/zh-CN.json new file mode 100644 index 0000000..762f212 --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/zh-CN.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%x %A %X", + "date": "%Y年%-m月%-d日", + "time": "%H:%M:%S", + "periods": ["上午", "下午"], + "days": ["星期日", "星期一", "星期二", "星期三", "星期四", "星期五", "星期六"], + "shortDays": ["周日", "周一", "周二", "周三", "周四", "周五", "周六"], + "months": ["一月", "二月", "三月", "四月", "五月", "六月", "七月", "八月", "九月", "十月", "十一月", "十二月"], + "shortMonths": ["一月", "二月", "三月", "四月", "五月", "六月", "七月", "八月", "九月", "十月", "十一月", "十二月"] +} diff --git a/frontend/node_modules/d3-time-format/locale/zh-TW.json b/frontend/node_modules/d3-time-format/locale/zh-TW.json new file mode 100644 index 0000000..767b2ba --- /dev/null +++ b/frontend/node_modules/d3-time-format/locale/zh-TW.json @@ -0,0 +1,10 @@ +{ + "dateTime": "%x %A %X", + "date": "%Y年%-m月%-d日", + "time": "%H:%M:%S", + "periods": ["上午", "下午"], + "days": ["星期日", "星期一", "星期二", "星期三", "星期四", "星期五", "星期六"], + "shortDays": ["日", "一", "二", "三", "四", "五", "六"], + "months": ["一月", "二月", "三月", "四月", "五月", "六月", "七月", "八月", "九月", "十月", "十一月", "十二月"], + "shortMonths": ["1月", "2月", "3月", "4月", "5月", "6月", "7月", "8月", "9月", "10月", "11月", "12月"] +} diff --git a/frontend/node_modules/d3-time-format/package.json b/frontend/node_modules/d3-time-format/package.json new file mode 100644 index 0000000..fbdac72 --- /dev/null +++ b/frontend/node_modules/d3-time-format/package.json @@ -0,0 +1,60 @@ +{ + "name": "d3-time-format", + "version": "4.1.0", + "description": "A JavaScript time formatter and parser inspired by strftime and strptime.", + "homepage": "https://d3js.org/d3-time-format/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-time-format.git" + }, + "keywords": [ + "d3", + "d3-module", + "time", + "format", + "strftime", + "strptime" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "http://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js", + "locale/*.json" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-time-format.min.js", + "unpkg": "dist/d3-time-format.min.js", + "exports": { + ".": { + "umd": "./dist/d3-time-format.min.js", + "default": "./src/index.js" + }, + "./locale/*": "./locale/*.json" + }, + "sideEffects": [ + "./src/defaultLocale.js" + ], + "dependencies": { + "d3-time": "1 - 3" + }, + "devDependencies": { + "eslint": "8", + "mocha": "9", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "TZ=America/Los_Angeles mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-time-format/src/defaultLocale.js b/frontend/node_modules/d3-time-format/src/defaultLocale.js new file mode 100644 index 0000000..d762db5 --- /dev/null +++ b/frontend/node_modules/d3-time-format/src/defaultLocale.js @@ -0,0 +1,27 @@ +import formatLocale from "./locale.js"; + +var locale; +export var timeFormat; +export var timeParse; +export var utcFormat; +export var utcParse; + +defaultLocale({ + dateTime: "%x, %X", + date: "%-m/%-d/%Y", + time: "%-I:%M:%S %p", + periods: ["AM", "PM"], + days: ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"], + shortDays: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"], + months: ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"], + shortMonths: ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"] +}); + +export default function defaultLocale(definition) { + locale = formatLocale(definition); + timeFormat = locale.format; + timeParse = locale.parse; + utcFormat = locale.utcFormat; + utcParse = locale.utcParse; + return locale; +} diff --git a/frontend/node_modules/d3-time-format/src/index.js b/frontend/node_modules/d3-time-format/src/index.js new file mode 100644 index 0000000..6c93971 --- /dev/null +++ b/frontend/node_modules/d3-time-format/src/index.js @@ -0,0 +1,4 @@ +export {default as timeFormatDefaultLocale, timeFormat, timeParse, utcFormat, utcParse} from "./defaultLocale.js"; +export {default as timeFormatLocale} from "./locale.js"; +export {default as isoFormat} from "./isoFormat.js"; +export {default as isoParse} from "./isoParse.js"; diff --git a/frontend/node_modules/d3-time-format/src/isoFormat.js b/frontend/node_modules/d3-time-format/src/isoFormat.js new file mode 100644 index 0000000..43185a3 --- /dev/null +++ b/frontend/node_modules/d3-time-format/src/isoFormat.js @@ -0,0 +1,13 @@ +import {utcFormat} from "./defaultLocale.js"; + +export var isoSpecifier = "%Y-%m-%dT%H:%M:%S.%LZ"; + +function formatIsoNative(date) { + return date.toISOString(); +} + +var formatIso = Date.prototype.toISOString + ? formatIsoNative + : utcFormat(isoSpecifier); + +export default formatIso; diff --git a/frontend/node_modules/d3-time-format/src/isoParse.js b/frontend/node_modules/d3-time-format/src/isoParse.js new file mode 100644 index 0000000..381d1c9 --- /dev/null +++ b/frontend/node_modules/d3-time-format/src/isoParse.js @@ -0,0 +1,13 @@ +import {isoSpecifier} from "./isoFormat.js"; +import {utcParse} from "./defaultLocale.js"; + +function parseIsoNative(string) { + var date = new Date(string); + return isNaN(date) ? null : date; +} + +var parseIso = +new Date("2000-01-01T00:00:00.000Z") + ? parseIsoNative + : utcParse(isoSpecifier); + +export default parseIso; diff --git a/frontend/node_modules/d3-time-format/src/locale.js b/frontend/node_modules/d3-time-format/src/locale.js new file mode 100644 index 0000000..cc0dac2 --- /dev/null +++ b/frontend/node_modules/d3-time-format/src/locale.js @@ -0,0 +1,697 @@ +import { + timeDay, + timeSunday, + timeMonday, + timeThursday, + timeYear, + utcDay, + utcSunday, + utcMonday, + utcThursday, + utcYear +} from "d3-time"; + +function localDate(d) { + if (0 <= d.y && d.y < 100) { + var date = new Date(-1, d.m, d.d, d.H, d.M, d.S, d.L); + date.setFullYear(d.y); + return date; + } + return new Date(d.y, d.m, d.d, d.H, d.M, d.S, d.L); +} + +function utcDate(d) { + if (0 <= d.y && d.y < 100) { + var date = new Date(Date.UTC(-1, d.m, d.d, d.H, d.M, d.S, d.L)); + date.setUTCFullYear(d.y); + return date; + } + return new Date(Date.UTC(d.y, d.m, d.d, d.H, d.M, d.S, d.L)); +} + +function newDate(y, m, d) { + return {y: y, m: m, d: d, H: 0, M: 0, S: 0, L: 0}; +} + +export default function formatLocale(locale) { + var locale_dateTime = locale.dateTime, + locale_date = locale.date, + locale_time = locale.time, + locale_periods = locale.periods, + locale_weekdays = locale.days, + locale_shortWeekdays = locale.shortDays, + locale_months = locale.months, + locale_shortMonths = locale.shortMonths; + + var periodRe = formatRe(locale_periods), + periodLookup = formatLookup(locale_periods), + weekdayRe = formatRe(locale_weekdays), + weekdayLookup = formatLookup(locale_weekdays), + shortWeekdayRe = formatRe(locale_shortWeekdays), + shortWeekdayLookup = formatLookup(locale_shortWeekdays), + monthRe = formatRe(locale_months), + monthLookup = formatLookup(locale_months), + shortMonthRe = formatRe(locale_shortMonths), + shortMonthLookup = formatLookup(locale_shortMonths); + + var formats = { + "a": formatShortWeekday, + "A": formatWeekday, + "b": formatShortMonth, + "B": formatMonth, + "c": null, + "d": formatDayOfMonth, + "e": formatDayOfMonth, + "f": formatMicroseconds, + "g": formatYearISO, + "G": formatFullYearISO, + "H": formatHour24, + "I": formatHour12, + "j": formatDayOfYear, + "L": formatMilliseconds, + "m": formatMonthNumber, + "M": formatMinutes, + "p": formatPeriod, + "q": formatQuarter, + "Q": formatUnixTimestamp, + "s": formatUnixTimestampSeconds, + "S": formatSeconds, + "u": formatWeekdayNumberMonday, + "U": formatWeekNumberSunday, + "V": formatWeekNumberISO, + "w": formatWeekdayNumberSunday, + "W": formatWeekNumberMonday, + "x": null, + "X": null, + "y": formatYear, + "Y": formatFullYear, + "Z": formatZone, + "%": formatLiteralPercent + }; + + var utcFormats = { + "a": formatUTCShortWeekday, + "A": formatUTCWeekday, + "b": formatUTCShortMonth, + "B": formatUTCMonth, + "c": null, + "d": formatUTCDayOfMonth, + "e": formatUTCDayOfMonth, + "f": formatUTCMicroseconds, + "g": formatUTCYearISO, + "G": formatUTCFullYearISO, + "H": formatUTCHour24, + "I": formatUTCHour12, + "j": formatUTCDayOfYear, + "L": formatUTCMilliseconds, + "m": formatUTCMonthNumber, + "M": formatUTCMinutes, + "p": formatUTCPeriod, + "q": formatUTCQuarter, + "Q": formatUnixTimestamp, + "s": formatUnixTimestampSeconds, + "S": formatUTCSeconds, + "u": formatUTCWeekdayNumberMonday, + "U": formatUTCWeekNumberSunday, + "V": formatUTCWeekNumberISO, + "w": formatUTCWeekdayNumberSunday, + "W": formatUTCWeekNumberMonday, + "x": null, + "X": null, + "y": formatUTCYear, + "Y": formatUTCFullYear, + "Z": formatUTCZone, + "%": formatLiteralPercent + }; + + var parses = { + "a": parseShortWeekday, + "A": parseWeekday, + "b": parseShortMonth, + "B": parseMonth, + "c": parseLocaleDateTime, + "d": parseDayOfMonth, + "e": parseDayOfMonth, + "f": parseMicroseconds, + "g": parseYear, + "G": parseFullYear, + "H": parseHour24, + "I": parseHour24, + "j": parseDayOfYear, + "L": parseMilliseconds, + "m": parseMonthNumber, + "M": parseMinutes, + "p": parsePeriod, + "q": parseQuarter, + "Q": parseUnixTimestamp, + "s": parseUnixTimestampSeconds, + "S": parseSeconds, + "u": parseWeekdayNumberMonday, + "U": parseWeekNumberSunday, + "V": parseWeekNumberISO, + "w": parseWeekdayNumberSunday, + "W": parseWeekNumberMonday, + "x": parseLocaleDate, + "X": parseLocaleTime, + "y": parseYear, + "Y": parseFullYear, + "Z": parseZone, + "%": parseLiteralPercent + }; + + // These recursive directive definitions must be deferred. + formats.x = newFormat(locale_date, formats); + formats.X = newFormat(locale_time, formats); + formats.c = newFormat(locale_dateTime, formats); + utcFormats.x = newFormat(locale_date, utcFormats); + utcFormats.X = newFormat(locale_time, utcFormats); + utcFormats.c = newFormat(locale_dateTime, utcFormats); + + function newFormat(specifier, formats) { + return function(date) { + var string = [], + i = -1, + j = 0, + n = specifier.length, + c, + pad, + format; + + if (!(date instanceof Date)) date = new Date(+date); + + while (++i < n) { + if (specifier.charCodeAt(i) === 37) { + string.push(specifier.slice(j, i)); + if ((pad = pads[c = specifier.charAt(++i)]) != null) c = specifier.charAt(++i); + else pad = c === "e" ? " " : "0"; + if (format = formats[c]) c = format(date, pad); + string.push(c); + j = i + 1; + } + } + + string.push(specifier.slice(j, i)); + return string.join(""); + }; + } + + function newParse(specifier, Z) { + return function(string) { + var d = newDate(1900, undefined, 1), + i = parseSpecifier(d, specifier, string += "", 0), + week, day; + if (i != string.length) return null; + + // If a UNIX timestamp is specified, return it. + if ("Q" in d) return new Date(d.Q); + if ("s" in d) return new Date(d.s * 1000 + ("L" in d ? d.L : 0)); + + // If this is utcParse, never use the local timezone. + if (Z && !("Z" in d)) d.Z = 0; + + // The am-pm flag is 0 for AM, and 1 for PM. + if ("p" in d) d.H = d.H % 12 + d.p * 12; + + // If the month was not specified, inherit from the quarter. + if (d.m === undefined) d.m = "q" in d ? d.q : 0; + + // Convert day-of-week and week-of-year to day-of-year. + if ("V" in d) { + if (d.V < 1 || d.V > 53) return null; + if (!("w" in d)) d.w = 1; + if ("Z" in d) { + week = utcDate(newDate(d.y, 0, 1)), day = week.getUTCDay(); + week = day > 4 || day === 0 ? utcMonday.ceil(week) : utcMonday(week); + week = utcDay.offset(week, (d.V - 1) * 7); + d.y = week.getUTCFullYear(); + d.m = week.getUTCMonth(); + d.d = week.getUTCDate() + (d.w + 6) % 7; + } else { + week = localDate(newDate(d.y, 0, 1)), day = week.getDay(); + week = day > 4 || day === 0 ? timeMonday.ceil(week) : timeMonday(week); + week = timeDay.offset(week, (d.V - 1) * 7); + d.y = week.getFullYear(); + d.m = week.getMonth(); + d.d = week.getDate() + (d.w + 6) % 7; + } + } else if ("W" in d || "U" in d) { + if (!("w" in d)) d.w = "u" in d ? d.u % 7 : "W" in d ? 1 : 0; + day = "Z" in d ? utcDate(newDate(d.y, 0, 1)).getUTCDay() : localDate(newDate(d.y, 0, 1)).getDay(); + d.m = 0; + d.d = "W" in d ? (d.w + 6) % 7 + d.W * 7 - (day + 5) % 7 : d.w + d.U * 7 - (day + 6) % 7; + } + + // If a time zone is specified, all fields are interpreted as UTC and then + // offset according to the specified time zone. + if ("Z" in d) { + d.H += d.Z / 100 | 0; + d.M += d.Z % 100; + return utcDate(d); + } + + // Otherwise, all fields are in local time. + return localDate(d); + }; + } + + function parseSpecifier(d, specifier, string, j) { + var i = 0, + n = specifier.length, + m = string.length, + c, + parse; + + while (i < n) { + if (j >= m) return -1; + c = specifier.charCodeAt(i++); + if (c === 37) { + c = specifier.charAt(i++); + parse = parses[c in pads ? specifier.charAt(i++) : c]; + if (!parse || ((j = parse(d, string, j)) < 0)) return -1; + } else if (c != string.charCodeAt(j++)) { + return -1; + } + } + + return j; + } + + function parsePeriod(d, string, i) { + var n = periodRe.exec(string.slice(i)); + return n ? (d.p = periodLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseShortWeekday(d, string, i) { + var n = shortWeekdayRe.exec(string.slice(i)); + return n ? (d.w = shortWeekdayLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseWeekday(d, string, i) { + var n = weekdayRe.exec(string.slice(i)); + return n ? (d.w = weekdayLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseShortMonth(d, string, i) { + var n = shortMonthRe.exec(string.slice(i)); + return n ? (d.m = shortMonthLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseMonth(d, string, i) { + var n = monthRe.exec(string.slice(i)); + return n ? (d.m = monthLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseLocaleDateTime(d, string, i) { + return parseSpecifier(d, locale_dateTime, string, i); + } + + function parseLocaleDate(d, string, i) { + return parseSpecifier(d, locale_date, string, i); + } + + function parseLocaleTime(d, string, i) { + return parseSpecifier(d, locale_time, string, i); + } + + function formatShortWeekday(d) { + return locale_shortWeekdays[d.getDay()]; + } + + function formatWeekday(d) { + return locale_weekdays[d.getDay()]; + } + + function formatShortMonth(d) { + return locale_shortMonths[d.getMonth()]; + } + + function formatMonth(d) { + return locale_months[d.getMonth()]; + } + + function formatPeriod(d) { + return locale_periods[+(d.getHours() >= 12)]; + } + + function formatQuarter(d) { + return 1 + ~~(d.getMonth() / 3); + } + + function formatUTCShortWeekday(d) { + return locale_shortWeekdays[d.getUTCDay()]; + } + + function formatUTCWeekday(d) { + return locale_weekdays[d.getUTCDay()]; + } + + function formatUTCShortMonth(d) { + return locale_shortMonths[d.getUTCMonth()]; + } + + function formatUTCMonth(d) { + return locale_months[d.getUTCMonth()]; + } + + function formatUTCPeriod(d) { + return locale_periods[+(d.getUTCHours() >= 12)]; + } + + function formatUTCQuarter(d) { + return 1 + ~~(d.getUTCMonth() / 3); + } + + return { + format: function(specifier) { + var f = newFormat(specifier += "", formats); + f.toString = function() { return specifier; }; + return f; + }, + parse: function(specifier) { + var p = newParse(specifier += "", false); + p.toString = function() { return specifier; }; + return p; + }, + utcFormat: function(specifier) { + var f = newFormat(specifier += "", utcFormats); + f.toString = function() { return specifier; }; + return f; + }, + utcParse: function(specifier) { + var p = newParse(specifier += "", true); + p.toString = function() { return specifier; }; + return p; + } + }; +} + +var pads = {"-": "", "_": " ", "0": "0"}, + numberRe = /^\s*\d+/, // note: ignores next directive + percentRe = /^%/, + requoteRe = /[\\^$*+?|[\]().{}]/g; + +function pad(value, fill, width) { + var sign = value < 0 ? "-" : "", + string = (sign ? -value : value) + "", + length = string.length; + return sign + (length < width ? new Array(width - length + 1).join(fill) + string : string); +} + +function requote(s) { + return s.replace(requoteRe, "\\$&"); +} + +function formatRe(names) { + return new RegExp("^(?:" + names.map(requote).join("|") + ")", "i"); +} + +function formatLookup(names) { + return new Map(names.map((name, i) => [name.toLowerCase(), i])); +} + +function parseWeekdayNumberSunday(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 1)); + return n ? (d.w = +n[0], i + n[0].length) : -1; +} + +function parseWeekdayNumberMonday(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 1)); + return n ? (d.u = +n[0], i + n[0].length) : -1; +} + +function parseWeekNumberSunday(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.U = +n[0], i + n[0].length) : -1; +} + +function parseWeekNumberISO(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.V = +n[0], i + n[0].length) : -1; +} + +function parseWeekNumberMonday(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.W = +n[0], i + n[0].length) : -1; +} + +function parseFullYear(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 4)); + return n ? (d.y = +n[0], i + n[0].length) : -1; +} + +function parseYear(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.y = +n[0] + (+n[0] > 68 ? 1900 : 2000), i + n[0].length) : -1; +} + +function parseZone(d, string, i) { + var n = /^(Z)|([+-]\d\d)(?::?(\d\d))?/.exec(string.slice(i, i + 6)); + return n ? (d.Z = n[1] ? 0 : -(n[2] + (n[3] || "00")), i + n[0].length) : -1; +} + +function parseQuarter(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 1)); + return n ? (d.q = n[0] * 3 - 3, i + n[0].length) : -1; +} + +function parseMonthNumber(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.m = n[0] - 1, i + n[0].length) : -1; +} + +function parseDayOfMonth(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.d = +n[0], i + n[0].length) : -1; +} + +function parseDayOfYear(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 3)); + return n ? (d.m = 0, d.d = +n[0], i + n[0].length) : -1; +} + +function parseHour24(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.H = +n[0], i + n[0].length) : -1; +} + +function parseMinutes(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.M = +n[0], i + n[0].length) : -1; +} + +function parseSeconds(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.S = +n[0], i + n[0].length) : -1; +} + +function parseMilliseconds(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 3)); + return n ? (d.L = +n[0], i + n[0].length) : -1; +} + +function parseMicroseconds(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 6)); + return n ? (d.L = Math.floor(n[0] / 1000), i + n[0].length) : -1; +} + +function parseLiteralPercent(d, string, i) { + var n = percentRe.exec(string.slice(i, i + 1)); + return n ? i + n[0].length : -1; +} + +function parseUnixTimestamp(d, string, i) { + var n = numberRe.exec(string.slice(i)); + return n ? (d.Q = +n[0], i + n[0].length) : -1; +} + +function parseUnixTimestampSeconds(d, string, i) { + var n = numberRe.exec(string.slice(i)); + return n ? (d.s = +n[0], i + n[0].length) : -1; +} + +function formatDayOfMonth(d, p) { + return pad(d.getDate(), p, 2); +} + +function formatHour24(d, p) { + return pad(d.getHours(), p, 2); +} + +function formatHour12(d, p) { + return pad(d.getHours() % 12 || 12, p, 2); +} + +function formatDayOfYear(d, p) { + return pad(1 + timeDay.count(timeYear(d), d), p, 3); +} + +function formatMilliseconds(d, p) { + return pad(d.getMilliseconds(), p, 3); +} + +function formatMicroseconds(d, p) { + return formatMilliseconds(d, p) + "000"; +} + +function formatMonthNumber(d, p) { + return pad(d.getMonth() + 1, p, 2); +} + +function formatMinutes(d, p) { + return pad(d.getMinutes(), p, 2); +} + +function formatSeconds(d, p) { + return pad(d.getSeconds(), p, 2); +} + +function formatWeekdayNumberMonday(d) { + var day = d.getDay(); + return day === 0 ? 7 : day; +} + +function formatWeekNumberSunday(d, p) { + return pad(timeSunday.count(timeYear(d) - 1, d), p, 2); +} + +function dISO(d) { + var day = d.getDay(); + return (day >= 4 || day === 0) ? timeThursday(d) : timeThursday.ceil(d); +} + +function formatWeekNumberISO(d, p) { + d = dISO(d); + return pad(timeThursday.count(timeYear(d), d) + (timeYear(d).getDay() === 4), p, 2); +} + +function formatWeekdayNumberSunday(d) { + return d.getDay(); +} + +function formatWeekNumberMonday(d, p) { + return pad(timeMonday.count(timeYear(d) - 1, d), p, 2); +} + +function formatYear(d, p) { + return pad(d.getFullYear() % 100, p, 2); +} + +function formatYearISO(d, p) { + d = dISO(d); + return pad(d.getFullYear() % 100, p, 2); +} + +function formatFullYear(d, p) { + return pad(d.getFullYear() % 10000, p, 4); +} + +function formatFullYearISO(d, p) { + var day = d.getDay(); + d = (day >= 4 || day === 0) ? timeThursday(d) : timeThursday.ceil(d); + return pad(d.getFullYear() % 10000, p, 4); +} + +function formatZone(d) { + var z = d.getTimezoneOffset(); + return (z > 0 ? "-" : (z *= -1, "+")) + + pad(z / 60 | 0, "0", 2) + + pad(z % 60, "0", 2); +} + +function formatUTCDayOfMonth(d, p) { + return pad(d.getUTCDate(), p, 2); +} + +function formatUTCHour24(d, p) { + return pad(d.getUTCHours(), p, 2); +} + +function formatUTCHour12(d, p) { + return pad(d.getUTCHours() % 12 || 12, p, 2); +} + +function formatUTCDayOfYear(d, p) { + return pad(1 + utcDay.count(utcYear(d), d), p, 3); +} + +function formatUTCMilliseconds(d, p) { + return pad(d.getUTCMilliseconds(), p, 3); +} + +function formatUTCMicroseconds(d, p) { + return formatUTCMilliseconds(d, p) + "000"; +} + +function formatUTCMonthNumber(d, p) { + return pad(d.getUTCMonth() + 1, p, 2); +} + +function formatUTCMinutes(d, p) { + return pad(d.getUTCMinutes(), p, 2); +} + +function formatUTCSeconds(d, p) { + return pad(d.getUTCSeconds(), p, 2); +} + +function formatUTCWeekdayNumberMonday(d) { + var dow = d.getUTCDay(); + return dow === 0 ? 7 : dow; +} + +function formatUTCWeekNumberSunday(d, p) { + return pad(utcSunday.count(utcYear(d) - 1, d), p, 2); +} + +function UTCdISO(d) { + var day = d.getUTCDay(); + return (day >= 4 || day === 0) ? utcThursday(d) : utcThursday.ceil(d); +} + +function formatUTCWeekNumberISO(d, p) { + d = UTCdISO(d); + return pad(utcThursday.count(utcYear(d), d) + (utcYear(d).getUTCDay() === 4), p, 2); +} + +function formatUTCWeekdayNumberSunday(d) { + return d.getUTCDay(); +} + +function formatUTCWeekNumberMonday(d, p) { + return pad(utcMonday.count(utcYear(d) - 1, d), p, 2); +} + +function formatUTCYear(d, p) { + return pad(d.getUTCFullYear() % 100, p, 2); +} + +function formatUTCYearISO(d, p) { + d = UTCdISO(d); + return pad(d.getUTCFullYear() % 100, p, 2); +} + +function formatUTCFullYear(d, p) { + return pad(d.getUTCFullYear() % 10000, p, 4); +} + +function formatUTCFullYearISO(d, p) { + var day = d.getUTCDay(); + d = (day >= 4 || day === 0) ? utcThursday(d) : utcThursday.ceil(d); + return pad(d.getUTCFullYear() % 10000, p, 4); +} + +function formatUTCZone() { + return "+0000"; +} + +function formatLiteralPercent() { + return "%"; +} + +function formatUnixTimestamp(d) { + return +d; +} + +function formatUnixTimestampSeconds(d) { + return Math.floor(+d / 1000); +} diff --git a/frontend/node_modules/d3-time/LICENSE b/frontend/node_modules/d3-time/LICENSE new file mode 100644 index 0000000..fbe44bd --- /dev/null +++ b/frontend/node_modules/d3-time/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2022 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-time/README.md b/frontend/node_modules/d3-time/README.md new file mode 100644 index 0000000..4a05cdf --- /dev/null +++ b/frontend/node_modules/d3-time/README.md @@ -0,0 +1,380 @@ +# d3-time + +When visualizing time series data, analyzing temporal patterns, or working with time in general, the irregularities of conventional time units quickly become apparent. In the [Gregorian calendar](https://en.wikipedia.org/wiki/Gregorian_calendar), for example, most months have 31 days but some have 28, 29 or 30; most years have 365 days but [leap years](https://en.wikipedia.org/wiki/Leap_year) have 366; and with [daylight saving](https://en.wikipedia.org/wiki/Daylight_saving_time), most days have 24 hours but some have 23 or 25. Adding to complexity, daylight saving conventions vary around the world. + +As a result of these temporal peculiarities, it can be difficult to perform seemingly-trivial tasks. For example, if you want to compute the number of days that have passed between two dates, you can’t simply subtract and divide by 24 hours (86,400,000 ms): + +```js +start = new Date(2015, 02, 01) // 2015-03-01T00:00 +end = new Date(2015, 03, 01) // 2015-04-01T00:00 +(end - start) / 864e5 // 30.958333333333332, oops! 🤯 +``` + +You can, however, use [d3.timeDay](#timeDay).[count](#interval_count): + +```js +d3.timeDay.count(start, end) // 31 😌 +``` + +The [day](#day) [interval](#api-reference) is one of several provided by d3-time. Each interval represents a conventional unit of time—[hours](#timeHour), [weeks](#timeWeek), [months](#timeMonth), *etc.*—and has methods to calculate boundary dates. For example, [d3.timeDay](#timeDay) computes midnight (typically 12:00 AM local time) of the corresponding day. In addition to [rounding](#interval_round) and [counting](#interval_count), intervals can also be used to generate arrays of boundary dates. For example, to compute each Sunday in the current month: + +```js +start = d3.timeMonth.floor() // 2015-01-01T00:00 +stop = d3.timeMonth.ceil() // 2015-02-01T00:00 +d3.timeWeek.range(start, stop) // [2015-01-07T00:00, 2015-01-14T00:00, 2015-01-21T00:00, 2015-01-28T00:00] +``` + +The d3-time module does not implement its own calendaring system; it merely implements a convenient API for calendar math on top of ECMAScript [Date](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date). Thus, it ignores leap seconds and can only work with the local time zone and [Coordinated Universal Time](https://en.wikipedia.org/wiki/Coordinated_Universal_Time) (UTC). + +This module is used by D3’s time scales to generate sensible ticks, by D3’s time format, and can also be used directly to do things like [calendar layouts](http://bl.ocks.org/mbostock/4063318). + +## Installing + +If you use npm, `npm install d3-time`. You can also download the [latest release on GitHub](https://github.com/d3/d3-time/releases/latest). For vanilla HTML in modern browsers, import d3-time from Skypack: + +```html + +``` + +For legacy environments, you can load d3-time’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + + +``` + +[Try d3-time in your browser.](https://observablehq.com/collection/@d3/d3-time) + +## API Reference + +# interval([date]) · [Source](https://github.com/d3/d3-time/blob/main/src/interval.js) + +Equivalent to [*interval*.floor](#interval_floor), except if *date* is not specified, it defaults to the current time. For example, [d3.timeYear](#timeYear)(*date*) and d3.timeYear.floor(*date*) are equivalent. + +```js +monday = d3.timeMonday() // the latest preceeding Monday, local time +``` + +# interval.floor(date) · [Source](https://github.com/d3/d3-time/blob/main/src/interval.js) + +Returns a new date representing the latest interval boundary date before or equal to *date*. For example, [d3.timeDay](#timeDay).floor(*date*) typically returns 12:00 AM local time on the given *date*. + +This method is idempotent: if the specified *date* is already floored to the current interval, a new date with an identical time is returned. Furthermore, the returned date is the minimum expressible value of the associated interval, such that *interval*.floor(*interval*.floor(*date*) - 1) returns the preceeding interval boundary date. + +Note that the `==` and `===` operators do not compare by value with [Date](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date) objects, and thus you cannot use them to tell whether the specified *date* has already been floored. Instead, coerce to a number and then compare: + +```js +// Returns true if the specified date is a day boundary. +function isDay(date) { + return +d3.timeDay.floor(date) === +date; +} +``` + +This is more reliable than testing whether the time is 12:00 AM, as in some time zones midnight may not exist due to daylight saving. + +# interval.round(date) · [Source](https://github.com/d3/d3-time/blob/main/src/interval.js) + +Returns a new date representing the closest interval boundary date to *date*. For example, [d3.timeDay](#timeDay).round(*date*) typically returns 12:00 AM local time on the given *date* if it is on or before noon, and 12:00 AM of the following day if it is after noon. + +This method is idempotent: if the specified *date* is already rounded to the current interval, a new date with an identical time is returned. + +# interval.ceil(date) · [Source](https://github.com/d3/d3-time/blob/main/src/interval.js) + +Returns a new date representing the earliest interval boundary date after or equal to *date*. For example, [d3.timeDay](#timeDay).ceil(*date*) typically returns 12:00 AM local time on the date following the given *date*. + +This method is idempotent: if the specified *date* is already ceilinged to the current interval, a new date with an identical time is returned. Furthermore, the returned date is the maximum expressible value of the associated interval, such that *interval*.ceil(*interval*.ceil(*date*) + 1) returns the following interval boundary date. + +# interval.offset(date[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/interval.js) + +Returns a new date equal to *date* plus *step* intervals. If *step* is not specified it defaults to 1. If *step* is negative, then the returned date will be before the specified *date*; if *step* is zero, then a copy of the specified *date* is returned; if *step* is not an integer, it is [floored](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Math/floor). This method does not round the specified *date* to the interval. For example, if *date* is today at 5:34 PM, then [d3.timeDay](#timeDay).offset(*date*, 1) returns 5:34 PM tomorrow (even if daylight saving changes!). + +# interval.range(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/interval.js) + +Returns an array of dates representing every interval boundary after or equal to *start* (inclusive) and before *stop* (exclusive). If *step* is specified, then every *step*th boundary will be returned; for example, for the [d3.timeDay](#timeDay) interval a *step* of 2 will return every other day. If *step* is not an integer, it is [floored](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Math/floor). + +The first date in the returned array is the earliest boundary after or equal to *start*; subsequent dates are [offset](#interval_offset) by *step* intervals and [floored](#interval_floor). Thus, two overlapping ranges may be consistent. For example, this range contains odd days: + +```js +d3.timeDay.range(new Date(2015, 0, 1), new Date(2015, 0, 7), 2) // [2015-01-01T00:00, 2015-01-03T00:00, 2015-01-05T00:00] +``` + +While this contains even days: + +```js +d3.timeDay.range(new Date(2015, 0, 2), new Date(2015, 0, 8), 2) // [2015-01-02T00:00, 2015-01-04T00:00, 2015-01-06T00:00] +``` + +To make ranges consistent when a *step* is specified, use [*interval*.every](#interval_every) instead. + +# interval.filter(test) · [Source](https://github.com/d3/d3-time/blob/main/src/interval.js) + +Returns a new interval that is a filtered subset of this interval using the specified *test* function. The *test* function is passed a date and should return true if and only if the specified date should be considered part of the interval. For example, to create an interval that returns the 1st, 11th, 21th and 31th (if it exists) of each month: + +```js +d3.timeDay.filter(d => (d.getDate() - 1) % 10 === 0) +``` + +The returned filtered interval does not support [*interval*.count](#interval_count). See also [*interval*.every](#interval_every). + +# interval.every(step) · [Source](https://github.com/d3/d3-time/blob/main/src/interval.js) + +Returns a [filtered](#interval_filter) view of this interval representing every *step*th date. The meaning of *step* is dependent on this interval’s parent interval as defined by the field function. For example, [d3.timeMinute](#timeMinute).every(15) returns an interval representing every fifteen minutes, starting on the hour: :00, :15, :30, :45, etc. Note that for some intervals, the resulting dates may not be uniformly-spaced; [d3.timeDay](#timeDay)’s parent interval is [d3.timeMonth](#timeMonth), and thus the interval number resets at the start of each month. If *step* is not valid, returns null. If *step* is one, returns this interval. + +This method can be used in conjunction with [*interval*.range](#interval_range) to ensure that two overlapping ranges are consistent. For example, this range contains odd days: + +```js +d3.timeDay.every(2).range(new Date(2015, 0, 1), new Date(2015, 0, 7)) // [2015-01-01T00:00, 2015-01-03T00:00, 2015-01-05T00:00] +``` + +As does this one: + +```js +d3.timeDay.every(2).range(new Date(2015, 0, 2), new Date(2015, 0, 8)) // [2015-01-03T00:00, 2015-01-05T00:00, 2015-01-07T00:00] +``` + +The returned filtered interval does not support [*interval*.count](#interval_count). See also [*interval*.filter](#interval_filter). + +# interval.count(start, end) · [Source](https://github.com/d3/d3-time/blob/main/src/interval.js) + +Returns the number of interval boundaries after *start* (exclusive) and before or equal to *end* (inclusive). Note that this behavior is slightly different than [*interval*.range](#interval_range) because its purpose is to return the zero-based number of the specified *end* date relative to the specified *start* date. For example, to compute the current zero-based day-of-year number: + +```js +d3.timeDay.count(d3.timeYear(now), now) // 177 +``` + +Likewise, to compute the current zero-based week-of-year number for weeks that start on Sunday: + +```js +d3.timeSunday.count(d3.timeYear(now), now) // 25 +``` + +# d3.timeInterval(floor, offset[, count[, field]]) · [Source](https://github.com/d3/d3-time/blob/main/src/interval.js) + +Constructs a new custom interval given the specified *floor* and *offset* functions and an optional *count* function. + +The *floor* function takes a single date as an argument and rounds it down to the nearest interval boundary. + +The *offset* function takes a date and an integer step as arguments and advances the specified date by the specified number of boundaries; the step may be positive, negative or zero. + +The optional *count* function takes a start date and an end date, already floored to the current interval, and returns the number of boundaries between the start (exclusive) and end (inclusive). If a *count* function is not specified, the returned interval does not expose [*interval*.count](#interval_count) or [*interval*.every](#interval_every) methods. Note: due to an internal optimization, the specified *count* function must not invoke *interval*.count on other time intervals. + +The optional *field* function takes a date, already floored to the current interval, and returns the field value of the specified date, corresponding to the number of boundaries between this date (exclusive) and the latest previous parent boundary. For example, for the [d3.timeDay](#timeDay) interval, this returns the number of days since the start of the month. If a *field* function is not specified, it defaults to counting the number of interval boundaries since the UNIX epoch of January 1, 1970 UTC. The *field* function defines the behavior of [*interval*.every](#interval_every). + +### Intervals + +The following intervals are provided: + +# d3.timeMillisecond · [Source](https://github.com/d3/d3-time/blob/main/src/millisecond.js "Source") +
    # d3.utcMillisecond + +Milliseconds; the shortest available time unit. + +# d3.timeSecond · [Source](https://github.com/d3/d3-time/blob/main/src/second.js "Source") +
    # d3.utcSecond + +Seconds (e.g., 01:23:45.0000 AM); 1,000 milliseconds. + +# d3.timeMinute · [Source](https://github.com/d3/d3-time/blob/main/src/minute.js "Source") +
    # d3.utcMinute · [Source](https://github.com/d3/d3-time/blob/main/src/utcMinute.js "Source") + +Minutes (e.g., 01:02:00 AM); 60 seconds. Note that ECMAScript [ignores leap seconds](http://www.ecma-international.org/ecma-262/5.1/#sec-15.9.1.1). + +# d3.timeHour · [Source](https://github.com/d3/d3-time/blob/main/src/hour.js "Source") +
    # d3.utcHour · [Source](https://github.com/d3/d3-time/blob/main/src/utcHour.js "Source") + +Hours (e.g., 01:00 AM); 60 minutes. Note that advancing time by one hour in local time can return the same hour or skip an hour due to daylight saving. + +# d3.timeDay · [Source](https://github.com/d3/d3-time/blob/main/src/day.js "Source") +
    # d3.utcDay · [Source](https://github.com/d3/d3-time/blob/main/src/utcDay.js "Source") +
    # d3.unixDay · [Source](https://github.com/d3/d3-time/blob/main/src/unixDay.js "Source") + +Days (e.g., February 7, 2012 at 12:00 AM); typically 24 hours. Days in local time may range from 23 to 25 hours due to daylight saving. d3.unixDay is like [d3.utcDay](#timeDay), except it counts days since the UNIX epoch (January 1, 1970) such that *interval*.every returns uniformly-spaced dates rather than varying based on day-of-month. + +# d3.timeWeek · [Source](https://github.com/d3/d3-time/blob/main/src/week.js "Source") +
    # d3.utcWeek · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js "Source") + +Alias for [d3.timeSunday](#timeSunday); 7 days and typically 168 hours. Weeks in local time may range from 167 to 169 hours due to daylight saving. + +# d3.timeSunday · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcSunday · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Sunday-based weeks (e.g., February 5, 2012 at 12:00 AM). + +# d3.timeMonday · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcMonday · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Monday-based weeks (e.g., February 6, 2012 at 12:00 AM). + +# d3.timeTuesday · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcTuesday · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Tuesday-based weeks (e.g., February 7, 2012 at 12:00 AM). + +# d3.timeWednesday · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcWednesday · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Wednesday-based weeks (e.g., February 8, 2012 at 12:00 AM). + +# d3.timeThursday · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcThursday · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Thursday-based weeks (e.g., February 9, 2012 at 12:00 AM). + +# d3.timeFriday · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcFriday · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Friday-based weeks (e.g., February 10, 2012 at 12:00 AM). + +# d3.timeSaturday · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcSaturday · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Saturday-based weeks (e.g., February 11, 2012 at 12:00 AM). + +# d3.timeMonth · [Source](https://github.com/d3/d3-time/blob/main/src/month.js "Source") +
    # d3.utcMonth · [Source](https://github.com/d3/d3-time/blob/main/src/utcMonth.js "Source") + +Months (e.g., February 1, 2012 at 12:00 AM); ranges from 28 to 31 days. + +# d3.timeYear · [Source](https://github.com/d3/d3-time/blob/main/src/year.js "Source") +
    # d3.utcYear · [Source](https://github.com/d3/d3-time/blob/main/src/utcYear.js "Source") + +Years (e.g., January 1, 2012 at 12:00 AM); ranges from 365 to 366 days. + +### Ranges + +For convenience, aliases for [*interval*.range](#interval_range) are also provided as plural forms of the corresponding interval. + +# d3.timeMilliseconds(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/millisecond.js) +
    # d3.utcMilliseconds(start, stop[, step]) + +Aliases for [d3.timeMillisecond](#timeMillisecond).[range](#interval_range) and [d3.utcMillisecond](#timeMillisecond).[range](#interval_range). + +# d3.timeSeconds(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/second.js) +
    # d3.utcSeconds(start, stop[, step]) + +Aliases for [d3.timeSecond](#timeSecond).[range](#interval_range) and [d3.utcSecond](#timeSecond).[range](#interval_range). + +# d3.timeMinutes(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/minute.js) +
    # d3.utcMinutes(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/utcMinute.js) + +Aliases for [d3.timeMinute](#timeMinute).[range](#interval_range) and [d3.utcMinute](#timeMinute).[range](#interval_range). + +# d3.timeHours(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/hour.js) +
    # d3.utcHours(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/utcHour.js) + +Aliases for [d3.timeHour](#timeHour).[range](#interval_range) and [d3.utcHour](#timeHour).[range](#interval_range). + +# d3.timeDays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/day.js) +
    # d3.utcDays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/utcDay.js) +
    # d3.unixDays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/unixDay.js) + +Aliases for [d3.timeDay](#timeDay).[range](#interval_range), [d3.utcDay](#timeDay).[range](#interval_range), and [d3.unixDay](#timeDay).[range](#interval_range). + +# d3.timeWeeks(start, stop[, step]) +
    # d3.utcWeeks(start, stop[, step]) + +Aliases for [d3.timeWeek](#timeWeek).[range](#interval_range) and [d3.utcWeek](#timeWeek).[range](#interval_range). + +# d3.timeSundays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcSundays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Aliases for [d3.timeSunday](#timeSunday).[range](#interval_range) and [d3.utcSunday](#timeSunday).[range](#interval_range). + +# d3.timeMondays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcMondays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Aliases for [d3.timeMonday](#timeMonday).[range](#interval_range) and [d3.utcMonday](#timeMonday).[range](#interval_range). + +# d3.timeTuesdays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcTuesdays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Aliases for [d3.timeTuesday](#timeTuesday).[range](#interval_range) and [d3.utcTuesday](#timeTuesday).[range](#interval_range). + +# d3.timeWednesdays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcWednesdays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Aliases for [d3.timeWednesday](#timeWednesday).[range](#interval_range) and [d3.utcWednesday](#timeWednesday).[range](#interval_range). + +# d3.timeThursdays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcThursdays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Aliases for [d3.timeThursday](#timeThursday).[range](#interval_range) and [d3.utcThursday](#timeThursday).[range](#interval_range). + +# d3.timeFridays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcFridays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Aliases for [d3.timeFriday](#timeFriday).[range](#interval_range) and [d3.utcFriday](#timeFriday).[range](#interval_range). + +# d3.timeSaturdays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/week.js) +
    # d3.utcSaturdays(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/utcWeek.js) + +Aliases for [d3.timeSaturday](#timeSaturday).[range](#interval_range) and [d3.utcSaturday](#timeSaturday).[range](#interval_range). + +# d3.timeMonths(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/month.js) +
    # d3.utcMonths(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/utcMonth.js) + +Aliases for [d3.timeMonth](#timeMonth).[range](#interval_range) and [d3.utcMonth](#timeMonth).[range](#interval_range). + +# d3.timeYears(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/year.js) +
    # d3.utcYears(start, stop[, step]) · [Source](https://github.com/d3/d3-time/blob/main/src/utcYear.js) + +Aliases for [d3.timeYear](#timeYear).[range](#interval_range) and [d3.utcYear](#timeYear).[range](#interval_range). + +### Ticks + +# d3.timeTicks(start, stop, count) · [Source](https://github.com/d3/d3-time/blob/main/src/ticks.js) + +Equivalent to [d3.utcTicks](#utcTicks), but in local time. + +# d3.timeTickInterval(start, stop, count) · [Source](https://github.com/d3/d3-time/blob/main/src/ticks.js) + +Returns the time interval that would be used by [d3.timeTicks](#timeTicks) given the same arguments. + +# d3.utcTicks(start, stop, count) · [Source](https://github.com/d3/d3-time/blob/main/src/ticks.js) + +Returns an array of approximately *count* dates at regular intervals between *start* and *stop* (inclusive). If *stop* is before *start*, dates are returned in reverse chronological order; otherwise dates are returned in chronological order. The following UTC time intervals are considered: + +* 1 second +* 5 seconds +* 15 seconds +* 30 seconds +* 1 minute +* 5 minutes +* 15 minutes +* 30 minutes +* 1 hour +* 3 hours +* 6 hours +* 12 hours +* 1 day +* 2 days +* 1 week +* 1 month +* 3 months +* 1 year + +Multiples of milliseconds (for small ranges) and years (for large ranges) are also considered, following the rules of [d3.ticks](https://github.com/d3/d3-array/blob/main/README.md#ticks). The interval producing the number of dates that is closest to *count* is used. For example: + +```js +start = new Date(Date.UTC(1970, 2, 1)) +stop = new Date(Date.UTC(1996, 2, 19)) +count = 4 +d3.utcTicks(start, stop, count) // [1975-01-01, 1980-01-01, 1985-01-01, 1990-01-01, 1995-01-01] +``` + +If *count* is a time interval, this function behaves similarly to [*interval*.range](#interval_range) except that both *start* and *stop* are inclusive and it may return dates in reverse chronological order if *stop* is before *start*. + +# d3.utcTickInterval(start, stop, count) · [Source](https://github.com/d3/d3-time/blob/main/src/ticks.js) + +Returns the time interval that would be used by [d3.utcTicks](#utcTicks) given the same arguments. If there is no associated interval, such as when *start* or *stop* is invalid, returns null. diff --git a/frontend/node_modules/d3-time/dist/d3-time.js b/frontend/node_modules/d3-time/dist/d3-time.js new file mode 100644 index 0000000..6ca6e2d --- /dev/null +++ b/frontend/node_modules/d3-time/dist/d3-time.js @@ -0,0 +1,445 @@ +// https://d3js.org/d3-time/ v3.1.0 Copyright 2010-2022 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-array')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-array'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3)); +})(this, (function (exports, d3Array) { 'use strict'; + +const t0 = new Date, t1 = new Date; + +function timeInterval(floori, offseti, count, field) { + + function interval(date) { + return floori(date = arguments.length === 0 ? new Date : new Date(+date)), date; + } + + interval.floor = (date) => { + return floori(date = new Date(+date)), date; + }; + + interval.ceil = (date) => { + return floori(date = new Date(date - 1)), offseti(date, 1), floori(date), date; + }; + + interval.round = (date) => { + const d0 = interval(date), d1 = interval.ceil(date); + return date - d0 < d1 - date ? d0 : d1; + }; + + interval.offset = (date, step) => { + return offseti(date = new Date(+date), step == null ? 1 : Math.floor(step)), date; + }; + + interval.range = (start, stop, step) => { + const range = []; + start = interval.ceil(start); + step = step == null ? 1 : Math.floor(step); + if (!(start < stop) || !(step > 0)) return range; // also handles Invalid Date + let previous; + do range.push(previous = new Date(+start)), offseti(start, step), floori(start); + while (previous < start && start < stop); + return range; + }; + + interval.filter = (test) => { + return timeInterval((date) => { + if (date >= date) while (floori(date), !test(date)) date.setTime(date - 1); + }, (date, step) => { + if (date >= date) { + if (step < 0) while (++step <= 0) { + while (offseti(date, -1), !test(date)) {} // eslint-disable-line no-empty + } else while (--step >= 0) { + while (offseti(date, +1), !test(date)) {} // eslint-disable-line no-empty + } + } + }); + }; + + if (count) { + interval.count = (start, end) => { + t0.setTime(+start), t1.setTime(+end); + floori(t0), floori(t1); + return Math.floor(count(t0, t1)); + }; + + interval.every = (step) => { + step = Math.floor(step); + return !isFinite(step) || !(step > 0) ? null + : !(step > 1) ? interval + : interval.filter(field + ? (d) => field(d) % step === 0 + : (d) => interval.count(0, d) % step === 0); + }; + } + + return interval; +} + +const millisecond = timeInterval(() => { + // noop +}, (date, step) => { + date.setTime(+date + step); +}, (start, end) => { + return end - start; +}); + +// An optimized implementation for this simple case. +millisecond.every = (k) => { + k = Math.floor(k); + if (!isFinite(k) || !(k > 0)) return null; + if (!(k > 1)) return millisecond; + return timeInterval((date) => { + date.setTime(Math.floor(date / k) * k); + }, (date, step) => { + date.setTime(+date + step * k); + }, (start, end) => { + return (end - start) / k; + }); +}; + +const milliseconds = millisecond.range; + +const durationSecond = 1000; +const durationMinute = durationSecond * 60; +const durationHour = durationMinute * 60; +const durationDay = durationHour * 24; +const durationWeek = durationDay * 7; +const durationMonth = durationDay * 30; +const durationYear = durationDay * 365; + +const second = timeInterval((date) => { + date.setTime(date - date.getMilliseconds()); +}, (date, step) => { + date.setTime(+date + step * durationSecond); +}, (start, end) => { + return (end - start) / durationSecond; +}, (date) => { + return date.getUTCSeconds(); +}); + +const seconds = second.range; + +const timeMinute = timeInterval((date) => { + date.setTime(date - date.getMilliseconds() - date.getSeconds() * durationSecond); +}, (date, step) => { + date.setTime(+date + step * durationMinute); +}, (start, end) => { + return (end - start) / durationMinute; +}, (date) => { + return date.getMinutes(); +}); + +const timeMinutes = timeMinute.range; + +const utcMinute = timeInterval((date) => { + date.setUTCSeconds(0, 0); +}, (date, step) => { + date.setTime(+date + step * durationMinute); +}, (start, end) => { + return (end - start) / durationMinute; +}, (date) => { + return date.getUTCMinutes(); +}); + +const utcMinutes = utcMinute.range; + +const timeHour = timeInterval((date) => { + date.setTime(date - date.getMilliseconds() - date.getSeconds() * durationSecond - date.getMinutes() * durationMinute); +}, (date, step) => { + date.setTime(+date + step * durationHour); +}, (start, end) => { + return (end - start) / durationHour; +}, (date) => { + return date.getHours(); +}); + +const timeHours = timeHour.range; + +const utcHour = timeInterval((date) => { + date.setUTCMinutes(0, 0, 0); +}, (date, step) => { + date.setTime(+date + step * durationHour); +}, (start, end) => { + return (end - start) / durationHour; +}, (date) => { + return date.getUTCHours(); +}); + +const utcHours = utcHour.range; + +const timeDay = timeInterval( + date => date.setHours(0, 0, 0, 0), + (date, step) => date.setDate(date.getDate() + step), + (start, end) => (end - start - (end.getTimezoneOffset() - start.getTimezoneOffset()) * durationMinute) / durationDay, + date => date.getDate() - 1 +); + +const timeDays = timeDay.range; + +const utcDay = timeInterval((date) => { + date.setUTCHours(0, 0, 0, 0); +}, (date, step) => { + date.setUTCDate(date.getUTCDate() + step); +}, (start, end) => { + return (end - start) / durationDay; +}, (date) => { + return date.getUTCDate() - 1; +}); + +const utcDays = utcDay.range; + +const unixDay = timeInterval((date) => { + date.setUTCHours(0, 0, 0, 0); +}, (date, step) => { + date.setUTCDate(date.getUTCDate() + step); +}, (start, end) => { + return (end - start) / durationDay; +}, (date) => { + return Math.floor(date / durationDay); +}); + +const unixDays = unixDay.range; + +function timeWeekday(i) { + return timeInterval((date) => { + date.setDate(date.getDate() - (date.getDay() + 7 - i) % 7); + date.setHours(0, 0, 0, 0); + }, (date, step) => { + date.setDate(date.getDate() + step * 7); + }, (start, end) => { + return (end - start - (end.getTimezoneOffset() - start.getTimezoneOffset()) * durationMinute) / durationWeek; + }); +} + +const timeSunday = timeWeekday(0); +const timeMonday = timeWeekday(1); +const timeTuesday = timeWeekday(2); +const timeWednesday = timeWeekday(3); +const timeThursday = timeWeekday(4); +const timeFriday = timeWeekday(5); +const timeSaturday = timeWeekday(6); + +const timeSundays = timeSunday.range; +const timeMondays = timeMonday.range; +const timeTuesdays = timeTuesday.range; +const timeWednesdays = timeWednesday.range; +const timeThursdays = timeThursday.range; +const timeFridays = timeFriday.range; +const timeSaturdays = timeSaturday.range; + +function utcWeekday(i) { + return timeInterval((date) => { + date.setUTCDate(date.getUTCDate() - (date.getUTCDay() + 7 - i) % 7); + date.setUTCHours(0, 0, 0, 0); + }, (date, step) => { + date.setUTCDate(date.getUTCDate() + step * 7); + }, (start, end) => { + return (end - start) / durationWeek; + }); +} + +const utcSunday = utcWeekday(0); +const utcMonday = utcWeekday(1); +const utcTuesday = utcWeekday(2); +const utcWednesday = utcWeekday(3); +const utcThursday = utcWeekday(4); +const utcFriday = utcWeekday(5); +const utcSaturday = utcWeekday(6); + +const utcSundays = utcSunday.range; +const utcMondays = utcMonday.range; +const utcTuesdays = utcTuesday.range; +const utcWednesdays = utcWednesday.range; +const utcThursdays = utcThursday.range; +const utcFridays = utcFriday.range; +const utcSaturdays = utcSaturday.range; + +const timeMonth = timeInterval((date) => { + date.setDate(1); + date.setHours(0, 0, 0, 0); +}, (date, step) => { + date.setMonth(date.getMonth() + step); +}, (start, end) => { + return end.getMonth() - start.getMonth() + (end.getFullYear() - start.getFullYear()) * 12; +}, (date) => { + return date.getMonth(); +}); + +const timeMonths = timeMonth.range; + +const utcMonth = timeInterval((date) => { + date.setUTCDate(1); + date.setUTCHours(0, 0, 0, 0); +}, (date, step) => { + date.setUTCMonth(date.getUTCMonth() + step); +}, (start, end) => { + return end.getUTCMonth() - start.getUTCMonth() + (end.getUTCFullYear() - start.getUTCFullYear()) * 12; +}, (date) => { + return date.getUTCMonth(); +}); + +const utcMonths = utcMonth.range; + +const timeYear = timeInterval((date) => { + date.setMonth(0, 1); + date.setHours(0, 0, 0, 0); +}, (date, step) => { + date.setFullYear(date.getFullYear() + step); +}, (start, end) => { + return end.getFullYear() - start.getFullYear(); +}, (date) => { + return date.getFullYear(); +}); + +// An optimized implementation for this simple case. +timeYear.every = (k) => { + return !isFinite(k = Math.floor(k)) || !(k > 0) ? null : timeInterval((date) => { + date.setFullYear(Math.floor(date.getFullYear() / k) * k); + date.setMonth(0, 1); + date.setHours(0, 0, 0, 0); + }, (date, step) => { + date.setFullYear(date.getFullYear() + step * k); + }); +}; + +const timeYears = timeYear.range; + +const utcYear = timeInterval((date) => { + date.setUTCMonth(0, 1); + date.setUTCHours(0, 0, 0, 0); +}, (date, step) => { + date.setUTCFullYear(date.getUTCFullYear() + step); +}, (start, end) => { + return end.getUTCFullYear() - start.getUTCFullYear(); +}, (date) => { + return date.getUTCFullYear(); +}); + +// An optimized implementation for this simple case. +utcYear.every = (k) => { + return !isFinite(k = Math.floor(k)) || !(k > 0) ? null : timeInterval((date) => { + date.setUTCFullYear(Math.floor(date.getUTCFullYear() / k) * k); + date.setUTCMonth(0, 1); + date.setUTCHours(0, 0, 0, 0); + }, (date, step) => { + date.setUTCFullYear(date.getUTCFullYear() + step * k); + }); +}; + +const utcYears = utcYear.range; + +function ticker(year, month, week, day, hour, minute) { + + const tickIntervals = [ + [second, 1, durationSecond], + [second, 5, 5 * durationSecond], + [second, 15, 15 * durationSecond], + [second, 30, 30 * durationSecond], + [minute, 1, durationMinute], + [minute, 5, 5 * durationMinute], + [minute, 15, 15 * durationMinute], + [minute, 30, 30 * durationMinute], + [ hour, 1, durationHour ], + [ hour, 3, 3 * durationHour ], + [ hour, 6, 6 * durationHour ], + [ hour, 12, 12 * durationHour ], + [ day, 1, durationDay ], + [ day, 2, 2 * durationDay ], + [ week, 1, durationWeek ], + [ month, 1, durationMonth ], + [ month, 3, 3 * durationMonth ], + [ year, 1, durationYear ] + ]; + + function ticks(start, stop, count) { + const reverse = stop < start; + if (reverse) [start, stop] = [stop, start]; + const interval = count && typeof count.range === "function" ? count : tickInterval(start, stop, count); + const ticks = interval ? interval.range(start, +stop + 1) : []; // inclusive stop + return reverse ? ticks.reverse() : ticks; + } + + function tickInterval(start, stop, count) { + const target = Math.abs(stop - start) / count; + const i = d3Array.bisector(([,, step]) => step).right(tickIntervals, target); + if (i === tickIntervals.length) return year.every(d3Array.tickStep(start / durationYear, stop / durationYear, count)); + if (i === 0) return millisecond.every(Math.max(d3Array.tickStep(start, stop, count), 1)); + const [t, step] = tickIntervals[target / tickIntervals[i - 1][2] < tickIntervals[i][2] / target ? i - 1 : i]; + return t.every(step); + } + + return [ticks, tickInterval]; +} + +const [utcTicks, utcTickInterval] = ticker(utcYear, utcMonth, utcSunday, unixDay, utcHour, utcMinute); +const [timeTicks, timeTickInterval] = ticker(timeYear, timeMonth, timeSunday, timeDay, timeHour, timeMinute); + +exports.timeDay = timeDay; +exports.timeDays = timeDays; +exports.timeFriday = timeFriday; +exports.timeFridays = timeFridays; +exports.timeHour = timeHour; +exports.timeHours = timeHours; +exports.timeInterval = timeInterval; +exports.timeMillisecond = millisecond; +exports.timeMilliseconds = milliseconds; +exports.timeMinute = timeMinute; +exports.timeMinutes = timeMinutes; +exports.timeMonday = timeMonday; +exports.timeMondays = timeMondays; +exports.timeMonth = timeMonth; +exports.timeMonths = timeMonths; +exports.timeSaturday = timeSaturday; +exports.timeSaturdays = timeSaturdays; +exports.timeSecond = second; +exports.timeSeconds = seconds; +exports.timeSunday = timeSunday; +exports.timeSundays = timeSundays; +exports.timeThursday = timeThursday; +exports.timeThursdays = timeThursdays; +exports.timeTickInterval = timeTickInterval; +exports.timeTicks = timeTicks; +exports.timeTuesday = timeTuesday; +exports.timeTuesdays = timeTuesdays; +exports.timeWednesday = timeWednesday; +exports.timeWednesdays = timeWednesdays; +exports.timeWeek = timeSunday; +exports.timeWeeks = timeSundays; +exports.timeYear = timeYear; +exports.timeYears = timeYears; +exports.unixDay = unixDay; +exports.unixDays = unixDays; +exports.utcDay = utcDay; +exports.utcDays = utcDays; +exports.utcFriday = utcFriday; +exports.utcFridays = utcFridays; +exports.utcHour = utcHour; +exports.utcHours = utcHours; +exports.utcMillisecond = millisecond; +exports.utcMilliseconds = milliseconds; +exports.utcMinute = utcMinute; +exports.utcMinutes = utcMinutes; +exports.utcMonday = utcMonday; +exports.utcMondays = utcMondays; +exports.utcMonth = utcMonth; +exports.utcMonths = utcMonths; +exports.utcSaturday = utcSaturday; +exports.utcSaturdays = utcSaturdays; +exports.utcSecond = second; +exports.utcSeconds = seconds; +exports.utcSunday = utcSunday; +exports.utcSundays = utcSundays; +exports.utcThursday = utcThursday; +exports.utcThursdays = utcThursdays; +exports.utcTickInterval = utcTickInterval; +exports.utcTicks = utcTicks; +exports.utcTuesday = utcTuesday; +exports.utcTuesdays = utcTuesdays; +exports.utcWednesday = utcWednesday; +exports.utcWednesdays = utcWednesdays; +exports.utcWeek = utcSunday; +exports.utcWeeks = utcSundays; +exports.utcYear = utcYear; +exports.utcYears = utcYears; + +})); diff --git a/frontend/node_modules/d3-time/dist/d3-time.min.js b/frontend/node_modules/d3-time/dist/d3-time.min.js new file mode 100644 index 0000000..27b04db --- /dev/null +++ b/frontend/node_modules/d3-time/dist/d3-time.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-time/ v3.1.0 Copyright 2010-2022 Mike Bostock +!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports,require("d3-array")):"function"==typeof define&&define.amd?define(["exports","d3-array"],t):t((e="undefined"!=typeof globalThis?globalThis:e||self).d3=e.d3||{},e.d3)}(this,(function(e,t){"use strict";const n=new Date,s=new Date;function r(e,t,a,u){function i(t){return e(t=0===arguments.length?new Date:new Date(+t)),t}return i.floor=t=>(e(t=new Date(+t)),t),i.ceil=n=>(e(n=new Date(n-1)),t(n,1),e(n),n),i.round=e=>{const t=i(e),n=i.ceil(e);return e-t(t(e=new Date(+e),null==n?1:Math.floor(n)),e),i.range=(n,s,r)=>{const a=[];if(n=i.ceil(n),r=null==r?1:Math.floor(r),!(n0))return a;let u;do{a.push(u=new Date(+n)),t(n,r),e(n)}while(ur((t=>{if(t>=t)for(;e(t),!n(t);)t.setTime(t-1)}),((e,s)=>{if(e>=e)if(s<0)for(;++s<=0;)for(;t(e,-1),!n(e););else for(;--s>=0;)for(;t(e,1),!n(e););})),a&&(i.count=(t,r)=>(n.setTime(+t),s.setTime(+r),e(n),e(s),Math.floor(a(n,s))),i.every=e=>(e=Math.floor(e),isFinite(e)&&e>0?e>1?i.filter(u?t=>u(t)%e==0:t=>i.count(0,t)%e==0):i:null)),i}const a=r((()=>{}),((e,t)=>{e.setTime(+e+t)}),((e,t)=>t-e));a.every=e=>(e=Math.floor(e),isFinite(e)&&e>0?e>1?r((t=>{t.setTime(Math.floor(t/e)*e)}),((t,n)=>{t.setTime(+t+n*e)}),((t,n)=>(n-t)/e)):a:null);const u=a.range,i=1e3,o=6e4,l=36e5,c=864e5,g=6048e5,T=2592e6,d=31536e6,f=r((e=>{e.setTime(e-e.getMilliseconds())}),((e,t)=>{e.setTime(+e+t*i)}),((e,t)=>(t-e)/i),(e=>e.getUTCSeconds())),m=f.range,y=r((e=>{e.setTime(e-e.getMilliseconds()-e.getSeconds()*i)}),((e,t)=>{e.setTime(+e+t*o)}),((e,t)=>(t-e)/o),(e=>e.getMinutes())),M=y.range,h=r((e=>{e.setUTCSeconds(0,0)}),((e,t)=>{e.setTime(+e+t*o)}),((e,t)=>(t-e)/o),(e=>e.getUTCMinutes())),C=h.range,U=r((e=>{e.setTime(e-e.getMilliseconds()-e.getSeconds()*i-e.getMinutes()*o)}),((e,t)=>{e.setTime(+e+t*l)}),((e,t)=>(t-e)/l),(e=>e.getHours())),D=U.range,F=r((e=>{e.setUTCMinutes(0,0,0)}),((e,t)=>{e.setTime(+e+t*l)}),((e,t)=>(t-e)/l),(e=>e.getUTCHours())),Y=F.range,S=r((e=>e.setHours(0,0,0,0)),((e,t)=>e.setDate(e.getDate()+t)),((e,t)=>(t-e-(t.getTimezoneOffset()-e.getTimezoneOffset())*o)/c),(e=>e.getDate()-1)),H=S.range,p=r((e=>{e.setUTCHours(0,0,0,0)}),((e,t)=>{e.setUTCDate(e.getUTCDate()+t)}),((e,t)=>(t-e)/c),(e=>e.getUTCDate()-1)),v=p.range,k=r((e=>{e.setUTCHours(0,0,0,0)}),((e,t)=>{e.setUTCDate(e.getUTCDate()+t)}),((e,t)=>(t-e)/c),(e=>Math.floor(e/c))),w=k.range;function W(e){return r((t=>{t.setDate(t.getDate()-(t.getDay()+7-e)%7),t.setHours(0,0,0,0)}),((e,t)=>{e.setDate(e.getDate()+7*t)}),((e,t)=>(t-e-(t.getTimezoneOffset()-e.getTimezoneOffset())*o)/g))}const x=W(0),b=W(1),z=W(2),O=W(3),I=W(4),j=W(5),q=W(6),A=x.range,B=b.range,E=z.range,G=O.range,J=I.range,K=j.range,L=q.range;function N(e){return r((t=>{t.setUTCDate(t.getUTCDate()-(t.getUTCDay()+7-e)%7),t.setUTCHours(0,0,0,0)}),((e,t)=>{e.setUTCDate(e.getUTCDate()+7*t)}),((e,t)=>(t-e)/g))}const P=N(0),Q=N(1),R=N(2),V=N(3),X=N(4),Z=N(5),$=N(6),_=P.range,ee=Q.range,te=R.range,ne=V.range,se=X.range,re=Z.range,ae=$.range,ue=r((e=>{e.setDate(1),e.setHours(0,0,0,0)}),((e,t)=>{e.setMonth(e.getMonth()+t)}),((e,t)=>t.getMonth()-e.getMonth()+12*(t.getFullYear()-e.getFullYear())),(e=>e.getMonth())),ie=ue.range,oe=r((e=>{e.setUTCDate(1),e.setUTCHours(0,0,0,0)}),((e,t)=>{e.setUTCMonth(e.getUTCMonth()+t)}),((e,t)=>t.getUTCMonth()-e.getUTCMonth()+12*(t.getUTCFullYear()-e.getUTCFullYear())),(e=>e.getUTCMonth())),le=oe.range,ce=r((e=>{e.setMonth(0,1),e.setHours(0,0,0,0)}),((e,t)=>{e.setFullYear(e.getFullYear()+t)}),((e,t)=>t.getFullYear()-e.getFullYear()),(e=>e.getFullYear()));ce.every=e=>isFinite(e=Math.floor(e))&&e>0?r((t=>{t.setFullYear(Math.floor(t.getFullYear()/e)*e),t.setMonth(0,1),t.setHours(0,0,0,0)}),((t,n)=>{t.setFullYear(t.getFullYear()+n*e)})):null;const ge=ce.range,Te=r((e=>{e.setUTCMonth(0,1),e.setUTCHours(0,0,0,0)}),((e,t)=>{e.setUTCFullYear(e.getUTCFullYear()+t)}),((e,t)=>t.getUTCFullYear()-e.getUTCFullYear()),(e=>e.getUTCFullYear()));Te.every=e=>isFinite(e=Math.floor(e))&&e>0?r((t=>{t.setUTCFullYear(Math.floor(t.getUTCFullYear()/e)*e),t.setUTCMonth(0,1),t.setUTCHours(0,0,0,0)}),((t,n)=>{t.setUTCFullYear(t.getUTCFullYear()+n*e)})):null;const de=Te.range;function fe(e,n,s,r,u,m){const y=[[f,1,i],[f,5,5e3],[f,15,15e3],[f,30,3e4],[m,1,o],[m,5,3e5],[m,15,9e5],[m,30,18e5],[u,1,l],[u,3,108e5],[u,6,216e5],[u,12,432e5],[r,1,c],[r,2,1728e5],[s,1,g],[n,1,T],[n,3,7776e6],[e,1,d]];function M(n,s,r){const u=Math.abs(s-n)/r,i=t.bisector((([,,e])=>e)).right(y,u);if(i===y.length)return e.every(t.tickStep(n/d,s/d,r));if(0===i)return a.every(Math.max(t.tickStep(n,s,r),1));const[o,l]=y[u/y[i-1][2]=12" + } +} diff --git a/frontend/node_modules/d3-time/src/day.js b/frontend/node_modules/d3-time/src/day.js new file mode 100644 index 0000000..2b5d4b6 --- /dev/null +++ b/frontend/node_modules/d3-time/src/day.js @@ -0,0 +1,35 @@ +import {timeInterval} from "./interval.js"; +import {durationDay, durationMinute} from "./duration.js"; + +export const timeDay = timeInterval( + date => date.setHours(0, 0, 0, 0), + (date, step) => date.setDate(date.getDate() + step), + (start, end) => (end - start - (end.getTimezoneOffset() - start.getTimezoneOffset()) * durationMinute) / durationDay, + date => date.getDate() - 1 +); + +export const timeDays = timeDay.range; + +export const utcDay = timeInterval((date) => { + date.setUTCHours(0, 0, 0, 0); +}, (date, step) => { + date.setUTCDate(date.getUTCDate() + step); +}, (start, end) => { + return (end - start) / durationDay; +}, (date) => { + return date.getUTCDate() - 1; +}); + +export const utcDays = utcDay.range; + +export const unixDay = timeInterval((date) => { + date.setUTCHours(0, 0, 0, 0); +}, (date, step) => { + date.setUTCDate(date.getUTCDate() + step); +}, (start, end) => { + return (end - start) / durationDay; +}, (date) => { + return Math.floor(date / durationDay); +}); + +export const unixDays = unixDay.range; diff --git a/frontend/node_modules/d3-time/src/duration.js b/frontend/node_modules/d3-time/src/duration.js new file mode 100644 index 0000000..341fa8f --- /dev/null +++ b/frontend/node_modules/d3-time/src/duration.js @@ -0,0 +1,7 @@ +export const durationSecond = 1000; +export const durationMinute = durationSecond * 60; +export const durationHour = durationMinute * 60; +export const durationDay = durationHour * 24; +export const durationWeek = durationDay * 7; +export const durationMonth = durationDay * 30; +export const durationYear = durationDay * 365; diff --git a/frontend/node_modules/d3-time/src/hour.js b/frontend/node_modules/d3-time/src/hour.js new file mode 100644 index 0000000..77b77a3 --- /dev/null +++ b/frontend/node_modules/d3-time/src/hour.js @@ -0,0 +1,26 @@ +import {timeInterval} from "./interval.js"; +import {durationHour, durationMinute, durationSecond} from "./duration.js"; + +export const timeHour = timeInterval((date) => { + date.setTime(date - date.getMilliseconds() - date.getSeconds() * durationSecond - date.getMinutes() * durationMinute); +}, (date, step) => { + date.setTime(+date + step * durationHour); +}, (start, end) => { + return (end - start) / durationHour; +}, (date) => { + return date.getHours(); +}); + +export const timeHours = timeHour.range; + +export const utcHour = timeInterval((date) => { + date.setUTCMinutes(0, 0, 0); +}, (date, step) => { + date.setTime(+date + step * durationHour); +}, (start, end) => { + return (end - start) / durationHour; +}, (date) => { + return date.getUTCHours(); +}); + +export const utcHours = utcHour.range; diff --git a/frontend/node_modules/d3-time/src/index.js b/frontend/node_modules/d3-time/src/index.js new file mode 100644 index 0000000..d6dfd90 --- /dev/null +++ b/frontend/node_modules/d3-time/src/index.js @@ -0,0 +1,96 @@ +export { + timeInterval +} from "./interval.js"; + +export { + millisecond as utcMillisecond, + milliseconds as utcMilliseconds, + millisecond as timeMillisecond, + milliseconds as timeMilliseconds +} from "./millisecond.js"; + +export { + second as utcSecond, + seconds as utcSeconds, + second as timeSecond, + seconds as timeSeconds +} from "./second.js"; + +export { + timeMinute, + timeMinutes, + utcMinute, + utcMinutes +} from "./minute.js"; + +export { + timeHour, + timeHours, + utcHour, + utcHours +} from "./hour.js"; + +export { + timeDay, + timeDays, + utcDay, + utcDays, + unixDay, + unixDays +} from "./day.js"; + +export { + timeSunday as timeWeek, + timeSundays as timeWeeks, + timeSunday, + timeSundays, + timeMonday, + timeMondays, + timeTuesday, + timeTuesdays, + timeWednesday, + timeWednesdays, + timeThursday, + timeThursdays, + timeFriday, + timeFridays, + timeSaturday, + timeSaturdays, + utcSunday as utcWeek, + utcSundays as utcWeeks, + utcSunday, + utcSundays, + utcMonday, + utcMondays, + utcTuesday, + utcTuesdays, + utcWednesday, + utcWednesdays, + utcThursday, + utcThursdays, + utcFriday, + utcFridays, + utcSaturday, + utcSaturdays +} from "./week.js"; + +export { + timeMonth, + timeMonths, + utcMonth, + utcMonths +} from "./month.js"; + +export { + timeYear, + timeYears, + utcYear, + utcYears +} from "./year.js"; + +export { + utcTicks, + utcTickInterval, + timeTicks, + timeTickInterval +} from "./ticks.js"; diff --git a/frontend/node_modules/d3-time/src/interval.js b/frontend/node_modules/d3-time/src/interval.js new file mode 100644 index 0000000..492ae90 --- /dev/null +++ b/frontend/node_modules/d3-time/src/interval.js @@ -0,0 +1,69 @@ +const t0 = new Date, t1 = new Date; + +export function timeInterval(floori, offseti, count, field) { + + function interval(date) { + return floori(date = arguments.length === 0 ? new Date : new Date(+date)), date; + } + + interval.floor = (date) => { + return floori(date = new Date(+date)), date; + }; + + interval.ceil = (date) => { + return floori(date = new Date(date - 1)), offseti(date, 1), floori(date), date; + }; + + interval.round = (date) => { + const d0 = interval(date), d1 = interval.ceil(date); + return date - d0 < d1 - date ? d0 : d1; + }; + + interval.offset = (date, step) => { + return offseti(date = new Date(+date), step == null ? 1 : Math.floor(step)), date; + }; + + interval.range = (start, stop, step) => { + const range = []; + start = interval.ceil(start); + step = step == null ? 1 : Math.floor(step); + if (!(start < stop) || !(step > 0)) return range; // also handles Invalid Date + let previous; + do range.push(previous = new Date(+start)), offseti(start, step), floori(start); + while (previous < start && start < stop); + return range; + }; + + interval.filter = (test) => { + return timeInterval((date) => { + if (date >= date) while (floori(date), !test(date)) date.setTime(date - 1); + }, (date, step) => { + if (date >= date) { + if (step < 0) while (++step <= 0) { + while (offseti(date, -1), !test(date)) {} // eslint-disable-line no-empty + } else while (--step >= 0) { + while (offseti(date, +1), !test(date)) {} // eslint-disable-line no-empty + } + } + }); + }; + + if (count) { + interval.count = (start, end) => { + t0.setTime(+start), t1.setTime(+end); + floori(t0), floori(t1); + return Math.floor(count(t0, t1)); + }; + + interval.every = (step) => { + step = Math.floor(step); + return !isFinite(step) || !(step > 0) ? null + : !(step > 1) ? interval + : interval.filter(field + ? (d) => field(d) % step === 0 + : (d) => interval.count(0, d) % step === 0); + }; + } + + return interval; +} diff --git a/frontend/node_modules/d3-time/src/millisecond.js b/frontend/node_modules/d3-time/src/millisecond.js new file mode 100644 index 0000000..e3aa380 --- /dev/null +++ b/frontend/node_modules/d3-time/src/millisecond.js @@ -0,0 +1,25 @@ +import {timeInterval} from "./interval.js"; + +export const millisecond = timeInterval(() => { + // noop +}, (date, step) => { + date.setTime(+date + step); +}, (start, end) => { + return end - start; +}); + +// An optimized implementation for this simple case. +millisecond.every = (k) => { + k = Math.floor(k); + if (!isFinite(k) || !(k > 0)) return null; + if (!(k > 1)) return millisecond; + return timeInterval((date) => { + date.setTime(Math.floor(date / k) * k); + }, (date, step) => { + date.setTime(+date + step * k); + }, (start, end) => { + return (end - start) / k; + }); +}; + +export const milliseconds = millisecond.range; diff --git a/frontend/node_modules/d3-time/src/minute.js b/frontend/node_modules/d3-time/src/minute.js new file mode 100644 index 0000000..ba8e4d9 --- /dev/null +++ b/frontend/node_modules/d3-time/src/minute.js @@ -0,0 +1,26 @@ +import {timeInterval} from "./interval.js"; +import {durationMinute, durationSecond} from "./duration.js"; + +export const timeMinute = timeInterval((date) => { + date.setTime(date - date.getMilliseconds() - date.getSeconds() * durationSecond); +}, (date, step) => { + date.setTime(+date + step * durationMinute); +}, (start, end) => { + return (end - start) / durationMinute; +}, (date) => { + return date.getMinutes(); +}); + +export const timeMinutes = timeMinute.range; + +export const utcMinute = timeInterval((date) => { + date.setUTCSeconds(0, 0); +}, (date, step) => { + date.setTime(+date + step * durationMinute); +}, (start, end) => { + return (end - start) / durationMinute; +}, (date) => { + return date.getUTCMinutes(); +}); + +export const utcMinutes = utcMinute.range; diff --git a/frontend/node_modules/d3-time/src/month.js b/frontend/node_modules/d3-time/src/month.js new file mode 100644 index 0000000..6dab69c --- /dev/null +++ b/frontend/node_modules/d3-time/src/month.js @@ -0,0 +1,27 @@ +import {timeInterval} from "./interval.js"; + +export const timeMonth = timeInterval((date) => { + date.setDate(1); + date.setHours(0, 0, 0, 0); +}, (date, step) => { + date.setMonth(date.getMonth() + step); +}, (start, end) => { + return end.getMonth() - start.getMonth() + (end.getFullYear() - start.getFullYear()) * 12; +}, (date) => { + return date.getMonth(); +}); + +export const timeMonths = timeMonth.range; + +export const utcMonth = timeInterval((date) => { + date.setUTCDate(1); + date.setUTCHours(0, 0, 0, 0); +}, (date, step) => { + date.setUTCMonth(date.getUTCMonth() + step); +}, (start, end) => { + return end.getUTCMonth() - start.getUTCMonth() + (end.getUTCFullYear() - start.getUTCFullYear()) * 12; +}, (date) => { + return date.getUTCMonth(); +}); + +export const utcMonths = utcMonth.range; diff --git a/frontend/node_modules/d3-time/src/second.js b/frontend/node_modules/d3-time/src/second.js new file mode 100644 index 0000000..47b2f43 --- /dev/null +++ b/frontend/node_modules/d3-time/src/second.js @@ -0,0 +1,14 @@ +import {timeInterval} from "./interval.js"; +import {durationSecond} from "./duration.js"; + +export const second = timeInterval((date) => { + date.setTime(date - date.getMilliseconds()); +}, (date, step) => { + date.setTime(+date + step * durationSecond); +}, (start, end) => { + return (end - start) / durationSecond; +}, (date) => { + return date.getUTCSeconds(); +}); + +export const seconds = second.range; diff --git a/frontend/node_modules/d3-time/src/ticks.js b/frontend/node_modules/d3-time/src/ticks.js new file mode 100644 index 0000000..c314789 --- /dev/null +++ b/frontend/node_modules/d3-time/src/ticks.js @@ -0,0 +1,58 @@ +import {bisector, tickStep} from "d3-array"; +import {durationDay, durationHour, durationMinute, durationMonth, durationSecond, durationWeek, durationYear} from "./duration.js"; +import {millisecond} from "./millisecond.js"; +import {second} from "./second.js"; +import {timeMinute, utcMinute} from "./minute.js"; +import {timeHour, utcHour} from "./hour.js"; +import {timeDay, unixDay} from "./day.js"; +import {timeSunday, utcSunday} from "./week.js"; +import {timeMonth, utcMonth} from "./month.js"; +import {timeYear, utcYear} from "./year.js"; + +function ticker(year, month, week, day, hour, minute) { + + const tickIntervals = [ + [second, 1, durationSecond], + [second, 5, 5 * durationSecond], + [second, 15, 15 * durationSecond], + [second, 30, 30 * durationSecond], + [minute, 1, durationMinute], + [minute, 5, 5 * durationMinute], + [minute, 15, 15 * durationMinute], + [minute, 30, 30 * durationMinute], + [ hour, 1, durationHour ], + [ hour, 3, 3 * durationHour ], + [ hour, 6, 6 * durationHour ], + [ hour, 12, 12 * durationHour ], + [ day, 1, durationDay ], + [ day, 2, 2 * durationDay ], + [ week, 1, durationWeek ], + [ month, 1, durationMonth ], + [ month, 3, 3 * durationMonth ], + [ year, 1, durationYear ] + ]; + + function ticks(start, stop, count) { + const reverse = stop < start; + if (reverse) [start, stop] = [stop, start]; + const interval = count && typeof count.range === "function" ? count : tickInterval(start, stop, count); + const ticks = interval ? interval.range(start, +stop + 1) : []; // inclusive stop + return reverse ? ticks.reverse() : ticks; + } + + function tickInterval(start, stop, count) { + const target = Math.abs(stop - start) / count; + const i = bisector(([,, step]) => step).right(tickIntervals, target); + if (i === tickIntervals.length) return year.every(tickStep(start / durationYear, stop / durationYear, count)); + if (i === 0) return millisecond.every(Math.max(tickStep(start, stop, count), 1)); + const [t, step] = tickIntervals[target / tickIntervals[i - 1][2] < tickIntervals[i][2] / target ? i - 1 : i]; + return t.every(step); + } + + return [ticks, tickInterval]; +} + +const [utcTicks, utcTickInterval] = ticker(utcYear, utcMonth, utcSunday, unixDay, utcHour, utcMinute); +const [timeTicks, timeTickInterval] = ticker(timeYear, timeMonth, timeSunday, timeDay, timeHour, timeMinute); + +export {utcTicks, utcTickInterval, timeTicks, timeTickInterval}; diff --git a/frontend/node_modules/d3-time/src/week.js b/frontend/node_modules/d3-time/src/week.js new file mode 100644 index 0000000..f75ff52 --- /dev/null +++ b/frontend/node_modules/d3-time/src/week.js @@ -0,0 +1,56 @@ +import {timeInterval} from "./interval.js"; +import {durationMinute, durationWeek} from "./duration.js"; + +function timeWeekday(i) { + return timeInterval((date) => { + date.setDate(date.getDate() - (date.getDay() + 7 - i) % 7); + date.setHours(0, 0, 0, 0); + }, (date, step) => { + date.setDate(date.getDate() + step * 7); + }, (start, end) => { + return (end - start - (end.getTimezoneOffset() - start.getTimezoneOffset()) * durationMinute) / durationWeek; + }); +} + +export const timeSunday = timeWeekday(0); +export const timeMonday = timeWeekday(1); +export const timeTuesday = timeWeekday(2); +export const timeWednesday = timeWeekday(3); +export const timeThursday = timeWeekday(4); +export const timeFriday = timeWeekday(5); +export const timeSaturday = timeWeekday(6); + +export const timeSundays = timeSunday.range; +export const timeMondays = timeMonday.range; +export const timeTuesdays = timeTuesday.range; +export const timeWednesdays = timeWednesday.range; +export const timeThursdays = timeThursday.range; +export const timeFridays = timeFriday.range; +export const timeSaturdays = timeSaturday.range; + +function utcWeekday(i) { + return timeInterval((date) => { + date.setUTCDate(date.getUTCDate() - (date.getUTCDay() + 7 - i) % 7); + date.setUTCHours(0, 0, 0, 0); + }, (date, step) => { + date.setUTCDate(date.getUTCDate() + step * 7); + }, (start, end) => { + return (end - start) / durationWeek; + }); +} + +export const utcSunday = utcWeekday(0); +export const utcMonday = utcWeekday(1); +export const utcTuesday = utcWeekday(2); +export const utcWednesday = utcWeekday(3); +export const utcThursday = utcWeekday(4); +export const utcFriday = utcWeekday(5); +export const utcSaturday = utcWeekday(6); + +export const utcSundays = utcSunday.range; +export const utcMondays = utcMonday.range; +export const utcTuesdays = utcTuesday.range; +export const utcWednesdays = utcWednesday.range; +export const utcThursdays = utcThursday.range; +export const utcFridays = utcFriday.range; +export const utcSaturdays = utcSaturday.range; diff --git a/frontend/node_modules/d3-time/src/year.js b/frontend/node_modules/d3-time/src/year.js new file mode 100644 index 0000000..9eadff3 --- /dev/null +++ b/frontend/node_modules/d3-time/src/year.js @@ -0,0 +1,49 @@ +import {timeInterval} from "./interval.js"; + +export const timeYear = timeInterval((date) => { + date.setMonth(0, 1); + date.setHours(0, 0, 0, 0); +}, (date, step) => { + date.setFullYear(date.getFullYear() + step); +}, (start, end) => { + return end.getFullYear() - start.getFullYear(); +}, (date) => { + return date.getFullYear(); +}); + +// An optimized implementation for this simple case. +timeYear.every = (k) => { + return !isFinite(k = Math.floor(k)) || !(k > 0) ? null : timeInterval((date) => { + date.setFullYear(Math.floor(date.getFullYear() / k) * k); + date.setMonth(0, 1); + date.setHours(0, 0, 0, 0); + }, (date, step) => { + date.setFullYear(date.getFullYear() + step * k); + }); +}; + +export const timeYears = timeYear.range; + +export const utcYear = timeInterval((date) => { + date.setUTCMonth(0, 1); + date.setUTCHours(0, 0, 0, 0); +}, (date, step) => { + date.setUTCFullYear(date.getUTCFullYear() + step); +}, (start, end) => { + return end.getUTCFullYear() - start.getUTCFullYear(); +}, (date) => { + return date.getUTCFullYear(); +}); + +// An optimized implementation for this simple case. +utcYear.every = (k) => { + return !isFinite(k = Math.floor(k)) || !(k > 0) ? null : timeInterval((date) => { + date.setUTCFullYear(Math.floor(date.getUTCFullYear() / k) * k); + date.setUTCMonth(0, 1); + date.setUTCHours(0, 0, 0, 0); + }, (date, step) => { + date.setUTCFullYear(date.getUTCFullYear() + step * k); + }); +}; + +export const utcYears = utcYear.range; diff --git a/frontend/node_modules/d3-timer/LICENSE b/frontend/node_modules/d3-timer/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-timer/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-timer/README.md b/frontend/node_modules/d3-timer/README.md new file mode 100644 index 0000000..a78ce3e --- /dev/null +++ b/frontend/node_modules/d3-timer/README.md @@ -0,0 +1,87 @@ +# d3-timer + +This module provides an efficient queue capable of managing thousands of concurrent animations, while guaranteeing consistent, synchronized timing with concurrent or staged animations. Internally, it uses [requestAnimationFrame](https://developer.mozilla.org/en-US/docs/Web/API/window/requestAnimationFrame) for fluid animation (if available), switching to [setTimeout](https://developer.mozilla.org/en-US/docs/Web/API/WindowTimers/setTimeout) for delays longer than 24ms. + +## Installing + +If you use npm, `npm install d3-timer`. You can also download the [latest release on GitHub](https://github.com/d3/d3-timer/releases/latest). For vanilla HTML in modern browsers, import d3-timer from Skypack: + +```html + +``` + +For legacy environments, you can load d3-timer’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + +``` + +## API Reference + +# d3.now() [<>](https://github.com/d3/d3-timer/blob/master/src/timer.js "Source") + +Returns the current time as defined by [performance.now](https://developer.mozilla.org/en-US/docs/Web/API/Performance/now) if available, and [Date.now](https://developer.mozilla.org/en-US/docs/JavaScript/Reference/Global_Objects/Date/now) if not. The current time is updated at the start of a frame; it is thus consistent during the frame, and any timers scheduled during the same frame will be synchronized. If this method is called outside of a frame, such as in response to a user event, the current time is calculated and then fixed until the next frame, again ensuring consistent timing during event handling. + +# d3.timer(callback[, delay[, time]]) [<>](https://github.com/d3/d3-timer/blob/master/src/timer.js "Source") + +Schedules a new timer, invoking the specified *callback* repeatedly until the timer is [stopped](#timer_stop). An optional numeric *delay* in milliseconds may be specified to invoke the given *callback* after a delay; if *delay* is not specified, it defaults to zero. The delay is relative to the specified *time* in milliseconds; if *time* is not specified, it defaults to [now](#now). + +The *callback* is passed the (apparent) *elapsed* time since the timer became active. For example: + +```js +const t = d3.timer((elapsed) => { + console.log(elapsed); + if (elapsed > 200) t.stop(); +}, 150); +``` + +This produces roughly the following console output: + +``` +3 +25 +48 +65 +85 +106 +125 +146 +167 +189 +209 +``` + +(The exact values may vary depending on your JavaScript runtime and what else your computer is doing.) Note that the first *elapsed* time is 3ms: this is the elapsed time since the timer started, not since the timer was scheduled. Here the timer started 150ms after it was scheduled due to the specified delay. The apparent *elapsed* time may be less than the true *elapsed* time if the page is backgrounded and [requestAnimationFrame](https://developer.mozilla.org/en-US/docs/Web/API/window/requestAnimationFrame) is paused; in the background, apparent time is frozen. + +If [timer](#timer) is called within the callback of another timer, the new timer callback (if eligible as determined by the specified *delay* and *time*) will be invoked immediately at the end of the current frame, rather than waiting until the next frame. Within a frame, timer callbacks are guaranteed to be invoked in the order they were scheduled, regardless of their start time. + +# timer.restart(callback[, delay[, time]]) [<>](https://github.com/d3/d3-timer/blob/master/src/timer.js "Source") + +Restart a timer with the specified *callback* and optional *delay* and *time*. This is equivalent to stopping this timer and creating a new timer with the specified arguments, although this timer retains the original invocation priority. + +# timer.stop() [<>](https://github.com/d3/d3-timer/blob/master/src/timer.js "Source") + +Stops this timer, preventing subsequent callbacks. This method has no effect if the timer has already stopped. + +# d3.timerFlush() [<>](https://github.com/d3/d3-timer/blob/master/src/timer.js "Source") + +Immediately invoke any eligible timer callbacks. Note that zero-delay timers are normally first executed after one frame (~17ms). This can cause a brief flicker because the browser renders the page twice: once at the end of the first event loop, then again immediately on the first timer callback. By flushing the timer queue at the end of the first event loop, you can run any zero-delay timers immediately and avoid the flicker. + +# d3.timeout(callback[, delay[, time]]) [<>](https://github.com/d3/d3-timer/blob/master/src/timeout.js "Source") + +Like [timer](#timer), except the timer automatically [stops](#timer_stop) on its first callback. A suitable replacement for [setTimeout](https://developer.mozilla.org/en-US/docs/Web/API/WindowTimers/setTimeout) that is guaranteed to not run in the background. The *callback* is passed the elapsed time. + +# d3.interval(callback[, delay[, time]]) [<>](https://github.com/d3/d3-timer/blob/master/src/interval.js "Source") + +Like [timer](#timer), except the *callback* is invoked only every *delay* milliseconds; if *delay* is not specified, this is equivalent to [timer](#timer). A suitable replacement for [setInterval](https://developer.mozilla.org/en-US/docs/Web/API/WindowTimers/setInterval) that is guaranteed to not run in the background. The *callback* is passed the elapsed time. diff --git a/frontend/node_modules/d3-timer/dist/d3-timer.js b/frontend/node_modules/d3-timer/dist/d3-timer.js new file mode 100644 index 0000000..023aa5c --- /dev/null +++ b/frontend/node_modules/d3-timer/dist/d3-timer.js @@ -0,0 +1,153 @@ +// https://d3js.org/d3-timer/ v3.0.1 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +}(this, (function (exports) { 'use strict'; + +var frame = 0, // is an animation frame pending? + timeout$1 = 0, // is a timeout pending? + interval$1 = 0, // are any timers active? + pokeDelay = 1000, // how frequently we check for clock skew + taskHead, + taskTail, + clockLast = 0, + clockNow = 0, + clockSkew = 0, + clock = typeof performance === "object" && performance.now ? performance : Date, + setFrame = typeof window === "object" && window.requestAnimationFrame ? window.requestAnimationFrame.bind(window) : function(f) { setTimeout(f, 17); }; + +function now() { + return clockNow || (setFrame(clearNow), clockNow = clock.now() + clockSkew); +} + +function clearNow() { + clockNow = 0; +} + +function Timer() { + this._call = + this._time = + this._next = null; +} + +Timer.prototype = timer.prototype = { + constructor: Timer, + restart: function(callback, delay, time) { + if (typeof callback !== "function") throw new TypeError("callback is not a function"); + time = (time == null ? now() : +time) + (delay == null ? 0 : +delay); + if (!this._next && taskTail !== this) { + if (taskTail) taskTail._next = this; + else taskHead = this; + taskTail = this; + } + this._call = callback; + this._time = time; + sleep(); + }, + stop: function() { + if (this._call) { + this._call = null; + this._time = Infinity; + sleep(); + } + } +}; + +function timer(callback, delay, time) { + var t = new Timer; + t.restart(callback, delay, time); + return t; +} + +function timerFlush() { + now(); // Get the current time, if not already set. + ++frame; // Pretend we’ve set an alarm, if we haven’t already. + var t = taskHead, e; + while (t) { + if ((e = clockNow - t._time) >= 0) t._call.call(undefined, e); + t = t._next; + } + --frame; +} + +function wake() { + clockNow = (clockLast = clock.now()) + clockSkew; + frame = timeout$1 = 0; + try { + timerFlush(); + } finally { + frame = 0; + nap(); + clockNow = 0; + } +} + +function poke() { + var now = clock.now(), delay = now - clockLast; + if (delay > pokeDelay) clockSkew -= delay, clockLast = now; +} + +function nap() { + var t0, t1 = taskHead, t2, time = Infinity; + while (t1) { + if (t1._call) { + if (time > t1._time) time = t1._time; + t0 = t1, t1 = t1._next; + } else { + t2 = t1._next, t1._next = null; + t1 = t0 ? t0._next = t2 : taskHead = t2; + } + } + taskTail = t0; + sleep(time); +} + +function sleep(time) { + if (frame) return; // Soonest alarm already set, or will be. + if (timeout$1) timeout$1 = clearTimeout(timeout$1); + var delay = time - clockNow; // Strictly less than if we recomputed clockNow. + if (delay > 24) { + if (time < Infinity) timeout$1 = setTimeout(wake, time - clock.now() - clockSkew); + if (interval$1) interval$1 = clearInterval(interval$1); + } else { + if (!interval$1) clockLast = clock.now(), interval$1 = setInterval(poke, pokeDelay); + frame = 1, setFrame(wake); + } +} + +function timeout(callback, delay, time) { + var t = new Timer; + delay = delay == null ? 0 : +delay; + t.restart(elapsed => { + t.stop(); + callback(elapsed + delay); + }, delay, time); + return t; +} + +function interval(callback, delay, time) { + var t = new Timer, total = delay; + if (delay == null) return t.restart(callback, delay, time), t; + t._restart = t.restart; + t.restart = function(callback, delay, time) { + delay = +delay, time = time == null ? now() : +time; + t._restart(function tick(elapsed) { + elapsed += total; + t._restart(tick, total += delay, time); + callback(elapsed); + }, delay, time); + }; + t.restart(callback, delay, time); + return t; +} + +exports.interval = interval; +exports.now = now; +exports.timeout = timeout; +exports.timer = timer; +exports.timerFlush = timerFlush; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-timer/dist/d3-timer.min.js b/frontend/node_modules/d3-timer/dist/d3-timer.min.js new file mode 100644 index 0000000..7fee967 --- /dev/null +++ b/frontend/node_modules/d3-timer/dist/d3-timer.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-timer/ v3.0.1 Copyright 2010-2021 Mike Bostock +!function(t,n){"object"==typeof exports&&"undefined"!=typeof module?n(exports):"function"==typeof define&&define.amd?define(["exports"],n):n((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{})}(this,(function(t){"use strict";var n,e,o=0,i=0,r=0,l=0,u=0,a=0,s="object"==typeof performance&&performance.now?performance:Date,c="object"==typeof window&&window.requestAnimationFrame?window.requestAnimationFrame.bind(window):function(t){setTimeout(t,17)};function f(){return u||(c(_),u=s.now()+a)}function _(){u=0}function m(){this._call=this._time=this._next=null}function p(t,n,e){var o=new m;return o.restart(t,n,e),o}function w(){f(),++o;for(var t,e=n;e;)(t=u-e._time)>=0&&e._call.call(void 0,t),e=e._next;--o}function d(){u=(l=s.now())+a,o=i=0;try{w()}finally{o=0,function(){var t,o,i=n,r=1/0;for(;i;)i._call?(r>i._time&&(r=i._time),t=i,i=i._next):(o=i._next,i._next=null,i=t?t._next=o:n=o);e=t,y(r)}(),u=0}}function h(){var t=s.now(),n=t-l;n>1e3&&(a-=n,l=t)}function y(t){o||(i&&(i=clearTimeout(i)),t-u>24?(t<1/0&&(i=setTimeout(d,t-s.now()-a)),r&&(r=clearInterval(r))):(r||(l=s.now(),r=setInterval(h,1e3)),o=1,c(d)))}m.prototype=p.prototype={constructor:m,restart:function(t,o,i){if("function"!=typeof t)throw new TypeError("callback is not a function");i=(null==i?f():+i)+(null==o?0:+o),this._next||e===this||(e?e._next=this:n=this,e=this),this._call=t,this._time=i,y()},stop:function(){this._call&&(this._call=null,this._time=1/0,y())}},t.interval=function(t,n,e){var o=new m,i=n;return null==n?(o.restart(t,n,e),o):(o._restart=o.restart,o.restart=function(t,n,e){n=+n,e=null==e?f():+e,o._restart((function r(l){l+=i,o._restart(r,i+=n,e),t(l)}),n,e)},o.restart(t,n,e),o)},t.now=f,t.timeout=function(t,n,e){var o=new m;return n=null==n?0:+n,o.restart((e=>{o.stop(),t(e+n)}),n,e),o},t.timer=p,t.timerFlush=w,Object.defineProperty(t,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-timer/package.json b/frontend/node_modules/d3-timer/package.json new file mode 100644 index 0000000..fc52f55 --- /dev/null +++ b/frontend/node_modules/d3-timer/package.json @@ -0,0 +1,53 @@ +{ + "name": "d3-timer", + "version": "3.0.1", + "description": "An efficient queue capable of managing thousands of concurrent animations.", + "homepage": "https://d3js.org/d3-timer/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-timer.git" + }, + "keywords": [ + "d3", + "d3-module", + "timer", + "transition", + "animation", + "requestAnimationFrame", + "setTimeout", + "setInterval" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "http://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-timer.min.js", + "unpkg": "dist/d3-timer.min.js", + "exports": { + "umd": "./dist/d3-timer.min.js", + "default": "./src/index.js" + }, + "sideEffects": false, + "devDependencies": { + "eslint": "7", + "mocha": "8", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c", + "postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + } +} diff --git a/frontend/node_modules/d3-timer/src/index.js b/frontend/node_modules/d3-timer/src/index.js new file mode 100644 index 0000000..66fb8c9 --- /dev/null +++ b/frontend/node_modules/d3-timer/src/index.js @@ -0,0 +1,13 @@ +export { + now, + timer, + timerFlush +} from "./timer.js"; + +export { + default as timeout +} from "./timeout.js"; + +export { + default as interval +} from "./interval.js"; diff --git a/frontend/node_modules/d3-timer/src/interval.js b/frontend/node_modules/d3-timer/src/interval.js new file mode 100644 index 0000000..e38e1bd --- /dev/null +++ b/frontend/node_modules/d3-timer/src/interval.js @@ -0,0 +1,17 @@ +import {Timer, now} from "./timer.js"; + +export default function(callback, delay, time) { + var t = new Timer, total = delay; + if (delay == null) return t.restart(callback, delay, time), t; + t._restart = t.restart; + t.restart = function(callback, delay, time) { + delay = +delay, time = time == null ? now() : +time; + t._restart(function tick(elapsed) { + elapsed += total; + t._restart(tick, total += delay, time); + callback(elapsed); + }, delay, time); + } + t.restart(callback, delay, time); + return t; +} diff --git a/frontend/node_modules/d3-timer/src/timeout.js b/frontend/node_modules/d3-timer/src/timeout.js new file mode 100644 index 0000000..29b4dd2 --- /dev/null +++ b/frontend/node_modules/d3-timer/src/timeout.js @@ -0,0 +1,11 @@ +import {Timer} from "./timer.js"; + +export default function(callback, delay, time) { + var t = new Timer; + delay = delay == null ? 0 : +delay; + t.restart(elapsed => { + t.stop(); + callback(elapsed + delay); + }, delay, time); + return t; +} diff --git a/frontend/node_modules/d3-timer/src/timer.js b/frontend/node_modules/d3-timer/src/timer.js new file mode 100644 index 0000000..79cdf10 --- /dev/null +++ b/frontend/node_modules/d3-timer/src/timer.js @@ -0,0 +1,110 @@ +var frame = 0, // is an animation frame pending? + timeout = 0, // is a timeout pending? + interval = 0, // are any timers active? + pokeDelay = 1000, // how frequently we check for clock skew + taskHead, + taskTail, + clockLast = 0, + clockNow = 0, + clockSkew = 0, + clock = typeof performance === "object" && performance.now ? performance : Date, + setFrame = typeof window === "object" && window.requestAnimationFrame ? window.requestAnimationFrame.bind(window) : function(f) { setTimeout(f, 17); }; + +export function now() { + return clockNow || (setFrame(clearNow), clockNow = clock.now() + clockSkew); +} + +function clearNow() { + clockNow = 0; +} + +export function Timer() { + this._call = + this._time = + this._next = null; +} + +Timer.prototype = timer.prototype = { + constructor: Timer, + restart: function(callback, delay, time) { + if (typeof callback !== "function") throw new TypeError("callback is not a function"); + time = (time == null ? now() : +time) + (delay == null ? 0 : +delay); + if (!this._next && taskTail !== this) { + if (taskTail) taskTail._next = this; + else taskHead = this; + taskTail = this; + } + this._call = callback; + this._time = time; + sleep(); + }, + stop: function() { + if (this._call) { + this._call = null; + this._time = Infinity; + sleep(); + } + } +}; + +export function timer(callback, delay, time) { + var t = new Timer; + t.restart(callback, delay, time); + return t; +} + +export function timerFlush() { + now(); // Get the current time, if not already set. + ++frame; // Pretend we’ve set an alarm, if we haven’t already. + var t = taskHead, e; + while (t) { + if ((e = clockNow - t._time) >= 0) t._call.call(undefined, e); + t = t._next; + } + --frame; +} + +function wake() { + clockNow = (clockLast = clock.now()) + clockSkew; + frame = timeout = 0; + try { + timerFlush(); + } finally { + frame = 0; + nap(); + clockNow = 0; + } +} + +function poke() { + var now = clock.now(), delay = now - clockLast; + if (delay > pokeDelay) clockSkew -= delay, clockLast = now; +} + +function nap() { + var t0, t1 = taskHead, t2, time = Infinity; + while (t1) { + if (t1._call) { + if (time > t1._time) time = t1._time; + t0 = t1, t1 = t1._next; + } else { + t2 = t1._next, t1._next = null; + t1 = t0 ? t0._next = t2 : taskHead = t2; + } + } + taskTail = t0; + sleep(time); +} + +function sleep(time) { + if (frame) return; // Soonest alarm already set, or will be. + if (timeout) timeout = clearTimeout(timeout); + var delay = time - clockNow; // Strictly less than if we recomputed clockNow. + if (delay > 24) { + if (time < Infinity) timeout = setTimeout(wake, time - clock.now() - clockSkew); + if (interval) interval = clearInterval(interval); + } else { + if (!interval) clockLast = clock.now(), interval = setInterval(poke, pokeDelay); + frame = 1, setFrame(wake); + } +} diff --git a/frontend/node_modules/d3-transition/LICENSE b/frontend/node_modules/d3-transition/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-transition/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-transition/README.md b/frontend/node_modules/d3-transition/README.md new file mode 100644 index 0000000..3802a99 --- /dev/null +++ b/frontend/node_modules/d3-transition/README.md @@ -0,0 +1,490 @@ +# d3-transition + +A transition is a [selection](https://github.com/d3/d3-selection)-like interface for animating changes to the DOM. Instead of applying changes instantaneously, transitions smoothly interpolate the DOM from its current state to the desired target state over a given duration. + +To apply a transition, select elements, call [*selection*.transition](#selection_transition), and then make the desired changes. For example: + +```js +d3.select("body") + .transition() + .style("background-color", "red"); +``` + +Transitions support most selection methods (such as [*transition*.attr](#transition_attr) and [*transition*.style](#transition_style) in place of [*selection*.attr](https://github.com/d3/d3-selection#selection_attr) and [*selection*.style](https://github.com/d3/d3-selection#selection_style)), but not all methods are supported; for example, you must [append](https://github.com/d3/d3-selection#selection_append) elements or [bind data](https://github.com/d3/d3-selection#joining-data) before a transition starts. A [*transition*.remove](#transition_remove) operator is provided for convenient removal of elements when the transition ends. + +To compute intermediate state, transitions leverage a variety of [built-in interpolators](https://github.com/d3/d3-interpolate). [Colors](https://github.com/d3/d3-interpolate#interpolateRgb), [numbers](https://github.com/d3/d3-interpolate#interpolateNumber), and [transforms](https://github.com/d3/d3-interpolate#interpolateTransform) are automatically detected. [Strings](https://github.com/d3/d3-interpolate#interpolateString) with embedded numbers are also detected, as is common with many styles (such as padding or font sizes) and paths. To specify a custom interpolator, use [*transition*.attrTween](#transition_attrTween), [*transition*.styleTween](#transition_styleTween) or [*transition*.tween](#transition_tween). + +## Installing + +If you use npm, `npm install d3-transition`. You can also download the [latest release on GitHub](https://github.com/d3/d3-transition/releases/latest). For vanilla HTML in modern browsers, import d3-transition from Skypack: + +```html + +``` + +For legacy environments, you can load d3-transition’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + + + + + + + +``` + +[Try d3-transition in your browser.](https://observablehq.com/collection/@d3/d3-transition) + +## API Reference + +* [Selecting Elements](#selecting-elements) +* [Modifying Elements](#modifying-elements) +* [Timing](#timing) +* [Control Flow](#control-flow) +* [The Life of a Transition](#the-life-of-a-transition) + +### Selecting Elements + +Transitions are derived from [selections](https://github.com/d3/d3-selection) via [*selection*.transition](#selection_transition). You can also create a transition on the document root element using [d3.transition](#transition). + +# selection.transition([name]) · [Source](https://github.com/d3/d3-transition/blob/master/src/selection/transition.js) + +Returns a new transition on the given *selection* with the specified *name*. If a *name* is not specified, null is used. The new transition is only exclusive with other transitions of the same name. + +If the *name* is a [transition](#transition) instance, the returned transition has the same id and name as the specified transition. If a transition with the same id already exists on a selected element, the existing transition is returned for that element. Otherwise, the timing of the returned transition is inherited from the existing transition of the same id on the nearest ancestor of each selected element. Thus, this method can be used to synchronize a transition across multiple selections, or to re-select a transition for specific elements and modify its configuration. For example: + +```js +var t = d3.transition() + .duration(750) + .ease(d3.easeLinear); + +d3.selectAll(".apple").transition(t) + .style("fill", "red"); + +d3.selectAll(".orange").transition(t) + .style("fill", "orange"); +``` + +If the specified *transition* is not found on a selected node or its ancestors (such as if the transition [already ended](#the-life-of-a-transition)), the default timing parameters are used; however, in a future release, this will likely be changed to throw an error. See [#59](https://github.com/d3/d3-transition/issues/59). + +# selection.interrupt([name]) · [Source](https://github.com/d3/d3-transition/blob/master/src/selection/interrupt.js) + +Interrupts the active transition of the specified *name* on the selected elements, and cancels any pending transitions with the specified *name*, if any. If a name is not specified, null is used. + +Interrupting a transition on an element has no effect on any transitions on any descendant elements. For example, an [axis transition](https://github.com/d3/d3-axis) consists of multiple independent, synchronized transitions on the descendants of the axis [G element](https://www.w3.org/TR/SVG/struct.html#Groups) (the tick lines, the tick labels, the domain path, *etc.*). To interrupt the axis transition, you must therefore interrupt the descendants: + +```js +selection.selectAll("*").interrupt(); +``` + +The [universal selector](https://developer.mozilla.org/en-US/docs/Web/CSS/Universal_selectors), `*`, selects all descendant elements. If you also want to interrupt the G element itself: + +```js +selection.interrupt().selectAll("*").interrupt(); +``` + +# d3.interrupt(node[, name]) · [Source](https://github.com/d3/d3-transition/blob/master/src/interrupt.js) + +Interrupts the active transition of the specified *name* on the specified *node*, and cancels any pending transitions with the specified *name*, if any. If a name is not specified, null is used. See also [*selection*.interrupt](#selection_interrupt). + +# d3.transition([name]) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/index.js#L29) + +Returns a new transition on the root element, `document.documentElement`, with the specified *name*. If a *name* is not specified, null is used. The new transition is only exclusive with other transitions of the same name. The *name* may also be a [transition](#transition) instance; see [*selection*.transition](#selection_transition). This method is equivalent to: + +```js +d3.selection() + .transition(name) +``` + +This function can also be used to test for transitions (`instanceof d3.transition`) or to extend the transition prototype. + +# transition.select(selector) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/select.js) + +For each selected element, selects the first descendant element that matches the specified *selector* string, if any, and returns a transition on the resulting selection. The *selector* may be specified either as a selector string or a function. If a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. The new transition has the same id, name and timing as this transition; however, if a transition with the same id already exists on a selected element, the existing transition is returned for that element. + +This method is equivalent to deriving the selection for this transition via [*transition*.selection](#transition_selection), creating a subselection via [*selection*.select](https://github.com/d3/d3-selection#selection_select), and then creating a new transition via [*selection*.transition](#selection_transition): + +```js +transition + .selection() + .select(selector) + .transition(transition) +``` + +# transition.selectAll(selector) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/selectAll.js) + +For each selected element, selects all descendant elements that match the specified *selector* string, if any, and returns a transition on the resulting selection. The *selector* may be specified either as a selector string or a function. If a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. The new transition has the same id, name and timing as this transition; however, if a transition with the same id already exists on a selected element, the existing transition is returned for that element. + +This method is equivalent to deriving the selection for this transition via [*transition*.selection](#transition_selection), creating a subselection via [*selection*.selectAll](https://github.com/d3/d3-selection#selection_selectAll), and then creating a new transition via [*selection*.transition](#selection_transition): + +```js +transition + .selection() + .selectAll(selector) + .transition(transition) +``` + +# transition.selectChild([selector]) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/select.js) + +For each selected element, selects the first child element that matches the specified *selector* string, if any, and returns a transition on the resulting selection. The *selector* may be specified either as a selector string or a function. If a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. The new transition has the same id, name and timing as this transition; however, if a transition with the same id already exists on a selected element, the existing transition is returned for that element. + +This method is equivalent to deriving the selection for this transition via [*transition*.selection](#transition_selection), creating a subselection via [*selection*.selectChild](https://github.com/d3/d3-selection#selection_selectChild), and then creating a new transition via [*selection*.transition](#selection_transition): + +```js +transition + .selection() + .selectChild(selector) + .transition(transition) +``` + +# transition.selectChildren([selector]) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/selectAll.js) + +For each selected element, selects all children that match the specified *selector* string, if any, and returns a transition on the resulting selection. The *selector* may be specified either as a selector string or a function. If a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. The new transition has the same id, name and timing as this transition; however, if a transition with the same id already exists on a selected element, the existing transition is returned for that element. + +This method is equivalent to deriving the selection for this transition via [*transition*.selection](#transition_selection), creating a subselection via [*selection*.selectChildren](https://github.com/d3/d3-selection#selection_selectChildren), and then creating a new transition via [*selection*.transition](#selection_transition): + +```js +transition + .selection() + .selectChildren(selector) + .transition(transition) +``` + +# transition.filter(filter) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/filter.js) + +For each selected element, selects only the elements that match the specified *filter*, and returns a transition on the resulting selection. The *filter* may be specified either as a selector string or a function. If a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. The new transition has the same id, name and timing as this transition; however, if a transition with the same id already exists on a selected element, the existing transition is returned for that element. + +This method is equivalent to deriving the selection for this transition via [*transition*.selection](#transition_selection), creating a subselection via [*selection*.filter](https://github.com/d3/d3-selection#selection_filter), and then creating a new transition via [*selection*.transition](#selection_transition): + +```js +transition + .selection() + .filter(filter) + .transition(transition) +``` + +# transition.merge(other) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/merge.js) + +Returns a new transition merging this transition with the specified *other* transition, which must have the same id as this transition. The returned transition has the same number of groups, the same parents, the same name and the same id as this transition. Any missing (null) elements in this transition are filled with the corresponding element, if present (not null), from the *other* transition. + +This method is equivalent to deriving the selection for this transition via [*transition*.selection](#transition_selection), merging with the selection likewise derived from the *other* transition via [*selection*.merge](https://github.com/d3/d3-selection#selection_merge), and then creating a new transition via [*selection*.transition](#selection_transition): + +```js +transition + .selection() + .merge(other.selection()) + .transition(transition) +``` + +# transition.transition() · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/transition.js) + +Returns a new transition on the same selected elements as this transition, scheduled to start when this transition ends. The new transition inherits a reference time equal to this transition’s time plus its [delay](#transition_delay) and [duration](#transition_duration). The new transition also inherits this transition’s name, duration, and [easing](#transition_ease). This method can be used to schedule a sequence of chained transitions. For example: + +```js +d3.selectAll(".apple") + .transition() // First fade to green. + .style("fill", "green") + .transition() // Then red. + .style("fill", "red") + .transition() // Wait one second. Then brown, and remove. + .delay(1000) + .style("fill", "brown") + .remove(); +``` + +The delay for each transition is relative to its previous transition. Thus, in the above example, apples will stay red for one second before the last transition to brown starts. + +# transition.selection() · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/selection.js) + +Returns the [selection](https://github.com/d3/d3-selection#selection) corresponding to this transition. + +# d3.active(node[, name]) · [Source](https://github.com/d3/d3-transition/blob/master/src/active.js) + +Returns the active transition on the specified *node* with the specified *name*, if any. If no *name* is specified, null is used. Returns null if there is no such active transition on the specified node. This method is useful for creating chained transitions. For example, to initiate disco mode: + +```js +d3.selectAll("circle").transition() + .delay(function(d, i) { return i * 50; }) + .on("start", function repeat() { + d3.active(this) + .style("fill", "red") + .transition() + .style("fill", "green") + .transition() + .style("fill", "blue") + .transition() + .on("start", repeat); + }); +``` + +See [chained transitions](https://bl.ocks.org/mbostock/70d5541b547cc222aa02) for an example. + +### Modifying Elements + +After selecting elements and creating a transition with [*selection*.transition](#selection_transition), use the transition’s transformation methods to affect document content. + +# transition.attr(name, value) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/attr.js) + +For each selected element, assigns the [attribute tween](#transition_attrTween) for the attribute with the specified *name* to the specified target *value*. The starting value of the tween is the attribute’s value when the transition starts. The target *value* may be specified either as a constant or a function. If a function, it is immediately evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. + +If the target value is null, the attribute is removed when the transition starts. Otherwise, an interpolator is chosen based on the type of the target value, using the following algorithm: + +1. If *value* is a number, use [interpolateNumber](https://github.com/d3/d3-interpolate#interpolateNumber). +2. If *value* is a [color](https://github.com/d3/d3-color#color) or a string coercible to a color, use [interpolateRgb](https://github.com/d3/d3-interpolate#interpolateRgb). +3. Use [interpolateString](https://github.com/d3/d3-interpolate#interpolateString). + +To apply a different interpolator, use [*transition*.attrTween](#transition_attrTween). + +# transition.attrTween(name[, factory]) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/attrTween.js) + +If *factory* is specified and not null, assigns the attribute [tween](#transition_tween) for the attribute with the specified *name* to the specified interpolator *factory*. An interpolator factory is a function that returns an [interpolator](https://github.com/d3/d3-interpolate); when the transition starts, the *factory* is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. The returned interpolator will then be invoked for each frame of the transition, in order, being passed the [eased](#transition_ease) time *t*, typically in the range [0, 1]. Lastly, the return value of the interpolator will be used to set the attribute value. The interpolator must return a string. (To remove an attribute at the start of a transition, use [*transition*.attr](#transition_attr); to remove an attribute at the end of a transition, use [*transition*.on](#transition_on) to listen for the *end* event.) + +If the specified *factory* is null, removes the previously-assigned attribute tween of the specified *name*, if any. If *factory* is not specified, returns the current interpolator factory for attribute with the specified *name*, or undefined if no such tween exists. + +For example, to interpolate the fill attribute from red to blue: + +```js +transition.attrTween("fill", function() { + return d3.interpolateRgb("red", "blue"); +}); +``` + +Or to interpolate from the current fill to blue, like [*transition*.attr](#transition_attr): + +```js +transition.attrTween("fill", function() { + return d3.interpolateRgb(this.getAttribute("fill"), "blue"); +}); +``` + +Or to apply a custom rainbow interpolator: + +```js +transition.attrTween("fill", function() { + return function(t) { + return "hsl(" + t * 360 + ",100%,50%)"; + }; +}); +``` + +This method is useful to specify a custom interpolator, such as one that understands [SVG paths](https://bl.ocks.org/mbostock/3916621). A useful technique is *data interpolation*, where [d3.interpolateObject](https://github.com/d3/d3-interpolate#interpolateObject) is used to interpolate two data values, and the resulting value is then used (say, with a [shape](https://github.com/d3/d3-shape)) to compute the new attribute value. + +# transition.style(name, value[, priority]) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/style.js) + +For each selected element, assigns the [style tween](#transition_styleTween) for the style with the specified *name* to the specified target *value* with the specified *priority*. The starting value of the tween is the style’s inline value if present, and otherwise its computed value, when the transition starts. The target *value* may be specified either as a constant or a function. If a function, it is immediately evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. + +If the target value is null, the style is removed when the transition starts. Otherwise, an interpolator is chosen based on the type of the target value, using the following algorithm: + +1. If *value* is a number, use [interpolateNumber](https://github.com/d3/d3-interpolate#interpolateNumber). +2. If *value* is a [color](https://github.com/d3/d3-color#color) or a string coercible to a color, use [interpolateRgb](https://github.com/d3/d3-interpolate#interpolateRgb). +3. Use [interpolateString](https://github.com/d3/d3-interpolate#interpolateString). + +To apply a different interpolator, use [*transition*.styleTween](#transition_styleTween). + +# transition.styleTween(name[, factory[, priority]]) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/styleTween.js) + +If *factory* is specified and not null, assigns the style [tween](#transition_tween) for the style with the specified *name* to the specified interpolator *factory*. An interpolator factory is a function that returns an [interpolator](https://github.com/d3/d3-interpolate); when the transition starts, the *factory* is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. The returned interpolator will then be invoked for each frame of the transition, in order, being passed the [eased](#transition_ease) time *t*, typically in the range [0, 1]. Lastly, the return value of the interpolator will be used to set the style value with the specified *priority*. The interpolator must return a string. (To remove an style at the start of a transition, use [*transition*.style](#transition_style); to remove an style at the end of a transition, use [*transition*.on](#transition_on) to listen for the *end* event.) + +If the specified *factory* is null, removes the previously-assigned style tween of the specified *name*, if any. If *factory* is not specified, returns the current interpolator factory for style with the specified *name*, or undefined if no such tween exists. + +For example, to interpolate the fill style from red to blue: + +```js +transition.styleTween("fill", function() { + return d3.interpolateRgb("red", "blue"); +}); +``` + +Or to interpolate from the current fill to blue, like [*transition*.style](#transition_style): + +```js +transition.styleTween("fill", function() { + return d3.interpolateRgb(this.style.fill, "blue"); +}); +``` + +Or to apply a custom rainbow interpolator: + +```js +transition.styleTween("fill", function() { + return function(t) { + return "hsl(" + t * 360 + ",100%,50%)"; + }; +}); +``` + +This method is useful to specify a custom interpolator, such as with *data interpolation*, where [d3.interpolateObject](https://github.com/d3/d3-interpolate#interpolateObject) is used to interpolate two data values, and the resulting value is then used to compute the new style value. + +# transition.text(value) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/text.js) + +For each selected element, sets the [text content](http://www.w3.org/TR/DOM-Level-3-Core/core.html#Node3-textContent) to the specified target *value* when the transition starts. The *value* may be specified either as a constant or a function. If a function, it is immediately evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. The function’s return value is then used to set each element’s text content. A null value will clear the content. + +To interpolate text rather than to set it on start, use [*transition*.textTween](#transition_textTween) or append a replacement element and cross-fade opacity. Text is not interpolated by default because it is usually undesirable. + +# transition.textTween(factory) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/textTween.js), [Examples](https://observablehq.com/@d3/transition-texttween) + +If *factory* is specified and not null, assigns the text [tween](#transition_tween) to the specified interpolator *factory*. An interpolator factory is a function that returns an [interpolator](https://github.com/d3/d3-interpolate); when the transition starts, the *factory* is evaluated for each selected element, in order, being passed the current datum `d` and index `i`, with the `this` context as the current DOM element. The returned interpolator will then be invoked for each frame of the transition, in order, being passed the [eased](#transition_ease) time *t*, typically in the range [0, 1]. Lastly, the return value of the interpolator will be used to set the text. The interpolator must return a string. + +For example, to interpolate the text with integers from 0 to 100: + +```js +transition.textTween(function() { + return d3.interpolateRound(0, 100); +}); +``` + +If the specified *factory* is null, removes the previously-assigned text tween, if any. If *factory* is not specified, returns the current interpolator factory for text, or undefined if no such tween exists. + +# transition.remove() · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/remove.js) + +For each selected element, [removes](https://github.com/d3/d3-selection#selection_remove) the element when the transition ends, as long as the element has no other active or pending transitions. If the element has other active or pending transitions, does nothing. + +# transition.tween(name[, value]) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/tween.js) + +For each selected element, assigns the tween with the specified *name* with the specified *value* function. The *value* must be specified as a function that returns a function. When the transition starts, the *value* function is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. The returned function is then invoked for each frame of the transition, in order, being passed the [eased](#transition_ease) time *t*, typically in the range [0, 1]. If the specified *value* is null, removes the previously-assigned tween of the specified *name*, if any. + +For example, to interpolate the fill attribute to blue, like [*transition*.attr](#transition_attr): + +```js +transition.tween("attr.fill", function() { + var i = d3.interpolateRgb(this.getAttribute("fill"), "blue"); + return function(t) { + this.setAttribute("fill", i(t)); + }; +}); +``` + +This method is useful to specify a custom interpolator, or to perform side-effects, say to animate the [scroll offset](https://bl.ocks.org/mbostock/1649463). + +### Timing + +The [easing](#transition_ease), [delay](#transition_delay) and [duration](#transition_duration) of a transition is configurable. For example, a per-element delay can be used to [stagger the reordering](https://observablehq.com/@d3/sortable-bar-chart) of elements, improving perception. See [Animated Transitions in Statistical Data Graphics](http://vis.berkeley.edu/papers/animated_transitions/) for recommendations. + +# transition.delay([value]) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/delay.js) + +For each selected element, sets the transition delay to the specified *value* in milliseconds. The *value* may be specified either as a constant or a function. If a function, it is immediately evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. The function’s return value is then used to set each element’s transition delay. If a delay is not specified, it defaults to zero. + +If a *value* is not specified, returns the current value of the delay for the first (non-null) element in the transition. This is generally useful only if you know that the transition contains exactly one element. + +Setting the delay to a multiple of the index `i` is a convenient way to stagger transitions across a set of elements. For example: + +```js +transition.delay(function(d, i) { return i * 10; }); +``` + +Of course, you can also compute the delay as a function of the data, or [sort the selection](https://github.com/d3/d3-selection#selection_sort) before computed an index-based delay. + +# transition.duration([value]) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/duration.js) + +For each selected element, sets the transition duration to the specified *value* in milliseconds. The *value* may be specified either as a constant or a function. If a function, it is immediately evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. The function’s return value is then used to set each element’s transition duration. If a duration is not specified, it defaults to 250ms. + +If a *value* is not specified, returns the current value of the duration for the first (non-null) element in the transition. This is generally useful only if you know that the transition contains exactly one element. + +# transition.ease([value]) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/ease.js) + +Specifies the transition [easing function](https://github.com/d3/d3-ease) for all selected elements. The *value* must be specified as a function. The easing function is invoked for each frame of the animation, being passed the normalized time *t* in the range [0, 1]; it must then return the eased time *tʹ* which is typically also in the range [0, 1]. A good easing function should return 0 if *t* = 0 and 1 if *t* = 1. If an easing function is not specified, it defaults to [d3.easeCubic](https://github.com/d3/d3-ease#easeCubic). + +If a *value* is not specified, returns the current easing function for the first (non-null) element in the transition. This is generally useful only if you know that the transition contains exactly one element. + +# transition.easeVarying(factory) [<>](https://github.com/d3/d3-transition/blob/master/src/transition/easeVarying.js "Source") + +Specifies a factory for the transition [easing function](https://github.com/d3/d3-ease). The *factory* must be a function. It is invoked for each node of the selection, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. It must return an easing function. + +### Control Flow + +For advanced usage, transitions provide methods for custom control flow. + +# transition.end() · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/end.js) + +Returns a promise that resolves when every selected element finishes transitioning. If any element’s transition is cancelled or interrupted, the promise rejects. + +# transition.on(typenames[, listener]) · [Source](https://github.com/d3/d3-transition/blob/master/src/transition/on.js) + +Adds or removes a *listener* to each selected element for the specified event *typenames*. The *typenames* is one of the following string event types: + +* `start` - when the transition starts. +* `end` - when the transition ends. +* `interrupt` - when the transition is interrupted. +* `cancel` - when the transition is cancelled. + +See [The Life of a Transition](#the-life-of-a-transition) for more. Note that these are *not* native DOM events as implemented by [*selection*.on](https://github.com/d3/d3-selection#selection_on) and [*selection*.dispatch](https://github.com/d3/d3-selection#selection_dispatch), but transition events! + +The type may be optionally followed by a period (`.`) and a name; the optional name allows multiple callbacks to be registered to receive events of the same type, such as `start.foo` and `start.bar`. To specify multiple typenames, separate typenames with spaces, such as `interrupt end` or `start.foo start.bar`. + +When a specified transition event is dispatched on a selected node, the specified *listener* will be invoked for the transitioning element, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. Listeners always see the latest datum for their element, but the index is a property of the selection and is fixed when the listener is assigned; to update the index, re-assign the listener. + +If an event listener was previously registered for the same *typename* on a selected element, the old listener is removed before the new listener is added. To remove a listener, pass null as the *listener*. To remove all listeners for a given name, pass null as the *listener* and `.foo` as the *typename*, where `foo` is the name; to remove all listeners with no name, specify `.` as the *typename*. + +If a *listener* is not specified, returns the currently-assigned listener for the specified event *typename* on the first (non-null) selected element, if any. If multiple typenames are specified, the first matching listener is returned. + +# transition.each(function) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/each.js) + +Invokes the specified *function* for each selected element, passing in the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element. This method can be used to invoke arbitrary code for each selected element, and is useful for creating a context to access parent and child data simultaneously. Equivalent to [*selection*.each](https://github.com/d3/d3-selection#selection_each). + +# transition.call(function[, arguments…]) · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/call.js) + +Invokes the specified *function* exactly once, passing in this transition along with any optional *arguments*. Returns this transition. This is equivalent to invoking the function by hand but facilitates method chaining. For example, to set several attributes in a reusable function: + +```js +function color(transition, fill, stroke) { + transition + .style("fill", fill) + .style("stroke", stroke); +} +``` + +Now say: + +```js +d3.selectAll("div").transition().call(color, "red", "blue"); +``` + +This is equivalent to: + +```js +color(d3.selectAll("div").transition(), "red", "blue"); +``` + +Equivalent to [*selection*.call](https://github.com/d3/d3-selection#selection_call). + +# transition.empty() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/empty.js) + +Returns true if this transition contains no (non-null) elements. Equivalent to [*selection*.empty](https://github.com/d3/d3-selection#selection_empty). + +# transition.nodes() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/nodes.js) + +Returns an array of all (non-null) elements in this transition. Equivalent to [*selection*.nodes](https://github.com/d3/d3-selection#selection_nodes). + +# transition.node() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/node.js) + +Returns the first (non-null) element in this transition. If the transition is empty, returns null. Equivalent to [*selection*.node](https://github.com/d3/d3-selection#selection_node). + +# transition.size() · [Source](https://github.com/d3/d3-selection/blob/master/src/selection/size.js) + +Returns the total number of elements in this transition. Equivalent to [*selection*.size](https://github.com/d3/d3-selection#selection_size). + +### The Life of a Transition + +Immediately after creating a transition, such as by [*selection*.transition](#selection_transition) or [*transition*.transition](#transition_transition), you may configure the transition using methods such as [*transition*.delay](#transition_delay), [*transition*.duration](#transition_duration), [*transition*.attr](#transition_attr) and [*transition*.style](#transition_style). Methods that specify target values (such as *transition*.attr) are evaluated synchronously; however, methods that require the starting value for interpolation, such as [*transition*.attrTween](#transition_attrTween) and [*transition*.styleTween](#transition_styleTween), must be deferred until the transition starts. + +Shortly after creation, either at the end of the current frame or during the next frame, the transition is scheduled. At this point, the delay and `start` event listeners may no longer be changed; attempting to do so throws an error with the message “too late: already scheduled” (or if the transition has ended, “transition not found”). + +When the transition subsequently starts, it interrupts the active transition of the same name on the same element, if any, dispatching an `interrupt` event to registered listeners. (Note that interrupts happen on start, not creation, and thus even a zero-delay transition will not immediately interrupt the active transition: the old transition is given a final frame. Use [*selection*.interrupt](#selection_interrupt) to interrupt immediately.) The starting transition also cancels any pending transitions of the same name on the same element that were created before the starting transition. The transition then dispatches a `start` event to registered listeners. This is the last moment at which the transition may be modified: the transition’s timing, tweens, and listeners may not be changed when it is running; attempting to do so throws an error with the message “too late: already running” (or if the transition has ended, “transition not found”). The transition initializes its tweens immediately after starting. + +During the frame the transition starts, but *after* all transitions starting this frame have been started, the transition invokes its tweens for the first time. Batching tween initialization, which typically involves reading from the DOM, improves performance by avoiding interleaved DOM reads and writes. + +For each frame that a transition is active, it invokes its tweens with an [eased](#transition_ease) *t*-value ranging from 0 to 1. Within each frame, the transition invokes its tweens in the order they were registered. + +When a transition ends, it invokes its tweens a final time with a (non-eased) *t*-value of 1. It then dispatches an `end` event to registered listeners. This is the last moment at which the transition may be inspected: after ending, the transition is deleted from the element, and its configuration is destroyed. (A transition’s configuration is also destroyed on interrupt or cancel.) Attempting to inspect a transition after it is destroyed throws an error with the message “transition not found”. diff --git a/frontend/node_modules/d3-transition/dist/d3-transition.js b/frontend/node_modules/d3-transition/dist/d3-transition.js new file mode 100644 index 0000000..81849c2 --- /dev/null +++ b/frontend/node_modules/d3-transition/dist/d3-transition.js @@ -0,0 +1,900 @@ +// https://d3js.org/d3-transition/ v3.0.1 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-selection'), require('d3-dispatch'), require('d3-timer'), require('d3-interpolate'), require('d3-color'), require('d3-ease')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-selection', 'd3-dispatch', 'd3-timer', 'd3-interpolate', 'd3-color', 'd3-ease'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3, global.d3, global.d3, global.d3, global.d3, global.d3)); +}(this, (function (exports, d3Selection, d3Dispatch, d3Timer, d3Interpolate, d3Color, d3Ease) { 'use strict'; + +var emptyOn = d3Dispatch.dispatch("start", "end", "cancel", "interrupt"); +var emptyTween = []; + +var CREATED = 0; +var SCHEDULED = 1; +var STARTING = 2; +var STARTED = 3; +var RUNNING = 4; +var ENDING = 5; +var ENDED = 6; + +function schedule(node, name, id, index, group, timing) { + var schedules = node.__transition; + if (!schedules) node.__transition = {}; + else if (id in schedules) return; + create(node, id, { + name: name, + index: index, // For context during callback. + group: group, // For context during callback. + on: emptyOn, + tween: emptyTween, + time: timing.time, + delay: timing.delay, + duration: timing.duration, + ease: timing.ease, + timer: null, + state: CREATED + }); +} + +function init(node, id) { + var schedule = get(node, id); + if (schedule.state > CREATED) throw new Error("too late; already scheduled"); + return schedule; +} + +function set(node, id) { + var schedule = get(node, id); + if (schedule.state > STARTED) throw new Error("too late; already running"); + return schedule; +} + +function get(node, id) { + var schedule = node.__transition; + if (!schedule || !(schedule = schedule[id])) throw new Error("transition not found"); + return schedule; +} + +function create(node, id, self) { + var schedules = node.__transition, + tween; + + // Initialize the self timer when the transition is created. + // Note the actual delay is not known until the first callback! + schedules[id] = self; + self.timer = d3Timer.timer(schedule, 0, self.time); + + function schedule(elapsed) { + self.state = SCHEDULED; + self.timer.restart(start, self.delay, self.time); + + // If the elapsed delay is less than our first sleep, start immediately. + if (self.delay <= elapsed) start(elapsed - self.delay); + } + + function start(elapsed) { + var i, j, n, o; + + // If the state is not SCHEDULED, then we previously errored on start. + if (self.state !== SCHEDULED) return stop(); + + for (i in schedules) { + o = schedules[i]; + if (o.name !== self.name) continue; + + // While this element already has a starting transition during this frame, + // defer starting an interrupting transition until that transition has a + // chance to tick (and possibly end); see d3/d3-transition#54! + if (o.state === STARTED) return d3Timer.timeout(start); + + // Interrupt the active transition, if any. + if (o.state === RUNNING) { + o.state = ENDED; + o.timer.stop(); + o.on.call("interrupt", node, node.__data__, o.index, o.group); + delete schedules[i]; + } + + // Cancel any pre-empted transitions. + else if (+i < id) { + o.state = ENDED; + o.timer.stop(); + o.on.call("cancel", node, node.__data__, o.index, o.group); + delete schedules[i]; + } + } + + // Defer the first tick to end of the current frame; see d3/d3#1576. + // Note the transition may be canceled after start and before the first tick! + // Note this must be scheduled before the start event; see d3/d3-transition#16! + // Assuming this is successful, subsequent callbacks go straight to tick. + d3Timer.timeout(function() { + if (self.state === STARTED) { + self.state = RUNNING; + self.timer.restart(tick, self.delay, self.time); + tick(elapsed); + } + }); + + // Dispatch the start event. + // Note this must be done before the tween are initialized. + self.state = STARTING; + self.on.call("start", node, node.__data__, self.index, self.group); + if (self.state !== STARTING) return; // interrupted + self.state = STARTED; + + // Initialize the tween, deleting null tween. + tween = new Array(n = self.tween.length); + for (i = 0, j = -1; i < n; ++i) { + if (o = self.tween[i].value.call(node, node.__data__, self.index, self.group)) { + tween[++j] = o; + } + } + tween.length = j + 1; + } + + function tick(elapsed) { + var t = elapsed < self.duration ? self.ease.call(null, elapsed / self.duration) : (self.timer.restart(stop), self.state = ENDING, 1), + i = -1, + n = tween.length; + + while (++i < n) { + tween[i].call(node, t); + } + + // Dispatch the end event. + if (self.state === ENDING) { + self.on.call("end", node, node.__data__, self.index, self.group); + stop(); + } + } + + function stop() { + self.state = ENDED; + self.timer.stop(); + delete schedules[id]; + for (var i in schedules) return; // eslint-disable-line no-unused-vars + delete node.__transition; + } +} + +function interrupt(node, name) { + var schedules = node.__transition, + schedule, + active, + empty = true, + i; + + if (!schedules) return; + + name = name == null ? null : name + ""; + + for (i in schedules) { + if ((schedule = schedules[i]).name !== name) { empty = false; continue; } + active = schedule.state > STARTING && schedule.state < ENDING; + schedule.state = ENDED; + schedule.timer.stop(); + schedule.on.call(active ? "interrupt" : "cancel", node, node.__data__, schedule.index, schedule.group); + delete schedules[i]; + } + + if (empty) delete node.__transition; +} + +function selection_interrupt(name) { + return this.each(function() { + interrupt(this, name); + }); +} + +function tweenRemove(id, name) { + var tween0, tween1; + return function() { + var schedule = set(this, id), + tween = schedule.tween; + + // If this node shared tween with the previous node, + // just assign the updated shared tween and we’re done! + // Otherwise, copy-on-write. + if (tween !== tween0) { + tween1 = tween0 = tween; + for (var i = 0, n = tween1.length; i < n; ++i) { + if (tween1[i].name === name) { + tween1 = tween1.slice(); + tween1.splice(i, 1); + break; + } + } + } + + schedule.tween = tween1; + }; +} + +function tweenFunction(id, name, value) { + var tween0, tween1; + if (typeof value !== "function") throw new Error; + return function() { + var schedule = set(this, id), + tween = schedule.tween; + + // If this node shared tween with the previous node, + // just assign the updated shared tween and we’re done! + // Otherwise, copy-on-write. + if (tween !== tween0) { + tween1 = (tween0 = tween).slice(); + for (var t = {name: name, value: value}, i = 0, n = tween1.length; i < n; ++i) { + if (tween1[i].name === name) { + tween1[i] = t; + break; + } + } + if (i === n) tween1.push(t); + } + + schedule.tween = tween1; + }; +} + +function transition_tween(name, value) { + var id = this._id; + + name += ""; + + if (arguments.length < 2) { + var tween = get(this.node(), id).tween; + for (var i = 0, n = tween.length, t; i < n; ++i) { + if ((t = tween[i]).name === name) { + return t.value; + } + } + return null; + } + + return this.each((value == null ? tweenRemove : tweenFunction)(id, name, value)); +} + +function tweenValue(transition, name, value) { + var id = transition._id; + + transition.each(function() { + var schedule = set(this, id); + (schedule.value || (schedule.value = {}))[name] = value.apply(this, arguments); + }); + + return function(node) { + return get(node, id).value[name]; + }; +} + +function interpolate(a, b) { + var c; + return (typeof b === "number" ? d3Interpolate.interpolateNumber + : b instanceof d3Color.color ? d3Interpolate.interpolateRgb + : (c = d3Color.color(b)) ? (b = c, d3Interpolate.interpolateRgb) + : d3Interpolate.interpolateString)(a, b); +} + +function attrRemove(name) { + return function() { + this.removeAttribute(name); + }; +} + +function attrRemoveNS(fullname) { + return function() { + this.removeAttributeNS(fullname.space, fullname.local); + }; +} + +function attrConstant(name, interpolate, value1) { + var string00, + string1 = value1 + "", + interpolate0; + return function() { + var string0 = this.getAttribute(name); + return string0 === string1 ? null + : string0 === string00 ? interpolate0 + : interpolate0 = interpolate(string00 = string0, value1); + }; +} + +function attrConstantNS(fullname, interpolate, value1) { + var string00, + string1 = value1 + "", + interpolate0; + return function() { + var string0 = this.getAttributeNS(fullname.space, fullname.local); + return string0 === string1 ? null + : string0 === string00 ? interpolate0 + : interpolate0 = interpolate(string00 = string0, value1); + }; +} + +function attrFunction(name, interpolate, value) { + var string00, + string10, + interpolate0; + return function() { + var string0, value1 = value(this), string1; + if (value1 == null) return void this.removeAttribute(name); + string0 = this.getAttribute(name); + string1 = value1 + ""; + return string0 === string1 ? null + : string0 === string00 && string1 === string10 ? interpolate0 + : (string10 = string1, interpolate0 = interpolate(string00 = string0, value1)); + }; +} + +function attrFunctionNS(fullname, interpolate, value) { + var string00, + string10, + interpolate0; + return function() { + var string0, value1 = value(this), string1; + if (value1 == null) return void this.removeAttributeNS(fullname.space, fullname.local); + string0 = this.getAttributeNS(fullname.space, fullname.local); + string1 = value1 + ""; + return string0 === string1 ? null + : string0 === string00 && string1 === string10 ? interpolate0 + : (string10 = string1, interpolate0 = interpolate(string00 = string0, value1)); + }; +} + +function transition_attr(name, value) { + var fullname = d3Selection.namespace(name), i = fullname === "transform" ? d3Interpolate.interpolateTransformSvg : interpolate; + return this.attrTween(name, typeof value === "function" + ? (fullname.local ? attrFunctionNS : attrFunction)(fullname, i, tweenValue(this, "attr." + name, value)) + : value == null ? (fullname.local ? attrRemoveNS : attrRemove)(fullname) + : (fullname.local ? attrConstantNS : attrConstant)(fullname, i, value)); +} + +function attrInterpolate(name, i) { + return function(t) { + this.setAttribute(name, i.call(this, t)); + }; +} + +function attrInterpolateNS(fullname, i) { + return function(t) { + this.setAttributeNS(fullname.space, fullname.local, i.call(this, t)); + }; +} + +function attrTweenNS(fullname, value) { + var t0, i0; + function tween() { + var i = value.apply(this, arguments); + if (i !== i0) t0 = (i0 = i) && attrInterpolateNS(fullname, i); + return t0; + } + tween._value = value; + return tween; +} + +function attrTween(name, value) { + var t0, i0; + function tween() { + var i = value.apply(this, arguments); + if (i !== i0) t0 = (i0 = i) && attrInterpolate(name, i); + return t0; + } + tween._value = value; + return tween; +} + +function transition_attrTween(name, value) { + var key = "attr." + name; + if (arguments.length < 2) return (key = this.tween(key)) && key._value; + if (value == null) return this.tween(key, null); + if (typeof value !== "function") throw new Error; + var fullname = d3Selection.namespace(name); + return this.tween(key, (fullname.local ? attrTweenNS : attrTween)(fullname, value)); +} + +function delayFunction(id, value) { + return function() { + init(this, id).delay = +value.apply(this, arguments); + }; +} + +function delayConstant(id, value) { + return value = +value, function() { + init(this, id).delay = value; + }; +} + +function transition_delay(value) { + var id = this._id; + + return arguments.length + ? this.each((typeof value === "function" + ? delayFunction + : delayConstant)(id, value)) + : get(this.node(), id).delay; +} + +function durationFunction(id, value) { + return function() { + set(this, id).duration = +value.apply(this, arguments); + }; +} + +function durationConstant(id, value) { + return value = +value, function() { + set(this, id).duration = value; + }; +} + +function transition_duration(value) { + var id = this._id; + + return arguments.length + ? this.each((typeof value === "function" + ? durationFunction + : durationConstant)(id, value)) + : get(this.node(), id).duration; +} + +function easeConstant(id, value) { + if (typeof value !== "function") throw new Error; + return function() { + set(this, id).ease = value; + }; +} + +function transition_ease(value) { + var id = this._id; + + return arguments.length + ? this.each(easeConstant(id, value)) + : get(this.node(), id).ease; +} + +function easeVarying(id, value) { + return function() { + var v = value.apply(this, arguments); + if (typeof v !== "function") throw new Error; + set(this, id).ease = v; + }; +} + +function transition_easeVarying(value) { + if (typeof value !== "function") throw new Error; + return this.each(easeVarying(this._id, value)); +} + +function transition_filter(match) { + if (typeof match !== "function") match = d3Selection.matcher(match); + + for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, subgroup = subgroups[j] = [], node, i = 0; i < n; ++i) { + if ((node = group[i]) && match.call(node, node.__data__, i, group)) { + subgroup.push(node); + } + } + } + + return new Transition(subgroups, this._parents, this._name, this._id); +} + +function transition_merge(transition) { + if (transition._id !== this._id) throw new Error; + + for (var groups0 = this._groups, groups1 = transition._groups, m0 = groups0.length, m1 = groups1.length, m = Math.min(m0, m1), merges = new Array(m0), j = 0; j < m; ++j) { + for (var group0 = groups0[j], group1 = groups1[j], n = group0.length, merge = merges[j] = new Array(n), node, i = 0; i < n; ++i) { + if (node = group0[i] || group1[i]) { + merge[i] = node; + } + } + } + + for (; j < m0; ++j) { + merges[j] = groups0[j]; + } + + return new Transition(merges, this._parents, this._name, this._id); +} + +function start(name) { + return (name + "").trim().split(/^|\s+/).every(function(t) { + var i = t.indexOf("."); + if (i >= 0) t = t.slice(0, i); + return !t || t === "start"; + }); +} + +function onFunction(id, name, listener) { + var on0, on1, sit = start(name) ? init : set; + return function() { + var schedule = sit(this, id), + on = schedule.on; + + // If this node shared a dispatch with the previous node, + // just assign the updated shared dispatch and we’re done! + // Otherwise, copy-on-write. + if (on !== on0) (on1 = (on0 = on).copy()).on(name, listener); + + schedule.on = on1; + }; +} + +function transition_on(name, listener) { + var id = this._id; + + return arguments.length < 2 + ? get(this.node(), id).on.on(name) + : this.each(onFunction(id, name, listener)); +} + +function removeFunction(id) { + return function() { + var parent = this.parentNode; + for (var i in this.__transition) if (+i !== id) return; + if (parent) parent.removeChild(this); + }; +} + +function transition_remove() { + return this.on("end.remove", removeFunction(this._id)); +} + +function transition_select(select) { + var name = this._name, + id = this._id; + + if (typeof select !== "function") select = d3Selection.selector(select); + + for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, subgroup = subgroups[j] = new Array(n), node, subnode, i = 0; i < n; ++i) { + if ((node = group[i]) && (subnode = select.call(node, node.__data__, i, group))) { + if ("__data__" in node) subnode.__data__ = node.__data__; + subgroup[i] = subnode; + schedule(subgroup[i], name, id, i, subgroup, get(node, id)); + } + } + } + + return new Transition(subgroups, this._parents, name, id); +} + +function transition_selectAll(select) { + var name = this._name, + id = this._id; + + if (typeof select !== "function") select = d3Selection.selectorAll(select); + + for (var groups = this._groups, m = groups.length, subgroups = [], parents = [], j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) { + if (node = group[i]) { + for (var children = select.call(node, node.__data__, i, group), child, inherit = get(node, id), k = 0, l = children.length; k < l; ++k) { + if (child = children[k]) { + schedule(child, name, id, k, children, inherit); + } + } + subgroups.push(children); + parents.push(node); + } + } + } + + return new Transition(subgroups, parents, name, id); +} + +var Selection = d3Selection.selection.prototype.constructor; + +function transition_selection() { + return new Selection(this._groups, this._parents); +} + +function styleNull(name, interpolate) { + var string00, + string10, + interpolate0; + return function() { + var string0 = d3Selection.style(this, name), + string1 = (this.style.removeProperty(name), d3Selection.style(this, name)); + return string0 === string1 ? null + : string0 === string00 && string1 === string10 ? interpolate0 + : interpolate0 = interpolate(string00 = string0, string10 = string1); + }; +} + +function styleRemove(name) { + return function() { + this.style.removeProperty(name); + }; +} + +function styleConstant(name, interpolate, value1) { + var string00, + string1 = value1 + "", + interpolate0; + return function() { + var string0 = d3Selection.style(this, name); + return string0 === string1 ? null + : string0 === string00 ? interpolate0 + : interpolate0 = interpolate(string00 = string0, value1); + }; +} + +function styleFunction(name, interpolate, value) { + var string00, + string10, + interpolate0; + return function() { + var string0 = d3Selection.style(this, name), + value1 = value(this), + string1 = value1 + ""; + if (value1 == null) string1 = value1 = (this.style.removeProperty(name), d3Selection.style(this, name)); + return string0 === string1 ? null + : string0 === string00 && string1 === string10 ? interpolate0 + : (string10 = string1, interpolate0 = interpolate(string00 = string0, value1)); + }; +} + +function styleMaybeRemove(id, name) { + var on0, on1, listener0, key = "style." + name, event = "end." + key, remove; + return function() { + var schedule = set(this, id), + on = schedule.on, + listener = schedule.value[key] == null ? remove || (remove = styleRemove(name)) : undefined; + + // If this node shared a dispatch with the previous node, + // just assign the updated shared dispatch and we’re done! + // Otherwise, copy-on-write. + if (on !== on0 || listener0 !== listener) (on1 = (on0 = on).copy()).on(event, listener0 = listener); + + schedule.on = on1; + }; +} + +function transition_style(name, value, priority) { + var i = (name += "") === "transform" ? d3Interpolate.interpolateTransformCss : interpolate; + return value == null ? this + .styleTween(name, styleNull(name, i)) + .on("end.style." + name, styleRemove(name)) + : typeof value === "function" ? this + .styleTween(name, styleFunction(name, i, tweenValue(this, "style." + name, value))) + .each(styleMaybeRemove(this._id, name)) + : this + .styleTween(name, styleConstant(name, i, value), priority) + .on("end.style." + name, null); +} + +function styleInterpolate(name, i, priority) { + return function(t) { + this.style.setProperty(name, i.call(this, t), priority); + }; +} + +function styleTween(name, value, priority) { + var t, i0; + function tween() { + var i = value.apply(this, arguments); + if (i !== i0) t = (i0 = i) && styleInterpolate(name, i, priority); + return t; + } + tween._value = value; + return tween; +} + +function transition_styleTween(name, value, priority) { + var key = "style." + (name += ""); + if (arguments.length < 2) return (key = this.tween(key)) && key._value; + if (value == null) return this.tween(key, null); + if (typeof value !== "function") throw new Error; + return this.tween(key, styleTween(name, value, priority == null ? "" : priority)); +} + +function textConstant(value) { + return function() { + this.textContent = value; + }; +} + +function textFunction(value) { + return function() { + var value1 = value(this); + this.textContent = value1 == null ? "" : value1; + }; +} + +function transition_text(value) { + return this.tween("text", typeof value === "function" + ? textFunction(tweenValue(this, "text", value)) + : textConstant(value == null ? "" : value + "")); +} + +function textInterpolate(i) { + return function(t) { + this.textContent = i.call(this, t); + }; +} + +function textTween(value) { + var t0, i0; + function tween() { + var i = value.apply(this, arguments); + if (i !== i0) t0 = (i0 = i) && textInterpolate(i); + return t0; + } + tween._value = value; + return tween; +} + +function transition_textTween(value) { + var key = "text"; + if (arguments.length < 1) return (key = this.tween(key)) && key._value; + if (value == null) return this.tween(key, null); + if (typeof value !== "function") throw new Error; + return this.tween(key, textTween(value)); +} + +function transition_transition() { + var name = this._name, + id0 = this._id, + id1 = newId(); + + for (var groups = this._groups, m = groups.length, j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) { + if (node = group[i]) { + var inherit = get(node, id0); + schedule(node, name, id1, i, group, { + time: inherit.time + inherit.delay + inherit.duration, + delay: 0, + duration: inherit.duration, + ease: inherit.ease + }); + } + } + } + + return new Transition(groups, this._parents, name, id1); +} + +function transition_end() { + var on0, on1, that = this, id = that._id, size = that.size(); + return new Promise(function(resolve, reject) { + var cancel = {value: reject}, + end = {value: function() { if (--size === 0) resolve(); }}; + + that.each(function() { + var schedule = set(this, id), + on = schedule.on; + + // If this node shared a dispatch with the previous node, + // just assign the updated shared dispatch and we’re done! + // Otherwise, copy-on-write. + if (on !== on0) { + on1 = (on0 = on).copy(); + on1._.cancel.push(cancel); + on1._.interrupt.push(cancel); + on1._.end.push(end); + } + + schedule.on = on1; + }); + + // The selection was empty, resolve end immediately + if (size === 0) resolve(); + }); +} + +var id = 0; + +function Transition(groups, parents, name, id) { + this._groups = groups; + this._parents = parents; + this._name = name; + this._id = id; +} + +function transition(name) { + return d3Selection.selection().transition(name); +} + +function newId() { + return ++id; +} + +var selection_prototype = d3Selection.selection.prototype; + +Transition.prototype = transition.prototype = { + constructor: Transition, + select: transition_select, + selectAll: transition_selectAll, + selectChild: selection_prototype.selectChild, + selectChildren: selection_prototype.selectChildren, + filter: transition_filter, + merge: transition_merge, + selection: transition_selection, + transition: transition_transition, + call: selection_prototype.call, + nodes: selection_prototype.nodes, + node: selection_prototype.node, + size: selection_prototype.size, + empty: selection_prototype.empty, + each: selection_prototype.each, + on: transition_on, + attr: transition_attr, + attrTween: transition_attrTween, + style: transition_style, + styleTween: transition_styleTween, + text: transition_text, + textTween: transition_textTween, + remove: transition_remove, + tween: transition_tween, + delay: transition_delay, + duration: transition_duration, + ease: transition_ease, + easeVarying: transition_easeVarying, + end: transition_end, + [Symbol.iterator]: selection_prototype[Symbol.iterator] +}; + +var defaultTiming = { + time: null, // Set on use. + delay: 0, + duration: 250, + ease: d3Ease.easeCubicInOut +}; + +function inherit(node, id) { + var timing; + while (!(timing = node.__transition) || !(timing = timing[id])) { + if (!(node = node.parentNode)) { + throw new Error(`transition ${id} not found`); + } + } + return timing; +} + +function selection_transition(name) { + var id, + timing; + + if (name instanceof Transition) { + id = name._id, name = name._name; + } else { + id = newId(), (timing = defaultTiming).time = d3Timer.now(), name = name == null ? null : name + ""; + } + + for (var groups = this._groups, m = groups.length, j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) { + if (node = group[i]) { + schedule(node, name, id, i, group, timing || inherit(node, id)); + } + } + } + + return new Transition(groups, this._parents, name, id); +} + +d3Selection.selection.prototype.interrupt = selection_interrupt; +d3Selection.selection.prototype.transition = selection_transition; + +var root = [null]; + +function active(node, name) { + var schedules = node.__transition, + schedule, + i; + + if (schedules) { + name = name == null ? null : name + ""; + for (i in schedules) { + if ((schedule = schedules[i]).state > SCHEDULED && schedule.name === name) { + return new Transition([[node]], root, name, +i); + } + } + } + + return null; +} + +exports.active = active; +exports.interrupt = interrupt; +exports.transition = transition; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-transition/dist/d3-transition.min.js b/frontend/node_modules/d3-transition/dist/d3-transition.min.js new file mode 100644 index 0000000..8e9bffd --- /dev/null +++ b/frontend/node_modules/d3-transition/dist/d3-transition.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-transition/ v3.0.1 Copyright 2010-2021 Mike Bostock +!function(t,n){"object"==typeof exports&&"undefined"!=typeof module?n(exports,require("d3-selection"),require("d3-dispatch"),require("d3-timer"),require("d3-interpolate"),require("d3-color"),require("d3-ease")):"function"==typeof define&&define.amd?define(["exports","d3-selection","d3-dispatch","d3-timer","d3-interpolate","d3-color","d3-ease"],n):n((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{},t.d3,t.d3,t.d3,t.d3,t.d3,t.d3)}(this,(function(t,n,e,r,i,o,u){"use strict";var a=e.dispatch("start","end","cancel","interrupt"),s=[];function l(t,n,e,i,o,u){var l=t.__transition;if(l){if(e in l)return}else t.__transition={};!function(t,n,e){var i,o=t.__transition;function u(t){e.state=1,e.timer.restart(a,e.delay,e.time),e.delay<=t&&a(t-e.delay)}function a(u){var f,c,h,d;if(1!==e.state)return l();for(f in o)if((d=o[f]).name===e.name){if(3===d.state)return r.timeout(a);4===d.state?(d.state=6,d.timer.stop(),d.on.call("interrupt",t,t.__data__,d.index,d.group),delete o[f]):+f0)throw new Error("too late; already scheduled");return e}function c(t,n){var e=h(t,n);if(e.state>3)throw new Error("too late; already running");return e}function h(t,n){var e=t.__transition;if(!e||!(e=e[n]))throw new Error("transition not found");return e}function d(t,n){var e,r,i,o=t.__transition,u=!0;if(o){for(i in n=null==n?null:n+"",o)(e=o[i]).name===n?(r=e.state>2&&e.state<5,e.state=6,e.timer.stop(),e.on.call(r?"interrupt":"cancel",t,t.__data__,e.index,e.group),delete o[i]):u=!1;u&&delete t.__transition}}function p(t,n){var e,r;return function(){var i=c(this,t),o=i.tween;if(o!==e)for(var u=0,a=(r=e=o).length;u=0&&(t=t.slice(0,n)),!t||"start"===t}))}(n)?f:c;return function(){var u=o(this,t),a=u.on;a!==r&&(i=(r=a).copy()).on(n,e),u.on=i}}var k=n.selection.prototype.constructor;function M(t){return function(){this.style.removeProperty(t)}}function R(t,n,e){return function(r){this.style.setProperty(t,n.call(this,r),e)}}function I(t,n,e){var r,i;function o(){var o=n.apply(this,arguments);return o!==i&&(r=(i=o)&&R(t,o,e)),r}return o._value=n,o}function V(t){return function(n){this.textContent=t.call(this,n)}}function $(t){var n,e;function r(){var r=t.apply(this,arguments);return r!==e&&(n=(e=r)&&V(r)),n}return r._value=t,r}var B=0;function D(t,n,e,r){this._groups=t,this._parents=n,this._name=e,this._id=r}function F(t){return n.selection().transition(t)}function G(){return++B}var H=n.selection.prototype;D.prototype=F.prototype={constructor:D,select:function(t){var e=this._name,r=this._id;"function"!=typeof t&&(t=n.selector(t));for(var i=this._groups,o=i.length,u=new Array(o),a=0;a1&&e.name===n)return new D([[t]],L,n,+r);return null},t.interrupt=d,t.transition=F,Object.defineProperty(t,"__esModule",{value:!0})})); diff --git a/frontend/node_modules/d3-transition/package.json b/frontend/node_modules/d3-transition/package.json new file mode 100644 index 0000000..b38ab5d --- /dev/null +++ b/frontend/node_modules/d3-transition/package.json @@ -0,0 +1,65 @@ +{ + "name": "d3-transition", + "version": "3.0.1", + "description": "Animated transitions for D3 selections.", + "homepage": "https://d3js.org/d3-transition/", + "repository": { + "type": "git", + "url": "https://github.com/d3/d3-transition.git" + }, + "keywords": [ + "d3", + "d3-module", + "dom", + "transition", + "animation" + ], + "license": "ISC", + "author": { + "name": "Mike Bostock", + "url": "https://bost.ocks.org/mike" + }, + "type": "module", + "files": [ + "dist/**/*.js", + "src/**/*.js" + ], + "module": "src/index.js", + "main": "src/index.js", + "jsdelivr": "dist/d3-transition.min.js", + "unpkg": "dist/d3-transition.min.js", + "exports": { + "umd": "./dist/d3-transition.min.js", + "default": "./src/index.js" + }, + "sideEffects": [ + "./src/index.js", + "./src/selection/index.js" + ], + "dependencies": { + "d3-color": "1 - 3", + "d3-dispatch": "1 - 3", + "d3-ease": "1 - 3", + "d3-interpolate": "1 - 3", + "d3-timer": "1 - 3" + }, + "devDependencies": { + "d3-selection": "2 - 3", + "eslint": "7", + "jsdom": "16", + "mocha": "9", + "rollup": "2", + "rollup-plugin-terser": "7" + }, + "scripts": { + "test": "mocha 'test/**/*-test.js' && eslint src test", + "prepublishOnly": "rm -rf dist && yarn test && rollup -c && git push", + "postpublish": "git push --tags && cd ../d3.github.com && git pull && cp ../${npm_package_name}/dist/${npm_package_name}.js ${npm_package_name}.v${npm_package_version%%.*}.js && cp ../${npm_package_name}/dist/${npm_package_name}.min.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git add ${npm_package_name}.v${npm_package_version%%.*}.js ${npm_package_name}.v${npm_package_version%%.*}.min.js && git commit -m \"${npm_package_name} ${npm_package_version}\" && git push && cd -" + }, + "engines": { + "node": ">=12" + }, + "peerDependencies": { + "d3-selection": "2 - 3" + } +} diff --git a/frontend/node_modules/d3-transition/src/active.js b/frontend/node_modules/d3-transition/src/active.js new file mode 100644 index 0000000..abd4c67 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/active.js @@ -0,0 +1,21 @@ +import {Transition} from "./transition/index.js"; +import {SCHEDULED} from "./transition/schedule.js"; + +var root = [null]; + +export default function(node, name) { + var schedules = node.__transition, + schedule, + i; + + if (schedules) { + name = name == null ? null : name + ""; + for (i in schedules) { + if ((schedule = schedules[i]).state > SCHEDULED && schedule.name === name) { + return new Transition([[node]], root, name, +i); + } + } + } + + return null; +} diff --git a/frontend/node_modules/d3-transition/src/index.js b/frontend/node_modules/d3-transition/src/index.js new file mode 100644 index 0000000..d6a6dd3 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/index.js @@ -0,0 +1,4 @@ +import "./selection/index.js"; +export {default as transition} from "./transition/index.js"; +export {default as active} from "./active.js"; +export {default as interrupt} from "./interrupt.js"; diff --git a/frontend/node_modules/d3-transition/src/interrupt.js b/frontend/node_modules/d3-transition/src/interrupt.js new file mode 100644 index 0000000..efb455e --- /dev/null +++ b/frontend/node_modules/d3-transition/src/interrupt.js @@ -0,0 +1,24 @@ +import {STARTING, ENDING, ENDED} from "./transition/schedule.js"; + +export default function(node, name) { + var schedules = node.__transition, + schedule, + active, + empty = true, + i; + + if (!schedules) return; + + name = name == null ? null : name + ""; + + for (i in schedules) { + if ((schedule = schedules[i]).name !== name) { empty = false; continue; } + active = schedule.state > STARTING && schedule.state < ENDING; + schedule.state = ENDED; + schedule.timer.stop(); + schedule.on.call(active ? "interrupt" : "cancel", node, node.__data__, schedule.index, schedule.group); + delete schedules[i]; + } + + if (empty) delete node.__transition; +} diff --git a/frontend/node_modules/d3-transition/src/selection/index.js b/frontend/node_modules/d3-transition/src/selection/index.js new file mode 100644 index 0000000..c5512ef --- /dev/null +++ b/frontend/node_modules/d3-transition/src/selection/index.js @@ -0,0 +1,6 @@ +import {selection} from "d3-selection"; +import selection_interrupt from "./interrupt.js"; +import selection_transition from "./transition.js"; + +selection.prototype.interrupt = selection_interrupt; +selection.prototype.transition = selection_transition; diff --git a/frontend/node_modules/d3-transition/src/selection/interrupt.js b/frontend/node_modules/d3-transition/src/selection/interrupt.js new file mode 100644 index 0000000..799a923 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/selection/interrupt.js @@ -0,0 +1,7 @@ +import interrupt from "../interrupt.js"; + +export default function(name) { + return this.each(function() { + interrupt(this, name); + }); +} diff --git a/frontend/node_modules/d3-transition/src/selection/transition.js b/frontend/node_modules/d3-transition/src/selection/transition.js new file mode 100644 index 0000000..a328dcb --- /dev/null +++ b/frontend/node_modules/d3-transition/src/selection/transition.js @@ -0,0 +1,42 @@ +import {Transition, newId} from "../transition/index.js"; +import schedule from "../transition/schedule.js"; +import {easeCubicInOut} from "d3-ease"; +import {now} from "d3-timer"; + +var defaultTiming = { + time: null, // Set on use. + delay: 0, + duration: 250, + ease: easeCubicInOut +}; + +function inherit(node, id) { + var timing; + while (!(timing = node.__transition) || !(timing = timing[id])) { + if (!(node = node.parentNode)) { + throw new Error(`transition ${id} not found`); + } + } + return timing; +} + +export default function(name) { + var id, + timing; + + if (name instanceof Transition) { + id = name._id, name = name._name; + } else { + id = newId(), (timing = defaultTiming).time = now(), name = name == null ? null : name + ""; + } + + for (var groups = this._groups, m = groups.length, j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) { + if (node = group[i]) { + schedule(node, name, id, i, group, timing || inherit(node, id)); + } + } + } + + return new Transition(groups, this._parents, name, id); +} diff --git a/frontend/node_modules/d3-transition/src/transition/attr.js b/frontend/node_modules/d3-transition/src/transition/attr.js new file mode 100644 index 0000000..3c3c764 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/attr.js @@ -0,0 +1,78 @@ +import {interpolateTransformSvg as interpolateTransform} from "d3-interpolate"; +import {namespace} from "d3-selection"; +import {tweenValue} from "./tween.js"; +import interpolate from "./interpolate.js"; + +function attrRemove(name) { + return function() { + this.removeAttribute(name); + }; +} + +function attrRemoveNS(fullname) { + return function() { + this.removeAttributeNS(fullname.space, fullname.local); + }; +} + +function attrConstant(name, interpolate, value1) { + var string00, + string1 = value1 + "", + interpolate0; + return function() { + var string0 = this.getAttribute(name); + return string0 === string1 ? null + : string0 === string00 ? interpolate0 + : interpolate0 = interpolate(string00 = string0, value1); + }; +} + +function attrConstantNS(fullname, interpolate, value1) { + var string00, + string1 = value1 + "", + interpolate0; + return function() { + var string0 = this.getAttributeNS(fullname.space, fullname.local); + return string0 === string1 ? null + : string0 === string00 ? interpolate0 + : interpolate0 = interpolate(string00 = string0, value1); + }; +} + +function attrFunction(name, interpolate, value) { + var string00, + string10, + interpolate0; + return function() { + var string0, value1 = value(this), string1; + if (value1 == null) return void this.removeAttribute(name); + string0 = this.getAttribute(name); + string1 = value1 + ""; + return string0 === string1 ? null + : string0 === string00 && string1 === string10 ? interpolate0 + : (string10 = string1, interpolate0 = interpolate(string00 = string0, value1)); + }; +} + +function attrFunctionNS(fullname, interpolate, value) { + var string00, + string10, + interpolate0; + return function() { + var string0, value1 = value(this), string1; + if (value1 == null) return void this.removeAttributeNS(fullname.space, fullname.local); + string0 = this.getAttributeNS(fullname.space, fullname.local); + string1 = value1 + ""; + return string0 === string1 ? null + : string0 === string00 && string1 === string10 ? interpolate0 + : (string10 = string1, interpolate0 = interpolate(string00 = string0, value1)); + }; +} + +export default function(name, value) { + var fullname = namespace(name), i = fullname === "transform" ? interpolateTransform : interpolate; + return this.attrTween(name, typeof value === "function" + ? (fullname.local ? attrFunctionNS : attrFunction)(fullname, i, tweenValue(this, "attr." + name, value)) + : value == null ? (fullname.local ? attrRemoveNS : attrRemove)(fullname) + : (fullname.local ? attrConstantNS : attrConstant)(fullname, i, value)); +} diff --git a/frontend/node_modules/d3-transition/src/transition/attrTween.js b/frontend/node_modules/d3-transition/src/transition/attrTween.js new file mode 100644 index 0000000..0dd4a00 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/attrTween.js @@ -0,0 +1,44 @@ +import {namespace} from "d3-selection"; + +function attrInterpolate(name, i) { + return function(t) { + this.setAttribute(name, i.call(this, t)); + }; +} + +function attrInterpolateNS(fullname, i) { + return function(t) { + this.setAttributeNS(fullname.space, fullname.local, i.call(this, t)); + }; +} + +function attrTweenNS(fullname, value) { + var t0, i0; + function tween() { + var i = value.apply(this, arguments); + if (i !== i0) t0 = (i0 = i) && attrInterpolateNS(fullname, i); + return t0; + } + tween._value = value; + return tween; +} + +function attrTween(name, value) { + var t0, i0; + function tween() { + var i = value.apply(this, arguments); + if (i !== i0) t0 = (i0 = i) && attrInterpolate(name, i); + return t0; + } + tween._value = value; + return tween; +} + +export default function(name, value) { + var key = "attr." + name; + if (arguments.length < 2) return (key = this.tween(key)) && key._value; + if (value == null) return this.tween(key, null); + if (typeof value !== "function") throw new Error; + var fullname = namespace(name); + return this.tween(key, (fullname.local ? attrTweenNS : attrTween)(fullname, value)); +} diff --git a/frontend/node_modules/d3-transition/src/transition/delay.js b/frontend/node_modules/d3-transition/src/transition/delay.js new file mode 100644 index 0000000..1ba1acd --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/delay.js @@ -0,0 +1,23 @@ +import {get, init} from "./schedule.js"; + +function delayFunction(id, value) { + return function() { + init(this, id).delay = +value.apply(this, arguments); + }; +} + +function delayConstant(id, value) { + return value = +value, function() { + init(this, id).delay = value; + }; +} + +export default function(value) { + var id = this._id; + + return arguments.length + ? this.each((typeof value === "function" + ? delayFunction + : delayConstant)(id, value)) + : get(this.node(), id).delay; +} diff --git a/frontend/node_modules/d3-transition/src/transition/duration.js b/frontend/node_modules/d3-transition/src/transition/duration.js new file mode 100644 index 0000000..445691e --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/duration.js @@ -0,0 +1,23 @@ +import {get, set} from "./schedule.js"; + +function durationFunction(id, value) { + return function() { + set(this, id).duration = +value.apply(this, arguments); + }; +} + +function durationConstant(id, value) { + return value = +value, function() { + set(this, id).duration = value; + }; +} + +export default function(value) { + var id = this._id; + + return arguments.length + ? this.each((typeof value === "function" + ? durationFunction + : durationConstant)(id, value)) + : get(this.node(), id).duration; +} diff --git a/frontend/node_modules/d3-transition/src/transition/ease.js b/frontend/node_modules/d3-transition/src/transition/ease.js new file mode 100644 index 0000000..83b1445 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/ease.js @@ -0,0 +1,16 @@ +import {get, set} from "./schedule.js"; + +function easeConstant(id, value) { + if (typeof value !== "function") throw new Error; + return function() { + set(this, id).ease = value; + }; +} + +export default function(value) { + var id = this._id; + + return arguments.length + ? this.each(easeConstant(id, value)) + : get(this.node(), id).ease; +} diff --git a/frontend/node_modules/d3-transition/src/transition/easeVarying.js b/frontend/node_modules/d3-transition/src/transition/easeVarying.js new file mode 100644 index 0000000..51e3a0d --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/easeVarying.js @@ -0,0 +1,14 @@ +import {set} from "./schedule.js"; + +function easeVarying(id, value) { + return function() { + var v = value.apply(this, arguments); + if (typeof v !== "function") throw new Error; + set(this, id).ease = v; + }; +} + +export default function(value) { + if (typeof value !== "function") throw new Error; + return this.each(easeVarying(this._id, value)); +} diff --git a/frontend/node_modules/d3-transition/src/transition/end.js b/frontend/node_modules/d3-transition/src/transition/end.js new file mode 100644 index 0000000..d9aa373 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/end.js @@ -0,0 +1,29 @@ +import {set} from "./schedule.js"; + +export default function() { + var on0, on1, that = this, id = that._id, size = that.size(); + return new Promise(function(resolve, reject) { + var cancel = {value: reject}, + end = {value: function() { if (--size === 0) resolve(); }}; + + that.each(function() { + var schedule = set(this, id), + on = schedule.on; + + // If this node shared a dispatch with the previous node, + // just assign the updated shared dispatch and we’re done! + // Otherwise, copy-on-write. + if (on !== on0) { + on1 = (on0 = on).copy(); + on1._.cancel.push(cancel); + on1._.interrupt.push(cancel); + on1._.end.push(end); + } + + schedule.on = on1; + }); + + // The selection was empty, resolve end immediately + if (size === 0) resolve(); + }); +} diff --git a/frontend/node_modules/d3-transition/src/transition/filter.js b/frontend/node_modules/d3-transition/src/transition/filter.js new file mode 100644 index 0000000..f5237be --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/filter.js @@ -0,0 +1,16 @@ +import {matcher} from "d3-selection"; +import {Transition} from "./index.js"; + +export default function(match) { + if (typeof match !== "function") match = matcher(match); + + for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, subgroup = subgroups[j] = [], node, i = 0; i < n; ++i) { + if ((node = group[i]) && match.call(node, node.__data__, i, group)) { + subgroup.push(node); + } + } + } + + return new Transition(subgroups, this._parents, this._name, this._id); +} diff --git a/frontend/node_modules/d3-transition/src/transition/index.js b/frontend/node_modules/d3-transition/src/transition/index.js new file mode 100644 index 0000000..81e7747 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/index.js @@ -0,0 +1,73 @@ +import {selection} from "d3-selection"; +import transition_attr from "./attr.js"; +import transition_attrTween from "./attrTween.js"; +import transition_delay from "./delay.js"; +import transition_duration from "./duration.js"; +import transition_ease from "./ease.js"; +import transition_easeVarying from "./easeVarying.js"; +import transition_filter from "./filter.js"; +import transition_merge from "./merge.js"; +import transition_on from "./on.js"; +import transition_remove from "./remove.js"; +import transition_select from "./select.js"; +import transition_selectAll from "./selectAll.js"; +import transition_selection from "./selection.js"; +import transition_style from "./style.js"; +import transition_styleTween from "./styleTween.js"; +import transition_text from "./text.js"; +import transition_textTween from "./textTween.js"; +import transition_transition from "./transition.js"; +import transition_tween from "./tween.js"; +import transition_end from "./end.js"; + +var id = 0; + +export function Transition(groups, parents, name, id) { + this._groups = groups; + this._parents = parents; + this._name = name; + this._id = id; +} + +export default function transition(name) { + return selection().transition(name); +} + +export function newId() { + return ++id; +} + +var selection_prototype = selection.prototype; + +Transition.prototype = transition.prototype = { + constructor: Transition, + select: transition_select, + selectAll: transition_selectAll, + selectChild: selection_prototype.selectChild, + selectChildren: selection_prototype.selectChildren, + filter: transition_filter, + merge: transition_merge, + selection: transition_selection, + transition: transition_transition, + call: selection_prototype.call, + nodes: selection_prototype.nodes, + node: selection_prototype.node, + size: selection_prototype.size, + empty: selection_prototype.empty, + each: selection_prototype.each, + on: transition_on, + attr: transition_attr, + attrTween: transition_attrTween, + style: transition_style, + styleTween: transition_styleTween, + text: transition_text, + textTween: transition_textTween, + remove: transition_remove, + tween: transition_tween, + delay: transition_delay, + duration: transition_duration, + ease: transition_ease, + easeVarying: transition_easeVarying, + end: transition_end, + [Symbol.iterator]: selection_prototype[Symbol.iterator] +}; diff --git a/frontend/node_modules/d3-transition/src/transition/interpolate.js b/frontend/node_modules/d3-transition/src/transition/interpolate.js new file mode 100644 index 0000000..d389d62 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/interpolate.js @@ -0,0 +1,10 @@ +import {color} from "d3-color"; +import {interpolateNumber, interpolateRgb, interpolateString} from "d3-interpolate"; + +export default function(a, b) { + var c; + return (typeof b === "number" ? interpolateNumber + : b instanceof color ? interpolateRgb + : (c = color(b)) ? (b = c, interpolateRgb) + : interpolateString)(a, b); +} diff --git a/frontend/node_modules/d3-transition/src/transition/merge.js b/frontend/node_modules/d3-transition/src/transition/merge.js new file mode 100644 index 0000000..4660953 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/merge.js @@ -0,0 +1,19 @@ +import {Transition} from "./index.js"; + +export default function(transition) { + if (transition._id !== this._id) throw new Error; + + for (var groups0 = this._groups, groups1 = transition._groups, m0 = groups0.length, m1 = groups1.length, m = Math.min(m0, m1), merges = new Array(m0), j = 0; j < m; ++j) { + for (var group0 = groups0[j], group1 = groups1[j], n = group0.length, merge = merges[j] = new Array(n), node, i = 0; i < n; ++i) { + if (node = group0[i] || group1[i]) { + merge[i] = node; + } + } + } + + for (; j < m0; ++j) { + merges[j] = groups0[j]; + } + + return new Transition(merges, this._parents, this._name, this._id); +} diff --git a/frontend/node_modules/d3-transition/src/transition/on.js b/frontend/node_modules/d3-transition/src/transition/on.js new file mode 100644 index 0000000..b6a91d3 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/on.js @@ -0,0 +1,32 @@ +import {get, set, init} from "./schedule.js"; + +function start(name) { + return (name + "").trim().split(/^|\s+/).every(function(t) { + var i = t.indexOf("."); + if (i >= 0) t = t.slice(0, i); + return !t || t === "start"; + }); +} + +function onFunction(id, name, listener) { + var on0, on1, sit = start(name) ? init : set; + return function() { + var schedule = sit(this, id), + on = schedule.on; + + // If this node shared a dispatch with the previous node, + // just assign the updated shared dispatch and we’re done! + // Otherwise, copy-on-write. + if (on !== on0) (on1 = (on0 = on).copy()).on(name, listener); + + schedule.on = on1; + }; +} + +export default function(name, listener) { + var id = this._id; + + return arguments.length < 2 + ? get(this.node(), id).on.on(name) + : this.each(onFunction(id, name, listener)); +} diff --git a/frontend/node_modules/d3-transition/src/transition/remove.js b/frontend/node_modules/d3-transition/src/transition/remove.js new file mode 100644 index 0000000..c4bff9b --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/remove.js @@ -0,0 +1,11 @@ +function removeFunction(id) { + return function() { + var parent = this.parentNode; + for (var i in this.__transition) if (+i !== id) return; + if (parent) parent.removeChild(this); + }; +} + +export default function() { + return this.on("end.remove", removeFunction(this._id)); +} diff --git a/frontend/node_modules/d3-transition/src/transition/schedule.js b/frontend/node_modules/d3-transition/src/transition/schedule.js new file mode 100644 index 0000000..f4e88d7 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/schedule.js @@ -0,0 +1,153 @@ +import {dispatch} from "d3-dispatch"; +import {timer, timeout} from "d3-timer"; + +var emptyOn = dispatch("start", "end", "cancel", "interrupt"); +var emptyTween = []; + +export var CREATED = 0; +export var SCHEDULED = 1; +export var STARTING = 2; +export var STARTED = 3; +export var RUNNING = 4; +export var ENDING = 5; +export var ENDED = 6; + +export default function(node, name, id, index, group, timing) { + var schedules = node.__transition; + if (!schedules) node.__transition = {}; + else if (id in schedules) return; + create(node, id, { + name: name, + index: index, // For context during callback. + group: group, // For context during callback. + on: emptyOn, + tween: emptyTween, + time: timing.time, + delay: timing.delay, + duration: timing.duration, + ease: timing.ease, + timer: null, + state: CREATED + }); +} + +export function init(node, id) { + var schedule = get(node, id); + if (schedule.state > CREATED) throw new Error("too late; already scheduled"); + return schedule; +} + +export function set(node, id) { + var schedule = get(node, id); + if (schedule.state > STARTED) throw new Error("too late; already running"); + return schedule; +} + +export function get(node, id) { + var schedule = node.__transition; + if (!schedule || !(schedule = schedule[id])) throw new Error("transition not found"); + return schedule; +} + +function create(node, id, self) { + var schedules = node.__transition, + tween; + + // Initialize the self timer when the transition is created. + // Note the actual delay is not known until the first callback! + schedules[id] = self; + self.timer = timer(schedule, 0, self.time); + + function schedule(elapsed) { + self.state = SCHEDULED; + self.timer.restart(start, self.delay, self.time); + + // If the elapsed delay is less than our first sleep, start immediately. + if (self.delay <= elapsed) start(elapsed - self.delay); + } + + function start(elapsed) { + var i, j, n, o; + + // If the state is not SCHEDULED, then we previously errored on start. + if (self.state !== SCHEDULED) return stop(); + + for (i in schedules) { + o = schedules[i]; + if (o.name !== self.name) continue; + + // While this element already has a starting transition during this frame, + // defer starting an interrupting transition until that transition has a + // chance to tick (and possibly end); see d3/d3-transition#54! + if (o.state === STARTED) return timeout(start); + + // Interrupt the active transition, if any. + if (o.state === RUNNING) { + o.state = ENDED; + o.timer.stop(); + o.on.call("interrupt", node, node.__data__, o.index, o.group); + delete schedules[i]; + } + + // Cancel any pre-empted transitions. + else if (+i < id) { + o.state = ENDED; + o.timer.stop(); + o.on.call("cancel", node, node.__data__, o.index, o.group); + delete schedules[i]; + } + } + + // Defer the first tick to end of the current frame; see d3/d3#1576. + // Note the transition may be canceled after start and before the first tick! + // Note this must be scheduled before the start event; see d3/d3-transition#16! + // Assuming this is successful, subsequent callbacks go straight to tick. + timeout(function() { + if (self.state === STARTED) { + self.state = RUNNING; + self.timer.restart(tick, self.delay, self.time); + tick(elapsed); + } + }); + + // Dispatch the start event. + // Note this must be done before the tween are initialized. + self.state = STARTING; + self.on.call("start", node, node.__data__, self.index, self.group); + if (self.state !== STARTING) return; // interrupted + self.state = STARTED; + + // Initialize the tween, deleting null tween. + tween = new Array(n = self.tween.length); + for (i = 0, j = -1; i < n; ++i) { + if (o = self.tween[i].value.call(node, node.__data__, self.index, self.group)) { + tween[++j] = o; + } + } + tween.length = j + 1; + } + + function tick(elapsed) { + var t = elapsed < self.duration ? self.ease.call(null, elapsed / self.duration) : (self.timer.restart(stop), self.state = ENDING, 1), + i = -1, + n = tween.length; + + while (++i < n) { + tween[i].call(node, t); + } + + // Dispatch the end event. + if (self.state === ENDING) { + self.on.call("end", node, node.__data__, self.index, self.group); + stop(); + } + } + + function stop() { + self.state = ENDED; + self.timer.stop(); + delete schedules[id]; + for (var i in schedules) return; // eslint-disable-line no-unused-vars + delete node.__transition; + } +} diff --git a/frontend/node_modules/d3-transition/src/transition/select.js b/frontend/node_modules/d3-transition/src/transition/select.js new file mode 100644 index 0000000..959c8c0 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/select.js @@ -0,0 +1,22 @@ +import {selector} from "d3-selection"; +import {Transition} from "./index.js"; +import schedule, {get} from "./schedule.js"; + +export default function(select) { + var name = this._name, + id = this._id; + + if (typeof select !== "function") select = selector(select); + + for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, subgroup = subgroups[j] = new Array(n), node, subnode, i = 0; i < n; ++i) { + if ((node = group[i]) && (subnode = select.call(node, node.__data__, i, group))) { + if ("__data__" in node) subnode.__data__ = node.__data__; + subgroup[i] = subnode; + schedule(subgroup[i], name, id, i, subgroup, get(node, id)); + } + } + } + + return new Transition(subgroups, this._parents, name, id); +} diff --git a/frontend/node_modules/d3-transition/src/transition/selectAll.js b/frontend/node_modules/d3-transition/src/transition/selectAll.js new file mode 100644 index 0000000..1ba4801 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/selectAll.js @@ -0,0 +1,26 @@ +import {selectorAll} from "d3-selection"; +import {Transition} from "./index.js"; +import schedule, {get} from "./schedule.js"; + +export default function(select) { + var name = this._name, + id = this._id; + + if (typeof select !== "function") select = selectorAll(select); + + for (var groups = this._groups, m = groups.length, subgroups = [], parents = [], j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) { + if (node = group[i]) { + for (var children = select.call(node, node.__data__, i, group), child, inherit = get(node, id), k = 0, l = children.length; k < l; ++k) { + if (child = children[k]) { + schedule(child, name, id, k, children, inherit); + } + } + subgroups.push(children); + parents.push(node); + } + } + } + + return new Transition(subgroups, parents, name, id); +} diff --git a/frontend/node_modules/d3-transition/src/transition/selection.js b/frontend/node_modules/d3-transition/src/transition/selection.js new file mode 100644 index 0000000..d0c5944 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/selection.js @@ -0,0 +1,7 @@ +import {selection} from "d3-selection"; + +var Selection = selection.prototype.constructor; + +export default function() { + return new Selection(this._groups, this._parents); +} diff --git a/frontend/node_modules/d3-transition/src/transition/style.js b/frontend/node_modules/d3-transition/src/transition/style.js new file mode 100644 index 0000000..7dcb187 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/style.js @@ -0,0 +1,80 @@ +import {interpolateTransformCss as interpolateTransform} from "d3-interpolate"; +import {style} from "d3-selection"; +import {set} from "./schedule.js"; +import {tweenValue} from "./tween.js"; +import interpolate from "./interpolate.js"; + +function styleNull(name, interpolate) { + var string00, + string10, + interpolate0; + return function() { + var string0 = style(this, name), + string1 = (this.style.removeProperty(name), style(this, name)); + return string0 === string1 ? null + : string0 === string00 && string1 === string10 ? interpolate0 + : interpolate0 = interpolate(string00 = string0, string10 = string1); + }; +} + +function styleRemove(name) { + return function() { + this.style.removeProperty(name); + }; +} + +function styleConstant(name, interpolate, value1) { + var string00, + string1 = value1 + "", + interpolate0; + return function() { + var string0 = style(this, name); + return string0 === string1 ? null + : string0 === string00 ? interpolate0 + : interpolate0 = interpolate(string00 = string0, value1); + }; +} + +function styleFunction(name, interpolate, value) { + var string00, + string10, + interpolate0; + return function() { + var string0 = style(this, name), + value1 = value(this), + string1 = value1 + ""; + if (value1 == null) string1 = value1 = (this.style.removeProperty(name), style(this, name)); + return string0 === string1 ? null + : string0 === string00 && string1 === string10 ? interpolate0 + : (string10 = string1, interpolate0 = interpolate(string00 = string0, value1)); + }; +} + +function styleMaybeRemove(id, name) { + var on0, on1, listener0, key = "style." + name, event = "end." + key, remove; + return function() { + var schedule = set(this, id), + on = schedule.on, + listener = schedule.value[key] == null ? remove || (remove = styleRemove(name)) : undefined; + + // If this node shared a dispatch with the previous node, + // just assign the updated shared dispatch and we’re done! + // Otherwise, copy-on-write. + if (on !== on0 || listener0 !== listener) (on1 = (on0 = on).copy()).on(event, listener0 = listener); + + schedule.on = on1; + }; +} + +export default function(name, value, priority) { + var i = (name += "") === "transform" ? interpolateTransform : interpolate; + return value == null ? this + .styleTween(name, styleNull(name, i)) + .on("end.style." + name, styleRemove(name)) + : typeof value === "function" ? this + .styleTween(name, styleFunction(name, i, tweenValue(this, "style." + name, value))) + .each(styleMaybeRemove(this._id, name)) + : this + .styleTween(name, styleConstant(name, i, value), priority) + .on("end.style." + name, null); +} diff --git a/frontend/node_modules/d3-transition/src/transition/styleTween.js b/frontend/node_modules/d3-transition/src/transition/styleTween.js new file mode 100644 index 0000000..f692483 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/styleTween.js @@ -0,0 +1,24 @@ +function styleInterpolate(name, i, priority) { + return function(t) { + this.style.setProperty(name, i.call(this, t), priority); + }; +} + +function styleTween(name, value, priority) { + var t, i0; + function tween() { + var i = value.apply(this, arguments); + if (i !== i0) t = (i0 = i) && styleInterpolate(name, i, priority); + return t; + } + tween._value = value; + return tween; +} + +export default function(name, value, priority) { + var key = "style." + (name += ""); + if (arguments.length < 2) return (key = this.tween(key)) && key._value; + if (value == null) return this.tween(key, null); + if (typeof value !== "function") throw new Error; + return this.tween(key, styleTween(name, value, priority == null ? "" : priority)); +} diff --git a/frontend/node_modules/d3-transition/src/transition/text.js b/frontend/node_modules/d3-transition/src/transition/text.js new file mode 100644 index 0000000..a7f75d9 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/text.js @@ -0,0 +1,20 @@ +import {tweenValue} from "./tween.js"; + +function textConstant(value) { + return function() { + this.textContent = value; + }; +} + +function textFunction(value) { + return function() { + var value1 = value(this); + this.textContent = value1 == null ? "" : value1; + }; +} + +export default function(value) { + return this.tween("text", typeof value === "function" + ? textFunction(tweenValue(this, "text", value)) + : textConstant(value == null ? "" : value + "")); +} diff --git a/frontend/node_modules/d3-transition/src/transition/textTween.js b/frontend/node_modules/d3-transition/src/transition/textTween.js new file mode 100644 index 0000000..16d1bf1 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/textTween.js @@ -0,0 +1,24 @@ +function textInterpolate(i) { + return function(t) { + this.textContent = i.call(this, t); + }; +} + +function textTween(value) { + var t0, i0; + function tween() { + var i = value.apply(this, arguments); + if (i !== i0) t0 = (i0 = i) && textInterpolate(i); + return t0; + } + tween._value = value; + return tween; +} + +export default function(value) { + var key = "text"; + if (arguments.length < 1) return (key = this.tween(key)) && key._value; + if (value == null) return this.tween(key, null); + if (typeof value !== "function") throw new Error; + return this.tween(key, textTween(value)); +} diff --git a/frontend/node_modules/d3-transition/src/transition/transition.js b/frontend/node_modules/d3-transition/src/transition/transition.js new file mode 100644 index 0000000..6a6dd24 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/transition.js @@ -0,0 +1,24 @@ +import {Transition, newId} from "./index.js"; +import schedule, {get} from "./schedule.js"; + +export default function() { + var name = this._name, + id0 = this._id, + id1 = newId(); + + for (var groups = this._groups, m = groups.length, j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) { + if (node = group[i]) { + var inherit = get(node, id0); + schedule(node, name, id1, i, group, { + time: inherit.time + inherit.delay + inherit.duration, + delay: 0, + duration: inherit.duration, + ease: inherit.ease + }); + } + } + } + + return new Transition(groups, this._parents, name, id1); +} diff --git a/frontend/node_modules/d3-transition/src/transition/tween.js b/frontend/node_modules/d3-transition/src/transition/tween.js new file mode 100644 index 0000000..ba96781 --- /dev/null +++ b/frontend/node_modules/d3-transition/src/transition/tween.js @@ -0,0 +1,81 @@ +import {get, set} from "./schedule.js"; + +function tweenRemove(id, name) { + var tween0, tween1; + return function() { + var schedule = set(this, id), + tween = schedule.tween; + + // If this node shared tween with the previous node, + // just assign the updated shared tween and we’re done! + // Otherwise, copy-on-write. + if (tween !== tween0) { + tween1 = tween0 = tween; + for (var i = 0, n = tween1.length; i < n; ++i) { + if (tween1[i].name === name) { + tween1 = tween1.slice(); + tween1.splice(i, 1); + break; + } + } + } + + schedule.tween = tween1; + }; +} + +function tweenFunction(id, name, value) { + var tween0, tween1; + if (typeof value !== "function") throw new Error; + return function() { + var schedule = set(this, id), + tween = schedule.tween; + + // If this node shared tween with the previous node, + // just assign the updated shared tween and we’re done! + // Otherwise, copy-on-write. + if (tween !== tween0) { + tween1 = (tween0 = tween).slice(); + for (var t = {name: name, value: value}, i = 0, n = tween1.length; i < n; ++i) { + if (tween1[i].name === name) { + tween1[i] = t; + break; + } + } + if (i === n) tween1.push(t); + } + + schedule.tween = tween1; + }; +} + +export default function(name, value) { + var id = this._id; + + name += ""; + + if (arguments.length < 2) { + var tween = get(this.node(), id).tween; + for (var i = 0, n = tween.length, t; i < n; ++i) { + if ((t = tween[i]).name === name) { + return t.value; + } + } + return null; + } + + return this.each((value == null ? tweenRemove : tweenFunction)(id, name, value)); +} + +export function tweenValue(transition, name, value) { + var id = transition._id; + + transition.each(function() { + var schedule = set(this, id); + (schedule.value || (schedule.value = {}))[name] = value.apply(this, arguments); + }); + + return function(node) { + return get(node, id).value[name]; + }; +} diff --git a/frontend/node_modules/d3-zoom/LICENSE b/frontend/node_modules/d3-zoom/LICENSE new file mode 100644 index 0000000..b014515 --- /dev/null +++ b/frontend/node_modules/d3-zoom/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2021 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3-zoom/README.md b/frontend/node_modules/d3-zoom/README.md new file mode 100644 index 0000000..adcb856 --- /dev/null +++ b/frontend/node_modules/d3-zoom/README.md @@ -0,0 +1,414 @@ +# d3-zoom + +Panning and zooming are popular interaction techniques which let the user focus on a region of interest by restricting the view. It is easy to learn due to direct manipulation: click-and-drag to pan (translate), spin the wheel to zoom (scale), or use touch. Panning and zooming are widely used in web-based mapping, but can also be used with visualizations such as time-series and scatterplots. + +The zoom behavior implemented by d3-zoom is a convenient but flexible abstraction for enabling pan-and-zoom on [selections](https://github.com/d3/d3-selection). It handles a surprising variety of [input events](#api-reference) and browser quirks. The zoom behavior is agnostic about the DOM, so you can use it with SVG, HTML or Canvas. + +[Canvas Zooming](https://observablehq.com/@d3/zoom-canvas)[SVG Zooming](https://observablehq.com/@d3/zoom) + +The zoom behavior is also designed to work with [d3-scale](https://github.com/d3/d3-scale) and [d3-axis](https://github.com/d3/d3-axis); see [*transform*.rescaleX](#transform_rescaleX) and [*transform*.rescaleY](#transform_rescaleY). You can also restrict zooming using [*zoom*.scaleExtent](#zoom_scaleExtent) and panning using [*zoom*.translateExtent](#zoom_translateExtent). + +[Axis Zooming](https://observablehq.com/@d3/zoomable-scatterplot) + +The zoom behavior can be combined with other behaviors, such as [d3-drag](https://github.com/d3/d3-drag) for dragging, and [d3-brush](https://github.com/d3/d3-brush) for focus + context. + +[Drag & Zoom II](https://observablehq.com/@d3/drag-zoom)[Brush & Zoom](https://observablehq.com/@d3/focus-context) + +The zoom behavior can be controlled programmatically using [*zoom*.transform](#zoom_transform), allowing you to implement user interface controls which drive the display or to stage animated tours through your data. Smooth zoom transitions are based on [“Smooth and efficient zooming and panning”](http://www.win.tue.nl/~vanwijk/zoompan.pdf) by Jarke J. van Wijk and Wim A.A. Nuij. + +[Zoom Transitions](https://observablehq.com/@d3/programmatic-zoom) + +See also [d3-tile](https://github.com/d3/d3-tile) for examples panning and zooming maps. + +## Installing + +If you use npm, `npm install d3-zoom`. You can also download the [latest release on GitHub](https://github.com/d3/d3-zoom/releases/latest). For vanilla HTML in modern browsers, import d3-zoom from Skypack: + +```html + +``` + +For legacy environments, you can load d3-zoom’s UMD bundle from an npm-based CDN such as jsDelivr; a `d3` global is exported: + +```html + + + + + + + + + + +``` + +[Try d3-zoom in your browser.](https://observablehq.com/collection/@d3/d3-zoom) + +## API Reference + +This table describes how the zoom behavior interprets native events: + +| Event | Listening Element | Zoom Event | Default Prevented? | +| ------------ | ----------------- | ----------- | ------------------ | +| mousedown⁵ | selection | start | no¹ | +| mousemove² | window¹ | zoom | yes | +| mouseup² | window¹ | end | yes | +| dragstart² | window | - | yes | +| selectstart² | window | - | yes | +| click³ | window | - | yes | +| dblclick | selection | *multiple*⁶ | yes | +| wheel⁸ | selection | zoom⁷ | yes | +| touchstart | selection | *multiple*⁶ | no⁴ | +| touchmove | selection | zoom | yes | +| touchend | selection | end | no⁴ | +| touchcancel | selection | end | no⁴ | + +The propagation of all consumed events is [immediately stopped](https://dom.spec.whatwg.org/#dom-event-stopimmediatepropagation). + +¹ Necessary to capture events outside an iframe; see [d3-drag#9](https://github.com/d3/d3-drag/issues/9). +
    ² Only applies during an active, mouse-based gesture; see [d3-drag#9](https://github.com/d3/d3-drag/issues/9). +
    ³ Only applies immediately after some mouse-based gestures; see [*zoom*.clickDistance](#zoom_clickDistance). +
    ⁴ Necessary to allow [click emulation](https://developer.apple.com/library/ios/documentation/AppleApplications/Reference/SafariWebContent/HandlingEvents/HandlingEvents.html#//apple_ref/doc/uid/TP40006511-SW7) on touch input; see [d3-drag#9](https://github.com/d3/d3-drag/issues/9). +
    ⁵ Ignored if within 500ms of a touch gesture ending; assumes [click emulation](https://developer.apple.com/library/ios/documentation/AppleApplications/Reference/SafariWebContent/HandlingEvents/HandlingEvents.html#//apple_ref/doc/uid/TP40006511-SW7). +
    ⁶ Double-click and double-tap initiate a transition that emits start, zoom and end events; see [*zoom*.tapDistance](#zoom_tapDistance).. +
    ⁷ The first wheel event emits a start event; an end event is emitted when no wheel events are received for 150ms. +
    ⁸ Ignored if already at the corresponding limit of the [scale extent](#zoom_scaleExtent). + +# d3.zoom() · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js), [Examples](https://observablehq.com/collection/@d3/d3-zoom) + +Creates a new zoom behavior. The returned behavior, [*zoom*](#_drag), is both an object and a function, and is typically applied to selected elements via [*selection*.call](https://github.com/d3/d3-selection#selection_call). + +# zoom(selection) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js), [Examples](https://observablehq.com/collection/@d3/d3-zoom) + +Applies this zoom behavior to the specified [*selection*](https://github.com/d3/d3-selection), binding the necessary event listeners to allow panning and zooming, and initializing the [zoom transform](#zoom-transforms) on each selected element to the identity transform if not already defined. This function is typically not invoked directly, and is instead invoked via [*selection*.call](https://github.com/d3/d3-selection#selection_call). For example, to instantiate a zoom behavior and apply it to a selection: + +```js +selection.call(d3.zoom().on("zoom", zoomed)); +``` + +Internally, the zoom behavior uses [*selection*.on](https://github.com/d3/d3-selection#selection_on) to bind the necessary event listeners for zooming. The listeners use the name `.zoom`, so you can subsequently unbind the zoom behavior as follows: + +```js +selection.on(".zoom", null); +``` + +To disable just wheel-driven zooming (say to not interfere with native scrolling), you can remove the zoom behavior’s wheel event listener after applying the zoom behavior to the selection: + +```js +selection + .call(zoom) + .on("wheel.zoom", null); +``` + +Alternatively, use [*zoom*.filter](#zoom_filter) for greater control over which events can initiate zoom gestures. + +Applying the zoom behavior also sets the [-webkit-tap-highlight-color](https://developer.apple.com/library/mac/documentation/AppleApplications/Reference/SafariWebContent/AdjustingtheTextSize/AdjustingtheTextSize.html#//apple_ref/doc/uid/TP40006510-SW5) style to transparent, disabling the tap highlight on iOS. If you want a different tap highlight color, remove or re-apply this style after applying the drag behavior. + +# zoom.transform(selection, transform[, point]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js), [Examples](https://observablehq.com/collection/@d3/d3-zoom) + +If *selection* is a selection, sets the [current zoom transform](#zoomTransform) of the selected elements to the specified *transform*, instantaneously emitting start, zoom and end [events](#zoom-events). If *selection* is a transition, defines a “zoom” tween to the specified *transform* using [d3.interpolateZoom](https://github.com/d3/d3-interpolate/blob/master/README.md#interpolateZoom), emitting a start event when the transition starts, zoom events for each tick of the transition, and then an end event when the transition ends (or is interrupted). The transition will attempt to minimize the visual movement around the specified *point*; if the *point* is not specified, it defaults to the center of the viewport [extent](#zoom_extent). The *transform* may be specified either as a [zoom transform](#zoom-transforms) or as a function that returns a zoom transform; similarly, the *point* may be specified either as a two-element array [*x*, *y*] or a function that returns such an array. If a function, it is invoked for each selected element, being passed the current event (`event`) and datum `d`, with the `this` context as the current DOM element. + +This function is typically not invoked directly, and is instead invoked via [*selection*.call](https://github.com/d3/d3-selection#selection_call) or [*transition*.call](https://github.com/d3/d3-transition#transition_call). For example, to reset the zoom transform to the [identity transform](#zoomIdentity) instantaneously: + +```js +selection.call(zoom.transform, d3.zoomIdentity); +``` + +To smoothly reset the zoom transform to the identity transform over 750 milliseconds: + +```js +selection.transition().duration(750).call(zoom.transform, d3.zoomIdentity); +``` + +This method requires that you specify the new zoom transform completely, and does not enforce the defined [scale extent](#zoom_scaleExtent) and [translate extent](#zoom_translateExtent), if any. To derive a new transform from the existing transform, and to enforce the scale and translate extents, see the convenience methods [*zoom*.translateBy](#zoom_translateBy), [*zoom*.scaleBy](#zoom_scaleBy) and [*zoom*.scaleTo](#zoom_scaleTo). + +# zoom.translateBy(selection, x, y) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *selection* is a selection, [translates](#transform_translate) the [current zoom transform](#zoomTransform) of the selected elements by *x* and *y*, such that the new *tx1* = *tx0* + *kx* and *ty1* = *ty0* + *ky*. If *selection* is a transition, defines a “zoom” tween translating the current transform. This method is a convenience method for [*zoom*.transform](#zoom_transform). The *x* and *y* translation amounts may be specified either as numbers or as functions that return numbers. If a function, it is invoked for each selected element, being passed the current datum `d` and index `i`, with the `this` context as the current DOM element. + +# zoom.translateTo(selection, x, y[, p]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *selection* is a selection, [translates](#transform_translate) the [current zoom transform](#zoomTransform) of the selected elements such that the given position ⟨*x*,*y*⟩ appears at given point *p*. The new *tx* = *px* - *kx* and *ty* = *py* - *ky*. If *p* is not specified, it defaults to the center of the viewport [extent](#zoom_extent). If *selection* is a transition, defines a “zoom” tween translating the current transform. This method is a convenience method for [*zoom*.transform](#zoom_transform). The *x* and *y* coordinates may be specified either as numbers or as functions that returns numbers; similarly the *p* point may be specified either as a two-element array [*px*,*py*] or a function. If a function, it is invoked for each selected element, being passed the current datum `d` and index `i`, with the `this` context as the current DOM element. + +# zoom.scaleBy(selection, k[, p]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *selection* is a selection, [scales](#transform_scale) the [current zoom transform](#zoomTransform) of the selected elements by *k*, such that the new *k₁* = *k₀k*. The reference point *p* does move. If *p* is not specified, it defaults to the center of the viewport [extent](#zoom_extent). If *selection* is a transition, defines a “zoom” tween translating the current transform. This method is a convenience method for [*zoom*.transform](#zoom_transform). The *k* scale factor may be specified either as a number or a function that returns a number; similarly the *p* point may be specified either as a two-element array [*px*,*py*] or a function. If a function, it is invoked for each selected element, being passed the current datum `d` and index `i`, with the `this` context as the current DOM element. + +# zoom.scaleTo(selection, k[, p]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *selection* is a selection, [scales](#transform_scale) the [current zoom transform](#zoomTransform) of the selected elements to *k*, such that the new *k₁* = *k*. The reference point *p* does move. If *p* is not specified, it defaults to the center of the viewport [extent](#zoom_extent). If *selection* is a transition, defines a “zoom” tween translating the current transform. This method is a convenience method for [*zoom*.transform](#zoom_transform). The *k* scale factor may be specified either as a number or a function that returns a number; similarly the *p* point may be specified either as a two-element array [*px*,*py*] or a function. If a function, it is invoked for each selected element, being passed the current datum `d` and index `i`, with the `this` context as the current DOM element. + +# zoom.constrain([constrain]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *constrain* is specified, sets the transform constraint function to the specified function and returns the zoom behavior. If *constrain* is not specified, returns the current constraint function, which defaults to: + +```js +function constrain(transform, extent, translateExtent) { + var dx0 = transform.invertX(extent[0][0]) - translateExtent[0][0], + dx1 = transform.invertX(extent[1][0]) - translateExtent[1][0], + dy0 = transform.invertY(extent[0][1]) - translateExtent[0][1], + dy1 = transform.invertY(extent[1][1]) - translateExtent[1][1]; + return transform.translate( + dx1 > dx0 ? (dx0 + dx1) / 2 : Math.min(0, dx0) || Math.max(0, dx1), + dy1 > dy0 ? (dy0 + dy1) / 2 : Math.min(0, dy0) || Math.max(0, dy1) + ); +} +``` + +The constraint function must return a [*transform*](#zoom-transforms) given the current *transform*, [viewport extent](#zoom_extent) and [translate extent](#zoom_translateExtent). The default implementation attempts to ensure that the viewport extent does not go outside the translate extent. + +# zoom.filter([filter]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *filter* is specified, sets the filter to the specified function and returns the zoom behavior. If *filter* is not specified, returns the current filter, which defaults to: + +```js +function filter(event) { + return (!event.ctrlKey || event.type === 'wheel') && !event.button; +} +``` + +The filter is passed the current event (`event`) and datum `d`, with the `this` context as the current DOM element. If the filter returns falsey, the initiating event is ignored and no zoom gestures are started. Thus, the filter determines which input events are ignored. The default filter ignores mousedown events on secondary buttons, since those buttons are typically intended for other purposes, such as the context menu. + +# zoom.touchable([touchable]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *touchable* is specified, sets the touch support detector to the specified function and returns the zoom behavior. If *touchable* is not specified, returns the current touch support detector, which defaults to: + +```js +function touchable() { + return navigator.maxTouchPoints || ("ontouchstart" in this); +} +``` + +Touch event listeners are only registered if the detector returns truthy for the corresponding element when the zoom behavior is [applied](#_zoom). The default detector works well for most browsers that are capable of touch input, but not all; Chrome’s mobile device emulator, for example, fails detection. + +# zoom.wheelDelta([delta]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *delta* is specified, sets the wheel delta function to the specified function and returns the zoom behavior. If *delta* is not specified, returns the current wheel delta function, which defaults to: + +```js +function wheelDelta(event) { + return -event.deltaY * (event.deltaMode === 1 ? 0.05 : event.deltaMode ? 1 : 0.002); +} +``` + +The value *Δ* returned by the wheel delta function determines the amount of scaling applied in response to a [WheelEvent](https://developer.mozilla.org/en-US/docs/Web/API/WheelEvent). The scale factor [*transform*.k](#zoomTransform) is multiplied by 2*Δ*; for example, a *Δ* of +1 doubles the scale factor, *Δ* of -1 halves the scale factor. + +# zoom.extent([extent]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *extent* is specified, sets the viewport extent to the specified array of points [[*x0*, *y0*], [*x1*, *y1*]], where [*x0*, *y0*] is the top-left corner of the viewport and [*x1*, *y1*] is the bottom-right corner of the viewport, and returns this zoom behavior. The *extent* may also be specified as a function which returns such an array; if a function, it is invoked for each selected element, being passed the current datum `d`, with the `this` context as the current DOM element. + +If *extent* is not specified, returns the current extent accessor, which defaults to [[0, 0], [*width*, *height*]] where *width* is the [client width](https://developer.mozilla.org/en-US/docs/Web/API/Element/clientWidth) of the element and *height* is its [client height](https://developer.mozilla.org/en-US/docs/Web/API/Element/clientHeight); for SVG elements, the nearest ancestor SVG element’s viewBox, or [width](https://www.w3.org/TR/SVG/struct.html#SVGElementWidthAttribute) and [height](https://www.w3.org/TR/SVG/struct.html#SVGElementHeightAttribute) attributes, are used. Alternatively, consider using [*element*.getBoundingClientRect](https://developer.mozilla.org/en-US/docs/Web/API/Element/getBoundingClientRect). + +The viewport extent affects several functions: the center of the viewport remains fixed during changes by [*zoom*.scaleBy](#zoom_scaleBy) and [*zoom*.scaleTo](#zoom_scaleTo); the viewport center and dimensions affect the path chosen by [d3.interpolateZoom](https://github.com/d3/d3-interpolate#interpolateZoom); and the viewport extent is needed to enforce the optional [translate extent](#zoom_translateExtent). + +# zoom.scaleExtent([extent]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *extent* is specified, sets the scale extent to the specified array of numbers [*k0*, *k1*] where *k0* is the minimum allowed scale factor and *k1* is the maximum allowed scale factor, and returns this zoom behavior. If *extent* is not specified, returns the current scale extent, which defaults to [0, ∞]. The scale extent restricts zooming in and out. It is enforced on interaction and when using [*zoom*.scaleBy](#zoom_scaleBy), [*zoom*.scaleTo](#zoom_scaleTo) and [*zoom*.translateBy](#zoom_translateBy); however, it is not enforced when using [*zoom*.transform](#zoom_transform) to set the transform explicitly. + +If the user tries to zoom by wheeling when already at the corresponding limit of the scale extent, the wheel events will be ignored and not initiate a zoom gesture. This allows the user to scroll down past a zoomable area after zooming in, or to scroll up after zooming out. If you would prefer to always prevent scrolling on wheel input regardless of the scale extent, register a wheel event listener to prevent the browser default behavior: + +```js +selection + .call(zoom) + .on("wheel", event => event.preventDefault()); +``` + +# zoom.translateExtent([extent]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *extent* is specified, sets the translate extent to the specified array of points [[*x0*, *y0*], [*x1*, *y1*]], where [*x0*, *y0*] is the top-left corner of the world and [*x1*, *y1*] is the bottom-right corner of the world, and returns this zoom behavior. If *extent* is not specified, returns the current translate extent, which defaults to [[-∞, -∞], [+∞, +∞]]. The translate extent restricts panning, and may cause translation on zoom out. It is enforced on interaction and when using [*zoom*.scaleBy](#zoom_scaleBy), [*zoom*.scaleTo](#zoom_scaleTo) and [*zoom*.translateBy](#zoom_translateBy); however, it is not enforced when using [*zoom*.transform](#zoom_transform) to set the transform explicitly. + +# zoom.clickDistance([distance]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *distance* is specified, sets the maximum distance that the mouse can move between mousedown and mouseup that will trigger a subsequent click event. If at any point between mousedown and mouseup the mouse is greater than or equal to *distance* from its position on mousedown, the click event following mouseup will be suppressed. If *distance* is not specified, returns the current distance threshold, which defaults to zero. The distance threshold is measured in client coordinates ([*event*.clientX](https://developer.mozilla.org/en-US/docs/Web/API/MouseEvent/clientX) and [*event*.clientY](https://developer.mozilla.org/en-US/docs/Web/API/MouseEvent/clientY)). + +# zoom.tapDistance([distance]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *distance* is specified, sets the maximum distance that a double-tap gesture can move between first touchstart and second touchend that will trigger a subsequent double-click event. If *distance* is not specified, returns the current distance threshold, which defaults to 10. The distance threshold is measured in client coordinates ([*event*.clientX](https://developer.mozilla.org/en-US/docs/Web/API/MouseEvent/clientX) and [*event*.clientY](https://developer.mozilla.org/en-US/docs/Web/API/MouseEvent/clientY)). + +# zoom.duration([duration]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *duration* is specified, sets the duration for zoom transitions on double-click and double-tap to the specified number of milliseconds and returns the zoom behavior. If *duration* is not specified, returns the current duration, which defaults to 250 milliseconds. If the duration is not greater than zero, double-click and -tap trigger instantaneous changes to the zoom transform rather than initiating smooth transitions. + +To disable double-click and double-tap transitions, you can remove the zoom behavior’s dblclick event listener after applying the zoom behavior to the selection: + +```js +selection + .call(zoom) + .on("dblclick.zoom", null); +``` + +# zoom.interpolate([interpolate]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *interpolate* is specified, sets the interpolation factory for zoom transitions to the specified function. If *interpolate* is not specified, returns the current interpolation factory, which defaults to [d3.interpolateZoom](https://github.com/d3/d3-interpolate#interpolateZoom) to implement smooth zooming. To apply direct interpolation between two views, try [d3.interpolate](https://github.com/d3/d3-interpolate#interpolate) instead. + +# zoom.on(typenames[, listener]) · [Source](https://github.com/d3/d3-zoom/blob/master/src/zoom.js) + +If *listener* is specified, sets the event *listener* for the specified *typenames* and returns the zoom behavior. If an event listener was already registered for the same type and name, the existing listener is removed before the new listener is added. If *listener* is null, removes the current event listeners for the specified *typenames*, if any. If *listener* is not specified, returns the first currently-assigned listener matching the specified *typenames*, if any. When a specified event is dispatched, each *listener* will be invoked with the same context and arguments as [*selection*.on](https://github.com/d3/d3-selection#selection_on) listeners: the current event (`event`) and datum `d`, with the `this` context as the current DOM element. + +The *typenames* is a string containing one or more *typename* separated by whitespace. Each *typename* is a *type*, optionally followed by a period (`.`) and a *name*, such as `zoom.foo` and `zoom.bar`; the name allows multiple listeners to be registered for the same *type*. The *type* must be one of the following: + +* `start` - after zooming begins (such as on mousedown). +* `zoom` - after a change to the zoom transform (such as on mousemove). +* `end` - after zooming ends (such as on mouseup ). + +See [*dispatch*.on](https://github.com/d3/d3-dispatch#dispatch_on) for more. + +### Zoom Events + +When a [zoom event listener](#zoom_on) is invoked, it receives the current zoom event as a first argument. The *event* object exposes several fields: + +* *event*.target - the associated [zoom behavior](#zoom). +* *event*.type - the string “start”, “zoom” or “end”; see [*zoom*.on](#zoom_on). +* *event*.transform - the current [zoom transform](#zoom-transforms). +* *event*.sourceEvent - the underlying input event, such as mousemove or touchmove. + +### Zoom Transforms + +The zoom behavior stores the zoom state on the element to which the zoom behavior was [applied](#_zoom), not on the zoom behavior itself. This is because the zoom behavior can be applied to many elements simultaneously, and each element can be zoomed independently. The zoom state can change either on user interaction or programmatically via [*zoom*.transform](#zoom_transform). + +To retrieve the zoom state, use *event*.transform on the current [zoom event](#zoom-events) within a zoom event listener (see [*zoom*.on](#zoom_on)), or use [d3.zoomTransform](#zoomTransform) for a given node. The latter is particularly useful for modifying the zoom state programmatically, say to implement buttons for zooming in and out. + +# d3.zoomTransform(node) · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +Returns the current transform for the specified *node*. Note that *node* should typically be a DOM element, not a *selection*. (A selection may consist of multiple nodes, in different states, and this function only returns a single transform.) If you have a selection, call [*selection*.node](https://github.com/d3/d3-selection#selection_node) first: + +```js +var transform = d3.zoomTransform(selection.node()); +``` + +In the context of an [event listener](https://github.com/d3/d3-selection#selection_on), the *node* is typically the element that received the input event (which should be equal to [*event*.transform](#zoom-events)), *this*: + +```js +var transform = d3.zoomTransform(this); +``` + +Internally, an element’s transform is stored as *element*.\_\_zoom; however, you should use this method rather than accessing it directly. If the given *node* has no defined transform, returns the transform of the closest ancestor, or if none exists, the [identity transformation](#zoomIdentity). The returned transform represents a two-dimensional [transformation matrix](https://en.wikipedia.org/wiki/Transformation_matrix#Affine_transformations) of the form: + +*k* 0 *tx* +
    0 *k* *ty* +
    0 0 1 + +(This matrix is capable of representing only scale and translation; a future release may also allow rotation, though this would probably not be a backwards-compatible change.) The position ⟨*x*,*y*⟩ is transformed to ⟨*xk* + *tx*,*yk* + *ty*⟩. The transform object exposes the following properties: + +* *transform*.x - the translation amount *tx* along the *x*-axis. +* *transform*.y - the translation amount *ty* along the *y*-axis. +* *transform*.k - the scale factor *k*. + +These properties should be considered read-only; instead of mutating a transform, use [*transform*.scale](#transform_scale) and [*transform*.translate](#transform_translate) to derive a new transform. Also see [*zoom*.scaleBy](#zoom_scaleBy), [*zoom*.scaleTo](#zoom_scaleTo) and [*zoom*.translateBy](#zoom_translateBy) for convenience methods on the zoom behavior. To create a transform with a given *k*, *tx*, and *ty*: + +```js +var t = d3.zoomIdentity.translate(x, y).scale(k); +``` + +To apply the transformation to a [Canvas 2D context](https://www.w3.org/TR/2dcontext/), use [*context*.translate](https://www.w3.org/TR/2dcontext/#dom-context-2d-translate) followed by [*context*.scale](https://www.w3.org/TR/2dcontext/#dom-context-2d-scale): + +```js +context.translate(transform.x, transform.y); +context.scale(transform.k, transform.k); +``` + +Similarly, to apply the transformation to HTML elements via [CSS](https://www.w3.org/TR/css-transforms-1/): + +```js +div.style("transform", "translate(" + transform.x + "px," + transform.y + "px) scale(" + transform.k + ")"); +div.style("transform-origin", "0 0"); +``` + +To apply the transformation to [SVG](https://www.w3.org/TR/SVG/coords.html#TransformAttribute): + +```js +g.attr("transform", "translate(" + transform.x + "," + transform.y + ") scale(" + transform.k + ")"); +``` + +Or more simply, taking advantage of [*transform*.toString](#transform_toString): + +```js +g.attr("transform", transform); +``` + +Note that the order of transformations matters! The translate must be applied before the scale. + +# transform.scale(k) · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +Returns a transform whose scale *k₁* is equal to *k₀k*, where *k₀* is this transform’s scale. + +# transform.translate(x, y) · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +Returns a transform whose translation *tx1* and *ty1* is equal to *tx0* + *tk x* and *ty0* + *tk y*, where *tx0* and *ty0* is this transform’s translation and *tk* is this transform’s scale. + +# transform.apply(point) · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +Returns the transformation of the specified *point* which is a two-element array of numbers [*x*, *y*]. The returned point is equal to [*xk* + *tx*, *yk* + *ty*]. + +# transform.applyX(x) · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +Returns the transformation of the specified *x*-coordinate, *xk* + *tx*. + +# transform.applyY(y) · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +Returns the transformation of the specified *y*-coordinate, *yk* + *ty*. + +# transform.invert(point) · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +Returns the inverse transformation of the specified *point* which is a two-element array of numbers [*x*, *y*]. The returned point is equal to [(*x* - *tx*) / *k*, (*y* - *ty*) / *k*]. + +# transform.invertX(x) · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +Returns the inverse transformation of the specified *x*-coordinate, (*x* - *tx*) / *k*. + +# transform.invertY(y) · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +Returns the inverse transformation of the specified *y*-coordinate, (*y* - *ty*) / *k*. + +# transform.rescaleX(x) · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +Returns a [copy](https://github.com/d3/d3-scale#continuous_copy) of the [continuous scale](https://github.com/d3/d3-scale#continuous-scales) *x* whose [domain](https://github.com/d3/d3-scale#continuous_domain) is transformed. This is implemented by first applying the [inverse *x*-transform](#transform_invertX) on the scale’s [range](https://github.com/d3/d3-scale#continuous_range), and then applying the [inverse scale](https://github.com/d3/d3-scale#continuous_invert) to compute the corresponding domain: + +```js +function rescaleX(x) { + var range = x.range().map(transform.invertX, transform), + domain = range.map(x.invert, x); + return x.copy().domain(domain); +} +``` + +The scale *x* must use [d3.interpolateNumber](https://github.com/d3/d3-interpolate#interpolateNumber); do not use [*continuous*.rangeRound](https://github.com/d3/d3-scale#continuous_rangeRound) as this reduces the accuracy of [*continuous*.invert](https://github.com/d3/d3-scale#continuous_invert) and can lead to an inaccurate rescaled domain. This method does not modify the input scale *x*; *x* thus represents the untransformed scale, while the returned scale represents its transformed view. + +# transform.rescaleY(y) · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +Returns a [copy](https://github.com/d3/d3-scale#continuous_copy) of the [continuous scale](https://github.com/d3/d3-scale#continuous-scales) *y* whose [domain](https://github.com/d3/d3-scale#continuous_domain) is transformed. This is implemented by first applying the [inverse *y*-transform](#transform_invertY) on the scale’s [range](https://github.com/d3/d3-scale#continuous_range), and then applying the [inverse scale](https://github.com/d3/d3-scale#continuous_invert) to compute the corresponding domain: + +```js +function rescaleY(y) { + var range = y.range().map(transform.invertY, transform), + domain = range.map(y.invert, y); + return y.copy().domain(domain); +} +``` + +The scale *y* must use [d3.interpolateNumber](https://github.com/d3/d3-interpolate#interpolateNumber); do not use [*continuous*.rangeRound](https://github.com/d3/d3-scale#continuous_rangeRound) as this reduces the accuracy of [*continuous*.invert](https://github.com/d3/d3-scale#continuous_invert) and can lead to an inaccurate rescaled domain. This method does not modify the input scale *y*; *y* thus represents the untransformed scale, while the returned scale represents its transformed view. + +# transform.toString() · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +Returns a string representing the [SVG transform](https://www.w3.org/TR/SVG/coords.html#TransformAttribute) corresponding to this transform. Implemented as: + +```js +function toString() { + return "translate(" + this.x + "," + this.y + ") scale(" + this.k + ")"; +} +``` + +# d3.zoomIdentity · [Source](https://github.com/d3/d3-zoom/blob/master/src/transform.js) + +The identity transform, where *k* = 1, *tx* = *ty* = 0. diff --git a/frontend/node_modules/d3-zoom/dist/d3-zoom.js b/frontend/node_modules/d3-zoom/dist/d3-zoom.js new file mode 100644 index 0000000..ddf02ae --- /dev/null +++ b/frontend/node_modules/d3-zoom/dist/d3-zoom.js @@ -0,0 +1,531 @@ +// https://d3js.org/d3-zoom/ v3.0.0 Copyright 2010-2021 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-dispatch'), require('d3-drag'), require('d3-interpolate'), require('d3-selection'), require('d3-transition')) : +typeof define === 'function' && define.amd ? define(['exports', 'd3-dispatch', 'd3-drag', 'd3-interpolate', 'd3-selection', 'd3-transition'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {}, global.d3, global.d3, global.d3, global.d3, global.d3)); +}(this, (function (exports, d3Dispatch, d3Drag, d3Interpolate, d3Selection, d3Transition) { 'use strict'; + +var constant = x => () => x; + +function ZoomEvent(type, { + sourceEvent, + target, + transform, + dispatch +}) { + Object.defineProperties(this, { + type: {value: type, enumerable: true, configurable: true}, + sourceEvent: {value: sourceEvent, enumerable: true, configurable: true}, + target: {value: target, enumerable: true, configurable: true}, + transform: {value: transform, enumerable: true, configurable: true}, + _: {value: dispatch} + }); +} + +function Transform(k, x, y) { + this.k = k; + this.x = x; + this.y = y; +} + +Transform.prototype = { + constructor: Transform, + scale: function(k) { + return k === 1 ? this : new Transform(this.k * k, this.x, this.y); + }, + translate: function(x, y) { + return x === 0 & y === 0 ? this : new Transform(this.k, this.x + this.k * x, this.y + this.k * y); + }, + apply: function(point) { + return [point[0] * this.k + this.x, point[1] * this.k + this.y]; + }, + applyX: function(x) { + return x * this.k + this.x; + }, + applyY: function(y) { + return y * this.k + this.y; + }, + invert: function(location) { + return [(location[0] - this.x) / this.k, (location[1] - this.y) / this.k]; + }, + invertX: function(x) { + return (x - this.x) / this.k; + }, + invertY: function(y) { + return (y - this.y) / this.k; + }, + rescaleX: function(x) { + return x.copy().domain(x.range().map(this.invertX, this).map(x.invert, x)); + }, + rescaleY: function(y) { + return y.copy().domain(y.range().map(this.invertY, this).map(y.invert, y)); + }, + toString: function() { + return "translate(" + this.x + "," + this.y + ") scale(" + this.k + ")"; + } +}; + +var identity = new Transform(1, 0, 0); + +transform.prototype = Transform.prototype; + +function transform(node) { + while (!node.__zoom) if (!(node = node.parentNode)) return identity; + return node.__zoom; +} + +function nopropagation(event) { + event.stopImmediatePropagation(); +} + +function noevent(event) { + event.preventDefault(); + event.stopImmediatePropagation(); +} + +// Ignore right-click, since that should open the context menu. +// except for pinch-to-zoom, which is sent as a wheel+ctrlKey event +function defaultFilter(event) { + return (!event.ctrlKey || event.type === 'wheel') && !event.button; +} + +function defaultExtent() { + var e = this; + if (e instanceof SVGElement) { + e = e.ownerSVGElement || e; + if (e.hasAttribute("viewBox")) { + e = e.viewBox.baseVal; + return [[e.x, e.y], [e.x + e.width, e.y + e.height]]; + } + return [[0, 0], [e.width.baseVal.value, e.height.baseVal.value]]; + } + return [[0, 0], [e.clientWidth, e.clientHeight]]; +} + +function defaultTransform() { + return this.__zoom || identity; +} + +function defaultWheelDelta(event) { + return -event.deltaY * (event.deltaMode === 1 ? 0.05 : event.deltaMode ? 1 : 0.002) * (event.ctrlKey ? 10 : 1); +} + +function defaultTouchable() { + return navigator.maxTouchPoints || ("ontouchstart" in this); +} + +function defaultConstrain(transform, extent, translateExtent) { + var dx0 = transform.invertX(extent[0][0]) - translateExtent[0][0], + dx1 = transform.invertX(extent[1][0]) - translateExtent[1][0], + dy0 = transform.invertY(extent[0][1]) - translateExtent[0][1], + dy1 = transform.invertY(extent[1][1]) - translateExtent[1][1]; + return transform.translate( + dx1 > dx0 ? (dx0 + dx1) / 2 : Math.min(0, dx0) || Math.max(0, dx1), + dy1 > dy0 ? (dy0 + dy1) / 2 : Math.min(0, dy0) || Math.max(0, dy1) + ); +} + +function zoom() { + var filter = defaultFilter, + extent = defaultExtent, + constrain = defaultConstrain, + wheelDelta = defaultWheelDelta, + touchable = defaultTouchable, + scaleExtent = [0, Infinity], + translateExtent = [[-Infinity, -Infinity], [Infinity, Infinity]], + duration = 250, + interpolate = d3Interpolate.interpolateZoom, + listeners = d3Dispatch.dispatch("start", "zoom", "end"), + touchstarting, + touchfirst, + touchending, + touchDelay = 500, + wheelDelay = 150, + clickDistance2 = 0, + tapDistance = 10; + + function zoom(selection) { + selection + .property("__zoom", defaultTransform) + .on("wheel.zoom", wheeled, {passive: false}) + .on("mousedown.zoom", mousedowned) + .on("dblclick.zoom", dblclicked) + .filter(touchable) + .on("touchstart.zoom", touchstarted) + .on("touchmove.zoom", touchmoved) + .on("touchend.zoom touchcancel.zoom", touchended) + .style("-webkit-tap-highlight-color", "rgba(0,0,0,0)"); + } + + zoom.transform = function(collection, transform, point, event) { + var selection = collection.selection ? collection.selection() : collection; + selection.property("__zoom", defaultTransform); + if (collection !== selection) { + schedule(collection, transform, point, event); + } else { + selection.interrupt().each(function() { + gesture(this, arguments) + .event(event) + .start() + .zoom(null, typeof transform === "function" ? transform.apply(this, arguments) : transform) + .end(); + }); + } + }; + + zoom.scaleBy = function(selection, k, p, event) { + zoom.scaleTo(selection, function() { + var k0 = this.__zoom.k, + k1 = typeof k === "function" ? k.apply(this, arguments) : k; + return k0 * k1; + }, p, event); + }; + + zoom.scaleTo = function(selection, k, p, event) { + zoom.transform(selection, function() { + var e = extent.apply(this, arguments), + t0 = this.__zoom, + p0 = p == null ? centroid(e) : typeof p === "function" ? p.apply(this, arguments) : p, + p1 = t0.invert(p0), + k1 = typeof k === "function" ? k.apply(this, arguments) : k; + return constrain(translate(scale(t0, k1), p0, p1), e, translateExtent); + }, p, event); + }; + + zoom.translateBy = function(selection, x, y, event) { + zoom.transform(selection, function() { + return constrain(this.__zoom.translate( + typeof x === "function" ? x.apply(this, arguments) : x, + typeof y === "function" ? y.apply(this, arguments) : y + ), extent.apply(this, arguments), translateExtent); + }, null, event); + }; + + zoom.translateTo = function(selection, x, y, p, event) { + zoom.transform(selection, function() { + var e = extent.apply(this, arguments), + t = this.__zoom, + p0 = p == null ? centroid(e) : typeof p === "function" ? p.apply(this, arguments) : p; + return constrain(identity.translate(p0[0], p0[1]).scale(t.k).translate( + typeof x === "function" ? -x.apply(this, arguments) : -x, + typeof y === "function" ? -y.apply(this, arguments) : -y + ), e, translateExtent); + }, p, event); + }; + + function scale(transform, k) { + k = Math.max(scaleExtent[0], Math.min(scaleExtent[1], k)); + return k === transform.k ? transform : new Transform(k, transform.x, transform.y); + } + + function translate(transform, p0, p1) { + var x = p0[0] - p1[0] * transform.k, y = p0[1] - p1[1] * transform.k; + return x === transform.x && y === transform.y ? transform : new Transform(transform.k, x, y); + } + + function centroid(extent) { + return [(+extent[0][0] + +extent[1][0]) / 2, (+extent[0][1] + +extent[1][1]) / 2]; + } + + function schedule(transition, transform, point, event) { + transition + .on("start.zoom", function() { gesture(this, arguments).event(event).start(); }) + .on("interrupt.zoom end.zoom", function() { gesture(this, arguments).event(event).end(); }) + .tween("zoom", function() { + var that = this, + args = arguments, + g = gesture(that, args).event(event), + e = extent.apply(that, args), + p = point == null ? centroid(e) : typeof point === "function" ? point.apply(that, args) : point, + w = Math.max(e[1][0] - e[0][0], e[1][1] - e[0][1]), + a = that.__zoom, + b = typeof transform === "function" ? transform.apply(that, args) : transform, + i = interpolate(a.invert(p).concat(w / a.k), b.invert(p).concat(w / b.k)); + return function(t) { + if (t === 1) t = b; // Avoid rounding error on end. + else { var l = i(t), k = w / l[2]; t = new Transform(k, p[0] - l[0] * k, p[1] - l[1] * k); } + g.zoom(null, t); + }; + }); + } + + function gesture(that, args, clean) { + return (!clean && that.__zooming) || new Gesture(that, args); + } + + function Gesture(that, args) { + this.that = that; + this.args = args; + this.active = 0; + this.sourceEvent = null; + this.extent = extent.apply(that, args); + this.taps = 0; + } + + Gesture.prototype = { + event: function(event) { + if (event) this.sourceEvent = event; + return this; + }, + start: function() { + if (++this.active === 1) { + this.that.__zooming = this; + this.emit("start"); + } + return this; + }, + zoom: function(key, transform) { + if (this.mouse && key !== "mouse") this.mouse[1] = transform.invert(this.mouse[0]); + if (this.touch0 && key !== "touch") this.touch0[1] = transform.invert(this.touch0[0]); + if (this.touch1 && key !== "touch") this.touch1[1] = transform.invert(this.touch1[0]); + this.that.__zoom = transform; + this.emit("zoom"); + return this; + }, + end: function() { + if (--this.active === 0) { + delete this.that.__zooming; + this.emit("end"); + } + return this; + }, + emit: function(type) { + var d = d3Selection.select(this.that).datum(); + listeners.call( + type, + this.that, + new ZoomEvent(type, { + sourceEvent: this.sourceEvent, + target: zoom, + type, + transform: this.that.__zoom, + dispatch: listeners + }), + d + ); + } + }; + + function wheeled(event, ...args) { + if (!filter.apply(this, arguments)) return; + var g = gesture(this, args).event(event), + t = this.__zoom, + k = Math.max(scaleExtent[0], Math.min(scaleExtent[1], t.k * Math.pow(2, wheelDelta.apply(this, arguments)))), + p = d3Selection.pointer(event); + + // If the mouse is in the same location as before, reuse it. + // If there were recent wheel events, reset the wheel idle timeout. + if (g.wheel) { + if (g.mouse[0][0] !== p[0] || g.mouse[0][1] !== p[1]) { + g.mouse[1] = t.invert(g.mouse[0] = p); + } + clearTimeout(g.wheel); + } + + // If this wheel event won’t trigger a transform change, ignore it. + else if (t.k === k) return; + + // Otherwise, capture the mouse point and location at the start. + else { + g.mouse = [p, t.invert(p)]; + d3Transition.interrupt(this); + g.start(); + } + + noevent(event); + g.wheel = setTimeout(wheelidled, wheelDelay); + g.zoom("mouse", constrain(translate(scale(t, k), g.mouse[0], g.mouse[1]), g.extent, translateExtent)); + + function wheelidled() { + g.wheel = null; + g.end(); + } + } + + function mousedowned(event, ...args) { + if (touchending || !filter.apply(this, arguments)) return; + var currentTarget = event.currentTarget, + g = gesture(this, args, true).event(event), + v = d3Selection.select(event.view).on("mousemove.zoom", mousemoved, true).on("mouseup.zoom", mouseupped, true), + p = d3Selection.pointer(event, currentTarget), + x0 = event.clientX, + y0 = event.clientY; + + d3Drag.dragDisable(event.view); + nopropagation(event); + g.mouse = [p, this.__zoom.invert(p)]; + d3Transition.interrupt(this); + g.start(); + + function mousemoved(event) { + noevent(event); + if (!g.moved) { + var dx = event.clientX - x0, dy = event.clientY - y0; + g.moved = dx * dx + dy * dy > clickDistance2; + } + g.event(event) + .zoom("mouse", constrain(translate(g.that.__zoom, g.mouse[0] = d3Selection.pointer(event, currentTarget), g.mouse[1]), g.extent, translateExtent)); + } + + function mouseupped(event) { + v.on("mousemove.zoom mouseup.zoom", null); + d3Drag.dragEnable(event.view, g.moved); + noevent(event); + g.event(event).end(); + } + } + + function dblclicked(event, ...args) { + if (!filter.apply(this, arguments)) return; + var t0 = this.__zoom, + p0 = d3Selection.pointer(event.changedTouches ? event.changedTouches[0] : event, this), + p1 = t0.invert(p0), + k1 = t0.k * (event.shiftKey ? 0.5 : 2), + t1 = constrain(translate(scale(t0, k1), p0, p1), extent.apply(this, args), translateExtent); + + noevent(event); + if (duration > 0) d3Selection.select(this).transition().duration(duration).call(schedule, t1, p0, event); + else d3Selection.select(this).call(zoom.transform, t1, p0, event); + } + + function touchstarted(event, ...args) { + if (!filter.apply(this, arguments)) return; + var touches = event.touches, + n = touches.length, + g = gesture(this, args, event.changedTouches.length === n).event(event), + started, i, t, p; + + nopropagation(event); + for (i = 0; i < n; ++i) { + t = touches[i], p = d3Selection.pointer(t, this); + p = [p, this.__zoom.invert(p), t.identifier]; + if (!g.touch0) g.touch0 = p, started = true, g.taps = 1 + !!touchstarting; + else if (!g.touch1 && g.touch0[2] !== p[2]) g.touch1 = p, g.taps = 0; + } + + if (touchstarting) touchstarting = clearTimeout(touchstarting); + + if (started) { + if (g.taps < 2) touchfirst = p[0], touchstarting = setTimeout(function() { touchstarting = null; }, touchDelay); + d3Transition.interrupt(this); + g.start(); + } + } + + function touchmoved(event, ...args) { + if (!this.__zooming) return; + var g = gesture(this, args).event(event), + touches = event.changedTouches, + n = touches.length, i, t, p, l; + + noevent(event); + for (i = 0; i < n; ++i) { + t = touches[i], p = d3Selection.pointer(t, this); + if (g.touch0 && g.touch0[2] === t.identifier) g.touch0[0] = p; + else if (g.touch1 && g.touch1[2] === t.identifier) g.touch1[0] = p; + } + t = g.that.__zoom; + if (g.touch1) { + var p0 = g.touch0[0], l0 = g.touch0[1], + p1 = g.touch1[0], l1 = g.touch1[1], + dp = (dp = p1[0] - p0[0]) * dp + (dp = p1[1] - p0[1]) * dp, + dl = (dl = l1[0] - l0[0]) * dl + (dl = l1[1] - l0[1]) * dl; + t = scale(t, Math.sqrt(dp / dl)); + p = [(p0[0] + p1[0]) / 2, (p0[1] + p1[1]) / 2]; + l = [(l0[0] + l1[0]) / 2, (l0[1] + l1[1]) / 2]; + } + else if (g.touch0) p = g.touch0[0], l = g.touch0[1]; + else return; + + g.zoom("touch", constrain(translate(t, p, l), g.extent, translateExtent)); + } + + function touchended(event, ...args) { + if (!this.__zooming) return; + var g = gesture(this, args).event(event), + touches = event.changedTouches, + n = touches.length, i, t; + + nopropagation(event); + if (touchending) clearTimeout(touchending); + touchending = setTimeout(function() { touchending = null; }, touchDelay); + for (i = 0; i < n; ++i) { + t = touches[i]; + if (g.touch0 && g.touch0[2] === t.identifier) delete g.touch0; + else if (g.touch1 && g.touch1[2] === t.identifier) delete g.touch1; + } + if (g.touch1 && !g.touch0) g.touch0 = g.touch1, delete g.touch1; + if (g.touch0) g.touch0[1] = this.__zoom.invert(g.touch0[0]); + else { + g.end(); + // If this was a dbltap, reroute to the (optional) dblclick.zoom handler. + if (g.taps === 2) { + t = d3Selection.pointer(t, this); + if (Math.hypot(touchfirst[0] - t[0], touchfirst[1] - t[1]) < tapDistance) { + var p = d3Selection.select(this).on("dblclick.zoom"); + if (p) p.apply(this, arguments); + } + } + } + } + + zoom.wheelDelta = function(_) { + return arguments.length ? (wheelDelta = typeof _ === "function" ? _ : constant(+_), zoom) : wheelDelta; + }; + + zoom.filter = function(_) { + return arguments.length ? (filter = typeof _ === "function" ? _ : constant(!!_), zoom) : filter; + }; + + zoom.touchable = function(_) { + return arguments.length ? (touchable = typeof _ === "function" ? _ : constant(!!_), zoom) : touchable; + }; + + zoom.extent = function(_) { + return arguments.length ? (extent = typeof _ === "function" ? _ : constant([[+_[0][0], +_[0][1]], [+_[1][0], +_[1][1]]]), zoom) : extent; + }; + + zoom.scaleExtent = function(_) { + return arguments.length ? (scaleExtent[0] = +_[0], scaleExtent[1] = +_[1], zoom) : [scaleExtent[0], scaleExtent[1]]; + }; + + zoom.translateExtent = function(_) { + return arguments.length ? (translateExtent[0][0] = +_[0][0], translateExtent[1][0] = +_[1][0], translateExtent[0][1] = +_[0][1], translateExtent[1][1] = +_[1][1], zoom) : [[translateExtent[0][0], translateExtent[0][1]], [translateExtent[1][0], translateExtent[1][1]]]; + }; + + zoom.constrain = function(_) { + return arguments.length ? (constrain = _, zoom) : constrain; + }; + + zoom.duration = function(_) { + return arguments.length ? (duration = +_, zoom) : duration; + }; + + zoom.interpolate = function(_) { + return arguments.length ? (interpolate = _, zoom) : interpolate; + }; + + zoom.on = function() { + var value = listeners.on.apply(listeners, arguments); + return value === listeners ? zoom : value; + }; + + zoom.clickDistance = function(_) { + return arguments.length ? (clickDistance2 = (_ = +_) * _, zoom) : Math.sqrt(clickDistance2); + }; + + zoom.tapDistance = function(_) { + return arguments.length ? (tapDistance = +_, zoom) : tapDistance; + }; + + return zoom; +} + +exports.ZoomTransform = Transform; +exports.zoom = zoom; +exports.zoomIdentity = identity; +exports.zoomTransform = transform; + +Object.defineProperty(exports, '__esModule', { value: true }); + +}))); diff --git a/frontend/node_modules/d3-zoom/dist/d3-zoom.min.js b/frontend/node_modules/d3-zoom/dist/d3-zoom.min.js new file mode 100644 index 0000000..974aea1 --- /dev/null +++ b/frontend/node_modules/d3-zoom/dist/d3-zoom.min.js @@ -0,0 +1,2 @@ +// https://d3js.org/d3-zoom/ v3.0.0 Copyright 2010-2021 Mike Bostock +!function(t,e){"object"==typeof exports&&"undefined"!=typeof module?e(exports,require("d3-dispatch"),require("d3-drag"),require("d3-interpolate"),require("d3-selection"),require("d3-transition")):"function"==typeof define&&define.amd?define(["exports","d3-dispatch","d3-drag","d3-interpolate","d3-selection","d3-transition"],e):e((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{},t.d3,t.d3,t.d3,t.d3,t.d3)}(this,(function(t,e,n,o,i,r){"use strict";var u=t=>()=>t;function s(t,{sourceEvent:e,target:n,transform:o,dispatch:i}){Object.defineProperties(this,{type:{value:t,enumerable:!0,configurable:!0},sourceEvent:{value:e,enumerable:!0,configurable:!0},target:{value:n,enumerable:!0,configurable:!0},transform:{value:o,enumerable:!0,configurable:!0},_:{value:i}})}function h(t,e,n){this.k=t,this.x=e,this.y=n}h.prototype={constructor:h,scale:function(t){return 1===t?this:new h(this.k*t,this.x,this.y)},translate:function(t,e){return 0===t&0===e?this:new h(this.k,this.x+this.k*t,this.y+this.k*e)},apply:function(t){return[t[0]*this.k+this.x,t[1]*this.k+this.y]},applyX:function(t){return t*this.k+this.x},applyY:function(t){return t*this.k+this.y},invert:function(t){return[(t[0]-this.x)/this.k,(t[1]-this.y)/this.k]},invertX:function(t){return(t-this.x)/this.k},invertY:function(t){return(t-this.y)/this.k},rescaleX:function(t){return t.copy().domain(t.range().map(this.invertX,this).map(t.invert,t))},rescaleY:function(t){return t.copy().domain(t.range().map(this.invertY,this).map(t.invert,t))},toString:function(){return"translate("+this.x+","+this.y+") scale("+this.k+")"}};var a=new h(1,0,0);function c(t){for(;!t.__zoom;)if(!(t=t.parentNode))return a;return t.__zoom}function l(t){t.stopImmediatePropagation()}function f(t){t.preventDefault(),t.stopImmediatePropagation()}function p(t){return!(t.ctrlKey&&"wheel"!==t.type||t.button)}function m(){var t=this;return t instanceof SVGElement?(t=t.ownerSVGElement||t).hasAttribute("viewBox")?[[(t=t.viewBox.baseVal).x,t.y],[t.x+t.width,t.y+t.height]]:[[0,0],[t.width.baseVal.value,t.height.baseVal.value]]:[[0,0],[t.clientWidth,t.clientHeight]]}function v(){return this.__zoom||a}function d(t){return-t.deltaY*(1===t.deltaMode?.05:t.deltaMode?1:.002)*(t.ctrlKey?10:1)}function y(){return navigator.maxTouchPoints||"ontouchstart"in this}function g(t,e,n){var o=t.invertX(e[0][0])-n[0][0],i=t.invertX(e[1][0])-n[1][0],r=t.invertY(e[0][1])-n[0][1],u=t.invertY(e[1][1])-n[1][1];return t.translate(i>o?(o+i)/2:Math.min(0,o)||Math.max(0,i),u>r?(r+u)/2:Math.min(0,r)||Math.max(0,u))}c.prototype=h.prototype,t.ZoomTransform=h,t.zoom=function(){var t,c,z,_=p,x=m,k=g,w=d,b=y,T=[0,1/0],M=[[-1/0,-1/0],[1/0,1/0]],E=250,Y=o.interpolateZoom,X=e.dispatch("start","zoom","end"),q=500,D=0,P=10;function V(t){t.property("__zoom",v).on("wheel.zoom",O,{passive:!1}).on("mousedown.zoom",Z).on("dblclick.zoom",A).filter(b).on("touchstart.zoom",H).on("touchmove.zoom",N).on("touchend.zoom touchcancel.zoom",W).style("-webkit-tap-highlight-color","rgba(0,0,0,0)")}function B(t,e){return(e=Math.max(T[0],Math.min(T[1],e)))===t.k?t:new h(e,t.x,t.y)}function j(t,e,n){var o=e[0]-n[0]*t.k,i=e[1]-n[1]*t.k;return o===t.x&&i===t.y?t:new h(t.k,o,i)}function I(t){return[(+t[0][0]+ +t[1][0])/2,(+t[0][1]+ +t[1][1])/2]}function K(t,e,n,o){t.on("start.zoom",(function(){S(this,arguments).event(o).start()})).on("interrupt.zoom end.zoom",(function(){S(this,arguments).event(o).end()})).tween("zoom",(function(){var t=this,i=arguments,r=S(t,i).event(o),u=x.apply(t,i),s=null==n?I(u):"function"==typeof n?n.apply(t,i):n,a=Math.max(u[1][0]-u[0][0],u[1][1]-u[0][1]),c=t.__zoom,l="function"==typeof e?e.apply(t,i):e,f=Y(c.invert(s).concat(a/c.k),l.invert(s).concat(a/l.k));return function(t){if(1===t)t=l;else{var e=f(t),n=a/e[2];t=new h(n,s[0]-e[0]*n,s[1]-e[1]*n)}r.zoom(null,t)}}))}function S(t,e,n){return!n&&t.__zooming||new G(t,e)}function G(t,e){this.that=t,this.args=e,this.active=0,this.sourceEvent=null,this.extent=x.apply(t,e),this.taps=0}function O(t,...e){if(_.apply(this,arguments)){var n=S(this,e).event(t),o=this.__zoom,u=Math.max(T[0],Math.min(T[1],o.k*Math.pow(2,w.apply(this,arguments)))),s=i.pointer(t);if(n.wheel)n.mouse[0][0]===s[0]&&n.mouse[0][1]===s[1]||(n.mouse[1]=o.invert(n.mouse[0]=s)),clearTimeout(n.wheel);else{if(o.k===u)return;n.mouse=[s,o.invert(s)],r.interrupt(this),n.start()}f(t),n.wheel=setTimeout(h,150),n.zoom("mouse",k(j(B(o,u),n.mouse[0],n.mouse[1]),n.extent,M))}function h(){n.wheel=null,n.end()}}function Z(t,...e){if(!z&&_.apply(this,arguments)){var o=t.currentTarget,u=S(this,e,!0).event(t),s=i.select(t.view).on("mousemove.zoom",p,!0).on("mouseup.zoom",m,!0),h=i.pointer(t,o),a=t.clientX,c=t.clientY;n.dragDisable(t.view),l(t),u.mouse=[h,this.__zoom.invert(h)],r.interrupt(this),u.start()}function p(t){if(f(t),!u.moved){var e=t.clientX-a,n=t.clientY-c;u.moved=e*e+n*n>D}u.event(t).zoom("mouse",k(j(u.that.__zoom,u.mouse[0]=i.pointer(t,o),u.mouse[1]),u.extent,M))}function m(t){s.on("mousemove.zoom mouseup.zoom",null),n.dragEnable(t.view,u.moved),f(t),u.event(t).end()}}function A(t,...e){if(_.apply(this,arguments)){var n=this.__zoom,o=i.pointer(t.changedTouches?t.changedTouches[0]:t,this),r=n.invert(o),u=n.k*(t.shiftKey?.5:2),s=k(j(B(n,u),o,r),x.apply(this,e),M);f(t),E>0?i.select(this).transition().duration(E).call(K,s,o,t):i.select(this).call(V.transform,s,o,t)}}function H(e,...n){if(_.apply(this,arguments)){var o,u,s,h,a=e.touches,f=a.length,p=S(this,n,e.changedTouches.length===f).event(e);for(l(e),u=0;u=12" + } +} diff --git a/frontend/node_modules/d3-zoom/src/constant.js b/frontend/node_modules/d3-zoom/src/constant.js new file mode 100644 index 0000000..3487c0d --- /dev/null +++ b/frontend/node_modules/d3-zoom/src/constant.js @@ -0,0 +1 @@ +export default x => () => x; diff --git a/frontend/node_modules/d3-zoom/src/event.js b/frontend/node_modules/d3-zoom/src/event.js new file mode 100644 index 0000000..0a28790 --- /dev/null +++ b/frontend/node_modules/d3-zoom/src/event.js @@ -0,0 +1,14 @@ +export default function ZoomEvent(type, { + sourceEvent, + target, + transform, + dispatch +}) { + Object.defineProperties(this, { + type: {value: type, enumerable: true, configurable: true}, + sourceEvent: {value: sourceEvent, enumerable: true, configurable: true}, + target: {value: target, enumerable: true, configurable: true}, + transform: {value: transform, enumerable: true, configurable: true}, + _: {value: dispatch} + }); +} diff --git a/frontend/node_modules/d3-zoom/src/index.js b/frontend/node_modules/d3-zoom/src/index.js new file mode 100644 index 0000000..4a5f278 --- /dev/null +++ b/frontend/node_modules/d3-zoom/src/index.js @@ -0,0 +1,2 @@ +export {default as zoom} from "./zoom.js"; +export {default as zoomTransform, identity as zoomIdentity, Transform as ZoomTransform} from "./transform.js"; diff --git a/frontend/node_modules/d3-zoom/src/noevent.js b/frontend/node_modules/d3-zoom/src/noevent.js new file mode 100644 index 0000000..b32552d --- /dev/null +++ b/frontend/node_modules/d3-zoom/src/noevent.js @@ -0,0 +1,8 @@ +export function nopropagation(event) { + event.stopImmediatePropagation(); +} + +export default function(event) { + event.preventDefault(); + event.stopImmediatePropagation(); +} diff --git a/frontend/node_modules/d3-zoom/src/transform.js b/frontend/node_modules/d3-zoom/src/transform.js new file mode 100644 index 0000000..8e19f1b --- /dev/null +++ b/frontend/node_modules/d3-zoom/src/transform.js @@ -0,0 +1,51 @@ +export function Transform(k, x, y) { + this.k = k; + this.x = x; + this.y = y; +} + +Transform.prototype = { + constructor: Transform, + scale: function(k) { + return k === 1 ? this : new Transform(this.k * k, this.x, this.y); + }, + translate: function(x, y) { + return x === 0 & y === 0 ? this : new Transform(this.k, this.x + this.k * x, this.y + this.k * y); + }, + apply: function(point) { + return [point[0] * this.k + this.x, point[1] * this.k + this.y]; + }, + applyX: function(x) { + return x * this.k + this.x; + }, + applyY: function(y) { + return y * this.k + this.y; + }, + invert: function(location) { + return [(location[0] - this.x) / this.k, (location[1] - this.y) / this.k]; + }, + invertX: function(x) { + return (x - this.x) / this.k; + }, + invertY: function(y) { + return (y - this.y) / this.k; + }, + rescaleX: function(x) { + return x.copy().domain(x.range().map(this.invertX, this).map(x.invert, x)); + }, + rescaleY: function(y) { + return y.copy().domain(y.range().map(this.invertY, this).map(y.invert, y)); + }, + toString: function() { + return "translate(" + this.x + "," + this.y + ") scale(" + this.k + ")"; + } +}; + +export var identity = new Transform(1, 0, 0); + +transform.prototype = Transform.prototype; + +export default function transform(node) { + while (!node.__zoom) if (!(node = node.parentNode)) return identity; + return node.__zoom; +} diff --git a/frontend/node_modules/d3-zoom/src/zoom.js b/frontend/node_modules/d3-zoom/src/zoom.js new file mode 100644 index 0000000..d564388 --- /dev/null +++ b/frontend/node_modules/d3-zoom/src/zoom.js @@ -0,0 +1,447 @@ +import {dispatch} from "d3-dispatch"; +import {dragDisable, dragEnable} from "d3-drag"; +import {interpolateZoom} from "d3-interpolate"; +import {select, pointer} from "d3-selection"; +import {interrupt} from "d3-transition"; +import constant from "./constant.js"; +import ZoomEvent from "./event.js"; +import {Transform, identity} from "./transform.js"; +import noevent, {nopropagation} from "./noevent.js"; + +// Ignore right-click, since that should open the context menu. +// except for pinch-to-zoom, which is sent as a wheel+ctrlKey event +function defaultFilter(event) { + return (!event.ctrlKey || event.type === 'wheel') && !event.button; +} + +function defaultExtent() { + var e = this; + if (e instanceof SVGElement) { + e = e.ownerSVGElement || e; + if (e.hasAttribute("viewBox")) { + e = e.viewBox.baseVal; + return [[e.x, e.y], [e.x + e.width, e.y + e.height]]; + } + return [[0, 0], [e.width.baseVal.value, e.height.baseVal.value]]; + } + return [[0, 0], [e.clientWidth, e.clientHeight]]; +} + +function defaultTransform() { + return this.__zoom || identity; +} + +function defaultWheelDelta(event) { + return -event.deltaY * (event.deltaMode === 1 ? 0.05 : event.deltaMode ? 1 : 0.002) * (event.ctrlKey ? 10 : 1); +} + +function defaultTouchable() { + return navigator.maxTouchPoints || ("ontouchstart" in this); +} + +function defaultConstrain(transform, extent, translateExtent) { + var dx0 = transform.invertX(extent[0][0]) - translateExtent[0][0], + dx1 = transform.invertX(extent[1][0]) - translateExtent[1][0], + dy0 = transform.invertY(extent[0][1]) - translateExtent[0][1], + dy1 = transform.invertY(extent[1][1]) - translateExtent[1][1]; + return transform.translate( + dx1 > dx0 ? (dx0 + dx1) / 2 : Math.min(0, dx0) || Math.max(0, dx1), + dy1 > dy0 ? (dy0 + dy1) / 2 : Math.min(0, dy0) || Math.max(0, dy1) + ); +} + +export default function() { + var filter = defaultFilter, + extent = defaultExtent, + constrain = defaultConstrain, + wheelDelta = defaultWheelDelta, + touchable = defaultTouchable, + scaleExtent = [0, Infinity], + translateExtent = [[-Infinity, -Infinity], [Infinity, Infinity]], + duration = 250, + interpolate = interpolateZoom, + listeners = dispatch("start", "zoom", "end"), + touchstarting, + touchfirst, + touchending, + touchDelay = 500, + wheelDelay = 150, + clickDistance2 = 0, + tapDistance = 10; + + function zoom(selection) { + selection + .property("__zoom", defaultTransform) + .on("wheel.zoom", wheeled, {passive: false}) + .on("mousedown.zoom", mousedowned) + .on("dblclick.zoom", dblclicked) + .filter(touchable) + .on("touchstart.zoom", touchstarted) + .on("touchmove.zoom", touchmoved) + .on("touchend.zoom touchcancel.zoom", touchended) + .style("-webkit-tap-highlight-color", "rgba(0,0,0,0)"); + } + + zoom.transform = function(collection, transform, point, event) { + var selection = collection.selection ? collection.selection() : collection; + selection.property("__zoom", defaultTransform); + if (collection !== selection) { + schedule(collection, transform, point, event); + } else { + selection.interrupt().each(function() { + gesture(this, arguments) + .event(event) + .start() + .zoom(null, typeof transform === "function" ? transform.apply(this, arguments) : transform) + .end(); + }); + } + }; + + zoom.scaleBy = function(selection, k, p, event) { + zoom.scaleTo(selection, function() { + var k0 = this.__zoom.k, + k1 = typeof k === "function" ? k.apply(this, arguments) : k; + return k0 * k1; + }, p, event); + }; + + zoom.scaleTo = function(selection, k, p, event) { + zoom.transform(selection, function() { + var e = extent.apply(this, arguments), + t0 = this.__zoom, + p0 = p == null ? centroid(e) : typeof p === "function" ? p.apply(this, arguments) : p, + p1 = t0.invert(p0), + k1 = typeof k === "function" ? k.apply(this, arguments) : k; + return constrain(translate(scale(t0, k1), p0, p1), e, translateExtent); + }, p, event); + }; + + zoom.translateBy = function(selection, x, y, event) { + zoom.transform(selection, function() { + return constrain(this.__zoom.translate( + typeof x === "function" ? x.apply(this, arguments) : x, + typeof y === "function" ? y.apply(this, arguments) : y + ), extent.apply(this, arguments), translateExtent); + }, null, event); + }; + + zoom.translateTo = function(selection, x, y, p, event) { + zoom.transform(selection, function() { + var e = extent.apply(this, arguments), + t = this.__zoom, + p0 = p == null ? centroid(e) : typeof p === "function" ? p.apply(this, arguments) : p; + return constrain(identity.translate(p0[0], p0[1]).scale(t.k).translate( + typeof x === "function" ? -x.apply(this, arguments) : -x, + typeof y === "function" ? -y.apply(this, arguments) : -y + ), e, translateExtent); + }, p, event); + }; + + function scale(transform, k) { + k = Math.max(scaleExtent[0], Math.min(scaleExtent[1], k)); + return k === transform.k ? transform : new Transform(k, transform.x, transform.y); + } + + function translate(transform, p0, p1) { + var x = p0[0] - p1[0] * transform.k, y = p0[1] - p1[1] * transform.k; + return x === transform.x && y === transform.y ? transform : new Transform(transform.k, x, y); + } + + function centroid(extent) { + return [(+extent[0][0] + +extent[1][0]) / 2, (+extent[0][1] + +extent[1][1]) / 2]; + } + + function schedule(transition, transform, point, event) { + transition + .on("start.zoom", function() { gesture(this, arguments).event(event).start(); }) + .on("interrupt.zoom end.zoom", function() { gesture(this, arguments).event(event).end(); }) + .tween("zoom", function() { + var that = this, + args = arguments, + g = gesture(that, args).event(event), + e = extent.apply(that, args), + p = point == null ? centroid(e) : typeof point === "function" ? point.apply(that, args) : point, + w = Math.max(e[1][0] - e[0][0], e[1][1] - e[0][1]), + a = that.__zoom, + b = typeof transform === "function" ? transform.apply(that, args) : transform, + i = interpolate(a.invert(p).concat(w / a.k), b.invert(p).concat(w / b.k)); + return function(t) { + if (t === 1) t = b; // Avoid rounding error on end. + else { var l = i(t), k = w / l[2]; t = new Transform(k, p[0] - l[0] * k, p[1] - l[1] * k); } + g.zoom(null, t); + }; + }); + } + + function gesture(that, args, clean) { + return (!clean && that.__zooming) || new Gesture(that, args); + } + + function Gesture(that, args) { + this.that = that; + this.args = args; + this.active = 0; + this.sourceEvent = null; + this.extent = extent.apply(that, args); + this.taps = 0; + } + + Gesture.prototype = { + event: function(event) { + if (event) this.sourceEvent = event; + return this; + }, + start: function() { + if (++this.active === 1) { + this.that.__zooming = this; + this.emit("start"); + } + return this; + }, + zoom: function(key, transform) { + if (this.mouse && key !== "mouse") this.mouse[1] = transform.invert(this.mouse[0]); + if (this.touch0 && key !== "touch") this.touch0[1] = transform.invert(this.touch0[0]); + if (this.touch1 && key !== "touch") this.touch1[1] = transform.invert(this.touch1[0]); + this.that.__zoom = transform; + this.emit("zoom"); + return this; + }, + end: function() { + if (--this.active === 0) { + delete this.that.__zooming; + this.emit("end"); + } + return this; + }, + emit: function(type) { + var d = select(this.that).datum(); + listeners.call( + type, + this.that, + new ZoomEvent(type, { + sourceEvent: this.sourceEvent, + target: zoom, + type, + transform: this.that.__zoom, + dispatch: listeners + }), + d + ); + } + }; + + function wheeled(event, ...args) { + if (!filter.apply(this, arguments)) return; + var g = gesture(this, args).event(event), + t = this.__zoom, + k = Math.max(scaleExtent[0], Math.min(scaleExtent[1], t.k * Math.pow(2, wheelDelta.apply(this, arguments)))), + p = pointer(event); + + // If the mouse is in the same location as before, reuse it. + // If there were recent wheel events, reset the wheel idle timeout. + if (g.wheel) { + if (g.mouse[0][0] !== p[0] || g.mouse[0][1] !== p[1]) { + g.mouse[1] = t.invert(g.mouse[0] = p); + } + clearTimeout(g.wheel); + } + + // If this wheel event won’t trigger a transform change, ignore it. + else if (t.k === k) return; + + // Otherwise, capture the mouse point and location at the start. + else { + g.mouse = [p, t.invert(p)]; + interrupt(this); + g.start(); + } + + noevent(event); + g.wheel = setTimeout(wheelidled, wheelDelay); + g.zoom("mouse", constrain(translate(scale(t, k), g.mouse[0], g.mouse[1]), g.extent, translateExtent)); + + function wheelidled() { + g.wheel = null; + g.end(); + } + } + + function mousedowned(event, ...args) { + if (touchending || !filter.apply(this, arguments)) return; + var currentTarget = event.currentTarget, + g = gesture(this, args, true).event(event), + v = select(event.view).on("mousemove.zoom", mousemoved, true).on("mouseup.zoom", mouseupped, true), + p = pointer(event, currentTarget), + x0 = event.clientX, + y0 = event.clientY; + + dragDisable(event.view); + nopropagation(event); + g.mouse = [p, this.__zoom.invert(p)]; + interrupt(this); + g.start(); + + function mousemoved(event) { + noevent(event); + if (!g.moved) { + var dx = event.clientX - x0, dy = event.clientY - y0; + g.moved = dx * dx + dy * dy > clickDistance2; + } + g.event(event) + .zoom("mouse", constrain(translate(g.that.__zoom, g.mouse[0] = pointer(event, currentTarget), g.mouse[1]), g.extent, translateExtent)); + } + + function mouseupped(event) { + v.on("mousemove.zoom mouseup.zoom", null); + dragEnable(event.view, g.moved); + noevent(event); + g.event(event).end(); + } + } + + function dblclicked(event, ...args) { + if (!filter.apply(this, arguments)) return; + var t0 = this.__zoom, + p0 = pointer(event.changedTouches ? event.changedTouches[0] : event, this), + p1 = t0.invert(p0), + k1 = t0.k * (event.shiftKey ? 0.5 : 2), + t1 = constrain(translate(scale(t0, k1), p0, p1), extent.apply(this, args), translateExtent); + + noevent(event); + if (duration > 0) select(this).transition().duration(duration).call(schedule, t1, p0, event); + else select(this).call(zoom.transform, t1, p0, event); + } + + function touchstarted(event, ...args) { + if (!filter.apply(this, arguments)) return; + var touches = event.touches, + n = touches.length, + g = gesture(this, args, event.changedTouches.length === n).event(event), + started, i, t, p; + + nopropagation(event); + for (i = 0; i < n; ++i) { + t = touches[i], p = pointer(t, this); + p = [p, this.__zoom.invert(p), t.identifier]; + if (!g.touch0) g.touch0 = p, started = true, g.taps = 1 + !!touchstarting; + else if (!g.touch1 && g.touch0[2] !== p[2]) g.touch1 = p, g.taps = 0; + } + + if (touchstarting) touchstarting = clearTimeout(touchstarting); + + if (started) { + if (g.taps < 2) touchfirst = p[0], touchstarting = setTimeout(function() { touchstarting = null; }, touchDelay); + interrupt(this); + g.start(); + } + } + + function touchmoved(event, ...args) { + if (!this.__zooming) return; + var g = gesture(this, args).event(event), + touches = event.changedTouches, + n = touches.length, i, t, p, l; + + noevent(event); + for (i = 0; i < n; ++i) { + t = touches[i], p = pointer(t, this); + if (g.touch0 && g.touch0[2] === t.identifier) g.touch0[0] = p; + else if (g.touch1 && g.touch1[2] === t.identifier) g.touch1[0] = p; + } + t = g.that.__zoom; + if (g.touch1) { + var p0 = g.touch0[0], l0 = g.touch0[1], + p1 = g.touch1[0], l1 = g.touch1[1], + dp = (dp = p1[0] - p0[0]) * dp + (dp = p1[1] - p0[1]) * dp, + dl = (dl = l1[0] - l0[0]) * dl + (dl = l1[1] - l0[1]) * dl; + t = scale(t, Math.sqrt(dp / dl)); + p = [(p0[0] + p1[0]) / 2, (p0[1] + p1[1]) / 2]; + l = [(l0[0] + l1[0]) / 2, (l0[1] + l1[1]) / 2]; + } + else if (g.touch0) p = g.touch0[0], l = g.touch0[1]; + else return; + + g.zoom("touch", constrain(translate(t, p, l), g.extent, translateExtent)); + } + + function touchended(event, ...args) { + if (!this.__zooming) return; + var g = gesture(this, args).event(event), + touches = event.changedTouches, + n = touches.length, i, t; + + nopropagation(event); + if (touchending) clearTimeout(touchending); + touchending = setTimeout(function() { touchending = null; }, touchDelay); + for (i = 0; i < n; ++i) { + t = touches[i]; + if (g.touch0 && g.touch0[2] === t.identifier) delete g.touch0; + else if (g.touch1 && g.touch1[2] === t.identifier) delete g.touch1; + } + if (g.touch1 && !g.touch0) g.touch0 = g.touch1, delete g.touch1; + if (g.touch0) g.touch0[1] = this.__zoom.invert(g.touch0[0]); + else { + g.end(); + // If this was a dbltap, reroute to the (optional) dblclick.zoom handler. + if (g.taps === 2) { + t = pointer(t, this); + if (Math.hypot(touchfirst[0] - t[0], touchfirst[1] - t[1]) < tapDistance) { + var p = select(this).on("dblclick.zoom"); + if (p) p.apply(this, arguments); + } + } + } + } + + zoom.wheelDelta = function(_) { + return arguments.length ? (wheelDelta = typeof _ === "function" ? _ : constant(+_), zoom) : wheelDelta; + }; + + zoom.filter = function(_) { + return arguments.length ? (filter = typeof _ === "function" ? _ : constant(!!_), zoom) : filter; + }; + + zoom.touchable = function(_) { + return arguments.length ? (touchable = typeof _ === "function" ? _ : constant(!!_), zoom) : touchable; + }; + + zoom.extent = function(_) { + return arguments.length ? (extent = typeof _ === "function" ? _ : constant([[+_[0][0], +_[0][1]], [+_[1][0], +_[1][1]]]), zoom) : extent; + }; + + zoom.scaleExtent = function(_) { + return arguments.length ? (scaleExtent[0] = +_[0], scaleExtent[1] = +_[1], zoom) : [scaleExtent[0], scaleExtent[1]]; + }; + + zoom.translateExtent = function(_) { + return arguments.length ? (translateExtent[0][0] = +_[0][0], translateExtent[1][0] = +_[1][0], translateExtent[0][1] = +_[0][1], translateExtent[1][1] = +_[1][1], zoom) : [[translateExtent[0][0], translateExtent[0][1]], [translateExtent[1][0], translateExtent[1][1]]]; + }; + + zoom.constrain = function(_) { + return arguments.length ? (constrain = _, zoom) : constrain; + }; + + zoom.duration = function(_) { + return arguments.length ? (duration = +_, zoom) : duration; + }; + + zoom.interpolate = function(_) { + return arguments.length ? (interpolate = _, zoom) : interpolate; + }; + + zoom.on = function() { + var value = listeners.on.apply(listeners, arguments); + return value === listeners ? zoom : value; + }; + + zoom.clickDistance = function(_) { + return arguments.length ? (clickDistance2 = (_ = +_) * _, zoom) : Math.sqrt(clickDistance2); + }; + + zoom.tapDistance = function(_) { + return arguments.length ? (tapDistance = +_, zoom) : tapDistance; + }; + + return zoom; +} diff --git a/frontend/node_modules/d3/LICENSE b/frontend/node_modules/d3/LICENSE new file mode 100644 index 0000000..3594fff --- /dev/null +++ b/frontend/node_modules/d3/LICENSE @@ -0,0 +1,13 @@ +Copyright 2010-2023 Mike Bostock + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/d3/README.md b/frontend/node_modules/d3/README.md new file mode 100644 index 0000000..39e125d --- /dev/null +++ b/frontend/node_modules/d3/README.md @@ -0,0 +1,12 @@ +# D3: Data-Driven Documents + + + +**D3** (or **D3.js**) is a free, open-source JavaScript library for visualizing data. Its low-level approach built on web standards offers unparalleled flexibility in authoring dynamic, data-driven graphics. For more than a decade D3 has powered groundbreaking and award-winning visualizations, become a foundational building block of higher-level chart libraries, and fostered a vibrant community of data practitioners around the world. + +## Resources + +* [Documentation](https://d3js.org) +* [Examples](https://observablehq.com/@d3/gallery) +* [Releases](https://github.com/d3/d3/releases) +* [Getting help](https://d3js.org/community) diff --git a/frontend/node_modules/d3/dist/d3.js b/frontend/node_modules/d3/dist/d3.js new file mode 100644 index 0000000..6c6bf89 --- /dev/null +++ b/frontend/node_modules/d3/dist/d3.js @@ -0,0 +1,20625 @@ +// https://d3js.org v7.9.0 Copyright 2010-2023 Mike Bostock +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : +typeof define === 'function' && define.amd ? define(['exports'], factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3 = global.d3 || {})); +})(this, (function (exports) { 'use strict'; + +var version = "7.9.0"; + +function ascending$3(a, b) { + return a == null || b == null ? NaN : a < b ? -1 : a > b ? 1 : a >= b ? 0 : NaN; +} + +function descending$2(a, b) { + return a == null || b == null ? NaN + : b < a ? -1 + : b > a ? 1 + : b >= a ? 0 + : NaN; +} + +function bisector(f) { + let compare1, compare2, delta; + + // If an accessor is specified, promote it to a comparator. In this case we + // can test whether the search value is (self-) comparable. We can’t do this + // for a comparator (except for specific, known comparators) because we can’t + // tell if the comparator is symmetric, and an asymmetric comparator can’t be + // used to test whether a single value is comparable. + if (f.length !== 2) { + compare1 = ascending$3; + compare2 = (d, x) => ascending$3(f(d), x); + delta = (d, x) => f(d) - x; + } else { + compare1 = f === ascending$3 || f === descending$2 ? f : zero$1; + compare2 = f; + delta = f; + } + + function left(a, x, lo = 0, hi = a.length) { + if (lo < hi) { + if (compare1(x, x) !== 0) return hi; + do { + const mid = (lo + hi) >>> 1; + if (compare2(a[mid], x) < 0) lo = mid + 1; + else hi = mid; + } while (lo < hi); + } + return lo; + } + + function right(a, x, lo = 0, hi = a.length) { + if (lo < hi) { + if (compare1(x, x) !== 0) return hi; + do { + const mid = (lo + hi) >>> 1; + if (compare2(a[mid], x) <= 0) lo = mid + 1; + else hi = mid; + } while (lo < hi); + } + return lo; + } + + function center(a, x, lo = 0, hi = a.length) { + const i = left(a, x, lo, hi - 1); + return i > lo && delta(a[i - 1], x) > -delta(a[i], x) ? i - 1 : i; + } + + return {left, center, right}; +} + +function zero$1() { + return 0; +} + +function number$3(x) { + return x === null ? NaN : +x; +} + +function* numbers(values, valueof) { + if (valueof === undefined) { + for (let value of values) { + if (value != null && (value = +value) >= value) { + yield value; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && (value = +value) >= value) { + yield value; + } + } + } +} + +const ascendingBisect = bisector(ascending$3); +const bisectRight = ascendingBisect.right; +const bisectLeft = ascendingBisect.left; +const bisectCenter = bisector(number$3).center; +var bisect = bisectRight; + +function blur(values, r) { + if (!((r = +r) >= 0)) throw new RangeError("invalid r"); + let length = values.length; + if (!((length = Math.floor(length)) >= 0)) throw new RangeError("invalid length"); + if (!length || !r) return values; + const blur = blurf(r); + const temp = values.slice(); + blur(values, temp, 0, length, 1); + blur(temp, values, 0, length, 1); + blur(values, temp, 0, length, 1); + return values; +} + +const blur2 = Blur2(blurf); + +const blurImage = Blur2(blurfImage); + +function Blur2(blur) { + return function(data, rx, ry = rx) { + if (!((rx = +rx) >= 0)) throw new RangeError("invalid rx"); + if (!((ry = +ry) >= 0)) throw new RangeError("invalid ry"); + let {data: values, width, height} = data; + if (!((width = Math.floor(width)) >= 0)) throw new RangeError("invalid width"); + if (!((height = Math.floor(height !== undefined ? height : values.length / width)) >= 0)) throw new RangeError("invalid height"); + if (!width || !height || (!rx && !ry)) return data; + const blurx = rx && blur(rx); + const blury = ry && blur(ry); + const temp = values.slice(); + if (blurx && blury) { + blurh(blurx, temp, values, width, height); + blurh(blurx, values, temp, width, height); + blurh(blurx, temp, values, width, height); + blurv(blury, values, temp, width, height); + blurv(blury, temp, values, width, height); + blurv(blury, values, temp, width, height); + } else if (blurx) { + blurh(blurx, values, temp, width, height); + blurh(blurx, temp, values, width, height); + blurh(blurx, values, temp, width, height); + } else if (blury) { + blurv(blury, values, temp, width, height); + blurv(blury, temp, values, width, height); + blurv(blury, values, temp, width, height); + } + return data; + }; +} + +function blurh(blur, T, S, w, h) { + for (let y = 0, n = w * h; y < n;) { + blur(T, S, y, y += w, 1); + } +} + +function blurv(blur, T, S, w, h) { + for (let x = 0, n = w * h; x < w; ++x) { + blur(T, S, x, x + n, w); + } +} + +function blurfImage(radius) { + const blur = blurf(radius); + return (T, S, start, stop, step) => { + start <<= 2, stop <<= 2, step <<= 2; + blur(T, S, start + 0, stop + 0, step); + blur(T, S, start + 1, stop + 1, step); + blur(T, S, start + 2, stop + 2, step); + blur(T, S, start + 3, stop + 3, step); + }; +} + +// Given a target array T, a source array S, sets each value T[i] to the average +// of {S[i - r], …, S[i], …, S[i + r]}, where r = ⌊radius⌋, start <= i < stop, +// for each i, i + step, i + 2 * step, etc., and where S[j] is clamped between +// S[start] (inclusive) and S[stop] (exclusive). If the given radius is not an +// integer, S[i - r - 1] and S[i + r + 1] are added to the sum, each weighted +// according to r - ⌊radius⌋. +function blurf(radius) { + const radius0 = Math.floor(radius); + if (radius0 === radius) return bluri(radius); + const t = radius - radius0; + const w = 2 * radius + 1; + return (T, S, start, stop, step) => { // stop must be aligned! + if (!((stop -= step) >= start)) return; // inclusive stop + let sum = radius0 * S[start]; + const s0 = step * radius0; + const s1 = s0 + step; + for (let i = start, j = start + s0; i < j; i += step) { + sum += S[Math.min(stop, i)]; + } + for (let i = start, j = stop; i <= j; i += step) { + sum += S[Math.min(stop, i + s0)]; + T[i] = (sum + t * (S[Math.max(start, i - s1)] + S[Math.min(stop, i + s1)])) / w; + sum -= S[Math.max(start, i - s0)]; + } + }; +} + +// Like blurf, but optimized for integer radius. +function bluri(radius) { + const w = 2 * radius + 1; + return (T, S, start, stop, step) => { // stop must be aligned! + if (!((stop -= step) >= start)) return; // inclusive stop + let sum = radius * S[start]; + const s = step * radius; + for (let i = start, j = start + s; i < j; i += step) { + sum += S[Math.min(stop, i)]; + } + for (let i = start, j = stop; i <= j; i += step) { + sum += S[Math.min(stop, i + s)]; + T[i] = sum / w; + sum -= S[Math.max(start, i - s)]; + } + }; +} + +function count$1(values, valueof) { + let count = 0; + if (valueof === undefined) { + for (let value of values) { + if (value != null && (value = +value) >= value) { + ++count; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && (value = +value) >= value) { + ++count; + } + } + } + return count; +} + +function length$3(array) { + return array.length | 0; +} + +function empty$2(length) { + return !(length > 0); +} + +function arrayify(values) { + return typeof values !== "object" || "length" in values ? values : Array.from(values); +} + +function reducer(reduce) { + return values => reduce(...values); +} + +function cross$2(...values) { + const reduce = typeof values[values.length - 1] === "function" && reducer(values.pop()); + values = values.map(arrayify); + const lengths = values.map(length$3); + const j = values.length - 1; + const index = new Array(j + 1).fill(0); + const product = []; + if (j < 0 || lengths.some(empty$2)) return product; + while (true) { + product.push(index.map((j, i) => values[i][j])); + let i = j; + while (++index[i] === lengths[i]) { + if (i === 0) return reduce ? product.map(reduce) : product; + index[i--] = 0; + } + } +} + +function cumsum(values, valueof) { + var sum = 0, index = 0; + return Float64Array.from(values, valueof === undefined + ? v => (sum += +v || 0) + : v => (sum += +valueof(v, index++, values) || 0)); +} + +function variance(values, valueof) { + let count = 0; + let delta; + let mean = 0; + let sum = 0; + if (valueof === undefined) { + for (let value of values) { + if (value != null && (value = +value) >= value) { + delta = value - mean; + mean += delta / ++count; + sum += delta * (value - mean); + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && (value = +value) >= value) { + delta = value - mean; + mean += delta / ++count; + sum += delta * (value - mean); + } + } + } + if (count > 1) return sum / (count - 1); +} + +function deviation(values, valueof) { + const v = variance(values, valueof); + return v ? Math.sqrt(v) : v; +} + +function extent$1(values, valueof) { + let min; + let max; + if (valueof === undefined) { + for (const value of values) { + if (value != null) { + if (min === undefined) { + if (value >= value) min = max = value; + } else { + if (min > value) min = value; + if (max < value) max = value; + } + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null) { + if (min === undefined) { + if (value >= value) min = max = value; + } else { + if (min > value) min = value; + if (max < value) max = value; + } + } + } + } + return [min, max]; +} + +// https://github.com/python/cpython/blob/a74eea238f5baba15797e2e8b570d153bc8690a7/Modules/mathmodule.c#L1423 +class Adder { + constructor() { + this._partials = new Float64Array(32); + this._n = 0; + } + add(x) { + const p = this._partials; + let i = 0; + for (let j = 0; j < this._n && j < 32; j++) { + const y = p[j], + hi = x + y, + lo = Math.abs(x) < Math.abs(y) ? x - (hi - y) : y - (hi - x); + if (lo) p[i++] = lo; + x = hi; + } + p[i] = x; + this._n = i + 1; + return this; + } + valueOf() { + const p = this._partials; + let n = this._n, x, y, lo, hi = 0; + if (n > 0) { + hi = p[--n]; + while (n > 0) { + x = hi; + y = p[--n]; + hi = x + y; + lo = y - (hi - x); + if (lo) break; + } + if (n > 0 && ((lo < 0 && p[n - 1] < 0) || (lo > 0 && p[n - 1] > 0))) { + y = lo * 2; + x = hi + y; + if (y == x - hi) hi = x; + } + } + return hi; + } +} + +function fsum(values, valueof) { + const adder = new Adder(); + if (valueof === undefined) { + for (let value of values) { + if (value = +value) { + adder.add(value); + } + } + } else { + let index = -1; + for (let value of values) { + if (value = +valueof(value, ++index, values)) { + adder.add(value); + } + } + } + return +adder; +} + +function fcumsum(values, valueof) { + const adder = new Adder(); + let index = -1; + return Float64Array.from(values, valueof === undefined + ? v => adder.add(+v || 0) + : v => adder.add(+valueof(v, ++index, values) || 0) + ); +} + +class InternMap extends Map { + constructor(entries, key = keyof) { + super(); + Object.defineProperties(this, {_intern: {value: new Map()}, _key: {value: key}}); + if (entries != null) for (const [key, value] of entries) this.set(key, value); + } + get(key) { + return super.get(intern_get(this, key)); + } + has(key) { + return super.has(intern_get(this, key)); + } + set(key, value) { + return super.set(intern_set(this, key), value); + } + delete(key) { + return super.delete(intern_delete(this, key)); + } +} + +class InternSet extends Set { + constructor(values, key = keyof) { + super(); + Object.defineProperties(this, {_intern: {value: new Map()}, _key: {value: key}}); + if (values != null) for (const value of values) this.add(value); + } + has(value) { + return super.has(intern_get(this, value)); + } + add(value) { + return super.add(intern_set(this, value)); + } + delete(value) { + return super.delete(intern_delete(this, value)); + } +} + +function intern_get({_intern, _key}, value) { + const key = _key(value); + return _intern.has(key) ? _intern.get(key) : value; +} + +function intern_set({_intern, _key}, value) { + const key = _key(value); + if (_intern.has(key)) return _intern.get(key); + _intern.set(key, value); + return value; +} + +function intern_delete({_intern, _key}, value) { + const key = _key(value); + if (_intern.has(key)) { + value = _intern.get(key); + _intern.delete(key); + } + return value; +} + +function keyof(value) { + return value !== null && typeof value === "object" ? value.valueOf() : value; +} + +function identity$9(x) { + return x; +} + +function group(values, ...keys) { + return nest(values, identity$9, identity$9, keys); +} + +function groups(values, ...keys) { + return nest(values, Array.from, identity$9, keys); +} + +function flatten$1(groups, keys) { + for (let i = 1, n = keys.length; i < n; ++i) { + groups = groups.flatMap(g => g.pop().map(([key, value]) => [...g, key, value])); + } + return groups; +} + +function flatGroup(values, ...keys) { + return flatten$1(groups(values, ...keys), keys); +} + +function flatRollup(values, reduce, ...keys) { + return flatten$1(rollups(values, reduce, ...keys), keys); +} + +function rollup(values, reduce, ...keys) { + return nest(values, identity$9, reduce, keys); +} + +function rollups(values, reduce, ...keys) { + return nest(values, Array.from, reduce, keys); +} + +function index$4(values, ...keys) { + return nest(values, identity$9, unique, keys); +} + +function indexes(values, ...keys) { + return nest(values, Array.from, unique, keys); +} + +function unique(values) { + if (values.length !== 1) throw new Error("duplicate key"); + return values[0]; +} + +function nest(values, map, reduce, keys) { + return (function regroup(values, i) { + if (i >= keys.length) return reduce(values); + const groups = new InternMap(); + const keyof = keys[i++]; + let index = -1; + for (const value of values) { + const key = keyof(value, ++index, values); + const group = groups.get(key); + if (group) group.push(value); + else groups.set(key, [value]); + } + for (const [key, values] of groups) { + groups.set(key, regroup(values, i)); + } + return map(groups); + })(values, 0); +} + +function permute(source, keys) { + return Array.from(keys, key => source[key]); +} + +function sort(values, ...F) { + if (typeof values[Symbol.iterator] !== "function") throw new TypeError("values is not iterable"); + values = Array.from(values); + let [f] = F; + if ((f && f.length !== 2) || F.length > 1) { + const index = Uint32Array.from(values, (d, i) => i); + if (F.length > 1) { + F = F.map(f => values.map(f)); + index.sort((i, j) => { + for (const f of F) { + const c = ascendingDefined(f[i], f[j]); + if (c) return c; + } + }); + } else { + f = values.map(f); + index.sort((i, j) => ascendingDefined(f[i], f[j])); + } + return permute(values, index); + } + return values.sort(compareDefined(f)); +} + +function compareDefined(compare = ascending$3) { + if (compare === ascending$3) return ascendingDefined; + if (typeof compare !== "function") throw new TypeError("compare is not a function"); + return (a, b) => { + const x = compare(a, b); + if (x || x === 0) return x; + return (compare(b, b) === 0) - (compare(a, a) === 0); + }; +} + +function ascendingDefined(a, b) { + return (a == null || !(a >= a)) - (b == null || !(b >= b)) || (a < b ? -1 : a > b ? 1 : 0); +} + +function groupSort(values, reduce, key) { + return (reduce.length !== 2 + ? sort(rollup(values, reduce, key), (([ak, av], [bk, bv]) => ascending$3(av, bv) || ascending$3(ak, bk))) + : sort(group(values, key), (([ak, av], [bk, bv]) => reduce(av, bv) || ascending$3(ak, bk)))) + .map(([key]) => key); +} + +var array$5 = Array.prototype; + +var slice$3 = array$5.slice; + +function constant$b(x) { + return () => x; +} + +const e10 = Math.sqrt(50), + e5 = Math.sqrt(10), + e2 = Math.sqrt(2); + +function tickSpec(start, stop, count) { + const step = (stop - start) / Math.max(0, count), + power = Math.floor(Math.log10(step)), + error = step / Math.pow(10, power), + factor = error >= e10 ? 10 : error >= e5 ? 5 : error >= e2 ? 2 : 1; + let i1, i2, inc; + if (power < 0) { + inc = Math.pow(10, -power) / factor; + i1 = Math.round(start * inc); + i2 = Math.round(stop * inc); + if (i1 / inc < start) ++i1; + if (i2 / inc > stop) --i2; + inc = -inc; + } else { + inc = Math.pow(10, power) * factor; + i1 = Math.round(start / inc); + i2 = Math.round(stop / inc); + if (i1 * inc < start) ++i1; + if (i2 * inc > stop) --i2; + } + if (i2 < i1 && 0.5 <= count && count < 2) return tickSpec(start, stop, count * 2); + return [i1, i2, inc]; +} + +function ticks(start, stop, count) { + stop = +stop, start = +start, count = +count; + if (!(count > 0)) return []; + if (start === stop) return [start]; + const reverse = stop < start, [i1, i2, inc] = reverse ? tickSpec(stop, start, count) : tickSpec(start, stop, count); + if (!(i2 >= i1)) return []; + const n = i2 - i1 + 1, ticks = new Array(n); + if (reverse) { + if (inc < 0) for (let i = 0; i < n; ++i) ticks[i] = (i2 - i) / -inc; + else for (let i = 0; i < n; ++i) ticks[i] = (i2 - i) * inc; + } else { + if (inc < 0) for (let i = 0; i < n; ++i) ticks[i] = (i1 + i) / -inc; + else for (let i = 0; i < n; ++i) ticks[i] = (i1 + i) * inc; + } + return ticks; +} + +function tickIncrement(start, stop, count) { + stop = +stop, start = +start, count = +count; + return tickSpec(start, stop, count)[2]; +} + +function tickStep(start, stop, count) { + stop = +stop, start = +start, count = +count; + const reverse = stop < start, inc = reverse ? tickIncrement(stop, start, count) : tickIncrement(start, stop, count); + return (reverse ? -1 : 1) * (inc < 0 ? 1 / -inc : inc); +} + +function nice$1(start, stop, count) { + let prestep; + while (true) { + const step = tickIncrement(start, stop, count); + if (step === prestep || step === 0 || !isFinite(step)) { + return [start, stop]; + } else if (step > 0) { + start = Math.floor(start / step) * step; + stop = Math.ceil(stop / step) * step; + } else if (step < 0) { + start = Math.ceil(start * step) / step; + stop = Math.floor(stop * step) / step; + } + prestep = step; + } +} + +function thresholdSturges(values) { + return Math.max(1, Math.ceil(Math.log(count$1(values)) / Math.LN2) + 1); +} + +function bin() { + var value = identity$9, + domain = extent$1, + threshold = thresholdSturges; + + function histogram(data) { + if (!Array.isArray(data)) data = Array.from(data); + + var i, + n = data.length, + x, + step, + values = new Array(n); + + for (i = 0; i < n; ++i) { + values[i] = value(data[i], i, data); + } + + var xz = domain(values), + x0 = xz[0], + x1 = xz[1], + tz = threshold(values, x0, x1); + + // Convert number of thresholds into uniform thresholds, and nice the + // default domain accordingly. + if (!Array.isArray(tz)) { + const max = x1, tn = +tz; + if (domain === extent$1) [x0, x1] = nice$1(x0, x1, tn); + tz = ticks(x0, x1, tn); + + // If the domain is aligned with the first tick (which it will by + // default), then we can use quantization rather than bisection to bin + // values, which is substantially faster. + if (tz[0] <= x0) step = tickIncrement(x0, x1, tn); + + // If the last threshold is coincident with the domain’s upper bound, the + // last bin will be zero-width. If the default domain is used, and this + // last threshold is coincident with the maximum input value, we can + // extend the niced upper bound by one tick to ensure uniform bin widths; + // otherwise, we simply remove the last threshold. Note that we don’t + // coerce values or the domain to numbers, and thus must be careful to + // compare order (>=) rather than strict equality (===)! + if (tz[tz.length - 1] >= x1) { + if (max >= x1 && domain === extent$1) { + const step = tickIncrement(x0, x1, tn); + if (isFinite(step)) { + if (step > 0) { + x1 = (Math.floor(x1 / step) + 1) * step; + } else if (step < 0) { + x1 = (Math.ceil(x1 * -step) + 1) / -step; + } + } + } else { + tz.pop(); + } + } + } + + // Remove any thresholds outside the domain. + // Be careful not to mutate an array owned by the user! + var m = tz.length, a = 0, b = m; + while (tz[a] <= x0) ++a; + while (tz[b - 1] > x1) --b; + if (a || b < m) tz = tz.slice(a, b), m = b - a; + + var bins = new Array(m + 1), + bin; + + // Initialize bins. + for (i = 0; i <= m; ++i) { + bin = bins[i] = []; + bin.x0 = i > 0 ? tz[i - 1] : x0; + bin.x1 = i < m ? tz[i] : x1; + } + + // Assign data to bins by value, ignoring any outside the domain. + if (isFinite(step)) { + if (step > 0) { + for (i = 0; i < n; ++i) { + if ((x = values[i]) != null && x0 <= x && x <= x1) { + bins[Math.min(m, Math.floor((x - x0) / step))].push(data[i]); + } + } + } else if (step < 0) { + for (i = 0; i < n; ++i) { + if ((x = values[i]) != null && x0 <= x && x <= x1) { + const j = Math.floor((x0 - x) * step); + bins[Math.min(m, j + (tz[j] <= x))].push(data[i]); // handle off-by-one due to rounding + } + } + } + } else { + for (i = 0; i < n; ++i) { + if ((x = values[i]) != null && x0 <= x && x <= x1) { + bins[bisect(tz, x, 0, m)].push(data[i]); + } + } + } + + return bins; + } + + histogram.value = function(_) { + return arguments.length ? (value = typeof _ === "function" ? _ : constant$b(_), histogram) : value; + }; + + histogram.domain = function(_) { + return arguments.length ? (domain = typeof _ === "function" ? _ : constant$b([_[0], _[1]]), histogram) : domain; + }; + + histogram.thresholds = function(_) { + return arguments.length ? (threshold = typeof _ === "function" ? _ : constant$b(Array.isArray(_) ? slice$3.call(_) : _), histogram) : threshold; + }; + + return histogram; +} + +function max$3(values, valueof) { + let max; + if (valueof === undefined) { + for (const value of values) { + if (value != null + && (max < value || (max === undefined && value >= value))) { + max = value; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null + && (max < value || (max === undefined && value >= value))) { + max = value; + } + } + } + return max; +} + +function maxIndex(values, valueof) { + let max; + let maxIndex = -1; + let index = -1; + if (valueof === undefined) { + for (const value of values) { + ++index; + if (value != null + && (max < value || (max === undefined && value >= value))) { + max = value, maxIndex = index; + } + } + } else { + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null + && (max < value || (max === undefined && value >= value))) { + max = value, maxIndex = index; + } + } + } + return maxIndex; +} + +function min$2(values, valueof) { + let min; + if (valueof === undefined) { + for (const value of values) { + if (value != null + && (min > value || (min === undefined && value >= value))) { + min = value; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null + && (min > value || (min === undefined && value >= value))) { + min = value; + } + } + } + return min; +} + +function minIndex(values, valueof) { + let min; + let minIndex = -1; + let index = -1; + if (valueof === undefined) { + for (const value of values) { + ++index; + if (value != null + && (min > value || (min === undefined && value >= value))) { + min = value, minIndex = index; + } + } + } else { + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null + && (min > value || (min === undefined && value >= value))) { + min = value, minIndex = index; + } + } + } + return minIndex; +} + +// Based on https://github.com/mourner/quickselect +// ISC license, Copyright 2018 Vladimir Agafonkin. +function quickselect(array, k, left = 0, right = Infinity, compare) { + k = Math.floor(k); + left = Math.floor(Math.max(0, left)); + right = Math.floor(Math.min(array.length - 1, right)); + + if (!(left <= k && k <= right)) return array; + + compare = compare === undefined ? ascendingDefined : compareDefined(compare); + + while (right > left) { + if (right - left > 600) { + const n = right - left + 1; + const m = k - left + 1; + const z = Math.log(n); + const s = 0.5 * Math.exp(2 * z / 3); + const sd = 0.5 * Math.sqrt(z * s * (n - s) / n) * (m - n / 2 < 0 ? -1 : 1); + const newLeft = Math.max(left, Math.floor(k - m * s / n + sd)); + const newRight = Math.min(right, Math.floor(k + (n - m) * s / n + sd)); + quickselect(array, k, newLeft, newRight, compare); + } + + const t = array[k]; + let i = left; + let j = right; + + swap$1(array, left, k); + if (compare(array[right], t) > 0) swap$1(array, left, right); + + while (i < j) { + swap$1(array, i, j), ++i, --j; + while (compare(array[i], t) < 0) ++i; + while (compare(array[j], t) > 0) --j; + } + + if (compare(array[left], t) === 0) swap$1(array, left, j); + else ++j, swap$1(array, j, right); + + if (j <= k) left = j + 1; + if (k <= j) right = j - 1; + } + + return array; +} + +function swap$1(array, i, j) { + const t = array[i]; + array[i] = array[j]; + array[j] = t; +} + +function greatest(values, compare = ascending$3) { + let max; + let defined = false; + if (compare.length === 1) { + let maxValue; + for (const element of values) { + const value = compare(element); + if (defined + ? ascending$3(value, maxValue) > 0 + : ascending$3(value, value) === 0) { + max = element; + maxValue = value; + defined = true; + } + } + } else { + for (const value of values) { + if (defined + ? compare(value, max) > 0 + : compare(value, value) === 0) { + max = value; + defined = true; + } + } + } + return max; +} + +function quantile$1(values, p, valueof) { + values = Float64Array.from(numbers(values, valueof)); + if (!(n = values.length) || isNaN(p = +p)) return; + if (p <= 0 || n < 2) return min$2(values); + if (p >= 1) return max$3(values); + var n, + i = (n - 1) * p, + i0 = Math.floor(i), + value0 = max$3(quickselect(values, i0).subarray(0, i0 + 1)), + value1 = min$2(values.subarray(i0 + 1)); + return value0 + (value1 - value0) * (i - i0); +} + +function quantileSorted(values, p, valueof = number$3) { + if (!(n = values.length) || isNaN(p = +p)) return; + if (p <= 0 || n < 2) return +valueof(values[0], 0, values); + if (p >= 1) return +valueof(values[n - 1], n - 1, values); + var n, + i = (n - 1) * p, + i0 = Math.floor(i), + value0 = +valueof(values[i0], i0, values), + value1 = +valueof(values[i0 + 1], i0 + 1, values); + return value0 + (value1 - value0) * (i - i0); +} + +function quantileIndex(values, p, valueof = number$3) { + if (isNaN(p = +p)) return; + numbers = Float64Array.from(values, (_, i) => number$3(valueof(values[i], i, values))); + if (p <= 0) return minIndex(numbers); + if (p >= 1) return maxIndex(numbers); + var numbers, + index = Uint32Array.from(values, (_, i) => i), + j = numbers.length - 1, + i = Math.floor(j * p); + quickselect(index, i, 0, j, (i, j) => ascendingDefined(numbers[i], numbers[j])); + i = greatest(index.subarray(0, i + 1), (i) => numbers[i]); + return i >= 0 ? i : -1; +} + +function thresholdFreedmanDiaconis(values, min, max) { + const c = count$1(values), d = quantile$1(values, 0.75) - quantile$1(values, 0.25); + return c && d ? Math.ceil((max - min) / (2 * d * Math.pow(c, -1 / 3))) : 1; +} + +function thresholdScott(values, min, max) { + const c = count$1(values), d = deviation(values); + return c && d ? Math.ceil((max - min) * Math.cbrt(c) / (3.49 * d)) : 1; +} + +function mean(values, valueof) { + let count = 0; + let sum = 0; + if (valueof === undefined) { + for (let value of values) { + if (value != null && (value = +value) >= value) { + ++count, sum += value; + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && (value = +value) >= value) { + ++count, sum += value; + } + } + } + if (count) return sum / count; +} + +function median(values, valueof) { + return quantile$1(values, 0.5, valueof); +} + +function medianIndex(values, valueof) { + return quantileIndex(values, 0.5, valueof); +} + +function* flatten(arrays) { + for (const array of arrays) { + yield* array; + } +} + +function merge(arrays) { + return Array.from(flatten(arrays)); +} + +function mode(values, valueof) { + const counts = new InternMap(); + if (valueof === undefined) { + for (let value of values) { + if (value != null && value >= value) { + counts.set(value, (counts.get(value) || 0) + 1); + } + } + } else { + let index = -1; + for (let value of values) { + if ((value = valueof(value, ++index, values)) != null && value >= value) { + counts.set(value, (counts.get(value) || 0) + 1); + } + } + } + let modeValue; + let modeCount = 0; + for (const [value, count] of counts) { + if (count > modeCount) { + modeCount = count; + modeValue = value; + } + } + return modeValue; +} + +function pairs(values, pairof = pair) { + const pairs = []; + let previous; + let first = false; + for (const value of values) { + if (first) pairs.push(pairof(previous, value)); + previous = value; + first = true; + } + return pairs; +} + +function pair(a, b) { + return [a, b]; +} + +function range$2(start, stop, step) { + start = +start, stop = +stop, step = (n = arguments.length) < 2 ? (stop = start, start = 0, 1) : n < 3 ? 1 : +step; + + var i = -1, + n = Math.max(0, Math.ceil((stop - start) / step)) | 0, + range = new Array(n); + + while (++i < n) { + range[i] = start + i * step; + } + + return range; +} + +function rank(values, valueof = ascending$3) { + if (typeof values[Symbol.iterator] !== "function") throw new TypeError("values is not iterable"); + let V = Array.from(values); + const R = new Float64Array(V.length); + if (valueof.length !== 2) V = V.map(valueof), valueof = ascending$3; + const compareIndex = (i, j) => valueof(V[i], V[j]); + let k, r; + values = Uint32Array.from(V, (_, i) => i); + // Risky chaining due to Safari 14 https://github.com/d3/d3-array/issues/123 + values.sort(valueof === ascending$3 ? (i, j) => ascendingDefined(V[i], V[j]) : compareDefined(compareIndex)); + values.forEach((j, i) => { + const c = compareIndex(j, k === undefined ? j : k); + if (c >= 0) { + if (k === undefined || c > 0) k = j, r = i; + R[j] = r; + } else { + R[j] = NaN; + } + }); + return R; +} + +function least(values, compare = ascending$3) { + let min; + let defined = false; + if (compare.length === 1) { + let minValue; + for (const element of values) { + const value = compare(element); + if (defined + ? ascending$3(value, minValue) < 0 + : ascending$3(value, value) === 0) { + min = element; + minValue = value; + defined = true; + } + } + } else { + for (const value of values) { + if (defined + ? compare(value, min) < 0 + : compare(value, value) === 0) { + min = value; + defined = true; + } + } + } + return min; +} + +function leastIndex(values, compare = ascending$3) { + if (compare.length === 1) return minIndex(values, compare); + let minValue; + let min = -1; + let index = -1; + for (const value of values) { + ++index; + if (min < 0 + ? compare(value, value) === 0 + : compare(value, minValue) < 0) { + minValue = value; + min = index; + } + } + return min; +} + +function greatestIndex(values, compare = ascending$3) { + if (compare.length === 1) return maxIndex(values, compare); + let maxValue; + let max = -1; + let index = -1; + for (const value of values) { + ++index; + if (max < 0 + ? compare(value, value) === 0 + : compare(value, maxValue) > 0) { + maxValue = value; + max = index; + } + } + return max; +} + +function scan(values, compare) { + const index = leastIndex(values, compare); + return index < 0 ? undefined : index; +} + +var shuffle$1 = shuffler(Math.random); + +function shuffler(random) { + return function shuffle(array, i0 = 0, i1 = array.length) { + let m = i1 - (i0 = +i0); + while (m) { + const i = random() * m-- | 0, t = array[m + i0]; + array[m + i0] = array[i + i0]; + array[i + i0] = t; + } + return array; + }; +} + +function sum$2(values, valueof) { + let sum = 0; + if (valueof === undefined) { + for (let value of values) { + if (value = +value) { + sum += value; + } + } + } else { + let index = -1; + for (let value of values) { + if (value = +valueof(value, ++index, values)) { + sum += value; + } + } + } + return sum; +} + +function transpose(matrix) { + if (!(n = matrix.length)) return []; + for (var i = -1, m = min$2(matrix, length$2), transpose = new Array(m); ++i < m;) { + for (var j = -1, n, row = transpose[i] = new Array(n); ++j < n;) { + row[j] = matrix[j][i]; + } + } + return transpose; +} + +function length$2(d) { + return d.length; +} + +function zip() { + return transpose(arguments); +} + +function every(values, test) { + if (typeof test !== "function") throw new TypeError("test is not a function"); + let index = -1; + for (const value of values) { + if (!test(value, ++index, values)) { + return false; + } + } + return true; +} + +function some(values, test) { + if (typeof test !== "function") throw new TypeError("test is not a function"); + let index = -1; + for (const value of values) { + if (test(value, ++index, values)) { + return true; + } + } + return false; +} + +function filter$1(values, test) { + if (typeof test !== "function") throw new TypeError("test is not a function"); + const array = []; + let index = -1; + for (const value of values) { + if (test(value, ++index, values)) { + array.push(value); + } + } + return array; +} + +function map$1(values, mapper) { + if (typeof values[Symbol.iterator] !== "function") throw new TypeError("values is not iterable"); + if (typeof mapper !== "function") throw new TypeError("mapper is not a function"); + return Array.from(values, (value, index) => mapper(value, index, values)); +} + +function reduce(values, reducer, value) { + if (typeof reducer !== "function") throw new TypeError("reducer is not a function"); + const iterator = values[Symbol.iterator](); + let done, next, index = -1; + if (arguments.length < 3) { + ({done, value} = iterator.next()); + if (done) return; + ++index; + } + while (({done, value: next} = iterator.next()), !done) { + value = reducer(value, next, ++index, values); + } + return value; +} + +function reverse$1(values) { + if (typeof values[Symbol.iterator] !== "function") throw new TypeError("values is not iterable"); + return Array.from(values).reverse(); +} + +function difference(values, ...others) { + values = new InternSet(values); + for (const other of others) { + for (const value of other) { + values.delete(value); + } + } + return values; +} + +function disjoint(values, other) { + const iterator = other[Symbol.iterator](), set = new InternSet(); + for (const v of values) { + if (set.has(v)) return false; + let value, done; + while (({value, done} = iterator.next())) { + if (done) break; + if (Object.is(v, value)) return false; + set.add(value); + } + } + return true; +} + +function intersection(values, ...others) { + values = new InternSet(values); + others = others.map(set$2); + out: for (const value of values) { + for (const other of others) { + if (!other.has(value)) { + values.delete(value); + continue out; + } + } + } + return values; +} + +function set$2(values) { + return values instanceof InternSet ? values : new InternSet(values); +} + +function superset(values, other) { + const iterator = values[Symbol.iterator](), set = new Set(); + for (const o of other) { + const io = intern(o); + if (set.has(io)) continue; + let value, done; + while (({value, done} = iterator.next())) { + if (done) return false; + const ivalue = intern(value); + set.add(ivalue); + if (Object.is(io, ivalue)) break; + } + } + return true; +} + +function intern(value) { + return value !== null && typeof value === "object" ? value.valueOf() : value; +} + +function subset(values, other) { + return superset(other, values); +} + +function union(...others) { + const set = new InternSet(); + for (const other of others) { + for (const o of other) { + set.add(o); + } + } + return set; +} + +function identity$8(x) { + return x; +} + +var top = 1, + right = 2, + bottom = 3, + left = 4, + epsilon$6 = 1e-6; + +function translateX(x) { + return "translate(" + x + ",0)"; +} + +function translateY(y) { + return "translate(0," + y + ")"; +} + +function number$2(scale) { + return d => +scale(d); +} + +function center$1(scale, offset) { + offset = Math.max(0, scale.bandwidth() - offset * 2) / 2; + if (scale.round()) offset = Math.round(offset); + return d => +scale(d) + offset; +} + +function entering() { + return !this.__axis; +} + +function axis(orient, scale) { + var tickArguments = [], + tickValues = null, + tickFormat = null, + tickSizeInner = 6, + tickSizeOuter = 6, + tickPadding = 3, + offset = typeof window !== "undefined" && window.devicePixelRatio > 1 ? 0 : 0.5, + k = orient === top || orient === left ? -1 : 1, + x = orient === left || orient === right ? "x" : "y", + transform = orient === top || orient === bottom ? translateX : translateY; + + function axis(context) { + var values = tickValues == null ? (scale.ticks ? scale.ticks.apply(scale, tickArguments) : scale.domain()) : tickValues, + format = tickFormat == null ? (scale.tickFormat ? scale.tickFormat.apply(scale, tickArguments) : identity$8) : tickFormat, + spacing = Math.max(tickSizeInner, 0) + tickPadding, + range = scale.range(), + range0 = +range[0] + offset, + range1 = +range[range.length - 1] + offset, + position = (scale.bandwidth ? center$1 : number$2)(scale.copy(), offset), + selection = context.selection ? context.selection() : context, + path = selection.selectAll(".domain").data([null]), + tick = selection.selectAll(".tick").data(values, scale).order(), + tickExit = tick.exit(), + tickEnter = tick.enter().append("g").attr("class", "tick"), + line = tick.select("line"), + text = tick.select("text"); + + path = path.merge(path.enter().insert("path", ".tick") + .attr("class", "domain") + .attr("stroke", "currentColor")); + + tick = tick.merge(tickEnter); + + line = line.merge(tickEnter.append("line") + .attr("stroke", "currentColor") + .attr(x + "2", k * tickSizeInner)); + + text = text.merge(tickEnter.append("text") + .attr("fill", "currentColor") + .attr(x, k * spacing) + .attr("dy", orient === top ? "0em" : orient === bottom ? "0.71em" : "0.32em")); + + if (context !== selection) { + path = path.transition(context); + tick = tick.transition(context); + line = line.transition(context); + text = text.transition(context); + + tickExit = tickExit.transition(context) + .attr("opacity", epsilon$6) + .attr("transform", function(d) { return isFinite(d = position(d)) ? transform(d + offset) : this.getAttribute("transform"); }); + + tickEnter + .attr("opacity", epsilon$6) + .attr("transform", function(d) { var p = this.parentNode.__axis; return transform((p && isFinite(p = p(d)) ? p : position(d)) + offset); }); + } + + tickExit.remove(); + + path + .attr("d", orient === left || orient === right + ? (tickSizeOuter ? "M" + k * tickSizeOuter + "," + range0 + "H" + offset + "V" + range1 + "H" + k * tickSizeOuter : "M" + offset + "," + range0 + "V" + range1) + : (tickSizeOuter ? "M" + range0 + "," + k * tickSizeOuter + "V" + offset + "H" + range1 + "V" + k * tickSizeOuter : "M" + range0 + "," + offset + "H" + range1)); + + tick + .attr("opacity", 1) + .attr("transform", function(d) { return transform(position(d) + offset); }); + + line + .attr(x + "2", k * tickSizeInner); + + text + .attr(x, k * spacing) + .text(format); + + selection.filter(entering) + .attr("fill", "none") + .attr("font-size", 10) + .attr("font-family", "sans-serif") + .attr("text-anchor", orient === right ? "start" : orient === left ? "end" : "middle"); + + selection + .each(function() { this.__axis = position; }); + } + + axis.scale = function(_) { + return arguments.length ? (scale = _, axis) : scale; + }; + + axis.ticks = function() { + return tickArguments = Array.from(arguments), axis; + }; + + axis.tickArguments = function(_) { + return arguments.length ? (tickArguments = _ == null ? [] : Array.from(_), axis) : tickArguments.slice(); + }; + + axis.tickValues = function(_) { + return arguments.length ? (tickValues = _ == null ? null : Array.from(_), axis) : tickValues && tickValues.slice(); + }; + + axis.tickFormat = function(_) { + return arguments.length ? (tickFormat = _, axis) : tickFormat; + }; + + axis.tickSize = function(_) { + return arguments.length ? (tickSizeInner = tickSizeOuter = +_, axis) : tickSizeInner; + }; + + axis.tickSizeInner = function(_) { + return arguments.length ? (tickSizeInner = +_, axis) : tickSizeInner; + }; + + axis.tickSizeOuter = function(_) { + return arguments.length ? (tickSizeOuter = +_, axis) : tickSizeOuter; + }; + + axis.tickPadding = function(_) { + return arguments.length ? (tickPadding = +_, axis) : tickPadding; + }; + + axis.offset = function(_) { + return arguments.length ? (offset = +_, axis) : offset; + }; + + return axis; +} + +function axisTop(scale) { + return axis(top, scale); +} + +function axisRight(scale) { + return axis(right, scale); +} + +function axisBottom(scale) { + return axis(bottom, scale); +} + +function axisLeft(scale) { + return axis(left, scale); +} + +var noop$3 = {value: () => {}}; + +function dispatch() { + for (var i = 0, n = arguments.length, _ = {}, t; i < n; ++i) { + if (!(t = arguments[i] + "") || (t in _) || /[\s.]/.test(t)) throw new Error("illegal type: " + t); + _[t] = []; + } + return new Dispatch(_); +} + +function Dispatch(_) { + this._ = _; +} + +function parseTypenames$1(typenames, types) { + return typenames.trim().split(/^|\s+/).map(function(t) { + var name = "", i = t.indexOf("."); + if (i >= 0) name = t.slice(i + 1), t = t.slice(0, i); + if (t && !types.hasOwnProperty(t)) throw new Error("unknown type: " + t); + return {type: t, name: name}; + }); +} + +Dispatch.prototype = dispatch.prototype = { + constructor: Dispatch, + on: function(typename, callback) { + var _ = this._, + T = parseTypenames$1(typename + "", _), + t, + i = -1, + n = T.length; + + // If no callback was specified, return the callback of the given type and name. + if (arguments.length < 2) { + while (++i < n) if ((t = (typename = T[i]).type) && (t = get$1(_[t], typename.name))) return t; + return; + } + + // If a type was specified, set the callback for the given type and name. + // Otherwise, if a null callback was specified, remove callbacks of the given name. + if (callback != null && typeof callback !== "function") throw new Error("invalid callback: " + callback); + while (++i < n) { + if (t = (typename = T[i]).type) _[t] = set$1(_[t], typename.name, callback); + else if (callback == null) for (t in _) _[t] = set$1(_[t], typename.name, null); + } + + return this; + }, + copy: function() { + var copy = {}, _ = this._; + for (var t in _) copy[t] = _[t].slice(); + return new Dispatch(copy); + }, + call: function(type, that) { + if ((n = arguments.length - 2) > 0) for (var args = new Array(n), i = 0, n, t; i < n; ++i) args[i] = arguments[i + 2]; + if (!this._.hasOwnProperty(type)) throw new Error("unknown type: " + type); + for (t = this._[type], i = 0, n = t.length; i < n; ++i) t[i].value.apply(that, args); + }, + apply: function(type, that, args) { + if (!this._.hasOwnProperty(type)) throw new Error("unknown type: " + type); + for (var t = this._[type], i = 0, n = t.length; i < n; ++i) t[i].value.apply(that, args); + } +}; + +function get$1(type, name) { + for (var i = 0, n = type.length, c; i < n; ++i) { + if ((c = type[i]).name === name) { + return c.value; + } + } +} + +function set$1(type, name, callback) { + for (var i = 0, n = type.length; i < n; ++i) { + if (type[i].name === name) { + type[i] = noop$3, type = type.slice(0, i).concat(type.slice(i + 1)); + break; + } + } + if (callback != null) type.push({name: name, value: callback}); + return type; +} + +var xhtml = "http://www.w3.org/1999/xhtml"; + +var namespaces = { + svg: "http://www.w3.org/2000/svg", + xhtml: xhtml, + xlink: "http://www.w3.org/1999/xlink", + xml: "http://www.w3.org/XML/1998/namespace", + xmlns: "http://www.w3.org/2000/xmlns/" +}; + +function namespace(name) { + var prefix = name += "", i = prefix.indexOf(":"); + if (i >= 0 && (prefix = name.slice(0, i)) !== "xmlns") name = name.slice(i + 1); + return namespaces.hasOwnProperty(prefix) ? {space: namespaces[prefix], local: name} : name; // eslint-disable-line no-prototype-builtins +} + +function creatorInherit(name) { + return function() { + var document = this.ownerDocument, + uri = this.namespaceURI; + return uri === xhtml && document.documentElement.namespaceURI === xhtml + ? document.createElement(name) + : document.createElementNS(uri, name); + }; +} + +function creatorFixed(fullname) { + return function() { + return this.ownerDocument.createElementNS(fullname.space, fullname.local); + }; +} + +function creator(name) { + var fullname = namespace(name); + return (fullname.local + ? creatorFixed + : creatorInherit)(fullname); +} + +function none$2() {} + +function selector(selector) { + return selector == null ? none$2 : function() { + return this.querySelector(selector); + }; +} + +function selection_select(select) { + if (typeof select !== "function") select = selector(select); + + for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, subgroup = subgroups[j] = new Array(n), node, subnode, i = 0; i < n; ++i) { + if ((node = group[i]) && (subnode = select.call(node, node.__data__, i, group))) { + if ("__data__" in node) subnode.__data__ = node.__data__; + subgroup[i] = subnode; + } + } + } + + return new Selection$1(subgroups, this._parents); +} + +// Given something array like (or null), returns something that is strictly an +// array. This is used to ensure that array-like objects passed to d3.selectAll +// or selection.selectAll are converted into proper arrays when creating a +// selection; we don’t ever want to create a selection backed by a live +// HTMLCollection or NodeList. However, note that selection.selectAll will use a +// static NodeList as a group, since it safely derived from querySelectorAll. +function array$4(x) { + return x == null ? [] : Array.isArray(x) ? x : Array.from(x); +} + +function empty$1() { + return []; +} + +function selectorAll(selector) { + return selector == null ? empty$1 : function() { + return this.querySelectorAll(selector); + }; +} + +function arrayAll(select) { + return function() { + return array$4(select.apply(this, arguments)); + }; +} + +function selection_selectAll(select) { + if (typeof select === "function") select = arrayAll(select); + else select = selectorAll(select); + + for (var groups = this._groups, m = groups.length, subgroups = [], parents = [], j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) { + if (node = group[i]) { + subgroups.push(select.call(node, node.__data__, i, group)); + parents.push(node); + } + } + } + + return new Selection$1(subgroups, parents); +} + +function matcher(selector) { + return function() { + return this.matches(selector); + }; +} + +function childMatcher(selector) { + return function(node) { + return node.matches(selector); + }; +} + +var find$1 = Array.prototype.find; + +function childFind(match) { + return function() { + return find$1.call(this.children, match); + }; +} + +function childFirst() { + return this.firstElementChild; +} + +function selection_selectChild(match) { + return this.select(match == null ? childFirst + : childFind(typeof match === "function" ? match : childMatcher(match))); +} + +var filter = Array.prototype.filter; + +function children() { + return Array.from(this.children); +} + +function childrenFilter(match) { + return function() { + return filter.call(this.children, match); + }; +} + +function selection_selectChildren(match) { + return this.selectAll(match == null ? children + : childrenFilter(typeof match === "function" ? match : childMatcher(match))); +} + +function selection_filter(match) { + if (typeof match !== "function") match = matcher(match); + + for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, subgroup = subgroups[j] = [], node, i = 0; i < n; ++i) { + if ((node = group[i]) && match.call(node, node.__data__, i, group)) { + subgroup.push(node); + } + } + } + + return new Selection$1(subgroups, this._parents); +} + +function sparse(update) { + return new Array(update.length); +} + +function selection_enter() { + return new Selection$1(this._enter || this._groups.map(sparse), this._parents); +} + +function EnterNode(parent, datum) { + this.ownerDocument = parent.ownerDocument; + this.namespaceURI = parent.namespaceURI; + this._next = null; + this._parent = parent; + this.__data__ = datum; +} + +EnterNode.prototype = { + constructor: EnterNode, + appendChild: function(child) { return this._parent.insertBefore(child, this._next); }, + insertBefore: function(child, next) { return this._parent.insertBefore(child, next); }, + querySelector: function(selector) { return this._parent.querySelector(selector); }, + querySelectorAll: function(selector) { return this._parent.querySelectorAll(selector); } +}; + +function constant$a(x) { + return function() { + return x; + }; +} + +function bindIndex(parent, group, enter, update, exit, data) { + var i = 0, + node, + groupLength = group.length, + dataLength = data.length; + + // Put any non-null nodes that fit into update. + // Put any null nodes into enter. + // Put any remaining data into enter. + for (; i < dataLength; ++i) { + if (node = group[i]) { + node.__data__ = data[i]; + update[i] = node; + } else { + enter[i] = new EnterNode(parent, data[i]); + } + } + + // Put any non-null nodes that don’t fit into exit. + for (; i < groupLength; ++i) { + if (node = group[i]) { + exit[i] = node; + } + } +} + +function bindKey(parent, group, enter, update, exit, data, key) { + var i, + node, + nodeByKeyValue = new Map, + groupLength = group.length, + dataLength = data.length, + keyValues = new Array(groupLength), + keyValue; + + // Compute the key for each node. + // If multiple nodes have the same key, the duplicates are added to exit. + for (i = 0; i < groupLength; ++i) { + if (node = group[i]) { + keyValues[i] = keyValue = key.call(node, node.__data__, i, group) + ""; + if (nodeByKeyValue.has(keyValue)) { + exit[i] = node; + } else { + nodeByKeyValue.set(keyValue, node); + } + } + } + + // Compute the key for each datum. + // If there a node associated with this key, join and add it to update. + // If there is not (or the key is a duplicate), add it to enter. + for (i = 0; i < dataLength; ++i) { + keyValue = key.call(parent, data[i], i, data) + ""; + if (node = nodeByKeyValue.get(keyValue)) { + update[i] = node; + node.__data__ = data[i]; + nodeByKeyValue.delete(keyValue); + } else { + enter[i] = new EnterNode(parent, data[i]); + } + } + + // Add any remaining nodes that were not bound to data to exit. + for (i = 0; i < groupLength; ++i) { + if ((node = group[i]) && (nodeByKeyValue.get(keyValues[i]) === node)) { + exit[i] = node; + } + } +} + +function datum(node) { + return node.__data__; +} + +function selection_data(value, key) { + if (!arguments.length) return Array.from(this, datum); + + var bind = key ? bindKey : bindIndex, + parents = this._parents, + groups = this._groups; + + if (typeof value !== "function") value = constant$a(value); + + for (var m = groups.length, update = new Array(m), enter = new Array(m), exit = new Array(m), j = 0; j < m; ++j) { + var parent = parents[j], + group = groups[j], + groupLength = group.length, + data = arraylike(value.call(parent, parent && parent.__data__, j, parents)), + dataLength = data.length, + enterGroup = enter[j] = new Array(dataLength), + updateGroup = update[j] = new Array(dataLength), + exitGroup = exit[j] = new Array(groupLength); + + bind(parent, group, enterGroup, updateGroup, exitGroup, data, key); + + // Now connect the enter nodes to their following update node, such that + // appendChild can insert the materialized enter node before this node, + // rather than at the end of the parent node. + for (var i0 = 0, i1 = 0, previous, next; i0 < dataLength; ++i0) { + if (previous = enterGroup[i0]) { + if (i0 >= i1) i1 = i0 + 1; + while (!(next = updateGroup[i1]) && ++i1 < dataLength); + previous._next = next || null; + } + } + } + + update = new Selection$1(update, parents); + update._enter = enter; + update._exit = exit; + return update; +} + +// Given some data, this returns an array-like view of it: an object that +// exposes a length property and allows numeric indexing. Note that unlike +// selectAll, this isn’t worried about “live” collections because the resulting +// array will only be used briefly while data is being bound. (It is possible to +// cause the data to change while iterating by using a key function, but please +// don’t; we’d rather avoid a gratuitous copy.) +function arraylike(data) { + return typeof data === "object" && "length" in data + ? data // Array, TypedArray, NodeList, array-like + : Array.from(data); // Map, Set, iterable, string, or anything else +} + +function selection_exit() { + return new Selection$1(this._exit || this._groups.map(sparse), this._parents); +} + +function selection_join(onenter, onupdate, onexit) { + var enter = this.enter(), update = this, exit = this.exit(); + if (typeof onenter === "function") { + enter = onenter(enter); + if (enter) enter = enter.selection(); + } else { + enter = enter.append(onenter + ""); + } + if (onupdate != null) { + update = onupdate(update); + if (update) update = update.selection(); + } + if (onexit == null) exit.remove(); else onexit(exit); + return enter && update ? enter.merge(update).order() : update; +} + +function selection_merge(context) { + var selection = context.selection ? context.selection() : context; + + for (var groups0 = this._groups, groups1 = selection._groups, m0 = groups0.length, m1 = groups1.length, m = Math.min(m0, m1), merges = new Array(m0), j = 0; j < m; ++j) { + for (var group0 = groups0[j], group1 = groups1[j], n = group0.length, merge = merges[j] = new Array(n), node, i = 0; i < n; ++i) { + if (node = group0[i] || group1[i]) { + merge[i] = node; + } + } + } + + for (; j < m0; ++j) { + merges[j] = groups0[j]; + } + + return new Selection$1(merges, this._parents); +} + +function selection_order() { + + for (var groups = this._groups, j = -1, m = groups.length; ++j < m;) { + for (var group = groups[j], i = group.length - 1, next = group[i], node; --i >= 0;) { + if (node = group[i]) { + if (next && node.compareDocumentPosition(next) ^ 4) next.parentNode.insertBefore(node, next); + next = node; + } + } + } + + return this; +} + +function selection_sort(compare) { + if (!compare) compare = ascending$2; + + function compareNode(a, b) { + return a && b ? compare(a.__data__, b.__data__) : !a - !b; + } + + for (var groups = this._groups, m = groups.length, sortgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, sortgroup = sortgroups[j] = new Array(n), node, i = 0; i < n; ++i) { + if (node = group[i]) { + sortgroup[i] = node; + } + } + sortgroup.sort(compareNode); + } + + return new Selection$1(sortgroups, this._parents).order(); +} + +function ascending$2(a, b) { + return a < b ? -1 : a > b ? 1 : a >= b ? 0 : NaN; +} + +function selection_call() { + var callback = arguments[0]; + arguments[0] = this; + callback.apply(null, arguments); + return this; +} + +function selection_nodes() { + return Array.from(this); +} + +function selection_node() { + + for (var groups = this._groups, j = 0, m = groups.length; j < m; ++j) { + for (var group = groups[j], i = 0, n = group.length; i < n; ++i) { + var node = group[i]; + if (node) return node; + } + } + + return null; +} + +function selection_size() { + let size = 0; + for (const node of this) ++size; // eslint-disable-line no-unused-vars + return size; +} + +function selection_empty() { + return !this.node(); +} + +function selection_each(callback) { + + for (var groups = this._groups, j = 0, m = groups.length; j < m; ++j) { + for (var group = groups[j], i = 0, n = group.length, node; i < n; ++i) { + if (node = group[i]) callback.call(node, node.__data__, i, group); + } + } + + return this; +} + +function attrRemove$1(name) { + return function() { + this.removeAttribute(name); + }; +} + +function attrRemoveNS$1(fullname) { + return function() { + this.removeAttributeNS(fullname.space, fullname.local); + }; +} + +function attrConstant$1(name, value) { + return function() { + this.setAttribute(name, value); + }; +} + +function attrConstantNS$1(fullname, value) { + return function() { + this.setAttributeNS(fullname.space, fullname.local, value); + }; +} + +function attrFunction$1(name, value) { + return function() { + var v = value.apply(this, arguments); + if (v == null) this.removeAttribute(name); + else this.setAttribute(name, v); + }; +} + +function attrFunctionNS$1(fullname, value) { + return function() { + var v = value.apply(this, arguments); + if (v == null) this.removeAttributeNS(fullname.space, fullname.local); + else this.setAttributeNS(fullname.space, fullname.local, v); + }; +} + +function selection_attr(name, value) { + var fullname = namespace(name); + + if (arguments.length < 2) { + var node = this.node(); + return fullname.local + ? node.getAttributeNS(fullname.space, fullname.local) + : node.getAttribute(fullname); + } + + return this.each((value == null + ? (fullname.local ? attrRemoveNS$1 : attrRemove$1) : (typeof value === "function" + ? (fullname.local ? attrFunctionNS$1 : attrFunction$1) + : (fullname.local ? attrConstantNS$1 : attrConstant$1)))(fullname, value)); +} + +function defaultView(node) { + return (node.ownerDocument && node.ownerDocument.defaultView) // node is a Node + || (node.document && node) // node is a Window + || node.defaultView; // node is a Document +} + +function styleRemove$1(name) { + return function() { + this.style.removeProperty(name); + }; +} + +function styleConstant$1(name, value, priority) { + return function() { + this.style.setProperty(name, value, priority); + }; +} + +function styleFunction$1(name, value, priority) { + return function() { + var v = value.apply(this, arguments); + if (v == null) this.style.removeProperty(name); + else this.style.setProperty(name, v, priority); + }; +} + +function selection_style(name, value, priority) { + return arguments.length > 1 + ? this.each((value == null + ? styleRemove$1 : typeof value === "function" + ? styleFunction$1 + : styleConstant$1)(name, value, priority == null ? "" : priority)) + : styleValue(this.node(), name); +} + +function styleValue(node, name) { + return node.style.getPropertyValue(name) + || defaultView(node).getComputedStyle(node, null).getPropertyValue(name); +} + +function propertyRemove(name) { + return function() { + delete this[name]; + }; +} + +function propertyConstant(name, value) { + return function() { + this[name] = value; + }; +} + +function propertyFunction(name, value) { + return function() { + var v = value.apply(this, arguments); + if (v == null) delete this[name]; + else this[name] = v; + }; +} + +function selection_property(name, value) { + return arguments.length > 1 + ? this.each((value == null + ? propertyRemove : typeof value === "function" + ? propertyFunction + : propertyConstant)(name, value)) + : this.node()[name]; +} + +function classArray(string) { + return string.trim().split(/^|\s+/); +} + +function classList(node) { + return node.classList || new ClassList(node); +} + +function ClassList(node) { + this._node = node; + this._names = classArray(node.getAttribute("class") || ""); +} + +ClassList.prototype = { + add: function(name) { + var i = this._names.indexOf(name); + if (i < 0) { + this._names.push(name); + this._node.setAttribute("class", this._names.join(" ")); + } + }, + remove: function(name) { + var i = this._names.indexOf(name); + if (i >= 0) { + this._names.splice(i, 1); + this._node.setAttribute("class", this._names.join(" ")); + } + }, + contains: function(name) { + return this._names.indexOf(name) >= 0; + } +}; + +function classedAdd(node, names) { + var list = classList(node), i = -1, n = names.length; + while (++i < n) list.add(names[i]); +} + +function classedRemove(node, names) { + var list = classList(node), i = -1, n = names.length; + while (++i < n) list.remove(names[i]); +} + +function classedTrue(names) { + return function() { + classedAdd(this, names); + }; +} + +function classedFalse(names) { + return function() { + classedRemove(this, names); + }; +} + +function classedFunction(names, value) { + return function() { + (value.apply(this, arguments) ? classedAdd : classedRemove)(this, names); + }; +} + +function selection_classed(name, value) { + var names = classArray(name + ""); + + if (arguments.length < 2) { + var list = classList(this.node()), i = -1, n = names.length; + while (++i < n) if (!list.contains(names[i])) return false; + return true; + } + + return this.each((typeof value === "function" + ? classedFunction : value + ? classedTrue + : classedFalse)(names, value)); +} + +function textRemove() { + this.textContent = ""; +} + +function textConstant$1(value) { + return function() { + this.textContent = value; + }; +} + +function textFunction$1(value) { + return function() { + var v = value.apply(this, arguments); + this.textContent = v == null ? "" : v; + }; +} + +function selection_text(value) { + return arguments.length + ? this.each(value == null + ? textRemove : (typeof value === "function" + ? textFunction$1 + : textConstant$1)(value)) + : this.node().textContent; +} + +function htmlRemove() { + this.innerHTML = ""; +} + +function htmlConstant(value) { + return function() { + this.innerHTML = value; + }; +} + +function htmlFunction(value) { + return function() { + var v = value.apply(this, arguments); + this.innerHTML = v == null ? "" : v; + }; +} + +function selection_html(value) { + return arguments.length + ? this.each(value == null + ? htmlRemove : (typeof value === "function" + ? htmlFunction + : htmlConstant)(value)) + : this.node().innerHTML; +} + +function raise() { + if (this.nextSibling) this.parentNode.appendChild(this); +} + +function selection_raise() { + return this.each(raise); +} + +function lower() { + if (this.previousSibling) this.parentNode.insertBefore(this, this.parentNode.firstChild); +} + +function selection_lower() { + return this.each(lower); +} + +function selection_append(name) { + var create = typeof name === "function" ? name : creator(name); + return this.select(function() { + return this.appendChild(create.apply(this, arguments)); + }); +} + +function constantNull() { + return null; +} + +function selection_insert(name, before) { + var create = typeof name === "function" ? name : creator(name), + select = before == null ? constantNull : typeof before === "function" ? before : selector(before); + return this.select(function() { + return this.insertBefore(create.apply(this, arguments), select.apply(this, arguments) || null); + }); +} + +function remove() { + var parent = this.parentNode; + if (parent) parent.removeChild(this); +} + +function selection_remove() { + return this.each(remove); +} + +function selection_cloneShallow() { + var clone = this.cloneNode(false), parent = this.parentNode; + return parent ? parent.insertBefore(clone, this.nextSibling) : clone; +} + +function selection_cloneDeep() { + var clone = this.cloneNode(true), parent = this.parentNode; + return parent ? parent.insertBefore(clone, this.nextSibling) : clone; +} + +function selection_clone(deep) { + return this.select(deep ? selection_cloneDeep : selection_cloneShallow); +} + +function selection_datum(value) { + return arguments.length + ? this.property("__data__", value) + : this.node().__data__; +} + +function contextListener(listener) { + return function(event) { + listener.call(this, event, this.__data__); + }; +} + +function parseTypenames(typenames) { + return typenames.trim().split(/^|\s+/).map(function(t) { + var name = "", i = t.indexOf("."); + if (i >= 0) name = t.slice(i + 1), t = t.slice(0, i); + return {type: t, name: name}; + }); +} + +function onRemove(typename) { + return function() { + var on = this.__on; + if (!on) return; + for (var j = 0, i = -1, m = on.length, o; j < m; ++j) { + if (o = on[j], (!typename.type || o.type === typename.type) && o.name === typename.name) { + this.removeEventListener(o.type, o.listener, o.options); + } else { + on[++i] = o; + } + } + if (++i) on.length = i; + else delete this.__on; + }; +} + +function onAdd(typename, value, options) { + return function() { + var on = this.__on, o, listener = contextListener(value); + if (on) for (var j = 0, m = on.length; j < m; ++j) { + if ((o = on[j]).type === typename.type && o.name === typename.name) { + this.removeEventListener(o.type, o.listener, o.options); + this.addEventListener(o.type, o.listener = listener, o.options = options); + o.value = value; + return; + } + } + this.addEventListener(typename.type, listener, options); + o = {type: typename.type, name: typename.name, value: value, listener: listener, options: options}; + if (!on) this.__on = [o]; + else on.push(o); + }; +} + +function selection_on(typename, value, options) { + var typenames = parseTypenames(typename + ""), i, n = typenames.length, t; + + if (arguments.length < 2) { + var on = this.node().__on; + if (on) for (var j = 0, m = on.length, o; j < m; ++j) { + for (i = 0, o = on[j]; i < n; ++i) { + if ((t = typenames[i]).type === o.type && t.name === o.name) { + return o.value; + } + } + } + return; + } + + on = value ? onAdd : onRemove; + for (i = 0; i < n; ++i) this.each(on(typenames[i], value, options)); + return this; +} + +function dispatchEvent(node, type, params) { + var window = defaultView(node), + event = window.CustomEvent; + + if (typeof event === "function") { + event = new event(type, params); + } else { + event = window.document.createEvent("Event"); + if (params) event.initEvent(type, params.bubbles, params.cancelable), event.detail = params.detail; + else event.initEvent(type, false, false); + } + + node.dispatchEvent(event); +} + +function dispatchConstant(type, params) { + return function() { + return dispatchEvent(this, type, params); + }; +} + +function dispatchFunction(type, params) { + return function() { + return dispatchEvent(this, type, params.apply(this, arguments)); + }; +} + +function selection_dispatch(type, params) { + return this.each((typeof params === "function" + ? dispatchFunction + : dispatchConstant)(type, params)); +} + +function* selection_iterator() { + for (var groups = this._groups, j = 0, m = groups.length; j < m; ++j) { + for (var group = groups[j], i = 0, n = group.length, node; i < n; ++i) { + if (node = group[i]) yield node; + } + } +} + +var root$1 = [null]; + +function Selection$1(groups, parents) { + this._groups = groups; + this._parents = parents; +} + +function selection() { + return new Selection$1([[document.documentElement]], root$1); +} + +function selection_selection() { + return this; +} + +Selection$1.prototype = selection.prototype = { + constructor: Selection$1, + select: selection_select, + selectAll: selection_selectAll, + selectChild: selection_selectChild, + selectChildren: selection_selectChildren, + filter: selection_filter, + data: selection_data, + enter: selection_enter, + exit: selection_exit, + join: selection_join, + merge: selection_merge, + selection: selection_selection, + order: selection_order, + sort: selection_sort, + call: selection_call, + nodes: selection_nodes, + node: selection_node, + size: selection_size, + empty: selection_empty, + each: selection_each, + attr: selection_attr, + style: selection_style, + property: selection_property, + classed: selection_classed, + text: selection_text, + html: selection_html, + raise: selection_raise, + lower: selection_lower, + append: selection_append, + insert: selection_insert, + remove: selection_remove, + clone: selection_clone, + datum: selection_datum, + on: selection_on, + dispatch: selection_dispatch, + [Symbol.iterator]: selection_iterator +}; + +function select(selector) { + return typeof selector === "string" + ? new Selection$1([[document.querySelector(selector)]], [document.documentElement]) + : new Selection$1([[selector]], root$1); +} + +function create$1(name) { + return select(creator(name).call(document.documentElement)); +} + +var nextId = 0; + +function local$1() { + return new Local; +} + +function Local() { + this._ = "@" + (++nextId).toString(36); +} + +Local.prototype = local$1.prototype = { + constructor: Local, + get: function(node) { + var id = this._; + while (!(id in node)) if (!(node = node.parentNode)) return; + return node[id]; + }, + set: function(node, value) { + return node[this._] = value; + }, + remove: function(node) { + return this._ in node && delete node[this._]; + }, + toString: function() { + return this._; + } +}; + +function sourceEvent(event) { + let sourceEvent; + while (sourceEvent = event.sourceEvent) event = sourceEvent; + return event; +} + +function pointer(event, node) { + event = sourceEvent(event); + if (node === undefined) node = event.currentTarget; + if (node) { + var svg = node.ownerSVGElement || node; + if (svg.createSVGPoint) { + var point = svg.createSVGPoint(); + point.x = event.clientX, point.y = event.clientY; + point = point.matrixTransform(node.getScreenCTM().inverse()); + return [point.x, point.y]; + } + if (node.getBoundingClientRect) { + var rect = node.getBoundingClientRect(); + return [event.clientX - rect.left - node.clientLeft, event.clientY - rect.top - node.clientTop]; + } + } + return [event.pageX, event.pageY]; +} + +function pointers(events, node) { + if (events.target) { // i.e., instanceof Event, not TouchList or iterable + events = sourceEvent(events); + if (node === undefined) node = events.currentTarget; + events = events.touches || [events]; + } + return Array.from(events, event => pointer(event, node)); +} + +function selectAll(selector) { + return typeof selector === "string" + ? new Selection$1([document.querySelectorAll(selector)], [document.documentElement]) + : new Selection$1([array$4(selector)], root$1); +} + +// These are typically used in conjunction with noevent to ensure that we can +// preventDefault on the event. +const nonpassive = {passive: false}; +const nonpassivecapture = {capture: true, passive: false}; + +function nopropagation$2(event) { + event.stopImmediatePropagation(); +} + +function noevent$2(event) { + event.preventDefault(); + event.stopImmediatePropagation(); +} + +function dragDisable(view) { + var root = view.document.documentElement, + selection = select(view).on("dragstart.drag", noevent$2, nonpassivecapture); + if ("onselectstart" in root) { + selection.on("selectstart.drag", noevent$2, nonpassivecapture); + } else { + root.__noselect = root.style.MozUserSelect; + root.style.MozUserSelect = "none"; + } +} + +function yesdrag(view, noclick) { + var root = view.document.documentElement, + selection = select(view).on("dragstart.drag", null); + if (noclick) { + selection.on("click.drag", noevent$2, nonpassivecapture); + setTimeout(function() { selection.on("click.drag", null); }, 0); + } + if ("onselectstart" in root) { + selection.on("selectstart.drag", null); + } else { + root.style.MozUserSelect = root.__noselect; + delete root.__noselect; + } +} + +var constant$9 = x => () => x; + +function DragEvent(type, { + sourceEvent, + subject, + target, + identifier, + active, + x, y, dx, dy, + dispatch +}) { + Object.defineProperties(this, { + type: {value: type, enumerable: true, configurable: true}, + sourceEvent: {value: sourceEvent, enumerable: true, configurable: true}, + subject: {value: subject, enumerable: true, configurable: true}, + target: {value: target, enumerable: true, configurable: true}, + identifier: {value: identifier, enumerable: true, configurable: true}, + active: {value: active, enumerable: true, configurable: true}, + x: {value: x, enumerable: true, configurable: true}, + y: {value: y, enumerable: true, configurable: true}, + dx: {value: dx, enumerable: true, configurable: true}, + dy: {value: dy, enumerable: true, configurable: true}, + _: {value: dispatch} + }); +} + +DragEvent.prototype.on = function() { + var value = this._.on.apply(this._, arguments); + return value === this._ ? this : value; +}; + +// Ignore right-click, since that should open the context menu. +function defaultFilter$2(event) { + return !event.ctrlKey && !event.button; +} + +function defaultContainer() { + return this.parentNode; +} + +function defaultSubject(event, d) { + return d == null ? {x: event.x, y: event.y} : d; +} + +function defaultTouchable$2() { + return navigator.maxTouchPoints || ("ontouchstart" in this); +} + +function drag() { + var filter = defaultFilter$2, + container = defaultContainer, + subject = defaultSubject, + touchable = defaultTouchable$2, + gestures = {}, + listeners = dispatch("start", "drag", "end"), + active = 0, + mousedownx, + mousedowny, + mousemoving, + touchending, + clickDistance2 = 0; + + function drag(selection) { + selection + .on("mousedown.drag", mousedowned) + .filter(touchable) + .on("touchstart.drag", touchstarted) + .on("touchmove.drag", touchmoved, nonpassive) + .on("touchend.drag touchcancel.drag", touchended) + .style("touch-action", "none") + .style("-webkit-tap-highlight-color", "rgba(0,0,0,0)"); + } + + function mousedowned(event, d) { + if (touchending || !filter.call(this, event, d)) return; + var gesture = beforestart(this, container.call(this, event, d), event, d, "mouse"); + if (!gesture) return; + select(event.view) + .on("mousemove.drag", mousemoved, nonpassivecapture) + .on("mouseup.drag", mouseupped, nonpassivecapture); + dragDisable(event.view); + nopropagation$2(event); + mousemoving = false; + mousedownx = event.clientX; + mousedowny = event.clientY; + gesture("start", event); + } + + function mousemoved(event) { + noevent$2(event); + if (!mousemoving) { + var dx = event.clientX - mousedownx, dy = event.clientY - mousedowny; + mousemoving = dx * dx + dy * dy > clickDistance2; + } + gestures.mouse("drag", event); + } + + function mouseupped(event) { + select(event.view).on("mousemove.drag mouseup.drag", null); + yesdrag(event.view, mousemoving); + noevent$2(event); + gestures.mouse("end", event); + } + + function touchstarted(event, d) { + if (!filter.call(this, event, d)) return; + var touches = event.changedTouches, + c = container.call(this, event, d), + n = touches.length, i, gesture; + + for (i = 0; i < n; ++i) { + if (gesture = beforestart(this, c, event, d, touches[i].identifier, touches[i])) { + nopropagation$2(event); + gesture("start", event, touches[i]); + } + } + } + + function touchmoved(event) { + var touches = event.changedTouches, + n = touches.length, i, gesture; + + for (i = 0; i < n; ++i) { + if (gesture = gestures[touches[i].identifier]) { + noevent$2(event); + gesture("drag", event, touches[i]); + } + } + } + + function touchended(event) { + var touches = event.changedTouches, + n = touches.length, i, gesture; + + if (touchending) clearTimeout(touchending); + touchending = setTimeout(function() { touchending = null; }, 500); // Ghost clicks are delayed! + for (i = 0; i < n; ++i) { + if (gesture = gestures[touches[i].identifier]) { + nopropagation$2(event); + gesture("end", event, touches[i]); + } + } + } + + function beforestart(that, container, event, d, identifier, touch) { + var dispatch = listeners.copy(), + p = pointer(touch || event, container), dx, dy, + s; + + if ((s = subject.call(that, new DragEvent("beforestart", { + sourceEvent: event, + target: drag, + identifier, + active, + x: p[0], + y: p[1], + dx: 0, + dy: 0, + dispatch + }), d)) == null) return; + + dx = s.x - p[0] || 0; + dy = s.y - p[1] || 0; + + return function gesture(type, event, touch) { + var p0 = p, n; + switch (type) { + case "start": gestures[identifier] = gesture, n = active++; break; + case "end": delete gestures[identifier], --active; // falls through + case "drag": p = pointer(touch || event, container), n = active; break; + } + dispatch.call( + type, + that, + new DragEvent(type, { + sourceEvent: event, + subject: s, + target: drag, + identifier, + active: n, + x: p[0] + dx, + y: p[1] + dy, + dx: p[0] - p0[0], + dy: p[1] - p0[1], + dispatch + }), + d + ); + }; + } + + drag.filter = function(_) { + return arguments.length ? (filter = typeof _ === "function" ? _ : constant$9(!!_), drag) : filter; + }; + + drag.container = function(_) { + return arguments.length ? (container = typeof _ === "function" ? _ : constant$9(_), drag) : container; + }; + + drag.subject = function(_) { + return arguments.length ? (subject = typeof _ === "function" ? _ : constant$9(_), drag) : subject; + }; + + drag.touchable = function(_) { + return arguments.length ? (touchable = typeof _ === "function" ? _ : constant$9(!!_), drag) : touchable; + }; + + drag.on = function() { + var value = listeners.on.apply(listeners, arguments); + return value === listeners ? drag : value; + }; + + drag.clickDistance = function(_) { + return arguments.length ? (clickDistance2 = (_ = +_) * _, drag) : Math.sqrt(clickDistance2); + }; + + return drag; +} + +function define(constructor, factory, prototype) { + constructor.prototype = factory.prototype = prototype; + prototype.constructor = constructor; +} + +function extend(parent, definition) { + var prototype = Object.create(parent.prototype); + for (var key in definition) prototype[key] = definition[key]; + return prototype; +} + +function Color() {} + +var darker = 0.7; +var brighter = 1 / darker; + +var reI = "\\s*([+-]?\\d+)\\s*", + reN = "\\s*([+-]?(?:\\d*\\.)?\\d+(?:[eE][+-]?\\d+)?)\\s*", + reP = "\\s*([+-]?(?:\\d*\\.)?\\d+(?:[eE][+-]?\\d+)?)%\\s*", + reHex = /^#([0-9a-f]{3,8})$/, + reRgbInteger = new RegExp(`^rgb\\(${reI},${reI},${reI}\\)$`), + reRgbPercent = new RegExp(`^rgb\\(${reP},${reP},${reP}\\)$`), + reRgbaInteger = new RegExp(`^rgba\\(${reI},${reI},${reI},${reN}\\)$`), + reRgbaPercent = new RegExp(`^rgba\\(${reP},${reP},${reP},${reN}\\)$`), + reHslPercent = new RegExp(`^hsl\\(${reN},${reP},${reP}\\)$`), + reHslaPercent = new RegExp(`^hsla\\(${reN},${reP},${reP},${reN}\\)$`); + +var named = { + aliceblue: 0xf0f8ff, + antiquewhite: 0xfaebd7, + aqua: 0x00ffff, + aquamarine: 0x7fffd4, + azure: 0xf0ffff, + beige: 0xf5f5dc, + bisque: 0xffe4c4, + black: 0x000000, + blanchedalmond: 0xffebcd, + blue: 0x0000ff, + blueviolet: 0x8a2be2, + brown: 0xa52a2a, + burlywood: 0xdeb887, + cadetblue: 0x5f9ea0, + chartreuse: 0x7fff00, + chocolate: 0xd2691e, + coral: 0xff7f50, + cornflowerblue: 0x6495ed, + cornsilk: 0xfff8dc, + crimson: 0xdc143c, + cyan: 0x00ffff, + darkblue: 0x00008b, + darkcyan: 0x008b8b, + darkgoldenrod: 0xb8860b, + darkgray: 0xa9a9a9, + darkgreen: 0x006400, + darkgrey: 0xa9a9a9, + darkkhaki: 0xbdb76b, + darkmagenta: 0x8b008b, + darkolivegreen: 0x556b2f, + darkorange: 0xff8c00, + darkorchid: 0x9932cc, + darkred: 0x8b0000, + darksalmon: 0xe9967a, + darkseagreen: 0x8fbc8f, + darkslateblue: 0x483d8b, + darkslategray: 0x2f4f4f, + darkslategrey: 0x2f4f4f, + darkturquoise: 0x00ced1, + darkviolet: 0x9400d3, + deeppink: 0xff1493, + deepskyblue: 0x00bfff, + dimgray: 0x696969, + dimgrey: 0x696969, + dodgerblue: 0x1e90ff, + firebrick: 0xb22222, + floralwhite: 0xfffaf0, + forestgreen: 0x228b22, + fuchsia: 0xff00ff, + gainsboro: 0xdcdcdc, + ghostwhite: 0xf8f8ff, + gold: 0xffd700, + goldenrod: 0xdaa520, + gray: 0x808080, + green: 0x008000, + greenyellow: 0xadff2f, + grey: 0x808080, + honeydew: 0xf0fff0, + hotpink: 0xff69b4, + indianred: 0xcd5c5c, + indigo: 0x4b0082, + ivory: 0xfffff0, + khaki: 0xf0e68c, + lavender: 0xe6e6fa, + lavenderblush: 0xfff0f5, + lawngreen: 0x7cfc00, + lemonchiffon: 0xfffacd, + lightblue: 0xadd8e6, + lightcoral: 0xf08080, + lightcyan: 0xe0ffff, + lightgoldenrodyellow: 0xfafad2, + lightgray: 0xd3d3d3, + lightgreen: 0x90ee90, + lightgrey: 0xd3d3d3, + lightpink: 0xffb6c1, + lightsalmon: 0xffa07a, + lightseagreen: 0x20b2aa, + lightskyblue: 0x87cefa, + lightslategray: 0x778899, + lightslategrey: 0x778899, + lightsteelblue: 0xb0c4de, + lightyellow: 0xffffe0, + lime: 0x00ff00, + limegreen: 0x32cd32, + linen: 0xfaf0e6, + magenta: 0xff00ff, + maroon: 0x800000, + mediumaquamarine: 0x66cdaa, + mediumblue: 0x0000cd, + mediumorchid: 0xba55d3, + mediumpurple: 0x9370db, + mediumseagreen: 0x3cb371, + mediumslateblue: 0x7b68ee, + mediumspringgreen: 0x00fa9a, + mediumturquoise: 0x48d1cc, + mediumvioletred: 0xc71585, + midnightblue: 0x191970, + mintcream: 0xf5fffa, + mistyrose: 0xffe4e1, + moccasin: 0xffe4b5, + navajowhite: 0xffdead, + navy: 0x000080, + oldlace: 0xfdf5e6, + olive: 0x808000, + olivedrab: 0x6b8e23, + orange: 0xffa500, + orangered: 0xff4500, + orchid: 0xda70d6, + palegoldenrod: 0xeee8aa, + palegreen: 0x98fb98, + paleturquoise: 0xafeeee, + palevioletred: 0xdb7093, + papayawhip: 0xffefd5, + peachpuff: 0xffdab9, + peru: 0xcd853f, + pink: 0xffc0cb, + plum: 0xdda0dd, + powderblue: 0xb0e0e6, + purple: 0x800080, + rebeccapurple: 0x663399, + red: 0xff0000, + rosybrown: 0xbc8f8f, + royalblue: 0x4169e1, + saddlebrown: 0x8b4513, + salmon: 0xfa8072, + sandybrown: 0xf4a460, + seagreen: 0x2e8b57, + seashell: 0xfff5ee, + sienna: 0xa0522d, + silver: 0xc0c0c0, + skyblue: 0x87ceeb, + slateblue: 0x6a5acd, + slategray: 0x708090, + slategrey: 0x708090, + snow: 0xfffafa, + springgreen: 0x00ff7f, + steelblue: 0x4682b4, + tan: 0xd2b48c, + teal: 0x008080, + thistle: 0xd8bfd8, + tomato: 0xff6347, + turquoise: 0x40e0d0, + violet: 0xee82ee, + wheat: 0xf5deb3, + white: 0xffffff, + whitesmoke: 0xf5f5f5, + yellow: 0xffff00, + yellowgreen: 0x9acd32 +}; + +define(Color, color, { + copy(channels) { + return Object.assign(new this.constructor, this, channels); + }, + displayable() { + return this.rgb().displayable(); + }, + hex: color_formatHex, // Deprecated! Use color.formatHex. + formatHex: color_formatHex, + formatHex8: color_formatHex8, + formatHsl: color_formatHsl, + formatRgb: color_formatRgb, + toString: color_formatRgb +}); + +function color_formatHex() { + return this.rgb().formatHex(); +} + +function color_formatHex8() { + return this.rgb().formatHex8(); +} + +function color_formatHsl() { + return hslConvert(this).formatHsl(); +} + +function color_formatRgb() { + return this.rgb().formatRgb(); +} + +function color(format) { + var m, l; + format = (format + "").trim().toLowerCase(); + return (m = reHex.exec(format)) ? (l = m[1].length, m = parseInt(m[1], 16), l === 6 ? rgbn(m) // #ff0000 + : l === 3 ? new Rgb((m >> 8 & 0xf) | (m >> 4 & 0xf0), (m >> 4 & 0xf) | (m & 0xf0), ((m & 0xf) << 4) | (m & 0xf), 1) // #f00 + : l === 8 ? rgba(m >> 24 & 0xff, m >> 16 & 0xff, m >> 8 & 0xff, (m & 0xff) / 0xff) // #ff000000 + : l === 4 ? rgba((m >> 12 & 0xf) | (m >> 8 & 0xf0), (m >> 8 & 0xf) | (m >> 4 & 0xf0), (m >> 4 & 0xf) | (m & 0xf0), (((m & 0xf) << 4) | (m & 0xf)) / 0xff) // #f000 + : null) // invalid hex + : (m = reRgbInteger.exec(format)) ? new Rgb(m[1], m[2], m[3], 1) // rgb(255, 0, 0) + : (m = reRgbPercent.exec(format)) ? new Rgb(m[1] * 255 / 100, m[2] * 255 / 100, m[3] * 255 / 100, 1) // rgb(100%, 0%, 0%) + : (m = reRgbaInteger.exec(format)) ? rgba(m[1], m[2], m[3], m[4]) // rgba(255, 0, 0, 1) + : (m = reRgbaPercent.exec(format)) ? rgba(m[1] * 255 / 100, m[2] * 255 / 100, m[3] * 255 / 100, m[4]) // rgb(100%, 0%, 0%, 1) + : (m = reHslPercent.exec(format)) ? hsla(m[1], m[2] / 100, m[3] / 100, 1) // hsl(120, 50%, 50%) + : (m = reHslaPercent.exec(format)) ? hsla(m[1], m[2] / 100, m[3] / 100, m[4]) // hsla(120, 50%, 50%, 1) + : named.hasOwnProperty(format) ? rgbn(named[format]) // eslint-disable-line no-prototype-builtins + : format === "transparent" ? new Rgb(NaN, NaN, NaN, 0) + : null; +} + +function rgbn(n) { + return new Rgb(n >> 16 & 0xff, n >> 8 & 0xff, n & 0xff, 1); +} + +function rgba(r, g, b, a) { + if (a <= 0) r = g = b = NaN; + return new Rgb(r, g, b, a); +} + +function rgbConvert(o) { + if (!(o instanceof Color)) o = color(o); + if (!o) return new Rgb; + o = o.rgb(); + return new Rgb(o.r, o.g, o.b, o.opacity); +} + +function rgb(r, g, b, opacity) { + return arguments.length === 1 ? rgbConvert(r) : new Rgb(r, g, b, opacity == null ? 1 : opacity); +} + +function Rgb(r, g, b, opacity) { + this.r = +r; + this.g = +g; + this.b = +b; + this.opacity = +opacity; +} + +define(Rgb, rgb, extend(Color, { + brighter(k) { + k = k == null ? brighter : Math.pow(brighter, k); + return new Rgb(this.r * k, this.g * k, this.b * k, this.opacity); + }, + darker(k) { + k = k == null ? darker : Math.pow(darker, k); + return new Rgb(this.r * k, this.g * k, this.b * k, this.opacity); + }, + rgb() { + return this; + }, + clamp() { + return new Rgb(clampi(this.r), clampi(this.g), clampi(this.b), clampa(this.opacity)); + }, + displayable() { + return (-0.5 <= this.r && this.r < 255.5) + && (-0.5 <= this.g && this.g < 255.5) + && (-0.5 <= this.b && this.b < 255.5) + && (0 <= this.opacity && this.opacity <= 1); + }, + hex: rgb_formatHex, // Deprecated! Use color.formatHex. + formatHex: rgb_formatHex, + formatHex8: rgb_formatHex8, + formatRgb: rgb_formatRgb, + toString: rgb_formatRgb +})); + +function rgb_formatHex() { + return `#${hex(this.r)}${hex(this.g)}${hex(this.b)}`; +} + +function rgb_formatHex8() { + return `#${hex(this.r)}${hex(this.g)}${hex(this.b)}${hex((isNaN(this.opacity) ? 1 : this.opacity) * 255)}`; +} + +function rgb_formatRgb() { + const a = clampa(this.opacity); + return `${a === 1 ? "rgb(" : "rgba("}${clampi(this.r)}, ${clampi(this.g)}, ${clampi(this.b)}${a === 1 ? ")" : `, ${a})`}`; +} + +function clampa(opacity) { + return isNaN(opacity) ? 1 : Math.max(0, Math.min(1, opacity)); +} + +function clampi(value) { + return Math.max(0, Math.min(255, Math.round(value) || 0)); +} + +function hex(value) { + value = clampi(value); + return (value < 16 ? "0" : "") + value.toString(16); +} + +function hsla(h, s, l, a) { + if (a <= 0) h = s = l = NaN; + else if (l <= 0 || l >= 1) h = s = NaN; + else if (s <= 0) h = NaN; + return new Hsl(h, s, l, a); +} + +function hslConvert(o) { + if (o instanceof Hsl) return new Hsl(o.h, o.s, o.l, o.opacity); + if (!(o instanceof Color)) o = color(o); + if (!o) return new Hsl; + if (o instanceof Hsl) return o; + o = o.rgb(); + var r = o.r / 255, + g = o.g / 255, + b = o.b / 255, + min = Math.min(r, g, b), + max = Math.max(r, g, b), + h = NaN, + s = max - min, + l = (max + min) / 2; + if (s) { + if (r === max) h = (g - b) / s + (g < b) * 6; + else if (g === max) h = (b - r) / s + 2; + else h = (r - g) / s + 4; + s /= l < 0.5 ? max + min : 2 - max - min; + h *= 60; + } else { + s = l > 0 && l < 1 ? 0 : h; + } + return new Hsl(h, s, l, o.opacity); +} + +function hsl$2(h, s, l, opacity) { + return arguments.length === 1 ? hslConvert(h) : new Hsl(h, s, l, opacity == null ? 1 : opacity); +} + +function Hsl(h, s, l, opacity) { + this.h = +h; + this.s = +s; + this.l = +l; + this.opacity = +opacity; +} + +define(Hsl, hsl$2, extend(Color, { + brighter(k) { + k = k == null ? brighter : Math.pow(brighter, k); + return new Hsl(this.h, this.s, this.l * k, this.opacity); + }, + darker(k) { + k = k == null ? darker : Math.pow(darker, k); + return new Hsl(this.h, this.s, this.l * k, this.opacity); + }, + rgb() { + var h = this.h % 360 + (this.h < 0) * 360, + s = isNaN(h) || isNaN(this.s) ? 0 : this.s, + l = this.l, + m2 = l + (l < 0.5 ? l : 1 - l) * s, + m1 = 2 * l - m2; + return new Rgb( + hsl2rgb(h >= 240 ? h - 240 : h + 120, m1, m2), + hsl2rgb(h, m1, m2), + hsl2rgb(h < 120 ? h + 240 : h - 120, m1, m2), + this.opacity + ); + }, + clamp() { + return new Hsl(clamph(this.h), clampt(this.s), clampt(this.l), clampa(this.opacity)); + }, + displayable() { + return (0 <= this.s && this.s <= 1 || isNaN(this.s)) + && (0 <= this.l && this.l <= 1) + && (0 <= this.opacity && this.opacity <= 1); + }, + formatHsl() { + const a = clampa(this.opacity); + return `${a === 1 ? "hsl(" : "hsla("}${clamph(this.h)}, ${clampt(this.s) * 100}%, ${clampt(this.l) * 100}%${a === 1 ? ")" : `, ${a})`}`; + } +})); + +function clamph(value) { + value = (value || 0) % 360; + return value < 0 ? value + 360 : value; +} + +function clampt(value) { + return Math.max(0, Math.min(1, value || 0)); +} + +/* From FvD 13.37, CSS Color Module Level 3 */ +function hsl2rgb(h, m1, m2) { + return (h < 60 ? m1 + (m2 - m1) * h / 60 + : h < 180 ? m2 + : h < 240 ? m1 + (m2 - m1) * (240 - h) / 60 + : m1) * 255; +} + +const radians$1 = Math.PI / 180; +const degrees$2 = 180 / Math.PI; + +// https://observablehq.com/@mbostock/lab-and-rgb +const K = 18, + Xn = 0.96422, + Yn = 1, + Zn = 0.82521, + t0$1 = 4 / 29, + t1$1 = 6 / 29, + t2 = 3 * t1$1 * t1$1, + t3 = t1$1 * t1$1 * t1$1; + +function labConvert(o) { + if (o instanceof Lab) return new Lab(o.l, o.a, o.b, o.opacity); + if (o instanceof Hcl) return hcl2lab(o); + if (!(o instanceof Rgb)) o = rgbConvert(o); + var r = rgb2lrgb(o.r), + g = rgb2lrgb(o.g), + b = rgb2lrgb(o.b), + y = xyz2lab((0.2225045 * r + 0.7168786 * g + 0.0606169 * b) / Yn), x, z; + if (r === g && g === b) x = z = y; else { + x = xyz2lab((0.4360747 * r + 0.3850649 * g + 0.1430804 * b) / Xn); + z = xyz2lab((0.0139322 * r + 0.0971045 * g + 0.7141733 * b) / Zn); + } + return new Lab(116 * y - 16, 500 * (x - y), 200 * (y - z), o.opacity); +} + +function gray(l, opacity) { + return new Lab(l, 0, 0, opacity == null ? 1 : opacity); +} + +function lab$1(l, a, b, opacity) { + return arguments.length === 1 ? labConvert(l) : new Lab(l, a, b, opacity == null ? 1 : opacity); +} + +function Lab(l, a, b, opacity) { + this.l = +l; + this.a = +a; + this.b = +b; + this.opacity = +opacity; +} + +define(Lab, lab$1, extend(Color, { + brighter(k) { + return new Lab(this.l + K * (k == null ? 1 : k), this.a, this.b, this.opacity); + }, + darker(k) { + return new Lab(this.l - K * (k == null ? 1 : k), this.a, this.b, this.opacity); + }, + rgb() { + var y = (this.l + 16) / 116, + x = isNaN(this.a) ? y : y + this.a / 500, + z = isNaN(this.b) ? y : y - this.b / 200; + x = Xn * lab2xyz(x); + y = Yn * lab2xyz(y); + z = Zn * lab2xyz(z); + return new Rgb( + lrgb2rgb( 3.1338561 * x - 1.6168667 * y - 0.4906146 * z), + lrgb2rgb(-0.9787684 * x + 1.9161415 * y + 0.0334540 * z), + lrgb2rgb( 0.0719453 * x - 0.2289914 * y + 1.4052427 * z), + this.opacity + ); + } +})); + +function xyz2lab(t) { + return t > t3 ? Math.pow(t, 1 / 3) : t / t2 + t0$1; +} + +function lab2xyz(t) { + return t > t1$1 ? t * t * t : t2 * (t - t0$1); +} + +function lrgb2rgb(x) { + return 255 * (x <= 0.0031308 ? 12.92 * x : 1.055 * Math.pow(x, 1 / 2.4) - 0.055); +} + +function rgb2lrgb(x) { + return (x /= 255) <= 0.04045 ? x / 12.92 : Math.pow((x + 0.055) / 1.055, 2.4); +} + +function hclConvert(o) { + if (o instanceof Hcl) return new Hcl(o.h, o.c, o.l, o.opacity); + if (!(o instanceof Lab)) o = labConvert(o); + if (o.a === 0 && o.b === 0) return new Hcl(NaN, 0 < o.l && o.l < 100 ? 0 : NaN, o.l, o.opacity); + var h = Math.atan2(o.b, o.a) * degrees$2; + return new Hcl(h < 0 ? h + 360 : h, Math.sqrt(o.a * o.a + o.b * o.b), o.l, o.opacity); +} + +function lch(l, c, h, opacity) { + return arguments.length === 1 ? hclConvert(l) : new Hcl(h, c, l, opacity == null ? 1 : opacity); +} + +function hcl$2(h, c, l, opacity) { + return arguments.length === 1 ? hclConvert(h) : new Hcl(h, c, l, opacity == null ? 1 : opacity); +} + +function Hcl(h, c, l, opacity) { + this.h = +h; + this.c = +c; + this.l = +l; + this.opacity = +opacity; +} + +function hcl2lab(o) { + if (isNaN(o.h)) return new Lab(o.l, 0, 0, o.opacity); + var h = o.h * radians$1; + return new Lab(o.l, Math.cos(h) * o.c, Math.sin(h) * o.c, o.opacity); +} + +define(Hcl, hcl$2, extend(Color, { + brighter(k) { + return new Hcl(this.h, this.c, this.l + K * (k == null ? 1 : k), this.opacity); + }, + darker(k) { + return new Hcl(this.h, this.c, this.l - K * (k == null ? 1 : k), this.opacity); + }, + rgb() { + return hcl2lab(this).rgb(); + } +})); + +var A = -0.14861, + B$1 = +1.78277, + C = -0.29227, + D$1 = -0.90649, + E = +1.97294, + ED = E * D$1, + EB = E * B$1, + BC_DA = B$1 * C - D$1 * A; + +function cubehelixConvert(o) { + if (o instanceof Cubehelix) return new Cubehelix(o.h, o.s, o.l, o.opacity); + if (!(o instanceof Rgb)) o = rgbConvert(o); + var r = o.r / 255, + g = o.g / 255, + b = o.b / 255, + l = (BC_DA * b + ED * r - EB * g) / (BC_DA + ED - EB), + bl = b - l, + k = (E * (g - l) - C * bl) / D$1, + s = Math.sqrt(k * k + bl * bl) / (E * l * (1 - l)), // NaN if l=0 or l=1 + h = s ? Math.atan2(k, bl) * degrees$2 - 120 : NaN; + return new Cubehelix(h < 0 ? h + 360 : h, s, l, o.opacity); +} + +function cubehelix$3(h, s, l, opacity) { + return arguments.length === 1 ? cubehelixConvert(h) : new Cubehelix(h, s, l, opacity == null ? 1 : opacity); +} + +function Cubehelix(h, s, l, opacity) { + this.h = +h; + this.s = +s; + this.l = +l; + this.opacity = +opacity; +} + +define(Cubehelix, cubehelix$3, extend(Color, { + brighter(k) { + k = k == null ? brighter : Math.pow(brighter, k); + return new Cubehelix(this.h, this.s, this.l * k, this.opacity); + }, + darker(k) { + k = k == null ? darker : Math.pow(darker, k); + return new Cubehelix(this.h, this.s, this.l * k, this.opacity); + }, + rgb() { + var h = isNaN(this.h) ? 0 : (this.h + 120) * radians$1, + l = +this.l, + a = isNaN(this.s) ? 0 : this.s * l * (1 - l), + cosh = Math.cos(h), + sinh = Math.sin(h); + return new Rgb( + 255 * (l + a * (A * cosh + B$1 * sinh)), + 255 * (l + a * (C * cosh + D$1 * sinh)), + 255 * (l + a * (E * cosh)), + this.opacity + ); + } +})); + +function basis$1(t1, v0, v1, v2, v3) { + var t2 = t1 * t1, t3 = t2 * t1; + return ((1 - 3 * t1 + 3 * t2 - t3) * v0 + + (4 - 6 * t2 + 3 * t3) * v1 + + (1 + 3 * t1 + 3 * t2 - 3 * t3) * v2 + + t3 * v3) / 6; +} + +function basis$2(values) { + var n = values.length - 1; + return function(t) { + var i = t <= 0 ? (t = 0) : t >= 1 ? (t = 1, n - 1) : Math.floor(t * n), + v1 = values[i], + v2 = values[i + 1], + v0 = i > 0 ? values[i - 1] : 2 * v1 - v2, + v3 = i < n - 1 ? values[i + 2] : 2 * v2 - v1; + return basis$1((t - i / n) * n, v0, v1, v2, v3); + }; +} + +function basisClosed$1(values) { + var n = values.length; + return function(t) { + var i = Math.floor(((t %= 1) < 0 ? ++t : t) * n), + v0 = values[(i + n - 1) % n], + v1 = values[i % n], + v2 = values[(i + 1) % n], + v3 = values[(i + 2) % n]; + return basis$1((t - i / n) * n, v0, v1, v2, v3); + }; +} + +var constant$8 = x => () => x; + +function linear$2(a, d) { + return function(t) { + return a + t * d; + }; +} + +function exponential$1(a, b, y) { + return a = Math.pow(a, y), b = Math.pow(b, y) - a, y = 1 / y, function(t) { + return Math.pow(a + t * b, y); + }; +} + +function hue$1(a, b) { + var d = b - a; + return d ? linear$2(a, d > 180 || d < -180 ? d - 360 * Math.round(d / 360) : d) : constant$8(isNaN(a) ? b : a); +} + +function gamma$1(y) { + return (y = +y) === 1 ? nogamma : function(a, b) { + return b - a ? exponential$1(a, b, y) : constant$8(isNaN(a) ? b : a); + }; +} + +function nogamma(a, b) { + var d = b - a; + return d ? linear$2(a, d) : constant$8(isNaN(a) ? b : a); +} + +var interpolateRgb = (function rgbGamma(y) { + var color = gamma$1(y); + + function rgb$1(start, end) { + var r = color((start = rgb(start)).r, (end = rgb(end)).r), + g = color(start.g, end.g), + b = color(start.b, end.b), + opacity = nogamma(start.opacity, end.opacity); + return function(t) { + start.r = r(t); + start.g = g(t); + start.b = b(t); + start.opacity = opacity(t); + return start + ""; + }; + } + + rgb$1.gamma = rgbGamma; + + return rgb$1; +})(1); + +function rgbSpline(spline) { + return function(colors) { + var n = colors.length, + r = new Array(n), + g = new Array(n), + b = new Array(n), + i, color; + for (i = 0; i < n; ++i) { + color = rgb(colors[i]); + r[i] = color.r || 0; + g[i] = color.g || 0; + b[i] = color.b || 0; + } + r = spline(r); + g = spline(g); + b = spline(b); + color.opacity = 1; + return function(t) { + color.r = r(t); + color.g = g(t); + color.b = b(t); + return color + ""; + }; + }; +} + +var rgbBasis = rgbSpline(basis$2); +var rgbBasisClosed = rgbSpline(basisClosed$1); + +function numberArray(a, b) { + if (!b) b = []; + var n = a ? Math.min(b.length, a.length) : 0, + c = b.slice(), + i; + return function(t) { + for (i = 0; i < n; ++i) c[i] = a[i] * (1 - t) + b[i] * t; + return c; + }; +} + +function isNumberArray(x) { + return ArrayBuffer.isView(x) && !(x instanceof DataView); +} + +function array$3(a, b) { + return (isNumberArray(b) ? numberArray : genericArray)(a, b); +} + +function genericArray(a, b) { + var nb = b ? b.length : 0, + na = a ? Math.min(nb, a.length) : 0, + x = new Array(na), + c = new Array(nb), + i; + + for (i = 0; i < na; ++i) x[i] = interpolate$2(a[i], b[i]); + for (; i < nb; ++i) c[i] = b[i]; + + return function(t) { + for (i = 0; i < na; ++i) c[i] = x[i](t); + return c; + }; +} + +function date$1(a, b) { + var d = new Date; + return a = +a, b = +b, function(t) { + return d.setTime(a * (1 - t) + b * t), d; + }; +} + +function interpolateNumber(a, b) { + return a = +a, b = +b, function(t) { + return a * (1 - t) + b * t; + }; +} + +function object$1(a, b) { + var i = {}, + c = {}, + k; + + if (a === null || typeof a !== "object") a = {}; + if (b === null || typeof b !== "object") b = {}; + + for (k in b) { + if (k in a) { + i[k] = interpolate$2(a[k], b[k]); + } else { + c[k] = b[k]; + } + } + + return function(t) { + for (k in i) c[k] = i[k](t); + return c; + }; +} + +var reA = /[-+]?(?:\d+\.?\d*|\.?\d+)(?:[eE][-+]?\d+)?/g, + reB = new RegExp(reA.source, "g"); + +function zero(b) { + return function() { + return b; + }; +} + +function one(b) { + return function(t) { + return b(t) + ""; + }; +} + +function interpolateString(a, b) { + var bi = reA.lastIndex = reB.lastIndex = 0, // scan index for next number in b + am, // current match in a + bm, // current match in b + bs, // string preceding current number in b, if any + i = -1, // index in s + s = [], // string constants and placeholders + q = []; // number interpolators + + // Coerce inputs to strings. + a = a + "", b = b + ""; + + // Interpolate pairs of numbers in a & b. + while ((am = reA.exec(a)) + && (bm = reB.exec(b))) { + if ((bs = bm.index) > bi) { // a string precedes the next number in b + bs = b.slice(bi, bs); + if (s[i]) s[i] += bs; // coalesce with previous string + else s[++i] = bs; + } + if ((am = am[0]) === (bm = bm[0])) { // numbers in a & b match + if (s[i]) s[i] += bm; // coalesce with previous string + else s[++i] = bm; + } else { // interpolate non-matching numbers + s[++i] = null; + q.push({i: i, x: interpolateNumber(am, bm)}); + } + bi = reB.lastIndex; + } + + // Add remains of b. + if (bi < b.length) { + bs = b.slice(bi); + if (s[i]) s[i] += bs; // coalesce with previous string + else s[++i] = bs; + } + + // Special optimization for only a single match. + // Otherwise, interpolate each of the numbers and rejoin the string. + return s.length < 2 ? (q[0] + ? one(q[0].x) + : zero(b)) + : (b = q.length, function(t) { + for (var i = 0, o; i < b; ++i) s[(o = q[i]).i] = o.x(t); + return s.join(""); + }); +} + +function interpolate$2(a, b) { + var t = typeof b, c; + return b == null || t === "boolean" ? constant$8(b) + : (t === "number" ? interpolateNumber + : t === "string" ? ((c = color(b)) ? (b = c, interpolateRgb) : interpolateString) + : b instanceof color ? interpolateRgb + : b instanceof Date ? date$1 + : isNumberArray(b) ? numberArray + : Array.isArray(b) ? genericArray + : typeof b.valueOf !== "function" && typeof b.toString !== "function" || isNaN(b) ? object$1 + : interpolateNumber)(a, b); +} + +function discrete(range) { + var n = range.length; + return function(t) { + return range[Math.max(0, Math.min(n - 1, Math.floor(t * n)))]; + }; +} + +function hue(a, b) { + var i = hue$1(+a, +b); + return function(t) { + var x = i(t); + return x - 360 * Math.floor(x / 360); + }; +} + +function interpolateRound(a, b) { + return a = +a, b = +b, function(t) { + return Math.round(a * (1 - t) + b * t); + }; +} + +var degrees$1 = 180 / Math.PI; + +var identity$7 = { + translateX: 0, + translateY: 0, + rotate: 0, + skewX: 0, + scaleX: 1, + scaleY: 1 +}; + +function decompose(a, b, c, d, e, f) { + var scaleX, scaleY, skewX; + if (scaleX = Math.sqrt(a * a + b * b)) a /= scaleX, b /= scaleX; + if (skewX = a * c + b * d) c -= a * skewX, d -= b * skewX; + if (scaleY = Math.sqrt(c * c + d * d)) c /= scaleY, d /= scaleY, skewX /= scaleY; + if (a * d < b * c) a = -a, b = -b, skewX = -skewX, scaleX = -scaleX; + return { + translateX: e, + translateY: f, + rotate: Math.atan2(b, a) * degrees$1, + skewX: Math.atan(skewX) * degrees$1, + scaleX: scaleX, + scaleY: scaleY + }; +} + +var svgNode; + +/* eslint-disable no-undef */ +function parseCss(value) { + const m = new (typeof DOMMatrix === "function" ? DOMMatrix : WebKitCSSMatrix)(value + ""); + return m.isIdentity ? identity$7 : decompose(m.a, m.b, m.c, m.d, m.e, m.f); +} + +function parseSvg(value) { + if (value == null) return identity$7; + if (!svgNode) svgNode = document.createElementNS("http://www.w3.org/2000/svg", "g"); + svgNode.setAttribute("transform", value); + if (!(value = svgNode.transform.baseVal.consolidate())) return identity$7; + value = value.matrix; + return decompose(value.a, value.b, value.c, value.d, value.e, value.f); +} + +function interpolateTransform(parse, pxComma, pxParen, degParen) { + + function pop(s) { + return s.length ? s.pop() + " " : ""; + } + + function translate(xa, ya, xb, yb, s, q) { + if (xa !== xb || ya !== yb) { + var i = s.push("translate(", null, pxComma, null, pxParen); + q.push({i: i - 4, x: interpolateNumber(xa, xb)}, {i: i - 2, x: interpolateNumber(ya, yb)}); + } else if (xb || yb) { + s.push("translate(" + xb + pxComma + yb + pxParen); + } + } + + function rotate(a, b, s, q) { + if (a !== b) { + if (a - b > 180) b += 360; else if (b - a > 180) a += 360; // shortest path + q.push({i: s.push(pop(s) + "rotate(", null, degParen) - 2, x: interpolateNumber(a, b)}); + } else if (b) { + s.push(pop(s) + "rotate(" + b + degParen); + } + } + + function skewX(a, b, s, q) { + if (a !== b) { + q.push({i: s.push(pop(s) + "skewX(", null, degParen) - 2, x: interpolateNumber(a, b)}); + } else if (b) { + s.push(pop(s) + "skewX(" + b + degParen); + } + } + + function scale(xa, ya, xb, yb, s, q) { + if (xa !== xb || ya !== yb) { + var i = s.push(pop(s) + "scale(", null, ",", null, ")"); + q.push({i: i - 4, x: interpolateNumber(xa, xb)}, {i: i - 2, x: interpolateNumber(ya, yb)}); + } else if (xb !== 1 || yb !== 1) { + s.push(pop(s) + "scale(" + xb + "," + yb + ")"); + } + } + + return function(a, b) { + var s = [], // string constants and placeholders + q = []; // number interpolators + a = parse(a), b = parse(b); + translate(a.translateX, a.translateY, b.translateX, b.translateY, s, q); + rotate(a.rotate, b.rotate, s, q); + skewX(a.skewX, b.skewX, s, q); + scale(a.scaleX, a.scaleY, b.scaleX, b.scaleY, s, q); + a = b = null; // gc + return function(t) { + var i = -1, n = q.length, o; + while (++i < n) s[(o = q[i]).i] = o.x(t); + return s.join(""); + }; + }; +} + +var interpolateTransformCss = interpolateTransform(parseCss, "px, ", "px)", "deg)"); +var interpolateTransformSvg = interpolateTransform(parseSvg, ", ", ")", ")"); + +var epsilon2$1 = 1e-12; + +function cosh(x) { + return ((x = Math.exp(x)) + 1 / x) / 2; +} + +function sinh(x) { + return ((x = Math.exp(x)) - 1 / x) / 2; +} + +function tanh(x) { + return ((x = Math.exp(2 * x)) - 1) / (x + 1); +} + +var interpolateZoom = (function zoomRho(rho, rho2, rho4) { + + // p0 = [ux0, uy0, w0] + // p1 = [ux1, uy1, w1] + function zoom(p0, p1) { + var ux0 = p0[0], uy0 = p0[1], w0 = p0[2], + ux1 = p1[0], uy1 = p1[1], w1 = p1[2], + dx = ux1 - ux0, + dy = uy1 - uy0, + d2 = dx * dx + dy * dy, + i, + S; + + // Special case for u0 ≅ u1. + if (d2 < epsilon2$1) { + S = Math.log(w1 / w0) / rho; + i = function(t) { + return [ + ux0 + t * dx, + uy0 + t * dy, + w0 * Math.exp(rho * t * S) + ]; + }; + } + + // General case. + else { + var d1 = Math.sqrt(d2), + b0 = (w1 * w1 - w0 * w0 + rho4 * d2) / (2 * w0 * rho2 * d1), + b1 = (w1 * w1 - w0 * w0 - rho4 * d2) / (2 * w1 * rho2 * d1), + r0 = Math.log(Math.sqrt(b0 * b0 + 1) - b0), + r1 = Math.log(Math.sqrt(b1 * b1 + 1) - b1); + S = (r1 - r0) / rho; + i = function(t) { + var s = t * S, + coshr0 = cosh(r0), + u = w0 / (rho2 * d1) * (coshr0 * tanh(rho * s + r0) - sinh(r0)); + return [ + ux0 + u * dx, + uy0 + u * dy, + w0 * coshr0 / cosh(rho * s + r0) + ]; + }; + } + + i.duration = S * 1000 * rho / Math.SQRT2; + + return i; + } + + zoom.rho = function(_) { + var _1 = Math.max(1e-3, +_), _2 = _1 * _1, _4 = _2 * _2; + return zoomRho(_1, _2, _4); + }; + + return zoom; +})(Math.SQRT2, 2, 4); + +function hsl(hue) { + return function(start, end) { + var h = hue((start = hsl$2(start)).h, (end = hsl$2(end)).h), + s = nogamma(start.s, end.s), + l = nogamma(start.l, end.l), + opacity = nogamma(start.opacity, end.opacity); + return function(t) { + start.h = h(t); + start.s = s(t); + start.l = l(t); + start.opacity = opacity(t); + return start + ""; + }; + } +} + +var hsl$1 = hsl(hue$1); +var hslLong = hsl(nogamma); + +function lab(start, end) { + var l = nogamma((start = lab$1(start)).l, (end = lab$1(end)).l), + a = nogamma(start.a, end.a), + b = nogamma(start.b, end.b), + opacity = nogamma(start.opacity, end.opacity); + return function(t) { + start.l = l(t); + start.a = a(t); + start.b = b(t); + start.opacity = opacity(t); + return start + ""; + }; +} + +function hcl(hue) { + return function(start, end) { + var h = hue((start = hcl$2(start)).h, (end = hcl$2(end)).h), + c = nogamma(start.c, end.c), + l = nogamma(start.l, end.l), + opacity = nogamma(start.opacity, end.opacity); + return function(t) { + start.h = h(t); + start.c = c(t); + start.l = l(t); + start.opacity = opacity(t); + return start + ""; + }; + } +} + +var hcl$1 = hcl(hue$1); +var hclLong = hcl(nogamma); + +function cubehelix$1(hue) { + return (function cubehelixGamma(y) { + y = +y; + + function cubehelix(start, end) { + var h = hue((start = cubehelix$3(start)).h, (end = cubehelix$3(end)).h), + s = nogamma(start.s, end.s), + l = nogamma(start.l, end.l), + opacity = nogamma(start.opacity, end.opacity); + return function(t) { + start.h = h(t); + start.s = s(t); + start.l = l(Math.pow(t, y)); + start.opacity = opacity(t); + return start + ""; + }; + } + + cubehelix.gamma = cubehelixGamma; + + return cubehelix; + })(1); +} + +var cubehelix$2 = cubehelix$1(hue$1); +var cubehelixLong = cubehelix$1(nogamma); + +function piecewise(interpolate, values) { + if (values === undefined) values = interpolate, interpolate = interpolate$2; + var i = 0, n = values.length - 1, v = values[0], I = new Array(n < 0 ? 0 : n); + while (i < n) I[i] = interpolate(v, v = values[++i]); + return function(t) { + var i = Math.max(0, Math.min(n - 1, Math.floor(t *= n))); + return I[i](t - i); + }; +} + +function quantize$1(interpolator, n) { + var samples = new Array(n); + for (var i = 0; i < n; ++i) samples[i] = interpolator(i / (n - 1)); + return samples; +} + +var frame = 0, // is an animation frame pending? + timeout$1 = 0, // is a timeout pending? + interval$1 = 0, // are any timers active? + pokeDelay = 1000, // how frequently we check for clock skew + taskHead, + taskTail, + clockLast = 0, + clockNow = 0, + clockSkew = 0, + clock = typeof performance === "object" && performance.now ? performance : Date, + setFrame = typeof window === "object" && window.requestAnimationFrame ? window.requestAnimationFrame.bind(window) : function(f) { setTimeout(f, 17); }; + +function now() { + return clockNow || (setFrame(clearNow), clockNow = clock.now() + clockSkew); +} + +function clearNow() { + clockNow = 0; +} + +function Timer() { + this._call = + this._time = + this._next = null; +} + +Timer.prototype = timer.prototype = { + constructor: Timer, + restart: function(callback, delay, time) { + if (typeof callback !== "function") throw new TypeError("callback is not a function"); + time = (time == null ? now() : +time) + (delay == null ? 0 : +delay); + if (!this._next && taskTail !== this) { + if (taskTail) taskTail._next = this; + else taskHead = this; + taskTail = this; + } + this._call = callback; + this._time = time; + sleep(); + }, + stop: function() { + if (this._call) { + this._call = null; + this._time = Infinity; + sleep(); + } + } +}; + +function timer(callback, delay, time) { + var t = new Timer; + t.restart(callback, delay, time); + return t; +} + +function timerFlush() { + now(); // Get the current time, if not already set. + ++frame; // Pretend we’ve set an alarm, if we haven’t already. + var t = taskHead, e; + while (t) { + if ((e = clockNow - t._time) >= 0) t._call.call(undefined, e); + t = t._next; + } + --frame; +} + +function wake() { + clockNow = (clockLast = clock.now()) + clockSkew; + frame = timeout$1 = 0; + try { + timerFlush(); + } finally { + frame = 0; + nap(); + clockNow = 0; + } +} + +function poke() { + var now = clock.now(), delay = now - clockLast; + if (delay > pokeDelay) clockSkew -= delay, clockLast = now; +} + +function nap() { + var t0, t1 = taskHead, t2, time = Infinity; + while (t1) { + if (t1._call) { + if (time > t1._time) time = t1._time; + t0 = t1, t1 = t1._next; + } else { + t2 = t1._next, t1._next = null; + t1 = t0 ? t0._next = t2 : taskHead = t2; + } + } + taskTail = t0; + sleep(time); +} + +function sleep(time) { + if (frame) return; // Soonest alarm already set, or will be. + if (timeout$1) timeout$1 = clearTimeout(timeout$1); + var delay = time - clockNow; // Strictly less than if we recomputed clockNow. + if (delay > 24) { + if (time < Infinity) timeout$1 = setTimeout(wake, time - clock.now() - clockSkew); + if (interval$1) interval$1 = clearInterval(interval$1); + } else { + if (!interval$1) clockLast = clock.now(), interval$1 = setInterval(poke, pokeDelay); + frame = 1, setFrame(wake); + } +} + +function timeout(callback, delay, time) { + var t = new Timer; + delay = delay == null ? 0 : +delay; + t.restart(elapsed => { + t.stop(); + callback(elapsed + delay); + }, delay, time); + return t; +} + +function interval(callback, delay, time) { + var t = new Timer, total = delay; + if (delay == null) return t.restart(callback, delay, time), t; + t._restart = t.restart; + t.restart = function(callback, delay, time) { + delay = +delay, time = time == null ? now() : +time; + t._restart(function tick(elapsed) { + elapsed += total; + t._restart(tick, total += delay, time); + callback(elapsed); + }, delay, time); + }; + t.restart(callback, delay, time); + return t; +} + +var emptyOn = dispatch("start", "end", "cancel", "interrupt"); +var emptyTween = []; + +var CREATED = 0; +var SCHEDULED = 1; +var STARTING = 2; +var STARTED = 3; +var RUNNING = 4; +var ENDING = 5; +var ENDED = 6; + +function schedule(node, name, id, index, group, timing) { + var schedules = node.__transition; + if (!schedules) node.__transition = {}; + else if (id in schedules) return; + create(node, id, { + name: name, + index: index, // For context during callback. + group: group, // For context during callback. + on: emptyOn, + tween: emptyTween, + time: timing.time, + delay: timing.delay, + duration: timing.duration, + ease: timing.ease, + timer: null, + state: CREATED + }); +} + +function init(node, id) { + var schedule = get(node, id); + if (schedule.state > CREATED) throw new Error("too late; already scheduled"); + return schedule; +} + +function set(node, id) { + var schedule = get(node, id); + if (schedule.state > STARTED) throw new Error("too late; already running"); + return schedule; +} + +function get(node, id) { + var schedule = node.__transition; + if (!schedule || !(schedule = schedule[id])) throw new Error("transition not found"); + return schedule; +} + +function create(node, id, self) { + var schedules = node.__transition, + tween; + + // Initialize the self timer when the transition is created. + // Note the actual delay is not known until the first callback! + schedules[id] = self; + self.timer = timer(schedule, 0, self.time); + + function schedule(elapsed) { + self.state = SCHEDULED; + self.timer.restart(start, self.delay, self.time); + + // If the elapsed delay is less than our first sleep, start immediately. + if (self.delay <= elapsed) start(elapsed - self.delay); + } + + function start(elapsed) { + var i, j, n, o; + + // If the state is not SCHEDULED, then we previously errored on start. + if (self.state !== SCHEDULED) return stop(); + + for (i in schedules) { + o = schedules[i]; + if (o.name !== self.name) continue; + + // While this element already has a starting transition during this frame, + // defer starting an interrupting transition until that transition has a + // chance to tick (and possibly end); see d3/d3-transition#54! + if (o.state === STARTED) return timeout(start); + + // Interrupt the active transition, if any. + if (o.state === RUNNING) { + o.state = ENDED; + o.timer.stop(); + o.on.call("interrupt", node, node.__data__, o.index, o.group); + delete schedules[i]; + } + + // Cancel any pre-empted transitions. + else if (+i < id) { + o.state = ENDED; + o.timer.stop(); + o.on.call("cancel", node, node.__data__, o.index, o.group); + delete schedules[i]; + } + } + + // Defer the first tick to end of the current frame; see d3/d3#1576. + // Note the transition may be canceled after start and before the first tick! + // Note this must be scheduled before the start event; see d3/d3-transition#16! + // Assuming this is successful, subsequent callbacks go straight to tick. + timeout(function() { + if (self.state === STARTED) { + self.state = RUNNING; + self.timer.restart(tick, self.delay, self.time); + tick(elapsed); + } + }); + + // Dispatch the start event. + // Note this must be done before the tween are initialized. + self.state = STARTING; + self.on.call("start", node, node.__data__, self.index, self.group); + if (self.state !== STARTING) return; // interrupted + self.state = STARTED; + + // Initialize the tween, deleting null tween. + tween = new Array(n = self.tween.length); + for (i = 0, j = -1; i < n; ++i) { + if (o = self.tween[i].value.call(node, node.__data__, self.index, self.group)) { + tween[++j] = o; + } + } + tween.length = j + 1; + } + + function tick(elapsed) { + var t = elapsed < self.duration ? self.ease.call(null, elapsed / self.duration) : (self.timer.restart(stop), self.state = ENDING, 1), + i = -1, + n = tween.length; + + while (++i < n) { + tween[i].call(node, t); + } + + // Dispatch the end event. + if (self.state === ENDING) { + self.on.call("end", node, node.__data__, self.index, self.group); + stop(); + } + } + + function stop() { + self.state = ENDED; + self.timer.stop(); + delete schedules[id]; + for (var i in schedules) return; // eslint-disable-line no-unused-vars + delete node.__transition; + } +} + +function interrupt(node, name) { + var schedules = node.__transition, + schedule, + active, + empty = true, + i; + + if (!schedules) return; + + name = name == null ? null : name + ""; + + for (i in schedules) { + if ((schedule = schedules[i]).name !== name) { empty = false; continue; } + active = schedule.state > STARTING && schedule.state < ENDING; + schedule.state = ENDED; + schedule.timer.stop(); + schedule.on.call(active ? "interrupt" : "cancel", node, node.__data__, schedule.index, schedule.group); + delete schedules[i]; + } + + if (empty) delete node.__transition; +} + +function selection_interrupt(name) { + return this.each(function() { + interrupt(this, name); + }); +} + +function tweenRemove(id, name) { + var tween0, tween1; + return function() { + var schedule = set(this, id), + tween = schedule.tween; + + // If this node shared tween with the previous node, + // just assign the updated shared tween and we’re done! + // Otherwise, copy-on-write. + if (tween !== tween0) { + tween1 = tween0 = tween; + for (var i = 0, n = tween1.length; i < n; ++i) { + if (tween1[i].name === name) { + tween1 = tween1.slice(); + tween1.splice(i, 1); + break; + } + } + } + + schedule.tween = tween1; + }; +} + +function tweenFunction(id, name, value) { + var tween0, tween1; + if (typeof value !== "function") throw new Error; + return function() { + var schedule = set(this, id), + tween = schedule.tween; + + // If this node shared tween with the previous node, + // just assign the updated shared tween and we’re done! + // Otherwise, copy-on-write. + if (tween !== tween0) { + tween1 = (tween0 = tween).slice(); + for (var t = {name: name, value: value}, i = 0, n = tween1.length; i < n; ++i) { + if (tween1[i].name === name) { + tween1[i] = t; + break; + } + } + if (i === n) tween1.push(t); + } + + schedule.tween = tween1; + }; +} + +function transition_tween(name, value) { + var id = this._id; + + name += ""; + + if (arguments.length < 2) { + var tween = get(this.node(), id).tween; + for (var i = 0, n = tween.length, t; i < n; ++i) { + if ((t = tween[i]).name === name) { + return t.value; + } + } + return null; + } + + return this.each((value == null ? tweenRemove : tweenFunction)(id, name, value)); +} + +function tweenValue(transition, name, value) { + var id = transition._id; + + transition.each(function() { + var schedule = set(this, id); + (schedule.value || (schedule.value = {}))[name] = value.apply(this, arguments); + }); + + return function(node) { + return get(node, id).value[name]; + }; +} + +function interpolate$1(a, b) { + var c; + return (typeof b === "number" ? interpolateNumber + : b instanceof color ? interpolateRgb + : (c = color(b)) ? (b = c, interpolateRgb) + : interpolateString)(a, b); +} + +function attrRemove(name) { + return function() { + this.removeAttribute(name); + }; +} + +function attrRemoveNS(fullname) { + return function() { + this.removeAttributeNS(fullname.space, fullname.local); + }; +} + +function attrConstant(name, interpolate, value1) { + var string00, + string1 = value1 + "", + interpolate0; + return function() { + var string0 = this.getAttribute(name); + return string0 === string1 ? null + : string0 === string00 ? interpolate0 + : interpolate0 = interpolate(string00 = string0, value1); + }; +} + +function attrConstantNS(fullname, interpolate, value1) { + var string00, + string1 = value1 + "", + interpolate0; + return function() { + var string0 = this.getAttributeNS(fullname.space, fullname.local); + return string0 === string1 ? null + : string0 === string00 ? interpolate0 + : interpolate0 = interpolate(string00 = string0, value1); + }; +} + +function attrFunction(name, interpolate, value) { + var string00, + string10, + interpolate0; + return function() { + var string0, value1 = value(this), string1; + if (value1 == null) return void this.removeAttribute(name); + string0 = this.getAttribute(name); + string1 = value1 + ""; + return string0 === string1 ? null + : string0 === string00 && string1 === string10 ? interpolate0 + : (string10 = string1, interpolate0 = interpolate(string00 = string0, value1)); + }; +} + +function attrFunctionNS(fullname, interpolate, value) { + var string00, + string10, + interpolate0; + return function() { + var string0, value1 = value(this), string1; + if (value1 == null) return void this.removeAttributeNS(fullname.space, fullname.local); + string0 = this.getAttributeNS(fullname.space, fullname.local); + string1 = value1 + ""; + return string0 === string1 ? null + : string0 === string00 && string1 === string10 ? interpolate0 + : (string10 = string1, interpolate0 = interpolate(string00 = string0, value1)); + }; +} + +function transition_attr(name, value) { + var fullname = namespace(name), i = fullname === "transform" ? interpolateTransformSvg : interpolate$1; + return this.attrTween(name, typeof value === "function" + ? (fullname.local ? attrFunctionNS : attrFunction)(fullname, i, tweenValue(this, "attr." + name, value)) + : value == null ? (fullname.local ? attrRemoveNS : attrRemove)(fullname) + : (fullname.local ? attrConstantNS : attrConstant)(fullname, i, value)); +} + +function attrInterpolate(name, i) { + return function(t) { + this.setAttribute(name, i.call(this, t)); + }; +} + +function attrInterpolateNS(fullname, i) { + return function(t) { + this.setAttributeNS(fullname.space, fullname.local, i.call(this, t)); + }; +} + +function attrTweenNS(fullname, value) { + var t0, i0; + function tween() { + var i = value.apply(this, arguments); + if (i !== i0) t0 = (i0 = i) && attrInterpolateNS(fullname, i); + return t0; + } + tween._value = value; + return tween; +} + +function attrTween(name, value) { + var t0, i0; + function tween() { + var i = value.apply(this, arguments); + if (i !== i0) t0 = (i0 = i) && attrInterpolate(name, i); + return t0; + } + tween._value = value; + return tween; +} + +function transition_attrTween(name, value) { + var key = "attr." + name; + if (arguments.length < 2) return (key = this.tween(key)) && key._value; + if (value == null) return this.tween(key, null); + if (typeof value !== "function") throw new Error; + var fullname = namespace(name); + return this.tween(key, (fullname.local ? attrTweenNS : attrTween)(fullname, value)); +} + +function delayFunction(id, value) { + return function() { + init(this, id).delay = +value.apply(this, arguments); + }; +} + +function delayConstant(id, value) { + return value = +value, function() { + init(this, id).delay = value; + }; +} + +function transition_delay(value) { + var id = this._id; + + return arguments.length + ? this.each((typeof value === "function" + ? delayFunction + : delayConstant)(id, value)) + : get(this.node(), id).delay; +} + +function durationFunction(id, value) { + return function() { + set(this, id).duration = +value.apply(this, arguments); + }; +} + +function durationConstant(id, value) { + return value = +value, function() { + set(this, id).duration = value; + }; +} + +function transition_duration(value) { + var id = this._id; + + return arguments.length + ? this.each((typeof value === "function" + ? durationFunction + : durationConstant)(id, value)) + : get(this.node(), id).duration; +} + +function easeConstant(id, value) { + if (typeof value !== "function") throw new Error; + return function() { + set(this, id).ease = value; + }; +} + +function transition_ease(value) { + var id = this._id; + + return arguments.length + ? this.each(easeConstant(id, value)) + : get(this.node(), id).ease; +} + +function easeVarying(id, value) { + return function() { + var v = value.apply(this, arguments); + if (typeof v !== "function") throw new Error; + set(this, id).ease = v; + }; +} + +function transition_easeVarying(value) { + if (typeof value !== "function") throw new Error; + return this.each(easeVarying(this._id, value)); +} + +function transition_filter(match) { + if (typeof match !== "function") match = matcher(match); + + for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, subgroup = subgroups[j] = [], node, i = 0; i < n; ++i) { + if ((node = group[i]) && match.call(node, node.__data__, i, group)) { + subgroup.push(node); + } + } + } + + return new Transition(subgroups, this._parents, this._name, this._id); +} + +function transition_merge(transition) { + if (transition._id !== this._id) throw new Error; + + for (var groups0 = this._groups, groups1 = transition._groups, m0 = groups0.length, m1 = groups1.length, m = Math.min(m0, m1), merges = new Array(m0), j = 0; j < m; ++j) { + for (var group0 = groups0[j], group1 = groups1[j], n = group0.length, merge = merges[j] = new Array(n), node, i = 0; i < n; ++i) { + if (node = group0[i] || group1[i]) { + merge[i] = node; + } + } + } + + for (; j < m0; ++j) { + merges[j] = groups0[j]; + } + + return new Transition(merges, this._parents, this._name, this._id); +} + +function start(name) { + return (name + "").trim().split(/^|\s+/).every(function(t) { + var i = t.indexOf("."); + if (i >= 0) t = t.slice(0, i); + return !t || t === "start"; + }); +} + +function onFunction(id, name, listener) { + var on0, on1, sit = start(name) ? init : set; + return function() { + var schedule = sit(this, id), + on = schedule.on; + + // If this node shared a dispatch with the previous node, + // just assign the updated shared dispatch and we’re done! + // Otherwise, copy-on-write. + if (on !== on0) (on1 = (on0 = on).copy()).on(name, listener); + + schedule.on = on1; + }; +} + +function transition_on(name, listener) { + var id = this._id; + + return arguments.length < 2 + ? get(this.node(), id).on.on(name) + : this.each(onFunction(id, name, listener)); +} + +function removeFunction(id) { + return function() { + var parent = this.parentNode; + for (var i in this.__transition) if (+i !== id) return; + if (parent) parent.removeChild(this); + }; +} + +function transition_remove() { + return this.on("end.remove", removeFunction(this._id)); +} + +function transition_select(select) { + var name = this._name, + id = this._id; + + if (typeof select !== "function") select = selector(select); + + for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, subgroup = subgroups[j] = new Array(n), node, subnode, i = 0; i < n; ++i) { + if ((node = group[i]) && (subnode = select.call(node, node.__data__, i, group))) { + if ("__data__" in node) subnode.__data__ = node.__data__; + subgroup[i] = subnode; + schedule(subgroup[i], name, id, i, subgroup, get(node, id)); + } + } + } + + return new Transition(subgroups, this._parents, name, id); +} + +function transition_selectAll(select) { + var name = this._name, + id = this._id; + + if (typeof select !== "function") select = selectorAll(select); + + for (var groups = this._groups, m = groups.length, subgroups = [], parents = [], j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) { + if (node = group[i]) { + for (var children = select.call(node, node.__data__, i, group), child, inherit = get(node, id), k = 0, l = children.length; k < l; ++k) { + if (child = children[k]) { + schedule(child, name, id, k, children, inherit); + } + } + subgroups.push(children); + parents.push(node); + } + } + } + + return new Transition(subgroups, parents, name, id); +} + +var Selection = selection.prototype.constructor; + +function transition_selection() { + return new Selection(this._groups, this._parents); +} + +function styleNull(name, interpolate) { + var string00, + string10, + interpolate0; + return function() { + var string0 = styleValue(this, name), + string1 = (this.style.removeProperty(name), styleValue(this, name)); + return string0 === string1 ? null + : string0 === string00 && string1 === string10 ? interpolate0 + : interpolate0 = interpolate(string00 = string0, string10 = string1); + }; +} + +function styleRemove(name) { + return function() { + this.style.removeProperty(name); + }; +} + +function styleConstant(name, interpolate, value1) { + var string00, + string1 = value1 + "", + interpolate0; + return function() { + var string0 = styleValue(this, name); + return string0 === string1 ? null + : string0 === string00 ? interpolate0 + : interpolate0 = interpolate(string00 = string0, value1); + }; +} + +function styleFunction(name, interpolate, value) { + var string00, + string10, + interpolate0; + return function() { + var string0 = styleValue(this, name), + value1 = value(this), + string1 = value1 + ""; + if (value1 == null) string1 = value1 = (this.style.removeProperty(name), styleValue(this, name)); + return string0 === string1 ? null + : string0 === string00 && string1 === string10 ? interpolate0 + : (string10 = string1, interpolate0 = interpolate(string00 = string0, value1)); + }; +} + +function styleMaybeRemove(id, name) { + var on0, on1, listener0, key = "style." + name, event = "end." + key, remove; + return function() { + var schedule = set(this, id), + on = schedule.on, + listener = schedule.value[key] == null ? remove || (remove = styleRemove(name)) : undefined; + + // If this node shared a dispatch with the previous node, + // just assign the updated shared dispatch and we’re done! + // Otherwise, copy-on-write. + if (on !== on0 || listener0 !== listener) (on1 = (on0 = on).copy()).on(event, listener0 = listener); + + schedule.on = on1; + }; +} + +function transition_style(name, value, priority) { + var i = (name += "") === "transform" ? interpolateTransformCss : interpolate$1; + return value == null ? this + .styleTween(name, styleNull(name, i)) + .on("end.style." + name, styleRemove(name)) + : typeof value === "function" ? this + .styleTween(name, styleFunction(name, i, tweenValue(this, "style." + name, value))) + .each(styleMaybeRemove(this._id, name)) + : this + .styleTween(name, styleConstant(name, i, value), priority) + .on("end.style." + name, null); +} + +function styleInterpolate(name, i, priority) { + return function(t) { + this.style.setProperty(name, i.call(this, t), priority); + }; +} + +function styleTween(name, value, priority) { + var t, i0; + function tween() { + var i = value.apply(this, arguments); + if (i !== i0) t = (i0 = i) && styleInterpolate(name, i, priority); + return t; + } + tween._value = value; + return tween; +} + +function transition_styleTween(name, value, priority) { + var key = "style." + (name += ""); + if (arguments.length < 2) return (key = this.tween(key)) && key._value; + if (value == null) return this.tween(key, null); + if (typeof value !== "function") throw new Error; + return this.tween(key, styleTween(name, value, priority == null ? "" : priority)); +} + +function textConstant(value) { + return function() { + this.textContent = value; + }; +} + +function textFunction(value) { + return function() { + var value1 = value(this); + this.textContent = value1 == null ? "" : value1; + }; +} + +function transition_text(value) { + return this.tween("text", typeof value === "function" + ? textFunction(tweenValue(this, "text", value)) + : textConstant(value == null ? "" : value + "")); +} + +function textInterpolate(i) { + return function(t) { + this.textContent = i.call(this, t); + }; +} + +function textTween(value) { + var t0, i0; + function tween() { + var i = value.apply(this, arguments); + if (i !== i0) t0 = (i0 = i) && textInterpolate(i); + return t0; + } + tween._value = value; + return tween; +} + +function transition_textTween(value) { + var key = "text"; + if (arguments.length < 1) return (key = this.tween(key)) && key._value; + if (value == null) return this.tween(key, null); + if (typeof value !== "function") throw new Error; + return this.tween(key, textTween(value)); +} + +function transition_transition() { + var name = this._name, + id0 = this._id, + id1 = newId(); + + for (var groups = this._groups, m = groups.length, j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) { + if (node = group[i]) { + var inherit = get(node, id0); + schedule(node, name, id1, i, group, { + time: inherit.time + inherit.delay + inherit.duration, + delay: 0, + duration: inherit.duration, + ease: inherit.ease + }); + } + } + } + + return new Transition(groups, this._parents, name, id1); +} + +function transition_end() { + var on0, on1, that = this, id = that._id, size = that.size(); + return new Promise(function(resolve, reject) { + var cancel = {value: reject}, + end = {value: function() { if (--size === 0) resolve(); }}; + + that.each(function() { + var schedule = set(this, id), + on = schedule.on; + + // If this node shared a dispatch with the previous node, + // just assign the updated shared dispatch and we’re done! + // Otherwise, copy-on-write. + if (on !== on0) { + on1 = (on0 = on).copy(); + on1._.cancel.push(cancel); + on1._.interrupt.push(cancel); + on1._.end.push(end); + } + + schedule.on = on1; + }); + + // The selection was empty, resolve end immediately + if (size === 0) resolve(); + }); +} + +var id = 0; + +function Transition(groups, parents, name, id) { + this._groups = groups; + this._parents = parents; + this._name = name; + this._id = id; +} + +function transition(name) { + return selection().transition(name); +} + +function newId() { + return ++id; +} + +var selection_prototype = selection.prototype; + +Transition.prototype = transition.prototype = { + constructor: Transition, + select: transition_select, + selectAll: transition_selectAll, + selectChild: selection_prototype.selectChild, + selectChildren: selection_prototype.selectChildren, + filter: transition_filter, + merge: transition_merge, + selection: transition_selection, + transition: transition_transition, + call: selection_prototype.call, + nodes: selection_prototype.nodes, + node: selection_prototype.node, + size: selection_prototype.size, + empty: selection_prototype.empty, + each: selection_prototype.each, + on: transition_on, + attr: transition_attr, + attrTween: transition_attrTween, + style: transition_style, + styleTween: transition_styleTween, + text: transition_text, + textTween: transition_textTween, + remove: transition_remove, + tween: transition_tween, + delay: transition_delay, + duration: transition_duration, + ease: transition_ease, + easeVarying: transition_easeVarying, + end: transition_end, + [Symbol.iterator]: selection_prototype[Symbol.iterator] +}; + +const linear$1 = t => +t; + +function quadIn(t) { + return t * t; +} + +function quadOut(t) { + return t * (2 - t); +} + +function quadInOut(t) { + return ((t *= 2) <= 1 ? t * t : --t * (2 - t) + 1) / 2; +} + +function cubicIn(t) { + return t * t * t; +} + +function cubicOut(t) { + return --t * t * t + 1; +} + +function cubicInOut(t) { + return ((t *= 2) <= 1 ? t * t * t : (t -= 2) * t * t + 2) / 2; +} + +var exponent$1 = 3; + +var polyIn = (function custom(e) { + e = +e; + + function polyIn(t) { + return Math.pow(t, e); + } + + polyIn.exponent = custom; + + return polyIn; +})(exponent$1); + +var polyOut = (function custom(e) { + e = +e; + + function polyOut(t) { + return 1 - Math.pow(1 - t, e); + } + + polyOut.exponent = custom; + + return polyOut; +})(exponent$1); + +var polyInOut = (function custom(e) { + e = +e; + + function polyInOut(t) { + return ((t *= 2) <= 1 ? Math.pow(t, e) : 2 - Math.pow(2 - t, e)) / 2; + } + + polyInOut.exponent = custom; + + return polyInOut; +})(exponent$1); + +var pi$4 = Math.PI, + halfPi$3 = pi$4 / 2; + +function sinIn(t) { + return (+t === 1) ? 1 : 1 - Math.cos(t * halfPi$3); +} + +function sinOut(t) { + return Math.sin(t * halfPi$3); +} + +function sinInOut(t) { + return (1 - Math.cos(pi$4 * t)) / 2; +} + +// tpmt is two power minus ten times t scaled to [0,1] +function tpmt(x) { + return (Math.pow(2, -10 * x) - 0.0009765625) * 1.0009775171065494; +} + +function expIn(t) { + return tpmt(1 - +t); +} + +function expOut(t) { + return 1 - tpmt(t); +} + +function expInOut(t) { + return ((t *= 2) <= 1 ? tpmt(1 - t) : 2 - tpmt(t - 1)) / 2; +} + +function circleIn(t) { + return 1 - Math.sqrt(1 - t * t); +} + +function circleOut(t) { + return Math.sqrt(1 - --t * t); +} + +function circleInOut(t) { + return ((t *= 2) <= 1 ? 1 - Math.sqrt(1 - t * t) : Math.sqrt(1 - (t -= 2) * t) + 1) / 2; +} + +var b1 = 4 / 11, + b2 = 6 / 11, + b3 = 8 / 11, + b4 = 3 / 4, + b5 = 9 / 11, + b6 = 10 / 11, + b7 = 15 / 16, + b8 = 21 / 22, + b9 = 63 / 64, + b0 = 1 / b1 / b1; + +function bounceIn(t) { + return 1 - bounceOut(1 - t); +} + +function bounceOut(t) { + return (t = +t) < b1 ? b0 * t * t : t < b3 ? b0 * (t -= b2) * t + b4 : t < b6 ? b0 * (t -= b5) * t + b7 : b0 * (t -= b8) * t + b9; +} + +function bounceInOut(t) { + return ((t *= 2) <= 1 ? 1 - bounceOut(1 - t) : bounceOut(t - 1) + 1) / 2; +} + +var overshoot = 1.70158; + +var backIn = (function custom(s) { + s = +s; + + function backIn(t) { + return (t = +t) * t * (s * (t - 1) + t); + } + + backIn.overshoot = custom; + + return backIn; +})(overshoot); + +var backOut = (function custom(s) { + s = +s; + + function backOut(t) { + return --t * t * ((t + 1) * s + t) + 1; + } + + backOut.overshoot = custom; + + return backOut; +})(overshoot); + +var backInOut = (function custom(s) { + s = +s; + + function backInOut(t) { + return ((t *= 2) < 1 ? t * t * ((s + 1) * t - s) : (t -= 2) * t * ((s + 1) * t + s) + 2) / 2; + } + + backInOut.overshoot = custom; + + return backInOut; +})(overshoot); + +var tau$5 = 2 * Math.PI, + amplitude = 1, + period = 0.3; + +var elasticIn = (function custom(a, p) { + var s = Math.asin(1 / (a = Math.max(1, a))) * (p /= tau$5); + + function elasticIn(t) { + return a * tpmt(-(--t)) * Math.sin((s - t) / p); + } + + elasticIn.amplitude = function(a) { return custom(a, p * tau$5); }; + elasticIn.period = function(p) { return custom(a, p); }; + + return elasticIn; +})(amplitude, period); + +var elasticOut = (function custom(a, p) { + var s = Math.asin(1 / (a = Math.max(1, a))) * (p /= tau$5); + + function elasticOut(t) { + return 1 - a * tpmt(t = +t) * Math.sin((t + s) / p); + } + + elasticOut.amplitude = function(a) { return custom(a, p * tau$5); }; + elasticOut.period = function(p) { return custom(a, p); }; + + return elasticOut; +})(amplitude, period); + +var elasticInOut = (function custom(a, p) { + var s = Math.asin(1 / (a = Math.max(1, a))) * (p /= tau$5); + + function elasticInOut(t) { + return ((t = t * 2 - 1) < 0 + ? a * tpmt(-t) * Math.sin((s - t) / p) + : 2 - a * tpmt(t) * Math.sin((s + t) / p)) / 2; + } + + elasticInOut.amplitude = function(a) { return custom(a, p * tau$5); }; + elasticInOut.period = function(p) { return custom(a, p); }; + + return elasticInOut; +})(amplitude, period); + +var defaultTiming = { + time: null, // Set on use. + delay: 0, + duration: 250, + ease: cubicInOut +}; + +function inherit(node, id) { + var timing; + while (!(timing = node.__transition) || !(timing = timing[id])) { + if (!(node = node.parentNode)) { + throw new Error(`transition ${id} not found`); + } + } + return timing; +} + +function selection_transition(name) { + var id, + timing; + + if (name instanceof Transition) { + id = name._id, name = name._name; + } else { + id = newId(), (timing = defaultTiming).time = now(), name = name == null ? null : name + ""; + } + + for (var groups = this._groups, m = groups.length, j = 0; j < m; ++j) { + for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) { + if (node = group[i]) { + schedule(node, name, id, i, group, timing || inherit(node, id)); + } + } + } + + return new Transition(groups, this._parents, name, id); +} + +selection.prototype.interrupt = selection_interrupt; +selection.prototype.transition = selection_transition; + +var root = [null]; + +function active(node, name) { + var schedules = node.__transition, + schedule, + i; + + if (schedules) { + name = name == null ? null : name + ""; + for (i in schedules) { + if ((schedule = schedules[i]).state > SCHEDULED && schedule.name === name) { + return new Transition([[node]], root, name, +i); + } + } + } + + return null; +} + +var constant$7 = x => () => x; + +function BrushEvent(type, { + sourceEvent, + target, + selection, + mode, + dispatch +}) { + Object.defineProperties(this, { + type: {value: type, enumerable: true, configurable: true}, + sourceEvent: {value: sourceEvent, enumerable: true, configurable: true}, + target: {value: target, enumerable: true, configurable: true}, + selection: {value: selection, enumerable: true, configurable: true}, + mode: {value: mode, enumerable: true, configurable: true}, + _: {value: dispatch} + }); +} + +function nopropagation$1(event) { + event.stopImmediatePropagation(); +} + +function noevent$1(event) { + event.preventDefault(); + event.stopImmediatePropagation(); +} + +var MODE_DRAG = {name: "drag"}, + MODE_SPACE = {name: "space"}, + MODE_HANDLE = {name: "handle"}, + MODE_CENTER = {name: "center"}; + +const {abs: abs$3, max: max$2, min: min$1} = Math; + +function number1(e) { + return [+e[0], +e[1]]; +} + +function number2(e) { + return [number1(e[0]), number1(e[1])]; +} + +var X = { + name: "x", + handles: ["w", "e"].map(type), + input: function(x, e) { return x == null ? null : [[+x[0], e[0][1]], [+x[1], e[1][1]]]; }, + output: function(xy) { return xy && [xy[0][0], xy[1][0]]; } +}; + +var Y = { + name: "y", + handles: ["n", "s"].map(type), + input: function(y, e) { return y == null ? null : [[e[0][0], +y[0]], [e[1][0], +y[1]]]; }, + output: function(xy) { return xy && [xy[0][1], xy[1][1]]; } +}; + +var XY = { + name: "xy", + handles: ["n", "w", "e", "s", "nw", "ne", "sw", "se"].map(type), + input: function(xy) { return xy == null ? null : number2(xy); }, + output: function(xy) { return xy; } +}; + +var cursors = { + overlay: "crosshair", + selection: "move", + n: "ns-resize", + e: "ew-resize", + s: "ns-resize", + w: "ew-resize", + nw: "nwse-resize", + ne: "nesw-resize", + se: "nwse-resize", + sw: "nesw-resize" +}; + +var flipX = { + e: "w", + w: "e", + nw: "ne", + ne: "nw", + se: "sw", + sw: "se" +}; + +var flipY = { + n: "s", + s: "n", + nw: "sw", + ne: "se", + se: "ne", + sw: "nw" +}; + +var signsX = { + overlay: +1, + selection: +1, + n: null, + e: +1, + s: null, + w: -1, + nw: -1, + ne: +1, + se: +1, + sw: -1 +}; + +var signsY = { + overlay: +1, + selection: +1, + n: -1, + e: null, + s: +1, + w: null, + nw: -1, + ne: -1, + se: +1, + sw: +1 +}; + +function type(t) { + return {type: t}; +} + +// Ignore right-click, since that should open the context menu. +function defaultFilter$1(event) { + return !event.ctrlKey && !event.button; +} + +function defaultExtent$1() { + var svg = this.ownerSVGElement || this; + if (svg.hasAttribute("viewBox")) { + svg = svg.viewBox.baseVal; + return [[svg.x, svg.y], [svg.x + svg.width, svg.y + svg.height]]; + } + return [[0, 0], [svg.width.baseVal.value, svg.height.baseVal.value]]; +} + +function defaultTouchable$1() { + return navigator.maxTouchPoints || ("ontouchstart" in this); +} + +// Like d3.local, but with the name “__brush” rather than auto-generated. +function local(node) { + while (!node.__brush) if (!(node = node.parentNode)) return; + return node.__brush; +} + +function empty(extent) { + return extent[0][0] === extent[1][0] + || extent[0][1] === extent[1][1]; +} + +function brushSelection(node) { + var state = node.__brush; + return state ? state.dim.output(state.selection) : null; +} + +function brushX() { + return brush$1(X); +} + +function brushY() { + return brush$1(Y); +} + +function brush() { + return brush$1(XY); +} + +function brush$1(dim) { + var extent = defaultExtent$1, + filter = defaultFilter$1, + touchable = defaultTouchable$1, + keys = true, + listeners = dispatch("start", "brush", "end"), + handleSize = 6, + touchending; + + function brush(group) { + var overlay = group + .property("__brush", initialize) + .selectAll(".overlay") + .data([type("overlay")]); + + overlay.enter().append("rect") + .attr("class", "overlay") + .attr("pointer-events", "all") + .attr("cursor", cursors.overlay) + .merge(overlay) + .each(function() { + var extent = local(this).extent; + select(this) + .attr("x", extent[0][0]) + .attr("y", extent[0][1]) + .attr("width", extent[1][0] - extent[0][0]) + .attr("height", extent[1][1] - extent[0][1]); + }); + + group.selectAll(".selection") + .data([type("selection")]) + .enter().append("rect") + .attr("class", "selection") + .attr("cursor", cursors.selection) + .attr("fill", "#777") + .attr("fill-opacity", 0.3) + .attr("stroke", "#fff") + .attr("shape-rendering", "crispEdges"); + + var handle = group.selectAll(".handle") + .data(dim.handles, function(d) { return d.type; }); + + handle.exit().remove(); + + handle.enter().append("rect") + .attr("class", function(d) { return "handle handle--" + d.type; }) + .attr("cursor", function(d) { return cursors[d.type]; }); + + group + .each(redraw) + .attr("fill", "none") + .attr("pointer-events", "all") + .on("mousedown.brush", started) + .filter(touchable) + .on("touchstart.brush", started) + .on("touchmove.brush", touchmoved) + .on("touchend.brush touchcancel.brush", touchended) + .style("touch-action", "none") + .style("-webkit-tap-highlight-color", "rgba(0,0,0,0)"); + } + + brush.move = function(group, selection, event) { + if (group.tween) { + group + .on("start.brush", function(event) { emitter(this, arguments).beforestart().start(event); }) + .on("interrupt.brush end.brush", function(event) { emitter(this, arguments).end(event); }) + .tween("brush", function() { + var that = this, + state = that.__brush, + emit = emitter(that, arguments), + selection0 = state.selection, + selection1 = dim.input(typeof selection === "function" ? selection.apply(this, arguments) : selection, state.extent), + i = interpolate$2(selection0, selection1); + + function tween(t) { + state.selection = t === 1 && selection1 === null ? null : i(t); + redraw.call(that); + emit.brush(); + } + + return selection0 !== null && selection1 !== null ? tween : tween(1); + }); + } else { + group + .each(function() { + var that = this, + args = arguments, + state = that.__brush, + selection1 = dim.input(typeof selection === "function" ? selection.apply(that, args) : selection, state.extent), + emit = emitter(that, args).beforestart(); + + interrupt(that); + state.selection = selection1 === null ? null : selection1; + redraw.call(that); + emit.start(event).brush(event).end(event); + }); + } + }; + + brush.clear = function(group, event) { + brush.move(group, null, event); + }; + + function redraw() { + var group = select(this), + selection = local(this).selection; + + if (selection) { + group.selectAll(".selection") + .style("display", null) + .attr("x", selection[0][0]) + .attr("y", selection[0][1]) + .attr("width", selection[1][0] - selection[0][0]) + .attr("height", selection[1][1] - selection[0][1]); + + group.selectAll(".handle") + .style("display", null) + .attr("x", function(d) { return d.type[d.type.length - 1] === "e" ? selection[1][0] - handleSize / 2 : selection[0][0] - handleSize / 2; }) + .attr("y", function(d) { return d.type[0] === "s" ? selection[1][1] - handleSize / 2 : selection[0][1] - handleSize / 2; }) + .attr("width", function(d) { return d.type === "n" || d.type === "s" ? selection[1][0] - selection[0][0] + handleSize : handleSize; }) + .attr("height", function(d) { return d.type === "e" || d.type === "w" ? selection[1][1] - selection[0][1] + handleSize : handleSize; }); + } + + else { + group.selectAll(".selection,.handle") + .style("display", "none") + .attr("x", null) + .attr("y", null) + .attr("width", null) + .attr("height", null); + } + } + + function emitter(that, args, clean) { + var emit = that.__brush.emitter; + return emit && (!clean || !emit.clean) ? emit : new Emitter(that, args, clean); + } + + function Emitter(that, args, clean) { + this.that = that; + this.args = args; + this.state = that.__brush; + this.active = 0; + this.clean = clean; + } + + Emitter.prototype = { + beforestart: function() { + if (++this.active === 1) this.state.emitter = this, this.starting = true; + return this; + }, + start: function(event, mode) { + if (this.starting) this.starting = false, this.emit("start", event, mode); + else this.emit("brush", event); + return this; + }, + brush: function(event, mode) { + this.emit("brush", event, mode); + return this; + }, + end: function(event, mode) { + if (--this.active === 0) delete this.state.emitter, this.emit("end", event, mode); + return this; + }, + emit: function(type, event, mode) { + var d = select(this.that).datum(); + listeners.call( + type, + this.that, + new BrushEvent(type, { + sourceEvent: event, + target: brush, + selection: dim.output(this.state.selection), + mode, + dispatch: listeners + }), + d + ); + } + }; + + function started(event) { + if (touchending && !event.touches) return; + if (!filter.apply(this, arguments)) return; + + var that = this, + type = event.target.__data__.type, + mode = (keys && event.metaKey ? type = "overlay" : type) === "selection" ? MODE_DRAG : (keys && event.altKey ? MODE_CENTER : MODE_HANDLE), + signX = dim === Y ? null : signsX[type], + signY = dim === X ? null : signsY[type], + state = local(that), + extent = state.extent, + selection = state.selection, + W = extent[0][0], w0, w1, + N = extent[0][1], n0, n1, + E = extent[1][0], e0, e1, + S = extent[1][1], s0, s1, + dx = 0, + dy = 0, + moving, + shifting = signX && signY && keys && event.shiftKey, + lockX, + lockY, + points = Array.from(event.touches || [event], t => { + const i = t.identifier; + t = pointer(t, that); + t.point0 = t.slice(); + t.identifier = i; + return t; + }); + + interrupt(that); + var emit = emitter(that, arguments, true).beforestart(); + + if (type === "overlay") { + if (selection) moving = true; + const pts = [points[0], points[1] || points[0]]; + state.selection = selection = [[ + w0 = dim === Y ? W : min$1(pts[0][0], pts[1][0]), + n0 = dim === X ? N : min$1(pts[0][1], pts[1][1]) + ], [ + e0 = dim === Y ? E : max$2(pts[0][0], pts[1][0]), + s0 = dim === X ? S : max$2(pts[0][1], pts[1][1]) + ]]; + if (points.length > 1) move(event); + } else { + w0 = selection[0][0]; + n0 = selection[0][1]; + e0 = selection[1][0]; + s0 = selection[1][1]; + } + + w1 = w0; + n1 = n0; + e1 = e0; + s1 = s0; + + var group = select(that) + .attr("pointer-events", "none"); + + var overlay = group.selectAll(".overlay") + .attr("cursor", cursors[type]); + + if (event.touches) { + emit.moved = moved; + emit.ended = ended; + } else { + var view = select(event.view) + .on("mousemove.brush", moved, true) + .on("mouseup.brush", ended, true); + if (keys) view + .on("keydown.brush", keydowned, true) + .on("keyup.brush", keyupped, true); + + dragDisable(event.view); + } + + redraw.call(that); + emit.start(event, mode.name); + + function moved(event) { + for (const p of event.changedTouches || [event]) { + for (const d of points) + if (d.identifier === p.identifier) d.cur = pointer(p, that); + } + if (shifting && !lockX && !lockY && points.length === 1) { + const point = points[0]; + if (abs$3(point.cur[0] - point[0]) > abs$3(point.cur[1] - point[1])) + lockY = true; + else + lockX = true; + } + for (const point of points) + if (point.cur) point[0] = point.cur[0], point[1] = point.cur[1]; + moving = true; + noevent$1(event); + move(event); + } + + function move(event) { + const point = points[0], point0 = point.point0; + var t; + + dx = point[0] - point0[0]; + dy = point[1] - point0[1]; + + switch (mode) { + case MODE_SPACE: + case MODE_DRAG: { + if (signX) dx = max$2(W - w0, min$1(E - e0, dx)), w1 = w0 + dx, e1 = e0 + dx; + if (signY) dy = max$2(N - n0, min$1(S - s0, dy)), n1 = n0 + dy, s1 = s0 + dy; + break; + } + case MODE_HANDLE: { + if (points[1]) { + if (signX) w1 = max$2(W, min$1(E, points[0][0])), e1 = max$2(W, min$1(E, points[1][0])), signX = 1; + if (signY) n1 = max$2(N, min$1(S, points[0][1])), s1 = max$2(N, min$1(S, points[1][1])), signY = 1; + } else { + if (signX < 0) dx = max$2(W - w0, min$1(E - w0, dx)), w1 = w0 + dx, e1 = e0; + else if (signX > 0) dx = max$2(W - e0, min$1(E - e0, dx)), w1 = w0, e1 = e0 + dx; + if (signY < 0) dy = max$2(N - n0, min$1(S - n0, dy)), n1 = n0 + dy, s1 = s0; + else if (signY > 0) dy = max$2(N - s0, min$1(S - s0, dy)), n1 = n0, s1 = s0 + dy; + } + break; + } + case MODE_CENTER: { + if (signX) w1 = max$2(W, min$1(E, w0 - dx * signX)), e1 = max$2(W, min$1(E, e0 + dx * signX)); + if (signY) n1 = max$2(N, min$1(S, n0 - dy * signY)), s1 = max$2(N, min$1(S, s0 + dy * signY)); + break; + } + } + + if (e1 < w1) { + signX *= -1; + t = w0, w0 = e0, e0 = t; + t = w1, w1 = e1, e1 = t; + if (type in flipX) overlay.attr("cursor", cursors[type = flipX[type]]); + } + + if (s1 < n1) { + signY *= -1; + t = n0, n0 = s0, s0 = t; + t = n1, n1 = s1, s1 = t; + if (type in flipY) overlay.attr("cursor", cursors[type = flipY[type]]); + } + + if (state.selection) selection = state.selection; // May be set by brush.move! + if (lockX) w1 = selection[0][0], e1 = selection[1][0]; + if (lockY) n1 = selection[0][1], s1 = selection[1][1]; + + if (selection[0][0] !== w1 + || selection[0][1] !== n1 + || selection[1][0] !== e1 + || selection[1][1] !== s1) { + state.selection = [[w1, n1], [e1, s1]]; + redraw.call(that); + emit.brush(event, mode.name); + } + } + + function ended(event) { + nopropagation$1(event); + if (event.touches) { + if (event.touches.length) return; + if (touchending) clearTimeout(touchending); + touchending = setTimeout(function() { touchending = null; }, 500); // Ghost clicks are delayed! + } else { + yesdrag(event.view, moving); + view.on("keydown.brush keyup.brush mousemove.brush mouseup.brush", null); + } + group.attr("pointer-events", "all"); + overlay.attr("cursor", cursors.overlay); + if (state.selection) selection = state.selection; // May be set by brush.move (on start)! + if (empty(selection)) state.selection = null, redraw.call(that); + emit.end(event, mode.name); + } + + function keydowned(event) { + switch (event.keyCode) { + case 16: { // SHIFT + shifting = signX && signY; + break; + } + case 18: { // ALT + if (mode === MODE_HANDLE) { + if (signX) e0 = e1 - dx * signX, w0 = w1 + dx * signX; + if (signY) s0 = s1 - dy * signY, n0 = n1 + dy * signY; + mode = MODE_CENTER; + move(event); + } + break; + } + case 32: { // SPACE; takes priority over ALT + if (mode === MODE_HANDLE || mode === MODE_CENTER) { + if (signX < 0) e0 = e1 - dx; else if (signX > 0) w0 = w1 - dx; + if (signY < 0) s0 = s1 - dy; else if (signY > 0) n0 = n1 - dy; + mode = MODE_SPACE; + overlay.attr("cursor", cursors.selection); + move(event); + } + break; + } + default: return; + } + noevent$1(event); + } + + function keyupped(event) { + switch (event.keyCode) { + case 16: { // SHIFT + if (shifting) { + lockX = lockY = shifting = false; + move(event); + } + break; + } + case 18: { // ALT + if (mode === MODE_CENTER) { + if (signX < 0) e0 = e1; else if (signX > 0) w0 = w1; + if (signY < 0) s0 = s1; else if (signY > 0) n0 = n1; + mode = MODE_HANDLE; + move(event); + } + break; + } + case 32: { // SPACE + if (mode === MODE_SPACE) { + if (event.altKey) { + if (signX) e0 = e1 - dx * signX, w0 = w1 + dx * signX; + if (signY) s0 = s1 - dy * signY, n0 = n1 + dy * signY; + mode = MODE_CENTER; + } else { + if (signX < 0) e0 = e1; else if (signX > 0) w0 = w1; + if (signY < 0) s0 = s1; else if (signY > 0) n0 = n1; + mode = MODE_HANDLE; + } + overlay.attr("cursor", cursors[type]); + move(event); + } + break; + } + default: return; + } + noevent$1(event); + } + } + + function touchmoved(event) { + emitter(this, arguments).moved(event); + } + + function touchended(event) { + emitter(this, arguments).ended(event); + } + + function initialize() { + var state = this.__brush || {selection: null}; + state.extent = number2(extent.apply(this, arguments)); + state.dim = dim; + return state; + } + + brush.extent = function(_) { + return arguments.length ? (extent = typeof _ === "function" ? _ : constant$7(number2(_)), brush) : extent; + }; + + brush.filter = function(_) { + return arguments.length ? (filter = typeof _ === "function" ? _ : constant$7(!!_), brush) : filter; + }; + + brush.touchable = function(_) { + return arguments.length ? (touchable = typeof _ === "function" ? _ : constant$7(!!_), brush) : touchable; + }; + + brush.handleSize = function(_) { + return arguments.length ? (handleSize = +_, brush) : handleSize; + }; + + brush.keyModifiers = function(_) { + return arguments.length ? (keys = !!_, brush) : keys; + }; + + brush.on = function() { + var value = listeners.on.apply(listeners, arguments); + return value === listeners ? brush : value; + }; + + return brush; +} + +var abs$2 = Math.abs; +var cos$2 = Math.cos; +var sin$2 = Math.sin; +var pi$3 = Math.PI; +var halfPi$2 = pi$3 / 2; +var tau$4 = pi$3 * 2; +var max$1 = Math.max; +var epsilon$5 = 1e-12; + +function range$1(i, j) { + return Array.from({length: j - i}, (_, k) => i + k); +} + +function compareValue(compare) { + return function(a, b) { + return compare( + a.source.value + a.target.value, + b.source.value + b.target.value + ); + }; +} + +function chord() { + return chord$1(false, false); +} + +function chordTranspose() { + return chord$1(false, true); +} + +function chordDirected() { + return chord$1(true, false); +} + +function chord$1(directed, transpose) { + var padAngle = 0, + sortGroups = null, + sortSubgroups = null, + sortChords = null; + + function chord(matrix) { + var n = matrix.length, + groupSums = new Array(n), + groupIndex = range$1(0, n), + chords = new Array(n * n), + groups = new Array(n), + k = 0, dx; + + matrix = Float64Array.from({length: n * n}, transpose + ? (_, i) => matrix[i % n][i / n | 0] + : (_, i) => matrix[i / n | 0][i % n]); + + // Compute the scaling factor from value to angle in [0, 2pi]. + for (let i = 0; i < n; ++i) { + let x = 0; + for (let j = 0; j < n; ++j) x += matrix[i * n + j] + directed * matrix[j * n + i]; + k += groupSums[i] = x; + } + k = max$1(0, tau$4 - padAngle * n) / k; + dx = k ? padAngle : tau$4 / n; + + // Compute the angles for each group and constituent chord. + { + let x = 0; + if (sortGroups) groupIndex.sort((a, b) => sortGroups(groupSums[a], groupSums[b])); + for (const i of groupIndex) { + const x0 = x; + if (directed) { + const subgroupIndex = range$1(~n + 1, n).filter(j => j < 0 ? matrix[~j * n + i] : matrix[i * n + j]); + if (sortSubgroups) subgroupIndex.sort((a, b) => sortSubgroups(a < 0 ? -matrix[~a * n + i] : matrix[i * n + a], b < 0 ? -matrix[~b * n + i] : matrix[i * n + b])); + for (const j of subgroupIndex) { + if (j < 0) { + const chord = chords[~j * n + i] || (chords[~j * n + i] = {source: null, target: null}); + chord.target = {index: i, startAngle: x, endAngle: x += matrix[~j * n + i] * k, value: matrix[~j * n + i]}; + } else { + const chord = chords[i * n + j] || (chords[i * n + j] = {source: null, target: null}); + chord.source = {index: i, startAngle: x, endAngle: x += matrix[i * n + j] * k, value: matrix[i * n + j]}; + } + } + groups[i] = {index: i, startAngle: x0, endAngle: x, value: groupSums[i]}; + } else { + const subgroupIndex = range$1(0, n).filter(j => matrix[i * n + j] || matrix[j * n + i]); + if (sortSubgroups) subgroupIndex.sort((a, b) => sortSubgroups(matrix[i * n + a], matrix[i * n + b])); + for (const j of subgroupIndex) { + let chord; + if (i < j) { + chord = chords[i * n + j] || (chords[i * n + j] = {source: null, target: null}); + chord.source = {index: i, startAngle: x, endAngle: x += matrix[i * n + j] * k, value: matrix[i * n + j]}; + } else { + chord = chords[j * n + i] || (chords[j * n + i] = {source: null, target: null}); + chord.target = {index: i, startAngle: x, endAngle: x += matrix[i * n + j] * k, value: matrix[i * n + j]}; + if (i === j) chord.source = chord.target; + } + if (chord.source && chord.target && chord.source.value < chord.target.value) { + const source = chord.source; + chord.source = chord.target; + chord.target = source; + } + } + groups[i] = {index: i, startAngle: x0, endAngle: x, value: groupSums[i]}; + } + x += dx; + } + } + + // Remove empty chords. + chords = Object.values(chords); + chords.groups = groups; + return sortChords ? chords.sort(sortChords) : chords; + } + + chord.padAngle = function(_) { + return arguments.length ? (padAngle = max$1(0, _), chord) : padAngle; + }; + + chord.sortGroups = function(_) { + return arguments.length ? (sortGroups = _, chord) : sortGroups; + }; + + chord.sortSubgroups = function(_) { + return arguments.length ? (sortSubgroups = _, chord) : sortSubgroups; + }; + + chord.sortChords = function(_) { + return arguments.length ? (_ == null ? sortChords = null : (sortChords = compareValue(_))._ = _, chord) : sortChords && sortChords._; + }; + + return chord; +} + +const pi$2 = Math.PI, + tau$3 = 2 * pi$2, + epsilon$4 = 1e-6, + tauEpsilon = tau$3 - epsilon$4; + +function append$1(strings) { + this._ += strings[0]; + for (let i = 1, n = strings.length; i < n; ++i) { + this._ += arguments[i] + strings[i]; + } +} + +function appendRound$1(digits) { + let d = Math.floor(digits); + if (!(d >= 0)) throw new Error(`invalid digits: ${digits}`); + if (d > 15) return append$1; + const k = 10 ** d; + return function(strings) { + this._ += strings[0]; + for (let i = 1, n = strings.length; i < n; ++i) { + this._ += Math.round(arguments[i] * k) / k + strings[i]; + } + }; +} + +let Path$1 = class Path { + constructor(digits) { + this._x0 = this._y0 = // start of current subpath + this._x1 = this._y1 = null; // end of current subpath + this._ = ""; + this._append = digits == null ? append$1 : appendRound$1(digits); + } + moveTo(x, y) { + this._append`M${this._x0 = this._x1 = +x},${this._y0 = this._y1 = +y}`; + } + closePath() { + if (this._x1 !== null) { + this._x1 = this._x0, this._y1 = this._y0; + this._append`Z`; + } + } + lineTo(x, y) { + this._append`L${this._x1 = +x},${this._y1 = +y}`; + } + quadraticCurveTo(x1, y1, x, y) { + this._append`Q${+x1},${+y1},${this._x1 = +x},${this._y1 = +y}`; + } + bezierCurveTo(x1, y1, x2, y2, x, y) { + this._append`C${+x1},${+y1},${+x2},${+y2},${this._x1 = +x},${this._y1 = +y}`; + } + arcTo(x1, y1, x2, y2, r) { + x1 = +x1, y1 = +y1, x2 = +x2, y2 = +y2, r = +r; + + // Is the radius negative? Error. + if (r < 0) throw new Error(`negative radius: ${r}`); + + let x0 = this._x1, + y0 = this._y1, + x21 = x2 - x1, + y21 = y2 - y1, + x01 = x0 - x1, + y01 = y0 - y1, + l01_2 = x01 * x01 + y01 * y01; + + // Is this path empty? Move to (x1,y1). + if (this._x1 === null) { + this._append`M${this._x1 = x1},${this._y1 = y1}`; + } + + // Or, is (x1,y1) coincident with (x0,y0)? Do nothing. + else if (!(l01_2 > epsilon$4)); + + // Or, are (x0,y0), (x1,y1) and (x2,y2) collinear? + // Equivalently, is (x1,y1) coincident with (x2,y2)? + // Or, is the radius zero? Line to (x1,y1). + else if (!(Math.abs(y01 * x21 - y21 * x01) > epsilon$4) || !r) { + this._append`L${this._x1 = x1},${this._y1 = y1}`; + } + + // Otherwise, draw an arc! + else { + let x20 = x2 - x0, + y20 = y2 - y0, + l21_2 = x21 * x21 + y21 * y21, + l20_2 = x20 * x20 + y20 * y20, + l21 = Math.sqrt(l21_2), + l01 = Math.sqrt(l01_2), + l = r * Math.tan((pi$2 - Math.acos((l21_2 + l01_2 - l20_2) / (2 * l21 * l01))) / 2), + t01 = l / l01, + t21 = l / l21; + + // If the start tangent is not coincident with (x0,y0), line to. + if (Math.abs(t01 - 1) > epsilon$4) { + this._append`L${x1 + t01 * x01},${y1 + t01 * y01}`; + } + + this._append`A${r},${r},0,0,${+(y01 * x20 > x01 * y20)},${this._x1 = x1 + t21 * x21},${this._y1 = y1 + t21 * y21}`; + } + } + arc(x, y, r, a0, a1, ccw) { + x = +x, y = +y, r = +r, ccw = !!ccw; + + // Is the radius negative? Error. + if (r < 0) throw new Error(`negative radius: ${r}`); + + let dx = r * Math.cos(a0), + dy = r * Math.sin(a0), + x0 = x + dx, + y0 = y + dy, + cw = 1 ^ ccw, + da = ccw ? a0 - a1 : a1 - a0; + + // Is this path empty? Move to (x0,y0). + if (this._x1 === null) { + this._append`M${x0},${y0}`; + } + + // Or, is (x0,y0) not coincident with the previous point? Line to (x0,y0). + else if (Math.abs(this._x1 - x0) > epsilon$4 || Math.abs(this._y1 - y0) > epsilon$4) { + this._append`L${x0},${y0}`; + } + + // Is this arc empty? We’re done. + if (!r) return; + + // Does the angle go the wrong way? Flip the direction. + if (da < 0) da = da % tau$3 + tau$3; + + // Is this a complete circle? Draw two arcs to complete the circle. + if (da > tauEpsilon) { + this._append`A${r},${r},0,1,${cw},${x - dx},${y - dy}A${r},${r},0,1,${cw},${this._x1 = x0},${this._y1 = y0}`; + } + + // Is this arc non-empty? Draw an arc! + else if (da > epsilon$4) { + this._append`A${r},${r},0,${+(da >= pi$2)},${cw},${this._x1 = x + r * Math.cos(a1)},${this._y1 = y + r * Math.sin(a1)}`; + } + } + rect(x, y, w, h) { + this._append`M${this._x0 = this._x1 = +x},${this._y0 = this._y1 = +y}h${w = +w}v${+h}h${-w}Z`; + } + toString() { + return this._; + } +}; + +function path() { + return new Path$1; +} + +// Allow instanceof d3.path +path.prototype = Path$1.prototype; + +function pathRound(digits = 3) { + return new Path$1(+digits); +} + +var slice$2 = Array.prototype.slice; + +function constant$6(x) { + return function() { + return x; + }; +} + +function defaultSource$1(d) { + return d.source; +} + +function defaultTarget(d) { + return d.target; +} + +function defaultRadius$1(d) { + return d.radius; +} + +function defaultStartAngle(d) { + return d.startAngle; +} + +function defaultEndAngle(d) { + return d.endAngle; +} + +function defaultPadAngle() { + return 0; +} + +function defaultArrowheadRadius() { + return 10; +} + +function ribbon(headRadius) { + var source = defaultSource$1, + target = defaultTarget, + sourceRadius = defaultRadius$1, + targetRadius = defaultRadius$1, + startAngle = defaultStartAngle, + endAngle = defaultEndAngle, + padAngle = defaultPadAngle, + context = null; + + function ribbon() { + var buffer, + s = source.apply(this, arguments), + t = target.apply(this, arguments), + ap = padAngle.apply(this, arguments) / 2, + argv = slice$2.call(arguments), + sr = +sourceRadius.apply(this, (argv[0] = s, argv)), + sa0 = startAngle.apply(this, argv) - halfPi$2, + sa1 = endAngle.apply(this, argv) - halfPi$2, + tr = +targetRadius.apply(this, (argv[0] = t, argv)), + ta0 = startAngle.apply(this, argv) - halfPi$2, + ta1 = endAngle.apply(this, argv) - halfPi$2; + + if (!context) context = buffer = path(); + + if (ap > epsilon$5) { + if (abs$2(sa1 - sa0) > ap * 2 + epsilon$5) sa1 > sa0 ? (sa0 += ap, sa1 -= ap) : (sa0 -= ap, sa1 += ap); + else sa0 = sa1 = (sa0 + sa1) / 2; + if (abs$2(ta1 - ta0) > ap * 2 + epsilon$5) ta1 > ta0 ? (ta0 += ap, ta1 -= ap) : (ta0 -= ap, ta1 += ap); + else ta0 = ta1 = (ta0 + ta1) / 2; + } + + context.moveTo(sr * cos$2(sa0), sr * sin$2(sa0)); + context.arc(0, 0, sr, sa0, sa1); + if (sa0 !== ta0 || sa1 !== ta1) { + if (headRadius) { + var hr = +headRadius.apply(this, arguments), tr2 = tr - hr, ta2 = (ta0 + ta1) / 2; + context.quadraticCurveTo(0, 0, tr2 * cos$2(ta0), tr2 * sin$2(ta0)); + context.lineTo(tr * cos$2(ta2), tr * sin$2(ta2)); + context.lineTo(tr2 * cos$2(ta1), tr2 * sin$2(ta1)); + } else { + context.quadraticCurveTo(0, 0, tr * cos$2(ta0), tr * sin$2(ta0)); + context.arc(0, 0, tr, ta0, ta1); + } + } + context.quadraticCurveTo(0, 0, sr * cos$2(sa0), sr * sin$2(sa0)); + context.closePath(); + + if (buffer) return context = null, buffer + "" || null; + } + + if (headRadius) ribbon.headRadius = function(_) { + return arguments.length ? (headRadius = typeof _ === "function" ? _ : constant$6(+_), ribbon) : headRadius; + }; + + ribbon.radius = function(_) { + return arguments.length ? (sourceRadius = targetRadius = typeof _ === "function" ? _ : constant$6(+_), ribbon) : sourceRadius; + }; + + ribbon.sourceRadius = function(_) { + return arguments.length ? (sourceRadius = typeof _ === "function" ? _ : constant$6(+_), ribbon) : sourceRadius; + }; + + ribbon.targetRadius = function(_) { + return arguments.length ? (targetRadius = typeof _ === "function" ? _ : constant$6(+_), ribbon) : targetRadius; + }; + + ribbon.startAngle = function(_) { + return arguments.length ? (startAngle = typeof _ === "function" ? _ : constant$6(+_), ribbon) : startAngle; + }; + + ribbon.endAngle = function(_) { + return arguments.length ? (endAngle = typeof _ === "function" ? _ : constant$6(+_), ribbon) : endAngle; + }; + + ribbon.padAngle = function(_) { + return arguments.length ? (padAngle = typeof _ === "function" ? _ : constant$6(+_), ribbon) : padAngle; + }; + + ribbon.source = function(_) { + return arguments.length ? (source = _, ribbon) : source; + }; + + ribbon.target = function(_) { + return arguments.length ? (target = _, ribbon) : target; + }; + + ribbon.context = function(_) { + return arguments.length ? ((context = _ == null ? null : _), ribbon) : context; + }; + + return ribbon; +} + +function ribbon$1() { + return ribbon(); +} + +function ribbonArrow() { + return ribbon(defaultArrowheadRadius); +} + +var array$2 = Array.prototype; + +var slice$1 = array$2.slice; + +function ascending$1(a, b) { + return a - b; +} + +function area$3(ring) { + var i = 0, n = ring.length, area = ring[n - 1][1] * ring[0][0] - ring[n - 1][0] * ring[0][1]; + while (++i < n) area += ring[i - 1][1] * ring[i][0] - ring[i - 1][0] * ring[i][1]; + return area; +} + +var constant$5 = x => () => x; + +function contains$2(ring, hole) { + var i = -1, n = hole.length, c; + while (++i < n) if (c = ringContains(ring, hole[i])) return c; + return 0; +} + +function ringContains(ring, point) { + var x = point[0], y = point[1], contains = -1; + for (var i = 0, n = ring.length, j = n - 1; i < n; j = i++) { + var pi = ring[i], xi = pi[0], yi = pi[1], pj = ring[j], xj = pj[0], yj = pj[1]; + if (segmentContains(pi, pj, point)) return 0; + if (((yi > y) !== (yj > y)) && ((x < (xj - xi) * (y - yi) / (yj - yi) + xi))) contains = -contains; + } + return contains; +} + +function segmentContains(a, b, c) { + var i; return collinear$1(a, b, c) && within(a[i = +(a[0] === b[0])], c[i], b[i]); +} + +function collinear$1(a, b, c) { + return (b[0] - a[0]) * (c[1] - a[1]) === (c[0] - a[0]) * (b[1] - a[1]); +} + +function within(p, q, r) { + return p <= q && q <= r || r <= q && q <= p; +} + +function noop$2() {} + +var cases = [ + [], + [[[1.0, 1.5], [0.5, 1.0]]], + [[[1.5, 1.0], [1.0, 1.5]]], + [[[1.5, 1.0], [0.5, 1.0]]], + [[[1.0, 0.5], [1.5, 1.0]]], + [[[1.0, 1.5], [0.5, 1.0]], [[1.0, 0.5], [1.5, 1.0]]], + [[[1.0, 0.5], [1.0, 1.5]]], + [[[1.0, 0.5], [0.5, 1.0]]], + [[[0.5, 1.0], [1.0, 0.5]]], + [[[1.0, 1.5], [1.0, 0.5]]], + [[[0.5, 1.0], [1.0, 0.5]], [[1.5, 1.0], [1.0, 1.5]]], + [[[1.5, 1.0], [1.0, 0.5]]], + [[[0.5, 1.0], [1.5, 1.0]]], + [[[1.0, 1.5], [1.5, 1.0]]], + [[[0.5, 1.0], [1.0, 1.5]]], + [] +]; + +function Contours() { + var dx = 1, + dy = 1, + threshold = thresholdSturges, + smooth = smoothLinear; + + function contours(values) { + var tz = threshold(values); + + // Convert number of thresholds into uniform thresholds. + if (!Array.isArray(tz)) { + const e = extent$1(values, finite); + tz = ticks(...nice$1(e[0], e[1], tz), tz); + while (tz[tz.length - 1] >= e[1]) tz.pop(); + while (tz[1] < e[0]) tz.shift(); + } else { + tz = tz.slice().sort(ascending$1); + } + + return tz.map(value => contour(values, value)); + } + + // Accumulate, smooth contour rings, assign holes to exterior rings. + // Based on https://github.com/mbostock/shapefile/blob/v0.6.2/shp/polygon.js + function contour(values, value) { + const v = value == null ? NaN : +value; + if (isNaN(v)) throw new Error(`invalid value: ${value}`); + + var polygons = [], + holes = []; + + isorings(values, v, function(ring) { + smooth(ring, values, v); + if (area$3(ring) > 0) polygons.push([ring]); + else holes.push(ring); + }); + + holes.forEach(function(hole) { + for (var i = 0, n = polygons.length, polygon; i < n; ++i) { + if (contains$2((polygon = polygons[i])[0], hole) !== -1) { + polygon.push(hole); + return; + } + } + }); + + return { + type: "MultiPolygon", + value: value, + coordinates: polygons + }; + } + + // Marching squares with isolines stitched into rings. + // Based on https://github.com/topojson/topojson-client/blob/v3.0.0/src/stitch.js + function isorings(values, value, callback) { + var fragmentByStart = new Array, + fragmentByEnd = new Array, + x, y, t0, t1, t2, t3; + + // Special case for the first row (y = -1, t2 = t3 = 0). + x = y = -1; + t1 = above(values[0], value); + cases[t1 << 1].forEach(stitch); + while (++x < dx - 1) { + t0 = t1, t1 = above(values[x + 1], value); + cases[t0 | t1 << 1].forEach(stitch); + } + cases[t1 << 0].forEach(stitch); + + // General case for the intermediate rows. + while (++y < dy - 1) { + x = -1; + t1 = above(values[y * dx + dx], value); + t2 = above(values[y * dx], value); + cases[t1 << 1 | t2 << 2].forEach(stitch); + while (++x < dx - 1) { + t0 = t1, t1 = above(values[y * dx + dx + x + 1], value); + t3 = t2, t2 = above(values[y * dx + x + 1], value); + cases[t0 | t1 << 1 | t2 << 2 | t3 << 3].forEach(stitch); + } + cases[t1 | t2 << 3].forEach(stitch); + } + + // Special case for the last row (y = dy - 1, t0 = t1 = 0). + x = -1; + t2 = values[y * dx] >= value; + cases[t2 << 2].forEach(stitch); + while (++x < dx - 1) { + t3 = t2, t2 = above(values[y * dx + x + 1], value); + cases[t2 << 2 | t3 << 3].forEach(stitch); + } + cases[t2 << 3].forEach(stitch); + + function stitch(line) { + var start = [line[0][0] + x, line[0][1] + y], + end = [line[1][0] + x, line[1][1] + y], + startIndex = index(start), + endIndex = index(end), + f, g; + if (f = fragmentByEnd[startIndex]) { + if (g = fragmentByStart[endIndex]) { + delete fragmentByEnd[f.end]; + delete fragmentByStart[g.start]; + if (f === g) { + f.ring.push(end); + callback(f.ring); + } else { + fragmentByStart[f.start] = fragmentByEnd[g.end] = {start: f.start, end: g.end, ring: f.ring.concat(g.ring)}; + } + } else { + delete fragmentByEnd[f.end]; + f.ring.push(end); + fragmentByEnd[f.end = endIndex] = f; + } + } else if (f = fragmentByStart[endIndex]) { + if (g = fragmentByEnd[startIndex]) { + delete fragmentByStart[f.start]; + delete fragmentByEnd[g.end]; + if (f === g) { + f.ring.push(end); + callback(f.ring); + } else { + fragmentByStart[g.start] = fragmentByEnd[f.end] = {start: g.start, end: f.end, ring: g.ring.concat(f.ring)}; + } + } else { + delete fragmentByStart[f.start]; + f.ring.unshift(start); + fragmentByStart[f.start = startIndex] = f; + } + } else { + fragmentByStart[startIndex] = fragmentByEnd[endIndex] = {start: startIndex, end: endIndex, ring: [start, end]}; + } + } + } + + function index(point) { + return point[0] * 2 + point[1] * (dx + 1) * 4; + } + + function smoothLinear(ring, values, value) { + ring.forEach(function(point) { + var x = point[0], + y = point[1], + xt = x | 0, + yt = y | 0, + v1 = valid(values[yt * dx + xt]); + if (x > 0 && x < dx && xt === x) { + point[0] = smooth1(x, valid(values[yt * dx + xt - 1]), v1, value); + } + if (y > 0 && y < dy && yt === y) { + point[1] = smooth1(y, valid(values[(yt - 1) * dx + xt]), v1, value); + } + }); + } + + contours.contour = contour; + + contours.size = function(_) { + if (!arguments.length) return [dx, dy]; + var _0 = Math.floor(_[0]), _1 = Math.floor(_[1]); + if (!(_0 >= 0 && _1 >= 0)) throw new Error("invalid size"); + return dx = _0, dy = _1, contours; + }; + + contours.thresholds = function(_) { + return arguments.length ? (threshold = typeof _ === "function" ? _ : Array.isArray(_) ? constant$5(slice$1.call(_)) : constant$5(_), contours) : threshold; + }; + + contours.smooth = function(_) { + return arguments.length ? (smooth = _ ? smoothLinear : noop$2, contours) : smooth === smoothLinear; + }; + + return contours; +} + +// When computing the extent, ignore infinite values (as well as invalid ones). +function finite(x) { + return isFinite(x) ? x : NaN; +} + +// Is the (possibly invalid) x greater than or equal to the (known valid) value? +// Treat any invalid value as below negative infinity. +function above(x, value) { + return x == null ? false : +x >= value; +} + +// During smoothing, treat any invalid value as negative infinity. +function valid(v) { + return v == null || isNaN(v = +v) ? -Infinity : v; +} + +function smooth1(x, v0, v1, value) { + const a = value - v0; + const b = v1 - v0; + const d = isFinite(a) || isFinite(b) ? a / b : Math.sign(a) / Math.sign(b); + return isNaN(d) ? x : x + d - 0.5; +} + +function defaultX$1(d) { + return d[0]; +} + +function defaultY$1(d) { + return d[1]; +} + +function defaultWeight() { + return 1; +} + +function density() { + var x = defaultX$1, + y = defaultY$1, + weight = defaultWeight, + dx = 960, + dy = 500, + r = 20, // blur radius + k = 2, // log2(grid cell size) + o = r * 3, // grid offset, to pad for blur + n = (dx + o * 2) >> k, // grid width + m = (dy + o * 2) >> k, // grid height + threshold = constant$5(20); + + function grid(data) { + var values = new Float32Array(n * m), + pow2k = Math.pow(2, -k), + i = -1; + + for (const d of data) { + var xi = (x(d, ++i, data) + o) * pow2k, + yi = (y(d, i, data) + o) * pow2k, + wi = +weight(d, i, data); + if (wi && xi >= 0 && xi < n && yi >= 0 && yi < m) { + var x0 = Math.floor(xi), + y0 = Math.floor(yi), + xt = xi - x0 - 0.5, + yt = yi - y0 - 0.5; + values[x0 + y0 * n] += (1 - xt) * (1 - yt) * wi; + values[x0 + 1 + y0 * n] += xt * (1 - yt) * wi; + values[x0 + 1 + (y0 + 1) * n] += xt * yt * wi; + values[x0 + (y0 + 1) * n] += (1 - xt) * yt * wi; + } + } + + blur2({data: values, width: n, height: m}, r * pow2k); + return values; + } + + function density(data) { + var values = grid(data), + tz = threshold(values), + pow4k = Math.pow(2, 2 * k); + + // Convert number of thresholds into uniform thresholds. + if (!Array.isArray(tz)) { + tz = ticks(Number.MIN_VALUE, max$3(values) / pow4k, tz); + } + + return Contours() + .size([n, m]) + .thresholds(tz.map(d => d * pow4k)) + (values) + .map((c, i) => (c.value = +tz[i], transform(c))); + } + + density.contours = function(data) { + var values = grid(data), + contours = Contours().size([n, m]), + pow4k = Math.pow(2, 2 * k), + contour = value => { + value = +value; + var c = transform(contours.contour(values, value * pow4k)); + c.value = value; // preserve exact threshold value + return c; + }; + Object.defineProperty(contour, "max", {get: () => max$3(values) / pow4k}); + return contour; + }; + + function transform(geometry) { + geometry.coordinates.forEach(transformPolygon); + return geometry; + } + + function transformPolygon(coordinates) { + coordinates.forEach(transformRing); + } + + function transformRing(coordinates) { + coordinates.forEach(transformPoint); + } + + // TODO Optimize. + function transformPoint(coordinates) { + coordinates[0] = coordinates[0] * Math.pow(2, k) - o; + coordinates[1] = coordinates[1] * Math.pow(2, k) - o; + } + + function resize() { + o = r * 3; + n = (dx + o * 2) >> k; + m = (dy + o * 2) >> k; + return density; + } + + density.x = function(_) { + return arguments.length ? (x = typeof _ === "function" ? _ : constant$5(+_), density) : x; + }; + + density.y = function(_) { + return arguments.length ? (y = typeof _ === "function" ? _ : constant$5(+_), density) : y; + }; + + density.weight = function(_) { + return arguments.length ? (weight = typeof _ === "function" ? _ : constant$5(+_), density) : weight; + }; + + density.size = function(_) { + if (!arguments.length) return [dx, dy]; + var _0 = +_[0], _1 = +_[1]; + if (!(_0 >= 0 && _1 >= 0)) throw new Error("invalid size"); + return dx = _0, dy = _1, resize(); + }; + + density.cellSize = function(_) { + if (!arguments.length) return 1 << k; + if (!((_ = +_) >= 1)) throw new Error("invalid cell size"); + return k = Math.floor(Math.log(_) / Math.LN2), resize(); + }; + + density.thresholds = function(_) { + return arguments.length ? (threshold = typeof _ === "function" ? _ : Array.isArray(_) ? constant$5(slice$1.call(_)) : constant$5(_), density) : threshold; + }; + + density.bandwidth = function(_) { + if (!arguments.length) return Math.sqrt(r * (r + 1)); + if (!((_ = +_) >= 0)) throw new Error("invalid bandwidth"); + return r = (Math.sqrt(4 * _ * _ + 1) - 1) / 2, resize(); + }; + + return density; +} + +const epsilon$3 = 1.1102230246251565e-16; +const splitter = 134217729; +const resulterrbound = (3 + 8 * epsilon$3) * epsilon$3; + +// fast_expansion_sum_zeroelim routine from oritinal code +function sum$1(elen, e, flen, f, h) { + let Q, Qnew, hh, bvirt; + let enow = e[0]; + let fnow = f[0]; + let eindex = 0; + let findex = 0; + if ((fnow > enow) === (fnow > -enow)) { + Q = enow; + enow = e[++eindex]; + } else { + Q = fnow; + fnow = f[++findex]; + } + let hindex = 0; + if (eindex < elen && findex < flen) { + if ((fnow > enow) === (fnow > -enow)) { + Qnew = enow + Q; + hh = Q - (Qnew - enow); + enow = e[++eindex]; + } else { + Qnew = fnow + Q; + hh = Q - (Qnew - fnow); + fnow = f[++findex]; + } + Q = Qnew; + if (hh !== 0) { + h[hindex++] = hh; + } + while (eindex < elen && findex < flen) { + if ((fnow > enow) === (fnow > -enow)) { + Qnew = Q + enow; + bvirt = Qnew - Q; + hh = Q - (Qnew - bvirt) + (enow - bvirt); + enow = e[++eindex]; + } else { + Qnew = Q + fnow; + bvirt = Qnew - Q; + hh = Q - (Qnew - bvirt) + (fnow - bvirt); + fnow = f[++findex]; + } + Q = Qnew; + if (hh !== 0) { + h[hindex++] = hh; + } + } + } + while (eindex < elen) { + Qnew = Q + enow; + bvirt = Qnew - Q; + hh = Q - (Qnew - bvirt) + (enow - bvirt); + enow = e[++eindex]; + Q = Qnew; + if (hh !== 0) { + h[hindex++] = hh; + } + } + while (findex < flen) { + Qnew = Q + fnow; + bvirt = Qnew - Q; + hh = Q - (Qnew - bvirt) + (fnow - bvirt); + fnow = f[++findex]; + Q = Qnew; + if (hh !== 0) { + h[hindex++] = hh; + } + } + if (Q !== 0 || hindex === 0) { + h[hindex++] = Q; + } + return hindex; +} + +function estimate(elen, e) { + let Q = e[0]; + for (let i = 1; i < elen; i++) Q += e[i]; + return Q; +} + +function vec(n) { + return new Float64Array(n); +} + +const ccwerrboundA = (3 + 16 * epsilon$3) * epsilon$3; +const ccwerrboundB = (2 + 12 * epsilon$3) * epsilon$3; +const ccwerrboundC = (9 + 64 * epsilon$3) * epsilon$3 * epsilon$3; + +const B = vec(4); +const C1 = vec(8); +const C2 = vec(12); +const D = vec(16); +const u = vec(4); + +function orient2dadapt(ax, ay, bx, by, cx, cy, detsum) { + let acxtail, acytail, bcxtail, bcytail; + let bvirt, c, ahi, alo, bhi, blo, _i, _j, _0, s1, s0, t1, t0, u3; + + const acx = ax - cx; + const bcx = bx - cx; + const acy = ay - cy; + const bcy = by - cy; + + s1 = acx * bcy; + c = splitter * acx; + ahi = c - (c - acx); + alo = acx - ahi; + c = splitter * bcy; + bhi = c - (c - bcy); + blo = bcy - bhi; + s0 = alo * blo - (s1 - ahi * bhi - alo * bhi - ahi * blo); + t1 = acy * bcx; + c = splitter * acy; + ahi = c - (c - acy); + alo = acy - ahi; + c = splitter * bcx; + bhi = c - (c - bcx); + blo = bcx - bhi; + t0 = alo * blo - (t1 - ahi * bhi - alo * bhi - ahi * blo); + _i = s0 - t0; + bvirt = s0 - _i; + B[0] = s0 - (_i + bvirt) + (bvirt - t0); + _j = s1 + _i; + bvirt = _j - s1; + _0 = s1 - (_j - bvirt) + (_i - bvirt); + _i = _0 - t1; + bvirt = _0 - _i; + B[1] = _0 - (_i + bvirt) + (bvirt - t1); + u3 = _j + _i; + bvirt = u3 - _j; + B[2] = _j - (u3 - bvirt) + (_i - bvirt); + B[3] = u3; + + let det = estimate(4, B); + let errbound = ccwerrboundB * detsum; + if (det >= errbound || -det >= errbound) { + return det; + } + + bvirt = ax - acx; + acxtail = ax - (acx + bvirt) + (bvirt - cx); + bvirt = bx - bcx; + bcxtail = bx - (bcx + bvirt) + (bvirt - cx); + bvirt = ay - acy; + acytail = ay - (acy + bvirt) + (bvirt - cy); + bvirt = by - bcy; + bcytail = by - (bcy + bvirt) + (bvirt - cy); + + if (acxtail === 0 && acytail === 0 && bcxtail === 0 && bcytail === 0) { + return det; + } + + errbound = ccwerrboundC * detsum + resulterrbound * Math.abs(det); + det += (acx * bcytail + bcy * acxtail) - (acy * bcxtail + bcx * acytail); + if (det >= errbound || -det >= errbound) return det; + + s1 = acxtail * bcy; + c = splitter * acxtail; + ahi = c - (c - acxtail); + alo = acxtail - ahi; + c = splitter * bcy; + bhi = c - (c - bcy); + blo = bcy - bhi; + s0 = alo * blo - (s1 - ahi * bhi - alo * bhi - ahi * blo); + t1 = acytail * bcx; + c = splitter * acytail; + ahi = c - (c - acytail); + alo = acytail - ahi; + c = splitter * bcx; + bhi = c - (c - bcx); + blo = bcx - bhi; + t0 = alo * blo - (t1 - ahi * bhi - alo * bhi - ahi * blo); + _i = s0 - t0; + bvirt = s0 - _i; + u[0] = s0 - (_i + bvirt) + (bvirt - t0); + _j = s1 + _i; + bvirt = _j - s1; + _0 = s1 - (_j - bvirt) + (_i - bvirt); + _i = _0 - t1; + bvirt = _0 - _i; + u[1] = _0 - (_i + bvirt) + (bvirt - t1); + u3 = _j + _i; + bvirt = u3 - _j; + u[2] = _j - (u3 - bvirt) + (_i - bvirt); + u[3] = u3; + const C1len = sum$1(4, B, 4, u, C1); + + s1 = acx * bcytail; + c = splitter * acx; + ahi = c - (c - acx); + alo = acx - ahi; + c = splitter * bcytail; + bhi = c - (c - bcytail); + blo = bcytail - bhi; + s0 = alo * blo - (s1 - ahi * bhi - alo * bhi - ahi * blo); + t1 = acy * bcxtail; + c = splitter * acy; + ahi = c - (c - acy); + alo = acy - ahi; + c = splitter * bcxtail; + bhi = c - (c - bcxtail); + blo = bcxtail - bhi; + t0 = alo * blo - (t1 - ahi * bhi - alo * bhi - ahi * blo); + _i = s0 - t0; + bvirt = s0 - _i; + u[0] = s0 - (_i + bvirt) + (bvirt - t0); + _j = s1 + _i; + bvirt = _j - s1; + _0 = s1 - (_j - bvirt) + (_i - bvirt); + _i = _0 - t1; + bvirt = _0 - _i; + u[1] = _0 - (_i + bvirt) + (bvirt - t1); + u3 = _j + _i; + bvirt = u3 - _j; + u[2] = _j - (u3 - bvirt) + (_i - bvirt); + u[3] = u3; + const C2len = sum$1(C1len, C1, 4, u, C2); + + s1 = acxtail * bcytail; + c = splitter * acxtail; + ahi = c - (c - acxtail); + alo = acxtail - ahi; + c = splitter * bcytail; + bhi = c - (c - bcytail); + blo = bcytail - bhi; + s0 = alo * blo - (s1 - ahi * bhi - alo * bhi - ahi * blo); + t1 = acytail * bcxtail; + c = splitter * acytail; + ahi = c - (c - acytail); + alo = acytail - ahi; + c = splitter * bcxtail; + bhi = c - (c - bcxtail); + blo = bcxtail - bhi; + t0 = alo * blo - (t1 - ahi * bhi - alo * bhi - ahi * blo); + _i = s0 - t0; + bvirt = s0 - _i; + u[0] = s0 - (_i + bvirt) + (bvirt - t0); + _j = s1 + _i; + bvirt = _j - s1; + _0 = s1 - (_j - bvirt) + (_i - bvirt); + _i = _0 - t1; + bvirt = _0 - _i; + u[1] = _0 - (_i + bvirt) + (bvirt - t1); + u3 = _j + _i; + bvirt = u3 - _j; + u[2] = _j - (u3 - bvirt) + (_i - bvirt); + u[3] = u3; + const Dlen = sum$1(C2len, C2, 4, u, D); + + return D[Dlen - 1]; +} + +function orient2d(ax, ay, bx, by, cx, cy) { + const detleft = (ay - cy) * (bx - cx); + const detright = (ax - cx) * (by - cy); + const det = detleft - detright; + + const detsum = Math.abs(detleft + detright); + if (Math.abs(det) >= ccwerrboundA * detsum) return det; + + return -orient2dadapt(ax, ay, bx, by, cx, cy, detsum); +} + +const EPSILON = Math.pow(2, -52); +const EDGE_STACK = new Uint32Array(512); + +class Delaunator { + + static from(points, getX = defaultGetX, getY = defaultGetY) { + const n = points.length; + const coords = new Float64Array(n * 2); + + for (let i = 0; i < n; i++) { + const p = points[i]; + coords[2 * i] = getX(p); + coords[2 * i + 1] = getY(p); + } + + return new Delaunator(coords); + } + + constructor(coords) { + const n = coords.length >> 1; + if (n > 0 && typeof coords[0] !== 'number') throw new Error('Expected coords to contain numbers.'); + + this.coords = coords; + + // arrays that will store the triangulation graph + const maxTriangles = Math.max(2 * n - 5, 0); + this._triangles = new Uint32Array(maxTriangles * 3); + this._halfedges = new Int32Array(maxTriangles * 3); + + // temporary arrays for tracking the edges of the advancing convex hull + this._hashSize = Math.ceil(Math.sqrt(n)); + this._hullPrev = new Uint32Array(n); // edge to prev edge + this._hullNext = new Uint32Array(n); // edge to next edge + this._hullTri = new Uint32Array(n); // edge to adjacent triangle + this._hullHash = new Int32Array(this._hashSize); // angular edge hash + + // temporary arrays for sorting points + this._ids = new Uint32Array(n); + this._dists = new Float64Array(n); + + this.update(); + } + + update() { + const {coords, _hullPrev: hullPrev, _hullNext: hullNext, _hullTri: hullTri, _hullHash: hullHash} = this; + const n = coords.length >> 1; + + // populate an array of point indices; calculate input data bbox + let minX = Infinity; + let minY = Infinity; + let maxX = -Infinity; + let maxY = -Infinity; + + for (let i = 0; i < n; i++) { + const x = coords[2 * i]; + const y = coords[2 * i + 1]; + if (x < minX) minX = x; + if (y < minY) minY = y; + if (x > maxX) maxX = x; + if (y > maxY) maxY = y; + this._ids[i] = i; + } + const cx = (minX + maxX) / 2; + const cy = (minY + maxY) / 2; + + let i0, i1, i2; + + // pick a seed point close to the center + for (let i = 0, minDist = Infinity; i < n; i++) { + const d = dist(cx, cy, coords[2 * i], coords[2 * i + 1]); + if (d < minDist) { + i0 = i; + minDist = d; + } + } + const i0x = coords[2 * i0]; + const i0y = coords[2 * i0 + 1]; + + // find the point closest to the seed + for (let i = 0, minDist = Infinity; i < n; i++) { + if (i === i0) continue; + const d = dist(i0x, i0y, coords[2 * i], coords[2 * i + 1]); + if (d < minDist && d > 0) { + i1 = i; + minDist = d; + } + } + let i1x = coords[2 * i1]; + let i1y = coords[2 * i1 + 1]; + + let minRadius = Infinity; + + // find the third point which forms the smallest circumcircle with the first two + for (let i = 0; i < n; i++) { + if (i === i0 || i === i1) continue; + const r = circumradius(i0x, i0y, i1x, i1y, coords[2 * i], coords[2 * i + 1]); + if (r < minRadius) { + i2 = i; + minRadius = r; + } + } + let i2x = coords[2 * i2]; + let i2y = coords[2 * i2 + 1]; + + if (minRadius === Infinity) { + // order collinear points by dx (or dy if all x are identical) + // and return the list as a hull + for (let i = 0; i < n; i++) { + this._dists[i] = (coords[2 * i] - coords[0]) || (coords[2 * i + 1] - coords[1]); + } + quicksort(this._ids, this._dists, 0, n - 1); + const hull = new Uint32Array(n); + let j = 0; + for (let i = 0, d0 = -Infinity; i < n; i++) { + const id = this._ids[i]; + const d = this._dists[id]; + if (d > d0) { + hull[j++] = id; + d0 = d; + } + } + this.hull = hull.subarray(0, j); + this.triangles = new Uint32Array(0); + this.halfedges = new Uint32Array(0); + return; + } + + // swap the order of the seed points for counter-clockwise orientation + if (orient2d(i0x, i0y, i1x, i1y, i2x, i2y) < 0) { + const i = i1; + const x = i1x; + const y = i1y; + i1 = i2; + i1x = i2x; + i1y = i2y; + i2 = i; + i2x = x; + i2y = y; + } + + const center = circumcenter(i0x, i0y, i1x, i1y, i2x, i2y); + this._cx = center.x; + this._cy = center.y; + + for (let i = 0; i < n; i++) { + this._dists[i] = dist(coords[2 * i], coords[2 * i + 1], center.x, center.y); + } + + // sort the points by distance from the seed triangle circumcenter + quicksort(this._ids, this._dists, 0, n - 1); + + // set up the seed triangle as the starting hull + this._hullStart = i0; + let hullSize = 3; + + hullNext[i0] = hullPrev[i2] = i1; + hullNext[i1] = hullPrev[i0] = i2; + hullNext[i2] = hullPrev[i1] = i0; + + hullTri[i0] = 0; + hullTri[i1] = 1; + hullTri[i2] = 2; + + hullHash.fill(-1); + hullHash[this._hashKey(i0x, i0y)] = i0; + hullHash[this._hashKey(i1x, i1y)] = i1; + hullHash[this._hashKey(i2x, i2y)] = i2; + + this.trianglesLen = 0; + this._addTriangle(i0, i1, i2, -1, -1, -1); + + for (let k = 0, xp, yp; k < this._ids.length; k++) { + const i = this._ids[k]; + const x = coords[2 * i]; + const y = coords[2 * i + 1]; + + // skip near-duplicate points + if (k > 0 && Math.abs(x - xp) <= EPSILON && Math.abs(y - yp) <= EPSILON) continue; + xp = x; + yp = y; + + // skip seed triangle points + if (i === i0 || i === i1 || i === i2) continue; + + // find a visible edge on the convex hull using edge hash + let start = 0; + for (let j = 0, key = this._hashKey(x, y); j < this._hashSize; j++) { + start = hullHash[(key + j) % this._hashSize]; + if (start !== -1 && start !== hullNext[start]) break; + } + + start = hullPrev[start]; + let e = start, q; + while (q = hullNext[e], orient2d(x, y, coords[2 * e], coords[2 * e + 1], coords[2 * q], coords[2 * q + 1]) >= 0) { + e = q; + if (e === start) { + e = -1; + break; + } + } + if (e === -1) continue; // likely a near-duplicate point; skip it + + // add the first triangle from the point + let t = this._addTriangle(e, i, hullNext[e], -1, -1, hullTri[e]); + + // recursively flip triangles from the point until they satisfy the Delaunay condition + hullTri[i] = this._legalize(t + 2); + hullTri[e] = t; // keep track of boundary triangles on the hull + hullSize++; + + // walk forward through the hull, adding more triangles and flipping recursively + let n = hullNext[e]; + while (q = hullNext[n], orient2d(x, y, coords[2 * n], coords[2 * n + 1], coords[2 * q], coords[2 * q + 1]) < 0) { + t = this._addTriangle(n, i, q, hullTri[i], -1, hullTri[n]); + hullTri[i] = this._legalize(t + 2); + hullNext[n] = n; // mark as removed + hullSize--; + n = q; + } + + // walk backward from the other side, adding more triangles and flipping + if (e === start) { + while (q = hullPrev[e], orient2d(x, y, coords[2 * q], coords[2 * q + 1], coords[2 * e], coords[2 * e + 1]) < 0) { + t = this._addTriangle(q, i, e, -1, hullTri[e], hullTri[q]); + this._legalize(t + 2); + hullTri[q] = t; + hullNext[e] = e; // mark as removed + hullSize--; + e = q; + } + } + + // update the hull indices + this._hullStart = hullPrev[i] = e; + hullNext[e] = hullPrev[n] = i; + hullNext[i] = n; + + // save the two new edges in the hash table + hullHash[this._hashKey(x, y)] = i; + hullHash[this._hashKey(coords[2 * e], coords[2 * e + 1])] = e; + } + + this.hull = new Uint32Array(hullSize); + for (let i = 0, e = this._hullStart; i < hullSize; i++) { + this.hull[i] = e; + e = hullNext[e]; + } + + // trim typed triangle mesh arrays + this.triangles = this._triangles.subarray(0, this.trianglesLen); + this.halfedges = this._halfedges.subarray(0, this.trianglesLen); + } + + _hashKey(x, y) { + return Math.floor(pseudoAngle(x - this._cx, y - this._cy) * this._hashSize) % this._hashSize; + } + + _legalize(a) { + const {_triangles: triangles, _halfedges: halfedges, coords} = this; + + let i = 0; + let ar = 0; + + // recursion eliminated with a fixed-size stack + while (true) { + const b = halfedges[a]; + + /* if the pair of triangles doesn't satisfy the Delaunay condition + * (p1 is inside the circumcircle of [p0, pl, pr]), flip them, + * then do the same check/flip recursively for the new pair of triangles + * + * pl pl + * /||\ / \ + * al/ || \bl al/ \a + * / || \ / \ + * / a||b \ flip /___ar___\ + * p0\ || /p1 => p0\---bl---/p1 + * \ || / \ / + * ar\ || /br b\ /br + * \||/ \ / + * pr pr + */ + const a0 = a - a % 3; + ar = a0 + (a + 2) % 3; + + if (b === -1) { // convex hull edge + if (i === 0) break; + a = EDGE_STACK[--i]; + continue; + } + + const b0 = b - b % 3; + const al = a0 + (a + 1) % 3; + const bl = b0 + (b + 2) % 3; + + const p0 = triangles[ar]; + const pr = triangles[a]; + const pl = triangles[al]; + const p1 = triangles[bl]; + + const illegal = inCircle( + coords[2 * p0], coords[2 * p0 + 1], + coords[2 * pr], coords[2 * pr + 1], + coords[2 * pl], coords[2 * pl + 1], + coords[2 * p1], coords[2 * p1 + 1]); + + if (illegal) { + triangles[a] = p1; + triangles[b] = p0; + + const hbl = halfedges[bl]; + + // edge swapped on the other side of the hull (rare); fix the halfedge reference + if (hbl === -1) { + let e = this._hullStart; + do { + if (this._hullTri[e] === bl) { + this._hullTri[e] = a; + break; + } + e = this._hullPrev[e]; + } while (e !== this._hullStart); + } + this._link(a, hbl); + this._link(b, halfedges[ar]); + this._link(ar, bl); + + const br = b0 + (b + 1) % 3; + + // don't worry about hitting the cap: it can only happen on extremely degenerate input + if (i < EDGE_STACK.length) { + EDGE_STACK[i++] = br; + } + } else { + if (i === 0) break; + a = EDGE_STACK[--i]; + } + } + + return ar; + } + + _link(a, b) { + this._halfedges[a] = b; + if (b !== -1) this._halfedges[b] = a; + } + + // add a new triangle given vertex indices and adjacent half-edge ids + _addTriangle(i0, i1, i2, a, b, c) { + const t = this.trianglesLen; + + this._triangles[t] = i0; + this._triangles[t + 1] = i1; + this._triangles[t + 2] = i2; + + this._link(t, a); + this._link(t + 1, b); + this._link(t + 2, c); + + this.trianglesLen += 3; + + return t; + } +} + +// monotonically increases with real angle, but doesn't need expensive trigonometry +function pseudoAngle(dx, dy) { + const p = dx / (Math.abs(dx) + Math.abs(dy)); + return (dy > 0 ? 3 - p : 1 + p) / 4; // [0..1] +} + +function dist(ax, ay, bx, by) { + const dx = ax - bx; + const dy = ay - by; + return dx * dx + dy * dy; +} + +function inCircle(ax, ay, bx, by, cx, cy, px, py) { + const dx = ax - px; + const dy = ay - py; + const ex = bx - px; + const ey = by - py; + const fx = cx - px; + const fy = cy - py; + + const ap = dx * dx + dy * dy; + const bp = ex * ex + ey * ey; + const cp = fx * fx + fy * fy; + + return dx * (ey * cp - bp * fy) - + dy * (ex * cp - bp * fx) + + ap * (ex * fy - ey * fx) < 0; +} + +function circumradius(ax, ay, bx, by, cx, cy) { + const dx = bx - ax; + const dy = by - ay; + const ex = cx - ax; + const ey = cy - ay; + + const bl = dx * dx + dy * dy; + const cl = ex * ex + ey * ey; + const d = 0.5 / (dx * ey - dy * ex); + + const x = (ey * bl - dy * cl) * d; + const y = (dx * cl - ex * bl) * d; + + return x * x + y * y; +} + +function circumcenter(ax, ay, bx, by, cx, cy) { + const dx = bx - ax; + const dy = by - ay; + const ex = cx - ax; + const ey = cy - ay; + + const bl = dx * dx + dy * dy; + const cl = ex * ex + ey * ey; + const d = 0.5 / (dx * ey - dy * ex); + + const x = ax + (ey * bl - dy * cl) * d; + const y = ay + (dx * cl - ex * bl) * d; + + return {x, y}; +} + +function quicksort(ids, dists, left, right) { + if (right - left <= 20) { + for (let i = left + 1; i <= right; i++) { + const temp = ids[i]; + const tempDist = dists[temp]; + let j = i - 1; + while (j >= left && dists[ids[j]] > tempDist) ids[j + 1] = ids[j--]; + ids[j + 1] = temp; + } + } else { + const median = (left + right) >> 1; + let i = left + 1; + let j = right; + swap(ids, median, i); + if (dists[ids[left]] > dists[ids[right]]) swap(ids, left, right); + if (dists[ids[i]] > dists[ids[right]]) swap(ids, i, right); + if (dists[ids[left]] > dists[ids[i]]) swap(ids, left, i); + + const temp = ids[i]; + const tempDist = dists[temp]; + while (true) { + do i++; while (dists[ids[i]] < tempDist); + do j--; while (dists[ids[j]] > tempDist); + if (j < i) break; + swap(ids, i, j); + } + ids[left + 1] = ids[j]; + ids[j] = temp; + + if (right - i + 1 >= j - left) { + quicksort(ids, dists, i, right); + quicksort(ids, dists, left, j - 1); + } else { + quicksort(ids, dists, left, j - 1); + quicksort(ids, dists, i, right); + } + } +} + +function swap(arr, i, j) { + const tmp = arr[i]; + arr[i] = arr[j]; + arr[j] = tmp; +} + +function defaultGetX(p) { + return p[0]; +} +function defaultGetY(p) { + return p[1]; +} + +const epsilon$2 = 1e-6; + +class Path { + constructor() { + this._x0 = this._y0 = // start of current subpath + this._x1 = this._y1 = null; // end of current subpath + this._ = ""; + } + moveTo(x, y) { + this._ += `M${this._x0 = this._x1 = +x},${this._y0 = this._y1 = +y}`; + } + closePath() { + if (this._x1 !== null) { + this._x1 = this._x0, this._y1 = this._y0; + this._ += "Z"; + } + } + lineTo(x, y) { + this._ += `L${this._x1 = +x},${this._y1 = +y}`; + } + arc(x, y, r) { + x = +x, y = +y, r = +r; + const x0 = x + r; + const y0 = y; + if (r < 0) throw new Error("negative radius"); + if (this._x1 === null) this._ += `M${x0},${y0}`; + else if (Math.abs(this._x1 - x0) > epsilon$2 || Math.abs(this._y1 - y0) > epsilon$2) this._ += "L" + x0 + "," + y0; + if (!r) return; + this._ += `A${r},${r},0,1,1,${x - r},${y}A${r},${r},0,1,1,${this._x1 = x0},${this._y1 = y0}`; + } + rect(x, y, w, h) { + this._ += `M${this._x0 = this._x1 = +x},${this._y0 = this._y1 = +y}h${+w}v${+h}h${-w}Z`; + } + value() { + return this._ || null; + } +} + +class Polygon { + constructor() { + this._ = []; + } + moveTo(x, y) { + this._.push([x, y]); + } + closePath() { + this._.push(this._[0].slice()); + } + lineTo(x, y) { + this._.push([x, y]); + } + value() { + return this._.length ? this._ : null; + } +} + +class Voronoi { + constructor(delaunay, [xmin, ymin, xmax, ymax] = [0, 0, 960, 500]) { + if (!((xmax = +xmax) >= (xmin = +xmin)) || !((ymax = +ymax) >= (ymin = +ymin))) throw new Error("invalid bounds"); + this.delaunay = delaunay; + this._circumcenters = new Float64Array(delaunay.points.length * 2); + this.vectors = new Float64Array(delaunay.points.length * 2); + this.xmax = xmax, this.xmin = xmin; + this.ymax = ymax, this.ymin = ymin; + this._init(); + } + update() { + this.delaunay.update(); + this._init(); + return this; + } + _init() { + const {delaunay: {points, hull, triangles}, vectors} = this; + let bx, by; // lazily computed barycenter of the hull + + // Compute circumcenters. + const circumcenters = this.circumcenters = this._circumcenters.subarray(0, triangles.length / 3 * 2); + for (let i = 0, j = 0, n = triangles.length, x, y; i < n; i += 3, j += 2) { + const t1 = triangles[i] * 2; + const t2 = triangles[i + 1] * 2; + const t3 = triangles[i + 2] * 2; + const x1 = points[t1]; + const y1 = points[t1 + 1]; + const x2 = points[t2]; + const y2 = points[t2 + 1]; + const x3 = points[t3]; + const y3 = points[t3 + 1]; + + const dx = x2 - x1; + const dy = y2 - y1; + const ex = x3 - x1; + const ey = y3 - y1; + const ab = (dx * ey - dy * ex) * 2; + + if (Math.abs(ab) < 1e-9) { + // For a degenerate triangle, the circumcenter is at the infinity, in a + // direction orthogonal to the halfedge and away from the “center” of + // the diagram , defined as the hull’s barycenter. + if (bx === undefined) { + bx = by = 0; + for (const i of hull) bx += points[i * 2], by += points[i * 2 + 1]; + bx /= hull.length, by /= hull.length; + } + const a = 1e9 * Math.sign((bx - x1) * ey - (by - y1) * ex); + x = (x1 + x3) / 2 - a * ey; + y = (y1 + y3) / 2 + a * ex; + } else { + const d = 1 / ab; + const bl = dx * dx + dy * dy; + const cl = ex * ex + ey * ey; + x = x1 + (ey * bl - dy * cl) * d; + y = y1 + (dx * cl - ex * bl) * d; + } + circumcenters[j] = x; + circumcenters[j + 1] = y; + } + + // Compute exterior cell rays. + let h = hull[hull.length - 1]; + let p0, p1 = h * 4; + let x0, x1 = points[2 * h]; + let y0, y1 = points[2 * h + 1]; + vectors.fill(0); + for (let i = 0; i < hull.length; ++i) { + h = hull[i]; + p0 = p1, x0 = x1, y0 = y1; + p1 = h * 4, x1 = points[2 * h], y1 = points[2 * h + 1]; + vectors[p0 + 2] = vectors[p1] = y0 - y1; + vectors[p0 + 3] = vectors[p1 + 1] = x1 - x0; + } + } + render(context) { + const buffer = context == null ? context = new Path : undefined; + const {delaunay: {halfedges, inedges, hull}, circumcenters, vectors} = this; + if (hull.length <= 1) return null; + for (let i = 0, n = halfedges.length; i < n; ++i) { + const j = halfedges[i]; + if (j < i) continue; + const ti = Math.floor(i / 3) * 2; + const tj = Math.floor(j / 3) * 2; + const xi = circumcenters[ti]; + const yi = circumcenters[ti + 1]; + const xj = circumcenters[tj]; + const yj = circumcenters[tj + 1]; + this._renderSegment(xi, yi, xj, yj, context); + } + let h0, h1 = hull[hull.length - 1]; + for (let i = 0; i < hull.length; ++i) { + h0 = h1, h1 = hull[i]; + const t = Math.floor(inedges[h1] / 3) * 2; + const x = circumcenters[t]; + const y = circumcenters[t + 1]; + const v = h0 * 4; + const p = this._project(x, y, vectors[v + 2], vectors[v + 3]); + if (p) this._renderSegment(x, y, p[0], p[1], context); + } + return buffer && buffer.value(); + } + renderBounds(context) { + const buffer = context == null ? context = new Path : undefined; + context.rect(this.xmin, this.ymin, this.xmax - this.xmin, this.ymax - this.ymin); + return buffer && buffer.value(); + } + renderCell(i, context) { + const buffer = context == null ? context = new Path : undefined; + const points = this._clip(i); + if (points === null || !points.length) return; + context.moveTo(points[0], points[1]); + let n = points.length; + while (points[0] === points[n-2] && points[1] === points[n-1] && n > 1) n -= 2; + for (let i = 2; i < n; i += 2) { + if (points[i] !== points[i-2] || points[i+1] !== points[i-1]) + context.lineTo(points[i], points[i + 1]); + } + context.closePath(); + return buffer && buffer.value(); + } + *cellPolygons() { + const {delaunay: {points}} = this; + for (let i = 0, n = points.length / 2; i < n; ++i) { + const cell = this.cellPolygon(i); + if (cell) cell.index = i, yield cell; + } + } + cellPolygon(i) { + const polygon = new Polygon; + this.renderCell(i, polygon); + return polygon.value(); + } + _renderSegment(x0, y0, x1, y1, context) { + let S; + const c0 = this._regioncode(x0, y0); + const c1 = this._regioncode(x1, y1); + if (c0 === 0 && c1 === 0) { + context.moveTo(x0, y0); + context.lineTo(x1, y1); + } else if (S = this._clipSegment(x0, y0, x1, y1, c0, c1)) { + context.moveTo(S[0], S[1]); + context.lineTo(S[2], S[3]); + } + } + contains(i, x, y) { + if ((x = +x, x !== x) || (y = +y, y !== y)) return false; + return this.delaunay._step(i, x, y) === i; + } + *neighbors(i) { + const ci = this._clip(i); + if (ci) for (const j of this.delaunay.neighbors(i)) { + const cj = this._clip(j); + // find the common edge + if (cj) loop: for (let ai = 0, li = ci.length; ai < li; ai += 2) { + for (let aj = 0, lj = cj.length; aj < lj; aj += 2) { + if (ci[ai] === cj[aj] + && ci[ai + 1] === cj[aj + 1] + && ci[(ai + 2) % li] === cj[(aj + lj - 2) % lj] + && ci[(ai + 3) % li] === cj[(aj + lj - 1) % lj]) { + yield j; + break loop; + } + } + } + } + } + _cell(i) { + const {circumcenters, delaunay: {inedges, halfedges, triangles}} = this; + const e0 = inedges[i]; + if (e0 === -1) return null; // coincident point + const points = []; + let e = e0; + do { + const t = Math.floor(e / 3); + points.push(circumcenters[t * 2], circumcenters[t * 2 + 1]); + e = e % 3 === 2 ? e - 2 : e + 1; + if (triangles[e] !== i) break; // bad triangulation + e = halfedges[e]; + } while (e !== e0 && e !== -1); + return points; + } + _clip(i) { + // degenerate case (1 valid point: return the box) + if (i === 0 && this.delaunay.hull.length === 1) { + return [this.xmax, this.ymin, this.xmax, this.ymax, this.xmin, this.ymax, this.xmin, this.ymin]; + } + const points = this._cell(i); + if (points === null) return null; + const {vectors: V} = this; + const v = i * 4; + return this._simplify(V[v] || V[v + 1] + ? this._clipInfinite(i, points, V[v], V[v + 1], V[v + 2], V[v + 3]) + : this._clipFinite(i, points)); + } + _clipFinite(i, points) { + const n = points.length; + let P = null; + let x0, y0, x1 = points[n - 2], y1 = points[n - 1]; + let c0, c1 = this._regioncode(x1, y1); + let e0, e1 = 0; + for (let j = 0; j < n; j += 2) { + x0 = x1, y0 = y1, x1 = points[j], y1 = points[j + 1]; + c0 = c1, c1 = this._regioncode(x1, y1); + if (c0 === 0 && c1 === 0) { + e0 = e1, e1 = 0; + if (P) P.push(x1, y1); + else P = [x1, y1]; + } else { + let S, sx0, sy0, sx1, sy1; + if (c0 === 0) { + if ((S = this._clipSegment(x0, y0, x1, y1, c0, c1)) === null) continue; + [sx0, sy0, sx1, sy1] = S; + } else { + if ((S = this._clipSegment(x1, y1, x0, y0, c1, c0)) === null) continue; + [sx1, sy1, sx0, sy0] = S; + e0 = e1, e1 = this._edgecode(sx0, sy0); + if (e0 && e1) this._edge(i, e0, e1, P, P.length); + if (P) P.push(sx0, sy0); + else P = [sx0, sy0]; + } + e0 = e1, e1 = this._edgecode(sx1, sy1); + if (e0 && e1) this._edge(i, e0, e1, P, P.length); + if (P) P.push(sx1, sy1); + else P = [sx1, sy1]; + } + } + if (P) { + e0 = e1, e1 = this._edgecode(P[0], P[1]); + if (e0 && e1) this._edge(i, e0, e1, P, P.length); + } else if (this.contains(i, (this.xmin + this.xmax) / 2, (this.ymin + this.ymax) / 2)) { + return [this.xmax, this.ymin, this.xmax, this.ymax, this.xmin, this.ymax, this.xmin, this.ymin]; + } + return P; + } + _clipSegment(x0, y0, x1, y1, c0, c1) { + // for more robustness, always consider the segment in the same order + const flip = c0 < c1; + if (flip) [x0, y0, x1, y1, c0, c1] = [x1, y1, x0, y0, c1, c0]; + while (true) { + if (c0 === 0 && c1 === 0) return flip ? [x1, y1, x0, y0] : [x0, y0, x1, y1]; + if (c0 & c1) return null; + let x, y, c = c0 || c1; + if (c & 0b1000) x = x0 + (x1 - x0) * (this.ymax - y0) / (y1 - y0), y = this.ymax; + else if (c & 0b0100) x = x0 + (x1 - x0) * (this.ymin - y0) / (y1 - y0), y = this.ymin; + else if (c & 0b0010) y = y0 + (y1 - y0) * (this.xmax - x0) / (x1 - x0), x = this.xmax; + else y = y0 + (y1 - y0) * (this.xmin - x0) / (x1 - x0), x = this.xmin; + if (c0) x0 = x, y0 = y, c0 = this._regioncode(x0, y0); + else x1 = x, y1 = y, c1 = this._regioncode(x1, y1); + } + } + _clipInfinite(i, points, vx0, vy0, vxn, vyn) { + let P = Array.from(points), p; + if (p = this._project(P[0], P[1], vx0, vy0)) P.unshift(p[0], p[1]); + if (p = this._project(P[P.length - 2], P[P.length - 1], vxn, vyn)) P.push(p[0], p[1]); + if (P = this._clipFinite(i, P)) { + for (let j = 0, n = P.length, c0, c1 = this._edgecode(P[n - 2], P[n - 1]); j < n; j += 2) { + c0 = c1, c1 = this._edgecode(P[j], P[j + 1]); + if (c0 && c1) j = this._edge(i, c0, c1, P, j), n = P.length; + } + } else if (this.contains(i, (this.xmin + this.xmax) / 2, (this.ymin + this.ymax) / 2)) { + P = [this.xmin, this.ymin, this.xmax, this.ymin, this.xmax, this.ymax, this.xmin, this.ymax]; + } + return P; + } + _edge(i, e0, e1, P, j) { + while (e0 !== e1) { + let x, y; + switch (e0) { + case 0b0101: e0 = 0b0100; continue; // top-left + case 0b0100: e0 = 0b0110, x = this.xmax, y = this.ymin; break; // top + case 0b0110: e0 = 0b0010; continue; // top-right + case 0b0010: e0 = 0b1010, x = this.xmax, y = this.ymax; break; // right + case 0b1010: e0 = 0b1000; continue; // bottom-right + case 0b1000: e0 = 0b1001, x = this.xmin, y = this.ymax; break; // bottom + case 0b1001: e0 = 0b0001; continue; // bottom-left + case 0b0001: e0 = 0b0101, x = this.xmin, y = this.ymin; break; // left + } + // Note: this implicitly checks for out of bounds: if P[j] or P[j+1] are + // undefined, the conditional statement will be executed. + if ((P[j] !== x || P[j + 1] !== y) && this.contains(i, x, y)) { + P.splice(j, 0, x, y), j += 2; + } + } + return j; + } + _project(x0, y0, vx, vy) { + let t = Infinity, c, x, y; + if (vy < 0) { // top + if (y0 <= this.ymin) return null; + if ((c = (this.ymin - y0) / vy) < t) y = this.ymin, x = x0 + (t = c) * vx; + } else if (vy > 0) { // bottom + if (y0 >= this.ymax) return null; + if ((c = (this.ymax - y0) / vy) < t) y = this.ymax, x = x0 + (t = c) * vx; + } + if (vx > 0) { // right + if (x0 >= this.xmax) return null; + if ((c = (this.xmax - x0) / vx) < t) x = this.xmax, y = y0 + (t = c) * vy; + } else if (vx < 0) { // left + if (x0 <= this.xmin) return null; + if ((c = (this.xmin - x0) / vx) < t) x = this.xmin, y = y0 + (t = c) * vy; + } + return [x, y]; + } + _edgecode(x, y) { + return (x === this.xmin ? 0b0001 + : x === this.xmax ? 0b0010 : 0b0000) + | (y === this.ymin ? 0b0100 + : y === this.ymax ? 0b1000 : 0b0000); + } + _regioncode(x, y) { + return (x < this.xmin ? 0b0001 + : x > this.xmax ? 0b0010 : 0b0000) + | (y < this.ymin ? 0b0100 + : y > this.ymax ? 0b1000 : 0b0000); + } + _simplify(P) { + if (P && P.length > 4) { + for (let i = 0; i < P.length; i+= 2) { + const j = (i + 2) % P.length, k = (i + 4) % P.length; + if (P[i] === P[j] && P[j] === P[k] || P[i + 1] === P[j + 1] && P[j + 1] === P[k + 1]) { + P.splice(j, 2), i -= 2; + } + } + if (!P.length) P = null; + } + return P; + } +} + +const tau$2 = 2 * Math.PI, pow$2 = Math.pow; + +function pointX(p) { + return p[0]; +} + +function pointY(p) { + return p[1]; +} + +// A triangulation is collinear if all its triangles have a non-null area +function collinear(d) { + const {triangles, coords} = d; + for (let i = 0; i < triangles.length; i += 3) { + const a = 2 * triangles[i], + b = 2 * triangles[i + 1], + c = 2 * triangles[i + 2], + cross = (coords[c] - coords[a]) * (coords[b + 1] - coords[a + 1]) + - (coords[b] - coords[a]) * (coords[c + 1] - coords[a + 1]); + if (cross > 1e-10) return false; + } + return true; +} + +function jitter(x, y, r) { + return [x + Math.sin(x + y) * r, y + Math.cos(x - y) * r]; +} + +class Delaunay { + static from(points, fx = pointX, fy = pointY, that) { + return new Delaunay("length" in points + ? flatArray(points, fx, fy, that) + : Float64Array.from(flatIterable(points, fx, fy, that))); + } + constructor(points) { + this._delaunator = new Delaunator(points); + this.inedges = new Int32Array(points.length / 2); + this._hullIndex = new Int32Array(points.length / 2); + this.points = this._delaunator.coords; + this._init(); + } + update() { + this._delaunator.update(); + this._init(); + return this; + } + _init() { + const d = this._delaunator, points = this.points; + + // check for collinear + if (d.hull && d.hull.length > 2 && collinear(d)) { + this.collinear = Int32Array.from({length: points.length/2}, (_,i) => i) + .sort((i, j) => points[2 * i] - points[2 * j] || points[2 * i + 1] - points[2 * j + 1]); // for exact neighbors + const e = this.collinear[0], f = this.collinear[this.collinear.length - 1], + bounds = [ points[2 * e], points[2 * e + 1], points[2 * f], points[2 * f + 1] ], + r = 1e-8 * Math.hypot(bounds[3] - bounds[1], bounds[2] - bounds[0]); + for (let i = 0, n = points.length / 2; i < n; ++i) { + const p = jitter(points[2 * i], points[2 * i + 1], r); + points[2 * i] = p[0]; + points[2 * i + 1] = p[1]; + } + this._delaunator = new Delaunator(points); + } else { + delete this.collinear; + } + + const halfedges = this.halfedges = this._delaunator.halfedges; + const hull = this.hull = this._delaunator.hull; + const triangles = this.triangles = this._delaunator.triangles; + const inedges = this.inedges.fill(-1); + const hullIndex = this._hullIndex.fill(-1); + + // Compute an index from each point to an (arbitrary) incoming halfedge + // Used to give the first neighbor of each point; for this reason, + // on the hull we give priority to exterior halfedges + for (let e = 0, n = halfedges.length; e < n; ++e) { + const p = triangles[e % 3 === 2 ? e - 2 : e + 1]; + if (halfedges[e] === -1 || inedges[p] === -1) inedges[p] = e; + } + for (let i = 0, n = hull.length; i < n; ++i) { + hullIndex[hull[i]] = i; + } + + // degenerate case: 1 or 2 (distinct) points + if (hull.length <= 2 && hull.length > 0) { + this.triangles = new Int32Array(3).fill(-1); + this.halfedges = new Int32Array(3).fill(-1); + this.triangles[0] = hull[0]; + inedges[hull[0]] = 1; + if (hull.length === 2) { + inedges[hull[1]] = 0; + this.triangles[1] = hull[1]; + this.triangles[2] = hull[1]; + } + } + } + voronoi(bounds) { + return new Voronoi(this, bounds); + } + *neighbors(i) { + const {inedges, hull, _hullIndex, halfedges, triangles, collinear} = this; + + // degenerate case with several collinear points + if (collinear) { + const l = collinear.indexOf(i); + if (l > 0) yield collinear[l - 1]; + if (l < collinear.length - 1) yield collinear[l + 1]; + return; + } + + const e0 = inedges[i]; + if (e0 === -1) return; // coincident point + let e = e0, p0 = -1; + do { + yield p0 = triangles[e]; + e = e % 3 === 2 ? e - 2 : e + 1; + if (triangles[e] !== i) return; // bad triangulation + e = halfedges[e]; + if (e === -1) { + const p = hull[(_hullIndex[i] + 1) % hull.length]; + if (p !== p0) yield p; + return; + } + } while (e !== e0); + } + find(x, y, i = 0) { + if ((x = +x, x !== x) || (y = +y, y !== y)) return -1; + const i0 = i; + let c; + while ((c = this._step(i, x, y)) >= 0 && c !== i && c !== i0) i = c; + return c; + } + _step(i, x, y) { + const {inedges, hull, _hullIndex, halfedges, triangles, points} = this; + if (inedges[i] === -1 || !points.length) return (i + 1) % (points.length >> 1); + let c = i; + let dc = pow$2(x - points[i * 2], 2) + pow$2(y - points[i * 2 + 1], 2); + const e0 = inedges[i]; + let e = e0; + do { + let t = triangles[e]; + const dt = pow$2(x - points[t * 2], 2) + pow$2(y - points[t * 2 + 1], 2); + if (dt < dc) dc = dt, c = t; + e = e % 3 === 2 ? e - 2 : e + 1; + if (triangles[e] !== i) break; // bad triangulation + e = halfedges[e]; + if (e === -1) { + e = hull[(_hullIndex[i] + 1) % hull.length]; + if (e !== t) { + if (pow$2(x - points[e * 2], 2) + pow$2(y - points[e * 2 + 1], 2) < dc) return e; + } + break; + } + } while (e !== e0); + return c; + } + render(context) { + const buffer = context == null ? context = new Path : undefined; + const {points, halfedges, triangles} = this; + for (let i = 0, n = halfedges.length; i < n; ++i) { + const j = halfedges[i]; + if (j < i) continue; + const ti = triangles[i] * 2; + const tj = triangles[j] * 2; + context.moveTo(points[ti], points[ti + 1]); + context.lineTo(points[tj], points[tj + 1]); + } + this.renderHull(context); + return buffer && buffer.value(); + } + renderPoints(context, r) { + if (r === undefined && (!context || typeof context.moveTo !== "function")) r = context, context = null; + r = r == undefined ? 2 : +r; + const buffer = context == null ? context = new Path : undefined; + const {points} = this; + for (let i = 0, n = points.length; i < n; i += 2) { + const x = points[i], y = points[i + 1]; + context.moveTo(x + r, y); + context.arc(x, y, r, 0, tau$2); + } + return buffer && buffer.value(); + } + renderHull(context) { + const buffer = context == null ? context = new Path : undefined; + const {hull, points} = this; + const h = hull[0] * 2, n = hull.length; + context.moveTo(points[h], points[h + 1]); + for (let i = 1; i < n; ++i) { + const h = 2 * hull[i]; + context.lineTo(points[h], points[h + 1]); + } + context.closePath(); + return buffer && buffer.value(); + } + hullPolygon() { + const polygon = new Polygon; + this.renderHull(polygon); + return polygon.value(); + } + renderTriangle(i, context) { + const buffer = context == null ? context = new Path : undefined; + const {points, triangles} = this; + const t0 = triangles[i *= 3] * 2; + const t1 = triangles[i + 1] * 2; + const t2 = triangles[i + 2] * 2; + context.moveTo(points[t0], points[t0 + 1]); + context.lineTo(points[t1], points[t1 + 1]); + context.lineTo(points[t2], points[t2 + 1]); + context.closePath(); + return buffer && buffer.value(); + } + *trianglePolygons() { + const {triangles} = this; + for (let i = 0, n = triangles.length / 3; i < n; ++i) { + yield this.trianglePolygon(i); + } + } + trianglePolygon(i) { + const polygon = new Polygon; + this.renderTriangle(i, polygon); + return polygon.value(); + } +} + +function flatArray(points, fx, fy, that) { + const n = points.length; + const array = new Float64Array(n * 2); + for (let i = 0; i < n; ++i) { + const p = points[i]; + array[i * 2] = fx.call(that, p, i, points); + array[i * 2 + 1] = fy.call(that, p, i, points); + } + return array; +} + +function* flatIterable(points, fx, fy, that) { + let i = 0; + for (const p of points) { + yield fx.call(that, p, i, points); + yield fy.call(that, p, i, points); + ++i; + } +} + +var EOL = {}, + EOF = {}, + QUOTE = 34, + NEWLINE = 10, + RETURN = 13; + +function objectConverter(columns) { + return new Function("d", "return {" + columns.map(function(name, i) { + return JSON.stringify(name) + ": d[" + i + "] || \"\""; + }).join(",") + "}"); +} + +function customConverter(columns, f) { + var object = objectConverter(columns); + return function(row, i) { + return f(object(row), i, columns); + }; +} + +// Compute unique columns in order of discovery. +function inferColumns(rows) { + var columnSet = Object.create(null), + columns = []; + + rows.forEach(function(row) { + for (var column in row) { + if (!(column in columnSet)) { + columns.push(columnSet[column] = column); + } + } + }); + + return columns; +} + +function pad$1(value, width) { + var s = value + "", length = s.length; + return length < width ? new Array(width - length + 1).join(0) + s : s; +} + +function formatYear$1(year) { + return year < 0 ? "-" + pad$1(-year, 6) + : year > 9999 ? "+" + pad$1(year, 6) + : pad$1(year, 4); +} + +function formatDate(date) { + var hours = date.getUTCHours(), + minutes = date.getUTCMinutes(), + seconds = date.getUTCSeconds(), + milliseconds = date.getUTCMilliseconds(); + return isNaN(date) ? "Invalid Date" + : formatYear$1(date.getUTCFullYear()) + "-" + pad$1(date.getUTCMonth() + 1, 2) + "-" + pad$1(date.getUTCDate(), 2) + + (milliseconds ? "T" + pad$1(hours, 2) + ":" + pad$1(minutes, 2) + ":" + pad$1(seconds, 2) + "." + pad$1(milliseconds, 3) + "Z" + : seconds ? "T" + pad$1(hours, 2) + ":" + pad$1(minutes, 2) + ":" + pad$1(seconds, 2) + "Z" + : minutes || hours ? "T" + pad$1(hours, 2) + ":" + pad$1(minutes, 2) + "Z" + : ""); +} + +function dsvFormat(delimiter) { + var reFormat = new RegExp("[\"" + delimiter + "\n\r]"), + DELIMITER = delimiter.charCodeAt(0); + + function parse(text, f) { + var convert, columns, rows = parseRows(text, function(row, i) { + if (convert) return convert(row, i - 1); + columns = row, convert = f ? customConverter(row, f) : objectConverter(row); + }); + rows.columns = columns || []; + return rows; + } + + function parseRows(text, f) { + var rows = [], // output rows + N = text.length, + I = 0, // current character index + n = 0, // current line number + t, // current token + eof = N <= 0, // current token followed by EOF? + eol = false; // current token followed by EOL? + + // Strip the trailing newline. + if (text.charCodeAt(N - 1) === NEWLINE) --N; + if (text.charCodeAt(N - 1) === RETURN) --N; + + function token() { + if (eof) return EOF; + if (eol) return eol = false, EOL; + + // Unescape quotes. + var i, j = I, c; + if (text.charCodeAt(j) === QUOTE) { + while (I++ < N && text.charCodeAt(I) !== QUOTE || text.charCodeAt(++I) === QUOTE); + if ((i = I) >= N) eof = true; + else if ((c = text.charCodeAt(I++)) === NEWLINE) eol = true; + else if (c === RETURN) { eol = true; if (text.charCodeAt(I) === NEWLINE) ++I; } + return text.slice(j + 1, i - 1).replace(/""/g, "\""); + } + + // Find next delimiter or newline. + while (I < N) { + if ((c = text.charCodeAt(i = I++)) === NEWLINE) eol = true; + else if (c === RETURN) { eol = true; if (text.charCodeAt(I) === NEWLINE) ++I; } + else if (c !== DELIMITER) continue; + return text.slice(j, i); + } + + // Return last token before EOF. + return eof = true, text.slice(j, N); + } + + while ((t = token()) !== EOF) { + var row = []; + while (t !== EOL && t !== EOF) row.push(t), t = token(); + if (f && (row = f(row, n++)) == null) continue; + rows.push(row); + } + + return rows; + } + + function preformatBody(rows, columns) { + return rows.map(function(row) { + return columns.map(function(column) { + return formatValue(row[column]); + }).join(delimiter); + }); + } + + function format(rows, columns) { + if (columns == null) columns = inferColumns(rows); + return [columns.map(formatValue).join(delimiter)].concat(preformatBody(rows, columns)).join("\n"); + } + + function formatBody(rows, columns) { + if (columns == null) columns = inferColumns(rows); + return preformatBody(rows, columns).join("\n"); + } + + function formatRows(rows) { + return rows.map(formatRow).join("\n"); + } + + function formatRow(row) { + return row.map(formatValue).join(delimiter); + } + + function formatValue(value) { + return value == null ? "" + : value instanceof Date ? formatDate(value) + : reFormat.test(value += "") ? "\"" + value.replace(/"/g, "\"\"") + "\"" + : value; + } + + return { + parse: parse, + parseRows: parseRows, + format: format, + formatBody: formatBody, + formatRows: formatRows, + formatRow: formatRow, + formatValue: formatValue + }; +} + +var csv$1 = dsvFormat(","); + +var csvParse = csv$1.parse; +var csvParseRows = csv$1.parseRows; +var csvFormat = csv$1.format; +var csvFormatBody = csv$1.formatBody; +var csvFormatRows = csv$1.formatRows; +var csvFormatRow = csv$1.formatRow; +var csvFormatValue = csv$1.formatValue; + +var tsv$1 = dsvFormat("\t"); + +var tsvParse = tsv$1.parse; +var tsvParseRows = tsv$1.parseRows; +var tsvFormat = tsv$1.format; +var tsvFormatBody = tsv$1.formatBody; +var tsvFormatRows = tsv$1.formatRows; +var tsvFormatRow = tsv$1.formatRow; +var tsvFormatValue = tsv$1.formatValue; + +function autoType(object) { + for (var key in object) { + var value = object[key].trim(), number, m; + if (!value) value = null; + else if (value === "true") value = true; + else if (value === "false") value = false; + else if (value === "NaN") value = NaN; + else if (!isNaN(number = +value)) value = number; + else if (m = value.match(/^([-+]\d{2})?\d{4}(-\d{2}(-\d{2})?)?(T\d{2}:\d{2}(:\d{2}(\.\d{3})?)?(Z|[-+]\d{2}:\d{2})?)?$/)) { + if (fixtz && !!m[4] && !m[7]) value = value.replace(/-/g, "/").replace(/T/, " "); + value = new Date(value); + } + else continue; + object[key] = value; + } + return object; +} + +// https://github.com/d3/d3-dsv/issues/45 +const fixtz = new Date("2019-01-01T00:00").getHours() || new Date("2019-07-01T00:00").getHours(); + +function responseBlob(response) { + if (!response.ok) throw new Error(response.status + " " + response.statusText); + return response.blob(); +} + +function blob(input, init) { + return fetch(input, init).then(responseBlob); +} + +function responseArrayBuffer(response) { + if (!response.ok) throw new Error(response.status + " " + response.statusText); + return response.arrayBuffer(); +} + +function buffer(input, init) { + return fetch(input, init).then(responseArrayBuffer); +} + +function responseText(response) { + if (!response.ok) throw new Error(response.status + " " + response.statusText); + return response.text(); +} + +function text(input, init) { + return fetch(input, init).then(responseText); +} + +function dsvParse(parse) { + return function(input, init, row) { + if (arguments.length === 2 && typeof init === "function") row = init, init = undefined; + return text(input, init).then(function(response) { + return parse(response, row); + }); + }; +} + +function dsv(delimiter, input, init, row) { + if (arguments.length === 3 && typeof init === "function") row = init, init = undefined; + var format = dsvFormat(delimiter); + return text(input, init).then(function(response) { + return format.parse(response, row); + }); +} + +var csv = dsvParse(csvParse); +var tsv = dsvParse(tsvParse); + +function image(input, init) { + return new Promise(function(resolve, reject) { + var image = new Image; + for (var key in init) image[key] = init[key]; + image.onerror = reject; + image.onload = function() { resolve(image); }; + image.src = input; + }); +} + +function responseJson(response) { + if (!response.ok) throw new Error(response.status + " " + response.statusText); + if (response.status === 204 || response.status === 205) return; + return response.json(); +} + +function json(input, init) { + return fetch(input, init).then(responseJson); +} + +function parser(type) { + return (input, init) => text(input, init) + .then(text => (new DOMParser).parseFromString(text, type)); +} + +var xml = parser("application/xml"); + +var html = parser("text/html"); + +var svg = parser("image/svg+xml"); + +function center(x, y) { + var nodes, strength = 1; + + if (x == null) x = 0; + if (y == null) y = 0; + + function force() { + var i, + n = nodes.length, + node, + sx = 0, + sy = 0; + + for (i = 0; i < n; ++i) { + node = nodes[i], sx += node.x, sy += node.y; + } + + for (sx = (sx / n - x) * strength, sy = (sy / n - y) * strength, i = 0; i < n; ++i) { + node = nodes[i], node.x -= sx, node.y -= sy; + } + } + + force.initialize = function(_) { + nodes = _; + }; + + force.x = function(_) { + return arguments.length ? (x = +_, force) : x; + }; + + force.y = function(_) { + return arguments.length ? (y = +_, force) : y; + }; + + force.strength = function(_) { + return arguments.length ? (strength = +_, force) : strength; + }; + + return force; +} + +function tree_add(d) { + const x = +this._x.call(null, d), + y = +this._y.call(null, d); + return add(this.cover(x, y), x, y, d); +} + +function add(tree, x, y, d) { + if (isNaN(x) || isNaN(y)) return tree; // ignore invalid points + + var parent, + node = tree._root, + leaf = {data: d}, + x0 = tree._x0, + y0 = tree._y0, + x1 = tree._x1, + y1 = tree._y1, + xm, + ym, + xp, + yp, + right, + bottom, + i, + j; + + // If the tree is empty, initialize the root as a leaf. + if (!node) return tree._root = leaf, tree; + + // Find the existing leaf for the new point, or add it. + while (node.length) { + if (right = x >= (xm = (x0 + x1) / 2)) x0 = xm; else x1 = xm; + if (bottom = y >= (ym = (y0 + y1) / 2)) y0 = ym; else y1 = ym; + if (parent = node, !(node = node[i = bottom << 1 | right])) return parent[i] = leaf, tree; + } + + // Is the new point is exactly coincident with the existing point? + xp = +tree._x.call(null, node.data); + yp = +tree._y.call(null, node.data); + if (x === xp && y === yp) return leaf.next = node, parent ? parent[i] = leaf : tree._root = leaf, tree; + + // Otherwise, split the leaf node until the old and new point are separated. + do { + parent = parent ? parent[i] = new Array(4) : tree._root = new Array(4); + if (right = x >= (xm = (x0 + x1) / 2)) x0 = xm; else x1 = xm; + if (bottom = y >= (ym = (y0 + y1) / 2)) y0 = ym; else y1 = ym; + } while ((i = bottom << 1 | right) === (j = (yp >= ym) << 1 | (xp >= xm))); + return parent[j] = node, parent[i] = leaf, tree; +} + +function addAll(data) { + var d, i, n = data.length, + x, + y, + xz = new Array(n), + yz = new Array(n), + x0 = Infinity, + y0 = Infinity, + x1 = -Infinity, + y1 = -Infinity; + + // Compute the points and their extent. + for (i = 0; i < n; ++i) { + if (isNaN(x = +this._x.call(null, d = data[i])) || isNaN(y = +this._y.call(null, d))) continue; + xz[i] = x; + yz[i] = y; + if (x < x0) x0 = x; + if (x > x1) x1 = x; + if (y < y0) y0 = y; + if (y > y1) y1 = y; + } + + // If there were no (valid) points, abort. + if (x0 > x1 || y0 > y1) return this; + + // Expand the tree to cover the new points. + this.cover(x0, y0).cover(x1, y1); + + // Add the new points. + for (i = 0; i < n; ++i) { + add(this, xz[i], yz[i], data[i]); + } + + return this; +} + +function tree_cover(x, y) { + if (isNaN(x = +x) || isNaN(y = +y)) return this; // ignore invalid points + + var x0 = this._x0, + y0 = this._y0, + x1 = this._x1, + y1 = this._y1; + + // If the quadtree has no extent, initialize them. + // Integer extent are necessary so that if we later double the extent, + // the existing quadrant boundaries don’t change due to floating point error! + if (isNaN(x0)) { + x1 = (x0 = Math.floor(x)) + 1; + y1 = (y0 = Math.floor(y)) + 1; + } + + // Otherwise, double repeatedly to cover. + else { + var z = x1 - x0 || 1, + node = this._root, + parent, + i; + + while (x0 > x || x >= x1 || y0 > y || y >= y1) { + i = (y < y0) << 1 | (x < x0); + parent = new Array(4), parent[i] = node, node = parent, z *= 2; + switch (i) { + case 0: x1 = x0 + z, y1 = y0 + z; break; + case 1: x0 = x1 - z, y1 = y0 + z; break; + case 2: x1 = x0 + z, y0 = y1 - z; break; + case 3: x0 = x1 - z, y0 = y1 - z; break; + } + } + + if (this._root && this._root.length) this._root = node; + } + + this._x0 = x0; + this._y0 = y0; + this._x1 = x1; + this._y1 = y1; + return this; +} + +function tree_data() { + var data = []; + this.visit(function(node) { + if (!node.length) do data.push(node.data); while (node = node.next) + }); + return data; +} + +function tree_extent(_) { + return arguments.length + ? this.cover(+_[0][0], +_[0][1]).cover(+_[1][0], +_[1][1]) + : isNaN(this._x0) ? undefined : [[this._x0, this._y0], [this._x1, this._y1]]; +} + +function Quad(node, x0, y0, x1, y1) { + this.node = node; + this.x0 = x0; + this.y0 = y0; + this.x1 = x1; + this.y1 = y1; +} + +function tree_find(x, y, radius) { + var data, + x0 = this._x0, + y0 = this._y0, + x1, + y1, + x2, + y2, + x3 = this._x1, + y3 = this._y1, + quads = [], + node = this._root, + q, + i; + + if (node) quads.push(new Quad(node, x0, y0, x3, y3)); + if (radius == null) radius = Infinity; + else { + x0 = x - radius, y0 = y - radius; + x3 = x + radius, y3 = y + radius; + radius *= radius; + } + + while (q = quads.pop()) { + + // Stop searching if this quadrant can’t contain a closer node. + if (!(node = q.node) + || (x1 = q.x0) > x3 + || (y1 = q.y0) > y3 + || (x2 = q.x1) < x0 + || (y2 = q.y1) < y0) continue; + + // Bisect the current quadrant. + if (node.length) { + var xm = (x1 + x2) / 2, + ym = (y1 + y2) / 2; + + quads.push( + new Quad(node[3], xm, ym, x2, y2), + new Quad(node[2], x1, ym, xm, y2), + new Quad(node[1], xm, y1, x2, ym), + new Quad(node[0], x1, y1, xm, ym) + ); + + // Visit the closest quadrant first. + if (i = (y >= ym) << 1 | (x >= xm)) { + q = quads[quads.length - 1]; + quads[quads.length - 1] = quads[quads.length - 1 - i]; + quads[quads.length - 1 - i] = q; + } + } + + // Visit this point. (Visiting coincident points isn’t necessary!) + else { + var dx = x - +this._x.call(null, node.data), + dy = y - +this._y.call(null, node.data), + d2 = dx * dx + dy * dy; + if (d2 < radius) { + var d = Math.sqrt(radius = d2); + x0 = x - d, y0 = y - d; + x3 = x + d, y3 = y + d; + data = node.data; + } + } + } + + return data; +} + +function tree_remove(d) { + if (isNaN(x = +this._x.call(null, d)) || isNaN(y = +this._y.call(null, d))) return this; // ignore invalid points + + var parent, + node = this._root, + retainer, + previous, + next, + x0 = this._x0, + y0 = this._y0, + x1 = this._x1, + y1 = this._y1, + x, + y, + xm, + ym, + right, + bottom, + i, + j; + + // If the tree is empty, initialize the root as a leaf. + if (!node) return this; + + // Find the leaf node for the point. + // While descending, also retain the deepest parent with a non-removed sibling. + if (node.length) while (true) { + if (right = x >= (xm = (x0 + x1) / 2)) x0 = xm; else x1 = xm; + if (bottom = y >= (ym = (y0 + y1) / 2)) y0 = ym; else y1 = ym; + if (!(parent = node, node = node[i = bottom << 1 | right])) return this; + if (!node.length) break; + if (parent[(i + 1) & 3] || parent[(i + 2) & 3] || parent[(i + 3) & 3]) retainer = parent, j = i; + } + + // Find the point to remove. + while (node.data !== d) if (!(previous = node, node = node.next)) return this; + if (next = node.next) delete node.next; + + // If there are multiple coincident points, remove just the point. + if (previous) return (next ? previous.next = next : delete previous.next), this; + + // If this is the root point, remove it. + if (!parent) return this._root = next, this; + + // Remove this leaf. + next ? parent[i] = next : delete parent[i]; + + // If the parent now contains exactly one leaf, collapse superfluous parents. + if ((node = parent[0] || parent[1] || parent[2] || parent[3]) + && node === (parent[3] || parent[2] || parent[1] || parent[0]) + && !node.length) { + if (retainer) retainer[j] = node; + else this._root = node; + } + + return this; +} + +function removeAll(data) { + for (var i = 0, n = data.length; i < n; ++i) this.remove(data[i]); + return this; +} + +function tree_root() { + return this._root; +} + +function tree_size() { + var size = 0; + this.visit(function(node) { + if (!node.length) do ++size; while (node = node.next) + }); + return size; +} + +function tree_visit(callback) { + var quads = [], q, node = this._root, child, x0, y0, x1, y1; + if (node) quads.push(new Quad(node, this._x0, this._y0, this._x1, this._y1)); + while (q = quads.pop()) { + if (!callback(node = q.node, x0 = q.x0, y0 = q.y0, x1 = q.x1, y1 = q.y1) && node.length) { + var xm = (x0 + x1) / 2, ym = (y0 + y1) / 2; + if (child = node[3]) quads.push(new Quad(child, xm, ym, x1, y1)); + if (child = node[2]) quads.push(new Quad(child, x0, ym, xm, y1)); + if (child = node[1]) quads.push(new Quad(child, xm, y0, x1, ym)); + if (child = node[0]) quads.push(new Quad(child, x0, y0, xm, ym)); + } + } + return this; +} + +function tree_visitAfter(callback) { + var quads = [], next = [], q; + if (this._root) quads.push(new Quad(this._root, this._x0, this._y0, this._x1, this._y1)); + while (q = quads.pop()) { + var node = q.node; + if (node.length) { + var child, x0 = q.x0, y0 = q.y0, x1 = q.x1, y1 = q.y1, xm = (x0 + x1) / 2, ym = (y0 + y1) / 2; + if (child = node[0]) quads.push(new Quad(child, x0, y0, xm, ym)); + if (child = node[1]) quads.push(new Quad(child, xm, y0, x1, ym)); + if (child = node[2]) quads.push(new Quad(child, x0, ym, xm, y1)); + if (child = node[3]) quads.push(new Quad(child, xm, ym, x1, y1)); + } + next.push(q); + } + while (q = next.pop()) { + callback(q.node, q.x0, q.y0, q.x1, q.y1); + } + return this; +} + +function defaultX(d) { + return d[0]; +} + +function tree_x(_) { + return arguments.length ? (this._x = _, this) : this._x; +} + +function defaultY(d) { + return d[1]; +} + +function tree_y(_) { + return arguments.length ? (this._y = _, this) : this._y; +} + +function quadtree(nodes, x, y) { + var tree = new Quadtree(x == null ? defaultX : x, y == null ? defaultY : y, NaN, NaN, NaN, NaN); + return nodes == null ? tree : tree.addAll(nodes); +} + +function Quadtree(x, y, x0, y0, x1, y1) { + this._x = x; + this._y = y; + this._x0 = x0; + this._y0 = y0; + this._x1 = x1; + this._y1 = y1; + this._root = undefined; +} + +function leaf_copy(leaf) { + var copy = {data: leaf.data}, next = copy; + while (leaf = leaf.next) next = next.next = {data: leaf.data}; + return copy; +} + +var treeProto = quadtree.prototype = Quadtree.prototype; + +treeProto.copy = function() { + var copy = new Quadtree(this._x, this._y, this._x0, this._y0, this._x1, this._y1), + node = this._root, + nodes, + child; + + if (!node) return copy; + + if (!node.length) return copy._root = leaf_copy(node), copy; + + nodes = [{source: node, target: copy._root = new Array(4)}]; + while (node = nodes.pop()) { + for (var i = 0; i < 4; ++i) { + if (child = node.source[i]) { + if (child.length) nodes.push({source: child, target: node.target[i] = new Array(4)}); + else node.target[i] = leaf_copy(child); + } + } + } + + return copy; +}; + +treeProto.add = tree_add; +treeProto.addAll = addAll; +treeProto.cover = tree_cover; +treeProto.data = tree_data; +treeProto.extent = tree_extent; +treeProto.find = tree_find; +treeProto.remove = tree_remove; +treeProto.removeAll = removeAll; +treeProto.root = tree_root; +treeProto.size = tree_size; +treeProto.visit = tree_visit; +treeProto.visitAfter = tree_visitAfter; +treeProto.x = tree_x; +treeProto.y = tree_y; + +function constant$4(x) { + return function() { + return x; + }; +} + +function jiggle(random) { + return (random() - 0.5) * 1e-6; +} + +function x$3(d) { + return d.x + d.vx; +} + +function y$3(d) { + return d.y + d.vy; +} + +function collide(radius) { + var nodes, + radii, + random, + strength = 1, + iterations = 1; + + if (typeof radius !== "function") radius = constant$4(radius == null ? 1 : +radius); + + function force() { + var i, n = nodes.length, + tree, + node, + xi, + yi, + ri, + ri2; + + for (var k = 0; k < iterations; ++k) { + tree = quadtree(nodes, x$3, y$3).visitAfter(prepare); + for (i = 0; i < n; ++i) { + node = nodes[i]; + ri = radii[node.index], ri2 = ri * ri; + xi = node.x + node.vx; + yi = node.y + node.vy; + tree.visit(apply); + } + } + + function apply(quad, x0, y0, x1, y1) { + var data = quad.data, rj = quad.r, r = ri + rj; + if (data) { + if (data.index > node.index) { + var x = xi - data.x - data.vx, + y = yi - data.y - data.vy, + l = x * x + y * y; + if (l < r * r) { + if (x === 0) x = jiggle(random), l += x * x; + if (y === 0) y = jiggle(random), l += y * y; + l = (r - (l = Math.sqrt(l))) / l * strength; + node.vx += (x *= l) * (r = (rj *= rj) / (ri2 + rj)); + node.vy += (y *= l) * r; + data.vx -= x * (r = 1 - r); + data.vy -= y * r; + } + } + return; + } + return x0 > xi + r || x1 < xi - r || y0 > yi + r || y1 < yi - r; + } + } + + function prepare(quad) { + if (quad.data) return quad.r = radii[quad.data.index]; + for (var i = quad.r = 0; i < 4; ++i) { + if (quad[i] && quad[i].r > quad.r) { + quad.r = quad[i].r; + } + } + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length, node; + radii = new Array(n); + for (i = 0; i < n; ++i) node = nodes[i], radii[node.index] = +radius(node, i, nodes); + } + + force.initialize = function(_nodes, _random) { + nodes = _nodes; + random = _random; + initialize(); + }; + + force.iterations = function(_) { + return arguments.length ? (iterations = +_, force) : iterations; + }; + + force.strength = function(_) { + return arguments.length ? (strength = +_, force) : strength; + }; + + force.radius = function(_) { + return arguments.length ? (radius = typeof _ === "function" ? _ : constant$4(+_), initialize(), force) : radius; + }; + + return force; +} + +function index$3(d) { + return d.index; +} + +function find(nodeById, nodeId) { + var node = nodeById.get(nodeId); + if (!node) throw new Error("node not found: " + nodeId); + return node; +} + +function link$2(links) { + var id = index$3, + strength = defaultStrength, + strengths, + distance = constant$4(30), + distances, + nodes, + count, + bias, + random, + iterations = 1; + + if (links == null) links = []; + + function defaultStrength(link) { + return 1 / Math.min(count[link.source.index], count[link.target.index]); + } + + function force(alpha) { + for (var k = 0, n = links.length; k < iterations; ++k) { + for (var i = 0, link, source, target, x, y, l, b; i < n; ++i) { + link = links[i], source = link.source, target = link.target; + x = target.x + target.vx - source.x - source.vx || jiggle(random); + y = target.y + target.vy - source.y - source.vy || jiggle(random); + l = Math.sqrt(x * x + y * y); + l = (l - distances[i]) / l * alpha * strengths[i]; + x *= l, y *= l; + target.vx -= x * (b = bias[i]); + target.vy -= y * b; + source.vx += x * (b = 1 - b); + source.vy += y * b; + } + } + } + + function initialize() { + if (!nodes) return; + + var i, + n = nodes.length, + m = links.length, + nodeById = new Map(nodes.map((d, i) => [id(d, i, nodes), d])), + link; + + for (i = 0, count = new Array(n); i < m; ++i) { + link = links[i], link.index = i; + if (typeof link.source !== "object") link.source = find(nodeById, link.source); + if (typeof link.target !== "object") link.target = find(nodeById, link.target); + count[link.source.index] = (count[link.source.index] || 0) + 1; + count[link.target.index] = (count[link.target.index] || 0) + 1; + } + + for (i = 0, bias = new Array(m); i < m; ++i) { + link = links[i], bias[i] = count[link.source.index] / (count[link.source.index] + count[link.target.index]); + } + + strengths = new Array(m), initializeStrength(); + distances = new Array(m), initializeDistance(); + } + + function initializeStrength() { + if (!nodes) return; + + for (var i = 0, n = links.length; i < n; ++i) { + strengths[i] = +strength(links[i], i, links); + } + } + + function initializeDistance() { + if (!nodes) return; + + for (var i = 0, n = links.length; i < n; ++i) { + distances[i] = +distance(links[i], i, links); + } + } + + force.initialize = function(_nodes, _random) { + nodes = _nodes; + random = _random; + initialize(); + }; + + force.links = function(_) { + return arguments.length ? (links = _, initialize(), force) : links; + }; + + force.id = function(_) { + return arguments.length ? (id = _, force) : id; + }; + + force.iterations = function(_) { + return arguments.length ? (iterations = +_, force) : iterations; + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant$4(+_), initializeStrength(), force) : strength; + }; + + force.distance = function(_) { + return arguments.length ? (distance = typeof _ === "function" ? _ : constant$4(+_), initializeDistance(), force) : distance; + }; + + return force; +} + +// https://en.wikipedia.org/wiki/Linear_congruential_generator#Parameters_in_common_use +const a$2 = 1664525; +const c$4 = 1013904223; +const m$1 = 4294967296; // 2^32 + +function lcg$2() { + let s = 1; + return () => (s = (a$2 * s + c$4) % m$1) / m$1; +} + +function x$2(d) { + return d.x; +} + +function y$2(d) { + return d.y; +} + +var initialRadius = 10, + initialAngle = Math.PI * (3 - Math.sqrt(5)); + +function simulation(nodes) { + var simulation, + alpha = 1, + alphaMin = 0.001, + alphaDecay = 1 - Math.pow(alphaMin, 1 / 300), + alphaTarget = 0, + velocityDecay = 0.6, + forces = new Map(), + stepper = timer(step), + event = dispatch("tick", "end"), + random = lcg$2(); + + if (nodes == null) nodes = []; + + function step() { + tick(); + event.call("tick", simulation); + if (alpha < alphaMin) { + stepper.stop(); + event.call("end", simulation); + } + } + + function tick(iterations) { + var i, n = nodes.length, node; + + if (iterations === undefined) iterations = 1; + + for (var k = 0; k < iterations; ++k) { + alpha += (alphaTarget - alpha) * alphaDecay; + + forces.forEach(function(force) { + force(alpha); + }); + + for (i = 0; i < n; ++i) { + node = nodes[i]; + if (node.fx == null) node.x += node.vx *= velocityDecay; + else node.x = node.fx, node.vx = 0; + if (node.fy == null) node.y += node.vy *= velocityDecay; + else node.y = node.fy, node.vy = 0; + } + } + + return simulation; + } + + function initializeNodes() { + for (var i = 0, n = nodes.length, node; i < n; ++i) { + node = nodes[i], node.index = i; + if (node.fx != null) node.x = node.fx; + if (node.fy != null) node.y = node.fy; + if (isNaN(node.x) || isNaN(node.y)) { + var radius = initialRadius * Math.sqrt(0.5 + i), angle = i * initialAngle; + node.x = radius * Math.cos(angle); + node.y = radius * Math.sin(angle); + } + if (isNaN(node.vx) || isNaN(node.vy)) { + node.vx = node.vy = 0; + } + } + } + + function initializeForce(force) { + if (force.initialize) force.initialize(nodes, random); + return force; + } + + initializeNodes(); + + return simulation = { + tick: tick, + + restart: function() { + return stepper.restart(step), simulation; + }, + + stop: function() { + return stepper.stop(), simulation; + }, + + nodes: function(_) { + return arguments.length ? (nodes = _, initializeNodes(), forces.forEach(initializeForce), simulation) : nodes; + }, + + alpha: function(_) { + return arguments.length ? (alpha = +_, simulation) : alpha; + }, + + alphaMin: function(_) { + return arguments.length ? (alphaMin = +_, simulation) : alphaMin; + }, + + alphaDecay: function(_) { + return arguments.length ? (alphaDecay = +_, simulation) : +alphaDecay; + }, + + alphaTarget: function(_) { + return arguments.length ? (alphaTarget = +_, simulation) : alphaTarget; + }, + + velocityDecay: function(_) { + return arguments.length ? (velocityDecay = 1 - _, simulation) : 1 - velocityDecay; + }, + + randomSource: function(_) { + return arguments.length ? (random = _, forces.forEach(initializeForce), simulation) : random; + }, + + force: function(name, _) { + return arguments.length > 1 ? ((_ == null ? forces.delete(name) : forces.set(name, initializeForce(_))), simulation) : forces.get(name); + }, + + find: function(x, y, radius) { + var i = 0, + n = nodes.length, + dx, + dy, + d2, + node, + closest; + + if (radius == null) radius = Infinity; + else radius *= radius; + + for (i = 0; i < n; ++i) { + node = nodes[i]; + dx = x - node.x; + dy = y - node.y; + d2 = dx * dx + dy * dy; + if (d2 < radius) closest = node, radius = d2; + } + + return closest; + }, + + on: function(name, _) { + return arguments.length > 1 ? (event.on(name, _), simulation) : event.on(name); + } + }; +} + +function manyBody() { + var nodes, + node, + random, + alpha, + strength = constant$4(-30), + strengths, + distanceMin2 = 1, + distanceMax2 = Infinity, + theta2 = 0.81; + + function force(_) { + var i, n = nodes.length, tree = quadtree(nodes, x$2, y$2).visitAfter(accumulate); + for (alpha = _, i = 0; i < n; ++i) node = nodes[i], tree.visit(apply); + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length, node; + strengths = new Array(n); + for (i = 0; i < n; ++i) node = nodes[i], strengths[node.index] = +strength(node, i, nodes); + } + + function accumulate(quad) { + var strength = 0, q, c, weight = 0, x, y, i; + + // For internal nodes, accumulate forces from child quadrants. + if (quad.length) { + for (x = y = i = 0; i < 4; ++i) { + if ((q = quad[i]) && (c = Math.abs(q.value))) { + strength += q.value, weight += c, x += c * q.x, y += c * q.y; + } + } + quad.x = x / weight; + quad.y = y / weight; + } + + // For leaf nodes, accumulate forces from coincident quadrants. + else { + q = quad; + q.x = q.data.x; + q.y = q.data.y; + do strength += strengths[q.data.index]; + while (q = q.next); + } + + quad.value = strength; + } + + function apply(quad, x1, _, x2) { + if (!quad.value) return true; + + var x = quad.x - node.x, + y = quad.y - node.y, + w = x2 - x1, + l = x * x + y * y; + + // Apply the Barnes-Hut approximation if possible. + // Limit forces for very close nodes; randomize direction if coincident. + if (w * w / theta2 < l) { + if (l < distanceMax2) { + if (x === 0) x = jiggle(random), l += x * x; + if (y === 0) y = jiggle(random), l += y * y; + if (l < distanceMin2) l = Math.sqrt(distanceMin2 * l); + node.vx += x * quad.value * alpha / l; + node.vy += y * quad.value * alpha / l; + } + return true; + } + + // Otherwise, process points directly. + else if (quad.length || l >= distanceMax2) return; + + // Limit forces for very close nodes; randomize direction if coincident. + if (quad.data !== node || quad.next) { + if (x === 0) x = jiggle(random), l += x * x; + if (y === 0) y = jiggle(random), l += y * y; + if (l < distanceMin2) l = Math.sqrt(distanceMin2 * l); + } + + do if (quad.data !== node) { + w = strengths[quad.data.index] * alpha / l; + node.vx += x * w; + node.vy += y * w; + } while (quad = quad.next); + } + + force.initialize = function(_nodes, _random) { + nodes = _nodes; + random = _random; + initialize(); + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant$4(+_), initialize(), force) : strength; + }; + + force.distanceMin = function(_) { + return arguments.length ? (distanceMin2 = _ * _, force) : Math.sqrt(distanceMin2); + }; + + force.distanceMax = function(_) { + return arguments.length ? (distanceMax2 = _ * _, force) : Math.sqrt(distanceMax2); + }; + + force.theta = function(_) { + return arguments.length ? (theta2 = _ * _, force) : Math.sqrt(theta2); + }; + + return force; +} + +function radial$1(radius, x, y) { + var nodes, + strength = constant$4(0.1), + strengths, + radiuses; + + if (typeof radius !== "function") radius = constant$4(+radius); + if (x == null) x = 0; + if (y == null) y = 0; + + function force(alpha) { + for (var i = 0, n = nodes.length; i < n; ++i) { + var node = nodes[i], + dx = node.x - x || 1e-6, + dy = node.y - y || 1e-6, + r = Math.sqrt(dx * dx + dy * dy), + k = (radiuses[i] - r) * strengths[i] * alpha / r; + node.vx += dx * k; + node.vy += dy * k; + } + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length; + strengths = new Array(n); + radiuses = new Array(n); + for (i = 0; i < n; ++i) { + radiuses[i] = +radius(nodes[i], i, nodes); + strengths[i] = isNaN(radiuses[i]) ? 0 : +strength(nodes[i], i, nodes); + } + } + + force.initialize = function(_) { + nodes = _, initialize(); + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant$4(+_), initialize(), force) : strength; + }; + + force.radius = function(_) { + return arguments.length ? (radius = typeof _ === "function" ? _ : constant$4(+_), initialize(), force) : radius; + }; + + force.x = function(_) { + return arguments.length ? (x = +_, force) : x; + }; + + force.y = function(_) { + return arguments.length ? (y = +_, force) : y; + }; + + return force; +} + +function x$1(x) { + var strength = constant$4(0.1), + nodes, + strengths, + xz; + + if (typeof x !== "function") x = constant$4(x == null ? 0 : +x); + + function force(alpha) { + for (var i = 0, n = nodes.length, node; i < n; ++i) { + node = nodes[i], node.vx += (xz[i] - node.x) * strengths[i] * alpha; + } + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length; + strengths = new Array(n); + xz = new Array(n); + for (i = 0; i < n; ++i) { + strengths[i] = isNaN(xz[i] = +x(nodes[i], i, nodes)) ? 0 : +strength(nodes[i], i, nodes); + } + } + + force.initialize = function(_) { + nodes = _; + initialize(); + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant$4(+_), initialize(), force) : strength; + }; + + force.x = function(_) { + return arguments.length ? (x = typeof _ === "function" ? _ : constant$4(+_), initialize(), force) : x; + }; + + return force; +} + +function y$1(y) { + var strength = constant$4(0.1), + nodes, + strengths, + yz; + + if (typeof y !== "function") y = constant$4(y == null ? 0 : +y); + + function force(alpha) { + for (var i = 0, n = nodes.length, node; i < n; ++i) { + node = nodes[i], node.vy += (yz[i] - node.y) * strengths[i] * alpha; + } + } + + function initialize() { + if (!nodes) return; + var i, n = nodes.length; + strengths = new Array(n); + yz = new Array(n); + for (i = 0; i < n; ++i) { + strengths[i] = isNaN(yz[i] = +y(nodes[i], i, nodes)) ? 0 : +strength(nodes[i], i, nodes); + } + } + + force.initialize = function(_) { + nodes = _; + initialize(); + }; + + force.strength = function(_) { + return arguments.length ? (strength = typeof _ === "function" ? _ : constant$4(+_), initialize(), force) : strength; + }; + + force.y = function(_) { + return arguments.length ? (y = typeof _ === "function" ? _ : constant$4(+_), initialize(), force) : y; + }; + + return force; +} + +function formatDecimal(x) { + return Math.abs(x = Math.round(x)) >= 1e21 + ? x.toLocaleString("en").replace(/,/g, "") + : x.toString(10); +} + +// Computes the decimal coefficient and exponent of the specified number x with +// significant digits p, where x is positive and p is in [1, 21] or undefined. +// For example, formatDecimalParts(1.23) returns ["123", 0]. +function formatDecimalParts(x, p) { + if ((i = (x = p ? x.toExponential(p - 1) : x.toExponential()).indexOf("e")) < 0) return null; // NaN, ±Infinity + var i, coefficient = x.slice(0, i); + + // The string returned by toExponential either has the form \d\.\d+e[-+]\d+ + // (e.g., 1.2e+3) or the form \de[-+]\d+ (e.g., 1e+3). + return [ + coefficient.length > 1 ? coefficient[0] + coefficient.slice(2) : coefficient, + +x.slice(i + 1) + ]; +} + +function exponent(x) { + return x = formatDecimalParts(Math.abs(x)), x ? x[1] : NaN; +} + +function formatGroup(grouping, thousands) { + return function(value, width) { + var i = value.length, + t = [], + j = 0, + g = grouping[0], + length = 0; + + while (i > 0 && g > 0) { + if (length + g + 1 > width) g = Math.max(1, width - length); + t.push(value.substring(i -= g, i + g)); + if ((length += g + 1) > width) break; + g = grouping[j = (j + 1) % grouping.length]; + } + + return t.reverse().join(thousands); + }; +} + +function formatNumerals(numerals) { + return function(value) { + return value.replace(/[0-9]/g, function(i) { + return numerals[+i]; + }); + }; +} + +// [[fill]align][sign][symbol][0][width][,][.precision][~][type] +var re = /^(?:(.)?([<>=^]))?([+\-( ])?([$#])?(0)?(\d+)?(,)?(\.\d+)?(~)?([a-z%])?$/i; + +function formatSpecifier(specifier) { + if (!(match = re.exec(specifier))) throw new Error("invalid format: " + specifier); + var match; + return new FormatSpecifier({ + fill: match[1], + align: match[2], + sign: match[3], + symbol: match[4], + zero: match[5], + width: match[6], + comma: match[7], + precision: match[8] && match[8].slice(1), + trim: match[9], + type: match[10] + }); +} + +formatSpecifier.prototype = FormatSpecifier.prototype; // instanceof + +function FormatSpecifier(specifier) { + this.fill = specifier.fill === undefined ? " " : specifier.fill + ""; + this.align = specifier.align === undefined ? ">" : specifier.align + ""; + this.sign = specifier.sign === undefined ? "-" : specifier.sign + ""; + this.symbol = specifier.symbol === undefined ? "" : specifier.symbol + ""; + this.zero = !!specifier.zero; + this.width = specifier.width === undefined ? undefined : +specifier.width; + this.comma = !!specifier.comma; + this.precision = specifier.precision === undefined ? undefined : +specifier.precision; + this.trim = !!specifier.trim; + this.type = specifier.type === undefined ? "" : specifier.type + ""; +} + +FormatSpecifier.prototype.toString = function() { + return this.fill + + this.align + + this.sign + + this.symbol + + (this.zero ? "0" : "") + + (this.width === undefined ? "" : Math.max(1, this.width | 0)) + + (this.comma ? "," : "") + + (this.precision === undefined ? "" : "." + Math.max(0, this.precision | 0)) + + (this.trim ? "~" : "") + + this.type; +}; + +// Trims insignificant zeros, e.g., replaces 1.2000k with 1.2k. +function formatTrim(s) { + out: for (var n = s.length, i = 1, i0 = -1, i1; i < n; ++i) { + switch (s[i]) { + case ".": i0 = i1 = i; break; + case "0": if (i0 === 0) i0 = i; i1 = i; break; + default: if (!+s[i]) break out; if (i0 > 0) i0 = 0; break; + } + } + return i0 > 0 ? s.slice(0, i0) + s.slice(i1 + 1) : s; +} + +var prefixExponent; + +function formatPrefixAuto(x, p) { + var d = formatDecimalParts(x, p); + if (!d) return x + ""; + var coefficient = d[0], + exponent = d[1], + i = exponent - (prefixExponent = Math.max(-8, Math.min(8, Math.floor(exponent / 3))) * 3) + 1, + n = coefficient.length; + return i === n ? coefficient + : i > n ? coefficient + new Array(i - n + 1).join("0") + : i > 0 ? coefficient.slice(0, i) + "." + coefficient.slice(i) + : "0." + new Array(1 - i).join("0") + formatDecimalParts(x, Math.max(0, p + i - 1))[0]; // less than 1y! +} + +function formatRounded(x, p) { + var d = formatDecimalParts(x, p); + if (!d) return x + ""; + var coefficient = d[0], + exponent = d[1]; + return exponent < 0 ? "0." + new Array(-exponent).join("0") + coefficient + : coefficient.length > exponent + 1 ? coefficient.slice(0, exponent + 1) + "." + coefficient.slice(exponent + 1) + : coefficient + new Array(exponent - coefficient.length + 2).join("0"); +} + +var formatTypes = { + "%": (x, p) => (x * 100).toFixed(p), + "b": (x) => Math.round(x).toString(2), + "c": (x) => x + "", + "d": formatDecimal, + "e": (x, p) => x.toExponential(p), + "f": (x, p) => x.toFixed(p), + "g": (x, p) => x.toPrecision(p), + "o": (x) => Math.round(x).toString(8), + "p": (x, p) => formatRounded(x * 100, p), + "r": formatRounded, + "s": formatPrefixAuto, + "X": (x) => Math.round(x).toString(16).toUpperCase(), + "x": (x) => Math.round(x).toString(16) +}; + +function identity$6(x) { + return x; +} + +var map = Array.prototype.map, + prefixes = ["y","z","a","f","p","n","µ","m","","k","M","G","T","P","E","Z","Y"]; + +function formatLocale$1(locale) { + var group = locale.grouping === undefined || locale.thousands === undefined ? identity$6 : formatGroup(map.call(locale.grouping, Number), locale.thousands + ""), + currencyPrefix = locale.currency === undefined ? "" : locale.currency[0] + "", + currencySuffix = locale.currency === undefined ? "" : locale.currency[1] + "", + decimal = locale.decimal === undefined ? "." : locale.decimal + "", + numerals = locale.numerals === undefined ? identity$6 : formatNumerals(map.call(locale.numerals, String)), + percent = locale.percent === undefined ? "%" : locale.percent + "", + minus = locale.minus === undefined ? "−" : locale.minus + "", + nan = locale.nan === undefined ? "NaN" : locale.nan + ""; + + function newFormat(specifier) { + specifier = formatSpecifier(specifier); + + var fill = specifier.fill, + align = specifier.align, + sign = specifier.sign, + symbol = specifier.symbol, + zero = specifier.zero, + width = specifier.width, + comma = specifier.comma, + precision = specifier.precision, + trim = specifier.trim, + type = specifier.type; + + // The "n" type is an alias for ",g". + if (type === "n") comma = true, type = "g"; + + // The "" type, and any invalid type, is an alias for ".12~g". + else if (!formatTypes[type]) precision === undefined && (precision = 12), trim = true, type = "g"; + + // If zero fill is specified, padding goes after sign and before digits. + if (zero || (fill === "0" && align === "=")) zero = true, fill = "0", align = "="; + + // Compute the prefix and suffix. + // For SI-prefix, the suffix is lazily computed. + var prefix = symbol === "$" ? currencyPrefix : symbol === "#" && /[boxX]/.test(type) ? "0" + type.toLowerCase() : "", + suffix = symbol === "$" ? currencySuffix : /[%p]/.test(type) ? percent : ""; + + // What format function should we use? + // Is this an integer type? + // Can this type generate exponential notation? + var formatType = formatTypes[type], + maybeSuffix = /[defgprs%]/.test(type); + + // Set the default precision if not specified, + // or clamp the specified precision to the supported range. + // For significant precision, it must be in [1, 21]. + // For fixed precision, it must be in [0, 20]. + precision = precision === undefined ? 6 + : /[gprs]/.test(type) ? Math.max(1, Math.min(21, precision)) + : Math.max(0, Math.min(20, precision)); + + function format(value) { + var valuePrefix = prefix, + valueSuffix = suffix, + i, n, c; + + if (type === "c") { + valueSuffix = formatType(value) + valueSuffix; + value = ""; + } else { + value = +value; + + // Determine the sign. -0 is not less than 0, but 1 / -0 is! + var valueNegative = value < 0 || 1 / value < 0; + + // Perform the initial formatting. + value = isNaN(value) ? nan : formatType(Math.abs(value), precision); + + // Trim insignificant zeros. + if (trim) value = formatTrim(value); + + // If a negative value rounds to zero after formatting, and no explicit positive sign is requested, hide the sign. + if (valueNegative && +value === 0 && sign !== "+") valueNegative = false; + + // Compute the prefix and suffix. + valuePrefix = (valueNegative ? (sign === "(" ? sign : minus) : sign === "-" || sign === "(" ? "" : sign) + valuePrefix; + valueSuffix = (type === "s" ? prefixes[8 + prefixExponent / 3] : "") + valueSuffix + (valueNegative && sign === "(" ? ")" : ""); + + // Break the formatted value into the integer “value” part that can be + // grouped, and fractional or exponential “suffix” part that is not. + if (maybeSuffix) { + i = -1, n = value.length; + while (++i < n) { + if (c = value.charCodeAt(i), 48 > c || c > 57) { + valueSuffix = (c === 46 ? decimal + value.slice(i + 1) : value.slice(i)) + valueSuffix; + value = value.slice(0, i); + break; + } + } + } + } + + // If the fill character is not "0", grouping is applied before padding. + if (comma && !zero) value = group(value, Infinity); + + // Compute the padding. + var length = valuePrefix.length + value.length + valueSuffix.length, + padding = length < width ? new Array(width - length + 1).join(fill) : ""; + + // If the fill character is "0", grouping is applied after padding. + if (comma && zero) value = group(padding + value, padding.length ? width - valueSuffix.length : Infinity), padding = ""; + + // Reconstruct the final output based on the desired alignment. + switch (align) { + case "<": value = valuePrefix + value + valueSuffix + padding; break; + case "=": value = valuePrefix + padding + value + valueSuffix; break; + case "^": value = padding.slice(0, length = padding.length >> 1) + valuePrefix + value + valueSuffix + padding.slice(length); break; + default: value = padding + valuePrefix + value + valueSuffix; break; + } + + return numerals(value); + } + + format.toString = function() { + return specifier + ""; + }; + + return format; + } + + function formatPrefix(specifier, value) { + var f = newFormat((specifier = formatSpecifier(specifier), specifier.type = "f", specifier)), + e = Math.max(-8, Math.min(8, Math.floor(exponent(value) / 3))) * 3, + k = Math.pow(10, -e), + prefix = prefixes[8 + e / 3]; + return function(value) { + return f(k * value) + prefix; + }; + } + + return { + format: newFormat, + formatPrefix: formatPrefix + }; +} + +var locale$1; +exports.format = void 0; +exports.formatPrefix = void 0; + +defaultLocale$1({ + thousands: ",", + grouping: [3], + currency: ["$", ""] +}); + +function defaultLocale$1(definition) { + locale$1 = formatLocale$1(definition); + exports.format = locale$1.format; + exports.formatPrefix = locale$1.formatPrefix; + return locale$1; +} + +function precisionFixed(step) { + return Math.max(0, -exponent(Math.abs(step))); +} + +function precisionPrefix(step, value) { + return Math.max(0, Math.max(-8, Math.min(8, Math.floor(exponent(value) / 3))) * 3 - exponent(Math.abs(step))); +} + +function precisionRound(step, max) { + step = Math.abs(step), max = Math.abs(max) - step; + return Math.max(0, exponent(max) - exponent(step)) + 1; +} + +var epsilon$1 = 1e-6; +var epsilon2 = 1e-12; +var pi$1 = Math.PI; +var halfPi$1 = pi$1 / 2; +var quarterPi = pi$1 / 4; +var tau$1 = pi$1 * 2; + +var degrees = 180 / pi$1; +var radians = pi$1 / 180; + +var abs$1 = Math.abs; +var atan = Math.atan; +var atan2$1 = Math.atan2; +var cos$1 = Math.cos; +var ceil = Math.ceil; +var exp = Math.exp; +var hypot = Math.hypot; +var log$1 = Math.log; +var pow$1 = Math.pow; +var sin$1 = Math.sin; +var sign$1 = Math.sign || function(x) { return x > 0 ? 1 : x < 0 ? -1 : 0; }; +var sqrt$2 = Math.sqrt; +var tan = Math.tan; + +function acos$1(x) { + return x > 1 ? 0 : x < -1 ? pi$1 : Math.acos(x); +} + +function asin$1(x) { + return x > 1 ? halfPi$1 : x < -1 ? -halfPi$1 : Math.asin(x); +} + +function haversin(x) { + return (x = sin$1(x / 2)) * x; +} + +function noop$1() {} + +function streamGeometry(geometry, stream) { + if (geometry && streamGeometryType.hasOwnProperty(geometry.type)) { + streamGeometryType[geometry.type](geometry, stream); + } +} + +var streamObjectType = { + Feature: function(object, stream) { + streamGeometry(object.geometry, stream); + }, + FeatureCollection: function(object, stream) { + var features = object.features, i = -1, n = features.length; + while (++i < n) streamGeometry(features[i].geometry, stream); + } +}; + +var streamGeometryType = { + Sphere: function(object, stream) { + stream.sphere(); + }, + Point: function(object, stream) { + object = object.coordinates; + stream.point(object[0], object[1], object[2]); + }, + MultiPoint: function(object, stream) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) object = coordinates[i], stream.point(object[0], object[1], object[2]); + }, + LineString: function(object, stream) { + streamLine(object.coordinates, stream, 0); + }, + MultiLineString: function(object, stream) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) streamLine(coordinates[i], stream, 0); + }, + Polygon: function(object, stream) { + streamPolygon(object.coordinates, stream); + }, + MultiPolygon: function(object, stream) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) streamPolygon(coordinates[i], stream); + }, + GeometryCollection: function(object, stream) { + var geometries = object.geometries, i = -1, n = geometries.length; + while (++i < n) streamGeometry(geometries[i], stream); + } +}; + +function streamLine(coordinates, stream, closed) { + var i = -1, n = coordinates.length - closed, coordinate; + stream.lineStart(); + while (++i < n) coordinate = coordinates[i], stream.point(coordinate[0], coordinate[1], coordinate[2]); + stream.lineEnd(); +} + +function streamPolygon(coordinates, stream) { + var i = -1, n = coordinates.length; + stream.polygonStart(); + while (++i < n) streamLine(coordinates[i], stream, 1); + stream.polygonEnd(); +} + +function geoStream(object, stream) { + if (object && streamObjectType.hasOwnProperty(object.type)) { + streamObjectType[object.type](object, stream); + } else { + streamGeometry(object, stream); + } +} + +var areaRingSum$1 = new Adder(); + +// hello? + +var areaSum$1 = new Adder(), + lambda00$2, + phi00$2, + lambda0$2, + cosPhi0$1, + sinPhi0$1; + +var areaStream$1 = { + point: noop$1, + lineStart: noop$1, + lineEnd: noop$1, + polygonStart: function() { + areaRingSum$1 = new Adder(); + areaStream$1.lineStart = areaRingStart$1; + areaStream$1.lineEnd = areaRingEnd$1; + }, + polygonEnd: function() { + var areaRing = +areaRingSum$1; + areaSum$1.add(areaRing < 0 ? tau$1 + areaRing : areaRing); + this.lineStart = this.lineEnd = this.point = noop$1; + }, + sphere: function() { + areaSum$1.add(tau$1); + } +}; + +function areaRingStart$1() { + areaStream$1.point = areaPointFirst$1; +} + +function areaRingEnd$1() { + areaPoint$1(lambda00$2, phi00$2); +} + +function areaPointFirst$1(lambda, phi) { + areaStream$1.point = areaPoint$1; + lambda00$2 = lambda, phi00$2 = phi; + lambda *= radians, phi *= radians; + lambda0$2 = lambda, cosPhi0$1 = cos$1(phi = phi / 2 + quarterPi), sinPhi0$1 = sin$1(phi); +} + +function areaPoint$1(lambda, phi) { + lambda *= radians, phi *= radians; + phi = phi / 2 + quarterPi; // half the angular distance from south pole + + // Spherical excess E for a spherical triangle with vertices: south pole, + // previous point, current point. Uses a formula derived from Cagnoli’s + // theorem. See Todhunter, Spherical Trig. (1871), Sec. 103, Eq. (2). + var dLambda = lambda - lambda0$2, + sdLambda = dLambda >= 0 ? 1 : -1, + adLambda = sdLambda * dLambda, + cosPhi = cos$1(phi), + sinPhi = sin$1(phi), + k = sinPhi0$1 * sinPhi, + u = cosPhi0$1 * cosPhi + k * cos$1(adLambda), + v = k * sdLambda * sin$1(adLambda); + areaRingSum$1.add(atan2$1(v, u)); + + // Advance the previous points. + lambda0$2 = lambda, cosPhi0$1 = cosPhi, sinPhi0$1 = sinPhi; +} + +function area$2(object) { + areaSum$1 = new Adder(); + geoStream(object, areaStream$1); + return areaSum$1 * 2; +} + +function spherical(cartesian) { + return [atan2$1(cartesian[1], cartesian[0]), asin$1(cartesian[2])]; +} + +function cartesian(spherical) { + var lambda = spherical[0], phi = spherical[1], cosPhi = cos$1(phi); + return [cosPhi * cos$1(lambda), cosPhi * sin$1(lambda), sin$1(phi)]; +} + +function cartesianDot(a, b) { + return a[0] * b[0] + a[1] * b[1] + a[2] * b[2]; +} + +function cartesianCross(a, b) { + return [a[1] * b[2] - a[2] * b[1], a[2] * b[0] - a[0] * b[2], a[0] * b[1] - a[1] * b[0]]; +} + +// TODO return a +function cartesianAddInPlace(a, b) { + a[0] += b[0], a[1] += b[1], a[2] += b[2]; +} + +function cartesianScale(vector, k) { + return [vector[0] * k, vector[1] * k, vector[2] * k]; +} + +// TODO return d +function cartesianNormalizeInPlace(d) { + var l = sqrt$2(d[0] * d[0] + d[1] * d[1] + d[2] * d[2]); + d[0] /= l, d[1] /= l, d[2] /= l; +} + +var lambda0$1, phi0, lambda1, phi1, // bounds + lambda2, // previous lambda-coordinate + lambda00$1, phi00$1, // first point + p0, // previous 3D point + deltaSum, + ranges, + range; + +var boundsStream$2 = { + point: boundsPoint$1, + lineStart: boundsLineStart, + lineEnd: boundsLineEnd, + polygonStart: function() { + boundsStream$2.point = boundsRingPoint; + boundsStream$2.lineStart = boundsRingStart; + boundsStream$2.lineEnd = boundsRingEnd; + deltaSum = new Adder(); + areaStream$1.polygonStart(); + }, + polygonEnd: function() { + areaStream$1.polygonEnd(); + boundsStream$2.point = boundsPoint$1; + boundsStream$2.lineStart = boundsLineStart; + boundsStream$2.lineEnd = boundsLineEnd; + if (areaRingSum$1 < 0) lambda0$1 = -(lambda1 = 180), phi0 = -(phi1 = 90); + else if (deltaSum > epsilon$1) phi1 = 90; + else if (deltaSum < -epsilon$1) phi0 = -90; + range[0] = lambda0$1, range[1] = lambda1; + }, + sphere: function() { + lambda0$1 = -(lambda1 = 180), phi0 = -(phi1 = 90); + } +}; + +function boundsPoint$1(lambda, phi) { + ranges.push(range = [lambda0$1 = lambda, lambda1 = lambda]); + if (phi < phi0) phi0 = phi; + if (phi > phi1) phi1 = phi; +} + +function linePoint(lambda, phi) { + var p = cartesian([lambda * radians, phi * radians]); + if (p0) { + var normal = cartesianCross(p0, p), + equatorial = [normal[1], -normal[0], 0], + inflection = cartesianCross(equatorial, normal); + cartesianNormalizeInPlace(inflection); + inflection = spherical(inflection); + var delta = lambda - lambda2, + sign = delta > 0 ? 1 : -1, + lambdai = inflection[0] * degrees * sign, + phii, + antimeridian = abs$1(delta) > 180; + if (antimeridian ^ (sign * lambda2 < lambdai && lambdai < sign * lambda)) { + phii = inflection[1] * degrees; + if (phii > phi1) phi1 = phii; + } else if (lambdai = (lambdai + 360) % 360 - 180, antimeridian ^ (sign * lambda2 < lambdai && lambdai < sign * lambda)) { + phii = -inflection[1] * degrees; + if (phii < phi0) phi0 = phii; + } else { + if (phi < phi0) phi0 = phi; + if (phi > phi1) phi1 = phi; + } + if (antimeridian) { + if (lambda < lambda2) { + if (angle(lambda0$1, lambda) > angle(lambda0$1, lambda1)) lambda1 = lambda; + } else { + if (angle(lambda, lambda1) > angle(lambda0$1, lambda1)) lambda0$1 = lambda; + } + } else { + if (lambda1 >= lambda0$1) { + if (lambda < lambda0$1) lambda0$1 = lambda; + if (lambda > lambda1) lambda1 = lambda; + } else { + if (lambda > lambda2) { + if (angle(lambda0$1, lambda) > angle(lambda0$1, lambda1)) lambda1 = lambda; + } else { + if (angle(lambda, lambda1) > angle(lambda0$1, lambda1)) lambda0$1 = lambda; + } + } + } + } else { + ranges.push(range = [lambda0$1 = lambda, lambda1 = lambda]); + } + if (phi < phi0) phi0 = phi; + if (phi > phi1) phi1 = phi; + p0 = p, lambda2 = lambda; +} + +function boundsLineStart() { + boundsStream$2.point = linePoint; +} + +function boundsLineEnd() { + range[0] = lambda0$1, range[1] = lambda1; + boundsStream$2.point = boundsPoint$1; + p0 = null; +} + +function boundsRingPoint(lambda, phi) { + if (p0) { + var delta = lambda - lambda2; + deltaSum.add(abs$1(delta) > 180 ? delta + (delta > 0 ? 360 : -360) : delta); + } else { + lambda00$1 = lambda, phi00$1 = phi; + } + areaStream$1.point(lambda, phi); + linePoint(lambda, phi); +} + +function boundsRingStart() { + areaStream$1.lineStart(); +} + +function boundsRingEnd() { + boundsRingPoint(lambda00$1, phi00$1); + areaStream$1.lineEnd(); + if (abs$1(deltaSum) > epsilon$1) lambda0$1 = -(lambda1 = 180); + range[0] = lambda0$1, range[1] = lambda1; + p0 = null; +} + +// Finds the left-right distance between two longitudes. +// This is almost the same as (lambda1 - lambda0 + 360°) % 360°, except that we want +// the distance between ±180° to be 360°. +function angle(lambda0, lambda1) { + return (lambda1 -= lambda0) < 0 ? lambda1 + 360 : lambda1; +} + +function rangeCompare(a, b) { + return a[0] - b[0]; +} + +function rangeContains(range, x) { + return range[0] <= range[1] ? range[0] <= x && x <= range[1] : x < range[0] || range[1] < x; +} + +function bounds(feature) { + var i, n, a, b, merged, deltaMax, delta; + + phi1 = lambda1 = -(lambda0$1 = phi0 = Infinity); + ranges = []; + geoStream(feature, boundsStream$2); + + // First, sort ranges by their minimum longitudes. + if (n = ranges.length) { + ranges.sort(rangeCompare); + + // Then, merge any ranges that overlap. + for (i = 1, a = ranges[0], merged = [a]; i < n; ++i) { + b = ranges[i]; + if (rangeContains(a, b[0]) || rangeContains(a, b[1])) { + if (angle(a[0], b[1]) > angle(a[0], a[1])) a[1] = b[1]; + if (angle(b[0], a[1]) > angle(a[0], a[1])) a[0] = b[0]; + } else { + merged.push(a = b); + } + } + + // Finally, find the largest gap between the merged ranges. + // The final bounding box will be the inverse of this gap. + for (deltaMax = -Infinity, n = merged.length - 1, i = 0, a = merged[n]; i <= n; a = b, ++i) { + b = merged[i]; + if ((delta = angle(a[1], b[0])) > deltaMax) deltaMax = delta, lambda0$1 = b[0], lambda1 = a[1]; + } + } + + ranges = range = null; + + return lambda0$1 === Infinity || phi0 === Infinity + ? [[NaN, NaN], [NaN, NaN]] + : [[lambda0$1, phi0], [lambda1, phi1]]; +} + +var W0, W1, + X0$1, Y0$1, Z0$1, + X1$1, Y1$1, Z1$1, + X2$1, Y2$1, Z2$1, + lambda00, phi00, // first point + x0$4, y0$4, z0; // previous point + +var centroidStream$1 = { + sphere: noop$1, + point: centroidPoint$1, + lineStart: centroidLineStart$1, + lineEnd: centroidLineEnd$1, + polygonStart: function() { + centroidStream$1.lineStart = centroidRingStart$1; + centroidStream$1.lineEnd = centroidRingEnd$1; + }, + polygonEnd: function() { + centroidStream$1.lineStart = centroidLineStart$1; + centroidStream$1.lineEnd = centroidLineEnd$1; + } +}; + +// Arithmetic mean of Cartesian vectors. +function centroidPoint$1(lambda, phi) { + lambda *= radians, phi *= radians; + var cosPhi = cos$1(phi); + centroidPointCartesian(cosPhi * cos$1(lambda), cosPhi * sin$1(lambda), sin$1(phi)); +} + +function centroidPointCartesian(x, y, z) { + ++W0; + X0$1 += (x - X0$1) / W0; + Y0$1 += (y - Y0$1) / W0; + Z0$1 += (z - Z0$1) / W0; +} + +function centroidLineStart$1() { + centroidStream$1.point = centroidLinePointFirst; +} + +function centroidLinePointFirst(lambda, phi) { + lambda *= radians, phi *= radians; + var cosPhi = cos$1(phi); + x0$4 = cosPhi * cos$1(lambda); + y0$4 = cosPhi * sin$1(lambda); + z0 = sin$1(phi); + centroidStream$1.point = centroidLinePoint; + centroidPointCartesian(x0$4, y0$4, z0); +} + +function centroidLinePoint(lambda, phi) { + lambda *= radians, phi *= radians; + var cosPhi = cos$1(phi), + x = cosPhi * cos$1(lambda), + y = cosPhi * sin$1(lambda), + z = sin$1(phi), + w = atan2$1(sqrt$2((w = y0$4 * z - z0 * y) * w + (w = z0 * x - x0$4 * z) * w + (w = x0$4 * y - y0$4 * x) * w), x0$4 * x + y0$4 * y + z0 * z); + W1 += w; + X1$1 += w * (x0$4 + (x0$4 = x)); + Y1$1 += w * (y0$4 + (y0$4 = y)); + Z1$1 += w * (z0 + (z0 = z)); + centroidPointCartesian(x0$4, y0$4, z0); +} + +function centroidLineEnd$1() { + centroidStream$1.point = centroidPoint$1; +} + +// See J. E. Brock, The Inertia Tensor for a Spherical Triangle, +// J. Applied Mechanics 42, 239 (1975). +function centroidRingStart$1() { + centroidStream$1.point = centroidRingPointFirst; +} + +function centroidRingEnd$1() { + centroidRingPoint(lambda00, phi00); + centroidStream$1.point = centroidPoint$1; +} + +function centroidRingPointFirst(lambda, phi) { + lambda00 = lambda, phi00 = phi; + lambda *= radians, phi *= radians; + centroidStream$1.point = centroidRingPoint; + var cosPhi = cos$1(phi); + x0$4 = cosPhi * cos$1(lambda); + y0$4 = cosPhi * sin$1(lambda); + z0 = sin$1(phi); + centroidPointCartesian(x0$4, y0$4, z0); +} + +function centroidRingPoint(lambda, phi) { + lambda *= radians, phi *= radians; + var cosPhi = cos$1(phi), + x = cosPhi * cos$1(lambda), + y = cosPhi * sin$1(lambda), + z = sin$1(phi), + cx = y0$4 * z - z0 * y, + cy = z0 * x - x0$4 * z, + cz = x0$4 * y - y0$4 * x, + m = hypot(cx, cy, cz), + w = asin$1(m), // line weight = angle + v = m && -w / m; // area weight multiplier + X2$1.add(v * cx); + Y2$1.add(v * cy); + Z2$1.add(v * cz); + W1 += w; + X1$1 += w * (x0$4 + (x0$4 = x)); + Y1$1 += w * (y0$4 + (y0$4 = y)); + Z1$1 += w * (z0 + (z0 = z)); + centroidPointCartesian(x0$4, y0$4, z0); +} + +function centroid$1(object) { + W0 = W1 = + X0$1 = Y0$1 = Z0$1 = + X1$1 = Y1$1 = Z1$1 = 0; + X2$1 = new Adder(); + Y2$1 = new Adder(); + Z2$1 = new Adder(); + geoStream(object, centroidStream$1); + + var x = +X2$1, + y = +Y2$1, + z = +Z2$1, + m = hypot(x, y, z); + + // If the area-weighted ccentroid is undefined, fall back to length-weighted ccentroid. + if (m < epsilon2) { + x = X1$1, y = Y1$1, z = Z1$1; + // If the feature has zero length, fall back to arithmetic mean of point vectors. + if (W1 < epsilon$1) x = X0$1, y = Y0$1, z = Z0$1; + m = hypot(x, y, z); + // If the feature still has an undefined ccentroid, then return. + if (m < epsilon2) return [NaN, NaN]; + } + + return [atan2$1(y, x) * degrees, asin$1(z / m) * degrees]; +} + +function constant$3(x) { + return function() { + return x; + }; +} + +function compose(a, b) { + + function compose(x, y) { + return x = a(x, y), b(x[0], x[1]); + } + + if (a.invert && b.invert) compose.invert = function(x, y) { + return x = b.invert(x, y), x && a.invert(x[0], x[1]); + }; + + return compose; +} + +function rotationIdentity(lambda, phi) { + if (abs$1(lambda) > pi$1) lambda -= Math.round(lambda / tau$1) * tau$1; + return [lambda, phi]; +} + +rotationIdentity.invert = rotationIdentity; + +function rotateRadians(deltaLambda, deltaPhi, deltaGamma) { + return (deltaLambda %= tau$1) ? (deltaPhi || deltaGamma ? compose(rotationLambda(deltaLambda), rotationPhiGamma(deltaPhi, deltaGamma)) + : rotationLambda(deltaLambda)) + : (deltaPhi || deltaGamma ? rotationPhiGamma(deltaPhi, deltaGamma) + : rotationIdentity); +} + +function forwardRotationLambda(deltaLambda) { + return function(lambda, phi) { + lambda += deltaLambda; + if (abs$1(lambda) > pi$1) lambda -= Math.round(lambda / tau$1) * tau$1; + return [lambda, phi]; + }; +} + +function rotationLambda(deltaLambda) { + var rotation = forwardRotationLambda(deltaLambda); + rotation.invert = forwardRotationLambda(-deltaLambda); + return rotation; +} + +function rotationPhiGamma(deltaPhi, deltaGamma) { + var cosDeltaPhi = cos$1(deltaPhi), + sinDeltaPhi = sin$1(deltaPhi), + cosDeltaGamma = cos$1(deltaGamma), + sinDeltaGamma = sin$1(deltaGamma); + + function rotation(lambda, phi) { + var cosPhi = cos$1(phi), + x = cos$1(lambda) * cosPhi, + y = sin$1(lambda) * cosPhi, + z = sin$1(phi), + k = z * cosDeltaPhi + x * sinDeltaPhi; + return [ + atan2$1(y * cosDeltaGamma - k * sinDeltaGamma, x * cosDeltaPhi - z * sinDeltaPhi), + asin$1(k * cosDeltaGamma + y * sinDeltaGamma) + ]; + } + + rotation.invert = function(lambda, phi) { + var cosPhi = cos$1(phi), + x = cos$1(lambda) * cosPhi, + y = sin$1(lambda) * cosPhi, + z = sin$1(phi), + k = z * cosDeltaGamma - y * sinDeltaGamma; + return [ + atan2$1(y * cosDeltaGamma + z * sinDeltaGamma, x * cosDeltaPhi + k * sinDeltaPhi), + asin$1(k * cosDeltaPhi - x * sinDeltaPhi) + ]; + }; + + return rotation; +} + +function rotation(rotate) { + rotate = rotateRadians(rotate[0] * radians, rotate[1] * radians, rotate.length > 2 ? rotate[2] * radians : 0); + + function forward(coordinates) { + coordinates = rotate(coordinates[0] * radians, coordinates[1] * radians); + return coordinates[0] *= degrees, coordinates[1] *= degrees, coordinates; + } + + forward.invert = function(coordinates) { + coordinates = rotate.invert(coordinates[0] * radians, coordinates[1] * radians); + return coordinates[0] *= degrees, coordinates[1] *= degrees, coordinates; + }; + + return forward; +} + +// Generates a circle centered at [0°, 0°], with a given radius and precision. +function circleStream(stream, radius, delta, direction, t0, t1) { + if (!delta) return; + var cosRadius = cos$1(radius), + sinRadius = sin$1(radius), + step = direction * delta; + if (t0 == null) { + t0 = radius + direction * tau$1; + t1 = radius - step / 2; + } else { + t0 = circleRadius(cosRadius, t0); + t1 = circleRadius(cosRadius, t1); + if (direction > 0 ? t0 < t1 : t0 > t1) t0 += direction * tau$1; + } + for (var point, t = t0; direction > 0 ? t > t1 : t < t1; t -= step) { + point = spherical([cosRadius, -sinRadius * cos$1(t), -sinRadius * sin$1(t)]); + stream.point(point[0], point[1]); + } +} + +// Returns the signed angle of a cartesian point relative to [cosRadius, 0, 0]. +function circleRadius(cosRadius, point) { + point = cartesian(point), point[0] -= cosRadius; + cartesianNormalizeInPlace(point); + var radius = acos$1(-point[1]); + return ((-point[2] < 0 ? -radius : radius) + tau$1 - epsilon$1) % tau$1; +} + +function circle$1() { + var center = constant$3([0, 0]), + radius = constant$3(90), + precision = constant$3(2), + ring, + rotate, + stream = {point: point}; + + function point(x, y) { + ring.push(x = rotate(x, y)); + x[0] *= degrees, x[1] *= degrees; + } + + function circle() { + var c = center.apply(this, arguments), + r = radius.apply(this, arguments) * radians, + p = precision.apply(this, arguments) * radians; + ring = []; + rotate = rotateRadians(-c[0] * radians, -c[1] * radians, 0).invert; + circleStream(stream, r, p, 1); + c = {type: "Polygon", coordinates: [ring]}; + ring = rotate = null; + return c; + } + + circle.center = function(_) { + return arguments.length ? (center = typeof _ === "function" ? _ : constant$3([+_[0], +_[1]]), circle) : center; + }; + + circle.radius = function(_) { + return arguments.length ? (radius = typeof _ === "function" ? _ : constant$3(+_), circle) : radius; + }; + + circle.precision = function(_) { + return arguments.length ? (precision = typeof _ === "function" ? _ : constant$3(+_), circle) : precision; + }; + + return circle; +} + +function clipBuffer() { + var lines = [], + line; + return { + point: function(x, y, m) { + line.push([x, y, m]); + }, + lineStart: function() { + lines.push(line = []); + }, + lineEnd: noop$1, + rejoin: function() { + if (lines.length > 1) lines.push(lines.pop().concat(lines.shift())); + }, + result: function() { + var result = lines; + lines = []; + line = null; + return result; + } + }; +} + +function pointEqual(a, b) { + return abs$1(a[0] - b[0]) < epsilon$1 && abs$1(a[1] - b[1]) < epsilon$1; +} + +function Intersection(point, points, other, entry) { + this.x = point; + this.z = points; + this.o = other; // another intersection + this.e = entry; // is an entry? + this.v = false; // visited + this.n = this.p = null; // next & previous +} + +// A generalized polygon clipping algorithm: given a polygon that has been cut +// into its visible line segments, and rejoins the segments by interpolating +// along the clip edge. +function clipRejoin(segments, compareIntersection, startInside, interpolate, stream) { + var subject = [], + clip = [], + i, + n; + + segments.forEach(function(segment) { + if ((n = segment.length - 1) <= 0) return; + var n, p0 = segment[0], p1 = segment[n], x; + + if (pointEqual(p0, p1)) { + if (!p0[2] && !p1[2]) { + stream.lineStart(); + for (i = 0; i < n; ++i) stream.point((p0 = segment[i])[0], p0[1]); + stream.lineEnd(); + return; + } + // handle degenerate cases by moving the point + p1[0] += 2 * epsilon$1; + } + + subject.push(x = new Intersection(p0, segment, null, true)); + clip.push(x.o = new Intersection(p0, null, x, false)); + subject.push(x = new Intersection(p1, segment, null, false)); + clip.push(x.o = new Intersection(p1, null, x, true)); + }); + + if (!subject.length) return; + + clip.sort(compareIntersection); + link$1(subject); + link$1(clip); + + for (i = 0, n = clip.length; i < n; ++i) { + clip[i].e = startInside = !startInside; + } + + var start = subject[0], + points, + point; + + while (1) { + // Find first unvisited intersection. + var current = start, + isSubject = true; + while (current.v) if ((current = current.n) === start) return; + points = current.z; + stream.lineStart(); + do { + current.v = current.o.v = true; + if (current.e) { + if (isSubject) { + for (i = 0, n = points.length; i < n; ++i) stream.point((point = points[i])[0], point[1]); + } else { + interpolate(current.x, current.n.x, 1, stream); + } + current = current.n; + } else { + if (isSubject) { + points = current.p.z; + for (i = points.length - 1; i >= 0; --i) stream.point((point = points[i])[0], point[1]); + } else { + interpolate(current.x, current.p.x, -1, stream); + } + current = current.p; + } + current = current.o; + points = current.z; + isSubject = !isSubject; + } while (!current.v); + stream.lineEnd(); + } +} + +function link$1(array) { + if (!(n = array.length)) return; + var n, + i = 0, + a = array[0], + b; + while (++i < n) { + a.n = b = array[i]; + b.p = a; + a = b; + } + a.n = b = array[0]; + b.p = a; +} + +function longitude(point) { + return abs$1(point[0]) <= pi$1 ? point[0] : sign$1(point[0]) * ((abs$1(point[0]) + pi$1) % tau$1 - pi$1); +} + +function polygonContains(polygon, point) { + var lambda = longitude(point), + phi = point[1], + sinPhi = sin$1(phi), + normal = [sin$1(lambda), -cos$1(lambda), 0], + angle = 0, + winding = 0; + + var sum = new Adder(); + + if (sinPhi === 1) phi = halfPi$1 + epsilon$1; + else if (sinPhi === -1) phi = -halfPi$1 - epsilon$1; + + for (var i = 0, n = polygon.length; i < n; ++i) { + if (!(m = (ring = polygon[i]).length)) continue; + var ring, + m, + point0 = ring[m - 1], + lambda0 = longitude(point0), + phi0 = point0[1] / 2 + quarterPi, + sinPhi0 = sin$1(phi0), + cosPhi0 = cos$1(phi0); + + for (var j = 0; j < m; ++j, lambda0 = lambda1, sinPhi0 = sinPhi1, cosPhi0 = cosPhi1, point0 = point1) { + var point1 = ring[j], + lambda1 = longitude(point1), + phi1 = point1[1] / 2 + quarterPi, + sinPhi1 = sin$1(phi1), + cosPhi1 = cos$1(phi1), + delta = lambda1 - lambda0, + sign = delta >= 0 ? 1 : -1, + absDelta = sign * delta, + antimeridian = absDelta > pi$1, + k = sinPhi0 * sinPhi1; + + sum.add(atan2$1(k * sign * sin$1(absDelta), cosPhi0 * cosPhi1 + k * cos$1(absDelta))); + angle += antimeridian ? delta + sign * tau$1 : delta; + + // Are the longitudes either side of the point’s meridian (lambda), + // and are the latitudes smaller than the parallel (phi)? + if (antimeridian ^ lambda0 >= lambda ^ lambda1 >= lambda) { + var arc = cartesianCross(cartesian(point0), cartesian(point1)); + cartesianNormalizeInPlace(arc); + var intersection = cartesianCross(normal, arc); + cartesianNormalizeInPlace(intersection); + var phiArc = (antimeridian ^ delta >= 0 ? -1 : 1) * asin$1(intersection[2]); + if (phi > phiArc || phi === phiArc && (arc[0] || arc[1])) { + winding += antimeridian ^ delta >= 0 ? 1 : -1; + } + } + } + } + + // First, determine whether the South pole is inside or outside: + // + // It is inside if: + // * the polygon winds around it in a clockwise direction. + // * the polygon does not (cumulatively) wind around it, but has a negative + // (counter-clockwise) area. + // + // Second, count the (signed) number of times a segment crosses a lambda + // from the point to the South pole. If it is zero, then the point is the + // same side as the South pole. + + return (angle < -epsilon$1 || angle < epsilon$1 && sum < -epsilon2) ^ (winding & 1); +} + +function clip(pointVisible, clipLine, interpolate, start) { + return function(sink) { + var line = clipLine(sink), + ringBuffer = clipBuffer(), + ringSink = clipLine(ringBuffer), + polygonStarted = false, + polygon, + segments, + ring; + + var clip = { + point: point, + lineStart: lineStart, + lineEnd: lineEnd, + polygonStart: function() { + clip.point = pointRing; + clip.lineStart = ringStart; + clip.lineEnd = ringEnd; + segments = []; + polygon = []; + }, + polygonEnd: function() { + clip.point = point; + clip.lineStart = lineStart; + clip.lineEnd = lineEnd; + segments = merge(segments); + var startInside = polygonContains(polygon, start); + if (segments.length) { + if (!polygonStarted) sink.polygonStart(), polygonStarted = true; + clipRejoin(segments, compareIntersection, startInside, interpolate, sink); + } else if (startInside) { + if (!polygonStarted) sink.polygonStart(), polygonStarted = true; + sink.lineStart(); + interpolate(null, null, 1, sink); + sink.lineEnd(); + } + if (polygonStarted) sink.polygonEnd(), polygonStarted = false; + segments = polygon = null; + }, + sphere: function() { + sink.polygonStart(); + sink.lineStart(); + interpolate(null, null, 1, sink); + sink.lineEnd(); + sink.polygonEnd(); + } + }; + + function point(lambda, phi) { + if (pointVisible(lambda, phi)) sink.point(lambda, phi); + } + + function pointLine(lambda, phi) { + line.point(lambda, phi); + } + + function lineStart() { + clip.point = pointLine; + line.lineStart(); + } + + function lineEnd() { + clip.point = point; + line.lineEnd(); + } + + function pointRing(lambda, phi) { + ring.push([lambda, phi]); + ringSink.point(lambda, phi); + } + + function ringStart() { + ringSink.lineStart(); + ring = []; + } + + function ringEnd() { + pointRing(ring[0][0], ring[0][1]); + ringSink.lineEnd(); + + var clean = ringSink.clean(), + ringSegments = ringBuffer.result(), + i, n = ringSegments.length, m, + segment, + point; + + ring.pop(); + polygon.push(ring); + ring = null; + + if (!n) return; + + // No intersections. + if (clean & 1) { + segment = ringSegments[0]; + if ((m = segment.length - 1) > 0) { + if (!polygonStarted) sink.polygonStart(), polygonStarted = true; + sink.lineStart(); + for (i = 0; i < m; ++i) sink.point((point = segment[i])[0], point[1]); + sink.lineEnd(); + } + return; + } + + // Rejoin connected segments. + // TODO reuse ringBuffer.rejoin()? + if (n > 1 && clean & 2) ringSegments.push(ringSegments.pop().concat(ringSegments.shift())); + + segments.push(ringSegments.filter(validSegment)); + } + + return clip; + }; +} + +function validSegment(segment) { + return segment.length > 1; +} + +// Intersections are sorted along the clip edge. For both antimeridian cutting +// and circle clipping, the same comparison is used. +function compareIntersection(a, b) { + return ((a = a.x)[0] < 0 ? a[1] - halfPi$1 - epsilon$1 : halfPi$1 - a[1]) + - ((b = b.x)[0] < 0 ? b[1] - halfPi$1 - epsilon$1 : halfPi$1 - b[1]); +} + +var clipAntimeridian = clip( + function() { return true; }, + clipAntimeridianLine, + clipAntimeridianInterpolate, + [-pi$1, -halfPi$1] +); + +// Takes a line and cuts into visible segments. Return values: 0 - there were +// intersections or the line was empty; 1 - no intersections; 2 - there were +// intersections, and the first and last segments should be rejoined. +function clipAntimeridianLine(stream) { + var lambda0 = NaN, + phi0 = NaN, + sign0 = NaN, + clean; // no intersections + + return { + lineStart: function() { + stream.lineStart(); + clean = 1; + }, + point: function(lambda1, phi1) { + var sign1 = lambda1 > 0 ? pi$1 : -pi$1, + delta = abs$1(lambda1 - lambda0); + if (abs$1(delta - pi$1) < epsilon$1) { // line crosses a pole + stream.point(lambda0, phi0 = (phi0 + phi1) / 2 > 0 ? halfPi$1 : -halfPi$1); + stream.point(sign0, phi0); + stream.lineEnd(); + stream.lineStart(); + stream.point(sign1, phi0); + stream.point(lambda1, phi0); + clean = 0; + } else if (sign0 !== sign1 && delta >= pi$1) { // line crosses antimeridian + if (abs$1(lambda0 - sign0) < epsilon$1) lambda0 -= sign0 * epsilon$1; // handle degeneracies + if (abs$1(lambda1 - sign1) < epsilon$1) lambda1 -= sign1 * epsilon$1; + phi0 = clipAntimeridianIntersect(lambda0, phi0, lambda1, phi1); + stream.point(sign0, phi0); + stream.lineEnd(); + stream.lineStart(); + stream.point(sign1, phi0); + clean = 0; + } + stream.point(lambda0 = lambda1, phi0 = phi1); + sign0 = sign1; + }, + lineEnd: function() { + stream.lineEnd(); + lambda0 = phi0 = NaN; + }, + clean: function() { + return 2 - clean; // if intersections, rejoin first and last segments + } + }; +} + +function clipAntimeridianIntersect(lambda0, phi0, lambda1, phi1) { + var cosPhi0, + cosPhi1, + sinLambda0Lambda1 = sin$1(lambda0 - lambda1); + return abs$1(sinLambda0Lambda1) > epsilon$1 + ? atan((sin$1(phi0) * (cosPhi1 = cos$1(phi1)) * sin$1(lambda1) + - sin$1(phi1) * (cosPhi0 = cos$1(phi0)) * sin$1(lambda0)) + / (cosPhi0 * cosPhi1 * sinLambda0Lambda1)) + : (phi0 + phi1) / 2; +} + +function clipAntimeridianInterpolate(from, to, direction, stream) { + var phi; + if (from == null) { + phi = direction * halfPi$1; + stream.point(-pi$1, phi); + stream.point(0, phi); + stream.point(pi$1, phi); + stream.point(pi$1, 0); + stream.point(pi$1, -phi); + stream.point(0, -phi); + stream.point(-pi$1, -phi); + stream.point(-pi$1, 0); + stream.point(-pi$1, phi); + } else if (abs$1(from[0] - to[0]) > epsilon$1) { + var lambda = from[0] < to[0] ? pi$1 : -pi$1; + phi = direction * lambda / 2; + stream.point(-lambda, phi); + stream.point(0, phi); + stream.point(lambda, phi); + } else { + stream.point(to[0], to[1]); + } +} + +function clipCircle(radius) { + var cr = cos$1(radius), + delta = 2 * radians, + smallRadius = cr > 0, + notHemisphere = abs$1(cr) > epsilon$1; // TODO optimise for this common case + + function interpolate(from, to, direction, stream) { + circleStream(stream, radius, delta, direction, from, to); + } + + function visible(lambda, phi) { + return cos$1(lambda) * cos$1(phi) > cr; + } + + // Takes a line and cuts into visible segments. Return values used for polygon + // clipping: 0 - there were intersections or the line was empty; 1 - no + // intersections 2 - there were intersections, and the first and last segments + // should be rejoined. + function clipLine(stream) { + var point0, // previous point + c0, // code for previous point + v0, // visibility of previous point + v00, // visibility of first point + clean; // no intersections + return { + lineStart: function() { + v00 = v0 = false; + clean = 1; + }, + point: function(lambda, phi) { + var point1 = [lambda, phi], + point2, + v = visible(lambda, phi), + c = smallRadius + ? v ? 0 : code(lambda, phi) + : v ? code(lambda + (lambda < 0 ? pi$1 : -pi$1), phi) : 0; + if (!point0 && (v00 = v0 = v)) stream.lineStart(); + if (v !== v0) { + point2 = intersect(point0, point1); + if (!point2 || pointEqual(point0, point2) || pointEqual(point1, point2)) + point1[2] = 1; + } + if (v !== v0) { + clean = 0; + if (v) { + // outside going in + stream.lineStart(); + point2 = intersect(point1, point0); + stream.point(point2[0], point2[1]); + } else { + // inside going out + point2 = intersect(point0, point1); + stream.point(point2[0], point2[1], 2); + stream.lineEnd(); + } + point0 = point2; + } else if (notHemisphere && point0 && smallRadius ^ v) { + var t; + // If the codes for two points are different, or are both zero, + // and there this segment intersects with the small circle. + if (!(c & c0) && (t = intersect(point1, point0, true))) { + clean = 0; + if (smallRadius) { + stream.lineStart(); + stream.point(t[0][0], t[0][1]); + stream.point(t[1][0], t[1][1]); + stream.lineEnd(); + } else { + stream.point(t[1][0], t[1][1]); + stream.lineEnd(); + stream.lineStart(); + stream.point(t[0][0], t[0][1], 3); + } + } + } + if (v && (!point0 || !pointEqual(point0, point1))) { + stream.point(point1[0], point1[1]); + } + point0 = point1, v0 = v, c0 = c; + }, + lineEnd: function() { + if (v0) stream.lineEnd(); + point0 = null; + }, + // Rejoin first and last segments if there were intersections and the first + // and last points were visible. + clean: function() { + return clean | ((v00 && v0) << 1); + } + }; + } + + // Intersects the great circle between a and b with the clip circle. + function intersect(a, b, two) { + var pa = cartesian(a), + pb = cartesian(b); + + // We have two planes, n1.p = d1 and n2.p = d2. + // Find intersection line p(t) = c1 n1 + c2 n2 + t (n1 ⨯ n2). + var n1 = [1, 0, 0], // normal + n2 = cartesianCross(pa, pb), + n2n2 = cartesianDot(n2, n2), + n1n2 = n2[0], // cartesianDot(n1, n2), + determinant = n2n2 - n1n2 * n1n2; + + // Two polar points. + if (!determinant) return !two && a; + + var c1 = cr * n2n2 / determinant, + c2 = -cr * n1n2 / determinant, + n1xn2 = cartesianCross(n1, n2), + A = cartesianScale(n1, c1), + B = cartesianScale(n2, c2); + cartesianAddInPlace(A, B); + + // Solve |p(t)|^2 = 1. + var u = n1xn2, + w = cartesianDot(A, u), + uu = cartesianDot(u, u), + t2 = w * w - uu * (cartesianDot(A, A) - 1); + + if (t2 < 0) return; + + var t = sqrt$2(t2), + q = cartesianScale(u, (-w - t) / uu); + cartesianAddInPlace(q, A); + q = spherical(q); + + if (!two) return q; + + // Two intersection points. + var lambda0 = a[0], + lambda1 = b[0], + phi0 = a[1], + phi1 = b[1], + z; + + if (lambda1 < lambda0) z = lambda0, lambda0 = lambda1, lambda1 = z; + + var delta = lambda1 - lambda0, + polar = abs$1(delta - pi$1) < epsilon$1, + meridian = polar || delta < epsilon$1; + + if (!polar && phi1 < phi0) z = phi0, phi0 = phi1, phi1 = z; + + // Check that the first point is between a and b. + if (meridian + ? polar + ? phi0 + phi1 > 0 ^ q[1] < (abs$1(q[0] - lambda0) < epsilon$1 ? phi0 : phi1) + : phi0 <= q[1] && q[1] <= phi1 + : delta > pi$1 ^ (lambda0 <= q[0] && q[0] <= lambda1)) { + var q1 = cartesianScale(u, (-w + t) / uu); + cartesianAddInPlace(q1, A); + return [q, spherical(q1)]; + } + } + + // Generates a 4-bit vector representing the location of a point relative to + // the small circle's bounding box. + function code(lambda, phi) { + var r = smallRadius ? radius : pi$1 - radius, + code = 0; + if (lambda < -r) code |= 1; // left + else if (lambda > r) code |= 2; // right + if (phi < -r) code |= 4; // below + else if (phi > r) code |= 8; // above + return code; + } + + return clip(visible, clipLine, interpolate, smallRadius ? [0, -radius] : [-pi$1, radius - pi$1]); +} + +function clipLine(a, b, x0, y0, x1, y1) { + var ax = a[0], + ay = a[1], + bx = b[0], + by = b[1], + t0 = 0, + t1 = 1, + dx = bx - ax, + dy = by - ay, + r; + + r = x0 - ax; + if (!dx && r > 0) return; + r /= dx; + if (dx < 0) { + if (r < t0) return; + if (r < t1) t1 = r; + } else if (dx > 0) { + if (r > t1) return; + if (r > t0) t0 = r; + } + + r = x1 - ax; + if (!dx && r < 0) return; + r /= dx; + if (dx < 0) { + if (r > t1) return; + if (r > t0) t0 = r; + } else if (dx > 0) { + if (r < t0) return; + if (r < t1) t1 = r; + } + + r = y0 - ay; + if (!dy && r > 0) return; + r /= dy; + if (dy < 0) { + if (r < t0) return; + if (r < t1) t1 = r; + } else if (dy > 0) { + if (r > t1) return; + if (r > t0) t0 = r; + } + + r = y1 - ay; + if (!dy && r < 0) return; + r /= dy; + if (dy < 0) { + if (r > t1) return; + if (r > t0) t0 = r; + } else if (dy > 0) { + if (r < t0) return; + if (r < t1) t1 = r; + } + + if (t0 > 0) a[0] = ax + t0 * dx, a[1] = ay + t0 * dy; + if (t1 < 1) b[0] = ax + t1 * dx, b[1] = ay + t1 * dy; + return true; +} + +var clipMax = 1e9, clipMin = -clipMax; + +// TODO Use d3-polygon’s polygonContains here for the ring check? +// TODO Eliminate duplicate buffering in clipBuffer and polygon.push? + +function clipRectangle(x0, y0, x1, y1) { + + function visible(x, y) { + return x0 <= x && x <= x1 && y0 <= y && y <= y1; + } + + function interpolate(from, to, direction, stream) { + var a = 0, a1 = 0; + if (from == null + || (a = corner(from, direction)) !== (a1 = corner(to, direction)) + || comparePoint(from, to) < 0 ^ direction > 0) { + do stream.point(a === 0 || a === 3 ? x0 : x1, a > 1 ? y1 : y0); + while ((a = (a + direction + 4) % 4) !== a1); + } else { + stream.point(to[0], to[1]); + } + } + + function corner(p, direction) { + return abs$1(p[0] - x0) < epsilon$1 ? direction > 0 ? 0 : 3 + : abs$1(p[0] - x1) < epsilon$1 ? direction > 0 ? 2 : 1 + : abs$1(p[1] - y0) < epsilon$1 ? direction > 0 ? 1 : 0 + : direction > 0 ? 3 : 2; // abs(p[1] - y1) < epsilon + } + + function compareIntersection(a, b) { + return comparePoint(a.x, b.x); + } + + function comparePoint(a, b) { + var ca = corner(a, 1), + cb = corner(b, 1); + return ca !== cb ? ca - cb + : ca === 0 ? b[1] - a[1] + : ca === 1 ? a[0] - b[0] + : ca === 2 ? a[1] - b[1] + : b[0] - a[0]; + } + + return function(stream) { + var activeStream = stream, + bufferStream = clipBuffer(), + segments, + polygon, + ring, + x__, y__, v__, // first point + x_, y_, v_, // previous point + first, + clean; + + var clipStream = { + point: point, + lineStart: lineStart, + lineEnd: lineEnd, + polygonStart: polygonStart, + polygonEnd: polygonEnd + }; + + function point(x, y) { + if (visible(x, y)) activeStream.point(x, y); + } + + function polygonInside() { + var winding = 0; + + for (var i = 0, n = polygon.length; i < n; ++i) { + for (var ring = polygon[i], j = 1, m = ring.length, point = ring[0], a0, a1, b0 = point[0], b1 = point[1]; j < m; ++j) { + a0 = b0, a1 = b1, point = ring[j], b0 = point[0], b1 = point[1]; + if (a1 <= y1) { if (b1 > y1 && (b0 - a0) * (y1 - a1) > (b1 - a1) * (x0 - a0)) ++winding; } + else { if (b1 <= y1 && (b0 - a0) * (y1 - a1) < (b1 - a1) * (x0 - a0)) --winding; } + } + } + + return winding; + } + + // Buffer geometry within a polygon and then clip it en masse. + function polygonStart() { + activeStream = bufferStream, segments = [], polygon = [], clean = true; + } + + function polygonEnd() { + var startInside = polygonInside(), + cleanInside = clean && startInside, + visible = (segments = merge(segments)).length; + if (cleanInside || visible) { + stream.polygonStart(); + if (cleanInside) { + stream.lineStart(); + interpolate(null, null, 1, stream); + stream.lineEnd(); + } + if (visible) { + clipRejoin(segments, compareIntersection, startInside, interpolate, stream); + } + stream.polygonEnd(); + } + activeStream = stream, segments = polygon = ring = null; + } + + function lineStart() { + clipStream.point = linePoint; + if (polygon) polygon.push(ring = []); + first = true; + v_ = false; + x_ = y_ = NaN; + } + + // TODO rather than special-case polygons, simply handle them separately. + // Ideally, coincident intersection points should be jittered to avoid + // clipping issues. + function lineEnd() { + if (segments) { + linePoint(x__, y__); + if (v__ && v_) bufferStream.rejoin(); + segments.push(bufferStream.result()); + } + clipStream.point = point; + if (v_) activeStream.lineEnd(); + } + + function linePoint(x, y) { + var v = visible(x, y); + if (polygon) ring.push([x, y]); + if (first) { + x__ = x, y__ = y, v__ = v; + first = false; + if (v) { + activeStream.lineStart(); + activeStream.point(x, y); + } + } else { + if (v && v_) activeStream.point(x, y); + else { + var a = [x_ = Math.max(clipMin, Math.min(clipMax, x_)), y_ = Math.max(clipMin, Math.min(clipMax, y_))], + b = [x = Math.max(clipMin, Math.min(clipMax, x)), y = Math.max(clipMin, Math.min(clipMax, y))]; + if (clipLine(a, b, x0, y0, x1, y1)) { + if (!v_) { + activeStream.lineStart(); + activeStream.point(a[0], a[1]); + } + activeStream.point(b[0], b[1]); + if (!v) activeStream.lineEnd(); + clean = false; + } else if (v) { + activeStream.lineStart(); + activeStream.point(x, y); + clean = false; + } + } + } + x_ = x, y_ = y, v_ = v; + } + + return clipStream; + }; +} + +function extent() { + var x0 = 0, + y0 = 0, + x1 = 960, + y1 = 500, + cache, + cacheStream, + clip; + + return clip = { + stream: function(stream) { + return cache && cacheStream === stream ? cache : cache = clipRectangle(x0, y0, x1, y1)(cacheStream = stream); + }, + extent: function(_) { + return arguments.length ? (x0 = +_[0][0], y0 = +_[0][1], x1 = +_[1][0], y1 = +_[1][1], cache = cacheStream = null, clip) : [[x0, y0], [x1, y1]]; + } + }; +} + +var lengthSum$1, + lambda0, + sinPhi0, + cosPhi0; + +var lengthStream$1 = { + sphere: noop$1, + point: noop$1, + lineStart: lengthLineStart, + lineEnd: noop$1, + polygonStart: noop$1, + polygonEnd: noop$1 +}; + +function lengthLineStart() { + lengthStream$1.point = lengthPointFirst$1; + lengthStream$1.lineEnd = lengthLineEnd; +} + +function lengthLineEnd() { + lengthStream$1.point = lengthStream$1.lineEnd = noop$1; +} + +function lengthPointFirst$1(lambda, phi) { + lambda *= radians, phi *= radians; + lambda0 = lambda, sinPhi0 = sin$1(phi), cosPhi0 = cos$1(phi); + lengthStream$1.point = lengthPoint$1; +} + +function lengthPoint$1(lambda, phi) { + lambda *= radians, phi *= radians; + var sinPhi = sin$1(phi), + cosPhi = cos$1(phi), + delta = abs$1(lambda - lambda0), + cosDelta = cos$1(delta), + sinDelta = sin$1(delta), + x = cosPhi * sinDelta, + y = cosPhi0 * sinPhi - sinPhi0 * cosPhi * cosDelta, + z = sinPhi0 * sinPhi + cosPhi0 * cosPhi * cosDelta; + lengthSum$1.add(atan2$1(sqrt$2(x * x + y * y), z)); + lambda0 = lambda, sinPhi0 = sinPhi, cosPhi0 = cosPhi; +} + +function length$1(object) { + lengthSum$1 = new Adder(); + geoStream(object, lengthStream$1); + return +lengthSum$1; +} + +var coordinates = [null, null], + object = {type: "LineString", coordinates: coordinates}; + +function distance(a, b) { + coordinates[0] = a; + coordinates[1] = b; + return length$1(object); +} + +var containsObjectType = { + Feature: function(object, point) { + return containsGeometry(object.geometry, point); + }, + FeatureCollection: function(object, point) { + var features = object.features, i = -1, n = features.length; + while (++i < n) if (containsGeometry(features[i].geometry, point)) return true; + return false; + } +}; + +var containsGeometryType = { + Sphere: function() { + return true; + }, + Point: function(object, point) { + return containsPoint(object.coordinates, point); + }, + MultiPoint: function(object, point) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) if (containsPoint(coordinates[i], point)) return true; + return false; + }, + LineString: function(object, point) { + return containsLine(object.coordinates, point); + }, + MultiLineString: function(object, point) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) if (containsLine(coordinates[i], point)) return true; + return false; + }, + Polygon: function(object, point) { + return containsPolygon(object.coordinates, point); + }, + MultiPolygon: function(object, point) { + var coordinates = object.coordinates, i = -1, n = coordinates.length; + while (++i < n) if (containsPolygon(coordinates[i], point)) return true; + return false; + }, + GeometryCollection: function(object, point) { + var geometries = object.geometries, i = -1, n = geometries.length; + while (++i < n) if (containsGeometry(geometries[i], point)) return true; + return false; + } +}; + +function containsGeometry(geometry, point) { + return geometry && containsGeometryType.hasOwnProperty(geometry.type) + ? containsGeometryType[geometry.type](geometry, point) + : false; +} + +function containsPoint(coordinates, point) { + return distance(coordinates, point) === 0; +} + +function containsLine(coordinates, point) { + var ao, bo, ab; + for (var i = 0, n = coordinates.length; i < n; i++) { + bo = distance(coordinates[i], point); + if (bo === 0) return true; + if (i > 0) { + ab = distance(coordinates[i], coordinates[i - 1]); + if ( + ab > 0 && + ao <= ab && + bo <= ab && + (ao + bo - ab) * (1 - Math.pow((ao - bo) / ab, 2)) < epsilon2 * ab + ) + return true; + } + ao = bo; + } + return false; +} + +function containsPolygon(coordinates, point) { + return !!polygonContains(coordinates.map(ringRadians), pointRadians(point)); +} + +function ringRadians(ring) { + return ring = ring.map(pointRadians), ring.pop(), ring; +} + +function pointRadians(point) { + return [point[0] * radians, point[1] * radians]; +} + +function contains$1(object, point) { + return (object && containsObjectType.hasOwnProperty(object.type) + ? containsObjectType[object.type] + : containsGeometry)(object, point); +} + +function graticuleX(y0, y1, dy) { + var y = range$2(y0, y1 - epsilon$1, dy).concat(y1); + return function(x) { return y.map(function(y) { return [x, y]; }); }; +} + +function graticuleY(x0, x1, dx) { + var x = range$2(x0, x1 - epsilon$1, dx).concat(x1); + return function(y) { return x.map(function(x) { return [x, y]; }); }; +} + +function graticule() { + var x1, x0, X1, X0, + y1, y0, Y1, Y0, + dx = 10, dy = dx, DX = 90, DY = 360, + x, y, X, Y, + precision = 2.5; + + function graticule() { + return {type: "MultiLineString", coordinates: lines()}; + } + + function lines() { + return range$2(ceil(X0 / DX) * DX, X1, DX).map(X) + .concat(range$2(ceil(Y0 / DY) * DY, Y1, DY).map(Y)) + .concat(range$2(ceil(x0 / dx) * dx, x1, dx).filter(function(x) { return abs$1(x % DX) > epsilon$1; }).map(x)) + .concat(range$2(ceil(y0 / dy) * dy, y1, dy).filter(function(y) { return abs$1(y % DY) > epsilon$1; }).map(y)); + } + + graticule.lines = function() { + return lines().map(function(coordinates) { return {type: "LineString", coordinates: coordinates}; }); + }; + + graticule.outline = function() { + return { + type: "Polygon", + coordinates: [ + X(X0).concat( + Y(Y1).slice(1), + X(X1).reverse().slice(1), + Y(Y0).reverse().slice(1)) + ] + }; + }; + + graticule.extent = function(_) { + if (!arguments.length) return graticule.extentMinor(); + return graticule.extentMajor(_).extentMinor(_); + }; + + graticule.extentMajor = function(_) { + if (!arguments.length) return [[X0, Y0], [X1, Y1]]; + X0 = +_[0][0], X1 = +_[1][0]; + Y0 = +_[0][1], Y1 = +_[1][1]; + if (X0 > X1) _ = X0, X0 = X1, X1 = _; + if (Y0 > Y1) _ = Y0, Y0 = Y1, Y1 = _; + return graticule.precision(precision); + }; + + graticule.extentMinor = function(_) { + if (!arguments.length) return [[x0, y0], [x1, y1]]; + x0 = +_[0][0], x1 = +_[1][0]; + y0 = +_[0][1], y1 = +_[1][1]; + if (x0 > x1) _ = x0, x0 = x1, x1 = _; + if (y0 > y1) _ = y0, y0 = y1, y1 = _; + return graticule.precision(precision); + }; + + graticule.step = function(_) { + if (!arguments.length) return graticule.stepMinor(); + return graticule.stepMajor(_).stepMinor(_); + }; + + graticule.stepMajor = function(_) { + if (!arguments.length) return [DX, DY]; + DX = +_[0], DY = +_[1]; + return graticule; + }; + + graticule.stepMinor = function(_) { + if (!arguments.length) return [dx, dy]; + dx = +_[0], dy = +_[1]; + return graticule; + }; + + graticule.precision = function(_) { + if (!arguments.length) return precision; + precision = +_; + x = graticuleX(y0, y1, 90); + y = graticuleY(x0, x1, precision); + X = graticuleX(Y0, Y1, 90); + Y = graticuleY(X0, X1, precision); + return graticule; + }; + + return graticule + .extentMajor([[-180, -90 + epsilon$1], [180, 90 - epsilon$1]]) + .extentMinor([[-180, -80 - epsilon$1], [180, 80 + epsilon$1]]); +} + +function graticule10() { + return graticule()(); +} + +function interpolate(a, b) { + var x0 = a[0] * radians, + y0 = a[1] * radians, + x1 = b[0] * radians, + y1 = b[1] * radians, + cy0 = cos$1(y0), + sy0 = sin$1(y0), + cy1 = cos$1(y1), + sy1 = sin$1(y1), + kx0 = cy0 * cos$1(x0), + ky0 = cy0 * sin$1(x0), + kx1 = cy1 * cos$1(x1), + ky1 = cy1 * sin$1(x1), + d = 2 * asin$1(sqrt$2(haversin(y1 - y0) + cy0 * cy1 * haversin(x1 - x0))), + k = sin$1(d); + + var interpolate = d ? function(t) { + var B = sin$1(t *= d) / k, + A = sin$1(d - t) / k, + x = A * kx0 + B * kx1, + y = A * ky0 + B * ky1, + z = A * sy0 + B * sy1; + return [ + atan2$1(y, x) * degrees, + atan2$1(z, sqrt$2(x * x + y * y)) * degrees + ]; + } : function() { + return [x0 * degrees, y0 * degrees]; + }; + + interpolate.distance = d; + + return interpolate; +} + +var identity$5 = x => x; + +var areaSum = new Adder(), + areaRingSum = new Adder(), + x00$2, + y00$2, + x0$3, + y0$3; + +var areaStream = { + point: noop$1, + lineStart: noop$1, + lineEnd: noop$1, + polygonStart: function() { + areaStream.lineStart = areaRingStart; + areaStream.lineEnd = areaRingEnd; + }, + polygonEnd: function() { + areaStream.lineStart = areaStream.lineEnd = areaStream.point = noop$1; + areaSum.add(abs$1(areaRingSum)); + areaRingSum = new Adder(); + }, + result: function() { + var area = areaSum / 2; + areaSum = new Adder(); + return area; + } +}; + +function areaRingStart() { + areaStream.point = areaPointFirst; +} + +function areaPointFirst(x, y) { + areaStream.point = areaPoint; + x00$2 = x0$3 = x, y00$2 = y0$3 = y; +} + +function areaPoint(x, y) { + areaRingSum.add(y0$3 * x - x0$3 * y); + x0$3 = x, y0$3 = y; +} + +function areaRingEnd() { + areaPoint(x00$2, y00$2); +} + +var pathArea = areaStream; + +var x0$2 = Infinity, + y0$2 = x0$2, + x1 = -x0$2, + y1 = x1; + +var boundsStream = { + point: boundsPoint, + lineStart: noop$1, + lineEnd: noop$1, + polygonStart: noop$1, + polygonEnd: noop$1, + result: function() { + var bounds = [[x0$2, y0$2], [x1, y1]]; + x1 = y1 = -(y0$2 = x0$2 = Infinity); + return bounds; + } +}; + +function boundsPoint(x, y) { + if (x < x0$2) x0$2 = x; + if (x > x1) x1 = x; + if (y < y0$2) y0$2 = y; + if (y > y1) y1 = y; +} + +var boundsStream$1 = boundsStream; + +// TODO Enforce positive area for exterior, negative area for interior? + +var X0 = 0, + Y0 = 0, + Z0 = 0, + X1 = 0, + Y1 = 0, + Z1 = 0, + X2 = 0, + Y2 = 0, + Z2 = 0, + x00$1, + y00$1, + x0$1, + y0$1; + +var centroidStream = { + point: centroidPoint, + lineStart: centroidLineStart, + lineEnd: centroidLineEnd, + polygonStart: function() { + centroidStream.lineStart = centroidRingStart; + centroidStream.lineEnd = centroidRingEnd; + }, + polygonEnd: function() { + centroidStream.point = centroidPoint; + centroidStream.lineStart = centroidLineStart; + centroidStream.lineEnd = centroidLineEnd; + }, + result: function() { + var centroid = Z2 ? [X2 / Z2, Y2 / Z2] + : Z1 ? [X1 / Z1, Y1 / Z1] + : Z0 ? [X0 / Z0, Y0 / Z0] + : [NaN, NaN]; + X0 = Y0 = Z0 = + X1 = Y1 = Z1 = + X2 = Y2 = Z2 = 0; + return centroid; + } +}; + +function centroidPoint(x, y) { + X0 += x; + Y0 += y; + ++Z0; +} + +function centroidLineStart() { + centroidStream.point = centroidPointFirstLine; +} + +function centroidPointFirstLine(x, y) { + centroidStream.point = centroidPointLine; + centroidPoint(x0$1 = x, y0$1 = y); +} + +function centroidPointLine(x, y) { + var dx = x - x0$1, dy = y - y0$1, z = sqrt$2(dx * dx + dy * dy); + X1 += z * (x0$1 + x) / 2; + Y1 += z * (y0$1 + y) / 2; + Z1 += z; + centroidPoint(x0$1 = x, y0$1 = y); +} + +function centroidLineEnd() { + centroidStream.point = centroidPoint; +} + +function centroidRingStart() { + centroidStream.point = centroidPointFirstRing; +} + +function centroidRingEnd() { + centroidPointRing(x00$1, y00$1); +} + +function centroidPointFirstRing(x, y) { + centroidStream.point = centroidPointRing; + centroidPoint(x00$1 = x0$1 = x, y00$1 = y0$1 = y); +} + +function centroidPointRing(x, y) { + var dx = x - x0$1, + dy = y - y0$1, + z = sqrt$2(dx * dx + dy * dy); + + X1 += z * (x0$1 + x) / 2; + Y1 += z * (y0$1 + y) / 2; + Z1 += z; + + z = y0$1 * x - x0$1 * y; + X2 += z * (x0$1 + x); + Y2 += z * (y0$1 + y); + Z2 += z * 3; + centroidPoint(x0$1 = x, y0$1 = y); +} + +var pathCentroid = centroidStream; + +function PathContext(context) { + this._context = context; +} + +PathContext.prototype = { + _radius: 4.5, + pointRadius: function(_) { + return this._radius = _, this; + }, + polygonStart: function() { + this._line = 0; + }, + polygonEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._point = 0; + }, + lineEnd: function() { + if (this._line === 0) this._context.closePath(); + this._point = NaN; + }, + point: function(x, y) { + switch (this._point) { + case 0: { + this._context.moveTo(x, y); + this._point = 1; + break; + } + case 1: { + this._context.lineTo(x, y); + break; + } + default: { + this._context.moveTo(x + this._radius, y); + this._context.arc(x, y, this._radius, 0, tau$1); + break; + } + } + }, + result: noop$1 +}; + +var lengthSum = new Adder(), + lengthRing, + x00, + y00, + x0, + y0; + +var lengthStream = { + point: noop$1, + lineStart: function() { + lengthStream.point = lengthPointFirst; + }, + lineEnd: function() { + if (lengthRing) lengthPoint(x00, y00); + lengthStream.point = noop$1; + }, + polygonStart: function() { + lengthRing = true; + }, + polygonEnd: function() { + lengthRing = null; + }, + result: function() { + var length = +lengthSum; + lengthSum = new Adder(); + return length; + } +}; + +function lengthPointFirst(x, y) { + lengthStream.point = lengthPoint; + x00 = x0 = x, y00 = y0 = y; +} + +function lengthPoint(x, y) { + x0 -= x, y0 -= y; + lengthSum.add(sqrt$2(x0 * x0 + y0 * y0)); + x0 = x, y0 = y; +} + +var pathMeasure = lengthStream; + +// Simple caching for constant-radius points. +let cacheDigits, cacheAppend, cacheRadius, cacheCircle; + +class PathString { + constructor(digits) { + this._append = digits == null ? append : appendRound(digits); + this._radius = 4.5; + this._ = ""; + } + pointRadius(_) { + this._radius = +_; + return this; + } + polygonStart() { + this._line = 0; + } + polygonEnd() { + this._line = NaN; + } + lineStart() { + this._point = 0; + } + lineEnd() { + if (this._line === 0) this._ += "Z"; + this._point = NaN; + } + point(x, y) { + switch (this._point) { + case 0: { + this._append`M${x},${y}`; + this._point = 1; + break; + } + case 1: { + this._append`L${x},${y}`; + break; + } + default: { + this._append`M${x},${y}`; + if (this._radius !== cacheRadius || this._append !== cacheAppend) { + const r = this._radius; + const s = this._; + this._ = ""; // stash the old string so we can cache the circle path fragment + this._append`m0,${r}a${r},${r} 0 1,1 0,${-2 * r}a${r},${r} 0 1,1 0,${2 * r}z`; + cacheRadius = r; + cacheAppend = this._append; + cacheCircle = this._; + this._ = s; + } + this._ += cacheCircle; + break; + } + } + } + result() { + const result = this._; + this._ = ""; + return result.length ? result : null; + } +} + +function append(strings) { + let i = 1; + this._ += strings[0]; + for (const j = strings.length; i < j; ++i) { + this._ += arguments[i] + strings[i]; + } +} + +function appendRound(digits) { + const d = Math.floor(digits); + if (!(d >= 0)) throw new RangeError(`invalid digits: ${digits}`); + if (d > 15) return append; + if (d !== cacheDigits) { + const k = 10 ** d; + cacheDigits = d; + cacheAppend = function append(strings) { + let i = 1; + this._ += strings[0]; + for (const j = strings.length; i < j; ++i) { + this._ += Math.round(arguments[i] * k) / k + strings[i]; + } + }; + } + return cacheAppend; +} + +function index$2(projection, context) { + let digits = 3, + pointRadius = 4.5, + projectionStream, + contextStream; + + function path(object) { + if (object) { + if (typeof pointRadius === "function") contextStream.pointRadius(+pointRadius.apply(this, arguments)); + geoStream(object, projectionStream(contextStream)); + } + return contextStream.result(); + } + + path.area = function(object) { + geoStream(object, projectionStream(pathArea)); + return pathArea.result(); + }; + + path.measure = function(object) { + geoStream(object, projectionStream(pathMeasure)); + return pathMeasure.result(); + }; + + path.bounds = function(object) { + geoStream(object, projectionStream(boundsStream$1)); + return boundsStream$1.result(); + }; + + path.centroid = function(object) { + geoStream(object, projectionStream(pathCentroid)); + return pathCentroid.result(); + }; + + path.projection = function(_) { + if (!arguments.length) return projection; + projectionStream = _ == null ? (projection = null, identity$5) : (projection = _).stream; + return path; + }; + + path.context = function(_) { + if (!arguments.length) return context; + contextStream = _ == null ? (context = null, new PathString(digits)) : new PathContext(context = _); + if (typeof pointRadius !== "function") contextStream.pointRadius(pointRadius); + return path; + }; + + path.pointRadius = function(_) { + if (!arguments.length) return pointRadius; + pointRadius = typeof _ === "function" ? _ : (contextStream.pointRadius(+_), +_); + return path; + }; + + path.digits = function(_) { + if (!arguments.length) return digits; + if (_ == null) digits = null; + else { + const d = Math.floor(_); + if (!(d >= 0)) throw new RangeError(`invalid digits: ${_}`); + digits = d; + } + if (context === null) contextStream = new PathString(digits); + return path; + }; + + return path.projection(projection).digits(digits).context(context); +} + +function transform$1(methods) { + return { + stream: transformer$3(methods) + }; +} + +function transformer$3(methods) { + return function(stream) { + var s = new TransformStream; + for (var key in methods) s[key] = methods[key]; + s.stream = stream; + return s; + }; +} + +function TransformStream() {} + +TransformStream.prototype = { + constructor: TransformStream, + point: function(x, y) { this.stream.point(x, y); }, + sphere: function() { this.stream.sphere(); }, + lineStart: function() { this.stream.lineStart(); }, + lineEnd: function() { this.stream.lineEnd(); }, + polygonStart: function() { this.stream.polygonStart(); }, + polygonEnd: function() { this.stream.polygonEnd(); } +}; + +function fit(projection, fitBounds, object) { + var clip = projection.clipExtent && projection.clipExtent(); + projection.scale(150).translate([0, 0]); + if (clip != null) projection.clipExtent(null); + geoStream(object, projection.stream(boundsStream$1)); + fitBounds(boundsStream$1.result()); + if (clip != null) projection.clipExtent(clip); + return projection; +} + +function fitExtent(projection, extent, object) { + return fit(projection, function(b) { + var w = extent[1][0] - extent[0][0], + h = extent[1][1] - extent[0][1], + k = Math.min(w / (b[1][0] - b[0][0]), h / (b[1][1] - b[0][1])), + x = +extent[0][0] + (w - k * (b[1][0] + b[0][0])) / 2, + y = +extent[0][1] + (h - k * (b[1][1] + b[0][1])) / 2; + projection.scale(150 * k).translate([x, y]); + }, object); +} + +function fitSize(projection, size, object) { + return fitExtent(projection, [[0, 0], size], object); +} + +function fitWidth(projection, width, object) { + return fit(projection, function(b) { + var w = +width, + k = w / (b[1][0] - b[0][0]), + x = (w - k * (b[1][0] + b[0][0])) / 2, + y = -k * b[0][1]; + projection.scale(150 * k).translate([x, y]); + }, object); +} + +function fitHeight(projection, height, object) { + return fit(projection, function(b) { + var h = +height, + k = h / (b[1][1] - b[0][1]), + x = -k * b[0][0], + y = (h - k * (b[1][1] + b[0][1])) / 2; + projection.scale(150 * k).translate([x, y]); + }, object); +} + +var maxDepth = 16, // maximum depth of subdivision + cosMinDistance = cos$1(30 * radians); // cos(minimum angular distance) + +function resample(project, delta2) { + return +delta2 ? resample$1(project, delta2) : resampleNone(project); +} + +function resampleNone(project) { + return transformer$3({ + point: function(x, y) { + x = project(x, y); + this.stream.point(x[0], x[1]); + } + }); +} + +function resample$1(project, delta2) { + + function resampleLineTo(x0, y0, lambda0, a0, b0, c0, x1, y1, lambda1, a1, b1, c1, depth, stream) { + var dx = x1 - x0, + dy = y1 - y0, + d2 = dx * dx + dy * dy; + if (d2 > 4 * delta2 && depth--) { + var a = a0 + a1, + b = b0 + b1, + c = c0 + c1, + m = sqrt$2(a * a + b * b + c * c), + phi2 = asin$1(c /= m), + lambda2 = abs$1(abs$1(c) - 1) < epsilon$1 || abs$1(lambda0 - lambda1) < epsilon$1 ? (lambda0 + lambda1) / 2 : atan2$1(b, a), + p = project(lambda2, phi2), + x2 = p[0], + y2 = p[1], + dx2 = x2 - x0, + dy2 = y2 - y0, + dz = dy * dx2 - dx * dy2; + if (dz * dz / d2 > delta2 // perpendicular projected distance + || abs$1((dx * dx2 + dy * dy2) / d2 - 0.5) > 0.3 // midpoint close to an end + || a0 * a1 + b0 * b1 + c0 * c1 < cosMinDistance) { // angular distance + resampleLineTo(x0, y0, lambda0, a0, b0, c0, x2, y2, lambda2, a /= m, b /= m, c, depth, stream); + stream.point(x2, y2); + resampleLineTo(x2, y2, lambda2, a, b, c, x1, y1, lambda1, a1, b1, c1, depth, stream); + } + } + } + return function(stream) { + var lambda00, x00, y00, a00, b00, c00, // first point + lambda0, x0, y0, a0, b0, c0; // previous point + + var resampleStream = { + point: point, + lineStart: lineStart, + lineEnd: lineEnd, + polygonStart: function() { stream.polygonStart(); resampleStream.lineStart = ringStart; }, + polygonEnd: function() { stream.polygonEnd(); resampleStream.lineStart = lineStart; } + }; + + function point(x, y) { + x = project(x, y); + stream.point(x[0], x[1]); + } + + function lineStart() { + x0 = NaN; + resampleStream.point = linePoint; + stream.lineStart(); + } + + function linePoint(lambda, phi) { + var c = cartesian([lambda, phi]), p = project(lambda, phi); + resampleLineTo(x0, y0, lambda0, a0, b0, c0, x0 = p[0], y0 = p[1], lambda0 = lambda, a0 = c[0], b0 = c[1], c0 = c[2], maxDepth, stream); + stream.point(x0, y0); + } + + function lineEnd() { + resampleStream.point = point; + stream.lineEnd(); + } + + function ringStart() { + lineStart(); + resampleStream.point = ringPoint; + resampleStream.lineEnd = ringEnd; + } + + function ringPoint(lambda, phi) { + linePoint(lambda00 = lambda, phi), x00 = x0, y00 = y0, a00 = a0, b00 = b0, c00 = c0; + resampleStream.point = linePoint; + } + + function ringEnd() { + resampleLineTo(x0, y0, lambda0, a0, b0, c0, x00, y00, lambda00, a00, b00, c00, maxDepth, stream); + resampleStream.lineEnd = lineEnd; + lineEnd(); + } + + return resampleStream; + }; +} + +var transformRadians = transformer$3({ + point: function(x, y) { + this.stream.point(x * radians, y * radians); + } +}); + +function transformRotate(rotate) { + return transformer$3({ + point: function(x, y) { + var r = rotate(x, y); + return this.stream.point(r[0], r[1]); + } + }); +} + +function scaleTranslate(k, dx, dy, sx, sy) { + function transform(x, y) { + x *= sx; y *= sy; + return [dx + k * x, dy - k * y]; + } + transform.invert = function(x, y) { + return [(x - dx) / k * sx, (dy - y) / k * sy]; + }; + return transform; +} + +function scaleTranslateRotate(k, dx, dy, sx, sy, alpha) { + if (!alpha) return scaleTranslate(k, dx, dy, sx, sy); + var cosAlpha = cos$1(alpha), + sinAlpha = sin$1(alpha), + a = cosAlpha * k, + b = sinAlpha * k, + ai = cosAlpha / k, + bi = sinAlpha / k, + ci = (sinAlpha * dy - cosAlpha * dx) / k, + fi = (sinAlpha * dx + cosAlpha * dy) / k; + function transform(x, y) { + x *= sx; y *= sy; + return [a * x - b * y + dx, dy - b * x - a * y]; + } + transform.invert = function(x, y) { + return [sx * (ai * x - bi * y + ci), sy * (fi - bi * x - ai * y)]; + }; + return transform; +} + +function projection(project) { + return projectionMutator(function() { return project; })(); +} + +function projectionMutator(projectAt) { + var project, + k = 150, // scale + x = 480, y = 250, // translate + lambda = 0, phi = 0, // center + deltaLambda = 0, deltaPhi = 0, deltaGamma = 0, rotate, // pre-rotate + alpha = 0, // post-rotate angle + sx = 1, // reflectX + sy = 1, // reflectX + theta = null, preclip = clipAntimeridian, // pre-clip angle + x0 = null, y0, x1, y1, postclip = identity$5, // post-clip extent + delta2 = 0.5, // precision + projectResample, + projectTransform, + projectRotateTransform, + cache, + cacheStream; + + function projection(point) { + return projectRotateTransform(point[0] * radians, point[1] * radians); + } + + function invert(point) { + point = projectRotateTransform.invert(point[0], point[1]); + return point && [point[0] * degrees, point[1] * degrees]; + } + + projection.stream = function(stream) { + return cache && cacheStream === stream ? cache : cache = transformRadians(transformRotate(rotate)(preclip(projectResample(postclip(cacheStream = stream))))); + }; + + projection.preclip = function(_) { + return arguments.length ? (preclip = _, theta = undefined, reset()) : preclip; + }; + + projection.postclip = function(_) { + return arguments.length ? (postclip = _, x0 = y0 = x1 = y1 = null, reset()) : postclip; + }; + + projection.clipAngle = function(_) { + return arguments.length ? (preclip = +_ ? clipCircle(theta = _ * radians) : (theta = null, clipAntimeridian), reset()) : theta * degrees; + }; + + projection.clipExtent = function(_) { + return arguments.length ? (postclip = _ == null ? (x0 = y0 = x1 = y1 = null, identity$5) : clipRectangle(x0 = +_[0][0], y0 = +_[0][1], x1 = +_[1][0], y1 = +_[1][1]), reset()) : x0 == null ? null : [[x0, y0], [x1, y1]]; + }; + + projection.scale = function(_) { + return arguments.length ? (k = +_, recenter()) : k; + }; + + projection.translate = function(_) { + return arguments.length ? (x = +_[0], y = +_[1], recenter()) : [x, y]; + }; + + projection.center = function(_) { + return arguments.length ? (lambda = _[0] % 360 * radians, phi = _[1] % 360 * radians, recenter()) : [lambda * degrees, phi * degrees]; + }; + + projection.rotate = function(_) { + return arguments.length ? (deltaLambda = _[0] % 360 * radians, deltaPhi = _[1] % 360 * radians, deltaGamma = _.length > 2 ? _[2] % 360 * radians : 0, recenter()) : [deltaLambda * degrees, deltaPhi * degrees, deltaGamma * degrees]; + }; + + projection.angle = function(_) { + return arguments.length ? (alpha = _ % 360 * radians, recenter()) : alpha * degrees; + }; + + projection.reflectX = function(_) { + return arguments.length ? (sx = _ ? -1 : 1, recenter()) : sx < 0; + }; + + projection.reflectY = function(_) { + return arguments.length ? (sy = _ ? -1 : 1, recenter()) : sy < 0; + }; + + projection.precision = function(_) { + return arguments.length ? (projectResample = resample(projectTransform, delta2 = _ * _), reset()) : sqrt$2(delta2); + }; + + projection.fitExtent = function(extent, object) { + return fitExtent(projection, extent, object); + }; + + projection.fitSize = function(size, object) { + return fitSize(projection, size, object); + }; + + projection.fitWidth = function(width, object) { + return fitWidth(projection, width, object); + }; + + projection.fitHeight = function(height, object) { + return fitHeight(projection, height, object); + }; + + function recenter() { + var center = scaleTranslateRotate(k, 0, 0, sx, sy, alpha).apply(null, project(lambda, phi)), + transform = scaleTranslateRotate(k, x - center[0], y - center[1], sx, sy, alpha); + rotate = rotateRadians(deltaLambda, deltaPhi, deltaGamma); + projectTransform = compose(project, transform); + projectRotateTransform = compose(rotate, projectTransform); + projectResample = resample(projectTransform, delta2); + return reset(); + } + + function reset() { + cache = cacheStream = null; + return projection; + } + + return function() { + project = projectAt.apply(this, arguments); + projection.invert = project.invert && invert; + return recenter(); + }; +} + +function conicProjection(projectAt) { + var phi0 = 0, + phi1 = pi$1 / 3, + m = projectionMutator(projectAt), + p = m(phi0, phi1); + + p.parallels = function(_) { + return arguments.length ? m(phi0 = _[0] * radians, phi1 = _[1] * radians) : [phi0 * degrees, phi1 * degrees]; + }; + + return p; +} + +function cylindricalEqualAreaRaw(phi0) { + var cosPhi0 = cos$1(phi0); + + function forward(lambda, phi) { + return [lambda * cosPhi0, sin$1(phi) / cosPhi0]; + } + + forward.invert = function(x, y) { + return [x / cosPhi0, asin$1(y * cosPhi0)]; + }; + + return forward; +} + +function conicEqualAreaRaw(y0, y1) { + var sy0 = sin$1(y0), n = (sy0 + sin$1(y1)) / 2; + + // Are the parallels symmetrical around the Equator? + if (abs$1(n) < epsilon$1) return cylindricalEqualAreaRaw(y0); + + var c = 1 + sy0 * (2 * n - sy0), r0 = sqrt$2(c) / n; + + function project(x, y) { + var r = sqrt$2(c - 2 * n * sin$1(y)) / n; + return [r * sin$1(x *= n), r0 - r * cos$1(x)]; + } + + project.invert = function(x, y) { + var r0y = r0 - y, + l = atan2$1(x, abs$1(r0y)) * sign$1(r0y); + if (r0y * n < 0) + l -= pi$1 * sign$1(x) * sign$1(r0y); + return [l / n, asin$1((c - (x * x + r0y * r0y) * n * n) / (2 * n))]; + }; + + return project; +} + +function conicEqualArea() { + return conicProjection(conicEqualAreaRaw) + .scale(155.424) + .center([0, 33.6442]); +} + +function albers() { + return conicEqualArea() + .parallels([29.5, 45.5]) + .scale(1070) + .translate([480, 250]) + .rotate([96, 0]) + .center([-0.6, 38.7]); +} + +// The projections must have mutually exclusive clip regions on the sphere, +// as this will avoid emitting interleaving lines and polygons. +function multiplex(streams) { + var n = streams.length; + return { + point: function(x, y) { var i = -1; while (++i < n) streams[i].point(x, y); }, + sphere: function() { var i = -1; while (++i < n) streams[i].sphere(); }, + lineStart: function() { var i = -1; while (++i < n) streams[i].lineStart(); }, + lineEnd: function() { var i = -1; while (++i < n) streams[i].lineEnd(); }, + polygonStart: function() { var i = -1; while (++i < n) streams[i].polygonStart(); }, + polygonEnd: function() { var i = -1; while (++i < n) streams[i].polygonEnd(); } + }; +} + +// A composite projection for the United States, configured by default for +// 960×500. The projection also works quite well at 960×600 if you change the +// scale to 1285 and adjust the translate accordingly. The set of standard +// parallels for each region comes from USGS, which is published here: +// http://egsc.usgs.gov/isb/pubs/MapProjections/projections.html#albers +function albersUsa() { + var cache, + cacheStream, + lower48 = albers(), lower48Point, + alaska = conicEqualArea().rotate([154, 0]).center([-2, 58.5]).parallels([55, 65]), alaskaPoint, // EPSG:3338 + hawaii = conicEqualArea().rotate([157, 0]).center([-3, 19.9]).parallels([8, 18]), hawaiiPoint, // ESRI:102007 + point, pointStream = {point: function(x, y) { point = [x, y]; }}; + + function albersUsa(coordinates) { + var x = coordinates[0], y = coordinates[1]; + return point = null, + (lower48Point.point(x, y), point) + || (alaskaPoint.point(x, y), point) + || (hawaiiPoint.point(x, y), point); + } + + albersUsa.invert = function(coordinates) { + var k = lower48.scale(), + t = lower48.translate(), + x = (coordinates[0] - t[0]) / k, + y = (coordinates[1] - t[1]) / k; + return (y >= 0.120 && y < 0.234 && x >= -0.425 && x < -0.214 ? alaska + : y >= 0.166 && y < 0.234 && x >= -0.214 && x < -0.115 ? hawaii + : lower48).invert(coordinates); + }; + + albersUsa.stream = function(stream) { + return cache && cacheStream === stream ? cache : cache = multiplex([lower48.stream(cacheStream = stream), alaska.stream(stream), hawaii.stream(stream)]); + }; + + albersUsa.precision = function(_) { + if (!arguments.length) return lower48.precision(); + lower48.precision(_), alaska.precision(_), hawaii.precision(_); + return reset(); + }; + + albersUsa.scale = function(_) { + if (!arguments.length) return lower48.scale(); + lower48.scale(_), alaska.scale(_ * 0.35), hawaii.scale(_); + return albersUsa.translate(lower48.translate()); + }; + + albersUsa.translate = function(_) { + if (!arguments.length) return lower48.translate(); + var k = lower48.scale(), x = +_[0], y = +_[1]; + + lower48Point = lower48 + .translate(_) + .clipExtent([[x - 0.455 * k, y - 0.238 * k], [x + 0.455 * k, y + 0.238 * k]]) + .stream(pointStream); + + alaskaPoint = alaska + .translate([x - 0.307 * k, y + 0.201 * k]) + .clipExtent([[x - 0.425 * k + epsilon$1, y + 0.120 * k + epsilon$1], [x - 0.214 * k - epsilon$1, y + 0.234 * k - epsilon$1]]) + .stream(pointStream); + + hawaiiPoint = hawaii + .translate([x - 0.205 * k, y + 0.212 * k]) + .clipExtent([[x - 0.214 * k + epsilon$1, y + 0.166 * k + epsilon$1], [x - 0.115 * k - epsilon$1, y + 0.234 * k - epsilon$1]]) + .stream(pointStream); + + return reset(); + }; + + albersUsa.fitExtent = function(extent, object) { + return fitExtent(albersUsa, extent, object); + }; + + albersUsa.fitSize = function(size, object) { + return fitSize(albersUsa, size, object); + }; + + albersUsa.fitWidth = function(width, object) { + return fitWidth(albersUsa, width, object); + }; + + albersUsa.fitHeight = function(height, object) { + return fitHeight(albersUsa, height, object); + }; + + function reset() { + cache = cacheStream = null; + return albersUsa; + } + + return albersUsa.scale(1070); +} + +function azimuthalRaw(scale) { + return function(x, y) { + var cx = cos$1(x), + cy = cos$1(y), + k = scale(cx * cy); + if (k === Infinity) return [2, 0]; + return [ + k * cy * sin$1(x), + k * sin$1(y) + ]; + } +} + +function azimuthalInvert(angle) { + return function(x, y) { + var z = sqrt$2(x * x + y * y), + c = angle(z), + sc = sin$1(c), + cc = cos$1(c); + return [ + atan2$1(x * sc, z * cc), + asin$1(z && y * sc / z) + ]; + } +} + +var azimuthalEqualAreaRaw = azimuthalRaw(function(cxcy) { + return sqrt$2(2 / (1 + cxcy)); +}); + +azimuthalEqualAreaRaw.invert = azimuthalInvert(function(z) { + return 2 * asin$1(z / 2); +}); + +function azimuthalEqualArea() { + return projection(azimuthalEqualAreaRaw) + .scale(124.75) + .clipAngle(180 - 1e-3); +} + +var azimuthalEquidistantRaw = azimuthalRaw(function(c) { + return (c = acos$1(c)) && c / sin$1(c); +}); + +azimuthalEquidistantRaw.invert = azimuthalInvert(function(z) { + return z; +}); + +function azimuthalEquidistant() { + return projection(azimuthalEquidistantRaw) + .scale(79.4188) + .clipAngle(180 - 1e-3); +} + +function mercatorRaw(lambda, phi) { + return [lambda, log$1(tan((halfPi$1 + phi) / 2))]; +} + +mercatorRaw.invert = function(x, y) { + return [x, 2 * atan(exp(y)) - halfPi$1]; +}; + +function mercator() { + return mercatorProjection(mercatorRaw) + .scale(961 / tau$1); +} + +function mercatorProjection(project) { + var m = projection(project), + center = m.center, + scale = m.scale, + translate = m.translate, + clipExtent = m.clipExtent, + x0 = null, y0, x1, y1; // clip extent + + m.scale = function(_) { + return arguments.length ? (scale(_), reclip()) : scale(); + }; + + m.translate = function(_) { + return arguments.length ? (translate(_), reclip()) : translate(); + }; + + m.center = function(_) { + return arguments.length ? (center(_), reclip()) : center(); + }; + + m.clipExtent = function(_) { + return arguments.length ? ((_ == null ? x0 = y0 = x1 = y1 = null : (x0 = +_[0][0], y0 = +_[0][1], x1 = +_[1][0], y1 = +_[1][1])), reclip()) : x0 == null ? null : [[x0, y0], [x1, y1]]; + }; + + function reclip() { + var k = pi$1 * scale(), + t = m(rotation(m.rotate()).invert([0, 0])); + return clipExtent(x0 == null + ? [[t[0] - k, t[1] - k], [t[0] + k, t[1] + k]] : project === mercatorRaw + ? [[Math.max(t[0] - k, x0), y0], [Math.min(t[0] + k, x1), y1]] + : [[x0, Math.max(t[1] - k, y0)], [x1, Math.min(t[1] + k, y1)]]); + } + + return reclip(); +} + +function tany(y) { + return tan((halfPi$1 + y) / 2); +} + +function conicConformalRaw(y0, y1) { + var cy0 = cos$1(y0), + n = y0 === y1 ? sin$1(y0) : log$1(cy0 / cos$1(y1)) / log$1(tany(y1) / tany(y0)), + f = cy0 * pow$1(tany(y0), n) / n; + + if (!n) return mercatorRaw; + + function project(x, y) { + if (f > 0) { if (y < -halfPi$1 + epsilon$1) y = -halfPi$1 + epsilon$1; } + else { if (y > halfPi$1 - epsilon$1) y = halfPi$1 - epsilon$1; } + var r = f / pow$1(tany(y), n); + return [r * sin$1(n * x), f - r * cos$1(n * x)]; + } + + project.invert = function(x, y) { + var fy = f - y, r = sign$1(n) * sqrt$2(x * x + fy * fy), + l = atan2$1(x, abs$1(fy)) * sign$1(fy); + if (fy * n < 0) + l -= pi$1 * sign$1(x) * sign$1(fy); + return [l / n, 2 * atan(pow$1(f / r, 1 / n)) - halfPi$1]; + }; + + return project; +} + +function conicConformal() { + return conicProjection(conicConformalRaw) + .scale(109.5) + .parallels([30, 30]); +} + +function equirectangularRaw(lambda, phi) { + return [lambda, phi]; +} + +equirectangularRaw.invert = equirectangularRaw; + +function equirectangular() { + return projection(equirectangularRaw) + .scale(152.63); +} + +function conicEquidistantRaw(y0, y1) { + var cy0 = cos$1(y0), + n = y0 === y1 ? sin$1(y0) : (cy0 - cos$1(y1)) / (y1 - y0), + g = cy0 / n + y0; + + if (abs$1(n) < epsilon$1) return equirectangularRaw; + + function project(x, y) { + var gy = g - y, nx = n * x; + return [gy * sin$1(nx), g - gy * cos$1(nx)]; + } + + project.invert = function(x, y) { + var gy = g - y, + l = atan2$1(x, abs$1(gy)) * sign$1(gy); + if (gy * n < 0) + l -= pi$1 * sign$1(x) * sign$1(gy); + return [l / n, g - sign$1(n) * sqrt$2(x * x + gy * gy)]; + }; + + return project; +} + +function conicEquidistant() { + return conicProjection(conicEquidistantRaw) + .scale(131.154) + .center([0, 13.9389]); +} + +var A1 = 1.340264, + A2 = -0.081106, + A3 = 0.000893, + A4 = 0.003796, + M = sqrt$2(3) / 2, + iterations = 12; + +function equalEarthRaw(lambda, phi) { + var l = asin$1(M * sin$1(phi)), l2 = l * l, l6 = l2 * l2 * l2; + return [ + lambda * cos$1(l) / (M * (A1 + 3 * A2 * l2 + l6 * (7 * A3 + 9 * A4 * l2))), + l * (A1 + A2 * l2 + l6 * (A3 + A4 * l2)) + ]; +} + +equalEarthRaw.invert = function(x, y) { + var l = y, l2 = l * l, l6 = l2 * l2 * l2; + for (var i = 0, delta, fy, fpy; i < iterations; ++i) { + fy = l * (A1 + A2 * l2 + l6 * (A3 + A4 * l2)) - y; + fpy = A1 + 3 * A2 * l2 + l6 * (7 * A3 + 9 * A4 * l2); + l -= delta = fy / fpy, l2 = l * l, l6 = l2 * l2 * l2; + if (abs$1(delta) < epsilon2) break; + } + return [ + M * x * (A1 + 3 * A2 * l2 + l6 * (7 * A3 + 9 * A4 * l2)) / cos$1(l), + asin$1(sin$1(l) / M) + ]; +}; + +function equalEarth() { + return projection(equalEarthRaw) + .scale(177.158); +} + +function gnomonicRaw(x, y) { + var cy = cos$1(y), k = cos$1(x) * cy; + return [cy * sin$1(x) / k, sin$1(y) / k]; +} + +gnomonicRaw.invert = azimuthalInvert(atan); + +function gnomonic() { + return projection(gnomonicRaw) + .scale(144.049) + .clipAngle(60); +} + +function identity$4() { + var k = 1, tx = 0, ty = 0, sx = 1, sy = 1, // scale, translate and reflect + alpha = 0, ca, sa, // angle + x0 = null, y0, x1, y1, // clip extent + kx = 1, ky = 1, + transform = transformer$3({ + point: function(x, y) { + var p = projection([x, y]); + this.stream.point(p[0], p[1]); + } + }), + postclip = identity$5, + cache, + cacheStream; + + function reset() { + kx = k * sx; + ky = k * sy; + cache = cacheStream = null; + return projection; + } + + function projection (p) { + var x = p[0] * kx, y = p[1] * ky; + if (alpha) { + var t = y * ca - x * sa; + x = x * ca + y * sa; + y = t; + } + return [x + tx, y + ty]; + } + projection.invert = function(p) { + var x = p[0] - tx, y = p[1] - ty; + if (alpha) { + var t = y * ca + x * sa; + x = x * ca - y * sa; + y = t; + } + return [x / kx, y / ky]; + }; + projection.stream = function(stream) { + return cache && cacheStream === stream ? cache : cache = transform(postclip(cacheStream = stream)); + }; + projection.postclip = function(_) { + return arguments.length ? (postclip = _, x0 = y0 = x1 = y1 = null, reset()) : postclip; + }; + projection.clipExtent = function(_) { + return arguments.length ? (postclip = _ == null ? (x0 = y0 = x1 = y1 = null, identity$5) : clipRectangle(x0 = +_[0][0], y0 = +_[0][1], x1 = +_[1][0], y1 = +_[1][1]), reset()) : x0 == null ? null : [[x0, y0], [x1, y1]]; + }; + projection.scale = function(_) { + return arguments.length ? (k = +_, reset()) : k; + }; + projection.translate = function(_) { + return arguments.length ? (tx = +_[0], ty = +_[1], reset()) : [tx, ty]; + }; + projection.angle = function(_) { + return arguments.length ? (alpha = _ % 360 * radians, sa = sin$1(alpha), ca = cos$1(alpha), reset()) : alpha * degrees; + }; + projection.reflectX = function(_) { + return arguments.length ? (sx = _ ? -1 : 1, reset()) : sx < 0; + }; + projection.reflectY = function(_) { + return arguments.length ? (sy = _ ? -1 : 1, reset()) : sy < 0; + }; + projection.fitExtent = function(extent, object) { + return fitExtent(projection, extent, object); + }; + projection.fitSize = function(size, object) { + return fitSize(projection, size, object); + }; + projection.fitWidth = function(width, object) { + return fitWidth(projection, width, object); + }; + projection.fitHeight = function(height, object) { + return fitHeight(projection, height, object); + }; + + return projection; +} + +function naturalEarth1Raw(lambda, phi) { + var phi2 = phi * phi, phi4 = phi2 * phi2; + return [ + lambda * (0.8707 - 0.131979 * phi2 + phi4 * (-0.013791 + phi4 * (0.003971 * phi2 - 0.001529 * phi4))), + phi * (1.007226 + phi2 * (0.015085 + phi4 * (-0.044475 + 0.028874 * phi2 - 0.005916 * phi4))) + ]; +} + +naturalEarth1Raw.invert = function(x, y) { + var phi = y, i = 25, delta; + do { + var phi2 = phi * phi, phi4 = phi2 * phi2; + phi -= delta = (phi * (1.007226 + phi2 * (0.015085 + phi4 * (-0.044475 + 0.028874 * phi2 - 0.005916 * phi4))) - y) / + (1.007226 + phi2 * (0.015085 * 3 + phi4 * (-0.044475 * 7 + 0.028874 * 9 * phi2 - 0.005916 * 11 * phi4))); + } while (abs$1(delta) > epsilon$1 && --i > 0); + return [ + x / (0.8707 + (phi2 = phi * phi) * (-0.131979 + phi2 * (-0.013791 + phi2 * phi2 * phi2 * (0.003971 - 0.001529 * phi2)))), + phi + ]; +}; + +function naturalEarth1() { + return projection(naturalEarth1Raw) + .scale(175.295); +} + +function orthographicRaw(x, y) { + return [cos$1(y) * sin$1(x), sin$1(y)]; +} + +orthographicRaw.invert = azimuthalInvert(asin$1); + +function orthographic() { + return projection(orthographicRaw) + .scale(249.5) + .clipAngle(90 + epsilon$1); +} + +function stereographicRaw(x, y) { + var cy = cos$1(y), k = 1 + cos$1(x) * cy; + return [cy * sin$1(x) / k, sin$1(y) / k]; +} + +stereographicRaw.invert = azimuthalInvert(function(z) { + return 2 * atan(z); +}); + +function stereographic() { + return projection(stereographicRaw) + .scale(250) + .clipAngle(142); +} + +function transverseMercatorRaw(lambda, phi) { + return [log$1(tan((halfPi$1 + phi) / 2)), -lambda]; +} + +transverseMercatorRaw.invert = function(x, y) { + return [-y, 2 * atan(exp(x)) - halfPi$1]; +}; + +function transverseMercator() { + var m = mercatorProjection(transverseMercatorRaw), + center = m.center, + rotate = m.rotate; + + m.center = function(_) { + return arguments.length ? center([-_[1], _[0]]) : (_ = center(), [_[1], -_[0]]); + }; + + m.rotate = function(_) { + return arguments.length ? rotate([_[0], _[1], _.length > 2 ? _[2] + 90 : 90]) : (_ = rotate(), [_[0], _[1], _[2] - 90]); + }; + + return rotate([0, 0, 90]) + .scale(159.155); +} + +function defaultSeparation$1(a, b) { + return a.parent === b.parent ? 1 : 2; +} + +function meanX(children) { + return children.reduce(meanXReduce, 0) / children.length; +} + +function meanXReduce(x, c) { + return x + c.x; +} + +function maxY(children) { + return 1 + children.reduce(maxYReduce, 0); +} + +function maxYReduce(y, c) { + return Math.max(y, c.y); +} + +function leafLeft(node) { + var children; + while (children = node.children) node = children[0]; + return node; +} + +function leafRight(node) { + var children; + while (children = node.children) node = children[children.length - 1]; + return node; +} + +function cluster() { + var separation = defaultSeparation$1, + dx = 1, + dy = 1, + nodeSize = false; + + function cluster(root) { + var previousNode, + x = 0; + + // First walk, computing the initial x & y values. + root.eachAfter(function(node) { + var children = node.children; + if (children) { + node.x = meanX(children); + node.y = maxY(children); + } else { + node.x = previousNode ? x += separation(node, previousNode) : 0; + node.y = 0; + previousNode = node; + } + }); + + var left = leafLeft(root), + right = leafRight(root), + x0 = left.x - separation(left, right) / 2, + x1 = right.x + separation(right, left) / 2; + + // Second walk, normalizing x & y to the desired size. + return root.eachAfter(nodeSize ? function(node) { + node.x = (node.x - root.x) * dx; + node.y = (root.y - node.y) * dy; + } : function(node) { + node.x = (node.x - x0) / (x1 - x0) * dx; + node.y = (1 - (root.y ? node.y / root.y : 1)) * dy; + }); + } + + cluster.separation = function(x) { + return arguments.length ? (separation = x, cluster) : separation; + }; + + cluster.size = function(x) { + return arguments.length ? (nodeSize = false, dx = +x[0], dy = +x[1], cluster) : (nodeSize ? null : [dx, dy]); + }; + + cluster.nodeSize = function(x) { + return arguments.length ? (nodeSize = true, dx = +x[0], dy = +x[1], cluster) : (nodeSize ? [dx, dy] : null); + }; + + return cluster; +} + +function count(node) { + var sum = 0, + children = node.children, + i = children && children.length; + if (!i) sum = 1; + else while (--i >= 0) sum += children[i].value; + node.value = sum; +} + +function node_count() { + return this.eachAfter(count); +} + +function node_each(callback, that) { + let index = -1; + for (const node of this) { + callback.call(that, node, ++index, this); + } + return this; +} + +function node_eachBefore(callback, that) { + var node = this, nodes = [node], children, i, index = -1; + while (node = nodes.pop()) { + callback.call(that, node, ++index, this); + if (children = node.children) { + for (i = children.length - 1; i >= 0; --i) { + nodes.push(children[i]); + } + } + } + return this; +} + +function node_eachAfter(callback, that) { + var node = this, nodes = [node], next = [], children, i, n, index = -1; + while (node = nodes.pop()) { + next.push(node); + if (children = node.children) { + for (i = 0, n = children.length; i < n; ++i) { + nodes.push(children[i]); + } + } + } + while (node = next.pop()) { + callback.call(that, node, ++index, this); + } + return this; +} + +function node_find(callback, that) { + let index = -1; + for (const node of this) { + if (callback.call(that, node, ++index, this)) { + return node; + } + } +} + +function node_sum(value) { + return this.eachAfter(function(node) { + var sum = +value(node.data) || 0, + children = node.children, + i = children && children.length; + while (--i >= 0) sum += children[i].value; + node.value = sum; + }); +} + +function node_sort(compare) { + return this.eachBefore(function(node) { + if (node.children) { + node.children.sort(compare); + } + }); +} + +function node_path(end) { + var start = this, + ancestor = leastCommonAncestor(start, end), + nodes = [start]; + while (start !== ancestor) { + start = start.parent; + nodes.push(start); + } + var k = nodes.length; + while (end !== ancestor) { + nodes.splice(k, 0, end); + end = end.parent; + } + return nodes; +} + +function leastCommonAncestor(a, b) { + if (a === b) return a; + var aNodes = a.ancestors(), + bNodes = b.ancestors(), + c = null; + a = aNodes.pop(); + b = bNodes.pop(); + while (a === b) { + c = a; + a = aNodes.pop(); + b = bNodes.pop(); + } + return c; +} + +function node_ancestors() { + var node = this, nodes = [node]; + while (node = node.parent) { + nodes.push(node); + } + return nodes; +} + +function node_descendants() { + return Array.from(this); +} + +function node_leaves() { + var leaves = []; + this.eachBefore(function(node) { + if (!node.children) { + leaves.push(node); + } + }); + return leaves; +} + +function node_links() { + var root = this, links = []; + root.each(function(node) { + if (node !== root) { // Don’t include the root’s parent, if any. + links.push({source: node.parent, target: node}); + } + }); + return links; +} + +function* node_iterator() { + var node = this, current, next = [node], children, i, n; + do { + current = next.reverse(), next = []; + while (node = current.pop()) { + yield node; + if (children = node.children) { + for (i = 0, n = children.length; i < n; ++i) { + next.push(children[i]); + } + } + } + } while (next.length); +} + +function hierarchy(data, children) { + if (data instanceof Map) { + data = [undefined, data]; + if (children === undefined) children = mapChildren; + } else if (children === undefined) { + children = objectChildren; + } + + var root = new Node$1(data), + node, + nodes = [root], + child, + childs, + i, + n; + + while (node = nodes.pop()) { + if ((childs = children(node.data)) && (n = (childs = Array.from(childs)).length)) { + node.children = childs; + for (i = n - 1; i >= 0; --i) { + nodes.push(child = childs[i] = new Node$1(childs[i])); + child.parent = node; + child.depth = node.depth + 1; + } + } + } + + return root.eachBefore(computeHeight); +} + +function node_copy() { + return hierarchy(this).eachBefore(copyData); +} + +function objectChildren(d) { + return d.children; +} + +function mapChildren(d) { + return Array.isArray(d) ? d[1] : null; +} + +function copyData(node) { + if (node.data.value !== undefined) node.value = node.data.value; + node.data = node.data.data; +} + +function computeHeight(node) { + var height = 0; + do node.height = height; + while ((node = node.parent) && (node.height < ++height)); +} + +function Node$1(data) { + this.data = data; + this.depth = + this.height = 0; + this.parent = null; +} + +Node$1.prototype = hierarchy.prototype = { + constructor: Node$1, + count: node_count, + each: node_each, + eachAfter: node_eachAfter, + eachBefore: node_eachBefore, + find: node_find, + sum: node_sum, + sort: node_sort, + path: node_path, + ancestors: node_ancestors, + descendants: node_descendants, + leaves: node_leaves, + links: node_links, + copy: node_copy, + [Symbol.iterator]: node_iterator +}; + +function optional(f) { + return f == null ? null : required(f); +} + +function required(f) { + if (typeof f !== "function") throw new Error; + return f; +} + +function constantZero() { + return 0; +} + +function constant$2(x) { + return function() { + return x; + }; +} + +// https://en.wikipedia.org/wiki/Linear_congruential_generator#Parameters_in_common_use +const a$1 = 1664525; +const c$3 = 1013904223; +const m = 4294967296; // 2^32 + +function lcg$1() { + let s = 1; + return () => (s = (a$1 * s + c$3) % m) / m; +} + +function array$1(x) { + return typeof x === "object" && "length" in x + ? x // Array, TypedArray, NodeList, array-like + : Array.from(x); // Map, Set, iterable, string, or anything else +} + +function shuffle(array, random) { + let m = array.length, + t, + i; + + while (m) { + i = random() * m-- | 0; + t = array[m]; + array[m] = array[i]; + array[i] = t; + } + + return array; +} + +function enclose(circles) { + return packEncloseRandom(circles, lcg$1()); +} + +function packEncloseRandom(circles, random) { + var i = 0, n = (circles = shuffle(Array.from(circles), random)).length, B = [], p, e; + + while (i < n) { + p = circles[i]; + if (e && enclosesWeak(e, p)) ++i; + else e = encloseBasis(B = extendBasis(B, p)), i = 0; + } + + return e; +} + +function extendBasis(B, p) { + var i, j; + + if (enclosesWeakAll(p, B)) return [p]; + + // If we get here then B must have at least one element. + for (i = 0; i < B.length; ++i) { + if (enclosesNot(p, B[i]) + && enclosesWeakAll(encloseBasis2(B[i], p), B)) { + return [B[i], p]; + } + } + + // If we get here then B must have at least two elements. + for (i = 0; i < B.length - 1; ++i) { + for (j = i + 1; j < B.length; ++j) { + if (enclosesNot(encloseBasis2(B[i], B[j]), p) + && enclosesNot(encloseBasis2(B[i], p), B[j]) + && enclosesNot(encloseBasis2(B[j], p), B[i]) + && enclosesWeakAll(encloseBasis3(B[i], B[j], p), B)) { + return [B[i], B[j], p]; + } + } + } + + // If we get here then something is very wrong. + throw new Error; +} + +function enclosesNot(a, b) { + var dr = a.r - b.r, dx = b.x - a.x, dy = b.y - a.y; + return dr < 0 || dr * dr < dx * dx + dy * dy; +} + +function enclosesWeak(a, b) { + var dr = a.r - b.r + Math.max(a.r, b.r, 1) * 1e-9, dx = b.x - a.x, dy = b.y - a.y; + return dr > 0 && dr * dr > dx * dx + dy * dy; +} + +function enclosesWeakAll(a, B) { + for (var i = 0; i < B.length; ++i) { + if (!enclosesWeak(a, B[i])) { + return false; + } + } + return true; +} + +function encloseBasis(B) { + switch (B.length) { + case 1: return encloseBasis1(B[0]); + case 2: return encloseBasis2(B[0], B[1]); + case 3: return encloseBasis3(B[0], B[1], B[2]); + } +} + +function encloseBasis1(a) { + return { + x: a.x, + y: a.y, + r: a.r + }; +} + +function encloseBasis2(a, b) { + var x1 = a.x, y1 = a.y, r1 = a.r, + x2 = b.x, y2 = b.y, r2 = b.r, + x21 = x2 - x1, y21 = y2 - y1, r21 = r2 - r1, + l = Math.sqrt(x21 * x21 + y21 * y21); + return { + x: (x1 + x2 + x21 / l * r21) / 2, + y: (y1 + y2 + y21 / l * r21) / 2, + r: (l + r1 + r2) / 2 + }; +} + +function encloseBasis3(a, b, c) { + var x1 = a.x, y1 = a.y, r1 = a.r, + x2 = b.x, y2 = b.y, r2 = b.r, + x3 = c.x, y3 = c.y, r3 = c.r, + a2 = x1 - x2, + a3 = x1 - x3, + b2 = y1 - y2, + b3 = y1 - y3, + c2 = r2 - r1, + c3 = r3 - r1, + d1 = x1 * x1 + y1 * y1 - r1 * r1, + d2 = d1 - x2 * x2 - y2 * y2 + r2 * r2, + d3 = d1 - x3 * x3 - y3 * y3 + r3 * r3, + ab = a3 * b2 - a2 * b3, + xa = (b2 * d3 - b3 * d2) / (ab * 2) - x1, + xb = (b3 * c2 - b2 * c3) / ab, + ya = (a3 * d2 - a2 * d3) / (ab * 2) - y1, + yb = (a2 * c3 - a3 * c2) / ab, + A = xb * xb + yb * yb - 1, + B = 2 * (r1 + xa * xb + ya * yb), + C = xa * xa + ya * ya - r1 * r1, + r = -(Math.abs(A) > 1e-6 ? (B + Math.sqrt(B * B - 4 * A * C)) / (2 * A) : C / B); + return { + x: x1 + xa + xb * r, + y: y1 + ya + yb * r, + r: r + }; +} + +function place(b, a, c) { + var dx = b.x - a.x, x, a2, + dy = b.y - a.y, y, b2, + d2 = dx * dx + dy * dy; + if (d2) { + a2 = a.r + c.r, a2 *= a2; + b2 = b.r + c.r, b2 *= b2; + if (a2 > b2) { + x = (d2 + b2 - a2) / (2 * d2); + y = Math.sqrt(Math.max(0, b2 / d2 - x * x)); + c.x = b.x - x * dx - y * dy; + c.y = b.y - x * dy + y * dx; + } else { + x = (d2 + a2 - b2) / (2 * d2); + y = Math.sqrt(Math.max(0, a2 / d2 - x * x)); + c.x = a.x + x * dx - y * dy; + c.y = a.y + x * dy + y * dx; + } + } else { + c.x = a.x + c.r; + c.y = a.y; + } +} + +function intersects(a, b) { + var dr = a.r + b.r - 1e-6, dx = b.x - a.x, dy = b.y - a.y; + return dr > 0 && dr * dr > dx * dx + dy * dy; +} + +function score(node) { + var a = node._, + b = node.next._, + ab = a.r + b.r, + dx = (a.x * b.r + b.x * a.r) / ab, + dy = (a.y * b.r + b.y * a.r) / ab; + return dx * dx + dy * dy; +} + +function Node(circle) { + this._ = circle; + this.next = null; + this.previous = null; +} + +function packSiblingsRandom(circles, random) { + if (!(n = (circles = array$1(circles)).length)) return 0; + + var a, b, c, n, aa, ca, i, j, k, sj, sk; + + // Place the first circle. + a = circles[0], a.x = 0, a.y = 0; + if (!(n > 1)) return a.r; + + // Place the second circle. + b = circles[1], a.x = -b.r, b.x = a.r, b.y = 0; + if (!(n > 2)) return a.r + b.r; + + // Place the third circle. + place(b, a, c = circles[2]); + + // Initialize the front-chain using the first three circles a, b and c. + a = new Node(a), b = new Node(b), c = new Node(c); + a.next = c.previous = b; + b.next = a.previous = c; + c.next = b.previous = a; + + // Attempt to place each remaining circle… + pack: for (i = 3; i < n; ++i) { + place(a._, b._, c = circles[i]), c = new Node(c); + + // Find the closest intersecting circle on the front-chain, if any. + // “Closeness” is determined by linear distance along the front-chain. + // “Ahead” or “behind” is likewise determined by linear distance. + j = b.next, k = a.previous, sj = b._.r, sk = a._.r; + do { + if (sj <= sk) { + if (intersects(j._, c._)) { + b = j, a.next = b, b.previous = a, --i; + continue pack; + } + sj += j._.r, j = j.next; + } else { + if (intersects(k._, c._)) { + a = k, a.next = b, b.previous = a, --i; + continue pack; + } + sk += k._.r, k = k.previous; + } + } while (j !== k.next); + + // Success! Insert the new circle c between a and b. + c.previous = a, c.next = b, a.next = b.previous = b = c; + + // Compute the new closest circle pair to the centroid. + aa = score(a); + while ((c = c.next) !== b) { + if ((ca = score(c)) < aa) { + a = c, aa = ca; + } + } + b = a.next; + } + + // Compute the enclosing circle of the front chain. + a = [b._], c = b; while ((c = c.next) !== b) a.push(c._); c = packEncloseRandom(a, random); + + // Translate the circles to put the enclosing circle around the origin. + for (i = 0; i < n; ++i) a = circles[i], a.x -= c.x, a.y -= c.y; + + return c.r; +} + +function siblings(circles) { + packSiblingsRandom(circles, lcg$1()); + return circles; +} + +function defaultRadius(d) { + return Math.sqrt(d.value); +} + +function index$1() { + var radius = null, + dx = 1, + dy = 1, + padding = constantZero; + + function pack(root) { + const random = lcg$1(); + root.x = dx / 2, root.y = dy / 2; + if (radius) { + root.eachBefore(radiusLeaf(radius)) + .eachAfter(packChildrenRandom(padding, 0.5, random)) + .eachBefore(translateChild(1)); + } else { + root.eachBefore(radiusLeaf(defaultRadius)) + .eachAfter(packChildrenRandom(constantZero, 1, random)) + .eachAfter(packChildrenRandom(padding, root.r / Math.min(dx, dy), random)) + .eachBefore(translateChild(Math.min(dx, dy) / (2 * root.r))); + } + return root; + } + + pack.radius = function(x) { + return arguments.length ? (radius = optional(x), pack) : radius; + }; + + pack.size = function(x) { + return arguments.length ? (dx = +x[0], dy = +x[1], pack) : [dx, dy]; + }; + + pack.padding = function(x) { + return arguments.length ? (padding = typeof x === "function" ? x : constant$2(+x), pack) : padding; + }; + + return pack; +} + +function radiusLeaf(radius) { + return function(node) { + if (!node.children) { + node.r = Math.max(0, +radius(node) || 0); + } + }; +} + +function packChildrenRandom(padding, k, random) { + return function(node) { + if (children = node.children) { + var children, + i, + n = children.length, + r = padding(node) * k || 0, + e; + + if (r) for (i = 0; i < n; ++i) children[i].r += r; + e = packSiblingsRandom(children, random); + if (r) for (i = 0; i < n; ++i) children[i].r -= r; + node.r = e + r; + } + }; +} + +function translateChild(k) { + return function(node) { + var parent = node.parent; + node.r *= k; + if (parent) { + node.x = parent.x + k * node.x; + node.y = parent.y + k * node.y; + } + }; +} + +function roundNode(node) { + node.x0 = Math.round(node.x0); + node.y0 = Math.round(node.y0); + node.x1 = Math.round(node.x1); + node.y1 = Math.round(node.y1); +} + +function treemapDice(parent, x0, y0, x1, y1) { + var nodes = parent.children, + node, + i = -1, + n = nodes.length, + k = parent.value && (x1 - x0) / parent.value; + + while (++i < n) { + node = nodes[i], node.y0 = y0, node.y1 = y1; + node.x0 = x0, node.x1 = x0 += node.value * k; + } +} + +function partition() { + var dx = 1, + dy = 1, + padding = 0, + round = false; + + function partition(root) { + var n = root.height + 1; + root.x0 = + root.y0 = padding; + root.x1 = dx; + root.y1 = dy / n; + root.eachBefore(positionNode(dy, n)); + if (round) root.eachBefore(roundNode); + return root; + } + + function positionNode(dy, n) { + return function(node) { + if (node.children) { + treemapDice(node, node.x0, dy * (node.depth + 1) / n, node.x1, dy * (node.depth + 2) / n); + } + var x0 = node.x0, + y0 = node.y0, + x1 = node.x1 - padding, + y1 = node.y1 - padding; + if (x1 < x0) x0 = x1 = (x0 + x1) / 2; + if (y1 < y0) y0 = y1 = (y0 + y1) / 2; + node.x0 = x0; + node.y0 = y0; + node.x1 = x1; + node.y1 = y1; + }; + } + + partition.round = function(x) { + return arguments.length ? (round = !!x, partition) : round; + }; + + partition.size = function(x) { + return arguments.length ? (dx = +x[0], dy = +x[1], partition) : [dx, dy]; + }; + + partition.padding = function(x) { + return arguments.length ? (padding = +x, partition) : padding; + }; + + return partition; +} + +var preroot = {depth: -1}, + ambiguous = {}, + imputed = {}; + +function defaultId(d) { + return d.id; +} + +function defaultParentId(d) { + return d.parentId; +} + +function stratify() { + var id = defaultId, + parentId = defaultParentId, + path; + + function stratify(data) { + var nodes = Array.from(data), + currentId = id, + currentParentId = parentId, + n, + d, + i, + root, + parent, + node, + nodeId, + nodeKey, + nodeByKey = new Map; + + if (path != null) { + const I = nodes.map((d, i) => normalize$1(path(d, i, data))); + const P = I.map(parentof); + const S = new Set(I).add(""); + for (const i of P) { + if (!S.has(i)) { + S.add(i); + I.push(i); + P.push(parentof(i)); + nodes.push(imputed); + } + } + currentId = (_, i) => I[i]; + currentParentId = (_, i) => P[i]; + } + + for (i = 0, n = nodes.length; i < n; ++i) { + d = nodes[i], node = nodes[i] = new Node$1(d); + if ((nodeId = currentId(d, i, data)) != null && (nodeId += "")) { + nodeKey = node.id = nodeId; + nodeByKey.set(nodeKey, nodeByKey.has(nodeKey) ? ambiguous : node); + } + if ((nodeId = currentParentId(d, i, data)) != null && (nodeId += "")) { + node.parent = nodeId; + } + } + + for (i = 0; i < n; ++i) { + node = nodes[i]; + if (nodeId = node.parent) { + parent = nodeByKey.get(nodeId); + if (!parent) throw new Error("missing: " + nodeId); + if (parent === ambiguous) throw new Error("ambiguous: " + nodeId); + if (parent.children) parent.children.push(node); + else parent.children = [node]; + node.parent = parent; + } else { + if (root) throw new Error("multiple roots"); + root = node; + } + } + + if (!root) throw new Error("no root"); + + // When imputing internal nodes, only introduce roots if needed. + // Then replace the imputed marker data with null. + if (path != null) { + while (root.data === imputed && root.children.length === 1) { + root = root.children[0], --n; + } + for (let i = nodes.length - 1; i >= 0; --i) { + node = nodes[i]; + if (node.data !== imputed) break; + node.data = null; + } + } + + root.parent = preroot; + root.eachBefore(function(node) { node.depth = node.parent.depth + 1; --n; }).eachBefore(computeHeight); + root.parent = null; + if (n > 0) throw new Error("cycle"); + + return root; + } + + stratify.id = function(x) { + return arguments.length ? (id = optional(x), stratify) : id; + }; + + stratify.parentId = function(x) { + return arguments.length ? (parentId = optional(x), stratify) : parentId; + }; + + stratify.path = function(x) { + return arguments.length ? (path = optional(x), stratify) : path; + }; + + return stratify; +} + +// To normalize a path, we coerce to a string, strip the trailing slash if any +// (as long as the trailing slash is not immediately preceded by another slash), +// and add leading slash if missing. +function normalize$1(path) { + path = `${path}`; + let i = path.length; + if (slash(path, i - 1) && !slash(path, i - 2)) path = path.slice(0, -1); + return path[0] === "/" ? path : `/${path}`; +} + +// Walk backwards to find the first slash that is not the leading slash, e.g.: +// "/foo/bar" ⇥ "/foo", "/foo" ⇥ "/", "/" ↦ "". (The root is special-cased +// because the id of the root must be a truthy value.) +function parentof(path) { + let i = path.length; + if (i < 2) return ""; + while (--i > 1) if (slash(path, i)) break; + return path.slice(0, i); +} + +// Slashes can be escaped; to determine whether a slash is a path delimiter, we +// count the number of preceding backslashes escaping the forward slash: an odd +// number indicates an escaped forward slash. +function slash(path, i) { + if (path[i] === "/") { + let k = 0; + while (i > 0 && path[--i] === "\\") ++k; + if ((k & 1) === 0) return true; + } + return false; +} + +function defaultSeparation(a, b) { + return a.parent === b.parent ? 1 : 2; +} + +// function radialSeparation(a, b) { +// return (a.parent === b.parent ? 1 : 2) / a.depth; +// } + +// This function is used to traverse the left contour of a subtree (or +// subforest). It returns the successor of v on this contour. This successor is +// either given by the leftmost child of v or by the thread of v. The function +// returns null if and only if v is on the highest level of its subtree. +function nextLeft(v) { + var children = v.children; + return children ? children[0] : v.t; +} + +// This function works analogously to nextLeft. +function nextRight(v) { + var children = v.children; + return children ? children[children.length - 1] : v.t; +} + +// Shifts the current subtree rooted at w+. This is done by increasing +// prelim(w+) and mod(w+) by shift. +function moveSubtree(wm, wp, shift) { + var change = shift / (wp.i - wm.i); + wp.c -= change; + wp.s += shift; + wm.c += change; + wp.z += shift; + wp.m += shift; +} + +// All other shifts, applied to the smaller subtrees between w- and w+, are +// performed by this function. To prepare the shifts, we have to adjust +// change(w+), shift(w+), and change(w-). +function executeShifts(v) { + var shift = 0, + change = 0, + children = v.children, + i = children.length, + w; + while (--i >= 0) { + w = children[i]; + w.z += shift; + w.m += shift; + shift += w.s + (change += w.c); + } +} + +// If vi-’s ancestor is a sibling of v, returns vi-’s ancestor. Otherwise, +// returns the specified (default) ancestor. +function nextAncestor(vim, v, ancestor) { + return vim.a.parent === v.parent ? vim.a : ancestor; +} + +function TreeNode(node, i) { + this._ = node; + this.parent = null; + this.children = null; + this.A = null; // default ancestor + this.a = this; // ancestor + this.z = 0; // prelim + this.m = 0; // mod + this.c = 0; // change + this.s = 0; // shift + this.t = null; // thread + this.i = i; // number +} + +TreeNode.prototype = Object.create(Node$1.prototype); + +function treeRoot(root) { + var tree = new TreeNode(root, 0), + node, + nodes = [tree], + child, + children, + i, + n; + + while (node = nodes.pop()) { + if (children = node._.children) { + node.children = new Array(n = children.length); + for (i = n - 1; i >= 0; --i) { + nodes.push(child = node.children[i] = new TreeNode(children[i], i)); + child.parent = node; + } + } + } + + (tree.parent = new TreeNode(null, 0)).children = [tree]; + return tree; +} + +// Node-link tree diagram using the Reingold-Tilford "tidy" algorithm +function tree() { + var separation = defaultSeparation, + dx = 1, + dy = 1, + nodeSize = null; + + function tree(root) { + var t = treeRoot(root); + + // Compute the layout using Buchheim et al.’s algorithm. + t.eachAfter(firstWalk), t.parent.m = -t.z; + t.eachBefore(secondWalk); + + // If a fixed node size is specified, scale x and y. + if (nodeSize) root.eachBefore(sizeNode); + + // If a fixed tree size is specified, scale x and y based on the extent. + // Compute the left-most, right-most, and depth-most nodes for extents. + else { + var left = root, + right = root, + bottom = root; + root.eachBefore(function(node) { + if (node.x < left.x) left = node; + if (node.x > right.x) right = node; + if (node.depth > bottom.depth) bottom = node; + }); + var s = left === right ? 1 : separation(left, right) / 2, + tx = s - left.x, + kx = dx / (right.x + s + tx), + ky = dy / (bottom.depth || 1); + root.eachBefore(function(node) { + node.x = (node.x + tx) * kx; + node.y = node.depth * ky; + }); + } + + return root; + } + + // Computes a preliminary x-coordinate for v. Before that, FIRST WALK is + // applied recursively to the children of v, as well as the function + // APPORTION. After spacing out the children by calling EXECUTE SHIFTS, the + // node v is placed to the midpoint of its outermost children. + function firstWalk(v) { + var children = v.children, + siblings = v.parent.children, + w = v.i ? siblings[v.i - 1] : null; + if (children) { + executeShifts(v); + var midpoint = (children[0].z + children[children.length - 1].z) / 2; + if (w) { + v.z = w.z + separation(v._, w._); + v.m = v.z - midpoint; + } else { + v.z = midpoint; + } + } else if (w) { + v.z = w.z + separation(v._, w._); + } + v.parent.A = apportion(v, w, v.parent.A || siblings[0]); + } + + // Computes all real x-coordinates by summing up the modifiers recursively. + function secondWalk(v) { + v._.x = v.z + v.parent.m; + v.m += v.parent.m; + } + + // The core of the algorithm. Here, a new subtree is combined with the + // previous subtrees. Threads are used to traverse the inside and outside + // contours of the left and right subtree up to the highest common level. The + // vertices used for the traversals are vi+, vi-, vo-, and vo+, where the + // superscript o means outside and i means inside, the subscript - means left + // subtree and + means right subtree. For summing up the modifiers along the + // contour, we use respective variables si+, si-, so-, and so+. Whenever two + // nodes of the inside contours conflict, we compute the left one of the + // greatest uncommon ancestors using the function ANCESTOR and call MOVE + // SUBTREE to shift the subtree and prepare the shifts of smaller subtrees. + // Finally, we add a new thread (if necessary). + function apportion(v, w, ancestor) { + if (w) { + var vip = v, + vop = v, + vim = w, + vom = vip.parent.children[0], + sip = vip.m, + sop = vop.m, + sim = vim.m, + som = vom.m, + shift; + while (vim = nextRight(vim), vip = nextLeft(vip), vim && vip) { + vom = nextLeft(vom); + vop = nextRight(vop); + vop.a = v; + shift = vim.z + sim - vip.z - sip + separation(vim._, vip._); + if (shift > 0) { + moveSubtree(nextAncestor(vim, v, ancestor), v, shift); + sip += shift; + sop += shift; + } + sim += vim.m; + sip += vip.m; + som += vom.m; + sop += vop.m; + } + if (vim && !nextRight(vop)) { + vop.t = vim; + vop.m += sim - sop; + } + if (vip && !nextLeft(vom)) { + vom.t = vip; + vom.m += sip - som; + ancestor = v; + } + } + return ancestor; + } + + function sizeNode(node) { + node.x *= dx; + node.y = node.depth * dy; + } + + tree.separation = function(x) { + return arguments.length ? (separation = x, tree) : separation; + }; + + tree.size = function(x) { + return arguments.length ? (nodeSize = false, dx = +x[0], dy = +x[1], tree) : (nodeSize ? null : [dx, dy]); + }; + + tree.nodeSize = function(x) { + return arguments.length ? (nodeSize = true, dx = +x[0], dy = +x[1], tree) : (nodeSize ? [dx, dy] : null); + }; + + return tree; +} + +function treemapSlice(parent, x0, y0, x1, y1) { + var nodes = parent.children, + node, + i = -1, + n = nodes.length, + k = parent.value && (y1 - y0) / parent.value; + + while (++i < n) { + node = nodes[i], node.x0 = x0, node.x1 = x1; + node.y0 = y0, node.y1 = y0 += node.value * k; + } +} + +var phi = (1 + Math.sqrt(5)) / 2; + +function squarifyRatio(ratio, parent, x0, y0, x1, y1) { + var rows = [], + nodes = parent.children, + row, + nodeValue, + i0 = 0, + i1 = 0, + n = nodes.length, + dx, dy, + value = parent.value, + sumValue, + minValue, + maxValue, + newRatio, + minRatio, + alpha, + beta; + + while (i0 < n) { + dx = x1 - x0, dy = y1 - y0; + + // Find the next non-empty node. + do sumValue = nodes[i1++].value; while (!sumValue && i1 < n); + minValue = maxValue = sumValue; + alpha = Math.max(dy / dx, dx / dy) / (value * ratio); + beta = sumValue * sumValue * alpha; + minRatio = Math.max(maxValue / beta, beta / minValue); + + // Keep adding nodes while the aspect ratio maintains or improves. + for (; i1 < n; ++i1) { + sumValue += nodeValue = nodes[i1].value; + if (nodeValue < minValue) minValue = nodeValue; + if (nodeValue > maxValue) maxValue = nodeValue; + beta = sumValue * sumValue * alpha; + newRatio = Math.max(maxValue / beta, beta / minValue); + if (newRatio > minRatio) { sumValue -= nodeValue; break; } + minRatio = newRatio; + } + + // Position and record the row orientation. + rows.push(row = {value: sumValue, dice: dx < dy, children: nodes.slice(i0, i1)}); + if (row.dice) treemapDice(row, x0, y0, x1, value ? y0 += dy * sumValue / value : y1); + else treemapSlice(row, x0, y0, value ? x0 += dx * sumValue / value : x1, y1); + value -= sumValue, i0 = i1; + } + + return rows; +} + +var squarify = (function custom(ratio) { + + function squarify(parent, x0, y0, x1, y1) { + squarifyRatio(ratio, parent, x0, y0, x1, y1); + } + + squarify.ratio = function(x) { + return custom((x = +x) > 1 ? x : 1); + }; + + return squarify; +})(phi); + +function index() { + var tile = squarify, + round = false, + dx = 1, + dy = 1, + paddingStack = [0], + paddingInner = constantZero, + paddingTop = constantZero, + paddingRight = constantZero, + paddingBottom = constantZero, + paddingLeft = constantZero; + + function treemap(root) { + root.x0 = + root.y0 = 0; + root.x1 = dx; + root.y1 = dy; + root.eachBefore(positionNode); + paddingStack = [0]; + if (round) root.eachBefore(roundNode); + return root; + } + + function positionNode(node) { + var p = paddingStack[node.depth], + x0 = node.x0 + p, + y0 = node.y0 + p, + x1 = node.x1 - p, + y1 = node.y1 - p; + if (x1 < x0) x0 = x1 = (x0 + x1) / 2; + if (y1 < y0) y0 = y1 = (y0 + y1) / 2; + node.x0 = x0; + node.y0 = y0; + node.x1 = x1; + node.y1 = y1; + if (node.children) { + p = paddingStack[node.depth + 1] = paddingInner(node) / 2; + x0 += paddingLeft(node) - p; + y0 += paddingTop(node) - p; + x1 -= paddingRight(node) - p; + y1 -= paddingBottom(node) - p; + if (x1 < x0) x0 = x1 = (x0 + x1) / 2; + if (y1 < y0) y0 = y1 = (y0 + y1) / 2; + tile(node, x0, y0, x1, y1); + } + } + + treemap.round = function(x) { + return arguments.length ? (round = !!x, treemap) : round; + }; + + treemap.size = function(x) { + return arguments.length ? (dx = +x[0], dy = +x[1], treemap) : [dx, dy]; + }; + + treemap.tile = function(x) { + return arguments.length ? (tile = required(x), treemap) : tile; + }; + + treemap.padding = function(x) { + return arguments.length ? treemap.paddingInner(x).paddingOuter(x) : treemap.paddingInner(); + }; + + treemap.paddingInner = function(x) { + return arguments.length ? (paddingInner = typeof x === "function" ? x : constant$2(+x), treemap) : paddingInner; + }; + + treemap.paddingOuter = function(x) { + return arguments.length ? treemap.paddingTop(x).paddingRight(x).paddingBottom(x).paddingLeft(x) : treemap.paddingTop(); + }; + + treemap.paddingTop = function(x) { + return arguments.length ? (paddingTop = typeof x === "function" ? x : constant$2(+x), treemap) : paddingTop; + }; + + treemap.paddingRight = function(x) { + return arguments.length ? (paddingRight = typeof x === "function" ? x : constant$2(+x), treemap) : paddingRight; + }; + + treemap.paddingBottom = function(x) { + return arguments.length ? (paddingBottom = typeof x === "function" ? x : constant$2(+x), treemap) : paddingBottom; + }; + + treemap.paddingLeft = function(x) { + return arguments.length ? (paddingLeft = typeof x === "function" ? x : constant$2(+x), treemap) : paddingLeft; + }; + + return treemap; +} + +function binary(parent, x0, y0, x1, y1) { + var nodes = parent.children, + i, n = nodes.length, + sum, sums = new Array(n + 1); + + for (sums[0] = sum = i = 0; i < n; ++i) { + sums[i + 1] = sum += nodes[i].value; + } + + partition(0, n, parent.value, x0, y0, x1, y1); + + function partition(i, j, value, x0, y0, x1, y1) { + if (i >= j - 1) { + var node = nodes[i]; + node.x0 = x0, node.y0 = y0; + node.x1 = x1, node.y1 = y1; + return; + } + + var valueOffset = sums[i], + valueTarget = (value / 2) + valueOffset, + k = i + 1, + hi = j - 1; + + while (k < hi) { + var mid = k + hi >>> 1; + if (sums[mid] < valueTarget) k = mid + 1; + else hi = mid; + } + + if ((valueTarget - sums[k - 1]) < (sums[k] - valueTarget) && i + 1 < k) --k; + + var valueLeft = sums[k] - valueOffset, + valueRight = value - valueLeft; + + if ((x1 - x0) > (y1 - y0)) { + var xk = value ? (x0 * valueRight + x1 * valueLeft) / value : x1; + partition(i, k, valueLeft, x0, y0, xk, y1); + partition(k, j, valueRight, xk, y0, x1, y1); + } else { + var yk = value ? (y0 * valueRight + y1 * valueLeft) / value : y1; + partition(i, k, valueLeft, x0, y0, x1, yk); + partition(k, j, valueRight, x0, yk, x1, y1); + } + } +} + +function sliceDice(parent, x0, y0, x1, y1) { + (parent.depth & 1 ? treemapSlice : treemapDice)(parent, x0, y0, x1, y1); +} + +var resquarify = (function custom(ratio) { + + function resquarify(parent, x0, y0, x1, y1) { + if ((rows = parent._squarify) && (rows.ratio === ratio)) { + var rows, + row, + nodes, + i, + j = -1, + n, + m = rows.length, + value = parent.value; + + while (++j < m) { + row = rows[j], nodes = row.children; + for (i = row.value = 0, n = nodes.length; i < n; ++i) row.value += nodes[i].value; + if (row.dice) treemapDice(row, x0, y0, x1, value ? y0 += (y1 - y0) * row.value / value : y1); + else treemapSlice(row, x0, y0, value ? x0 += (x1 - x0) * row.value / value : x1, y1); + value -= row.value; + } + } else { + parent._squarify = rows = squarifyRatio(ratio, parent, x0, y0, x1, y1); + rows.ratio = ratio; + } + } + + resquarify.ratio = function(x) { + return custom((x = +x) > 1 ? x : 1); + }; + + return resquarify; +})(phi); + +function area$1(polygon) { + var i = -1, + n = polygon.length, + a, + b = polygon[n - 1], + area = 0; + + while (++i < n) { + a = b; + b = polygon[i]; + area += a[1] * b[0] - a[0] * b[1]; + } + + return area / 2; +} + +function centroid(polygon) { + var i = -1, + n = polygon.length, + x = 0, + y = 0, + a, + b = polygon[n - 1], + c, + k = 0; + + while (++i < n) { + a = b; + b = polygon[i]; + k += c = a[0] * b[1] - b[0] * a[1]; + x += (a[0] + b[0]) * c; + y += (a[1] + b[1]) * c; + } + + return k *= 3, [x / k, y / k]; +} + +// Returns the 2D cross product of AB and AC vectors, i.e., the z-component of +// the 3D cross product in a quadrant I Cartesian coordinate system (+x is +// right, +y is up). Returns a positive value if ABC is counter-clockwise, +// negative if clockwise, and zero if the points are collinear. +function cross$1(a, b, c) { + return (b[0] - a[0]) * (c[1] - a[1]) - (b[1] - a[1]) * (c[0] - a[0]); +} + +function lexicographicOrder(a, b) { + return a[0] - b[0] || a[1] - b[1]; +} + +// Computes the upper convex hull per the monotone chain algorithm. +// Assumes points.length >= 3, is sorted by x, unique in y. +// Returns an array of indices into points in left-to-right order. +function computeUpperHullIndexes(points) { + const n = points.length, + indexes = [0, 1]; + let size = 2, i; + + for (i = 2; i < n; ++i) { + while (size > 1 && cross$1(points[indexes[size - 2]], points[indexes[size - 1]], points[i]) <= 0) --size; + indexes[size++] = i; + } + + return indexes.slice(0, size); // remove popped points +} + +function hull(points) { + if ((n = points.length) < 3) return null; + + var i, + n, + sortedPoints = new Array(n), + flippedPoints = new Array(n); + + for (i = 0; i < n; ++i) sortedPoints[i] = [+points[i][0], +points[i][1], i]; + sortedPoints.sort(lexicographicOrder); + for (i = 0; i < n; ++i) flippedPoints[i] = [sortedPoints[i][0], -sortedPoints[i][1]]; + + var upperIndexes = computeUpperHullIndexes(sortedPoints), + lowerIndexes = computeUpperHullIndexes(flippedPoints); + + // Construct the hull polygon, removing possible duplicate endpoints. + var skipLeft = lowerIndexes[0] === upperIndexes[0], + skipRight = lowerIndexes[lowerIndexes.length - 1] === upperIndexes[upperIndexes.length - 1], + hull = []; + + // Add upper hull in right-to-l order. + // Then add lower hull in left-to-right order. + for (i = upperIndexes.length - 1; i >= 0; --i) hull.push(points[sortedPoints[upperIndexes[i]][2]]); + for (i = +skipLeft; i < lowerIndexes.length - skipRight; ++i) hull.push(points[sortedPoints[lowerIndexes[i]][2]]); + + return hull; +} + +function contains(polygon, point) { + var n = polygon.length, + p = polygon[n - 1], + x = point[0], y = point[1], + x0 = p[0], y0 = p[1], + x1, y1, + inside = false; + + for (var i = 0; i < n; ++i) { + p = polygon[i], x1 = p[0], y1 = p[1]; + if (((y1 > y) !== (y0 > y)) && (x < (x0 - x1) * (y - y1) / (y0 - y1) + x1)) inside = !inside; + x0 = x1, y0 = y1; + } + + return inside; +} + +function length(polygon) { + var i = -1, + n = polygon.length, + b = polygon[n - 1], + xa, + ya, + xb = b[0], + yb = b[1], + perimeter = 0; + + while (++i < n) { + xa = xb; + ya = yb; + b = polygon[i]; + xb = b[0]; + yb = b[1]; + xa -= xb; + ya -= yb; + perimeter += Math.hypot(xa, ya); + } + + return perimeter; +} + +var defaultSource = Math.random; + +var uniform = (function sourceRandomUniform(source) { + function randomUniform(min, max) { + min = min == null ? 0 : +min; + max = max == null ? 1 : +max; + if (arguments.length === 1) max = min, min = 0; + else max -= min; + return function() { + return source() * max + min; + }; + } + + randomUniform.source = sourceRandomUniform; + + return randomUniform; +})(defaultSource); + +var int = (function sourceRandomInt(source) { + function randomInt(min, max) { + if (arguments.length < 2) max = min, min = 0; + min = Math.floor(min); + max = Math.floor(max) - min; + return function() { + return Math.floor(source() * max + min); + }; + } + + randomInt.source = sourceRandomInt; + + return randomInt; +})(defaultSource); + +var normal = (function sourceRandomNormal(source) { + function randomNormal(mu, sigma) { + var x, r; + mu = mu == null ? 0 : +mu; + sigma = sigma == null ? 1 : +sigma; + return function() { + var y; + + // If available, use the second previously-generated uniform random. + if (x != null) y = x, x = null; + + // Otherwise, generate a new x and y. + else do { + x = source() * 2 - 1; + y = source() * 2 - 1; + r = x * x + y * y; + } while (!r || r > 1); + + return mu + sigma * y * Math.sqrt(-2 * Math.log(r) / r); + }; + } + + randomNormal.source = sourceRandomNormal; + + return randomNormal; +})(defaultSource); + +var logNormal = (function sourceRandomLogNormal(source) { + var N = normal.source(source); + + function randomLogNormal() { + var randomNormal = N.apply(this, arguments); + return function() { + return Math.exp(randomNormal()); + }; + } + + randomLogNormal.source = sourceRandomLogNormal; + + return randomLogNormal; +})(defaultSource); + +var irwinHall = (function sourceRandomIrwinHall(source) { + function randomIrwinHall(n) { + if ((n = +n) <= 0) return () => 0; + return function() { + for (var sum = 0, i = n; i > 1; --i) sum += source(); + return sum + i * source(); + }; + } + + randomIrwinHall.source = sourceRandomIrwinHall; + + return randomIrwinHall; +})(defaultSource); + +var bates = (function sourceRandomBates(source) { + var I = irwinHall.source(source); + + function randomBates(n) { + // use limiting distribution at n === 0 + if ((n = +n) === 0) return source; + var randomIrwinHall = I(n); + return function() { + return randomIrwinHall() / n; + }; + } + + randomBates.source = sourceRandomBates; + + return randomBates; +})(defaultSource); + +var exponential = (function sourceRandomExponential(source) { + function randomExponential(lambda) { + return function() { + return -Math.log1p(-source()) / lambda; + }; + } + + randomExponential.source = sourceRandomExponential; + + return randomExponential; +})(defaultSource); + +var pareto = (function sourceRandomPareto(source) { + function randomPareto(alpha) { + if ((alpha = +alpha) < 0) throw new RangeError("invalid alpha"); + alpha = 1 / -alpha; + return function() { + return Math.pow(1 - source(), alpha); + }; + } + + randomPareto.source = sourceRandomPareto; + + return randomPareto; +})(defaultSource); + +var bernoulli = (function sourceRandomBernoulli(source) { + function randomBernoulli(p) { + if ((p = +p) < 0 || p > 1) throw new RangeError("invalid p"); + return function() { + return Math.floor(source() + p); + }; + } + + randomBernoulli.source = sourceRandomBernoulli; + + return randomBernoulli; +})(defaultSource); + +var geometric = (function sourceRandomGeometric(source) { + function randomGeometric(p) { + if ((p = +p) < 0 || p > 1) throw new RangeError("invalid p"); + if (p === 0) return () => Infinity; + if (p === 1) return () => 1; + p = Math.log1p(-p); + return function() { + return 1 + Math.floor(Math.log1p(-source()) / p); + }; + } + + randomGeometric.source = sourceRandomGeometric; + + return randomGeometric; +})(defaultSource); + +var gamma = (function sourceRandomGamma(source) { + var randomNormal = normal.source(source)(); + + function randomGamma(k, theta) { + if ((k = +k) < 0) throw new RangeError("invalid k"); + // degenerate distribution if k === 0 + if (k === 0) return () => 0; + theta = theta == null ? 1 : +theta; + // exponential distribution if k === 1 + if (k === 1) return () => -Math.log1p(-source()) * theta; + + var d = (k < 1 ? k + 1 : k) - 1 / 3, + c = 1 / (3 * Math.sqrt(d)), + multiplier = k < 1 ? () => Math.pow(source(), 1 / k) : () => 1; + return function() { + do { + do { + var x = randomNormal(), + v = 1 + c * x; + } while (v <= 0); + v *= v * v; + var u = 1 - source(); + } while (u >= 1 - 0.0331 * x * x * x * x && Math.log(u) >= 0.5 * x * x + d * (1 - v + Math.log(v))); + return d * v * multiplier() * theta; + }; + } + + randomGamma.source = sourceRandomGamma; + + return randomGamma; +})(defaultSource); + +var beta = (function sourceRandomBeta(source) { + var G = gamma.source(source); + + function randomBeta(alpha, beta) { + var X = G(alpha), + Y = G(beta); + return function() { + var x = X(); + return x === 0 ? 0 : x / (x + Y()); + }; + } + + randomBeta.source = sourceRandomBeta; + + return randomBeta; +})(defaultSource); + +var binomial = (function sourceRandomBinomial(source) { + var G = geometric.source(source), + B = beta.source(source); + + function randomBinomial(n, p) { + n = +n; + if ((p = +p) >= 1) return () => n; + if (p <= 0) return () => 0; + return function() { + var acc = 0, nn = n, pp = p; + while (nn * pp > 16 && nn * (1 - pp) > 16) { + var i = Math.floor((nn + 1) * pp), + y = B(i, nn - i + 1)(); + if (y <= pp) { + acc += i; + nn -= i; + pp = (pp - y) / (1 - y); + } else { + nn = i - 1; + pp /= y; + } + } + var sign = pp < 0.5, + pFinal = sign ? pp : 1 - pp, + g = G(pFinal); + for (var s = g(), k = 0; s <= nn; ++k) s += g(); + return acc + (sign ? k : nn - k); + }; + } + + randomBinomial.source = sourceRandomBinomial; + + return randomBinomial; +})(defaultSource); + +var weibull = (function sourceRandomWeibull(source) { + function randomWeibull(k, a, b) { + var outerFunc; + if ((k = +k) === 0) { + outerFunc = x => -Math.log(x); + } else { + k = 1 / k; + outerFunc = x => Math.pow(x, k); + } + a = a == null ? 0 : +a; + b = b == null ? 1 : +b; + return function() { + return a + b * outerFunc(-Math.log1p(-source())); + }; + } + + randomWeibull.source = sourceRandomWeibull; + + return randomWeibull; +})(defaultSource); + +var cauchy = (function sourceRandomCauchy(source) { + function randomCauchy(a, b) { + a = a == null ? 0 : +a; + b = b == null ? 1 : +b; + return function() { + return a + b * Math.tan(Math.PI * source()); + }; + } + + randomCauchy.source = sourceRandomCauchy; + + return randomCauchy; +})(defaultSource); + +var logistic = (function sourceRandomLogistic(source) { + function randomLogistic(a, b) { + a = a == null ? 0 : +a; + b = b == null ? 1 : +b; + return function() { + var u = source(); + return a + b * Math.log(u / (1 - u)); + }; + } + + randomLogistic.source = sourceRandomLogistic; + + return randomLogistic; +})(defaultSource); + +var poisson = (function sourceRandomPoisson(source) { + var G = gamma.source(source), + B = binomial.source(source); + + function randomPoisson(lambda) { + return function() { + var acc = 0, l = lambda; + while (l > 16) { + var n = Math.floor(0.875 * l), + t = G(n)(); + if (t > l) return acc + B(n - 1, l / t)(); + acc += n; + l -= t; + } + for (var s = -Math.log1p(-source()), k = 0; s <= l; ++k) s -= Math.log1p(-source()); + return acc + k; + }; + } + + randomPoisson.source = sourceRandomPoisson; + + return randomPoisson; +})(defaultSource); + +// https://en.wikipedia.org/wiki/Linear_congruential_generator#Parameters_in_common_use +const mul = 0x19660D; +const inc = 0x3C6EF35F; +const eps = 1 / 0x100000000; + +function lcg(seed = Math.random()) { + let state = (0 <= seed && seed < 1 ? seed / eps : Math.abs(seed)) | 0; + return () => (state = mul * state + inc | 0, eps * (state >>> 0)); +} + +function initRange(domain, range) { + switch (arguments.length) { + case 0: break; + case 1: this.range(domain); break; + default: this.range(range).domain(domain); break; + } + return this; +} + +function initInterpolator(domain, interpolator) { + switch (arguments.length) { + case 0: break; + case 1: { + if (typeof domain === "function") this.interpolator(domain); + else this.range(domain); + break; + } + default: { + this.domain(domain); + if (typeof interpolator === "function") this.interpolator(interpolator); + else this.range(interpolator); + break; + } + } + return this; +} + +const implicit = Symbol("implicit"); + +function ordinal() { + var index = new InternMap(), + domain = [], + range = [], + unknown = implicit; + + function scale(d) { + let i = index.get(d); + if (i === undefined) { + if (unknown !== implicit) return unknown; + index.set(d, i = domain.push(d) - 1); + } + return range[i % range.length]; + } + + scale.domain = function(_) { + if (!arguments.length) return domain.slice(); + domain = [], index = new InternMap(); + for (const value of _) { + if (index.has(value)) continue; + index.set(value, domain.push(value) - 1); + } + return scale; + }; + + scale.range = function(_) { + return arguments.length ? (range = Array.from(_), scale) : range.slice(); + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.copy = function() { + return ordinal(domain, range).unknown(unknown); + }; + + initRange.apply(scale, arguments); + + return scale; +} + +function band() { + var scale = ordinal().unknown(undefined), + domain = scale.domain, + ordinalRange = scale.range, + r0 = 0, + r1 = 1, + step, + bandwidth, + round = false, + paddingInner = 0, + paddingOuter = 0, + align = 0.5; + + delete scale.unknown; + + function rescale() { + var n = domain().length, + reverse = r1 < r0, + start = reverse ? r1 : r0, + stop = reverse ? r0 : r1; + step = (stop - start) / Math.max(1, n - paddingInner + paddingOuter * 2); + if (round) step = Math.floor(step); + start += (stop - start - step * (n - paddingInner)) * align; + bandwidth = step * (1 - paddingInner); + if (round) start = Math.round(start), bandwidth = Math.round(bandwidth); + var values = range$2(n).map(function(i) { return start + step * i; }); + return ordinalRange(reverse ? values.reverse() : values); + } + + scale.domain = function(_) { + return arguments.length ? (domain(_), rescale()) : domain(); + }; + + scale.range = function(_) { + return arguments.length ? ([r0, r1] = _, r0 = +r0, r1 = +r1, rescale()) : [r0, r1]; + }; + + scale.rangeRound = function(_) { + return [r0, r1] = _, r0 = +r0, r1 = +r1, round = true, rescale(); + }; + + scale.bandwidth = function() { + return bandwidth; + }; + + scale.step = function() { + return step; + }; + + scale.round = function(_) { + return arguments.length ? (round = !!_, rescale()) : round; + }; + + scale.padding = function(_) { + return arguments.length ? (paddingInner = Math.min(1, paddingOuter = +_), rescale()) : paddingInner; + }; + + scale.paddingInner = function(_) { + return arguments.length ? (paddingInner = Math.min(1, _), rescale()) : paddingInner; + }; + + scale.paddingOuter = function(_) { + return arguments.length ? (paddingOuter = +_, rescale()) : paddingOuter; + }; + + scale.align = function(_) { + return arguments.length ? (align = Math.max(0, Math.min(1, _)), rescale()) : align; + }; + + scale.copy = function() { + return band(domain(), [r0, r1]) + .round(round) + .paddingInner(paddingInner) + .paddingOuter(paddingOuter) + .align(align); + }; + + return initRange.apply(rescale(), arguments); +} + +function pointish(scale) { + var copy = scale.copy; + + scale.padding = scale.paddingOuter; + delete scale.paddingInner; + delete scale.paddingOuter; + + scale.copy = function() { + return pointish(copy()); + }; + + return scale; +} + +function point$4() { + return pointish(band.apply(null, arguments).paddingInner(1)); +} + +function constants(x) { + return function() { + return x; + }; +} + +function number$1(x) { + return +x; +} + +var unit = [0, 1]; + +function identity$3(x) { + return x; +} + +function normalize(a, b) { + return (b -= (a = +a)) + ? function(x) { return (x - a) / b; } + : constants(isNaN(b) ? NaN : 0.5); +} + +function clamper(a, b) { + var t; + if (a > b) t = a, a = b, b = t; + return function(x) { return Math.max(a, Math.min(b, x)); }; +} + +// normalize(a, b)(x) takes a domain value x in [a,b] and returns the corresponding parameter t in [0,1]. +// interpolate(a, b)(t) takes a parameter t in [0,1] and returns the corresponding range value x in [a,b]. +function bimap(domain, range, interpolate) { + var d0 = domain[0], d1 = domain[1], r0 = range[0], r1 = range[1]; + if (d1 < d0) d0 = normalize(d1, d0), r0 = interpolate(r1, r0); + else d0 = normalize(d0, d1), r0 = interpolate(r0, r1); + return function(x) { return r0(d0(x)); }; +} + +function polymap(domain, range, interpolate) { + var j = Math.min(domain.length, range.length) - 1, + d = new Array(j), + r = new Array(j), + i = -1; + + // Reverse descending domains. + if (domain[j] < domain[0]) { + domain = domain.slice().reverse(); + range = range.slice().reverse(); + } + + while (++i < j) { + d[i] = normalize(domain[i], domain[i + 1]); + r[i] = interpolate(range[i], range[i + 1]); + } + + return function(x) { + var i = bisect(domain, x, 1, j) - 1; + return r[i](d[i](x)); + }; +} + +function copy$1(source, target) { + return target + .domain(source.domain()) + .range(source.range()) + .interpolate(source.interpolate()) + .clamp(source.clamp()) + .unknown(source.unknown()); +} + +function transformer$2() { + var domain = unit, + range = unit, + interpolate = interpolate$2, + transform, + untransform, + unknown, + clamp = identity$3, + piecewise, + output, + input; + + function rescale() { + var n = Math.min(domain.length, range.length); + if (clamp !== identity$3) clamp = clamper(domain[0], domain[n - 1]); + piecewise = n > 2 ? polymap : bimap; + output = input = null; + return scale; + } + + function scale(x) { + return x == null || isNaN(x = +x) ? unknown : (output || (output = piecewise(domain.map(transform), range, interpolate)))(transform(clamp(x))); + } + + scale.invert = function(y) { + return clamp(untransform((input || (input = piecewise(range, domain.map(transform), interpolateNumber)))(y))); + }; + + scale.domain = function(_) { + return arguments.length ? (domain = Array.from(_, number$1), rescale()) : domain.slice(); + }; + + scale.range = function(_) { + return arguments.length ? (range = Array.from(_), rescale()) : range.slice(); + }; + + scale.rangeRound = function(_) { + return range = Array.from(_), interpolate = interpolateRound, rescale(); + }; + + scale.clamp = function(_) { + return arguments.length ? (clamp = _ ? true : identity$3, rescale()) : clamp !== identity$3; + }; + + scale.interpolate = function(_) { + return arguments.length ? (interpolate = _, rescale()) : interpolate; + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + return function(t, u) { + transform = t, untransform = u; + return rescale(); + }; +} + +function continuous() { + return transformer$2()(identity$3, identity$3); +} + +function tickFormat(start, stop, count, specifier) { + var step = tickStep(start, stop, count), + precision; + specifier = formatSpecifier(specifier == null ? ",f" : specifier); + switch (specifier.type) { + case "s": { + var value = Math.max(Math.abs(start), Math.abs(stop)); + if (specifier.precision == null && !isNaN(precision = precisionPrefix(step, value))) specifier.precision = precision; + return exports.formatPrefix(specifier, value); + } + case "": + case "e": + case "g": + case "p": + case "r": { + if (specifier.precision == null && !isNaN(precision = precisionRound(step, Math.max(Math.abs(start), Math.abs(stop))))) specifier.precision = precision - (specifier.type === "e"); + break; + } + case "f": + case "%": { + if (specifier.precision == null && !isNaN(precision = precisionFixed(step))) specifier.precision = precision - (specifier.type === "%") * 2; + break; + } + } + return exports.format(specifier); +} + +function linearish(scale) { + var domain = scale.domain; + + scale.ticks = function(count) { + var d = domain(); + return ticks(d[0], d[d.length - 1], count == null ? 10 : count); + }; + + scale.tickFormat = function(count, specifier) { + var d = domain(); + return tickFormat(d[0], d[d.length - 1], count == null ? 10 : count, specifier); + }; + + scale.nice = function(count) { + if (count == null) count = 10; + + var d = domain(); + var i0 = 0; + var i1 = d.length - 1; + var start = d[i0]; + var stop = d[i1]; + var prestep; + var step; + var maxIter = 10; + + if (stop < start) { + step = start, start = stop, stop = step; + step = i0, i0 = i1, i1 = step; + } + + while (maxIter-- > 0) { + step = tickIncrement(start, stop, count); + if (step === prestep) { + d[i0] = start; + d[i1] = stop; + return domain(d); + } else if (step > 0) { + start = Math.floor(start / step) * step; + stop = Math.ceil(stop / step) * step; + } else if (step < 0) { + start = Math.ceil(start * step) / step; + stop = Math.floor(stop * step) / step; + } else { + break; + } + prestep = step; + } + + return scale; + }; + + return scale; +} + +function linear() { + var scale = continuous(); + + scale.copy = function() { + return copy$1(scale, linear()); + }; + + initRange.apply(scale, arguments); + + return linearish(scale); +} + +function identity$2(domain) { + var unknown; + + function scale(x) { + return x == null || isNaN(x = +x) ? unknown : x; + } + + scale.invert = scale; + + scale.domain = scale.range = function(_) { + return arguments.length ? (domain = Array.from(_, number$1), scale) : domain.slice(); + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.copy = function() { + return identity$2(domain).unknown(unknown); + }; + + domain = arguments.length ? Array.from(domain, number$1) : [0, 1]; + + return linearish(scale); +} + +function nice(domain, interval) { + domain = domain.slice(); + + var i0 = 0, + i1 = domain.length - 1, + x0 = domain[i0], + x1 = domain[i1], + t; + + if (x1 < x0) { + t = i0, i0 = i1, i1 = t; + t = x0, x0 = x1, x1 = t; + } + + domain[i0] = interval.floor(x0); + domain[i1] = interval.ceil(x1); + return domain; +} + +function transformLog(x) { + return Math.log(x); +} + +function transformExp(x) { + return Math.exp(x); +} + +function transformLogn(x) { + return -Math.log(-x); +} + +function transformExpn(x) { + return -Math.exp(-x); +} + +function pow10(x) { + return isFinite(x) ? +("1e" + x) : x < 0 ? 0 : x; +} + +function powp(base) { + return base === 10 ? pow10 + : base === Math.E ? Math.exp + : x => Math.pow(base, x); +} + +function logp(base) { + return base === Math.E ? Math.log + : base === 10 && Math.log10 + || base === 2 && Math.log2 + || (base = Math.log(base), x => Math.log(x) / base); +} + +function reflect(f) { + return (x, k) => -f(-x, k); +} + +function loggish(transform) { + const scale = transform(transformLog, transformExp); + const domain = scale.domain; + let base = 10; + let logs; + let pows; + + function rescale() { + logs = logp(base), pows = powp(base); + if (domain()[0] < 0) { + logs = reflect(logs), pows = reflect(pows); + transform(transformLogn, transformExpn); + } else { + transform(transformLog, transformExp); + } + return scale; + } + + scale.base = function(_) { + return arguments.length ? (base = +_, rescale()) : base; + }; + + scale.domain = function(_) { + return arguments.length ? (domain(_), rescale()) : domain(); + }; + + scale.ticks = count => { + const d = domain(); + let u = d[0]; + let v = d[d.length - 1]; + const r = v < u; + + if (r) ([u, v] = [v, u]); + + let i = logs(u); + let j = logs(v); + let k; + let t; + const n = count == null ? 10 : +count; + let z = []; + + if (!(base % 1) && j - i < n) { + i = Math.floor(i), j = Math.ceil(j); + if (u > 0) for (; i <= j; ++i) { + for (k = 1; k < base; ++k) { + t = i < 0 ? k / pows(-i) : k * pows(i); + if (t < u) continue; + if (t > v) break; + z.push(t); + } + } else for (; i <= j; ++i) { + for (k = base - 1; k >= 1; --k) { + t = i > 0 ? k / pows(-i) : k * pows(i); + if (t < u) continue; + if (t > v) break; + z.push(t); + } + } + if (z.length * 2 < n) z = ticks(u, v, n); + } else { + z = ticks(i, j, Math.min(j - i, n)).map(pows); + } + return r ? z.reverse() : z; + }; + + scale.tickFormat = (count, specifier) => { + if (count == null) count = 10; + if (specifier == null) specifier = base === 10 ? "s" : ","; + if (typeof specifier !== "function") { + if (!(base % 1) && (specifier = formatSpecifier(specifier)).precision == null) specifier.trim = true; + specifier = exports.format(specifier); + } + if (count === Infinity) return specifier; + const k = Math.max(1, base * count / scale.ticks().length); // TODO fast estimate? + return d => { + let i = d / pows(Math.round(logs(d))); + if (i * base < base - 0.5) i *= base; + return i <= k ? specifier(d) : ""; + }; + }; + + scale.nice = () => { + return domain(nice(domain(), { + floor: x => pows(Math.floor(logs(x))), + ceil: x => pows(Math.ceil(logs(x))) + })); + }; + + return scale; +} + +function log() { + const scale = loggish(transformer$2()).domain([1, 10]); + scale.copy = () => copy$1(scale, log()).base(scale.base()); + initRange.apply(scale, arguments); + return scale; +} + +function transformSymlog(c) { + return function(x) { + return Math.sign(x) * Math.log1p(Math.abs(x / c)); + }; +} + +function transformSymexp(c) { + return function(x) { + return Math.sign(x) * Math.expm1(Math.abs(x)) * c; + }; +} + +function symlogish(transform) { + var c = 1, scale = transform(transformSymlog(c), transformSymexp(c)); + + scale.constant = function(_) { + return arguments.length ? transform(transformSymlog(c = +_), transformSymexp(c)) : c; + }; + + return linearish(scale); +} + +function symlog() { + var scale = symlogish(transformer$2()); + + scale.copy = function() { + return copy$1(scale, symlog()).constant(scale.constant()); + }; + + return initRange.apply(scale, arguments); +} + +function transformPow(exponent) { + return function(x) { + return x < 0 ? -Math.pow(-x, exponent) : Math.pow(x, exponent); + }; +} + +function transformSqrt(x) { + return x < 0 ? -Math.sqrt(-x) : Math.sqrt(x); +} + +function transformSquare(x) { + return x < 0 ? -x * x : x * x; +} + +function powish(transform) { + var scale = transform(identity$3, identity$3), + exponent = 1; + + function rescale() { + return exponent === 1 ? transform(identity$3, identity$3) + : exponent === 0.5 ? transform(transformSqrt, transformSquare) + : transform(transformPow(exponent), transformPow(1 / exponent)); + } + + scale.exponent = function(_) { + return arguments.length ? (exponent = +_, rescale()) : exponent; + }; + + return linearish(scale); +} + +function pow() { + var scale = powish(transformer$2()); + + scale.copy = function() { + return copy$1(scale, pow()).exponent(scale.exponent()); + }; + + initRange.apply(scale, arguments); + + return scale; +} + +function sqrt$1() { + return pow.apply(null, arguments).exponent(0.5); +} + +function square$1(x) { + return Math.sign(x) * x * x; +} + +function unsquare(x) { + return Math.sign(x) * Math.sqrt(Math.abs(x)); +} + +function radial() { + var squared = continuous(), + range = [0, 1], + round = false, + unknown; + + function scale(x) { + var y = unsquare(squared(x)); + return isNaN(y) ? unknown : round ? Math.round(y) : y; + } + + scale.invert = function(y) { + return squared.invert(square$1(y)); + }; + + scale.domain = function(_) { + return arguments.length ? (squared.domain(_), scale) : squared.domain(); + }; + + scale.range = function(_) { + return arguments.length ? (squared.range((range = Array.from(_, number$1)).map(square$1)), scale) : range.slice(); + }; + + scale.rangeRound = function(_) { + return scale.range(_).round(true); + }; + + scale.round = function(_) { + return arguments.length ? (round = !!_, scale) : round; + }; + + scale.clamp = function(_) { + return arguments.length ? (squared.clamp(_), scale) : squared.clamp(); + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.copy = function() { + return radial(squared.domain(), range) + .round(round) + .clamp(squared.clamp()) + .unknown(unknown); + }; + + initRange.apply(scale, arguments); + + return linearish(scale); +} + +function quantile() { + var domain = [], + range = [], + thresholds = [], + unknown; + + function rescale() { + var i = 0, n = Math.max(1, range.length); + thresholds = new Array(n - 1); + while (++i < n) thresholds[i - 1] = quantileSorted(domain, i / n); + return scale; + } + + function scale(x) { + return x == null || isNaN(x = +x) ? unknown : range[bisect(thresholds, x)]; + } + + scale.invertExtent = function(y) { + var i = range.indexOf(y); + return i < 0 ? [NaN, NaN] : [ + i > 0 ? thresholds[i - 1] : domain[0], + i < thresholds.length ? thresholds[i] : domain[domain.length - 1] + ]; + }; + + scale.domain = function(_) { + if (!arguments.length) return domain.slice(); + domain = []; + for (let d of _) if (d != null && !isNaN(d = +d)) domain.push(d); + domain.sort(ascending$3); + return rescale(); + }; + + scale.range = function(_) { + return arguments.length ? (range = Array.from(_), rescale()) : range.slice(); + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.quantiles = function() { + return thresholds.slice(); + }; + + scale.copy = function() { + return quantile() + .domain(domain) + .range(range) + .unknown(unknown); + }; + + return initRange.apply(scale, arguments); +} + +function quantize() { + var x0 = 0, + x1 = 1, + n = 1, + domain = [0.5], + range = [0, 1], + unknown; + + function scale(x) { + return x != null && x <= x ? range[bisect(domain, x, 0, n)] : unknown; + } + + function rescale() { + var i = -1; + domain = new Array(n); + while (++i < n) domain[i] = ((i + 1) * x1 - (i - n) * x0) / (n + 1); + return scale; + } + + scale.domain = function(_) { + return arguments.length ? ([x0, x1] = _, x0 = +x0, x1 = +x1, rescale()) : [x0, x1]; + }; + + scale.range = function(_) { + return arguments.length ? (n = (range = Array.from(_)).length - 1, rescale()) : range.slice(); + }; + + scale.invertExtent = function(y) { + var i = range.indexOf(y); + return i < 0 ? [NaN, NaN] + : i < 1 ? [x0, domain[0]] + : i >= n ? [domain[n - 1], x1] + : [domain[i - 1], domain[i]]; + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : scale; + }; + + scale.thresholds = function() { + return domain.slice(); + }; + + scale.copy = function() { + return quantize() + .domain([x0, x1]) + .range(range) + .unknown(unknown); + }; + + return initRange.apply(linearish(scale), arguments); +} + +function threshold() { + var domain = [0.5], + range = [0, 1], + unknown, + n = 1; + + function scale(x) { + return x != null && x <= x ? range[bisect(domain, x, 0, n)] : unknown; + } + + scale.domain = function(_) { + return arguments.length ? (domain = Array.from(_), n = Math.min(domain.length, range.length - 1), scale) : domain.slice(); + }; + + scale.range = function(_) { + return arguments.length ? (range = Array.from(_), n = Math.min(domain.length, range.length - 1), scale) : range.slice(); + }; + + scale.invertExtent = function(y) { + var i = range.indexOf(y); + return [domain[i - 1], domain[i]]; + }; + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + scale.copy = function() { + return threshold() + .domain(domain) + .range(range) + .unknown(unknown); + }; + + return initRange.apply(scale, arguments); +} + +const t0 = new Date, t1 = new Date; + +function timeInterval(floori, offseti, count, field) { + + function interval(date) { + return floori(date = arguments.length === 0 ? new Date : new Date(+date)), date; + } + + interval.floor = (date) => { + return floori(date = new Date(+date)), date; + }; + + interval.ceil = (date) => { + return floori(date = new Date(date - 1)), offseti(date, 1), floori(date), date; + }; + + interval.round = (date) => { + const d0 = interval(date), d1 = interval.ceil(date); + return date - d0 < d1 - date ? d0 : d1; + }; + + interval.offset = (date, step) => { + return offseti(date = new Date(+date), step == null ? 1 : Math.floor(step)), date; + }; + + interval.range = (start, stop, step) => { + const range = []; + start = interval.ceil(start); + step = step == null ? 1 : Math.floor(step); + if (!(start < stop) || !(step > 0)) return range; // also handles Invalid Date + let previous; + do range.push(previous = new Date(+start)), offseti(start, step), floori(start); + while (previous < start && start < stop); + return range; + }; + + interval.filter = (test) => { + return timeInterval((date) => { + if (date >= date) while (floori(date), !test(date)) date.setTime(date - 1); + }, (date, step) => { + if (date >= date) { + if (step < 0) while (++step <= 0) { + while (offseti(date, -1), !test(date)) {} // eslint-disable-line no-empty + } else while (--step >= 0) { + while (offseti(date, +1), !test(date)) {} // eslint-disable-line no-empty + } + } + }); + }; + + if (count) { + interval.count = (start, end) => { + t0.setTime(+start), t1.setTime(+end); + floori(t0), floori(t1); + return Math.floor(count(t0, t1)); + }; + + interval.every = (step) => { + step = Math.floor(step); + return !isFinite(step) || !(step > 0) ? null + : !(step > 1) ? interval + : interval.filter(field + ? (d) => field(d) % step === 0 + : (d) => interval.count(0, d) % step === 0); + }; + } + + return interval; +} + +const millisecond = timeInterval(() => { + // noop +}, (date, step) => { + date.setTime(+date + step); +}, (start, end) => { + return end - start; +}); + +// An optimized implementation for this simple case. +millisecond.every = (k) => { + k = Math.floor(k); + if (!isFinite(k) || !(k > 0)) return null; + if (!(k > 1)) return millisecond; + return timeInterval((date) => { + date.setTime(Math.floor(date / k) * k); + }, (date, step) => { + date.setTime(+date + step * k); + }, (start, end) => { + return (end - start) / k; + }); +}; + +const milliseconds = millisecond.range; + +const durationSecond = 1000; +const durationMinute = durationSecond * 60; +const durationHour = durationMinute * 60; +const durationDay = durationHour * 24; +const durationWeek = durationDay * 7; +const durationMonth = durationDay * 30; +const durationYear = durationDay * 365; + +const second = timeInterval((date) => { + date.setTime(date - date.getMilliseconds()); +}, (date, step) => { + date.setTime(+date + step * durationSecond); +}, (start, end) => { + return (end - start) / durationSecond; +}, (date) => { + return date.getUTCSeconds(); +}); + +const seconds = second.range; + +const timeMinute = timeInterval((date) => { + date.setTime(date - date.getMilliseconds() - date.getSeconds() * durationSecond); +}, (date, step) => { + date.setTime(+date + step * durationMinute); +}, (start, end) => { + return (end - start) / durationMinute; +}, (date) => { + return date.getMinutes(); +}); + +const timeMinutes = timeMinute.range; + +const utcMinute = timeInterval((date) => { + date.setUTCSeconds(0, 0); +}, (date, step) => { + date.setTime(+date + step * durationMinute); +}, (start, end) => { + return (end - start) / durationMinute; +}, (date) => { + return date.getUTCMinutes(); +}); + +const utcMinutes = utcMinute.range; + +const timeHour = timeInterval((date) => { + date.setTime(date - date.getMilliseconds() - date.getSeconds() * durationSecond - date.getMinutes() * durationMinute); +}, (date, step) => { + date.setTime(+date + step * durationHour); +}, (start, end) => { + return (end - start) / durationHour; +}, (date) => { + return date.getHours(); +}); + +const timeHours = timeHour.range; + +const utcHour = timeInterval((date) => { + date.setUTCMinutes(0, 0, 0); +}, (date, step) => { + date.setTime(+date + step * durationHour); +}, (start, end) => { + return (end - start) / durationHour; +}, (date) => { + return date.getUTCHours(); +}); + +const utcHours = utcHour.range; + +const timeDay = timeInterval( + date => date.setHours(0, 0, 0, 0), + (date, step) => date.setDate(date.getDate() + step), + (start, end) => (end - start - (end.getTimezoneOffset() - start.getTimezoneOffset()) * durationMinute) / durationDay, + date => date.getDate() - 1 +); + +const timeDays = timeDay.range; + +const utcDay = timeInterval((date) => { + date.setUTCHours(0, 0, 0, 0); +}, (date, step) => { + date.setUTCDate(date.getUTCDate() + step); +}, (start, end) => { + return (end - start) / durationDay; +}, (date) => { + return date.getUTCDate() - 1; +}); + +const utcDays = utcDay.range; + +const unixDay = timeInterval((date) => { + date.setUTCHours(0, 0, 0, 0); +}, (date, step) => { + date.setUTCDate(date.getUTCDate() + step); +}, (start, end) => { + return (end - start) / durationDay; +}, (date) => { + return Math.floor(date / durationDay); +}); + +const unixDays = unixDay.range; + +function timeWeekday(i) { + return timeInterval((date) => { + date.setDate(date.getDate() - (date.getDay() + 7 - i) % 7); + date.setHours(0, 0, 0, 0); + }, (date, step) => { + date.setDate(date.getDate() + step * 7); + }, (start, end) => { + return (end - start - (end.getTimezoneOffset() - start.getTimezoneOffset()) * durationMinute) / durationWeek; + }); +} + +const timeSunday = timeWeekday(0); +const timeMonday = timeWeekday(1); +const timeTuesday = timeWeekday(2); +const timeWednesday = timeWeekday(3); +const timeThursday = timeWeekday(4); +const timeFriday = timeWeekday(5); +const timeSaturday = timeWeekday(6); + +const timeSundays = timeSunday.range; +const timeMondays = timeMonday.range; +const timeTuesdays = timeTuesday.range; +const timeWednesdays = timeWednesday.range; +const timeThursdays = timeThursday.range; +const timeFridays = timeFriday.range; +const timeSaturdays = timeSaturday.range; + +function utcWeekday(i) { + return timeInterval((date) => { + date.setUTCDate(date.getUTCDate() - (date.getUTCDay() + 7 - i) % 7); + date.setUTCHours(0, 0, 0, 0); + }, (date, step) => { + date.setUTCDate(date.getUTCDate() + step * 7); + }, (start, end) => { + return (end - start) / durationWeek; + }); +} + +const utcSunday = utcWeekday(0); +const utcMonday = utcWeekday(1); +const utcTuesday = utcWeekday(2); +const utcWednesday = utcWeekday(3); +const utcThursday = utcWeekday(4); +const utcFriday = utcWeekday(5); +const utcSaturday = utcWeekday(6); + +const utcSundays = utcSunday.range; +const utcMondays = utcMonday.range; +const utcTuesdays = utcTuesday.range; +const utcWednesdays = utcWednesday.range; +const utcThursdays = utcThursday.range; +const utcFridays = utcFriday.range; +const utcSaturdays = utcSaturday.range; + +const timeMonth = timeInterval((date) => { + date.setDate(1); + date.setHours(0, 0, 0, 0); +}, (date, step) => { + date.setMonth(date.getMonth() + step); +}, (start, end) => { + return end.getMonth() - start.getMonth() + (end.getFullYear() - start.getFullYear()) * 12; +}, (date) => { + return date.getMonth(); +}); + +const timeMonths = timeMonth.range; + +const utcMonth = timeInterval((date) => { + date.setUTCDate(1); + date.setUTCHours(0, 0, 0, 0); +}, (date, step) => { + date.setUTCMonth(date.getUTCMonth() + step); +}, (start, end) => { + return end.getUTCMonth() - start.getUTCMonth() + (end.getUTCFullYear() - start.getUTCFullYear()) * 12; +}, (date) => { + return date.getUTCMonth(); +}); + +const utcMonths = utcMonth.range; + +const timeYear = timeInterval((date) => { + date.setMonth(0, 1); + date.setHours(0, 0, 0, 0); +}, (date, step) => { + date.setFullYear(date.getFullYear() + step); +}, (start, end) => { + return end.getFullYear() - start.getFullYear(); +}, (date) => { + return date.getFullYear(); +}); + +// An optimized implementation for this simple case. +timeYear.every = (k) => { + return !isFinite(k = Math.floor(k)) || !(k > 0) ? null : timeInterval((date) => { + date.setFullYear(Math.floor(date.getFullYear() / k) * k); + date.setMonth(0, 1); + date.setHours(0, 0, 0, 0); + }, (date, step) => { + date.setFullYear(date.getFullYear() + step * k); + }); +}; + +const timeYears = timeYear.range; + +const utcYear = timeInterval((date) => { + date.setUTCMonth(0, 1); + date.setUTCHours(0, 0, 0, 0); +}, (date, step) => { + date.setUTCFullYear(date.getUTCFullYear() + step); +}, (start, end) => { + return end.getUTCFullYear() - start.getUTCFullYear(); +}, (date) => { + return date.getUTCFullYear(); +}); + +// An optimized implementation for this simple case. +utcYear.every = (k) => { + return !isFinite(k = Math.floor(k)) || !(k > 0) ? null : timeInterval((date) => { + date.setUTCFullYear(Math.floor(date.getUTCFullYear() / k) * k); + date.setUTCMonth(0, 1); + date.setUTCHours(0, 0, 0, 0); + }, (date, step) => { + date.setUTCFullYear(date.getUTCFullYear() + step * k); + }); +}; + +const utcYears = utcYear.range; + +function ticker(year, month, week, day, hour, minute) { + + const tickIntervals = [ + [second, 1, durationSecond], + [second, 5, 5 * durationSecond], + [second, 15, 15 * durationSecond], + [second, 30, 30 * durationSecond], + [minute, 1, durationMinute], + [minute, 5, 5 * durationMinute], + [minute, 15, 15 * durationMinute], + [minute, 30, 30 * durationMinute], + [ hour, 1, durationHour ], + [ hour, 3, 3 * durationHour ], + [ hour, 6, 6 * durationHour ], + [ hour, 12, 12 * durationHour ], + [ day, 1, durationDay ], + [ day, 2, 2 * durationDay ], + [ week, 1, durationWeek ], + [ month, 1, durationMonth ], + [ month, 3, 3 * durationMonth ], + [ year, 1, durationYear ] + ]; + + function ticks(start, stop, count) { + const reverse = stop < start; + if (reverse) [start, stop] = [stop, start]; + const interval = count && typeof count.range === "function" ? count : tickInterval(start, stop, count); + const ticks = interval ? interval.range(start, +stop + 1) : []; // inclusive stop + return reverse ? ticks.reverse() : ticks; + } + + function tickInterval(start, stop, count) { + const target = Math.abs(stop - start) / count; + const i = bisector(([,, step]) => step).right(tickIntervals, target); + if (i === tickIntervals.length) return year.every(tickStep(start / durationYear, stop / durationYear, count)); + if (i === 0) return millisecond.every(Math.max(tickStep(start, stop, count), 1)); + const [t, step] = tickIntervals[target / tickIntervals[i - 1][2] < tickIntervals[i][2] / target ? i - 1 : i]; + return t.every(step); + } + + return [ticks, tickInterval]; +} + +const [utcTicks, utcTickInterval] = ticker(utcYear, utcMonth, utcSunday, unixDay, utcHour, utcMinute); +const [timeTicks, timeTickInterval] = ticker(timeYear, timeMonth, timeSunday, timeDay, timeHour, timeMinute); + +function localDate(d) { + if (0 <= d.y && d.y < 100) { + var date = new Date(-1, d.m, d.d, d.H, d.M, d.S, d.L); + date.setFullYear(d.y); + return date; + } + return new Date(d.y, d.m, d.d, d.H, d.M, d.S, d.L); +} + +function utcDate(d) { + if (0 <= d.y && d.y < 100) { + var date = new Date(Date.UTC(-1, d.m, d.d, d.H, d.M, d.S, d.L)); + date.setUTCFullYear(d.y); + return date; + } + return new Date(Date.UTC(d.y, d.m, d.d, d.H, d.M, d.S, d.L)); +} + +function newDate(y, m, d) { + return {y: y, m: m, d: d, H: 0, M: 0, S: 0, L: 0}; +} + +function formatLocale(locale) { + var locale_dateTime = locale.dateTime, + locale_date = locale.date, + locale_time = locale.time, + locale_periods = locale.periods, + locale_weekdays = locale.days, + locale_shortWeekdays = locale.shortDays, + locale_months = locale.months, + locale_shortMonths = locale.shortMonths; + + var periodRe = formatRe(locale_periods), + periodLookup = formatLookup(locale_periods), + weekdayRe = formatRe(locale_weekdays), + weekdayLookup = formatLookup(locale_weekdays), + shortWeekdayRe = formatRe(locale_shortWeekdays), + shortWeekdayLookup = formatLookup(locale_shortWeekdays), + monthRe = formatRe(locale_months), + monthLookup = formatLookup(locale_months), + shortMonthRe = formatRe(locale_shortMonths), + shortMonthLookup = formatLookup(locale_shortMonths); + + var formats = { + "a": formatShortWeekday, + "A": formatWeekday, + "b": formatShortMonth, + "B": formatMonth, + "c": null, + "d": formatDayOfMonth, + "e": formatDayOfMonth, + "f": formatMicroseconds, + "g": formatYearISO, + "G": formatFullYearISO, + "H": formatHour24, + "I": formatHour12, + "j": formatDayOfYear, + "L": formatMilliseconds, + "m": formatMonthNumber, + "M": formatMinutes, + "p": formatPeriod, + "q": formatQuarter, + "Q": formatUnixTimestamp, + "s": formatUnixTimestampSeconds, + "S": formatSeconds, + "u": formatWeekdayNumberMonday, + "U": formatWeekNumberSunday, + "V": formatWeekNumberISO, + "w": formatWeekdayNumberSunday, + "W": formatWeekNumberMonday, + "x": null, + "X": null, + "y": formatYear, + "Y": formatFullYear, + "Z": formatZone, + "%": formatLiteralPercent + }; + + var utcFormats = { + "a": formatUTCShortWeekday, + "A": formatUTCWeekday, + "b": formatUTCShortMonth, + "B": formatUTCMonth, + "c": null, + "d": formatUTCDayOfMonth, + "e": formatUTCDayOfMonth, + "f": formatUTCMicroseconds, + "g": formatUTCYearISO, + "G": formatUTCFullYearISO, + "H": formatUTCHour24, + "I": formatUTCHour12, + "j": formatUTCDayOfYear, + "L": formatUTCMilliseconds, + "m": formatUTCMonthNumber, + "M": formatUTCMinutes, + "p": formatUTCPeriod, + "q": formatUTCQuarter, + "Q": formatUnixTimestamp, + "s": formatUnixTimestampSeconds, + "S": formatUTCSeconds, + "u": formatUTCWeekdayNumberMonday, + "U": formatUTCWeekNumberSunday, + "V": formatUTCWeekNumberISO, + "w": formatUTCWeekdayNumberSunday, + "W": formatUTCWeekNumberMonday, + "x": null, + "X": null, + "y": formatUTCYear, + "Y": formatUTCFullYear, + "Z": formatUTCZone, + "%": formatLiteralPercent + }; + + var parses = { + "a": parseShortWeekday, + "A": parseWeekday, + "b": parseShortMonth, + "B": parseMonth, + "c": parseLocaleDateTime, + "d": parseDayOfMonth, + "e": parseDayOfMonth, + "f": parseMicroseconds, + "g": parseYear, + "G": parseFullYear, + "H": parseHour24, + "I": parseHour24, + "j": parseDayOfYear, + "L": parseMilliseconds, + "m": parseMonthNumber, + "M": parseMinutes, + "p": parsePeriod, + "q": parseQuarter, + "Q": parseUnixTimestamp, + "s": parseUnixTimestampSeconds, + "S": parseSeconds, + "u": parseWeekdayNumberMonday, + "U": parseWeekNumberSunday, + "V": parseWeekNumberISO, + "w": parseWeekdayNumberSunday, + "W": parseWeekNumberMonday, + "x": parseLocaleDate, + "X": parseLocaleTime, + "y": parseYear, + "Y": parseFullYear, + "Z": parseZone, + "%": parseLiteralPercent + }; + + // These recursive directive definitions must be deferred. + formats.x = newFormat(locale_date, formats); + formats.X = newFormat(locale_time, formats); + formats.c = newFormat(locale_dateTime, formats); + utcFormats.x = newFormat(locale_date, utcFormats); + utcFormats.X = newFormat(locale_time, utcFormats); + utcFormats.c = newFormat(locale_dateTime, utcFormats); + + function newFormat(specifier, formats) { + return function(date) { + var string = [], + i = -1, + j = 0, + n = specifier.length, + c, + pad, + format; + + if (!(date instanceof Date)) date = new Date(+date); + + while (++i < n) { + if (specifier.charCodeAt(i) === 37) { + string.push(specifier.slice(j, i)); + if ((pad = pads[c = specifier.charAt(++i)]) != null) c = specifier.charAt(++i); + else pad = c === "e" ? " " : "0"; + if (format = formats[c]) c = format(date, pad); + string.push(c); + j = i + 1; + } + } + + string.push(specifier.slice(j, i)); + return string.join(""); + }; + } + + function newParse(specifier, Z) { + return function(string) { + var d = newDate(1900, undefined, 1), + i = parseSpecifier(d, specifier, string += "", 0), + week, day; + if (i != string.length) return null; + + // If a UNIX timestamp is specified, return it. + if ("Q" in d) return new Date(d.Q); + if ("s" in d) return new Date(d.s * 1000 + ("L" in d ? d.L : 0)); + + // If this is utcParse, never use the local timezone. + if (Z && !("Z" in d)) d.Z = 0; + + // The am-pm flag is 0 for AM, and 1 for PM. + if ("p" in d) d.H = d.H % 12 + d.p * 12; + + // If the month was not specified, inherit from the quarter. + if (d.m === undefined) d.m = "q" in d ? d.q : 0; + + // Convert day-of-week and week-of-year to day-of-year. + if ("V" in d) { + if (d.V < 1 || d.V > 53) return null; + if (!("w" in d)) d.w = 1; + if ("Z" in d) { + week = utcDate(newDate(d.y, 0, 1)), day = week.getUTCDay(); + week = day > 4 || day === 0 ? utcMonday.ceil(week) : utcMonday(week); + week = utcDay.offset(week, (d.V - 1) * 7); + d.y = week.getUTCFullYear(); + d.m = week.getUTCMonth(); + d.d = week.getUTCDate() + (d.w + 6) % 7; + } else { + week = localDate(newDate(d.y, 0, 1)), day = week.getDay(); + week = day > 4 || day === 0 ? timeMonday.ceil(week) : timeMonday(week); + week = timeDay.offset(week, (d.V - 1) * 7); + d.y = week.getFullYear(); + d.m = week.getMonth(); + d.d = week.getDate() + (d.w + 6) % 7; + } + } else if ("W" in d || "U" in d) { + if (!("w" in d)) d.w = "u" in d ? d.u % 7 : "W" in d ? 1 : 0; + day = "Z" in d ? utcDate(newDate(d.y, 0, 1)).getUTCDay() : localDate(newDate(d.y, 0, 1)).getDay(); + d.m = 0; + d.d = "W" in d ? (d.w + 6) % 7 + d.W * 7 - (day + 5) % 7 : d.w + d.U * 7 - (day + 6) % 7; + } + + // If a time zone is specified, all fields are interpreted as UTC and then + // offset according to the specified time zone. + if ("Z" in d) { + d.H += d.Z / 100 | 0; + d.M += d.Z % 100; + return utcDate(d); + } + + // Otherwise, all fields are in local time. + return localDate(d); + }; + } + + function parseSpecifier(d, specifier, string, j) { + var i = 0, + n = specifier.length, + m = string.length, + c, + parse; + + while (i < n) { + if (j >= m) return -1; + c = specifier.charCodeAt(i++); + if (c === 37) { + c = specifier.charAt(i++); + parse = parses[c in pads ? specifier.charAt(i++) : c]; + if (!parse || ((j = parse(d, string, j)) < 0)) return -1; + } else if (c != string.charCodeAt(j++)) { + return -1; + } + } + + return j; + } + + function parsePeriod(d, string, i) { + var n = periodRe.exec(string.slice(i)); + return n ? (d.p = periodLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseShortWeekday(d, string, i) { + var n = shortWeekdayRe.exec(string.slice(i)); + return n ? (d.w = shortWeekdayLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseWeekday(d, string, i) { + var n = weekdayRe.exec(string.slice(i)); + return n ? (d.w = weekdayLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseShortMonth(d, string, i) { + var n = shortMonthRe.exec(string.slice(i)); + return n ? (d.m = shortMonthLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseMonth(d, string, i) { + var n = monthRe.exec(string.slice(i)); + return n ? (d.m = monthLookup.get(n[0].toLowerCase()), i + n[0].length) : -1; + } + + function parseLocaleDateTime(d, string, i) { + return parseSpecifier(d, locale_dateTime, string, i); + } + + function parseLocaleDate(d, string, i) { + return parseSpecifier(d, locale_date, string, i); + } + + function parseLocaleTime(d, string, i) { + return parseSpecifier(d, locale_time, string, i); + } + + function formatShortWeekday(d) { + return locale_shortWeekdays[d.getDay()]; + } + + function formatWeekday(d) { + return locale_weekdays[d.getDay()]; + } + + function formatShortMonth(d) { + return locale_shortMonths[d.getMonth()]; + } + + function formatMonth(d) { + return locale_months[d.getMonth()]; + } + + function formatPeriod(d) { + return locale_periods[+(d.getHours() >= 12)]; + } + + function formatQuarter(d) { + return 1 + ~~(d.getMonth() / 3); + } + + function formatUTCShortWeekday(d) { + return locale_shortWeekdays[d.getUTCDay()]; + } + + function formatUTCWeekday(d) { + return locale_weekdays[d.getUTCDay()]; + } + + function formatUTCShortMonth(d) { + return locale_shortMonths[d.getUTCMonth()]; + } + + function formatUTCMonth(d) { + return locale_months[d.getUTCMonth()]; + } + + function formatUTCPeriod(d) { + return locale_periods[+(d.getUTCHours() >= 12)]; + } + + function formatUTCQuarter(d) { + return 1 + ~~(d.getUTCMonth() / 3); + } + + return { + format: function(specifier) { + var f = newFormat(specifier += "", formats); + f.toString = function() { return specifier; }; + return f; + }, + parse: function(specifier) { + var p = newParse(specifier += "", false); + p.toString = function() { return specifier; }; + return p; + }, + utcFormat: function(specifier) { + var f = newFormat(specifier += "", utcFormats); + f.toString = function() { return specifier; }; + return f; + }, + utcParse: function(specifier) { + var p = newParse(specifier += "", true); + p.toString = function() { return specifier; }; + return p; + } + }; +} + +var pads = {"-": "", "_": " ", "0": "0"}, + numberRe = /^\s*\d+/, // note: ignores next directive + percentRe = /^%/, + requoteRe = /[\\^$*+?|[\]().{}]/g; + +function pad(value, fill, width) { + var sign = value < 0 ? "-" : "", + string = (sign ? -value : value) + "", + length = string.length; + return sign + (length < width ? new Array(width - length + 1).join(fill) + string : string); +} + +function requote(s) { + return s.replace(requoteRe, "\\$&"); +} + +function formatRe(names) { + return new RegExp("^(?:" + names.map(requote).join("|") + ")", "i"); +} + +function formatLookup(names) { + return new Map(names.map((name, i) => [name.toLowerCase(), i])); +} + +function parseWeekdayNumberSunday(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 1)); + return n ? (d.w = +n[0], i + n[0].length) : -1; +} + +function parseWeekdayNumberMonday(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 1)); + return n ? (d.u = +n[0], i + n[0].length) : -1; +} + +function parseWeekNumberSunday(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.U = +n[0], i + n[0].length) : -1; +} + +function parseWeekNumberISO(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.V = +n[0], i + n[0].length) : -1; +} + +function parseWeekNumberMonday(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.W = +n[0], i + n[0].length) : -1; +} + +function parseFullYear(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 4)); + return n ? (d.y = +n[0], i + n[0].length) : -1; +} + +function parseYear(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.y = +n[0] + (+n[0] > 68 ? 1900 : 2000), i + n[0].length) : -1; +} + +function parseZone(d, string, i) { + var n = /^(Z)|([+-]\d\d)(?::?(\d\d))?/.exec(string.slice(i, i + 6)); + return n ? (d.Z = n[1] ? 0 : -(n[2] + (n[3] || "00")), i + n[0].length) : -1; +} + +function parseQuarter(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 1)); + return n ? (d.q = n[0] * 3 - 3, i + n[0].length) : -1; +} + +function parseMonthNumber(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.m = n[0] - 1, i + n[0].length) : -1; +} + +function parseDayOfMonth(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.d = +n[0], i + n[0].length) : -1; +} + +function parseDayOfYear(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 3)); + return n ? (d.m = 0, d.d = +n[0], i + n[0].length) : -1; +} + +function parseHour24(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.H = +n[0], i + n[0].length) : -1; +} + +function parseMinutes(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.M = +n[0], i + n[0].length) : -1; +} + +function parseSeconds(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 2)); + return n ? (d.S = +n[0], i + n[0].length) : -1; +} + +function parseMilliseconds(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 3)); + return n ? (d.L = +n[0], i + n[0].length) : -1; +} + +function parseMicroseconds(d, string, i) { + var n = numberRe.exec(string.slice(i, i + 6)); + return n ? (d.L = Math.floor(n[0] / 1000), i + n[0].length) : -1; +} + +function parseLiteralPercent(d, string, i) { + var n = percentRe.exec(string.slice(i, i + 1)); + return n ? i + n[0].length : -1; +} + +function parseUnixTimestamp(d, string, i) { + var n = numberRe.exec(string.slice(i)); + return n ? (d.Q = +n[0], i + n[0].length) : -1; +} + +function parseUnixTimestampSeconds(d, string, i) { + var n = numberRe.exec(string.slice(i)); + return n ? (d.s = +n[0], i + n[0].length) : -1; +} + +function formatDayOfMonth(d, p) { + return pad(d.getDate(), p, 2); +} + +function formatHour24(d, p) { + return pad(d.getHours(), p, 2); +} + +function formatHour12(d, p) { + return pad(d.getHours() % 12 || 12, p, 2); +} + +function formatDayOfYear(d, p) { + return pad(1 + timeDay.count(timeYear(d), d), p, 3); +} + +function formatMilliseconds(d, p) { + return pad(d.getMilliseconds(), p, 3); +} + +function formatMicroseconds(d, p) { + return formatMilliseconds(d, p) + "000"; +} + +function formatMonthNumber(d, p) { + return pad(d.getMonth() + 1, p, 2); +} + +function formatMinutes(d, p) { + return pad(d.getMinutes(), p, 2); +} + +function formatSeconds(d, p) { + return pad(d.getSeconds(), p, 2); +} + +function formatWeekdayNumberMonday(d) { + var day = d.getDay(); + return day === 0 ? 7 : day; +} + +function formatWeekNumberSunday(d, p) { + return pad(timeSunday.count(timeYear(d) - 1, d), p, 2); +} + +function dISO(d) { + var day = d.getDay(); + return (day >= 4 || day === 0) ? timeThursday(d) : timeThursday.ceil(d); +} + +function formatWeekNumberISO(d, p) { + d = dISO(d); + return pad(timeThursday.count(timeYear(d), d) + (timeYear(d).getDay() === 4), p, 2); +} + +function formatWeekdayNumberSunday(d) { + return d.getDay(); +} + +function formatWeekNumberMonday(d, p) { + return pad(timeMonday.count(timeYear(d) - 1, d), p, 2); +} + +function formatYear(d, p) { + return pad(d.getFullYear() % 100, p, 2); +} + +function formatYearISO(d, p) { + d = dISO(d); + return pad(d.getFullYear() % 100, p, 2); +} + +function formatFullYear(d, p) { + return pad(d.getFullYear() % 10000, p, 4); +} + +function formatFullYearISO(d, p) { + var day = d.getDay(); + d = (day >= 4 || day === 0) ? timeThursday(d) : timeThursday.ceil(d); + return pad(d.getFullYear() % 10000, p, 4); +} + +function formatZone(d) { + var z = d.getTimezoneOffset(); + return (z > 0 ? "-" : (z *= -1, "+")) + + pad(z / 60 | 0, "0", 2) + + pad(z % 60, "0", 2); +} + +function formatUTCDayOfMonth(d, p) { + return pad(d.getUTCDate(), p, 2); +} + +function formatUTCHour24(d, p) { + return pad(d.getUTCHours(), p, 2); +} + +function formatUTCHour12(d, p) { + return pad(d.getUTCHours() % 12 || 12, p, 2); +} + +function formatUTCDayOfYear(d, p) { + return pad(1 + utcDay.count(utcYear(d), d), p, 3); +} + +function formatUTCMilliseconds(d, p) { + return pad(d.getUTCMilliseconds(), p, 3); +} + +function formatUTCMicroseconds(d, p) { + return formatUTCMilliseconds(d, p) + "000"; +} + +function formatUTCMonthNumber(d, p) { + return pad(d.getUTCMonth() + 1, p, 2); +} + +function formatUTCMinutes(d, p) { + return pad(d.getUTCMinutes(), p, 2); +} + +function formatUTCSeconds(d, p) { + return pad(d.getUTCSeconds(), p, 2); +} + +function formatUTCWeekdayNumberMonday(d) { + var dow = d.getUTCDay(); + return dow === 0 ? 7 : dow; +} + +function formatUTCWeekNumberSunday(d, p) { + return pad(utcSunday.count(utcYear(d) - 1, d), p, 2); +} + +function UTCdISO(d) { + var day = d.getUTCDay(); + return (day >= 4 || day === 0) ? utcThursday(d) : utcThursday.ceil(d); +} + +function formatUTCWeekNumberISO(d, p) { + d = UTCdISO(d); + return pad(utcThursday.count(utcYear(d), d) + (utcYear(d).getUTCDay() === 4), p, 2); +} + +function formatUTCWeekdayNumberSunday(d) { + return d.getUTCDay(); +} + +function formatUTCWeekNumberMonday(d, p) { + return pad(utcMonday.count(utcYear(d) - 1, d), p, 2); +} + +function formatUTCYear(d, p) { + return pad(d.getUTCFullYear() % 100, p, 2); +} + +function formatUTCYearISO(d, p) { + d = UTCdISO(d); + return pad(d.getUTCFullYear() % 100, p, 2); +} + +function formatUTCFullYear(d, p) { + return pad(d.getUTCFullYear() % 10000, p, 4); +} + +function formatUTCFullYearISO(d, p) { + var day = d.getUTCDay(); + d = (day >= 4 || day === 0) ? utcThursday(d) : utcThursday.ceil(d); + return pad(d.getUTCFullYear() % 10000, p, 4); +} + +function formatUTCZone() { + return "+0000"; +} + +function formatLiteralPercent() { + return "%"; +} + +function formatUnixTimestamp(d) { + return +d; +} + +function formatUnixTimestampSeconds(d) { + return Math.floor(+d / 1000); +} + +var locale; +exports.timeFormat = void 0; +exports.timeParse = void 0; +exports.utcFormat = void 0; +exports.utcParse = void 0; + +defaultLocale({ + dateTime: "%x, %X", + date: "%-m/%-d/%Y", + time: "%-I:%M:%S %p", + periods: ["AM", "PM"], + days: ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"], + shortDays: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"], + months: ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"], + shortMonths: ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"] +}); + +function defaultLocale(definition) { + locale = formatLocale(definition); + exports.timeFormat = locale.format; + exports.timeParse = locale.parse; + exports.utcFormat = locale.utcFormat; + exports.utcParse = locale.utcParse; + return locale; +} + +var isoSpecifier = "%Y-%m-%dT%H:%M:%S.%LZ"; + +function formatIsoNative(date) { + return date.toISOString(); +} + +var formatIso = Date.prototype.toISOString + ? formatIsoNative + : exports.utcFormat(isoSpecifier); + +var formatIso$1 = formatIso; + +function parseIsoNative(string) { + var date = new Date(string); + return isNaN(date) ? null : date; +} + +var parseIso = +new Date("2000-01-01T00:00:00.000Z") + ? parseIsoNative + : exports.utcParse(isoSpecifier); + +var parseIso$1 = parseIso; + +function date(t) { + return new Date(t); +} + +function number(t) { + return t instanceof Date ? +t : +new Date(+t); +} + +function calendar(ticks, tickInterval, year, month, week, day, hour, minute, second, format) { + var scale = continuous(), + invert = scale.invert, + domain = scale.domain; + + var formatMillisecond = format(".%L"), + formatSecond = format(":%S"), + formatMinute = format("%I:%M"), + formatHour = format("%I %p"), + formatDay = format("%a %d"), + formatWeek = format("%b %d"), + formatMonth = format("%B"), + formatYear = format("%Y"); + + function tickFormat(date) { + return (second(date) < date ? formatMillisecond + : minute(date) < date ? formatSecond + : hour(date) < date ? formatMinute + : day(date) < date ? formatHour + : month(date) < date ? (week(date) < date ? formatDay : formatWeek) + : year(date) < date ? formatMonth + : formatYear)(date); + } + + scale.invert = function(y) { + return new Date(invert(y)); + }; + + scale.domain = function(_) { + return arguments.length ? domain(Array.from(_, number)) : domain().map(date); + }; + + scale.ticks = function(interval) { + var d = domain(); + return ticks(d[0], d[d.length - 1], interval == null ? 10 : interval); + }; + + scale.tickFormat = function(count, specifier) { + return specifier == null ? tickFormat : format(specifier); + }; + + scale.nice = function(interval) { + var d = domain(); + if (!interval || typeof interval.range !== "function") interval = tickInterval(d[0], d[d.length - 1], interval == null ? 10 : interval); + return interval ? domain(nice(d, interval)) : scale; + }; + + scale.copy = function() { + return copy$1(scale, calendar(ticks, tickInterval, year, month, week, day, hour, minute, second, format)); + }; + + return scale; +} + +function time() { + return initRange.apply(calendar(timeTicks, timeTickInterval, timeYear, timeMonth, timeSunday, timeDay, timeHour, timeMinute, second, exports.timeFormat).domain([new Date(2000, 0, 1), new Date(2000, 0, 2)]), arguments); +} + +function utcTime() { + return initRange.apply(calendar(utcTicks, utcTickInterval, utcYear, utcMonth, utcSunday, utcDay, utcHour, utcMinute, second, exports.utcFormat).domain([Date.UTC(2000, 0, 1), Date.UTC(2000, 0, 2)]), arguments); +} + +function transformer$1() { + var x0 = 0, + x1 = 1, + t0, + t1, + k10, + transform, + interpolator = identity$3, + clamp = false, + unknown; + + function scale(x) { + return x == null || isNaN(x = +x) ? unknown : interpolator(k10 === 0 ? 0.5 : (x = (transform(x) - t0) * k10, clamp ? Math.max(0, Math.min(1, x)) : x)); + } + + scale.domain = function(_) { + return arguments.length ? ([x0, x1] = _, t0 = transform(x0 = +x0), t1 = transform(x1 = +x1), k10 = t0 === t1 ? 0 : 1 / (t1 - t0), scale) : [x0, x1]; + }; + + scale.clamp = function(_) { + return arguments.length ? (clamp = !!_, scale) : clamp; + }; + + scale.interpolator = function(_) { + return arguments.length ? (interpolator = _, scale) : interpolator; + }; + + function range(interpolate) { + return function(_) { + var r0, r1; + return arguments.length ? ([r0, r1] = _, interpolator = interpolate(r0, r1), scale) : [interpolator(0), interpolator(1)]; + }; + } + + scale.range = range(interpolate$2); + + scale.rangeRound = range(interpolateRound); + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + return function(t) { + transform = t, t0 = t(x0), t1 = t(x1), k10 = t0 === t1 ? 0 : 1 / (t1 - t0); + return scale; + }; +} + +function copy(source, target) { + return target + .domain(source.domain()) + .interpolator(source.interpolator()) + .clamp(source.clamp()) + .unknown(source.unknown()); +} + +function sequential() { + var scale = linearish(transformer$1()(identity$3)); + + scale.copy = function() { + return copy(scale, sequential()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function sequentialLog() { + var scale = loggish(transformer$1()).domain([1, 10]); + + scale.copy = function() { + return copy(scale, sequentialLog()).base(scale.base()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function sequentialSymlog() { + var scale = symlogish(transformer$1()); + + scale.copy = function() { + return copy(scale, sequentialSymlog()).constant(scale.constant()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function sequentialPow() { + var scale = powish(transformer$1()); + + scale.copy = function() { + return copy(scale, sequentialPow()).exponent(scale.exponent()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function sequentialSqrt() { + return sequentialPow.apply(null, arguments).exponent(0.5); +} + +function sequentialQuantile() { + var domain = [], + interpolator = identity$3; + + function scale(x) { + if (x != null && !isNaN(x = +x)) return interpolator((bisect(domain, x, 1) - 1) / (domain.length - 1)); + } + + scale.domain = function(_) { + if (!arguments.length) return domain.slice(); + domain = []; + for (let d of _) if (d != null && !isNaN(d = +d)) domain.push(d); + domain.sort(ascending$3); + return scale; + }; + + scale.interpolator = function(_) { + return arguments.length ? (interpolator = _, scale) : interpolator; + }; + + scale.range = function() { + return domain.map((d, i) => interpolator(i / (domain.length - 1))); + }; + + scale.quantiles = function(n) { + return Array.from({length: n + 1}, (_, i) => quantile$1(domain, i / n)); + }; + + scale.copy = function() { + return sequentialQuantile(interpolator).domain(domain); + }; + + return initInterpolator.apply(scale, arguments); +} + +function transformer() { + var x0 = 0, + x1 = 0.5, + x2 = 1, + s = 1, + t0, + t1, + t2, + k10, + k21, + interpolator = identity$3, + transform, + clamp = false, + unknown; + + function scale(x) { + return isNaN(x = +x) ? unknown : (x = 0.5 + ((x = +transform(x)) - t1) * (s * x < s * t1 ? k10 : k21), interpolator(clamp ? Math.max(0, Math.min(1, x)) : x)); + } + + scale.domain = function(_) { + return arguments.length ? ([x0, x1, x2] = _, t0 = transform(x0 = +x0), t1 = transform(x1 = +x1), t2 = transform(x2 = +x2), k10 = t0 === t1 ? 0 : 0.5 / (t1 - t0), k21 = t1 === t2 ? 0 : 0.5 / (t2 - t1), s = t1 < t0 ? -1 : 1, scale) : [x0, x1, x2]; + }; + + scale.clamp = function(_) { + return arguments.length ? (clamp = !!_, scale) : clamp; + }; + + scale.interpolator = function(_) { + return arguments.length ? (interpolator = _, scale) : interpolator; + }; + + function range(interpolate) { + return function(_) { + var r0, r1, r2; + return arguments.length ? ([r0, r1, r2] = _, interpolator = piecewise(interpolate, [r0, r1, r2]), scale) : [interpolator(0), interpolator(0.5), interpolator(1)]; + }; + } + + scale.range = range(interpolate$2); + + scale.rangeRound = range(interpolateRound); + + scale.unknown = function(_) { + return arguments.length ? (unknown = _, scale) : unknown; + }; + + return function(t) { + transform = t, t0 = t(x0), t1 = t(x1), t2 = t(x2), k10 = t0 === t1 ? 0 : 0.5 / (t1 - t0), k21 = t1 === t2 ? 0 : 0.5 / (t2 - t1), s = t1 < t0 ? -1 : 1; + return scale; + }; +} + +function diverging$1() { + var scale = linearish(transformer()(identity$3)); + + scale.copy = function() { + return copy(scale, diverging$1()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function divergingLog() { + var scale = loggish(transformer()).domain([0.1, 1, 10]); + + scale.copy = function() { + return copy(scale, divergingLog()).base(scale.base()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function divergingSymlog() { + var scale = symlogish(transformer()); + + scale.copy = function() { + return copy(scale, divergingSymlog()).constant(scale.constant()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function divergingPow() { + var scale = powish(transformer()); + + scale.copy = function() { + return copy(scale, divergingPow()).exponent(scale.exponent()); + }; + + return initInterpolator.apply(scale, arguments); +} + +function divergingSqrt() { + return divergingPow.apply(null, arguments).exponent(0.5); +} + +function colors(specifier) { + var n = specifier.length / 6 | 0, colors = new Array(n), i = 0; + while (i < n) colors[i] = "#" + specifier.slice(i * 6, ++i * 6); + return colors; +} + +var category10 = colors("1f77b4ff7f0e2ca02cd627289467bd8c564be377c27f7f7fbcbd2217becf"); + +var Accent = colors("7fc97fbeaed4fdc086ffff99386cb0f0027fbf5b17666666"); + +var Dark2 = colors("1b9e77d95f027570b3e7298a66a61ee6ab02a6761d666666"); + +var observable10 = colors("4269d0efb118ff725c6cc5b03ca951ff8ab7a463f297bbf59c6b4e9498a0"); + +var Paired = colors("a6cee31f78b4b2df8a33a02cfb9a99e31a1cfdbf6fff7f00cab2d66a3d9affff99b15928"); + +var Pastel1 = colors("fbb4aeb3cde3ccebc5decbe4fed9a6ffffcce5d8bdfddaecf2f2f2"); + +var Pastel2 = colors("b3e2cdfdcdaccbd5e8f4cae4e6f5c9fff2aef1e2cccccccc"); + +var Set1 = colors("e41a1c377eb84daf4a984ea3ff7f00ffff33a65628f781bf999999"); + +var Set2 = colors("66c2a5fc8d628da0cbe78ac3a6d854ffd92fe5c494b3b3b3"); + +var Set3 = colors("8dd3c7ffffb3bebadafb807280b1d3fdb462b3de69fccde5d9d9d9bc80bdccebc5ffed6f"); + +var Tableau10 = colors("4e79a7f28e2ce1575976b7b259a14fedc949af7aa1ff9da79c755fbab0ab"); + +var ramp$1 = scheme => rgbBasis(scheme[scheme.length - 1]); + +var scheme$q = new Array(3).concat( + "d8b365f5f5f55ab4ac", + "a6611adfc27d80cdc1018571", + "a6611adfc27df5f5f580cdc1018571", + "8c510ad8b365f6e8c3c7eae55ab4ac01665e", + "8c510ad8b365f6e8c3f5f5f5c7eae55ab4ac01665e", + "8c510abf812ddfc27df6e8c3c7eae580cdc135978f01665e", + "8c510abf812ddfc27df6e8c3f5f5f5c7eae580cdc135978f01665e", + "5430058c510abf812ddfc27df6e8c3c7eae580cdc135978f01665e003c30", + "5430058c510abf812ddfc27df6e8c3f5f5f5c7eae580cdc135978f01665e003c30" +).map(colors); + +var BrBG = ramp$1(scheme$q); + +var scheme$p = new Array(3).concat( + "af8dc3f7f7f77fbf7b", + "7b3294c2a5cfa6dba0008837", + "7b3294c2a5cff7f7f7a6dba0008837", + "762a83af8dc3e7d4e8d9f0d37fbf7b1b7837", + "762a83af8dc3e7d4e8f7f7f7d9f0d37fbf7b1b7837", + "762a839970abc2a5cfe7d4e8d9f0d3a6dba05aae611b7837", + "762a839970abc2a5cfe7d4e8f7f7f7d9f0d3a6dba05aae611b7837", + "40004b762a839970abc2a5cfe7d4e8d9f0d3a6dba05aae611b783700441b", + "40004b762a839970abc2a5cfe7d4e8f7f7f7d9f0d3a6dba05aae611b783700441b" +).map(colors); + +var PRGn = ramp$1(scheme$p); + +var scheme$o = new Array(3).concat( + "e9a3c9f7f7f7a1d76a", + "d01c8bf1b6dab8e1864dac26", + "d01c8bf1b6daf7f7f7b8e1864dac26", + "c51b7de9a3c9fde0efe6f5d0a1d76a4d9221", + "c51b7de9a3c9fde0eff7f7f7e6f5d0a1d76a4d9221", + "c51b7dde77aef1b6dafde0efe6f5d0b8e1867fbc414d9221", + "c51b7dde77aef1b6dafde0eff7f7f7e6f5d0b8e1867fbc414d9221", + "8e0152c51b7dde77aef1b6dafde0efe6f5d0b8e1867fbc414d9221276419", + "8e0152c51b7dde77aef1b6dafde0eff7f7f7e6f5d0b8e1867fbc414d9221276419" +).map(colors); + +var PiYG = ramp$1(scheme$o); + +var scheme$n = new Array(3).concat( + "998ec3f7f7f7f1a340", + "5e3c99b2abd2fdb863e66101", + "5e3c99b2abd2f7f7f7fdb863e66101", + "542788998ec3d8daebfee0b6f1a340b35806", + "542788998ec3d8daebf7f7f7fee0b6f1a340b35806", + "5427888073acb2abd2d8daebfee0b6fdb863e08214b35806", + "5427888073acb2abd2d8daebf7f7f7fee0b6fdb863e08214b35806", + "2d004b5427888073acb2abd2d8daebfee0b6fdb863e08214b358067f3b08", + "2d004b5427888073acb2abd2d8daebf7f7f7fee0b6fdb863e08214b358067f3b08" +).map(colors); + +var PuOr = ramp$1(scheme$n); + +var scheme$m = new Array(3).concat( + "ef8a62f7f7f767a9cf", + "ca0020f4a58292c5de0571b0", + "ca0020f4a582f7f7f792c5de0571b0", + "b2182bef8a62fddbc7d1e5f067a9cf2166ac", + "b2182bef8a62fddbc7f7f7f7d1e5f067a9cf2166ac", + "b2182bd6604df4a582fddbc7d1e5f092c5de4393c32166ac", + "b2182bd6604df4a582fddbc7f7f7f7d1e5f092c5de4393c32166ac", + "67001fb2182bd6604df4a582fddbc7d1e5f092c5de4393c32166ac053061", + "67001fb2182bd6604df4a582fddbc7f7f7f7d1e5f092c5de4393c32166ac053061" +).map(colors); + +var RdBu = ramp$1(scheme$m); + +var scheme$l = new Array(3).concat( + "ef8a62ffffff999999", + "ca0020f4a582bababa404040", + "ca0020f4a582ffffffbababa404040", + "b2182bef8a62fddbc7e0e0e09999994d4d4d", + "b2182bef8a62fddbc7ffffffe0e0e09999994d4d4d", + "b2182bd6604df4a582fddbc7e0e0e0bababa8787874d4d4d", + "b2182bd6604df4a582fddbc7ffffffe0e0e0bababa8787874d4d4d", + "67001fb2182bd6604df4a582fddbc7e0e0e0bababa8787874d4d4d1a1a1a", + "67001fb2182bd6604df4a582fddbc7ffffffe0e0e0bababa8787874d4d4d1a1a1a" +).map(colors); + +var RdGy = ramp$1(scheme$l); + +var scheme$k = new Array(3).concat( + "fc8d59ffffbf91bfdb", + "d7191cfdae61abd9e92c7bb6", + "d7191cfdae61ffffbfabd9e92c7bb6", + "d73027fc8d59fee090e0f3f891bfdb4575b4", + "d73027fc8d59fee090ffffbfe0f3f891bfdb4575b4", + "d73027f46d43fdae61fee090e0f3f8abd9e974add14575b4", + "d73027f46d43fdae61fee090ffffbfe0f3f8abd9e974add14575b4", + "a50026d73027f46d43fdae61fee090e0f3f8abd9e974add14575b4313695", + "a50026d73027f46d43fdae61fee090ffffbfe0f3f8abd9e974add14575b4313695" +).map(colors); + +var RdYlBu = ramp$1(scheme$k); + +var scheme$j = new Array(3).concat( + "fc8d59ffffbf91cf60", + "d7191cfdae61a6d96a1a9641", + "d7191cfdae61ffffbfa6d96a1a9641", + "d73027fc8d59fee08bd9ef8b91cf601a9850", + "d73027fc8d59fee08bffffbfd9ef8b91cf601a9850", + "d73027f46d43fdae61fee08bd9ef8ba6d96a66bd631a9850", + "d73027f46d43fdae61fee08bffffbfd9ef8ba6d96a66bd631a9850", + "a50026d73027f46d43fdae61fee08bd9ef8ba6d96a66bd631a9850006837", + "a50026d73027f46d43fdae61fee08bffffbfd9ef8ba6d96a66bd631a9850006837" +).map(colors); + +var RdYlGn = ramp$1(scheme$j); + +var scheme$i = new Array(3).concat( + "fc8d59ffffbf99d594", + "d7191cfdae61abdda42b83ba", + "d7191cfdae61ffffbfabdda42b83ba", + "d53e4ffc8d59fee08be6f59899d5943288bd", + "d53e4ffc8d59fee08bffffbfe6f59899d5943288bd", + "d53e4ff46d43fdae61fee08be6f598abdda466c2a53288bd", + "d53e4ff46d43fdae61fee08bffffbfe6f598abdda466c2a53288bd", + "9e0142d53e4ff46d43fdae61fee08be6f598abdda466c2a53288bd5e4fa2", + "9e0142d53e4ff46d43fdae61fee08bffffbfe6f598abdda466c2a53288bd5e4fa2" +).map(colors); + +var Spectral = ramp$1(scheme$i); + +var scheme$h = new Array(3).concat( + "e5f5f999d8c92ca25f", + "edf8fbb2e2e266c2a4238b45", + "edf8fbb2e2e266c2a42ca25f006d2c", + "edf8fbccece699d8c966c2a42ca25f006d2c", + "edf8fbccece699d8c966c2a441ae76238b45005824", + "f7fcfde5f5f9ccece699d8c966c2a441ae76238b45005824", + "f7fcfde5f5f9ccece699d8c966c2a441ae76238b45006d2c00441b" +).map(colors); + +var BuGn = ramp$1(scheme$h); + +var scheme$g = new Array(3).concat( + "e0ecf49ebcda8856a7", + "edf8fbb3cde38c96c688419d", + "edf8fbb3cde38c96c68856a7810f7c", + "edf8fbbfd3e69ebcda8c96c68856a7810f7c", + "edf8fbbfd3e69ebcda8c96c68c6bb188419d6e016b", + "f7fcfde0ecf4bfd3e69ebcda8c96c68c6bb188419d6e016b", + "f7fcfde0ecf4bfd3e69ebcda8c96c68c6bb188419d810f7c4d004b" +).map(colors); + +var BuPu = ramp$1(scheme$g); + +var scheme$f = new Array(3).concat( + "e0f3dba8ddb543a2ca", + "f0f9e8bae4bc7bccc42b8cbe", + "f0f9e8bae4bc7bccc443a2ca0868ac", + "f0f9e8ccebc5a8ddb57bccc443a2ca0868ac", + "f0f9e8ccebc5a8ddb57bccc44eb3d32b8cbe08589e", + "f7fcf0e0f3dbccebc5a8ddb57bccc44eb3d32b8cbe08589e", + "f7fcf0e0f3dbccebc5a8ddb57bccc44eb3d32b8cbe0868ac084081" +).map(colors); + +var GnBu = ramp$1(scheme$f); + +var scheme$e = new Array(3).concat( + "fee8c8fdbb84e34a33", + "fef0d9fdcc8afc8d59d7301f", + "fef0d9fdcc8afc8d59e34a33b30000", + "fef0d9fdd49efdbb84fc8d59e34a33b30000", + "fef0d9fdd49efdbb84fc8d59ef6548d7301f990000", + "fff7ecfee8c8fdd49efdbb84fc8d59ef6548d7301f990000", + "fff7ecfee8c8fdd49efdbb84fc8d59ef6548d7301fb300007f0000" +).map(colors); + +var OrRd = ramp$1(scheme$e); + +var scheme$d = new Array(3).concat( + "ece2f0a6bddb1c9099", + "f6eff7bdc9e167a9cf02818a", + "f6eff7bdc9e167a9cf1c9099016c59", + "f6eff7d0d1e6a6bddb67a9cf1c9099016c59", + "f6eff7d0d1e6a6bddb67a9cf3690c002818a016450", + "fff7fbece2f0d0d1e6a6bddb67a9cf3690c002818a016450", + "fff7fbece2f0d0d1e6a6bddb67a9cf3690c002818a016c59014636" +).map(colors); + +var PuBuGn = ramp$1(scheme$d); + +var scheme$c = new Array(3).concat( + "ece7f2a6bddb2b8cbe", + "f1eef6bdc9e174a9cf0570b0", + "f1eef6bdc9e174a9cf2b8cbe045a8d", + "f1eef6d0d1e6a6bddb74a9cf2b8cbe045a8d", + "f1eef6d0d1e6a6bddb74a9cf3690c00570b0034e7b", + "fff7fbece7f2d0d1e6a6bddb74a9cf3690c00570b0034e7b", + "fff7fbece7f2d0d1e6a6bddb74a9cf3690c00570b0045a8d023858" +).map(colors); + +var PuBu = ramp$1(scheme$c); + +var scheme$b = new Array(3).concat( + "e7e1efc994c7dd1c77", + "f1eef6d7b5d8df65b0ce1256", + "f1eef6d7b5d8df65b0dd1c77980043", + "f1eef6d4b9dac994c7df65b0dd1c77980043", + "f1eef6d4b9dac994c7df65b0e7298ace125691003f", + "f7f4f9e7e1efd4b9dac994c7df65b0e7298ace125691003f", + "f7f4f9e7e1efd4b9dac994c7df65b0e7298ace125698004367001f" +).map(colors); + +var PuRd = ramp$1(scheme$b); + +var scheme$a = new Array(3).concat( + "fde0ddfa9fb5c51b8a", + "feebe2fbb4b9f768a1ae017e", + "feebe2fbb4b9f768a1c51b8a7a0177", + "feebe2fcc5c0fa9fb5f768a1c51b8a7a0177", + "feebe2fcc5c0fa9fb5f768a1dd3497ae017e7a0177", + "fff7f3fde0ddfcc5c0fa9fb5f768a1dd3497ae017e7a0177", + "fff7f3fde0ddfcc5c0fa9fb5f768a1dd3497ae017e7a017749006a" +).map(colors); + +var RdPu = ramp$1(scheme$a); + +var scheme$9 = new Array(3).concat( + "edf8b17fcdbb2c7fb8", + "ffffcca1dab441b6c4225ea8", + "ffffcca1dab441b6c42c7fb8253494", + "ffffccc7e9b47fcdbb41b6c42c7fb8253494", + "ffffccc7e9b47fcdbb41b6c41d91c0225ea80c2c84", + "ffffd9edf8b1c7e9b47fcdbb41b6c41d91c0225ea80c2c84", + "ffffd9edf8b1c7e9b47fcdbb41b6c41d91c0225ea8253494081d58" +).map(colors); + +var YlGnBu = ramp$1(scheme$9); + +var scheme$8 = new Array(3).concat( + "f7fcb9addd8e31a354", + "ffffccc2e69978c679238443", + "ffffccc2e69978c67931a354006837", + "ffffccd9f0a3addd8e78c67931a354006837", + "ffffccd9f0a3addd8e78c67941ab5d238443005a32", + "ffffe5f7fcb9d9f0a3addd8e78c67941ab5d238443005a32", + "ffffe5f7fcb9d9f0a3addd8e78c67941ab5d238443006837004529" +).map(colors); + +var YlGn = ramp$1(scheme$8); + +var scheme$7 = new Array(3).concat( + "fff7bcfec44fd95f0e", + "ffffd4fed98efe9929cc4c02", + "ffffd4fed98efe9929d95f0e993404", + "ffffd4fee391fec44ffe9929d95f0e993404", + "ffffd4fee391fec44ffe9929ec7014cc4c028c2d04", + "ffffe5fff7bcfee391fec44ffe9929ec7014cc4c028c2d04", + "ffffe5fff7bcfee391fec44ffe9929ec7014cc4c02993404662506" +).map(colors); + +var YlOrBr = ramp$1(scheme$7); + +var scheme$6 = new Array(3).concat( + "ffeda0feb24cf03b20", + "ffffb2fecc5cfd8d3ce31a1c", + "ffffb2fecc5cfd8d3cf03b20bd0026", + "ffffb2fed976feb24cfd8d3cf03b20bd0026", + "ffffb2fed976feb24cfd8d3cfc4e2ae31a1cb10026", + "ffffccffeda0fed976feb24cfd8d3cfc4e2ae31a1cb10026", + "ffffccffeda0fed976feb24cfd8d3cfc4e2ae31a1cbd0026800026" +).map(colors); + +var YlOrRd = ramp$1(scheme$6); + +var scheme$5 = new Array(3).concat( + "deebf79ecae13182bd", + "eff3ffbdd7e76baed62171b5", + "eff3ffbdd7e76baed63182bd08519c", + "eff3ffc6dbef9ecae16baed63182bd08519c", + "eff3ffc6dbef9ecae16baed64292c62171b5084594", + "f7fbffdeebf7c6dbef9ecae16baed64292c62171b5084594", + "f7fbffdeebf7c6dbef9ecae16baed64292c62171b508519c08306b" +).map(colors); + +var Blues = ramp$1(scheme$5); + +var scheme$4 = new Array(3).concat( + "e5f5e0a1d99b31a354", + "edf8e9bae4b374c476238b45", + "edf8e9bae4b374c47631a354006d2c", + "edf8e9c7e9c0a1d99b74c47631a354006d2c", + "edf8e9c7e9c0a1d99b74c47641ab5d238b45005a32", + "f7fcf5e5f5e0c7e9c0a1d99b74c47641ab5d238b45005a32", + "f7fcf5e5f5e0c7e9c0a1d99b74c47641ab5d238b45006d2c00441b" +).map(colors); + +var Greens = ramp$1(scheme$4); + +var scheme$3 = new Array(3).concat( + "f0f0f0bdbdbd636363", + "f7f7f7cccccc969696525252", + "f7f7f7cccccc969696636363252525", + "f7f7f7d9d9d9bdbdbd969696636363252525", + "f7f7f7d9d9d9bdbdbd969696737373525252252525", + "fffffff0f0f0d9d9d9bdbdbd969696737373525252252525", + "fffffff0f0f0d9d9d9bdbdbd969696737373525252252525000000" +).map(colors); + +var Greys = ramp$1(scheme$3); + +var scheme$2 = new Array(3).concat( + "efedf5bcbddc756bb1", + "f2f0f7cbc9e29e9ac86a51a3", + "f2f0f7cbc9e29e9ac8756bb154278f", + "f2f0f7dadaebbcbddc9e9ac8756bb154278f", + "f2f0f7dadaebbcbddc9e9ac8807dba6a51a34a1486", + "fcfbfdefedf5dadaebbcbddc9e9ac8807dba6a51a34a1486", + "fcfbfdefedf5dadaebbcbddc9e9ac8807dba6a51a354278f3f007d" +).map(colors); + +var Purples = ramp$1(scheme$2); + +var scheme$1 = new Array(3).concat( + "fee0d2fc9272de2d26", + "fee5d9fcae91fb6a4acb181d", + "fee5d9fcae91fb6a4ade2d26a50f15", + "fee5d9fcbba1fc9272fb6a4ade2d26a50f15", + "fee5d9fcbba1fc9272fb6a4aef3b2ccb181d99000d", + "fff5f0fee0d2fcbba1fc9272fb6a4aef3b2ccb181d99000d", + "fff5f0fee0d2fcbba1fc9272fb6a4aef3b2ccb181da50f1567000d" +).map(colors); + +var Reds = ramp$1(scheme$1); + +var scheme = new Array(3).concat( + "fee6cefdae6be6550d", + "feeddefdbe85fd8d3cd94701", + "feeddefdbe85fd8d3ce6550da63603", + "feeddefdd0a2fdae6bfd8d3ce6550da63603", + "feeddefdd0a2fdae6bfd8d3cf16913d948018c2d04", + "fff5ebfee6cefdd0a2fdae6bfd8d3cf16913d948018c2d04", + "fff5ebfee6cefdd0a2fdae6bfd8d3cf16913d94801a636037f2704" +).map(colors); + +var Oranges = ramp$1(scheme); + +function cividis(t) { + t = Math.max(0, Math.min(1, t)); + return "rgb(" + + Math.max(0, Math.min(255, Math.round(-4.54 - t * (35.34 - t * (2381.73 - t * (6402.7 - t * (7024.72 - t * 2710.57))))))) + ", " + + Math.max(0, Math.min(255, Math.round(32.49 + t * (170.73 + t * (52.82 - t * (131.46 - t * (176.58 - t * 67.37))))))) + ", " + + Math.max(0, Math.min(255, Math.round(81.24 + t * (442.36 - t * (2482.43 - t * (6167.24 - t * (6614.94 - t * 2475.67))))))) + + ")"; +} + +var cubehelix = cubehelixLong(cubehelix$3(300, 0.5, 0.0), cubehelix$3(-240, 0.5, 1.0)); + +var warm = cubehelixLong(cubehelix$3(-100, 0.75, 0.35), cubehelix$3(80, 1.50, 0.8)); + +var cool = cubehelixLong(cubehelix$3(260, 0.75, 0.35), cubehelix$3(80, 1.50, 0.8)); + +var c$2 = cubehelix$3(); + +function rainbow(t) { + if (t < 0 || t > 1) t -= Math.floor(t); + var ts = Math.abs(t - 0.5); + c$2.h = 360 * t - 100; + c$2.s = 1.5 - 1.5 * ts; + c$2.l = 0.8 - 0.9 * ts; + return c$2 + ""; +} + +var c$1 = rgb(), + pi_1_3 = Math.PI / 3, + pi_2_3 = Math.PI * 2 / 3; + +function sinebow(t) { + var x; + t = (0.5 - t) * Math.PI; + c$1.r = 255 * (x = Math.sin(t)) * x; + c$1.g = 255 * (x = Math.sin(t + pi_1_3)) * x; + c$1.b = 255 * (x = Math.sin(t + pi_2_3)) * x; + return c$1 + ""; +} + +function turbo(t) { + t = Math.max(0, Math.min(1, t)); + return "rgb(" + + Math.max(0, Math.min(255, Math.round(34.61 + t * (1172.33 - t * (10793.56 - t * (33300.12 - t * (38394.49 - t * 14825.05))))))) + ", " + + Math.max(0, Math.min(255, Math.round(23.31 + t * (557.33 + t * (1225.33 - t * (3574.96 - t * (1073.77 + t * 707.56))))))) + ", " + + Math.max(0, Math.min(255, Math.round(27.2 + t * (3211.1 - t * (15327.97 - t * (27814 - t * (22569.18 - t * 6838.66))))))) + + ")"; +} + +function ramp(range) { + var n = range.length; + return function(t) { + return range[Math.max(0, Math.min(n - 1, Math.floor(t * n)))]; + }; +} + +var viridis = ramp(colors("44015444025645045745055946075a46085c460a5d460b5e470d60470e6147106347116447136548146748166848176948186a481a6c481b6d481c6e481d6f481f70482071482173482374482475482576482677482878482979472a7a472c7a472d7b472e7c472f7d46307e46327e46337f463480453581453781453882443983443a83443b84433d84433e85423f854240864241864142874144874045884046883f47883f48893e49893e4a893e4c8a3d4d8a3d4e8a3c4f8a3c508b3b518b3b528b3a538b3a548c39558c39568c38588c38598c375a8c375b8d365c8d365d8d355e8d355f8d34608d34618d33628d33638d32648e32658e31668e31678e31688e30698e306a8e2f6b8e2f6c8e2e6d8e2e6e8e2e6f8e2d708e2d718e2c718e2c728e2c738e2b748e2b758e2a768e2a778e2a788e29798e297a8e297b8e287c8e287d8e277e8e277f8e27808e26818e26828e26828e25838e25848e25858e24868e24878e23888e23898e238a8d228b8d228c8d228d8d218e8d218f8d21908d21918c20928c20928c20938c1f948c1f958b1f968b1f978b1f988b1f998a1f9a8a1e9b8a1e9c891e9d891f9e891f9f881fa0881fa1881fa1871fa28720a38620a48621a58521a68522a78522a88423a98324aa8325ab8225ac8226ad8127ad8128ae8029af7f2ab07f2cb17e2db27d2eb37c2fb47c31b57b32b67a34b67935b77937b87838b9773aba763bbb753dbc743fbc7340bd7242be7144bf7046c06f48c16e4ac16d4cc26c4ec36b50c46a52c56954c56856c66758c7655ac8645cc8635ec96260ca6063cb5f65cb5e67cc5c69cd5b6ccd5a6ece5870cf5773d05675d05477d1537ad1517cd2507fd34e81d34d84d44b86d54989d5488bd6468ed64590d74393d74195d84098d83e9bd93c9dd93ba0da39a2da37a5db36a8db34aadc32addc30b0dd2fb2dd2db5de2bb8de29bade28bddf26c0df25c2df23c5e021c8e020cae11fcde11dd0e11cd2e21bd5e21ad8e219dae319dde318dfe318e2e418e5e419e7e419eae51aece51befe51cf1e51df4e61ef6e620f8e621fbe723fde725")); + +var magma = ramp(colors("00000401000501010601010802010902020b02020d03030f03031204041405041606051806051a07061c08071e0907200a08220b09240c09260d0a290e0b2b100b2d110c2f120d31130d34140e36150e38160f3b180f3d19103f1a10421c10441d11471e114920114b21114e22115024125325125527125829115a2a115c2c115f2d11612f116331116533106734106936106b38106c390f6e3b0f703d0f713f0f72400f74420f75440f764510774710784910784a10794c117a4e117b4f127b51127c52137c54137d56147d57157e59157e5a167e5c167f5d177f5f187f601880621980641a80651a80671b80681c816a1c816b1d816d1d816e1e81701f81721f817320817521817621817822817922827b23827c23827e24828025828125818326818426818627818827818928818b29818c29818e2a81902a81912b81932b80942c80962c80982d80992d809b2e7f9c2e7f9e2f7fa02f7fa1307ea3307ea5317ea6317da8327daa337dab337cad347cae347bb0357bb2357bb3367ab5367ab73779b83779ba3878bc3978bd3977bf3a77c03a76c23b75c43c75c53c74c73d73c83e73ca3e72cc3f71cd4071cf4070d0416fd2426fd3436ed5446dd6456cd8456cd9466bdb476adc4869de4968df4a68e04c67e24d66e34e65e44f64e55064e75263e85362e95462ea5661eb5760ec5860ed5a5fee5b5eef5d5ef05f5ef1605df2625df2645cf3655cf4675cf4695cf56b5cf66c5cf66e5cf7705cf7725cf8745cf8765cf9785df9795df97b5dfa7d5efa7f5efa815ffb835ffb8560fb8761fc8961fc8a62fc8c63fc8e64fc9065fd9266fd9467fd9668fd9869fd9a6afd9b6bfe9d6cfe9f6dfea16efea36ffea571fea772fea973feaa74feac76feae77feb078feb27afeb47bfeb67cfeb77efeb97ffebb81febd82febf84fec185fec287fec488fec68afec88cfeca8dfecc8ffecd90fecf92fed194fed395fed597fed799fed89afdda9cfddc9efddea0fde0a1fde2a3fde3a5fde5a7fde7a9fde9aafdebacfcecaefceeb0fcf0b2fcf2b4fcf4b6fcf6b8fcf7b9fcf9bbfcfbbdfcfdbf")); + +var inferno = ramp(colors("00000401000501010601010802010a02020c02020e03021004031204031405041706041907051b08051d09061f0a07220b07240c08260d08290e092b10092d110a30120a32140b34150b37160b39180c3c190c3e1b0c411c0c431e0c451f0c48210c4a230c4c240c4f260c51280b53290b552b0b572d0b592f0a5b310a5c320a5e340a5f3609613809623909633b09643d09653e0966400a67420a68440a68450a69470b6a490b6a4a0c6b4c0c6b4d0d6c4f0d6c510e6c520e6d540f6d550f6d57106e59106e5a116e5c126e5d126e5f136e61136e62146e64156e65156e67166e69166e6a176e6c186e6d186e6f196e71196e721a6e741a6e751b6e771c6d781c6d7a1d6d7c1d6d7d1e6d7f1e6c801f6c82206c84206b85216b87216b88226a8a226a8c23698d23698f24699025689225689326679526679727669827669a28659b29649d29649f2a63a02a63a22b62a32c61a52c60a62d60a82e5fa92e5eab2f5ead305dae305cb0315bb1325ab3325ab43359b63458b73557b93556ba3655bc3754bd3853bf3952c03a51c13a50c33b4fc43c4ec63d4dc73e4cc83f4bca404acb4149cc4248ce4347cf4446d04545d24644d34743d44842d54a41d74b3fd84c3ed94d3dda4e3cdb503bdd513ade5238df5337e05536e15635e25734e35933e45a31e55c30e65d2fe75e2ee8602de9612bea632aeb6429eb6628ec6726ed6925ee6a24ef6c23ef6e21f06f20f1711ff1731df2741cf3761bf37819f47918f57b17f57d15f67e14f68013f78212f78410f8850ff8870ef8890cf98b0bf98c0af98e09fa9008fa9207fa9407fb9606fb9706fb9906fb9b06fb9d07fc9f07fca108fca309fca50afca60cfca80dfcaa0ffcac11fcae12fcb014fcb216fcb418fbb61afbb81dfbba1ffbbc21fbbe23fac026fac228fac42afac62df9c72ff9c932f9cb35f8cd37f8cf3af7d13df7d340f6d543f6d746f5d949f5db4cf4dd4ff4df53f4e156f3e35af3e55df2e661f2e865f2ea69f1ec6df1ed71f1ef75f1f179f2f27df2f482f3f586f3f68af4f88ef5f992f6fa96f8fb9af9fc9dfafda1fcffa4")); + +var plasma = ramp(colors("0d088710078813078916078a19068c1b068d1d068e20068f2206902406912605912805922a05932c05942e05952f059631059733059735049837049938049a3a049a3c049b3e049c3f049c41049d43039e44039e46039f48039f4903a04b03a14c02a14e02a25002a25102a35302a35502a45601a45801a45901a55b01a55c01a65e01a66001a66100a76300a76400a76600a76700a86900a86a00a86c00a86e00a86f00a87100a87201a87401a87501a87701a87801a87a02a87b02a87d03a87e03a88004a88104a78305a78405a78606a68707a68808a68a09a58b0aa58d0ba58e0ca48f0da4910ea3920fa39410a29511a19613a19814a099159f9a169f9c179e9d189d9e199da01a9ca11b9ba21d9aa31e9aa51f99a62098a72197a82296aa2395ab2494ac2694ad2793ae2892b02991b12a90b22b8fb32c8eb42e8db52f8cb6308bb7318ab83289ba3388bb3488bc3587bd3786be3885bf3984c03a83c13b82c23c81c33d80c43e7fc5407ec6417dc7427cc8437bc9447aca457acb4679cc4778cc4977cd4a76ce4b75cf4c74d04d73d14e72d24f71d35171d45270d5536fd5546ed6556dd7566cd8576bd9586ada5a6ada5b69db5c68dc5d67dd5e66de5f65de6164df6263e06363e16462e26561e26660e3685fe4695ee56a5de56b5de66c5ce76e5be76f5ae87059e97158e97257ea7457eb7556eb7655ec7754ed7953ed7a52ee7b51ef7c51ef7e50f07f4ff0804ef1814df1834cf2844bf3854bf3874af48849f48948f58b47f58c46f68d45f68f44f79044f79143f79342f89441f89540f9973ff9983ef99a3efa9b3dfa9c3cfa9e3bfb9f3afba139fba238fca338fca537fca636fca835fca934fdab33fdac33fdae32fdaf31fdb130fdb22ffdb42ffdb52efeb72dfeb82cfeba2cfebb2bfebd2afebe2afec029fdc229fdc328fdc527fdc627fdc827fdca26fdcb26fccd25fcce25fcd025fcd225fbd324fbd524fbd724fad824fada24f9dc24f9dd25f8df25f8e125f7e225f7e425f6e626f6e826f5e926f5eb27f4ed27f3ee27f3f027f2f227f1f426f1f525f0f724f0f921")); + +function constant$1(x) { + return function constant() { + return x; + }; +} + +const abs = Math.abs; +const atan2 = Math.atan2; +const cos = Math.cos; +const max = Math.max; +const min = Math.min; +const sin = Math.sin; +const sqrt = Math.sqrt; + +const epsilon = 1e-12; +const pi = Math.PI; +const halfPi = pi / 2; +const tau = 2 * pi; + +function acos(x) { + return x > 1 ? 0 : x < -1 ? pi : Math.acos(x); +} + +function asin(x) { + return x >= 1 ? halfPi : x <= -1 ? -halfPi : Math.asin(x); +} + +function withPath(shape) { + let digits = 3; + + shape.digits = function(_) { + if (!arguments.length) return digits; + if (_ == null) { + digits = null; + } else { + const d = Math.floor(_); + if (!(d >= 0)) throw new RangeError(`invalid digits: ${_}`); + digits = d; + } + return shape; + }; + + return () => new Path$1(digits); +} + +function arcInnerRadius(d) { + return d.innerRadius; +} + +function arcOuterRadius(d) { + return d.outerRadius; +} + +function arcStartAngle(d) { + return d.startAngle; +} + +function arcEndAngle(d) { + return d.endAngle; +} + +function arcPadAngle(d) { + return d && d.padAngle; // Note: optional! +} + +function intersect(x0, y0, x1, y1, x2, y2, x3, y3) { + var x10 = x1 - x0, y10 = y1 - y0, + x32 = x3 - x2, y32 = y3 - y2, + t = y32 * x10 - x32 * y10; + if (t * t < epsilon) return; + t = (x32 * (y0 - y2) - y32 * (x0 - x2)) / t; + return [x0 + t * x10, y0 + t * y10]; +} + +// Compute perpendicular offset line of length rc. +// http://mathworld.wolfram.com/Circle-LineIntersection.html +function cornerTangents(x0, y0, x1, y1, r1, rc, cw) { + var x01 = x0 - x1, + y01 = y0 - y1, + lo = (cw ? rc : -rc) / sqrt(x01 * x01 + y01 * y01), + ox = lo * y01, + oy = -lo * x01, + x11 = x0 + ox, + y11 = y0 + oy, + x10 = x1 + ox, + y10 = y1 + oy, + x00 = (x11 + x10) / 2, + y00 = (y11 + y10) / 2, + dx = x10 - x11, + dy = y10 - y11, + d2 = dx * dx + dy * dy, + r = r1 - rc, + D = x11 * y10 - x10 * y11, + d = (dy < 0 ? -1 : 1) * sqrt(max(0, r * r * d2 - D * D)), + cx0 = (D * dy - dx * d) / d2, + cy0 = (-D * dx - dy * d) / d2, + cx1 = (D * dy + dx * d) / d2, + cy1 = (-D * dx + dy * d) / d2, + dx0 = cx0 - x00, + dy0 = cy0 - y00, + dx1 = cx1 - x00, + dy1 = cy1 - y00; + + // Pick the closer of the two intersection points. + // TODO Is there a faster way to determine which intersection to use? + if (dx0 * dx0 + dy0 * dy0 > dx1 * dx1 + dy1 * dy1) cx0 = cx1, cy0 = cy1; + + return { + cx: cx0, + cy: cy0, + x01: -ox, + y01: -oy, + x11: cx0 * (r1 / r - 1), + y11: cy0 * (r1 / r - 1) + }; +} + +function arc() { + var innerRadius = arcInnerRadius, + outerRadius = arcOuterRadius, + cornerRadius = constant$1(0), + padRadius = null, + startAngle = arcStartAngle, + endAngle = arcEndAngle, + padAngle = arcPadAngle, + context = null, + path = withPath(arc); + + function arc() { + var buffer, + r, + r0 = +innerRadius.apply(this, arguments), + r1 = +outerRadius.apply(this, arguments), + a0 = startAngle.apply(this, arguments) - halfPi, + a1 = endAngle.apply(this, arguments) - halfPi, + da = abs(a1 - a0), + cw = a1 > a0; + + if (!context) context = buffer = path(); + + // Ensure that the outer radius is always larger than the inner radius. + if (r1 < r0) r = r1, r1 = r0, r0 = r; + + // Is it a point? + if (!(r1 > epsilon)) context.moveTo(0, 0); + + // Or is it a circle or annulus? + else if (da > tau - epsilon) { + context.moveTo(r1 * cos(a0), r1 * sin(a0)); + context.arc(0, 0, r1, a0, a1, !cw); + if (r0 > epsilon) { + context.moveTo(r0 * cos(a1), r0 * sin(a1)); + context.arc(0, 0, r0, a1, a0, cw); + } + } + + // Or is it a circular or annular sector? + else { + var a01 = a0, + a11 = a1, + a00 = a0, + a10 = a1, + da0 = da, + da1 = da, + ap = padAngle.apply(this, arguments) / 2, + rp = (ap > epsilon) && (padRadius ? +padRadius.apply(this, arguments) : sqrt(r0 * r0 + r1 * r1)), + rc = min(abs(r1 - r0) / 2, +cornerRadius.apply(this, arguments)), + rc0 = rc, + rc1 = rc, + t0, + t1; + + // Apply padding? Note that since r1 ≥ r0, da1 ≥ da0. + if (rp > epsilon) { + var p0 = asin(rp / r0 * sin(ap)), + p1 = asin(rp / r1 * sin(ap)); + if ((da0 -= p0 * 2) > epsilon) p0 *= (cw ? 1 : -1), a00 += p0, a10 -= p0; + else da0 = 0, a00 = a10 = (a0 + a1) / 2; + if ((da1 -= p1 * 2) > epsilon) p1 *= (cw ? 1 : -1), a01 += p1, a11 -= p1; + else da1 = 0, a01 = a11 = (a0 + a1) / 2; + } + + var x01 = r1 * cos(a01), + y01 = r1 * sin(a01), + x10 = r0 * cos(a10), + y10 = r0 * sin(a10); + + // Apply rounded corners? + if (rc > epsilon) { + var x11 = r1 * cos(a11), + y11 = r1 * sin(a11), + x00 = r0 * cos(a00), + y00 = r0 * sin(a00), + oc; + + // Restrict the corner radius according to the sector angle. If this + // intersection fails, it’s probably because the arc is too small, so + // disable the corner radius entirely. + if (da < pi) { + if (oc = intersect(x01, y01, x00, y00, x11, y11, x10, y10)) { + var ax = x01 - oc[0], + ay = y01 - oc[1], + bx = x11 - oc[0], + by = y11 - oc[1], + kc = 1 / sin(acos((ax * bx + ay * by) / (sqrt(ax * ax + ay * ay) * sqrt(bx * bx + by * by))) / 2), + lc = sqrt(oc[0] * oc[0] + oc[1] * oc[1]); + rc0 = min(rc, (r0 - lc) / (kc - 1)); + rc1 = min(rc, (r1 - lc) / (kc + 1)); + } else { + rc0 = rc1 = 0; + } + } + } + + // Is the sector collapsed to a line? + if (!(da1 > epsilon)) context.moveTo(x01, y01); + + // Does the sector’s outer ring have rounded corners? + else if (rc1 > epsilon) { + t0 = cornerTangents(x00, y00, x01, y01, r1, rc1, cw); + t1 = cornerTangents(x11, y11, x10, y10, r1, rc1, cw); + + context.moveTo(t0.cx + t0.x01, t0.cy + t0.y01); + + // Have the corners merged? + if (rc1 < rc) context.arc(t0.cx, t0.cy, rc1, atan2(t0.y01, t0.x01), atan2(t1.y01, t1.x01), !cw); + + // Otherwise, draw the two corners and the ring. + else { + context.arc(t0.cx, t0.cy, rc1, atan2(t0.y01, t0.x01), atan2(t0.y11, t0.x11), !cw); + context.arc(0, 0, r1, atan2(t0.cy + t0.y11, t0.cx + t0.x11), atan2(t1.cy + t1.y11, t1.cx + t1.x11), !cw); + context.arc(t1.cx, t1.cy, rc1, atan2(t1.y11, t1.x11), atan2(t1.y01, t1.x01), !cw); + } + } + + // Or is the outer ring just a circular arc? + else context.moveTo(x01, y01), context.arc(0, 0, r1, a01, a11, !cw); + + // Is there no inner ring, and it’s a circular sector? + // Or perhaps it’s an annular sector collapsed due to padding? + if (!(r0 > epsilon) || !(da0 > epsilon)) context.lineTo(x10, y10); + + // Does the sector’s inner ring (or point) have rounded corners? + else if (rc0 > epsilon) { + t0 = cornerTangents(x10, y10, x11, y11, r0, -rc0, cw); + t1 = cornerTangents(x01, y01, x00, y00, r0, -rc0, cw); + + context.lineTo(t0.cx + t0.x01, t0.cy + t0.y01); + + // Have the corners merged? + if (rc0 < rc) context.arc(t0.cx, t0.cy, rc0, atan2(t0.y01, t0.x01), atan2(t1.y01, t1.x01), !cw); + + // Otherwise, draw the two corners and the ring. + else { + context.arc(t0.cx, t0.cy, rc0, atan2(t0.y01, t0.x01), atan2(t0.y11, t0.x11), !cw); + context.arc(0, 0, r0, atan2(t0.cy + t0.y11, t0.cx + t0.x11), atan2(t1.cy + t1.y11, t1.cx + t1.x11), cw); + context.arc(t1.cx, t1.cy, rc0, atan2(t1.y11, t1.x11), atan2(t1.y01, t1.x01), !cw); + } + } + + // Or is the inner ring just a circular arc? + else context.arc(0, 0, r0, a10, a00, cw); + } + + context.closePath(); + + if (buffer) return context = null, buffer + "" || null; + } + + arc.centroid = function() { + var r = (+innerRadius.apply(this, arguments) + +outerRadius.apply(this, arguments)) / 2, + a = (+startAngle.apply(this, arguments) + +endAngle.apply(this, arguments)) / 2 - pi / 2; + return [cos(a) * r, sin(a) * r]; + }; + + arc.innerRadius = function(_) { + return arguments.length ? (innerRadius = typeof _ === "function" ? _ : constant$1(+_), arc) : innerRadius; + }; + + arc.outerRadius = function(_) { + return arguments.length ? (outerRadius = typeof _ === "function" ? _ : constant$1(+_), arc) : outerRadius; + }; + + arc.cornerRadius = function(_) { + return arguments.length ? (cornerRadius = typeof _ === "function" ? _ : constant$1(+_), arc) : cornerRadius; + }; + + arc.padRadius = function(_) { + return arguments.length ? (padRadius = _ == null ? null : typeof _ === "function" ? _ : constant$1(+_), arc) : padRadius; + }; + + arc.startAngle = function(_) { + return arguments.length ? (startAngle = typeof _ === "function" ? _ : constant$1(+_), arc) : startAngle; + }; + + arc.endAngle = function(_) { + return arguments.length ? (endAngle = typeof _ === "function" ? _ : constant$1(+_), arc) : endAngle; + }; + + arc.padAngle = function(_) { + return arguments.length ? (padAngle = typeof _ === "function" ? _ : constant$1(+_), arc) : padAngle; + }; + + arc.context = function(_) { + return arguments.length ? ((context = _ == null ? null : _), arc) : context; + }; + + return arc; +} + +var slice = Array.prototype.slice; + +function array(x) { + return typeof x === "object" && "length" in x + ? x // Array, TypedArray, NodeList, array-like + : Array.from(x); // Map, Set, iterable, string, or anything else +} + +function Linear(context) { + this._context = context; +} + +Linear.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._point = 0; + }, + lineEnd: function() { + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; // falls through + default: this._context.lineTo(x, y); break; + } + } +}; + +function curveLinear(context) { + return new Linear(context); +} + +function x(p) { + return p[0]; +} + +function y(p) { + return p[1]; +} + +function line(x$1, y$1) { + var defined = constant$1(true), + context = null, + curve = curveLinear, + output = null, + path = withPath(line); + + x$1 = typeof x$1 === "function" ? x$1 : (x$1 === undefined) ? x : constant$1(x$1); + y$1 = typeof y$1 === "function" ? y$1 : (y$1 === undefined) ? y : constant$1(y$1); + + function line(data) { + var i, + n = (data = array(data)).length, + d, + defined0 = false, + buffer; + + if (context == null) output = curve(buffer = path()); + + for (i = 0; i <= n; ++i) { + if (!(i < n && defined(d = data[i], i, data)) === defined0) { + if (defined0 = !defined0) output.lineStart(); + else output.lineEnd(); + } + if (defined0) output.point(+x$1(d, i, data), +y$1(d, i, data)); + } + + if (buffer) return output = null, buffer + "" || null; + } + + line.x = function(_) { + return arguments.length ? (x$1 = typeof _ === "function" ? _ : constant$1(+_), line) : x$1; + }; + + line.y = function(_) { + return arguments.length ? (y$1 = typeof _ === "function" ? _ : constant$1(+_), line) : y$1; + }; + + line.defined = function(_) { + return arguments.length ? (defined = typeof _ === "function" ? _ : constant$1(!!_), line) : defined; + }; + + line.curve = function(_) { + return arguments.length ? (curve = _, context != null && (output = curve(context)), line) : curve; + }; + + line.context = function(_) { + return arguments.length ? (_ == null ? context = output = null : output = curve(context = _), line) : context; + }; + + return line; +} + +function area(x0, y0, y1) { + var x1 = null, + defined = constant$1(true), + context = null, + curve = curveLinear, + output = null, + path = withPath(area); + + x0 = typeof x0 === "function" ? x0 : (x0 === undefined) ? x : constant$1(+x0); + y0 = typeof y0 === "function" ? y0 : (y0 === undefined) ? constant$1(0) : constant$1(+y0); + y1 = typeof y1 === "function" ? y1 : (y1 === undefined) ? y : constant$1(+y1); + + function area(data) { + var i, + j, + k, + n = (data = array(data)).length, + d, + defined0 = false, + buffer, + x0z = new Array(n), + y0z = new Array(n); + + if (context == null) output = curve(buffer = path()); + + for (i = 0; i <= n; ++i) { + if (!(i < n && defined(d = data[i], i, data)) === defined0) { + if (defined0 = !defined0) { + j = i; + output.areaStart(); + output.lineStart(); + } else { + output.lineEnd(); + output.lineStart(); + for (k = i - 1; k >= j; --k) { + output.point(x0z[k], y0z[k]); + } + output.lineEnd(); + output.areaEnd(); + } + } + if (defined0) { + x0z[i] = +x0(d, i, data), y0z[i] = +y0(d, i, data); + output.point(x1 ? +x1(d, i, data) : x0z[i], y1 ? +y1(d, i, data) : y0z[i]); + } + } + + if (buffer) return output = null, buffer + "" || null; + } + + function arealine() { + return line().defined(defined).curve(curve).context(context); + } + + area.x = function(_) { + return arguments.length ? (x0 = typeof _ === "function" ? _ : constant$1(+_), x1 = null, area) : x0; + }; + + area.x0 = function(_) { + return arguments.length ? (x0 = typeof _ === "function" ? _ : constant$1(+_), area) : x0; + }; + + area.x1 = function(_) { + return arguments.length ? (x1 = _ == null ? null : typeof _ === "function" ? _ : constant$1(+_), area) : x1; + }; + + area.y = function(_) { + return arguments.length ? (y0 = typeof _ === "function" ? _ : constant$1(+_), y1 = null, area) : y0; + }; + + area.y0 = function(_) { + return arguments.length ? (y0 = typeof _ === "function" ? _ : constant$1(+_), area) : y0; + }; + + area.y1 = function(_) { + return arguments.length ? (y1 = _ == null ? null : typeof _ === "function" ? _ : constant$1(+_), area) : y1; + }; + + area.lineX0 = + area.lineY0 = function() { + return arealine().x(x0).y(y0); + }; + + area.lineY1 = function() { + return arealine().x(x0).y(y1); + }; + + area.lineX1 = function() { + return arealine().x(x1).y(y0); + }; + + area.defined = function(_) { + return arguments.length ? (defined = typeof _ === "function" ? _ : constant$1(!!_), area) : defined; + }; + + area.curve = function(_) { + return arguments.length ? (curve = _, context != null && (output = curve(context)), area) : curve; + }; + + area.context = function(_) { + return arguments.length ? (_ == null ? context = output = null : output = curve(context = _), area) : context; + }; + + return area; +} + +function descending$1(a, b) { + return b < a ? -1 : b > a ? 1 : b >= a ? 0 : NaN; +} + +function identity$1(d) { + return d; +} + +function pie() { + var value = identity$1, + sortValues = descending$1, + sort = null, + startAngle = constant$1(0), + endAngle = constant$1(tau), + padAngle = constant$1(0); + + function pie(data) { + var i, + n = (data = array(data)).length, + j, + k, + sum = 0, + index = new Array(n), + arcs = new Array(n), + a0 = +startAngle.apply(this, arguments), + da = Math.min(tau, Math.max(-tau, endAngle.apply(this, arguments) - a0)), + a1, + p = Math.min(Math.abs(da) / n, padAngle.apply(this, arguments)), + pa = p * (da < 0 ? -1 : 1), + v; + + for (i = 0; i < n; ++i) { + if ((v = arcs[index[i] = i] = +value(data[i], i, data)) > 0) { + sum += v; + } + } + + // Optionally sort the arcs by previously-computed values or by data. + if (sortValues != null) index.sort(function(i, j) { return sortValues(arcs[i], arcs[j]); }); + else if (sort != null) index.sort(function(i, j) { return sort(data[i], data[j]); }); + + // Compute the arcs! They are stored in the original data's order. + for (i = 0, k = sum ? (da - n * pa) / sum : 0; i < n; ++i, a0 = a1) { + j = index[i], v = arcs[j], a1 = a0 + (v > 0 ? v * k : 0) + pa, arcs[j] = { + data: data[j], + index: i, + value: v, + startAngle: a0, + endAngle: a1, + padAngle: p + }; + } + + return arcs; + } + + pie.value = function(_) { + return arguments.length ? (value = typeof _ === "function" ? _ : constant$1(+_), pie) : value; + }; + + pie.sortValues = function(_) { + return arguments.length ? (sortValues = _, sort = null, pie) : sortValues; + }; + + pie.sort = function(_) { + return arguments.length ? (sort = _, sortValues = null, pie) : sort; + }; + + pie.startAngle = function(_) { + return arguments.length ? (startAngle = typeof _ === "function" ? _ : constant$1(+_), pie) : startAngle; + }; + + pie.endAngle = function(_) { + return arguments.length ? (endAngle = typeof _ === "function" ? _ : constant$1(+_), pie) : endAngle; + }; + + pie.padAngle = function(_) { + return arguments.length ? (padAngle = typeof _ === "function" ? _ : constant$1(+_), pie) : padAngle; + }; + + return pie; +} + +var curveRadialLinear = curveRadial(curveLinear); + +function Radial(curve) { + this._curve = curve; +} + +Radial.prototype = { + areaStart: function() { + this._curve.areaStart(); + }, + areaEnd: function() { + this._curve.areaEnd(); + }, + lineStart: function() { + this._curve.lineStart(); + }, + lineEnd: function() { + this._curve.lineEnd(); + }, + point: function(a, r) { + this._curve.point(r * Math.sin(a), r * -Math.cos(a)); + } +}; + +function curveRadial(curve) { + + function radial(context) { + return new Radial(curve(context)); + } + + radial._curve = curve; + + return radial; +} + +function lineRadial(l) { + var c = l.curve; + + l.angle = l.x, delete l.x; + l.radius = l.y, delete l.y; + + l.curve = function(_) { + return arguments.length ? c(curveRadial(_)) : c()._curve; + }; + + return l; +} + +function lineRadial$1() { + return lineRadial(line().curve(curveRadialLinear)); +} + +function areaRadial() { + var a = area().curve(curveRadialLinear), + c = a.curve, + x0 = a.lineX0, + x1 = a.lineX1, + y0 = a.lineY0, + y1 = a.lineY1; + + a.angle = a.x, delete a.x; + a.startAngle = a.x0, delete a.x0; + a.endAngle = a.x1, delete a.x1; + a.radius = a.y, delete a.y; + a.innerRadius = a.y0, delete a.y0; + a.outerRadius = a.y1, delete a.y1; + a.lineStartAngle = function() { return lineRadial(x0()); }, delete a.lineX0; + a.lineEndAngle = function() { return lineRadial(x1()); }, delete a.lineX1; + a.lineInnerRadius = function() { return lineRadial(y0()); }, delete a.lineY0; + a.lineOuterRadius = function() { return lineRadial(y1()); }, delete a.lineY1; + + a.curve = function(_) { + return arguments.length ? c(curveRadial(_)) : c()._curve; + }; + + return a; +} + +function pointRadial(x, y) { + return [(y = +y) * Math.cos(x -= Math.PI / 2), y * Math.sin(x)]; +} + +class Bump { + constructor(context, x) { + this._context = context; + this._x = x; + } + areaStart() { + this._line = 0; + } + areaEnd() { + this._line = NaN; + } + lineStart() { + this._point = 0; + } + lineEnd() { + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + } + point(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: { + this._point = 1; + if (this._line) this._context.lineTo(x, y); + else this._context.moveTo(x, y); + break; + } + case 1: this._point = 2; // falls through + default: { + if (this._x) this._context.bezierCurveTo(this._x0 = (this._x0 + x) / 2, this._y0, this._x0, y, x, y); + else this._context.bezierCurveTo(this._x0, this._y0 = (this._y0 + y) / 2, x, this._y0, x, y); + break; + } + } + this._x0 = x, this._y0 = y; + } +} + +class BumpRadial { + constructor(context) { + this._context = context; + } + lineStart() { + this._point = 0; + } + lineEnd() {} + point(x, y) { + x = +x, y = +y; + if (this._point === 0) { + this._point = 1; + } else { + const p0 = pointRadial(this._x0, this._y0); + const p1 = pointRadial(this._x0, this._y0 = (this._y0 + y) / 2); + const p2 = pointRadial(x, this._y0); + const p3 = pointRadial(x, y); + this._context.moveTo(...p0); + this._context.bezierCurveTo(...p1, ...p2, ...p3); + } + this._x0 = x, this._y0 = y; + } +} + +function bumpX(context) { + return new Bump(context, true); +} + +function bumpY(context) { + return new Bump(context, false); +} + +function bumpRadial(context) { + return new BumpRadial(context); +} + +function linkSource(d) { + return d.source; +} + +function linkTarget(d) { + return d.target; +} + +function link(curve) { + let source = linkSource, + target = linkTarget, + x$1 = x, + y$1 = y, + context = null, + output = null, + path = withPath(link); + + function link() { + let buffer; + const argv = slice.call(arguments); + const s = source.apply(this, argv); + const t = target.apply(this, argv); + if (context == null) output = curve(buffer = path()); + output.lineStart(); + argv[0] = s, output.point(+x$1.apply(this, argv), +y$1.apply(this, argv)); + argv[0] = t, output.point(+x$1.apply(this, argv), +y$1.apply(this, argv)); + output.lineEnd(); + if (buffer) return output = null, buffer + "" || null; + } + + link.source = function(_) { + return arguments.length ? (source = _, link) : source; + }; + + link.target = function(_) { + return arguments.length ? (target = _, link) : target; + }; + + link.x = function(_) { + return arguments.length ? (x$1 = typeof _ === "function" ? _ : constant$1(+_), link) : x$1; + }; + + link.y = function(_) { + return arguments.length ? (y$1 = typeof _ === "function" ? _ : constant$1(+_), link) : y$1; + }; + + link.context = function(_) { + return arguments.length ? (_ == null ? context = output = null : output = curve(context = _), link) : context; + }; + + return link; +} + +function linkHorizontal() { + return link(bumpX); +} + +function linkVertical() { + return link(bumpY); +} + +function linkRadial() { + const l = link(bumpRadial); + l.angle = l.x, delete l.x; + l.radius = l.y, delete l.y; + return l; +} + +const sqrt3$2 = sqrt(3); + +var asterisk = { + draw(context, size) { + const r = sqrt(size + min(size / 28, 0.75)) * 0.59436; + const t = r / 2; + const u = t * sqrt3$2; + context.moveTo(0, r); + context.lineTo(0, -r); + context.moveTo(-u, -t); + context.lineTo(u, t); + context.moveTo(-u, t); + context.lineTo(u, -t); + } +}; + +var circle = { + draw(context, size) { + const r = sqrt(size / pi); + context.moveTo(r, 0); + context.arc(0, 0, r, 0, tau); + } +}; + +var cross = { + draw(context, size) { + const r = sqrt(size / 5) / 2; + context.moveTo(-3 * r, -r); + context.lineTo(-r, -r); + context.lineTo(-r, -3 * r); + context.lineTo(r, -3 * r); + context.lineTo(r, -r); + context.lineTo(3 * r, -r); + context.lineTo(3 * r, r); + context.lineTo(r, r); + context.lineTo(r, 3 * r); + context.lineTo(-r, 3 * r); + context.lineTo(-r, r); + context.lineTo(-3 * r, r); + context.closePath(); + } +}; + +const tan30 = sqrt(1 / 3); +const tan30_2 = tan30 * 2; + +var diamond = { + draw(context, size) { + const y = sqrt(size / tan30_2); + const x = y * tan30; + context.moveTo(0, -y); + context.lineTo(x, 0); + context.lineTo(0, y); + context.lineTo(-x, 0); + context.closePath(); + } +}; + +var diamond2 = { + draw(context, size) { + const r = sqrt(size) * 0.62625; + context.moveTo(0, -r); + context.lineTo(r, 0); + context.lineTo(0, r); + context.lineTo(-r, 0); + context.closePath(); + } +}; + +var plus = { + draw(context, size) { + const r = sqrt(size - min(size / 7, 2)) * 0.87559; + context.moveTo(-r, 0); + context.lineTo(r, 0); + context.moveTo(0, r); + context.lineTo(0, -r); + } +}; + +var square = { + draw(context, size) { + const w = sqrt(size); + const x = -w / 2; + context.rect(x, x, w, w); + } +}; + +var square2 = { + draw(context, size) { + const r = sqrt(size) * 0.4431; + context.moveTo(r, r); + context.lineTo(r, -r); + context.lineTo(-r, -r); + context.lineTo(-r, r); + context.closePath(); + } +}; + +const ka = 0.89081309152928522810; +const kr = sin(pi / 10) / sin(7 * pi / 10); +const kx = sin(tau / 10) * kr; +const ky = -cos(tau / 10) * kr; + +var star = { + draw(context, size) { + const r = sqrt(size * ka); + const x = kx * r; + const y = ky * r; + context.moveTo(0, -r); + context.lineTo(x, y); + for (let i = 1; i < 5; ++i) { + const a = tau * i / 5; + const c = cos(a); + const s = sin(a); + context.lineTo(s * r, -c * r); + context.lineTo(c * x - s * y, s * x + c * y); + } + context.closePath(); + } +}; + +const sqrt3$1 = sqrt(3); + +var triangle = { + draw(context, size) { + const y = -sqrt(size / (sqrt3$1 * 3)); + context.moveTo(0, y * 2); + context.lineTo(-sqrt3$1 * y, -y); + context.lineTo(sqrt3$1 * y, -y); + context.closePath(); + } +}; + +const sqrt3 = sqrt(3); + +var triangle2 = { + draw(context, size) { + const s = sqrt(size) * 0.6824; + const t = s / 2; + const u = (s * sqrt3) / 2; // cos(Math.PI / 6) + context.moveTo(0, -s); + context.lineTo(u, t); + context.lineTo(-u, t); + context.closePath(); + } +}; + +const c = -0.5; +const s = sqrt(3) / 2; +const k = 1 / sqrt(12); +const a = (k / 2 + 1) * 3; + +var wye = { + draw(context, size) { + const r = sqrt(size / a); + const x0 = r / 2, y0 = r * k; + const x1 = x0, y1 = r * k + r; + const x2 = -x1, y2 = y1; + context.moveTo(x0, y0); + context.lineTo(x1, y1); + context.lineTo(x2, y2); + context.lineTo(c * x0 - s * y0, s * x0 + c * y0); + context.lineTo(c * x1 - s * y1, s * x1 + c * y1); + context.lineTo(c * x2 - s * y2, s * x2 + c * y2); + context.lineTo(c * x0 + s * y0, c * y0 - s * x0); + context.lineTo(c * x1 + s * y1, c * y1 - s * x1); + context.lineTo(c * x2 + s * y2, c * y2 - s * x2); + context.closePath(); + } +}; + +var times = { + draw(context, size) { + const r = sqrt(size - min(size / 6, 1.7)) * 0.6189; + context.moveTo(-r, -r); + context.lineTo(r, r); + context.moveTo(-r, r); + context.lineTo(r, -r); + } +}; + +// These symbols are designed to be filled. +const symbolsFill = [ + circle, + cross, + diamond, + square, + star, + triangle, + wye +]; + +// These symbols are designed to be stroked (with a width of 1.5px and round caps). +const symbolsStroke = [ + circle, + plus, + times, + triangle2, + asterisk, + square2, + diamond2 +]; + +function Symbol$1(type, size) { + let context = null, + path = withPath(symbol); + + type = typeof type === "function" ? type : constant$1(type || circle); + size = typeof size === "function" ? size : constant$1(size === undefined ? 64 : +size); + + function symbol() { + let buffer; + if (!context) context = buffer = path(); + type.apply(this, arguments).draw(context, +size.apply(this, arguments)); + if (buffer) return context = null, buffer + "" || null; + } + + symbol.type = function(_) { + return arguments.length ? (type = typeof _ === "function" ? _ : constant$1(_), symbol) : type; + }; + + symbol.size = function(_) { + return arguments.length ? (size = typeof _ === "function" ? _ : constant$1(+_), symbol) : size; + }; + + symbol.context = function(_) { + return arguments.length ? (context = _ == null ? null : _, symbol) : context; + }; + + return symbol; +} + +function noop() {} + +function point$3(that, x, y) { + that._context.bezierCurveTo( + (2 * that._x0 + that._x1) / 3, + (2 * that._y0 + that._y1) / 3, + (that._x0 + 2 * that._x1) / 3, + (that._y0 + 2 * that._y1) / 3, + (that._x0 + 4 * that._x1 + x) / 6, + (that._y0 + 4 * that._y1 + y) / 6 + ); +} + +function Basis(context) { + this._context = context; +} + +Basis.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = + this._y0 = this._y1 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 3: point$3(this, this._x1, this._y1); // falls through + case 2: this._context.lineTo(this._x1, this._y1); break; + } + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; break; + case 2: this._point = 3; this._context.lineTo((5 * this._x0 + this._x1) / 6, (5 * this._y0 + this._y1) / 6); // falls through + default: point$3(this, x, y); break; + } + this._x0 = this._x1, this._x1 = x; + this._y0 = this._y1, this._y1 = y; + } +}; + +function basis(context) { + return new Basis(context); +} + +function BasisClosed(context) { + this._context = context; +} + +BasisClosed.prototype = { + areaStart: noop, + areaEnd: noop, + lineStart: function() { + this._x0 = this._x1 = this._x2 = this._x3 = this._x4 = + this._y0 = this._y1 = this._y2 = this._y3 = this._y4 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 1: { + this._context.moveTo(this._x2, this._y2); + this._context.closePath(); + break; + } + case 2: { + this._context.moveTo((this._x2 + 2 * this._x3) / 3, (this._y2 + 2 * this._y3) / 3); + this._context.lineTo((this._x3 + 2 * this._x2) / 3, (this._y3 + 2 * this._y2) / 3); + this._context.closePath(); + break; + } + case 3: { + this.point(this._x2, this._y2); + this.point(this._x3, this._y3); + this.point(this._x4, this._y4); + break; + } + } + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._x2 = x, this._y2 = y; break; + case 1: this._point = 2; this._x3 = x, this._y3 = y; break; + case 2: this._point = 3; this._x4 = x, this._y4 = y; this._context.moveTo((this._x0 + 4 * this._x1 + x) / 6, (this._y0 + 4 * this._y1 + y) / 6); break; + default: point$3(this, x, y); break; + } + this._x0 = this._x1, this._x1 = x; + this._y0 = this._y1, this._y1 = y; + } +}; + +function basisClosed(context) { + return new BasisClosed(context); +} + +function BasisOpen(context) { + this._context = context; +} + +BasisOpen.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = + this._y0 = this._y1 = NaN; + this._point = 0; + }, + lineEnd: function() { + if (this._line || (this._line !== 0 && this._point === 3)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; break; + case 1: this._point = 2; break; + case 2: this._point = 3; var x0 = (this._x0 + 4 * this._x1 + x) / 6, y0 = (this._y0 + 4 * this._y1 + y) / 6; this._line ? this._context.lineTo(x0, y0) : this._context.moveTo(x0, y0); break; + case 3: this._point = 4; // falls through + default: point$3(this, x, y); break; + } + this._x0 = this._x1, this._x1 = x; + this._y0 = this._y1, this._y1 = y; + } +}; + +function basisOpen(context) { + return new BasisOpen(context); +} + +function Bundle(context, beta) { + this._basis = new Basis(context); + this._beta = beta; +} + +Bundle.prototype = { + lineStart: function() { + this._x = []; + this._y = []; + this._basis.lineStart(); + }, + lineEnd: function() { + var x = this._x, + y = this._y, + j = x.length - 1; + + if (j > 0) { + var x0 = x[0], + y0 = y[0], + dx = x[j] - x0, + dy = y[j] - y0, + i = -1, + t; + + while (++i <= j) { + t = i / j; + this._basis.point( + this._beta * x[i] + (1 - this._beta) * (x0 + t * dx), + this._beta * y[i] + (1 - this._beta) * (y0 + t * dy) + ); + } + } + + this._x = this._y = null; + this._basis.lineEnd(); + }, + point: function(x, y) { + this._x.push(+x); + this._y.push(+y); + } +}; + +var bundle = (function custom(beta) { + + function bundle(context) { + return beta === 1 ? new Basis(context) : new Bundle(context, beta); + } + + bundle.beta = function(beta) { + return custom(+beta); + }; + + return bundle; +})(0.85); + +function point$2(that, x, y) { + that._context.bezierCurveTo( + that._x1 + that._k * (that._x2 - that._x0), + that._y1 + that._k * (that._y2 - that._y0), + that._x2 + that._k * (that._x1 - x), + that._y2 + that._k * (that._y1 - y), + that._x2, + that._y2 + ); +} + +function Cardinal(context, tension) { + this._context = context; + this._k = (1 - tension) / 6; +} + +Cardinal.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = this._x2 = + this._y0 = this._y1 = this._y2 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 2: this._context.lineTo(this._x2, this._y2); break; + case 3: point$2(this, this._x1, this._y1); break; + } + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; this._x1 = x, this._y1 = y; break; + case 2: this._point = 3; // falls through + default: point$2(this, x, y); break; + } + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +var cardinal = (function custom(tension) { + + function cardinal(context) { + return new Cardinal(context, tension); + } + + cardinal.tension = function(tension) { + return custom(+tension); + }; + + return cardinal; +})(0); + +function CardinalClosed(context, tension) { + this._context = context; + this._k = (1 - tension) / 6; +} + +CardinalClosed.prototype = { + areaStart: noop, + areaEnd: noop, + lineStart: function() { + this._x0 = this._x1 = this._x2 = this._x3 = this._x4 = this._x5 = + this._y0 = this._y1 = this._y2 = this._y3 = this._y4 = this._y5 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 1: { + this._context.moveTo(this._x3, this._y3); + this._context.closePath(); + break; + } + case 2: { + this._context.lineTo(this._x3, this._y3); + this._context.closePath(); + break; + } + case 3: { + this.point(this._x3, this._y3); + this.point(this._x4, this._y4); + this.point(this._x5, this._y5); + break; + } + } + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._x3 = x, this._y3 = y; break; + case 1: this._point = 2; this._context.moveTo(this._x4 = x, this._y4 = y); break; + case 2: this._point = 3; this._x5 = x, this._y5 = y; break; + default: point$2(this, x, y); break; + } + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +var cardinalClosed = (function custom(tension) { + + function cardinal(context) { + return new CardinalClosed(context, tension); + } + + cardinal.tension = function(tension) { + return custom(+tension); + }; + + return cardinal; +})(0); + +function CardinalOpen(context, tension) { + this._context = context; + this._k = (1 - tension) / 6; +} + +CardinalOpen.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = this._x2 = + this._y0 = this._y1 = this._y2 = NaN; + this._point = 0; + }, + lineEnd: function() { + if (this._line || (this._line !== 0 && this._point === 3)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; break; + case 1: this._point = 2; break; + case 2: this._point = 3; this._line ? this._context.lineTo(this._x2, this._y2) : this._context.moveTo(this._x2, this._y2); break; + case 3: this._point = 4; // falls through + default: point$2(this, x, y); break; + } + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +var cardinalOpen = (function custom(tension) { + + function cardinal(context) { + return new CardinalOpen(context, tension); + } + + cardinal.tension = function(tension) { + return custom(+tension); + }; + + return cardinal; +})(0); + +function point$1(that, x, y) { + var x1 = that._x1, + y1 = that._y1, + x2 = that._x2, + y2 = that._y2; + + if (that._l01_a > epsilon) { + var a = 2 * that._l01_2a + 3 * that._l01_a * that._l12_a + that._l12_2a, + n = 3 * that._l01_a * (that._l01_a + that._l12_a); + x1 = (x1 * a - that._x0 * that._l12_2a + that._x2 * that._l01_2a) / n; + y1 = (y1 * a - that._y0 * that._l12_2a + that._y2 * that._l01_2a) / n; + } + + if (that._l23_a > epsilon) { + var b = 2 * that._l23_2a + 3 * that._l23_a * that._l12_a + that._l12_2a, + m = 3 * that._l23_a * (that._l23_a + that._l12_a); + x2 = (x2 * b + that._x1 * that._l23_2a - x * that._l12_2a) / m; + y2 = (y2 * b + that._y1 * that._l23_2a - y * that._l12_2a) / m; + } + + that._context.bezierCurveTo(x1, y1, x2, y2, that._x2, that._y2); +} + +function CatmullRom(context, alpha) { + this._context = context; + this._alpha = alpha; +} + +CatmullRom.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = this._x2 = + this._y0 = this._y1 = this._y2 = NaN; + this._l01_a = this._l12_a = this._l23_a = + this._l01_2a = this._l12_2a = this._l23_2a = + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 2: this._context.lineTo(this._x2, this._y2); break; + case 3: this.point(this._x2, this._y2); break; + } + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + + if (this._point) { + var x23 = this._x2 - x, + y23 = this._y2 - y; + this._l23_a = Math.sqrt(this._l23_2a = Math.pow(x23 * x23 + y23 * y23, this._alpha)); + } + + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; break; + case 2: this._point = 3; // falls through + default: point$1(this, x, y); break; + } + + this._l01_a = this._l12_a, this._l12_a = this._l23_a; + this._l01_2a = this._l12_2a, this._l12_2a = this._l23_2a; + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +var catmullRom = (function custom(alpha) { + + function catmullRom(context) { + return alpha ? new CatmullRom(context, alpha) : new Cardinal(context, 0); + } + + catmullRom.alpha = function(alpha) { + return custom(+alpha); + }; + + return catmullRom; +})(0.5); + +function CatmullRomClosed(context, alpha) { + this._context = context; + this._alpha = alpha; +} + +CatmullRomClosed.prototype = { + areaStart: noop, + areaEnd: noop, + lineStart: function() { + this._x0 = this._x1 = this._x2 = this._x3 = this._x4 = this._x5 = + this._y0 = this._y1 = this._y2 = this._y3 = this._y4 = this._y5 = NaN; + this._l01_a = this._l12_a = this._l23_a = + this._l01_2a = this._l12_2a = this._l23_2a = + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 1: { + this._context.moveTo(this._x3, this._y3); + this._context.closePath(); + break; + } + case 2: { + this._context.lineTo(this._x3, this._y3); + this._context.closePath(); + break; + } + case 3: { + this.point(this._x3, this._y3); + this.point(this._x4, this._y4); + this.point(this._x5, this._y5); + break; + } + } + }, + point: function(x, y) { + x = +x, y = +y; + + if (this._point) { + var x23 = this._x2 - x, + y23 = this._y2 - y; + this._l23_a = Math.sqrt(this._l23_2a = Math.pow(x23 * x23 + y23 * y23, this._alpha)); + } + + switch (this._point) { + case 0: this._point = 1; this._x3 = x, this._y3 = y; break; + case 1: this._point = 2; this._context.moveTo(this._x4 = x, this._y4 = y); break; + case 2: this._point = 3; this._x5 = x, this._y5 = y; break; + default: point$1(this, x, y); break; + } + + this._l01_a = this._l12_a, this._l12_a = this._l23_a; + this._l01_2a = this._l12_2a, this._l12_2a = this._l23_2a; + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +var catmullRomClosed = (function custom(alpha) { + + function catmullRom(context) { + return alpha ? new CatmullRomClosed(context, alpha) : new CardinalClosed(context, 0); + } + + catmullRom.alpha = function(alpha) { + return custom(+alpha); + }; + + return catmullRom; +})(0.5); + +function CatmullRomOpen(context, alpha) { + this._context = context; + this._alpha = alpha; +} + +CatmullRomOpen.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = this._x2 = + this._y0 = this._y1 = this._y2 = NaN; + this._l01_a = this._l12_a = this._l23_a = + this._l01_2a = this._l12_2a = this._l23_2a = + this._point = 0; + }, + lineEnd: function() { + if (this._line || (this._line !== 0 && this._point === 3)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + + if (this._point) { + var x23 = this._x2 - x, + y23 = this._y2 - y; + this._l23_a = Math.sqrt(this._l23_2a = Math.pow(x23 * x23 + y23 * y23, this._alpha)); + } + + switch (this._point) { + case 0: this._point = 1; break; + case 1: this._point = 2; break; + case 2: this._point = 3; this._line ? this._context.lineTo(this._x2, this._y2) : this._context.moveTo(this._x2, this._y2); break; + case 3: this._point = 4; // falls through + default: point$1(this, x, y); break; + } + + this._l01_a = this._l12_a, this._l12_a = this._l23_a; + this._l01_2a = this._l12_2a, this._l12_2a = this._l23_2a; + this._x0 = this._x1, this._x1 = this._x2, this._x2 = x; + this._y0 = this._y1, this._y1 = this._y2, this._y2 = y; + } +}; + +var catmullRomOpen = (function custom(alpha) { + + function catmullRom(context) { + return alpha ? new CatmullRomOpen(context, alpha) : new CardinalOpen(context, 0); + } + + catmullRom.alpha = function(alpha) { + return custom(+alpha); + }; + + return catmullRom; +})(0.5); + +function LinearClosed(context) { + this._context = context; +} + +LinearClosed.prototype = { + areaStart: noop, + areaEnd: noop, + lineStart: function() { + this._point = 0; + }, + lineEnd: function() { + if (this._point) this._context.closePath(); + }, + point: function(x, y) { + x = +x, y = +y; + if (this._point) this._context.lineTo(x, y); + else this._point = 1, this._context.moveTo(x, y); + } +}; + +function linearClosed(context) { + return new LinearClosed(context); +} + +function sign(x) { + return x < 0 ? -1 : 1; +} + +// Calculate the slopes of the tangents (Hermite-type interpolation) based on +// the following paper: Steffen, M. 1990. A Simple Method for Monotonic +// Interpolation in One Dimension. Astronomy and Astrophysics, Vol. 239, NO. +// NOV(II), P. 443, 1990. +function slope3(that, x2, y2) { + var h0 = that._x1 - that._x0, + h1 = x2 - that._x1, + s0 = (that._y1 - that._y0) / (h0 || h1 < 0 && -0), + s1 = (y2 - that._y1) / (h1 || h0 < 0 && -0), + p = (s0 * h1 + s1 * h0) / (h0 + h1); + return (sign(s0) + sign(s1)) * Math.min(Math.abs(s0), Math.abs(s1), 0.5 * Math.abs(p)) || 0; +} + +// Calculate a one-sided slope. +function slope2(that, t) { + var h = that._x1 - that._x0; + return h ? (3 * (that._y1 - that._y0) / h - t) / 2 : t; +} + +// According to https://en.wikipedia.org/wiki/Cubic_Hermite_spline#Representations +// "you can express cubic Hermite interpolation in terms of cubic Bézier curves +// with respect to the four values p0, p0 + m0 / 3, p1 - m1 / 3, p1". +function point(that, t0, t1) { + var x0 = that._x0, + y0 = that._y0, + x1 = that._x1, + y1 = that._y1, + dx = (x1 - x0) / 3; + that._context.bezierCurveTo(x0 + dx, y0 + dx * t0, x1 - dx, y1 - dx * t1, x1, y1); +} + +function MonotoneX(context) { + this._context = context; +} + +MonotoneX.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x0 = this._x1 = + this._y0 = this._y1 = + this._t0 = NaN; + this._point = 0; + }, + lineEnd: function() { + switch (this._point) { + case 2: this._context.lineTo(this._x1, this._y1); break; + case 3: point(this, this._t0, slope2(this, this._t0)); break; + } + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + this._line = 1 - this._line; + }, + point: function(x, y) { + var t1 = NaN; + + x = +x, y = +y; + if (x === this._x1 && y === this._y1) return; // Ignore coincident points. + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; break; + case 2: this._point = 3; point(this, slope2(this, t1 = slope3(this, x, y)), t1); break; + default: point(this, this._t0, t1 = slope3(this, x, y)); break; + } + + this._x0 = this._x1, this._x1 = x; + this._y0 = this._y1, this._y1 = y; + this._t0 = t1; + } +}; + +function MonotoneY(context) { + this._context = new ReflectContext(context); +} + +(MonotoneY.prototype = Object.create(MonotoneX.prototype)).point = function(x, y) { + MonotoneX.prototype.point.call(this, y, x); +}; + +function ReflectContext(context) { + this._context = context; +} + +ReflectContext.prototype = { + moveTo: function(x, y) { this._context.moveTo(y, x); }, + closePath: function() { this._context.closePath(); }, + lineTo: function(x, y) { this._context.lineTo(y, x); }, + bezierCurveTo: function(x1, y1, x2, y2, x, y) { this._context.bezierCurveTo(y1, x1, y2, x2, y, x); } +}; + +function monotoneX(context) { + return new MonotoneX(context); +} + +function monotoneY(context) { + return new MonotoneY(context); +} + +function Natural(context) { + this._context = context; +} + +Natural.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x = []; + this._y = []; + }, + lineEnd: function() { + var x = this._x, + y = this._y, + n = x.length; + + if (n) { + this._line ? this._context.lineTo(x[0], y[0]) : this._context.moveTo(x[0], y[0]); + if (n === 2) { + this._context.lineTo(x[1], y[1]); + } else { + var px = controlPoints(x), + py = controlPoints(y); + for (var i0 = 0, i1 = 1; i1 < n; ++i0, ++i1) { + this._context.bezierCurveTo(px[0][i0], py[0][i0], px[1][i0], py[1][i0], x[i1], y[i1]); + } + } + } + + if (this._line || (this._line !== 0 && n === 1)) this._context.closePath(); + this._line = 1 - this._line; + this._x = this._y = null; + }, + point: function(x, y) { + this._x.push(+x); + this._y.push(+y); + } +}; + +// See https://www.particleincell.com/2012/bezier-splines/ for derivation. +function controlPoints(x) { + var i, + n = x.length - 1, + m, + a = new Array(n), + b = new Array(n), + r = new Array(n); + a[0] = 0, b[0] = 2, r[0] = x[0] + 2 * x[1]; + for (i = 1; i < n - 1; ++i) a[i] = 1, b[i] = 4, r[i] = 4 * x[i] + 2 * x[i + 1]; + a[n - 1] = 2, b[n - 1] = 7, r[n - 1] = 8 * x[n - 1] + x[n]; + for (i = 1; i < n; ++i) m = a[i] / b[i - 1], b[i] -= m, r[i] -= m * r[i - 1]; + a[n - 1] = r[n - 1] / b[n - 1]; + for (i = n - 2; i >= 0; --i) a[i] = (r[i] - a[i + 1]) / b[i]; + b[n - 1] = (x[n] + a[n - 1]) / 2; + for (i = 0; i < n - 1; ++i) b[i] = 2 * x[i + 1] - a[i + 1]; + return [a, b]; +} + +function natural(context) { + return new Natural(context); +} + +function Step(context, t) { + this._context = context; + this._t = t; +} + +Step.prototype = { + areaStart: function() { + this._line = 0; + }, + areaEnd: function() { + this._line = NaN; + }, + lineStart: function() { + this._x = this._y = NaN; + this._point = 0; + }, + lineEnd: function() { + if (0 < this._t && this._t < 1 && this._point === 2) this._context.lineTo(this._x, this._y); + if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); + if (this._line >= 0) this._t = 1 - this._t, this._line = 1 - this._line; + }, + point: function(x, y) { + x = +x, y = +y; + switch (this._point) { + case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; + case 1: this._point = 2; // falls through + default: { + if (this._t <= 0) { + this._context.lineTo(this._x, y); + this._context.lineTo(x, y); + } else { + var x1 = this._x * (1 - this._t) + x * this._t; + this._context.lineTo(x1, this._y); + this._context.lineTo(x1, y); + } + break; + } + } + this._x = x, this._y = y; + } +}; + +function step(context) { + return new Step(context, 0.5); +} + +function stepBefore(context) { + return new Step(context, 0); +} + +function stepAfter(context) { + return new Step(context, 1); +} + +function none$1(series, order) { + if (!((n = series.length) > 1)) return; + for (var i = 1, j, s0, s1 = series[order[0]], n, m = s1.length; i < n; ++i) { + s0 = s1, s1 = series[order[i]]; + for (j = 0; j < m; ++j) { + s1[j][1] += s1[j][0] = isNaN(s0[j][1]) ? s0[j][0] : s0[j][1]; + } + } +} + +function none(series) { + var n = series.length, o = new Array(n); + while (--n >= 0) o[n] = n; + return o; +} + +function stackValue(d, key) { + return d[key]; +} + +function stackSeries(key) { + const series = []; + series.key = key; + return series; +} + +function stack() { + var keys = constant$1([]), + order = none, + offset = none$1, + value = stackValue; + + function stack(data) { + var sz = Array.from(keys.apply(this, arguments), stackSeries), + i, n = sz.length, j = -1, + oz; + + for (const d of data) { + for (i = 0, ++j; i < n; ++i) { + (sz[i][j] = [0, +value(d, sz[i].key, j, data)]).data = d; + } + } + + for (i = 0, oz = array(order(sz)); i < n; ++i) { + sz[oz[i]].index = i; + } + + offset(sz, oz); + return sz; + } + + stack.keys = function(_) { + return arguments.length ? (keys = typeof _ === "function" ? _ : constant$1(Array.from(_)), stack) : keys; + }; + + stack.value = function(_) { + return arguments.length ? (value = typeof _ === "function" ? _ : constant$1(+_), stack) : value; + }; + + stack.order = function(_) { + return arguments.length ? (order = _ == null ? none : typeof _ === "function" ? _ : constant$1(Array.from(_)), stack) : order; + }; + + stack.offset = function(_) { + return arguments.length ? (offset = _ == null ? none$1 : _, stack) : offset; + }; + + return stack; +} + +function expand(series, order) { + if (!((n = series.length) > 0)) return; + for (var i, n, j = 0, m = series[0].length, y; j < m; ++j) { + for (y = i = 0; i < n; ++i) y += series[i][j][1] || 0; + if (y) for (i = 0; i < n; ++i) series[i][j][1] /= y; + } + none$1(series, order); +} + +function diverging(series, order) { + if (!((n = series.length) > 0)) return; + for (var i, j = 0, d, dy, yp, yn, n, m = series[order[0]].length; j < m; ++j) { + for (yp = yn = 0, i = 0; i < n; ++i) { + if ((dy = (d = series[order[i]][j])[1] - d[0]) > 0) { + d[0] = yp, d[1] = yp += dy; + } else if (dy < 0) { + d[1] = yn, d[0] = yn += dy; + } else { + d[0] = 0, d[1] = dy; + } + } + } +} + +function silhouette(series, order) { + if (!((n = series.length) > 0)) return; + for (var j = 0, s0 = series[order[0]], n, m = s0.length; j < m; ++j) { + for (var i = 0, y = 0; i < n; ++i) y += series[i][j][1] || 0; + s0[j][1] += s0[j][0] = -y / 2; + } + none$1(series, order); +} + +function wiggle(series, order) { + if (!((n = series.length) > 0) || !((m = (s0 = series[order[0]]).length) > 0)) return; + for (var y = 0, j = 1, s0, m, n; j < m; ++j) { + for (var i = 0, s1 = 0, s2 = 0; i < n; ++i) { + var si = series[order[i]], + sij0 = si[j][1] || 0, + sij1 = si[j - 1][1] || 0, + s3 = (sij0 - sij1) / 2; + for (var k = 0; k < i; ++k) { + var sk = series[order[k]], + skj0 = sk[j][1] || 0, + skj1 = sk[j - 1][1] || 0; + s3 += skj0 - skj1; + } + s1 += sij0, s2 += s3 * sij0; + } + s0[j - 1][1] += s0[j - 1][0] = y; + if (s1) y -= s2 / s1; + } + s0[j - 1][1] += s0[j - 1][0] = y; + none$1(series, order); +} + +function appearance(series) { + var peaks = series.map(peak); + return none(series).sort(function(a, b) { return peaks[a] - peaks[b]; }); +} + +function peak(series) { + var i = -1, j = 0, n = series.length, vi, vj = -Infinity; + while (++i < n) if ((vi = +series[i][1]) > vj) vj = vi, j = i; + return j; +} + +function ascending(series) { + var sums = series.map(sum); + return none(series).sort(function(a, b) { return sums[a] - sums[b]; }); +} + +function sum(series) { + var s = 0, i = -1, n = series.length, v; + while (++i < n) if (v = +series[i][1]) s += v; + return s; +} + +function descending(series) { + return ascending(series).reverse(); +} + +function insideOut(series) { + var n = series.length, + i, + j, + sums = series.map(sum), + order = appearance(series), + top = 0, + bottom = 0, + tops = [], + bottoms = []; + + for (i = 0; i < n; ++i) { + j = order[i]; + if (top < bottom) { + top += sums[j]; + tops.push(j); + } else { + bottom += sums[j]; + bottoms.push(j); + } + } + + return bottoms.reverse().concat(tops); +} + +function reverse(series) { + return none(series).reverse(); +} + +var constant = x => () => x; + +function ZoomEvent(type, { + sourceEvent, + target, + transform, + dispatch +}) { + Object.defineProperties(this, { + type: {value: type, enumerable: true, configurable: true}, + sourceEvent: {value: sourceEvent, enumerable: true, configurable: true}, + target: {value: target, enumerable: true, configurable: true}, + transform: {value: transform, enumerable: true, configurable: true}, + _: {value: dispatch} + }); +} + +function Transform(k, x, y) { + this.k = k; + this.x = x; + this.y = y; +} + +Transform.prototype = { + constructor: Transform, + scale: function(k) { + return k === 1 ? this : new Transform(this.k * k, this.x, this.y); + }, + translate: function(x, y) { + return x === 0 & y === 0 ? this : new Transform(this.k, this.x + this.k * x, this.y + this.k * y); + }, + apply: function(point) { + return [point[0] * this.k + this.x, point[1] * this.k + this.y]; + }, + applyX: function(x) { + return x * this.k + this.x; + }, + applyY: function(y) { + return y * this.k + this.y; + }, + invert: function(location) { + return [(location[0] - this.x) / this.k, (location[1] - this.y) / this.k]; + }, + invertX: function(x) { + return (x - this.x) / this.k; + }, + invertY: function(y) { + return (y - this.y) / this.k; + }, + rescaleX: function(x) { + return x.copy().domain(x.range().map(this.invertX, this).map(x.invert, x)); + }, + rescaleY: function(y) { + return y.copy().domain(y.range().map(this.invertY, this).map(y.invert, y)); + }, + toString: function() { + return "translate(" + this.x + "," + this.y + ") scale(" + this.k + ")"; + } +}; + +var identity = new Transform(1, 0, 0); + +transform.prototype = Transform.prototype; + +function transform(node) { + while (!node.__zoom) if (!(node = node.parentNode)) return identity; + return node.__zoom; +} + +function nopropagation(event) { + event.stopImmediatePropagation(); +} + +function noevent(event) { + event.preventDefault(); + event.stopImmediatePropagation(); +} + +// Ignore right-click, since that should open the context menu. +// except for pinch-to-zoom, which is sent as a wheel+ctrlKey event +function defaultFilter(event) { + return (!event.ctrlKey || event.type === 'wheel') && !event.button; +} + +function defaultExtent() { + var e = this; + if (e instanceof SVGElement) { + e = e.ownerSVGElement || e; + if (e.hasAttribute("viewBox")) { + e = e.viewBox.baseVal; + return [[e.x, e.y], [e.x + e.width, e.y + e.height]]; + } + return [[0, 0], [e.width.baseVal.value, e.height.baseVal.value]]; + } + return [[0, 0], [e.clientWidth, e.clientHeight]]; +} + +function defaultTransform() { + return this.__zoom || identity; +} + +function defaultWheelDelta(event) { + return -event.deltaY * (event.deltaMode === 1 ? 0.05 : event.deltaMode ? 1 : 0.002) * (event.ctrlKey ? 10 : 1); +} + +function defaultTouchable() { + return navigator.maxTouchPoints || ("ontouchstart" in this); +} + +function defaultConstrain(transform, extent, translateExtent) { + var dx0 = transform.invertX(extent[0][0]) - translateExtent[0][0], + dx1 = transform.invertX(extent[1][0]) - translateExtent[1][0], + dy0 = transform.invertY(extent[0][1]) - translateExtent[0][1], + dy1 = transform.invertY(extent[1][1]) - translateExtent[1][1]; + return transform.translate( + dx1 > dx0 ? (dx0 + dx1) / 2 : Math.min(0, dx0) || Math.max(0, dx1), + dy1 > dy0 ? (dy0 + dy1) / 2 : Math.min(0, dy0) || Math.max(0, dy1) + ); +} + +function zoom() { + var filter = defaultFilter, + extent = defaultExtent, + constrain = defaultConstrain, + wheelDelta = defaultWheelDelta, + touchable = defaultTouchable, + scaleExtent = [0, Infinity], + translateExtent = [[-Infinity, -Infinity], [Infinity, Infinity]], + duration = 250, + interpolate = interpolateZoom, + listeners = dispatch("start", "zoom", "end"), + touchstarting, + touchfirst, + touchending, + touchDelay = 500, + wheelDelay = 150, + clickDistance2 = 0, + tapDistance = 10; + + function zoom(selection) { + selection + .property("__zoom", defaultTransform) + .on("wheel.zoom", wheeled, {passive: false}) + .on("mousedown.zoom", mousedowned) + .on("dblclick.zoom", dblclicked) + .filter(touchable) + .on("touchstart.zoom", touchstarted) + .on("touchmove.zoom", touchmoved) + .on("touchend.zoom touchcancel.zoom", touchended) + .style("-webkit-tap-highlight-color", "rgba(0,0,0,0)"); + } + + zoom.transform = function(collection, transform, point, event) { + var selection = collection.selection ? collection.selection() : collection; + selection.property("__zoom", defaultTransform); + if (collection !== selection) { + schedule(collection, transform, point, event); + } else { + selection.interrupt().each(function() { + gesture(this, arguments) + .event(event) + .start() + .zoom(null, typeof transform === "function" ? transform.apply(this, arguments) : transform) + .end(); + }); + } + }; + + zoom.scaleBy = function(selection, k, p, event) { + zoom.scaleTo(selection, function() { + var k0 = this.__zoom.k, + k1 = typeof k === "function" ? k.apply(this, arguments) : k; + return k0 * k1; + }, p, event); + }; + + zoom.scaleTo = function(selection, k, p, event) { + zoom.transform(selection, function() { + var e = extent.apply(this, arguments), + t0 = this.__zoom, + p0 = p == null ? centroid(e) : typeof p === "function" ? p.apply(this, arguments) : p, + p1 = t0.invert(p0), + k1 = typeof k === "function" ? k.apply(this, arguments) : k; + return constrain(translate(scale(t0, k1), p0, p1), e, translateExtent); + }, p, event); + }; + + zoom.translateBy = function(selection, x, y, event) { + zoom.transform(selection, function() { + return constrain(this.__zoom.translate( + typeof x === "function" ? x.apply(this, arguments) : x, + typeof y === "function" ? y.apply(this, arguments) : y + ), extent.apply(this, arguments), translateExtent); + }, null, event); + }; + + zoom.translateTo = function(selection, x, y, p, event) { + zoom.transform(selection, function() { + var e = extent.apply(this, arguments), + t = this.__zoom, + p0 = p == null ? centroid(e) : typeof p === "function" ? p.apply(this, arguments) : p; + return constrain(identity.translate(p0[0], p0[1]).scale(t.k).translate( + typeof x === "function" ? -x.apply(this, arguments) : -x, + typeof y === "function" ? -y.apply(this, arguments) : -y + ), e, translateExtent); + }, p, event); + }; + + function scale(transform, k) { + k = Math.max(scaleExtent[0], Math.min(scaleExtent[1], k)); + return k === transform.k ? transform : new Transform(k, transform.x, transform.y); + } + + function translate(transform, p0, p1) { + var x = p0[0] - p1[0] * transform.k, y = p0[1] - p1[1] * transform.k; + return x === transform.x && y === transform.y ? transform : new Transform(transform.k, x, y); + } + + function centroid(extent) { + return [(+extent[0][0] + +extent[1][0]) / 2, (+extent[0][1] + +extent[1][1]) / 2]; + } + + function schedule(transition, transform, point, event) { + transition + .on("start.zoom", function() { gesture(this, arguments).event(event).start(); }) + .on("interrupt.zoom end.zoom", function() { gesture(this, arguments).event(event).end(); }) + .tween("zoom", function() { + var that = this, + args = arguments, + g = gesture(that, args).event(event), + e = extent.apply(that, args), + p = point == null ? centroid(e) : typeof point === "function" ? point.apply(that, args) : point, + w = Math.max(e[1][0] - e[0][0], e[1][1] - e[0][1]), + a = that.__zoom, + b = typeof transform === "function" ? transform.apply(that, args) : transform, + i = interpolate(a.invert(p).concat(w / a.k), b.invert(p).concat(w / b.k)); + return function(t) { + if (t === 1) t = b; // Avoid rounding error on end. + else { var l = i(t), k = w / l[2]; t = new Transform(k, p[0] - l[0] * k, p[1] - l[1] * k); } + g.zoom(null, t); + }; + }); + } + + function gesture(that, args, clean) { + return (!clean && that.__zooming) || new Gesture(that, args); + } + + function Gesture(that, args) { + this.that = that; + this.args = args; + this.active = 0; + this.sourceEvent = null; + this.extent = extent.apply(that, args); + this.taps = 0; + } + + Gesture.prototype = { + event: function(event) { + if (event) this.sourceEvent = event; + return this; + }, + start: function() { + if (++this.active === 1) { + this.that.__zooming = this; + this.emit("start"); + } + return this; + }, + zoom: function(key, transform) { + if (this.mouse && key !== "mouse") this.mouse[1] = transform.invert(this.mouse[0]); + if (this.touch0 && key !== "touch") this.touch0[1] = transform.invert(this.touch0[0]); + if (this.touch1 && key !== "touch") this.touch1[1] = transform.invert(this.touch1[0]); + this.that.__zoom = transform; + this.emit("zoom"); + return this; + }, + end: function() { + if (--this.active === 0) { + delete this.that.__zooming; + this.emit("end"); + } + return this; + }, + emit: function(type) { + var d = select(this.that).datum(); + listeners.call( + type, + this.that, + new ZoomEvent(type, { + sourceEvent: this.sourceEvent, + target: zoom, + type, + transform: this.that.__zoom, + dispatch: listeners + }), + d + ); + } + }; + + function wheeled(event, ...args) { + if (!filter.apply(this, arguments)) return; + var g = gesture(this, args).event(event), + t = this.__zoom, + k = Math.max(scaleExtent[0], Math.min(scaleExtent[1], t.k * Math.pow(2, wheelDelta.apply(this, arguments)))), + p = pointer(event); + + // If the mouse is in the same location as before, reuse it. + // If there were recent wheel events, reset the wheel idle timeout. + if (g.wheel) { + if (g.mouse[0][0] !== p[0] || g.mouse[0][1] !== p[1]) { + g.mouse[1] = t.invert(g.mouse[0] = p); + } + clearTimeout(g.wheel); + } + + // If this wheel event won’t trigger a transform change, ignore it. + else if (t.k === k) return; + + // Otherwise, capture the mouse point and location at the start. + else { + g.mouse = [p, t.invert(p)]; + interrupt(this); + g.start(); + } + + noevent(event); + g.wheel = setTimeout(wheelidled, wheelDelay); + g.zoom("mouse", constrain(translate(scale(t, k), g.mouse[0], g.mouse[1]), g.extent, translateExtent)); + + function wheelidled() { + g.wheel = null; + g.end(); + } + } + + function mousedowned(event, ...args) { + if (touchending || !filter.apply(this, arguments)) return; + var currentTarget = event.currentTarget, + g = gesture(this, args, true).event(event), + v = select(event.view).on("mousemove.zoom", mousemoved, true).on("mouseup.zoom", mouseupped, true), + p = pointer(event, currentTarget), + x0 = event.clientX, + y0 = event.clientY; + + dragDisable(event.view); + nopropagation(event); + g.mouse = [p, this.__zoom.invert(p)]; + interrupt(this); + g.start(); + + function mousemoved(event) { + noevent(event); + if (!g.moved) { + var dx = event.clientX - x0, dy = event.clientY - y0; + g.moved = dx * dx + dy * dy > clickDistance2; + } + g.event(event) + .zoom("mouse", constrain(translate(g.that.__zoom, g.mouse[0] = pointer(event, currentTarget), g.mouse[1]), g.extent, translateExtent)); + } + + function mouseupped(event) { + v.on("mousemove.zoom mouseup.zoom", null); + yesdrag(event.view, g.moved); + noevent(event); + g.event(event).end(); + } + } + + function dblclicked(event, ...args) { + if (!filter.apply(this, arguments)) return; + var t0 = this.__zoom, + p0 = pointer(event.changedTouches ? event.changedTouches[0] : event, this), + p1 = t0.invert(p0), + k1 = t0.k * (event.shiftKey ? 0.5 : 2), + t1 = constrain(translate(scale(t0, k1), p0, p1), extent.apply(this, args), translateExtent); + + noevent(event); + if (duration > 0) select(this).transition().duration(duration).call(schedule, t1, p0, event); + else select(this).call(zoom.transform, t1, p0, event); + } + + function touchstarted(event, ...args) { + if (!filter.apply(this, arguments)) return; + var touches = event.touches, + n = touches.length, + g = gesture(this, args, event.changedTouches.length === n).event(event), + started, i, t, p; + + nopropagation(event); + for (i = 0; i < n; ++i) { + t = touches[i], p = pointer(t, this); + p = [p, this.__zoom.invert(p), t.identifier]; + if (!g.touch0) g.touch0 = p, started = true, g.taps = 1 + !!touchstarting; + else if (!g.touch1 && g.touch0[2] !== p[2]) g.touch1 = p, g.taps = 0; + } + + if (touchstarting) touchstarting = clearTimeout(touchstarting); + + if (started) { + if (g.taps < 2) touchfirst = p[0], touchstarting = setTimeout(function() { touchstarting = null; }, touchDelay); + interrupt(this); + g.start(); + } + } + + function touchmoved(event, ...args) { + if (!this.__zooming) return; + var g = gesture(this, args).event(event), + touches = event.changedTouches, + n = touches.length, i, t, p, l; + + noevent(event); + for (i = 0; i < n; ++i) { + t = touches[i], p = pointer(t, this); + if (g.touch0 && g.touch0[2] === t.identifier) g.touch0[0] = p; + else if (g.touch1 && g.touch1[2] === t.identifier) g.touch1[0] = p; + } + t = g.that.__zoom; + if (g.touch1) { + var p0 = g.touch0[0], l0 = g.touch0[1], + p1 = g.touch1[0], l1 = g.touch1[1], + dp = (dp = p1[0] - p0[0]) * dp + (dp = p1[1] - p0[1]) * dp, + dl = (dl = l1[0] - l0[0]) * dl + (dl = l1[1] - l0[1]) * dl; + t = scale(t, Math.sqrt(dp / dl)); + p = [(p0[0] + p1[0]) / 2, (p0[1] + p1[1]) / 2]; + l = [(l0[0] + l1[0]) / 2, (l0[1] + l1[1]) / 2]; + } + else if (g.touch0) p = g.touch0[0], l = g.touch0[1]; + else return; + + g.zoom("touch", constrain(translate(t, p, l), g.extent, translateExtent)); + } + + function touchended(event, ...args) { + if (!this.__zooming) return; + var g = gesture(this, args).event(event), + touches = event.changedTouches, + n = touches.length, i, t; + + nopropagation(event); + if (touchending) clearTimeout(touchending); + touchending = setTimeout(function() { touchending = null; }, touchDelay); + for (i = 0; i < n; ++i) { + t = touches[i]; + if (g.touch0 && g.touch0[2] === t.identifier) delete g.touch0; + else if (g.touch1 && g.touch1[2] === t.identifier) delete g.touch1; + } + if (g.touch1 && !g.touch0) g.touch0 = g.touch1, delete g.touch1; + if (g.touch0) g.touch0[1] = this.__zoom.invert(g.touch0[0]); + else { + g.end(); + // If this was a dbltap, reroute to the (optional) dblclick.zoom handler. + if (g.taps === 2) { + t = pointer(t, this); + if (Math.hypot(touchfirst[0] - t[0], touchfirst[1] - t[1]) < tapDistance) { + var p = select(this).on("dblclick.zoom"); + if (p) p.apply(this, arguments); + } + } + } + } + + zoom.wheelDelta = function(_) { + return arguments.length ? (wheelDelta = typeof _ === "function" ? _ : constant(+_), zoom) : wheelDelta; + }; + + zoom.filter = function(_) { + return arguments.length ? (filter = typeof _ === "function" ? _ : constant(!!_), zoom) : filter; + }; + + zoom.touchable = function(_) { + return arguments.length ? (touchable = typeof _ === "function" ? _ : constant(!!_), zoom) : touchable; + }; + + zoom.extent = function(_) { + return arguments.length ? (extent = typeof _ === "function" ? _ : constant([[+_[0][0], +_[0][1]], [+_[1][0], +_[1][1]]]), zoom) : extent; + }; + + zoom.scaleExtent = function(_) { + return arguments.length ? (scaleExtent[0] = +_[0], scaleExtent[1] = +_[1], zoom) : [scaleExtent[0], scaleExtent[1]]; + }; + + zoom.translateExtent = function(_) { + return arguments.length ? (translateExtent[0][0] = +_[0][0], translateExtent[1][0] = +_[1][0], translateExtent[0][1] = +_[0][1], translateExtent[1][1] = +_[1][1], zoom) : [[translateExtent[0][0], translateExtent[0][1]], [translateExtent[1][0], translateExtent[1][1]]]; + }; + + zoom.constrain = function(_) { + return arguments.length ? (constrain = _, zoom) : constrain; + }; + + zoom.duration = function(_) { + return arguments.length ? (duration = +_, zoom) : duration; + }; + + zoom.interpolate = function(_) { + return arguments.length ? (interpolate = _, zoom) : interpolate; + }; + + zoom.on = function() { + var value = listeners.on.apply(listeners, arguments); + return value === listeners ? zoom : value; + }; + + zoom.clickDistance = function(_) { + return arguments.length ? (clickDistance2 = (_ = +_) * _, zoom) : Math.sqrt(clickDistance2); + }; + + zoom.tapDistance = function(_) { + return arguments.length ? (tapDistance = +_, zoom) : tapDistance; + }; + + return zoom; +} + +exports.Adder = Adder; +exports.Delaunay = Delaunay; +exports.FormatSpecifier = FormatSpecifier; +exports.InternMap = InternMap; +exports.InternSet = InternSet; +exports.Node = Node$1; +exports.Path = Path$1; +exports.Voronoi = Voronoi; +exports.ZoomTransform = Transform; +exports.active = active; +exports.arc = arc; +exports.area = area; +exports.areaRadial = areaRadial; +exports.ascending = ascending$3; +exports.autoType = autoType; +exports.axisBottom = axisBottom; +exports.axisLeft = axisLeft; +exports.axisRight = axisRight; +exports.axisTop = axisTop; +exports.bin = bin; +exports.bisect = bisect; +exports.bisectCenter = bisectCenter; +exports.bisectLeft = bisectLeft; +exports.bisectRight = bisectRight; +exports.bisector = bisector; +exports.blob = blob; +exports.blur = blur; +exports.blur2 = blur2; +exports.blurImage = blurImage; +exports.brush = brush; +exports.brushSelection = brushSelection; +exports.brushX = brushX; +exports.brushY = brushY; +exports.buffer = buffer; +exports.chord = chord; +exports.chordDirected = chordDirected; +exports.chordTranspose = chordTranspose; +exports.cluster = cluster; +exports.color = color; +exports.contourDensity = density; +exports.contours = Contours; +exports.count = count$1; +exports.create = create$1; +exports.creator = creator; +exports.cross = cross$2; +exports.csv = csv; +exports.csvFormat = csvFormat; +exports.csvFormatBody = csvFormatBody; +exports.csvFormatRow = csvFormatRow; +exports.csvFormatRows = csvFormatRows; +exports.csvFormatValue = csvFormatValue; +exports.csvParse = csvParse; +exports.csvParseRows = csvParseRows; +exports.cubehelix = cubehelix$3; +exports.cumsum = cumsum; +exports.curveBasis = basis; +exports.curveBasisClosed = basisClosed; +exports.curveBasisOpen = basisOpen; +exports.curveBumpX = bumpX; +exports.curveBumpY = bumpY; +exports.curveBundle = bundle; +exports.curveCardinal = cardinal; +exports.curveCardinalClosed = cardinalClosed; +exports.curveCardinalOpen = cardinalOpen; +exports.curveCatmullRom = catmullRom; +exports.curveCatmullRomClosed = catmullRomClosed; +exports.curveCatmullRomOpen = catmullRomOpen; +exports.curveLinear = curveLinear; +exports.curveLinearClosed = linearClosed; +exports.curveMonotoneX = monotoneX; +exports.curveMonotoneY = monotoneY; +exports.curveNatural = natural; +exports.curveStep = step; +exports.curveStepAfter = stepAfter; +exports.curveStepBefore = stepBefore; +exports.descending = descending$2; +exports.deviation = deviation; +exports.difference = difference; +exports.disjoint = disjoint; +exports.dispatch = dispatch; +exports.drag = drag; +exports.dragDisable = dragDisable; +exports.dragEnable = yesdrag; +exports.dsv = dsv; +exports.dsvFormat = dsvFormat; +exports.easeBack = backInOut; +exports.easeBackIn = backIn; +exports.easeBackInOut = backInOut; +exports.easeBackOut = backOut; +exports.easeBounce = bounceOut; +exports.easeBounceIn = bounceIn; +exports.easeBounceInOut = bounceInOut; +exports.easeBounceOut = bounceOut; +exports.easeCircle = circleInOut; +exports.easeCircleIn = circleIn; +exports.easeCircleInOut = circleInOut; +exports.easeCircleOut = circleOut; +exports.easeCubic = cubicInOut; +exports.easeCubicIn = cubicIn; +exports.easeCubicInOut = cubicInOut; +exports.easeCubicOut = cubicOut; +exports.easeElastic = elasticOut; +exports.easeElasticIn = elasticIn; +exports.easeElasticInOut = elasticInOut; +exports.easeElasticOut = elasticOut; +exports.easeExp = expInOut; +exports.easeExpIn = expIn; +exports.easeExpInOut = expInOut; +exports.easeExpOut = expOut; +exports.easeLinear = linear$1; +exports.easePoly = polyInOut; +exports.easePolyIn = polyIn; +exports.easePolyInOut = polyInOut; +exports.easePolyOut = polyOut; +exports.easeQuad = quadInOut; +exports.easeQuadIn = quadIn; +exports.easeQuadInOut = quadInOut; +exports.easeQuadOut = quadOut; +exports.easeSin = sinInOut; +exports.easeSinIn = sinIn; +exports.easeSinInOut = sinInOut; +exports.easeSinOut = sinOut; +exports.every = every; +exports.extent = extent$1; +exports.fcumsum = fcumsum; +exports.filter = filter$1; +exports.flatGroup = flatGroup; +exports.flatRollup = flatRollup; +exports.forceCenter = center; +exports.forceCollide = collide; +exports.forceLink = link$2; +exports.forceManyBody = manyBody; +exports.forceRadial = radial$1; +exports.forceSimulation = simulation; +exports.forceX = x$1; +exports.forceY = y$1; +exports.formatDefaultLocale = defaultLocale$1; +exports.formatLocale = formatLocale$1; +exports.formatSpecifier = formatSpecifier; +exports.fsum = fsum; +exports.geoAlbers = albers; +exports.geoAlbersUsa = albersUsa; +exports.geoArea = area$2; +exports.geoAzimuthalEqualArea = azimuthalEqualArea; +exports.geoAzimuthalEqualAreaRaw = azimuthalEqualAreaRaw; +exports.geoAzimuthalEquidistant = azimuthalEquidistant; +exports.geoAzimuthalEquidistantRaw = azimuthalEquidistantRaw; +exports.geoBounds = bounds; +exports.geoCentroid = centroid$1; +exports.geoCircle = circle$1; +exports.geoClipAntimeridian = clipAntimeridian; +exports.geoClipCircle = clipCircle; +exports.geoClipExtent = extent; +exports.geoClipRectangle = clipRectangle; +exports.geoConicConformal = conicConformal; +exports.geoConicConformalRaw = conicConformalRaw; +exports.geoConicEqualArea = conicEqualArea; +exports.geoConicEqualAreaRaw = conicEqualAreaRaw; +exports.geoConicEquidistant = conicEquidistant; +exports.geoConicEquidistantRaw = conicEquidistantRaw; +exports.geoContains = contains$1; +exports.geoDistance = distance; +exports.geoEqualEarth = equalEarth; +exports.geoEqualEarthRaw = equalEarthRaw; +exports.geoEquirectangular = equirectangular; +exports.geoEquirectangularRaw = equirectangularRaw; +exports.geoGnomonic = gnomonic; +exports.geoGnomonicRaw = gnomonicRaw; +exports.geoGraticule = graticule; +exports.geoGraticule10 = graticule10; +exports.geoIdentity = identity$4; +exports.geoInterpolate = interpolate; +exports.geoLength = length$1; +exports.geoMercator = mercator; +exports.geoMercatorRaw = mercatorRaw; +exports.geoNaturalEarth1 = naturalEarth1; +exports.geoNaturalEarth1Raw = naturalEarth1Raw; +exports.geoOrthographic = orthographic; +exports.geoOrthographicRaw = orthographicRaw; +exports.geoPath = index$2; +exports.geoProjection = projection; +exports.geoProjectionMutator = projectionMutator; +exports.geoRotation = rotation; +exports.geoStereographic = stereographic; +exports.geoStereographicRaw = stereographicRaw; +exports.geoStream = geoStream; +exports.geoTransform = transform$1; +exports.geoTransverseMercator = transverseMercator; +exports.geoTransverseMercatorRaw = transverseMercatorRaw; +exports.gray = gray; +exports.greatest = greatest; +exports.greatestIndex = greatestIndex; +exports.group = group; +exports.groupSort = groupSort; +exports.groups = groups; +exports.hcl = hcl$2; +exports.hierarchy = hierarchy; +exports.histogram = bin; +exports.hsl = hsl$2; +exports.html = html; +exports.image = image; +exports.index = index$4; +exports.indexes = indexes; +exports.interpolate = interpolate$2; +exports.interpolateArray = array$3; +exports.interpolateBasis = basis$2; +exports.interpolateBasisClosed = basisClosed$1; +exports.interpolateBlues = Blues; +exports.interpolateBrBG = BrBG; +exports.interpolateBuGn = BuGn; +exports.interpolateBuPu = BuPu; +exports.interpolateCividis = cividis; +exports.interpolateCool = cool; +exports.interpolateCubehelix = cubehelix$2; +exports.interpolateCubehelixDefault = cubehelix; +exports.interpolateCubehelixLong = cubehelixLong; +exports.interpolateDate = date$1; +exports.interpolateDiscrete = discrete; +exports.interpolateGnBu = GnBu; +exports.interpolateGreens = Greens; +exports.interpolateGreys = Greys; +exports.interpolateHcl = hcl$1; +exports.interpolateHclLong = hclLong; +exports.interpolateHsl = hsl$1; +exports.interpolateHslLong = hslLong; +exports.interpolateHue = hue; +exports.interpolateInferno = inferno; +exports.interpolateLab = lab; +exports.interpolateMagma = magma; +exports.interpolateNumber = interpolateNumber; +exports.interpolateNumberArray = numberArray; +exports.interpolateObject = object$1; +exports.interpolateOrRd = OrRd; +exports.interpolateOranges = Oranges; +exports.interpolatePRGn = PRGn; +exports.interpolatePiYG = PiYG; +exports.interpolatePlasma = plasma; +exports.interpolatePuBu = PuBu; +exports.interpolatePuBuGn = PuBuGn; +exports.interpolatePuOr = PuOr; +exports.interpolatePuRd = PuRd; +exports.interpolatePurples = Purples; +exports.interpolateRainbow = rainbow; +exports.interpolateRdBu = RdBu; +exports.interpolateRdGy = RdGy; +exports.interpolateRdPu = RdPu; +exports.interpolateRdYlBu = RdYlBu; +exports.interpolateRdYlGn = RdYlGn; +exports.interpolateReds = Reds; +exports.interpolateRgb = interpolateRgb; +exports.interpolateRgbBasis = rgbBasis; +exports.interpolateRgbBasisClosed = rgbBasisClosed; +exports.interpolateRound = interpolateRound; +exports.interpolateSinebow = sinebow; +exports.interpolateSpectral = Spectral; +exports.interpolateString = interpolateString; +exports.interpolateTransformCss = interpolateTransformCss; +exports.interpolateTransformSvg = interpolateTransformSvg; +exports.interpolateTurbo = turbo; +exports.interpolateViridis = viridis; +exports.interpolateWarm = warm; +exports.interpolateYlGn = YlGn; +exports.interpolateYlGnBu = YlGnBu; +exports.interpolateYlOrBr = YlOrBr; +exports.interpolateYlOrRd = YlOrRd; +exports.interpolateZoom = interpolateZoom; +exports.interrupt = interrupt; +exports.intersection = intersection; +exports.interval = interval; +exports.isoFormat = formatIso$1; +exports.isoParse = parseIso$1; +exports.json = json; +exports.lab = lab$1; +exports.lch = lch; +exports.least = least; +exports.leastIndex = leastIndex; +exports.line = line; +exports.lineRadial = lineRadial$1; +exports.link = link; +exports.linkHorizontal = linkHorizontal; +exports.linkRadial = linkRadial; +exports.linkVertical = linkVertical; +exports.local = local$1; +exports.map = map$1; +exports.matcher = matcher; +exports.max = max$3; +exports.maxIndex = maxIndex; +exports.mean = mean; +exports.median = median; +exports.medianIndex = medianIndex; +exports.merge = merge; +exports.min = min$2; +exports.minIndex = minIndex; +exports.mode = mode; +exports.namespace = namespace; +exports.namespaces = namespaces; +exports.nice = nice$1; +exports.now = now; +exports.pack = index$1; +exports.packEnclose = enclose; +exports.packSiblings = siblings; +exports.pairs = pairs; +exports.partition = partition; +exports.path = path; +exports.pathRound = pathRound; +exports.permute = permute; +exports.pie = pie; +exports.piecewise = piecewise; +exports.pointRadial = pointRadial; +exports.pointer = pointer; +exports.pointers = pointers; +exports.polygonArea = area$1; +exports.polygonCentroid = centroid; +exports.polygonContains = contains; +exports.polygonHull = hull; +exports.polygonLength = length; +exports.precisionFixed = precisionFixed; +exports.precisionPrefix = precisionPrefix; +exports.precisionRound = precisionRound; +exports.quadtree = quadtree; +exports.quantile = quantile$1; +exports.quantileIndex = quantileIndex; +exports.quantileSorted = quantileSorted; +exports.quantize = quantize$1; +exports.quickselect = quickselect; +exports.radialArea = areaRadial; +exports.radialLine = lineRadial$1; +exports.randomBates = bates; +exports.randomBernoulli = bernoulli; +exports.randomBeta = beta; +exports.randomBinomial = binomial; +exports.randomCauchy = cauchy; +exports.randomExponential = exponential; +exports.randomGamma = gamma; +exports.randomGeometric = geometric; +exports.randomInt = int; +exports.randomIrwinHall = irwinHall; +exports.randomLcg = lcg; +exports.randomLogNormal = logNormal; +exports.randomLogistic = logistic; +exports.randomNormal = normal; +exports.randomPareto = pareto; +exports.randomPoisson = poisson; +exports.randomUniform = uniform; +exports.randomWeibull = weibull; +exports.range = range$2; +exports.rank = rank; +exports.reduce = reduce; +exports.reverse = reverse$1; +exports.rgb = rgb; +exports.ribbon = ribbon$1; +exports.ribbonArrow = ribbonArrow; +exports.rollup = rollup; +exports.rollups = rollups; +exports.scaleBand = band; +exports.scaleDiverging = diverging$1; +exports.scaleDivergingLog = divergingLog; +exports.scaleDivergingPow = divergingPow; +exports.scaleDivergingSqrt = divergingSqrt; +exports.scaleDivergingSymlog = divergingSymlog; +exports.scaleIdentity = identity$2; +exports.scaleImplicit = implicit; +exports.scaleLinear = linear; +exports.scaleLog = log; +exports.scaleOrdinal = ordinal; +exports.scalePoint = point$4; +exports.scalePow = pow; +exports.scaleQuantile = quantile; +exports.scaleQuantize = quantize; +exports.scaleRadial = radial; +exports.scaleSequential = sequential; +exports.scaleSequentialLog = sequentialLog; +exports.scaleSequentialPow = sequentialPow; +exports.scaleSequentialQuantile = sequentialQuantile; +exports.scaleSequentialSqrt = sequentialSqrt; +exports.scaleSequentialSymlog = sequentialSymlog; +exports.scaleSqrt = sqrt$1; +exports.scaleSymlog = symlog; +exports.scaleThreshold = threshold; +exports.scaleTime = time; +exports.scaleUtc = utcTime; +exports.scan = scan; +exports.schemeAccent = Accent; +exports.schemeBlues = scheme$5; +exports.schemeBrBG = scheme$q; +exports.schemeBuGn = scheme$h; +exports.schemeBuPu = scheme$g; +exports.schemeCategory10 = category10; +exports.schemeDark2 = Dark2; +exports.schemeGnBu = scheme$f; +exports.schemeGreens = scheme$4; +exports.schemeGreys = scheme$3; +exports.schemeObservable10 = observable10; +exports.schemeOrRd = scheme$e; +exports.schemeOranges = scheme; +exports.schemePRGn = scheme$p; +exports.schemePaired = Paired; +exports.schemePastel1 = Pastel1; +exports.schemePastel2 = Pastel2; +exports.schemePiYG = scheme$o; +exports.schemePuBu = scheme$c; +exports.schemePuBuGn = scheme$d; +exports.schemePuOr = scheme$n; +exports.schemePuRd = scheme$b; +exports.schemePurples = scheme$2; +exports.schemeRdBu = scheme$m; +exports.schemeRdGy = scheme$l; +exports.schemeRdPu = scheme$a; +exports.schemeRdYlBu = scheme$k; +exports.schemeRdYlGn = scheme$j; +exports.schemeReds = scheme$1; +exports.schemeSet1 = Set1; +exports.schemeSet2 = Set2; +exports.schemeSet3 = Set3; +exports.schemeSpectral = scheme$i; +exports.schemeTableau10 = Tableau10; +exports.schemeYlGn = scheme$8; +exports.schemeYlGnBu = scheme$9; +exports.schemeYlOrBr = scheme$7; +exports.schemeYlOrRd = scheme$6; +exports.select = select; +exports.selectAll = selectAll; +exports.selection = selection; +exports.selector = selector; +exports.selectorAll = selectorAll; +exports.shuffle = shuffle$1; +exports.shuffler = shuffler; +exports.some = some; +exports.sort = sort; +exports.stack = stack; +exports.stackOffsetDiverging = diverging; +exports.stackOffsetExpand = expand; +exports.stackOffsetNone = none$1; +exports.stackOffsetSilhouette = silhouette; +exports.stackOffsetWiggle = wiggle; +exports.stackOrderAppearance = appearance; +exports.stackOrderAscending = ascending; +exports.stackOrderDescending = descending; +exports.stackOrderInsideOut = insideOut; +exports.stackOrderNone = none; +exports.stackOrderReverse = reverse; +exports.stratify = stratify; +exports.style = styleValue; +exports.subset = subset; +exports.sum = sum$2; +exports.superset = superset; +exports.svg = svg; +exports.symbol = Symbol$1; +exports.symbolAsterisk = asterisk; +exports.symbolCircle = circle; +exports.symbolCross = cross; +exports.symbolDiamond = diamond; +exports.symbolDiamond2 = diamond2; +exports.symbolPlus = plus; +exports.symbolSquare = square; +exports.symbolSquare2 = square2; +exports.symbolStar = star; +exports.symbolTimes = times; +exports.symbolTriangle = triangle; +exports.symbolTriangle2 = triangle2; +exports.symbolWye = wye; +exports.symbolX = times; +exports.symbols = symbolsFill; +exports.symbolsFill = symbolsFill; +exports.symbolsStroke = symbolsStroke; +exports.text = text; +exports.thresholdFreedmanDiaconis = thresholdFreedmanDiaconis; +exports.thresholdScott = thresholdScott; +exports.thresholdSturges = thresholdSturges; +exports.tickFormat = tickFormat; +exports.tickIncrement = tickIncrement; +exports.tickStep = tickStep; +exports.ticks = ticks; +exports.timeDay = timeDay; +exports.timeDays = timeDays; +exports.timeFormatDefaultLocale = defaultLocale; +exports.timeFormatLocale = formatLocale; +exports.timeFriday = timeFriday; +exports.timeFridays = timeFridays; +exports.timeHour = timeHour; +exports.timeHours = timeHours; +exports.timeInterval = timeInterval; +exports.timeMillisecond = millisecond; +exports.timeMilliseconds = milliseconds; +exports.timeMinute = timeMinute; +exports.timeMinutes = timeMinutes; +exports.timeMonday = timeMonday; +exports.timeMondays = timeMondays; +exports.timeMonth = timeMonth; +exports.timeMonths = timeMonths; +exports.timeSaturday = timeSaturday; +exports.timeSaturdays = timeSaturdays; +exports.timeSecond = second; +exports.timeSeconds = seconds; +exports.timeSunday = timeSunday; +exports.timeSundays = timeSundays; +exports.timeThursday = timeThursday; +exports.timeThursdays = timeThursdays; +exports.timeTickInterval = timeTickInterval; +exports.timeTicks = timeTicks; +exports.timeTuesday = timeTuesday; +exports.timeTuesdays = timeTuesdays; +exports.timeWednesday = timeWednesday; +exports.timeWednesdays = timeWednesdays; +exports.timeWeek = timeSunday; +exports.timeWeeks = timeSundays; +exports.timeYear = timeYear; +exports.timeYears = timeYears; +exports.timeout = timeout; +exports.timer = timer; +exports.timerFlush = timerFlush; +exports.transition = transition; +exports.transpose = transpose; +exports.tree = tree; +exports.treemap = index; +exports.treemapBinary = binary; +exports.treemapDice = treemapDice; +exports.treemapResquarify = resquarify; +exports.treemapSlice = treemapSlice; +exports.treemapSliceDice = sliceDice; +exports.treemapSquarify = squarify; +exports.tsv = tsv; +exports.tsvFormat = tsvFormat; +exports.tsvFormatBody = tsvFormatBody; +exports.tsvFormatRow = tsvFormatRow; +exports.tsvFormatRows = tsvFormatRows; +exports.tsvFormatValue = tsvFormatValue; +exports.tsvParse = tsvParse; +exports.tsvParseRows = tsvParseRows; +exports.union = union; +exports.unixDay = unixDay; +exports.unixDays = unixDays; +exports.utcDay = utcDay; +exports.utcDays = utcDays; +exports.utcFriday = utcFriday; +exports.utcFridays = utcFridays; +exports.utcHour = utcHour; +exports.utcHours = utcHours; +exports.utcMillisecond = millisecond; +exports.utcMilliseconds = milliseconds; +exports.utcMinute = utcMinute; +exports.utcMinutes = utcMinutes; +exports.utcMonday = utcMonday; +exports.utcMondays = utcMondays; +exports.utcMonth = utcMonth; +exports.utcMonths = utcMonths; +exports.utcSaturday = utcSaturday; +exports.utcSaturdays = utcSaturdays; +exports.utcSecond = second; +exports.utcSeconds = seconds; +exports.utcSunday = utcSunday; +exports.utcSundays = utcSundays; +exports.utcThursday = utcThursday; +exports.utcThursdays = utcThursdays; +exports.utcTickInterval = utcTickInterval; +exports.utcTicks = utcTicks; +exports.utcTuesday = utcTuesday; +exports.utcTuesdays = utcTuesdays; +exports.utcWednesday = utcWednesday; +exports.utcWednesdays = utcWednesdays; +exports.utcWeek = utcSunday; +exports.utcWeeks = utcSundays; +exports.utcYear = utcYear; +exports.utcYears = utcYears; +exports.variance = variance; +exports.version = version; +exports.window = defaultView; +exports.xml = xml; +exports.zip = zip; +exports.zoom = zoom; +exports.zoomIdentity = identity; +exports.zoomTransform = transform; + +})); diff --git a/frontend/node_modules/d3/dist/d3.min.js b/frontend/node_modules/d3/dist/d3.min.js new file mode 100644 index 0000000..33bb880 --- /dev/null +++ b/frontend/node_modules/d3/dist/d3.min.js @@ -0,0 +1,2 @@ +// https://d3js.org v7.9.0 Copyright 2010-2023 Mike Bostock +!function(t,n){"object"==typeof exports&&"undefined"!=typeof module?n(exports):"function"==typeof define&&define.amd?define(["exports"],n):n((t="undefined"!=typeof globalThis?globalThis:t||self).d3=t.d3||{})}(this,(function(t){"use strict";function n(t,n){return null==t||null==n?NaN:tn?1:t>=n?0:NaN}function e(t,n){return null==t||null==n?NaN:nt?1:n>=t?0:NaN}function r(t){let r,o,a;function u(t,n,e=0,i=t.length){if(e>>1;o(t[r],n)<0?e=r+1:i=r}while(en(t(e),r),a=(n,e)=>t(n)-e):(r=t===n||t===e?t:i,o=t,a=t),{left:u,center:function(t,n,e=0,r=t.length){const i=u(t,n,e,r-1);return i>e&&a(t[i-1],n)>-a(t[i],n)?i-1:i},right:function(t,n,e=0,i=t.length){if(e>>1;o(t[r],n)<=0?e=r+1:i=r}while(e{n(t,e,(r<<=2)+0,(i<<=2)+0,o<<=2),n(t,e,r+1,i+1,o),n(t,e,r+2,i+2,o),n(t,e,r+3,i+3,o)}}));function d(t){return function(n,e,r=e){if(!((e=+e)>=0))throw new RangeError("invalid rx");if(!((r=+r)>=0))throw new RangeError("invalid ry");let{data:i,width:o,height:a}=n;if(!((o=Math.floor(o))>=0))throw new RangeError("invalid width");if(!((a=Math.floor(void 0!==a?a:i.length/o))>=0))throw new RangeError("invalid height");if(!o||!a||!e&&!r)return n;const u=e&&t(e),c=r&&t(r),f=i.slice();return u&&c?(p(u,f,i,o,a),p(u,i,f,o,a),p(u,f,i,o,a),g(c,i,f,o,a),g(c,f,i,o,a),g(c,i,f,o,a)):u?(p(u,i,f,o,a),p(u,f,i,o,a),p(u,i,f,o,a)):c&&(g(c,i,f,o,a),g(c,f,i,o,a),g(c,i,f,o,a)),n}}function p(t,n,e,r,i){for(let o=0,a=r*i;o{if(!((o-=a)>=i))return;let u=t*r[i];const c=a*t;for(let t=i,n=i+c;t{if(!((a-=u)>=o))return;let c=n*i[o];const f=u*n,s=f+u;for(let t=o,n=o+f;t=n&&++e;else{let r=-1;for(let i of t)null!=(i=n(i,++r,t))&&(i=+i)>=i&&++e}return e}function _(t){return 0|t.length}function b(t){return!(t>0)}function m(t){return"object"!=typeof t||"length"in t?t:Array.from(t)}function x(t,n){let e,r=0,i=0,o=0;if(void 0===n)for(let n of t)null!=n&&(n=+n)>=n&&(e=n-i,i+=e/++r,o+=e*(n-i));else{let a=-1;for(let u of t)null!=(u=n(u,++a,t))&&(u=+u)>=u&&(e=u-i,i+=e/++r,o+=e*(u-i))}if(r>1)return o/(r-1)}function w(t,n){const e=x(t,n);return e?Math.sqrt(e):e}function M(t,n){let e,r;if(void 0===n)for(const n of t)null!=n&&(void 0===e?n>=n&&(e=r=n):(e>n&&(e=n),r=o&&(e=r=o):(e>o&&(e=o),r0){for(o=t[--i];i>0&&(n=o,e=t[--i],o=n+e,r=e-(o-n),!r););i>0&&(r<0&&t[i-1]<0||r>0&&t[i-1]>0)&&(e=2*r,n=o+e,e==n-o&&(o=n))}return o}}class InternMap extends Map{constructor(t,n=N){if(super(),Object.defineProperties(this,{_intern:{value:new Map},_key:{value:n}}),null!=t)for(const[n,e]of t)this.set(n,e)}get(t){return super.get(A(this,t))}has(t){return super.has(A(this,t))}set(t,n){return super.set(S(this,t),n)}delete(t){return super.delete(E(this,t))}}class InternSet extends Set{constructor(t,n=N){if(super(),Object.defineProperties(this,{_intern:{value:new Map},_key:{value:n}}),null!=t)for(const n of t)this.add(n)}has(t){return super.has(A(this,t))}add(t){return super.add(S(this,t))}delete(t){return super.delete(E(this,t))}}function A({_intern:t,_key:n},e){const r=n(e);return t.has(r)?t.get(r):e}function S({_intern:t,_key:n},e){const r=n(e);return t.has(r)?t.get(r):(t.set(r,e),e)}function E({_intern:t,_key:n},e){const r=n(e);return t.has(r)&&(e=t.get(r),t.delete(r)),e}function N(t){return null!==t&&"object"==typeof t?t.valueOf():t}function k(t){return t}function C(t,...n){return F(t,k,k,n)}function P(t,...n){return F(t,Array.from,k,n)}function z(t,n){for(let e=1,r=n.length;et.pop().map((([n,e])=>[...t,n,e]))));return t}function $(t,n,...e){return F(t,k,n,e)}function D(t,n,...e){return F(t,Array.from,n,e)}function R(t){if(1!==t.length)throw new Error("duplicate key");return t[0]}function F(t,n,e,r){return function t(i,o){if(o>=r.length)return e(i);const a=new InternMap,u=r[o++];let c=-1;for(const t of i){const n=u(t,++c,i),e=a.get(n);e?e.push(t):a.set(n,[t])}for(const[n,e]of a)a.set(n,t(e,o));return n(a)}(t,0)}function q(t,n){return Array.from(n,(n=>t[n]))}function U(t,...n){if("function"!=typeof t[Symbol.iterator])throw new TypeError("values is not iterable");t=Array.from(t);let[e]=n;if(e&&2!==e.length||n.length>1){const r=Uint32Array.from(t,((t,n)=>n));return n.length>1?(n=n.map((n=>t.map(n))),r.sort(((t,e)=>{for(const r of n){const n=O(r[t],r[e]);if(n)return n}}))):(e=t.map(e),r.sort(((t,n)=>O(e[t],e[n])))),q(t,r)}return t.sort(I(e))}function I(t=n){if(t===n)return O;if("function"!=typeof t)throw new TypeError("compare is not a function");return(n,e)=>{const r=t(n,e);return r||0===r?r:(0===t(e,e))-(0===t(n,n))}}function O(t,n){return(null==t||!(t>=t))-(null==n||!(n>=n))||(tn?1:0)}var B=Array.prototype.slice;function Y(t){return()=>t}const L=Math.sqrt(50),j=Math.sqrt(10),H=Math.sqrt(2);function X(t,n,e){const r=(n-t)/Math.max(0,e),i=Math.floor(Math.log10(r)),o=r/Math.pow(10,i),a=o>=L?10:o>=j?5:o>=H?2:1;let u,c,f;return i<0?(f=Math.pow(10,-i)/a,u=Math.round(t*f),c=Math.round(n*f),u/fn&&--c,f=-f):(f=Math.pow(10,i)*a,u=Math.round(t/f),c=Math.round(n/f),u*fn&&--c),c0))return[];if((t=+t)===(n=+n))return[t];const r=n=i))return[];const u=o-i+1,c=new Array(u);if(r)if(a<0)for(let t=0;t0?(t=Math.floor(t/i)*i,n=Math.ceil(n/i)*i):i<0&&(t=Math.ceil(t*i)/i,n=Math.floor(n*i)/i),r=i}}function K(t){return Math.max(1,Math.ceil(Math.log(v(t))/Math.LN2)+1)}function Q(){var t=k,n=M,e=K;function r(r){Array.isArray(r)||(r=Array.from(r));var i,o,a,u=r.length,c=new Array(u);for(i=0;i=h)if(t>=h&&n===M){const t=V(l,h,e);isFinite(t)&&(t>0?h=(Math.floor(h/t)+1)*t:t<0&&(h=(Math.ceil(h*-t)+1)/-t))}else d.pop()}for(var p=d.length,g=0,y=p;d[g]<=l;)++g;for(;d[y-1]>h;)--y;(g||y0?d[i-1]:l,v.x1=i0)for(i=0;i=n)&&(e=n);else{let r=-1;for(let i of t)null!=(i=n(i,++r,t))&&(e=i)&&(e=i)}return e}function tt(t,n){let e,r=-1,i=-1;if(void 0===n)for(const n of t)++i,null!=n&&(e=n)&&(e=n,r=i);else for(let o of t)null!=(o=n(o,++i,t))&&(e=o)&&(e=o,r=i);return r}function nt(t,n){let e;if(void 0===n)for(const n of t)null!=n&&(e>n||void 0===e&&n>=n)&&(e=n);else{let r=-1;for(let i of t)null!=(i=n(i,++r,t))&&(e>i||void 0===e&&i>=i)&&(e=i)}return e}function et(t,n){let e,r=-1,i=-1;if(void 0===n)for(const n of t)++i,null!=n&&(e>n||void 0===e&&n>=n)&&(e=n,r=i);else for(let o of t)null!=(o=n(o,++i,t))&&(e>o||void 0===e&&o>=o)&&(e=o,r=i);return r}function rt(t,n,e=0,r=1/0,i){if(n=Math.floor(n),e=Math.floor(Math.max(0,e)),r=Math.floor(Math.min(t.length-1,r)),!(e<=n&&n<=r))return t;for(i=void 0===i?O:I(i);r>e;){if(r-e>600){const o=r-e+1,a=n-e+1,u=Math.log(o),c=.5*Math.exp(2*u/3),f=.5*Math.sqrt(u*c*(o-c)/o)*(a-o/2<0?-1:1);rt(t,n,Math.max(e,Math.floor(n-a*c/o+f)),Math.min(r,Math.floor(n+(o-a)*c/o+f)),i)}const o=t[n];let a=e,u=r;for(it(t,e,n),i(t[r],o)>0&&it(t,e,r);a0;)--u}0===i(t[e],o)?it(t,e,u):(++u,it(t,u,r)),u<=n&&(e=u+1),n<=u&&(r=u-1)}return t}function it(t,n,e){const r=t[n];t[n]=t[e],t[e]=r}function ot(t,e=n){let r,i=!1;if(1===e.length){let o;for(const a of t){const t=e(a);(i?n(t,o)>0:0===n(t,t))&&(r=a,o=t,i=!0)}}else for(const n of t)(i?e(n,r)>0:0===e(n,n))&&(r=n,i=!0);return r}function at(t,n,e){if(t=Float64Array.from(function*(t,n){if(void 0===n)for(let n of t)null!=n&&(n=+n)>=n&&(yield n);else{let e=-1;for(let r of t)null!=(r=n(r,++e,t))&&(r=+r)>=r&&(yield r)}}(t,e)),(r=t.length)&&!isNaN(n=+n)){if(n<=0||r<2)return nt(t);if(n>=1)return J(t);var r,i=(r-1)*n,o=Math.floor(i),a=J(rt(t,o).subarray(0,o+1));return a+(nt(t.subarray(o+1))-a)*(i-o)}}function ut(t,n,e=o){if((r=t.length)&&!isNaN(n=+n)){if(n<=0||r<2)return+e(t[0],0,t);if(n>=1)return+e(t[r-1],r-1,t);var r,i=(r-1)*n,a=Math.floor(i),u=+e(t[a],a,t);return u+(+e(t[a+1],a+1,t)-u)*(i-a)}}function ct(t,n,e=o){if(!isNaN(n=+n)){if(r=Float64Array.from(t,((n,r)=>o(e(t[r],r,t)))),n<=0)return et(r);if(n>=1)return tt(r);var r,i=Uint32Array.from(t,((t,n)=>n)),a=r.length-1,u=Math.floor(a*n);return rt(i,u,0,a,((t,n)=>O(r[t],r[n]))),(u=ot(i.subarray(0,u+1),(t=>r[t])))>=0?u:-1}}function ft(t){return Array.from(function*(t){for(const n of t)yield*n}(t))}function st(t,n){return[t,n]}function lt(t,n,e){t=+t,n=+n,e=(i=arguments.length)<2?(n=t,t=0,1):i<3?1:+e;for(var r=-1,i=0|Math.max(0,Math.ceil((n-t)/e)),o=new Array(i);++r+t(n)}function kt(t,n){return n=Math.max(0,t.bandwidth()-2*n)/2,t.round()&&(n=Math.round(n)),e=>+t(e)+n}function Ct(){return!this.__axis}function Pt(t,n){var e=[],r=null,i=null,o=6,a=6,u=3,c="undefined"!=typeof window&&window.devicePixelRatio>1?0:.5,f=t===xt||t===Tt?-1:1,s=t===Tt||t===wt?"x":"y",l=t===xt||t===Mt?St:Et;function h(h){var d=null==r?n.ticks?n.ticks.apply(n,e):n.domain():r,p=null==i?n.tickFormat?n.tickFormat.apply(n,e):mt:i,g=Math.max(o,0)+u,y=n.range(),v=+y[0]+c,_=+y[y.length-1]+c,b=(n.bandwidth?kt:Nt)(n.copy(),c),m=h.selection?h.selection():h,x=m.selectAll(".domain").data([null]),w=m.selectAll(".tick").data(d,n).order(),M=w.exit(),T=w.enter().append("g").attr("class","tick"),A=w.select("line"),S=w.select("text");x=x.merge(x.enter().insert("path",".tick").attr("class","domain").attr("stroke","currentColor")),w=w.merge(T),A=A.merge(T.append("line").attr("stroke","currentColor").attr(s+"2",f*o)),S=S.merge(T.append("text").attr("fill","currentColor").attr(s,f*g).attr("dy",t===xt?"0em":t===Mt?"0.71em":"0.32em")),h!==m&&(x=x.transition(h),w=w.transition(h),A=A.transition(h),S=S.transition(h),M=M.transition(h).attr("opacity",At).attr("transform",(function(t){return isFinite(t=b(t))?l(t+c):this.getAttribute("transform")})),T.attr("opacity",At).attr("transform",(function(t){var n=this.parentNode.__axis;return l((n&&isFinite(n=n(t))?n:b(t))+c)}))),M.remove(),x.attr("d",t===Tt||t===wt?a?"M"+f*a+","+v+"H"+c+"V"+_+"H"+f*a:"M"+c+","+v+"V"+_:a?"M"+v+","+f*a+"V"+c+"H"+_+"V"+f*a:"M"+v+","+c+"H"+_),w.attr("opacity",1).attr("transform",(function(t){return l(b(t)+c)})),A.attr(s+"2",f*o),S.attr(s,f*g).text(p),m.filter(Ct).attr("fill","none").attr("font-size",10).attr("font-family","sans-serif").attr("text-anchor",t===wt?"start":t===Tt?"end":"middle"),m.each((function(){this.__axis=b}))}return h.scale=function(t){return arguments.length?(n=t,h):n},h.ticks=function(){return e=Array.from(arguments),h},h.tickArguments=function(t){return arguments.length?(e=null==t?[]:Array.from(t),h):e.slice()},h.tickValues=function(t){return arguments.length?(r=null==t?null:Array.from(t),h):r&&r.slice()},h.tickFormat=function(t){return arguments.length?(i=t,h):i},h.tickSize=function(t){return arguments.length?(o=a=+t,h):o},h.tickSizeInner=function(t){return arguments.length?(o=+t,h):o},h.tickSizeOuter=function(t){return arguments.length?(a=+t,h):a},h.tickPadding=function(t){return arguments.length?(u=+t,h):u},h.offset=function(t){return arguments.length?(c=+t,h):c},h}var zt={value:()=>{}};function $t(){for(var t,n=0,e=arguments.length,r={};n=0&&(n=t.slice(e+1),t=t.slice(0,e)),t&&!r.hasOwnProperty(t))throw new Error("unknown type: "+t);return{type:t,name:n}}))),a=-1,u=o.length;if(!(arguments.length<2)){if(null!=n&&"function"!=typeof n)throw new Error("invalid callback: "+n);for(;++a0)for(var e,r,i=new Array(e),o=0;o=0&&"xmlns"!==(n=t.slice(0,e))&&(t=t.slice(e+1)),Ut.hasOwnProperty(n)?{space:Ut[n],local:t}:t}function Ot(t){return function(){var n=this.ownerDocument,e=this.namespaceURI;return e===qt&&n.documentElement.namespaceURI===qt?n.createElement(t):n.createElementNS(e,t)}}function Bt(t){return function(){return this.ownerDocument.createElementNS(t.space,t.local)}}function Yt(t){var n=It(t);return(n.local?Bt:Ot)(n)}function Lt(){}function jt(t){return null==t?Lt:function(){return this.querySelector(t)}}function Ht(t){return null==t?[]:Array.isArray(t)?t:Array.from(t)}function Xt(){return[]}function Gt(t){return null==t?Xt:function(){return this.querySelectorAll(t)}}function Vt(t){return function(){return this.matches(t)}}function Wt(t){return function(n){return n.matches(t)}}var Zt=Array.prototype.find;function Kt(){return this.firstElementChild}var Qt=Array.prototype.filter;function Jt(){return Array.from(this.children)}function tn(t){return new Array(t.length)}function nn(t,n){this.ownerDocument=t.ownerDocument,this.namespaceURI=t.namespaceURI,this._next=null,this._parent=t,this.__data__=n}function en(t,n,e,r,i,o){for(var a,u=0,c=n.length,f=o.length;un?1:t>=n?0:NaN}function cn(t){return function(){this.removeAttribute(t)}}function fn(t){return function(){this.removeAttributeNS(t.space,t.local)}}function sn(t,n){return function(){this.setAttribute(t,n)}}function ln(t,n){return function(){this.setAttributeNS(t.space,t.local,n)}}function hn(t,n){return function(){var e=n.apply(this,arguments);null==e?this.removeAttribute(t):this.setAttribute(t,e)}}function dn(t,n){return function(){var e=n.apply(this,arguments);null==e?this.removeAttributeNS(t.space,t.local):this.setAttributeNS(t.space,t.local,e)}}function pn(t){return t.ownerDocument&&t.ownerDocument.defaultView||t.document&&t||t.defaultView}function gn(t){return function(){this.style.removeProperty(t)}}function yn(t,n,e){return function(){this.style.setProperty(t,n,e)}}function vn(t,n,e){return function(){var r=n.apply(this,arguments);null==r?this.style.removeProperty(t):this.style.setProperty(t,r,e)}}function _n(t,n){return t.style.getPropertyValue(n)||pn(t).getComputedStyle(t,null).getPropertyValue(n)}function bn(t){return function(){delete this[t]}}function mn(t,n){return function(){this[t]=n}}function xn(t,n){return function(){var e=n.apply(this,arguments);null==e?delete this[t]:this[t]=e}}function wn(t){return t.trim().split(/^|\s+/)}function Mn(t){return t.classList||new Tn(t)}function Tn(t){this._node=t,this._names=wn(t.getAttribute("class")||"")}function An(t,n){for(var e=Mn(t),r=-1,i=n.length;++r=0&&(this._names.splice(n,1),this._node.setAttribute("class",this._names.join(" ")))},contains:function(t){return this._names.indexOf(t)>=0}};var Gn=[null];function Vn(t,n){this._groups=t,this._parents=n}function Wn(){return new Vn([[document.documentElement]],Gn)}function Zn(t){return"string"==typeof t?new Vn([[document.querySelector(t)]],[document.documentElement]):new Vn([[t]],Gn)}Vn.prototype=Wn.prototype={constructor:Vn,select:function(t){"function"!=typeof t&&(t=jt(t));for(var n=this._groups,e=n.length,r=new Array(e),i=0;i=m&&(m=b+1);!(_=y[m])&&++m=0;)(r=i[o])&&(a&&4^r.compareDocumentPosition(a)&&a.parentNode.insertBefore(r,a),a=r);return this},sort:function(t){function n(n,e){return n&&e?t(n.__data__,e.__data__):!n-!e}t||(t=un);for(var e=this._groups,r=e.length,i=new Array(r),o=0;o1?this.each((null==n?gn:"function"==typeof n?vn:yn)(t,n,null==e?"":e)):_n(this.node(),t)},property:function(t,n){return arguments.length>1?this.each((null==n?bn:"function"==typeof n?xn:mn)(t,n)):this.node()[t]},classed:function(t,n){var e=wn(t+"");if(arguments.length<2){for(var r=Mn(this.node()),i=-1,o=e.length;++i=0&&(n=t.slice(e+1),t=t.slice(0,e)),{type:t,name:n}}))}(t+""),a=o.length;if(!(arguments.length<2)){for(u=n?Ln:Yn,r=0;r()=>t;function fe(t,{sourceEvent:n,subject:e,target:r,identifier:i,active:o,x:a,y:u,dx:c,dy:f,dispatch:s}){Object.defineProperties(this,{type:{value:t,enumerable:!0,configurable:!0},sourceEvent:{value:n,enumerable:!0,configurable:!0},subject:{value:e,enumerable:!0,configurable:!0},target:{value:r,enumerable:!0,configurable:!0},identifier:{value:i,enumerable:!0,configurable:!0},active:{value:o,enumerable:!0,configurable:!0},x:{value:a,enumerable:!0,configurable:!0},y:{value:u,enumerable:!0,configurable:!0},dx:{value:c,enumerable:!0,configurable:!0},dy:{value:f,enumerable:!0,configurable:!0},_:{value:s}})}function se(t){return!t.ctrlKey&&!t.button}function le(){return this.parentNode}function he(t,n){return null==n?{x:t.x,y:t.y}:n}function de(){return navigator.maxTouchPoints||"ontouchstart"in this}function pe(t,n,e){t.prototype=n.prototype=e,e.constructor=t}function ge(t,n){var e=Object.create(t.prototype);for(var r in n)e[r]=n[r];return e}function ye(){}fe.prototype.on=function(){var t=this._.on.apply(this._,arguments);return t===this._?this:t};var ve=.7,_e=1/ve,be="\\s*([+-]?\\d+)\\s*",me="\\s*([+-]?(?:\\d*\\.)?\\d+(?:[eE][+-]?\\d+)?)\\s*",xe="\\s*([+-]?(?:\\d*\\.)?\\d+(?:[eE][+-]?\\d+)?)%\\s*",we=/^#([0-9a-f]{3,8})$/,Me=new RegExp(`^rgb\\(${be},${be},${be}\\)$`),Te=new RegExp(`^rgb\\(${xe},${xe},${xe}\\)$`),Ae=new RegExp(`^rgba\\(${be},${be},${be},${me}\\)$`),Se=new RegExp(`^rgba\\(${xe},${xe},${xe},${me}\\)$`),Ee=new RegExp(`^hsl\\(${me},${xe},${xe}\\)$`),Ne=new RegExp(`^hsla\\(${me},${xe},${xe},${me}\\)$`),ke={aliceblue:15792383,antiquewhite:16444375,aqua:65535,aquamarine:8388564,azure:15794175,beige:16119260,bisque:16770244,black:0,blanchedalmond:16772045,blue:255,blueviolet:9055202,brown:10824234,burlywood:14596231,cadetblue:6266528,chartreuse:8388352,chocolate:13789470,coral:16744272,cornflowerblue:6591981,cornsilk:16775388,crimson:14423100,cyan:65535,darkblue:139,darkcyan:35723,darkgoldenrod:12092939,darkgray:11119017,darkgreen:25600,darkgrey:11119017,darkkhaki:12433259,darkmagenta:9109643,darkolivegreen:5597999,darkorange:16747520,darkorchid:10040012,darkred:9109504,darksalmon:15308410,darkseagreen:9419919,darkslateblue:4734347,darkslategray:3100495,darkslategrey:3100495,darkturquoise:52945,darkviolet:9699539,deeppink:16716947,deepskyblue:49151,dimgray:6908265,dimgrey:6908265,dodgerblue:2003199,firebrick:11674146,floralwhite:16775920,forestgreen:2263842,fuchsia:16711935,gainsboro:14474460,ghostwhite:16316671,gold:16766720,goldenrod:14329120,gray:8421504,green:32768,greenyellow:11403055,grey:8421504,honeydew:15794160,hotpink:16738740,indianred:13458524,indigo:4915330,ivory:16777200,khaki:15787660,lavender:15132410,lavenderblush:16773365,lawngreen:8190976,lemonchiffon:16775885,lightblue:11393254,lightcoral:15761536,lightcyan:14745599,lightgoldenrodyellow:16448210,lightgray:13882323,lightgreen:9498256,lightgrey:13882323,lightpink:16758465,lightsalmon:16752762,lightseagreen:2142890,lightskyblue:8900346,lightslategray:7833753,lightslategrey:7833753,lightsteelblue:11584734,lightyellow:16777184,lime:65280,limegreen:3329330,linen:16445670,magenta:16711935,maroon:8388608,mediumaquamarine:6737322,mediumblue:205,mediumorchid:12211667,mediumpurple:9662683,mediumseagreen:3978097,mediumslateblue:8087790,mediumspringgreen:64154,mediumturquoise:4772300,mediumvioletred:13047173,midnightblue:1644912,mintcream:16121850,mistyrose:16770273,moccasin:16770229,navajowhite:16768685,navy:128,oldlace:16643558,olive:8421376,olivedrab:7048739,orange:16753920,orangered:16729344,orchid:14315734,palegoldenrod:15657130,palegreen:10025880,paleturquoise:11529966,palevioletred:14381203,papayawhip:16773077,peachpuff:16767673,peru:13468991,pink:16761035,plum:14524637,powderblue:11591910,purple:8388736,rebeccapurple:6697881,red:16711680,rosybrown:12357519,royalblue:4286945,saddlebrown:9127187,salmon:16416882,sandybrown:16032864,seagreen:3050327,seashell:16774638,sienna:10506797,silver:12632256,skyblue:8900331,slateblue:6970061,slategray:7372944,slategrey:7372944,snow:16775930,springgreen:65407,steelblue:4620980,tan:13808780,teal:32896,thistle:14204888,tomato:16737095,turquoise:4251856,violet:15631086,wheat:16113331,white:16777215,whitesmoke:16119285,yellow:16776960,yellowgreen:10145074};function Ce(){return this.rgb().formatHex()}function Pe(){return this.rgb().formatRgb()}function ze(t){var n,e;return t=(t+"").trim().toLowerCase(),(n=we.exec(t))?(e=n[1].length,n=parseInt(n[1],16),6===e?$e(n):3===e?new qe(n>>8&15|n>>4&240,n>>4&15|240&n,(15&n)<<4|15&n,1):8===e?De(n>>24&255,n>>16&255,n>>8&255,(255&n)/255):4===e?De(n>>12&15|n>>8&240,n>>8&15|n>>4&240,n>>4&15|240&n,((15&n)<<4|15&n)/255):null):(n=Me.exec(t))?new qe(n[1],n[2],n[3],1):(n=Te.exec(t))?new qe(255*n[1]/100,255*n[2]/100,255*n[3]/100,1):(n=Ae.exec(t))?De(n[1],n[2],n[3],n[4]):(n=Se.exec(t))?De(255*n[1]/100,255*n[2]/100,255*n[3]/100,n[4]):(n=Ee.exec(t))?Le(n[1],n[2]/100,n[3]/100,1):(n=Ne.exec(t))?Le(n[1],n[2]/100,n[3]/100,n[4]):ke.hasOwnProperty(t)?$e(ke[t]):"transparent"===t?new qe(NaN,NaN,NaN,0):null}function $e(t){return new qe(t>>16&255,t>>8&255,255&t,1)}function De(t,n,e,r){return r<=0&&(t=n=e=NaN),new qe(t,n,e,r)}function Re(t){return t instanceof ye||(t=ze(t)),t?new qe((t=t.rgb()).r,t.g,t.b,t.opacity):new qe}function Fe(t,n,e,r){return 1===arguments.length?Re(t):new qe(t,n,e,null==r?1:r)}function qe(t,n,e,r){this.r=+t,this.g=+n,this.b=+e,this.opacity=+r}function Ue(){return`#${Ye(this.r)}${Ye(this.g)}${Ye(this.b)}`}function Ie(){const t=Oe(this.opacity);return`${1===t?"rgb(":"rgba("}${Be(this.r)}, ${Be(this.g)}, ${Be(this.b)}${1===t?")":`, ${t})`}`}function Oe(t){return isNaN(t)?1:Math.max(0,Math.min(1,t))}function Be(t){return Math.max(0,Math.min(255,Math.round(t)||0))}function Ye(t){return((t=Be(t))<16?"0":"")+t.toString(16)}function Le(t,n,e,r){return r<=0?t=n=e=NaN:e<=0||e>=1?t=n=NaN:n<=0&&(t=NaN),new Xe(t,n,e,r)}function je(t){if(t instanceof Xe)return new Xe(t.h,t.s,t.l,t.opacity);if(t instanceof ye||(t=ze(t)),!t)return new Xe;if(t instanceof Xe)return t;var n=(t=t.rgb()).r/255,e=t.g/255,r=t.b/255,i=Math.min(n,e,r),o=Math.max(n,e,r),a=NaN,u=o-i,c=(o+i)/2;return u?(a=n===o?(e-r)/u+6*(e0&&c<1?0:a,new Xe(a,u,c,t.opacity)}function He(t,n,e,r){return 1===arguments.length?je(t):new Xe(t,n,e,null==r?1:r)}function Xe(t,n,e,r){this.h=+t,this.s=+n,this.l=+e,this.opacity=+r}function Ge(t){return(t=(t||0)%360)<0?t+360:t}function Ve(t){return Math.max(0,Math.min(1,t||0))}function We(t,n,e){return 255*(t<60?n+(e-n)*t/60:t<180?e:t<240?n+(e-n)*(240-t)/60:n)}pe(ye,ze,{copy(t){return Object.assign(new this.constructor,this,t)},displayable(){return this.rgb().displayable()},hex:Ce,formatHex:Ce,formatHex8:function(){return this.rgb().formatHex8()},formatHsl:function(){return je(this).formatHsl()},formatRgb:Pe,toString:Pe}),pe(qe,Fe,ge(ye,{brighter(t){return t=null==t?_e:Math.pow(_e,t),new qe(this.r*t,this.g*t,this.b*t,this.opacity)},darker(t){return t=null==t?ve:Math.pow(ve,t),new qe(this.r*t,this.g*t,this.b*t,this.opacity)},rgb(){return this},clamp(){return new qe(Be(this.r),Be(this.g),Be(this.b),Oe(this.opacity))},displayable(){return-.5<=this.r&&this.r<255.5&&-.5<=this.g&&this.g<255.5&&-.5<=this.b&&this.b<255.5&&0<=this.opacity&&this.opacity<=1},hex:Ue,formatHex:Ue,formatHex8:function(){return`#${Ye(this.r)}${Ye(this.g)}${Ye(this.b)}${Ye(255*(isNaN(this.opacity)?1:this.opacity))}`},formatRgb:Ie,toString:Ie})),pe(Xe,He,ge(ye,{brighter(t){return t=null==t?_e:Math.pow(_e,t),new Xe(this.h,this.s,this.l*t,this.opacity)},darker(t){return t=null==t?ve:Math.pow(ve,t),new Xe(this.h,this.s,this.l*t,this.opacity)},rgb(){var t=this.h%360+360*(this.h<0),n=isNaN(t)||isNaN(this.s)?0:this.s,e=this.l,r=e+(e<.5?e:1-e)*n,i=2*e-r;return new qe(We(t>=240?t-240:t+120,i,r),We(t,i,r),We(t<120?t+240:t-120,i,r),this.opacity)},clamp(){return new Xe(Ge(this.h),Ve(this.s),Ve(this.l),Oe(this.opacity))},displayable(){return(0<=this.s&&this.s<=1||isNaN(this.s))&&0<=this.l&&this.l<=1&&0<=this.opacity&&this.opacity<=1},formatHsl(){const t=Oe(this.opacity);return`${1===t?"hsl(":"hsla("}${Ge(this.h)}, ${100*Ve(this.s)}%, ${100*Ve(this.l)}%${1===t?")":`, ${t})`}`}}));const Ze=Math.PI/180,Ke=180/Math.PI,Qe=.96422,Je=1,tr=.82521,nr=4/29,er=6/29,rr=3*er*er,ir=er*er*er;function or(t){if(t instanceof ur)return new ur(t.l,t.a,t.b,t.opacity);if(t instanceof pr)return gr(t);t instanceof qe||(t=Re(t));var n,e,r=lr(t.r),i=lr(t.g),o=lr(t.b),a=cr((.2225045*r+.7168786*i+.0606169*o)/Je);return r===i&&i===o?n=e=a:(n=cr((.4360747*r+.3850649*i+.1430804*o)/Qe),e=cr((.0139322*r+.0971045*i+.7141733*o)/tr)),new ur(116*a-16,500*(n-a),200*(a-e),t.opacity)}function ar(t,n,e,r){return 1===arguments.length?or(t):new ur(t,n,e,null==r?1:r)}function ur(t,n,e,r){this.l=+t,this.a=+n,this.b=+e,this.opacity=+r}function cr(t){return t>ir?Math.pow(t,1/3):t/rr+nr}function fr(t){return t>er?t*t*t:rr*(t-nr)}function sr(t){return 255*(t<=.0031308?12.92*t:1.055*Math.pow(t,1/2.4)-.055)}function lr(t){return(t/=255)<=.04045?t/12.92:Math.pow((t+.055)/1.055,2.4)}function hr(t){if(t instanceof pr)return new pr(t.h,t.c,t.l,t.opacity);if(t instanceof ur||(t=or(t)),0===t.a&&0===t.b)return new pr(NaN,0=1?(e=1,n-1):Math.floor(e*n),i=t[r],o=t[r+1],a=r>0?t[r-1]:2*i-o,u=r()=>t;function Cr(t,n){return function(e){return t+e*n}}function Pr(t,n){var e=n-t;return e?Cr(t,e>180||e<-180?e-360*Math.round(e/360):e):kr(isNaN(t)?n:t)}function zr(t){return 1==(t=+t)?$r:function(n,e){return e-n?function(t,n,e){return t=Math.pow(t,e),n=Math.pow(n,e)-t,e=1/e,function(r){return Math.pow(t+r*n,e)}}(n,e,t):kr(isNaN(n)?e:n)}}function $r(t,n){var e=n-t;return e?Cr(t,e):kr(isNaN(t)?n:t)}var Dr=function t(n){var e=zr(n);function r(t,n){var r=e((t=Fe(t)).r,(n=Fe(n)).r),i=e(t.g,n.g),o=e(t.b,n.b),a=$r(t.opacity,n.opacity);return function(n){return t.r=r(n),t.g=i(n),t.b=o(n),t.opacity=a(n),t+""}}return r.gamma=t,r}(1);function Rr(t){return function(n){var e,r,i=n.length,o=new Array(i),a=new Array(i),u=new Array(i);for(e=0;eo&&(i=n.slice(o,i),u[a]?u[a]+=i:u[++a]=i),(e=e[0])===(r=r[0])?u[a]?u[a]+=r:u[++a]=r:(u[++a]=null,c.push({i:a,x:Yr(e,r)})),o=Hr.lastIndex;return o180?n+=360:n-t>180&&(t+=360),o.push({i:e.push(i(e)+"rotate(",null,r)-2,x:Yr(t,n)})):n&&e.push(i(e)+"rotate("+n+r)}(o.rotate,a.rotate,u,c),function(t,n,e,o){t!==n?o.push({i:e.push(i(e)+"skewX(",null,r)-2,x:Yr(t,n)}):n&&e.push(i(e)+"skewX("+n+r)}(o.skewX,a.skewX,u,c),function(t,n,e,r,o,a){if(t!==e||n!==r){var u=o.push(i(o)+"scale(",null,",",null,")");a.push({i:u-4,x:Yr(t,e)},{i:u-2,x:Yr(n,r)})}else 1===e&&1===r||o.push(i(o)+"scale("+e+","+r+")")}(o.scaleX,o.scaleY,a.scaleX,a.scaleY,u,c),o=a=null,function(t){for(var n,e=-1,r=c.length;++e=0&&n._call.call(void 0,t),n=n._next;--yi}function Ci(){xi=(mi=Mi.now())+wi,yi=vi=0;try{ki()}finally{yi=0,function(){var t,n,e=pi,r=1/0;for(;e;)e._call?(r>e._time&&(r=e._time),t=e,e=e._next):(n=e._next,e._next=null,e=t?t._next=n:pi=n);gi=t,zi(r)}(),xi=0}}function Pi(){var t=Mi.now(),n=t-mi;n>bi&&(wi-=n,mi=t)}function zi(t){yi||(vi&&(vi=clearTimeout(vi)),t-xi>24?(t<1/0&&(vi=setTimeout(Ci,t-Mi.now()-wi)),_i&&(_i=clearInterval(_i))):(_i||(mi=Mi.now(),_i=setInterval(Pi,bi)),yi=1,Ti(Ci)))}function $i(t,n,e){var r=new Ei;return n=null==n?0:+n,r.restart((e=>{r.stop(),t(e+n)}),n,e),r}Ei.prototype=Ni.prototype={constructor:Ei,restart:function(t,n,e){if("function"!=typeof t)throw new TypeError("callback is not a function");e=(null==e?Ai():+e)+(null==n?0:+n),this._next||gi===this||(gi?gi._next=this:pi=this,gi=this),this._call=t,this._time=e,zi()},stop:function(){this._call&&(this._call=null,this._time=1/0,zi())}};var Di=$t("start","end","cancel","interrupt"),Ri=[],Fi=0,qi=1,Ui=2,Ii=3,Oi=4,Bi=5,Yi=6;function Li(t,n,e,r,i,o){var a=t.__transition;if(a){if(e in a)return}else t.__transition={};!function(t,n,e){var r,i=t.__transition;function o(t){e.state=qi,e.timer.restart(a,e.delay,e.time),e.delay<=t&&a(t-e.delay)}function a(o){var f,s,l,h;if(e.state!==qi)return c();for(f in i)if((h=i[f]).name===e.name){if(h.state===Ii)return $i(a);h.state===Oi?(h.state=Yi,h.timer.stop(),h.on.call("interrupt",t,t.__data__,h.index,h.group),delete i[f]):+fFi)throw new Error("too late; already scheduled");return e}function Hi(t,n){var e=Xi(t,n);if(e.state>Ii)throw new Error("too late; already running");return e}function Xi(t,n){var e=t.__transition;if(!e||!(e=e[n]))throw new Error("transition not found");return e}function Gi(t,n){var e,r,i,o=t.__transition,a=!0;if(o){for(i in n=null==n?null:n+"",o)(e=o[i]).name===n?(r=e.state>Ui&&e.state=0&&(t=t.slice(0,n)),!t||"start"===t}))}(n)?ji:Hi;return function(){var a=o(this,t),u=a.on;u!==r&&(i=(r=u).copy()).on(n,e),a.on=i}}(e,t,n))},attr:function(t,n){var e=It(t),r="transform"===e?ni:Ki;return this.attrTween(t,"function"==typeof n?(e.local?ro:eo)(e,r,Zi(this,"attr."+t,n)):null==n?(e.local?Ji:Qi)(e):(e.local?no:to)(e,r,n))},attrTween:function(t,n){var e="attr."+t;if(arguments.length<2)return(e=this.tween(e))&&e._value;if(null==n)return this.tween(e,null);if("function"!=typeof n)throw new Error;var r=It(t);return this.tween(e,(r.local?io:oo)(r,n))},style:function(t,n,e){var r="transform"==(t+="")?ti:Ki;return null==n?this.styleTween(t,function(t,n){var e,r,i;return function(){var o=_n(this,t),a=(this.style.removeProperty(t),_n(this,t));return o===a?null:o===e&&a===r?i:i=n(e=o,r=a)}}(t,r)).on("end.style."+t,lo(t)):"function"==typeof n?this.styleTween(t,function(t,n,e){var r,i,o;return function(){var a=_n(this,t),u=e(this),c=u+"";return null==u&&(this.style.removeProperty(t),c=u=_n(this,t)),a===c?null:a===r&&c===i?o:(i=c,o=n(r=a,u))}}(t,r,Zi(this,"style."+t,n))).each(function(t,n){var e,r,i,o,a="style."+n,u="end."+a;return function(){var c=Hi(this,t),f=c.on,s=null==c.value[a]?o||(o=lo(n)):void 0;f===e&&i===s||(r=(e=f).copy()).on(u,i=s),c.on=r}}(this._id,t)):this.styleTween(t,function(t,n,e){var r,i,o=e+"";return function(){var a=_n(this,t);return a===o?null:a===r?i:i=n(r=a,e)}}(t,r,n),e).on("end.style."+t,null)},styleTween:function(t,n,e){var r="style."+(t+="");if(arguments.length<2)return(r=this.tween(r))&&r._value;if(null==n)return this.tween(r,null);if("function"!=typeof n)throw new Error;return this.tween(r,function(t,n,e){var r,i;function o(){var o=n.apply(this,arguments);return o!==i&&(r=(i=o)&&function(t,n,e){return function(r){this.style.setProperty(t,n.call(this,r),e)}}(t,o,e)),r}return o._value=n,o}(t,n,null==e?"":e))},text:function(t){return this.tween("text","function"==typeof t?function(t){return function(){var n=t(this);this.textContent=null==n?"":n}}(Zi(this,"text",t)):function(t){return function(){this.textContent=t}}(null==t?"":t+""))},textTween:function(t){var n="text";if(arguments.length<1)return(n=this.tween(n))&&n._value;if(null==t)return this.tween(n,null);if("function"!=typeof t)throw new Error;return this.tween(n,function(t){var n,e;function r(){var r=t.apply(this,arguments);return r!==e&&(n=(e=r)&&function(t){return function(n){this.textContent=t.call(this,n)}}(r)),n}return r._value=t,r}(t))},remove:function(){return this.on("end.remove",function(t){return function(){var n=this.parentNode;for(var e in this.__transition)if(+e!==t)return;n&&n.removeChild(this)}}(this._id))},tween:function(t,n){var e=this._id;if(t+="",arguments.length<2){for(var r,i=Xi(this.node(),e).tween,o=0,a=i.length;o()=>t;function Qo(t,{sourceEvent:n,target:e,selection:r,mode:i,dispatch:o}){Object.defineProperties(this,{type:{value:t,enumerable:!0,configurable:!0},sourceEvent:{value:n,enumerable:!0,configurable:!0},target:{value:e,enumerable:!0,configurable:!0},selection:{value:r,enumerable:!0,configurable:!0},mode:{value:i,enumerable:!0,configurable:!0},_:{value:o}})}function Jo(t){t.preventDefault(),t.stopImmediatePropagation()}var ta={name:"drag"},na={name:"space"},ea={name:"handle"},ra={name:"center"};const{abs:ia,max:oa,min:aa}=Math;function ua(t){return[+t[0],+t[1]]}function ca(t){return[ua(t[0]),ua(t[1])]}var fa={name:"x",handles:["w","e"].map(va),input:function(t,n){return null==t?null:[[+t[0],n[0][1]],[+t[1],n[1][1]]]},output:function(t){return t&&[t[0][0],t[1][0]]}},sa={name:"y",handles:["n","s"].map(va),input:function(t,n){return null==t?null:[[n[0][0],+t[0]],[n[1][0],+t[1]]]},output:function(t){return t&&[t[0][1],t[1][1]]}},la={name:"xy",handles:["n","w","e","s","nw","ne","sw","se"].map(va),input:function(t){return null==t?null:ca(t)},output:function(t){return t}},ha={overlay:"crosshair",selection:"move",n:"ns-resize",e:"ew-resize",s:"ns-resize",w:"ew-resize",nw:"nwse-resize",ne:"nesw-resize",se:"nwse-resize",sw:"nesw-resize"},da={e:"w",w:"e",nw:"ne",ne:"nw",se:"sw",sw:"se"},pa={n:"s",s:"n",nw:"sw",ne:"se",se:"ne",sw:"nw"},ga={overlay:1,selection:1,n:null,e:1,s:null,w:-1,nw:-1,ne:1,se:1,sw:-1},ya={overlay:1,selection:1,n:-1,e:null,s:1,w:null,nw:-1,ne:-1,se:1,sw:1};function va(t){return{type:t}}function _a(t){return!t.ctrlKey&&!t.button}function ba(){var t=this.ownerSVGElement||this;return t.hasAttribute("viewBox")?[[(t=t.viewBox.baseVal).x,t.y],[t.x+t.width,t.y+t.height]]:[[0,0],[t.width.baseVal.value,t.height.baseVal.value]]}function ma(){return navigator.maxTouchPoints||"ontouchstart"in this}function xa(t){for(;!t.__brush;)if(!(t=t.parentNode))return;return t.__brush}function wa(t){var n,e=ba,r=_a,i=ma,o=!0,a=$t("start","brush","end"),u=6;function c(n){var e=n.property("__brush",g).selectAll(".overlay").data([va("overlay")]);e.enter().append("rect").attr("class","overlay").attr("pointer-events","all").attr("cursor",ha.overlay).merge(e).each((function(){var t=xa(this).extent;Zn(this).attr("x",t[0][0]).attr("y",t[0][1]).attr("width",t[1][0]-t[0][0]).attr("height",t[1][1]-t[0][1])})),n.selectAll(".selection").data([va("selection")]).enter().append("rect").attr("class","selection").attr("cursor",ha.selection).attr("fill","#777").attr("fill-opacity",.3).attr("stroke","#fff").attr("shape-rendering","crispEdges");var r=n.selectAll(".handle").data(t.handles,(function(t){return t.type}));r.exit().remove(),r.enter().append("rect").attr("class",(function(t){return"handle handle--"+t.type})).attr("cursor",(function(t){return ha[t.type]})),n.each(f).attr("fill","none").attr("pointer-events","all").on("mousedown.brush",h).filter(i).on("touchstart.brush",h).on("touchmove.brush",d).on("touchend.brush touchcancel.brush",p).style("touch-action","none").style("-webkit-tap-highlight-color","rgba(0,0,0,0)")}function f(){var t=Zn(this),n=xa(this).selection;n?(t.selectAll(".selection").style("display",null).attr("x",n[0][0]).attr("y",n[0][1]).attr("width",n[1][0]-n[0][0]).attr("height",n[1][1]-n[0][1]),t.selectAll(".handle").style("display",null).attr("x",(function(t){return"e"===t.type[t.type.length-1]?n[1][0]-u/2:n[0][0]-u/2})).attr("y",(function(t){return"s"===t.type[0]?n[1][1]-u/2:n[0][1]-u/2})).attr("width",(function(t){return"n"===t.type||"s"===t.type?n[1][0]-n[0][0]+u:u})).attr("height",(function(t){return"e"===t.type||"w"===t.type?n[1][1]-n[0][1]+u:u}))):t.selectAll(".selection,.handle").style("display","none").attr("x",null).attr("y",null).attr("width",null).attr("height",null)}function s(t,n,e){var r=t.__brush.emitter;return!r||e&&r.clean?new l(t,n,e):r}function l(t,n,e){this.that=t,this.args=n,this.state=t.__brush,this.active=0,this.clean=e}function h(e){if((!n||e.touches)&&r.apply(this,arguments)){var i,a,u,c,l,h,d,p,g,y,v,_=this,b=e.target.__data__.type,m="selection"===(o&&e.metaKey?b="overlay":b)?ta:o&&e.altKey?ra:ea,x=t===sa?null:ga[b],w=t===fa?null:ya[b],M=xa(_),T=M.extent,A=M.selection,S=T[0][0],E=T[0][1],N=T[1][0],k=T[1][1],C=0,P=0,z=x&&w&&o&&e.shiftKey,$=Array.from(e.touches||[e],(t=>{const n=t.identifier;return(t=ne(t,_)).point0=t.slice(),t.identifier=n,t}));Gi(_);var D=s(_,arguments,!0).beforestart();if("overlay"===b){A&&(g=!0);const n=[$[0],$[1]||$[0]];M.selection=A=[[i=t===sa?S:aa(n[0][0],n[1][0]),u=t===fa?E:aa(n[0][1],n[1][1])],[l=t===sa?N:oa(n[0][0],n[1][0]),d=t===fa?k:oa(n[0][1],n[1][1])]],$.length>1&&I(e)}else i=A[0][0],u=A[0][1],l=A[1][0],d=A[1][1];a=i,c=u,h=l,p=d;var R=Zn(_).attr("pointer-events","none"),F=R.selectAll(".overlay").attr("cursor",ha[b]);if(e.touches)D.moved=U,D.ended=O;else{var q=Zn(e.view).on("mousemove.brush",U,!0).on("mouseup.brush",O,!0);o&&q.on("keydown.brush",(function(t){switch(t.keyCode){case 16:z=x&&w;break;case 18:m===ea&&(x&&(l=h-C*x,i=a+C*x),w&&(d=p-P*w,u=c+P*w),m=ra,I(t));break;case 32:m!==ea&&m!==ra||(x<0?l=h-C:x>0&&(i=a-C),w<0?d=p-P:w>0&&(u=c-P),m=na,F.attr("cursor",ha.selection),I(t));break;default:return}Jo(t)}),!0).on("keyup.brush",(function(t){switch(t.keyCode){case 16:z&&(y=v=z=!1,I(t));break;case 18:m===ra&&(x<0?l=h:x>0&&(i=a),w<0?d=p:w>0&&(u=c),m=ea,I(t));break;case 32:m===na&&(t.altKey?(x&&(l=h-C*x,i=a+C*x),w&&(d=p-P*w,u=c+P*w),m=ra):(x<0?l=h:x>0&&(i=a),w<0?d=p:w>0&&(u=c),m=ea),F.attr("cursor",ha[b]),I(t));break;default:return}Jo(t)}),!0),ae(e.view)}f.call(_),D.start(e,m.name)}function U(t){for(const n of t.changedTouches||[t])for(const t of $)t.identifier===n.identifier&&(t.cur=ne(n,_));if(z&&!y&&!v&&1===$.length){const t=$[0];ia(t.cur[0]-t[0])>ia(t.cur[1]-t[1])?v=!0:y=!0}for(const t of $)t.cur&&(t[0]=t.cur[0],t[1]=t.cur[1]);g=!0,Jo(t),I(t)}function I(t){const n=$[0],e=n.point0;var r;switch(C=n[0]-e[0],P=n[1]-e[1],m){case na:case ta:x&&(C=oa(S-i,aa(N-l,C)),a=i+C,h=l+C),w&&(P=oa(E-u,aa(k-d,P)),c=u+P,p=d+P);break;case ea:$[1]?(x&&(a=oa(S,aa(N,$[0][0])),h=oa(S,aa(N,$[1][0])),x=1),w&&(c=oa(E,aa(k,$[0][1])),p=oa(E,aa(k,$[1][1])),w=1)):(x<0?(C=oa(S-i,aa(N-i,C)),a=i+C,h=l):x>0&&(C=oa(S-l,aa(N-l,C)),a=i,h=l+C),w<0?(P=oa(E-u,aa(k-u,P)),c=u+P,p=d):w>0&&(P=oa(E-d,aa(k-d,P)),c=u,p=d+P));break;case ra:x&&(a=oa(S,aa(N,i-C*x)),h=oa(S,aa(N,l+C*x))),w&&(c=oa(E,aa(k,u-P*w)),p=oa(E,aa(k,d+P*w)))}ht+e))}function za(t,n){var e=0,r=null,i=null,o=null;function a(a){var u,c=a.length,f=new Array(c),s=Pa(0,c),l=new Array(c*c),h=new Array(c),d=0;a=Float64Array.from({length:c*c},n?(t,n)=>a[n%c][n/c|0]:(t,n)=>a[n/c|0][n%c]);for(let n=0;nr(f[t],f[n])));for(const e of s){const r=n;if(t){const t=Pa(1+~c,c).filter((t=>t<0?a[~t*c+e]:a[e*c+t]));i&&t.sort(((t,n)=>i(t<0?-a[~t*c+e]:a[e*c+t],n<0?-a[~n*c+e]:a[e*c+n])));for(const r of t)if(r<0){(l[~r*c+e]||(l[~r*c+e]={source:null,target:null})).target={index:e,startAngle:n,endAngle:n+=a[~r*c+e]*d,value:a[~r*c+e]}}else{(l[e*c+r]||(l[e*c+r]={source:null,target:null})).source={index:e,startAngle:n,endAngle:n+=a[e*c+r]*d,value:a[e*c+r]}}h[e]={index:e,startAngle:r,endAngle:n,value:f[e]}}else{const t=Pa(0,c).filter((t=>a[e*c+t]||a[t*c+e]));i&&t.sort(((t,n)=>i(a[e*c+t],a[e*c+n])));for(const r of t){let t;if(e=0))throw new Error(`invalid digits: ${t}`);if(n>15)return qa;const e=10**n;return function(t){this._+=t[0];for(let n=1,r=t.length;nRa)if(Math.abs(s*u-c*f)>Ra&&i){let h=e-o,d=r-a,p=u*u+c*c,g=h*h+d*d,y=Math.sqrt(p),v=Math.sqrt(l),_=i*Math.tan(($a-Math.acos((p+l-g)/(2*y*v)))/2),b=_/v,m=_/y;Math.abs(b-1)>Ra&&this._append`L${t+b*f},${n+b*s}`,this._append`A${i},${i},0,0,${+(s*h>f*d)},${this._x1=t+m*u},${this._y1=n+m*c}`}else this._append`L${this._x1=t},${this._y1=n}`;else;}arc(t,n,e,r,i,o){if(t=+t,n=+n,o=!!o,(e=+e)<0)throw new Error(`negative radius: ${e}`);let a=e*Math.cos(r),u=e*Math.sin(r),c=t+a,f=n+u,s=1^o,l=o?r-i:i-r;null===this._x1?this._append`M${c},${f}`:(Math.abs(this._x1-c)>Ra||Math.abs(this._y1-f)>Ra)&&this._append`L${c},${f}`,e&&(l<0&&(l=l%Da+Da),l>Fa?this._append`A${e},${e},0,1,${s},${t-a},${n-u}A${e},${e},0,1,${s},${this._x1=c},${this._y1=f}`:l>Ra&&this._append`A${e},${e},0,${+(l>=$a)},${s},${this._x1=t+e*Math.cos(i)},${this._y1=n+e*Math.sin(i)}`)}rect(t,n,e,r){this._append`M${this._x0=this._x1=+t},${this._y0=this._y1=+n}h${e=+e}v${+r}h${-e}Z`}toString(){return this._}};function Ia(){return new Ua}Ia.prototype=Ua.prototype;var Oa=Array.prototype.slice;function Ba(t){return function(){return t}}function Ya(t){return t.source}function La(t){return t.target}function ja(t){return t.radius}function Ha(t){return t.startAngle}function Xa(t){return t.endAngle}function Ga(){return 0}function Va(){return 10}function Wa(t){var n=Ya,e=La,r=ja,i=ja,o=Ha,a=Xa,u=Ga,c=null;function f(){var f,s=n.apply(this,arguments),l=e.apply(this,arguments),h=u.apply(this,arguments)/2,d=Oa.call(arguments),p=+r.apply(this,(d[0]=s,d)),g=o.apply(this,d)-Ea,y=a.apply(this,d)-Ea,v=+i.apply(this,(d[0]=l,d)),_=o.apply(this,d)-Ea,b=a.apply(this,d)-Ea;if(c||(c=f=Ia()),h>Ca&&(Ma(y-g)>2*h+Ca?y>g?(g+=h,y-=h):(g-=h,y+=h):g=y=(g+y)/2,Ma(b-_)>2*h+Ca?b>_?(_+=h,b-=h):(_-=h,b+=h):_=b=(_+b)/2),c.moveTo(p*Ta(g),p*Aa(g)),c.arc(0,0,p,g,y),g!==_||y!==b)if(t){var m=v-+t.apply(this,arguments),x=(_+b)/2;c.quadraticCurveTo(0,0,m*Ta(_),m*Aa(_)),c.lineTo(v*Ta(x),v*Aa(x)),c.lineTo(m*Ta(b),m*Aa(b))}else c.quadraticCurveTo(0,0,v*Ta(_),v*Aa(_)),c.arc(0,0,v,_,b);if(c.quadraticCurveTo(0,0,p*Ta(g),p*Aa(g)),c.closePath(),f)return c=null,f+""||null}return t&&(f.headRadius=function(n){return arguments.length?(t="function"==typeof n?n:Ba(+n),f):t}),f.radius=function(t){return arguments.length?(r=i="function"==typeof t?t:Ba(+t),f):r},f.sourceRadius=function(t){return arguments.length?(r="function"==typeof t?t:Ba(+t),f):r},f.targetRadius=function(t){return arguments.length?(i="function"==typeof t?t:Ba(+t),f):i},f.startAngle=function(t){return arguments.length?(o="function"==typeof t?t:Ba(+t),f):o},f.endAngle=function(t){return arguments.length?(a="function"==typeof t?t:Ba(+t),f):a},f.padAngle=function(t){return arguments.length?(u="function"==typeof t?t:Ba(+t),f):u},f.source=function(t){return arguments.length?(n=t,f):n},f.target=function(t){return arguments.length?(e=t,f):e},f.context=function(t){return arguments.length?(c=null==t?null:t,f):c},f}var Za=Array.prototype.slice;function Ka(t,n){return t-n}var Qa=t=>()=>t;function Ja(t,n){for(var e,r=-1,i=n.length;++rr!=d>r&&e<(h-f)*(r-s)/(d-s)+f&&(i=-i)}return i}function nu(t,n,e){var r,i,o,a;return function(t,n,e){return(n[0]-t[0])*(e[1]-t[1])==(e[0]-t[0])*(n[1]-t[1])}(t,n,e)&&(i=t[r=+(t[0]===n[0])],o=e[r],a=n[r],i<=o&&o<=a||a<=o&&o<=i)}function eu(){}var ru=[[],[[[1,1.5],[.5,1]]],[[[1.5,1],[1,1.5]]],[[[1.5,1],[.5,1]]],[[[1,.5],[1.5,1]]],[[[1,1.5],[.5,1]],[[1,.5],[1.5,1]]],[[[1,.5],[1,1.5]]],[[[1,.5],[.5,1]]],[[[.5,1],[1,.5]]],[[[1,1.5],[1,.5]]],[[[.5,1],[1,.5]],[[1.5,1],[1,1.5]]],[[[1.5,1],[1,.5]]],[[[.5,1],[1.5,1]]],[[[1,1.5],[1.5,1]]],[[[.5,1],[1,1.5]]],[]];function iu(){var t=1,n=1,e=K,r=u;function i(t){var n=e(t);if(Array.isArray(n))n=n.slice().sort(Ka);else{const e=M(t,ou);for(n=G(...Z(e[0],e[1],n),n);n[n.length-1]>=e[1];)n.pop();for(;n[1]o(t,n)))}function o(e,i){const o=null==i?NaN:+i;if(isNaN(o))throw new Error(`invalid value: ${i}`);var u=[],c=[];return function(e,r,i){var o,u,c,f,s,l,h=new Array,d=new Array;o=u=-1,f=au(e[0],r),ru[f<<1].forEach(p);for(;++o=r,ru[s<<2].forEach(p);for(;++o0?u.push([t]):c.push(t)})),c.forEach((function(t){for(var n,e=0,r=u.length;e0&&o0&&a=0&&o>=0))throw new Error("invalid size");return t=r,n=o,i},i.thresholds=function(t){return arguments.length?(e="function"==typeof t?t:Array.isArray(t)?Qa(Za.call(t)):Qa(t),i):e},i.smooth=function(t){return arguments.length?(r=t?u:eu,i):r===u},i}function ou(t){return isFinite(t)?t:NaN}function au(t,n){return null!=t&&+t>=n}function uu(t){return null==t||isNaN(t=+t)?-1/0:t}function cu(t,n,e,r){const i=r-n,o=e-n,a=isFinite(i)||isFinite(o)?i/o:Math.sign(i)/Math.sign(o);return isNaN(a)?t:t+a-.5}function fu(t){return t[0]}function su(t){return t[1]}function lu(){return 1}const hu=134217729,du=33306690738754706e-32;function pu(t,n,e,r,i){let o,a,u,c,f=n[0],s=r[0],l=0,h=0;s>f==s>-f?(o=f,f=n[++l]):(o=s,s=r[++h]);let d=0;if(lf==s>-f?(a=f+o,u=o-(a-f),f=n[++l]):(a=s+o,u=o-(a-s),s=r[++h]),o=a,0!==u&&(i[d++]=u);lf==s>-f?(a=o+f,c=a-o,u=o-(a-c)+(f-c),f=n[++l]):(a=o+s,c=a-o,u=o-(a-c)+(s-c),s=r[++h]),o=a,0!==u&&(i[d++]=u);for(;l=33306690738754716e-32*f?c:-function(t,n,e,r,i,o,a){let u,c,f,s,l,h,d,p,g,y,v,_,b,m,x,w,M,T;const A=t-i,S=e-i,E=n-o,N=r-o;m=A*N,h=hu*A,d=h-(h-A),p=A-d,h=hu*N,g=h-(h-N),y=N-g,x=p*y-(m-d*g-p*g-d*y),w=E*S,h=hu*E,d=h-(h-E),p=E-d,h=hu*S,g=h-(h-S),y=S-g,M=p*y-(w-d*g-p*g-d*y),v=x-M,l=x-v,_u[0]=x-(v+l)+(l-M),_=m+v,l=_-m,b=m-(_-l)+(v-l),v=b-w,l=b-v,_u[1]=b-(v+l)+(l-w),T=_+v,l=T-_,_u[2]=_-(T-l)+(v-l),_u[3]=T;let k=function(t,n){let e=n[0];for(let r=1;r=C||-k>=C)return k;if(l=t-A,u=t-(A+l)+(l-i),l=e-S,f=e-(S+l)+(l-i),l=n-E,c=n-(E+l)+(l-o),l=r-N,s=r-(N+l)+(l-o),0===u&&0===c&&0===f&&0===s)return k;if(C=vu*a+du*Math.abs(k),k+=A*s+N*u-(E*f+S*c),k>=C||-k>=C)return k;m=u*N,h=hu*u,d=h-(h-u),p=u-d,h=hu*N,g=h-(h-N),y=N-g,x=p*y-(m-d*g-p*g-d*y),w=c*S,h=hu*c,d=h-(h-c),p=c-d,h=hu*S,g=h-(h-S),y=S-g,M=p*y-(w-d*g-p*g-d*y),v=x-M,l=x-v,wu[0]=x-(v+l)+(l-M),_=m+v,l=_-m,b=m-(_-l)+(v-l),v=b-w,l=b-v,wu[1]=b-(v+l)+(l-w),T=_+v,l=T-_,wu[2]=_-(T-l)+(v-l),wu[3]=T;const P=pu(4,_u,4,wu,bu);m=A*s,h=hu*A,d=h-(h-A),p=A-d,h=hu*s,g=h-(h-s),y=s-g,x=p*y-(m-d*g-p*g-d*y),w=E*f,h=hu*E,d=h-(h-E),p=E-d,h=hu*f,g=h-(h-f),y=f-g,M=p*y-(w-d*g-p*g-d*y),v=x-M,l=x-v,wu[0]=x-(v+l)+(l-M),_=m+v,l=_-m,b=m-(_-l)+(v-l),v=b-w,l=b-v,wu[1]=b-(v+l)+(l-w),T=_+v,l=T-_,wu[2]=_-(T-l)+(v-l),wu[3]=T;const z=pu(P,bu,4,wu,mu);m=u*s,h=hu*u,d=h-(h-u),p=u-d,h=hu*s,g=h-(h-s),y=s-g,x=p*y-(m-d*g-p*g-d*y),w=c*f,h=hu*c,d=h-(h-c),p=c-d,h=hu*f,g=h-(h-f),y=f-g,M=p*y-(w-d*g-p*g-d*y),v=x-M,l=x-v,wu[0]=x-(v+l)+(l-M),_=m+v,l=_-m,b=m-(_-l)+(v-l),v=b-w,l=b-v,wu[1]=b-(v+l)+(l-w),T=_+v,l=T-_,wu[2]=_-(T-l)+(v-l),wu[3]=T;const $=pu(z,mu,4,wu,xu);return xu[$-1]}(t,n,e,r,i,o,f)}const Tu=Math.pow(2,-52),Au=new Uint32Array(512);class Su{static from(t,n=zu,e=$u){const r=t.length,i=new Float64Array(2*r);for(let o=0;o>1;if(n>0&&"number"!=typeof t[0])throw new Error("Expected coords to contain numbers.");this.coords=t;const e=Math.max(2*n-5,0);this._triangles=new Uint32Array(3*e),this._halfedges=new Int32Array(3*e),this._hashSize=Math.ceil(Math.sqrt(n)),this._hullPrev=new Uint32Array(n),this._hullNext=new Uint32Array(n),this._hullTri=new Uint32Array(n),this._hullHash=new Int32Array(this._hashSize),this._ids=new Uint32Array(n),this._dists=new Float64Array(n),this.update()}update(){const{coords:t,_hullPrev:n,_hullNext:e,_hullTri:r,_hullHash:i}=this,o=t.length>>1;let a=1/0,u=1/0,c=-1/0,f=-1/0;for(let n=0;nc&&(c=e),r>f&&(f=r),this._ids[n]=n}const s=(a+c)/2,l=(u+f)/2;let h,d,p;for(let n=0,e=1/0;n0&&(d=n,e=r)}let v=t[2*d],_=t[2*d+1],b=1/0;for(let n=0;nr&&(n[e++]=i,r=o)}return this.hull=n.subarray(0,e),this.triangles=new Uint32Array(0),void(this.halfedges=new Uint32Array(0))}if(Mu(g,y,v,_,m,x)<0){const t=d,n=v,e=_;d=p,v=m,_=x,p=t,m=n,x=e}const w=function(t,n,e,r,i,o){const a=e-t,u=r-n,c=i-t,f=o-n,s=a*a+u*u,l=c*c+f*f,h=.5/(a*f-u*c),d=t+(f*s-u*l)*h,p=n+(a*l-c*s)*h;return{x:d,y:p}}(g,y,v,_,m,x);this._cx=w.x,this._cy=w.y;for(let n=0;n0&&Math.abs(f-o)<=Tu&&Math.abs(s-a)<=Tu)continue;if(o=f,a=s,c===h||c===d||c===p)continue;let l=0;for(let t=0,n=this._hashKey(f,s);t=0;)if(y=g,y===l){y=-1;break}if(-1===y)continue;let v=this._addTriangle(y,c,e[y],-1,-1,r[y]);r[c]=this._legalize(v+2),r[y]=v,M++;let _=e[y];for(;g=e[_],Mu(f,s,t[2*_],t[2*_+1],t[2*g],t[2*g+1])<0;)v=this._addTriangle(_,c,g,r[c],-1,r[_]),r[c]=this._legalize(v+2),e[_]=_,M--,_=g;if(y===l)for(;g=n[y],Mu(f,s,t[2*g],t[2*g+1],t[2*y],t[2*y+1])<0;)v=this._addTriangle(g,c,y,-1,r[y],r[g]),this._legalize(v+2),r[g]=v,e[y]=y,M--,y=g;this._hullStart=n[c]=y,e[y]=n[_]=c,e[c]=_,i[this._hashKey(f,s)]=c,i[this._hashKey(t[2*y],t[2*y+1])]=y}this.hull=new Uint32Array(M);for(let t=0,n=this._hullStart;t0?3-e:1+e)/4}(t-this._cx,n-this._cy)*this._hashSize)%this._hashSize}_legalize(t){const{_triangles:n,_halfedges:e,coords:r}=this;let i=0,o=0;for(;;){const a=e[t],u=t-t%3;if(o=u+(t+2)%3,-1===a){if(0===i)break;t=Au[--i];continue}const c=a-a%3,f=u+(t+1)%3,s=c+(a+2)%3,l=n[o],h=n[t],d=n[f],p=n[s];if(Nu(r[2*l],r[2*l+1],r[2*h],r[2*h+1],r[2*d],r[2*d+1],r[2*p],r[2*p+1])){n[t]=p,n[a]=l;const r=e[s];if(-1===r){let n=this._hullStart;do{if(this._hullTri[n]===s){this._hullTri[n]=t;break}n=this._hullPrev[n]}while(n!==this._hullStart)}this._link(t,r),this._link(a,e[o]),this._link(o,s);const u=c+(a+1)%3;i=e&&n[t[a]]>o;)t[a+1]=t[a--];t[a+1]=r}else{let i=e+1,o=r;Pu(t,e+r>>1,i),n[t[e]]>n[t[r]]&&Pu(t,e,r),n[t[i]]>n[t[r]]&&Pu(t,i,r),n[t[e]]>n[t[i]]&&Pu(t,e,i);const a=t[i],u=n[a];for(;;){do{i++}while(n[t[i]]u);if(o=o-e?(Cu(t,n,i,r),Cu(t,n,e,o-1)):(Cu(t,n,e,o-1),Cu(t,n,i,r))}}function Pu(t,n,e){const r=t[n];t[n]=t[e],t[e]=r}function zu(t){return t[0]}function $u(t){return t[1]}const Du=1e-6;class Ru{constructor(){this._x0=this._y0=this._x1=this._y1=null,this._=""}moveTo(t,n){this._+=`M${this._x0=this._x1=+t},${this._y0=this._y1=+n}`}closePath(){null!==this._x1&&(this._x1=this._x0,this._y1=this._y0,this._+="Z")}lineTo(t,n){this._+=`L${this._x1=+t},${this._y1=+n}`}arc(t,n,e){const r=(t=+t)+(e=+e),i=n=+n;if(e<0)throw new Error("negative radius");null===this._x1?this._+=`M${r},${i}`:(Math.abs(this._x1-r)>Du||Math.abs(this._y1-i)>Du)&&(this._+="L"+r+","+i),e&&(this._+=`A${e},${e},0,1,1,${t-e},${n}A${e},${e},0,1,1,${this._x1=r},${this._y1=i}`)}rect(t,n,e,r){this._+=`M${this._x0=this._x1=+t},${this._y0=this._y1=+n}h${+e}v${+r}h${-e}Z`}value(){return this._||null}}class Fu{constructor(){this._=[]}moveTo(t,n){this._.push([t,n])}closePath(){this._.push(this._[0].slice())}lineTo(t,n){this._.push([t,n])}value(){return this._.length?this._:null}}class qu{constructor(t,[n,e,r,i]=[0,0,960,500]){if(!((r=+r)>=(n=+n)&&(i=+i)>=(e=+e)))throw new Error("invalid bounds");this.delaunay=t,this._circumcenters=new Float64Array(2*t.points.length),this.vectors=new Float64Array(2*t.points.length),this.xmax=r,this.xmin=n,this.ymax=i,this.ymin=e,this._init()}update(){return this.delaunay.update(),this._init(),this}_init(){const{delaunay:{points:t,hull:n,triangles:e},vectors:r}=this;let i,o;const a=this.circumcenters=this._circumcenters.subarray(0,e.length/3*2);for(let r,u,c=0,f=0,s=e.length;c1;)i-=2;for(let t=2;t0){if(n>=this.ymax)return null;(i=(this.ymax-n)/r)0){if(t>=this.xmax)return null;(i=(this.xmax-t)/e)this.xmax?2:0)|(nthis.ymax?8:0)}_simplify(t){if(t&&t.length>4){for(let n=0;n2&&function(t){const{triangles:n,coords:e}=t;for(let t=0;t1e-10)return!1}return!0}(t)){this.collinear=Int32Array.from({length:n.length/2},((t,n)=>n)).sort(((t,e)=>n[2*t]-n[2*e]||n[2*t+1]-n[2*e+1]));const t=this.collinear[0],e=this.collinear[this.collinear.length-1],r=[n[2*t],n[2*t+1],n[2*e],n[2*e+1]],i=1e-8*Math.hypot(r[3]-r[1],r[2]-r[0]);for(let t=0,e=n.length/2;t0&&(this.triangles=new Int32Array(3).fill(-1),this.halfedges=new Int32Array(3).fill(-1),this.triangles[0]=r[0],o[r[0]]=1,2===r.length&&(o[r[1]]=0,this.triangles[1]=r[1],this.triangles[2]=r[1]))}voronoi(t){return new qu(this,t)}*neighbors(t){const{inedges:n,hull:e,_hullIndex:r,halfedges:i,triangles:o,collinear:a}=this;if(a){const n=a.indexOf(t);return n>0&&(yield a[n-1]),void(n=0&&i!==e&&i!==r;)e=i;return i}_step(t,n,e){const{inedges:r,hull:i,_hullIndex:o,halfedges:a,triangles:u,points:c}=this;if(-1===r[t]||!c.length)return(t+1)%(c.length>>1);let f=t,s=Iu(n-c[2*t],2)+Iu(e-c[2*t+1],2);const l=r[t];let h=l;do{let r=u[h];const l=Iu(n-c[2*r],2)+Iu(e-c[2*r+1],2);if(l9999?"+"+Ku(n,6):Ku(n,4))+"-"+Ku(t.getUTCMonth()+1,2)+"-"+Ku(t.getUTCDate(),2)+(o?"T"+Ku(e,2)+":"+Ku(r,2)+":"+Ku(i,2)+"."+Ku(o,3)+"Z":i?"T"+Ku(e,2)+":"+Ku(r,2)+":"+Ku(i,2)+"Z":r||e?"T"+Ku(e,2)+":"+Ku(r,2)+"Z":"")}function Ju(t){var n=new RegExp('["'+t+"\n\r]"),e=t.charCodeAt(0);function r(t,n){var r,i=[],o=t.length,a=0,u=0,c=o<=0,f=!1;function s(){if(c)return Hu;if(f)return f=!1,ju;var n,r,i=a;if(t.charCodeAt(i)===Xu){for(;a++=o?c=!0:(r=t.charCodeAt(a++))===Gu?f=!0:r===Vu&&(f=!0,t.charCodeAt(a)===Gu&&++a),t.slice(i+1,n-1).replace(/""/g,'"')}for(;amc(n,e).then((n=>(new DOMParser).parseFromString(n,t)))}var Sc=Ac("application/xml"),Ec=Ac("text/html"),Nc=Ac("image/svg+xml");function kc(t,n,e,r){if(isNaN(n)||isNaN(e))return t;var i,o,a,u,c,f,s,l,h,d=t._root,p={data:r},g=t._x0,y=t._y0,v=t._x1,_=t._y1;if(!d)return t._root=p,t;for(;d.length;)if((f=n>=(o=(g+v)/2))?g=o:v=o,(s=e>=(a=(y+_)/2))?y=a:_=a,i=d,!(d=d[l=s<<1|f]))return i[l]=p,t;if(u=+t._x.call(null,d.data),c=+t._y.call(null,d.data),n===u&&e===c)return p.next=d,i?i[l]=p:t._root=p,t;do{i=i?i[l]=new Array(4):t._root=new Array(4),(f=n>=(o=(g+v)/2))?g=o:v=o,(s=e>=(a=(y+_)/2))?y=a:_=a}while((l=s<<1|f)==(h=(c>=a)<<1|u>=o));return i[h]=d,i[l]=p,t}function Cc(t,n,e,r,i){this.node=t,this.x0=n,this.y0=e,this.x1=r,this.y1=i}function Pc(t){return t[0]}function zc(t){return t[1]}function $c(t,n,e){var r=new Dc(null==n?Pc:n,null==e?zc:e,NaN,NaN,NaN,NaN);return null==t?r:r.addAll(t)}function Dc(t,n,e,r,i,o){this._x=t,this._y=n,this._x0=e,this._y0=r,this._x1=i,this._y1=o,this._root=void 0}function Rc(t){for(var n={data:t.data},e=n;t=t.next;)e=e.next={data:t.data};return n}var Fc=$c.prototype=Dc.prototype;function qc(t){return function(){return t}}function Uc(t){return 1e-6*(t()-.5)}function Ic(t){return t.x+t.vx}function Oc(t){return t.y+t.vy}function Bc(t){return t.index}function Yc(t,n){var e=t.get(n);if(!e)throw new Error("node not found: "+n);return e}Fc.copy=function(){var t,n,e=new Dc(this._x,this._y,this._x0,this._y0,this._x1,this._y1),r=this._root;if(!r)return e;if(!r.length)return e._root=Rc(r),e;for(t=[{source:r,target:e._root=new Array(4)}];r=t.pop();)for(var i=0;i<4;++i)(n=r.source[i])&&(n.length?t.push({source:n,target:r.target[i]=new Array(4)}):r.target[i]=Rc(n));return e},Fc.add=function(t){const n=+this._x.call(null,t),e=+this._y.call(null,t);return kc(this.cover(n,e),n,e,t)},Fc.addAll=function(t){var n,e,r,i,o=t.length,a=new Array(o),u=new Array(o),c=1/0,f=1/0,s=-1/0,l=-1/0;for(e=0;es&&(s=r),il&&(l=i));if(c>s||f>l)return this;for(this.cover(c,f).cover(s,l),e=0;et||t>=i||r>n||n>=o;)switch(u=(nh||(o=c.y0)>d||(a=c.x1)=v)<<1|t>=y)&&(c=p[p.length-1],p[p.length-1]=p[p.length-1-f],p[p.length-1-f]=c)}else{var _=t-+this._x.call(null,g.data),b=n-+this._y.call(null,g.data),m=_*_+b*b;if(m=(u=(p+y)/2))?p=u:y=u,(s=a>=(c=(g+v)/2))?g=c:v=c,n=d,!(d=d[l=s<<1|f]))return this;if(!d.length)break;(n[l+1&3]||n[l+2&3]||n[l+3&3])&&(e=n,h=l)}for(;d.data!==t;)if(r=d,!(d=d.next))return this;return(i=d.next)&&delete d.next,r?(i?r.next=i:delete r.next,this):n?(i?n[l]=i:delete n[l],(d=n[0]||n[1]||n[2]||n[3])&&d===(n[3]||n[2]||n[1]||n[0])&&!d.length&&(e?e[h]=d:this._root=d),this):(this._root=i,this)},Fc.removeAll=function(t){for(var n=0,e=t.length;n1?r[0]+r.slice(2):r,+t.slice(e+1)]}function Zc(t){return(t=Wc(Math.abs(t)))?t[1]:NaN}var Kc,Qc=/^(?:(.)?([<>=^]))?([+\-( ])?([$#])?(0)?(\d+)?(,)?(\.\d+)?(~)?([a-z%])?$/i;function Jc(t){if(!(n=Qc.exec(t)))throw new Error("invalid format: "+t);var n;return new tf({fill:n[1],align:n[2],sign:n[3],symbol:n[4],zero:n[5],width:n[6],comma:n[7],precision:n[8]&&n[8].slice(1),trim:n[9],type:n[10]})}function tf(t){this.fill=void 0===t.fill?" ":t.fill+"",this.align=void 0===t.align?">":t.align+"",this.sign=void 0===t.sign?"-":t.sign+"",this.symbol=void 0===t.symbol?"":t.symbol+"",this.zero=!!t.zero,this.width=void 0===t.width?void 0:+t.width,this.comma=!!t.comma,this.precision=void 0===t.precision?void 0:+t.precision,this.trim=!!t.trim,this.type=void 0===t.type?"":t.type+""}function nf(t,n){var e=Wc(t,n);if(!e)return t+"";var r=e[0],i=e[1];return i<0?"0."+new Array(-i).join("0")+r:r.length>i+1?r.slice(0,i+1)+"."+r.slice(i+1):r+new Array(i-r.length+2).join("0")}Jc.prototype=tf.prototype,tf.prototype.toString=function(){return this.fill+this.align+this.sign+this.symbol+(this.zero?"0":"")+(void 0===this.width?"":Math.max(1,0|this.width))+(this.comma?",":"")+(void 0===this.precision?"":"."+Math.max(0,0|this.precision))+(this.trim?"~":"")+this.type};var ef={"%":(t,n)=>(100*t).toFixed(n),b:t=>Math.round(t).toString(2),c:t=>t+"",d:function(t){return Math.abs(t=Math.round(t))>=1e21?t.toLocaleString("en").replace(/,/g,""):t.toString(10)},e:(t,n)=>t.toExponential(n),f:(t,n)=>t.toFixed(n),g:(t,n)=>t.toPrecision(n),o:t=>Math.round(t).toString(8),p:(t,n)=>nf(100*t,n),r:nf,s:function(t,n){var e=Wc(t,n);if(!e)return t+"";var r=e[0],i=e[1],o=i-(Kc=3*Math.max(-8,Math.min(8,Math.floor(i/3))))+1,a=r.length;return o===a?r:o>a?r+new Array(o-a+1).join("0"):o>0?r.slice(0,o)+"."+r.slice(o):"0."+new Array(1-o).join("0")+Wc(t,Math.max(0,n+o-1))[0]},X:t=>Math.round(t).toString(16).toUpperCase(),x:t=>Math.round(t).toString(16)};function rf(t){return t}var of,af=Array.prototype.map,uf=["y","z","a","f","p","n","µ","m","","k","M","G","T","P","E","Z","Y"];function cf(t){var n,e,r=void 0===t.grouping||void 0===t.thousands?rf:(n=af.call(t.grouping,Number),e=t.thousands+"",function(t,r){for(var i=t.length,o=[],a=0,u=n[0],c=0;i>0&&u>0&&(c+u+1>r&&(u=Math.max(1,r-c)),o.push(t.substring(i-=u,i+u)),!((c+=u+1)>r));)u=n[a=(a+1)%n.length];return o.reverse().join(e)}),i=void 0===t.currency?"":t.currency[0]+"",o=void 0===t.currency?"":t.currency[1]+"",a=void 0===t.decimal?".":t.decimal+"",u=void 0===t.numerals?rf:function(t){return function(n){return n.replace(/[0-9]/g,(function(n){return t[+n]}))}}(af.call(t.numerals,String)),c=void 0===t.percent?"%":t.percent+"",f=void 0===t.minus?"−":t.minus+"",s=void 0===t.nan?"NaN":t.nan+"";function l(t){var n=(t=Jc(t)).fill,e=t.align,l=t.sign,h=t.symbol,d=t.zero,p=t.width,g=t.comma,y=t.precision,v=t.trim,_=t.type;"n"===_?(g=!0,_="g"):ef[_]||(void 0===y&&(y=12),v=!0,_="g"),(d||"0"===n&&"="===e)&&(d=!0,n="0",e="=");var b="$"===h?i:"#"===h&&/[boxX]/.test(_)?"0"+_.toLowerCase():"",m="$"===h?o:/[%p]/.test(_)?c:"",x=ef[_],w=/[defgprs%]/.test(_);function M(t){var i,o,c,h=b,M=m;if("c"===_)M=x(t)+M,t="";else{var T=(t=+t)<0||1/t<0;if(t=isNaN(t)?s:x(Math.abs(t),y),v&&(t=function(t){t:for(var n,e=t.length,r=1,i=-1;r0&&(i=0)}return i>0?t.slice(0,i)+t.slice(n+1):t}(t)),T&&0==+t&&"+"!==l&&(T=!1),h=(T?"("===l?l:f:"-"===l||"("===l?"":l)+h,M=("s"===_?uf[8+Kc/3]:"")+M+(T&&"("===l?")":""),w)for(i=-1,o=t.length;++i(c=t.charCodeAt(i))||c>57){M=(46===c?a+t.slice(i+1):t.slice(i))+M,t=t.slice(0,i);break}}g&&!d&&(t=r(t,1/0));var A=h.length+t.length+M.length,S=A>1)+h+t+M+S.slice(A);break;default:t=S+h+t+M}return u(t)}return y=void 0===y?6:/[gprs]/.test(_)?Math.max(1,Math.min(21,y)):Math.max(0,Math.min(20,y)),M.toString=function(){return t+""},M}return{format:l,formatPrefix:function(t,n){var e=l(((t=Jc(t)).type="f",t)),r=3*Math.max(-8,Math.min(8,Math.floor(Zc(n)/3))),i=Math.pow(10,-r),o=uf[8+r/3];return function(t){return e(i*t)+o}}}}function ff(n){return of=cf(n),t.format=of.format,t.formatPrefix=of.formatPrefix,of}function sf(t){return Math.max(0,-Zc(Math.abs(t)))}function lf(t,n){return Math.max(0,3*Math.max(-8,Math.min(8,Math.floor(Zc(n)/3)))-Zc(Math.abs(t)))}function hf(t,n){return t=Math.abs(t),n=Math.abs(n)-t,Math.max(0,Zc(n)-Zc(t))+1}t.format=void 0,t.formatPrefix=void 0,ff({thousands:",",grouping:[3],currency:["$",""]});var df=1e-6,pf=1e-12,gf=Math.PI,yf=gf/2,vf=gf/4,_f=2*gf,bf=180/gf,mf=gf/180,xf=Math.abs,wf=Math.atan,Mf=Math.atan2,Tf=Math.cos,Af=Math.ceil,Sf=Math.exp,Ef=Math.hypot,Nf=Math.log,kf=Math.pow,Cf=Math.sin,Pf=Math.sign||function(t){return t>0?1:t<0?-1:0},zf=Math.sqrt,$f=Math.tan;function Df(t){return t>1?0:t<-1?gf:Math.acos(t)}function Rf(t){return t>1?yf:t<-1?-yf:Math.asin(t)}function Ff(t){return(t=Cf(t/2))*t}function qf(){}function Uf(t,n){t&&Of.hasOwnProperty(t.type)&&Of[t.type](t,n)}var If={Feature:function(t,n){Uf(t.geometry,n)},FeatureCollection:function(t,n){for(var e=t.features,r=-1,i=e.length;++r=0?1:-1,i=r*e,o=Tf(n=(n*=mf)/2+vf),a=Cf(n),u=Vf*a,c=Gf*o+u*Tf(i),f=u*r*Cf(i);as.add(Mf(f,c)),Xf=t,Gf=o,Vf=a}function ds(t){return[Mf(t[1],t[0]),Rf(t[2])]}function ps(t){var n=t[0],e=t[1],r=Tf(e);return[r*Tf(n),r*Cf(n),Cf(e)]}function gs(t,n){return t[0]*n[0]+t[1]*n[1]+t[2]*n[2]}function ys(t,n){return[t[1]*n[2]-t[2]*n[1],t[2]*n[0]-t[0]*n[2],t[0]*n[1]-t[1]*n[0]]}function vs(t,n){t[0]+=n[0],t[1]+=n[1],t[2]+=n[2]}function _s(t,n){return[t[0]*n,t[1]*n,t[2]*n]}function bs(t){var n=zf(t[0]*t[0]+t[1]*t[1]+t[2]*t[2]);t[0]/=n,t[1]/=n,t[2]/=n}var ms,xs,ws,Ms,Ts,As,Ss,Es,Ns,ks,Cs,Ps,zs,$s,Ds,Rs,Fs={point:qs,lineStart:Is,lineEnd:Os,polygonStart:function(){Fs.point=Bs,Fs.lineStart=Ys,Fs.lineEnd=Ls,rs=new T,cs.polygonStart()},polygonEnd:function(){cs.polygonEnd(),Fs.point=qs,Fs.lineStart=Is,Fs.lineEnd=Os,as<0?(Wf=-(Kf=180),Zf=-(Qf=90)):rs>df?Qf=90:rs<-df&&(Zf=-90),os[0]=Wf,os[1]=Kf},sphere:function(){Wf=-(Kf=180),Zf=-(Qf=90)}};function qs(t,n){is.push(os=[Wf=t,Kf=t]),nQf&&(Qf=n)}function Us(t,n){var e=ps([t*mf,n*mf]);if(es){var r=ys(es,e),i=ys([r[1],-r[0],0],r);bs(i),i=ds(i);var o,a=t-Jf,u=a>0?1:-1,c=i[0]*bf*u,f=xf(a)>180;f^(u*JfQf&&(Qf=o):f^(u*Jf<(c=(c+360)%360-180)&&cQf&&(Qf=n)),f?tjs(Wf,Kf)&&(Kf=t):js(t,Kf)>js(Wf,Kf)&&(Wf=t):Kf>=Wf?(tKf&&(Kf=t)):t>Jf?js(Wf,t)>js(Wf,Kf)&&(Kf=t):js(t,Kf)>js(Wf,Kf)&&(Wf=t)}else is.push(os=[Wf=t,Kf=t]);nQf&&(Qf=n),es=e,Jf=t}function Is(){Fs.point=Us}function Os(){os[0]=Wf,os[1]=Kf,Fs.point=qs,es=null}function Bs(t,n){if(es){var e=t-Jf;rs.add(xf(e)>180?e+(e>0?360:-360):e)}else ts=t,ns=n;cs.point(t,n),Us(t,n)}function Ys(){cs.lineStart()}function Ls(){Bs(ts,ns),cs.lineEnd(),xf(rs)>df&&(Wf=-(Kf=180)),os[0]=Wf,os[1]=Kf,es=null}function js(t,n){return(n-=t)<0?n+360:n}function Hs(t,n){return t[0]-n[0]}function Xs(t,n){return t[0]<=t[1]?t[0]<=n&&n<=t[1]:ngf&&(t-=Math.round(t/_f)*_f),[t,n]}function ul(t,n,e){return(t%=_f)?n||e?ol(fl(t),sl(n,e)):fl(t):n||e?sl(n,e):al}function cl(t){return function(n,e){return xf(n+=t)>gf&&(n-=Math.round(n/_f)*_f),[n,e]}}function fl(t){var n=cl(t);return n.invert=cl(-t),n}function sl(t,n){var e=Tf(t),r=Cf(t),i=Tf(n),o=Cf(n);function a(t,n){var a=Tf(n),u=Tf(t)*a,c=Cf(t)*a,f=Cf(n),s=f*e+u*r;return[Mf(c*i-s*o,u*e-f*r),Rf(s*i+c*o)]}return a.invert=function(t,n){var a=Tf(n),u=Tf(t)*a,c=Cf(t)*a,f=Cf(n),s=f*i-c*o;return[Mf(c*i+f*o,u*e+s*r),Rf(s*e-u*r)]},a}function ll(t){function n(n){return(n=t(n[0]*mf,n[1]*mf))[0]*=bf,n[1]*=bf,n}return t=ul(t[0]*mf,t[1]*mf,t.length>2?t[2]*mf:0),n.invert=function(n){return(n=t.invert(n[0]*mf,n[1]*mf))[0]*=bf,n[1]*=bf,n},n}function hl(t,n,e,r,i,o){if(e){var a=Tf(n),u=Cf(n),c=r*e;null==i?(i=n+r*_f,o=n-c/2):(i=dl(a,i),o=dl(a,o),(r>0?io)&&(i+=r*_f));for(var f,s=i;r>0?s>o:s1&&n.push(n.pop().concat(n.shift()))},result:function(){var e=n;return n=[],t=null,e}}}function gl(t,n){return xf(t[0]-n[0])=0;--o)i.point((s=f[o])[0],s[1]);else r(h.x,h.p.x,-1,i);h=h.p}f=(h=h.o).z,d=!d}while(!h.v);i.lineEnd()}}}function _l(t){if(n=t.length){for(var n,e,r=0,i=t[0];++r=0?1:-1,E=S*A,N=E>gf,k=y*w;if(c.add(Mf(k*S*Cf(E),v*M+k*Tf(E))),a+=N?A+S*_f:A,N^p>=e^m>=e){var C=ys(ps(d),ps(b));bs(C);var P=ys(o,C);bs(P);var z=(N^A>=0?-1:1)*Rf(P[2]);(r>z||r===z&&(C[0]||C[1]))&&(u+=N^A>=0?1:-1)}}return(a<-df||a0){for(l||(i.polygonStart(),l=!0),i.lineStart(),t=0;t1&&2&c&&h.push(h.pop().concat(h.shift())),a.push(h.filter(wl))}return h}}function wl(t){return t.length>1}function Ml(t,n){return((t=t.x)[0]<0?t[1]-yf-df:yf-t[1])-((n=n.x)[0]<0?n[1]-yf-df:yf-n[1])}al.invert=al;var Tl=xl((function(){return!0}),(function(t){var n,e=NaN,r=NaN,i=NaN;return{lineStart:function(){t.lineStart(),n=1},point:function(o,a){var u=o>0?gf:-gf,c=xf(o-e);xf(c-gf)0?yf:-yf),t.point(i,r),t.lineEnd(),t.lineStart(),t.point(u,r),t.point(o,r),n=0):i!==u&&c>=gf&&(xf(e-i)df?wf((Cf(n)*(o=Tf(r))*Cf(e)-Cf(r)*(i=Tf(n))*Cf(t))/(i*o*a)):(n+r)/2}(e,r,o,a),t.point(i,r),t.lineEnd(),t.lineStart(),t.point(u,r),n=0),t.point(e=o,r=a),i=u},lineEnd:function(){t.lineEnd(),e=r=NaN},clean:function(){return 2-n}}}),(function(t,n,e,r){var i;if(null==t)i=e*yf,r.point(-gf,i),r.point(0,i),r.point(gf,i),r.point(gf,0),r.point(gf,-i),r.point(0,-i),r.point(-gf,-i),r.point(-gf,0),r.point(-gf,i);else if(xf(t[0]-n[0])>df){var o=t[0]0,i=xf(n)>df;function o(t,e){return Tf(t)*Tf(e)>n}function a(t,e,r){var i=[1,0,0],o=ys(ps(t),ps(e)),a=gs(o,o),u=o[0],c=a-u*u;if(!c)return!r&&t;var f=n*a/c,s=-n*u/c,l=ys(i,o),h=_s(i,f);vs(h,_s(o,s));var d=l,p=gs(h,d),g=gs(d,d),y=p*p-g*(gs(h,h)-1);if(!(y<0)){var v=zf(y),_=_s(d,(-p-v)/g);if(vs(_,h),_=ds(_),!r)return _;var b,m=t[0],x=e[0],w=t[1],M=e[1];x0^_[1]<(xf(_[0]-m)gf^(m<=_[0]&&_[0]<=x)){var S=_s(d,(-p+v)/g);return vs(S,h),[_,ds(S)]}}}function u(n,e){var i=r?t:gf-t,o=0;return n<-i?o|=1:n>i&&(o|=2),e<-i?o|=4:e>i&&(o|=8),o}return xl(o,(function(t){var n,e,c,f,s;return{lineStart:function(){f=c=!1,s=1},point:function(l,h){var d,p=[l,h],g=o(l,h),y=r?g?0:u(l,h):g?u(l+(l<0?gf:-gf),h):0;if(!n&&(f=c=g)&&t.lineStart(),g!==c&&(!(d=a(n,p))||gl(n,d)||gl(p,d))&&(p[2]=1),g!==c)s=0,g?(t.lineStart(),d=a(p,n),t.point(d[0],d[1])):(d=a(n,p),t.point(d[0],d[1],2),t.lineEnd()),n=d;else if(i&&n&&r^g){var v;y&e||!(v=a(p,n,!0))||(s=0,r?(t.lineStart(),t.point(v[0][0],v[0][1]),t.point(v[1][0],v[1][1]),t.lineEnd()):(t.point(v[1][0],v[1][1]),t.lineEnd(),t.lineStart(),t.point(v[0][0],v[0][1],3)))}!g||n&&gl(n,p)||t.point(p[0],p[1]),n=p,c=g,e=y},lineEnd:function(){c&&t.lineEnd(),n=null},clean:function(){return s|(f&&c)<<1}}}),(function(n,r,i,o){hl(o,t,e,i,n,r)}),r?[0,-t]:[-gf,t-gf])}var Sl,El,Nl,kl,Cl=1e9,Pl=-Cl;function zl(t,n,e,r){function i(i,o){return t<=i&&i<=e&&n<=o&&o<=r}function o(i,o,u,f){var s=0,l=0;if(null==i||(s=a(i,u))!==(l=a(o,u))||c(i,o)<0^u>0)do{f.point(0===s||3===s?t:e,s>1?r:n)}while((s=(s+u+4)%4)!==l);else f.point(o[0],o[1])}function a(r,i){return xf(r[0]-t)0?0:3:xf(r[0]-e)0?2:1:xf(r[1]-n)0?1:0:i>0?3:2}function u(t,n){return c(t.x,n.x)}function c(t,n){var e=a(t,1),r=a(n,1);return e!==r?e-r:0===e?n[1]-t[1]:1===e?t[0]-n[0]:2===e?t[1]-n[1]:n[0]-t[0]}return function(a){var c,f,s,l,h,d,p,g,y,v,_,b=a,m=pl(),x={point:w,lineStart:function(){x.point=M,f&&f.push(s=[]);v=!0,y=!1,p=g=NaN},lineEnd:function(){c&&(M(l,h),d&&y&&m.rejoin(),c.push(m.result()));x.point=w,y&&b.lineEnd()},polygonStart:function(){b=m,c=[],f=[],_=!0},polygonEnd:function(){var n=function(){for(var n=0,e=0,i=f.length;er&&(h-o)*(r-a)>(d-a)*(t-o)&&++n:d<=r&&(h-o)*(r-a)<(d-a)*(t-o)&&--n;return n}(),e=_&&n,i=(c=ft(c)).length;(e||i)&&(a.polygonStart(),e&&(a.lineStart(),o(null,null,1,a),a.lineEnd()),i&&vl(c,u,n,o,a),a.polygonEnd());b=a,c=f=s=null}};function w(t,n){i(t,n)&&b.point(t,n)}function M(o,a){var u=i(o,a);if(f&&s.push([o,a]),v)l=o,h=a,d=u,v=!1,u&&(b.lineStart(),b.point(o,a));else if(u&&y)b.point(o,a);else{var c=[p=Math.max(Pl,Math.min(Cl,p)),g=Math.max(Pl,Math.min(Cl,g))],m=[o=Math.max(Pl,Math.min(Cl,o)),a=Math.max(Pl,Math.min(Cl,a))];!function(t,n,e,r,i,o){var a,u=t[0],c=t[1],f=0,s=1,l=n[0]-u,h=n[1]-c;if(a=e-u,l||!(a>0)){if(a/=l,l<0){if(a0){if(a>s)return;a>f&&(f=a)}if(a=i-u,l||!(a<0)){if(a/=l,l<0){if(a>s)return;a>f&&(f=a)}else if(l>0){if(a0)){if(a/=h,h<0){if(a0){if(a>s)return;a>f&&(f=a)}if(a=o-c,h||!(a<0)){if(a/=h,h<0){if(a>s)return;a>f&&(f=a)}else if(h>0){if(a0&&(t[0]=u+f*l,t[1]=c+f*h),s<1&&(n[0]=u+s*l,n[1]=c+s*h),!0}}}}}(c,m,t,n,e,r)?u&&(b.lineStart(),b.point(o,a),_=!1):(y||(b.lineStart(),b.point(c[0],c[1])),b.point(m[0],m[1]),u||b.lineEnd(),_=!1)}p=o,g=a,y=u}return x}}var $l={sphere:qf,point:qf,lineStart:function(){$l.point=Rl,$l.lineEnd=Dl},lineEnd:qf,polygonStart:qf,polygonEnd:qf};function Dl(){$l.point=$l.lineEnd=qf}function Rl(t,n){El=t*=mf,Nl=Cf(n*=mf),kl=Tf(n),$l.point=Fl}function Fl(t,n){t*=mf;var e=Cf(n*=mf),r=Tf(n),i=xf(t-El),o=Tf(i),a=r*Cf(i),u=kl*e-Nl*r*o,c=Nl*e+kl*r*o;Sl.add(Mf(zf(a*a+u*u),c)),El=t,Nl=e,kl=r}function ql(t){return Sl=new T,Lf(t,$l),+Sl}var Ul=[null,null],Il={type:"LineString",coordinates:Ul};function Ol(t,n){return Ul[0]=t,Ul[1]=n,ql(Il)}var Bl={Feature:function(t,n){return Ll(t.geometry,n)},FeatureCollection:function(t,n){for(var e=t.features,r=-1,i=e.length;++r0&&(i=Ol(t[o],t[o-1]))>0&&e<=i&&r<=i&&(e+r-i)*(1-Math.pow((e-r)/i,2))df})).map(c)).concat(lt(Af(o/d)*d,i,d).filter((function(t){return xf(t%g)>df})).map(f))}return v.lines=function(){return _().map((function(t){return{type:"LineString",coordinates:t}}))},v.outline=function(){return{type:"Polygon",coordinates:[s(r).concat(l(a).slice(1),s(e).reverse().slice(1),l(u).reverse().slice(1))]}},v.extent=function(t){return arguments.length?v.extentMajor(t).extentMinor(t):v.extentMinor()},v.extentMajor=function(t){return arguments.length?(r=+t[0][0],e=+t[1][0],u=+t[0][1],a=+t[1][1],r>e&&(t=r,r=e,e=t),u>a&&(t=u,u=a,a=t),v.precision(y)):[[r,u],[e,a]]},v.extentMinor=function(e){return arguments.length?(n=+e[0][0],t=+e[1][0],o=+e[0][1],i=+e[1][1],n>t&&(e=n,n=t,t=e),o>i&&(e=o,o=i,i=e),v.precision(y)):[[n,o],[t,i]]},v.step=function(t){return arguments.length?v.stepMajor(t).stepMinor(t):v.stepMinor()},v.stepMajor=function(t){return arguments.length?(p=+t[0],g=+t[1],v):[p,g]},v.stepMinor=function(t){return arguments.length?(h=+t[0],d=+t[1],v):[h,d]},v.precision=function(h){return arguments.length?(y=+h,c=Wl(o,i,90),f=Zl(n,t,y),s=Wl(u,a,90),l=Zl(r,e,y),v):y},v.extentMajor([[-180,-90+df],[180,90-df]]).extentMinor([[-180,-80-df],[180,80+df]])}var Ql,Jl,th,nh,eh=t=>t,rh=new T,ih=new T,oh={point:qf,lineStart:qf,lineEnd:qf,polygonStart:function(){oh.lineStart=ah,oh.lineEnd=fh},polygonEnd:function(){oh.lineStart=oh.lineEnd=oh.point=qf,rh.add(xf(ih)),ih=new T},result:function(){var t=rh/2;return rh=new T,t}};function ah(){oh.point=uh}function uh(t,n){oh.point=ch,Ql=th=t,Jl=nh=n}function ch(t,n){ih.add(nh*t-th*n),th=t,nh=n}function fh(){ch(Ql,Jl)}var sh=oh,lh=1/0,hh=lh,dh=-lh,ph=dh,gh={point:function(t,n){tdh&&(dh=t);nph&&(ph=n)},lineStart:qf,lineEnd:qf,polygonStart:qf,polygonEnd:qf,result:function(){var t=[[lh,hh],[dh,ph]];return dh=ph=-(hh=lh=1/0),t}};var yh,vh,_h,bh,mh=gh,xh=0,wh=0,Mh=0,Th=0,Ah=0,Sh=0,Eh=0,Nh=0,kh=0,Ch={point:Ph,lineStart:zh,lineEnd:Rh,polygonStart:function(){Ch.lineStart=Fh,Ch.lineEnd=qh},polygonEnd:function(){Ch.point=Ph,Ch.lineStart=zh,Ch.lineEnd=Rh},result:function(){var t=kh?[Eh/kh,Nh/kh]:Sh?[Th/Sh,Ah/Sh]:Mh?[xh/Mh,wh/Mh]:[NaN,NaN];return xh=wh=Mh=Th=Ah=Sh=Eh=Nh=kh=0,t}};function Ph(t,n){xh+=t,wh+=n,++Mh}function zh(){Ch.point=$h}function $h(t,n){Ch.point=Dh,Ph(_h=t,bh=n)}function Dh(t,n){var e=t-_h,r=n-bh,i=zf(e*e+r*r);Th+=i*(_h+t)/2,Ah+=i*(bh+n)/2,Sh+=i,Ph(_h=t,bh=n)}function Rh(){Ch.point=Ph}function Fh(){Ch.point=Uh}function qh(){Ih(yh,vh)}function Uh(t,n){Ch.point=Ih,Ph(yh=_h=t,vh=bh=n)}function Ih(t,n){var e=t-_h,r=n-bh,i=zf(e*e+r*r);Th+=i*(_h+t)/2,Ah+=i*(bh+n)/2,Sh+=i,Eh+=(i=bh*t-_h*n)*(_h+t),Nh+=i*(bh+n),kh+=3*i,Ph(_h=t,bh=n)}var Oh=Ch;function Bh(t){this._context=t}Bh.prototype={_radius:4.5,pointRadius:function(t){return this._radius=t,this},polygonStart:function(){this._line=0},polygonEnd:function(){this._line=NaN},lineStart:function(){this._point=0},lineEnd:function(){0===this._line&&this._context.closePath(),this._point=NaN},point:function(t,n){switch(this._point){case 0:this._context.moveTo(t,n),this._point=1;break;case 1:this._context.lineTo(t,n);break;default:this._context.moveTo(t+this._radius,n),this._context.arc(t,n,this._radius,0,_f)}},result:qf};var Yh,Lh,jh,Hh,Xh,Gh=new T,Vh={point:qf,lineStart:function(){Vh.point=Wh},lineEnd:function(){Yh&&Zh(Lh,jh),Vh.point=qf},polygonStart:function(){Yh=!0},polygonEnd:function(){Yh=null},result:function(){var t=+Gh;return Gh=new T,t}};function Wh(t,n){Vh.point=Zh,Lh=Hh=t,jh=Xh=n}function Zh(t,n){Hh-=t,Xh-=n,Gh.add(zf(Hh*Hh+Xh*Xh)),Hh=t,Xh=n}var Kh=Vh;let Qh,Jh,td,nd;class ed{constructor(t){this._append=null==t?rd:function(t){const n=Math.floor(t);if(!(n>=0))throw new RangeError(`invalid digits: ${t}`);if(n>15)return rd;if(n!==Qh){const t=10**n;Qh=n,Jh=function(n){let e=1;this._+=n[0];for(const r=n.length;e4*n&&g--){var m=a+h,x=u+d,w=c+p,M=zf(m*m+x*x+w*w),T=Rf(w/=M),A=xf(xf(w)-1)n||xf((v*k+_*C)/b-.5)>.3||a*h+u*d+c*p2?t[2]%360*mf:0,k()):[y*bf,v*bf,_*bf]},E.angle=function(t){return arguments.length?(b=t%360*mf,k()):b*bf},E.reflectX=function(t){return arguments.length?(m=t?-1:1,k()):m<0},E.reflectY=function(t){return arguments.length?(x=t?-1:1,k()):x<0},E.precision=function(t){return arguments.length?(a=dd(u,S=t*t),C()):zf(S)},E.fitExtent=function(t,n){return ud(E,t,n)},E.fitSize=function(t,n){return cd(E,t,n)},E.fitWidth=function(t,n){return fd(E,t,n)},E.fitHeight=function(t,n){return sd(E,t,n)},function(){return n=t.apply(this,arguments),E.invert=n.invert&&N,k()}}function _d(t){var n=0,e=gf/3,r=vd(t),i=r(n,e);return i.parallels=function(t){return arguments.length?r(n=t[0]*mf,e=t[1]*mf):[n*bf,e*bf]},i}function bd(t,n){var e=Cf(t),r=(e+Cf(n))/2;if(xf(r)0?n<-yf+df&&(n=-yf+df):n>yf-df&&(n=yf-df);var e=i/kf(Nd(n),r);return[e*Cf(r*t),i-e*Tf(r*t)]}return o.invert=function(t,n){var e=i-n,o=Pf(r)*zf(t*t+e*e),a=Mf(t,xf(e))*Pf(e);return e*r<0&&(a-=gf*Pf(t)*Pf(e)),[a/r,2*wf(kf(i/o,1/r))-yf]},o}function Cd(t,n){return[t,n]}function Pd(t,n){var e=Tf(t),r=t===n?Cf(t):(e-Tf(n))/(n-t),i=e/r+t;if(xf(r)=0;)n+=e[r].value;else n=1;t.value=n}function Gd(t,n){t instanceof Map?(t=[void 0,t],void 0===n&&(n=Wd)):void 0===n&&(n=Vd);for(var e,r,i,o,a,u=new Qd(t),c=[u];e=c.pop();)if((i=n(e.data))&&(a=(i=Array.from(i)).length))for(e.children=i,o=a-1;o>=0;--o)c.push(r=i[o]=new Qd(i[o])),r.parent=e,r.depth=e.depth+1;return u.eachBefore(Kd)}function Vd(t){return t.children}function Wd(t){return Array.isArray(t)?t[1]:null}function Zd(t){void 0!==t.data.value&&(t.value=t.data.value),t.data=t.data.data}function Kd(t){var n=0;do{t.height=n}while((t=t.parent)&&t.height<++n)}function Qd(t){this.data=t,this.depth=this.height=0,this.parent=null}function Jd(t){return null==t?null:tp(t)}function tp(t){if("function"!=typeof t)throw new Error;return t}function np(){return 0}function ep(t){return function(){return t}}qd.invert=function(t,n){for(var e,r=n,i=r*r,o=i*i*i,a=0;a<12&&(o=(i=(r-=e=(r*(zd+$d*i+o*(Dd+Rd*i))-n)/(zd+3*$d*i+o*(7*Dd+9*Rd*i)))*r)*i*i,!(xf(e)df&&--i>0);return[t/(.8707+(o=r*r)*(o*(o*o*o*(.003971-.001529*o)-.013791)-.131979)),r]},Od.invert=Md(Rf),Bd.invert=Md((function(t){return 2*wf(t)})),Yd.invert=function(t,n){return[-n,2*wf(Sf(t))-yf]},Qd.prototype=Gd.prototype={constructor:Qd,count:function(){return this.eachAfter(Xd)},each:function(t,n){let e=-1;for(const r of this)t.call(n,r,++e,this);return this},eachAfter:function(t,n){for(var e,r,i,o=this,a=[o],u=[],c=-1;o=a.pop();)if(u.push(o),e=o.children)for(r=0,i=e.length;r=0;--r)o.push(e[r]);return this},find:function(t,n){let e=-1;for(const r of this)if(t.call(n,r,++e,this))return r},sum:function(t){return this.eachAfter((function(n){for(var e=+t(n.data)||0,r=n.children,i=r&&r.length;--i>=0;)e+=r[i].value;n.value=e}))},sort:function(t){return this.eachBefore((function(n){n.children&&n.children.sort(t)}))},path:function(t){for(var n=this,e=function(t,n){if(t===n)return t;var e=t.ancestors(),r=n.ancestors(),i=null;t=e.pop(),n=r.pop();for(;t===n;)i=t,t=e.pop(),n=r.pop();return i}(n,t),r=[n];n!==e;)n=n.parent,r.push(n);for(var i=r.length;t!==e;)r.splice(i,0,t),t=t.parent;return r},ancestors:function(){for(var t=this,n=[t];t=t.parent;)n.push(t);return n},descendants:function(){return Array.from(this)},leaves:function(){var t=[];return this.eachBefore((function(n){n.children||t.push(n)})),t},links:function(){var t=this,n=[];return t.each((function(e){e!==t&&n.push({source:e.parent,target:e})})),n},copy:function(){return Gd(this).eachBefore(Zd)},[Symbol.iterator]:function*(){var t,n,e,r,i=this,o=[i];do{for(t=o.reverse(),o=[];i=t.pop();)if(yield i,n=i.children)for(e=0,r=n.length;e(t=(rp*t+ip)%op)/op}function up(t,n){for(var e,r,i=0,o=(t=function(t,n){let e,r,i=t.length;for(;i;)r=n()*i--|0,e=t[i],t[i]=t[r],t[r]=e;return t}(Array.from(t),n)).length,a=[];i0&&e*e>r*r+i*i}function lp(t,n){for(var e=0;e1e-6?(E+Math.sqrt(E*E-4*S*N))/(2*S):N/E);return{x:r+w+M*k,y:i+T+A*k,r:k}}function gp(t,n,e){var r,i,o,a,u=t.x-n.x,c=t.y-n.y,f=u*u+c*c;f?(i=n.r+e.r,i*=i,a=t.r+e.r,i>(a*=a)?(r=(f+a-i)/(2*f),o=Math.sqrt(Math.max(0,a/f-r*r)),e.x=t.x-r*u-o*c,e.y=t.y-r*c+o*u):(r=(f+i-a)/(2*f),o=Math.sqrt(Math.max(0,i/f-r*r)),e.x=n.x+r*u-o*c,e.y=n.y+r*c+o*u)):(e.x=n.x+e.r,e.y=n.y)}function yp(t,n){var e=t.r+n.r-1e-6,r=n.x-t.x,i=n.y-t.y;return e>0&&e*e>r*r+i*i}function vp(t){var n=t._,e=t.next._,r=n.r+e.r,i=(n.x*e.r+e.x*n.r)/r,o=(n.y*e.r+e.y*n.r)/r;return i*i+o*o}function _p(t){this._=t,this.next=null,this.previous=null}function bp(t,n){if(!(o=(t=function(t){return"object"==typeof t&&"length"in t?t:Array.from(t)}(t)).length))return 0;var e,r,i,o,a,u,c,f,s,l,h;if((e=t[0]).x=0,e.y=0,!(o>1))return e.r;if(r=t[1],e.x=-r.r,r.x=e.r,r.y=0,!(o>2))return e.r+r.r;gp(r,e,i=t[2]),e=new _p(e),r=new _p(r),i=new _p(i),e.next=i.previous=r,r.next=e.previous=i,i.next=r.previous=e;t:for(c=3;c1&&!zp(t,n););return t.slice(0,n)}function zp(t,n){if("/"===t[n]){let e=0;for(;n>0&&"\\"===t[--n];)++e;if(!(1&e))return!0}return!1}function $p(t,n){return t.parent===n.parent?1:2}function Dp(t){var n=t.children;return n?n[0]:t.t}function Rp(t){var n=t.children;return n?n[n.length-1]:t.t}function Fp(t,n,e){var r=e/(n.i-t.i);n.c-=r,n.s+=e,t.c+=r,n.z+=e,n.m+=e}function qp(t,n,e){return t.a.parent===n.parent?t.a:e}function Up(t,n){this._=t,this.parent=null,this.children=null,this.A=null,this.a=this,this.z=0,this.m=0,this.c=0,this.s=0,this.t=null,this.i=n}function Ip(t,n,e,r,i){for(var o,a=t.children,u=-1,c=a.length,f=t.value&&(i-e)/t.value;++uh&&(h=u),y=s*s*g,(d=Math.max(h/y,y/l))>p){s-=u;break}p=d}v.push(a={value:s,dice:c1?n:1)},e}(Op);var Lp=function t(n){function e(t,e,r,i,o){if((a=t._squarify)&&a.ratio===n)for(var a,u,c,f,s,l=-1,h=a.length,d=t.value;++l1?n:1)},e}(Op);function jp(t,n,e){return(n[0]-t[0])*(e[1]-t[1])-(n[1]-t[1])*(e[0]-t[0])}function Hp(t,n){return t[0]-n[0]||t[1]-n[1]}function Xp(t){const n=t.length,e=[0,1];let r,i=2;for(r=2;r1&&jp(t[e[i-2]],t[e[i-1]],t[r])<=0;)--i;e[i++]=r}return e.slice(0,i)}var Gp=Math.random,Vp=function t(n){function e(t,e){return t=null==t?0:+t,e=null==e?1:+e,1===arguments.length?(e=t,t=0):e-=t,function(){return n()*e+t}}return e.source=t,e}(Gp),Wp=function t(n){function e(t,e){return arguments.length<2&&(e=t,t=0),t=Math.floor(t),e=Math.floor(e)-t,function(){return Math.floor(n()*e+t)}}return e.source=t,e}(Gp),Zp=function t(n){function e(t,e){var r,i;return t=null==t?0:+t,e=null==e?1:+e,function(){var o;if(null!=r)o=r,r=null;else do{r=2*n()-1,o=2*n()-1,i=r*r+o*o}while(!i||i>1);return t+e*o*Math.sqrt(-2*Math.log(i)/i)}}return e.source=t,e}(Gp),Kp=function t(n){var e=Zp.source(n);function r(){var t=e.apply(this,arguments);return function(){return Math.exp(t())}}return r.source=t,r}(Gp),Qp=function t(n){function e(t){return(t=+t)<=0?()=>0:function(){for(var e=0,r=t;r>1;--r)e+=n();return e+r*n()}}return e.source=t,e}(Gp),Jp=function t(n){var e=Qp.source(n);function r(t){if(0==(t=+t))return n;var r=e(t);return function(){return r()/t}}return r.source=t,r}(Gp),tg=function t(n){function e(t){return function(){return-Math.log1p(-n())/t}}return e.source=t,e}(Gp),ng=function t(n){function e(t){if((t=+t)<0)throw new RangeError("invalid alpha");return t=1/-t,function(){return Math.pow(1-n(),t)}}return e.source=t,e}(Gp),eg=function t(n){function e(t){if((t=+t)<0||t>1)throw new RangeError("invalid p");return function(){return Math.floor(n()+t)}}return e.source=t,e}(Gp),rg=function t(n){function e(t){if((t=+t)<0||t>1)throw new RangeError("invalid p");return 0===t?()=>1/0:1===t?()=>1:(t=Math.log1p(-t),function(){return 1+Math.floor(Math.log1p(-n())/t)})}return e.source=t,e}(Gp),ig=function t(n){var e=Zp.source(n)();function r(t,r){if((t=+t)<0)throw new RangeError("invalid k");if(0===t)return()=>0;if(r=null==r?1:+r,1===t)return()=>-Math.log1p(-n())*r;var i=(t<1?t+1:t)-1/3,o=1/(3*Math.sqrt(i)),a=t<1?()=>Math.pow(n(),1/t):()=>1;return function(){do{do{var t=e(),u=1+o*t}while(u<=0);u*=u*u;var c=1-n()}while(c>=1-.0331*t*t*t*t&&Math.log(c)>=.5*t*t+i*(1-u+Math.log(u)));return i*u*a()*r}}return r.source=t,r}(Gp),og=function t(n){var e=ig.source(n);function r(t,n){var r=e(t),i=e(n);return function(){var t=r();return 0===t?0:t/(t+i())}}return r.source=t,r}(Gp),ag=function t(n){var e=rg.source(n),r=og.source(n);function i(t,n){return t=+t,(n=+n)>=1?()=>t:n<=0?()=>0:function(){for(var i=0,o=t,a=n;o*a>16&&o*(1-a)>16;){var u=Math.floor((o+1)*a),c=r(u,o-u+1)();c<=a?(i+=u,o-=u,a=(a-c)/(1-c)):(o=u-1,a/=c)}for(var f=a<.5,s=e(f?a:1-a),l=s(),h=0;l<=o;++h)l+=s();return i+(f?h:o-h)}}return i.source=t,i}(Gp),ug=function t(n){function e(t,e,r){var i;return 0==(t=+t)?i=t=>-Math.log(t):(t=1/t,i=n=>Math.pow(n,t)),e=null==e?0:+e,r=null==r?1:+r,function(){return e+r*i(-Math.log1p(-n()))}}return e.source=t,e}(Gp),cg=function t(n){function e(t,e){return t=null==t?0:+t,e=null==e?1:+e,function(){return t+e*Math.tan(Math.PI*n())}}return e.source=t,e}(Gp),fg=function t(n){function e(t,e){return t=null==t?0:+t,e=null==e?1:+e,function(){var r=n();return t+e*Math.log(r/(1-r))}}return e.source=t,e}(Gp),sg=function t(n){var e=ig.source(n),r=ag.source(n);function i(t){return function(){for(var i=0,o=t;o>16;){var a=Math.floor(.875*o),u=e(a)();if(u>o)return i+r(a-1,o/u)();i+=a,o-=u}for(var c=-Math.log1p(-n()),f=0;c<=o;++f)c-=Math.log1p(-n());return i+f}}return i.source=t,i}(Gp);const lg=1/4294967296;function hg(t,n){switch(arguments.length){case 0:break;case 1:this.range(t);break;default:this.range(n).domain(t)}return this}function dg(t,n){switch(arguments.length){case 0:break;case 1:"function"==typeof t?this.interpolator(t):this.range(t);break;default:this.domain(t),"function"==typeof n?this.interpolator(n):this.range(n)}return this}const pg=Symbol("implicit");function gg(){var t=new InternMap,n=[],e=[],r=pg;function i(i){let o=t.get(i);if(void 0===o){if(r!==pg)return r;t.set(i,o=n.push(i)-1)}return e[o%e.length]}return i.domain=function(e){if(!arguments.length)return n.slice();n=[],t=new InternMap;for(const r of e)t.has(r)||t.set(r,n.push(r)-1);return i},i.range=function(t){return arguments.length?(e=Array.from(t),i):e.slice()},i.unknown=function(t){return arguments.length?(r=t,i):r},i.copy=function(){return gg(n,e).unknown(r)},hg.apply(i,arguments),i}function yg(){var t,n,e=gg().unknown(void 0),r=e.domain,i=e.range,o=0,a=1,u=!1,c=0,f=0,s=.5;function l(){var e=r().length,l=an&&(e=t,t=n,n=e),function(e){return Math.max(t,Math.min(n,e))}}(a[0],a[t-1])),r=t>2?Mg:wg,i=o=null,l}function l(n){return null==n||isNaN(n=+n)?e:(i||(i=r(a.map(t),u,c)))(t(f(n)))}return l.invert=function(e){return f(n((o||(o=r(u,a.map(t),Yr)))(e)))},l.domain=function(t){return arguments.length?(a=Array.from(t,_g),s()):a.slice()},l.range=function(t){return arguments.length?(u=Array.from(t),s()):u.slice()},l.rangeRound=function(t){return u=Array.from(t),c=Vr,s()},l.clamp=function(t){return arguments.length?(f=!!t||mg,s()):f!==mg},l.interpolate=function(t){return arguments.length?(c=t,s()):c},l.unknown=function(t){return arguments.length?(e=t,l):e},function(e,r){return t=e,n=r,s()}}function Sg(){return Ag()(mg,mg)}function Eg(n,e,r,i){var o,a=W(n,e,r);switch((i=Jc(null==i?",f":i)).type){case"s":var u=Math.max(Math.abs(n),Math.abs(e));return null!=i.precision||isNaN(o=lf(a,u))||(i.precision=o),t.formatPrefix(i,u);case"":case"e":case"g":case"p":case"r":null!=i.precision||isNaN(o=hf(a,Math.max(Math.abs(n),Math.abs(e))))||(i.precision=o-("e"===i.type));break;case"f":case"%":null!=i.precision||isNaN(o=sf(a))||(i.precision=o-2*("%"===i.type))}return t.format(i)}function Ng(t){var n=t.domain;return t.ticks=function(t){var e=n();return G(e[0],e[e.length-1],null==t?10:t)},t.tickFormat=function(t,e){var r=n();return Eg(r[0],r[r.length-1],null==t?10:t,e)},t.nice=function(e){null==e&&(e=10);var r,i,o=n(),a=0,u=o.length-1,c=o[a],f=o[u],s=10;for(f0;){if((i=V(c,f,e))===r)return o[a]=c,o[u]=f,n(o);if(i>0)c=Math.floor(c/i)*i,f=Math.ceil(f/i)*i;else{if(!(i<0))break;c=Math.ceil(c*i)/i,f=Math.floor(f*i)/i}r=i}return t},t}function kg(t,n){var e,r=0,i=(t=t.slice()).length-1,o=t[r],a=t[i];return a-t(-n,e)}function Fg(n){const e=n(Cg,Pg),r=e.domain;let i,o,a=10;function u(){return i=function(t){return t===Math.E?Math.log:10===t&&Math.log10||2===t&&Math.log2||(t=Math.log(t),n=>Math.log(n)/t)}(a),o=function(t){return 10===t?Dg:t===Math.E?Math.exp:n=>Math.pow(t,n)}(a),r()[0]<0?(i=Rg(i),o=Rg(o),n(zg,$g)):n(Cg,Pg),e}return e.base=function(t){return arguments.length?(a=+t,u()):a},e.domain=function(t){return arguments.length?(r(t),u()):r()},e.ticks=t=>{const n=r();let e=n[0],u=n[n.length-1];const c=u0){for(;l<=h;++l)for(f=1;fu)break;p.push(s)}}else for(;l<=h;++l)for(f=a-1;f>=1;--f)if(s=l>0?f/o(-l):f*o(l),!(su)break;p.push(s)}2*p.length{if(null==n&&(n=10),null==r&&(r=10===a?"s":","),"function"!=typeof r&&(a%1||null!=(r=Jc(r)).precision||(r.trim=!0),r=t.format(r)),n===1/0)return r;const u=Math.max(1,a*n/e.ticks().length);return t=>{let n=t/o(Math.round(i(t)));return n*ar(kg(r(),{floor:t=>o(Math.floor(i(t))),ceil:t=>o(Math.ceil(i(t)))})),e}function qg(t){return function(n){return Math.sign(n)*Math.log1p(Math.abs(n/t))}}function Ug(t){return function(n){return Math.sign(n)*Math.expm1(Math.abs(n))*t}}function Ig(t){var n=1,e=t(qg(n),Ug(n));return e.constant=function(e){return arguments.length?t(qg(n=+e),Ug(n)):n},Ng(e)}function Og(t){return function(n){return n<0?-Math.pow(-n,t):Math.pow(n,t)}}function Bg(t){return t<0?-Math.sqrt(-t):Math.sqrt(t)}function Yg(t){return t<0?-t*t:t*t}function Lg(t){var n=t(mg,mg),e=1;return n.exponent=function(n){return arguments.length?1===(e=+n)?t(mg,mg):.5===e?t(Bg,Yg):t(Og(e),Og(1/e)):e},Ng(n)}function jg(){var t=Lg(Ag());return t.copy=function(){return Tg(t,jg()).exponent(t.exponent())},hg.apply(t,arguments),t}function Hg(t){return Math.sign(t)*t*t}const Xg=new Date,Gg=new Date;function Vg(t,n,e,r){function i(n){return t(n=0===arguments.length?new Date:new Date(+n)),n}return i.floor=n=>(t(n=new Date(+n)),n),i.ceil=e=>(t(e=new Date(e-1)),n(e,1),t(e),e),i.round=t=>{const n=i(t),e=i.ceil(t);return t-n(n(t=new Date(+t),null==e?1:Math.floor(e)),t),i.range=(e,r,o)=>{const a=[];if(e=i.ceil(e),o=null==o?1:Math.floor(o),!(e0))return a;let u;do{a.push(u=new Date(+e)),n(e,o),t(e)}while(uVg((n=>{if(n>=n)for(;t(n),!e(n);)n.setTime(n-1)}),((t,r)=>{if(t>=t)if(r<0)for(;++r<=0;)for(;n(t,-1),!e(t););else for(;--r>=0;)for(;n(t,1),!e(t););})),e&&(i.count=(n,r)=>(Xg.setTime(+n),Gg.setTime(+r),t(Xg),t(Gg),Math.floor(e(Xg,Gg))),i.every=t=>(t=Math.floor(t),isFinite(t)&&t>0?t>1?i.filter(r?n=>r(n)%t==0:n=>i.count(0,n)%t==0):i:null)),i}const Wg=Vg((()=>{}),((t,n)=>{t.setTime(+t+n)}),((t,n)=>n-t));Wg.every=t=>(t=Math.floor(t),isFinite(t)&&t>0?t>1?Vg((n=>{n.setTime(Math.floor(n/t)*t)}),((n,e)=>{n.setTime(+n+e*t)}),((n,e)=>(e-n)/t)):Wg:null);const Zg=Wg.range,Kg=1e3,Qg=6e4,Jg=36e5,ty=864e5,ny=6048e5,ey=2592e6,ry=31536e6,iy=Vg((t=>{t.setTime(t-t.getMilliseconds())}),((t,n)=>{t.setTime(+t+n*Kg)}),((t,n)=>(n-t)/Kg),(t=>t.getUTCSeconds())),oy=iy.range,ay=Vg((t=>{t.setTime(t-t.getMilliseconds()-t.getSeconds()*Kg)}),((t,n)=>{t.setTime(+t+n*Qg)}),((t,n)=>(n-t)/Qg),(t=>t.getMinutes())),uy=ay.range,cy=Vg((t=>{t.setUTCSeconds(0,0)}),((t,n)=>{t.setTime(+t+n*Qg)}),((t,n)=>(n-t)/Qg),(t=>t.getUTCMinutes())),fy=cy.range,sy=Vg((t=>{t.setTime(t-t.getMilliseconds()-t.getSeconds()*Kg-t.getMinutes()*Qg)}),((t,n)=>{t.setTime(+t+n*Jg)}),((t,n)=>(n-t)/Jg),(t=>t.getHours())),ly=sy.range,hy=Vg((t=>{t.setUTCMinutes(0,0,0)}),((t,n)=>{t.setTime(+t+n*Jg)}),((t,n)=>(n-t)/Jg),(t=>t.getUTCHours())),dy=hy.range,py=Vg((t=>t.setHours(0,0,0,0)),((t,n)=>t.setDate(t.getDate()+n)),((t,n)=>(n-t-(n.getTimezoneOffset()-t.getTimezoneOffset())*Qg)/ty),(t=>t.getDate()-1)),gy=py.range,yy=Vg((t=>{t.setUTCHours(0,0,0,0)}),((t,n)=>{t.setUTCDate(t.getUTCDate()+n)}),((t,n)=>(n-t)/ty),(t=>t.getUTCDate()-1)),vy=yy.range,_y=Vg((t=>{t.setUTCHours(0,0,0,0)}),((t,n)=>{t.setUTCDate(t.getUTCDate()+n)}),((t,n)=>(n-t)/ty),(t=>Math.floor(t/ty))),by=_y.range;function my(t){return Vg((n=>{n.setDate(n.getDate()-(n.getDay()+7-t)%7),n.setHours(0,0,0,0)}),((t,n)=>{t.setDate(t.getDate()+7*n)}),((t,n)=>(n-t-(n.getTimezoneOffset()-t.getTimezoneOffset())*Qg)/ny))}const xy=my(0),wy=my(1),My=my(2),Ty=my(3),Ay=my(4),Sy=my(5),Ey=my(6),Ny=xy.range,ky=wy.range,Cy=My.range,Py=Ty.range,zy=Ay.range,$y=Sy.range,Dy=Ey.range;function Ry(t){return Vg((n=>{n.setUTCDate(n.getUTCDate()-(n.getUTCDay()+7-t)%7),n.setUTCHours(0,0,0,0)}),((t,n)=>{t.setUTCDate(t.getUTCDate()+7*n)}),((t,n)=>(n-t)/ny))}const Fy=Ry(0),qy=Ry(1),Uy=Ry(2),Iy=Ry(3),Oy=Ry(4),By=Ry(5),Yy=Ry(6),Ly=Fy.range,jy=qy.range,Hy=Uy.range,Xy=Iy.range,Gy=Oy.range,Vy=By.range,Wy=Yy.range,Zy=Vg((t=>{t.setDate(1),t.setHours(0,0,0,0)}),((t,n)=>{t.setMonth(t.getMonth()+n)}),((t,n)=>n.getMonth()-t.getMonth()+12*(n.getFullYear()-t.getFullYear())),(t=>t.getMonth())),Ky=Zy.range,Qy=Vg((t=>{t.setUTCDate(1),t.setUTCHours(0,0,0,0)}),((t,n)=>{t.setUTCMonth(t.getUTCMonth()+n)}),((t,n)=>n.getUTCMonth()-t.getUTCMonth()+12*(n.getUTCFullYear()-t.getUTCFullYear())),(t=>t.getUTCMonth())),Jy=Qy.range,tv=Vg((t=>{t.setMonth(0,1),t.setHours(0,0,0,0)}),((t,n)=>{t.setFullYear(t.getFullYear()+n)}),((t,n)=>n.getFullYear()-t.getFullYear()),(t=>t.getFullYear()));tv.every=t=>isFinite(t=Math.floor(t))&&t>0?Vg((n=>{n.setFullYear(Math.floor(n.getFullYear()/t)*t),n.setMonth(0,1),n.setHours(0,0,0,0)}),((n,e)=>{n.setFullYear(n.getFullYear()+e*t)})):null;const nv=tv.range,ev=Vg((t=>{t.setUTCMonth(0,1),t.setUTCHours(0,0,0,0)}),((t,n)=>{t.setUTCFullYear(t.getUTCFullYear()+n)}),((t,n)=>n.getUTCFullYear()-t.getUTCFullYear()),(t=>t.getUTCFullYear()));ev.every=t=>isFinite(t=Math.floor(t))&&t>0?Vg((n=>{n.setUTCFullYear(Math.floor(n.getUTCFullYear()/t)*t),n.setUTCMonth(0,1),n.setUTCHours(0,0,0,0)}),((n,e)=>{n.setUTCFullYear(n.getUTCFullYear()+e*t)})):null;const rv=ev.range;function iv(t,n,e,i,o,a){const u=[[iy,1,Kg],[iy,5,5e3],[iy,15,15e3],[iy,30,3e4],[a,1,Qg],[a,5,3e5],[a,15,9e5],[a,30,18e5],[o,1,Jg],[o,3,108e5],[o,6,216e5],[o,12,432e5],[i,1,ty],[i,2,1728e5],[e,1,ny],[n,1,ey],[n,3,7776e6],[t,1,ry]];function c(n,e,i){const o=Math.abs(e-n)/i,a=r((([,,t])=>t)).right(u,o);if(a===u.length)return t.every(W(n/ry,e/ry,i));if(0===a)return Wg.every(Math.max(W(n,e,i),1));const[c,f]=u[o/u[a-1][2]=12)]},q:function(t){return 1+~~(t.getMonth()/3)},Q:k_,s:C_,S:Zv,u:Kv,U:Qv,V:t_,w:n_,W:e_,x:null,X:null,y:r_,Y:o_,Z:u_,"%":N_},m={a:function(t){return a[t.getUTCDay()]},A:function(t){return o[t.getUTCDay()]},b:function(t){return c[t.getUTCMonth()]},B:function(t){return u[t.getUTCMonth()]},c:null,d:c_,e:c_,f:d_,g:T_,G:S_,H:f_,I:s_,j:l_,L:h_,m:p_,M:g_,p:function(t){return i[+(t.getUTCHours()>=12)]},q:function(t){return 1+~~(t.getUTCMonth()/3)},Q:k_,s:C_,S:y_,u:v_,U:__,V:m_,w:x_,W:w_,x:null,X:null,y:M_,Y:A_,Z:E_,"%":N_},x={a:function(t,n,e){var r=d.exec(n.slice(e));return r?(t.w=p.get(r[0].toLowerCase()),e+r[0].length):-1},A:function(t,n,e){var r=l.exec(n.slice(e));return r?(t.w=h.get(r[0].toLowerCase()),e+r[0].length):-1},b:function(t,n,e){var r=v.exec(n.slice(e));return r?(t.m=_.get(r[0].toLowerCase()),e+r[0].length):-1},B:function(t,n,e){var r=g.exec(n.slice(e));return r?(t.m=y.get(r[0].toLowerCase()),e+r[0].length):-1},c:function(t,e,r){return T(t,n,e,r)},d:zv,e:zv,f:Uv,g:Nv,G:Ev,H:Dv,I:Dv,j:$v,L:qv,m:Pv,M:Rv,p:function(t,n,e){var r=f.exec(n.slice(e));return r?(t.p=s.get(r[0].toLowerCase()),e+r[0].length):-1},q:Cv,Q:Ov,s:Bv,S:Fv,u:Mv,U:Tv,V:Av,w:wv,W:Sv,x:function(t,n,r){return T(t,e,n,r)},X:function(t,n,e){return T(t,r,n,e)},y:Nv,Y:Ev,Z:kv,"%":Iv};function w(t,n){return function(e){var r,i,o,a=[],u=-1,c=0,f=t.length;for(e instanceof Date||(e=new Date(+e));++u53)return null;"w"in o||(o.w=1),"Z"in o?(i=(r=sv(lv(o.y,0,1))).getUTCDay(),r=i>4||0===i?qy.ceil(r):qy(r),r=yy.offset(r,7*(o.V-1)),o.y=r.getUTCFullYear(),o.m=r.getUTCMonth(),o.d=r.getUTCDate()+(o.w+6)%7):(i=(r=fv(lv(o.y,0,1))).getDay(),r=i>4||0===i?wy.ceil(r):wy(r),r=py.offset(r,7*(o.V-1)),o.y=r.getFullYear(),o.m=r.getMonth(),o.d=r.getDate()+(o.w+6)%7)}else("W"in o||"U"in o)&&("w"in o||(o.w="u"in o?o.u%7:"W"in o?1:0),i="Z"in o?sv(lv(o.y,0,1)).getUTCDay():fv(lv(o.y,0,1)).getDay(),o.m=0,o.d="W"in o?(o.w+6)%7+7*o.W-(i+5)%7:o.w+7*o.U-(i+6)%7);return"Z"in o?(o.H+=o.Z/100|0,o.M+=o.Z%100,sv(o)):fv(o)}}function T(t,n,e,r){for(var i,o,a=0,u=n.length,c=e.length;a=c)return-1;if(37===(i=n.charCodeAt(a++))){if(i=n.charAt(a++),!(o=x[i in pv?n.charAt(a++):i])||(r=o(t,e,r))<0)return-1}else if(i!=e.charCodeAt(r++))return-1}return r}return b.x=w(e,b),b.X=w(r,b),b.c=w(n,b),m.x=w(e,m),m.X=w(r,m),m.c=w(n,m),{format:function(t){var n=w(t+="",b);return n.toString=function(){return t},n},parse:function(t){var n=M(t+="",!1);return n.toString=function(){return t},n},utcFormat:function(t){var n=w(t+="",m);return n.toString=function(){return t},n},utcParse:function(t){var n=M(t+="",!0);return n.toString=function(){return t},n}}}var dv,pv={"-":"",_:" ",0:"0"},gv=/^\s*\d+/,yv=/^%/,vv=/[\\^$*+?|[\]().{}]/g;function _v(t,n,e){var r=t<0?"-":"",i=(r?-t:t)+"",o=i.length;return r+(o[t.toLowerCase(),n])))}function wv(t,n,e){var r=gv.exec(n.slice(e,e+1));return r?(t.w=+r[0],e+r[0].length):-1}function Mv(t,n,e){var r=gv.exec(n.slice(e,e+1));return r?(t.u=+r[0],e+r[0].length):-1}function Tv(t,n,e){var r=gv.exec(n.slice(e,e+2));return r?(t.U=+r[0],e+r[0].length):-1}function Av(t,n,e){var r=gv.exec(n.slice(e,e+2));return r?(t.V=+r[0],e+r[0].length):-1}function Sv(t,n,e){var r=gv.exec(n.slice(e,e+2));return r?(t.W=+r[0],e+r[0].length):-1}function Ev(t,n,e){var r=gv.exec(n.slice(e,e+4));return r?(t.y=+r[0],e+r[0].length):-1}function Nv(t,n,e){var r=gv.exec(n.slice(e,e+2));return r?(t.y=+r[0]+(+r[0]>68?1900:2e3),e+r[0].length):-1}function kv(t,n,e){var r=/^(Z)|([+-]\d\d)(?::?(\d\d))?/.exec(n.slice(e,e+6));return r?(t.Z=r[1]?0:-(r[2]+(r[3]||"00")),e+r[0].length):-1}function Cv(t,n,e){var r=gv.exec(n.slice(e,e+1));return r?(t.q=3*r[0]-3,e+r[0].length):-1}function Pv(t,n,e){var r=gv.exec(n.slice(e,e+2));return r?(t.m=r[0]-1,e+r[0].length):-1}function zv(t,n,e){var r=gv.exec(n.slice(e,e+2));return r?(t.d=+r[0],e+r[0].length):-1}function $v(t,n,e){var r=gv.exec(n.slice(e,e+3));return r?(t.m=0,t.d=+r[0],e+r[0].length):-1}function Dv(t,n,e){var r=gv.exec(n.slice(e,e+2));return r?(t.H=+r[0],e+r[0].length):-1}function Rv(t,n,e){var r=gv.exec(n.slice(e,e+2));return r?(t.M=+r[0],e+r[0].length):-1}function Fv(t,n,e){var r=gv.exec(n.slice(e,e+2));return r?(t.S=+r[0],e+r[0].length):-1}function qv(t,n,e){var r=gv.exec(n.slice(e,e+3));return r?(t.L=+r[0],e+r[0].length):-1}function Uv(t,n,e){var r=gv.exec(n.slice(e,e+6));return r?(t.L=Math.floor(r[0]/1e3),e+r[0].length):-1}function Iv(t,n,e){var r=yv.exec(n.slice(e,e+1));return r?e+r[0].length:-1}function Ov(t,n,e){var r=gv.exec(n.slice(e));return r?(t.Q=+r[0],e+r[0].length):-1}function Bv(t,n,e){var r=gv.exec(n.slice(e));return r?(t.s=+r[0],e+r[0].length):-1}function Yv(t,n){return _v(t.getDate(),n,2)}function Lv(t,n){return _v(t.getHours(),n,2)}function jv(t,n){return _v(t.getHours()%12||12,n,2)}function Hv(t,n){return _v(1+py.count(tv(t),t),n,3)}function Xv(t,n){return _v(t.getMilliseconds(),n,3)}function Gv(t,n){return Xv(t,n)+"000"}function Vv(t,n){return _v(t.getMonth()+1,n,2)}function Wv(t,n){return _v(t.getMinutes(),n,2)}function Zv(t,n){return _v(t.getSeconds(),n,2)}function Kv(t){var n=t.getDay();return 0===n?7:n}function Qv(t,n){return _v(xy.count(tv(t)-1,t),n,2)}function Jv(t){var n=t.getDay();return n>=4||0===n?Ay(t):Ay.ceil(t)}function t_(t,n){return t=Jv(t),_v(Ay.count(tv(t),t)+(4===tv(t).getDay()),n,2)}function n_(t){return t.getDay()}function e_(t,n){return _v(wy.count(tv(t)-1,t),n,2)}function r_(t,n){return _v(t.getFullYear()%100,n,2)}function i_(t,n){return _v((t=Jv(t)).getFullYear()%100,n,2)}function o_(t,n){return _v(t.getFullYear()%1e4,n,4)}function a_(t,n){var e=t.getDay();return _v((t=e>=4||0===e?Ay(t):Ay.ceil(t)).getFullYear()%1e4,n,4)}function u_(t){var n=t.getTimezoneOffset();return(n>0?"-":(n*=-1,"+"))+_v(n/60|0,"0",2)+_v(n%60,"0",2)}function c_(t,n){return _v(t.getUTCDate(),n,2)}function f_(t,n){return _v(t.getUTCHours(),n,2)}function s_(t,n){return _v(t.getUTCHours()%12||12,n,2)}function l_(t,n){return _v(1+yy.count(ev(t),t),n,3)}function h_(t,n){return _v(t.getUTCMilliseconds(),n,3)}function d_(t,n){return h_(t,n)+"000"}function p_(t,n){return _v(t.getUTCMonth()+1,n,2)}function g_(t,n){return _v(t.getUTCMinutes(),n,2)}function y_(t,n){return _v(t.getUTCSeconds(),n,2)}function v_(t){var n=t.getUTCDay();return 0===n?7:n}function __(t,n){return _v(Fy.count(ev(t)-1,t),n,2)}function b_(t){var n=t.getUTCDay();return n>=4||0===n?Oy(t):Oy.ceil(t)}function m_(t,n){return t=b_(t),_v(Oy.count(ev(t),t)+(4===ev(t).getUTCDay()),n,2)}function x_(t){return t.getUTCDay()}function w_(t,n){return _v(qy.count(ev(t)-1,t),n,2)}function M_(t,n){return _v(t.getUTCFullYear()%100,n,2)}function T_(t,n){return _v((t=b_(t)).getUTCFullYear()%100,n,2)}function A_(t,n){return _v(t.getUTCFullYear()%1e4,n,4)}function S_(t,n){var e=t.getUTCDay();return _v((t=e>=4||0===e?Oy(t):Oy.ceil(t)).getUTCFullYear()%1e4,n,4)}function E_(){return"+0000"}function N_(){return"%"}function k_(t){return+t}function C_(t){return Math.floor(+t/1e3)}function P_(n){return dv=hv(n),t.timeFormat=dv.format,t.timeParse=dv.parse,t.utcFormat=dv.utcFormat,t.utcParse=dv.utcParse,dv}t.timeFormat=void 0,t.timeParse=void 0,t.utcFormat=void 0,t.utcParse=void 0,P_({dateTime:"%x, %X",date:"%-m/%-d/%Y",time:"%-I:%M:%S %p",periods:["AM","PM"],days:["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"],shortDays:["Sun","Mon","Tue","Wed","Thu","Fri","Sat"],months:["January","February","March","April","May","June","July","August","September","October","November","December"],shortMonths:["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"]});var z_="%Y-%m-%dT%H:%M:%S.%LZ";var $_=Date.prototype.toISOString?function(t){return t.toISOString()}:t.utcFormat(z_),D_=$_;var R_=+new Date("2000-01-01T00:00:00.000Z")?function(t){var n=new Date(t);return isNaN(n)?null:n}:t.utcParse(z_),F_=R_;function q_(t){return new Date(t)}function U_(t){return t instanceof Date?+t:+new Date(+t)}function I_(t,n,e,r,i,o,a,u,c,f){var s=Sg(),l=s.invert,h=s.domain,d=f(".%L"),p=f(":%S"),g=f("%I:%M"),y=f("%I %p"),v=f("%a %d"),_=f("%b %d"),b=f("%B"),m=f("%Y");function x(t){return(c(t)Fr(t[t.length-1]),ib=new Array(3).concat("d8b365f5f5f55ab4ac","a6611adfc27d80cdc1018571","a6611adfc27df5f5f580cdc1018571","8c510ad8b365f6e8c3c7eae55ab4ac01665e","8c510ad8b365f6e8c3f5f5f5c7eae55ab4ac01665e","8c510abf812ddfc27df6e8c3c7eae580cdc135978f01665e","8c510abf812ddfc27df6e8c3f5f5f5c7eae580cdc135978f01665e","5430058c510abf812ddfc27df6e8c3c7eae580cdc135978f01665e003c30","5430058c510abf812ddfc27df6e8c3f5f5f5c7eae580cdc135978f01665e003c30").map(H_),ob=rb(ib),ab=new Array(3).concat("af8dc3f7f7f77fbf7b","7b3294c2a5cfa6dba0008837","7b3294c2a5cff7f7f7a6dba0008837","762a83af8dc3e7d4e8d9f0d37fbf7b1b7837","762a83af8dc3e7d4e8f7f7f7d9f0d37fbf7b1b7837","762a839970abc2a5cfe7d4e8d9f0d3a6dba05aae611b7837","762a839970abc2a5cfe7d4e8f7f7f7d9f0d3a6dba05aae611b7837","40004b762a839970abc2a5cfe7d4e8d9f0d3a6dba05aae611b783700441b","40004b762a839970abc2a5cfe7d4e8f7f7f7d9f0d3a6dba05aae611b783700441b").map(H_),ub=rb(ab),cb=new Array(3).concat("e9a3c9f7f7f7a1d76a","d01c8bf1b6dab8e1864dac26","d01c8bf1b6daf7f7f7b8e1864dac26","c51b7de9a3c9fde0efe6f5d0a1d76a4d9221","c51b7de9a3c9fde0eff7f7f7e6f5d0a1d76a4d9221","c51b7dde77aef1b6dafde0efe6f5d0b8e1867fbc414d9221","c51b7dde77aef1b6dafde0eff7f7f7e6f5d0b8e1867fbc414d9221","8e0152c51b7dde77aef1b6dafde0efe6f5d0b8e1867fbc414d9221276419","8e0152c51b7dde77aef1b6dafde0eff7f7f7e6f5d0b8e1867fbc414d9221276419").map(H_),fb=rb(cb),sb=new Array(3).concat("998ec3f7f7f7f1a340","5e3c99b2abd2fdb863e66101","5e3c99b2abd2f7f7f7fdb863e66101","542788998ec3d8daebfee0b6f1a340b35806","542788998ec3d8daebf7f7f7fee0b6f1a340b35806","5427888073acb2abd2d8daebfee0b6fdb863e08214b35806","5427888073acb2abd2d8daebf7f7f7fee0b6fdb863e08214b35806","2d004b5427888073acb2abd2d8daebfee0b6fdb863e08214b358067f3b08","2d004b5427888073acb2abd2d8daebf7f7f7fee0b6fdb863e08214b358067f3b08").map(H_),lb=rb(sb),hb=new Array(3).concat("ef8a62f7f7f767a9cf","ca0020f4a58292c5de0571b0","ca0020f4a582f7f7f792c5de0571b0","b2182bef8a62fddbc7d1e5f067a9cf2166ac","b2182bef8a62fddbc7f7f7f7d1e5f067a9cf2166ac","b2182bd6604df4a582fddbc7d1e5f092c5de4393c32166ac","b2182bd6604df4a582fddbc7f7f7f7d1e5f092c5de4393c32166ac","67001fb2182bd6604df4a582fddbc7d1e5f092c5de4393c32166ac053061","67001fb2182bd6604df4a582fddbc7f7f7f7d1e5f092c5de4393c32166ac053061").map(H_),db=rb(hb),pb=new Array(3).concat("ef8a62ffffff999999","ca0020f4a582bababa404040","ca0020f4a582ffffffbababa404040","b2182bef8a62fddbc7e0e0e09999994d4d4d","b2182bef8a62fddbc7ffffffe0e0e09999994d4d4d","b2182bd6604df4a582fddbc7e0e0e0bababa8787874d4d4d","b2182bd6604df4a582fddbc7ffffffe0e0e0bababa8787874d4d4d","67001fb2182bd6604df4a582fddbc7e0e0e0bababa8787874d4d4d1a1a1a","67001fb2182bd6604df4a582fddbc7ffffffe0e0e0bababa8787874d4d4d1a1a1a").map(H_),gb=rb(pb),yb=new Array(3).concat("fc8d59ffffbf91bfdb","d7191cfdae61abd9e92c7bb6","d7191cfdae61ffffbfabd9e92c7bb6","d73027fc8d59fee090e0f3f891bfdb4575b4","d73027fc8d59fee090ffffbfe0f3f891bfdb4575b4","d73027f46d43fdae61fee090e0f3f8abd9e974add14575b4","d73027f46d43fdae61fee090ffffbfe0f3f8abd9e974add14575b4","a50026d73027f46d43fdae61fee090e0f3f8abd9e974add14575b4313695","a50026d73027f46d43fdae61fee090ffffbfe0f3f8abd9e974add14575b4313695").map(H_),vb=rb(yb),_b=new Array(3).concat("fc8d59ffffbf91cf60","d7191cfdae61a6d96a1a9641","d7191cfdae61ffffbfa6d96a1a9641","d73027fc8d59fee08bd9ef8b91cf601a9850","d73027fc8d59fee08bffffbfd9ef8b91cf601a9850","d73027f46d43fdae61fee08bd9ef8ba6d96a66bd631a9850","d73027f46d43fdae61fee08bffffbfd9ef8ba6d96a66bd631a9850","a50026d73027f46d43fdae61fee08bd9ef8ba6d96a66bd631a9850006837","a50026d73027f46d43fdae61fee08bffffbfd9ef8ba6d96a66bd631a9850006837").map(H_),bb=rb(_b),mb=new Array(3).concat("fc8d59ffffbf99d594","d7191cfdae61abdda42b83ba","d7191cfdae61ffffbfabdda42b83ba","d53e4ffc8d59fee08be6f59899d5943288bd","d53e4ffc8d59fee08bffffbfe6f59899d5943288bd","d53e4ff46d43fdae61fee08be6f598abdda466c2a53288bd","d53e4ff46d43fdae61fee08bffffbfe6f598abdda466c2a53288bd","9e0142d53e4ff46d43fdae61fee08be6f598abdda466c2a53288bd5e4fa2","9e0142d53e4ff46d43fdae61fee08bffffbfe6f598abdda466c2a53288bd5e4fa2").map(H_),xb=rb(mb),wb=new Array(3).concat("e5f5f999d8c92ca25f","edf8fbb2e2e266c2a4238b45","edf8fbb2e2e266c2a42ca25f006d2c","edf8fbccece699d8c966c2a42ca25f006d2c","edf8fbccece699d8c966c2a441ae76238b45005824","f7fcfde5f5f9ccece699d8c966c2a441ae76238b45005824","f7fcfde5f5f9ccece699d8c966c2a441ae76238b45006d2c00441b").map(H_),Mb=rb(wb),Tb=new Array(3).concat("e0ecf49ebcda8856a7","edf8fbb3cde38c96c688419d","edf8fbb3cde38c96c68856a7810f7c","edf8fbbfd3e69ebcda8c96c68856a7810f7c","edf8fbbfd3e69ebcda8c96c68c6bb188419d6e016b","f7fcfde0ecf4bfd3e69ebcda8c96c68c6bb188419d6e016b","f7fcfde0ecf4bfd3e69ebcda8c96c68c6bb188419d810f7c4d004b").map(H_),Ab=rb(Tb),Sb=new Array(3).concat("e0f3dba8ddb543a2ca","f0f9e8bae4bc7bccc42b8cbe","f0f9e8bae4bc7bccc443a2ca0868ac","f0f9e8ccebc5a8ddb57bccc443a2ca0868ac","f0f9e8ccebc5a8ddb57bccc44eb3d32b8cbe08589e","f7fcf0e0f3dbccebc5a8ddb57bccc44eb3d32b8cbe08589e","f7fcf0e0f3dbccebc5a8ddb57bccc44eb3d32b8cbe0868ac084081").map(H_),Eb=rb(Sb),Nb=new Array(3).concat("fee8c8fdbb84e34a33","fef0d9fdcc8afc8d59d7301f","fef0d9fdcc8afc8d59e34a33b30000","fef0d9fdd49efdbb84fc8d59e34a33b30000","fef0d9fdd49efdbb84fc8d59ef6548d7301f990000","fff7ecfee8c8fdd49efdbb84fc8d59ef6548d7301f990000","fff7ecfee8c8fdd49efdbb84fc8d59ef6548d7301fb300007f0000").map(H_),kb=rb(Nb),Cb=new Array(3).concat("ece2f0a6bddb1c9099","f6eff7bdc9e167a9cf02818a","f6eff7bdc9e167a9cf1c9099016c59","f6eff7d0d1e6a6bddb67a9cf1c9099016c59","f6eff7d0d1e6a6bddb67a9cf3690c002818a016450","fff7fbece2f0d0d1e6a6bddb67a9cf3690c002818a016450","fff7fbece2f0d0d1e6a6bddb67a9cf3690c002818a016c59014636").map(H_),Pb=rb(Cb),zb=new Array(3).concat("ece7f2a6bddb2b8cbe","f1eef6bdc9e174a9cf0570b0","f1eef6bdc9e174a9cf2b8cbe045a8d","f1eef6d0d1e6a6bddb74a9cf2b8cbe045a8d","f1eef6d0d1e6a6bddb74a9cf3690c00570b0034e7b","fff7fbece7f2d0d1e6a6bddb74a9cf3690c00570b0034e7b","fff7fbece7f2d0d1e6a6bddb74a9cf3690c00570b0045a8d023858").map(H_),$b=rb(zb),Db=new Array(3).concat("e7e1efc994c7dd1c77","f1eef6d7b5d8df65b0ce1256","f1eef6d7b5d8df65b0dd1c77980043","f1eef6d4b9dac994c7df65b0dd1c77980043","f1eef6d4b9dac994c7df65b0e7298ace125691003f","f7f4f9e7e1efd4b9dac994c7df65b0e7298ace125691003f","f7f4f9e7e1efd4b9dac994c7df65b0e7298ace125698004367001f").map(H_),Rb=rb(Db),Fb=new Array(3).concat("fde0ddfa9fb5c51b8a","feebe2fbb4b9f768a1ae017e","feebe2fbb4b9f768a1c51b8a7a0177","feebe2fcc5c0fa9fb5f768a1c51b8a7a0177","feebe2fcc5c0fa9fb5f768a1dd3497ae017e7a0177","fff7f3fde0ddfcc5c0fa9fb5f768a1dd3497ae017e7a0177","fff7f3fde0ddfcc5c0fa9fb5f768a1dd3497ae017e7a017749006a").map(H_),qb=rb(Fb),Ub=new Array(3).concat("edf8b17fcdbb2c7fb8","ffffcca1dab441b6c4225ea8","ffffcca1dab441b6c42c7fb8253494","ffffccc7e9b47fcdbb41b6c42c7fb8253494","ffffccc7e9b47fcdbb41b6c41d91c0225ea80c2c84","ffffd9edf8b1c7e9b47fcdbb41b6c41d91c0225ea80c2c84","ffffd9edf8b1c7e9b47fcdbb41b6c41d91c0225ea8253494081d58").map(H_),Ib=rb(Ub),Ob=new Array(3).concat("f7fcb9addd8e31a354","ffffccc2e69978c679238443","ffffccc2e69978c67931a354006837","ffffccd9f0a3addd8e78c67931a354006837","ffffccd9f0a3addd8e78c67941ab5d238443005a32","ffffe5f7fcb9d9f0a3addd8e78c67941ab5d238443005a32","ffffe5f7fcb9d9f0a3addd8e78c67941ab5d238443006837004529").map(H_),Bb=rb(Ob),Yb=new Array(3).concat("fff7bcfec44fd95f0e","ffffd4fed98efe9929cc4c02","ffffd4fed98efe9929d95f0e993404","ffffd4fee391fec44ffe9929d95f0e993404","ffffd4fee391fec44ffe9929ec7014cc4c028c2d04","ffffe5fff7bcfee391fec44ffe9929ec7014cc4c028c2d04","ffffe5fff7bcfee391fec44ffe9929ec7014cc4c02993404662506").map(H_),Lb=rb(Yb),jb=new Array(3).concat("ffeda0feb24cf03b20","ffffb2fecc5cfd8d3ce31a1c","ffffb2fecc5cfd8d3cf03b20bd0026","ffffb2fed976feb24cfd8d3cf03b20bd0026","ffffb2fed976feb24cfd8d3cfc4e2ae31a1cb10026","ffffccffeda0fed976feb24cfd8d3cfc4e2ae31a1cb10026","ffffccffeda0fed976feb24cfd8d3cfc4e2ae31a1cbd0026800026").map(H_),Hb=rb(jb),Xb=new Array(3).concat("deebf79ecae13182bd","eff3ffbdd7e76baed62171b5","eff3ffbdd7e76baed63182bd08519c","eff3ffc6dbef9ecae16baed63182bd08519c","eff3ffc6dbef9ecae16baed64292c62171b5084594","f7fbffdeebf7c6dbef9ecae16baed64292c62171b5084594","f7fbffdeebf7c6dbef9ecae16baed64292c62171b508519c08306b").map(H_),Gb=rb(Xb),Vb=new Array(3).concat("e5f5e0a1d99b31a354","edf8e9bae4b374c476238b45","edf8e9bae4b374c47631a354006d2c","edf8e9c7e9c0a1d99b74c47631a354006d2c","edf8e9c7e9c0a1d99b74c47641ab5d238b45005a32","f7fcf5e5f5e0c7e9c0a1d99b74c47641ab5d238b45005a32","f7fcf5e5f5e0c7e9c0a1d99b74c47641ab5d238b45006d2c00441b").map(H_),Wb=rb(Vb),Zb=new Array(3).concat("f0f0f0bdbdbd636363","f7f7f7cccccc969696525252","f7f7f7cccccc969696636363252525","f7f7f7d9d9d9bdbdbd969696636363252525","f7f7f7d9d9d9bdbdbd969696737373525252252525","fffffff0f0f0d9d9d9bdbdbd969696737373525252252525","fffffff0f0f0d9d9d9bdbdbd969696737373525252252525000000").map(H_),Kb=rb(Zb),Qb=new Array(3).concat("efedf5bcbddc756bb1","f2f0f7cbc9e29e9ac86a51a3","f2f0f7cbc9e29e9ac8756bb154278f","f2f0f7dadaebbcbddc9e9ac8756bb154278f","f2f0f7dadaebbcbddc9e9ac8807dba6a51a34a1486","fcfbfdefedf5dadaebbcbddc9e9ac8807dba6a51a34a1486","fcfbfdefedf5dadaebbcbddc9e9ac8807dba6a51a354278f3f007d").map(H_),Jb=rb(Qb),tm=new Array(3).concat("fee0d2fc9272de2d26","fee5d9fcae91fb6a4acb181d","fee5d9fcae91fb6a4ade2d26a50f15","fee5d9fcbba1fc9272fb6a4ade2d26a50f15","fee5d9fcbba1fc9272fb6a4aef3b2ccb181d99000d","fff5f0fee0d2fcbba1fc9272fb6a4aef3b2ccb181d99000d","fff5f0fee0d2fcbba1fc9272fb6a4aef3b2ccb181da50f1567000d").map(H_),nm=rb(tm),em=new Array(3).concat("fee6cefdae6be6550d","feeddefdbe85fd8d3cd94701","feeddefdbe85fd8d3ce6550da63603","feeddefdd0a2fdae6bfd8d3ce6550da63603","feeddefdd0a2fdae6bfd8d3cf16913d948018c2d04","fff5ebfee6cefdd0a2fdae6bfd8d3cf16913d948018c2d04","fff5ebfee6cefdd0a2fdae6bfd8d3cf16913d94801a636037f2704").map(H_),rm=rb(em);var im=hi(Tr(300,.5,0),Tr(-240,.5,1)),om=hi(Tr(-100,.75,.35),Tr(80,1.5,.8)),am=hi(Tr(260,.75,.35),Tr(80,1.5,.8)),um=Tr();var cm=Fe(),fm=Math.PI/3,sm=2*Math.PI/3;function lm(t){var n=t.length;return function(e){return t[Math.max(0,Math.min(n-1,Math.floor(e*n)))]}}var hm=lm(H_("44015444025645045745055946075a46085c460a5d460b5e470d60470e6147106347116447136548146748166848176948186a481a6c481b6d481c6e481d6f481f70482071482173482374482475482576482677482878482979472a7a472c7a472d7b472e7c472f7d46307e46327e46337f463480453581453781453882443983443a83443b84433d84433e85423f854240864241864142874144874045884046883f47883f48893e49893e4a893e4c8a3d4d8a3d4e8a3c4f8a3c508b3b518b3b528b3a538b3a548c39558c39568c38588c38598c375a8c375b8d365c8d365d8d355e8d355f8d34608d34618d33628d33638d32648e32658e31668e31678e31688e30698e306a8e2f6b8e2f6c8e2e6d8e2e6e8e2e6f8e2d708e2d718e2c718e2c728e2c738e2b748e2b758e2a768e2a778e2a788e29798e297a8e297b8e287c8e287d8e277e8e277f8e27808e26818e26828e26828e25838e25848e25858e24868e24878e23888e23898e238a8d228b8d228c8d228d8d218e8d218f8d21908d21918c20928c20928c20938c1f948c1f958b1f968b1f978b1f988b1f998a1f9a8a1e9b8a1e9c891e9d891f9e891f9f881fa0881fa1881fa1871fa28720a38620a48621a58521a68522a78522a88423a98324aa8325ab8225ac8226ad8127ad8128ae8029af7f2ab07f2cb17e2db27d2eb37c2fb47c31b57b32b67a34b67935b77937b87838b9773aba763bbb753dbc743fbc7340bd7242be7144bf7046c06f48c16e4ac16d4cc26c4ec36b50c46a52c56954c56856c66758c7655ac8645cc8635ec96260ca6063cb5f65cb5e67cc5c69cd5b6ccd5a6ece5870cf5773d05675d05477d1537ad1517cd2507fd34e81d34d84d44b86d54989d5488bd6468ed64590d74393d74195d84098d83e9bd93c9dd93ba0da39a2da37a5db36a8db34aadc32addc30b0dd2fb2dd2db5de2bb8de29bade28bddf26c0df25c2df23c5e021c8e020cae11fcde11dd0e11cd2e21bd5e21ad8e219dae319dde318dfe318e2e418e5e419e7e419eae51aece51befe51cf1e51df4e61ef6e620f8e621fbe723fde725")),dm=lm(H_("00000401000501010601010802010902020b02020d03030f03031204041405041606051806051a07061c08071e0907200a08220b09240c09260d0a290e0b2b100b2d110c2f120d31130d34140e36150e38160f3b180f3d19103f1a10421c10441d11471e114920114b21114e22115024125325125527125829115a2a115c2c115f2d11612f116331116533106734106936106b38106c390f6e3b0f703d0f713f0f72400f74420f75440f764510774710784910784a10794c117a4e117b4f127b51127c52137c54137d56147d57157e59157e5a167e5c167f5d177f5f187f601880621980641a80651a80671b80681c816a1c816b1d816d1d816e1e81701f81721f817320817521817621817822817922827b23827c23827e24828025828125818326818426818627818827818928818b29818c29818e2a81902a81912b81932b80942c80962c80982d80992d809b2e7f9c2e7f9e2f7fa02f7fa1307ea3307ea5317ea6317da8327daa337dab337cad347cae347bb0357bb2357bb3367ab5367ab73779b83779ba3878bc3978bd3977bf3a77c03a76c23b75c43c75c53c74c73d73c83e73ca3e72cc3f71cd4071cf4070d0416fd2426fd3436ed5446dd6456cd8456cd9466bdb476adc4869de4968df4a68e04c67e24d66e34e65e44f64e55064e75263e85362e95462ea5661eb5760ec5860ed5a5fee5b5eef5d5ef05f5ef1605df2625df2645cf3655cf4675cf4695cf56b5cf66c5cf66e5cf7705cf7725cf8745cf8765cf9785df9795df97b5dfa7d5efa7f5efa815ffb835ffb8560fb8761fc8961fc8a62fc8c63fc8e64fc9065fd9266fd9467fd9668fd9869fd9a6afd9b6bfe9d6cfe9f6dfea16efea36ffea571fea772fea973feaa74feac76feae77feb078feb27afeb47bfeb67cfeb77efeb97ffebb81febd82febf84fec185fec287fec488fec68afec88cfeca8dfecc8ffecd90fecf92fed194fed395fed597fed799fed89afdda9cfddc9efddea0fde0a1fde2a3fde3a5fde5a7fde7a9fde9aafdebacfcecaefceeb0fcf0b2fcf2b4fcf4b6fcf6b8fcf7b9fcf9bbfcfbbdfcfdbf")),pm=lm(H_("00000401000501010601010802010a02020c02020e03021004031204031405041706041907051b08051d09061f0a07220b07240c08260d08290e092b10092d110a30120a32140b34150b37160b39180c3c190c3e1b0c411c0c431e0c451f0c48210c4a230c4c240c4f260c51280b53290b552b0b572d0b592f0a5b310a5c320a5e340a5f3609613809623909633b09643d09653e0966400a67420a68440a68450a69470b6a490b6a4a0c6b4c0c6b4d0d6c4f0d6c510e6c520e6d540f6d550f6d57106e59106e5a116e5c126e5d126e5f136e61136e62146e64156e65156e67166e69166e6a176e6c186e6d186e6f196e71196e721a6e741a6e751b6e771c6d781c6d7a1d6d7c1d6d7d1e6d7f1e6c801f6c82206c84206b85216b87216b88226a8a226a8c23698d23698f24699025689225689326679526679727669827669a28659b29649d29649f2a63a02a63a22b62a32c61a52c60a62d60a82e5fa92e5eab2f5ead305dae305cb0315bb1325ab3325ab43359b63458b73557b93556ba3655bc3754bd3853bf3952c03a51c13a50c33b4fc43c4ec63d4dc73e4cc83f4bca404acb4149cc4248ce4347cf4446d04545d24644d34743d44842d54a41d74b3fd84c3ed94d3dda4e3cdb503bdd513ade5238df5337e05536e15635e25734e35933e45a31e55c30e65d2fe75e2ee8602de9612bea632aeb6429eb6628ec6726ed6925ee6a24ef6c23ef6e21f06f20f1711ff1731df2741cf3761bf37819f47918f57b17f57d15f67e14f68013f78212f78410f8850ff8870ef8890cf98b0bf98c0af98e09fa9008fa9207fa9407fb9606fb9706fb9906fb9b06fb9d07fc9f07fca108fca309fca50afca60cfca80dfcaa0ffcac11fcae12fcb014fcb216fcb418fbb61afbb81dfbba1ffbbc21fbbe23fac026fac228fac42afac62df9c72ff9c932f9cb35f8cd37f8cf3af7d13df7d340f6d543f6d746f5d949f5db4cf4dd4ff4df53f4e156f3e35af3e55df2e661f2e865f2ea69f1ec6df1ed71f1ef75f1f179f2f27df2f482f3f586f3f68af4f88ef5f992f6fa96f8fb9af9fc9dfafda1fcffa4")),gm=lm(H_("0d088710078813078916078a19068c1b068d1d068e20068f2206902406912605912805922a05932c05942e05952f059631059733059735049837049938049a3a049a3c049b3e049c3f049c41049d43039e44039e46039f48039f4903a04b03a14c02a14e02a25002a25102a35302a35502a45601a45801a45901a55b01a55c01a65e01a66001a66100a76300a76400a76600a76700a86900a86a00a86c00a86e00a86f00a87100a87201a87401a87501a87701a87801a87a02a87b02a87d03a87e03a88004a88104a78305a78405a78606a68707a68808a68a09a58b0aa58d0ba58e0ca48f0da4910ea3920fa39410a29511a19613a19814a099159f9a169f9c179e9d189d9e199da01a9ca11b9ba21d9aa31e9aa51f99a62098a72197a82296aa2395ab2494ac2694ad2793ae2892b02991b12a90b22b8fb32c8eb42e8db52f8cb6308bb7318ab83289ba3388bb3488bc3587bd3786be3885bf3984c03a83c13b82c23c81c33d80c43e7fc5407ec6417dc7427cc8437bc9447aca457acb4679cc4778cc4977cd4a76ce4b75cf4c74d04d73d14e72d24f71d35171d45270d5536fd5546ed6556dd7566cd8576bd9586ada5a6ada5b69db5c68dc5d67dd5e66de5f65de6164df6263e06363e16462e26561e26660e3685fe4695ee56a5de56b5de66c5ce76e5be76f5ae87059e97158e97257ea7457eb7556eb7655ec7754ed7953ed7a52ee7b51ef7c51ef7e50f07f4ff0804ef1814df1834cf2844bf3854bf3874af48849f48948f58b47f58c46f68d45f68f44f79044f79143f79342f89441f89540f9973ff9983ef99a3efa9b3dfa9c3cfa9e3bfb9f3afba139fba238fca338fca537fca636fca835fca934fdab33fdac33fdae32fdaf31fdb130fdb22ffdb42ffdb52efeb72dfeb82cfeba2cfebb2bfebd2afebe2afec029fdc229fdc328fdc527fdc627fdc827fdca26fdcb26fccd25fcce25fcd025fcd225fbd324fbd524fbd724fad824fada24f9dc24f9dd25f8df25f8e125f7e225f7e425f6e626f6e826f5e926f5eb27f4ed27f3ee27f3f027f2f227f1f426f1f525f0f724f0f921"));function ym(t){return function(){return t}}const vm=Math.abs,_m=Math.atan2,bm=Math.cos,mm=Math.max,xm=Math.min,wm=Math.sin,Mm=Math.sqrt,Tm=1e-12,Am=Math.PI,Sm=Am/2,Em=2*Am;function Nm(t){return t>=1?Sm:t<=-1?-Sm:Math.asin(t)}function km(t){let n=3;return t.digits=function(e){if(!arguments.length)return n;if(null==e)n=null;else{const t=Math.floor(e);if(!(t>=0))throw new RangeError(`invalid digits: ${e}`);n=t}return t},()=>new Ua(n)}function Cm(t){return t.innerRadius}function Pm(t){return t.outerRadius}function zm(t){return t.startAngle}function $m(t){return t.endAngle}function Dm(t){return t&&t.padAngle}function Rm(t,n,e,r,i,o,a){var u=t-e,c=n-r,f=(a?o:-o)/Mm(u*u+c*c),s=f*c,l=-f*u,h=t+s,d=n+l,p=e+s,g=r+l,y=(h+p)/2,v=(d+g)/2,_=p-h,b=g-d,m=_*_+b*b,x=i-o,w=h*g-p*d,M=(b<0?-1:1)*Mm(mm(0,x*x*m-w*w)),T=(w*b-_*M)/m,A=(-w*_-b*M)/m,S=(w*b+_*M)/m,E=(-w*_+b*M)/m,N=T-y,k=A-v,C=S-y,P=E-v;return N*N+k*k>C*C+P*P&&(T=S,A=E),{cx:T,cy:A,x01:-s,y01:-l,x11:T*(i/x-1),y11:A*(i/x-1)}}var Fm=Array.prototype.slice;function qm(t){return"object"==typeof t&&"length"in t?t:Array.from(t)}function Um(t){this._context=t}function Im(t){return new Um(t)}function Om(t){return t[0]}function Bm(t){return t[1]}function Ym(t,n){var e=ym(!0),r=null,i=Im,o=null,a=km(u);function u(u){var c,f,s,l=(u=qm(u)).length,h=!1;for(null==r&&(o=i(s=a())),c=0;c<=l;++c)!(c=l;--h)u.point(v[h],_[h]);u.lineEnd(),u.areaEnd()}y&&(v[s]=+t(d,s,f),_[s]=+n(d,s,f),u.point(r?+r(d,s,f):v[s],e?+e(d,s,f):_[s]))}if(p)return u=null,p+""||null}function s(){return Ym().defined(i).curve(a).context(o)}return t="function"==typeof t?t:void 0===t?Om:ym(+t),n="function"==typeof n?n:ym(void 0===n?0:+n),e="function"==typeof e?e:void 0===e?Bm:ym(+e),f.x=function(n){return arguments.length?(t="function"==typeof n?n:ym(+n),r=null,f):t},f.x0=function(n){return arguments.length?(t="function"==typeof n?n:ym(+n),f):t},f.x1=function(t){return arguments.length?(r=null==t?null:"function"==typeof t?t:ym(+t),f):r},f.y=function(t){return arguments.length?(n="function"==typeof t?t:ym(+t),e=null,f):n},f.y0=function(t){return arguments.length?(n="function"==typeof t?t:ym(+t),f):n},f.y1=function(t){return arguments.length?(e=null==t?null:"function"==typeof t?t:ym(+t),f):e},f.lineX0=f.lineY0=function(){return s().x(t).y(n)},f.lineY1=function(){return s().x(t).y(e)},f.lineX1=function(){return s().x(r).y(n)},f.defined=function(t){return arguments.length?(i="function"==typeof t?t:ym(!!t),f):i},f.curve=function(t){return arguments.length?(a=t,null!=o&&(u=a(o)),f):a},f.context=function(t){return arguments.length?(null==t?o=u=null:u=a(o=t),f):o},f}function jm(t,n){return nt?1:n>=t?0:NaN}function Hm(t){return t}Um.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._point=0},lineEnd:function(){(this._line||0!==this._line&&1===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._line?this._context.lineTo(t,n):this._context.moveTo(t,n);break;case 1:this._point=2;default:this._context.lineTo(t,n)}}};var Xm=Vm(Im);function Gm(t){this._curve=t}function Vm(t){function n(n){return new Gm(t(n))}return n._curve=t,n}function Wm(t){var n=t.curve;return t.angle=t.x,delete t.x,t.radius=t.y,delete t.y,t.curve=function(t){return arguments.length?n(Vm(t)):n()._curve},t}function Zm(){return Wm(Ym().curve(Xm))}function Km(){var t=Lm().curve(Xm),n=t.curve,e=t.lineX0,r=t.lineX1,i=t.lineY0,o=t.lineY1;return t.angle=t.x,delete t.x,t.startAngle=t.x0,delete t.x0,t.endAngle=t.x1,delete t.x1,t.radius=t.y,delete t.y,t.innerRadius=t.y0,delete t.y0,t.outerRadius=t.y1,delete t.y1,t.lineStartAngle=function(){return Wm(e())},delete t.lineX0,t.lineEndAngle=function(){return Wm(r())},delete t.lineX1,t.lineInnerRadius=function(){return Wm(i())},delete t.lineY0,t.lineOuterRadius=function(){return Wm(o())},delete t.lineY1,t.curve=function(t){return arguments.length?n(Vm(t)):n()._curve},t}function Qm(t,n){return[(n=+n)*Math.cos(t-=Math.PI/2),n*Math.sin(t)]}Gm.prototype={areaStart:function(){this._curve.areaStart()},areaEnd:function(){this._curve.areaEnd()},lineStart:function(){this._curve.lineStart()},lineEnd:function(){this._curve.lineEnd()},point:function(t,n){this._curve.point(n*Math.sin(t),n*-Math.cos(t))}};class Jm{constructor(t,n){this._context=t,this._x=n}areaStart(){this._line=0}areaEnd(){this._line=NaN}lineStart(){this._point=0}lineEnd(){(this._line||0!==this._line&&1===this._point)&&this._context.closePath(),this._line=1-this._line}point(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._line?this._context.lineTo(t,n):this._context.moveTo(t,n);break;case 1:this._point=2;default:this._x?this._context.bezierCurveTo(this._x0=(this._x0+t)/2,this._y0,this._x0,n,t,n):this._context.bezierCurveTo(this._x0,this._y0=(this._y0+n)/2,t,this._y0,t,n)}this._x0=t,this._y0=n}}class tx{constructor(t){this._context=t}lineStart(){this._point=0}lineEnd(){}point(t,n){if(t=+t,n=+n,0===this._point)this._point=1;else{const e=Qm(this._x0,this._y0),r=Qm(this._x0,this._y0=(this._y0+n)/2),i=Qm(t,this._y0),o=Qm(t,n);this._context.moveTo(...e),this._context.bezierCurveTo(...r,...i,...o)}this._x0=t,this._y0=n}}function nx(t){return new Jm(t,!0)}function ex(t){return new Jm(t,!1)}function rx(t){return new tx(t)}function ix(t){return t.source}function ox(t){return t.target}function ax(t){let n=ix,e=ox,r=Om,i=Bm,o=null,a=null,u=km(c);function c(){let c;const f=Fm.call(arguments),s=n.apply(this,f),l=e.apply(this,f);if(null==o&&(a=t(c=u())),a.lineStart(),f[0]=s,a.point(+r.apply(this,f),+i.apply(this,f)),f[0]=l,a.point(+r.apply(this,f),+i.apply(this,f)),a.lineEnd(),c)return a=null,c+""||null}return c.source=function(t){return arguments.length?(n=t,c):n},c.target=function(t){return arguments.length?(e=t,c):e},c.x=function(t){return arguments.length?(r="function"==typeof t?t:ym(+t),c):r},c.y=function(t){return arguments.length?(i="function"==typeof t?t:ym(+t),c):i},c.context=function(n){return arguments.length?(null==n?o=a=null:a=t(o=n),c):o},c}const ux=Mm(3);var cx={draw(t,n){const e=.59436*Mm(n+xm(n/28,.75)),r=e/2,i=r*ux;t.moveTo(0,e),t.lineTo(0,-e),t.moveTo(-i,-r),t.lineTo(i,r),t.moveTo(-i,r),t.lineTo(i,-r)}},fx={draw(t,n){const e=Mm(n/Am);t.moveTo(e,0),t.arc(0,0,e,0,Em)}},sx={draw(t,n){const e=Mm(n/5)/2;t.moveTo(-3*e,-e),t.lineTo(-e,-e),t.lineTo(-e,-3*e),t.lineTo(e,-3*e),t.lineTo(e,-e),t.lineTo(3*e,-e),t.lineTo(3*e,e),t.lineTo(e,e),t.lineTo(e,3*e),t.lineTo(-e,3*e),t.lineTo(-e,e),t.lineTo(-3*e,e),t.closePath()}};const lx=Mm(1/3),hx=2*lx;var dx={draw(t,n){const e=Mm(n/hx),r=e*lx;t.moveTo(0,-e),t.lineTo(r,0),t.lineTo(0,e),t.lineTo(-r,0),t.closePath()}},px={draw(t,n){const e=.62625*Mm(n);t.moveTo(0,-e),t.lineTo(e,0),t.lineTo(0,e),t.lineTo(-e,0),t.closePath()}},gx={draw(t,n){const e=.87559*Mm(n-xm(n/7,2));t.moveTo(-e,0),t.lineTo(e,0),t.moveTo(0,e),t.lineTo(0,-e)}},yx={draw(t,n){const e=Mm(n),r=-e/2;t.rect(r,r,e,e)}},vx={draw(t,n){const e=.4431*Mm(n);t.moveTo(e,e),t.lineTo(e,-e),t.lineTo(-e,-e),t.lineTo(-e,e),t.closePath()}};const _x=wm(Am/10)/wm(7*Am/10),bx=wm(Em/10)*_x,mx=-bm(Em/10)*_x;var xx={draw(t,n){const e=Mm(.8908130915292852*n),r=bx*e,i=mx*e;t.moveTo(0,-e),t.lineTo(r,i);for(let n=1;n<5;++n){const o=Em*n/5,a=bm(o),u=wm(o);t.lineTo(u*e,-a*e),t.lineTo(a*r-u*i,u*r+a*i)}t.closePath()}};const wx=Mm(3);var Mx={draw(t,n){const e=-Mm(n/(3*wx));t.moveTo(0,2*e),t.lineTo(-wx*e,-e),t.lineTo(wx*e,-e),t.closePath()}};const Tx=Mm(3);var Ax={draw(t,n){const e=.6824*Mm(n),r=e/2,i=e*Tx/2;t.moveTo(0,-e),t.lineTo(i,r),t.lineTo(-i,r),t.closePath()}};const Sx=-.5,Ex=Mm(3)/2,Nx=1/Mm(12),kx=3*(Nx/2+1);var Cx={draw(t,n){const e=Mm(n/kx),r=e/2,i=e*Nx,o=r,a=e*Nx+e,u=-o,c=a;t.moveTo(r,i),t.lineTo(o,a),t.lineTo(u,c),t.lineTo(Sx*r-Ex*i,Ex*r+Sx*i),t.lineTo(Sx*o-Ex*a,Ex*o+Sx*a),t.lineTo(Sx*u-Ex*c,Ex*u+Sx*c),t.lineTo(Sx*r+Ex*i,Sx*i-Ex*r),t.lineTo(Sx*o+Ex*a,Sx*a-Ex*o),t.lineTo(Sx*u+Ex*c,Sx*c-Ex*u),t.closePath()}},Px={draw(t,n){const e=.6189*Mm(n-xm(n/6,1.7));t.moveTo(-e,-e),t.lineTo(e,e),t.moveTo(-e,e),t.lineTo(e,-e)}};const zx=[fx,sx,dx,yx,xx,Mx,Cx],$x=[fx,gx,Px,Ax,cx,vx,px];function Dx(){}function Rx(t,n,e){t._context.bezierCurveTo((2*t._x0+t._x1)/3,(2*t._y0+t._y1)/3,(t._x0+2*t._x1)/3,(t._y0+2*t._y1)/3,(t._x0+4*t._x1+n)/6,(t._y0+4*t._y1+e)/6)}function Fx(t){this._context=t}function qx(t){this._context=t}function Ux(t){this._context=t}function Ix(t,n){this._basis=new Fx(t),this._beta=n}Fx.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._x0=this._x1=this._y0=this._y1=NaN,this._point=0},lineEnd:function(){switch(this._point){case 3:Rx(this,this._x1,this._y1);case 2:this._context.lineTo(this._x1,this._y1)}(this._line||0!==this._line&&1===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._line?this._context.lineTo(t,n):this._context.moveTo(t,n);break;case 1:this._point=2;break;case 2:this._point=3,this._context.lineTo((5*this._x0+this._x1)/6,(5*this._y0+this._y1)/6);default:Rx(this,t,n)}this._x0=this._x1,this._x1=t,this._y0=this._y1,this._y1=n}},qx.prototype={areaStart:Dx,areaEnd:Dx,lineStart:function(){this._x0=this._x1=this._x2=this._x3=this._x4=this._y0=this._y1=this._y2=this._y3=this._y4=NaN,this._point=0},lineEnd:function(){switch(this._point){case 1:this._context.moveTo(this._x2,this._y2),this._context.closePath();break;case 2:this._context.moveTo((this._x2+2*this._x3)/3,(this._y2+2*this._y3)/3),this._context.lineTo((this._x3+2*this._x2)/3,(this._y3+2*this._y2)/3),this._context.closePath();break;case 3:this.point(this._x2,this._y2),this.point(this._x3,this._y3),this.point(this._x4,this._y4)}},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._x2=t,this._y2=n;break;case 1:this._point=2,this._x3=t,this._y3=n;break;case 2:this._point=3,this._x4=t,this._y4=n,this._context.moveTo((this._x0+4*this._x1+t)/6,(this._y0+4*this._y1+n)/6);break;default:Rx(this,t,n)}this._x0=this._x1,this._x1=t,this._y0=this._y1,this._y1=n}},Ux.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._x0=this._x1=this._y0=this._y1=NaN,this._point=0},lineEnd:function(){(this._line||0!==this._line&&3===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1;break;case 1:this._point=2;break;case 2:this._point=3;var e=(this._x0+4*this._x1+t)/6,r=(this._y0+4*this._y1+n)/6;this._line?this._context.lineTo(e,r):this._context.moveTo(e,r);break;case 3:this._point=4;default:Rx(this,t,n)}this._x0=this._x1,this._x1=t,this._y0=this._y1,this._y1=n}},Ix.prototype={lineStart:function(){this._x=[],this._y=[],this._basis.lineStart()},lineEnd:function(){var t=this._x,n=this._y,e=t.length-1;if(e>0)for(var r,i=t[0],o=n[0],a=t[e]-i,u=n[e]-o,c=-1;++c<=e;)r=c/e,this._basis.point(this._beta*t[c]+(1-this._beta)*(i+r*a),this._beta*n[c]+(1-this._beta)*(o+r*u));this._x=this._y=null,this._basis.lineEnd()},point:function(t,n){this._x.push(+t),this._y.push(+n)}};var Ox=function t(n){function e(t){return 1===n?new Fx(t):new Ix(t,n)}return e.beta=function(n){return t(+n)},e}(.85);function Bx(t,n,e){t._context.bezierCurveTo(t._x1+t._k*(t._x2-t._x0),t._y1+t._k*(t._y2-t._y0),t._x2+t._k*(t._x1-n),t._y2+t._k*(t._y1-e),t._x2,t._y2)}function Yx(t,n){this._context=t,this._k=(1-n)/6}Yx.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._x0=this._x1=this._x2=this._y0=this._y1=this._y2=NaN,this._point=0},lineEnd:function(){switch(this._point){case 2:this._context.lineTo(this._x2,this._y2);break;case 3:Bx(this,this._x1,this._y1)}(this._line||0!==this._line&&1===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._line?this._context.lineTo(t,n):this._context.moveTo(t,n);break;case 1:this._point=2,this._x1=t,this._y1=n;break;case 2:this._point=3;default:Bx(this,t,n)}this._x0=this._x1,this._x1=this._x2,this._x2=t,this._y0=this._y1,this._y1=this._y2,this._y2=n}};var Lx=function t(n){function e(t){return new Yx(t,n)}return e.tension=function(n){return t(+n)},e}(0);function jx(t,n){this._context=t,this._k=(1-n)/6}jx.prototype={areaStart:Dx,areaEnd:Dx,lineStart:function(){this._x0=this._x1=this._x2=this._x3=this._x4=this._x5=this._y0=this._y1=this._y2=this._y3=this._y4=this._y5=NaN,this._point=0},lineEnd:function(){switch(this._point){case 1:this._context.moveTo(this._x3,this._y3),this._context.closePath();break;case 2:this._context.lineTo(this._x3,this._y3),this._context.closePath();break;case 3:this.point(this._x3,this._y3),this.point(this._x4,this._y4),this.point(this._x5,this._y5)}},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._x3=t,this._y3=n;break;case 1:this._point=2,this._context.moveTo(this._x4=t,this._y4=n);break;case 2:this._point=3,this._x5=t,this._y5=n;break;default:Bx(this,t,n)}this._x0=this._x1,this._x1=this._x2,this._x2=t,this._y0=this._y1,this._y1=this._y2,this._y2=n}};var Hx=function t(n){function e(t){return new jx(t,n)}return e.tension=function(n){return t(+n)},e}(0);function Xx(t,n){this._context=t,this._k=(1-n)/6}Xx.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._x0=this._x1=this._x2=this._y0=this._y1=this._y2=NaN,this._point=0},lineEnd:function(){(this._line||0!==this._line&&3===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1;break;case 1:this._point=2;break;case 2:this._point=3,this._line?this._context.lineTo(this._x2,this._y2):this._context.moveTo(this._x2,this._y2);break;case 3:this._point=4;default:Bx(this,t,n)}this._x0=this._x1,this._x1=this._x2,this._x2=t,this._y0=this._y1,this._y1=this._y2,this._y2=n}};var Gx=function t(n){function e(t){return new Xx(t,n)}return e.tension=function(n){return t(+n)},e}(0);function Vx(t,n,e){var r=t._x1,i=t._y1,o=t._x2,a=t._y2;if(t._l01_a>Tm){var u=2*t._l01_2a+3*t._l01_a*t._l12_a+t._l12_2a,c=3*t._l01_a*(t._l01_a+t._l12_a);r=(r*u-t._x0*t._l12_2a+t._x2*t._l01_2a)/c,i=(i*u-t._y0*t._l12_2a+t._y2*t._l01_2a)/c}if(t._l23_a>Tm){var f=2*t._l23_2a+3*t._l23_a*t._l12_a+t._l12_2a,s=3*t._l23_a*(t._l23_a+t._l12_a);o=(o*f+t._x1*t._l23_2a-n*t._l12_2a)/s,a=(a*f+t._y1*t._l23_2a-e*t._l12_2a)/s}t._context.bezierCurveTo(r,i,o,a,t._x2,t._y2)}function Wx(t,n){this._context=t,this._alpha=n}Wx.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._x0=this._x1=this._x2=this._y0=this._y1=this._y2=NaN,this._l01_a=this._l12_a=this._l23_a=this._l01_2a=this._l12_2a=this._l23_2a=this._point=0},lineEnd:function(){switch(this._point){case 2:this._context.lineTo(this._x2,this._y2);break;case 3:this.point(this._x2,this._y2)}(this._line||0!==this._line&&1===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){if(t=+t,n=+n,this._point){var e=this._x2-t,r=this._y2-n;this._l23_a=Math.sqrt(this._l23_2a=Math.pow(e*e+r*r,this._alpha))}switch(this._point){case 0:this._point=1,this._line?this._context.lineTo(t,n):this._context.moveTo(t,n);break;case 1:this._point=2;break;case 2:this._point=3;default:Vx(this,t,n)}this._l01_a=this._l12_a,this._l12_a=this._l23_a,this._l01_2a=this._l12_2a,this._l12_2a=this._l23_2a,this._x0=this._x1,this._x1=this._x2,this._x2=t,this._y0=this._y1,this._y1=this._y2,this._y2=n}};var Zx=function t(n){function e(t){return n?new Wx(t,n):new Yx(t,0)}return e.alpha=function(n){return t(+n)},e}(.5);function Kx(t,n){this._context=t,this._alpha=n}Kx.prototype={areaStart:Dx,areaEnd:Dx,lineStart:function(){this._x0=this._x1=this._x2=this._x3=this._x4=this._x5=this._y0=this._y1=this._y2=this._y3=this._y4=this._y5=NaN,this._l01_a=this._l12_a=this._l23_a=this._l01_2a=this._l12_2a=this._l23_2a=this._point=0},lineEnd:function(){switch(this._point){case 1:this._context.moveTo(this._x3,this._y3),this._context.closePath();break;case 2:this._context.lineTo(this._x3,this._y3),this._context.closePath();break;case 3:this.point(this._x3,this._y3),this.point(this._x4,this._y4),this.point(this._x5,this._y5)}},point:function(t,n){if(t=+t,n=+n,this._point){var e=this._x2-t,r=this._y2-n;this._l23_a=Math.sqrt(this._l23_2a=Math.pow(e*e+r*r,this._alpha))}switch(this._point){case 0:this._point=1,this._x3=t,this._y3=n;break;case 1:this._point=2,this._context.moveTo(this._x4=t,this._y4=n);break;case 2:this._point=3,this._x5=t,this._y5=n;break;default:Vx(this,t,n)}this._l01_a=this._l12_a,this._l12_a=this._l23_a,this._l01_2a=this._l12_2a,this._l12_2a=this._l23_2a,this._x0=this._x1,this._x1=this._x2,this._x2=t,this._y0=this._y1,this._y1=this._y2,this._y2=n}};var Qx=function t(n){function e(t){return n?new Kx(t,n):new jx(t,0)}return e.alpha=function(n){return t(+n)},e}(.5);function Jx(t,n){this._context=t,this._alpha=n}Jx.prototype={areaStart:function(){this._line=0},areaEnd:function(){this._line=NaN},lineStart:function(){this._x0=this._x1=this._x2=this._y0=this._y1=this._y2=NaN,this._l01_a=this._l12_a=this._l23_a=this._l01_2a=this._l12_2a=this._l23_2a=this._point=0},lineEnd:function(){(this._line||0!==this._line&&3===this._point)&&this._context.closePath(),this._line=1-this._line},point:function(t,n){if(t=+t,n=+n,this._point){var e=this._x2-t,r=this._y2-n;this._l23_a=Math.sqrt(this._l23_2a=Math.pow(e*e+r*r,this._alpha))}switch(this._point){case 0:this._point=1;break;case 1:this._point=2;break;case 2:this._point=3,this._line?this._context.lineTo(this._x2,this._y2):this._context.moveTo(this._x2,this._y2);break;case 3:this._point=4;default:Vx(this,t,n)}this._l01_a=this._l12_a,this._l12_a=this._l23_a,this._l01_2a=this._l12_2a,this._l12_2a=this._l23_2a,this._x0=this._x1,this._x1=this._x2,this._x2=t,this._y0=this._y1,this._y1=this._y2,this._y2=n}};var tw=function t(n){function e(t){return n?new Jx(t,n):new Xx(t,0)}return e.alpha=function(n){return t(+n)},e}(.5);function nw(t){this._context=t}function ew(t){return t<0?-1:1}function rw(t,n,e){var r=t._x1-t._x0,i=n-t._x1,o=(t._y1-t._y0)/(r||i<0&&-0),a=(e-t._y1)/(i||r<0&&-0),u=(o*i+a*r)/(r+i);return(ew(o)+ew(a))*Math.min(Math.abs(o),Math.abs(a),.5*Math.abs(u))||0}function iw(t,n){var e=t._x1-t._x0;return e?(3*(t._y1-t._y0)/e-n)/2:n}function ow(t,n,e){var r=t._x0,i=t._y0,o=t._x1,a=t._y1,u=(o-r)/3;t._context.bezierCurveTo(r+u,i+u*n,o-u,a-u*e,o,a)}function aw(t){this._context=t}function uw(t){this._context=new cw(t)}function cw(t){this._context=t}function fw(t){this._context=t}function sw(t){var n,e,r=t.length-1,i=new Array(r),o=new Array(r),a=new Array(r);for(i[0]=0,o[0]=2,a[0]=t[0]+2*t[1],n=1;n=0;--n)i[n]=(a[n]-i[n+1])/o[n];for(o[r-1]=(t[r]+i[r-1])/2,n=0;n1)for(var e,r,i,o=1,a=t[n[0]],u=a.length;o=0;)e[n]=n;return e}function pw(t,n){return t[n]}function gw(t){const n=[];return n.key=t,n}function yw(t){var n=t.map(vw);return dw(t).sort((function(t,e){return n[t]-n[e]}))}function vw(t){for(var n,e=-1,r=0,i=t.length,o=-1/0;++eo&&(o=n,r=e);return r}function _w(t){var n=t.map(bw);return dw(t).sort((function(t,e){return n[t]-n[e]}))}function bw(t){for(var n,e=0,r=-1,i=t.length;++r=0&&(this._t=1-this._t,this._line=1-this._line)},point:function(t,n){switch(t=+t,n=+n,this._point){case 0:this._point=1,this._line?this._context.lineTo(t,n):this._context.moveTo(t,n);break;case 1:this._point=2;default:if(this._t<=0)this._context.lineTo(this._x,n),this._context.lineTo(t,n);else{var e=this._x*(1-this._t)+t*this._t;this._context.lineTo(e,this._y),this._context.lineTo(e,n)}}this._x=t,this._y=n}};var mw=t=>()=>t;function xw(t,{sourceEvent:n,target:e,transform:r,dispatch:i}){Object.defineProperties(this,{type:{value:t,enumerable:!0,configurable:!0},sourceEvent:{value:n,enumerable:!0,configurable:!0},target:{value:e,enumerable:!0,configurable:!0},transform:{value:r,enumerable:!0,configurable:!0},_:{value:i}})}function ww(t,n,e){this.k=t,this.x=n,this.y=e}ww.prototype={constructor:ww,scale:function(t){return 1===t?this:new ww(this.k*t,this.x,this.y)},translate:function(t,n){return 0===t&0===n?this:new ww(this.k,this.x+this.k*t,this.y+this.k*n)},apply:function(t){return[t[0]*this.k+this.x,t[1]*this.k+this.y]},applyX:function(t){return t*this.k+this.x},applyY:function(t){return t*this.k+this.y},invert:function(t){return[(t[0]-this.x)/this.k,(t[1]-this.y)/this.k]},invertX:function(t){return(t-this.x)/this.k},invertY:function(t){return(t-this.y)/this.k},rescaleX:function(t){return t.copy().domain(t.range().map(this.invertX,this).map(t.invert,t))},rescaleY:function(t){return t.copy().domain(t.range().map(this.invertY,this).map(t.invert,t))},toString:function(){return"translate("+this.x+","+this.y+") scale("+this.k+")"}};var Mw=new ww(1,0,0);function Tw(t){for(;!t.__zoom;)if(!(t=t.parentNode))return Mw;return t.__zoom}function Aw(t){t.stopImmediatePropagation()}function Sw(t){t.preventDefault(),t.stopImmediatePropagation()}function Ew(t){return!(t.ctrlKey&&"wheel"!==t.type||t.button)}function Nw(){var t=this;return t instanceof SVGElement?(t=t.ownerSVGElement||t).hasAttribute("viewBox")?[[(t=t.viewBox.baseVal).x,t.y],[t.x+t.width,t.y+t.height]]:[[0,0],[t.width.baseVal.value,t.height.baseVal.value]]:[[0,0],[t.clientWidth,t.clientHeight]]}function kw(){return this.__zoom||Mw}function Cw(t){return-t.deltaY*(1===t.deltaMode?.05:t.deltaMode?1:.002)*(t.ctrlKey?10:1)}function Pw(){return navigator.maxTouchPoints||"ontouchstart"in this}function zw(t,n,e){var r=t.invertX(n[0][0])-e[0][0],i=t.invertX(n[1][0])-e[1][0],o=t.invertY(n[0][1])-e[0][1],a=t.invertY(n[1][1])-e[1][1];return t.translate(i>r?(r+i)/2:Math.min(0,r)||Math.max(0,i),a>o?(o+a)/2:Math.min(0,o)||Math.max(0,a))}Tw.prototype=ww.prototype,t.Adder=T,t.Delaunay=Lu,t.FormatSpecifier=tf,t.InternMap=InternMap,t.InternSet=InternSet,t.Node=Qd,t.Path=Ua,t.Voronoi=qu,t.ZoomTransform=ww,t.active=function(t,n){var e,r,i=t.__transition;if(i)for(r in n=null==n?null:n+"",i)if((e=i[r]).state>qi&&e.name===n)return new po([[t]],Zo,n,+r);return null},t.arc=function(){var t=Cm,n=Pm,e=ym(0),r=null,i=zm,o=$m,a=Dm,u=null,c=km(f);function f(){var f,s,l=+t.apply(this,arguments),h=+n.apply(this,arguments),d=i.apply(this,arguments)-Sm,p=o.apply(this,arguments)-Sm,g=vm(p-d),y=p>d;if(u||(u=f=c()),hTm)if(g>Em-Tm)u.moveTo(h*bm(d),h*wm(d)),u.arc(0,0,h,d,p,!y),l>Tm&&(u.moveTo(l*bm(p),l*wm(p)),u.arc(0,0,l,p,d,y));else{var v,_,b=d,m=p,x=d,w=p,M=g,T=g,A=a.apply(this,arguments)/2,S=A>Tm&&(r?+r.apply(this,arguments):Mm(l*l+h*h)),E=xm(vm(h-l)/2,+e.apply(this,arguments)),N=E,k=E;if(S>Tm){var C=Nm(S/l*wm(A)),P=Nm(S/h*wm(A));(M-=2*C)>Tm?(x+=C*=y?1:-1,w-=C):(M=0,x=w=(d+p)/2),(T-=2*P)>Tm?(b+=P*=y?1:-1,m-=P):(T=0,b=m=(d+p)/2)}var z=h*bm(b),$=h*wm(b),D=l*bm(w),R=l*wm(w);if(E>Tm){var F,q=h*bm(m),U=h*wm(m),I=l*bm(x),O=l*wm(x);if(g1?0:t<-1?Am:Math.acos(t)}((B*L+Y*j)/(Mm(B*B+Y*Y)*Mm(L*L+j*j)))/2),X=Mm(F[0]*F[0]+F[1]*F[1]);N=xm(E,(l-X)/(H-1)),k=xm(E,(h-X)/(H+1))}else N=k=0}T>Tm?k>Tm?(v=Rm(I,O,z,$,h,k,y),_=Rm(q,U,D,R,h,k,y),u.moveTo(v.cx+v.x01,v.cy+v.y01),kTm&&M>Tm?N>Tm?(v=Rm(D,R,q,U,l,-N,y),_=Rm(z,$,I,O,l,-N,y),u.lineTo(v.cx+v.x01,v.cy+v.y01),N=0))throw new RangeError("invalid r");let e=t.length;if(!((e=Math.floor(e))>=0))throw new RangeError("invalid length");if(!e||!n)return t;const r=y(n),i=t.slice();return r(t,i,0,e,1),r(i,t,0,e,1),r(t,i,0,e,1),t},t.blur2=l,t.blurImage=h,t.brush=function(){return wa(la)},t.brushSelection=function(t){var n=t.__brush;return n?n.dim.output(n.selection):null},t.brushX=function(){return wa(fa)},t.brushY=function(){return wa(sa)},t.buffer=function(t,n){return fetch(t,n).then(_c)},t.chord=function(){return za(!1,!1)},t.chordDirected=function(){return za(!0,!1)},t.chordTranspose=function(){return za(!1,!0)},t.cluster=function(){var t=Ld,n=1,e=1,r=!1;function i(i){var o,a=0;i.eachAfter((function(n){var e=n.children;e?(n.x=function(t){return t.reduce(jd,0)/t.length}(e),n.y=function(t){return 1+t.reduce(Hd,0)}(e)):(n.x=o?a+=t(n,o):0,n.y=0,o=n)}));var u=function(t){for(var n;n=t.children;)t=n[0];return t}(i),c=function(t){for(var n;n=t.children;)t=n[n.length-1];return t}(i),f=u.x-t(u,c)/2,s=c.x+t(c,u)/2;return i.eachAfter(r?function(t){t.x=(t.x-i.x)*n,t.y=(i.y-t.y)*e}:function(t){t.x=(t.x-f)/(s-f)*n,t.y=(1-(i.y?t.y/i.y:1))*e})}return i.separation=function(n){return arguments.length?(t=n,i):t},i.size=function(t){return arguments.length?(r=!1,n=+t[0],e=+t[1],i):r?null:[n,e]},i.nodeSize=function(t){return arguments.length?(r=!0,n=+t[0],e=+t[1],i):r?[n,e]:null},i},t.color=ze,t.contourDensity=function(){var t=fu,n=su,e=lu,r=960,i=500,o=20,a=2,u=3*o,c=r+2*u>>a,f=i+2*u>>a,s=Qa(20);function h(r){var i=new Float32Array(c*f),s=Math.pow(2,-a),h=-1;for(const o of r){var d=(t(o,++h,r)+u)*s,p=(n(o,h,r)+u)*s,g=+e(o,h,r);if(g&&d>=0&&d=0&&pt*r)))(n).map(((t,n)=>(t.value=+e[n],p(t))))}function p(t){return t.coordinates.forEach(g),t}function g(t){t.forEach(y)}function y(t){t.forEach(v)}function v(t){t[0]=t[0]*Math.pow(2,a)-u,t[1]=t[1]*Math.pow(2,a)-u}function _(){return c=r+2*(u=3*o)>>a,f=i+2*u>>a,d}return d.contours=function(t){var n=h(t),e=iu().size([c,f]),r=Math.pow(2,2*a),i=t=>{t=+t;var i=p(e.contour(n,t*r));return i.value=t,i};return Object.defineProperty(i,"max",{get:()=>J(n)/r}),i},d.x=function(n){return arguments.length?(t="function"==typeof n?n:Qa(+n),d):t},d.y=function(t){return arguments.length?(n="function"==typeof t?t:Qa(+t),d):n},d.weight=function(t){return arguments.length?(e="function"==typeof t?t:Qa(+t),d):e},d.size=function(t){if(!arguments.length)return[r,i];var n=+t[0],e=+t[1];if(!(n>=0&&e>=0))throw new Error("invalid size");return r=n,i=e,_()},d.cellSize=function(t){if(!arguments.length)return 1<=1))throw new Error("invalid cell size");return a=Math.floor(Math.log(t)/Math.LN2),_()},d.thresholds=function(t){return arguments.length?(s="function"==typeof t?t:Array.isArray(t)?Qa(Za.call(t)):Qa(t),d):s},d.bandwidth=function(t){if(!arguments.length)return Math.sqrt(o*(o+1));if(!((t=+t)>=0))throw new Error("invalid bandwidth");return o=(Math.sqrt(4*t*t+1)-1)/2,_()},d},t.contours=iu,t.count=v,t.create=function(t){return Zn(Yt(t).call(document.documentElement))},t.creator=Yt,t.cross=function(...t){const n="function"==typeof t[t.length-1]&&function(t){return n=>t(...n)}(t.pop()),e=(t=t.map(m)).map(_),r=t.length-1,i=new Array(r+1).fill(0),o=[];if(r<0||e.some(b))return o;for(;;){o.push(i.map(((n,e)=>t[e][n])));let a=r;for(;++i[a]===e[a];){if(0===a)return n?o.map(n):o;i[a--]=0}}},t.csv=wc,t.csvFormat=rc,t.csvFormatBody=ic,t.csvFormatRow=ac,t.csvFormatRows=oc,t.csvFormatValue=uc,t.csvParse=nc,t.csvParseRows=ec,t.cubehelix=Tr,t.cumsum=function(t,n){var e=0,r=0;return Float64Array.from(t,void 0===n?t=>e+=+t||0:i=>e+=+n(i,r++,t)||0)},t.curveBasis=function(t){return new Fx(t)},t.curveBasisClosed=function(t){return new qx(t)},t.curveBasisOpen=function(t){return new Ux(t)},t.curveBumpX=nx,t.curveBumpY=ex,t.curveBundle=Ox,t.curveCardinal=Lx,t.curveCardinalClosed=Hx,t.curveCardinalOpen=Gx,t.curveCatmullRom=Zx,t.curveCatmullRomClosed=Qx,t.curveCatmullRomOpen=tw,t.curveLinear=Im,t.curveLinearClosed=function(t){return new nw(t)},t.curveMonotoneX=function(t){return new aw(t)},t.curveMonotoneY=function(t){return new uw(t)},t.curveNatural=function(t){return new fw(t)},t.curveStep=function(t){return new lw(t,.5)},t.curveStepAfter=function(t){return new lw(t,1)},t.curveStepBefore=function(t){return new lw(t,0)},t.descending=e,t.deviation=w,t.difference=function(t,...n){t=new InternSet(t);for(const e of n)for(const n of e)t.delete(n);return t},t.disjoint=function(t,n){const e=n[Symbol.iterator](),r=new InternSet;for(const n of t){if(r.has(n))return!1;let t,i;for(;({value:t,done:i}=e.next())&&!i;){if(Object.is(n,t))return!1;r.add(t)}}return!0},t.dispatch=$t,t.drag=function(){var t,n,e,r,i=se,o=le,a=he,u=de,c={},f=$t("start","drag","end"),s=0,l=0;function h(t){t.on("mousedown.drag",d).filter(u).on("touchstart.drag",y).on("touchmove.drag",v,ee).on("touchend.drag touchcancel.drag",_).style("touch-action","none").style("-webkit-tap-highlight-color","rgba(0,0,0,0)")}function d(a,u){if(!r&&i.call(this,a,u)){var c=b(this,o.call(this,a,u),a,u,"mouse");c&&(Zn(a.view).on("mousemove.drag",p,re).on("mouseup.drag",g,re),ae(a.view),ie(a),e=!1,t=a.clientX,n=a.clientY,c("start",a))}}function p(r){if(oe(r),!e){var i=r.clientX-t,o=r.clientY-n;e=i*i+o*o>l}c.mouse("drag",r)}function g(t){Zn(t.view).on("mousemove.drag mouseup.drag",null),ue(t.view,e),oe(t),c.mouse("end",t)}function y(t,n){if(i.call(this,t,n)){var e,r,a=t.changedTouches,u=o.call(this,t,n),c=a.length;for(e=0;e+t,t.easePoly=wo,t.easePolyIn=mo,t.easePolyInOut=wo,t.easePolyOut=xo,t.easeQuad=_o,t.easeQuadIn=function(t){return t*t},t.easeQuadInOut=_o,t.easeQuadOut=function(t){return t*(2-t)},t.easeSin=Ao,t.easeSinIn=function(t){return 1==+t?1:1-Math.cos(t*To)},t.easeSinInOut=Ao,t.easeSinOut=function(t){return Math.sin(t*To)},t.every=function(t,n){if("function"!=typeof n)throw new TypeError("test is not a function");let e=-1;for(const r of t)if(!n(r,++e,t))return!1;return!0},t.extent=M,t.fcumsum=function(t,n){const e=new T;let r=-1;return Float64Array.from(t,void 0===n?t=>e.add(+t||0):i=>e.add(+n(i,++r,t)||0))},t.filter=function(t,n){if("function"!=typeof n)throw new TypeError("test is not a function");const e=[];let r=-1;for(const i of t)n(i,++r,t)&&e.push(i);return e},t.flatGroup=function(t,...n){return z(P(t,...n),n)},t.flatRollup=function(t,n,...e){return z(D(t,n,...e),e)},t.forceCenter=function(t,n){var e,r=1;function i(){var i,o,a=e.length,u=0,c=0;for(i=0;if+p||os+p||ac.index){var g=f-u.x-u.vx,y=s-u.y-u.vy,v=g*g+y*y;vt.r&&(t.r=t[n].r)}function c(){if(n){var r,i,o=n.length;for(e=new Array(o),r=0;r[u(t,n,r),t])));for(a=0,i=new Array(f);a=u)){(t.data!==n||t.next)&&(0===l&&(p+=(l=Uc(e))*l),0===h&&(p+=(h=Uc(e))*h),p(t=(Lc*t+jc)%Hc)/Hc}();function l(){h(),f.call("tick",n),e1?(null==e?u.delete(t):u.set(t,p(e)),n):u.get(t)},find:function(n,e,r){var i,o,a,u,c,f=0,s=t.length;for(null==r?r=1/0:r*=r,f=0;f1?(f.on(t,e),n):f.on(t)}}},t.forceX=function(t){var n,e,r,i=qc(.1);function o(t){for(var i,o=0,a=n.length;o=.12&&i<.234&&r>=-.425&&r<-.214?u:i>=.166&&i<.234&&r>=-.214&&r<-.115?c:a).invert(t)},s.stream=function(e){return t&&n===e?t:(r=[a.stream(n=e),u.stream(e),c.stream(e)],i=r.length,t={point:function(t,n){for(var e=-1;++ejs(r[0],r[1])&&(r[1]=i[1]),js(i[0],r[1])>js(r[0],r[1])&&(r[0]=i[0])):o.push(r=i);for(a=-1/0,n=0,r=o[e=o.length-1];n<=e;r=i,++n)i=o[n],(u=js(r[1],i[0]))>a&&(a=u,Wf=i[0],Kf=r[1])}return is=os=null,Wf===1/0||Zf===1/0?[[NaN,NaN],[NaN,NaN]]:[[Wf,Zf],[Kf,Qf]]},t.geoCentroid=function(t){ms=xs=ws=Ms=Ts=As=Ss=Es=0,Ns=new T,ks=new T,Cs=new T,Lf(t,Gs);var n=+Ns,e=+ks,r=+Cs,i=Ef(n,e,r);return i=0))throw new RangeError(`invalid digits: ${t}`);i=n}return null===n&&(r=new ed(i)),a},a.projection(t).digits(i).context(n)},t.geoProjection=yd,t.geoProjectionMutator=vd,t.geoRotation=ll,t.geoStereographic=function(){return yd(Bd).scale(250).clipAngle(142)},t.geoStereographicRaw=Bd,t.geoStream=Lf,t.geoTransform=function(t){return{stream:id(t)}},t.geoTransverseMercator=function(){var t=Ed(Yd),n=t.center,e=t.rotate;return t.center=function(t){return arguments.length?n([-t[1],t[0]]):[(t=n())[1],-t[0]]},t.rotate=function(t){return arguments.length?e([t[0],t[1],t.length>2?t[2]+90:90]):[(t=e())[0],t[1],t[2]-90]},e([0,0,90]).scale(159.155)},t.geoTransverseMercatorRaw=Yd,t.gray=function(t,n){return new ur(t,0,0,null==n?1:n)},t.greatest=ot,t.greatestIndex=function(t,e=n){if(1===e.length)return tt(t,e);let r,i=-1,o=-1;for(const n of t)++o,(i<0?0===e(n,n):e(n,r)>0)&&(r=n,i=o);return i},t.group=C,t.groupSort=function(t,e,r){return(2!==e.length?U($(t,e,r),(([t,e],[r,i])=>n(e,i)||n(t,r))):U(C(t,r),(([t,r],[i,o])=>e(r,o)||n(t,i)))).map((([t])=>t))},t.groups=P,t.hcl=dr,t.hierarchy=Gd,t.histogram=Q,t.hsl=He,t.html=Ec,t.image=function(t,n){return new Promise((function(e,r){var i=new Image;for(var o in n)i[o]=n[o];i.onerror=r,i.onload=function(){e(i)},i.src=t}))},t.index=function(t,...n){return F(t,k,R,n)},t.indexes=function(t,...n){return F(t,Array.from,R,n)},t.interpolate=Gr,t.interpolateArray=function(t,n){return(Ir(n)?Ur:Or)(t,n)},t.interpolateBasis=Er,t.interpolateBasisClosed=Nr,t.interpolateBlues=Gb,t.interpolateBrBG=ob,t.interpolateBuGn=Mb,t.interpolateBuPu=Ab,t.interpolateCividis=function(t){return t=Math.max(0,Math.min(1,t)),"rgb("+Math.max(0,Math.min(255,Math.round(-4.54-t*(35.34-t*(2381.73-t*(6402.7-t*(7024.72-2710.57*t)))))))+", "+Math.max(0,Math.min(255,Math.round(32.49+t*(170.73+t*(52.82-t*(131.46-t*(176.58-67.37*t)))))))+", "+Math.max(0,Math.min(255,Math.round(81.24+t*(442.36-t*(2482.43-t*(6167.24-t*(6614.94-2475.67*t)))))))+")"},t.interpolateCool=am,t.interpolateCubehelix=li,t.interpolateCubehelixDefault=im,t.interpolateCubehelixLong=hi,t.interpolateDate=Br,t.interpolateDiscrete=function(t){var n=t.length;return function(e){return t[Math.max(0,Math.min(n-1,Math.floor(e*n)))]}},t.interpolateGnBu=Eb,t.interpolateGreens=Wb,t.interpolateGreys=Kb,t.interpolateHcl=ci,t.interpolateHclLong=fi,t.interpolateHsl=oi,t.interpolateHslLong=ai,t.interpolateHue=function(t,n){var e=Pr(+t,+n);return function(t){var n=e(t);return n-360*Math.floor(n/360)}},t.interpolateInferno=pm,t.interpolateLab=function(t,n){var e=$r((t=ar(t)).l,(n=ar(n)).l),r=$r(t.a,n.a),i=$r(t.b,n.b),o=$r(t.opacity,n.opacity);return function(n){return t.l=e(n),t.a=r(n),t.b=i(n),t.opacity=o(n),t+""}},t.interpolateMagma=dm,t.interpolateNumber=Yr,t.interpolateNumberArray=Ur,t.interpolateObject=Lr,t.interpolateOrRd=kb,t.interpolateOranges=rm,t.interpolatePRGn=ub,t.interpolatePiYG=fb,t.interpolatePlasma=gm,t.interpolatePuBu=$b,t.interpolatePuBuGn=Pb,t.interpolatePuOr=lb,t.interpolatePuRd=Rb,t.interpolatePurples=Jb,t.interpolateRainbow=function(t){(t<0||t>1)&&(t-=Math.floor(t));var n=Math.abs(t-.5);return um.h=360*t-100,um.s=1.5-1.5*n,um.l=.8-.9*n,um+""},t.interpolateRdBu=db,t.interpolateRdGy=gb,t.interpolateRdPu=qb,t.interpolateRdYlBu=vb,t.interpolateRdYlGn=bb,t.interpolateReds=nm,t.interpolateRgb=Dr,t.interpolateRgbBasis=Fr,t.interpolateRgbBasisClosed=qr,t.interpolateRound=Vr,t.interpolateSinebow=function(t){var n;return t=(.5-t)*Math.PI,cm.r=255*(n=Math.sin(t))*n,cm.g=255*(n=Math.sin(t+fm))*n,cm.b=255*(n=Math.sin(t+sm))*n,cm+""},t.interpolateSpectral=xb,t.interpolateString=Xr,t.interpolateTransformCss=ti,t.interpolateTransformSvg=ni,t.interpolateTurbo=function(t){return t=Math.max(0,Math.min(1,t)),"rgb("+Math.max(0,Math.min(255,Math.round(34.61+t*(1172.33-t*(10793.56-t*(33300.12-t*(38394.49-14825.05*t)))))))+", "+Math.max(0,Math.min(255,Math.round(23.31+t*(557.33+t*(1225.33-t*(3574.96-t*(1073.77+707.56*t)))))))+", "+Math.max(0,Math.min(255,Math.round(27.2+t*(3211.1-t*(15327.97-t*(27814-t*(22569.18-6838.66*t)))))))+")"},t.interpolateViridis=hm,t.interpolateWarm=om,t.interpolateYlGn=Bb,t.interpolateYlGnBu=Ib,t.interpolateYlOrBr=Lb,t.interpolateYlOrRd=Hb,t.interpolateZoom=ri,t.interrupt=Gi,t.intersection=function(t,...n){t=new InternSet(t),n=n.map(vt);t:for(const e of t)for(const r of n)if(!r.has(e)){t.delete(e);continue t}return t},t.interval=function(t,n,e){var r=new Ei,i=n;return null==n?(r.restart(t,n,e),r):(r._restart=r.restart,r.restart=function(t,n,e){n=+n,e=null==e?Ai():+e,r._restart((function o(a){a+=i,r._restart(o,i+=n,e),t(a)}),n,e)},r.restart(t,n,e),r)},t.isoFormat=D_,t.isoParse=F_,t.json=function(t,n){return fetch(t,n).then(Tc)},t.lab=ar,t.lch=function(t,n,e,r){return 1===arguments.length?hr(t):new pr(e,n,t,null==r?1:r)},t.least=function(t,e=n){let r,i=!1;if(1===e.length){let o;for(const a of t){const t=e(a);(i?n(t,o)<0:0===n(t,t))&&(r=a,o=t,i=!0)}}else for(const n of t)(i?e(n,r)<0:0===e(n,n))&&(r=n,i=!0);return r},t.leastIndex=ht,t.line=Ym,t.lineRadial=Zm,t.link=ax,t.linkHorizontal=function(){return ax(nx)},t.linkRadial=function(){const t=ax(rx);return t.angle=t.x,delete t.x,t.radius=t.y,delete t.y,t},t.linkVertical=function(){return ax(ex)},t.local=Qn,t.map=function(t,n){if("function"!=typeof t[Symbol.iterator])throw new TypeError("values is not iterable");if("function"!=typeof n)throw new TypeError("mapper is not a function");return Array.from(t,((e,r)=>n(e,r,t)))},t.matcher=Vt,t.max=J,t.maxIndex=tt,t.mean=function(t,n){let e=0,r=0;if(void 0===n)for(let n of t)null!=n&&(n=+n)>=n&&(++e,r+=n);else{let i=-1;for(let o of t)null!=(o=n(o,++i,t))&&(o=+o)>=o&&(++e,r+=o)}if(e)return r/e},t.median=function(t,n){return at(t,.5,n)},t.medianIndex=function(t,n){return ct(t,.5,n)},t.merge=ft,t.min=nt,t.minIndex=et,t.mode=function(t,n){const e=new InternMap;if(void 0===n)for(let n of t)null!=n&&n>=n&&e.set(n,(e.get(n)||0)+1);else{let r=-1;for(let i of t)null!=(i=n(i,++r,t))&&i>=i&&e.set(i,(e.get(i)||0)+1)}let r,i=0;for(const[t,n]of e)n>i&&(i=n,r=t);return r},t.namespace=It,t.namespaces=Ut,t.nice=Z,t.now=Ai,t.pack=function(){var t=null,n=1,e=1,r=np;function i(i){const o=ap();return i.x=n/2,i.y=e/2,t?i.eachBefore(xp(t)).eachAfter(wp(r,.5,o)).eachBefore(Mp(1)):i.eachBefore(xp(mp)).eachAfter(wp(np,1,o)).eachAfter(wp(r,i.r/Math.min(n,e),o)).eachBefore(Mp(Math.min(n,e)/(2*i.r))),i}return i.radius=function(n){return arguments.length?(t=Jd(n),i):t},i.size=function(t){return arguments.length?(n=+t[0],e=+t[1],i):[n,e]},i.padding=function(t){return arguments.length?(r="function"==typeof t?t:ep(+t),i):r},i},t.packEnclose=function(t){return up(t,ap())},t.packSiblings=function(t){return bp(t,ap()),t},t.pairs=function(t,n=st){const e=[];let r,i=!1;for(const o of t)i&&e.push(n(r,o)),r=o,i=!0;return e},t.partition=function(){var t=1,n=1,e=0,r=!1;function i(i){var o=i.height+1;return i.x0=i.y0=e,i.x1=t,i.y1=n/o,i.eachBefore(function(t,n){return function(r){r.children&&Ap(r,r.x0,t*(r.depth+1)/n,r.x1,t*(r.depth+2)/n);var i=r.x0,o=r.y0,a=r.x1-e,u=r.y1-e;a0&&(d+=l);for(null!=n?p.sort((function(t,e){return n(g[t],g[e])})):null!=e&&p.sort((function(t,n){return e(a[t],a[n])})),u=0,f=d?(v-h*b)/d:0;u0?l*f:0)+b,g[c]={data:a[c],index:u,value:l,startAngle:y,endAngle:s,padAngle:_};return g}return a.value=function(n){return arguments.length?(t="function"==typeof n?n:ym(+n),a):t},a.sortValues=function(t){return arguments.length?(n=t,e=null,a):n},a.sort=function(t){return arguments.length?(e=t,n=null,a):e},a.startAngle=function(t){return arguments.length?(r="function"==typeof t?t:ym(+t),a):r},a.endAngle=function(t){return arguments.length?(i="function"==typeof t?t:ym(+t),a):i},a.padAngle=function(t){return arguments.length?(o="function"==typeof t?t:ym(+t),a):o},a},t.piecewise=di,t.pointRadial=Qm,t.pointer=ne,t.pointers=function(t,n){return t.target&&(t=te(t),void 0===n&&(n=t.currentTarget),t=t.touches||[t]),Array.from(t,(t=>ne(t,n)))},t.polygonArea=function(t){for(var n,e=-1,r=t.length,i=t[r-1],o=0;++eu!=f>u&&a<(c-e)*(u-r)/(f-r)+e&&(s=!s),c=e,f=r;return s},t.polygonHull=function(t){if((e=t.length)<3)return null;var n,e,r=new Array(e),i=new Array(e);for(n=0;n=0;--n)f.push(t[r[o[n]][2]]);for(n=+u;n(n=1664525*n+1013904223|0,lg*(n>>>0))},t.randomLogNormal=Kp,t.randomLogistic=fg,t.randomNormal=Zp,t.randomPareto=ng,t.randomPoisson=sg,t.randomUniform=Vp,t.randomWeibull=ug,t.range=lt,t.rank=function(t,e=n){if("function"!=typeof t[Symbol.iterator])throw new TypeError("values is not iterable");let r=Array.from(t);const i=new Float64Array(r.length);2!==e.length&&(r=r.map(e),e=n);const o=(t,n)=>e(r[t],r[n]);let a,u;return(t=Uint32Array.from(r,((t,n)=>n))).sort(e===n?(t,n)=>O(r[t],r[n]):I(o)),t.forEach(((t,n)=>{const e=o(t,void 0===a?t:a);e>=0?((void 0===a||e>0)&&(a=t,u=n),i[t]=u):i[t]=NaN})),i},t.reduce=function(t,n,e){if("function"!=typeof n)throw new TypeError("reducer is not a function");const r=t[Symbol.iterator]();let i,o,a=-1;if(arguments.length<3){if(({done:i,value:e}=r.next()),i)return;++a}for(;({done:i,value:o}=r.next()),!i;)e=n(e,o,++a,t);return e},t.reverse=function(t){if("function"!=typeof t[Symbol.iterator])throw new TypeError("values is not iterable");return Array.from(t).reverse()},t.rgb=Fe,t.ribbon=function(){return Wa()},t.ribbonArrow=function(){return Wa(Va)},t.rollup=$,t.rollups=D,t.scaleBand=yg,t.scaleDiverging=function t(){var n=Ng(L_()(mg));return n.copy=function(){return B_(n,t())},dg.apply(n,arguments)},t.scaleDivergingLog=function t(){var n=Fg(L_()).domain([.1,1,10]);return n.copy=function(){return B_(n,t()).base(n.base())},dg.apply(n,arguments)},t.scaleDivergingPow=j_,t.scaleDivergingSqrt=function(){return j_.apply(null,arguments).exponent(.5)},t.scaleDivergingSymlog=function t(){var n=Ig(L_());return n.copy=function(){return B_(n,t()).constant(n.constant())},dg.apply(n,arguments)},t.scaleIdentity=function t(n){var e;function r(t){return null==t||isNaN(t=+t)?e:t}return r.invert=r,r.domain=r.range=function(t){return arguments.length?(n=Array.from(t,_g),r):n.slice()},r.unknown=function(t){return arguments.length?(e=t,r):e},r.copy=function(){return t(n).unknown(e)},n=arguments.length?Array.from(n,_g):[0,1],Ng(r)},t.scaleImplicit=pg,t.scaleLinear=function t(){var n=Sg();return n.copy=function(){return Tg(n,t())},hg.apply(n,arguments),Ng(n)},t.scaleLog=function t(){const n=Fg(Ag()).domain([1,10]);return n.copy=()=>Tg(n,t()).base(n.base()),hg.apply(n,arguments),n},t.scaleOrdinal=gg,t.scalePoint=function(){return vg(yg.apply(null,arguments).paddingInner(1))},t.scalePow=jg,t.scaleQuantile=function t(){var e,r=[],i=[],o=[];function a(){var t=0,n=Math.max(1,i.length);for(o=new Array(n-1);++t0?o[n-1]:r[0],n=i?[o[i-1],r]:[o[n-1],o[n]]},u.unknown=function(t){return arguments.length?(n=t,u):u},u.thresholds=function(){return o.slice()},u.copy=function(){return t().domain([e,r]).range(a).unknown(n)},hg.apply(Ng(u),arguments)},t.scaleRadial=function t(){var n,e=Sg(),r=[0,1],i=!1;function o(t){var r=function(t){return Math.sign(t)*Math.sqrt(Math.abs(t))}(e(t));return isNaN(r)?n:i?Math.round(r):r}return o.invert=function(t){return e.invert(Hg(t))},o.domain=function(t){return arguments.length?(e.domain(t),o):e.domain()},o.range=function(t){return arguments.length?(e.range((r=Array.from(t,_g)).map(Hg)),o):r.slice()},o.rangeRound=function(t){return o.range(t).round(!0)},o.round=function(t){return arguments.length?(i=!!t,o):i},o.clamp=function(t){return arguments.length?(e.clamp(t),o):e.clamp()},o.unknown=function(t){return arguments.length?(n=t,o):n},o.copy=function(){return t(e.domain(),r).round(i).clamp(e.clamp()).unknown(n)},hg.apply(o,arguments),Ng(o)},t.scaleSequential=function t(){var n=Ng(O_()(mg));return n.copy=function(){return B_(n,t())},dg.apply(n,arguments)},t.scaleSequentialLog=function t(){var n=Fg(O_()).domain([1,10]);return n.copy=function(){return B_(n,t()).base(n.base())},dg.apply(n,arguments)},t.scaleSequentialPow=Y_,t.scaleSequentialQuantile=function t(){var e=[],r=mg;function i(t){if(null!=t&&!isNaN(t=+t))return r((s(e,t,1)-1)/(e.length-1))}return i.domain=function(t){if(!arguments.length)return e.slice();e=[];for(let n of t)null==n||isNaN(n=+n)||e.push(n);return e.sort(n),i},i.interpolator=function(t){return arguments.length?(r=t,i):r},i.range=function(){return e.map(((t,n)=>r(n/(e.length-1))))},i.quantiles=function(t){return Array.from({length:t+1},((n,r)=>at(e,r/t)))},i.copy=function(){return t(r).domain(e)},dg.apply(i,arguments)},t.scaleSequentialSqrt=function(){return Y_.apply(null,arguments).exponent(.5)},t.scaleSequentialSymlog=function t(){var n=Ig(O_());return n.copy=function(){return B_(n,t()).constant(n.constant())},dg.apply(n,arguments)},t.scaleSqrt=function(){return jg.apply(null,arguments).exponent(.5)},t.scaleSymlog=function t(){var n=Ig(Ag());return n.copy=function(){return Tg(n,t()).constant(n.constant())},hg.apply(n,arguments)},t.scaleThreshold=function t(){var n,e=[.5],r=[0,1],i=1;function o(t){return null!=t&&t<=t?r[s(e,t,0,i)]:n}return o.domain=function(t){return arguments.length?(e=Array.from(t),i=Math.min(e.length,r.length-1),o):e.slice()},o.range=function(t){return arguments.length?(r=Array.from(t),i=Math.min(e.length,r.length-1),o):r.slice()},o.invertExtent=function(t){var n=r.indexOf(t);return[e[n-1],e[n]]},o.unknown=function(t){return arguments.length?(n=t,o):n},o.copy=function(){return t().domain(e).range(r).unknown(n)},hg.apply(o,arguments)},t.scaleTime=function(){return hg.apply(I_(uv,cv,tv,Zy,xy,py,sy,ay,iy,t.timeFormat).domain([new Date(2e3,0,1),new Date(2e3,0,2)]),arguments)},t.scaleUtc=function(){return hg.apply(I_(ov,av,ev,Qy,Fy,yy,hy,cy,iy,t.utcFormat).domain([Date.UTC(2e3,0,1),Date.UTC(2e3,0,2)]),arguments)},t.scan=function(t,n){const e=ht(t,n);return e<0?void 0:e},t.schemeAccent=G_,t.schemeBlues=Xb,t.schemeBrBG=ib,t.schemeBuGn=wb,t.schemeBuPu=Tb,t.schemeCategory10=X_,t.schemeDark2=V_,t.schemeGnBu=Sb,t.schemeGreens=Vb,t.schemeGreys=Zb,t.schemeObservable10=W_,t.schemeOrRd=Nb,t.schemeOranges=em,t.schemePRGn=ab,t.schemePaired=Z_,t.schemePastel1=K_,t.schemePastel2=Q_,t.schemePiYG=cb,t.schemePuBu=zb,t.schemePuBuGn=Cb,t.schemePuOr=sb,t.schemePuRd=Db,t.schemePurples=Qb,t.schemeRdBu=hb,t.schemeRdGy=pb,t.schemeRdPu=Fb,t.schemeRdYlBu=yb,t.schemeRdYlGn=_b,t.schemeReds=tm,t.schemeSet1=J_,t.schemeSet2=tb,t.schemeSet3=nb,t.schemeSpectral=mb,t.schemeTableau10=eb,t.schemeYlGn=Ob,t.schemeYlGnBu=Ub,t.schemeYlOrBr=Yb,t.schemeYlOrRd=jb,t.select=Zn,t.selectAll=function(t){return"string"==typeof t?new Vn([document.querySelectorAll(t)],[document.documentElement]):new Vn([Ht(t)],Gn)},t.selection=Wn,t.selector=jt,t.selectorAll=Gt,t.shuffle=dt,t.shuffler=pt,t.some=function(t,n){if("function"!=typeof n)throw new TypeError("test is not a function");let e=-1;for(const r of t)if(n(r,++e,t))return!0;return!1},t.sort=U,t.stack=function(){var t=ym([]),n=dw,e=hw,r=pw;function i(i){var o,a,u=Array.from(t.apply(this,arguments),gw),c=u.length,f=-1;for(const t of i)for(o=0,++f;o0)for(var e,r,i,o,a,u,c=0,f=t[n[0]].length;c0?(r[0]=o,r[1]=o+=i):i<0?(r[1]=a,r[0]=a+=i):(r[0]=0,r[1]=i)},t.stackOffsetExpand=function(t,n){if((r=t.length)>0){for(var e,r,i,o=0,a=t[0].length;o0){for(var e,r=0,i=t[n[0]],o=i.length;r0&&(r=(e=t[n[0]]).length)>0){for(var e,r,i,o=0,a=1;afunction(t){t=`${t}`;let n=t.length;zp(t,n-1)&&!zp(t,n-2)&&(t=t.slice(0,-1));return"/"===t[0]?t:`/${t}`}(t(n,e,r)))),e=n.map(Pp),i=new Set(n).add("");for(const t of e)i.has(t)||(i.add(t),n.push(t),e.push(Pp(t)),h.push(Np));d=(t,e)=>n[e],p=(t,n)=>e[n]}for(a=0,i=h.length;a=0&&(f=h[t]).data===Np;--t)f.data=null}if(u.parent=Sp,u.eachBefore((function(t){t.depth=t.parent.depth+1,--i})).eachBefore(Kd),u.parent=null,i>0)throw new Error("cycle");return u}return r.id=function(t){return arguments.length?(n=Jd(t),r):n},r.parentId=function(t){return arguments.length?(e=Jd(t),r):e},r.path=function(n){return arguments.length?(t=Jd(n),r):t},r},t.style=_n,t.subset=function(t,n){return _t(n,t)},t.sum=function(t,n){let e=0;if(void 0===n)for(let n of t)(n=+n)&&(e+=n);else{let r=-1;for(let i of t)(i=+n(i,++r,t))&&(e+=i)}return e},t.superset=_t,t.svg=Nc,t.symbol=function(t,n){let e=null,r=km(i);function i(){let i;if(e||(e=i=r()),t.apply(this,arguments).draw(e,+n.apply(this,arguments)),i)return e=null,i+""||null}return t="function"==typeof t?t:ym(t||fx),n="function"==typeof n?n:ym(void 0===n?64:+n),i.type=function(n){return arguments.length?(t="function"==typeof n?n:ym(n),i):t},i.size=function(t){return arguments.length?(n="function"==typeof t?t:ym(+t),i):n},i.context=function(t){return arguments.length?(e=null==t?null:t,i):e},i},t.symbolAsterisk=cx,t.symbolCircle=fx,t.symbolCross=sx,t.symbolDiamond=dx,t.symbolDiamond2=px,t.symbolPlus=gx,t.symbolSquare=yx,t.symbolSquare2=vx,t.symbolStar=xx,t.symbolTimes=Px,t.symbolTriangle=Mx,t.symbolTriangle2=Ax,t.symbolWye=Cx,t.symbolX=Px,t.symbols=zx,t.symbolsFill=zx,t.symbolsStroke=$x,t.text=mc,t.thresholdFreedmanDiaconis=function(t,n,e){const r=v(t),i=at(t,.75)-at(t,.25);return r&&i?Math.ceil((e-n)/(2*i*Math.pow(r,-1/3))):1},t.thresholdScott=function(t,n,e){const r=v(t),i=w(t);return r&&i?Math.ceil((e-n)*Math.cbrt(r)/(3.49*i)):1},t.thresholdSturges=K,t.tickFormat=Eg,t.tickIncrement=V,t.tickStep=W,t.ticks=G,t.timeDay=py,t.timeDays=gy,t.timeFormatDefaultLocale=P_,t.timeFormatLocale=hv,t.timeFriday=Sy,t.timeFridays=$y,t.timeHour=sy,t.timeHours=ly,t.timeInterval=Vg,t.timeMillisecond=Wg,t.timeMilliseconds=Zg,t.timeMinute=ay,t.timeMinutes=uy,t.timeMonday=wy,t.timeMondays=ky,t.timeMonth=Zy,t.timeMonths=Ky,t.timeSaturday=Ey,t.timeSaturdays=Dy,t.timeSecond=iy,t.timeSeconds=oy,t.timeSunday=xy,t.timeSundays=Ny,t.timeThursday=Ay,t.timeThursdays=zy,t.timeTickInterval=cv,t.timeTicks=uv,t.timeTuesday=My,t.timeTuesdays=Cy,t.timeWednesday=Ty,t.timeWednesdays=Py,t.timeWeek=xy,t.timeWeeks=Ny,t.timeYear=tv,t.timeYears=nv,t.timeout=$i,t.timer=Ni,t.timerFlush=ki,t.transition=go,t.transpose=gt,t.tree=function(){var t=$p,n=1,e=1,r=null;function i(i){var c=function(t){for(var n,e,r,i,o,a=new Up(t,0),u=[a];n=u.pop();)if(r=n._.children)for(n.children=new Array(o=r.length),i=o-1;i>=0;--i)u.push(e=n.children[i]=new Up(r[i],i)),e.parent=n;return(a.parent=new Up(null,0)).children=[a],a}(i);if(c.eachAfter(o),c.parent.m=-c.z,c.eachBefore(a),r)i.eachBefore(u);else{var f=i,s=i,l=i;i.eachBefore((function(t){t.xs.x&&(s=t),t.depth>l.depth&&(l=t)}));var h=f===s?1:t(f,s)/2,d=h-f.x,p=n/(s.x+h+d),g=e/(l.depth||1);i.eachBefore((function(t){t.x=(t.x+d)*p,t.y=t.depth*g}))}return i}function o(n){var e=n.children,r=n.parent.children,i=n.i?r[n.i-1]:null;if(e){!function(t){for(var n,e=0,r=0,i=t.children,o=i.length;--o>=0;)(n=i[o]).z+=e,n.m+=e,e+=n.s+(r+=n.c)}(n);var o=(e[0].z+e[e.length-1].z)/2;i?(n.z=i.z+t(n._,i._),n.m=n.z-o):n.z=o}else i&&(n.z=i.z+t(n._,i._));n.parent.A=function(n,e,r){if(e){for(var i,o=n,a=n,u=e,c=o.parent.children[0],f=o.m,s=a.m,l=u.m,h=c.m;u=Rp(u),o=Dp(o),u&&o;)c=Dp(c),(a=Rp(a)).a=n,(i=u.z+l-o.z-f+t(u._,o._))>0&&(Fp(qp(u,n,r),n,i),f+=i,s+=i),l+=u.m,f+=o.m,h+=c.m,s+=a.m;u&&!Rp(a)&&(a.t=u,a.m+=l-s),o&&!Dp(c)&&(c.t=o,c.m+=f-h,r=n)}return r}(n,i,n.parent.A||r[0])}function a(t){t._.x=t.z+t.parent.m,t.m+=t.parent.m}function u(t){t.x*=n,t.y=t.depth*e}return i.separation=function(n){return arguments.length?(t=n,i):t},i.size=function(t){return arguments.length?(r=!1,n=+t[0],e=+t[1],i):r?null:[n,e]},i.nodeSize=function(t){return arguments.length?(r=!0,n=+t[0],e=+t[1],i):r?[n,e]:null},i},t.treemap=function(){var t=Yp,n=!1,e=1,r=1,i=[0],o=np,a=np,u=np,c=np,f=np;function s(t){return t.x0=t.y0=0,t.x1=e,t.y1=r,t.eachBefore(l),i=[0],n&&t.eachBefore(Tp),t}function l(n){var e=i[n.depth],r=n.x0+e,s=n.y0+e,l=n.x1-e,h=n.y1-e;l=e-1){var s=u[n];return s.x0=i,s.y0=o,s.x1=a,void(s.y1=c)}var l=f[n],h=r/2+l,d=n+1,p=e-1;for(;d>>1;f[g]c-o){var _=r?(i*v+a*y)/r:a;t(n,d,y,i,o,_,c),t(d,e,v,_,o,a,c)}else{var b=r?(o*v+c*y)/r:c;t(n,d,y,i,o,a,b),t(d,e,v,i,b,a,c)}}(0,c,t.value,n,e,r,i)},t.treemapDice=Ap,t.treemapResquarify=Lp,t.treemapSlice=Ip,t.treemapSliceDice=function(t,n,e,r,i){(1&t.depth?Ip:Ap)(t,n,e,r,i)},t.treemapSquarify=Yp,t.tsv=Mc,t.tsvFormat=lc,t.tsvFormatBody=hc,t.tsvFormatRow=pc,t.tsvFormatRows=dc,t.tsvFormatValue=gc,t.tsvParse=fc,t.tsvParseRows=sc,t.union=function(...t){const n=new InternSet;for(const e of t)for(const t of e)n.add(t);return n},t.unixDay=_y,t.unixDays=by,t.utcDay=yy,t.utcDays=vy,t.utcFriday=By,t.utcFridays=Vy,t.utcHour=hy,t.utcHours=dy,t.utcMillisecond=Wg,t.utcMilliseconds=Zg,t.utcMinute=cy,t.utcMinutes=fy,t.utcMonday=qy,t.utcMondays=jy,t.utcMonth=Qy,t.utcMonths=Jy,t.utcSaturday=Yy,t.utcSaturdays=Wy,t.utcSecond=iy,t.utcSeconds=oy,t.utcSunday=Fy,t.utcSundays=Ly,t.utcThursday=Oy,t.utcThursdays=Gy,t.utcTickInterval=av,t.utcTicks=ov,t.utcTuesday=Uy,t.utcTuesdays=Hy,t.utcWednesday=Iy,t.utcWednesdays=Xy,t.utcWeek=Fy,t.utcWeeks=Ly,t.utcYear=ev,t.utcYears=rv,t.variance=x,t.version="7.9.0",t.window=pn,t.xml=Sc,t.zip=function(){return gt(arguments)},t.zoom=function(){var t,n,e,r=Ew,i=Nw,o=zw,a=Cw,u=Pw,c=[0,1/0],f=[[-1/0,-1/0],[1/0,1/0]],s=250,l=ri,h=$t("start","zoom","end"),d=500,p=150,g=0,y=10;function v(t){t.property("__zoom",kw).on("wheel.zoom",T,{passive:!1}).on("mousedown.zoom",A).on("dblclick.zoom",S).filter(u).on("touchstart.zoom",E).on("touchmove.zoom",N).on("touchend.zoom touchcancel.zoom",k).style("-webkit-tap-highlight-color","rgba(0,0,0,0)")}function _(t,n){return(n=Math.max(c[0],Math.min(c[1],n)))===t.k?t:new ww(n,t.x,t.y)}function b(t,n,e){var r=n[0]-e[0]*t.k,i=n[1]-e[1]*t.k;return r===t.x&&i===t.y?t:new ww(t.k,r,i)}function m(t){return[(+t[0][0]+ +t[1][0])/2,(+t[0][1]+ +t[1][1])/2]}function x(t,n,e,r){t.on("start.zoom",(function(){w(this,arguments).event(r).start()})).on("interrupt.zoom end.zoom",(function(){w(this,arguments).event(r).end()})).tween("zoom",(function(){var t=this,o=arguments,a=w(t,o).event(r),u=i.apply(t,o),c=null==e?m(u):"function"==typeof e?e.apply(t,o):e,f=Math.max(u[1][0]-u[0][0],u[1][1]-u[0][1]),s=t.__zoom,h="function"==typeof n?n.apply(t,o):n,d=l(s.invert(c).concat(f/s.k),h.invert(c).concat(f/h.k));return function(t){if(1===t)t=h;else{var n=d(t),e=f/n[2];t=new ww(e,c[0]-n[0]*e,c[1]-n[1]*e)}a.zoom(null,t)}}))}function w(t,n,e){return!e&&t.__zooming||new M(t,n)}function M(t,n){this.that=t,this.args=n,this.active=0,this.sourceEvent=null,this.extent=i.apply(t,n),this.taps=0}function T(t,...n){if(r.apply(this,arguments)){var e=w(this,n).event(t),i=this.__zoom,u=Math.max(c[0],Math.min(c[1],i.k*Math.pow(2,a.apply(this,arguments)))),s=ne(t);if(e.wheel)e.mouse[0][0]===s[0]&&e.mouse[0][1]===s[1]||(e.mouse[1]=i.invert(e.mouse[0]=s)),clearTimeout(e.wheel);else{if(i.k===u)return;e.mouse=[s,i.invert(s)],Gi(this),e.start()}Sw(t),e.wheel=setTimeout((function(){e.wheel=null,e.end()}),p),e.zoom("mouse",o(b(_(i,u),e.mouse[0],e.mouse[1]),e.extent,f))}}function A(t,...n){if(!e&&r.apply(this,arguments)){var i=t.currentTarget,a=w(this,n,!0).event(t),u=Zn(t.view).on("mousemove.zoom",(function(t){if(Sw(t),!a.moved){var n=t.clientX-s,e=t.clientY-l;a.moved=n*n+e*e>g}a.event(t).zoom("mouse",o(b(a.that.__zoom,a.mouse[0]=ne(t,i),a.mouse[1]),a.extent,f))}),!0).on("mouseup.zoom",(function(t){u.on("mousemove.zoom mouseup.zoom",null),ue(t.view,a.moved),Sw(t),a.event(t).end()}),!0),c=ne(t,i),s=t.clientX,l=t.clientY;ae(t.view),Aw(t),a.mouse=[c,this.__zoom.invert(c)],Gi(this),a.start()}}function S(t,...n){if(r.apply(this,arguments)){var e=this.__zoom,a=ne(t.changedTouches?t.changedTouches[0]:t,this),u=e.invert(a),c=e.k*(t.shiftKey?.5:2),l=o(b(_(e,c),a,u),i.apply(this,n),f);Sw(t),s>0?Zn(this).transition().duration(s).call(x,l,a,t):Zn(this).call(v.transform,l,a,t)}}function E(e,...i){if(r.apply(this,arguments)){var o,a,u,c,f=e.touches,s=f.length,l=w(this,i,e.changedTouches.length===s).event(e);for(Aw(e),a=0;a=12" + } +} diff --git a/frontend/node_modules/d3/src/index.js b/frontend/node_modules/d3/src/index.js new file mode 100644 index 0000000..f33e31f --- /dev/null +++ b/frontend/node_modules/d3/src/index.js @@ -0,0 +1,30 @@ +export * from "d3-array"; +export * from "d3-axis"; +export * from "d3-brush"; +export * from "d3-chord"; +export * from "d3-color"; +export * from "d3-contour"; +export * from "d3-delaunay"; +export * from "d3-dispatch"; +export * from "d3-drag"; +export * from "d3-dsv"; +export * from "d3-ease"; +export * from "d3-fetch"; +export * from "d3-force"; +export * from "d3-format"; +export * from "d3-geo"; +export * from "d3-hierarchy"; +export * from "d3-interpolate"; +export * from "d3-path"; +export * from "d3-polygon"; +export * from "d3-quadtree"; +export * from "d3-random"; +export * from "d3-scale"; +export * from "d3-scale-chromatic"; +export * from "d3-selection"; +export * from "d3-shape"; +export * from "d3-time"; +export * from "d3-time-format"; +export * from "d3-timer"; +export * from "d3-transition"; +export * from "d3-zoom"; diff --git a/frontend/node_modules/delaunator/LICENSE b/frontend/node_modules/delaunator/LICENSE new file mode 100644 index 0000000..631921c --- /dev/null +++ b/frontend/node_modules/delaunator/LICENSE @@ -0,0 +1,15 @@ +ISC License + +Copyright (c) 2021, Mapbox + +Permission to use, copy, modify, and/or distribute this software for any purpose +with or without fee is hereby granted, provided that the above copyright notice +and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS +OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER +TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF +THIS SOFTWARE. diff --git a/frontend/node_modules/delaunator/README.md b/frontend/node_modules/delaunator/README.md new file mode 100644 index 0000000..db4af73 --- /dev/null +++ b/frontend/node_modules/delaunator/README.md @@ -0,0 +1,141 @@ +# Delaunator [![Build Status](https://app.travis-ci.com/mapbox/delaunator.svg?branch=main)](https://app.travis-ci.com/mapbox/delaunator) [![](https://img.shields.io/badge/simply-awesome-brightgreen.svg)](https://github.com/mourner/projects) [![](https://badgen.net/bundlephobia/minzip/delaunator)](https://unpkg.com/delaunator) + +An incredibly fast and robust JavaScript library for +[Delaunay triangulation](https://en.wikipedia.org/wiki/Delaunay_triangulation) of 2D points. + +- [Interactive Demo](https://mapbox.github.io/delaunator/demo.html) +- [Guide to data structures](https://mapbox.github.io/delaunator/) + +Delaunay triangulation example + +### Projects based on Delaunator + +- [d3-delaunay](https://github.com/d3/d3-delaunay) for Voronoi diagrams, search, traversal and rendering (a part of [D3](https://d3js.org)). +- [d3-geo-voronoi](https://github.com/Fil/d3-geo-voronoi) for Delaunay triangulations and Voronoi diagrams on a sphere (e.g. for geographic locations). + +## Example + +```js +const coords = [168,180, 168,178, 168,179, 168,181, 168,183, ...]; + +const delaunay = new Delaunator(coords); +console.log(delaunay.triangles); +// [623, 636, 619, 636, 444, 619, ...] +``` + +## Install + +Install with NPM (`npm install delaunator`) or Yarn (`yarn add delaunator`), then import as an ES module: + +```js +import Delaunator from 'delaunator'; +``` + +To use as a module in a browser: + +```html + +``` + +Or use a browser UMD build that exposes a `Delaunator` global variable: + +```html + +``` + +## API Reference + +#### new Delaunator(coords) + +Constructs a delaunay triangulation object given an array of point coordinates of the form: +`[x0, y0, x1, y1, ...]` (use a typed array for best performance). + +#### Delaunator.from(points[, getX, getY]) + +Constructs a delaunay triangulation object given an array of points (`[x, y]` by default). +`getX` and `getY` are optional functions of the form `(point) => value` for custom point formats. +Duplicate points are skipped. + +#### delaunay.triangles + +A `Uint32Array` array of triangle vertex indices (each group of three numbers forms a triangle). +All triangles are directed counterclockwise. + +To get the coordinates of all triangles, use: + +```js +for (let i = 0; i < triangles.length; i += 3) { + coordinates.push([ + points[triangles[i]], + points[triangles[i + 1]], + points[triangles[i + 2]] + ]); +} +``` + +#### delaunay.halfedges + +A `Int32Array` array of triangle half-edge indices that allows you to traverse the triangulation. +`i`-th half-edge in the array corresponds to vertex `triangles[i]` the half-edge is coming from. +`halfedges[i]` is the index of a twin half-edge in an adjacent triangle +(or `-1` for outer half-edges on the convex hull). + +The flat array-based data structures might be counterintuitive, +but they're one of the key reasons this library is fast. + +#### delaunay.hull + +A `Uint32Array` array of indices that reference points on the convex hull of the input data, counter-clockwise. + +#### delaunay.coords + +An array of input coordinates in the form `[x0, y0, x1, y1, ....]`, +of the type provided in the constructor (or `Float64Array` if you used `Delaunator.from`). + +#### delaunay.update() + +Updates the triangulation if you modified `delaunay.coords` values in place, avoiding expensive memory allocations. +Useful for iterative relaxation algorithms such as [Lloyd's](https://en.wikipedia.org/wiki/Lloyd%27s_algorithm). + +## Performance + +Benchmark results against other Delaunay JS libraries +(`npm run bench` on Macbook Pro Retina 15" 2017, Node v10.10.0): + +  | uniform 100k | gauss 100k | grid 100k | degen 100k | uniform 1 million | gauss 1 million | grid 1 million | degen 1 million +:-- | --: | --: | --: | --: | --: | --: | --: | --: +**delaunator** | 82ms | 61ms | 66ms | 25ms | 1.07s | 950ms | 830ms | 278ms +[faster‑delaunay](https://github.com/Bathlamos/delaunay-triangulation) | 473ms | 411ms | 272ms | 68ms | 4.27s | 4.62s | 4.3s | 810ms +[incremental‑delaunay](https://github.com/mikolalysenko/incremental-delaunay) | 547ms | 505ms | 172ms | 528ms | 5.9s | 6.08s | 2.11s | 6.09s +[d3‑voronoi](https://github.com/d3/d3-voronoi) | 972ms | 909ms | 358ms | 720ms | 15.04s | 13.86s | 5.55s | 11.13s +[delaunay‑fast](https://github.com/ironwallaby/delaunay) | 3.8s | 4s | 12.57s | timeout | 132s | 138s | 399s | timeout +[delaunay](https://github.com/darkskyapp/delaunay) | 4.85s | 5.73s | 15.05s | timeout | 156s | 178s | 326s | timeout +[delaunay‑triangulate](https://github.com/mikolalysenko/delaunay-triangulate) | 2.24s | 2.04s | OOM | 1.51s | OOM | OOM | OOM | OOM +[cdt2d](https://github.com/mikolalysenko/cdt2d) | 45s | 51s | 118s | 17s | timeout | timeout | timeout | timeout + +## Papers + +The algorithm is based on ideas from the following papers: + +- [A simple sweep-line Delaunay triangulation algorithm](http://www.academicpub.org/jao/paperInfo.aspx?paperid=15630), 2013, Liu Yonghe, Feng Jinming and Shao Yuehong +- [S-hull: a fast radial sweep-hull routine for Delaunay triangulation](http://www.s-hull.org/paper/s_hull.pdf), 2010, David Sinclair +- [A faster circle-sweep Delaunay triangulation algorithm](http://cglab.ca/~biniaz/papers/Sweep%20Circle.pdf), 2011, Ahmad Biniaz and Gholamhossein Dastghaibyfard + +## Robustness + +Delaunator should produce valid output even on highly degenerate input. It does so by depending on [robust-predicates](https://github.com/mourner/robust-predicates), a modern port of Jonathan Shewchuk's robust geometric predicates, an industry standard in computational geometry. + +## Ports to other languages + +- [delaunator-rs](https://github.com/mourner/delaunator-rs) (Rust) +- [fogleman/delaunay](https://github.com/fogleman/delaunay) (Go) +- [delaunator-cpp](https://github.com/abellgithub/delaunator-cpp) (C++) +- [delaunator-sharp](https://github.com/nol1fe/delaunator-sharp) (C#) +- [delaunator-ruby](https://github.com/hendrixfan/delaunator-ruby) (Ruby) +- [Delaunator-Python](https://github.com/HakanSeven12/Delaunator-Python) (Python) +- [ricardomatias/delaunator](https://github.com/ricardomatias/delaunator) (Kotlin) +- [delaunator-java](https://github.com/waveware4ai/delaunator-java) (Java) +- [delaunay-Stata](https://github.com/asjadnaqvi/stata-delaunay-voronoi) (Stata/Mata) +- [Delaunator.jl](https://github.com/JuliaGeometry/Delaunator.jl) (Julia) diff --git a/frontend/node_modules/delaunator/delaunator.js b/frontend/node_modules/delaunator/delaunator.js new file mode 100644 index 0000000..e056773 --- /dev/null +++ b/frontend/node_modules/delaunator/delaunator.js @@ -0,0 +1,753 @@ +(function (global, factory) { +typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() : +typeof define === 'function' && define.amd ? define(factory) : +(global = typeof globalThis !== 'undefined' ? globalThis : global || self, global.Delaunator = factory()); +})(this, (function () { 'use strict'; + +const epsilon = 1.1102230246251565e-16; +const splitter = 134217729; +const resulterrbound = (3 + 8 * epsilon) * epsilon; + +// fast_expansion_sum_zeroelim routine from oritinal code +function sum(elen, e, flen, f, h) { + let Q, Qnew, hh, bvirt; + let enow = e[0]; + let fnow = f[0]; + let eindex = 0; + let findex = 0; + if ((fnow > enow) === (fnow > -enow)) { + Q = enow; + enow = e[++eindex]; + } else { + Q = fnow; + fnow = f[++findex]; + } + let hindex = 0; + if (eindex < elen && findex < flen) { + if ((fnow > enow) === (fnow > -enow)) { + Qnew = enow + Q; + hh = Q - (Qnew - enow); + enow = e[++eindex]; + } else { + Qnew = fnow + Q; + hh = Q - (Qnew - fnow); + fnow = f[++findex]; + } + Q = Qnew; + if (hh !== 0) { + h[hindex++] = hh; + } + while (eindex < elen && findex < flen) { + if ((fnow > enow) === (fnow > -enow)) { + Qnew = Q + enow; + bvirt = Qnew - Q; + hh = Q - (Qnew - bvirt) + (enow - bvirt); + enow = e[++eindex]; + } else { + Qnew = Q + fnow; + bvirt = Qnew - Q; + hh = Q - (Qnew - bvirt) + (fnow - bvirt); + fnow = f[++findex]; + } + Q = Qnew; + if (hh !== 0) { + h[hindex++] = hh; + } + } + } + while (eindex < elen) { + Qnew = Q + enow; + bvirt = Qnew - Q; + hh = Q - (Qnew - bvirt) + (enow - bvirt); + enow = e[++eindex]; + Q = Qnew; + if (hh !== 0) { + h[hindex++] = hh; + } + } + while (findex < flen) { + Qnew = Q + fnow; + bvirt = Qnew - Q; + hh = Q - (Qnew - bvirt) + (fnow - bvirt); + fnow = f[++findex]; + Q = Qnew; + if (hh !== 0) { + h[hindex++] = hh; + } + } + if (Q !== 0 || hindex === 0) { + h[hindex++] = Q; + } + return hindex; +} + +function estimate(elen, e) { + let Q = e[0]; + for (let i = 1; i < elen; i++) Q += e[i]; + return Q; +} + +function vec(n) { + return new Float64Array(n); +} + +const ccwerrboundA = (3 + 16 * epsilon) * epsilon; +const ccwerrboundB = (2 + 12 * epsilon) * epsilon; +const ccwerrboundC = (9 + 64 * epsilon) * epsilon * epsilon; + +const B = vec(4); +const C1 = vec(8); +const C2 = vec(12); +const D = vec(16); +const u = vec(4); + +function orient2dadapt(ax, ay, bx, by, cx, cy, detsum) { + let acxtail, acytail, bcxtail, bcytail; + let bvirt, c, ahi, alo, bhi, blo, _i, _j, _0, s1, s0, t1, t0, u3; + + const acx = ax - cx; + const bcx = bx - cx; + const acy = ay - cy; + const bcy = by - cy; + + s1 = acx * bcy; + c = splitter * acx; + ahi = c - (c - acx); + alo = acx - ahi; + c = splitter * bcy; + bhi = c - (c - bcy); + blo = bcy - bhi; + s0 = alo * blo - (s1 - ahi * bhi - alo * bhi - ahi * blo); + t1 = acy * bcx; + c = splitter * acy; + ahi = c - (c - acy); + alo = acy - ahi; + c = splitter * bcx; + bhi = c - (c - bcx); + blo = bcx - bhi; + t0 = alo * blo - (t1 - ahi * bhi - alo * bhi - ahi * blo); + _i = s0 - t0; + bvirt = s0 - _i; + B[0] = s0 - (_i + bvirt) + (bvirt - t0); + _j = s1 + _i; + bvirt = _j - s1; + _0 = s1 - (_j - bvirt) + (_i - bvirt); + _i = _0 - t1; + bvirt = _0 - _i; + B[1] = _0 - (_i + bvirt) + (bvirt - t1); + u3 = _j + _i; + bvirt = u3 - _j; + B[2] = _j - (u3 - bvirt) + (_i - bvirt); + B[3] = u3; + + let det = estimate(4, B); + let errbound = ccwerrboundB * detsum; + if (det >= errbound || -det >= errbound) { + return det; + } + + bvirt = ax - acx; + acxtail = ax - (acx + bvirt) + (bvirt - cx); + bvirt = bx - bcx; + bcxtail = bx - (bcx + bvirt) + (bvirt - cx); + bvirt = ay - acy; + acytail = ay - (acy + bvirt) + (bvirt - cy); + bvirt = by - bcy; + bcytail = by - (bcy + bvirt) + (bvirt - cy); + + if (acxtail === 0 && acytail === 0 && bcxtail === 0 && bcytail === 0) { + return det; + } + + errbound = ccwerrboundC * detsum + resulterrbound * Math.abs(det); + det += (acx * bcytail + bcy * acxtail) - (acy * bcxtail + bcx * acytail); + if (det >= errbound || -det >= errbound) return det; + + s1 = acxtail * bcy; + c = splitter * acxtail; + ahi = c - (c - acxtail); + alo = acxtail - ahi; + c = splitter * bcy; + bhi = c - (c - bcy); + blo = bcy - bhi; + s0 = alo * blo - (s1 - ahi * bhi - alo * bhi - ahi * blo); + t1 = acytail * bcx; + c = splitter * acytail; + ahi = c - (c - acytail); + alo = acytail - ahi; + c = splitter * bcx; + bhi = c - (c - bcx); + blo = bcx - bhi; + t0 = alo * blo - (t1 - ahi * bhi - alo * bhi - ahi * blo); + _i = s0 - t0; + bvirt = s0 - _i; + u[0] = s0 - (_i + bvirt) + (bvirt - t0); + _j = s1 + _i; + bvirt = _j - s1; + _0 = s1 - (_j - bvirt) + (_i - bvirt); + _i = _0 - t1; + bvirt = _0 - _i; + u[1] = _0 - (_i + bvirt) + (bvirt - t1); + u3 = _j + _i; + bvirt = u3 - _j; + u[2] = _j - (u3 - bvirt) + (_i - bvirt); + u[3] = u3; + const C1len = sum(4, B, 4, u, C1); + + s1 = acx * bcytail; + c = splitter * acx; + ahi = c - (c - acx); + alo = acx - ahi; + c = splitter * bcytail; + bhi = c - (c - bcytail); + blo = bcytail - bhi; + s0 = alo * blo - (s1 - ahi * bhi - alo * bhi - ahi * blo); + t1 = acy * bcxtail; + c = splitter * acy; + ahi = c - (c - acy); + alo = acy - ahi; + c = splitter * bcxtail; + bhi = c - (c - bcxtail); + blo = bcxtail - bhi; + t0 = alo * blo - (t1 - ahi * bhi - alo * bhi - ahi * blo); + _i = s0 - t0; + bvirt = s0 - _i; + u[0] = s0 - (_i + bvirt) + (bvirt - t0); + _j = s1 + _i; + bvirt = _j - s1; + _0 = s1 - (_j - bvirt) + (_i - bvirt); + _i = _0 - t1; + bvirt = _0 - _i; + u[1] = _0 - (_i + bvirt) + (bvirt - t1); + u3 = _j + _i; + bvirt = u3 - _j; + u[2] = _j - (u3 - bvirt) + (_i - bvirt); + u[3] = u3; + const C2len = sum(C1len, C1, 4, u, C2); + + s1 = acxtail * bcytail; + c = splitter * acxtail; + ahi = c - (c - acxtail); + alo = acxtail - ahi; + c = splitter * bcytail; + bhi = c - (c - bcytail); + blo = bcytail - bhi; + s0 = alo * blo - (s1 - ahi * bhi - alo * bhi - ahi * blo); + t1 = acytail * bcxtail; + c = splitter * acytail; + ahi = c - (c - acytail); + alo = acytail - ahi; + c = splitter * bcxtail; + bhi = c - (c - bcxtail); + blo = bcxtail - bhi; + t0 = alo * blo - (t1 - ahi * bhi - alo * bhi - ahi * blo); + _i = s0 - t0; + bvirt = s0 - _i; + u[0] = s0 - (_i + bvirt) + (bvirt - t0); + _j = s1 + _i; + bvirt = _j - s1; + _0 = s1 - (_j - bvirt) + (_i - bvirt); + _i = _0 - t1; + bvirt = _0 - _i; + u[1] = _0 - (_i + bvirt) + (bvirt - t1); + u3 = _j + _i; + bvirt = u3 - _j; + u[2] = _j - (u3 - bvirt) + (_i - bvirt); + u[3] = u3; + const Dlen = sum(C2len, C2, 4, u, D); + + return D[Dlen - 1]; +} + +function orient2d(ax, ay, bx, by, cx, cy) { + const detleft = (ay - cy) * (bx - cx); + const detright = (ax - cx) * (by - cy); + const det = detleft - detright; + + const detsum = Math.abs(detleft + detright); + if (Math.abs(det) >= ccwerrboundA * detsum) return det; + + return -orient2dadapt(ax, ay, bx, by, cx, cy, detsum); +} + +const EPSILON = Math.pow(2, -52); +const EDGE_STACK = new Uint32Array(512); + +class Delaunator { + + static from(points, getX = defaultGetX, getY = defaultGetY) { + const n = points.length; + const coords = new Float64Array(n * 2); + + for (let i = 0; i < n; i++) { + const p = points[i]; + coords[2 * i] = getX(p); + coords[2 * i + 1] = getY(p); + } + + return new Delaunator(coords); + } + + constructor(coords) { + const n = coords.length >> 1; + if (n > 0 && typeof coords[0] !== 'number') throw new Error('Expected coords to contain numbers.'); + + this.coords = coords; + + // arrays that will store the triangulation graph + const maxTriangles = Math.max(2 * n - 5, 0); + this._triangles = new Uint32Array(maxTriangles * 3); + this._halfedges = new Int32Array(maxTriangles * 3); + + // temporary arrays for tracking the edges of the advancing convex hull + this._hashSize = Math.ceil(Math.sqrt(n)); + this._hullPrev = new Uint32Array(n); // edge to prev edge + this._hullNext = new Uint32Array(n); // edge to next edge + this._hullTri = new Uint32Array(n); // edge to adjacent triangle + this._hullHash = new Int32Array(this._hashSize); // angular edge hash + + // temporary arrays for sorting points + this._ids = new Uint32Array(n); + this._dists = new Float64Array(n); + + this.update(); + } + + update() { + const {coords, _hullPrev: hullPrev, _hullNext: hullNext, _hullTri: hullTri, _hullHash: hullHash} = this; + const n = coords.length >> 1; + + // populate an array of point indices; calculate input data bbox + let minX = Infinity; + let minY = Infinity; + let maxX = -Infinity; + let maxY = -Infinity; + + for (let i = 0; i < n; i++) { + const x = coords[2 * i]; + const y = coords[2 * i + 1]; + if (x < minX) minX = x; + if (y < minY) minY = y; + if (x > maxX) maxX = x; + if (y > maxY) maxY = y; + this._ids[i] = i; + } + const cx = (minX + maxX) / 2; + const cy = (minY + maxY) / 2; + + let i0, i1, i2; + + // pick a seed point close to the center + for (let i = 0, minDist = Infinity; i < n; i++) { + const d = dist(cx, cy, coords[2 * i], coords[2 * i + 1]); + if (d < minDist) { + i0 = i; + minDist = d; + } + } + const i0x = coords[2 * i0]; + const i0y = coords[2 * i0 + 1]; + + // find the point closest to the seed + for (let i = 0, minDist = Infinity; i < n; i++) { + if (i === i0) continue; + const d = dist(i0x, i0y, coords[2 * i], coords[2 * i + 1]); + if (d < minDist && d > 0) { + i1 = i; + minDist = d; + } + } + let i1x = coords[2 * i1]; + let i1y = coords[2 * i1 + 1]; + + let minRadius = Infinity; + + // find the third point which forms the smallest circumcircle with the first two + for (let i = 0; i < n; i++) { + if (i === i0 || i === i1) continue; + const r = circumradius(i0x, i0y, i1x, i1y, coords[2 * i], coords[2 * i + 1]); + if (r < minRadius) { + i2 = i; + minRadius = r; + } + } + let i2x = coords[2 * i2]; + let i2y = coords[2 * i2 + 1]; + + if (minRadius === Infinity) { + // order collinear points by dx (or dy if all x are identical) + // and return the list as a hull + for (let i = 0; i < n; i++) { + this._dists[i] = (coords[2 * i] - coords[0]) || (coords[2 * i + 1] - coords[1]); + } + quicksort(this._ids, this._dists, 0, n - 1); + const hull = new Uint32Array(n); + let j = 0; + for (let i = 0, d0 = -Infinity; i < n; i++) { + const id = this._ids[i]; + const d = this._dists[id]; + if (d > d0) { + hull[j++] = id; + d0 = d; + } + } + this.hull = hull.subarray(0, j); + this.triangles = new Uint32Array(0); + this.halfedges = new Uint32Array(0); + return; + } + + // swap the order of the seed points for counter-clockwise orientation + if (orient2d(i0x, i0y, i1x, i1y, i2x, i2y) < 0) { + const i = i1; + const x = i1x; + const y = i1y; + i1 = i2; + i1x = i2x; + i1y = i2y; + i2 = i; + i2x = x; + i2y = y; + } + + const center = circumcenter(i0x, i0y, i1x, i1y, i2x, i2y); + this._cx = center.x; + this._cy = center.y; + + for (let i = 0; i < n; i++) { + this._dists[i] = dist(coords[2 * i], coords[2 * i + 1], center.x, center.y); + } + + // sort the points by distance from the seed triangle circumcenter + quicksort(this._ids, this._dists, 0, n - 1); + + // set up the seed triangle as the starting hull + this._hullStart = i0; + let hullSize = 3; + + hullNext[i0] = hullPrev[i2] = i1; + hullNext[i1] = hullPrev[i0] = i2; + hullNext[i2] = hullPrev[i1] = i0; + + hullTri[i0] = 0; + hullTri[i1] = 1; + hullTri[i2] = 2; + + hullHash.fill(-1); + hullHash[this._hashKey(i0x, i0y)] = i0; + hullHash[this._hashKey(i1x, i1y)] = i1; + hullHash[this._hashKey(i2x, i2y)] = i2; + + this.trianglesLen = 0; + this._addTriangle(i0, i1, i2, -1, -1, -1); + + for (let k = 0, xp, yp; k < this._ids.length; k++) { + const i = this._ids[k]; + const x = coords[2 * i]; + const y = coords[2 * i + 1]; + + // skip near-duplicate points + if (k > 0 && Math.abs(x - xp) <= EPSILON && Math.abs(y - yp) <= EPSILON) continue; + xp = x; + yp = y; + + // skip seed triangle points + if (i === i0 || i === i1 || i === i2) continue; + + // find a visible edge on the convex hull using edge hash + let start = 0; + for (let j = 0, key = this._hashKey(x, y); j < this._hashSize; j++) { + start = hullHash[(key + j) % this._hashSize]; + if (start !== -1 && start !== hullNext[start]) break; + } + + start = hullPrev[start]; + let e = start, q; + while (q = hullNext[e], orient2d(x, y, coords[2 * e], coords[2 * e + 1], coords[2 * q], coords[2 * q + 1]) >= 0) { + e = q; + if (e === start) { + e = -1; + break; + } + } + if (e === -1) continue; // likely a near-duplicate point; skip it + + // add the first triangle from the point + let t = this._addTriangle(e, i, hullNext[e], -1, -1, hullTri[e]); + + // recursively flip triangles from the point until they satisfy the Delaunay condition + hullTri[i] = this._legalize(t + 2); + hullTri[e] = t; // keep track of boundary triangles on the hull + hullSize++; + + // walk forward through the hull, adding more triangles and flipping recursively + let n = hullNext[e]; + while (q = hullNext[n], orient2d(x, y, coords[2 * n], coords[2 * n + 1], coords[2 * q], coords[2 * q + 1]) < 0) { + t = this._addTriangle(n, i, q, hullTri[i], -1, hullTri[n]); + hullTri[i] = this._legalize(t + 2); + hullNext[n] = n; // mark as removed + hullSize--; + n = q; + } + + // walk backward from the other side, adding more triangles and flipping + if (e === start) { + while (q = hullPrev[e], orient2d(x, y, coords[2 * q], coords[2 * q + 1], coords[2 * e], coords[2 * e + 1]) < 0) { + t = this._addTriangle(q, i, e, -1, hullTri[e], hullTri[q]); + this._legalize(t + 2); + hullTri[q] = t; + hullNext[e] = e; // mark as removed + hullSize--; + e = q; + } + } + + // update the hull indices + this._hullStart = hullPrev[i] = e; + hullNext[e] = hullPrev[n] = i; + hullNext[i] = n; + + // save the two new edges in the hash table + hullHash[this._hashKey(x, y)] = i; + hullHash[this._hashKey(coords[2 * e], coords[2 * e + 1])] = e; + } + + this.hull = new Uint32Array(hullSize); + for (let i = 0, e = this._hullStart; i < hullSize; i++) { + this.hull[i] = e; + e = hullNext[e]; + } + + // trim typed triangle mesh arrays + this.triangles = this._triangles.subarray(0, this.trianglesLen); + this.halfedges = this._halfedges.subarray(0, this.trianglesLen); + } + + _hashKey(x, y) { + return Math.floor(pseudoAngle(x - this._cx, y - this._cy) * this._hashSize) % this._hashSize; + } + + _legalize(a) { + const {_triangles: triangles, _halfedges: halfedges, coords} = this; + + let i = 0; + let ar = 0; + + // recursion eliminated with a fixed-size stack + while (true) { + const b = halfedges[a]; + + /* if the pair of triangles doesn't satisfy the Delaunay condition + * (p1 is inside the circumcircle of [p0, pl, pr]), flip them, + * then do the same check/flip recursively for the new pair of triangles + * + * pl pl + * /||\ / \ + * al/ || \bl al/ \a + * / || \ / \ + * / a||b \ flip /___ar___\ + * p0\ || /p1 => p0\---bl---/p1 + * \ || / \ / + * ar\ || /br b\ /br + * \||/ \ / + * pr pr + */ + const a0 = a - a % 3; + ar = a0 + (a + 2) % 3; + + if (b === -1) { // convex hull edge + if (i === 0) break; + a = EDGE_STACK[--i]; + continue; + } + + const b0 = b - b % 3; + const al = a0 + (a + 1) % 3; + const bl = b0 + (b + 2) % 3; + + const p0 = triangles[ar]; + const pr = triangles[a]; + const pl = triangles[al]; + const p1 = triangles[bl]; + + const illegal = inCircle( + coords[2 * p0], coords[2 * p0 + 1], + coords[2 * pr], coords[2 * pr + 1], + coords[2 * pl], coords[2 * pl + 1], + coords[2 * p1], coords[2 * p1 + 1]); + + if (illegal) { + triangles[a] = p1; + triangles[b] = p0; + + const hbl = halfedges[bl]; + + // edge swapped on the other side of the hull (rare); fix the halfedge reference + if (hbl === -1) { + let e = this._hullStart; + do { + if (this._hullTri[e] === bl) { + this._hullTri[e] = a; + break; + } + e = this._hullPrev[e]; + } while (e !== this._hullStart); + } + this._link(a, hbl); + this._link(b, halfedges[ar]); + this._link(ar, bl); + + const br = b0 + (b + 1) % 3; + + // don't worry about hitting the cap: it can only happen on extremely degenerate input + if (i < EDGE_STACK.length) { + EDGE_STACK[i++] = br; + } + } else { + if (i === 0) break; + a = EDGE_STACK[--i]; + } + } + + return ar; + } + + _link(a, b) { + this._halfedges[a] = b; + if (b !== -1) this._halfedges[b] = a; + } + + // add a new triangle given vertex indices and adjacent half-edge ids + _addTriangle(i0, i1, i2, a, b, c) { + const t = this.trianglesLen; + + this._triangles[t] = i0; + this._triangles[t + 1] = i1; + this._triangles[t + 2] = i2; + + this._link(t, a); + this._link(t + 1, b); + this._link(t + 2, c); + + this.trianglesLen += 3; + + return t; + } +} + +// monotonically increases with real angle, but doesn't need expensive trigonometry +function pseudoAngle(dx, dy) { + const p = dx / (Math.abs(dx) + Math.abs(dy)); + return (dy > 0 ? 3 - p : 1 + p) / 4; // [0..1] +} + +function dist(ax, ay, bx, by) { + const dx = ax - bx; + const dy = ay - by; + return dx * dx + dy * dy; +} + +function inCircle(ax, ay, bx, by, cx, cy, px, py) { + const dx = ax - px; + const dy = ay - py; + const ex = bx - px; + const ey = by - py; + const fx = cx - px; + const fy = cy - py; + + const ap = dx * dx + dy * dy; + const bp = ex * ex + ey * ey; + const cp = fx * fx + fy * fy; + + return dx * (ey * cp - bp * fy) - + dy * (ex * cp - bp * fx) + + ap * (ex * fy - ey * fx) < 0; +} + +function circumradius(ax, ay, bx, by, cx, cy) { + const dx = bx - ax; + const dy = by - ay; + const ex = cx - ax; + const ey = cy - ay; + + const bl = dx * dx + dy * dy; + const cl = ex * ex + ey * ey; + const d = 0.5 / (dx * ey - dy * ex); + + const x = (ey * bl - dy * cl) * d; + const y = (dx * cl - ex * bl) * d; + + return x * x + y * y; +} + +function circumcenter(ax, ay, bx, by, cx, cy) { + const dx = bx - ax; + const dy = by - ay; + const ex = cx - ax; + const ey = cy - ay; + + const bl = dx * dx + dy * dy; + const cl = ex * ex + ey * ey; + const d = 0.5 / (dx * ey - dy * ex); + + const x = ax + (ey * bl - dy * cl) * d; + const y = ay + (dx * cl - ex * bl) * d; + + return {x, y}; +} + +function quicksort(ids, dists, left, right) { + if (right - left <= 20) { + for (let i = left + 1; i <= right; i++) { + const temp = ids[i]; + const tempDist = dists[temp]; + let j = i - 1; + while (j >= left && dists[ids[j]] > tempDist) ids[j + 1] = ids[j--]; + ids[j + 1] = temp; + } + } else { + const median = (left + right) >> 1; + let i = left + 1; + let j = right; + swap(ids, median, i); + if (dists[ids[left]] > dists[ids[right]]) swap(ids, left, right); + if (dists[ids[i]] > dists[ids[right]]) swap(ids, i, right); + if (dists[ids[left]] > dists[ids[i]]) swap(ids, left, i); + + const temp = ids[i]; + const tempDist = dists[temp]; + while (true) { + do i++; while (dists[ids[i]] < tempDist); + do j--; while (dists[ids[j]] > tempDist); + if (j < i) break; + swap(ids, i, j); + } + ids[left + 1] = ids[j]; + ids[j] = temp; + + if (right - i + 1 >= j - left) { + quicksort(ids, dists, i, right); + quicksort(ids, dists, left, j - 1); + } else { + quicksort(ids, dists, left, j - 1); + quicksort(ids, dists, i, right); + } + } +} + +function swap(arr, i, j) { + const tmp = arr[i]; + arr[i] = arr[j]; + arr[j] = tmp; +} + +function defaultGetX(p) { + return p[0]; +} +function defaultGetY(p) { + return p[1]; +} + +return Delaunator; + +})); diff --git a/frontend/node_modules/delaunator/delaunator.min.js b/frontend/node_modules/delaunator/delaunator.min.js new file mode 100644 index 0000000..a07c909 --- /dev/null +++ b/frontend/node_modules/delaunator/delaunator.min.js @@ -0,0 +1 @@ +!function(t,i){"object"==typeof exports&&"undefined"!=typeof module?module.exports=i():"function"==typeof define&&define.amd?define(i):(t="undefined"!=typeof globalThis?globalThis:t||self).Delaunator=i()}(this,(function(){"use strict";const t=11102230246251565e-32,i=134217729,s=(3+8*t)*t;function e(t,i,s,e,n){let h,r,l,o,a=i[0],f=e[0],c=0,u=0;f>a==f>-a?(h=a,a=i[++c]):(h=f,f=e[++u]);let _=0;if(ca==f>-a?(r=a+h,l=h-(r-a),a=i[++c]):(r=f+h,l=h-(r-f),f=e[++u]),h=r,0!==l&&(n[_++]=l);ca==f>-a?(r=h+a,o=r-h,l=h-(r-o)+(a-o),a=i[++c]):(r=h+f,o=r-h,l=h-(r-o)+(f-o),f=e[++u]),h=r,0!==l&&(n[_++]=l);for(;c=33306690738754716e-32*A?b:-function(t,n,u,_,d,g,y){let w,b,A,k,M,p,x,S,T,z,U,m,K,L,v,F,P,E;const H=t-d,I=u-d,N=n-g,j=_-g;L=H*j,p=i*H,x=p-(p-H),S=H-x,p=i*j,T=p-(p-j),z=j-T,v=S*z-(L-x*T-S*T-x*z),F=N*I,p=i*N,x=p-(p-N),S=N-x,p=i*I,T=p-(p-I),z=I-T,P=S*z-(F-x*T-S*T-x*z),U=v-P,M=v-U,l[0]=v-(U+M)+(M-P),m=L+U,M=m-L,K=L-(m-M)+(U-M),U=K-F,M=K-U,l[1]=K-(U+M)+(M-F),E=m+U,M=E-m,l[2]=m-(E-M)+(U-M),l[3]=E;let q=function(t,i){let s=i[0];for(let e=1;e=D||-q>=D)return q;if(M=t-H,w=t-(H+M)+(M-d),M=u-I,A=u-(I+M)+(M-d),M=n-N,b=n-(N+M)+(M-g),M=_-j,k=_-(j+M)+(M-g),0===w&&0===b&&0===A&&0===k)return q;if(D=r*y+s*Math.abs(q),q+=H*k+j*w-(N*A+I*b),q>=D||-q>=D)return q;L=w*j,p=i*w,x=p-(p-w),S=w-x,p=i*j,T=p-(p-j),z=j-T,v=S*z-(L-x*T-S*T-x*z),F=b*I,p=i*b,x=p-(p-b),S=b-x,p=i*I,T=p-(p-I),z=I-T,P=S*z-(F-x*T-S*T-x*z),U=v-P,M=v-U,c[0]=v-(U+M)+(M-P),m=L+U,M=m-L,K=L-(m-M)+(U-M),U=K-F,M=K-U,c[1]=K-(U+M)+(M-F),E=m+U,M=E-m,c[2]=m-(E-M)+(U-M),c[3]=E;const B=e(4,l,4,c,o);L=H*k,p=i*H,x=p-(p-H),S=H-x,p=i*k,T=p-(p-k),z=k-T,v=S*z-(L-x*T-S*T-x*z),F=N*A,p=i*N,x=p-(p-N),S=N-x,p=i*A,T=p-(p-A),z=A-T,P=S*z-(F-x*T-S*T-x*z),U=v-P,M=v-U,c[0]=v-(U+M)+(M-P),m=L+U,M=m-L,K=L-(m-M)+(U-M),U=K-F,M=K-U,c[1]=K-(U+M)+(M-F),E=m+U,M=E-m,c[2]=m-(E-M)+(U-M),c[3]=E;const C=e(B,o,4,c,a);L=w*k,p=i*w,x=p-(p-w),S=w-x,p=i*k,T=p-(p-k),z=k-T,v=S*z-(L-x*T-S*T-x*z),F=b*A,p=i*b,x=p-(p-b),S=b-x,p=i*A,T=p-(p-A),z=A-T,P=S*z-(F-x*T-S*T-x*z),U=v-P,M=v-U,c[0]=v-(U+M)+(M-P),m=L+U,M=m-L,K=L-(m-M)+(U-M),U=K-F,M=K-U,c[1]=K-(U+M)+(M-F),E=m+U,M=E-m,c[2]=m-(E-M)+(U-M),c[3]=E;const G=e(C,a,4,c,f);return f[G-1]}(t,n,u,_,d,g,A)}const _=Math.pow(2,-52),d=new Uint32Array(512);class g{static from(t,i=M,s=p){const e=t.length,n=new Float64Array(2*e);for(let h=0;h>1;if(i>0&&"number"!=typeof t[0])throw new Error("Expected coords to contain numbers.");this.coords=t;const s=Math.max(2*i-5,0);this._triangles=new Uint32Array(3*s),this._halfedges=new Int32Array(3*s),this._hashSize=Math.ceil(Math.sqrt(i)),this._hullPrev=new Uint32Array(i),this._hullNext=new Uint32Array(i),this._hullTri=new Uint32Array(i),this._hullHash=new Int32Array(this._hashSize),this._ids=new Uint32Array(i),this._dists=new Float64Array(i),this.update()}update(){const{coords:t,_hullPrev:i,_hullNext:s,_hullTri:e,_hullHash:n}=this,h=t.length>>1;let r=1/0,l=1/0,o=-1/0,a=-1/0;for(let i=0;io&&(o=s),e>a&&(a=e),this._ids[i]=i}const f=(r+o)/2,c=(l+a)/2;let d,g,w;for(let i=0,s=1/0;i0&&(g=i,s=e)}let p=t[2*g],x=t[2*g+1],S=1/0;for(let i=0;ie&&(i[s++]=n,e=h)}return this.hull=i.subarray(0,s),this.triangles=new Uint32Array(0),void(this.halfedges=new Uint32Array(0))}if(u(k,M,p,x,T,z)<0){const t=g,i=p,s=x;g=w,p=T,x=z,w=t,T=i,z=s}const U=function(t,i,s,e,n,h){const r=s-t,l=e-i,o=n-t,a=h-i,f=r*r+l*l,c=o*o+a*a,u=.5/(r*a-l*o);return{x:t+(a*f-l*c)*u,y:i+(r*c-o*f)*u}}(k,M,p,x,T,z);this._cx=U.x,this._cy=U.y;for(let i=0;i0&&Math.abs(a-h)<=_&&Math.abs(f-r)<=_)continue;if(h=a,r=f,o===d||o===g||o===w)continue;let c=0;for(let t=0,i=this._hashKey(a,f);t=0;)if(b=y,b===c){b=-1;break}if(-1===b)continue;let A=this._addTriangle(b,o,s[b],-1,-1,e[b]);e[o]=this._legalize(A+2),e[b]=A,m++;let k=s[b];for(;y=s[k],u(a,f,t[2*k],t[2*k+1],t[2*y],t[2*y+1])<0;)A=this._addTriangle(k,o,y,e[o],-1,e[k]),e[o]=this._legalize(A+2),s[k]=k,m--,k=y;if(b===c)for(;y=i[b],u(a,f,t[2*y],t[2*y+1],t[2*b],t[2*b+1])<0;)A=this._addTriangle(y,o,b,-1,e[b],e[y]),this._legalize(A+2),e[y]=A,s[b]=b,m--,b=y;this._hullStart=i[o]=b,s[b]=i[k]=o,s[o]=k,n[this._hashKey(a,f)]=o,n[this._hashKey(t[2*b],t[2*b+1])]=b}this.hull=new Uint32Array(m);for(let t=0,i=this._hullStart;t0?3-s:1+s)/4}(t-this._cx,i-this._cy)*this._hashSize)%this._hashSize}_legalize(t){const{_triangles:i,_halfedges:s,coords:e}=this;let n=0,h=0;for(;;){const r=s[t],l=t-t%3;if(h=l+(t+2)%3,-1===r){if(0===n)break;t=d[--n];continue}const o=r-r%3,a=l+(t+1)%3,f=o+(r+2)%3,c=i[h],u=i[t],_=i[a],g=i[f];if(w(e[2*c],e[2*c+1],e[2*u],e[2*u+1],e[2*_],e[2*_+1],e[2*g],e[2*g+1])){i[t]=g,i[r]=c;const e=s[f];if(-1===e){let i=this._hullStart;do{if(this._hullTri[i]===f){this._hullTri[i]=t;break}i=this._hullPrev[i]}while(i!==this._hullStart)}this._link(t,e),this._link(r,s[h]),this._link(h,f);const l=o+(r+1)%3;n=s&&i[t[r]]>h;)t[r+1]=t[r--];t[r+1]=e}else{let n=s+1,h=e;k(t,s+e>>1,n),i[t[s]]>i[t[e]]&&k(t,s,e),i[t[n]]>i[t[e]]&&k(t,n,e),i[t[s]]>i[t[n]]&&k(t,s,n);const r=t[n],l=i[r];for(;;){do{n++}while(i[t[n]]l);if(h=h-s?(A(t,i,n,e),A(t,i,s,h-1)):(A(t,i,s,h-1),A(t,i,n,e))}}function k(t,i,s){const e=t[i];t[i]=t[s],t[s]=e}function M(t){return t[0]}function p(t){return t[1]}return g})); diff --git a/frontend/node_modules/delaunator/index.js b/frontend/node_modules/delaunator/index.js new file mode 100644 index 0000000..3275551 --- /dev/null +++ b/frontend/node_modules/delaunator/index.js @@ -0,0 +1,480 @@ + +const EPSILON = Math.pow(2, -52); +const EDGE_STACK = new Uint32Array(512); + +import {orient2d} from 'robust-predicates'; + +export default class Delaunator { + + static from(points, getX = defaultGetX, getY = defaultGetY) { + const n = points.length; + const coords = new Float64Array(n * 2); + + for (let i = 0; i < n; i++) { + const p = points[i]; + coords[2 * i] = getX(p); + coords[2 * i + 1] = getY(p); + } + + return new Delaunator(coords); + } + + constructor(coords) { + const n = coords.length >> 1; + if (n > 0 && typeof coords[0] !== 'number') throw new Error('Expected coords to contain numbers.'); + + this.coords = coords; + + // arrays that will store the triangulation graph + const maxTriangles = Math.max(2 * n - 5, 0); + this._triangles = new Uint32Array(maxTriangles * 3); + this._halfedges = new Int32Array(maxTriangles * 3); + + // temporary arrays for tracking the edges of the advancing convex hull + this._hashSize = Math.ceil(Math.sqrt(n)); + this._hullPrev = new Uint32Array(n); // edge to prev edge + this._hullNext = new Uint32Array(n); // edge to next edge + this._hullTri = new Uint32Array(n); // edge to adjacent triangle + this._hullHash = new Int32Array(this._hashSize); // angular edge hash + + // temporary arrays for sorting points + this._ids = new Uint32Array(n); + this._dists = new Float64Array(n); + + this.update(); + } + + update() { + const {coords, _hullPrev: hullPrev, _hullNext: hullNext, _hullTri: hullTri, _hullHash: hullHash} = this; + const n = coords.length >> 1; + + // populate an array of point indices; calculate input data bbox + let minX = Infinity; + let minY = Infinity; + let maxX = -Infinity; + let maxY = -Infinity; + + for (let i = 0; i < n; i++) { + const x = coords[2 * i]; + const y = coords[2 * i + 1]; + if (x < minX) minX = x; + if (y < minY) minY = y; + if (x > maxX) maxX = x; + if (y > maxY) maxY = y; + this._ids[i] = i; + } + const cx = (minX + maxX) / 2; + const cy = (minY + maxY) / 2; + + let i0, i1, i2; + + // pick a seed point close to the center + for (let i = 0, minDist = Infinity; i < n; i++) { + const d = dist(cx, cy, coords[2 * i], coords[2 * i + 1]); + if (d < minDist) { + i0 = i; + minDist = d; + } + } + const i0x = coords[2 * i0]; + const i0y = coords[2 * i0 + 1]; + + // find the point closest to the seed + for (let i = 0, minDist = Infinity; i < n; i++) { + if (i === i0) continue; + const d = dist(i0x, i0y, coords[2 * i], coords[2 * i + 1]); + if (d < minDist && d > 0) { + i1 = i; + minDist = d; + } + } + let i1x = coords[2 * i1]; + let i1y = coords[2 * i1 + 1]; + + let minRadius = Infinity; + + // find the third point which forms the smallest circumcircle with the first two + for (let i = 0; i < n; i++) { + if (i === i0 || i === i1) continue; + const r = circumradius(i0x, i0y, i1x, i1y, coords[2 * i], coords[2 * i + 1]); + if (r < minRadius) { + i2 = i; + minRadius = r; + } + } + let i2x = coords[2 * i2]; + let i2y = coords[2 * i2 + 1]; + + if (minRadius === Infinity) { + // order collinear points by dx (or dy if all x are identical) + // and return the list as a hull + for (let i = 0; i < n; i++) { + this._dists[i] = (coords[2 * i] - coords[0]) || (coords[2 * i + 1] - coords[1]); + } + quicksort(this._ids, this._dists, 0, n - 1); + const hull = new Uint32Array(n); + let j = 0; + for (let i = 0, d0 = -Infinity; i < n; i++) { + const id = this._ids[i]; + const d = this._dists[id]; + if (d > d0) { + hull[j++] = id; + d0 = d; + } + } + this.hull = hull.subarray(0, j); + this.triangles = new Uint32Array(0); + this.halfedges = new Uint32Array(0); + return; + } + + // swap the order of the seed points for counter-clockwise orientation + if (orient2d(i0x, i0y, i1x, i1y, i2x, i2y) < 0) { + const i = i1; + const x = i1x; + const y = i1y; + i1 = i2; + i1x = i2x; + i1y = i2y; + i2 = i; + i2x = x; + i2y = y; + } + + const center = circumcenter(i0x, i0y, i1x, i1y, i2x, i2y); + this._cx = center.x; + this._cy = center.y; + + for (let i = 0; i < n; i++) { + this._dists[i] = dist(coords[2 * i], coords[2 * i + 1], center.x, center.y); + } + + // sort the points by distance from the seed triangle circumcenter + quicksort(this._ids, this._dists, 0, n - 1); + + // set up the seed triangle as the starting hull + this._hullStart = i0; + let hullSize = 3; + + hullNext[i0] = hullPrev[i2] = i1; + hullNext[i1] = hullPrev[i0] = i2; + hullNext[i2] = hullPrev[i1] = i0; + + hullTri[i0] = 0; + hullTri[i1] = 1; + hullTri[i2] = 2; + + hullHash.fill(-1); + hullHash[this._hashKey(i0x, i0y)] = i0; + hullHash[this._hashKey(i1x, i1y)] = i1; + hullHash[this._hashKey(i2x, i2y)] = i2; + + this.trianglesLen = 0; + this._addTriangle(i0, i1, i2, -1, -1, -1); + + for (let k = 0, xp, yp; k < this._ids.length; k++) { + const i = this._ids[k]; + const x = coords[2 * i]; + const y = coords[2 * i + 1]; + + // skip near-duplicate points + if (k > 0 && Math.abs(x - xp) <= EPSILON && Math.abs(y - yp) <= EPSILON) continue; + xp = x; + yp = y; + + // skip seed triangle points + if (i === i0 || i === i1 || i === i2) continue; + + // find a visible edge on the convex hull using edge hash + let start = 0; + for (let j = 0, key = this._hashKey(x, y); j < this._hashSize; j++) { + start = hullHash[(key + j) % this._hashSize]; + if (start !== -1 && start !== hullNext[start]) break; + } + + start = hullPrev[start]; + let e = start, q; + while (q = hullNext[e], orient2d(x, y, coords[2 * e], coords[2 * e + 1], coords[2 * q], coords[2 * q + 1]) >= 0) { + e = q; + if (e === start) { + e = -1; + break; + } + } + if (e === -1) continue; // likely a near-duplicate point; skip it + + // add the first triangle from the point + let t = this._addTriangle(e, i, hullNext[e], -1, -1, hullTri[e]); + + // recursively flip triangles from the point until they satisfy the Delaunay condition + hullTri[i] = this._legalize(t + 2); + hullTri[e] = t; // keep track of boundary triangles on the hull + hullSize++; + + // walk forward through the hull, adding more triangles and flipping recursively + let n = hullNext[e]; + while (q = hullNext[n], orient2d(x, y, coords[2 * n], coords[2 * n + 1], coords[2 * q], coords[2 * q + 1]) < 0) { + t = this._addTriangle(n, i, q, hullTri[i], -1, hullTri[n]); + hullTri[i] = this._legalize(t + 2); + hullNext[n] = n; // mark as removed + hullSize--; + n = q; + } + + // walk backward from the other side, adding more triangles and flipping + if (e === start) { + while (q = hullPrev[e], orient2d(x, y, coords[2 * q], coords[2 * q + 1], coords[2 * e], coords[2 * e + 1]) < 0) { + t = this._addTriangle(q, i, e, -1, hullTri[e], hullTri[q]); + this._legalize(t + 2); + hullTri[q] = t; + hullNext[e] = e; // mark as removed + hullSize--; + e = q; + } + } + + // update the hull indices + this._hullStart = hullPrev[i] = e; + hullNext[e] = hullPrev[n] = i; + hullNext[i] = n; + + // save the two new edges in the hash table + hullHash[this._hashKey(x, y)] = i; + hullHash[this._hashKey(coords[2 * e], coords[2 * e + 1])] = e; + } + + this.hull = new Uint32Array(hullSize); + for (let i = 0, e = this._hullStart; i < hullSize; i++) { + this.hull[i] = e; + e = hullNext[e]; + } + + // trim typed triangle mesh arrays + this.triangles = this._triangles.subarray(0, this.trianglesLen); + this.halfedges = this._halfedges.subarray(0, this.trianglesLen); + } + + _hashKey(x, y) { + return Math.floor(pseudoAngle(x - this._cx, y - this._cy) * this._hashSize) % this._hashSize; + } + + _legalize(a) { + const {_triangles: triangles, _halfedges: halfedges, coords} = this; + + let i = 0; + let ar = 0; + + // recursion eliminated with a fixed-size stack + while (true) { + const b = halfedges[a]; + + /* if the pair of triangles doesn't satisfy the Delaunay condition + * (p1 is inside the circumcircle of [p0, pl, pr]), flip them, + * then do the same check/flip recursively for the new pair of triangles + * + * pl pl + * /||\ / \ + * al/ || \bl al/ \a + * / || \ / \ + * / a||b \ flip /___ar___\ + * p0\ || /p1 => p0\---bl---/p1 + * \ || / \ / + * ar\ || /br b\ /br + * \||/ \ / + * pr pr + */ + const a0 = a - a % 3; + ar = a0 + (a + 2) % 3; + + if (b === -1) { // convex hull edge + if (i === 0) break; + a = EDGE_STACK[--i]; + continue; + } + + const b0 = b - b % 3; + const al = a0 + (a + 1) % 3; + const bl = b0 + (b + 2) % 3; + + const p0 = triangles[ar]; + const pr = triangles[a]; + const pl = triangles[al]; + const p1 = triangles[bl]; + + const illegal = inCircle( + coords[2 * p0], coords[2 * p0 + 1], + coords[2 * pr], coords[2 * pr + 1], + coords[2 * pl], coords[2 * pl + 1], + coords[2 * p1], coords[2 * p1 + 1]); + + if (illegal) { + triangles[a] = p1; + triangles[b] = p0; + + const hbl = halfedges[bl]; + + // edge swapped on the other side of the hull (rare); fix the halfedge reference + if (hbl === -1) { + let e = this._hullStart; + do { + if (this._hullTri[e] === bl) { + this._hullTri[e] = a; + break; + } + e = this._hullPrev[e]; + } while (e !== this._hullStart); + } + this._link(a, hbl); + this._link(b, halfedges[ar]); + this._link(ar, bl); + + const br = b0 + (b + 1) % 3; + + // don't worry about hitting the cap: it can only happen on extremely degenerate input + if (i < EDGE_STACK.length) { + EDGE_STACK[i++] = br; + } + } else { + if (i === 0) break; + a = EDGE_STACK[--i]; + } + } + + return ar; + } + + _link(a, b) { + this._halfedges[a] = b; + if (b !== -1) this._halfedges[b] = a; + } + + // add a new triangle given vertex indices and adjacent half-edge ids + _addTriangle(i0, i1, i2, a, b, c) { + const t = this.trianglesLen; + + this._triangles[t] = i0; + this._triangles[t + 1] = i1; + this._triangles[t + 2] = i2; + + this._link(t, a); + this._link(t + 1, b); + this._link(t + 2, c); + + this.trianglesLen += 3; + + return t; + } +} + +// monotonically increases with real angle, but doesn't need expensive trigonometry +function pseudoAngle(dx, dy) { + const p = dx / (Math.abs(dx) + Math.abs(dy)); + return (dy > 0 ? 3 - p : 1 + p) / 4; // [0..1] +} + +function dist(ax, ay, bx, by) { + const dx = ax - bx; + const dy = ay - by; + return dx * dx + dy * dy; +} + +function inCircle(ax, ay, bx, by, cx, cy, px, py) { + const dx = ax - px; + const dy = ay - py; + const ex = bx - px; + const ey = by - py; + const fx = cx - px; + const fy = cy - py; + + const ap = dx * dx + dy * dy; + const bp = ex * ex + ey * ey; + const cp = fx * fx + fy * fy; + + return dx * (ey * cp - bp * fy) - + dy * (ex * cp - bp * fx) + + ap * (ex * fy - ey * fx) < 0; +} + +function circumradius(ax, ay, bx, by, cx, cy) { + const dx = bx - ax; + const dy = by - ay; + const ex = cx - ax; + const ey = cy - ay; + + const bl = dx * dx + dy * dy; + const cl = ex * ex + ey * ey; + const d = 0.5 / (dx * ey - dy * ex); + + const x = (ey * bl - dy * cl) * d; + const y = (dx * cl - ex * bl) * d; + + return x * x + y * y; +} + +function circumcenter(ax, ay, bx, by, cx, cy) { + const dx = bx - ax; + const dy = by - ay; + const ex = cx - ax; + const ey = cy - ay; + + const bl = dx * dx + dy * dy; + const cl = ex * ex + ey * ey; + const d = 0.5 / (dx * ey - dy * ex); + + const x = ax + (ey * bl - dy * cl) * d; + const y = ay + (dx * cl - ex * bl) * d; + + return {x, y}; +} + +function quicksort(ids, dists, left, right) { + if (right - left <= 20) { + for (let i = left + 1; i <= right; i++) { + const temp = ids[i]; + const tempDist = dists[temp]; + let j = i - 1; + while (j >= left && dists[ids[j]] > tempDist) ids[j + 1] = ids[j--]; + ids[j + 1] = temp; + } + } else { + const median = (left + right) >> 1; + let i = left + 1; + let j = right; + swap(ids, median, i); + if (dists[ids[left]] > dists[ids[right]]) swap(ids, left, right); + if (dists[ids[i]] > dists[ids[right]]) swap(ids, i, right); + if (dists[ids[left]] > dists[ids[i]]) swap(ids, left, i); + + const temp = ids[i]; + const tempDist = dists[temp]; + while (true) { + do i++; while (dists[ids[i]] < tempDist); + do j--; while (dists[ids[j]] > tempDist); + if (j < i) break; + swap(ids, i, j); + } + ids[left + 1] = ids[j]; + ids[j] = temp; + + if (right - i + 1 >= j - left) { + quicksort(ids, dists, i, right); + quicksort(ids, dists, left, j - 1); + } else { + quicksort(ids, dists, left, j - 1); + quicksort(ids, dists, i, right); + } + } +} + +function swap(arr, i, j) { + const tmp = arr[i]; + arr[i] = arr[j]; + arr[j] = tmp; +} + +function defaultGetX(p) { + return p[0]; +} +function defaultGetY(p) { + return p[1]; +} diff --git a/frontend/node_modules/delaunator/package.json b/frontend/node_modules/delaunator/package.json new file mode 100644 index 0000000..b1b68f3 --- /dev/null +++ b/frontend/node_modules/delaunator/package.json @@ -0,0 +1,56 @@ +{ + "name": "delaunator", + "version": "5.0.1", + "description": "An incredibly fast JavaScript library for Delaunay triangulation of 2D points", + "main": "index.js", + "module": "index.js", + "type": "module", + "jsdelivr": "delaunator.min.js", + "unpkg": "delaunator.min.js", + "sideEffects": false, + "dependencies": { + "robust-predicates": "^3.0.2" + }, + "devDependencies": { + "@rollup/plugin-node-resolve": "^15.2.3", + "@rollup/plugin-terser": "^0.4.4", + "eslint": "^8.56.0", + "eslint-config-mourner": "^3.0.0", + "rollup": "^4.9.6" + }, + "repository": { + "type": "git", + "url": "https://github.com/mapbox/delaunator.git" + }, + "scripts": { + "lint": "eslint index.js test/test.js bench.js rollup.config.js docs/diagrams.js", + "pretest": "npm run lint", + "test": "node --test-reporter spec test/test.js", + "cov": "node --experimental-test-coverage test/test.js", + "bench": "node bench.js", + "build": "rollup -c", + "start": "rollup -cw", + "prepublishOnly": "npm test && npm run build" + }, + "files": [ + "index.js", + "delaunator.js", + "delaunator.min.js" + ], + "eslintConfig": { + "extends": "mourner", + "rules": { + "no-sequences": 0 + }, + "parserOptions": { + "ecmaVersion": 2020 + } + }, + "keywords": [ + "delaunay triangulation", + "computational geometry", + "algorithms" + ], + "author": "Vladimir Agafonkin", + "license": "ISC" +} diff --git a/frontend/node_modules/dom-serializer/LICENSE b/frontend/node_modules/dom-serializer/LICENSE new file mode 100644 index 0000000..3d241a8 --- /dev/null +++ b/frontend/node_modules/dom-serializer/LICENSE @@ -0,0 +1,11 @@ +License + +(The MIT License) + +Copyright (c) 2014 The cheeriojs contributors + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the 'Software'), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/frontend/node_modules/dom-serializer/README.md b/frontend/node_modules/dom-serializer/README.md new file mode 100644 index 0000000..0a301ab --- /dev/null +++ b/frontend/node_modules/dom-serializer/README.md @@ -0,0 +1,109 @@ +# dom-serializer [![Build Status](https://travis-ci.com/cheeriojs/dom-serializer.svg?branch=master)](https://travis-ci.com/cheeriojs/dom-serializer) + +Renders a [domhandler](https://github.com/fb55/domhandler) DOM node or an array of domhandler DOM nodes to a string. + +```js +import render from "dom-serializer"; + +// OR + +const render = require("dom-serializer").default; +``` + +# API + +## `render` + +▸ **render**(`node`: Node \| Node[], `options?`: [_Options_](#Options)): _string_ + +Renders a DOM node or an array of DOM nodes to a string. + +Can be thought of as the equivalent of the `outerHTML` of the passed node(s). + +#### Parameters: + +| Name | Type | Default value | Description | +| :-------- | :--------------------------------- | :------------ | :----------------------------- | +| `node` | Node \| Node[] | - | Node to be rendered. | +| `options` | [_DomSerializerOptions_](#Options) | {} | Changes serialization behavior | + +**Returns:** _string_ + +## Options + +### `encodeEntities` + +• `Optional` **decodeEntities**: _boolean | "utf8"_ + +Encode characters that are either reserved in HTML or XML. + +If `xmlMode` is `true` or the value not `'utf8'`, characters outside of the utf8 range will be encoded as well. + +**`default`** `decodeEntities` + +--- + +### `decodeEntities` + +• `Optional` **decodeEntities**: _boolean_ + +Option inherited from parsing; will be used as the default value for `encodeEntities`. + +**`default`** true + +--- + +### `emptyAttrs` + +• `Optional` **emptyAttrs**: _boolean_ + +Print an empty attribute's value. + +**`default`** xmlMode + +**`example`** With emptyAttrs: false: <input checked> + +**`example`** With emptyAttrs: true: <input checked=""> + +--- + +### `selfClosingTags` + +• `Optional` **selfClosingTags**: _boolean_ + +Print self-closing tags for tags without contents. + +**`default`** xmlMode + +**`example`** With selfClosingTags: false: <foo></foo> + +**`example`** With selfClosingTags: true: <foo /> + +--- + +### `xmlMode` + +• `Optional` **xmlMode**: _boolean_ \| _"foreign"_ + +Treat the input as an XML document; enables the `emptyAttrs` and `selfClosingTags` options. + +If the value is `"foreign"`, it will try to correct mixed-case attribute names. + +**`default`** false + +--- + +## Ecosystem + +| Name | Description | +| ------------------------------------------------------------- | ------------------------------------------------------- | +| [htmlparser2](https://github.com/fb55/htmlparser2) | Fast & forgiving HTML/XML parser | +| [domhandler](https://github.com/fb55/domhandler) | Handler for htmlparser2 that turns documents into a DOM | +| [domutils](https://github.com/fb55/domutils) | Utilities for working with domhandler's DOM | +| [css-select](https://github.com/fb55/css-select) | CSS selector engine, compatible with domhandler's DOM | +| [cheerio](https://github.com/cheeriojs/cheerio) | The jQuery API for domhandler's DOM | +| [dom-serializer](https://github.com/cheeriojs/dom-serializer) | Serializer for domhandler's DOM | + +--- + +LICENSE: MIT diff --git a/frontend/node_modules/dom-serializer/lib/esm/foreignNames.d.ts b/frontend/node_modules/dom-serializer/lib/esm/foreignNames.d.ts new file mode 100644 index 0000000..a8b0938 --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/esm/foreignNames.d.ts @@ -0,0 +1,3 @@ +export declare const elementNames: Map; +export declare const attributeNames: Map; +//# sourceMappingURL=foreignNames.d.ts.map \ No newline at end of file diff --git a/frontend/node_modules/dom-serializer/lib/esm/foreignNames.d.ts.map b/frontend/node_modules/dom-serializer/lib/esm/foreignNames.d.ts.map new file mode 100644 index 0000000..f471fd0 --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/esm/foreignNames.d.ts.map @@ -0,0 +1 @@ +{"version":3,"file":"foreignNames.d.ts","sourceRoot":"","sources":["../../src/foreignNames.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,YAAY,qBAwCxB,CAAC;AACF,eAAO,MAAM,cAAc,qBA8D1B,CAAC"} \ No newline at end of file diff --git a/frontend/node_modules/dom-serializer/lib/esm/foreignNames.js b/frontend/node_modules/dom-serializer/lib/esm/foreignNames.js new file mode 100644 index 0000000..ebd6272 --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/esm/foreignNames.js @@ -0,0 +1,100 @@ +export const elementNames = new Map([ + "altGlyph", + "altGlyphDef", + "altGlyphItem", + "animateColor", + "animateMotion", + "animateTransform", + "clipPath", + "feBlend", + "feColorMatrix", + "feComponentTransfer", + "feComposite", + "feConvolveMatrix", + "feDiffuseLighting", + "feDisplacementMap", + "feDistantLight", + "feDropShadow", + "feFlood", + "feFuncA", + "feFuncB", + "feFuncG", + "feFuncR", + "feGaussianBlur", + "feImage", + "feMerge", + "feMergeNode", + "feMorphology", + "feOffset", + "fePointLight", + "feSpecularLighting", + "feSpotLight", + "feTile", + "feTurbulence", + "foreignObject", + "glyphRef", + "linearGradient", + "radialGradient", + "textPath", +].map((val) => [val.toLowerCase(), val])); +export const attributeNames = new Map([ + "definitionURL", + "attributeName", + "attributeType", + "baseFrequency", + "baseProfile", + "calcMode", + "clipPathUnits", + "diffuseConstant", + "edgeMode", + "filterUnits", + "glyphRef", + "gradientTransform", + "gradientUnits", + "kernelMatrix", + "kernelUnitLength", + "keyPoints", + "keySplines", + "keyTimes", + "lengthAdjust", + "limitingConeAngle", + "markerHeight", + "markerUnits", + "markerWidth", + "maskContentUnits", + "maskUnits", + "numOctaves", + "pathLength", + "patternContentUnits", + "patternTransform", + "patternUnits", + "pointsAtX", + "pointsAtY", + "pointsAtZ", + "preserveAlpha", + "preserveAspectRatio", + "primitiveUnits", + "refX", + "refY", + "repeatCount", + "repeatDur", + "requiredExtensions", + "requiredFeatures", + "specularConstant", + "specularExponent", + "spreadMethod", + "startOffset", + "stdDeviation", + "stitchTiles", + "surfaceScale", + "systemLanguage", + "tableValues", + "targetX", + "targetY", + "textLength", + "viewBox", + "viewTarget", + "xChannelSelector", + "yChannelSelector", + "zoomAndPan", +].map((val) => [val.toLowerCase(), val])); diff --git a/frontend/node_modules/dom-serializer/lib/esm/index.d.ts b/frontend/node_modules/dom-serializer/lib/esm/index.d.ts new file mode 100644 index 0000000..cdf04f0 --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/esm/index.d.ts @@ -0,0 +1,52 @@ +import type { AnyNode } from "domhandler"; +export interface DomSerializerOptions { + /** + * Print an empty attribute's value. + * + * @default xmlMode + * @example With emptyAttrs: false: <input checked> + * @example With emptyAttrs: true: <input checked=""> + */ + emptyAttrs?: boolean; + /** + * Print self-closing tags for tags without contents. + * + * @default xmlMode + * @example With selfClosingTags: false: <foo></foo> + * @example With selfClosingTags: true: <foo /> + */ + selfClosingTags?: boolean; + /** + * Treat the input as an XML document; enables the `emptyAttrs` and `selfClosingTags` options. + * + * If the value is `"foreign"`, it will try to correct mixed-case attribute names. + * + * @default false + */ + xmlMode?: boolean | "foreign"; + /** + * Encode characters that are either reserved in HTML or XML. + * + * If `xmlMode` is `true` or the value not `'utf8'`, characters outside of the utf8 range will be encoded as well. + * + * @default `decodeEntities` + */ + encodeEntities?: boolean | "utf8"; + /** + * Option inherited from parsing; will be used as the default value for `encodeEntities`. + * + * @default true + */ + decodeEntities?: boolean; +} +/** + * Renders a DOM node or an array of DOM nodes to a string. + * + * Can be thought of as the equivalent of the `outerHTML` of the passed node(s). + * + * @param node Node to be rendered. + * @param options Changes serialization behavior + */ +export declare function render(node: AnyNode | ArrayLike, options?: DomSerializerOptions): string; +export default render; +//# sourceMappingURL=index.d.ts.map \ No newline at end of file diff --git a/frontend/node_modules/dom-serializer/lib/esm/index.d.ts.map b/frontend/node_modules/dom-serializer/lib/esm/index.d.ts.map new file mode 100644 index 0000000..0476a46 --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/esm/index.d.ts.map @@ -0,0 +1 @@ +{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EACV,OAAO,EAMR,MAAM,YAAY,CAAC;AAWpB,MAAM,WAAW,oBAAoB;IACnC;;;;;;OAMG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB;;;;;;OAMG;IACH,eAAe,CAAC,EAAE,OAAO,CAAC;IAC1B;;;;;;OAMG;IACH,OAAO,CAAC,EAAE,OAAO,GAAG,SAAS,CAAC;IAC9B;;;;;;OAMG;IACH,cAAc,CAAC,EAAE,OAAO,GAAG,MAAM,CAAC;IAClC;;;;OAIG;IACH,cAAc,CAAC,EAAE,OAAO,CAAC;CAC1B;AA4ED;;;;;;;GAOG;AACH,wBAAgB,MAAM,CACpB,IAAI,EAAE,OAAO,GAAG,SAAS,CAAC,OAAO,CAAC,EAClC,OAAO,GAAE,oBAAyB,GACjC,MAAM,CAUR;AAED,eAAe,MAAM,CAAC"} \ No newline at end of file diff --git a/frontend/node_modules/dom-serializer/lib/esm/index.js b/frontend/node_modules/dom-serializer/lib/esm/index.js new file mode 100644 index 0000000..1ccc9d5 --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/esm/index.js @@ -0,0 +1,190 @@ +/* + * Module dependencies + */ +import * as ElementType from "domelementtype"; +import { encodeXML, escapeAttribute, escapeText } from "entities"; +/** + * Mixed-case SVG and MathML tags & attributes + * recognized by the HTML parser. + * + * @see https://html.spec.whatwg.org/multipage/parsing.html#parsing-main-inforeign + */ +import { elementNames, attributeNames } from "./foreignNames.js"; +const unencodedElements = new Set([ + "style", + "script", + "xmp", + "iframe", + "noembed", + "noframes", + "plaintext", + "noscript", +]); +function replaceQuotes(value) { + return value.replace(/"/g, """); +} +/** + * Format attributes + */ +function formatAttributes(attributes, opts) { + var _a; + if (!attributes) + return; + const encode = ((_a = opts.encodeEntities) !== null && _a !== void 0 ? _a : opts.decodeEntities) === false + ? replaceQuotes + : opts.xmlMode || opts.encodeEntities !== "utf8" + ? encodeXML + : escapeAttribute; + return Object.keys(attributes) + .map((key) => { + var _a, _b; + const value = (_a = attributes[key]) !== null && _a !== void 0 ? _a : ""; + if (opts.xmlMode === "foreign") { + /* Fix up mixed-case attribute names */ + key = (_b = attributeNames.get(key)) !== null && _b !== void 0 ? _b : key; + } + if (!opts.emptyAttrs && !opts.xmlMode && value === "") { + return key; + } + return `${key}="${encode(value)}"`; + }) + .join(" "); +} +/** + * Self-enclosing tags + */ +const singleTag = new Set([ + "area", + "base", + "basefont", + "br", + "col", + "command", + "embed", + "frame", + "hr", + "img", + "input", + "isindex", + "keygen", + "link", + "meta", + "param", + "source", + "track", + "wbr", +]); +/** + * Renders a DOM node or an array of DOM nodes to a string. + * + * Can be thought of as the equivalent of the `outerHTML` of the passed node(s). + * + * @param node Node to be rendered. + * @param options Changes serialization behavior + */ +export function render(node, options = {}) { + const nodes = "length" in node ? node : [node]; + let output = ""; + for (let i = 0; i < nodes.length; i++) { + output += renderNode(nodes[i], options); + } + return output; +} +export default render; +function renderNode(node, options) { + switch (node.type) { + case ElementType.Root: + return render(node.children, options); + // @ts-expect-error We don't use `Doctype` yet + case ElementType.Doctype: + case ElementType.Directive: + return renderDirective(node); + case ElementType.Comment: + return renderComment(node); + case ElementType.CDATA: + return renderCdata(node); + case ElementType.Script: + case ElementType.Style: + case ElementType.Tag: + return renderTag(node, options); + case ElementType.Text: + return renderText(node, options); + } +} +const foreignModeIntegrationPoints = new Set([ + "mi", + "mo", + "mn", + "ms", + "mtext", + "annotation-xml", + "foreignObject", + "desc", + "title", +]); +const foreignElements = new Set(["svg", "math"]); +function renderTag(elem, opts) { + var _a; + // Handle SVG / MathML in HTML + if (opts.xmlMode === "foreign") { + /* Fix up mixed-case element names */ + elem.name = (_a = elementNames.get(elem.name)) !== null && _a !== void 0 ? _a : elem.name; + /* Exit foreign mode at integration points */ + if (elem.parent && + foreignModeIntegrationPoints.has(elem.parent.name)) { + opts = { ...opts, xmlMode: false }; + } + } + if (!opts.xmlMode && foreignElements.has(elem.name)) { + opts = { ...opts, xmlMode: "foreign" }; + } + let tag = `<${elem.name}`; + const attribs = formatAttributes(elem.attribs, opts); + if (attribs) { + tag += ` ${attribs}`; + } + if (elem.children.length === 0 && + (opts.xmlMode + ? // In XML mode or foreign mode, and user hasn't explicitly turned off self-closing tags + opts.selfClosingTags !== false + : // User explicitly asked for self-closing tags, even in HTML mode + opts.selfClosingTags && singleTag.has(elem.name))) { + if (!opts.xmlMode) + tag += " "; + tag += "/>"; + } + else { + tag += ">"; + if (elem.children.length > 0) { + tag += render(elem.children, opts); + } + if (opts.xmlMode || !singleTag.has(elem.name)) { + tag += ``; + } + } + return tag; +} +function renderDirective(elem) { + return `<${elem.data}>`; +} +function renderText(elem, opts) { + var _a; + let data = elem.data || ""; + // If entities weren't decoded, no need to encode them back + if (((_a = opts.encodeEntities) !== null && _a !== void 0 ? _a : opts.decodeEntities) !== false && + !(!opts.xmlMode && + elem.parent && + unencodedElements.has(elem.parent.name))) { + data = + opts.xmlMode || opts.encodeEntities !== "utf8" + ? encodeXML(data) + : escapeText(data); + } + return data; +} +function renderCdata(elem) { + return ``; +} +function renderComment(elem) { + return ``; +} diff --git a/frontend/node_modules/dom-serializer/lib/esm/package.json b/frontend/node_modules/dom-serializer/lib/esm/package.json new file mode 100644 index 0000000..089153b --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/esm/package.json @@ -0,0 +1 @@ +{"type":"module"} diff --git a/frontend/node_modules/dom-serializer/lib/foreignNames.d.ts b/frontend/node_modules/dom-serializer/lib/foreignNames.d.ts new file mode 100644 index 0000000..a8b0938 --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/foreignNames.d.ts @@ -0,0 +1,3 @@ +export declare const elementNames: Map; +export declare const attributeNames: Map; +//# sourceMappingURL=foreignNames.d.ts.map \ No newline at end of file diff --git a/frontend/node_modules/dom-serializer/lib/foreignNames.d.ts.map b/frontend/node_modules/dom-serializer/lib/foreignNames.d.ts.map new file mode 100644 index 0000000..bc1d2d0 --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/foreignNames.d.ts.map @@ -0,0 +1 @@ +{"version":3,"file":"foreignNames.d.ts","sourceRoot":"","sources":["../src/foreignNames.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,YAAY,qBAwCxB,CAAC;AACF,eAAO,MAAM,cAAc,qBA8D1B,CAAC"} \ No newline at end of file diff --git a/frontend/node_modules/dom-serializer/lib/foreignNames.js b/frontend/node_modules/dom-serializer/lib/foreignNames.js new file mode 100644 index 0000000..3b24b75 --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/foreignNames.js @@ -0,0 +1,103 @@ +"use strict"; +Object.defineProperty(exports, "__esModule", { value: true }); +exports.attributeNames = exports.elementNames = void 0; +exports.elementNames = new Map([ + "altGlyph", + "altGlyphDef", + "altGlyphItem", + "animateColor", + "animateMotion", + "animateTransform", + "clipPath", + "feBlend", + "feColorMatrix", + "feComponentTransfer", + "feComposite", + "feConvolveMatrix", + "feDiffuseLighting", + "feDisplacementMap", + "feDistantLight", + "feDropShadow", + "feFlood", + "feFuncA", + "feFuncB", + "feFuncG", + "feFuncR", + "feGaussianBlur", + "feImage", + "feMerge", + "feMergeNode", + "feMorphology", + "feOffset", + "fePointLight", + "feSpecularLighting", + "feSpotLight", + "feTile", + "feTurbulence", + "foreignObject", + "glyphRef", + "linearGradient", + "radialGradient", + "textPath", +].map(function (val) { return [val.toLowerCase(), val]; })); +exports.attributeNames = new Map([ + "definitionURL", + "attributeName", + "attributeType", + "baseFrequency", + "baseProfile", + "calcMode", + "clipPathUnits", + "diffuseConstant", + "edgeMode", + "filterUnits", + "glyphRef", + "gradientTransform", + "gradientUnits", + "kernelMatrix", + "kernelUnitLength", + "keyPoints", + "keySplines", + "keyTimes", + "lengthAdjust", + "limitingConeAngle", + "markerHeight", + "markerUnits", + "markerWidth", + "maskContentUnits", + "maskUnits", + "numOctaves", + "pathLength", + "patternContentUnits", + "patternTransform", + "patternUnits", + "pointsAtX", + "pointsAtY", + "pointsAtZ", + "preserveAlpha", + "preserveAspectRatio", + "primitiveUnits", + "refX", + "refY", + "repeatCount", + "repeatDur", + "requiredExtensions", + "requiredFeatures", + "specularConstant", + "specularExponent", + "spreadMethod", + "startOffset", + "stdDeviation", + "stitchTiles", + "surfaceScale", + "systemLanguage", + "tableValues", + "targetX", + "targetY", + "textLength", + "viewBox", + "viewTarget", + "xChannelSelector", + "yChannelSelector", + "zoomAndPan", +].map(function (val) { return [val.toLowerCase(), val]; })); diff --git a/frontend/node_modules/dom-serializer/lib/index.d.ts b/frontend/node_modules/dom-serializer/lib/index.d.ts new file mode 100644 index 0000000..cdf04f0 --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/index.d.ts @@ -0,0 +1,52 @@ +import type { AnyNode } from "domhandler"; +export interface DomSerializerOptions { + /** + * Print an empty attribute's value. + * + * @default xmlMode + * @example With emptyAttrs: false: <input checked> + * @example With emptyAttrs: true: <input checked=""> + */ + emptyAttrs?: boolean; + /** + * Print self-closing tags for tags without contents. + * + * @default xmlMode + * @example With selfClosingTags: false: <foo></foo> + * @example With selfClosingTags: true: <foo /> + */ + selfClosingTags?: boolean; + /** + * Treat the input as an XML document; enables the `emptyAttrs` and `selfClosingTags` options. + * + * If the value is `"foreign"`, it will try to correct mixed-case attribute names. + * + * @default false + */ + xmlMode?: boolean | "foreign"; + /** + * Encode characters that are either reserved in HTML or XML. + * + * If `xmlMode` is `true` or the value not `'utf8'`, characters outside of the utf8 range will be encoded as well. + * + * @default `decodeEntities` + */ + encodeEntities?: boolean | "utf8"; + /** + * Option inherited from parsing; will be used as the default value for `encodeEntities`. + * + * @default true + */ + decodeEntities?: boolean; +} +/** + * Renders a DOM node or an array of DOM nodes to a string. + * + * Can be thought of as the equivalent of the `outerHTML` of the passed node(s). + * + * @param node Node to be rendered. + * @param options Changes serialization behavior + */ +export declare function render(node: AnyNode | ArrayLike, options?: DomSerializerOptions): string; +export default render; +//# sourceMappingURL=index.d.ts.map \ No newline at end of file diff --git a/frontend/node_modules/dom-serializer/lib/index.d.ts.map b/frontend/node_modules/dom-serializer/lib/index.d.ts.map new file mode 100644 index 0000000..6d9d0b6 --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/index.d.ts.map @@ -0,0 +1 @@ +{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EACV,OAAO,EAMR,MAAM,YAAY,CAAC;AAWpB,MAAM,WAAW,oBAAoB;IACnC;;;;;;OAMG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB;;;;;;OAMG;IACH,eAAe,CAAC,EAAE,OAAO,CAAC;IAC1B;;;;;;OAMG;IACH,OAAO,CAAC,EAAE,OAAO,GAAG,SAAS,CAAC;IAC9B;;;;;;OAMG;IACH,cAAc,CAAC,EAAE,OAAO,GAAG,MAAM,CAAC;IAClC;;;;OAIG;IACH,cAAc,CAAC,EAAE,OAAO,CAAC;CAC1B;AA4ED;;;;;;;GAOG;AACH,wBAAgB,MAAM,CACpB,IAAI,EAAE,OAAO,GAAG,SAAS,CAAC,OAAO,CAAC,EAClC,OAAO,GAAE,oBAAyB,GACjC,MAAM,CAUR;AAED,eAAe,MAAM,CAAC"} \ No newline at end of file diff --git a/frontend/node_modules/dom-serializer/lib/index.js b/frontend/node_modules/dom-serializer/lib/index.js new file mode 100644 index 0000000..af996ff --- /dev/null +++ b/frontend/node_modules/dom-serializer/lib/index.js @@ -0,0 +1,229 @@ +"use strict"; +var __assign = (this && this.__assign) || function () { + __assign = Object.assign || function(t) { + for (var s, i = 1, n = arguments.length; i < n; i++) { + s = arguments[i]; + for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) + t[p] = s[p]; + } + return t; + }; + return __assign.apply(this, arguments); +}; +var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) { + if (k2 === undefined) k2 = k; + var desc = Object.getOwnPropertyDescriptor(m, k); + if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) { + desc = { enumerable: true, get: function() { return m[k]; } }; + } + Object.defineProperty(o, k2, desc); +}) : (function(o, m, k, k2) { + if (k2 === undefined) k2 = k; + o[k2] = m[k]; +})); +var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) { + Object.defineProperty(o, "default", { enumerable: true, value: v }); +}) : function(o, v) { + o["default"] = v; +}); +var __importStar = (this && this.__importStar) || function (mod) { + if (mod && mod.__esModule) return mod; + var result = {}; + if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k); + __setModuleDefault(result, mod); + return result; +}; +Object.defineProperty(exports, "__esModule", { value: true }); +exports.render = void 0; +/* + * Module dependencies + */ +var ElementType = __importStar(require("domelementtype")); +var entities_1 = require("entities"); +/** + * Mixed-case SVG and MathML tags & attributes + * recognized by the HTML parser. + * + * @see https://html.spec.whatwg.org/multipage/parsing.html#parsing-main-inforeign + */ +var foreignNames_js_1 = require("./foreignNames.js"); +var unencodedElements = new Set([ + "style", + "script", + "xmp", + "iframe", + "noembed", + "noframes", + "plaintext", + "noscript", +]); +function replaceQuotes(value) { + return value.replace(/"/g, """); +} +/** + * Format attributes + */ +function formatAttributes(attributes, opts) { + var _a; + if (!attributes) + return; + var encode = ((_a = opts.encodeEntities) !== null && _a !== void 0 ? _a : opts.decodeEntities) === false + ? replaceQuotes + : opts.xmlMode || opts.encodeEntities !== "utf8" + ? entities_1.encodeXML + : entities_1.escapeAttribute; + return Object.keys(attributes) + .map(function (key) { + var _a, _b; + var value = (_a = attributes[key]) !== null && _a !== void 0 ? _a : ""; + if (opts.xmlMode === "foreign") { + /* Fix up mixed-case attribute names */ + key = (_b = foreignNames_js_1.attributeNames.get(key)) !== null && _b !== void 0 ? _b : key; + } + if (!opts.emptyAttrs && !opts.xmlMode && value === "") { + return key; + } + return "".concat(key, "=\"").concat(encode(value), "\""); + }) + .join(" "); +} +/** + * Self-enclosing tags + */ +var singleTag = new Set([ + "area", + "base", + "basefont", + "br", + "col", + "command", + "embed", + "frame", + "hr", + "img", + "input", + "isindex", + "keygen", + "link", + "meta", + "param", + "source", + "track", + "wbr", +]); +/** + * Renders a DOM node or an array of DOM nodes to a string. + * + * Can be thought of as the equivalent of the `outerHTML` of the passed node(s). + * + * @param node Node to be rendered. + * @param options Changes serialization behavior + */ +function render(node, options) { + if (options === void 0) { options = {}; } + var nodes = "length" in node ? node : [node]; + var output = ""; + for (var i = 0; i < nodes.length; i++) { + output += renderNode(nodes[i], options); + } + return output; +} +exports.render = render; +exports.default = render; +function renderNode(node, options) { + switch (node.type) { + case ElementType.Root: + return render(node.children, options); + // @ts-expect-error We don't use `Doctype` yet + case ElementType.Doctype: + case ElementType.Directive: + return renderDirective(node); + case ElementType.Comment: + return renderComment(node); + case ElementType.CDATA: + return renderCdata(node); + case ElementType.Script: + case ElementType.Style: + case ElementType.Tag: + return renderTag(node, options); + case ElementType.Text: + return renderText(node, options); + } +} +var foreignModeIntegrationPoints = new Set([ + "mi", + "mo", + "mn", + "ms", + "mtext", + "annotation-xml", + "foreignObject", + "desc", + "title", +]); +var foreignElements = new Set(["svg", "math"]); +function renderTag(elem, opts) { + var _a; + // Handle SVG / MathML in HTML + if (opts.xmlMode === "foreign") { + /* Fix up mixed-case element names */ + elem.name = (_a = foreignNames_js_1.elementNames.get(elem.name)) !== null && _a !== void 0 ? _a : elem.name; + /* Exit foreign mode at integration points */ + if (elem.parent && + foreignModeIntegrationPoints.has(elem.parent.name)) { + opts = __assign(__assign({}, opts), { xmlMode: false }); + } + } + if (!opts.xmlMode && foreignElements.has(elem.name)) { + opts = __assign(__assign({}, opts), { xmlMode: "foreign" }); + } + var tag = "<".concat(elem.name); + var attribs = formatAttributes(elem.attribs, opts); + if (attribs) { + tag += " ".concat(attribs); + } + if (elem.children.length === 0 && + (opts.xmlMode + ? // In XML mode or foreign mode, and user hasn't explicitly turned off self-closing tags + opts.selfClosingTags !== false + : // User explicitly asked for self-closing tags, even in HTML mode + opts.selfClosingTags && singleTag.has(elem.name))) { + if (!opts.xmlMode) + tag += " "; + tag += "/>"; + } + else { + tag += ">"; + if (elem.children.length > 0) { + tag += render(elem.children, opts); + } + if (opts.xmlMode || !singleTag.has(elem.name)) { + tag += ""); + } + } + return tag; +} +function renderDirective(elem) { + return "<".concat(elem.data, ">"); +} +function renderText(elem, opts) { + var _a; + var data = elem.data || ""; + // If entities weren't decoded, no need to encode them back + if (((_a = opts.encodeEntities) !== null && _a !== void 0 ? _a : opts.decodeEntities) !== false && + !(!opts.xmlMode && + elem.parent && + unencodedElements.has(elem.parent.name))) { + data = + opts.xmlMode || opts.encodeEntities !== "utf8" + ? (0, entities_1.encodeXML)(data) + : (0, entities_1.escapeText)(data); + } + return data; +} +function renderCdata(elem) { + return ""); +} +function renderComment(elem) { + return ""); +} diff --git a/frontend/node_modules/dom-serializer/package.json b/frontend/node_modules/dom-serializer/package.json new file mode 100644 index 0000000..002681c --- /dev/null +++ b/frontend/node_modules/dom-serializer/package.json @@ -0,0 +1,69 @@ +{ + "name": "dom-serializer", + "version": "2.0.0", + "description": "render domhandler DOM nodes to a string", + "author": "Felix Boehm ", + "sideEffects": false, + "keywords": [ + "html", + "xml", + "render" + ], + "repository": { + "type": "git", + "url": "git://github.com/cheeriojs/dom-serializer.git" + }, + "main": "lib/index.js", + "types": "lib/index.d.ts", + "module": "lib/esm/index.js", + "exports": { + "require": "./lib/index.js", + "import": "./lib/esm/index.js" + }, + "files": [ + "lib/**/*" + ], + "dependencies": { + "domelementtype": "^2.3.0", + "domhandler": "^5.0.2", + "entities": "^4.2.0" + }, + "devDependencies": { + "@types/jest": "^27.4.1", + "@types/node": "^17.0.23", + "@typescript-eslint/eslint-plugin": "^5.18.0", + "@typescript-eslint/parser": "^5.18.0", + "cheerio": "^1.0.0-rc.9", + "eslint": "^8.12.0", + "eslint-config-prettier": "^8.5.0", + "htmlparser2": "^7.2.0", + "jest": "^27.5.1", + "prettier": "^2.6.2", + "ts-jest": "^27.1.4", + "typescript": "^4.6.3" + }, + "scripts": { + "test": "npm run test:jest && npm run lint", + "test:jest": "jest", + "lint": "npm run lint:es && npm run lint:prettier", + "lint:es": "eslint --ignore-path .gitignore .", + "lint:prettier": "npm run prettier -- --check", + "format": "npm run format:es && npm run format:prettier", + "format:es": "npm run lint:es -- --fix", + "format:prettier": "npm run prettier -- --write", + "prettier": "prettier \"**/*.{ts,md,json,yml}\" --ignore-path .gitignore", + "build": "npm run build:cjs && npm run build:esm", + "build:cjs": "tsc", + "build:esm": "tsc --module esnext --target es2019 --outDir lib/esm && echo '{\"type\":\"module\"}' > lib/esm/package.json", + "prepare": "npm run build" + }, + "jest": { + "preset": "ts-jest", + "testEnvironment": "node", + "moduleNameMapper": { + "^(.*)\\.js$": "$1" + } + }, + "funding": "https://github.com/cheeriojs/dom-serializer?sponsor=1", + "license": "MIT" +} diff --git a/frontend/node_modules/domelementtype/LICENSE b/frontend/node_modules/domelementtype/LICENSE new file mode 100644 index 0000000..c464f86 --- /dev/null +++ b/frontend/node_modules/domelementtype/LICENSE @@ -0,0 +1,11 @@ +Copyright (c) Felix Böhm +All rights reserved. + +Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: + +Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. + +Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. + +THIS IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS, +EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/frontend/node_modules/domelementtype/lib/esm/index.d.ts b/frontend/node_modules/domelementtype/lib/esm/index.d.ts new file mode 100644 index 0000000..72fa4f8 --- /dev/null +++ b/frontend/node_modules/domelementtype/lib/esm/index.d.ts @@ -0,0 +1,48 @@ +/** Types of elements found in htmlparser2's DOM */ +export declare enum ElementType { + /** Type for the root element of a document */ + Root = "root", + /** Type for Text */ + Text = "text", + /** Type for */ + Directive = "directive", + /** Type for */ + Comment = "comment", + /** Type for "; +const handler = new DomHandler((error, dom) => { + if (error) { + // Handle error + } else { + // Parsing completed, do something + console.log(dom); + } +}); +const parser = new Parser(handler); +parser.write(rawHtml); +parser.end(); +``` + +Output: + +```javascript +[ + { + data: "Xyz ", + type: "text", + }, + { + type: "script", + name: "script", + attribs: { + language: "javascript", + }, + children: [ + { + data: "var foo = '';<", + type: "text", + }, + ], + }, + { + data: ""), +}; +function isAsciiAlpha(c) { + return ((c >= Chars.UpperA && c <= Chars.UpperZ) || + (c >= Chars.LowerA && c <= Chars.LowerZ)); +} +function isQuote(c) { + return c === Chars.DQUOTE || c === Chars.SQUOTE; +} +class Sniffer { + setResult(label, type) { + if (this.resultType === ResultType.DEFAULT || this.resultType > type) { + const encoding = (0, whatwg_encoding_1.labelToName)(label); + if (encoding) { + this.encoding = + // Check if we are in a meta tag and the encoding is `x-user-defined` + type === ResultType.META_TAG && + encoding === "x-user-defined" + ? "windows-1252" + : // Check if we are in a meta tag or xml declaration, and the encoding is UTF-16 + (type === ResultType.META_TAG || + type === ResultType.XML_ENCODING) && + (encoding === "UTF-16LE" || encoding === "UTF-16BE") + ? "UTF-8" + : encoding; + this.resultType = type; + } + } + } + constructor({ maxBytes = 1024, userEncoding, transportLayerEncodingLabel, defaultEncoding, } = {}) { + /** The offset of the previous buffers. */ + this.offset = 0; + this.state = State.Begin; + this.sectionIndex = 0; + this.attribType = AttribType.None; + /** + * Indicates if the `http-equiv` is `content-type`. + * + * Initially `null`, a boolean when a value is found. + */ + this.gotPragma = null; + this.needsPragma = null; + this.inMetaTag = false; + this.encoding = "windows-1252"; + this.resultType = ResultType.DEFAULT; + this.quoteCharacter = 0; + this.attributeValue = []; + this.maxBytes = maxBytes; + if (userEncoding) { + this.setResult(userEncoding, ResultType.PASSED); + } + if (transportLayerEncodingLabel) { + this.setResult(transportLayerEncodingLabel, ResultType.PASSED); + } + if (defaultEncoding) { + this.setResult(defaultEncoding, ResultType.DEFAULT); + } + } + stateBegin(c) { + switch (c) { + case exports.STRINGS.UTF16BE_BOM[0]: { + this.state = State.BOM16BE; + break; + } + case exports.STRINGS.UTF16LE_BOM[0]: { + this.state = State.BOM16LE; + break; + } + case exports.STRINGS.UTF8_BOM[0]: { + this.sectionIndex = 1; + this.state = State.BOM8; + break; + } + case Chars.NIL: { + this.state = State.UTF16BE_XML_PREFIX; + this.sectionIndex = 1; + break; + } + case Chars.LT: { + this.state = State.BeginLT; + break; + } + default: { + this.state = State.BeforeTag; + } + } + } + stateBeginLT(c) { + if (c === Chars.NIL) { + this.state = State.UTF16LE_XML_PREFIX; + this.sectionIndex = 2; + } + else if (c === Chars.QUESTION) { + this.state = State.XMLDeclaration; + this.sectionIndex = 2; + } + else { + this.state = State.BeforeTagName; + this.stateBeforeTagName(c); + } + } + stateUTF16BE_XML_PREFIX(c) { + // Advance position in the section + if (this.advanceSection(exports.STRINGS.UTF16BE_XML_PREFIX, c)) { + if (this.sectionIndex === exports.STRINGS.UTF16BE_XML_PREFIX.length) { + // We have the whole prefix + this.setResult("utf-16be", ResultType.XML_PREFIX); + } + } + else { + this.state = State.BeforeTag; + this.stateBeforeTag(c); + } + } + stateUTF16LE_XML_PREFIX(c) { + // Advance position in the section + if (this.advanceSection(exports.STRINGS.UTF16LE_XML_PREFIX, c)) { + if (this.sectionIndex === exports.STRINGS.UTF16LE_XML_PREFIX.length) { + // We have the whole prefix + this.setResult("utf-16le", ResultType.XML_PREFIX); + } + } + else { + this.state = State.BeforeTag; + this.stateBeforeTag(c); + } + } + stateBOM16LE(c) { + if (c === exports.STRINGS.UTF16LE_BOM[1]) { + this.setResult("utf-16le", ResultType.BOM); + } + else { + this.state = State.BeforeTag; + this.stateBeforeTag(c); + } + } + stateBOM16BE(c) { + if (c === exports.STRINGS.UTF16BE_BOM[1]) { + this.setResult("utf-16be", ResultType.BOM); + } + else { + this.state = State.BeforeTag; + this.stateBeforeTag(c); + } + } + stateBOM8(c) { + if (this.advanceSection(exports.STRINGS.UTF8_BOM, c) && + this.sectionIndex === exports.STRINGS.UTF8_BOM.length) { + this.setResult("utf-8", ResultType.BOM); + } + } + stateBeforeTag(c) { + if (c === Chars.LT) { + this.state = State.BeforeTagName; + this.inMetaTag = false; + } + } + /** + * We have seen a `<`, and now have to figure out what to do. + * + * Options: + * - `` above. + * Set this to 2, to support many dashes before the closing `>`. + */ + this.sectionIndex = 2; + } + } + /** + * Any section starting with ``. + this.stateTagNameOther(c); + } + stateTagNameOther(c) { + if (SPACE_CHARACTERS.has(c)) { + this.state = State.BeforeAttribute; + } + else if (c === Chars.GT) { + this.state = State.BeforeTag; + } + } + stateBeforeAttribute(c) { + if (SPACE_CHARACTERS.has(c)) + return; + if (this.inMetaTag) { + const lower = c | 0x20; + if (lower === exports.STRINGS.HTTP_EQUIV[0]) { + this.sectionIndex = 1; + this.state = State.MetaAttribHttpEquiv; + return; + } + else if (lower === exports.STRINGS.CHARSET[0]) { + this.sectionIndex = 1; + this.state = State.MetaAttribC; + return; + } + } + this.state = + c === Chars.SLASH || c === Chars.GT + ? State.BeforeTag + : State.AnyAttribName; + } + handleMetaAttrib(c, section, type) { + if (this.advanceSectionIC(section, c)) { + if (this.sectionIndex === section.length) { + this.attribType = type; + this.state = State.MetaAttribAfterName; + } + } + else { + this.state = State.AnyAttribName; + this.stateAnyAttribName(c); + } + } + stateMetaAttribHttpEquiv(c) { + this.handleMetaAttrib(c, exports.STRINGS.HTTP_EQUIV, AttribType.HttpEquiv); + } + stateMetaAttribC(c) { + const lower = c | 0x20; + if (lower === exports.STRINGS.CHARSET[1]) { + this.sectionIndex = 2; + this.state = State.MetaAttribCharset; + } + else if (lower === exports.STRINGS.CONTENT[1]) { + this.sectionIndex = 2; + this.state = State.MetaAttribContent; + } + else { + this.state = State.AnyAttribName; + this.stateAnyAttribName(c); + } + } + stateMetaAttribCharset(c) { + this.handleMetaAttrib(c, exports.STRINGS.CHARSET, AttribType.Charset); + } + stateMetaAttribContent(c) { + this.handleMetaAttrib(c, exports.STRINGS.CONTENT, AttribType.Content); + } + stateMetaAttribAfterName(c) { + if (SPACE_CHARACTERS.has(c) || c === Chars.EQUALS) { + this.state = State.AfterAttributeName; + this.stateAfterAttributeName(c); + } + else { + this.state = State.AnyAttribName; + this.stateAnyAttribName(c); + } + } + stateAnyAttribName(c) { + if (SPACE_CHARACTERS.has(c)) { + this.attribType = AttribType.None; + this.state = State.AfterAttributeName; + } + else if (c === Chars.SLASH || c === Chars.GT) { + this.state = State.BeforeTag; + } + else if (c === Chars.EQUALS) { + this.state = State.BeforeAttributeValue; + } + } + stateAfterAttributeName(c) { + if (SPACE_CHARACTERS.has(c)) + return; + if (c === Chars.EQUALS) { + this.state = State.BeforeAttributeValue; + } + else { + this.state = State.BeforeAttribute; + this.stateBeforeAttribute(c); + } + } + stateBeforeAttributeValue(c) { + if (SPACE_CHARACTERS.has(c)) + return; + this.attributeValue.length = 0; + this.sectionIndex = 0; + if (isQuote(c)) { + this.quoteCharacter = c; + this.state = + this.attribType === AttribType.Content + ? State.MetaContentValueQuotedBeforeEncoding + : this.attribType === AttribType.HttpEquiv + ? State.MetaAttribHttpEquivValue + : State.AttributeValueQuoted; + } + else if (this.attribType === AttribType.Content) { + this.state = State.MetaContentValueUnquotedBeforeEncoding; + this.stateMetaContentValueUnquotedBeforeEncoding(c); + } + else if (this.attribType === AttribType.HttpEquiv) { + // We use `quoteCharacter = 0` to signify that the value is unquoted. + this.quoteCharacter = 0; + this.sectionIndex = 0; + this.state = State.MetaAttribHttpEquivValue; + this.stateMetaAttribHttpEquivValue(c); + } + else { + this.state = State.AttributeValueUnquoted; + this.stateAttributeValueUnquoted(c); + } + } + // The value has to be `content-type` + stateMetaAttribHttpEquivValue(c) { + if (this.sectionIndex === exports.STRINGS.CONTENT_TYPE.length) { + if (this.quoteCharacter === 0 + ? END_OF_UNQUOTED_ATTRIBUTE_VALUE.has(c) + : c === this.quoteCharacter) { + if (this.needsPragma !== null) { + this.setResult(this.needsPragma, ResultType.META_TAG); + } + else if (this.gotPragma === null) { + this.gotPragma = true; + } + this.state = State.BeforeAttribute; + return; + } + } + else if (this.advanceSectionIC(exports.STRINGS.CONTENT_TYPE, c)) { + return; + } + this.gotPragma = false; + if (this.quoteCharacter === 0) { + this.state = State.AttributeValueUnquoted; + this.stateAttributeValueUnquoted(c); + } + else { + this.state = State.AttributeValueQuoted; + this.stateAttributeValueQuoted(c); + } + } + handleMetaContentValue() { + if (this.attributeValue.length === 0) + return; + const encoding = String.fromCharCode(...this.attributeValue); + if (this.gotPragma) { + this.setResult(encoding, ResultType.META_TAG); + } + else if (this.needsPragma === null) { + // Don't override a previous result. + this.needsPragma = encoding; + } + this.attributeValue.length = 0; + } + handleAttributeValue() { + if (this.attribType === AttribType.Charset) { + this.setResult(String.fromCharCode(...this.attributeValue), ResultType.META_TAG); + } + } + stateAttributeValueUnquoted(c) { + if (SPACE_CHARACTERS.has(c)) { + this.handleAttributeValue(); + this.state = State.BeforeAttribute; + } + else if (c === Chars.SLASH || c === Chars.GT) { + this.handleAttributeValue(); + this.state = State.BeforeTag; + } + else if (this.attribType === AttribType.Charset) { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + findMetaContentEncoding(c) { + if (this.advanceSectionIC(exports.STRINGS.CHARSET, c)) { + if (this.sectionIndex === exports.STRINGS.CHARSET.length) { + return true; + } + } + else { + // If we encountered another `c`, assume we started over. + this.sectionIndex = Number(c === exports.STRINGS.CHARSET[0]); + } + return false; + } + stateMetaContentValueUnquotedBeforeEncoding(c) { + if (END_OF_UNQUOTED_ATTRIBUTE_VALUE.has(c)) { + this.stateAttributeValueUnquoted(c); + } + else if (this.sectionIndex === exports.STRINGS.CHARSET.length) { + if (c === Chars.EQUALS) { + this.state = State.MetaContentValueUnquotedBeforeValue; + } + } + else { + this.findMetaContentEncoding(c); + } + } + stateMetaContentValueUnquotedBeforeValue(c) { + if (isQuote(c)) { + this.quoteCharacter = c; + this.state = State.MetaContentValueUnquotedValueQuoted; + } + else if (END_OF_UNQUOTED_ATTRIBUTE_VALUE.has(c)) { + // Can't have spaces here, as it would no longer be part of the attribute value. + this.stateAttributeValueUnquoted(c); + } + else { + this.state = State.MetaContentValueUnquotedValueUnquoted; + this.stateMetaContentValueUnquotedValueUnquoted(c); + } + } + stateMetaContentValueUnquotedValueQuoted(c) { + if (END_OF_UNQUOTED_ATTRIBUTE_VALUE.has(c)) { + // Quotes weren't matched, so we're done. + this.stateAttributeValueUnquoted(c); + } + else if (c === this.quoteCharacter) { + this.handleMetaContentValue(); + this.state = State.AttributeValueUnquoted; + } + else { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + stateMetaContentValueUnquotedValueUnquoted(c) { + if (END_OF_UNQUOTED_ATTRIBUTE_VALUE.has(c) || c === Chars.SEMICOLON) { + this.handleMetaContentValue(); + this.state = State.AttributeValueUnquoted; + this.stateAttributeValueUnquoted(c); + } + else { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + stateMetaContentValueQuotedValueUnquoted(c) { + if (isQuote(c) || SPACE_CHARACTERS.has(c) || c === Chars.SEMICOLON) { + this.handleMetaContentValue(); + // We are done with the value, but might not be at the end of the attribute + this.state = State.AttributeValueQuoted; + this.stateAttributeValueQuoted(c); + } + else { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + stateMetaContentValueQuotedValueQuoted(c) { + if (isQuote(c)) { + // We have reached the end of our value. + if (c !== this.quoteCharacter) { + // Only handle the value if inner quotes were matched. + this.handleMetaContentValue(); + } + this.state = State.AttributeValueQuoted; + this.stateAttributeValueQuoted(c); + } + else { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + stateMetaContentValueQuotedBeforeEncoding(c) { + if (c === this.quoteCharacter) { + this.stateAttributeValueQuoted(c); + } + else if (this.findMetaContentEncoding(c)) { + this.state = State.MetaContentValueQuotedAfterEncoding; + } + } + stateMetaContentValueQuotedAfterEncoding(c) { + if (c === Chars.EQUALS) { + this.state = State.MetaContentValueQuotedBeforeValue; + } + else if (!SPACE_CHARACTERS.has(c)) { + // Look for the next encoding + this.state = State.MetaContentValueQuotedBeforeEncoding; + this.stateMetaContentValueQuotedBeforeEncoding(c); + } + } + stateMetaContentValueQuotedBeforeValue(c) { + if (c === this.quoteCharacter) { + this.stateAttributeValueQuoted(c); + } + else if (isQuote(c)) { + this.state = State.MetaContentValueQuotedValueQuoted; + } + else if (!SPACE_CHARACTERS.has(c)) { + this.state = State.MetaContentValueQuotedValueUnquoted; + this.stateMetaContentValueQuotedValueUnquoted(c); + } + } + stateAttributeValueQuoted(c) { + if (c === this.quoteCharacter) { + this.handleAttributeValue(); + this.state = State.BeforeAttribute; + } + else if (this.attribType === AttribType.Charset) { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + // Read STRINGS.XML_DECLARATION + stateXMLDeclaration(c) { + if (this.advanceSection(exports.STRINGS.XML_DECLARATION, c)) { + if (this.sectionIndex === exports.STRINGS.XML_DECLARATION.length) { + this.sectionIndex = 0; + this.state = State.XMLDeclarationBeforeEncoding; + } + } + else { + this.state = State.WeirdTag; + } + } + stateXMLDeclarationBeforeEncoding(c) { + if (this.advanceSection(exports.STRINGS.ENCODING, c)) { + if (this.sectionIndex === exports.STRINGS.ENCODING.length) { + this.state = State.XMLDeclarationAfterEncoding; + } + } + else if (c === Chars.GT) { + this.state = State.BeforeTag; + } + else { + // If we encountered another `c`, assume we started over. + this.sectionIndex = Number(c === exports.STRINGS.ENCODING[0]); + } + } + stateXMLDeclarationAfterEncoding(c) { + if (c === Chars.EQUALS) { + this.state = State.XMLDeclarationBeforeValue; + } + else if (c > Chars.SPACE) { + this.state = State.WeirdTag; + this.stateWeirdTag(c); + } + } + stateXMLDeclarationBeforeValue(c) { + if (isQuote(c)) { + this.attributeValue.length = 0; + this.state = State.XMLDeclarationValue; + } + else if (c > Chars.SPACE) { + this.state = State.WeirdTag; + this.stateWeirdTag(c); + } + } + stateXMLDeclarationValue(c) { + if (isQuote(c)) { + this.setResult(String.fromCharCode(...this.attributeValue), ResultType.XML_ENCODING); + this.state = State.WeirdTag; + } + else if (c === Chars.GT) { + this.state = State.BeforeTag; + } + else if (c <= Chars.SPACE) { + this.state = State.WeirdTag; + } + else { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + write(buffer) { + let index = 0; + for (; index < buffer.length && this.offset + index < this.maxBytes; index++) { + const c = buffer[index]; + switch (this.state) { + case State.Begin: { + this.stateBegin(c); + break; + } + case State.BOM16BE: { + this.stateBOM16BE(c); + break; + } + case State.BOM16LE: { + this.stateBOM16LE(c); + break; + } + case State.BOM8: { + this.stateBOM8(c); + break; + } + case State.UTF16LE_XML_PREFIX: { + this.stateUTF16LE_XML_PREFIX(c); + break; + } + case State.BeginLT: { + this.stateBeginLT(c); + break; + } + case State.UTF16BE_XML_PREFIX: { + this.stateUTF16BE_XML_PREFIX(c); + break; + } + case State.BeforeTag: { + // Optimization: Skip all characters until we find a `<` + const idx = buffer.indexOf(Chars.LT, index); + if (idx === -1) { + // We are done with this buffer. Stay in the state and try on the next one. + index = buffer.length; + } + else { + index = idx; + this.stateBeforeTag(Chars.LT); + } + break; + } + case State.BeforeTagName: { + this.stateBeforeTagName(c); + break; + } + case State.BeforeCloseTagName: { + this.stateBeforeCloseTagName(c); + break; + } + case State.CommentStart: { + this.stateCommentStart(c); + break; + } + case State.CommentEnd: { + this.stateCommentEnd(c); + break; + } + case State.TagNameMeta: { + this.stateTagNameMeta(c); + break; + } + case State.TagNameOther: { + this.stateTagNameOther(c); + break; + } + case State.XMLDeclaration: { + this.stateXMLDeclaration(c); + break; + } + case State.XMLDeclarationBeforeEncoding: { + this.stateXMLDeclarationBeforeEncoding(c); + break; + } + case State.XMLDeclarationAfterEncoding: { + this.stateXMLDeclarationAfterEncoding(c); + break; + } + case State.XMLDeclarationBeforeValue: { + this.stateXMLDeclarationBeforeValue(c); + break; + } + case State.XMLDeclarationValue: { + this.stateXMLDeclarationValue(c); + break; + } + case State.WeirdTag: { + this.stateWeirdTag(c); + break; + } + case State.BeforeAttribute: { + this.stateBeforeAttribute(c); + break; + } + case State.MetaAttribHttpEquiv: { + this.stateMetaAttribHttpEquiv(c); + break; + } + case State.MetaAttribHttpEquivValue: { + this.stateMetaAttribHttpEquivValue(c); + break; + } + case State.MetaAttribC: { + this.stateMetaAttribC(c); + break; + } + case State.MetaAttribContent: { + this.stateMetaAttribContent(c); + break; + } + case State.MetaAttribCharset: { + this.stateMetaAttribCharset(c); + break; + } + case State.MetaAttribAfterName: { + this.stateMetaAttribAfterName(c); + break; + } + case State.MetaContentValueQuotedBeforeEncoding: { + this.stateMetaContentValueQuotedBeforeEncoding(c); + break; + } + case State.MetaContentValueQuotedAfterEncoding: { + this.stateMetaContentValueQuotedAfterEncoding(c); + break; + } + case State.MetaContentValueQuotedBeforeValue: { + this.stateMetaContentValueQuotedBeforeValue(c); + break; + } + case State.MetaContentValueQuotedValueQuoted: { + this.stateMetaContentValueQuotedValueQuoted(c); + break; + } + case State.MetaContentValueQuotedValueUnquoted: { + this.stateMetaContentValueQuotedValueUnquoted(c); + break; + } + case State.MetaContentValueUnquotedBeforeEncoding: { + this.stateMetaContentValueUnquotedBeforeEncoding(c); + break; + } + case State.MetaContentValueUnquotedBeforeValue: { + this.stateMetaContentValueUnquotedBeforeValue(c); + break; + } + case State.MetaContentValueUnquotedValueQuoted: { + this.stateMetaContentValueUnquotedValueQuoted(c); + break; + } + case State.MetaContentValueUnquotedValueUnquoted: { + this.stateMetaContentValueUnquotedValueUnquoted(c); + break; + } + case State.AnyAttribName: { + this.stateAnyAttribName(c); + break; + } + case State.AfterAttributeName: { + this.stateAfterAttributeName(c); + break; + } + case State.BeforeAttributeValue: { + this.stateBeforeAttributeValue(c); + break; + } + case State.AttributeValueQuoted: { + this.stateAttributeValueQuoted(c); + break; + } + case State.AttributeValueUnquoted: { + this.stateAttributeValueUnquoted(c); + break; + } + } + } + this.offset += index; + } +} +exports.Sniffer = Sniffer; +/** Get the encoding for the passed buffer. */ +function getEncoding(buffer, options) { + const sniffer = new Sniffer(options); + sniffer.write(buffer); + return sniffer.encoding; +} +//# sourceMappingURL=sniffer.js.map \ No newline at end of file diff --git a/frontend/node_modules/encoding-sniffer/dist/commonjs/sniffer.js.map b/frontend/node_modules/encoding-sniffer/dist/commonjs/sniffer.js.map new file mode 100644 index 0000000..f13f7d3 --- /dev/null +++ b/frontend/node_modules/encoding-sniffer/dist/commonjs/sniffer.js.map @@ -0,0 +1 @@ +{"version":3,"file":"sniffer.js","sourceRoot":"","sources":["../../src/sniffer.ts"],"names":[],"mappings":"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"} \ No newline at end of file diff --git a/frontend/node_modules/encoding-sniffer/dist/esm/index.d.ts b/frontend/node_modules/encoding-sniffer/dist/esm/index.d.ts new file mode 100644 index 0000000..586481b --- /dev/null +++ b/frontend/node_modules/encoding-sniffer/dist/esm/index.d.ts @@ -0,0 +1,31 @@ +import { Transform, type TransformCallback } from "node:stream"; +import type { SnifferOptions } from "./sniffer.js"; +/** + * Sniff the encoding of a buffer, then decode it. + * + * @param buffer Buffer to be decoded + * @param options Options for the sniffer + * @returns The decoded buffer + */ +export declare function decodeBuffer(buffer: Buffer, options?: SnifferOptions): string; +/** + * Decodes a stream of buffers into a stream of strings. + * + * Reads the first 1024 bytes and passes them to the sniffer. Once an encoding + * has been determined, it passes all data to iconv-lite's stream and outputs + * the results. + */ +export declare class DecodeStream extends Transform { + private readonly sniffer; + private readonly buffers; + /** The iconv decode stream. If it is set, we have read more than `options.maxBytes` bytes. */ + private iconv; + private readonly maxBytes; + private readBytes; + constructor(options?: SnifferOptions); + _transform(chunk: Uint8Array, _encoding: string, callback: TransformCallback): void; + private getIconvStream; + _flush(callback: TransformCallback): void; +} +export { type SnifferOptions, getEncoding } from "./sniffer.js"; +//# sourceMappingURL=index.d.ts.map \ No newline at end of file diff --git a/frontend/node_modules/encoding-sniffer/dist/esm/index.d.ts.map b/frontend/node_modules/encoding-sniffer/dist/esm/index.d.ts.map new file mode 100644 index 0000000..5a7c838 --- /dev/null +++ b/frontend/node_modules/encoding-sniffer/dist/esm/index.d.ts.map @@ -0,0 +1 @@ +{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,KAAK,iBAAiB,EAAE,MAAM,aAAa,CAAC;AAEhE,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,cAAc,CAAC;AAGnD;;;;;;GAMG;AACH,wBAAgB,YAAY,CACxB,MAAM,EAAE,MAAM,EACd,OAAO,GAAE,cAAmB,GAC7B,MAAM,CAER;AAED;;;;;;GAMG;AACH,qBAAa,YAAa,SAAQ,SAAS;IACvC,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAU;IAClC,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAoB;IAC5C,8FAA8F;IAC9F,OAAO,CAAC,KAAK,CAAuC;IACpD,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAC;IAC1B,OAAO,CAAC,SAAS,CAAK;gBAEV,OAAO,CAAC,EAAE,cAAc;IAM3B,UAAU,CACf,KAAK,EAAE,UAAU,EACjB,SAAS,EAAE,MAAM,EACjB,QAAQ,EAAE,iBAAiB,GAC5B,IAAI;IAeP,OAAO,CAAC,cAAc;IAmBb,MAAM,CAAC,QAAQ,EAAE,iBAAiB,GAAG,IAAI;CAGrD;AAED,OAAO,EAAE,KAAK,cAAc,EAAE,WAAW,EAAE,MAAM,cAAc,CAAC"} \ No newline at end of file diff --git a/frontend/node_modules/encoding-sniffer/dist/esm/index.js b/frontend/node_modules/encoding-sniffer/dist/esm/index.js new file mode 100644 index 0000000..2b8f056 --- /dev/null +++ b/frontend/node_modules/encoding-sniffer/dist/esm/index.js @@ -0,0 +1,63 @@ +import { Transform } from "node:stream"; +import iconv from "iconv-lite"; +import { Sniffer, getEncoding } from "./sniffer.js"; +/** + * Sniff the encoding of a buffer, then decode it. + * + * @param buffer Buffer to be decoded + * @param options Options for the sniffer + * @returns The decoded buffer + */ +export function decodeBuffer(buffer, options = {}) { + return iconv.decode(buffer, getEncoding(buffer, options)); +} +/** + * Decodes a stream of buffers into a stream of strings. + * + * Reads the first 1024 bytes and passes them to the sniffer. Once an encoding + * has been determined, it passes all data to iconv-lite's stream and outputs + * the results. + */ +export class DecodeStream extends Transform { + constructor(options) { + var _a; + super({ decodeStrings: false, encoding: "utf-8" }); + this.buffers = []; + /** The iconv decode stream. If it is set, we have read more than `options.maxBytes` bytes. */ + this.iconv = null; + this.readBytes = 0; + this.sniffer = new Sniffer(options); + this.maxBytes = (_a = options === null || options === void 0 ? void 0 : options.maxBytes) !== null && _a !== void 0 ? _a : 1024; + } + _transform(chunk, _encoding, callback) { + if (this.readBytes < this.maxBytes) { + this.sniffer.write(chunk); + this.readBytes += chunk.length; + if (this.readBytes < this.maxBytes) { + this.buffers.push(chunk); + callback(); + return; + } + } + this.getIconvStream().write(chunk, callback); + } + getIconvStream() { + if (this.iconv) { + return this.iconv; + } + const stream = iconv.decodeStream(this.sniffer.encoding); + stream.on("data", (chunk) => this.push(chunk, "utf-8")); + stream.on("end", () => this.push(null)); + this.iconv = stream; + for (const buffer of this.buffers) { + stream.write(buffer); + } + this.buffers.length = 0; + return stream; + } + _flush(callback) { + this.getIconvStream().end(callback); + } +} +export { getEncoding } from "./sniffer.js"; +//# sourceMappingURL=index.js.map \ No newline at end of file diff --git a/frontend/node_modules/encoding-sniffer/dist/esm/index.js.map b/frontend/node_modules/encoding-sniffer/dist/esm/index.js.map new file mode 100644 index 0000000..28762b0 --- /dev/null +++ b/frontend/node_modules/encoding-sniffer/dist/esm/index.js.map @@ -0,0 +1 @@ +{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAA0B,MAAM,aAAa,CAAC;AAChE,OAAO,KAAK,MAAM,YAAY,CAAC;AAE/B,OAAO,EAAE,OAAO,EAAE,WAAW,EAAE,MAAM,cAAc,CAAC;AAEpD;;;;;;GAMG;AACH,MAAM,UAAU,YAAY,CACxB,MAAc,EACd,UAA0B,EAAE;IAE5B,OAAO,KAAK,CAAC,MAAM,CAAC,MAAM,EAAE,WAAW,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC;AAC9D,CAAC;AAED;;;;;;GAMG;AACH,MAAM,OAAO,YAAa,SAAQ,SAAS;IAQvC,YAAY,OAAwB;;QAChC,KAAK,CAAC,EAAE,aAAa,EAAE,KAAK,EAAE,QAAQ,EAAE,OAAO,EAAE,CAAC,CAAC;QAPtC,YAAO,GAAiB,EAAE,CAAC;QAC5C,8FAA8F;QACtF,UAAK,GAAkC,IAAI,CAAC;QAE5C,cAAS,GAAG,CAAC,CAAC;QAIlB,IAAI,CAAC,OAAO,GAAG,IAAI,OAAO,CAAC,OAAO,CAAC,CAAC;QACpC,IAAI,CAAC,QAAQ,GAAG,MAAA,OAAO,aAAP,OAAO,uBAAP,OAAO,CAAE,QAAQ,mCAAI,IAAI,CAAC;IAC9C,CAAC;IAEQ,UAAU,CACf,KAAiB,EACjB,SAAiB,EACjB,QAA2B;QAE3B,IAAI,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC,QAAQ,EAAE,CAAC;YACjC,IAAI,CAAC,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;YAC1B,IAAI,CAAC,SAAS,IAAI,KAAK,CAAC,MAAM,CAAC;YAE/B,IAAI,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC,QAAQ,EAAE,CAAC;gBACjC,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;gBACzB,QAAQ,EAAE,CAAC;gBACX,OAAO;YACX,CAAC;QACL,CAAC;QAED,IAAI,CAAC,cAAc,EAAE,CAAC,KAAK,CAAC,KAAK,EAAE,QAAQ,CAAC,CAAC;IACjD,CAAC;IAEO,cAAc;QAClB,IAAI,IAAI,CAAC,KAAK,EAAE,CAAC;YACb,OAAO,IAAI,CAAC,KAAK,CAAC;QACtB,CAAC;QAED,MAAM,MAAM,GAAG,KAAK,CAAC,YAAY,CAAC,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;QACzD,MAAM,CAAC,EAAE,CAAC,MAAM,EAAE,CAAC,KAAa,EAAE,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,EAAE,OAAO,CAAC,CAAC,CAAC;QAChE,MAAM,CAAC,EAAE,CAAC,KAAK,EAAE,GAAG,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;QAExC,IAAI,CAAC,KAAK,GAAG,MAAM,CAAC;QAEpB,KAAK,MAAM,MAAM,IAAI,IAAI,CAAC,OAAO,EAAE,CAAC;YAChC,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC;QACzB,CAAC;QACD,IAAI,CAAC,OAAO,CAAC,MAAM,GAAG,CAAC,CAAC;QAExB,OAAO,MAAM,CAAC;IAClB,CAAC;IAEQ,MAAM,CAAC,QAA2B;QACvC,IAAI,CAAC,cAAc,EAAE,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC;IACxC,CAAC;CACJ;AAED,OAAO,EAAuB,WAAW,EAAE,MAAM,cAAc,CAAC"} \ No newline at end of file diff --git a/frontend/node_modules/encoding-sniffer/dist/esm/package.json b/frontend/node_modules/encoding-sniffer/dist/esm/package.json new file mode 100644 index 0000000..3dbc1ca --- /dev/null +++ b/frontend/node_modules/encoding-sniffer/dist/esm/package.json @@ -0,0 +1,3 @@ +{ + "type": "module" +} diff --git a/frontend/node_modules/encoding-sniffer/dist/esm/sniffer.d.ts b/frontend/node_modules/encoding-sniffer/dist/esm/sniffer.d.ts new file mode 100644 index 0000000..e36d703 --- /dev/null +++ b/frontend/node_modules/encoding-sniffer/dist/esm/sniffer.d.ts @@ -0,0 +1,148 @@ +export declare enum ResultType { + BOM = 0, + PASSED = 1, + XML_PREFIX = 2, + META_TAG = 3, + XML_ENCODING = 4, + DEFAULT = 5 +} +export declare const STRINGS: { + UTF8_BOM: Uint8Array; + UTF16LE_BOM: Uint8Array; + UTF16BE_BOM: Uint8Array; + UTF16LE_XML_PREFIX: Uint8Array; + UTF16BE_XML_PREFIX: Uint8Array; + XML_DECLARATION: Uint8Array; + ENCODING: Uint8Array; + META: Uint8Array; + HTTP_EQUIV: Uint8Array; + CONTENT: Uint8Array; + CONTENT_TYPE: Uint8Array; + CHARSET: Uint8Array; + COMMENT_START: Uint8Array; + COMMENT_END: Uint8Array; +}; +export interface SnifferOptions { + /** + * The maximum number of bytes to sniff. + * + * @default 1024 + */ + maxBytes?: number; + /** + * The encoding specified by the user. + */ + userEncoding?: string; + /** + * The encoding specified by the transport layer. + */ + transportLayerEncodingLabel?: string; + /** + * The default encoding to use. + * + * @default "windows-1252" + */ + defaultEncoding?: string; +} +export declare class Sniffer { + /** The maximum number of bytes to sniff. */ + private readonly maxBytes; + /** The offset of the previous buffers. */ + private offset; + private state; + private sectionIndex; + private attribType; + /** + * Indicates if the `http-equiv` is `content-type`. + * + * Initially `null`, a boolean when a value is found. + */ + private gotPragma; + private needsPragma; + private inMetaTag; + encoding: string; + resultType: ResultType; + private setResult; + constructor({ maxBytes, userEncoding, transportLayerEncodingLabel, defaultEncoding, }?: SnifferOptions); + private stateBegin; + private stateBeginLT; + private stateUTF16BE_XML_PREFIX; + private stateUTF16LE_XML_PREFIX; + private stateBOM16LE; + private stateBOM16BE; + private stateBOM8; + private stateBeforeTag; + /** + * We have seen a `<`, and now have to figure out what to do. + * + * Options: + * - `"), +}; +function isAsciiAlpha(c) { + return ((c >= Chars.UpperA && c <= Chars.UpperZ) || + (c >= Chars.LowerA && c <= Chars.LowerZ)); +} +function isQuote(c) { + return c === Chars.DQUOTE || c === Chars.SQUOTE; +} +export class Sniffer { + setResult(label, type) { + if (this.resultType === ResultType.DEFAULT || this.resultType > type) { + const encoding = labelToName(label); + if (encoding) { + this.encoding = + // Check if we are in a meta tag and the encoding is `x-user-defined` + type === ResultType.META_TAG && + encoding === "x-user-defined" + ? "windows-1252" + : // Check if we are in a meta tag or xml declaration, and the encoding is UTF-16 + (type === ResultType.META_TAG || + type === ResultType.XML_ENCODING) && + (encoding === "UTF-16LE" || encoding === "UTF-16BE") + ? "UTF-8" + : encoding; + this.resultType = type; + } + } + } + constructor({ maxBytes = 1024, userEncoding, transportLayerEncodingLabel, defaultEncoding, } = {}) { + /** The offset of the previous buffers. */ + this.offset = 0; + this.state = State.Begin; + this.sectionIndex = 0; + this.attribType = AttribType.None; + /** + * Indicates if the `http-equiv` is `content-type`. + * + * Initially `null`, a boolean when a value is found. + */ + this.gotPragma = null; + this.needsPragma = null; + this.inMetaTag = false; + this.encoding = "windows-1252"; + this.resultType = ResultType.DEFAULT; + this.quoteCharacter = 0; + this.attributeValue = []; + this.maxBytes = maxBytes; + if (userEncoding) { + this.setResult(userEncoding, ResultType.PASSED); + } + if (transportLayerEncodingLabel) { + this.setResult(transportLayerEncodingLabel, ResultType.PASSED); + } + if (defaultEncoding) { + this.setResult(defaultEncoding, ResultType.DEFAULT); + } + } + stateBegin(c) { + switch (c) { + case STRINGS.UTF16BE_BOM[0]: { + this.state = State.BOM16BE; + break; + } + case STRINGS.UTF16LE_BOM[0]: { + this.state = State.BOM16LE; + break; + } + case STRINGS.UTF8_BOM[0]: { + this.sectionIndex = 1; + this.state = State.BOM8; + break; + } + case Chars.NIL: { + this.state = State.UTF16BE_XML_PREFIX; + this.sectionIndex = 1; + break; + } + case Chars.LT: { + this.state = State.BeginLT; + break; + } + default: { + this.state = State.BeforeTag; + } + } + } + stateBeginLT(c) { + if (c === Chars.NIL) { + this.state = State.UTF16LE_XML_PREFIX; + this.sectionIndex = 2; + } + else if (c === Chars.QUESTION) { + this.state = State.XMLDeclaration; + this.sectionIndex = 2; + } + else { + this.state = State.BeforeTagName; + this.stateBeforeTagName(c); + } + } + stateUTF16BE_XML_PREFIX(c) { + // Advance position in the section + if (this.advanceSection(STRINGS.UTF16BE_XML_PREFIX, c)) { + if (this.sectionIndex === STRINGS.UTF16BE_XML_PREFIX.length) { + // We have the whole prefix + this.setResult("utf-16be", ResultType.XML_PREFIX); + } + } + else { + this.state = State.BeforeTag; + this.stateBeforeTag(c); + } + } + stateUTF16LE_XML_PREFIX(c) { + // Advance position in the section + if (this.advanceSection(STRINGS.UTF16LE_XML_PREFIX, c)) { + if (this.sectionIndex === STRINGS.UTF16LE_XML_PREFIX.length) { + // We have the whole prefix + this.setResult("utf-16le", ResultType.XML_PREFIX); + } + } + else { + this.state = State.BeforeTag; + this.stateBeforeTag(c); + } + } + stateBOM16LE(c) { + if (c === STRINGS.UTF16LE_BOM[1]) { + this.setResult("utf-16le", ResultType.BOM); + } + else { + this.state = State.BeforeTag; + this.stateBeforeTag(c); + } + } + stateBOM16BE(c) { + if (c === STRINGS.UTF16BE_BOM[1]) { + this.setResult("utf-16be", ResultType.BOM); + } + else { + this.state = State.BeforeTag; + this.stateBeforeTag(c); + } + } + stateBOM8(c) { + if (this.advanceSection(STRINGS.UTF8_BOM, c) && + this.sectionIndex === STRINGS.UTF8_BOM.length) { + this.setResult("utf-8", ResultType.BOM); + } + } + stateBeforeTag(c) { + if (c === Chars.LT) { + this.state = State.BeforeTagName; + this.inMetaTag = false; + } + } + /** + * We have seen a `<`, and now have to figure out what to do. + * + * Options: + * - `` above. + * Set this to 2, to support many dashes before the closing `>`. + */ + this.sectionIndex = 2; + } + } + /** + * Any section starting with ``. + this.stateTagNameOther(c); + } + stateTagNameOther(c) { + if (SPACE_CHARACTERS.has(c)) { + this.state = State.BeforeAttribute; + } + else if (c === Chars.GT) { + this.state = State.BeforeTag; + } + } + stateBeforeAttribute(c) { + if (SPACE_CHARACTERS.has(c)) + return; + if (this.inMetaTag) { + const lower = c | 0x20; + if (lower === STRINGS.HTTP_EQUIV[0]) { + this.sectionIndex = 1; + this.state = State.MetaAttribHttpEquiv; + return; + } + else if (lower === STRINGS.CHARSET[0]) { + this.sectionIndex = 1; + this.state = State.MetaAttribC; + return; + } + } + this.state = + c === Chars.SLASH || c === Chars.GT + ? State.BeforeTag + : State.AnyAttribName; + } + handleMetaAttrib(c, section, type) { + if (this.advanceSectionIC(section, c)) { + if (this.sectionIndex === section.length) { + this.attribType = type; + this.state = State.MetaAttribAfterName; + } + } + else { + this.state = State.AnyAttribName; + this.stateAnyAttribName(c); + } + } + stateMetaAttribHttpEquiv(c) { + this.handleMetaAttrib(c, STRINGS.HTTP_EQUIV, AttribType.HttpEquiv); + } + stateMetaAttribC(c) { + const lower = c | 0x20; + if (lower === STRINGS.CHARSET[1]) { + this.sectionIndex = 2; + this.state = State.MetaAttribCharset; + } + else if (lower === STRINGS.CONTENT[1]) { + this.sectionIndex = 2; + this.state = State.MetaAttribContent; + } + else { + this.state = State.AnyAttribName; + this.stateAnyAttribName(c); + } + } + stateMetaAttribCharset(c) { + this.handleMetaAttrib(c, STRINGS.CHARSET, AttribType.Charset); + } + stateMetaAttribContent(c) { + this.handleMetaAttrib(c, STRINGS.CONTENT, AttribType.Content); + } + stateMetaAttribAfterName(c) { + if (SPACE_CHARACTERS.has(c) || c === Chars.EQUALS) { + this.state = State.AfterAttributeName; + this.stateAfterAttributeName(c); + } + else { + this.state = State.AnyAttribName; + this.stateAnyAttribName(c); + } + } + stateAnyAttribName(c) { + if (SPACE_CHARACTERS.has(c)) { + this.attribType = AttribType.None; + this.state = State.AfterAttributeName; + } + else if (c === Chars.SLASH || c === Chars.GT) { + this.state = State.BeforeTag; + } + else if (c === Chars.EQUALS) { + this.state = State.BeforeAttributeValue; + } + } + stateAfterAttributeName(c) { + if (SPACE_CHARACTERS.has(c)) + return; + if (c === Chars.EQUALS) { + this.state = State.BeforeAttributeValue; + } + else { + this.state = State.BeforeAttribute; + this.stateBeforeAttribute(c); + } + } + stateBeforeAttributeValue(c) { + if (SPACE_CHARACTERS.has(c)) + return; + this.attributeValue.length = 0; + this.sectionIndex = 0; + if (isQuote(c)) { + this.quoteCharacter = c; + this.state = + this.attribType === AttribType.Content + ? State.MetaContentValueQuotedBeforeEncoding + : this.attribType === AttribType.HttpEquiv + ? State.MetaAttribHttpEquivValue + : State.AttributeValueQuoted; + } + else if (this.attribType === AttribType.Content) { + this.state = State.MetaContentValueUnquotedBeforeEncoding; + this.stateMetaContentValueUnquotedBeforeEncoding(c); + } + else if (this.attribType === AttribType.HttpEquiv) { + // We use `quoteCharacter = 0` to signify that the value is unquoted. + this.quoteCharacter = 0; + this.sectionIndex = 0; + this.state = State.MetaAttribHttpEquivValue; + this.stateMetaAttribHttpEquivValue(c); + } + else { + this.state = State.AttributeValueUnquoted; + this.stateAttributeValueUnquoted(c); + } + } + // The value has to be `content-type` + stateMetaAttribHttpEquivValue(c) { + if (this.sectionIndex === STRINGS.CONTENT_TYPE.length) { + if (this.quoteCharacter === 0 + ? END_OF_UNQUOTED_ATTRIBUTE_VALUE.has(c) + : c === this.quoteCharacter) { + if (this.needsPragma !== null) { + this.setResult(this.needsPragma, ResultType.META_TAG); + } + else if (this.gotPragma === null) { + this.gotPragma = true; + } + this.state = State.BeforeAttribute; + return; + } + } + else if (this.advanceSectionIC(STRINGS.CONTENT_TYPE, c)) { + return; + } + this.gotPragma = false; + if (this.quoteCharacter === 0) { + this.state = State.AttributeValueUnquoted; + this.stateAttributeValueUnquoted(c); + } + else { + this.state = State.AttributeValueQuoted; + this.stateAttributeValueQuoted(c); + } + } + handleMetaContentValue() { + if (this.attributeValue.length === 0) + return; + const encoding = String.fromCharCode(...this.attributeValue); + if (this.gotPragma) { + this.setResult(encoding, ResultType.META_TAG); + } + else if (this.needsPragma === null) { + // Don't override a previous result. + this.needsPragma = encoding; + } + this.attributeValue.length = 0; + } + handleAttributeValue() { + if (this.attribType === AttribType.Charset) { + this.setResult(String.fromCharCode(...this.attributeValue), ResultType.META_TAG); + } + } + stateAttributeValueUnquoted(c) { + if (SPACE_CHARACTERS.has(c)) { + this.handleAttributeValue(); + this.state = State.BeforeAttribute; + } + else if (c === Chars.SLASH || c === Chars.GT) { + this.handleAttributeValue(); + this.state = State.BeforeTag; + } + else if (this.attribType === AttribType.Charset) { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + findMetaContentEncoding(c) { + if (this.advanceSectionIC(STRINGS.CHARSET, c)) { + if (this.sectionIndex === STRINGS.CHARSET.length) { + return true; + } + } + else { + // If we encountered another `c`, assume we started over. + this.sectionIndex = Number(c === STRINGS.CHARSET[0]); + } + return false; + } + stateMetaContentValueUnquotedBeforeEncoding(c) { + if (END_OF_UNQUOTED_ATTRIBUTE_VALUE.has(c)) { + this.stateAttributeValueUnquoted(c); + } + else if (this.sectionIndex === STRINGS.CHARSET.length) { + if (c === Chars.EQUALS) { + this.state = State.MetaContentValueUnquotedBeforeValue; + } + } + else { + this.findMetaContentEncoding(c); + } + } + stateMetaContentValueUnquotedBeforeValue(c) { + if (isQuote(c)) { + this.quoteCharacter = c; + this.state = State.MetaContentValueUnquotedValueQuoted; + } + else if (END_OF_UNQUOTED_ATTRIBUTE_VALUE.has(c)) { + // Can't have spaces here, as it would no longer be part of the attribute value. + this.stateAttributeValueUnquoted(c); + } + else { + this.state = State.MetaContentValueUnquotedValueUnquoted; + this.stateMetaContentValueUnquotedValueUnquoted(c); + } + } + stateMetaContentValueUnquotedValueQuoted(c) { + if (END_OF_UNQUOTED_ATTRIBUTE_VALUE.has(c)) { + // Quotes weren't matched, so we're done. + this.stateAttributeValueUnquoted(c); + } + else if (c === this.quoteCharacter) { + this.handleMetaContentValue(); + this.state = State.AttributeValueUnquoted; + } + else { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + stateMetaContentValueUnquotedValueUnquoted(c) { + if (END_OF_UNQUOTED_ATTRIBUTE_VALUE.has(c) || c === Chars.SEMICOLON) { + this.handleMetaContentValue(); + this.state = State.AttributeValueUnquoted; + this.stateAttributeValueUnquoted(c); + } + else { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + stateMetaContentValueQuotedValueUnquoted(c) { + if (isQuote(c) || SPACE_CHARACTERS.has(c) || c === Chars.SEMICOLON) { + this.handleMetaContentValue(); + // We are done with the value, but might not be at the end of the attribute + this.state = State.AttributeValueQuoted; + this.stateAttributeValueQuoted(c); + } + else { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + stateMetaContentValueQuotedValueQuoted(c) { + if (isQuote(c)) { + // We have reached the end of our value. + if (c !== this.quoteCharacter) { + // Only handle the value if inner quotes were matched. + this.handleMetaContentValue(); + } + this.state = State.AttributeValueQuoted; + this.stateAttributeValueQuoted(c); + } + else { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + stateMetaContentValueQuotedBeforeEncoding(c) { + if (c === this.quoteCharacter) { + this.stateAttributeValueQuoted(c); + } + else if (this.findMetaContentEncoding(c)) { + this.state = State.MetaContentValueQuotedAfterEncoding; + } + } + stateMetaContentValueQuotedAfterEncoding(c) { + if (c === Chars.EQUALS) { + this.state = State.MetaContentValueQuotedBeforeValue; + } + else if (!SPACE_CHARACTERS.has(c)) { + // Look for the next encoding + this.state = State.MetaContentValueQuotedBeforeEncoding; + this.stateMetaContentValueQuotedBeforeEncoding(c); + } + } + stateMetaContentValueQuotedBeforeValue(c) { + if (c === this.quoteCharacter) { + this.stateAttributeValueQuoted(c); + } + else if (isQuote(c)) { + this.state = State.MetaContentValueQuotedValueQuoted; + } + else if (!SPACE_CHARACTERS.has(c)) { + this.state = State.MetaContentValueQuotedValueUnquoted; + this.stateMetaContentValueQuotedValueUnquoted(c); + } + } + stateAttributeValueQuoted(c) { + if (c === this.quoteCharacter) { + this.handleAttributeValue(); + this.state = State.BeforeAttribute; + } + else if (this.attribType === AttribType.Charset) { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + // Read STRINGS.XML_DECLARATION + stateXMLDeclaration(c) { + if (this.advanceSection(STRINGS.XML_DECLARATION, c)) { + if (this.sectionIndex === STRINGS.XML_DECLARATION.length) { + this.sectionIndex = 0; + this.state = State.XMLDeclarationBeforeEncoding; + } + } + else { + this.state = State.WeirdTag; + } + } + stateXMLDeclarationBeforeEncoding(c) { + if (this.advanceSection(STRINGS.ENCODING, c)) { + if (this.sectionIndex === STRINGS.ENCODING.length) { + this.state = State.XMLDeclarationAfterEncoding; + } + } + else if (c === Chars.GT) { + this.state = State.BeforeTag; + } + else { + // If we encountered another `c`, assume we started over. + this.sectionIndex = Number(c === STRINGS.ENCODING[0]); + } + } + stateXMLDeclarationAfterEncoding(c) { + if (c === Chars.EQUALS) { + this.state = State.XMLDeclarationBeforeValue; + } + else if (c > Chars.SPACE) { + this.state = State.WeirdTag; + this.stateWeirdTag(c); + } + } + stateXMLDeclarationBeforeValue(c) { + if (isQuote(c)) { + this.attributeValue.length = 0; + this.state = State.XMLDeclarationValue; + } + else if (c > Chars.SPACE) { + this.state = State.WeirdTag; + this.stateWeirdTag(c); + } + } + stateXMLDeclarationValue(c) { + if (isQuote(c)) { + this.setResult(String.fromCharCode(...this.attributeValue), ResultType.XML_ENCODING); + this.state = State.WeirdTag; + } + else if (c === Chars.GT) { + this.state = State.BeforeTag; + } + else if (c <= Chars.SPACE) { + this.state = State.WeirdTag; + } + else { + this.attributeValue.push(c | (c >= 0x41 && c <= 0x5a ? 0x20 : 0)); + } + } + write(buffer) { + let index = 0; + for (; index < buffer.length && this.offset + index < this.maxBytes; index++) { + const c = buffer[index]; + switch (this.state) { + case State.Begin: { + this.stateBegin(c); + break; + } + case State.BOM16BE: { + this.stateBOM16BE(c); + break; + } + case State.BOM16LE: { + this.stateBOM16LE(c); + break; + } + case State.BOM8: { + this.stateBOM8(c); + break; + } + case State.UTF16LE_XML_PREFIX: { + this.stateUTF16LE_XML_PREFIX(c); + break; + } + case State.BeginLT: { + this.stateBeginLT(c); + break; + } + case State.UTF16BE_XML_PREFIX: { + this.stateUTF16BE_XML_PREFIX(c); + break; + } + case State.BeforeTag: { + // Optimization: Skip all characters until we find a `<` + const idx = buffer.indexOf(Chars.LT, index); + if (idx === -1) { + // We are done with this buffer. Stay in the state and try on the next one. + index = buffer.length; + } + else { + index = idx; + this.stateBeforeTag(Chars.LT); + } + break; + } + case State.BeforeTagName: { + this.stateBeforeTagName(c); + break; + } + case State.BeforeCloseTagName: { + this.stateBeforeCloseTagName(c); + break; + } + case State.CommentStart: { + this.stateCommentStart(c); + break; + } + case State.CommentEnd: { + this.stateCommentEnd(c); + break; + } + case State.TagNameMeta: { + this.stateTagNameMeta(c); + break; + } + case State.TagNameOther: { + this.stateTagNameOther(c); + break; + } + case State.XMLDeclaration: { + this.stateXMLDeclaration(c); + break; + } + case State.XMLDeclarationBeforeEncoding: { + this.stateXMLDeclarationBeforeEncoding(c); + break; + } + case State.XMLDeclarationAfterEncoding: { + this.stateXMLDeclarationAfterEncoding(c); + break; + } + case State.XMLDeclarationBeforeValue: { + this.stateXMLDeclarationBeforeValue(c); + break; + } + case State.XMLDeclarationValue: { + this.stateXMLDeclarationValue(c); + break; + } + case State.WeirdTag: { + this.stateWeirdTag(c); + break; + } + case State.BeforeAttribute: { + this.stateBeforeAttribute(c); + break; + } + case State.MetaAttribHttpEquiv: { + this.stateMetaAttribHttpEquiv(c); + break; + } + case State.MetaAttribHttpEquivValue: { + this.stateMetaAttribHttpEquivValue(c); + break; + } + case State.MetaAttribC: { + this.stateMetaAttribC(c); + break; + } + case State.MetaAttribContent: { + this.stateMetaAttribContent(c); + break; + } + case State.MetaAttribCharset: { + this.stateMetaAttribCharset(c); + break; + } + case State.MetaAttribAfterName: { + this.stateMetaAttribAfterName(c); + break; + } + case State.MetaContentValueQuotedBeforeEncoding: { + this.stateMetaContentValueQuotedBeforeEncoding(c); + break; + } + case State.MetaContentValueQuotedAfterEncoding: { + this.stateMetaContentValueQuotedAfterEncoding(c); + break; + } + case State.MetaContentValueQuotedBeforeValue: { + this.stateMetaContentValueQuotedBeforeValue(c); + break; + } + case State.MetaContentValueQuotedValueQuoted: { + this.stateMetaContentValueQuotedValueQuoted(c); + break; + } + case State.MetaContentValueQuotedValueUnquoted: { + this.stateMetaContentValueQuotedValueUnquoted(c); + break; + } + case State.MetaContentValueUnquotedBeforeEncoding: { + this.stateMetaContentValueUnquotedBeforeEncoding(c); + break; + } + case State.MetaContentValueUnquotedBeforeValue: { + this.stateMetaContentValueUnquotedBeforeValue(c); + break; + } + case State.MetaContentValueUnquotedValueQuoted: { + this.stateMetaContentValueUnquotedValueQuoted(c); + break; + } + case State.MetaContentValueUnquotedValueUnquoted: { + this.stateMetaContentValueUnquotedValueUnquoted(c); + break; + } + case State.AnyAttribName: { + this.stateAnyAttribName(c); + break; + } + case State.AfterAttributeName: { + this.stateAfterAttributeName(c); + break; + } + case State.BeforeAttributeValue: { + this.stateBeforeAttributeValue(c); + break; + } + case State.AttributeValueQuoted: { + this.stateAttributeValueQuoted(c); + break; + } + case State.AttributeValueUnquoted: { + this.stateAttributeValueUnquoted(c); + break; + } + } + } + this.offset += index; + } +} +/** Get the encoding for the passed buffer. */ +export function getEncoding(buffer, options) { + const sniffer = new Sniffer(options); + sniffer.write(buffer); + return sniffer.encoding; +} +//# sourceMappingURL=sniffer.js.map \ No newline at end of file diff --git a/frontend/node_modules/encoding-sniffer/dist/esm/sniffer.js.map b/frontend/node_modules/encoding-sniffer/dist/esm/sniffer.js.map new file mode 100644 index 0000000..900d78d --- /dev/null +++ b/frontend/node_modules/encoding-sniffer/dist/esm/sniffer.js.map @@ -0,0 +1 @@ +{"version":3,"file":"sniffer.js","sourceRoot":"","sources":["../../src/sniffer.ts"],"names":[],"mappings":"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"} \ No newline at end of file diff --git a/frontend/node_modules/encoding-sniffer/package.json b/frontend/node_modules/encoding-sniffer/package.json new file mode 100644 index 0000000..33aaba8 --- /dev/null +++ b/frontend/node_modules/encoding-sniffer/package.json @@ -0,0 +1,94 @@ +{ + "name": "encoding-sniffer", + "version": "0.2.1", + "description": "Implementation of the HTML encoding sniffer algo, with stream support", + "bugs": { + "url": "https://github.com/fb55/encoding-sniffer/issues" + }, + "repository": { + "type": "git", + "url": "git://github.com/fb55/encoding-sniffer.git" + }, + "funding": "https://github.com/fb55/encoding-sniffer?sponsor=1", + "license": "MIT", + "author": "Felix Boehm ", + "type": "module", + "exports": { + ".": { + "import": { + "types": "./dist/esm/index.d.ts", + "default": "./dist/esm/index.js" + }, + "require": { + "types": "./dist/commonjs/index.d.ts", + "default": "./dist/commonjs/index.js" + } + }, + "./sniffer": { + "import": { + "types": "./dist/esm/sniffer.d.ts", + "default": "./dist/esm/sniffer.js" + }, + "require": { + "types": "./dist/commonjs/sniffer.d.ts", + "default": "./dist/commonjs/sniffer.js" + } + } + }, + "main": "./dist/commonjs/index.js", + "module": "./dist/esm/index.js", + "types": "./dist/commonjs/index.d.ts", + "files": [ + "sniffer.js", + "sniffer.d.ts", + "dist" + ], + "scripts": { + "build": "tshy", + "build:docs": "typedoc --hideGenerator src/index.ts", + "format": "npm run format:es && npm run format:prettier", + "format:es": "npm run lint:es -- --fix", + "format:prettier": "npm run prettier -- --write", + "lint": "npm run lint:es && npm run lint:ts && npm run lint:prettier", + "lint:es": "eslint --ignore-path .gitignore .", + "lint:prettier": "npm run prettier -- --check", + "lint:ts": "tsc --noEmit", + "prepublishOnly": "npm run build", + "prettier": "prettier '**/*.{ts,md,json,yml}'", + "test": "npm run test:vi && npm run lint", + "test:vi": "vitest run" + }, + "prettier": { + "proseWrap": "always", + "tabWidth": 4 + }, + "dependencies": { + "iconv-lite": "^0.6.3", + "whatwg-encoding": "^3.1.1" + }, + "devDependencies": { + "@types/node": "^22.15.30", + "@types/whatwg-encoding": "^2.0.3", + "@typescript-eslint/eslint-plugin": "^8.27.0", + "@typescript-eslint/parser": "^8.33.1", + "@vitest/coverage-v8": "^2.1.8", + "eslint": "^8.57.1", + "eslint-config-prettier": "^10.1.5", + "eslint-plugin-n": "^17.19.0", + "eslint-plugin-unicorn": "^56.0.1", + "prettier": "^3.5.3", + "tshy": "^3.0.2", + "typedoc": "^0.28.5", + "typescript": "^5.8.3", + "vitest": "^2.0.2" + }, + "tshy": { + "exports": { + ".": "./src/index.ts", + "./sniffer": "./src/sniffer.ts" + }, + "exclude": [ + "src/**/*.spec.ts" + ] + } +} diff --git a/frontend/node_modules/encoding-sniffer/sniffer.d.ts b/frontend/node_modules/encoding-sniffer/sniffer.d.ts new file mode 100644 index 0000000..d446ac9 --- /dev/null +++ b/frontend/node_modules/encoding-sniffer/sniffer.d.ts @@ -0,0 +1,2 @@ +// eslint-disable-next-line n/no-missing-import +export * from "./dist/commonjs/sniffer.js"; diff --git a/frontend/node_modules/encoding-sniffer/sniffer.js b/frontend/node_modules/encoding-sniffer/sniffer.js new file mode 100644 index 0000000..e35a1b0 --- /dev/null +++ b/frontend/node_modules/encoding-sniffer/sniffer.js @@ -0,0 +1,3 @@ +// Make exports work in Node < 12 +// eslint-disable-next-line no-undef +module.exports = require("./dist/commonjs/sniffer.js"); diff --git a/frontend/node_modules/highlight.js/CHANGES.md b/frontend/node_modules/highlight.js/CHANGES.md new file mode 100644 index 0000000..76fa83e --- /dev/null +++ b/frontend/node_modules/highlight.js/CHANGES.md @@ -0,0 +1,3556 @@ +## Version 11.11.1 + +- Fixes regression with Rust grammar. + + +## Version 11.11.0 + +CAVEATS / POTENTIALLY BREAKING CHANGES + +- Nothing yet. + + +Core Grammars: + +- fix(rust) - adds emoji support in single quote strings [joshgoebel][] +- fix(apache) - support line continuation via `\` [Josh Goebel][] +- fix(makefile) - allow strings inside `$()` expressions [aneesh98][] +- enh(arcade) updated to ArcGIS Arcade version 1.29 [Kristian Ekenes][] +- enh(css) add all properties listed on MDN (96 additions including `anchor-name`, `aspect-ratio`, `backdrop-filter`, `container`, `margin-trim`, `place-content`, `scroll-timeline`, ...) [BaliBalo][] +- enh(excel) add built-in functions for Excel 365 release to 2024 [Danny Winrow][] +- enh(erlang) OTP 27 triple-quoted strings [nixxquality][] +- enh(erlang) OTP 27 doc attribute [nixxquality][] +- enh(erlang) OTP 27 Sigil type [nixxquality][] +- enh(erlang) OTP25/27 maybe statement [nixxquality][] +- enh(dart) Support digit-separators in number literals [Sam Rawlins][] +- enh(csharp) add Contextual keywords `file`, `args`, `dynamic`, `record`, `required` and `scoped` [Alvin Joy][] +- enh(lua) add 'pluto' as an alias [Sainan] +- enh(bash) add reserved keywords `time` and `coproc` [Álvaro Mondéjar][] +- enh(nix) update keywords [h7x4][] +- enh(nix) support paths [h7x4][] +- enh(nix) support lookup paths [h7x4][] +- enh(nix) support operators [h7x4][] +- enh(nix) support REPL keywords [h7x4][] +- enh(nix) support markdown comments [h7x4][] +- enh(nix) support basic function params [h7x4][] +- enh(nix) better parsing of attrsets [h7x4][] +- fix(c) - Fixed hex numbers with decimals [Dxuian] +- fix(typescript) - Fixedoptional property not highlighted correctly [Dxuian] +- fix(ruby) - fix `|=` operator false positives (as block arguments) [Aboobacker MK] +- enh(gcode) rewrote language for modern gcode support [Barthélémy Bonhomme][] +- fix(sql) - Fixed sql primary key and foreign key spacing issue [Dxuian] +- fix(cpp) added flat_set and flat_map as a part of cpp 23 version [Lavan] +- fix(yaml) - Fixed special chars in yaml [Dxuian] +- fix(basic) - Fixed closing quotation marks not required for a PRINT statement [Somya] +- fix(nix) remove `add` builtin [h7x4][] +- fix(nix) mark `or` as builtin instead of literal [h7x4][] +- fix(nix) handle `'''` string escapes [h7x4][] +- fix(nix) handle backslash string escapes [h7x4][] +- fix(nix) don't mix escapes for `"` and `''` strings [h7x4][] +- fix(swift) - Fixed syntax highlighting for class func/var declarations [guuido] +- fix(yaml) - Fixed wrong escaping behavior in single quoted strings [guuido] +- enh(nim) - Add `concept` and `defer` to list of Nim keywords [Jake Leahy] + +New Grammars: + +- added 3rd party TTCN-3 grammar to SUPPORTED_LANGUAGES [Osmocom][] +- added 3rd party Odin grammar to SUPPORTED_LANGUAGES [clsource][] +- added 3rd party Liquid grammar to SUPPORTED_LANGUAGES [Laurel King][] + +Developer Tools: + +- Nothing yet. + +Themes: + +- Added `Rosé Pine` theme [William Wilkinson][] +- Added `Cybertopia Cherry` theme [Alexandre ZANNI][] +- Added `Cybertopia Dimmer` theme [Alexandre ZANNI][] +- Added `Cybertopia Icecap` theme [Alexandre ZANNI][] +- Added `Cybertopia Saturated` theme [Alexandre ZANNI][] + +Improvements: + +- Resolve the memory leak problem when creating multiple Highlight.js instances [Imken][] + +CONTRIBUTORS + +[Josh Goebel]: https://github.com/joshgoebel +[aneesh98]: https://github.com/aneesh98 +[BaliBalo]: https://github.com/BaliBalo +[William Wilkinson]: https://github.com/wilkinson4 +[nixxquality]: https://github.com/nixxquality +[srawlins]: https://github.com/srawlins +[Alvin Joy]: https://github.com/alvinsjoy +[Dxuian]:https://github.com/Dxuian +[Aboobacker MK]: https://github.com/tachyons +[Imken]: https://github.com/immccn123 +[Sainan]: https://github.com/Sainan +[Osmocom]: https://github.com/osmocom +[Álvaro Mondéjar]: https://github.com/mondeja +[Alexandre ZANNI]: https://github.com/noraj +[Barthélémy Bonhomme]: https://github.com/barthy-koeln +[Lavan]: https://github.com/jvlavan +[Somya]: https://github.com/somya-05 +[guuido]: https://github.com/guuido +[clsource]: https://github.com/clsource +[Jake Leahy]: https://github.com/ire4ever1190 +[Laurel King]: https://github.com/laurelthorburn +[Kristian Ekenes]: https://github.com/ekenes +[Danny Winrow]: https://github.com/dannywinrow + + +## Version 11.10.0 + +CAVEATS / POTENTIALLY BREAKING CHANGES + +- Drops support for Node 16.x, which is no longer supported by Node.js. + +Core Grammars: + +- enh(typescript) add support for `satisfies` operator [Kisaragi Hiu][] +- enc(c) added more C23 keywords [Melkor-1][] +- enh(json) added jsonc as an alias [BackupMiles][] +- enh(gml) updated to latest language version (GML v2024.2) [gnysek][] +- enh(c) added more C23 keywords and preprcoessor directives [Eisenwave][] +- enh(js/ts) support namespaced tagged template strings [Aral Balkan][] +- enh(perl) fix false-positive variable match at end of string [Josh Goebel][] +- fix(cpp) not all kinds of number literals are highlighted correctly [Lê Duy Quang][] +- fix(css) fix overly greedy pseudo class matching [Bradley Mackey][] +- enh(arcade) updated to ArcGIS Arcade version 1.24 [Kristian Ekenes][] +- fix(typescript): params types [Mohamed Ali][] +- fix(rust) fix escaped double quotes in string [Mohamed Ali][] +- fix(rust) fix for r# raw identifier not being highlighted correctly. [JaeBaek Lee][] +- enh(rust) Adding union to be recognized as a keyword in Rust. [JaeBaek Lee][] +- fix(yaml) fix for yaml with keys having brackets highlighted incorrectly [Aneesh Kulkarni][] +- fix(csharp) add raw string highlighting for C# 11. [Tara][] +- fix(bash) fix # within token being detected as the start of a comment [Felix Uhl][] +- fix(python) fix `or` conflicts with string highlighting [Mohamed Ali][] +- enh(python) adds a scope to the `self` variable [Lee Falin][] +- enh(delphi) allow digits to be omitted for hex and binary literals [Jonah Jeleniewski][] +- enh(delphi) add support for digit separators [Jonah Jeleniewski][] +- enh(delphi) add support for character strings with non-decimal numerics [Jonah Jeleniewski][] +- fix(javascript) incorrect function name highlighting [CY Fung][] +- fix(1c) fix escaped symbols "+-;():=,[]" literals [Vitaly Barilko][] +- fix(swift) correctly highlight generics and conformances in type definitions [Bradley Mackey][] +- enh(swift) add package keyword [Bradley Mackey][] +- fix(swift) ensure keyword attributes highlight correctly [Bradley Mackey][] +- fix(types) fix interface LanguageDetail > keywords [Patrick Chiu] +- enh(java) add `goto` to be recognized as a keyword in Java [Alvin Joy][] +- enh(bash) add keyword `sudo` [Alvin Joy][] +- fix(haxe) captures `new` keyword without capturing it within variables/class names [Cameron Taylor][] +- fix(go) fix go number literals to accept `_` separators, add hex p exponents [Lisa Ugray][] +- enh(markdown) add entity support [David Schach][] [TaraLei][] +- enh(css) add `justify-items` and `justify-self` attributes [Vasily Polovnyov][] +- enh(css) add `accent-color`, `appearance`, `color-scheme`, `rotate`, `scale` and `translate` attributes [Carl Räfting][] +- fix(fortran) fixes parsing of keywords delimited by dots [Julien Bloino][] +- enh(css) add `select`, `option`, `optgroup`, `picture` and `source` to list of known tags [Vasily Polovnyov][] +- enh(css) add `inset`, `inset-*`, `border-start-*-radius` and `border-end-*-radius` attributes [Vasily Polovnyov][] +- enh(css) add `text-decoration-skip-ink`, `text-decoration-thickness` and `text-underline-offset` attributes [Vasily Polovnyov][] +- enh(java) add `when` to be recognized as a keyword in Java [Chiel van de Steeg][] + +New Grammars: + +- added 3rd party CODEOWNERS grammar to SUPPORTED_LANGUAGES [nataliia-radina][] +- added 3rd party Luau grammar to SUPPORTED_LANGUAGES [Robloxian Demo][] +- added 3rd party ReScript grammar to SUPPORTED_LANGUAGES [Paul Tsnobiladzé][] +- added 3rd party Zig grammar to SUPPORTED_LANGUAGES [Hyou BunKen][] +- added 3rd party WGSL grammar to SUPPORTED_LANGUAGES [Arman Uguray][] +- added 3rd party Unison grammar to SUPPORTED_LANGUAGES [Rúnar Bjarnason][] +- added 3rd party Phix grammar to SUPPORTED_LANGUAGES [PeteLomax][] +- added 3rd party Mirth grammar to SUPPORTED_LANGUAGES [Sierra][] +- added 3rd party JSONata grammar to SUPPORTED_LANGUAGES [Vlad Dimov][] + +Developer Tool: + +- enh(tools): order CSS options picklist [David Schach][] +- enh(tools): remove duplicate CSS options [David Schach][] +- (typescript): deprecate old `highlight` API [Misha Kaletsky][] + +Themes: + +- Added `1c-light` theme a like in the IDE 1C:Enterprise 8 (for 1c) [Vitaly Barilko][] + +[Kisaragi Hiu]: https://github.com/kisaragi-hiu +[Melkor-1]: https://github.com/Melkor-1 +[PeteLomax]: https://github.com/petelomax +[gnysek]: https://github.com/gnysek +[Eisenwave]: https://github.com/Eisenwave +[Aral Balkan]: https://github.com/aral +[Lê Duy Quang]: https://github.com/leduyquang753 +[Mohamed Ali]: https://github.com/MohamedAli00949 +[JaeBaek Lee]: https://github.com/ThinkingVincent +[Bradley Mackey]: https://github.com/bradleymackey +[Kristian Ekenes]: https://github.com/ekenes +[Aneesh Kulkarni]: https://github.com/aneesh98 +[Bruno Meneguele]: https://github.com/bmeneg +[Tara]: https://github.com/taralei +[Felix Uhl]: https://github.com/iFreilicht +[nataliia-radina]: https://github.com/Nataliia-Radina +[Robloxian Demo]: https://github.com/RobloxianDemo +[Paul Tsnobiladzé]: https://github.com/tsnobip +[Jonah Jeleniewski]: https://github.com/cirras +[Josh Goebel]: https://github.com/joshgoebel +[CY Fung]: https://github.com/cyfung1031 +[Vitaly Barilko]: https://github.com/Diversus23 +[Patrick Chiu]: https://github.com/patrick-kw-chiu +[Alvin Joy]: https://github.com/alvinsjoy +[Lisa Ugray]: https://github.com/lugray +[TaraLei]: https://github.com/TaraLei +[Cameron Taylor]: https://github.com/ninjamuffin99 +[Vasily Polovnyov]: https://github.com/vast +[Arman Uguray]: https://github.com/armansito +[Rúnar Bjarnason]: https://github.com/runarorama +[Carl Räfting]: https://github.com/carlrafting +[BackupMiles]: https://github.com/BackupMiles +[Julien Bloino]: https://github.com/jbloino +[Sierra]: https://github.com/casuallyblue +[Vlad Dimov]: https://github.com/DevDimov +[Chiel van de Steeg]: https://github.com/cvdsteeg + + +## Version 11.9.0 + +CAVEATS / POTENTIALLY BREAKING CHANGES + +- Drops support for Node 14.x, which is no longer supported by Node.js. +- In the `node` build `styles/*.css` files now ship un-minified + with minified counterparts as: `styles/*.min.css` [mvorisek][] + (this makes things consistent with our `cdn` builds) + +Parser: + +- (enh) prevent re-highlighting of an element [joshgoebel][] +- (chore) Remove discontinued badges from README [Bradley Mackey][] +- (chore) Fix build size report [Bradley Mackey][] + +New Grammars: + +- added 3rd party Iptables grammar to SUPPORTED_LANGUAGES [Checconio][] +- added 3rd party x86asmatt grammar to SUPPORTED_LANGUAGES [gondow][] +- added 3rd party riscv64 grammar to SUPPORTED_LANGUAGES [aana-h2][] +- added 3rd party Ballerina grammar to SUPPORTED_LANGUAGES [Yasith Deelaka][] + +Core Grammars: + +- fix(cpp) fixed highlighter break state [Md Saad Akhtar][] +- fix(rust) added negative-lookahead for callable keywords `if` `while` `for` [Omar Hussein][] +- enh(armasm) added `x0-x30` and `w0-w30` ARMv8 registers [Nicholas Thompson][] +- enh(haxe) added `final`, `is`, `macro` keywords and `$` identifiers [Robert Borghese][] +- enh(haxe) support numeric separators and suffixes [Robert Borghese][] +- fix(haxe) fixed metadata arguments and support non-colon syntax [Robert Borghese][] +- fix(haxe) differentiate `abstract` declaration from keyword [Robert Borghese][] +- fix(bash) do not delimit a string by an escaped apostrophe [hancar][] +- enh(swift) support `macro` keyword [Bradley Mackey][] +- enh(swift) support parameter pack keywords [Bradley Mackey][] +- enh(swift) regex literal support [Bradley Mackey][] +- enh(swift) `@unchecked` and `@Sendable` support [Bradley Mackey][] +- enh(scala) add using directives support `//> using foo bar` [Jamie Thompson][] +- fix(scala) fixed comments in constructor arguments not being properly highlighted [Isaac Nonato][] +- enh(swift) ownership modifiers support [Bradley Mackey][] +- enh(nsis) Add `!assert` compiler flag [idleberg][] +- fix(haskell) do not treat double dashes inside infix operators as comments [Zlondrej][] +- enh(rust) added `eprintln!` macro [qoheniac][] +- enh(leaf) update syntax to 4.0 [Samuel Bishop][] +- fix(reasonml) simplify syntax and align it with ocaml [jchavarri][] +- fix(swift) `warn_unqualified_access` is an attribute [Bradley Mackey][] +- enh(swift) macro attributes are highlighted as keywords [Bradley Mackey][] +- enh(stan) updated for version 2.33 (#3859) [Brian Ward][] +- enh(llvm) match additional types [wtz][] +- fix(css) added '_' css variable detection [Md Saad Akhtar][] +- enh(groovy) add `record` and `var` as keywords [Guillaume Laforge][] + +Developer Tool: + +- (chore) Update dev tool to use the new `highlight` API. [Shah Shabbir Ahmmed][] +- (enh) Auto-update the highlighted output when the language dropdown changes. [Shah Shabbir Ahmmed][] + +[Robert Borghese]: https://github.com/RobertBorghese +[Isaac Nonato]: https://github.com/isaacnonato +[Shah Shabbir Ahmmed]: https://github.com/shabbir23ah +[Josh Goebel]: https://github.com/joshgoebel +[Checconio]: https://github.com/Checconio +[Bradley Mackey]: https://github.com/bradleymackey +[mvorisek]: https://github.com/mvorisek +[qoheniac]: https://github.com/qoheniac +[Samuel Bishop]: https://github.com/dannflor +[gondow]: https://github.com/gondow +[jchavarri]: https://github.com/jchavarri +[aana-h2]: https://github.com/aana-h2 +[Nicholas Thompson]: https://github.com/NAThompson +[Yasith Deelaka]: https://github.com/YasithD +[Brian Ward]: https://github.com/WardBrian +[wtz]: https://github.com/wangtz0607 +[Md Saad Akhtar]: https://github.com/akhtarmdsaad +[Guillaume Laforge]: https://github.com/glaforge + + +## Version 11.8.0 + +Parser engine: + +- added a function to default export to generate a fresh highlighter instance to be used by extensions [WisamMechano][] +- added BETA `__emitTokens` key to grammars to allow then to direct their own parsing, only using Highlight.js for the HTML rendering [Josh Goebel][] +- (enh) add `removePlugin` api [faga295][] +- (fix) typo in language name of `JavaScript` [Cyrus Kao][] + +New Grammars: + +- added 3rd party Lang grammar to SUPPORTED_LANGUAGES [AdamRaichu][] +- added 3rd party C3 grammar to SUPPORTED_LANGUAGES [aliaegik][] + +Core Grammars: + +- enh(sql) support `_` in variable names [joshgoebel][] +- enh(mathematica) update keywords list to 13.2.1 [arnoudbuzing][] +- enh(protobuf) add `proto` alias for Protobuf [dimitropoulos][] +- enh(sqf) latest changes in Arma 3 v2.11 [Leopard20][] +- enh(js/ts) Added support for GraphQL tagged template strings [Ali Ukani][] +- enh(javascript) add sessionStorage to list of built-in variables [Jeroen van Vianen][] +- enh(http) Add support for HTTP/3 [Rijenkii][] +- added 3rd party Motoko grammar to SUPPORTED_LANGUAGES [rvanasa][] +- added 3rd party Candid grammar to SUPPORTED_LANGUAGES [rvanasa][] +- fix(haskell) Added support for characters [CrystalSplitter][] +- enh(dart) Add `base`, `interface`, `sealed`, and `when` keywords [Sam Rawlins][] +- enh(php) detect newer more flexible NOWdoc syntax (#3679) [Timur Kamaev][] +- enh(python) improve autodetection of code with type hinting any function's return type (making the `->` operator legal) [Keyacom][] +- enh(bash) add `select` and `until` as keywords + +[arnoudbuzing]: https://github.com/arnoudbuzing +[aliaegik]: https://github.com/aliaegik +[Josh Goebel]: https://github.com/joshgoebel +[Timur Kamaev]: https://github.com/doiftrue +[Leopard20]: https://github.com/Leopard20/ +[WisamMechano]: https://github.com/wisammechano +[faga295]: https://github.com/faga295 +[AdamRaichu]: https://github.com/AdamRaichu +[Ali Ukani]: https://github.com/ali +[Jeroen van Vianen]: https://github.com/morinel +[gnysek]: https://github.com/gnysek +[Rijenkii]: https://github.com/rijenkii +[faga295]: https://github.com/faga295 +[rvanasa]: https://github.com/rvanasa +[CrystalSplitter]: https://github.com/CrystalSplitter +[Sam Rawlins]: https://github.com/srawlins +[Keyacom]: https://github.com/Keyacom +[Boris Verkhovskiy]: https://github.com/verhovsky +[Cyrus Kao]: https://github.com/CyrusKao +[Zlondrej]: https://github.com/zlondrej + + +## Version 11.7.0 + +New Grammars: + +- added 3rd party LookML grammar to SUPPORTED_LANGUAGES [Josh Temple][] +- added 3rd party FunC grammar to SUPPORTED_LANGUAGES [Nikita Sobolev][] +- Added 3rd party Flix grammar to SUPPORTED_LANGUAGES [The Flix Organisation][] +- Added 3rd party RVT grammar to SUPPORTED_LANGUAGES [Sopitive][] + +Grammars: + +- enh(scheme) add `scm` alias for Scheme [matyklug18][] +- fix(typescript) patterns like ` async function title highlights (#3405) [Josh Goebel][] +- enh(twig) update keywords list (#3415) [Matthieu Lempereur][] +- fix(python) def, class keywords detected mid-identifier (#3381) [Josh Goebel][] +- fix(python) Fix recognition of numeric literals followed by keywords without whitespace (#2985) [Richard Gibson][] +- enh(swift) add SE-0290 unavailability condition (#3382) [Bradley Mackey][] +- fix(fsharp) Highlight operators, match type names only in type annotations, support quoted identifiers, and other smaller fixes. [Melvyn Laïly][] +- enh(java) add `sealed` and `non-sealed` keywords (#3386) [Bradley Mackey][] +- enh(js/ts) improve `CLASS_REFERENCE` (#3411) [Josh Goebel][] +- enh(nsis) Update defines pattern to allow `!` (#3417) [idleberg][] +- enh(nsis) Update language strings pattern to allow `!` (#3420) [idleberg][] +- fix(stan) Updated for Stan 2.28 and other misc. improvements (#3410) +- enh(nsis) Update variables pattern (#3416) [idleberg][] +- fix(clojure) Several issues with Clojure highlighting (#3397) [Björn Ebbinghaus][] + - fix(clojure) `comment` macro catches more than it should (#3395) + - fix(clojure) `$` in symbol breaks highlighting + - fix(clojure) Add complete regex for number detection + - enh(clojure) Add character mode for character literals + - fix(clojure) Inconsistent namespaced map highlighting + - enh(clojure) Add `regex` mode to regex literal + - fix(clojure) Remove inconsistent/broken highlighting for metadata + - enh(clojure) Add `punctuation` mode for commas. +- fix(julia) Enable the `jldoctest` alias (#3432) [Fons van der Plas][] + +Developer Tools: + +- (chore) add gzip size compression report (#3400) [Bradley Mackey][] + +Themes: + +- Modified background color in css for Gradient Light and Gradient Dark themes [Samia Ali][] + +[John Foster]: https://github.com/jf990 +[Pegasis]: https://github.com/PegasisForever +[Wojciech Kania]: https://github.com/wkania +[Jeylani B]: https://github.com/jeyllani +[Richard Gibson]: https://github.com/gibson042 +[Bradley Mackey]: https://github.com/bradleymackey +[Melvyn Laïly]: https://github.com/mlaily +[Björn Ebbinghaus]: https://github.com/MrEbbinghaus +[Josh Goebel]: https://github.com/joshgoebel +[Samia Ali]: https://github.com/samiaab1990 +[Matthieu Lempereur]: https://github.com/MrYamous +[idleberg]: https://github.com/idleberg +[Fons van der Plas]: https://github.com/fonsp +[Felipe Contreras]: https://github.com/felipec + +## Version 11.3.1 + +Build: + +- (fix) Grammar CDN modules not generated correctly. (#3363) [Josh Goebel][] + +[Josh Goebel]: https://github.com/joshgoebel + + +## Version 11.3.0 + +Build: + +- add `HighlightJS` named export (#3295) [Josh Goebel][] +- add `.default` named export to CJS builds (#3333) [Josh Goebel][] + +Parser: + +- add first rough performance testing script (#3280) [Austin Schick][] +- add `throwUnescapedHTML` to warn against potential HTML injection [Josh Goebel][] +- expose `regex` helper functions via `hljs` injection [Josh Goebel][] + - concat + - lookahead + - either + - optional + - anyNumberOfTimes + +Grammars: + +- fix(ts) some complex types would classify as JSX (#3278) [Josh Goebel][] +- fix(js/ts) less false positives for `class X extends Y` (#3278) [Josh Goebel][] +- enh(css): add properties from several W3C (Candidate) Recommendations (#3308) +- fix(js/ts) `Float32Array` highlighted incorrectly (#3353) [Josh Goebel][] +- fix(css) single-colon psuedo-elements no longer break highlighting (#3240) [Josh Goebel][] +- fix(scss) single-colon psuedo-elements no longer break highlighting (#3240) [Josh Goebel][] +- enh(fsharp) rewrite most of the grammar, with many improvements [Melvyn Laïly][] +- enh(go) better type highlighting, add `error` type [Josh Goebel][] +- fix(js/ts) regex inside `SUBST` is no longer highlighted [Josh Goebel][] +- fix(python) added support for unicode identifiers (#3280) [Austin Schick][] +- enh(css/less/stylus/scss) improve consistency of function dispatch (#3301) [Josh Goebel][] +- enh(css/less/stylus/scss) detect block comments more fully (#3301) [Josh Goebel][] +- fix(cpp) switch is a keyword (#3312) [Josh Goebel][] +- fix(cpp) fix `xor_eq` keyword highlighting. [Denis Kovalchuk][] +- enh(c,cpp) highlight type modifiers as type (#3316) [Josh Goebel][] +- enh(css/less/stylus/scss) add support for CSS Grid properties [monochromer][] +- enh(java) add support for Java Text Block (#3322) [Teletha][] +- enh(scala) add missing `do` and `then` keyword (#3323) [Nicolas Stucki][] +- enh(scala) add missing `enum`, `export` and `given` keywords (#3328) [Nicolas Stucki][] +- enh(scala) remove symbol syntax and fix quoted code syntax (#3324) [Nicolas Stucki][] +- enh(scala) add Scala 3 `extension` soft keyword (#3326) [Nicolas Stucki][] +- enh(scala) add Scala 3 `end` soft keyword (#3327) [Nicolas Stucki][] +- enh(scala) add `inline` soft keyword (#3329) [Nicolas Stucki][] +- enh(scala) add `using` soft keyword (#3330) [Nicolas Stucki][] +- enh(fsharp) added `f#` alias (#3337) [Bahnschrift][] +- enh(bash) added gnu core utilities (#3342) [katzeprior][] +- enh(nsis) add new NSIS commands (#3351) [idleberg][] +- fix(nsis) set `case_insensitive` to `true` (#3351) [idleberg][] +- fix(css/less/stylus/scss) highlight single-colon psuedo-elements properly (#3240) [zsoltlengyelit][] +- fix(css) add css hex color alpha support (#3360) [ierehon1905][] + +[Austin Schick]: https://github.com/austin-schick +[Josh Goebel]: https://github.com/joshgoebel +[Denis Kovalchuk]: https://github.com/deniskovalchuk +[monochromer]: https://github.com/monochromer +[Teletha]: https://github.com/teletha +[Nicolas Stucki]: https://github.com/nicolasstucki +[Bahnschrift]: https://github.com/Bahnschrift +[Melvyn Laïly]: https://github.com/mlaily +[katzeprior]: https://github.com/katzeprior +[zsoltlengyelit]: github.com/zsoltlengyelit +[Syb Wartna]:https://github.com/waarissyb +[idleberg]: https://github.com/idleberg +[ierehon1905]: https://github.com/ierehon1905 + + +## Version 11.2.0 + +Build: + +- fix: run Node build CSS files thru CSS processor also (#3284) [Josh Goebel][] + +Parser: + +- fix(csharp) Fix assignments flagging as functions [Josh Goebel][] +- fix(types) Fix some type definition issues (#3274) [Josh Goebel][] +- fix(verilog) Fix directive handling (#3283) [Josh Goebel][] +- fix(verilog) Fix binary number false positives on `_` (#3283) [Josh Goebel][] +- enh(verilog) `__FILE__` and `__LINE__` constants (#3283) [Josh Goebel][] +- enh(verilog) tighten keyword regex (#3283) [Josh Goebel][] + + +Grammars: + +- enh(swift) Add `isolated`/`nonisolated` keywords (#3296) [Bradley Mackey][] + +New Languages: + +- Added 3rd party X# grammar to SUPPORTED_LANGUAGES [Patrick Kruselburger][] +- Added 3rd party MKB grammar to SUPPORTED_LANGUAGES (#3297) [Dereavy][] + +[Josh Goebel]: https://github.com/joshgoebel +[Patrick Kruselburger]: https://github.com/PatrickKru +[Bradley Mackey]: https://github.com/bradleymackey +[Dereavy]: https://github.com/dereavy + + +## Version 11.1.0 + +Grammars: + +- fix(csharp) add missing `catch` keyword (#3251) [Konrad Rudolph][] +- add additional keywords to csp.js (#3244) [Elijah Conners][] +- feat(css) handle css variables syntax (#3239) [Thanos Karagiannis][] +- fix(markdown) Images with empty alt or links with empty text (#3233) [Josh Goebel][] +- enh(powershell) added `pwsh` alias (#3236) [tebeco][] +- fix(r) fix bug highlighting examples in doc comments [Konrad Rudolph][] +- fix(python) identifiers starting with underscore not highlighted (#3221) [Antoine Lambert][] +- enh(clojure) added `edn` alias (#3213) [Stel Abrego][] +- enh(elixir) much improved regular expression sigil support (#3207) [Josh Goebel][] +- enh(elixir) updated list of keywords (#3212) [Angelika Tyborska][] +- fix(elixir) fixed number detection when numbers start with a zero (#3212) [Angelika Tyborska][] +- fix(ps1) Flag highlighted incorrectly (#3167) [Pankaj Patil][] +- fix(latex) Allow wider syntax for magic comments (#3243) [Benedikt Wilde][] +- fix(js/ts) Constants may include numbers [Josh Goebel][] + +[Stel Abrego]: https://github.com/stelcodes +[Josh Goebel]: https://github.com/joshgoebel +[Antoine Lambert]: https://github.com/anlambert +[Elijah Conners]: https://github.com/elijahepepe +[Angelika Tyborska]: https://github.com/angelikatyborska +[Konrad Rudolph]: https://github.com/klmr +[tebeco]: https://github.com/tebeco +[Pankaj Patil]: https://github.com/patil2099 +[Benedikt Wilde]: https://github.com/schtandard +[Thanos Karagiannis]: https://github.com/thanoskrg + + +## Version 11.0.0 + +**This is a major release.** As such it contains breaking changes which may require action from users. Please read [VERSION_11_UPGRADE.md](https://github.com/highlightjs/highlight.js/blob/main/VERSION_11_UPGRADE.md) for a detailed summary of all breaking changes. + +### Potentially breaking changes + +Unless otherwise attributed items below are thanks to [Josh Goebel][] (ref: [#2558](https://github.com/highlightjs/highlight.js/issues/2558)). + +*The below list should only be considered to be a high-level summary.* + +Deprecations / Removals / API Changes: + +- `initHighlighting()` and `initHighlightingOnLoad()` deprecated. **Use `highlightAll()`.** +- `highlightBlock(el)` deprecated. **Use `highlightElement(el)`** +- `before:highlightBlock` & `after:highlightBlock` callbacks deprecated. **Use equivalent `highlightElement` callbacks.** +- `highlight(languageName, code, ignoreIllegals, continuation)` signature deprecated. **Use `highlight(code, {language, ignoreIllegals})`.** +- Deprecated `highlight()` signature no longer supports `continuation` argument. +- `tabReplace` option removed. Consider a plugin. +- `useBR` option removed. Consider a plugin or CSS. +- `requireLanguage()` removed. **Use `getLanguage()`.** +- `endSameAsBegin` mode key removed. **Use `hljs.END_SAME_AS_BEGIN`.** +- `lexemes` mode key removed. **Use `keywords.$pattern`.** +- The return values/keys of some APIs have changed slightly. + +Security: + +- HTML auto-passthru has been removed. Consider a plugin. +- Unescaped HTML is now stripped (for security). A warning is logged to the console. (#3057) [Josh Goebel][] + +Themes: + +- The default padding of all themes increases (0.5em => 1em). +- `schoolbook` has been updated to remove the lined background. +- `github` updated to better match modern GitHub (#1616) [Jan Pilzer][] +- `github-gist` has been removed in favor of `github` [Jan Pilzer][] +- Base16 named themes have been updated to their "canonical" versions +- `nnfx` updated for v11 xml styles and improved css support + +Language Grammars: + +- Default CDN build drops support for several languages. +- Some language grammar files have been removed. +- Some redundant language aliases have been removed. + +### Other changes + +Parser: + +- enh(vala) improve language detection for Vala (#3195) [Konrad Rudolph][] +- enh(r) add support for operators, fix number highlighting bug (#3194, #3195) [Konrad Rudolph][] +- enh(parser) add `beginScope` and `endScope` to allow separate scoping begin and end (#3159) [Josh Goebel][] +- enh(parsed) `endScope` now supports multi-class matchers as well (#3159) [Josh Goebel][] +- enh(parser) `highlightElement` now always tags blocks with a consistent `language-[name]` class [Josh Goebel][] + - subLanguage `span` tags now also always have the `language-` prefix added +- enh(parser) support multi-class matchers (#3081) [Josh Goebel][] +- enh(parser) Detect comments based on english like text, rather than keyword list [Josh Goebel][] +- adds `title.class.inherited` sub-scope support [Josh Goebel][] +- adds `title.class` sub-scope support (#3078) [Josh Goebel][] +- adds `title.function` sub-scope support (#3078) [Josh Goebel][] +- adds `beforeMatch` compiler extension (#3078) [Josh Goebel][] +- adds `cssSelector ` configuration option (#3180) [James Edington][] + +Grammars: + +- enh(all) `.meta-keyword` => `.meta .keyword` (nested scopes) (#3167) [Josh Goebel][] +- enh(all) `.meta-string` => `.meta .string` (nested scopes) (#3167) [Josh Goebel][] +- enh(swift) add `actor` keyword (#3171) [Bradley Mackey][] +- enh(crystal) highlight variables (#3154) [Josh Goebel][] +- fix(ruby) Heredoc without interpolation (#3154) [Josh Goebel][] +- enh(swift) add `@resultBuilder` attribute (#3151) [Bradley Mackey][] +- enh(processing) added `pde` alias (#3142) [Dylan McBean][] +- enh(thrift) Use proper scope for types [Josh Goebel][] +- enh(java) Simplified class-like matcher (#3078) [Josh Goebel][] +- enh(cpp) Simplified class-like matcher (#3078) [Josh Goebel][] +- enh(rust) Simplified class-like matcher (#3078) [Josh Goebel][] +- enh(actionscript) Simplified class-like matcher (#3078) [Josh Goebel][] +- enh(arcade) `function.title` => `title.function` (#3078) [Josh Goebel][] +- enh(autoit) `function.title` => `title.function` (#3078) [Josh Goebel][] +- enh(c) `function.title` => `title.function` (#3078) [Josh Goebel][] +- enh(rust) support function invoke and `impl` (#3078) [Josh Goebel][] +- chore(properties) disable auto-detection #3102 [Josh Goebel][] +- fix(properties) fix incorrect handling of non-alphanumeric keys #3102 [Egor Rogov][] +- enh(java) support functions with nested template types (#2641) [Josh Goebel][] +- enh(java) highlight types and literals separate from keywords (#3074) [Josh Goebel][] +- enh(shell) add alias ShellSession [Ryan Mulligan][] +- enh(shell) consider one space after prompt as part of prompt [Ryan Mulligan][] +- fix(nginx) fix bug with $ and @ variables [Josh Goebel][] +- enh(nginx) improving highlighting of some sections [Josh Goebel][] +- fix(vim) variable names may not be zero length [Josh Goebel][] +- enh(sqf) Updated keywords to Arma 3 v2.02 (#3084) [R3voA3][] +- enh(sqf) Refactored function regex to match CBA component func naming scheme (#3181) [JonBons][] +- enh(nim) highlight types properly (not as built-ins) [Josh Goebel][] +- (chore) throttle deprecation messages (#3092) [Mihkel Eidast][] +- enh(c) Update keyword list for C11/C18 (#3010) [Josh Goebel][] +- enh(parser) highlight object properties (#3072) [Josh Goebel][] +- enh(javascript/typescript) highlight object properties (#3072) [Josh Goebel][] +- enh(haskell) add support for BinaryLiterals (#3150) [Martijn Bastiaan][] +- enh(haskell) add support for NumericUnderscores (#3150) [Martijn Bastiaan][] +- enh(haskell) add support for HexFloatLiterals (#3150) [Martijn Bastiaan][] +- fix(c,cpp) allow declaring multiple functions and (for C++) parenthetical initializers (#3155) [Erik Demaine][] +- enh(rust) highlight raw byte string literals correctly (#3173) [Nico Abram][] +- fix(cpp) fix detection of common functions that are function templates (#3178) [Kris van Rens][] +- enh(cpp) add various keywords and commonly used types for hinting (#3178) [Kris van Rens][] +- enh(cpp) cleanup reserved keywords and type lists (#3178) [Kris van Rens][] + +New Languages: + +- Added 3rd party Glimmer grammar to SUPPORTED_LANGUAGES(#3123) [NullVoxPopuli][] +- Added Wren support [Josh Goebel][] +- Added NestedText support [Josh Goebel][] +- Added WebAssembly language grammar [Josh Goebel][] +- Added 3rd party Splunk search processing language grammar to SUPPORTED_LANGUAGES (#3090) [Wei Su][] +- Added 3rd party ZenScript grammar to SUPPORTED_LANGUAGES(#3106) [Jared Luboff][] +- Added 3rd party Papyrus grammar to SUPPORTED_LANGUAGES(#3125) [Mike Watling][] + +Theme Improvements: + +- Added all official Base16 themes (over 150 new themes) [Josh Goebel][] +- chore(themes) remove `builtin-name` CSS class (#3119) [Josh Goebel][] +- chore(theme) Update GitHub theme css to match GitHub's current styling (#1616) [Jan Pilzer][] +- chore(theme) Update Srcery theme css to match its Emacs implementation [Chen Bin][] + +New Themes: + +- DeviBeans Dark by [Farzad Sadeghi][] +- GitHub Dark and GitHub Dark Dimmed [Jan Pilzer][] + +Dev Improvements: + +- (chore) greatly improve match scope visualization in dev tool (#3126) [NullVoxPopuli][] +- (fix) CSS used for devtool needed an adjustment to fix too wide of content (#3133) [NullVoxPopuli][] + +[Farzad Sadeghi]: https://github.com/terminaldweller +[Martijn Bastiaan]: https://github.com/martijnbastiaan +[Bradley Mackey]: https://github.com/bradleymackey +[Dylan McBean]: https://github.com/DylanMcBean +[Josh Goebel]: https://github.com/joshgoebel +[Ryan Mulligan]: https://github.com/ryantm +[R3voA3]: https://github.com/R3voA3 +[JonBons]: https://github.com/JonBons +[Wei Su]: https://github.com/swsoyee +[Jared Luboff]: https://github.com/jaredlll08 +[NullVoxPopuli]: https://github.com/NullVoxPopuli +[Mike Watling]: https://github.com/Pickysaurus +[Nico Abram]: https://github.com/nico-abram +[James Edington]: http://www.ishygddt.xyz/ +[Jan Pilzer]: https://github.com/Hirse +[Kris van Rens]: https://github.com/krisvanrens + + +## Version 10.7.1 + +- fix(parser) Resolves issues with TypeScript types [Josh Goebel][] + +### Version 10.7.0 + +Parser: + +- keywords now have a maximum # of times they provide relevance (#3129) [Josh Goebel][] +- enh(api) add `unregisterLanguage` method (#3009) [Antoine du Hamel][] +- enh: Make alias registration case insensitive (#3026) [David Ostrovsky][] +- fix(parser) `highlightAll()` now works if the library is lazy loaded [Josh Goebel][] + +New Languages: + +- Added 3rd party RiScript grammar to SUPPORTED_LANGUAGES (#2988) [John C][] +- Added 3rd party HLSL grammar to SUPPORTED_LANGUAGES (#3002) [Stef Levesque][] +- Added 3rd party Q# grammar to SUPPORTED_LANGUAGES(#3006) [Vyron Vasileiadis][] + +Language grammar improvements: + +- enh(js/ts) class references (CamelCase) are highlighted (#3169) [Josh Goebel][] +- enh(js/ts) constants (ALL_CAPS) are highlighted (#3169) [Josh Goebel][] +- enh(js/ts) highlights function invokation (#3169) [Josh Goebel][] +- enh(js/ts) functions assigned to variables are now highlighted `title.function` (#3169) [Josh Goebel][] +- enh(parser) smarter detection of comments (#2827) [Josh Goebel][] +- fix(python) allow keywords immediately following numbers (#2985) [Josh Goebel][] +- fix(xml) char immediately following tag close mis-highlighted (#3044) [Josh Goebel][] +- fix(ruby) fix `defined?()` mis-highlighted as `def` (#3025) [Josh Goebel][] +- fix(c) comments after `#include ` blocks (#3041) [Josh Goebel][] +- fix(cpp) comments after `#include ` blocks (#3041) [Josh Goebel][] +- enh(cpp) Highlight all function dispatches (#3005) [Josh Goebel][] +- enh(python) support type hints and better type support (#2972) [Josh Goebel][] +- enh(gml) Add additional GML 2.3 keywords (#2984) [xDGameStudios][] +- fix(cpp) constructor support for initializers (#3001) [Josh Goebel][] +- enh(php) Add `trait` to class-like naming patterns (#2997) [Ayesh][] +- enh(php) Add `Stringable`, `UnhandledMatchError`, and `WeakMap` classes/interfaces (#2997) [Ayesh][] +- enh(php) Add `mixed` to list of keywords (#2997) [Ayesh][] +- enh(php) Add support binary, octal, hex and scientific numerals with underscore separator support (#2997) [Ayesh][] +- enh(php) Add support for Enums (#3004) [Ayesh][] +- enh(ecmascript) Add built-in types [Vaibhav Chanana][] +- enh(kotlin) Add `kts` as an alias for Kotlin (#3021) [Vaibhav Chanana][] +- enh(css) Add `font-smoothing` to attributes list for CSS (#3027) [AndyKIron][] +- fix(python) Highlight `print` and `exec` as a builtin (#1468) [Samuel Colvin][] +- fix(csharp) Fix unit being highlighted instead of uint (#3046) [Spacehamster][] +- enh(swift) add async/await keywords (#3048) [Bradley Mackey][] + +Deprecations: + +- `highlight(languageName, code, ignoreIllegals, continuation)` deprecated as of 10.7 + - Please use the newer API which takes `code` and then accepts options as an object + - IE: `highlight(code, {language, ignoreIllegals})` + - `continuation` is for internal use only and no longer supported +- `highlightBlock(el)` deprecated as of 10.7. + - Please use `highlightElement(el)` instead. + - Plugin callbacks renamed `before/after:highlightBlock` => `before/after:highlightElement` + - Plugin callback now takes `el` vs `block` attribute + - The old API and callbacks will be supported until v12. + + +[Stef Levesque]: https://github.com/stef-levesque +[Josh Goebel]: https://github.com/joshgoebel +[John Cheung]: https://github.com/Real-John-Cheung +[xDGameStudios]: https://github.com/xDGameStudios +[Ayesh]: https://github.com/Ayesh +[Vyron Vasileiadis]: https://github.com/fedonman +[Antoine du Hamel]: https://github.com/aduh95 +[Vaibhav Chanana]: https://github.com/il3ven +[David Ostrovsky]: https://github.com/davido +[AndyKIron]: https://github.com/AndyKIron +[Samuel Colvin]: https://github.com/samuelcolvin + +## Version 10.6.0 + +New Languages: + +- Added 3rd party Laravel Blade grammar to SUPPORTED_LANGUAGES (#2944) [Michael Newton][] + +Language grammar improvements: + +- enh(scala) fix triple quoted strings (#2987) [Josh Goebel][] +- enh(perl) Much improved regex detection (#2960) [Josh Goebel][] +- enh(swift) Improved highlighting for operator and precedencegroup declarations. (#2938) [Steven Van Impe][] +- fix(xml) Support single-character namespaces. (#2957) [Jan Pilzer][] +- enh(ruby) Support for character literals (#2950) [Vaibhav Chanana][] +- enh(powershell) Add three VALID_VERBS and update the reference link (#2981) [davidhcefx][] +- fix(php) Highlighting of anonymous functions without {} block [Vaibhav Chanana][] + +Grammar Deprecations: + +- Deprecate `c-like`, though you should not be using it directly anyways. + - will be removed in v11. +- `c` and `cpp` are now wholly unique grammars that will diverge over time + +Parser: + +- new simpler `highlightAll()` API (#2962) [Josh Goebel][] + - this should be a drop-in replacement for both `initHighlighting()` and `initHighlightingOnLoad()` + - note: it does not prevent itself from being called multiple times (as the previous API did) +- `beginKeyword` no longer bestows double relevance (#2953) [Josh Goebel][] +- allow `keywords` to be an array of strings [Josh Goebel][] +- add `modes.MATCH_NOTHING_RE` that will never match + - This can be used with `end` to hold a mode open (it must then be ended with `endsParent` in one of it's children modes) [Josh Goebel][] + +Deprecations: + +- `initHighlighting()` and `initHighlightingOnLoad()` deprecated. + - Please use the new `highlightAll()` API instead. + - Deprecated as of 10.6. + - These will both be aliases to `highlightAll` in v11. + +[Michael Newton]: https://github.com/miken32 +[Steven Van Impe]: https://github.com/svanimpe/ +[Josh Goebel]: https://github.com/joshgoebel +[Vaibhav Chanana]: https://github.com/il3ven +[davidhcefx]: https://github.com/davidhcefx +[Jan Pilzer]: https://github.com/Hirse + + +## Version 10.5.0 + +Build: + +- Add Subresource Integrity digest lists to `cdn-assets` [Josh Goebel][] +- R and VB.net grammars now ship in our default build (`:common`) [Josh Goebel][] + +Parser: + +- add `match` as sugar for simple `begin` only matches (#2834) [Josh Goebel][] +- allow `illegal` to also be an array of regex (#2834) [Josh Goebel][] +- add `compilerExtensions` allows grammers to influence mode compilation (#2834) [Josh Goebel][] + - some internal pieces are now simple compiler extensions + +New Languages: + +- Added 3rd party Red & Rebol grammar to SUPPORTED_LANGUAGES (#2872) [Oldes Huhuman][] + +Language grammar improvements: + +- enh: CSS grammars now share common foundation, keywords, etc. (#2937) [Josh Goebel][] + - enh(css): many consistency improvements + - enh(scss): many consistency improvements + - enh(stylus): many consistency improvements + - enh(less): many consistency improvements +- enh(cpp): Support C++ pack expansion in function arguments [Martin Dørum][] +- enh(makefile): Add `make` as an alias (#2883) [tripleee][] +- enh(swift) Improved grammar for strings (#2819) [Steven Van Impe][] +- enh(swift) Grammar improvements (#2908) [Steven Van Impe][] + - New grammar for keywords and built-ins + - Added support for operator highlighting + - New grammar for attributes + - Added support for quoted identifiers, implicit parameters, and property wrapper projections + - Support for more complex expressions in string interpolation +- enh(swift) Improved highlighting for types and generic arguments (#2920) [Steven Van Impe][] +- enh(swift) Improved highlighting for functions, initializers, and subscripts (#2930) [Steven Van Impe][] +- fix(http) avoid recursive sublanguage and tighten rules (#2893) [Josh Goebel][] +- fix(asciidoc): Handle section titles level 5 (#2868) [Vaibhav Chanana][] +- fix(asciidoc): Support unconstrained emphasis syntax (#2869) [Guillaume Grossetie][] +- enh(scheme) Allow `[]` for argument lists (#2913) [Josh Goebel][] +- enh(vb) Large rework of VB.net grammar (#2808) [Jan Pilzer][] + - Adds support for Date data types, see (#2775) + - Adds support for `REM` comments and fixes `'''` doctags (#2875) (#2851) + - Custom number mode to support VB.net specific number flags + - Hex (&H), Oct (&O), and binary (&B) prefixes + - Separating digits with underscores: 90_946 + - Type suffixes: 123UI (unsigned integer) + - Improves directives detection and adds support for `Enable`, `Disable`, and `Then` keywords + - Adds more markup tests +- fix(javascript) Empty block-comments break highlighting (#2896) [Jan Pilzer][] +- enh(dart) Fix empty block-comments from breaking highlighting (#2898) [Jan Pilzer][] +- enh(dart) Fix empty doc-comment eating next line [Jan Pilzer][] +- enh(asciidoc) Adds support for unconstrained bold syntax (#2869) [Guillaume Grossetie][] +- enh(c-like) Incorrect highlighting for interger suffix (#2919) [Vaibhav Chanana][] +- enh(properties) Correctly handle trailing backslash (#2922) [Vaibhav Chanana][] + +Recent Deprecations: + +- HTML "merging" is deprecated. (#2873) [Josh Goebel][] + - HTML inside `
    ` blocks will no longer be magically merged back into the
    +  highlighted code's HTML result - it will instead be silently removed.
    +  - Consider [using a plugin][htmlPlugin] if you truly need this functionality
    +  - Deprecated as of 10.5.0 - will be removed in v11.
    +- `tabReplace` option deprecated. (#2873) [Josh Goebel][]
    +  - **Consider:** Use the CSS `tab-size` property, or simply pre-process the
    +    text yourself before rendering the initial HTML
    +  - otherwise, [use a plugin][tabPlugin]
    +  - Deprecated as of 10.5.0 - will be removed in v11.
    +- `useBR` option deprecated. (#2559) [Josh Goebel][]
    +  - **Recommended:** You really should just use the HTML `
    ` tag
    +  - or perhaps try CSS `white-space: pre;`
    +  - otherwise, [use a plugin][brPlugin]
    +  - Deprecated as of 10.3.0 - will be removed in v11.
    +- `requireLanguage` API is deprecated, will be removed in v11.0.
    +  - **Consider:** Use `getLanguage` (with custom error handling) or built-time dependencies.
    +  - See [Library API](https://highlightjs.readthedocs.io/en/latest/api.html#requirelanguage-name) for more information.
    +  - Deprecated as of 10.4.0 - will be removed in v11.
    +
    +[htmlPlugin]: https://github.com/highlightjs/highlight.js/issues/2889
    +[tabPlugin]: https://github.com/highlightjs/highlight.js/issues/2874
    +[brPlugin]: https://github.com/highlightjs/highlight.js/issues/2559
    +
    +[Martin Dørum]: https://github.com/mortie
    +[Jan Pilzer]: https://github.com/Hirse
    +[Oldes Huhuman]: https://github.com/Oldes
    +[Josh Goebel]: https://github.com/joshgoebel
    +[tripleee]: https://github.com/tripleee
    +[Steven Van Impe]: https://github.com/svanimpe/
    +[Vaibhav Chanana]: https://github.com/il3ven
    +[Guillaume Grossetie]: https://github.com/mogztter
    +
    +
    +## Version 10.4.1 (tentative)
    +
    +Security
    +
    +- (fix) Exponential backtracking fixes for: [Josh Goebel][]
    +  - cpp
    +  - handlebars
    +  - gams
    +  - perl
    +  - jboss-cli
    +  - r
    +  - erlang-repl
    +  - powershell
    +  - routeros
    +- (fix) Polynomial backtracking fixes for: [Josh Goebel][]
    +  - asciidoc
    +  - reasonml
    +  - latex
    +  - kotlin
    +  - gcode
    +  - d
    +  - aspectj
    +  - moonscript
    +  - coffeescript/livescript
    +  - csharp
    +  - scilab
    +  - crystal
    +  - elixir
    +  - basic
    +  - ebnf
    +  - ruby
    +  - fortran/irpf90
    +  - livecodeserver
    +  - yaml
    +  - x86asm
    +  - dsconfig
    +  - markdown
    +  - ruleslanguage
    +  - xquery
    +  - sqf
    +
    +Very grateful to [Michael Schmidt][] for all the help.
    +
    +[Michael Schmidt]: https://github.com/RunDevelopment
    +[Josh Goebel]: https://github.com/joshgoebel
    +
    +
    +## Version 10.4.0
    +
    +A largish release with many improvements and fixes from quite a few different contributors.  Enjoy!
    +
    +Deprecations:
    +
    +- (chore) `requireLanguage` is deprecated.
    +  - Prefer `getLanguage` (with custom error handling) or built-time dependencies.
    +  - See [Library API](https://highlightjs.readthedocs.io/en/latest/api.html#requirelanguage-name) for more information.
    +
    +Parser:
    +
    +- enh(parser) use negative look-ahead for `beginKeywords` support (#2813) [Josh Goebel][]
    +- enh(grammars) allow `classNameAliases` for more complex grammars [Josh Goebel][]
    +- fix(vue): Language name now appears in CSS class (#2807) [Michael Rush][]
    +- (chore) Clean up all regexs to be UTF-8 compliant/ready (#2759) [Josh Goebel][]
    +- enh(grammars) allow `classNameAliases` for more complex grammars [Josh Goebel][]
    +
    +New Languages:
    +
    +- Added 3rd party Chapel grammar to SUPPORTED_LANGUAGES (#2806) [Brad Chamberlain][]
    +- Added BBCode grammar to SUPPORTED_LANGUAGES (#2867) [Paul Reid][]
    +- enh(javascript) Added `node-repl` for Node.js REPL sessions (#2792) [Marat Nagayev][]
    +
    +Language Improvements:
    +
    +- enh(shell) Recognize prompts which contain tilde `~` (#2859) [Guillaume Grossetie][]
    +- enh(shell) Add support for multiline commands with line continuation `\` (#2861) [Guillaume Grossetie][]
    +- enh(autodetect) Over 30+ improvements to auto-detect (#2745) [Josh Goebel][]
    +    - 4-5% improvement in auto-detect against large sample set
    +    - properties, angelscript, lsl, javascript, n1ql, ocaml, ruby
    +    - protobuf, hy, scheme, crystal, yaml, r, vbscript, groovy
    +    - python, java, php, lisp, matlab, clojure, csharp, css
    +- fix(r) fixed keywords not properly spaced (#2852) [Josh Goebel][]
    +- fix(javascript) fix potential catastrophic backtracking (#2852) [Josh Goebel][]
    +- fix(livescript) fix potential catastrophic backtracking (#2852) [Josh Goebel][]
    +- bug(xml) XML grammar was far too imprecise/fuzzy [Josh Goebel][]
    +- enh(xml) Improve precision to prevent false auto-detect positives [Josh Goebel][]
    +- fix(js/ts) Prevent for/while/if/switch from falsly matching as functions (#2803) [Josh Goebel][]
    +- enh(julia) Update keyword lists for Julia 1.x (#2781) [Fredrik Ekre][]
    +- enh(python) Match numeric literals per the language reference [Richard Gibson][]
    +- enh(ruby) Match numeric literals per language documentation [Richard Gibson][]
    +- enh(javascript) Match numeric literals per ECMA-262 spec [Richard Gibson][]
    +- enh(java) Match numeric literals per Java Language Specification [Richard Gibson][]
    +- enh(swift) Match numeric literals per language reference [Richard Gibson][]
    +- enh(php) highlight variables (#2785) [Taufik Nurrohman][]
    +- fix(python) Handle comments on decorators (#2804) [Jonathan Sharpe][]
    +- enh(diff) improve highlighting of diff for git patches [Florian Bezdeka][]
    +- fix(llvm) lots of small improvements and fixes (#2830) [Josh Goebel][]
    +- enh(mathematica) Rework entire implementation [Patrick Scheibe][]
    +  - Correct matching of the many variations of Mathematica's numbers
    +  - Matching of named-characters aka special symbols like `\[Gamma]`
    +  - Updated list of version 12.1 built-in symbols
    +  - Matching of patterns, slots, message-names and braces
    +- fix(swift) Handle keywords that start with `#` [Marcus Ortiz][]
    +- enh(swift) Match `some` keyword [Marcus Ortiz][]
    +- enh(swift) Match `@main` attribute [Marcus Ortiz][]
    +
    +Dev Improvements:
    +
    +- chore(dev) add theme picker to the tools/developer tool (#2770) [Josh Goebel][]
    +- fix(dev) the Vue.js plugin no longer throws an exception when hljs is not in the global namespace [Kyle Brown][]
    +
    +New themes:
    +
    +- *StackOverflow Dark* by [Jan Pilzer][]
    +- *StackOverflow Light* by [Jan Pilzer][]
    +
    +[Guillaume Grossetie]: https://github.com/mogztter
    +[Brad Chamberlain]: https://github.com/bradcray
    +[Marat Nagayev]: https://github.com/nagayev
    +[Fredrik Ekre]: https://github.com/fredrikekre
    +[Richard Gibson]: https://github.com/gibson042
    +[Josh Goebel]: https://github.com/joshgoebel
    +[Taufik Nurrohman]: https://github.com/taufik-nurrohman
    +[Jan Pilzer]: https://github.com/Hirse
    +[Jonathan Sharpe]: https://github.com/textbook
    +[Michael Rush]: https://github.com/rushimusmaximus
    +[Patrick Scheibe]: https://github.com/halirutan
    +[Kyle Brown]: https://github.com/kylebrown9
    +[Marcus Ortiz]: https://github.com/mportiz08
    +[Paul Reid]: https://github.com/RedGuy12
    +
    +
    +## Version 10.3.1
    +
    +Prior version let some look-behind regex sneak in, which does not work
    +yet on Safari.  This release removes those incompatible regexes.
    +
    +Fix:
    +
    +- fix(Safari) Remove currently unsupported look-behind regex ([fix][187e7cfc]) [Josh Goebel][]
    +
    +[Josh Goebel]: https://github.com/joshgoebel
    +[187e7cfc]: https://github.com/highlightjs/highlight.js/commit/187e7cfcb06277ce13b5f35fb6c37ab7a7b46de9
    +
    +
    +## Version 10.3.0
    +
    +Language Improvements:
    +
    +- enh(latex) Complete ground up rewrite of LaTex grammar [schtandard][]
    +- fix(cpp) implement backslash line continuation in comments (#2757) [Konrad Rudolph][]
    +- fix(cpp) improve parsing issues with templates (#2752) [Josh Goebel][]
    +- enh(cpp) add support for `enum (struct|class)` and `union` (#2752) [Josh Goebel][]
    +- fix(js/ts) Fix nesting of `{}` inside template literals SUBST expression (#2748) [Josh Goebel][]
    +- enh(js/ts) Highlight class methods as functions (#2727) [Josh Goebel][]
    +- fix(js/ts) `constructor` is now highlighted as a function title (not keyword) (#2727) [Josh Goebel][]
    +- fix(c-like) preprocessor directives not detected after else (#2738) [Josh Goebel][]
    +- enh(javascript) allow `#` for private class fields (#2701) [Chris Krycho][]
    +- fix(js) prevent runaway regex (#2746) [Josh Goebel][]
    +- fix(bash) enh(bash) allow nested params (#2731) [Josh Goebel][]
    +- fix(python) Fix highlighting of keywords and strings (#2713, #2715) [Konrad Rudolph][]
    +- fix(fsharp) Prevent `(*)` from being detected as a multi-line comment [Josh Goebel][]
    +- enh(bash) add support for heredocs (#2684) [Josh Goebel][]
    +- enh(r) major overhaul of the R language grammar (and fix a few bugs) (#2680) [Konrad Rudolph][]
    +- enh(csharp) Add all C# 9 keywords, and other missing keywords (#2679) [David Pine][]
    +- enh(objectivec) Add `objective-c++` and `obj-c++` aliases for Objective-C [Josh Goebel][]
    +- enh(java) Add support for `record` (#2685) [Josh Goebel][]
    +- fix(csharp) prevent modifier keywords wrongly flagged as `title` (#2683) [Josh Goebel][]
    +- enh(axapta) Update keyword list for Axapta (X++) (#2686) [Ryan Jonasson][]
    +- fix(fortran) FORTRAN 77-style comments (#2677) [Philipp Engel][]
    +- fix(javascript) Comments inside params should be highlighted (#2702) [Josh Goebel][]
    +- fix(scala) Comments inside class header should be highlighted (#1559) [Josh Goebel][]
    +- fix(c-like) Correctly highlight modifiers (`final`) in class declaration (#2696) [Josh Goebel][]
    +- enh(angelscript) Improve heredocs, numbers, metadata blocks (#2724) [Melissa Geels][]
    +- enh(javascript) Implement Numeric Separators (#2617) [Antoine du Hamel][]
    +- enh(typescript) TypeScript also gains support for numeric separators (#2617) [Antoine du Hamel][]
    +- enh(php) Add support for PHP 8 `match` keyword and add `php8` as an alias (#2733) [Ayesh Karunaratne][]
    +- fix(handlebars) Support if else keyboards (#2659) [Tom Wallace][]
    +
    +Deprecations:
    +
    +- `useBR` option deprecated and will be removed in v11.0. (#2559) [Josh Goebel][]
    +
    +[Chris Krycho]: https://github.com/chriskrycho
    +[David Pine]: https://github.com/IEvangelist
    +
    +
    +[Ryan Jonasson]: https://github.com/ryanjonasson
    +[Philipp Engel]: https://github.com/interkosmos
    +[Konrad Rudolph]: https://github.com/klmr
    +[Melissa Geels]: https://github.com/codecat
    +[Antoine du Hamel]: https://github.com/aduh95
    +[Ayesh Karunaratne]: https://github.com/Ayesh
    +[Tom Wallace]: https://github.com/thomasmichaelwallace
    +[schtandard]: https://github.com/schtandard
    +
    +
    +## Version 10.2.1
    +
    + Parser Engine:
    +
    + -  fix(parser) complete fix for resuming matches from same index (#2678) [Josh Goebel][]
    +
    + [Josh Goebel]: https://github.com/yyyc514
    +
    +
    +## Version 10.2.0
    +
    +Parser Engine:
    +
    +- (fix) When ignoring a potential match highlighting can terminate early (#2649) [Josh Goebel][]
    +
    +
    +New themes:
    +
    +- *Gradient Light* by [Samia Ali]()
    +
    +Deprecations:
    +
    +- `fixMarkup` is now deprecated and will be removed in v11.0. (#2534) [Josh Goebel][]
    +
    +Big picture:
    +
    +- Add simple Vue plugin for basic use cases (#2544) [Josh Goebel][]
    +
    +Language Improvements:
    +
    +- fix(bash) Fewer false positives for keywords in arguments (#2669) [sirosen][]
    +- fix(js) Prevent long series of /////// from causing freezes (#2656) [Josh Goebel][]
    +- enh(csharp) Add `init` and `record` keywords for C# 9.0 (#2660) [Youssef Victor][]
    +- enh(matlab) Add new R2019b `arguments` keyword and fix `enumeration` keyword (#2619) [Andrew Janke][]
    +- fix(kotlin) Remove very old keywords and update example code (#2623) [kageru][]
    +- fix(night) Prevent object prototypes method values from being returned in `getLanguage` (#2636) [night][]
    +- enh(java) Add support for `enum`, which will identify as a `class` now (#2643) [ezksd][]
    +- enh(nsis) Add support for NSIS 3.06 commands (#2653) [idleberg][]
    +- enh(php) detect newer more flexible HEREdoc syntax (#2658) [eytienne][]
    +
    +[Youssef Victor]: https://github.com/Youssef1313
    +[Josh Goebel]: https://github.com/joshgoebel
    +[Andrew Janke]: https://github.com/apjanke
    +[Samia Ali]: https://github.com/samiaab1990
    +[kageru]: https://github.com/kageru
    +[night]: https://github.com/night
    +[ezksd]: https://github.com/ezksd
    +[idleberg]: https://github.com/idleberg
    +[eytienne]: https://github.com/eytienne
    +[sirosen]: https://github.com/sirosen
    +
    +## Version 10.1.1
    +
    +Fixes:
    +
    +- Resolve issue on Node 6 due to dangling comma (#2608) [Edwin Hoogerbeets][]
    +- Resolve `index.d.ts is not a module` error (#2603) [Josh Goebel][]
    +
    +[Josh Goebel]: https://github.com/joshgoebel
    +[Edwin Hoogerbeets]: https://github.com/ehoogerbeets
    +
    +
    +## Version 10.1.0
    +
    +New themes:
    +
    +- *NNFX* and *NNFX-dark* by [Jim Mason][]
    +- *lioshi* by [lioshi][]
    +
    +Parser Engine:
    +
    +- (parser) Now escapes quotes in text content when escaping HTML (#2564) [Josh Goebel][]
    +- (parser) Adds `keywords.$pattern` key to grammar definitions (#2519) [Josh Goebel][]
    +- (parser) Adds SHEBANG utility mode [Josh Goebel][]
    +- (parser) Adds `registerAliases` method (#2540) [Taufik Nurrohman][]
    +- (enh) Added `on:begin` callback for modes (#2261) [Josh Goebel][]
    +- (enh) Added `on:end` callback for modes (#2261) [Josh Goebel][]
    +- (enh) Added ability to programatically ignore begin and end matches (#2261) [Josh Goebel][]
    +- (enh) Added `END_SAME_AS_BEGIN` mode to replace `endSameAsBegin` parser attribute (#2261) [Josh Goebel][]
    +- (fix) `fixMarkup` would rarely destroy markup when `useBR` was enabled (#2532) [Josh Goebel][]
    +
    +Deprecations:
    +
    +- `htmlbars` grammar is now deprecated. Use `handlebars` instead. (#2344) [Nils Knappmeier][]
    +- when using `highlightBlock` `result.re` deprecated. Use `result.relevance` instead. (#2552) [Josh Goebel][]
    +- ditto for `result.second_best.re` => `result.second_best.relevance` (#2552)
    +- `lexemes` is now deprecated in favor of `keywords.$pattern` key (#2519) [Josh Goebel][]
    +- `endSameAsBegin` is now deprecated. (#2261) [Josh Goebel][]
    +
    +Language Improvements:
    +
    +- fix(groovy) strings are not allowed inside ternary clauses (#2217) [Josh Goebel][]
    +- fix(typescript) add `readonly` keyword (#2562) [Martin (Lhoerion)][]
    +- fix(javascript) fix regex inside parens after a non-regex (#2530) [Josh Goebel][]
    +- enh(typescript) use identifier to match potential keywords, preventing false positivites (#2519) [Josh Goebel][]
    +- enh(javascript) use identifier to match potential keywords, preventing false positivites (#2519) [Josh Goebel][]
    +- [enh] Add `OPTIMIZE:` and `HACK:` to the labels highlighted inside comments [Josh Goebel][]
    +- enh(typescript/javascript/coffeescript/livescript) derive ECMAscript keywords from a common foudation (#2518) [Josh Goebel][]
    +- enh(typescript) add setInterval, setTimeout, clearInterval, clearTimeout (#2514) [Josh Goebel][]
    +- enh(javascript) add setInterval, setTimeout, clearInterval, clearTimeout (#2514) [Vania Kucher][]
    +- enh(cpp) add `pair`, `make_pair`, `priority_queue` as built-ins (#2538) [Hankun Lin][]
    +- enh(cpp) recognize `priority_queue` `pair` as cpp containers (#2541) [Hankun Lin][]
    +- fix(javascript) prevent `set` keyword conflicting with setTimeout, etc. (#2514) [Vania Kucher][]
    +- fix(cpp) Fix highlighting of unterminated raw strings (#2261) [David Benjamin][]
    +- fix(javascript) `=>` function with nested `()` in params now works (#2502) [Josh Goebel][]
    +- fix(typescript) `=>` function with nested `()` in params now works (#2502) [Josh Goebel][]
    +- fix(yaml) Fix tags to include non-word characters (#2486) [Peter Plantinga][]
    +- fix(swift) `@objcMembers` was being partially highlighted (#2543) [Nick Randall][]
    +- enh(dart) Add `late` and `required` keywords, the `Never` built-in type, and nullable built-in types (#2550) [Sam Rawlins][]
    +- enh(erlang) Add underscore separators to numeric literals (#2554) [Sergey Prokhorov][]
    +- enh(handlebars) Support for sub-expressions, path-expressions, hashes, block-parameters and literals (#2344) [Nils Knappmeier][]
    +- enh(protobuf) Support multiline comments (#2597) [Pavel Evstigneev][]
    +- fix(toml) Improve key parsing (#2595) [Antoine du Hamel][]
    +
    +[Josh Goebel]: https://github.com/joshgoebel
    +[Peter Plantinga]: https://github.com/pplantinga
    +[David Benjamin]: https://github.com/davidben
    +[Vania Kucher]: https://github.com/qWici
    +[Hankun Lin]: https://github.com/Linhk1606
    +[Nick Randall]: https://github.com/nicked
    +[Sam Rawlins]: https://github.com/srawlins
    +[Sergey Prokhorov]: https://github.com/seriyps
    +[Nils Knappmeier]: https://github.com/nknapp
    +[Martin (Lhoerion)]: https://github.com/Lhoerion
    +[Jim Mason]: https://github.com/RocketMan
    +[lioshi]: https://github.com/lioshi
    +[Pavel Evstigneev]: https://github.com/Paxa
    +[Antoine du Hamel]: https://github.com/aduh95
    +
    +
    +## Version 10.0.2
    +
    +Brower build:
    +
    +- [Issue](https://github.com/highlightjs/highlight.js/issues/2505) (bug) Fix: Version 10 fails to load as CommonJS module. (#2511) [Josh Goebel][]
    +- [Issue](https://github.com/highlightjs/highlight.js/issues/2505) (removal) AMD module loading support has been removed. (#2511) [Josh Goebel][]
    +
    +Parser Engine Changes:
    +
    +- [Issue](https://github.com/highlightjs/highlight.js/issues/2522) fix(parser) Fix freez issue with illegal 0 width matches (#2524) [Josh Goebel][]
    +
    +
    +[Josh Goebel]: https://github.com/joshgoebel
    +
    +
    +## Version 10.0.1
    +
    +Parser Engine Changes:
    +
    +- (bug) Fix sublanguage with no relevance score (#2506) [Josh Goebel][]
    +
    +[Josh Goebel]: https://github.com/joshgoebel
    +
    +
    +## Version 10.0.0
    +
    +New languages:
    +
    +- add(php-template) Explicit language to detect PHP templates (vs xml) [Josh Goebel][]
    +- enh(python) Added `python-repl` for Python REPL sessions
    +- add(never) Added 3rd party Never language support
    +
    +New themes:
    +
    +- *Srcery* by [Chen Bin][]
    +
    +Parser Engine Changes:
    +
    +- (bug) Fix `beginKeywords` to ignore . matches (#2434) [Josh Goebel][]
    +- (enh) add `before:highlight` plugin API callback (#2395) [Josh Goebel][]
    +- (enh) add `after:highlight` plugin API callback (#2395) [Josh Goebel][]
    +- (enh) split out parse tree generation and HTML rendering concerns (#2404) [Josh Goebel][]
    +- (enh) every language can have a `name` attribute now (#2400) [Josh Goebel][]
    +- (enh) improve regular expression detect (less false-positives) (#2380) [Josh Goebel][]
    +- (enh) make `noHighlightRe` and `languagePrefixRe` configurable (#2374) [Josh Goebel][]
    +
    +Language Improvements:
    +
    +- enh(python) Exclude parens from functions params (#2490) [Álvaro Mondéjar][]
    +- enh(swift) Add `compactMap` to keywords as built_in (#2478) [Omid Golparvar][]
    +- enh(nim) adds `func` keyword (#2468) [Adnan Yaqoob][]
    +- enh(xml) deprecate ActionScript inside script tags (#2444) [Josh Goebel][]
    +- fix(javascript) prevent get/set variables conflicting with keywords (#2440) [Josh Goebel][]
    +- bug(clojure) Now highlights `defn-` properly (#2438) [Josh Goebel][]
    +- enh(bash) default value is another variable (#2439) [Josh Goebel][]
    +- enh(bash) string nested within string (#2439) [Josh Goebel][]
    +- enh(bash) Add arithmetic expression support (#2439) [Josh Goebel][]
    +- enh(clojure) Add support for global definitions name (#2347) [Alexandre Grison][]
    +- enh(fortran) Support Fortran 77 style comments (#2416) [Josh Goebel][]
    +- (csharp) add support for `@identifier` style identifiers (#2414) [Josh Goebel][]
    +- fix(elixir) Support function names with a slash (#2406) [Josh Goebel][]
    +- fix(javascript) comma is allowed in a "value container" (#2403) [Josh Goebel][]
    +- enh(apache) add `deny` and `allow` keywords [Josh Goebel][]
    +- enh(apache) highlight numeric attributes values [Josh Goebel][]
    +- enh(apache) highlight IP addresses, ports, and strings in sections [Josh Goebel][]
    +- enh(php) added more keywords and include `` functions, highlighted object attributes and
    +  parsing within template string substitution blocks (`${...}`).
    +- Fixed another corner case with self-closing `` in JSX.
    +- Added `HEALTHCHECK` directive in Docker.
    +- Delphi updated with new Free Pascal keywords.
    +- Fixed digit separator parsing in C++.
    +- C# updated with new keywords and fixed to allow multiple identifiers within
    +  generics `<...>`.
    +- Fixed another slow regex in Less.
    +
    +
    +## Version 9.6.0
    +
    +New languages:
    +
    +- *ABNF* and *EBNF* by [Alex McKibben][]
    +- *Awk* by [Matthew Daly][]
    +- *SubUnit* by [Sergey Bronnikov][]
    +
    +New styles:
    +
    +- *Atom One* in both Dark and Light variants  by [Daniel Gamage][]
    +
    +Plus, a few smaller updates for *Lasso*, *Elixir*, *C++* and *SQL*.
    +
    +[Alex McKibben]: https://github.com/mckibbenta
    +[Daniel Gamage]: https://github.com/danielgamage
    +[Matthew Daly]: https://github.com/matthewbdaly
    +[Sergey Bronnikov]: https://github.com/ligurio
    +
    +
    +## Version 9.5.0
    +
    +New languages:
    +
    +- *Excel* by [Victor Zhou][]
    +- *Linden Scripting Language* by [Builder's Brewery][]
    +- *TAP* (Test Anything Protocol) by [Sergey Bronnikov][]
    +- *Pony* by [Joe Eli McIlvain][]
    +- *Coq* by [Stephan Boyer][]
    +- *dsconfig* and *LDIF* by [Jacob Childress][]
    +
    +New styles:
    +
    +- *Ocean Dark* by [Gavin Siu][]
    +
    +Notable changes:
    +
    +- [Minh Nguyễn][] added more built-ins to Objective C.
    +- [Jeremy Hull][] fixed corner cases in C++ preprocessor directives and Diff
    +  comments.
    +- [Victor Zhou][] added support for digit separators in C++ numbers.
    +
    +[Gavin Siu]: https://github.com/gavsiu
    +[Builder's Brewery]: https://github.com/buildersbrewery
    +[Victor Zhou]: https://github.com/OiCMudkips
    +[Sergey Bronnikov]: https://github.com/ligurio
    +[Joe Eli McIlvain]: https://github.com/jemc
    +[Stephan Boyer]: https://github.com/boyers
    +[Jacob Childress]: https://github.com/braveulysses
    +[Minh Nguyễn]: https://github.com/1ec5
    +[Jeremy Hull]: https://github.com/sourrust
    +
    +
    +## Version 9.4.0
    +
    +New languages:
    +
    +- *PureBASIC* by [Tristano Ajmone][]
    +- *BNF* by [Oleg Efimov][]
    +- *Ada* by [Lars Schulna][]
    +
    +New styles:
    +
    +- *PureBASIC* by [Tristano Ajmone][]
    +
    +Improvements to existing languages and styles:
    +
    +- We now highlight function declarations in Go.
    +- [Taisuke Fujimoto][] contributed very convoluted rules for raw and
    +  interpolated strings in C#.
    +- [Boone Severson][] updated Verilog to comply with IEEE 1800-2012
    +  SystemVerilog.
    +- [Victor Zhou][] improved rules for comments and strings in PowerShell files.
    +- [Janis Voigtländer][] updated the definition of Elm to version 0.17 of the
    +  languages. Elm is now featured on the front page of .
    +- Special variable `$this` is highlighted as a keyword in PHP.
    +- `usize` and `isize` are now highlighted in Rust.
    +- Fixed labels and directives in x86 assembler.
    +
    +[Tristano Ajmone]: https://github.com/tajmone
    +[Taisuke Fujimoto]: https://github.com/temp-impl
    +[Oleg Efimov]: https://github.com/Sannis
    +[Boone Severson]: https://github.com/BooneJS
    +[Victor Zhou]: https://github.com/OiCMudkips
    +[Lars Schulna]: https://github.com/captain-hanuta
    +[Janis Voigtländer]: https://github.com/jvoigtlaender
    +
    +
    +## Version 9.3.0
    +
    +New languages:
    +
    +- *Tagger Script* by [Philipp Wolfer][]
    +- *MoonScript* by [Billy Quith][]
    +
    +New styles:
    +
    +- *xt256* by [Herbert Shin][]
    +
    +Improvements to existing languages and styles:
    +
    +- More robust handling of unquoted HTML tag attributes
    +- Relevance tuning for QML which was unnecessary eager at seizing other
    +  languages' code
    +- Improve GAMS language parsing
    +- Fixed a bunch of bugs around selectors in Less
    +- Kotlin's got a new definition for annotations, updated keywords and other
    +  minor improvements
    +- Added `move` to Rust keywords
    +- Markdown now recognizes \`\`\`-fenced code blocks
    +- Improved detection of function declarations in C++ and C#
    +
    +[Philipp Wolfer]: https://github.com/phw
    +[Billy Quith]: https://github.com/billyquith
    +[Herbert Shin]: https://github.com/initbar
    +
    +
    +## Version 9.2.0
    +
    +New languages:
    +
    +- *QML* by [John Foster][]
    +- *HTMLBars* by [Michael Johnston][]
    +- *CSP* by [Taras][]
    +- *Maxima* by [Robert Dodier][]
    +
    +New styles:
    +
    +- *Gruvbox* by [Qeole][]
    +- *Dracula* by [Denis Ciccale][]
    +
    +Improvements to existing languages and styles:
    +
    +- We now correctly handle JSX with arbitrary node tree depth.
    +- Argument list for `(lambda)` in Scheme is no longer highlighted as a function
    +  call.
    +- Stylus syntax doesn't break on valid CSS.
    +- More correct handling of comments and strings and other improvements for
    +  VimScript.
    +- More subtle work on the default style.
    +- We now use anonymous modules for AMD.
    +- `macro_rules!` is now recognized as a built-in in Rust.
    +
    +[John Foster]: https://github.com/jf990
    +[Qeole]: https://github.com/Qeole
    +[Denis Ciccale]: https://github.com/dciccale
    +[Michael Johnston]: https://github.com/lastobelus
    +[Taras]: https://github.com/oxdef
    +[Robert Dodier]: https://github.com/robert-dodier
    +
    +
    +## Version 9.1.0
    +
    +New languages:
    +
    +- *Stan* by [Brendan Rocks][]
    +- *BASIC* by [Raphaël Assénat][]
    +- *GAUSS* by [Matt Evans][]
    +- *DTS* by [Martin Braun][]
    +- *Arduino* by [Stefania Mellai][]
    +
    +New Styles:
    +
    +- *Arduino Light* by [Stefania Mellai][]
    +
    +Improvements to existing languages and styles:
    +
    +- Handle return type annotations in Python
    +- Allow shebang headers in Javascript
    +- Support strings in Rust meta
    +- Recognize `struct` as a class-level definition in Rust
    +- Recognize b-prefixed chars and strings in Rust
    +- Better numbers handling in Verilog
    +
    +[Brendan Rocks]: http://brendanrocks.com
    +[Raphaël Assénat]: https://github.com/raphnet
    +[Matt Evans]: https://github.com/matthewevans
    +[Martin Braun]: https://github.com/mbr0wn
    +[Stefania Mellai]: https://github.com/smellai
    +
    +
    +## Version 9.0.0
    +
    +The new major version brings a reworked styling system. Highlight.js now defines
    +a limited set of highlightable classes giving a consistent result across all the
    +styles and languages. You can read a more detailed explanation and background in
    +the [tracking issue][#348] that started this long process back in May.
    +
    +This change is backwards incompatible for those who uses highlight.js with a
    +custom stylesheet. The [new style guide][sg] explains how to write styles
    +in this new world.
    +
    +Bundled themes have also suffered a significant amount of improvements and may
    +look different in places, but all the things now consistent and make more sense.
    +Among others, the Default style has got a refresh and will probably be tweaked
    +some more in next releases. Please do give your feedback in our
    +[issue tracker][issues].
    +
    +New languages in this release:
    +
    +- *Caché Object Script* by [Nikita Savchenko][]
    +- *YAML* by [Stefan Wienert][]
    +- *MIPS Assembler* by [Nebuleon Fumika][]
    +- *HSP* by [prince][]
    +
    +Improvements to existing languages and styles:
    +
    +- ECMAScript 6 modules import now do not require closing semicolon.
    +- ECMAScript 6 classes constructors now highlighted.
    +- Template string support for Typescript, as for ECMAScript 6.
    +- Scala case classes params highlight fixed.
    +- Built-in names introduced in Julia v0.4 added by [Kenta Sato][].
    +- Refreshed Default style.
    +
    +Other notable changes:
    +
    +- [Web workers support][webworkers] added bu [Jan Kühle][].
    +- We now have tests for compressed browser builds as well.
    +- The building tool chain has been switched to node.js 4.x. and is now
    +  shamelessly uses ES6 features all over the place, courtesy of [Jeremy Hull][].
    +- License added to non-compressed browser build.
    +
    +[Jan Kühle]: https://github.com/frigus02
    +[Stefan Wienert]: https://github.com/zealot128
    +[Kenta Sato]: https://github.com/bicycle1885
    +[Nikita Savchenko]: https://github.com/ZitRos
    +[webworkers]: https://github.com/isagalaev/highlight.js#web-workers
    +[Jeremy Hull]: https://github.com/sourrust
    +[#348]: https://github.com/isagalaev/highlight.js/issues/348
    +[sg]: http://highlightjs.readthedocs.org/en/latest/style-guide.html
    +[issues]: https://github.com/isagalaev/highlight.js/issues
    +[Nebuleon Fumika]: https://github.com/Nebuleon
    +[prince]: https://github.com/prince-0203
    +
    +
    +## Version 8.9.1
    +
    +Some last-minute changes reverted due to strange bug with minified browser build:
    +
    +- Scala case classes params highlight fixed
    +- ECMAScript 6 modules import now do not require closing semicolon
    +- ECMAScript 6 classes constructors now highlighted
    +- Template string support for Typescript, as for ECMAScript 6
    +- License added to not minified browser build
    +
    +
    +## Version 8.9.0
    +
    +New languages:
    +
    +- *crmsh* by [Kristoffer Gronlund][]
    +- *SQF* by [Soren Enevoldsen][]
    +
    +[Kristoffer Gronlund]: https://github.com/krig
    +[Soren Enevoldsen]: https://github.com/senevoldsen90
    +
    +Notable fixes and improvements to existing languages:
    +
    +- Added `abstract` and `namespace` keywords to TypeScript by [Daniel Rosenwasser][]
    +- Added `label` support to Dockerfile by [Ladislav Prskavec][]
    +- Crystal highlighting improved by [Tsuyusato Kitsune][]
    +- Missing Swift keywords added by [Nate Cook][]
    +- Improve detection of C block comments
    +- ~~Scala case classes params highlight fixed~~
    +- ~~ECMAScript 6 modules import now do not require closing semicolon~~
    +- ~~ECMAScript 6 classes constructors now highlighted~~
    +- ~~Template string support for Typescript, as for ECMAScript 6~~
    +
    +Other notable changes:
    +
    +- ~~License added to not minified browser build~~
    +
    +[Kristoffer Gronlund]: https://github.com/krig
    +[Søren Enevoldsen]: https://github.com/senevoldsen90
    +[Daniel Rosenwasser]: https://github.com/DanielRosenwasser
    +[Ladislav Prskavec]: https://github.com/abtris
    +[Tsuyusato Kitsune]: https://github.com/MakeNowJust
    +[Nate Cook]: https://github.com/natecook1000
    +
    +
    +## Version 8.8.0
    +
    +New languages:
    +
    +- *Golo* by [Philippe Charrière][]
    +- *GAMS* by [Stefan Bechert][]
    +- *IRPF90* by [Anthony Scemama][]
    +- *Access logs* by [Oleg Efimov][]
    +- *Crystal* by [Tsuyusato Kitsune][]
    +
    +Notable fixes and improvements to existing languages:
    +
    +- JavaScript highlighting no longer fails with ES6 default parameters
    +- Added keywords `async` and `await` to Python
    +- PHP heredoc support improved
    +- Allow preprocessor directives within C++ functions
    +
    +Other notable changes:
    +
    +- Change versions to X.Y.Z SemVer-compatible format
    +- Added ability to build all targets at once
    +
    +[Philippe Charrière]: https://github.com/k33g
    +[Stefan Bechert]: https://github.com/b-pos465
    +[Anthony Scemama]: https://github.com/scemama
    +[Oleg Efimov]: https://github.com/Sannis
    +[Tsuyusato Kitsune]: https://github.com/MakeNowJust
    +
    +
    +## Version 8.7
    +
    +New languages:
    +
    +- *Zephir* by [Oleg Efimov][]
    +- *Elm* by [Janis Voigtländer][]
    +- *XQuery* by [Dirk Kirsten][]
    +- *Mojolicious* by [Dotan Dimet][]
    +- *AutoIt* by Manh Tuan from [J2TeaM][]
    +- *Toml* (ini extension) by [Guillaume Gomez][]
    +
    +New styles:
    +
    +- *Hopscotch* by [Jan T. Sott][]
    +- *Grayscale* by [MY Sun][]
    +
    +Notable fixes and improvements to existing languages:
    +
    +- Fix encoding of images when copied over in certain builds
    +- Fix incorrect highlighting of the word "bug" in comments
    +- Treat decorators different from matrix multiplication in Python
    +- Fix traits inheritance highlighting in Rust
    +- Fix incorrect document
    +- Oracle keywords added to SQL language definition by [Vadimtro][]
    +- Postgres keywords added to SQL language definition by [Benjamin Auder][]
    +- Fix registers in x86asm being highlighted as a hex number
    +- Fix highlighting for numbers with a leading decimal point
    +- Correctly highlight numbers and strings inside of C/C++ macros
    +- C/C++ functions now support pointer, reference, and move returns
    +
    +[Oleg Efimov]: https://github.com/Sannis
    +[Guillaume Gomez]: https://github.com/GuillaumeGomez
    +[Janis Voigtländer]: https://github.com/jvoigtlaender
    +[Jan T. Sott]: https://github.com/idleberg
    +[Dirk Kirsten]: https://github.com/dirkk
    +[MY Sun]: https://github.com/simonmysun
    +[Vadimtro]: https://github.com/Vadimtro
    +[Benjamin Auder]: https://github.com/ghost
    +[Dotan Dimet]: https://github.com/dotandimet
    +[J2TeaM]: https://github.com/J2TeaM
    +
    +
    +## Version 8.6
    +
    +New languages:
    +
    +- *C/AL* by [Kenneth Fuglsang][]
    +- *DNS zone file* by [Tim Schumacher][]
    +- *Ceylon* by [Lucas Werkmeister][]
    +- *OpenSCAD* by [Dan Panzarella][]
    +- *Inform7* by [Bruno Dias][]
    +- *armasm* by [Dan Panzarella][]
    +- *TP* by [Jay Strybis][]
    +
    +New styles:
    +
    +- *Atelier Cave*, *Atelier Estuary*,
    +  *Atelier Plateau* and *Atelier Savanna* by [Bram de Haan][]
    +- *Github Gist* by [Louis Barranqueiro][]
    +
    +Notable fixes and improvements to existing languages:
    +
    +- Multi-line raw strings from C++11 are now supported
    +- Fix class names with dashes in HAML
    +- The `async` keyword from ES6/7 is now supported
    +- TypeScript functions handle type and parameter complexity better
    +- We unified phpdoc/javadoc/yardoc etc modes across all languages
    +- CSS .class selectors relevance was dropped to prevent wrong language detection
    +- Images is now included to CDN build
    +- Release process is now automated
    +
    +[Bram de Haan]: https://github.com/atelierbram
    +[Kenneth Fuglsang]: https://github.com/kfuglsang
    +[Louis Barranqueiro]: https://github.com/LouisBarranqueiro
    +[Tim Schumacher]: https://github.com/enko
    +[Lucas Werkmeister]: https://github.com/lucaswerkmeister
    +[Dan Panzarella]: https://github.com/pzl
    +[Bruno Dias]: https://github.com/sequitur
    +[Jay Strybis]: https://github.com/unreal
    +
    +
    +## Version 8.5
    +
    +New languages:
    +
    +- *pf.conf* by [Peter Piwowarski][]
    +- *Julia* by [Kenta Sato][]
    +- *Prolog* by [Raivo Laanemets][]
    +- *Docker* by [Alexis Hénaut][]
    +- *Fortran* by [Anthony Scemama][] and [Thomas Applencourt][]
    +- *Kotlin* by [Sergey Mashkov][]
    +
    +New styles:
    +
    +- *Agate* by [Taufik Nurrohman][]
    +- *Darcula* by [JetBrains][]
    +- *Atelier Sulphurpool* by [Bram de Haan][]
    +- *Android Studio* by [Pedro Oliveira][]
    +
    +Notable fixes and improvements to existing languages:
    +
    +- ES6 features in JavaScript are better supported now by [Gu Yiling][].
    +- Swift now recognizes body-less method definitions.
    +- Single expression functions `def foo, do: ... ` now work in Elixir.
    +- More uniform detection of built-in classes in Objective C.
    +- Fixes for number literals and processor directives in Rust.
    +- HTML `
    +  ```
    +
    +- `tabReplace` and `useBR` that were used in different places are also unified
    +  into the global options object and are to be set using `configure(options)`.
    +  This function is documented in our [API docs][]. Also note that these
    +  parameters are gone from `highlightBlock` and `fixMarkup` which are now also
    +  rely on `configure`.
    +
    +- We removed public-facing (though undocumented) object `hljs.LANGUAGES` which
    +  was used to register languages with the library in favor of two new methods:
    +  `registerLanguage` and `getLanguage`. Both are documented in our [API docs][].
    +
    +- Result returned from `highlight` and `highlightAuto` no longer contains two
    +  separate attributes contributing to relevance score, `relevance` and
    +  `keyword_count`. They are now unified in `relevance`.
    +
    +Another technically compatible change that nonetheless might need attention:
    +
    +- The structure of the NPM package was refactored, so if you had installed it
    +  locally, you'll have to update your paths. The usual `require('highlight.js')`
    +  works as before. This is contributed by [Dmitry Smolin][].
    +
    +New features:
    +
    +- Languages now can be recognized by multiple names like "js" for JavaScript or
    +  "html" for, well, HTML (which earlier insisted on calling it "xml"). These
    +  aliases can be specified in the class attribute of the code container in your
    +  HTML as well as in various API calls. For now there are only a few very common
    +  aliases but we'll expand it in the future. All of them are listed in the
    +  [class reference][cr].
    +
    +- Language detection can now be restricted to a subset of languages relevant in
    +  a given context — a web page or even a single highlighting call. This is
    +  especially useful for node.js build that includes all the known languages.
    +  Another example is a StackOverflow-style site where users specify languages
    +  as tags rather than in the markdown-formatted code snippets. This is
    +  documented in the [API reference][] (see methods `highlightAuto` and
    +  `configure`).
    +
    +- Language definition syntax streamlined with [variants][] and
    +  [beginKeywords][].
    +
    +New languages and styles:
    +
    +- *Oxygene* by [Carlo Kok][]
    +- *Mathematica* by [Daniel Kvasnička][]
    +- *Autohotkey* by [Seongwon Lee][]
    +- *Atelier* family of styles in 10 variants by [Bram de Haan][]
    +- *Paraíso* styles by [Jan T. Sott][]
    +
    +Miscellaneous improvements:
    +
    +- Highlighting `=>` prompts in Clojure.
    +- [Jeremy Hull][] fixed a lot of styles for consistency.
    +- Finally, highlighting PHP and HTML [mixed in peculiar ways][php-html].
    +- Objective C and C# now properly highlight titles in method definition.
    +- Big overhaul of relevance counting for a number of languages. Please do report
    +  bugs about mis-detection of non-trivial code snippets!
    +
    +[API reference]: http://highlightjs.readthedocs.org/en/latest/api.html
    +
    +[cr]: http://highlightjs.readthedocs.org/en/latest/css-classes-reference.html
    +[api docs]: http://highlightjs.readthedocs.org/en/latest/api.html
    +[variants]: https://groups.google.com/d/topic/highlightjs/VoGC9-1p5vk/discussion
    +[beginKeywords]: https://github.com/isagalaev/highlight.js/commit/6c7fdea002eb3949577a85b3f7930137c7c3038d
    +[php-html]: https://twitter.com/highlightjs/status/408890903017689088
    +
    +[Carlo Kok]: https://github.com/carlokok
    +[Bram de Haan]: https://github.com/atelierbram
    +[Daniel Kvasnička]: https://github.com/dkvasnicka
    +[Dmitry Smolin]: https://github.com/dimsmol
    +[Jeremy Hull]: https://github.com/sourrust
    +[Seongwon Lee]: https://github.com/dlimpid
    +[Jan T. Sott]: https://github.com/idleberg
    +
    +
    +## Version 7.5
    +
    +A catch-up release dealing with some of the accumulated contributions. This one
    +is probably will be the last before the 8.0 which will be slightly backwards
    +incompatible regarding some advanced use-cases.
    +
    +One outstanding change in this version is the addition of 6 languages to the
    +[hosted script][d]: Markdown, ObjectiveC, CoffeeScript, Apache, Nginx and
    +Makefile. It now weighs about 6K more but we're going to keep it under 30K.
    +
    +New languages:
    +
    +- OCaml by [Mehdi Dogguy][mehdid] and [Nicolas Braud-Santoni][nbraud]
    +- [LiveCode Server][lcs] by [Ralf Bitter][revig]
    +- Scilab by [Sylvestre Ledru][sylvestre]
    +- basic support for Makefile by [Ivan Sagalaev][isagalaev]
    +
    +Improvements:
    +
    +- Ruby's got support for characters like `?A`, `?1`, `?\012` etc. and `%r{..}`
    +  regexps.
    +- Clojure now allows a function call in the beginning of s-expressions
    +  `(($filter "myCount") (arr 1 2 3 4 5))`.
    +- Haskell's got new keywords and now recognizes more things like pragmas,
    +  preprocessors, modules, containers, FFIs etc. Thanks to [Zena Treep][treep]
    +  for the implementation and to [Jeremy Hull][sourrust] for guiding it.
    +- Miscellaneous fixes in PHP, Brainfuck, SCSS, Asciidoc, CMake, Python and F#.
    +
    +[mehdid]: https://github.com/mehdid
    +[nbraud]: https://github.com/nbraud
    +[revig]: https://github.com/revig
    +[lcs]: http://livecode.com/developers/guides/server/
    +[sylvestre]: https://github.com/sylvestre
    +[isagalaev]: https://github.com/isagalaev
    +[treep]: https://github.com/treep
    +[sourrust]: https://github.com/sourrust
    +[d]: http://highlightjs.org/download/
    +
    +
    +## New core developers
    +
    +The latest long period of almost complete inactivity in the project coincided
    +with growing interest to it led to a decision that now seems completely obvious:
    +we need more core developers.
    +
    +So without further ado let me welcome to the core team two long-time
    +contributors: [Jeremy Hull][] and [Oleg
    +Efimov][].
    +
    +Hope now we'll be able to work through stuff faster!
    +
    +P.S. The historical commit is [here][1] for the record.
    +
    +[Jeremy Hull]: https://github.com/sourrust
    +[Oleg Efimov]: https://github.com/sannis
    +[1]: https://github.com/isagalaev/highlight.js/commit/f3056941bda56d2b72276b97bc0dd5f230f2473f
    +
    +
    +## Version 7.4
    +
    +This long overdue version is a snapshot of the current source tree with all the
    +changes that happened during the past year. Sorry for taking so long!
    +
    +Along with the changes in code highlight.js has finally got its new home at
    +, moving from its cradle on Software Maniacs which it
    +outgrew a long time ago. Be sure to report any bugs about the site to
    +.
    +
    +On to what's new…
    +
    +New languages:
    +
    +- Handlebars templates by [Robin Ward][]
    +- Oracle Rules Language by [Jason Jacobson][]
    +- F# by [Joans Follesø][]
    +- AsciiDoc and Haml by [Dan Allen][]
    +- Lasso by [Eric Knibbe][]
    +- SCSS by [Kurt Emch][]
    +- VB.NET by [Poren Chiang][]
    +- Mizar by [Kelley van Evert][]
    +
    +[Robin Ward]: https://github.com/eviltrout
    +[Jason Jacobson]: https://github.com/jayce7
    +[Joans Follesø]: https://github.com/follesoe
    +[Dan Allen]: https://github.com/mojavelinux
    +[Eric Knibbe]: https://github.com/EricFromCanada
    +[Kurt Emch]: https://github.com/kemch
    +[Poren Chiang]: https://github.com/rschiang
    +[Kelley van Evert]: https://github.com/kelleyvanevert
    +
    +New style themes:
    +
    +- Monokai Sublime by [noformnocontent][]
    +- Railscasts by [Damien White][]
    +- Obsidian by [Alexander Marenin][]
    +- Docco by [Simon Madine][]
    +- Mono Blue by [Ivan Sagalaev][] (uses a single color hue for everything)
    +- Foundation by [Dan Allen][]
    +
    +[noformnocontent]: http://nn.mit-license.org/
    +[Damien White]: https://github.com/visoft
    +[Alexander Marenin]: https://github.com/ioncreature
    +[Simon Madine]: https://github.com/thingsinjars
    +[Ivan Sagalaev]: https://github.com/isagalaev
    +
    +Other notable changes:
    +
    +- Corrected many corner cases in CSS.
    +- Dropped Python 2 version of the build tool.
    +- Implemented building for the AMD format.
    +- Updated Rust keywords (thanks to [Dmitry Medvinsky][]).
    +- Literal regexes can now be used in language definitions.
    +- CoffeeScript highlighting is now significantly more robust and rich due to
    +  input from [Cédric Néhémie][].
    +
    +[Dmitry Medvinsky]: https://github.com/dmedvinsky
    +[Cédric Néhémie]: https://github.com/abe33
    +
    +
    +## Version 7.3
    +
    +- Since this version highlight.js no longer works in IE version 8 and older.
    +  It's made it possible to reduce the library size and dramatically improve code
    +  readability and made it easier to maintain. Time to go forward!
    +
    +- New languages: AppleScript (by [Nathan Grigg][ng] and [Dr. Drang][dd]) and
    +  Brainfuck (by [Evgeny Stepanischev][bolk]).
    +
    +- Improvements to existing languages:
    +
    +    - interpreter prompt in Python (`>>>` and `...`)
    +    - @-properties and classes in CoffeeScript
    +    - E4X in JavaScript (by [Oleg Efimov][oe])
    +    - new keywords in Perl (by [Kirk Kimmel][kk])
    +    - big Ruby syntax update (by [Vasily Polovnyov][vast])
    +    - small fixes in Bash
    +
    +- Also Oleg Efimov did a great job of moving all the docs for language and style
    +  developers and contributors from the old wiki under the source code in the
    +  "docs" directory. Now these docs are nicely presented at
    +  .
    +
    +[ng]: https://github.com/nathan11g
    +[dd]: https://github.com/drdrang
    +[bolk]: https://github.com/bolknote
    +[oe]: https://github.com/Sannis
    +[kk]: https://github.com/kimmel
    +[vast]: https://github.com/vast
    +
    +
    +## Version 7.2
    +
    +A regular bug-fix release without any significant new features. Enjoy!
    +
    +
    +## Version 7.1
    +
    +A Summer crop:
    +
    +- [Marc Fornos][mf] made the definition for Clojure along with the matching
    +  style Rainbow (which, of course, works for other languages too).
    +- CoffeeScript support continues to improve getting support for regular
    +  expressions.
    +- Yoshihide Jimbo ported to highlight.js [five Tomorrow styles][tm] from the
    +  [project by Chris Kempson][tm0].
    +- Thanks to [Casey Duncun][cd] the library can now be built in the popular
    +  [AMD format][amd].
    +- And last but not least, we've got a fair number of correctness and consistency
    +  fixes, including a pretty significant refactoring of Ruby.
    +
    +[mf]: https://github.com/mfornos
    +[tm]: http://jmblog.github.com/color-themes-for-highlightjs/
    +[tm0]: https://github.com/ChrisKempson/Tomorrow-Theme
    +[cd]: https://github.com/caseman
    +[amd]: http://requirejs.org/docs/whyamd.html
    +
    +
    +## Version 7.0
    +
    +The reason for the new major version update is a global change of keyword syntax
    +which resulted in the library getting smaller once again. For example, the
    +hosted build is 2K less than at the previous version while supporting two new
    +languages.
    +
    +Notable changes:
    +
    +- The library now works not only in a browser but also with [node.js][]. It is
    +  installable with `npm install highlight.js`. [API][] docs are available on our
    +  wiki.
    +
    +- The new unique feature (apparently) among syntax highlighters is highlighting
    +  *HTTP* headers and an arbitrary language in the request body. The most useful
    +  languages here are *XML* and *JSON* both of which highlight.js does support.
    +  Here's [the detailed post][p] about the feature.
    +
    +- Two new style themes: a dark "south" *[Pojoaque][]* by Jason Tate and an
    +  emulation of*XCode* IDE by [Angel Olloqui][ao].
    +
    +- Three new languages: *D* by [Aleksandar Ružičić][ar], *R* by [Joe Cheng][jc]
    +  and *GLSL* by [Sergey Tikhomirov][st].
    +
    +- *Nginx* syntax has become a million times smaller and more universal thanks to
    +  remaking it in a more generic manner that doesn't require listing all the
    +  directives in the known universe.
    +
    +- Function titles are now highlighted in *PHP*.
    +
    +- *Haskell* and *VHDL* were significantly reworked to be more rich and correct
    +  by their respective maintainers [Jeremy Hull][sr] and [Igor Kalnitsky][ik].
    +
    +And last but not least, many bugs have been fixed around correctness and
    +language detection.
    +
    +Overall highlight.js currently supports 51 languages and 20 style themes.
    +
    +[node.js]: http://nodejs.org/
    +[api]: http://softwaremaniacs.org/wiki/doku.php/highlight.js:api
    +[p]: http://softwaremaniacs.org/blog/2012/05/10/http-and-json-in-highlight-js/en/
    +[pojoaque]: http://web-cms-designs.com/ftopict-10-pojoaque-style-for-highlight-js-code-highlighter.html
    +[ao]: https://github.com/angelolloqui
    +[ar]: https://github.com/raleksandar
    +[jc]: https://github.com/jcheng5
    +[st]: https://github.com/tikhomirov
    +[sr]: https://github.com/sourrust
    +[ik]: https://github.com/ikalnitsky
    +
    +
    +## Version 6.2
    +
    +A lot of things happened in highlight.js since the last version! We've got nine
    +new contributors, the discussion group came alive, and the main branch on GitHub
    +now counts more than 350 followers. Here are most significant results coming
    +from all this activity:
    +
    +- 5 (five!) new languages: Rust, ActionScript, CoffeeScript, MatLab and
    +  experimental support for markdown. Thanks go to [Andrey Vlasovskikh][av],
    +  [Alexander Myadzel][am], [Dmytrii Nagirniak][dn], [Oleg Efimov][oe], [Denis
    +  Bardadym][db] and [John Crepezzi][jc].
    +
    +- 2 new style themes: Monokai by [Luigi Maselli][lm] and stylistic imitation of
    +  another well-known highlighter Google Code Prettify by [Aahan Krish][ak].
    +
    +- A vast number of [correctness fixes and code refactorings][log], mostly made
    +  by [Oleg Efimov][oe] and [Evgeny Stepanischev][es].
    +
    +[av]: https://github.com/vlasovskikh
    +[am]: https://github.com/myadzel
    +[dn]: https://github.com/dnagir
    +[oe]: https://github.com/Sannis
    +[db]: https://github.com/btd
    +[jc]: https://github.com/seejohnrun
    +[lm]: http://grigio.org/
    +[ak]: https://github.com/geekpanth3r
    +[es]: https://github.com/bolknote
    +[log]: https://github.com/isagalaev/highlight.js/commits/
    +
    +
    +## Version 6.1 — Solarized
    +
    +[Jeremy Hull][jh] has implemented my dream feature — a port of [Solarized][]
    +style theme famous for being based on the intricate color theory to achieve
    +correct contrast and color perception. It is now available for highlight.js in
    +both variants — light and dark.
    +
    +This version also adds a new original style Arta. Its author pumbur maintains a
    +[heavily modified fork of highlight.js][pb] on GitHub.
    +
    +[jh]: https://github.com/sourrust
    +[solarized]: http://ethanschoonover.com/solarized
    +[pb]: https://github.com/pumbur/highlight.js
    +
    +
    +## Version 6.0
    +
    +New major version of the highlighter has been built on a significantly
    +refactored syntax. Due to this it's even smaller than the previous one while
    +supporting more languages!
    +
    +New languages are:
    +
    +- Haskell by [Jeremy Hull][sourrust]
    +- Erlang in two varieties — module and REPL — made collectively by [Nikolay
    +  Zakharov][desh], [Dmitry Kovega][arhibot] and [Sergey Ignatov][ignatov]
    +- Objective C by [Valerii Hiora][vhbit]
    +- Vala by [Antono Vasiljev][antono]
    +- Go by [Stephan Kountso][steplg]
    +
    +[sourrust]: https://github.com/sourrust
    +[desh]: http://desh.su/
    +[arhibot]: https://github.com/arhibot
    +[ignatov]: https://github.com/ignatov
    +[vhbit]: https://github.com/vhbit
    +[antono]: https://github.com/antono
    +[steplg]: https://github.com/steplg
    +
    +Also this version is marginally faster and fixes a number of small long-standing
    +bugs.
    +
    +Developer overview of the new language syntax is available in a [blog post about
    +recent beta release][beta].
    +
    +[beta]: http://softwaremaniacs.org/blog/2011/04/25/highlight-js-60-beta/en/
    +
    +P.S. New version is not yet available on a Yandex CDN, so for now you have to
    +download [your own copy][d].
    +
    +[d]: /soft/highlight/en/download/
    +
    +
    +## Version 5.14
    +
    +Fixed bugs in HTML/XML detection and relevance introduced in previous
    +refactoring.
    +
    +Also test.html now shows the second best result of language detection by
    +relevance.
    +
    +
    +## Version 5.13
    +
    +Past weekend began with a couple of simple additions for existing languages but
    +ended up in a big code refactoring bringing along nice improvements for language
    +developers.
    +
    +### For users
    +
    +- Description of C++ has got new keywords from the upcoming [C++ 0x][] standard.
    +- Description of HTML has got new tags from [HTML 5][].
    +- CSS-styles have been unified to use consistent padding and also have lost
    +  pop-outs with names of detected languages.
    +- [Igor Kalnitsky][ik] has sent two new language descriptions: CMake & VHDL.
    +
    +This makes total number of languages supported by highlight.js to reach 35.
    +
    +Bug fixes:
    +
    +- Custom classes on `
    ` tags are not being overridden anymore
    +- More correct highlighting of code blocks inside non-`
    ` containers:
    +  highlighter now doesn't insist on replacing them with its own container and
    +  just replaces the contents.
    +- Small fixes in browser compatibility and heuristics.
    +
    +[c++ 0x]: http://ru.wikipedia.org/wiki/C%2B%2B0x
    +[html 5]: http://en.wikipedia.org/wiki/HTML5
    +[ik]: http://kalnitsky.org.ua/
    +
    +### For developers
    +
    +The most significant change is the ability to include language submodes right
    +under `contains` instead of defining explicit named submodes in the main array:
    +
    +    contains: [
    +      'string',
    +      'number',
    +      {begin: '\\n', end: hljs.IMMEDIATE_RE}
    +    ]
    +
    +This is useful for auxiliary modes needed only in one place to define parsing.
    +Note that such modes often don't have `className` and hence won't generate a
    +separate `` in the resulting markup. This is similar in effect to
    +`noMarkup: true`. All existing languages have been refactored accordingly.
    +
    +Test file test.html has at last become a real test. Now it not only puts the
    +detected language name under the code snippet but also tests if it matches the
    +expected one. Test summary is displayed right above all language snippets.
    +
    +
    +## CDN
    +
    +Fine people at [Yandex][] agreed to host highlight.js on their big fast servers.
    +[Link up][l]!
    +
    +[yandex]: http://yandex.com/
    +[l]: http://softwaremaniacs.org/soft/highlight/en/download/
    +
    +
    +## Version 5.10 — "Paris".
    +
    +Though I'm on a vacation in Paris, I decided to release a new version with a
    +couple of small fixes:
    +
    +- Tomas Vitvar discovered that TAB replacement doesn't always work when used
    +  with custom markup in code
    +- SQL parsing is even more rigid now and doesn't step over SmallTalk in tests
    +
    +
    +## Version 5.9
    +
    +A long-awaited version is finally released.
    +
    +New languages:
    +
    +- Andrew Fedorov made a definition for Lua
    +- a long-time highlight.js contributor [Peter Leonov][pl] made a definition for
    +  Nginx config
    +- [Vladimir Moskva][vm] made a definition for TeX
    +
    +[pl]: http://kung-fu-tzu.ru/
    +[vm]: http://fulc.ru/
    +
    +Fixes for existing languages:
    +
    +- [Loren Segal][ls] reworked the Ruby definition and added highlighting for
    +  [YARD][] inline documentation
    +- the definition of SQL has become more solid and now it shouldn't be overly
    +  greedy when it comes to language detection
    +
    +[ls]: http://gnuu.org/
    +[yard]: http://yardoc.org/
    +
    +The highlighter has become more usable as a library allowing to do highlighting
    +from initialization code of JS frameworks and in ajax methods (see.
    +readme.eng.txt).
    +
    +Also this version drops support for the [WordPress][wp] plugin. Everyone is
    +welcome to [pick up its maintenance][p] if needed.
    +
    +[wp]: http://wordpress.org/
    +[p]: http://bazaar.launchpad.net/~isagalaev/+junk/highlight/annotate/342/src/wp_highlight.js.php
    +
    +
    +## Version 5.8
    +
    +- Jan Berkel has contributed a definition for Scala. +1 to hotness!
    +- All CSS-styles are rewritten to work only inside `
    ` tags to avoid
    +  conflicts with host site styles.
    +
    +
    +## Version 5.7.
    +
    +Fixed escaping of quotes in VBScript strings.
    +
    +
    +## Version 5.5
    +
    +This version brings a small change: now .ini-files allow digits, underscores and
    +square brackets in key names.
    +
    +
    +## Version 5.4
    +
    +Fixed small but upsetting bug in the packer which caused incorrect highlighting
    +of explicitly specified languages. Thanks to Andrew Fedorov for precise
    +diagnostics!
    +
    +
    +## Version 5.3
    +
    +The version to fulfil old promises.
    +
    +The most significant change is that highlight.js now preserves custom user
    +markup in code along with its own highlighting markup. This means that now it's
    +possible to use, say, links in code. Thanks to [Vladimir Dolzhenko][vd] for the
    +[initial proposal][1] and for making a proof-of-concept patch.
    +
    +Also in this version:
    +
    +- [Vasily Polovnyov][vp] has sent a GitHub-like style and has implemented
    +  support for CSS @-rules and Ruby symbols.
    +- Yura Zaripov has sent two styles: Brown Paper and School Book.
    +- Oleg Volchkov has sent a definition for [Parser 3][p3].
    +
    +[1]: http://softwaremaniacs.org/forum/highlightjs/6612/
    +[p3]: http://www.parser.ru/
    +[vp]: http://vasily.polovnyov.ru/
    +[vd]: http://dolzhenko.blogspot.com/
    +
    +
    +## Version 5.2
    +
    +- at last it's possible to replace indentation TABs with something sensible
    +  (e.g. 2 or 4 spaces)
    +- new keywords and built-ins for 1C by Sergey Baranov
    +- a couple of small fixes to Apache highlighting
    +
    +
    +## Version 5.1
    +
    +This is one of those nice version consisting entirely of new and shiny
    +contributions!
    +
    +- [Vladimir Ermakov][vooon] created highlighting for AVR Assembler
    +- [Ruslan Keba][rukeba] created highlighting for Apache config file. Also his
    +  original visual style for it is now available for all highlight.js languages
    +  under the name "Magula".
    +- [Shuen-Huei Guan][drake] (aka Drake) sent new keywords for RenderMan
    +  languages. Also thanks go to [Konstantin Evdokimenko][ke] for his advice on
    +  the matter.
    +
    +[vooon]: http://vehq.ru/about/
    +[rukeba]: http://rukeba.com/
    +[drake]: http://drakeguan.org/
    +[ke]: http://k-evdokimenko.moikrug.ru/
    +
    +
    +## Version 5.0
    +
    +The main change in the new major version of highlight.js is a mechanism for
    +packing several languages along with the library itself into a single compressed
    +file. Now sites using several languages will load considerably faster because
    +the library won't dynamically include additional files while loading.
    +
    +Also this version fixes a long-standing bug with Javascript highlighting that
    +couldn't distinguish between regular expressions and division operations.
    +
    +And as usually there were a couple of minor correctness fixes.
    +
    +Great thanks to all contributors! Keep using highlight.js.
    +
    +
    +## Version 4.3
    +
    +This version comes with two contributions from [Jason Diamond][jd]:
    +
    +- language definition for C# (yes! it was a long-missed thing!)
    +- Visual Studio-like highlighting style
    +
    +Plus there are a couple of minor bug fixes for parsing HTML and XML attributes.
    +
    +[jd]: http://jason.diamond.name/weblog/
    +
    +
    +## Version 4.2
    +
    +The biggest news is highlighting for Lisp, courtesy of Vasily Polovnyov. It's
    +somewhat experimental meaning that for highlighting "keywords" it doesn't use
    +any pre-defined set of a Lisp dialect. Instead it tries to highlight first word
    +in parentheses wherever it makes sense. I'd like to ask people programming in
    +Lisp to confirm if it's a good idea and send feedback to [the forum][f].
    +
    +Other changes:
    +
    +- Smalltalk was excluded from DEFAULT_LANGUAGES to save traffic
    +- [Vladimir Epifanov][voldmar] has implemented javascript style switcher for
    +  test.html
    +- comments now allowed inside Ruby function definition
    +- [MEL][] language from [Shuen-Huei Guan][drake]
    +- whitespace now allowed between `
    ` and ``
    +- better auto-detection of C++ and PHP
    +- HTML allows embedded VBScript (`<% .. %>`)
    +
    +[f]: http://softwaremaniacs.org/forum/highlightjs/
    +[voldmar]: http://voldmar.ya.ru/
    +[mel]: http://en.wikipedia.org/wiki/Maya_Embedded_Language
    +[drake]: http://drakeguan.org/
    +
    +
    +## Version 4.1
    +
    +Languages:
    +
    +- Bash from Vah
    +- DOS bat-files from Alexander Makarov (Sam)
    +- Diff files from Vasily Polovnyov
    +- Ini files from myself though initial idea was from Sam
    +
    +Styles:
    +
    +- Zenburn from Vladimir Epifanov, this is an imitation of a
    +  [well-known theme for Vim][zenburn].
    +- Ascetic from myself, as a realization of ideals of non-flashy highlighting:
    +  just one color in only three gradations :-)
    +
    +In other news. [One small bug][bug] was fixed, built-in keywords were added for
    +Python and C++ which improved auto-detection for the latter (it was shame that
    +[my wife's blog][alenacpp] had issues with it from time to time). And lastly
    +thanks go to Sam for getting rid of my stylistic comments in code that were
    +getting in the way of [JSMin][].
    +
    +[zenburn]: http://en.wikipedia.org/wiki/Zenburn
    +[alenacpp]: http://alenacpp.blogspot.com/
    +[bug]: http://softwaremaniacs.org/forum/viewtopic.php?id=1823
    +[jsmin]: http://code.google.com/p/jsmin-php/
    +
    +
    +## Version 4.0
    +
    +New major version is a result of vast refactoring and of many contributions.
    +
    +Visible new features:
    +
    +- Highlighting of embedded languages. Currently is implemented highlighting of
    +  Javascript and CSS inside HTML.
    +- Bundled 5 ready-made style themes!
    +
    +Invisible new features:
    +
    +- Highlight.js no longer pollutes global namespace. Only one object and one
    +  function for backward compatibility.
    +- Performance is further increased by about 15%.
    +
    +Changing of a major version number caused by a new format of language definition
    +files. If you use some third-party language files they should be updated.
    +
    +
    +## Version 3.5
    +
    +A very nice version in my opinion fixing a number of small bugs and slightly
    +increased speed in a couple of corner cases. Thanks to everybody who reports
    +bugs in he [forum][f] and by email!
    +
    +There is also a new language — XML. A custom XML formerly was detected as HTML
    +and didn't highlight custom tags. In this version I tried to make custom XML to
    +be detected and highlighted by its own rules. Which by the way include such
    +things as CDATA sections and processing instructions (``).
    +
    +[f]: http://softwaremaniacs.org/forum/viewforum.php?id=6
    +
    +
    +## Version 3.3
    +
    +[Vladimir Gubarkov][xonix] has provided an interesting and useful addition.
    +File export.html contains a little program that shows and allows to copy and
    +paste an HTML code generated by the highlighter for any code snippet. This can
    +be useful in situations when one can't use the script itself on a site.
    +
    +
    +[xonix]: http://xonixx.blogspot.com/
    +
    +
    +## Version 3.2 consists completely of contributions:
    +
    +- Vladimir Gubarkov has described SmallTalk
    +- Yuri Ivanov has described 1C
    +- Peter Leonov has packaged the highlighter as a Firefox extension
    +- Vladimir Ermakov has compiled a mod for phpBB
    +
    +Many thanks to you all!
    +
    +
    +## Version 3.1
    +
    +Three new languages are available: Django templates, SQL and Axapta. The latter
    +two are sent by [Dmitri Roudakov][1]. However I've almost entirely rewrote an
    +SQL definition but I'd never started it be it from the ground up :-)
    +
    +The engine itself has got a long awaited feature of grouping keywords
    +("keyword", "built-in function", "literal"). No more hacks!
    +
    +[1]: http://roudakov.ru/
    +
    +
    +## Version 3.0
    +
    +It is major mainly because now highlight.js has grown large and has become
    +modular. Now when you pass it a list of languages to highlight it will
    +dynamically load into a browser only those languages.
    +
    +Also:
    +
    +- Konstantin Evdokimenko of [RibKit][] project has created a highlighting for
    +  RenderMan Shading Language and RenderMan Interface Bytestream. Yay for more
    +  languages!
    +- Heuristics for C++ and HTML got better.
    +- I've implemented (at last) a correct handling of backslash escapes in C-like
    +  languages.
    +
    +There is also a small backwards incompatible change in the new version. The
    +function initHighlighting that was used to initialize highlighting instead of
    +initHighlightingOnLoad a long time ago no longer works. If you by chance still
    +use it — replace it with the new one.
    +
    +[RibKit]: http://ribkit.sourceforge.net/
    +
    +
    +## Version 2.9
    +
    +Highlight.js is a parser, not just a couple of regular expressions. That said
    +I'm glad to announce that in the new version 2.9 has support for:
    +
    +- in-string substitutions for Ruby -- `#{...}`
    +- strings from from numeric symbol codes (like #XX) for Delphi
    +
    +
    +## Version 2.8
    +
    +A maintenance release with more tuned heuristics. Fully backwards compatible.
    +
    +
    +## Version 2.7
    +
    +- Nikita Ledyaev presents highlighting for VBScript, yay!
    +- A couple of bugs with escaping in strings were fixed thanks to Mickle
    +- Ongoing tuning of heuristics
    +
    +Fixed bugs were rather unpleasant so I encourage everyone to upgrade!
    +
    +
    +## Version 2.4
    +
    +- Peter Leonov provides another improved highlighting for Perl
    +- Javascript gets a new kind of keywords — "literals". These are the words
    +  "true", "false" and "null"
    +
    +Also highlight.js homepage now lists sites that use the library. Feel free to
    +add your site by [dropping me a message][mail] until I find the time to build a
    +submit form.
    +
    +[mail]: mailto:Maniac@SoftwareManiacs.Org
    +
    +
    +## Version 2.3
    +
    +This version fixes IE breakage in previous version. My apologies to all who have
    +already downloaded that one!
    +
    +
    +## Version 2.2
    +
    +- added highlighting for Javascript
    +- at last fixed parsing of Delphi's escaped apostrophes in strings
    +- in Ruby fixed highlighting of keywords 'def' and 'class', same for 'sub' in
    +  Perl
    +
    +
    +## Version 2.0
    +
    +- Ruby support by [Anton Kovalyov][ak]
    +- speed increased by orders of magnitude due to new way of parsing
    +- this same way allows now correct highlighting of keywords in some tricky
    +  places (like keyword "End" at the end of Delphi classes)
    +
    +[ak]: http://anton.kovalyov.net/
    +
    +
    +## Version 1.0
    +
    +Version 1.0 of javascript syntax highlighter is released!
    +
    +It's the first version available with English description. Feel free to post
    +your comments and question to [highlight.js forum][forum]. And don't be afraid
    +if you find there some fancy Cyrillic letters -- it's for Russian users too :-)
    +
    +[forum]: http://softwaremaniacs.org/forum/viewforum.php?id=6
    diff --git a/frontend/node_modules/highlight.js/LICENSE b/frontend/node_modules/highlight.js/LICENSE
    new file mode 100644
    index 0000000..2250cc7
    --- /dev/null
    +++ b/frontend/node_modules/highlight.js/LICENSE
    @@ -0,0 +1,29 @@
    +BSD 3-Clause License
    +
    +Copyright (c) 2006, Ivan Sagalaev.
    +All rights reserved.
    +
    +Redistribution and use in source and binary forms, with or without
    +modification, are permitted provided that the following conditions are met:
    +
    +* Redistributions of source code must retain the above copyright notice, this
    +  list of conditions and the following disclaimer.
    +
    +* Redistributions in binary form must reproduce the above copyright notice,
    +  this list of conditions and the following disclaimer in the documentation
    +  and/or other materials provided with the distribution.
    +
    +* Neither the name of the copyright holder nor the names of its
    +  contributors may be used to endorse or promote products derived from
    +  this software without specific prior written permission.
    +
    +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
    +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
    +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
    +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
    +FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
    +DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
    +SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
    +CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
    +OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
    +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
    diff --git a/frontend/node_modules/highlight.js/README.md b/frontend/node_modules/highlight.js/README.md
    new file mode 100644
    index 0000000..b01f59f
    --- /dev/null
    +++ b/frontend/node_modules/highlight.js/README.md
    @@ -0,0 +1,521 @@
    +# Highlight.js
    +
    +[![latest version](https://badgen.net/npm/v/highlight.js?label=latest)](https://www.npmjs.com/package/highlight.js)
    +[![license](https://badgen.net/github/license/highlightjs/highlight.js?color=cyan)](https://github.com/highlightjs/highlight.js/blob/main/LICENSE)
    +[![install size](https://badgen.net/packagephobia/install/highlight.js?label=npm+install)](https://packagephobia.now.sh/result?p=highlight.js)
    +![minified](https://img.shields.io/github/size/highlightjs/cdn-release/build/highlight.min.js?label=minified)
    +[![NPM downloads weekly](https://badgen.net/npm/dw/highlight.js?label=npm+downloads&color=purple)](https://www.npmjs.com/package/highlight.js)
    +[![jsDelivr CDN downloads](https://badgen.net/jsdelivr/hits/gh/highlightjs/cdn-release?label=jsDelivr+CDN&color=purple)](https://www.jsdelivr.com/package/gh/highlightjs/cdn-release)
    +
    +[![ci status](https://badgen.net/github/checks/highlightjs/highlight.js/main?label=build)](https://github.com/highlightjs/highlight.js/actions/workflows/tests.js.yml)
    +[![CodeQL](https://github.com/highlightjs/highlight.js/workflows/CodeQL/badge.svg)](https://github.com/highlightjs/highlight.js/actions/workflows/github-code-scanning/codeql)
    +[![vulnerabilities](https://badgen.net/snyk/highlightjs/highlight.js)](https://snyk.io/test/github/highlightjs/highlight.js?targetFile=package.json)
    +
    +[![discord](https://badgen.net/badge/icon/discord?icon=discord&label&color=pink)](https://discord.gg/M24EbU7ja9)
    +[![open issues](https://badgen.net/github/open-issues/highlightjs/highlight.js?label=issues)](https://github.com/highlightjs/highlight.js/issues)
    +[![help welcome issues](https://badgen.net/github/label-issues/highlightjs/highlight.js/help%20welcome/open)](https://github.com/highlightjs/highlight.js/issues?q=is%3Aopen+is%3Aissue+label%3A%22help+welcome%22)
    +[![good first issue](https://badgen.net/github/label-issues/highlightjs/highlight.js/good%20first%20issue/open)](https://github.com/highlightjs/highlight.js/issues?q=is%3Aopen+is%3Aissue+label%3A%22good+first+issue%22)
    +
    +
    +
    +
    +
    +
    +
    +
    +Highlight.js is a syntax highlighter written in JavaScript. It works in
    +the browser as well as on the server. It can work with pretty much any
    +markup, doesn’t depend on any other frameworks, and has automatic language
    +detection.
    +
    +**Contents**
    +
    +- [Basic Usage](#basic-usage)
    +  - [In the Browser](#in-the-browser)
    +    - [Plaintext Code Blocks](#plaintext-code-blocks)
    +    - [Ignoring a Code Block](#ignoring-a-code-block)
    +  - [Node.js on the Server](#nodejs-on-the-server)
    +- [Supported Languages](#supported-languages)
    +- [Custom Usage](#custom-usage)
    +  - [Using custom HTML](#using-custom-html)
    +  - [Using with Vue.js](#using-with-vuejs)
    +  - [Using Web Workers](#using-web-workers)
    +- [Importing the Library](#importing-the-library)
    +  - [Node.js CommonJS Modules / `require`](#nodejs-commonjs-modules--require)
    +  - [Node.js ES6 Modules / `import`](#nodejs-es6-modules--import)
    +  - [Browser ES6 Modules](#browser-es6-modules)
    +- [Getting the Library](#getting-the-library)
    +  - [Fetch via CDN](#fetch-via-cdn)
    +    - [cdnjs (link)](#cdnjs-link)
    +    - [jsdelivr (link)](#jsdelivr-link)
    +    - [unpkg (link)](#unpkg-link)
    +  - [Download prebuilt CDN assets](#download-prebuilt-cdn-assets)
    +  - [Download from our website](#download-from-our-website)
    +  - [Install via NPM package](#install-via-npm-package)
    +  - [Build from Source](#build-from-source)
    +- [Requirements](#requirements)
    +- [License](#license)
    +- [Links](#links)
    +
    +---
    +
    +#### Upgrading to Version 11
    +
    +As always, major releases do contain breaking changes which may require action from users.  Please read [VERSION_11_UPGRADE.md](https://github.com/highlightjs/highlight.js/blob/main/VERSION_11_UPGRADE.md) for a detailed summary of breaking changes and any actions you may need to take.
    +
    +
    +#### Support for older versions 
    +
    +Please see [SECURITY.md](https://github.com/highlightjs/highlight.js/blob/main/SECURITY.md) for long-term support information.
    +
    +---
    +
    +## Basic Usage
    +### In the Browser
    +
    +The bare minimum for using highlight.js on a web page is linking to the
    +library along with one of the themes and calling [`highlightAll`][1]:
    +
    +```html
    +
    +
    +
    +```
    +
    +This will find and highlight code inside of `
    ` tags; it tries
    +to detect the language automatically. If automatic detection doesn’t
    +work for you, or you simply prefer to be explicit, you can specify the language manually by using the `class` attribute:
    +
    +
    +```html
    +
    ...
    +``` + +#### Plaintext Code Blocks + +To apply the Highlight.js styling to plaintext without actually highlighting it, use the `plaintext` language: + +```html +
    ...
    +``` + +#### Ignoring a Code Block + +To skip highlighting of a code block completely, use the `nohighlight` class: + +```html +
    ...
    +``` + +### Node.js on the Server + +The bare minimum to auto-detect the language and highlight some code. + +```js +// load the library and ALL languages +hljs = require('highlight.js'); +html = hljs.highlightAuto('

    Hello World!

    ').value +``` + +To load only a "common" subset of popular languages: + +```js +hljs = require('highlight.js/lib/common'); +``` + +To highlight code with a specific language, use `highlight`: + +```js +html = hljs.highlight('

    Hello World!

    ', {language: 'xml'}).value +``` + +See [Importing the Library](#importing-the-library) for more examples of `require` vs `import` usage, etc. For more information about the result object returned by `highlight` or `highlightAuto` refer to the [api docs](https://highlightjs.readthedocs.io/en/latest/api.html). + + + +## Supported Languages + +Highlight.js supports over 180 languages in the core library. There are also 3rd party +language definitions available to support even more languages. You can find the full list of supported languages in [SUPPORTED_LANGUAGES.md][9]. + +## Custom Usage + +If you need a bit more control over the initialization of +Highlight.js, you can use the [`highlightElement`][3] and [`configure`][4] +functions. This allows you to better control *what* to highlight and *when*. + +For example, here’s the rough equivalent of calling [`highlightAll`][1] but doing the work manually instead: + +```js +document.addEventListener('DOMContentLoaded', (event) => { + document.querySelectorAll('pre code').forEach((el) => { + hljs.highlightElement(el); + }); +}); +``` + +Please refer to the documentation for [`configure`][4] options. + + +### Using custom HTML + +We strongly recommend `
    ` wrapping for code blocks. It's quite
    +semantic and "just works" out of the box with zero fiddling. It is possible to
    +use other HTML elements (or combos), but you may need to pay special attention to
    +preserving linebreaks.
    +
    +Let's say your markup for code blocks uses divs:
    +
    +```html
    +
    ...
    +``` + +To highlight such blocks manually: + +```js +// first, find all the div.code blocks +document.querySelectorAll('div.code').forEach(el => { + // then highlight each + hljs.highlightElement(el); +}); +``` + +Without using a tag that preserves linebreaks (like `pre`) you'll need some +additional CSS to help preserve them. You could also [pre and post-process line +breaks with a plug-in][brPlugin], but *we recommend using CSS*. + +[brPlugin]: https://github.com/highlightjs/highlight.js/issues/2559 + +To preserve linebreaks inside a `div` using CSS: + +```css +div.code { + white-space: pre; +} +``` + + +### Using with Vue.js + +See [highlightjs/vue-plugin](https://github.com/highlightjs/vue-plugin) for a simple Vue plugin that works great with Highlight.js. + +An example of `vue-plugin` in action: + +```html +
    + + + + +
    +``` + +### Using Web Workers + +You can run highlighting inside a web worker to avoid freezing the browser +window while dealing with very big chunks of code. + +In your main script: + +```js +addEventListener('load', () => { + const code = document.querySelector('#code'); + const worker = new Worker('worker.js'); + worker.onmessage = (event) => { code.innerHTML = event.data; } + worker.postMessage(code.textContent); +}); +``` + +In worker.js: + +```js +onmessage = (event) => { + importScripts('/highlight.min.js'); + const result = self.hljs.highlightAuto(event.data); + postMessage(result.value); +}; +``` + +## Importing the Library + +First, you'll likely be installing the library via `npm` or `yarn` -- see [Getting the Library](#getting-the-library). + + +### Node.js CommonJS Modules / `require` + +Requiring the top-level library will load all languages: + +```js +// require the highlight.js library, including all languages +const hljs = require('./highlight.js'); +const highlightedCode = hljs.highlightAuto('Hello World!').value +``` + +For a smaller footprint, load our common subset of languages (the same set used for our default web build). + +```js +const hljs = require('highlight.js/lib/common'); +``` + +For the smallest footprint, load only the languages you need: + +```js +const hljs = require('highlight.js/lib/core'); +hljs.registerLanguage('xml', require('highlight.js/lib/languages/xml')); + +const highlightedCode = hljs.highlight('Hello World!', {language: 'xml'}).value +``` + + +### Node.js ES6 Modules / `import` + +The default import will register all languages: + +```js +import hljs from 'highlight.js'; +``` + +It is more efficient to import only the library and register the languages you need: + +```js +import hljs from 'highlight.js/lib/core'; +import javascript from 'highlight.js/lib/languages/javascript'; +hljs.registerLanguage('javascript', javascript); +``` + +If your build tool processes CSS imports, you can also import the theme directly as a module: + +```js +import hljs from 'highlight.js'; +import 'highlight.js/styles/github.css'; +``` + +### Browser ES6 Modules + +*Note: For now you'll want to install `@highlightjs/cdn-assets` package instead of `highlight.js`. +See [Download prebuilt CDN assets](#download-prebuilt-cdn-assets)* + +To import the library and register only those languages that you need: + +```js +import hljs from './assets/js/@highlightjs/cdn-assets/es/core.js'; +import javascript from './assets/js/@highlightjs/cdn-assets/es/languages/javascript.min.js'; + +hljs.registerLanguage('javascript', javascript); +``` + +To import the library and register all languages: + +```js +import hljs from './assets/js/@highlightjs/cdn-assets/es/highlight.js'; +``` + +*Note: The path to these files will vary depending on where you have installed/copied them +within your project or site. The above path is only an example.* + +You can also use [`importmap`](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/script/type/importmap) to import in similar way as Node: + +```html + +``` + +Use the above code in your HTML. After that, your JavaScript can import using the named key from +your `importmap`, for example `@highlightjs` in this case: + +```js +import hljs from '@highlightjs/core.js'; +import javascript from '@highlightjs/languages/javascript.min.js'; + +hljs.registerLanguage('javascript', javascript); +``` + +*Note: You can also import directly from fully static URLs, such as our very own pre-built ES6 Module CDN resources. See [Fetch via CDN](#fetch-via-cdn) for specific examples.* + + +## Getting the Library + +You can get highlight.js as a hosted, or custom-build, browser script or +as a server module. Right out of the box the browser script supports +both AMD and CommonJS, so if you wish you can use RequireJS or +Browserify without having to build from source. The server module also +works perfectly fine with Browserify, but there is the option to use a +build specific to browsers rather than something meant for a server. + + +**Do not link to GitHub directly.** The library is not supposed to work straight +from the source, it requires building. If none of the pre-packaged options +work for you refer to the [building documentation][6]. + +**On Almond.** You need to use the optimizer to give the module a name. For +example: + +```bash +r.js -o name=hljs paths.hljs=/path/to/highlight out=highlight.js +``` + +### Fetch via CDN + +A prebuilt version of Highlight.js bundled with many common languages is hosted by several popular CDNs. +When using Highlight.js via CDN you can use Subresource Integrity for additional security. For details +see [DIGESTS.md](https://github.com/highlightjs/cdn-release/blob/main/DIGESTS.md). + +#### cdnjs ([link](https://cdnjs.com/libraries/highlight.js)) + +##### Common JS + +```html + + + + +``` + +##### ES6 Modules + +````html + + + +```` + + +#### jsdelivr ([link](https://www.jsdelivr.com/package/gh/highlightjs/cdn-release)) + +##### Common JS + +```html + + + + +``` + +##### ES6 Modules + +```html + + +``` + +#### unpkg ([link](https://unpkg.com/browse/@highlightjs/cdn-assets/)) + +##### Common JS + +```html + + + + +``` + +##### ES6 Modules + +```html + + +``` + + +**Note:** *The CDN-hosted `highlight.min.js` package doesn't bundle every language.* It would be +very large. You can find our list of "common" languages that we bundle by default on our [download page][5]. + +### Download prebuilt CDN assets + +You can also download and self-host the same assets we serve up via our own CDNs. We publish those builds to the [cdn-release](https://github.com/highlightjs/cdn-release) GitHub repository. You can easily pull individual files off the CDN endpoints with `curl`, etc; if say you only needed `highlight.min.js` and a single CSS file. + +There is also an npm package [@highlightjs/cdn-assets](https://www.npmjs.com/package/@highlightjs/cdn-assets) if pulling the assets in via `npm` or `yarn` would be easier for your build process. + +### Download from our website + +The [download page][5] can quickly generate a custom single-file minified bundle including only the languages you desire. + +**Note:** [Building from source](#build-from-source) can produce slightly smaller builds than the website download. + + +### Install via NPM package + +Our NPM package including all supported languages can be installed with NPM or Yarn: + +```bash +npm install highlight.js +# or +yarn add highlight.js +``` + +There is also another npm package [@highlightjs/cdn-assets](https://www.npmjs.com/package/@highlightjs/cdn-assets) that contains prebuilt CDN assets including [ES6 Modules that can be imported in browser](#browser-es6-modules): + +```bash +npm install @highlightjs/cdn-assets +# or +yarn add @highlightjs/cdn-assets +``` + +Alternatively, you can build the NPM package from source. + + +### Build from Source + +The [current source code][10] is always available on GitHub. + +```bash +node tools/build.js -t node +node tools/build.js -t browser :common +node tools/build.js -t cdn :common +``` + +See our [building documentation][6] for more information. + + +## Requirements + +Highlight.js works on all modern browsers and currently supported Node.js versions. You'll need the following software to contribute to the core library: + +- Node.js >= 12.x +- npm >= 6.x + +## License + +Highlight.js is released under the BSD License. See our [LICENSE][7] file +for details. + + +## Links + +The official website for the library is . + +Further in-depth documentation for the API and other topics is at +. + +A list of the Core Team and contributors can be found in the [CONTRIBUTORS.md][8] file. + +[1]: http://highlightjs.readthedocs.io/en/latest/api.html#highlightall +[2]: http://highlightjs.readthedocs.io/en/latest/css-classes-reference.html +[3]: http://highlightjs.readthedocs.io/en/latest/api.html#highlightelement +[4]: http://highlightjs.readthedocs.io/en/latest/api.html#configure +[5]: https://highlightjs.org/download/ +[6]: http://highlightjs.readthedocs.io/en/latest/building-testing.html +[7]: https://github.com/highlightjs/highlight.js/blob/main/LICENSE +[8]: https://github.com/highlightjs/highlight.js/blob/main/CONTRIBUTORS.md +[9]: https://github.com/highlightjs/highlight.js/blob/main/SUPPORTED_LANGUAGES.md +[10]: https://github.com/highlightjs/ diff --git a/frontend/node_modules/highlight.js/SECURITY.md b/frontend/node_modules/highlight.js/SECURITY.md new file mode 100644 index 0000000..086a034 --- /dev/null +++ b/frontend/node_modules/highlight.js/SECURITY.md @@ -0,0 +1,19 @@ +# Security Policy + +Due to both time and resource constrains the Highlight.js core team fully supports only the current major/minor release of the library. Prior major releases may be supported for a short time after new major releases are issued. Problems with minor releases are often resolved by upgrading to the most recent minor release. + +### Release Status + +| Version | Support | Status | +| :-----: | :-: | :------ | +| 11.x | :white_check_mark: | The 11.x series recieves regular updates, new features & security fixes. | +| 10.7.x | :x: | No longer supported.
    See [VERSION_11_UPGRADE.md](https://github.com/highlightjs/highlight.js/blob/master/VERSION_11_UPGRADE.md).| +| <= 10.4.0 | :x: | Known vulnerabities. | +| <= 9.18.5 | :x: | Known vulnerabities. [EOL](https://github.com/highlightjs/highlight.js/issues/2877) | +| 7.x, 8.x | :x: | Obsolete. Known vulnerabities. | + + +### Reporting a Vulnerability + +Many vulnerabilities can simply be reported (and tracked) via our [GitHub issues](https://github.com/highlightjs/highlight.js/issues). If you feel your issue is more sensitive than that you can always reach us via email: [security@highlightjs.org](mailto:security@highlightjs.org) + diff --git a/frontend/node_modules/highlight.js/SUPPORTED_LANGUAGES.md b/frontend/node_modules/highlight.js/SUPPORTED_LANGUAGES.md new file mode 100644 index 0000000..3757dfa --- /dev/null +++ b/frontend/node_modules/highlight.js/SUPPORTED_LANGUAGES.md @@ -0,0 +1,283 @@ +# Supported Languages + +The table below shows the full list of languages (and corresponding classes/aliases) supported by Highlight.js. Languages that list a **Package** below are 3rd party languages and are not bundled with the core library. You can find their repositories by following the links. + +**Note:** The languages available will depend on how you've built or are included the library in your app. For example our default minified web build includes only ~40 popular languages. See [Getting the Library][1] and [Importing the Library][2] in the README for examples of how to load additional/specific languages. + + +| Language | Aliases | Package | +| :-----------------------| :--------------------- | :------ | +| 1C | 1c | | +| 4D | 4d |[highlightjs-4d](https://github.com/highlightjs/highlightjs-4d) | +| ABAP | sap-abap, abap |[highlight-sap-abap](https://github.com/highlightjs/highlightjs-sap-abap) | +| ABNF | abnf | | +| Access logs | accesslog | | +| Ada | ada | | +| Apex | apex | [highlightjs-apex](https://github.com/highlightjs/highlightjs-apex/) | +| Arduino (C++ w/Arduino libs) | arduino, ino | | +| ARM assembler | armasm, arm | | +| AVR assembler | avrasm | | +| ActionScript | actionscript, as | | +| Alan IF | alan, i | [highlightjs-alan](https://github.com/highlightjs/highlightjs-alan) | +| Alan | ln | [highlightjs-alan](https://github.com/alantech/highlightjs-alan) | +| AngelScript | angelscript, asc | | +| Apache | apache, apacheconf | | +| AppleScript | applescript, osascript | | +| Arcade | arcade | | +| AsciiDoc | asciidoc, adoc | | +| AspectJ | aspectj | | +| AutoHotkey | autohotkey | | +| AutoIt | autoit | | +| Awk | awk, mawk, nawk, gawk | | +| Ballerina | ballerina, bal | [highlightjs-ballerina](https://github.com/highlightjs/highlightjs-ballerina) | +| Bash | bash, sh, zsh | | +| Basic | basic | | +| BBCode | bbcode | [highlightjs-bbcode](https://github.com/RedGuy12/highlightjs-bbcode) | +| Blade (Laravel) | blade | [highlightjs-blade](https://github.com/miken32/highlightjs-blade) | +| BNF | bnf | | +| BQN | bqn | [highlightjs-bqn](https://github.com/razetime/highlightjs-bqn) | +| Brainfuck | brainfuck, bf | | +| C# | csharp, cs | | +| C | c, h | | +| C++ | cpp, hpp, cc, hh, c++, h++, cxx, hxx | | +| C/AL | cal | | +| C3 | c3 | [highlightjs-c3](https://github.com/highlightjs/highlightjs-c3) | +| Cache Object Script | cos, cls | | +| Candid | candid, did | [highlightjs-motoko](https://github.com/rvanasa/highlightjs-motoko) | +| CMake | cmake, cmake.in | | +| COBOL | cobol, standard-cobol | [highlightjs-cobol](https://github.com/otterkit/highlightjs-cobol) | +| CODEOWNERS | codeowners | [highlightjs-codeowners](https://github.com/highlightjs/highlightjs-codeowners) | +| Coq | coq | | +| CSP | csp | | +| CSS | css | | +| Cap’n Proto | capnproto, capnp | | +| Chaos | chaos, kaos | [highlightjs-chaos](https://github.com/chaos-lang/highlightjs-chaos) | +| Chapel | chapel, chpl | [highlightjs-chapel](https://github.com/chapel-lang/highlightjs-chapel) | +| Cisco CLI | cisco | [highlightjs-cisco-cli](https://github.com/BMatheas/highlightjs-cisco-cli) | +| Clojure | clojure, clj | | +| CoffeeScript | coffeescript, coffee, cson, iced | | +| CpcdosC+ | cpc | [highlightjs-cpcdos](https://github.com/SPinti-Software/highlightjs-cpcdos) | +| Crmsh | crmsh, crm, pcmk | | +| Crystal | crystal, cr | | +| cURL | curl | [highlightjs-curl](https://github.com/highlightjs/highlightjs-curl) | +| Cypher (Neo4j) | cypher | [highlightjs-cypher](https://github.com/highlightjs/highlightjs-cypher) | +| D | d | | +| Dafny | dafny | [highlightjs-dafny](https://github.com/ConsenSys/highlightjs-dafny)| +| Dart | dart | | +| Delphi | dpr, dfm, pas, pascal | | +| Diff | diff, patch | | +| Django | django, jinja | | +| DNS Zone file | dns, zone, bind | | +| Dockerfile | dockerfile, docker | | +| DOS | dos, bat, cmd | | +| dsconfig | dsconfig | | +| DTS (Device Tree) | dts | | +| Dust | dust, dst | | +| Dylan | dylan | [highlightjs-dylan](https://github.com/highlightjs/highlightjs-dylan) | +| EBNF | ebnf | | +| Elixir | elixir | | +| Elm | elm | | +| Erlang | erlang, erl | | +| Excel | excel, xls, xlsx | | +| Extempore | extempore, xtlang, xtm | [highlightjs-xtlang](https://github.com/highlightjs/highlightjs-xtlang) | +| F# | fsharp, fs, fsx, fsi, fsscript | | +| FIX | fix | | +| Flix | flix | [highlightjs-flix](https://github.com/flix/highlightjs-flix) | +| Fortran | fortran, f90, f95 | | +| FunC | func | [highlightjs-func](https://github.com/highlightjs/highlightjs-func) | +| G-Code | gcode, nc | | +| Gams | gams, gms | | +| GAUSS | gauss, gss | | +| GDScript | godot, gdscript | [highlightjs-gdscript](https://github.com/highlightjs/highlightjs-gdscript) | +| Gherkin | gherkin | | +| Glimmer and EmberJS | hbs, glimmer, html.hbs, html.handlebars, htmlbars | [highlightjs-glimmer](https://github.com/NullVoxPopuli/highlightjs-glimmer) | +| GN for Ninja | gn, gni | [highlightjs-GN](https://github.com/highlightjs/highlightjs-GN) | +| Go | go, golang | | +| Grammatical Framework | gf | [highlightjs-gf](https://github.com/johnjcamilleri/highlightjs-gf) | +| Golo | golo, gololang | | +| Gradle | gradle | | +| GraphQL | graphql, gql | | +| Groovy | groovy | | +| GSQL | gsql | [highlightjs-gsql](https://github.com/DanBarkus/highlightjs-gsql) | +| HTML, XML | xml, html, xhtml, rss, atom, xjb, xsd, xsl, plist, svg | | +| HTTP | http, https | | +| Haml | haml | | +| Handlebars | handlebars, hbs, html.hbs, html.handlebars | | +| Haskell | haskell, hs | | +| Haxe | haxe, hx | | +| High-level shader language| hlsl | [highlightjs-hlsl](https://github.com/highlightjs/highlightjs-hlsl) | +| Hy | hy, hylang | | +| Ini, TOML | ini, toml | | +| Inform7 | inform7, i7 | | +| IRPF90 | irpf90 | | +| Iptables | iptables | [highlightjs-iptables](https://github.com/highlightjs/highlightjs-iptables) | +| JSON | json, jsonc | | +| JSONata | jsonata | [highlightjs-jsonata](https://github.com/DevDimov/highlightjs-jsonata) | +| Java | java, jsp | | +| JavaScript | javascript, js, jsx | | +| Jolie | jolie, iol, ol | [highlightjs-jolie](https://github.com/xiroV/highlightjs-jolie) | +| Julia | julia, jl | | +| Julia REPL | julia-repl | | +| Kotlin | kotlin, kt | | +| Lang | | [highlightjs-lang](https://github.com/highlightjs/highlightjs-lang) +| LaTeX | tex | | +| Leaf | leaf | | +| Lean | lean | [highlightjs-lean](https://github.com/leanprover-community/highlightjs-lean) | +| Lasso | lasso, ls, lassoscript | | +| Less | less | | +| LDIF | ldif | | +| Liquid | liquid | [highlightjs-liquid](https://github.com/highlightjs/highlightjs-liquid) | +| Lisp | lisp | | +| LiveCode Server | livecodeserver | | +| LiveScript | livescript, ls | | +| LookML | lookml | [highlightjs-lookml](https://github.com/spectacles-ci/highlightjs-lookml) | +| Lua | lua, pluto | | +| Luau | luau | [highlightjs-luau](https://github.com/highlightjs/highlightjs-luau) | +| Macaulay2 | macaulay2 | [highlightjs-macaulay2](https://github.com/d-torrance/highlightjs-macaulay2) | +| Makefile | makefile, mk, mak, make | | +| Markdown | markdown, md, mkdown, mkd | | +| Mathematica | mathematica, mma, wl | | +| Matlab | matlab | | +| Maxima | maxima | | +| Maya Embedded Language | mel | | +| Mercury | mercury | | +| MetaPost | metapost | [highlightjs-metapost](https://github.com/chupinmaxime/highlightjs-metapost) | | +| MIPS Assembler | mips, mipsasm | | +| Mint | mint | [highlightjs-mint](https://github.com/mint-lang/highlightjs-mint) | +| Mirth | mirth | [highlightjs-mirth](https://github.com/highlightjs/highlightjs-mirth) | +| mIRC Scripting Language | mirc, mrc | [highlightjs-mirc](https://github.com/highlightjs/highlightjs-mirc) | +| Mizar | mizar | | +| MKB | mkb | [highlightjs-mkb](https://github.com/Dereavy/highlightjs-mkb) | +| MLIR | mlir | [highlightjs-mlir](https://github.com/highlightjs/highlightjs-mlir) | +| Mojolicious | mojolicious | | +| Monkey | monkey | | +| Moonscript | moonscript, moon | | +| Motoko | motoko, mo | [highlightjs-motoko](https://github.com/rvanasa/highlightjs-motoko) | +| N1QL | n1ql | | +| NSIS | nsis | | +| Never | never | [highlightjs-never](https://github.com/never-lang/highlightjs-never) | +| Nginx | nginx, nginxconf | | +| Nim | nim, nimrod | | +| Nix | nix | | +| Oak | oak | [highlightjs-oak](https://github.com/timlabs/highlightjs-oak) | +| Object Constraint Language | ocl | [highlightjs-ocl](https://github.com/nhomble/highlightjs-ocl) | +| OCaml | ocaml, ml | | +| Objective C | objectivec, mm, objc, obj-c, obj-c++, objective-c++ | | +| Odin | odin | [highlightjs-odin](https://github.com/NinjasCL/highlightjs-odin) | +| OpenGL Shading Language | glsl | | +| OpenSCAD | openscad, scad | | +| Oracle Rules Language | ruleslanguage | | +| Oxygene | oxygene | | +| PF | pf, pf.conf | | +| PHP | php | | +| Papyrus | papyrus, psc |[highlightjs-papyrus](https://github.com/Pickysaurus/highlightjs-papyrus) | +| Parser3 | parser3 | | +| Perl | perl, pl, pm | | +| Phix | phix | [highlightjs-phix](https://github.com/highlightjs/highlightjs-phix) | +| Pine Script | pine, pinescript | [highlightjs-pine](https://github.com/jeyllani/highlightjs-pine) | +| Plaintext | plaintext, txt, text | | +| Pony | pony | | +| PostgreSQL & PL/pgSQL | pgsql, postgres, postgresql | | +| PowerOn | poweron, po | [highlightjs-poweron](https://github.com/libum-llc/highlightjs-poweron) | +| PowerShell | powershell, ps, ps1 | | +| Processing | processing | | +| Prolog | prolog | | +| Properties | properties | | +| Protocol Buffers | proto, protobuf | | +| Puppet | puppet, pp | | +| Python | python, py, gyp | | +| Python profiler results | profile | | +| Python REPL | python-repl, pycon | | +| Q# | qsharp | [highlightjs-qsharp](https://github.com/fedonman/highlightjs-qsharp) | +| Q | k, kdb | | +| QML | qml | | +| R | r | | +| Raku | raku, perl6, p6, pm6, rakumod | [highlightjs-raku](https://github.com/highlightjs/highlightjs-raku) | +| RakuDoc | pod6, rakudoc | [highlightjs-raku](https://github.com/highlightjs/highlightjs-raku) | +| RakuQuoting | rakuquoting | [highlightjs-raku](https://github.com/highlightjs/highlightjs-raku) | +| RakuRegexe | rakuregexe | [highlightjs-raku](https://github.com/highlightjs/highlightjs-raku) | +| Razor CSHTML | cshtml, razor, razor-cshtml | [highlightjs-cshtml-razor](https://github.com/highlightjs/highlightjs-cshtml-razor) | +| ReasonML | reasonml, re | | +| Rebol & Red | redbol, rebol, red, red-system | [highlightjs-redbol](https://github.com/oldes/highlightjs-redbol) | +| RenderMan RIB | rib | | +| RenderMan RSL | rsl | | +| ReScript | rescript, res | [highlightjs-rescript](https://github.com/tsnobip/highlightjs-rescript) | +| RiScript | risc, riscript | [highlightjs-riscript](https://github.com/highlightjs/highlightjs-riscript) | +| RISC-V Assembly | riscv, riscvasm | [highlightjs-riscvasm](https://github.com/highlightjs/highlightjs-riscvasm) | +| Roboconf | graph, instances | | +| Robot Framework | robot, rf | [highlightjs-robot](https://github.com/highlightjs/highlightjs-robot) | +| RPM spec files | rpm-specfile, rpm, spec, rpm-spec, specfile | [highlightjs-rpm-specfile](https://github.com/highlightjs/highlightjs-rpm-specfile) | +| Ruby | ruby, rb, gemspec, podspec, thor, irb | | +| Rust | rust, rs | | +| RVT Script | rvt, rvt-script | [highlightjs-rvt-script](https://github.com/Sopitive/highlightjs-rvt-script) | +| SAS | SAS, sas | | +| SCSS | scss | | +| SQL | sql | | +| STEP Part 21 | p21, step, stp | | +| Scala | scala | | +| Scheme | scheme | | +| Scilab | scilab, sci | | +| SFZ | sfz | [highlightjs-sfz](https://github.com/sfz/highlight.js) | +| Shape Expressions | shexc | [highlightjs-shexc](https://github.com/highlightjs/highlightjs-shexc) | +| Shell | shell, console | | +| Smali | smali | | +| Smalltalk | smalltalk, st | | +| SML | sml, ml | | +| Solidity | solidity, sol | [highlightjs-solidity](https://github.com/highlightjs/highlightjs-solidity) | +| Splunk SPL | spl | [highlightjs-spl](https://github.com/swsoyee/highlightjs-spl) | +| Stan | stan, stanfuncs | | +| Stata | stata | | +| Structured Text | iecst, scl, stl, structured-text | [highlightjs-structured-text](https://github.com/highlightjs/highlightjs-structured-text) | +| Stylus | stylus, styl | | +| SubUnit | subunit | | +| Supercollider | supercollider, sc | [highlightjs-supercollider](https://github.com/highlightjs/highlightjs-supercollider) | +| Svelte | svelte | [highlight.svelte](https://github.com/moonlitgrace/highlight.svelte) | +| Swift | swift | | +| Tcl | tcl, tk | | +| Terraform (HCL) | terraform, tf, hcl | [highlightjs-terraform](https://github.com/highlightjs/highlightjs-terraform) | +| Test Anything Protocol | tap | | +| Thrift | thrift | | +| Toit | toit | [toit-highlight](https://github.com/snxx-lppxx/toit-highlight) | +| TP | tp | | +| Transact-SQL | tsql | [highlightjs-tsql](https://github.com/highlightjs/highlightjs-tsql) | +| TTCN-3 | ttcn, ttcnpp, ttcn3 | [highlightjs-ttcn3](https://gitea.osmocom.org/ttcn3/highlightjs-ttcn3) | +| Twig | twig, craftcms | | +| TypeScript | typescript, ts, tsx, mts, cts | | +| Unicorn Rails log | unicorn-rails-log | [highlightjs-unicorn-rails-log](https://github.com/sweetppro/highlightjs-unicorn-rails-log) | +| Unison | unison, u | [highlightjs-unison](https://github.com/highlightjs/highlightjs-unison) | +| VB.Net | vbnet, vb | | +| VBA | vba | [highlightjs-vba](https://github.com/dullin/highlightjs-vba) | +| VBScript | vbscript, vbs | | +| VHDL | vhdl | | +| Vala | vala | | +| Verilog | verilog, v | | +| Vim Script | vim | | +| WGSL | wgsl | [highlightjs-wgsl](https://github.com/highlightjs/highlightjs-wgsl) | +| X# | xsharp, xs, prg | [highlightjs-xsharp](https://github.com/InfomindsAg/highlightjs-xsharp) | +| X++ | axapta, x++ | | +| x86 Assembly | x86asm | | +| x86 Assembly (AT&T) | x86asmatt | [highlightjs-x86asmatt](https://github.com/gondow/highlightjs-x86asmatt) | +| XL | xl, tao | | +| XQuery | xquery, xpath, xq, xqm | | +| YAML | yml, yaml | | +| ZenScript | zenscript, zs |[highlightjs-zenscript](https://github.com/highlightjs/highlightjs-zenscript) | +| Zephir | zephir, zep | | +| Zig | zig |[highlightjs-zig](https://github.com/fwx5618177/highlightjs-zig) | + + + +## Alias Overlap + +If you are using either of these languages at the same time please be sure to +use the full name and not the alias to avoid any ambiguity. + +| Language | Overlap | +| :-----------------------| :--------------------- | +| SML | ml | +| OCaml | ml | +| Lasso | ls | +| LiveScript | ls | + + +[1]: https://github.com/highlightjs/highlight.js#getting-the-library +[2]: https://github.com/highlightjs/highlight.js#importing-the-library diff --git a/frontend/node_modules/highlight.js/VERSION_10_UPGRADE.md b/frontend/node_modules/highlight.js/VERSION_10_UPGRADE.md new file mode 100644 index 0000000..645c88e --- /dev/null +++ b/frontend/node_modules/highlight.js/VERSION_10_UPGRADE.md @@ -0,0 +1,58 @@ +# Upgrading to Version 10.0 + +Welcome to version 10.0. This a major release and therefore will contain breaking changes. + +## Breaking Changes + +Our normal minor releases try to never break anything, holding all breaking changes for major releases. +We tried to squeeze in as many as we could this time so that after 10.0 ships we'll be back to quiet sailing for a while before we need to push version 11. That said, we're very conservative about what we consider a breaking change. + +*IE, if there it could possibly break things for anyone, it's typically a breaking change.* The fact is a vast majority of users should upgrade and probably not notice any changes at all. + +See [VERSION_10_BREAKING_CHANGES.md](https://github.com/highlightjs/highlight.js/blob/main/VERSION_10_BREAKING_CHANGES.md) for a comprehensive list of breaking changes, but here is a summary... if you use: + +### Core highlight.js lib on the client (with no extra CDN languages) + +Just keep doing that. + +- If you're using `darkula.css`, you'll need to change that to `darcula.css` +- The minified distributable has changed from `.pack.js` to `.min.js`, update your name when you update your URL. +- If your users have very old browsers, they may no longer be supported (no more IE11, etc.). (We're using ES2015 code now.) +- `nohighlight` or `no-highlight` are the only two CSS classes that will SKIP highlighting completely. `*text*` and `*plain*` no longer will do this. + +### Core highlight.js lib on the client (plus additional CDN languages) + +Quite a few grammars have been renamed. Ex: `nimrod.js` is now `nim.js`. + +- Check the renamed grammars to see if you might need to update your links. +- Be aware that you can't use version 9 CDN JS files anymore, they aren't compatible. +- Plus read the above list of items. + +### highlight.js on the server (via NPM) and only use the public API + +If you're just pulling in the FULL library (`require('./highlight.js')`) just keep doing that. You might not need to change anything. + +- If you're manually loading a smaller set of languages and using `registerLanguage` make sure you check out all the renamed grammars and dependency changes. +- Read the client-side lists above also. + +### highlight.js on the server (via NPM) with a custom integration + +Read the complete breaking changes list carefully. + +- Read the client-side lists above also. + +### highlight.js lib on the client, with source directly from our GitHub repo + +That will no longer work. The source needs to be built to work properly and cannot be used "raw" unless you've also setup your own build pipeline (rollup, etc.). Fetch a static build from the CDN, the [cdn-release repo](https://github.com/highlightjs/cdn-release) or use the new [`highlightjs-dist`]() NPM package. + +### highlight.js source code directly from our GitHub repo with a custom integration + +All bets are off, since we only try to guarantee stability of our NPM and CDN builds and the public API. Read all the breaking changes and perhaps skim the commit history. + +- We're using ES6 modules now. +- We're using an entirely new build system. +- The source will likely become more and more modular during the 10.0 timeline. + +## Enjoy and good luck. + +As always if you have any questions or issues, jump on the [Github Issues](https://github.com/highlightjs/highlight.js/issues). diff --git a/frontend/node_modules/highlight.js/VERSION_11_UPGRADE.md b/frontend/node_modules/highlight.js/VERSION_11_UPGRADE.md new file mode 100644 index 0000000..29364ca --- /dev/null +++ b/frontend/node_modules/highlight.js/VERSION_11_UPGRADE.md @@ -0,0 +1,203 @@ +# Upgrading to Highlight.js v11.0 + +- [Overview of Breaking Changes](#overview-of-breaking-changes) + - [Built-in set of "Common" Languages](#built-in-set-of-common-languages) + - [Language Files](#language-files) + - [Language Aliases](#language-aliases) + - [Styles and CSS](#styles-and-css) + - [Grammar Scopes](#grammar-scopes) + - [Behavioral changes](#behavioral-changes) + - [API changes](#api-changes) + - [Changes to Result Data](#changes-to-result-data) + - [Feature Removal](#feature-removal) + - [Small Things](#small-things) + - [Upgrading from Version 9.x](#upgrading-from-version-9x) + + +## Overview of Breaking Changes + +Welcome to version 11.0. This a major release and therefore contains breaking changes. Below is a complete list of those such changes. + + +### Built-in set of "Common" Languages + +The default `highlight.min.js` build **removes** a few less popular grammars: + +- apache +- http +- nginx +- properties +- coffeescript + +If you need any of these, you can always create a custom build. + +Ref: https://github.com/highlightjs/highlight.js/issues/2848 + + +### Language Files + +This would matter if you are requiring any of these files directly (via Node.js or CDN). + +- `htmlbars` has been removed. Use `handlebars` instead. +- `c-like` has been removed. Use `c`, `cpp`, or `arduino`. +- `sql_more` has been removed. Use `sql` instead or a more specific 3rd party grammar. + + +### Language Aliases + +This would matter if you are using these aliases. + +- `php3`,`php4`,`php5`, `php6`, `php7`, and `php8` have been removed. Use `php` instead. +- `zsh` has been removed. Use `sh` or `bash` instead. +- `freepascal`, `lazarus`, `lpr`, and `lpm` removed. Use `delphi` instead. + +You can of course re-register any of these aliases easily if necessary. For example to restore the PHP aliases: + +```js +hljs.registerAliases(["php3","php4","php5","php6","php7","php8"],{ languageName: "php" }) +``` + +### Styles and CSS + +- The default padding on `.hljs` element has been increased and is now `1em` (it was `0.5em` previously). If your design depends on the smaller spacing you may need to update your CSS to override. +- `schoolbook` no longer has a custom lined background, it is solid color now. The old image and CSS can be found in the [10-stable branch](https://github.com/highlightjs/highlight.js/tree/10-stable/src/styles) if you wish to manually copy it into your project. +- `github` includes significant changes to more properly match modern GitHub syntax highlighting. If you desire the old theme you can manually copy it into your project from the [10-stable branch](https://github.com/highlightjs/highlight.js/tree/10-stable/src/styles). +- `github-gist` has been removed in favor of `github` as GitHub and GitHub Gist have converged. If you desire the theme you can manually copy it into your project from the [10-stable branch](https://github.com/highlightjs/highlight.js/tree/10-stable/src/styles). +- The `.hljs` CSS selector is now further scoped. It now targets `code.hljs` (inline code) and `pre code.hljs` (code blocks). If you are using a different element you may need to update your CSS to reapply some styling. +- All [Base16 themes](https://github.com/highlightjs/base16-highlightjs) now live in the `styles/base16` directory - this means some CSS files have moved. Please confirm themes you use reference the new locations. + + +#### Grammar Scopes + +- `.meta-string` removed/deprecated. Use `.meta .string` (a nested scope) instead. See [meta-keyword][]. +- `.meta-keyword` removed/deprecated. Use `.meta .keyword` (a nested scope) instead. See [meta-keyword][]. + +### Behavioral changes + +- `after:highlightElement` plugin callback is now fired *after* the DOM has been updated, not before. + +#### API changes + +- The option `ignoreIllegals` is now `true` by default (for `highlight()`). Previously it was `false`. +- The `highlight(language,code, ...args)` API no longer accepts `continuation` as a 4th argument. +- The `highlight(language,code, ...args)` API is deprecated (to be removed in 12.0). + +The new call signature is `highlight(code, {options})`. ([see docs](https://highlightjs.readthedocs.io/en/latest/api.html#highlight)) + +Code using the old API: + +```js +// highlight(language, code, ignoreIllegals, continuation) +highlight("javascript", "var a = 5;", true) +``` +...would be upgraded to the newer API as follows: + +```js +// highlight(code, {language, ignoreIllegals}) +highlight("var a = 5;", {language: "javascript", ignoreIllegals: true}) +``` + +The new API purposely does not support `continuation` as this is only intended for internal library usage. + +- `initHighlighting()` is deprecated (to be removed in 12.0). +- `initHighlightingOnLoad()` is deprecated (to be removed in 12.0). + +**Use `highlightAll()` instead.** ([see docs](https://highlightjs.readthedocs.io/en/latest/api.html#highlight-all)) The old functions are now simply aliases of `highlightAll()`. The new function may be called before or after the DOM is loaded and should do the correct thing in all cases, replacing the need for the previous individual functions. + +Note: `highlightAll()` does not guard against calling itself repeatedly as the previous functions did. Your code should be careful to avoid doing this. + +- `highlightBlock()` is deprecated (to be removed in 12.0). + +**Use `highlightElement()` instead.** ([see docs](https://highlightjs.readthedocs.io/en/latest/api.html#highlight-element)) This is merely a naming change. + +Note: The object literal passed to the `before:highlightElement` callback now passes the element in the `el` key vs the `block` key. + +##### Changes to Result Data + +- `highlightAuto()`'s `second_best` key has been renamed to `secondBest` +- `highlightElement()`'s result now no longer includes a `re` key. Use the `relevance` key now. +- `highlight()` renames some result keys to more clearly mark them as private: `_top`, `_emitter`, and `_illegalBy`. You should not depend on these keys as they are subject to change at any time. +- The `relevance` key returned by `highlight()` is no longer guaranteed to be an even integer. +- `highlightElement` now always tags blocks with a consistent `language-[name]` class + +This behavior was inconsistent before. Sometimes `[name]` class would be added, sometimes the alias name would be added, something no class would be added. now `language-[name]` is always added. This also affects sublanguage `span` tags which now also include the `language-` prefix. + +#### Feature Removal + +- HTML auto-passthru is now no longer included in core. Use a plugin instead. For a possible plugin please see [#2889](https://github.com/highlightjs/highlight.js/issues/2889). + +An example: + +```html +
    
    +var a = 4;
    +var a = 4;
    +
    +``` + +Unescaped HTML like this will now be ignored (stripped before highlighting) and a warning will be logged to the console. All HTML to be highlighted should be properly escaped to avoid potential HTML/JS injection attacks. + +- `fixMarkup` has been removed. + +This function was deprecated in v10.2. It is not our goal to provide random string utilities. You may need to provide your own replacement [Ref: #2534](https://github.com/highlightjs/highlight.js/issues/2634) + +- `CSS_NUMBER_MODE` has been removed. + +This rule was too broad for bring inclusion in core and has been removed. + +- `lexemes` mode attribute has been removed. + +Use the new `keywords.$pattern` instead. + +Before: + +```js +{ + keywords: "do.it start.now begin.later end.immediately" + lexemes: /[a-z.]+/ +} +``` + +After: + +```js +{ + keywords: { + $pattern: /[a-z.]+/ + keyword: "do.it start.now begin.later end.immediately", + } +} +``` + +This may required converting your `keywords` key into an object if it's not already (as shown above). + +- `endSameAsBegin` mode attribute has been removed. + +Use the new `END_SAME_AS_BEGIN` mode rule/function instead. + +- `useBR` configuration has been removed. + +This configuration option was deprecated in v10.1. Use a plugin or preferably simply CSS `white-space: pre`. [Ref: #2559](https://github.com/highlightjs/highlight.js/issues/2559) + + +- `tabReplace` configuration has been removed. + +This configuration option was deprecated in v10.5. Use a plugin or pre-render content instead with desired spacing. [Ref: #2874](https://github.com/highlightjs/highlight.js/issues/2874) + + + + + +### Small Things + +- The `regex` utility `join` has been renamed to `_eitherRewriteBackreferences` (this has always been intended for internal use only) + +### Upgrading from Version 9.x + +If you're upgrading all the way from version 9 it may still be helpful to review all the breaking changes in version 10 as well: + +- [VERSION_10_UPGRADE.md](https://github.com/highlightjs/highlight.js/blob/main/VERSION_10_UPGRADE.md) +- [VERSION_10_BREAKING_CHANGES.md](https://github.com/highlightjs/highlight.js/blob/main/VERSION_10_BREAKING_CHANGES.md) + + +[meta-keyword]: https://github.com/highlightjs/highlight.js/pull/3167 diff --git a/frontend/node_modules/highlight.js/es/common.d.ts b/frontend/node_modules/highlight.js/es/common.d.ts new file mode 100644 index 0000000..202edff --- /dev/null +++ b/frontend/node_modules/highlight.js/es/common.d.ts @@ -0,0 +1,3 @@ +import hljs from "highlight.js"; +export default hljs; + diff --git a/frontend/node_modules/highlight.js/es/common.js b/frontend/node_modules/highlight.js/es/common.js new file mode 100644 index 0000000..94dcc95 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/common.js @@ -0,0 +1,4 @@ +// https://nodejs.org/api/packages.html#packages_writing_dual_packages_while_avoiding_or_minimizing_hazards +import HighlightJS from '../lib/common.js'; +export { HighlightJS }; +export default HighlightJS; diff --git a/frontend/node_modules/highlight.js/es/core.d.ts b/frontend/node_modules/highlight.js/es/core.d.ts new file mode 100644 index 0000000..202edff --- /dev/null +++ b/frontend/node_modules/highlight.js/es/core.d.ts @@ -0,0 +1,3 @@ +import hljs from "highlight.js"; +export default hljs; + diff --git a/frontend/node_modules/highlight.js/es/core.js b/frontend/node_modules/highlight.js/es/core.js new file mode 100644 index 0000000..f115fde --- /dev/null +++ b/frontend/node_modules/highlight.js/es/core.js @@ -0,0 +1,4 @@ +// https://nodejs.org/api/packages.html#packages_writing_dual_packages_while_avoiding_or_minimizing_hazards +import HighlightJS from '../lib/core.js'; +export { HighlightJS }; +export default HighlightJS; diff --git a/frontend/node_modules/highlight.js/es/index.js b/frontend/node_modules/highlight.js/es/index.js new file mode 100644 index 0000000..603e048 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/index.js @@ -0,0 +1,4 @@ +// https://nodejs.org/api/packages.html#packages_writing_dual_packages_while_avoiding_or_minimizing_hazards +import HighlightJS from '../lib/index.js'; +export { HighlightJS }; +export default HighlightJS; diff --git a/frontend/node_modules/highlight.js/es/languages/1c.js b/frontend/node_modules/highlight.js/es/languages/1c.js new file mode 100644 index 0000000..206f9b5 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/1c.js @@ -0,0 +1,544 @@ +/* +Language: 1C:Enterprise +Author: Stanislav Belov +Description: built-in language 1C:Enterprise (v7, v8) +Category: enterprise +*/ + +function _1c(hljs) { + // общий паттерн для определения идентификаторов + const UNDERSCORE_IDENT_RE = '[A-Za-zА-Яа-яёЁ_][A-Za-zА-Яа-яёЁ_0-9]+'; + + // v7 уникальные ключевые слова, отсутствующие в v8 ==> keyword + const v7_keywords = + 'далее '; + + // v8 ключевые слова ==> keyword + const v8_keywords = + 'возврат вызватьисключение выполнить для если и из или иначе иначеесли исключение каждого конецесли ' + + 'конецпопытки конеццикла не новый перейти перем по пока попытка прервать продолжить тогда цикл экспорт '; + + // keyword : ключевые слова + const KEYWORD = v7_keywords + v8_keywords; + + // v7 уникальные директивы, отсутствующие в v8 ==> meta-keyword + const v7_meta_keywords = + 'загрузитьизфайла '; + + // v8 ключевые слова в инструкциях препроцессора, директивах компиляции, аннотациях ==> meta-keyword + const v8_meta_keywords = + 'вебклиент вместо внешнеесоединение клиент конецобласти мобильноеприложениеклиент мобильноеприложениесервер ' + + 'наклиенте наклиентенасервере наклиентенасерверебезконтекста насервере насерверебезконтекста область перед ' + + 'после сервер толстыйклиентобычноеприложение толстыйклиентуправляемоеприложение тонкийклиент '; + + // meta-keyword : ключевые слова в инструкциях препроцессора, директивах компиляции, аннотациях + const METAKEYWORD = v7_meta_keywords + v8_meta_keywords; + + // v7 системные константы ==> built_in + const v7_system_constants = + 'разделительстраниц разделительстрок символтабуляции '; + + // v7 уникальные методы глобального контекста, отсутствующие в v8 ==> built_in + const v7_global_context_methods = + 'ansitooem oemtoansi ввестивидсубконто ввестиперечисление ввестипериод ввестиплансчетов выбранныйплансчетов ' + + 'датагод датамесяц датачисло заголовоксистемы значениевстроку значениеизстроки каталогиб каталогпользователя ' + + 'кодсимв конгода конецпериодаби конецрассчитанногопериодаби конецстандартногоинтервала конквартала конмесяца ' + + 'коннедели лог лог10 максимальноеколичествосубконто названиеинтерфейса названиенабораправ назначитьвид ' + + 'назначитьсчет найтиссылки началопериодаби началостандартногоинтервала начгода начквартала начмесяца ' + + 'начнедели номерднягода номерднянедели номернеделигода обработкаожидания основнойжурналрасчетов ' + + 'основнойплансчетов основнойязык очиститьокносообщений периодстр получитьвремята получитьдатута ' + + 'получитьдокументта получитьзначенияотбора получитьпозициюта получитьпустоезначение получитьта ' + + 'префиксавтонумерации пропись пустоезначение разм разобратьпозициюдокумента рассчитатьрегистрына ' + + 'рассчитатьрегистрыпо симв создатьобъект статусвозврата стрколичествострок сформироватьпозициюдокумента ' + + 'счетпокоду текущеевремя типзначения типзначениястр установитьтана установитьтапо фиксшаблон шаблон '; + + // v8 методы глобального контекста ==> built_in + const v8_global_context_methods = + 'acos asin atan base64значение base64строка cos exp log log10 pow sin sqrt tan xmlзначение xmlстрока ' + + 'xmlтип xmlтипзнч активноеокно безопасныйрежим безопасныйрежимразделенияданных булево ввестидату ввестизначение ' + + 'ввестистроку ввестичисло возможностьчтенияxml вопрос восстановитьзначение врег выгрузитьжурналрегистрации ' + + 'выполнитьобработкуоповещения выполнитьпроверкуправдоступа вычислить год данныеформывзначение дата день деньгода ' + + 'деньнедели добавитьмесяц заблокироватьданныедляредактирования заблокироватьработупользователя завершитьработусистемы ' + + 'загрузитьвнешнююкомпоненту закрытьсправку записатьjson записатьxml записатьдатуjson записьжурналарегистрации ' + + 'заполнитьзначениясвойств запроситьразрешениепользователя запуститьприложение запуститьсистему зафиксироватьтранзакцию ' + + 'значениевданныеформы значениевстрокувнутр значениевфайл значениезаполнено значениеизстрокивнутр значениеизфайла ' + + 'изxmlтипа импортмоделиxdto имякомпьютера имяпользователя инициализироватьпредопределенныеданные информацияобошибке ' + + 'каталогбиблиотекимобильногоустройства каталогвременныхфайлов каталогдокументов каталогпрограммы кодироватьстроку ' + + 'кодлокализацииинформационнойбазы кодсимвола командасистемы конецгода конецдня конецквартала конецмесяца конецминуты ' + + 'конецнедели конецчаса конфигурациябазыданныхизмененадинамически конфигурацияизменена копироватьданныеформы ' + + 'копироватьфайл краткоепредставлениеошибки лев макс местноевремя месяц мин минута монопольныйрежим найти ' + + 'найтинедопустимыесимволыxml найтиокнопонавигационнойссылке найтипомеченныенаудаление найтипоссылкам найтифайлы ' + + 'началогода началодня началоквартала началомесяца началоминуты началонедели началочаса начатьзапросразрешенияпользователя ' + + 'начатьзапускприложения начатькопированиефайла начатьперемещениефайла начатьподключениевнешнейкомпоненты ' + + 'начатьподключениерасширенияработыскриптографией начатьподключениерасширенияработысфайлами начатьпоискфайлов ' + + 'начатьполучениекаталогавременныхфайлов начатьполучениекаталогадокументов начатьполучениерабочегокаталогаданныхпользователя ' + + 'начатьполучениефайлов начатьпомещениефайла начатьпомещениефайлов начатьсозданиедвоичныхданныхизфайла начатьсозданиекаталога ' + + 'начатьтранзакцию начатьудалениефайлов начатьустановкувнешнейкомпоненты начатьустановкурасширенияработыскриптографией ' + + 'начатьустановкурасширенияработысфайлами неделягода необходимостьзавершениясоединения номерсеансаинформационнойбазы ' + + 'номерсоединенияинформационнойбазы нрег нстр обновитьинтерфейс обновитьнумерациюобъектов обновитьповторноиспользуемыезначения ' + + 'обработкапрерыванияпользователя объединитьфайлы окр описаниеошибки оповестить оповеститьобизменении ' + + 'отключитьобработчикзапросанастроекклиенталицензирования отключитьобработчикожидания отключитьобработчикоповещения ' + + 'открытьзначение открытьиндекссправки открытьсодержаниесправки открытьсправку открытьформу открытьформумодально ' + + 'отменитьтранзакцию очиститьжурналрегистрации очиститьнастройкипользователя очиститьсообщения параметрыдоступа ' + + 'перейтипонавигационнойссылке переместитьфайл подключитьвнешнююкомпоненту ' + + 'подключитьобработчикзапросанастроекклиенталицензирования подключитьобработчикожидания подключитьобработчикоповещения ' + + 'подключитьрасширениеработыскриптографией подключитьрасширениеработысфайлами подробноепредставлениеошибки ' + + 'показатьвводдаты показатьвводзначения показатьвводстроки показатьвводчисла показатьвопрос показатьзначение ' + + 'показатьинформациюобошибке показатьнакарте показатьоповещениепользователя показатьпредупреждение полноеимяпользователя ' + + 'получитьcomобъект получитьxmlтип получитьадреспоместоположению получитьблокировкусеансов получитьвремязавершенияспящегосеанса ' + + 'получитьвремязасыпанияпассивногосеанса получитьвремяожиданияблокировкиданных получитьданныевыбора ' + + 'получитьдополнительныйпараметрклиенталицензирования получитьдопустимыекодылокализации получитьдопустимыечасовыепояса ' + + 'получитьзаголовокклиентскогоприложения получитьзаголовоксистемы получитьзначенияотборажурналарегистрации ' + + 'получитьидентификаторконфигурации получитьизвременногохранилища получитьимявременногофайла ' + + 'получитьимяклиенталицензирования получитьинформациюэкрановклиента получитьиспользованиежурналарегистрации ' + + 'получитьиспользованиесобытияжурналарегистрации получитькраткийзаголовокприложения получитьмакетоформления ' + + 'получитьмаскувсефайлы получитьмаскувсефайлыклиента получитьмаскувсефайлысервера получитьместоположениепоадресу ' + + 'получитьминимальнуюдлинупаролейпользователей получитьнавигационнуюссылку получитьнавигационнуюссылкуинформационнойбазы ' + + 'получитьобновлениеконфигурациибазыданных получитьобновлениепредопределенныхданныхинформационнойбазы получитьобщиймакет ' + + 'получитьобщуюформу получитьокна получитьоперативнуюотметкувремени получитьотключениебезопасногорежима ' + + 'получитьпараметрыфункциональныхопцийинтерфейса получитьполноеимяпредопределенногозначения ' + + 'получитьпредставлениянавигационныхссылок получитьпроверкусложностипаролейпользователей получитьразделительпути ' + + 'получитьразделительпутиклиента получитьразделительпутисервера получитьсеансыинформационнойбазы ' + + 'получитьскоростьклиентскогосоединения получитьсоединенияинформационнойбазы получитьсообщенияпользователю ' + + 'получитьсоответствиеобъектаиформы получитьсоставстандартногоинтерфейсаodata получитьструктурухранениябазыданных ' + + 'получитьтекущийсеансинформационнойбазы получитьфайл получитьфайлы получитьформу получитьфункциональнуюопцию ' + + 'получитьфункциональнуюопциюинтерфейса получитьчасовойпоясинформационнойбазы пользователиос поместитьвовременноехранилище ' + + 'поместитьфайл поместитьфайлы прав праводоступа предопределенноезначение представлениекодалокализации представлениепериода ' + + 'представлениеправа представлениеприложения представлениесобытияжурналарегистрации представлениечасовогопояса предупреждение ' + + 'прекратитьработусистемы привилегированныйрежим продолжитьвызов прочитатьjson прочитатьxml прочитатьдатуjson пустаястрока ' + + 'рабочийкаталогданныхпользователя разблокироватьданныедляредактирования разделитьфайл разорватьсоединениесвнешнимисточникомданных ' + + 'раскодироватьстроку рольдоступна секунда сигнал символ скопироватьжурналрегистрации смещениелетнеговремени ' + + 'смещениестандартноговремени соединитьбуферыдвоичныхданных создатькаталог создатьфабрикуxdto сокрл сокрлп сокрп сообщить ' + + 'состояние сохранитьзначение сохранитьнастройкипользователя сред стрдлина стрзаканчиваетсяна стрзаменить стрнайти стрначинаетсяс ' + + 'строка строкасоединенияинформационнойбазы стрполучитьстроку стрразделить стрсоединить стрсравнить стрчисловхождений ' + + 'стрчислострок стршаблон текущаядата текущаядатасеанса текущаяуниверсальнаядата текущаяуниверсальнаядатавмиллисекундах ' + + 'текущийвариантинтерфейсаклиентскогоприложения текущийвариантосновногошрифтаклиентскогоприложения текущийкодлокализации ' + + 'текущийрежимзапуска текущийязык текущийязыксистемы тип типзнч транзакцияактивна трег удалитьданныеинформационнойбазы ' + + 'удалитьизвременногохранилища удалитьобъекты удалитьфайлы универсальноевремя установитьбезопасныйрежим ' + + 'установитьбезопасныйрежимразделенияданных установитьблокировкусеансов установитьвнешнююкомпоненту ' + + 'установитьвремязавершенияспящегосеанса установитьвремязасыпанияпассивногосеанса установитьвремяожиданияблокировкиданных ' + + 'установитьзаголовокклиентскогоприложения установитьзаголовоксистемы установитьиспользованиежурналарегистрации ' + + 'установитьиспользованиесобытияжурналарегистрации установитькраткийзаголовокприложения ' + + 'установитьминимальнуюдлинупаролейпользователей установитьмонопольныйрежим установитьнастройкиклиенталицензирования ' + + 'установитьобновлениепредопределенныхданныхинформационнойбазы установитьотключениебезопасногорежима ' + + 'установитьпараметрыфункциональныхопцийинтерфейса установитьпривилегированныйрежим ' + + 'установитьпроверкусложностипаролейпользователей установитьрасширениеработыскриптографией ' + + 'установитьрасширениеработысфайлами установитьсоединениесвнешнимисточникомданных установитьсоответствиеобъектаиформы ' + + 'установитьсоставстандартногоинтерфейсаodata установитьчасовойпоясинформационнойбазы установитьчасовойпояссеанса ' + + 'формат цел час часовойпояс часовойпояссеанса число числопрописью этоадресвременногохранилища '; + + // v8 свойства глобального контекста ==> built_in + const v8_global_context_property = + 'wsссылки библиотекакартинок библиотекамакетовоформлениякомпоновкиданных библиотекастилей бизнеспроцессы ' + + 'внешниеисточникиданных внешниеобработки внешниеотчеты встроенныепокупки главныйинтерфейс главныйстиль ' + + 'документы доставляемыеуведомления журналыдокументов задачи информацияобинтернетсоединении использованиерабочейдаты ' + + 'историяработыпользователя константы критерииотбора метаданные обработки отображениерекламы отправкадоставляемыхуведомлений ' + + 'отчеты панельзадачос параметрзапуска параметрысеанса перечисления планывидоврасчета планывидовхарактеристик ' + + 'планыобмена планысчетов полнотекстовыйпоиск пользователиинформационнойбазы последовательности проверкавстроенныхпокупок ' + + 'рабочаядата расширенияконфигурации регистрыбухгалтерии регистрынакопления регистрырасчета регистрысведений ' + + 'регламентныезадания сериализаторxdto справочники средствагеопозиционирования средствакриптографии средствамультимедиа ' + + 'средстваотображениярекламы средствапочты средствателефонии фабрикаxdto файловыепотоки фоновыезадания хранилищанастроек ' + + 'хранилищевариантовотчетов хранилищенастроекданныхформ хранилищеобщихнастроек хранилищепользовательскихнастроекдинамическихсписков ' + + 'хранилищепользовательскихнастроекотчетов хранилищесистемныхнастроек '; + + // built_in : встроенные или библиотечные объекты (константы, классы, функции) + const BUILTIN = + v7_system_constants + + v7_global_context_methods + v8_global_context_methods + + v8_global_context_property; + + // v8 системные наборы значений ==> class + const v8_system_sets_of_values = + 'webцвета windowsцвета windowsшрифты библиотекакартинок рамкистиля символы цветастиля шрифтыстиля '; + + // v8 системные перечисления - интерфейсные ==> class + const v8_system_enums_interface = + 'автоматическоесохранениеданныхформывнастройках автонумерациявформе автораздвижениесерий ' + + 'анимациядиаграммы вариантвыравниванияэлементовизаголовков вариантуправлениявысотойтаблицы ' + + 'вертикальнаяпрокруткаформы вертикальноеположение вертикальноеположениеэлемента видгруппыформы ' + + 'виддекорацииформы виддополненияэлементаформы видизмененияданных видкнопкиформы видпереключателя ' + + 'видподписейкдиаграмме видполяформы видфлажка влияниеразмеранапузырекдиаграммы горизонтальноеположение ' + + 'горизонтальноеположениеэлемента группировкаколонок группировкаподчиненныхэлементовформы ' + + 'группыиэлементы действиеперетаскивания дополнительныйрежимотображения допустимыедействияперетаскивания ' + + 'интервалмеждуэлементамиформы использованиевывода использованиеполосыпрокрутки ' + + 'используемоезначениеточкибиржевойдиаграммы историявыборапривводе источникзначенийоситочекдиаграммы ' + + 'источникзначенияразмерапузырькадиаграммы категориягруппыкоманд максимумсерий начальноеотображениедерева ' + + 'начальноеотображениесписка обновлениетекстаредактирования ориентациядендрограммы ориентациядиаграммы ' + + 'ориентацияметокдиаграммы ориентацияметоксводнойдиаграммы ориентацияэлементаформы отображениевдиаграмме ' + + 'отображениевлегендедиаграммы отображениегруппыкнопок отображениезаголовкашкалыдиаграммы ' + + 'отображениезначенийсводнойдиаграммы отображениезначенияизмерительнойдиаграммы ' + + 'отображениеинтерваладиаграммыганта отображениекнопки отображениекнопкивыбора отображениеобсужденийформы ' + + 'отображениеобычнойгруппы отображениеотрицательныхзначенийпузырьковойдиаграммы отображениепанелипоиска ' + + 'отображениеподсказки отображениепредупрежденияприредактировании отображениеразметкиполосырегулирования ' + + 'отображениестраницформы отображениетаблицы отображениетекстазначениядиаграммыганта ' + + 'отображениеуправленияобычнойгруппы отображениефигурыкнопки палитрацветовдиаграммы поведениеобычнойгруппы ' + + 'поддержкамасштабадендрограммы поддержкамасштабадиаграммыганта поддержкамасштабасводнойдиаграммы ' + + 'поисквтаблицепривводе положениезаголовкаэлементаформы положениекартинкикнопкиформы ' + + 'положениекартинкиэлементаграфическойсхемы положениекоманднойпанелиформы положениекоманднойпанелиэлементаформы ' + + 'положениеопорнойточкиотрисовки положениеподписейкдиаграмме положениеподписейшкалызначенийизмерительнойдиаграммы ' + + 'положениесостоянияпросмотра положениестрокипоиска положениетекстасоединительнойлинии положениеуправленияпоиском ' + + 'положениешкалывремени порядокотображенияточекгоризонтальнойгистограммы порядоксерийвлегендедиаграммы ' + + 'размеркартинки расположениезаголовкашкалыдиаграммы растягиваниеповертикалидиаграммыганта ' + + 'режимавтоотображениясостояния режимвводастроктаблицы режимвыборанезаполненного режимвыделениядаты ' + + 'режимвыделениястрокитаблицы режимвыделениятаблицы режимизмененияразмера режимизменениясвязанногозначения ' + + 'режимиспользованиядиалогапечати режимиспользованияпараметракоманды режиммасштабированияпросмотра ' + + 'режимосновногоокнаклиентскогоприложения режимоткрытияокнаформы режимотображениявыделения ' + + 'режимотображениягеографическойсхемы режимотображениязначенийсерии режимотрисовкисеткиграфическойсхемы ' + + 'режимполупрозрачностидиаграммы режимпробеловдиаграммы режимразмещениянастранице режимредактированияколонки ' + + 'режимсглаживаниядиаграммы режимсглаживанияиндикатора режимсписказадач сквозноевыравнивание ' + + 'сохранениеданныхформывнастройках способзаполнениятекстазаголовкашкалыдиаграммы ' + + 'способопределенияограничивающегозначениядиаграммы стандартнаягруппакоманд стандартноеоформление ' + + 'статусоповещенияпользователя стильстрелки типаппроксимациилиниитрендадиаграммы типдиаграммы ' + + 'типединицышкалывремени типимпортасерийслоягеографическойсхемы типлиниигеографическойсхемы типлиниидиаграммы ' + + 'типмаркерагеографическойсхемы типмаркерадиаграммы типобластиоформления ' + + 'типорганизацииисточникаданныхгеографическойсхемы типотображениясериислоягеографическойсхемы ' + + 'типотображенияточечногообъектагеографическойсхемы типотображенияшкалыэлементалегендыгеографическойсхемы ' + + 'типпоискаобъектовгеографическойсхемы типпроекциигеографическойсхемы типразмещенияизмерений ' + + 'типразмещенияреквизитовизмерений типрамкиэлементауправления типсводнойдиаграммы ' + + 'типсвязидиаграммыганта типсоединениязначенийпосериямдиаграммы типсоединенияточекдиаграммы ' + + 'типсоединительнойлинии типстороныэлементаграфическойсхемы типформыотчета типшкалырадарнойдиаграммы ' + + 'факторлиниитрендадиаграммы фигуракнопки фигурыграфическойсхемы фиксациявтаблице форматдняшкалывремени ' + + 'форматкартинки ширинаподчиненныхэлементовформы '; + + // v8 системные перечисления - свойства прикладных объектов ==> class + const v8_system_enums_objects_properties = + 'виддвижениябухгалтерии виддвижениянакопления видпериодарегистрарасчета видсчета видточкимаршрутабизнеспроцесса ' + + 'использованиеагрегатарегистранакопления использованиегруппиэлементов использованиережимапроведения ' + + 'использованиесреза периодичностьагрегатарегистранакопления режимавтовремя режимзаписидокумента режимпроведениядокумента '; + + // v8 системные перечисления - планы обмена ==> class + const v8_system_enums_exchange_plans = + 'авторегистрацияизменений допустимыйномерсообщения отправкаэлементаданных получениеэлементаданных '; + + // v8 системные перечисления - табличный документ ==> class + const v8_system_enums_tabular_document = + 'использованиерасшифровкитабличногодокумента ориентациястраницы положениеитоговколоноксводнойтаблицы ' + + 'положениеитоговстроксводнойтаблицы положениетекстаотносительнокартинки расположениезаголовкагруппировкитабличногодокумента ' + + 'способчтениязначенийтабличногодокумента типдвустороннейпечати типзаполненияобластитабличногодокумента ' + + 'типкурсоровтабличногодокумента типлиниирисункатабличногодокумента типлинииячейкитабличногодокумента ' + + 'типнаправленияпереходатабличногодокумента типотображениявыделениятабличногодокумента типотображениялинийсводнойтаблицы ' + + 'типразмещениятекстатабличногодокумента типрисункатабличногодокумента типсмещениятабличногодокумента ' + + 'типузоратабличногодокумента типфайлатабличногодокумента точностьпечати чередованиерасположениястраниц '; + + // v8 системные перечисления - планировщик ==> class + const v8_system_enums_sheduler = + 'отображениевремениэлементовпланировщика '; + + // v8 системные перечисления - форматированный документ ==> class + const v8_system_enums_formatted_document = + 'типфайлаформатированногодокумента '; + + // v8 системные перечисления - запрос ==> class + const v8_system_enums_query = + 'обходрезультатазапроса типзаписизапроса '; + + // v8 системные перечисления - построитель отчета ==> class + const v8_system_enums_report_builder = + 'видзаполнениярасшифровкипостроителяотчета типдобавленияпредставлений типизмеренияпостроителяотчета типразмещенияитогов '; + + // v8 системные перечисления - работа с файлами ==> class + const v8_system_enums_files = + 'доступкфайлу режимдиалогавыборафайла режимоткрытияфайла '; + + // v8 системные перечисления - построитель запроса ==> class + const v8_system_enums_query_builder = + 'типизмеренияпостроителязапроса '; + + // v8 системные перечисления - анализ данных ==> class + const v8_system_enums_data_analysis = + 'видданныханализа методкластеризации типединицыинтервалавременианализаданных типзаполнениятаблицырезультатаанализаданных ' + + 'типиспользованиячисловыхзначенийанализаданных типисточникаданныхпоискаассоциаций типколонкианализаданныхдереворешений ' + + 'типколонкианализаданныхкластеризация типколонкианализаданныхобщаястатистика типколонкианализаданныхпоискассоциаций ' + + 'типколонкианализаданныхпоискпоследовательностей типколонкимоделипрогноза типмерырасстоянияанализаданных ' + + 'типотсеченияправилассоциации типполяанализаданных типстандартизациианализаданных типупорядочиванияправилассоциациианализаданных ' + + 'типупорядочиванияшаблоновпоследовательностейанализаданных типупрощениядереварешений '; + + // v8 системные перечисления - xml, json, xs, dom, xdto, web-сервисы ==> class + const v8_system_enums_xml_json_xs_dom_xdto_ws = + 'wsнаправлениепараметра вариантxpathxs вариантзаписидатыjson вариантпростоготипаxs видгруппымоделиxs видфасетаxdto ' + + 'действиепостроителяdom завершенностьпростоготипаxs завершенностьсоставноготипаxs завершенностьсхемыxs запрещенныеподстановкиxs ' + + 'исключениягруппподстановкиxs категорияиспользованияатрибутаxs категорияограниченияидентичностиxs категорияограниченияпространствименxs ' + + 'методнаследованияxs модельсодержимогоxs назначениетипаxml недопустимыеподстановкиxs обработкапробельныхсимволовxs обработкасодержимогоxs ' + + 'ограничениезначенияxs параметрыотбораузловdom переносстрокjson позициявдокументеdom пробельныесимволыxml типатрибутаxml типзначенияjson ' + + 'типканоническогоxml типкомпонентыxs типпроверкиxml типрезультатаdomxpath типузлаdom типузлаxml формаxml формапредставленияxs ' + + 'форматдатыjson экранированиесимволовjson '; + + // v8 системные перечисления - система компоновки данных ==> class + const v8_system_enums_data_composition_system = + 'видсравнениякомпоновкиданных действиеобработкирасшифровкикомпоновкиданных направлениесортировкикомпоновкиданных ' + + 'расположениевложенныхэлементоврезультатакомпоновкиданных расположениеитоговкомпоновкиданных расположениегруппировкикомпоновкиданных ' + + 'расположениеполейгруппировкикомпоновкиданных расположениеполякомпоновкиданных расположениереквизитовкомпоновкиданных ' + + 'расположениересурсовкомпоновкиданных типбухгалтерскогоостаткакомпоновкиданных типвыводатекстакомпоновкиданных ' + + 'типгруппировкикомпоновкиданных типгруппыэлементовотборакомпоновкиданных типдополненияпериодакомпоновкиданных ' + + 'типзаголовкаполейкомпоновкиданных типмакетагруппировкикомпоновкиданных типмакетаобластикомпоновкиданных типостаткакомпоновкиданных ' + + 'типпериодакомпоновкиданных типразмещениятекстакомпоновкиданных типсвязинаборовданныхкомпоновкиданных типэлементарезультатакомпоновкиданных ' + + 'расположениелегендыдиаграммыкомпоновкиданных типпримененияотборакомпоновкиданных режимотображенияэлементанастройкикомпоновкиданных ' + + 'режимотображениянастроеккомпоновкиданных состояниеэлементанастройкикомпоновкиданных способвосстановлениянастроеккомпоновкиданных ' + + 'режимкомпоновкирезультата использованиепараметракомпоновкиданных автопозицияресурсовкомпоновкиданных ' + + 'вариантиспользованиягруппировкикомпоновкиданных расположениересурсоввдиаграммекомпоновкиданных фиксациякомпоновкиданных ' + + 'использованиеусловногооформлениякомпоновкиданных '; + + // v8 системные перечисления - почта ==> class + const v8_system_enums_email = + 'важностьинтернетпочтовогосообщения обработкатекстаинтернетпочтовогосообщения способкодированияинтернетпочтовоговложения ' + + 'способкодированиянеasciiсимволовинтернетпочтовогосообщения типтекстапочтовогосообщения протоколинтернетпочты ' + + 'статусразборапочтовогосообщения '; + + // v8 системные перечисления - журнал регистрации ==> class + const v8_system_enums_logbook = + 'режимтранзакциизаписижурналарегистрации статустранзакциизаписижурналарегистрации уровеньжурналарегистрации '; + + // v8 системные перечисления - криптография ==> class + const v8_system_enums_cryptography = + 'расположениехранилищасертификатовкриптографии режимвключениясертификатовкриптографии режимпроверкисертификатакриптографии ' + + 'типхранилищасертификатовкриптографии '; + + // v8 системные перечисления - ZIP ==> class + const v8_system_enums_zip = + 'кодировкаименфайловвzipфайле методсжатияzip методшифрованияzip режимвосстановленияпутейфайловzip режимобработкиподкаталоговzip ' + + 'режимсохраненияпутейzip уровеньсжатияzip '; + + // v8 системные перечисления - + // Блокировка данных, Фоновые задания, Автоматизированное тестирование, + // Доставляемые уведомления, Встроенные покупки, Интернет, Работа с двоичными данными ==> class + const v8_system_enums_other = + 'звуковоеоповещение направлениепереходакстроке позициявпотоке порядокбайтов режимблокировкиданных режимуправленияблокировкойданных ' + + 'сервисвстроенныхпокупок состояниефоновогозадания типподписчикадоставляемыхуведомлений уровеньиспользованиязащищенногосоединенияftp '; + + // v8 системные перечисления - схема запроса ==> class + const v8_system_enums_request_schema = + 'направлениепорядкасхемызапроса типдополненияпериодамисхемызапроса типконтрольнойточкисхемызапроса типобъединениясхемызапроса ' + + 'типпараметрадоступнойтаблицысхемызапроса типсоединениясхемызапроса '; + + // v8 системные перечисления - свойства объектов метаданных ==> class + const v8_system_enums_properties_of_metadata_objects = + 'httpметод автоиспользованиеобщегореквизита автопрефиксномеразадачи вариантвстроенногоязыка видиерархии видрегистранакопления ' + + 'видтаблицывнешнегоисточникаданных записьдвиженийприпроведении заполнениепоследовательностей индексирование ' + + 'использованиебазыпланавидоврасчета использованиебыстроговыбора использованиеобщегореквизита использованиеподчинения ' + + 'использованиеполнотекстовогопоиска использованиеразделяемыхданныхобщегореквизита использованиереквизита ' + + 'назначениеиспользованияприложения назначениерасширенияконфигурации направлениепередачи обновлениепредопределенныхданных ' + + 'оперативноепроведение основноепредставлениевидарасчета основноепредставлениевидахарактеристики основноепредставлениезадачи ' + + 'основноепредставлениепланаобмена основноепредставлениесправочника основноепредставлениесчета перемещениеграницыприпроведении ' + + 'периодичностьномерабизнеспроцесса периодичностьномерадокумента периодичностьрегистрарасчета периодичностьрегистрасведений ' + + 'повторноеиспользованиевозвращаемыхзначений полнотекстовыйпоискпривводепостроке принадлежностьобъекта проведение ' + + 'разделениеаутентификацииобщегореквизита разделениеданныхобщегореквизита разделениерасширенийконфигурацииобщегореквизита ' + + 'режимавтонумерацииобъектов режимзаписирегистра режимиспользованиямодальности ' + + 'режимиспользованиясинхронныхвызововрасширенийплатформыивнешнихкомпонент режимповторногоиспользованиясеансов ' + + 'режимполученияданныхвыборапривводепостроке режимсовместимости режимсовместимостиинтерфейса ' + + 'режимуправленияблокировкойданныхпоумолчанию сериикодовпланавидовхарактеристик сериикодовпланасчетов ' + + 'сериикодовсправочника созданиепривводе способвыбора способпоискастрокипривводепостроке способредактирования ' + + 'типданныхтаблицывнешнегоисточникаданных типкодапланавидоврасчета типкодасправочника типмакета типномерабизнеспроцесса ' + + 'типномерадокумента типномеразадачи типформы удалениедвижений '; + + // v8 системные перечисления - разные ==> class + const v8_system_enums_differents = + 'важностьпроблемыприменениярасширенияконфигурации вариантинтерфейсаклиентскогоприложения вариантмасштабаформклиентскогоприложения ' + + 'вариантосновногошрифтаклиентскогоприложения вариантстандартногопериода вариантстандартнойдатыначала видграницы видкартинки ' + + 'видотображенияполнотекстовогопоиска видрамки видсравнения видцвета видчисловогозначения видшрифта допустимаядлина допустимыйзнак ' + + 'использованиеbyteordermark использованиеметаданныхполнотекстовогопоиска источникрасширенийконфигурации клавиша кодвозвратадиалога ' + + 'кодировкаxbase кодировкатекста направлениепоиска направлениесортировки обновлениепредопределенныхданных обновлениеприизмененииданных ' + + 'отображениепанелиразделов проверказаполнения режимдиалогавопрос режимзапускаклиентскогоприложения режимокругления режимоткрытияформприложения ' + + 'режимполнотекстовогопоиска скоростьклиентскогосоединения состояниевнешнегоисточникаданных состояниеобновленияконфигурациибазыданных ' + + 'способвыборасертификатаwindows способкодированиястроки статуссообщения типвнешнейкомпоненты типплатформы типповеденияклавишиenter ' + + 'типэлементаинформацииовыполненииобновленияконфигурациибазыданных уровеньизоляциитранзакций хешфункция частидаты'; + + // class: встроенные наборы значений, системные перечисления (содержат дочерние значения, обращения к которым через разыменование) + const CLASS = + v8_system_sets_of_values + + v8_system_enums_interface + + v8_system_enums_objects_properties + + v8_system_enums_exchange_plans + + v8_system_enums_tabular_document + + v8_system_enums_sheduler + + v8_system_enums_formatted_document + + v8_system_enums_query + + v8_system_enums_report_builder + + v8_system_enums_files + + v8_system_enums_query_builder + + v8_system_enums_data_analysis + + v8_system_enums_xml_json_xs_dom_xdto_ws + + v8_system_enums_data_composition_system + + v8_system_enums_email + + v8_system_enums_logbook + + v8_system_enums_cryptography + + v8_system_enums_zip + + v8_system_enums_other + + v8_system_enums_request_schema + + v8_system_enums_properties_of_metadata_objects + + v8_system_enums_differents; + + // v8 общие объекты (у объектов есть конструктор, экземпляры создаются методом НОВЫЙ) ==> type + const v8_shared_object = + 'comобъект ftpсоединение httpзапрос httpсервисответ httpсоединение wsопределения wsпрокси xbase анализданных аннотацияxs ' + + 'блокировкаданных буфердвоичныхданных включениеxs выражениекомпоновкиданных генераторслучайныхчисел географическаясхема ' + + 'географическиекоординаты графическаясхема группамоделиxs данныерасшифровкикомпоновкиданных двоичныеданные дендрограмма ' + + 'диаграмма диаграммаганта диалогвыборафайла диалогвыборацвета диалогвыборашрифта диалограсписаниярегламентногозадания ' + + 'диалогредактированиястандартногопериода диапазон документdom документhtml документацияxs доставляемоеуведомление ' + + 'записьdom записьfastinfoset записьhtml записьjson записьxml записьzipфайла записьданных записьтекста записьузловdom ' + + 'запрос защищенноесоединениеopenssl значенияполейрасшифровкикомпоновкиданных извлечениетекста импортxs интернетпочта ' + + 'интернетпочтовоесообщение интернетпочтовыйпрофиль интернетпрокси интернетсоединение информациядляприложенияxs ' + + 'использованиеатрибутаxs использованиесобытияжурналарегистрации источникдоступныхнастроеккомпоновкиданных ' + + 'итераторузловdom картинка квалификаторыдаты квалификаторыдвоичныхданных квалификаторыстроки квалификаторычисла ' + + 'компоновщикмакетакомпоновкиданных компоновщикнастроеккомпоновкиданных конструктормакетаоформлениякомпоновкиданных ' + + 'конструкторнастроеккомпоновкиданных конструкторформатнойстроки линия макеткомпоновкиданных макетобластикомпоновкиданных ' + + 'макетоформлениякомпоновкиданных маскаxs менеджеркриптографии наборсхемxml настройкикомпоновкиданных настройкисериализацииjson ' + + 'обработкакартинок обработкарасшифровкикомпоновкиданных обходдереваdom объявлениеатрибутаxs объявлениенотацииxs ' + + 'объявлениеэлементаxs описаниеиспользованиясобытиядоступжурналарегистрации ' + + 'описаниеиспользованиясобытияотказвдоступежурналарегистрации описаниеобработкирасшифровкикомпоновкиданных ' + + 'описаниепередаваемогофайла описаниетипов определениегруппыатрибутовxs определениегруппымоделиxs ' + + 'определениеограниченияидентичностиxs определениепростоготипаxs определениесоставноготипаxs определениетипадокументаdom ' + + 'определенияxpathxs отборкомпоновкиданных пакетотображаемыхдокументов параметрвыбора параметркомпоновкиданных ' + + 'параметрызаписиjson параметрызаписиxml параметрычтенияxml переопределениеxs планировщик полеанализаданных ' + + 'полекомпоновкиданных построительdom построительзапроса построительотчета построительотчетаанализаданных ' + + 'построительсхемxml поток потоквпамяти почта почтовоесообщение преобразованиеxsl преобразованиекканоническомуxml ' + + 'процессорвыводарезультатакомпоновкиданныхвколлекциюзначений процессорвыводарезультатакомпоновкиданныхвтабличныйдокумент ' + + 'процессоркомпоновкиданных разыменовательпространствименdom рамка расписаниерегламентногозадания расширенноеимяxml ' + + 'результатчтенияданных своднаядиаграмма связьпараметравыбора связьпотипу связьпотипукомпоновкиданных сериализаторxdto ' + + 'сертификатклиентаwindows сертификатклиентафайл сертификаткриптографии сертификатыудостоверяющихцентровwindows ' + + 'сертификатыудостоверяющихцентровфайл сжатиеданных системнаяинформация сообщениепользователю сочетаниеклавиш ' + + 'сравнениезначений стандартнаядатаначала стандартныйпериод схемаxml схемакомпоновкиданных табличныйдокумент ' + + 'текстовыйдокумент тестируемоеприложение типданныхxml уникальныйидентификатор фабрикаxdto файл файловыйпоток ' + + 'фасетдлиныxs фасетколичестваразрядовдробнойчастиxs фасетмаксимальноговключающегозначенияxs ' + + 'фасетмаксимальногоисключающегозначенияxs фасетмаксимальнойдлиныxs фасетминимальноговключающегозначенияxs ' + + 'фасетминимальногоисключающегозначенияxs фасетминимальнойдлиныxs фасетобразцаxs фасетобщегоколичестваразрядовxs ' + + 'фасетперечисленияxs фасетпробельныхсимволовxs фильтрузловdom форматированнаястрока форматированныйдокумент ' + + 'фрагментxs хешированиеданных хранилищезначения цвет чтениеfastinfoset чтениеhtml чтениеjson чтениеxml чтениеzipфайла ' + + 'чтениеданных чтениетекста чтениеузловdom шрифт элементрезультатакомпоновкиданных '; + + // v8 универсальные коллекции значений ==> type + const v8_universal_collection = + 'comsafearray деревозначений массив соответствие списокзначений структура таблицазначений фиксированнаяструктура ' + + 'фиксированноесоответствие фиксированныймассив '; + + // type : встроенные типы + const TYPE = + v8_shared_object + + v8_universal_collection; + + // literal : примитивные типы + const LITERAL = 'null истина ложь неопределено'; + + // number : числа + const NUMBERS = hljs.inherit(hljs.NUMBER_MODE); + + // string : строки + const STRINGS = { + className: 'string', + begin: '"|\\|', + end: '"|$', + contains: [ { begin: '""' } ] + }; + + // number : даты + const DATE = { + begin: "'", + end: "'", + excludeBegin: true, + excludeEnd: true, + contains: [ + { + className: 'number', + begin: '\\d{4}([\\.\\\\/:-]?\\d{2}){0,5}' + } + ] + }; + + const PUNCTUATION = { + match: /[;()+\-:=,]/, + className: "punctuation", + relevance: 0 + }; + + // comment : комментарии + const COMMENTS = hljs.inherit(hljs.C_LINE_COMMENT_MODE); + + // meta : инструкции препроцессора, директивы компиляции + const META = { + className: 'meta', + + begin: '#|&', + end: '$', + keywords: { + $pattern: UNDERSCORE_IDENT_RE, + keyword: KEYWORD + METAKEYWORD + }, + contains: [ COMMENTS ] + }; + + // symbol : метка goto + const SYMBOL = { + className: 'symbol', + begin: '~', + end: ';|:', + excludeEnd: true + }; + + // function : объявление процедур и функций + const FUNCTION = { + className: 'function', + variants: [ + { + begin: 'процедура|функция', + end: '\\)', + keywords: 'процедура функция' + }, + { + begin: 'конецпроцедуры|конецфункции', + keywords: 'конецпроцедуры конецфункции' + } + ], + contains: [ + { + begin: '\\(', + end: '\\)', + endsParent: true, + contains: [ + { + className: 'params', + begin: UNDERSCORE_IDENT_RE, + end: ',', + excludeEnd: true, + endsWithParent: true, + keywords: { + $pattern: UNDERSCORE_IDENT_RE, + keyword: 'знач', + literal: LITERAL + }, + contains: [ + NUMBERS, + STRINGS, + DATE + ] + }, + COMMENTS + ] + }, + hljs.inherit(hljs.TITLE_MODE, { begin: UNDERSCORE_IDENT_RE }) + ] + }; + + return { + name: '1C:Enterprise', + case_insensitive: true, + keywords: { + $pattern: UNDERSCORE_IDENT_RE, + keyword: KEYWORD, + built_in: BUILTIN, + class: CLASS, + type: TYPE, + literal: LITERAL + }, + contains: [ + META, + FUNCTION, + COMMENTS, + SYMBOL, + NUMBERS, + STRINGS, + DATE, + PUNCTUATION + ] + }; +} + +export { _1c as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/1c.js.js b/frontend/node_modules/highlight.js/es/languages/1c.js.js new file mode 100644 index 0000000..af41c0e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/1c.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/1c" instead of "highlight.js/lib/languages/1c.js"' + ); + } + } + emitWarning(); + import lang from './1c.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/abnf.js b/frontend/node_modules/highlight.js/es/languages/abnf.js new file mode 100644 index 0000000..8b7d81f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/abnf.js @@ -0,0 +1,83 @@ +/* +Language: Augmented Backus-Naur Form +Author: Alex McKibben +Website: https://tools.ietf.org/html/rfc5234 +Category: syntax +Audit: 2020 +*/ + +/** @type LanguageFn */ +function abnf(hljs) { + const regex = hljs.regex; + const IDENT = /^[a-zA-Z][a-zA-Z0-9-]*/; + + const KEYWORDS = [ + "ALPHA", + "BIT", + "CHAR", + "CR", + "CRLF", + "CTL", + "DIGIT", + "DQUOTE", + "HEXDIG", + "HTAB", + "LF", + "LWSP", + "OCTET", + "SP", + "VCHAR", + "WSP" + ]; + + const COMMENT = hljs.COMMENT(/;/, /$/); + + const TERMINAL_BINARY = { + scope: "symbol", + match: /%b[0-1]+(-[0-1]+|(\.[0-1]+)+)?/ + }; + + const TERMINAL_DECIMAL = { + scope: "symbol", + match: /%d[0-9]+(-[0-9]+|(\.[0-9]+)+)?/ + }; + + const TERMINAL_HEXADECIMAL = { + scope: "symbol", + match: /%x[0-9A-F]+(-[0-9A-F]+|(\.[0-9A-F]+)+)?/ + }; + + const CASE_SENSITIVITY = { + scope: "symbol", + match: /%[si](?=".*")/ + }; + + const RULE_DECLARATION = { + scope: "attribute", + match: regex.concat(IDENT, /(?=\s*=)/) + }; + + const ASSIGNMENT = { + scope: "operator", + match: /=\/?/ + }; + + return { + name: 'Augmented Backus-Naur Form', + illegal: /[!@#$^&',?+~`|:]/, + keywords: KEYWORDS, + contains: [ + ASSIGNMENT, + RULE_DECLARATION, + COMMENT, + TERMINAL_BINARY, + TERMINAL_DECIMAL, + TERMINAL_HEXADECIMAL, + CASE_SENSITIVITY, + hljs.QUOTE_STRING_MODE, + hljs.NUMBER_MODE + ] + }; +} + +export { abnf as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/abnf.js.js b/frontend/node_modules/highlight.js/es/languages/abnf.js.js new file mode 100644 index 0000000..dc6be99 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/abnf.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/abnf" instead of "highlight.js/lib/languages/abnf.js"' + ); + } + } + emitWarning(); + import lang from './abnf.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/accesslog.js b/frontend/node_modules/highlight.js/es/languages/accesslog.js new file mode 100644 index 0000000..fa4b977 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/accesslog.js @@ -0,0 +1,92 @@ +/* + Language: Apache Access Log + Author: Oleg Efimov + Description: Apache/Nginx Access Logs + Website: https://httpd.apache.org/docs/2.4/logs.html#accesslog + Category: web, logs + Audit: 2020 + */ + +/** @type LanguageFn */ +function accesslog(hljs) { + const regex = hljs.regex; + // https://developer.mozilla.org/en-US/docs/Web/HTTP/Methods + const HTTP_VERBS = [ + "GET", + "POST", + "HEAD", + "PUT", + "DELETE", + "CONNECT", + "OPTIONS", + "PATCH", + "TRACE" + ]; + return { + name: 'Apache Access Log', + contains: [ + // IP + { + className: 'number', + begin: /^\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}(:\d{1,5})?\b/, + relevance: 5 + }, + // Other numbers + { + className: 'number', + begin: /\b\d+\b/, + relevance: 0 + }, + // Requests + { + className: 'string', + begin: regex.concat(/"/, regex.either(...HTTP_VERBS)), + end: /"/, + keywords: HTTP_VERBS, + illegal: /\n/, + relevance: 5, + contains: [ + { + begin: /HTTP\/[12]\.\d'/, + relevance: 5 + } + ] + }, + // Dates + { + className: 'string', + // dates must have a certain length, this prevents matching + // simple array accesses a[123] and [] and other common patterns + // found in other languages + begin: /\[\d[^\]\n]{8,}\]/, + illegal: /\n/, + relevance: 1 + }, + { + className: 'string', + begin: /\[/, + end: /\]/, + illegal: /\n/, + relevance: 0 + }, + // User agent / relevance boost + { + className: 'string', + begin: /"Mozilla\/\d\.\d \(/, + end: /"/, + illegal: /\n/, + relevance: 3 + }, + // Strings + { + className: 'string', + begin: /"/, + end: /"/, + illegal: /\n/, + relevance: 0 + } + ] + }; +} + +export { accesslog as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/accesslog.js.js b/frontend/node_modules/highlight.js/es/languages/accesslog.js.js new file mode 100644 index 0000000..5cfe625 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/accesslog.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/accesslog" instead of "highlight.js/lib/languages/accesslog.js"' + ); + } + } + emitWarning(); + import lang from './accesslog.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/actionscript.js b/frontend/node_modules/highlight.js/es/languages/actionscript.js new file mode 100644 index 0000000..e267f58 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/actionscript.js @@ -0,0 +1,153 @@ +/* +Language: ActionScript +Author: Alexander Myadzel +Category: scripting +Audit: 2020 +*/ + +/** @type LanguageFn */ +function actionscript(hljs) { + const regex = hljs.regex; + const IDENT_RE = /[a-zA-Z_$][a-zA-Z0-9_$]*/; + const PKG_NAME_RE = regex.concat( + IDENT_RE, + regex.concat("(\\.", IDENT_RE, ")*") + ); + const IDENT_FUNC_RETURN_TYPE_RE = /([*]|[a-zA-Z_$][a-zA-Z0-9_$]*)/; + + const AS3_REST_ARG_MODE = { + className: 'rest_arg', + begin: /[.]{3}/, + end: IDENT_RE, + relevance: 10 + }; + + const KEYWORDS = [ + "as", + "break", + "case", + "catch", + "class", + "const", + "continue", + "default", + "delete", + "do", + "dynamic", + "each", + "else", + "extends", + "final", + "finally", + "for", + "function", + "get", + "if", + "implements", + "import", + "in", + "include", + "instanceof", + "interface", + "internal", + "is", + "namespace", + "native", + "new", + "override", + "package", + "private", + "protected", + "public", + "return", + "set", + "static", + "super", + "switch", + "this", + "throw", + "try", + "typeof", + "use", + "var", + "void", + "while", + "with" + ]; + const LITERALS = [ + "true", + "false", + "null", + "undefined" + ]; + + return { + name: 'ActionScript', + aliases: [ 'as' ], + keywords: { + keyword: KEYWORDS, + literal: LITERALS + }, + contains: [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.C_NUMBER_MODE, + { + match: [ + /\bpackage/, + /\s+/, + PKG_NAME_RE + ], + className: { + 1: "keyword", + 3: "title.class" + } + }, + { + match: [ + /\b(?:class|interface|extends|implements)/, + /\s+/, + IDENT_RE + ], + className: { + 1: "keyword", + 3: "title.class" + } + }, + { + className: 'meta', + beginKeywords: 'import include', + end: /;/, + keywords: { keyword: 'import include' } + }, + { + beginKeywords: 'function', + end: /[{;]/, + excludeEnd: true, + illegal: /\S/, + contains: [ + hljs.inherit(hljs.TITLE_MODE, { className: "title.function" }), + { + className: 'params', + begin: /\(/, + end: /\)/, + contains: [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + AS3_REST_ARG_MODE + ] + }, + { begin: regex.concat(/:\s*/, IDENT_FUNC_RETURN_TYPE_RE) } + ] + }, + hljs.METHOD_GUARD + ], + illegal: /#/ + }; +} + +export { actionscript as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/actionscript.js.js b/frontend/node_modules/highlight.js/es/languages/actionscript.js.js new file mode 100644 index 0000000..ab44fb7 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/actionscript.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/actionscript" instead of "highlight.js/lib/languages/actionscript.js"' + ); + } + } + emitWarning(); + import lang from './actionscript.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/ada.js b/frontend/node_modules/highlight.js/es/languages/ada.js new file mode 100644 index 0000000..734c617 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ada.js @@ -0,0 +1,265 @@ +/* +Language: Ada +Author: Lars Schulna +Description: Ada is a general-purpose programming language that has great support for saftey critical and real-time applications. + It has been developed by the DoD and thus has been used in military and safety-critical applications (like civil aviation). + The first version appeared in the 80s, but it's still actively developed today with + the newest standard being Ada2012. +*/ + +// We try to support full Ada2012 +// +// We highlight all appearances of types, keywords, literals (string, char, number, bool) +// and titles (user defined function/procedure/package) +// CSS classes are set accordingly +// +// Languages causing problems for language detection: +// xml (broken by Foo : Bar type), elm (broken by Foo : Bar type), vbscript-html (broken by body keyword) +// sql (ada default.txt has a lot of sql keywords) + +/** @type LanguageFn */ +function ada(hljs) { + // Regular expression for Ada numeric literals. + // stolen form the VHDL highlighter + + // Decimal literal: + const INTEGER_RE = '\\d(_|\\d)*'; + const EXPONENT_RE = '[eE][-+]?' + INTEGER_RE; + const DECIMAL_LITERAL_RE = INTEGER_RE + '(\\.' + INTEGER_RE + ')?' + '(' + EXPONENT_RE + ')?'; + + // Based literal: + const BASED_INTEGER_RE = '\\w+'; + const BASED_LITERAL_RE = INTEGER_RE + '#' + BASED_INTEGER_RE + '(\\.' + BASED_INTEGER_RE + ')?' + '#' + '(' + EXPONENT_RE + ')?'; + + const NUMBER_RE = '\\b(' + BASED_LITERAL_RE + '|' + DECIMAL_LITERAL_RE + ')'; + + // Identifier regex + const ID_REGEX = '[A-Za-z](_?[A-Za-z0-9.])*'; + + // bad chars, only allowed in literals + const BAD_CHARS = `[]\\{\\}%#'"`; + + // Ada doesn't have block comments, only line comments + const COMMENTS = hljs.COMMENT('--', '$'); + + // variable declarations of the form + // Foo : Bar := Baz; + // where only Bar will be highlighted + const VAR_DECLS = { + // TODO: These spaces are not required by the Ada syntax + // however, I have yet to see handwritten Ada code where + // someone does not put spaces around : + begin: '\\s+:\\s+', + end: '\\s*(:=|;|\\)|=>|$)', + // endsWithParent: true, + // returnBegin: true, + illegal: BAD_CHARS, + contains: [ + { + // workaround to avoid highlighting + // named loops and declare blocks + beginKeywords: 'loop for declare others', + endsParent: true + }, + { + // properly highlight all modifiers + className: 'keyword', + beginKeywords: 'not null constant access function procedure in out aliased exception' + }, + { + className: 'type', + begin: ID_REGEX, + endsParent: true, + relevance: 0 + } + ] + }; + + const KEYWORDS = [ + "abort", + "else", + "new", + "return", + "abs", + "elsif", + "not", + "reverse", + "abstract", + "end", + "accept", + "entry", + "select", + "access", + "exception", + "of", + "separate", + "aliased", + "exit", + "or", + "some", + "all", + "others", + "subtype", + "and", + "for", + "out", + "synchronized", + "array", + "function", + "overriding", + "at", + "tagged", + "generic", + "package", + "task", + "begin", + "goto", + "pragma", + "terminate", + "body", + "private", + "then", + "if", + "procedure", + "type", + "case", + "in", + "protected", + "constant", + "interface", + "is", + "raise", + "use", + "declare", + "range", + "delay", + "limited", + "record", + "when", + "delta", + "loop", + "rem", + "while", + "digits", + "renames", + "with", + "do", + "mod", + "requeue", + "xor" + ]; + + return { + name: 'Ada', + case_insensitive: true, + keywords: { + keyword: KEYWORDS, + literal: [ + "True", + "False" + ] + }, + contains: [ + COMMENTS, + // strings "foobar" + { + className: 'string', + begin: /"/, + end: /"/, + contains: [ + { + begin: /""/, + relevance: 0 + } + ] + }, + // characters '' + { + // character literals always contain one char + className: 'string', + begin: /'.'/ + }, + { + // number literals + className: 'number', + begin: NUMBER_RE, + relevance: 0 + }, + { + // Attributes + className: 'symbol', + begin: "'" + ID_REGEX + }, + { + // package definition, maybe inside generic + className: 'title', + begin: '(\\bwith\\s+)?(\\bprivate\\s+)?\\bpackage\\s+(\\bbody\\s+)?', + end: '(is|$)', + keywords: 'package body', + excludeBegin: true, + excludeEnd: true, + illegal: BAD_CHARS + }, + { + // function/procedure declaration/definition + // maybe inside generic + begin: '(\\b(with|overriding)\\s+)?\\b(function|procedure)\\s+', + end: '(\\bis|\\bwith|\\brenames|\\)\\s*;)', + keywords: 'overriding function procedure with is renames return', + // we need to re-match the 'function' keyword, so that + // the title mode below matches only exactly once + returnBegin: true, + contains: + [ + COMMENTS, + { + // name of the function/procedure + className: 'title', + begin: '(\\bwith\\s+)?\\b(function|procedure)\\s+', + end: '(\\(|\\s+|$)', + excludeBegin: true, + excludeEnd: true, + illegal: BAD_CHARS + }, + // 'self' + // // parameter types + VAR_DECLS, + { + // return type + className: 'type', + begin: '\\breturn\\s+', + end: '(\\s+|;|$)', + keywords: 'return', + excludeBegin: true, + excludeEnd: true, + // we are done with functions + endsParent: true, + illegal: BAD_CHARS + + } + ] + }, + { + // new type declarations + // maybe inside generic + className: 'type', + begin: '\\b(sub)?type\\s+', + end: '\\s+', + keywords: 'type', + excludeBegin: true, + illegal: BAD_CHARS + }, + + // see comment above the definition + VAR_DECLS + + // no markup + // relevance boosters for small snippets + // {begin: '\\s*=>\\s*'}, + // {begin: '\\s*:=\\s*'}, + // {begin: '\\s+:=\\s+'}, + ] + }; +} + +export { ada as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/ada.js.js b/frontend/node_modules/highlight.js/es/languages/ada.js.js new file mode 100644 index 0000000..40096ef --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ada.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/ada" instead of "highlight.js/lib/languages/ada.js"' + ); + } + } + emitWarning(); + import lang from './ada.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/angelscript.js b/frontend/node_modules/highlight.js/es/languages/angelscript.js new file mode 100644 index 0000000..6bc1f6b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/angelscript.js @@ -0,0 +1,178 @@ +/* +Language: AngelScript +Author: Melissa Geels +Category: scripting +Website: https://www.angelcode.com/angelscript/ +*/ + +/** @type LanguageFn */ +function angelscript(hljs) { + const builtInTypeMode = { + className: 'built_in', + begin: '\\b(void|bool|int8|int16|int32|int64|int|uint8|uint16|uint32|uint64|uint|string|ref|array|double|float|auto|dictionary)' + }; + + const objectHandleMode = { + className: 'symbol', + begin: '[a-zA-Z0-9_]+@' + }; + + const genericMode = { + className: 'keyword', + begin: '<', + end: '>', + contains: [ + builtInTypeMode, + objectHandleMode + ] + }; + + builtInTypeMode.contains = [ genericMode ]; + objectHandleMode.contains = [ genericMode ]; + + const KEYWORDS = [ + "for", + "in|0", + "break", + "continue", + "while", + "do|0", + "return", + "if", + "else", + "case", + "switch", + "namespace", + "is", + "cast", + "or", + "and", + "xor", + "not", + "get|0", + "in", + "inout|10", + "out", + "override", + "set|0", + "private", + "public", + "const", + "default|0", + "final", + "shared", + "external", + "mixin|10", + "enum", + "typedef", + "funcdef", + "this", + "super", + "import", + "from", + "interface", + "abstract|0", + "try", + "catch", + "protected", + "explicit", + "property" + ]; + + return { + name: 'AngelScript', + aliases: [ 'asc' ], + + keywords: KEYWORDS, + + // avoid close detection with C# and JS + illegal: '(^using\\s+[A-Za-z0-9_\\.]+;$|\\bfunction\\s*[^\\(])', + + contains: [ + { // 'strings' + className: 'string', + begin: '\'', + end: '\'', + illegal: '\\n', + contains: [ hljs.BACKSLASH_ESCAPE ], + relevance: 0 + }, + + // """heredoc strings""" + { + className: 'string', + begin: '"""', + end: '"""' + }, + + { // "strings" + className: 'string', + begin: '"', + end: '"', + illegal: '\\n', + contains: [ hljs.BACKSLASH_ESCAPE ], + relevance: 0 + }, + + hljs.C_LINE_COMMENT_MODE, // single-line comments + hljs.C_BLOCK_COMMENT_MODE, // comment blocks + + { // metadata + className: 'string', + begin: '^\\s*\\[', + end: '\\]' + }, + + { // interface or namespace declaration + beginKeywords: 'interface namespace', + end: /\{/, + illegal: '[;.\\-]', + contains: [ + { // interface or namespace name + className: 'symbol', + begin: '[a-zA-Z0-9_]+' + } + ] + }, + + { // class declaration + beginKeywords: 'class', + end: /\{/, + illegal: '[;.\\-]', + contains: [ + { // class name + className: 'symbol', + begin: '[a-zA-Z0-9_]+', + contains: [ + { + begin: '[:,]\\s*', + contains: [ + { + className: 'symbol', + begin: '[a-zA-Z0-9_]+' + } + ] + } + ] + } + ] + }, + + builtInTypeMode, // built-in types + objectHandleMode, // object handles + + { // literals + className: 'literal', + begin: '\\b(null|true|false)' + }, + + { // numbers + className: 'number', + relevance: 0, + begin: '(-?)(\\b0[xXbBoOdD][a-fA-F0-9]+|(\\b\\d+(\\.\\d*)?f?|\\.\\d+f?)([eE][-+]?\\d+f?)?)' + } + ] + }; +} + +export { angelscript as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/angelscript.js.js b/frontend/node_modules/highlight.js/es/languages/angelscript.js.js new file mode 100644 index 0000000..f25e7fa --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/angelscript.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/angelscript" instead of "highlight.js/lib/languages/angelscript.js"' + ); + } + } + emitWarning(); + import lang from './angelscript.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/apache.js b/frontend/node_modules/highlight.js/es/languages/apache.js new file mode 100644 index 0000000..f8f9e4f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/apache.js @@ -0,0 +1,105 @@ +/* +Language: Apache config +Author: Ruslan Keba +Contributors: Ivan Sagalaev +Website: https://httpd.apache.org +Description: language definition for Apache configuration files (httpd.conf & .htaccess) +Category: config, web +Audit: 2020 +*/ + +/** @type LanguageFn */ +function apache(hljs) { + const NUMBER_REF = { + className: 'number', + begin: /[$%]\d+/ + }; + const NUMBER = { + className: 'number', + begin: /\b\d+/ + }; + const IP_ADDRESS = { + className: "number", + begin: /\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}(:\d{1,5})?/ + }; + const PORT_NUMBER = { + className: "number", + begin: /:\d{1,5}/ + }; + return { + name: 'Apache config', + aliases: [ 'apacheconf' ], + case_insensitive: true, + contains: [ + hljs.HASH_COMMENT_MODE, + { + className: 'section', + begin: /<\/?/, + end: />/, + contains: [ + IP_ADDRESS, + PORT_NUMBER, + // low relevance prevents us from claming XML/HTML where this rule would + // match strings inside of XML tags + hljs.inherit(hljs.QUOTE_STRING_MODE, { relevance: 0 }) + ] + }, + { + className: 'attribute', + begin: /\w+/, + relevance: 0, + // keywords aren’t needed for highlighting per se, they only boost relevance + // for a very generally defined mode (starts with a word, ends with line-end + keywords: { _: [ + "order", + "deny", + "allow", + "setenv", + "rewriterule", + "rewriteengine", + "rewritecond", + "documentroot", + "sethandler", + "errordocument", + "loadmodule", + "options", + "header", + "listen", + "serverroot", + "servername" + ] }, + starts: { + end: /$/, + relevance: 0, + keywords: { literal: 'on off all deny allow' }, + contains: [ + { + scope: "punctuation", + match: /\\\n/ + }, + { + className: 'meta', + begin: /\s\[/, + end: /\]$/ + }, + { + className: 'variable', + begin: /[\$%]\{/, + end: /\}/, + contains: [ + 'self', + NUMBER_REF + ] + }, + IP_ADDRESS, + NUMBER, + hljs.QUOTE_STRING_MODE + ] + } + } + ], + illegal: /\S/ + }; +} + +export { apache as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/apache.js.js b/frontend/node_modules/highlight.js/es/languages/apache.js.js new file mode 100644 index 0000000..a30877d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/apache.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/apache" instead of "highlight.js/lib/languages/apache.js"' + ); + } + } + emitWarning(); + import lang from './apache.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/applescript.js b/frontend/node_modules/highlight.js/es/languages/applescript.js new file mode 100644 index 0000000..7807429 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/applescript.js @@ -0,0 +1,149 @@ +/* +Language: AppleScript +Authors: Nathan Grigg , Dr. Drang +Category: scripting +Website: https://developer.apple.com/library/archive/documentation/AppleScript/Conceptual/AppleScriptLangGuide/introduction/ASLR_intro.html +Audit: 2020 +*/ + +/** @type LanguageFn */ +function applescript(hljs) { + const regex = hljs.regex; + const STRING = hljs.inherit( + hljs.QUOTE_STRING_MODE, { illegal: null }); + const PARAMS = { + className: 'params', + begin: /\(/, + end: /\)/, + contains: [ + 'self', + hljs.C_NUMBER_MODE, + STRING + ] + }; + const COMMENT_MODE_1 = hljs.COMMENT(/--/, /$/); + const COMMENT_MODE_2 = hljs.COMMENT( + /\(\*/, + /\*\)/, + { contains: [ + 'self', // allow nesting + COMMENT_MODE_1 + ] } + ); + const COMMENTS = [ + COMMENT_MODE_1, + COMMENT_MODE_2, + hljs.HASH_COMMENT_MODE + ]; + + const KEYWORD_PATTERNS = [ + /apart from/, + /aside from/, + /instead of/, + /out of/, + /greater than/, + /isn't|(doesn't|does not) (equal|come before|come after|contain)/, + /(greater|less) than( or equal)?/, + /(starts?|ends|begins?) with/, + /contained by/, + /comes (before|after)/, + /a (ref|reference)/, + /POSIX (file|path)/, + /(date|time) string/, + /quoted form/ + ]; + + const BUILT_IN_PATTERNS = [ + /clipboard info/, + /the clipboard/, + /info for/, + /list (disks|folder)/, + /mount volume/, + /path to/, + /(close|open for) access/, + /(get|set) eof/, + /current date/, + /do shell script/, + /get volume settings/, + /random number/, + /set volume/, + /system attribute/, + /system info/, + /time to GMT/, + /(load|run|store) script/, + /scripting components/, + /ASCII (character|number)/, + /localized string/, + /choose (application|color|file|file name|folder|from list|remote application|URL)/, + /display (alert|dialog)/ + ]; + + return { + name: 'AppleScript', + aliases: [ 'osascript' ], + keywords: { + keyword: + 'about above after against and around as at back before beginning ' + + 'behind below beneath beside between but by considering ' + + 'contain contains continue copy div does eighth else end equal ' + + 'equals error every exit fifth first for fourth from front ' + + 'get given global if ignoring in into is it its last local me ' + + 'middle mod my ninth not of on onto or over prop property put ref ' + + 'reference repeat returning script second set seventh since ' + + 'sixth some tell tenth that the|0 then third through thru ' + + 'timeout times to transaction try until where while whose with ' + + 'without', + literal: + 'AppleScript false linefeed return pi quote result space tab true', + built_in: + 'alias application boolean class constant date file integer list ' + + 'number real record string text ' + + 'activate beep count delay launch log offset read round ' + + 'run say summarize write ' + + 'character characters contents day frontmost id item length ' + + 'month name|0 paragraph paragraphs rest reverse running time version ' + + 'weekday word words year' + }, + contains: [ + STRING, + hljs.C_NUMBER_MODE, + { + className: 'built_in', + begin: regex.concat( + /\b/, + regex.either(...BUILT_IN_PATTERNS), + /\b/ + ) + }, + { + className: 'built_in', + begin: /^\s*return\b/ + }, + { + className: 'literal', + begin: + /\b(text item delimiters|current application|missing value)\b/ + }, + { + className: 'keyword', + begin: regex.concat( + /\b/, + regex.either(...KEYWORD_PATTERNS), + /\b/ + ) + }, + { + beginKeywords: 'on', + illegal: /[${=;\n]/, + contains: [ + hljs.UNDERSCORE_TITLE_MODE, + PARAMS + ] + }, + ...COMMENTS + ], + illegal: /\/\/|->|=>|\[\[/ + }; +} + +export { applescript as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/applescript.js.js b/frontend/node_modules/highlight.js/es/languages/applescript.js.js new file mode 100644 index 0000000..f377013 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/applescript.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/applescript" instead of "highlight.js/lib/languages/applescript.js"' + ); + } + } + emitWarning(); + import lang from './applescript.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/arcade.js b/frontend/node_modules/highlight.js/es/languages/arcade.js new file mode 100644 index 0000000..29101d4 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/arcade.js @@ -0,0 +1,428 @@ +/* + Language: ArcGIS Arcade + Category: scripting + Website: https://developers.arcgis.com/arcade/ + Description: ArcGIS Arcade is an expression language used in many Esri ArcGIS products such as Pro, Online, Server, Runtime, JavaScript, and Python +*/ + +/** @type LanguageFn */ +function arcade(hljs) { + const regex = hljs.regex; + const IDENT_RE = '[A-Za-z_][0-9A-Za-z_]*'; + const KEYWORDS = { + keyword: [ + "break", + "case", + "catch", + "continue", + "debugger", + "do", + "else", + "export", + "for", + "function", + "if", + "import", + "in", + "new", + "of", + "return", + "switch", + "try", + "var", + "void", + "while" + ], + literal: [ + "BackSlash", + "DoubleQuote", + "ForwardSlash", + "Infinity", + "NaN", + "NewLine", + "PI", + "SingleQuote", + "Tab", + "TextFormatting", + "false", + "null", + "true", + "undefined" + ], + built_in: [ + "Abs", + "Acos", + "All", + "Angle", + "Any", + "Area", + "AreaGeodetic", + "Array", + "Asin", + "Atan", + "Atan2", + "Attachments", + "Average", + "Back", + "Bearing", + "Boolean", + "Buffer", + "BufferGeodetic", + "Ceil", + "Centroid", + "ChangeTimeZone", + "Clip", + "Concatenate", + "Console", + "Constrain", + "Contains", + "ConvertDirection", + "ConvexHull", + "Cos", + "Count", + "Crosses", + "Cut", + "Date|0", + "DateAdd", + "DateDiff", + "DateOnly", + "Day", + "Decode", + "DefaultValue", + "Densify", + "DensifyGeodetic", + "Dictionary", + "Difference", + "Disjoint", + "Distance", + "DistanceGeodetic", + "DistanceToCoordinate", + "Distinct", + "Domain", + "DomainCode", + "DomainName", + "EnvelopeIntersects", + "Equals", + "Erase", + "Exp", + "Expects", + "Extent", + "Feature", + "FeatureInFilter", + "FeatureSet", + "FeatureSetByAssociation", + "FeatureSetById", + "FeatureSetByName", + "FeatureSetByPortalItem", + "FeatureSetByRelationshipClass", + "FeatureSetByRelationshipName", + "Filter", + "FilterBySubtypeCode", + "Find", + "First|0", + "Floor", + "FromCharCode", + "FromCodePoint", + "FromJSON", + "Front", + "GdbVersion", + "Generalize", + "Geometry", + "GetEnvironment", + "GetFeatureSet", + "GetFeatureSetInfo", + "GetUser", + "GroupBy", + "Guid", + "HasKey", + "HasValue", + "Hash", + "Hour", + "IIf", + "ISOMonth", + "ISOWeek", + "ISOWeekday", + "ISOYear", + "Includes", + "IndexOf", + "Insert", + "Intersection", + "Intersects", + "IsEmpty", + "IsNan", + "IsSelfIntersecting", + "IsSimple", + "KnowledgeGraphByPortalItem", + "Left|0", + "Length", + "Length3D", + "LengthGeodetic", + "Log", + "Lower", + "Map", + "Max", + "Mean", + "MeasureToCoordinate", + "Mid", + "Millisecond", + "Min", + "Minute", + "Month", + "MultiPartToSinglePart", + "Multipoint", + "NearestCoordinate", + "NearestVertex", + "NextSequenceValue", + "None", + "Now", + "Number", + "Offset", + "OrderBy", + "Overlaps", + "Point", + "PointToCoordinate", + "Polygon", + "Polyline", + "Pop", + "Portal", + "Pow", + "Proper", + "Push", + "QueryGraph", + "Random", + "Reduce", + "Relate", + "Replace", + "Resize", + "Reverse", + "Right|0", + "RingIsClockwise", + "Rotate", + "Round", + "Schema", + "Second", + "SetGeometry", + "Simplify", + "Sin", + "Slice", + "Sort", + "Splice", + "Split", + "Sqrt", + "StandardizeFilename", + "StandardizeGuid", + "Stdev", + "SubtypeCode", + "SubtypeName", + "Subtypes", + "Sum", + "SymmetricDifference", + "Tan", + "Text", + "Time", + "TimeZone", + "TimeZoneOffset", + "Timestamp", + "ToCharCode", + "ToCodePoint", + "ToHex", + "ToLocal", + "ToUTC", + "Today", + "Top|0", + "Touches", + "TrackAccelerationAt", + "TrackAccelerationWindow", + "TrackCurrentAcceleration", + "TrackCurrentDistance", + "TrackCurrentSpeed", + "TrackCurrentTime", + "TrackDistanceAt", + "TrackDistanceWindow", + "TrackDuration", + "TrackFieldWindow", + "TrackGeometryWindow", + "TrackIndex", + "TrackSpeedAt", + "TrackSpeedWindow", + "TrackStartTime", + "TrackWindow", + "Trim", + "TypeOf", + "Union", + "Upper", + "UrlEncode", + "Variance", + "Week", + "Weekday", + "When|0", + "Within", + "Year|0", + ] + }; + const PROFILE_VARS = [ + "aggregatedFeatures", + "analytic", + "config", + "datapoint", + "datastore", + "editcontext", + "feature", + "featureSet", + "feedfeature", + "fencefeature", + "fencenotificationtype", + "graph", + "join", + "layer", + "locationupdate", + "map", + "measure", + "measure", + "originalFeature", + "record", + "reference", + "rowindex", + "sourcedatastore", + "sourcefeature", + "sourcelayer", + "target", + "targetdatastore", + "targetfeature", + "targetlayer", + "userInput", + "value", + "variables", + "view" + ]; + const SYMBOL = { + className: 'symbol', + begin: '\\$' + regex.either(...PROFILE_VARS) + }; + const NUMBER = { + className: 'number', + variants: [ + { begin: '\\b(0[bB][01]+)' }, + { begin: '\\b(0[oO][0-7]+)' }, + { begin: hljs.C_NUMBER_RE } + ], + relevance: 0 + }; + const SUBST = { + className: 'subst', + begin: '\\$\\{', + end: '\\}', + keywords: KEYWORDS, + contains: [] // defined later + }; + const TEMPLATE_STRING = { + className: 'string', + begin: '`', + end: '`', + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST + ] + }; + SUBST.contains = [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + TEMPLATE_STRING, + NUMBER, + hljs.REGEXP_MODE + ]; + const PARAMS_CONTAINS = SUBST.contains.concat([ + hljs.C_BLOCK_COMMENT_MODE, + hljs.C_LINE_COMMENT_MODE + ]); + + return { + name: 'ArcGIS Arcade', + case_insensitive: true, + keywords: KEYWORDS, + contains: [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + TEMPLATE_STRING, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + SYMBOL, + NUMBER, + { // object attr container + begin: /[{,]\s*/, + relevance: 0, + contains: [ + { + begin: IDENT_RE + '\\s*:', + returnBegin: true, + relevance: 0, + contains: [ + { + className: 'attr', + begin: IDENT_RE, + relevance: 0 + } + ] + } + ] + }, + { // "value" container + begin: '(' + hljs.RE_STARTERS_RE + '|\\b(return)\\b)\\s*', + keywords: 'return', + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.REGEXP_MODE, + { + className: 'function', + begin: '(\\(.*?\\)|' + IDENT_RE + ')\\s*=>', + returnBegin: true, + end: '\\s*=>', + contains: [ + { + className: 'params', + variants: [ + { begin: IDENT_RE }, + { begin: /\(\s*\)/ }, + { + begin: /\(/, + end: /\)/, + excludeBegin: true, + excludeEnd: true, + keywords: KEYWORDS, + contains: PARAMS_CONTAINS + } + ] + } + ] + } + ], + relevance: 0 + }, + { + beginKeywords: 'function', + end: /\{/, + excludeEnd: true, + contains: [ + hljs.inherit(hljs.TITLE_MODE, { + className: "title.function", + begin: IDENT_RE + }), + { + className: 'params', + begin: /\(/, + end: /\)/, + excludeBegin: true, + excludeEnd: true, + contains: PARAMS_CONTAINS + } + ], + illegal: /\[|%/ + }, + { begin: /\$[(.]/ } + ], + illegal: /#(?!!)/ + }; +} + +export { arcade as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/arcade.js.js b/frontend/node_modules/highlight.js/es/languages/arcade.js.js new file mode 100644 index 0000000..46b21ae --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/arcade.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/arcade" instead of "highlight.js/lib/languages/arcade.js"' + ); + } + } + emitWarning(); + import lang from './arcade.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/arduino.js b/frontend/node_modules/highlight.js/es/languages/arduino.js new file mode 100644 index 0000000..cb8a772 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/arduino.js @@ -0,0 +1,1008 @@ +/* +Language: C++ +Category: common, system +Website: https://isocpp.org +*/ + +/** @type LanguageFn */ +function cPlusPlus(hljs) { + const regex = hljs.regex; + // added for historic reasons because `hljs.C_LINE_COMMENT_MODE` does + // not include such support nor can we be sure all the grammars depending + // on it would desire this behavior + const C_LINE_COMMENT_MODE = hljs.COMMENT('//', '$', { contains: [ { begin: /\\\n/ } ] }); + const DECLTYPE_AUTO_RE = 'decltype\\(auto\\)'; + const NAMESPACE_RE = '[a-zA-Z_]\\w*::'; + const TEMPLATE_ARGUMENT_RE = '<[^<>]+>'; + const FUNCTION_TYPE_RE = '(?!struct)(' + + DECLTYPE_AUTO_RE + '|' + + regex.optional(NAMESPACE_RE) + + '[a-zA-Z_]\\w*' + regex.optional(TEMPLATE_ARGUMENT_RE) + + ')'; + + const CPP_PRIMITIVE_TYPES = { + className: 'type', + begin: '\\b[a-z\\d_]*_t\\b' + }; + + // https://en.cppreference.com/w/cpp/language/escape + // \\ \x \xFF \u2837 \u00323747 \374 + const CHARACTER_ESCAPES = '\\\\(x[0-9A-Fa-f]{2}|u[0-9A-Fa-f]{4,8}|[0-7]{3}|\\S)'; + const STRINGS = { + className: 'string', + variants: [ + { + begin: '(u8?|U|L)?"', + end: '"', + illegal: '\\n', + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: '(u8?|U|L)?\'(' + CHARACTER_ESCAPES + '|.)', + end: '\'', + illegal: '.' + }, + hljs.END_SAME_AS_BEGIN({ + begin: /(?:u8?|U|L)?R"([^()\\ ]{0,16})\(/, + end: /\)([^()\\ ]{0,16})"/ + }) + ] + }; + + const NUMBERS = { + className: 'number', + variants: [ + // Floating-point literal. + { begin: + "[+-]?(?:" // Leading sign. + // Decimal. + + "(?:" + +"[0-9](?:'?[0-9])*\\.(?:[0-9](?:'?[0-9])*)?" + + "|\\.[0-9](?:'?[0-9])*" + + ")(?:[Ee][+-]?[0-9](?:'?[0-9])*)?" + + "|[0-9](?:'?[0-9])*[Ee][+-]?[0-9](?:'?[0-9])*" + // Hexadecimal. + + "|0[Xx](?:" + +"[0-9A-Fa-f](?:'?[0-9A-Fa-f])*(?:\\.(?:[0-9A-Fa-f](?:'?[0-9A-Fa-f])*)?)?" + + "|\\.[0-9A-Fa-f](?:'?[0-9A-Fa-f])*" + + ")[Pp][+-]?[0-9](?:'?[0-9])*" + + ")(?:" // Literal suffixes. + + "[Ff](?:16|32|64|128)?" + + "|(BF|bf)16" + + "|[Ll]" + + "|" // Literal suffix is optional. + + ")" + }, + // Integer literal. + { begin: + "[+-]?\\b(?:" // Leading sign. + + "0[Bb][01](?:'?[01])*" // Binary. + + "|0[Xx][0-9A-Fa-f](?:'?[0-9A-Fa-f])*" // Hexadecimal. + + "|0(?:'?[0-7])*" // Octal or just a lone zero. + + "|[1-9](?:'?[0-9])*" // Decimal. + + ")(?:" // Literal suffixes. + + "[Uu](?:LL?|ll?)" + + "|[Uu][Zz]?" + + "|(?:LL?|ll?)[Uu]?" + + "|[Zz][Uu]" + + "|" // Literal suffix is optional. + + ")" + // Note: there are user-defined literal suffixes too, but perhaps having the custom suffix not part of the + // literal highlight actually makes it stand out more. + } + ], + relevance: 0 + }; + + const PREPROCESSOR = { + className: 'meta', + begin: /#\s*[a-z]+\b/, + end: /$/, + keywords: { keyword: + 'if else elif endif define undef warning error line ' + + 'pragma _Pragma ifdef ifndef include' }, + contains: [ + { + begin: /\\\n/, + relevance: 0 + }, + hljs.inherit(STRINGS, { className: 'string' }), + { + className: 'string', + begin: /<.*?>/ + }, + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }; + + const TITLE_MODE = { + className: 'title', + begin: regex.optional(NAMESPACE_RE) + hljs.IDENT_RE, + relevance: 0 + }; + + const FUNCTION_TITLE = regex.optional(NAMESPACE_RE) + hljs.IDENT_RE + '\\s*\\('; + + // https://en.cppreference.com/w/cpp/keyword + const RESERVED_KEYWORDS = [ + 'alignas', + 'alignof', + 'and', + 'and_eq', + 'asm', + 'atomic_cancel', + 'atomic_commit', + 'atomic_noexcept', + 'auto', + 'bitand', + 'bitor', + 'break', + 'case', + 'catch', + 'class', + 'co_await', + 'co_return', + 'co_yield', + 'compl', + 'concept', + 'const_cast|10', + 'consteval', + 'constexpr', + 'constinit', + 'continue', + 'decltype', + 'default', + 'delete', + 'do', + 'dynamic_cast|10', + 'else', + 'enum', + 'explicit', + 'export', + 'extern', + 'false', + 'final', + 'for', + 'friend', + 'goto', + 'if', + 'import', + 'inline', + 'module', + 'mutable', + 'namespace', + 'new', + 'noexcept', + 'not', + 'not_eq', + 'nullptr', + 'operator', + 'or', + 'or_eq', + 'override', + 'private', + 'protected', + 'public', + 'reflexpr', + 'register', + 'reinterpret_cast|10', + 'requires', + 'return', + 'sizeof', + 'static_assert', + 'static_cast|10', + 'struct', + 'switch', + 'synchronized', + 'template', + 'this', + 'thread_local', + 'throw', + 'transaction_safe', + 'transaction_safe_dynamic', + 'true', + 'try', + 'typedef', + 'typeid', + 'typename', + 'union', + 'using', + 'virtual', + 'volatile', + 'while', + 'xor', + 'xor_eq' + ]; + + // https://en.cppreference.com/w/cpp/keyword + const RESERVED_TYPES = [ + 'bool', + 'char', + 'char16_t', + 'char32_t', + 'char8_t', + 'double', + 'float', + 'int', + 'long', + 'short', + 'void', + 'wchar_t', + 'unsigned', + 'signed', + 'const', + 'static' + ]; + + const TYPE_HINTS = [ + 'any', + 'auto_ptr', + 'barrier', + 'binary_semaphore', + 'bitset', + 'complex', + 'condition_variable', + 'condition_variable_any', + 'counting_semaphore', + 'deque', + 'false_type', + 'flat_map', + 'flat_set', + 'future', + 'imaginary', + 'initializer_list', + 'istringstream', + 'jthread', + 'latch', + 'lock_guard', + 'multimap', + 'multiset', + 'mutex', + 'optional', + 'ostringstream', + 'packaged_task', + 'pair', + 'promise', + 'priority_queue', + 'queue', + 'recursive_mutex', + 'recursive_timed_mutex', + 'scoped_lock', + 'set', + 'shared_future', + 'shared_lock', + 'shared_mutex', + 'shared_timed_mutex', + 'shared_ptr', + 'stack', + 'string_view', + 'stringstream', + 'timed_mutex', + 'thread', + 'true_type', + 'tuple', + 'unique_lock', + 'unique_ptr', + 'unordered_map', + 'unordered_multimap', + 'unordered_multiset', + 'unordered_set', + 'variant', + 'vector', + 'weak_ptr', + 'wstring', + 'wstring_view' + ]; + + const FUNCTION_HINTS = [ + 'abort', + 'abs', + 'acos', + 'apply', + 'as_const', + 'asin', + 'atan', + 'atan2', + 'calloc', + 'ceil', + 'cerr', + 'cin', + 'clog', + 'cos', + 'cosh', + 'cout', + 'declval', + 'endl', + 'exchange', + 'exit', + 'exp', + 'fabs', + 'floor', + 'fmod', + 'forward', + 'fprintf', + 'fputs', + 'free', + 'frexp', + 'fscanf', + 'future', + 'invoke', + 'isalnum', + 'isalpha', + 'iscntrl', + 'isdigit', + 'isgraph', + 'islower', + 'isprint', + 'ispunct', + 'isspace', + 'isupper', + 'isxdigit', + 'labs', + 'launder', + 'ldexp', + 'log', + 'log10', + 'make_pair', + 'make_shared', + 'make_shared_for_overwrite', + 'make_tuple', + 'make_unique', + 'malloc', + 'memchr', + 'memcmp', + 'memcpy', + 'memset', + 'modf', + 'move', + 'pow', + 'printf', + 'putchar', + 'puts', + 'realloc', + 'scanf', + 'sin', + 'sinh', + 'snprintf', + 'sprintf', + 'sqrt', + 'sscanf', + 'std', + 'stderr', + 'stdin', + 'stdout', + 'strcat', + 'strchr', + 'strcmp', + 'strcpy', + 'strcspn', + 'strlen', + 'strncat', + 'strncmp', + 'strncpy', + 'strpbrk', + 'strrchr', + 'strspn', + 'strstr', + 'swap', + 'tan', + 'tanh', + 'terminate', + 'to_underlying', + 'tolower', + 'toupper', + 'vfprintf', + 'visit', + 'vprintf', + 'vsprintf' + ]; + + const LITERALS = [ + 'NULL', + 'false', + 'nullopt', + 'nullptr', + 'true' + ]; + + // https://en.cppreference.com/w/cpp/keyword + const BUILT_IN = [ '_Pragma' ]; + + const CPP_KEYWORDS = { + type: RESERVED_TYPES, + keyword: RESERVED_KEYWORDS, + literal: LITERALS, + built_in: BUILT_IN, + _type_hints: TYPE_HINTS + }; + + const FUNCTION_DISPATCH = { + className: 'function.dispatch', + relevance: 0, + keywords: { + // Only for relevance, not highlighting. + _hint: FUNCTION_HINTS }, + begin: regex.concat( + /\b/, + /(?!decltype)/, + /(?!if)/, + /(?!for)/, + /(?!switch)/, + /(?!while)/, + hljs.IDENT_RE, + regex.lookahead(/(<[^<>]+>|)\s*\(/)) + }; + + const EXPRESSION_CONTAINS = [ + FUNCTION_DISPATCH, + PREPROCESSOR, + CPP_PRIMITIVE_TYPES, + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + NUMBERS, + STRINGS + ]; + + const EXPRESSION_CONTEXT = { + // This mode covers expression context where we can't expect a function + // definition and shouldn't highlight anything that looks like one: + // `return some()`, `else if()`, `(x*sum(1, 2))` + variants: [ + { + begin: /=/, + end: /;/ + }, + { + begin: /\(/, + end: /\)/ + }, + { + beginKeywords: 'new throw return else', + end: /;/ + } + ], + keywords: CPP_KEYWORDS, + contains: EXPRESSION_CONTAINS.concat([ + { + begin: /\(/, + end: /\)/, + keywords: CPP_KEYWORDS, + contains: EXPRESSION_CONTAINS.concat([ 'self' ]), + relevance: 0 + } + ]), + relevance: 0 + }; + + const FUNCTION_DECLARATION = { + className: 'function', + begin: '(' + FUNCTION_TYPE_RE + '[\\*&\\s]+)+' + FUNCTION_TITLE, + returnBegin: true, + end: /[{;=]/, + excludeEnd: true, + keywords: CPP_KEYWORDS, + illegal: /[^\w\s\*&:<>.]/, + contains: [ + { // to prevent it from being confused as the function title + begin: DECLTYPE_AUTO_RE, + keywords: CPP_KEYWORDS, + relevance: 0 + }, + { + begin: FUNCTION_TITLE, + returnBegin: true, + contains: [ TITLE_MODE ], + relevance: 0 + }, + // needed because we do not have look-behind on the below rule + // to prevent it from grabbing the final : in a :: pair + { + begin: /::/, + relevance: 0 + }, + // initializers + { + begin: /:/, + endsWithParent: true, + contains: [ + STRINGS, + NUMBERS + ] + }, + // allow for multiple declarations, e.g.: + // extern void f(int), g(char); + { + relevance: 0, + match: /,/ + }, + { + className: 'params', + begin: /\(/, + end: /\)/, + keywords: CPP_KEYWORDS, + relevance: 0, + contains: [ + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + STRINGS, + NUMBERS, + CPP_PRIMITIVE_TYPES, + // Count matching parentheses. + { + begin: /\(/, + end: /\)/, + keywords: CPP_KEYWORDS, + relevance: 0, + contains: [ + 'self', + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + STRINGS, + NUMBERS, + CPP_PRIMITIVE_TYPES + ] + } + ] + }, + CPP_PRIMITIVE_TYPES, + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + PREPROCESSOR + ] + }; + + return { + name: 'C++', + aliases: [ + 'cc', + 'c++', + 'h++', + 'hpp', + 'hh', + 'hxx', + 'cxx' + ], + keywords: CPP_KEYWORDS, + illegal: ' rooms (9);` + begin: '\\b(deque|list|queue|priority_queue|pair|stack|vector|map|set|bitset|multiset|multimap|unordered_map|unordered_set|unordered_multiset|unordered_multimap|array|tuple|optional|variant|function|flat_map|flat_set)\\s*<(?!<)', + end: '>', + keywords: CPP_KEYWORDS, + contains: [ + 'self', + CPP_PRIMITIVE_TYPES + ] + }, + { + begin: hljs.IDENT_RE + '::', + keywords: CPP_KEYWORDS + }, + { + match: [ + // extra complexity to deal with `enum class` and `enum struct` + /\b(?:enum(?:\s+(?:class|struct))?|class|struct|union)/, + /\s+/, + /\w+/ + ], + className: { + 1: 'keyword', + 3: 'title.class' + } + } + ]) + }; +} + +/* +Language: Arduino +Author: Stefania Mellai +Description: The Arduino® Language is a superset of C++. This rules are designed to highlight the Arduino® source code. For info about language see http://www.arduino.cc. +Website: https://www.arduino.cc +Category: system +*/ + + +/** @type LanguageFn */ +function arduino(hljs) { + const ARDUINO_KW = { + type: [ + "boolean", + "byte", + "word", + "String" + ], + built_in: [ + "KeyboardController", + "MouseController", + "SoftwareSerial", + "EthernetServer", + "EthernetClient", + "LiquidCrystal", + "RobotControl", + "GSMVoiceCall", + "EthernetUDP", + "EsploraTFT", + "HttpClient", + "RobotMotor", + "WiFiClient", + "GSMScanner", + "FileSystem", + "Scheduler", + "GSMServer", + "YunClient", + "YunServer", + "IPAddress", + "GSMClient", + "GSMModem", + "Keyboard", + "Ethernet", + "Console", + "GSMBand", + "Esplora", + "Stepper", + "Process", + "WiFiUDP", + "GSM_SMS", + "Mailbox", + "USBHost", + "Firmata", + "PImage", + "Client", + "Server", + "GSMPIN", + "FileIO", + "Bridge", + "Serial", + "EEPROM", + "Stream", + "Mouse", + "Audio", + "Servo", + "File", + "Task", + "GPRS", + "WiFi", + "Wire", + "TFT", + "GSM", + "SPI", + "SD" + ], + _hints: [ + "setup", + "loop", + "runShellCommandAsynchronously", + "analogWriteResolution", + "retrieveCallingNumber", + "printFirmwareVersion", + "analogReadResolution", + "sendDigitalPortPair", + "noListenOnLocalhost", + "readJoystickButton", + "setFirmwareVersion", + "readJoystickSwitch", + "scrollDisplayRight", + "getVoiceCallStatus", + "scrollDisplayLeft", + "writeMicroseconds", + "delayMicroseconds", + "beginTransmission", + "getSignalStrength", + "runAsynchronously", + "getAsynchronously", + "listenOnLocalhost", + "getCurrentCarrier", + "readAccelerometer", + "messageAvailable", + "sendDigitalPorts", + "lineFollowConfig", + "countryNameWrite", + "runShellCommand", + "readStringUntil", + "rewindDirectory", + "readTemperature", + "setClockDivider", + "readLightSensor", + "endTransmission", + "analogReference", + "detachInterrupt", + "countryNameRead", + "attachInterrupt", + "encryptionType", + "readBytesUntil", + "robotNameWrite", + "readMicrophone", + "robotNameRead", + "cityNameWrite", + "userNameWrite", + "readJoystickY", + "readJoystickX", + "mouseReleased", + "openNextFile", + "scanNetworks", + "noInterrupts", + "digitalWrite", + "beginSpeaker", + "mousePressed", + "isActionDone", + "mouseDragged", + "displayLogos", + "noAutoscroll", + "addParameter", + "remoteNumber", + "getModifiers", + "keyboardRead", + "userNameRead", + "waitContinue", + "processInput", + "parseCommand", + "printVersion", + "readNetworks", + "writeMessage", + "blinkVersion", + "cityNameRead", + "readMessage", + "setDataMode", + "parsePacket", + "isListening", + "setBitOrder", + "beginPacket", + "isDirectory", + "motorsWrite", + "drawCompass", + "digitalRead", + "clearScreen", + "serialEvent", + "rightToLeft", + "setTextSize", + "leftToRight", + "requestFrom", + "keyReleased", + "compassRead", + "analogWrite", + "interrupts", + "WiFiServer", + "disconnect", + "playMelody", + "parseFloat", + "autoscroll", + "getPINUsed", + "setPINUsed", + "setTimeout", + "sendAnalog", + "readSlider", + "analogRead", + "beginWrite", + "createChar", + "motorsStop", + "keyPressed", + "tempoWrite", + "readButton", + "subnetMask", + "debugPrint", + "macAddress", + "writeGreen", + "randomSeed", + "attachGPRS", + "readString", + "sendString", + "remotePort", + "releaseAll", + "mouseMoved", + "background", + "getXChange", + "getYChange", + "answerCall", + "getResult", + "voiceCall", + "endPacket", + "constrain", + "getSocket", + "writeJSON", + "getButton", + "available", + "connected", + "findUntil", + "readBytes", + "exitValue", + "readGreen", + "writeBlue", + "startLoop", + "IPAddress", + "isPressed", + "sendSysex", + "pauseMode", + "gatewayIP", + "setCursor", + "getOemKey", + "tuneWrite", + "noDisplay", + "loadImage", + "switchPIN", + "onRequest", + "onReceive", + "changePIN", + "playFile", + "noBuffer", + "parseInt", + "overflow", + "checkPIN", + "knobRead", + "beginTFT", + "bitClear", + "updateIR", + "bitWrite", + "position", + "writeRGB", + "highByte", + "writeRed", + "setSpeed", + "readBlue", + "noStroke", + "remoteIP", + "transfer", + "shutdown", + "hangCall", + "beginSMS", + "endWrite", + "attached", + "maintain", + "noCursor", + "checkReg", + "checkPUK", + "shiftOut", + "isValid", + "shiftIn", + "pulseIn", + "connect", + "println", + "localIP", + "pinMode", + "getIMEI", + "display", + "noBlink", + "process", + "getBand", + "running", + "beginSD", + "drawBMP", + "lowByte", + "setBand", + "release", + "bitRead", + "prepare", + "pointTo", + "readRed", + "setMode", + "noFill", + "remove", + "listen", + "stroke", + "detach", + "attach", + "noTone", + "exists", + "buffer", + "height", + "bitSet", + "circle", + "config", + "cursor", + "random", + "IRread", + "setDNS", + "endSMS", + "getKey", + "micros", + "millis", + "begin", + "print", + "write", + "ready", + "flush", + "width", + "isPIN", + "blink", + "clear", + "press", + "mkdir", + "rmdir", + "close", + "point", + "yield", + "image", + "BSSID", + "click", + "delay", + "read", + "text", + "move", + "peek", + "beep", + "rect", + "line", + "open", + "seek", + "fill", + "size", + "turn", + "stop", + "home", + "find", + "step", + "tone", + "sqrt", + "RSSI", + "SSID", + "end", + "bit", + "tan", + "cos", + "sin", + "pow", + "map", + "abs", + "max", + "min", + "get", + "run", + "put" + ], + literal: [ + "DIGITAL_MESSAGE", + "FIRMATA_STRING", + "ANALOG_MESSAGE", + "REPORT_DIGITAL", + "REPORT_ANALOG", + "INPUT_PULLUP", + "SET_PIN_MODE", + "INTERNAL2V56", + "SYSTEM_RESET", + "LED_BUILTIN", + "INTERNAL1V1", + "SYSEX_START", + "INTERNAL", + "EXTERNAL", + "DEFAULT", + "OUTPUT", + "INPUT", + "HIGH", + "LOW" + ] + }; + + const ARDUINO = cPlusPlus(hljs); + + const kws = /** @type {Record} */ (ARDUINO.keywords); + + kws.type = [ + ...kws.type, + ...ARDUINO_KW.type + ]; + kws.literal = [ + ...kws.literal, + ...ARDUINO_KW.literal + ]; + kws.built_in = [ + ...kws.built_in, + ...ARDUINO_KW.built_in + ]; + kws._hints = ARDUINO_KW._hints; + + ARDUINO.name = 'Arduino'; + ARDUINO.aliases = [ 'ino' ]; + ARDUINO.supersetOf = "cpp"; + + return ARDUINO; +} + +export { arduino as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/arduino.js.js b/frontend/node_modules/highlight.js/es/languages/arduino.js.js new file mode 100644 index 0000000..5415d1d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/arduino.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/arduino" instead of "highlight.js/lib/languages/arduino.js"' + ); + } + } + emitWarning(); + import lang from './arduino.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/armasm.js b/frontend/node_modules/highlight.js/es/languages/armasm.js new file mode 100644 index 0000000..40e7eec --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/armasm.js @@ -0,0 +1,124 @@ +/* +Language: ARM Assembly +Author: Dan Panzarella +Description: ARM Assembly including Thumb and Thumb2 instructions +Category: assembler +*/ + +/** @type LanguageFn */ +function armasm(hljs) { + // local labels: %?[FB]?[AT]?\d{1,2}\w+ + + const COMMENT = { variants: [ + hljs.COMMENT('^[ \\t]*(?=#)', '$', { + relevance: 0, + excludeBegin: true + }), + hljs.COMMENT('[;@]', '$', { relevance: 0 }), + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] }; + + return { + name: 'ARM Assembly', + case_insensitive: true, + aliases: [ 'arm' ], + keywords: { + $pattern: '\\.?' + hljs.IDENT_RE, + meta: + // GNU preprocs + '.2byte .4byte .align .ascii .asciz .balign .byte .code .data .else .end .endif .endm .endr .equ .err .exitm .extern .global .hword .if .ifdef .ifndef .include .irp .long .macro .rept .req .section .set .skip .space .text .word .arm .thumb .code16 .code32 .force_thumb .thumb_func .ltorg ' + // ARM directives + + 'ALIAS ALIGN ARM AREA ASSERT ATTR CN CODE CODE16 CODE32 COMMON CP DATA DCB DCD DCDU DCDO DCFD DCFDU DCI DCQ DCQU DCW DCWU DN ELIF ELSE END ENDFUNC ENDIF ENDP ENTRY EQU EXPORT EXPORTAS EXTERN FIELD FILL FUNCTION GBLA GBLL GBLS GET GLOBAL IF IMPORT INCBIN INCLUDE INFO KEEP LCLA LCLL LCLS LTORG MACRO MAP MEND MEXIT NOFP OPT PRESERVE8 PROC QN READONLY RELOC REQUIRE REQUIRE8 RLIST FN ROUT SETA SETL SETS SN SPACE SUBT THUMB THUMBX TTL WHILE WEND ', + built_in: + 'r0 r1 r2 r3 r4 r5 r6 r7 r8 r9 r10 r11 r12 r13 r14 r15 ' // standard registers + + 'w0 w1 w2 w3 w4 w5 w6 w7 w8 w9 w10 w11 w12 w13 w14 w15 ' // 32 bit ARMv8 registers + + 'w16 w17 w18 w19 w20 w21 w22 w23 w24 w25 w26 w27 w28 w29 w30 ' + + 'x0 x1 x2 x3 x4 x5 x6 x7 x8 x9 x10 x11 x12 x13 x14 x15 ' // 64 bit ARMv8 registers + + 'x16 x17 x18 x19 x20 x21 x22 x23 x24 x25 x26 x27 x28 x29 x30 ' + + 'pc lr sp ip sl sb fp ' // typical regs plus backward compatibility + + 'a1 a2 a3 a4 v1 v2 v3 v4 v5 v6 v7 v8 f0 f1 f2 f3 f4 f5 f6 f7 ' // more regs and fp + + 'p0 p1 p2 p3 p4 p5 p6 p7 p8 p9 p10 p11 p12 p13 p14 p15 ' // coprocessor regs + + 'c0 c1 c2 c3 c4 c5 c6 c7 c8 c9 c10 c11 c12 c13 c14 c15 ' // more coproc + + 'q0 q1 q2 q3 q4 q5 q6 q7 q8 q9 q10 q11 q12 q13 q14 q15 ' // advanced SIMD NEON regs + + // program status registers + + 'cpsr_c cpsr_x cpsr_s cpsr_f cpsr_cx cpsr_cxs cpsr_xs cpsr_xsf cpsr_sf cpsr_cxsf ' + + 'spsr_c spsr_x spsr_s spsr_f spsr_cx spsr_cxs spsr_xs spsr_xsf spsr_sf spsr_cxsf ' + + // NEON and VFP registers + + 's0 s1 s2 s3 s4 s5 s6 s7 s8 s9 s10 s11 s12 s13 s14 s15 ' + + 's16 s17 s18 s19 s20 s21 s22 s23 s24 s25 s26 s27 s28 s29 s30 s31 ' + + 'd0 d1 d2 d3 d4 d5 d6 d7 d8 d9 d10 d11 d12 d13 d14 d15 ' + + 'd16 d17 d18 d19 d20 d21 d22 d23 d24 d25 d26 d27 d28 d29 d30 d31 ' + + + '{PC} {VAR} {TRUE} {FALSE} {OPT} {CONFIG} {ENDIAN} {CODESIZE} {CPU} {FPU} {ARCHITECTURE} {PCSTOREOFFSET} {ARMASM_VERSION} {INTER} {ROPI} {RWPI} {SWST} {NOSWST} . @' + }, + contains: [ + { + className: 'keyword', + begin: '\\b(' // mnemonics + + 'adc|' + + '(qd?|sh?|u[qh]?)?add(8|16)?|usada?8|(q|sh?|u[qh]?)?(as|sa)x|' + + 'and|adrl?|sbc|rs[bc]|asr|b[lx]?|blx|bxj|cbn?z|tb[bh]|bic|' + + 'bfc|bfi|[su]bfx|bkpt|cdp2?|clz|clrex|cmp|cmn|cpsi[ed]|cps|' + + 'setend|dbg|dmb|dsb|eor|isb|it[te]{0,3}|lsl|lsr|ror|rrx|' + + 'ldm(([id][ab])|f[ds])?|ldr((s|ex)?[bhd])?|movt?|mvn|mra|mar|' + + 'mul|[us]mull|smul[bwt][bt]|smu[as]d|smmul|smmla|' + + 'mla|umlaal|smlal?([wbt][bt]|d)|mls|smlsl?[ds]|smc|svc|sev|' + + 'mia([bt]{2}|ph)?|mrr?c2?|mcrr2?|mrs|msr|orr|orn|pkh(tb|bt)|rbit|' + + 'rev(16|sh)?|sel|[su]sat(16)?|nop|pop|push|rfe([id][ab])?|' + + 'stm([id][ab])?|str(ex)?[bhd]?|(qd?)?sub|(sh?|q|u[qh]?)?sub(8|16)|' + + '[su]xt(a?h|a?b(16)?)|srs([id][ab])?|swpb?|swi|smi|tst|teq|' + + 'wfe|wfi|yield' + + ')' + + '(eq|ne|cs|cc|mi|pl|vs|vc|hi|ls|ge|lt|gt|le|al|hs|lo)?' // condition codes + + '[sptrx]?' // legal postfixes + + '(?=\\s)' // followed by space + }, + COMMENT, + hljs.QUOTE_STRING_MODE, + { + className: 'string', + begin: '\'', + end: '[^\\\\]\'', + relevance: 0 + }, + { + className: 'title', + begin: '\\|', + end: '\\|', + illegal: '\\n', + relevance: 0 + }, + { + className: 'number', + variants: [ + { // hex + begin: '[#$=]?0x[0-9a-f]+' }, + { // bin + begin: '[#$=]?0b[01]+' }, + { // literal + begin: '[#$=]\\d+' }, + { // bare number + begin: '\\b\\d+' } + ], + relevance: 0 + }, + { + className: 'symbol', + variants: [ + { // GNU ARM syntax + begin: '^[ \\t]*[a-z_\\.\\$][a-z0-9_\\.\\$]+:' }, + { // ARM syntax + begin: '^[a-z_\\.\\$][a-z0-9_\\.\\$]+' }, + { // label reference + begin: '[=#]\\w+' } + ], + relevance: 0 + } + ] + }; +} + +export { armasm as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/armasm.js.js b/frontend/node_modules/highlight.js/es/languages/armasm.js.js new file mode 100644 index 0000000..b40c9f3 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/armasm.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/armasm" instead of "highlight.js/lib/languages/armasm.js"' + ); + } + } + emitWarning(); + import lang from './armasm.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/asciidoc.js b/frontend/node_modules/highlight.js/es/languages/asciidoc.js new file mode 100644 index 0000000..feb7953 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/asciidoc.js @@ -0,0 +1,261 @@ +/* +Language: AsciiDoc +Requires: xml.js +Author: Dan Allen +Website: http://asciidoc.org +Description: A semantic, text-based document format that can be exported to HTML, DocBook and other backends. +Category: markup +*/ + +/** @type LanguageFn */ +function asciidoc(hljs) { + const regex = hljs.regex; + const HORIZONTAL_RULE = { + begin: '^\'{3,}[ \\t]*$', + relevance: 10 + }; + const ESCAPED_FORMATTING = [ + // escaped constrained formatting marks (i.e., \* \_ or \`) + { begin: /\\[*_`]/ }, + // escaped unconstrained formatting marks (i.e., \\** \\__ or \\``) + // must ignore until the next formatting marks + // this rule might not be 100% compliant with Asciidoctor 2.0 but we are entering undefined behavior territory... + { begin: /\\\\\*{2}[^\n]*?\*{2}/ }, + { begin: /\\\\_{2}[^\n]*_{2}/ }, + { begin: /\\\\`{2}[^\n]*`{2}/ }, + // guard: constrained formatting mark may not be preceded by ":", ";" or + // "}". match these so the constrained rule doesn't see them + { begin: /[:;}][*_`](?![*_`])/ } + ]; + const STRONG = [ + // inline unconstrained strong (single line) + { + className: 'strong', + begin: /\*{2}([^\n]+?)\*{2}/ + }, + // inline unconstrained strong (multi-line) + { + className: 'strong', + begin: regex.concat( + /\*\*/, + /((\*(?!\*)|\\[^\n]|[^*\n\\])+\n)+/, + /(\*(?!\*)|\\[^\n]|[^*\n\\])*/, + /\*\*/ + ), + relevance: 0 + }, + // inline constrained strong (single line) + { + className: 'strong', + // must not precede or follow a word character + begin: /\B\*(\S|\S[^\n]*?\S)\*(?!\w)/ + }, + // inline constrained strong (multi-line) + { + className: 'strong', + // must not precede or follow a word character + begin: /\*[^\s]([^\n]+\n)+([^\n]+)\*/ + } + ]; + const EMPHASIS = [ + // inline unconstrained emphasis (single line) + { + className: 'emphasis', + begin: /_{2}([^\n]+?)_{2}/ + }, + // inline unconstrained emphasis (multi-line) + { + className: 'emphasis', + begin: regex.concat( + /__/, + /((_(?!_)|\\[^\n]|[^_\n\\])+\n)+/, + /(_(?!_)|\\[^\n]|[^_\n\\])*/, + /__/ + ), + relevance: 0 + }, + // inline constrained emphasis (single line) + { + className: 'emphasis', + // must not precede or follow a word character + begin: /\b_(\S|\S[^\n]*?\S)_(?!\w)/ + }, + // inline constrained emphasis (multi-line) + { + className: 'emphasis', + // must not precede or follow a word character + begin: /_[^\s]([^\n]+\n)+([^\n]+)_/ + }, + // inline constrained emphasis using single quote (legacy) + { + className: 'emphasis', + // must not follow a word character or be followed by a single quote or space + begin: '\\B\'(?![\'\\s])', + end: '(\\n{2}|\')', + // allow escaped single quote followed by word char + contains: [ + { + begin: '\\\\\'\\w', + relevance: 0 + } + ], + relevance: 0 + } + ]; + const ADMONITION = { + className: 'symbol', + begin: '^(NOTE|TIP|IMPORTANT|WARNING|CAUTION):\\s+', + relevance: 10 + }; + const BULLET_LIST = { + className: 'bullet', + begin: '^(\\*+|-+|\\.+|[^\\n]+?::)\\s+' + }; + + return { + name: 'AsciiDoc', + aliases: [ 'adoc' ], + contains: [ + // block comment + hljs.COMMENT( + '^/{4,}\\n', + '\\n/{4,}$', + // can also be done as... + // '^/{4,}$', + // '^/{4,}$', + { relevance: 10 } + ), + // line comment + hljs.COMMENT( + '^//', + '$', + { relevance: 0 } + ), + // title + { + className: 'title', + begin: '^\\.\\w.*$' + }, + // example, admonition & sidebar blocks + { + begin: '^[=\\*]{4,}\\n', + end: '\\n^[=\\*]{4,}$', + relevance: 10 + }, + // headings + { + className: 'section', + relevance: 10, + variants: [ + { begin: '^(={1,6})[ \t].+?([ \t]\\1)?$' }, + { begin: '^[^\\[\\]\\n]+?\\n[=\\-~\\^\\+]{2,}$' } + ] + }, + // document attributes + { + className: 'meta', + begin: '^:.+?:', + end: '\\s', + excludeEnd: true, + relevance: 10 + }, + // block attributes + { + className: 'meta', + begin: '^\\[.+?\\]$', + relevance: 0 + }, + // quoteblocks + { + className: 'quote', + begin: '^_{4,}\\n', + end: '\\n_{4,}$', + relevance: 10 + }, + // listing and literal blocks + { + className: 'code', + begin: '^[\\-\\.]{4,}\\n', + end: '\\n[\\-\\.]{4,}$', + relevance: 10 + }, + // passthrough blocks + { + begin: '^\\+{4,}\\n', + end: '\\n\\+{4,}$', + contains: [ + { + begin: '<', + end: '>', + subLanguage: 'xml', + relevance: 0 + } + ], + relevance: 10 + }, + + BULLET_LIST, + ADMONITION, + ...ESCAPED_FORMATTING, + ...STRONG, + ...EMPHASIS, + + // inline smart quotes + { + className: 'string', + variants: [ + { begin: "``.+?''" }, + { begin: "`.+?'" } + ] + }, + // inline unconstrained emphasis + { + className: 'code', + begin: /`{2}/, + end: /(\n{2}|`{2})/ + }, + // inline code snippets (TODO should get same treatment as strong and emphasis) + { + className: 'code', + begin: '(`.+?`|\\+.+?\\+)', + relevance: 0 + }, + // indented literal block + { + className: 'code', + begin: '^[ \\t]', + end: '$', + relevance: 0 + }, + HORIZONTAL_RULE, + // images and links + { + begin: '(link:)?(http|https|ftp|file|irc|image:?):\\S+?\\[[^[]*?\\]', + returnBegin: true, + contains: [ + { + begin: '(link|image:?):', + relevance: 0 + }, + { + className: 'link', + begin: '\\w', + end: '[^\\[]+', + relevance: 0 + }, + { + className: 'string', + begin: '\\[', + end: '\\]', + excludeBegin: true, + excludeEnd: true, + relevance: 0 + } + ], + relevance: 10 + } + ] + }; +} + +export { asciidoc as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/asciidoc.js.js b/frontend/node_modules/highlight.js/es/languages/asciidoc.js.js new file mode 100644 index 0000000..31079b0 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/asciidoc.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/asciidoc" instead of "highlight.js/lib/languages/asciidoc.js"' + ); + } + } + emitWarning(); + import lang from './asciidoc.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/aspectj.js b/frontend/node_modules/highlight.js/es/languages/aspectj.js new file mode 100644 index 0000000..24c946e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/aspectj.js @@ -0,0 +1,231 @@ +/* +Language: AspectJ +Author: Hakan Ozler +Website: https://www.eclipse.org/aspectj/ +Description: Syntax Highlighting for the AspectJ Language which is a general-purpose aspect-oriented extension to the Java programming language. +Category: system +Audit: 2020 +*/ + +/** @type LanguageFn */ +function aspectj(hljs) { + const regex = hljs.regex; + const KEYWORDS = [ + "false", + "synchronized", + "int", + "abstract", + "float", + "private", + "char", + "boolean", + "static", + "null", + "if", + "const", + "for", + "true", + "while", + "long", + "throw", + "strictfp", + "finally", + "protected", + "import", + "native", + "final", + "return", + "void", + "enum", + "else", + "extends", + "implements", + "break", + "transient", + "new", + "catch", + "instanceof", + "byte", + "super", + "volatile", + "case", + "assert", + "short", + "package", + "default", + "double", + "public", + "try", + "this", + "switch", + "continue", + "throws", + "privileged", + "aspectOf", + "adviceexecution", + "proceed", + "cflowbelow", + "cflow", + "initialization", + "preinitialization", + "staticinitialization", + "withincode", + "target", + "within", + "execution", + "getWithinTypeName", + "handler", + "thisJoinPoint", + "thisJoinPointStaticPart", + "thisEnclosingJoinPointStaticPart", + "declare", + "parents", + "warning", + "error", + "soft", + "precedence", + "thisAspectInstance" + ]; + const SHORTKEYS = [ + "get", + "set", + "args", + "call" + ]; + + return { + name: 'AspectJ', + keywords: KEYWORDS, + illegal: /<\/|#/, + contains: [ + hljs.COMMENT( + /\/\*\*/, + /\*\//, + { + relevance: 0, + contains: [ + { + // eat up @'s in emails to prevent them to be recognized as doctags + begin: /\w+@/, + relevance: 0 + }, + { + className: 'doctag', + begin: /@[A-Za-z]+/ + } + ] + } + ), + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + { + className: 'class', + beginKeywords: 'aspect', + end: /[{;=]/, + excludeEnd: true, + illegal: /[:;"\[\]]/, + contains: [ + { beginKeywords: 'extends implements pertypewithin perthis pertarget percflowbelow percflow issingleton' }, + hljs.UNDERSCORE_TITLE_MODE, + { + begin: /\([^\)]*/, + end: /[)]+/, + keywords: KEYWORDS.concat(SHORTKEYS), + excludeEnd: false + } + ] + }, + { + className: 'class', + beginKeywords: 'class interface', + end: /[{;=]/, + excludeEnd: true, + relevance: 0, + keywords: 'class interface', + illegal: /[:"\[\]]/, + contains: [ + { beginKeywords: 'extends implements' }, + hljs.UNDERSCORE_TITLE_MODE + ] + }, + { + // AspectJ Constructs + beginKeywords: 'pointcut after before around throwing returning', + end: /[)]/, + excludeEnd: false, + illegal: /["\[\]]/, + contains: [ + { + begin: regex.concat(hljs.UNDERSCORE_IDENT_RE, /\s*\(/), + returnBegin: true, + contains: [ hljs.UNDERSCORE_TITLE_MODE ] + } + ] + }, + { + begin: /[:]/, + returnBegin: true, + end: /[{;]/, + relevance: 0, + excludeEnd: false, + keywords: KEYWORDS, + illegal: /["\[\]]/, + contains: [ + { + begin: regex.concat(hljs.UNDERSCORE_IDENT_RE, /\s*\(/), + keywords: KEYWORDS.concat(SHORTKEYS), + relevance: 0 + }, + hljs.QUOTE_STRING_MODE + ] + }, + { + // this prevents 'new Name(...), or throw ...' from being recognized as a function definition + beginKeywords: 'new throw', + relevance: 0 + }, + { + // the function class is a bit different for AspectJ compared to the Java language + className: 'function', + begin: /\w+ +\w+(\.\w+)?\s*\([^\)]*\)\s*((throws)[\w\s,]+)?[\{;]/, + returnBegin: true, + end: /[{;=]/, + keywords: KEYWORDS, + excludeEnd: true, + contains: [ + { + begin: regex.concat(hljs.UNDERSCORE_IDENT_RE, /\s*\(/), + returnBegin: true, + relevance: 0, + contains: [ hljs.UNDERSCORE_TITLE_MODE ] + }, + { + className: 'params', + begin: /\(/, + end: /\)/, + relevance: 0, + keywords: KEYWORDS, + contains: [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.C_NUMBER_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + hljs.C_NUMBER_MODE, + { + // annotation is also used in this language + className: 'meta', + begin: /@[A-Za-z]+/ + } + ] + }; +} + +export { aspectj as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/aspectj.js.js b/frontend/node_modules/highlight.js/es/languages/aspectj.js.js new file mode 100644 index 0000000..9a0ab9a --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/aspectj.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/aspectj" instead of "highlight.js/lib/languages/aspectj.js"' + ); + } + } + emitWarning(); + import lang from './aspectj.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/autohotkey.js b/frontend/node_modules/highlight.js/es/languages/autohotkey.js new file mode 100644 index 0000000..24fbce4 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/autohotkey.js @@ -0,0 +1,75 @@ +/* +Language: AutoHotkey +Author: Seongwon Lee +Description: AutoHotkey language definition +Category: scripting +*/ + +/** @type LanguageFn */ +function autohotkey(hljs) { + const BACKTICK_ESCAPE = { begin: '`[\\s\\S]' }; + + return { + name: 'AutoHotkey', + case_insensitive: true, + aliases: [ 'ahk' ], + keywords: { + keyword: 'Break Continue Critical Exit ExitApp Gosub Goto New OnExit Pause return SetBatchLines SetTimer Suspend Thread Throw Until ahk_id ahk_class ahk_pid ahk_exe ahk_group', + literal: 'true false NOT AND OR', + built_in: 'ComSpec Clipboard ClipboardAll ErrorLevel' + }, + contains: [ + BACKTICK_ESCAPE, + hljs.inherit(hljs.QUOTE_STRING_MODE, { contains: [ BACKTICK_ESCAPE ] }), + hljs.COMMENT(';', '$', { relevance: 0 }), + hljs.C_BLOCK_COMMENT_MODE, + { + className: 'number', + begin: hljs.NUMBER_RE, + relevance: 0 + }, + { + // subst would be the most accurate however fails the point of + // highlighting. variable is comparably the most accurate that actually + // has some effect + className: 'variable', + begin: '%[a-zA-Z0-9#_$@]+%' + }, + { + className: 'built_in', + begin: '^\\s*\\w+\\s*(,|%)' + // I don't really know if this is totally relevant + }, + { + // symbol would be most accurate however is highlighted just like + // built_in and that makes up a lot of AutoHotkey code meaning that it + // would fail to highlight anything + className: 'title', + variants: [ + { begin: '^[^\\n";]+::(?!=)' }, + { + begin: '^[^\\n";]+:(?!=)', + // zero relevance as it catches a lot of things + // followed by a single ':' in many languages + relevance: 0 + } + ] + }, + { + className: 'meta', + begin: '^\\s*#\\w+', + end: '$', + relevance: 0 + }, + { + className: 'built_in', + begin: 'A_[a-zA-Z0-9]+' + }, + { + // consecutive commas, not for highlighting but just for relevance + begin: ',\\s*,' } + ] + }; +} + +export { autohotkey as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/autohotkey.js.js b/frontend/node_modules/highlight.js/es/languages/autohotkey.js.js new file mode 100644 index 0000000..7068b26 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/autohotkey.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/autohotkey" instead of "highlight.js/lib/languages/autohotkey.js"' + ); + } + } + emitWarning(); + import lang from './autohotkey.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/autoit.js b/frontend/node_modules/highlight.js/es/languages/autoit.js new file mode 100644 index 0000000..b13e686 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/autoit.js @@ -0,0 +1,178 @@ +/* +Language: AutoIt +Author: Manh Tuan +Description: AutoIt language definition +Category: scripting +*/ + +/** @type LanguageFn */ +function autoit(hljs) { + const KEYWORDS = 'ByRef Case Const ContinueCase ContinueLoop ' + + 'Dim Do Else ElseIf EndFunc EndIf EndSelect ' + + 'EndSwitch EndWith Enum Exit ExitLoop For Func ' + + 'Global If In Local Next ReDim Return Select Static ' + + 'Step Switch Then To Until Volatile WEnd While With'; + + const DIRECTIVES = [ + "EndRegion", + "forcedef", + "forceref", + "ignorefunc", + "include", + "include-once", + "NoTrayIcon", + "OnAutoItStartRegister", + "pragma", + "Region", + "RequireAdmin", + "Tidy_Off", + "Tidy_On", + "Tidy_Parameters" + ]; + + const LITERAL = 'True False And Null Not Or Default'; + + const BUILT_IN = + 'Abs ACos AdlibRegister AdlibUnRegister Asc AscW ASin Assign ATan AutoItSetOption AutoItWinGetTitle AutoItWinSetTitle Beep Binary BinaryLen BinaryMid BinaryToString BitAND BitNOT BitOR BitRotate BitShift BitXOR BlockInput Break Call CDTray Ceiling Chr ChrW ClipGet ClipPut ConsoleRead ConsoleWrite ConsoleWriteError ControlClick ControlCommand ControlDisable ControlEnable ControlFocus ControlGetFocus ControlGetHandle ControlGetPos ControlGetText ControlHide ControlListView ControlMove ControlSend ControlSetText ControlShow ControlTreeView Cos Dec DirCopy DirCreate DirGetSize DirMove DirRemove DllCall DllCallAddress DllCallbackFree DllCallbackGetPtr DllCallbackRegister DllClose DllOpen DllStructCreate DllStructGetData DllStructGetPtr DllStructGetSize DllStructSetData DriveGetDrive DriveGetFileSystem DriveGetLabel DriveGetSerial DriveGetType DriveMapAdd DriveMapDel DriveMapGet DriveSetLabel DriveSpaceFree DriveSpaceTotal DriveStatus EnvGet EnvSet EnvUpdate Eval Execute Exp FileChangeDir FileClose FileCopy FileCreateNTFSLink FileCreateShortcut FileDelete FileExists FileFindFirstFile FileFindNextFile FileFlush FileGetAttrib FileGetEncoding FileGetLongName FileGetPos FileGetShortcut FileGetShortName FileGetSize FileGetTime FileGetVersion FileInstall FileMove FileOpen FileOpenDialog FileRead FileReadLine FileReadToArray FileRecycle FileRecycleEmpty FileSaveDialog FileSelectFolder FileSetAttrib FileSetEnd FileSetPos FileSetTime FileWrite FileWriteLine Floor FtpSetProxy FuncName GUICreate GUICtrlCreateAvi GUICtrlCreateButton GUICtrlCreateCheckbox GUICtrlCreateCombo GUICtrlCreateContextMenu GUICtrlCreateDate GUICtrlCreateDummy GUICtrlCreateEdit GUICtrlCreateGraphic GUICtrlCreateGroup GUICtrlCreateIcon GUICtrlCreateInput GUICtrlCreateLabel GUICtrlCreateList GUICtrlCreateListView GUICtrlCreateListViewItem GUICtrlCreateMenu GUICtrlCreateMenuItem GUICtrlCreateMonthCal GUICtrlCreateObj GUICtrlCreatePic GUICtrlCreateProgress GUICtrlCreateRadio GUICtrlCreateSlider GUICtrlCreateTab GUICtrlCreateTabItem GUICtrlCreateTreeView GUICtrlCreateTreeViewItem GUICtrlCreateUpdown GUICtrlDelete GUICtrlGetHandle GUICtrlGetState GUICtrlRead GUICtrlRecvMsg GUICtrlRegisterListViewSort GUICtrlSendMsg GUICtrlSendToDummy GUICtrlSetBkColor GUICtrlSetColor GUICtrlSetCursor GUICtrlSetData GUICtrlSetDefBkColor GUICtrlSetDefColor GUICtrlSetFont GUICtrlSetGraphic GUICtrlSetImage GUICtrlSetLimit GUICtrlSetOnEvent GUICtrlSetPos GUICtrlSetResizing GUICtrlSetState GUICtrlSetStyle GUICtrlSetTip GUIDelete GUIGetCursorInfo GUIGetMsg GUIGetStyle GUIRegisterMsg GUISetAccelerators GUISetBkColor GUISetCoord GUISetCursor GUISetFont GUISetHelp GUISetIcon GUISetOnEvent GUISetState GUISetStyle GUIStartGroup GUISwitch Hex HotKeySet HttpSetProxy HttpSetUserAgent HWnd InetClose InetGet InetGetInfo InetGetSize InetRead IniDelete IniRead IniReadSection IniReadSectionNames IniRenameSection IniWrite IniWriteSection InputBox Int IsAdmin IsArray IsBinary IsBool IsDeclared IsDllStruct IsFloat IsFunc IsHWnd IsInt IsKeyword IsNumber IsObj IsPtr IsString Log MemGetStats Mod MouseClick MouseClickDrag MouseDown MouseGetCursor MouseGetPos MouseMove MouseUp MouseWheel MsgBox Number ObjCreate ObjCreateInterface ObjEvent ObjGet ObjName OnAutoItExitRegister OnAutoItExitUnRegister Ping PixelChecksum PixelGetColor PixelSearch ProcessClose ProcessExists ProcessGetStats ProcessList ProcessSetPriority ProcessWait ProcessWaitClose ProgressOff ProgressOn ProgressSet Ptr Random RegDelete RegEnumKey RegEnumVal RegRead RegWrite Round Run RunAs RunAsWait RunWait Send SendKeepActive SetError SetExtended ShellExecute ShellExecuteWait Shutdown Sin Sleep SoundPlay SoundSetWaveVolume SplashImageOn SplashOff SplashTextOn Sqrt SRandom StatusbarGetText StderrRead StdinWrite StdioClose StdoutRead String StringAddCR StringCompare StringFormat StringFromASCIIArray StringInStr StringIsAlNum StringIsAlpha StringIsASCII StringIsDigit StringIsFloat StringIsInt StringIsLower StringIsSpace StringIsUpper StringIsXDigit StringLeft StringLen StringLower StringMid StringRegExp StringRegExpReplace StringReplace StringReverse StringRight StringSplit StringStripCR StringStripWS StringToASCIIArray StringToBinary StringTrimLeft StringTrimRight StringUpper Tan TCPAccept TCPCloseSocket TCPConnect TCPListen TCPNameToIP TCPRecv TCPSend TCPShutdown, UDPShutdown TCPStartup, UDPStartup TimerDiff TimerInit ToolTip TrayCreateItem TrayCreateMenu TrayGetMsg TrayItemDelete TrayItemGetHandle TrayItemGetState TrayItemGetText TrayItemSetOnEvent TrayItemSetState TrayItemSetText TraySetClick TraySetIcon TraySetOnEvent TraySetPauseIcon TraySetState TraySetToolTip TrayTip UBound UDPBind UDPCloseSocket UDPOpen UDPRecv UDPSend VarGetType WinActivate WinActive WinClose WinExists WinFlash WinGetCaretPos WinGetClassList WinGetClientSize WinGetHandle WinGetPos WinGetProcess WinGetState WinGetText WinGetTitle WinKill WinList WinMenuSelectItem WinMinimizeAll WinMinimizeAllUndo WinMove WinSetOnTop WinSetState WinSetTitle WinSetTrans WinWait WinWaitActive WinWaitClose WinWaitNotActive'; + + const COMMENT = { variants: [ + hljs.COMMENT(';', '$', { relevance: 0 }), + hljs.COMMENT('#cs', '#ce'), + hljs.COMMENT('#comments-start', '#comments-end') + ] }; + + const VARIABLE = { begin: '\\$[A-z0-9_]+' }; + + const STRING = { + className: 'string', + variants: [ + { + begin: /"/, + end: /"/, + contains: [ + { + begin: /""/, + relevance: 0 + } + ] + }, + { + begin: /'/, + end: /'/, + contains: [ + { + begin: /''/, + relevance: 0 + } + ] + } + ] + }; + + const NUMBER = { variants: [ + hljs.BINARY_NUMBER_MODE, + hljs.C_NUMBER_MODE + ] }; + + const PREPROCESSOR = { + className: 'meta', + begin: '#', + end: '$', + keywords: { keyword: DIRECTIVES }, + contains: [ + { + begin: /\\\n/, + relevance: 0 + }, + { + beginKeywords: 'include', + keywords: { keyword: 'include' }, + end: '$', + contains: [ + STRING, + { + className: 'string', + variants: [ + { + begin: '<', + end: '>' + }, + { + begin: /"/, + end: /"/, + contains: [ + { + begin: /""/, + relevance: 0 + } + ] + }, + { + begin: /'/, + end: /'/, + contains: [ + { + begin: /''/, + relevance: 0 + } + ] + } + ] + } + ] + }, + STRING, + COMMENT + ] + }; + + const CONSTANT = { + className: 'symbol', + // begin: '@', + // end: '$', + // keywords: 'AppDataCommonDir AppDataDir AutoItExe AutoItPID AutoItVersion AutoItX64 COM_EventObj CommonFilesDir Compiled ComputerName ComSpec CPUArch CR CRLF DesktopCommonDir DesktopDepth DesktopDir DesktopHeight DesktopRefresh DesktopWidth DocumentsCommonDir error exitCode exitMethod extended FavoritesCommonDir FavoritesDir GUI_CtrlHandle GUI_CtrlId GUI_DragFile GUI_DragId GUI_DropId GUI_WinHandle HomeDrive HomePath HomeShare HotKeyPressed HOUR IPAddress1 IPAddress2 IPAddress3 IPAddress4 KBLayout LF LocalAppDataDir LogonDNSDomain LogonDomain LogonServer MDAY MIN MON MSEC MUILang MyDocumentsDir NumParams OSArch OSBuild OSLang OSServicePack OSType OSVersion ProgramFilesDir ProgramsCommonDir ProgramsDir ScriptDir ScriptFullPath ScriptLineNumber ScriptName SEC StartMenuCommonDir StartMenuDir StartupCommonDir StartupDir SW_DISABLE SW_ENABLE SW_HIDE SW_LOCK SW_MAXIMIZE SW_MINIMIZE SW_RESTORE SW_SHOW SW_SHOWDEFAULT SW_SHOWMAXIMIZED SW_SHOWMINIMIZED SW_SHOWMINNOACTIVE SW_SHOWNA SW_SHOWNOACTIVATE SW_SHOWNORMAL SW_UNLOCK SystemDir TAB TempDir TRAY_ID TrayIconFlashing TrayIconVisible UserName UserProfileDir WDAY WindowsDir WorkingDir YDAY YEAR', + // relevance: 5 + begin: '@[A-z0-9_]+' + }; + + const FUNCTION = { + beginKeywords: 'Func', + end: '$', + illegal: '\\$|\\[|%', + contains: [ + hljs.inherit(hljs.UNDERSCORE_TITLE_MODE, { className: "title.function" }), + { + className: 'params', + begin: '\\(', + end: '\\)', + contains: [ + VARIABLE, + STRING, + NUMBER + ] + } + ] + }; + + return { + name: 'AutoIt', + case_insensitive: true, + illegal: /\/\*/, + keywords: { + keyword: KEYWORDS, + built_in: BUILT_IN, + literal: LITERAL + }, + contains: [ + COMMENT, + VARIABLE, + STRING, + NUMBER, + PREPROCESSOR, + CONSTANT, + FUNCTION + ] + }; +} + +export { autoit as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/autoit.js.js b/frontend/node_modules/highlight.js/es/languages/autoit.js.js new file mode 100644 index 0000000..0218f2c --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/autoit.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/autoit" instead of "highlight.js/lib/languages/autoit.js"' + ); + } + } + emitWarning(); + import lang from './autoit.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/avrasm.js b/frontend/node_modules/highlight.js/es/languages/avrasm.js new file mode 100644 index 0000000..d3c490d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/avrasm.js @@ -0,0 +1,78 @@ +/* +Language: AVR Assembly +Author: Vladimir Ermakov +Category: assembler +Website: https://www.microchip.com/webdoc/avrassembler/avrassembler.wb_instruction_list.html +*/ + +/** @type LanguageFn */ +function avrasm(hljs) { + return { + name: 'AVR Assembly', + case_insensitive: true, + keywords: { + $pattern: '\\.?' + hljs.IDENT_RE, + keyword: + /* mnemonic */ + 'adc add adiw and andi asr bclr bld brbc brbs brcc brcs break breq brge brhc brhs ' + + 'brid brie brlo brlt brmi brne brpl brsh brtc brts brvc brvs bset bst call cbi cbr ' + + 'clc clh cli cln clr cls clt clv clz com cp cpc cpi cpse dec eicall eijmp elpm eor ' + + 'fmul fmuls fmulsu icall ijmp in inc jmp ld ldd ldi lds lpm lsl lsr mov movw mul ' + + 'muls mulsu neg nop or ori out pop push rcall ret reti rjmp rol ror sbc sbr sbrc sbrs ' + + 'sec seh sbi sbci sbic sbis sbiw sei sen ser ses set sev sez sleep spm st std sts sub ' + + 'subi swap tst wdr', + built_in: + /* general purpose registers */ + 'r0 r1 r2 r3 r4 r5 r6 r7 r8 r9 r10 r11 r12 r13 r14 r15 r16 r17 r18 r19 r20 r21 r22 ' + + 'r23 r24 r25 r26 r27 r28 r29 r30 r31 x|0 xh xl y|0 yh yl z|0 zh zl ' + /* IO Registers (ATMega128) */ + + 'ucsr1c udr1 ucsr1a ucsr1b ubrr1l ubrr1h ucsr0c ubrr0h tccr3c tccr3a tccr3b tcnt3h ' + + 'tcnt3l ocr3ah ocr3al ocr3bh ocr3bl ocr3ch ocr3cl icr3h icr3l etimsk etifr tccr1c ' + + 'ocr1ch ocr1cl twcr twdr twar twsr twbr osccal xmcra xmcrb eicra spmcsr spmcr portg ' + + 'ddrg ping portf ddrf sreg sph spl xdiv rampz eicrb eimsk gimsk gicr eifr gifr timsk ' + + 'tifr mcucr mcucsr tccr0 tcnt0 ocr0 assr tccr1a tccr1b tcnt1h tcnt1l ocr1ah ocr1al ' + + 'ocr1bh ocr1bl icr1h icr1l tccr2 tcnt2 ocr2 ocdr wdtcr sfior eearh eearl eedr eecr ' + + 'porta ddra pina portb ddrb pinb portc ddrc pinc portd ddrd pind spdr spsr spcr udr0 ' + + 'ucsr0a ucsr0b ubrr0l acsr admux adcsr adch adcl porte ddre pine pinf', + meta: + '.byte .cseg .db .def .device .dseg .dw .endmacro .equ .eseg .exit .include .list ' + + '.listmac .macro .nolist .org .set' + }, + contains: [ + hljs.C_BLOCK_COMMENT_MODE, + hljs.COMMENT( + ';', + '$', + { relevance: 0 } + ), + hljs.C_NUMBER_MODE, // 0x..., decimal, float + hljs.BINARY_NUMBER_MODE, // 0b... + { + className: 'number', + begin: '\\b(\\$[a-zA-Z0-9]+|0o[0-7]+)' // $..., 0o... + }, + hljs.QUOTE_STRING_MODE, + { + className: 'string', + begin: '\'', + end: '[^\\\\]\'', + illegal: '[^\\\\][^\']' + }, + { + className: 'symbol', + begin: '^[A-Za-z0-9_.$]+:' + }, + { + className: 'meta', + begin: '#', + end: '$' + }, + { // substitution within a macro + className: 'subst', + begin: '@[0-9]+' + } + ] + }; +} + +export { avrasm as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/avrasm.js.js b/frontend/node_modules/highlight.js/es/languages/avrasm.js.js new file mode 100644 index 0000000..938af11 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/avrasm.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/avrasm" instead of "highlight.js/lib/languages/avrasm.js"' + ); + } + } + emitWarning(); + import lang from './avrasm.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/awk.js b/frontend/node_modules/highlight.js/es/languages/awk.js new file mode 100644 index 0000000..2b74d39 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/awk.js @@ -0,0 +1,68 @@ +/* +Language: Awk +Author: Matthew Daly +Website: https://www.gnu.org/software/gawk/manual/gawk.html +Description: language definition for Awk scripts +Category: scripting +*/ + +/** @type LanguageFn */ +function awk(hljs) { + const VARIABLE = { + className: 'variable', + variants: [ + { begin: /\$[\w\d#@][\w\d_]*/ }, + { begin: /\$\{(.*?)\}/ } + ] + }; + const KEYWORDS = 'BEGIN END if else while do for in break continue delete next nextfile function func exit|10'; + const STRING = { + className: 'string', + contains: [ hljs.BACKSLASH_ESCAPE ], + variants: [ + { + begin: /(u|b)?r?'''/, + end: /'''/, + relevance: 10 + }, + { + begin: /(u|b)?r?"""/, + end: /"""/, + relevance: 10 + }, + { + begin: /(u|r|ur)'/, + end: /'/, + relevance: 10 + }, + { + begin: /(u|r|ur)"/, + end: /"/, + relevance: 10 + }, + { + begin: /(b|br)'/, + end: /'/ + }, + { + begin: /(b|br)"/, + end: /"/ + }, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE + ] + }; + return { + name: 'Awk', + keywords: { keyword: KEYWORDS }, + contains: [ + VARIABLE, + STRING, + hljs.REGEXP_MODE, + hljs.HASH_COMMENT_MODE, + hljs.NUMBER_MODE + ] + }; +} + +export { awk as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/awk.js.js b/frontend/node_modules/highlight.js/es/languages/awk.js.js new file mode 100644 index 0000000..5ae75bc --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/awk.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/awk" instead of "highlight.js/lib/languages/awk.js"' + ); + } + } + emitWarning(); + import lang from './awk.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/axapta.js b/frontend/node_modules/highlight.js/es/languages/axapta.js new file mode 100644 index 0000000..d840513 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/axapta.js @@ -0,0 +1,188 @@ +/* +Language: Microsoft X++ +Description: X++ is a language used in Microsoft Dynamics 365, Dynamics AX, and Axapta. +Author: Dmitri Roudakov +Website: https://dynamics.microsoft.com/en-us/ax-overview/ +Category: enterprise +*/ + +/** @type LanguageFn */ +function axapta(hljs) { + const IDENT_RE = hljs.UNDERSCORE_IDENT_RE; + const BUILT_IN_KEYWORDS = [ + 'anytype', + 'boolean', + 'byte', + 'char', + 'container', + 'date', + 'double', + 'enum', + 'guid', + 'int', + 'int64', + 'long', + 'real', + 'short', + 'str', + 'utcdatetime', + 'var' + ]; + + const LITERAL_KEYWORDS = [ + 'default', + 'false', + 'null', + 'true' + ]; + + const NORMAL_KEYWORDS = [ + 'abstract', + 'as', + 'asc', + 'avg', + 'break', + 'breakpoint', + 'by', + 'byref', + 'case', + 'catch', + 'changecompany', + 'class', + 'client', + 'client', + 'common', + 'const', + 'continue', + 'count', + 'crosscompany', + 'delegate', + 'delete_from', + 'desc', + 'display', + 'div', + 'do', + 'edit', + 'else', + 'eventhandler', + 'exists', + 'extends', + 'final', + 'finally', + 'firstfast', + 'firstonly', + 'firstonly1', + 'firstonly10', + 'firstonly100', + 'firstonly1000', + 'flush', + 'for', + 'forceliterals', + 'forcenestedloop', + 'forceplaceholders', + 'forceselectorder', + 'forupdate', + 'from', + 'generateonly', + 'group', + 'hint', + 'if', + 'implements', + 'in', + 'index', + 'insert_recordset', + 'interface', + 'internal', + 'is', + 'join', + 'like', + 'maxof', + 'minof', + 'mod', + 'namespace', + 'new', + 'next', + 'nofetch', + 'notexists', + 'optimisticlock', + 'order', + 'outer', + 'pessimisticlock', + 'print', + 'private', + 'protected', + 'public', + 'readonly', + 'repeatableread', + 'retry', + 'return', + 'reverse', + 'select', + 'server', + 'setting', + 'static', + 'sum', + 'super', + 'switch', + 'this', + 'throw', + 'try', + 'ttsabort', + 'ttsbegin', + 'ttscommit', + 'unchecked', + 'update_recordset', + 'using', + 'validtimestate', + 'void', + 'where', + 'while' + ]; + + const KEYWORDS = { + keyword: NORMAL_KEYWORDS, + built_in: BUILT_IN_KEYWORDS, + literal: LITERAL_KEYWORDS + }; + + const CLASS_DEFINITION = { + variants: [ + { match: [ + /(class|interface)\s+/, + IDENT_RE, + /\s+(extends|implements)\s+/, + IDENT_RE + ] }, + { match: [ + /class\s+/, + IDENT_RE + ] } + ], + scope: { + 2: "title.class", + 4: "title.class.inherited" + }, + keywords: KEYWORDS + }; + + return { + name: 'X++', + aliases: [ 'x++' ], + keywords: KEYWORDS, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.C_NUMBER_MODE, + { + className: 'meta', + begin: '#', + end: '$' + }, + CLASS_DEFINITION + ] + }; +} + +export { axapta as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/axapta.js.js b/frontend/node_modules/highlight.js/es/languages/axapta.js.js new file mode 100644 index 0000000..48a2d49 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/axapta.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/axapta" instead of "highlight.js/lib/languages/axapta.js"' + ); + } + } + emitWarning(); + import lang from './axapta.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/bash.js b/frontend/node_modules/highlight.js/es/languages/bash.js new file mode 100644 index 0000000..1fc226c --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/bash.js @@ -0,0 +1,409 @@ +/* +Language: Bash +Author: vah +Contributrors: Benjamin Pannell +Website: https://www.gnu.org/software/bash/ +Category: common, scripting +*/ + +/** @type LanguageFn */ +function bash(hljs) { + const regex = hljs.regex; + const VAR = {}; + const BRACED_VAR = { + begin: /\$\{/, + end: /\}/, + contains: [ + "self", + { + begin: /:-/, + contains: [ VAR ] + } // default values + ] + }; + Object.assign(VAR, { + className: 'variable', + variants: [ + { begin: regex.concat(/\$[\w\d#@][\w\d_]*/, + // negative look-ahead tries to avoid matching patterns that are not + // Perl at all like $ident$, @ident@, etc. + `(?![\\w\\d])(?![$])`) }, + BRACED_VAR + ] + }); + + const SUBST = { + className: 'subst', + begin: /\$\(/, + end: /\)/, + contains: [ hljs.BACKSLASH_ESCAPE ] + }; + const COMMENT = hljs.inherit( + hljs.COMMENT(), + { + match: [ + /(^|\s)/, + /#.*$/ + ], + scope: { + 2: 'comment' + } + } + ); + const HERE_DOC = { + begin: /<<-?\s*(?=\w+)/, + starts: { contains: [ + hljs.END_SAME_AS_BEGIN({ + begin: /(\w+)/, + end: /(\w+)/, + className: 'string' + }) + ] } + }; + const QUOTE_STRING = { + className: 'string', + begin: /"/, + end: /"/, + contains: [ + hljs.BACKSLASH_ESCAPE, + VAR, + SUBST + ] + }; + SUBST.contains.push(QUOTE_STRING); + const ESCAPED_QUOTE = { + match: /\\"/ + }; + const APOS_STRING = { + className: 'string', + begin: /'/, + end: /'/ + }; + const ESCAPED_APOS = { + match: /\\'/ + }; + const ARITHMETIC = { + begin: /\$?\(\(/, + end: /\)\)/, + contains: [ + { + begin: /\d+#[0-9a-f]+/, + className: "number" + }, + hljs.NUMBER_MODE, + VAR + ] + }; + const SH_LIKE_SHELLS = [ + "fish", + "bash", + "zsh", + "sh", + "csh", + "ksh", + "tcsh", + "dash", + "scsh", + ]; + const KNOWN_SHEBANG = hljs.SHEBANG({ + binary: `(${SH_LIKE_SHELLS.join("|")})`, + relevance: 10 + }); + const FUNCTION = { + className: 'function', + begin: /\w[\w\d_]*\s*\(\s*\)\s*\{/, + returnBegin: true, + contains: [ hljs.inherit(hljs.TITLE_MODE, { begin: /\w[\w\d_]*/ }) ], + relevance: 0 + }; + + const KEYWORDS = [ + "if", + "then", + "else", + "elif", + "fi", + "time", + "for", + "while", + "until", + "in", + "do", + "done", + "case", + "esac", + "coproc", + "function", + "select" + ]; + + const LITERALS = [ + "true", + "false" + ]; + + // to consume paths to prevent keyword matches inside them + const PATH_MODE = { match: /(\/[a-z._-]+)+/ }; + + // http://www.gnu.org/software/bash/manual/html_node/Shell-Builtin-Commands.html + const SHELL_BUILT_INS = [ + "break", + "cd", + "continue", + "eval", + "exec", + "exit", + "export", + "getopts", + "hash", + "pwd", + "readonly", + "return", + "shift", + "test", + "times", + "trap", + "umask", + "unset" + ]; + + const BASH_BUILT_INS = [ + "alias", + "bind", + "builtin", + "caller", + "command", + "declare", + "echo", + "enable", + "help", + "let", + "local", + "logout", + "mapfile", + "printf", + "read", + "readarray", + "source", + "sudo", + "type", + "typeset", + "ulimit", + "unalias" + ]; + + const ZSH_BUILT_INS = [ + "autoload", + "bg", + "bindkey", + "bye", + "cap", + "chdir", + "clone", + "comparguments", + "compcall", + "compctl", + "compdescribe", + "compfiles", + "compgroups", + "compquote", + "comptags", + "comptry", + "compvalues", + "dirs", + "disable", + "disown", + "echotc", + "echoti", + "emulate", + "fc", + "fg", + "float", + "functions", + "getcap", + "getln", + "history", + "integer", + "jobs", + "kill", + "limit", + "log", + "noglob", + "popd", + "print", + "pushd", + "pushln", + "rehash", + "sched", + "setcap", + "setopt", + "stat", + "suspend", + "ttyctl", + "unfunction", + "unhash", + "unlimit", + "unsetopt", + "vared", + "wait", + "whence", + "where", + "which", + "zcompile", + "zformat", + "zftp", + "zle", + "zmodload", + "zparseopts", + "zprof", + "zpty", + "zregexparse", + "zsocket", + "zstyle", + "ztcp" + ]; + + const GNU_CORE_UTILS = [ + "chcon", + "chgrp", + "chown", + "chmod", + "cp", + "dd", + "df", + "dir", + "dircolors", + "ln", + "ls", + "mkdir", + "mkfifo", + "mknod", + "mktemp", + "mv", + "realpath", + "rm", + "rmdir", + "shred", + "sync", + "touch", + "truncate", + "vdir", + "b2sum", + "base32", + "base64", + "cat", + "cksum", + "comm", + "csplit", + "cut", + "expand", + "fmt", + "fold", + "head", + "join", + "md5sum", + "nl", + "numfmt", + "od", + "paste", + "ptx", + "pr", + "sha1sum", + "sha224sum", + "sha256sum", + "sha384sum", + "sha512sum", + "shuf", + "sort", + "split", + "sum", + "tac", + "tail", + "tr", + "tsort", + "unexpand", + "uniq", + "wc", + "arch", + "basename", + "chroot", + "date", + "dirname", + "du", + "echo", + "env", + "expr", + "factor", + // "false", // keyword literal already + "groups", + "hostid", + "id", + "link", + "logname", + "nice", + "nohup", + "nproc", + "pathchk", + "pinky", + "printenv", + "printf", + "pwd", + "readlink", + "runcon", + "seq", + "sleep", + "stat", + "stdbuf", + "stty", + "tee", + "test", + "timeout", + // "true", // keyword literal already + "tty", + "uname", + "unlink", + "uptime", + "users", + "who", + "whoami", + "yes" + ]; + + return { + name: 'Bash', + aliases: [ + 'sh', + 'zsh' + ], + keywords: { + $pattern: /\b[a-z][a-z0-9._-]+\b/, + keyword: KEYWORDS, + literal: LITERALS, + built_in: [ + ...SHELL_BUILT_INS, + ...BASH_BUILT_INS, + // Shell modifiers + "set", + "shopt", + ...ZSH_BUILT_INS, + ...GNU_CORE_UTILS + ] + }, + contains: [ + KNOWN_SHEBANG, // to catch known shells and boost relevancy + hljs.SHEBANG(), // to catch unknown shells but still highlight the shebang + FUNCTION, + ARITHMETIC, + COMMENT, + HERE_DOC, + PATH_MODE, + QUOTE_STRING, + ESCAPED_QUOTE, + APOS_STRING, + ESCAPED_APOS, + VAR + ] + }; +} + +export { bash as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/bash.js.js b/frontend/node_modules/highlight.js/es/languages/bash.js.js new file mode 100644 index 0000000..7b90a59 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/bash.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/bash" instead of "highlight.js/lib/languages/bash.js"' + ); + } + } + emitWarning(); + import lang from './bash.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/basic.js b/frontend/node_modules/highlight.js/es/languages/basic.js new file mode 100644 index 0000000..1037071 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/basic.js @@ -0,0 +1,236 @@ +/* +Language: BASIC +Author: Raphaël Assénat +Description: Based on the BASIC reference from the Tandy 1000 guide +Website: https://en.wikipedia.org/wiki/Tandy_1000 +Category: system +*/ + +/** @type LanguageFn */ +function basic(hljs) { + const KEYWORDS = [ + "ABS", + "ASC", + "AND", + "ATN", + "AUTO|0", + "BEEP", + "BLOAD|10", + "BSAVE|10", + "CALL", + "CALLS", + "CDBL", + "CHAIN", + "CHDIR", + "CHR$|10", + "CINT", + "CIRCLE", + "CLEAR", + "CLOSE", + "CLS", + "COLOR", + "COM", + "COMMON", + "CONT", + "COS", + "CSNG", + "CSRLIN", + "CVD", + "CVI", + "CVS", + "DATA", + "DATE$", + "DEFDBL", + "DEFINT", + "DEFSNG", + "DEFSTR", + "DEF|0", + "SEG", + "USR", + "DELETE", + "DIM", + "DRAW", + "EDIT", + "END", + "ENVIRON", + "ENVIRON$", + "EOF", + "EQV", + "ERASE", + "ERDEV", + "ERDEV$", + "ERL", + "ERR", + "ERROR", + "EXP", + "FIELD", + "FILES", + "FIX", + "FOR|0", + "FRE", + "GET", + "GOSUB|10", + "GOTO", + "HEX$", + "IF", + "THEN", + "ELSE|0", + "INKEY$", + "INP", + "INPUT", + "INPUT#", + "INPUT$", + "INSTR", + "IMP", + "INT", + "IOCTL", + "IOCTL$", + "KEY", + "ON", + "OFF", + "LIST", + "KILL", + "LEFT$", + "LEN", + "LET", + "LINE", + "LLIST", + "LOAD", + "LOC", + "LOCATE", + "LOF", + "LOG", + "LPRINT", + "USING", + "LSET", + "MERGE", + "MID$", + "MKDIR", + "MKD$", + "MKI$", + "MKS$", + "MOD", + "NAME", + "NEW", + "NEXT", + "NOISE", + "NOT", + "OCT$", + "ON", + "OR", + "PEN", + "PLAY", + "STRIG", + "OPEN", + "OPTION", + "BASE", + "OUT", + "PAINT", + "PALETTE", + "PCOPY", + "PEEK", + "PMAP", + "POINT", + "POKE", + "POS", + "PRINT", + "PRINT]", + "PSET", + "PRESET", + "PUT", + "RANDOMIZE", + "READ", + "REM", + "RENUM", + "RESET|0", + "RESTORE", + "RESUME", + "RETURN|0", + "RIGHT$", + "RMDIR", + "RND", + "RSET", + "RUN", + "SAVE", + "SCREEN", + "SGN", + "SHELL", + "SIN", + "SOUND", + "SPACE$", + "SPC", + "SQR", + "STEP", + "STICK", + "STOP", + "STR$", + "STRING$", + "SWAP", + "SYSTEM", + "TAB", + "TAN", + "TIME$", + "TIMER", + "TROFF", + "TRON", + "TO", + "USR", + "VAL", + "VARPTR", + "VARPTR$", + "VIEW", + "WAIT", + "WHILE", + "WEND", + "WIDTH", + "WINDOW", + "WRITE", + "XOR" + ]; + + return { + name: 'BASIC', + case_insensitive: true, + illegal: '^\.', + // Support explicitly typed variables that end with $%! or #. + keywords: { + $pattern: '[a-zA-Z][a-zA-Z0-9_$%!#]*', + keyword: KEYWORDS + }, + contains: [ + { + // Match strings that start with " and end with " or a line break + scope: 'string', + begin: /"/, + end: /"|$/, + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + hljs.COMMENT('REM', '$', { relevance: 10 }), + hljs.COMMENT('\'', '$', { relevance: 0 }), + { + // Match line numbers + className: 'symbol', + begin: '^[0-9]+ ', + relevance: 10 + }, + { + // Match typed numeric constants (1000, 12.34!, 1.2e5, 1.5#, 1.2D2) + className: 'number', + begin: '\\b\\d+(\\.\\d+)?([edED]\\d+)?[#\!]?', + relevance: 0 + }, + { + // Match hexadecimal numbers (&Hxxxx) + className: 'number', + begin: '(&[hH][0-9a-fA-F]{1,4})' + }, + { + // Match octal numbers (&Oxxxxxx) + className: 'number', + begin: '(&[oO][0-7]{1,6})' + } + ] + }; +} + +export { basic as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/basic.js.js b/frontend/node_modules/highlight.js/es/languages/basic.js.js new file mode 100644 index 0000000..021da05 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/basic.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/basic" instead of "highlight.js/lib/languages/basic.js"' + ); + } + } + emitWarning(); + import lang from './basic.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/bnf.js b/frontend/node_modules/highlight.js/es/languages/bnf.js new file mode 100644 index 0000000..345d1cb --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/bnf.js @@ -0,0 +1,39 @@ +/* +Language: Backus–Naur Form +Website: https://en.wikipedia.org/wiki/Backus–Naur_form +Category: syntax +Author: Oleg Efimov +*/ + +/** @type LanguageFn */ +function bnf(hljs) { + return { + name: 'Backus–Naur Form', + contains: [ + // Attribute + { + className: 'attribute', + begin: // + }, + // Specific + { + begin: /::=/, + end: /$/, + contains: [ + { + begin: // + }, + // Common + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE + ] + } + ] + }; +} + +export { bnf as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/bnf.js.js b/frontend/node_modules/highlight.js/es/languages/bnf.js.js new file mode 100644 index 0000000..4ab9a08 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/bnf.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/bnf" instead of "highlight.js/lib/languages/bnf.js"' + ); + } + } + emitWarning(); + import lang from './bnf.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/brainfuck.js b/frontend/node_modules/highlight.js/es/languages/brainfuck.js new file mode 100644 index 0000000..02c2ae1 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/brainfuck.js @@ -0,0 +1,54 @@ +/* +Language: Brainfuck +Author: Evgeny Stepanischev +Website: https://esolangs.org/wiki/Brainfuck +*/ + +/** @type LanguageFn */ +function brainfuck(hljs) { + const LITERAL = { + className: 'literal', + begin: /[+-]+/, + relevance: 0 + }; + return { + name: 'Brainfuck', + aliases: [ 'bf' ], + contains: [ + hljs.COMMENT( + /[^\[\]\.,\+\-<> \r\n]/, + /[\[\]\.,\+\-<> \r\n]/, + { + contains: [ + { + match: /[ ]+[^\[\]\.,\+\-<> \r\n]/, + relevance: 0 + } + ], + returnEnd: true, + relevance: 0 + } + ), + { + className: 'title', + begin: '[\\[\\]]', + relevance: 0 + }, + { + className: 'string', + begin: '[\\.,]', + relevance: 0 + }, + { + // this mode works as the only relevance counter + // it looks ahead to find the start of a run of literals + // so only the runs are counted as relevant + begin: /(?=\+\+|--)/, + contains: [ LITERAL ] + }, + LITERAL + ] + }; +} + +export { brainfuck as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/brainfuck.js.js b/frontend/node_modules/highlight.js/es/languages/brainfuck.js.js new file mode 100644 index 0000000..0c3dee4 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/brainfuck.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/brainfuck" instead of "highlight.js/lib/languages/brainfuck.js"' + ); + } + } + emitWarning(); + import lang from './brainfuck.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/c.js b/frontend/node_modules/highlight.js/es/languages/c.js new file mode 100644 index 0000000..65bbd43 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/c.js @@ -0,0 +1,333 @@ +/* +Language: C +Category: common, system +Website: https://en.wikipedia.org/wiki/C_(programming_language) +*/ + +/** @type LanguageFn */ +function c(hljs) { + const regex = hljs.regex; + // added for historic reasons because `hljs.C_LINE_COMMENT_MODE` does + // not include such support nor can we be sure all the grammars depending + // on it would desire this behavior + const C_LINE_COMMENT_MODE = hljs.COMMENT('//', '$', { contains: [ { begin: /\\\n/ } ] }); + const DECLTYPE_AUTO_RE = 'decltype\\(auto\\)'; + const NAMESPACE_RE = '[a-zA-Z_]\\w*::'; + const TEMPLATE_ARGUMENT_RE = '<[^<>]+>'; + const FUNCTION_TYPE_RE = '(' + + DECLTYPE_AUTO_RE + '|' + + regex.optional(NAMESPACE_RE) + + '[a-zA-Z_]\\w*' + regex.optional(TEMPLATE_ARGUMENT_RE) + + ')'; + + + const TYPES = { + className: 'type', + variants: [ + { begin: '\\b[a-z\\d_]*_t\\b' }, + { match: /\batomic_[a-z]{3,6}\b/ } + ] + + }; + + // https://en.cppreference.com/w/cpp/language/escape + // \\ \x \xFF \u2837 \u00323747 \374 + const CHARACTER_ESCAPES = '\\\\(x[0-9A-Fa-f]{2}|u[0-9A-Fa-f]{4,8}|[0-7]{3}|\\S)'; + const STRINGS = { + className: 'string', + variants: [ + { + begin: '(u8?|U|L)?"', + end: '"', + illegal: '\\n', + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: '(u8?|U|L)?\'(' + CHARACTER_ESCAPES + "|.)", + end: '\'', + illegal: '.' + }, + hljs.END_SAME_AS_BEGIN({ + begin: /(?:u8?|U|L)?R"([^()\\ ]{0,16})\(/, + end: /\)([^()\\ ]{0,16})"/ + }) + ] + }; + + const NUMBERS = { + className: 'number', + variants: [ + { match: /\b(0b[01']+)/ }, + { match: /(-?)\b([\d']+(\.[\d']*)?|\.[\d']+)((ll|LL|l|L)(u|U)?|(u|U)(ll|LL|l|L)?|f|F|b|B)/ }, + { match: /(-?)\b(0[xX][a-fA-F0-9]+(?:'[a-fA-F0-9]+)*(?:\.[a-fA-F0-9]*(?:'[a-fA-F0-9]*)*)?(?:[pP][-+]?[0-9]+)?(l|L)?(u|U)?)/ }, + { match: /(-?)\b\d+(?:'\d+)*(?:\.\d*(?:'\d*)*)?(?:[eE][-+]?\d+)?/ } + ], + relevance: 0 + }; + + const PREPROCESSOR = { + className: 'meta', + begin: /#\s*[a-z]+\b/, + end: /$/, + keywords: { keyword: + 'if else elif endif define undef warning error line ' + + 'pragma _Pragma ifdef ifndef elifdef elifndef include' }, + contains: [ + { + begin: /\\\n/, + relevance: 0 + }, + hljs.inherit(STRINGS, { className: 'string' }), + { + className: 'string', + begin: /<.*?>/ + }, + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }; + + const TITLE_MODE = { + className: 'title', + begin: regex.optional(NAMESPACE_RE) + hljs.IDENT_RE, + relevance: 0 + }; + + const FUNCTION_TITLE = regex.optional(NAMESPACE_RE) + hljs.IDENT_RE + '\\s*\\('; + + const C_KEYWORDS = [ + "asm", + "auto", + "break", + "case", + "continue", + "default", + "do", + "else", + "enum", + "extern", + "for", + "fortran", + "goto", + "if", + "inline", + "register", + "restrict", + "return", + "sizeof", + "typeof", + "typeof_unqual", + "struct", + "switch", + "typedef", + "union", + "volatile", + "while", + "_Alignas", + "_Alignof", + "_Atomic", + "_Generic", + "_Noreturn", + "_Static_assert", + "_Thread_local", + // aliases + "alignas", + "alignof", + "noreturn", + "static_assert", + "thread_local", + // not a C keyword but is, for all intents and purposes, treated exactly like one. + "_Pragma" + ]; + + const C_TYPES = [ + "float", + "double", + "signed", + "unsigned", + "int", + "short", + "long", + "char", + "void", + "_Bool", + "_BitInt", + "_Complex", + "_Imaginary", + "_Decimal32", + "_Decimal64", + "_Decimal96", + "_Decimal128", + "_Decimal64x", + "_Decimal128x", + "_Float16", + "_Float32", + "_Float64", + "_Float128", + "_Float32x", + "_Float64x", + "_Float128x", + // modifiers + "const", + "static", + "constexpr", + // aliases + "complex", + "bool", + "imaginary" + ]; + + const KEYWORDS = { + keyword: C_KEYWORDS, + type: C_TYPES, + literal: 'true false NULL', + // TODO: apply hinting work similar to what was done in cpp.js + built_in: 'std string wstring cin cout cerr clog stdin stdout stderr stringstream istringstream ostringstream ' + + 'auto_ptr deque list queue stack vector map set pair bitset multiset multimap unordered_set ' + + 'unordered_map unordered_multiset unordered_multimap priority_queue make_pair array shared_ptr abort terminate abs acos ' + + 'asin atan2 atan calloc ceil cosh cos exit exp fabs floor fmod fprintf fputs free frexp ' + + 'fscanf future isalnum isalpha iscntrl isdigit isgraph islower isprint ispunct isspace isupper ' + + 'isxdigit tolower toupper labs ldexp log10 log malloc realloc memchr memcmp memcpy memset modf pow ' + + 'printf putchar puts scanf sinh sin snprintf sprintf sqrt sscanf strcat strchr strcmp ' + + 'strcpy strcspn strlen strncat strncmp strncpy strpbrk strrchr strspn strstr tanh tan ' + + 'vfprintf vprintf vsprintf endl initializer_list unique_ptr', + }; + + const EXPRESSION_CONTAINS = [ + PREPROCESSOR, + TYPES, + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + NUMBERS, + STRINGS + ]; + + const EXPRESSION_CONTEXT = { + // This mode covers expression context where we can't expect a function + // definition and shouldn't highlight anything that looks like one: + // `return some()`, `else if()`, `(x*sum(1, 2))` + variants: [ + { + begin: /=/, + end: /;/ + }, + { + begin: /\(/, + end: /\)/ + }, + { + beginKeywords: 'new throw return else', + end: /;/ + } + ], + keywords: KEYWORDS, + contains: EXPRESSION_CONTAINS.concat([ + { + begin: /\(/, + end: /\)/, + keywords: KEYWORDS, + contains: EXPRESSION_CONTAINS.concat([ 'self' ]), + relevance: 0 + } + ]), + relevance: 0 + }; + + const FUNCTION_DECLARATION = { + begin: '(' + FUNCTION_TYPE_RE + '[\\*&\\s]+)+' + FUNCTION_TITLE, + returnBegin: true, + end: /[{;=]/, + excludeEnd: true, + keywords: KEYWORDS, + illegal: /[^\w\s\*&:<>.]/, + contains: [ + { // to prevent it from being confused as the function title + begin: DECLTYPE_AUTO_RE, + keywords: KEYWORDS, + relevance: 0 + }, + { + begin: FUNCTION_TITLE, + returnBegin: true, + contains: [ hljs.inherit(TITLE_MODE, { className: "title.function" }) ], + relevance: 0 + }, + // allow for multiple declarations, e.g.: + // extern void f(int), g(char); + { + relevance: 0, + match: /,/ + }, + { + className: 'params', + begin: /\(/, + end: /\)/, + keywords: KEYWORDS, + relevance: 0, + contains: [ + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + STRINGS, + NUMBERS, + TYPES, + // Count matching parentheses. + { + begin: /\(/, + end: /\)/, + keywords: KEYWORDS, + relevance: 0, + contains: [ + 'self', + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + STRINGS, + NUMBERS, + TYPES + ] + } + ] + }, + TYPES, + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + PREPROCESSOR + ] + }; + + return { + name: "C", + aliases: [ 'h' ], + keywords: KEYWORDS, + // Until differentiations are added between `c` and `cpp`, `c` will + // not be auto-detected to avoid auto-detect conflicts between C and C++ + disableAutodetect: true, + illegal: '=]/, + contains: [ + { beginKeywords: "final class struct" }, + hljs.TITLE_MODE + ] + } + ]), + exports: { + preprocessor: PREPROCESSOR, + strings: STRINGS, + keywords: KEYWORDS + } + }; +} + +export { c as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/c.js.js b/frontend/node_modules/highlight.js/es/languages/c.js.js new file mode 100644 index 0000000..cd45a8d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/c.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/c" instead of "highlight.js/lib/languages/c.js"' + ); + } + } + emitWarning(); + import lang from './c.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/cal.js b/frontend/node_modules/highlight.js/es/languages/cal.js new file mode 100644 index 0000000..9ec55e8 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/cal.js @@ -0,0 +1,160 @@ +/* +Language: C/AL +Author: Kenneth Fuglsang Christensen +Description: Provides highlighting of Microsoft Dynamics NAV C/AL code files +Website: https://docs.microsoft.com/en-us/dynamics-nav/programming-in-c-al +Category: enterprise +*/ + +/** @type LanguageFn */ +function cal(hljs) { + const regex = hljs.regex; + const KEYWORDS = [ + "div", + "mod", + "in", + "and", + "or", + "not", + "xor", + "asserterror", + "begin", + "case", + "do", + "downto", + "else", + "end", + "exit", + "for", + "local", + "if", + "of", + "repeat", + "then", + "to", + "until", + "while", + "with", + "var" + ]; + const LITERALS = 'false true'; + const COMMENT_MODES = [ + hljs.C_LINE_COMMENT_MODE, + hljs.COMMENT( + /\{/, + /\}/, + { relevance: 0 } + ), + hljs.COMMENT( + /\(\*/, + /\*\)/, + { relevance: 10 } + ) + ]; + const STRING = { + className: 'string', + begin: /'/, + end: /'/, + contains: [ { begin: /''/ } ] + }; + const CHAR_STRING = { + className: 'string', + begin: /(#\d+)+/ + }; + const DATE = { + className: 'number', + begin: '\\b\\d+(\\.\\d+)?(DT|D|T)', + relevance: 0 + }; + const DBL_QUOTED_VARIABLE = { + className: 'string', // not a string technically but makes sense to be highlighted in the same style + begin: '"', + end: '"' + }; + + const PROCEDURE = { + match: [ + /procedure/, + /\s+/, + /[a-zA-Z_][\w@]*/, + /\s*/ + ], + scope: { + 1: "keyword", + 3: "title.function" + }, + contains: [ + { + className: 'params', + begin: /\(/, + end: /\)/, + keywords: KEYWORDS, + contains: [ + STRING, + CHAR_STRING, + hljs.NUMBER_MODE + ] + }, + ...COMMENT_MODES + ] + }; + + const OBJECT_TYPES = [ + "Table", + "Form", + "Report", + "Dataport", + "Codeunit", + "XMLport", + "MenuSuite", + "Page", + "Query" + ]; + const OBJECT = { + match: [ + /OBJECT/, + /\s+/, + regex.either(...OBJECT_TYPES), + /\s+/, + /\d+/, + /\s+(?=[^\s])/, + /.*/, + /$/ + ], + relevance: 3, + scope: { + 1: "keyword", + 3: "type", + 5: "number", + 7: "title" + } + }; + + const PROPERTY = { + match: /[\w]+(?=\=)/, + scope: "attribute", + relevance: 0 + }; + + return { + name: 'C/AL', + case_insensitive: true, + keywords: { + keyword: KEYWORDS, + literal: LITERALS + }, + illegal: /\/\*/, + contains: [ + PROPERTY, + STRING, + CHAR_STRING, + DATE, + DBL_QUOTED_VARIABLE, + hljs.NUMBER_MODE, + OBJECT, + PROCEDURE + ] + }; +} + +export { cal as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/cal.js.js b/frontend/node_modules/highlight.js/es/languages/cal.js.js new file mode 100644 index 0000000..396450f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/cal.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/cal" instead of "highlight.js/lib/languages/cal.js"' + ); + } + } + emitWarning(); + import lang from './cal.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/capnproto.js b/frontend/node_modules/highlight.js/es/languages/capnproto.js new file mode 100644 index 0000000..5560072 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/capnproto.js @@ -0,0 +1,99 @@ +/* +Language: Cap’n Proto +Author: Oleg Efimov +Description: Cap’n Proto message definition format +Website: https://capnproto.org/capnp-tool.html +Category: protocols +*/ + +/** @type LanguageFn */ +function capnproto(hljs) { + const KEYWORDS = [ + "struct", + "enum", + "interface", + "union", + "group", + "import", + "using", + "const", + "annotation", + "extends", + "in", + "of", + "on", + "as", + "with", + "from", + "fixed" + ]; + const TYPES = [ + "Void", + "Bool", + "Int8", + "Int16", + "Int32", + "Int64", + "UInt8", + "UInt16", + "UInt32", + "UInt64", + "Float32", + "Float64", + "Text", + "Data", + "AnyPointer", + "AnyStruct", + "Capability", + "List" + ]; + const LITERALS = [ + "true", + "false" + ]; + const CLASS_DEFINITION = { + variants: [ + { match: [ + /(struct|enum|interface)/, + /\s+/, + hljs.IDENT_RE + ] }, + { match: [ + /extends/, + /\s*\(/, + hljs.IDENT_RE, + /\s*\)/ + ] } + ], + scope: { + 1: "keyword", + 3: "title.class" + } + }; + return { + name: 'Cap’n Proto', + aliases: [ 'capnp' ], + keywords: { + keyword: KEYWORDS, + type: TYPES, + literal: LITERALS + }, + contains: [ + hljs.QUOTE_STRING_MODE, + hljs.NUMBER_MODE, + hljs.HASH_COMMENT_MODE, + { + className: 'meta', + begin: /@0x[\w\d]{16};/, + illegal: /\n/ + }, + { + className: 'symbol', + begin: /@\d+\b/ + }, + CLASS_DEFINITION + ] + }; +} + +export { capnproto as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/capnproto.js.js b/frontend/node_modules/highlight.js/es/languages/capnproto.js.js new file mode 100644 index 0000000..23a8a0e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/capnproto.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/capnproto" instead of "highlight.js/lib/languages/capnproto.js"' + ); + } + } + emitWarning(); + import lang from './capnproto.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/ceylon.js b/frontend/node_modules/highlight.js/es/languages/ceylon.js new file mode 100644 index 0000000..31cb17e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ceylon.js @@ -0,0 +1,140 @@ +/* +Language: Ceylon +Author: Lucas Werkmeister +Website: https://ceylon-lang.org +Category: system +*/ + +/** @type LanguageFn */ +function ceylon(hljs) { + // 2.3. Identifiers and keywords + const KEYWORDS = [ + "assembly", + "module", + "package", + "import", + "alias", + "class", + "interface", + "object", + "given", + "value", + "assign", + "void", + "function", + "new", + "of", + "extends", + "satisfies", + "abstracts", + "in", + "out", + "return", + "break", + "continue", + "throw", + "assert", + "dynamic", + "if", + "else", + "switch", + "case", + "for", + "while", + "try", + "catch", + "finally", + "then", + "let", + "this", + "outer", + "super", + "is", + "exists", + "nonempty" + ]; + // 7.4.1 Declaration Modifiers + const DECLARATION_MODIFIERS = [ + "shared", + "abstract", + "formal", + "default", + "actual", + "variable", + "late", + "native", + "deprecated", + "final", + "sealed", + "annotation", + "suppressWarnings", + "small" + ]; + // 7.4.2 Documentation + const DOCUMENTATION = [ + "doc", + "by", + "license", + "see", + "throws", + "tagged" + ]; + const SUBST = { + className: 'subst', + excludeBegin: true, + excludeEnd: true, + begin: /``/, + end: /``/, + keywords: KEYWORDS, + relevance: 10 + }; + const EXPRESSIONS = [ + { + // verbatim string + className: 'string', + begin: '"""', + end: '"""', + relevance: 10 + }, + { + // string literal or template + className: 'string', + begin: '"', + end: '"', + contains: [ SUBST ] + }, + { + // character literal + className: 'string', + begin: "'", + end: "'" + }, + { + // numeric literal + className: 'number', + begin: '#[0-9a-fA-F_]+|\\$[01_]+|[0-9_]+(?:\\.[0-9_](?:[eE][+-]?\\d+)?)?[kMGTPmunpf]?', + relevance: 0 + } + ]; + SUBST.contains = EXPRESSIONS; + + return { + name: 'Ceylon', + keywords: { + keyword: KEYWORDS.concat(DECLARATION_MODIFIERS), + meta: DOCUMENTATION + }, + illegal: '\\$[^01]|#[^0-9a-fA-F]', + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.COMMENT('/\\*', '\\*/', { contains: [ 'self' ] }), + { + // compiler annotation + className: 'meta', + begin: '@[a-z]\\w*(?::"[^"]*")?' + } + ].concat(EXPRESSIONS) + }; +} + +export { ceylon as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/ceylon.js.js b/frontend/node_modules/highlight.js/es/languages/ceylon.js.js new file mode 100644 index 0000000..11bf995 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ceylon.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/ceylon" instead of "highlight.js/lib/languages/ceylon.js"' + ); + } + } + emitWarning(); + import lang from './ceylon.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/clean.js b/frontend/node_modules/highlight.js/es/languages/clean.js new file mode 100644 index 0000000..05a477d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/clean.js @@ -0,0 +1,67 @@ +/* +Language: Clean +Author: Camil Staps +Category: functional +Website: http://clean.cs.ru.nl +*/ + +/** @type LanguageFn */ +function clean(hljs) { + const KEYWORDS = [ + "if", + "let", + "in", + "with", + "where", + "case", + "of", + "class", + "instance", + "otherwise", + "implementation", + "definition", + "system", + "module", + "from", + "import", + "qualified", + "as", + "special", + "code", + "inline", + "foreign", + "export", + "ccall", + "stdcall", + "generic", + "derive", + "infix", + "infixl", + "infixr" + ]; + return { + name: 'Clean', + aliases: [ + 'icl', + 'dcl' + ], + keywords: { + keyword: KEYWORDS, + built_in: + 'Int Real Char Bool', + literal: + 'True False' + }, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.C_NUMBER_MODE, + { // relevance booster + begin: '->|<-[|:]?|#!?|>>=|\\{\\||\\|\\}|:==|=:|<>' } + ] + }; +} + +export { clean as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/clean.js.js b/frontend/node_modules/highlight.js/es/languages/clean.js.js new file mode 100644 index 0000000..e399c06 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/clean.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/clean" instead of "highlight.js/lib/languages/clean.js"' + ); + } + } + emitWarning(); + import lang from './clean.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/clojure-repl.js b/frontend/node_modules/highlight.js/es/languages/clojure-repl.js new file mode 100644 index 0000000..5c45a17 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/clojure-repl.js @@ -0,0 +1,27 @@ +/* +Language: Clojure REPL +Description: Clojure REPL sessions +Author: Ivan Sagalaev +Requires: clojure.js +Website: https://clojure.org +Category: lisp +*/ + +/** @type LanguageFn */ +function clojureRepl(hljs) { + return { + name: 'Clojure REPL', + contains: [ + { + className: 'meta.prompt', + begin: /^([\w.-]+|\s*#_)?=>/, + starts: { + end: /$/, + subLanguage: 'clojure' + } + } + ] + }; +} + +export { clojureRepl as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/clojure-repl.js.js b/frontend/node_modules/highlight.js/es/languages/clojure-repl.js.js new file mode 100644 index 0000000..b910a65 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/clojure-repl.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/clojure-repl" instead of "highlight.js/lib/languages/clojure-repl.js"' + ); + } + } + emitWarning(); + import lang from './clojure-repl.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/clojure.js b/frontend/node_modules/highlight.js/es/languages/clojure.js new file mode 100644 index 0000000..5068a6b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/clojure.js @@ -0,0 +1,184 @@ +/* +Language: Clojure +Description: Clojure syntax (based on lisp.js) +Author: mfornos +Website: https://clojure.org +Category: lisp +*/ + +/** @type LanguageFn */ +function clojure(hljs) { + const SYMBOLSTART = 'a-zA-Z_\\-!.?+*=<>&\''; + const SYMBOL_RE = '[#]?[' + SYMBOLSTART + '][' + SYMBOLSTART + '0-9/;:$#]*'; + const globals = 'def defonce defprotocol defstruct defmulti defmethod defn- defn defmacro deftype defrecord'; + const keywords = { + $pattern: SYMBOL_RE, + built_in: + // Clojure keywords + globals + ' ' + + 'cond apply if-not if-let if not not= =|0 <|0 >|0 <=|0 >=|0 ==|0 +|0 /|0 *|0 -|0 rem ' + + 'quot neg? pos? delay? symbol? keyword? true? false? integer? empty? coll? list? ' + + 'set? ifn? fn? associative? sequential? sorted? counted? reversible? number? decimal? ' + + 'class? distinct? isa? float? rational? reduced? ratio? odd? even? char? seq? vector? ' + + 'string? map? nil? contains? zero? instance? not-every? not-any? libspec? -> ->> .. . ' + + 'inc compare do dotimes mapcat take remove take-while drop letfn drop-last take-last ' + + 'drop-while while intern condp case reduced cycle split-at split-with repeat replicate ' + + 'iterate range merge zipmap declare line-seq sort comparator sort-by dorun doall nthnext ' + + 'nthrest partition eval doseq await await-for let agent atom send send-off release-pending-sends ' + + 'add-watch mapv filterv remove-watch agent-error restart-agent set-error-handler error-handler ' + + 'set-error-mode! error-mode shutdown-agents quote var fn loop recur throw try monitor-enter ' + + 'monitor-exit macroexpand macroexpand-1 for dosync and or ' + + 'when when-not when-let comp juxt partial sequence memoize constantly complement identity assert ' + + 'peek pop doto proxy first rest cons cast coll last butlast ' + + 'sigs reify second ffirst fnext nfirst nnext meta with-meta ns in-ns create-ns import ' + + 'refer keys select-keys vals key val rseq name namespace promise into transient persistent! conj! ' + + 'assoc! dissoc! pop! disj! use class type num float double short byte boolean bigint biginteger ' + + 'bigdec print-method print-dup throw-if printf format load compile get-in update-in pr pr-on newline ' + + 'flush read slurp read-line subvec with-open memfn time re-find re-groups rand-int rand mod locking ' + + 'assert-valid-fdecl alias resolve ref deref refset swap! reset! set-validator! compare-and-set! alter-meta! ' + + 'reset-meta! commute get-validator alter ref-set ref-history-count ref-min-history ref-max-history ensure sync io! ' + + 'new next conj set! to-array future future-call into-array aset gen-class reduce map filter find empty ' + + 'hash-map hash-set sorted-map sorted-map-by sorted-set sorted-set-by vec vector seq flatten reverse assoc dissoc list ' + + 'disj get union difference intersection extend extend-type extend-protocol int nth delay count concat chunk chunk-buffer ' + + 'chunk-append chunk-first chunk-rest max min dec unchecked-inc-int unchecked-inc unchecked-dec-inc unchecked-dec unchecked-negate ' + + 'unchecked-add-int unchecked-add unchecked-subtract-int unchecked-subtract chunk-next chunk-cons chunked-seq? prn vary-meta ' + + 'lazy-seq spread list* str find-keyword keyword symbol gensym force rationalize' + }; + + const SYMBOL = { + begin: SYMBOL_RE, + relevance: 0 + }; + const NUMBER = { + scope: 'number', + relevance: 0, + variants: [ + { match: /[-+]?0[xX][0-9a-fA-F]+N?/ }, // hexadecimal // 0x2a + { match: /[-+]?0[0-7]+N?/ }, // octal // 052 + { match: /[-+]?[1-9][0-9]?[rR][0-9a-zA-Z]+N?/ }, // variable radix from 2 to 36 // 2r101010, 8r52, 36r16 + { match: /[-+]?[0-9]+\/[0-9]+N?/ }, // ratio // 1/2 + { match: /[-+]?[0-9]+((\.[0-9]*([eE][+-]?[0-9]+)?M?)|([eE][+-]?[0-9]+M?|M))/ }, // float // 0.42 4.2E-1M 42E1 42M + { match: /[-+]?([1-9][0-9]*|0)N?/ }, // int (don't match leading 0) // 42 42N + ] + }; + const CHARACTER = { + scope: 'character', + variants: [ + { match: /\\o[0-3]?[0-7]{1,2}/ }, // Unicode Octal 0 - 377 + { match: /\\u[0-9a-fA-F]{4}/ }, // Unicode Hex 0000 - FFFF + { match: /\\(newline|space|tab|formfeed|backspace|return)/ }, // special characters + { + match: /\\\S/, + relevance: 0 + } // any non-whitespace char + ] + }; + const REGEX = { + scope: 'regex', + begin: /#"/, + end: /"/, + contains: [ hljs.BACKSLASH_ESCAPE ] + }; + const STRING = hljs.inherit(hljs.QUOTE_STRING_MODE, { illegal: null }); + const COMMA = { + scope: 'punctuation', + match: /,/, + relevance: 0 + }; + const COMMENT = hljs.COMMENT( + ';', + '$', + { relevance: 0 } + ); + const LITERAL = { + className: 'literal', + begin: /\b(true|false|nil)\b/ + }; + const COLLECTION = { + begin: "\\[|(#::?" + SYMBOL_RE + ")?\\{", + end: '[\\]\\}]', + relevance: 0 + }; + const KEY = { + className: 'symbol', + begin: '[:]{1,2}' + SYMBOL_RE + }; + const LIST = { + begin: '\\(', + end: '\\)' + }; + const BODY = { + endsWithParent: true, + relevance: 0 + }; + const NAME = { + keywords: keywords, + className: 'name', + begin: SYMBOL_RE, + relevance: 0, + starts: BODY + }; + const DEFAULT_CONTAINS = [ + COMMA, + LIST, + CHARACTER, + REGEX, + STRING, + COMMENT, + KEY, + COLLECTION, + NUMBER, + LITERAL, + SYMBOL + ]; + + const GLOBAL = { + beginKeywords: globals, + keywords: { + $pattern: SYMBOL_RE, + keyword: globals + }, + end: '(\\[|#|\\d|"|:|\\{|\\)|\\(|$)', + contains: [ + { + className: 'title', + begin: SYMBOL_RE, + relevance: 0, + excludeEnd: true, + // we can only have a single title + endsParent: true + } + ].concat(DEFAULT_CONTAINS) + }; + + LIST.contains = [ + GLOBAL, + NAME, + BODY + ]; + BODY.contains = DEFAULT_CONTAINS; + COLLECTION.contains = DEFAULT_CONTAINS; + + return { + name: 'Clojure', + aliases: [ + 'clj', + 'edn' + ], + illegal: /\S/, + contains: [ + COMMA, + LIST, + CHARACTER, + REGEX, + STRING, + COMMENT, + KEY, + COLLECTION, + NUMBER, + LITERAL + ] + }; +} + +export { clojure as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/clojure.js.js b/frontend/node_modules/highlight.js/es/languages/clojure.js.js new file mode 100644 index 0000000..f5230a3 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/clojure.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/clojure" instead of "highlight.js/lib/languages/clojure.js"' + ); + } + } + emitWarning(); + import lang from './clojure.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/cmake.js b/frontend/node_modules/highlight.js/es/languages/cmake.js new file mode 100644 index 0000000..8efa659 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/cmake.js @@ -0,0 +1,64 @@ +/* +Language: CMake +Description: CMake is an open-source cross-platform system for build automation. +Author: Igor Kalnitsky +Website: https://cmake.org +Category: build-system +*/ + +/** @type LanguageFn */ +function cmake(hljs) { + return { + name: 'CMake', + aliases: [ 'cmake.in' ], + case_insensitive: true, + keywords: { keyword: + // scripting commands + 'break cmake_host_system_information cmake_minimum_required cmake_parse_arguments ' + + 'cmake_policy configure_file continue elseif else endforeach endfunction endif endmacro ' + + 'endwhile execute_process file find_file find_library find_package find_path ' + + 'find_program foreach function get_cmake_property get_directory_property ' + + 'get_filename_component get_property if include include_guard list macro ' + + 'mark_as_advanced math message option return separate_arguments ' + + 'set_directory_properties set_property set site_name string unset variable_watch while ' + // project commands + + 'add_compile_definitions add_compile_options add_custom_command add_custom_target ' + + 'add_definitions add_dependencies add_executable add_library add_link_options ' + + 'add_subdirectory add_test aux_source_directory build_command create_test_sourcelist ' + + 'define_property enable_language enable_testing export fltk_wrap_ui ' + + 'get_source_file_property get_target_property get_test_property include_directories ' + + 'include_external_msproject include_regular_expression install link_directories ' + + 'link_libraries load_cache project qt_wrap_cpp qt_wrap_ui remove_definitions ' + + 'set_source_files_properties set_target_properties set_tests_properties source_group ' + + 'target_compile_definitions target_compile_features target_compile_options ' + + 'target_include_directories target_link_directories target_link_libraries ' + + 'target_link_options target_sources try_compile try_run ' + // CTest commands + + 'ctest_build ctest_configure ctest_coverage ctest_empty_binary_directory ctest_memcheck ' + + 'ctest_read_custom_files ctest_run_script ctest_sleep ctest_start ctest_submit ' + + 'ctest_test ctest_update ctest_upload ' + // deprecated commands + + 'build_name exec_program export_library_dependencies install_files install_programs ' + + 'install_targets load_command make_directory output_required_files remove ' + + 'subdir_depends subdirs use_mangled_mesa utility_source variable_requires write_file ' + + 'qt5_use_modules qt5_use_package qt5_wrap_cpp ' + // core keywords + + 'on off true false and or not command policy target test exists is_newer_than ' + + 'is_directory is_symlink is_absolute matches less greater equal less_equal ' + + 'greater_equal strless strgreater strequal strless_equal strgreater_equal version_less ' + + 'version_greater version_equal version_less_equal version_greater_equal in_list defined' }, + contains: [ + { + className: 'variable', + begin: /\$\{/, + end: /\}/ + }, + hljs.COMMENT(/#\[\[/, /]]/), + hljs.HASH_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + hljs.NUMBER_MODE + ] + }; +} + +export { cmake as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/cmake.js.js b/frontend/node_modules/highlight.js/es/languages/cmake.js.js new file mode 100644 index 0000000..829fced --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/cmake.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/cmake" instead of "highlight.js/lib/languages/cmake.js"' + ); + } + } + emitWarning(); + import lang from './cmake.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/coffeescript.js b/frontend/node_modules/highlight.js/es/languages/coffeescript.js new file mode 100644 index 0000000..35d4f91 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/coffeescript.js @@ -0,0 +1,368 @@ +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", + // It's reached stage 3, which is "recommended for implementation": + "using" +]; +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_INS = [].concat( + BUILT_IN_GLOBALS, + TYPES, + ERROR_TYPES +); + +/* +Language: CoffeeScript +Author: Dmytrii Nagirniak +Contributors: Oleg Efimov , Cédric Néhémie +Description: CoffeeScript is a programming language that transcompiles to JavaScript. For info about language see http://coffeescript.org/ +Category: scripting +Website: https://coffeescript.org +*/ + + +/** @type LanguageFn */ +function coffeescript(hljs) { + const COFFEE_BUILT_INS = [ + 'npm', + 'print' + ]; + const COFFEE_LITERALS = [ + 'yes', + 'no', + 'on', + 'off' + ]; + const COFFEE_KEYWORDS = [ + 'then', + 'unless', + 'until', + 'loop', + 'by', + 'when', + 'and', + 'or', + 'is', + 'isnt', + 'not' + ]; + const NOT_VALID_KEYWORDS = [ + "var", + "const", + "let", + "function", + "static" + ]; + const excluding = (list) => + (kw) => !list.includes(kw); + const KEYWORDS$1 = { + keyword: KEYWORDS.concat(COFFEE_KEYWORDS).filter(excluding(NOT_VALID_KEYWORDS)), + literal: LITERALS.concat(COFFEE_LITERALS), + built_in: BUILT_INS.concat(COFFEE_BUILT_INS) + }; + const JS_IDENT_RE = '[A-Za-z$_][0-9A-Za-z$_]*'; + const SUBST = { + className: 'subst', + begin: /#\{/, + end: /\}/, + keywords: KEYWORDS$1 + }; + const EXPRESSIONS = [ + hljs.BINARY_NUMBER_MODE, + hljs.inherit(hljs.C_NUMBER_MODE, { starts: { + end: '(\\s*/)?', + relevance: 0 + } }), // a number tries to eat the following slash to prevent treating it as a regexp + { + className: 'string', + variants: [ + { + begin: /'''/, + end: /'''/, + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: /'/, + end: /'/, + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: /"""/, + end: /"""/, + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST + ] + }, + { + begin: /"/, + end: /"/, + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST + ] + } + ] + }, + { + className: 'regexp', + variants: [ + { + begin: '///', + end: '///', + contains: [ + SUBST, + hljs.HASH_COMMENT_MODE + ] + }, + { + begin: '//[gim]{0,3}(?=\\W)', + relevance: 0 + }, + { + // regex can't start with space to parse x / 2 / 3 as two divisions + // regex can't start with *, and it supports an "illegal" in the main mode + begin: /\/(?![ *]).*?(?![\\]).\/[gim]{0,3}(?=\W)/ } + ] + }, + { begin: '@' + JS_IDENT_RE // relevance booster + }, + { + subLanguage: 'javascript', + excludeBegin: true, + excludeEnd: true, + variants: [ + { + begin: '```', + end: '```' + }, + { + begin: '`', + end: '`' + } + ] + } + ]; + SUBST.contains = EXPRESSIONS; + + const TITLE = hljs.inherit(hljs.TITLE_MODE, { begin: JS_IDENT_RE }); + const POSSIBLE_PARAMS_RE = '(\\(.*\\)\\s*)?\\B[-=]>'; + const PARAMS = { + className: 'params', + begin: '\\([^\\(]', + returnBegin: true, + /* We need another contained nameless mode to not have every nested + pair of parens to be called "params" */ + contains: [ + { + begin: /\(/, + end: /\)/, + keywords: KEYWORDS$1, + contains: [ 'self' ].concat(EXPRESSIONS) + } + ] + }; + + const CLASS_DEFINITION = { + variants: [ + { match: [ + /class\s+/, + JS_IDENT_RE, + /\s+extends\s+/, + JS_IDENT_RE + ] }, + { match: [ + /class\s+/, + JS_IDENT_RE + ] } + ], + scope: { + 2: "title.class", + 4: "title.class.inherited" + }, + keywords: KEYWORDS$1 + }; + + return { + name: 'CoffeeScript', + aliases: [ + 'coffee', + 'cson', + 'iced' + ], + keywords: KEYWORDS$1, + illegal: /\/\*/, + contains: [ + ...EXPRESSIONS, + hljs.COMMENT('###', '###'), + hljs.HASH_COMMENT_MODE, + { + className: 'function', + begin: '^\\s*' + JS_IDENT_RE + '\\s*=\\s*' + POSSIBLE_PARAMS_RE, + end: '[-=]>', + returnBegin: true, + contains: [ + TITLE, + PARAMS + ] + }, + { + // anonymous function start + begin: /[:\(,=]\s*/, + relevance: 0, + contains: [ + { + className: 'function', + begin: POSSIBLE_PARAMS_RE, + end: '[-=]>', + returnBegin: true, + contains: [ PARAMS ] + } + ] + }, + CLASS_DEFINITION, + { + begin: JS_IDENT_RE + ':', + end: ':', + returnBegin: true, + returnEnd: true, + relevance: 0 + } + ] + }; +} + +export { coffeescript as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/coffeescript.js.js b/frontend/node_modules/highlight.js/es/languages/coffeescript.js.js new file mode 100644 index 0000000..2611a7f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/coffeescript.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/coffeescript" instead of "highlight.js/lib/languages/coffeescript.js"' + ); + } + } + emitWarning(); + import lang from './coffeescript.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/coq.js b/frontend/node_modules/highlight.js/es/languages/coq.js new file mode 100644 index 0000000..0c965d2 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/coq.js @@ -0,0 +1,445 @@ +/* +Language: Coq +Author: Stephan Boyer +Category: functional +Website: https://coq.inria.fr +*/ + +/** @type LanguageFn */ +function coq(hljs) { + const KEYWORDS = [ + "_|0", + "as", + "at", + "cofix", + "else", + "end", + "exists", + "exists2", + "fix", + "for", + "forall", + "fun", + "if", + "IF", + "in", + "let", + "match", + "mod", + "Prop", + "return", + "Set", + "then", + "Type", + "using", + "where", + "with", + "Abort", + "About", + "Add", + "Admit", + "Admitted", + "All", + "Arguments", + "Assumptions", + "Axiom", + "Back", + "BackTo", + "Backtrack", + "Bind", + "Blacklist", + "Canonical", + "Cd", + "Check", + "Class", + "Classes", + "Close", + "Coercion", + "Coercions", + "CoFixpoint", + "CoInductive", + "Collection", + "Combined", + "Compute", + "Conjecture", + "Conjectures", + "Constant", + "constr", + "Constraint", + "Constructors", + "Context", + "Corollary", + "CreateHintDb", + "Cut", + "Declare", + "Defined", + "Definition", + "Delimit", + "Dependencies", + "Dependent", + "Derive", + "Drop", + "eauto", + "End", + "Equality", + "Eval", + "Example", + "Existential", + "Existentials", + "Existing", + "Export", + "exporting", + "Extern", + "Extract", + "Extraction", + "Fact", + "Field", + "Fields", + "File", + "Fixpoint", + "Focus", + "for", + "From", + "Function", + "Functional", + "Generalizable", + "Global", + "Goal", + "Grab", + "Grammar", + "Graph", + "Guarded", + "Heap", + "Hint", + "HintDb", + "Hints", + "Hypotheses", + "Hypothesis", + "ident", + "Identity", + "If", + "Immediate", + "Implicit", + "Import", + "Include", + "Inductive", + "Infix", + "Info", + "Initial", + "Inline", + "Inspect", + "Instance", + "Instances", + "Intro", + "Intros", + "Inversion", + "Inversion_clear", + "Language", + "Left", + "Lemma", + "Let", + "Libraries", + "Library", + "Load", + "LoadPath", + "Local", + "Locate", + "Ltac", + "ML", + "Mode", + "Module", + "Modules", + "Monomorphic", + "Morphism", + "Next", + "NoInline", + "Notation", + "Obligation", + "Obligations", + "Opaque", + "Open", + "Optimize", + "Options", + "Parameter", + "Parameters", + "Parametric", + "Path", + "Paths", + "pattern", + "Polymorphic", + "Preterm", + "Print", + "Printing", + "Program", + "Projections", + "Proof", + "Proposition", + "Pwd", + "Qed", + "Quit", + "Rec", + "Record", + "Recursive", + "Redirect", + "Relation", + "Remark", + "Remove", + "Require", + "Reserved", + "Reset", + "Resolve", + "Restart", + "Rewrite", + "Right", + "Ring", + "Rings", + "Save", + "Scheme", + "Scope", + "Scopes", + "Script", + "Search", + "SearchAbout", + "SearchHead", + "SearchPattern", + "SearchRewrite", + "Section", + "Separate", + "Set", + "Setoid", + "Show", + "Solve", + "Sorted", + "Step", + "Strategies", + "Strategy", + "Structure", + "SubClass", + "Table", + "Tables", + "Tactic", + "Term", + "Test", + "Theorem", + "Time", + "Timeout", + "Transparent", + "Type", + "Typeclasses", + "Types", + "Undelimit", + "Undo", + "Unfocus", + "Unfocused", + "Unfold", + "Universe", + "Universes", + "Unset", + "Unshelve", + "using", + "Variable", + "Variables", + "Variant", + "Verbose", + "Visibility", + "where", + "with" + ]; + const BUILT_INS = [ + "abstract", + "absurd", + "admit", + "after", + "apply", + "as", + "assert", + "assumption", + "at", + "auto", + "autorewrite", + "autounfold", + "before", + "bottom", + "btauto", + "by", + "case", + "case_eq", + "cbn", + "cbv", + "change", + "classical_left", + "classical_right", + "clear", + "clearbody", + "cofix", + "compare", + "compute", + "congruence", + "constr_eq", + "constructor", + "contradict", + "contradiction", + "cut", + "cutrewrite", + "cycle", + "decide", + "decompose", + "dependent", + "destruct", + "destruction", + "dintuition", + "discriminate", + "discrR", + "do", + "double", + "dtauto", + "eapply", + "eassumption", + "eauto", + "ecase", + "econstructor", + "edestruct", + "ediscriminate", + "eelim", + "eexact", + "eexists", + "einduction", + "einjection", + "eleft", + "elim", + "elimtype", + "enough", + "equality", + "erewrite", + "eright", + "esimplify_eq", + "esplit", + "evar", + "exact", + "exactly_once", + "exfalso", + "exists", + "f_equal", + "fail", + "field", + "field_simplify", + "field_simplify_eq", + "first", + "firstorder", + "fix", + "fold", + "fourier", + "functional", + "generalize", + "generalizing", + "gfail", + "give_up", + "has_evar", + "hnf", + "idtac", + "in", + "induction", + "injection", + "instantiate", + "intro", + "intro_pattern", + "intros", + "intuition", + "inversion", + "inversion_clear", + "is_evar", + "is_var", + "lapply", + "lazy", + "left", + "lia", + "lra", + "move", + "native_compute", + "nia", + "nsatz", + "omega", + "once", + "pattern", + "pose", + "progress", + "proof", + "psatz", + "quote", + "record", + "red", + "refine", + "reflexivity", + "remember", + "rename", + "repeat", + "replace", + "revert", + "revgoals", + "rewrite", + "rewrite_strat", + "right", + "ring", + "ring_simplify", + "rtauto", + "set", + "setoid_reflexivity", + "setoid_replace", + "setoid_rewrite", + "setoid_symmetry", + "setoid_transitivity", + "shelve", + "shelve_unifiable", + "simpl", + "simple", + "simplify_eq", + "solve", + "specialize", + "split", + "split_Rabs", + "split_Rmult", + "stepl", + "stepr", + "subst", + "sum", + "swap", + "symmetry", + "tactic", + "tauto", + "time", + "timeout", + "top", + "transitivity", + "trivial", + "try", + "tryif", + "unfold", + "unify", + "until", + "using", + "vm_compute", + "with" + ]; + return { + name: 'Coq', + keywords: { + keyword: KEYWORDS, + built_in: BUILT_INS + }, + contains: [ + hljs.QUOTE_STRING_MODE, + hljs.COMMENT('\\(\\*', '\\*\\)'), + hljs.C_NUMBER_MODE, + { + className: 'type', + excludeBegin: true, + begin: '\\|\\s*', + end: '\\w+' + }, + { // relevance booster + begin: /[-=]>/ } + ] + }; +} + +export { coq as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/coq.js.js b/frontend/node_modules/highlight.js/es/languages/coq.js.js new file mode 100644 index 0000000..d235005 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/coq.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/coq" instead of "highlight.js/lib/languages/coq.js"' + ); + } + } + emitWarning(); + import lang from './coq.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/cos.js b/frontend/node_modules/highlight.js/es/languages/cos.js new file mode 100644 index 0000000..ac17ee2 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/cos.js @@ -0,0 +1,140 @@ +/* +Language: Caché Object Script +Author: Nikita Savchenko +Category: enterprise, scripting +Website: https://cedocs.intersystems.com/latest/csp/docbook/DocBook.UI.Page.cls +*/ + +/** @type LanguageFn */ +function cos(hljs) { + const STRINGS = { + className: 'string', + variants: [ + { + begin: '"', + end: '"', + contains: [ + { // escaped + begin: "\"\"", + relevance: 0 + } + ] + } + ] + }; + + const NUMBERS = { + className: "number", + begin: "\\b(\\d+(\\.\\d*)?|\\.\\d+)", + relevance: 0 + }; + + const COS_KEYWORDS = + 'property parameter class classmethod clientmethod extends as break ' + + 'catch close continue do d|0 else elseif for goto halt hang h|0 if job ' + + 'j|0 kill k|0 lock l|0 merge new open quit q|0 read r|0 return set s|0 ' + + 'tcommit throw trollback try tstart use view while write w|0 xecute x|0 ' + + 'zkill znspace zn ztrap zwrite zw zzdump zzwrite print zbreak zinsert ' + + 'zload zprint zremove zsave zzprint mv mvcall mvcrt mvdim mvprint zquit ' + + 'zsync ascii'; + + // registered function - no need in them due to all functions are highlighted, + // but I'll just leave this here. + + // "$bit", "$bitcount", + // "$bitfind", "$bitlogic", "$case", "$char", "$classmethod", "$classname", + // "$compile", "$data", "$decimal", "$double", "$extract", "$factor", + // "$find", "$fnumber", "$get", "$increment", "$inumber", "$isobject", + // "$isvaliddouble", "$isvalidnum", "$justify", "$length", "$list", + // "$listbuild", "$listdata", "$listfind", "$listfromstring", "$listget", + // "$listlength", "$listnext", "$listsame", "$listtostring", "$listvalid", + // "$locate", "$match", "$method", "$name", "$nconvert", "$next", + // "$normalize", "$now", "$number", "$order", "$parameter", "$piece", + // "$prefetchoff", "$prefetchon", "$property", "$qlength", "$qsubscript", + // "$query", "$random", "$replace", "$reverse", "$sconvert", "$select", + // "$sortbegin", "$sortend", "$stack", "$text", "$translate", "$view", + // "$wascii", "$wchar", "$wextract", "$wfind", "$wiswide", "$wlength", + // "$wreverse", "$xecute", "$zabs", "$zarccos", "$zarcsin", "$zarctan", + // "$zcos", "$zcot", "$zcsc", "$zdate", "$zdateh", "$zdatetime", + // "$zdatetimeh", "$zexp", "$zhex", "$zln", "$zlog", "$zpower", "$zsec", + // "$zsin", "$zsqr", "$ztan", "$ztime", "$ztimeh", "$zboolean", + // "$zconvert", "$zcrc", "$zcyc", "$zdascii", "$zdchar", "$zf", + // "$ziswide", "$zlascii", "$zlchar", "$zname", "$zposition", "$zqascii", + // "$zqchar", "$zsearch", "$zseek", "$zstrip", "$zwascii", "$zwchar", + // "$zwidth", "$zwpack", "$zwbpack", "$zwunpack", "$zwbunpack", "$zzenkaku", + // "$change", "$mv", "$mvat", "$mvfmt", "$mvfmts", "$mviconv", + // "$mviconvs", "$mvinmat", "$mvlover", "$mvoconv", "$mvoconvs", "$mvraise", + // "$mvtrans", "$mvv", "$mvname", "$zbitand", "$zbitcount", "$zbitfind", + // "$zbitget", "$zbitlen", "$zbitnot", "$zbitor", "$zbitset", "$zbitstr", + // "$zbitxor", "$zincrement", "$znext", "$zorder", "$zprevious", "$zsort", + // "device", "$ecode", "$estack", "$etrap", "$halt", "$horolog", + // "$io", "$job", "$key", "$namespace", "$principal", "$quit", "$roles", + // "$storage", "$system", "$test", "$this", "$tlevel", "$username", + // "$x", "$y", "$za", "$zb", "$zchild", "$zeof", "$zeos", "$zerror", + // "$zhorolog", "$zio", "$zjob", "$zmode", "$znspace", "$zparent", "$zpi", + // "$zpos", "$zreference", "$zstorage", "$ztimestamp", "$ztimezone", + // "$ztrap", "$zversion" + + return { + name: 'Caché Object Script', + case_insensitive: true, + aliases: [ "cls" ], + keywords: COS_KEYWORDS, + contains: [ + NUMBERS, + STRINGS, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + { + className: "comment", + begin: /;/, + end: "$", + relevance: 0 + }, + { // Functions and user-defined functions: write $ztime(60*60*3), $$myFunc(10), $$^Val(1) + className: "built_in", + begin: /(?:\$\$?|\.\.)\^?[a-zA-Z]+/ + }, + { // Macro command: quit $$$OK + className: "built_in", + begin: /\$\$\$[a-zA-Z]+/ + }, + { // Special (global) variables: write %request.Content; Built-in classes: %Library.Integer + className: "built_in", + begin: /%[a-z]+(?:\.[a-z]+)*/ + }, + { // Global variable: set ^globalName = 12 write ^globalName + className: "symbol", + begin: /\^%?[a-zA-Z][\w]*/ + }, + { // Some control constructions: do ##class(Package.ClassName).Method(), ##super() + className: "keyword", + begin: /##class|##super|#define|#dim/ + }, + // sub-languages: are not fully supported by hljs by 11/15/2015 + // left for the future implementation. + { + begin: /&sql\(/, + end: /\)/, + excludeBegin: true, + excludeEnd: true, + subLanguage: "sql" + }, + { + begin: /&(js|jscript|javascript)/, + excludeBegin: true, + excludeEnd: true, + subLanguage: "javascript" + }, + { + // this brakes first and last tag, but this is the only way to embed a valid html + begin: /&html<\s*\s*>/, + subLanguage: "xml" + } + ] + }; +} + +export { cos as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/cos.js.js b/frontend/node_modules/highlight.js/es/languages/cos.js.js new file mode 100644 index 0000000..e0e79ed --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/cos.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/cos" instead of "highlight.js/lib/languages/cos.js"' + ); + } + } + emitWarning(); + import lang from './cos.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/cpp.js b/frontend/node_modules/highlight.js/es/languages/cpp.js new file mode 100644 index 0000000..2899f66 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/cpp.js @@ -0,0 +1,605 @@ +/* +Language: C++ +Category: common, system +Website: https://isocpp.org +*/ + +/** @type LanguageFn */ +function cpp(hljs) { + const regex = hljs.regex; + // added for historic reasons because `hljs.C_LINE_COMMENT_MODE` does + // not include such support nor can we be sure all the grammars depending + // on it would desire this behavior + const C_LINE_COMMENT_MODE = hljs.COMMENT('//', '$', { contains: [ { begin: /\\\n/ } ] }); + const DECLTYPE_AUTO_RE = 'decltype\\(auto\\)'; + const NAMESPACE_RE = '[a-zA-Z_]\\w*::'; + const TEMPLATE_ARGUMENT_RE = '<[^<>]+>'; + const FUNCTION_TYPE_RE = '(?!struct)(' + + DECLTYPE_AUTO_RE + '|' + + regex.optional(NAMESPACE_RE) + + '[a-zA-Z_]\\w*' + regex.optional(TEMPLATE_ARGUMENT_RE) + + ')'; + + const CPP_PRIMITIVE_TYPES = { + className: 'type', + begin: '\\b[a-z\\d_]*_t\\b' + }; + + // https://en.cppreference.com/w/cpp/language/escape + // \\ \x \xFF \u2837 \u00323747 \374 + const CHARACTER_ESCAPES = '\\\\(x[0-9A-Fa-f]{2}|u[0-9A-Fa-f]{4,8}|[0-7]{3}|\\S)'; + const STRINGS = { + className: 'string', + variants: [ + { + begin: '(u8?|U|L)?"', + end: '"', + illegal: '\\n', + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: '(u8?|U|L)?\'(' + CHARACTER_ESCAPES + '|.)', + end: '\'', + illegal: '.' + }, + hljs.END_SAME_AS_BEGIN({ + begin: /(?:u8?|U|L)?R"([^()\\ ]{0,16})\(/, + end: /\)([^()\\ ]{0,16})"/ + }) + ] + }; + + const NUMBERS = { + className: 'number', + variants: [ + // Floating-point literal. + { begin: + "[+-]?(?:" // Leading sign. + // Decimal. + + "(?:" + +"[0-9](?:'?[0-9])*\\.(?:[0-9](?:'?[0-9])*)?" + + "|\\.[0-9](?:'?[0-9])*" + + ")(?:[Ee][+-]?[0-9](?:'?[0-9])*)?" + + "|[0-9](?:'?[0-9])*[Ee][+-]?[0-9](?:'?[0-9])*" + // Hexadecimal. + + "|0[Xx](?:" + +"[0-9A-Fa-f](?:'?[0-9A-Fa-f])*(?:\\.(?:[0-9A-Fa-f](?:'?[0-9A-Fa-f])*)?)?" + + "|\\.[0-9A-Fa-f](?:'?[0-9A-Fa-f])*" + + ")[Pp][+-]?[0-9](?:'?[0-9])*" + + ")(?:" // Literal suffixes. + + "[Ff](?:16|32|64|128)?" + + "|(BF|bf)16" + + "|[Ll]" + + "|" // Literal suffix is optional. + + ")" + }, + // Integer literal. + { begin: + "[+-]?\\b(?:" // Leading sign. + + "0[Bb][01](?:'?[01])*" // Binary. + + "|0[Xx][0-9A-Fa-f](?:'?[0-9A-Fa-f])*" // Hexadecimal. + + "|0(?:'?[0-7])*" // Octal or just a lone zero. + + "|[1-9](?:'?[0-9])*" // Decimal. + + ")(?:" // Literal suffixes. + + "[Uu](?:LL?|ll?)" + + "|[Uu][Zz]?" + + "|(?:LL?|ll?)[Uu]?" + + "|[Zz][Uu]" + + "|" // Literal suffix is optional. + + ")" + // Note: there are user-defined literal suffixes too, but perhaps having the custom suffix not part of the + // literal highlight actually makes it stand out more. + } + ], + relevance: 0 + }; + + const PREPROCESSOR = { + className: 'meta', + begin: /#\s*[a-z]+\b/, + end: /$/, + keywords: { keyword: + 'if else elif endif define undef warning error line ' + + 'pragma _Pragma ifdef ifndef include' }, + contains: [ + { + begin: /\\\n/, + relevance: 0 + }, + hljs.inherit(STRINGS, { className: 'string' }), + { + className: 'string', + begin: /<.*?>/ + }, + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }; + + const TITLE_MODE = { + className: 'title', + begin: regex.optional(NAMESPACE_RE) + hljs.IDENT_RE, + relevance: 0 + }; + + const FUNCTION_TITLE = regex.optional(NAMESPACE_RE) + hljs.IDENT_RE + '\\s*\\('; + + // https://en.cppreference.com/w/cpp/keyword + const RESERVED_KEYWORDS = [ + 'alignas', + 'alignof', + 'and', + 'and_eq', + 'asm', + 'atomic_cancel', + 'atomic_commit', + 'atomic_noexcept', + 'auto', + 'bitand', + 'bitor', + 'break', + 'case', + 'catch', + 'class', + 'co_await', + 'co_return', + 'co_yield', + 'compl', + 'concept', + 'const_cast|10', + 'consteval', + 'constexpr', + 'constinit', + 'continue', + 'decltype', + 'default', + 'delete', + 'do', + 'dynamic_cast|10', + 'else', + 'enum', + 'explicit', + 'export', + 'extern', + 'false', + 'final', + 'for', + 'friend', + 'goto', + 'if', + 'import', + 'inline', + 'module', + 'mutable', + 'namespace', + 'new', + 'noexcept', + 'not', + 'not_eq', + 'nullptr', + 'operator', + 'or', + 'or_eq', + 'override', + 'private', + 'protected', + 'public', + 'reflexpr', + 'register', + 'reinterpret_cast|10', + 'requires', + 'return', + 'sizeof', + 'static_assert', + 'static_cast|10', + 'struct', + 'switch', + 'synchronized', + 'template', + 'this', + 'thread_local', + 'throw', + 'transaction_safe', + 'transaction_safe_dynamic', + 'true', + 'try', + 'typedef', + 'typeid', + 'typename', + 'union', + 'using', + 'virtual', + 'volatile', + 'while', + 'xor', + 'xor_eq' + ]; + + // https://en.cppreference.com/w/cpp/keyword + const RESERVED_TYPES = [ + 'bool', + 'char', + 'char16_t', + 'char32_t', + 'char8_t', + 'double', + 'float', + 'int', + 'long', + 'short', + 'void', + 'wchar_t', + 'unsigned', + 'signed', + 'const', + 'static' + ]; + + const TYPE_HINTS = [ + 'any', + 'auto_ptr', + 'barrier', + 'binary_semaphore', + 'bitset', + 'complex', + 'condition_variable', + 'condition_variable_any', + 'counting_semaphore', + 'deque', + 'false_type', + 'flat_map', + 'flat_set', + 'future', + 'imaginary', + 'initializer_list', + 'istringstream', + 'jthread', + 'latch', + 'lock_guard', + 'multimap', + 'multiset', + 'mutex', + 'optional', + 'ostringstream', + 'packaged_task', + 'pair', + 'promise', + 'priority_queue', + 'queue', + 'recursive_mutex', + 'recursive_timed_mutex', + 'scoped_lock', + 'set', + 'shared_future', + 'shared_lock', + 'shared_mutex', + 'shared_timed_mutex', + 'shared_ptr', + 'stack', + 'string_view', + 'stringstream', + 'timed_mutex', + 'thread', + 'true_type', + 'tuple', + 'unique_lock', + 'unique_ptr', + 'unordered_map', + 'unordered_multimap', + 'unordered_multiset', + 'unordered_set', + 'variant', + 'vector', + 'weak_ptr', + 'wstring', + 'wstring_view' + ]; + + const FUNCTION_HINTS = [ + 'abort', + 'abs', + 'acos', + 'apply', + 'as_const', + 'asin', + 'atan', + 'atan2', + 'calloc', + 'ceil', + 'cerr', + 'cin', + 'clog', + 'cos', + 'cosh', + 'cout', + 'declval', + 'endl', + 'exchange', + 'exit', + 'exp', + 'fabs', + 'floor', + 'fmod', + 'forward', + 'fprintf', + 'fputs', + 'free', + 'frexp', + 'fscanf', + 'future', + 'invoke', + 'isalnum', + 'isalpha', + 'iscntrl', + 'isdigit', + 'isgraph', + 'islower', + 'isprint', + 'ispunct', + 'isspace', + 'isupper', + 'isxdigit', + 'labs', + 'launder', + 'ldexp', + 'log', + 'log10', + 'make_pair', + 'make_shared', + 'make_shared_for_overwrite', + 'make_tuple', + 'make_unique', + 'malloc', + 'memchr', + 'memcmp', + 'memcpy', + 'memset', + 'modf', + 'move', + 'pow', + 'printf', + 'putchar', + 'puts', + 'realloc', + 'scanf', + 'sin', + 'sinh', + 'snprintf', + 'sprintf', + 'sqrt', + 'sscanf', + 'std', + 'stderr', + 'stdin', + 'stdout', + 'strcat', + 'strchr', + 'strcmp', + 'strcpy', + 'strcspn', + 'strlen', + 'strncat', + 'strncmp', + 'strncpy', + 'strpbrk', + 'strrchr', + 'strspn', + 'strstr', + 'swap', + 'tan', + 'tanh', + 'terminate', + 'to_underlying', + 'tolower', + 'toupper', + 'vfprintf', + 'visit', + 'vprintf', + 'vsprintf' + ]; + + const LITERALS = [ + 'NULL', + 'false', + 'nullopt', + 'nullptr', + 'true' + ]; + + // https://en.cppreference.com/w/cpp/keyword + const BUILT_IN = [ '_Pragma' ]; + + const CPP_KEYWORDS = { + type: RESERVED_TYPES, + keyword: RESERVED_KEYWORDS, + literal: LITERALS, + built_in: BUILT_IN, + _type_hints: TYPE_HINTS + }; + + const FUNCTION_DISPATCH = { + className: 'function.dispatch', + relevance: 0, + keywords: { + // Only for relevance, not highlighting. + _hint: FUNCTION_HINTS }, + begin: regex.concat( + /\b/, + /(?!decltype)/, + /(?!if)/, + /(?!for)/, + /(?!switch)/, + /(?!while)/, + hljs.IDENT_RE, + regex.lookahead(/(<[^<>]+>|)\s*\(/)) + }; + + const EXPRESSION_CONTAINS = [ + FUNCTION_DISPATCH, + PREPROCESSOR, + CPP_PRIMITIVE_TYPES, + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + NUMBERS, + STRINGS + ]; + + const EXPRESSION_CONTEXT = { + // This mode covers expression context where we can't expect a function + // definition and shouldn't highlight anything that looks like one: + // `return some()`, `else if()`, `(x*sum(1, 2))` + variants: [ + { + begin: /=/, + end: /;/ + }, + { + begin: /\(/, + end: /\)/ + }, + { + beginKeywords: 'new throw return else', + end: /;/ + } + ], + keywords: CPP_KEYWORDS, + contains: EXPRESSION_CONTAINS.concat([ + { + begin: /\(/, + end: /\)/, + keywords: CPP_KEYWORDS, + contains: EXPRESSION_CONTAINS.concat([ 'self' ]), + relevance: 0 + } + ]), + relevance: 0 + }; + + const FUNCTION_DECLARATION = { + className: 'function', + begin: '(' + FUNCTION_TYPE_RE + '[\\*&\\s]+)+' + FUNCTION_TITLE, + returnBegin: true, + end: /[{;=]/, + excludeEnd: true, + keywords: CPP_KEYWORDS, + illegal: /[^\w\s\*&:<>.]/, + contains: [ + { // to prevent it from being confused as the function title + begin: DECLTYPE_AUTO_RE, + keywords: CPP_KEYWORDS, + relevance: 0 + }, + { + begin: FUNCTION_TITLE, + returnBegin: true, + contains: [ TITLE_MODE ], + relevance: 0 + }, + // needed because we do not have look-behind on the below rule + // to prevent it from grabbing the final : in a :: pair + { + begin: /::/, + relevance: 0 + }, + // initializers + { + begin: /:/, + endsWithParent: true, + contains: [ + STRINGS, + NUMBERS + ] + }, + // allow for multiple declarations, e.g.: + // extern void f(int), g(char); + { + relevance: 0, + match: /,/ + }, + { + className: 'params', + begin: /\(/, + end: /\)/, + keywords: CPP_KEYWORDS, + relevance: 0, + contains: [ + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + STRINGS, + NUMBERS, + CPP_PRIMITIVE_TYPES, + // Count matching parentheses. + { + begin: /\(/, + end: /\)/, + keywords: CPP_KEYWORDS, + relevance: 0, + contains: [ + 'self', + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + STRINGS, + NUMBERS, + CPP_PRIMITIVE_TYPES + ] + } + ] + }, + CPP_PRIMITIVE_TYPES, + C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + PREPROCESSOR + ] + }; + + return { + name: 'C++', + aliases: [ + 'cc', + 'c++', + 'h++', + 'hpp', + 'hh', + 'hxx', + 'cxx' + ], + keywords: CPP_KEYWORDS, + illegal: ' rooms (9);` + begin: '\\b(deque|list|queue|priority_queue|pair|stack|vector|map|set|bitset|multiset|multimap|unordered_map|unordered_set|unordered_multiset|unordered_multimap|array|tuple|optional|variant|function|flat_map|flat_set)\\s*<(?!<)', + end: '>', + keywords: CPP_KEYWORDS, + contains: [ + 'self', + CPP_PRIMITIVE_TYPES + ] + }, + { + begin: hljs.IDENT_RE + '::', + keywords: CPP_KEYWORDS + }, + { + match: [ + // extra complexity to deal with `enum class` and `enum struct` + /\b(?:enum(?:\s+(?:class|struct))?|class|struct|union)/, + /\s+/, + /\w+/ + ], + className: { + 1: 'keyword', + 3: 'title.class' + } + } + ]) + }; +} + +export { cpp as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/cpp.js.js b/frontend/node_modules/highlight.js/es/languages/cpp.js.js new file mode 100644 index 0000000..32adb95 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/cpp.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/cpp" instead of "highlight.js/lib/languages/cpp.js"' + ); + } + } + emitWarning(); + import lang from './cpp.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/crmsh.js b/frontend/node_modules/highlight.js/es/languages/crmsh.js new file mode 100644 index 0000000..1c3c229 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/crmsh.js @@ -0,0 +1,100 @@ +/* +Language: crmsh +Author: Kristoffer Gronlund +Website: http://crmsh.github.io +Description: Syntax Highlighting for the crmsh DSL +Category: config +*/ + +/** @type LanguageFn */ +function crmsh(hljs) { + const RESOURCES = 'primitive rsc_template'; + const COMMANDS = 'group clone ms master location colocation order fencing_topology ' + + 'rsc_ticket acl_target acl_group user role ' + + 'tag xml'; + const PROPERTY_SETS = 'property rsc_defaults op_defaults'; + const KEYWORDS = 'params meta operations op rule attributes utilization'; + const OPERATORS = 'read write deny defined not_defined in_range date spec in ' + + 'ref reference attribute type xpath version and or lt gt tag ' + + 'lte gte eq ne \\'; + const TYPES = 'number string'; + const LITERALS = 'Master Started Slave Stopped start promote demote stop monitor true false'; + + return { + name: 'crmsh', + aliases: [ + 'crm', + 'pcmk' + ], + case_insensitive: true, + keywords: { + keyword: KEYWORDS + ' ' + OPERATORS + ' ' + TYPES, + literal: LITERALS + }, + contains: [ + hljs.HASH_COMMENT_MODE, + { + beginKeywords: 'node', + starts: { + end: '\\s*([\\w_-]+:)?', + starts: { + className: 'title', + end: '\\s*[\\$\\w_][\\w_-]*' + } + } + }, + { + beginKeywords: RESOURCES, + starts: { + className: 'title', + end: '\\s*[\\$\\w_][\\w_-]*', + starts: { end: '\\s*@?[\\w_][\\w_\\.:-]*' } + } + }, + { + begin: '\\b(' + COMMANDS.split(' ').join('|') + ')\\s+', + keywords: COMMANDS, + starts: { + className: 'title', + end: '[\\$\\w_][\\w_-]*' + } + }, + { + beginKeywords: PROPERTY_SETS, + starts: { + className: 'title', + end: '\\s*([\\w_-]+:)?' + } + }, + hljs.QUOTE_STRING_MODE, + { + className: 'meta', + begin: '(ocf|systemd|service|lsb):[\\w_:-]+', + relevance: 0 + }, + { + className: 'number', + begin: '\\b\\d+(\\.\\d+)?(ms|s|h|m)?', + relevance: 0 + }, + { + className: 'literal', + begin: '[-]?(infinity|inf)', + relevance: 0 + }, + { + className: 'attr', + begin: /([A-Za-z$_#][\w_-]+)=/, + relevance: 0 + }, + { + className: 'tag', + begin: '', + relevance: 0 + } + ] + }; +} + +export { crmsh as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/crmsh.js.js b/frontend/node_modules/highlight.js/es/languages/crmsh.js.js new file mode 100644 index 0000000..8b634c5 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/crmsh.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/crmsh" instead of "highlight.js/lib/languages/crmsh.js"' + ); + } + } + emitWarning(); + import lang from './crmsh.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/crystal.js b/frontend/node_modules/highlight.js/es/languages/crystal.js new file mode 100644 index 0000000..348db32 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/crystal.js @@ -0,0 +1,312 @@ +/* +Language: Crystal +Author: TSUYUSATO Kitsune +Website: https://crystal-lang.org +Category: system +*/ + +/** @type LanguageFn */ +function crystal(hljs) { + const INT_SUFFIX = '(_?[ui](8|16|32|64|128))?'; + const FLOAT_SUFFIX = '(_?f(32|64))?'; + const CRYSTAL_IDENT_RE = '[a-zA-Z_]\\w*[!?=]?'; + const CRYSTAL_METHOD_RE = '[a-zA-Z_]\\w*[!?=]?|[-+~]@|<<|>>|[=!]~|===?|<=>|[<>]=?|\\*\\*|[-/+%^&*~|]|//|//=|&[-+*]=?|&\\*\\*|\\[\\][=?]?'; + const CRYSTAL_PATH_RE = '[A-Za-z_]\\w*(::\\w+)*(\\?|!)?'; + const CRYSTAL_KEYWORDS = { + $pattern: CRYSTAL_IDENT_RE, + keyword: + 'abstract alias annotation as as? asm begin break case class def do else elsif end ensure enum extend for fun if ' + + 'include instance_sizeof is_a? lib macro module next nil? of out pointerof private protected rescue responds_to? ' + + 'return require select self sizeof struct super then type typeof union uninitialized unless until verbatim when while with yield ' + + '__DIR__ __END_LINE__ __FILE__ __LINE__', + literal: 'false nil true' + }; + const SUBST = { + className: 'subst', + begin: /#\{/, + end: /\}/, + keywords: CRYSTAL_KEYWORDS + }; + // borrowed from Ruby + const VARIABLE = { + // negative-look forward attemps to prevent false matches like: + // @ident@ or $ident$ that might indicate this is not ruby at all + className: "variable", + begin: '(\\$\\W)|((\\$|@@?)(\\w+))(?=[^@$?])' + `(?![A-Za-z])(?![@$?'])` + }; + const EXPANSION = { + className: 'template-variable', + variants: [ + { + begin: '\\{\\{', + end: '\\}\\}' + }, + { + begin: '\\{%', + end: '%\\}' + } + ], + keywords: CRYSTAL_KEYWORDS + }; + + function recursiveParen(begin, end) { + const + contains = [ + { + begin: begin, + end: end + } + ]; + contains[0].contains = contains; + return contains; + } + const STRING = { + className: 'string', + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST + ], + variants: [ + { + begin: /'/, + end: /'/ + }, + { + begin: /"/, + end: /"/ + }, + { + begin: /`/, + end: /`/ + }, + { + begin: '%[Qwi]?\\(', + end: '\\)', + contains: recursiveParen('\\(', '\\)') + }, + { + begin: '%[Qwi]?\\[', + end: '\\]', + contains: recursiveParen('\\[', '\\]') + }, + { + begin: '%[Qwi]?\\{', + end: /\}/, + contains: recursiveParen(/\{/, /\}/) + }, + { + begin: '%[Qwi]?<', + end: '>', + contains: recursiveParen('<', '>') + }, + { + begin: '%[Qwi]?\\|', + end: '\\|' + }, + { + begin: /<<-\w+$/, + end: /^\s*\w+$/ + } + ], + relevance: 0 + }; + const Q_STRING = { + className: 'string', + variants: [ + { + begin: '%q\\(', + end: '\\)', + contains: recursiveParen('\\(', '\\)') + }, + { + begin: '%q\\[', + end: '\\]', + contains: recursiveParen('\\[', '\\]') + }, + { + begin: '%q\\{', + end: /\}/, + contains: recursiveParen(/\{/, /\}/) + }, + { + begin: '%q<', + end: '>', + contains: recursiveParen('<', '>') + }, + { + begin: '%q\\|', + end: '\\|' + }, + { + begin: /<<-'\w+'$/, + end: /^\s*\w+$/ + } + ], + relevance: 0 + }; + const REGEXP = { + begin: '(?!%\\})(' + hljs.RE_STARTERS_RE + '|\\n|\\b(case|if|select|unless|until|when|while)\\b)\\s*', + keywords: 'case if select unless until when while', + contains: [ + { + className: 'regexp', + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST + ], + variants: [ + { + begin: '//[a-z]*', + relevance: 0 + }, + { + begin: '/(?!\\/)', + end: '/[a-z]*' + } + ] + } + ], + relevance: 0 + }; + const REGEXP2 = { + className: 'regexp', + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST + ], + variants: [ + { + begin: '%r\\(', + end: '\\)', + contains: recursiveParen('\\(', '\\)') + }, + { + begin: '%r\\[', + end: '\\]', + contains: recursiveParen('\\[', '\\]') + }, + { + begin: '%r\\{', + end: /\}/, + contains: recursiveParen(/\{/, /\}/) + }, + { + begin: '%r<', + end: '>', + contains: recursiveParen('<', '>') + }, + { + begin: '%r\\|', + end: '\\|' + } + ], + relevance: 0 + }; + const ATTRIBUTE = { + className: 'meta', + begin: '@\\[', + end: '\\]', + contains: [ hljs.inherit(hljs.QUOTE_STRING_MODE, { className: 'string' }) ] + }; + const CRYSTAL_DEFAULT_CONTAINS = [ + EXPANSION, + STRING, + Q_STRING, + REGEXP2, + REGEXP, + ATTRIBUTE, + VARIABLE, + hljs.HASH_COMMENT_MODE, + { + className: 'class', + beginKeywords: 'class module struct', + end: '$|;', + illegal: /=/, + contains: [ + hljs.HASH_COMMENT_MODE, + hljs.inherit(hljs.TITLE_MODE, { begin: CRYSTAL_PATH_RE }), + { // relevance booster for inheritance + begin: '<' } + ] + }, + { + className: 'class', + beginKeywords: 'lib enum union', + end: '$|;', + illegal: /=/, + contains: [ + hljs.HASH_COMMENT_MODE, + hljs.inherit(hljs.TITLE_MODE, { begin: CRYSTAL_PATH_RE }) + ] + }, + { + beginKeywords: 'annotation', + end: '$|;', + illegal: /=/, + contains: [ + hljs.HASH_COMMENT_MODE, + hljs.inherit(hljs.TITLE_MODE, { begin: CRYSTAL_PATH_RE }) + ], + relevance: 2 + }, + { + className: 'function', + beginKeywords: 'def', + end: /\B\b/, + contains: [ + hljs.inherit(hljs.TITLE_MODE, { + begin: CRYSTAL_METHOD_RE, + endsParent: true + }) + ] + }, + { + className: 'function', + beginKeywords: 'fun macro', + end: /\B\b/, + contains: [ + hljs.inherit(hljs.TITLE_MODE, { + begin: CRYSTAL_METHOD_RE, + endsParent: true + }) + ], + relevance: 2 + }, + { + className: 'symbol', + begin: hljs.UNDERSCORE_IDENT_RE + '(!|\\?)?:', + relevance: 0 + }, + { + className: 'symbol', + begin: ':', + contains: [ + STRING, + { begin: CRYSTAL_METHOD_RE } + ], + relevance: 0 + }, + { + className: 'number', + variants: [ + { begin: '\\b0b([01_]+)' + INT_SUFFIX }, + { begin: '\\b0o([0-7_]+)' + INT_SUFFIX }, + { begin: '\\b0x([A-Fa-f0-9_]+)' + INT_SUFFIX }, + { begin: '\\b([1-9][0-9_]*[0-9]|[0-9])(\\.[0-9][0-9_]*)?([eE]_?[-+]?[0-9_]*)?' + FLOAT_SUFFIX + '(?!_)' }, + { begin: '\\b([1-9][0-9_]*|0)' + INT_SUFFIX } + ], + relevance: 0 + } + ]; + SUBST.contains = CRYSTAL_DEFAULT_CONTAINS; + EXPANSION.contains = CRYSTAL_DEFAULT_CONTAINS.slice(1); // without EXPANSION + + return { + name: 'Crystal', + aliases: [ 'cr' ], + keywords: CRYSTAL_KEYWORDS, + contains: CRYSTAL_DEFAULT_CONTAINS + }; +} + +export { crystal as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/crystal.js.js b/frontend/node_modules/highlight.js/es/languages/crystal.js.js new file mode 100644 index 0000000..0cef9c9 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/crystal.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/crystal" instead of "highlight.js/lib/languages/crystal.js"' + ); + } + } + emitWarning(); + import lang from './crystal.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/csharp.js b/frontend/node_modules/highlight.js/es/languages/csharp.js new file mode 100644 index 0000000..0f73aff --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/csharp.js @@ -0,0 +1,412 @@ +/* +Language: C# +Author: Jason Diamond +Contributor: Nicolas LLOBERA , Pieter Vantorre , David Pine +Website: https://docs.microsoft.com/dotnet/csharp/ +Category: common +*/ + +/** @type LanguageFn */ +function csharp(hljs) { + const BUILT_IN_KEYWORDS = [ + 'bool', + 'byte', + 'char', + 'decimal', + 'delegate', + 'double', + 'dynamic', + 'enum', + 'float', + 'int', + 'long', + 'nint', + 'nuint', + 'object', + 'sbyte', + 'short', + 'string', + 'ulong', + 'uint', + 'ushort' + ]; + const FUNCTION_MODIFIERS = [ + 'public', + 'private', + 'protected', + 'static', + 'internal', + 'protected', + 'abstract', + 'async', + 'extern', + 'override', + 'unsafe', + 'virtual', + 'new', + 'sealed', + 'partial' + ]; + const LITERAL_KEYWORDS = [ + 'default', + 'false', + 'null', + 'true' + ]; + const NORMAL_KEYWORDS = [ + 'abstract', + 'as', + 'base', + 'break', + 'case', + 'catch', + 'class', + 'const', + 'continue', + 'do', + 'else', + 'event', + 'explicit', + 'extern', + 'finally', + 'fixed', + 'for', + 'foreach', + 'goto', + 'if', + 'implicit', + 'in', + 'interface', + 'internal', + 'is', + 'lock', + 'namespace', + 'new', + 'operator', + 'out', + 'override', + 'params', + 'private', + 'protected', + 'public', + 'readonly', + 'record', + 'ref', + 'return', + 'scoped', + 'sealed', + 'sizeof', + 'stackalloc', + 'static', + 'struct', + 'switch', + 'this', + 'throw', + 'try', + 'typeof', + 'unchecked', + 'unsafe', + 'using', + 'virtual', + 'void', + 'volatile', + 'while' + ]; + const CONTEXTUAL_KEYWORDS = [ + 'add', + 'alias', + 'and', + 'ascending', + 'args', + 'async', + 'await', + 'by', + 'descending', + 'dynamic', + 'equals', + 'file', + 'from', + 'get', + 'global', + 'group', + 'init', + 'into', + 'join', + 'let', + 'nameof', + 'not', + 'notnull', + 'on', + 'or', + 'orderby', + 'partial', + 'record', + 'remove', + 'required', + 'scoped', + 'select', + 'set', + 'unmanaged', + 'value|0', + 'var', + 'when', + 'where', + 'with', + 'yield' + ]; + + const KEYWORDS = { + keyword: NORMAL_KEYWORDS.concat(CONTEXTUAL_KEYWORDS), + built_in: BUILT_IN_KEYWORDS, + literal: LITERAL_KEYWORDS + }; + const TITLE_MODE = hljs.inherit(hljs.TITLE_MODE, { begin: '[a-zA-Z](\\.?\\w)*' }); + const NUMBERS = { + className: 'number', + variants: [ + { begin: '\\b(0b[01\']+)' }, + { begin: '(-?)\\b([\\d\']+(\\.[\\d\']*)?|\\.[\\d\']+)(u|U|l|L|ul|UL|f|F|b|B)' }, + { begin: '(-?)(\\b0[xX][a-fA-F0-9\']+|(\\b[\\d\']+(\\.[\\d\']*)?|\\.[\\d\']+)([eE][-+]?[\\d\']+)?)' } + ], + relevance: 0 + }; + const RAW_STRING = { + className: 'string', + begin: /"""("*)(?!")(.|\n)*?"""\1/, + relevance: 1 + }; + const VERBATIM_STRING = { + className: 'string', + begin: '@"', + end: '"', + contains: [ { begin: '""' } ] + }; + const VERBATIM_STRING_NO_LF = hljs.inherit(VERBATIM_STRING, { illegal: /\n/ }); + const SUBST = { + className: 'subst', + begin: /\{/, + end: /\}/, + keywords: KEYWORDS + }; + const SUBST_NO_LF = hljs.inherit(SUBST, { illegal: /\n/ }); + const INTERPOLATED_STRING = { + className: 'string', + begin: /\$"/, + end: '"', + illegal: /\n/, + contains: [ + { begin: /\{\{/ }, + { begin: /\}\}/ }, + hljs.BACKSLASH_ESCAPE, + SUBST_NO_LF + ] + }; + const INTERPOLATED_VERBATIM_STRING = { + className: 'string', + begin: /\$@"/, + end: '"', + contains: [ + { begin: /\{\{/ }, + { begin: /\}\}/ }, + { begin: '""' }, + SUBST + ] + }; + const INTERPOLATED_VERBATIM_STRING_NO_LF = hljs.inherit(INTERPOLATED_VERBATIM_STRING, { + illegal: /\n/, + contains: [ + { begin: /\{\{/ }, + { begin: /\}\}/ }, + { begin: '""' }, + SUBST_NO_LF + ] + }); + SUBST.contains = [ + INTERPOLATED_VERBATIM_STRING, + INTERPOLATED_STRING, + VERBATIM_STRING, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + NUMBERS, + hljs.C_BLOCK_COMMENT_MODE + ]; + SUBST_NO_LF.contains = [ + INTERPOLATED_VERBATIM_STRING_NO_LF, + INTERPOLATED_STRING, + VERBATIM_STRING_NO_LF, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + NUMBERS, + hljs.inherit(hljs.C_BLOCK_COMMENT_MODE, { illegal: /\n/ }) + ]; + const STRING = { variants: [ + RAW_STRING, + INTERPOLATED_VERBATIM_STRING, + INTERPOLATED_STRING, + VERBATIM_STRING, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE + ] }; + + const GENERIC_MODIFIER = { + begin: "<", + end: ">", + contains: [ + { beginKeywords: "in out" }, + TITLE_MODE + ] + }; + const TYPE_IDENT_RE = hljs.IDENT_RE + '(<' + hljs.IDENT_RE + '(\\s*,\\s*' + hljs.IDENT_RE + ')*>)?(\\[\\])?'; + const AT_IDENTIFIER = { + // prevents expressions like `@class` from incorrect flagging + // `class` as a keyword + begin: "@" + hljs.IDENT_RE, + relevance: 0 + }; + + return { + name: 'C#', + aliases: [ + 'cs', + 'c#' + ], + keywords: KEYWORDS, + illegal: /::/, + contains: [ + hljs.COMMENT( + '///', + '$', + { + returnBegin: true, + contains: [ + { + className: 'doctag', + variants: [ + { + begin: '///', + relevance: 0 + }, + { begin: '' }, + { + begin: '' + } + ] + } + ] + } + ), + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + { + className: 'meta', + begin: '#', + end: '$', + keywords: { keyword: 'if else elif endif define undef warning error line region endregion pragma checksum' } + }, + STRING, + NUMBERS, + { + beginKeywords: 'class interface', + relevance: 0, + end: /[{;=]/, + illegal: /[^\s:,]/, + contains: [ + { beginKeywords: "where class" }, + TITLE_MODE, + GENERIC_MODIFIER, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + { + beginKeywords: 'namespace', + relevance: 0, + end: /[{;=]/, + illegal: /[^\s:]/, + contains: [ + TITLE_MODE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + { + beginKeywords: 'record', + relevance: 0, + end: /[{;=]/, + illegal: /[^\s:]/, + contains: [ + TITLE_MODE, + GENERIC_MODIFIER, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + { + // [Attributes("")] + className: 'meta', + begin: '^\\s*\\[(?=[\\w])', + excludeBegin: true, + end: '\\]', + excludeEnd: true, + contains: [ + { + className: 'string', + begin: /"/, + end: /"/ + } + ] + }, + { + // Expression keywords prevent 'keyword Name(...)' from being + // recognized as a function definition + beginKeywords: 'new return throw await else', + relevance: 0 + }, + { + className: 'function', + begin: '(' + TYPE_IDENT_RE + '\\s+)+' + hljs.IDENT_RE + '\\s*(<[^=]+>\\s*)?\\(', + returnBegin: true, + end: /\s*[{;=]/, + excludeEnd: true, + keywords: KEYWORDS, + contains: [ + // prevents these from being highlighted `title` + { + beginKeywords: FUNCTION_MODIFIERS.join(" "), + relevance: 0 + }, + { + begin: hljs.IDENT_RE + '\\s*(<[^=]+>\\s*)?\\(', + returnBegin: true, + contains: [ + hljs.TITLE_MODE, + GENERIC_MODIFIER + ], + relevance: 0 + }, + { match: /\(\)/ }, + { + className: 'params', + begin: /\(/, + end: /\)/, + excludeBegin: true, + excludeEnd: true, + keywords: KEYWORDS, + relevance: 0, + contains: [ + STRING, + NUMBERS, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + AT_IDENTIFIER + ] + }; +} + +export { csharp as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/csharp.js.js b/frontend/node_modules/highlight.js/es/languages/csharp.js.js new file mode 100644 index 0000000..b586ab5 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/csharp.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/csharp" instead of "highlight.js/lib/languages/csharp.js"' + ); + } + } + emitWarning(); + import lang from './csharp.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/csp.js b/frontend/node_modules/highlight.js/es/languages/csp.js new file mode 100644 index 0000000..3d9565a --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/csp.js @@ -0,0 +1,58 @@ +/* +Language: CSP +Description: Content Security Policy definition highlighting +Author: Taras +Website: https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP +Category: web + +vim: ts=2 sw=2 st=2 +*/ + +/** @type LanguageFn */ +function csp(hljs) { + const KEYWORDS = [ + "base-uri", + "child-src", + "connect-src", + "default-src", + "font-src", + "form-action", + "frame-ancestors", + "frame-src", + "img-src", + "manifest-src", + "media-src", + "object-src", + "plugin-types", + "report-uri", + "sandbox", + "script-src", + "style-src", + "trusted-types", + "unsafe-hashes", + "worker-src" + ]; + return { + name: 'CSP', + case_insensitive: false, + keywords: { + $pattern: '[a-zA-Z][a-zA-Z0-9_-]*', + keyword: KEYWORDS + }, + contains: [ + { + className: 'string', + begin: "'", + end: "'" + }, + { + className: 'attribute', + begin: '^Content', + end: ':', + excludeEnd: true + } + ] + }; +} + +export { csp as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/csp.js.js b/frontend/node_modules/highlight.js/es/languages/csp.js.js new file mode 100644 index 0000000..2cda27b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/csp.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/csp" instead of "highlight.js/lib/languages/csp.js"' + ); + } + } + emitWarning(); + import lang from './csp.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/css.js b/frontend/node_modules/highlight.js/es/languages/css.js new file mode 100644 index 0000000..955e6fa --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/css.js @@ -0,0 +1,949 @@ +const MODES = (hljs) => { + return { + IMPORTANT: { + scope: 'meta', + begin: '!important' + }, + BLOCK_COMMENT: hljs.C_BLOCK_COMMENT_MODE, + HEXCOLOR: { + scope: 'number', + begin: /#(([0-9a-fA-F]{3,4})|(([0-9a-fA-F]{2}){3,4}))\b/ + }, + FUNCTION_DISPATCH: { + className: "built_in", + begin: /[\w-]+(?=\()/ + }, + ATTRIBUTE_SELECTOR_MODE: { + scope: 'selector-attr', + begin: /\[/, + end: /\]/, + illegal: '$', + contains: [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE + ] + }, + CSS_NUMBER_MODE: { + scope: 'number', + begin: hljs.NUMBER_RE + '(' + + '%|em|ex|ch|rem' + + '|vw|vh|vmin|vmax' + + '|cm|mm|in|pt|pc|px' + + '|deg|grad|rad|turn' + + '|s|ms' + + '|Hz|kHz' + + '|dpi|dpcm|dppx' + + ')?', + relevance: 0 + }, + CSS_VARIABLE: { + className: "attr", + begin: /--[A-Za-z_][A-Za-z0-9_-]*/ + } + }; +}; + +const HTML_TAGS = [ + 'a', + 'abbr', + 'address', + 'article', + 'aside', + 'audio', + 'b', + 'blockquote', + 'body', + 'button', + 'canvas', + 'caption', + 'cite', + 'code', + 'dd', + 'del', + 'details', + 'dfn', + 'div', + 'dl', + 'dt', + 'em', + 'fieldset', + 'figcaption', + 'figure', + 'footer', + 'form', + 'h1', + 'h2', + 'h3', + 'h4', + 'h5', + 'h6', + 'header', + 'hgroup', + 'html', + 'i', + 'iframe', + 'img', + 'input', + 'ins', + 'kbd', + 'label', + 'legend', + 'li', + 'main', + 'mark', + 'menu', + 'nav', + 'object', + 'ol', + 'optgroup', + 'option', + 'p', + 'picture', + 'q', + 'quote', + 'samp', + 'section', + 'select', + 'source', + 'span', + 'strong', + 'summary', + 'sup', + 'table', + 'tbody', + 'td', + 'textarea', + 'tfoot', + 'th', + 'thead', + 'time', + 'tr', + 'ul', + 'var', + 'video' +]; + +const SVG_TAGS = [ + 'defs', + 'g', + 'marker', + 'mask', + 'pattern', + 'svg', + 'switch', + 'symbol', + 'feBlend', + 'feColorMatrix', + 'feComponentTransfer', + 'feComposite', + 'feConvolveMatrix', + 'feDiffuseLighting', + 'feDisplacementMap', + 'feFlood', + 'feGaussianBlur', + 'feImage', + 'feMerge', + 'feMorphology', + 'feOffset', + 'feSpecularLighting', + 'feTile', + 'feTurbulence', + 'linearGradient', + 'radialGradient', + 'stop', + 'circle', + 'ellipse', + 'image', + 'line', + 'path', + 'polygon', + 'polyline', + 'rect', + 'text', + 'use', + 'textPath', + 'tspan', + 'foreignObject', + 'clipPath' +]; + +const TAGS = [ + ...HTML_TAGS, + ...SVG_TAGS, +]; + +// Sorting, then reversing makes sure longer attributes/elements like +// `font-weight` are matched fully instead of getting false positives on say `font` + +const MEDIA_FEATURES = [ + 'any-hover', + 'any-pointer', + 'aspect-ratio', + 'color', + 'color-gamut', + 'color-index', + 'device-aspect-ratio', + 'device-height', + 'device-width', + 'display-mode', + 'forced-colors', + 'grid', + 'height', + 'hover', + 'inverted-colors', + 'monochrome', + 'orientation', + 'overflow-block', + 'overflow-inline', + 'pointer', + 'prefers-color-scheme', + 'prefers-contrast', + 'prefers-reduced-motion', + 'prefers-reduced-transparency', + 'resolution', + 'scan', + 'scripting', + 'update', + 'width', + // TODO: find a better solution? + 'min-width', + 'max-width', + 'min-height', + 'max-height' +].sort().reverse(); + +// https://developer.mozilla.org/en-US/docs/Web/CSS/Pseudo-classes +const PSEUDO_CLASSES = [ + 'active', + 'any-link', + 'blank', + 'checked', + 'current', + 'default', + 'defined', + 'dir', // dir() + 'disabled', + 'drop', + 'empty', + 'enabled', + 'first', + 'first-child', + 'first-of-type', + 'fullscreen', + 'future', + 'focus', + 'focus-visible', + 'focus-within', + 'has', // has() + 'host', // host or host() + 'host-context', // host-context() + 'hover', + 'indeterminate', + 'in-range', + 'invalid', + 'is', // is() + 'lang', // lang() + 'last-child', + 'last-of-type', + 'left', + 'link', + 'local-link', + 'not', // not() + 'nth-child', // nth-child() + 'nth-col', // nth-col() + 'nth-last-child', // nth-last-child() + 'nth-last-col', // nth-last-col() + 'nth-last-of-type', //nth-last-of-type() + 'nth-of-type', //nth-of-type() + 'only-child', + 'only-of-type', + 'optional', + 'out-of-range', + 'past', + 'placeholder-shown', + 'read-only', + 'read-write', + 'required', + 'right', + 'root', + 'scope', + 'target', + 'target-within', + 'user-invalid', + 'valid', + 'visited', + 'where' // where() +].sort().reverse(); + +// https://developer.mozilla.org/en-US/docs/Web/CSS/Pseudo-elements +const PSEUDO_ELEMENTS = [ + 'after', + 'backdrop', + 'before', + 'cue', + 'cue-region', + 'first-letter', + 'first-line', + 'grammar-error', + 'marker', + 'part', + 'placeholder', + 'selection', + 'slotted', + 'spelling-error' +].sort().reverse(); + +const ATTRIBUTES = [ + 'accent-color', + 'align-content', + 'align-items', + 'align-self', + 'alignment-baseline', + 'all', + 'anchor-name', + 'animation', + 'animation-composition', + 'animation-delay', + 'animation-direction', + 'animation-duration', + 'animation-fill-mode', + 'animation-iteration-count', + 'animation-name', + 'animation-play-state', + 'animation-range', + 'animation-range-end', + 'animation-range-start', + 'animation-timeline', + 'animation-timing-function', + 'appearance', + 'aspect-ratio', + 'backdrop-filter', + 'backface-visibility', + 'background', + 'background-attachment', + 'background-blend-mode', + 'background-clip', + 'background-color', + 'background-image', + 'background-origin', + 'background-position', + 'background-position-x', + 'background-position-y', + 'background-repeat', + 'background-size', + 'baseline-shift', + 'block-size', + 'border', + 'border-block', + 'border-block-color', + 'border-block-end', + 'border-block-end-color', + 'border-block-end-style', + 'border-block-end-width', + 'border-block-start', + 'border-block-start-color', + 'border-block-start-style', + 'border-block-start-width', + 'border-block-style', + 'border-block-width', + 'border-bottom', + 'border-bottom-color', + 'border-bottom-left-radius', + 'border-bottom-right-radius', + 'border-bottom-style', + 'border-bottom-width', + 'border-collapse', + 'border-color', + 'border-end-end-radius', + 'border-end-start-radius', + 'border-image', + 'border-image-outset', + 'border-image-repeat', + 'border-image-slice', + 'border-image-source', + 'border-image-width', + 'border-inline', + 'border-inline-color', + 'border-inline-end', + 'border-inline-end-color', + 'border-inline-end-style', + 'border-inline-end-width', + 'border-inline-start', + 'border-inline-start-color', + 'border-inline-start-style', + 'border-inline-start-width', + 'border-inline-style', + 'border-inline-width', + 'border-left', + 'border-left-color', + 'border-left-style', + 'border-left-width', + 'border-radius', + 'border-right', + 'border-right-color', + 'border-right-style', + 'border-right-width', + 'border-spacing', + 'border-start-end-radius', + 'border-start-start-radius', + 'border-style', + 'border-top', + 'border-top-color', + 'border-top-left-radius', + 'border-top-right-radius', + 'border-top-style', + 'border-top-width', + 'border-width', + 'bottom', + 'box-align', + 'box-decoration-break', + 'box-direction', + 'box-flex', + 'box-flex-group', + 'box-lines', + 'box-ordinal-group', + 'box-orient', + 'box-pack', + 'box-shadow', + 'box-sizing', + 'break-after', + 'break-before', + 'break-inside', + 'caption-side', + 'caret-color', + 'clear', + 'clip', + 'clip-path', + 'clip-rule', + 'color', + 'color-interpolation', + 'color-interpolation-filters', + 'color-profile', + 'color-rendering', + 'color-scheme', + 'column-count', + 'column-fill', + 'column-gap', + 'column-rule', + 'column-rule-color', + 'column-rule-style', + 'column-rule-width', + 'column-span', + 'column-width', + 'columns', + 'contain', + 'contain-intrinsic-block-size', + 'contain-intrinsic-height', + 'contain-intrinsic-inline-size', + 'contain-intrinsic-size', + 'contain-intrinsic-width', + 'container', + 'container-name', + 'container-type', + 'content', + 'content-visibility', + 'counter-increment', + 'counter-reset', + 'counter-set', + 'cue', + 'cue-after', + 'cue-before', + 'cursor', + 'cx', + 'cy', + 'direction', + 'display', + 'dominant-baseline', + 'empty-cells', + 'enable-background', + 'field-sizing', + 'fill', + 'fill-opacity', + 'fill-rule', + 'filter', + 'flex', + 'flex-basis', + 'flex-direction', + 'flex-flow', + 'flex-grow', + 'flex-shrink', + 'flex-wrap', + 'float', + 'flood-color', + 'flood-opacity', + 'flow', + 'font', + 'font-display', + 'font-family', + 'font-feature-settings', + 'font-kerning', + 'font-language-override', + 'font-optical-sizing', + 'font-palette', + 'font-size', + 'font-size-adjust', + 'font-smooth', + 'font-smoothing', + 'font-stretch', + 'font-style', + 'font-synthesis', + 'font-synthesis-position', + 'font-synthesis-small-caps', + 'font-synthesis-style', + 'font-synthesis-weight', + 'font-variant', + 'font-variant-alternates', + 'font-variant-caps', + 'font-variant-east-asian', + 'font-variant-emoji', + 'font-variant-ligatures', + 'font-variant-numeric', + 'font-variant-position', + 'font-variation-settings', + 'font-weight', + 'forced-color-adjust', + 'gap', + 'glyph-orientation-horizontal', + 'glyph-orientation-vertical', + 'grid', + 'grid-area', + 'grid-auto-columns', + 'grid-auto-flow', + 'grid-auto-rows', + 'grid-column', + 'grid-column-end', + 'grid-column-start', + 'grid-gap', + 'grid-row', + 'grid-row-end', + 'grid-row-start', + 'grid-template', + 'grid-template-areas', + 'grid-template-columns', + 'grid-template-rows', + 'hanging-punctuation', + 'height', + 'hyphenate-character', + 'hyphenate-limit-chars', + 'hyphens', + 'icon', + 'image-orientation', + 'image-rendering', + 'image-resolution', + 'ime-mode', + 'initial-letter', + 'initial-letter-align', + 'inline-size', + 'inset', + 'inset-area', + 'inset-block', + 'inset-block-end', + 'inset-block-start', + 'inset-inline', + 'inset-inline-end', + 'inset-inline-start', + 'isolation', + 'justify-content', + 'justify-items', + 'justify-self', + 'kerning', + 'left', + 'letter-spacing', + 'lighting-color', + 'line-break', + 'line-height', + 'line-height-step', + 'list-style', + 'list-style-image', + 'list-style-position', + 'list-style-type', + 'margin', + 'margin-block', + 'margin-block-end', + 'margin-block-start', + 'margin-bottom', + 'margin-inline', + 'margin-inline-end', + 'margin-inline-start', + 'margin-left', + 'margin-right', + 'margin-top', + 'margin-trim', + 'marker', + 'marker-end', + 'marker-mid', + 'marker-start', + 'marks', + 'mask', + 'mask-border', + 'mask-border-mode', + 'mask-border-outset', + 'mask-border-repeat', + 'mask-border-slice', + 'mask-border-source', + 'mask-border-width', + 'mask-clip', + 'mask-composite', + 'mask-image', + 'mask-mode', + 'mask-origin', + 'mask-position', + 'mask-repeat', + 'mask-size', + 'mask-type', + 'masonry-auto-flow', + 'math-depth', + 'math-shift', + 'math-style', + 'max-block-size', + 'max-height', + 'max-inline-size', + 'max-width', + 'min-block-size', + 'min-height', + 'min-inline-size', + 'min-width', + 'mix-blend-mode', + 'nav-down', + 'nav-index', + 'nav-left', + 'nav-right', + 'nav-up', + 'none', + 'normal', + 'object-fit', + 'object-position', + 'offset', + 'offset-anchor', + 'offset-distance', + 'offset-path', + 'offset-position', + 'offset-rotate', + 'opacity', + 'order', + 'orphans', + 'outline', + 'outline-color', + 'outline-offset', + 'outline-style', + 'outline-width', + 'overflow', + 'overflow-anchor', + 'overflow-block', + 'overflow-clip-margin', + 'overflow-inline', + 'overflow-wrap', + 'overflow-x', + 'overflow-y', + 'overlay', + 'overscroll-behavior', + 'overscroll-behavior-block', + 'overscroll-behavior-inline', + 'overscroll-behavior-x', + 'overscroll-behavior-y', + 'padding', + 'padding-block', + 'padding-block-end', + 'padding-block-start', + 'padding-bottom', + 'padding-inline', + 'padding-inline-end', + 'padding-inline-start', + 'padding-left', + 'padding-right', + 'padding-top', + 'page', + 'page-break-after', + 'page-break-before', + 'page-break-inside', + 'paint-order', + 'pause', + 'pause-after', + 'pause-before', + 'perspective', + 'perspective-origin', + 'place-content', + 'place-items', + 'place-self', + 'pointer-events', + 'position', + 'position-anchor', + 'position-visibility', + 'print-color-adjust', + 'quotes', + 'r', + 'resize', + 'rest', + 'rest-after', + 'rest-before', + 'right', + 'rotate', + 'row-gap', + 'ruby-align', + 'ruby-position', + 'scale', + 'scroll-behavior', + 'scroll-margin', + 'scroll-margin-block', + 'scroll-margin-block-end', + 'scroll-margin-block-start', + 'scroll-margin-bottom', + 'scroll-margin-inline', + 'scroll-margin-inline-end', + 'scroll-margin-inline-start', + 'scroll-margin-left', + 'scroll-margin-right', + 'scroll-margin-top', + 'scroll-padding', + 'scroll-padding-block', + 'scroll-padding-block-end', + 'scroll-padding-block-start', + 'scroll-padding-bottom', + 'scroll-padding-inline', + 'scroll-padding-inline-end', + 'scroll-padding-inline-start', + 'scroll-padding-left', + 'scroll-padding-right', + 'scroll-padding-top', + 'scroll-snap-align', + 'scroll-snap-stop', + 'scroll-snap-type', + 'scroll-timeline', + 'scroll-timeline-axis', + 'scroll-timeline-name', + 'scrollbar-color', + 'scrollbar-gutter', + 'scrollbar-width', + 'shape-image-threshold', + 'shape-margin', + 'shape-outside', + 'shape-rendering', + 'speak', + 'speak-as', + 'src', // @font-face + 'stop-color', + 'stop-opacity', + 'stroke', + 'stroke-dasharray', + 'stroke-dashoffset', + 'stroke-linecap', + 'stroke-linejoin', + 'stroke-miterlimit', + 'stroke-opacity', + 'stroke-width', + 'tab-size', + 'table-layout', + 'text-align', + 'text-align-all', + 'text-align-last', + 'text-anchor', + 'text-combine-upright', + 'text-decoration', + 'text-decoration-color', + 'text-decoration-line', + 'text-decoration-skip', + 'text-decoration-skip-ink', + 'text-decoration-style', + 'text-decoration-thickness', + 'text-emphasis', + 'text-emphasis-color', + 'text-emphasis-position', + 'text-emphasis-style', + 'text-indent', + 'text-justify', + 'text-orientation', + 'text-overflow', + 'text-rendering', + 'text-shadow', + 'text-size-adjust', + 'text-transform', + 'text-underline-offset', + 'text-underline-position', + 'text-wrap', + 'text-wrap-mode', + 'text-wrap-style', + 'timeline-scope', + 'top', + 'touch-action', + 'transform', + 'transform-box', + 'transform-origin', + 'transform-style', + 'transition', + 'transition-behavior', + 'transition-delay', + 'transition-duration', + 'transition-property', + 'transition-timing-function', + 'translate', + 'unicode-bidi', + 'user-modify', + 'user-select', + 'vector-effect', + 'vertical-align', + 'view-timeline', + 'view-timeline-axis', + 'view-timeline-inset', + 'view-timeline-name', + 'view-transition-name', + 'visibility', + 'voice-balance', + 'voice-duration', + 'voice-family', + 'voice-pitch', + 'voice-range', + 'voice-rate', + 'voice-stress', + 'voice-volume', + 'white-space', + 'white-space-collapse', + 'widows', + 'width', + 'will-change', + 'word-break', + 'word-spacing', + 'word-wrap', + 'writing-mode', + 'x', + 'y', + 'z-index', + 'zoom' +].sort().reverse(); + +/* +Language: CSS +Category: common, css, web +Website: https://developer.mozilla.org/en-US/docs/Web/CSS +*/ + + +/** @type LanguageFn */ +function css(hljs) { + const regex = hljs.regex; + const modes = MODES(hljs); + const VENDOR_PREFIX = { begin: /-(webkit|moz|ms|o)-(?=[a-z])/ }; + const AT_MODIFIERS = "and or not only"; + const AT_PROPERTY_RE = /@-?\w[\w]*(-\w+)*/; // @-webkit-keyframes + const IDENT_RE = '[a-zA-Z-][a-zA-Z0-9_-]*'; + const STRINGS = [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE + ]; + + return { + name: 'CSS', + case_insensitive: true, + illegal: /[=|'\$]/, + keywords: { keyframePosition: "from to" }, + classNameAliases: { + // for visual continuity with `tag {}` and because we + // don't have a great class for this? + keyframePosition: "selector-tag" }, + contains: [ + modes.BLOCK_COMMENT, + VENDOR_PREFIX, + // to recognize keyframe 40% etc which are outside the scope of our + // attribute value mode + modes.CSS_NUMBER_MODE, + { + className: 'selector-id', + begin: /#[A-Za-z0-9_-]+/, + relevance: 0 + }, + { + className: 'selector-class', + begin: '\\.' + IDENT_RE, + relevance: 0 + }, + modes.ATTRIBUTE_SELECTOR_MODE, + { + className: 'selector-pseudo', + variants: [ + { begin: ':(' + PSEUDO_CLASSES.join('|') + ')' }, + { begin: ':(:)?(' + PSEUDO_ELEMENTS.join('|') + ')' } + ] + }, + // we may actually need this (12/2020) + // { // pseudo-selector params + // begin: /\(/, + // end: /\)/, + // contains: [ hljs.CSS_NUMBER_MODE ] + // }, + modes.CSS_VARIABLE, + { + className: 'attribute', + begin: '\\b(' + ATTRIBUTES.join('|') + ')\\b' + }, + // attribute values + { + begin: /:/, + end: /[;}{]/, + contains: [ + modes.BLOCK_COMMENT, + modes.HEXCOLOR, + modes.IMPORTANT, + modes.CSS_NUMBER_MODE, + ...STRINGS, + // needed to highlight these as strings and to avoid issues with + // illegal characters that might be inside urls that would tigger the + // languages illegal stack + { + begin: /(url|data-uri)\(/, + end: /\)/, + relevance: 0, // from keywords + keywords: { built_in: "url data-uri" }, + contains: [ + ...STRINGS, + { + className: "string", + // any character other than `)` as in `url()` will be the start + // of a string, which ends with `)` (from the parent mode) + begin: /[^)]/, + endsWithParent: true, + excludeEnd: true + } + ] + }, + modes.FUNCTION_DISPATCH + ] + }, + { + begin: regex.lookahead(/@/), + end: '[{;]', + relevance: 0, + illegal: /:/, // break on Less variables @var: ... + contains: [ + { + className: 'keyword', + begin: AT_PROPERTY_RE + }, + { + begin: /\s/, + endsWithParent: true, + excludeEnd: true, + relevance: 0, + keywords: { + $pattern: /[a-z-]+/, + keyword: AT_MODIFIERS, + attribute: MEDIA_FEATURES.join(" ") + }, + contains: [ + { + begin: /[a-z-]+(?=:)/, + className: "attribute" + }, + ...STRINGS, + modes.CSS_NUMBER_MODE + ] + } + ] + }, + { + className: 'selector-tag', + begin: '\\b(' + TAGS.join('|') + ')\\b' + } + ] + }; +} + +export { css as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/css.js.js b/frontend/node_modules/highlight.js/es/languages/css.js.js new file mode 100644 index 0000000..5315f64 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/css.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/css" instead of "highlight.js/lib/languages/css.js"' + ); + } + } + emitWarning(); + import lang from './css.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/d.js b/frontend/node_modules/highlight.js/es/languages/d.js new file mode 100644 index 0000000..f164df5 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/d.js @@ -0,0 +1,272 @@ +/* +Language: D +Author: Aleksandar Ruzicic +Description: D is a language with C-like syntax and static typing. It pragmatically combines efficiency, control, and modeling power, with safety and programmer productivity. +Version: 1.0a +Website: https://dlang.org +Category: system +Date: 2012-04-08 +*/ + +/** + * Known issues: + * + * - invalid hex string literals will be recognized as a double quoted strings + * but 'x' at the beginning of string will not be matched + * + * - delimited string literals are not checked for matching end delimiter + * (not possible to do with js regexp) + * + * - content of token string is colored as a string (i.e. no keyword coloring inside a token string) + * also, content of token string is not validated to contain only valid D tokens + * + * - special token sequence rule is not strictly following D grammar (anything following #line + * up to the end of line is matched as special token sequence) + */ + +/** @type LanguageFn */ +function d(hljs) { + /** + * Language keywords + * + * @type {Object} + */ + const D_KEYWORDS = { + $pattern: hljs.UNDERSCORE_IDENT_RE, + keyword: + 'abstract alias align asm assert auto body break byte case cast catch class ' + + 'const continue debug default delete deprecated do else enum export extern final ' + + 'finally for foreach foreach_reverse|10 goto if immutable import in inout int ' + + 'interface invariant is lazy macro mixin module new nothrow out override package ' + + 'pragma private protected public pure ref return scope shared static struct ' + + 'super switch synchronized template this throw try typedef typeid typeof union ' + + 'unittest version void volatile while with __FILE__ __LINE__ __gshared|10 ' + + '__thread __traits __DATE__ __EOF__ __TIME__ __TIMESTAMP__ __VENDOR__ __VERSION__', + built_in: + 'bool cdouble cent cfloat char creal dchar delegate double dstring float function ' + + 'idouble ifloat ireal long real short string ubyte ucent uint ulong ushort wchar ' + + 'wstring', + literal: + 'false null true' + }; + + /** + * Number literal regexps + * + * @type {String} + */ + const decimal_integer_re = '(0|[1-9][\\d_]*)'; + const decimal_integer_nosus_re = '(0|[1-9][\\d_]*|\\d[\\d_]*|[\\d_]+?\\d)'; + const binary_integer_re = '0[bB][01_]+'; + const hexadecimal_digits_re = '([\\da-fA-F][\\da-fA-F_]*|_[\\da-fA-F][\\da-fA-F_]*)'; + const hexadecimal_integer_re = '0[xX]' + hexadecimal_digits_re; + + const decimal_exponent_re = '([eE][+-]?' + decimal_integer_nosus_re + ')'; + const decimal_float_re = '(' + decimal_integer_nosus_re + '(\\.\\d*|' + decimal_exponent_re + ')|' + + '\\d+\\.' + decimal_integer_nosus_re + '|' + + '\\.' + decimal_integer_re + decimal_exponent_re + '?' + + ')'; + const hexadecimal_float_re = '(0[xX](' + + hexadecimal_digits_re + '\\.' + hexadecimal_digits_re + '|' + + '\\.?' + hexadecimal_digits_re + + ')[pP][+-]?' + decimal_integer_nosus_re + ')'; + + const integer_re = '(' + + decimal_integer_re + '|' + + binary_integer_re + '|' + + hexadecimal_integer_re + + ')'; + + const float_re = '(' + + hexadecimal_float_re + '|' + + decimal_float_re + + ')'; + + /** + * Escape sequence supported in D string and character literals + * + * @type {String} + */ + const escape_sequence_re = '\\\\(' + + '[\'"\\?\\\\abfnrtv]|' // common escapes + + 'u[\\dA-Fa-f]{4}|' // four hex digit unicode codepoint + + '[0-7]{1,3}|' // one to three octal digit ascii char code + + 'x[\\dA-Fa-f]{2}|' // two hex digit ascii char code + + 'U[\\dA-Fa-f]{8}' // eight hex digit unicode codepoint + + ')|' + + '&[a-zA-Z\\d]{2,};'; // named character entity + + /** + * D integer number literals + * + * @type {Object} + */ + const D_INTEGER_MODE = { + className: 'number', + begin: '\\b' + integer_re + '(L|u|U|Lu|LU|uL|UL)?', + relevance: 0 + }; + + /** + * [D_FLOAT_MODE description] + * @type {Object} + */ + const D_FLOAT_MODE = { + className: 'number', + begin: '\\b(' + + float_re + '([fF]|L|i|[fF]i|Li)?|' + + integer_re + '(i|[fF]i|Li)' + + ')', + relevance: 0 + }; + + /** + * D character literal + * + * @type {Object} + */ + const D_CHARACTER_MODE = { + className: 'string', + begin: '\'(' + escape_sequence_re + '|.)', + end: '\'', + illegal: '.' + }; + + /** + * D string escape sequence + * + * @type {Object} + */ + const D_ESCAPE_SEQUENCE = { + begin: escape_sequence_re, + relevance: 0 + }; + + /** + * D double quoted string literal + * + * @type {Object} + */ + const D_STRING_MODE = { + className: 'string', + begin: '"', + contains: [ D_ESCAPE_SEQUENCE ], + end: '"[cwd]?' + }; + + /** + * D wysiwyg and delimited string literals + * + * @type {Object} + */ + const D_WYSIWYG_DELIMITED_STRING_MODE = { + className: 'string', + begin: '[rq]"', + end: '"[cwd]?', + relevance: 5 + }; + + /** + * D alternate wysiwyg string literal + * + * @type {Object} + */ + const D_ALTERNATE_WYSIWYG_STRING_MODE = { + className: 'string', + begin: '`', + end: '`[cwd]?' + }; + + /** + * D hexadecimal string literal + * + * @type {Object} + */ + const D_HEX_STRING_MODE = { + className: 'string', + begin: 'x"[\\da-fA-F\\s\\n\\r]*"[cwd]?', + relevance: 10 + }; + + /** + * D delimited string literal + * + * @type {Object} + */ + const D_TOKEN_STRING_MODE = { + className: 'string', + begin: 'q"\\{', + end: '\\}"' + }; + + /** + * Hashbang support + * + * @type {Object} + */ + const D_HASHBANG_MODE = { + className: 'meta', + begin: '^#!', + end: '$', + relevance: 5 + }; + + /** + * D special token sequence + * + * @type {Object} + */ + const D_SPECIAL_TOKEN_SEQUENCE_MODE = { + className: 'meta', + begin: '#(line)', + end: '$', + relevance: 5 + }; + + /** + * D attributes + * + * @type {Object} + */ + const D_ATTRIBUTE_MODE = { + className: 'keyword', + begin: '@[a-zA-Z_][a-zA-Z_\\d]*' + }; + + /** + * D nesting comment + * + * @type {Object} + */ + const D_NESTING_COMMENT_MODE = hljs.COMMENT( + '\\/\\+', + '\\+\\/', + { + contains: [ 'self' ], + relevance: 10 + } + ); + + return { + name: 'D', + keywords: D_KEYWORDS, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + D_NESTING_COMMENT_MODE, + D_HEX_STRING_MODE, + D_STRING_MODE, + D_WYSIWYG_DELIMITED_STRING_MODE, + D_ALTERNATE_WYSIWYG_STRING_MODE, + D_TOKEN_STRING_MODE, + D_FLOAT_MODE, + D_INTEGER_MODE, + D_CHARACTER_MODE, + D_HASHBANG_MODE, + D_SPECIAL_TOKEN_SEQUENCE_MODE, + D_ATTRIBUTE_MODE + ] + }; +} + +export { d as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/d.js.js b/frontend/node_modules/highlight.js/es/languages/d.js.js new file mode 100644 index 0000000..671b524 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/d.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/d" instead of "highlight.js/lib/languages/d.js"' + ); + } + } + emitWarning(); + import lang from './d.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/dart.js b/frontend/node_modules/highlight.js/es/languages/dart.js new file mode 100644 index 0000000..90c11a3 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/dart.js @@ -0,0 +1,271 @@ +/* +Language: Dart +Requires: markdown.js +Author: Maxim Dikun +Description: Dart a modern, object-oriented language developed by Google. For more information see https://www.dartlang.org/ +Website: https://dart.dev +Category: scripting +*/ + +/** @type LanguageFn */ +function dart(hljs) { + const SUBST = { + className: 'subst', + variants: [ { begin: '\\$[A-Za-z0-9_]+' } ] + }; + + const BRACED_SUBST = { + className: 'subst', + variants: [ + { + begin: /\$\{/, + end: /\}/ + } + ], + keywords: 'true false null this is new super' + }; + + const NUMBER = { + className: 'number', + relevance: 0, + variants: [ + { match: /\b[0-9][0-9_]*(\.[0-9][0-9_]*)?([eE][+-]?[0-9][0-9_]*)?\b/ }, + { match: /\b0[xX][0-9A-Fa-f][0-9A-Fa-f_]*\b/ } + ] + }; + + const STRING = { + className: 'string', + variants: [ + { + begin: 'r\'\'\'', + end: '\'\'\'' + }, + { + begin: 'r"""', + end: '"""' + }, + { + begin: 'r\'', + end: '\'', + illegal: '\\n' + }, + { + begin: 'r"', + end: '"', + illegal: '\\n' + }, + { + begin: '\'\'\'', + end: '\'\'\'', + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST, + BRACED_SUBST + ] + }, + { + begin: '"""', + end: '"""', + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST, + BRACED_SUBST + ] + }, + { + begin: '\'', + end: '\'', + illegal: '\\n', + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST, + BRACED_SUBST + ] + }, + { + begin: '"', + end: '"', + illegal: '\\n', + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST, + BRACED_SUBST + ] + } + ] + }; + BRACED_SUBST.contains = [ + NUMBER, + STRING + ]; + + const BUILT_IN_TYPES = [ + // dart:core + 'Comparable', + 'DateTime', + 'Duration', + 'Function', + 'Iterable', + 'Iterator', + 'List', + 'Map', + 'Match', + 'Object', + 'Pattern', + 'RegExp', + 'Set', + 'Stopwatch', + 'String', + 'StringBuffer', + 'StringSink', + 'Symbol', + 'Type', + 'Uri', + 'bool', + 'double', + 'int', + 'num', + // dart:html + 'Element', + 'ElementList' + ]; + const NULLABLE_BUILT_IN_TYPES = BUILT_IN_TYPES.map((e) => `${e}?`); + + const BASIC_KEYWORDS = [ + "abstract", + "as", + "assert", + "async", + "await", + "base", + "break", + "case", + "catch", + "class", + "const", + "continue", + "covariant", + "default", + "deferred", + "do", + "dynamic", + "else", + "enum", + "export", + "extends", + "extension", + "external", + "factory", + "false", + "final", + "finally", + "for", + "Function", + "get", + "hide", + "if", + "implements", + "import", + "in", + "interface", + "is", + "late", + "library", + "mixin", + "new", + "null", + "on", + "operator", + "part", + "required", + "rethrow", + "return", + "sealed", + "set", + "show", + "static", + "super", + "switch", + "sync", + "this", + "throw", + "true", + "try", + "typedef", + "var", + "void", + "when", + "while", + "with", + "yield" + ]; + + const KEYWORDS = { + keyword: BASIC_KEYWORDS, + built_in: + BUILT_IN_TYPES + .concat(NULLABLE_BUILT_IN_TYPES) + .concat([ + // dart:core + 'Never', + 'Null', + 'dynamic', + 'print', + // dart:html + 'document', + 'querySelector', + 'querySelectorAll', + 'window' + ]), + $pattern: /[A-Za-z][A-Za-z0-9_]*\??/ + }; + + return { + name: 'Dart', + keywords: KEYWORDS, + contains: [ + STRING, + hljs.COMMENT( + /\/\*\*(?!\/)/, + /\*\//, + { + subLanguage: 'markdown', + relevance: 0 + } + ), + hljs.COMMENT( + /\/{3,} ?/, + /$/, { contains: [ + { + subLanguage: 'markdown', + begin: '.', + end: '$', + relevance: 0 + } + ] } + ), + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + { + className: 'class', + beginKeywords: 'class interface', + end: /\{/, + excludeEnd: true, + contains: [ + { beginKeywords: 'extends implements' }, + hljs.UNDERSCORE_TITLE_MODE + ] + }, + NUMBER, + { + className: 'meta', + begin: '@[A-Za-z]+' + }, + { begin: '=>' // No markup, just a relevance booster + } + ] + }; +} + +export { dart as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/dart.js.js b/frontend/node_modules/highlight.js/es/languages/dart.js.js new file mode 100644 index 0000000..37cb15e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/dart.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/dart" instead of "highlight.js/lib/languages/dart.js"' + ); + } + } + emitWarning(); + import lang from './dart.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/delphi.js b/frontend/node_modules/highlight.js/es/languages/delphi.js new file mode 100644 index 0000000..1a41cbd --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/delphi.js @@ -0,0 +1,246 @@ +/* +Language: Delphi +Website: https://www.embarcadero.com/products/delphi +Category: system +*/ + +/** @type LanguageFn */ +function delphi(hljs) { + const KEYWORDS = [ + "exports", + "register", + "file", + "shl", + "array", + "record", + "property", + "for", + "mod", + "while", + "set", + "ally", + "label", + "uses", + "raise", + "not", + "stored", + "class", + "safecall", + "var", + "interface", + "or", + "private", + "static", + "exit", + "index", + "inherited", + "to", + "else", + "stdcall", + "override", + "shr", + "asm", + "far", + "resourcestring", + "finalization", + "packed", + "virtual", + "out", + "and", + "protected", + "library", + "do", + "xorwrite", + "goto", + "near", + "function", + "end", + "div", + "overload", + "object", + "unit", + "begin", + "string", + "on", + "inline", + "repeat", + "until", + "destructor", + "write", + "message", + "program", + "with", + "read", + "initialization", + "except", + "default", + "nil", + "if", + "case", + "cdecl", + "in", + "downto", + "threadvar", + "of", + "try", + "pascal", + "const", + "external", + "constructor", + "type", + "public", + "then", + "implementation", + "finally", + "published", + "procedure", + "absolute", + "reintroduce", + "operator", + "as", + "is", + "abstract", + "alias", + "assembler", + "bitpacked", + "break", + "continue", + "cppdecl", + "cvar", + "enumerator", + "experimental", + "platform", + "deprecated", + "unimplemented", + "dynamic", + "export", + "far16", + "forward", + "generic", + "helper", + "implements", + "interrupt", + "iochecks", + "local", + "name", + "nodefault", + "noreturn", + "nostackframe", + "oldfpccall", + "otherwise", + "saveregisters", + "softfloat", + "specialize", + "strict", + "unaligned", + "varargs" + ]; + const COMMENT_MODES = [ + hljs.C_LINE_COMMENT_MODE, + hljs.COMMENT(/\{/, /\}/, { relevance: 0 }), + hljs.COMMENT(/\(\*/, /\*\)/, { relevance: 10 }) + ]; + const DIRECTIVE = { + className: 'meta', + variants: [ + { + begin: /\{\$/, + end: /\}/ + }, + { + begin: /\(\*\$/, + end: /\*\)/ + } + ] + }; + const STRING = { + className: 'string', + begin: /'/, + end: /'/, + contains: [ { begin: /''/ } ] + }; + const NUMBER = { + className: 'number', + relevance: 0, + // Source: https://www.freepascal.org/docs-html/ref/refse6.html + variants: [ + { + // Regular numbers, e.g., 123, 123.456. + match: /\b\d[\d_]*(\.\d[\d_]*)?/ }, + { + // Hexadecimal notation, e.g., $7F. + match: /\$[\dA-Fa-f_]+/ }, + { + // Hexadecimal literal with no digits + match: /\$/, + relevance: 0 }, + { + // Octal notation, e.g., &42. + match: /&[0-7][0-7_]*/ }, + { + // Binary notation, e.g., %1010. + match: /%[01_]+/ }, + { + // Binary literal with no digits + match: /%/, + relevance: 0 } + ] + }; + const CHAR_STRING = { + className: 'string', + variants: [ + { match: /#\d[\d_]*/ }, + { match: /#\$[\dA-Fa-f][\dA-Fa-f_]*/ }, + { match: /#&[0-7][0-7_]*/ }, + { match: /#%[01][01_]*/ } + ] + }; + const CLASS = { + begin: hljs.IDENT_RE + '\\s*=\\s*class\\s*\\(', + returnBegin: true, + contains: [ hljs.TITLE_MODE ] + }; + const FUNCTION = { + className: 'function', + beginKeywords: 'function constructor destructor procedure', + end: /[:;]/, + keywords: 'function constructor|10 destructor|10 procedure|10', + contains: [ + hljs.TITLE_MODE, + { + className: 'params', + begin: /\(/, + end: /\)/, + keywords: KEYWORDS, + contains: [ + STRING, + CHAR_STRING, + DIRECTIVE + ].concat(COMMENT_MODES) + }, + DIRECTIVE + ].concat(COMMENT_MODES) + }; + return { + name: 'Delphi', + aliases: [ + 'dpr', + 'dfm', + 'pas', + 'pascal' + ], + case_insensitive: true, + keywords: KEYWORDS, + illegal: /"|\$[G-Zg-z]|\/\*|<\/|\|/, + contains: [ + STRING, + CHAR_STRING, + NUMBER, + CLASS, + FUNCTION, + DIRECTIVE + ].concat(COMMENT_MODES) + }; +} + +export { delphi as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/delphi.js.js b/frontend/node_modules/highlight.js/es/languages/delphi.js.js new file mode 100644 index 0000000..a18e4ee --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/delphi.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/delphi" instead of "highlight.js/lib/languages/delphi.js"' + ); + } + } + emitWarning(); + import lang from './delphi.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/diff.js b/frontend/node_modules/highlight.js/es/languages/diff.js new file mode 100644 index 0000000..878dffa --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/diff.js @@ -0,0 +1,62 @@ +/* +Language: Diff +Description: Unified and context diff +Author: Vasily Polovnyov +Website: https://www.gnu.org/software/diffutils/ +Category: common +*/ + +/** @type LanguageFn */ +function diff(hljs) { + const regex = hljs.regex; + return { + name: 'Diff', + aliases: [ 'patch' ], + contains: [ + { + className: 'meta', + relevance: 10, + match: regex.either( + /^@@ +-\d+,\d+ +\+\d+,\d+ +@@/, + /^\*\*\* +\d+,\d+ +\*\*\*\*$/, + /^--- +\d+,\d+ +----$/ + ) + }, + { + className: 'comment', + variants: [ + { + begin: regex.either( + /Index: /, + /^index/, + /={3,}/, + /^-{3}/, + /^\*{3} /, + /^\+{3}/, + /^diff --git/ + ), + end: /$/ + }, + { match: /^\*{15}$/ } + ] + }, + { + className: 'addition', + begin: /^\+/, + end: /$/ + }, + { + className: 'deletion', + begin: /^-/, + end: /$/ + }, + { + className: 'addition', + begin: /^!/, + end: /$/ + } + ] + }; +} + +export { diff as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/diff.js.js b/frontend/node_modules/highlight.js/es/languages/diff.js.js new file mode 100644 index 0000000..dcb2fc0 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/diff.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/diff" instead of "highlight.js/lib/languages/diff.js"' + ); + } + } + emitWarning(); + import lang from './diff.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/django.js b/frontend/node_modules/highlight.js/es/languages/django.js new file mode 100644 index 0000000..a4385ec --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/django.js @@ -0,0 +1,75 @@ +/* +Language: Django +Description: Django is a high-level Python Web framework that encourages rapid development and clean, pragmatic design. +Requires: xml.js +Author: Ivan Sagalaev +Contributors: Ilya Baryshev +Website: https://www.djangoproject.com +Category: template +*/ + +/** @type LanguageFn */ +function django(hljs) { + const FILTER = { + begin: /\|[A-Za-z]+:?/, + keywords: { name: + 'truncatewords removetags linebreaksbr yesno get_digit timesince random striptags ' + + 'filesizeformat escape linebreaks length_is ljust rjust cut urlize fix_ampersands ' + + 'title floatformat capfirst pprint divisibleby add make_list unordered_list urlencode ' + + 'timeuntil urlizetrunc wordcount stringformat linenumbers slice date dictsort ' + + 'dictsortreversed default_if_none pluralize lower join center default ' + + 'truncatewords_html upper length phone2numeric wordwrap time addslashes slugify first ' + + 'escapejs force_escape iriencode last safe safeseq truncatechars localize unlocalize ' + + 'localtime utc timezone' }, + contains: [ + hljs.QUOTE_STRING_MODE, + hljs.APOS_STRING_MODE + ] + }; + + return { + name: 'Django', + aliases: [ 'jinja' ], + case_insensitive: true, + subLanguage: 'xml', + contains: [ + hljs.COMMENT(/\{%\s*comment\s*%\}/, /\{%\s*endcomment\s*%\}/), + hljs.COMMENT(/\{#/, /#\}/), + { + className: 'template-tag', + begin: /\{%/, + end: /%\}/, + contains: [ + { + className: 'name', + begin: /\w+/, + keywords: { name: + 'comment endcomment load templatetag ifchanged endifchanged if endif firstof for ' + + 'endfor ifnotequal endifnotequal widthratio extends include spaceless ' + + 'endspaceless regroup ifequal endifequal ssi now with cycle url filter ' + + 'endfilter debug block endblock else autoescape endautoescape csrf_token empty elif ' + + 'endwith static trans blocktrans endblocktrans get_static_prefix get_media_prefix ' + + 'plural get_current_language language get_available_languages ' + + 'get_current_language_bidi get_language_info get_language_info_list localize ' + + 'endlocalize localtime endlocaltime timezone endtimezone get_current_timezone ' + + 'verbatim' }, + starts: { + endsWithParent: true, + keywords: 'in by as', + contains: [ FILTER ], + relevance: 0 + } + } + ] + }, + { + className: 'template-variable', + begin: /\{\{/, + end: /\}\}/, + contains: [ FILTER ] + } + ] + }; +} + +export { django as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/django.js.js b/frontend/node_modules/highlight.js/es/languages/django.js.js new file mode 100644 index 0000000..21e96c6 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/django.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/django" instead of "highlight.js/lib/languages/django.js"' + ); + } + } + emitWarning(); + import lang from './django.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/dns.js b/frontend/node_modules/highlight.js/es/languages/dns.js new file mode 100644 index 0000000..dbdb38d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/dns.js @@ -0,0 +1,78 @@ +/* +Language: DNS Zone +Author: Tim Schumacher +Category: config +Website: https://en.wikipedia.org/wiki/Zone_file +*/ + +/** @type LanguageFn */ +function dns(hljs) { + const KEYWORDS = [ + "IN", + "A", + "AAAA", + "AFSDB", + "APL", + "CAA", + "CDNSKEY", + "CDS", + "CERT", + "CNAME", + "DHCID", + "DLV", + "DNAME", + "DNSKEY", + "DS", + "HIP", + "IPSECKEY", + "KEY", + "KX", + "LOC", + "MX", + "NAPTR", + "NS", + "NSEC", + "NSEC3", + "NSEC3PARAM", + "PTR", + "RRSIG", + "RP", + "SIG", + "SOA", + "SRV", + "SSHFP", + "TA", + "TKEY", + "TLSA", + "TSIG", + "TXT" + ]; + return { + name: 'DNS Zone', + aliases: [ + 'bind', + 'zone' + ], + keywords: KEYWORDS, + contains: [ + hljs.COMMENT(';', '$', { relevance: 0 }), + { + className: 'meta', + begin: /^\$(TTL|GENERATE|INCLUDE|ORIGIN)\b/ + }, + // IPv6 + { + className: 'number', + begin: '((([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))|(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})|:((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3}))|:))|(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3}))|:))|(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3}))|:)))\\b' + }, + // IPv4 + { + className: 'number', + begin: '((25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])\.){3,3}(25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])\\b' + }, + hljs.inherit(hljs.NUMBER_MODE, { begin: /\b\d+[dhwm]?/ }) + ] + }; +} + +export { dns as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/dns.js.js b/frontend/node_modules/highlight.js/es/languages/dns.js.js new file mode 100644 index 0000000..e904d28 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/dns.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/dns" instead of "highlight.js/lib/languages/dns.js"' + ); + } + } + emitWarning(); + import lang from './dns.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/dockerfile.js b/frontend/node_modules/highlight.js/es/languages/dockerfile.js new file mode 100644 index 0000000..7d52b86 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/dockerfile.js @@ -0,0 +1,44 @@ +/* +Language: Dockerfile +Requires: bash.js +Author: Alexis Hénaut +Description: language definition for Dockerfile files +Website: https://docs.docker.com/engine/reference/builder/ +Category: config +*/ + +/** @type LanguageFn */ +function dockerfile(hljs) { + const KEYWORDS = [ + "from", + "maintainer", + "expose", + "env", + "arg", + "user", + "onbuild", + "stopsignal" + ]; + return { + name: 'Dockerfile', + aliases: [ 'docker' ], + case_insensitive: true, + keywords: KEYWORDS, + contains: [ + hljs.HASH_COMMENT_MODE, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.NUMBER_MODE, + { + beginKeywords: 'run cmd entrypoint volume add copy workdir label healthcheck shell', + starts: { + end: /[^\\]$/, + subLanguage: 'bash' + } + } + ], + illegal: ' +Contributors: Anton Kochkov +Website: https://en.wikipedia.org/wiki/Batch_file +Category: scripting +*/ + +/** @type LanguageFn */ +function dos(hljs) { + const COMMENT = hljs.COMMENT( + /^\s*@?rem\b/, /$/, + { relevance: 10 } + ); + const LABEL = { + className: 'symbol', + begin: '^\\s*[A-Za-z._?][A-Za-z0-9_$#@~.?]*(:|\\s+label)', + relevance: 0 + }; + const KEYWORDS = [ + "if", + "else", + "goto", + "for", + "in", + "do", + "call", + "exit", + "not", + "exist", + "errorlevel", + "defined", + "equ", + "neq", + "lss", + "leq", + "gtr", + "geq" + ]; + const BUILT_INS = [ + "prn", + "nul", + "lpt3", + "lpt2", + "lpt1", + "con", + "com4", + "com3", + "com2", + "com1", + "aux", + "shift", + "cd", + "dir", + "echo", + "setlocal", + "endlocal", + "set", + "pause", + "copy", + "append", + "assoc", + "at", + "attrib", + "break", + "cacls", + "cd", + "chcp", + "chdir", + "chkdsk", + "chkntfs", + "cls", + "cmd", + "color", + "comp", + "compact", + "convert", + "date", + "dir", + "diskcomp", + "diskcopy", + "doskey", + "erase", + "fs", + "find", + "findstr", + "format", + "ftype", + "graftabl", + "help", + "keyb", + "label", + "md", + "mkdir", + "mode", + "more", + "move", + "path", + "pause", + "print", + "popd", + "pushd", + "promt", + "rd", + "recover", + "rem", + "rename", + "replace", + "restore", + "rmdir", + "shift", + "sort", + "start", + "subst", + "time", + "title", + "tree", + "type", + "ver", + "verify", + "vol", + // winutils + "ping", + "net", + "ipconfig", + "taskkill", + "xcopy", + "ren", + "del" + ]; + return { + name: 'Batch file (DOS)', + aliases: [ + 'bat', + 'cmd' + ], + case_insensitive: true, + illegal: /\/\*/, + keywords: { + keyword: KEYWORDS, + built_in: BUILT_INS + }, + contains: [ + { + className: 'variable', + begin: /%%[^ ]|%[^ ]+?%|![^ ]+?!/ + }, + { + className: 'function', + begin: LABEL.begin, + end: 'goto:eof', + contains: [ + hljs.inherit(hljs.TITLE_MODE, { begin: '([_a-zA-Z]\\w*\\.)*([_a-zA-Z]\\w*:)?[_a-zA-Z]\\w*' }), + COMMENT + ] + }, + { + className: 'number', + begin: '\\b\\d+', + relevance: 0 + }, + COMMENT + ] + }; +} + +export { dos as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/dos.js.js b/frontend/node_modules/highlight.js/es/languages/dos.js.js new file mode 100644 index 0000000..c8e0927 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/dos.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/dos" instead of "highlight.js/lib/languages/dos.js"' + ); + } + } + emitWarning(); + import lang from './dos.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/dsconfig.js b/frontend/node_modules/highlight.js/es/languages/dsconfig.js new file mode 100644 index 0000000..163975b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/dsconfig.js @@ -0,0 +1,66 @@ +/* + Language: dsconfig + Description: dsconfig batch configuration language for LDAP directory servers + Contributors: Jacob Childress + Category: enterprise, config + */ + +/** @type LanguageFn */ +function dsconfig(hljs) { + const QUOTED_PROPERTY = { + className: 'string', + begin: /"/, + end: /"/ + }; + const APOS_PROPERTY = { + className: 'string', + begin: /'/, + end: /'/ + }; + const UNQUOTED_PROPERTY = { + className: 'string', + begin: /[\w\-?]+:\w+/, + end: /\W/, + relevance: 0 + }; + const VALUELESS_PROPERTY = { + className: 'string', + begin: /\w+(\-\w+)*/, + end: /(?=\W)/, + relevance: 0 + }; + + return { + keywords: 'dsconfig', + contains: [ + { + className: 'keyword', + begin: '^dsconfig', + end: /\s/, + excludeEnd: true, + relevance: 10 + }, + { + className: 'built_in', + begin: /(list|create|get|set|delete)-(\w+)/, + end: /\s/, + excludeEnd: true, + illegal: '!@#$%^&*()', + relevance: 10 + }, + { + className: 'built_in', + begin: /--(\w+)/, + end: /\s/, + excludeEnd: true + }, + QUOTED_PROPERTY, + APOS_PROPERTY, + UNQUOTED_PROPERTY, + VALUELESS_PROPERTY, + hljs.HASH_COMMENT_MODE + ] + }; +} + +export { dsconfig as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/dsconfig.js.js b/frontend/node_modules/highlight.js/es/languages/dsconfig.js.js new file mode 100644 index 0000000..7f3b38d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/dsconfig.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/dsconfig" instead of "highlight.js/lib/languages/dsconfig.js"' + ); + } + } + emitWarning(); + import lang from './dsconfig.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/dts.js b/frontend/node_modules/highlight.js/es/languages/dts.js new file mode 100644 index 0000000..8e8356a --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/dts.js @@ -0,0 +1,157 @@ +/* +Language: Device Tree +Description: *.dts files used in the Linux kernel +Author: Martin Braun , Moritz Fischer +Website: https://elinux.org/Device_Tree_Reference +Category: config +*/ + +/** @type LanguageFn */ +function dts(hljs) { + const STRINGS = { + className: 'string', + variants: [ + hljs.inherit(hljs.QUOTE_STRING_MODE, { begin: '((u8?|U)|L)?"' }), + { + begin: '(u8?|U)?R"', + end: '"', + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: '\'\\\\?.', + end: '\'', + illegal: '.' + } + ] + }; + + const NUMBERS = { + className: 'number', + variants: [ + { begin: '\\b(\\d+(\\.\\d*)?|\\.\\d+)(u|U|l|L|ul|UL|f|F)' }, + { begin: hljs.C_NUMBER_RE } + ], + relevance: 0 + }; + + const PREPROCESSOR = { + className: 'meta', + begin: '#', + end: '$', + keywords: { keyword: 'if else elif endif define undef ifdef ifndef' }, + contains: [ + { + begin: /\\\n/, + relevance: 0 + }, + { + beginKeywords: 'include', + end: '$', + keywords: { keyword: 'include' }, + contains: [ + hljs.inherit(STRINGS, { className: 'string' }), + { + className: 'string', + begin: '<', + end: '>', + illegal: '\\n' + } + ] + }, + STRINGS, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }; + + const REFERENCE = { + className: 'variable', + begin: /&[a-z\d_]*\b/ + }; + + const KEYWORD = { + className: 'keyword', + begin: '/[a-z][a-z\\d-]*/' + }; + + const LABEL = { + className: 'symbol', + begin: '^\\s*[a-zA-Z_][a-zA-Z\\d_]*:' + }; + + const CELL_PROPERTY = { + className: 'params', + relevance: 0, + begin: '<', + end: '>', + contains: [ + NUMBERS, + REFERENCE + ] + }; + + const NODE = { + className: 'title.class', + begin: /[a-zA-Z_][a-zA-Z\d_@-]*(?=\s\{)/, + relevance: 0.2 + }; + + const ROOT_NODE = { + className: 'title.class', + begin: /^\/(?=\s*\{)/, + relevance: 10 + }; + + // TODO: `attribute` might be the right scope here, unsure + // I'm not sure if all these key names have semantic meaning or not + const ATTR_NO_VALUE = { + match: /[a-z][a-z-,]+(?=;)/, + relevance: 0, + scope: "attr" + }; + const ATTR = { + relevance: 0, + match: [ + /[a-z][a-z-,]+/, + /\s*/, + /=/ + ], + scope: { + 1: "attr", + 3: "operator" + } + }; + + const PUNC = { + scope: "punctuation", + relevance: 0, + // `};` combined is just to avoid tons of useless punctuation nodes + match: /\};|[;{}]/ + }; + + return { + name: 'Device Tree', + contains: [ + ROOT_NODE, + REFERENCE, + KEYWORD, + LABEL, + NODE, + ATTR, + ATTR_NO_VALUE, + CELL_PROPERTY, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + NUMBERS, + STRINGS, + PREPROCESSOR, + PUNC, + { + begin: hljs.IDENT_RE + '::', + keywords: "" + } + ] + }; +} + +export { dts as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/dts.js.js b/frontend/node_modules/highlight.js/es/languages/dts.js.js new file mode 100644 index 0000000..26019f6 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/dts.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/dts" instead of "highlight.js/lib/languages/dts.js"' + ); + } + } + emitWarning(); + import lang from './dts.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/dust.js b/frontend/node_modules/highlight.js/es/languages/dust.js new file mode 100644 index 0000000..3e02c49 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/dust.js @@ -0,0 +1,47 @@ +/* +Language: Dust +Requires: xml.js +Author: Michael Allen +Description: Matcher for dust.js templates. +Website: https://www.dustjs.com +Category: template +*/ + +/** @type LanguageFn */ +function dust(hljs) { + const EXPRESSION_KEYWORDS = 'if eq ne lt lte gt gte select default math sep'; + return { + name: 'Dust', + aliases: [ 'dst' ], + case_insensitive: true, + subLanguage: 'xml', + contains: [ + { + className: 'template-tag', + begin: /\{[#\/]/, + end: /\}/, + illegal: /;/, + contains: [ + { + className: 'name', + begin: /[a-zA-Z\.-]+/, + starts: { + endsWithParent: true, + relevance: 0, + contains: [ hljs.QUOTE_STRING_MODE ] + } + } + ] + }, + { + className: 'template-variable', + begin: /\{/, + end: /\}/, + illegal: /;/, + keywords: EXPRESSION_KEYWORDS + } + ] + }; +} + +export { dust as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/dust.js.js b/frontend/node_modules/highlight.js/es/languages/dust.js.js new file mode 100644 index 0000000..87b8c38 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/dust.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/dust" instead of "highlight.js/lib/languages/dust.js"' + ); + } + } + emitWarning(); + import lang from './dust.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/ebnf.js b/frontend/node_modules/highlight.js/es/languages/ebnf.js new file mode 100644 index 0000000..e512caf --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ebnf.js @@ -0,0 +1,54 @@ +/* +Language: Extended Backus-Naur Form +Author: Alex McKibben +Website: https://en.wikipedia.org/wiki/Extended_Backus–Naur_form +Category: syntax +*/ + +/** @type LanguageFn */ +function ebnf(hljs) { + const commentMode = hljs.COMMENT(/\(\*/, /\*\)/); + + const nonTerminalMode = { + className: "attribute", + begin: /^[ ]*[a-zA-Z]+([\s_-]+[a-zA-Z]+)*/ + }; + + const specialSequenceMode = { + className: "meta", + begin: /\?.*\?/ + }; + + const ruleBodyMode = { + begin: /=/, + end: /[.;]/, + contains: [ + commentMode, + specialSequenceMode, + { + // terminals + className: 'string', + variants: [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + { + begin: '`', + end: '`' + } + ] + } + ] + }; + + return { + name: 'Extended Backus-Naur Form', + illegal: /\S/, + contains: [ + commentMode, + nonTerminalMode, + ruleBodyMode + ] + }; +} + +export { ebnf as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/ebnf.js.js b/frontend/node_modules/highlight.js/es/languages/ebnf.js.js new file mode 100644 index 0000000..187a47f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ebnf.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/ebnf" instead of "highlight.js/lib/languages/ebnf.js"' + ); + } + } + emitWarning(); + import lang from './ebnf.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/elixir.js b/frontend/node_modules/highlight.js/es/languages/elixir.js new file mode 100644 index 0000000..ff2c179 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/elixir.js @@ -0,0 +1,279 @@ +/* +Language: Elixir +Author: Josh Adams +Description: language definition for Elixir source code files (.ex and .exs). Based on ruby language support. +Category: functional +Website: https://elixir-lang.org +*/ + +/** @type LanguageFn */ +function elixir(hljs) { + const regex = hljs.regex; + const ELIXIR_IDENT_RE = '[a-zA-Z_][a-zA-Z0-9_.]*(!|\\?)?'; + const ELIXIR_METHOD_RE = '[a-zA-Z_]\\w*[!?=]?|[-+~]@|<<|>>|=~|===?|<=>|[<>]=?|\\*\\*|[-/+%^&*~`|]|\\[\\]=?'; + const KEYWORDS = [ + "after", + "alias", + "and", + "case", + "catch", + "cond", + "defstruct", + "defguard", + "do", + "else", + "end", + "fn", + "for", + "if", + "import", + "in", + "not", + "or", + "quote", + "raise", + "receive", + "require", + "reraise", + "rescue", + "try", + "unless", + "unquote", + "unquote_splicing", + "use", + "when", + "with|0" + ]; + const LITERALS = [ + "false", + "nil", + "true" + ]; + const KWS = { + $pattern: ELIXIR_IDENT_RE, + keyword: KEYWORDS, + literal: LITERALS + }; + const SUBST = { + className: 'subst', + begin: /#\{/, + end: /\}/, + keywords: KWS + }; + const NUMBER = { + className: 'number', + begin: '(\\b0o[0-7_]+)|(\\b0b[01_]+)|(\\b0x[0-9a-fA-F_]+)|(-?\\b[0-9][0-9_]*(\\.[0-9_]+([eE][-+]?[0-9]+)?)?)', + relevance: 0 + }; + // TODO: could be tightened + // https://elixir-lang.readthedocs.io/en/latest/intro/18.html + // but you also need to include closing delemeters in the escape list per + // individual sigil mode from what I can tell, + // ie: \} might or might not be an escape depending on the sigil used + const ESCAPES_RE = /\\[\s\S]/; + // const ESCAPES_RE = /\\["'\\abdefnrstv0]/; + const BACKSLASH_ESCAPE = { + match: ESCAPES_RE, + scope: "char.escape", + relevance: 0 + }; + const SIGIL_DELIMITERS = '[/|([{<"\']'; + const SIGIL_DELIMITER_MODES = [ + { + begin: /"/, + end: /"/ + }, + { + begin: /'/, + end: /'/ + }, + { + begin: /\//, + end: /\// + }, + { + begin: /\|/, + end: /\|/ + }, + { + begin: /\(/, + end: /\)/ + }, + { + begin: /\[/, + end: /\]/ + }, + { + begin: /\{/, + end: /\}/ + }, + { + begin: // + } + ]; + const escapeSigilEnd = (end) => { + return { + scope: "char.escape", + begin: regex.concat(/\\/, end), + relevance: 0 + }; + }; + const LOWERCASE_SIGIL = { + className: 'string', + begin: '~[a-z]' + '(?=' + SIGIL_DELIMITERS + ')', + contains: SIGIL_DELIMITER_MODES.map(x => hljs.inherit(x, + { contains: [ + escapeSigilEnd(x.end), + BACKSLASH_ESCAPE, + SUBST + ] } + )) + }; + + const UPCASE_SIGIL = { + className: 'string', + begin: '~[A-Z]' + '(?=' + SIGIL_DELIMITERS + ')', + contains: SIGIL_DELIMITER_MODES.map(x => hljs.inherit(x, + { contains: [ escapeSigilEnd(x.end) ] } + )) + }; + + const REGEX_SIGIL = { + className: 'regex', + variants: [ + { + begin: '~r' + '(?=' + SIGIL_DELIMITERS + ')', + contains: SIGIL_DELIMITER_MODES.map(x => hljs.inherit(x, + { + end: regex.concat(x.end, /[uismxfU]{0,7}/), + contains: [ + escapeSigilEnd(x.end), + BACKSLASH_ESCAPE, + SUBST + ] + } + )) + }, + { + begin: '~R' + '(?=' + SIGIL_DELIMITERS + ')', + contains: SIGIL_DELIMITER_MODES.map(x => hljs.inherit(x, + { + end: regex.concat(x.end, /[uismxfU]{0,7}/), + contains: [ escapeSigilEnd(x.end) ] + }) + ) + } + ] + }; + + const STRING = { + className: 'string', + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST + ], + variants: [ + { + begin: /"""/, + end: /"""/ + }, + { + begin: /'''/, + end: /'''/ + }, + { + begin: /~S"""/, + end: /"""/, + contains: [] // override default + }, + { + begin: /~S"/, + end: /"/, + contains: [] // override default + }, + { + begin: /~S'''/, + end: /'''/, + contains: [] // override default + }, + { + begin: /~S'/, + end: /'/, + contains: [] // override default + }, + { + begin: /'/, + end: /'/ + }, + { + begin: /"/, + end: /"/ + } + ] + }; + const FUNCTION = { + className: 'function', + beginKeywords: 'def defp defmacro defmacrop', + end: /\B\b/, // the mode is ended by the title + contains: [ + hljs.inherit(hljs.TITLE_MODE, { + begin: ELIXIR_IDENT_RE, + endsParent: true + }) + ] + }; + const CLASS = hljs.inherit(FUNCTION, { + className: 'class', + beginKeywords: 'defimpl defmodule defprotocol defrecord', + end: /\bdo\b|$|;/ + }); + const ELIXIR_DEFAULT_CONTAINS = [ + STRING, + REGEX_SIGIL, + UPCASE_SIGIL, + LOWERCASE_SIGIL, + hljs.HASH_COMMENT_MODE, + CLASS, + FUNCTION, + { begin: '::' }, + { + className: 'symbol', + begin: ':(?![\\s:])', + contains: [ + STRING, + { begin: ELIXIR_METHOD_RE } + ], + relevance: 0 + }, + { + className: 'symbol', + begin: ELIXIR_IDENT_RE + ':(?!:)', + relevance: 0 + }, + { // Usage of a module, struct, etc. + className: 'title.class', + begin: /(\b[A-Z][a-zA-Z0-9_]+)/, + relevance: 0 + }, + NUMBER, + { + className: 'variable', + begin: '(\\$\\W)|((\\$|@@?)(\\w+))' + } + // -> has been removed, capnproto always uses this grammar construct + ]; + SUBST.contains = ELIXIR_DEFAULT_CONTAINS; + + return { + name: 'Elixir', + aliases: [ + 'ex', + 'exs' + ], + keywords: KWS, + contains: ELIXIR_DEFAULT_CONTAINS + }; +} + +export { elixir as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/elixir.js.js b/frontend/node_modules/highlight.js/es/languages/elixir.js.js new file mode 100644 index 0000000..cedb747 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/elixir.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/elixir" instead of "highlight.js/lib/languages/elixir.js"' + ); + } + } + emitWarning(); + import lang from './elixir.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/elm.js b/frontend/node_modules/highlight.js/es/languages/elm.js new file mode 100644 index 0000000..30eed5f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/elm.js @@ -0,0 +1,143 @@ +/* +Language: Elm +Author: Janis Voigtlaender +Website: https://elm-lang.org +Category: functional +*/ + +/** @type LanguageFn */ +function elm(hljs) { + const COMMENT = { variants: [ + hljs.COMMENT('--', '$'), + hljs.COMMENT( + /\{-/, + /-\}/, + { contains: [ 'self' ] } + ) + ] }; + + const CONSTRUCTOR = { + className: 'type', + begin: '\\b[A-Z][\\w\']*', // TODO: other constructors (built-in, infix). + relevance: 0 + }; + + const LIST = { + begin: '\\(', + end: '\\)', + illegal: '"', + contains: [ + { + className: 'type', + begin: '\\b[A-Z][\\w]*(\\((\\.\\.|,|\\w+)\\))?' + }, + COMMENT + ] + }; + + const RECORD = { + begin: /\{/, + end: /\}/, + contains: LIST.contains + }; + + const CHARACTER = { + className: 'string', + begin: '\'\\\\?.', + end: '\'', + illegal: '.' + }; + + const KEYWORDS = [ + "let", + "in", + "if", + "then", + "else", + "case", + "of", + "where", + "module", + "import", + "exposing", + "type", + "alias", + "as", + "infix", + "infixl", + "infixr", + "port", + "effect", + "command", + "subscription" + ]; + + return { + name: 'Elm', + keywords: KEYWORDS, + contains: [ + + // Top-level constructions. + + { + beginKeywords: 'port effect module', + end: 'exposing', + keywords: 'port effect module where command subscription exposing', + contains: [ + LIST, + COMMENT + ], + illegal: '\\W\\.|;' + }, + { + begin: 'import', + end: '$', + keywords: 'import as exposing', + contains: [ + LIST, + COMMENT + ], + illegal: '\\W\\.|;' + }, + { + begin: 'type', + end: '$', + keywords: 'type alias', + contains: [ + CONSTRUCTOR, + LIST, + RECORD, + COMMENT + ] + }, + { + beginKeywords: 'infix infixl infixr', + end: '$', + contains: [ + hljs.C_NUMBER_MODE, + COMMENT + ] + }, + { + begin: 'port', + end: '$', + keywords: 'port', + contains: [ COMMENT ] + }, + + // Literals and names. + CHARACTER, + hljs.QUOTE_STRING_MODE, + hljs.C_NUMBER_MODE, + CONSTRUCTOR, + hljs.inherit(hljs.TITLE_MODE, { begin: '^[_a-z][\\w\']*' }), + COMMENT, + + { // No markup, relevance booster + begin: '->|<-' } + ], + illegal: /;/ + }; +} + +export { elm as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/elm.js.js b/frontend/node_modules/highlight.js/es/languages/elm.js.js new file mode 100644 index 0000000..8d84af0 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/elm.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/elm" instead of "highlight.js/lib/languages/elm.js"' + ); + } + } + emitWarning(); + import lang from './elm.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/erb.js b/frontend/node_modules/highlight.js/es/languages/erb.js new file mode 100644 index 0000000..7ea3e4b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/erb.js @@ -0,0 +1,29 @@ +/* +Language: ERB (Embedded Ruby) +Requires: xml.js, ruby.js +Author: Lucas Mazza +Contributors: Kassio Borges +Description: "Bridge" language defining fragments of Ruby in HTML within <% .. %> +Website: https://ruby-doc.org/stdlib-2.6.5/libdoc/erb/rdoc/ERB.html +Category: template +*/ + +/** @type LanguageFn */ +function erb(hljs) { + return { + name: 'ERB', + subLanguage: 'xml', + contains: [ + hljs.COMMENT('<%#', '%>'), + { + begin: '<%[%=-]?', + end: '[%-]?%>', + subLanguage: 'ruby', + excludeBegin: true, + excludeEnd: true + } + ] + }; +} + +export { erb as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/erb.js.js b/frontend/node_modules/highlight.js/es/languages/erb.js.js new file mode 100644 index 0000000..8223529 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/erb.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/erb" instead of "highlight.js/lib/languages/erb.js"' + ); + } + } + emitWarning(); + import lang from './erb.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/erlang-repl.js b/frontend/node_modules/highlight.js/es/languages/erlang-repl.js new file mode 100644 index 0000000..9e90533 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/erlang-repl.js @@ -0,0 +1,54 @@ +/* +Language: Erlang REPL +Author: Sergey Ignatov +Website: https://www.erlang.org +Category: functional +*/ + +/** @type LanguageFn */ +function erlangRepl(hljs) { + const regex = hljs.regex; + return { + name: 'Erlang REPL', + keywords: { + built_in: + 'spawn spawn_link self', + keyword: + 'after and andalso|10 band begin bnot bor bsl bsr bxor case catch cond div end fun if ' + + 'let not of or orelse|10 query receive rem try when xor' + }, + contains: [ + { + className: 'meta.prompt', + begin: '^[0-9]+> ', + relevance: 10 + }, + hljs.COMMENT('%', '$'), + { + className: 'number', + begin: '\\b(\\d+(_\\d+)*#[a-fA-F0-9]+(_[a-fA-F0-9]+)*|\\d+(_\\d+)*(\\.\\d+(_\\d+)*)?([eE][-+]?\\d+)?)', + relevance: 0 + }, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + { begin: regex.concat( + /\?(::)?/, + /([A-Z]\w*)/, // at least one identifier + /((::)[A-Z]\w*)*/ // perhaps more + ) }, + { begin: '->' }, + { begin: 'ok' }, + { begin: '!' }, + { + begin: '(\\b[a-z\'][a-zA-Z0-9_\']*:[a-z\'][a-zA-Z0-9_\']*)|(\\b[a-z\'][a-zA-Z0-9_\']*)', + relevance: 0 + }, + { + begin: '[A-Z][a-zA-Z0-9_\']*', + relevance: 0 + } + ] + }; +} + +export { erlangRepl as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/erlang-repl.js.js b/frontend/node_modules/highlight.js/es/languages/erlang-repl.js.js new file mode 100644 index 0000000..52db750 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/erlang-repl.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/erlang-repl" instead of "highlight.js/lib/languages/erlang-repl.js"' + ); + } + } + emitWarning(); + import lang from './erlang-repl.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/erlang.js b/frontend/node_modules/highlight.js/es/languages/erlang.js new file mode 100644 index 0000000..7243da2 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/erlang.js @@ -0,0 +1,235 @@ +/* +Language: Erlang +Description: Erlang is a general-purpose functional language, with strict evaluation, single assignment, and dynamic typing. +Author: Nikolay Zakharov , Dmitry Kovega +Website: https://www.erlang.org +Category: functional +*/ + +/** @type LanguageFn */ +function erlang(hljs) { + const BASIC_ATOM_RE = '[a-z\'][a-zA-Z0-9_\']*'; + const FUNCTION_NAME_RE = '(' + BASIC_ATOM_RE + ':' + BASIC_ATOM_RE + '|' + BASIC_ATOM_RE + ')'; + const ERLANG_RESERVED = { + keyword: + 'after and andalso|10 band begin bnot bor bsl bzr bxor case catch cond div end fun if ' + + 'let not of orelse|10 query receive rem try when xor maybe else', + literal: + 'false true' + }; + + const COMMENT = hljs.COMMENT('%', '$'); + const NUMBER = { + className: 'number', + begin: '\\b(\\d+(_\\d+)*#[a-fA-F0-9]+(_[a-fA-F0-9]+)*|\\d+(_\\d+)*(\\.\\d+(_\\d+)*)?([eE][-+]?\\d+)?)', + relevance: 0 + }; + const NAMED_FUN = { begin: 'fun\\s+' + BASIC_ATOM_RE + '/\\d+' }; + const FUNCTION_CALL = { + begin: FUNCTION_NAME_RE + '\\(', + end: '\\)', + returnBegin: true, + relevance: 0, + contains: [ + { + begin: FUNCTION_NAME_RE, + relevance: 0 + }, + { + begin: '\\(', + end: '\\)', + endsWithParent: true, + returnEnd: true, + relevance: 0 + // "contains" defined later + } + ] + }; + const TUPLE = { + begin: /\{/, + end: /\}/, + relevance: 0 + // "contains" defined later + }; + const VAR1 = { + begin: '\\b_([A-Z][A-Za-z0-9_]*)?', + relevance: 0 + }; + const VAR2 = { + begin: '[A-Z][a-zA-Z0-9_]*', + relevance: 0 + }; + const RECORD_ACCESS = { + begin: '#' + hljs.UNDERSCORE_IDENT_RE, + relevance: 0, + returnBegin: true, + contains: [ + { + begin: '#' + hljs.UNDERSCORE_IDENT_RE, + relevance: 0 + }, + { + begin: /\{/, + end: /\}/, + relevance: 0 + // "contains" defined later + } + ] + }; + const CHAR_LITERAL = { + scope: 'string', + match: /\$(\\([^0-9]|[0-9]{1,3}|)|.)/, + }; + const TRIPLE_QUOTE = { + scope: 'string', + match: /"""("*)(?!")[\s\S]*?"""\1/, + }; + + const SIGIL = { + scope: 'string', + contains: [ hljs.BACKSLASH_ESCAPE ], + variants: [ + {match: /~\w?"""("*)(?!")[\s\S]*?"""\1/}, + {begin: /~\w?\(/, end: /\)/}, + {begin: /~\w?\[/, end: /\]/}, + {begin: /~\w?{/, end: /}/}, + {begin: /~\w?/}, + {begin: /~\w?\//, end: /\//}, + {begin: /~\w?\|/, end: /\|/}, + {begin: /~\w?'/, end: /'/}, + {begin: /~\w?"/, end: /"/}, + {begin: /~\w?`/, end: /`/}, + {begin: /~\w?#/, end: /#/}, + ], + }; + + const BLOCK_STATEMENTS = { + beginKeywords: 'fun receive if try case maybe', + end: 'end', + keywords: ERLANG_RESERVED + }; + BLOCK_STATEMENTS.contains = [ + COMMENT, + NAMED_FUN, + hljs.inherit(hljs.APOS_STRING_MODE, { className: '' }), + BLOCK_STATEMENTS, + FUNCTION_CALL, + SIGIL, + TRIPLE_QUOTE, + hljs.QUOTE_STRING_MODE, + NUMBER, + TUPLE, + VAR1, + VAR2, + RECORD_ACCESS, + CHAR_LITERAL + ]; + + const BASIC_MODES = [ + COMMENT, + NAMED_FUN, + BLOCK_STATEMENTS, + FUNCTION_CALL, + SIGIL, + TRIPLE_QUOTE, + hljs.QUOTE_STRING_MODE, + NUMBER, + TUPLE, + VAR1, + VAR2, + RECORD_ACCESS, + CHAR_LITERAL + ]; + FUNCTION_CALL.contains[1].contains = BASIC_MODES; + TUPLE.contains = BASIC_MODES; + RECORD_ACCESS.contains[1].contains = BASIC_MODES; + + const DIRECTIVES = [ + "-module", + "-record", + "-undef", + "-export", + "-ifdef", + "-ifndef", + "-author", + "-copyright", + "-doc", + "-moduledoc", + "-vsn", + "-import", + "-include", + "-include_lib", + "-compile", + "-define", + "-else", + "-endif", + "-file", + "-behaviour", + "-behavior", + "-spec", + "-on_load", + "-nifs", + ]; + + const PARAMS = { + className: 'params', + begin: '\\(', + end: '\\)', + contains: BASIC_MODES + }; + + return { + name: 'Erlang', + aliases: [ 'erl' ], + keywords: ERLANG_RESERVED, + illegal: '(', + returnBegin: true, + illegal: '\\(|#|//|/\\*|\\\\|:|;', + contains: [ + PARAMS, + hljs.inherit(hljs.TITLE_MODE, { begin: BASIC_ATOM_RE }) + ], + starts: { + end: ';|\\.', + keywords: ERLANG_RESERVED, + contains: BASIC_MODES + } + }, + COMMENT, + { + begin: '^-', + end: '\\.', + relevance: 0, + excludeEnd: true, + returnBegin: true, + keywords: { + $pattern: '-' + hljs.IDENT_RE, + keyword: DIRECTIVES.map(x => `${x}|1.5`).join(" ") + }, + contains: [ + PARAMS, + SIGIL, + TRIPLE_QUOTE, + hljs.QUOTE_STRING_MODE + ] + }, + NUMBER, + SIGIL, + TRIPLE_QUOTE, + hljs.QUOTE_STRING_MODE, + RECORD_ACCESS, + VAR1, + VAR2, + TUPLE, + CHAR_LITERAL, + { begin: /\.$/ } // relevance booster + ] + }; +} + +export { erlang as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/erlang.js.js b/frontend/node_modules/highlight.js/es/languages/erlang.js.js new file mode 100644 index 0000000..dcdbf50 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/erlang.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/erlang" instead of "highlight.js/lib/languages/erlang.js"' + ); + } + } + emitWarning(); + import lang from './erlang.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/excel.js b/frontend/node_modules/highlight.js/es/languages/excel.js new file mode 100644 index 0000000..68b73c5 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/excel.js @@ -0,0 +1,580 @@ +/* +Language: Excel formulae +Author: Victor Zhou +Description: Excel formulae +Website: https://products.office.com/en-us/excel/ +Category: enterprise +*/ + +/** @type LanguageFn */ +function excel(hljs) { + // built-in functions imported from https://web.archive.org/web/20241205190205/https://support.microsoft.com/en-us/office/excel-functions-alphabetical-b3944572-255d-4efb-bb96-c6d90033e188 + const BUILT_INS = [ + "ABS", + "ACCRINT", + "ACCRINTM", + "ACOS", + "ACOSH", + "ACOT", + "ACOTH", + "AGGREGATE", + "ADDRESS", + "AMORDEGRC", + "AMORLINC", + "AND", + "ARABIC", + "AREAS", + "ARRAYTOTEXT", + "ASC", + "ASIN", + "ASINH", + "ATAN", + "ATAN2", + "ATANH", + "AVEDEV", + "AVERAGE", + "AVERAGEA", + "AVERAGEIF", + "AVERAGEIFS", + "BAHTTEXT", + "BASE", + "BESSELI", + "BESSELJ", + "BESSELK", + "BESSELY", + "BETADIST", + "BETA.DIST", + "BETAINV", + "BETA.INV", + "BIN2DEC", + "BIN2HEX", + "BIN2OCT", + "BINOMDIST", + "BINOM.DIST", + "BINOM.DIST.RANGE", + "BINOM.INV", + "BITAND", + "BITLSHIFT", + "BITOR", + "BITRSHIFT", + "BITXOR", + "BYCOL", + "BYROW", + "CALL", + "CEILING", + "CEILING.MATH", + "CEILING.PRECISE", + "CELL", + "CHAR", + "CHIDIST", + "CHIINV", + "CHITEST", + "CHISQ.DIST", + "CHISQ.DIST.RT", + "CHISQ.INV", + "CHISQ.INV.RT", + "CHISQ.TEST", + "CHOOSE", + "CHOOSECOLS", + "CHOOSEROWS", + "CLEAN", + "CODE", + "COLUMN", + "COLUMNS", + "COMBIN", + "COMBINA", + "COMPLEX", + "CONCAT", + "CONCATENATE", + "CONFIDENCE", + "CONFIDENCE.NORM", + "CONFIDENCE.T", + "CONVERT", + "CORREL", + "COS", + "COSH", + "COT", + "COTH", + "COUNT", + "COUNTA", + "COUNTBLANK", + "COUNTIF", + "COUNTIFS", + "COUPDAYBS", + "COUPDAYS", + "COUPDAYSNC", + "COUPNCD", + "COUPNUM", + "COUPPCD", + "COVAR", + "COVARIANCE.P", + "COVARIANCE.S", + "CRITBINOM", + "CSC", + "CSCH", + "CUBEKPIMEMBER", + "CUBEMEMBER", + "CUBEMEMBERPROPERTY", + "CUBERANKEDMEMBER", + "CUBESET", + "CUBESETCOUNT", + "CUBEVALUE", + "CUMIPMT", + "CUMPRINC", + "DATE", + "DATEDIF", + "DATEVALUE", + "DAVERAGE", + "DAY", + "DAYS", + "DAYS360", + "DB", + "DBCS", + "DCOUNT", + "DCOUNTA", + "DDB", + "DEC2BIN", + "DEC2HEX", + "DEC2OCT", + "DECIMAL", + "DEGREES", + "DELTA", + "DEVSQ", + "DGET", + "DISC", + "DMAX", + "DMIN", + "DOLLAR", + "DOLLARDE", + "DOLLARFR", + "DPRODUCT", + "DROP", + "DSTDEV", + "DSTDEVP", + "DSUM", + "DURATION", + "DVAR", + "DVARP", + "EDATE", + "EFFECT", + "ENCODEURL", + "EOMONTH", + "ERF", + "ERF.PRECISE", + "ERFC", + "ERFC.PRECISE", + "ERROR.TYPE", + "EUROCONVERT", + "EVEN", + "EXACT", + "EXP", + "EXPAND", + "EXPON.DIST", + "EXPONDIST", + "FACT", + "FACTDOUBLE", + "FALSE", + "F.DIST", + "FDIST", + "F.DIST.RT", + "FILTER", + "FILTERXML", + "FIND", + "FINDB", + "F.INV", + "F.INV.RT", + "FINV", + "FISHER", + "FISHERINV", + "FIXED", + "FLOOR", + "FLOOR.MATH", + "FLOOR.PRECISE", + "FORECAST", + "FORECAST.ETS", + "FORECAST.ETS.CONFINT", + "FORECAST.ETS.SEASONALITY", + "FORECAST.ETS.STAT", + "FORECAST.LINEAR", + "FORMULATEXT", + "FREQUENCY", + "F.TEST", + "FTEST", + "FV", + "FVSCHEDULE", + "GAMMA", + "GAMMA.DIST", + "GAMMADIST", + "GAMMA.INV", + "GAMMAINV", + "GAMMALN", + "GAMMALN.PRECISE", + "GAUSS", + "GCD", + "GEOMEAN", + "GESTEP", + "GETPIVOTDATA", + "GROWTH", + "HARMEAN", + "HEX2BIN", + "HEX2DEC", + "HEX2OCT", + "HLOOKUP", + "HOUR", + "HSTACK", + "HYPERLINK", + "HYPGEOM.DIST", + "HYPGEOMDIST", + "IF", + "IFERROR", + "IFNA", + "IFS", + "IMABS", + "IMAGE", + "IMAGINARY", + "IMARGUMENT", + "IMCONJUGATE", + "IMCOS", + "IMCOSH", + "IMCOT", + "IMCSC", + "IMCSCH", + "IMDIV", + "IMEXP", + "IMLN", + "IMLOG10", + "IMLOG2", + "IMPOWER", + "IMPRODUCT", + "IMREAL", + "IMSEC", + "IMSECH", + "IMSIN", + "IMSINH", + "IMSQRT", + "IMSUB", + "IMSUM", + "IMTAN", + "INDEX", + "INDIRECT", + "INFO", + "INT", + "INTERCEPT", + "INTRATE", + "IPMT", + "IRR", + "ISBLANK", + "ISERR", + "ISERROR", + "ISEVEN", + "ISFORMULA", + "ISLOGICAL", + "ISNA", + "ISNONTEXT", + "ISNUMBER", + "ISODD", + "ISOMITTED", + "ISREF", + "ISTEXT", + "ISO.CEILING", + "ISOWEEKNUM", + "ISPMT", + "JIS", + "KURT", + "LAMBDA", + "LARGE", + "LCM", + "LEFT", + "LEFTB", + "LEN", + "LENB", + "LET", + "LINEST", + "LN", + "LOG", + "LOG10", + "LOGEST", + "LOGINV", + "LOGNORM.DIST", + "LOGNORMDIST", + "LOGNORM.INV", + "LOOKUP", + "LOWER", + "MAKEARRAY", + "MAP", + "MATCH", + "MAX", + "MAXA", + "MAXIFS", + "MDETERM", + "MDURATION", + "MEDIAN", + "MID", + "MIDB", + "MIN", + "MINIFS", + "MINA", + "MINUTE", + "MINVERSE", + "MIRR", + "MMULT", + "MOD", + "MODE", + "MODE.MULT", + "MODE.SNGL", + "MONTH", + "MROUND", + "MULTINOMIAL", + "MUNIT", + "N", + "NA", + "NEGBINOM.DIST", + "NEGBINOMDIST", + "NETWORKDAYS", + "NETWORKDAYS.INTL", + "NOMINAL", + "NORM.DIST", + "NORMDIST", + "NORMINV", + "NORM.INV", + "NORM.S.DIST", + "NORMSDIST", + "NORM.S.INV", + "NORMSINV", + "NOT", + "NOW", + "NPER", + "NPV", + "NUMBERVALUE", + "OCT2BIN", + "OCT2DEC", + "OCT2HEX", + "ODD", + "ODDFPRICE", + "ODDFYIELD", + "ODDLPRICE", + "ODDLYIELD", + "OFFSET", + "OR", + "PDURATION", + "PEARSON", + "PERCENTILE.EXC", + "PERCENTILE.INC", + "PERCENTILE", + "PERCENTRANK.EXC", + "PERCENTRANK.INC", + "PERCENTRANK", + "PERMUT", + "PERMUTATIONA", + "PHI", + "PHONETIC", + "PI", + "PMT", + "POISSON.DIST", + "POISSON", + "POWER", + "PPMT", + "PRICE", + "PRICEDISC", + "PRICEMAT", + "PROB", + "PRODUCT", + "PROPER", + "PV", + "QUARTILE", + "QUARTILE.EXC", + "QUARTILE.INC", + "QUOTIENT", + "RADIANS", + "RAND", + "RANDARRAY", + "RANDBETWEEN", + "RANK.AVG", + "RANK.EQ", + "RANK", + "RATE", + "RECEIVED", + "REDUCE", + "REGISTER.ID", + "REPLACE", + "REPLACEB", + "REPT", + "RIGHT", + "RIGHTB", + "ROMAN", + "ROUND", + "ROUNDDOWN", + "ROUNDUP", + "ROW", + "ROWS", + "RRI", + "RSQ", + "RTD", + "SCAN", + "SEARCH", + "SEARCHB", + "SEC", + "SECH", + "SECOND", + "SEQUENCE", + "SERIESSUM", + "SHEET", + "SHEETS", + "SIGN", + "SIN", + "SINH", + "SKEW", + "SKEW.P", + "SLN", + "SLOPE", + "SMALL", + "SORT", + "SORTBY", + "SQRT", + "SQRTPI", + "SQL.REQUEST", + "STANDARDIZE", + "STOCKHISTORY", + "STDEV", + "STDEV.P", + "STDEV.S", + "STDEVA", + "STDEVP", + "STDEVPA", + "STEYX", + "SUBSTITUTE", + "SUBTOTAL", + "SUM", + "SUMIF", + "SUMIFS", + "SUMPRODUCT", + "SUMSQ", + "SUMX2MY2", + "SUMX2PY2", + "SUMXMY2", + "SWITCH", + "SYD", + "T", + "TAN", + "TANH", + "TAKE", + "TBILLEQ", + "TBILLPRICE", + "TBILLYIELD", + "T.DIST", + "T.DIST.2T", + "T.DIST.RT", + "TDIST", + "TEXT", + "TEXTAFTER", + "TEXTBEFORE", + "TEXTJOIN", + "TEXTSPLIT", + "TIME", + "TIMEVALUE", + "T.INV", + "T.INV.2T", + "TINV", + "TOCOL", + "TOROW", + "TODAY", + "TRANSPOSE", + "TREND", + "TRIM", + "TRIMMEAN", + "TRUE", + "TRUNC", + "T.TEST", + "TTEST", + "TYPE", + "UNICHAR", + "UNICODE", + "UNIQUE", + "UPPER", + "VALUE", + "VALUETOTEXT", + "VAR", + "VAR.P", + "VAR.S", + "VARA", + "VARP", + "VARPA", + "VDB", + "VLOOKUP", + "VSTACK", + "WEBSERVICE", + "WEEKDAY", + "WEEKNUM", + "WEIBULL", + "WEIBULL.DIST", + "WORKDAY", + "WORKDAY.INTL", + "WRAPCOLS", + "WRAPROWS", + "XIRR", + "XLOOKUP", + "XMATCH", + "XNPV", + "XOR", + "YEAR", + "YEARFRAC", + "YIELD", + "YIELDDISC", + "YIELDMAT", + "Z.TEST", + "ZTEST" + ]; + return { + name: 'Excel formulae', + aliases: [ + 'xlsx', + 'xls' + ], + case_insensitive: true, + keywords: { + $pattern: /[a-zA-Z][\w\.]*/, + built_in: BUILT_INS + }, + contains: [ + { + /* matches a beginning equal sign found in Excel formula examples */ + begin: /^=/, + end: /[^=]/, + returnEnd: true, + illegal: /=/, /* only allow single equal sign at front of line */ + relevance: 10 + }, + /* technically, there can be more than 2 letters in column names, but this prevents conflict with some keywords */ + { + /* matches a reference to a single cell */ + className: 'symbol', + begin: /\b[A-Z]{1,2}\d+\b/, + end: /[^\d]/, + excludeEnd: true, + relevance: 0 + }, + { + /* matches a reference to a range of cells */ + className: 'symbol', + begin: /[A-Z]{0,2}\d*:[A-Z]{0,2}\d*/, + relevance: 0 + }, + hljs.BACKSLASH_ESCAPE, + hljs.QUOTE_STRING_MODE, + { + className: 'number', + begin: hljs.NUMBER_RE + '(%)?', + relevance: 0 + }, + /* Excel formula comments are done by putting the comment in a function call to N() */ + hljs.COMMENT(/\bN\(/, /\)/, + { + excludeBegin: true, + excludeEnd: true, + illegal: /\n/ + }) + ] + }; +} + +export { excel as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/excel.js.js b/frontend/node_modules/highlight.js/es/languages/excel.js.js new file mode 100644 index 0000000..4f33136 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/excel.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/excel" instead of "highlight.js/lib/languages/excel.js"' + ); + } + } + emitWarning(); + import lang from './excel.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/fix.js b/frontend/node_modules/highlight.js/es/languages/fix.js new file mode 100644 index 0000000..0ab3520 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/fix.js @@ -0,0 +1,39 @@ +/* +Language: FIX +Author: Brent Bradbury +*/ + +/** @type LanguageFn */ +function fix(hljs) { + return { + name: 'FIX', + contains: [ + { + begin: /[^\u2401\u0001]+/, + end: /[\u2401\u0001]/, + excludeEnd: true, + returnBegin: true, + returnEnd: false, + contains: [ + { + begin: /([^\u2401\u0001=]+)/, + end: /=([^\u2401\u0001=]+)/, + returnEnd: true, + returnBegin: false, + className: 'attr' + }, + { + begin: /=/, + end: /([\u2401\u0001])/, + excludeEnd: true, + excludeBegin: true, + className: 'string' + } + ] + } + ], + case_insensitive: true + }; +} + +export { fix as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/fix.js.js b/frontend/node_modules/highlight.js/es/languages/fix.js.js new file mode 100644 index 0000000..d7505b8 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/fix.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/fix" instead of "highlight.js/lib/languages/fix.js"' + ); + } + } + emitWarning(); + import lang from './fix.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/flix.js b/frontend/node_modules/highlight.js/es/languages/flix.js new file mode 100644 index 0000000..fb6c0a4 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/flix.js @@ -0,0 +1,79 @@ +/* + Language: Flix + Category: functional + Author: Magnus Madsen + Website: https://flix.dev/ + */ + +/** @type LanguageFn */ +function flix(hljs) { + const CHAR = { + className: 'string', + begin: /'(.|\\[xXuU][a-zA-Z0-9]+)'/ + }; + + const STRING = { + className: 'string', + variants: [ + { + begin: '"', + end: '"' + } + ] + }; + + const NAME = { + className: 'title', + relevance: 0, + begin: /[^0-9\n\t "'(),.`{}\[\]:;][^\n\t "'(),.`{}\[\]:;]+|[^0-9\n\t "'(),.`{}\[\]:;=]/ + }; + + const METHOD = { + className: 'function', + beginKeywords: 'def', + end: /[:={\[(\n;]/, + excludeEnd: true, + contains: [ NAME ] + }; + + return { + name: 'Flix', + keywords: { + keyword: [ + "case", + "class", + "def", + "else", + "enum", + "if", + "impl", + "import", + "in", + "lat", + "rel", + "index", + "let", + "match", + "namespace", + "switch", + "type", + "yield", + "with" + ], + literal: [ + "true", + "false" + ] + }, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + CHAR, + STRING, + METHOD, + hljs.C_NUMBER_MODE + ] + }; +} + +export { flix as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/flix.js.js b/frontend/node_modules/highlight.js/es/languages/flix.js.js new file mode 100644 index 0000000..5047ab7 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/flix.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/flix" instead of "highlight.js/lib/languages/flix.js"' + ); + } + } + emitWarning(); + import lang from './flix.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/fortran.js b/frontend/node_modules/highlight.js/es/languages/fortran.js new file mode 100644 index 0000000..62f2223 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/fortran.js @@ -0,0 +1,574 @@ +/* +Language: Fortran +Author: Anthony Scemama +Website: https://en.wikipedia.org/wiki/Fortran +Category: scientific +*/ + +/** @type LanguageFn */ +function fortran(hljs) { + const regex = hljs.regex; + const PARAMS = { + className: 'params', + begin: '\\(', + end: '\\)' + }; + + const COMMENT = { variants: [ + hljs.COMMENT('!', '$', { relevance: 0 }), + // allow FORTRAN 77 style comments + hljs.COMMENT('^C[ ]', '$', { relevance: 0 }), + hljs.COMMENT('^C$', '$', { relevance: 0 }) + ] }; + + // regex in both fortran and irpf90 should match + const OPTIONAL_NUMBER_SUFFIX = /(_[a-z_\d]+)?/; + const OPTIONAL_NUMBER_EXP = /([de][+-]?\d+)?/; + const NUMBER = { + className: 'number', + variants: [ + { begin: regex.concat(/\b\d+/, /\.(\d*)/, OPTIONAL_NUMBER_EXP, OPTIONAL_NUMBER_SUFFIX) }, + { begin: regex.concat(/\b\d+/, OPTIONAL_NUMBER_EXP, OPTIONAL_NUMBER_SUFFIX) }, + { begin: regex.concat(/\.\d+/, OPTIONAL_NUMBER_EXP, OPTIONAL_NUMBER_SUFFIX) } + ], + relevance: 0 + }; + + const FUNCTION_DEF = { + className: 'function', + beginKeywords: 'subroutine function program', + illegal: '[${=\\n]', + contains: [ + hljs.UNDERSCORE_TITLE_MODE, + PARAMS + ] + }; + + const STRING = { + className: 'string', + relevance: 0, + variants: [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE + ] + }; + + const KEYWORDS = [ + "kind", + "do", + "concurrent", + "local", + "shared", + "while", + "private", + "call", + "intrinsic", + "where", + "elsewhere", + "type", + "endtype", + "endmodule", + "endselect", + "endinterface", + "end", + "enddo", + "endif", + "if", + "forall", + "endforall", + "only", + "contains", + "default", + "return", + "stop", + "then", + "block", + "endblock", + "endassociate", + "public", + "subroutine|10", + "function", + "program", + ".and.", + ".or.", + ".not.", + ".le.", + ".eq.", + ".ge.", + ".gt.", + ".lt.", + "goto", + "save", + "else", + "use", + "module", + "select", + "case", + "access", + "blank", + "direct", + "exist", + "file", + "fmt", + "form", + "formatted", + "iostat", + "name", + "named", + "nextrec", + "number", + "opened", + "rec", + "recl", + "sequential", + "status", + "unformatted", + "unit", + "continue", + "format", + "pause", + "cycle", + "exit", + "c_null_char", + "c_alert", + "c_backspace", + "c_form_feed", + "flush", + "wait", + "decimal", + "round", + "iomsg", + "synchronous", + "nopass", + "non_overridable", + "pass", + "protected", + "volatile", + "abstract", + "extends", + "import", + "non_intrinsic", + "value", + "deferred", + "generic", + "final", + "enumerator", + "class", + "associate", + "bind", + "enum", + "c_int", + "c_short", + "c_long", + "c_long_long", + "c_signed_char", + "c_size_t", + "c_int8_t", + "c_int16_t", + "c_int32_t", + "c_int64_t", + "c_int_least8_t", + "c_int_least16_t", + "c_int_least32_t", + "c_int_least64_t", + "c_int_fast8_t", + "c_int_fast16_t", + "c_int_fast32_t", + "c_int_fast64_t", + "c_intmax_t", + "C_intptr_t", + "c_float", + "c_double", + "c_long_double", + "c_float_complex", + "c_double_complex", + "c_long_double_complex", + "c_bool", + "c_char", + "c_null_ptr", + "c_null_funptr", + "c_new_line", + "c_carriage_return", + "c_horizontal_tab", + "c_vertical_tab", + "iso_c_binding", + "c_loc", + "c_funloc", + "c_associated", + "c_f_pointer", + "c_ptr", + "c_funptr", + "iso_fortran_env", + "character_storage_size", + "error_unit", + "file_storage_size", + "input_unit", + "iostat_end", + "iostat_eor", + "numeric_storage_size", + "output_unit", + "c_f_procpointer", + "ieee_arithmetic", + "ieee_support_underflow_control", + "ieee_get_underflow_mode", + "ieee_set_underflow_mode", + "newunit", + "contiguous", + "recursive", + "pad", + "position", + "action", + "delim", + "readwrite", + "eor", + "advance", + "nml", + "interface", + "procedure", + "namelist", + "include", + "sequence", + "elemental", + "pure", + "impure", + "integer", + "real", + "character", + "complex", + "logical", + "codimension", + "dimension", + "allocatable|10", + "parameter", + "external", + "implicit|10", + "none", + "double", + "precision", + "assign", + "intent", + "optional", + "pointer", + "target", + "in", + "out", + "common", + "equivalence", + "data" + ]; + const LITERALS = [ + ".False.", + ".True." + ]; + const BUILT_INS = [ + "alog", + "alog10", + "amax0", + "amax1", + "amin0", + "amin1", + "amod", + "cabs", + "ccos", + "cexp", + "clog", + "csin", + "csqrt", + "dabs", + "dacos", + "dasin", + "datan", + "datan2", + "dcos", + "dcosh", + "ddim", + "dexp", + "dint", + "dlog", + "dlog10", + "dmax1", + "dmin1", + "dmod", + "dnint", + "dsign", + "dsin", + "dsinh", + "dsqrt", + "dtan", + "dtanh", + "float", + "iabs", + "idim", + "idint", + "idnint", + "ifix", + "isign", + "max0", + "max1", + "min0", + "min1", + "sngl", + "algama", + "cdabs", + "cdcos", + "cdexp", + "cdlog", + "cdsin", + "cdsqrt", + "cqabs", + "cqcos", + "cqexp", + "cqlog", + "cqsin", + "cqsqrt", + "dcmplx", + "dconjg", + "derf", + "derfc", + "dfloat", + "dgamma", + "dimag", + "dlgama", + "iqint", + "qabs", + "qacos", + "qasin", + "qatan", + "qatan2", + "qcmplx", + "qconjg", + "qcos", + "qcosh", + "qdim", + "qerf", + "qerfc", + "qexp", + "qgamma", + "qimag", + "qlgama", + "qlog", + "qlog10", + "qmax1", + "qmin1", + "qmod", + "qnint", + "qsign", + "qsin", + "qsinh", + "qsqrt", + "qtan", + "qtanh", + "abs", + "acos", + "aimag", + "aint", + "anint", + "asin", + "atan", + "atan2", + "char", + "cmplx", + "conjg", + "cos", + "cosh", + "exp", + "ichar", + "index", + "int", + "log", + "log10", + "max", + "min", + "nint", + "sign", + "sin", + "sinh", + "sqrt", + "tan", + "tanh", + "print", + "write", + "dim", + "lge", + "lgt", + "lle", + "llt", + "mod", + "nullify", + "allocate", + "deallocate", + "adjustl", + "adjustr", + "all", + "allocated", + "any", + "associated", + "bit_size", + "btest", + "ceiling", + "count", + "cshift", + "date_and_time", + "digits", + "dot_product", + "eoshift", + "epsilon", + "exponent", + "floor", + "fraction", + "huge", + "iand", + "ibclr", + "ibits", + "ibset", + "ieor", + "ior", + "ishft", + "ishftc", + "lbound", + "len_trim", + "matmul", + "maxexponent", + "maxloc", + "maxval", + "merge", + "minexponent", + "minloc", + "minval", + "modulo", + "mvbits", + "nearest", + "pack", + "present", + "product", + "radix", + "random_number", + "random_seed", + "range", + "repeat", + "reshape", + "rrspacing", + "scale", + "scan", + "selected_int_kind", + "selected_real_kind", + "set_exponent", + "shape", + "size", + "spacing", + "spread", + "sum", + "system_clock", + "tiny", + "transpose", + "trim", + "ubound", + "unpack", + "verify", + "achar", + "iachar", + "transfer", + "dble", + "entry", + "dprod", + "cpu_time", + "command_argument_count", + "get_command", + "get_command_argument", + "get_environment_variable", + "is_iostat_end", + "ieee_arithmetic", + "ieee_support_underflow_control", + "ieee_get_underflow_mode", + "ieee_set_underflow_mode", + "is_iostat_eor", + "move_alloc", + "new_line", + "selected_char_kind", + "same_type_as", + "extends_type_of", + "acosh", + "asinh", + "atanh", + "bessel_j0", + "bessel_j1", + "bessel_jn", + "bessel_y0", + "bessel_y1", + "bessel_yn", + "erf", + "erfc", + "erfc_scaled", + "gamma", + "log_gamma", + "hypot", + "norm2", + "atomic_define", + "atomic_ref", + "execute_command_line", + "leadz", + "trailz", + "storage_size", + "merge_bits", + "bge", + "bgt", + "ble", + "blt", + "dshiftl", + "dshiftr", + "findloc", + "iall", + "iany", + "iparity", + "image_index", + "lcobound", + "ucobound", + "maskl", + "maskr", + "num_images", + "parity", + "popcnt", + "poppar", + "shifta", + "shiftl", + "shiftr", + "this_image", + "sync", + "change", + "team", + "co_broadcast", + "co_max", + "co_min", + "co_sum", + "co_reduce" + ]; + return { + name: 'Fortran', + case_insensitive: true, + aliases: [ + 'f90', + 'f95' + ], + keywords: { + $pattern: /\b[a-z][a-z0-9_]+\b|\.[a-z][a-z0-9_]+\./, + keyword: KEYWORDS, + literal: LITERALS, + built_in: BUILT_INS + }, + illegal: /\/\*/, + contains: [ + STRING, + FUNCTION_DEF, + // allow `C = value` for assignments so they aren't misdetected + // as Fortran 77 style comments + { + begin: /^C\s*=(?!=)/, + relevance: 0 + }, + COMMENT, + NUMBER + ] + }; +} + +export { fortran as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/fortran.js.js b/frontend/node_modules/highlight.js/es/languages/fortran.js.js new file mode 100644 index 0000000..3638f06 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/fortran.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/fortran" instead of "highlight.js/lib/languages/fortran.js"' + ); + } + } + emitWarning(); + import lang from './fortran.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/fsharp.js b/frontend/node_modules/highlight.js/es/languages/fsharp.js new file mode 100644 index 0000000..252bf68 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/fsharp.js @@ -0,0 +1,627 @@ +/** + * @param {string} value + * @returns {RegExp} + * */ +function escape(value) { + return new RegExp(value.replace(/[-/\\^$*+?.()|[\]{}]/g, '\\$&'), 'm'); +} + +/** + * @param {RegExp | string } re + * @returns {string} + */ +function source(re) { + if (!re) return null; + if (typeof re === "string") return re; + + return re.source; +} + +/** + * @param {RegExp | string } re + * @returns {string} + */ +function lookahead(re) { + return concat('(?=', re, ')'); +} + +/** + * @param {...(RegExp | string) } args + * @returns {string} + */ +function concat(...args) { + const joined = args.map((x) => source(x)).join(""); + return joined; +} + +/** + * @param { Array } args + * @returns {object} + */ +function stripOptionsFromArgs(args) { + const opts = args[args.length - 1]; + + if (typeof opts === 'object' && opts.constructor === Object) { + args.splice(args.length - 1, 1); + return opts; + } else { + return {}; + } +} + +/** @typedef { {capture?: boolean} } RegexEitherOptions */ + +/** + * Any of the passed expresssions may match + * + * Creates a huge this | this | that | that match + * @param {(RegExp | string)[] | [...(RegExp | string)[], RegexEitherOptions]} args + * @returns {string} + */ +function either(...args) { + /** @type { object & {capture?: boolean} } */ + const opts = stripOptionsFromArgs(args); + const joined = '(' + + (opts.capture ? "" : "?:") + + args.map((x) => source(x)).join("|") + ")"; + return joined; +} + +/* +Language: F# +Author: Jonas Follesø +Contributors: Troy Kershaw , Henrik Feldt , Melvyn Laïly +Website: https://docs.microsoft.com/en-us/dotnet/fsharp/ +Category: functional +*/ + + +/** @type LanguageFn */ +function fsharp(hljs) { + const KEYWORDS = [ + "abstract", + "and", + "as", + "assert", + "base", + "begin", + "class", + "default", + "delegate", + "do", + "done", + "downcast", + "downto", + "elif", + "else", + "end", + "exception", + "extern", + // "false", // literal + "finally", + "fixed", + "for", + "fun", + "function", + "global", + "if", + "in", + "inherit", + "inline", + "interface", + "internal", + "lazy", + "let", + "match", + "member", + "module", + "mutable", + "namespace", + "new", + // "not", // built_in + // "null", // literal + "of", + "open", + "or", + "override", + "private", + "public", + "rec", + "return", + "static", + "struct", + "then", + "to", + // "true", // literal + "try", + "type", + "upcast", + "use", + "val", + "void", + "when", + "while", + "with", + "yield" + ]; + + const BANG_KEYWORD_MODE = { + // monad builder keywords (matches before non-bang keywords) + scope: 'keyword', + match: /\b(yield|return|let|do|match|use)!/ + }; + + const PREPROCESSOR_KEYWORDS = [ + "if", + "else", + "endif", + "line", + "nowarn", + "light", + "r", + "i", + "I", + "load", + "time", + "help", + "quit" + ]; + + const LITERALS = [ + "true", + "false", + "null", + "Some", + "None", + "Ok", + "Error", + "infinity", + "infinityf", + "nan", + "nanf" + ]; + + const SPECIAL_IDENTIFIERS = [ + "__LINE__", + "__SOURCE_DIRECTORY__", + "__SOURCE_FILE__" + ]; + + // Since it's possible to re-bind/shadow names (e.g. let char = 'c'), + // these builtin types should only be matched when a type name is expected. + const KNOWN_TYPES = [ + // basic types + "bool", + "byte", + "sbyte", + "int8", + "int16", + "int32", + "uint8", + "uint16", + "uint32", + "int", + "uint", + "int64", + "uint64", + "nativeint", + "unativeint", + "decimal", + "float", + "double", + "float32", + "single", + "char", + "string", + "unit", + "bigint", + // other native types or lowercase aliases + "option", + "voption", + "list", + "array", + "seq", + "byref", + "exn", + "inref", + "nativeptr", + "obj", + "outref", + "voidptr", + // other important FSharp types + "Result" + ]; + + const BUILTINS = [ + // Somewhat arbitrary list of builtin functions and values. + // Most of them are declared in Microsoft.FSharp.Core + // I tried to stay relevant by adding only the most idiomatic + // and most used symbols that are not already declared as types. + "not", + "ref", + "raise", + "reraise", + "dict", + "readOnlyDict", + "set", + "get", + "enum", + "sizeof", + "typeof", + "typedefof", + "nameof", + "nullArg", + "invalidArg", + "invalidOp", + "id", + "fst", + "snd", + "ignore", + "lock", + "using", + "box", + "unbox", + "tryUnbox", + "printf", + "printfn", + "sprintf", + "eprintf", + "eprintfn", + "fprintf", + "fprintfn", + "failwith", + "failwithf" + ]; + + const ALL_KEYWORDS = { + keyword: KEYWORDS, + literal: LITERALS, + built_in: BUILTINS, + 'variable.constant': SPECIAL_IDENTIFIERS + }; + + // (* potentially multi-line Meta Language style comment *) + const ML_COMMENT = + hljs.COMMENT(/\(\*(?!\))/, /\*\)/, { + contains: ["self"] + }); + // Either a multi-line (* Meta Language style comment *) or a single line // C style comment. + const COMMENT = { + variants: [ + ML_COMMENT, + hljs.C_LINE_COMMENT_MODE, + ] + }; + + // Most identifiers can contain apostrophes + const IDENTIFIER_RE = /[a-zA-Z_](\w|')*/; + + const QUOTED_IDENTIFIER = { + scope: 'variable', + begin: /``/, + end: /``/ + }; + + // 'a or ^a where a can be a ``quoted identifier`` + const BEGIN_GENERIC_TYPE_SYMBOL_RE = /\B('|\^)/; + const GENERIC_TYPE_SYMBOL = { + scope: 'symbol', + variants: [ + // the type name is a quoted identifier: + { match: concat(BEGIN_GENERIC_TYPE_SYMBOL_RE, /``.*?``/) }, + // the type name is a normal identifier (we don't use IDENTIFIER_RE because there cannot be another apostrophe here): + { match: concat(BEGIN_GENERIC_TYPE_SYMBOL_RE, hljs.UNDERSCORE_IDENT_RE) } + ], + relevance: 0 + }; + + const makeOperatorMode = function({ includeEqual }) { + // List or symbolic operator characters from the FSharp Spec 4.1, minus the dot, and with `?` added, used for nullable operators. + let allOperatorChars; + if (includeEqual) + allOperatorChars = "!%&*+-/<=>@^|~?"; + else + allOperatorChars = "!%&*+-/<>@^|~?"; + const OPERATOR_CHARS = Array.from(allOperatorChars); + const OPERATOR_CHAR_RE = concat('[', ...OPERATOR_CHARS.map(escape), ']'); + // The lone dot operator is special. It cannot be redefined, and we don't want to highlight it. It can be used as part of a multi-chars operator though. + const OPERATOR_CHAR_OR_DOT_RE = either(OPERATOR_CHAR_RE, /\./); + // When a dot is present, it must be followed by another operator char: + const OPERATOR_FIRST_CHAR_OF_MULTIPLE_RE = concat(OPERATOR_CHAR_OR_DOT_RE, lookahead(OPERATOR_CHAR_OR_DOT_RE)); + const SYMBOLIC_OPERATOR_RE = either( + concat(OPERATOR_FIRST_CHAR_OF_MULTIPLE_RE, OPERATOR_CHAR_OR_DOT_RE, '*'), // Matches at least 2 chars operators + concat(OPERATOR_CHAR_RE, '+'), // Matches at least one char operators + ); + return { + scope: 'operator', + match: either( + // symbolic operators: + SYMBOLIC_OPERATOR_RE, + // other symbolic keywords: + // Type casting and conversion operators: + /:\?>/, + /:\?/, + /:>/, + /:=/, // Reference cell assignment + /::?/, // : or :: + /\$/), // A single $ can be used as an operator + relevance: 0 + }; + }; + + const OPERATOR = makeOperatorMode({ includeEqual: true }); + // This variant is used when matching '=' should end a parent mode: + const OPERATOR_WITHOUT_EQUAL = makeOperatorMode({ includeEqual: false }); + + const makeTypeAnnotationMode = function(prefix, prefixScope) { + return { + begin: concat( // a type annotation is a + prefix, // should be a colon or the 'of' keyword + lookahead( // that has to be followed by + concat( + /\s*/, // optional space + either( // then either of: + /\w/, // word + /'/, // generic type name + /\^/, // generic type name + /#/, // flexible type name + /``/, // quoted type name + /\(/, // parens type expression + /{\|/, // anonymous type annotation + )))), + beginScope: prefixScope, + // BUG: because ending with \n is necessary for some cases, multi-line type annotations are not properly supported. + // Examples where \n is required at the end: + // - abstract member definitions in classes: abstract Property : int * string + // - return type annotations: let f f' = f' () : returnTypeAnnotation + // - record fields definitions: { A : int \n B : string } + end: lookahead( + either( + /\n/, + /=/)), + relevance: 0, + // we need the known types, and we need the type constraint keywords and literals. e.g.: when 'a : null + keywords: hljs.inherit(ALL_KEYWORDS, { type: KNOWN_TYPES }), + contains: [ + COMMENT, + GENERIC_TYPE_SYMBOL, + hljs.inherit(QUOTED_IDENTIFIER, { scope: null }), // match to avoid strange patterns inside that may break the parsing + OPERATOR_WITHOUT_EQUAL + ] + }; + }; + + const TYPE_ANNOTATION = makeTypeAnnotationMode(/:/, 'operator'); + const DISCRIMINATED_UNION_TYPE_ANNOTATION = makeTypeAnnotationMode(/\bof\b/, 'keyword'); + + // type MyType<'a> = ... + const TYPE_DECLARATION = { + begin: [ + /(^|\s+)/, // prevents matching the following: `match s.stype with` + /type/, + /\s+/, + IDENTIFIER_RE + ], + beginScope: { + 2: 'keyword', + 4: 'title.class' + }, + end: lookahead(/\(|=|$/), + keywords: ALL_KEYWORDS, // match keywords in type constraints. e.g.: when 'a : null + contains: [ + COMMENT, + hljs.inherit(QUOTED_IDENTIFIER, { scope: null }), // match to avoid strange patterns inside that may break the parsing + GENERIC_TYPE_SYMBOL, + { + // For visual consistency, highlight type brackets as operators. + scope: 'operator', + match: /<|>/ + }, + TYPE_ANNOTATION // generic types can have constraints, which are type annotations. e.g. type MyType<'T when 'T : delegate> = + ] + }; + + const COMPUTATION_EXPRESSION = { + // computation expressions: + scope: 'computation-expression', + // BUG: might conflict with record deconstruction. e.g. let f { Name = name } = name // will highlight f + match: /\b[_a-z]\w*(?=\s*\{)/ + }; + + const PREPROCESSOR = { + // preprocessor directives and fsi commands: + begin: [ + /^\s*/, + concat(/#/, either(...PREPROCESSOR_KEYWORDS)), + /\b/ + ], + beginScope: { 2: 'meta' }, + end: lookahead(/\s|$/) + }; + + // TODO: this definition is missing support for type suffixes and octal notation. + // BUG: range operator without any space is wrongly interpreted as a single number (e.g. 1..10 ) + const NUMBER = { + variants: [ + hljs.BINARY_NUMBER_MODE, + hljs.C_NUMBER_MODE + ] + }; + + // All the following string definitions are potentially multi-line. + // BUG: these definitions are missing support for byte strings (suffixed with B) + + // "..." + const QUOTED_STRING = { + scope: 'string', + begin: /"/, + end: /"/, + contains: [ + hljs.BACKSLASH_ESCAPE + ] + }; + // @"..." + const VERBATIM_STRING = { + scope: 'string', + begin: /@"/, + end: /"/, + contains: [ + { + match: /""/ // escaped " + }, + hljs.BACKSLASH_ESCAPE + ] + }; + // """...""" + const TRIPLE_QUOTED_STRING = { + scope: 'string', + begin: /"""/, + end: /"""/, + relevance: 2 + }; + const SUBST = { + scope: 'subst', + begin: /\{/, + end: /\}/, + keywords: ALL_KEYWORDS + }; + // $"...{1+1}..." + const INTERPOLATED_STRING = { + scope: 'string', + begin: /\$"/, + end: /"/, + contains: [ + { + match: /\{\{/ // escaped { + }, + { + match: /\}\}/ // escaped } + }, + hljs.BACKSLASH_ESCAPE, + SUBST + ] + }; + // $@"...{1+1}..." + const INTERPOLATED_VERBATIM_STRING = { + scope: 'string', + begin: /(\$@|@\$)"/, + end: /"/, + contains: [ + { + match: /\{\{/ // escaped { + }, + { + match: /\}\}/ // escaped } + }, + { + match: /""/ + }, + hljs.BACKSLASH_ESCAPE, + SUBST + ] + }; + // $"""...{1+1}...""" + const INTERPOLATED_TRIPLE_QUOTED_STRING = { + scope: 'string', + begin: /\$"""/, + end: /"""/, + contains: [ + { + match: /\{\{/ // escaped { + }, + { + match: /\}\}/ // escaped } + }, + SUBST + ], + relevance: 2 + }; + // '.' + const CHAR_LITERAL = { + scope: 'string', + match: concat( + /'/, + either( + /[^\\']/, // either a single non escaped char... + /\\(?:.|\d{3}|x[a-fA-F\d]{2}|u[a-fA-F\d]{4}|U[a-fA-F\d]{8})/ // ...or an escape sequence + ), + /'/ + ) + }; + // F# allows a lot of things inside string placeholders. + // Things that don't currently seem allowed by the compiler: types definition, attributes usage. + // (Strictly speaking, some of the followings are only allowed inside triple quoted interpolated strings...) + SUBST.contains = [ + INTERPOLATED_VERBATIM_STRING, + INTERPOLATED_STRING, + VERBATIM_STRING, + QUOTED_STRING, + CHAR_LITERAL, + BANG_KEYWORD_MODE, + COMMENT, + QUOTED_IDENTIFIER, + TYPE_ANNOTATION, + COMPUTATION_EXPRESSION, + PREPROCESSOR, + NUMBER, + GENERIC_TYPE_SYMBOL, + OPERATOR + ]; + const STRING = { + variants: [ + INTERPOLATED_TRIPLE_QUOTED_STRING, + INTERPOLATED_VERBATIM_STRING, + INTERPOLATED_STRING, + TRIPLE_QUOTED_STRING, + VERBATIM_STRING, + QUOTED_STRING, + CHAR_LITERAL + ] + }; + + return { + name: 'F#', + aliases: [ + 'fs', + 'f#' + ], + keywords: ALL_KEYWORDS, + illegal: /\/\*/, + classNameAliases: { + 'computation-expression': 'keyword' + }, + contains: [ + BANG_KEYWORD_MODE, + STRING, + COMMENT, + QUOTED_IDENTIFIER, + TYPE_DECLARATION, + { + // e.g. [] or [<``module``: MyCustomAttributeThatWorksOnModules>] + // or [] + scope: 'meta', + begin: /\[\]/, + relevance: 2, + contains: [ + QUOTED_IDENTIFIER, + // can contain any constant value + TRIPLE_QUOTED_STRING, + VERBATIM_STRING, + QUOTED_STRING, + CHAR_LITERAL, + NUMBER + ] + }, + DISCRIMINATED_UNION_TYPE_ANNOTATION, + TYPE_ANNOTATION, + COMPUTATION_EXPRESSION, + PREPROCESSOR, + NUMBER, + GENERIC_TYPE_SYMBOL, + OPERATOR + ] + }; +} + +export { fsharp as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/fsharp.js.js b/frontend/node_modules/highlight.js/es/languages/fsharp.js.js new file mode 100644 index 0000000..77ebf95 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/fsharp.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/fsharp" instead of "highlight.js/lib/languages/fsharp.js"' + ); + } + } + emitWarning(); + import lang from './fsharp.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/gams.js b/frontend/node_modules/highlight.js/es/languages/gams.js new file mode 100644 index 0000000..63a3595 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/gams.js @@ -0,0 +1,181 @@ +/* + Language: GAMS + Author: Stefan Bechert + Contributors: Oleg Efimov , Mikko Kouhia + Description: The General Algebraic Modeling System language + Website: https://www.gams.com + Category: scientific + */ + +/** @type LanguageFn */ +function gams(hljs) { + const regex = hljs.regex; + const KEYWORDS = { + keyword: + 'abort acronym acronyms alias all and assign binary card diag display ' + + 'else eq file files for free ge gt if integer le loop lt maximizing ' + + 'minimizing model models ne negative no not option options or ord ' + + 'positive prod put putpage puttl repeat sameas semicont semiint smax ' + + 'smin solve sos1 sos2 sum system table then until using while xor yes', + literal: + 'eps inf na', + built_in: + 'abs arccos arcsin arctan arctan2 Beta betaReg binomial ceil centropy ' + + 'cos cosh cvPower div div0 eDist entropy errorf execSeed exp fact ' + + 'floor frac gamma gammaReg log logBeta logGamma log10 log2 mapVal max ' + + 'min mod ncpCM ncpF ncpVUpow ncpVUsin normal pi poly power ' + + 'randBinomial randLinear randTriangle round rPower sigmoid sign ' + + 'signPower sin sinh slexp sllog10 slrec sqexp sqlog10 sqr sqrec sqrt ' + + 'tan tanh trunc uniform uniformInt vcPower bool_and bool_eqv bool_imp ' + + 'bool_not bool_or bool_xor ifThen rel_eq rel_ge rel_gt rel_le rel_lt ' + + 'rel_ne gday gdow ghour gleap gmillisec gminute gmonth gsecond gyear ' + + 'jdate jnow jstart jtime errorLevel execError gamsRelease gamsVersion ' + + 'handleCollect handleDelete handleStatus handleSubmit heapFree ' + + 'heapLimit heapSize jobHandle jobKill jobStatus jobTerminate ' + + 'licenseLevel licenseStatus maxExecError sleep timeClose timeComp ' + + 'timeElapsed timeExec timeStart' + }; + const PARAMS = { + className: 'params', + begin: /\(/, + end: /\)/, + excludeBegin: true, + excludeEnd: true + }; + const SYMBOLS = { + className: 'symbol', + variants: [ + { begin: /=[lgenxc]=/ }, + { begin: /\$/ } + ] + }; + const QSTR = { // One-line quoted comment string + className: 'comment', + variants: [ + { + begin: '\'', + end: '\'' + }, + { + begin: '"', + end: '"' + } + ], + illegal: '\\n', + contains: [ hljs.BACKSLASH_ESCAPE ] + }; + const ASSIGNMENT = { + begin: '/', + end: '/', + keywords: KEYWORDS, + contains: [ + QSTR, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + hljs.APOS_STRING_MODE, + hljs.C_NUMBER_MODE + ] + }; + const COMMENT_WORD = /[a-z0-9&#*=?@\\><:,()$[\]_.{}!+%^-]+/; + const DESCTEXT = { // Parameter/set/variable description text + begin: /[a-z][a-z0-9_]*(\([a-z0-9_, ]*\))?[ \t]+/, + excludeBegin: true, + end: '$', + endsWithParent: true, + contains: [ + QSTR, + ASSIGNMENT, + { + className: 'comment', + // one comment word, then possibly more + begin: regex.concat( + COMMENT_WORD, + // [ ] because \s would be too broad (matching newlines) + regex.anyNumberOfTimes(regex.concat(/[ ]+/, COMMENT_WORD)) + ), + relevance: 0 + } + ] + }; + + return { + name: 'GAMS', + aliases: [ 'gms' ], + case_insensitive: true, + keywords: KEYWORDS, + contains: [ + hljs.COMMENT(/^\$ontext/, /^\$offtext/), + { + className: 'meta', + begin: '^\\$[a-z0-9]+', + end: '$', + returnBegin: true, + contains: [ + { + className: 'keyword', + begin: '^\\$[a-z0-9]+' + } + ] + }, + hljs.COMMENT('^\\*', '$'), + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + hljs.APOS_STRING_MODE, + // Declarations + { + beginKeywords: + 'set sets parameter parameters variable variables ' + + 'scalar scalars equation equations', + end: ';', + contains: [ + hljs.COMMENT('^\\*', '$'), + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + hljs.APOS_STRING_MODE, + ASSIGNMENT, + DESCTEXT + ] + }, + { // table environment + beginKeywords: 'table', + end: ';', + returnBegin: true, + contains: [ + { // table header row + beginKeywords: 'table', + end: '$', + contains: [ DESCTEXT ] + }, + hljs.COMMENT('^\\*', '$'), + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + hljs.APOS_STRING_MODE, + hljs.C_NUMBER_MODE + // Table does not contain DESCTEXT or ASSIGNMENT + ] + }, + // Function definitions + { + className: 'function', + begin: /^[a-z][a-z0-9_,\-+' ()$]+\.{2}/, + returnBegin: true, + contains: [ + { // Function title + className: 'title', + begin: /^[a-z0-9_]+/ + }, + PARAMS, + SYMBOLS + ] + }, + hljs.C_NUMBER_MODE, + SYMBOLS + ] + }; +} + +export { gams as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/gams.js.js b/frontend/node_modules/highlight.js/es/languages/gams.js.js new file mode 100644 index 0000000..a85d8a2 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/gams.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/gams" instead of "highlight.js/lib/languages/gams.js"' + ); + } + } + emitWarning(); + import lang from './gams.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/gauss.js b/frontend/node_modules/highlight.js/es/languages/gauss.js new file mode 100644 index 0000000..2dda1c1 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/gauss.js @@ -0,0 +1,306 @@ +/* +Language: GAUSS +Author: Matt Evans +Description: GAUSS Mathematical and Statistical language +Website: https://www.aptech.com +Category: scientific +*/ +function gauss(hljs) { + const KEYWORDS = { + keyword: 'bool break call callexe checkinterrupt clear clearg closeall cls comlog compile ' + + 'continue create debug declare delete disable dlibrary dllcall do dos ed edit else ' + + 'elseif enable end endfor endif endp endo errorlog errorlogat expr external fn ' + + 'for format goto gosub graph if keyword let lib library line load loadarray loadexe ' + + 'loadf loadk loadm loadp loads loadx local locate loopnextindex lprint lpwidth lshow ' + + 'matrix msym ndpclex new open output outwidth plot plotsym pop prcsn print ' + + 'printdos proc push retp return rndcon rndmod rndmult rndseed run save saveall screen ' + + 'scroll setarray show sparse stop string struct system trace trap threadfor ' + + 'threadendfor threadbegin threadjoin threadstat threadend until use while winprint ' + + 'ne ge le gt lt and xor or not eq eqv', + built_in: 'abs acf aconcat aeye amax amean AmericanBinomCall AmericanBinomCall_Greeks AmericanBinomCall_ImpVol ' + + 'AmericanBinomPut AmericanBinomPut_Greeks AmericanBinomPut_ImpVol AmericanBSCall AmericanBSCall_Greeks ' + + 'AmericanBSCall_ImpVol AmericanBSPut AmericanBSPut_Greeks AmericanBSPut_ImpVol amin amult annotationGetDefaults ' + + 'annotationSetBkd annotationSetFont annotationSetLineColor annotationSetLineStyle annotationSetLineThickness ' + + 'annualTradingDays arccos arcsin areshape arrayalloc arrayindex arrayinit arraytomat asciiload asclabel astd ' + + 'astds asum atan atan2 atranspose axmargin balance band bandchol bandcholsol bandltsol bandrv bandsolpd bar ' + + 'base10 begwind besselj bessely beta box boxcox cdfBeta cdfBetaInv cdfBinomial cdfBinomialInv cdfBvn cdfBvn2 ' + + 'cdfBvn2e cdfCauchy cdfCauchyInv cdfChic cdfChii cdfChinc cdfChincInv cdfExp cdfExpInv cdfFc cdfFnc cdfFncInv ' + + 'cdfGam cdfGenPareto cdfHyperGeo cdfLaplace cdfLaplaceInv cdfLogistic cdfLogisticInv cdfmControlCreate cdfMvn ' + + 'cdfMvn2e cdfMvnce cdfMvne cdfMvt2e cdfMvtce cdfMvte cdfN cdfN2 cdfNc cdfNegBinomial cdfNegBinomialInv cdfNi ' + + 'cdfPoisson cdfPoissonInv cdfRayleigh cdfRayleighInv cdfTc cdfTci cdfTnc cdfTvn cdfWeibull cdfWeibullInv cdir ' + + 'ceil ChangeDir chdir chiBarSquare chol choldn cholsol cholup chrs close code cols colsf combinate combinated ' + + 'complex con cond conj cons ConScore contour conv convertsatostr convertstrtosa corrm corrms corrvc corrx corrxs ' + + 'cos cosh counts countwts crossprd crout croutp csrcol csrlin csvReadM csvReadSA cumprodc cumsumc curve cvtos ' + + 'datacreate datacreatecomplex datalist dataload dataloop dataopen datasave date datestr datestring datestrymd ' + + 'dayinyr dayofweek dbAddDatabase dbClose dbCommit dbCreateQuery dbExecQuery dbGetConnectOptions dbGetDatabaseName ' + + 'dbGetDriverName dbGetDrivers dbGetHostName dbGetLastErrorNum dbGetLastErrorText dbGetNumericalPrecPolicy ' + + 'dbGetPassword dbGetPort dbGetTableHeaders dbGetTables dbGetUserName dbHasFeature dbIsDriverAvailable dbIsOpen ' + + 'dbIsOpenError dbOpen dbQueryBindValue dbQueryClear dbQueryCols dbQueryExecPrepared dbQueryFetchAllM dbQueryFetchAllSA ' + + 'dbQueryFetchOneM dbQueryFetchOneSA dbQueryFinish dbQueryGetBoundValue dbQueryGetBoundValues dbQueryGetField ' + + 'dbQueryGetLastErrorNum dbQueryGetLastErrorText dbQueryGetLastInsertID dbQueryGetLastQuery dbQueryGetPosition ' + + 'dbQueryIsActive dbQueryIsForwardOnly dbQueryIsNull dbQueryIsSelect dbQueryIsValid dbQueryPrepare dbQueryRows ' + + 'dbQuerySeek dbQuerySeekFirst dbQuerySeekLast dbQuerySeekNext dbQuerySeekPrevious dbQuerySetForwardOnly ' + + 'dbRemoveDatabase dbRollback dbSetConnectOptions dbSetDatabaseName dbSetHostName dbSetNumericalPrecPolicy ' + + 'dbSetPort dbSetUserName dbTransaction DeleteFile delif delrows denseToSp denseToSpRE denToZero design det detl ' + + 'dfft dffti diag diagrv digamma doswin DOSWinCloseall DOSWinOpen dotfeq dotfeqmt dotfge dotfgemt dotfgt dotfgtmt ' + + 'dotfle dotflemt dotflt dotfltmt dotfne dotfnemt draw drop dsCreate dstat dstatmt dstatmtControlCreate dtdate dtday ' + + 'dttime dttodtv dttostr dttoutc dtvnormal dtvtodt dtvtoutc dummy dummybr dummydn eig eigh eighv eigv elapsedTradingDays ' + + 'endwind envget eof eqSolve eqSolvemt eqSolvemtControlCreate eqSolvemtOutCreate eqSolveset erf erfc erfccplx erfcplx error ' + + 'etdays ethsec etstr EuropeanBinomCall EuropeanBinomCall_Greeks EuropeanBinomCall_ImpVol EuropeanBinomPut ' + + 'EuropeanBinomPut_Greeks EuropeanBinomPut_ImpVol EuropeanBSCall EuropeanBSCall_Greeks EuropeanBSCall_ImpVol ' + + 'EuropeanBSPut EuropeanBSPut_Greeks EuropeanBSPut_ImpVol exctsmpl exec execbg exp extern eye fcheckerr fclearerr feq ' + + 'feqmt fflush fft ffti fftm fftmi fftn fge fgemt fgets fgetsa fgetsat fgetst fgt fgtmt fileinfo filesa fle flemt ' + + 'floor flt fltmt fmod fne fnemt fonts fopen formatcv formatnv fputs fputst fseek fstrerror ftell ftocv ftos ftostrC ' + + 'gamma gammacplx gammaii gausset gdaAppend gdaCreate gdaDStat gdaDStatMat gdaGetIndex gdaGetName gdaGetNames gdaGetOrders ' + + 'gdaGetType gdaGetTypes gdaGetVarInfo gdaIsCplx gdaLoad gdaPack gdaRead gdaReadByIndex gdaReadSome gdaReadSparse ' + + 'gdaReadStruct gdaReportVarInfo gdaSave gdaUpdate gdaUpdateAndPack gdaVars gdaWrite gdaWrite32 gdaWriteSome getarray ' + + 'getdims getf getGAUSShome getmatrix getmatrix4D getname getnamef getNextTradingDay getNextWeekDay getnr getorders ' + + 'getpath getPreviousTradingDay getPreviousWeekDay getRow getscalar3D getscalar4D getTrRow getwind glm gradcplx gradMT ' + + 'gradMTm gradMTT gradMTTm gradp graphprt graphset hasimag header headermt hess hessMT hessMTg hessMTgw hessMTm ' + + 'hessMTmw hessMTT hessMTTg hessMTTgw hessMTTm hessMTw hessp hist histf histp hsec imag indcv indexcat indices indices2 ' + + 'indicesf indicesfn indnv indsav integrate1d integrateControlCreate intgrat2 intgrat3 inthp1 inthp2 inthp3 inthp4 ' + + 'inthpControlCreate intquad1 intquad2 intquad3 intrleav intrleavsa intrsect intsimp inv invpd invswp iscplx iscplxf ' + + 'isden isinfnanmiss ismiss key keyav keyw lag lag1 lagn lapEighb lapEighi lapEighvb lapEighvi lapgEig lapgEigh lapgEighv ' + + 'lapgEigv lapgSchur lapgSvdcst lapgSvds lapgSvdst lapSvdcusv lapSvds lapSvdusv ldlp ldlsol linSolve listwise ln lncdfbvn ' + + 'lncdfbvn2 lncdfmvn lncdfn lncdfn2 lncdfnc lnfact lngammacplx lnpdfmvn lnpdfmvt lnpdfn lnpdft loadd loadstruct loadwind ' + + 'loess loessmt loessmtControlCreate log loglog logx logy lower lowmat lowmat1 ltrisol lu lusol machEpsilon make makevars ' + + 'makewind margin matalloc matinit mattoarray maxbytes maxc maxindc maxv maxvec mbesselei mbesselei0 mbesselei1 mbesseli ' + + 'mbesseli0 mbesseli1 meanc median mergeby mergevar minc minindc minv miss missex missrv moment momentd movingave ' + + 'movingaveExpwgt movingaveWgt nextindex nextn nextnevn nextwind ntos null null1 numCombinations ols olsmt olsmtControlCreate ' + + 'olsqr olsqr2 olsqrmt ones optn optnevn orth outtyp pacf packedToSp packr parse pause pdfCauchy pdfChi pdfExp pdfGenPareto ' + + 'pdfHyperGeo pdfLaplace pdfLogistic pdfn pdfPoisson pdfRayleigh pdfWeibull pi pinv pinvmt plotAddArrow plotAddBar plotAddBox ' + + 'plotAddHist plotAddHistF plotAddHistP plotAddPolar plotAddScatter plotAddShape plotAddTextbox plotAddTS plotAddXY plotArea ' + + 'plotBar plotBox plotClearLayout plotContour plotCustomLayout plotGetDefaults plotHist plotHistF plotHistP plotLayout ' + + 'plotLogLog plotLogX plotLogY plotOpenWindow plotPolar plotSave plotScatter plotSetAxesPen plotSetBar plotSetBarFill ' + + 'plotSetBarStacked plotSetBkdColor plotSetFill plotSetGrid plotSetLegend plotSetLineColor plotSetLineStyle plotSetLineSymbol ' + + 'plotSetLineThickness plotSetNewWindow plotSetTitle plotSetWhichYAxis plotSetXAxisShow plotSetXLabel plotSetXRange ' + + 'plotSetXTicInterval plotSetXTicLabel plotSetYAxisShow plotSetYLabel plotSetYRange plotSetZAxisShow plotSetZLabel ' + + 'plotSurface plotTS plotXY polar polychar polyeval polygamma polyint polymake polymat polymroot polymult polyroot ' + + 'pqgwin previousindex princomp printfm printfmt prodc psi putarray putf putvals pvCreate pvGetIndex pvGetParNames ' + + 'pvGetParVector pvLength pvList pvPack pvPacki pvPackm pvPackmi pvPacks pvPacksi pvPacksm pvPacksmi pvPutParVector ' + + 'pvTest pvUnpack QNewton QNewtonmt QNewtonmtControlCreate QNewtonmtOutCreate QNewtonSet QProg QProgmt QProgmtInCreate ' + + 'qqr qqre qqrep qr qre qrep qrsol qrtsol qtyr qtyre qtyrep quantile quantiled qyr qyre qyrep qz rank rankindx readr ' + + 'real reclassify reclassifyCuts recode recserar recsercp recserrc rerun rescale reshape rets rev rfft rffti rfftip rfftn ' + + 'rfftnp rfftp rndBernoulli rndBeta rndBinomial rndCauchy rndChiSquare rndCon rndCreateState rndExp rndGamma rndGeo rndGumbel ' + + 'rndHyperGeo rndi rndKMbeta rndKMgam rndKMi rndKMn rndKMnb rndKMp rndKMu rndKMvm rndLaplace rndLCbeta rndLCgam rndLCi rndLCn ' + + 'rndLCnb rndLCp rndLCu rndLCvm rndLogNorm rndMTu rndMVn rndMVt rndn rndnb rndNegBinomial rndp rndPoisson rndRayleigh ' + + 'rndStateSkip rndu rndvm rndWeibull rndWishart rotater round rows rowsf rref sampleData satostrC saved saveStruct savewind ' + + 'scale scale3d scalerr scalinfnanmiss scalmiss schtoc schur searchsourcepath seekr select selif seqa seqm setdif setdifsa ' + + 'setvars setvwrmode setwind shell shiftr sin singleindex sinh sleep solpd sortc sortcc sortd sorthc sorthcc sortind ' + + 'sortindc sortmc sortr sortrc spBiconjGradSol spChol spConjGradSol spCreate spDenseSubmat spDiagRvMat spEigv spEye spLDL ' + + 'spline spLU spNumNZE spOnes spreadSheetReadM spreadSheetReadSA spreadSheetWrite spScale spSubmat spToDense spTrTDense ' + + 'spTScalar spZeros sqpSolve sqpSolveMT sqpSolveMTControlCreate sqpSolveMTlagrangeCreate sqpSolveMToutCreate sqpSolveSet ' + + 'sqrt statements stdc stdsc stocv stof strcombine strindx strlen strput strrindx strsect strsplit strsplitPad strtodt ' + + 'strtof strtofcplx strtriml strtrimr strtrunc strtruncl strtruncpad strtruncr submat subscat substute subvec sumc sumr ' + + 'surface svd svd1 svd2 svdcusv svds svdusv sysstate tab tan tanh tempname ' + + 'time timedt timestr timeutc title tkf2eps tkf2ps tocart todaydt toeplitz token topolar trapchk ' + + 'trigamma trimr trunc type typecv typef union unionsa uniqindx uniqindxsa unique uniquesa upmat upmat1 upper utctodt ' + + 'utctodtv utrisol vals varCovMS varCovXS varget vargetl varmall varmares varput varputl vartypef vcm vcms vcx vcxs ' + + 'vec vech vecr vector vget view viewxyz vlist vnamecv volume vput vread vtypecv wait waitc walkindex where window ' + + 'writer xlabel xlsGetSheetCount xlsGetSheetSize xlsGetSheetTypes xlsMakeRange xlsReadM xlsReadSA xlsWrite xlsWriteM ' + + 'xlsWriteSA xpnd xtics xy xyz ylabel ytics zeros zeta zlabel ztics cdfEmpirical dot h5create h5open h5read h5readAttribute ' + + 'h5write h5writeAttribute ldl plotAddErrorBar plotAddSurface plotCDFEmpirical plotSetColormap plotSetContourLabels ' + + 'plotSetLegendFont plotSetTextInterpreter plotSetXTicCount plotSetYTicCount plotSetZLevels powerm strjoin sylvester ' + + 'strtrim', + literal: 'DB_AFTER_LAST_ROW DB_ALL_TABLES DB_BATCH_OPERATIONS DB_BEFORE_FIRST_ROW DB_BLOB DB_EVENT_NOTIFICATIONS ' + + 'DB_FINISH_QUERY DB_HIGH_PRECISION DB_LAST_INSERT_ID DB_LOW_PRECISION_DOUBLE DB_LOW_PRECISION_INT32 ' + + 'DB_LOW_PRECISION_INT64 DB_LOW_PRECISION_NUMBERS DB_MULTIPLE_RESULT_SETS DB_NAMED_PLACEHOLDERS ' + + 'DB_POSITIONAL_PLACEHOLDERS DB_PREPARED_QUERIES DB_QUERY_SIZE DB_SIMPLE_LOCKING DB_SYSTEM_TABLES DB_TABLES ' + + 'DB_TRANSACTIONS DB_UNICODE DB_VIEWS __STDIN __STDOUT __STDERR __FILE_DIR' + }; + + const AT_COMMENT_MODE = hljs.COMMENT('@', '@'); + + const PREPROCESSOR = + { + className: 'meta', + begin: '#', + end: '$', + keywords: { keyword: 'define definecs|10 undef ifdef ifndef iflight ifdllcall ifmac ifos2win ifunix else endif lineson linesoff srcfile srcline' }, + contains: [ + { + begin: /\\\n/, + relevance: 0 + }, + { + beginKeywords: 'include', + end: '$', + keywords: { keyword: 'include' }, + contains: [ + { + className: 'string', + begin: '"', + end: '"', + illegal: '\\n' + } + ] + }, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + AT_COMMENT_MODE + ] + }; + + const STRUCT_TYPE = + { + begin: /\bstruct\s+/, + end: /\s/, + keywords: "struct", + contains: [ + { + className: "type", + begin: hljs.UNDERSCORE_IDENT_RE, + relevance: 0 + } + ] + }; + + // only for definitions + const PARSE_PARAMS = [ + { + className: 'params', + begin: /\(/, + end: /\)/, + excludeBegin: true, + excludeEnd: true, + endsWithParent: true, + relevance: 0, + contains: [ + { // dots + className: 'literal', + begin: /\.\.\./ + }, + hljs.C_NUMBER_MODE, + hljs.C_BLOCK_COMMENT_MODE, + AT_COMMENT_MODE, + STRUCT_TYPE + ] + } + ]; + + const FUNCTION_DEF = + { + className: "title", + begin: hljs.UNDERSCORE_IDENT_RE, + relevance: 0 + }; + + const DEFINITION = function(beginKeywords, end, inherits) { + const mode = hljs.inherit( + { + className: "function", + beginKeywords: beginKeywords, + end: end, + excludeEnd: true, + contains: [].concat(PARSE_PARAMS) + }, + {} + ); + mode.contains.push(FUNCTION_DEF); + mode.contains.push(hljs.C_NUMBER_MODE); + mode.contains.push(hljs.C_BLOCK_COMMENT_MODE); + mode.contains.push(AT_COMMENT_MODE); + return mode; + }; + + const BUILT_IN_REF = + { // these are explicitly named internal function calls + className: 'built_in', + begin: '\\b(' + KEYWORDS.built_in.split(' ').join('|') + ')\\b' + }; + + const STRING_REF = + { + className: 'string', + begin: '"', + end: '"', + contains: [ hljs.BACKSLASH_ESCAPE ], + relevance: 0 + }; + + const FUNCTION_REF = + { + // className: "fn_ref", + begin: hljs.UNDERSCORE_IDENT_RE + '\\s*\\(', + returnBegin: true, + keywords: KEYWORDS, + relevance: 0, + contains: [ + { beginKeywords: KEYWORDS.keyword }, + BUILT_IN_REF, + { // ambiguously named function calls get a relevance of 0 + className: 'built_in', + begin: hljs.UNDERSCORE_IDENT_RE, + relevance: 0 + } + ] + }; + + const FUNCTION_REF_PARAMS = + { + // className: "fn_ref_params", + begin: /\(/, + end: /\)/, + relevance: 0, + keywords: { + built_in: KEYWORDS.built_in, + literal: KEYWORDS.literal + }, + contains: [ + hljs.C_NUMBER_MODE, + hljs.C_BLOCK_COMMENT_MODE, + AT_COMMENT_MODE, + BUILT_IN_REF, + FUNCTION_REF, + STRING_REF, + 'self' + ] + }; + + FUNCTION_REF.contains.push(FUNCTION_REF_PARAMS); + + return { + name: 'GAUSS', + aliases: [ 'gss' ], + case_insensitive: true, // language is case-insensitive + keywords: KEYWORDS, + illegal: /(\{[%#]|[%#]\}| <- )/, + contains: [ + hljs.C_NUMBER_MODE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + AT_COMMENT_MODE, + STRING_REF, + PREPROCESSOR, + { + className: 'keyword', + begin: /\bexternal (matrix|string|array|sparse matrix|struct|proc|keyword|fn)/ + }, + DEFINITION('proc keyword', ';'), + DEFINITION('fn', '='), + { + beginKeywords: 'for threadfor', + end: /;/, + // end: /\(/, + relevance: 0, + contains: [ + hljs.C_BLOCK_COMMENT_MODE, + AT_COMMENT_MODE, + FUNCTION_REF_PARAMS + ] + }, + { // custom method guard + // excludes method names from keyword processing + variants: [ + { begin: hljs.UNDERSCORE_IDENT_RE + '\\.' + hljs.UNDERSCORE_IDENT_RE }, + { begin: hljs.UNDERSCORE_IDENT_RE + '\\s*=' } + ], + relevance: 0 + }, + FUNCTION_REF, + STRUCT_TYPE + ] + }; +} + +export { gauss as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/gauss.js.js b/frontend/node_modules/highlight.js/es/languages/gauss.js.js new file mode 100644 index 0000000..afb1be9 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/gauss.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/gauss" instead of "highlight.js/lib/languages/gauss.js"' + ); + } + } + emitWarning(); + import lang from './gauss.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/gcode.js b/frontend/node_modules/highlight.js/es/languages/gcode.js new file mode 100644 index 0000000..c52cbf1 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/gcode.js @@ -0,0 +1,189 @@ +/* + Language: G-code (ISO 6983) + Contributors: Adam Joseph Cook + Description: G-code syntax highlighter for Fanuc and other common CNC machine tool controls. + Website: https://www.sis.se/api/document/preview/911952/ + Category: hardware + */ + +function gcode(hljs) { + const regex = hljs.regex; + const GCODE_KEYWORDS = { + $pattern: /[A-Z]+|%/, + keyword: [ + // conditions + 'THEN', + 'ELSE', + 'ENDIF', + 'IF', + + // controls + 'GOTO', + 'DO', + 'WHILE', + 'WH', + 'END', + 'CALL', + + // scoping + 'SUB', + 'ENDSUB', + + // comparisons + 'EQ', + 'NE', + 'LT', + 'GT', + 'LE', + 'GE', + 'AND', + 'OR', + 'XOR', + + // start/end of program + '%' + ], + built_in: [ + 'ATAN', + 'ABS', + 'ACOS', + 'ASIN', + 'COS', + 'EXP', + 'FIX', + 'FUP', + 'ROUND', + 'LN', + 'SIN', + 'SQRT', + 'TAN', + 'EXISTS' + ] + }; + + + // TODO: post v12 lets use look-behind, until then \b and a callback filter will be used + // const LETTER_BOUNDARY_RE = /(?= '0' && charBeforeMatch <= '9') { + return; + } + + if (charBeforeMatch === '_') { + return; + } + + response.ignoreMatch(); + } + + const NUMBER_RE = /[+-]?((\.\d+)|(\d+)(\.\d*)?)/; + + const GENERAL_MISC_FUNCTION_RE = /[GM]\s*\d+(\.\d+)?/; + const TOOLS_RE = /T\s*\d+/; + const SUBROUTINE_RE = /O\s*\d+/; + const SUBROUTINE_NAMED_RE = /O<.+>/; + const AXES_RE = /[ABCUVWXYZ]\s*/; + const PARAMETERS_RE = /[FHIJKPQRS]\s*/; + + const GCODE_CODE = [ + // comments + hljs.COMMENT(/\(/, /\)/), + hljs.COMMENT(/;/, /$/), + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.C_NUMBER_MODE, + + // gcodes + { + scope: 'title.function', + variants: [ + // G General functions: G0, G5.1, G5.2, … + // M Misc functions: M0, M55.6, M199, … + { match: regex.concat(LETTER_BOUNDARY_RE, GENERAL_MISC_FUNCTION_RE) }, + { + begin: GENERAL_MISC_FUNCTION_RE, + 'on:begin': LETTER_BOUNDARY_CALLBACK + }, + // T Tools + { match: regex.concat(LETTER_BOUNDARY_RE, TOOLS_RE), }, + { + begin: TOOLS_RE, + 'on:begin': LETTER_BOUNDARY_CALLBACK + } + ] + }, + + { + scope: 'symbol', + variants: [ + // O Subroutine ID: O100, O110, … + { match: regex.concat(LETTER_BOUNDARY_RE, SUBROUTINE_RE) }, + { + begin: SUBROUTINE_RE, + 'on:begin': LETTER_BOUNDARY_CALLBACK + }, + // O Subroutine name: O, … + { match: regex.concat(LETTER_BOUNDARY_RE, SUBROUTINE_NAMED_RE) }, + { + begin: SUBROUTINE_NAMED_RE, + 'on:begin': LETTER_BOUNDARY_CALLBACK + }, + // Checksum at end of line: *71, *199, … + { match: /\*\s*\d+\s*$/ } + ] + }, + + { + scope: 'operator', // N Line number: N1, N2, N1020, … + match: /^N\s*\d+/ + }, + + { + scope: 'variable', + match: /-?#\s*\d+/ + }, + + { + scope: 'property', // Physical axes, + variants: [ + { match: regex.concat(LETTER_BOUNDARY_RE, AXES_RE, NUMBER_RE) }, + { + begin: regex.concat(AXES_RE, NUMBER_RE), + 'on:begin': LETTER_BOUNDARY_CALLBACK + }, + ] + }, + + { + scope: 'params', // Different types of parameters + variants: [ + { match: regex.concat(LETTER_BOUNDARY_RE, PARAMETERS_RE, NUMBER_RE) }, + { + begin: regex.concat(PARAMETERS_RE, NUMBER_RE), + 'on:begin': LETTER_BOUNDARY_CALLBACK + }, + ] + }, + ]; + + return { + name: 'G-code (ISO 6983)', + aliases: [ 'nc' ], + // Some implementations (CNC controls) of G-code are interoperable with uppercase and lowercase letters seamlessly. + // However, most prefer all uppercase and uppercase is customary. + case_insensitive: true, + // TODO: post v12 with the use of look-behind this can be enabled + disableAutodetect: true, + keywords: GCODE_KEYWORDS, + contains: GCODE_CODE + }; +} + +export { gcode as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/gcode.js.js b/frontend/node_modules/highlight.js/es/languages/gcode.js.js new file mode 100644 index 0000000..bd79f60 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/gcode.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/gcode" instead of "highlight.js/lib/languages/gcode.js"' + ); + } + } + emitWarning(); + import lang from './gcode.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/gherkin.js b/frontend/node_modules/highlight.js/es/languages/gherkin.js new file mode 100644 index 0000000..a708078 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/gherkin.js @@ -0,0 +1,49 @@ +/* + Language: Gherkin + Author: Sam Pikesley (@pikesley) + Description: Gherkin is the format for cucumber specifications. It is a domain specific language which helps you to describe business behavior without the need to go into detail of implementation. + Website: https://cucumber.io/docs/gherkin/ + */ + +function gherkin(hljs) { + return { + name: 'Gherkin', + aliases: [ 'feature' ], + keywords: 'Feature Background Ability Business\ Need Scenario Scenarios Scenario\ Outline Scenario\ Template Examples Given And Then But When', + contains: [ + { + className: 'symbol', + begin: '\\*', + relevance: 0 + }, + { + className: 'meta', + begin: '@[^@\\s]+' + }, + { + begin: '\\|', + end: '\\|\\w*$', + contains: [ + { + className: 'string', + begin: '[^|]+' + } + ] + }, + { + className: 'variable', + begin: '<', + end: '>' + }, + hljs.HASH_COMMENT_MODE, + { + className: 'string', + begin: '"""', + end: '"""' + }, + hljs.QUOTE_STRING_MODE + ] + }; +} + +export { gherkin as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/gherkin.js.js b/frontend/node_modules/highlight.js/es/languages/gherkin.js.js new file mode 100644 index 0000000..d06f6c2 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/gherkin.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/gherkin" instead of "highlight.js/lib/languages/gherkin.js"' + ); + } + } + emitWarning(); + import lang from './gherkin.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/glsl.js b/frontend/node_modules/highlight.js/es/languages/glsl.js new file mode 100644 index 0000000..53eb182 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/glsl.js @@ -0,0 +1,128 @@ +/* +Language: GLSL +Description: OpenGL Shading Language +Author: Sergey Tikhomirov +Website: https://en.wikipedia.org/wiki/OpenGL_Shading_Language +Category: graphics +*/ + +function glsl(hljs) { + return { + name: 'GLSL', + keywords: { + keyword: + // Statements + 'break continue discard do else for if return while switch case default ' + // Qualifiers + + 'attribute binding buffer ccw centroid centroid varying coherent column_major const cw ' + + 'depth_any depth_greater depth_less depth_unchanged early_fragment_tests equal_spacing ' + + 'flat fractional_even_spacing fractional_odd_spacing highp in index inout invariant ' + + 'invocations isolines layout line_strip lines lines_adjacency local_size_x local_size_y ' + + 'local_size_z location lowp max_vertices mediump noperspective offset origin_upper_left ' + + 'out packed patch pixel_center_integer point_mode points precise precision quads r11f_g11f_b10f ' + + 'r16 r16_snorm r16f r16i r16ui r32f r32i r32ui r8 r8_snorm r8i r8ui readonly restrict ' + + 'rg16 rg16_snorm rg16f rg16i rg16ui rg32f rg32i rg32ui rg8 rg8_snorm rg8i rg8ui rgb10_a2 ' + + 'rgb10_a2ui rgba16 rgba16_snorm rgba16f rgba16i rgba16ui rgba32f rgba32i rgba32ui rgba8 ' + + 'rgba8_snorm rgba8i rgba8ui row_major sample shared smooth std140 std430 stream triangle_strip ' + + 'triangles triangles_adjacency uniform varying vertices volatile writeonly', + type: + 'atomic_uint bool bvec2 bvec3 bvec4 dmat2 dmat2x2 dmat2x3 dmat2x4 dmat3 dmat3x2 dmat3x3 ' + + 'dmat3x4 dmat4 dmat4x2 dmat4x3 dmat4x4 double dvec2 dvec3 dvec4 float iimage1D iimage1DArray ' + + 'iimage2D iimage2DArray iimage2DMS iimage2DMSArray iimage2DRect iimage3D iimageBuffer ' + + 'iimageCube iimageCubeArray image1D image1DArray image2D image2DArray image2DMS image2DMSArray ' + + 'image2DRect image3D imageBuffer imageCube imageCubeArray int isampler1D isampler1DArray ' + + 'isampler2D isampler2DArray isampler2DMS isampler2DMSArray isampler2DRect isampler3D ' + + 'isamplerBuffer isamplerCube isamplerCubeArray ivec2 ivec3 ivec4 mat2 mat2x2 mat2x3 ' + + 'mat2x4 mat3 mat3x2 mat3x3 mat3x4 mat4 mat4x2 mat4x3 mat4x4 sampler1D sampler1DArray ' + + 'sampler1DArrayShadow sampler1DShadow sampler2D sampler2DArray sampler2DArrayShadow ' + + 'sampler2DMS sampler2DMSArray sampler2DRect sampler2DRectShadow sampler2DShadow sampler3D ' + + 'samplerBuffer samplerCube samplerCubeArray samplerCubeArrayShadow samplerCubeShadow ' + + 'image1D uimage1DArray uimage2D uimage2DArray uimage2DMS uimage2DMSArray uimage2DRect ' + + 'uimage3D uimageBuffer uimageCube uimageCubeArray uint usampler1D usampler1DArray ' + + 'usampler2D usampler2DArray usampler2DMS usampler2DMSArray usampler2DRect usampler3D ' + + 'samplerBuffer usamplerCube usamplerCubeArray uvec2 uvec3 uvec4 vec2 vec3 vec4 void', + built_in: + // Constants + 'gl_MaxAtomicCounterBindings gl_MaxAtomicCounterBufferSize gl_MaxClipDistances gl_MaxClipPlanes ' + + 'gl_MaxCombinedAtomicCounterBuffers gl_MaxCombinedAtomicCounters gl_MaxCombinedImageUniforms ' + + 'gl_MaxCombinedImageUnitsAndFragmentOutputs gl_MaxCombinedTextureImageUnits gl_MaxComputeAtomicCounterBuffers ' + + 'gl_MaxComputeAtomicCounters gl_MaxComputeImageUniforms gl_MaxComputeTextureImageUnits ' + + 'gl_MaxComputeUniformComponents gl_MaxComputeWorkGroupCount gl_MaxComputeWorkGroupSize ' + + 'gl_MaxDrawBuffers gl_MaxFragmentAtomicCounterBuffers gl_MaxFragmentAtomicCounters ' + + 'gl_MaxFragmentImageUniforms gl_MaxFragmentInputComponents gl_MaxFragmentInputVectors ' + + 'gl_MaxFragmentUniformComponents gl_MaxFragmentUniformVectors gl_MaxGeometryAtomicCounterBuffers ' + + 'gl_MaxGeometryAtomicCounters gl_MaxGeometryImageUniforms gl_MaxGeometryInputComponents ' + + 'gl_MaxGeometryOutputComponents gl_MaxGeometryOutputVertices gl_MaxGeometryTextureImageUnits ' + + 'gl_MaxGeometryTotalOutputComponents gl_MaxGeometryUniformComponents gl_MaxGeometryVaryingComponents ' + + 'gl_MaxImageSamples gl_MaxImageUnits gl_MaxLights gl_MaxPatchVertices gl_MaxProgramTexelOffset ' + + 'gl_MaxTessControlAtomicCounterBuffers gl_MaxTessControlAtomicCounters gl_MaxTessControlImageUniforms ' + + 'gl_MaxTessControlInputComponents gl_MaxTessControlOutputComponents gl_MaxTessControlTextureImageUnits ' + + 'gl_MaxTessControlTotalOutputComponents gl_MaxTessControlUniformComponents ' + + 'gl_MaxTessEvaluationAtomicCounterBuffers gl_MaxTessEvaluationAtomicCounters ' + + 'gl_MaxTessEvaluationImageUniforms gl_MaxTessEvaluationInputComponents gl_MaxTessEvaluationOutputComponents ' + + 'gl_MaxTessEvaluationTextureImageUnits gl_MaxTessEvaluationUniformComponents ' + + 'gl_MaxTessGenLevel gl_MaxTessPatchComponents gl_MaxTextureCoords gl_MaxTextureImageUnits ' + + 'gl_MaxTextureUnits gl_MaxVaryingComponents gl_MaxVaryingFloats gl_MaxVaryingVectors ' + + 'gl_MaxVertexAtomicCounterBuffers gl_MaxVertexAtomicCounters gl_MaxVertexAttribs gl_MaxVertexImageUniforms ' + + 'gl_MaxVertexOutputComponents gl_MaxVertexOutputVectors gl_MaxVertexTextureImageUnits ' + + 'gl_MaxVertexUniformComponents gl_MaxVertexUniformVectors gl_MaxViewports gl_MinProgramTexelOffset ' + // Variables + + 'gl_BackColor gl_BackLightModelProduct gl_BackLightProduct gl_BackMaterial ' + + 'gl_BackSecondaryColor gl_ClipDistance gl_ClipPlane gl_ClipVertex gl_Color ' + + 'gl_DepthRange gl_EyePlaneQ gl_EyePlaneR gl_EyePlaneS gl_EyePlaneT gl_Fog gl_FogCoord ' + + 'gl_FogFragCoord gl_FragColor gl_FragCoord gl_FragData gl_FragDepth gl_FrontColor ' + + 'gl_FrontFacing gl_FrontLightModelProduct gl_FrontLightProduct gl_FrontMaterial ' + + 'gl_FrontSecondaryColor gl_GlobalInvocationID gl_InstanceID gl_InvocationID gl_Layer gl_LightModel ' + + 'gl_LightSource gl_LocalInvocationID gl_LocalInvocationIndex gl_ModelViewMatrix ' + + 'gl_ModelViewMatrixInverse gl_ModelViewMatrixInverseTranspose gl_ModelViewMatrixTranspose ' + + 'gl_ModelViewProjectionMatrix gl_ModelViewProjectionMatrixInverse gl_ModelViewProjectionMatrixInverseTranspose ' + + 'gl_ModelViewProjectionMatrixTranspose gl_MultiTexCoord0 gl_MultiTexCoord1 gl_MultiTexCoord2 ' + + 'gl_MultiTexCoord3 gl_MultiTexCoord4 gl_MultiTexCoord5 gl_MultiTexCoord6 gl_MultiTexCoord7 ' + + 'gl_Normal gl_NormalMatrix gl_NormalScale gl_NumSamples gl_NumWorkGroups gl_ObjectPlaneQ ' + + 'gl_ObjectPlaneR gl_ObjectPlaneS gl_ObjectPlaneT gl_PatchVerticesIn gl_Point gl_PointCoord ' + + 'gl_PointSize gl_Position gl_PrimitiveID gl_PrimitiveIDIn gl_ProjectionMatrix gl_ProjectionMatrixInverse ' + + 'gl_ProjectionMatrixInverseTranspose gl_ProjectionMatrixTranspose gl_SampleID gl_SampleMask ' + + 'gl_SampleMaskIn gl_SamplePosition gl_SecondaryColor gl_TessCoord gl_TessLevelInner gl_TessLevelOuter ' + + 'gl_TexCoord gl_TextureEnvColor gl_TextureMatrix gl_TextureMatrixInverse gl_TextureMatrixInverseTranspose ' + + 'gl_TextureMatrixTranspose gl_Vertex gl_VertexID gl_ViewportIndex gl_WorkGroupID gl_WorkGroupSize gl_in gl_out ' + // Functions + + 'EmitStreamVertex EmitVertex EndPrimitive EndStreamPrimitive abs acos acosh all any asin ' + + 'asinh atan atanh atomicAdd atomicAnd atomicCompSwap atomicCounter atomicCounterDecrement ' + + 'atomicCounterIncrement atomicExchange atomicMax atomicMin atomicOr atomicXor barrier ' + + 'bitCount bitfieldExtract bitfieldInsert bitfieldReverse ceil clamp cos cosh cross ' + + 'dFdx dFdy degrees determinant distance dot equal exp exp2 faceforward findLSB findMSB ' + + 'floatBitsToInt floatBitsToUint floor fma fract frexp ftransform fwidth greaterThan ' + + 'greaterThanEqual groupMemoryBarrier imageAtomicAdd imageAtomicAnd imageAtomicCompSwap ' + + 'imageAtomicExchange imageAtomicMax imageAtomicMin imageAtomicOr imageAtomicXor imageLoad ' + + 'imageSize imageStore imulExtended intBitsToFloat interpolateAtCentroid interpolateAtOffset ' + + 'interpolateAtSample inverse inversesqrt isinf isnan ldexp length lessThan lessThanEqual log ' + + 'log2 matrixCompMult max memoryBarrier memoryBarrierAtomicCounter memoryBarrierBuffer ' + + 'memoryBarrierImage memoryBarrierShared min mix mod modf noise1 noise2 noise3 noise4 ' + + 'normalize not notEqual outerProduct packDouble2x32 packHalf2x16 packSnorm2x16 packSnorm4x8 ' + + 'packUnorm2x16 packUnorm4x8 pow radians reflect refract round roundEven shadow1D shadow1DLod ' + + 'shadow1DProj shadow1DProjLod shadow2D shadow2DLod shadow2DProj shadow2DProjLod sign sin sinh ' + + 'smoothstep sqrt step tan tanh texelFetch texelFetchOffset texture texture1D texture1DLod ' + + 'texture1DProj texture1DProjLod texture2D texture2DLod texture2DProj texture2DProjLod ' + + 'texture3D texture3DLod texture3DProj texture3DProjLod textureCube textureCubeLod ' + + 'textureGather textureGatherOffset textureGatherOffsets textureGrad textureGradOffset ' + + 'textureLod textureLodOffset textureOffset textureProj textureProjGrad textureProjGradOffset ' + + 'textureProjLod textureProjLodOffset textureProjOffset textureQueryLevels textureQueryLod ' + + 'textureSize transpose trunc uaddCarry uintBitsToFloat umulExtended unpackDouble2x32 ' + + 'unpackHalf2x16 unpackSnorm2x16 unpackSnorm4x8 unpackUnorm2x16 unpackUnorm4x8 usubBorrow', + literal: 'true false' + }, + illegal: '"', + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.C_NUMBER_MODE, + { + className: 'meta', + begin: '#', + end: '$' + } + ] + }; +} + +export { glsl as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/glsl.js.js b/frontend/node_modules/highlight.js/es/languages/glsl.js.js new file mode 100644 index 0000000..38eb353 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/glsl.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/glsl" instead of "highlight.js/lib/languages/glsl.js"' + ); + } + } + emitWarning(); + import lang from './glsl.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/gml.js b/frontend/node_modules/highlight.js/es/languages/gml.js new file mode 100644 index 0000000..4f1bc0f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/gml.js @@ -0,0 +1,3130 @@ +/* +Language: GML +Description: Game Maker Language for GameMaker (rev. 2023.1) +Website: https://manual.yoyogames.com/ +Category: scripting +*/ + +function gml(hljs) { + const KEYWORDS = [ + "#endregion", + "#macro", + "#region", + "and", + "begin", + "break", + "case", + "constructor", + "continue", + "default", + "delete", + "div", + "do", + "else", + "end", + "enum", + "exit", + "for", + "function", + "globalvar", + "if", + "mod", + "new", + "not", + "or", + "repeat", + "return", + "static", + "switch", + "then", + "until", + "var", + "while", + "with", + "xor" + ]; + + const BUILT_INS = [ + "abs", + "alarm_get", + "alarm_set", + "angle_difference", + "animcurve_channel_evaluate", + "animcurve_channel_new", + "animcurve_create", + "animcurve_destroy", + "animcurve_exists", + "animcurve_get", + "animcurve_get_channel", + "animcurve_get_channel_index", + "animcurve_point_new", + "ansi_char", + "application_get_position", + "application_surface_draw_enable", + "application_surface_enable", + "application_surface_is_enabled", + "arccos", + "arcsin", + "arctan", + "arctan2", + "array_all", + "array_any", + "array_concat", + "array_contains", + "array_contains_ext", + "array_copy", + "array_copy_while", + "array_create", + "array_create_ext", + "array_delete", + "array_equals", + "array_filter", + "array_filter_ext", + "array_find_index", + "array_first", + "array_foreach", + "array_get", + "array_get_index", + "array_insert", + "array_intersection", + "array_last", + "array_length", + "array_map", + "array_map_ext", + "array_pop", + "array_push", + "array_reduce", + "array_resize", + "array_reverse", + "array_reverse_ext", + "array_set", + "array_shuffle", + "array_shuffle_ext", + "array_sort", + "array_union", + "array_unique", + "array_unique_ext", + "asset_add_tags", + "asset_clear_tags", + "asset_get_ids", + "asset_get_index", + "asset_get_tags", + "asset_get_type", + "asset_has_any_tag", + "asset_has_tags", + "asset_remove_tags", + "audio_bus_clear_emitters", + "audio_bus_create", + "audio_bus_get_emitters", + "audio_channel_num", + "audio_create_buffer_sound", + "audio_create_play_queue", + "audio_create_stream", + "audio_create_sync_group", + "audio_debug", + "audio_destroy_stream", + "audio_destroy_sync_group", + "audio_effect_create", + "audio_emitter_bus", + "audio_emitter_create", + "audio_emitter_exists", + "audio_emitter_falloff", + "audio_emitter_free", + "audio_emitter_gain", + "audio_emitter_get_bus", + "audio_emitter_get_gain", + "audio_emitter_get_listener_mask", + "audio_emitter_get_pitch", + "audio_emitter_get_vx", + "audio_emitter_get_vy", + "audio_emitter_get_vz", + "audio_emitter_get_x", + "audio_emitter_get_y", + "audio_emitter_get_z", + "audio_emitter_pitch", + "audio_emitter_position", + "audio_emitter_set_listener_mask", + "audio_emitter_velocity", + "audio_exists", + "audio_falloff_set_model", + "audio_free_buffer_sound", + "audio_free_play_queue", + "audio_get_listener_count", + "audio_get_listener_info", + "audio_get_listener_mask", + "audio_get_master_gain", + "audio_get_name", + "audio_get_recorder_count", + "audio_get_recorder_info", + "audio_get_type", + "audio_group_get_assets", + "audio_group_get_gain", + "audio_group_is_loaded", + "audio_group_load", + "audio_group_load_progress", + "audio_group_name", + "audio_group_set_gain", + "audio_group_stop_all", + "audio_group_unload", + "audio_is_paused", + "audio_is_playing", + "audio_listener_get_data", + "audio_listener_orientation", + "audio_listener_position", + "audio_listener_set_orientation", + "audio_listener_set_position", + "audio_listener_set_velocity", + "audio_listener_velocity", + "audio_master_gain", + "audio_pause_all", + "audio_pause_sound", + "audio_pause_sync_group", + "audio_play_in_sync_group", + "audio_play_sound", + "audio_play_sound_at", + "audio_play_sound_ext", + "audio_play_sound_on", + "audio_queue_sound", + "audio_resume_all", + "audio_resume_sound", + "audio_resume_sync_group", + "audio_set_listener_mask", + "audio_set_master_gain", + "audio_sound_gain", + "audio_sound_get_audio_group", + "audio_sound_get_gain", + "audio_sound_get_listener_mask", + "audio_sound_get_loop", + "audio_sound_get_loop_end", + "audio_sound_get_loop_start", + "audio_sound_get_pitch", + "audio_sound_get_track_position", + "audio_sound_is_playable", + "audio_sound_length", + "audio_sound_loop", + "audio_sound_loop_end", + "audio_sound_loop_start", + "audio_sound_pitch", + "audio_sound_set_listener_mask", + "audio_sound_set_track_position", + "audio_start_recording", + "audio_start_sync_group", + "audio_stop_all", + "audio_stop_recording", + "audio_stop_sound", + "audio_stop_sync_group", + "audio_sync_group_debug", + "audio_sync_group_get_track_pos", + "audio_sync_group_is_paused", + "audio_sync_group_is_playing", + "audio_system_is_available", + "audio_system_is_initialised", + "base64_decode", + "base64_encode", + "bool", + "browser_input_capture", + "buffer_async_group_begin", + "buffer_async_group_end", + "buffer_async_group_option", + "buffer_base64_decode", + "buffer_base64_decode_ext", + "buffer_base64_encode", + "buffer_compress", + "buffer_copy", + "buffer_copy_from_vertex_buffer", + "buffer_copy_stride", + "buffer_crc32", + "buffer_create", + "buffer_create_from_vertex_buffer", + "buffer_create_from_vertex_buffer_ext", + "buffer_decompress", + "buffer_delete", + "buffer_exists", + "buffer_fill", + "buffer_get_address", + "buffer_get_alignment", + "buffer_get_size", + "buffer_get_surface", + "buffer_get_type", + "buffer_load", + "buffer_load_async", + "buffer_load_ext", + "buffer_load_partial", + "buffer_md5", + "buffer_peek", + "buffer_poke", + "buffer_read", + "buffer_resize", + "buffer_save", + "buffer_save_async", + "buffer_save_ext", + "buffer_seek", + "buffer_set_surface", + "buffer_set_used_size", + "buffer_sha1", + "buffer_sizeof", + "buffer_tell", + "buffer_write", + "call_cancel", + "call_later", + "camera_apply", + "camera_copy_transforms", + "camera_create", + "camera_create_view", + "camera_destroy", + "camera_get_active", + "camera_get_begin_script", + "camera_get_default", + "camera_get_end_script", + "camera_get_proj_mat", + "camera_get_update_script", + "camera_get_view_angle", + "camera_get_view_border_x", + "camera_get_view_border_y", + "camera_get_view_height", + "camera_get_view_mat", + "camera_get_view_speed_x", + "camera_get_view_speed_y", + "camera_get_view_target", + "camera_get_view_width", + "camera_get_view_x", + "camera_get_view_y", + "camera_set_begin_script", + "camera_set_default", + "camera_set_end_script", + "camera_set_proj_mat", + "camera_set_update_script", + "camera_set_view_angle", + "camera_set_view_border", + "camera_set_view_mat", + "camera_set_view_pos", + "camera_set_view_size", + "camera_set_view_speed", + "camera_set_view_target", + "ceil", + "choose", + "chr", + "clamp", + "clickable_add", + "clickable_add_ext", + "clickable_change", + "clickable_change_ext", + "clickable_delete", + "clickable_exists", + "clickable_set_style", + "clipboard_get_text", + "clipboard_has_text", + "clipboard_set_text", + "cloud_file_save", + "cloud_string_save", + "cloud_synchronise", + "code_is_compiled", + "collision_circle", + "collision_circle_list", + "collision_ellipse", + "collision_ellipse_list", + "collision_line", + "collision_line_list", + "collision_point", + "collision_point_list", + "collision_rectangle", + "collision_rectangle_list", + "color_get_blue", + "color_get_green", + "color_get_hue", + "color_get_red", + "color_get_saturation", + "color_get_value", + "colour_get_blue", + "colour_get_green", + "colour_get_hue", + "colour_get_red", + "colour_get_saturation", + "colour_get_value", + "cos", + "darccos", + "darcsin", + "darctan", + "darctan2", + "date_compare_date", + "date_compare_datetime", + "date_compare_time", + "date_create_datetime", + "date_current_datetime", + "date_date_of", + "date_date_string", + "date_datetime_string", + "date_day_span", + "date_days_in_month", + "date_days_in_year", + "date_get_day", + "date_get_day_of_year", + "date_get_hour", + "date_get_hour_of_year", + "date_get_minute", + "date_get_minute_of_year", + "date_get_month", + "date_get_second", + "date_get_second_of_year", + "date_get_timezone", + "date_get_week", + "date_get_weekday", + "date_get_year", + "date_hour_span", + "date_inc_day", + "date_inc_hour", + "date_inc_minute", + "date_inc_month", + "date_inc_second", + "date_inc_week", + "date_inc_year", + "date_is_today", + "date_leap_year", + "date_minute_span", + "date_month_span", + "date_second_span", + "date_set_timezone", + "date_time_of", + "date_time_string", + "date_valid_datetime", + "date_week_span", + "date_year_span", + "db_to_lin", + "dbg_add_font_glyphs", + "dbg_button", + "dbg_checkbox", + "dbg_color", + "dbg_colour", + "dbg_drop_down", + "dbg_same_line", + "dbg_section", + "dbg_section_delete", + "dbg_section_exists", + "dbg_slider", + "dbg_slider_int", + "dbg_sprite", + "dbg_text", + "dbg_text_input", + "dbg_view", + "dbg_view_delete", + "dbg_view_exists", + "dbg_watch", + "dcos", + "debug_event", + "debug_get_callstack", + "degtorad", + "device_get_tilt_x", + "device_get_tilt_y", + "device_get_tilt_z", + "device_is_keypad_open", + "device_mouse_check_button", + "device_mouse_check_button_pressed", + "device_mouse_check_button_released", + "device_mouse_dbclick_enable", + "device_mouse_raw_x", + "device_mouse_raw_y", + "device_mouse_x", + "device_mouse_x_to_gui", + "device_mouse_y", + "device_mouse_y_to_gui", + "directory_create", + "directory_destroy", + "directory_exists", + "display_get_dpi_x", + "display_get_dpi_y", + "display_get_frequency", + "display_get_gui_height", + "display_get_gui_width", + "display_get_height", + "display_get_orientation", + "display_get_sleep_margin", + "display_get_timing_method", + "display_get_width", + "display_mouse_get_x", + "display_mouse_get_y", + "display_mouse_set", + "display_reset", + "display_set_gui_maximise", + "display_set_gui_maximize", + "display_set_gui_size", + "display_set_sleep_margin", + "display_set_timing_method", + "display_set_ui_visibility", + "distance_to_object", + "distance_to_point", + "dot_product", + "dot_product_3d", + "dot_product_3d_normalised", + "dot_product_3d_normalized", + "dot_product_normalised", + "dot_product_normalized", + "draw_arrow", + "draw_button", + "draw_circle", + "draw_circle_color", + "draw_circle_colour", + "draw_clear", + "draw_clear_alpha", + "draw_ellipse", + "draw_ellipse_color", + "draw_ellipse_colour", + "draw_enable_drawevent", + "draw_enable_skeleton_blendmodes", + "draw_enable_swf_aa", + "draw_flush", + "draw_get_alpha", + "draw_get_color", + "draw_get_colour", + "draw_get_enable_skeleton_blendmodes", + "draw_get_font", + "draw_get_halign", + "draw_get_lighting", + "draw_get_swf_aa_level", + "draw_get_valign", + "draw_getpixel", + "draw_getpixel_ext", + "draw_healthbar", + "draw_highscore", + "draw_light_define_ambient", + "draw_light_define_direction", + "draw_light_define_point", + "draw_light_enable", + "draw_light_get", + "draw_light_get_ambient", + "draw_line", + "draw_line_color", + "draw_line_colour", + "draw_line_width", + "draw_line_width_color", + "draw_line_width_colour", + "draw_path", + "draw_point", + "draw_point_color", + "draw_point_colour", + "draw_primitive_begin", + "draw_primitive_begin_texture", + "draw_primitive_end", + "draw_rectangle", + "draw_rectangle_color", + "draw_rectangle_colour", + "draw_roundrect", + "draw_roundrect_color", + "draw_roundrect_color_ext", + "draw_roundrect_colour", + "draw_roundrect_colour_ext", + "draw_roundrect_ext", + "draw_self", + "draw_set_alpha", + "draw_set_circle_precision", + "draw_set_color", + "draw_set_colour", + "draw_set_font", + "draw_set_halign", + "draw_set_lighting", + "draw_set_swf_aa_level", + "draw_set_valign", + "draw_skeleton", + "draw_skeleton_collision", + "draw_skeleton_instance", + "draw_skeleton_time", + "draw_sprite", + "draw_sprite_ext", + "draw_sprite_general", + "draw_sprite_part", + "draw_sprite_part_ext", + "draw_sprite_pos", + "draw_sprite_stretched", + "draw_sprite_stretched_ext", + "draw_sprite_tiled", + "draw_sprite_tiled_ext", + "draw_surface", + "draw_surface_ext", + "draw_surface_general", + "draw_surface_part", + "draw_surface_part_ext", + "draw_surface_stretched", + "draw_surface_stretched_ext", + "draw_surface_tiled", + "draw_surface_tiled_ext", + "draw_text", + "draw_text_color", + "draw_text_colour", + "draw_text_ext", + "draw_text_ext_color", + "draw_text_ext_colour", + "draw_text_ext_transformed", + "draw_text_ext_transformed_color", + "draw_text_ext_transformed_colour", + "draw_text_transformed", + "draw_text_transformed_color", + "draw_text_transformed_colour", + "draw_texture_flush", + "draw_tile", + "draw_tilemap", + "draw_triangle", + "draw_triangle_color", + "draw_triangle_colour", + "draw_vertex", + "draw_vertex_color", + "draw_vertex_colour", + "draw_vertex_texture", + "draw_vertex_texture_color", + "draw_vertex_texture_colour", + "ds_exists", + "ds_grid_add", + "ds_grid_add_disk", + "ds_grid_add_grid_region", + "ds_grid_add_region", + "ds_grid_clear", + "ds_grid_copy", + "ds_grid_create", + "ds_grid_destroy", + "ds_grid_get", + "ds_grid_get_disk_max", + "ds_grid_get_disk_mean", + "ds_grid_get_disk_min", + "ds_grid_get_disk_sum", + "ds_grid_get_max", + "ds_grid_get_mean", + "ds_grid_get_min", + "ds_grid_get_sum", + "ds_grid_height", + "ds_grid_multiply", + "ds_grid_multiply_disk", + "ds_grid_multiply_grid_region", + "ds_grid_multiply_region", + "ds_grid_read", + "ds_grid_resize", + "ds_grid_set", + "ds_grid_set_disk", + "ds_grid_set_grid_region", + "ds_grid_set_region", + "ds_grid_shuffle", + "ds_grid_sort", + "ds_grid_to_mp_grid", + "ds_grid_value_disk_exists", + "ds_grid_value_disk_x", + "ds_grid_value_disk_y", + "ds_grid_value_exists", + "ds_grid_value_x", + "ds_grid_value_y", + "ds_grid_width", + "ds_grid_write", + "ds_list_add", + "ds_list_clear", + "ds_list_copy", + "ds_list_create", + "ds_list_delete", + "ds_list_destroy", + "ds_list_empty", + "ds_list_find_index", + "ds_list_find_value", + "ds_list_insert", + "ds_list_is_list", + "ds_list_is_map", + "ds_list_mark_as_list", + "ds_list_mark_as_map", + "ds_list_read", + "ds_list_replace", + "ds_list_set", + "ds_list_shuffle", + "ds_list_size", + "ds_list_sort", + "ds_list_write", + "ds_map_add", + "ds_map_add_list", + "ds_map_add_map", + "ds_map_clear", + "ds_map_copy", + "ds_map_create", + "ds_map_delete", + "ds_map_destroy", + "ds_map_empty", + "ds_map_exists", + "ds_map_find_first", + "ds_map_find_last", + "ds_map_find_next", + "ds_map_find_previous", + "ds_map_find_value", + "ds_map_is_list", + "ds_map_is_map", + "ds_map_keys_to_array", + "ds_map_read", + "ds_map_replace", + "ds_map_replace_list", + "ds_map_replace_map", + "ds_map_secure_load", + "ds_map_secure_load_buffer", + "ds_map_secure_save", + "ds_map_secure_save_buffer", + "ds_map_set", + "ds_map_size", + "ds_map_values_to_array", + "ds_map_write", + "ds_priority_add", + "ds_priority_change_priority", + "ds_priority_clear", + "ds_priority_copy", + "ds_priority_create", + "ds_priority_delete_max", + "ds_priority_delete_min", + "ds_priority_delete_value", + "ds_priority_destroy", + "ds_priority_empty", + "ds_priority_find_max", + "ds_priority_find_min", + "ds_priority_find_priority", + "ds_priority_read", + "ds_priority_size", + "ds_priority_write", + "ds_queue_clear", + "ds_queue_copy", + "ds_queue_create", + "ds_queue_dequeue", + "ds_queue_destroy", + "ds_queue_empty", + "ds_queue_enqueue", + "ds_queue_head", + "ds_queue_read", + "ds_queue_size", + "ds_queue_tail", + "ds_queue_write", + "ds_set_precision", + "ds_stack_clear", + "ds_stack_copy", + "ds_stack_create", + "ds_stack_destroy", + "ds_stack_empty", + "ds_stack_pop", + "ds_stack_push", + "ds_stack_read", + "ds_stack_size", + "ds_stack_top", + "ds_stack_write", + "dsin", + "dtan", + "effect_clear", + "effect_create_above", + "effect_create_below", + "effect_create_depth", + "effect_create_layer", + "environment_get_variable", + "event_inherited", + "event_perform", + "event_perform_async", + "event_perform_object", + "event_user", + "exception_unhandled_handler", + "exp", + "extension_exists", + "extension_get_option_count", + "extension_get_option_names", + "extension_get_option_value", + "extension_get_options", + "extension_get_version", + "external_call", + "external_define", + "external_free", + "file_attributes", + "file_bin_close", + "file_bin_open", + "file_bin_position", + "file_bin_read_byte", + "file_bin_rewrite", + "file_bin_seek", + "file_bin_size", + "file_bin_write_byte", + "file_copy", + "file_delete", + "file_exists", + "file_find_close", + "file_find_first", + "file_find_next", + "file_rename", + "file_text_close", + "file_text_eof", + "file_text_eoln", + "file_text_open_append", + "file_text_open_from_string", + "file_text_open_read", + "file_text_open_write", + "file_text_read_real", + "file_text_read_string", + "file_text_readln", + "file_text_write_real", + "file_text_write_string", + "file_text_writeln", + "filename_change_ext", + "filename_dir", + "filename_drive", + "filename_ext", + "filename_name", + "filename_path", + "floor", + "font_add", + "font_add_enable_aa", + "font_add_get_enable_aa", + "font_add_sprite", + "font_add_sprite_ext", + "font_cache_glyph", + "font_delete", + "font_enable_effects", + "font_enable_sdf", + "font_exists", + "font_get_bold", + "font_get_first", + "font_get_fontname", + "font_get_info", + "font_get_italic", + "font_get_last", + "font_get_name", + "font_get_sdf_enabled", + "font_get_sdf_spread", + "font_get_size", + "font_get_texture", + "font_get_uvs", + "font_replace_sprite", + "font_replace_sprite_ext", + "font_sdf_spread", + "font_set_cache_size", + "frac", + "fx_create", + "fx_get_name", + "fx_get_parameter", + "fx_get_parameter_names", + "fx_get_parameters", + "fx_get_single_layer", + "fx_set_parameter", + "fx_set_parameters", + "fx_set_single_layer", + "game_change", + "game_end", + "game_get_speed", + "game_load", + "game_load_buffer", + "game_restart", + "game_save", + "game_save_buffer", + "game_set_speed", + "gamepad_axis_count", + "gamepad_axis_value", + "gamepad_button_check", + "gamepad_button_check_pressed", + "gamepad_button_check_released", + "gamepad_button_count", + "gamepad_button_value", + "gamepad_get_axis_deadzone", + "gamepad_get_button_threshold", + "gamepad_get_description", + "gamepad_get_device_count", + "gamepad_get_guid", + "gamepad_get_mapping", + "gamepad_get_option", + "gamepad_hat_count", + "gamepad_hat_value", + "gamepad_is_connected", + "gamepad_is_supported", + "gamepad_remove_mapping", + "gamepad_set_axis_deadzone", + "gamepad_set_button_threshold", + "gamepad_set_color", + "gamepad_set_colour", + "gamepad_set_option", + "gamepad_set_vibration", + "gamepad_test_mapping", + "gc_collect", + "gc_enable", + "gc_get_stats", + "gc_get_target_frame_time", + "gc_is_enabled", + "gc_target_frame_time", + "gesture_double_tap_distance", + "gesture_double_tap_time", + "gesture_drag_distance", + "gesture_drag_time", + "gesture_flick_speed", + "gesture_get_double_tap_distance", + "gesture_get_double_tap_time", + "gesture_get_drag_distance", + "gesture_get_drag_time", + "gesture_get_flick_speed", + "gesture_get_pinch_angle_away", + "gesture_get_pinch_angle_towards", + "gesture_get_pinch_distance", + "gesture_get_rotate_angle", + "gesture_get_rotate_time", + "gesture_get_tap_count", + "gesture_pinch_angle_away", + "gesture_pinch_angle_towards", + "gesture_pinch_distance", + "gesture_rotate_angle", + "gesture_rotate_time", + "gesture_tap_count", + "get_integer", + "get_integer_async", + "get_login_async", + "get_open_filename", + "get_open_filename_ext", + "get_save_filename", + "get_save_filename_ext", + "get_string", + "get_string_async", + "get_timer", + "gif_add_surface", + "gif_open", + "gif_save", + "gif_save_buffer", + "gml_pragma", + "gml_release_mode", + "gpu_get_alphatestenable", + "gpu_get_alphatestref", + "gpu_get_blendenable", + "gpu_get_blendmode", + "gpu_get_blendmode_dest", + "gpu_get_blendmode_destalpha", + "gpu_get_blendmode_ext", + "gpu_get_blendmode_ext_sepalpha", + "gpu_get_blendmode_src", + "gpu_get_blendmode_srcalpha", + "gpu_get_colorwriteenable", + "gpu_get_colourwriteenable", + "gpu_get_cullmode", + "gpu_get_depth", + "gpu_get_fog", + "gpu_get_state", + "gpu_get_tex_filter", + "gpu_get_tex_filter_ext", + "gpu_get_tex_max_aniso", + "gpu_get_tex_max_aniso_ext", + "gpu_get_tex_max_mip", + "gpu_get_tex_max_mip_ext", + "gpu_get_tex_min_mip", + "gpu_get_tex_min_mip_ext", + "gpu_get_tex_mip_bias", + "gpu_get_tex_mip_bias_ext", + "gpu_get_tex_mip_enable", + "gpu_get_tex_mip_enable_ext", + "gpu_get_tex_mip_filter", + "gpu_get_tex_mip_filter_ext", + "gpu_get_tex_repeat", + "gpu_get_tex_repeat_ext", + "gpu_get_texfilter", + "gpu_get_texfilter_ext", + "gpu_get_texrepeat", + "gpu_get_texrepeat_ext", + "gpu_get_zfunc", + "gpu_get_ztestenable", + "gpu_get_zwriteenable", + "gpu_pop_state", + "gpu_push_state", + "gpu_set_alphatestenable", + "gpu_set_alphatestref", + "gpu_set_blendenable", + "gpu_set_blendmode", + "gpu_set_blendmode_ext", + "gpu_set_blendmode_ext_sepalpha", + "gpu_set_colorwriteenable", + "gpu_set_colourwriteenable", + "gpu_set_cullmode", + "gpu_set_depth", + "gpu_set_fog", + "gpu_set_state", + "gpu_set_tex_filter", + "gpu_set_tex_filter_ext", + "gpu_set_tex_max_aniso", + "gpu_set_tex_max_aniso_ext", + "gpu_set_tex_max_mip", + "gpu_set_tex_max_mip_ext", + "gpu_set_tex_min_mip", + "gpu_set_tex_min_mip_ext", + "gpu_set_tex_mip_bias", + "gpu_set_tex_mip_bias_ext", + "gpu_set_tex_mip_enable", + "gpu_set_tex_mip_enable_ext", + "gpu_set_tex_mip_filter", + "gpu_set_tex_mip_filter_ext", + "gpu_set_tex_repeat", + "gpu_set_tex_repeat_ext", + "gpu_set_texfilter", + "gpu_set_texfilter_ext", + "gpu_set_texrepeat", + "gpu_set_texrepeat_ext", + "gpu_set_zfunc", + "gpu_set_ztestenable", + "gpu_set_zwriteenable", + "handle_parse", + "highscore_add", + "highscore_clear", + "highscore_name", + "highscore_value", + "http_get", + "http_get_file", + "http_get_request_crossorigin", + "http_post_string", + "http_request", + "http_set_request_crossorigin", + "iap_acquire", + "iap_activate", + "iap_consume", + "iap_enumerate_products", + "iap_product_details", + "iap_purchase_details", + "iap_restore_all", + "iap_status", + "ini_close", + "ini_key_delete", + "ini_key_exists", + "ini_open", + "ini_open_from_string", + "ini_read_real", + "ini_read_string", + "ini_section_delete", + "ini_section_exists", + "ini_write_real", + "ini_write_string", + "instance_activate_all", + "instance_activate_layer", + "instance_activate_object", + "instance_activate_region", + "instance_change", + "instance_copy", + "instance_create_depth", + "instance_create_layer", + "instance_deactivate_all", + "instance_deactivate_layer", + "instance_deactivate_object", + "instance_deactivate_region", + "instance_destroy", + "instance_exists", + "instance_find", + "instance_furthest", + "instance_id_get", + "instance_nearest", + "instance_number", + "instance_place", + "instance_place_list", + "instance_position", + "instance_position_list", + "instanceof", + "int64", + "io_clear", + "irandom", + "irandom_range", + "is_array", + "is_bool", + "is_callable", + "is_debug_overlay_open", + "is_handle", + "is_infinity", + "is_instanceof", + "is_int32", + "is_int64", + "is_keyboard_used_debug_overlay", + "is_method", + "is_mouse_over_debug_overlay", + "is_nan", + "is_numeric", + "is_ptr", + "is_real", + "is_string", + "is_struct", + "is_undefined", + "json_decode", + "json_encode", + "json_parse", + "json_stringify", + "keyboard_check", + "keyboard_check_direct", + "keyboard_check_pressed", + "keyboard_check_released", + "keyboard_clear", + "keyboard_get_map", + "keyboard_get_numlock", + "keyboard_key_press", + "keyboard_key_release", + "keyboard_set_map", + "keyboard_set_numlock", + "keyboard_unset_map", + "keyboard_virtual_height", + "keyboard_virtual_hide", + "keyboard_virtual_show", + "keyboard_virtual_status", + "layer_add_instance", + "layer_background_alpha", + "layer_background_blend", + "layer_background_change", + "layer_background_create", + "layer_background_destroy", + "layer_background_exists", + "layer_background_get_alpha", + "layer_background_get_blend", + "layer_background_get_htiled", + "layer_background_get_id", + "layer_background_get_index", + "layer_background_get_speed", + "layer_background_get_sprite", + "layer_background_get_stretch", + "layer_background_get_visible", + "layer_background_get_vtiled", + "layer_background_get_xscale", + "layer_background_get_yscale", + "layer_background_htiled", + "layer_background_index", + "layer_background_speed", + "layer_background_sprite", + "layer_background_stretch", + "layer_background_visible", + "layer_background_vtiled", + "layer_background_xscale", + "layer_background_yscale", + "layer_clear_fx", + "layer_create", + "layer_depth", + "layer_destroy", + "layer_destroy_instances", + "layer_element_move", + "layer_enable_fx", + "layer_exists", + "layer_force_draw_depth", + "layer_fx_is_enabled", + "layer_get_all", + "layer_get_all_elements", + "layer_get_depth", + "layer_get_element_layer", + "layer_get_element_type", + "layer_get_forced_depth", + "layer_get_fx", + "layer_get_hspeed", + "layer_get_id", + "layer_get_id_at_depth", + "layer_get_name", + "layer_get_script_begin", + "layer_get_script_end", + "layer_get_shader", + "layer_get_target_room", + "layer_get_visible", + "layer_get_vspeed", + "layer_get_x", + "layer_get_y", + "layer_has_instance", + "layer_hspeed", + "layer_instance_get_instance", + "layer_is_draw_depth_forced", + "layer_reset_target_room", + "layer_script_begin", + "layer_script_end", + "layer_sequence_angle", + "layer_sequence_create", + "layer_sequence_destroy", + "layer_sequence_exists", + "layer_sequence_get_angle", + "layer_sequence_get_headdir", + "layer_sequence_get_headpos", + "layer_sequence_get_instance", + "layer_sequence_get_length", + "layer_sequence_get_sequence", + "layer_sequence_get_speedscale", + "layer_sequence_get_x", + "layer_sequence_get_xscale", + "layer_sequence_get_y", + "layer_sequence_get_yscale", + "layer_sequence_headdir", + "layer_sequence_headpos", + "layer_sequence_is_finished", + "layer_sequence_is_paused", + "layer_sequence_pause", + "layer_sequence_play", + "layer_sequence_speedscale", + "layer_sequence_x", + "layer_sequence_xscale", + "layer_sequence_y", + "layer_sequence_yscale", + "layer_set_fx", + "layer_set_target_room", + "layer_set_visible", + "layer_shader", + "layer_sprite_alpha", + "layer_sprite_angle", + "layer_sprite_blend", + "layer_sprite_change", + "layer_sprite_create", + "layer_sprite_destroy", + "layer_sprite_exists", + "layer_sprite_get_alpha", + "layer_sprite_get_angle", + "layer_sprite_get_blend", + "layer_sprite_get_id", + "layer_sprite_get_index", + "layer_sprite_get_speed", + "layer_sprite_get_sprite", + "layer_sprite_get_x", + "layer_sprite_get_xscale", + "layer_sprite_get_y", + "layer_sprite_get_yscale", + "layer_sprite_index", + "layer_sprite_speed", + "layer_sprite_x", + "layer_sprite_xscale", + "layer_sprite_y", + "layer_sprite_yscale", + "layer_tile_alpha", + "layer_tile_blend", + "layer_tile_change", + "layer_tile_create", + "layer_tile_destroy", + "layer_tile_exists", + "layer_tile_get_alpha", + "layer_tile_get_blend", + "layer_tile_get_region", + "layer_tile_get_sprite", + "layer_tile_get_visible", + "layer_tile_get_x", + "layer_tile_get_xscale", + "layer_tile_get_y", + "layer_tile_get_yscale", + "layer_tile_region", + "layer_tile_visible", + "layer_tile_x", + "layer_tile_xscale", + "layer_tile_y", + "layer_tile_yscale", + "layer_tilemap_create", + "layer_tilemap_destroy", + "layer_tilemap_exists", + "layer_tilemap_get_id", + "layer_vspeed", + "layer_x", + "layer_y", + "lengthdir_x", + "lengthdir_y", + "lerp", + "lin_to_db", + "ln", + "load_csv", + "log10", + "log2", + "logn", + "make_color_hsv", + "make_color_rgb", + "make_colour_hsv", + "make_colour_rgb", + "math_get_epsilon", + "math_set_epsilon", + "matrix_build", + "matrix_build_identity", + "matrix_build_lookat", + "matrix_build_projection_ortho", + "matrix_build_projection_perspective", + "matrix_build_projection_perspective_fov", + "matrix_get", + "matrix_multiply", + "matrix_set", + "matrix_stack_clear", + "matrix_stack_is_empty", + "matrix_stack_pop", + "matrix_stack_push", + "matrix_stack_set", + "matrix_stack_top", + "matrix_transform_vertex", + "max", + "md5_file", + "md5_string_unicode", + "md5_string_utf8", + "mean", + "median", + "merge_color", + "merge_colour", + "method", + "method_call", + "method_get_index", + "method_get_self", + "min", + "motion_add", + "motion_set", + "mouse_check_button", + "mouse_check_button_pressed", + "mouse_check_button_released", + "mouse_clear", + "mouse_wheel_down", + "mouse_wheel_up", + "move_and_collide", + "move_bounce_all", + "move_bounce_solid", + "move_contact_all", + "move_contact_solid", + "move_outside_all", + "move_outside_solid", + "move_random", + "move_snap", + "move_towards_point", + "move_wrap", + "mp_grid_add_cell", + "mp_grid_add_instances", + "mp_grid_add_rectangle", + "mp_grid_clear_all", + "mp_grid_clear_cell", + "mp_grid_clear_rectangle", + "mp_grid_create", + "mp_grid_destroy", + "mp_grid_draw", + "mp_grid_get_cell", + "mp_grid_path", + "mp_grid_to_ds_grid", + "mp_linear_path", + "mp_linear_path_object", + "mp_linear_step", + "mp_linear_step_object", + "mp_potential_path", + "mp_potential_path_object", + "mp_potential_settings", + "mp_potential_step", + "mp_potential_step_object", + "nameof", + "network_connect", + "network_connect_async", + "network_connect_raw", + "network_connect_raw_async", + "network_create_server", + "network_create_server_raw", + "network_create_socket", + "network_create_socket_ext", + "network_destroy", + "network_resolve", + "network_send_broadcast", + "network_send_packet", + "network_send_raw", + "network_send_udp", + "network_send_udp_raw", + "network_set_config", + "network_set_timeout", + "object_exists", + "object_get_mask", + "object_get_name", + "object_get_parent", + "object_get_persistent", + "object_get_physics", + "object_get_solid", + "object_get_sprite", + "object_get_visible", + "object_is_ancestor", + "object_set_mask", + "object_set_persistent", + "object_set_solid", + "object_set_sprite", + "object_set_visible", + "ord", + "os_check_permission", + "os_get_config", + "os_get_info", + "os_get_language", + "os_get_region", + "os_is_network_connected", + "os_is_paused", + "os_lock_orientation", + "os_powersave_enable", + "os_request_permission", + "os_set_orientation_lock", + "parameter_count", + "parameter_string", + "part_emitter_burst", + "part_emitter_clear", + "part_emitter_create", + "part_emitter_delay", + "part_emitter_destroy", + "part_emitter_destroy_all", + "part_emitter_enable", + "part_emitter_exists", + "part_emitter_interval", + "part_emitter_region", + "part_emitter_relative", + "part_emitter_stream", + "part_particles_burst", + "part_particles_clear", + "part_particles_count", + "part_particles_create", + "part_particles_create_color", + "part_particles_create_colour", + "part_system_angle", + "part_system_automatic_draw", + "part_system_automatic_update", + "part_system_clear", + "part_system_color", + "part_system_colour", + "part_system_create", + "part_system_create_layer", + "part_system_depth", + "part_system_destroy", + "part_system_draw_order", + "part_system_drawit", + "part_system_exists", + "part_system_get_info", + "part_system_get_layer", + "part_system_global_space", + "part_system_layer", + "part_system_position", + "part_system_update", + "part_type_alpha1", + "part_type_alpha2", + "part_type_alpha3", + "part_type_blend", + "part_type_clear", + "part_type_color1", + "part_type_color2", + "part_type_color3", + "part_type_color_hsv", + "part_type_color_mix", + "part_type_color_rgb", + "part_type_colour1", + "part_type_colour2", + "part_type_colour3", + "part_type_colour_hsv", + "part_type_colour_mix", + "part_type_colour_rgb", + "part_type_create", + "part_type_death", + "part_type_destroy", + "part_type_direction", + "part_type_exists", + "part_type_gravity", + "part_type_life", + "part_type_orientation", + "part_type_scale", + "part_type_shape", + "part_type_size", + "part_type_size_x", + "part_type_size_y", + "part_type_speed", + "part_type_sprite", + "part_type_step", + "part_type_subimage", + "particle_exists", + "particle_get_info", + "path_add", + "path_add_point", + "path_append", + "path_assign", + "path_change_point", + "path_clear_points", + "path_delete", + "path_delete_point", + "path_duplicate", + "path_end", + "path_exists", + "path_flip", + "path_get_closed", + "path_get_kind", + "path_get_length", + "path_get_name", + "path_get_number", + "path_get_point_speed", + "path_get_point_x", + "path_get_point_y", + "path_get_precision", + "path_get_speed", + "path_get_x", + "path_get_y", + "path_insert_point", + "path_mirror", + "path_rescale", + "path_reverse", + "path_rotate", + "path_set_closed", + "path_set_kind", + "path_set_precision", + "path_shift", + "path_start", + "physics_apply_angular_impulse", + "physics_apply_force", + "physics_apply_impulse", + "physics_apply_local_force", + "physics_apply_local_impulse", + "physics_apply_torque", + "physics_draw_debug", + "physics_fixture_add_point", + "physics_fixture_bind", + "physics_fixture_bind_ext", + "physics_fixture_create", + "physics_fixture_delete", + "physics_fixture_set_angular_damping", + "physics_fixture_set_awake", + "physics_fixture_set_box_shape", + "physics_fixture_set_chain_shape", + "physics_fixture_set_circle_shape", + "physics_fixture_set_collision_group", + "physics_fixture_set_density", + "physics_fixture_set_edge_shape", + "physics_fixture_set_friction", + "physics_fixture_set_kinematic", + "physics_fixture_set_linear_damping", + "physics_fixture_set_polygon_shape", + "physics_fixture_set_restitution", + "physics_fixture_set_sensor", + "physics_get_density", + "physics_get_friction", + "physics_get_restitution", + "physics_joint_delete", + "physics_joint_distance_create", + "physics_joint_enable_motor", + "physics_joint_friction_create", + "physics_joint_gear_create", + "physics_joint_get_value", + "physics_joint_prismatic_create", + "physics_joint_pulley_create", + "physics_joint_revolute_create", + "physics_joint_rope_create", + "physics_joint_set_value", + "physics_joint_weld_create", + "physics_joint_wheel_create", + "physics_mass_properties", + "physics_particle_count", + "physics_particle_create", + "physics_particle_delete", + "physics_particle_delete_region_box", + "physics_particle_delete_region_circle", + "physics_particle_delete_region_poly", + "physics_particle_draw", + "physics_particle_draw_ext", + "physics_particle_get_damping", + "physics_particle_get_data", + "physics_particle_get_data_particle", + "physics_particle_get_density", + "physics_particle_get_gravity_scale", + "physics_particle_get_group_flags", + "physics_particle_get_max_count", + "physics_particle_get_radius", + "physics_particle_group_add_point", + "physics_particle_group_begin", + "physics_particle_group_box", + "physics_particle_group_circle", + "physics_particle_group_count", + "physics_particle_group_delete", + "physics_particle_group_end", + "physics_particle_group_get_ang_vel", + "physics_particle_group_get_angle", + "physics_particle_group_get_centre_x", + "physics_particle_group_get_centre_y", + "physics_particle_group_get_data", + "physics_particle_group_get_inertia", + "physics_particle_group_get_mass", + "physics_particle_group_get_vel_x", + "physics_particle_group_get_vel_y", + "physics_particle_group_get_x", + "physics_particle_group_get_y", + "physics_particle_group_join", + "physics_particle_group_polygon", + "physics_particle_set_category_flags", + "physics_particle_set_damping", + "physics_particle_set_density", + "physics_particle_set_flags", + "physics_particle_set_gravity_scale", + "physics_particle_set_group_flags", + "physics_particle_set_max_count", + "physics_particle_set_radius", + "physics_pause_enable", + "physics_remove_fixture", + "physics_set_density", + "physics_set_friction", + "physics_set_restitution", + "physics_test_overlap", + "physics_world_create", + "physics_world_draw_debug", + "physics_world_gravity", + "physics_world_update_iterations", + "physics_world_update_speed", + "place_empty", + "place_free", + "place_meeting", + "place_snapped", + "point_direction", + "point_distance", + "point_distance_3d", + "point_in_circle", + "point_in_rectangle", + "point_in_triangle", + "position_change", + "position_destroy", + "position_empty", + "position_meeting", + "power", + "ptr", + "radtodeg", + "random", + "random_get_seed", + "random_range", + "random_set_seed", + "randomise", + "randomize", + "real", + "rectangle_in_circle", + "rectangle_in_rectangle", + "rectangle_in_triangle", + "ref_create", + "rollback_chat", + "rollback_create_game", + "rollback_define_extra_network_latency", + "rollback_define_input", + "rollback_define_input_frame_delay", + "rollback_define_mock_input", + "rollback_define_player", + "rollback_display_events", + "rollback_get_info", + "rollback_get_input", + "rollback_get_player_prefs", + "rollback_join_game", + "rollback_leave_game", + "rollback_set_player_prefs", + "rollback_start_game", + "rollback_sync_on_frame", + "rollback_use_late_join", + "rollback_use_manual_start", + "rollback_use_player_prefs", + "rollback_use_random_input", + "room_add", + "room_assign", + "room_duplicate", + "room_exists", + "room_get_camera", + "room_get_info", + "room_get_name", + "room_get_viewport", + "room_goto", + "room_goto_next", + "room_goto_previous", + "room_instance_add", + "room_instance_clear", + "room_next", + "room_previous", + "room_restart", + "room_set_camera", + "room_set_height", + "room_set_persistent", + "room_set_view_enabled", + "room_set_viewport", + "room_set_width", + "round", + "scheduler_resolution_get", + "scheduler_resolution_set", + "screen_save", + "screen_save_part", + "script_execute", + "script_execute_ext", + "script_exists", + "script_get_name", + "sequence_create", + "sequence_destroy", + "sequence_exists", + "sequence_get", + "sequence_get_objects", + "sequence_instance_override_object", + "sequence_keyframe_new", + "sequence_keyframedata_new", + "sequence_track_new", + "sha1_file", + "sha1_string_unicode", + "sha1_string_utf8", + "shader_current", + "shader_enable_corner_id", + "shader_get_name", + "shader_get_sampler_index", + "shader_get_uniform", + "shader_is_compiled", + "shader_reset", + "shader_set", + "shader_set_uniform_f", + "shader_set_uniform_f_array", + "shader_set_uniform_f_buffer", + "shader_set_uniform_i", + "shader_set_uniform_i_array", + "shader_set_uniform_matrix", + "shader_set_uniform_matrix_array", + "shaders_are_supported", + "shop_leave_rating", + "show_debug_message", + "show_debug_message_ext", + "show_debug_overlay", + "show_error", + "show_message", + "show_message_async", + "show_question", + "show_question_async", + "sign", + "sin", + "skeleton_animation_clear", + "skeleton_animation_get", + "skeleton_animation_get_duration", + "skeleton_animation_get_event_frames", + "skeleton_animation_get_ext", + "skeleton_animation_get_frame", + "skeleton_animation_get_frames", + "skeleton_animation_get_position", + "skeleton_animation_is_finished", + "skeleton_animation_is_looping", + "skeleton_animation_list", + "skeleton_animation_mix", + "skeleton_animation_set", + "skeleton_animation_set_ext", + "skeleton_animation_set_frame", + "skeleton_animation_set_position", + "skeleton_attachment_create", + "skeleton_attachment_create_color", + "skeleton_attachment_create_colour", + "skeleton_attachment_destroy", + "skeleton_attachment_exists", + "skeleton_attachment_get", + "skeleton_attachment_replace", + "skeleton_attachment_replace_color", + "skeleton_attachment_replace_colour", + "skeleton_attachment_set", + "skeleton_bone_data_get", + "skeleton_bone_data_set", + "skeleton_bone_list", + "skeleton_bone_state_get", + "skeleton_bone_state_set", + "skeleton_collision_draw_set", + "skeleton_find_slot", + "skeleton_get_bounds", + "skeleton_get_minmax", + "skeleton_get_num_bounds", + "skeleton_skin_create", + "skeleton_skin_get", + "skeleton_skin_list", + "skeleton_skin_set", + "skeleton_slot_alpha_get", + "skeleton_slot_color_get", + "skeleton_slot_color_set", + "skeleton_slot_colour_get", + "skeleton_slot_colour_set", + "skeleton_slot_data", + "skeleton_slot_data_instance", + "skeleton_slot_list", + "sprite_add", + "sprite_add_ext", + "sprite_add_from_surface", + "sprite_assign", + "sprite_collision_mask", + "sprite_create_from_surface", + "sprite_delete", + "sprite_duplicate", + "sprite_exists", + "sprite_flush", + "sprite_flush_multi", + "sprite_get_bbox_bottom", + "sprite_get_bbox_left", + "sprite_get_bbox_mode", + "sprite_get_bbox_right", + "sprite_get_bbox_top", + "sprite_get_height", + "sprite_get_info", + "sprite_get_name", + "sprite_get_nineslice", + "sprite_get_number", + "sprite_get_speed", + "sprite_get_speed_type", + "sprite_get_texture", + "sprite_get_tpe", + "sprite_get_uvs", + "sprite_get_width", + "sprite_get_xoffset", + "sprite_get_yoffset", + "sprite_merge", + "sprite_nineslice_create", + "sprite_prefetch", + "sprite_prefetch_multi", + "sprite_replace", + "sprite_save", + "sprite_save_strip", + "sprite_set_alpha_from_sprite", + "sprite_set_bbox", + "sprite_set_bbox_mode", + "sprite_set_cache_size", + "sprite_set_cache_size_ext", + "sprite_set_nineslice", + "sprite_set_offset", + "sprite_set_speed", + "sqr", + "sqrt", + "static_get", + "static_set", + "string", + "string_byte_at", + "string_byte_length", + "string_char_at", + "string_concat", + "string_concat_ext", + "string_copy", + "string_count", + "string_delete", + "string_digits", + "string_ends_with", + "string_ext", + "string_foreach", + "string_format", + "string_hash_to_newline", + "string_height", + "string_height_ext", + "string_insert", + "string_join", + "string_join_ext", + "string_last_pos", + "string_last_pos_ext", + "string_length", + "string_letters", + "string_lettersdigits", + "string_lower", + "string_ord_at", + "string_pos", + "string_pos_ext", + "string_repeat", + "string_replace", + "string_replace_all", + "string_set_byte_at", + "string_split", + "string_split_ext", + "string_starts_with", + "string_trim", + "string_trim_end", + "string_trim_start", + "string_upper", + "string_width", + "string_width_ext", + "struct_exists", + "struct_foreach", + "struct_get", + "struct_get_from_hash", + "struct_get_names", + "struct_names_count", + "struct_remove", + "struct_set", + "struct_set_from_hash", + "surface_copy", + "surface_copy_part", + "surface_create", + "surface_create_ext", + "surface_depth_disable", + "surface_exists", + "surface_format_is_supported", + "surface_free", + "surface_get_depth_disable", + "surface_get_format", + "surface_get_height", + "surface_get_target", + "surface_get_target_ext", + "surface_get_texture", + "surface_get_width", + "surface_getpixel", + "surface_getpixel_ext", + "surface_reset_target", + "surface_resize", + "surface_save", + "surface_save_part", + "surface_set_target", + "surface_set_target_ext", + "tag_get_asset_ids", + "tag_get_assets", + "tan", + "texture_debug_messages", + "texture_flush", + "texture_get_height", + "texture_get_texel_height", + "texture_get_texel_width", + "texture_get_uvs", + "texture_get_width", + "texture_global_scale", + "texture_is_ready", + "texture_prefetch", + "texture_set_stage", + "texturegroup_get_fonts", + "texturegroup_get_names", + "texturegroup_get_sprites", + "texturegroup_get_status", + "texturegroup_get_textures", + "texturegroup_get_tilesets", + "texturegroup_load", + "texturegroup_set_mode", + "texturegroup_unload", + "tile_get_empty", + "tile_get_flip", + "tile_get_index", + "tile_get_mirror", + "tile_get_rotate", + "tile_set_empty", + "tile_set_flip", + "tile_set_index", + "tile_set_mirror", + "tile_set_rotate", + "tilemap_clear", + "tilemap_get", + "tilemap_get_at_pixel", + "tilemap_get_cell_x_at_pixel", + "tilemap_get_cell_y_at_pixel", + "tilemap_get_frame", + "tilemap_get_global_mask", + "tilemap_get_height", + "tilemap_get_mask", + "tilemap_get_tile_height", + "tilemap_get_tile_width", + "tilemap_get_tileset", + "tilemap_get_width", + "tilemap_get_x", + "tilemap_get_y", + "tilemap_set", + "tilemap_set_at_pixel", + "tilemap_set_global_mask", + "tilemap_set_height", + "tilemap_set_mask", + "tilemap_set_width", + "tilemap_tileset", + "tilemap_x", + "tilemap_y", + "tileset_get_info", + "tileset_get_name", + "tileset_get_texture", + "tileset_get_uvs", + "time_bpm_to_seconds", + "time_seconds_to_bpm", + "time_source_create", + "time_source_destroy", + "time_source_exists", + "time_source_get_children", + "time_source_get_parent", + "time_source_get_period", + "time_source_get_reps_completed", + "time_source_get_reps_remaining", + "time_source_get_state", + "time_source_get_time_remaining", + "time_source_get_units", + "time_source_pause", + "time_source_reconfigure", + "time_source_reset", + "time_source_resume", + "time_source_start", + "time_source_stop", + "timeline_add", + "timeline_clear", + "timeline_delete", + "timeline_exists", + "timeline_get_name", + "timeline_max_moment", + "timeline_moment_add_script", + "timeline_moment_clear", + "timeline_size", + "typeof", + "url_get_domain", + "url_open", + "url_open_ext", + "url_open_full", + "uwp_device_touchscreen_available", + "uwp_livetile_badge_clear", + "uwp_livetile_badge_notification", + "uwp_livetile_notification_begin", + "uwp_livetile_notification_end", + "uwp_livetile_notification_expiry", + "uwp_livetile_notification_image_add", + "uwp_livetile_notification_secondary_begin", + "uwp_livetile_notification_tag", + "uwp_livetile_notification_template_add", + "uwp_livetile_notification_text_add", + "uwp_livetile_queue_enable", + "uwp_livetile_tile_clear", + "uwp_secondarytile_badge_clear", + "uwp_secondarytile_badge_notification", + "uwp_secondarytile_delete", + "uwp_secondarytile_pin", + "uwp_secondarytile_tile_clear", + "variable_clone", + "variable_get_hash", + "variable_global_exists", + "variable_global_get", + "variable_global_set", + "variable_instance_exists", + "variable_instance_get", + "variable_instance_get_names", + "variable_instance_names_count", + "variable_instance_set", + "variable_struct_exists", + "variable_struct_get", + "variable_struct_get_names", + "variable_struct_names_count", + "variable_struct_remove", + "variable_struct_set", + "vertex_argb", + "vertex_begin", + "vertex_color", + "vertex_colour", + "vertex_create_buffer", + "vertex_create_buffer_ext", + "vertex_create_buffer_from_buffer", + "vertex_create_buffer_from_buffer_ext", + "vertex_delete_buffer", + "vertex_end", + "vertex_float1", + "vertex_float2", + "vertex_float3", + "vertex_float4", + "vertex_format_add_color", + "vertex_format_add_colour", + "vertex_format_add_custom", + "vertex_format_add_normal", + "vertex_format_add_position", + "vertex_format_add_position_3d", + "vertex_format_add_texcoord", + "vertex_format_begin", + "vertex_format_delete", + "vertex_format_end", + "vertex_format_get_info", + "vertex_freeze", + "vertex_get_buffer_size", + "vertex_get_number", + "vertex_normal", + "vertex_position", + "vertex_position_3d", + "vertex_submit", + "vertex_submit_ext", + "vertex_texcoord", + "vertex_ubyte4", + "vertex_update_buffer_from_buffer", + "vertex_update_buffer_from_vertex", + "video_close", + "video_draw", + "video_enable_loop", + "video_get_duration", + "video_get_format", + "video_get_position", + "video_get_status", + "video_get_volume", + "video_is_looping", + "video_open", + "video_pause", + "video_resume", + "video_seek_to", + "video_set_volume", + "view_get_camera", + "view_get_hport", + "view_get_surface_id", + "view_get_visible", + "view_get_wport", + "view_get_xport", + "view_get_yport", + "view_set_camera", + "view_set_hport", + "view_set_surface_id", + "view_set_visible", + "view_set_wport", + "view_set_xport", + "view_set_yport", + "virtual_key_add", + "virtual_key_delete", + "virtual_key_hide", + "virtual_key_show", + "wallpaper_set_config", + "wallpaper_set_subscriptions", + "weak_ref_alive", + "weak_ref_any_alive", + "weak_ref_create", + "window_center", + "window_device", + "window_enable_borderless_fullscreen", + "window_get_borderless_fullscreen", + "window_get_caption", + "window_get_color", + "window_get_colour", + "window_get_cursor", + "window_get_fullscreen", + "window_get_height", + "window_get_showborder", + "window_get_visible_rects", + "window_get_width", + "window_get_x", + "window_get_y", + "window_handle", + "window_has_focus", + "window_mouse_get_delta_x", + "window_mouse_get_delta_y", + "window_mouse_get_locked", + "window_mouse_get_x", + "window_mouse_get_y", + "window_mouse_set", + "window_mouse_set_locked", + "window_set_caption", + "window_set_color", + "window_set_colour", + "window_set_cursor", + "window_set_fullscreen", + "window_set_max_height", + "window_set_max_width", + "window_set_min_height", + "window_set_min_width", + "window_set_position", + "window_set_rectangle", + "window_set_showborder", + "window_set_size", + "window_view_mouse_get_x", + "window_view_mouse_get_y", + "window_views_mouse_get_x", + "window_views_mouse_get_y", + "winphone_tile_background_color", + "winphone_tile_background_colour", + "zip_add_file", + "zip_create", + "zip_save", + "zip_unzip", + "zip_unzip_async" + ]; + const SYMBOLS = [ + "AudioEffect", + "AudioEffectType", + "AudioLFOType", + "GM_build_date", + "GM_build_type", + "GM_is_sandboxed", + "GM_project_filename", + "GM_runtime_version", + "GM_version", + "NaN", + "_GMFILE_", + "_GMFUNCTION_", + "_GMLINE_", + "alignmentH", + "alignmentV", + "all", + "animcurvetype_bezier", + "animcurvetype_catmullrom", + "animcurvetype_linear", + "asset_animationcurve", + "asset_font", + "asset_object", + "asset_path", + "asset_room", + "asset_script", + "asset_sequence", + "asset_shader", + "asset_sound", + "asset_sprite", + "asset_tiles", + "asset_timeline", + "asset_unknown", + "audio_3D", + "audio_bus_main", + "audio_falloff_exponent_distance", + "audio_falloff_exponent_distance_clamped", + "audio_falloff_exponent_distance_scaled", + "audio_falloff_inverse_distance", + "audio_falloff_inverse_distance_clamped", + "audio_falloff_inverse_distance_scaled", + "audio_falloff_linear_distance", + "audio_falloff_linear_distance_clamped", + "audio_falloff_none", + "audio_mono", + "audio_stereo", + "bboxkind_diamond", + "bboxkind_ellipse", + "bboxkind_precise", + "bboxkind_rectangular", + "bboxmode_automatic", + "bboxmode_fullimage", + "bboxmode_manual", + "bm_add", + "bm_dest_alpha", + "bm_dest_color", + "bm_dest_colour", + "bm_inv_dest_alpha", + "bm_inv_dest_color", + "bm_inv_dest_colour", + "bm_inv_src_alpha", + "bm_inv_src_color", + "bm_inv_src_colour", + "bm_max", + "bm_normal", + "bm_one", + "bm_src_alpha", + "bm_src_alpha_sat", + "bm_src_color", + "bm_src_colour", + "bm_subtract", + "bm_zero", + "browser_chrome", + "browser_edge", + "browser_firefox", + "browser_ie", + "browser_ie_mobile", + "browser_not_a_browser", + "browser_opera", + "browser_safari", + "browser_safari_mobile", + "browser_tizen", + "browser_unknown", + "browser_windows_store", + "buffer_bool", + "buffer_f16", + "buffer_f32", + "buffer_f64", + "buffer_fast", + "buffer_fixed", + "buffer_grow", + "buffer_s16", + "buffer_s32", + "buffer_s8", + "buffer_seek_end", + "buffer_seek_relative", + "buffer_seek_start", + "buffer_string", + "buffer_text", + "buffer_u16", + "buffer_u32", + "buffer_u64", + "buffer_u8", + "buffer_vbuffer", + "buffer_wrap", + "c_aqua", + "c_black", + "c_blue", + "c_dkgray", + "c_dkgrey", + "c_fuchsia", + "c_gray", + "c_green", + "c_grey", + "c_lime", + "c_ltgray", + "c_ltgrey", + "c_maroon", + "c_navy", + "c_olive", + "c_orange", + "c_purple", + "c_red", + "c_silver", + "c_teal", + "c_white", + "c_yellow", + "cache_directory", + "characterSpacing", + "cmpfunc_always", + "cmpfunc_equal", + "cmpfunc_greater", + "cmpfunc_greaterequal", + "cmpfunc_less", + "cmpfunc_lessequal", + "cmpfunc_never", + "cmpfunc_notequal", + "coreColor", + "coreColour", + "cr_appstart", + "cr_arrow", + "cr_beam", + "cr_cross", + "cr_default", + "cr_drag", + "cr_handpoint", + "cr_hourglass", + "cr_none", + "cr_size_all", + "cr_size_nesw", + "cr_size_ns", + "cr_size_nwse", + "cr_size_we", + "cr_uparrow", + "cull_clockwise", + "cull_counterclockwise", + "cull_noculling", + "device_emulator", + "device_ios_ipad", + "device_ios_ipad_retina", + "device_ios_iphone", + "device_ios_iphone5", + "device_ios_iphone6", + "device_ios_iphone6plus", + "device_ios_iphone_retina", + "device_ios_unknown", + "device_tablet", + "display_landscape", + "display_landscape_flipped", + "display_portrait", + "display_portrait_flipped", + "dll_cdecl", + "dll_stdcall", + "dropShadowEnabled", + "dropShadowEnabled", + "ds_type_grid", + "ds_type_list", + "ds_type_map", + "ds_type_priority", + "ds_type_queue", + "ds_type_stack", + "ef_cloud", + "ef_ellipse", + "ef_explosion", + "ef_firework", + "ef_flare", + "ef_rain", + "ef_ring", + "ef_smoke", + "ef_smokeup", + "ef_snow", + "ef_spark", + "ef_star", + "effectsEnabled", + "effectsEnabled", + "ev_alarm", + "ev_animation_end", + "ev_animation_event", + "ev_animation_update", + "ev_async_audio_playback", + "ev_async_audio_playback_ended", + "ev_async_audio_recording", + "ev_async_dialog", + "ev_async_push_notification", + "ev_async_save_load", + "ev_async_save_load", + "ev_async_social", + "ev_async_system_event", + "ev_async_web", + "ev_async_web_cloud", + "ev_async_web_iap", + "ev_async_web_image_load", + "ev_async_web_networking", + "ev_async_web_steam", + "ev_audio_playback", + "ev_audio_playback_ended", + "ev_audio_recording", + "ev_boundary", + "ev_boundary_view0", + "ev_boundary_view1", + "ev_boundary_view2", + "ev_boundary_view3", + "ev_boundary_view4", + "ev_boundary_view5", + "ev_boundary_view6", + "ev_boundary_view7", + "ev_broadcast_message", + "ev_cleanup", + "ev_collision", + "ev_create", + "ev_destroy", + "ev_dialog_async", + "ev_draw", + "ev_draw_begin", + "ev_draw_end", + "ev_draw_normal", + "ev_draw_post", + "ev_draw_pre", + "ev_end_of_path", + "ev_game_end", + "ev_game_start", + "ev_gesture", + "ev_gesture_double_tap", + "ev_gesture_drag_end", + "ev_gesture_drag_start", + "ev_gesture_dragging", + "ev_gesture_flick", + "ev_gesture_pinch_end", + "ev_gesture_pinch_in", + "ev_gesture_pinch_out", + "ev_gesture_pinch_start", + "ev_gesture_rotate_end", + "ev_gesture_rotate_start", + "ev_gesture_rotating", + "ev_gesture_tap", + "ev_global_gesture_double_tap", + "ev_global_gesture_drag_end", + "ev_global_gesture_drag_start", + "ev_global_gesture_dragging", + "ev_global_gesture_flick", + "ev_global_gesture_pinch_end", + "ev_global_gesture_pinch_in", + "ev_global_gesture_pinch_out", + "ev_global_gesture_pinch_start", + "ev_global_gesture_rotate_end", + "ev_global_gesture_rotate_start", + "ev_global_gesture_rotating", + "ev_global_gesture_tap", + "ev_global_left_button", + "ev_global_left_press", + "ev_global_left_release", + "ev_global_middle_button", + "ev_global_middle_press", + "ev_global_middle_release", + "ev_global_right_button", + "ev_global_right_press", + "ev_global_right_release", + "ev_gui", + "ev_gui_begin", + "ev_gui_end", + "ev_joystick1_button1", + "ev_joystick1_button2", + "ev_joystick1_button3", + "ev_joystick1_button4", + "ev_joystick1_button5", + "ev_joystick1_button6", + "ev_joystick1_button7", + "ev_joystick1_button8", + "ev_joystick1_down", + "ev_joystick1_left", + "ev_joystick1_right", + "ev_joystick1_up", + "ev_joystick2_button1", + "ev_joystick2_button2", + "ev_joystick2_button3", + "ev_joystick2_button4", + "ev_joystick2_button5", + "ev_joystick2_button6", + "ev_joystick2_button7", + "ev_joystick2_button8", + "ev_joystick2_down", + "ev_joystick2_left", + "ev_joystick2_right", + "ev_joystick2_up", + "ev_keyboard", + "ev_keypress", + "ev_keyrelease", + "ev_left_button", + "ev_left_press", + "ev_left_release", + "ev_middle_button", + "ev_middle_press", + "ev_middle_release", + "ev_mouse", + "ev_mouse_enter", + "ev_mouse_leave", + "ev_mouse_wheel_down", + "ev_mouse_wheel_up", + "ev_no_button", + "ev_no_more_health", + "ev_no_more_lives", + "ev_other", + "ev_outside", + "ev_outside_view0", + "ev_outside_view1", + "ev_outside_view2", + "ev_outside_view3", + "ev_outside_view4", + "ev_outside_view5", + "ev_outside_view6", + "ev_outside_view7", + "ev_pre_create", + "ev_push_notification", + "ev_right_button", + "ev_right_press", + "ev_right_release", + "ev_room_end", + "ev_room_start", + "ev_social", + "ev_step", + "ev_step_begin", + "ev_step_end", + "ev_step_normal", + "ev_system_event", + "ev_trigger", + "ev_user0", + "ev_user1", + "ev_user10", + "ev_user11", + "ev_user12", + "ev_user13", + "ev_user14", + "ev_user15", + "ev_user2", + "ev_user3", + "ev_user4", + "ev_user5", + "ev_user6", + "ev_user7", + "ev_user8", + "ev_user9", + "ev_web_async", + "ev_web_cloud", + "ev_web_iap", + "ev_web_image_load", + "ev_web_networking", + "ev_web_sound_load", + "ev_web_steam", + "fa_archive", + "fa_bottom", + "fa_center", + "fa_directory", + "fa_hidden", + "fa_left", + "fa_middle", + "fa_none", + "fa_readonly", + "fa_right", + "fa_sysfile", + "fa_top", + "fa_volumeid", + "false", + "frameSizeX", + "frameSizeY", + "gamespeed_fps", + "gamespeed_microseconds", + "global", + "glowColor", + "glowColour", + "glowEnabled", + "glowEnabled", + "glowEnd", + "glowStart", + "gp_axis_acceleration_x", + "gp_axis_acceleration_y", + "gp_axis_acceleration_z", + "gp_axis_angular_velocity_x", + "gp_axis_angular_velocity_y", + "gp_axis_angular_velocity_z", + "gp_axis_orientation_w", + "gp_axis_orientation_x", + "gp_axis_orientation_y", + "gp_axis_orientation_z", + "gp_axislh", + "gp_axislv", + "gp_axisrh", + "gp_axisrv", + "gp_face1", + "gp_face2", + "gp_face3", + "gp_face4", + "gp_padd", + "gp_padl", + "gp_padr", + "gp_padu", + "gp_select", + "gp_shoulderl", + "gp_shoulderlb", + "gp_shoulderr", + "gp_shoulderrb", + "gp_start", + "gp_stickl", + "gp_stickr", + "iap_available", + "iap_canceled", + "iap_ev_consume", + "iap_ev_product", + "iap_ev_purchase", + "iap_ev_restore", + "iap_ev_storeload", + "iap_failed", + "iap_purchased", + "iap_refunded", + "iap_status_available", + "iap_status_loading", + "iap_status_processing", + "iap_status_restoring", + "iap_status_unavailable", + "iap_status_uninitialised", + "iap_storeload_failed", + "iap_storeload_ok", + "iap_unavailable", + "infinity", + "kbv_autocapitalize_characters", + "kbv_autocapitalize_none", + "kbv_autocapitalize_sentences", + "kbv_autocapitalize_words", + "kbv_returnkey_continue", + "kbv_returnkey_default", + "kbv_returnkey_done", + "kbv_returnkey_emergency", + "kbv_returnkey_go", + "kbv_returnkey_google", + "kbv_returnkey_join", + "kbv_returnkey_next", + "kbv_returnkey_route", + "kbv_returnkey_search", + "kbv_returnkey_send", + "kbv_returnkey_yahoo", + "kbv_type_ascii", + "kbv_type_default", + "kbv_type_email", + "kbv_type_numbers", + "kbv_type_phone", + "kbv_type_phone_name", + "kbv_type_url", + "layerelementtype_background", + "layerelementtype_instance", + "layerelementtype_oldtilemap", + "layerelementtype_particlesystem", + "layerelementtype_sequence", + "layerelementtype_sprite", + "layerelementtype_tile", + "layerelementtype_tilemap", + "layerelementtype_undefined", + "leaderboard_type_number", + "leaderboard_type_time_mins_secs", + "lighttype_dir", + "lighttype_point", + "lineSpacing", + "m_axisx", + "m_axisx_gui", + "m_axisy", + "m_axisy_gui", + "m_scroll_down", + "m_scroll_up", + "matrix_projection", + "matrix_view", + "matrix_world", + "mb_any", + "mb_left", + "mb_middle", + "mb_none", + "mb_right", + "mb_side1", + "mb_side2", + "mip_markedonly", + "mip_off", + "mip_on", + "network_config_avoid_time_wait", + "network_config_connect_timeout", + "network_config_disable_multicast", + "network_config_disable_reliable_udp", + "network_config_enable_multicast", + "network_config_enable_reliable_udp", + "network_config_use_non_blocking_socket", + "network_config_websocket_protocol", + "network_connect_active", + "network_connect_blocking", + "network_connect_nonblocking", + "network_connect_none", + "network_connect_passive", + "network_send_binary", + "network_send_text", + "network_socket_bluetooth", + "network_socket_tcp", + "network_socket_udp", + "network_socket_ws", + "network_socket_wss", + "network_type_connect", + "network_type_data", + "network_type_disconnect", + "network_type_down", + "network_type_non_blocking_connect", + "network_type_up", + "network_type_up_failed", + "nineslice_blank", + "nineslice_bottom", + "nineslice_center", + "nineslice_centre", + "nineslice_hide", + "nineslice_left", + "nineslice_mirror", + "nineslice_repeat", + "nineslice_right", + "nineslice_stretch", + "nineslice_top", + "noone", + "of_challenge_lose", + "of_challenge_tie", + "of_challenge_win", + "os_android", + "os_gdk", + "os_gxgames", + "os_ios", + "os_linux", + "os_macosx", + "os_operagx", + "os_permission_denied", + "os_permission_denied_dont_request", + "os_permission_granted", + "os_ps3", + "os_ps4", + "os_ps5", + "os_psvita", + "os_switch", + "os_tvos", + "os_unknown", + "os_uwp", + "os_win8native", + "os_windows", + "os_winphone", + "os_xboxone", + "os_xboxseriesxs", + "other", + "outlineColor", + "outlineColour", + "outlineDist", + "outlineEnabled", + "outlineEnabled", + "paragraphSpacing", + "path_action_continue", + "path_action_restart", + "path_action_reverse", + "path_action_stop", + "phy_debug_render_aabb", + "phy_debug_render_collision_pairs", + "phy_debug_render_coms", + "phy_debug_render_core_shapes", + "phy_debug_render_joints", + "phy_debug_render_obb", + "phy_debug_render_shapes", + "phy_joint_anchor_1_x", + "phy_joint_anchor_1_y", + "phy_joint_anchor_2_x", + "phy_joint_anchor_2_y", + "phy_joint_angle", + "phy_joint_angle_limits", + "phy_joint_damping_ratio", + "phy_joint_frequency", + "phy_joint_length_1", + "phy_joint_length_2", + "phy_joint_lower_angle_limit", + "phy_joint_max_force", + "phy_joint_max_length", + "phy_joint_max_motor_force", + "phy_joint_max_motor_torque", + "phy_joint_max_torque", + "phy_joint_motor_force", + "phy_joint_motor_speed", + "phy_joint_motor_torque", + "phy_joint_reaction_force_x", + "phy_joint_reaction_force_y", + "phy_joint_reaction_torque", + "phy_joint_speed", + "phy_joint_translation", + "phy_joint_upper_angle_limit", + "phy_particle_data_flag_category", + "phy_particle_data_flag_color", + "phy_particle_data_flag_colour", + "phy_particle_data_flag_position", + "phy_particle_data_flag_typeflags", + "phy_particle_data_flag_velocity", + "phy_particle_flag_colormixing", + "phy_particle_flag_colourmixing", + "phy_particle_flag_elastic", + "phy_particle_flag_powder", + "phy_particle_flag_spring", + "phy_particle_flag_tensile", + "phy_particle_flag_viscous", + "phy_particle_flag_wall", + "phy_particle_flag_water", + "phy_particle_flag_zombie", + "phy_particle_group_flag_rigid", + "phy_particle_group_flag_solid", + "pi", + "pointer_invalid", + "pointer_null", + "pr_linelist", + "pr_linestrip", + "pr_pointlist", + "pr_trianglefan", + "pr_trianglelist", + "pr_trianglestrip", + "ps_distr_gaussian", + "ps_distr_invgaussian", + "ps_distr_linear", + "ps_mode_burst", + "ps_mode_stream", + "ps_shape_diamond", + "ps_shape_ellipse", + "ps_shape_line", + "ps_shape_rectangle", + "pt_shape_circle", + "pt_shape_cloud", + "pt_shape_disk", + "pt_shape_explosion", + "pt_shape_flare", + "pt_shape_line", + "pt_shape_pixel", + "pt_shape_ring", + "pt_shape_smoke", + "pt_shape_snow", + "pt_shape_spark", + "pt_shape_sphere", + "pt_shape_square", + "pt_shape_star", + "rollback_chat_message", + "rollback_connect_error", + "rollback_connect_info", + "rollback_connected_to_peer", + "rollback_connection_rejected", + "rollback_disconnected_from_peer", + "rollback_end_game", + "rollback_game_full", + "rollback_game_info", + "rollback_game_interrupted", + "rollback_game_resumed", + "rollback_high_latency", + "rollback_player_prefs", + "rollback_protocol_rejected", + "rollback_synchronized_with_peer", + "rollback_synchronizing_with_peer", + "self", + "seqaudiokey_loop", + "seqaudiokey_oneshot", + "seqdir_left", + "seqdir_right", + "seqinterpolation_assign", + "seqinterpolation_lerp", + "seqplay_loop", + "seqplay_oneshot", + "seqplay_pingpong", + "seqtextkey_bottom", + "seqtextkey_center", + "seqtextkey_justify", + "seqtextkey_left", + "seqtextkey_middle", + "seqtextkey_right", + "seqtextkey_top", + "seqtracktype_audio", + "seqtracktype_bool", + "seqtracktype_clipmask", + "seqtracktype_clipmask_mask", + "seqtracktype_clipmask_subject", + "seqtracktype_color", + "seqtracktype_colour", + "seqtracktype_empty", + "seqtracktype_graphic", + "seqtracktype_group", + "seqtracktype_instance", + "seqtracktype_message", + "seqtracktype_moment", + "seqtracktype_particlesystem", + "seqtracktype_real", + "seqtracktype_sequence", + "seqtracktype_spriteframes", + "seqtracktype_string", + "seqtracktype_text", + "shadowColor", + "shadowColour", + "shadowOffsetX", + "shadowOffsetY", + "shadowSoftness", + "sprite_add_ext_error_cancelled", + "sprite_add_ext_error_decompressfailed", + "sprite_add_ext_error_loadfailed", + "sprite_add_ext_error_setupfailed", + "sprite_add_ext_error_spritenotfound", + "sprite_add_ext_error_unknown", + "spritespeed_framespergameframe", + "spritespeed_framespersecond", + "surface_r16float", + "surface_r32float", + "surface_r8unorm", + "surface_rg8unorm", + "surface_rgba16float", + "surface_rgba32float", + "surface_rgba4unorm", + "surface_rgba8unorm", + "texturegroup_status_fetched", + "texturegroup_status_loaded", + "texturegroup_status_loading", + "texturegroup_status_unloaded", + "tf_anisotropic", + "tf_linear", + "tf_point", + "thickness", + "tile_flip", + "tile_index_mask", + "tile_mirror", + "tile_rotate", + "time_source_expire_after", + "time_source_expire_nearest", + "time_source_game", + "time_source_global", + "time_source_state_active", + "time_source_state_initial", + "time_source_state_paused", + "time_source_state_stopped", + "time_source_units_frames", + "time_source_units_seconds", + "timezone_local", + "timezone_utc", + "tm_countvsyncs", + "tm_sleep", + "tm_systemtiming", + "true", + "ty_real", + "ty_string", + "undefined", + "vertex_type_color", + "vertex_type_colour", + "vertex_type_float1", + "vertex_type_float2", + "vertex_type_float3", + "vertex_type_float4", + "vertex_type_ubyte4", + "vertex_usage_binormal", + "vertex_usage_blendindices", + "vertex_usage_blendweight", + "vertex_usage_color", + "vertex_usage_colour", + "vertex_usage_depth", + "vertex_usage_fog", + "vertex_usage_normal", + "vertex_usage_position", + "vertex_usage_psize", + "vertex_usage_sample", + "vertex_usage_tangent", + "vertex_usage_texcoord", + "video_format_rgba", + "video_format_yuv", + "video_status_closed", + "video_status_paused", + "video_status_playing", + "video_status_preparing", + "vk_add", + "vk_alt", + "vk_anykey", + "vk_backspace", + "vk_control", + "vk_decimal", + "vk_delete", + "vk_divide", + "vk_down", + "vk_end", + "vk_enter", + "vk_escape", + "vk_f1", + "vk_f10", + "vk_f11", + "vk_f12", + "vk_f2", + "vk_f3", + "vk_f4", + "vk_f5", + "vk_f6", + "vk_f7", + "vk_f8", + "vk_f9", + "vk_home", + "vk_insert", + "vk_lalt", + "vk_lcontrol", + "vk_left", + "vk_lshift", + "vk_multiply", + "vk_nokey", + "vk_numpad0", + "vk_numpad1", + "vk_numpad2", + "vk_numpad3", + "vk_numpad4", + "vk_numpad5", + "vk_numpad6", + "vk_numpad7", + "vk_numpad8", + "vk_numpad9", + "vk_pagedown", + "vk_pageup", + "vk_pause", + "vk_printscreen", + "vk_ralt", + "vk_rcontrol", + "vk_return", + "vk_right", + "vk_rshift", + "vk_shift", + "vk_space", + "vk_subtract", + "vk_tab", + "vk_up", + "wallpaper_config", + "wallpaper_subscription_data", + "wrap" + ]; + const LANGUAGE_VARIABLES = [ + "alarm", + "application_surface", + "argument", + "argument0", + "argument1", + "argument2", + "argument3", + "argument4", + "argument5", + "argument6", + "argument7", + "argument8", + "argument9", + "argument10", + "argument11", + "argument12", + "argument13", + "argument14", + "argument15", + "argument_count", + "async_load", + "background_color", + "background_colour", + "background_showcolor", + "background_showcolour", + "bbox_bottom", + "bbox_left", + "bbox_right", + "bbox_top", + "browser_height", + "browser_width", + "colour?ColourTrack", + "current_day", + "current_hour", + "current_minute", + "current_month", + "current_second", + "current_time", + "current_weekday", + "current_year", + "cursor_sprite", + "debug_mode", + "delta_time", + "depth", + "direction", + "display_aa", + "drawn_by_sequence", + "event_action", + "event_data", + "event_number", + "event_object", + "event_type", + "font_texture_page_size", + "fps", + "fps_real", + "friction", + "game_display_name", + "game_id", + "game_project_name", + "game_save_id", + "gravity", + "gravity_direction", + "health", + "hspeed", + "iap_data", + "id", + "image_alpha", + "image_angle", + "image_blend", + "image_index", + "image_number", + "image_speed", + "image_xscale", + "image_yscale", + "in_collision_tree", + "in_sequence", + "instance_count", + "instance_id", + "keyboard_key", + "keyboard_lastchar", + "keyboard_lastkey", + "keyboard_string", + "layer", + "lives", + "longMessage", + "managed", + "mask_index", + "message", + "mouse_button", + "mouse_lastbutton", + "mouse_x", + "mouse_y", + "object_index", + "os_browser", + "os_device", + "os_type", + "os_version", + "path_endaction", + "path_index", + "path_orientation", + "path_position", + "path_positionprevious", + "path_scale", + "path_speed", + "persistent", + "phy_active", + "phy_angular_damping", + "phy_angular_velocity", + "phy_bullet", + "phy_col_normal_x", + "phy_col_normal_y", + "phy_collision_points", + "phy_collision_x", + "phy_collision_y", + "phy_com_x", + "phy_com_y", + "phy_dynamic", + "phy_fixed_rotation", + "phy_inertia", + "phy_kinematic", + "phy_linear_damping", + "phy_linear_velocity_x", + "phy_linear_velocity_y", + "phy_mass", + "phy_position_x", + "phy_position_xprevious", + "phy_position_y", + "phy_position_yprevious", + "phy_rotation", + "phy_sleeping", + "phy_speed", + "phy_speed_x", + "phy_speed_y", + "player_avatar_sprite", + "player_avatar_url", + "player_id", + "player_local", + "player_type", + "player_user_id", + "program_directory", + "rollback_api_server", + "rollback_confirmed_frame", + "rollback_current_frame", + "rollback_event_id", + "rollback_event_param", + "rollback_game_running", + "room", + "room_first", + "room_height", + "room_last", + "room_persistent", + "room_speed", + "room_width", + "score", + "script", + "sequence_instance", + "solid", + "speed", + "sprite_height", + "sprite_index", + "sprite_width", + "sprite_xoffset", + "sprite_yoffset", + "stacktrace", + "temp_directory", + "timeline_index", + "timeline_loop", + "timeline_position", + "timeline_running", + "timeline_speed", + "view_camera", + "view_current", + "view_enabled", + "view_hport", + "view_surface_id", + "view_visible", + "view_wport", + "view_xport", + "view_yport", + "visible", + "vspeed", + "webgl_enabled", + "working_directory", + "x", + "xprevious", + "xstart", + "y", + "yprevious", + "ystart" + ]; + return { + name: 'GML', + case_insensitive: false, // language is case-insensitive + keywords: { + keyword: KEYWORDS, + built_in: BUILT_INS, + symbol: SYMBOLS, + "variable.language": LANGUAGE_VARIABLES + }, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.C_NUMBER_MODE + ] + }; +} + +export { gml as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/gml.js.js b/frontend/node_modules/highlight.js/es/languages/gml.js.js new file mode 100644 index 0000000..f5e94cf --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/gml.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/gml" instead of "highlight.js/lib/languages/gml.js"' + ); + } + } + emitWarning(); + import lang from './gml.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/go.js b/frontend/node_modules/highlight.js/es/languages/go.js new file mode 100644 index 0000000..9b03bd0 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/go.js @@ -0,0 +1,156 @@ +/* +Language: Go +Author: Stephan Kountso aka StepLg +Contributors: Evgeny Stepanischev +Description: Google go language (golang). For info about language +Website: http://golang.org/ +Category: common, system +*/ + +function go(hljs) { + const LITERALS = [ + "true", + "false", + "iota", + "nil" + ]; + const BUILT_INS = [ + "append", + "cap", + "close", + "complex", + "copy", + "imag", + "len", + "make", + "new", + "panic", + "print", + "println", + "real", + "recover", + "delete" + ]; + const TYPES = [ + "bool", + "byte", + "complex64", + "complex128", + "error", + "float32", + "float64", + "int8", + "int16", + "int32", + "int64", + "string", + "uint8", + "uint16", + "uint32", + "uint64", + "int", + "uint", + "uintptr", + "rune" + ]; + const KWS = [ + "break", + "case", + "chan", + "const", + "continue", + "default", + "defer", + "else", + "fallthrough", + "for", + "func", + "go", + "goto", + "if", + "import", + "interface", + "map", + "package", + "range", + "return", + "select", + "struct", + "switch", + "type", + "var", + ]; + const KEYWORDS = { + keyword: KWS, + type: TYPES, + literal: LITERALS, + built_in: BUILT_INS + }; + return { + name: 'Go', + aliases: [ 'golang' ], + keywords: KEYWORDS, + illegal: ' +Description: a lightweight dynamic language for the JVM +Website: http://golo-lang.org/ +Category: system +*/ + +function golo(hljs) { + const KEYWORDS = [ + "println", + "readln", + "print", + "import", + "module", + "function", + "local", + "return", + "let", + "var", + "while", + "for", + "foreach", + "times", + "in", + "case", + "when", + "match", + "with", + "break", + "continue", + "augment", + "augmentation", + "each", + "find", + "filter", + "reduce", + "if", + "then", + "else", + "otherwise", + "try", + "catch", + "finally", + "raise", + "throw", + "orIfNull", + "DynamicObject|10", + "DynamicVariable", + "struct", + "Observable", + "map", + "set", + "vector", + "list", + "array" + ]; + + return { + name: 'Golo', + keywords: { + keyword: KEYWORDS, + literal: [ + "true", + "false", + "null" + ] + }, + contains: [ + hljs.HASH_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + hljs.C_NUMBER_MODE, + { + className: 'meta', + begin: '@[A-Za-z]+' + } + ] + }; +} + +export { golo as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/golo.js.js b/frontend/node_modules/highlight.js/es/languages/golo.js.js new file mode 100644 index 0000000..4611012 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/golo.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/golo" instead of "highlight.js/lib/languages/golo.js"' + ); + } + } + emitWarning(); + import lang from './golo.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/gradle.js b/frontend/node_modules/highlight.js/es/languages/gradle.js new file mode 100644 index 0000000..a823974 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/gradle.js @@ -0,0 +1,190 @@ +/* +Language: Gradle +Description: Gradle is an open-source build automation tool focused on flexibility and performance. +Website: https://gradle.org +Author: Damian Mee +Category: build-system +*/ + +function gradle(hljs) { + const KEYWORDS = [ + "task", + "project", + "allprojects", + "subprojects", + "artifacts", + "buildscript", + "configurations", + "dependencies", + "repositories", + "sourceSets", + "description", + "delete", + "from", + "into", + "include", + "exclude", + "source", + "classpath", + "destinationDir", + "includes", + "options", + "sourceCompatibility", + "targetCompatibility", + "group", + "flatDir", + "doLast", + "doFirst", + "flatten", + "todir", + "fromdir", + "ant", + "def", + "abstract", + "break", + "case", + "catch", + "continue", + "default", + "do", + "else", + "extends", + "final", + "finally", + "for", + "if", + "implements", + "instanceof", + "native", + "new", + "private", + "protected", + "public", + "return", + "static", + "switch", + "synchronized", + "throw", + "throws", + "transient", + "try", + "volatile", + "while", + "strictfp", + "package", + "import", + "false", + "null", + "super", + "this", + "true", + "antlrtask", + "checkstyle", + "codenarc", + "copy", + "boolean", + "byte", + "char", + "class", + "double", + "float", + "int", + "interface", + "long", + "short", + "void", + "compile", + "runTime", + "file", + "fileTree", + "abs", + "any", + "append", + "asList", + "asWritable", + "call", + "collect", + "compareTo", + "count", + "div", + "dump", + "each", + "eachByte", + "eachFile", + "eachLine", + "every", + "find", + "findAll", + "flatten", + "getAt", + "getErr", + "getIn", + "getOut", + "getText", + "grep", + "immutable", + "inject", + "inspect", + "intersect", + "invokeMethods", + "isCase", + "join", + "leftShift", + "minus", + "multiply", + "newInputStream", + "newOutputStream", + "newPrintWriter", + "newReader", + "newWriter", + "next", + "plus", + "pop", + "power", + "previous", + "print", + "println", + "push", + "putAt", + "read", + "readBytes", + "readLines", + "reverse", + "reverseEach", + "round", + "size", + "sort", + "splitEachLine", + "step", + "subMap", + "times", + "toInteger", + "toList", + "tokenize", + "upto", + "waitForOrKill", + "withPrintWriter", + "withReader", + "withStream", + "withWriter", + "withWriterAppend", + "write", + "writeLine" + ]; + return { + name: 'Gradle', + case_insensitive: true, + keywords: KEYWORDS, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.NUMBER_MODE, + hljs.REGEXP_MODE + + ] + }; +} + +export { gradle as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/gradle.js.js b/frontend/node_modules/highlight.js/es/languages/gradle.js.js new file mode 100644 index 0000000..021ceed --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/gradle.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/gradle" instead of "highlight.js/lib/languages/gradle.js"' + ); + } + } + emitWarning(); + import lang from './gradle.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/graphql.js b/frontend/node_modules/highlight.js/es/languages/graphql.js new file mode 100644 index 0000000..d473495 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/graphql.js @@ -0,0 +1,78 @@ +/* + Language: GraphQL + Author: John Foster (GH jf990), and others + Description: GraphQL is a query language for APIs + Category: web, common +*/ + +/** @type LanguageFn */ +function graphql(hljs) { + const regex = hljs.regex; + const GQL_NAME = /[_A-Za-z][_0-9A-Za-z]*/; + return { + name: "GraphQL", + aliases: [ "gql" ], + case_insensitive: true, + disableAutodetect: false, + keywords: { + keyword: [ + "query", + "mutation", + "subscription", + "type", + "input", + "schema", + "directive", + "interface", + "union", + "scalar", + "fragment", + "enum", + "on" + ], + literal: [ + "true", + "false", + "null" + ] + }, + contains: [ + hljs.HASH_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + hljs.NUMBER_MODE, + { + scope: "punctuation", + match: /[.]{3}/, + relevance: 0 + }, + { + scope: "punctuation", + begin: /[\!\(\)\:\=\[\]\{\|\}]{1}/, + relevance: 0 + }, + { + scope: "variable", + begin: /\$/, + end: /\W/, + excludeEnd: true, + relevance: 0 + }, + { + scope: "meta", + match: /@\w+/, + excludeEnd: true + }, + { + scope: "symbol", + begin: regex.concat(GQL_NAME, regex.lookahead(/\s*:/)), + relevance: 0 + } + ], + illegal: [ + /[;<']/, + /BEGIN/ + ] + }; +} + +export { graphql as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/graphql.js.js b/frontend/node_modules/highlight.js/es/languages/graphql.js.js new file mode 100644 index 0000000..2f8c537 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/graphql.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/graphql" instead of "highlight.js/lib/languages/graphql.js"' + ); + } + } + emitWarning(); + import lang from './graphql.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/groovy.js b/frontend/node_modules/highlight.js/es/languages/groovy.js new file mode 100644 index 0000000..df56854 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/groovy.js @@ -0,0 +1,190 @@ +/* + Language: Groovy + Author: Guillaume Laforge + Description: Groovy programming language implementation inspired from Vsevolod's Java mode + Website: https://groovy-lang.org + Category: system + */ + +function variants(variants, obj = {}) { + obj.variants = variants; + return obj; +} + +function groovy(hljs) { + const regex = hljs.regex; + const IDENT_RE = '[A-Za-z0-9_$]+'; + const COMMENT = variants([ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.COMMENT( + '/\\*\\*', + '\\*/', + { + relevance: 0, + contains: [ + { + // eat up @'s in emails to prevent them to be recognized as doctags + begin: /\w+@/, + relevance: 0 + }, + { + className: 'doctag', + begin: '@[A-Za-z]+' + } + ] + } + ) + ]); + const REGEXP = { + className: 'regexp', + begin: /~?\/[^\/\n]+\//, + contains: [ hljs.BACKSLASH_ESCAPE ] + }; + const NUMBER = variants([ + hljs.BINARY_NUMBER_MODE, + hljs.C_NUMBER_MODE + ]); + const STRING = variants([ + { + begin: /"""/, + end: /"""/ + }, + { + begin: /'''/, + end: /'''/ + }, + { + begin: "\\$/", + end: "/\\$", + relevance: 10 + }, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE + ], + { className: "string" } + ); + + const CLASS_DEFINITION = { + match: [ + /(class|interface|trait|enum|record|extends|implements)/, + /\s+/, + hljs.UNDERSCORE_IDENT_RE + ], + scope: { + 1: "keyword", + 3: "title.class", + } + }; + const TYPES = [ + "byte", + "short", + "char", + "int", + "long", + "boolean", + "float", + "double", + "void" + ]; + const KEYWORDS = [ + // groovy specific keywords + "def", + "as", + "in", + "assert", + "trait", + // common keywords with Java + "abstract", + "static", + "volatile", + "transient", + "public", + "private", + "protected", + "synchronized", + "final", + "class", + "interface", + "enum", + "if", + "else", + "for", + "while", + "switch", + "case", + "break", + "default", + "continue", + "throw", + "throws", + "try", + "catch", + "finally", + "implements", + "extends", + "new", + "import", + "package", + "return", + "instanceof", + "var" + ]; + + return { + name: 'Groovy', + keywords: { + "variable.language": 'this super', + literal: 'true false null', + type: TYPES, + keyword: KEYWORDS + }, + contains: [ + hljs.SHEBANG({ + binary: "groovy", + relevance: 10 + }), + COMMENT, + STRING, + REGEXP, + NUMBER, + CLASS_DEFINITION, + { + className: 'meta', + begin: '@[A-Za-z]+', + relevance: 0 + }, + { + // highlight map keys and named parameters as attrs + className: 'attr', + begin: IDENT_RE + '[ \t]*:', + relevance: 0 + }, + { + // catch middle element of the ternary operator + // to avoid highlight it as a label, named parameter, or map key + begin: /\?/, + end: /:/, + relevance: 0, + contains: [ + COMMENT, + STRING, + REGEXP, + NUMBER, + 'self' + ] + }, + { + // highlight labeled statements + className: 'symbol', + begin: '^[ \t]*' + regex.lookahead(IDENT_RE + ':'), + excludeBegin: true, + end: IDENT_RE + ':', + relevance: 0 + } + ], + illegal: /#|<\// + }; +} + +export { groovy as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/groovy.js.js b/frontend/node_modules/highlight.js/es/languages/groovy.js.js new file mode 100644 index 0000000..38508e2 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/groovy.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/groovy" instead of "highlight.js/lib/languages/groovy.js"' + ); + } + } + emitWarning(); + import lang from './groovy.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/haml.js b/frontend/node_modules/highlight.js/es/languages/haml.js new file mode 100644 index 0000000..f692c1c --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/haml.js @@ -0,0 +1,113 @@ +/* +Language: HAML +Requires: ruby.js +Author: Dan Allen +Website: http://haml.info +Category: template +*/ + +// TODO support filter tags like :javascript, support inline HTML +function haml(hljs) { + return { + name: 'HAML', + case_insensitive: true, + contains: [ + { + className: 'meta', + begin: '^!!!( (5|1\\.1|Strict|Frameset|Basic|Mobile|RDFa|XML\\b.*))?$', + relevance: 10 + }, + // FIXME these comments should be allowed to span indented lines + hljs.COMMENT( + '^\\s*(!=#|=#|-#|/).*$', + null, + { relevance: 0 } + ), + { + begin: '^\\s*(-|=|!=)(?!#)', + end: /$/, + subLanguage: 'ruby', + excludeBegin: true, + excludeEnd: true + }, + { + className: 'tag', + begin: '^\\s*%', + contains: [ + { + className: 'selector-tag', + begin: '\\w+' + }, + { + className: 'selector-id', + begin: '#[\\w-]+' + }, + { + className: 'selector-class', + begin: '\\.[\\w-]+' + }, + { + begin: /\{\s*/, + end: /\s*\}/, + contains: [ + { + begin: ':\\w+\\s*=>', + end: ',\\s+', + returnBegin: true, + endsWithParent: true, + contains: [ + { + className: 'attr', + begin: ':\\w+' + }, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + { + begin: '\\w+', + relevance: 0 + } + ] + } + ] + }, + { + begin: '\\(\\s*', + end: '\\s*\\)', + excludeEnd: true, + contains: [ + { + begin: '\\w+\\s*=', + end: '\\s+', + returnBegin: true, + endsWithParent: true, + contains: [ + { + className: 'attr', + begin: '\\w+', + relevance: 0 + }, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + { + begin: '\\w+', + relevance: 0 + } + ] + } + ] + } + ] + }, + { begin: '^\\s*[=~]\\s*' }, + { + begin: /#\{/, + end: /\}/, + subLanguage: 'ruby', + excludeBegin: true, + excludeEnd: true + } + ] + }; +} + +export { haml as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/haml.js.js b/frontend/node_modules/highlight.js/es/languages/haml.js.js new file mode 100644 index 0000000..11bc74f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/haml.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/haml" instead of "highlight.js/lib/languages/haml.js"' + ); + } + } + emitWarning(); + import lang from './haml.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/handlebars.js b/frontend/node_modules/highlight.js/es/languages/handlebars.js new file mode 100644 index 0000000..04a31a2 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/handlebars.js @@ -0,0 +1,258 @@ +/* +Language: Handlebars +Requires: xml.js +Author: Robin Ward +Description: Matcher for Handlebars as well as EmberJS additions. +Website: https://handlebarsjs.com +Category: template +*/ + +function handlebars(hljs) { + const regex = hljs.regex; + const BUILT_INS = { + $pattern: /[\w.\/]+/, + built_in: [ + 'action', + 'bindattr', + 'collection', + 'component', + 'concat', + 'debugger', + 'each', + 'each-in', + 'get', + 'hash', + 'if', + 'in', + 'input', + 'link-to', + 'loc', + 'log', + 'lookup', + 'mut', + 'outlet', + 'partial', + 'query-params', + 'render', + 'template', + 'textarea', + 'unbound', + 'unless', + 'view', + 'with', + 'yield' + ] + }; + + const LITERALS = { + $pattern: /[\w.\/]+/, + literal: [ + 'true', + 'false', + 'undefined', + 'null' + ] + }; + + // as defined in https://handlebarsjs.com/guide/expressions.html#literal-segments + // this regex matches literal segments like ' abc ' or [ abc ] as well as helpers and paths + // like a/b, ./abc/cde, and abc.bcd + + const DOUBLE_QUOTED_ID_REGEX = /""|"[^"]+"/; + const SINGLE_QUOTED_ID_REGEX = /''|'[^']+'/; + const BRACKET_QUOTED_ID_REGEX = /\[\]|\[[^\]]+\]/; + const PLAIN_ID_REGEX = /[^\s!"#%&'()*+,.\/;<=>@\[\\\]^`{|}~]+/; + const PATH_DELIMITER_REGEX = /(\.|\/)/; + const ANY_ID = regex.either( + DOUBLE_QUOTED_ID_REGEX, + SINGLE_QUOTED_ID_REGEX, + BRACKET_QUOTED_ID_REGEX, + PLAIN_ID_REGEX + ); + + const IDENTIFIER_REGEX = regex.concat( + regex.optional(/\.|\.\/|\//), // relative or absolute path + ANY_ID, + regex.anyNumberOfTimes(regex.concat( + PATH_DELIMITER_REGEX, + ANY_ID + )) + ); + + // identifier followed by a equal-sign (without the equal sign) + const HASH_PARAM_REGEX = regex.concat( + '(', + BRACKET_QUOTED_ID_REGEX, '|', + PLAIN_ID_REGEX, + ')(?==)' + ); + + const HELPER_NAME_OR_PATH_EXPRESSION = { begin: IDENTIFIER_REGEX }; + + const HELPER_PARAMETER = hljs.inherit(HELPER_NAME_OR_PATH_EXPRESSION, { keywords: LITERALS }); + + const SUB_EXPRESSION = { + begin: /\(/, + end: /\)/ + // the "contains" is added below when all necessary sub-modes are defined + }; + + const HASH = { + // fka "attribute-assignment", parameters of the form 'key=value' + className: 'attr', + begin: HASH_PARAM_REGEX, + relevance: 0, + starts: { + begin: /=/, + end: /=/, + starts: { contains: [ + hljs.NUMBER_MODE, + hljs.QUOTE_STRING_MODE, + hljs.APOS_STRING_MODE, + HELPER_PARAMETER, + SUB_EXPRESSION + ] } + } + }; + + const BLOCK_PARAMS = { + // parameters of the form '{{#with x as | y |}}...{{/with}}' + begin: /as\s+\|/, + keywords: { keyword: 'as' }, + end: /\|/, + contains: [ + { + // define sub-mode in order to prevent highlighting of block-parameter named "as" + begin: /\w+/ } + ] + }; + + const HELPER_PARAMETERS = { + contains: [ + hljs.NUMBER_MODE, + hljs.QUOTE_STRING_MODE, + hljs.APOS_STRING_MODE, + BLOCK_PARAMS, + HASH, + HELPER_PARAMETER, + SUB_EXPRESSION + ], + returnEnd: true + // the property "end" is defined through inheritance when the mode is used. If depends + // on the surrounding mode, but "endsWithParent" does not work here (i.e. it includes the + // end-token of the surrounding mode) + }; + + const SUB_EXPRESSION_CONTENTS = hljs.inherit(HELPER_NAME_OR_PATH_EXPRESSION, { + className: 'name', + keywords: BUILT_INS, + starts: hljs.inherit(HELPER_PARAMETERS, { end: /\)/ }) + }); + + SUB_EXPRESSION.contains = [ SUB_EXPRESSION_CONTENTS ]; + + const OPENING_BLOCK_MUSTACHE_CONTENTS = hljs.inherit(HELPER_NAME_OR_PATH_EXPRESSION, { + keywords: BUILT_INS, + className: 'name', + starts: hljs.inherit(HELPER_PARAMETERS, { end: /\}\}/ }) + }); + + const CLOSING_BLOCK_MUSTACHE_CONTENTS = hljs.inherit(HELPER_NAME_OR_PATH_EXPRESSION, { + keywords: BUILT_INS, + className: 'name' + }); + + const BASIC_MUSTACHE_CONTENTS = hljs.inherit(HELPER_NAME_OR_PATH_EXPRESSION, { + className: 'name', + keywords: BUILT_INS, + starts: hljs.inherit(HELPER_PARAMETERS, { end: /\}\}/ }) + }); + + const ESCAPE_MUSTACHE_WITH_PRECEEDING_BACKSLASH = { + begin: /\\\{\{/, + skip: true + }; + const PREVENT_ESCAPE_WITH_ANOTHER_PRECEEDING_BACKSLASH = { + begin: /\\\\(?=\{\{)/, + skip: true + }; + + return { + name: 'Handlebars', + aliases: [ + 'hbs', + 'html.hbs', + 'html.handlebars', + 'htmlbars' + ], + case_insensitive: true, + subLanguage: 'xml', + contains: [ + ESCAPE_MUSTACHE_WITH_PRECEEDING_BACKSLASH, + PREVENT_ESCAPE_WITH_ANOTHER_PRECEEDING_BACKSLASH, + hljs.COMMENT(/\{\{!--/, /--\}\}/), + hljs.COMMENT(/\{\{!/, /\}\}/), + { + // open raw block "{{{{raw}}}} content not evaluated {{{{/raw}}}}" + className: 'template-tag', + begin: /\{\{\{\{(?!\/)/, + end: /\}\}\}\}/, + contains: [ OPENING_BLOCK_MUSTACHE_CONTENTS ], + starts: { + end: /\{\{\{\{\//, + returnEnd: true, + subLanguage: 'xml' + } + }, + { + // close raw block + className: 'template-tag', + begin: /\{\{\{\{\//, + end: /\}\}\}\}/, + contains: [ CLOSING_BLOCK_MUSTACHE_CONTENTS ] + }, + { + // open block statement + className: 'template-tag', + begin: /\{\{#/, + end: /\}\}/, + contains: [ OPENING_BLOCK_MUSTACHE_CONTENTS ] + }, + { + className: 'template-tag', + begin: /\{\{(?=else\}\})/, + end: /\}\}/, + keywords: 'else' + }, + { + className: 'template-tag', + begin: /\{\{(?=else if)/, + end: /\}\}/, + keywords: 'else if' + }, + { + // closing block statement + className: 'template-tag', + begin: /\{\{\//, + end: /\}\}/, + contains: [ CLOSING_BLOCK_MUSTACHE_CONTENTS ] + }, + { + // template variable or helper-call that is NOT html-escaped + className: 'template-variable', + begin: /\{\{\{/, + end: /\}\}\}/, + contains: [ BASIC_MUSTACHE_CONTENTS ] + }, + { + // template variable or helper-call that is html-escaped + className: 'template-variable', + begin: /\{\{/, + end: /\}\}/, + contains: [ BASIC_MUSTACHE_CONTENTS ] + } + ] + }; +} + +export { handlebars as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/handlebars.js.js b/frontend/node_modules/highlight.js/es/languages/handlebars.js.js new file mode 100644 index 0000000..bbaeee4 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/handlebars.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/handlebars" instead of "highlight.js/lib/languages/handlebars.js"' + ); + } + } + emitWarning(); + import lang from './handlebars.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/haskell.js b/frontend/node_modules/highlight.js/es/languages/haskell.js new file mode 100644 index 0000000..490a97a --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/haskell.js @@ -0,0 +1,217 @@ +/* +Language: Haskell +Author: Jeremy Hull +Contributors: Zena Treep +Website: https://www.haskell.org +Category: functional +*/ + +function haskell(hljs) { + + /* See: + - https://www.haskell.org/onlinereport/lexemes.html + - https://downloads.haskell.org/ghc/9.0.1/docs/html/users_guide/exts/binary_literals.html + - https://downloads.haskell.org/ghc/9.0.1/docs/html/users_guide/exts/numeric_underscores.html + - https://downloads.haskell.org/ghc/9.0.1/docs/html/users_guide/exts/hex_float_literals.html + */ + const decimalDigits = '([0-9]_*)+'; + const hexDigits = '([0-9a-fA-F]_*)+'; + const binaryDigits = '([01]_*)+'; + const octalDigits = '([0-7]_*)+'; + const ascSymbol = '[!#$%&*+.\\/<=>?@\\\\^~-]'; + const uniSymbol = '(\\p{S}|\\p{P})'; // Symbol or Punctuation + const special = '[(),;\\[\\]`|{}]'; + const symbol = `(${ascSymbol}|(?!(${special}|[_:"']))${uniSymbol})`; + + const COMMENT = { variants: [ + // Double dash forms a valid comment only if it's not part of legal lexeme. + // See: Haskell 98 report: https://www.haskell.org/onlinereport/lexemes.html + // + // The commented code does the job, but we can't use negative lookbehind, + // due to poor support by Safari browser. + // > hljs.COMMENT(`(?|<-' } + ] + }; +} + +export { haskell as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/haskell.js.js b/frontend/node_modules/highlight.js/es/languages/haskell.js.js new file mode 100644 index 0000000..320c13f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/haskell.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/haskell" instead of "highlight.js/lib/languages/haskell.js"' + ); + } + } + emitWarning(); + import lang from './haskell.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/haxe.js b/frontend/node_modules/highlight.js/es/languages/haxe.js new file mode 100644 index 0000000..9ad3a8b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/haxe.js @@ -0,0 +1,167 @@ +/* +Language: Haxe +Description: Haxe is an open source toolkit based on a modern, high level, strictly typed programming language. +Author: Christopher Kaster (Based on the actionscript.js language file by Alexander Myadzel) +Contributors: Kenton Hamaluik +Website: https://haxe.org +Category: system +*/ + +function haxe(hljs) { + const IDENT_RE = '[a-zA-Z_$][a-zA-Z0-9_$]*'; + + // C_NUMBER_RE with underscores and literal suffixes + const HAXE_NUMBER_RE = /(-?)(\b0[xX][a-fA-F0-9_]+|(\b\d+(\.[\d_]*)?|\.[\d_]+)(([eE][-+]?\d+)|i32|u32|i64|f64)?)/; + + const HAXE_BASIC_TYPES = 'Int Float String Bool Dynamic Void Array '; + + return { + name: 'Haxe', + aliases: [ 'hx' ], + keywords: { + keyword: 'abstract break case cast catch continue default do dynamic else enum extern ' + + 'final for function here if import in inline is macro never new override package private get set ' + + 'public return static super switch this throw trace try typedef untyped using var while ' + + HAXE_BASIC_TYPES, + built_in: + 'trace this', + literal: + 'true false null _' + }, + contains: [ + { + className: 'string', // interpolate-able strings + begin: '\'', + end: '\'', + contains: [ + hljs.BACKSLASH_ESCAPE, + { + className: 'subst', // interpolation + begin: /\$\{/, + end: /\}/ + }, + { + className: 'subst', // interpolation + begin: /\$/, + end: /\W\}/ + } + ] + }, + hljs.QUOTE_STRING_MODE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + { + className: 'number', + begin: HAXE_NUMBER_RE, + relevance: 0 + }, + { + className: 'variable', + begin: "\\$" + IDENT_RE, + }, + { + className: 'meta', // compiler meta + begin: /@:?/, + end: /\(|$/, + excludeEnd: true, + }, + { + className: 'meta', // compiler conditionals + begin: '#', + end: '$', + keywords: { keyword: 'if else elseif end error' } + }, + { + className: 'type', // function types + begin: /:[ \t]*/, + end: /[^A-Za-z0-9_ \t\->]/, + excludeBegin: true, + excludeEnd: true, + relevance: 0 + }, + { + className: 'type', // types + begin: /:[ \t]*/, + end: /\W/, + excludeBegin: true, + excludeEnd: true + }, + { + className: 'type', // instantiation + beginKeywords: 'new', + end: /\W/, + excludeBegin: true, + excludeEnd: true + }, + { + className: 'title.class', // enums + beginKeywords: 'enum', + end: /\{/, + contains: [ hljs.TITLE_MODE ] + }, + { + className: 'title.class', // abstracts + begin: '\\babstract\\b(?=\\s*' + hljs.IDENT_RE + '\\s*\\()', + end: /[\{$]/, + contains: [ + { + className: 'type', + begin: /\(/, + end: /\)/, + excludeBegin: true, + excludeEnd: true + }, + { + className: 'type', + begin: /from +/, + end: /\W/, + excludeBegin: true, + excludeEnd: true + }, + { + className: 'type', + begin: /to +/, + end: /\W/, + excludeBegin: true, + excludeEnd: true + }, + hljs.TITLE_MODE + ], + keywords: { keyword: 'abstract from to' } + }, + { + className: 'title.class', // classes + begin: /\b(class|interface) +/, + end: /[\{$]/, + excludeEnd: true, + keywords: 'class interface', + contains: [ + { + className: 'keyword', + begin: /\b(extends|implements) +/, + keywords: 'extends implements', + contains: [ + { + className: 'type', + begin: hljs.IDENT_RE, + relevance: 0 + } + ] + }, + hljs.TITLE_MODE + ] + }, + { + className: 'title.function', + beginKeywords: 'function', + end: /\(/, + excludeEnd: true, + illegal: /\S/, + contains: [ hljs.TITLE_MODE ] + } + ], + illegal: /<\// + }; +} + +export { haxe as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/haxe.js.js b/frontend/node_modules/highlight.js/es/languages/haxe.js.js new file mode 100644 index 0000000..5310d67 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/haxe.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/haxe" instead of "highlight.js/lib/languages/haxe.js"' + ); + } + } + emitWarning(); + import lang from './haxe.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/hsp.js b/frontend/node_modules/highlight.js/es/languages/hsp.js new file mode 100644 index 0000000..6f265bc --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/hsp.js @@ -0,0 +1,59 @@ +/* +Language: HSP +Author: prince +Website: https://en.wikipedia.org/wiki/Hot_Soup_Processor +Category: scripting +*/ + +function hsp(hljs) { + return { + name: 'HSP', + case_insensitive: true, + keywords: { + $pattern: /[\w._]+/, + keyword: 'goto gosub return break repeat loop continue wait await dim sdim foreach dimtype dup dupptr end stop newmod delmod mref run exgoto on mcall assert logmes newlab resume yield onexit onerror onkey onclick oncmd exist delete mkdir chdir dirlist bload bsave bcopy memfile if else poke wpoke lpoke getstr chdpm memexpand memcpy memset notesel noteadd notedel noteload notesave randomize noteunsel noteget split strrep setease button chgdisp exec dialog mmload mmplay mmstop mci pset pget syscolor mes print title pos circle cls font sysfont objsize picload color palcolor palette redraw width gsel gcopy gzoom gmode bmpsave hsvcolor getkey listbox chkbox combox input mesbox buffer screen bgscr mouse objsel groll line clrobj boxf objprm objmode stick grect grotate gsquare gradf objimage objskip objenable celload celdiv celput newcom querycom delcom cnvstow comres axobj winobj sendmsg comevent comevarg sarrayconv callfunc cnvwtos comevdisp libptr system hspstat hspver stat cnt err strsize looplev sublev iparam wparam lparam refstr refdval int rnd strlen length length2 length3 length4 vartype gettime peek wpeek lpeek varptr varuse noteinfo instr abs limit getease str strmid strf getpath strtrim sin cos tan atan sqrt double absf expf logf limitf powf geteasef mousex mousey mousew hwnd hinstance hdc ginfo objinfo dirinfo sysinfo thismod __hspver__ __hsp30__ __date__ __time__ __line__ __file__ _debug __hspdef__ and or xor not screen_normal screen_palette screen_hide screen_fixedsize screen_tool screen_frame gmode_gdi gmode_mem gmode_rgb0 gmode_alpha gmode_rgb0alpha gmode_add gmode_sub gmode_pixela ginfo_mx ginfo_my ginfo_act ginfo_sel ginfo_wx1 ginfo_wy1 ginfo_wx2 ginfo_wy2 ginfo_vx ginfo_vy ginfo_sizex ginfo_sizey ginfo_winx ginfo_winy ginfo_mesx ginfo_mesy ginfo_r ginfo_g ginfo_b ginfo_paluse ginfo_dispx ginfo_dispy ginfo_cx ginfo_cy ginfo_intid ginfo_newid ginfo_sx ginfo_sy objinfo_mode objinfo_bmscr objinfo_hwnd notemax notesize dir_cur dir_exe dir_win dir_sys dir_cmdline dir_desktop dir_mydoc dir_tv font_normal font_bold font_italic font_underline font_strikeout font_antialias objmode_normal objmode_guifont objmode_usefont gsquare_grad msgothic msmincho do until while wend for next _break _continue switch case default swbreak swend ddim ldim alloc m_pi rad2deg deg2rad ease_linear ease_quad_in ease_quad_out ease_quad_inout ease_cubic_in ease_cubic_out ease_cubic_inout ease_quartic_in ease_quartic_out ease_quartic_inout ease_bounce_in ease_bounce_out ease_bounce_inout ease_shake_in ease_shake_out ease_shake_inout ease_loop' + }, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + hljs.APOS_STRING_MODE, + + { + // multi-line string + className: 'string', + begin: /\{"/, + end: /"\}/, + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + + hljs.COMMENT(';', '$', { relevance: 0 }), + + { + // pre-processor + className: 'meta', + begin: '#', + end: '$', + keywords: { keyword: 'addion cfunc cmd cmpopt comfunc const defcfunc deffunc define else endif enum epack func global if ifdef ifndef include modcfunc modfunc modinit modterm module pack packopt regcmd runtime undef usecom uselib' }, + contains: [ + hljs.inherit(hljs.QUOTE_STRING_MODE, { className: 'string' }), + hljs.NUMBER_MODE, + hljs.C_NUMBER_MODE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + + { + // label + className: 'symbol', + begin: '^\\*(\\w+|@)' + }, + + hljs.NUMBER_MODE, + hljs.C_NUMBER_MODE + ] + }; +} + +export { hsp as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/hsp.js.js b/frontend/node_modules/highlight.js/es/languages/hsp.js.js new file mode 100644 index 0000000..bd988c0 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/hsp.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/hsp" instead of "highlight.js/lib/languages/hsp.js"' + ); + } + } + emitWarning(); + import lang from './hsp.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/http.js b/frontend/node_modules/highlight.js/es/languages/http.js new file mode 100644 index 0000000..8577d7e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/http.js @@ -0,0 +1,97 @@ +/* +Language: HTTP +Description: HTTP request and response headers with automatic body highlighting +Author: Ivan Sagalaev +Category: protocols, web +Website: https://developer.mozilla.org/en-US/docs/Web/HTTP/Overview +*/ + +function http(hljs) { + const regex = hljs.regex; + const VERSION = 'HTTP/([32]|1\\.[01])'; + const HEADER_NAME = /[A-Za-z][A-Za-z0-9-]*/; + const HEADER = { + className: 'attribute', + begin: regex.concat('^', HEADER_NAME, '(?=\\:\\s)'), + starts: { contains: [ + { + className: "punctuation", + begin: /: /, + relevance: 0, + starts: { + end: '$', + relevance: 0 + } + } + ] } + }; + const HEADERS_AND_BODY = [ + HEADER, + { + begin: '\\n\\n', + starts: { + subLanguage: [], + endsWithParent: true + } + } + ]; + + return { + name: 'HTTP', + aliases: [ 'https' ], + illegal: /\S/, + contains: [ + // response + { + begin: '^(?=' + VERSION + " \\d{3})", + end: /$/, + contains: [ + { + className: "meta", + begin: VERSION + }, + { + className: 'number', + begin: '\\b\\d{3}\\b' + } + ], + starts: { + end: /\b\B/, + illegal: /\S/, + contains: HEADERS_AND_BODY + } + }, + // request + { + begin: '(?=^[A-Z]+ (.*?) ' + VERSION + '$)', + end: /$/, + contains: [ + { + className: 'string', + begin: ' ', + end: ' ', + excludeBegin: true, + excludeEnd: true + }, + { + className: "meta", + begin: VERSION + }, + { + className: 'keyword', + begin: '[A-Z]+' + } + ], + starts: { + end: /\b\B/, + illegal: /\S/, + contains: HEADERS_AND_BODY + } + }, + // to allow headers to work even without a preamble + hljs.inherit(HEADER, { relevance: 0 }) + ] + }; +} + +export { http as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/http.js.js b/frontend/node_modules/highlight.js/es/languages/http.js.js new file mode 100644 index 0000000..bf0ce63 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/http.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/http" instead of "highlight.js/lib/languages/http.js"' + ); + } + } + emitWarning(); + import lang from './http.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/hy.js b/frontend/node_modules/highlight.js/es/languages/hy.js new file mode 100644 index 0000000..417be0b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/hy.js @@ -0,0 +1,137 @@ +/* +Language: Hy +Description: Hy is a wonderful dialect of Lisp that’s embedded in Python. +Author: Sergey Sobko +Website: http://docs.hylang.org/en/stable/ +Category: lisp +*/ + +function hy(hljs) { + const SYMBOLSTART = 'a-zA-Z_\\-!.?+*=<>&#\''; + const SYMBOL_RE = '[' + SYMBOLSTART + '][' + SYMBOLSTART + '0-9/;:]*'; + const keywords = { + $pattern: SYMBOL_RE, + built_in: + // keywords + '!= % %= & &= * ** **= *= *map ' + + '+ += , --build-class-- --import-- -= . / // //= ' + + '/= < << <<= <= = > >= >> >>= ' + + '@ @= ^ ^= abs accumulate all and any ap-compose ' + + 'ap-dotimes ap-each ap-each-while ap-filter ap-first ap-if ap-last ap-map ap-map-when ap-pipe ' + + 'ap-reduce ap-reject apply as-> ascii assert assoc bin break butlast ' + + 'callable calling-module-name car case cdr chain chr coll? combinations compile ' + + 'compress cond cons cons? continue count curry cut cycle dec ' + + 'def default-method defclass defmacro defmacro-alias defmacro/g! defmain defmethod defmulti defn ' + + 'defn-alias defnc defnr defreader defseq del delattr delete-route dict-comp dir ' + + 'disassemble dispatch-reader-macro distinct divmod do doto drop drop-last drop-while empty? ' + + 'end-sequence eval eval-and-compile eval-when-compile even? every? except exec filter first ' + + 'flatten float? fn fnc fnr for for* format fraction genexpr ' + + 'gensym get getattr global globals group-by hasattr hash hex id ' + + 'identity if if* if-not if-python2 import in inc input instance? ' + + 'integer integer-char? integer? interleave interpose is is-coll is-cons is-empty is-even ' + + 'is-every is-float is-instance is-integer is-integer-char is-iterable is-iterator is-keyword is-neg is-none ' + + 'is-not is-numeric is-odd is-pos is-string is-symbol is-zero isinstance islice issubclass ' + + 'iter iterable? iterate iterator? keyword keyword? lambda last len let ' + + 'lif lif-not list* list-comp locals loop macro-error macroexpand macroexpand-1 macroexpand-all ' + + 'map max merge-with method-decorator min multi-decorator multicombinations name neg? next ' + + 'none? nonlocal not not-in not? nth numeric? oct odd? open ' + + 'or ord partition permutations pos? post-route postwalk pow prewalk print ' + + 'product profile/calls profile/cpu put-route quasiquote quote raise range read read-str ' + + 'recursive-replace reduce remove repeat repeatedly repr require rest round route ' + + 'route-with-methods rwm second seq set-comp setattr setv some sorted string ' + + 'string? sum switch symbol? take take-nth take-while tee try unless ' + + 'unquote unquote-splicing vars walk when while with with* with-decorator with-gensyms ' + + 'xi xor yield yield-from zero? zip zip-longest | |= ~' + }; + + const SIMPLE_NUMBER_RE = '[-+]?\\d+(\\.\\d+)?'; + + const SYMBOL = { + begin: SYMBOL_RE, + relevance: 0 + }; + const NUMBER = { + className: 'number', + begin: SIMPLE_NUMBER_RE, + relevance: 0 + }; + const STRING = hljs.inherit(hljs.QUOTE_STRING_MODE, { illegal: null }); + const COMMENT = hljs.COMMENT( + ';', + '$', + { relevance: 0 } + ); + const LITERAL = { + className: 'literal', + begin: /\b([Tt]rue|[Ff]alse|nil|None)\b/ + }; + const COLLECTION = { + begin: '[\\[\\{]', + end: '[\\]\\}]', + relevance: 0 + }; + const HINT = { + className: 'comment', + begin: '\\^' + SYMBOL_RE + }; + const HINT_COL = hljs.COMMENT('\\^\\{', '\\}'); + const KEY = { + className: 'symbol', + begin: '[:]{1,2}' + SYMBOL_RE + }; + const LIST = { + begin: '\\(', + end: '\\)' + }; + const BODY = { + endsWithParent: true, + relevance: 0 + }; + const NAME = { + className: 'name', + relevance: 0, + keywords: keywords, + begin: SYMBOL_RE, + starts: BODY + }; + const DEFAULT_CONTAINS = [ + LIST, + STRING, + HINT, + HINT_COL, + COMMENT, + KEY, + COLLECTION, + NUMBER, + LITERAL, + SYMBOL + ]; + + LIST.contains = [ + hljs.COMMENT('comment', ''), + NAME, + BODY + ]; + BODY.contains = DEFAULT_CONTAINS; + COLLECTION.contains = DEFAULT_CONTAINS; + + return { + name: 'Hy', + aliases: [ 'hylang' ], + illegal: /\S/, + contains: [ + hljs.SHEBANG(), + LIST, + STRING, + HINT, + HINT_COL, + COMMENT, + KEY, + COLLECTION, + NUMBER, + LITERAL + ] + }; +} + +export { hy as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/hy.js.js b/frontend/node_modules/highlight.js/es/languages/hy.js.js new file mode 100644 index 0000000..c1d9338 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/hy.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/hy" instead of "highlight.js/lib/languages/hy.js"' + ); + } + } + emitWarning(); + import lang from './hy.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/inform7.js b/frontend/node_modules/highlight.js/es/languages/inform7.js new file mode 100644 index 0000000..fee8fe4 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/inform7.js @@ -0,0 +1,70 @@ +/* +Language: Inform 7 +Author: Bruno Dias +Description: Language definition for Inform 7, a DSL for writing parser interactive fiction. +Website: http://inform7.com +Category: gaming +*/ + +function inform7(hljs) { + const START_BRACKET = '\\['; + const END_BRACKET = '\\]'; + return { + name: 'Inform 7', + aliases: [ 'i7' ], + case_insensitive: true, + keywords: { + // Some keywords more or less unique to I7, for relevance. + keyword: + // kind: + 'thing room person man woman animal container ' + + 'supporter backdrop door ' + // characteristic: + + 'scenery open closed locked inside gender ' + // verb: + + 'is are say understand ' + // misc keyword: + + 'kind of rule' }, + contains: [ + { + className: 'string', + begin: '"', + end: '"', + relevance: 0, + contains: [ + { + className: 'subst', + begin: START_BRACKET, + end: END_BRACKET + } + ] + }, + { + className: 'section', + begin: /^(Volume|Book|Part|Chapter|Section|Table)\b/, + end: '$' + }, + { + // Rule definition + // This is here for relevance. + begin: /^(Check|Carry out|Report|Instead of|To|Rule|When|Before|After)\b/, + end: ':', + contains: [ + { + // Rule name + begin: '\\(This', + end: '\\)' + } + ] + }, + { + className: 'comment', + begin: START_BRACKET, + end: END_BRACKET, + contains: [ 'self' ] + } + ] + }; +} + +export { inform7 as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/inform7.js.js b/frontend/node_modules/highlight.js/es/languages/inform7.js.js new file mode 100644 index 0000000..ae60d23 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/inform7.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/inform7" instead of "highlight.js/lib/languages/inform7.js"' + ); + } + } + emitWarning(); + import lang from './inform7.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/ini.js b/frontend/node_modules/highlight.js/es/languages/ini.js new file mode 100644 index 0000000..a43977f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ini.js @@ -0,0 +1,121 @@ +/* +Language: TOML, also INI +Description: TOML aims to be a minimal configuration file format that's easy to read due to obvious semantics. +Contributors: Guillaume Gomez +Category: common, config +Website: https://github.com/toml-lang/toml +*/ + +function ini(hljs) { + const regex = hljs.regex; + const NUMBERS = { + className: 'number', + relevance: 0, + variants: [ + { begin: /([+-]+)?[\d]+_[\d_]+/ }, + { begin: hljs.NUMBER_RE } + ] + }; + const COMMENTS = hljs.COMMENT(); + COMMENTS.variants = [ + { + begin: /;/, + end: /$/ + }, + { + begin: /#/, + end: /$/ + } + ]; + const VARIABLES = { + className: 'variable', + variants: [ + { begin: /\$[\w\d"][\w\d_]*/ }, + { begin: /\$\{(.*?)\}/ } + ] + }; + const LITERALS = { + className: 'literal', + begin: /\bon|off|true|false|yes|no\b/ + }; + const STRINGS = { + className: "string", + contains: [ hljs.BACKSLASH_ESCAPE ], + variants: [ + { + begin: "'''", + end: "'''", + relevance: 10 + }, + { + begin: '"""', + end: '"""', + relevance: 10 + }, + { + begin: '"', + end: '"' + }, + { + begin: "'", + end: "'" + } + ] + }; + const ARRAY = { + begin: /\[/, + end: /\]/, + contains: [ + COMMENTS, + LITERALS, + VARIABLES, + STRINGS, + NUMBERS, + 'self' + ], + relevance: 0 + }; + + const BARE_KEY = /[A-Za-z0-9_-]+/; + const QUOTED_KEY_DOUBLE_QUOTE = /"(\\"|[^"])*"/; + const QUOTED_KEY_SINGLE_QUOTE = /'[^']*'/; + const ANY_KEY = regex.either( + BARE_KEY, QUOTED_KEY_DOUBLE_QUOTE, QUOTED_KEY_SINGLE_QUOTE + ); + const DOTTED_KEY = regex.concat( + ANY_KEY, '(\\s*\\.\\s*', ANY_KEY, ')*', + regex.lookahead(/\s*=\s*[^#\s]/) + ); + + return { + name: 'TOML, also INI', + aliases: [ 'toml' ], + case_insensitive: true, + illegal: /\S/, + contains: [ + COMMENTS, + { + className: 'section', + begin: /\[+/, + end: /\]+/ + }, + { + begin: DOTTED_KEY, + className: 'attr', + starts: { + end: /$/, + contains: [ + COMMENTS, + ARRAY, + LITERALS, + VARIABLES, + STRINGS, + NUMBERS + ] + } + } + ] + }; +} + +export { ini as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/ini.js.js b/frontend/node_modules/highlight.js/es/languages/ini.js.js new file mode 100644 index 0000000..05b9994 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ini.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/ini" instead of "highlight.js/lib/languages/ini.js"' + ); + } + } + emitWarning(); + import lang from './ini.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/irpf90.js b/frontend/node_modules/highlight.js/es/languages/irpf90.js new file mode 100644 index 0000000..4fc8950 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/irpf90.js @@ -0,0 +1,107 @@ +/* +Language: IRPF90 +Author: Anthony Scemama +Description: IRPF90 is an open-source Fortran code generator +Website: http://irpf90.ups-tlse.fr +Category: scientific +*/ + +/** @type LanguageFn */ +function irpf90(hljs) { + const regex = hljs.regex; + const PARAMS = { + className: 'params', + begin: '\\(', + end: '\\)' + }; + + // regex in both fortran and irpf90 should match + const OPTIONAL_NUMBER_SUFFIX = /(_[a-z_\d]+)?/; + const OPTIONAL_NUMBER_EXP = /([de][+-]?\d+)?/; + const NUMBER = { + className: 'number', + variants: [ + { begin: regex.concat(/\b\d+/, /\.(\d*)/, OPTIONAL_NUMBER_EXP, OPTIONAL_NUMBER_SUFFIX) }, + { begin: regex.concat(/\b\d+/, OPTIONAL_NUMBER_EXP, OPTIONAL_NUMBER_SUFFIX) }, + { begin: regex.concat(/\.\d+/, OPTIONAL_NUMBER_EXP, OPTIONAL_NUMBER_SUFFIX) } + ], + relevance: 0 + }; + + const F_KEYWORDS = { + literal: '.False. .True.', + keyword: 'kind do while private call intrinsic where elsewhere ' + + 'type endtype endmodule endselect endinterface end enddo endif if forall endforall only contains default return stop then ' + + 'public subroutine|10 function program .and. .or. .not. .le. .eq. .ge. .gt. .lt. ' + + 'goto save else use module select case ' + + 'access blank direct exist file fmt form formatted iostat name named nextrec number opened rec recl sequential status unformatted unit ' + + 'continue format pause cycle exit ' + + 'c_null_char c_alert c_backspace c_form_feed flush wait decimal round iomsg ' + + 'synchronous nopass non_overridable pass protected volatile abstract extends import ' + + 'non_intrinsic value deferred generic final enumerator class associate bind enum ' + + 'c_int c_short c_long c_long_long c_signed_char c_size_t c_int8_t c_int16_t c_int32_t c_int64_t c_int_least8_t c_int_least16_t ' + + 'c_int_least32_t c_int_least64_t c_int_fast8_t c_int_fast16_t c_int_fast32_t c_int_fast64_t c_intmax_t C_intptr_t c_float c_double ' + + 'c_long_double c_float_complex c_double_complex c_long_double_complex c_bool c_char c_null_ptr c_null_funptr ' + + 'c_new_line c_carriage_return c_horizontal_tab c_vertical_tab iso_c_binding c_loc c_funloc c_associated c_f_pointer ' + + 'c_ptr c_funptr iso_fortran_env character_storage_size error_unit file_storage_size input_unit iostat_end iostat_eor ' + + 'numeric_storage_size output_unit c_f_procpointer ieee_arithmetic ieee_support_underflow_control ' + + 'ieee_get_underflow_mode ieee_set_underflow_mode newunit contiguous recursive ' + + 'pad position action delim readwrite eor advance nml interface procedure namelist include sequence elemental pure ' + + 'integer real character complex logical dimension allocatable|10 parameter ' + + 'external implicit|10 none double precision assign intent optional pointer ' + + 'target in out common equivalence data ' + // IRPF90 special keywords + + 'begin_provider &begin_provider end_provider begin_shell end_shell begin_template end_template subst assert touch ' + + 'soft_touch provide no_dep free irp_if irp_else irp_endif irp_write irp_read', + built_in: 'alog alog10 amax0 amax1 amin0 amin1 amod cabs ccos cexp clog csin csqrt dabs dacos dasin datan datan2 dcos dcosh ddim dexp dint ' + + 'dlog dlog10 dmax1 dmin1 dmod dnint dsign dsin dsinh dsqrt dtan dtanh float iabs idim idint idnint ifix isign max0 max1 min0 min1 sngl ' + + 'algama cdabs cdcos cdexp cdlog cdsin cdsqrt cqabs cqcos cqexp cqlog cqsin cqsqrt dcmplx dconjg derf derfc dfloat dgamma dimag dlgama ' + + 'iqint qabs qacos qasin qatan qatan2 qcmplx qconjg qcos qcosh qdim qerf qerfc qexp qgamma qimag qlgama qlog qlog10 qmax1 qmin1 qmod ' + + 'qnint qsign qsin qsinh qsqrt qtan qtanh abs acos aimag aint anint asin atan atan2 char cmplx conjg cos cosh exp ichar index int log ' + + 'log10 max min nint sign sin sinh sqrt tan tanh print write dim lge lgt lle llt mod nullify allocate deallocate ' + + 'adjustl adjustr all allocated any associated bit_size btest ceiling count cshift date_and_time digits dot_product ' + + 'eoshift epsilon exponent floor fraction huge iand ibclr ibits ibset ieor ior ishft ishftc lbound len_trim matmul ' + + 'maxexponent maxloc maxval merge minexponent minloc minval modulo mvbits nearest pack present product ' + + 'radix random_number random_seed range repeat reshape rrspacing scale scan selected_int_kind selected_real_kind ' + + 'set_exponent shape size spacing spread sum system_clock tiny transpose trim ubound unpack verify achar iachar transfer ' + + 'dble entry dprod cpu_time command_argument_count get_command get_command_argument get_environment_variable is_iostat_end ' + + 'ieee_arithmetic ieee_support_underflow_control ieee_get_underflow_mode ieee_set_underflow_mode ' + + 'is_iostat_eor move_alloc new_line selected_char_kind same_type_as extends_type_of ' + + 'acosh asinh atanh bessel_j0 bessel_j1 bessel_jn bessel_y0 bessel_y1 bessel_yn erf erfc erfc_scaled gamma log_gamma hypot norm2 ' + + 'atomic_define atomic_ref execute_command_line leadz trailz storage_size merge_bits ' + + 'bge bgt ble blt dshiftl dshiftr findloc iall iany iparity image_index lcobound ucobound maskl maskr ' + + 'num_images parity popcnt poppar shifta shiftl shiftr this_image ' + // IRPF90 special built_ins + + 'IRP_ALIGN irp_here' + }; + return { + name: 'IRPF90', + case_insensitive: true, + keywords: F_KEYWORDS, + illegal: /\/\*/, + contains: [ + hljs.inherit(hljs.APOS_STRING_MODE, { + className: 'string', + relevance: 0 + }), + hljs.inherit(hljs.QUOTE_STRING_MODE, { + className: 'string', + relevance: 0 + }), + { + className: 'function', + beginKeywords: 'subroutine function program', + illegal: '[${=\\n]', + contains: [ + hljs.UNDERSCORE_TITLE_MODE, + PARAMS + ] + }, + hljs.COMMENT('!', '$', { relevance: 0 }), + hljs.COMMENT('begin_doc', 'end_doc', { relevance: 10 }), + NUMBER + ] + }; +} + +export { irpf90 as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/irpf90.js.js b/frontend/node_modules/highlight.js/es/languages/irpf90.js.js new file mode 100644 index 0000000..f2cbec9 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/irpf90.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/irpf90" instead of "highlight.js/lib/languages/irpf90.js"' + ); + } + } + emitWarning(); + import lang from './irpf90.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/isbl.js b/frontend/node_modules/highlight.js/es/languages/isbl.js new file mode 100644 index 0000000..6f2049f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/isbl.js @@ -0,0 +1,3205 @@ +/* +Language: ISBL +Author: Dmitriy Tarasov +Description: built-in language DIRECTUM +Category: enterprise +*/ + +function isbl(hljs) { + // Определение идентификаторов + const UNDERSCORE_IDENT_RE = "[A-Za-zА-Яа-яёЁ_!][A-Za-zА-Яа-яёЁ_0-9]*"; + + // Определение имен функций + const FUNCTION_NAME_IDENT_RE = "[A-Za-zА-Яа-яёЁ_][A-Za-zА-Яа-яёЁ_0-9]*"; + + // keyword : ключевые слова + const KEYWORD = + "and и else иначе endexcept endfinally endforeach конецвсе endif конецесли endwhile конецпока " + + "except exitfor finally foreach все if если in в not не or или try while пока "; + + // SYSRES Constants + const sysres_constants = + "SYSRES_CONST_ACCES_RIGHT_TYPE_EDIT " + + "SYSRES_CONST_ACCES_RIGHT_TYPE_FULL " + + "SYSRES_CONST_ACCES_RIGHT_TYPE_VIEW " + + "SYSRES_CONST_ACCESS_MODE_REQUISITE_CODE " + + "SYSRES_CONST_ACCESS_NO_ACCESS_VIEW " + + "SYSRES_CONST_ACCESS_NO_ACCESS_VIEW_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_ADD_REQUISITE_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_ADD_REQUISITE_YES_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_CHANGE_REQUISITE_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_CHANGE_REQUISITE_YES_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_DELETE_REQUISITE_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_DELETE_REQUISITE_YES_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_EXECUTE_REQUISITE_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_EXECUTE_REQUISITE_YES_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_NO_ACCESS_REQUISITE_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_NO_ACCESS_REQUISITE_YES_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_RATIFY_REQUISITE_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_RATIFY_REQUISITE_YES_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_REQUISITE_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_VIEW " + + "SYSRES_CONST_ACCESS_RIGHTS_VIEW_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_VIEW_REQUISITE_CODE " + + "SYSRES_CONST_ACCESS_RIGHTS_VIEW_REQUISITE_YES_CODE " + + "SYSRES_CONST_ACCESS_TYPE_CHANGE " + + "SYSRES_CONST_ACCESS_TYPE_CHANGE_CODE " + + "SYSRES_CONST_ACCESS_TYPE_EXISTS " + + "SYSRES_CONST_ACCESS_TYPE_EXISTS_CODE " + + "SYSRES_CONST_ACCESS_TYPE_FULL " + + "SYSRES_CONST_ACCESS_TYPE_FULL_CODE " + + "SYSRES_CONST_ACCESS_TYPE_VIEW " + + "SYSRES_CONST_ACCESS_TYPE_VIEW_CODE " + + "SYSRES_CONST_ACTION_TYPE_ABORT " + + "SYSRES_CONST_ACTION_TYPE_ACCEPT " + + "SYSRES_CONST_ACTION_TYPE_ACCESS_RIGHTS " + + "SYSRES_CONST_ACTION_TYPE_ADD_ATTACHMENT " + + "SYSRES_CONST_ACTION_TYPE_CHANGE_CARD " + + "SYSRES_CONST_ACTION_TYPE_CHANGE_KIND " + + "SYSRES_CONST_ACTION_TYPE_CHANGE_STORAGE " + + "SYSRES_CONST_ACTION_TYPE_CONTINUE " + + "SYSRES_CONST_ACTION_TYPE_COPY " + + "SYSRES_CONST_ACTION_TYPE_CREATE " + + "SYSRES_CONST_ACTION_TYPE_CREATE_VERSION " + + "SYSRES_CONST_ACTION_TYPE_DELETE " + + "SYSRES_CONST_ACTION_TYPE_DELETE_ATTACHMENT " + + "SYSRES_CONST_ACTION_TYPE_DELETE_VERSION " + + "SYSRES_CONST_ACTION_TYPE_DISABLE_DELEGATE_ACCESS_RIGHTS " + + "SYSRES_CONST_ACTION_TYPE_ENABLE_DELEGATE_ACCESS_RIGHTS " + + "SYSRES_CONST_ACTION_TYPE_ENCRYPTION_BY_CERTIFICATE " + + "SYSRES_CONST_ACTION_TYPE_ENCRYPTION_BY_CERTIFICATE_AND_PASSWORD " + + "SYSRES_CONST_ACTION_TYPE_ENCRYPTION_BY_PASSWORD " + + "SYSRES_CONST_ACTION_TYPE_EXPORT_WITH_LOCK " + + "SYSRES_CONST_ACTION_TYPE_EXPORT_WITHOUT_LOCK " + + "SYSRES_CONST_ACTION_TYPE_IMPORT_WITH_UNLOCK " + + "SYSRES_CONST_ACTION_TYPE_IMPORT_WITHOUT_UNLOCK " + + "SYSRES_CONST_ACTION_TYPE_LIFE_CYCLE_STAGE " + + "SYSRES_CONST_ACTION_TYPE_LOCK " + + "SYSRES_CONST_ACTION_TYPE_LOCK_FOR_SERVER " + + "SYSRES_CONST_ACTION_TYPE_LOCK_MODIFY " + + "SYSRES_CONST_ACTION_TYPE_MARK_AS_READED " + + "SYSRES_CONST_ACTION_TYPE_MARK_AS_UNREADED " + + "SYSRES_CONST_ACTION_TYPE_MODIFY " + + "SYSRES_CONST_ACTION_TYPE_MODIFY_CARD " + + "SYSRES_CONST_ACTION_TYPE_MOVE_TO_ARCHIVE " + + "SYSRES_CONST_ACTION_TYPE_OFF_ENCRYPTION " + + "SYSRES_CONST_ACTION_TYPE_PASSWORD_CHANGE " + + "SYSRES_CONST_ACTION_TYPE_PERFORM " + + "SYSRES_CONST_ACTION_TYPE_RECOVER_FROM_LOCAL_COPY " + + "SYSRES_CONST_ACTION_TYPE_RESTART " + + "SYSRES_CONST_ACTION_TYPE_RESTORE_FROM_ARCHIVE " + + "SYSRES_CONST_ACTION_TYPE_REVISION " + + "SYSRES_CONST_ACTION_TYPE_SEND_BY_MAIL " + + "SYSRES_CONST_ACTION_TYPE_SIGN " + + "SYSRES_CONST_ACTION_TYPE_START " + + "SYSRES_CONST_ACTION_TYPE_UNLOCK " + + "SYSRES_CONST_ACTION_TYPE_UNLOCK_FROM_SERVER " + + "SYSRES_CONST_ACTION_TYPE_VERSION_STATE " + + "SYSRES_CONST_ACTION_TYPE_VERSION_VISIBILITY " + + "SYSRES_CONST_ACTION_TYPE_VIEW " + + "SYSRES_CONST_ACTION_TYPE_VIEW_SHADOW_COPY " + + "SYSRES_CONST_ACTION_TYPE_WORKFLOW_DESCRIPTION_MODIFY " + + "SYSRES_CONST_ACTION_TYPE_WRITE_HISTORY " + + "SYSRES_CONST_ACTIVE_VERSION_STATE_PICK_VALUE " + + "SYSRES_CONST_ADD_REFERENCE_MODE_NAME " + + "SYSRES_CONST_ADDITION_REQUISITE_CODE " + + "SYSRES_CONST_ADDITIONAL_PARAMS_REQUISITE_CODE " + + "SYSRES_CONST_ADITIONAL_JOB_END_DATE_REQUISITE_NAME " + + "SYSRES_CONST_ADITIONAL_JOB_READ_REQUISITE_NAME " + + "SYSRES_CONST_ADITIONAL_JOB_START_DATE_REQUISITE_NAME " + + "SYSRES_CONST_ADITIONAL_JOB_STATE_REQUISITE_NAME " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_ADDING_USER_TO_GROUP_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_ADDING_USER_TO_GROUP_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_CREATION_COMP_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_CREATION_COMP_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_CREATION_GROUP_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_CREATION_GROUP_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_CREATION_USER_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_CREATION_USER_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_DATABASE_USER_CREATION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_DATABASE_USER_CREATION_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_DATABASE_USER_DELETION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_DATABASE_USER_DELETION_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_DELETION_COMP_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_DELETION_COMP_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_DELETION_GROUP_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_DELETION_GROUP_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_DELETION_USER_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_DELETION_USER_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_DELETION_USER_FROM_GROUP_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_DELETION_USER_FROM_GROUP_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_GRANTING_FILTERER_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_GRANTING_FILTERER_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_GRANTING_FILTERER_RESTRICTION_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_GRANTING_FILTERER_RESTRICTION_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_GRANTING_PRIVILEGE_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_GRANTING_PRIVILEGE_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_GRANTING_RIGHTS_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_GRANTING_RIGHTS_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_IS_MAIN_SERVER_CHANGED_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_IS_MAIN_SERVER_CHANGED_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_IS_PUBLIC_CHANGED_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_IS_PUBLIC_CHANGED_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_REMOVING_FILTERER_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_REMOVING_FILTERER_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_REMOVING_FILTERER_RESTRICTION_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_REMOVING_FILTERER_RESTRICTION_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_REMOVING_PRIVILEGE_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_REMOVING_PRIVILEGE_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_REMOVING_RIGHTS_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_REMOVING_RIGHTS_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_SERVER_LOGIN_CREATION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_SERVER_LOGIN_CREATION_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_SERVER_LOGIN_DELETION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_SERVER_LOGIN_DELETION_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_CATEGORY_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_CATEGORY_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_COMP_TITLE_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_COMP_TITLE_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_FULL_NAME_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_FULL_NAME_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_GROUP_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_GROUP_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_PARENT_GROUP_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_PARENT_GROUP_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_USER_AUTH_TYPE_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_USER_AUTH_TYPE_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_USER_LOGIN_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_USER_LOGIN_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_USER_STATUS_ACTION " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_UPDATING_USER_STATUS_ACTION_CODE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_USER_PASSWORD_CHANGE " + + "SYSRES_CONST_ADMINISTRATION_HISTORY_USER_PASSWORD_CHANGE_ACTION " + + "SYSRES_CONST_ALL_ACCEPT_CONDITION_RUS " + + "SYSRES_CONST_ALL_USERS_GROUP " + + "SYSRES_CONST_ALL_USERS_GROUP_NAME " + + "SYSRES_CONST_ALL_USERS_SERVER_GROUP_NAME " + + "SYSRES_CONST_ALLOWED_ACCESS_TYPE_CODE " + + "SYSRES_CONST_ALLOWED_ACCESS_TYPE_NAME " + + "SYSRES_CONST_APP_VIEWER_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_APPROVING_SIGNATURE_NAME " + + "SYSRES_CONST_APPROVING_SIGNATURE_REQUISITE_CODE " + + "SYSRES_CONST_ASSISTANT_SUBSTITUE_TYPE " + + "SYSRES_CONST_ASSISTANT_SUBSTITUE_TYPE_CODE " + + "SYSRES_CONST_ATTACH_TYPE_COMPONENT_TOKEN " + + "SYSRES_CONST_ATTACH_TYPE_DOC " + + "SYSRES_CONST_ATTACH_TYPE_EDOC " + + "SYSRES_CONST_ATTACH_TYPE_FOLDER " + + "SYSRES_CONST_ATTACH_TYPE_JOB " + + "SYSRES_CONST_ATTACH_TYPE_REFERENCE " + + "SYSRES_CONST_ATTACH_TYPE_TASK " + + "SYSRES_CONST_AUTH_ENCODED_PASSWORD " + + "SYSRES_CONST_AUTH_ENCODED_PASSWORD_CODE " + + "SYSRES_CONST_AUTH_NOVELL " + + "SYSRES_CONST_AUTH_PASSWORD " + + "SYSRES_CONST_AUTH_PASSWORD_CODE " + + "SYSRES_CONST_AUTH_WINDOWS " + + "SYSRES_CONST_AUTHENTICATING_SIGNATURE_NAME " + + "SYSRES_CONST_AUTHENTICATING_SIGNATURE_REQUISITE_CODE " + + "SYSRES_CONST_AUTO_ENUM_METHOD_FLAG " + + "SYSRES_CONST_AUTO_NUMERATION_CODE " + + "SYSRES_CONST_AUTO_STRONG_ENUM_METHOD_FLAG " + + "SYSRES_CONST_AUTOTEXT_NAME_REQUISITE_CODE " + + "SYSRES_CONST_AUTOTEXT_TEXT_REQUISITE_CODE " + + "SYSRES_CONST_AUTOTEXT_USAGE_ALL " + + "SYSRES_CONST_AUTOTEXT_USAGE_ALL_CODE " + + "SYSRES_CONST_AUTOTEXT_USAGE_SIGN " + + "SYSRES_CONST_AUTOTEXT_USAGE_SIGN_CODE " + + "SYSRES_CONST_AUTOTEXT_USAGE_WORK " + + "SYSRES_CONST_AUTOTEXT_USAGE_WORK_CODE " + + "SYSRES_CONST_AUTOTEXT_USE_ANYWHERE_CODE " + + "SYSRES_CONST_AUTOTEXT_USE_ON_SIGNING_CODE " + + "SYSRES_CONST_AUTOTEXT_USE_ON_WORK_CODE " + + "SYSRES_CONST_BEGIN_DATE_REQUISITE_CODE " + + "SYSRES_CONST_BLACK_LIFE_CYCLE_STAGE_FONT_COLOR " + + "SYSRES_CONST_BLUE_LIFE_CYCLE_STAGE_FONT_COLOR " + + "SYSRES_CONST_BTN_PART " + + "SYSRES_CONST_CALCULATED_ROLE_TYPE_CODE " + + "SYSRES_CONST_CALL_TYPE_VARIABLE_BUTTON_VALUE " + + "SYSRES_CONST_CALL_TYPE_VARIABLE_PROGRAM_VALUE " + + "SYSRES_CONST_CANCEL_MESSAGE_FUNCTION_RESULT " + + "SYSRES_CONST_CARD_PART " + + "SYSRES_CONST_CARD_REFERENCE_MODE_NAME " + + "SYSRES_CONST_CERTIFICATE_TYPE_REQUISITE_ENCRYPT_VALUE " + + "SYSRES_CONST_CERTIFICATE_TYPE_REQUISITE_SIGN_AND_ENCRYPT_VALUE " + + "SYSRES_CONST_CERTIFICATE_TYPE_REQUISITE_SIGN_VALUE " + + "SYSRES_CONST_CHECK_PARAM_VALUE_DATE_PARAM_TYPE " + + "SYSRES_CONST_CHECK_PARAM_VALUE_FLOAT_PARAM_TYPE " + + "SYSRES_CONST_CHECK_PARAM_VALUE_INTEGER_PARAM_TYPE " + + "SYSRES_CONST_CHECK_PARAM_VALUE_PICK_PARAM_TYPE " + + "SYSRES_CONST_CHECK_PARAM_VALUE_REEFRENCE_PARAM_TYPE " + + "SYSRES_CONST_CLOSED_RECORD_FLAG_VALUE_FEMININE " + + "SYSRES_CONST_CLOSED_RECORD_FLAG_VALUE_MASCULINE " + + "SYSRES_CONST_CODE_COMPONENT_TYPE_ADMIN " + + "SYSRES_CONST_CODE_COMPONENT_TYPE_DEVELOPER " + + "SYSRES_CONST_CODE_COMPONENT_TYPE_DOCS " + + "SYSRES_CONST_CODE_COMPONENT_TYPE_EDOC_CARDS " + + "SYSRES_CONST_CODE_COMPONENT_TYPE_EXTERNAL_EXECUTABLE " + + "SYSRES_CONST_CODE_COMPONENT_TYPE_OTHER " + + "SYSRES_CONST_CODE_COMPONENT_TYPE_REFERENCE " + + "SYSRES_CONST_CODE_COMPONENT_TYPE_REPORT " + + "SYSRES_CONST_CODE_COMPONENT_TYPE_SCRIPT " + + "SYSRES_CONST_CODE_COMPONENT_TYPE_URL " + + "SYSRES_CONST_CODE_REQUISITE_ACCESS " + + "SYSRES_CONST_CODE_REQUISITE_CODE " + + "SYSRES_CONST_CODE_REQUISITE_COMPONENT " + + "SYSRES_CONST_CODE_REQUISITE_DESCRIPTION " + + "SYSRES_CONST_CODE_REQUISITE_EXCLUDE_COMPONENT " + + "SYSRES_CONST_CODE_REQUISITE_RECORD " + + "SYSRES_CONST_COMMENT_REQ_CODE " + + "SYSRES_CONST_COMMON_SETTINGS_REQUISITE_CODE " + + "SYSRES_CONST_COMP_CODE_GRD " + + "SYSRES_CONST_COMPONENT_GROUP_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_COMPONENT_TYPE_ADMIN_COMPONENTS " + + "SYSRES_CONST_COMPONENT_TYPE_DEVELOPER_COMPONENTS " + + "SYSRES_CONST_COMPONENT_TYPE_DOCS " + + "SYSRES_CONST_COMPONENT_TYPE_EDOC_CARDS " + + "SYSRES_CONST_COMPONENT_TYPE_EDOCS " + + "SYSRES_CONST_COMPONENT_TYPE_EXTERNAL_EXECUTABLE " + + "SYSRES_CONST_COMPONENT_TYPE_OTHER " + + "SYSRES_CONST_COMPONENT_TYPE_REFERENCE_TYPES " + + "SYSRES_CONST_COMPONENT_TYPE_REFERENCES " + + "SYSRES_CONST_COMPONENT_TYPE_REPORTS " + + "SYSRES_CONST_COMPONENT_TYPE_SCRIPTS " + + "SYSRES_CONST_COMPONENT_TYPE_URL " + + "SYSRES_CONST_COMPONENTS_REMOTE_SERVERS_VIEW_CODE " + + "SYSRES_CONST_CONDITION_BLOCK_DESCRIPTION " + + "SYSRES_CONST_CONST_FIRM_STATUS_COMMON " + + "SYSRES_CONST_CONST_FIRM_STATUS_INDIVIDUAL " + + "SYSRES_CONST_CONST_NEGATIVE_VALUE " + + "SYSRES_CONST_CONST_POSITIVE_VALUE " + + "SYSRES_CONST_CONST_SERVER_STATUS_DONT_REPLICATE " + + "SYSRES_CONST_CONST_SERVER_STATUS_REPLICATE " + + "SYSRES_CONST_CONTENTS_REQUISITE_CODE " + + "SYSRES_CONST_DATA_TYPE_BOOLEAN " + + "SYSRES_CONST_DATA_TYPE_DATE " + + "SYSRES_CONST_DATA_TYPE_FLOAT " + + "SYSRES_CONST_DATA_TYPE_INTEGER " + + "SYSRES_CONST_DATA_TYPE_PICK " + + "SYSRES_CONST_DATA_TYPE_REFERENCE " + + "SYSRES_CONST_DATA_TYPE_STRING " + + "SYSRES_CONST_DATA_TYPE_TEXT " + + "SYSRES_CONST_DATA_TYPE_VARIANT " + + "SYSRES_CONST_DATE_CLOSE_REQ_CODE " + + "SYSRES_CONST_DATE_FORMAT_DATE_ONLY_CHAR " + + "SYSRES_CONST_DATE_OPEN_REQ_CODE " + + "SYSRES_CONST_DATE_REQUISITE " + + "SYSRES_CONST_DATE_REQUISITE_CODE " + + "SYSRES_CONST_DATE_REQUISITE_NAME " + + "SYSRES_CONST_DATE_REQUISITE_TYPE " + + "SYSRES_CONST_DATE_TYPE_CHAR " + + "SYSRES_CONST_DATETIME_FORMAT_VALUE " + + "SYSRES_CONST_DEA_ACCESS_RIGHTS_ACTION_CODE " + + "SYSRES_CONST_DESCRIPTION_LOCALIZE_ID_REQUISITE_CODE " + + "SYSRES_CONST_DESCRIPTION_REQUISITE_CODE " + + "SYSRES_CONST_DET1_PART " + + "SYSRES_CONST_DET2_PART " + + "SYSRES_CONST_DET3_PART " + + "SYSRES_CONST_DET4_PART " + + "SYSRES_CONST_DET5_PART " + + "SYSRES_CONST_DET6_PART " + + "SYSRES_CONST_DETAIL_DATASET_KEY_REQUISITE_CODE " + + "SYSRES_CONST_DETAIL_PICK_REQUISITE_CODE " + + "SYSRES_CONST_DETAIL_REQ_CODE " + + "SYSRES_CONST_DO_NOT_USE_ACCESS_TYPE_CODE " + + "SYSRES_CONST_DO_NOT_USE_ACCESS_TYPE_NAME " + + "SYSRES_CONST_DO_NOT_USE_ON_VIEW_ACCESS_TYPE_CODE " + + "SYSRES_CONST_DO_NOT_USE_ON_VIEW_ACCESS_TYPE_NAME " + + "SYSRES_CONST_DOCUMENT_STORAGES_CODE " + + "SYSRES_CONST_DOCUMENT_TEMPLATES_TYPE_NAME " + + "SYSRES_CONST_DOUBLE_REQUISITE_CODE " + + "SYSRES_CONST_EDITOR_CLOSE_FILE_OBSERV_TYPE_CODE " + + "SYSRES_CONST_EDITOR_CLOSE_PROCESS_OBSERV_TYPE_CODE " + + "SYSRES_CONST_EDITOR_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_EDITORS_APPLICATION_NAME_REQUISITE_CODE " + + "SYSRES_CONST_EDITORS_CREATE_SEVERAL_PROCESSES_REQUISITE_CODE " + + "SYSRES_CONST_EDITORS_EXTENSION_REQUISITE_CODE " + + "SYSRES_CONST_EDITORS_OBSERVER_BY_PROCESS_TYPE " + + "SYSRES_CONST_EDITORS_REFERENCE_CODE " + + "SYSRES_CONST_EDITORS_REPLACE_SPEC_CHARS_REQUISITE_CODE " + + "SYSRES_CONST_EDITORS_USE_PLUGINS_REQUISITE_CODE " + + "SYSRES_CONST_EDITORS_VIEW_DOCUMENT_OPENED_TO_EDIT_CODE " + + "SYSRES_CONST_EDOC_CARD_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_EDOC_CARD_TYPES_LINK_REQUISITE_CODE " + + "SYSRES_CONST_EDOC_CERTIFICATE_AND_PASSWORD_ENCODE_CODE " + + "SYSRES_CONST_EDOC_CERTIFICATE_ENCODE_CODE " + + "SYSRES_CONST_EDOC_DATE_REQUISITE_CODE " + + "SYSRES_CONST_EDOC_KIND_REFERENCE_CODE " + + "SYSRES_CONST_EDOC_KINDS_BY_TEMPLATE_ACTION_CODE " + + "SYSRES_CONST_EDOC_MANAGE_ACCESS_CODE " + + "SYSRES_CONST_EDOC_NONE_ENCODE_CODE " + + "SYSRES_CONST_EDOC_NUMBER_REQUISITE_CODE " + + "SYSRES_CONST_EDOC_PASSWORD_ENCODE_CODE " + + "SYSRES_CONST_EDOC_READONLY_ACCESS_CODE " + + "SYSRES_CONST_EDOC_SHELL_LIFE_TYPE_VIEW_VALUE " + + "SYSRES_CONST_EDOC_SIZE_RESTRICTION_PRIORITY_REQUISITE_CODE " + + "SYSRES_CONST_EDOC_STORAGE_CHECK_ACCESS_RIGHTS_REQUISITE_CODE " + + "SYSRES_CONST_EDOC_STORAGE_COMPUTER_NAME_REQUISITE_CODE " + + "SYSRES_CONST_EDOC_STORAGE_DATABASE_NAME_REQUISITE_CODE " + + "SYSRES_CONST_EDOC_STORAGE_EDIT_IN_STORAGE_REQUISITE_CODE " + + "SYSRES_CONST_EDOC_STORAGE_LOCAL_PATH_REQUISITE_CODE " + + "SYSRES_CONST_EDOC_STORAGE_SHARED_SOURCE_NAME_REQUISITE_CODE " + + "SYSRES_CONST_EDOC_TEMPLATE_REQUISITE_CODE " + + "SYSRES_CONST_EDOC_TYPES_REFERENCE_CODE " + + "SYSRES_CONST_EDOC_VERSION_ACTIVE_STAGE_CODE " + + "SYSRES_CONST_EDOC_VERSION_DESIGN_STAGE_CODE " + + "SYSRES_CONST_EDOC_VERSION_OBSOLETE_STAGE_CODE " + + "SYSRES_CONST_EDOC_WRITE_ACCES_CODE " + + "SYSRES_CONST_EDOCUMENT_CARD_REQUISITES_REFERENCE_CODE_SELECTED_REQUISITE " + + "SYSRES_CONST_ENCODE_CERTIFICATE_TYPE_CODE " + + "SYSRES_CONST_END_DATE_REQUISITE_CODE " + + "SYSRES_CONST_ENUMERATION_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_EXECUTE_ACCESS_RIGHTS_TYPE_CODE " + + "SYSRES_CONST_EXECUTIVE_FILE_STORAGE_TYPE " + + "SYSRES_CONST_EXIST_CONST " + + "SYSRES_CONST_EXIST_VALUE " + + "SYSRES_CONST_EXPORT_LOCK_TYPE_ASK " + + "SYSRES_CONST_EXPORT_LOCK_TYPE_WITH_LOCK " + + "SYSRES_CONST_EXPORT_LOCK_TYPE_WITHOUT_LOCK " + + "SYSRES_CONST_EXPORT_VERSION_TYPE_ASK " + + "SYSRES_CONST_EXPORT_VERSION_TYPE_LAST " + + "SYSRES_CONST_EXPORT_VERSION_TYPE_LAST_ACTIVE " + + "SYSRES_CONST_EXTENSION_REQUISITE_CODE " + + "SYSRES_CONST_FILTER_NAME_REQUISITE_CODE " + + "SYSRES_CONST_FILTER_REQUISITE_CODE " + + "SYSRES_CONST_FILTER_TYPE_COMMON_CODE " + + "SYSRES_CONST_FILTER_TYPE_COMMON_NAME " + + "SYSRES_CONST_FILTER_TYPE_USER_CODE " + + "SYSRES_CONST_FILTER_TYPE_USER_NAME " + + "SYSRES_CONST_FILTER_VALUE_REQUISITE_NAME " + + "SYSRES_CONST_FLOAT_NUMBER_FORMAT_CHAR " + + "SYSRES_CONST_FLOAT_REQUISITE_TYPE " + + "SYSRES_CONST_FOLDER_AUTHOR_VALUE " + + "SYSRES_CONST_FOLDER_KIND_ANY_OBJECTS " + + "SYSRES_CONST_FOLDER_KIND_COMPONENTS " + + "SYSRES_CONST_FOLDER_KIND_EDOCS " + + "SYSRES_CONST_FOLDER_KIND_JOBS " + + "SYSRES_CONST_FOLDER_KIND_TASKS " + + "SYSRES_CONST_FOLDER_TYPE_COMMON " + + "SYSRES_CONST_FOLDER_TYPE_COMPONENT " + + "SYSRES_CONST_FOLDER_TYPE_FAVORITES " + + "SYSRES_CONST_FOLDER_TYPE_INBOX " + + "SYSRES_CONST_FOLDER_TYPE_OUTBOX " + + "SYSRES_CONST_FOLDER_TYPE_QUICK_LAUNCH " + + "SYSRES_CONST_FOLDER_TYPE_SEARCH " + + "SYSRES_CONST_FOLDER_TYPE_SHORTCUTS " + + "SYSRES_CONST_FOLDER_TYPE_USER " + + "SYSRES_CONST_FROM_DICTIONARY_ENUM_METHOD_FLAG " + + "SYSRES_CONST_FULL_SUBSTITUTE_TYPE " + + "SYSRES_CONST_FULL_SUBSTITUTE_TYPE_CODE " + + "SYSRES_CONST_FUNCTION_CANCEL_RESULT " + + "SYSRES_CONST_FUNCTION_CATEGORY_SYSTEM " + + "SYSRES_CONST_FUNCTION_CATEGORY_USER " + + "SYSRES_CONST_FUNCTION_FAILURE_RESULT " + + "SYSRES_CONST_FUNCTION_SAVE_RESULT " + + "SYSRES_CONST_GENERATED_REQUISITE " + + "SYSRES_CONST_GREEN_LIFE_CYCLE_STAGE_FONT_COLOR " + + "SYSRES_CONST_GROUP_ACCOUNT_TYPE_VALUE_CODE " + + "SYSRES_CONST_GROUP_CATEGORY_NORMAL_CODE " + + "SYSRES_CONST_GROUP_CATEGORY_NORMAL_NAME " + + "SYSRES_CONST_GROUP_CATEGORY_SERVICE_CODE " + + "SYSRES_CONST_GROUP_CATEGORY_SERVICE_NAME " + + "SYSRES_CONST_GROUP_COMMON_CATEGORY_FIELD_VALUE " + + "SYSRES_CONST_GROUP_FULL_NAME_REQUISITE_CODE " + + "SYSRES_CONST_GROUP_NAME_REQUISITE_CODE " + + "SYSRES_CONST_GROUP_RIGHTS_T_REQUISITE_CODE " + + "SYSRES_CONST_GROUP_SERVER_CODES_REQUISITE_CODE " + + "SYSRES_CONST_GROUP_SERVER_NAME_REQUISITE_CODE " + + "SYSRES_CONST_GROUP_SERVICE_CATEGORY_FIELD_VALUE " + + "SYSRES_CONST_GROUP_USER_REQUISITE_CODE " + + "SYSRES_CONST_GROUPS_REFERENCE_CODE " + + "SYSRES_CONST_GROUPS_REQUISITE_CODE " + + "SYSRES_CONST_HIDDEN_MODE_NAME " + + "SYSRES_CONST_HIGH_LVL_REQUISITE_CODE " + + "SYSRES_CONST_HISTORY_ACTION_CREATE_CODE " + + "SYSRES_CONST_HISTORY_ACTION_DELETE_CODE " + + "SYSRES_CONST_HISTORY_ACTION_EDIT_CODE " + + "SYSRES_CONST_HOUR_CHAR " + + "SYSRES_CONST_ID_REQUISITE_CODE " + + "SYSRES_CONST_IDSPS_REQUISITE_CODE " + + "SYSRES_CONST_IMAGE_MODE_COLOR " + + "SYSRES_CONST_IMAGE_MODE_GREYSCALE " + + "SYSRES_CONST_IMAGE_MODE_MONOCHROME " + + "SYSRES_CONST_IMPORTANCE_HIGH " + + "SYSRES_CONST_IMPORTANCE_LOW " + + "SYSRES_CONST_IMPORTANCE_NORMAL " + + "SYSRES_CONST_IN_DESIGN_VERSION_STATE_PICK_VALUE " + + "SYSRES_CONST_INCOMING_WORK_RULE_TYPE_CODE " + + "SYSRES_CONST_INT_REQUISITE " + + "SYSRES_CONST_INT_REQUISITE_TYPE " + + "SYSRES_CONST_INTEGER_NUMBER_FORMAT_CHAR " + + "SYSRES_CONST_INTEGER_TYPE_CHAR " + + "SYSRES_CONST_IS_GENERATED_REQUISITE_NEGATIVE_VALUE " + + "SYSRES_CONST_IS_PUBLIC_ROLE_REQUISITE_CODE " + + "SYSRES_CONST_IS_REMOTE_USER_NEGATIVE_VALUE " + + "SYSRES_CONST_IS_REMOTE_USER_POSITIVE_VALUE " + + "SYSRES_CONST_IS_STORED_REQUISITE_NEGATIVE_VALUE " + + "SYSRES_CONST_IS_STORED_REQUISITE_STORED_VALUE " + + "SYSRES_CONST_ITALIC_LIFE_CYCLE_STAGE_DRAW_STYLE " + + "SYSRES_CONST_JOB_BLOCK_DESCRIPTION " + + "SYSRES_CONST_JOB_KIND_CONTROL_JOB " + + "SYSRES_CONST_JOB_KIND_JOB " + + "SYSRES_CONST_JOB_KIND_NOTICE " + + "SYSRES_CONST_JOB_STATE_ABORTED " + + "SYSRES_CONST_JOB_STATE_COMPLETE " + + "SYSRES_CONST_JOB_STATE_WORKING " + + "SYSRES_CONST_KIND_REQUISITE_CODE " + + "SYSRES_CONST_KIND_REQUISITE_NAME " + + "SYSRES_CONST_KINDS_CREATE_SHADOW_COPIES_REQUISITE_CODE " + + "SYSRES_CONST_KINDS_DEFAULT_EDOC_LIFE_STAGE_REQUISITE_CODE " + + "SYSRES_CONST_KINDS_EDOC_ALL_TEPLATES_ALLOWED_REQUISITE_CODE " + + "SYSRES_CONST_KINDS_EDOC_ALLOW_LIFE_CYCLE_STAGE_CHANGING_REQUISITE_CODE " + + "SYSRES_CONST_KINDS_EDOC_ALLOW_MULTIPLE_ACTIVE_VERSIONS_REQUISITE_CODE " + + "SYSRES_CONST_KINDS_EDOC_SHARE_ACCES_RIGHTS_BY_DEFAULT_CODE " + + "SYSRES_CONST_KINDS_EDOC_TEMPLATE_REQUISITE_CODE " + + "SYSRES_CONST_KINDS_EDOC_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_KINDS_SIGNERS_REQUISITES_CODE " + + "SYSRES_CONST_KOD_INPUT_TYPE " + + "SYSRES_CONST_LAST_UPDATE_DATE_REQUISITE_CODE " + + "SYSRES_CONST_LIFE_CYCLE_START_STAGE_REQUISITE_CODE " + + "SYSRES_CONST_LILAC_LIFE_CYCLE_STAGE_FONT_COLOR " + + "SYSRES_CONST_LINK_OBJECT_KIND_COMPONENT " + + "SYSRES_CONST_LINK_OBJECT_KIND_DOCUMENT " + + "SYSRES_CONST_LINK_OBJECT_KIND_EDOC " + + "SYSRES_CONST_LINK_OBJECT_KIND_FOLDER " + + "SYSRES_CONST_LINK_OBJECT_KIND_JOB " + + "SYSRES_CONST_LINK_OBJECT_KIND_REFERENCE " + + "SYSRES_CONST_LINK_OBJECT_KIND_TASK " + + "SYSRES_CONST_LINK_REF_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_LIST_REFERENCE_MODE_NAME " + + "SYSRES_CONST_LOCALIZATION_DICTIONARY_MAIN_VIEW_CODE " + + "SYSRES_CONST_MAIN_VIEW_CODE " + + "SYSRES_CONST_MANUAL_ENUM_METHOD_FLAG " + + "SYSRES_CONST_MASTER_COMP_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_MASTER_TABLE_REC_ID_REQUISITE_CODE " + + "SYSRES_CONST_MAXIMIZED_MODE_NAME " + + "SYSRES_CONST_ME_VALUE " + + "SYSRES_CONST_MESSAGE_ATTENTION_CAPTION " + + "SYSRES_CONST_MESSAGE_CONFIRMATION_CAPTION " + + "SYSRES_CONST_MESSAGE_ERROR_CAPTION " + + "SYSRES_CONST_MESSAGE_INFORMATION_CAPTION " + + "SYSRES_CONST_MINIMIZED_MODE_NAME " + + "SYSRES_CONST_MINUTE_CHAR " + + "SYSRES_CONST_MODULE_REQUISITE_CODE " + + "SYSRES_CONST_MONITORING_BLOCK_DESCRIPTION " + + "SYSRES_CONST_MONTH_FORMAT_VALUE " + + "SYSRES_CONST_NAME_LOCALIZE_ID_REQUISITE_CODE " + + "SYSRES_CONST_NAME_REQUISITE_CODE " + + "SYSRES_CONST_NAME_SINGULAR_REQUISITE_CODE " + + "SYSRES_CONST_NAMEAN_INPUT_TYPE " + + "SYSRES_CONST_NEGATIVE_PICK_VALUE " + + "SYSRES_CONST_NEGATIVE_VALUE " + + "SYSRES_CONST_NO " + + "SYSRES_CONST_NO_PICK_VALUE " + + "SYSRES_CONST_NO_SIGNATURE_REQUISITE_CODE " + + "SYSRES_CONST_NO_VALUE " + + "SYSRES_CONST_NONE_ACCESS_RIGHTS_TYPE_CODE " + + "SYSRES_CONST_NONOPERATING_RECORD_FLAG_VALUE " + + "SYSRES_CONST_NONOPERATING_RECORD_FLAG_VALUE_MASCULINE " + + "SYSRES_CONST_NORMAL_ACCESS_RIGHTS_TYPE_CODE " + + "SYSRES_CONST_NORMAL_LIFE_CYCLE_STAGE_DRAW_STYLE " + + "SYSRES_CONST_NORMAL_MODE_NAME " + + "SYSRES_CONST_NOT_ALLOWED_ACCESS_TYPE_CODE " + + "SYSRES_CONST_NOT_ALLOWED_ACCESS_TYPE_NAME " + + "SYSRES_CONST_NOTE_REQUISITE_CODE " + + "SYSRES_CONST_NOTICE_BLOCK_DESCRIPTION " + + "SYSRES_CONST_NUM_REQUISITE " + + "SYSRES_CONST_NUM_STR_REQUISITE_CODE " + + "SYSRES_CONST_NUMERATION_AUTO_NOT_STRONG " + + "SYSRES_CONST_NUMERATION_AUTO_STRONG " + + "SYSRES_CONST_NUMERATION_FROM_DICTONARY " + + "SYSRES_CONST_NUMERATION_MANUAL " + + "SYSRES_CONST_NUMERIC_TYPE_CHAR " + + "SYSRES_CONST_NUMREQ_REQUISITE_CODE " + + "SYSRES_CONST_OBSOLETE_VERSION_STATE_PICK_VALUE " + + "SYSRES_CONST_OPERATING_RECORD_FLAG_VALUE " + + "SYSRES_CONST_OPERATING_RECORD_FLAG_VALUE_CODE " + + "SYSRES_CONST_OPERATING_RECORD_FLAG_VALUE_FEMININE " + + "SYSRES_CONST_OPERATING_RECORD_FLAG_VALUE_MASCULINE " + + "SYSRES_CONST_OPTIONAL_FORM_COMP_REQCODE_PREFIX " + + "SYSRES_CONST_ORANGE_LIFE_CYCLE_STAGE_FONT_COLOR " + + "SYSRES_CONST_ORIGINALREF_REQUISITE_CODE " + + "SYSRES_CONST_OURFIRM_REF_CODE " + + "SYSRES_CONST_OURFIRM_REQUISITE_CODE " + + "SYSRES_CONST_OURFIRM_VAR " + + "SYSRES_CONST_OUTGOING_WORK_RULE_TYPE_CODE " + + "SYSRES_CONST_PICK_NEGATIVE_RESULT " + + "SYSRES_CONST_PICK_POSITIVE_RESULT " + + "SYSRES_CONST_PICK_REQUISITE " + + "SYSRES_CONST_PICK_REQUISITE_TYPE " + + "SYSRES_CONST_PICK_TYPE_CHAR " + + "SYSRES_CONST_PLAN_STATUS_REQUISITE_CODE " + + "SYSRES_CONST_PLATFORM_VERSION_COMMENT " + + "SYSRES_CONST_PLUGINS_SETTINGS_DESCRIPTION_REQUISITE_CODE " + + "SYSRES_CONST_POSITIVE_PICK_VALUE " + + "SYSRES_CONST_POWER_TO_CREATE_ACTION_CODE " + + "SYSRES_CONST_POWER_TO_SIGN_ACTION_CODE " + + "SYSRES_CONST_PRIORITY_REQUISITE_CODE " + + "SYSRES_CONST_QUALIFIED_TASK_TYPE " + + "SYSRES_CONST_QUALIFIED_TASK_TYPE_CODE " + + "SYSRES_CONST_RECSTAT_REQUISITE_CODE " + + "SYSRES_CONST_RED_LIFE_CYCLE_STAGE_FONT_COLOR " + + "SYSRES_CONST_REF_ID_T_REF_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_REF_REQUISITE " + + "SYSRES_CONST_REF_REQUISITE_TYPE " + + "SYSRES_CONST_REF_REQUISITES_REFERENCE_CODE_SELECTED_REQUISITE " + + "SYSRES_CONST_REFERENCE_RECORD_HISTORY_CREATE_ACTION_CODE " + + "SYSRES_CONST_REFERENCE_RECORD_HISTORY_DELETE_ACTION_CODE " + + "SYSRES_CONST_REFERENCE_RECORD_HISTORY_MODIFY_ACTION_CODE " + + "SYSRES_CONST_REFERENCE_TYPE_CHAR " + + "SYSRES_CONST_REFERENCE_TYPE_REQUISITE_NAME " + + "SYSRES_CONST_REFERENCES_ADD_PARAMS_REQUISITE_CODE " + + "SYSRES_CONST_REFERENCES_DISPLAY_REQUISITE_REQUISITE_CODE " + + "SYSRES_CONST_REMOTE_SERVER_STATUS_WORKING " + + "SYSRES_CONST_REMOTE_SERVER_TYPE_MAIN " + + "SYSRES_CONST_REMOTE_SERVER_TYPE_SECONDARY " + + "SYSRES_CONST_REMOTE_USER_FLAG_VALUE_CODE " + + "SYSRES_CONST_REPORT_APP_EDITOR_INTERNAL " + + "SYSRES_CONST_REPORT_BASE_REPORT_ID_REQUISITE_CODE " + + "SYSRES_CONST_REPORT_BASE_REPORT_REQUISITE_CODE " + + "SYSRES_CONST_REPORT_SCRIPT_REQUISITE_CODE " + + "SYSRES_CONST_REPORT_TEMPLATE_REQUISITE_CODE " + + "SYSRES_CONST_REPORT_VIEWER_CODE_REQUISITE_CODE " + + "SYSRES_CONST_REQ_ALLOW_COMPONENT_DEFAULT_VALUE " + + "SYSRES_CONST_REQ_ALLOW_RECORD_DEFAULT_VALUE " + + "SYSRES_CONST_REQ_ALLOW_SERVER_COMPONENT_DEFAULT_VALUE " + + "SYSRES_CONST_REQ_MODE_AVAILABLE_CODE " + + "SYSRES_CONST_REQ_MODE_EDIT_CODE " + + "SYSRES_CONST_REQ_MODE_HIDDEN_CODE " + + "SYSRES_CONST_REQ_MODE_NOT_AVAILABLE_CODE " + + "SYSRES_CONST_REQ_MODE_VIEW_CODE " + + "SYSRES_CONST_REQ_NUMBER_REQUISITE_CODE " + + "SYSRES_CONST_REQ_SECTION_VALUE " + + "SYSRES_CONST_REQ_TYPE_VALUE " + + "SYSRES_CONST_REQUISITE_FORMAT_BY_UNIT " + + "SYSRES_CONST_REQUISITE_FORMAT_DATE_FULL " + + "SYSRES_CONST_REQUISITE_FORMAT_DATE_TIME " + + "SYSRES_CONST_REQUISITE_FORMAT_LEFT " + + "SYSRES_CONST_REQUISITE_FORMAT_RIGHT " + + "SYSRES_CONST_REQUISITE_FORMAT_WITHOUT_UNIT " + + "SYSRES_CONST_REQUISITE_NUMBER_REQUISITE_CODE " + + "SYSRES_CONST_REQUISITE_SECTION_ACTIONS " + + "SYSRES_CONST_REQUISITE_SECTION_BUTTON " + + "SYSRES_CONST_REQUISITE_SECTION_BUTTONS " + + "SYSRES_CONST_REQUISITE_SECTION_CARD " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE10 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE11 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE12 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE13 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE14 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE15 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE16 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE17 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE18 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE19 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE2 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE20 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE21 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE22 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE23 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE24 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE3 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE4 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE5 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE6 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE7 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE8 " + + "SYSRES_CONST_REQUISITE_SECTION_TABLE9 " + + "SYSRES_CONST_REQUISITES_PSEUDOREFERENCE_REQUISITE_NUMBER_REQUISITE_CODE " + + "SYSRES_CONST_RIGHT_ALIGNMENT_CODE " + + "SYSRES_CONST_ROLES_REFERENCE_CODE " + + "SYSRES_CONST_ROUTE_STEP_AFTER_RUS " + + "SYSRES_CONST_ROUTE_STEP_AND_CONDITION_RUS " + + "SYSRES_CONST_ROUTE_STEP_OR_CONDITION_RUS " + + "SYSRES_CONST_ROUTE_TYPE_COMPLEX " + + "SYSRES_CONST_ROUTE_TYPE_PARALLEL " + + "SYSRES_CONST_ROUTE_TYPE_SERIAL " + + "SYSRES_CONST_SBDATASETDESC_NEGATIVE_VALUE " + + "SYSRES_CONST_SBDATASETDESC_POSITIVE_VALUE " + + "SYSRES_CONST_SBVIEWSDESC_POSITIVE_VALUE " + + "SYSRES_CONST_SCRIPT_BLOCK_DESCRIPTION " + + "SYSRES_CONST_SEARCH_BY_TEXT_REQUISITE_CODE " + + "SYSRES_CONST_SEARCHES_COMPONENT_CONTENT " + + "SYSRES_CONST_SEARCHES_CRITERIA_ACTION_NAME " + + "SYSRES_CONST_SEARCHES_EDOC_CONTENT " + + "SYSRES_CONST_SEARCHES_FOLDER_CONTENT " + + "SYSRES_CONST_SEARCHES_JOB_CONTENT " + + "SYSRES_CONST_SEARCHES_REFERENCE_CODE " + + "SYSRES_CONST_SEARCHES_TASK_CONTENT " + + "SYSRES_CONST_SECOND_CHAR " + + "SYSRES_CONST_SECTION_REQUISITE_ACTIONS_VALUE " + + "SYSRES_CONST_SECTION_REQUISITE_CARD_VALUE " + + "SYSRES_CONST_SECTION_REQUISITE_CODE " + + "SYSRES_CONST_SECTION_REQUISITE_DETAIL_1_VALUE " + + "SYSRES_CONST_SECTION_REQUISITE_DETAIL_2_VALUE " + + "SYSRES_CONST_SECTION_REQUISITE_DETAIL_3_VALUE " + + "SYSRES_CONST_SECTION_REQUISITE_DETAIL_4_VALUE " + + "SYSRES_CONST_SECTION_REQUISITE_DETAIL_5_VALUE " + + "SYSRES_CONST_SECTION_REQUISITE_DETAIL_6_VALUE " + + "SYSRES_CONST_SELECT_REFERENCE_MODE_NAME " + + "SYSRES_CONST_SELECT_TYPE_SELECTABLE " + + "SYSRES_CONST_SELECT_TYPE_SELECTABLE_ONLY_CHILD " + + "SYSRES_CONST_SELECT_TYPE_SELECTABLE_WITH_CHILD " + + "SYSRES_CONST_SELECT_TYPE_UNSLECTABLE " + + "SYSRES_CONST_SERVER_TYPE_MAIN " + + "SYSRES_CONST_SERVICE_USER_CATEGORY_FIELD_VALUE " + + "SYSRES_CONST_SETTINGS_USER_REQUISITE_CODE " + + "SYSRES_CONST_SIGNATURE_AND_ENCODE_CERTIFICATE_TYPE_CODE " + + "SYSRES_CONST_SIGNATURE_CERTIFICATE_TYPE_CODE " + + "SYSRES_CONST_SINGULAR_TITLE_REQUISITE_CODE " + + "SYSRES_CONST_SQL_SERVER_AUTHENTIFICATION_FLAG_VALUE_CODE " + + "SYSRES_CONST_SQL_SERVER_ENCODE_AUTHENTIFICATION_FLAG_VALUE_CODE " + + "SYSRES_CONST_STANDART_ROUTE_REFERENCE_CODE " + + "SYSRES_CONST_STANDART_ROUTE_REFERENCE_COMMENT_REQUISITE_CODE " + + "SYSRES_CONST_STANDART_ROUTES_GROUPS_REFERENCE_CODE " + + "SYSRES_CONST_STATE_REQ_NAME " + + "SYSRES_CONST_STATE_REQUISITE_ACTIVE_VALUE " + + "SYSRES_CONST_STATE_REQUISITE_CLOSED_VALUE " + + "SYSRES_CONST_STATE_REQUISITE_CODE " + + "SYSRES_CONST_STATIC_ROLE_TYPE_CODE " + + "SYSRES_CONST_STATUS_PLAN_DEFAULT_VALUE " + + "SYSRES_CONST_STATUS_VALUE_AUTOCLEANING " + + "SYSRES_CONST_STATUS_VALUE_BLUE_SQUARE " + + "SYSRES_CONST_STATUS_VALUE_COMPLETE " + + "SYSRES_CONST_STATUS_VALUE_GREEN_SQUARE " + + "SYSRES_CONST_STATUS_VALUE_ORANGE_SQUARE " + + "SYSRES_CONST_STATUS_VALUE_PURPLE_SQUARE " + + "SYSRES_CONST_STATUS_VALUE_RED_SQUARE " + + "SYSRES_CONST_STATUS_VALUE_SUSPEND " + + "SYSRES_CONST_STATUS_VALUE_YELLOW_SQUARE " + + "SYSRES_CONST_STDROUTE_SHOW_TO_USERS_REQUISITE_CODE " + + "SYSRES_CONST_STORAGE_TYPE_FILE " + + "SYSRES_CONST_STORAGE_TYPE_SQL_SERVER " + + "SYSRES_CONST_STR_REQUISITE " + + "SYSRES_CONST_STRIKEOUT_LIFE_CYCLE_STAGE_DRAW_STYLE " + + "SYSRES_CONST_STRING_FORMAT_LEFT_ALIGN_CHAR " + + "SYSRES_CONST_STRING_FORMAT_RIGHT_ALIGN_CHAR " + + "SYSRES_CONST_STRING_REQUISITE_CODE " + + "SYSRES_CONST_STRING_REQUISITE_TYPE " + + "SYSRES_CONST_STRING_TYPE_CHAR " + + "SYSRES_CONST_SUBSTITUTES_PSEUDOREFERENCE_CODE " + + "SYSRES_CONST_SUBTASK_BLOCK_DESCRIPTION " + + "SYSRES_CONST_SYSTEM_SETTING_CURRENT_USER_PARAM_VALUE " + + "SYSRES_CONST_SYSTEM_SETTING_EMPTY_VALUE_PARAM_VALUE " + + "SYSRES_CONST_SYSTEM_VERSION_COMMENT " + + "SYSRES_CONST_TASK_ACCESS_TYPE_ALL " + + "SYSRES_CONST_TASK_ACCESS_TYPE_ALL_MEMBERS " + + "SYSRES_CONST_TASK_ACCESS_TYPE_MANUAL " + + "SYSRES_CONST_TASK_ENCODE_TYPE_CERTIFICATION " + + "SYSRES_CONST_TASK_ENCODE_TYPE_CERTIFICATION_AND_PASSWORD " + + "SYSRES_CONST_TASK_ENCODE_TYPE_NONE " + + "SYSRES_CONST_TASK_ENCODE_TYPE_PASSWORD " + + "SYSRES_CONST_TASK_ROUTE_ALL_CONDITION " + + "SYSRES_CONST_TASK_ROUTE_AND_CONDITION " + + "SYSRES_CONST_TASK_ROUTE_OR_CONDITION " + + "SYSRES_CONST_TASK_STATE_ABORTED " + + "SYSRES_CONST_TASK_STATE_COMPLETE " + + "SYSRES_CONST_TASK_STATE_CONTINUED " + + "SYSRES_CONST_TASK_STATE_CONTROL " + + "SYSRES_CONST_TASK_STATE_INIT " + + "SYSRES_CONST_TASK_STATE_WORKING " + + "SYSRES_CONST_TASK_TITLE " + + "SYSRES_CONST_TASK_TYPES_GROUPS_REFERENCE_CODE " + + "SYSRES_CONST_TASK_TYPES_REFERENCE_CODE " + + "SYSRES_CONST_TEMPLATES_REFERENCE_CODE " + + "SYSRES_CONST_TEST_DATE_REQUISITE_NAME " + + "SYSRES_CONST_TEST_DEV_DATABASE_NAME " + + "SYSRES_CONST_TEST_DEV_SYSTEM_CODE " + + "SYSRES_CONST_TEST_EDMS_DATABASE_NAME " + + "SYSRES_CONST_TEST_EDMS_MAIN_CODE " + + "SYSRES_CONST_TEST_EDMS_MAIN_DB_NAME " + + "SYSRES_CONST_TEST_EDMS_SECOND_CODE " + + "SYSRES_CONST_TEST_EDMS_SECOND_DB_NAME " + + "SYSRES_CONST_TEST_EDMS_SYSTEM_CODE " + + "SYSRES_CONST_TEST_NUMERIC_REQUISITE_NAME " + + "SYSRES_CONST_TEXT_REQUISITE " + + "SYSRES_CONST_TEXT_REQUISITE_CODE " + + "SYSRES_CONST_TEXT_REQUISITE_TYPE " + + "SYSRES_CONST_TEXT_TYPE_CHAR " + + "SYSRES_CONST_TYPE_CODE_REQUISITE_CODE " + + "SYSRES_CONST_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_UNDEFINED_LIFE_CYCLE_STAGE_FONT_COLOR " + + "SYSRES_CONST_UNITS_SECTION_ID_REQUISITE_CODE " + + "SYSRES_CONST_UNITS_SECTION_REQUISITE_CODE " + + "SYSRES_CONST_UNOPERATING_RECORD_FLAG_VALUE_CODE " + + "SYSRES_CONST_UNSTORED_DATA_REQUISITE_CODE " + + "SYSRES_CONST_UNSTORED_DATA_REQUISITE_NAME " + + "SYSRES_CONST_USE_ACCESS_TYPE_CODE " + + "SYSRES_CONST_USE_ACCESS_TYPE_NAME " + + "SYSRES_CONST_USER_ACCOUNT_TYPE_VALUE_CODE " + + "SYSRES_CONST_USER_ADDITIONAL_INFORMATION_REQUISITE_CODE " + + "SYSRES_CONST_USER_AND_GROUP_ID_FROM_PSEUDOREFERENCE_REQUISITE_CODE " + + "SYSRES_CONST_USER_CATEGORY_NORMAL " + + "SYSRES_CONST_USER_CERTIFICATE_REQUISITE_CODE " + + "SYSRES_CONST_USER_CERTIFICATE_STATE_REQUISITE_CODE " + + "SYSRES_CONST_USER_CERTIFICATE_SUBJECT_NAME_REQUISITE_CODE " + + "SYSRES_CONST_USER_CERTIFICATE_THUMBPRINT_REQUISITE_CODE " + + "SYSRES_CONST_USER_COMMON_CATEGORY " + + "SYSRES_CONST_USER_COMMON_CATEGORY_CODE " + + "SYSRES_CONST_USER_FULL_NAME_REQUISITE_CODE " + + "SYSRES_CONST_USER_GROUP_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_USER_LOGIN_REQUISITE_CODE " + + "SYSRES_CONST_USER_REMOTE_CONTROLLER_REQUISITE_CODE " + + "SYSRES_CONST_USER_REMOTE_SYSTEM_REQUISITE_CODE " + + "SYSRES_CONST_USER_RIGHTS_T_REQUISITE_CODE " + + "SYSRES_CONST_USER_SERVER_NAME_REQUISITE_CODE " + + "SYSRES_CONST_USER_SERVICE_CATEGORY " + + "SYSRES_CONST_USER_SERVICE_CATEGORY_CODE " + + "SYSRES_CONST_USER_STATUS_ADMINISTRATOR_CODE " + + "SYSRES_CONST_USER_STATUS_ADMINISTRATOR_NAME " + + "SYSRES_CONST_USER_STATUS_DEVELOPER_CODE " + + "SYSRES_CONST_USER_STATUS_DEVELOPER_NAME " + + "SYSRES_CONST_USER_STATUS_DISABLED_CODE " + + "SYSRES_CONST_USER_STATUS_DISABLED_NAME " + + "SYSRES_CONST_USER_STATUS_SYSTEM_DEVELOPER_CODE " + + "SYSRES_CONST_USER_STATUS_USER_CODE " + + "SYSRES_CONST_USER_STATUS_USER_NAME " + + "SYSRES_CONST_USER_STATUS_USER_NAME_DEPRECATED " + + "SYSRES_CONST_USER_TYPE_FIELD_VALUE_USER " + + "SYSRES_CONST_USER_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_USERS_CONTROLLER_REQUISITE_CODE " + + "SYSRES_CONST_USERS_IS_MAIN_SERVER_REQUISITE_CODE " + + "SYSRES_CONST_USERS_REFERENCE_CODE " + + "SYSRES_CONST_USERS_REGISTRATION_CERTIFICATES_ACTION_NAME " + + "SYSRES_CONST_USERS_REQUISITE_CODE " + + "SYSRES_CONST_USERS_SYSTEM_REQUISITE_CODE " + + "SYSRES_CONST_USERS_USER_ACCESS_RIGHTS_TYPR_REQUISITE_CODE " + + "SYSRES_CONST_USERS_USER_AUTHENTICATION_REQUISITE_CODE " + + "SYSRES_CONST_USERS_USER_COMPONENT_REQUISITE_CODE " + + "SYSRES_CONST_USERS_USER_GROUP_REQUISITE_CODE " + + "SYSRES_CONST_USERS_VIEW_CERTIFICATES_ACTION_NAME " + + "SYSRES_CONST_VIEW_DEFAULT_CODE " + + "SYSRES_CONST_VIEW_DEFAULT_NAME " + + "SYSRES_CONST_VIEWER_REQUISITE_CODE " + + "SYSRES_CONST_WAITING_BLOCK_DESCRIPTION " + + "SYSRES_CONST_WIZARD_FORM_LABEL_TEST_STRING " + + "SYSRES_CONST_WIZARD_QUERY_PARAM_HEIGHT_ETALON_STRING " + + "SYSRES_CONST_WIZARD_REFERENCE_COMMENT_REQUISITE_CODE " + + "SYSRES_CONST_WORK_RULES_DESCRIPTION_REQUISITE_CODE " + + "SYSRES_CONST_WORK_TIME_CALENDAR_REFERENCE_CODE " + + "SYSRES_CONST_WORK_WORKFLOW_HARD_ROUTE_TYPE_VALUE " + + "SYSRES_CONST_WORK_WORKFLOW_HARD_ROUTE_TYPE_VALUE_CODE " + + "SYSRES_CONST_WORK_WORKFLOW_HARD_ROUTE_TYPE_VALUE_CODE_RUS " + + "SYSRES_CONST_WORK_WORKFLOW_SOFT_ROUTE_TYPE_VALUE_CODE_RUS " + + "SYSRES_CONST_WORKFLOW_ROUTE_TYPR_HARD " + + "SYSRES_CONST_WORKFLOW_ROUTE_TYPR_SOFT " + + "SYSRES_CONST_XML_ENCODING " + + "SYSRES_CONST_XREC_STAT_REQUISITE_CODE " + + "SYSRES_CONST_XRECID_FIELD_NAME " + + "SYSRES_CONST_YES " + + "SYSRES_CONST_YES_NO_2_REQUISITE_CODE " + + "SYSRES_CONST_YES_NO_REQUISITE_CODE " + + "SYSRES_CONST_YES_NO_T_REF_TYPE_REQUISITE_CODE " + + "SYSRES_CONST_YES_PICK_VALUE " + + "SYSRES_CONST_YES_VALUE "; + + // Base constant + const base_constants = "CR FALSE nil NO_VALUE NULL TAB TRUE YES_VALUE "; + + // Base group name + const base_group_name_constants = + "ADMINISTRATORS_GROUP_NAME CUSTOMIZERS_GROUP_NAME DEVELOPERS_GROUP_NAME SERVICE_USERS_GROUP_NAME "; + + // Decision block properties + const decision_block_properties_constants = + "DECISION_BLOCK_FIRST_OPERAND_PROPERTY DECISION_BLOCK_NAME_PROPERTY DECISION_BLOCK_OPERATION_PROPERTY " + + "DECISION_BLOCK_RESULT_TYPE_PROPERTY DECISION_BLOCK_SECOND_OPERAND_PROPERTY "; + + // File extension + const file_extension_constants = + "ANY_FILE_EXTENTION COMPRESSED_DOCUMENT_EXTENSION EXTENDED_DOCUMENT_EXTENSION " + + "SHORT_COMPRESSED_DOCUMENT_EXTENSION SHORT_EXTENDED_DOCUMENT_EXTENSION "; + + // Job block properties + const job_block_properties_constants = + "JOB_BLOCK_ABORT_DEADLINE_PROPERTY " + + "JOB_BLOCK_AFTER_FINISH_EVENT " + + "JOB_BLOCK_AFTER_QUERY_PARAMETERS_EVENT " + + "JOB_BLOCK_ATTACHMENT_PROPERTY " + + "JOB_BLOCK_ATTACHMENTS_RIGHTS_GROUP_PROPERTY " + + "JOB_BLOCK_ATTACHMENTS_RIGHTS_TYPE_PROPERTY " + + "JOB_BLOCK_BEFORE_QUERY_PARAMETERS_EVENT " + + "JOB_BLOCK_BEFORE_START_EVENT " + + "JOB_BLOCK_CREATED_JOBS_PROPERTY " + + "JOB_BLOCK_DEADLINE_PROPERTY " + + "JOB_BLOCK_EXECUTION_RESULTS_PROPERTY " + + "JOB_BLOCK_IS_PARALLEL_PROPERTY " + + "JOB_BLOCK_IS_RELATIVE_ABORT_DEADLINE_PROPERTY " + + "JOB_BLOCK_IS_RELATIVE_DEADLINE_PROPERTY " + + "JOB_BLOCK_JOB_TEXT_PROPERTY " + + "JOB_BLOCK_NAME_PROPERTY " + + "JOB_BLOCK_NEED_SIGN_ON_PERFORM_PROPERTY " + + "JOB_BLOCK_PERFORMER_PROPERTY " + + "JOB_BLOCK_RELATIVE_ABORT_DEADLINE_TYPE_PROPERTY " + + "JOB_BLOCK_RELATIVE_DEADLINE_TYPE_PROPERTY " + + "JOB_BLOCK_SUBJECT_PROPERTY "; + + // Language code + const language_code_constants = "ENGLISH_LANGUAGE_CODE RUSSIAN_LANGUAGE_CODE "; + + // Launching external applications + const launching_external_applications_constants = + "smHidden smMaximized smMinimized smNormal wmNo wmYes "; + + // Link kind + const link_kind_constants = + "COMPONENT_TOKEN_LINK_KIND " + + "DOCUMENT_LINK_KIND " + + "EDOCUMENT_LINK_KIND " + + "FOLDER_LINK_KIND " + + "JOB_LINK_KIND " + + "REFERENCE_LINK_KIND " + + "TASK_LINK_KIND "; + + // Lock type + const lock_type_constants = + "COMPONENT_TOKEN_LOCK_TYPE EDOCUMENT_VERSION_LOCK_TYPE "; + + // Monitor block properties + const monitor_block_properties_constants = + "MONITOR_BLOCK_AFTER_FINISH_EVENT " + + "MONITOR_BLOCK_BEFORE_START_EVENT " + + "MONITOR_BLOCK_DEADLINE_PROPERTY " + + "MONITOR_BLOCK_INTERVAL_PROPERTY " + + "MONITOR_BLOCK_INTERVAL_TYPE_PROPERTY " + + "MONITOR_BLOCK_IS_RELATIVE_DEADLINE_PROPERTY " + + "MONITOR_BLOCK_NAME_PROPERTY " + + "MONITOR_BLOCK_RELATIVE_DEADLINE_TYPE_PROPERTY " + + "MONITOR_BLOCK_SEARCH_SCRIPT_PROPERTY "; + + // Notice block properties + const notice_block_properties_constants = + "NOTICE_BLOCK_AFTER_FINISH_EVENT " + + "NOTICE_BLOCK_ATTACHMENT_PROPERTY " + + "NOTICE_BLOCK_ATTACHMENTS_RIGHTS_GROUP_PROPERTY " + + "NOTICE_BLOCK_ATTACHMENTS_RIGHTS_TYPE_PROPERTY " + + "NOTICE_BLOCK_BEFORE_START_EVENT " + + "NOTICE_BLOCK_CREATED_NOTICES_PROPERTY " + + "NOTICE_BLOCK_DEADLINE_PROPERTY " + + "NOTICE_BLOCK_IS_RELATIVE_DEADLINE_PROPERTY " + + "NOTICE_BLOCK_NAME_PROPERTY " + + "NOTICE_BLOCK_NOTICE_TEXT_PROPERTY " + + "NOTICE_BLOCK_PERFORMER_PROPERTY " + + "NOTICE_BLOCK_RELATIVE_DEADLINE_TYPE_PROPERTY " + + "NOTICE_BLOCK_SUBJECT_PROPERTY "; + + // Object events + const object_events_constants = + "dseAfterCancel " + + "dseAfterClose " + + "dseAfterDelete " + + "dseAfterDeleteOutOfTransaction " + + "dseAfterInsert " + + "dseAfterOpen " + + "dseAfterScroll " + + "dseAfterUpdate " + + "dseAfterUpdateOutOfTransaction " + + "dseBeforeCancel " + + "dseBeforeClose " + + "dseBeforeDelete " + + "dseBeforeDetailUpdate " + + "dseBeforeInsert " + + "dseBeforeOpen " + + "dseBeforeUpdate " + + "dseOnAnyRequisiteChange " + + "dseOnCloseRecord " + + "dseOnDeleteError " + + "dseOnOpenRecord " + + "dseOnPrepareUpdate " + + "dseOnUpdateError " + + "dseOnUpdateRatifiedRecord " + + "dseOnValidDelete " + + "dseOnValidUpdate " + + "reOnChange " + + "reOnChangeValues " + + "SELECTION_BEGIN_ROUTE_EVENT " + + "SELECTION_END_ROUTE_EVENT "; + + // Object params + const object_params_constants = + "CURRENT_PERIOD_IS_REQUIRED " + + "PREVIOUS_CARD_TYPE_NAME " + + "SHOW_RECORD_PROPERTIES_FORM "; + + // Other + const other_constants = + "ACCESS_RIGHTS_SETTING_DIALOG_CODE " + + "ADMINISTRATOR_USER_CODE " + + "ANALYTIC_REPORT_TYPE " + + "asrtHideLocal " + + "asrtHideRemote " + + "CALCULATED_ROLE_TYPE_CODE " + + "COMPONENTS_REFERENCE_DEVELOPER_VIEW_CODE " + + "DCTS_TEST_PROTOCOLS_FOLDER_PATH " + + "E_EDOC_VERSION_ALREADY_APPROVINGLY_SIGNED " + + "E_EDOC_VERSION_ALREADY_APPROVINGLY_SIGNED_BY_USER " + + "E_EDOC_VERSION_ALREDY_SIGNED " + + "E_EDOC_VERSION_ALREDY_SIGNED_BY_USER " + + "EDOC_TYPES_CODE_REQUISITE_FIELD_NAME " + + "EDOCUMENTS_ALIAS_NAME " + + "FILES_FOLDER_PATH " + + "FILTER_OPERANDS_DELIMITER " + + "FILTER_OPERATIONS_DELIMITER " + + "FORMCARD_NAME " + + "FORMLIST_NAME " + + "GET_EXTENDED_DOCUMENT_EXTENSION_CREATION_MODE " + + "GET_EXTENDED_DOCUMENT_EXTENSION_IMPORT_MODE " + + "INTEGRATED_REPORT_TYPE " + + "IS_BUILDER_APPLICATION_ROLE " + + "IS_BUILDER_APPLICATION_ROLE2 " + + "IS_BUILDER_USERS " + + "ISBSYSDEV " + + "LOG_FOLDER_PATH " + + "mbCancel " + + "mbNo " + + "mbNoToAll " + + "mbOK " + + "mbYes " + + "mbYesToAll " + + "MEMORY_DATASET_DESRIPTIONS_FILENAME " + + "mrNo " + + "mrNoToAll " + + "mrYes " + + "mrYesToAll " + + "MULTIPLE_SELECT_DIALOG_CODE " + + "NONOPERATING_RECORD_FLAG_FEMININE " + + "NONOPERATING_RECORD_FLAG_MASCULINE " + + "OPERATING_RECORD_FLAG_FEMININE " + + "OPERATING_RECORD_FLAG_MASCULINE " + + "PROFILING_SETTINGS_COMMON_SETTINGS_CODE_VALUE " + + "PROGRAM_INITIATED_LOOKUP_ACTION " + + "ratDelete " + + "ratEdit " + + "ratInsert " + + "REPORT_TYPE " + + "REQUIRED_PICK_VALUES_VARIABLE " + + "rmCard " + + "rmList " + + "SBRTE_PROGID_DEV " + + "SBRTE_PROGID_RELEASE " + + "STATIC_ROLE_TYPE_CODE " + + "SUPPRESS_EMPTY_TEMPLATE_CREATION " + + "SYSTEM_USER_CODE " + + "UPDATE_DIALOG_DATASET " + + "USED_IN_OBJECT_HINT_PARAM " + + "USER_INITIATED_LOOKUP_ACTION " + + "USER_NAME_FORMAT " + + "USER_SELECTION_RESTRICTIONS " + + "WORKFLOW_TEST_PROTOCOLS_FOLDER_PATH " + + "ELS_SUBTYPE_CONTROL_NAME " + + "ELS_FOLDER_KIND_CONTROL_NAME " + + "REPEAT_PROCESS_CURRENT_OBJECT_EXCEPTION_NAME "; + + // Privileges + const privileges_constants = + "PRIVILEGE_COMPONENT_FULL_ACCESS " + + "PRIVILEGE_DEVELOPMENT_EXPORT " + + "PRIVILEGE_DEVELOPMENT_IMPORT " + + "PRIVILEGE_DOCUMENT_DELETE " + + "PRIVILEGE_ESD " + + "PRIVILEGE_FOLDER_DELETE " + + "PRIVILEGE_MANAGE_ACCESS_RIGHTS " + + "PRIVILEGE_MANAGE_REPLICATION " + + "PRIVILEGE_MANAGE_SESSION_SERVER " + + "PRIVILEGE_OBJECT_FULL_ACCESS " + + "PRIVILEGE_OBJECT_VIEW " + + "PRIVILEGE_RESERVE_LICENSE " + + "PRIVILEGE_SYSTEM_CUSTOMIZE " + + "PRIVILEGE_SYSTEM_DEVELOP " + + "PRIVILEGE_SYSTEM_INSTALL " + + "PRIVILEGE_TASK_DELETE " + + "PRIVILEGE_USER_PLUGIN_SETTINGS_CUSTOMIZE " + + "PRIVILEGES_PSEUDOREFERENCE_CODE "; + + // Pseudoreference code + const pseudoreference_code_constants = + "ACCESS_TYPES_PSEUDOREFERENCE_CODE " + + "ALL_AVAILABLE_COMPONENTS_PSEUDOREFERENCE_CODE " + + "ALL_AVAILABLE_PRIVILEGES_PSEUDOREFERENCE_CODE " + + "ALL_REPLICATE_COMPONENTS_PSEUDOREFERENCE_CODE " + + "AVAILABLE_DEVELOPERS_COMPONENTS_PSEUDOREFERENCE_CODE " + + "COMPONENTS_PSEUDOREFERENCE_CODE " + + "FILTRATER_SETTINGS_CONFLICTS_PSEUDOREFERENCE_CODE " + + "GROUPS_PSEUDOREFERENCE_CODE " + + "RECEIVE_PROTOCOL_PSEUDOREFERENCE_CODE " + + "REFERENCE_REQUISITE_PSEUDOREFERENCE_CODE " + + "REFERENCE_REQUISITES_PSEUDOREFERENCE_CODE " + + "REFTYPES_PSEUDOREFERENCE_CODE " + + "REPLICATION_SEANCES_DIARY_PSEUDOREFERENCE_CODE " + + "SEND_PROTOCOL_PSEUDOREFERENCE_CODE " + + "SUBSTITUTES_PSEUDOREFERENCE_CODE " + + "SYSTEM_SETTINGS_PSEUDOREFERENCE_CODE " + + "UNITS_PSEUDOREFERENCE_CODE " + + "USERS_PSEUDOREFERENCE_CODE " + + "VIEWERS_PSEUDOREFERENCE_CODE "; + + // Requisite ISBCertificateType values + const requisite_ISBCertificateType_values_constants = + "CERTIFICATE_TYPE_ENCRYPT " + + "CERTIFICATE_TYPE_SIGN " + + "CERTIFICATE_TYPE_SIGN_AND_ENCRYPT "; + + // Requisite ISBEDocStorageType values + const requisite_ISBEDocStorageType_values_constants = + "STORAGE_TYPE_FILE " + + "STORAGE_TYPE_NAS_CIFS " + + "STORAGE_TYPE_SAPERION " + + "STORAGE_TYPE_SQL_SERVER "; + + // Requisite CompType2 values + const requisite_compType2_values_constants = + "COMPTYPE2_REQUISITE_DOCUMENTS_VALUE " + + "COMPTYPE2_REQUISITE_TASKS_VALUE " + + "COMPTYPE2_REQUISITE_FOLDERS_VALUE " + + "COMPTYPE2_REQUISITE_REFERENCES_VALUE "; + + // Requisite name + const requisite_name_constants = + "SYSREQ_CODE " + + "SYSREQ_COMPTYPE2 " + + "SYSREQ_CONST_AVAILABLE_FOR_WEB " + + "SYSREQ_CONST_COMMON_CODE " + + "SYSREQ_CONST_COMMON_VALUE " + + "SYSREQ_CONST_FIRM_CODE " + + "SYSREQ_CONST_FIRM_STATUS " + + "SYSREQ_CONST_FIRM_VALUE " + + "SYSREQ_CONST_SERVER_STATUS " + + "SYSREQ_CONTENTS " + + "SYSREQ_DATE_OPEN " + + "SYSREQ_DATE_CLOSE " + + "SYSREQ_DESCRIPTION " + + "SYSREQ_DESCRIPTION_LOCALIZE_ID " + + "SYSREQ_DOUBLE " + + "SYSREQ_EDOC_ACCESS_TYPE " + + "SYSREQ_EDOC_AUTHOR " + + "SYSREQ_EDOC_CREATED " + + "SYSREQ_EDOC_DELEGATE_RIGHTS_REQUISITE_CODE " + + "SYSREQ_EDOC_EDITOR " + + "SYSREQ_EDOC_ENCODE_TYPE " + + "SYSREQ_EDOC_ENCRYPTION_PLUGIN_NAME " + + "SYSREQ_EDOC_ENCRYPTION_PLUGIN_VERSION " + + "SYSREQ_EDOC_EXPORT_DATE " + + "SYSREQ_EDOC_EXPORTER " + + "SYSREQ_EDOC_KIND " + + "SYSREQ_EDOC_LIFE_STAGE_NAME " + + "SYSREQ_EDOC_LOCKED_FOR_SERVER_CODE " + + "SYSREQ_EDOC_MODIFIED " + + "SYSREQ_EDOC_NAME " + + "SYSREQ_EDOC_NOTE " + + "SYSREQ_EDOC_QUALIFIED_ID " + + "SYSREQ_EDOC_SESSION_KEY " + + "SYSREQ_EDOC_SESSION_KEY_ENCRYPTION_PLUGIN_NAME " + + "SYSREQ_EDOC_SESSION_KEY_ENCRYPTION_PLUGIN_VERSION " + + "SYSREQ_EDOC_SIGNATURE_TYPE " + + "SYSREQ_EDOC_SIGNED " + + "SYSREQ_EDOC_STORAGE " + + "SYSREQ_EDOC_STORAGES_ARCHIVE_STORAGE " + + "SYSREQ_EDOC_STORAGES_CHECK_RIGHTS " + + "SYSREQ_EDOC_STORAGES_COMPUTER_NAME " + + "SYSREQ_EDOC_STORAGES_EDIT_IN_STORAGE " + + "SYSREQ_EDOC_STORAGES_EXECUTIVE_STORAGE " + + "SYSREQ_EDOC_STORAGES_FUNCTION " + + "SYSREQ_EDOC_STORAGES_INITIALIZED " + + "SYSREQ_EDOC_STORAGES_LOCAL_PATH " + + "SYSREQ_EDOC_STORAGES_SAPERION_DATABASE_NAME " + + "SYSREQ_EDOC_STORAGES_SEARCH_BY_TEXT " + + "SYSREQ_EDOC_STORAGES_SERVER_NAME " + + "SYSREQ_EDOC_STORAGES_SHARED_SOURCE_NAME " + + "SYSREQ_EDOC_STORAGES_TYPE " + + "SYSREQ_EDOC_TEXT_MODIFIED " + + "SYSREQ_EDOC_TYPE_ACT_CODE " + + "SYSREQ_EDOC_TYPE_ACT_DESCRIPTION " + + "SYSREQ_EDOC_TYPE_ACT_DESCRIPTION_LOCALIZE_ID " + + "SYSREQ_EDOC_TYPE_ACT_ON_EXECUTE " + + "SYSREQ_EDOC_TYPE_ACT_ON_EXECUTE_EXISTS " + + "SYSREQ_EDOC_TYPE_ACT_SECTION " + + "SYSREQ_EDOC_TYPE_ADD_PARAMS " + + "SYSREQ_EDOC_TYPE_COMMENT " + + "SYSREQ_EDOC_TYPE_EVENT_TEXT " + + "SYSREQ_EDOC_TYPE_NAME_IN_SINGULAR " + + "SYSREQ_EDOC_TYPE_NAME_IN_SINGULAR_LOCALIZE_ID " + + "SYSREQ_EDOC_TYPE_NAME_LOCALIZE_ID " + + "SYSREQ_EDOC_TYPE_NUMERATION_METHOD " + + "SYSREQ_EDOC_TYPE_PSEUDO_REQUISITE_CODE " + + "SYSREQ_EDOC_TYPE_REQ_CODE " + + "SYSREQ_EDOC_TYPE_REQ_DESCRIPTION " + + "SYSREQ_EDOC_TYPE_REQ_DESCRIPTION_LOCALIZE_ID " + + "SYSREQ_EDOC_TYPE_REQ_IS_LEADING " + + "SYSREQ_EDOC_TYPE_REQ_IS_REQUIRED " + + "SYSREQ_EDOC_TYPE_REQ_NUMBER " + + "SYSREQ_EDOC_TYPE_REQ_ON_CHANGE " + + "SYSREQ_EDOC_TYPE_REQ_ON_CHANGE_EXISTS " + + "SYSREQ_EDOC_TYPE_REQ_ON_SELECT " + + "SYSREQ_EDOC_TYPE_REQ_ON_SELECT_KIND " + + "SYSREQ_EDOC_TYPE_REQ_SECTION " + + "SYSREQ_EDOC_TYPE_VIEW_CARD " + + "SYSREQ_EDOC_TYPE_VIEW_CODE " + + "SYSREQ_EDOC_TYPE_VIEW_COMMENT " + + "SYSREQ_EDOC_TYPE_VIEW_IS_MAIN " + + "SYSREQ_EDOC_TYPE_VIEW_NAME " + + "SYSREQ_EDOC_TYPE_VIEW_NAME_LOCALIZE_ID " + + "SYSREQ_EDOC_VERSION_AUTHOR " + + "SYSREQ_EDOC_VERSION_CRC " + + "SYSREQ_EDOC_VERSION_DATA " + + "SYSREQ_EDOC_VERSION_EDITOR " + + "SYSREQ_EDOC_VERSION_EXPORT_DATE " + + "SYSREQ_EDOC_VERSION_EXPORTER " + + "SYSREQ_EDOC_VERSION_HIDDEN " + + "SYSREQ_EDOC_VERSION_LIFE_STAGE " + + "SYSREQ_EDOC_VERSION_MODIFIED " + + "SYSREQ_EDOC_VERSION_NOTE " + + "SYSREQ_EDOC_VERSION_SIGNATURE_TYPE " + + "SYSREQ_EDOC_VERSION_SIGNED " + + "SYSREQ_EDOC_VERSION_SIZE " + + "SYSREQ_EDOC_VERSION_SOURCE " + + "SYSREQ_EDOC_VERSION_TEXT_MODIFIED " + + "SYSREQ_EDOCKIND_DEFAULT_VERSION_STATE_CODE " + + "SYSREQ_FOLDER_KIND " + + "SYSREQ_FUNC_CATEGORY " + + "SYSREQ_FUNC_COMMENT " + + "SYSREQ_FUNC_GROUP " + + "SYSREQ_FUNC_GROUP_COMMENT " + + "SYSREQ_FUNC_GROUP_NUMBER " + + "SYSREQ_FUNC_HELP " + + "SYSREQ_FUNC_PARAM_DEF_VALUE " + + "SYSREQ_FUNC_PARAM_IDENT " + + "SYSREQ_FUNC_PARAM_NUMBER " + + "SYSREQ_FUNC_PARAM_TYPE " + + "SYSREQ_FUNC_TEXT " + + "SYSREQ_GROUP_CATEGORY " + + "SYSREQ_ID " + + "SYSREQ_LAST_UPDATE " + + "SYSREQ_LEADER_REFERENCE " + + "SYSREQ_LINE_NUMBER " + + "SYSREQ_MAIN_RECORD_ID " + + "SYSREQ_NAME " + + "SYSREQ_NAME_LOCALIZE_ID " + + "SYSREQ_NOTE " + + "SYSREQ_ORIGINAL_RECORD " + + "SYSREQ_OUR_FIRM " + + "SYSREQ_PROFILING_SETTINGS_BATCH_LOGING " + + "SYSREQ_PROFILING_SETTINGS_BATCH_SIZE " + + "SYSREQ_PROFILING_SETTINGS_PROFILING_ENABLED " + + "SYSREQ_PROFILING_SETTINGS_SQL_PROFILING_ENABLED " + + "SYSREQ_PROFILING_SETTINGS_START_LOGGED " + + "SYSREQ_RECORD_STATUS " + + "SYSREQ_REF_REQ_FIELD_NAME " + + "SYSREQ_REF_REQ_FORMAT " + + "SYSREQ_REF_REQ_GENERATED " + + "SYSREQ_REF_REQ_LENGTH " + + "SYSREQ_REF_REQ_PRECISION " + + "SYSREQ_REF_REQ_REFERENCE " + + "SYSREQ_REF_REQ_SECTION " + + "SYSREQ_REF_REQ_STORED " + + "SYSREQ_REF_REQ_TOKENS " + + "SYSREQ_REF_REQ_TYPE " + + "SYSREQ_REF_REQ_VIEW " + + "SYSREQ_REF_TYPE_ACT_CODE " + + "SYSREQ_REF_TYPE_ACT_DESCRIPTION " + + "SYSREQ_REF_TYPE_ACT_DESCRIPTION_LOCALIZE_ID " + + "SYSREQ_REF_TYPE_ACT_ON_EXECUTE " + + "SYSREQ_REF_TYPE_ACT_ON_EXECUTE_EXISTS " + + "SYSREQ_REF_TYPE_ACT_SECTION " + + "SYSREQ_REF_TYPE_ADD_PARAMS " + + "SYSREQ_REF_TYPE_COMMENT " + + "SYSREQ_REF_TYPE_COMMON_SETTINGS " + + "SYSREQ_REF_TYPE_DISPLAY_REQUISITE_NAME " + + "SYSREQ_REF_TYPE_EVENT_TEXT " + + "SYSREQ_REF_TYPE_MAIN_LEADING_REF " + + "SYSREQ_REF_TYPE_NAME_IN_SINGULAR " + + "SYSREQ_REF_TYPE_NAME_IN_SINGULAR_LOCALIZE_ID " + + "SYSREQ_REF_TYPE_NAME_LOCALIZE_ID " + + "SYSREQ_REF_TYPE_NUMERATION_METHOD " + + "SYSREQ_REF_TYPE_REQ_CODE " + + "SYSREQ_REF_TYPE_REQ_DESCRIPTION " + + "SYSREQ_REF_TYPE_REQ_DESCRIPTION_LOCALIZE_ID " + + "SYSREQ_REF_TYPE_REQ_IS_CONTROL " + + "SYSREQ_REF_TYPE_REQ_IS_FILTER " + + "SYSREQ_REF_TYPE_REQ_IS_LEADING " + + "SYSREQ_REF_TYPE_REQ_IS_REQUIRED " + + "SYSREQ_REF_TYPE_REQ_NUMBER " + + "SYSREQ_REF_TYPE_REQ_ON_CHANGE " + + "SYSREQ_REF_TYPE_REQ_ON_CHANGE_EXISTS " + + "SYSREQ_REF_TYPE_REQ_ON_SELECT " + + "SYSREQ_REF_TYPE_REQ_ON_SELECT_KIND " + + "SYSREQ_REF_TYPE_REQ_SECTION " + + "SYSREQ_REF_TYPE_VIEW_CARD " + + "SYSREQ_REF_TYPE_VIEW_CODE " + + "SYSREQ_REF_TYPE_VIEW_COMMENT " + + "SYSREQ_REF_TYPE_VIEW_IS_MAIN " + + "SYSREQ_REF_TYPE_VIEW_NAME " + + "SYSREQ_REF_TYPE_VIEW_NAME_LOCALIZE_ID " + + "SYSREQ_REFERENCE_TYPE_ID " + + "SYSREQ_STATE " + + "SYSREQ_STATЕ " + + "SYSREQ_SYSTEM_SETTINGS_VALUE " + + "SYSREQ_TYPE " + + "SYSREQ_UNIT " + + "SYSREQ_UNIT_ID " + + "SYSREQ_USER_GROUPS_GROUP_FULL_NAME " + + "SYSREQ_USER_GROUPS_GROUP_NAME " + + "SYSREQ_USER_GROUPS_GROUP_SERVER_NAME " + + "SYSREQ_USERS_ACCESS_RIGHTS " + + "SYSREQ_USERS_AUTHENTICATION " + + "SYSREQ_USERS_CATEGORY " + + "SYSREQ_USERS_COMPONENT " + + "SYSREQ_USERS_COMPONENT_USER_IS_PUBLIC " + + "SYSREQ_USERS_DOMAIN " + + "SYSREQ_USERS_FULL_USER_NAME " + + "SYSREQ_USERS_GROUP " + + "SYSREQ_USERS_IS_MAIN_SERVER " + + "SYSREQ_USERS_LOGIN " + + "SYSREQ_USERS_REFERENCE_USER_IS_PUBLIC " + + "SYSREQ_USERS_STATUS " + + "SYSREQ_USERS_USER_CERTIFICATE " + + "SYSREQ_USERS_USER_CERTIFICATE_INFO " + + "SYSREQ_USERS_USER_CERTIFICATE_PLUGIN_NAME " + + "SYSREQ_USERS_USER_CERTIFICATE_PLUGIN_VERSION " + + "SYSREQ_USERS_USER_CERTIFICATE_STATE " + + "SYSREQ_USERS_USER_CERTIFICATE_SUBJECT_NAME " + + "SYSREQ_USERS_USER_CERTIFICATE_THUMBPRINT " + + "SYSREQ_USERS_USER_DEFAULT_CERTIFICATE " + + "SYSREQ_USERS_USER_DESCRIPTION " + + "SYSREQ_USERS_USER_GLOBAL_NAME " + + "SYSREQ_USERS_USER_LOGIN " + + "SYSREQ_USERS_USER_MAIN_SERVER " + + "SYSREQ_USERS_USER_TYPE " + + "SYSREQ_WORK_RULES_FOLDER_ID "; + + // Result + const result_constants = "RESULT_VAR_NAME RESULT_VAR_NAME_ENG "; + + // Rule identification + const rule_identification_constants = + "AUTO_NUMERATION_RULE_ID " + + "CANT_CHANGE_ID_REQUISITE_RULE_ID " + + "CANT_CHANGE_OURFIRM_REQUISITE_RULE_ID " + + "CHECK_CHANGING_REFERENCE_RECORD_USE_RULE_ID " + + "CHECK_CODE_REQUISITE_RULE_ID " + + "CHECK_DELETING_REFERENCE_RECORD_USE_RULE_ID " + + "CHECK_FILTRATER_CHANGES_RULE_ID " + + "CHECK_RECORD_INTERVAL_RULE_ID " + + "CHECK_REFERENCE_INTERVAL_RULE_ID " + + "CHECK_REQUIRED_DATA_FULLNESS_RULE_ID " + + "CHECK_REQUIRED_REQUISITES_FULLNESS_RULE_ID " + + "MAKE_RECORD_UNRATIFIED_RULE_ID " + + "RESTORE_AUTO_NUMERATION_RULE_ID " + + "SET_FIRM_CONTEXT_FROM_RECORD_RULE_ID " + + "SET_FIRST_RECORD_IN_LIST_FORM_RULE_ID " + + "SET_IDSPS_VALUE_RULE_ID " + + "SET_NEXT_CODE_VALUE_RULE_ID " + + "SET_OURFIRM_BOUNDS_RULE_ID " + + "SET_OURFIRM_REQUISITE_RULE_ID "; + + // Script block properties + const script_block_properties_constants = + "SCRIPT_BLOCK_AFTER_FINISH_EVENT " + + "SCRIPT_BLOCK_BEFORE_START_EVENT " + + "SCRIPT_BLOCK_EXECUTION_RESULTS_PROPERTY " + + "SCRIPT_BLOCK_NAME_PROPERTY " + + "SCRIPT_BLOCK_SCRIPT_PROPERTY "; + + // Subtask block properties + const subtask_block_properties_constants = + "SUBTASK_BLOCK_ABORT_DEADLINE_PROPERTY " + + "SUBTASK_BLOCK_AFTER_FINISH_EVENT " + + "SUBTASK_BLOCK_ASSIGN_PARAMS_EVENT " + + "SUBTASK_BLOCK_ATTACHMENTS_PROPERTY " + + "SUBTASK_BLOCK_ATTACHMENTS_RIGHTS_GROUP_PROPERTY " + + "SUBTASK_BLOCK_ATTACHMENTS_RIGHTS_TYPE_PROPERTY " + + "SUBTASK_BLOCK_BEFORE_START_EVENT " + + "SUBTASK_BLOCK_CREATED_TASK_PROPERTY " + + "SUBTASK_BLOCK_CREATION_EVENT " + + "SUBTASK_BLOCK_DEADLINE_PROPERTY " + + "SUBTASK_BLOCK_IMPORTANCE_PROPERTY " + + "SUBTASK_BLOCK_INITIATOR_PROPERTY " + + "SUBTASK_BLOCK_IS_RELATIVE_ABORT_DEADLINE_PROPERTY " + + "SUBTASK_BLOCK_IS_RELATIVE_DEADLINE_PROPERTY " + + "SUBTASK_BLOCK_JOBS_TYPE_PROPERTY " + + "SUBTASK_BLOCK_NAME_PROPERTY " + + "SUBTASK_BLOCK_PARALLEL_ROUTE_PROPERTY " + + "SUBTASK_BLOCK_PERFORMERS_PROPERTY " + + "SUBTASK_BLOCK_RELATIVE_ABORT_DEADLINE_TYPE_PROPERTY " + + "SUBTASK_BLOCK_RELATIVE_DEADLINE_TYPE_PROPERTY " + + "SUBTASK_BLOCK_REQUIRE_SIGN_PROPERTY " + + "SUBTASK_BLOCK_STANDARD_ROUTE_PROPERTY " + + "SUBTASK_BLOCK_START_EVENT " + + "SUBTASK_BLOCK_STEP_CONTROL_PROPERTY " + + "SUBTASK_BLOCK_SUBJECT_PROPERTY " + + "SUBTASK_BLOCK_TASK_CONTROL_PROPERTY " + + "SUBTASK_BLOCK_TEXT_PROPERTY " + + "SUBTASK_BLOCK_UNLOCK_ATTACHMENTS_ON_STOP_PROPERTY " + + "SUBTASK_BLOCK_USE_STANDARD_ROUTE_PROPERTY " + + "SUBTASK_BLOCK_WAIT_FOR_TASK_COMPLETE_PROPERTY "; + + // System component + const system_component_constants = + "SYSCOMP_CONTROL_JOBS " + + "SYSCOMP_FOLDERS " + + "SYSCOMP_JOBS " + + "SYSCOMP_NOTICES " + + "SYSCOMP_TASKS "; + + // System dialogs + const system_dialogs_constants = + "SYSDLG_CREATE_EDOCUMENT " + + "SYSDLG_CREATE_EDOCUMENT_VERSION " + + "SYSDLG_CURRENT_PERIOD " + + "SYSDLG_EDIT_FUNCTION_HELP " + + "SYSDLG_EDOCUMENT_KINDS_FOR_TEMPLATE " + + "SYSDLG_EXPORT_MULTIPLE_EDOCUMENTS " + + "SYSDLG_EXPORT_SINGLE_EDOCUMENT " + + "SYSDLG_IMPORT_EDOCUMENT " + + "SYSDLG_MULTIPLE_SELECT " + + "SYSDLG_SETUP_ACCESS_RIGHTS " + + "SYSDLG_SETUP_DEFAULT_RIGHTS " + + "SYSDLG_SETUP_FILTER_CONDITION " + + "SYSDLG_SETUP_SIGN_RIGHTS " + + "SYSDLG_SETUP_TASK_OBSERVERS " + + "SYSDLG_SETUP_TASK_ROUTE " + + "SYSDLG_SETUP_USERS_LIST " + + "SYSDLG_SIGN_EDOCUMENT " + + "SYSDLG_SIGN_MULTIPLE_EDOCUMENTS "; + + // System reference names + const system_reference_names_constants = + "SYSREF_ACCESS_RIGHTS_TYPES " + + "SYSREF_ADMINISTRATION_HISTORY " + + "SYSREF_ALL_AVAILABLE_COMPONENTS " + + "SYSREF_ALL_AVAILABLE_PRIVILEGES " + + "SYSREF_ALL_REPLICATING_COMPONENTS " + + "SYSREF_AVAILABLE_DEVELOPERS_COMPONENTS " + + "SYSREF_CALENDAR_EVENTS " + + "SYSREF_COMPONENT_TOKEN_HISTORY " + + "SYSREF_COMPONENT_TOKENS " + + "SYSREF_COMPONENTS " + + "SYSREF_CONSTANTS " + + "SYSREF_DATA_RECEIVE_PROTOCOL " + + "SYSREF_DATA_SEND_PROTOCOL " + + "SYSREF_DIALOGS " + + "SYSREF_DIALOGS_REQUISITES " + + "SYSREF_EDITORS " + + "SYSREF_EDOC_CARDS " + + "SYSREF_EDOC_TYPES " + + "SYSREF_EDOCUMENT_CARD_REQUISITES " + + "SYSREF_EDOCUMENT_CARD_TYPES " + + "SYSREF_EDOCUMENT_CARD_TYPES_REFERENCE " + + "SYSREF_EDOCUMENT_CARDS " + + "SYSREF_EDOCUMENT_HISTORY " + + "SYSREF_EDOCUMENT_KINDS " + + "SYSREF_EDOCUMENT_REQUISITES " + + "SYSREF_EDOCUMENT_SIGNATURES " + + "SYSREF_EDOCUMENT_TEMPLATES " + + "SYSREF_EDOCUMENT_TEXT_STORAGES " + + "SYSREF_EDOCUMENT_VIEWS " + + "SYSREF_FILTERER_SETUP_CONFLICTS " + + "SYSREF_FILTRATER_SETTING_CONFLICTS " + + "SYSREF_FOLDER_HISTORY " + + "SYSREF_FOLDERS " + + "SYSREF_FUNCTION_GROUPS " + + "SYSREF_FUNCTION_PARAMS " + + "SYSREF_FUNCTIONS " + + "SYSREF_JOB_HISTORY " + + "SYSREF_LINKS " + + "SYSREF_LOCALIZATION_DICTIONARY " + + "SYSREF_LOCALIZATION_LANGUAGES " + + "SYSREF_MODULES " + + "SYSREF_PRIVILEGES " + + "SYSREF_RECORD_HISTORY " + + "SYSREF_REFERENCE_REQUISITES " + + "SYSREF_REFERENCE_TYPE_VIEWS " + + "SYSREF_REFERENCE_TYPES " + + "SYSREF_REFERENCES " + + "SYSREF_REFERENCES_REQUISITES " + + "SYSREF_REMOTE_SERVERS " + + "SYSREF_REPLICATION_SESSIONS_LOG " + + "SYSREF_REPLICATION_SESSIONS_PROTOCOL " + + "SYSREF_REPORTS " + + "SYSREF_ROLES " + + "SYSREF_ROUTE_BLOCK_GROUPS " + + "SYSREF_ROUTE_BLOCKS " + + "SYSREF_SCRIPTS " + + "SYSREF_SEARCHES " + + "SYSREF_SERVER_EVENTS " + + "SYSREF_SERVER_EVENTS_HISTORY " + + "SYSREF_STANDARD_ROUTE_GROUPS " + + "SYSREF_STANDARD_ROUTES " + + "SYSREF_STATUSES " + + "SYSREF_SYSTEM_SETTINGS " + + "SYSREF_TASK_HISTORY " + + "SYSREF_TASK_KIND_GROUPS " + + "SYSREF_TASK_KINDS " + + "SYSREF_TASK_RIGHTS " + + "SYSREF_TASK_SIGNATURES " + + "SYSREF_TASKS " + + "SYSREF_UNITS " + + "SYSREF_USER_GROUPS " + + "SYSREF_USER_GROUPS_REFERENCE " + + "SYSREF_USER_SUBSTITUTION " + + "SYSREF_USERS " + + "SYSREF_USERS_REFERENCE " + + "SYSREF_VIEWERS " + + "SYSREF_WORKING_TIME_CALENDARS "; + + // Table name + const table_name_constants = + "ACCESS_RIGHTS_TABLE_NAME " + + "EDMS_ACCESS_TABLE_NAME " + + "EDOC_TYPES_TABLE_NAME "; + + // Test + const test_constants = + "TEST_DEV_DB_NAME " + + "TEST_DEV_SYSTEM_CODE " + + "TEST_EDMS_DB_NAME " + + "TEST_EDMS_MAIN_CODE " + + "TEST_EDMS_MAIN_DB_NAME " + + "TEST_EDMS_SECOND_CODE " + + "TEST_EDMS_SECOND_DB_NAME " + + "TEST_EDMS_SYSTEM_CODE " + + "TEST_ISB5_MAIN_CODE " + + "TEST_ISB5_SECOND_CODE " + + "TEST_SQL_SERVER_2005_NAME " + + "TEST_SQL_SERVER_NAME "; + + // Using the dialog windows + const using_the_dialog_windows_constants = + "ATTENTION_CAPTION " + + "cbsCommandLinks " + + "cbsDefault " + + "CONFIRMATION_CAPTION " + + "ERROR_CAPTION " + + "INFORMATION_CAPTION " + + "mrCancel " + + "mrOk "; + + // Using the document + const using_the_document_constants = + "EDOC_VERSION_ACTIVE_STAGE_CODE " + + "EDOC_VERSION_DESIGN_STAGE_CODE " + + "EDOC_VERSION_OBSOLETE_STAGE_CODE "; + + // Using the EA and encryption + const using_the_EA_and_encryption_constants = + "cpDataEnciphermentEnabled " + + "cpDigitalSignatureEnabled " + + "cpID " + + "cpIssuer " + + "cpPluginVersion " + + "cpSerial " + + "cpSubjectName " + + "cpSubjSimpleName " + + "cpValidFromDate " + + "cpValidToDate "; + + // Using the ISBL-editor + const using_the_ISBL_editor_constants = + "ISBL_SYNTAX " + "NO_SYNTAX " + "XML_SYNTAX "; + + // Wait block properties + const wait_block_properties_constants = + "WAIT_BLOCK_AFTER_FINISH_EVENT " + + "WAIT_BLOCK_BEFORE_START_EVENT " + + "WAIT_BLOCK_DEADLINE_PROPERTY " + + "WAIT_BLOCK_IS_RELATIVE_DEADLINE_PROPERTY " + + "WAIT_BLOCK_NAME_PROPERTY " + + "WAIT_BLOCK_RELATIVE_DEADLINE_TYPE_PROPERTY "; + + // SYSRES Common + const sysres_common_constants = + "SYSRES_COMMON " + + "SYSRES_CONST " + + "SYSRES_MBFUNC " + + "SYSRES_SBDATA " + + "SYSRES_SBGUI " + + "SYSRES_SBINTF " + + "SYSRES_SBREFDSC " + + "SYSRES_SQLERRORS " + + "SYSRES_SYSCOMP "; + + // Константы ==> built_in + const CONSTANTS = + sysres_constants + + base_constants + + base_group_name_constants + + decision_block_properties_constants + + file_extension_constants + + job_block_properties_constants + + language_code_constants + + launching_external_applications_constants + + link_kind_constants + + lock_type_constants + + monitor_block_properties_constants + + notice_block_properties_constants + + object_events_constants + + object_params_constants + + other_constants + + privileges_constants + + pseudoreference_code_constants + + requisite_ISBCertificateType_values_constants + + requisite_ISBEDocStorageType_values_constants + + requisite_compType2_values_constants + + requisite_name_constants + + result_constants + + rule_identification_constants + + script_block_properties_constants + + subtask_block_properties_constants + + system_component_constants + + system_dialogs_constants + + system_reference_names_constants + + table_name_constants + + test_constants + + using_the_dialog_windows_constants + + using_the_document_constants + + using_the_EA_and_encryption_constants + + using_the_ISBL_editor_constants + + wait_block_properties_constants + + sysres_common_constants; + + // enum TAccountType + const TAccountType = "atUser atGroup atRole "; + + // enum TActionEnabledMode + const TActionEnabledMode = + "aemEnabledAlways " + + "aemDisabledAlways " + + "aemEnabledOnBrowse " + + "aemEnabledOnEdit " + + "aemDisabledOnBrowseEmpty "; + + // enum TAddPosition + const TAddPosition = "apBegin apEnd "; + + // enum TAlignment + const TAlignment = "alLeft alRight "; + + // enum TAreaShowMode + const TAreaShowMode = + "asmNever " + + "asmNoButCustomize " + + "asmAsLastTime " + + "asmYesButCustomize " + + "asmAlways "; + + // enum TCertificateInvalidationReason + const TCertificateInvalidationReason = "cirCommon cirRevoked "; + + // enum TCertificateType + const TCertificateType = "ctSignature ctEncode ctSignatureEncode "; + + // enum TCheckListBoxItemState + const TCheckListBoxItemState = "clbUnchecked clbChecked clbGrayed "; + + // enum TCloseOnEsc + const TCloseOnEsc = "ceISB ceAlways ceNever "; + + // enum TCompType + const TCompType = + "ctDocument " + + "ctReference " + + "ctScript " + + "ctUnknown " + + "ctReport " + + "ctDialog " + + "ctFunction " + + "ctFolder " + + "ctEDocument " + + "ctTask " + + "ctJob " + + "ctNotice " + + "ctControlJob "; + + // enum TConditionFormat + const TConditionFormat = "cfInternal cfDisplay "; + + // enum TConnectionIntent + const TConnectionIntent = "ciUnspecified ciWrite ciRead "; + + // enum TContentKind + const TContentKind = + "ckFolder " + + "ckEDocument " + + "ckTask " + + "ckJob " + + "ckComponentToken " + + "ckAny " + + "ckReference " + + "ckScript " + + "ckReport " + + "ckDialog "; + + // enum TControlType + const TControlType = + "ctISBLEditor " + + "ctBevel " + + "ctButton " + + "ctCheckListBox " + + "ctComboBox " + + "ctComboEdit " + + "ctGrid " + + "ctDBCheckBox " + + "ctDBComboBox " + + "ctDBEdit " + + "ctDBEllipsis " + + "ctDBMemo " + + "ctDBNavigator " + + "ctDBRadioGroup " + + "ctDBStatusLabel " + + "ctEdit " + + "ctGroupBox " + + "ctInplaceHint " + + "ctMemo " + + "ctPanel " + + "ctListBox " + + "ctRadioButton " + + "ctRichEdit " + + "ctTabSheet " + + "ctWebBrowser " + + "ctImage " + + "ctHyperLink " + + "ctLabel " + + "ctDBMultiEllipsis " + + "ctRibbon " + + "ctRichView " + + "ctInnerPanel " + + "ctPanelGroup " + + "ctBitButton "; + + // enum TCriterionContentType + const TCriterionContentType = + "cctDate " + + "cctInteger " + + "cctNumeric " + + "cctPick " + + "cctReference " + + "cctString " + + "cctText "; + + // enum TCultureType + const TCultureType = "cltInternal cltPrimary cltGUI "; + + // enum TDataSetEventType + const TDataSetEventType = + "dseBeforeOpen " + + "dseAfterOpen " + + "dseBeforeClose " + + "dseAfterClose " + + "dseOnValidDelete " + + "dseBeforeDelete " + + "dseAfterDelete " + + "dseAfterDeleteOutOfTransaction " + + "dseOnDeleteError " + + "dseBeforeInsert " + + "dseAfterInsert " + + "dseOnValidUpdate " + + "dseBeforeUpdate " + + "dseOnUpdateRatifiedRecord " + + "dseAfterUpdate " + + "dseAfterUpdateOutOfTransaction " + + "dseOnUpdateError " + + "dseAfterScroll " + + "dseOnOpenRecord " + + "dseOnCloseRecord " + + "dseBeforeCancel " + + "dseAfterCancel " + + "dseOnUpdateDeadlockError " + + "dseBeforeDetailUpdate " + + "dseOnPrepareUpdate " + + "dseOnAnyRequisiteChange "; + + // enum TDataSetState + const TDataSetState = "dssEdit dssInsert dssBrowse dssInActive "; + + // enum TDateFormatType + const TDateFormatType = "dftDate dftShortDate dftDateTime dftTimeStamp "; + + // enum TDateOffsetType + const TDateOffsetType = "dotDays dotHours dotMinutes dotSeconds "; + + // enum TDateTimeKind + const TDateTimeKind = "dtkndLocal dtkndUTC "; + + // enum TDeaAccessRights + const TDeaAccessRights = "arNone arView arEdit arFull "; + + // enum TDocumentDefaultAction + const TDocumentDefaultAction = "ddaView ddaEdit "; + + // enum TEditMode + const TEditMode = + "emLock " + + "emEdit " + + "emSign " + + "emExportWithLock " + + "emImportWithUnlock " + + "emChangeVersionNote " + + "emOpenForModify " + + "emChangeLifeStage " + + "emDelete " + + "emCreateVersion " + + "emImport " + + "emUnlockExportedWithLock " + + "emStart " + + "emAbort " + + "emReInit " + + "emMarkAsReaded " + + "emMarkAsUnreaded " + + "emPerform " + + "emAccept " + + "emResume " + + "emChangeRights " + + "emEditRoute " + + "emEditObserver " + + "emRecoveryFromLocalCopy " + + "emChangeWorkAccessType " + + "emChangeEncodeTypeToCertificate " + + "emChangeEncodeTypeToPassword " + + "emChangeEncodeTypeToNone " + + "emChangeEncodeTypeToCertificatePassword " + + "emChangeStandardRoute " + + "emGetText " + + "emOpenForView " + + "emMoveToStorage " + + "emCreateObject " + + "emChangeVersionHidden " + + "emDeleteVersion " + + "emChangeLifeCycleStage " + + "emApprovingSign " + + "emExport " + + "emContinue " + + "emLockFromEdit " + + "emUnLockForEdit " + + "emLockForServer " + + "emUnlockFromServer " + + "emDelegateAccessRights " + + "emReEncode "; + + // enum TEditorCloseObservType + const TEditorCloseObservType = "ecotFile ecotProcess "; + + // enum TEdmsApplicationAction + const TEdmsApplicationAction = "eaGet eaCopy eaCreate eaCreateStandardRoute "; + + // enum TEDocumentLockType + const TEDocumentLockType = "edltAll edltNothing edltQuery "; + + // enum TEDocumentStepShowMode + const TEDocumentStepShowMode = "essmText essmCard "; + + // enum TEDocumentStepVersionType + const TEDocumentStepVersionType = "esvtLast esvtLastActive esvtSpecified "; + + // enum TEDocumentStorageFunction + const TEDocumentStorageFunction = "edsfExecutive edsfArchive "; + + // enum TEDocumentStorageType + const TEDocumentStorageType = "edstSQLServer edstFile "; + + // enum TEDocumentVersionSourceType + const TEDocumentVersionSourceType = + "edvstNone edvstEDocumentVersionCopy edvstFile edvstTemplate edvstScannedFile "; + + // enum TEDocumentVersionState + const TEDocumentVersionState = "vsDefault vsDesign vsActive vsObsolete "; + + // enum TEncodeType + const TEncodeType = "etNone etCertificate etPassword etCertificatePassword "; + + // enum TExceptionCategory + const TExceptionCategory = "ecException ecWarning ecInformation "; + + // enum TExportedSignaturesType + const TExportedSignaturesType = "estAll estApprovingOnly "; + + // enum TExportedVersionType + const TExportedVersionType = "evtLast evtLastActive evtQuery "; + + // enum TFieldDataType + const TFieldDataType = + "fdtString " + + "fdtNumeric " + + "fdtInteger " + + "fdtDate " + + "fdtText " + + "fdtUnknown " + + "fdtWideString " + + "fdtLargeInteger "; + + // enum TFolderType + const TFolderType = + "ftInbox " + + "ftOutbox " + + "ftFavorites " + + "ftCommonFolder " + + "ftUserFolder " + + "ftComponents " + + "ftQuickLaunch " + + "ftShortcuts " + + "ftSearch "; + + // enum TGridRowHeight + const TGridRowHeight = "grhAuto " + "grhX1 " + "grhX2 " + "grhX3 "; + + // enum THyperlinkType + const THyperlinkType = "hltText " + "hltRTF " + "hltHTML "; + + // enum TImageFileFormat + const TImageFileFormat = + "iffBMP " + + "iffJPEG " + + "iffMultiPageTIFF " + + "iffSinglePageTIFF " + + "iffTIFF " + + "iffPNG "; + + // enum TImageMode + const TImageMode = "im8bGrayscale " + "im24bRGB " + "im1bMonochrome "; + + // enum TImageType + const TImageType = "itBMP " + "itJPEG " + "itWMF " + "itPNG "; + + // enum TInplaceHintKind + const TInplaceHintKind = + "ikhInformation " + "ikhWarning " + "ikhError " + "ikhNoIcon "; + + // enum TISBLContext + const TISBLContext = + "icUnknown " + + "icScript " + + "icFunction " + + "icIntegratedReport " + + "icAnalyticReport " + + "icDataSetEventHandler " + + "icActionHandler " + + "icFormEventHandler " + + "icLookUpEventHandler " + + "icRequisiteChangeEventHandler " + + "icBeforeSearchEventHandler " + + "icRoleCalculation " + + "icSelectRouteEventHandler " + + "icBlockPropertyCalculation " + + "icBlockQueryParamsEventHandler " + + "icChangeSearchResultEventHandler " + + "icBlockEventHandler " + + "icSubTaskInitEventHandler " + + "icEDocDataSetEventHandler " + + "icEDocLookUpEventHandler " + + "icEDocActionHandler " + + "icEDocFormEventHandler " + + "icEDocRequisiteChangeEventHandler " + + "icStructuredConversionRule " + + "icStructuredConversionEventBefore " + + "icStructuredConversionEventAfter " + + "icWizardEventHandler " + + "icWizardFinishEventHandler " + + "icWizardStepEventHandler " + + "icWizardStepFinishEventHandler " + + "icWizardActionEnableEventHandler " + + "icWizardActionExecuteEventHandler " + + "icCreateJobsHandler " + + "icCreateNoticesHandler " + + "icBeforeLookUpEventHandler " + + "icAfterLookUpEventHandler " + + "icTaskAbortEventHandler " + + "icWorkflowBlockActionHandler " + + "icDialogDataSetEventHandler " + + "icDialogActionHandler " + + "icDialogLookUpEventHandler " + + "icDialogRequisiteChangeEventHandler " + + "icDialogFormEventHandler " + + "icDialogValidCloseEventHandler " + + "icBlockFormEventHandler " + + "icTaskFormEventHandler " + + "icReferenceMethod " + + "icEDocMethod " + + "icDialogMethod " + + "icProcessMessageHandler "; + + // enum TItemShow + const TItemShow = "isShow " + "isHide " + "isByUserSettings "; + + // enum TJobKind + const TJobKind = "jkJob " + "jkNotice " + "jkControlJob "; + + // enum TJoinType + const TJoinType = "jtInner " + "jtLeft " + "jtRight " + "jtFull " + "jtCross "; + + // enum TLabelPos + const TLabelPos = "lbpAbove " + "lbpBelow " + "lbpLeft " + "lbpRight "; + + // enum TLicensingType + const TLicensingType = "eltPerConnection " + "eltPerUser "; + + // enum TLifeCycleStageFontColor + const TLifeCycleStageFontColor = + "sfcUndefined " + + "sfcBlack " + + "sfcGreen " + + "sfcRed " + + "sfcBlue " + + "sfcOrange " + + "sfcLilac "; + + // enum TLifeCycleStageFontStyle + const TLifeCycleStageFontStyle = "sfsItalic " + "sfsStrikeout " + "sfsNormal "; + + // enum TLockableDevelopmentComponentType + const TLockableDevelopmentComponentType = + "ldctStandardRoute " + + "ldctWizard " + + "ldctScript " + + "ldctFunction " + + "ldctRouteBlock " + + "ldctIntegratedReport " + + "ldctAnalyticReport " + + "ldctReferenceType " + + "ldctEDocumentType " + + "ldctDialog " + + "ldctServerEvents "; + + // enum TMaxRecordCountRestrictionType + const TMaxRecordCountRestrictionType = + "mrcrtNone " + "mrcrtUser " + "mrcrtMaximal " + "mrcrtCustom "; + + // enum TRangeValueType + const TRangeValueType = + "vtEqual " + "vtGreaterOrEqual " + "vtLessOrEqual " + "vtRange "; + + // enum TRelativeDate + const TRelativeDate = + "rdYesterday " + + "rdToday " + + "rdTomorrow " + + "rdThisWeek " + + "rdThisMonth " + + "rdThisYear " + + "rdNextMonth " + + "rdNextWeek " + + "rdLastWeek " + + "rdLastMonth "; + + // enum TReportDestination + const TReportDestination = "rdWindow " + "rdFile " + "rdPrinter "; + + // enum TReqDataType + const TReqDataType = + "rdtString " + + "rdtNumeric " + + "rdtInteger " + + "rdtDate " + + "rdtReference " + + "rdtAccount " + + "rdtText " + + "rdtPick " + + "rdtUnknown " + + "rdtLargeInteger " + + "rdtDocument "; + + // enum TRequisiteEventType + const TRequisiteEventType = "reOnChange " + "reOnChangeValues "; + + // enum TSBTimeType + const TSBTimeType = "ttGlobal " + "ttLocal " + "ttUser " + "ttSystem "; + + // enum TSearchShowMode + const TSearchShowMode = + "ssmBrowse " + "ssmSelect " + "ssmMultiSelect " + "ssmBrowseModal "; + + // enum TSelectMode + const TSelectMode = "smSelect " + "smLike " + "smCard "; + + // enum TSignatureType + const TSignatureType = "stNone " + "stAuthenticating " + "stApproving "; + + // enum TSignerContentType + const TSignerContentType = "sctString " + "sctStream "; + + // enum TStringsSortType + const TStringsSortType = "sstAnsiSort " + "sstNaturalSort "; + + // enum TStringValueType + const TStringValueType = "svtEqual " + "svtContain "; + + // enum TStructuredObjectAttributeType + const TStructuredObjectAttributeType = + "soatString " + + "soatNumeric " + + "soatInteger " + + "soatDatetime " + + "soatReferenceRecord " + + "soatText " + + "soatPick " + + "soatBoolean " + + "soatEDocument " + + "soatAccount " + + "soatIntegerCollection " + + "soatNumericCollection " + + "soatStringCollection " + + "soatPickCollection " + + "soatDatetimeCollection " + + "soatBooleanCollection " + + "soatReferenceRecordCollection " + + "soatEDocumentCollection " + + "soatAccountCollection " + + "soatContents " + + "soatUnknown "; + + // enum TTaskAbortReason + const TTaskAbortReason = "tarAbortByUser " + "tarAbortByWorkflowException "; + + // enum TTextValueType + const TTextValueType = "tvtAllWords " + "tvtExactPhrase " + "tvtAnyWord "; + + // enum TUserObjectStatus + const TUserObjectStatus = + "usNone " + + "usCompleted " + + "usRedSquare " + + "usBlueSquare " + + "usYellowSquare " + + "usGreenSquare " + + "usOrangeSquare " + + "usPurpleSquare " + + "usFollowUp "; + + // enum TUserType + const TUserType = + "utUnknown " + + "utUser " + + "utDeveloper " + + "utAdministrator " + + "utSystemDeveloper " + + "utDisconnected "; + + // enum TValuesBuildType + const TValuesBuildType = + "btAnd " + "btDetailAnd " + "btOr " + "btNotOr " + "btOnly "; + + // enum TViewMode + const TViewMode = "vmView " + "vmSelect " + "vmNavigation "; + + // enum TViewSelectionMode + const TViewSelectionMode = + "vsmSingle " + "vsmMultiple " + "vsmMultipleCheck " + "vsmNoSelection "; + + // enum TWizardActionType + const TWizardActionType = + "wfatPrevious " + "wfatNext " + "wfatCancel " + "wfatFinish "; + + // enum TWizardFormElementProperty + const TWizardFormElementProperty = + "wfepUndefined " + + "wfepText3 " + + "wfepText6 " + + "wfepText9 " + + "wfepSpinEdit " + + "wfepDropDown " + + "wfepRadioGroup " + + "wfepFlag " + + "wfepText12 " + + "wfepText15 " + + "wfepText18 " + + "wfepText21 " + + "wfepText24 " + + "wfepText27 " + + "wfepText30 " + + "wfepRadioGroupColumn1 " + + "wfepRadioGroupColumn2 " + + "wfepRadioGroupColumn3 "; + + // enum TWizardFormElementType + const TWizardFormElementType = + "wfetQueryParameter " + "wfetText " + "wfetDelimiter " + "wfetLabel "; + + // enum TWizardParamType + const TWizardParamType = + "wptString " + + "wptInteger " + + "wptNumeric " + + "wptBoolean " + + "wptDateTime " + + "wptPick " + + "wptText " + + "wptUser " + + "wptUserList " + + "wptEDocumentInfo " + + "wptEDocumentInfoList " + + "wptReferenceRecordInfo " + + "wptReferenceRecordInfoList " + + "wptFolderInfo " + + "wptTaskInfo " + + "wptContents " + + "wptFileName " + + "wptDate "; + + // enum TWizardStepResult + const TWizardStepResult = + "wsrComplete " + + "wsrGoNext " + + "wsrGoPrevious " + + "wsrCustom " + + "wsrCancel " + + "wsrGoFinal "; + + // enum TWizardStepType + const TWizardStepType = + "wstForm " + + "wstEDocument " + + "wstTaskCard " + + "wstReferenceRecordCard " + + "wstFinal "; + + // enum TWorkAccessType + const TWorkAccessType = "waAll " + "waPerformers " + "waManual "; + + // enum TWorkflowBlockType + const TWorkflowBlockType = + "wsbStart " + + "wsbFinish " + + "wsbNotice " + + "wsbStep " + + "wsbDecision " + + "wsbWait " + + "wsbMonitor " + + "wsbScript " + + "wsbConnector " + + "wsbSubTask " + + "wsbLifeCycleStage " + + "wsbPause "; + + // enum TWorkflowDataType + const TWorkflowDataType = + "wdtInteger " + + "wdtFloat " + + "wdtString " + + "wdtPick " + + "wdtDateTime " + + "wdtBoolean " + + "wdtTask " + + "wdtJob " + + "wdtFolder " + + "wdtEDocument " + + "wdtReferenceRecord " + + "wdtUser " + + "wdtGroup " + + "wdtRole " + + "wdtIntegerCollection " + + "wdtFloatCollection " + + "wdtStringCollection " + + "wdtPickCollection " + + "wdtDateTimeCollection " + + "wdtBooleanCollection " + + "wdtTaskCollection " + + "wdtJobCollection " + + "wdtFolderCollection " + + "wdtEDocumentCollection " + + "wdtReferenceRecordCollection " + + "wdtUserCollection " + + "wdtGroupCollection " + + "wdtRoleCollection " + + "wdtContents " + + "wdtUserList " + + "wdtSearchDescription " + + "wdtDeadLine " + + "wdtPickSet " + + "wdtAccountCollection "; + + // enum TWorkImportance + const TWorkImportance = "wiLow " + "wiNormal " + "wiHigh "; + + // enum TWorkRouteType + const TWorkRouteType = "wrtSoft " + "wrtHard "; + + // enum TWorkState + const TWorkState = + "wsInit " + + "wsRunning " + + "wsDone " + + "wsControlled " + + "wsAborted " + + "wsContinued "; + + // enum TWorkTextBuildingMode + const TWorkTextBuildingMode = + "wtmFull " + "wtmFromCurrent " + "wtmOnlyCurrent "; + + // Перечисления + const ENUMS = + TAccountType + + TActionEnabledMode + + TAddPosition + + TAlignment + + TAreaShowMode + + TCertificateInvalidationReason + + TCertificateType + + TCheckListBoxItemState + + TCloseOnEsc + + TCompType + + TConditionFormat + + TConnectionIntent + + TContentKind + + TControlType + + TCriterionContentType + + TCultureType + + TDataSetEventType + + TDataSetState + + TDateFormatType + + TDateOffsetType + + TDateTimeKind + + TDeaAccessRights + + TDocumentDefaultAction + + TEditMode + + TEditorCloseObservType + + TEdmsApplicationAction + + TEDocumentLockType + + TEDocumentStepShowMode + + TEDocumentStepVersionType + + TEDocumentStorageFunction + + TEDocumentStorageType + + TEDocumentVersionSourceType + + TEDocumentVersionState + + TEncodeType + + TExceptionCategory + + TExportedSignaturesType + + TExportedVersionType + + TFieldDataType + + TFolderType + + TGridRowHeight + + THyperlinkType + + TImageFileFormat + + TImageMode + + TImageType + + TInplaceHintKind + + TISBLContext + + TItemShow + + TJobKind + + TJoinType + + TLabelPos + + TLicensingType + + TLifeCycleStageFontColor + + TLifeCycleStageFontStyle + + TLockableDevelopmentComponentType + + TMaxRecordCountRestrictionType + + TRangeValueType + + TRelativeDate + + TReportDestination + + TReqDataType + + TRequisiteEventType + + TSBTimeType + + TSearchShowMode + + TSelectMode + + TSignatureType + + TSignerContentType + + TStringsSortType + + TStringValueType + + TStructuredObjectAttributeType + + TTaskAbortReason + + TTextValueType + + TUserObjectStatus + + TUserType + + TValuesBuildType + + TViewMode + + TViewSelectionMode + + TWizardActionType + + TWizardFormElementProperty + + TWizardFormElementType + + TWizardParamType + + TWizardStepResult + + TWizardStepType + + TWorkAccessType + + TWorkflowBlockType + + TWorkflowDataType + + TWorkImportance + + TWorkRouteType + + TWorkState + + TWorkTextBuildingMode; + + // Системные функции ==> SYSFUNCTIONS + const system_functions = + "AddSubString " + + "AdjustLineBreaks " + + "AmountInWords " + + "Analysis " + + "ArrayDimCount " + + "ArrayHighBound " + + "ArrayLowBound " + + "ArrayOf " + + "ArrayReDim " + + "Assert " + + "Assigned " + + "BeginOfMonth " + + "BeginOfPeriod " + + "BuildProfilingOperationAnalysis " + + "CallProcedure " + + "CanReadFile " + + "CArrayElement " + + "CDataSetRequisite " + + "ChangeDate " + + "ChangeReferenceDataset " + + "Char " + + "CharPos " + + "CheckParam " + + "CheckParamValue " + + "CompareStrings " + + "ConstantExists " + + "ControlState " + + "ConvertDateStr " + + "Copy " + + "CopyFile " + + "CreateArray " + + "CreateCachedReference " + + "CreateConnection " + + "CreateDialog " + + "CreateDualListDialog " + + "CreateEditor " + + "CreateException " + + "CreateFile " + + "CreateFolderDialog " + + "CreateInputDialog " + + "CreateLinkFile " + + "CreateList " + + "CreateLock " + + "CreateMemoryDataSet " + + "CreateObject " + + "CreateOpenDialog " + + "CreateProgress " + + "CreateQuery " + + "CreateReference " + + "CreateReport " + + "CreateSaveDialog " + + "CreateScript " + + "CreateSQLPivotFunction " + + "CreateStringList " + + "CreateTreeListSelectDialog " + + "CSelectSQL " + + "CSQL " + + "CSubString " + + "CurrentUserID " + + "CurrentUserName " + + "CurrentVersion " + + "DataSetLocateEx " + + "DateDiff " + + "DateTimeDiff " + + "DateToStr " + + "DayOfWeek " + + "DeleteFile " + + "DirectoryExists " + + "DisableCheckAccessRights " + + "DisableCheckFullShowingRestriction " + + "DisableMassTaskSendingRestrictions " + + "DropTable " + + "DupeString " + + "EditText " + + "EnableCheckAccessRights " + + "EnableCheckFullShowingRestriction " + + "EnableMassTaskSendingRestrictions " + + "EndOfMonth " + + "EndOfPeriod " + + "ExceptionExists " + + "ExceptionsOff " + + "ExceptionsOn " + + "Execute " + + "ExecuteProcess " + + "Exit " + + "ExpandEnvironmentVariables " + + "ExtractFileDrive " + + "ExtractFileExt " + + "ExtractFileName " + + "ExtractFilePath " + + "ExtractParams " + + "FileExists " + + "FileSize " + + "FindFile " + + "FindSubString " + + "FirmContext " + + "ForceDirectories " + + "Format " + + "FormatDate " + + "FormatNumeric " + + "FormatSQLDate " + + "FormatString " + + "FreeException " + + "GetComponent " + + "GetComponentLaunchParam " + + "GetConstant " + + "GetLastException " + + "GetReferenceRecord " + + "GetRefTypeByRefID " + + "GetTableID " + + "GetTempFolder " + + "IfThen " + + "In " + + "IndexOf " + + "InputDialog " + + "InputDialogEx " + + "InteractiveMode " + + "IsFileLocked " + + "IsGraphicFile " + + "IsNumeric " + + "Length " + + "LoadString " + + "LoadStringFmt " + + "LocalTimeToUTC " + + "LowerCase " + + "Max " + + "MessageBox " + + "MessageBoxEx " + + "MimeDecodeBinary " + + "MimeDecodeString " + + "MimeEncodeBinary " + + "MimeEncodeString " + + "Min " + + "MoneyInWords " + + "MoveFile " + + "NewID " + + "Now " + + "OpenFile " + + "Ord " + + "Precision " + + "Raise " + + "ReadCertificateFromFile " + + "ReadFile " + + "ReferenceCodeByID " + + "ReferenceNumber " + + "ReferenceRequisiteMode " + + "ReferenceRequisiteValue " + + "RegionDateSettings " + + "RegionNumberSettings " + + "RegionTimeSettings " + + "RegRead " + + "RegWrite " + + "RenameFile " + + "Replace " + + "Round " + + "SelectServerCode " + + "SelectSQL " + + "ServerDateTime " + + "SetConstant " + + "SetManagedFolderFieldsState " + + "ShowConstantsInputDialog " + + "ShowMessage " + + "Sleep " + + "Split " + + "SQL " + + "SQL2XLSTAB " + + "SQLProfilingSendReport " + + "StrToDate " + + "SubString " + + "SubStringCount " + + "SystemSetting " + + "Time " + + "TimeDiff " + + "Today " + + "Transliterate " + + "Trim " + + "UpperCase " + + "UserStatus " + + "UTCToLocalTime " + + "ValidateXML " + + "VarIsClear " + + "VarIsEmpty " + + "VarIsNull " + + "WorkTimeDiff " + + "WriteFile " + + "WriteFileEx " + + "WriteObjectHistory " + + "Анализ " + + "БазаДанных " + + "БлокЕсть " + + "БлокЕстьРасш " + + "БлокИнфо " + + "БлокСнять " + + "БлокСнятьРасш " + + "БлокУстановить " + + "Ввод " + + "ВводМеню " + + "ВедС " + + "ВедСпр " + + "ВерхняяГраницаМассива " + + "ВнешПрогр " + + "Восст " + + "ВременнаяПапка " + + "Время " + + "ВыборSQL " + + "ВыбратьЗапись " + + "ВыделитьСтр " + + "Вызвать " + + "Выполнить " + + "ВыпПрогр " + + "ГрафическийФайл " + + "ГруппаДополнительно " + + "ДатаВремяСерв " + + "ДеньНедели " + + "ДиалогДаНет " + + "ДлинаСтр " + + "ДобПодстр " + + "ЕПусто " + + "ЕслиТо " + + "ЕЧисло " + + "ЗамПодстр " + + "ЗаписьСправочника " + + "ЗначПоляСпр " + + "ИДТипСпр " + + "ИзвлечьДиск " + + "ИзвлечьИмяФайла " + + "ИзвлечьПуть " + + "ИзвлечьРасширение " + + "ИзмДат " + + "ИзменитьРазмерМассива " + + "ИзмеренийМассива " + + "ИмяОрг " + + "ИмяПоляСпр " + + "Индекс " + + "ИндикаторЗакрыть " + + "ИндикаторОткрыть " + + "ИндикаторШаг " + + "ИнтерактивныйРежим " + + "ИтогТблСпр " + + "КодВидВедСпр " + + "КодВидСпрПоИД " + + "КодПоAnalit " + + "КодСимвола " + + "КодСпр " + + "КолПодстр " + + "КолПроп " + + "КонМес " + + "Конст " + + "КонстЕсть " + + "КонстЗнач " + + "КонТран " + + "КопироватьФайл " + + "КопияСтр " + + "КПериод " + + "КСтрТблСпр " + + "Макс " + + "МаксСтрТблСпр " + + "Массив " + + "Меню " + + "МенюРасш " + + "Мин " + + "НаборДанныхНайтиРасш " + + "НаимВидСпр " + + "НаимПоAnalit " + + "НаимСпр " + + "НастроитьПереводыСтрок " + + "НачМес " + + "НачТран " + + "НижняяГраницаМассива " + + "НомерСпр " + + "НПериод " + + "Окно " + + "Окр " + + "Окружение " + + "ОтлИнфДобавить " + + "ОтлИнфУдалить " + + "Отчет " + + "ОтчетАнал " + + "ОтчетИнт " + + "ПапкаСуществует " + + "Пауза " + + "ПВыборSQL " + + "ПереименоватьФайл " + + "Переменные " + + "ПереместитьФайл " + + "Подстр " + + "ПоискПодстр " + + "ПоискСтр " + + "ПолучитьИДТаблицы " + + "ПользовательДополнительно " + + "ПользовательИД " + + "ПользовательИмя " + + "ПользовательСтатус " + + "Прервать " + + "ПроверитьПараметр " + + "ПроверитьПараметрЗнач " + + "ПроверитьУсловие " + + "РазбСтр " + + "РазнВремя " + + "РазнДат " + + "РазнДатаВремя " + + "РазнРабВремя " + + "РегУстВрем " + + "РегУстДат " + + "РегУстЧсл " + + "РедТекст " + + "РеестрЗапись " + + "РеестрСписокИменПарам " + + "РеестрЧтение " + + "РеквСпр " + + "РеквСпрПр " + + "Сегодня " + + "Сейчас " + + "Сервер " + + "СерверПроцессИД " + + "СертификатФайлСчитать " + + "СжПроб " + + "Символ " + + "СистемаДиректумКод " + + "СистемаИнформация " + + "СистемаКод " + + "Содержит " + + "СоединениеЗакрыть " + + "СоединениеОткрыть " + + "СоздатьДиалог " + + "СоздатьДиалогВыбораИзДвухСписков " + + "СоздатьДиалогВыбораПапки " + + "СоздатьДиалогОткрытияФайла " + + "СоздатьДиалогСохраненияФайла " + + "СоздатьЗапрос " + + "СоздатьИндикатор " + + "СоздатьИсключение " + + "СоздатьКэшированныйСправочник " + + "СоздатьМассив " + + "СоздатьНаборДанных " + + "СоздатьОбъект " + + "СоздатьОтчет " + + "СоздатьПапку " + + "СоздатьРедактор " + + "СоздатьСоединение " + + "СоздатьСписок " + + "СоздатьСписокСтрок " + + "СоздатьСправочник " + + "СоздатьСценарий " + + "СоздСпр " + + "СостСпр " + + "Сохр " + + "СохрСпр " + + "СписокСистем " + + "Спр " + + "Справочник " + + "СпрБлокЕсть " + + "СпрБлокСнять " + + "СпрБлокСнятьРасш " + + "СпрБлокУстановить " + + "СпрИзмНабДан " + + "СпрКод " + + "СпрНомер " + + "СпрОбновить " + + "СпрОткрыть " + + "СпрОтменить " + + "СпрПарам " + + "СпрПолеЗнач " + + "СпрПолеИмя " + + "СпрРекв " + + "СпрРеквВведЗн " + + "СпрРеквНовые " + + "СпрРеквПр " + + "СпрРеквПредЗн " + + "СпрРеквРежим " + + "СпрРеквТипТекст " + + "СпрСоздать " + + "СпрСост " + + "СпрСохранить " + + "СпрТблИтог " + + "СпрТблСтр " + + "СпрТблСтрКол " + + "СпрТблСтрМакс " + + "СпрТблСтрМин " + + "СпрТблСтрПред " + + "СпрТблСтрСлед " + + "СпрТблСтрСозд " + + "СпрТблСтрУд " + + "СпрТекПредст " + + "СпрУдалить " + + "СравнитьСтр " + + "СтрВерхРегистр " + + "СтрНижнРегистр " + + "СтрТблСпр " + + "СумПроп " + + "Сценарий " + + "СценарийПарам " + + "ТекВерсия " + + "ТекОрг " + + "Точн " + + "Тран " + + "Транслитерация " + + "УдалитьТаблицу " + + "УдалитьФайл " + + "УдСпр " + + "УдСтрТблСпр " + + "Уст " + + "УстановкиКонстант " + + "ФайлАтрибутСчитать " + + "ФайлАтрибутУстановить " + + "ФайлВремя " + + "ФайлВремяУстановить " + + "ФайлВыбрать " + + "ФайлЗанят " + + "ФайлЗаписать " + + "ФайлИскать " + + "ФайлКопировать " + + "ФайлМожноЧитать " + + "ФайлОткрыть " + + "ФайлПереименовать " + + "ФайлПерекодировать " + + "ФайлПереместить " + + "ФайлПросмотреть " + + "ФайлРазмер " + + "ФайлСоздать " + + "ФайлСсылкаСоздать " + + "ФайлСуществует " + + "ФайлСчитать " + + "ФайлУдалить " + + "ФмтSQLДат " + + "ФмтДат " + + "ФмтСтр " + + "ФмтЧсл " + + "Формат " + + "ЦМассивЭлемент " + + "ЦНаборДанныхРеквизит " + + "ЦПодстр "; + + // Предопределенные переменные ==> built_in + const predefined_variables = + "AltState " + + "Application " + + "CallType " + + "ComponentTokens " + + "CreatedJobs " + + "CreatedNotices " + + "ControlState " + + "DialogResult " + + "Dialogs " + + "EDocuments " + + "EDocumentVersionSource " + + "Folders " + + "GlobalIDs " + + "Job " + + "Jobs " + + "InputValue " + + "LookUpReference " + + "LookUpRequisiteNames " + + "LookUpSearch " + + "Object " + + "ParentComponent " + + "Processes " + + "References " + + "Requisite " + + "ReportName " + + "Reports " + + "Result " + + "Scripts " + + "Searches " + + "SelectedAttachments " + + "SelectedItems " + + "SelectMode " + + "Sender " + + "ServerEvents " + + "ServiceFactory " + + "ShiftState " + + "SubTask " + + "SystemDialogs " + + "Tasks " + + "Wizard " + + "Wizards " + + "Work " + + "ВызовСпособ " + + "ИмяОтчета " + + "РеквЗнач "; + + // Интерфейсы ==> type + const interfaces = + "IApplication " + + "IAccessRights " + + "IAccountRepository " + + "IAccountSelectionRestrictions " + + "IAction " + + "IActionList " + + "IAdministrationHistoryDescription " + + "IAnchors " + + "IApplication " + + "IArchiveInfo " + + "IAttachment " + + "IAttachmentList " + + "ICheckListBox " + + "ICheckPointedList " + + "IColumn " + + "IComponent " + + "IComponentDescription " + + "IComponentToken " + + "IComponentTokenFactory " + + "IComponentTokenInfo " + + "ICompRecordInfo " + + "IConnection " + + "IContents " + + "IControl " + + "IControlJob " + + "IControlJobInfo " + + "IControlList " + + "ICrypto " + + "ICrypto2 " + + "ICustomJob " + + "ICustomJobInfo " + + "ICustomListBox " + + "ICustomObjectWizardStep " + + "ICustomWork " + + "ICustomWorkInfo " + + "IDataSet " + + "IDataSetAccessInfo " + + "IDataSigner " + + "IDateCriterion " + + "IDateRequisite " + + "IDateRequisiteDescription " + + "IDateValue " + + "IDeaAccessRights " + + "IDeaObjectInfo " + + "IDevelopmentComponentLock " + + "IDialog " + + "IDialogFactory " + + "IDialogPickRequisiteItems " + + "IDialogsFactory " + + "IDICSFactory " + + "IDocRequisite " + + "IDocumentInfo " + + "IDualListDialog " + + "IECertificate " + + "IECertificateInfo " + + "IECertificates " + + "IEditControl " + + "IEditorForm " + + "IEdmsExplorer " + + "IEdmsObject " + + "IEdmsObjectDescription " + + "IEdmsObjectFactory " + + "IEdmsObjectInfo " + + "IEDocument " + + "IEDocumentAccessRights " + + "IEDocumentDescription " + + "IEDocumentEditor " + + "IEDocumentFactory " + + "IEDocumentInfo " + + "IEDocumentStorage " + + "IEDocumentVersion " + + "IEDocumentVersionListDialog " + + "IEDocumentVersionSource " + + "IEDocumentWizardStep " + + "IEDocVerSignature " + + "IEDocVersionState " + + "IEnabledMode " + + "IEncodeProvider " + + "IEncrypter " + + "IEvent " + + "IEventList " + + "IException " + + "IExternalEvents " + + "IExternalHandler " + + "IFactory " + + "IField " + + "IFileDialog " + + "IFolder " + + "IFolderDescription " + + "IFolderDialog " + + "IFolderFactory " + + "IFolderInfo " + + "IForEach " + + "IForm " + + "IFormTitle " + + "IFormWizardStep " + + "IGlobalIDFactory " + + "IGlobalIDInfo " + + "IGrid " + + "IHasher " + + "IHistoryDescription " + + "IHyperLinkControl " + + "IImageButton " + + "IImageControl " + + "IInnerPanel " + + "IInplaceHint " + + "IIntegerCriterion " + + "IIntegerList " + + "IIntegerRequisite " + + "IIntegerValue " + + "IISBLEditorForm " + + "IJob " + + "IJobDescription " + + "IJobFactory " + + "IJobForm " + + "IJobInfo " + + "ILabelControl " + + "ILargeIntegerCriterion " + + "ILargeIntegerRequisite " + + "ILargeIntegerValue " + + "ILicenseInfo " + + "ILifeCycleStage " + + "IList " + + "IListBox " + + "ILocalIDInfo " + + "ILocalization " + + "ILock " + + "IMemoryDataSet " + + "IMessagingFactory " + + "IMetadataRepository " + + "INotice " + + "INoticeInfo " + + "INumericCriterion " + + "INumericRequisite " + + "INumericValue " + + "IObject " + + "IObjectDescription " + + "IObjectImporter " + + "IObjectInfo " + + "IObserver " + + "IPanelGroup " + + "IPickCriterion " + + "IPickProperty " + + "IPickRequisite " + + "IPickRequisiteDescription " + + "IPickRequisiteItem " + + "IPickRequisiteItems " + + "IPickValue " + + "IPrivilege " + + "IPrivilegeList " + + "IProcess " + + "IProcessFactory " + + "IProcessMessage " + + "IProgress " + + "IProperty " + + "IPropertyChangeEvent " + + "IQuery " + + "IReference " + + "IReferenceCriterion " + + "IReferenceEnabledMode " + + "IReferenceFactory " + + "IReferenceHistoryDescription " + + "IReferenceInfo " + + "IReferenceRecordCardWizardStep " + + "IReferenceRequisiteDescription " + + "IReferencesFactory " + + "IReferenceValue " + + "IRefRequisite " + + "IReport " + + "IReportFactory " + + "IRequisite " + + "IRequisiteDescription " + + "IRequisiteDescriptionList " + + "IRequisiteFactory " + + "IRichEdit " + + "IRouteStep " + + "IRule " + + "IRuleList " + + "ISchemeBlock " + + "IScript " + + "IScriptFactory " + + "ISearchCriteria " + + "ISearchCriterion " + + "ISearchDescription " + + "ISearchFactory " + + "ISearchFolderInfo " + + "ISearchForObjectDescription " + + "ISearchResultRestrictions " + + "ISecuredContext " + + "ISelectDialog " + + "IServerEvent " + + "IServerEventFactory " + + "IServiceDialog " + + "IServiceFactory " + + "ISignature " + + "ISignProvider " + + "ISignProvider2 " + + "ISignProvider3 " + + "ISimpleCriterion " + + "IStringCriterion " + + "IStringList " + + "IStringRequisite " + + "IStringRequisiteDescription " + + "IStringValue " + + "ISystemDialogsFactory " + + "ISystemInfo " + + "ITabSheet " + + "ITask " + + "ITaskAbortReasonInfo " + + "ITaskCardWizardStep " + + "ITaskDescription " + + "ITaskFactory " + + "ITaskInfo " + + "ITaskRoute " + + "ITextCriterion " + + "ITextRequisite " + + "ITextValue " + + "ITreeListSelectDialog " + + "IUser " + + "IUserList " + + "IValue " + + "IView " + + "IWebBrowserControl " + + "IWizard " + + "IWizardAction " + + "IWizardFactory " + + "IWizardFormElement " + + "IWizardParam " + + "IWizardPickParam " + + "IWizardReferenceParam " + + "IWizardStep " + + "IWorkAccessRights " + + "IWorkDescription " + + "IWorkflowAskableParam " + + "IWorkflowAskableParams " + + "IWorkflowBlock " + + "IWorkflowBlockResult " + + "IWorkflowEnabledMode " + + "IWorkflowParam " + + "IWorkflowPickParam " + + "IWorkflowReferenceParam " + + "IWorkState " + + "IWorkTreeCustomNode " + + "IWorkTreeJobNode " + + "IWorkTreeTaskNode " + + "IXMLEditorForm " + + "SBCrypto "; + + // built_in : встроенные или библиотечные объекты (константы, перечисления) + const BUILTIN = CONSTANTS + ENUMS; + + // class: встроенные наборы значений, системные объекты, фабрики + const CLASS = predefined_variables; + + // literal : примитивные типы + const LITERAL = "null true false nil "; + + // number : числа + const NUMBERS = { + className: "number", + begin: hljs.NUMBER_RE, + relevance: 0 + }; + + // string : строки + const STRINGS = { + className: "string", + variants: [ + { + begin: '"', + end: '"' + }, + { + begin: "'", + end: "'" + } + ] + }; + + // Токены + const DOCTAGS = { + className: "doctag", + begin: "\\b(?:TODO|DONE|BEGIN|END|STUB|CHG|FIXME|NOTE|BUG|XXX)\\b", + relevance: 0 + }; + + // Однострочный комментарий + const ISBL_LINE_COMMENT_MODE = { + className: "comment", + begin: "//", + end: "$", + relevance: 0, + contains: [ + hljs.PHRASAL_WORDS_MODE, + DOCTAGS + ] + }; + + // Многострочный комментарий + const ISBL_BLOCK_COMMENT_MODE = { + className: "comment", + begin: "/\\*", + end: "\\*/", + relevance: 0, + contains: [ + hljs.PHRASAL_WORDS_MODE, + DOCTAGS + ] + }; + + // comment : комментарии + const COMMENTS = { variants: [ + ISBL_LINE_COMMENT_MODE, + ISBL_BLOCK_COMMENT_MODE + ] }; + + // keywords : ключевые слова + const KEYWORDS = { + $pattern: UNDERSCORE_IDENT_RE, + keyword: KEYWORD, + built_in: BUILTIN, + class: CLASS, + literal: LITERAL + }; + + // methods : методы + const METHODS = { + begin: "\\.\\s*" + hljs.UNDERSCORE_IDENT_RE, + keywords: KEYWORDS, + relevance: 0 + }; + + // type : встроенные типы + const TYPES = { + className: "type", + begin: ":[ \\t]*(" + interfaces.trim().replace(/\s/g, "|") + ")", + end: "[ \\t]*=", + excludeEnd: true + }; + + // variables : переменные + const VARIABLES = { + className: "variable", + keywords: KEYWORDS, + begin: UNDERSCORE_IDENT_RE, + relevance: 0, + contains: [ + TYPES, + METHODS + ] + }; + + // Имена функций + const FUNCTION_TITLE = FUNCTION_NAME_IDENT_RE + "\\("; + + const TITLE_MODE = { + className: "title", + keywords: { + $pattern: UNDERSCORE_IDENT_RE, + built_in: system_functions + }, + begin: FUNCTION_TITLE, + end: "\\(", + returnBegin: true, + excludeEnd: true + }; + + // function : функции + const FUNCTIONS = { + className: "function", + begin: FUNCTION_TITLE, + end: "\\)$", + returnBegin: true, + keywords: KEYWORDS, + illegal: "[\\[\\]\\|\\$\\?%,~#@]", + contains: [ + TITLE_MODE, + METHODS, + VARIABLES, + STRINGS, + NUMBERS, + COMMENTS + ] + }; + + return { + name: 'ISBL', + case_insensitive: true, + keywords: KEYWORDS, + illegal: "\\$|\\?|%|,|;$|~|#|@| +Category: common, enterprise +Website: https://www.java.com/ +*/ + + +/** + * Allows recursive regex expressions to a given depth + * + * ie: recurRegex("(abc~~~)", /~~~/g, 2) becomes: + * (abc(abc(abc))) + * + * @param {string} re + * @param {RegExp} substitution (should be a g mode regex) + * @param {number} depth + * @returns {string}`` + */ +function recurRegex(re, substitution, depth) { + if (depth === -1) return ""; + + return re.replace(substitution, _ => { + return recurRegex(re, substitution, depth - 1); + }); +} + +/** @type LanguageFn */ +function java(hljs) { + const regex = hljs.regex; + const JAVA_IDENT_RE = '[\u00C0-\u02B8a-zA-Z_$][\u00C0-\u02B8a-zA-Z_$0-9]*'; + const GENERIC_IDENT_RE = JAVA_IDENT_RE + + recurRegex('(?:<' + JAVA_IDENT_RE + '~~~(?:\\s*,\\s*' + JAVA_IDENT_RE + '~~~)*>)?', /~~~/g, 2); + const MAIN_KEYWORDS = [ + 'synchronized', + 'abstract', + 'private', + 'var', + 'static', + 'if', + 'const ', + 'for', + 'while', + 'strictfp', + 'finally', + 'protected', + 'import', + 'native', + 'final', + 'void', + 'enum', + 'else', + 'break', + 'transient', + 'catch', + 'instanceof', + 'volatile', + 'case', + 'assert', + 'package', + 'default', + 'public', + 'try', + 'switch', + 'continue', + 'throws', + 'protected', + 'public', + 'private', + 'module', + 'requires', + 'exports', + 'do', + 'sealed', + 'yield', + 'permits', + 'goto', + 'when' + ]; + + const BUILT_INS = [ + 'super', + 'this' + ]; + + const LITERALS = [ + 'false', + 'true', + 'null' + ]; + + const TYPES = [ + 'char', + 'boolean', + 'long', + 'float', + 'int', + 'byte', + 'short', + 'double' + ]; + + const KEYWORDS = { + keyword: MAIN_KEYWORDS, + literal: LITERALS, + type: TYPES, + built_in: BUILT_INS + }; + + const ANNOTATION = { + className: 'meta', + begin: '@' + JAVA_IDENT_RE, + contains: [ + { + begin: /\(/, + end: /\)/, + contains: [ "self" ] // allow nested () inside our annotation + } + ] + }; + const PARAMS = { + className: 'params', + begin: /\(/, + end: /\)/, + keywords: KEYWORDS, + relevance: 0, + contains: [ hljs.C_BLOCK_COMMENT_MODE ], + endsParent: true + }; + + return { + name: 'Java', + aliases: [ 'jsp' ], + keywords: KEYWORDS, + illegal: /<\/|#/, + contains: [ + hljs.COMMENT( + '/\\*\\*', + '\\*/', + { + relevance: 0, + contains: [ + { + // eat up @'s in emails to prevent them to be recognized as doctags + begin: /\w+@/, + relevance: 0 + }, + { + className: 'doctag', + begin: '@[A-Za-z]+' + } + ] + } + ), + // relevance boost + { + begin: /import java\.[a-z]+\./, + keywords: "import", + relevance: 2 + }, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + { + begin: /"""/, + end: /"""/, + className: "string", + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + { + match: [ + /\b(?:class|interface|enum|extends|implements|new)/, + /\s+/, + JAVA_IDENT_RE + ], + className: { + 1: "keyword", + 3: "title.class" + } + }, + { + // Exceptions for hyphenated keywords + match: /non-sealed/, + scope: "keyword" + }, + { + begin: [ + regex.concat(/(?!else)/, JAVA_IDENT_RE), + /\s+/, + JAVA_IDENT_RE, + /\s+/, + /=(?!=)/ + ], + className: { + 1: "type", + 3: "variable", + 5: "operator" + } + }, + { + begin: [ + /record/, + /\s+/, + JAVA_IDENT_RE + ], + className: { + 1: "keyword", + 3: "title.class" + }, + contains: [ + PARAMS, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + { + // Expression keywords prevent 'keyword Name(...)' from being + // recognized as a function definition + beginKeywords: 'new throw return else', + relevance: 0 + }, + { + begin: [ + '(?:' + GENERIC_IDENT_RE + '\\s+)', + hljs.UNDERSCORE_IDENT_RE, + /\s*(?=\()/ + ], + className: { 2: "title.function" }, + keywords: KEYWORDS, + contains: [ + { + className: 'params', + begin: /\(/, + end: /\)/, + keywords: KEYWORDS, + relevance: 0, + contains: [ + ANNOTATION, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + NUMERIC, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + NUMERIC, + ANNOTATION + ] + }; +} + +export { java as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/java.js.js b/frontend/node_modules/highlight.js/es/languages/java.js.js new file mode 100644 index 0000000..f7488dc --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/java.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/java" instead of "highlight.js/lib/languages/java.js"' + ); + } + } + emitWarning(); + import lang from './java.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/javascript.js b/frontend/node_modules/highlight.js/es/languages/javascript.js new file mode 100644 index 0000000..98091b4 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/javascript.js @@ -0,0 +1,769 @@ +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", + // It's reached stage 3, which is "recommended for implementation": + "using" +]; +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 " { + const tag = "', + 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? + // `>`, etc. + nextChar === "<" || + // the , gives away that this is not HTML + // `` + nextChar === "," + ) { + response.ignoreMatch(); + return; + } + + // `` + // 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(); + } + } + + // `` (self-closing) + // handled by simpleSelfClosing rule + + let m; + const afterMatch = match.input.substring(afterMatchIndex); + + // some more template typing stuff + // (key?: string) => Modify< + if ((m = afterMatch.match(/^\s*=/))) { + response.ignoreMatch(); + return; + } + + // `` + // 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: /(\s*)\(/, + end: /\)/, + keywords: KEYWORDS$1, + contains: ["self"].concat(SUBST_AND_COMMENTS) + } + ]); + const PARAMS = { + className: 'params', + // convert this to negative lookbehind in v12 + begin: /(\s*)\(/, // to match the parms with + 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" + ].map(x => `${x}\\s*\\(`)), + IDENT_RE$1, regex.lookahead(/\s*\(/)), + 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, + { + scope: 'attr', + match: 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: /(\s*)\(/, + 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` + } + ] + }; +} + +export { javascript as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/javascript.js.js b/frontend/node_modules/highlight.js/es/languages/javascript.js.js new file mode 100644 index 0000000..1b87533 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/javascript.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/javascript" instead of "highlight.js/lib/languages/javascript.js"' + ); + } + } + emitWarning(); + import lang from './javascript.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/jboss-cli.js b/frontend/node_modules/highlight.js/es/languages/jboss-cli.js new file mode 100644 index 0000000..fb6988b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/jboss-cli.js @@ -0,0 +1,63 @@ +/* + Language: JBoss CLI + Author: Raphaël Parrëe + Description: language definition jboss cli + Website: https://docs.jboss.org/author/display/WFLY/Command+Line+Interface + Category: config + */ + +function jbossCli(hljs) { + const PARAM = { + begin: /[\w-]+ *=/, + returnBegin: true, + relevance: 0, + contains: [ + { + className: 'attr', + begin: /[\w-]+/ + } + ] + }; + const PARAMSBLOCK = { + className: 'params', + begin: /\(/, + end: /\)/, + contains: [ PARAM ], + relevance: 0 + }; + const OPERATION = { + className: 'function', + begin: /:[\w\-.]+/, + relevance: 0 + }; + const PATH = { + className: 'string', + begin: /\B([\/.])[\w\-.\/=]+/ + }; + const COMMAND_PARAMS = { + className: 'params', + begin: /--[\w\-=\/]+/ + }; + return { + name: 'JBoss CLI', + aliases: [ 'wildfly-cli' ], + keywords: { + $pattern: '[a-z\-]+', + keyword: 'alias batch cd clear command connect connection-factory connection-info data-source deploy ' + + 'deployment-info deployment-overlay echo echo-dmr help history if jdbc-driver-info jms-queue|20 jms-topic|20 ls ' + + 'patch pwd quit read-attribute read-operation reload rollout-plan run-batch set shutdown try unalias ' + + 'undeploy unset version xa-data-source', // module + literal: 'true false' + }, + contains: [ + hljs.HASH_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + COMMAND_PARAMS, + OPERATION, + PATH, + PARAMSBLOCK + ] + }; +} + +export { jbossCli as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/jboss-cli.js.js b/frontend/node_modules/highlight.js/es/languages/jboss-cli.js.js new file mode 100644 index 0000000..4bd02c3 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/jboss-cli.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/jboss-cli" instead of "highlight.js/lib/languages/jboss-cli.js"' + ); + } + } + emitWarning(); + import lang from './jboss-cli.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/json.js b/frontend/node_modules/highlight.js/es/languages/json.js new file mode 100644 index 0000000..49a7cf4 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/json.js @@ -0,0 +1,54 @@ +/* +Language: JSON +Description: JSON (JavaScript Object Notation) is a lightweight data-interchange format. +Author: Ivan Sagalaev +Website: http://www.json.org +Category: common, protocols, web +*/ + +function json(hljs) { + const ATTRIBUTE = { + className: 'attr', + begin: /"(\\.|[^\\"\r\n])*"(?=\s*:)/, + relevance: 1.01 + }; + const PUNCTUATION = { + match: /[{}[\],:]/, + className: "punctuation", + relevance: 0 + }; + const LITERALS = [ + "true", + "false", + "null" + ]; + // NOTE: normally we would rely on `keywords` for this but using a mode here allows us + // - to use the very tight `illegal: \S` rule later to flag any other character + // - as illegal indicating that despite looking like JSON we do not truly have + // - JSON and thus improve false-positively greatly since JSON will try and claim + // - all sorts of JSON looking stuff + const LITERALS_MODE = { + scope: "literal", + beginKeywords: LITERALS.join(" "), + }; + + return { + name: 'JSON', + aliases: ['jsonc'], + keywords:{ + literal: LITERALS, + }, + contains: [ + ATTRIBUTE, + PUNCTUATION, + hljs.QUOTE_STRING_MODE, + LITERALS_MODE, + hljs.C_NUMBER_MODE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ], + illegal: '\\S' + }; +} + +export { json as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/json.js.js b/frontend/node_modules/highlight.js/es/languages/json.js.js new file mode 100644 index 0000000..57cbe21 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/json.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/json" instead of "highlight.js/lib/languages/json.js"' + ); + } + } + emitWarning(); + import lang from './json.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/julia-repl.js b/frontend/node_modules/highlight.js/es/languages/julia-repl.js new file mode 100644 index 0000000..41a6abf --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/julia-repl.js @@ -0,0 +1,51 @@ +/* +Language: Julia REPL +Description: Julia REPL sessions +Author: Morten Piibeleht +Website: https://julialang.org +Requires: julia.js +Category: scientific + +The Julia REPL code blocks look something like the following: + + julia> function foo(x) + x + 1 + end + foo (generic function with 1 method) + +They start on a new line with "julia>". Usually there should also be a space after this, but +we also allow the code to start right after the > character. The code may run over multiple +lines, but the additional lines must start with six spaces (i.e. be indented to match +"julia>"). The rest of the code is assumed to be output from the executed code and will be +left un-highlighted. + +Using simply spaces to identify line continuations may get a false-positive if the output +also prints out six spaces, but such cases should be rare. +*/ + +function juliaRepl(hljs) { + return { + name: 'Julia REPL', + contains: [ + { + className: 'meta.prompt', + begin: /^julia>/, + relevance: 10, + starts: { + // end the highlighting if we are on a new line and the line does not have at + // least six spaces in the beginning + end: /^(?![ ]{6})/, + subLanguage: 'julia' + }, + }, + ], + // jldoctest Markdown blocks are used in the Julia manual and package docs indicate + // code snippets that should be verified when the documentation is built. They can be + // either REPL-like or script-like, but are usually REPL-like and therefore we apply + // julia-repl highlighting to them. More information can be found in Documenter's + // manual: https://juliadocs.github.io/Documenter.jl/latest/man/doctests.html + aliases: [ 'jldoctest' ], + }; +} + +export { juliaRepl as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/julia-repl.js.js b/frontend/node_modules/highlight.js/es/languages/julia-repl.js.js new file mode 100644 index 0000000..430095b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/julia-repl.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/julia-repl" instead of "highlight.js/lib/languages/julia-repl.js"' + ); + } + } + emitWarning(); + import lang from './julia-repl.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/julia.js b/frontend/node_modules/highlight.js/es/languages/julia.js new file mode 100644 index 0000000..5fe61b1 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/julia.js @@ -0,0 +1,442 @@ +/* +Language: Julia +Description: Julia is a high-level, high-performance, dynamic programming language. +Author: Kenta Sato +Contributors: Alex Arslan , Fredrik Ekre +Website: https://julialang.org +Category: scientific +*/ + +function julia(hljs) { + // Since there are numerous special names in Julia, it is too much trouble + // to maintain them by hand. Hence these names (i.e. keywords, literals and + // built-ins) are automatically generated from Julia 1.5.2 itself through + // the following scripts for each. + + // ref: https://docs.julialang.org/en/v1/manual/variables/#Allowed-Variable-Names + const VARIABLE_NAME_RE = '[A-Za-z_\\u00A1-\\uFFFF][A-Za-z_0-9\\u00A1-\\uFFFF]*'; + + // # keyword generator, multi-word keywords handled manually below (Julia 1.5.2) + // import REPL.REPLCompletions + // res = String["in", "isa", "where"] + // for kw in collect(x.keyword for x in REPLCompletions.complete_keyword("")) + // if !(contains(kw, " ") || kw == "struct") + // push!(res, kw) + // end + // end + // sort!(unique!(res)) + // foreach(x -> println("\'", x, "\',"), res) + const KEYWORD_LIST = [ + 'baremodule', + 'begin', + 'break', + 'catch', + 'ccall', + 'const', + 'continue', + 'do', + 'else', + 'elseif', + 'end', + 'export', + 'false', + 'finally', + 'for', + 'function', + 'global', + 'if', + 'import', + 'in', + 'isa', + 'let', + 'local', + 'macro', + 'module', + 'quote', + 'return', + 'true', + 'try', + 'using', + 'where', + 'while', + ]; + + // # literal generator (Julia 1.5.2) + // import REPL.REPLCompletions + // res = String["true", "false"] + // for compl in filter!(x -> isa(x, REPLCompletions.ModuleCompletion) && (x.parent === Base || x.parent === Core), + // REPLCompletions.completions("", 0)[1]) + // try + // v = eval(Symbol(compl.mod)) + // if !(v isa Function || v isa Type || v isa TypeVar || v isa Module || v isa Colon) + // push!(res, compl.mod) + // end + // catch e + // end + // end + // sort!(unique!(res)) + // foreach(x -> println("\'", x, "\',"), res) + const LITERAL_LIST = [ + 'ARGS', + 'C_NULL', + 'DEPOT_PATH', + 'ENDIAN_BOM', + 'ENV', + 'Inf', + 'Inf16', + 'Inf32', + 'Inf64', + 'InsertionSort', + 'LOAD_PATH', + 'MergeSort', + 'NaN', + 'NaN16', + 'NaN32', + 'NaN64', + 'PROGRAM_FILE', + 'QuickSort', + 'RoundDown', + 'RoundFromZero', + 'RoundNearest', + 'RoundNearestTiesAway', + 'RoundNearestTiesUp', + 'RoundToZero', + 'RoundUp', + 'VERSION|0', + 'devnull', + 'false', + 'im', + 'missing', + 'nothing', + 'pi', + 'stderr', + 'stdin', + 'stdout', + 'true', + 'undef', + 'π', + 'ℯ', + ]; + + // # built_in generator (Julia 1.5.2) + // import REPL.REPLCompletions + // res = String[] + // for compl in filter!(x -> isa(x, REPLCompletions.ModuleCompletion) && (x.parent === Base || x.parent === Core), + // REPLCompletions.completions("", 0)[1]) + // try + // v = eval(Symbol(compl.mod)) + // if (v isa Type || v isa TypeVar) && (compl.mod != "=>") + // push!(res, compl.mod) + // end + // catch e + // end + // end + // sort!(unique!(res)) + // foreach(x -> println("\'", x, "\',"), res) + const BUILT_IN_LIST = [ + 'AbstractArray', + 'AbstractChannel', + 'AbstractChar', + 'AbstractDict', + 'AbstractDisplay', + 'AbstractFloat', + 'AbstractIrrational', + 'AbstractMatrix', + 'AbstractRange', + 'AbstractSet', + 'AbstractString', + 'AbstractUnitRange', + 'AbstractVecOrMat', + 'AbstractVector', + 'Any', + 'ArgumentError', + 'Array', + 'AssertionError', + 'BigFloat', + 'BigInt', + 'BitArray', + 'BitMatrix', + 'BitSet', + 'BitVector', + 'Bool', + 'BoundsError', + 'CapturedException', + 'CartesianIndex', + 'CartesianIndices', + 'Cchar', + 'Cdouble', + 'Cfloat', + 'Channel', + 'Char', + 'Cint', + 'Cintmax_t', + 'Clong', + 'Clonglong', + 'Cmd', + 'Colon', + 'Complex', + 'ComplexF16', + 'ComplexF32', + 'ComplexF64', + 'CompositeException', + 'Condition', + 'Cptrdiff_t', + 'Cshort', + 'Csize_t', + 'Cssize_t', + 'Cstring', + 'Cuchar', + 'Cuint', + 'Cuintmax_t', + 'Culong', + 'Culonglong', + 'Cushort', + 'Cvoid', + 'Cwchar_t', + 'Cwstring', + 'DataType', + 'DenseArray', + 'DenseMatrix', + 'DenseVecOrMat', + 'DenseVector', + 'Dict', + 'DimensionMismatch', + 'Dims', + 'DivideError', + 'DomainError', + 'EOFError', + 'Enum', + 'ErrorException', + 'Exception', + 'ExponentialBackOff', + 'Expr', + 'Float16', + 'Float32', + 'Float64', + 'Function', + 'GlobalRef', + 'HTML', + 'IO', + 'IOBuffer', + 'IOContext', + 'IOStream', + 'IdDict', + 'IndexCartesian', + 'IndexLinear', + 'IndexStyle', + 'InexactError', + 'InitError', + 'Int', + 'Int128', + 'Int16', + 'Int32', + 'Int64', + 'Int8', + 'Integer', + 'InterruptException', + 'InvalidStateException', + 'Irrational', + 'KeyError', + 'LinRange', + 'LineNumberNode', + 'LinearIndices', + 'LoadError', + 'MIME', + 'Matrix', + 'Method', + 'MethodError', + 'Missing', + 'MissingException', + 'Module', + 'NTuple', + 'NamedTuple', + 'Nothing', + 'Number', + 'OrdinalRange', + 'OutOfMemoryError', + 'OverflowError', + 'Pair', + 'PartialQuickSort', + 'PermutedDimsArray', + 'Pipe', + 'ProcessFailedException', + 'Ptr', + 'QuoteNode', + 'Rational', + 'RawFD', + 'ReadOnlyMemoryError', + 'Real', + 'ReentrantLock', + 'Ref', + 'Regex', + 'RegexMatch', + 'RoundingMode', + 'SegmentationFault', + 'Set', + 'Signed', + 'Some', + 'StackOverflowError', + 'StepRange', + 'StepRangeLen', + 'StridedArray', + 'StridedMatrix', + 'StridedVecOrMat', + 'StridedVector', + 'String', + 'StringIndexError', + 'SubArray', + 'SubString', + 'SubstitutionString', + 'Symbol', + 'SystemError', + 'Task', + 'TaskFailedException', + 'Text', + 'TextDisplay', + 'Timer', + 'Tuple', + 'Type', + 'TypeError', + 'TypeVar', + 'UInt', + 'UInt128', + 'UInt16', + 'UInt32', + 'UInt64', + 'UInt8', + 'UndefInitializer', + 'UndefKeywordError', + 'UndefRefError', + 'UndefVarError', + 'Union', + 'UnionAll', + 'UnitRange', + 'Unsigned', + 'Val', + 'Vararg', + 'VecElement', + 'VecOrMat', + 'Vector', + 'VersionNumber', + 'WeakKeyDict', + 'WeakRef', + ]; + + const KEYWORDS = { + $pattern: VARIABLE_NAME_RE, + keyword: KEYWORD_LIST, + literal: LITERAL_LIST, + built_in: BUILT_IN_LIST, + }; + + // placeholder for recursive self-reference + const DEFAULT = { + keywords: KEYWORDS, + illegal: /<\// + }; + + // ref: https://docs.julialang.org/en/v1/manual/integers-and-floating-point-numbers/ + const NUMBER = { + className: 'number', + // supported numeric literals: + // * binary literal (e.g. 0x10) + // * octal literal (e.g. 0o76543210) + // * hexadecimal literal (e.g. 0xfedcba876543210) + // * hexadecimal floating point literal (e.g. 0x1p0, 0x1.2p2) + // * decimal literal (e.g. 9876543210, 100_000_000) + // * floating pointe literal (e.g. 1.2, 1.2f, .2, 1., 1.2e10, 1.2e-10) + begin: /(\b0x[\d_]*(\.[\d_]*)?|0x\.\d[\d_]*)p[-+]?\d+|\b0[box][a-fA-F0-9][a-fA-F0-9_]*|(\b\d[\d_]*(\.[\d_]*)?|\.\d[\d_]*)([eEfF][-+]?\d+)?/, + relevance: 0 + }; + + const CHAR = { + className: 'string', + begin: /'(.|\\[xXuU][a-zA-Z0-9]+)'/ + }; + + const INTERPOLATION = { + className: 'subst', + begin: /\$\(/, + end: /\)/, + keywords: KEYWORDS + }; + + const INTERPOLATED_VARIABLE = { + className: 'variable', + begin: '\\$' + VARIABLE_NAME_RE + }; + + // TODO: neatly escape normal code in string literal + const STRING = { + className: 'string', + contains: [ + hljs.BACKSLASH_ESCAPE, + INTERPOLATION, + INTERPOLATED_VARIABLE + ], + variants: [ + { + begin: /\w*"""/, + end: /"""\w*/, + relevance: 10 + }, + { + begin: /\w*"/, + end: /"\w*/ + } + ] + }; + + const COMMAND = { + className: 'string', + contains: [ + hljs.BACKSLASH_ESCAPE, + INTERPOLATION, + INTERPOLATED_VARIABLE + ], + begin: '`', + end: '`' + }; + + const MACROCALL = { + className: 'meta', + begin: '@' + VARIABLE_NAME_RE + }; + + const COMMENT = { + className: 'comment', + variants: [ + { + begin: '#=', + end: '=#', + relevance: 10 + }, + { + begin: '#', + end: '$' + } + ] + }; + + DEFAULT.name = 'Julia'; + DEFAULT.contains = [ + NUMBER, + CHAR, + STRING, + COMMAND, + MACROCALL, + COMMENT, + hljs.HASH_COMMENT_MODE, + { + className: 'keyword', + begin: + '\\b(((abstract|primitive)\\s+)type|(mutable\\s+)?struct)\\b' + }, + { begin: /<:/ } // relevance booster + ]; + INTERPOLATION.contains = DEFAULT.contains; + + return DEFAULT; +} + +export { julia as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/julia.js.js b/frontend/node_modules/highlight.js/es/languages/julia.js.js new file mode 100644 index 0000000..05974a8 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/julia.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/julia" instead of "highlight.js/lib/languages/julia.js"' + ); + } + } + emitWarning(); + import lang from './julia.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/kotlin.js b/frontend/node_modules/highlight.js/es/languages/kotlin.js new file mode 100644 index 0000000..76bd950 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/kotlin.js @@ -0,0 +1,286 @@ +// https://docs.oracle.com/javase/specs/jls/se15/html/jls-3.html#jls-3.10 +var decimalDigits = '[0-9](_*[0-9])*'; +var frac = `\\.(${decimalDigits})`; +var hexDigits = '[0-9a-fA-F](_*[0-9a-fA-F])*'; +var NUMERIC = { + className: 'number', + variants: [ + // DecimalFloatingPointLiteral + // including ExponentPart + { begin: `(\\b(${decimalDigits})((${frac})|\\.)?|(${frac}))` + + `[eE][+-]?(${decimalDigits})[fFdD]?\\b` }, + // excluding ExponentPart + { begin: `\\b(${decimalDigits})((${frac})[fFdD]?\\b|\\.([fFdD]\\b)?)` }, + { begin: `(${frac})[fFdD]?\\b` }, + { begin: `\\b(${decimalDigits})[fFdD]\\b` }, + + // HexadecimalFloatingPointLiteral + { begin: `\\b0[xX]((${hexDigits})\\.?|(${hexDigits})?\\.(${hexDigits}))` + + `[pP][+-]?(${decimalDigits})[fFdD]?\\b` }, + + // DecimalIntegerLiteral + { begin: '\\b(0|[1-9](_*[0-9])*)[lL]?\\b' }, + + // HexIntegerLiteral + { begin: `\\b0[xX](${hexDigits})[lL]?\\b` }, + + // OctalIntegerLiteral + { begin: '\\b0(_*[0-7])*[lL]?\\b' }, + + // BinaryIntegerLiteral + { begin: '\\b0[bB][01](_*[01])*[lL]?\\b' }, + ], + relevance: 0 +}; + +/* + Language: Kotlin + Description: Kotlin is an OSS statically typed programming language that targets the JVM, Android, JavaScript and Native. + Author: Sergey Mashkov + Website: https://kotlinlang.org + Category: common + */ + + +function kotlin(hljs) { + const KEYWORDS = { + keyword: + 'abstract as val var vararg get set class object open private protected public noinline ' + + 'crossinline dynamic final enum if else do while for when throw try catch finally ' + + 'import package is in fun override companion reified inline lateinit init ' + + 'interface annotation data sealed internal infix operator out by constructor super ' + + 'tailrec where const inner suspend typealias external expect actual', + built_in: + 'Byte Short Char Int Long Boolean Float Double Void Unit Nothing', + literal: + 'true false null' + }; + const KEYWORDS_WITH_LABEL = { + className: 'keyword', + begin: /\b(break|continue|return|this)\b/, + starts: { contains: [ + { + className: 'symbol', + begin: /@\w+/ + } + ] } + }; + const LABEL = { + className: 'symbol', + begin: hljs.UNDERSCORE_IDENT_RE + '@' + }; + + // for string templates + const SUBST = { + className: 'subst', + begin: /\$\{/, + end: /\}/, + contains: [ hljs.C_NUMBER_MODE ] + }; + const VARIABLE = { + className: 'variable', + begin: '\\$' + hljs.UNDERSCORE_IDENT_RE + }; + const STRING = { + className: 'string', + variants: [ + { + begin: '"""', + end: '"""(?=[^"])', + contains: [ + VARIABLE, + SUBST + ] + }, + // Can't use built-in modes easily, as we want to use STRING in the meta + // context as 'meta-string' and there's no syntax to remove explicitly set + // classNames in built-in modes. + { + begin: '\'', + end: '\'', + illegal: /\n/, + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: '"', + end: '"', + illegal: /\n/, + contains: [ + hljs.BACKSLASH_ESCAPE, + VARIABLE, + SUBST + ] + } + ] + }; + SUBST.contains.push(STRING); + + const ANNOTATION_USE_SITE = { + className: 'meta', + begin: '@(?:file|property|field|get|set|receiver|param|setparam|delegate)\\s*:(?:\\s*' + hljs.UNDERSCORE_IDENT_RE + ')?' + }; + const ANNOTATION = { + className: 'meta', + begin: '@' + hljs.UNDERSCORE_IDENT_RE, + contains: [ + { + begin: /\(/, + end: /\)/, + contains: [ + hljs.inherit(STRING, { className: 'string' }), + "self" + ] + } + ] + }; + + // https://kotlinlang.org/docs/reference/whatsnew11.html#underscores-in-numeric-literals + // According to the doc above, the number mode of kotlin is the same as java 8, + // so the code below is copied from java.js + const KOTLIN_NUMBER_MODE = NUMERIC; + const KOTLIN_NESTED_COMMENT = hljs.COMMENT( + '/\\*', '\\*/', + { contains: [ hljs.C_BLOCK_COMMENT_MODE ] } + ); + const KOTLIN_PAREN_TYPE = { variants: [ + { + className: 'type', + begin: hljs.UNDERSCORE_IDENT_RE + }, + { + begin: /\(/, + end: /\)/, + contains: [] // defined later + } + ] }; + const KOTLIN_PAREN_TYPE2 = KOTLIN_PAREN_TYPE; + KOTLIN_PAREN_TYPE2.variants[1].contains = [ KOTLIN_PAREN_TYPE ]; + KOTLIN_PAREN_TYPE.variants[1].contains = [ KOTLIN_PAREN_TYPE2 ]; + + return { + name: 'Kotlin', + aliases: [ + 'kt', + 'kts' + ], + keywords: KEYWORDS, + contains: [ + hljs.COMMENT( + '/\\*\\*', + '\\*/', + { + relevance: 0, + contains: [ + { + className: 'doctag', + begin: '@[A-Za-z]+' + } + ] + } + ), + hljs.C_LINE_COMMENT_MODE, + KOTLIN_NESTED_COMMENT, + KEYWORDS_WITH_LABEL, + LABEL, + ANNOTATION_USE_SITE, + ANNOTATION, + { + className: 'function', + beginKeywords: 'fun', + end: '[(]|$', + returnBegin: true, + excludeEnd: true, + keywords: KEYWORDS, + relevance: 5, + contains: [ + { + begin: hljs.UNDERSCORE_IDENT_RE + '\\s*\\(', + returnBegin: true, + relevance: 0, + contains: [ hljs.UNDERSCORE_TITLE_MODE ] + }, + { + className: 'type', + begin: //, + keywords: 'reified', + relevance: 0 + }, + { + className: 'params', + begin: /\(/, + end: /\)/, + endsParent: true, + keywords: KEYWORDS, + relevance: 0, + contains: [ + { + begin: /:/, + end: /[=,\/]/, + endsWithParent: true, + contains: [ + KOTLIN_PAREN_TYPE, + hljs.C_LINE_COMMENT_MODE, + KOTLIN_NESTED_COMMENT + ], + relevance: 0 + }, + hljs.C_LINE_COMMENT_MODE, + KOTLIN_NESTED_COMMENT, + ANNOTATION_USE_SITE, + ANNOTATION, + STRING, + hljs.C_NUMBER_MODE + ] + }, + KOTLIN_NESTED_COMMENT + ] + }, + { + begin: [ + /class|interface|trait/, + /\s+/, + hljs.UNDERSCORE_IDENT_RE + ], + beginScope: { + 3: "title.class" + }, + keywords: 'class interface trait', + end: /[:\{(]|$/, + excludeEnd: true, + illegal: 'extends implements', + contains: [ + { beginKeywords: 'public protected internal private constructor' }, + hljs.UNDERSCORE_TITLE_MODE, + { + className: 'type', + begin: //, + excludeBegin: true, + excludeEnd: true, + relevance: 0 + }, + { + className: 'type', + begin: /[,:]\s*/, + end: /[<\(,){\s]|$/, + excludeBegin: true, + returnEnd: true + }, + ANNOTATION_USE_SITE, + ANNOTATION + ] + }, + STRING, + { + className: 'meta', + begin: "^#!/usr/bin/env", + end: '$', + illegal: '\n' + }, + KOTLIN_NUMBER_MODE + ] + }; +} + +export { kotlin as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/kotlin.js.js b/frontend/node_modules/highlight.js/es/languages/kotlin.js.js new file mode 100644 index 0000000..accf259 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/kotlin.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/kotlin" instead of "highlight.js/lib/languages/kotlin.js"' + ); + } + } + emitWarning(); + import lang from './kotlin.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/lasso.js b/frontend/node_modules/highlight.js/es/languages/lasso.js new file mode 100644 index 0000000..93d3122 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/lasso.js @@ -0,0 +1,171 @@ +/* +Language: Lasso +Author: Eric Knibbe +Description: Lasso is a language and server platform for database-driven web applications. This definition handles Lasso 9 syntax and LassoScript for Lasso 8.6 and earlier. +Website: http://www.lassosoft.com/What-Is-Lasso +Category: database, web +*/ + +function lasso(hljs) { + const LASSO_IDENT_RE = '[a-zA-Z_][\\w.]*'; + const LASSO_ANGLE_RE = '<\\?(lasso(script)?|=)'; + const LASSO_CLOSE_RE = '\\]|\\?>'; + const LASSO_KEYWORDS = { + $pattern: LASSO_IDENT_RE + '|&[lg]t;', + literal: + 'true false none minimal full all void and or not ' + + 'bw nbw ew new cn ncn lt lte gt gte eq neq rx nrx ft', + built_in: + 'array date decimal duration integer map pair string tag xml null ' + + 'boolean bytes keyword list locale queue set stack staticarray ' + + 'local var variable global data self inherited currentcapture givenblock', + keyword: + 'cache database_names database_schemanames database_tablenames ' + + 'define_tag define_type email_batch encode_set html_comment handle ' + + 'handle_error header if inline iterate ljax_target link ' + + 'link_currentaction link_currentgroup link_currentrecord link_detail ' + + 'link_firstgroup link_firstrecord link_lastgroup link_lastrecord ' + + 'link_nextgroup link_nextrecord link_prevgroup link_prevrecord log ' + + 'loop namespace_using output_none portal private protect records ' + + 'referer referrer repeating resultset rows search_args ' + + 'search_arguments select sort_args sort_arguments thread_atomic ' + + 'value_list while abort case else fail_if fail_ifnot fail if_empty ' + + 'if_false if_null if_true loop_abort loop_continue loop_count params ' + + 'params_up return return_value run_children soap_definetag ' + + 'soap_lastrequest soap_lastresponse tag_name ascending average by ' + + 'define descending do equals frozen group handle_failure import in ' + + 'into join let match max min on order parent protected provide public ' + + 'require returnhome skip split_thread sum take thread to trait type ' + + 'where with yield yieldhome' + }; + const HTML_COMMENT = hljs.COMMENT( + '', + { relevance: 0 } + ); + const LASSO_NOPROCESS = { + className: 'meta', + begin: '\\[noprocess\\]', + starts: { + end: '\\[/noprocess\\]', + returnEnd: true, + contains: [ HTML_COMMENT ] + } + }; + const LASSO_START = { + className: 'meta', + begin: '\\[/noprocess|' + LASSO_ANGLE_RE + }; + const LASSO_DATAMEMBER = { + className: 'symbol', + begin: '\'' + LASSO_IDENT_RE + '\'' + }; + const LASSO_CODE = [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.inherit(hljs.C_NUMBER_MODE, { begin: hljs.C_NUMBER_RE + '|(-?infinity|NaN)\\b' }), + hljs.inherit(hljs.APOS_STRING_MODE, { illegal: null }), + hljs.inherit(hljs.QUOTE_STRING_MODE, { illegal: null }), + { + className: 'string', + begin: '`', + end: '`' + }, + { // variables + variants: [ + { begin: '[#$]' + LASSO_IDENT_RE }, + { + begin: '#', + end: '\\d+', + illegal: '\\W' + } + ] }, + { + className: 'type', + begin: '::\\s*', + end: LASSO_IDENT_RE, + illegal: '\\W' + }, + { + className: 'params', + variants: [ + { + begin: '-(?!infinity)' + LASSO_IDENT_RE, + relevance: 0 + }, + { begin: '(\\.\\.\\.)' } + ] + }, + { + begin: /(->|\.)\s*/, + relevance: 0, + contains: [ LASSO_DATAMEMBER ] + }, + { + className: 'class', + beginKeywords: 'define', + returnEnd: true, + end: '\\(|=>', + contains: [ hljs.inherit(hljs.TITLE_MODE, { begin: LASSO_IDENT_RE + '(=(?!>))?|[-+*/%](?!>)' }) ] + } + ]; + return { + name: 'Lasso', + aliases: [ + 'ls', + 'lassoscript' + ], + case_insensitive: true, + keywords: LASSO_KEYWORDS, + contains: [ + { + className: 'meta', + begin: LASSO_CLOSE_RE, + relevance: 0, + starts: { // markup + end: '\\[|' + LASSO_ANGLE_RE, + returnEnd: true, + relevance: 0, + contains: [ HTML_COMMENT ] + } + }, + LASSO_NOPROCESS, + LASSO_START, + { + className: 'meta', + begin: '\\[no_square_brackets', + starts: { + end: '\\[/no_square_brackets\\]', // not implemented in the language + keywords: LASSO_KEYWORDS, + contains: [ + { + className: 'meta', + begin: LASSO_CLOSE_RE, + relevance: 0, + starts: { + end: '\\[noprocess\\]|' + LASSO_ANGLE_RE, + returnEnd: true, + contains: [ HTML_COMMENT ] + } + }, + LASSO_NOPROCESS, + LASSO_START + ].concat(LASSO_CODE) + } + }, + { + className: 'meta', + begin: '\\[', + relevance: 0 + }, + { + className: 'meta', + begin: '^#!', + end: 'lasso9$', + relevance: 10 + } + ].concat(LASSO_CODE) + }; +} + +export { lasso as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/lasso.js.js b/frontend/node_modules/highlight.js/es/languages/lasso.js.js new file mode 100644 index 0000000..97e2e24 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/lasso.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/lasso" instead of "highlight.js/lib/languages/lasso.js"' + ); + } + } + emitWarning(); + import lang from './lasso.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/latex.js b/frontend/node_modules/highlight.js/es/languages/latex.js new file mode 100644 index 0000000..b61f6d7 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/latex.js @@ -0,0 +1,278 @@ +/* +Language: LaTeX +Author: Benedikt Wilde +Website: https://www.latex-project.org +Category: markup +*/ + +/** @type LanguageFn */ +function latex(hljs) { + const regex = hljs.regex; + const KNOWN_CONTROL_WORDS = regex.either(...[ + '(?:NeedsTeXFormat|RequirePackage|GetIdInfo)', + 'Provides(?:Expl)?(?:Package|Class|File)', + '(?:DeclareOption|ProcessOptions)', + '(?:documentclass|usepackage|input|include)', + 'makeat(?:letter|other)', + 'ExplSyntax(?:On|Off)', + '(?:new|renew|provide)?command', + '(?:re)newenvironment', + '(?:New|Renew|Provide|Declare)(?:Expandable)?DocumentCommand', + '(?:New|Renew|Provide|Declare)DocumentEnvironment', + '(?:(?:e|g|x)?def|let)', + '(?:begin|end)', + '(?:part|chapter|(?:sub){0,2}section|(?:sub)?paragraph)', + 'caption', + '(?:label|(?:eq|page|name)?ref|(?:paren|foot|super)?cite)', + '(?:alpha|beta|[Gg]amma|[Dd]elta|(?:var)?epsilon|zeta|eta|[Tt]heta|vartheta)', + '(?:iota|(?:var)?kappa|[Ll]ambda|mu|nu|[Xx]i|[Pp]i|varpi|(?:var)rho)', + '(?:[Ss]igma|varsigma|tau|[Uu]psilon|[Pp]hi|varphi|chi|[Pp]si|[Oo]mega)', + '(?:frac|sum|prod|lim|infty|times|sqrt|leq|geq|left|right|middle|[bB]igg?)', + '(?:[lr]angle|q?quad|[lcvdi]?dots|d?dot|hat|tilde|bar)' + ].map(word => word + '(?![a-zA-Z@:_])')); + const L3_REGEX = new RegExp([ + // A function \module_function_name:signature or \__module_function_name:signature, + // where both module and function_name need at least two characters and + // function_name may contain single underscores. + '(?:__)?[a-zA-Z]{2,}_[a-zA-Z](?:_?[a-zA-Z])+:[a-zA-Z]*', + // A variable \scope_module_and_name_type or \scope__module_ane_name_type, + // where scope is one of l, g or c, type needs at least two characters + // and module_and_name may contain single underscores. + '[lgc]__?[a-zA-Z](?:_?[a-zA-Z])*_[a-zA-Z]{2,}', + // A quark \q_the_name or \q__the_name or + // scan mark \s_the_name or \s__vthe_name, + // where variable_name needs at least two characters and + // may contain single underscores. + '[qs]__?[a-zA-Z](?:_?[a-zA-Z])+', + // Other LaTeX3 macro names that are not covered by the three rules above. + 'use(?:_i)?:[a-zA-Z]*', + '(?:else|fi|or):', + '(?:if|cs|exp):w', + '(?:hbox|vbox):n', + '::[a-zA-Z]_unbraced', + '::[a-zA-Z:]' + ].map(pattern => pattern + '(?![a-zA-Z:_])').join('|')); + const L2_VARIANTS = [ + { begin: /[a-zA-Z@]+/ }, // control word + { begin: /[^a-zA-Z@]?/ } // control symbol + ]; + const DOUBLE_CARET_VARIANTS = [ + { begin: /\^{6}[0-9a-f]{6}/ }, + { begin: /\^{5}[0-9a-f]{5}/ }, + { begin: /\^{4}[0-9a-f]{4}/ }, + { begin: /\^{3}[0-9a-f]{3}/ }, + { begin: /\^{2}[0-9a-f]{2}/ }, + { begin: /\^{2}[\u0000-\u007f]/ } + ]; + const CONTROL_SEQUENCE = { + className: 'keyword', + begin: /\\/, + relevance: 0, + contains: [ + { + endsParent: true, + begin: KNOWN_CONTROL_WORDS + }, + { + endsParent: true, + begin: L3_REGEX + }, + { + endsParent: true, + variants: DOUBLE_CARET_VARIANTS + }, + { + endsParent: true, + relevance: 0, + variants: L2_VARIANTS + } + ] + }; + const MACRO_PARAM = { + className: 'params', + relevance: 0, + begin: /#+\d?/ + }; + const DOUBLE_CARET_CHAR = { + // relevance: 1 + variants: DOUBLE_CARET_VARIANTS }; + const SPECIAL_CATCODE = { + className: 'built_in', + relevance: 0, + begin: /[$&^_]/ + }; + const MAGIC_COMMENT = { + className: 'meta', + begin: /% ?!(T[eE]X|tex|BIB|bib)/, + end: '$', + relevance: 10 + }; + const COMMENT = hljs.COMMENT( + '%', + '$', + { relevance: 0 } + ); + const EVERYTHING_BUT_VERBATIM = [ + CONTROL_SEQUENCE, + MACRO_PARAM, + DOUBLE_CARET_CHAR, + SPECIAL_CATCODE, + MAGIC_COMMENT, + COMMENT + ]; + const BRACE_GROUP_NO_VERBATIM = { + begin: /\{/, + end: /\}/, + relevance: 0, + contains: [ + 'self', + ...EVERYTHING_BUT_VERBATIM + ] + }; + const ARGUMENT_BRACES = hljs.inherit( + BRACE_GROUP_NO_VERBATIM, + { + relevance: 0, + endsParent: true, + contains: [ + BRACE_GROUP_NO_VERBATIM, + ...EVERYTHING_BUT_VERBATIM + ] + } + ); + const ARGUMENT_BRACKETS = { + begin: /\[/, + end: /\]/, + endsParent: true, + relevance: 0, + contains: [ + BRACE_GROUP_NO_VERBATIM, + ...EVERYTHING_BUT_VERBATIM + ] + }; + const SPACE_GOBBLER = { + begin: /\s+/, + relevance: 0 + }; + const ARGUMENT_M = [ ARGUMENT_BRACES ]; + const ARGUMENT_O = [ ARGUMENT_BRACKETS ]; + const ARGUMENT_AND_THEN = function(arg, starts_mode) { + return { + contains: [ SPACE_GOBBLER ], + starts: { + relevance: 0, + contains: arg, + starts: starts_mode + } + }; + }; + const CSNAME = function(csname, starts_mode) { + return { + begin: '\\\\' + csname + '(?![a-zA-Z@:_])', + keywords: { + $pattern: /\\[a-zA-Z]+/, + keyword: '\\' + csname + }, + relevance: 0, + contains: [ SPACE_GOBBLER ], + starts: starts_mode + }; + }; + const BEGIN_ENV = function(envname, starts_mode) { + return hljs.inherit( + { + begin: '\\\\begin(?=[ \t]*(\\r?\\n[ \t]*)?\\{' + envname + '\\})', + keywords: { + $pattern: /\\[a-zA-Z]+/, + keyword: '\\begin' + }, + relevance: 0, + }, + ARGUMENT_AND_THEN(ARGUMENT_M, starts_mode) + ); + }; + const VERBATIM_DELIMITED_EQUAL = (innerName = "string") => { + return hljs.END_SAME_AS_BEGIN({ + className: innerName, + begin: /(.|\r?\n)/, + end: /(.|\r?\n)/, + excludeBegin: true, + excludeEnd: true, + endsParent: true + }); + }; + const VERBATIM_DELIMITED_ENV = function(envname) { + return { + className: 'string', + end: '(?=\\\\end\\{' + envname + '\\})' + }; + }; + + const VERBATIM_DELIMITED_BRACES = (innerName = "string") => { + return { + relevance: 0, + begin: /\{/, + starts: { + endsParent: true, + contains: [ + { + className: innerName, + end: /(?=\})/, + endsParent: true, + contains: [ + { + begin: /\{/, + end: /\}/, + relevance: 0, + contains: [ "self" ] + } + ], + } + ] + } + }; + }; + const VERBATIM = [ + ...[ + 'verb', + 'lstinline' + ].map(csname => CSNAME(csname, { contains: [ VERBATIM_DELIMITED_EQUAL() ] })), + CSNAME('mint', ARGUMENT_AND_THEN(ARGUMENT_M, { contains: [ VERBATIM_DELIMITED_EQUAL() ] })), + CSNAME('mintinline', ARGUMENT_AND_THEN(ARGUMENT_M, { contains: [ + VERBATIM_DELIMITED_BRACES(), + VERBATIM_DELIMITED_EQUAL() + ] })), + CSNAME('url', { contains: [ + VERBATIM_DELIMITED_BRACES("link"), + VERBATIM_DELIMITED_BRACES("link") + ] }), + CSNAME('hyperref', { contains: [ VERBATIM_DELIMITED_BRACES("link") ] }), + CSNAME('href', ARGUMENT_AND_THEN(ARGUMENT_O, { contains: [ VERBATIM_DELIMITED_BRACES("link") ] })), + ...[].concat(...[ + '', + '\\*' + ].map(suffix => [ + BEGIN_ENV('verbatim' + suffix, VERBATIM_DELIMITED_ENV('verbatim' + suffix)), + BEGIN_ENV('filecontents' + suffix, ARGUMENT_AND_THEN(ARGUMENT_M, VERBATIM_DELIMITED_ENV('filecontents' + suffix))), + ...[ + '', + 'B', + 'L' + ].map(prefix => + BEGIN_ENV(prefix + 'Verbatim' + suffix, ARGUMENT_AND_THEN(ARGUMENT_O, VERBATIM_DELIMITED_ENV(prefix + 'Verbatim' + suffix))) + ) + ])), + BEGIN_ENV('minted', ARGUMENT_AND_THEN(ARGUMENT_O, ARGUMENT_AND_THEN(ARGUMENT_M, VERBATIM_DELIMITED_ENV('minted')))), + ]; + + return { + name: 'LaTeX', + aliases: [ 'tex' ], + contains: [ + ...VERBATIM, + ...EVERYTHING_BUT_VERBATIM + ] + }; +} + +export { latex as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/latex.js.js b/frontend/node_modules/highlight.js/es/languages/latex.js.js new file mode 100644 index 0000000..938ae5c --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/latex.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/latex" instead of "highlight.js/lib/languages/latex.js"' + ); + } + } + emitWarning(); + import lang from './latex.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/ldif.js b/frontend/node_modules/highlight.js/es/languages/ldif.js new file mode 100644 index 0000000..cca0538 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ldif.js @@ -0,0 +1,31 @@ +/* +Language: LDIF +Contributors: Jacob Childress +Category: enterprise, config +Website: https://en.wikipedia.org/wiki/LDAP_Data_Interchange_Format +*/ + +/** @type LanguageFn */ +function ldif(hljs) { + return { + name: 'LDIF', + contains: [ + { + className: 'attribute', + match: '^dn(?=:)', + relevance: 10 + }, + { + className: 'attribute', + match: '^\\w+(?=:)' + }, + { + className: 'literal', + match: '^-' + }, + hljs.HASH_COMMENT_MODE + ] + }; +} + +export { ldif as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/ldif.js.js b/frontend/node_modules/highlight.js/es/languages/ldif.js.js new file mode 100644 index 0000000..4ee4894 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ldif.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/ldif" instead of "highlight.js/lib/languages/ldif.js"' + ); + } + } + emitWarning(); + import lang from './ldif.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/leaf.js b/frontend/node_modules/highlight.js/es/languages/leaf.js new file mode 100644 index 0000000..c865b3e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/leaf.js @@ -0,0 +1,97 @@ +/* +Language: Leaf +Description: A Swift-based templating language created for the Vapor project. +Website: https://docs.vapor.codes/leaf/overview +Category: template +*/ + +function leaf(hljs) { + const IDENT = /([A-Za-z_][A-Za-z_0-9]*)?/; + const LITERALS = [ + 'true', + 'false', + 'in' + ]; + const PARAMS = { + scope: 'params', + begin: /\(/, + end: /\)(?=\:?)/, + endsParent: true, + relevance: 7, + contains: [ + { + scope: 'string', + begin: '"', + end: '"' + }, + { + scope: 'keyword', + match: LITERALS.join("|"), + }, + { + scope: 'variable', + match: /[A-Za-z_][A-Za-z_0-9]*/ + }, + { + scope: 'operator', + match: /\+|\-|\*|\/|\%|\=\=|\=|\!|\>|\<|\&\&|\|\|/ + } + ] + }; + const INSIDE_DISPATCH = { + match: [ + IDENT, + /(?=\()/, + ], + scope: { + 1: "keyword" + }, + contains: [ PARAMS ] + }; + PARAMS.contains.unshift(INSIDE_DISPATCH); + return { + name: 'Leaf', + contains: [ + // #ident(): + { + match: [ + /#+/, + IDENT, + /(?=\()/, + ], + scope: { + 1: "punctuation", + 2: "keyword" + }, + // will start up after the ending `)` match from line ~44 + // just to grab the trailing `:` if we can match it + starts: { + contains: [ + { + match: /\:/, + scope: "punctuation" + } + ] + }, + contains: [ + PARAMS + ], + }, + // #ident or #ident: + { + match: [ + /#+/, + IDENT, + /:?/, + ], + scope: { + 1: "punctuation", + 2: "keyword", + 3: "punctuation" + } + }, + ] + }; +} + +export { leaf as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/leaf.js.js b/frontend/node_modules/highlight.js/es/languages/leaf.js.js new file mode 100644 index 0000000..6200dc2 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/leaf.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/leaf" instead of "highlight.js/lib/languages/leaf.js"' + ); + } + } + emitWarning(); + import lang from './leaf.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/less.js b/frontend/node_modules/highlight.js/es/languages/less.js new file mode 100644 index 0000000..f54f590 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/less.js @@ -0,0 +1,1050 @@ +const MODES = (hljs) => { + return { + IMPORTANT: { + scope: 'meta', + begin: '!important' + }, + BLOCK_COMMENT: hljs.C_BLOCK_COMMENT_MODE, + HEXCOLOR: { + scope: 'number', + begin: /#(([0-9a-fA-F]{3,4})|(([0-9a-fA-F]{2}){3,4}))\b/ + }, + FUNCTION_DISPATCH: { + className: "built_in", + begin: /[\w-]+(?=\()/ + }, + ATTRIBUTE_SELECTOR_MODE: { + scope: 'selector-attr', + begin: /\[/, + end: /\]/, + illegal: '$', + contains: [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE + ] + }, + CSS_NUMBER_MODE: { + scope: 'number', + begin: hljs.NUMBER_RE + '(' + + '%|em|ex|ch|rem' + + '|vw|vh|vmin|vmax' + + '|cm|mm|in|pt|pc|px' + + '|deg|grad|rad|turn' + + '|s|ms' + + '|Hz|kHz' + + '|dpi|dpcm|dppx' + + ')?', + relevance: 0 + }, + CSS_VARIABLE: { + className: "attr", + begin: /--[A-Za-z_][A-Za-z0-9_-]*/ + } + }; +}; + +const HTML_TAGS = [ + 'a', + 'abbr', + 'address', + 'article', + 'aside', + 'audio', + 'b', + 'blockquote', + 'body', + 'button', + 'canvas', + 'caption', + 'cite', + 'code', + 'dd', + 'del', + 'details', + 'dfn', + 'div', + 'dl', + 'dt', + 'em', + 'fieldset', + 'figcaption', + 'figure', + 'footer', + 'form', + 'h1', + 'h2', + 'h3', + 'h4', + 'h5', + 'h6', + 'header', + 'hgroup', + 'html', + 'i', + 'iframe', + 'img', + 'input', + 'ins', + 'kbd', + 'label', + 'legend', + 'li', + 'main', + 'mark', + 'menu', + 'nav', + 'object', + 'ol', + 'optgroup', + 'option', + 'p', + 'picture', + 'q', + 'quote', + 'samp', + 'section', + 'select', + 'source', + 'span', + 'strong', + 'summary', + 'sup', + 'table', + 'tbody', + 'td', + 'textarea', + 'tfoot', + 'th', + 'thead', + 'time', + 'tr', + 'ul', + 'var', + 'video' +]; + +const SVG_TAGS = [ + 'defs', + 'g', + 'marker', + 'mask', + 'pattern', + 'svg', + 'switch', + 'symbol', + 'feBlend', + 'feColorMatrix', + 'feComponentTransfer', + 'feComposite', + 'feConvolveMatrix', + 'feDiffuseLighting', + 'feDisplacementMap', + 'feFlood', + 'feGaussianBlur', + 'feImage', + 'feMerge', + 'feMorphology', + 'feOffset', + 'feSpecularLighting', + 'feTile', + 'feTurbulence', + 'linearGradient', + 'radialGradient', + 'stop', + 'circle', + 'ellipse', + 'image', + 'line', + 'path', + 'polygon', + 'polyline', + 'rect', + 'text', + 'use', + 'textPath', + 'tspan', + 'foreignObject', + 'clipPath' +]; + +const TAGS = [ + ...HTML_TAGS, + ...SVG_TAGS, +]; + +// Sorting, then reversing makes sure longer attributes/elements like +// `font-weight` are matched fully instead of getting false positives on say `font` + +const MEDIA_FEATURES = [ + 'any-hover', + 'any-pointer', + 'aspect-ratio', + 'color', + 'color-gamut', + 'color-index', + 'device-aspect-ratio', + 'device-height', + 'device-width', + 'display-mode', + 'forced-colors', + 'grid', + 'height', + 'hover', + 'inverted-colors', + 'monochrome', + 'orientation', + 'overflow-block', + 'overflow-inline', + 'pointer', + 'prefers-color-scheme', + 'prefers-contrast', + 'prefers-reduced-motion', + 'prefers-reduced-transparency', + 'resolution', + 'scan', + 'scripting', + 'update', + 'width', + // TODO: find a better solution? + 'min-width', + 'max-width', + 'min-height', + 'max-height' +].sort().reverse(); + +// https://developer.mozilla.org/en-US/docs/Web/CSS/Pseudo-classes +const PSEUDO_CLASSES = [ + 'active', + 'any-link', + 'blank', + 'checked', + 'current', + 'default', + 'defined', + 'dir', // dir() + 'disabled', + 'drop', + 'empty', + 'enabled', + 'first', + 'first-child', + 'first-of-type', + 'fullscreen', + 'future', + 'focus', + 'focus-visible', + 'focus-within', + 'has', // has() + 'host', // host or host() + 'host-context', // host-context() + 'hover', + 'indeterminate', + 'in-range', + 'invalid', + 'is', // is() + 'lang', // lang() + 'last-child', + 'last-of-type', + 'left', + 'link', + 'local-link', + 'not', // not() + 'nth-child', // nth-child() + 'nth-col', // nth-col() + 'nth-last-child', // nth-last-child() + 'nth-last-col', // nth-last-col() + 'nth-last-of-type', //nth-last-of-type() + 'nth-of-type', //nth-of-type() + 'only-child', + 'only-of-type', + 'optional', + 'out-of-range', + 'past', + 'placeholder-shown', + 'read-only', + 'read-write', + 'required', + 'right', + 'root', + 'scope', + 'target', + 'target-within', + 'user-invalid', + 'valid', + 'visited', + 'where' // where() +].sort().reverse(); + +// https://developer.mozilla.org/en-US/docs/Web/CSS/Pseudo-elements +const PSEUDO_ELEMENTS = [ + 'after', + 'backdrop', + 'before', + 'cue', + 'cue-region', + 'first-letter', + 'first-line', + 'grammar-error', + 'marker', + 'part', + 'placeholder', + 'selection', + 'slotted', + 'spelling-error' +].sort().reverse(); + +const ATTRIBUTES = [ + 'accent-color', + 'align-content', + 'align-items', + 'align-self', + 'alignment-baseline', + 'all', + 'anchor-name', + 'animation', + 'animation-composition', + 'animation-delay', + 'animation-direction', + 'animation-duration', + 'animation-fill-mode', + 'animation-iteration-count', + 'animation-name', + 'animation-play-state', + 'animation-range', + 'animation-range-end', + 'animation-range-start', + 'animation-timeline', + 'animation-timing-function', + 'appearance', + 'aspect-ratio', + 'backdrop-filter', + 'backface-visibility', + 'background', + 'background-attachment', + 'background-blend-mode', + 'background-clip', + 'background-color', + 'background-image', + 'background-origin', + 'background-position', + 'background-position-x', + 'background-position-y', + 'background-repeat', + 'background-size', + 'baseline-shift', + 'block-size', + 'border', + 'border-block', + 'border-block-color', + 'border-block-end', + 'border-block-end-color', + 'border-block-end-style', + 'border-block-end-width', + 'border-block-start', + 'border-block-start-color', + 'border-block-start-style', + 'border-block-start-width', + 'border-block-style', + 'border-block-width', + 'border-bottom', + 'border-bottom-color', + 'border-bottom-left-radius', + 'border-bottom-right-radius', + 'border-bottom-style', + 'border-bottom-width', + 'border-collapse', + 'border-color', + 'border-end-end-radius', + 'border-end-start-radius', + 'border-image', + 'border-image-outset', + 'border-image-repeat', + 'border-image-slice', + 'border-image-source', + 'border-image-width', + 'border-inline', + 'border-inline-color', + 'border-inline-end', + 'border-inline-end-color', + 'border-inline-end-style', + 'border-inline-end-width', + 'border-inline-start', + 'border-inline-start-color', + 'border-inline-start-style', + 'border-inline-start-width', + 'border-inline-style', + 'border-inline-width', + 'border-left', + 'border-left-color', + 'border-left-style', + 'border-left-width', + 'border-radius', + 'border-right', + 'border-right-color', + 'border-right-style', + 'border-right-width', + 'border-spacing', + 'border-start-end-radius', + 'border-start-start-radius', + 'border-style', + 'border-top', + 'border-top-color', + 'border-top-left-radius', + 'border-top-right-radius', + 'border-top-style', + 'border-top-width', + 'border-width', + 'bottom', + 'box-align', + 'box-decoration-break', + 'box-direction', + 'box-flex', + 'box-flex-group', + 'box-lines', + 'box-ordinal-group', + 'box-orient', + 'box-pack', + 'box-shadow', + 'box-sizing', + 'break-after', + 'break-before', + 'break-inside', + 'caption-side', + 'caret-color', + 'clear', + 'clip', + 'clip-path', + 'clip-rule', + 'color', + 'color-interpolation', + 'color-interpolation-filters', + 'color-profile', + 'color-rendering', + 'color-scheme', + 'column-count', + 'column-fill', + 'column-gap', + 'column-rule', + 'column-rule-color', + 'column-rule-style', + 'column-rule-width', + 'column-span', + 'column-width', + 'columns', + 'contain', + 'contain-intrinsic-block-size', + 'contain-intrinsic-height', + 'contain-intrinsic-inline-size', + 'contain-intrinsic-size', + 'contain-intrinsic-width', + 'container', + 'container-name', + 'container-type', + 'content', + 'content-visibility', + 'counter-increment', + 'counter-reset', + 'counter-set', + 'cue', + 'cue-after', + 'cue-before', + 'cursor', + 'cx', + 'cy', + 'direction', + 'display', + 'dominant-baseline', + 'empty-cells', + 'enable-background', + 'field-sizing', + 'fill', + 'fill-opacity', + 'fill-rule', + 'filter', + 'flex', + 'flex-basis', + 'flex-direction', + 'flex-flow', + 'flex-grow', + 'flex-shrink', + 'flex-wrap', + 'float', + 'flood-color', + 'flood-opacity', + 'flow', + 'font', + 'font-display', + 'font-family', + 'font-feature-settings', + 'font-kerning', + 'font-language-override', + 'font-optical-sizing', + 'font-palette', + 'font-size', + 'font-size-adjust', + 'font-smooth', + 'font-smoothing', + 'font-stretch', + 'font-style', + 'font-synthesis', + 'font-synthesis-position', + 'font-synthesis-small-caps', + 'font-synthesis-style', + 'font-synthesis-weight', + 'font-variant', + 'font-variant-alternates', + 'font-variant-caps', + 'font-variant-east-asian', + 'font-variant-emoji', + 'font-variant-ligatures', + 'font-variant-numeric', + 'font-variant-position', + 'font-variation-settings', + 'font-weight', + 'forced-color-adjust', + 'gap', + 'glyph-orientation-horizontal', + 'glyph-orientation-vertical', + 'grid', + 'grid-area', + 'grid-auto-columns', + 'grid-auto-flow', + 'grid-auto-rows', + 'grid-column', + 'grid-column-end', + 'grid-column-start', + 'grid-gap', + 'grid-row', + 'grid-row-end', + 'grid-row-start', + 'grid-template', + 'grid-template-areas', + 'grid-template-columns', + 'grid-template-rows', + 'hanging-punctuation', + 'height', + 'hyphenate-character', + 'hyphenate-limit-chars', + 'hyphens', + 'icon', + 'image-orientation', + 'image-rendering', + 'image-resolution', + 'ime-mode', + 'initial-letter', + 'initial-letter-align', + 'inline-size', + 'inset', + 'inset-area', + 'inset-block', + 'inset-block-end', + 'inset-block-start', + 'inset-inline', + 'inset-inline-end', + 'inset-inline-start', + 'isolation', + 'justify-content', + 'justify-items', + 'justify-self', + 'kerning', + 'left', + 'letter-spacing', + 'lighting-color', + 'line-break', + 'line-height', + 'line-height-step', + 'list-style', + 'list-style-image', + 'list-style-position', + 'list-style-type', + 'margin', + 'margin-block', + 'margin-block-end', + 'margin-block-start', + 'margin-bottom', + 'margin-inline', + 'margin-inline-end', + 'margin-inline-start', + 'margin-left', + 'margin-right', + 'margin-top', + 'margin-trim', + 'marker', + 'marker-end', + 'marker-mid', + 'marker-start', + 'marks', + 'mask', + 'mask-border', + 'mask-border-mode', + 'mask-border-outset', + 'mask-border-repeat', + 'mask-border-slice', + 'mask-border-source', + 'mask-border-width', + 'mask-clip', + 'mask-composite', + 'mask-image', + 'mask-mode', + 'mask-origin', + 'mask-position', + 'mask-repeat', + 'mask-size', + 'mask-type', + 'masonry-auto-flow', + 'math-depth', + 'math-shift', + 'math-style', + 'max-block-size', + 'max-height', + 'max-inline-size', + 'max-width', + 'min-block-size', + 'min-height', + 'min-inline-size', + 'min-width', + 'mix-blend-mode', + 'nav-down', + 'nav-index', + 'nav-left', + 'nav-right', + 'nav-up', + 'none', + 'normal', + 'object-fit', + 'object-position', + 'offset', + 'offset-anchor', + 'offset-distance', + 'offset-path', + 'offset-position', + 'offset-rotate', + 'opacity', + 'order', + 'orphans', + 'outline', + 'outline-color', + 'outline-offset', + 'outline-style', + 'outline-width', + 'overflow', + 'overflow-anchor', + 'overflow-block', + 'overflow-clip-margin', + 'overflow-inline', + 'overflow-wrap', + 'overflow-x', + 'overflow-y', + 'overlay', + 'overscroll-behavior', + 'overscroll-behavior-block', + 'overscroll-behavior-inline', + 'overscroll-behavior-x', + 'overscroll-behavior-y', + 'padding', + 'padding-block', + 'padding-block-end', + 'padding-block-start', + 'padding-bottom', + 'padding-inline', + 'padding-inline-end', + 'padding-inline-start', + 'padding-left', + 'padding-right', + 'padding-top', + 'page', + 'page-break-after', + 'page-break-before', + 'page-break-inside', + 'paint-order', + 'pause', + 'pause-after', + 'pause-before', + 'perspective', + 'perspective-origin', + 'place-content', + 'place-items', + 'place-self', + 'pointer-events', + 'position', + 'position-anchor', + 'position-visibility', + 'print-color-adjust', + 'quotes', + 'r', + 'resize', + 'rest', + 'rest-after', + 'rest-before', + 'right', + 'rotate', + 'row-gap', + 'ruby-align', + 'ruby-position', + 'scale', + 'scroll-behavior', + 'scroll-margin', + 'scroll-margin-block', + 'scroll-margin-block-end', + 'scroll-margin-block-start', + 'scroll-margin-bottom', + 'scroll-margin-inline', + 'scroll-margin-inline-end', + 'scroll-margin-inline-start', + 'scroll-margin-left', + 'scroll-margin-right', + 'scroll-margin-top', + 'scroll-padding', + 'scroll-padding-block', + 'scroll-padding-block-end', + 'scroll-padding-block-start', + 'scroll-padding-bottom', + 'scroll-padding-inline', + 'scroll-padding-inline-end', + 'scroll-padding-inline-start', + 'scroll-padding-left', + 'scroll-padding-right', + 'scroll-padding-top', + 'scroll-snap-align', + 'scroll-snap-stop', + 'scroll-snap-type', + 'scroll-timeline', + 'scroll-timeline-axis', + 'scroll-timeline-name', + 'scrollbar-color', + 'scrollbar-gutter', + 'scrollbar-width', + 'shape-image-threshold', + 'shape-margin', + 'shape-outside', + 'shape-rendering', + 'speak', + 'speak-as', + 'src', // @font-face + 'stop-color', + 'stop-opacity', + 'stroke', + 'stroke-dasharray', + 'stroke-dashoffset', + 'stroke-linecap', + 'stroke-linejoin', + 'stroke-miterlimit', + 'stroke-opacity', + 'stroke-width', + 'tab-size', + 'table-layout', + 'text-align', + 'text-align-all', + 'text-align-last', + 'text-anchor', + 'text-combine-upright', + 'text-decoration', + 'text-decoration-color', + 'text-decoration-line', + 'text-decoration-skip', + 'text-decoration-skip-ink', + 'text-decoration-style', + 'text-decoration-thickness', + 'text-emphasis', + 'text-emphasis-color', + 'text-emphasis-position', + 'text-emphasis-style', + 'text-indent', + 'text-justify', + 'text-orientation', + 'text-overflow', + 'text-rendering', + 'text-shadow', + 'text-size-adjust', + 'text-transform', + 'text-underline-offset', + 'text-underline-position', + 'text-wrap', + 'text-wrap-mode', + 'text-wrap-style', + 'timeline-scope', + 'top', + 'touch-action', + 'transform', + 'transform-box', + 'transform-origin', + 'transform-style', + 'transition', + 'transition-behavior', + 'transition-delay', + 'transition-duration', + 'transition-property', + 'transition-timing-function', + 'translate', + 'unicode-bidi', + 'user-modify', + 'user-select', + 'vector-effect', + 'vertical-align', + 'view-timeline', + 'view-timeline-axis', + 'view-timeline-inset', + 'view-timeline-name', + 'view-transition-name', + 'visibility', + 'voice-balance', + 'voice-duration', + 'voice-family', + 'voice-pitch', + 'voice-range', + 'voice-rate', + 'voice-stress', + 'voice-volume', + 'white-space', + 'white-space-collapse', + 'widows', + 'width', + 'will-change', + 'word-break', + 'word-spacing', + 'word-wrap', + 'writing-mode', + 'x', + 'y', + 'z-index', + 'zoom' +].sort().reverse(); + +// some grammars use them all as a single group +const PSEUDO_SELECTORS = PSEUDO_CLASSES.concat(PSEUDO_ELEMENTS).sort().reverse(); + +/* +Language: Less +Description: It's CSS, with just a little more. +Author: Max Mikhailov +Website: http://lesscss.org +Category: common, css, web +*/ + + +/** @type LanguageFn */ +function less(hljs) { + const modes = MODES(hljs); + const PSEUDO_SELECTORS$1 = PSEUDO_SELECTORS; + + const AT_MODIFIERS = "and or not only"; + const IDENT_RE = '[\\w-]+'; // yes, Less identifiers may begin with a digit + const INTERP_IDENT_RE = '(' + IDENT_RE + '|@\\{' + IDENT_RE + '\\})'; + + /* Generic Modes */ + + const RULES = []; const VALUE_MODES = []; // forward def. for recursive modes + + const STRING_MODE = function(c) { + return { + // Less strings are not multiline (also include '~' for more consistent coloring of "escaped" strings) + className: 'string', + begin: '~?' + c + '.*?' + c + }; + }; + + const IDENT_MODE = function(name, begin, relevance) { + return { + className: name, + begin: begin, + relevance: relevance + }; + }; + + const AT_KEYWORDS = { + $pattern: /[a-z-]+/, + keyword: AT_MODIFIERS, + attribute: MEDIA_FEATURES.join(" ") + }; + + const PARENS_MODE = { + // used only to properly balance nested parens inside mixin call, def. arg list + begin: '\\(', + end: '\\)', + contains: VALUE_MODES, + keywords: AT_KEYWORDS, + relevance: 0 + }; + + // generic Less highlighter (used almost everywhere except selectors): + VALUE_MODES.push( + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + STRING_MODE("'"), + STRING_MODE('"'), + modes.CSS_NUMBER_MODE, // fixme: it does not include dot for numbers like .5em :( + { + begin: '(url|data-uri)\\(', + starts: { + className: 'string', + end: '[\\)\\n]', + excludeEnd: true + } + }, + modes.HEXCOLOR, + PARENS_MODE, + IDENT_MODE('variable', '@@?' + IDENT_RE, 10), + IDENT_MODE('variable', '@\\{' + IDENT_RE + '\\}'), + IDENT_MODE('built_in', '~?`[^`]*?`'), // inline javascript (or whatever host language) *multiline* string + { // @media features (it’s here to not duplicate things in AT_RULE_MODE with extra PARENS_MODE overriding): + className: 'attribute', + begin: IDENT_RE + '\\s*:', + end: ':', + returnBegin: true, + excludeEnd: true + }, + modes.IMPORTANT, + { beginKeywords: 'and not' }, + modes.FUNCTION_DISPATCH + ); + + const VALUE_WITH_RULESETS = VALUE_MODES.concat({ + begin: /\{/, + end: /\}/, + contains: RULES + }); + + const MIXIN_GUARD_MODE = { + beginKeywords: 'when', + endsWithParent: true, + contains: [ { beginKeywords: 'and not' } ].concat(VALUE_MODES) // using this form to override VALUE’s 'function' match + }; + + /* Rule-Level Modes */ + + const RULE_MODE = { + begin: INTERP_IDENT_RE + '\\s*:', + returnBegin: true, + end: /[;}]/, + relevance: 0, + contains: [ + { begin: /-(webkit|moz|ms|o)-/ }, + modes.CSS_VARIABLE, + { + className: 'attribute', + begin: '\\b(' + ATTRIBUTES.join('|') + ')\\b', + end: /(?=:)/, + starts: { + endsWithParent: true, + illegal: '[<=$]', + relevance: 0, + contains: VALUE_MODES + } + } + ] + }; + + const AT_RULE_MODE = { + className: 'keyword', + begin: '@(import|media|charset|font-face|(-[a-z]+-)?keyframes|supports|document|namespace|page|viewport|host)\\b', + starts: { + end: '[;{}]', + keywords: AT_KEYWORDS, + returnEnd: true, + contains: VALUE_MODES, + relevance: 0 + } + }; + + // variable definitions and calls + const VAR_RULE_MODE = { + className: 'variable', + variants: [ + // using more strict pattern for higher relevance to increase chances of Less detection. + // this is *the only* Less specific statement used in most of the sources, so... + // (we’ll still often loose to the css-parser unless there's '//' comment, + // simply because 1 variable just can't beat 99 properties :) + { + begin: '@' + IDENT_RE + '\\s*:', + relevance: 15 + }, + { begin: '@' + IDENT_RE } + ], + starts: { + end: '[;}]', + returnEnd: true, + contains: VALUE_WITH_RULESETS + } + }; + + const SELECTOR_MODE = { + // first parse unambiguous selectors (i.e. those not starting with tag) + // then fall into the scary lookahead-discriminator variant. + // this mode also handles mixin definitions and calls + variants: [ + { + begin: '[\\.#:&\\[>]', + end: '[;{}]' // mixin calls end with ';' + }, + { + begin: INTERP_IDENT_RE, + end: /\{/ + } + ], + returnBegin: true, + returnEnd: true, + illegal: '[<=\'$"]', + relevance: 0, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + MIXIN_GUARD_MODE, + IDENT_MODE('keyword', 'all\\b'), + IDENT_MODE('variable', '@\\{' + IDENT_RE + '\\}'), // otherwise it’s identified as tag + + { + begin: '\\b(' + TAGS.join('|') + ')\\b', + className: 'selector-tag' + }, + modes.CSS_NUMBER_MODE, + IDENT_MODE('selector-tag', INTERP_IDENT_RE, 0), + IDENT_MODE('selector-id', '#' + INTERP_IDENT_RE), + IDENT_MODE('selector-class', '\\.' + INTERP_IDENT_RE, 0), + IDENT_MODE('selector-tag', '&', 0), + modes.ATTRIBUTE_SELECTOR_MODE, + { + className: 'selector-pseudo', + begin: ':(' + PSEUDO_CLASSES.join('|') + ')' + }, + { + className: 'selector-pseudo', + begin: ':(:)?(' + PSEUDO_ELEMENTS.join('|') + ')' + }, + { + begin: /\(/, + end: /\)/, + relevance: 0, + contains: VALUE_WITH_RULESETS + }, // argument list of parametric mixins + { begin: '!important' }, // eat !important after mixin call or it will be colored as tag + modes.FUNCTION_DISPATCH + ] + }; + + const PSEUDO_SELECTOR_MODE = { + begin: IDENT_RE + ':(:)?' + `(${PSEUDO_SELECTORS$1.join('|')})`, + returnBegin: true, + contains: [ SELECTOR_MODE ] + }; + + RULES.push( + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + AT_RULE_MODE, + VAR_RULE_MODE, + PSEUDO_SELECTOR_MODE, + RULE_MODE, + SELECTOR_MODE, + MIXIN_GUARD_MODE, + modes.FUNCTION_DISPATCH + ); + + return { + name: 'Less', + case_insensitive: true, + illegal: '[=>\'/<($"]', + contains: RULES + }; +} + +export { less as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/less.js.js b/frontend/node_modules/highlight.js/es/languages/less.js.js new file mode 100644 index 0000000..b7abb03 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/less.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/less" instead of "highlight.js/lib/languages/less.js"' + ); + } + } + emitWarning(); + import lang from './less.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/lisp.js b/frontend/node_modules/highlight.js/es/languages/lisp.js new file mode 100644 index 0000000..2c5538b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/lisp.js @@ -0,0 +1,139 @@ +/* +Language: Lisp +Description: Generic lisp syntax +Author: Vasily Polovnyov +Category: lisp +*/ + +function lisp(hljs) { + const LISP_IDENT_RE = '[a-zA-Z_\\-+\\*\\/<=>&#][a-zA-Z0-9_\\-+*\\/<=>&#!]*'; + const MEC_RE = '\\|[^]*?\\|'; + const LISP_SIMPLE_NUMBER_RE = '(-|\\+)?\\d+(\\.\\d+|\\/\\d+)?((d|e|f|l|s|D|E|F|L|S)(\\+|-)?\\d+)?'; + const LITERAL = { + className: 'literal', + begin: '\\b(t{1}|nil)\\b' + }; + const NUMBER = { + className: 'number', + variants: [ + { + begin: LISP_SIMPLE_NUMBER_RE, + relevance: 0 + }, + { begin: '#(b|B)[0-1]+(/[0-1]+)?' }, + { begin: '#(o|O)[0-7]+(/[0-7]+)?' }, + { begin: '#(x|X)[0-9a-fA-F]+(/[0-9a-fA-F]+)?' }, + { + begin: '#(c|C)\\(' + LISP_SIMPLE_NUMBER_RE + ' +' + LISP_SIMPLE_NUMBER_RE, + end: '\\)' + } + ] + }; + const STRING = hljs.inherit(hljs.QUOTE_STRING_MODE, { illegal: null }); + const COMMENT = hljs.COMMENT( + ';', '$', + { relevance: 0 } + ); + const VARIABLE = { + begin: '\\*', + end: '\\*' + }; + const KEYWORD = { + className: 'symbol', + begin: '[:&]' + LISP_IDENT_RE + }; + const IDENT = { + begin: LISP_IDENT_RE, + relevance: 0 + }; + const MEC = { begin: MEC_RE }; + const QUOTED_LIST = { + begin: '\\(', + end: '\\)', + contains: [ + 'self', + LITERAL, + STRING, + NUMBER, + IDENT + ] + }; + const QUOTED = { + contains: [ + NUMBER, + STRING, + VARIABLE, + KEYWORD, + QUOTED_LIST, + IDENT + ], + variants: [ + { + begin: '[\'`]\\(', + end: '\\)' + }, + { + begin: '\\(quote ', + end: '\\)', + keywords: { name: 'quote' } + }, + { begin: '\'' + MEC_RE } + ] + }; + const QUOTED_ATOM = { variants: [ + { begin: '\'' + LISP_IDENT_RE }, + { begin: '#\'' + LISP_IDENT_RE + '(::' + LISP_IDENT_RE + ')*' } + ] }; + const LIST = { + begin: '\\(\\s*', + end: '\\)' + }; + const BODY = { + endsWithParent: true, + relevance: 0 + }; + LIST.contains = [ + { + className: 'name', + variants: [ + { + begin: LISP_IDENT_RE, + relevance: 0, + }, + { begin: MEC_RE } + ] + }, + BODY + ]; + BODY.contains = [ + QUOTED, + QUOTED_ATOM, + LIST, + LITERAL, + NUMBER, + STRING, + COMMENT, + VARIABLE, + KEYWORD, + MEC, + IDENT + ]; + + return { + name: 'Lisp', + illegal: /\S/, + contains: [ + NUMBER, + hljs.SHEBANG(), + LITERAL, + STRING, + COMMENT, + QUOTED, + QUOTED_ATOM, + LIST, + IDENT + ] + }; +} + +export { lisp as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/lisp.js.js b/frontend/node_modules/highlight.js/es/languages/lisp.js.js new file mode 100644 index 0000000..dd1e4bc --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/lisp.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/lisp" instead of "highlight.js/lib/languages/lisp.js"' + ); + } + } + emitWarning(); + import lang from './lisp.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/livecodeserver.js b/frontend/node_modules/highlight.js/es/languages/livecodeserver.js new file mode 100644 index 0000000..6af162a --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/livecodeserver.js @@ -0,0 +1,173 @@ +/* +Language: LiveCode +Author: Ralf Bitter +Description: Language definition for LiveCode server accounting for revIgniter (a web application framework) characteristics. +Version: 1.1 +Date: 2019-04-17 +Category: enterprise +*/ + +function livecodeserver(hljs) { + const VARIABLE = { + className: 'variable', + variants: [ + { begin: '\\b([gtps][A-Z]{1}[a-zA-Z0-9]*)(\\[.+\\])?(?:\\s*?)' }, + { begin: '\\$_[A-Z]+' } + ], + relevance: 0 + }; + const COMMENT_MODES = [ + hljs.C_BLOCK_COMMENT_MODE, + hljs.HASH_COMMENT_MODE, + hljs.COMMENT('--', '$'), + hljs.COMMENT('[^:]//', '$') + ]; + const TITLE1 = hljs.inherit(hljs.TITLE_MODE, { variants: [ + { begin: '\\b_*rig[A-Z][A-Za-z0-9_\\-]*' }, + { begin: '\\b_[a-z0-9\\-]+' } + ] }); + const TITLE2 = hljs.inherit(hljs.TITLE_MODE, { begin: '\\b([A-Za-z0-9_\\-]+)\\b' }); + return { + name: 'LiveCode', + case_insensitive: false, + keywords: { + keyword: + '$_COOKIE $_FILES $_GET $_GET_BINARY $_GET_RAW $_POST $_POST_BINARY $_POST_RAW $_SESSION $_SERVER ' + + 'codepoint codepoints segment segments codeunit codeunits sentence sentences trueWord trueWords paragraph ' + + 'after byte bytes english the until http forever descending using line real8 with seventh ' + + 'for stdout finally element word words fourth before black ninth sixth characters chars stderr ' + + 'uInt1 uInt1s uInt2 uInt2s stdin string lines relative rel any fifth items from middle mid ' + + 'at else of catch then third it file milliseconds seconds second secs sec int1 int1s int4 ' + + 'int4s internet int2 int2s normal text item last long detailed effective uInt4 uInt4s repeat ' + + 'end repeat URL in try into switch to words https token binfile each tenth as ticks tick ' + + 'system real4 by dateItems without char character ascending eighth whole dateTime numeric short ' + + 'first ftp integer abbreviated abbr abbrev private case while if ' + + 'div mod wrap and or bitAnd bitNot bitOr bitXor among not in a an within ' + + 'contains ends with begins the keys of keys', + literal: + 'SIX TEN FORMFEED NINE ZERO NONE SPACE FOUR FALSE COLON CRLF PI COMMA ENDOFFILE EOF EIGHT FIVE ' + + 'QUOTE EMPTY ONE TRUE RETURN CR LINEFEED RIGHT BACKSLASH NULL SEVEN TAB THREE TWO ' + + 'six ten formfeed nine zero none space four false colon crlf pi comma endoffile eof eight five ' + + 'quote empty one true return cr linefeed right backslash null seven tab three two ' + + 'RIVERSION RISTATE FILE_READ_MODE FILE_WRITE_MODE FILE_WRITE_MODE DIR_WRITE_MODE FILE_READ_UMASK ' + + 'FILE_WRITE_UMASK DIR_READ_UMASK DIR_WRITE_UMASK', + built_in: + 'put abs acos aliasReference annuity arrayDecode arrayEncode asin atan atan2 average avg avgDev base64Decode ' + + 'base64Encode baseConvert binaryDecode binaryEncode byteOffset byteToNum cachedURL cachedURLs charToNum ' + + 'cipherNames codepointOffset codepointProperty codepointToNum codeunitOffset commandNames compound compress ' + + 'constantNames cos date dateFormat decompress difference directories ' + + 'diskSpace DNSServers exp exp1 exp2 exp10 extents files flushEvents folders format functionNames geometricMean global ' + + 'globals hasMemory harmonicMean hostAddress hostAddressToName hostName hostNameToAddress isNumber ISOToMac itemOffset ' + + 'keys len length libURLErrorData libUrlFormData libURLftpCommand libURLLastHTTPHeaders libURLLastRHHeaders ' + + 'libUrlMultipartFormAddPart libUrlMultipartFormData libURLVersion lineOffset ln ln1 localNames log log2 log10 ' + + 'longFilePath lower macToISO matchChunk matchText matrixMultiply max md5Digest median merge messageAuthenticationCode messageDigest millisec ' + + 'millisecs millisecond milliseconds min monthNames nativeCharToNum normalizeText num number numToByte numToChar ' + + 'numToCodepoint numToNativeChar offset open openfiles openProcesses openProcessIDs openSockets ' + + 'paragraphOffset paramCount param params peerAddress pendingMessages platform popStdDev populationStandardDeviation ' + + 'populationVariance popVariance processID random randomBytes replaceText result revCreateXMLTree revCreateXMLTreeFromFile ' + + 'revCurrentRecord revCurrentRecordIsFirst revCurrentRecordIsLast revDatabaseColumnCount revDatabaseColumnIsNull ' + + 'revDatabaseColumnLengths revDatabaseColumnNames revDatabaseColumnNamed revDatabaseColumnNumbered ' + + 'revDatabaseColumnTypes revDatabaseConnectResult revDatabaseCursors revDatabaseID revDatabaseTableNames ' + + 'revDatabaseType revDataFromQuery revdb_closeCursor revdb_columnbynumber revdb_columncount revdb_columnisnull ' + + 'revdb_columnlengths revdb_columnnames revdb_columntypes revdb_commit revdb_connect revdb_connections ' + + 'revdb_connectionerr revdb_currentrecord revdb_cursorconnection revdb_cursorerr revdb_cursors revdb_dbtype ' + + 'revdb_disconnect revdb_execute revdb_iseof revdb_isbof revdb_movefirst revdb_movelast revdb_movenext ' + + 'revdb_moveprev revdb_query revdb_querylist revdb_recordcount revdb_rollback revdb_tablenames ' + + 'revGetDatabaseDriverPath revNumberOfRecords revOpenDatabase revOpenDatabases revQueryDatabase ' + + 'revQueryDatabaseBlob revQueryResult revQueryIsAtStart revQueryIsAtEnd revUnixFromMacPath revXMLAttribute ' + + 'revXMLAttributes revXMLAttributeValues revXMLChildContents revXMLChildNames revXMLCreateTreeFromFileWithNamespaces ' + + 'revXMLCreateTreeWithNamespaces revXMLDataFromXPathQuery revXMLEvaluateXPath revXMLFirstChild revXMLMatchingNode ' + + 'revXMLNextSibling revXMLNodeContents revXMLNumberOfChildren revXMLParent revXMLPreviousSibling ' + + 'revXMLRootNode revXMLRPC_CreateRequest revXMLRPC_Documents revXMLRPC_Error ' + + 'revXMLRPC_GetHost revXMLRPC_GetMethod revXMLRPC_GetParam revXMLText revXMLRPC_Execute ' + + 'revXMLRPC_GetParamCount revXMLRPC_GetParamNode revXMLRPC_GetParamType revXMLRPC_GetPath revXMLRPC_GetPort ' + + 'revXMLRPC_GetProtocol revXMLRPC_GetRequest revXMLRPC_GetResponse revXMLRPC_GetSocket revXMLTree ' + + 'revXMLTrees revXMLValidateDTD revZipDescribeItem revZipEnumerateItems revZipOpenArchives round sampVariance ' + + 'sec secs seconds sentenceOffset sha1Digest shell shortFilePath sin specialFolderPath sqrt standardDeviation statRound ' + + 'stdDev sum sysError systemVersion tan tempName textDecode textEncode tick ticks time to tokenOffset toLower toUpper ' + + 'transpose truewordOffset trunc uniDecode uniEncode upper URLDecode URLEncode URLStatus uuid value variableNames ' + + 'variance version waitDepth weekdayNames wordOffset xsltApplyStylesheet xsltApplyStylesheetFromFile xsltLoadStylesheet ' + + 'xsltLoadStylesheetFromFile add breakpoint cancel clear local variable file word line folder directory URL close socket process ' + + 'combine constant convert create new alias folder directory decrypt delete variable word line folder ' + + 'directory URL dispatch divide do encrypt filter get include intersect kill libURLDownloadToFile ' + + 'libURLFollowHttpRedirects libURLftpUpload libURLftpUploadFile libURLresetAll libUrlSetAuthCallback libURLSetDriver ' + + 'libURLSetCustomHTTPHeaders libUrlSetExpect100 libURLSetFTPListCommand libURLSetFTPMode libURLSetFTPStopTime ' + + 'libURLSetStatusCallback load extension loadedExtensions multiply socket prepare process post seek rel relative read from process rename ' + + 'replace require resetAll resolve revAddXMLNode revAppendXML revCloseCursor revCloseDatabase revCommitDatabase ' + + 'revCopyFile revCopyFolder revCopyXMLNode revDeleteFolder revDeleteXMLNode revDeleteAllXMLTrees ' + + 'revDeleteXMLTree revExecuteSQL revGoURL revInsertXMLNode revMoveFolder revMoveToFirstRecord revMoveToLastRecord ' + + 'revMoveToNextRecord revMoveToPreviousRecord revMoveToRecord revMoveXMLNode revPutIntoXMLNode revRollBackDatabase ' + + 'revSetDatabaseDriverPath revSetXMLAttribute revXMLRPC_AddParam revXMLRPC_DeleteAllDocuments revXMLAddDTD ' + + 'revXMLRPC_Free revXMLRPC_FreeAll revXMLRPC_DeleteDocument revXMLRPC_DeleteParam revXMLRPC_SetHost ' + + 'revXMLRPC_SetMethod revXMLRPC_SetPort revXMLRPC_SetProtocol revXMLRPC_SetSocket revZipAddItemWithData ' + + 'revZipAddItemWithFile revZipAddUncompressedItemWithData revZipAddUncompressedItemWithFile revZipCancel ' + + 'revZipCloseArchive revZipDeleteItem revZipExtractItemToFile revZipExtractItemToVariable revZipSetProgressCallback ' + + 'revZipRenameItem revZipReplaceItemWithData revZipReplaceItemWithFile revZipOpenArchive send set sort split start stop ' + + 'subtract symmetric union unload vectorDotProduct wait write' + }, + contains: [ + VARIABLE, + { + className: 'keyword', + begin: '\\bend\\sif\\b' + }, + { + className: 'function', + beginKeywords: 'function', + end: '$', + contains: [ + VARIABLE, + TITLE2, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.BINARY_NUMBER_MODE, + hljs.C_NUMBER_MODE, + TITLE1 + ] + }, + { + className: 'function', + begin: '\\bend\\s+', + end: '$', + keywords: 'end', + contains: [ + TITLE2, + TITLE1 + ], + relevance: 0 + }, + { + beginKeywords: 'command on', + end: '$', + contains: [ + VARIABLE, + TITLE2, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.BINARY_NUMBER_MODE, + hljs.C_NUMBER_MODE, + TITLE1 + ] + }, + { + className: 'meta', + variants: [ + { + begin: '<\\?(rev|lc|livecode)', + relevance: 10 + }, + { begin: '<\\?' }, + { begin: '\\?>' } + ] + }, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.BINARY_NUMBER_MODE, + hljs.C_NUMBER_MODE, + TITLE1 + ].concat(COMMENT_MODES), + illegal: ';$|^\\[|^=|&|\\{' + }; +} + +export { livecodeserver as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/livecodeserver.js.js b/frontend/node_modules/highlight.js/es/languages/livecodeserver.js.js new file mode 100644 index 0000000..32253c1 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/livecodeserver.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/livecodeserver" instead of "highlight.js/lib/languages/livecodeserver.js"' + ); + } + } + emitWarning(); + import lang from './livecodeserver.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/livescript.js b/frontend/node_modules/highlight.js/es/languages/livescript.js new file mode 100644 index 0000000..a05df0e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/livescript.js @@ -0,0 +1,380 @@ +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", + // It's reached stage 3, which is "recommended for implementation": + "using" +]; +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_INS = [].concat( + BUILT_IN_GLOBALS, + TYPES, + ERROR_TYPES +); + +/* +Language: LiveScript +Author: Taneli Vatanen +Contributors: Jen Evers-Corvina +Origin: coffeescript.js +Description: LiveScript is a programming language that transcompiles to JavaScript. For info about language see http://livescript.net/ +Website: https://livescript.net +Category: scripting +*/ + + +function livescript(hljs) { + const LIVESCRIPT_BUILT_INS = [ + 'npm', + 'print' + ]; + const LIVESCRIPT_LITERALS = [ + 'yes', + 'no', + 'on', + 'off', + 'it', + 'that', + 'void' + ]; + const LIVESCRIPT_KEYWORDS = [ + 'then', + 'unless', + 'until', + 'loop', + 'of', + 'by', + 'when', + 'and', + 'or', + 'is', + 'isnt', + 'not', + 'it', + 'that', + 'otherwise', + 'from', + 'to', + 'til', + 'fallthrough', + 'case', + 'enum', + 'native', + 'list', + 'map', + '__hasProp', + '__extends', + '__slice', + '__bind', + '__indexOf' + ]; + const KEYWORDS$1 = { + keyword: KEYWORDS.concat(LIVESCRIPT_KEYWORDS), + literal: LITERALS.concat(LIVESCRIPT_LITERALS), + built_in: BUILT_INS.concat(LIVESCRIPT_BUILT_INS) + }; + const JS_IDENT_RE = '[A-Za-z$_](?:-[0-9A-Za-z$_]|[0-9A-Za-z$_])*'; + const TITLE = hljs.inherit(hljs.TITLE_MODE, { begin: JS_IDENT_RE }); + const SUBST = { + className: 'subst', + begin: /#\{/, + end: /\}/, + keywords: KEYWORDS$1 + }; + const SUBST_SIMPLE = { + className: 'subst', + begin: /#[A-Za-z$_]/, + end: /(?:-[0-9A-Za-z$_]|[0-9A-Za-z$_])*/, + keywords: KEYWORDS$1 + }; + const EXPRESSIONS = [ + hljs.BINARY_NUMBER_MODE, + { + className: 'number', + begin: '(\\b0[xX][a-fA-F0-9_]+)|(\\b\\d(\\d|_\\d)*(\\.(\\d(\\d|_\\d)*)?)?(_*[eE]([-+]\\d(_\\d|\\d)*)?)?[_a-z]*)', + relevance: 0, + starts: { + end: '(\\s*/)?', + relevance: 0 + } // a number tries to eat the following slash to prevent treating it as a regexp + }, + { + className: 'string', + variants: [ + { + begin: /'''/, + end: /'''/, + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: /'/, + end: /'/, + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: /"""/, + end: /"""/, + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST, + SUBST_SIMPLE + ] + }, + { + begin: /"/, + end: /"/, + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST, + SUBST_SIMPLE + ] + }, + { + begin: /\\/, + end: /(\s|$)/, + excludeEnd: true + } + ] + }, + { + className: 'regexp', + variants: [ + { + begin: '//', + end: '//[gim]*', + contains: [ + SUBST, + hljs.HASH_COMMENT_MODE + ] + }, + { + // regex can't start with space to parse x / 2 / 3 as two divisions + // regex can't start with *, and it supports an "illegal" in the main mode + begin: /\/(?![ *])(\\.|[^\\\n])*?\/[gim]*(?=\W)/ } + ] + }, + { begin: '@' + JS_IDENT_RE }, + { + begin: '``', + end: '``', + excludeBegin: true, + excludeEnd: true, + subLanguage: 'javascript' + } + ]; + SUBST.contains = EXPRESSIONS; + + const PARAMS = { + className: 'params', + begin: '\\(', + returnBegin: true, + /* We need another contained nameless mode to not have every nested + pair of parens to be called "params" */ + contains: [ + { + begin: /\(/, + end: /\)/, + keywords: KEYWORDS$1, + contains: [ 'self' ].concat(EXPRESSIONS) + } + ] + }; + + const SYMBOLS = { begin: '(#=>|=>|\\|>>|-?->|!->)' }; + + const CLASS_DEFINITION = { + variants: [ + { match: [ + /class\s+/, + JS_IDENT_RE, + /\s+extends\s+/, + JS_IDENT_RE + ] }, + { match: [ + /class\s+/, + JS_IDENT_RE + ] } + ], + scope: { + 2: "title.class", + 4: "title.class.inherited" + }, + keywords: KEYWORDS$1 + }; + + return { + name: 'LiveScript', + aliases: [ 'ls' ], + keywords: KEYWORDS$1, + illegal: /\/\*/, + contains: EXPRESSIONS.concat([ + hljs.COMMENT('\\/\\*', '\\*\\/'), + hljs.HASH_COMMENT_MODE, + SYMBOLS, // relevance booster + { + className: 'function', + contains: [ + TITLE, + PARAMS + ], + returnBegin: true, + variants: [ + { + begin: '(' + JS_IDENT_RE + '\\s*(?:=|:=)\\s*)?(\\(.*\\)\\s*)?\\B->\\*?', + end: '->\\*?' + }, + { + begin: '(' + JS_IDENT_RE + '\\s*(?:=|:=)\\s*)?!?(\\(.*\\)\\s*)?\\B[-~]{1,2}>\\*?', + end: '[-~]{1,2}>\\*?' + }, + { + begin: '(' + JS_IDENT_RE + '\\s*(?:=|:=)\\s*)?(\\(.*\\)\\s*)?\\B!?[-~]{1,2}>\\*?', + end: '!?[-~]{1,2}>\\*?' + } + ] + }, + CLASS_DEFINITION, + { + begin: JS_IDENT_RE + ':', + end: ':', + returnBegin: true, + returnEnd: true, + relevance: 0 + } + ]) + }; +} + +export { livescript as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/livescript.js.js b/frontend/node_modules/highlight.js/es/languages/livescript.js.js new file mode 100644 index 0000000..1b07772 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/livescript.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/livescript" instead of "highlight.js/lib/languages/livescript.js"' + ); + } + } + emitWarning(); + import lang from './livescript.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/llvm.js b/frontend/node_modules/highlight.js/es/languages/llvm.js new file mode 100644 index 0000000..302fb6c --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/llvm.js @@ -0,0 +1,135 @@ +/* +Language: LLVM IR +Author: Michael Rodler +Description: language used as intermediate representation in the LLVM compiler framework +Website: https://llvm.org/docs/LangRef.html +Category: assembler +Audit: 2020 +*/ + +/** @type LanguageFn */ +function llvm(hljs) { + const regex = hljs.regex; + const IDENT_RE = /([-a-zA-Z$._][\w$.-]*)/; + const TYPE = { + className: 'type', + begin: /\bi\d+(?=\s|\b)/ + }; + const OPERATOR = { + className: 'operator', + relevance: 0, + begin: /=/ + }; + const PUNCTUATION = { + className: 'punctuation', + relevance: 0, + begin: /,/ + }; + const NUMBER = { + className: 'number', + variants: [ + { begin: /[su]?0[xX][KMLHR]?[a-fA-F0-9]+/ }, + { begin: /[-+]?\d+(?:[.]\d+)?(?:[eE][-+]?\d+(?:[.]\d+)?)?/ } + ], + relevance: 0 + }; + const LABEL = { + className: 'symbol', + variants: [ { begin: /^\s*[a-z]+:/ }, // labels + ], + relevance: 0 + }; + const VARIABLE = { + className: 'variable', + variants: [ + { begin: regex.concat(/%/, IDENT_RE) }, + { begin: /%\d+/ }, + { begin: /#\d+/ }, + ] + }; + const FUNCTION = { + className: 'title', + variants: [ + { begin: regex.concat(/@/, IDENT_RE) }, + { begin: /@\d+/ }, + { begin: regex.concat(/!/, IDENT_RE) }, + { begin: regex.concat(/!\d+/, IDENT_RE) }, + // https://llvm.org/docs/LangRef.html#namedmetadatastructure + // obviously a single digit can also be used in this fashion + { begin: /!\d+/ } + ] + }; + + return { + name: 'LLVM IR', + // TODO: split into different categories of keywords + keywords: { + keyword: 'begin end true false declare define global ' + + 'constant private linker_private internal ' + + 'available_externally linkonce linkonce_odr weak ' + + 'weak_odr appending dllimport dllexport common ' + + 'default hidden protected extern_weak external ' + + 'thread_local zeroinitializer undef null to tail ' + + 'target triple datalayout volatile nuw nsw nnan ' + + 'ninf nsz arcp fast exact inbounds align ' + + 'addrspace section alias module asm sideeffect ' + + 'gc dbg linker_private_weak attributes blockaddress ' + + 'initialexec localdynamic localexec prefix unnamed_addr ' + + 'ccc fastcc coldcc x86_stdcallcc x86_fastcallcc ' + + 'arm_apcscc arm_aapcscc arm_aapcs_vfpcc ptx_device ' + + 'ptx_kernel intel_ocl_bicc msp430_intrcc spir_func ' + + 'spir_kernel x86_64_sysvcc x86_64_win64cc x86_thiscallcc ' + + 'cc c signext zeroext inreg sret nounwind ' + + 'noreturn noalias nocapture byval nest readnone ' + + 'readonly inlinehint noinline alwaysinline optsize ssp ' + + 'sspreq noredzone noimplicitfloat naked builtin cold ' + + 'nobuiltin noduplicate nonlazybind optnone returns_twice ' + + 'sanitize_address sanitize_memory sanitize_thread sspstrong ' + + 'uwtable returned type opaque eq ne slt sgt ' + + 'sle sge ult ugt ule uge oeq one olt ogt ' + + 'ole oge ord uno ueq une x acq_rel acquire ' + + 'alignstack atomic catch cleanup filter inteldialect ' + + 'max min monotonic nand personality release seq_cst ' + + 'singlethread umax umin unordered xchg add fadd ' + + 'sub fsub mul fmul udiv sdiv fdiv urem srem ' + + 'frem shl lshr ashr and or xor icmp fcmp ' + + 'phi call trunc zext sext fptrunc fpext uitofp ' + + 'sitofp fptoui fptosi inttoptr ptrtoint bitcast ' + + 'addrspacecast select va_arg ret br switch invoke ' + + 'unwind unreachable indirectbr landingpad resume ' + + 'malloc alloca free load store getelementptr ' + + 'extractelement insertelement shufflevector getresult ' + + 'extractvalue insertvalue atomicrmw cmpxchg fence ' + + 'argmemonly', + type: 'void half bfloat float double fp128 x86_fp80 ppc_fp128 ' + + 'x86_amx x86_mmx ptr label token metadata opaque' + }, + contains: [ + TYPE, + // this matches "empty comments"... + // ...because it's far more likely this is a statement terminator in + // another language than an actual comment + hljs.COMMENT(/;\s*$/, null, { relevance: 0 }), + hljs.COMMENT(/;/, /$/), + { + className: 'string', + begin: /"/, + end: /"/, + contains: [ + { + className: 'char.escape', + match: /\\\d\d/ + } + ] + }, + FUNCTION, + PUNCTUATION, + OPERATOR, + VARIABLE, + LABEL, + NUMBER + ] + }; +} + +export { llvm as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/llvm.js.js b/frontend/node_modules/highlight.js/es/languages/llvm.js.js new file mode 100644 index 0000000..e8933f2 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/llvm.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/llvm" instead of "highlight.js/lib/languages/llvm.js"' + ); + } + } + emitWarning(); + import lang from './llvm.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/lsl.js b/frontend/node_modules/highlight.js/es/languages/lsl.js new file mode 100644 index 0000000..c66546c --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/lsl.js @@ -0,0 +1,76 @@ +/* +Language: LSL (Linden Scripting Language) +Description: The Linden Scripting Language is used in Second Life by Linden Labs. +Author: Builder's Brewery +Website: http://wiki.secondlife.com/wiki/LSL_Portal +Category: scripting +*/ + +function lsl(hljs) { + const LSL_STRING_ESCAPE_CHARS = { + className: 'subst', + begin: /\\[tn"\\]/ + }; + + const LSL_STRINGS = { + className: 'string', + begin: '"', + end: '"', + contains: [ LSL_STRING_ESCAPE_CHARS ] + }; + + const LSL_NUMBERS = { + className: 'number', + relevance: 0, + begin: hljs.C_NUMBER_RE + }; + + const LSL_CONSTANTS = { + className: 'literal', + variants: [ + { begin: '\\b(PI|TWO_PI|PI_BY_TWO|DEG_TO_RAD|RAD_TO_DEG|SQRT2)\\b' }, + { begin: '\\b(XP_ERROR_(EXPERIENCES_DISABLED|EXPERIENCE_(DISABLED|SUSPENDED)|INVALID_(EXPERIENCE|PARAMETERS)|KEY_NOT_FOUND|MATURITY_EXCEEDED|NONE|NOT_(FOUND|PERMITTED(_LAND)?)|NO_EXPERIENCE|QUOTA_EXCEEDED|RETRY_UPDATE|STORAGE_EXCEPTION|STORE_DISABLED|THROTTLED|UNKNOWN_ERROR)|JSON_APPEND|STATUS_(PHYSICS|ROTATE_[XYZ]|PHANTOM|SANDBOX|BLOCK_GRAB(_OBJECT)?|(DIE|RETURN)_AT_EDGE|CAST_SHADOWS|OK|MALFORMED_PARAMS|TYPE_MISMATCH|BOUNDS_ERROR|NOT_(FOUND|SUPPORTED)|INTERNAL_ERROR|WHITELIST_FAILED)|AGENT(_(BY_(LEGACY_|USER)NAME|FLYING|ATTACHMENTS|SCRIPTED|MOUSELOOK|SITTING|ON_OBJECT|AWAY|WALKING|IN_AIR|TYPING|CROUCHING|BUSY|ALWAYS_RUN|AUTOPILOT|LIST_(PARCEL(_OWNER)?|REGION)))?|CAMERA_(PITCH|DISTANCE|BEHINDNESS_(ANGLE|LAG)|(FOCUS|POSITION)(_(THRESHOLD|LOCKED|LAG))?|FOCUS_OFFSET|ACTIVE)|ANIM_ON|LOOP|REVERSE|PING_PONG|SMOOTH|ROTATE|SCALE|ALL_SIDES|LINK_(ROOT|SET|ALL_(OTHERS|CHILDREN)|THIS)|ACTIVE|PASS(IVE|_(ALWAYS|IF_NOT_HANDLED|NEVER))|SCRIPTED|CONTROL_(FWD|BACK|(ROT_)?(LEFT|RIGHT)|UP|DOWN|(ML_)?LBUTTON)|PERMISSION_(RETURN_OBJECTS|DEBIT|OVERRIDE_ANIMATIONS|SILENT_ESTATE_MANAGEMENT|TAKE_CONTROLS|TRIGGER_ANIMATION|ATTACH|CHANGE_LINKS|(CONTROL|TRACK)_CAMERA|TELEPORT)|INVENTORY_(TEXTURE|SOUND|OBJECT|SCRIPT|LANDMARK|CLOTHING|NOTECARD|BODYPART|ANIMATION|GESTURE|ALL|NONE)|CHANGED_(INVENTORY|COLOR|SHAPE|SCALE|TEXTURE|LINK|ALLOWED_DROP|OWNER|REGION(_START)?|TELEPORT|MEDIA)|OBJECT_(CLICK_ACTION|HOVER_HEIGHT|LAST_OWNER_ID|(PHYSICS|SERVER|STREAMING)_COST|UNKNOWN_DETAIL|CHARACTER_TIME|PHANTOM|PHYSICS|TEMP_(ATTACHED|ON_REZ)|NAME|DESC|POS|PRIM_(COUNT|EQUIVALENCE)|RETURN_(PARCEL(_OWNER)?|REGION)|REZZER_KEY|ROO?T|VELOCITY|OMEGA|OWNER|GROUP(_TAG)?|CREATOR|ATTACHED_(POINT|SLOTS_AVAILABLE)|RENDER_WEIGHT|(BODY_SHAPE|PATHFINDING)_TYPE|(RUNNING|TOTAL)_SCRIPT_COUNT|TOTAL_INVENTORY_COUNT|SCRIPT_(MEMORY|TIME))|TYPE_(INTEGER|FLOAT|STRING|KEY|VECTOR|ROTATION|INVALID)|(DEBUG|PUBLIC)_CHANNEL|ATTACH_(AVATAR_CENTER|CHEST|HEAD|BACK|PELVIS|MOUTH|CHIN|NECK|NOSE|BELLY|[LR](SHOULDER|HAND|FOOT|EAR|EYE|[UL](ARM|LEG)|HIP)|(LEFT|RIGHT)_PEC|HUD_(CENTER_[12]|TOP_(RIGHT|CENTER|LEFT)|BOTTOM(_(RIGHT|LEFT))?)|[LR]HAND_RING1|TAIL_(BASE|TIP)|[LR]WING|FACE_(JAW|[LR]EAR|[LR]EYE|TOUNGE)|GROIN|HIND_[LR]FOOT)|LAND_(LEVEL|RAISE|LOWER|SMOOTH|NOISE|REVERT)|DATA_(ONLINE|NAME|BORN|SIM_(POS|STATUS|RATING)|PAYINFO)|PAYMENT_INFO_(ON_FILE|USED)|REMOTE_DATA_(CHANNEL|REQUEST|REPLY)|PSYS_(PART_(BF_(ZERO|ONE(_MINUS_(DEST_COLOR|SOURCE_(ALPHA|COLOR)))?|DEST_COLOR|SOURCE_(ALPHA|COLOR))|BLEND_FUNC_(DEST|SOURCE)|FLAGS|(START|END)_(COLOR|ALPHA|SCALE|GLOW)|MAX_AGE|(RIBBON|WIND|INTERP_(COLOR|SCALE)|BOUNCE|FOLLOW_(SRC|VELOCITY)|TARGET_(POS|LINEAR)|EMISSIVE)_MASK)|SRC_(MAX_AGE|PATTERN|ANGLE_(BEGIN|END)|BURST_(RATE|PART_COUNT|RADIUS|SPEED_(MIN|MAX))|ACCEL|TEXTURE|TARGET_KEY|OMEGA|PATTERN_(DROP|EXPLODE|ANGLE(_CONE(_EMPTY)?)?)))|VEHICLE_(REFERENCE_FRAME|TYPE_(NONE|SLED|CAR|BOAT|AIRPLANE|BALLOON)|(LINEAR|ANGULAR)_(FRICTION_TIMESCALE|MOTOR_DIRECTION)|LINEAR_MOTOR_OFFSET|HOVER_(HEIGHT|EFFICIENCY|TIMESCALE)|BUOYANCY|(LINEAR|ANGULAR)_(DEFLECTION_(EFFICIENCY|TIMESCALE)|MOTOR_(DECAY_)?TIMESCALE)|VERTICAL_ATTRACTION_(EFFICIENCY|TIMESCALE)|BANKING_(EFFICIENCY|MIX|TIMESCALE)|FLAG_(NO_DEFLECTION_UP|LIMIT_(ROLL_ONLY|MOTOR_UP)|HOVER_((WATER|TERRAIN|UP)_ONLY|GLOBAL_HEIGHT)|MOUSELOOK_(STEER|BANK)|CAMERA_DECOUPLED))|PRIM_(ALLOW_UNSIT|ALPHA_MODE(_(BLEND|EMISSIVE|MASK|NONE))?|NORMAL|SPECULAR|TYPE(_(BOX|CYLINDER|PRISM|SPHERE|TORUS|TUBE|RING|SCULPT))?|HOLE_(DEFAULT|CIRCLE|SQUARE|TRIANGLE)|MATERIAL(_(STONE|METAL|GLASS|WOOD|FLESH|PLASTIC|RUBBER))?|SHINY_(NONE|LOW|MEDIUM|HIGH)|BUMP_(NONE|BRIGHT|DARK|WOOD|BARK|BRICKS|CHECKER|CONCRETE|TILE|STONE|DISKS|GRAVEL|BLOBS|SIDING|LARGETILE|STUCCO|SUCTION|WEAVE)|TEXGEN_(DEFAULT|PLANAR)|SCRIPTED_SIT_ONLY|SCULPT_(TYPE_(SPHERE|TORUS|PLANE|CYLINDER|MASK)|FLAG_(MIRROR|INVERT))|PHYSICS(_(SHAPE_(CONVEX|NONE|PRIM|TYPE)))?|(POS|ROT)_LOCAL|SLICE|TEXT|FLEXIBLE|POINT_LIGHT|TEMP_ON_REZ|PHANTOM|POSITION|SIT_TARGET|SIZE|ROTATION|TEXTURE|NAME|OMEGA|DESC|LINK_TARGET|COLOR|BUMP_SHINY|FULLBRIGHT|TEXGEN|GLOW|MEDIA_(ALT_IMAGE_ENABLE|CONTROLS|(CURRENT|HOME)_URL|AUTO_(LOOP|PLAY|SCALE|ZOOM)|FIRST_CLICK_INTERACT|(WIDTH|HEIGHT)_PIXELS|WHITELIST(_ENABLE)?|PERMS_(INTERACT|CONTROL)|PARAM_MAX|CONTROLS_(STANDARD|MINI)|PERM_(NONE|OWNER|GROUP|ANYONE)|MAX_(URL_LENGTH|WHITELIST_(SIZE|COUNT)|(WIDTH|HEIGHT)_PIXELS)))|MASK_(BASE|OWNER|GROUP|EVERYONE|NEXT)|PERM_(TRANSFER|MODIFY|COPY|MOVE|ALL)|PARCEL_(MEDIA_COMMAND_(STOP|PAUSE|PLAY|LOOP|TEXTURE|URL|TIME|AGENT|UNLOAD|AUTO_ALIGN|TYPE|SIZE|DESC|LOOP_SET)|FLAG_(ALLOW_(FLY|(GROUP_)?SCRIPTS|LANDMARK|TERRAFORM|DAMAGE|CREATE_(GROUP_)?OBJECTS)|USE_(ACCESS_(GROUP|LIST)|BAN_LIST|LAND_PASS_LIST)|LOCAL_SOUND_ONLY|RESTRICT_PUSHOBJECT|ALLOW_(GROUP|ALL)_OBJECT_ENTRY)|COUNT_(TOTAL|OWNER|GROUP|OTHER|SELECTED|TEMP)|DETAILS_(NAME|DESC|OWNER|GROUP|AREA|ID|SEE_AVATARS))|LIST_STAT_(MAX|MIN|MEAN|MEDIAN|STD_DEV|SUM(_SQUARES)?|NUM_COUNT|GEOMETRIC_MEAN|RANGE)|PAY_(HIDE|DEFAULT)|REGION_FLAG_(ALLOW_DAMAGE|FIXED_SUN|BLOCK_TERRAFORM|SANDBOX|DISABLE_(COLLISIONS|PHYSICS)|BLOCK_FLY|ALLOW_DIRECT_TELEPORT|RESTRICT_PUSHOBJECT)|HTTP_(METHOD|MIMETYPE|BODY_(MAXLENGTH|TRUNCATED)|CUSTOM_HEADER|PRAGMA_NO_CACHE|VERBOSE_THROTTLE|VERIFY_CERT)|SIT_(INVALID_(AGENT|LINK_OBJECT)|NO(T_EXPERIENCE|_(ACCESS|EXPERIENCE_PERMISSION|SIT_TARGET)))|STRING_(TRIM(_(HEAD|TAIL))?)|CLICK_ACTION_(NONE|TOUCH|SIT|BUY|PAY|OPEN(_MEDIA)?|PLAY|ZOOM)|TOUCH_INVALID_FACE|PROFILE_(NONE|SCRIPT_MEMORY)|RC_(DATA_FLAGS|DETECT_PHANTOM|GET_(LINK_NUM|NORMAL|ROOT_KEY)|MAX_HITS|REJECT_(TYPES|AGENTS|(NON)?PHYSICAL|LAND))|RCERR_(CAST_TIME_EXCEEDED|SIM_PERF_LOW|UNKNOWN)|ESTATE_ACCESS_(ALLOWED_(AGENT|GROUP)_(ADD|REMOVE)|BANNED_AGENT_(ADD|REMOVE))|DENSITY|FRICTION|RESTITUTION|GRAVITY_MULTIPLIER|KFM_(COMMAND|CMD_(PLAY|STOP|PAUSE)|MODE|FORWARD|LOOP|PING_PONG|REVERSE|DATA|ROTATION|TRANSLATION)|ERR_(GENERIC|PARCEL_PERMISSIONS|MALFORMED_PARAMS|RUNTIME_PERMISSIONS|THROTTLED)|CHARACTER_(CMD_((SMOOTH_)?STOP|JUMP)|DESIRED_(TURN_)?SPEED|RADIUS|STAY_WITHIN_PARCEL|LENGTH|ORIENTATION|ACCOUNT_FOR_SKIPPED_FRAMES|AVOIDANCE_MODE|TYPE(_([ABCD]|NONE))?|MAX_(DECEL|TURN_RADIUS|(ACCEL|SPEED)))|PURSUIT_(OFFSET|FUZZ_FACTOR|GOAL_TOLERANCE|INTERCEPT)|REQUIRE_LINE_OF_SIGHT|FORCE_DIRECT_PATH|VERTICAL|HORIZONTAL|AVOID_(CHARACTERS|DYNAMIC_OBSTACLES|NONE)|PU_(EVADE_(HIDDEN|SPOTTED)|FAILURE_(DYNAMIC_PATHFINDING_DISABLED|INVALID_(GOAL|START)|NO_(NAVMESH|VALID_DESTINATION)|OTHER|TARGET_GONE|(PARCEL_)?UNREACHABLE)|(GOAL|SLOWDOWN_DISTANCE)_REACHED)|TRAVERSAL_TYPE(_(FAST|NONE|SLOW))?|CONTENT_TYPE_(ATOM|FORM|HTML|JSON|LLSD|RSS|TEXT|XHTML|XML)|GCNP_(RADIUS|STATIC)|(PATROL|WANDER)_PAUSE_AT_WAYPOINTS|OPT_(AVATAR|CHARACTER|EXCLUSION_VOLUME|LEGACY_LINKSET|MATERIAL_VOLUME|OTHER|STATIC_OBSTACLE|WALKABLE)|SIM_STAT_PCT_CHARS_STEPPED)\\b' }, + { begin: '\\b(FALSE|TRUE)\\b' }, + { begin: '\\b(ZERO_ROTATION)\\b' }, + { begin: '\\b(EOF|JSON_(ARRAY|DELETE|FALSE|INVALID|NULL|NUMBER|OBJECT|STRING|TRUE)|NULL_KEY|TEXTURE_(BLANK|DEFAULT|MEDIA|PLYWOOD|TRANSPARENT)|URL_REQUEST_(GRANTED|DENIED))\\b' }, + { begin: '\\b(ZERO_VECTOR|TOUCH_INVALID_(TEXCOORD|VECTOR))\\b' } + ] + }; + + const LSL_FUNCTIONS = { + className: 'built_in', + begin: '\\b(ll(AgentInExperience|(Create|DataSize|Delete|KeyCount|Keys|Read|Update)KeyValue|GetExperience(Details|ErrorMessage)|ReturnObjectsBy(ID|Owner)|Json(2List|[GS]etValue|ValueType)|Sin|Cos|Tan|Atan2|Sqrt|Pow|Abs|Fabs|Frand|Floor|Ceil|Round|Vec(Mag|Norm|Dist)|Rot(Between|2(Euler|Fwd|Left|Up))|(Euler|Axes)2Rot|Whisper|(Region|Owner)?Say|Shout|Listen(Control|Remove)?|Sensor(Repeat|Remove)?|Detected(Name|Key|Owner|Type|Pos|Vel|Grab|Rot|Group|LinkNumber)|Die|Ground|Wind|([GS]et)(AnimationOverride|MemoryLimit|PrimMediaParams|ParcelMusicURL|Object(Desc|Name)|PhysicsMaterial|Status|Scale|Color|Alpha|Texture|Pos|Rot|Force|Torque)|ResetAnimationOverride|(Scale|Offset|Rotate)Texture|(Rot)?Target(Remove)?|(Stop)?MoveToTarget|Apply(Rotational)?Impulse|Set(KeyframedMotion|ContentType|RegionPos|(Angular)?Velocity|Buoyancy|HoverHeight|ForceAndTorque|TimerEvent|ScriptState|Damage|TextureAnim|Sound(Queueing|Radius)|Vehicle(Type|(Float|Vector|Rotation)Param)|(Touch|Sit)?Text|Camera(Eye|At)Offset|PrimitiveParams|ClickAction|Link(Alpha|Color|PrimitiveParams(Fast)?|Texture(Anim)?|Camera|Media)|RemoteScriptAccessPin|PayPrice|LocalRot)|ScaleByFactor|Get((Max|Min)ScaleFactor|ClosestNavPoint|StaticPath|SimStats|Env|PrimitiveParams|Link(PrimitiveParams|Number(OfSides)?|Key|Name|Media)|HTTPHeader|FreeURLs|Object(Details|PermMask|PrimCount)|Parcel(MaxPrims|Details|Prim(Count|Owners))|Attached(List)?|(SPMax|Free|Used)Memory|Region(Name|TimeDilation|FPS|Corner|AgentCount)|Root(Position|Rotation)|UnixTime|(Parcel|Region)Flags|(Wall|GMT)clock|SimulatorHostname|BoundingBox|GeometricCenter|Creator|NumberOf(Prims|NotecardLines|Sides)|Animation(List)?|(Camera|Local)(Pos|Rot)|Vel|Accel|Omega|Time(stamp|OfDay)|(Object|CenterOf)?Mass|MassMKS|Energy|Owner|(Owner)?Key|SunDirection|Texture(Offset|Scale|Rot)|Inventory(Number|Name|Key|Type|Creator|PermMask)|Permissions(Key)?|StartParameter|List(Length|EntryType)|Date|Agent(Size|Info|Language|List)|LandOwnerAt|NotecardLine|Script(Name|State))|(Get|Reset|GetAndReset)Time|PlaySound(Slave)?|LoopSound(Master|Slave)?|(Trigger|Stop|Preload)Sound|((Get|Delete)Sub|Insert)String|To(Upper|Lower)|Give(InventoryList|Money)|RezObject|(Stop)?LookAt|Sleep|CollisionFilter|(Take|Release)Controls|DetachFromAvatar|AttachToAvatar(Temp)?|InstantMessage|(GetNext)?Email|StopHover|MinEventDelay|RotLookAt|String(Length|Trim)|(Start|Stop)Animation|TargetOmega|Request(Experience)?Permissions|(Create|Break)Link|BreakAllLinks|(Give|Remove)Inventory|Water|PassTouches|Request(Agent|Inventory)Data|TeleportAgent(Home|GlobalCoords)?|ModifyLand|CollisionSound|ResetScript|MessageLinked|PushObject|PassCollisions|AxisAngle2Rot|Rot2(Axis|Angle)|A(cos|sin)|AngleBetween|AllowInventoryDrop|SubStringIndex|List2(CSV|Integer|Json|Float|String|Key|Vector|Rot|List(Strided)?)|DeleteSubList|List(Statistics|Sort|Randomize|(Insert|Find|Replace)List)|EdgeOfWorld|AdjustSoundVolume|Key2Name|TriggerSoundLimited|EjectFromLand|(CSV|ParseString)2List|OverMyLand|SameGroup|UnSit|Ground(Slope|Normal|Contour)|GroundRepel|(Set|Remove)VehicleFlags|SitOnLink|(AvatarOn)?(Link)?SitTarget|Script(Danger|Profiler)|Dialog|VolumeDetect|ResetOtherScript|RemoteLoadScriptPin|(Open|Close)RemoteDataChannel|SendRemoteData|RemoteDataReply|(Integer|String)ToBase64|XorBase64|Log(10)?|Base64To(String|Integer)|ParseStringKeepNulls|RezAtRoot|RequestSimulatorData|ForceMouselook|(Load|Release|(E|Une)scape)URL|ParcelMedia(CommandList|Query)|ModPow|MapDestination|(RemoveFrom|AddTo|Reset)Land(Pass|Ban)List|(Set|Clear)CameraParams|HTTP(Request|Response)|TextBox|DetectedTouch(UV|Face|Pos|(N|Bin)ormal|ST)|(MD5|SHA1|DumpList2)String|Request(Secure)?URL|Clear(Prim|Link)Media|(Link)?ParticleSystem|(Get|Request)(Username|DisplayName)|RegionSayTo|CastRay|GenerateKey|TransferLindenDollars|ManageEstateAccess|(Create|Delete)Character|ExecCharacterCmd|Evade|FleeFrom|NavigateTo|PatrolPoints|Pursue|UpdateCharacter|WanderWithin))\\b' + }; + + return { + name: 'LSL (Linden Scripting Language)', + illegal: ':', + contains: [ + LSL_STRINGS, + { + className: 'comment', + variants: [ + hljs.COMMENT('//', '$'), + hljs.COMMENT('/\\*', '\\*/') + ], + relevance: 0 + }, + LSL_NUMBERS, + { + className: 'section', + variants: [ + { begin: '\\b(state|default)\\b' }, + { begin: '\\b(state_(entry|exit)|touch(_(start|end))?|(land_)?collision(_(start|end))?|timer|listen|(no_)?sensor|control|(not_)?at_(rot_)?target|money|email|experience_permissions(_denied)?|run_time_permissions|changed|attach|dataserver|moving_(start|end)|link_message|(on|object)_rez|remote_data|http_re(sponse|quest)|path_update|transaction_result)\\b' } + ] + }, + LSL_FUNCTIONS, + LSL_CONSTANTS, + { + className: 'type', + begin: '\\b(integer|float|string|key|vector|quaternion|rotation|list)\\b' + } + ] + }; +} + +export { lsl as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/lsl.js.js b/frontend/node_modules/highlight.js/es/languages/lsl.js.js new file mode 100644 index 0000000..1c8c0c3 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/lsl.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/lsl" instead of "highlight.js/lib/languages/lsl.js"' + ); + } + } + emitWarning(); + import lang from './lsl.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/lua.js b/frontend/node_modules/highlight.js/es/languages/lua.js new file mode 100644 index 0000000..993265e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/lua.js @@ -0,0 +1,81 @@ +/* +Language: Lua +Description: Lua is a powerful, efficient, lightweight, embeddable scripting language. +Author: Andrew Fedorov +Category: common, gaming, scripting +Website: https://www.lua.org +*/ + +function lua(hljs) { + const OPENING_LONG_BRACKET = '\\[=*\\['; + const CLOSING_LONG_BRACKET = '\\]=*\\]'; + const LONG_BRACKETS = { + begin: OPENING_LONG_BRACKET, + end: CLOSING_LONG_BRACKET, + contains: [ 'self' ] + }; + const COMMENTS = [ + hljs.COMMENT('--(?!' + OPENING_LONG_BRACKET + ')', '$'), + hljs.COMMENT( + '--' + OPENING_LONG_BRACKET, + CLOSING_LONG_BRACKET, + { + contains: [ LONG_BRACKETS ], + relevance: 10 + } + ) + ]; + return { + name: 'Lua', + aliases: ['pluto'], + keywords: { + $pattern: hljs.UNDERSCORE_IDENT_RE, + literal: "true false nil", + keyword: "and break do else elseif end for goto if in local not or repeat return then until while", + built_in: + // Metatags and globals: + '_G _ENV _VERSION __index __newindex __mode __call __metatable __tostring __len ' + + '__gc __add __sub __mul __div __mod __pow __concat __unm __eq __lt __le assert ' + // Standard methods and properties: + + 'collectgarbage dofile error getfenv getmetatable ipairs load loadfile loadstring ' + + 'module next pairs pcall print rawequal rawget rawset require select setfenv ' + + 'setmetatable tonumber tostring type unpack xpcall arg self ' + // Library methods and properties (one line per library): + + 'coroutine resume yield status wrap create running debug getupvalue ' + + 'debug sethook getmetatable gethook setmetatable setlocal traceback setfenv getinfo setupvalue getlocal getregistry getfenv ' + + 'io lines write close flush open output type read stderr stdin input stdout popen tmpfile ' + + 'math log max acos huge ldexp pi cos tanh pow deg tan cosh sinh random randomseed frexp ceil floor rad abs sqrt modf asin min mod fmod log10 atan2 exp sin atan ' + + 'os exit setlocale date getenv difftime remove time clock tmpname rename execute package preload loadlib loaded loaders cpath config path seeall ' + + 'string sub upper len gfind rep find match char dump gmatch reverse byte format gsub lower ' + + 'table setn insert getn foreachi maxn foreach concat sort remove' + }, + contains: COMMENTS.concat([ + { + className: 'function', + beginKeywords: 'function', + end: '\\)', + contains: [ + hljs.inherit(hljs.TITLE_MODE, { begin: '([_a-zA-Z]\\w*\\.)*([_a-zA-Z]\\w*:)?[_a-zA-Z]\\w*' }), + { + className: 'params', + begin: '\\(', + endsWithParent: true, + contains: COMMENTS + } + ].concat(COMMENTS) + }, + hljs.C_NUMBER_MODE, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + { + className: 'string', + begin: OPENING_LONG_BRACKET, + end: CLOSING_LONG_BRACKET, + contains: [ LONG_BRACKETS ], + relevance: 5 + } + ]) + }; +} + +export { lua as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/lua.js.js b/frontend/node_modules/highlight.js/es/languages/lua.js.js new file mode 100644 index 0000000..1fc6c58 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/lua.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/lua" instead of "highlight.js/lib/languages/lua.js"' + ); + } + } + emitWarning(); + import lang from './lua.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/makefile.js b/frontend/node_modules/highlight.js/es/languages/makefile.js new file mode 100644 index 0000000..47b2bad --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/makefile.js @@ -0,0 +1,89 @@ +/* +Language: Makefile +Author: Ivan Sagalaev +Contributors: Joël Porquet +Website: https://www.gnu.org/software/make/manual/html_node/Introduction.html +Category: common, build-system +*/ + +function makefile(hljs) { + /* Variables: simple (eg $(var)) and special (eg $@) */ + const VARIABLE = { + className: 'variable', + variants: [ + { + begin: '\\$\\(' + hljs.UNDERSCORE_IDENT_RE + '\\)', + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { begin: /\$[@% +Website: https://daringfireball.net/projects/markdown/ +Category: common, markup +*/ + +function markdown(hljs) { + const regex = hljs.regex; + const INLINE_HTML = { + begin: /<\/?[A-Za-z_]/, + end: '>', + subLanguage: 'xml', + relevance: 0 + }; + const HORIZONTAL_RULE = { + begin: '^[-\\*]{3,}', + end: '$' + }; + const CODE = { + className: 'code', + variants: [ + // TODO: fix to allow these to work with sublanguage also + { begin: '(`{3,})[^`](.|\\n)*?\\1`*[ ]*' }, + { begin: '(~{3,})[^~](.|\\n)*?\\1~*[ ]*' }, + // needed to allow markdown as a sublanguage to work + { + begin: '```', + end: '```+[ ]*$' + }, + { + begin: '~~~', + end: '~~~+[ ]*$' + }, + { begin: '`.+?`' }, + { + begin: '(?=^( {4}|\\t))', + // use contains to gobble up multiple lines to allow the block to be whatever size + // but only have a single open/close tag vs one per line + contains: [ + { + begin: '^( {4}|\\t)', + end: '(\\n)$' + } + ], + relevance: 0 + } + ] + }; + const LIST = { + className: 'bullet', + begin: '^[ \t]*([*+-]|(\\d+\\.))(?=\\s+)', + end: '\\s+', + excludeEnd: true + }; + const LINK_REFERENCE = { + begin: /^\[[^\n]+\]:/, + returnBegin: true, + contains: [ + { + className: 'symbol', + begin: /\[/, + end: /\]/, + excludeBegin: true, + excludeEnd: true + }, + { + className: 'link', + begin: /:\s*/, + end: /$/, + excludeBegin: true + } + ] + }; + const URL_SCHEME = /[A-Za-z][A-Za-z0-9+.-]*/; + const LINK = { + variants: [ + // too much like nested array access in so many languages + // to have any real relevance + { + begin: /\[.+?\]\[.*?\]/, + relevance: 0 + }, + // popular internet URLs + { + begin: /\[.+?\]\(((data|javascript|mailto):|(?:http|ftp)s?:\/\/).*?\)/, + relevance: 2 + }, + { + begin: regex.concat(/\[.+?\]\(/, URL_SCHEME, /:\/\/.*?\)/), + relevance: 2 + }, + // relative urls + { + begin: /\[.+?\]\([./?&#].*?\)/, + relevance: 1 + }, + // whatever else, lower relevance (might not be a link at all) + { + begin: /\[.*?\]\(.*?\)/, + relevance: 0 + } + ], + returnBegin: true, + contains: [ + { + // empty strings for alt or link text + match: /\[(?=\])/ }, + { + className: 'string', + relevance: 0, + begin: '\\[', + end: '\\]', + excludeBegin: true, + returnEnd: true + }, + { + className: 'link', + relevance: 0, + begin: '\\]\\(', + end: '\\)', + excludeBegin: true, + excludeEnd: true + }, + { + className: 'symbol', + relevance: 0, + begin: '\\]\\[', + end: '\\]', + excludeBegin: true, + excludeEnd: true + } + ] + }; + const BOLD = { + className: 'strong', + contains: [], // defined later + variants: [ + { + begin: /_{2}(?!\s)/, + end: /_{2}/ + }, + { + begin: /\*{2}(?!\s)/, + end: /\*{2}/ + } + ] + }; + const ITALIC = { + className: 'emphasis', + contains: [], // defined later + variants: [ + { + begin: /\*(?![*\s])/, + end: /\*/ + }, + { + begin: /_(?![_\s])/, + end: /_/, + relevance: 0 + } + ] + }; + + // 3 level deep nesting is not allowed because it would create confusion + // in cases like `***testing***` because where we don't know if the last + // `***` is starting a new bold/italic or finishing the last one + const BOLD_WITHOUT_ITALIC = hljs.inherit(BOLD, { contains: [] }); + const ITALIC_WITHOUT_BOLD = hljs.inherit(ITALIC, { contains: [] }); + BOLD.contains.push(ITALIC_WITHOUT_BOLD); + ITALIC.contains.push(BOLD_WITHOUT_ITALIC); + + let CONTAINABLE = [ + INLINE_HTML, + LINK + ]; + + [ + BOLD, + ITALIC, + BOLD_WITHOUT_ITALIC, + ITALIC_WITHOUT_BOLD + ].forEach(m => { + m.contains = m.contains.concat(CONTAINABLE); + }); + + CONTAINABLE = CONTAINABLE.concat(BOLD, ITALIC); + + const HEADER = { + className: 'section', + variants: [ + { + begin: '^#{1,6}', + end: '$', + contains: CONTAINABLE + }, + { + begin: '(?=^.+?\\n[=-]{2,}$)', + contains: [ + { begin: '^[=-]*$' }, + { + begin: '^', + end: "\\n", + contains: CONTAINABLE + } + ] + } + ] + }; + + const BLOCKQUOTE = { + className: 'quote', + begin: '^>\\s+', + contains: CONTAINABLE, + end: '$' + }; + + const ENTITY = { + //https://spec.commonmark.org/0.31.2/#entity-references + scope: 'literal', + match: /&([a-zA-Z0-9]+|#[0-9]{1,7}|#[Xx][0-9a-fA-F]{1,6});/ + }; + + return { + name: 'Markdown', + aliases: [ + 'md', + 'mkdown', + 'mkd' + ], + contains: [ + HEADER, + INLINE_HTML, + LIST, + BOLD, + ITALIC, + BLOCKQUOTE, + CODE, + HORIZONTAL_RULE, + LINK, + LINK_REFERENCE, + ENTITY + ] + }; +} + +export { markdown as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/markdown.js.js b/frontend/node_modules/highlight.js/es/languages/markdown.js.js new file mode 100644 index 0000000..5daa3d2 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/markdown.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/markdown" instead of "highlight.js/lib/languages/markdown.js"' + ); + } + } + emitWarning(); + import lang from './markdown.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/mathematica.js b/frontend/node_modules/highlight.js/es/languages/mathematica.js new file mode 100644 index 0000000..9135a97 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/mathematica.js @@ -0,0 +1,7359 @@ +const SYSTEM_SYMBOLS = [ + "AASTriangle", + "AbelianGroup", + "Abort", + "AbortKernels", + "AbortProtect", + "AbortScheduledTask", + "Above", + "Abs", + "AbsArg", + "AbsArgPlot", + "Absolute", + "AbsoluteCorrelation", + "AbsoluteCorrelationFunction", + "AbsoluteCurrentValue", + "AbsoluteDashing", + "AbsoluteFileName", + "AbsoluteOptions", + "AbsolutePointSize", + "AbsoluteThickness", + "AbsoluteTime", + "AbsoluteTiming", + "AcceptanceThreshold", + "AccountingForm", + "Accumulate", + "Accuracy", + "AccuracyGoal", + "AcousticAbsorbingValue", + "AcousticImpedanceValue", + "AcousticNormalVelocityValue", + "AcousticPDEComponent", + "AcousticPressureCondition", + "AcousticRadiationValue", + "AcousticSoundHardValue", + "AcousticSoundSoftCondition", + "ActionDelay", + "ActionMenu", + "ActionMenuBox", + "ActionMenuBoxOptions", + "Activate", + "Active", + "ActiveClassification", + "ActiveClassificationObject", + "ActiveItem", + "ActivePrediction", + "ActivePredictionObject", + "ActiveStyle", + "AcyclicGraphQ", + "AddOnHelpPath", + "AddSides", + "AddTo", + "AddToSearchIndex", + "AddUsers", + "AdjacencyGraph", + "AdjacencyList", + "AdjacencyMatrix", + "AdjacentMeshCells", + "Adjugate", + "AdjustmentBox", + "AdjustmentBoxOptions", + "AdjustTimeSeriesForecast", + "AdministrativeDivisionData", + "AffineHalfSpace", + "AffineSpace", + "AffineStateSpaceModel", + "AffineTransform", + "After", + "AggregatedEntityClass", + "AggregationLayer", + "AircraftData", + "AirportData", + "AirPressureData", + "AirSoundAttenuation", + "AirTemperatureData", + "AiryAi", + "AiryAiPrime", + "AiryAiZero", + "AiryBi", + "AiryBiPrime", + "AiryBiZero", + "AlgebraicIntegerQ", + "AlgebraicNumber", + "AlgebraicNumberDenominator", + "AlgebraicNumberNorm", + "AlgebraicNumberPolynomial", + "AlgebraicNumberTrace", + "AlgebraicRules", + "AlgebraicRulesData", + "Algebraics", + "AlgebraicUnitQ", + "Alignment", + "AlignmentMarker", + "AlignmentPoint", + "All", + "AllowAdultContent", + "AllowChatServices", + "AllowedCloudExtraParameters", + "AllowedCloudParameterExtensions", + "AllowedDimensions", + "AllowedFrequencyRange", + "AllowedHeads", + "AllowGroupClose", + "AllowIncomplete", + "AllowInlineCells", + "AllowKernelInitialization", + "AllowLooseGrammar", + "AllowReverseGroupClose", + "AllowScriptLevelChange", + "AllowVersionUpdate", + "AllTrue", + "Alphabet", + "AlphabeticOrder", + "AlphabeticSort", + "AlphaChannel", + "AlternateImage", + "AlternatingFactorial", + "AlternatingGroup", + "AlternativeHypothesis", + "Alternatives", + "AltitudeMethod", + "AmbientLight", + "AmbiguityFunction", + "AmbiguityList", + "Analytic", + "AnatomyData", + "AnatomyForm", + "AnatomyPlot3D", + "AnatomySkinStyle", + "AnatomyStyling", + "AnchoredSearch", + "And", + "AndersonDarlingTest", + "AngerJ", + "AngleBisector", + "AngleBracket", + "AnglePath", + "AnglePath3D", + "AngleVector", + "AngularGauge", + "Animate", + "AnimatedImage", + "AnimationCycleOffset", + "AnimationCycleRepetitions", + "AnimationDirection", + "AnimationDisplayTime", + "AnimationRate", + "AnimationRepetitions", + "AnimationRunning", + "AnimationRunTime", + "AnimationTimeIndex", + "AnimationVideo", + "Animator", + "AnimatorBox", + "AnimatorBoxOptions", + "AnimatorElements", + "Annotate", + "Annotation", + "AnnotationDelete", + "AnnotationKeys", + "AnnotationRules", + "AnnotationValue", + "Annuity", + "AnnuityDue", + "Annulus", + "AnomalyDetection", + "AnomalyDetector", + "AnomalyDetectorFunction", + "Anonymous", + "Antialiasing", + "Antihermitian", + "AntihermitianMatrixQ", + "Antisymmetric", + "AntisymmetricMatrixQ", + "Antonyms", + "AnyOrder", + "AnySubset", + "AnyTrue", + "Apart", + "ApartSquareFree", + "APIFunction", + "Appearance", + "AppearanceElements", + "AppearanceRules", + "AppellF1", + "Append", + "AppendCheck", + "AppendLayer", + "AppendTo", + "Application", + "Apply", + "ApplyReaction", + "ApplySides", + "ApplyTo", + "ArcCos", + "ArcCosh", + "ArcCot", + "ArcCoth", + "ArcCsc", + "ArcCsch", + "ArcCurvature", + "ARCHProcess", + "ArcLength", + "ArcSec", + "ArcSech", + "ArcSin", + "ArcSinDistribution", + "ArcSinh", + "ArcTan", + "ArcTanh", + "Area", + "Arg", + "ArgMax", + "ArgMin", + "ArgumentCountQ", + "ArgumentsOptions", + "ARIMAProcess", + "ArithmeticGeometricMean", + "ARMAProcess", + "Around", + "AroundReplace", + "ARProcess", + "Array", + "ArrayComponents", + "ArrayDepth", + "ArrayFilter", + "ArrayFlatten", + "ArrayMesh", + "ArrayPad", + "ArrayPlot", + "ArrayPlot3D", + "ArrayQ", + "ArrayReduce", + "ArrayResample", + "ArrayReshape", + "ArrayRules", + "Arrays", + "Arrow", + "Arrow3DBox", + "ArrowBox", + "Arrowheads", + "ASATriangle", + "Ask", + "AskAppend", + "AskConfirm", + "AskDisplay", + "AskedQ", + "AskedValue", + "AskFunction", + "AskState", + "AskTemplateDisplay", + "AspectRatio", + "AspectRatioFixed", + "Assert", + "AssessmentFunction", + "AssessmentResultObject", + "AssociateTo", + "Association", + "AssociationFormat", + "AssociationMap", + "AssociationQ", + "AssociationThread", + "AssumeDeterministic", + "Assuming", + "Assumptions", + "AstroAngularSeparation", + "AstroBackground", + "AstroCenter", + "AstroDistance", + "AstroGraphics", + "AstroGridLines", + "AstroGridLinesStyle", + "AstronomicalData", + "AstroPosition", + "AstroProjection", + "AstroRange", + "AstroRangePadding", + "AstroReferenceFrame", + "AstroStyling", + "AstroZoomLevel", + "Asymptotic", + "AsymptoticDSolveValue", + "AsymptoticEqual", + "AsymptoticEquivalent", + "AsymptoticExpectation", + "AsymptoticGreater", + "AsymptoticGreaterEqual", + "AsymptoticIntegrate", + "AsymptoticLess", + "AsymptoticLessEqual", + "AsymptoticOutputTracker", + "AsymptoticProbability", + "AsymptoticProduct", + "AsymptoticRSolveValue", + "AsymptoticSolve", + "AsymptoticSum", + "Asynchronous", + "AsynchronousTaskObject", + "AsynchronousTasks", + "Atom", + "AtomCoordinates", + "AtomCount", + "AtomDiagramCoordinates", + "AtomLabels", + "AtomLabelStyle", + "AtomList", + "AtomQ", + "AttachCell", + "AttachedCell", + "AttentionLayer", + "Attributes", + "Audio", + "AudioAmplify", + "AudioAnnotate", + "AudioAnnotationLookup", + "AudioBlockMap", + "AudioCapture", + "AudioChannelAssignment", + "AudioChannelCombine", + "AudioChannelMix", + "AudioChannels", + "AudioChannelSeparate", + "AudioData", + "AudioDelay", + "AudioDelete", + "AudioDevice", + "AudioDistance", + "AudioEncoding", + "AudioFade", + "AudioFrequencyShift", + "AudioGenerator", + "AudioIdentify", + "AudioInputDevice", + "AudioInsert", + "AudioInstanceQ", + "AudioIntervals", + "AudioJoin", + "AudioLabel", + "AudioLength", + "AudioLocalMeasurements", + "AudioLooping", + "AudioLoudness", + "AudioMeasurements", + "AudioNormalize", + "AudioOutputDevice", + "AudioOverlay", + "AudioPad", + "AudioPan", + "AudioPartition", + "AudioPause", + "AudioPitchShift", + "AudioPlay", + "AudioPlot", + "AudioQ", + "AudioRecord", + "AudioReplace", + "AudioResample", + "AudioReverb", + "AudioReverse", + "AudioSampleRate", + "AudioSpectralMap", + "AudioSpectralTransformation", + "AudioSplit", + "AudioStop", + "AudioStream", + "AudioStreams", + "AudioTimeStretch", + "AudioTrackApply", + "AudioTrackSelection", + "AudioTrim", + "AudioType", + "AugmentedPolyhedron", + "AugmentedSymmetricPolynomial", + "Authenticate", + "Authentication", + "AuthenticationDialog", + "AutoAction", + "Autocomplete", + "AutocompletionFunction", + "AutoCopy", + "AutocorrelationTest", + "AutoDelete", + "AutoEvaluateEvents", + "AutoGeneratedPackage", + "AutoIndent", + "AutoIndentSpacings", + "AutoItalicWords", + "AutoloadPath", + "AutoMatch", + "Automatic", + "AutomaticImageSize", + "AutoMultiplicationSymbol", + "AutoNumberFormatting", + "AutoOpenNotebooks", + "AutoOpenPalettes", + "AutoOperatorRenderings", + "AutoQuoteCharacters", + "AutoRefreshed", + "AutoRemove", + "AutorunSequencing", + "AutoScaling", + "AutoScroll", + "AutoSpacing", + "AutoStyleOptions", + "AutoStyleWords", + "AutoSubmitting", + "Axes", + "AxesEdge", + "AxesLabel", + "AxesOrigin", + "AxesStyle", + "AxiomaticTheory", + "Axis", + "Axis3DBox", + "Axis3DBoxOptions", + "AxisBox", + "AxisBoxOptions", + "AxisLabel", + "AxisObject", + "AxisStyle", + "BabyMonsterGroupB", + "Back", + "BackFaceColor", + "BackFaceGlowColor", + "BackFaceOpacity", + "BackFaceSpecularColor", + "BackFaceSpecularExponent", + "BackFaceSurfaceAppearance", + "BackFaceTexture", + "Background", + "BackgroundAppearance", + "BackgroundTasksSettings", + "Backslash", + "Backsubstitution", + "Backward", + "Ball", + "Band", + "BandpassFilter", + "BandstopFilter", + "BarabasiAlbertGraphDistribution", + "BarChart", + "BarChart3D", + "BarcodeImage", + "BarcodeRecognize", + "BaringhausHenzeTest", + "BarLegend", + "BarlowProschanImportance", + "BarnesG", + "BarOrigin", + "BarSpacing", + "BartlettHannWindow", + "BartlettWindow", + "BaseDecode", + "BaseEncode", + "BaseForm", + "Baseline", + "BaselinePosition", + "BaseStyle", + "BasicRecurrentLayer", + "BatchNormalizationLayer", + "BatchSize", + "BatesDistribution", + "BattleLemarieWavelet", + "BayesianMaximization", + "BayesianMaximizationObject", + "BayesianMinimization", + "BayesianMinimizationObject", + "Because", + "BeckmannDistribution", + "Beep", + "Before", + "Begin", + "BeginDialogPacket", + "BeginPackage", + "BellB", + "BellY", + "Below", + "BenfordDistribution", + "BeniniDistribution", + "BenktanderGibratDistribution", + "BenktanderWeibullDistribution", + "BernoulliB", + "BernoulliDistribution", + "BernoulliGraphDistribution", + "BernoulliProcess", + "BernsteinBasis", + "BesagL", + "BesselFilterModel", + "BesselI", + "BesselJ", + "BesselJZero", + "BesselK", + "BesselY", + "BesselYZero", + "Beta", + "BetaBinomialDistribution", + "BetaDistribution", + "BetaNegativeBinomialDistribution", + "BetaPrimeDistribution", + "BetaRegularized", + "Between", + "BetweennessCentrality", + "Beveled", + "BeveledPolyhedron", + "BezierCurve", + "BezierCurve3DBox", + "BezierCurve3DBoxOptions", + "BezierCurveBox", + "BezierCurveBoxOptions", + "BezierFunction", + "BilateralFilter", + "BilateralLaplaceTransform", + "BilateralZTransform", + "Binarize", + "BinaryDeserialize", + "BinaryDistance", + "BinaryFormat", + "BinaryImageQ", + "BinaryRead", + "BinaryReadList", + "BinarySerialize", + "BinaryWrite", + "BinCounts", + "BinLists", + "BinnedVariogramList", + "Binomial", + "BinomialDistribution", + "BinomialPointProcess", + "BinomialProcess", + "BinormalDistribution", + "BiorthogonalSplineWavelet", + "BioSequence", + "BioSequenceBackTranslateList", + "BioSequenceComplement", + "BioSequenceInstances", + "BioSequenceModify", + "BioSequencePlot", + "BioSequenceQ", + "BioSequenceReverseComplement", + "BioSequenceTranscribe", + "BioSequenceTranslate", + "BipartiteGraphQ", + "BiquadraticFilterModel", + "BirnbaumImportance", + "BirnbaumSaundersDistribution", + "BitAnd", + "BitClear", + "BitGet", + "BitLength", + "BitNot", + "BitOr", + "BitRate", + "BitSet", + "BitShiftLeft", + "BitShiftRight", + "BitXor", + "BiweightLocation", + "BiweightMidvariance", + "Black", + "BlackmanHarrisWindow", + "BlackmanNuttallWindow", + "BlackmanWindow", + "Blank", + "BlankForm", + "BlankNullSequence", + "BlankSequence", + "Blend", + "Block", + "BlockchainAddressData", + "BlockchainBase", + "BlockchainBlockData", + "BlockchainContractValue", + "BlockchainData", + "BlockchainGet", + "BlockchainKeyEncode", + "BlockchainPut", + "BlockchainTokenData", + "BlockchainTransaction", + "BlockchainTransactionData", + "BlockchainTransactionSign", + "BlockchainTransactionSubmit", + "BlockDiagonalMatrix", + "BlockLowerTriangularMatrix", + "BlockMap", + "BlockRandom", + "BlockUpperTriangularMatrix", + "BlomqvistBeta", + "BlomqvistBetaTest", + "Blue", + "Blur", + "Blurring", + "BodePlot", + "BohmanWindow", + "Bold", + "Bond", + "BondCount", + "BondLabels", + "BondLabelStyle", + "BondList", + "BondQ", + "Bookmarks", + "Boole", + "BooleanConsecutiveFunction", + "BooleanConvert", + "BooleanCountingFunction", + "BooleanFunction", + "BooleanGraph", + "BooleanMaxterms", + "BooleanMinimize", + "BooleanMinterms", + "BooleanQ", + "BooleanRegion", + "Booleans", + "BooleanStrings", + "BooleanTable", + "BooleanVariables", + "BorderDimensions", + "BorelTannerDistribution", + "Bottom", + "BottomHatTransform", + "BoundaryDiscretizeGraphics", + "BoundaryDiscretizeRegion", + "BoundaryMesh", + "BoundaryMeshRegion", + "BoundaryMeshRegionQ", + "BoundaryStyle", + "BoundedRegionQ", + "BoundingRegion", + "Bounds", + "Box", + "BoxBaselineShift", + "BoxData", + "BoxDimensions", + "Boxed", + "Boxes", + "BoxForm", + "BoxFormFormatTypes", + "BoxFrame", + "BoxID", + "BoxMargins", + "BoxMatrix", + "BoxObject", + "BoxRatios", + "BoxRotation", + "BoxRotationPoint", + "BoxStyle", + "BoxWhiskerChart", + "Bra", + "BracketingBar", + "BraKet", + "BrayCurtisDistance", + "BreadthFirstScan", + "Break", + "BridgeData", + "BrightnessEqualize", + "BroadcastStationData", + "Brown", + "BrownForsytheTest", + "BrownianBridgeProcess", + "BrowserCategory", + "BSplineBasis", + "BSplineCurve", + "BSplineCurve3DBox", + "BSplineCurve3DBoxOptions", + "BSplineCurveBox", + "BSplineCurveBoxOptions", + "BSplineFunction", + "BSplineSurface", + "BSplineSurface3DBox", + "BSplineSurface3DBoxOptions", + "BubbleChart", + "BubbleChart3D", + "BubbleScale", + "BubbleSizes", + "BuckyballGraph", + "BuildCompiledComponent", + "BuildingData", + "BulletGauge", + "BusinessDayQ", + "ButterflyGraph", + "ButterworthFilterModel", + "Button", + "ButtonBar", + "ButtonBox", + "ButtonBoxOptions", + "ButtonCell", + "ButtonContents", + "ButtonData", + "ButtonEvaluator", + "ButtonExpandable", + "ButtonFrame", + "ButtonFunction", + "ButtonMargins", + "ButtonMinHeight", + "ButtonNote", + "ButtonNotebook", + "ButtonSource", + "ButtonStyle", + "ButtonStyleMenuListing", + "Byte", + "ByteArray", + "ByteArrayFormat", + "ByteArrayFormatQ", + "ByteArrayQ", + "ByteArrayToString", + "ByteCount", + "ByteOrdering", + "C", + "CachedValue", + "CacheGraphics", + "CachePersistence", + "CalendarConvert", + "CalendarData", + "CalendarType", + "Callout", + "CalloutMarker", + "CalloutStyle", + "CallPacket", + "CanberraDistance", + "Cancel", + "CancelButton", + "CandlestickChart", + "CanonicalGraph", + "CanonicalizePolygon", + "CanonicalizePolyhedron", + "CanonicalizeRegion", + "CanonicalName", + "CanonicalWarpingCorrespondence", + "CanonicalWarpingDistance", + "CantorMesh", + "CantorStaircase", + "Canvas", + "Cap", + "CapForm", + "CapitalDifferentialD", + "Capitalize", + "CapsuleShape", + "CaptureRunning", + "CaputoD", + "CardinalBSplineBasis", + "CarlemanLinearize", + "CarlsonRC", + "CarlsonRD", + "CarlsonRE", + "CarlsonRF", + "CarlsonRG", + "CarlsonRJ", + "CarlsonRK", + "CarlsonRM", + "CarmichaelLambda", + "CaseOrdering", + "Cases", + "CaseSensitive", + "Cashflow", + "Casoratian", + "Cast", + "Catalan", + "CatalanNumber", + "Catch", + "CategoricalDistribution", + "Catenate", + "CatenateLayer", + "CauchyDistribution", + "CauchyMatrix", + "CauchyPointProcess", + "CauchyWindow", + "CayleyGraph", + "CDF", + "CDFDeploy", + "CDFInformation", + "CDFWavelet", + "Ceiling", + "CelestialSystem", + "Cell", + "CellAutoOverwrite", + "CellBaseline", + "CellBoundingBox", + "CellBracketOptions", + "CellChangeTimes", + "CellContents", + "CellContext", + "CellDingbat", + "CellDingbatMargin", + "CellDynamicExpression", + "CellEditDuplicate", + "CellElementsBoundingBox", + "CellElementSpacings", + "CellEpilog", + "CellEvaluationDuplicate", + "CellEvaluationFunction", + "CellEvaluationLanguage", + "CellEventActions", + "CellFrame", + "CellFrameColor", + "CellFrameLabelMargins", + "CellFrameLabels", + "CellFrameMargins", + "CellFrameStyle", + "CellGroup", + "CellGroupData", + "CellGrouping", + "CellGroupingRules", + "CellHorizontalScrolling", + "CellID", + "CellInsertionPointCell", + "CellLabel", + "CellLabelAutoDelete", + "CellLabelMargins", + "CellLabelPositioning", + "CellLabelStyle", + "CellLabelTemplate", + "CellMargins", + "CellObject", + "CellOpen", + "CellPrint", + "CellProlog", + "Cells", + "CellSize", + "CellStyle", + "CellTags", + "CellTrayPosition", + "CellTrayWidgets", + "CellularAutomaton", + "CensoredDistribution", + "Censoring", + "Center", + "CenterArray", + "CenterDot", + "CenteredInterval", + "CentralFeature", + "CentralMoment", + "CentralMomentGeneratingFunction", + "Cepstrogram", + "CepstrogramArray", + "CepstrumArray", + "CForm", + "ChampernowneNumber", + "ChangeOptions", + "ChannelBase", + "ChannelBrokerAction", + "ChannelDatabin", + "ChannelHistoryLength", + "ChannelListen", + "ChannelListener", + "ChannelListeners", + "ChannelListenerWait", + "ChannelObject", + "ChannelPreSendFunction", + "ChannelReceiverFunction", + "ChannelSend", + "ChannelSubscribers", + "ChanVeseBinarize", + "Character", + "CharacterCounts", + "CharacterEncoding", + "CharacterEncodingsPath", + "CharacteristicFunction", + "CharacteristicPolynomial", + "CharacterName", + "CharacterNormalize", + "CharacterRange", + "Characters", + "ChartBaseStyle", + "ChartElementData", + "ChartElementDataFunction", + "ChartElementFunction", + "ChartElements", + "ChartLabels", + "ChartLayout", + "ChartLegends", + "ChartStyle", + "Chebyshev1FilterModel", + "Chebyshev2FilterModel", + "ChebyshevDistance", + "ChebyshevT", + "ChebyshevU", + "Check", + "CheckAbort", + "CheckAll", + "CheckArguments", + "Checkbox", + "CheckboxBar", + "CheckboxBox", + "CheckboxBoxOptions", + "ChemicalConvert", + "ChemicalData", + "ChemicalFormula", + "ChemicalInstance", + "ChemicalReaction", + "ChessboardDistance", + "ChiDistribution", + "ChineseRemainder", + "ChiSquareDistribution", + "ChoiceButtons", + "ChoiceDialog", + "CholeskyDecomposition", + "Chop", + "ChromaticityPlot", + "ChromaticityPlot3D", + "ChromaticPolynomial", + "Circle", + "CircleBox", + "CircleDot", + "CircleMinus", + "CirclePlus", + "CirclePoints", + "CircleThrough", + "CircleTimes", + "CirculantGraph", + "CircularArcThrough", + "CircularOrthogonalMatrixDistribution", + "CircularQuaternionMatrixDistribution", + "CircularRealMatrixDistribution", + "CircularSymplecticMatrixDistribution", + "CircularUnitaryMatrixDistribution", + "Circumsphere", + "CityData", + "ClassifierFunction", + "ClassifierInformation", + "ClassifierMeasurements", + "ClassifierMeasurementsObject", + "Classify", + "ClassPriors", + "Clear", + "ClearAll", + "ClearAttributes", + "ClearCookies", + "ClearPermissions", + "ClearSystemCache", + "ClebschGordan", + "ClickPane", + "ClickToCopy", + "ClickToCopyEnabled", + "Clip", + "ClipboardNotebook", + "ClipFill", + "ClippingStyle", + "ClipPlanes", + "ClipPlanesStyle", + "ClipRange", + "Clock", + "ClockGauge", + "ClockwiseContourIntegral", + "Close", + "Closed", + "CloseKernels", + "ClosenessCentrality", + "Closing", + "ClosingAutoSave", + "ClosingEvent", + "CloudAccountData", + "CloudBase", + "CloudConnect", + "CloudConnections", + "CloudDeploy", + "CloudDirectory", + "CloudDisconnect", + "CloudEvaluate", + "CloudExport", + "CloudExpression", + "CloudExpressions", + "CloudFunction", + "CloudGet", + "CloudImport", + "CloudLoggingData", + "CloudObject", + "CloudObjectInformation", + "CloudObjectInformationData", + "CloudObjectNameFormat", + "CloudObjects", + "CloudObjectURLType", + "CloudPublish", + "CloudPut", + "CloudRenderingMethod", + "CloudSave", + "CloudShare", + "CloudSubmit", + "CloudSymbol", + "CloudUnshare", + "CloudUserID", + "ClusterClassify", + "ClusterDissimilarityFunction", + "ClusteringComponents", + "ClusteringMeasurements", + "ClusteringTree", + "CMYKColor", + "Coarse", + "CodeAssistOptions", + "Coefficient", + "CoefficientArrays", + "CoefficientDomain", + "CoefficientList", + "CoefficientRules", + "CoifletWavelet", + "Collect", + "CollinearPoints", + "Colon", + "ColonForm", + "ColorBalance", + "ColorCombine", + "ColorConvert", + "ColorCoverage", + "ColorData", + "ColorDataFunction", + "ColorDetect", + "ColorDistance", + "ColorFunction", + "ColorFunctionBinning", + "ColorFunctionScaling", + "Colorize", + "ColorNegate", + "ColorOutput", + "ColorProfileData", + "ColorQ", + "ColorQuantize", + "ColorReplace", + "ColorRules", + "ColorSelectorSettings", + "ColorSeparate", + "ColorSetter", + "ColorSetterBox", + "ColorSetterBoxOptions", + "ColorSlider", + "ColorsNear", + "ColorSpace", + "ColorToneMapping", + "Column", + "ColumnAlignments", + "ColumnBackgrounds", + "ColumnForm", + "ColumnLines", + "ColumnsEqual", + "ColumnSpacings", + "ColumnWidths", + "CombinatorB", + "CombinatorC", + "CombinatorI", + "CombinatorK", + "CombinatorS", + "CombinatorW", + "CombinatorY", + "CombinedEntityClass", + "CombinerFunction", + "CometData", + "CommonDefaultFormatTypes", + "Commonest", + "CommonestFilter", + "CommonName", + "CommonUnits", + "CommunityBoundaryStyle", + "CommunityGraphPlot", + "CommunityLabels", + "CommunityRegionStyle", + "CompanyData", + "CompatibleUnitQ", + "CompilationOptions", + "CompilationTarget", + "Compile", + "Compiled", + "CompiledCodeFunction", + "CompiledComponent", + "CompiledExpressionDeclaration", + "CompiledFunction", + "CompiledLayer", + "CompilerCallback", + "CompilerEnvironment", + "CompilerEnvironmentAppend", + "CompilerEnvironmentAppendTo", + "CompilerEnvironmentObject", + "CompilerOptions", + "Complement", + "ComplementedEntityClass", + "CompleteGraph", + "CompleteGraphQ", + "CompleteIntegral", + "CompleteKaryTree", + "CompletionsListPacket", + "Complex", + "ComplexArrayPlot", + "ComplexContourPlot", + "Complexes", + "ComplexExpand", + "ComplexInfinity", + "ComplexityFunction", + "ComplexListPlot", + "ComplexPlot", + "ComplexPlot3D", + "ComplexRegionPlot", + "ComplexStreamPlot", + "ComplexVectorPlot", + "ComponentMeasurements", + "ComponentwiseContextMenu", + "Compose", + "ComposeList", + "ComposeSeries", + "CompositeQ", + "Composition", + "CompoundElement", + "CompoundExpression", + "CompoundPoissonDistribution", + "CompoundPoissonProcess", + "CompoundRenewalProcess", + "Compress", + "CompressedData", + "CompressionLevel", + "ComputeUncertainty", + "ConcaveHullMesh", + "Condition", + "ConditionalExpression", + "Conditioned", + "Cone", + "ConeBox", + "ConfidenceLevel", + "ConfidenceRange", + "ConfidenceTransform", + "ConfigurationPath", + "Confirm", + "ConfirmAssert", + "ConfirmBy", + "ConfirmMatch", + "ConfirmQuiet", + "ConformationMethod", + "ConformAudio", + "ConformImages", + "Congruent", + "ConicGradientFilling", + "ConicHullRegion", + "ConicHullRegion3DBox", + "ConicHullRegion3DBoxOptions", + "ConicHullRegionBox", + "ConicHullRegionBoxOptions", + "ConicOptimization", + "Conjugate", + "ConjugateTranspose", + "Conjunction", + "Connect", + "ConnectedComponents", + "ConnectedGraphComponents", + "ConnectedGraphQ", + "ConnectedMeshComponents", + "ConnectedMoleculeComponents", + "ConnectedMoleculeQ", + "ConnectionSettings", + "ConnectLibraryCallbackFunction", + "ConnectSystemModelComponents", + "ConnectSystemModelController", + "ConnesWindow", + "ConoverTest", + "ConservativeConvectionPDETerm", + "ConsoleMessage", + "Constant", + "ConstantArray", + "ConstantArrayLayer", + "ConstantImage", + "ConstantPlusLayer", + "ConstantRegionQ", + "Constants", + "ConstantTimesLayer", + "ConstellationData", + "ConstrainedMax", + "ConstrainedMin", + "Construct", + "Containing", + "ContainsAll", + "ContainsAny", + "ContainsExactly", + "ContainsNone", + "ContainsOnly", + "ContentDetectorFunction", + "ContentFieldOptions", + "ContentLocationFunction", + "ContentObject", + "ContentPadding", + "ContentsBoundingBox", + "ContentSelectable", + "ContentSize", + "Context", + "ContextMenu", + "Contexts", + "ContextToFileName", + "Continuation", + "Continue", + "ContinuedFraction", + "ContinuedFractionK", + "ContinuousAction", + "ContinuousMarkovProcess", + "ContinuousTask", + "ContinuousTimeModelQ", + "ContinuousWaveletData", + "ContinuousWaveletTransform", + "ContourDetect", + "ContourGraphics", + "ContourIntegral", + "ContourLabels", + "ContourLines", + "ContourPlot", + "ContourPlot3D", + "Contours", + "ContourShading", + "ContourSmoothing", + "ContourStyle", + "ContraharmonicMean", + "ContrastiveLossLayer", + "Control", + "ControlActive", + "ControlAlignment", + "ControlGroupContentsBox", + "ControllabilityGramian", + "ControllabilityMatrix", + "ControllableDecomposition", + "ControllableModelQ", + "ControllerDuration", + "ControllerInformation", + "ControllerInformationData", + "ControllerLinking", + "ControllerManipulate", + "ControllerMethod", + "ControllerPath", + "ControllerState", + "ControlPlacement", + "ControlsRendering", + "ControlType", + "ConvectionPDETerm", + "Convergents", + "ConversionOptions", + "ConversionRules", + "ConvertToPostScript", + "ConvertToPostScriptPacket", + "ConvexHullMesh", + "ConvexHullRegion", + "ConvexOptimization", + "ConvexPolygonQ", + "ConvexPolyhedronQ", + "ConvexRegionQ", + "ConvolutionLayer", + "Convolve", + "ConwayGroupCo1", + "ConwayGroupCo2", + "ConwayGroupCo3", + "CookieFunction", + "Cookies", + "CoordinateBoundingBox", + "CoordinateBoundingBoxArray", + "CoordinateBounds", + "CoordinateBoundsArray", + "CoordinateChartData", + "CoordinatesToolOptions", + "CoordinateTransform", + "CoordinateTransformData", + "CoplanarPoints", + "CoprimeQ", + "Coproduct", + "CopulaDistribution", + "Copyable", + "CopyDatabin", + "CopyDirectory", + "CopyFile", + "CopyFunction", + "CopyTag", + "CopyToClipboard", + "CoreNilpotentDecomposition", + "CornerFilter", + "CornerNeighbors", + "Correlation", + "CorrelationDistance", + "CorrelationFunction", + "CorrelationTest", + "Cos", + "Cosh", + "CoshIntegral", + "CosineDistance", + "CosineWindow", + "CosIntegral", + "Cot", + "Coth", + "CoulombF", + "CoulombG", + "CoulombH1", + "CoulombH2", + "Count", + "CountDistinct", + "CountDistinctBy", + "CounterAssignments", + "CounterBox", + "CounterBoxOptions", + "CounterClockwiseContourIntegral", + "CounterEvaluator", + "CounterFunction", + "CounterIncrements", + "CounterStyle", + "CounterStyleMenuListing", + "CountRoots", + "CountryData", + "Counts", + "CountsBy", + "Covariance", + "CovarianceEstimatorFunction", + "CovarianceFunction", + "CoxianDistribution", + "CoxIngersollRossProcess", + "CoxModel", + "CoxModelFit", + "CramerVonMisesTest", + "CreateArchive", + "CreateCellID", + "CreateChannel", + "CreateCloudExpression", + "CreateCompilerEnvironment", + "CreateDatabin", + "CreateDataStructure", + "CreateDataSystemModel", + "CreateDialog", + "CreateDirectory", + "CreateDocument", + "CreateFile", + "CreateIntermediateDirectories", + "CreateLicenseEntitlement", + "CreateManagedLibraryExpression", + "CreateNotebook", + "CreatePacletArchive", + "CreatePalette", + "CreatePermissionsGroup", + "CreateScheduledTask", + "CreateSearchIndex", + "CreateSystemModel", + "CreateTemporary", + "CreateTypeInstance", + "CreateUUID", + "CreateWindow", + "CriterionFunction", + "CriticalityFailureImportance", + "CriticalitySuccessImportance", + "CriticalSection", + "Cross", + "CrossEntropyLossLayer", + "CrossingCount", + "CrossingDetect", + "CrossingPolygon", + "CrossMatrix", + "Csc", + "Csch", + "CSGRegion", + "CSGRegionQ", + "CSGRegionTree", + "CTCLossLayer", + "Cube", + "CubeRoot", + "Cubics", + "Cuboid", + "CuboidBox", + "CuboidBoxOptions", + "Cumulant", + "CumulantGeneratingFunction", + "CumulativeFeatureImpactPlot", + "Cup", + "CupCap", + "Curl", + "CurlyDoubleQuote", + "CurlyQuote", + "CurrencyConvert", + "CurrentDate", + "CurrentImage", + "CurrentNotebookImage", + "CurrentScreenImage", + "CurrentValue", + "Curry", + "CurryApplied", + "CurvatureFlowFilter", + "CurveClosed", + "Cyan", + "CycleGraph", + "CycleIndexPolynomial", + "Cycles", + "CyclicGroup", + "Cyclotomic", + "Cylinder", + "CylinderBox", + "CylinderBoxOptions", + "CylindricalDecomposition", + "CylindricalDecompositionFunction", + "D", + "DagumDistribution", + "DamData", + "DamerauLevenshteinDistance", + "DampingFactor", + "Darker", + "Dashed", + "Dashing", + "DatabaseConnect", + "DatabaseDisconnect", + "DatabaseReference", + "Databin", + "DatabinAdd", + "DatabinRemove", + "Databins", + "DatabinSubmit", + "DatabinUpload", + "DataCompression", + "DataDistribution", + "DataRange", + "DataReversed", + "Dataset", + "DatasetDisplayPanel", + "DatasetTheme", + "DataStructure", + "DataStructureQ", + "Date", + "DateBounds", + "Dated", + "DateDelimiters", + "DateDifference", + "DatedUnit", + "DateFormat", + "DateFunction", + "DateGranularity", + "DateHistogram", + "DateInterval", + "DateList", + "DateListLogPlot", + "DateListPlot", + "DateListStepPlot", + "DateObject", + "DateObjectQ", + "DateOverlapsQ", + "DatePattern", + "DatePlus", + "DateRange", + "DateReduction", + "DateScale", + "DateSelect", + "DateString", + "DateTicksFormat", + "DateValue", + "DateWithinQ", + "DaubechiesWavelet", + "DavisDistribution", + "DawsonF", + "DayCount", + "DayCountConvention", + "DayHemisphere", + "DaylightQ", + "DayMatchQ", + "DayName", + "DayNightTerminator", + "DayPlus", + "DayRange", + "DayRound", + "DeBruijnGraph", + "DeBruijnSequence", + "Debug", + "DebugTag", + "Decapitalize", + "Decimal", + "DecimalForm", + "DeclareCompiledComponent", + "DeclareKnownSymbols", + "DeclarePackage", + "Decompose", + "DeconvolutionLayer", + "Decrement", + "Decrypt", + "DecryptFile", + "DedekindEta", + "DeepSpaceProbeData", + "Default", + "Default2DTool", + "Default3DTool", + "DefaultAttachedCellStyle", + "DefaultAxesStyle", + "DefaultBaseStyle", + "DefaultBoxStyle", + "DefaultButton", + "DefaultColor", + "DefaultControlPlacement", + "DefaultDockedCellStyle", + "DefaultDuplicateCellStyle", + "DefaultDuration", + "DefaultElement", + "DefaultFaceGridsStyle", + "DefaultFieldHintStyle", + "DefaultFont", + "DefaultFontProperties", + "DefaultFormatType", + "DefaultFrameStyle", + "DefaultFrameTicksStyle", + "DefaultGridLinesStyle", + "DefaultInlineFormatType", + "DefaultInputFormatType", + "DefaultLabelStyle", + "DefaultMenuStyle", + "DefaultNaturalLanguage", + "DefaultNewCellStyle", + "DefaultNewInlineCellStyle", + "DefaultNotebook", + "DefaultOptions", + "DefaultOutputFormatType", + "DefaultPrintPrecision", + "DefaultStyle", + "DefaultStyleDefinitions", + "DefaultTextFormatType", + "DefaultTextInlineFormatType", + "DefaultTicksStyle", + "DefaultTooltipStyle", + "DefaultValue", + "DefaultValues", + "Defer", + "DefineExternal", + "DefineInputStreamMethod", + "DefineOutputStreamMethod", + "DefineResourceFunction", + "Definition", + "Degree", + "DegreeCentrality", + "DegreeGraphDistribution", + "DegreeLexicographic", + "DegreeReverseLexicographic", + "DEigensystem", + "DEigenvalues", + "Deinitialization", + "Del", + "DelaunayMesh", + "Delayed", + "Deletable", + "Delete", + "DeleteAdjacentDuplicates", + "DeleteAnomalies", + "DeleteBorderComponents", + "DeleteCases", + "DeleteChannel", + "DeleteCloudExpression", + "DeleteContents", + "DeleteDirectory", + "DeleteDuplicates", + "DeleteDuplicatesBy", + "DeleteElements", + "DeleteFile", + "DeleteMissing", + "DeleteObject", + "DeletePermissionsKey", + "DeleteSearchIndex", + "DeleteSmallComponents", + "DeleteStopwords", + "DeleteWithContents", + "DeletionWarning", + "DelimitedArray", + "DelimitedSequence", + "Delimiter", + "DelimiterAutoMatching", + "DelimiterFlashTime", + "DelimiterMatching", + "Delimiters", + "DeliveryFunction", + "Dendrogram", + "Denominator", + "DensityGraphics", + "DensityHistogram", + "DensityPlot", + "DensityPlot3D", + "DependentVariables", + "Deploy", + "Deployed", + "Depth", + "DepthFirstScan", + "Derivative", + "DerivativeFilter", + "DerivativePDETerm", + "DerivedKey", + "DescriptorStateSpace", + "DesignMatrix", + "DestroyAfterEvaluation", + "Det", + "DeviceClose", + "DeviceConfigure", + "DeviceExecute", + "DeviceExecuteAsynchronous", + "DeviceObject", + "DeviceOpen", + "DeviceOpenQ", + "DeviceRead", + "DeviceReadBuffer", + "DeviceReadLatest", + "DeviceReadList", + "DeviceReadTimeSeries", + "Devices", + "DeviceStreams", + "DeviceWrite", + "DeviceWriteBuffer", + "DGaussianWavelet", + "DiacriticalPositioning", + "Diagonal", + "DiagonalizableMatrixQ", + "DiagonalMatrix", + "DiagonalMatrixQ", + "Dialog", + "DialogIndent", + "DialogInput", + "DialogLevel", + "DialogNotebook", + "DialogProlog", + "DialogReturn", + "DialogSymbols", + "Diamond", + "DiamondMatrix", + "DiceDissimilarity", + "DictionaryLookup", + "DictionaryWordQ", + "DifferenceDelta", + "DifferenceOrder", + "DifferenceQuotient", + "DifferenceRoot", + "DifferenceRootReduce", + "Differences", + "DifferentialD", + "DifferentialRoot", + "DifferentialRootReduce", + "DifferentiatorFilter", + "DiffusionPDETerm", + "DiggleGatesPointProcess", + "DiggleGrattonPointProcess", + "DigitalSignature", + "DigitBlock", + "DigitBlockMinimum", + "DigitCharacter", + "DigitCount", + "DigitQ", + "DihedralAngle", + "DihedralGroup", + "Dilation", + "DimensionalCombinations", + "DimensionalMeshComponents", + "DimensionReduce", + "DimensionReducerFunction", + "DimensionReduction", + "Dimensions", + "DiracComb", + "DiracDelta", + "DirectedEdge", + "DirectedEdges", + "DirectedGraph", + "DirectedGraphQ", + "DirectedInfinity", + "Direction", + "DirectionalLight", + "Directive", + "Directory", + "DirectoryName", + "DirectoryQ", + "DirectoryStack", + "DirichletBeta", + "DirichletCharacter", + "DirichletCondition", + "DirichletConvolve", + "DirichletDistribution", + "DirichletEta", + "DirichletL", + "DirichletLambda", + "DirichletTransform", + "DirichletWindow", + "DisableConsolePrintPacket", + "DisableFormatting", + "DiscreteAsymptotic", + "DiscreteChirpZTransform", + "DiscreteConvolve", + "DiscreteDelta", + "DiscreteHadamardTransform", + "DiscreteIndicator", + "DiscreteInputOutputModel", + "DiscreteLimit", + "DiscreteLQEstimatorGains", + "DiscreteLQRegulatorGains", + "DiscreteLyapunovSolve", + "DiscreteMarkovProcess", + "DiscreteMaxLimit", + "DiscreteMinLimit", + "DiscretePlot", + "DiscretePlot3D", + "DiscreteRatio", + "DiscreteRiccatiSolve", + "DiscreteShift", + "DiscreteTimeModelQ", + "DiscreteUniformDistribution", + "DiscreteVariables", + "DiscreteWaveletData", + "DiscreteWaveletPacketTransform", + "DiscreteWaveletTransform", + "DiscretizeGraphics", + "DiscretizeRegion", + "Discriminant", + "DisjointQ", + "Disjunction", + "Disk", + "DiskBox", + "DiskBoxOptions", + "DiskMatrix", + "DiskSegment", + "Dispatch", + "DispatchQ", + "DispersionEstimatorFunction", + "Display", + "DisplayAllSteps", + "DisplayEndPacket", + "DisplayForm", + "DisplayFunction", + "DisplayPacket", + "DisplayRules", + "DisplayString", + "DisplayTemporary", + "DisplayWith", + "DisplayWithRef", + "DisplayWithVariable", + "DistanceFunction", + "DistanceMatrix", + "DistanceTransform", + "Distribute", + "Distributed", + "DistributedContexts", + "DistributeDefinitions", + "DistributionChart", + "DistributionDomain", + "DistributionFitTest", + "DistributionParameterAssumptions", + "DistributionParameterQ", + "Dithering", + "Div", + "Divergence", + "Divide", + "DivideBy", + "Dividers", + "DivideSides", + "Divisible", + "Divisors", + "DivisorSigma", + "DivisorSum", + "DMSList", + "DMSString", + "Do", + "DockedCell", + "DockedCells", + "DocumentGenerator", + "DocumentGeneratorInformation", + "DocumentGeneratorInformationData", + "DocumentGenerators", + "DocumentNotebook", + "DocumentWeightingRules", + "Dodecahedron", + "DomainRegistrationInformation", + "DominantColors", + "DominatorTreeGraph", + "DominatorVertexList", + "DOSTextFormat", + "Dot", + "DotDashed", + "DotEqual", + "DotLayer", + "DotPlusLayer", + "Dotted", + "DoubleBracketingBar", + "DoubleContourIntegral", + "DoubleDownArrow", + "DoubleLeftArrow", + "DoubleLeftRightArrow", + "DoubleLeftTee", + "DoubleLongLeftArrow", + "DoubleLongLeftRightArrow", + "DoubleLongRightArrow", + "DoubleRightArrow", + "DoubleRightTee", + "DoubleUpArrow", + "DoubleUpDownArrow", + "DoubleVerticalBar", + "DoublyInfinite", + "Down", + "DownArrow", + "DownArrowBar", + "DownArrowUpArrow", + "DownLeftRightVector", + "DownLeftTeeVector", + "DownLeftVector", + "DownLeftVectorBar", + "DownRightTeeVector", + "DownRightVector", + "DownRightVectorBar", + "Downsample", + "DownTee", + "DownTeeArrow", + "DownValues", + "DownValuesFunction", + "DragAndDrop", + "DrawBackFaces", + "DrawEdges", + "DrawFrontFaces", + "DrawHighlighted", + "DrazinInverse", + "Drop", + "DropoutLayer", + "DropShadowing", + "DSolve", + "DSolveChangeVariables", + "DSolveValue", + "Dt", + "DualLinearProgramming", + "DualPlanarGraph", + "DualPolyhedron", + "DualSystemsModel", + "DumpGet", + "DumpSave", + "DuplicateFreeQ", + "Duration", + "Dynamic", + "DynamicBox", + "DynamicBoxOptions", + "DynamicEvaluationTimeout", + "DynamicGeoGraphics", + "DynamicImage", + "DynamicLocation", + "DynamicModule", + "DynamicModuleBox", + "DynamicModuleBoxOptions", + "DynamicModuleParent", + "DynamicModuleValues", + "DynamicName", + "DynamicNamespace", + "DynamicReference", + "DynamicSetting", + "DynamicUpdating", + "DynamicWrapper", + "DynamicWrapperBox", + "DynamicWrapperBoxOptions", + "E", + "EarthImpactData", + "EarthquakeData", + "EccentricityCentrality", + "Echo", + "EchoEvaluation", + "EchoFunction", + "EchoLabel", + "EchoTiming", + "EclipseType", + "EdgeAdd", + "EdgeBetweennessCentrality", + "EdgeCapacity", + "EdgeCapForm", + "EdgeChromaticNumber", + "EdgeColor", + "EdgeConnectivity", + "EdgeContract", + "EdgeCost", + "EdgeCount", + "EdgeCoverQ", + "EdgeCycleMatrix", + "EdgeDashing", + "EdgeDelete", + "EdgeDetect", + "EdgeForm", + "EdgeIndex", + "EdgeJoinForm", + "EdgeLabeling", + "EdgeLabels", + "EdgeLabelStyle", + "EdgeList", + "EdgeOpacity", + "EdgeQ", + "EdgeRenderingFunction", + "EdgeRules", + "EdgeShapeFunction", + "EdgeStyle", + "EdgeTaggedGraph", + "EdgeTaggedGraphQ", + "EdgeTags", + "EdgeThickness", + "EdgeTransitiveGraphQ", + "EdgeValueRange", + "EdgeValueSizes", + "EdgeWeight", + "EdgeWeightedGraphQ", + "Editable", + "EditButtonSettings", + "EditCellTagsSettings", + "EditDistance", + "EffectiveInterest", + "Eigensystem", + "Eigenvalues", + "EigenvectorCentrality", + "Eigenvectors", + "Element", + "ElementData", + "ElementwiseLayer", + "ElidedForms", + "Eliminate", + "EliminationOrder", + "Ellipsoid", + "EllipticE", + "EllipticExp", + "EllipticExpPrime", + "EllipticF", + "EllipticFilterModel", + "EllipticK", + "EllipticLog", + "EllipticNomeQ", + "EllipticPi", + "EllipticReducedHalfPeriods", + "EllipticTheta", + "EllipticThetaPrime", + "EmbedCode", + "EmbeddedHTML", + "EmbeddedService", + "EmbeddedSQLEntityClass", + "EmbeddedSQLExpression", + "EmbeddingLayer", + "EmbeddingObject", + "EmitSound", + "EmphasizeSyntaxErrors", + "EmpiricalDistribution", + "Empty", + "EmptyGraphQ", + "EmptyRegion", + "EmptySpaceF", + "EnableConsolePrintPacket", + "Enabled", + "Enclose", + "Encode", + "Encrypt", + "EncryptedObject", + "EncryptFile", + "End", + "EndAdd", + "EndDialogPacket", + "EndOfBuffer", + "EndOfFile", + "EndOfLine", + "EndOfString", + "EndPackage", + "EngineEnvironment", + "EngineeringForm", + "Enter", + "EnterExpressionPacket", + "EnterTextPacket", + "Entity", + "EntityClass", + "EntityClassList", + "EntityCopies", + "EntityFunction", + "EntityGroup", + "EntityInstance", + "EntityList", + "EntityPrefetch", + "EntityProperties", + "EntityProperty", + "EntityPropertyClass", + "EntityRegister", + "EntityStore", + "EntityStores", + "EntityTypeName", + "EntityUnregister", + "EntityValue", + "Entropy", + "EntropyFilter", + "Environment", + "Epilog", + "EpilogFunction", + "Equal", + "EqualColumns", + "EqualRows", + "EqualTilde", + "EqualTo", + "EquatedTo", + "Equilibrium", + "EquirippleFilterKernel", + "Equivalent", + "Erf", + "Erfc", + "Erfi", + "ErlangB", + "ErlangC", + "ErlangDistribution", + "Erosion", + "ErrorBox", + "ErrorBoxOptions", + "ErrorNorm", + "ErrorPacket", + "ErrorsDialogSettings", + "EscapeRadius", + "EstimatedBackground", + "EstimatedDistribution", + "EstimatedPointNormals", + "EstimatedPointProcess", + "EstimatedProcess", + "EstimatedVariogramModel", + "EstimatorGains", + "EstimatorRegulator", + "EuclideanDistance", + "EulerAngles", + "EulerCharacteristic", + "EulerE", + "EulerGamma", + "EulerianGraphQ", + "EulerMatrix", + "EulerPhi", + "Evaluatable", + "Evaluate", + "Evaluated", + "EvaluatePacket", + "EvaluateScheduledTask", + "EvaluationBox", + "EvaluationCell", + "EvaluationCompletionAction", + "EvaluationData", + "EvaluationElements", + "EvaluationEnvironment", + "EvaluationMode", + "EvaluationMonitor", + "EvaluationNotebook", + "EvaluationObject", + "EvaluationOrder", + "EvaluationPrivileges", + "EvaluationRateLimit", + "Evaluator", + "EvaluatorNames", + "EvenQ", + "EventData", + "EventEvaluator", + "EventHandler", + "EventHandlerTag", + "EventLabels", + "EventSeries", + "ExactBlackmanWindow", + "ExactNumberQ", + "ExactRootIsolation", + "ExampleData", + "Except", + "ExcludedContexts", + "ExcludedForms", + "ExcludedLines", + "ExcludedPhysicalQuantities", + "ExcludePods", + "Exclusions", + "ExclusionsStyle", + "Exists", + "Exit", + "ExitDialog", + "ExoplanetData", + "Exp", + "Expand", + "ExpandAll", + "ExpandDenominator", + "ExpandFileName", + "ExpandNumerator", + "Expectation", + "ExpectationE", + "ExpectedValue", + "ExpGammaDistribution", + "ExpIntegralE", + "ExpIntegralEi", + "ExpirationDate", + "Exponent", + "ExponentFunction", + "ExponentialDistribution", + "ExponentialFamily", + "ExponentialGeneratingFunction", + "ExponentialMovingAverage", + "ExponentialPowerDistribution", + "ExponentPosition", + "ExponentStep", + "Export", + "ExportAutoReplacements", + "ExportByteArray", + "ExportForm", + "ExportPacket", + "ExportString", + "Expression", + "ExpressionCell", + "ExpressionGraph", + "ExpressionPacket", + "ExpressionTree", + "ExpressionUUID", + "ExpToTrig", + "ExtendedEntityClass", + "ExtendedGCD", + "Extension", + "ExtentElementFunction", + "ExtentMarkers", + "ExtentSize", + "ExternalBundle", + "ExternalCall", + "ExternalDataCharacterEncoding", + "ExternalEvaluate", + "ExternalFunction", + "ExternalFunctionName", + "ExternalIdentifier", + "ExternalObject", + "ExternalOptions", + "ExternalSessionObject", + "ExternalSessions", + "ExternalStorageBase", + "ExternalStorageDownload", + "ExternalStorageGet", + "ExternalStorageObject", + "ExternalStoragePut", + "ExternalStorageUpload", + "ExternalTypeSignature", + "ExternalValue", + "Extract", + "ExtractArchive", + "ExtractLayer", + "ExtractPacletArchive", + "ExtremeValueDistribution", + "FaceAlign", + "FaceForm", + "FaceGrids", + "FaceGridsStyle", + "FaceRecognize", + "FacialFeatures", + "Factor", + "FactorComplete", + "Factorial", + "Factorial2", + "FactorialMoment", + "FactorialMomentGeneratingFunction", + "FactorialPower", + "FactorInteger", + "FactorList", + "FactorSquareFree", + "FactorSquareFreeList", + "FactorTerms", + "FactorTermsList", + "Fail", + "Failure", + "FailureAction", + "FailureDistribution", + "FailureQ", + "False", + "FareySequence", + "FARIMAProcess", + "FeatureDistance", + "FeatureExtract", + "FeatureExtraction", + "FeatureExtractor", + "FeatureExtractorFunction", + "FeatureImpactPlot", + "FeatureNames", + "FeatureNearest", + "FeatureSpacePlot", + "FeatureSpacePlot3D", + "FeatureTypes", + "FeatureValueDependencyPlot", + "FeatureValueImpactPlot", + "FEDisableConsolePrintPacket", + "FeedbackLinearize", + "FeedbackSector", + "FeedbackSectorStyle", + "FeedbackType", + "FEEnableConsolePrintPacket", + "FetalGrowthData", + "Fibonacci", + "Fibonorial", + "FieldCompletionFunction", + "FieldHint", + "FieldHintStyle", + "FieldMasked", + "FieldSize", + "File", + "FileBaseName", + "FileByteCount", + "FileConvert", + "FileDate", + "FileExistsQ", + "FileExtension", + "FileFormat", + "FileFormatProperties", + "FileFormatQ", + "FileHandler", + "FileHash", + "FileInformation", + "FileName", + "FileNameDepth", + "FileNameDialogSettings", + "FileNameDrop", + "FileNameForms", + "FileNameJoin", + "FileNames", + "FileNameSetter", + "FileNameSplit", + "FileNameTake", + "FileNameToFormatList", + "FilePrint", + "FileSize", + "FileSystemMap", + "FileSystemScan", + "FileSystemTree", + "FileTemplate", + "FileTemplateApply", + "FileType", + "FilledCurve", + "FilledCurveBox", + "FilledCurveBoxOptions", + "FilledTorus", + "FillForm", + "Filling", + "FillingStyle", + "FillingTransform", + "FilteredEntityClass", + "FilterRules", + "FinancialBond", + "FinancialData", + "FinancialDerivative", + "FinancialIndicator", + "Find", + "FindAnomalies", + "FindArgMax", + "FindArgMin", + "FindChannels", + "FindClique", + "FindClusters", + "FindCookies", + "FindCurvePath", + "FindCycle", + "FindDevices", + "FindDistribution", + "FindDistributionParameters", + "FindDivisions", + "FindEdgeColoring", + "FindEdgeCover", + "FindEdgeCut", + "FindEdgeIndependentPaths", + "FindEquationalProof", + "FindEulerianCycle", + "FindExternalEvaluators", + "FindFaces", + "FindFile", + "FindFit", + "FindFormula", + "FindFundamentalCycles", + "FindGeneratingFunction", + "FindGeoLocation", + "FindGeometricConjectures", + "FindGeometricTransform", + "FindGraphCommunities", + "FindGraphIsomorphism", + "FindGraphPartition", + "FindHamiltonianCycle", + "FindHamiltonianPath", + "FindHiddenMarkovStates", + "FindImageText", + "FindIndependentEdgeSet", + "FindIndependentVertexSet", + "FindInstance", + "FindIntegerNullVector", + "FindIsomers", + "FindIsomorphicSubgraph", + "FindKClan", + "FindKClique", + "FindKClub", + "FindKPlex", + "FindLibrary", + "FindLinearRecurrence", + "FindList", + "FindMatchingColor", + "FindMaximum", + "FindMaximumCut", + "FindMaximumFlow", + "FindMaxValue", + "FindMeshDefects", + "FindMinimum", + "FindMinimumCostFlow", + "FindMinimumCut", + "FindMinValue", + "FindMoleculeSubstructure", + "FindPath", + "FindPeaks", + "FindPermutation", + "FindPlanarColoring", + "FindPointProcessParameters", + "FindPostmanTour", + "FindProcessParameters", + "FindRegionTransform", + "FindRepeat", + "FindRoot", + "FindSequenceFunction", + "FindSettings", + "FindShortestPath", + "FindShortestTour", + "FindSpanningTree", + "FindSubgraphIsomorphism", + "FindSystemModelEquilibrium", + "FindTextualAnswer", + "FindThreshold", + "FindTransientRepeat", + "FindVertexColoring", + "FindVertexCover", + "FindVertexCut", + "FindVertexIndependentPaths", + "Fine", + "FinishDynamic", + "FiniteAbelianGroupCount", + "FiniteGroupCount", + "FiniteGroupData", + "First", + "FirstCase", + "FirstPassageTimeDistribution", + "FirstPosition", + "FischerGroupFi22", + "FischerGroupFi23", + "FischerGroupFi24Prime", + "FisherHypergeometricDistribution", + "FisherRatioTest", + "FisherZDistribution", + "Fit", + "FitAll", + "FitRegularization", + "FittedModel", + "FixedOrder", + "FixedPoint", + "FixedPointList", + "FlashSelection", + "Flat", + "FlatShading", + "Flatten", + "FlattenAt", + "FlattenLayer", + "FlatTopWindow", + "FlightData", + "FlipView", + "Floor", + "FlowPolynomial", + "Fold", + "FoldList", + "FoldPair", + "FoldPairList", + "FoldWhile", + "FoldWhileList", + "FollowRedirects", + "Font", + "FontColor", + "FontFamily", + "FontForm", + "FontName", + "FontOpacity", + "FontPostScriptName", + "FontProperties", + "FontReencoding", + "FontSize", + "FontSlant", + "FontSubstitutions", + "FontTracking", + "FontVariations", + "FontWeight", + "For", + "ForAll", + "ForAllType", + "ForceVersionInstall", + "Format", + "FormatRules", + "FormatType", + "FormatTypeAutoConvert", + "FormatValues", + "FormBox", + "FormBoxOptions", + "FormControl", + "FormFunction", + "FormLayoutFunction", + "FormObject", + "FormPage", + "FormProtectionMethod", + "FormTheme", + "FormulaData", + "FormulaLookup", + "FortranForm", + "Forward", + "ForwardBackward", + "ForwardCloudCredentials", + "Fourier", + "FourierCoefficient", + "FourierCosCoefficient", + "FourierCosSeries", + "FourierCosTransform", + "FourierDCT", + "FourierDCTFilter", + "FourierDCTMatrix", + "FourierDST", + "FourierDSTMatrix", + "FourierMatrix", + "FourierParameters", + "FourierSequenceTransform", + "FourierSeries", + "FourierSinCoefficient", + "FourierSinSeries", + "FourierSinTransform", + "FourierTransform", + "FourierTrigSeries", + "FoxH", + "FoxHReduce", + "FractionalBrownianMotionProcess", + "FractionalD", + "FractionalGaussianNoiseProcess", + "FractionalPart", + "FractionBox", + "FractionBoxOptions", + "FractionLine", + "Frame", + "FrameBox", + "FrameBoxOptions", + "Framed", + "FrameInset", + "FrameLabel", + "Frameless", + "FrameListVideo", + "FrameMargins", + "FrameRate", + "FrameStyle", + "FrameTicks", + "FrameTicksStyle", + "FRatioDistribution", + "FrechetDistribution", + "FreeQ", + "FrenetSerretSystem", + "FrequencySamplingFilterKernel", + "FresnelC", + "FresnelF", + "FresnelG", + "FresnelS", + "Friday", + "FrobeniusNumber", + "FrobeniusSolve", + "FromAbsoluteTime", + "FromCharacterCode", + "FromCoefficientRules", + "FromContinuedFraction", + "FromDate", + "FromDateString", + "FromDigits", + "FromDMS", + "FromEntity", + "FromJulianDate", + "FromLetterNumber", + "FromPolarCoordinates", + "FromRawPointer", + "FromRomanNumeral", + "FromSphericalCoordinates", + "FromUnixTime", + "Front", + "FrontEndDynamicExpression", + "FrontEndEventActions", + "FrontEndExecute", + "FrontEndObject", + "FrontEndResource", + "FrontEndResourceString", + "FrontEndStackSize", + "FrontEndToken", + "FrontEndTokenExecute", + "FrontEndValueCache", + "FrontEndVersion", + "FrontFaceColor", + "FrontFaceGlowColor", + "FrontFaceOpacity", + "FrontFaceSpecularColor", + "FrontFaceSpecularExponent", + "FrontFaceSurfaceAppearance", + "FrontFaceTexture", + "Full", + "FullAxes", + "FullDefinition", + "FullForm", + "FullGraphics", + "FullInformationOutputRegulator", + "FullOptions", + "FullRegion", + "FullSimplify", + "Function", + "FunctionAnalytic", + "FunctionBijective", + "FunctionCompile", + "FunctionCompileExport", + "FunctionCompileExportByteArray", + "FunctionCompileExportLibrary", + "FunctionCompileExportString", + "FunctionContinuous", + "FunctionConvexity", + "FunctionDeclaration", + "FunctionDiscontinuities", + "FunctionDomain", + "FunctionExpand", + "FunctionInjective", + "FunctionInterpolation", + "FunctionLayer", + "FunctionMeromorphic", + "FunctionMonotonicity", + "FunctionPeriod", + "FunctionPoles", + "FunctionRange", + "FunctionSign", + "FunctionSingularities", + "FunctionSpace", + "FunctionSurjective", + "FussellVeselyImportance", + "GaborFilter", + "GaborMatrix", + "GaborWavelet", + "GainMargins", + "GainPhaseMargins", + "GalaxyData", + "GalleryView", + "Gamma", + "GammaDistribution", + "GammaRegularized", + "GapPenalty", + "GARCHProcess", + "GatedRecurrentLayer", + "Gather", + "GatherBy", + "GaugeFaceElementFunction", + "GaugeFaceStyle", + "GaugeFrameElementFunction", + "GaugeFrameSize", + "GaugeFrameStyle", + "GaugeLabels", + "GaugeMarkers", + "GaugeStyle", + "GaussianFilter", + "GaussianIntegers", + "GaussianMatrix", + "GaussianOrthogonalMatrixDistribution", + "GaussianSymplecticMatrixDistribution", + "GaussianUnitaryMatrixDistribution", + "GaussianWindow", + "GCD", + "GegenbauerC", + "General", + "GeneralizedLinearModelFit", + "GenerateAsymmetricKeyPair", + "GenerateConditions", + "GeneratedAssetFormat", + "GeneratedAssetLocation", + "GeneratedCell", + "GeneratedCellStyles", + "GeneratedDocumentBinding", + "GenerateDerivedKey", + "GenerateDigitalSignature", + "GenerateDocument", + "GeneratedParameters", + "GeneratedQuantityMagnitudes", + "GenerateFileSignature", + "GenerateHTTPResponse", + "GenerateSecuredAuthenticationKey", + "GenerateSymmetricKey", + "GeneratingFunction", + "GeneratorDescription", + "GeneratorHistoryLength", + "GeneratorOutputType", + "Generic", + "GenericCylindricalDecomposition", + "GenomeData", + "GenomeLookup", + "GeoAntipode", + "GeoArea", + "GeoArraySize", + "GeoBackground", + "GeoBoundary", + "GeoBoundingBox", + "GeoBounds", + "GeoBoundsRegion", + "GeoBoundsRegionBoundary", + "GeoBubbleChart", + "GeoCenter", + "GeoCircle", + "GeoContourPlot", + "GeoDensityPlot", + "GeodesicClosing", + "GeodesicDilation", + "GeodesicErosion", + "GeodesicOpening", + "GeodesicPolyhedron", + "GeoDestination", + "GeodesyData", + "GeoDirection", + "GeoDisk", + "GeoDisplacement", + "GeoDistance", + "GeoDistanceList", + "GeoElevationData", + "GeoEntities", + "GeoGraphics", + "GeoGraphPlot", + "GeoGraphValuePlot", + "GeogravityModelData", + "GeoGridDirectionDifference", + "GeoGridLines", + "GeoGridLinesStyle", + "GeoGridPosition", + "GeoGridRange", + "GeoGridRangePadding", + "GeoGridUnitArea", + "GeoGridUnitDistance", + "GeoGridVector", + "GeoGroup", + "GeoHemisphere", + "GeoHemisphereBoundary", + "GeoHistogram", + "GeoIdentify", + "GeoImage", + "GeoLabels", + "GeoLength", + "GeoListPlot", + "GeoLocation", + "GeologicalPeriodData", + "GeomagneticModelData", + "GeoMarker", + "GeometricAssertion", + "GeometricBrownianMotionProcess", + "GeometricDistribution", + "GeometricMean", + "GeometricMeanFilter", + "GeometricOptimization", + "GeometricScene", + "GeometricStep", + "GeometricStylingRules", + "GeometricTest", + "GeometricTransformation", + "GeometricTransformation3DBox", + "GeometricTransformation3DBoxOptions", + "GeometricTransformationBox", + "GeometricTransformationBoxOptions", + "GeoModel", + "GeoNearest", + "GeoOrientationData", + "GeoPath", + "GeoPolygon", + "GeoPosition", + "GeoPositionENU", + "GeoPositionXYZ", + "GeoProjection", + "GeoProjectionData", + "GeoRange", + "GeoRangePadding", + "GeoRegionValuePlot", + "GeoResolution", + "GeoScaleBar", + "GeoServer", + "GeoSmoothHistogram", + "GeoStreamPlot", + "GeoStyling", + "GeoStylingImageFunction", + "GeoVariant", + "GeoVector", + "GeoVectorENU", + "GeoVectorPlot", + "GeoVectorXYZ", + "GeoVisibleRegion", + "GeoVisibleRegionBoundary", + "GeoWithinQ", + "GeoZoomLevel", + "GestureHandler", + "GestureHandlerTag", + "Get", + "GetContext", + "GetEnvironment", + "GetFileName", + "GetLinebreakInformationPacket", + "GibbsPointProcess", + "Glaisher", + "GlobalClusteringCoefficient", + "GlobalPreferences", + "GlobalSession", + "Glow", + "GoldenAngle", + "GoldenRatio", + "GompertzMakehamDistribution", + "GoochShading", + "GoodmanKruskalGamma", + "GoodmanKruskalGammaTest", + "Goto", + "GouraudShading", + "Grad", + "Gradient", + "GradientFilter", + "GradientFittedMesh", + "GradientOrientationFilter", + "GrammarApply", + "GrammarRules", + "GrammarToken", + "Graph", + "Graph3D", + "GraphAssortativity", + "GraphAutomorphismGroup", + "GraphCenter", + "GraphComplement", + "GraphData", + "GraphDensity", + "GraphDiameter", + "GraphDifference", + "GraphDisjointUnion", + "GraphDistance", + "GraphDistanceMatrix", + "GraphEmbedding", + "GraphHighlight", + "GraphHighlightStyle", + "GraphHub", + "Graphics", + "Graphics3D", + "Graphics3DBox", + "Graphics3DBoxOptions", + "GraphicsArray", + "GraphicsBaseline", + "GraphicsBox", + "GraphicsBoxOptions", + "GraphicsColor", + "GraphicsColumn", + "GraphicsComplex", + "GraphicsComplex3DBox", + "GraphicsComplex3DBoxOptions", + "GraphicsComplexBox", + "GraphicsComplexBoxOptions", + "GraphicsContents", + "GraphicsData", + "GraphicsGrid", + "GraphicsGridBox", + "GraphicsGroup", + "GraphicsGroup3DBox", + "GraphicsGroup3DBoxOptions", + "GraphicsGroupBox", + "GraphicsGroupBoxOptions", + "GraphicsGrouping", + "GraphicsHighlightColor", + "GraphicsRow", + "GraphicsSpacing", + "GraphicsStyle", + "GraphIntersection", + "GraphJoin", + "GraphLayerLabels", + "GraphLayers", + "GraphLayerStyle", + "GraphLayout", + "GraphLinkEfficiency", + "GraphPeriphery", + "GraphPlot", + "GraphPlot3D", + "GraphPower", + "GraphProduct", + "GraphPropertyDistribution", + "GraphQ", + "GraphRadius", + "GraphReciprocity", + "GraphRoot", + "GraphStyle", + "GraphSum", + "GraphTree", + "GraphUnion", + "Gray", + "GrayLevel", + "Greater", + "GreaterEqual", + "GreaterEqualLess", + "GreaterEqualThan", + "GreaterFullEqual", + "GreaterGreater", + "GreaterLess", + "GreaterSlantEqual", + "GreaterThan", + "GreaterTilde", + "GreekStyle", + "Green", + "GreenFunction", + "Grid", + "GridBaseline", + "GridBox", + "GridBoxAlignment", + "GridBoxBackground", + "GridBoxDividers", + "GridBoxFrame", + "GridBoxItemSize", + "GridBoxItemStyle", + "GridBoxOptions", + "GridBoxSpacings", + "GridCreationSettings", + "GridDefaultElement", + "GridElementStyleOptions", + "GridFrame", + "GridFrameMargins", + "GridGraph", + "GridLines", + "GridLinesStyle", + "GridVideo", + "GroebnerBasis", + "GroupActionBase", + "GroupBy", + "GroupCentralizer", + "GroupElementFromWord", + "GroupElementPosition", + "GroupElementQ", + "GroupElements", + "GroupElementToWord", + "GroupGenerators", + "Groupings", + "GroupMultiplicationTable", + "GroupOpenerColor", + "GroupOpenerInsideFrame", + "GroupOrbits", + "GroupOrder", + "GroupPageBreakWithin", + "GroupSetwiseStabilizer", + "GroupStabilizer", + "GroupStabilizerChain", + "GroupTogetherGrouping", + "GroupTogetherNestedGrouping", + "GrowCutComponents", + "Gudermannian", + "GuidedFilter", + "GumbelDistribution", + "HaarWavelet", + "HadamardMatrix", + "HalfLine", + "HalfNormalDistribution", + "HalfPlane", + "HalfSpace", + "HalftoneShading", + "HamiltonianGraphQ", + "HammingDistance", + "HammingWindow", + "HandlerFunctions", + "HandlerFunctionsKeys", + "HankelH1", + "HankelH2", + "HankelMatrix", + "HankelTransform", + "HannPoissonWindow", + "HannWindow", + "HaradaNortonGroupHN", + "HararyGraph", + "HardcorePointProcess", + "HarmonicMean", + "HarmonicMeanFilter", + "HarmonicNumber", + "Hash", + "HatchFilling", + "HatchShading", + "Haversine", + "HazardFunction", + "Head", + "HeadCompose", + "HeaderAlignment", + "HeaderBackground", + "HeaderDisplayFunction", + "HeaderLines", + "Headers", + "HeaderSize", + "HeaderStyle", + "Heads", + "HeatFluxValue", + "HeatInsulationValue", + "HeatOutflowValue", + "HeatRadiationValue", + "HeatSymmetryValue", + "HeatTemperatureCondition", + "HeatTransferPDEComponent", + "HeatTransferValue", + "HeavisideLambda", + "HeavisidePi", + "HeavisideTheta", + "HeldGroupHe", + "HeldPart", + "HelmholtzPDEComponent", + "HelpBrowserLookup", + "HelpBrowserNotebook", + "HelpBrowserSettings", + "HelpViewerSettings", + "Here", + "HermiteDecomposition", + "HermiteH", + "Hermitian", + "HermitianMatrixQ", + "HessenbergDecomposition", + "Hessian", + "HeunB", + "HeunBPrime", + "HeunC", + "HeunCPrime", + "HeunD", + "HeunDPrime", + "HeunG", + "HeunGPrime", + "HeunT", + "HeunTPrime", + "HexadecimalCharacter", + "Hexahedron", + "HexahedronBox", + "HexahedronBoxOptions", + "HiddenItems", + "HiddenMarkovProcess", + "HiddenSurface", + "Highlighted", + "HighlightGraph", + "HighlightImage", + "HighlightMesh", + "HighlightString", + "HighpassFilter", + "HigmanSimsGroupHS", + "HilbertCurve", + "HilbertFilter", + "HilbertMatrix", + "Histogram", + "Histogram3D", + "HistogramDistribution", + "HistogramList", + "HistogramPointDensity", + "HistogramTransform", + "HistogramTransformInterpolation", + "HistoricalPeriodData", + "HitMissTransform", + "HITSCentrality", + "HjorthDistribution", + "HodgeDual", + "HoeffdingD", + "HoeffdingDTest", + "Hold", + "HoldAll", + "HoldAllComplete", + "HoldComplete", + "HoldFirst", + "HoldForm", + "HoldPattern", + "HoldRest", + "HolidayCalendar", + "HomeDirectory", + "HomePage", + "Horizontal", + "HorizontalForm", + "HorizontalGauge", + "HorizontalScrollPosition", + "HornerForm", + "HostLookup", + "HotellingTSquareDistribution", + "HoytDistribution", + "HTMLSave", + "HTTPErrorResponse", + "HTTPRedirect", + "HTTPRequest", + "HTTPRequestData", + "HTTPResponse", + "Hue", + "HumanGrowthData", + "HumpDownHump", + "HumpEqual", + "HurwitzLerchPhi", + "HurwitzZeta", + "HyperbolicDistribution", + "HypercubeGraph", + "HyperexponentialDistribution", + "Hyperfactorial", + "Hypergeometric0F1", + "Hypergeometric0F1Regularized", + "Hypergeometric1F1", + "Hypergeometric1F1Regularized", + "Hypergeometric2F1", + "Hypergeometric2F1Regularized", + "HypergeometricDistribution", + "HypergeometricPFQ", + "HypergeometricPFQRegularized", + "HypergeometricU", + "Hyperlink", + "HyperlinkAction", + "HyperlinkCreationSettings", + "Hyperplane", + "Hyphenation", + "HyphenationOptions", + "HypoexponentialDistribution", + "HypothesisTestData", + "I", + "IconData", + "Iconize", + "IconizedObject", + "IconRules", + "Icosahedron", + "Identity", + "IdentityMatrix", + "If", + "IfCompiled", + "IgnoreCase", + "IgnoreDiacritics", + "IgnoreIsotopes", + "IgnorePunctuation", + "IgnoreSpellCheck", + "IgnoreStereochemistry", + "IgnoringInactive", + "Im", + "Image", + "Image3D", + "Image3DProjection", + "Image3DSlices", + "ImageAccumulate", + "ImageAdd", + "ImageAdjust", + "ImageAlign", + "ImageApply", + "ImageApplyIndexed", + "ImageAspectRatio", + "ImageAssemble", + "ImageAugmentationLayer", + "ImageBoundingBoxes", + "ImageCache", + "ImageCacheValid", + "ImageCapture", + "ImageCaptureFunction", + "ImageCases", + "ImageChannels", + "ImageClip", + "ImageCollage", + "ImageColorSpace", + "ImageCompose", + "ImageContainsQ", + "ImageContents", + "ImageConvolve", + "ImageCooccurrence", + "ImageCorners", + "ImageCorrelate", + "ImageCorrespondingPoints", + "ImageCrop", + "ImageData", + "ImageDeconvolve", + "ImageDemosaic", + "ImageDifference", + "ImageDimensions", + "ImageDisplacements", + "ImageDistance", + "ImageEditMode", + "ImageEffect", + "ImageExposureCombine", + "ImageFeatureTrack", + "ImageFileApply", + "ImageFileFilter", + "ImageFileScan", + "ImageFilter", + "ImageFocusCombine", + "ImageForestingComponents", + "ImageFormattingWidth", + "ImageForwardTransformation", + "ImageGraphics", + "ImageHistogram", + "ImageIdentify", + "ImageInstanceQ", + "ImageKeypoints", + "ImageLabels", + "ImageLegends", + "ImageLevels", + "ImageLines", + "ImageMargins", + "ImageMarker", + "ImageMarkers", + "ImageMeasurements", + "ImageMesh", + "ImageMultiply", + "ImageOffset", + "ImagePad", + "ImagePadding", + "ImagePartition", + "ImagePeriodogram", + "ImagePerspectiveTransformation", + "ImagePosition", + "ImagePreviewFunction", + "ImagePyramid", + "ImagePyramidApply", + "ImageQ", + "ImageRangeCache", + "ImageRecolor", + "ImageReflect", + "ImageRegion", + "ImageResize", + "ImageResolution", + "ImageRestyle", + "ImageRotate", + "ImageRotated", + "ImageSaliencyFilter", + "ImageScaled", + "ImageScan", + "ImageSize", + "ImageSizeAction", + "ImageSizeCache", + "ImageSizeMultipliers", + "ImageSizeRaw", + "ImageStitch", + "ImageSubtract", + "ImageTake", + "ImageTransformation", + "ImageTrim", + "ImageType", + "ImageValue", + "ImageValuePositions", + "ImageVectorscopePlot", + "ImageWaveformPlot", + "ImagingDevice", + "ImplicitD", + "ImplicitRegion", + "Implies", + "Import", + "ImportAutoReplacements", + "ImportByteArray", + "ImportedObject", + "ImportOptions", + "ImportString", + "ImprovementImportance", + "In", + "Inactivate", + "Inactive", + "InactiveStyle", + "IncidenceGraph", + "IncidenceList", + "IncidenceMatrix", + "IncludeAromaticBonds", + "IncludeConstantBasis", + "IncludedContexts", + "IncludeDefinitions", + "IncludeDirectories", + "IncludeFileExtension", + "IncludeGeneratorTasks", + "IncludeHydrogens", + "IncludeInflections", + "IncludeMetaInformation", + "IncludePods", + "IncludeQuantities", + "IncludeRelatedTables", + "IncludeSingularSolutions", + "IncludeSingularTerm", + "IncludeWindowTimes", + "Increment", + "IndefiniteMatrixQ", + "Indent", + "IndentingNewlineSpacings", + "IndentMaxFraction", + "IndependenceTest", + "IndependentEdgeSetQ", + "IndependentPhysicalQuantity", + "IndependentUnit", + "IndependentUnitDimension", + "IndependentVertexSetQ", + "Indeterminate", + "IndeterminateThreshold", + "IndexCreationOptions", + "Indexed", + "IndexEdgeTaggedGraph", + "IndexGraph", + "IndexTag", + "Inequality", + "InertEvaluate", + "InertExpression", + "InexactNumberQ", + "InexactNumbers", + "InfiniteFuture", + "InfiniteLine", + "InfiniteLineThrough", + "InfinitePast", + "InfinitePlane", + "Infinity", + "Infix", + "InflationAdjust", + "InflationMethod", + "Information", + "InformationData", + "InformationDataGrid", + "Inherited", + "InheritScope", + "InhomogeneousPoissonPointProcess", + "InhomogeneousPoissonProcess", + "InitialEvaluationHistory", + "Initialization", + "InitializationCell", + "InitializationCellEvaluation", + "InitializationCellWarning", + "InitializationObject", + "InitializationObjects", + "InitializationValue", + "Initialize", + "InitialSeeding", + "InlineCounterAssignments", + "InlineCounterIncrements", + "InlineRules", + "Inner", + "InnerPolygon", + "InnerPolyhedron", + "Inpaint", + "Input", + "InputAliases", + "InputAssumptions", + "InputAutoReplacements", + "InputField", + "InputFieldBox", + "InputFieldBoxOptions", + "InputForm", + "InputGrouping", + "InputNamePacket", + "InputNotebook", + "InputPacket", + "InputPorts", + "InputSettings", + "InputStream", + "InputString", + "InputStringPacket", + "InputToBoxFormPacket", + "Insert", + "InsertionFunction", + "InsertionPointObject", + "InsertLinebreaks", + "InsertResults", + "Inset", + "Inset3DBox", + "Inset3DBoxOptions", + "InsetBox", + "InsetBoxOptions", + "Insphere", + "Install", + "InstallService", + "InstanceNormalizationLayer", + "InString", + "Integer", + "IntegerDigits", + "IntegerExponent", + "IntegerLength", + "IntegerName", + "IntegerPart", + "IntegerPartitions", + "IntegerQ", + "IntegerReverse", + "Integers", + "IntegerString", + "Integral", + "Integrate", + "IntegrateChangeVariables", + "Interactive", + "InteractiveTradingChart", + "InterfaceSwitched", + "Interlaced", + "Interleaving", + "InternallyBalancedDecomposition", + "InterpolatingFunction", + "InterpolatingPolynomial", + "Interpolation", + "InterpolationOrder", + "InterpolationPoints", + "InterpolationPrecision", + "Interpretation", + "InterpretationBox", + "InterpretationBoxOptions", + "InterpretationFunction", + "Interpreter", + "InterpretTemplate", + "InterquartileRange", + "Interrupt", + "InterruptSettings", + "IntersectedEntityClass", + "IntersectingQ", + "Intersection", + "Interval", + "IntervalIntersection", + "IntervalMarkers", + "IntervalMarkersStyle", + "IntervalMemberQ", + "IntervalSlider", + "IntervalUnion", + "Into", + "Inverse", + "InverseBetaRegularized", + "InverseBilateralLaplaceTransform", + "InverseBilateralZTransform", + "InverseCDF", + "InverseChiSquareDistribution", + "InverseContinuousWaveletTransform", + "InverseDistanceTransform", + "InverseEllipticNomeQ", + "InverseErf", + "InverseErfc", + "InverseFourier", + "InverseFourierCosTransform", + "InverseFourierSequenceTransform", + "InverseFourierSinTransform", + "InverseFourierTransform", + "InverseFunction", + "InverseFunctions", + "InverseGammaDistribution", + "InverseGammaRegularized", + "InverseGaussianDistribution", + "InverseGudermannian", + "InverseHankelTransform", + "InverseHaversine", + "InverseImagePyramid", + "InverseJacobiCD", + "InverseJacobiCN", + "InverseJacobiCS", + "InverseJacobiDC", + "InverseJacobiDN", + "InverseJacobiDS", + "InverseJacobiNC", + "InverseJacobiND", + "InverseJacobiNS", + "InverseJacobiSC", + "InverseJacobiSD", + "InverseJacobiSN", + "InverseLaplaceTransform", + "InverseMellinTransform", + "InversePermutation", + "InverseRadon", + "InverseRadonTransform", + "InverseSeries", + "InverseShortTimeFourier", + "InverseSpectrogram", + "InverseSurvivalFunction", + "InverseTransformedRegion", + "InverseWaveletTransform", + "InverseWeierstrassP", + "InverseWishartMatrixDistribution", + "InverseZTransform", + "Invisible", + "InvisibleApplication", + "InvisibleTimes", + "IPAddress", + "IrreduciblePolynomialQ", + "IslandData", + "IsolatingInterval", + "IsomorphicGraphQ", + "IsomorphicSubgraphQ", + "IsotopeData", + "Italic", + "Item", + "ItemAspectRatio", + "ItemBox", + "ItemBoxOptions", + "ItemDisplayFunction", + "ItemSize", + "ItemStyle", + "ItoProcess", + "JaccardDissimilarity", + "JacobiAmplitude", + "Jacobian", + "JacobiCD", + "JacobiCN", + "JacobiCS", + "JacobiDC", + "JacobiDN", + "JacobiDS", + "JacobiEpsilon", + "JacobiNC", + "JacobiND", + "JacobiNS", + "JacobiP", + "JacobiSC", + "JacobiSD", + "JacobiSN", + "JacobiSymbol", + "JacobiZeta", + "JacobiZN", + "JankoGroupJ1", + "JankoGroupJ2", + "JankoGroupJ3", + "JankoGroupJ4", + "JarqueBeraALMTest", + "JohnsonDistribution", + "Join", + "JoinAcross", + "Joined", + "JoinedCurve", + "JoinedCurveBox", + "JoinedCurveBoxOptions", + "JoinForm", + "JordanDecomposition", + "JordanModelDecomposition", + "JulianDate", + "JuliaSetBoettcher", + "JuliaSetIterationCount", + "JuliaSetPlot", + "JuliaSetPoints", + "K", + "KagiChart", + "KaiserBesselWindow", + "KaiserWindow", + "KalmanEstimator", + "KalmanFilter", + "KarhunenLoeveDecomposition", + "KaryTree", + "KatzCentrality", + "KCoreComponents", + "KDistribution", + "KEdgeConnectedComponents", + "KEdgeConnectedGraphQ", + "KeepExistingVersion", + "KelvinBei", + "KelvinBer", + "KelvinKei", + "KelvinKer", + "KendallTau", + "KendallTauTest", + "KernelConfiguration", + "KernelExecute", + "KernelFunction", + "KernelMixtureDistribution", + "KernelObject", + "Kernels", + "Ket", + "Key", + "KeyCollisionFunction", + "KeyComplement", + "KeyDrop", + "KeyDropFrom", + "KeyExistsQ", + "KeyFreeQ", + "KeyIntersection", + "KeyMap", + "KeyMemberQ", + "KeypointStrength", + "Keys", + "KeySelect", + "KeySort", + "KeySortBy", + "KeyTake", + "KeyUnion", + "KeyValueMap", + "KeyValuePattern", + "Khinchin", + "KillProcess", + "KirchhoffGraph", + "KirchhoffMatrix", + "KleinInvariantJ", + "KnapsackSolve", + "KnightTourGraph", + "KnotData", + "KnownUnitQ", + "KochCurve", + "KolmogorovSmirnovTest", + "KroneckerDelta", + "KroneckerModelDecomposition", + "KroneckerProduct", + "KroneckerSymbol", + "KuiperTest", + "KumaraswamyDistribution", + "Kurtosis", + "KuwaharaFilter", + "KVertexConnectedComponents", + "KVertexConnectedGraphQ", + "LABColor", + "Label", + "Labeled", + "LabeledSlider", + "LabelingFunction", + "LabelingSize", + "LabelStyle", + "LabelVisibility", + "LaguerreL", + "LakeData", + "LambdaComponents", + "LambertW", + "LameC", + "LameCPrime", + "LameEigenvalueA", + "LameEigenvalueB", + "LameS", + "LameSPrime", + "LaminaData", + "LanczosWindow", + "LandauDistribution", + "Language", + "LanguageCategory", + "LanguageData", + "LanguageIdentify", + "LanguageOptions", + "LaplaceDistribution", + "LaplaceTransform", + "Laplacian", + "LaplacianFilter", + "LaplacianGaussianFilter", + "LaplacianPDETerm", + "Large", + "Larger", + "Last", + "Latitude", + "LatitudeLongitude", + "LatticeData", + "LatticeReduce", + "Launch", + "LaunchKernels", + "LayeredGraphPlot", + "LayeredGraphPlot3D", + "LayerSizeFunction", + "LayoutInformation", + "LCHColor", + "LCM", + "LeaderSize", + "LeafCount", + "LeapVariant", + "LeapYearQ", + "LearnDistribution", + "LearnedDistribution", + "LearningRate", + "LearningRateMultipliers", + "LeastSquares", + "LeastSquaresFilterKernel", + "Left", + "LeftArrow", + "LeftArrowBar", + "LeftArrowRightArrow", + "LeftDownTeeVector", + "LeftDownVector", + "LeftDownVectorBar", + "LeftRightArrow", + "LeftRightVector", + "LeftTee", + "LeftTeeArrow", + "LeftTeeVector", + "LeftTriangle", + "LeftTriangleBar", + "LeftTriangleEqual", + "LeftUpDownVector", + "LeftUpTeeVector", + "LeftUpVector", + "LeftUpVectorBar", + "LeftVector", + "LeftVectorBar", + "LegendAppearance", + "Legended", + "LegendFunction", + "LegendLabel", + "LegendLayout", + "LegendMargins", + "LegendMarkers", + "LegendMarkerSize", + "LegendreP", + "LegendreQ", + "LegendreType", + "Length", + "LengthWhile", + "LerchPhi", + "Less", + "LessEqual", + "LessEqualGreater", + "LessEqualThan", + "LessFullEqual", + "LessGreater", + "LessLess", + "LessSlantEqual", + "LessThan", + "LessTilde", + "LetterCharacter", + "LetterCounts", + "LetterNumber", + "LetterQ", + "Level", + "LeveneTest", + "LeviCivitaTensor", + "LevyDistribution", + "Lexicographic", + "LexicographicOrder", + "LexicographicSort", + "LibraryDataType", + "LibraryFunction", + "LibraryFunctionDeclaration", + "LibraryFunctionError", + "LibraryFunctionInformation", + "LibraryFunctionLoad", + "LibraryFunctionUnload", + "LibraryLoad", + "LibraryUnload", + "LicenseEntitlementObject", + "LicenseEntitlements", + "LicenseID", + "LicensingSettings", + "LiftingFilterData", + "LiftingWaveletTransform", + "LightBlue", + "LightBrown", + "LightCyan", + "Lighter", + "LightGray", + "LightGreen", + "Lighting", + "LightingAngle", + "LightMagenta", + "LightOrange", + "LightPink", + "LightPurple", + "LightRed", + "LightSources", + "LightYellow", + "Likelihood", + "Limit", + "LimitsPositioning", + "LimitsPositioningTokens", + "LindleyDistribution", + "Line", + "Line3DBox", + "Line3DBoxOptions", + "LinearFilter", + "LinearFractionalOptimization", + "LinearFractionalTransform", + "LinearGradientFilling", + "LinearGradientImage", + "LinearizingTransformationData", + "LinearLayer", + "LinearModelFit", + "LinearOffsetFunction", + "LinearOptimization", + "LinearProgramming", + "LinearRecurrence", + "LinearSolve", + "LinearSolveFunction", + "LineBox", + "LineBoxOptions", + "LineBreak", + "LinebreakAdjustments", + "LineBreakChart", + "LinebreakSemicolonWeighting", + "LineBreakWithin", + "LineColor", + "LineGraph", + "LineIndent", + "LineIndentMaxFraction", + "LineIntegralConvolutionPlot", + "LineIntegralConvolutionScale", + "LineLegend", + "LineOpacity", + "LineSpacing", + "LineWrapParts", + "LinkActivate", + "LinkClose", + "LinkConnect", + "LinkConnectedQ", + "LinkCreate", + "LinkError", + "LinkFlush", + "LinkFunction", + "LinkHost", + "LinkInterrupt", + "LinkLaunch", + "LinkMode", + "LinkObject", + "LinkOpen", + "LinkOptions", + "LinkPatterns", + "LinkProtocol", + "LinkRankCentrality", + "LinkRead", + "LinkReadHeld", + "LinkReadyQ", + "Links", + "LinkService", + "LinkWrite", + "LinkWriteHeld", + "LiouvilleLambda", + "List", + "Listable", + "ListAnimate", + "ListContourPlot", + "ListContourPlot3D", + "ListConvolve", + "ListCorrelate", + "ListCurvePathPlot", + "ListDeconvolve", + "ListDensityPlot", + "ListDensityPlot3D", + "Listen", + "ListFormat", + "ListFourierSequenceTransform", + "ListInterpolation", + "ListLineIntegralConvolutionPlot", + "ListLinePlot", + "ListLinePlot3D", + "ListLogLinearPlot", + "ListLogLogPlot", + "ListLogPlot", + "ListPicker", + "ListPickerBox", + "ListPickerBoxBackground", + "ListPickerBoxOptions", + "ListPlay", + "ListPlot", + "ListPlot3D", + "ListPointPlot3D", + "ListPolarPlot", + "ListQ", + "ListSliceContourPlot3D", + "ListSliceDensityPlot3D", + "ListSliceVectorPlot3D", + "ListStepPlot", + "ListStreamDensityPlot", + "ListStreamPlot", + "ListStreamPlot3D", + "ListSurfacePlot3D", + "ListVectorDensityPlot", + "ListVectorDisplacementPlot", + "ListVectorDisplacementPlot3D", + "ListVectorPlot", + "ListVectorPlot3D", + "ListZTransform", + "Literal", + "LiteralSearch", + "LiteralType", + "LoadCompiledComponent", + "LocalAdaptiveBinarize", + "LocalCache", + "LocalClusteringCoefficient", + "LocalEvaluate", + "LocalizeDefinitions", + "LocalizeVariables", + "LocalObject", + "LocalObjects", + "LocalResponseNormalizationLayer", + "LocalSubmit", + "LocalSymbol", + "LocalTime", + "LocalTimeZone", + "LocationEquivalenceTest", + "LocationTest", + "Locator", + "LocatorAutoCreate", + "LocatorBox", + "LocatorBoxOptions", + "LocatorCentering", + "LocatorPane", + "LocatorPaneBox", + "LocatorPaneBoxOptions", + "LocatorRegion", + "Locked", + "Log", + "Log10", + "Log2", + "LogBarnesG", + "LogGamma", + "LogGammaDistribution", + "LogicalExpand", + "LogIntegral", + "LogisticDistribution", + "LogisticSigmoid", + "LogitModelFit", + "LogLikelihood", + "LogLinearPlot", + "LogLogisticDistribution", + "LogLogPlot", + "LogMultinormalDistribution", + "LogNormalDistribution", + "LogPlot", + "LogRankTest", + "LogSeriesDistribution", + "LongEqual", + "Longest", + "LongestCommonSequence", + "LongestCommonSequencePositions", + "LongestCommonSubsequence", + "LongestCommonSubsequencePositions", + "LongestMatch", + "LongestOrderedSequence", + "LongForm", + "Longitude", + "LongLeftArrow", + "LongLeftRightArrow", + "LongRightArrow", + "LongShortTermMemoryLayer", + "Lookup", + "Loopback", + "LoopFreeGraphQ", + "Looping", + "LossFunction", + "LowerCaseQ", + "LowerLeftArrow", + "LowerRightArrow", + "LowerTriangularize", + "LowerTriangularMatrix", + "LowerTriangularMatrixQ", + "LowpassFilter", + "LQEstimatorGains", + "LQGRegulator", + "LQOutputRegulatorGains", + "LQRegulatorGains", + "LUBackSubstitution", + "LucasL", + "LuccioSamiComponents", + "LUDecomposition", + "LunarEclipse", + "LUVColor", + "LyapunovSolve", + "LyonsGroupLy", + "MachineID", + "MachineName", + "MachineNumberQ", + "MachinePrecision", + "MacintoshSystemPageSetup", + "Magenta", + "Magnification", + "Magnify", + "MailAddressValidation", + "MailExecute", + "MailFolder", + "MailItem", + "MailReceiverFunction", + "MailResponseFunction", + "MailSearch", + "MailServerConnect", + "MailServerConnection", + "MailSettings", + "MainSolve", + "MaintainDynamicCaches", + "Majority", + "MakeBoxes", + "MakeExpression", + "MakeRules", + "ManagedLibraryExpressionID", + "ManagedLibraryExpressionQ", + "MandelbrotSetBoettcher", + "MandelbrotSetDistance", + "MandelbrotSetIterationCount", + "MandelbrotSetMemberQ", + "MandelbrotSetPlot", + "MangoldtLambda", + "ManhattanDistance", + "Manipulate", + "Manipulator", + "MannedSpaceMissionData", + "MannWhitneyTest", + "MantissaExponent", + "Manual", + "Map", + "MapAll", + "MapApply", + "MapAt", + "MapIndexed", + "MAProcess", + "MapThread", + "MarchenkoPasturDistribution", + "MarcumQ", + "MardiaCombinedTest", + "MardiaKurtosisTest", + "MardiaSkewnessTest", + "MarginalDistribution", + "MarkovProcessProperties", + "Masking", + "MassConcentrationCondition", + "MassFluxValue", + "MassImpermeableBoundaryValue", + "MassOutflowValue", + "MassSymmetryValue", + "MassTransferValue", + "MassTransportPDEComponent", + "MatchingDissimilarity", + "MatchLocalNameQ", + "MatchLocalNames", + "MatchQ", + "Material", + "MaterialShading", + "MaternPointProcess", + "MathematicalFunctionData", + "MathematicaNotation", + "MathieuC", + "MathieuCharacteristicA", + "MathieuCharacteristicB", + "MathieuCharacteristicExponent", + "MathieuCPrime", + "MathieuGroupM11", + "MathieuGroupM12", + "MathieuGroupM22", + "MathieuGroupM23", + "MathieuGroupM24", + "MathieuS", + "MathieuSPrime", + "MathMLForm", + "MathMLText", + "Matrices", + "MatrixExp", + "MatrixForm", + "MatrixFunction", + "MatrixLog", + "MatrixNormalDistribution", + "MatrixPlot", + "MatrixPower", + "MatrixPropertyDistribution", + "MatrixQ", + "MatrixRank", + "MatrixTDistribution", + "Max", + "MaxBend", + "MaxCellMeasure", + "MaxColorDistance", + "MaxDate", + "MaxDetect", + "MaxDisplayedChildren", + "MaxDuration", + "MaxExtraBandwidths", + "MaxExtraConditions", + "MaxFeatureDisplacement", + "MaxFeatures", + "MaxFilter", + "MaximalBy", + "Maximize", + "MaxItems", + "MaxIterations", + "MaxLimit", + "MaxMemoryUsed", + "MaxMixtureKernels", + "MaxOverlapFraction", + "MaxPlotPoints", + "MaxPoints", + "MaxRecursion", + "MaxStableDistribution", + "MaxStepFraction", + "MaxSteps", + "MaxStepSize", + "MaxTrainingRounds", + "MaxValue", + "MaxwellDistribution", + "MaxWordGap", + "McLaughlinGroupMcL", + "Mean", + "MeanAbsoluteLossLayer", + "MeanAround", + "MeanClusteringCoefficient", + "MeanDegreeConnectivity", + "MeanDeviation", + "MeanFilter", + "MeanGraphDistance", + "MeanNeighborDegree", + "MeanPointDensity", + "MeanShift", + "MeanShiftFilter", + "MeanSquaredLossLayer", + "Median", + "MedianDeviation", + "MedianFilter", + "MedicalTestData", + "Medium", + "MeijerG", + "MeijerGReduce", + "MeixnerDistribution", + "MellinConvolve", + "MellinTransform", + "MemberQ", + "MemoryAvailable", + "MemoryConstrained", + "MemoryConstraint", + "MemoryInUse", + "MengerMesh", + "Menu", + "MenuAppearance", + "MenuCommandKey", + "MenuEvaluator", + "MenuItem", + "MenuList", + "MenuPacket", + "MenuSortingValue", + "MenuStyle", + "MenuView", + "Merge", + "MergeDifferences", + "MergingFunction", + "MersennePrimeExponent", + "MersennePrimeExponentQ", + "Mesh", + "MeshCellCentroid", + "MeshCellCount", + "MeshCellHighlight", + "MeshCellIndex", + "MeshCellLabel", + "MeshCellMarker", + "MeshCellMeasure", + "MeshCellQuality", + "MeshCells", + "MeshCellShapeFunction", + "MeshCellStyle", + "MeshConnectivityGraph", + "MeshCoordinates", + "MeshFunctions", + "MeshPrimitives", + "MeshQualityGoal", + "MeshRange", + "MeshRefinementFunction", + "MeshRegion", + "MeshRegionQ", + "MeshShading", + "MeshStyle", + "Message", + "MessageDialog", + "MessageList", + "MessageName", + "MessageObject", + "MessageOptions", + "MessagePacket", + "Messages", + "MessagesNotebook", + "MetaCharacters", + "MetaInformation", + "MeteorShowerData", + "Method", + "MethodOptions", + "MexicanHatWavelet", + "MeyerWavelet", + "Midpoint", + "MIMETypeToFormatList", + "Min", + "MinColorDistance", + "MinDate", + "MinDetect", + "MineralData", + "MinFilter", + "MinimalBy", + "MinimalPolynomial", + "MinimalStateSpaceModel", + "Minimize", + "MinimumTimeIncrement", + "MinIntervalSize", + "MinkowskiQuestionMark", + "MinLimit", + "MinMax", + "MinorPlanetData", + "Minors", + "MinPointSeparation", + "MinRecursion", + "MinSize", + "MinStableDistribution", + "Minus", + "MinusPlus", + "MinValue", + "Missing", + "MissingBehavior", + "MissingDataMethod", + "MissingDataRules", + "MissingQ", + "MissingString", + "MissingStyle", + "MissingValuePattern", + "MissingValueSynthesis", + "MittagLefflerE", + "MixedFractionParts", + "MixedGraphQ", + "MixedMagnitude", + "MixedRadix", + "MixedRadixQuantity", + "MixedUnit", + "MixtureDistribution", + "Mod", + "Modal", + "Mode", + "ModelPredictiveController", + "Modular", + "ModularInverse", + "ModularLambda", + "Module", + "Modulus", + "MoebiusMu", + "Molecule", + "MoleculeAlign", + "MoleculeContainsQ", + "MoleculeDraw", + "MoleculeEquivalentQ", + "MoleculeFreeQ", + "MoleculeGraph", + "MoleculeMatchQ", + "MoleculeMaximumCommonSubstructure", + "MoleculeModify", + "MoleculeName", + "MoleculePattern", + "MoleculePlot", + "MoleculePlot3D", + "MoleculeProperty", + "MoleculeQ", + "MoleculeRecognize", + "MoleculeSubstructureCount", + "MoleculeValue", + "Moment", + "MomentConvert", + "MomentEvaluate", + "MomentGeneratingFunction", + "MomentOfInertia", + "Monday", + "Monitor", + "MonomialList", + "MonomialOrder", + "MonsterGroupM", + "MoonPhase", + "MoonPosition", + "MorletWavelet", + "MorphologicalBinarize", + "MorphologicalBranchPoints", + "MorphologicalComponents", + "MorphologicalEulerNumber", + "MorphologicalGraph", + "MorphologicalPerimeter", + "MorphologicalTransform", + "MortalityData", + "Most", + "MountainData", + "MouseAnnotation", + "MouseAppearance", + "MouseAppearanceTag", + "MouseButtons", + "Mouseover", + "MousePointerNote", + "MousePosition", + "MovieData", + "MovingAverage", + "MovingMap", + "MovingMedian", + "MoyalDistribution", + "MultiaxisArrangement", + "Multicolumn", + "MultiedgeStyle", + "MultigraphQ", + "MultilaunchWarning", + "MultiLetterItalics", + "MultiLetterStyle", + "MultilineFunction", + "Multinomial", + "MultinomialDistribution", + "MultinormalDistribution", + "MultiplicativeOrder", + "Multiplicity", + "MultiplySides", + "MultiscriptBoxOptions", + "Multiselection", + "MultivariateHypergeometricDistribution", + "MultivariatePoissonDistribution", + "MultivariateTDistribution", + "N", + "NakagamiDistribution", + "NameQ", + "Names", + "NamespaceBox", + "NamespaceBoxOptions", + "Nand", + "NArgMax", + "NArgMin", + "NBernoulliB", + "NBodySimulation", + "NBodySimulationData", + "NCache", + "NCaputoD", + "NDEigensystem", + "NDEigenvalues", + "NDSolve", + "NDSolveValue", + "Nearest", + "NearestFunction", + "NearestMeshCells", + "NearestNeighborG", + "NearestNeighborGraph", + "NearestTo", + "NebulaData", + "NeedlemanWunschSimilarity", + "Needs", + "Negative", + "NegativeBinomialDistribution", + "NegativeDefiniteMatrixQ", + "NegativeIntegers", + "NegativelyOrientedPoints", + "NegativeMultinomialDistribution", + "NegativeRationals", + "NegativeReals", + "NegativeSemidefiniteMatrixQ", + "NeighborhoodData", + "NeighborhoodGraph", + "Nest", + "NestedGreaterGreater", + "NestedLessLess", + "NestedScriptRules", + "NestGraph", + "NestList", + "NestTree", + "NestWhile", + "NestWhileList", + "NetAppend", + "NetArray", + "NetArrayLayer", + "NetBidirectionalOperator", + "NetChain", + "NetDecoder", + "NetDelete", + "NetDrop", + "NetEncoder", + "NetEvaluationMode", + "NetExternalObject", + "NetExtract", + "NetFlatten", + "NetFoldOperator", + "NetGANOperator", + "NetGraph", + "NetInformation", + "NetInitialize", + "NetInsert", + "NetInsertSharedArrays", + "NetJoin", + "NetMapOperator", + "NetMapThreadOperator", + "NetMeasurements", + "NetModel", + "NetNestOperator", + "NetPairEmbeddingOperator", + "NetPort", + "NetPortGradient", + "NetPrepend", + "NetRename", + "NetReplace", + "NetReplacePart", + "NetSharedArray", + "NetStateObject", + "NetTake", + "NetTrain", + "NetTrainResultsObject", + "NetUnfold", + "NetworkPacketCapture", + "NetworkPacketRecording", + "NetworkPacketRecordingDuring", + "NetworkPacketTrace", + "NeumannValue", + "NevilleThetaC", + "NevilleThetaD", + "NevilleThetaN", + "NevilleThetaS", + "NewPrimitiveStyle", + "NExpectation", + "Next", + "NextCell", + "NextDate", + "NextPrime", + "NextScheduledTaskTime", + "NeymanScottPointProcess", + "NFractionalD", + "NHoldAll", + "NHoldFirst", + "NHoldRest", + "NicholsGridLines", + "NicholsPlot", + "NightHemisphere", + "NIntegrate", + "NMaximize", + "NMaxValue", + "NMinimize", + "NMinValue", + "NominalScale", + "NominalVariables", + "NonAssociative", + "NoncentralBetaDistribution", + "NoncentralChiSquareDistribution", + "NoncentralFRatioDistribution", + "NoncentralStudentTDistribution", + "NonCommutativeMultiply", + "NonConstants", + "NondimensionalizationTransform", + "None", + "NoneTrue", + "NonlinearModelFit", + "NonlinearStateSpaceModel", + "NonlocalMeansFilter", + "NonNegative", + "NonNegativeIntegers", + "NonNegativeRationals", + "NonNegativeReals", + "NonPositive", + "NonPositiveIntegers", + "NonPositiveRationals", + "NonPositiveReals", + "Nor", + "NorlundB", + "Norm", + "Normal", + "NormalDistribution", + "NormalGrouping", + "NormalizationLayer", + "Normalize", + "Normalized", + "NormalizedSquaredEuclideanDistance", + "NormalMatrixQ", + "NormalsFunction", + "NormFunction", + "Not", + "NotCongruent", + "NotCupCap", + "NotDoubleVerticalBar", + "Notebook", + "NotebookApply", + "NotebookAutoSave", + "NotebookBrowseDirectory", + "NotebookClose", + "NotebookConvertSettings", + "NotebookCreate", + "NotebookDefault", + "NotebookDelete", + "NotebookDirectory", + "NotebookDynamicExpression", + "NotebookEvaluate", + "NotebookEventActions", + "NotebookFileName", + "NotebookFind", + "NotebookGet", + "NotebookImport", + "NotebookInformation", + "NotebookInterfaceObject", + "NotebookLocate", + "NotebookObject", + "NotebookOpen", + "NotebookPath", + "NotebookPrint", + "NotebookPut", + "NotebookRead", + "Notebooks", + "NotebookSave", + "NotebookSelection", + "NotebooksMenu", + "NotebookTemplate", + "NotebookWrite", + "NotElement", + "NotEqualTilde", + "NotExists", + "NotGreater", + "NotGreaterEqual", + "NotGreaterFullEqual", + "NotGreaterGreater", + "NotGreaterLess", + "NotGreaterSlantEqual", + "NotGreaterTilde", + "Nothing", + "NotHumpDownHump", + "NotHumpEqual", + "NotificationFunction", + "NotLeftTriangle", + "NotLeftTriangleBar", + "NotLeftTriangleEqual", + "NotLess", + "NotLessEqual", + "NotLessFullEqual", + "NotLessGreater", + "NotLessLess", + "NotLessSlantEqual", + "NotLessTilde", + "NotNestedGreaterGreater", + "NotNestedLessLess", + "NotPrecedes", + "NotPrecedesEqual", + "NotPrecedesSlantEqual", + "NotPrecedesTilde", + "NotReverseElement", + "NotRightTriangle", + "NotRightTriangleBar", + "NotRightTriangleEqual", + "NotSquareSubset", + "NotSquareSubsetEqual", + "NotSquareSuperset", + "NotSquareSupersetEqual", + "NotSubset", + "NotSubsetEqual", + "NotSucceeds", + "NotSucceedsEqual", + "NotSucceedsSlantEqual", + "NotSucceedsTilde", + "NotSuperset", + "NotSupersetEqual", + "NotTilde", + "NotTildeEqual", + "NotTildeFullEqual", + "NotTildeTilde", + "NotVerticalBar", + "Now", + "NoWhitespace", + "NProbability", + "NProduct", + "NProductFactors", + "NRoots", + "NSolve", + "NSolveValues", + "NSum", + "NSumTerms", + "NuclearExplosionData", + "NuclearReactorData", + "Null", + "NullRecords", + "NullSpace", + "NullWords", + "Number", + "NumberCompose", + "NumberDecompose", + "NumberDigit", + "NumberExpand", + "NumberFieldClassNumber", + "NumberFieldDiscriminant", + "NumberFieldFundamentalUnits", + "NumberFieldIntegralBasis", + "NumberFieldNormRepresentatives", + "NumberFieldRegulator", + "NumberFieldRootsOfUnity", + "NumberFieldSignature", + "NumberForm", + "NumberFormat", + "NumberLinePlot", + "NumberMarks", + "NumberMultiplier", + "NumberPadding", + "NumberPoint", + "NumberQ", + "NumberSeparator", + "NumberSigns", + "NumberString", + "Numerator", + "NumeratorDenominator", + "NumericalOrder", + "NumericalSort", + "NumericArray", + "NumericArrayQ", + "NumericArrayType", + "NumericFunction", + "NumericQ", + "NuttallWindow", + "NValues", + "NyquistGridLines", + "NyquistPlot", + "O", + "ObjectExistsQ", + "ObservabilityGramian", + "ObservabilityMatrix", + "ObservableDecomposition", + "ObservableModelQ", + "OceanData", + "Octahedron", + "OddQ", + "Off", + "Offset", + "OLEData", + "On", + "ONanGroupON", + "Once", + "OneIdentity", + "Opacity", + "OpacityFunction", + "OpacityFunctionScaling", + "Open", + "OpenAppend", + "Opener", + "OpenerBox", + "OpenerBoxOptions", + "OpenerView", + "OpenFunctionInspectorPacket", + "Opening", + "OpenRead", + "OpenSpecialOptions", + "OpenTemporary", + "OpenWrite", + "Operate", + "OperatingSystem", + "OperatorApplied", + "OptimumFlowData", + "Optional", + "OptionalElement", + "OptionInspectorSettings", + "OptionQ", + "Options", + "OptionsPacket", + "OptionsPattern", + "OptionValue", + "OptionValueBox", + "OptionValueBoxOptions", + "Or", + "Orange", + "Order", + "OrderDistribution", + "OrderedQ", + "Ordering", + "OrderingBy", + "OrderingLayer", + "Orderless", + "OrderlessPatternSequence", + "OrdinalScale", + "OrnsteinUhlenbeckProcess", + "Orthogonalize", + "OrthogonalMatrixQ", + "Out", + "Outer", + "OuterPolygon", + "OuterPolyhedron", + "OutputAutoOverwrite", + "OutputControllabilityMatrix", + "OutputControllableModelQ", + "OutputForm", + "OutputFormData", + "OutputGrouping", + "OutputMathEditExpression", + "OutputNamePacket", + "OutputPorts", + "OutputResponse", + "OutputSizeLimit", + "OutputStream", + "Over", + "OverBar", + "OverDot", + "Overflow", + "OverHat", + "Overlaps", + "Overlay", + "OverlayBox", + "OverlayBoxOptions", + "OverlayVideo", + "Overscript", + "OverscriptBox", + "OverscriptBoxOptions", + "OverTilde", + "OverVector", + "OverwriteTarget", + "OwenT", + "OwnValues", + "Package", + "PackingMethod", + "PackPaclet", + "PacletDataRebuild", + "PacletDirectoryAdd", + "PacletDirectoryLoad", + "PacletDirectoryRemove", + "PacletDirectoryUnload", + "PacletDisable", + "PacletEnable", + "PacletFind", + "PacletFindRemote", + "PacletInformation", + "PacletInstall", + "PacletInstallSubmit", + "PacletNewerQ", + "PacletObject", + "PacletObjectQ", + "PacletSite", + "PacletSiteObject", + "PacletSiteRegister", + "PacletSites", + "PacletSiteUnregister", + "PacletSiteUpdate", + "PacletSymbol", + "PacletUninstall", + "PacletUpdate", + "PaddedForm", + "Padding", + "PaddingLayer", + "PaddingSize", + "PadeApproximant", + "PadLeft", + "PadRight", + "PageBreakAbove", + "PageBreakBelow", + "PageBreakWithin", + "PageFooterLines", + "PageFooters", + "PageHeaderLines", + "PageHeaders", + "PageHeight", + "PageRankCentrality", + "PageTheme", + "PageWidth", + "Pagination", + "PairCorrelationG", + "PairedBarChart", + "PairedHistogram", + "PairedSmoothHistogram", + "PairedTTest", + "PairedZTest", + "PaletteNotebook", + "PalettePath", + "PalettesMenuSettings", + "PalindromeQ", + "Pane", + "PaneBox", + "PaneBoxOptions", + "Panel", + "PanelBox", + "PanelBoxOptions", + "Paneled", + "PaneSelector", + "PaneSelectorBox", + "PaneSelectorBoxOptions", + "PaperWidth", + "ParabolicCylinderD", + "ParagraphIndent", + "ParagraphSpacing", + "ParallelArray", + "ParallelAxisPlot", + "ParallelCombine", + "ParallelDo", + "Parallelepiped", + "ParallelEvaluate", + "Parallelization", + "Parallelize", + "ParallelKernels", + "ParallelMap", + "ParallelNeeds", + "Parallelogram", + "ParallelProduct", + "ParallelSubmit", + "ParallelSum", + "ParallelTable", + "ParallelTry", + "Parameter", + "ParameterEstimator", + "ParameterMixtureDistribution", + "ParameterVariables", + "ParametricConvexOptimization", + "ParametricFunction", + "ParametricNDSolve", + "ParametricNDSolveValue", + "ParametricPlot", + "ParametricPlot3D", + "ParametricRampLayer", + "ParametricRegion", + "ParentBox", + "ParentCell", + "ParentConnect", + "ParentDirectory", + "ParentEdgeLabel", + "ParentEdgeLabelFunction", + "ParentEdgeLabelStyle", + "ParentEdgeShapeFunction", + "ParentEdgeStyle", + "ParentEdgeStyleFunction", + "ParentForm", + "Parenthesize", + "ParentList", + "ParentNotebook", + "ParetoDistribution", + "ParetoPickandsDistribution", + "ParkData", + "Part", + "PartBehavior", + "PartialCorrelationFunction", + "PartialD", + "ParticleAcceleratorData", + "ParticleData", + "Partition", + "PartitionGranularity", + "PartitionsP", + "PartitionsQ", + "PartLayer", + "PartOfSpeech", + "PartProtection", + "ParzenWindow", + "PascalDistribution", + "PassEventsDown", + "PassEventsUp", + "Paste", + "PasteAutoQuoteCharacters", + "PasteBoxFormInlineCells", + "PasteButton", + "Path", + "PathGraph", + "PathGraphQ", + "Pattern", + "PatternFilling", + "PatternReaction", + "PatternSequence", + "PatternTest", + "PauliMatrix", + "PaulWavelet", + "Pause", + "PausedTime", + "PDF", + "PeakDetect", + "PeanoCurve", + "PearsonChiSquareTest", + "PearsonCorrelationTest", + "PearsonDistribution", + "PenttinenPointProcess", + "PercentForm", + "PerfectNumber", + "PerfectNumberQ", + "PerformanceGoal", + "Perimeter", + "PeriodicBoundaryCondition", + "PeriodicInterpolation", + "Periodogram", + "PeriodogramArray", + "Permanent", + "Permissions", + "PermissionsGroup", + "PermissionsGroupMemberQ", + "PermissionsGroups", + "PermissionsKey", + "PermissionsKeys", + "PermutationCycles", + "PermutationCyclesQ", + "PermutationGroup", + "PermutationLength", + "PermutationList", + "PermutationListQ", + "PermutationMatrix", + "PermutationMax", + "PermutationMin", + "PermutationOrder", + "PermutationPower", + "PermutationProduct", + "PermutationReplace", + "Permutations", + "PermutationSupport", + "Permute", + "PeronaMalikFilter", + "Perpendicular", + "PerpendicularBisector", + "PersistenceLocation", + "PersistenceTime", + "PersistentObject", + "PersistentObjects", + "PersistentSymbol", + "PersistentValue", + "PersonData", + "PERTDistribution", + "PetersenGraph", + "PhaseMargins", + "PhaseRange", + "PhongShading", + "PhysicalSystemData", + "Pi", + "Pick", + "PickedElements", + "PickMode", + "PIDData", + "PIDDerivativeFilter", + "PIDFeedforward", + "PIDTune", + "Piecewise", + "PiecewiseExpand", + "PieChart", + "PieChart3D", + "PillaiTrace", + "PillaiTraceTest", + "PingTime", + "Pink", + "PitchRecognize", + "Pivoting", + "PixelConstrained", + "PixelValue", + "PixelValuePositions", + "Placed", + "Placeholder", + "PlaceholderLayer", + "PlaceholderReplace", + "Plain", + "PlanarAngle", + "PlanarFaceList", + "PlanarGraph", + "PlanarGraphQ", + "PlanckRadiationLaw", + "PlaneCurveData", + "PlanetaryMoonData", + "PlanetData", + "PlantData", + "Play", + "PlaybackSettings", + "PlayRange", + "Plot", + "Plot3D", + "Plot3Matrix", + "PlotDivision", + "PlotJoined", + "PlotLabel", + "PlotLabels", + "PlotLayout", + "PlotLegends", + "PlotMarkers", + "PlotPoints", + "PlotRange", + "PlotRangeClipping", + "PlotRangeClipPlanesStyle", + "PlotRangePadding", + "PlotRegion", + "PlotStyle", + "PlotTheme", + "Pluralize", + "Plus", + "PlusMinus", + "Pochhammer", + "PodStates", + "PodWidth", + "Point", + "Point3DBox", + "Point3DBoxOptions", + "PointBox", + "PointBoxOptions", + "PointCountDistribution", + "PointDensity", + "PointDensityFunction", + "PointFigureChart", + "PointLegend", + "PointLight", + "PointProcessEstimator", + "PointProcessFitTest", + "PointProcessParameterAssumptions", + "PointProcessParameterQ", + "PointSize", + "PointStatisticFunction", + "PointValuePlot", + "PoissonConsulDistribution", + "PoissonDistribution", + "PoissonPDEComponent", + "PoissonPointProcess", + "PoissonProcess", + "PoissonWindow", + "PolarAxes", + "PolarAxesOrigin", + "PolarGridLines", + "PolarPlot", + "PolarTicks", + "PoleZeroMarkers", + "PolyaAeppliDistribution", + "PolyGamma", + "Polygon", + "Polygon3DBox", + "Polygon3DBoxOptions", + "PolygonalNumber", + "PolygonAngle", + "PolygonBox", + "PolygonBoxOptions", + "PolygonCoordinates", + "PolygonDecomposition", + "PolygonHoleScale", + "PolygonIntersections", + "PolygonScale", + "Polyhedron", + "PolyhedronAngle", + "PolyhedronBox", + "PolyhedronBoxOptions", + "PolyhedronCoordinates", + "PolyhedronData", + "PolyhedronDecomposition", + "PolyhedronGenus", + "PolyLog", + "PolynomialExpressionQ", + "PolynomialExtendedGCD", + "PolynomialForm", + "PolynomialGCD", + "PolynomialLCM", + "PolynomialMod", + "PolynomialQ", + "PolynomialQuotient", + "PolynomialQuotientRemainder", + "PolynomialReduce", + "PolynomialRemainder", + "Polynomials", + "PolynomialSumOfSquaresList", + "PoolingLayer", + "PopupMenu", + "PopupMenuBox", + "PopupMenuBoxOptions", + "PopupView", + "PopupWindow", + "Position", + "PositionIndex", + "PositionLargest", + "PositionSmallest", + "Positive", + "PositiveDefiniteMatrixQ", + "PositiveIntegers", + "PositivelyOrientedPoints", + "PositiveRationals", + "PositiveReals", + "PositiveSemidefiniteMatrixQ", + "PossibleZeroQ", + "Postfix", + "PostScript", + "Power", + "PowerDistribution", + "PowerExpand", + "PowerMod", + "PowerModList", + "PowerRange", + "PowerSpectralDensity", + "PowersRepresentations", + "PowerSymmetricPolynomial", + "Precedence", + "PrecedenceForm", + "Precedes", + "PrecedesEqual", + "PrecedesSlantEqual", + "PrecedesTilde", + "Precision", + "PrecisionGoal", + "PreDecrement", + "Predict", + "PredictionRoot", + "PredictorFunction", + "PredictorInformation", + "PredictorMeasurements", + "PredictorMeasurementsObject", + "PreemptProtect", + "PreferencesPath", + "PreferencesSettings", + "Prefix", + "PreIncrement", + "Prepend", + "PrependLayer", + "PrependTo", + "PreprocessingRules", + "PreserveColor", + "PreserveImageOptions", + "Previous", + "PreviousCell", + "PreviousDate", + "PriceGraphDistribution", + "PrimaryPlaceholder", + "Prime", + "PrimeNu", + "PrimeOmega", + "PrimePi", + "PrimePowerQ", + "PrimeQ", + "Primes", + "PrimeZetaP", + "PrimitivePolynomialQ", + "PrimitiveRoot", + "PrimitiveRootList", + "PrincipalComponents", + "PrincipalValue", + "Print", + "PrintableASCIIQ", + "PrintAction", + "PrintForm", + "PrintingCopies", + "PrintingOptions", + "PrintingPageRange", + "PrintingStartingPageNumber", + "PrintingStyleEnvironment", + "Printout3D", + "Printout3DPreviewer", + "PrintPrecision", + "PrintTemporary", + "Prism", + "PrismBox", + "PrismBoxOptions", + "PrivateCellOptions", + "PrivateEvaluationOptions", + "PrivateFontOptions", + "PrivateFrontEndOptions", + "PrivateKey", + "PrivateNotebookOptions", + "PrivatePaths", + "Probability", + "ProbabilityDistribution", + "ProbabilityPlot", + "ProbabilityPr", + "ProbabilityScalePlot", + "ProbitModelFit", + "ProcessConnection", + "ProcessDirectory", + "ProcessEnvironment", + "Processes", + "ProcessEstimator", + "ProcessInformation", + "ProcessObject", + "ProcessParameterAssumptions", + "ProcessParameterQ", + "ProcessStateDomain", + "ProcessStatus", + "ProcessTimeDomain", + "Product", + "ProductDistribution", + "ProductLog", + "ProgressIndicator", + "ProgressIndicatorBox", + "ProgressIndicatorBoxOptions", + "ProgressReporting", + "Projection", + "Prolog", + "PromptForm", + "ProofObject", + "PropagateAborts", + "Properties", + "Property", + "PropertyList", + "PropertyValue", + "Proportion", + "Proportional", + "Protect", + "Protected", + "ProteinData", + "Pruning", + "PseudoInverse", + "PsychrometricPropertyData", + "PublicKey", + "PublisherID", + "PulsarData", + "PunctuationCharacter", + "Purple", + "Put", + "PutAppend", + "Pyramid", + "PyramidBox", + "PyramidBoxOptions", + "QBinomial", + "QFactorial", + "QGamma", + "QHypergeometricPFQ", + "QnDispersion", + "QPochhammer", + "QPolyGamma", + "QRDecomposition", + "QuadraticIrrationalQ", + "QuadraticOptimization", + "Quantile", + "QuantilePlot", + "Quantity", + "QuantityArray", + "QuantityDistribution", + "QuantityForm", + "QuantityMagnitude", + "QuantityQ", + "QuantityUnit", + "QuantityVariable", + "QuantityVariableCanonicalUnit", + "QuantityVariableDimensions", + "QuantityVariableIdentifier", + "QuantityVariablePhysicalQuantity", + "Quartics", + "QuartileDeviation", + "Quartiles", + "QuartileSkewness", + "Query", + "QuestionGenerator", + "QuestionInterface", + "QuestionObject", + "QuestionSelector", + "QueueingNetworkProcess", + "QueueingProcess", + "QueueProperties", + "Quiet", + "QuietEcho", + "Quit", + "Quotient", + "QuotientRemainder", + "RadialAxisPlot", + "RadialGradientFilling", + "RadialGradientImage", + "RadialityCentrality", + "RadicalBox", + "RadicalBoxOptions", + "RadioButton", + "RadioButtonBar", + "RadioButtonBox", + "RadioButtonBoxOptions", + "Radon", + "RadonTransform", + "RamanujanTau", + "RamanujanTauL", + "RamanujanTauTheta", + "RamanujanTauZ", + "Ramp", + "Random", + "RandomArrayLayer", + "RandomChoice", + "RandomColor", + "RandomComplex", + "RandomDate", + "RandomEntity", + "RandomFunction", + "RandomGeneratorState", + "RandomGeoPosition", + "RandomGraph", + "RandomImage", + "RandomInstance", + "RandomInteger", + "RandomPermutation", + "RandomPoint", + "RandomPointConfiguration", + "RandomPolygon", + "RandomPolyhedron", + "RandomPrime", + "RandomReal", + "RandomSample", + "RandomSeed", + "RandomSeeding", + "RandomTime", + "RandomTree", + "RandomVariate", + "RandomWalkProcess", + "RandomWord", + "Range", + "RangeFilter", + "RangeSpecification", + "RankedMax", + "RankedMin", + "RarerProbability", + "Raster", + "Raster3D", + "Raster3DBox", + "Raster3DBoxOptions", + "RasterArray", + "RasterBox", + "RasterBoxOptions", + "Rasterize", + "RasterSize", + "Rational", + "RationalExpressionQ", + "RationalFunctions", + "Rationalize", + "Rationals", + "Ratios", + "RawArray", + "RawBoxes", + "RawData", + "RawMedium", + "RayleighDistribution", + "Re", + "ReactionBalance", + "ReactionBalancedQ", + "ReactionPDETerm", + "Read", + "ReadByteArray", + "ReadLine", + "ReadList", + "ReadProtected", + "ReadString", + "Real", + "RealAbs", + "RealBlockDiagonalForm", + "RealDigits", + "RealExponent", + "Reals", + "RealSign", + "Reap", + "RebuildPacletData", + "RecalibrationFunction", + "RecognitionPrior", + "RecognitionThreshold", + "ReconstructionMesh", + "Record", + "RecordLists", + "RecordSeparators", + "Rectangle", + "RectangleBox", + "RectangleBoxOptions", + "RectangleChart", + "RectangleChart3D", + "RectangularRepeatingElement", + "RecurrenceFilter", + "RecurrenceTable", + "RecurringDigitsForm", + "Red", + "Reduce", + "RefBox", + "ReferenceLineStyle", + "ReferenceMarkers", + "ReferenceMarkerStyle", + "Refine", + "ReflectionMatrix", + "ReflectionTransform", + "Refresh", + "RefreshRate", + "Region", + "RegionBinarize", + "RegionBoundary", + "RegionBoundaryStyle", + "RegionBounds", + "RegionCentroid", + "RegionCongruent", + "RegionConvert", + "RegionDifference", + "RegionDilation", + "RegionDimension", + "RegionDisjoint", + "RegionDistance", + "RegionDistanceFunction", + "RegionEmbeddingDimension", + "RegionEqual", + "RegionErosion", + "RegionFillingStyle", + "RegionFit", + "RegionFunction", + "RegionImage", + "RegionIntersection", + "RegionMeasure", + "RegionMember", + "RegionMemberFunction", + "RegionMoment", + "RegionNearest", + "RegionNearestFunction", + "RegionPlot", + "RegionPlot3D", + "RegionProduct", + "RegionQ", + "RegionResize", + "RegionSimilar", + "RegionSize", + "RegionSymmetricDifference", + "RegionUnion", + "RegionWithin", + "RegisterExternalEvaluator", + "RegularExpression", + "Regularization", + "RegularlySampledQ", + "RegularPolygon", + "ReIm", + "ReImLabels", + "ReImPlot", + "ReImStyle", + "Reinstall", + "RelationalDatabase", + "RelationGraph", + "Release", + "ReleaseHold", + "ReliabilityDistribution", + "ReliefImage", + "ReliefPlot", + "RemoteAuthorizationCaching", + "RemoteBatchJobAbort", + "RemoteBatchJobObject", + "RemoteBatchJobs", + "RemoteBatchMapSubmit", + "RemoteBatchSubmissionEnvironment", + "RemoteBatchSubmit", + "RemoteConnect", + "RemoteConnectionObject", + "RemoteEvaluate", + "RemoteFile", + "RemoteInputFiles", + "RemoteKernelObject", + "RemoteProviderSettings", + "RemoteRun", + "RemoteRunProcess", + "RemovalConditions", + "Remove", + "RemoveAlphaChannel", + "RemoveAsynchronousTask", + "RemoveAudioStream", + "RemoveBackground", + "RemoveChannelListener", + "RemoveChannelSubscribers", + "Removed", + "RemoveDiacritics", + "RemoveInputStreamMethod", + "RemoveOutputStreamMethod", + "RemoveProperty", + "RemoveScheduledTask", + "RemoveUsers", + "RemoveVideoStream", + "RenameDirectory", + "RenameFile", + "RenderAll", + "RenderingOptions", + "RenewalProcess", + "RenkoChart", + "RepairMesh", + "Repeated", + "RepeatedNull", + "RepeatedString", + "RepeatedTiming", + "RepeatingElement", + "Replace", + "ReplaceAll", + "ReplaceAt", + "ReplaceHeldPart", + "ReplaceImageValue", + "ReplaceList", + "ReplacePart", + "ReplacePixelValue", + "ReplaceRepeated", + "ReplicateLayer", + "RequiredPhysicalQuantities", + "Resampling", + "ResamplingAlgorithmData", + "ResamplingMethod", + "Rescale", + "RescalingTransform", + "ResetDirectory", + "ResetScheduledTask", + "ReshapeLayer", + "Residue", + "ResidueSum", + "ResizeLayer", + "Resolve", + "ResolveContextAliases", + "ResourceAcquire", + "ResourceData", + "ResourceFunction", + "ResourceObject", + "ResourceRegister", + "ResourceRemove", + "ResourceSearch", + "ResourceSubmissionObject", + "ResourceSubmit", + "ResourceSystemBase", + "ResourceSystemPath", + "ResourceUpdate", + "ResourceVersion", + "ResponseForm", + "Rest", + "RestartInterval", + "Restricted", + "Resultant", + "ResumePacket", + "Return", + "ReturnCreatesNewCell", + "ReturnEntersInput", + "ReturnExpressionPacket", + "ReturnInputFormPacket", + "ReturnPacket", + "ReturnReceiptFunction", + "ReturnTextPacket", + "Reverse", + "ReverseApplied", + "ReverseBiorthogonalSplineWavelet", + "ReverseElement", + "ReverseEquilibrium", + "ReverseGraph", + "ReverseSort", + "ReverseSortBy", + "ReverseUpEquilibrium", + "RevolutionAxis", + "RevolutionPlot3D", + "RGBColor", + "RiccatiSolve", + "RiceDistribution", + "RidgeFilter", + "RiemannR", + "RiemannSiegelTheta", + "RiemannSiegelZ", + "RiemannXi", + "Riffle", + "Right", + "RightArrow", + "RightArrowBar", + "RightArrowLeftArrow", + "RightComposition", + "RightCosetRepresentative", + "RightDownTeeVector", + "RightDownVector", + "RightDownVectorBar", + "RightTee", + "RightTeeArrow", + "RightTeeVector", + "RightTriangle", + "RightTriangleBar", + "RightTriangleEqual", + "RightUpDownVector", + "RightUpTeeVector", + "RightUpVector", + "RightUpVectorBar", + "RightVector", + "RightVectorBar", + "RipleyK", + "RipleyRassonRegion", + "RiskAchievementImportance", + "RiskReductionImportance", + "RobustConvexOptimization", + "RogersTanimotoDissimilarity", + "RollPitchYawAngles", + "RollPitchYawMatrix", + "RomanNumeral", + "Root", + "RootApproximant", + "RootIntervals", + "RootLocusPlot", + "RootMeanSquare", + "RootOfUnityQ", + "RootReduce", + "Roots", + "RootSum", + "RootTree", + "Rotate", + "RotateLabel", + "RotateLeft", + "RotateRight", + "RotationAction", + "RotationBox", + "RotationBoxOptions", + "RotationMatrix", + "RotationTransform", + "Round", + "RoundImplies", + "RoundingRadius", + "Row", + "RowAlignments", + "RowBackgrounds", + "RowBox", + "RowHeights", + "RowLines", + "RowMinHeight", + "RowReduce", + "RowsEqual", + "RowSpacings", + "RSolve", + "RSolveValue", + "RudinShapiro", + "RudvalisGroupRu", + "Rule", + "RuleCondition", + "RuleDelayed", + "RuleForm", + "RulePlot", + "RulerUnits", + "RulesTree", + "Run", + "RunProcess", + "RunScheduledTask", + "RunThrough", + "RuntimeAttributes", + "RuntimeOptions", + "RussellRaoDissimilarity", + "SameAs", + "SameQ", + "SameTest", + "SameTestProperties", + "SampledEntityClass", + "SampleDepth", + "SampledSoundFunction", + "SampledSoundList", + "SampleRate", + "SamplingPeriod", + "SARIMAProcess", + "SARMAProcess", + "SASTriangle", + "SatelliteData", + "SatisfiabilityCount", + "SatisfiabilityInstances", + "SatisfiableQ", + "Saturday", + "Save", + "Saveable", + "SaveAutoDelete", + "SaveConnection", + "SaveDefinitions", + "SavitzkyGolayMatrix", + "SawtoothWave", + "Scale", + "Scaled", + "ScaleDivisions", + "ScaledMousePosition", + "ScaleOrigin", + "ScalePadding", + "ScaleRanges", + "ScaleRangeStyle", + "ScalingFunctions", + "ScalingMatrix", + "ScalingTransform", + "Scan", + "ScheduledTask", + "ScheduledTaskActiveQ", + "ScheduledTaskInformation", + "ScheduledTaskInformationData", + "ScheduledTaskObject", + "ScheduledTasks", + "SchurDecomposition", + "ScientificForm", + "ScientificNotationThreshold", + "ScorerGi", + "ScorerGiPrime", + "ScorerHi", + "ScorerHiPrime", + "ScreenRectangle", + "ScreenStyleEnvironment", + "ScriptBaselineShifts", + "ScriptForm", + "ScriptLevel", + "ScriptMinSize", + "ScriptRules", + "ScriptSizeMultipliers", + "Scrollbars", + "ScrollingOptions", + "ScrollPosition", + "SearchAdjustment", + "SearchIndexObject", + "SearchIndices", + "SearchQueryString", + "SearchResultObject", + "Sec", + "Sech", + "SechDistribution", + "SecondOrderConeOptimization", + "SectionGrouping", + "SectorChart", + "SectorChart3D", + "SectorOrigin", + "SectorSpacing", + "SecuredAuthenticationKey", + "SecuredAuthenticationKeys", + "SecurityCertificate", + "SeedRandom", + "Select", + "Selectable", + "SelectComponents", + "SelectedCells", + "SelectedNotebook", + "SelectFirst", + "Selection", + "SelectionAnimate", + "SelectionCell", + "SelectionCellCreateCell", + "SelectionCellDefaultStyle", + "SelectionCellParentStyle", + "SelectionCreateCell", + "SelectionDebuggerTag", + "SelectionEvaluate", + "SelectionEvaluateCreateCell", + "SelectionMove", + "SelectionPlaceholder", + "SelectWithContents", + "SelfLoops", + "SelfLoopStyle", + "SemanticImport", + "SemanticImportString", + "SemanticInterpretation", + "SemialgebraicComponentInstances", + "SemidefiniteOptimization", + "SendMail", + "SendMessage", + "Sequence", + "SequenceAlignment", + "SequenceAttentionLayer", + "SequenceCases", + "SequenceCount", + "SequenceFold", + "SequenceFoldList", + "SequenceForm", + "SequenceHold", + "SequenceIndicesLayer", + "SequenceLastLayer", + "SequenceMostLayer", + "SequencePosition", + "SequencePredict", + "SequencePredictorFunction", + "SequenceReplace", + "SequenceRestLayer", + "SequenceReverseLayer", + "SequenceSplit", + "Series", + "SeriesCoefficient", + "SeriesData", + "SeriesTermGoal", + "ServiceConnect", + "ServiceDisconnect", + "ServiceExecute", + "ServiceObject", + "ServiceRequest", + "ServiceResponse", + "ServiceSubmit", + "SessionSubmit", + "SessionTime", + "Set", + "SetAccuracy", + "SetAlphaChannel", + "SetAttributes", + "Setbacks", + "SetCloudDirectory", + "SetCookies", + "SetDelayed", + "SetDirectory", + "SetEnvironment", + "SetFileDate", + "SetFileFormatProperties", + "SetOptions", + "SetOptionsPacket", + "SetPermissions", + "SetPrecision", + "SetProperty", + "SetSecuredAuthenticationKey", + "SetSelectedNotebook", + "SetSharedFunction", + "SetSharedVariable", + "SetStreamPosition", + "SetSystemModel", + "SetSystemOptions", + "Setter", + "SetterBar", + "SetterBox", + "SetterBoxOptions", + "Setting", + "SetUsers", + "Shading", + "Shallow", + "ShannonWavelet", + "ShapiroWilkTest", + "Share", + "SharingList", + "Sharpen", + "ShearingMatrix", + "ShearingTransform", + "ShellRegion", + "ShenCastanMatrix", + "ShiftedGompertzDistribution", + "ShiftRegisterSequence", + "Short", + "ShortDownArrow", + "Shortest", + "ShortestMatch", + "ShortestPathFunction", + "ShortLeftArrow", + "ShortRightArrow", + "ShortTimeFourier", + "ShortTimeFourierData", + "ShortUpArrow", + "Show", + "ShowAutoConvert", + "ShowAutoSpellCheck", + "ShowAutoStyles", + "ShowCellBracket", + "ShowCellLabel", + "ShowCellTags", + "ShowClosedCellArea", + "ShowCodeAssist", + "ShowContents", + "ShowControls", + "ShowCursorTracker", + "ShowGroupOpenCloseIcon", + "ShowGroupOpener", + "ShowInvisibleCharacters", + "ShowPageBreaks", + "ShowPredictiveInterface", + "ShowSelection", + "ShowShortBoxForm", + "ShowSpecialCharacters", + "ShowStringCharacters", + "ShowSyntaxStyles", + "ShrinkingDelay", + "ShrinkWrapBoundingBox", + "SiderealTime", + "SiegelTheta", + "SiegelTukeyTest", + "SierpinskiCurve", + "SierpinskiMesh", + "Sign", + "Signature", + "SignedRankTest", + "SignedRegionDistance", + "SignificanceLevel", + "SignPadding", + "SignTest", + "SimilarityRules", + "SimpleGraph", + "SimpleGraphQ", + "SimplePolygonQ", + "SimplePolyhedronQ", + "Simplex", + "Simplify", + "Sin", + "Sinc", + "SinghMaddalaDistribution", + "SingleEvaluation", + "SingleLetterItalics", + "SingleLetterStyle", + "SingularValueDecomposition", + "SingularValueList", + "SingularValuePlot", + "SingularValues", + "Sinh", + "SinhIntegral", + "SinIntegral", + "SixJSymbol", + "Skeleton", + "SkeletonTransform", + "SkellamDistribution", + "Skewness", + "SkewNormalDistribution", + "SkinStyle", + "Skip", + "SliceContourPlot3D", + "SliceDensityPlot3D", + "SliceDistribution", + "SliceVectorPlot3D", + "Slider", + "Slider2D", + "Slider2DBox", + "Slider2DBoxOptions", + "SliderBox", + "SliderBoxOptions", + "SlideShowVideo", + "SlideView", + "Slot", + "SlotSequence", + "Small", + "SmallCircle", + "Smaller", + "SmithDecomposition", + "SmithDelayCompensator", + "SmithWatermanSimilarity", + "SmoothDensityHistogram", + "SmoothHistogram", + "SmoothHistogram3D", + "SmoothKernelDistribution", + "SmoothPointDensity", + "SnDispersion", + "Snippet", + "SnippetsVideo", + "SnubPolyhedron", + "SocialMediaData", + "Socket", + "SocketConnect", + "SocketListen", + "SocketListener", + "SocketObject", + "SocketOpen", + "SocketReadMessage", + "SocketReadyQ", + "Sockets", + "SocketWaitAll", + "SocketWaitNext", + "SoftmaxLayer", + "SokalSneathDissimilarity", + "SolarEclipse", + "SolarSystemFeatureData", + "SolarTime", + "SolidAngle", + "SolidBoundaryLoadValue", + "SolidData", + "SolidDisplacementCondition", + "SolidFixedCondition", + "SolidMechanicsPDEComponent", + "SolidMechanicsStrain", + "SolidMechanicsStress", + "SolidRegionQ", + "Solve", + "SolveAlways", + "SolveDelayed", + "SolveValues", + "Sort", + "SortBy", + "SortedBy", + "SortedEntityClass", + "Sound", + "SoundAndGraphics", + "SoundNote", + "SoundVolume", + "SourceLink", + "SourcePDETerm", + "Sow", + "Space", + "SpaceCurveData", + "SpaceForm", + "Spacer", + "Spacings", + "Span", + "SpanAdjustments", + "SpanCharacterRounding", + "SpanFromAbove", + "SpanFromBoth", + "SpanFromLeft", + "SpanLineThickness", + "SpanMaxSize", + "SpanMinSize", + "SpanningCharacters", + "SpanSymmetric", + "SparseArray", + "SparseArrayQ", + "SpatialBinnedPointData", + "SpatialBoundaryCorrection", + "SpatialEstimate", + "SpatialEstimatorFunction", + "SpatialGraphDistribution", + "SpatialJ", + "SpatialMedian", + "SpatialNoiseLevel", + "SpatialObservationRegionQ", + "SpatialPointData", + "SpatialPointSelect", + "SpatialRandomnessTest", + "SpatialTransformationLayer", + "SpatialTrendFunction", + "Speak", + "SpeakerMatchQ", + "SpearmanRankTest", + "SpearmanRho", + "SpeciesData", + "SpecificityGoal", + "SpectralLineData", + "Spectrogram", + "SpectrogramArray", + "Specularity", + "SpeechCases", + "SpeechInterpreter", + "SpeechRecognize", + "SpeechSynthesize", + "SpellingCorrection", + "SpellingCorrectionList", + "SpellingDictionaries", + "SpellingDictionariesPath", + "SpellingOptions", + "Sphere", + "SphereBox", + "SphereBoxOptions", + "SpherePoints", + "SphericalBesselJ", + "SphericalBesselY", + "SphericalHankelH1", + "SphericalHankelH2", + "SphericalHarmonicY", + "SphericalPlot3D", + "SphericalRegion", + "SphericalShell", + "SpheroidalEigenvalue", + "SpheroidalJoiningFactor", + "SpheroidalPS", + "SpheroidalPSPrime", + "SpheroidalQS", + "SpheroidalQSPrime", + "SpheroidalRadialFactor", + "SpheroidalS1", + "SpheroidalS1Prime", + "SpheroidalS2", + "SpheroidalS2Prime", + "Splice", + "SplicedDistribution", + "SplineClosed", + "SplineDegree", + "SplineKnots", + "SplineWeights", + "Split", + "SplitBy", + "SpokenString", + "SpotLight", + "Sqrt", + "SqrtBox", + "SqrtBoxOptions", + "Square", + "SquaredEuclideanDistance", + "SquareFreeQ", + "SquareIntersection", + "SquareMatrixQ", + "SquareRepeatingElement", + "SquaresR", + "SquareSubset", + "SquareSubsetEqual", + "SquareSuperset", + "SquareSupersetEqual", + "SquareUnion", + "SquareWave", + "SSSTriangle", + "StabilityMargins", + "StabilityMarginsStyle", + "StableDistribution", + "Stack", + "StackBegin", + "StackComplete", + "StackedDateListPlot", + "StackedListPlot", + "StackInhibit", + "StadiumShape", + "StandardAtmosphereData", + "StandardDeviation", + "StandardDeviationFilter", + "StandardForm", + "Standardize", + "Standardized", + "StandardOceanData", + "StandbyDistribution", + "Star", + "StarClusterData", + "StarData", + "StarGraph", + "StartAsynchronousTask", + "StartExternalSession", + "StartingStepSize", + "StartOfLine", + "StartOfString", + "StartProcess", + "StartScheduledTask", + "StartupSound", + "StartWebSession", + "StateDimensions", + "StateFeedbackGains", + "StateOutputEstimator", + "StateResponse", + "StateSpaceModel", + "StateSpaceRealization", + "StateSpaceTransform", + "StateTransformationLinearize", + "StationaryDistribution", + "StationaryWaveletPacketTransform", + "StationaryWaveletTransform", + "StatusArea", + "StatusCentrality", + "StepMonitor", + "StereochemistryElements", + "StieltjesGamma", + "StippleShading", + "StirlingS1", + "StirlingS2", + "StopAsynchronousTask", + "StoppingPowerData", + "StopScheduledTask", + "StrataVariables", + "StratonovichProcess", + "StraussHardcorePointProcess", + "StraussPointProcess", + "StreamColorFunction", + "StreamColorFunctionScaling", + "StreamDensityPlot", + "StreamMarkers", + "StreamPlot", + "StreamPlot3D", + "StreamPoints", + "StreamPosition", + "Streams", + "StreamScale", + "StreamStyle", + "StrictInequalities", + "String", + "StringBreak", + "StringByteCount", + "StringCases", + "StringContainsQ", + "StringCount", + "StringDelete", + "StringDrop", + "StringEndsQ", + "StringExpression", + "StringExtract", + "StringForm", + "StringFormat", + "StringFormatQ", + "StringFreeQ", + "StringInsert", + "StringJoin", + "StringLength", + "StringMatchQ", + "StringPadLeft", + "StringPadRight", + "StringPart", + "StringPartition", + "StringPosition", + "StringQ", + "StringRepeat", + "StringReplace", + "StringReplaceList", + "StringReplacePart", + "StringReverse", + "StringRiffle", + "StringRotateLeft", + "StringRotateRight", + "StringSkeleton", + "StringSplit", + "StringStartsQ", + "StringTake", + "StringTakeDrop", + "StringTemplate", + "StringToByteArray", + "StringToStream", + "StringTrim", + "StripBoxes", + "StripOnInput", + "StripStyleOnPaste", + "StripWrapperBoxes", + "StrokeForm", + "Struckthrough", + "StructuralImportance", + "StructuredArray", + "StructuredArrayHeadQ", + "StructuredSelection", + "StruveH", + "StruveL", + "Stub", + "StudentTDistribution", + "Style", + "StyleBox", + "StyleBoxAutoDelete", + "StyleData", + "StyleDefinitions", + "StyleForm", + "StyleHints", + "StyleKeyMapping", + "StyleMenuListing", + "StyleNameDialogSettings", + "StyleNames", + "StylePrint", + "StyleSheetPath", + "Subdivide", + "Subfactorial", + "Subgraph", + "SubMinus", + "SubPlus", + "SubresultantPolynomialRemainders", + "SubresultantPolynomials", + "Subresultants", + "Subscript", + "SubscriptBox", + "SubscriptBoxOptions", + "Subscripted", + "Subsequences", + "Subset", + "SubsetCases", + "SubsetCount", + "SubsetEqual", + "SubsetMap", + "SubsetPosition", + "SubsetQ", + "SubsetReplace", + "Subsets", + "SubStar", + "SubstitutionSystem", + "Subsuperscript", + "SubsuperscriptBox", + "SubsuperscriptBoxOptions", + "SubtitleEncoding", + "SubtitleTrackSelection", + "Subtract", + "SubtractFrom", + "SubtractSides", + "SubValues", + "Succeeds", + "SucceedsEqual", + "SucceedsSlantEqual", + "SucceedsTilde", + "Success", + "SuchThat", + "Sum", + "SumConvergence", + "SummationLayer", + "Sunday", + "SunPosition", + "Sunrise", + "Sunset", + "SuperDagger", + "SuperMinus", + "SupernovaData", + "SuperPlus", + "Superscript", + "SuperscriptBox", + "SuperscriptBoxOptions", + "Superset", + "SupersetEqual", + "SuperStar", + "Surd", + "SurdForm", + "SurfaceAppearance", + "SurfaceArea", + "SurfaceColor", + "SurfaceData", + "SurfaceGraphics", + "SurvivalDistribution", + "SurvivalFunction", + "SurvivalModel", + "SurvivalModelFit", + "SuspendPacket", + "SuzukiDistribution", + "SuzukiGroupSuz", + "SwatchLegend", + "Switch", + "Symbol", + "SymbolName", + "SymletWavelet", + "Symmetric", + "SymmetricDifference", + "SymmetricGroup", + "SymmetricKey", + "SymmetricMatrixQ", + "SymmetricPolynomial", + "SymmetricReduction", + "Symmetrize", + "SymmetrizedArray", + "SymmetrizedArrayRules", + "SymmetrizedDependentComponents", + "SymmetrizedIndependentComponents", + "SymmetrizedReplacePart", + "SynchronousInitialization", + "SynchronousUpdating", + "Synonyms", + "Syntax", + "SyntaxForm", + "SyntaxInformation", + "SyntaxLength", + "SyntaxPacket", + "SyntaxQ", + "SynthesizeMissingValues", + "SystemCredential", + "SystemCredentialData", + "SystemCredentialKey", + "SystemCredentialKeys", + "SystemCredentialStoreObject", + "SystemDialogInput", + "SystemException", + "SystemGet", + "SystemHelpPath", + "SystemInformation", + "SystemInformationData", + "SystemInstall", + "SystemModel", + "SystemModeler", + "SystemModelExamples", + "SystemModelLinearize", + "SystemModelMeasurements", + "SystemModelParametricSimulate", + "SystemModelPlot", + "SystemModelProgressReporting", + "SystemModelReliability", + "SystemModels", + "SystemModelSimulate", + "SystemModelSimulateSensitivity", + "SystemModelSimulationData", + "SystemOpen", + "SystemOptions", + "SystemProcessData", + "SystemProcesses", + "SystemsConnectionsModel", + "SystemsModelControllerData", + "SystemsModelDelay", + "SystemsModelDelayApproximate", + "SystemsModelDelete", + "SystemsModelDimensions", + "SystemsModelExtract", + "SystemsModelFeedbackConnect", + "SystemsModelLabels", + "SystemsModelLinearity", + "SystemsModelMerge", + "SystemsModelOrder", + "SystemsModelParallelConnect", + "SystemsModelSeriesConnect", + "SystemsModelStateFeedbackConnect", + "SystemsModelVectorRelativeOrders", + "SystemStub", + "SystemTest", + "Tab", + "TabFilling", + "Table", + "TableAlignments", + "TableDepth", + "TableDirections", + "TableForm", + "TableHeadings", + "TableSpacing", + "TableView", + "TableViewBox", + "TableViewBoxAlignment", + "TableViewBoxBackground", + "TableViewBoxHeaders", + "TableViewBoxItemSize", + "TableViewBoxItemStyle", + "TableViewBoxOptions", + "TabSpacings", + "TabView", + "TabViewBox", + "TabViewBoxOptions", + "TagBox", + "TagBoxNote", + "TagBoxOptions", + "TaggingRules", + "TagSet", + "TagSetDelayed", + "TagStyle", + "TagUnset", + "Take", + "TakeDrop", + "TakeLargest", + "TakeLargestBy", + "TakeList", + "TakeSmallest", + "TakeSmallestBy", + "TakeWhile", + "Tally", + "Tan", + "Tanh", + "TargetDevice", + "TargetFunctions", + "TargetSystem", + "TargetUnits", + "TaskAbort", + "TaskExecute", + "TaskObject", + "TaskRemove", + "TaskResume", + "Tasks", + "TaskSuspend", + "TaskWait", + "TautologyQ", + "TelegraphProcess", + "TemplateApply", + "TemplateArgBox", + "TemplateBox", + "TemplateBoxOptions", + "TemplateEvaluate", + "TemplateExpression", + "TemplateIf", + "TemplateObject", + "TemplateSequence", + "TemplateSlot", + "TemplateSlotSequence", + "TemplateUnevaluated", + "TemplateVerbatim", + "TemplateWith", + "TemporalData", + "TemporalRegularity", + "Temporary", + "TemporaryVariable", + "TensorContract", + "TensorDimensions", + "TensorExpand", + "TensorProduct", + "TensorQ", + "TensorRank", + "TensorReduce", + "TensorSymmetry", + "TensorTranspose", + "TensorWedge", + "TerminatedEvaluation", + "TernaryListPlot", + "TernaryPlotCorners", + "TestID", + "TestReport", + "TestReportObject", + "TestResultObject", + "Tetrahedron", + "TetrahedronBox", + "TetrahedronBoxOptions", + "TeXForm", + "TeXSave", + "Text", + "Text3DBox", + "Text3DBoxOptions", + "TextAlignment", + "TextBand", + "TextBoundingBox", + "TextBox", + "TextCases", + "TextCell", + "TextClipboardType", + "TextContents", + "TextData", + "TextElement", + "TextForm", + "TextGrid", + "TextJustification", + "TextLine", + "TextPacket", + "TextParagraph", + "TextPosition", + "TextRecognize", + "TextSearch", + "TextSearchReport", + "TextSentences", + "TextString", + "TextStructure", + "TextStyle", + "TextTranslation", + "Texture", + "TextureCoordinateFunction", + "TextureCoordinateScaling", + "TextWords", + "Therefore", + "ThermodynamicData", + "ThermometerGauge", + "Thick", + "Thickness", + "Thin", + "Thinning", + "ThisLink", + "ThomasPointProcess", + "ThompsonGroupTh", + "Thread", + "Threaded", + "ThreadingLayer", + "ThreeJSymbol", + "Threshold", + "Through", + "Throw", + "ThueMorse", + "Thumbnail", + "Thursday", + "TickDirection", + "TickLabelOrientation", + "TickLabelPositioning", + "TickLabels", + "TickLengths", + "TickPositions", + "Ticks", + "TicksStyle", + "TideData", + "Tilde", + "TildeEqual", + "TildeFullEqual", + "TildeTilde", + "TimeConstrained", + "TimeConstraint", + "TimeDirection", + "TimeFormat", + "TimeGoal", + "TimelinePlot", + "TimeObject", + "TimeObjectQ", + "TimeRemaining", + "Times", + "TimesBy", + "TimeSeries", + "TimeSeriesAggregate", + "TimeSeriesForecast", + "TimeSeriesInsert", + "TimeSeriesInvertibility", + "TimeSeriesMap", + "TimeSeriesMapThread", + "TimeSeriesModel", + "TimeSeriesModelFit", + "TimeSeriesResample", + "TimeSeriesRescale", + "TimeSeriesShift", + "TimeSeriesThread", + "TimeSeriesWindow", + "TimeSystem", + "TimeSystemConvert", + "TimeUsed", + "TimeValue", + "TimeWarpingCorrespondence", + "TimeWarpingDistance", + "TimeZone", + "TimeZoneConvert", + "TimeZoneOffset", + "Timing", + "Tiny", + "TitleGrouping", + "TitsGroupT", + "ToBoxes", + "ToCharacterCode", + "ToColor", + "ToContinuousTimeModel", + "ToDate", + "Today", + "ToDiscreteTimeModel", + "ToEntity", + "ToeplitzMatrix", + "ToExpression", + "ToFileName", + "Together", + "Toggle", + "ToggleFalse", + "Toggler", + "TogglerBar", + "TogglerBox", + "TogglerBoxOptions", + "ToHeldExpression", + "ToInvertibleTimeSeries", + "TokenWords", + "Tolerance", + "ToLowerCase", + "Tomorrow", + "ToNumberField", + "TooBig", + "Tooltip", + "TooltipBox", + "TooltipBoxOptions", + "TooltipDelay", + "TooltipStyle", + "ToonShading", + "Top", + "TopHatTransform", + "ToPolarCoordinates", + "TopologicalSort", + "ToRadicals", + "ToRawPointer", + "ToRules", + "Torus", + "TorusGraph", + "ToSphericalCoordinates", + "ToString", + "Total", + "TotalHeight", + "TotalLayer", + "TotalVariationFilter", + "TotalWidth", + "TouchPosition", + "TouchscreenAutoZoom", + "TouchscreenControlPlacement", + "ToUpperCase", + "TourVideo", + "Tr", + "Trace", + "TraceAbove", + "TraceAction", + "TraceBackward", + "TraceDepth", + "TraceDialog", + "TraceForward", + "TraceInternal", + "TraceLevel", + "TraceOff", + "TraceOn", + "TraceOriginal", + "TracePrint", + "TraceScan", + "TrackCellChangeTimes", + "TrackedSymbols", + "TrackingFunction", + "TracyWidomDistribution", + "TradingChart", + "TraditionalForm", + "TraditionalFunctionNotation", + "TraditionalNotation", + "TraditionalOrder", + "TrainImageContentDetector", + "TrainingProgressCheckpointing", + "TrainingProgressFunction", + "TrainingProgressMeasurements", + "TrainingProgressReporting", + "TrainingStoppingCriterion", + "TrainingUpdateSchedule", + "TrainTextContentDetector", + "TransferFunctionCancel", + "TransferFunctionExpand", + "TransferFunctionFactor", + "TransferFunctionModel", + "TransferFunctionPoles", + "TransferFunctionTransform", + "TransferFunctionZeros", + "TransformationClass", + "TransformationFunction", + "TransformationFunctions", + "TransformationMatrix", + "TransformedDistribution", + "TransformedField", + "TransformedProcess", + "TransformedRegion", + "TransitionDirection", + "TransitionDuration", + "TransitionEffect", + "TransitiveClosureGraph", + "TransitiveReductionGraph", + "Translate", + "TranslationOptions", + "TranslationTransform", + "Transliterate", + "Transparent", + "TransparentColor", + "Transpose", + "TransposeLayer", + "TrapEnterKey", + "TrapSelection", + "TravelDirections", + "TravelDirectionsData", + "TravelDistance", + "TravelDistanceList", + "TravelMethod", + "TravelTime", + "Tree", + "TreeCases", + "TreeChildren", + "TreeCount", + "TreeData", + "TreeDelete", + "TreeDepth", + "TreeElementCoordinates", + "TreeElementLabel", + "TreeElementLabelFunction", + "TreeElementLabelStyle", + "TreeElementShape", + "TreeElementShapeFunction", + "TreeElementSize", + "TreeElementSizeFunction", + "TreeElementStyle", + "TreeElementStyleFunction", + "TreeExpression", + "TreeExtract", + "TreeFold", + "TreeForm", + "TreeGraph", + "TreeGraphQ", + "TreeInsert", + "TreeLayout", + "TreeLeafCount", + "TreeLeafQ", + "TreeLeaves", + "TreeLevel", + "TreeMap", + "TreeMapAt", + "TreeOutline", + "TreePlot", + "TreePosition", + "TreeQ", + "TreeReplacePart", + "TreeRules", + "TreeScan", + "TreeSelect", + "TreeSize", + "TreeTraversalOrder", + "TrendStyle", + "Triangle", + "TriangleCenter", + "TriangleConstruct", + "TriangleMeasurement", + "TriangleWave", + "TriangularDistribution", + "TriangulateMesh", + "Trig", + "TrigExpand", + "TrigFactor", + "TrigFactorList", + "Trigger", + "TrigReduce", + "TrigToExp", + "TrimmedMean", + "TrimmedVariance", + "TropicalStormData", + "True", + "TrueQ", + "TruncatedDistribution", + "TruncatedPolyhedron", + "TsallisQExponentialDistribution", + "TsallisQGaussianDistribution", + "TTest", + "Tube", + "TubeBezierCurveBox", + "TubeBezierCurveBoxOptions", + "TubeBox", + "TubeBoxOptions", + "TubeBSplineCurveBox", + "TubeBSplineCurveBoxOptions", + "Tuesday", + "TukeyLambdaDistribution", + "TukeyWindow", + "TunnelData", + "Tuples", + "TuranGraph", + "TuringMachine", + "TuttePolynomial", + "TwoWayRule", + "Typed", + "TypeDeclaration", + "TypeEvaluate", + "TypeHint", + "TypeOf", + "TypeSpecifier", + "UnateQ", + "Uncompress", + "UnconstrainedParameters", + "Undefined", + "UnderBar", + "Underflow", + "Underlined", + "Underoverscript", + "UnderoverscriptBox", + "UnderoverscriptBoxOptions", + "Underscript", + "UnderscriptBox", + "UnderscriptBoxOptions", + "UnderseaFeatureData", + "UndirectedEdge", + "UndirectedGraph", + "UndirectedGraphQ", + "UndoOptions", + "UndoTrackedVariables", + "Unequal", + "UnequalTo", + "Unevaluated", + "UniformDistribution", + "UniformGraphDistribution", + "UniformPolyhedron", + "UniformSumDistribution", + "Uninstall", + "Union", + "UnionedEntityClass", + "UnionPlus", + "Unique", + "UniqueElements", + "UnitaryMatrixQ", + "UnitBox", + "UnitConvert", + "UnitDimensions", + "Unitize", + "UnitRootTest", + "UnitSimplify", + "UnitStep", + "UnitSystem", + "UnitTriangle", + "UnitVector", + "UnitVectorLayer", + "UnityDimensions", + "UniverseModelData", + "UniversityData", + "UnixTime", + "UnlabeledTree", + "UnmanageObject", + "Unprotect", + "UnregisterExternalEvaluator", + "UnsameQ", + "UnsavedVariables", + "Unset", + "UnsetShared", + "Until", + "UntrackedVariables", + "Up", + "UpArrow", + "UpArrowBar", + "UpArrowDownArrow", + "Update", + "UpdateDynamicObjects", + "UpdateDynamicObjectsSynchronous", + "UpdateInterval", + "UpdatePacletSites", + "UpdateSearchIndex", + "UpDownArrow", + "UpEquilibrium", + "UpperCaseQ", + "UpperLeftArrow", + "UpperRightArrow", + "UpperTriangularize", + "UpperTriangularMatrix", + "UpperTriangularMatrixQ", + "Upsample", + "UpSet", + "UpSetDelayed", + "UpTee", + "UpTeeArrow", + "UpTo", + "UpValues", + "URL", + "URLBuild", + "URLDecode", + "URLDispatcher", + "URLDownload", + "URLDownloadSubmit", + "URLEncode", + "URLExecute", + "URLExpand", + "URLFetch", + "URLFetchAsynchronous", + "URLParse", + "URLQueryDecode", + "URLQueryEncode", + "URLRead", + "URLResponseTime", + "URLSave", + "URLSaveAsynchronous", + "URLShorten", + "URLSubmit", + "UseEmbeddedLibrary", + "UseGraphicsRange", + "UserDefinedWavelet", + "Using", + "UsingFrontEnd", + "UtilityFunction", + "V2Get", + "ValenceErrorHandling", + "ValenceFilling", + "ValidationLength", + "ValidationSet", + "ValueBox", + "ValueBoxOptions", + "ValueDimensions", + "ValueForm", + "ValuePreprocessingFunction", + "ValueQ", + "Values", + "ValuesData", + "VandermondeMatrix", + "Variables", + "Variance", + "VarianceEquivalenceTest", + "VarianceEstimatorFunction", + "VarianceGammaDistribution", + "VarianceGammaPointProcess", + "VarianceTest", + "VariogramFunction", + "VariogramModel", + "VectorAngle", + "VectorAround", + "VectorAspectRatio", + "VectorColorFunction", + "VectorColorFunctionScaling", + "VectorDensityPlot", + "VectorDisplacementPlot", + "VectorDisplacementPlot3D", + "VectorGlyphData", + "VectorGreater", + "VectorGreaterEqual", + "VectorLess", + "VectorLessEqual", + "VectorMarkers", + "VectorPlot", + "VectorPlot3D", + "VectorPoints", + "VectorQ", + "VectorRange", + "Vectors", + "VectorScale", + "VectorScaling", + "VectorSizes", + "VectorStyle", + "Vee", + "Verbatim", + "Verbose", + "VerificationTest", + "VerifyConvergence", + "VerifyDerivedKey", + "VerifyDigitalSignature", + "VerifyFileSignature", + "VerifyInterpretation", + "VerifySecurityCertificates", + "VerifySolutions", + "VerifyTestAssumptions", + "VersionedPreferences", + "VertexAdd", + "VertexCapacity", + "VertexChromaticNumber", + "VertexColors", + "VertexComponent", + "VertexConnectivity", + "VertexContract", + "VertexCoordinateRules", + "VertexCoordinates", + "VertexCorrelationSimilarity", + "VertexCosineSimilarity", + "VertexCount", + "VertexCoverQ", + "VertexDataCoordinates", + "VertexDegree", + "VertexDelete", + "VertexDiceSimilarity", + "VertexEccentricity", + "VertexInComponent", + "VertexInComponentGraph", + "VertexInDegree", + "VertexIndex", + "VertexJaccardSimilarity", + "VertexLabeling", + "VertexLabels", + "VertexLabelStyle", + "VertexList", + "VertexNormals", + "VertexOutComponent", + "VertexOutComponentGraph", + "VertexOutDegree", + "VertexQ", + "VertexRenderingFunction", + "VertexReplace", + "VertexShape", + "VertexShapeFunction", + "VertexSize", + "VertexStyle", + "VertexTextureCoordinates", + "VertexTransitiveGraphQ", + "VertexWeight", + "VertexWeightedGraphQ", + "Vertical", + "VerticalBar", + "VerticalForm", + "VerticalGauge", + "VerticalSeparator", + "VerticalSlider", + "VerticalTilde", + "Video", + "VideoCapture", + "VideoCombine", + "VideoDelete", + "VideoEncoding", + "VideoExtractFrames", + "VideoFrameList", + "VideoFrameMap", + "VideoGenerator", + "VideoInsert", + "VideoIntervals", + "VideoJoin", + "VideoMap", + "VideoMapList", + "VideoMapTimeSeries", + "VideoPadding", + "VideoPause", + "VideoPlay", + "VideoQ", + "VideoRecord", + "VideoReplace", + "VideoScreenCapture", + "VideoSplit", + "VideoStop", + "VideoStream", + "VideoStreams", + "VideoTimeStretch", + "VideoTrackSelection", + "VideoTranscode", + "VideoTransparency", + "VideoTrim", + "ViewAngle", + "ViewCenter", + "ViewMatrix", + "ViewPoint", + "ViewPointSelectorSettings", + "ViewPort", + "ViewProjection", + "ViewRange", + "ViewVector", + "ViewVertical", + "VirtualGroupData", + "Visible", + "VisibleCell", + "VoiceStyleData", + "VoigtDistribution", + "VolcanoData", + "Volume", + "VonMisesDistribution", + "VoronoiMesh", + "WaitAll", + "WaitAsynchronousTask", + "WaitNext", + "WaitUntil", + "WakebyDistribution", + "WalleniusHypergeometricDistribution", + "WaringYuleDistribution", + "WarpingCorrespondence", + "WarpingDistance", + "WatershedComponents", + "WatsonUSquareTest", + "WattsStrogatzGraphDistribution", + "WaveletBestBasis", + "WaveletFilterCoefficients", + "WaveletImagePlot", + "WaveletListPlot", + "WaveletMapIndexed", + "WaveletMatrixPlot", + "WaveletPhi", + "WaveletPsi", + "WaveletScale", + "WaveletScalogram", + "WaveletThreshold", + "WavePDEComponent", + "WeaklyConnectedComponents", + "WeaklyConnectedGraphComponents", + "WeaklyConnectedGraphQ", + "WeakStationarity", + "WeatherData", + "WeatherForecastData", + "WebAudioSearch", + "WebColumn", + "WebElementObject", + "WeberE", + "WebExecute", + "WebImage", + "WebImageSearch", + "WebItem", + "WebPageMetaInformation", + "WebRow", + "WebSearch", + "WebSessionObject", + "WebSessions", + "WebWindowObject", + "Wedge", + "Wednesday", + "WeibullDistribution", + "WeierstrassE1", + "WeierstrassE2", + "WeierstrassE3", + "WeierstrassEta1", + "WeierstrassEta2", + "WeierstrassEta3", + "WeierstrassHalfPeriods", + "WeierstrassHalfPeriodW1", + "WeierstrassHalfPeriodW2", + "WeierstrassHalfPeriodW3", + "WeierstrassInvariantG2", + "WeierstrassInvariantG3", + "WeierstrassInvariants", + "WeierstrassP", + "WeierstrassPPrime", + "WeierstrassSigma", + "WeierstrassZeta", + "WeightedAdjacencyGraph", + "WeightedAdjacencyMatrix", + "WeightedData", + "WeightedGraphQ", + "Weights", + "WelchWindow", + "WheelGraph", + "WhenEvent", + "Which", + "While", + "White", + "WhiteNoiseProcess", + "WhitePoint", + "Whitespace", + "WhitespaceCharacter", + "WhittakerM", + "WhittakerW", + "WholeCellGroupOpener", + "WienerFilter", + "WienerProcess", + "WignerD", + "WignerSemicircleDistribution", + "WikidataData", + "WikidataSearch", + "WikipediaData", + "WikipediaSearch", + "WilksW", + "WilksWTest", + "WindDirectionData", + "WindingCount", + "WindingPolygon", + "WindowClickSelect", + "WindowElements", + "WindowFloating", + "WindowFrame", + "WindowFrameElements", + "WindowMargins", + "WindowMovable", + "WindowOpacity", + "WindowPersistentStyles", + "WindowSelected", + "WindowSize", + "WindowStatusArea", + "WindowTitle", + "WindowToolbars", + "WindowWidth", + "WindSpeedData", + "WindVectorData", + "WinsorizedMean", + "WinsorizedVariance", + "WishartMatrixDistribution", + "With", + "WithCleanup", + "WithLock", + "WolframAlpha", + "WolframAlphaDate", + "WolframAlphaQuantity", + "WolframAlphaResult", + "WolframCloudSettings", + "WolframLanguageData", + "Word", + "WordBoundary", + "WordCharacter", + "WordCloud", + "WordCount", + "WordCounts", + "WordData", + "WordDefinition", + "WordFrequency", + "WordFrequencyData", + "WordList", + "WordOrientation", + "WordSearch", + "WordSelectionFunction", + "WordSeparators", + "WordSpacings", + "WordStem", + "WordTranslation", + "WorkingPrecision", + "WrapAround", + "Write", + "WriteLine", + "WriteString", + "Wronskian", + "XMLElement", + "XMLObject", + "XMLTemplate", + "Xnor", + "Xor", + "XYZColor", + "Yellow", + "Yesterday", + "YuleDissimilarity", + "ZernikeR", + "ZeroSymmetric", + "ZeroTest", + "ZeroWidthTimes", + "Zeta", + "ZetaZero", + "ZIPCodeData", + "ZipfDistribution", + "ZoomCenter", + "ZoomFactor", + "ZTest", + "ZTransform", + "$Aborted", + "$ActivationGroupID", + "$ActivationKey", + "$ActivationUserRegistered", + "$AddOnsDirectory", + "$AllowDataUpdates", + "$AllowExternalChannelFunctions", + "$AllowInternet", + "$AssertFunction", + "$Assumptions", + "$AsynchronousTask", + "$AudioDecoders", + "$AudioEncoders", + "$AudioInputDevices", + "$AudioOutputDevices", + "$BaseDirectory", + "$BasePacletsDirectory", + "$BatchInput", + "$BatchOutput", + "$BlockchainBase", + "$BoxForms", + "$ByteOrdering", + "$CacheBaseDirectory", + "$Canceled", + "$ChannelBase", + "$CharacterEncoding", + "$CharacterEncodings", + "$CloudAccountName", + "$CloudBase", + "$CloudConnected", + "$CloudConnection", + "$CloudCreditsAvailable", + "$CloudEvaluation", + "$CloudExpressionBase", + "$CloudObjectNameFormat", + "$CloudObjectURLType", + "$CloudRootDirectory", + "$CloudSymbolBase", + "$CloudUserID", + "$CloudUserUUID", + "$CloudVersion", + "$CloudVersionNumber", + "$CloudWolframEngineVersionNumber", + "$CommandLine", + "$CompilationTarget", + "$CompilerEnvironment", + "$ConditionHold", + "$ConfiguredKernels", + "$Context", + "$ContextAliases", + "$ContextPath", + "$ControlActiveSetting", + "$Cookies", + "$CookieStore", + "$CreationDate", + "$CryptographicEllipticCurveNames", + "$CurrentLink", + "$CurrentTask", + "$CurrentWebSession", + "$DataStructures", + "$DateStringFormat", + "$DefaultAudioInputDevice", + "$DefaultAudioOutputDevice", + "$DefaultFont", + "$DefaultFrontEnd", + "$DefaultImagingDevice", + "$DefaultKernels", + "$DefaultLocalBase", + "$DefaultLocalKernel", + "$DefaultMailbox", + "$DefaultNetworkInterface", + "$DefaultPath", + "$DefaultProxyRules", + "$DefaultRemoteBatchSubmissionEnvironment", + "$DefaultRemoteKernel", + "$DefaultSystemCredentialStore", + "$Display", + "$DisplayFunction", + "$DistributedContexts", + "$DynamicEvaluation", + "$Echo", + "$EmbedCodeEnvironments", + "$EmbeddableServices", + "$EntityStores", + "$Epilog", + "$EvaluationCloudBase", + "$EvaluationCloudObject", + "$EvaluationEnvironment", + "$ExportFormats", + "$ExternalIdentifierTypes", + "$ExternalStorageBase", + "$Failed", + "$FinancialDataSource", + "$FontFamilies", + "$FormatType", + "$FrontEnd", + "$FrontEndSession", + "$GeneratedAssetLocation", + "$GeoEntityTypes", + "$GeoLocation", + "$GeoLocationCity", + "$GeoLocationCountry", + "$GeoLocationPrecision", + "$GeoLocationSource", + "$HistoryLength", + "$HomeDirectory", + "$HTMLExportRules", + "$HTTPCookies", + "$HTTPRequest", + "$IgnoreEOF", + "$ImageFormattingWidth", + "$ImageResolution", + "$ImagingDevice", + "$ImagingDevices", + "$ImportFormats", + "$IncomingMailSettings", + "$InitialDirectory", + "$Initialization", + "$InitializationContexts", + "$Input", + "$InputFileName", + "$InputStreamMethods", + "$Inspector", + "$InstallationDate", + "$InstallationDirectory", + "$InterfaceEnvironment", + "$InterpreterTypes", + "$IterationLimit", + "$KernelCount", + "$KernelID", + "$Language", + "$LaunchDirectory", + "$LibraryPath", + "$LicenseExpirationDate", + "$LicenseID", + "$LicenseProcesses", + "$LicenseServer", + "$LicenseSubprocesses", + "$LicenseType", + "$Line", + "$Linked", + "$LinkSupported", + "$LoadedFiles", + "$LocalBase", + "$LocalSymbolBase", + "$MachineAddresses", + "$MachineDomain", + "$MachineDomains", + "$MachineEpsilon", + "$MachineID", + "$MachineName", + "$MachinePrecision", + "$MachineType", + "$MaxDisplayedChildren", + "$MaxExtraPrecision", + "$MaxLicenseProcesses", + "$MaxLicenseSubprocesses", + "$MaxMachineNumber", + "$MaxNumber", + "$MaxPiecewiseCases", + "$MaxPrecision", + "$MaxRootDegree", + "$MessageGroups", + "$MessageList", + "$MessagePrePrint", + "$Messages", + "$MinMachineNumber", + "$MinNumber", + "$MinorReleaseNumber", + "$MinPrecision", + "$MobilePhone", + "$ModuleNumber", + "$NetworkConnected", + "$NetworkInterfaces", + "$NetworkLicense", + "$NewMessage", + "$NewSymbol", + "$NotebookInlineStorageLimit", + "$Notebooks", + "$NoValue", + "$NumberMarks", + "$Off", + "$OperatingSystem", + "$Output", + "$OutputForms", + "$OutputSizeLimit", + "$OutputStreamMethods", + "$Packages", + "$ParentLink", + "$ParentProcessID", + "$PasswordFile", + "$PatchLevelID", + "$Path", + "$PathnameSeparator", + "$PerformanceGoal", + "$Permissions", + "$PermissionsGroupBase", + "$PersistenceBase", + "$PersistencePath", + "$PipeSupported", + "$PlotTheme", + "$Post", + "$Pre", + "$PreferencesDirectory", + "$PreInitialization", + "$PrePrint", + "$PreRead", + "$PrintForms", + "$PrintLiteral", + "$Printout3DPreviewer", + "$ProcessID", + "$ProcessorCount", + "$ProcessorType", + "$ProductInformation", + "$ProgramName", + "$ProgressReporting", + "$PublisherID", + "$RandomGeneratorState", + "$RandomState", + "$RecursionLimit", + "$RegisteredDeviceClasses", + "$RegisteredUserName", + "$ReleaseNumber", + "$RequesterAddress", + "$RequesterCloudUserID", + "$RequesterCloudUserUUID", + "$RequesterWolframID", + "$RequesterWolframUUID", + "$ResourceSystemBase", + "$ResourceSystemPath", + "$RootDirectory", + "$ScheduledTask", + "$ScriptCommandLine", + "$ScriptInputString", + "$SecuredAuthenticationKeyTokens", + "$ServiceCreditsAvailable", + "$Services", + "$SessionID", + "$SetParentLink", + "$SharedFunctions", + "$SharedVariables", + "$SoundDisplay", + "$SoundDisplayFunction", + "$SourceLink", + "$SSHAuthentication", + "$SubtitleDecoders", + "$SubtitleEncoders", + "$SummaryBoxDataSizeLimit", + "$SuppressInputFormHeads", + "$SynchronousEvaluation", + "$SyntaxHandler", + "$System", + "$SystemCharacterEncoding", + "$SystemCredentialStore", + "$SystemID", + "$SystemMemory", + "$SystemShell", + "$SystemTimeZone", + "$SystemWordLength", + "$TargetSystems", + "$TemplatePath", + "$TemporaryDirectory", + "$TemporaryPrefix", + "$TestFileName", + "$TextStyle", + "$TimedOut", + "$TimeUnit", + "$TimeZone", + "$TimeZoneEntity", + "$TopDirectory", + "$TraceOff", + "$TraceOn", + "$TracePattern", + "$TracePostAction", + "$TracePreAction", + "$UnitSystem", + "$Urgent", + "$UserAddOnsDirectory", + "$UserAgentLanguages", + "$UserAgentMachine", + "$UserAgentName", + "$UserAgentOperatingSystem", + "$UserAgentString", + "$UserAgentVersion", + "$UserBaseDirectory", + "$UserBasePacletsDirectory", + "$UserDocumentsDirectory", + "$Username", + "$UserName", + "$UserURLBase", + "$Version", + "$VersionNumber", + "$VideoDecoders", + "$VideoEncoders", + "$VoiceStyles", + "$WolframDocumentsDirectory", + "$WolframID", + "$WolframUUID" +]; + +/* +Language: Wolfram Language +Description: The Wolfram Language is the programming language used in Wolfram Mathematica, a modern technical computing system spanning most areas of technical computing. +Authors: Patrick Scheibe , Robert Jacobson +Website: https://www.wolfram.com/mathematica/ +Category: scientific +*/ + + +/** @type LanguageFn */ +function mathematica(hljs) { + const regex = hljs.regex; + /* + This rather scary looking matching of Mathematica numbers is carefully explained by Robert Jacobson here: + https://wltools.github.io/LanguageSpec/Specification/Syntax/Number-representations/ + */ + const BASE_RE = /([2-9]|[1-2]\d|[3][0-5])\^\^/; + const BASE_DIGITS_RE = /(\w*\.\w+|\w+\.\w*|\w+)/; + const NUMBER_RE = /(\d*\.\d+|\d+\.\d*|\d+)/; + const BASE_NUMBER_RE = regex.either(regex.concat(BASE_RE, BASE_DIGITS_RE), NUMBER_RE); + + const ACCURACY_RE = /``[+-]?(\d*\.\d+|\d+\.\d*|\d+)/; + const PRECISION_RE = /`([+-]?(\d*\.\d+|\d+\.\d*|\d+))?/; + const APPROXIMATE_NUMBER_RE = regex.either(ACCURACY_RE, PRECISION_RE); + + const SCIENTIFIC_NOTATION_RE = /\*\^[+-]?\d+/; + + const MATHEMATICA_NUMBER_RE = regex.concat( + BASE_NUMBER_RE, + regex.optional(APPROXIMATE_NUMBER_RE), + regex.optional(SCIENTIFIC_NOTATION_RE) + ); + + const NUMBERS = { + className: 'number', + relevance: 0, + begin: MATHEMATICA_NUMBER_RE + }; + + const SYMBOL_RE = /[a-zA-Z$][a-zA-Z0-9$]*/; + const SYSTEM_SYMBOLS_SET = new Set(SYSTEM_SYMBOLS); + /** @type {Mode} */ + const SYMBOLS = { variants: [ + { + className: 'builtin-symbol', + begin: SYMBOL_RE, + // for performance out of fear of regex.either(...Mathematica.SYSTEM_SYMBOLS) + "on:begin": (match, response) => { + if (!SYSTEM_SYMBOLS_SET.has(match[0])) response.ignoreMatch(); + } + }, + { + className: 'symbol', + relevance: 0, + begin: SYMBOL_RE + } + ] }; + + const NAMED_CHARACTER = { + className: 'named-character', + begin: /\\\[[$a-zA-Z][$a-zA-Z0-9]+\]/ + }; + + const OPERATORS = { + className: 'operator', + relevance: 0, + begin: /[+\-*/,;.:@~=><&|_`'^?!%]+/ + }; + const PATTERNS = { + className: 'pattern', + relevance: 0, + begin: /([a-zA-Z$][a-zA-Z0-9$]*)?_+([a-zA-Z$][a-zA-Z0-9$]*)?/ + }; + + const SLOTS = { + className: 'slot', + relevance: 0, + begin: /#[a-zA-Z$][a-zA-Z0-9$]*|#+[0-9]?/ + }; + + const BRACES = { + className: 'brace', + relevance: 0, + begin: /[[\](){}]/ + }; + + const MESSAGES = { + className: 'message-name', + relevance: 0, + begin: regex.concat("::", SYMBOL_RE) + }; + + return { + name: 'Mathematica', + aliases: [ + 'mma', + 'wl' + ], + classNameAliases: { + brace: 'punctuation', + pattern: 'type', + slot: 'type', + symbol: 'variable', + 'named-character': 'variable', + 'builtin-symbol': 'built_in', + 'message-name': 'string' + }, + contains: [ + hljs.COMMENT(/\(\*/, /\*\)/, { contains: [ 'self' ] }), + PATTERNS, + SLOTS, + MESSAGES, + SYMBOLS, + NAMED_CHARACTER, + hljs.QUOTE_STRING_MODE, + NUMBERS, + OPERATORS, + BRACES + ] + }; +} + +export { mathematica as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/mathematica.js.js b/frontend/node_modules/highlight.js/es/languages/mathematica.js.js new file mode 100644 index 0000000..e7b98b8 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/mathematica.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/mathematica" instead of "highlight.js/lib/languages/mathematica.js"' + ); + } + } + emitWarning(); + import lang from './mathematica.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/matlab.js b/frontend/node_modules/highlight.js/es/languages/matlab.js new file mode 100644 index 0000000..dcdddee --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/matlab.js @@ -0,0 +1,107 @@ +/* +Language: Matlab +Author: Denis Bardadym +Contributors: Eugene Nizhibitsky , Egor Rogov +Website: https://www.mathworks.com/products/matlab.html +Category: scientific +*/ + +/* + Formal syntax is not published, helpful link: + https://github.com/kornilova-l/matlab-IntelliJ-plugin/blob/master/src/main/grammar/Matlab.bnf +*/ +function matlab(hljs) { + const TRANSPOSE_RE = '(\'|\\.\')+'; + const TRANSPOSE = { + relevance: 0, + contains: [ { begin: TRANSPOSE_RE } ] + }; + + return { + name: 'Matlab', + keywords: { + keyword: + 'arguments break case catch classdef continue else elseif end enumeration events for function ' + + 'global if methods otherwise parfor persistent properties return spmd switch try while', + built_in: + 'sin sind sinh asin asind asinh cos cosd cosh acos acosd acosh tan tand tanh atan ' + + 'atand atan2 atanh sec secd sech asec asecd asech csc cscd csch acsc acscd acsch cot ' + + 'cotd coth acot acotd acoth hypot exp expm1 log log1p log10 log2 pow2 realpow reallog ' + + 'realsqrt sqrt nthroot nextpow2 abs angle complex conj imag real unwrap isreal ' + + 'cplxpair fix floor ceil round mod rem sign airy besselj bessely besselh besseli ' + + 'besselk beta betainc betaln ellipj ellipke erf erfc erfcx erfinv expint gamma ' + + 'gammainc gammaln psi legendre cross dot factor isprime primes gcd lcm rat rats perms ' + + 'nchoosek factorial cart2sph cart2pol pol2cart sph2cart hsv2rgb rgb2hsv zeros ones ' + + 'eye repmat rand randn linspace logspace freqspace meshgrid accumarray size length ' + + 'ndims numel disp isempty isequal isequalwithequalnans cat reshape diag blkdiag tril ' + + 'triu fliplr flipud flipdim rot90 find sub2ind ind2sub bsxfun ndgrid permute ipermute ' + + 'shiftdim circshift squeeze isscalar isvector ans eps realmax realmin pi i|0 inf nan ' + + 'isnan isinf isfinite j|0 why compan gallery hadamard hankel hilb invhilb magic pascal ' + + 'rosser toeplitz vander wilkinson max min nanmax nanmin mean nanmean type table ' + + 'readtable writetable sortrows sort figure plot plot3 scatter scatter3 cellfun ' + + 'legend intersect ismember procrustes hold num2cell ' + }, + illegal: '(//|"|#|/\\*|\\s+/\\w+)', + contains: [ + { + className: 'function', + beginKeywords: 'function', + end: '$', + contains: [ + hljs.UNDERSCORE_TITLE_MODE, + { + className: 'params', + variants: [ + { + begin: '\\(', + end: '\\)' + }, + { + begin: '\\[', + end: '\\]' + } + ] + } + ] + }, + { + className: 'built_in', + begin: /true|false/, + relevance: 0, + starts: TRANSPOSE + }, + { + begin: '[a-zA-Z][a-zA-Z_0-9]*' + TRANSPOSE_RE, + relevance: 0 + }, + { + className: 'number', + begin: hljs.C_NUMBER_RE, + relevance: 0, + starts: TRANSPOSE + }, + { + className: 'string', + begin: '\'', + end: '\'', + contains: [ { begin: '\'\'' } ] + }, + { + begin: /\]|\}|\)/, + relevance: 0, + starts: TRANSPOSE + }, + { + className: 'string', + begin: '"', + end: '"', + contains: [ { begin: '""' } ], + starts: TRANSPOSE + }, + hljs.COMMENT('^\\s*%\\{\\s*$', '^\\s*%\\}\\s*$'), + hljs.COMMENT('%', '$') + ] + }; +} + +export { matlab as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/matlab.js.js b/frontend/node_modules/highlight.js/es/languages/matlab.js.js new file mode 100644 index 0000000..c2f9fcc --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/matlab.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/matlab" instead of "highlight.js/lib/languages/matlab.js"' + ); + } + } + emitWarning(); + import lang from './matlab.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/maxima.js b/frontend/node_modules/highlight.js/es/languages/maxima.js new file mode 100644 index 0000000..1254036 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/maxima.js @@ -0,0 +1,414 @@ +/* +Language: Maxima +Author: Robert Dodier +Website: http://maxima.sourceforge.net +Category: scientific +*/ + +function maxima(hljs) { + const KEYWORDS = + 'if then else elseif for thru do while unless step in and or not'; + const LITERALS = + 'true false unknown inf minf ind und %e %i %pi %phi %gamma'; + const BUILTIN_FUNCTIONS = + ' abasep abs absint absolute_real_time acos acosh acot acoth acsc acsch activate' + + ' addcol add_edge add_edges addmatrices addrow add_vertex add_vertices adjacency_matrix' + + ' adjoin adjoint af agd airy airy_ai airy_bi airy_dai airy_dbi algsys alg_type' + + ' alias allroots alphacharp alphanumericp amortization %and annuity_fv' + + ' annuity_pv antid antidiff AntiDifference append appendfile apply apply1 apply2' + + ' applyb1 apropos args arit_amortization arithmetic arithsum array arrayapply' + + ' arrayinfo arraymake arraysetapply ascii asec asech asin asinh askinteger' + + ' asksign assoc assoc_legendre_p assoc_legendre_q assume assume_external_byte_order' + + ' asympa at atan atan2 atanh atensimp atom atvalue augcoefmatrix augmented_lagrangian_method' + + ' av average_degree backtrace bars barsplot barsplot_description base64 base64_decode' + + ' bashindices batch batchload bc2 bdvac belln benefit_cost bern bernpoly bernstein_approx' + + ' bernstein_expand bernstein_poly bessel bessel_i bessel_j bessel_k bessel_simplify' + + ' bessel_y beta beta_incomplete beta_incomplete_generalized beta_incomplete_regularized' + + ' bezout bfallroots bffac bf_find_root bf_fmin_cobyla bfhzeta bfloat bfloatp' + + ' bfpsi bfpsi0 bfzeta biconnected_components bimetric binomial bipartition' + + ' block blockmatrixp bode_gain bode_phase bothcoef box boxplot boxplot_description' + + ' break bug_report build_info|10 buildq build_sample burn cabs canform canten' + + ' cardinality carg cartan cartesian_product catch cauchy_matrix cbffac cdf_bernoulli' + + ' cdf_beta cdf_binomial cdf_cauchy cdf_chi2 cdf_continuous_uniform cdf_discrete_uniform' + + ' cdf_exp cdf_f cdf_gamma cdf_general_finite_discrete cdf_geometric cdf_gumbel' + + ' cdf_hypergeometric cdf_laplace cdf_logistic cdf_lognormal cdf_negative_binomial' + + ' cdf_noncentral_chi2 cdf_noncentral_student_t cdf_normal cdf_pareto cdf_poisson' + + ' cdf_rank_sum cdf_rayleigh cdf_signed_rank cdf_student_t cdf_weibull cdisplay' + + ' ceiling central_moment cequal cequalignore cf cfdisrep cfexpand cgeodesic' + + ' cgreaterp cgreaterpignore changename changevar chaosgame charat charfun charfun2' + + ' charlist charp charpoly chdir chebyshev_t chebyshev_u checkdiv check_overlaps' + + ' chinese cholesky christof chromatic_index chromatic_number cint circulant_graph' + + ' clear_edge_weight clear_rules clear_vertex_label clebsch_gordan clebsch_graph' + + ' clessp clesspignore close closefile cmetric coeff coefmatrix cograd col collapse' + + ' collectterms columnop columnspace columnswap columnvector combination combine' + + ' comp2pui compare compfile compile compile_file complement_graph complete_bipartite_graph' + + ' complete_graph complex_number_p components compose_functions concan concat' + + ' conjugate conmetderiv connected_components connect_vertices cons constant' + + ' constantp constituent constvalue cont2part content continuous_freq contortion' + + ' contour_plot contract contract_edge contragrad contrib_ode convert coord' + + ' copy copy_file copy_graph copylist copymatrix cor cos cosh cot coth cov cov1' + + ' covdiff covect covers crc24sum create_graph create_list csc csch csetup cspline' + + ' ctaylor ct_coordsys ctransform ctranspose cube_graph cuboctahedron_graph' + + ' cunlisp cv cycle_digraph cycle_graph cylindrical days360 dblint deactivate' + + ' declare declare_constvalue declare_dimensions declare_fundamental_dimensions' + + ' declare_fundamental_units declare_qty declare_translated declare_unit_conversion' + + ' declare_units declare_weights decsym defcon define define_alt_display define_variable' + + ' defint defmatch defrule defstruct deftaylor degree_sequence del delete deleten' + + ' delta demo demoivre denom depends derivdegree derivlist describe desolve' + + ' determinant dfloat dgauss_a dgauss_b dgeev dgemm dgeqrf dgesv dgesvd diag' + + ' diagmatrix diag_matrix diagmatrixp diameter diff digitcharp dimacs_export' + + ' dimacs_import dimension dimensionless dimensions dimensions_as_list direct' + + ' directory discrete_freq disjoin disjointp disolate disp dispcon dispform' + + ' dispfun dispJordan display disprule dispterms distrib divide divisors divsum' + + ' dkummer_m dkummer_u dlange dodecahedron_graph dotproduct dotsimp dpart' + + ' draw draw2d draw3d drawdf draw_file draw_graph dscalar echelon edge_coloring' + + ' edge_connectivity edges eigens_by_jacobi eigenvalues eigenvectors eighth' + + ' einstein eivals eivects elapsed_real_time elapsed_run_time ele2comp ele2polynome' + + ' ele2pui elem elementp elevation_grid elim elim_allbut eliminate eliminate_using' + + ' ellipse elliptic_e elliptic_ec elliptic_eu elliptic_f elliptic_kc elliptic_pi' + + ' ematrix empty_graph emptyp endcons entermatrix entertensor entier equal equalp' + + ' equiv_classes erf erfc erf_generalized erfi errcatch error errormsg errors' + + ' euler ev eval_string evenp every evolution evolution2d evundiff example exp' + + ' expand expandwrt expandwrt_factored expint expintegral_chi expintegral_ci' + + ' expintegral_e expintegral_e1 expintegral_ei expintegral_e_simplify expintegral_li' + + ' expintegral_shi expintegral_si explicit explose exponentialize express expt' + + ' exsec extdiff extract_linear_equations extremal_subset ezgcd %f f90 facsum' + + ' factcomb factor factorfacsum factorial factorout factorsum facts fast_central_elements' + + ' fast_linsolve fasttimes featurep fernfale fft fib fibtophi fifth filename_merge' + + ' file_search file_type fillarray findde find_root find_root_abs find_root_error' + + ' find_root_rel first fix flatten flength float floatnump floor flower_snark' + + ' flush flush1deriv flushd flushnd flush_output fmin_cobyla forget fortran' + + ' fourcos fourexpand fourier fourier_elim fourint fourintcos fourintsin foursimp' + + ' foursin fourth fposition frame_bracket freeof freshline fresnel_c fresnel_s' + + ' from_adjacency_matrix frucht_graph full_listify fullmap fullmapl fullratsimp' + + ' fullratsubst fullsetify funcsolve fundamental_dimensions fundamental_units' + + ' fundef funmake funp fv g0 g1 gamma gamma_greek gamma_incomplete gamma_incomplete_generalized' + + ' gamma_incomplete_regularized gauss gauss_a gauss_b gaussprob gcd gcdex gcdivide' + + ' gcfac gcfactor gd generalized_lambert_w genfact gen_laguerre genmatrix gensym' + + ' geo_amortization geo_annuity_fv geo_annuity_pv geomap geometric geometric_mean' + + ' geosum get getcurrentdirectory get_edge_weight getenv get_lu_factors get_output_stream_string' + + ' get_pixel get_plot_option get_tex_environment get_tex_environment_default' + + ' get_vertex_label gfactor gfactorsum ggf girth global_variances gn gnuplot_close' + + ' gnuplot_replot gnuplot_reset gnuplot_restart gnuplot_start go Gosper GosperSum' + + ' gr2d gr3d gradef gramschmidt graph6_decode graph6_encode graph6_export graph6_import' + + ' graph_center graph_charpoly graph_eigenvalues graph_flow graph_order graph_periphery' + + ' graph_product graph_size graph_union great_rhombicosidodecahedron_graph great_rhombicuboctahedron_graph' + + ' grid_graph grind grobner_basis grotzch_graph hamilton_cycle hamilton_path' + + ' hankel hankel_1 hankel_2 harmonic harmonic_mean hav heawood_graph hermite' + + ' hessian hgfred hilbertmap hilbert_matrix hipow histogram histogram_description' + + ' hodge horner hypergeometric i0 i1 %ibes ic1 ic2 ic_convert ichr1 ichr2 icosahedron_graph' + + ' icosidodecahedron_graph icurvature ident identfor identity idiff idim idummy' + + ' ieqn %if ifactors iframes ifs igcdex igeodesic_coords ilt image imagpart' + + ' imetric implicit implicit_derivative implicit_plot indexed_tensor indices' + + ' induced_subgraph inferencep inference_result infix info_display init_atensor' + + ' init_ctensor in_neighbors innerproduct inpart inprod inrt integerp integer_partitions' + + ' integrate intersect intersection intervalp intopois intosum invariant1 invariant2' + + ' inverse_fft inverse_jacobi_cd inverse_jacobi_cn inverse_jacobi_cs inverse_jacobi_dc' + + ' inverse_jacobi_dn inverse_jacobi_ds inverse_jacobi_nc inverse_jacobi_nd inverse_jacobi_ns' + + ' inverse_jacobi_sc inverse_jacobi_sd inverse_jacobi_sn invert invert_by_adjoint' + + ' invert_by_lu inv_mod irr is is_biconnected is_bipartite is_connected is_digraph' + + ' is_edge_in_graph is_graph is_graph_or_digraph ishow is_isomorphic isolate' + + ' isomorphism is_planar isqrt isreal_p is_sconnected is_tree is_vertex_in_graph' + + ' items_inference %j j0 j1 jacobi jacobian jacobi_cd jacobi_cn jacobi_cs jacobi_dc' + + ' jacobi_dn jacobi_ds jacobi_nc jacobi_nd jacobi_ns jacobi_p jacobi_sc jacobi_sd' + + ' jacobi_sn JF jn join jordan julia julia_set julia_sin %k kdels kdelta kill' + + ' killcontext kostka kron_delta kronecker_product kummer_m kummer_u kurtosis' + + ' kurtosis_bernoulli kurtosis_beta kurtosis_binomial kurtosis_chi2 kurtosis_continuous_uniform' + + ' kurtosis_discrete_uniform kurtosis_exp kurtosis_f kurtosis_gamma kurtosis_general_finite_discrete' + + ' kurtosis_geometric kurtosis_gumbel kurtosis_hypergeometric kurtosis_laplace' + + ' kurtosis_logistic kurtosis_lognormal kurtosis_negative_binomial kurtosis_noncentral_chi2' + + ' kurtosis_noncentral_student_t kurtosis_normal kurtosis_pareto kurtosis_poisson' + + ' kurtosis_rayleigh kurtosis_student_t kurtosis_weibull label labels lagrange' + + ' laguerre lambda lambert_w laplace laplacian_matrix last lbfgs lc2kdt lcharp' + + ' lc_l lcm lc_u ldefint ldisp ldisplay legendre_p legendre_q leinstein length' + + ' let letrules letsimp levi_civita lfreeof lgtreillis lhs li liediff limit' + + ' Lindstedt linear linearinterpol linear_program linear_regression line_graph' + + ' linsolve listarray list_correlations listify list_matrix_entries list_nc_monomials' + + ' listoftens listofvars listp lmax lmin load loadfile local locate_matrix_entry' + + ' log logcontract log_gamma lopow lorentz_gauge lowercasep lpart lratsubst' + + ' lreduce lriemann lsquares_estimates lsquares_estimates_approximate lsquares_estimates_exact' + + ' lsquares_mse lsquares_residual_mse lsquares_residuals lsum ltreillis lu_backsub' + + ' lucas lu_factor %m macroexpand macroexpand1 make_array makebox makefact makegamma' + + ' make_graph make_level_picture makelist makeOrders make_poly_continent make_poly_country' + + ' make_polygon make_random_state make_rgb_picture makeset make_string_input_stream' + + ' make_string_output_stream make_transform mandelbrot mandelbrot_set map mapatom' + + ' maplist matchdeclare matchfix mat_cond mat_fullunblocker mat_function mathml_display' + + ' mat_norm matrix matrixmap matrixp matrix_size mattrace mat_trace mat_unblocker' + + ' max max_clique max_degree max_flow maximize_lp max_independent_set max_matching' + + ' maybe md5sum mean mean_bernoulli mean_beta mean_binomial mean_chi2 mean_continuous_uniform' + + ' mean_deviation mean_discrete_uniform mean_exp mean_f mean_gamma mean_general_finite_discrete' + + ' mean_geometric mean_gumbel mean_hypergeometric mean_laplace mean_logistic' + + ' mean_lognormal mean_negative_binomial mean_noncentral_chi2 mean_noncentral_student_t' + + ' mean_normal mean_pareto mean_poisson mean_rayleigh mean_student_t mean_weibull' + + ' median median_deviation member mesh metricexpandall mgf1_sha1 min min_degree' + + ' min_edge_cut minfactorial minimalPoly minimize_lp minimum_spanning_tree minor' + + ' minpack_lsquares minpack_solve min_vertex_cover min_vertex_cut mkdir mnewton' + + ' mod mode_declare mode_identity ModeMatrix moebius mon2schur mono monomial_dimensions' + + ' multibernstein_poly multi_display_for_texinfo multi_elem multinomial multinomial_coeff' + + ' multi_orbit multiplot_mode multi_pui multsym multthru mycielski_graph nary' + + ' natural_unit nc_degree ncexpt ncharpoly negative_picture neighbors new newcontext' + + ' newdet new_graph newline newton new_variable next_prime nicedummies niceindices' + + ' ninth nofix nonarray noncentral_moment nonmetricity nonnegintegerp nonscalarp' + + ' nonzeroandfreeof notequal nounify nptetrad npv nroots nterms ntermst' + + ' nthroot nullity nullspace num numbered_boundaries numberp number_to_octets' + + ' num_distinct_partitions numerval numfactor num_partitions nusum nzeta nzetai' + + ' nzetar octets_to_number octets_to_oid odd_girth oddp ode2 ode_check odelin' + + ' oid_to_octets op opena opena_binary openr openr_binary openw openw_binary' + + ' operatorp opsubst optimize %or orbit orbits ordergreat ordergreatp orderless' + + ' orderlessp orthogonal_complement orthopoly_recur orthopoly_weight outermap' + + ' out_neighbors outofpois pade parabolic_cylinder_d parametric parametric_surface' + + ' parg parGosper parse_string parse_timedate part part2cont partfrac partition' + + ' partition_set partpol path_digraph path_graph pathname_directory pathname_name' + + ' pathname_type pdf_bernoulli pdf_beta pdf_binomial pdf_cauchy pdf_chi2 pdf_continuous_uniform' + + ' pdf_discrete_uniform pdf_exp pdf_f pdf_gamma pdf_general_finite_discrete' + + ' pdf_geometric pdf_gumbel pdf_hypergeometric pdf_laplace pdf_logistic pdf_lognormal' + + ' pdf_negative_binomial pdf_noncentral_chi2 pdf_noncentral_student_t pdf_normal' + + ' pdf_pareto pdf_poisson pdf_rank_sum pdf_rayleigh pdf_signed_rank pdf_student_t' + + ' pdf_weibull pearson_skewness permanent permut permutation permutations petersen_graph' + + ' petrov pickapart picture_equalp picturep piechart piechart_description planar_embedding' + + ' playback plog plot2d plot3d plotdf ploteq plsquares pochhammer points poisdiff' + + ' poisexpt poisint poismap poisplus poissimp poissubst poistimes poistrim polar' + + ' polarform polartorect polar_to_xy poly_add poly_buchberger poly_buchberger_criterion' + + ' poly_colon_ideal poly_content polydecomp poly_depends_p poly_elimination_ideal' + + ' poly_exact_divide poly_expand poly_expt poly_gcd polygon poly_grobner poly_grobner_equal' + + ' poly_grobner_member poly_grobner_subsetp poly_ideal_intersection poly_ideal_polysaturation' + + ' poly_ideal_polysaturation1 poly_ideal_saturation poly_ideal_saturation1 poly_lcm' + + ' poly_minimization polymod poly_multiply polynome2ele polynomialp poly_normal_form' + + ' poly_normalize poly_normalize_list poly_polysaturation_extension poly_primitive_part' + + ' poly_pseudo_divide poly_reduced_grobner poly_reduction poly_saturation_extension' + + ' poly_s_polynomial poly_subtract polytocompanion pop postfix potential power_mod' + + ' powerseries powerset prefix prev_prime primep primes principal_components' + + ' print printf printfile print_graph printpois printprops prodrac product properties' + + ' propvars psi psubst ptriangularize pui pui2comp pui2ele pui2polynome pui_direct' + + ' puireduc push put pv qput qrange qty quad_control quad_qag quad_qagi quad_qagp' + + ' quad_qags quad_qawc quad_qawf quad_qawo quad_qaws quadrilateral quantile' + + ' quantile_bernoulli quantile_beta quantile_binomial quantile_cauchy quantile_chi2' + + ' quantile_continuous_uniform quantile_discrete_uniform quantile_exp quantile_f' + + ' quantile_gamma quantile_general_finite_discrete quantile_geometric quantile_gumbel' + + ' quantile_hypergeometric quantile_laplace quantile_logistic quantile_lognormal' + + ' quantile_negative_binomial quantile_noncentral_chi2 quantile_noncentral_student_t' + + ' quantile_normal quantile_pareto quantile_poisson quantile_rayleigh quantile_student_t' + + ' quantile_weibull quartile_skewness quit qunit quotient racah_v racah_w radcan' + + ' radius random random_bernoulli random_beta random_binomial random_bipartite_graph' + + ' random_cauchy random_chi2 random_continuous_uniform random_digraph random_discrete_uniform' + + ' random_exp random_f random_gamma random_general_finite_discrete random_geometric' + + ' random_graph random_graph1 random_gumbel random_hypergeometric random_laplace' + + ' random_logistic random_lognormal random_negative_binomial random_network' + + ' random_noncentral_chi2 random_noncentral_student_t random_normal random_pareto' + + ' random_permutation random_poisson random_rayleigh random_regular_graph random_student_t' + + ' random_tournament random_tree random_weibull range rank rat ratcoef ratdenom' + + ' ratdiff ratdisrep ratexpand ratinterpol rational rationalize ratnumer ratnump' + + ' ratp ratsimp ratsubst ratvars ratweight read read_array read_binary_array' + + ' read_binary_list read_binary_matrix readbyte readchar read_hashed_array readline' + + ' read_list read_matrix read_nested_list readonly read_xpm real_imagpart_to_conjugate' + + ' realpart realroots rearray rectangle rectform rectform_log_if_constant recttopolar' + + ' rediff reduce_consts reduce_order region region_boundaries region_boundaries_plus' + + ' rem remainder remarray rembox remcomps remcon remcoord remfun remfunction' + + ' remlet remove remove_constvalue remove_dimensions remove_edge remove_fundamental_dimensions' + + ' remove_fundamental_units remove_plot_option remove_vertex rempart remrule' + + ' remsym remvalue rename rename_file reset reset_displays residue resolvante' + + ' resolvante_alternee1 resolvante_bipartite resolvante_diedrale resolvante_klein' + + ' resolvante_klein3 resolvante_produit_sym resolvante_unitaire resolvante_vierer' + + ' rest resultant return reveal reverse revert revert2 rgb2level rhs ricci riemann' + + ' rinvariant risch rk rmdir rncombine romberg room rootscontract round row' + + ' rowop rowswap rreduce run_testsuite %s save saving scalarp scaled_bessel_i' + + ' scaled_bessel_i0 scaled_bessel_i1 scalefactors scanmap scatterplot scatterplot_description' + + ' scene schur2comp sconcat scopy scsimp scurvature sdowncase sec sech second' + + ' sequal sequalignore set_alt_display setdifference set_draw_defaults set_edge_weight' + + ' setelmx setequalp setify setp set_partitions set_plot_option set_prompt set_random_state' + + ' set_tex_environment set_tex_environment_default setunits setup_autoload set_up_dot_simplifications' + + ' set_vertex_label seventh sexplode sf sha1sum sha256sum shortest_path shortest_weighted_path' + + ' show showcomps showratvars sierpinskiale sierpinskimap sign signum similaritytransform' + + ' simp_inequality simplify_sum simplode simpmetderiv simtran sin sinh sinsert' + + ' sinvertcase sixth skewness skewness_bernoulli skewness_beta skewness_binomial' + + ' skewness_chi2 skewness_continuous_uniform skewness_discrete_uniform skewness_exp' + + ' skewness_f skewness_gamma skewness_general_finite_discrete skewness_geometric' + + ' skewness_gumbel skewness_hypergeometric skewness_laplace skewness_logistic' + + ' skewness_lognormal skewness_negative_binomial skewness_noncentral_chi2 skewness_noncentral_student_t' + + ' skewness_normal skewness_pareto skewness_poisson skewness_rayleigh skewness_student_t' + + ' skewness_weibull slength smake small_rhombicosidodecahedron_graph small_rhombicuboctahedron_graph' + + ' smax smin smismatch snowmap snub_cube_graph snub_dodecahedron_graph solve' + + ' solve_rec solve_rec_rat some somrac sort sparse6_decode sparse6_encode sparse6_export' + + ' sparse6_import specint spherical spherical_bessel_j spherical_bessel_y spherical_hankel1' + + ' spherical_hankel2 spherical_harmonic spherical_to_xyz splice split sposition' + + ' sprint sqfr sqrt sqrtdenest sremove sremovefirst sreverse ssearch ssort sstatus' + + ' ssubst ssubstfirst staircase standardize standardize_inverse_trig starplot' + + ' starplot_description status std std1 std_bernoulli std_beta std_binomial' + + ' std_chi2 std_continuous_uniform std_discrete_uniform std_exp std_f std_gamma' + + ' std_general_finite_discrete std_geometric std_gumbel std_hypergeometric std_laplace' + + ' std_logistic std_lognormal std_negative_binomial std_noncentral_chi2 std_noncentral_student_t' + + ' std_normal std_pareto std_poisson std_rayleigh std_student_t std_weibull' + + ' stemplot stirling stirling1 stirling2 strim striml strimr string stringout' + + ' stringp strong_components struve_h struve_l sublis sublist sublist_indices' + + ' submatrix subsample subset subsetp subst substinpart subst_parallel substpart' + + ' substring subvar subvarp sum sumcontract summand_to_rec supcase supcontext' + + ' symbolp symmdifference symmetricp system take_channel take_inference tan' + + ' tanh taylor taylorinfo taylorp taylor_simplifier taytorat tcl_output tcontract' + + ' tellrat tellsimp tellsimpafter tentex tenth test_mean test_means_difference' + + ' test_normality test_proportion test_proportions_difference test_rank_sum' + + ' test_sign test_signed_rank test_variance test_variance_ratio tex tex1 tex_display' + + ' texput %th third throw time timedate timer timer_info tldefint tlimit todd_coxeter' + + ' toeplitz tokens to_lisp topological_sort to_poly to_poly_solve totaldisrep' + + ' totalfourier totient tpartpol trace tracematrix trace_options transform_sample' + + ' translate translate_file transpose treefale tree_reduce treillis treinat' + + ' triangle triangularize trigexpand trigrat trigreduce trigsimp trunc truncate' + + ' truncated_cube_graph truncated_dodecahedron_graph truncated_icosahedron_graph' + + ' truncated_tetrahedron_graph tr_warnings_get tube tutte_graph ueivects uforget' + + ' ultraspherical underlying_graph undiff union unique uniteigenvectors unitp' + + ' units unit_step unitvector unorder unsum untellrat untimer' + + ' untrace uppercasep uricci uriemann uvect vandermonde_matrix var var1 var_bernoulli' + + ' var_beta var_binomial var_chi2 var_continuous_uniform var_discrete_uniform' + + ' var_exp var_f var_gamma var_general_finite_discrete var_geometric var_gumbel' + + ' var_hypergeometric var_laplace var_logistic var_lognormal var_negative_binomial' + + ' var_noncentral_chi2 var_noncentral_student_t var_normal var_pareto var_poisson' + + ' var_rayleigh var_student_t var_weibull vector vectorpotential vectorsimp' + + ' verbify vers vertex_coloring vertex_connectivity vertex_degree vertex_distance' + + ' vertex_eccentricity vertex_in_degree vertex_out_degree vertices vertices_to_cycle' + + ' vertices_to_path %w weyl wheel_graph wiener_index wigner_3j wigner_6j' + + ' wigner_9j with_stdout write_binary_data writebyte write_data writefile wronskian' + + ' xreduce xthru %y Zeilberger zeroequiv zerofor zeromatrix zeromatrixp zeta' + + ' zgeev zheev zlange zn_add_table zn_carmichael_lambda zn_characteristic_factors' + + ' zn_determinant zn_factor_generators zn_invert_by_lu zn_log zn_mult_table' + + ' absboxchar activecontexts adapt_depth additive adim aform algebraic' + + ' algepsilon algexact aliases allbut all_dotsimp_denoms allocation allsym alphabetic' + + ' animation antisymmetric arrays askexp assume_pos assume_pos_pred assumescalar' + + ' asymbol atomgrad atrig1 axes axis_3d axis_bottom axis_left axis_right axis_top' + + ' azimuth background background_color backsubst berlefact bernstein_explicit' + + ' besselexpand beta_args_sum_to_integer beta_expand bftorat bftrunc bindtest' + + ' border boundaries_array box boxchar breakup %c capping cauchysum cbrange' + + ' cbtics center cflength cframe_flag cnonmet_flag color color_bar color_bar_tics' + + ' colorbox columns commutative complex cone context contexts contour contour_levels' + + ' cosnpiflag ctaypov ctaypt ctayswitch ctayvar ct_coords ctorsion_flag ctrgsimp' + + ' cube current_let_rule_package cylinder data_file_name debugmode decreasing' + + ' default_let_rule_package delay dependencies derivabbrev derivsubst detout' + + ' diagmetric diff dim dimensions dispflag display2d|10 display_format_internal' + + ' distribute_over doallmxops domain domxexpt domxmxops domxnctimes dontfactor' + + ' doscmxops doscmxplus dot0nscsimp dot0simp dot1simp dotassoc dotconstrules' + + ' dotdistrib dotexptsimp dotident dotscrules draw_graph_program draw_realpart' + + ' edge_color edge_coloring edge_partition edge_type edge_width %edispflag' + + ' elevation %emode endphi endtheta engineering_format_floats enhanced3d %enumer' + + ' epsilon_lp erfflag erf_representation errormsg error_size error_syms error_type' + + ' %e_to_numlog eval even evenfun evflag evfun ev_point expandwrt_denom expintexpand' + + ' expintrep expon expop exptdispflag exptisolate exptsubst facexpand facsum_combine' + + ' factlim factorflag factorial_expand factors_only fb feature features' + + ' file_name file_output_append file_search_demo file_search_lisp file_search_maxima|10' + + ' file_search_tests file_search_usage file_type_lisp file_type_maxima|10 fill_color' + + ' fill_density filled_func fixed_vertices flipflag float2bf font font_size' + + ' fortindent fortspaces fpprec fpprintprec functions gamma_expand gammalim' + + ' gdet genindex gensumnum GGFCFMAX GGFINFINITY globalsolve gnuplot_command' + + ' gnuplot_curve_styles gnuplot_curve_titles gnuplot_default_term_command gnuplot_dumb_term_command' + + ' gnuplot_file_args gnuplot_file_name gnuplot_out_file gnuplot_pdf_term_command' + + ' gnuplot_pm3d gnuplot_png_term_command gnuplot_postamble gnuplot_preamble' + + ' gnuplot_ps_term_command gnuplot_svg_term_command gnuplot_term gnuplot_view_args' + + ' Gosper_in_Zeilberger gradefs grid grid2d grind halfangles head_angle head_both' + + ' head_length head_type height hypergeometric_representation %iargs ibase' + + ' icc1 icc2 icounter idummyx ieqnprint ifb ifc1 ifc2 ifg ifgi ifr iframe_bracket_form' + + ' ifri igeowedge_flag ikt1 ikt2 imaginary inchar increasing infeval' + + ' infinity inflag infolists inm inmc1 inmc2 intanalysis integer integervalued' + + ' integrate_use_rootsof integration_constant integration_constant_counter interpolate_color' + + ' intfaclim ip_grid ip_grid_in irrational isolate_wrt_times iterations itr' + + ' julia_parameter %k1 %k2 keepfloat key key_pos kinvariant kt label label_alignment' + + ' label_orientation labels lassociative lbfgs_ncorrections lbfgs_nfeval_max' + + ' leftjust legend letrat let_rule_packages lfg lg lhospitallim limsubst linear' + + ' linear_solver linechar linel|10 linenum line_type linewidth line_width linsolve_params' + + ' linsolvewarn lispdisp listarith listconstvars listdummyvars lmxchar load_pathname' + + ' loadprint logabs logarc logcb logconcoeffp logexpand lognegint logsimp logx' + + ' logx_secondary logy logy_secondary logz lriem m1pbranch macroexpansion macros' + + ' mainvar manual_demo maperror mapprint matrix_element_add matrix_element_mult' + + ' matrix_element_transpose maxapplydepth maxapplyheight maxima_tempdir|10 maxima_userdir|10' + + ' maxnegex MAX_ORD maxposex maxpsifracdenom maxpsifracnum maxpsinegint maxpsiposint' + + ' maxtayorder mesh_lines_color method mod_big_prime mode_check_errorp' + + ' mode_checkp mode_check_warnp mod_test mod_threshold modular_linear_solver' + + ' modulus multiplicative multiplicities myoptions nary negdistrib negsumdispflag' + + ' newline newtonepsilon newtonmaxiter nextlayerfactor niceindicespref nm nmc' + + ' noeval nolabels nonegative_lp noninteger nonscalar noun noundisp nouns np' + + ' npi nticks ntrig numer numer_pbranch obase odd oddfun opacity opproperties' + + ' opsubst optimprefix optionset orientation origin orthopoly_returns_intervals' + + ' outative outchar packagefile palette partswitch pdf_file pfeformat phiresolution' + + ' %piargs piece pivot_count_sx pivot_max_sx plot_format plot_options plot_realpart' + + ' png_file pochhammer_max_index points pointsize point_size points_joined point_type' + + ' poislim poisson poly_coefficient_ring poly_elimination_order polyfactor poly_grobner_algorithm' + + ' poly_grobner_debug poly_monomial_order poly_primary_elimination_order poly_return_term_list' + + ' poly_secondary_elimination_order poly_top_reduction_only posfun position' + + ' powerdisp pred prederror primep_number_of_tests product_use_gamma program' + + ' programmode promote_float_to_bigfloat prompt proportional_axes props psexpand' + + ' ps_file radexpand radius radsubstflag rassociative ratalgdenom ratchristof' + + ' ratdenomdivide rateinstein ratepsilon ratfac rational ratmx ratprint ratriemann' + + ' ratsimpexpons ratvarswitch ratweights ratweyl ratwtlvl real realonly redraw' + + ' refcheck resolution restart resultant ric riem rmxchar %rnum_list rombergabs' + + ' rombergit rombergmin rombergtol rootsconmode rootsepsilon run_viewer same_xy' + + ' same_xyz savedef savefactors scalar scalarmatrixp scale scale_lp setcheck' + + ' setcheckbreak setval show_edge_color show_edges show_edge_type show_edge_width' + + ' show_id show_label showtime show_vertex_color show_vertex_size show_vertex_type' + + ' show_vertices show_weight simp simplified_output simplify_products simpproduct' + + ' simpsum sinnpiflag solvedecomposes solveexplicit solvefactors solvenullwarn' + + ' solveradcan solvetrigwarn space sparse sphere spring_embedding_depth sqrtdispflag' + + ' stardisp startphi starttheta stats_numer stringdisp structures style sublis_apply_lambda' + + ' subnumsimp sumexpand sumsplitfact surface surface_hide svg_file symmetric' + + ' tab taylordepth taylor_logexpand taylor_order_coefficients taylor_truncate_polynomials' + + ' tensorkill terminal testsuite_files thetaresolution timer_devalue title tlimswitch' + + ' tr track transcompile transform transform_xy translate_fast_arrays transparent' + + ' transrun tr_array_as_ref tr_bound_function_applyp tr_file_tty_messagesp tr_float_can_branch_complex' + + ' tr_function_call_default trigexpandplus trigexpandtimes triginverses trigsign' + + ' trivial_solutions tr_numer tr_optimize_max_loop tr_semicompile tr_state_vars' + + ' tr_warn_bad_function_calls tr_warn_fexpr tr_warn_meval tr_warn_mode' + + ' tr_warn_undeclared tr_warn_undefined_variable tstep ttyoff tube_extremes' + + ' ufg ug %unitexpand unit_vectors uric uriem use_fast_arrays user_preamble' + + ' usersetunits values vect_cross verbose vertex_color vertex_coloring vertex_partition' + + ' vertex_size vertex_type view warnings weyl width windowname windowtitle wired_surface' + + ' wireframe xaxis xaxis_color xaxis_secondary xaxis_type xaxis_width xlabel' + + ' xlabel_secondary xlength xrange xrange_secondary xtics xtics_axis xtics_rotate' + + ' xtics_rotate_secondary xtics_secondary xtics_secondary_axis xu_grid x_voxel' + + ' xy_file xyplane xy_scale yaxis yaxis_color yaxis_secondary yaxis_type yaxis_width' + + ' ylabel ylabel_secondary ylength yrange yrange_secondary ytics ytics_axis' + + ' ytics_rotate ytics_rotate_secondary ytics_secondary ytics_secondary_axis' + + ' yv_grid y_voxel yx_ratio zaxis zaxis_color zaxis_type zaxis_width zeroa zerob' + + ' zerobern zeta%pi zlabel zlabel_rotate zlength zmin zn_primroot_limit zn_primroot_pretest'; + const SYMBOLS = '_ __ %|0 %%|0'; + + return { + name: 'Maxima', + keywords: { + $pattern: '[A-Za-z_%][0-9A-Za-z_%]*', + keyword: KEYWORDS, + literal: LITERALS, + built_in: BUILTIN_FUNCTIONS, + symbol: SYMBOLS + }, + contains: [ + { + className: 'comment', + begin: '/\\*', + end: '\\*/', + contains: [ 'self' ] + }, + hljs.QUOTE_STRING_MODE, + { + className: 'number', + relevance: 0, + variants: [ + { + // float number w/ exponent + // hmm, I wonder if we ought to include other exponent markers? + begin: '\\b(\\d+|\\d+\\.|\\.\\d+|\\d+\\.\\d+)[Ee][-+]?\\d+\\b' }, + { + // bigfloat number + begin: '\\b(\\d+|\\d+\\.|\\.\\d+|\\d+\\.\\d+)[Bb][-+]?\\d+\\b', + relevance: 10 + }, + { + // float number w/out exponent + // Doesn't seem to recognize floats which start with '.' + begin: '\\b(\\.\\d+|\\d+\\.\\d+)\\b' }, + { + // integer in base up to 36 + // Doesn't seem to recognize integers which end with '.' + begin: '\\b(\\d+|0[0-9A-Za-z]+)\\.?\\b' } + ] + } + ], + illegal: /@/ + }; +} + +export { maxima as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/maxima.js.js b/frontend/node_modules/highlight.js/es/languages/maxima.js.js new file mode 100644 index 0000000..de85908 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/maxima.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/maxima" instead of "highlight.js/lib/languages/maxima.js"' + ); + } + } + emitWarning(); + import lang from './maxima.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/mel.js b/frontend/node_modules/highlight.js/es/languages/mel.js new file mode 100644 index 0000000..df58c73 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/mel.js @@ -0,0 +1,235 @@ +/* +Language: MEL +Description: Maya Embedded Language +Author: Shuen-Huei Guan +Website: http://www.autodesk.com/products/autodesk-maya/overview +Category: graphics +*/ + +function mel(hljs) { + return { + name: 'MEL', + keywords: + 'int float string vector matrix if else switch case default while do for in break ' + + 'continue global proc return about abs addAttr addAttributeEditorNodeHelp addDynamic ' + + 'addNewShelfTab addPP addPanelCategory addPrefixToName advanceToNextDrivenKey ' + + 'affectedNet affects aimConstraint air alias aliasAttr align alignCtx alignCurve ' + + 'alignSurface allViewFit ambientLight angle angleBetween animCone animCurveEditor ' + + 'animDisplay animView annotate appendStringArray applicationName applyAttrPreset ' + + 'applyTake arcLenDimContext arcLengthDimension arclen arrayMapper art3dPaintCtx ' + + 'artAttrCtx artAttrPaintVertexCtx artAttrSkinPaintCtx artAttrTool artBuildPaintMenu ' + + 'artFluidAttrCtx artPuttyCtx artSelectCtx artSetPaintCtx artUserPaintCtx assignCommand ' + + 'assignInputDevice assignViewportFactories attachCurve attachDeviceAttr attachSurface ' + + 'attrColorSliderGrp attrCompatibility attrControlGrp attrEnumOptionMenu ' + + 'attrEnumOptionMenuGrp attrFieldGrp attrFieldSliderGrp attrNavigationControlGrp ' + + 'attrPresetEditWin attributeExists attributeInfo attributeMenu attributeQuery ' + + 'autoKeyframe autoPlace bakeClip bakeFluidShading bakePartialHistory bakeResults ' + + 'bakeSimulation basename basenameEx batchRender bessel bevel bevelPlus binMembership ' + + 'bindSkin blend2 blendShape blendShapeEditor blendShapePanel blendTwoAttr blindDataType ' + + 'boneLattice boundary boxDollyCtx boxZoomCtx bufferCurve buildBookmarkMenu ' + + 'buildKeyframeMenu button buttonManip CBG cacheFile cacheFileCombine cacheFileMerge ' + + 'cacheFileTrack camera cameraView canCreateManip canvas capitalizeString catch ' + + 'catchQuiet ceil changeSubdivComponentDisplayLevel changeSubdivRegion channelBox ' + + 'character characterMap characterOutlineEditor characterize chdir checkBox checkBoxGrp ' + + 'checkDefaultRenderGlobals choice circle circularFillet clamp clear clearCache clip ' + + 'clipEditor clipEditorCurrentTimeCtx clipSchedule clipSchedulerOutliner clipTrimBefore ' + + 'closeCurve closeSurface cluster cmdFileOutput cmdScrollFieldExecuter ' + + 'cmdScrollFieldReporter cmdShell coarsenSubdivSelectionList collision color ' + + 'colorAtPoint colorEditor colorIndex colorIndexSliderGrp colorSliderButtonGrp ' + + 'colorSliderGrp columnLayout commandEcho commandLine commandPort compactHairSystem ' + + 'componentEditor compositingInterop computePolysetVolume condition cone confirmDialog ' + + 'connectAttr connectControl connectDynamic connectJoint connectionInfo constrain ' + + 'constrainValue constructionHistory container containsMultibyte contextInfo control ' + + 'convertFromOldLayers convertIffToPsd convertLightmap convertSolidTx convertTessellation ' + + 'convertUnit copyArray copyFlexor copyKey copySkinWeights cos cpButton cpCache ' + + 'cpClothSet cpCollision cpConstraint cpConvClothToMesh cpForces cpGetSolverAttr cpPanel ' + + 'cpProperty cpRigidCollisionFilter cpSeam cpSetEdit cpSetSolverAttr cpSolver ' + + 'cpSolverTypes cpTool cpUpdateClothUVs createDisplayLayer createDrawCtx createEditor ' + + 'createLayeredPsdFile createMotionField createNewShelf createNode createRenderLayer ' + + 'createSubdivRegion cross crossProduct ctxAbort ctxCompletion ctxEditMode ctxTraverse ' + + 'currentCtx currentTime currentTimeCtx currentUnit curve curveAddPtCtx ' + + 'curveCVCtx curveEPCtx curveEditorCtx curveIntersect curveMoveEPCtx curveOnSurface ' + + 'curveSketchCtx cutKey cycleCheck cylinder dagPose date defaultLightListCheckBox ' + + 'defaultNavigation defineDataServer defineVirtualDevice deformer deg_to_rad delete ' + + 'deleteAttr deleteShadingGroupsAndMaterials deleteShelfTab deleteUI deleteUnusedBrushes ' + + 'delrandstr detachCurve detachDeviceAttr detachSurface deviceEditor devicePanel dgInfo ' + + 'dgdirty dgeval dgtimer dimWhen directKeyCtx directionalLight dirmap dirname disable ' + + 'disconnectAttr disconnectJoint diskCache displacementToPoly displayAffected ' + + 'displayColor displayCull displayLevelOfDetail displayPref displayRGBColor ' + + 'displaySmoothness displayStats displayString displaySurface distanceDimContext ' + + 'distanceDimension doBlur dolly dollyCtx dopeSheetEditor dot dotProduct ' + + 'doubleProfileBirailSurface drag dragAttrContext draggerContext dropoffLocator ' + + 'duplicate duplicateCurve duplicateSurface dynCache dynControl dynExport dynExpression ' + + 'dynGlobals dynPaintEditor dynParticleCtx dynPref dynRelEdPanel dynRelEditor ' + + 'dynamicLoad editAttrLimits editDisplayLayerGlobals editDisplayLayerMembers ' + + 'editRenderLayerAdjustment editRenderLayerGlobals editRenderLayerMembers editor ' + + 'editorTemplate effector emit emitter enableDevice encodeString endString endsWith env ' + + 'equivalent equivalentTol erf error eval evalDeferred evalEcho event ' + + 'exactWorldBoundingBox exclusiveLightCheckBox exec executeForEachObject exists exp ' + + 'expression expressionEditorListen extendCurve extendSurface extrude fcheck fclose feof ' + + 'fflush fgetline fgetword file fileBrowserDialog fileDialog fileExtension fileInfo ' + + 'filetest filletCurve filter filterCurve filterExpand filterStudioImport ' + + 'findAllIntersections findAnimCurves findKeyframe findMenuItem findRelatedSkinCluster ' + + 'finder firstParentOf fitBspline flexor floatEq floatField floatFieldGrp floatScrollBar ' + + 'floatSlider floatSlider2 floatSliderButtonGrp floatSliderGrp floor flow fluidCacheInfo ' + + 'fluidEmitter fluidVoxelInfo flushUndo fmod fontDialog fopen formLayout format fprint ' + + 'frameLayout fread freeFormFillet frewind fromNativePath fwrite gamma gauss ' + + 'geometryConstraint getApplicationVersionAsFloat getAttr getClassification ' + + 'getDefaultBrush getFileList getFluidAttr getInputDeviceRange getMayaPanelTypes ' + + 'getModifiers getPanel getParticleAttr getPluginResource getenv getpid glRender ' + + 'glRenderEditor globalStitch gmatch goal gotoBindPose grabColor gradientControl ' + + 'gradientControlNoAttr graphDollyCtx graphSelectContext graphTrackCtx gravity grid ' + + 'gridLayout group groupObjectsByName HfAddAttractorToAS HfAssignAS HfBuildEqualMap ' + + 'HfBuildFurFiles HfBuildFurImages HfCancelAFR HfConnectASToHF HfCreateAttractor ' + + 'HfDeleteAS HfEditAS HfPerformCreateAS HfRemoveAttractorFromAS HfSelectAttached ' + + 'HfSelectAttractors HfUnAssignAS hardenPointCurve hardware hardwareRenderPanel ' + + 'headsUpDisplay headsUpMessage help helpLine hermite hide hilite hitTest hotBox hotkey ' + + 'hotkeyCheck hsv_to_rgb hudButton hudSlider hudSliderButton hwReflectionMap hwRender ' + + 'hwRenderLoad hyperGraph hyperPanel hyperShade hypot iconTextButton iconTextCheckBox ' + + 'iconTextRadioButton iconTextRadioCollection iconTextScrollList iconTextStaticLabel ' + + 'ikHandle ikHandleCtx ikHandleDisplayScale ikSolver ikSplineHandleCtx ikSystem ' + + 'ikSystemInfo ikfkDisplayMethod illustratorCurves image imfPlugins inheritTransform ' + + 'insertJoint insertJointCtx insertKeyCtx insertKnotCurve insertKnotSurface instance ' + + 'instanceable instancer intField intFieldGrp intScrollBar intSlider intSliderGrp ' + + 'interToUI internalVar intersect iprEngine isAnimCurve isConnected isDirty isParentOf ' + + 'isSameObject isTrue isValidObjectName isValidString isValidUiName isolateSelect ' + + 'itemFilter itemFilterAttr itemFilterRender itemFilterType joint jointCluster jointCtx ' + + 'jointDisplayScale jointLattice keyTangent keyframe keyframeOutliner ' + + 'keyframeRegionCurrentTimeCtx keyframeRegionDirectKeyCtx keyframeRegionDollyCtx ' + + 'keyframeRegionInsertKeyCtx keyframeRegionMoveKeyCtx keyframeRegionScaleKeyCtx ' + + 'keyframeRegionSelectKeyCtx keyframeRegionSetKeyCtx keyframeRegionTrackCtx ' + + 'keyframeStats lassoContext lattice latticeDeformKeyCtx launch launchImageEditor ' + + 'layerButton layeredShaderPort layeredTexturePort layout layoutDialog lightList ' + + 'lightListEditor lightListPanel lightlink lineIntersection linearPrecision linstep ' + + 'listAnimatable listAttr listCameras listConnections listDeviceAttachments listHistory ' + + 'listInputDeviceAxes listInputDeviceButtons listInputDevices listMenuAnnotation ' + + 'listNodeTypes listPanelCategories listRelatives listSets listTransforms ' + + 'listUnselected listerEditor loadFluid loadNewShelf loadPlugin ' + + 'loadPluginLanguageResources loadPrefObjects localizedPanelLabel lockNode loft log ' + + 'longNameOf lookThru ls lsThroughFilter lsType lsUI Mayatomr mag makeIdentity makeLive ' + + 'makePaintable makeRoll makeSingleSurface makeTubeOn makebot manipMoveContext ' + + 'manipMoveLimitsCtx manipOptions manipRotateContext manipRotateLimitsCtx ' + + 'manipScaleContext manipScaleLimitsCtx marker match max memory menu menuBarLayout ' + + 'menuEditor menuItem menuItemToShelf menuSet menuSetPref messageLine min minimizeApp ' + + 'mirrorJoint modelCurrentTimeCtx modelEditor modelPanel mouse movIn movOut move ' + + 'moveIKtoFK moveKeyCtx moveVertexAlongDirection multiProfileBirailSurface mute ' + + 'nParticle nameCommand nameField namespace namespaceInfo newPanelItems newton nodeCast ' + + 'nodeIconButton nodeOutliner nodePreset nodeType noise nonLinear normalConstraint ' + + 'normalize nurbsBoolean nurbsCopyUVSet nurbsCube nurbsEditUV nurbsPlane nurbsSelect ' + + 'nurbsSquare nurbsToPoly nurbsToPolygonsPref nurbsToSubdiv nurbsToSubdivPref ' + + 'nurbsUVSet nurbsViewDirectionVector objExists objectCenter objectLayer objectType ' + + 'objectTypeUI obsoleteProc oceanNurbsPreviewPlane offsetCurve offsetCurveOnSurface ' + + 'offsetSurface openGLExtension openMayaPref optionMenu optionMenuGrp optionVar orbit ' + + 'orbitCtx orientConstraint outlinerEditor outlinerPanel overrideModifier ' + + 'paintEffectsDisplay pairBlend palettePort paneLayout panel panelConfiguration ' + + 'panelHistory paramDimContext paramDimension paramLocator parent parentConstraint ' + + 'particle particleExists particleInstancer particleRenderInfo partition pasteKey ' + + 'pathAnimation pause pclose percent performanceOptions pfxstrokes pickWalk picture ' + + 'pixelMove planarSrf plane play playbackOptions playblast plugAttr plugNode pluginInfo ' + + 'pluginResourceUtil pointConstraint pointCurveConstraint pointLight pointMatrixMult ' + + 'pointOnCurve pointOnSurface pointPosition poleVectorConstraint polyAppend ' + + 'polyAppendFacetCtx polyAppendVertex polyAutoProjection polyAverageNormal ' + + 'polyAverageVertex polyBevel polyBlendColor polyBlindData polyBoolOp polyBridgeEdge ' + + 'polyCacheMonitor polyCheck polyChipOff polyClipboard polyCloseBorder polyCollapseEdge ' + + 'polyCollapseFacet polyColorBlindData polyColorDel polyColorPerVertex polyColorSet ' + + 'polyCompare polyCone polyCopyUV polyCrease polyCreaseCtx polyCreateFacet ' + + 'polyCreateFacetCtx polyCube polyCut polyCutCtx polyCylinder polyCylindricalProjection ' + + 'polyDelEdge polyDelFacet polyDelVertex polyDuplicateAndConnect polyDuplicateEdge ' + + 'polyEditUV polyEditUVShell polyEvaluate polyExtrudeEdge polyExtrudeFacet ' + + 'polyExtrudeVertex polyFlipEdge polyFlipUV polyForceUV polyGeoSampler polyHelix ' + + 'polyInfo polyInstallAction polyLayoutUV polyListComponentConversion polyMapCut ' + + 'polyMapDel polyMapSew polyMapSewMove polyMergeEdge polyMergeEdgeCtx polyMergeFacet ' + + 'polyMergeFacetCtx polyMergeUV polyMergeVertex polyMirrorFace polyMoveEdge ' + + 'polyMoveFacet polyMoveFacetUV polyMoveUV polyMoveVertex polyNormal polyNormalPerVertex ' + + 'polyNormalizeUV polyOptUvs polyOptions polyOutput polyPipe polyPlanarProjection ' + + 'polyPlane polyPlatonicSolid polyPoke polyPrimitive polyPrism polyProjection ' + + 'polyPyramid polyQuad polyQueryBlindData polyReduce polySelect polySelectConstraint ' + + 'polySelectConstraintMonitor polySelectCtx polySelectEditCtx polySeparate ' + + 'polySetToFaceNormal polySewEdge polyShortestPathCtx polySmooth polySoftEdge ' + + 'polySphere polySphericalProjection polySplit polySplitCtx polySplitEdge polySplitRing ' + + 'polySplitVertex polyStraightenUVBorder polySubdivideEdge polySubdivideFacet ' + + 'polyToSubdiv polyTorus polyTransfer polyTriangulate polyUVSet polyUnite polyWedgeFace ' + + 'popen popupMenu pose pow preloadRefEd print progressBar progressWindow projFileViewer ' + + 'projectCurve projectTangent projectionContext projectionManip promptDialog propModCtx ' + + 'propMove psdChannelOutliner psdEditTextureFile psdExport psdTextureFile putenv pwd ' + + 'python querySubdiv quit rad_to_deg radial radioButton radioButtonGrp radioCollection ' + + 'radioMenuItemCollection rampColorPort rand randomizeFollicles randstate rangeControl ' + + 'readTake rebuildCurve rebuildSurface recordAttr recordDevice redo reference ' + + 'referenceEdit referenceQuery refineSubdivSelectionList refresh refreshAE ' + + 'registerPluginResource rehash reloadImage removeJoint removeMultiInstance ' + + 'removePanelCategory rename renameAttr renameSelectionList renameUI render ' + + 'renderGlobalsNode renderInfo renderLayerButton renderLayerParent ' + + 'renderLayerPostProcess renderLayerUnparent renderManip renderPartition ' + + 'renderQualityNode renderSettings renderThumbnailUpdate renderWindowEditor ' + + 'renderWindowSelectContext renderer reorder reorderDeformers requires reroot ' + + 'resampleFluid resetAE resetPfxToPolyCamera resetTool resolutionNode retarget ' + + 'reverseCurve reverseSurface revolve rgb_to_hsv rigidBody rigidSolver roll rollCtx ' + + 'rootOf rot rotate rotationInterpolation roundConstantRadius rowColumnLayout rowLayout ' + + 'runTimeCommand runup sampleImage saveAllShelves saveAttrPreset saveFluid saveImage ' + + 'saveInitialState saveMenu savePrefObjects savePrefs saveShelf saveToolSettings scale ' + + 'scaleBrushBrightness scaleComponents scaleConstraint scaleKey scaleKeyCtx sceneEditor ' + + 'sceneUIReplacement scmh scriptCtx scriptEditorInfo scriptJob scriptNode scriptTable ' + + 'scriptToShelf scriptedPanel scriptedPanelType scrollField scrollLayout sculpt ' + + 'searchPathArray seed selLoadSettings select selectContext selectCurveCV selectKey ' + + 'selectKeyCtx selectKeyframeRegionCtx selectMode selectPref selectPriority selectType ' + + 'selectedNodes selectionConnection separator setAttr setAttrEnumResource ' + + 'setAttrMapping setAttrNiceNameResource setConstraintRestPosition ' + + 'setDefaultShadingGroup setDrivenKeyframe setDynamic setEditCtx setEditor setFluidAttr ' + + 'setFocus setInfinity setInputDeviceMapping setKeyCtx setKeyPath setKeyframe ' + + 'setKeyframeBlendshapeTargetWts setMenuMode setNodeNiceNameResource setNodeTypeFlag ' + + 'setParent setParticleAttr setPfxToPolyCamera setPluginResource setProject ' + + 'setStampDensity setStartupMessage setState setToolTo setUITemplate setXformManip sets ' + + 'shadingConnection shadingGeometryRelCtx shadingLightRelCtx shadingNetworkCompare ' + + 'shadingNode shapeCompare shelfButton shelfLayout shelfTabLayout shellField ' + + 'shortNameOf showHelp showHidden showManipCtx showSelectionInTitle ' + + 'showShadingGroupAttrEditor showWindow sign simplify sin singleProfileBirailSurface ' + + 'size sizeBytes skinCluster skinPercent smoothCurve smoothTangentSurface smoothstep ' + + 'snap2to2 snapKey snapMode snapTogetherCtx snapshot soft softMod softModCtx sort sound ' + + 'soundControl source spaceLocator sphere sphrand spotLight spotLightPreviewPort ' + + 'spreadSheetEditor spring sqrt squareSurface srtContext stackTrace startString ' + + 'startsWith stitchAndExplodeShell stitchSurface stitchSurfacePoints strcmp ' + + 'stringArrayCatenate stringArrayContains stringArrayCount stringArrayInsertAtIndex ' + + 'stringArrayIntersector stringArrayRemove stringArrayRemoveAtIndex ' + + 'stringArrayRemoveDuplicates stringArrayRemoveExact stringArrayToString ' + + 'stringToStringArray strip stripPrefixFromName stroke subdAutoProjection ' + + 'subdCleanTopology subdCollapse subdDuplicateAndConnect subdEditUV ' + + 'subdListComponentConversion subdMapCut subdMapSewMove subdMatchTopology subdMirror ' + + 'subdToBlind subdToPoly subdTransferUVsToCache subdiv subdivCrease ' + + 'subdivDisplaySmoothness substitute substituteAllString substituteGeometry substring ' + + 'surface surfaceSampler surfaceShaderList swatchDisplayPort switchTable symbolButton ' + + 'symbolCheckBox sysFile system tabLayout tan tangentConstraint texLatticeDeformContext ' + + 'texManipContext texMoveContext texMoveUVShellContext texRotateContext texScaleContext ' + + 'texSelectContext texSelectShortestPathCtx texSmudgeUVContext texWinToolCtx text ' + + 'textCurves textField textFieldButtonGrp textFieldGrp textManip textScrollList ' + + 'textToShelf textureDisplacePlane textureHairColor texturePlacementContext ' + + 'textureWindow threadCount threePointArcCtx timeControl timePort timerX toNativePath ' + + 'toggle toggleAxis toggleWindowVisibility tokenize tokenizeList tolerance tolower ' + + 'toolButton toolCollection toolDropped toolHasOptions toolPropertyWindow torus toupper ' + + 'trace track trackCtx transferAttributes transformCompare transformLimits translator ' + + 'trim trunc truncateFluidCache truncateHairCache tumble tumbleCtx turbulence ' + + 'twoPointArcCtx uiRes uiTemplate unassignInputDevice undo undoInfo ungroup uniform unit ' + + 'unloadPlugin untangleUV untitledFileName untrim upAxis updateAE userCtx uvLink ' + + 'uvSnapshot validateShelfName vectorize view2dToolCtx viewCamera viewClipPlane ' + + 'viewFit viewHeadOn viewLookAt viewManip viewPlace viewSet visor volumeAxis vortex ' + + 'waitCursor warning webBrowser webBrowserPrefs whatIs window windowPref wire ' + + 'wireContext workspace wrinkle wrinkleContext writeTake xbmLangPathList xform', + illegal: ' +Description: Mercury is a logic/functional programming language which combines the clarity and expressiveness of declarative programming with advanced static analysis and error detection features. +Website: https://www.mercurylang.org +Category: functional +*/ + +function mercury(hljs) { + const KEYWORDS = { + keyword: + 'module use_module import_module include_module end_module initialise ' + + 'mutable initialize finalize finalise interface implementation pred ' + + 'mode func type inst solver any_pred any_func is semidet det nondet ' + + 'multi erroneous failure cc_nondet cc_multi typeclass instance where ' + + 'pragma promise external trace atomic or_else require_complete_switch ' + + 'require_det require_semidet require_multi require_nondet ' + + 'require_cc_multi require_cc_nondet require_erroneous require_failure', + meta: + // pragma + 'inline no_inline type_spec source_file fact_table obsolete memo ' + + 'loop_check minimal_model terminates does_not_terminate ' + + 'check_termination promise_equivalent_clauses ' + // preprocessor + + 'foreign_proc foreign_decl foreign_code foreign_type ' + + 'foreign_import_module foreign_export_enum foreign_export ' + + 'foreign_enum may_call_mercury will_not_call_mercury thread_safe ' + + 'not_thread_safe maybe_thread_safe promise_pure promise_semipure ' + + 'tabled_for_io local untrailed trailed attach_to_io_state ' + + 'can_pass_as_mercury_type stable will_not_throw_exception ' + + 'may_modify_trail will_not_modify_trail may_duplicate ' + + 'may_not_duplicate affects_liveness does_not_affect_liveness ' + + 'doesnt_affect_liveness no_sharing unknown_sharing sharing', + built_in: + 'some all not if then else true fail false try catch catch_any ' + + 'semidet_true semidet_false semidet_fail impure_true impure semipure' + }; + + const COMMENT = hljs.COMMENT('%', '$'); + + const NUMCODE = { + className: 'number', + begin: "0'.\\|0[box][0-9a-fA-F]*" + }; + + const ATOM = hljs.inherit(hljs.APOS_STRING_MODE, { relevance: 0 }); + const STRING = hljs.inherit(hljs.QUOTE_STRING_MODE, { relevance: 0 }); + const STRING_FMT = { + className: 'subst', + begin: '\\\\[abfnrtv]\\|\\\\x[0-9a-fA-F]*\\\\\\|%[-+# *.0-9]*[dioxXucsfeEgGp]', + relevance: 0 + }; + STRING.contains = STRING.contains.slice(); // we need our own copy of contains + STRING.contains.push(STRING_FMT); + + const IMPLICATION = { + className: 'built_in', + variants: [ + { begin: '<=>' }, + { + begin: '<=', + relevance: 0 + }, + { + begin: '=>', + relevance: 0 + }, + { begin: '/\\\\' }, + { begin: '\\\\/' } + ] + }; + + const HEAD_BODY_CONJUNCTION = { + className: 'built_in', + variants: [ + { begin: ':-\\|-->' }, + { + begin: '=', + relevance: 0 + } + ] + }; + + return { + name: 'Mercury', + aliases: [ + 'm', + 'moo' + ], + keywords: KEYWORDS, + contains: [ + IMPLICATION, + HEAD_BODY_CONJUNCTION, + COMMENT, + hljs.C_BLOCK_COMMENT_MODE, + NUMCODE, + hljs.NUMBER_MODE, + ATOM, + STRING, + { // relevance booster + begin: /:-/ }, + { // relevance booster + begin: /\.$/ } + ] + }; +} + +export { mercury as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/mercury.js.js b/frontend/node_modules/highlight.js/es/languages/mercury.js.js new file mode 100644 index 0000000..0a48071 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/mercury.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/mercury" instead of "highlight.js/lib/languages/mercury.js"' + ); + } + } + emitWarning(); + import lang from './mercury.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/mipsasm.js b/frontend/node_modules/highlight.js/es/languages/mipsasm.js new file mode 100644 index 0000000..2ab2ef3 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/mipsasm.js @@ -0,0 +1,104 @@ +/* +Language: MIPS Assembly +Author: Nebuleon Fumika +Description: MIPS Assembly (up to MIPS32R2) +Website: https://en.wikipedia.org/wiki/MIPS_architecture +Category: assembler +*/ + +function mipsasm(hljs) { + // local labels: %?[FB]?[AT]?\d{1,2}\w+ + return { + name: 'MIPS Assembly', + case_insensitive: true, + aliases: [ 'mips' ], + keywords: { + $pattern: '\\.?' + hljs.IDENT_RE, + meta: + // GNU preprocs + '.2byte .4byte .align .ascii .asciz .balign .byte .code .data .else .end .endif .endm .endr .equ .err .exitm .extern .global .hword .if .ifdef .ifndef .include .irp .long .macro .rept .req .section .set .skip .space .text .word .ltorg ', + built_in: + '$0 $1 $2 $3 $4 $5 $6 $7 $8 $9 $10 $11 $12 $13 $14 $15 ' // integer registers + + '$16 $17 $18 $19 $20 $21 $22 $23 $24 $25 $26 $27 $28 $29 $30 $31 ' // integer registers + + 'zero at v0 v1 a0 a1 a2 a3 a4 a5 a6 a7 ' // integer register aliases + + 't0 t1 t2 t3 t4 t5 t6 t7 t8 t9 s0 s1 s2 s3 s4 s5 s6 s7 s8 ' // integer register aliases + + 'k0 k1 gp sp fp ra ' // integer register aliases + + '$f0 $f1 $f2 $f2 $f4 $f5 $f6 $f7 $f8 $f9 $f10 $f11 $f12 $f13 $f14 $f15 ' // floating-point registers + + '$f16 $f17 $f18 $f19 $f20 $f21 $f22 $f23 $f24 $f25 $f26 $f27 $f28 $f29 $f30 $f31 ' // floating-point registers + + 'Context Random EntryLo0 EntryLo1 Context PageMask Wired EntryHi ' // Coprocessor 0 registers + + 'HWREna BadVAddr Count Compare SR IntCtl SRSCtl SRSMap Cause EPC PRId ' // Coprocessor 0 registers + + 'EBase Config Config1 Config2 Config3 LLAddr Debug DEPC DESAVE CacheErr ' // Coprocessor 0 registers + + 'ECC ErrorEPC TagLo DataLo TagHi DataHi WatchLo WatchHi PerfCtl PerfCnt ' // Coprocessor 0 registers + }, + contains: [ + { + className: 'keyword', + begin: '\\b(' // mnemonics + // 32-bit integer instructions + + 'addi?u?|andi?|b(al)?|beql?|bgez(al)?l?|bgtzl?|blezl?|bltz(al)?l?|' + + 'bnel?|cl[oz]|divu?|ext|ins|j(al)?|jalr(\\.hb)?|jr(\\.hb)?|lbu?|lhu?|' + + 'll|lui|lw[lr]?|maddu?|mfhi|mflo|movn|movz|move|msubu?|mthi|mtlo|mul|' + + 'multu?|nop|nor|ori?|rotrv?|sb|sc|se[bh]|sh|sllv?|slti?u?|srav?|' + + 'srlv?|subu?|sw[lr]?|xori?|wsbh|' + // floating-point instructions + + 'abs\\.[sd]|add\\.[sd]|alnv.ps|bc1[ft]l?|' + + 'c\\.(s?f|un|u?eq|[ou]lt|[ou]le|ngle?|seq|l[et]|ng[et])\\.[sd]|' + + '(ceil|floor|round|trunc)\\.[lw]\\.[sd]|cfc1|cvt\\.d\\.[lsw]|' + + 'cvt\\.l\\.[dsw]|cvt\\.ps\\.s|cvt\\.s\\.[dlw]|cvt\\.s\\.p[lu]|cvt\\.w\\.[dls]|' + + 'div\\.[ds]|ldx?c1|luxc1|lwx?c1|madd\\.[sd]|mfc1|mov[fntz]?\\.[ds]|' + + 'msub\\.[sd]|mth?c1|mul\\.[ds]|neg\\.[ds]|nmadd\\.[ds]|nmsub\\.[ds]|' + + 'p[lu][lu]\\.ps|recip\\.fmt|r?sqrt\\.[ds]|sdx?c1|sub\\.[ds]|suxc1|' + + 'swx?c1|' + // system control instructions + + 'break|cache|d?eret|[de]i|ehb|mfc0|mtc0|pause|prefx?|rdhwr|' + + 'rdpgpr|sdbbp|ssnop|synci?|syscall|teqi?|tgei?u?|tlb(p|r|w[ir])|' + + 'tlti?u?|tnei?|wait|wrpgpr' + + ')', + end: '\\s' + }, + // lines ending with ; or # aren't really comments, probably auto-detect fail + hljs.COMMENT('[;#](?!\\s*$)', '$'), + hljs.C_BLOCK_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + { + className: 'string', + begin: '\'', + end: '[^\\\\]\'', + relevance: 0 + }, + { + className: 'title', + begin: '\\|', + end: '\\|', + illegal: '\\n', + relevance: 0 + }, + { + className: 'number', + variants: [ + { // hex + begin: '0x[0-9a-f]+' }, + { // bare number + begin: '\\b-?\\d+' } + ], + relevance: 0 + }, + { + className: 'symbol', + variants: [ + { // GNU MIPS syntax + begin: '^\\s*[a-z_\\.\\$][a-z0-9_\\.\\$]+:' }, + { // numbered local labels + begin: '^\\s*[0-9]+:' }, + { // number local label reference (backwards, forwards) + begin: '[0-9]+[bf]' } + ], + relevance: 0 + } + ], + // forward slashes are not allowed + illegal: /\// + }; +} + +export { mipsasm as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/mipsasm.js.js b/frontend/node_modules/highlight.js/es/languages/mipsasm.js.js new file mode 100644 index 0000000..4c53ff0 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/mipsasm.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/mipsasm" instead of "highlight.js/lib/languages/mipsasm.js"' + ); + } + } + emitWarning(); + import lang from './mipsasm.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/mizar.js b/frontend/node_modules/highlight.js/es/languages/mizar.js new file mode 100644 index 0000000..ec38f49 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/mizar.js @@ -0,0 +1,27 @@ +/* +Language: Mizar +Description: The Mizar Language is a formal language derived from the mathematical vernacular. +Author: Kelley van Evert +Website: http://mizar.org/language/ +Category: scientific +*/ + +function mizar(hljs) { + return { + name: 'Mizar', + keywords: + 'environ vocabularies notations constructors definitions ' + + 'registrations theorems schemes requirements begin end definition ' + + 'registration cluster existence pred func defpred deffunc theorem ' + + 'proof let take assume then thus hence ex for st holds consider ' + + 'reconsider such that and in provided of as from be being by means ' + + 'equals implies iff redefine define now not or attr is mode ' + + 'suppose per cases set thesis contradiction scheme reserve struct ' + + 'correctness compatibility coherence symmetry assymetry ' + + 'reflexivity irreflexivity connectedness uniqueness commutativity ' + + 'idempotence involutiveness projectivity', + contains: [ hljs.COMMENT('::', '$') ] + }; +} + +export { mizar as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/mizar.js.js b/frontend/node_modules/highlight.js/es/languages/mizar.js.js new file mode 100644 index 0000000..09d02c9 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/mizar.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/mizar" instead of "highlight.js/lib/languages/mizar.js"' + ); + } + } + emitWarning(); + import lang from './mizar.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/mojolicious.js b/frontend/node_modules/highlight.js/es/languages/mojolicious.js new file mode 100644 index 0000000..57d4904 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/mojolicious.js @@ -0,0 +1,36 @@ +/* +Language: Mojolicious +Requires: xml.js, perl.js +Author: Dotan Dimet +Description: Mojolicious .ep (Embedded Perl) templates +Website: https://mojolicious.org +Category: template +*/ +function mojolicious(hljs) { + return { + name: 'Mojolicious', + subLanguage: 'xml', + contains: [ + { + className: 'meta', + begin: '^__(END|DATA)__$' + }, + // mojolicious line + { + begin: "^\\s*%{1,2}={0,2}", + end: '$', + subLanguage: 'perl' + }, + // mojolicious block + { + begin: "<%{1,2}={0,2}", + end: "={0,1}%>", + subLanguage: 'perl', + excludeBegin: true, + excludeEnd: true + } + ] + }; +} + +export { mojolicious as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/mojolicious.js.js b/frontend/node_modules/highlight.js/es/languages/mojolicious.js.js new file mode 100644 index 0000000..217bc85 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/mojolicious.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/mojolicious" instead of "highlight.js/lib/languages/mojolicious.js"' + ); + } + } + emitWarning(); + import lang from './mojolicious.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/monkey.js b/frontend/node_modules/highlight.js/es/languages/monkey.js new file mode 100644 index 0000000..3110746 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/monkey.js @@ -0,0 +1,184 @@ +/* +Language: Monkey +Description: Monkey2 is an easy to use, cross platform, games oriented programming language from Blitz Research. +Author: Arthur Bikmullin +Website: https://blitzresearch.itch.io/monkey2 +Category: gaming +*/ + +function monkey(hljs) { + const NUMBER = { + className: 'number', + relevance: 0, + variants: [ + { begin: '[$][a-fA-F0-9]+' }, + hljs.NUMBER_MODE + ] + }; + const FUNC_DEFINITION = { + variants: [ + { match: [ + /(function|method)/, + /\s+/, + hljs.UNDERSCORE_IDENT_RE, + ] }, + ], + scope: { + 1: "keyword", + 3: "title.function" + } + }; + const CLASS_DEFINITION = { + variants: [ + { match: [ + /(class|interface|extends|implements)/, + /\s+/, + hljs.UNDERSCORE_IDENT_RE, + ] }, + ], + scope: { + 1: "keyword", + 3: "title.class" + } + }; + const BUILT_INS = [ + "DebugLog", + "DebugStop", + "Error", + "Print", + "ACos", + "ACosr", + "ASin", + "ASinr", + "ATan", + "ATan2", + "ATan2r", + "ATanr", + "Abs", + "Abs", + "Ceil", + "Clamp", + "Clamp", + "Cos", + "Cosr", + "Exp", + "Floor", + "Log", + "Max", + "Max", + "Min", + "Min", + "Pow", + "Sgn", + "Sgn", + "Sin", + "Sinr", + "Sqrt", + "Tan", + "Tanr", + "Seed", + "PI", + "HALFPI", + "TWOPI" + ]; + const LITERALS = [ + "true", + "false", + "null" + ]; + const KEYWORDS = [ + "public", + "private", + "property", + "continue", + "exit", + "extern", + "new", + "try", + "catch", + "eachin", + "not", + "abstract", + "final", + "select", + "case", + "default", + "const", + "local", + "global", + "field", + "end", + "if", + "then", + "else", + "elseif", + "endif", + "while", + "wend", + "repeat", + "until", + "forever", + "for", + "to", + "step", + "next", + "return", + "module", + "inline", + "throw", + "import", + // not positive, but these are not literals + "and", + "or", + "shl", + "shr", + "mod" + ]; + + return { + name: 'Monkey', + case_insensitive: true, + keywords: { + keyword: KEYWORDS, + built_in: BUILT_INS, + literal: LITERALS + }, + illegal: /\/\*/, + contains: [ + hljs.COMMENT('#rem', '#end'), + hljs.COMMENT( + "'", + '$', + { relevance: 0 } + ), + FUNC_DEFINITION, + CLASS_DEFINITION, + { + className: 'variable.language', + begin: /\b(self|super)\b/ + }, + { + className: 'meta', + begin: /\s*#/, + end: '$', + keywords: { keyword: 'if else elseif endif end then' } + }, + { + match: [ + /^\s*/, + /strict\b/ + ], + scope: { 2: "meta" } + }, + { + beginKeywords: 'alias', + end: '=', + contains: [ hljs.UNDERSCORE_TITLE_MODE ] + }, + hljs.QUOTE_STRING_MODE, + NUMBER + ] + }; +} + +export { monkey as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/monkey.js.js b/frontend/node_modules/highlight.js/es/languages/monkey.js.js new file mode 100644 index 0000000..7d26f09 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/monkey.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/monkey" instead of "highlight.js/lib/languages/monkey.js"' + ); + } + } + emitWarning(); + import lang from './monkey.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/moonscript.js b/frontend/node_modules/highlight.js/es/languages/moonscript.js new file mode 100644 index 0000000..e411948 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/moonscript.js @@ -0,0 +1,141 @@ +/* +Language: MoonScript +Author: Billy Quith +Description: MoonScript is a programming language that transcompiles to Lua. +Origin: coffeescript.js +Website: http://moonscript.org/ +Category: scripting +*/ + +function moonscript(hljs) { + const KEYWORDS = { + keyword: + // Moonscript keywords + 'if then not for in while do return else elseif break continue switch and or ' + + 'unless when class extends super local import export from using', + literal: + 'true false nil', + built_in: + '_G _VERSION assert collectgarbage dofile error getfenv getmetatable ipairs load ' + + 'loadfile loadstring module next pairs pcall print rawequal rawget rawset require ' + + 'select setfenv setmetatable tonumber tostring type unpack xpcall coroutine debug ' + + 'io math os package string table' + }; + const JS_IDENT_RE = '[A-Za-z$_][0-9A-Za-z$_]*'; + const SUBST = { + className: 'subst', + begin: /#\{/, + end: /\}/, + keywords: KEYWORDS + }; + const EXPRESSIONS = [ + hljs.inherit(hljs.C_NUMBER_MODE, + { starts: { + end: '(\\s*/)?', + relevance: 0 + } }), // a number tries to eat the following slash to prevent treating it as a regexp + { + className: 'string', + variants: [ + { + begin: /'/, + end: /'/, + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: /"/, + end: /"/, + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST + ] + } + ] + }, + { + className: 'built_in', + begin: '@__' + hljs.IDENT_RE + }, + { begin: '@' + hljs.IDENT_RE // relevance booster on par with CoffeeScript + }, + { begin: hljs.IDENT_RE + '\\\\' + hljs.IDENT_RE // inst\method + } + ]; + SUBST.contains = EXPRESSIONS; + + const TITLE = hljs.inherit(hljs.TITLE_MODE, { begin: JS_IDENT_RE }); + const POSSIBLE_PARAMS_RE = '(\\(.*\\)\\s*)?\\B[-=]>'; + const PARAMS = { + className: 'params', + begin: '\\([^\\(]', + returnBegin: true, + /* We need another contained nameless mode to not have every nested + pair of parens to be called "params" */ + contains: [ + { + begin: /\(/, + end: /\)/, + keywords: KEYWORDS, + contains: [ 'self' ].concat(EXPRESSIONS) + } + ] + }; + + return { + name: 'MoonScript', + aliases: [ 'moon' ], + keywords: KEYWORDS, + illegal: /\/\*/, + contains: EXPRESSIONS.concat([ + hljs.COMMENT('--', '$'), + { + className: 'function', // function: -> => + begin: '^\\s*' + JS_IDENT_RE + '\\s*=\\s*' + POSSIBLE_PARAMS_RE, + end: '[-=]>', + returnBegin: true, + contains: [ + TITLE, + PARAMS + ] + }, + { + begin: /[\(,:=]\s*/, // anonymous function start + relevance: 0, + contains: [ + { + className: 'function', + begin: POSSIBLE_PARAMS_RE, + end: '[-=]>', + returnBegin: true, + contains: [ PARAMS ] + } + ] + }, + { + className: 'class', + beginKeywords: 'class', + end: '$', + illegal: /[:="\[\]]/, + contains: [ + { + beginKeywords: 'extends', + endsWithParent: true, + illegal: /[:="\[\]]/, + contains: [ TITLE ] + }, + TITLE + ] + }, + { + className: 'name', // table + begin: JS_IDENT_RE + ':', + end: ':', + returnBegin: true, + returnEnd: true, + relevance: 0 + } + ]) + }; +} + +export { moonscript as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/moonscript.js.js b/frontend/node_modules/highlight.js/es/languages/moonscript.js.js new file mode 100644 index 0000000..c2302fd --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/moonscript.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/moonscript" instead of "highlight.js/lib/languages/moonscript.js"' + ); + } + } + emitWarning(); + import lang from './moonscript.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/n1ql.js b/frontend/node_modules/highlight.js/es/languages/n1ql.js new file mode 100644 index 0000000..f66781f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/n1ql.js @@ -0,0 +1,365 @@ +/* + Language: N1QL + Author: Andres Täht + Contributors: Rene Saarsoo + Description: Couchbase query language + Website: https://www.couchbase.com/products/n1ql + Category: database + */ + +function n1ql(hljs) { + // Taken from http://developer.couchbase.com/documentation/server/current/n1ql/n1ql-language-reference/reservedwords.html + const KEYWORDS = [ + "all", + "alter", + "analyze", + "and", + "any", + "array", + "as", + "asc", + "begin", + "between", + "binary", + "boolean", + "break", + "bucket", + "build", + "by", + "call", + "case", + "cast", + "cluster", + "collate", + "collection", + "commit", + "connect", + "continue", + "correlate", + "cover", + "create", + "database", + "dataset", + "datastore", + "declare", + "decrement", + "delete", + "derived", + "desc", + "describe", + "distinct", + "do", + "drop", + "each", + "element", + "else", + "end", + "every", + "except", + "exclude", + "execute", + "exists", + "explain", + "fetch", + "first", + "flatten", + "for", + "force", + "from", + "function", + "grant", + "group", + "gsi", + "having", + "if", + "ignore", + "ilike", + "in", + "include", + "increment", + "index", + "infer", + "inline", + "inner", + "insert", + "intersect", + "into", + "is", + "join", + "key", + "keys", + "keyspace", + "known", + "last", + "left", + "let", + "letting", + "like", + "limit", + "lsm", + "map", + "mapping", + "matched", + "materialized", + "merge", + "minus", + "namespace", + "nest", + "not", + "number", + "object", + "offset", + "on", + "option", + "or", + "order", + "outer", + "over", + "parse", + "partition", + "password", + "path", + "pool", + "prepare", + "primary", + "private", + "privilege", + "procedure", + "public", + "raw", + "realm", + "reduce", + "rename", + "return", + "returning", + "revoke", + "right", + "role", + "rollback", + "satisfies", + "schema", + "select", + "self", + "semi", + "set", + "show", + "some", + "start", + "statistics", + "string", + "system", + "then", + "to", + "transaction", + "trigger", + "truncate", + "under", + "union", + "unique", + "unknown", + "unnest", + "unset", + "update", + "upsert", + "use", + "user", + "using", + "validate", + "value", + "valued", + "values", + "via", + "view", + "when", + "where", + "while", + "with", + "within", + "work", + "xor" + ]; + // Taken from http://developer.couchbase.com/documentation/server/4.5/n1ql/n1ql-language-reference/literals.html + const LITERALS = [ + "true", + "false", + "null", + "missing|5" + ]; + // Taken from http://developer.couchbase.com/documentation/server/4.5/n1ql/n1ql-language-reference/functions.html + const BUILT_INS = [ + "array_agg", + "array_append", + "array_concat", + "array_contains", + "array_count", + "array_distinct", + "array_ifnull", + "array_length", + "array_max", + "array_min", + "array_position", + "array_prepend", + "array_put", + "array_range", + "array_remove", + "array_repeat", + "array_replace", + "array_reverse", + "array_sort", + "array_sum", + "avg", + "count", + "max", + "min", + "sum", + "greatest", + "least", + "ifmissing", + "ifmissingornull", + "ifnull", + "missingif", + "nullif", + "ifinf", + "ifnan", + "ifnanorinf", + "naninf", + "neginfif", + "posinfif", + "clock_millis", + "clock_str", + "date_add_millis", + "date_add_str", + "date_diff_millis", + "date_diff_str", + "date_part_millis", + "date_part_str", + "date_trunc_millis", + "date_trunc_str", + "duration_to_str", + "millis", + "str_to_millis", + "millis_to_str", + "millis_to_utc", + "millis_to_zone_name", + "now_millis", + "now_str", + "str_to_duration", + "str_to_utc", + "str_to_zone_name", + "decode_json", + "encode_json", + "encoded_size", + "poly_length", + "base64", + "base64_encode", + "base64_decode", + "meta", + "uuid", + "abs", + "acos", + "asin", + "atan", + "atan2", + "ceil", + "cos", + "degrees", + "e", + "exp", + "ln", + "log", + "floor", + "pi", + "power", + "radians", + "random", + "round", + "sign", + "sin", + "sqrt", + "tan", + "trunc", + "object_length", + "object_names", + "object_pairs", + "object_inner_pairs", + "object_values", + "object_inner_values", + "object_add", + "object_put", + "object_remove", + "object_unwrap", + "regexp_contains", + "regexp_like", + "regexp_position", + "regexp_replace", + "contains", + "initcap", + "length", + "lower", + "ltrim", + "position", + "repeat", + "replace", + "rtrim", + "split", + "substr", + "title", + "trim", + "upper", + "isarray", + "isatom", + "isboolean", + "isnumber", + "isobject", + "isstring", + "type", + "toarray", + "toatom", + "toboolean", + "tonumber", + "toobject", + "tostring" + ]; + + return { + name: 'N1QL', + case_insensitive: true, + contains: [ + { + beginKeywords: + 'build create index delete drop explain infer|10 insert merge prepare select update upsert|10', + end: /;/, + keywords: { + keyword: KEYWORDS, + literal: LITERALS, + built_in: BUILT_INS + }, + contains: [ + { + className: 'string', + begin: '\'', + end: '\'', + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + className: 'string', + begin: '"', + end: '"', + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + className: 'symbol', + begin: '`', + end: '`', + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + hljs.C_NUMBER_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + hljs.C_BLOCK_COMMENT_MODE + ] + }; +} + +export { n1ql as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/n1ql.js.js b/frontend/node_modules/highlight.js/es/languages/n1ql.js.js new file mode 100644 index 0000000..0a42c8e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/n1ql.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/n1ql" instead of "highlight.js/lib/languages/n1ql.js"' + ); + } + } + emitWarning(); + import lang from './n1ql.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/nestedtext.js b/frontend/node_modules/highlight.js/es/languages/nestedtext.js new file mode 100644 index 0000000..579268b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/nestedtext.js @@ -0,0 +1,83 @@ +/* +Language: NestedText +Description: NestedText is a file format for holding data that is to be entered, edited, or viewed by people. +Website: https://nestedtext.org/ +Category: config +*/ + +/** @type LanguageFn */ +function nestedtext(hljs) { + const NESTED = { + match: [ + /^\s*(?=\S)/, // have to look forward here to avoid polynomial backtracking + /[^:]+/, + /:\s*/, + /$/ + ], + className: { + 2: "attribute", + 3: "punctuation" + } + }; + const DICTIONARY_ITEM = { + match: [ + /^\s*(?=\S)/, // have to look forward here to avoid polynomial backtracking + /[^:]*[^: ]/, + /[ ]*:/, + /[ ]/, + /.*$/ + ], + className: { + 2: "attribute", + 3: "punctuation", + 5: "string" + } + }; + const STRING = { + match: [ + /^\s*/, + />/, + /[ ]/, + /.*$/ + ], + className: { + 2: "punctuation", + 4: "string" + } + }; + const LIST_ITEM = { + variants: [ + { match: [ + /^\s*/, + /-/, + /[ ]/, + /.*$/ + ] }, + { match: [ + /^\s*/, + /-$/ + ] } + ], + className: { + 2: "bullet", + 4: "string" + } + }; + + return { + name: 'Nested Text', + aliases: [ 'nt' ], + contains: [ + hljs.inherit(hljs.HASH_COMMENT_MODE, { + begin: /^\s*(?=#)/, + excludeBegin: true + }), + LIST_ITEM, + STRING, + NESTED, + DICTIONARY_ITEM + ] + }; +} + +export { nestedtext as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/nestedtext.js.js b/frontend/node_modules/highlight.js/es/languages/nestedtext.js.js new file mode 100644 index 0000000..054f33e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/nestedtext.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/nestedtext" instead of "highlight.js/lib/languages/nestedtext.js"' + ); + } + } + emitWarning(); + import lang from './nestedtext.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/nginx.js b/frontend/node_modules/highlight.js/es/languages/nginx.js new file mode 100644 index 0000000..a244ae1 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/nginx.js @@ -0,0 +1,153 @@ +/* +Language: Nginx config +Author: Peter Leonov +Contributors: Ivan Sagalaev +Category: config, web +Website: https://www.nginx.com +*/ + +/** @type LanguageFn */ +function nginx(hljs) { + const regex = hljs.regex; + const VAR = { + className: 'variable', + variants: [ + { begin: /\$\d+/ }, + { begin: /\$\{\w+\}/ }, + { begin: regex.concat(/[$@]/, hljs.UNDERSCORE_IDENT_RE) } + ] + }; + const LITERALS = [ + "on", + "off", + "yes", + "no", + "true", + "false", + "none", + "blocked", + "debug", + "info", + "notice", + "warn", + "error", + "crit", + "select", + "break", + "last", + "permanent", + "redirect", + "kqueue", + "rtsig", + "epoll", + "poll", + "/dev/poll" + ]; + const DEFAULT = { + endsWithParent: true, + keywords: { + $pattern: /[a-z_]{2,}|\/dev\/poll/, + literal: LITERALS + }, + relevance: 0, + illegal: '=>', + contains: [ + hljs.HASH_COMMENT_MODE, + { + className: 'string', + contains: [ + hljs.BACKSLASH_ESCAPE, + VAR + ], + variants: [ + { + begin: /"/, + end: /"/ + }, + { + begin: /'/, + end: /'/ + } + ] + }, + // this swallows entire URLs to avoid detecting numbers within + { + begin: '([a-z]+):/', + end: '\\s', + endsWithParent: true, + excludeEnd: true, + contains: [ VAR ] + }, + { + className: 'regexp', + contains: [ + hljs.BACKSLASH_ESCAPE, + VAR + ], + variants: [ + { + begin: "\\s\\^", + end: "\\s|\\{|;", + returnEnd: true + }, + // regexp locations (~, ~*) + { + begin: "~\\*?\\s+", + end: "\\s|\\{|;", + returnEnd: true + }, + // *.example.com + { begin: "\\*(\\.[a-z\\-]+)+" }, + // sub.example.* + { begin: "([a-z\\-]+\\.)+\\*" } + ] + }, + // IP + { + className: 'number', + begin: '\\b\\d{1,3}\\.\\d{1,3}\\.\\d{1,3}\\.\\d{1,3}(:\\d{1,5})?\\b' + }, + // units + { + className: 'number', + begin: '\\b\\d+[kKmMgGdshdwy]?\\b', + relevance: 0 + }, + VAR + ] + }; + + return { + name: 'Nginx config', + aliases: [ 'nginxconf' ], + contains: [ + hljs.HASH_COMMENT_MODE, + { + beginKeywords: "upstream location", + end: /;|\{/, + contains: DEFAULT.contains, + keywords: { section: "upstream location" } + }, + { + className: 'section', + begin: regex.concat(hljs.UNDERSCORE_IDENT_RE + regex.lookahead(/\s+\{/)), + relevance: 0 + }, + { + begin: regex.lookahead(hljs.UNDERSCORE_IDENT_RE + '\\s'), + end: ';|\\{', + contains: [ + { + className: 'attribute', + begin: hljs.UNDERSCORE_IDENT_RE, + starts: DEFAULT + } + ], + relevance: 0 + } + ], + illegal: '[^\\s\\}\\{]' + }; +} + +export { nginx as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/nginx.js.js b/frontend/node_modules/highlight.js/es/languages/nginx.js.js new file mode 100644 index 0000000..bf620b6 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/nginx.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/nginx" instead of "highlight.js/lib/languages/nginx.js"' + ); + } + } + emitWarning(); + import lang from './nginx.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/nim.js b/frontend/node_modules/highlight.js/es/languages/nim.js new file mode 100644 index 0000000..00b463f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/nim.js @@ -0,0 +1,187 @@ +/* +Language: Nim +Description: Nim is a statically typed compiled systems programming language. +Website: https://nim-lang.org +Category: system +*/ + +function nim(hljs) { + const TYPES = [ + "int", + "int8", + "int16", + "int32", + "int64", + "uint", + "uint8", + "uint16", + "uint32", + "uint64", + "float", + "float32", + "float64", + "bool", + "char", + "string", + "cstring", + "pointer", + "expr", + "stmt", + "void", + "auto", + "any", + "range", + "array", + "openarray", + "varargs", + "seq", + "set", + "clong", + "culong", + "cchar", + "cschar", + "cshort", + "cint", + "csize", + "clonglong", + "cfloat", + "cdouble", + "clongdouble", + "cuchar", + "cushort", + "cuint", + "culonglong", + "cstringarray", + "semistatic" + ]; + const KEYWORDS = [ + "addr", + "and", + "as", + "asm", + "bind", + "block", + "break", + "case", + "cast", + "concept", + "const", + "continue", + "converter", + "defer", + "discard", + "distinct", + "div", + "do", + "elif", + "else", + "end", + "enum", + "except", + "export", + "finally", + "for", + "from", + "func", + "generic", + "guarded", + "if", + "import", + "in", + "include", + "interface", + "is", + "isnot", + "iterator", + "let", + "macro", + "method", + "mixin", + "mod", + "nil", + "not", + "notin", + "object", + "of", + "or", + "out", + "proc", + "ptr", + "raise", + "ref", + "return", + "shared", + "shl", + "shr", + "static", + "template", + "try", + "tuple", + "type", + "using", + "var", + "when", + "while", + "with", + "without", + "xor", + "yield" + ]; + const BUILT_INS = [ + "stdin", + "stdout", + "stderr", + "result" + ]; + const LITERALS = [ + "true", + "false" + ]; + return { + name: 'Nim', + keywords: { + keyword: KEYWORDS, + literal: LITERALS, + type: TYPES, + built_in: BUILT_INS + }, + contains: [ + { + className: 'meta', // Actually pragma + begin: /\{\./, + end: /\.\}/, + relevance: 10 + }, + { + className: 'string', + begin: /[a-zA-Z]\w*"/, + end: /"/, + contains: [ { begin: /""/ } ] + }, + { + className: 'string', + begin: /([a-zA-Z]\w*)?"""/, + end: /"""/ + }, + hljs.QUOTE_STRING_MODE, + { + className: 'type', + begin: /\b[A-Z]\w+\b/, + relevance: 0 + }, + { + className: 'number', + relevance: 0, + variants: [ + { begin: /\b(0[xX][0-9a-fA-F][_0-9a-fA-F]*)('?[iIuU](8|16|32|64))?/ }, + { begin: /\b(0o[0-7][_0-7]*)('?[iIuUfF](8|16|32|64))?/ }, + { begin: /\b(0(b|B)[01][_01]*)('?[iIuUfF](8|16|32|64))?/ }, + { begin: /\b(\d[_\d]*)('?[iIuUfF](8|16|32|64))?/ } + ] + }, + hljs.HASH_COMMENT_MODE + ] + }; +} + +export { nim as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/nim.js.js b/frontend/node_modules/highlight.js/es/languages/nim.js.js new file mode 100644 index 0000000..f6832bb --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/nim.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/nim" instead of "highlight.js/lib/languages/nim.js"' + ); + } + } + emitWarning(); + import lang from './nim.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/nix.js b/frontend/node_modules/highlight.js/es/languages/nix.js new file mode 100644 index 0000000..053ec92 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/nix.js @@ -0,0 +1,372 @@ +/* +Language: Nix +Author: Domen Kožar +Description: Nix functional language +Website: http://nixos.org/nix +Category: system +*/ + +/** @type LanguageFn */ +function nix(hljs) { + const regex = hljs.regex; + const KEYWORDS = { + keyword: [ + "assert", + "else", + "if", + "in", + "inherit", + "let", + "or", + "rec", + "then", + "with", + ], + literal: [ + "true", + "false", + "null", + ], + built_in: [ + // toplevel builtins + "abort", + "baseNameOf", + "builtins", + "derivation", + "derivationStrict", + "dirOf", + "fetchGit", + "fetchMercurial", + "fetchTarball", + "fetchTree", + "fromTOML", + "import", + "isNull", + "map", + "placeholder", + "removeAttrs", + "scopedImport", + "throw", + "toString", + ], + }; + + const BUILTINS = { + scope: 'built_in', + match: regex.either(...[ + "abort", + "add", + "addDrvOutputDependencies", + "addErrorContext", + "all", + "any", + "appendContext", + "attrNames", + "attrValues", + "baseNameOf", + "bitAnd", + "bitOr", + "bitXor", + "break", + "builtins", + "catAttrs", + "ceil", + "compareVersions", + "concatLists", + "concatMap", + "concatStringsSep", + "convertHash", + "currentSystem", + "currentTime", + "deepSeq", + "derivation", + "derivationStrict", + "dirOf", + "div", + "elem", + "elemAt", + "false", + "fetchGit", + "fetchMercurial", + "fetchTarball", + "fetchTree", + "fetchurl", + "filter", + "filterSource", + "findFile", + "flakeRefToString", + "floor", + "foldl'", + "fromJSON", + "fromTOML", + "functionArgs", + "genList", + "genericClosure", + "getAttr", + "getContext", + "getEnv", + "getFlake", + "groupBy", + "hasAttr", + "hasContext", + "hashFile", + "hashString", + "head", + "import", + "intersectAttrs", + "isAttrs", + "isBool", + "isFloat", + "isFunction", + "isInt", + "isList", + "isNull", + "isPath", + "isString", + "langVersion", + "length", + "lessThan", + "listToAttrs", + "map", + "mapAttrs", + "match", + "mul", + "nixPath", + "nixVersion", + "null", + "parseDrvName", + "parseFlakeRef", + "partition", + "path", + "pathExists", + "placeholder", + "readDir", + "readFile", + "readFileType", + "removeAttrs", + "replaceStrings", + "scopedImport", + "seq", + "sort", + "split", + "splitVersion", + "storeDir", + "storePath", + "stringLength", + "sub", + "substring", + "tail", + "throw", + "toFile", + "toJSON", + "toPath", + "toString", + "toXML", + "trace", + "traceVerbose", + "true", + "tryEval", + "typeOf", + "unsafeDiscardOutputDependency", + "unsafeDiscardStringContext", + "unsafeGetAttrPos", + "warn", + "zipAttrsWith", + ].map(b => `builtins\\.${b}`)), + relevance: 10, + }; + + const IDENTIFIER_REGEX = '[A-Za-z_][A-Za-z0-9_\'-]*'; + + const LOOKUP_PATH = { + scope: 'symbol', + match: new RegExp(`<${IDENTIFIER_REGEX}(/${IDENTIFIER_REGEX})*>`), + }; + + const PATH_PIECE = "[A-Za-z0-9_\\+\\.-]+"; + const PATH = { + scope: 'symbol', + match: new RegExp(`(\\.\\.|\\.|~)?/(${PATH_PIECE})?(/${PATH_PIECE})*(?=[\\s;])`), + }; + + const OPERATOR_WITHOUT_MINUS_REGEX = regex.either(...[ + '==', + '=', + '\\+\\+', + '\\+', + '<=', + '<\\|', + '<', + '>=', + '>', + '->', + '//', + '/', + '!=', + '!', + '\\|\\|', + '\\|>', + '\\?', + '\\*', + '&&', + ]); + + const OPERATOR = { + scope: 'operator', + match: regex.concat(OPERATOR_WITHOUT_MINUS_REGEX, /(?!-)/), + relevance: 0, + }; + + // '-' is being handled by itself to ensure we are able to tell the difference + // between a dash in an identifier and a minus operator + const NUMBER = { + scope: 'number', + match: new RegExp(`${hljs.NUMBER_RE}(?!-)`), + relevance: 0, + }; + const MINUS_OPERATOR = { + variants: [ + { + scope: 'operator', + beforeMatch: /\s/, + // The (?!>) is used to ensure this doesn't collide with the '->' operator + begin: /-(?!>)/, + }, + { + begin: [ + new RegExp(`${hljs.NUMBER_RE}`), + /-/, + /(?!>)/, + ], + beginScope: { + 1: 'number', + 2: 'operator' + }, + }, + { + begin: [ + OPERATOR_WITHOUT_MINUS_REGEX, + /-/, + /(?!>)/, + ], + beginScope: { + 1: 'operator', + 2: 'operator' + }, + }, + ], + relevance: 0, + }; + + const ATTRS = { + beforeMatch: /(^|\{|;)\s*/, + begin: new RegExp(`${IDENTIFIER_REGEX}(\\.${IDENTIFIER_REGEX})*\\s*=(?!=)`), + returnBegin: true, + relevance: 0, + contains: [ + { + scope: 'attr', + match: new RegExp(`${IDENTIFIER_REGEX}(\\.${IDENTIFIER_REGEX})*(?=\\s*=)`), + relevance: 0.2, + } + ], + }; + + const NORMAL_ESCAPED_DOLLAR = { + scope: 'char.escape', + match: /\\\$/, + }; + const INDENTED_ESCAPED_DOLLAR = { + scope: 'char.escape', + match: /''\$/, + }; + const ANTIQUOTE = { + scope: 'subst', + begin: /\$\{/, + end: /\}/, + keywords: KEYWORDS, + }; + const ESCAPED_DOUBLEQUOTE = { + scope: 'char.escape', + match: /'''/, + }; + const ESCAPED_LITERAL = { + scope: 'char.escape', + match: /\\(?!\$)./, + }; + const STRING = { + scope: 'string', + variants: [ + { + begin: "''", + end: "''", + contains: [ + INDENTED_ESCAPED_DOLLAR, + ANTIQUOTE, + ESCAPED_DOUBLEQUOTE, + ESCAPED_LITERAL, + ], + }, + { + begin: '"', + end: '"', + contains: [ + NORMAL_ESCAPED_DOLLAR, + ANTIQUOTE, + ESCAPED_LITERAL, + ], + }, + ], + }; + + const FUNCTION_PARAMS = { + scope: 'params', + match: new RegExp(`${IDENTIFIER_REGEX}\\s*:(?=\\s)`), + }; + + const EXPRESSIONS = [ + NUMBER, + hljs.HASH_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.COMMENT( + /\/\*\*(?!\/)/, + /\*\//, + { + subLanguage: 'markdown', + relevance: 0 + } + ), + BUILTINS, + STRING, + LOOKUP_PATH, + PATH, + FUNCTION_PARAMS, + ATTRS, + MINUS_OPERATOR, + OPERATOR, + ]; + + ANTIQUOTE.contains = EXPRESSIONS; + + const REPL = [ + { + scope: 'meta.prompt', + match: /^nix-repl>(?=\s)/, + relevance: 10, + }, + { + scope: 'meta', + beforeMatch: /\s+/, + begin: /:([a-z]+|\?)/, + }, + ]; + + return { + name: 'Nix', + aliases: [ "nixos" ], + keywords: KEYWORDS, + contains: EXPRESSIONS.concat(REPL), + }; +} + +export { nix as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/nix.js.js b/frontend/node_modules/highlight.js/es/languages/nix.js.js new file mode 100644 index 0000000..4009121 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/nix.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/nix" instead of "highlight.js/lib/languages/nix.js"' + ); + } + } + emitWarning(); + import lang from './nix.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/node-repl.js b/frontend/node_modules/highlight.js/es/languages/node-repl.js new file mode 100644 index 0000000..37cf0ec --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/node-repl.js @@ -0,0 +1,33 @@ +/* +Language: Node REPL +Requires: javascript.js +Author: Marat Nagayev +Category: scripting +*/ + +/** @type LanguageFn */ +function nodeRepl(hljs) { + return { + name: 'Node REPL', + contains: [ + { + className: 'meta.prompt', + starts: { + // a space separates the REPL prefix from the actual code + // this is purely for cleaner HTML output + end: / |$/, + starts: { + end: '$', + subLanguage: 'javascript' + } + }, + variants: [ + { begin: /^>(?=[ ]|$)/ }, + { begin: /^\.\.\.(?=[ ]|$)/ } + ] + } + ] + }; +} + +export { nodeRepl as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/node-repl.js.js b/frontend/node_modules/highlight.js/es/languages/node-repl.js.js new file mode 100644 index 0000000..9f57edb --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/node-repl.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/node-repl" instead of "highlight.js/lib/languages/node-repl.js"' + ); + } + } + emitWarning(); + import lang from './node-repl.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/nsis.js b/frontend/node_modules/highlight.js/es/languages/nsis.js new file mode 100644 index 0000000..caa8b94 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/nsis.js @@ -0,0 +1,557 @@ +/* +Language: NSIS +Description: Nullsoft Scriptable Install System +Author: Jan T. Sott +Website: https://nsis.sourceforge.io/Main_Page +Category: scripting +*/ + + +function nsis(hljs) { + const regex = hljs.regex; + const LANGUAGE_CONSTANTS = [ + "ADMINTOOLS", + "APPDATA", + "CDBURN_AREA", + "CMDLINE", + "COMMONFILES32", + "COMMONFILES64", + "COMMONFILES", + "COOKIES", + "DESKTOP", + "DOCUMENTS", + "EXEDIR", + "EXEFILE", + "EXEPATH", + "FAVORITES", + "FONTS", + "HISTORY", + "HWNDPARENT", + "INSTDIR", + "INTERNET_CACHE", + "LANGUAGE", + "LOCALAPPDATA", + "MUSIC", + "NETHOOD", + "OUTDIR", + "PICTURES", + "PLUGINSDIR", + "PRINTHOOD", + "PROFILE", + "PROGRAMFILES32", + "PROGRAMFILES64", + "PROGRAMFILES", + "QUICKLAUNCH", + "RECENT", + "RESOURCES_LOCALIZED", + "RESOURCES", + "SENDTO", + "SMPROGRAMS", + "SMSTARTUP", + "STARTMENU", + "SYSDIR", + "TEMP", + "TEMPLATES", + "VIDEOS", + "WINDIR" + ]; + + const PARAM_NAMES = [ + "ARCHIVE", + "FILE_ATTRIBUTE_ARCHIVE", + "FILE_ATTRIBUTE_NORMAL", + "FILE_ATTRIBUTE_OFFLINE", + "FILE_ATTRIBUTE_READONLY", + "FILE_ATTRIBUTE_SYSTEM", + "FILE_ATTRIBUTE_TEMPORARY", + "HKCR", + "HKCU", + "HKDD", + "HKEY_CLASSES_ROOT", + "HKEY_CURRENT_CONFIG", + "HKEY_CURRENT_USER", + "HKEY_DYN_DATA", + "HKEY_LOCAL_MACHINE", + "HKEY_PERFORMANCE_DATA", + "HKEY_USERS", + "HKLM", + "HKPD", + "HKU", + "IDABORT", + "IDCANCEL", + "IDIGNORE", + "IDNO", + "IDOK", + "IDRETRY", + "IDYES", + "MB_ABORTRETRYIGNORE", + "MB_DEFBUTTON1", + "MB_DEFBUTTON2", + "MB_DEFBUTTON3", + "MB_DEFBUTTON4", + "MB_ICONEXCLAMATION", + "MB_ICONINFORMATION", + "MB_ICONQUESTION", + "MB_ICONSTOP", + "MB_OK", + "MB_OKCANCEL", + "MB_RETRYCANCEL", + "MB_RIGHT", + "MB_RTLREADING", + "MB_SETFOREGROUND", + "MB_TOPMOST", + "MB_USERICON", + "MB_YESNO", + "NORMAL", + "OFFLINE", + "READONLY", + "SHCTX", + "SHELL_CONTEXT", + "SYSTEM|TEMPORARY", + ]; + + const COMPILER_FLAGS = [ + "addincludedir", + "addplugindir", + "appendfile", + "assert", + "cd", + "define", + "delfile", + "echo", + "else", + "endif", + "error", + "execute", + "finalize", + "getdllversion", + "gettlbversion", + "if", + "ifdef", + "ifmacrodef", + "ifmacrondef", + "ifndef", + "include", + "insertmacro", + "macro", + "macroend", + "makensis", + "packhdr", + "searchparse", + "searchreplace", + "system", + "tempfile", + "undef", + "uninstfinalize", + "verbose", + "warning", + ]; + + const CONSTANTS = { + className: 'variable.constant', + begin: regex.concat(/\$/, regex.either(...LANGUAGE_CONSTANTS)) + }; + + const DEFINES = { + // ${defines} + className: 'variable', + begin: /\$+\{[\!\w.:-]+\}/ + }; + + const VARIABLES = { + // $variables + className: 'variable', + begin: /\$+\w[\w\.]*/, + illegal: /\(\)\{\}/ + }; + + const LANGUAGES = { + // $(language_strings) + className: 'variable', + begin: /\$+\([\w^.:!-]+\)/ + }; + + const PARAMETERS = { + // command parameters + className: 'params', + begin: regex.either(...PARAM_NAMES) + }; + + const COMPILER = { + // !compiler_flags + className: 'keyword', + begin: regex.concat( + /!/, + regex.either(...COMPILER_FLAGS) + ) + }; + + const ESCAPE_CHARS = { + // $\n, $\r, $\t, $$ + className: 'char.escape', + begin: /\$(\\[nrt]|\$)/ + }; + + const PLUGINS = { + // plug::ins + className: 'title.function', + begin: /\w+::\w+/ + }; + + const STRING = { + className: 'string', + variants: [ + { + begin: '"', + end: '"' + }, + { + begin: '\'', + end: '\'' + }, + { + begin: '`', + end: '`' + } + ], + illegal: /\n/, + contains: [ + ESCAPE_CHARS, + CONSTANTS, + DEFINES, + VARIABLES, + LANGUAGES + ] + }; + + const KEYWORDS = [ + "Abort", + "AddBrandingImage", + "AddSize", + "AllowRootDirInstall", + "AllowSkipFiles", + "AutoCloseWindow", + "BGFont", + "BGGradient", + "BrandingText", + "BringToFront", + "Call", + "CallInstDLL", + "Caption", + "ChangeUI", + "CheckBitmap", + "ClearErrors", + "CompletedText", + "ComponentText", + "CopyFiles", + "CRCCheck", + "CreateDirectory", + "CreateFont", + "CreateShortCut", + "Delete", + "DeleteINISec", + "DeleteINIStr", + "DeleteRegKey", + "DeleteRegValue", + "DetailPrint", + "DetailsButtonText", + "DirText", + "DirVar", + "DirVerify", + "EnableWindow", + "EnumRegKey", + "EnumRegValue", + "Exch", + "Exec", + "ExecShell", + "ExecShellWait", + "ExecWait", + "ExpandEnvStrings", + "File", + "FileBufSize", + "FileClose", + "FileErrorText", + "FileOpen", + "FileRead", + "FileReadByte", + "FileReadUTF16LE", + "FileReadWord", + "FileWriteUTF16LE", + "FileSeek", + "FileWrite", + "FileWriteByte", + "FileWriteWord", + "FindClose", + "FindFirst", + "FindNext", + "FindWindow", + "FlushINI", + "GetCurInstType", + "GetCurrentAddress", + "GetDlgItem", + "GetDLLVersion", + "GetDLLVersionLocal", + "GetErrorLevel", + "GetFileTime", + "GetFileTimeLocal", + "GetFullPathName", + "GetFunctionAddress", + "GetInstDirError", + "GetKnownFolderPath", + "GetLabelAddress", + "GetTempFileName", + "GetWinVer", + "Goto", + "HideWindow", + "Icon", + "IfAbort", + "IfErrors", + "IfFileExists", + "IfRebootFlag", + "IfRtlLanguage", + "IfShellVarContextAll", + "IfSilent", + "InitPluginsDir", + "InstallButtonText", + "InstallColors", + "InstallDir", + "InstallDirRegKey", + "InstProgressFlags", + "InstType", + "InstTypeGetText", + "InstTypeSetText", + "Int64Cmp", + "Int64CmpU", + "Int64Fmt", + "IntCmp", + "IntCmpU", + "IntFmt", + "IntOp", + "IntPtrCmp", + "IntPtrCmpU", + "IntPtrOp", + "IsWindow", + "LangString", + "LicenseBkColor", + "LicenseData", + "LicenseForceSelection", + "LicenseLangString", + "LicenseText", + "LoadAndSetImage", + "LoadLanguageFile", + "LockWindow", + "LogSet", + "LogText", + "ManifestDPIAware", + "ManifestLongPathAware", + "ManifestMaxVersionTested", + "ManifestSupportedOS", + "MessageBox", + "MiscButtonText", + "Name|0", + "Nop", + "OutFile", + "Page", + "PageCallbacks", + "PEAddResource", + "PEDllCharacteristics", + "PERemoveResource", + "PESubsysVer", + "Pop", + "Push", + "Quit", + "ReadEnvStr", + "ReadINIStr", + "ReadRegDWORD", + "ReadRegStr", + "Reboot", + "RegDLL", + "Rename", + "RequestExecutionLevel", + "ReserveFile", + "Return", + "RMDir", + "SearchPath", + "SectionGetFlags", + "SectionGetInstTypes", + "SectionGetSize", + "SectionGetText", + "SectionIn", + "SectionSetFlags", + "SectionSetInstTypes", + "SectionSetSize", + "SectionSetText", + "SendMessage", + "SetAutoClose", + "SetBrandingImage", + "SetCompress", + "SetCompressor", + "SetCompressorDictSize", + "SetCtlColors", + "SetCurInstType", + "SetDatablockOptimize", + "SetDateSave", + "SetDetailsPrint", + "SetDetailsView", + "SetErrorLevel", + "SetErrors", + "SetFileAttributes", + "SetFont", + "SetOutPath", + "SetOverwrite", + "SetRebootFlag", + "SetRegView", + "SetShellVarContext", + "SetSilent", + "ShowInstDetails", + "ShowUninstDetails", + "ShowWindow", + "SilentInstall", + "SilentUnInstall", + "Sleep", + "SpaceTexts", + "StrCmp", + "StrCmpS", + "StrCpy", + "StrLen", + "SubCaption", + "Unicode", + "UninstallButtonText", + "UninstallCaption", + "UninstallIcon", + "UninstallSubCaption", + "UninstallText", + "UninstPage", + "UnRegDLL", + "Var", + "VIAddVersionKey", + "VIFileVersion", + "VIProductVersion", + "WindowIcon", + "WriteINIStr", + "WriteRegBin", + "WriteRegDWORD", + "WriteRegExpandStr", + "WriteRegMultiStr", + "WriteRegNone", + "WriteRegStr", + "WriteUninstaller", + "XPStyle" + ]; + + const LITERALS = [ + "admin", + "all", + "auto", + "both", + "bottom", + "bzip2", + "colored", + "components", + "current", + "custom", + "directory", + "false", + "force", + "hide", + "highest", + "ifdiff", + "ifnewer", + "instfiles", + "lastused", + "leave", + "left", + "license", + "listonly", + "lzma", + "nevershow", + "none", + "normal", + "notset", + "off", + "on", + "open", + "print", + "right", + "show", + "silent", + "silentlog", + "smooth", + "textonly", + "top", + "true", + "try", + "un.components", + "un.custom", + "un.directory", + "un.instfiles", + "un.license", + "uninstConfirm", + "user", + "Win10", + "Win7", + "Win8", + "WinVista", + "zlib" + ]; + + const FUNCTION_DEFINITION = { + match: [ + /Function/, + /\s+/, + regex.concat(/(\.)?/, hljs.IDENT_RE) + ], + scope: { + 1: "keyword", + 3: "title.function" + } + }; + + // Var Custom.Variable.Name.Item + // Var /GLOBAL Custom.Variable.Name.Item + const VARIABLE_NAME_RE = /[A-Za-z][\w.]*/; + const VARIABLE_DEFINITION = { + match: [ + /Var/, + /\s+/, + /(?:\/GLOBAL\s+)?/, + VARIABLE_NAME_RE + ], + scope: { + 1: "keyword", + 3: "params", + 4: "variable" + } + }; + + return { + name: 'NSIS', + case_insensitive: true, + keywords: { + keyword: KEYWORDS, + literal: LITERALS + }, + contains: [ + hljs.HASH_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.COMMENT( + ';', + '$', + { relevance: 0 } + ), + VARIABLE_DEFINITION, + FUNCTION_DEFINITION, + { beginKeywords: 'Function PageEx Section SectionGroup FunctionEnd SectionEnd', }, + STRING, + COMPILER, + DEFINES, + VARIABLES, + LANGUAGES, + PARAMETERS, + PLUGINS, + hljs.NUMBER_MODE + ] + }; +} + +export { nsis as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/nsis.js.js b/frontend/node_modules/highlight.js/es/languages/nsis.js.js new file mode 100644 index 0000000..f680ce9 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/nsis.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/nsis" instead of "highlight.js/lib/languages/nsis.js"' + ); + } + } + emitWarning(); + import lang from './nsis.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/objectivec.js b/frontend/node_modules/highlight.js/es/languages/objectivec.js new file mode 100644 index 0000000..964f22e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/objectivec.js @@ -0,0 +1,253 @@ +/* +Language: Objective-C +Author: Valerii Hiora +Contributors: Angel G. Olloqui , Matt Diephouse , Andrew Farmer , Minh Nguyễn +Website: https://developer.apple.com/documentation/objectivec +Category: common +*/ + +function objectivec(hljs) { + const API_CLASS = { + className: 'built_in', + begin: '\\b(AV|CA|CF|CG|CI|CL|CM|CN|CT|MK|MP|MTK|MTL|NS|SCN|SK|UI|WK|XC)\\w+' + }; + const IDENTIFIER_RE = /[a-zA-Z@][a-zA-Z0-9_]*/; + const TYPES = [ + "int", + "float", + "char", + "unsigned", + "signed", + "short", + "long", + "double", + "wchar_t", + "unichar", + "void", + "bool", + "BOOL", + "id|0", + "_Bool" + ]; + const KWS = [ + "while", + "export", + "sizeof", + "typedef", + "const", + "struct", + "for", + "union", + "volatile", + "static", + "mutable", + "if", + "do", + "return", + "goto", + "enum", + "else", + "break", + "extern", + "asm", + "case", + "default", + "register", + "explicit", + "typename", + "switch", + "continue", + "inline", + "readonly", + "assign", + "readwrite", + "self", + "@synchronized", + "id", + "typeof", + "nonatomic", + "IBOutlet", + "IBAction", + "strong", + "weak", + "copy", + "in", + "out", + "inout", + "bycopy", + "byref", + "oneway", + "__strong", + "__weak", + "__block", + "__autoreleasing", + "@private", + "@protected", + "@public", + "@try", + "@property", + "@end", + "@throw", + "@catch", + "@finally", + "@autoreleasepool", + "@synthesize", + "@dynamic", + "@selector", + "@optional", + "@required", + "@encode", + "@package", + "@import", + "@defs", + "@compatibility_alias", + "__bridge", + "__bridge_transfer", + "__bridge_retained", + "__bridge_retain", + "__covariant", + "__contravariant", + "__kindof", + "_Nonnull", + "_Nullable", + "_Null_unspecified", + "__FUNCTION__", + "__PRETTY_FUNCTION__", + "__attribute__", + "getter", + "setter", + "retain", + "unsafe_unretained", + "nonnull", + "nullable", + "null_unspecified", + "null_resettable", + "class", + "instancetype", + "NS_DESIGNATED_INITIALIZER", + "NS_UNAVAILABLE", + "NS_REQUIRES_SUPER", + "NS_RETURNS_INNER_POINTER", + "NS_INLINE", + "NS_AVAILABLE", + "NS_DEPRECATED", + "NS_ENUM", + "NS_OPTIONS", + "NS_SWIFT_UNAVAILABLE", + "NS_ASSUME_NONNULL_BEGIN", + "NS_ASSUME_NONNULL_END", + "NS_REFINED_FOR_SWIFT", + "NS_SWIFT_NAME", + "NS_SWIFT_NOTHROW", + "NS_DURING", + "NS_HANDLER", + "NS_ENDHANDLER", + "NS_VALUERETURN", + "NS_VOIDRETURN" + ]; + const LITERALS = [ + "false", + "true", + "FALSE", + "TRUE", + "nil", + "YES", + "NO", + "NULL" + ]; + const BUILT_INS = [ + "dispatch_once_t", + "dispatch_queue_t", + "dispatch_sync", + "dispatch_async", + "dispatch_once" + ]; + const KEYWORDS = { + "variable.language": [ + "this", + "super" + ], + $pattern: IDENTIFIER_RE, + keyword: KWS, + literal: LITERALS, + built_in: BUILT_INS, + type: TYPES + }; + const CLASS_KEYWORDS = { + $pattern: IDENTIFIER_RE, + keyword: [ + "@interface", + "@class", + "@protocol", + "@implementation" + ] + }; + return { + name: 'Objective-C', + aliases: [ + 'mm', + 'objc', + 'obj-c', + 'obj-c++', + 'objective-c++' + ], + keywords: KEYWORDS, + illegal: '/, + end: /$/, + illegal: '\\n' + }, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }, + { + className: 'class', + begin: '(' + CLASS_KEYWORDS.keyword.join('|') + ')\\b', + end: /(\{|$)/, + excludeEnd: true, + keywords: CLASS_KEYWORDS, + contains: [ hljs.UNDERSCORE_TITLE_MODE ] + }, + { + begin: '\\.' + hljs.UNDERSCORE_IDENT_RE, + relevance: 0 + } + ] + }; +} + +export { objectivec as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/objectivec.js.js b/frontend/node_modules/highlight.js/es/languages/objectivec.js.js new file mode 100644 index 0000000..07fa8e5 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/objectivec.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/objectivec" instead of "highlight.js/lib/languages/objectivec.js"' + ); + } + } + emitWarning(); + import lang from './objectivec.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/ocaml.js b/frontend/node_modules/highlight.js/es/languages/ocaml.js new file mode 100644 index 0000000..2d2824d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ocaml.js @@ -0,0 +1,83 @@ +/* +Language: OCaml +Author: Mehdi Dogguy +Contributors: Nicolas Braud-Santoni , Mickael Delahaye +Description: OCaml language definition. +Website: https://ocaml.org +Category: functional +*/ + +function ocaml(hljs) { + /* missing support for heredoc-like string (OCaml 4.0.2+) */ + return { + name: 'OCaml', + aliases: [ 'ml' ], + keywords: { + $pattern: '[a-z_]\\w*!?', + keyword: + 'and as assert asr begin class constraint do done downto else end ' + + 'exception external for fun function functor if in include ' + + 'inherit! inherit initializer land lazy let lor lsl lsr lxor match method!|10 method ' + + 'mod module mutable new object of open! open or private rec sig struct ' + + 'then to try type val! val virtual when while with ' + /* camlp4 */ + + 'parser value', + built_in: + /* built-in types */ + 'array bool bytes char exn|5 float int int32 int64 list lazy_t|5 nativeint|5 string unit ' + /* (some) types in Pervasives */ + + 'in_channel out_channel ref', + literal: + 'true false' + }, + illegal: /\/\/|>>/, + contains: [ + { + className: 'literal', + begin: '\\[(\\|\\|)?\\]|\\(\\)', + relevance: 0 + }, + hljs.COMMENT( + '\\(\\*', + '\\*\\)', + { contains: [ 'self' ] } + ), + { /* type variable */ + className: 'symbol', + begin: '\'[A-Za-z_](?!\')[\\w\']*' + /* the grammar is ambiguous on how 'a'b should be interpreted but not the compiler */ + }, + { /* polymorphic variant */ + className: 'type', + begin: '`[A-Z][\\w\']*' + }, + { /* module or constructor */ + className: 'type', + begin: '\\b[A-Z][\\w\']*', + relevance: 0 + }, + { /* don't color identifiers, but safely catch all identifiers with ' */ + begin: '[a-z_]\\w*\'[\\w\']*', + relevance: 0 + }, + hljs.inherit(hljs.APOS_STRING_MODE, { + className: 'string', + relevance: 0 + }), + hljs.inherit(hljs.QUOTE_STRING_MODE, { illegal: null }), + { + className: 'number', + begin: + '\\b(0[xX][a-fA-F0-9_]+[Lln]?|' + + '0[oO][0-7_]+[Lln]?|' + + '0[bB][01_]+[Lln]?|' + + '[0-9][0-9_]*([Lln]|(\\.[0-9_]*)?([eE][-+]?[0-9_]+)?)?)', + relevance: 0 + }, + { begin: /->/ // relevance booster + } + ] + }; +} + +export { ocaml as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/ocaml.js.js b/frontend/node_modules/highlight.js/es/languages/ocaml.js.js new file mode 100644 index 0000000..e6de3f8 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ocaml.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/ocaml" instead of "highlight.js/lib/languages/ocaml.js"' + ); + } + } + emitWarning(); + import lang from './ocaml.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/openscad.js b/frontend/node_modules/highlight.js/es/languages/openscad.js new file mode 100644 index 0000000..d6d492b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/openscad.js @@ -0,0 +1,77 @@ +/* +Language: OpenSCAD +Author: Dan Panzarella +Description: OpenSCAD is a language for the 3D CAD modeling software of the same name. +Website: https://www.openscad.org +Category: scientific +*/ + +function openscad(hljs) { + const SPECIAL_VARS = { + className: 'keyword', + begin: '\\$(f[asn]|t|vp[rtd]|children)' + }; + const LITERALS = { + className: 'literal', + begin: 'false|true|PI|undef' + }; + const NUMBERS = { + className: 'number', + begin: '\\b\\d+(\\.\\d+)?(e-?\\d+)?', // adds 1e5, 1e-10 + relevance: 0 + }; + const STRING = hljs.inherit(hljs.QUOTE_STRING_MODE, { illegal: null }); + const PREPRO = { + className: 'meta', + keywords: { keyword: 'include use' }, + begin: 'include|use <', + end: '>' + }; + const PARAMS = { + className: 'params', + begin: '\\(', + end: '\\)', + contains: [ + 'self', + NUMBERS, + STRING, + SPECIAL_VARS, + LITERALS + ] + }; + const MODIFIERS = { + begin: '[*!#%]', + relevance: 0 + }; + const FUNCTIONS = { + className: 'function', + beginKeywords: 'module function', + end: /=|\{/, + contains: [ + PARAMS, + hljs.UNDERSCORE_TITLE_MODE + ] + }; + + return { + name: 'OpenSCAD', + aliases: [ 'scad' ], + keywords: { + keyword: 'function module include use for intersection_for if else \\%', + literal: 'false true PI undef', + built_in: 'circle square polygon text sphere cube cylinder polyhedron translate rotate scale resize mirror multmatrix color offset hull minkowski union difference intersection abs sign sin cos tan acos asin atan atan2 floor round ceil ln log pow sqrt exp rands min max concat lookup str chr search version version_num norm cross parent_module echo import import_dxf dxf_linear_extrude linear_extrude rotate_extrude surface projection render children dxf_cross dxf_dim let assign' + }, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + NUMBERS, + PREPRO, + STRING, + SPECIAL_VARS, + MODIFIERS, + FUNCTIONS + ] + }; +} + +export { openscad as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/openscad.js.js b/frontend/node_modules/highlight.js/es/languages/openscad.js.js new file mode 100644 index 0000000..e9a7b02 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/openscad.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/openscad" instead of "highlight.js/lib/languages/openscad.js"' + ); + } + } + emitWarning(); + import lang from './openscad.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/oxygene.js b/frontend/node_modules/highlight.js/es/languages/oxygene.js new file mode 100644 index 0000000..3c1e98f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/oxygene.js @@ -0,0 +1,87 @@ +/* +Language: Oxygene +Author: Carlo Kok +Description: Oxygene is built on the foundation of Object Pascal, revamped and extended to be a modern language for the twenty-first century. +Website: https://www.elementscompiler.com/elements/default.aspx +Category: build-system +*/ + +function oxygene(hljs) { + const OXYGENE_KEYWORDS = { + $pattern: /\.?\w+/, + keyword: + 'abstract add and array as asc aspect assembly async begin break block by case class concat const copy constructor continue ' + + 'create default delegate desc distinct div do downto dynamic each else empty end ensure enum equals event except exit extension external false ' + + 'final finalize finalizer finally flags for forward from function future global group has if implementation implements implies in index inherited ' + + 'inline interface into invariants is iterator join locked locking loop matching method mod module namespace nested new nil not notify nullable of ' + + 'old on operator or order out override parallel params partial pinned private procedure property protected public queryable raise read readonly ' + + 'record reintroduce remove repeat require result reverse sealed select self sequence set shl shr skip static step soft take then to true try tuple ' + + 'type union unit unsafe until uses using var virtual raises volatile where while with write xor yield await mapped deprecated stdcall cdecl pascal ' + + 'register safecall overload library platform reference packed strict published autoreleasepool selector strong weak unretained' + }; + const CURLY_COMMENT = hljs.COMMENT( + /\{/, + /\}/, + { relevance: 0 } + ); + const PAREN_COMMENT = hljs.COMMENT( + '\\(\\*', + '\\*\\)', + { relevance: 10 } + ); + const STRING = { + className: 'string', + begin: '\'', + end: '\'', + contains: [ { begin: '\'\'' } ] + }; + const CHAR_STRING = { + className: 'string', + begin: '(#\\d+)+' + }; + const FUNCTION = { + beginKeywords: 'function constructor destructor procedure method', + end: '[:;]', + keywords: 'function constructor|10 destructor|10 procedure|10 method|10', + contains: [ + hljs.inherit(hljs.TITLE_MODE, { scope: "title.function" }), + { + className: 'params', + begin: '\\(', + end: '\\)', + keywords: OXYGENE_KEYWORDS, + contains: [ + STRING, + CHAR_STRING + ] + }, + CURLY_COMMENT, + PAREN_COMMENT + ] + }; + + const SEMICOLON = { + scope: "punctuation", + match: /;/, + relevance: 0 + }; + + return { + name: 'Oxygene', + case_insensitive: true, + keywords: OXYGENE_KEYWORDS, + illegal: '("|\\$[G-Zg-z]|\\/\\*||->)', + contains: [ + CURLY_COMMENT, + PAREN_COMMENT, + hljs.C_LINE_COMMENT_MODE, + STRING, + CHAR_STRING, + hljs.NUMBER_MODE, + FUNCTION, + SEMICOLON + ] + }; +} + +export { oxygene as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/oxygene.js.js b/frontend/node_modules/highlight.js/es/languages/oxygene.js.js new file mode 100644 index 0000000..8586865 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/oxygene.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/oxygene" instead of "highlight.js/lib/languages/oxygene.js"' + ); + } + } + emitWarning(); + import lang from './oxygene.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/parser3.js b/frontend/node_modules/highlight.js/es/languages/parser3.js new file mode 100644 index 0000000..10dd89a --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/parser3.js @@ -0,0 +1,55 @@ +/* +Language: Parser3 +Requires: xml.js +Author: Oleg Volchkov +Website: https://www.parser.ru/en/ +Category: template +*/ + +function parser3(hljs) { + const CURLY_SUBCOMMENT = hljs.COMMENT( + /\{/, + /\}/, + { contains: [ 'self' ] } + ); + return { + name: 'Parser3', + subLanguage: 'xml', + relevance: 0, + contains: [ + hljs.COMMENT('^#', '$'), + hljs.COMMENT( + /\^rem\{/, + /\}/, + { + relevance: 10, + contains: [ CURLY_SUBCOMMENT ] + } + ), + { + className: 'meta', + begin: '^@(?:BASE|USE|CLASS|OPTIONS)$', + relevance: 10 + }, + { + className: 'title', + begin: '@[\\w\\-]+\\[[\\w^;\\-]*\\](?:\\[[\\w^;\\-]*\\])?(?:.*)$' + }, + { + className: 'variable', + begin: /\$\{?[\w\-.:]+\}?/ + }, + { + className: 'keyword', + begin: /\^[\w\-.:]+/ + }, + { + className: 'number', + begin: '\\^#[0-9a-fA-F]+' + }, + hljs.C_NUMBER_MODE + ] + }; +} + +export { parser3 as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/parser3.js.js b/frontend/node_modules/highlight.js/es/languages/parser3.js.js new file mode 100644 index 0000000..4552db5 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/parser3.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/parser3" instead of "highlight.js/lib/languages/parser3.js"' + ); + } + } + emitWarning(); + import lang from './parser3.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/perl.js b/frontend/node_modules/highlight.js/es/languages/perl.js new file mode 100644 index 0000000..d535989 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/perl.js @@ -0,0 +1,504 @@ +/* +Language: Perl +Author: Peter Leonov +Website: https://www.perl.org +Category: common +*/ + +/** @type LanguageFn */ +function perl(hljs) { + const regex = hljs.regex; + const KEYWORDS = [ + 'abs', + 'accept', + 'alarm', + 'and', + 'atan2', + 'bind', + 'binmode', + 'bless', + 'break', + 'caller', + 'chdir', + 'chmod', + 'chomp', + 'chop', + 'chown', + 'chr', + 'chroot', + 'class', + 'close', + 'closedir', + 'connect', + 'continue', + 'cos', + 'crypt', + 'dbmclose', + 'dbmopen', + 'defined', + 'delete', + 'die', + 'do', + 'dump', + 'each', + 'else', + 'elsif', + 'endgrent', + 'endhostent', + 'endnetent', + 'endprotoent', + 'endpwent', + 'endservent', + 'eof', + 'eval', + 'exec', + 'exists', + 'exit', + 'exp', + 'fcntl', + 'field', + 'fileno', + 'flock', + 'for', + 'foreach', + 'fork', + 'format', + 'formline', + 'getc', + 'getgrent', + 'getgrgid', + 'getgrnam', + 'gethostbyaddr', + 'gethostbyname', + 'gethostent', + 'getlogin', + 'getnetbyaddr', + 'getnetbyname', + 'getnetent', + 'getpeername', + 'getpgrp', + 'getpriority', + 'getprotobyname', + 'getprotobynumber', + 'getprotoent', + 'getpwent', + 'getpwnam', + 'getpwuid', + 'getservbyname', + 'getservbyport', + 'getservent', + 'getsockname', + 'getsockopt', + 'given', + 'glob', + 'gmtime', + 'goto', + 'grep', + 'gt', + 'hex', + 'if', + 'index', + 'int', + 'ioctl', + 'join', + 'keys', + 'kill', + 'last', + 'lc', + 'lcfirst', + 'length', + 'link', + 'listen', + 'local', + 'localtime', + 'log', + 'lstat', + 'lt', + 'ma', + 'map', + 'method', + 'mkdir', + 'msgctl', + 'msgget', + 'msgrcv', + 'msgsnd', + 'my', + 'ne', + 'next', + 'no', + 'not', + 'oct', + 'open', + 'opendir', + 'or', + 'ord', + 'our', + 'pack', + 'package', + 'pipe', + 'pop', + 'pos', + 'print', + 'printf', + 'prototype', + 'push', + 'q|0', + 'qq', + 'quotemeta', + 'qw', + 'qx', + 'rand', + 'read', + 'readdir', + 'readline', + 'readlink', + 'readpipe', + 'recv', + 'redo', + 'ref', + 'rename', + 'require', + 'reset', + 'return', + 'reverse', + 'rewinddir', + 'rindex', + 'rmdir', + 'say', + 'scalar', + 'seek', + 'seekdir', + 'select', + 'semctl', + 'semget', + 'semop', + 'send', + 'setgrent', + 'sethostent', + 'setnetent', + 'setpgrp', + 'setpriority', + 'setprotoent', + 'setpwent', + 'setservent', + 'setsockopt', + 'shift', + 'shmctl', + 'shmget', + 'shmread', + 'shmwrite', + 'shutdown', + 'sin', + 'sleep', + 'socket', + 'socketpair', + 'sort', + 'splice', + 'split', + 'sprintf', + 'sqrt', + 'srand', + 'stat', + 'state', + 'study', + 'sub', + 'substr', + 'symlink', + 'syscall', + 'sysopen', + 'sysread', + 'sysseek', + 'system', + 'syswrite', + 'tell', + 'telldir', + 'tie', + 'tied', + 'time', + 'times', + 'tr', + 'truncate', + 'uc', + 'ucfirst', + 'umask', + 'undef', + 'unless', + 'unlink', + 'unpack', + 'unshift', + 'untie', + 'until', + 'use', + 'utime', + 'values', + 'vec', + 'wait', + 'waitpid', + 'wantarray', + 'warn', + 'when', + 'while', + 'write', + 'x|0', + 'xor', + 'y|0' + ]; + + // https://perldoc.perl.org/perlre#Modifiers + const REGEX_MODIFIERS = /[dualxmsipngr]{0,12}/; // aa and xx are valid, making max length 12 + const PERL_KEYWORDS = { + $pattern: /[\w.]+/, + keyword: KEYWORDS.join(" ") + }; + const SUBST = { + className: 'subst', + begin: '[$@]\\{', + end: '\\}', + keywords: PERL_KEYWORDS + }; + const METHOD = { + begin: /->\{/, + end: /\}/ + // contains defined later + }; + const ATTR = { + scope: 'attr', + match: /\s+:\s*\w+(\s*\(.*?\))?/, + }; + const VAR = { + scope: 'variable', + variants: [ + { begin: /\$\d/ }, + { begin: regex.concat( + /[$%@](?!")(\^\w\b|#\w+(::\w+)*|\{\w+\}|\w+(::\w*)*)/, + // negative look-ahead tries to avoid matching patterns that are not + // Perl at all like $ident$, @ident@, etc. + `(?![A-Za-z])(?![@$%])` + ) + }, + { + // Only $= is a special Perl variable and one can't declare @= or %=. + begin: /[$%@](?!")[^\s\w{=]|\$=/, + relevance: 0 + } + ], + contains: [ ATTR ], + }; + const NUMBER = { + className: 'number', + variants: [ + // decimal numbers: + // include the case where a number starts with a dot (eg. .9), and + // the leading 0? avoids mixing the first and second match on 0.x cases + { match: /0?\.[0-9][0-9_]+\b/ }, + // include the special versioned number (eg. v5.38) + { match: /\bv?(0|[1-9][0-9_]*(\.[0-9_]+)?|[1-9][0-9_]*)\b/ }, + // non-decimal numbers: + { match: /\b0[0-7][0-7_]*\b/ }, + { match: /\b0x[0-9a-fA-F][0-9a-fA-F_]*\b/ }, + { match: /\b0b[0-1][0-1_]*\b/ }, + ], + relevance: 0 + }; + const STRING_CONTAINS = [ + hljs.BACKSLASH_ESCAPE, + SUBST, + VAR + ]; + const REGEX_DELIMS = [ + /!/, + /\//, + /\|/, + /\?/, + /'/, + /"/, // valid but infrequent and weird + /#/ // valid but infrequent and weird + ]; + /** + * @param {string|RegExp} prefix + * @param {string|RegExp} open + * @param {string|RegExp} close + */ + const PAIRED_DOUBLE_RE = (prefix, open, close = '\\1') => { + const middle = (close === '\\1') + ? close + : regex.concat(close, open); + return regex.concat( + regex.concat("(?:", prefix, ")"), + open, + /(?:\\.|[^\\\/])*?/, + middle, + /(?:\\.|[^\\\/])*?/, + close, + REGEX_MODIFIERS + ); + }; + /** + * @param {string|RegExp} prefix + * @param {string|RegExp} open + * @param {string|RegExp} close + */ + const PAIRED_RE = (prefix, open, close) => { + return regex.concat( + regex.concat("(?:", prefix, ")"), + open, + /(?:\\.|[^\\\/])*?/, + close, + REGEX_MODIFIERS + ); + }; + const PERL_DEFAULT_CONTAINS = [ + VAR, + hljs.HASH_COMMENT_MODE, + hljs.COMMENT( + /^=\w/, + /=cut/, + { endsWithParent: true } + ), + METHOD, + { + className: 'string', + contains: STRING_CONTAINS, + variants: [ + { + begin: 'q[qwxr]?\\s*\\(', + end: '\\)', + relevance: 5 + }, + { + begin: 'q[qwxr]?\\s*\\[', + end: '\\]', + relevance: 5 + }, + { + begin: 'q[qwxr]?\\s*\\{', + end: '\\}', + relevance: 5 + }, + { + begin: 'q[qwxr]?\\s*\\|', + end: '\\|', + relevance: 5 + }, + { + begin: 'q[qwxr]?\\s*<', + end: '>', + relevance: 5 + }, + { + begin: 'qw\\s+q', + end: 'q', + relevance: 5 + }, + { + begin: '\'', + end: '\'', + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: '"', + end: '"' + }, + { + begin: '`', + end: '`', + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: /\{\w+\}/, + relevance: 0 + }, + { + begin: '-?\\w+\\s*=>', + relevance: 0 + } + ] + }, + NUMBER, + { // regexp container + begin: '(\\/\\/|' + hljs.RE_STARTERS_RE + '|\\b(split|return|print|reverse|grep)\\b)\\s*', + keywords: 'split return print reverse grep', + relevance: 0, + contains: [ + hljs.HASH_COMMENT_MODE, + { + className: 'regexp', + variants: [ + // allow matching common delimiters + { begin: PAIRED_DOUBLE_RE("s|tr|y", regex.either(...REGEX_DELIMS, { capture: true })) }, + // and then paired delmis + { begin: PAIRED_DOUBLE_RE("s|tr|y", "\\(", "\\)") }, + { begin: PAIRED_DOUBLE_RE("s|tr|y", "\\[", "\\]") }, + { begin: PAIRED_DOUBLE_RE("s|tr|y", "\\{", "\\}") } + ], + relevance: 2 + }, + { + className: 'regexp', + variants: [ + { + // could be a comment in many languages so do not count + // as relevant + begin: /(m|qr)\/\//, + relevance: 0 + }, + // prefix is optional with /regex/ + { begin: PAIRED_RE("(?:m|qr)?", /\//, /\//) }, + // allow matching common delimiters + { begin: PAIRED_RE("m|qr", regex.either(...REGEX_DELIMS, { capture: true }), /\1/) }, + // allow common paired delmins + { begin: PAIRED_RE("m|qr", /\(/, /\)/) }, + { begin: PAIRED_RE("m|qr", /\[/, /\]/) }, + { begin: PAIRED_RE("m|qr", /\{/, /\}/) } + ] + } + ] + }, + { + className: 'function', + beginKeywords: 'sub method', + end: '(\\s*\\(.*?\\))?[;{]', + excludeEnd: true, + relevance: 5, + contains: [ hljs.TITLE_MODE, ATTR ] + }, + { + className: 'class', + beginKeywords: 'class', + end: '[;{]', + excludeEnd: true, + relevance: 5, + contains: [ hljs.TITLE_MODE, ATTR, NUMBER ] + }, + { + begin: '-\\w\\b', + relevance: 0 + }, + { + begin: "^__DATA__$", + end: "^__END__$", + subLanguage: 'mojolicious', + contains: [ + { + begin: "^@@.*", + end: "$", + className: "comment" + } + ] + } + ]; + SUBST.contains = PERL_DEFAULT_CONTAINS; + METHOD.contains = PERL_DEFAULT_CONTAINS; + + return { + name: 'Perl', + aliases: [ + 'pl', + 'pm' + ], + keywords: PERL_KEYWORDS, + contains: PERL_DEFAULT_CONTAINS + }; +} + +export { perl as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/perl.js.js b/frontend/node_modules/highlight.js/es/languages/perl.js.js new file mode 100644 index 0000000..ddb8f32 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/perl.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/perl" instead of "highlight.js/lib/languages/perl.js"' + ); + } + } + emitWarning(); + import lang from './perl.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/pf.js b/frontend/node_modules/highlight.js/es/languages/pf.js new file mode 100644 index 0000000..af9023d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/pf.js @@ -0,0 +1,60 @@ +/* +Language: Packet Filter config +Description: pf.conf — packet filter configuration file (OpenBSD) +Author: Peter Piwowarski +Website: http://man.openbsd.org/pf.conf +Category: config +*/ + +function pf(hljs) { + const MACRO = { + className: 'variable', + begin: /\$[\w\d#@][\w\d_]*/, + relevance: 0 + }; + const TABLE = { + className: 'variable', + begin: /<(?!\/)/, + end: />/ + }; + + return { + name: 'Packet Filter config', + aliases: [ 'pf.conf' ], + keywords: { + $pattern: /[a-z0-9_<>-]+/, + built_in: /* block match pass are "actions" in pf.conf(5), the rest are + * lexically similar top-level commands. + */ + 'block match pass load anchor|5 antispoof|10 set table', + keyword: + 'in out log quick on rdomain inet inet6 proto from port os to route ' + + 'allow-opts divert-packet divert-reply divert-to flags group icmp-type ' + + 'icmp6-type label once probability recieved-on rtable prio queue ' + + 'tos tag tagged user keep fragment for os drop ' + + 'af-to|10 binat-to|10 nat-to|10 rdr-to|10 bitmask least-stats random round-robin ' + + 'source-hash static-port ' + + 'dup-to reply-to route-to ' + + 'parent bandwidth default min max qlimit ' + + 'block-policy debug fingerprints hostid limit loginterface optimization ' + + 'reassemble ruleset-optimization basic none profile skip state-defaults ' + + 'state-policy timeout ' + + 'const counters persist ' + + 'no modulate synproxy state|5 floating if-bound no-sync pflow|10 sloppy ' + + 'source-track global rule max-src-nodes max-src-states max-src-conn ' + + 'max-src-conn-rate overload flush ' + + 'scrub|5 max-mss min-ttl no-df|10 random-id', + literal: + 'all any no-route self urpf-failed egress|5 unknown' + }, + contains: [ + hljs.HASH_COMMENT_MODE, + hljs.NUMBER_MODE, + hljs.QUOTE_STRING_MODE, + MACRO, + TABLE + ] + }; +} + +export { pf as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/pf.js.js b/frontend/node_modules/highlight.js/es/languages/pf.js.js new file mode 100644 index 0000000..f13b611 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/pf.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/pf" instead of "highlight.js/lib/languages/pf.js"' + ); + } + } + emitWarning(); + import lang from './pf.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/pgsql.js b/frontend/node_modules/highlight.js/es/languages/pgsql.js new file mode 100644 index 0000000..604d84a --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/pgsql.js @@ -0,0 +1,525 @@ +/* +Language: PostgreSQL and PL/pgSQL +Author: Egor Rogov (e.rogov@postgrespro.ru) +Website: https://www.postgresql.org/docs/11/sql.html +Description: + This language incorporates both PostgreSQL SQL dialect and PL/pgSQL language. + It is based on PostgreSQL version 11. Some notes: + - Text in double-dollar-strings is _always_ interpreted as some programming code. Text + in ordinary quotes is _never_ interpreted that way and highlighted just as a string. + - There are quite a bit "special cases". That's because many keywords are not strictly + they are keywords in some contexts and ordinary identifiers in others. Only some + of such cases are handled; you still can get some of your identifiers highlighted + wrong way. + - Function names deliberately are not highlighted. There is no way to tell function + call from other constructs, hence we can't highlight _all_ function names. And + some names highlighted while others not looks ugly. +Category: database +*/ + +function pgsql(hljs) { + const COMMENT_MODE = hljs.COMMENT('--', '$'); + const UNQUOTED_IDENT = '[a-zA-Z_][a-zA-Z_0-9$]*'; + const DOLLAR_STRING = '\\$([a-zA-Z_]?|[a-zA-Z_][a-zA-Z_0-9]*)\\$'; + const LABEL = '<<\\s*' + UNQUOTED_IDENT + '\\s*>>'; + + const SQL_KW = + // https://www.postgresql.org/docs/11/static/sql-keywords-appendix.html + // https://www.postgresql.org/docs/11/static/sql-commands.html + // SQL commands (starting words) + 'ABORT ALTER ANALYZE BEGIN CALL CHECKPOINT|10 CLOSE CLUSTER COMMENT COMMIT COPY CREATE DEALLOCATE DECLARE ' + + 'DELETE DISCARD DO DROP END EXECUTE EXPLAIN FETCH GRANT IMPORT INSERT LISTEN LOAD LOCK MOVE NOTIFY ' + + 'PREPARE REASSIGN|10 REFRESH REINDEX RELEASE RESET REVOKE ROLLBACK SAVEPOINT SECURITY SELECT SET SHOW ' + + 'START TRUNCATE UNLISTEN|10 UPDATE VACUUM|10 VALUES ' + // SQL commands (others) + + 'AGGREGATE COLLATION CONVERSION|10 DATABASE DEFAULT PRIVILEGES DOMAIN TRIGGER EXTENSION FOREIGN ' + + 'WRAPPER|10 TABLE FUNCTION GROUP LANGUAGE LARGE OBJECT MATERIALIZED VIEW OPERATOR CLASS ' + + 'FAMILY POLICY PUBLICATION|10 ROLE RULE SCHEMA SEQUENCE SERVER STATISTICS SUBSCRIPTION SYSTEM ' + + 'TABLESPACE CONFIGURATION DICTIONARY PARSER TEMPLATE TYPE USER MAPPING PREPARED ACCESS ' + + 'METHOD CAST AS TRANSFORM TRANSACTION OWNED TO INTO SESSION AUTHORIZATION ' + + 'INDEX PROCEDURE ASSERTION ' + // additional reserved key words + + 'ALL ANALYSE AND ANY ARRAY ASC ASYMMETRIC|10 BOTH CASE CHECK ' + + 'COLLATE COLUMN CONCURRENTLY|10 CONSTRAINT CROSS ' + + 'DEFERRABLE RANGE ' + + 'DESC DISTINCT ELSE EXCEPT FOR FREEZE|10 FROM FULL HAVING ' + + 'ILIKE IN INITIALLY INNER INTERSECT IS ISNULL JOIN LATERAL LEADING LIKE LIMIT ' + + 'NATURAL NOT NOTNULL NULL OFFSET ON ONLY OR ORDER OUTER OVERLAPS PLACING PRIMARY ' + + 'REFERENCES RETURNING SIMILAR SOME SYMMETRIC TABLESAMPLE THEN ' + + 'TRAILING UNION UNIQUE USING VARIADIC|10 VERBOSE WHEN WHERE WINDOW WITH ' + // some of non-reserved (which are used in clauses or as PL/pgSQL keyword) + + 'BY RETURNS INOUT OUT SETOF|10 IF STRICT CURRENT CONTINUE OWNER LOCATION OVER PARTITION WITHIN ' + + 'BETWEEN ESCAPE EXTERNAL INVOKER DEFINER WORK RENAME VERSION CONNECTION CONNECT ' + + 'TABLES TEMP TEMPORARY FUNCTIONS SEQUENCES TYPES SCHEMAS OPTION CASCADE RESTRICT ADD ADMIN ' + + 'EXISTS VALID VALIDATE ENABLE DISABLE REPLICA|10 ALWAYS PASSING COLUMNS PATH ' + + 'REF VALUE OVERRIDING IMMUTABLE STABLE VOLATILE BEFORE AFTER EACH ROW PROCEDURAL ' + + 'ROUTINE NO HANDLER VALIDATOR OPTIONS STORAGE OIDS|10 WITHOUT INHERIT DEPENDS CALLED ' + + 'INPUT LEAKPROOF|10 COST ROWS NOWAIT SEARCH UNTIL ENCRYPTED|10 PASSWORD CONFLICT|10 ' + + 'INSTEAD INHERITS CHARACTERISTICS WRITE CURSOR ALSO STATEMENT SHARE EXCLUSIVE INLINE ' + + 'ISOLATION REPEATABLE READ COMMITTED SERIALIZABLE UNCOMMITTED LOCAL GLOBAL SQL PROCEDURES ' + + 'RECURSIVE SNAPSHOT ROLLUP CUBE TRUSTED|10 INCLUDE FOLLOWING PRECEDING UNBOUNDED RANGE GROUPS ' + + 'UNENCRYPTED|10 SYSID FORMAT DELIMITER HEADER QUOTE ENCODING FILTER OFF ' + // some parameters of VACUUM/ANALYZE/EXPLAIN + + 'FORCE_QUOTE FORCE_NOT_NULL FORCE_NULL COSTS BUFFERS TIMING SUMMARY DISABLE_PAGE_SKIPPING ' + // + + 'RESTART CYCLE GENERATED IDENTITY DEFERRED IMMEDIATE LEVEL LOGGED UNLOGGED ' + + 'OF NOTHING NONE EXCLUDE ATTRIBUTE ' + // from GRANT (not keywords actually) + + 'USAGE ROUTINES ' + // actually literals, but look better this way (due to IS TRUE, IS FALSE, ISNULL etc) + + 'TRUE FALSE NAN INFINITY '; + + const ROLE_ATTRS = // only those not in keywrods already + 'SUPERUSER NOSUPERUSER CREATEDB NOCREATEDB CREATEROLE NOCREATEROLE INHERIT NOINHERIT ' + + 'LOGIN NOLOGIN REPLICATION NOREPLICATION BYPASSRLS NOBYPASSRLS '; + + const PLPGSQL_KW = + 'ALIAS BEGIN CONSTANT DECLARE END EXCEPTION RETURN PERFORM|10 RAISE GET DIAGNOSTICS ' + + 'STACKED|10 FOREACH LOOP ELSIF EXIT WHILE REVERSE SLICE DEBUG LOG INFO NOTICE WARNING ASSERT ' + + 'OPEN '; + + const TYPES = + // https://www.postgresql.org/docs/11/static/datatype.html + 'BIGINT INT8 BIGSERIAL SERIAL8 BIT VARYING VARBIT BOOLEAN BOOL BOX BYTEA CHARACTER CHAR VARCHAR ' + + 'CIDR CIRCLE DATE DOUBLE PRECISION FLOAT8 FLOAT INET INTEGER INT INT4 INTERVAL JSON JSONB LINE LSEG|10 ' + + 'MACADDR MACADDR8 MONEY NUMERIC DEC DECIMAL PATH POINT POLYGON REAL FLOAT4 SMALLINT INT2 ' + + 'SMALLSERIAL|10 SERIAL2|10 SERIAL|10 SERIAL4|10 TEXT TIME ZONE TIMETZ|10 TIMESTAMP TIMESTAMPTZ|10 TSQUERY|10 TSVECTOR|10 ' + + 'TXID_SNAPSHOT|10 UUID XML NATIONAL NCHAR ' + + 'INT4RANGE|10 INT8RANGE|10 NUMRANGE|10 TSRANGE|10 TSTZRANGE|10 DATERANGE|10 ' + // pseudotypes + + 'ANYELEMENT ANYARRAY ANYNONARRAY ANYENUM ANYRANGE CSTRING INTERNAL ' + + 'RECORD PG_DDL_COMMAND VOID UNKNOWN OPAQUE REFCURSOR ' + // spec. type + + 'NAME ' + // OID-types + + 'OID REGPROC|10 REGPROCEDURE|10 REGOPER|10 REGOPERATOR|10 REGCLASS|10 REGTYPE|10 REGROLE|10 ' + + 'REGNAMESPACE|10 REGCONFIG|10 REGDICTIONARY|10 ';// + + + const TYPES_RE = + TYPES.trim() + .split(' ') + .map(function(val) { return val.split('|')[0]; }) + .join('|'); + + const SQL_BI = + 'CURRENT_TIME CURRENT_TIMESTAMP CURRENT_USER CURRENT_CATALOG|10 CURRENT_DATE LOCALTIME LOCALTIMESTAMP ' + + 'CURRENT_ROLE|10 CURRENT_SCHEMA|10 SESSION_USER PUBLIC '; + + const PLPGSQL_BI = + 'FOUND NEW OLD TG_NAME|10 TG_WHEN|10 TG_LEVEL|10 TG_OP|10 TG_RELID|10 TG_RELNAME|10 ' + + 'TG_TABLE_NAME|10 TG_TABLE_SCHEMA|10 TG_NARGS|10 TG_ARGV|10 TG_EVENT|10 TG_TAG|10 ' + // get diagnostics + + 'ROW_COUNT RESULT_OID|10 PG_CONTEXT|10 RETURNED_SQLSTATE COLUMN_NAME CONSTRAINT_NAME ' + + 'PG_DATATYPE_NAME|10 MESSAGE_TEXT TABLE_NAME SCHEMA_NAME PG_EXCEPTION_DETAIL|10 ' + + 'PG_EXCEPTION_HINT|10 PG_EXCEPTION_CONTEXT|10 '; + + const PLPGSQL_EXCEPTIONS = + // exceptions https://www.postgresql.org/docs/current/static/errcodes-appendix.html + 'SQLSTATE SQLERRM|10 ' + + 'SUCCESSFUL_COMPLETION WARNING DYNAMIC_RESULT_SETS_RETURNED IMPLICIT_ZERO_BIT_PADDING ' + + 'NULL_VALUE_ELIMINATED_IN_SET_FUNCTION PRIVILEGE_NOT_GRANTED PRIVILEGE_NOT_REVOKED ' + + 'STRING_DATA_RIGHT_TRUNCATION DEPRECATED_FEATURE NO_DATA NO_ADDITIONAL_DYNAMIC_RESULT_SETS_RETURNED ' + + 'SQL_STATEMENT_NOT_YET_COMPLETE CONNECTION_EXCEPTION CONNECTION_DOES_NOT_EXIST CONNECTION_FAILURE ' + + 'SQLCLIENT_UNABLE_TO_ESTABLISH_SQLCONNECTION SQLSERVER_REJECTED_ESTABLISHMENT_OF_SQLCONNECTION ' + + 'TRANSACTION_RESOLUTION_UNKNOWN PROTOCOL_VIOLATION TRIGGERED_ACTION_EXCEPTION FEATURE_NOT_SUPPORTED ' + + 'INVALID_TRANSACTION_INITIATION LOCATOR_EXCEPTION INVALID_LOCATOR_SPECIFICATION INVALID_GRANTOR ' + + 'INVALID_GRANT_OPERATION INVALID_ROLE_SPECIFICATION DIAGNOSTICS_EXCEPTION ' + + 'STACKED_DIAGNOSTICS_ACCESSED_WITHOUT_ACTIVE_HANDLER CASE_NOT_FOUND CARDINALITY_VIOLATION ' + + 'DATA_EXCEPTION ARRAY_SUBSCRIPT_ERROR CHARACTER_NOT_IN_REPERTOIRE DATETIME_FIELD_OVERFLOW ' + + 'DIVISION_BY_ZERO ERROR_IN_ASSIGNMENT ESCAPE_CHARACTER_CONFLICT INDICATOR_OVERFLOW ' + + 'INTERVAL_FIELD_OVERFLOW INVALID_ARGUMENT_FOR_LOGARITHM INVALID_ARGUMENT_FOR_NTILE_FUNCTION ' + + 'INVALID_ARGUMENT_FOR_NTH_VALUE_FUNCTION INVALID_ARGUMENT_FOR_POWER_FUNCTION ' + + 'INVALID_ARGUMENT_FOR_WIDTH_BUCKET_FUNCTION INVALID_CHARACTER_VALUE_FOR_CAST ' + + 'INVALID_DATETIME_FORMAT INVALID_ESCAPE_CHARACTER INVALID_ESCAPE_OCTET INVALID_ESCAPE_SEQUENCE ' + + 'NONSTANDARD_USE_OF_ESCAPE_CHARACTER INVALID_INDICATOR_PARAMETER_VALUE INVALID_PARAMETER_VALUE ' + + 'INVALID_REGULAR_EXPRESSION INVALID_ROW_COUNT_IN_LIMIT_CLAUSE ' + + 'INVALID_ROW_COUNT_IN_RESULT_OFFSET_CLAUSE INVALID_TABLESAMPLE_ARGUMENT INVALID_TABLESAMPLE_REPEAT ' + + 'INVALID_TIME_ZONE_DISPLACEMENT_VALUE INVALID_USE_OF_ESCAPE_CHARACTER MOST_SPECIFIC_TYPE_MISMATCH ' + + 'NULL_VALUE_NOT_ALLOWED NULL_VALUE_NO_INDICATOR_PARAMETER NUMERIC_VALUE_OUT_OF_RANGE ' + + 'SEQUENCE_GENERATOR_LIMIT_EXCEEDED STRING_DATA_LENGTH_MISMATCH STRING_DATA_RIGHT_TRUNCATION ' + + 'SUBSTRING_ERROR TRIM_ERROR UNTERMINATED_C_STRING ZERO_LENGTH_CHARACTER_STRING ' + + 'FLOATING_POINT_EXCEPTION INVALID_TEXT_REPRESENTATION INVALID_BINARY_REPRESENTATION ' + + 'BAD_COPY_FILE_FORMAT UNTRANSLATABLE_CHARACTER NOT_AN_XML_DOCUMENT INVALID_XML_DOCUMENT ' + + 'INVALID_XML_CONTENT INVALID_XML_COMMENT INVALID_XML_PROCESSING_INSTRUCTION ' + + 'INTEGRITY_CONSTRAINT_VIOLATION RESTRICT_VIOLATION NOT_NULL_VIOLATION FOREIGN_KEY_VIOLATION ' + + 'UNIQUE_VIOLATION CHECK_VIOLATION EXCLUSION_VIOLATION INVALID_CURSOR_STATE ' + + 'INVALID_TRANSACTION_STATE ACTIVE_SQL_TRANSACTION BRANCH_TRANSACTION_ALREADY_ACTIVE ' + + 'HELD_CURSOR_REQUIRES_SAME_ISOLATION_LEVEL INAPPROPRIATE_ACCESS_MODE_FOR_BRANCH_TRANSACTION ' + + 'INAPPROPRIATE_ISOLATION_LEVEL_FOR_BRANCH_TRANSACTION ' + + 'NO_ACTIVE_SQL_TRANSACTION_FOR_BRANCH_TRANSACTION READ_ONLY_SQL_TRANSACTION ' + + 'SCHEMA_AND_DATA_STATEMENT_MIXING_NOT_SUPPORTED NO_ACTIVE_SQL_TRANSACTION ' + + 'IN_FAILED_SQL_TRANSACTION IDLE_IN_TRANSACTION_SESSION_TIMEOUT INVALID_SQL_STATEMENT_NAME ' + + 'TRIGGERED_DATA_CHANGE_VIOLATION INVALID_AUTHORIZATION_SPECIFICATION INVALID_PASSWORD ' + + 'DEPENDENT_PRIVILEGE_DESCRIPTORS_STILL_EXIST DEPENDENT_OBJECTS_STILL_EXIST ' + + 'INVALID_TRANSACTION_TERMINATION SQL_ROUTINE_EXCEPTION FUNCTION_EXECUTED_NO_RETURN_STATEMENT ' + + 'MODIFYING_SQL_DATA_NOT_PERMITTED PROHIBITED_SQL_STATEMENT_ATTEMPTED ' + + 'READING_SQL_DATA_NOT_PERMITTED INVALID_CURSOR_NAME EXTERNAL_ROUTINE_EXCEPTION ' + + 'CONTAINING_SQL_NOT_PERMITTED MODIFYING_SQL_DATA_NOT_PERMITTED ' + + 'PROHIBITED_SQL_STATEMENT_ATTEMPTED READING_SQL_DATA_NOT_PERMITTED ' + + 'EXTERNAL_ROUTINE_INVOCATION_EXCEPTION INVALID_SQLSTATE_RETURNED NULL_VALUE_NOT_ALLOWED ' + + 'TRIGGER_PROTOCOL_VIOLATED SRF_PROTOCOL_VIOLATED EVENT_TRIGGER_PROTOCOL_VIOLATED ' + + 'SAVEPOINT_EXCEPTION INVALID_SAVEPOINT_SPECIFICATION INVALID_CATALOG_NAME ' + + 'INVALID_SCHEMA_NAME TRANSACTION_ROLLBACK TRANSACTION_INTEGRITY_CONSTRAINT_VIOLATION ' + + 'SERIALIZATION_FAILURE STATEMENT_COMPLETION_UNKNOWN DEADLOCK_DETECTED ' + + 'SYNTAX_ERROR_OR_ACCESS_RULE_VIOLATION SYNTAX_ERROR INSUFFICIENT_PRIVILEGE CANNOT_COERCE ' + + 'GROUPING_ERROR WINDOWING_ERROR INVALID_RECURSION INVALID_FOREIGN_KEY INVALID_NAME ' + + 'NAME_TOO_LONG RESERVED_NAME DATATYPE_MISMATCH INDETERMINATE_DATATYPE COLLATION_MISMATCH ' + + 'INDETERMINATE_COLLATION WRONG_OBJECT_TYPE GENERATED_ALWAYS UNDEFINED_COLUMN ' + + 'UNDEFINED_FUNCTION UNDEFINED_TABLE UNDEFINED_PARAMETER UNDEFINED_OBJECT ' + + 'DUPLICATE_COLUMN DUPLICATE_CURSOR DUPLICATE_DATABASE DUPLICATE_FUNCTION ' + + 'DUPLICATE_PREPARED_STATEMENT DUPLICATE_SCHEMA DUPLICATE_TABLE DUPLICATE_ALIAS ' + + 'DUPLICATE_OBJECT AMBIGUOUS_COLUMN AMBIGUOUS_FUNCTION AMBIGUOUS_PARAMETER AMBIGUOUS_ALIAS ' + + 'INVALID_COLUMN_REFERENCE INVALID_COLUMN_DEFINITION INVALID_CURSOR_DEFINITION ' + + 'INVALID_DATABASE_DEFINITION INVALID_FUNCTION_DEFINITION ' + + 'INVALID_PREPARED_STATEMENT_DEFINITION INVALID_SCHEMA_DEFINITION INVALID_TABLE_DEFINITION ' + + 'INVALID_OBJECT_DEFINITION WITH_CHECK_OPTION_VIOLATION INSUFFICIENT_RESOURCES DISK_FULL ' + + 'OUT_OF_MEMORY TOO_MANY_CONNECTIONS CONFIGURATION_LIMIT_EXCEEDED PROGRAM_LIMIT_EXCEEDED ' + + 'STATEMENT_TOO_COMPLEX TOO_MANY_COLUMNS TOO_MANY_ARGUMENTS OBJECT_NOT_IN_PREREQUISITE_STATE ' + + 'OBJECT_IN_USE CANT_CHANGE_RUNTIME_PARAM LOCK_NOT_AVAILABLE OPERATOR_INTERVENTION ' + + 'QUERY_CANCELED ADMIN_SHUTDOWN CRASH_SHUTDOWN CANNOT_CONNECT_NOW DATABASE_DROPPED ' + + 'SYSTEM_ERROR IO_ERROR UNDEFINED_FILE DUPLICATE_FILE SNAPSHOT_TOO_OLD CONFIG_FILE_ERROR ' + + 'LOCK_FILE_EXISTS FDW_ERROR FDW_COLUMN_NAME_NOT_FOUND FDW_DYNAMIC_PARAMETER_VALUE_NEEDED ' + + 'FDW_FUNCTION_SEQUENCE_ERROR FDW_INCONSISTENT_DESCRIPTOR_INFORMATION ' + + 'FDW_INVALID_ATTRIBUTE_VALUE FDW_INVALID_COLUMN_NAME FDW_INVALID_COLUMN_NUMBER ' + + 'FDW_INVALID_DATA_TYPE FDW_INVALID_DATA_TYPE_DESCRIPTORS ' + + 'FDW_INVALID_DESCRIPTOR_FIELD_IDENTIFIER FDW_INVALID_HANDLE FDW_INVALID_OPTION_INDEX ' + + 'FDW_INVALID_OPTION_NAME FDW_INVALID_STRING_LENGTH_OR_BUFFER_LENGTH ' + + 'FDW_INVALID_STRING_FORMAT FDW_INVALID_USE_OF_NULL_POINTER FDW_TOO_MANY_HANDLES ' + + 'FDW_OUT_OF_MEMORY FDW_NO_SCHEMAS FDW_OPTION_NAME_NOT_FOUND FDW_REPLY_HANDLE ' + + 'FDW_SCHEMA_NOT_FOUND FDW_TABLE_NOT_FOUND FDW_UNABLE_TO_CREATE_EXECUTION ' + + 'FDW_UNABLE_TO_CREATE_REPLY FDW_UNABLE_TO_ESTABLISH_CONNECTION PLPGSQL_ERROR ' + + 'RAISE_EXCEPTION NO_DATA_FOUND TOO_MANY_ROWS ASSERT_FAILURE INTERNAL_ERROR DATA_CORRUPTED ' + + 'INDEX_CORRUPTED '; + + const FUNCTIONS = + // https://www.postgresql.org/docs/11/static/functions-aggregate.html + 'ARRAY_AGG AVG BIT_AND BIT_OR BOOL_AND BOOL_OR COUNT EVERY JSON_AGG JSONB_AGG JSON_OBJECT_AGG ' + + 'JSONB_OBJECT_AGG MAX MIN MODE STRING_AGG SUM XMLAGG ' + + 'CORR COVAR_POP COVAR_SAMP REGR_AVGX REGR_AVGY REGR_COUNT REGR_INTERCEPT REGR_R2 REGR_SLOPE ' + + 'REGR_SXX REGR_SXY REGR_SYY STDDEV STDDEV_POP STDDEV_SAMP VARIANCE VAR_POP VAR_SAMP ' + + 'PERCENTILE_CONT PERCENTILE_DISC ' + // https://www.postgresql.org/docs/11/static/functions-window.html + + 'ROW_NUMBER RANK DENSE_RANK PERCENT_RANK CUME_DIST NTILE LAG LEAD FIRST_VALUE LAST_VALUE NTH_VALUE ' + // https://www.postgresql.org/docs/11/static/functions-comparison.html + + 'NUM_NONNULLS NUM_NULLS ' + // https://www.postgresql.org/docs/11/static/functions-math.html + + 'ABS CBRT CEIL CEILING DEGREES DIV EXP FLOOR LN LOG MOD PI POWER RADIANS ROUND SCALE SIGN SQRT ' + + 'TRUNC WIDTH_BUCKET ' + + 'RANDOM SETSEED ' + + 'ACOS ACOSD ASIN ASIND ATAN ATAND ATAN2 ATAN2D COS COSD COT COTD SIN SIND TAN TAND ' + // https://www.postgresql.org/docs/11/static/functions-string.html + + 'BIT_LENGTH CHAR_LENGTH CHARACTER_LENGTH LOWER OCTET_LENGTH OVERLAY POSITION SUBSTRING TREAT TRIM UPPER ' + + 'ASCII BTRIM CHR CONCAT CONCAT_WS CONVERT CONVERT_FROM CONVERT_TO DECODE ENCODE INITCAP ' + + 'LEFT LENGTH LPAD LTRIM MD5 PARSE_IDENT PG_CLIENT_ENCODING QUOTE_IDENT|10 QUOTE_LITERAL|10 ' + + 'QUOTE_NULLABLE|10 REGEXP_MATCH REGEXP_MATCHES REGEXP_REPLACE REGEXP_SPLIT_TO_ARRAY ' + + 'REGEXP_SPLIT_TO_TABLE REPEAT REPLACE REVERSE RIGHT RPAD RTRIM SPLIT_PART STRPOS SUBSTR ' + + 'TO_ASCII TO_HEX TRANSLATE ' + // https://www.postgresql.org/docs/11/static/functions-binarystring.html + + 'OCTET_LENGTH GET_BIT GET_BYTE SET_BIT SET_BYTE ' + // https://www.postgresql.org/docs/11/static/functions-formatting.html + + 'TO_CHAR TO_DATE TO_NUMBER TO_TIMESTAMP ' + // https://www.postgresql.org/docs/11/static/functions-datetime.html + + 'AGE CLOCK_TIMESTAMP|10 DATE_PART DATE_TRUNC ISFINITE JUSTIFY_DAYS JUSTIFY_HOURS JUSTIFY_INTERVAL ' + + 'MAKE_DATE MAKE_INTERVAL|10 MAKE_TIME MAKE_TIMESTAMP|10 MAKE_TIMESTAMPTZ|10 NOW STATEMENT_TIMESTAMP|10 ' + + 'TIMEOFDAY TRANSACTION_TIMESTAMP|10 ' + // https://www.postgresql.org/docs/11/static/functions-enum.html + + 'ENUM_FIRST ENUM_LAST ENUM_RANGE ' + // https://www.postgresql.org/docs/11/static/functions-geometry.html + + 'AREA CENTER DIAMETER HEIGHT ISCLOSED ISOPEN NPOINTS PCLOSE POPEN RADIUS WIDTH ' + + 'BOX BOUND_BOX CIRCLE LINE LSEG PATH POLYGON ' + // https://www.postgresql.org/docs/11/static/functions-net.html + + 'ABBREV BROADCAST HOST HOSTMASK MASKLEN NETMASK NETWORK SET_MASKLEN TEXT INET_SAME_FAMILY ' + + 'INET_MERGE MACADDR8_SET7BIT ' + // https://www.postgresql.org/docs/11/static/functions-textsearch.html + + 'ARRAY_TO_TSVECTOR GET_CURRENT_TS_CONFIG NUMNODE PLAINTO_TSQUERY PHRASETO_TSQUERY WEBSEARCH_TO_TSQUERY ' + + 'QUERYTREE SETWEIGHT STRIP TO_TSQUERY TO_TSVECTOR JSON_TO_TSVECTOR JSONB_TO_TSVECTOR TS_DELETE ' + + 'TS_FILTER TS_HEADLINE TS_RANK TS_RANK_CD TS_REWRITE TSQUERY_PHRASE TSVECTOR_TO_ARRAY ' + + 'TSVECTOR_UPDATE_TRIGGER TSVECTOR_UPDATE_TRIGGER_COLUMN ' + // https://www.postgresql.org/docs/11/static/functions-xml.html + + 'XMLCOMMENT XMLCONCAT XMLELEMENT XMLFOREST XMLPI XMLROOT ' + + 'XMLEXISTS XML_IS_WELL_FORMED XML_IS_WELL_FORMED_DOCUMENT XML_IS_WELL_FORMED_CONTENT ' + + 'XPATH XPATH_EXISTS XMLTABLE XMLNAMESPACES ' + + 'TABLE_TO_XML TABLE_TO_XMLSCHEMA TABLE_TO_XML_AND_XMLSCHEMA ' + + 'QUERY_TO_XML QUERY_TO_XMLSCHEMA QUERY_TO_XML_AND_XMLSCHEMA ' + + 'CURSOR_TO_XML CURSOR_TO_XMLSCHEMA ' + + 'SCHEMA_TO_XML SCHEMA_TO_XMLSCHEMA SCHEMA_TO_XML_AND_XMLSCHEMA ' + + 'DATABASE_TO_XML DATABASE_TO_XMLSCHEMA DATABASE_TO_XML_AND_XMLSCHEMA ' + + 'XMLATTRIBUTES ' + // https://www.postgresql.org/docs/11/static/functions-json.html + + 'TO_JSON TO_JSONB ARRAY_TO_JSON ROW_TO_JSON JSON_BUILD_ARRAY JSONB_BUILD_ARRAY JSON_BUILD_OBJECT ' + + 'JSONB_BUILD_OBJECT JSON_OBJECT JSONB_OBJECT JSON_ARRAY_LENGTH JSONB_ARRAY_LENGTH JSON_EACH ' + + 'JSONB_EACH JSON_EACH_TEXT JSONB_EACH_TEXT JSON_EXTRACT_PATH JSONB_EXTRACT_PATH ' + + 'JSON_OBJECT_KEYS JSONB_OBJECT_KEYS JSON_POPULATE_RECORD JSONB_POPULATE_RECORD JSON_POPULATE_RECORDSET ' + + 'JSONB_POPULATE_RECORDSET JSON_ARRAY_ELEMENTS JSONB_ARRAY_ELEMENTS JSON_ARRAY_ELEMENTS_TEXT ' + + 'JSONB_ARRAY_ELEMENTS_TEXT JSON_TYPEOF JSONB_TYPEOF JSON_TO_RECORD JSONB_TO_RECORD JSON_TO_RECORDSET ' + + 'JSONB_TO_RECORDSET JSON_STRIP_NULLS JSONB_STRIP_NULLS JSONB_SET JSONB_INSERT JSONB_PRETTY ' + // https://www.postgresql.org/docs/11/static/functions-sequence.html + + 'CURRVAL LASTVAL NEXTVAL SETVAL ' + // https://www.postgresql.org/docs/11/static/functions-conditional.html + + 'COALESCE NULLIF GREATEST LEAST ' + // https://www.postgresql.org/docs/11/static/functions-array.html + + 'ARRAY_APPEND ARRAY_CAT ARRAY_NDIMS ARRAY_DIMS ARRAY_FILL ARRAY_LENGTH ARRAY_LOWER ARRAY_POSITION ' + + 'ARRAY_POSITIONS ARRAY_PREPEND ARRAY_REMOVE ARRAY_REPLACE ARRAY_TO_STRING ARRAY_UPPER CARDINALITY ' + + 'STRING_TO_ARRAY UNNEST ' + // https://www.postgresql.org/docs/11/static/functions-range.html + + 'ISEMPTY LOWER_INC UPPER_INC LOWER_INF UPPER_INF RANGE_MERGE ' + // https://www.postgresql.org/docs/11/static/functions-srf.html + + 'GENERATE_SERIES GENERATE_SUBSCRIPTS ' + // https://www.postgresql.org/docs/11/static/functions-info.html + + 'CURRENT_DATABASE CURRENT_QUERY CURRENT_SCHEMA|10 CURRENT_SCHEMAS|10 INET_CLIENT_ADDR INET_CLIENT_PORT ' + + 'INET_SERVER_ADDR INET_SERVER_PORT ROW_SECURITY_ACTIVE FORMAT_TYPE ' + + 'TO_REGCLASS TO_REGPROC TO_REGPROCEDURE TO_REGOPER TO_REGOPERATOR TO_REGTYPE TO_REGNAMESPACE TO_REGROLE ' + + 'COL_DESCRIPTION OBJ_DESCRIPTION SHOBJ_DESCRIPTION ' + + 'TXID_CURRENT TXID_CURRENT_IF_ASSIGNED TXID_CURRENT_SNAPSHOT TXID_SNAPSHOT_XIP TXID_SNAPSHOT_XMAX ' + + 'TXID_SNAPSHOT_XMIN TXID_VISIBLE_IN_SNAPSHOT TXID_STATUS ' + // https://www.postgresql.org/docs/11/static/functions-admin.html + + 'CURRENT_SETTING SET_CONFIG BRIN_SUMMARIZE_NEW_VALUES BRIN_SUMMARIZE_RANGE BRIN_DESUMMARIZE_RANGE ' + + 'GIN_CLEAN_PENDING_LIST ' + // https://www.postgresql.org/docs/11/static/functions-trigger.html + + 'SUPPRESS_REDUNDANT_UPDATES_TRIGGER ' + // ihttps://www.postgresql.org/docs/devel/static/lo-funcs.html + + 'LO_FROM_BYTEA LO_PUT LO_GET LO_CREAT LO_CREATE LO_UNLINK LO_IMPORT LO_EXPORT LOREAD LOWRITE ' + // + + 'GROUPING CAST '; + + const FUNCTIONS_RE = + FUNCTIONS.trim() + .split(' ') + .map(function(val) { return val.split('|')[0]; }) + .join('|'); + + return { + name: 'PostgreSQL', + aliases: [ + 'postgres', + 'postgresql' + ], + supersetOf: "sql", + case_insensitive: true, + keywords: { + keyword: + SQL_KW + PLPGSQL_KW + ROLE_ATTRS, + built_in: + SQL_BI + PLPGSQL_BI + PLPGSQL_EXCEPTIONS + }, + // Forbid some cunstructs from other languages to improve autodetect. In fact + // "[a-z]:" is legal (as part of array slice), but improbabal. + illegal: /:==|\W\s*\(\*|(^|\s)\$[a-z]|\{\{|[a-z]:\s*$|\.\.\.|TO:|DO:/, + contains: [ + // special handling of some words, which are reserved only in some contexts + { + className: 'keyword', + variants: [ + { begin: /\bTEXT\s*SEARCH\b/ }, + { begin: /\b(PRIMARY|FOREIGN|FOR(\s+NO)?)\s+KEY\b/ }, + { begin: /\bPARALLEL\s+(UNSAFE|RESTRICTED|SAFE)\b/ }, + { begin: /\bSTORAGE\s+(PLAIN|EXTERNAL|EXTENDED|MAIN)\b/ }, + { begin: /\bMATCH\s+(FULL|PARTIAL|SIMPLE)\b/ }, + { begin: /\bNULLS\s+(FIRST|LAST)\b/ }, + { begin: /\bEVENT\s+TRIGGER\b/ }, + { begin: /\b(MAPPING|OR)\s+REPLACE\b/ }, + { begin: /\b(FROM|TO)\s+(PROGRAM|STDIN|STDOUT)\b/ }, + { begin: /\b(SHARE|EXCLUSIVE)\s+MODE\b/ }, + { begin: /\b(LEFT|RIGHT)\s+(OUTER\s+)?JOIN\b/ }, + { begin: /\b(FETCH|MOVE)\s+(NEXT|PRIOR|FIRST|LAST|ABSOLUTE|RELATIVE|FORWARD|BACKWARD)\b/ }, + { begin: /\bPRESERVE\s+ROWS\b/ }, + { begin: /\bDISCARD\s+PLANS\b/ }, + { begin: /\bREFERENCING\s+(OLD|NEW)\b/ }, + { begin: /\bSKIP\s+LOCKED\b/ }, + { begin: /\bGROUPING\s+SETS\b/ }, + { begin: /\b(BINARY|INSENSITIVE|SCROLL|NO\s+SCROLL)\s+(CURSOR|FOR)\b/ }, + { begin: /\b(WITH|WITHOUT)\s+HOLD\b/ }, + { begin: /\bWITH\s+(CASCADED|LOCAL)\s+CHECK\s+OPTION\b/ }, + { begin: /\bEXCLUDE\s+(TIES|NO\s+OTHERS)\b/ }, + { begin: /\bFORMAT\s+(TEXT|XML|JSON|YAML)\b/ }, + { begin: /\bSET\s+((SESSION|LOCAL)\s+)?NAMES\b/ }, + { begin: /\bIS\s+(NOT\s+)?UNKNOWN\b/ }, + { begin: /\bSECURITY\s+LABEL\b/ }, + { begin: /\bSTANDALONE\s+(YES|NO|NO\s+VALUE)\b/ }, + { begin: /\bWITH\s+(NO\s+)?DATA\b/ }, + { begin: /\b(FOREIGN|SET)\s+DATA\b/ }, + { begin: /\bSET\s+(CATALOG|CONSTRAINTS)\b/ }, + { begin: /\b(WITH|FOR)\s+ORDINALITY\b/ }, + { begin: /\bIS\s+(NOT\s+)?DOCUMENT\b/ }, + { begin: /\bXML\s+OPTION\s+(DOCUMENT|CONTENT)\b/ }, + { begin: /\b(STRIP|PRESERVE)\s+WHITESPACE\b/ }, + { begin: /\bNO\s+(ACTION|MAXVALUE|MINVALUE)\b/ }, + { begin: /\bPARTITION\s+BY\s+(RANGE|LIST|HASH)\b/ }, + { begin: /\bAT\s+TIME\s+ZONE\b/ }, + { begin: /\bGRANTED\s+BY\b/ }, + { begin: /\bRETURN\s+(QUERY|NEXT)\b/ }, + { begin: /\b(ATTACH|DETACH)\s+PARTITION\b/ }, + { begin: /\bFORCE\s+ROW\s+LEVEL\s+SECURITY\b/ }, + { begin: /\b(INCLUDING|EXCLUDING)\s+(COMMENTS|CONSTRAINTS|DEFAULTS|IDENTITY|INDEXES|STATISTICS|STORAGE|ALL)\b/ }, + { begin: /\bAS\s+(ASSIGNMENT|IMPLICIT|PERMISSIVE|RESTRICTIVE|ENUM|RANGE)\b/ } + ] + }, + // functions named as keywords, followed by '(' + { begin: /\b(FORMAT|FAMILY|VERSION)\s*\(/ + // keywords: { built_in: 'FORMAT FAMILY VERSION' } + }, + // INCLUDE ( ... ) in index_parameters in CREATE TABLE + { + begin: /\bINCLUDE\s*\(/, + keywords: 'INCLUDE' + }, + // not highlight RANGE if not in frame_clause (not 100% correct, but seems satisfactory) + { begin: /\bRANGE(?!\s*(BETWEEN|UNBOUNDED|CURRENT|[-0-9]+))/ }, + // disable highlighting in commands CREATE AGGREGATE/COLLATION/DATABASE/OPERTOR/TEXT SEARCH .../TYPE + // and in PL/pgSQL RAISE ... USING + { begin: /\b(VERSION|OWNER|TEMPLATE|TABLESPACE|CONNECTION\s+LIMIT|PROCEDURE|RESTRICT|JOIN|PARSER|COPY|START|END|COLLATION|INPUT|ANALYZE|STORAGE|LIKE|DEFAULT|DELIMITER|ENCODING|COLUMN|CONSTRAINT|TABLE|SCHEMA)\s*=/ }, + // PG_smth; HAS_some_PRIVILEGE + { + // className: 'built_in', + begin: /\b(PG_\w+?|HAS_[A-Z_]+_PRIVILEGE)\b/, + relevance: 10 + }, + // extract + { + begin: /\bEXTRACT\s*\(/, + end: /\bFROM\b/, + returnEnd: true, + keywords: { + // built_in: 'EXTRACT', + type: 'CENTURY DAY DECADE DOW DOY EPOCH HOUR ISODOW ISOYEAR MICROSECONDS ' + + 'MILLENNIUM MILLISECONDS MINUTE MONTH QUARTER SECOND TIMEZONE TIMEZONE_HOUR ' + + 'TIMEZONE_MINUTE WEEK YEAR' } + }, + // xmlelement, xmlpi - special NAME + { + begin: /\b(XMLELEMENT|XMLPI)\s*\(\s*NAME/, + keywords: { + // built_in: 'XMLELEMENT XMLPI', + keyword: 'NAME' } + }, + // xmlparse, xmlserialize + { + begin: /\b(XMLPARSE|XMLSERIALIZE)\s*\(\s*(DOCUMENT|CONTENT)/, + keywords: { + // built_in: 'XMLPARSE XMLSERIALIZE', + keyword: 'DOCUMENT CONTENT' } + }, + // Sequences. We actually skip everything between CACHE|INCREMENT|MAXVALUE|MINVALUE and + // nearest following numeric constant. Without with trick we find a lot of "keywords" + // in 'avrasm' autodetection test... + { + beginKeywords: 'CACHE INCREMENT MAXVALUE MINVALUE', + end: hljs.C_NUMBER_RE, + returnEnd: true, + keywords: 'BY CACHE INCREMENT MAXVALUE MINVALUE' + }, + // WITH|WITHOUT TIME ZONE as part of datatype + { + className: 'type', + begin: /\b(WITH|WITHOUT)\s+TIME\s+ZONE\b/ + }, + // INTERVAL optional fields + { + className: 'type', + begin: /\bINTERVAL\s+(YEAR|MONTH|DAY|HOUR|MINUTE|SECOND)(\s+TO\s+(MONTH|HOUR|MINUTE|SECOND))?\b/ + }, + // Pseudo-types which allowed only as return type + { + begin: /\bRETURNS\s+(LANGUAGE_HANDLER|TRIGGER|EVENT_TRIGGER|FDW_HANDLER|INDEX_AM_HANDLER|TSM_HANDLER)\b/, + keywords: { + keyword: 'RETURNS', + type: 'LANGUAGE_HANDLER TRIGGER EVENT_TRIGGER FDW_HANDLER INDEX_AM_HANDLER TSM_HANDLER' + } + }, + // Known functions - only when followed by '(' + { begin: '\\b(' + FUNCTIONS_RE + ')\\s*\\(' + // keywords: { built_in: FUNCTIONS } + }, + // Types + { begin: '\\.(' + TYPES_RE + ')\\b' // prevent highlight as type, say, 'oid' in 'pgclass.oid' + }, + { + begin: '\\b(' + TYPES_RE + ')\\s+PATH\\b', // in XMLTABLE + keywords: { + keyword: 'PATH', // hopefully no one would use PATH type in XMLTABLE... + type: TYPES.replace('PATH ', '') + } + }, + { + className: 'type', + begin: '\\b(' + TYPES_RE + ')\\b' + }, + // Strings, see https://www.postgresql.org/docs/11/static/sql-syntax-lexical.html#SQL-SYNTAX-CONSTANTS + { + className: 'string', + begin: '\'', + end: '\'', + contains: [ { begin: '\'\'' } ] + }, + { + className: 'string', + begin: '(e|E|u&|U&)\'', + end: '\'', + contains: [ { begin: '\\\\.' } ], + relevance: 10 + }, + hljs.END_SAME_AS_BEGIN({ + begin: DOLLAR_STRING, + end: DOLLAR_STRING, + contains: [ + { + // actually we want them all except SQL; listed are those with known implementations + // and XML + JSON just in case + subLanguage: [ + 'pgsql', + 'perl', + 'python', + 'tcl', + 'r', + 'lua', + 'java', + 'php', + 'ruby', + 'bash', + 'scheme', + 'xml', + 'json' + ], + endsWithParent: true + } + ] + }), + // identifiers in quotes + { + begin: '"', + end: '"', + contains: [ { begin: '""' } ] + }, + // numbers + hljs.C_NUMBER_MODE, + // comments + hljs.C_BLOCK_COMMENT_MODE, + COMMENT_MODE, + // PL/pgSQL staff + // %ROWTYPE, %TYPE, $n + { + className: 'meta', + variants: [ + { // %TYPE, %ROWTYPE + begin: '%(ROW)?TYPE', + relevance: 10 + }, + { // $n + begin: '\\$\\d+' }, + { // #compiler option + begin: '^#\\w', + end: '$' + } + ] + }, + // <> + { + className: 'symbol', + begin: LABEL, + relevance: 10 + } + ] + }; +} + +export { pgsql as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/pgsql.js.js b/frontend/node_modules/highlight.js/es/languages/pgsql.js.js new file mode 100644 index 0000000..720480d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/pgsql.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/pgsql" instead of "highlight.js/lib/languages/pgsql.js"' + ); + } + } + emitWarning(); + import lang from './pgsql.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/php-template.js b/frontend/node_modules/highlight.js/es/languages/php-template.js new file mode 100644 index 0000000..6dffd51 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/php-template.js @@ -0,0 +1,54 @@ +/* +Language: PHP Template +Requires: xml.js, php.js +Author: Josh Goebel +Website: https://www.php.net +Category: common +*/ + +function phpTemplate(hljs) { + return { + name: "PHP template", + subLanguage: 'xml', + contains: [ + { + begin: /<\?(php|=)?/, + end: /\?>/, + subLanguage: 'php', + contains: [ + // We don't want the php closing tag ?> to close the PHP block when + // inside any of the following blocks: + { + begin: '/\\*', + end: '\\*/', + skip: true + }, + { + begin: 'b"', + end: '"', + skip: true + }, + { + begin: 'b\'', + end: '\'', + skip: true + }, + hljs.inherit(hljs.APOS_STRING_MODE, { + illegal: null, + className: null, + contains: null, + skip: true + }), + hljs.inherit(hljs.QUOTE_STRING_MODE, { + illegal: null, + className: null, + contains: null, + skip: true + }) + ] + } + ] + }; +} + +export { phpTemplate as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/php-template.js.js b/frontend/node_modules/highlight.js/es/languages/php-template.js.js new file mode 100644 index 0000000..88debfa --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/php-template.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/php-template" instead of "highlight.js/lib/languages/php-template.js"' + ); + } + } + emitWarning(); + import lang from './php-template.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/php.js b/frontend/node_modules/highlight.js/es/languages/php.js new file mode 100644 index 0000000..da94bf2 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/php.js @@ -0,0 +1,625 @@ +/* +Language: PHP +Author: Victor Karamzin +Contributors: Evgeny Stepanischev , Ivan Sagalaev +Website: https://www.php.net +Category: common +*/ + +/** + * @param {HLJSApi} hljs + * @returns {LanguageDetail} + * */ +function php(hljs) { + const regex = hljs.regex; + // negative look-ahead tries to avoid matching patterns that are not + // Perl at all like $ident$, @ident@, etc. + const NOT_PERL_ETC = /(?![A-Za-z0-9])(?![$])/; + const IDENT_RE = regex.concat( + /[a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*/, + NOT_PERL_ETC); + // Will not detect camelCase classes + const PASCAL_CASE_CLASS_NAME_RE = regex.concat( + /(\\?[A-Z][a-z0-9_\x7f-\xff]+|\\?[A-Z]+(?=[A-Z][a-z0-9_\x7f-\xff])){1,}/, + NOT_PERL_ETC); + const UPCASE_NAME_RE = regex.concat( + /[A-Z]+/, + NOT_PERL_ETC); + const VARIABLE = { + scope: 'variable', + match: '\\$+' + IDENT_RE, + }; + const PREPROCESSOR = { + scope: "meta", + variants: [ + { begin: /<\?php/, relevance: 10 }, // boost for obvious PHP + { begin: /<\?=/ }, + // less relevant per PSR-1 which says not to use short-tags + { begin: /<\?/, relevance: 0.1 }, + { begin: /\?>/ } // end php tag + ] + }; + const SUBST = { + scope: 'subst', + variants: [ + { begin: /\$\w+/ }, + { + begin: /\{\$/, + end: /\}/ + } + ] + }; + const SINGLE_QUOTED = hljs.inherit(hljs.APOS_STRING_MODE, { illegal: null, }); + const DOUBLE_QUOTED = hljs.inherit(hljs.QUOTE_STRING_MODE, { + illegal: null, + contains: hljs.QUOTE_STRING_MODE.contains.concat(SUBST), + }); + + const HEREDOC = { + begin: /<<<[ \t]*(?:(\w+)|"(\w+)")\n/, + end: /[ \t]*(\w+)\b/, + contains: hljs.QUOTE_STRING_MODE.contains.concat(SUBST), + 'on:begin': (m, resp) => { resp.data._beginMatch = m[1] || m[2]; }, + 'on:end': (m, resp) => { if (resp.data._beginMatch !== m[1]) resp.ignoreMatch(); }, + }; + + const NOWDOC = hljs.END_SAME_AS_BEGIN({ + begin: /<<<[ \t]*'(\w+)'\n/, + end: /[ \t]*(\w+)\b/, + }); + // list of valid whitespaces because non-breaking space might be part of a IDENT_RE + const WHITESPACE = '[ \t\n]'; + const STRING = { + scope: 'string', + variants: [ + DOUBLE_QUOTED, + SINGLE_QUOTED, + HEREDOC, + NOWDOC + ] + }; + const NUMBER = { + scope: 'number', + variants: [ + { begin: `\\b0[bB][01]+(?:_[01]+)*\\b` }, // Binary w/ underscore support + { begin: `\\b0[oO][0-7]+(?:_[0-7]+)*\\b` }, // Octals w/ underscore support + { begin: `\\b0[xX][\\da-fA-F]+(?:_[\\da-fA-F]+)*\\b` }, // Hex w/ underscore support + // Decimals w/ underscore support, with optional fragments and scientific exponent (e) suffix. + { begin: `(?:\\b\\d+(?:_\\d+)*(\\.(?:\\d+(?:_\\d+)*))?|\\B\\.\\d+)(?:[eE][+-]?\\d+)?` } + ], + relevance: 0 + }; + const LITERALS = [ + "false", + "null", + "true" + ]; + const KWS = [ + // Magic constants: + // + "__CLASS__", + "__DIR__", + "__FILE__", + "__FUNCTION__", + "__COMPILER_HALT_OFFSET__", + "__LINE__", + "__METHOD__", + "__NAMESPACE__", + "__TRAIT__", + // Function that look like language construct or language construct that look like function: + // List of keywords that may not require parenthesis + "die", + "echo", + "exit", + "include", + "include_once", + "print", + "require", + "require_once", + // These are not language construct (function) but operate on the currently-executing function and can access the current symbol table + // 'compact extract func_get_arg func_get_args func_num_args get_called_class get_parent_class ' + + // Other keywords: + // + // + "array", + "abstract", + "and", + "as", + "binary", + "bool", + "boolean", + "break", + "callable", + "case", + "catch", + "class", + "clone", + "const", + "continue", + "declare", + "default", + "do", + "double", + "else", + "elseif", + "empty", + "enddeclare", + "endfor", + "endforeach", + "endif", + "endswitch", + "endwhile", + "enum", + "eval", + "extends", + "final", + "finally", + "float", + "for", + "foreach", + "from", + "global", + "goto", + "if", + "implements", + "instanceof", + "insteadof", + "int", + "integer", + "interface", + "isset", + "iterable", + "list", + "match|0", + "mixed", + "new", + "never", + "object", + "or", + "private", + "protected", + "public", + "readonly", + "real", + "return", + "string", + "switch", + "throw", + "trait", + "try", + "unset", + "use", + "var", + "void", + "while", + "xor", + "yield" + ]; + + const BUILT_INS = [ + // Standard PHP library: + // + "Error|0", + "AppendIterator", + "ArgumentCountError", + "ArithmeticError", + "ArrayIterator", + "ArrayObject", + "AssertionError", + "BadFunctionCallException", + "BadMethodCallException", + "CachingIterator", + "CallbackFilterIterator", + "CompileError", + "Countable", + "DirectoryIterator", + "DivisionByZeroError", + "DomainException", + "EmptyIterator", + "ErrorException", + "Exception", + "FilesystemIterator", + "FilterIterator", + "GlobIterator", + "InfiniteIterator", + "InvalidArgumentException", + "IteratorIterator", + "LengthException", + "LimitIterator", + "LogicException", + "MultipleIterator", + "NoRewindIterator", + "OutOfBoundsException", + "OutOfRangeException", + "OuterIterator", + "OverflowException", + "ParentIterator", + "ParseError", + "RangeException", + "RecursiveArrayIterator", + "RecursiveCachingIterator", + "RecursiveCallbackFilterIterator", + "RecursiveDirectoryIterator", + "RecursiveFilterIterator", + "RecursiveIterator", + "RecursiveIteratorIterator", + "RecursiveRegexIterator", + "RecursiveTreeIterator", + "RegexIterator", + "RuntimeException", + "SeekableIterator", + "SplDoublyLinkedList", + "SplFileInfo", + "SplFileObject", + "SplFixedArray", + "SplHeap", + "SplMaxHeap", + "SplMinHeap", + "SplObjectStorage", + "SplObserver", + "SplPriorityQueue", + "SplQueue", + "SplStack", + "SplSubject", + "SplTempFileObject", + "TypeError", + "UnderflowException", + "UnexpectedValueException", + "UnhandledMatchError", + // Reserved interfaces: + // + "ArrayAccess", + "BackedEnum", + "Closure", + "Fiber", + "Generator", + "Iterator", + "IteratorAggregate", + "Serializable", + "Stringable", + "Throwable", + "Traversable", + "UnitEnum", + "WeakReference", + "WeakMap", + // Reserved classes: + // + "Directory", + "__PHP_Incomplete_Class", + "parent", + "php_user_filter", + "self", + "static", + "stdClass" + ]; + + /** Dual-case keywords + * + * ["then","FILE"] => + * ["then", "THEN", "FILE", "file"] + * + * @param {string[]} items */ + const dualCase = (items) => { + /** @type string[] */ + const result = []; + items.forEach(item => { + result.push(item); + if (item.toLowerCase() === item) { + result.push(item.toUpperCase()); + } else { + result.push(item.toLowerCase()); + } + }); + return result; + }; + + const KEYWORDS = { + keyword: KWS, + literal: dualCase(LITERALS), + built_in: BUILT_INS, + }; + + /** + * @param {string[]} items */ + const normalizeKeywords = (items) => { + return items.map(item => { + return item.replace(/\|\d+$/, ""); + }); + }; + + const CONSTRUCTOR_CALL = { variants: [ + { + match: [ + /new/, + regex.concat(WHITESPACE, "+"), + // to prevent built ins from being confused as the class constructor call + regex.concat("(?!", normalizeKeywords(BUILT_INS).join("\\b|"), "\\b)"), + PASCAL_CASE_CLASS_NAME_RE, + ], + scope: { + 1: "keyword", + 4: "title.class", + }, + } + ] }; + + const CONSTANT_REFERENCE = regex.concat(IDENT_RE, "\\b(?!\\()"); + + const LEFT_AND_RIGHT_SIDE_OF_DOUBLE_COLON = { variants: [ + { + match: [ + regex.concat( + /::/, + regex.lookahead(/(?!class\b)/) + ), + CONSTANT_REFERENCE, + ], + scope: { 2: "variable.constant", }, + }, + { + match: [ + /::/, + /class/, + ], + scope: { 2: "variable.language", }, + }, + { + match: [ + PASCAL_CASE_CLASS_NAME_RE, + regex.concat( + /::/, + regex.lookahead(/(?!class\b)/) + ), + CONSTANT_REFERENCE, + ], + scope: { + 1: "title.class", + 3: "variable.constant", + }, + }, + { + match: [ + PASCAL_CASE_CLASS_NAME_RE, + regex.concat( + "::", + regex.lookahead(/(?!class\b)/) + ), + ], + scope: { 1: "title.class", }, + }, + { + match: [ + PASCAL_CASE_CLASS_NAME_RE, + /::/, + /class/, + ], + scope: { + 1: "title.class", + 3: "variable.language", + }, + } + ] }; + + const NAMED_ARGUMENT = { + scope: 'attr', + match: regex.concat(IDENT_RE, regex.lookahead(':'), regex.lookahead(/(?!::)/)), + }; + const PARAMS_MODE = { + relevance: 0, + begin: /\(/, + end: /\)/, + keywords: KEYWORDS, + contains: [ + NAMED_ARGUMENT, + VARIABLE, + LEFT_AND_RIGHT_SIDE_OF_DOUBLE_COLON, + hljs.C_BLOCK_COMMENT_MODE, + STRING, + NUMBER, + CONSTRUCTOR_CALL, + ], + }; + const FUNCTION_INVOKE = { + relevance: 0, + match: [ + /\b/, + // to prevent keywords from being confused as the function title + regex.concat("(?!fn\\b|function\\b|", normalizeKeywords(KWS).join("\\b|"), "|", normalizeKeywords(BUILT_INS).join("\\b|"), "\\b)"), + IDENT_RE, + regex.concat(WHITESPACE, "*"), + regex.lookahead(/(?=\()/) + ], + scope: { 3: "title.function.invoke", }, + contains: [ PARAMS_MODE ] + }; + PARAMS_MODE.contains.push(FUNCTION_INVOKE); + + const ATTRIBUTE_CONTAINS = [ + NAMED_ARGUMENT, + LEFT_AND_RIGHT_SIDE_OF_DOUBLE_COLON, + hljs.C_BLOCK_COMMENT_MODE, + STRING, + NUMBER, + CONSTRUCTOR_CALL, + ]; + + const ATTRIBUTES = { + begin: regex.concat(/#\[\s*\\?/, + regex.either( + PASCAL_CASE_CLASS_NAME_RE, + UPCASE_NAME_RE + ) + ), + beginScope: "meta", + end: /]/, + endScope: "meta", + keywords: { + literal: LITERALS, + keyword: [ + 'new', + 'array', + ] + }, + contains: [ + { + begin: /\[/, + end: /]/, + keywords: { + literal: LITERALS, + keyword: [ + 'new', + 'array', + ] + }, + contains: [ + 'self', + ...ATTRIBUTE_CONTAINS, + ] + }, + ...ATTRIBUTE_CONTAINS, + { + scope: 'meta', + variants: [ + { match: PASCAL_CASE_CLASS_NAME_RE }, + { match: UPCASE_NAME_RE } + ] + } + ] + }; + + return { + case_insensitive: false, + keywords: KEYWORDS, + contains: [ + ATTRIBUTES, + hljs.HASH_COMMENT_MODE, + hljs.COMMENT('//', '$'), + hljs.COMMENT( + '/\\*', + '\\*/', + { contains: [ + { + scope: 'doctag', + match: '@[A-Za-z]+' + } + ] } + ), + { + match: /__halt_compiler\(\);/, + keywords: '__halt_compiler', + starts: { + scope: "comment", + end: hljs.MATCH_NOTHING_RE, + contains: [ + { + match: /\?>/, + scope: "meta", + endsParent: true + } + ] + } + }, + PREPROCESSOR, + { + scope: 'variable.language', + match: /\$this\b/ + }, + VARIABLE, + FUNCTION_INVOKE, + LEFT_AND_RIGHT_SIDE_OF_DOUBLE_COLON, + { + match: [ + /const/, + /\s/, + IDENT_RE, + ], + scope: { + 1: "keyword", + 3: "variable.constant", + }, + }, + CONSTRUCTOR_CALL, + { + scope: 'function', + relevance: 0, + beginKeywords: 'fn function', + end: /[;{]/, + excludeEnd: true, + illegal: '[$%\\[]', + contains: [ + { beginKeywords: 'use', }, + hljs.UNDERSCORE_TITLE_MODE, + { + begin: '=>', // No markup, just a relevance booster + endsParent: true + }, + { + scope: 'params', + begin: '\\(', + end: '\\)', + excludeBegin: true, + excludeEnd: true, + keywords: KEYWORDS, + contains: [ + 'self', + ATTRIBUTES, + VARIABLE, + LEFT_AND_RIGHT_SIDE_OF_DOUBLE_COLON, + hljs.C_BLOCK_COMMENT_MODE, + STRING, + NUMBER + ] + }, + ] + }, + { + scope: 'class', + variants: [ + { + beginKeywords: "enum", + illegal: /[($"]/ + }, + { + beginKeywords: "class interface trait", + illegal: /[:($"]/ + } + ], + relevance: 0, + end: /\{/, + excludeEnd: true, + contains: [ + { beginKeywords: 'extends implements' }, + hljs.UNDERSCORE_TITLE_MODE + ] + }, + // both use and namespace still use "old style" rules (vs multi-match) + // because the namespace name can include `\` and we still want each + // element to be treated as its own *individual* title + { + beginKeywords: 'namespace', + relevance: 0, + end: ';', + illegal: /[.']/, + contains: [ hljs.inherit(hljs.UNDERSCORE_TITLE_MODE, { scope: "title.class" }) ] + }, + { + beginKeywords: 'use', + relevance: 0, + end: ';', + contains: [ + // TODO: title.function vs title.class + { + match: /\b(as|const|function)\b/, + scope: "keyword" + }, + // TODO: could be title.class or title.function + hljs.UNDERSCORE_TITLE_MODE + ] + }, + STRING, + NUMBER, + ] + }; +} + +export { php as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/php.js.js b/frontend/node_modules/highlight.js/es/languages/php.js.js new file mode 100644 index 0000000..01a92f5 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/php.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/php" instead of "highlight.js/lib/languages/php.js"' + ); + } + } + emitWarning(); + import lang from './php.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/plaintext.js b/frontend/node_modules/highlight.js/es/languages/plaintext.js new file mode 100644 index 0000000..d119222 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/plaintext.js @@ -0,0 +1,19 @@ +/* +Language: Plain text +Author: Egor Rogov (e.rogov@postgrespro.ru) +Description: Plain text without any highlighting. +Category: common +*/ + +function plaintext(hljs) { + return { + name: 'Plain text', + aliases: [ + 'text', + 'txt' + ], + disableAutodetect: true + }; +} + +export { plaintext as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/plaintext.js.js b/frontend/node_modules/highlight.js/es/languages/plaintext.js.js new file mode 100644 index 0000000..9b1ccd3 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/plaintext.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/plaintext" instead of "highlight.js/lib/languages/plaintext.js"' + ); + } + } + emitWarning(); + import lang from './plaintext.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/pony.js b/frontend/node_modules/highlight.js/es/languages/pony.js new file mode 100644 index 0000000..fa891e5 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/pony.js @@ -0,0 +1,90 @@ +/* +Language: Pony +Author: Joe Eli McIlvain +Description: Pony is an open-source, object-oriented, actor-model, + capabilities-secure, high performance programming language. +Website: https://www.ponylang.io +Category: system +*/ + +function pony(hljs) { + const KEYWORDS = { + keyword: + 'actor addressof and as be break class compile_error compile_intrinsic ' + + 'consume continue delegate digestof do else elseif embed end error ' + + 'for fun if ifdef in interface is isnt lambda let match new not object ' + + 'or primitive recover repeat return struct then trait try type until ' + + 'use var where while with xor', + meta: + 'iso val tag trn box ref', + literal: + 'this false true' + }; + + const TRIPLE_QUOTE_STRING_MODE = { + className: 'string', + begin: '"""', + end: '"""', + relevance: 10 + }; + + const QUOTE_STRING_MODE = { + className: 'string', + begin: '"', + end: '"', + contains: [ hljs.BACKSLASH_ESCAPE ] + }; + + const SINGLE_QUOTE_CHAR_MODE = { + className: 'string', + begin: '\'', + end: '\'', + contains: [ hljs.BACKSLASH_ESCAPE ], + relevance: 0 + }; + + const TYPE_NAME = { + className: 'type', + begin: '\\b_?[A-Z][\\w]*', + relevance: 0 + }; + + const PRIMED_NAME = { + begin: hljs.IDENT_RE + '\'', + relevance: 0 + }; + + const NUMBER_MODE = { + className: 'number', + begin: '(-?)(\\b0[xX][a-fA-F0-9]+|\\b0[bB][01]+|(\\b\\d+(_\\d+)?(\\.\\d*)?|\\.\\d+)([eE][-+]?\\d+)?)', + relevance: 0 + }; + + /** + * The `FUNCTION` and `CLASS` modes were intentionally removed to simplify + * highlighting and fix cases like + * ``` + * interface Iterator[A: A] + * fun has_next(): Bool + * fun next(): A? + * ``` + * where it is valid to have a function head without a body + */ + + return { + name: 'Pony', + keywords: KEYWORDS, + contains: [ + TYPE_NAME, + TRIPLE_QUOTE_STRING_MODE, + QUOTE_STRING_MODE, + SINGLE_QUOTE_CHAR_MODE, + PRIMED_NAME, + NUMBER_MODE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }; +} + +export { pony as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/pony.js.js b/frontend/node_modules/highlight.js/es/languages/pony.js.js new file mode 100644 index 0000000..979995a --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/pony.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/pony" instead of "highlight.js/lib/languages/pony.js"' + ); + } + } + emitWarning(); + import lang from './pony.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/powershell.js b/frontend/node_modules/highlight.js/es/languages/powershell.js new file mode 100644 index 0000000..ec5f5e4 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/powershell.js @@ -0,0 +1,317 @@ +/* +Language: PowerShell +Description: PowerShell is a task-based command-line shell and scripting language built on .NET. +Author: David Mohundro +Contributors: Nicholas Blumhardt , Victor Zhou , Nicolas Le Gall +Website: https://docs.microsoft.com/en-us/powershell/ +Category: scripting +*/ + +function powershell(hljs) { + const TYPES = [ + "string", + "char", + "byte", + "int", + "long", + "bool", + "decimal", + "single", + "double", + "DateTime", + "xml", + "array", + "hashtable", + "void" + ]; + + // https://docs.microsoft.com/en-us/powershell/scripting/developer/cmdlet/approved-verbs-for-windows-powershell-commands + const VALID_VERBS = + 'Add|Clear|Close|Copy|Enter|Exit|Find|Format|Get|Hide|Join|Lock|' + + 'Move|New|Open|Optimize|Pop|Push|Redo|Remove|Rename|Reset|Resize|' + + 'Search|Select|Set|Show|Skip|Split|Step|Switch|Undo|Unlock|' + + 'Watch|Backup|Checkpoint|Compare|Compress|Convert|ConvertFrom|' + + 'ConvertTo|Dismount|Edit|Expand|Export|Group|Import|Initialize|' + + 'Limit|Merge|Mount|Out|Publish|Restore|Save|Sync|Unpublish|Update|' + + 'Approve|Assert|Build|Complete|Confirm|Deny|Deploy|Disable|Enable|Install|Invoke|' + + 'Register|Request|Restart|Resume|Start|Stop|Submit|Suspend|Uninstall|' + + 'Unregister|Wait|Debug|Measure|Ping|Repair|Resolve|Test|Trace|Connect|' + + 'Disconnect|Read|Receive|Send|Write|Block|Grant|Protect|Revoke|Unblock|' + + 'Unprotect|Use|ForEach|Sort|Tee|Where'; + + const COMPARISON_OPERATORS = + '-and|-as|-band|-bnot|-bor|-bxor|-casesensitive|-ccontains|-ceq|-cge|-cgt|' + + '-cle|-clike|-clt|-cmatch|-cne|-cnotcontains|-cnotlike|-cnotmatch|-contains|' + + '-creplace|-csplit|-eq|-exact|-f|-file|-ge|-gt|-icontains|-ieq|-ige|-igt|' + + '-ile|-ilike|-ilt|-imatch|-in|-ine|-inotcontains|-inotlike|-inotmatch|' + + '-ireplace|-is|-isnot|-isplit|-join|-le|-like|-lt|-match|-ne|-not|' + + '-notcontains|-notin|-notlike|-notmatch|-or|-regex|-replace|-shl|-shr|' + + '-split|-wildcard|-xor'; + + const KEYWORDS = { + $pattern: /-?[A-z\.\-]+\b/, + keyword: + 'if else foreach return do while until elseif begin for trap data dynamicparam ' + + 'end break throw param continue finally in switch exit filter try process catch ' + + 'hidden static parameter', + // "echo" relevance has been set to 0 to avoid auto-detect conflicts with shell transcripts + built_in: + 'ac asnp cat cd CFS chdir clc clear clhy cli clp cls clv cnsn compare copy cp ' + + 'cpi cpp curl cvpa dbp del diff dir dnsn ebp echo|0 epal epcsv epsn erase etsn exsn fc fhx ' + + 'fl ft fw gal gbp gc gcb gci gcm gcs gdr gerr ghy gi gin gjb gl gm gmo gp gps gpv group ' + + 'gsn gsnp gsv gtz gu gv gwmi h history icm iex ihy ii ipal ipcsv ipmo ipsn irm ise iwmi ' + + 'iwr kill lp ls man md measure mi mount move mp mv nal ndr ni nmo npssc nsn nv ogv oh ' + + 'popd ps pushd pwd r rbp rcjb rcsn rd rdr ren ri rjb rm rmdir rmo rni rnp rp rsn rsnp ' + + 'rujb rv rvpa rwmi sajb sal saps sasv sbp sc scb select set shcm si sl sleep sls sort sp ' + + 'spjb spps spsv start stz sujb sv swmi tee trcm type wget where wjb write' + // TODO: 'validate[A-Z]+' can't work in keywords + }; + + const TITLE_NAME_RE = /\w[\w\d]*((-)[\w\d]+)*/; + + const BACKTICK_ESCAPE = { + begin: '`[\\s\\S]', + relevance: 0 + }; + + const VAR = { + className: 'variable', + variants: [ + { begin: /\$\B/ }, + { + className: 'keyword', + begin: /\$this/ + }, + { begin: /\$[\w\d][\w\d_:]*/ } + ] + }; + + const LITERAL = { + className: 'literal', + begin: /\$(null|true|false)\b/ + }; + + const QUOTE_STRING = { + className: "string", + variants: [ + { + begin: /"/, + end: /"/ + }, + { + begin: /@"/, + end: /^"@/ + } + ], + contains: [ + BACKTICK_ESCAPE, + VAR, + { + className: 'variable', + begin: /\$[A-z]/, + end: /[^A-z]/ + } + ] + }; + + const APOS_STRING = { + className: 'string', + variants: [ + { + begin: /'/, + end: /'/ + }, + { + begin: /@'/, + end: /^'@/ + } + ] + }; + + const PS_HELPTAGS = { + className: "doctag", + variants: [ + /* no paramater help tags */ + { begin: /\.(synopsis|description|example|inputs|outputs|notes|link|component|role|functionality)/ }, + /* one parameter help tags */ + { begin: /\.(parameter|forwardhelptargetname|forwardhelpcategory|remotehelprunspace|externalhelp)\s+\S+/ } + ] + }; + + const PS_COMMENT = hljs.inherit( + hljs.COMMENT(null, null), + { + variants: [ + /* single-line comment */ + { + begin: /#/, + end: /$/ + }, + /* multi-line comment */ + { + begin: /<#/, + end: /#>/ + } + ], + contains: [ PS_HELPTAGS ] + } + ); + + const CMDLETS = { + className: 'built_in', + variants: [ { begin: '('.concat(VALID_VERBS, ')+(-)[\\w\\d]+') } ] + }; + + const PS_CLASS = { + className: 'class', + beginKeywords: 'class enum', + end: /\s*[{]/, + excludeEnd: true, + relevance: 0, + contains: [ hljs.TITLE_MODE ] + }; + + const PS_FUNCTION = { + className: 'function', + begin: /function\s+/, + end: /\s*\{|$/, + excludeEnd: true, + returnBegin: true, + relevance: 0, + contains: [ + { + begin: "function", + relevance: 0, + className: "keyword" + }, + { + className: "title", + begin: TITLE_NAME_RE, + relevance: 0 + }, + { + begin: /\(/, + end: /\)/, + className: "params", + relevance: 0, + contains: [ VAR ] + } + // CMDLETS + ] + }; + + // Using statment, plus type, plus assembly name. + const PS_USING = { + begin: /using\s/, + end: /$/, + returnBegin: true, + contains: [ + QUOTE_STRING, + APOS_STRING, + { + className: 'keyword', + begin: /(using|assembly|command|module|namespace|type)/ + } + ] + }; + + // Comperison operators & function named parameters. + const PS_ARGUMENTS = { variants: [ + // PS literals are pretty verbose so it's a good idea to accent them a bit. + { + className: 'operator', + begin: '('.concat(COMPARISON_OPERATORS, ')\\b') + }, + { + className: 'literal', + begin: /(-){1,2}[\w\d-]+/, + relevance: 0 + } + ] }; + + const HASH_SIGNS = { + className: 'selector-tag', + begin: /@\B/, + relevance: 0 + }; + + // It's a very general rule so I'll narrow it a bit with some strict boundaries + // to avoid any possible false-positive collisions! + const PS_METHODS = { + className: 'function', + begin: /\[.*\]\s*[\w]+[ ]??\(/, + end: /$/, + returnBegin: true, + relevance: 0, + contains: [ + { + className: 'keyword', + begin: '('.concat( + KEYWORDS.keyword.toString().replace(/\s/g, '|' + ), ')\\b'), + endsParent: true, + relevance: 0 + }, + hljs.inherit(hljs.TITLE_MODE, { endsParent: true }) + ] + }; + + const GENTLEMANS_SET = [ + // STATIC_MEMBER, + PS_METHODS, + PS_COMMENT, + BACKTICK_ESCAPE, + hljs.NUMBER_MODE, + QUOTE_STRING, + APOS_STRING, + // PS_NEW_OBJECT_TYPE, + CMDLETS, + VAR, + LITERAL, + HASH_SIGNS + ]; + + const PS_TYPE = { + begin: /\[/, + end: /\]/, + excludeBegin: true, + excludeEnd: true, + relevance: 0, + contains: [].concat( + 'self', + GENTLEMANS_SET, + { + begin: "(" + TYPES.join("|") + ")", + className: "built_in", + relevance: 0 + }, + { + className: 'type', + begin: /[\.\w\d]+/, + relevance: 0 + } + ) + }; + + PS_METHODS.contains.unshift(PS_TYPE); + + return { + name: 'PowerShell', + aliases: [ + "pwsh", + "ps", + "ps1" + ], + case_insensitive: true, + keywords: KEYWORDS, + contains: GENTLEMANS_SET.concat( + PS_CLASS, + PS_FUNCTION, + PS_USING, + PS_ARGUMENTS, + PS_TYPE + ) + }; +} + +export { powershell as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/powershell.js.js b/frontend/node_modules/highlight.js/es/languages/powershell.js.js new file mode 100644 index 0000000..a8eff38 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/powershell.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/powershell" instead of "highlight.js/lib/languages/powershell.js"' + ); + } + } + emitWarning(); + import lang from './powershell.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/processing.js b/frontend/node_modules/highlight.js/es/languages/processing.js new file mode 100644 index 0000000..11ef9b6 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/processing.js @@ -0,0 +1,434 @@ +/* +Language: Processing +Description: Processing is a flexible software sketchbook and a language for learning how to code within the context of the visual arts. +Author: Erik Paluka +Website: https://processing.org +Category: graphics +*/ + +function processing(hljs) { + const regex = hljs.regex; + const BUILT_INS = [ + "displayHeight", + "displayWidth", + "mouseY", + "mouseX", + "mousePressed", + "pmouseX", + "pmouseY", + "key", + "keyCode", + "pixels", + "focused", + "frameCount", + "frameRate", + "height", + "width", + "size", + "createGraphics", + "beginDraw", + "createShape", + "loadShape", + "PShape", + "arc", + "ellipse", + "line", + "point", + "quad", + "rect", + "triangle", + "bezier", + "bezierDetail", + "bezierPoint", + "bezierTangent", + "curve", + "curveDetail", + "curvePoint", + "curveTangent", + "curveTightness", + "shape", + "shapeMode", + "beginContour", + "beginShape", + "bezierVertex", + "curveVertex", + "endContour", + "endShape", + "quadraticVertex", + "vertex", + "ellipseMode", + "noSmooth", + "rectMode", + "smooth", + "strokeCap", + "strokeJoin", + "strokeWeight", + "mouseClicked", + "mouseDragged", + "mouseMoved", + "mousePressed", + "mouseReleased", + "mouseWheel", + "keyPressed", + "keyPressedkeyReleased", + "keyTyped", + "print", + "println", + "save", + "saveFrame", + "day", + "hour", + "millis", + "minute", + "month", + "second", + "year", + "background", + "clear", + "colorMode", + "fill", + "noFill", + "noStroke", + "stroke", + "alpha", + "blue", + "brightness", + "color", + "green", + "hue", + "lerpColor", + "red", + "saturation", + "modelX", + "modelY", + "modelZ", + "screenX", + "screenY", + "screenZ", + "ambient", + "emissive", + "shininess", + "specular", + "add", + "createImage", + "beginCamera", + "camera", + "endCamera", + "frustum", + "ortho", + "perspective", + "printCamera", + "printProjection", + "cursor", + "frameRate", + "noCursor", + "exit", + "loop", + "noLoop", + "popStyle", + "pushStyle", + "redraw", + "binary", + "boolean", + "byte", + "char", + "float", + "hex", + "int", + "str", + "unbinary", + "unhex", + "join", + "match", + "matchAll", + "nf", + "nfc", + "nfp", + "nfs", + "split", + "splitTokens", + "trim", + "append", + "arrayCopy", + "concat", + "expand", + "reverse", + "shorten", + "sort", + "splice", + "subset", + "box", + "sphere", + "sphereDetail", + "createInput", + "createReader", + "loadBytes", + "loadJSONArray", + "loadJSONObject", + "loadStrings", + "loadTable", + "loadXML", + "open", + "parseXML", + "saveTable", + "selectFolder", + "selectInput", + "beginRaw", + "beginRecord", + "createOutput", + "createWriter", + "endRaw", + "endRecord", + "PrintWritersaveBytes", + "saveJSONArray", + "saveJSONObject", + "saveStream", + "saveStrings", + "saveXML", + "selectOutput", + "popMatrix", + "printMatrix", + "pushMatrix", + "resetMatrix", + "rotate", + "rotateX", + "rotateY", + "rotateZ", + "scale", + "shearX", + "shearY", + "translate", + "ambientLight", + "directionalLight", + "lightFalloff", + "lights", + "lightSpecular", + "noLights", + "normal", + "pointLight", + "spotLight", + "image", + "imageMode", + "loadImage", + "noTint", + "requestImage", + "tint", + "texture", + "textureMode", + "textureWrap", + "blend", + "copy", + "filter", + "get", + "loadPixels", + "set", + "updatePixels", + "blendMode", + "loadShader", + "PShaderresetShader", + "shader", + "createFont", + "loadFont", + "text", + "textFont", + "textAlign", + "textLeading", + "textMode", + "textSize", + "textWidth", + "textAscent", + "textDescent", + "abs", + "ceil", + "constrain", + "dist", + "exp", + "floor", + "lerp", + "log", + "mag", + "map", + "max", + "min", + "norm", + "pow", + "round", + "sq", + "sqrt", + "acos", + "asin", + "atan", + "atan2", + "cos", + "degrees", + "radians", + "sin", + "tan", + "noise", + "noiseDetail", + "noiseSeed", + "random", + "randomGaussian", + "randomSeed" + ]; + const IDENT = hljs.IDENT_RE; + const FUNC_NAME = { variants: [ + { + match: regex.concat(regex.either(...BUILT_INS), regex.lookahead(/\s*\(/)), + className: "built_in" + }, + { + relevance: 0, + match: regex.concat( + /\b(?!for|if|while)/, + IDENT, regex.lookahead(/\s*\(/)), + className: "title.function" + } + ] }; + const NEW_CLASS = { + match: [ + /new\s+/, + IDENT + ], + className: { + 1: "keyword", + 2: "class.title" + } + }; + const PROPERTY = { + relevance: 0, + match: [ + /\./, + IDENT + ], + className: { 2: "property" } + }; + const CLASS = { + variants: [ + { match: [ + /class/, + /\s+/, + IDENT, + /\s+/, + /extends/, + /\s+/, + IDENT + ] }, + { match: [ + /class/, + /\s+/, + IDENT + ] } + ], + className: { + 1: "keyword", + 3: "title.class", + 5: "keyword", + 7: "title.class.inherited" + } + }; + + const TYPES = [ + "boolean", + "byte", + "char", + "color", + "double", + "float", + "int", + "long", + "short", + ]; + const CLASSES = [ + "BufferedReader", + "PVector", + "PFont", + "PImage", + "PGraphics", + "HashMap", + "String", + "Array", + "FloatDict", + "ArrayList", + "FloatList", + "IntDict", + "IntList", + "JSONArray", + "JSONObject", + "Object", + "StringDict", + "StringList", + "Table", + "TableRow", + "XML" + ]; + const JAVA_KEYWORDS = [ + "abstract", + "assert", + "break", + "case", + "catch", + "const", + "continue", + "default", + "else", + "enum", + "final", + "finally", + "for", + "if", + "import", + "instanceof", + "long", + "native", + "new", + "package", + "private", + "private", + "protected", + "protected", + "public", + "public", + "return", + "static", + "strictfp", + "switch", + "synchronized", + "throw", + "throws", + "transient", + "try", + "void", + "volatile", + "while" + ]; + + return { + name: 'Processing', + aliases: [ 'pde' ], + keywords: { + keyword: [ ...JAVA_KEYWORDS ], + literal: 'P2D P3D HALF_PI PI QUARTER_PI TAU TWO_PI null true false', + title: 'setup draw', + variable: "super this", + built_in: [ + ...BUILT_INS, + ...CLASSES + ], + type: TYPES + }, + contains: [ + CLASS, + NEW_CLASS, + FUNC_NAME, + PROPERTY, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.C_NUMBER_MODE + ] + }; +} + +export { processing as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/processing.js.js b/frontend/node_modules/highlight.js/es/languages/processing.js.js new file mode 100644 index 0000000..fd28a4c --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/processing.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/processing" instead of "highlight.js/lib/languages/processing.js"' + ); + } + } + emitWarning(); + import lang from './processing.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/profile.js b/frontend/node_modules/highlight.js/es/languages/profile.js new file mode 100644 index 0000000..ebd52ef --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/profile.js @@ -0,0 +1,43 @@ +/* +Language: Python profiler +Description: Python profiler results +Author: Brian Beck +*/ + +function profile(hljs) { + return { + name: 'Python profiler', + contains: [ + hljs.C_NUMBER_MODE, + { + begin: '[a-zA-Z_][\\da-zA-Z_]+\\.[\\da-zA-Z_]{1,3}', + end: ':', + excludeEnd: true + }, + { + begin: '(ncalls|tottime|cumtime)', + end: '$', + keywords: 'ncalls tottime|10 cumtime|10 filename', + relevance: 10 + }, + { + begin: 'function calls', + end: '$', + contains: [ hljs.C_NUMBER_MODE ], + relevance: 10 + }, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + { + className: 'string', + begin: '\\(', + end: '\\)$', + excludeBegin: true, + excludeEnd: true, + relevance: 0 + } + ] + }; +} + +export { profile as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/profile.js.js b/frontend/node_modules/highlight.js/es/languages/profile.js.js new file mode 100644 index 0000000..f15f42e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/profile.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/profile" instead of "highlight.js/lib/languages/profile.js"' + ); + } + } + emitWarning(); + import lang from './profile.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/prolog.js b/frontend/node_modules/highlight.js/es/languages/prolog.js new file mode 100644 index 0000000..579967c --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/prolog.js @@ -0,0 +1,97 @@ +/* +Language: Prolog +Description: Prolog is a general purpose logic programming language associated with artificial intelligence and computational linguistics. +Author: Raivo Laanemets +Website: https://en.wikipedia.org/wiki/Prolog +Category: functional +*/ + +function prolog(hljs) { + const ATOM = { + + begin: /[a-z][A-Za-z0-9_]*/, + relevance: 0 + }; + + const VAR = { + + className: 'symbol', + variants: [ + { begin: /[A-Z][a-zA-Z0-9_]*/ }, + { begin: /_[A-Za-z0-9_]*/ } + ], + relevance: 0 + }; + + const PARENTED = { + + begin: /\(/, + end: /\)/, + relevance: 0 + }; + + const LIST = { + + begin: /\[/, + end: /\]/ + }; + + const LINE_COMMENT = { + + className: 'comment', + begin: /%/, + end: /$/, + contains: [ hljs.PHRASAL_WORDS_MODE ] + }; + + const BACKTICK_STRING = { + + className: 'string', + begin: /`/, + end: /`/, + contains: [ hljs.BACKSLASH_ESCAPE ] + }; + + const CHAR_CODE = { + className: 'string', // 0'a etc. + begin: /0'(\\'|.)/ + }; + + const SPACE_CODE = { + className: 'string', + begin: /0'\\s/ // 0'\s + }; + + const PRED_OP = { // relevance booster + begin: /:-/ }; + + const inner = [ + + ATOM, + VAR, + PARENTED, + PRED_OP, + LIST, + LINE_COMMENT, + hljs.C_BLOCK_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + hljs.APOS_STRING_MODE, + BACKTICK_STRING, + CHAR_CODE, + SPACE_CODE, + hljs.C_NUMBER_MODE + ]; + + PARENTED.contains = inner; + LIST.contains = inner; + + return { + name: 'Prolog', + contains: inner.concat([ + { // relevance booster + begin: /\.$/ } + ]) + }; +} + +export { prolog as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/prolog.js.js b/frontend/node_modules/highlight.js/es/languages/prolog.js.js new file mode 100644 index 0000000..3277caa --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/prolog.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/prolog" instead of "highlight.js/lib/languages/prolog.js"' + ); + } + } + emitWarning(); + import lang from './prolog.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/properties.js b/frontend/node_modules/highlight.js/es/languages/properties.js new file mode 100644 index 0000000..a355457 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/properties.js @@ -0,0 +1,68 @@ +/* +Language: .properties +Contributors: Valentin Aitken , Egor Rogov +Website: https://en.wikipedia.org/wiki/.properties +Category: config +*/ + +/** @type LanguageFn */ +function properties(hljs) { + // whitespaces: space, tab, formfeed + const WS0 = '[ \\t\\f]*'; + const WS1 = '[ \\t\\f]+'; + // delimiter + const EQUAL_DELIM = WS0 + '[:=]' + WS0; + const WS_DELIM = WS1; + const DELIM = '(' + EQUAL_DELIM + '|' + WS_DELIM + ')'; + const KEY = '([^\\\\:= \\t\\f\\n]|\\\\.)+'; + + const DELIM_AND_VALUE = { + // skip DELIM + end: DELIM, + relevance: 0, + starts: { + // value: everything until end of line (again, taking into account backslashes) + className: 'string', + end: /$/, + relevance: 0, + contains: [ + { begin: '\\\\\\\\' }, + { begin: '\\\\\\n' } + ] + } + }; + + return { + name: '.properties', + disableAutodetect: true, + case_insensitive: true, + illegal: /\S/, + contains: [ + hljs.COMMENT('^\\s*[!#]', '$'), + // key: everything until whitespace or = or : (taking into account backslashes) + // case of a key-value pair + { + returnBegin: true, + variants: [ + { begin: KEY + EQUAL_DELIM }, + { begin: KEY + WS_DELIM } + ], + contains: [ + { + className: 'attr', + begin: KEY, + endsParent: true + } + ], + starts: DELIM_AND_VALUE + }, + // case of an empty key + { + className: 'attr', + begin: KEY + WS0 + '$' + } + ] + }; +} + +export { properties as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/properties.js.js b/frontend/node_modules/highlight.js/es/languages/properties.js.js new file mode 100644 index 0000000..8c47475 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/properties.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/properties" instead of "highlight.js/lib/languages/properties.js"' + ); + } + } + emitWarning(); + import lang from './properties.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/protobuf.js b/frontend/node_modules/highlight.js/es/languages/protobuf.js new file mode 100644 index 0000000..af9f600 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/protobuf.js @@ -0,0 +1,79 @@ +/* +Language: Protocol Buffers +Author: Dan Tao +Description: Protocol buffer message definition format +Website: https://developers.google.com/protocol-buffers/docs/proto3 +Category: protocols +*/ + +function protobuf(hljs) { + const KEYWORDS = [ + "package", + "import", + "option", + "optional", + "required", + "repeated", + "group", + "oneof" + ]; + const TYPES = [ + "double", + "float", + "int32", + "int64", + "uint32", + "uint64", + "sint32", + "sint64", + "fixed32", + "fixed64", + "sfixed32", + "sfixed64", + "bool", + "string", + "bytes" + ]; + const CLASS_DEFINITION = { + match: [ + /(message|enum|service)\s+/, + hljs.IDENT_RE + ], + scope: { + 1: "keyword", + 2: "title.class" + } + }; + + return { + name: 'Protocol Buffers', + aliases: ['proto'], + keywords: { + keyword: KEYWORDS, + type: TYPES, + literal: [ + 'true', + 'false' + ] + }, + contains: [ + hljs.QUOTE_STRING_MODE, + hljs.NUMBER_MODE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + CLASS_DEFINITION, + { + className: 'function', + beginKeywords: 'rpc', + end: /[{;]/, + excludeEnd: true, + keywords: 'rpc returns' + }, + { // match enum items (relevance) + // BLAH = ...; + begin: /^\s*[A-Z_]+(?=\s*=[^\n]+;$)/ } + ] + }; +} + +export { protobuf as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/protobuf.js.js b/frontend/node_modules/highlight.js/es/languages/protobuf.js.js new file mode 100644 index 0000000..d2956f7 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/protobuf.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/protobuf" instead of "highlight.js/lib/languages/protobuf.js"' + ); + } + } + emitWarning(); + import lang from './protobuf.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/puppet.js b/frontend/node_modules/highlight.js/es/languages/puppet.js new file mode 100644 index 0000000..f434cff --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/puppet.js @@ -0,0 +1,146 @@ +/* +Language: Puppet +Author: Jose Molina Colmenero +Website: https://puppet.com/docs +Category: config +*/ + +function puppet(hljs) { + const PUPPET_KEYWORDS = { + keyword: + /* language keywords */ + 'and case default else elsif false if in import enherits node or true undef unless main settings $string ', + literal: + /* metaparameters */ + 'alias audit before loglevel noop require subscribe tag ' + /* normal attributes */ + + 'owner ensure group mode name|0 changes context force incl lens load_path onlyif provider returns root show_diff type_check ' + + 'en_address ip_address realname command environment hour monute month monthday special target weekday ' + + 'creates cwd ogoutput refresh refreshonly tries try_sleep umask backup checksum content ctime force ignore ' + + 'links mtime purge recurse recurselimit replace selinux_ignore_defaults selrange selrole seltype seluser source ' + + 'souirce_permissions sourceselect validate_cmd validate_replacement allowdupe attribute_membership auth_membership forcelocal gid ' + + 'ia_load_module members system host_aliases ip allowed_trunk_vlans description device_url duplex encapsulation etherchannel ' + + 'native_vlan speed principals allow_root auth_class auth_type authenticate_user k_of_n mechanisms rule session_owner shared options ' + + 'device fstype enable hasrestart directory present absent link atboot blockdevice device dump pass remounts poller_tag use ' + + 'message withpath adminfile allow_virtual allowcdrom category configfiles flavor install_options instance package_settings platform ' + + 'responsefile status uninstall_options vendor unless_system_user unless_uid binary control flags hasstatus manifest pattern restart running ' + + 'start stop allowdupe auths expiry gid groups home iterations key_membership keys managehome membership password password_max_age ' + + 'password_min_age profile_membership profiles project purge_ssh_keys role_membership roles salt shell uid baseurl cost descr enabled ' + + 'enablegroups exclude failovermethod gpgcheck gpgkey http_caching include includepkgs keepalive metadata_expire metalink mirrorlist ' + + 'priority protect proxy proxy_password proxy_username repo_gpgcheck s3_enabled skip_if_unavailable sslcacert sslclientcert sslclientkey ' + + 'sslverify mounted', + built_in: + /* core facts */ + 'architecture augeasversion blockdevices boardmanufacturer boardproductname boardserialnumber cfkey dhcp_servers ' + + 'domain ec2_ ec2_userdata facterversion filesystems ldom fqdn gid hardwareisa hardwaremodel hostname id|0 interfaces ' + + 'ipaddress ipaddress_ ipaddress6 ipaddress6_ iphostnumber is_virtual kernel kernelmajversion kernelrelease kernelversion ' + + 'kernelrelease kernelversion lsbdistcodename lsbdistdescription lsbdistid lsbdistrelease lsbmajdistrelease lsbminordistrelease ' + + 'lsbrelease macaddress macaddress_ macosx_buildversion macosx_productname macosx_productversion macosx_productverson_major ' + + 'macosx_productversion_minor manufacturer memoryfree memorysize netmask metmask_ network_ operatingsystem operatingsystemmajrelease ' + + 'operatingsystemrelease osfamily partitions path physicalprocessorcount processor processorcount productname ps puppetversion ' + + 'rubysitedir rubyversion selinux selinux_config_mode selinux_config_policy selinux_current_mode selinux_current_mode selinux_enforced ' + + 'selinux_policyversion serialnumber sp_ sshdsakey sshecdsakey sshrsakey swapencrypted swapfree swapsize timezone type uniqueid uptime ' + + 'uptime_days uptime_hours uptime_seconds uuid virtual vlans xendomains zfs_version zonenae zones zpool_version' + }; + + const COMMENT = hljs.COMMENT('#', '$'); + + const IDENT_RE = '([A-Za-z_]|::)(\\w|::)*'; + + const TITLE = hljs.inherit(hljs.TITLE_MODE, { begin: IDENT_RE }); + + const VARIABLE = { + className: 'variable', + begin: '\\$' + IDENT_RE + }; + + const STRING = { + className: 'string', + contains: [ + hljs.BACKSLASH_ESCAPE, + VARIABLE + ], + variants: [ + { + begin: /'/, + end: /'/ + }, + { + begin: /"/, + end: /"/ + } + ] + }; + + return { + name: 'Puppet', + aliases: [ 'pp' ], + contains: [ + COMMENT, + VARIABLE, + STRING, + { + beginKeywords: 'class', + end: '\\{|;', + illegal: /=/, + contains: [ + TITLE, + COMMENT + ] + }, + { + beginKeywords: 'define', + end: /\{/, + contains: [ + { + className: 'section', + begin: hljs.IDENT_RE, + endsParent: true + } + ] + }, + { + begin: hljs.IDENT_RE + '\\s+\\{', + returnBegin: true, + end: /\S/, + contains: [ + { + className: 'keyword', + begin: hljs.IDENT_RE, + relevance: 0.2 + }, + { + begin: /\{/, + end: /\}/, + keywords: PUPPET_KEYWORDS, + relevance: 0, + contains: [ + STRING, + COMMENT, + { + begin: '[a-zA-Z_]+\\s*=>', + returnBegin: true, + end: '=>', + contains: [ + { + className: 'attr', + begin: hljs.IDENT_RE + } + ] + }, + { + className: 'number', + begin: '(\\b0[0-7_]+)|(\\b0x[0-9a-fA-F_]+)|(\\b[1-9][0-9_]*(\\.[0-9_]+)?)|[0_]\\b', + relevance: 0 + }, + VARIABLE + ] + } + ], + relevance: 0 + } + ] + }; +} + +export { puppet as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/puppet.js.js b/frontend/node_modules/highlight.js/es/languages/puppet.js.js new file mode 100644 index 0000000..fcdf900 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/puppet.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/puppet" instead of "highlight.js/lib/languages/puppet.js"' + ); + } + } + emitWarning(); + import lang from './puppet.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/purebasic.js b/frontend/node_modules/highlight.js/es/languages/purebasic.js new file mode 100644 index 0000000..073185a --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/purebasic.js @@ -0,0 +1,100 @@ +/* +Language: PureBASIC +Author: Tristano Ajmone +Description: Syntax highlighting for PureBASIC (v.5.00-5.60). No inline ASM highlighting. (v.1.2, May 2017) +Credits: I've taken inspiration from the PureBasic language file for GeSHi, created by Gustavo Julio Fiorenza (GuShH). +Website: https://www.purebasic.com +Category: system +*/ + +// Base deafult colors in PB IDE: background: #FFFFDF; foreground: #000000; + +function purebasic(hljs) { + const STRINGS = { // PB IDE color: #0080FF (Azure Radiance) + className: 'string', + begin: '(~)?"', + end: '"', + illegal: '\\n' + }; + const CONSTANTS = { // PB IDE color: #924B72 (Cannon Pink) + // "#" + a letter or underscore + letters, digits or underscores + (optional) "$" + className: 'symbol', + begin: '#[a-zA-Z_]\\w*\\$?' + }; + + return { + name: 'PureBASIC', + aliases: [ + 'pb', + 'pbi' + ], + keywords: // PB IDE color: #006666 (Blue Stone) + Bold + // Keywords from all version of PureBASIC 5.00 upward ... + 'Align And Array As Break CallDebugger Case CompilerCase CompilerDefault ' + + 'CompilerElse CompilerElseIf CompilerEndIf CompilerEndSelect CompilerError ' + + 'CompilerIf CompilerSelect CompilerWarning Continue Data DataSection Debug ' + + 'DebugLevel Declare DeclareC DeclareCDLL DeclareDLL DeclareModule Default ' + + 'Define Dim DisableASM DisableDebugger DisableExplicit Else ElseIf EnableASM ' + + 'EnableDebugger EnableExplicit End EndDataSection EndDeclareModule EndEnumeration ' + + 'EndIf EndImport EndInterface EndMacro EndModule EndProcedure EndSelect ' + + 'EndStructure EndStructureUnion EndWith Enumeration EnumerationBinary Extends ' + + 'FakeReturn For ForEach ForEver Global Gosub Goto If Import ImportC ' + + 'IncludeBinary IncludeFile IncludePath Interface List Macro MacroExpandedCount ' + + 'Map Module NewList NewMap Next Not Or Procedure ProcedureC ' + + 'ProcedureCDLL ProcedureDLL ProcedureReturn Protected Prototype PrototypeC ReDim ' + + 'Read Repeat Restore Return Runtime Select Shared Static Step Structure ' + + 'StructureUnion Swap Threaded To UndefineMacro Until Until UnuseModule ' + + 'UseModule Wend While With XIncludeFile XOr', + contains: [ + // COMMENTS | PB IDE color: #00AAAA (Persian Green) + hljs.COMMENT(';', '$', { relevance: 0 }), + + { // PROCEDURES DEFINITIONS + className: 'function', + begin: '\\b(Procedure|Declare)(C|CDLL|DLL)?\\b', + end: '\\(', + excludeEnd: true, + returnBegin: true, + contains: [ + { // PROCEDURE KEYWORDS | PB IDE color: #006666 (Blue Stone) + Bold + className: 'keyword', + begin: '(Procedure|Declare)(C|CDLL|DLL)?', + excludeEnd: true + }, + { // PROCEDURE RETURN TYPE SETTING | PB IDE color: #000000 (Black) + className: 'type', + begin: '\\.\\w*' + // end: ' ', + }, + hljs.UNDERSCORE_TITLE_MODE // PROCEDURE NAME | PB IDE color: #006666 (Blue Stone) + ] + }, + STRINGS, + CONSTANTS + ] + }; +} + +/* ============================================================================== + CHANGELOG + ============================================================================== + - v.1.2 (2017-05-12) + -- BUG-FIX: Some keywords were accidentally joyned together. Now fixed. + - v.1.1 (2017-04-30) + -- Updated to PureBASIC 5.60. + -- Keywords list now built by extracting them from the PureBASIC SDK's + "SyntaxHilighting.dll" (from each PureBASIC version). Tokens from each + version are added to the list, and renamed or removed tokens are kept + for the sake of covering all versions of the language from PureBASIC + v5.00 upward. (NOTE: currently, there are no renamed or deprecated + tokens in the keywords list). For more info, see: + -- http://www.purebasic.fr/english/viewtopic.php?&p=506269 + -- https://github.com/tajmone/purebasic-archives/tree/master/syntax-highlighting/guidelines + - v.1.0 (April 2016) + -- First release + -- Keywords list taken and adapted from GuShH's (Gustavo Julio Fiorenza) + PureBasic language file for GeSHi: + -- https://github.com/easybook/geshi/blob/master/geshi/purebasic.php +*/ + +export { purebasic as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/purebasic.js.js b/frontend/node_modules/highlight.js/es/languages/purebasic.js.js new file mode 100644 index 0000000..27b00b9 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/purebasic.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/purebasic" instead of "highlight.js/lib/languages/purebasic.js"' + ); + } + } + emitWarning(); + import lang from './purebasic.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/python-repl.js b/frontend/node_modules/highlight.js/es/languages/python-repl.js new file mode 100644 index 0000000..80dfdd3 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/python-repl.js @@ -0,0 +1,32 @@ +/* +Language: Python REPL +Requires: python.js +Author: Josh Goebel +Category: common +*/ + +function pythonRepl(hljs) { + return { + aliases: [ 'pycon' ], + contains: [ + { + className: 'meta.prompt', + starts: { + // a space separates the REPL prefix from the actual code + // this is purely for cleaner HTML output + end: / |$/, + starts: { + end: '$', + subLanguage: 'python' + } + }, + variants: [ + { begin: /^>>>(?=[ ]|$)/ }, + { begin: /^\.\.\.(?=[ ]|$)/ } + ] + } + ] + }; +} + +export { pythonRepl as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/python-repl.js.js b/frontend/node_modules/highlight.js/es/languages/python-repl.js.js new file mode 100644 index 0000000..38d63b7 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/python-repl.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/python-repl" instead of "highlight.js/lib/languages/python-repl.js"' + ); + } + } + emitWarning(); + import lang from './python-repl.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/python.js b/frontend/node_modules/highlight.js/es/languages/python.js new file mode 100644 index 0000000..4956b71 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/python.js @@ -0,0 +1,436 @@ +/* +Language: Python +Description: Python is an interpreted, object-oriented, high-level programming language with dynamic semantics. +Website: https://www.python.org +Category: common +*/ + +function python(hljs) { + const regex = hljs.regex; + const IDENT_RE = /[\p{XID_Start}_]\p{XID_Continue}*/u; + const RESERVED_WORDS = [ + 'and', + 'as', + 'assert', + 'async', + 'await', + 'break', + 'case', + 'class', + 'continue', + 'def', + 'del', + 'elif', + 'else', + 'except', + 'finally', + 'for', + 'from', + 'global', + 'if', + 'import', + 'in', + 'is', + 'lambda', + 'match', + 'nonlocal|10', + 'not', + 'or', + 'pass', + 'raise', + 'return', + 'try', + 'while', + 'with', + 'yield' + ]; + + const BUILT_INS = [ + '__import__', + 'abs', + 'all', + 'any', + 'ascii', + 'bin', + 'bool', + 'breakpoint', + 'bytearray', + 'bytes', + 'callable', + 'chr', + 'classmethod', + 'compile', + 'complex', + 'delattr', + 'dict', + 'dir', + 'divmod', + 'enumerate', + 'eval', + 'exec', + 'filter', + 'float', + 'format', + 'frozenset', + 'getattr', + 'globals', + 'hasattr', + 'hash', + 'help', + 'hex', + 'id', + 'input', + 'int', + 'isinstance', + 'issubclass', + 'iter', + 'len', + 'list', + 'locals', + 'map', + 'max', + 'memoryview', + 'min', + 'next', + 'object', + 'oct', + 'open', + 'ord', + 'pow', + 'print', + 'property', + 'range', + 'repr', + 'reversed', + 'round', + 'set', + 'setattr', + 'slice', + 'sorted', + 'staticmethod', + 'str', + 'sum', + 'super', + 'tuple', + 'type', + 'vars', + 'zip' + ]; + + const LITERALS = [ + '__debug__', + 'Ellipsis', + 'False', + 'None', + 'NotImplemented', + 'True' + ]; + + // https://docs.python.org/3/library/typing.html + // TODO: Could these be supplemented by a CamelCase matcher in certain + // contexts, leaving these remaining only for relevance hinting? + const TYPES = [ + "Any", + "Callable", + "Coroutine", + "Dict", + "List", + "Literal", + "Generic", + "Optional", + "Sequence", + "Set", + "Tuple", + "Type", + "Union" + ]; + + const KEYWORDS = { + $pattern: /[A-Za-z]\w+|__\w+__/, + keyword: RESERVED_WORDS, + built_in: BUILT_INS, + literal: LITERALS, + type: TYPES + }; + + const PROMPT = { + className: 'meta', + begin: /^(>>>|\.\.\.) / + }; + + const SUBST = { + className: 'subst', + begin: /\{/, + end: /\}/, + keywords: KEYWORDS, + illegal: /#/ + }; + + const LITERAL_BRACKET = { + begin: /\{\{/, + relevance: 0 + }; + + const STRING = { + className: 'string', + contains: [ hljs.BACKSLASH_ESCAPE ], + variants: [ + { + begin: /([uU]|[bB]|[rR]|[bB][rR]|[rR][bB])?'''/, + end: /'''/, + contains: [ + hljs.BACKSLASH_ESCAPE, + PROMPT + ], + relevance: 10 + }, + { + begin: /([uU]|[bB]|[rR]|[bB][rR]|[rR][bB])?"""/, + end: /"""/, + contains: [ + hljs.BACKSLASH_ESCAPE, + PROMPT + ], + relevance: 10 + }, + { + begin: /([fF][rR]|[rR][fF]|[fF])'''/, + end: /'''/, + contains: [ + hljs.BACKSLASH_ESCAPE, + PROMPT, + LITERAL_BRACKET, + SUBST + ] + }, + { + begin: /([fF][rR]|[rR][fF]|[fF])"""/, + end: /"""/, + contains: [ + hljs.BACKSLASH_ESCAPE, + PROMPT, + LITERAL_BRACKET, + SUBST + ] + }, + { + begin: /([uU]|[rR])'/, + end: /'/, + relevance: 10 + }, + { + begin: /([uU]|[rR])"/, + end: /"/, + relevance: 10 + }, + { + begin: /([bB]|[bB][rR]|[rR][bB])'/, + end: /'/ + }, + { + begin: /([bB]|[bB][rR]|[rR][bB])"/, + end: /"/ + }, + { + begin: /([fF][rR]|[rR][fF]|[fF])'/, + end: /'/, + contains: [ + hljs.BACKSLASH_ESCAPE, + LITERAL_BRACKET, + SUBST + ] + }, + { + begin: /([fF][rR]|[rR][fF]|[fF])"/, + end: /"/, + contains: [ + hljs.BACKSLASH_ESCAPE, + LITERAL_BRACKET, + SUBST + ] + }, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE + ] + }; + + // https://docs.python.org/3.9/reference/lexical_analysis.html#numeric-literals + const digitpart = '[0-9](_?[0-9])*'; + const pointfloat = `(\\b(${digitpart}))?\\.(${digitpart})|\\b(${digitpart})\\.`; + // Whitespace after a number (or any lexical token) is needed only if its absence + // would change the tokenization + // https://docs.python.org/3.9/reference/lexical_analysis.html#whitespace-between-tokens + // We deviate slightly, requiring a word boundary or a keyword + // to avoid accidentally recognizing *prefixes* (e.g., `0` in `0x41` or `08` or `0__1`) + const lookahead = `\\b|${RESERVED_WORDS.join('|')}`; + const NUMBER = { + className: 'number', + relevance: 0, + variants: [ + // exponentfloat, pointfloat + // https://docs.python.org/3.9/reference/lexical_analysis.html#floating-point-literals + // optionally imaginary + // https://docs.python.org/3.9/reference/lexical_analysis.html#imaginary-literals + // Note: no leading \b because floats can start with a decimal point + // and we don't want to mishandle e.g. `fn(.5)`, + // no trailing \b for pointfloat because it can end with a decimal point + // and we don't want to mishandle e.g. `0..hex()`; this should be safe + // because both MUST contain a decimal point and so cannot be confused with + // the interior part of an identifier + { + begin: `(\\b(${digitpart})|(${pointfloat}))[eE][+-]?(${digitpart})[jJ]?(?=${lookahead})` + }, + { + begin: `(${pointfloat})[jJ]?` + }, + + // decinteger, bininteger, octinteger, hexinteger + // https://docs.python.org/3.9/reference/lexical_analysis.html#integer-literals + // optionally "long" in Python 2 + // https://docs.python.org/2.7/reference/lexical_analysis.html#integer-and-long-integer-literals + // decinteger is optionally imaginary + // https://docs.python.org/3.9/reference/lexical_analysis.html#imaginary-literals + { + begin: `\\b([1-9](_?[0-9])*|0+(_?0)*)[lLjJ]?(?=${lookahead})` + }, + { + begin: `\\b0[bB](_?[01])+[lL]?(?=${lookahead})` + }, + { + begin: `\\b0[oO](_?[0-7])+[lL]?(?=${lookahead})` + }, + { + begin: `\\b0[xX](_?[0-9a-fA-F])+[lL]?(?=${lookahead})` + }, + + // imagnumber (digitpart-based) + // https://docs.python.org/3.9/reference/lexical_analysis.html#imaginary-literals + { + begin: `\\b(${digitpart})[jJ](?=${lookahead})` + } + ] + }; + const COMMENT_TYPE = { + className: "comment", + begin: regex.lookahead(/# type:/), + end: /$/, + keywords: KEYWORDS, + contains: [ + { // prevent keywords from coloring `type` + begin: /# type:/ + }, + // comment within a datatype comment includes no keywords + { + begin: /#/, + end: /\b\B/, + endsWithParent: true + } + ] + }; + const PARAMS = { + className: 'params', + variants: [ + // Exclude params in functions without params + { + className: "", + begin: /\(\s*\)/, + skip: true + }, + { + begin: /\(/, + end: /\)/, + excludeBegin: true, + excludeEnd: true, + keywords: KEYWORDS, + contains: [ + 'self', + PROMPT, + NUMBER, + STRING, + hljs.HASH_COMMENT_MODE + ] + } + ] + }; + SUBST.contains = [ + STRING, + NUMBER, + PROMPT + ]; + + return { + name: 'Python', + aliases: [ + 'py', + 'gyp', + 'ipython' + ], + unicodeRegex: true, + keywords: KEYWORDS, + illegal: /(<\/|\?)|=>/, + contains: [ + PROMPT, + NUMBER, + { + // very common convention + scope: 'variable.language', + match: /\bself\b/ + }, + { + // eat "if" prior to string so that it won't accidentally be + // labeled as an f-string + beginKeywords: "if", + relevance: 0 + }, + { match: /\bor\b/, scope: "keyword" }, + STRING, + COMMENT_TYPE, + hljs.HASH_COMMENT_MODE, + { + match: [ + /\bdef/, /\s+/, + IDENT_RE, + ], + scope: { + 1: "keyword", + 3: "title.function" + }, + contains: [ PARAMS ] + }, + { + variants: [ + { + match: [ + /\bclass/, /\s+/, + IDENT_RE, /\s*/, + /\(\s*/, IDENT_RE,/\s*\)/ + ], + }, + { + match: [ + /\bclass/, /\s+/, + IDENT_RE + ], + } + ], + scope: { + 1: "keyword", + 3: "title.class", + 6: "title.class.inherited", + } + }, + { + className: 'meta', + begin: /^[\t ]*@/, + end: /(?=#)|$/, + contains: [ + NUMBER, + PARAMS, + STRING + ] + } + ] + }; +} + +export { python as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/python.js.js b/frontend/node_modules/highlight.js/es/languages/python.js.js new file mode 100644 index 0000000..25ffda5 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/python.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/python" instead of "highlight.js/lib/languages/python.js"' + ); + } + } + emitWarning(); + import lang from './python.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/q.js b/frontend/node_modules/highlight.js/es/languages/q.js new file mode 100644 index 0000000..e79889d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/q.js @@ -0,0 +1,38 @@ +/* +Language: Q +Description: Q is a vector-based functional paradigm programming language built into the kdb+ database. + (K/Q/Kdb+ from Kx Systems) +Author: Sergey Vidyuk +Website: https://kx.com/connect-with-us/developers/ +Category: enterprise, functional, database +*/ + +function q(hljs) { + const KEYWORDS = { + $pattern: /(`?)[A-Za-z0-9_]+\b/, + keyword: + 'do while select delete by update from', + literal: + '0b 1b', + built_in: + 'neg not null string reciprocal floor ceiling signum mod xbar xlog and or each scan over prior mmu lsq inv md5 ltime gtime count first var dev med cov cor all any rand sums prds mins maxs fills deltas ratios avgs differ prev next rank reverse iasc idesc asc desc msum mcount mavg mdev xrank mmin mmax xprev rotate distinct group where flip type key til get value attr cut set upsert raze union inter except cross sv vs sublist enlist read0 read1 hopen hclose hdel hsym hcount peach system ltrim rtrim trim lower upper ssr view tables views cols xcols keys xkey xcol xasc xdesc fkeys meta lj aj aj0 ij pj asof uj ww wj wj1 fby xgroup ungroup ej save load rsave rload show csv parse eval min max avg wavg wsum sin cos tan sum', + type: + '`float `double int `timestamp `timespan `datetime `time `boolean `symbol `char `byte `short `long `real `month `date `minute `second `guid' + }; + + return { + name: 'Q', + aliases: [ + 'k', + 'kdb' + ], + keywords: KEYWORDS, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + hljs.C_NUMBER_MODE + ] + }; +} + +export { q as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/q.js.js b/frontend/node_modules/highlight.js/es/languages/q.js.js new file mode 100644 index 0000000..7771a5c --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/q.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/q" instead of "highlight.js/lib/languages/q.js"' + ); + } + } + emitWarning(); + import lang from './q.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/qml.js b/frontend/node_modules/highlight.js/es/languages/qml.js new file mode 100644 index 0000000..1b9fa82 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/qml.js @@ -0,0 +1,189 @@ +/* +Language: QML +Requires: javascript.js, xml.js +Author: John Foster +Description: Syntax highlighting for the Qt Quick QML scripting language, based mostly off + the JavaScript parser. +Website: https://doc.qt.io/qt-5/qmlapplications.html +Category: scripting +*/ + +function qml(hljs) { + const regex = hljs.regex; + const KEYWORDS = { + keyword: + 'in of on if for while finally var new function do return void else break catch ' + + 'instanceof with throw case default try this switch continue typeof delete ' + + 'let yield const export super debugger as async await import', + literal: + 'true false null undefined NaN Infinity', + built_in: + 'eval isFinite isNaN parseFloat parseInt decodeURI decodeURIComponent ' + + 'encodeURI encodeURIComponent escape unescape Object Function Boolean Error ' + + 'EvalError InternalError RangeError ReferenceError StopIteration SyntaxError ' + + 'TypeError URIError Number Math Date String RegExp Array Float32Array ' + + 'Float64Array Int16Array Int32Array Int8Array Uint16Array Uint32Array ' + + 'Uint8Array Uint8ClampedArray ArrayBuffer DataView JSON Intl arguments require ' + + 'module console window document Symbol Set Map WeakSet WeakMap Proxy Reflect ' + + 'Behavior bool color coordinate date double enumeration font geocircle georectangle ' + + 'geoshape int list matrix4x4 parent point quaternion real rect ' + + 'size string url variant vector2d vector3d vector4d ' + + 'Promise' + }; + + const QML_IDENT_RE = '[a-zA-Z_][a-zA-Z0-9\\._]*'; + + // Isolate property statements. Ends at a :, =, ;, ,, a comment or end of line. + // Use property class. + const PROPERTY = { + className: 'keyword', + begin: '\\bproperty\\b', + starts: { + className: 'string', + end: '(:|=|;|,|//|/\\*|$)', + returnEnd: true + } + }; + + // Isolate signal statements. Ends at a ) a comment or end of line. + // Use property class. + const SIGNAL = { + className: 'keyword', + begin: '\\bsignal\\b', + starts: { + className: 'string', + end: '(\\(|:|=|;|,|//|/\\*|$)', + returnEnd: true + } + }; + + // id: is special in QML. When we see id: we want to mark the id: as attribute and + // emphasize the token following. + const ID_ID = { + className: 'attribute', + begin: '\\bid\\s*:', + starts: { + className: 'string', + end: QML_IDENT_RE, + returnEnd: false + } + }; + + // Find QML object attribute. An attribute is a QML identifier followed by :. + // Unfortunately it's hard to know where it ends, as it may contain scalars, + // objects, object definitions, or javascript. The true end is either when the parent + // ends or the next attribute is detected. + const QML_ATTRIBUTE = { + begin: QML_IDENT_RE + '\\s*:', + returnBegin: true, + contains: [ + { + className: 'attribute', + begin: QML_IDENT_RE, + end: '\\s*:', + excludeEnd: true, + relevance: 0 + } + ], + relevance: 0 + }; + + // Find QML object. A QML object is a QML identifier followed by { and ends at the matching }. + // All we really care about is finding IDENT followed by { and just mark up the IDENT and ignore the {. + const QML_OBJECT = { + begin: regex.concat(QML_IDENT_RE, /\s*\{/), + end: /\{/, + returnBegin: true, + relevance: 0, + contains: [ hljs.inherit(hljs.TITLE_MODE, { begin: QML_IDENT_RE }) ] + }; + + return { + name: 'QML', + aliases: [ 'qt' ], + case_insensitive: false, + keywords: KEYWORDS, + contains: [ + { + className: 'meta', + begin: /^\s*['"]use (strict|asm)['"]/ + }, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + { // template string + className: 'string', + begin: '`', + end: '`', + contains: [ + hljs.BACKSLASH_ESCAPE, + { + className: 'subst', + begin: '\\$\\{', + end: '\\}' + } + ] + }, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + { + className: 'number', + variants: [ + { begin: '\\b(0[bB][01]+)' }, + { begin: '\\b(0[oO][0-7]+)' }, + { begin: hljs.C_NUMBER_RE } + ], + relevance: 0 + }, + { // "value" container + begin: '(' + hljs.RE_STARTERS_RE + '|\\b(case|return|throw)\\b)\\s*', + keywords: 'return throw case', + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.REGEXP_MODE, + { // E4X / JSX + begin: /\s*[);\]]/, + relevance: 0, + subLanguage: 'xml' + } + ], + relevance: 0 + }, + SIGNAL, + PROPERTY, + { + className: 'function', + beginKeywords: 'function', + end: /\{/, + excludeEnd: true, + contains: [ + hljs.inherit(hljs.TITLE_MODE, { begin: /[A-Za-z$_][0-9A-Za-z$_]*/ }), + { + className: 'params', + begin: /\(/, + end: /\)/, + excludeBegin: true, + excludeEnd: true, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + } + ], + illegal: /\[|%/ + }, + { + // hack: prevents detection of keywords after dots + begin: '\\.' + hljs.IDENT_RE, + relevance: 0 + }, + ID_ID, + QML_ATTRIBUTE, + QML_OBJECT + ], + illegal: /#/ + }; +} + +export { qml as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/qml.js.js b/frontend/node_modules/highlight.js/es/languages/qml.js.js new file mode 100644 index 0000000..48c2425 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/qml.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/qml" instead of "highlight.js/lib/languages/qml.js"' + ); + } + } + emitWarning(); + import lang from './qml.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/r.js b/frontend/node_modules/highlight.js/es/languages/r.js new file mode 100644 index 0000000..d4a8469 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/r.js @@ -0,0 +1,257 @@ +/* +Language: R +Description: R is a free software environment for statistical computing and graphics. +Author: Joe Cheng +Contributors: Konrad Rudolph +Website: https://www.r-project.org +Category: common,scientific +*/ + +/** @type LanguageFn */ +function r(hljs) { + const regex = hljs.regex; + // Identifiers in R cannot start with `_`, but they can start with `.` if it + // is not immediately followed by a digit. + // R also supports quoted identifiers, which are near-arbitrary sequences + // delimited by backticks (`…`), which may contain escape sequences. These are + // handled in a separate mode. See `test/markup/r/names.txt` for examples. + // FIXME: Support Unicode identifiers. + const IDENT_RE = /(?:(?:[a-zA-Z]|\.[._a-zA-Z])[._a-zA-Z0-9]*)|\.(?!\d)/; + const NUMBER_TYPES_RE = regex.either( + // Special case: only hexadecimal binary powers can contain fractions + /0[xX][0-9a-fA-F]+\.[0-9a-fA-F]*[pP][+-]?\d+i?/, + // Hexadecimal numbers without fraction and optional binary power + /0[xX][0-9a-fA-F]+(?:[pP][+-]?\d+)?[Li]?/, + // Decimal numbers + /(?:\d+(?:\.\d*)?|\.\d+)(?:[eE][+-]?\d+)?[Li]?/ + ); + const OPERATORS_RE = /[=!<>:]=|\|\||&&|:::?|<-|<<-|->>|->|\|>|[-+*\/?!$&|:<=>@^~]|\*\*/; + const PUNCTUATION_RE = regex.either( + /[()]/, + /[{}]/, + /\[\[/, + /[[\]]/, + /\\/, + /,/ + ); + + return { + name: 'R', + + keywords: { + $pattern: IDENT_RE, + keyword: + 'function if in break next repeat else for while', + literal: + 'NULL NA TRUE FALSE Inf NaN NA_integer_|10 NA_real_|10 ' + + 'NA_character_|10 NA_complex_|10', + built_in: + // Builtin constants + 'LETTERS letters month.abb month.name pi T F ' + // Primitive functions + // These are all the functions in `base` that are implemented as a + // `.Primitive`, minus those functions that are also keywords. + + 'abs acos acosh all any anyNA Arg as.call as.character ' + + 'as.complex as.double as.environment as.integer as.logical ' + + 'as.null.default as.numeric as.raw asin asinh atan atanh attr ' + + 'attributes baseenv browser c call ceiling class Conj cos cosh ' + + 'cospi cummax cummin cumprod cumsum digamma dim dimnames ' + + 'emptyenv exp expression floor forceAndCall gamma gc.time ' + + 'globalenv Im interactive invisible is.array is.atomic is.call ' + + 'is.character is.complex is.double is.environment is.expression ' + + 'is.finite is.function is.infinite is.integer is.language ' + + 'is.list is.logical is.matrix is.na is.name is.nan is.null ' + + 'is.numeric is.object is.pairlist is.raw is.recursive is.single ' + + 'is.symbol lazyLoadDBfetch length lgamma list log max min ' + + 'missing Mod names nargs nzchar oldClass on.exit pos.to.env ' + + 'proc.time prod quote range Re rep retracemem return round ' + + 'seq_along seq_len seq.int sign signif sin sinh sinpi sqrt ' + + 'standardGeneric substitute sum switch tan tanh tanpi tracemem ' + + 'trigamma trunc unclass untracemem UseMethod xtfrm', + }, + + contains: [ + // Roxygen comments + hljs.COMMENT( + /#'/, + /$/, + { contains: [ + { + // Handle `@examples` separately to cause all subsequent code + // until the next `@`-tag on its own line to be kept as-is, + // preventing highlighting. This code is example R code, so nested + // doctags shouldn’t be treated as such. See + // `test/markup/r/roxygen.txt` for an example. + scope: 'doctag', + match: /@examples/, + starts: { + end: regex.lookahead(regex.either( + // end if another doc comment + /\n^#'\s*(?=@[a-zA-Z]+)/, + // or a line with no comment + /\n^(?!#')/ + )), + endsParent: true + } + }, + { + // Handle `@param` to highlight the parameter name following + // after. + scope: 'doctag', + begin: '@param', + end: /$/, + contains: [ + { + scope: 'variable', + variants: [ + { match: IDENT_RE }, + { match: /`(?:\\.|[^`\\])+`/ } + ], + endsParent: true + } + ] + }, + { + scope: 'doctag', + match: /@[a-zA-Z]+/ + }, + { + scope: 'keyword', + match: /\\[a-zA-Z]+/ + } + ] } + ), + + hljs.HASH_COMMENT_MODE, + + { + scope: 'string', + contains: [ hljs.BACKSLASH_ESCAPE ], + variants: [ + hljs.END_SAME_AS_BEGIN({ + begin: /[rR]"(-*)\(/, + end: /\)(-*)"/ + }), + hljs.END_SAME_AS_BEGIN({ + begin: /[rR]"(-*)\{/, + end: /\}(-*)"/ + }), + hljs.END_SAME_AS_BEGIN({ + begin: /[rR]"(-*)\[/, + end: /\](-*)"/ + }), + hljs.END_SAME_AS_BEGIN({ + begin: /[rR]'(-*)\(/, + end: /\)(-*)'/ + }), + hljs.END_SAME_AS_BEGIN({ + begin: /[rR]'(-*)\{/, + end: /\}(-*)'/ + }), + hljs.END_SAME_AS_BEGIN({ + begin: /[rR]'(-*)\[/, + end: /\](-*)'/ + }), + { + begin: '"', + end: '"', + relevance: 0 + }, + { + begin: "'", + end: "'", + relevance: 0 + } + ], + }, + + // Matching numbers immediately following punctuation and operators is + // tricky since we need to look at the character ahead of a number to + // ensure the number is not part of an identifier, and we cannot use + // negative look-behind assertions. So instead we explicitly handle all + // possible combinations of (operator|punctuation), number. + // TODO: replace with negative look-behind when available + // { begin: /(? +Category: functional +*/ +function reasonml(hljs) { + const BUILT_IN_TYPES = [ + "array", + "bool", + "bytes", + "char", + "exn|5", + "float", + "int", + "int32", + "int64", + "list", + "lazy_t|5", + "nativeint|5", + "ref", + "string", + "unit", + ]; + return { + name: 'ReasonML', + aliases: [ 're' ], + keywords: { + $pattern: /[a-z_]\w*!?/, + keyword: [ + "and", + "as", + "asr", + "assert", + "begin", + "class", + "constraint", + "do", + "done", + "downto", + "else", + "end", + "esfun", + "exception", + "external", + "for", + "fun", + "function", + "functor", + "if", + "in", + "include", + "inherit", + "initializer", + "land", + "lazy", + "let", + "lor", + "lsl", + "lsr", + "lxor", + "mod", + "module", + "mutable", + "new", + "nonrec", + "object", + "of", + "open", + "or", + "pri", + "pub", + "rec", + "sig", + "struct", + "switch", + "then", + "to", + "try", + "type", + "val", + "virtual", + "when", + "while", + "with", + ], + built_in: BUILT_IN_TYPES, + literal: ["true", "false"], + }, + illegal: /(:-|:=|\$\{|\+=)/, + contains: [ + { + scope: 'literal', + match: /\[(\|\|)?\]|\(\)/, + relevance: 0 + }, + hljs.C_LINE_COMMENT_MODE, + hljs.COMMENT(/\/\*/, /\*\//, { illegal: /^(#,\/\/)/ }), + { /* type variable */ + scope: 'symbol', + match: /\'[A-Za-z_](?!\')[\w\']*/ + /* the grammar is ambiguous on how 'a'b should be interpreted but not the compiler */ + }, + { /* polymorphic variant */ + scope: 'type', + match: /`[A-Z][\w\']*/ + }, + { /* module or constructor */ + scope: 'type', + match: /\b[A-Z][\w\']*/, + relevance: 0 + }, + { /* don't color identifiers, but safely catch all identifiers with ' */ + match: /[a-z_]\w*\'[\w\']*/, + relevance: 0 + }, + { + scope: 'operator', + match: /\s+(\|\||\+[\+\.]?|\*[\*\/\.]?|\/[\.]?|\.\.\.|\|>|&&|===?)\s+/, + relevance: 0 + }, + hljs.inherit(hljs.APOS_STRING_MODE, { + scope: 'string', + relevance: 0 + }), + hljs.inherit(hljs.QUOTE_STRING_MODE, { illegal: null }), + { + scope: 'number', + variants: [ + { match: /\b0[xX][a-fA-F0-9_]+[Lln]?/ }, + { match: /\b0[oO][0-7_]+[Lln]?/ }, + { match: /\b0[bB][01_]+[Lln]?/ }, + { match: /\b[0-9][0-9_]*([Lln]|(\.[0-9_]*)?([eE][-+]?[0-9_]+)?)/ }, + ], + relevance: 0 + }, + ] + }; +} + +export { reasonml as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/reasonml.js.js b/frontend/node_modules/highlight.js/es/languages/reasonml.js.js new file mode 100644 index 0000000..3ea41f0 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/reasonml.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/reasonml" instead of "highlight.js/lib/languages/reasonml.js"' + ); + } + } + emitWarning(); + import lang from './reasonml.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/rib.js b/frontend/node_modules/highlight.js/es/languages/rib.js new file mode 100644 index 0000000..aa64b78 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/rib.js @@ -0,0 +1,37 @@ +/* +Language: RenderMan RIB +Author: Konstantin Evdokimenko +Contributors: Shuen-Huei Guan +Website: https://renderman.pixar.com/resources/RenderMan_20/ribBinding.html +Category: graphics +*/ + +function rib(hljs) { + return { + name: 'RenderMan RIB', + keywords: + 'ArchiveRecord AreaLightSource Atmosphere Attribute AttributeBegin AttributeEnd Basis ' + + 'Begin Blobby Bound Clipping ClippingPlane Color ColorSamples ConcatTransform Cone ' + + 'CoordinateSystem CoordSysTransform CropWindow Curves Cylinder DepthOfField Detail ' + + 'DetailRange Disk Displacement Display End ErrorHandler Exposure Exterior Format ' + + 'FrameAspectRatio FrameBegin FrameEnd GeneralPolygon GeometricApproximation Geometry ' + + 'Hider Hyperboloid Identity Illuminate Imager Interior LightSource ' + + 'MakeCubeFaceEnvironment MakeLatLongEnvironment MakeShadow MakeTexture Matte ' + + 'MotionBegin MotionEnd NuPatch ObjectBegin ObjectEnd ObjectInstance Opacity Option ' + + 'Orientation Paraboloid Patch PatchMesh Perspective PixelFilter PixelSamples ' + + 'PixelVariance Points PointsGeneralPolygons PointsPolygons Polygon Procedural Projection ' + + 'Quantize ReadArchive RelativeDetail ReverseOrientation Rotate Scale ScreenWindow ' + + 'ShadingInterpolation ShadingRate Shutter Sides Skew SolidBegin SolidEnd Sphere ' + + 'SubdivisionMesh Surface TextureCoordinates Torus Transform TransformBegin TransformEnd ' + + 'TransformPoints Translate TrimCurve WorldBegin WorldEnd', + illegal: ' +Description: Syntax highlighting for Roboconf's DSL +Website: http://roboconf.net +Category: config +*/ + +function roboconf(hljs) { + const IDENTIFIER = '[a-zA-Z-_][^\\n{]+\\{'; + + const PROPERTY = { + className: 'attribute', + begin: /[a-zA-Z-_]+/, + end: /\s*:/, + excludeEnd: true, + starts: { + end: ';', + relevance: 0, + contains: [ + { + className: 'variable', + begin: /\.[a-zA-Z-_]+/ + }, + { + className: 'keyword', + begin: /\(optional\)/ + } + ] + } + }; + + return { + name: 'Roboconf', + aliases: [ + 'graph', + 'instances' + ], + case_insensitive: true, + keywords: 'import', + contains: [ + // Facet sections + { + begin: '^facet ' + IDENTIFIER, + end: /\}/, + keywords: 'facet', + contains: [ + PROPERTY, + hljs.HASH_COMMENT_MODE + ] + }, + + // Instance sections + { + begin: '^\\s*instance of ' + IDENTIFIER, + end: /\}/, + keywords: 'name count channels instance-data instance-state instance of', + illegal: /\S/, + contains: [ + 'self', + PROPERTY, + hljs.HASH_COMMENT_MODE + ] + }, + + // Component sections + { + begin: '^' + IDENTIFIER, + end: /\}/, + contains: [ + PROPERTY, + hljs.HASH_COMMENT_MODE + ] + }, + + // Comments + hljs.HASH_COMMENT_MODE + ] + }; +} + +export { roboconf as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/roboconf.js.js b/frontend/node_modules/highlight.js/es/languages/roboconf.js.js new file mode 100644 index 0000000..2f76c8a --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/roboconf.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/roboconf" instead of "highlight.js/lib/languages/roboconf.js"' + ); + } + } + emitWarning(); + import lang from './roboconf.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/routeros.js b/frontend/node_modules/highlight.js/es/languages/routeros.js new file mode 100644 index 0000000..64dcc3d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/routeros.js @@ -0,0 +1,164 @@ +/* +Language: MikroTik RouterOS script +Author: Ivan Dementev +Description: Scripting host provides a way to automate some router maintenance tasks by means of executing user-defined scripts bounded to some event occurrence +Website: https://wiki.mikrotik.com/wiki/Manual:Scripting +Category: scripting +*/ + +// Colors from RouterOS terminal: +// green - #0E9A00 +// teal - #0C9A9A +// purple - #99069A +// light-brown - #9A9900 + +function routeros(hljs) { + const STATEMENTS = 'foreach do while for if from to step else on-error and or not in'; + + // Global commands: Every global command should start with ":" token, otherwise it will be treated as variable. + const GLOBAL_COMMANDS = 'global local beep delay put len typeof pick log time set find environment terminal error execute parse resolve toarray tobool toid toip toip6 tonum tostr totime'; + + // Common commands: Following commands available from most sub-menus: + const COMMON_COMMANDS = 'add remove enable disable set get print export edit find run debug error info warning'; + + const LITERALS = 'true false yes no nothing nil null'; + + const OBJECTS = 'traffic-flow traffic-generator firewall scheduler aaa accounting address-list address align area bandwidth-server bfd bgp bridge client clock community config connection console customer default dhcp-client dhcp-server discovery dns e-mail ethernet filter firmware gps graphing group hardware health hotspot identity igmp-proxy incoming instance interface ip ipsec ipv6 irq l2tp-server lcd ldp logging mac-server mac-winbox mangle manual mirror mme mpls nat nd neighbor network note ntp ospf ospf-v3 ovpn-server page peer pim ping policy pool port ppp pppoe-client pptp-server prefix profile proposal proxy queue radius resource rip ripng route routing screen script security-profiles server service service-port settings shares smb sms sniffer snmp snooper socks sstp-server system tool tracking type upgrade upnp user-manager users user vlan secret vrrp watchdog web-access wireless pptp pppoe lan wan layer7-protocol lease simple raw'; + + const VAR = { + className: 'variable', + variants: [ + { begin: /\$[\w\d#@][\w\d_]*/ }, + { begin: /\$\{(.*?)\}/ } + ] + }; + + const QUOTE_STRING = { + className: 'string', + begin: /"/, + end: /"/, + contains: [ + hljs.BACKSLASH_ESCAPE, + VAR, + { + className: 'variable', + begin: /\$\(/, + end: /\)/, + contains: [ hljs.BACKSLASH_ESCAPE ] + } + ] + }; + + const APOS_STRING = { + className: 'string', + begin: /'/, + end: /'/ + }; + + return { + name: 'MikroTik RouterOS script', + aliases: [ 'mikrotik' ], + case_insensitive: true, + keywords: { + $pattern: /:?[\w-]+/, + literal: LITERALS, + keyword: STATEMENTS + ' :' + STATEMENTS.split(' ').join(' :') + ' :' + GLOBAL_COMMANDS.split(' ').join(' :') + }, + contains: [ + { // illegal syntax + variants: [ + { // -- comment + begin: /\/\*/, + end: /\*\// + }, + { // Stan comment + begin: /\/\//, + end: /$/ + }, + { // HTML tags + begin: /<\//, + end: />/ + } + ], + illegal: /./ + }, + hljs.COMMENT('^#', '$'), + QUOTE_STRING, + APOS_STRING, + VAR, + // attribute=value + { + // > is to avoid matches with => in other grammars + begin: /[\w-]+=([^\s{}[\]()>]+)/, + relevance: 0, + returnBegin: true, + contains: [ + { + className: 'attribute', + begin: /[^=]+/ + }, + { + begin: /=/, + endsWithParent: true, + relevance: 0, + contains: [ + QUOTE_STRING, + APOS_STRING, + VAR, + { + className: 'literal', + begin: '\\b(' + LITERALS.split(' ').join('|') + ')\\b' + }, + { + // Do not format unclassified values. Needed to exclude highlighting of values as built_in. + begin: /("[^"]*"|[^\s{}[\]]+)/ } + /* + { + // IPv4 addresses and subnets + className: 'number', + variants: [ + {begin: IPADDR_wBITMASK+'(,'+IPADDR_wBITMASK+')*'}, //192.168.0.0/24,1.2.3.0/24 + {begin: IPADDR+'-'+IPADDR}, // 192.168.0.1-192.168.0.3 + {begin: IPADDR+'(,'+IPADDR+')*'}, // 192.168.0.1,192.168.0.34,192.168.24.1,192.168.0.1 + ] + }, + { + // MAC addresses and DHCP Client IDs + className: 'number', + begin: /\b(1:)?([0-9A-Fa-f]{1,2}[:-]){5}([0-9A-Fa-f]){1,2}\b/, + }, + */ + ] + } + ] + }, + { + // HEX values + className: 'number', + begin: /\*[0-9a-fA-F]+/ + }, + { + begin: '\\b(' + COMMON_COMMANDS.split(' ').join('|') + ')([\\s[(\\]|])', + returnBegin: true, + contains: [ + { + className: 'built_in', // 'function', + begin: /\w+/ + } + ] + }, + { + className: 'built_in', + variants: [ + { begin: '(\\.\\./|/|\\s)((' + OBJECTS.split(' ').join('|') + ');?\\s)+' }, + { + begin: /\.\./, + relevance: 0 + } + ] + } + ] + }; +} + +export { routeros as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/routeros.js.js b/frontend/node_modules/highlight.js/es/languages/routeros.js.js new file mode 100644 index 0000000..4d6c368 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/routeros.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/routeros" instead of "highlight.js/lib/languages/routeros.js"' + ); + } + } + emitWarning(); + import lang from './routeros.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/rsl.js b/frontend/node_modules/highlight.js/es/languages/rsl.js new file mode 100644 index 0000000..c878fa7 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/rsl.js @@ -0,0 +1,149 @@ +/* +Language: RenderMan RSL +Author: Konstantin Evdokimenko +Contributors: Shuen-Huei Guan +Website: https://renderman.pixar.com/resources/RenderMan_20/shadingLanguage.html +Category: graphics +*/ + +function rsl(hljs) { + const BUILT_INS = [ + "abs", + "acos", + "ambient", + "area", + "asin", + "atan", + "atmosphere", + "attribute", + "calculatenormal", + "ceil", + "cellnoise", + "clamp", + "comp", + "concat", + "cos", + "degrees", + "depth", + "Deriv", + "diffuse", + "distance", + "Du", + "Dv", + "environment", + "exp", + "faceforward", + "filterstep", + "floor", + "format", + "fresnel", + "incident", + "length", + "lightsource", + "log", + "match", + "max", + "min", + "mod", + "noise", + "normalize", + "ntransform", + "opposite", + "option", + "phong", + "pnoise", + "pow", + "printf", + "ptlined", + "radians", + "random", + "reflect", + "refract", + "renderinfo", + "round", + "setcomp", + "setxcomp", + "setycomp", + "setzcomp", + "shadow", + "sign", + "sin", + "smoothstep", + "specular", + "specularbrdf", + "spline", + "sqrt", + "step", + "tan", + "texture", + "textureinfo", + "trace", + "transform", + "vtransform", + "xcomp", + "ycomp", + "zcomp" + ]; + + const TYPES = [ + "matrix", + "float", + "color", + "point", + "normal", + "vector" + ]; + + const KEYWORDS = [ + "while", + "for", + "if", + "do", + "return", + "else", + "break", + "extern", + "continue" + ]; + + const CLASS_DEFINITION = { + match: [ + /(surface|displacement|light|volume|imager)/, + /\s+/, + hljs.IDENT_RE, + ], + scope: { + 1: "keyword", + 3: "title.class", + } + }; + + return { + name: 'RenderMan RSL', + keywords: { + keyword: KEYWORDS, + built_in: BUILT_INS, + type: TYPES + }, + illegal: ' +Contributors: Peter Leonov , Vasily Polovnyov , Loren Segal , Pascal Hurni , Cedric Sohrauer +Category: common, scripting +*/ + +function ruby(hljs) { + const regex = hljs.regex; + const RUBY_METHOD_RE = '([a-zA-Z_]\\w*[!?=]?|[-+~]@|<<|>>|=~|===?|<=>|[<>]=?|\\*\\*|[-/+%^&*~`|]|\\[\\]=?)'; + // TODO: move concepts like CAMEL_CASE into `modes.js` + const CLASS_NAME_RE = regex.either( + /\b([A-Z]+[a-z0-9]+)+/, + // ends in caps + /\b([A-Z]+[a-z0-9]+)+[A-Z]+/, + ) + ; + const CLASS_NAME_WITH_NAMESPACE_RE = regex.concat(CLASS_NAME_RE, /(::\w+)*/); + // very popular ruby built-ins that one might even assume + // are actual keywords (despite that not being the case) + const PSEUDO_KWS = [ + "include", + "extend", + "prepend", + "public", + "private", + "protected", + "raise", + "throw" + ]; + const RUBY_KEYWORDS = { + "variable.constant": [ + "__FILE__", + "__LINE__", + "__ENCODING__" + ], + "variable.language": [ + "self", + "super", + ], + keyword: [ + "alias", + "and", + "begin", + "BEGIN", + "break", + "case", + "class", + "defined", + "do", + "else", + "elsif", + "end", + "END", + "ensure", + "for", + "if", + "in", + "module", + "next", + "not", + "or", + "redo", + "require", + "rescue", + "retry", + "return", + "then", + "undef", + "unless", + "until", + "when", + "while", + "yield", + ...PSEUDO_KWS + ], + built_in: [ + "proc", + "lambda", + "attr_accessor", + "attr_reader", + "attr_writer", + "define_method", + "private_constant", + "module_function" + ], + literal: [ + "true", + "false", + "nil" + ] + }; + const YARDOCTAG = { + className: 'doctag', + begin: '@[A-Za-z]+' + }; + const IRB_OBJECT = { + begin: '#<', + end: '>' + }; + const COMMENT_MODES = [ + hljs.COMMENT( + '#', + '$', + { contains: [ YARDOCTAG ] } + ), + hljs.COMMENT( + '^=begin', + '^=end', + { + contains: [ YARDOCTAG ], + relevance: 10 + } + ), + hljs.COMMENT('^__END__', hljs.MATCH_NOTHING_RE) + ]; + const SUBST = { + className: 'subst', + begin: /#\{/, + end: /\}/, + keywords: RUBY_KEYWORDS + }; + const STRING = { + className: 'string', + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST + ], + variants: [ + { + begin: /'/, + end: /'/ + }, + { + begin: /"/, + end: /"/ + }, + { + begin: /`/, + end: /`/ + }, + { + begin: /%[qQwWx]?\(/, + end: /\)/ + }, + { + begin: /%[qQwWx]?\[/, + end: /\]/ + }, + { + begin: /%[qQwWx]?\{/, + end: /\}/ + }, + { + begin: /%[qQwWx]?/ + }, + { + begin: /%[qQwWx]?\//, + end: /\// + }, + { + begin: /%[qQwWx]?%/, + end: /%/ + }, + { + begin: /%[qQwWx]?-/, + end: /-/ + }, + { + begin: /%[qQwWx]?\|/, + end: /\|/ + }, + // in the following expressions, \B in the beginning suppresses recognition of ?-sequences + // where ? is the last character of a preceding identifier, as in: `func?4` + { begin: /\B\?(\\\d{1,3})/ }, + { begin: /\B\?(\\x[A-Fa-f0-9]{1,2})/ }, + { begin: /\B\?(\\u\{?[A-Fa-f0-9]{1,6}\}?)/ }, + { begin: /\B\?(\\M-\\C-|\\M-\\c|\\c\\M-|\\M-|\\C-\\M-)[\x20-\x7e]/ }, + { begin: /\B\?\\(c|C-)[\x20-\x7e]/ }, + { begin: /\B\?\\?\S/ }, + // heredocs + { + // this guard makes sure that we have an entire heredoc and not a false + // positive (auto-detect, etc.) + begin: regex.concat( + /<<[-~]?'?/, + regex.lookahead(/(\w+)(?=\W)[^\n]*\n(?:[^\n]*\n)*?\s*\1\b/) + ), + contains: [ + hljs.END_SAME_AS_BEGIN({ + begin: /(\w+)/, + end: /(\w+)/, + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST + ] + }) + ] + } + ] + }; + + // Ruby syntax is underdocumented, but this grammar seems to be accurate + // as of version 2.7.2 (confirmed with (irb and `Ripper.sexp(...)`) + // https://docs.ruby-lang.org/en/2.7.0/doc/syntax/literals_rdoc.html#label-Numbers + const decimal = '[1-9](_?[0-9])*|0'; + const digits = '[0-9](_?[0-9])*'; + const NUMBER = { + className: 'number', + relevance: 0, + variants: [ + // decimal integer/float, optionally exponential or rational, optionally imaginary + { begin: `\\b(${decimal})(\\.(${digits}))?([eE][+-]?(${digits})|r)?i?\\b` }, + + // explicit decimal/binary/octal/hexadecimal integer, + // optionally rational and/or imaginary + { begin: "\\b0[dD][0-9](_?[0-9])*r?i?\\b" }, + { begin: "\\b0[bB][0-1](_?[0-1])*r?i?\\b" }, + { begin: "\\b0[oO][0-7](_?[0-7])*r?i?\\b" }, + { begin: "\\b0[xX][0-9a-fA-F](_?[0-9a-fA-F])*r?i?\\b" }, + + // 0-prefixed implicit octal integer, optionally rational and/or imaginary + { begin: "\\b0(_?[0-7])+r?i?\\b" } + ] + }; + + const PARAMS = { + variants: [ + { + match: /\(\)/, + }, + { + className: 'params', + begin: /\(/, + end: /(?=\))/, + excludeBegin: true, + endsParent: true, + keywords: RUBY_KEYWORDS, + } + ] + }; + + const INCLUDE_EXTEND = { + match: [ + /(include|extend)\s+/, + CLASS_NAME_WITH_NAMESPACE_RE + ], + scope: { + 2: "title.class" + }, + keywords: RUBY_KEYWORDS + }; + + const CLASS_DEFINITION = { + variants: [ + { + match: [ + /class\s+/, + CLASS_NAME_WITH_NAMESPACE_RE, + /\s+<\s+/, + CLASS_NAME_WITH_NAMESPACE_RE + ] + }, + { + match: [ + /\b(class|module)\s+/, + CLASS_NAME_WITH_NAMESPACE_RE + ] + } + ], + scope: { + 2: "title.class", + 4: "title.class.inherited" + }, + keywords: RUBY_KEYWORDS + }; + + const UPPER_CASE_CONSTANT = { + relevance: 0, + match: /\b[A-Z][A-Z_0-9]+\b/, + className: "variable.constant" + }; + + const METHOD_DEFINITION = { + match: [ + /def/, /\s+/, + RUBY_METHOD_RE + ], + scope: { + 1: "keyword", + 3: "title.function" + }, + contains: [ + PARAMS + ] + }; + + const OBJECT_CREATION = { + relevance: 0, + match: [ + CLASS_NAME_WITH_NAMESPACE_RE, + /\.new[. (]/ + ], + scope: { + 1: "title.class" + } + }; + + // CamelCase + const CLASS_REFERENCE = { + relevance: 0, + match: CLASS_NAME_RE, + scope: "title.class" + }; + + const RUBY_DEFAULT_CONTAINS = [ + STRING, + CLASS_DEFINITION, + INCLUDE_EXTEND, + OBJECT_CREATION, + UPPER_CASE_CONSTANT, + CLASS_REFERENCE, + METHOD_DEFINITION, + { + // swallow namespace qualifiers before symbols + begin: hljs.IDENT_RE + '::' }, + { + className: 'symbol', + begin: hljs.UNDERSCORE_IDENT_RE + '(!|\\?)?:', + relevance: 0 + }, + { + className: 'symbol', + begin: ':(?!\\s)', + contains: [ + STRING, + { begin: RUBY_METHOD_RE } + ], + relevance: 0 + }, + NUMBER, + { + // negative-look forward attempts to prevent false matches like: + // @ident@ or $ident$ that might indicate this is not ruby at all + className: "variable", + begin: '(\\$\\W)|((\\$|@@?)(\\w+))(?=[^@$?])' + `(?![A-Za-z])(?![@$?'])` + }, + { + className: 'params', + begin: /\|(?!=)/, + end: /\|/, + excludeBegin: true, + excludeEnd: true, + relevance: 0, // this could be a lot of things (in other languages) other than params + keywords: RUBY_KEYWORDS + }, + { // regexp container + begin: '(' + hljs.RE_STARTERS_RE + '|unless)\\s*', + keywords: 'unless', + contains: [ + { + className: 'regexp', + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST + ], + illegal: /\n/, + variants: [ + { + begin: '/', + end: '/[a-z]*' + }, + { + begin: /%r\{/, + end: /\}[a-z]*/ + }, + { + begin: '%r\\(', + end: '\\)[a-z]*' + }, + { + begin: '%r!', + end: '![a-z]*' + }, + { + begin: '%r\\[', + end: '\\][a-z]*' + } + ] + } + ].concat(IRB_OBJECT, COMMENT_MODES), + relevance: 0 + } + ].concat(IRB_OBJECT, COMMENT_MODES); + + SUBST.contains = RUBY_DEFAULT_CONTAINS; + PARAMS.contains = RUBY_DEFAULT_CONTAINS; + + // >> + // ?> + const SIMPLE_PROMPT = "[>?]>"; + // irb(main):001:0> + const DEFAULT_PROMPT = "[\\w#]+\\(\\w+\\):\\d+:\\d+[>*]"; + const RVM_PROMPT = "(\\w+-)?\\d+\\.\\d+\\.\\d+(p\\d+)?[^\\d][^>]+>"; + + const IRB_DEFAULT = [ + { + begin: /^\s*=>/, + starts: { + end: '$', + contains: RUBY_DEFAULT_CONTAINS + } + }, + { + className: 'meta.prompt', + begin: '^(' + SIMPLE_PROMPT + "|" + DEFAULT_PROMPT + '|' + RVM_PROMPT + ')(?=[ ])', + starts: { + end: '$', + keywords: RUBY_KEYWORDS, + contains: RUBY_DEFAULT_CONTAINS + } + } + ]; + + COMMENT_MODES.unshift(IRB_OBJECT); + + return { + name: 'Ruby', + aliases: [ + 'rb', + 'gemspec', + 'podspec', + 'thor', + 'irb' + ], + keywords: RUBY_KEYWORDS, + illegal: /\/\*/, + contains: [ hljs.SHEBANG({ binary: "ruby" }) ] + .concat(IRB_DEFAULT) + .concat(COMMENT_MODES) + .concat(RUBY_DEFAULT_CONTAINS) + }; +} + +export { ruby as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/ruby.js.js b/frontend/node_modules/highlight.js/es/languages/ruby.js.js new file mode 100644 index 0000000..4756226 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ruby.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/ruby" instead of "highlight.js/lib/languages/ruby.js"' + ); + } + } + emitWarning(); + import lang from './ruby.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/ruleslanguage.js b/frontend/node_modules/highlight.js/es/languages/ruleslanguage.js new file mode 100644 index 0000000..837d379 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ruleslanguage.js @@ -0,0 +1,76 @@ +/* +Language: Oracle Rules Language +Author: Jason Jacobson +Description: The Oracle Utilities Rules Language is used to program the Oracle Utilities Applications acquired from LODESTAR Corporation. The products include Billing Component, LPSS, Pricing Component etc. through version 1.6.1. +Website: https://docs.oracle.com/cd/E17904_01/dev.1111/e10227/rlref.htm +Category: enterprise +*/ + +function ruleslanguage(hljs) { + return { + name: 'Oracle Rules Language', + keywords: { + keyword: + 'BILL_PERIOD BILL_START BILL_STOP RS_EFFECTIVE_START RS_EFFECTIVE_STOP RS_JURIS_CODE RS_OPCO_CODE ' + + 'INTDADDATTRIBUTE|5 INTDADDVMSG|5 INTDBLOCKOP|5 INTDBLOCKOPNA|5 INTDCLOSE|5 INTDCOUNT|5 ' + + 'INTDCOUNTSTATUSCODE|5 INTDCREATEMASK|5 INTDCREATEDAYMASK|5 INTDCREATEFACTORMASK|5 ' + + 'INTDCREATEHANDLE|5 INTDCREATEOVERRIDEDAYMASK|5 INTDCREATEOVERRIDEMASK|5 ' + + 'INTDCREATESTATUSCODEMASK|5 INTDCREATETOUPERIOD|5 INTDDELETE|5 INTDDIPTEST|5 INTDEXPORT|5 ' + + 'INTDGETERRORCODE|5 INTDGETERRORMESSAGE|5 INTDISEQUAL|5 INTDJOIN|5 INTDLOAD|5 INTDLOADACTUALCUT|5 ' + + 'INTDLOADDATES|5 INTDLOADHIST|5 INTDLOADLIST|5 INTDLOADLISTDATES|5 INTDLOADLISTENERGY|5 ' + + 'INTDLOADLISTHIST|5 INTDLOADRELATEDCHANNEL|5 INTDLOADSP|5 INTDLOADSTAGING|5 INTDLOADUOM|5 ' + + 'INTDLOADUOMDATES|5 INTDLOADUOMHIST|5 INTDLOADVERSION|5 INTDOPEN|5 INTDREADFIRST|5 INTDREADNEXT|5 ' + + 'INTDRECCOUNT|5 INTDRELEASE|5 INTDREPLACE|5 INTDROLLAVG|5 INTDROLLPEAK|5 INTDSCALAROP|5 INTDSCALE|5 ' + + 'INTDSETATTRIBUTE|5 INTDSETDSTPARTICIPANT|5 INTDSETSTRING|5 INTDSETVALUE|5 INTDSETVALUESTATUS|5 ' + + 'INTDSHIFTSTARTTIME|5 INTDSMOOTH|5 INTDSORT|5 INTDSPIKETEST|5 INTDSUBSET|5 INTDTOU|5 ' + + 'INTDTOURELEASE|5 INTDTOUVALUE|5 INTDUPDATESTATS|5 INTDVALUE|5 STDEV INTDDELETEEX|5 ' + + 'INTDLOADEXACTUAL|5 INTDLOADEXCUT|5 INTDLOADEXDATES|5 INTDLOADEX|5 INTDLOADEXRELATEDCHANNEL|5 ' + + 'INTDSAVEEX|5 MVLOAD|5 MVLOADACCT|5 MVLOADACCTDATES|5 MVLOADACCTHIST|5 MVLOADDATES|5 MVLOADHIST|5 ' + + 'MVLOADLIST|5 MVLOADLISTDATES|5 MVLOADLISTHIST|5 IF FOR NEXT DONE SELECT END CALL ABORT CLEAR CHANNEL FACTOR LIST NUMBER ' + + 'OVERRIDE SET WEEK DISTRIBUTIONNODE ELSE WHEN THEN OTHERWISE IENUM CSV INCLUDE LEAVE RIDER SAVE DELETE ' + + 'NOVALUE SECTION WARN SAVE_UPDATE DETERMINANT LABEL REPORT REVENUE EACH ' + + 'IN FROM TOTAL CHARGE BLOCK AND OR CSV_FILE RATE_CODE AUXILIARY_DEMAND ' + + 'UIDACCOUNT RS BILL_PERIOD_SELECT HOURS_PER_MONTH INTD_ERROR_STOP SEASON_SCHEDULE_NAME ' + + 'ACCOUNTFACTOR ARRAYUPPERBOUND CALLSTOREDPROC GETADOCONNECTION GETCONNECT GETDATASOURCE ' + + 'GETQUALIFIER GETUSERID HASVALUE LISTCOUNT LISTOP LISTUPDATE LISTVALUE PRORATEFACTOR RSPRORATE ' + + 'SETBINPATH SETDBMONITOR WQ_OPEN BILLINGHOURS DATE DATEFROMFLOAT DATETIMEFROMSTRING ' + + 'DATETIMETOSTRING DATETOFLOAT DAY DAYDIFF DAYNAME DBDATETIME HOUR MINUTE MONTH MONTHDIFF ' + + 'MONTHHOURS MONTHNAME ROUNDDATE SAMEWEEKDAYLASTYEAR SECOND WEEKDAY WEEKDIFF YEAR YEARDAY ' + + 'YEARSTR COMPSUM HISTCOUNT HISTMAX HISTMIN HISTMINNZ HISTVALUE MAXNRANGE MAXRANGE MINRANGE ' + + 'COMPIKVA COMPKVA COMPKVARFROMKQKW COMPLF IDATTR FLAG LF2KW LF2KWH MAXKW POWERFACTOR ' + + 'READING2USAGE AVGSEASON MAXSEASON MONTHLYMERGE SEASONVALUE SUMSEASON ACCTREADDATES ' + + 'ACCTTABLELOAD CONFIGADD CONFIGGET CREATEOBJECT CREATEREPORT EMAILCLIENT EXPBLKMDMUSAGE ' + + 'EXPMDMUSAGE EXPORT_USAGE FACTORINEFFECT GETUSERSPECIFIEDSTOP INEFFECT ISHOLIDAY RUNRATE ' + + 'SAVE_PROFILE SETREPORTTITLE USEREXIT WATFORRUNRATE TO TABLE ACOS ASIN ATAN ATAN2 BITAND CEIL ' + + 'COS COSECANT COSH COTANGENT DIVQUOT DIVREM EXP FABS FLOOR FMOD FREPM FREXPN LOG LOG10 MAX MAXN ' + + 'MIN MINNZ MODF POW ROUND ROUND2VALUE ROUNDINT SECANT SIN SINH SQROOT TAN TANH FLOAT2STRING ' + + 'FLOAT2STRINGNC INSTR LEFT LEN LTRIM MID RIGHT RTRIM STRING STRINGNC TOLOWER TOUPPER TRIM ' + + 'NUMDAYS READ_DATE STAGING', + built_in: + 'IDENTIFIER OPTIONS XML_ELEMENT XML_OP XML_ELEMENT_OF DOMDOCCREATE DOMDOCLOADFILE DOMDOCLOADXML ' + + 'DOMDOCSAVEFILE DOMDOCGETROOT DOMDOCADDPI DOMNODEGETNAME DOMNODEGETTYPE DOMNODEGETVALUE DOMNODEGETCHILDCT ' + + 'DOMNODEGETFIRSTCHILD DOMNODEGETSIBLING DOMNODECREATECHILDELEMENT DOMNODESETATTRIBUTE ' + + 'DOMNODEGETCHILDELEMENTCT DOMNODEGETFIRSTCHILDELEMENT DOMNODEGETSIBLINGELEMENT DOMNODEGETATTRIBUTECT ' + + 'DOMNODEGETATTRIBUTEI DOMNODEGETATTRIBUTEBYNAME DOMNODEGETBYNAME' + }, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.C_NUMBER_MODE, + { + className: 'literal', + variants: [ + { // looks like #-comment + begin: '#\\s+', + relevance: 0 + }, + { begin: '#[a-zA-Z .]+' } + ] + } + ] + }; +} + +export { ruleslanguage as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/ruleslanguage.js.js b/frontend/node_modules/highlight.js/es/languages/ruleslanguage.js.js new file mode 100644 index 0000000..be9e72e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/ruleslanguage.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/ruleslanguage" instead of "highlight.js/lib/languages/ruleslanguage.js"' + ); + } + } + emitWarning(); + import lang from './ruleslanguage.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/rust.js b/frontend/node_modules/highlight.js/es/languages/rust.js new file mode 100644 index 0000000..6629887 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/rust.js @@ -0,0 +1,326 @@ +/* +Language: Rust +Author: Andrey Vlasovskikh +Contributors: Roman Shmatov , Kasper Andersen +Website: https://www.rust-lang.org +Category: common, system +*/ + +/** @type LanguageFn */ + +function rust(hljs) { + const regex = hljs.regex; + // ============================================ + // Added to support the r# keyword, which is a raw identifier in Rust. + const RAW_IDENTIFIER = /(r#)?/; + const UNDERSCORE_IDENT_RE = regex.concat(RAW_IDENTIFIER, hljs.UNDERSCORE_IDENT_RE); + const IDENT_RE = regex.concat(RAW_IDENTIFIER, hljs.IDENT_RE); + // ============================================ + const FUNCTION_INVOKE = { + className: "title.function.invoke", + relevance: 0, + begin: regex.concat( + /\b/, + /(?!let|for|while|if|else|match\b)/, + IDENT_RE, + regex.lookahead(/\s*\(/)) + }; + const NUMBER_SUFFIX = '([ui](8|16|32|64|128|size)|f(32|64))\?'; + const KEYWORDS = [ + "abstract", + "as", + "async", + "await", + "become", + "box", + "break", + "const", + "continue", + "crate", + "do", + "dyn", + "else", + "enum", + "extern", + "false", + "final", + "fn", + "for", + "if", + "impl", + "in", + "let", + "loop", + "macro", + "match", + "mod", + "move", + "mut", + "override", + "priv", + "pub", + "ref", + "return", + "self", + "Self", + "static", + "struct", + "super", + "trait", + "true", + "try", + "type", + "typeof", + "union", + "unsafe", + "unsized", + "use", + "virtual", + "where", + "while", + "yield" + ]; + const LITERALS = [ + "true", + "false", + "Some", + "None", + "Ok", + "Err" + ]; + const BUILTINS = [ + // functions + 'drop ', + // traits + "Copy", + "Send", + "Sized", + "Sync", + "Drop", + "Fn", + "FnMut", + "FnOnce", + "ToOwned", + "Clone", + "Debug", + "PartialEq", + "PartialOrd", + "Eq", + "Ord", + "AsRef", + "AsMut", + "Into", + "From", + "Default", + "Iterator", + "Extend", + "IntoIterator", + "DoubleEndedIterator", + "ExactSizeIterator", + "SliceConcatExt", + "ToString", + // macros + "assert!", + "assert_eq!", + "bitflags!", + "bytes!", + "cfg!", + "col!", + "concat!", + "concat_idents!", + "debug_assert!", + "debug_assert_eq!", + "env!", + "eprintln!", + "panic!", + "file!", + "format!", + "format_args!", + "include_bytes!", + "include_str!", + "line!", + "local_data_key!", + "module_path!", + "option_env!", + "print!", + "println!", + "select!", + "stringify!", + "try!", + "unimplemented!", + "unreachable!", + "vec!", + "write!", + "writeln!", + "macro_rules!", + "assert_ne!", + "debug_assert_ne!" + ]; + const TYPES = [ + "i8", + "i16", + "i32", + "i64", + "i128", + "isize", + "u8", + "u16", + "u32", + "u64", + "u128", + "usize", + "f32", + "f64", + "str", + "char", + "bool", + "Box", + "Option", + "Result", + "String", + "Vec" + ]; + return { + name: 'Rust', + aliases: [ 'rs' ], + keywords: { + $pattern: hljs.IDENT_RE + '!?', + type: TYPES, + keyword: KEYWORDS, + literal: LITERALS, + built_in: BUILTINS + }, + illegal: '' + }, + FUNCTION_INVOKE + ] + }; +} + +export { rust as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/rust.js.js b/frontend/node_modules/highlight.js/es/languages/rust.js.js new file mode 100644 index 0000000..298f105 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/rust.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/rust" instead of "highlight.js/lib/languages/rust.js"' + ); + } + } + emitWarning(); + import lang from './rust.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/sas.js b/frontend/node_modules/highlight.js/es/languages/sas.js new file mode 100644 index 0000000..c866fa6 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/sas.js @@ -0,0 +1,557 @@ +/* +Language: SAS +Author: Mauricio Caceres +Description: Syntax Highlighting for SAS +Category: scientific +*/ + +/** @type LanguageFn */ +function sas(hljs) { + const regex = hljs.regex; + // Data step and PROC SQL statements + const SAS_KEYWORDS = [ + "do", + "if", + "then", + "else", + "end", + "until", + "while", + "abort", + "array", + "attrib", + "by", + "call", + "cards", + "cards4", + "catname", + "continue", + "datalines", + "datalines4", + "delete", + "delim", + "delimiter", + "display", + "dm", + "drop", + "endsas", + "error", + "file", + "filename", + "footnote", + "format", + "goto", + "in", + "infile", + "informat", + "input", + "keep", + "label", + "leave", + "length", + "libname", + "link", + "list", + "lostcard", + "merge", + "missing", + "modify", + "options", + "output", + "out", + "page", + "put", + "redirect", + "remove", + "rename", + "replace", + "retain", + "return", + "select", + "set", + "skip", + "startsas", + "stop", + "title", + "update", + "waitsas", + "where", + "window", + "x|0", + "systask", + "add", + "and", + "alter", + "as", + "cascade", + "check", + "create", + "delete", + "describe", + "distinct", + "drop", + "foreign", + "from", + "group", + "having", + "index", + "insert", + "into", + "in", + "key", + "like", + "message", + "modify", + "msgtype", + "not", + "null", + "on", + "or", + "order", + "primary", + "references", + "reset", + "restrict", + "select", + "set", + "table", + "unique", + "update", + "validate", + "view", + "where" + ]; + + // Built-in SAS functions + const FUNCTIONS = [ + "abs", + "addr", + "airy", + "arcos", + "arsin", + "atan", + "attrc", + "attrn", + "band", + "betainv", + "blshift", + "bnot", + "bor", + "brshift", + "bxor", + "byte", + "cdf", + "ceil", + "cexist", + "cinv", + "close", + "cnonct", + "collate", + "compbl", + "compound", + "compress", + "cos", + "cosh", + "css", + "curobs", + "cv", + "daccdb", + "daccdbsl", + "daccsl", + "daccsyd", + "dacctab", + "dairy", + "date", + "datejul", + "datepart", + "datetime", + "day", + "dclose", + "depdb", + "depdbsl", + "depdbsl", + "depsl", + "depsl", + "depsyd", + "depsyd", + "deptab", + "deptab", + "dequote", + "dhms", + "dif", + "digamma", + "dim", + "dinfo", + "dnum", + "dopen", + "doptname", + "doptnum", + "dread", + "dropnote", + "dsname", + "erf", + "erfc", + "exist", + "exp", + "fappend", + "fclose", + "fcol", + "fdelete", + "fetch", + "fetchobs", + "fexist", + "fget", + "fileexist", + "filename", + "fileref", + "finfo", + "finv", + "fipname", + "fipnamel", + "fipstate", + "floor", + "fnonct", + "fnote", + "fopen", + "foptname", + "foptnum", + "fpoint", + "fpos", + "fput", + "fread", + "frewind", + "frlen", + "fsep", + "fuzz", + "fwrite", + "gaminv", + "gamma", + "getoption", + "getvarc", + "getvarn", + "hbound", + "hms", + "hosthelp", + "hour", + "ibessel", + "index", + "indexc", + "indexw", + "input", + "inputc", + "inputn", + "int", + "intck", + "intnx", + "intrr", + "irr", + "jbessel", + "juldate", + "kurtosis", + "lag", + "lbound", + "left", + "length", + "lgamma", + "libname", + "libref", + "log", + "log10", + "log2", + "logpdf", + "logpmf", + "logsdf", + "lowcase", + "max", + "mdy", + "mean", + "min", + "minute", + "mod", + "month", + "mopen", + "mort", + "n", + "netpv", + "nmiss", + "normal", + "note", + "npv", + "open", + "ordinal", + "pathname", + "pdf", + "peek", + "peekc", + "pmf", + "point", + "poisson", + "poke", + "probbeta", + "probbnml", + "probchi", + "probf", + "probgam", + "probhypr", + "probit", + "probnegb", + "probnorm", + "probt", + "put", + "putc", + "putn", + "qtr", + "quote", + "ranbin", + "rancau", + "ranexp", + "rangam", + "range", + "rank", + "rannor", + "ranpoi", + "rantbl", + "rantri", + "ranuni", + "repeat", + "resolve", + "reverse", + "rewind", + "right", + "round", + "saving", + "scan", + "sdf", + "second", + "sign", + "sin", + "sinh", + "skewness", + "soundex", + "spedis", + "sqrt", + "std", + "stderr", + "stfips", + "stname", + "stnamel", + "substr", + "sum", + "symget", + "sysget", + "sysmsg", + "sysprod", + "sysrc", + "system", + "tan", + "tanh", + "time", + "timepart", + "tinv", + "tnonct", + "today", + "translate", + "tranwrd", + "trigamma", + "trim", + "trimn", + "trunc", + "uniform", + "upcase", + "uss", + "var", + "varfmt", + "varinfmt", + "varlabel", + "varlen", + "varname", + "varnum", + "varray", + "varrayx", + "vartype", + "verify", + "vformat", + "vformatd", + "vformatdx", + "vformatn", + "vformatnx", + "vformatw", + "vformatwx", + "vformatx", + "vinarray", + "vinarrayx", + "vinformat", + "vinformatd", + "vinformatdx", + "vinformatn", + "vinformatnx", + "vinformatw", + "vinformatwx", + "vinformatx", + "vlabel", + "vlabelx", + "vlength", + "vlengthx", + "vname", + "vnamex", + "vtype", + "vtypex", + "weekday", + "year", + "yyq", + "zipfips", + "zipname", + "zipnamel", + "zipstate" + ]; + + // Built-in macro functions + const MACRO_FUNCTIONS = [ + "bquote", + "nrbquote", + "cmpres", + "qcmpres", + "compstor", + "datatyp", + "display", + "do", + "else", + "end", + "eval", + "global", + "goto", + "if", + "index", + "input", + "keydef", + "label", + "left", + "length", + "let", + "local", + "lowcase", + "macro", + "mend", + "nrbquote", + "nrquote", + "nrstr", + "put", + "qcmpres", + "qleft", + "qlowcase", + "qscan", + "qsubstr", + "qsysfunc", + "qtrim", + "quote", + "qupcase", + "scan", + "str", + "substr", + "superq", + "syscall", + "sysevalf", + "sysexec", + "sysfunc", + "sysget", + "syslput", + "sysprod", + "sysrc", + "sysrput", + "then", + "to", + "trim", + "unquote", + "until", + "upcase", + "verify", + "while", + "window" + ]; + + const LITERALS = [ + "null", + "missing", + "_all_", + "_automatic_", + "_character_", + "_infile_", + "_n_", + "_name_", + "_null_", + "_numeric_", + "_user_", + "_webout_" + ]; + + return { + name: 'SAS', + case_insensitive: true, + keywords: { + literal: LITERALS, + keyword: SAS_KEYWORDS + }, + contains: [ + { + // Distinct highlight for proc , data, run, quit + className: 'keyword', + begin: /^\s*(proc [\w\d_]+|data|run|quit)[\s;]/ + }, + { + // Macro variables + className: 'variable', + begin: /&[a-zA-Z_&][a-zA-Z0-9_]*\.?/ + }, + { + begin: [ + /^\s*/, + /datalines;|cards;/, + /(?:.*\n)+/, + /^\s*;\s*$/ + ], + className: { + 2: "keyword", + 3: "string" + } + }, + { + begin: [ + /%mend|%macro/, + /\s+/, + /[a-zA-Z_&][a-zA-Z0-9_]*/ + ], + className: { + 1: "built_in", + 3: "title.function" + } + }, + { // Built-in macro variables + className: 'built_in', + begin: '%' + regex.either(...MACRO_FUNCTIONS) + }, + { + // User-defined macro functions + className: 'title.function', + begin: /%[a-zA-Z_][a-zA-Z_0-9]*/ + }, + { + // TODO: this is most likely an incorrect classification + // built_in may need more nuance + // https://github.com/highlightjs/highlight.js/issues/2521 + className: 'meta', + begin: regex.either(...FUNCTIONS) + '(?=\\()' + }, + { + className: 'string', + variants: [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE + ] + }, + hljs.COMMENT('\\*', ';'), + hljs.C_BLOCK_COMMENT_MODE + ] + }; +} + +export { sas as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/sas.js.js b/frontend/node_modules/highlight.js/es/languages/sas.js.js new file mode 100644 index 0000000..04f9f69 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/sas.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/sas" instead of "highlight.js/lib/languages/sas.js"' + ); + } + } + emitWarning(); + import lang from './sas.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/scala.js b/frontend/node_modules/highlight.js/es/languages/scala.js new file mode 100644 index 0000000..34ce556 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/scala.js @@ -0,0 +1,214 @@ +/* +Language: Scala +Category: functional +Author: Jan Berkel +Contributors: Erik Osheim +Website: https://www.scala-lang.org +*/ + +function scala(hljs) { + const regex = hljs.regex; + const ANNOTATION = { + className: 'meta', + begin: '@[A-Za-z]+' + }; + + // used in strings for escaping/interpolation/substitution + const SUBST = { + className: 'subst', + variants: [ + { begin: '\\$[A-Za-z0-9_]+' }, + { + begin: /\$\{/, + end: /\}/ + } + ] + }; + + const STRING = { + className: 'string', + variants: [ + { + begin: '"""', + end: '"""' + }, + { + begin: '"', + end: '"', + illegal: '\\n', + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + begin: '[a-z]+"', + end: '"', + illegal: '\\n', + contains: [ + hljs.BACKSLASH_ESCAPE, + SUBST + ] + }, + { + className: 'string', + begin: '[a-z]+"""', + end: '"""', + contains: [ SUBST ], + relevance: 10 + } + ] + + }; + + const TYPE = { + className: 'type', + begin: '\\b[A-Z][A-Za-z0-9_]*', + relevance: 0 + }; + + const NAME = { + className: 'title', + begin: /[^0-9\n\t "'(),.`{}\[\]:;][^\n\t "'(),.`{}\[\]:;]+|[^0-9\n\t "'(),.`{}\[\]:;=]/, + relevance: 0 + }; + + const CLASS = { + className: 'class', + beginKeywords: 'class object trait type', + end: /[:={\[\n;]/, + excludeEnd: true, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + { + beginKeywords: 'extends with', + relevance: 10 + }, + { + begin: /\[/, + end: /\]/, + excludeBegin: true, + excludeEnd: true, + relevance: 0, + contains: [ + TYPE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + ] + }, + { + className: 'params', + begin: /\(/, + end: /\)/, + excludeBegin: true, + excludeEnd: true, + relevance: 0, + contains: [ + TYPE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + ] + }, + NAME + ] + }; + + const METHOD = { + className: 'function', + beginKeywords: 'def', + end: regex.lookahead(/[:={\[(\n;]/), + contains: [ NAME ] + }; + + const EXTENSION = { + begin: [ + /^\s*/, // Is first token on the line + 'extension', + /\s+(?=[[(])/, // followed by at least one space and `[` or `(` + ], + beginScope: { 2: "keyword", } + }; + + const END = { + begin: [ + /^\s*/, // Is first token on the line + /end/, + /\s+/, + /(extension\b)?/, // `extension` is the only marker that follows an `end` that cannot be captured by another rule. + ], + beginScope: { + 2: "keyword", + 4: "keyword", + } + }; + + // TODO: use negative look-behind in future + // /(?', + /\s+/, + /using/, + /\s+/, + /\S+/ + ], + beginScope: { + 1: "comment", + 3: "keyword", + 5: "type" + }, + end: /$/, + contains: [ + DIRECTIVE_VALUE, + ] + }; + + return { + name: 'Scala', + keywords: { + literal: 'true false null', + keyword: 'type yield lazy override def with val var sealed abstract private trait object if then forSome for while do throw finally protected extends import final return else break new catch super class case package default try this match continue throws implicit export enum given transparent' + }, + contains: [ + USING_DIRECTIVE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + STRING, + TYPE, + METHOD, + CLASS, + hljs.C_NUMBER_MODE, + EXTENSION, + END, + ...INLINE_MODES, + USING_PARAM_CLAUSE, + ANNOTATION + ] + }; +} + +export { scala as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/scala.js.js b/frontend/node_modules/highlight.js/es/languages/scala.js.js new file mode 100644 index 0000000..bb1cefc --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/scala.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/scala" instead of "highlight.js/lib/languages/scala.js"' + ); + } + } + emitWarning(); + import lang from './scala.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/scheme.js b/frontend/node_modules/highlight.js/es/languages/scheme.js new file mode 100644 index 0000000..1d6b34a --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/scheme.js @@ -0,0 +1,196 @@ +/* +Language: Scheme +Description: Scheme is a programming language in the Lisp family. + (keywords based on http://community.schemewiki.org/?scheme-keywords) +Author: JP Verkamp +Contributors: Ivan Sagalaev +Origin: clojure.js +Website: http://community.schemewiki.org/?what-is-scheme +Category: lisp +*/ + +function scheme(hljs) { + const SCHEME_IDENT_RE = '[^\\(\\)\\[\\]\\{\\}",\'`;#|\\\\\\s]+'; + const SCHEME_SIMPLE_NUMBER_RE = '(-|\\+)?\\d+([./]\\d+)?'; + const SCHEME_COMPLEX_NUMBER_RE = SCHEME_SIMPLE_NUMBER_RE + '[+\\-]' + SCHEME_SIMPLE_NUMBER_RE + 'i'; + const KEYWORDS = { + $pattern: SCHEME_IDENT_RE, + built_in: + 'case-lambda call/cc class define-class exit-handler field import ' + + 'inherit init-field interface let*-values let-values let/ec mixin ' + + 'opt-lambda override protect provide public rename require ' + + 'require-for-syntax syntax syntax-case syntax-error unit/sig unless ' + + 'when with-syntax and begin call-with-current-continuation ' + + 'call-with-input-file call-with-output-file case cond define ' + + 'define-syntax delay do dynamic-wind else for-each if lambda let let* ' + + 'let-syntax letrec letrec-syntax map or syntax-rules \' * + , ,@ - ... / ' + + '; < <= = => > >= ` abs acos angle append apply asin assoc assq assv atan ' + + 'boolean? caar cadr call-with-input-file call-with-output-file ' + + 'call-with-values car cdddar cddddr cdr ceiling char->integer ' + + 'char-alphabetic? char-ci<=? char-ci=? char-ci>? ' + + 'char-downcase char-lower-case? char-numeric? char-ready? char-upcase ' + + 'char-upper-case? char-whitespace? char<=? char=? char>? ' + + 'char? close-input-port close-output-port complex? cons cos ' + + 'current-input-port current-output-port denominator display eof-object? ' + + 'eq? equal? eqv? eval even? exact->inexact exact? exp expt floor ' + + 'force gcd imag-part inexact->exact inexact? input-port? integer->char ' + + 'integer? interaction-environment lcm length list list->string ' + + 'list->vector list-ref list-tail list? load log magnitude make-polar ' + + 'make-rectangular make-string make-vector max member memq memv min ' + + 'modulo negative? newline not null-environment null? number->string ' + + 'number? numerator odd? open-input-file open-output-file output-port? ' + + 'pair? peek-char port? positive? procedure? quasiquote quote quotient ' + + 'rational? rationalize read read-char real-part real? remainder reverse ' + + 'round scheme-report-environment set! set-car! set-cdr! sin sqrt string ' + + 'string->list string->number string->symbol string-append string-ci<=? ' + + 'string-ci=? string-ci>? string-copy ' + + 'string-fill! string-length string-ref string-set! string<=? string=? string>? string? substring symbol->string symbol? ' + + 'tan transcript-off transcript-on truncate values vector ' + + 'vector->list vector-fill! vector-length vector-ref vector-set! ' + + 'with-input-from-file with-output-to-file write write-char zero?' + }; + + const LITERAL = { + className: 'literal', + begin: '(#t|#f|#\\\\' + SCHEME_IDENT_RE + '|#\\\\.)' + }; + + const NUMBER = { + className: 'number', + variants: [ + { + begin: SCHEME_SIMPLE_NUMBER_RE, + relevance: 0 + }, + { + begin: SCHEME_COMPLEX_NUMBER_RE, + relevance: 0 + }, + { begin: '#b[0-1]+(/[0-1]+)?' }, + { begin: '#o[0-7]+(/[0-7]+)?' }, + { begin: '#x[0-9a-f]+(/[0-9a-f]+)?' } + ] + }; + + const STRING = hljs.QUOTE_STRING_MODE; + + const COMMENT_MODES = [ + hljs.COMMENT( + ';', + '$', + { relevance: 0 } + ), + hljs.COMMENT('#\\|', '\\|#') + ]; + + const IDENT = { + begin: SCHEME_IDENT_RE, + relevance: 0 + }; + + const QUOTED_IDENT = { + className: 'symbol', + begin: '\'' + SCHEME_IDENT_RE + }; + + const BODY = { + endsWithParent: true, + relevance: 0 + }; + + const QUOTED_LIST = { + variants: [ + { begin: /'/ }, + { begin: '`' } + ], + contains: [ + { + begin: '\\(', + end: '\\)', + contains: [ + 'self', + LITERAL, + STRING, + NUMBER, + IDENT, + QUOTED_IDENT + ] + } + ] + }; + + const NAME = { + className: 'name', + relevance: 0, + begin: SCHEME_IDENT_RE, + keywords: KEYWORDS + }; + + const LAMBDA = { + begin: /lambda/, + endsWithParent: true, + returnBegin: true, + contains: [ + NAME, + { + endsParent: true, + variants: [ + { + begin: /\(/, + end: /\)/ + }, + { + begin: /\[/, + end: /\]/ + } + ], + contains: [ IDENT ] + } + ] + }; + + const LIST = { + variants: [ + { + begin: '\\(', + end: '\\)' + }, + { + begin: '\\[', + end: '\\]' + } + ], + contains: [ + LAMBDA, + NAME, + BODY + ] + }; + + BODY.contains = [ + LITERAL, + NUMBER, + STRING, + IDENT, + QUOTED_IDENT, + QUOTED_LIST, + LIST + ].concat(COMMENT_MODES); + + return { + name: 'Scheme', + aliases: ['scm'], + illegal: /\S/, + contains: [ + hljs.SHEBANG(), + NUMBER, + STRING, + QUOTED_IDENT, + QUOTED_LIST, + LIST + ].concat(COMMENT_MODES) + }; +} + +export { scheme as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/scheme.js.js b/frontend/node_modules/highlight.js/es/languages/scheme.js.js new file mode 100644 index 0000000..98d340b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/scheme.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/scheme" instead of "highlight.js/lib/languages/scheme.js"' + ); + } + } + emitWarning(); + import lang from './scheme.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/scilab.js b/frontend/node_modules/highlight.js/es/languages/scilab.js new file mode 100644 index 0000000..2f5ee09 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/scilab.js @@ -0,0 +1,73 @@ +/* +Language: Scilab +Author: Sylvestre Ledru +Origin: matlab.js +Description: Scilab is a port from Matlab +Website: https://www.scilab.org +Category: scientific +*/ + +function scilab(hljs) { + const COMMON_CONTAINS = [ + hljs.C_NUMBER_MODE, + { + className: 'string', + begin: '\'|\"', + end: '\'|\"', + contains: [ + hljs.BACKSLASH_ESCAPE, + { begin: '\'\'' } + ] + } + ]; + + return { + name: 'Scilab', + aliases: [ 'sci' ], + keywords: { + $pattern: /%?\w+/, + keyword: 'abort break case clear catch continue do elseif else endfunction end for function ' + + 'global if pause return resume select try then while', + literal: + '%f %F %t %T %pi %eps %inf %nan %e %i %z %s', + built_in: // Scilab has more than 2000 functions. Just list the most commons + 'abs and acos asin atan ceil cd chdir clearglobal cosh cos cumprod deff disp error ' + + 'exec execstr exists exp eye gettext floor fprintf fread fsolve imag isdef isempty ' + + 'isinfisnan isvector lasterror length load linspace list listfiles log10 log2 log ' + + 'max min msprintf mclose mopen ones or pathconvert poly printf prod pwd rand real ' + + 'round sinh sin size gsort sprintf sqrt strcat strcmps tring sum system tanh tan ' + + 'type typename warning zeros matrix' + }, + illegal: '("|#|/\\*|\\s+/\\w+)', + contains: [ + { + className: 'function', + beginKeywords: 'function', + end: '$', + contains: [ + hljs.UNDERSCORE_TITLE_MODE, + { + className: 'params', + begin: '\\(', + end: '\\)' + } + ] + }, + // seems to be a guard against [ident]' or [ident]. + // perhaps to prevent attributes from flagging as keywords? + { + begin: '[a-zA-Z_][a-zA-Z_0-9]*[\\.\']+', + relevance: 0 + }, + { + begin: '\\[', + end: '\\][\\.\']*', + relevance: 0, + contains: COMMON_CONTAINS + }, + hljs.COMMENT('//', '$') + ].concat(COMMON_CONTAINS) + }; +} + +export { scilab as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/scilab.js.js b/frontend/node_modules/highlight.js/es/languages/scilab.js.js new file mode 100644 index 0000000..f618d43 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/scilab.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/scilab" instead of "highlight.js/lib/languages/scilab.js"' + ); + } + } + emitWarning(); + import lang from './scilab.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/scss.js b/frontend/node_modules/highlight.js/es/languages/scss.js new file mode 100644 index 0000000..a379f39 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/scss.js @@ -0,0 +1,939 @@ +const MODES = (hljs) => { + return { + IMPORTANT: { + scope: 'meta', + begin: '!important' + }, + BLOCK_COMMENT: hljs.C_BLOCK_COMMENT_MODE, + HEXCOLOR: { + scope: 'number', + begin: /#(([0-9a-fA-F]{3,4})|(([0-9a-fA-F]{2}){3,4}))\b/ + }, + FUNCTION_DISPATCH: { + className: "built_in", + begin: /[\w-]+(?=\()/ + }, + ATTRIBUTE_SELECTOR_MODE: { + scope: 'selector-attr', + begin: /\[/, + end: /\]/, + illegal: '$', + contains: [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE + ] + }, + CSS_NUMBER_MODE: { + scope: 'number', + begin: hljs.NUMBER_RE + '(' + + '%|em|ex|ch|rem' + + '|vw|vh|vmin|vmax' + + '|cm|mm|in|pt|pc|px' + + '|deg|grad|rad|turn' + + '|s|ms' + + '|Hz|kHz' + + '|dpi|dpcm|dppx' + + ')?', + relevance: 0 + }, + CSS_VARIABLE: { + className: "attr", + begin: /--[A-Za-z_][A-Za-z0-9_-]*/ + } + }; +}; + +const HTML_TAGS = [ + 'a', + 'abbr', + 'address', + 'article', + 'aside', + 'audio', + 'b', + 'blockquote', + 'body', + 'button', + 'canvas', + 'caption', + 'cite', + 'code', + 'dd', + 'del', + 'details', + 'dfn', + 'div', + 'dl', + 'dt', + 'em', + 'fieldset', + 'figcaption', + 'figure', + 'footer', + 'form', + 'h1', + 'h2', + 'h3', + 'h4', + 'h5', + 'h6', + 'header', + 'hgroup', + 'html', + 'i', + 'iframe', + 'img', + 'input', + 'ins', + 'kbd', + 'label', + 'legend', + 'li', + 'main', + 'mark', + 'menu', + 'nav', + 'object', + 'ol', + 'optgroup', + 'option', + 'p', + 'picture', + 'q', + 'quote', + 'samp', + 'section', + 'select', + 'source', + 'span', + 'strong', + 'summary', + 'sup', + 'table', + 'tbody', + 'td', + 'textarea', + 'tfoot', + 'th', + 'thead', + 'time', + 'tr', + 'ul', + 'var', + 'video' +]; + +const SVG_TAGS = [ + 'defs', + 'g', + 'marker', + 'mask', + 'pattern', + 'svg', + 'switch', + 'symbol', + 'feBlend', + 'feColorMatrix', + 'feComponentTransfer', + 'feComposite', + 'feConvolveMatrix', + 'feDiffuseLighting', + 'feDisplacementMap', + 'feFlood', + 'feGaussianBlur', + 'feImage', + 'feMerge', + 'feMorphology', + 'feOffset', + 'feSpecularLighting', + 'feTile', + 'feTurbulence', + 'linearGradient', + 'radialGradient', + 'stop', + 'circle', + 'ellipse', + 'image', + 'line', + 'path', + 'polygon', + 'polyline', + 'rect', + 'text', + 'use', + 'textPath', + 'tspan', + 'foreignObject', + 'clipPath' +]; + +const TAGS = [ + ...HTML_TAGS, + ...SVG_TAGS, +]; + +// Sorting, then reversing makes sure longer attributes/elements like +// `font-weight` are matched fully instead of getting false positives on say `font` + +const MEDIA_FEATURES = [ + 'any-hover', + 'any-pointer', + 'aspect-ratio', + 'color', + 'color-gamut', + 'color-index', + 'device-aspect-ratio', + 'device-height', + 'device-width', + 'display-mode', + 'forced-colors', + 'grid', + 'height', + 'hover', + 'inverted-colors', + 'monochrome', + 'orientation', + 'overflow-block', + 'overflow-inline', + 'pointer', + 'prefers-color-scheme', + 'prefers-contrast', + 'prefers-reduced-motion', + 'prefers-reduced-transparency', + 'resolution', + 'scan', + 'scripting', + 'update', + 'width', + // TODO: find a better solution? + 'min-width', + 'max-width', + 'min-height', + 'max-height' +].sort().reverse(); + +// https://developer.mozilla.org/en-US/docs/Web/CSS/Pseudo-classes +const PSEUDO_CLASSES = [ + 'active', + 'any-link', + 'blank', + 'checked', + 'current', + 'default', + 'defined', + 'dir', // dir() + 'disabled', + 'drop', + 'empty', + 'enabled', + 'first', + 'first-child', + 'first-of-type', + 'fullscreen', + 'future', + 'focus', + 'focus-visible', + 'focus-within', + 'has', // has() + 'host', // host or host() + 'host-context', // host-context() + 'hover', + 'indeterminate', + 'in-range', + 'invalid', + 'is', // is() + 'lang', // lang() + 'last-child', + 'last-of-type', + 'left', + 'link', + 'local-link', + 'not', // not() + 'nth-child', // nth-child() + 'nth-col', // nth-col() + 'nth-last-child', // nth-last-child() + 'nth-last-col', // nth-last-col() + 'nth-last-of-type', //nth-last-of-type() + 'nth-of-type', //nth-of-type() + 'only-child', + 'only-of-type', + 'optional', + 'out-of-range', + 'past', + 'placeholder-shown', + 'read-only', + 'read-write', + 'required', + 'right', + 'root', + 'scope', + 'target', + 'target-within', + 'user-invalid', + 'valid', + 'visited', + 'where' // where() +].sort().reverse(); + +// https://developer.mozilla.org/en-US/docs/Web/CSS/Pseudo-elements +const PSEUDO_ELEMENTS = [ + 'after', + 'backdrop', + 'before', + 'cue', + 'cue-region', + 'first-letter', + 'first-line', + 'grammar-error', + 'marker', + 'part', + 'placeholder', + 'selection', + 'slotted', + 'spelling-error' +].sort().reverse(); + +const ATTRIBUTES = [ + 'accent-color', + 'align-content', + 'align-items', + 'align-self', + 'alignment-baseline', + 'all', + 'anchor-name', + 'animation', + 'animation-composition', + 'animation-delay', + 'animation-direction', + 'animation-duration', + 'animation-fill-mode', + 'animation-iteration-count', + 'animation-name', + 'animation-play-state', + 'animation-range', + 'animation-range-end', + 'animation-range-start', + 'animation-timeline', + 'animation-timing-function', + 'appearance', + 'aspect-ratio', + 'backdrop-filter', + 'backface-visibility', + 'background', + 'background-attachment', + 'background-blend-mode', + 'background-clip', + 'background-color', + 'background-image', + 'background-origin', + 'background-position', + 'background-position-x', + 'background-position-y', + 'background-repeat', + 'background-size', + 'baseline-shift', + 'block-size', + 'border', + 'border-block', + 'border-block-color', + 'border-block-end', + 'border-block-end-color', + 'border-block-end-style', + 'border-block-end-width', + 'border-block-start', + 'border-block-start-color', + 'border-block-start-style', + 'border-block-start-width', + 'border-block-style', + 'border-block-width', + 'border-bottom', + 'border-bottom-color', + 'border-bottom-left-radius', + 'border-bottom-right-radius', + 'border-bottom-style', + 'border-bottom-width', + 'border-collapse', + 'border-color', + 'border-end-end-radius', + 'border-end-start-radius', + 'border-image', + 'border-image-outset', + 'border-image-repeat', + 'border-image-slice', + 'border-image-source', + 'border-image-width', + 'border-inline', + 'border-inline-color', + 'border-inline-end', + 'border-inline-end-color', + 'border-inline-end-style', + 'border-inline-end-width', + 'border-inline-start', + 'border-inline-start-color', + 'border-inline-start-style', + 'border-inline-start-width', + 'border-inline-style', + 'border-inline-width', + 'border-left', + 'border-left-color', + 'border-left-style', + 'border-left-width', + 'border-radius', + 'border-right', + 'border-right-color', + 'border-right-style', + 'border-right-width', + 'border-spacing', + 'border-start-end-radius', + 'border-start-start-radius', + 'border-style', + 'border-top', + 'border-top-color', + 'border-top-left-radius', + 'border-top-right-radius', + 'border-top-style', + 'border-top-width', + 'border-width', + 'bottom', + 'box-align', + 'box-decoration-break', + 'box-direction', + 'box-flex', + 'box-flex-group', + 'box-lines', + 'box-ordinal-group', + 'box-orient', + 'box-pack', + 'box-shadow', + 'box-sizing', + 'break-after', + 'break-before', + 'break-inside', + 'caption-side', + 'caret-color', + 'clear', + 'clip', + 'clip-path', + 'clip-rule', + 'color', + 'color-interpolation', + 'color-interpolation-filters', + 'color-profile', + 'color-rendering', + 'color-scheme', + 'column-count', + 'column-fill', + 'column-gap', + 'column-rule', + 'column-rule-color', + 'column-rule-style', + 'column-rule-width', + 'column-span', + 'column-width', + 'columns', + 'contain', + 'contain-intrinsic-block-size', + 'contain-intrinsic-height', + 'contain-intrinsic-inline-size', + 'contain-intrinsic-size', + 'contain-intrinsic-width', + 'container', + 'container-name', + 'container-type', + 'content', + 'content-visibility', + 'counter-increment', + 'counter-reset', + 'counter-set', + 'cue', + 'cue-after', + 'cue-before', + 'cursor', + 'cx', + 'cy', + 'direction', + 'display', + 'dominant-baseline', + 'empty-cells', + 'enable-background', + 'field-sizing', + 'fill', + 'fill-opacity', + 'fill-rule', + 'filter', + 'flex', + 'flex-basis', + 'flex-direction', + 'flex-flow', + 'flex-grow', + 'flex-shrink', + 'flex-wrap', + 'float', + 'flood-color', + 'flood-opacity', + 'flow', + 'font', + 'font-display', + 'font-family', + 'font-feature-settings', + 'font-kerning', + 'font-language-override', + 'font-optical-sizing', + 'font-palette', + 'font-size', + 'font-size-adjust', + 'font-smooth', + 'font-smoothing', + 'font-stretch', + 'font-style', + 'font-synthesis', + 'font-synthesis-position', + 'font-synthesis-small-caps', + 'font-synthesis-style', + 'font-synthesis-weight', + 'font-variant', + 'font-variant-alternates', + 'font-variant-caps', + 'font-variant-east-asian', + 'font-variant-emoji', + 'font-variant-ligatures', + 'font-variant-numeric', + 'font-variant-position', + 'font-variation-settings', + 'font-weight', + 'forced-color-adjust', + 'gap', + 'glyph-orientation-horizontal', + 'glyph-orientation-vertical', + 'grid', + 'grid-area', + 'grid-auto-columns', + 'grid-auto-flow', + 'grid-auto-rows', + 'grid-column', + 'grid-column-end', + 'grid-column-start', + 'grid-gap', + 'grid-row', + 'grid-row-end', + 'grid-row-start', + 'grid-template', + 'grid-template-areas', + 'grid-template-columns', + 'grid-template-rows', + 'hanging-punctuation', + 'height', + 'hyphenate-character', + 'hyphenate-limit-chars', + 'hyphens', + 'icon', + 'image-orientation', + 'image-rendering', + 'image-resolution', + 'ime-mode', + 'initial-letter', + 'initial-letter-align', + 'inline-size', + 'inset', + 'inset-area', + 'inset-block', + 'inset-block-end', + 'inset-block-start', + 'inset-inline', + 'inset-inline-end', + 'inset-inline-start', + 'isolation', + 'justify-content', + 'justify-items', + 'justify-self', + 'kerning', + 'left', + 'letter-spacing', + 'lighting-color', + 'line-break', + 'line-height', + 'line-height-step', + 'list-style', + 'list-style-image', + 'list-style-position', + 'list-style-type', + 'margin', + 'margin-block', + 'margin-block-end', + 'margin-block-start', + 'margin-bottom', + 'margin-inline', + 'margin-inline-end', + 'margin-inline-start', + 'margin-left', + 'margin-right', + 'margin-top', + 'margin-trim', + 'marker', + 'marker-end', + 'marker-mid', + 'marker-start', + 'marks', + 'mask', + 'mask-border', + 'mask-border-mode', + 'mask-border-outset', + 'mask-border-repeat', + 'mask-border-slice', + 'mask-border-source', + 'mask-border-width', + 'mask-clip', + 'mask-composite', + 'mask-image', + 'mask-mode', + 'mask-origin', + 'mask-position', + 'mask-repeat', + 'mask-size', + 'mask-type', + 'masonry-auto-flow', + 'math-depth', + 'math-shift', + 'math-style', + 'max-block-size', + 'max-height', + 'max-inline-size', + 'max-width', + 'min-block-size', + 'min-height', + 'min-inline-size', + 'min-width', + 'mix-blend-mode', + 'nav-down', + 'nav-index', + 'nav-left', + 'nav-right', + 'nav-up', + 'none', + 'normal', + 'object-fit', + 'object-position', + 'offset', + 'offset-anchor', + 'offset-distance', + 'offset-path', + 'offset-position', + 'offset-rotate', + 'opacity', + 'order', + 'orphans', + 'outline', + 'outline-color', + 'outline-offset', + 'outline-style', + 'outline-width', + 'overflow', + 'overflow-anchor', + 'overflow-block', + 'overflow-clip-margin', + 'overflow-inline', + 'overflow-wrap', + 'overflow-x', + 'overflow-y', + 'overlay', + 'overscroll-behavior', + 'overscroll-behavior-block', + 'overscroll-behavior-inline', + 'overscroll-behavior-x', + 'overscroll-behavior-y', + 'padding', + 'padding-block', + 'padding-block-end', + 'padding-block-start', + 'padding-bottom', + 'padding-inline', + 'padding-inline-end', + 'padding-inline-start', + 'padding-left', + 'padding-right', + 'padding-top', + 'page', + 'page-break-after', + 'page-break-before', + 'page-break-inside', + 'paint-order', + 'pause', + 'pause-after', + 'pause-before', + 'perspective', + 'perspective-origin', + 'place-content', + 'place-items', + 'place-self', + 'pointer-events', + 'position', + 'position-anchor', + 'position-visibility', + 'print-color-adjust', + 'quotes', + 'r', + 'resize', + 'rest', + 'rest-after', + 'rest-before', + 'right', + 'rotate', + 'row-gap', + 'ruby-align', + 'ruby-position', + 'scale', + 'scroll-behavior', + 'scroll-margin', + 'scroll-margin-block', + 'scroll-margin-block-end', + 'scroll-margin-block-start', + 'scroll-margin-bottom', + 'scroll-margin-inline', + 'scroll-margin-inline-end', + 'scroll-margin-inline-start', + 'scroll-margin-left', + 'scroll-margin-right', + 'scroll-margin-top', + 'scroll-padding', + 'scroll-padding-block', + 'scroll-padding-block-end', + 'scroll-padding-block-start', + 'scroll-padding-bottom', + 'scroll-padding-inline', + 'scroll-padding-inline-end', + 'scroll-padding-inline-start', + 'scroll-padding-left', + 'scroll-padding-right', + 'scroll-padding-top', + 'scroll-snap-align', + 'scroll-snap-stop', + 'scroll-snap-type', + 'scroll-timeline', + 'scroll-timeline-axis', + 'scroll-timeline-name', + 'scrollbar-color', + 'scrollbar-gutter', + 'scrollbar-width', + 'shape-image-threshold', + 'shape-margin', + 'shape-outside', + 'shape-rendering', + 'speak', + 'speak-as', + 'src', // @font-face + 'stop-color', + 'stop-opacity', + 'stroke', + 'stroke-dasharray', + 'stroke-dashoffset', + 'stroke-linecap', + 'stroke-linejoin', + 'stroke-miterlimit', + 'stroke-opacity', + 'stroke-width', + 'tab-size', + 'table-layout', + 'text-align', + 'text-align-all', + 'text-align-last', + 'text-anchor', + 'text-combine-upright', + 'text-decoration', + 'text-decoration-color', + 'text-decoration-line', + 'text-decoration-skip', + 'text-decoration-skip-ink', + 'text-decoration-style', + 'text-decoration-thickness', + 'text-emphasis', + 'text-emphasis-color', + 'text-emphasis-position', + 'text-emphasis-style', + 'text-indent', + 'text-justify', + 'text-orientation', + 'text-overflow', + 'text-rendering', + 'text-shadow', + 'text-size-adjust', + 'text-transform', + 'text-underline-offset', + 'text-underline-position', + 'text-wrap', + 'text-wrap-mode', + 'text-wrap-style', + 'timeline-scope', + 'top', + 'touch-action', + 'transform', + 'transform-box', + 'transform-origin', + 'transform-style', + 'transition', + 'transition-behavior', + 'transition-delay', + 'transition-duration', + 'transition-property', + 'transition-timing-function', + 'translate', + 'unicode-bidi', + 'user-modify', + 'user-select', + 'vector-effect', + 'vertical-align', + 'view-timeline', + 'view-timeline-axis', + 'view-timeline-inset', + 'view-timeline-name', + 'view-transition-name', + 'visibility', + 'voice-balance', + 'voice-duration', + 'voice-family', + 'voice-pitch', + 'voice-range', + 'voice-rate', + 'voice-stress', + 'voice-volume', + 'white-space', + 'white-space-collapse', + 'widows', + 'width', + 'will-change', + 'word-break', + 'word-spacing', + 'word-wrap', + 'writing-mode', + 'x', + 'y', + 'z-index', + 'zoom' +].sort().reverse(); + +/* +Language: SCSS +Description: Scss is an extension of the syntax of CSS. +Author: Kurt Emch +Website: https://sass-lang.com +Category: common, css, web +*/ + + +/** @type LanguageFn */ +function scss(hljs) { + const modes = MODES(hljs); + const PSEUDO_ELEMENTS$1 = PSEUDO_ELEMENTS; + const PSEUDO_CLASSES$1 = PSEUDO_CLASSES; + + const AT_IDENTIFIER = '@[a-z-]+'; // @font-face + const AT_MODIFIERS = "and or not only"; + const IDENT_RE = '[a-zA-Z-][a-zA-Z0-9_-]*'; + const VARIABLE = { + className: 'variable', + begin: '(\\$' + IDENT_RE + ')\\b', + relevance: 0 + }; + + return { + name: 'SCSS', + case_insensitive: true, + illegal: '[=/|\']', + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + // to recognize keyframe 40% etc which are outside the scope of our + // attribute value mode + modes.CSS_NUMBER_MODE, + { + className: 'selector-id', + begin: '#[A-Za-z0-9_-]+', + relevance: 0 + }, + { + className: 'selector-class', + begin: '\\.[A-Za-z0-9_-]+', + relevance: 0 + }, + modes.ATTRIBUTE_SELECTOR_MODE, + { + className: 'selector-tag', + begin: '\\b(' + TAGS.join('|') + ')\\b', + // was there, before, but why? + relevance: 0 + }, + { + className: 'selector-pseudo', + begin: ':(' + PSEUDO_CLASSES$1.join('|') + ')' + }, + { + className: 'selector-pseudo', + begin: ':(:)?(' + PSEUDO_ELEMENTS$1.join('|') + ')' + }, + VARIABLE, + { // pseudo-selector params + begin: /\(/, + end: /\)/, + contains: [ modes.CSS_NUMBER_MODE ] + }, + modes.CSS_VARIABLE, + { + className: 'attribute', + begin: '\\b(' + ATTRIBUTES.join('|') + ')\\b' + }, + { begin: '\\b(whitespace|wait|w-resize|visible|vertical-text|vertical-ideographic|uppercase|upper-roman|upper-alpha|underline|transparent|top|thin|thick|text|text-top|text-bottom|tb-rl|table-header-group|table-footer-group|sw-resize|super|strict|static|square|solid|small-caps|separate|se-resize|scroll|s-resize|rtl|row-resize|ridge|right|repeat|repeat-y|repeat-x|relative|progress|pointer|overline|outside|outset|oblique|nowrap|not-allowed|normal|none|nw-resize|no-repeat|no-drop|newspaper|ne-resize|n-resize|move|middle|medium|ltr|lr-tb|lowercase|lower-roman|lower-alpha|loose|list-item|line|line-through|line-edge|lighter|left|keep-all|justify|italic|inter-word|inter-ideograph|inside|inset|inline|inline-block|inherit|inactive|ideograph-space|ideograph-parenthesis|ideograph-numeric|ideograph-alpha|horizontal|hidden|help|hand|groove|fixed|ellipsis|e-resize|double|dotted|distribute|distribute-space|distribute-letter|distribute-all-lines|disc|disabled|default|decimal|dashed|crosshair|collapse|col-resize|circle|char|center|capitalize|break-word|break-all|bottom|both|bolder|bold|block|bidi-override|below|baseline|auto|always|all-scroll|absolute|table|table-cell)\\b' }, + { + begin: /:/, + end: /[;}{]/, + relevance: 0, + contains: [ + modes.BLOCK_COMMENT, + VARIABLE, + modes.HEXCOLOR, + modes.CSS_NUMBER_MODE, + hljs.QUOTE_STRING_MODE, + hljs.APOS_STRING_MODE, + modes.IMPORTANT, + modes.FUNCTION_DISPATCH + ] + }, + // matching these here allows us to treat them more like regular CSS + // rules so everything between the {} gets regular rule highlighting, + // which is what we want for page and font-face + { + begin: '@(page|font-face)', + keywords: { + $pattern: AT_IDENTIFIER, + keyword: '@page @font-face' + } + }, + { + begin: '@', + end: '[{;]', + returnBegin: true, + keywords: { + $pattern: /[a-z-]+/, + keyword: AT_MODIFIERS, + attribute: MEDIA_FEATURES.join(" ") + }, + contains: [ + { + begin: AT_IDENTIFIER, + className: "keyword" + }, + { + begin: /[a-z-]+(?=:)/, + className: "attribute" + }, + VARIABLE, + hljs.QUOTE_STRING_MODE, + hljs.APOS_STRING_MODE, + modes.HEXCOLOR, + modes.CSS_NUMBER_MODE + ] + }, + modes.FUNCTION_DISPATCH + ] + }; +} + +export { scss as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/scss.js.js b/frontend/node_modules/highlight.js/es/languages/scss.js.js new file mode 100644 index 0000000..b01bc25 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/scss.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/scss" instead of "highlight.js/lib/languages/scss.js"' + ); + } + } + emitWarning(); + import lang from './scss.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/shell.js b/frontend/node_modules/highlight.js/es/languages/shell.js new file mode 100644 index 0000000..de4831c --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/shell.js @@ -0,0 +1,33 @@ +/* +Language: Shell Session +Requires: bash.js +Author: TSUYUSATO Kitsune +Category: common +Audit: 2020 +*/ + +/** @type LanguageFn */ +function shell(hljs) { + return { + name: 'Shell Session', + aliases: [ + 'console', + 'shellsession' + ], + contains: [ + { + className: 'meta.prompt', + // We cannot add \s (spaces) in the regular expression otherwise it will be too broad and produce unexpected result. + // For instance, in the following example, it would match "echo /path/to/home >" as a prompt: + // echo /path/to/home > t.exe + begin: /^\s{0,3}[/~\w\d[\]()@-]*[>%$#][ ]?/, + starts: { + end: /[^\\](?=\s*$)/, + subLanguage: 'bash' + } + } + ] + }; +} + +export { shell as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/shell.js.js b/frontend/node_modules/highlight.js/es/languages/shell.js.js new file mode 100644 index 0000000..40bc7e4 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/shell.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/shell" instead of "highlight.js/lib/languages/shell.js"' + ); + } + } + emitWarning(); + import lang from './shell.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/smali.js b/frontend/node_modules/highlight.js/es/languages/smali.js new file mode 100644 index 0000000..db53572 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/smali.js @@ -0,0 +1,126 @@ +/* +Language: Smali +Author: Dennis Titze +Description: Basic Smali highlighting +Website: https://github.com/JesusFreke/smali +Category: assembler +*/ + +function smali(hljs) { + const smali_instr_low_prio = [ + 'add', + 'and', + 'cmp', + 'cmpg', + 'cmpl', + 'const', + 'div', + 'double', + 'float', + 'goto', + 'if', + 'int', + 'long', + 'move', + 'mul', + 'neg', + 'new', + 'nop', + 'not', + 'or', + 'rem', + 'return', + 'shl', + 'shr', + 'sput', + 'sub', + 'throw', + 'ushr', + 'xor' + ]; + const smali_instr_high_prio = [ + 'aget', + 'aput', + 'array', + 'check', + 'execute', + 'fill', + 'filled', + 'goto/16', + 'goto/32', + 'iget', + 'instance', + 'invoke', + 'iput', + 'monitor', + 'packed', + 'sget', + 'sparse' + ]; + const smali_keywords = [ + 'transient', + 'constructor', + 'abstract', + 'final', + 'synthetic', + 'public', + 'private', + 'protected', + 'static', + 'bridge', + 'system' + ]; + return { + name: 'Smali', + contains: [ + { + className: 'string', + begin: '"', + end: '"', + relevance: 0 + }, + hljs.COMMENT( + '#', + '$', + { relevance: 0 } + ), + { + className: 'keyword', + variants: [ + { begin: '\\s*\\.end\\s[a-zA-Z0-9]*' }, + { + begin: '^[ ]*\\.[a-zA-Z]*', + relevance: 0 + }, + { + begin: '\\s:[a-zA-Z_0-9]*', + relevance: 0 + }, + { begin: '\\s(' + smali_keywords.join('|') + ')' } + ] + }, + { + className: 'built_in', + variants: [ + { begin: '\\s(' + smali_instr_low_prio.join('|') + ')\\s' }, + { + begin: '\\s(' + smali_instr_low_prio.join('|') + ')((-|/)[a-zA-Z0-9]+)+\\s', + relevance: 10 + }, + { + begin: '\\s(' + smali_instr_high_prio.join('|') + ')((-|/)[a-zA-Z0-9]+)*\\s', + relevance: 10 + } + ] + }, + { + className: 'class', + begin: 'L[^\(;:\n]*;', + relevance: 0 + }, + { begin: '[vp][0-9]+' } + ] + }; +} + +export { smali as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/smali.js.js b/frontend/node_modules/highlight.js/es/languages/smali.js.js new file mode 100644 index 0000000..79784dd --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/smali.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/smali" instead of "highlight.js/lib/languages/smali.js"' + ); + } + } + emitWarning(); + import lang from './smali.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/smalltalk.js b/frontend/node_modules/highlight.js/es/languages/smalltalk.js new file mode 100644 index 0000000..0ff88c9 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/smalltalk.js @@ -0,0 +1,69 @@ +/* +Language: Smalltalk +Description: Smalltalk is an object-oriented, dynamically typed reflective programming language. +Author: Vladimir Gubarkov +Website: https://en.wikipedia.org/wiki/Smalltalk +Category: system +*/ + +function smalltalk(hljs) { + const VAR_IDENT_RE = '[a-z][a-zA-Z0-9_]*'; + const CHAR = { + className: 'string', + begin: '\\$.{1}' + }; + const SYMBOL = { + className: 'symbol', + begin: '#' + hljs.UNDERSCORE_IDENT_RE + }; + return { + name: 'Smalltalk', + aliases: [ 'st' ], + keywords: [ + "self", + "super", + "nil", + "true", + "false", + "thisContext" + ], + contains: [ + hljs.COMMENT('"', '"'), + hljs.APOS_STRING_MODE, + { + className: 'type', + begin: '\\b[A-Z][A-Za-z0-9_]*', + relevance: 0 + }, + { + begin: VAR_IDENT_RE + ':', + relevance: 0 + }, + hljs.C_NUMBER_MODE, + SYMBOL, + CHAR, + { + // This looks more complicated than needed to avoid combinatorial + // explosion under V8. It effectively means `| var1 var2 ... |` with + // whitespace adjacent to `|` being optional. + begin: '\\|[ ]*' + VAR_IDENT_RE + '([ ]+' + VAR_IDENT_RE + ')*[ ]*\\|', + returnBegin: true, + end: /\|/, + illegal: /\S/, + contains: [ { begin: '(\\|[ ]*)?' + VAR_IDENT_RE } ] + }, + { + begin: '#\\(', + end: '\\)', + contains: [ + hljs.APOS_STRING_MODE, + CHAR, + hljs.C_NUMBER_MODE, + SYMBOL + ] + } + ] + }; +} + +export { smalltalk as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/smalltalk.js.js b/frontend/node_modules/highlight.js/es/languages/smalltalk.js.js new file mode 100644 index 0000000..bed76b7 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/smalltalk.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/smalltalk" instead of "highlight.js/lib/languages/smalltalk.js"' + ); + } + } + emitWarning(); + import lang from './smalltalk.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/sml.js b/frontend/node_modules/highlight.js/es/languages/sml.js new file mode 100644 index 0000000..e526d0d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/sml.js @@ -0,0 +1,75 @@ +/* +Language: SML (Standard ML) +Author: Edwin Dalorzo +Description: SML language definition. +Website: https://www.smlnj.org +Origin: ocaml.js +Category: functional +*/ +function sml(hljs) { + return { + name: 'SML (Standard ML)', + aliases: [ 'ml' ], + keywords: { + $pattern: '[a-z_]\\w*!?', + keyword: + /* according to Definition of Standard ML 97 */ + 'abstype and andalso as case datatype do else end eqtype ' + + 'exception fn fun functor handle if in include infix infixr ' + + 'let local nonfix of op open orelse raise rec sharing sig ' + + 'signature struct structure then type val with withtype where while', + built_in: + /* built-in types according to basis library */ + 'array bool char exn int list option order real ref string substring vector unit word', + literal: + 'true false NONE SOME LESS EQUAL GREATER nil' + }, + illegal: /\/\/|>>/, + contains: [ + { + className: 'literal', + begin: /\[(\|\|)?\]|\(\)/, + relevance: 0 + }, + hljs.COMMENT( + '\\(\\*', + '\\*\\)', + { contains: [ 'self' ] } + ), + { /* type variable */ + className: 'symbol', + begin: '\'[A-Za-z_](?!\')[\\w\']*' + /* the grammar is ambiguous on how 'a'b should be interpreted but not the compiler */ + }, + { /* polymorphic variant */ + className: 'type', + begin: '`[A-Z][\\w\']*' + }, + { /* module or constructor */ + className: 'type', + begin: '\\b[A-Z][\\w\']*', + relevance: 0 + }, + { /* don't color identifiers, but safely catch all identifiers with ' */ + begin: '[a-z_]\\w*\'[\\w\']*' }, + hljs.inherit(hljs.APOS_STRING_MODE, { + className: 'string', + relevance: 0 + }), + hljs.inherit(hljs.QUOTE_STRING_MODE, { illegal: null }), + { + className: 'number', + begin: + '\\b(0[xX][a-fA-F0-9_]+[Lln]?|' + + '0[oO][0-7_]+[Lln]?|' + + '0[bB][01_]+[Lln]?|' + + '[0-9][0-9_]*([Lln]|(\\.[0-9_]*)?([eE][-+]?[0-9_]+)?)?)', + relevance: 0 + }, + { begin: /[-=]>/ // relevance booster + } + ] + }; +} + +export { sml as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/sml.js.js b/frontend/node_modules/highlight.js/es/languages/sml.js.js new file mode 100644 index 0000000..2dbf3c9 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/sml.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/sml" instead of "highlight.js/lib/languages/sml.js"' + ); + } + } + emitWarning(); + import lang from './sml.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/sqf.js b/frontend/node_modules/highlight.js/es/languages/sqf.js new file mode 100644 index 0000000..b2d6aab --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/sqf.js @@ -0,0 +1,2662 @@ +/* +Language: SQF +Author: Søren Enevoldsen +Contributors: Marvin Saignat , Dedmen Miller , Leopard20 +Description: Scripting language for the Arma game series +Website: https://community.bistudio.com/wiki/SQF_syntax +Category: scripting +Last update: 07.01.2023, Arma 3 v2.11 +*/ + +/* +//////////////////////////////////////////////////////////////////////////////////////////// + * Author: Leopard20 + + * Description: + This script can be used to dump all commands to the clipboard. + Make sure you're using the Diag EXE to dump all of the commands. + + * How to use: + Simply replace the _KEYWORDS and _LITERAL arrays with the one from this sqf.js file. + Execute the script from the debug console. + All commands will be copied to the clipboard. +//////////////////////////////////////////////////////////////////////////////////////////// +_KEYWORDS = ['if']; //Array of all KEYWORDS +_LITERALS = ['west']; //Array of all LITERALS +_allCommands = createHashMap; +{ + _type = _x select [0,1]; + if (_type != "t") then { + _command_lowercase = ((_x select [2]) splitString " ")#(((["n", "u", "b"] find _type) - 1) max 0); + _command_uppercase = supportInfo ("i:" + _command_lowercase) # 0 # 2; + _allCommands set [_command_lowercase, _command_uppercase]; + }; +} forEach supportInfo ""; +_allCommands = _allCommands toArray false; +_allCommands sort true; //sort by lowercase +_allCommands = ((_allCommands apply {_x#1}) -_KEYWORDS)-_LITERALS; //remove KEYWORDS and LITERALS +copyToClipboard (str (_allCommands select {_x regexMatch "\w+"}) regexReplace ["""", "'"] regexReplace [",", ",\n"]); +*/ + +function sqf(hljs) { + // In SQF, a local variable starts with _ + const VARIABLE = { + className: 'variable', + begin: /\b_+[a-zA-Z]\w*/ + }; + + // In SQF, a function should fit myTag_fnc_myFunction pattern + // https://community.bistudio.com/wiki/Functions_Library_(Arma_3)#Adding_a_Function + const FUNCTION = { + className: 'title', + begin: /[a-zA-Z][a-zA-Z_0-9]*_fnc_[a-zA-Z_0-9]+/ + }; + + // In SQF strings, quotes matching the start are escaped by adding a consecutive. + // Example of single escaped quotes: " "" " and ' '' '. + const STRINGS = { + className: 'string', + variants: [ + { + begin: '"', + end: '"', + contains: [ + { + begin: '""', + relevance: 0 + } + ] + }, + { + begin: '\'', + end: '\'', + contains: [ + { + begin: '\'\'', + relevance: 0 + } + ] + } + ] + }; + + const KEYWORDS = [ + 'break', + 'breakWith', + 'breakOut', + 'breakTo', + 'case', + 'catch', + 'continue', + 'continueWith', + 'default', + 'do', + 'else', + 'exit', + 'exitWith', + 'for', + 'forEach', + 'from', + 'if', + 'local', + 'private', + 'switch', + 'step', + 'then', + 'throw', + 'to', + 'try', + 'waitUntil', + 'while', + 'with' + ]; + + const LITERAL = [ + 'blufor', + 'civilian', + 'configNull', + 'controlNull', + 'displayNull', + 'diaryRecordNull', + 'east', + 'endl', + 'false', + 'grpNull', + 'independent', + 'lineBreak', + 'locationNull', + 'nil', + 'objNull', + 'opfor', + 'pi', + 'resistance', + 'scriptNull', + 'sideAmbientLife', + 'sideEmpty', + 'sideEnemy', + 'sideFriendly', + 'sideLogic', + 'sideUnknown', + 'taskNull', + 'teamMemberNull', + 'true', + 'west' + ]; + + const BUILT_IN = [ + 'abs', + 'accTime', + 'acos', + 'action', + 'actionIDs', + 'actionKeys', + 'actionKeysEx', + 'actionKeysImages', + 'actionKeysNames', + 'actionKeysNamesArray', + 'actionName', + 'actionParams', + 'activateAddons', + 'activatedAddons', + 'activateKey', + 'activeTitleEffectParams', + 'add3DENConnection', + 'add3DENEventHandler', + 'add3DENLayer', + 'addAction', + 'addBackpack', + 'addBackpackCargo', + 'addBackpackCargoGlobal', + 'addBackpackGlobal', + 'addBinocularItem', + 'addCamShake', + 'addCuratorAddons', + 'addCuratorCameraArea', + 'addCuratorEditableObjects', + 'addCuratorEditingArea', + 'addCuratorPoints', + 'addEditorObject', + 'addEventHandler', + 'addForce', + 'addForceGeneratorRTD', + 'addGoggles', + 'addGroupIcon', + 'addHandgunItem', + 'addHeadgear', + 'addItem', + 'addItemCargo', + 'addItemCargoGlobal', + 'addItemPool', + 'addItemToBackpack', + 'addItemToUniform', + 'addItemToVest', + 'addLiveStats', + 'addMagazine', + 'addMagazineAmmoCargo', + 'addMagazineCargo', + 'addMagazineCargoGlobal', + 'addMagazineGlobal', + 'addMagazinePool', + 'addMagazines', + 'addMagazineTurret', + 'addMenu', + 'addMenuItem', + 'addMissionEventHandler', + 'addMPEventHandler', + 'addMusicEventHandler', + 'addonFiles', + 'addOwnedMine', + 'addPlayerScores', + 'addPrimaryWeaponItem', + 'addPublicVariableEventHandler', + 'addRating', + 'addResources', + 'addScore', + 'addScoreSide', + 'addSecondaryWeaponItem', + 'addSwitchableUnit', + 'addTeamMember', + 'addToRemainsCollector', + 'addTorque', + 'addUniform', + 'addUserActionEventHandler', + 'addVehicle', + 'addVest', + 'addWaypoint', + 'addWeapon', + 'addWeaponCargo', + 'addWeaponCargoGlobal', + 'addWeaponGlobal', + 'addWeaponItem', + 'addWeaponPool', + 'addWeaponTurret', + 'addWeaponWithAttachmentsCargo', + 'addWeaponWithAttachmentsCargoGlobal', + 'admin', + 'agent', + 'agents', + 'AGLToASL', + 'aimedAtTarget', + 'aimPos', + 'airDensityCurveRTD', + 'airDensityRTD', + 'airplaneThrottle', + 'airportSide', + 'AISFinishHeal', + 'alive', + 'all3DENEntities', + 'allActiveTitleEffects', + 'allAddonsInfo', + 'allAirports', + 'allControls', + 'allCurators', + 'allCutLayers', + 'allDead', + 'allDeadMen', + 'allDiaryRecords', + 'allDiarySubjects', + 'allDisplays', + 'allEnv3DSoundSources', + 'allGroups', + 'allLODs', + 'allMapMarkers', + 'allMines', + 'allMissionObjects', + 'allObjects', + 'allow3DMode', + 'allowCrewInImmobile', + 'allowCuratorLogicIgnoreAreas', + 'allowDamage', + 'allowDammage', + 'allowedService', + 'allowFileOperations', + 'allowFleeing', + 'allowGetIn', + 'allowService', + 'allowSprint', + 'allPlayers', + 'allSimpleObjects', + 'allSites', + 'allTurrets', + 'allUnits', + 'allUnitsUAV', + 'allUsers', + 'allVariables', + 'ambientTemperature', + 'ammo', + 'ammoOnPylon', + 'and', + 'animate', + 'animateBay', + 'animateDoor', + 'animatePylon', + 'animateSource', + 'animationNames', + 'animationPhase', + 'animationSourcePhase', + 'animationState', + 'apertureParams', + 'append', + 'apply', + 'armoryPoints', + 'arrayIntersect', + 'asin', + 'ASLToAGL', + 'ASLToATL', + 'assert', + 'assignAsCargo', + 'assignAsCargoIndex', + 'assignAsCommander', + 'assignAsDriver', + 'assignAsGunner', + 'assignAsTurret', + 'assignCurator', + 'assignedCargo', + 'assignedCommander', + 'assignedDriver', + 'assignedGroup', + 'assignedGunner', + 'assignedItems', + 'assignedTarget', + 'assignedTeam', + 'assignedVehicle', + 'assignedVehicleRole', + 'assignedVehicles', + 'assignItem', + 'assignTeam', + 'assignToAirport', + 'atan', + 'atan2', + 'atg', + 'ATLToASL', + 'attachedObject', + 'attachedObjects', + 'attachedTo', + 'attachObject', + 'attachTo', + 'attackEnabled', + 'awake', + 'backpack', + 'backpackCargo', + 'backpackContainer', + 'backpackItems', + 'backpackMagazines', + 'backpackSpaceFor', + 'behaviour', + 'benchmark', + 'bezierInterpolation', + 'binocular', + 'binocularItems', + 'binocularMagazine', + 'boundingBox', + 'boundingBoxReal', + 'boundingCenter', + 'brakesDisabled', + 'briefingName', + 'buildingExit', + 'buildingPos', + 'buldozer_EnableRoadDiag', + 'buldozer_IsEnabledRoadDiag', + 'buldozer_LoadNewRoads', + 'buldozer_reloadOperMap', + 'buttonAction', + 'buttonSetAction', + 'cadetMode', + 'calculatePath', + 'calculatePlayerVisibilityByFriendly', + 'call', + 'callExtension', + 'camCommand', + 'camCommit', + 'camCommitPrepared', + 'camCommitted', + 'camConstuctionSetParams', + 'camCreate', + 'camDestroy', + 'cameraEffect', + 'cameraEffectEnableHUD', + 'cameraInterest', + 'cameraOn', + 'cameraView', + 'campaignConfigFile', + 'camPreload', + 'camPreloaded', + 'camPrepareBank', + 'camPrepareDir', + 'camPrepareDive', + 'camPrepareFocus', + 'camPrepareFov', + 'camPrepareFovRange', + 'camPreparePos', + 'camPrepareRelPos', + 'camPrepareTarget', + 'camSetBank', + 'camSetDir', + 'camSetDive', + 'camSetFocus', + 'camSetFov', + 'camSetFovRange', + 'camSetPos', + 'camSetRelPos', + 'camSetTarget', + 'camTarget', + 'camUseNVG', + 'canAdd', + 'canAddItemToBackpack', + 'canAddItemToUniform', + 'canAddItemToVest', + 'cancelSimpleTaskDestination', + 'canDeployWeapon', + 'canFire', + 'canMove', + 'canSlingLoad', + 'canStand', + 'canSuspend', + 'canTriggerDynamicSimulation', + 'canUnloadInCombat', + 'canVehicleCargo', + 'captive', + 'captiveNum', + 'cbChecked', + 'cbSetChecked', + 'ceil', + 'channelEnabled', + 'cheatsEnabled', + 'checkAIFeature', + 'checkVisibility', + 'className', + 'clear3DENAttribute', + 'clear3DENInventory', + 'clearAllItemsFromBackpack', + 'clearBackpackCargo', + 'clearBackpackCargoGlobal', + 'clearForcesRTD', + 'clearGroupIcons', + 'clearItemCargo', + 'clearItemCargoGlobal', + 'clearItemPool', + 'clearMagazineCargo', + 'clearMagazineCargoGlobal', + 'clearMagazinePool', + 'clearOverlay', + 'clearRadio', + 'clearWeaponCargo', + 'clearWeaponCargoGlobal', + 'clearWeaponPool', + 'clientOwner', + 'closeDialog', + 'closeDisplay', + 'closeOverlay', + 'collapseObjectTree', + 'collect3DENHistory', + 'collectiveRTD', + 'collisionDisabledWith', + 'combatBehaviour', + 'combatMode', + 'commandArtilleryFire', + 'commandChat', + 'commander', + 'commandFire', + 'commandFollow', + 'commandFSM', + 'commandGetOut', + 'commandingMenu', + 'commandMove', + 'commandRadio', + 'commandStop', + 'commandSuppressiveFire', + 'commandTarget', + 'commandWatch', + 'comment', + 'commitOverlay', + 'compatibleItems', + 'compatibleMagazines', + 'compile', + 'compileFinal', + 'compileScript', + 'completedFSM', + 'composeText', + 'configClasses', + 'configFile', + 'configHierarchy', + 'configName', + 'configOf', + 'configProperties', + 'configSourceAddonList', + 'configSourceMod', + 'configSourceModList', + 'confirmSensorTarget', + 'connectTerminalToUAV', + 'connectToServer', + 'controlsGroupCtrl', + 'conversationDisabled', + 'copyFromClipboard', + 'copyToClipboard', + 'copyWaypoints', + 'cos', + 'count', + 'countEnemy', + 'countFriendly', + 'countSide', + 'countType', + 'countUnknown', + 'create3DENComposition', + 'create3DENEntity', + 'createAgent', + 'createCenter', + 'createDialog', + 'createDiaryLink', + 'createDiaryRecord', + 'createDiarySubject', + 'createDisplay', + 'createGearDialog', + 'createGroup', + 'createGuardedPoint', + 'createHashMap', + 'createHashMapFromArray', + 'createLocation', + 'createMarker', + 'createMarkerLocal', + 'createMenu', + 'createMine', + 'createMissionDisplay', + 'createMPCampaignDisplay', + 'createSimpleObject', + 'createSimpleTask', + 'createSite', + 'createSoundSource', + 'createTask', + 'createTeam', + 'createTrigger', + 'createUnit', + 'createVehicle', + 'createVehicleCrew', + 'createVehicleLocal', + 'crew', + 'ctAddHeader', + 'ctAddRow', + 'ctClear', + 'ctCurSel', + 'ctData', + 'ctFindHeaderRows', + 'ctFindRowHeader', + 'ctHeaderControls', + 'ctHeaderCount', + 'ctRemoveHeaders', + 'ctRemoveRows', + 'ctrlActivate', + 'ctrlAddEventHandler', + 'ctrlAngle', + 'ctrlAnimateModel', + 'ctrlAnimationPhaseModel', + 'ctrlAt', + 'ctrlAutoScrollDelay', + 'ctrlAutoScrollRewind', + 'ctrlAutoScrollSpeed', + 'ctrlBackgroundColor', + 'ctrlChecked', + 'ctrlClassName', + 'ctrlCommit', + 'ctrlCommitted', + 'ctrlCreate', + 'ctrlDelete', + 'ctrlEnable', + 'ctrlEnabled', + 'ctrlFade', + 'ctrlFontHeight', + 'ctrlForegroundColor', + 'ctrlHTMLLoaded', + 'ctrlIDC', + 'ctrlIDD', + 'ctrlMapAnimAdd', + 'ctrlMapAnimClear', + 'ctrlMapAnimCommit', + 'ctrlMapAnimDone', + 'ctrlMapCursor', + 'ctrlMapMouseOver', + 'ctrlMapPosition', + 'ctrlMapScale', + 'ctrlMapScreenToWorld', + 'ctrlMapSetPosition', + 'ctrlMapWorldToScreen', + 'ctrlModel', + 'ctrlModelDirAndUp', + 'ctrlModelScale', + 'ctrlMousePosition', + 'ctrlParent', + 'ctrlParentControlsGroup', + 'ctrlPosition', + 'ctrlRemoveAllEventHandlers', + 'ctrlRemoveEventHandler', + 'ctrlScale', + 'ctrlScrollValues', + 'ctrlSetActiveColor', + 'ctrlSetAngle', + 'ctrlSetAutoScrollDelay', + 'ctrlSetAutoScrollRewind', + 'ctrlSetAutoScrollSpeed', + 'ctrlSetBackgroundColor', + 'ctrlSetChecked', + 'ctrlSetDisabledColor', + 'ctrlSetEventHandler', + 'ctrlSetFade', + 'ctrlSetFocus', + 'ctrlSetFont', + 'ctrlSetFontH1', + 'ctrlSetFontH1B', + 'ctrlSetFontH2', + 'ctrlSetFontH2B', + 'ctrlSetFontH3', + 'ctrlSetFontH3B', + 'ctrlSetFontH4', + 'ctrlSetFontH4B', + 'ctrlSetFontH5', + 'ctrlSetFontH5B', + 'ctrlSetFontH6', + 'ctrlSetFontH6B', + 'ctrlSetFontHeight', + 'ctrlSetFontHeightH1', + 'ctrlSetFontHeightH2', + 'ctrlSetFontHeightH3', + 'ctrlSetFontHeightH4', + 'ctrlSetFontHeightH5', + 'ctrlSetFontHeightH6', + 'ctrlSetFontHeightSecondary', + 'ctrlSetFontP', + 'ctrlSetFontPB', + 'ctrlSetFontSecondary', + 'ctrlSetForegroundColor', + 'ctrlSetModel', + 'ctrlSetModelDirAndUp', + 'ctrlSetModelScale', + 'ctrlSetMousePosition', + 'ctrlSetPixelPrecision', + 'ctrlSetPosition', + 'ctrlSetPositionH', + 'ctrlSetPositionW', + 'ctrlSetPositionX', + 'ctrlSetPositionY', + 'ctrlSetScale', + 'ctrlSetScrollValues', + 'ctrlSetShadow', + 'ctrlSetStructuredText', + 'ctrlSetText', + 'ctrlSetTextColor', + 'ctrlSetTextColorSecondary', + 'ctrlSetTextSecondary', + 'ctrlSetTextSelection', + 'ctrlSetTooltip', + 'ctrlSetTooltipColorBox', + 'ctrlSetTooltipColorShade', + 'ctrlSetTooltipColorText', + 'ctrlSetTooltipMaxWidth', + 'ctrlSetURL', + 'ctrlSetURLOverlayMode', + 'ctrlShadow', + 'ctrlShow', + 'ctrlShown', + 'ctrlStyle', + 'ctrlText', + 'ctrlTextColor', + 'ctrlTextHeight', + 'ctrlTextSecondary', + 'ctrlTextSelection', + 'ctrlTextWidth', + 'ctrlTooltip', + 'ctrlType', + 'ctrlURL', + 'ctrlURLOverlayMode', + 'ctrlVisible', + 'ctRowControls', + 'ctRowCount', + 'ctSetCurSel', + 'ctSetData', + 'ctSetHeaderTemplate', + 'ctSetRowTemplate', + 'ctSetValue', + 'ctValue', + 'curatorAddons', + 'curatorCamera', + 'curatorCameraArea', + 'curatorCameraAreaCeiling', + 'curatorCoef', + 'curatorEditableObjects', + 'curatorEditingArea', + 'curatorEditingAreaType', + 'curatorMouseOver', + 'curatorPoints', + 'curatorRegisteredObjects', + 'curatorSelected', + 'curatorWaypointCost', + 'current3DENOperation', + 'currentChannel', + 'currentCommand', + 'currentMagazine', + 'currentMagazineDetail', + 'currentMagazineDetailTurret', + 'currentMagazineTurret', + 'currentMuzzle', + 'currentNamespace', + 'currentPilot', + 'currentTask', + 'currentTasks', + 'currentThrowable', + 'currentVisionMode', + 'currentWaypoint', + 'currentWeapon', + 'currentWeaponMode', + 'currentWeaponTurret', + 'currentZeroing', + 'cursorObject', + 'cursorTarget', + 'customChat', + 'customRadio', + 'customWaypointPosition', + 'cutFadeOut', + 'cutObj', + 'cutRsc', + 'cutText', + 'damage', + 'date', + 'dateToNumber', + 'dayTime', + 'deActivateKey', + 'debriefingText', + 'debugFSM', + 'debugLog', + 'decayGraphValues', + 'deg', + 'delete3DENEntities', + 'deleteAt', + 'deleteCenter', + 'deleteCollection', + 'deleteEditorObject', + 'deleteGroup', + 'deleteGroupWhenEmpty', + 'deleteIdentity', + 'deleteLocation', + 'deleteMarker', + 'deleteMarkerLocal', + 'deleteRange', + 'deleteResources', + 'deleteSite', + 'deleteStatus', + 'deleteTeam', + 'deleteVehicle', + 'deleteVehicleCrew', + 'deleteWaypoint', + 'detach', + 'detectedMines', + 'diag_activeMissionFSMs', + 'diag_activeScripts', + 'diag_activeSQFScripts', + 'diag_activeSQSScripts', + 'diag_allMissionEventHandlers', + 'diag_captureFrame', + 'diag_captureFrameToFile', + 'diag_captureSlowFrame', + 'diag_codePerformance', + 'diag_deltaTime', + 'diag_drawmode', + 'diag_dumpCalltraceToLog', + 'diag_dumpScriptAssembly', + 'diag_dumpTerrainSynth', + 'diag_dynamicSimulationEnd', + 'diag_enable', + 'diag_enabled', + 'diag_exportConfig', + 'diag_exportTerrainSVG', + 'diag_fps', + 'diag_fpsmin', + 'diag_frameno', + 'diag_getTerrainSegmentOffset', + 'diag_lightNewLoad', + 'diag_list', + 'diag_localized', + 'diag_log', + 'diag_logSlowFrame', + 'diag_mergeConfigFile', + 'diag_recordTurretLimits', + 'diag_resetFSM', + 'diag_resetshapes', + 'diag_scope', + 'diag_setLightNew', + 'diag_stacktrace', + 'diag_tickTime', + 'diag_toggle', + 'dialog', + 'diarySubjectExists', + 'didJIP', + 'didJIPOwner', + 'difficulty', + 'difficultyEnabled', + 'difficultyEnabledRTD', + 'difficultyOption', + 'direction', + 'directionStabilizationEnabled', + 'directSay', + 'disableAI', + 'disableBrakes', + 'disableCollisionWith', + 'disableConversation', + 'disableDebriefingStats', + 'disableMapIndicators', + 'disableNVGEquipment', + 'disableRemoteSensors', + 'disableSerialization', + 'disableTIEquipment', + 'disableUAVConnectability', + 'disableUserInput', + 'displayAddEventHandler', + 'displayChild', + 'displayCtrl', + 'displayParent', + 'displayRemoveAllEventHandlers', + 'displayRemoveEventHandler', + 'displaySetEventHandler', + 'displayUniqueName', + 'displayUpdate', + 'dissolveTeam', + 'distance', + 'distance2D', + 'distanceSqr', + 'distributionRegion', + 'do3DENAction', + 'doArtilleryFire', + 'doFire', + 'doFollow', + 'doFSM', + 'doGetOut', + 'doMove', + 'doorPhase', + 'doStop', + 'doSuppressiveFire', + 'doTarget', + 'doWatch', + 'drawArrow', + 'drawEllipse', + 'drawIcon', + 'drawIcon3D', + 'drawLaser', + 'drawLine', + 'drawLine3D', + 'drawLink', + 'drawLocation', + 'drawPolygon', + 'drawRectangle', + 'drawTriangle', + 'driver', + 'drop', + 'dynamicSimulationDistance', + 'dynamicSimulationDistanceCoef', + 'dynamicSimulationEnabled', + 'dynamicSimulationSystemEnabled', + 'echo', + 'edit3DENMissionAttributes', + 'editObject', + 'editorSetEventHandler', + 'effectiveCommander', + 'elevatePeriscope', + 'emptyPositions', + 'enableAI', + 'enableAIFeature', + 'enableAimPrecision', + 'enableAttack', + 'enableAudioFeature', + 'enableAutoStartUpRTD', + 'enableAutoTrimRTD', + 'enableCamShake', + 'enableCaustics', + 'enableChannel', + 'enableCollisionWith', + 'enableCopilot', + 'enableDebriefingStats', + 'enableDiagLegend', + 'enableDirectionStabilization', + 'enableDynamicSimulation', + 'enableDynamicSimulationSystem', + 'enableEndDialog', + 'enableEngineArtillery', + 'enableEnvironment', + 'enableFatigue', + 'enableGunLights', + 'enableInfoPanelComponent', + 'enableIRLasers', + 'enableMimics', + 'enablePersonTurret', + 'enableRadio', + 'enableReload', + 'enableRopeAttach', + 'enableSatNormalOnDetail', + 'enableSaving', + 'enableSentences', + 'enableSimulation', + 'enableSimulationGlobal', + 'enableStamina', + 'enableStressDamage', + 'enableTeamSwitch', + 'enableTraffic', + 'enableUAVConnectability', + 'enableUAVWaypoints', + 'enableVehicleCargo', + 'enableVehicleSensor', + 'enableWeaponDisassembly', + 'endLoadingScreen', + 'endMission', + 'engineOn', + 'enginesIsOnRTD', + 'enginesPowerRTD', + 'enginesRpmRTD', + 'enginesTorqueRTD', + 'entities', + 'environmentEnabled', + 'environmentVolume', + 'equipmentDisabled', + 'estimatedEndServerTime', + 'estimatedTimeLeft', + 'evalObjectArgument', + 'everyBackpack', + 'everyContainer', + 'exec', + 'execEditorScript', + 'execFSM', + 'execVM', + 'exp', + 'expectedDestination', + 'exportJIPMessages', + 'eyeDirection', + 'eyePos', + 'face', + 'faction', + 'fadeEnvironment', + 'fadeMusic', + 'fadeRadio', + 'fadeSound', + 'fadeSpeech', + 'failMission', + 'fileExists', + 'fillWeaponsFromPool', + 'find', + 'findAny', + 'findCover', + 'findDisplay', + 'findEditorObject', + 'findEmptyPosition', + 'findEmptyPositionReady', + 'findIf', + 'findNearestEnemy', + 'finishMissionInit', + 'finite', + 'fire', + 'fireAtTarget', + 'firstBackpack', + 'flag', + 'flagAnimationPhase', + 'flagOwner', + 'flagSide', + 'flagTexture', + 'flatten', + 'fleeing', + 'floor', + 'flyInHeight', + 'flyInHeightASL', + 'focusedCtrl', + 'fog', + 'fogForecast', + 'fogParams', + 'forceAddUniform', + 'forceAtPositionRTD', + 'forceCadetDifficulty', + 'forcedMap', + 'forceEnd', + 'forceFlagTexture', + 'forceFollowRoad', + 'forceGeneratorRTD', + 'forceMap', + 'forceRespawn', + 'forceSpeed', + 'forceUnicode', + 'forceWalk', + 'forceWeaponFire', + 'forceWeatherChange', + 'forEachMember', + 'forEachMemberAgent', + 'forEachMemberTeam', + 'forgetTarget', + 'format', + 'formation', + 'formationDirection', + 'formationLeader', + 'formationMembers', + 'formationPosition', + 'formationTask', + 'formatText', + 'formLeader', + 'freeExtension', + 'freeLook', + 'fromEditor', + 'fuel', + 'fullCrew', + 'gearIDCAmmoCount', + 'gearSlotAmmoCount', + 'gearSlotData', + 'gestureState', + 'get', + 'get3DENActionState', + 'get3DENAttribute', + 'get3DENCamera', + 'get3DENConnections', + 'get3DENEntity', + 'get3DENEntityID', + 'get3DENGrid', + 'get3DENIconsVisible', + 'get3DENLayerEntities', + 'get3DENLinesVisible', + 'get3DENMissionAttribute', + 'get3DENMouseOver', + 'get3DENSelected', + 'getAimingCoef', + 'getAllEnv3DSoundControllers', + 'getAllEnvSoundControllers', + 'getAllHitPointsDamage', + 'getAllOwnedMines', + 'getAllPylonsInfo', + 'getAllSoundControllers', + 'getAllUnitTraits', + 'getAmmoCargo', + 'getAnimAimPrecision', + 'getAnimSpeedCoef', + 'getArray', + 'getArtilleryAmmo', + 'getArtilleryComputerSettings', + 'getArtilleryETA', + 'getAssetDLCInfo', + 'getAssignedCuratorLogic', + 'getAssignedCuratorUnit', + 'getAttackTarget', + 'getAudioOptionVolumes', + 'getBackpackCargo', + 'getBleedingRemaining', + 'getBurningValue', + 'getCalculatePlayerVisibilityByFriendly', + 'getCameraViewDirection', + 'getCargoIndex', + 'getCenterOfMass', + 'getClientState', + 'getClientStateNumber', + 'getCompatiblePylonMagazines', + 'getConnectedUAV', + 'getConnectedUAVUnit', + 'getContainerMaxLoad', + 'getCorpse', + 'getCruiseControl', + 'getCursorObjectParams', + 'getCustomAimCoef', + 'getCustomSoundController', + 'getCustomSoundControllerCount', + 'getDammage', + 'getDebriefingText', + 'getDescription', + 'getDir', + 'getDirVisual', + 'getDiverState', + 'getDLCAssetsUsage', + 'getDLCAssetsUsageByName', + 'getDLCs', + 'getDLCUsageTime', + 'getEditorCamera', + 'getEditorMode', + 'getEditorObjectScope', + 'getElevationOffset', + 'getEngineTargetRPMRTD', + 'getEnv3DSoundController', + 'getEnvSoundController', + 'getEventHandlerInfo', + 'getFatigue', + 'getFieldManualStartPage', + 'getForcedFlagTexture', + 'getForcedSpeed', + 'getFriend', + 'getFSMVariable', + 'getFuelCargo', + 'getGraphValues', + 'getGroupIcon', + 'getGroupIconParams', + 'getGroupIcons', + 'getHideFrom', + 'getHit', + 'getHitIndex', + 'getHitPointDamage', + 'getItemCargo', + 'getLighting', + 'getLightingAt', + 'getLoadedModsInfo', + 'getMagazineCargo', + 'getMarkerColor', + 'getMarkerPos', + 'getMarkerSize', + 'getMarkerType', + 'getMass', + 'getMissionConfig', + 'getMissionConfigValue', + 'getMissionDLCs', + 'getMissionLayerEntities', + 'getMissionLayers', + 'getMissionPath', + 'getModelInfo', + 'getMousePosition', + 'getMusicPlayedTime', + 'getNumber', + 'getObjectArgument', + 'getObjectChildren', + 'getObjectDLC', + 'getObjectFOV', + 'getObjectID', + 'getObjectMaterials', + 'getObjectProxy', + 'getObjectScale', + 'getObjectTextures', + 'getObjectType', + 'getObjectViewDistance', + 'getOpticsMode', + 'getOrDefault', + 'getOrDefaultCall', + 'getOxygenRemaining', + 'getPersonUsedDLCs', + 'getPilotCameraDirection', + 'getPilotCameraPosition', + 'getPilotCameraRotation', + 'getPilotCameraTarget', + 'getPiPViewDistance', + 'getPlateNumber', + 'getPlayerChannel', + 'getPlayerID', + 'getPlayerScores', + 'getPlayerUID', + 'getPlayerVoNVolume', + 'getPos', + 'getPosASL', + 'getPosASLVisual', + 'getPosASLW', + 'getPosATL', + 'getPosATLVisual', + 'getPosVisual', + 'getPosWorld', + 'getPosWorldVisual', + 'getPylonMagazines', + 'getRelDir', + 'getRelPos', + 'getRemoteSensorsDisabled', + 'getRepairCargo', + 'getResolution', + 'getRoadInfo', + 'getRotorBrakeRTD', + 'getSensorTargets', + 'getSensorThreats', + 'getShadowDistance', + 'getShotParents', + 'getSlingLoad', + 'getSoundController', + 'getSoundControllerResult', + 'getSpeed', + 'getStamina', + 'getStatValue', + 'getSteamFriendsServers', + 'getSubtitleOptions', + 'getSuppression', + 'getTerrainGrid', + 'getTerrainHeight', + 'getTerrainHeightASL', + 'getTerrainInfo', + 'getText', + 'getTextRaw', + 'getTextureInfo', + 'getTextWidth', + 'getTiParameters', + 'getTotalDLCUsageTime', + 'getTrimOffsetRTD', + 'getTurretLimits', + 'getTurretOpticsMode', + 'getUnitFreefallInfo', + 'getUnitLoadout', + 'getUnitTrait', + 'getUnloadInCombat', + 'getUserInfo', + 'getUserMFDText', + 'getUserMFDValue', + 'getVariable', + 'getVehicleCargo', + 'getVehicleTiPars', + 'getWeaponCargo', + 'getWeaponSway', + 'getWingsOrientationRTD', + 'getWingsPositionRTD', + 'getWPPos', + 'glanceAt', + 'globalChat', + 'globalRadio', + 'goggles', + 'goto', + 'group', + 'groupChat', + 'groupFromNetId', + 'groupIconSelectable', + 'groupIconsVisible', + 'groupID', + 'groupOwner', + 'groupRadio', + 'groups', + 'groupSelectedUnits', + 'groupSelectUnit', + 'gunner', + 'gusts', + 'halt', + 'handgunItems', + 'handgunMagazine', + 'handgunWeapon', + 'handsHit', + 'hashValue', + 'hasInterface', + 'hasPilotCamera', + 'hasWeapon', + 'hcAllGroups', + 'hcGroupParams', + 'hcLeader', + 'hcRemoveAllGroups', + 'hcRemoveGroup', + 'hcSelected', + 'hcSelectGroup', + 'hcSetGroup', + 'hcShowBar', + 'hcShownBar', + 'headgear', + 'hideBody', + 'hideObject', + 'hideObjectGlobal', + 'hideSelection', + 'hint', + 'hintC', + 'hintCadet', + 'hintSilent', + 'hmd', + 'hostMission', + 'htmlLoad', + 'HUDMovementLevels', + 'humidity', + 'image', + 'importAllGroups', + 'importance', + 'in', + 'inArea', + 'inAreaArray', + 'incapacitatedState', + 'inflame', + 'inflamed', + 'infoPanel', + 'infoPanelComponentEnabled', + 'infoPanelComponents', + 'infoPanels', + 'inGameUISetEventHandler', + 'inheritsFrom', + 'initAmbientLife', + 'inPolygon', + 'inputAction', + 'inputController', + 'inputMouse', + 'inRangeOfArtillery', + 'insert', + 'insertEditorObject', + 'intersect', + 'is3DEN', + 'is3DENMultiplayer', + 'is3DENPreview', + 'isAbleToBreathe', + 'isActionMenuVisible', + 'isAgent', + 'isAimPrecisionEnabled', + 'isAllowedCrewInImmobile', + 'isArray', + 'isAutoHoverOn', + 'isAutonomous', + 'isAutoStartUpEnabledRTD', + 'isAutotest', + 'isAutoTrimOnRTD', + 'isAwake', + 'isBleeding', + 'isBurning', + 'isClass', + 'isCollisionLightOn', + 'isCopilotEnabled', + 'isDamageAllowed', + 'isDedicated', + 'isDLCAvailable', + 'isEngineOn', + 'isEqualRef', + 'isEqualTo', + 'isEqualType', + 'isEqualTypeAll', + 'isEqualTypeAny', + 'isEqualTypeArray', + 'isEqualTypeParams', + 'isFilePatchingEnabled', + 'isFinal', + 'isFlashlightOn', + 'isFlatEmpty', + 'isForcedWalk', + 'isFormationLeader', + 'isGameFocused', + 'isGamePaused', + 'isGroupDeletedWhenEmpty', + 'isHidden', + 'isInRemainsCollector', + 'isInstructorFigureEnabled', + 'isIRLaserOn', + 'isKeyActive', + 'isKindOf', + 'isLaserOn', + 'isLightOn', + 'isLocalized', + 'isManualFire', + 'isMarkedForCollection', + 'isMissionProfileNamespaceLoaded', + 'isMultiplayer', + 'isMultiplayerSolo', + 'isNil', + 'isNotEqualRef', + 'isNotEqualTo', + 'isNull', + 'isNumber', + 'isObjectHidden', + 'isObjectRTD', + 'isOnRoad', + 'isPiPEnabled', + 'isPlayer', + 'isRealTime', + 'isRemoteExecuted', + 'isRemoteExecutedJIP', + 'isSaving', + 'isSensorTargetConfirmed', + 'isServer', + 'isShowing3DIcons', + 'isSimpleObject', + 'isSprintAllowed', + 'isStaminaEnabled', + 'isSteamMission', + 'isSteamOverlayEnabled', + 'isStreamFriendlyUIEnabled', + 'isStressDamageEnabled', + 'isText', + 'isTouchingGround', + 'isTurnedOut', + 'isTutHintsEnabled', + 'isUAVConnectable', + 'isUAVConnected', + 'isUIContext', + 'isUniformAllowed', + 'isVehicleCargo', + 'isVehicleRadarOn', + 'isVehicleSensorEnabled', + 'isWalking', + 'isWeaponDeployed', + 'isWeaponRested', + 'itemCargo', + 'items', + 'itemsWithMagazines', + 'join', + 'joinAs', + 'joinAsSilent', + 'joinSilent', + 'joinString', + 'kbAddDatabase', + 'kbAddDatabaseTargets', + 'kbAddTopic', + 'kbHasTopic', + 'kbReact', + 'kbRemoveTopic', + 'kbTell', + 'kbWasSaid', + 'keyImage', + 'keyName', + 'keys', + 'knowsAbout', + 'land', + 'landAt', + 'landResult', + 'language', + 'laserTarget', + 'lbAdd', + 'lbClear', + 'lbColor', + 'lbColorRight', + 'lbCurSel', + 'lbData', + 'lbDelete', + 'lbIsSelected', + 'lbPicture', + 'lbPictureRight', + 'lbSelection', + 'lbSetColor', + 'lbSetColorRight', + 'lbSetCurSel', + 'lbSetData', + 'lbSetPicture', + 'lbSetPictureColor', + 'lbSetPictureColorDisabled', + 'lbSetPictureColorSelected', + 'lbSetPictureRight', + 'lbSetPictureRightColor', + 'lbSetPictureRightColorDisabled', + 'lbSetPictureRightColorSelected', + 'lbSetSelectColor', + 'lbSetSelectColorRight', + 'lbSetSelected', + 'lbSetText', + 'lbSetTextRight', + 'lbSetTooltip', + 'lbSetValue', + 'lbSize', + 'lbSort', + 'lbSortBy', + 'lbSortByValue', + 'lbText', + 'lbTextRight', + 'lbTooltip', + 'lbValue', + 'leader', + 'leaderboardDeInit', + 'leaderboardGetRows', + 'leaderboardInit', + 'leaderboardRequestRowsFriends', + 'leaderboardRequestRowsGlobal', + 'leaderboardRequestRowsGlobalAroundUser', + 'leaderboardsRequestUploadScore', + 'leaderboardsRequestUploadScoreKeepBest', + 'leaderboardState', + 'leaveVehicle', + 'libraryCredits', + 'libraryDisclaimers', + 'lifeState', + 'lightAttachObject', + 'lightDetachObject', + 'lightIsOn', + 'lightnings', + 'limitSpeed', + 'linearConversion', + 'lineIntersects', + 'lineIntersectsObjs', + 'lineIntersectsSurfaces', + 'lineIntersectsWith', + 'linkItem', + 'list', + 'listObjects', + 'listRemoteTargets', + 'listVehicleSensors', + 'ln', + 'lnbAddArray', + 'lnbAddColumn', + 'lnbAddRow', + 'lnbClear', + 'lnbColor', + 'lnbColorRight', + 'lnbCurSelRow', + 'lnbData', + 'lnbDeleteColumn', + 'lnbDeleteRow', + 'lnbGetColumnsPosition', + 'lnbPicture', + 'lnbPictureRight', + 'lnbSetColor', + 'lnbSetColorRight', + 'lnbSetColumnsPos', + 'lnbSetCurSelRow', + 'lnbSetData', + 'lnbSetPicture', + 'lnbSetPictureColor', + 'lnbSetPictureColorRight', + 'lnbSetPictureColorSelected', + 'lnbSetPictureColorSelectedRight', + 'lnbSetPictureRight', + 'lnbSetText', + 'lnbSetTextRight', + 'lnbSetTooltip', + 'lnbSetValue', + 'lnbSize', + 'lnbSort', + 'lnbSortBy', + 'lnbSortByValue', + 'lnbText', + 'lnbTextRight', + 'lnbValue', + 'load', + 'loadAbs', + 'loadBackpack', + 'loadConfig', + 'loadFile', + 'loadGame', + 'loadIdentity', + 'loadMagazine', + 'loadOverlay', + 'loadStatus', + 'loadUniform', + 'loadVest', + 'localize', + 'localNamespace', + 'locationPosition', + 'lock', + 'lockCameraTo', + 'lockCargo', + 'lockDriver', + 'locked', + 'lockedCameraTo', + 'lockedCargo', + 'lockedDriver', + 'lockedInventory', + 'lockedTurret', + 'lockIdentity', + 'lockInventory', + 'lockTurret', + 'lockWp', + 'log', + 'logEntities', + 'logNetwork', + 'logNetworkTerminate', + 'lookAt', + 'lookAtPos', + 'magazineCargo', + 'magazines', + 'magazinesAllTurrets', + 'magazinesAmmo', + 'magazinesAmmoCargo', + 'magazinesAmmoFull', + 'magazinesDetail', + 'magazinesDetailBackpack', + 'magazinesDetailUniform', + 'magazinesDetailVest', + 'magazinesTurret', + 'magazineTurretAmmo', + 'mapAnimAdd', + 'mapAnimClear', + 'mapAnimCommit', + 'mapAnimDone', + 'mapCenterOnCamera', + 'mapGridPosition', + 'markAsFinishedOnSteam', + 'markerAlpha', + 'markerBrush', + 'markerChannel', + 'markerColor', + 'markerDir', + 'markerPolyline', + 'markerPos', + 'markerShadow', + 'markerShape', + 'markerSize', + 'markerText', + 'markerType', + 'matrixMultiply', + 'matrixTranspose', + 'max', + 'maxLoad', + 'members', + 'menuAction', + 'menuAdd', + 'menuChecked', + 'menuClear', + 'menuCollapse', + 'menuData', + 'menuDelete', + 'menuEnable', + 'menuEnabled', + 'menuExpand', + 'menuHover', + 'menuPicture', + 'menuSetAction', + 'menuSetCheck', + 'menuSetData', + 'menuSetPicture', + 'menuSetShortcut', + 'menuSetText', + 'menuSetURL', + 'menuSetValue', + 'menuShortcut', + 'menuShortcutText', + 'menuSize', + 'menuSort', + 'menuText', + 'menuURL', + 'menuValue', + 'merge', + 'min', + 'mineActive', + 'mineDetectedBy', + 'missileTarget', + 'missileTargetPos', + 'missionConfigFile', + 'missionDifficulty', + 'missionEnd', + 'missionName', + 'missionNameSource', + 'missionNamespace', + 'missionProfileNamespace', + 'missionStart', + 'missionVersion', + 'mod', + 'modelToWorld', + 'modelToWorldVisual', + 'modelToWorldVisualWorld', + 'modelToWorldWorld', + 'modParams', + 'moonIntensity', + 'moonPhase', + 'morale', + 'move', + 'move3DENCamera', + 'moveInAny', + 'moveInCargo', + 'moveInCommander', + 'moveInDriver', + 'moveInGunner', + 'moveInTurret', + 'moveObjectToEnd', + 'moveOut', + 'moveTime', + 'moveTo', + 'moveToCompleted', + 'moveToFailed', + 'musicVolume', + 'name', + 'namedProperties', + 'nameSound', + 'nearEntities', + 'nearestBuilding', + 'nearestLocation', + 'nearestLocations', + 'nearestLocationWithDubbing', + 'nearestMines', + 'nearestObject', + 'nearestObjects', + 'nearestTerrainObjects', + 'nearObjects', + 'nearObjectsReady', + 'nearRoads', + 'nearSupplies', + 'nearTargets', + 'needReload', + 'needService', + 'netId', + 'netObjNull', + 'newOverlay', + 'nextMenuItemIndex', + 'nextWeatherChange', + 'nMenuItems', + 'not', + 'numberOfEnginesRTD', + 'numberToDate', + 'objectCurators', + 'objectFromNetId', + 'objectParent', + 'objStatus', + 'onBriefingGroup', + 'onBriefingNotes', + 'onBriefingPlan', + 'onBriefingTeamSwitch', + 'onCommandModeChanged', + 'onDoubleClick', + 'onEachFrame', + 'onGroupIconClick', + 'onGroupIconOverEnter', + 'onGroupIconOverLeave', + 'onHCGroupSelectionChanged', + 'onMapSingleClick', + 'onPlayerConnected', + 'onPlayerDisconnected', + 'onPreloadFinished', + 'onPreloadStarted', + 'onShowNewObject', + 'onTeamSwitch', + 'openCuratorInterface', + 'openDLCPage', + 'openGPS', + 'openMap', + 'openSteamApp', + 'openYoutubeVideo', + 'or', + 'orderGetIn', + 'overcast', + 'overcastForecast', + 'owner', + 'param', + 'params', + 'parseNumber', + 'parseSimpleArray', + 'parseText', + 'parsingNamespace', + 'particlesQuality', + 'periscopeElevation', + 'pickWeaponPool', + 'pitch', + 'pixelGrid', + 'pixelGridBase', + 'pixelGridNoUIScale', + 'pixelH', + 'pixelW', + 'playableSlotsNumber', + 'playableUnits', + 'playAction', + 'playActionNow', + 'player', + 'playerRespawnTime', + 'playerSide', + 'playersNumber', + 'playGesture', + 'playMission', + 'playMove', + 'playMoveNow', + 'playMusic', + 'playScriptedMission', + 'playSound', + 'playSound3D', + 'playSoundUI', + 'pose', + 'position', + 'positionCameraToWorld', + 'posScreenToWorld', + 'posWorldToScreen', + 'ppEffectAdjust', + 'ppEffectCommit', + 'ppEffectCommitted', + 'ppEffectCreate', + 'ppEffectDestroy', + 'ppEffectEnable', + 'ppEffectEnabled', + 'ppEffectForceInNVG', + 'precision', + 'preloadCamera', + 'preloadObject', + 'preloadSound', + 'preloadTitleObj', + 'preloadTitleRsc', + 'preprocessFile', + 'preprocessFileLineNumbers', + 'primaryWeapon', + 'primaryWeaponItems', + 'primaryWeaponMagazine', + 'priority', + 'processDiaryLink', + 'productVersion', + 'profileName', + 'profileNamespace', + 'profileNameSteam', + 'progressLoadingScreen', + 'progressPosition', + 'progressSetPosition', + 'publicVariable', + 'publicVariableClient', + 'publicVariableServer', + 'pushBack', + 'pushBackUnique', + 'putWeaponPool', + 'queryItemsPool', + 'queryMagazinePool', + 'queryWeaponPool', + 'rad', + 'radioChannelAdd', + 'radioChannelCreate', + 'radioChannelInfo', + 'radioChannelRemove', + 'radioChannelSetCallSign', + 'radioChannelSetLabel', + 'radioEnabled', + 'radioVolume', + 'rain', + 'rainbow', + 'rainParams', + 'random', + 'rank', + 'rankId', + 'rating', + 'rectangular', + 'regexFind', + 'regexMatch', + 'regexReplace', + 'registeredTasks', + 'registerTask', + 'reload', + 'reloadEnabled', + 'remoteControl', + 'remoteExec', + 'remoteExecCall', + 'remoteExecutedOwner', + 'remove3DENConnection', + 'remove3DENEventHandler', + 'remove3DENLayer', + 'removeAction', + 'removeAll3DENEventHandlers', + 'removeAllActions', + 'removeAllAssignedItems', + 'removeAllBinocularItems', + 'removeAllContainers', + 'removeAllCuratorAddons', + 'removeAllCuratorCameraAreas', + 'removeAllCuratorEditingAreas', + 'removeAllEventHandlers', + 'removeAllHandgunItems', + 'removeAllItems', + 'removeAllItemsWithMagazines', + 'removeAllMissionEventHandlers', + 'removeAllMPEventHandlers', + 'removeAllMusicEventHandlers', + 'removeAllOwnedMines', + 'removeAllPrimaryWeaponItems', + 'removeAllSecondaryWeaponItems', + 'removeAllUserActionEventHandlers', + 'removeAllWeapons', + 'removeBackpack', + 'removeBackpackGlobal', + 'removeBinocularItem', + 'removeCuratorAddons', + 'removeCuratorCameraArea', + 'removeCuratorEditableObjects', + 'removeCuratorEditingArea', + 'removeDiaryRecord', + 'removeDiarySubject', + 'removeDrawIcon', + 'removeDrawLinks', + 'removeEventHandler', + 'removeFromRemainsCollector', + 'removeGoggles', + 'removeGroupIcon', + 'removeHandgunItem', + 'removeHeadgear', + 'removeItem', + 'removeItemFromBackpack', + 'removeItemFromUniform', + 'removeItemFromVest', + 'removeItems', + 'removeMagazine', + 'removeMagazineGlobal', + 'removeMagazines', + 'removeMagazinesTurret', + 'removeMagazineTurret', + 'removeMenuItem', + 'removeMissionEventHandler', + 'removeMPEventHandler', + 'removeMusicEventHandler', + 'removeOwnedMine', + 'removePrimaryWeaponItem', + 'removeSecondaryWeaponItem', + 'removeSimpleTask', + 'removeSwitchableUnit', + 'removeTeamMember', + 'removeUniform', + 'removeUserActionEventHandler', + 'removeVest', + 'removeWeapon', + 'removeWeaponAttachmentCargo', + 'removeWeaponCargo', + 'removeWeaponGlobal', + 'removeWeaponTurret', + 'reportRemoteTarget', + 'requiredVersion', + 'resetCamShake', + 'resetSubgroupDirection', + 'resize', + 'resources', + 'respawnVehicle', + 'restartEditorCamera', + 'reveal', + 'revealMine', + 'reverse', + 'reversedMouseY', + 'roadAt', + 'roadsConnectedTo', + 'roleDescription', + 'ropeAttachedObjects', + 'ropeAttachedTo', + 'ropeAttachEnabled', + 'ropeAttachTo', + 'ropeCreate', + 'ropeCut', + 'ropeDestroy', + 'ropeDetach', + 'ropeEndPosition', + 'ropeLength', + 'ropes', + 'ropesAttachedTo', + 'ropeSegments', + 'ropeUnwind', + 'ropeUnwound', + 'rotorsForcesRTD', + 'rotorsRpmRTD', + 'round', + 'runInitScript', + 'safeZoneH', + 'safeZoneW', + 'safeZoneWAbs', + 'safeZoneX', + 'safeZoneXAbs', + 'safeZoneY', + 'save3DENInventory', + 'saveGame', + 'saveIdentity', + 'saveJoysticks', + 'saveMissionProfileNamespace', + 'saveOverlay', + 'saveProfileNamespace', + 'saveStatus', + 'saveVar', + 'savingEnabled', + 'say', + 'say2D', + 'say3D', + 'scopeName', + 'score', + 'scoreSide', + 'screenshot', + 'screenToWorld', + 'scriptDone', + 'scriptName', + 'scudState', + 'secondaryWeapon', + 'secondaryWeaponItems', + 'secondaryWeaponMagazine', + 'select', + 'selectBestPlaces', + 'selectDiarySubject', + 'selectedEditorObjects', + 'selectEditorObject', + 'selectionNames', + 'selectionPosition', + 'selectionVectorDirAndUp', + 'selectLeader', + 'selectMax', + 'selectMin', + 'selectNoPlayer', + 'selectPlayer', + 'selectRandom', + 'selectRandomWeighted', + 'selectWeapon', + 'selectWeaponTurret', + 'sendAUMessage', + 'sendSimpleCommand', + 'sendTask', + 'sendTaskResult', + 'sendUDPMessage', + 'sentencesEnabled', + 'serverCommand', + 'serverCommandAvailable', + 'serverCommandExecutable', + 'serverName', + 'serverNamespace', + 'serverTime', + 'set', + 'set3DENAttribute', + 'set3DENAttributes', + 'set3DENGrid', + 'set3DENIconsVisible', + 'set3DENLayer', + 'set3DENLinesVisible', + 'set3DENLogicType', + 'set3DENMissionAttribute', + 'set3DENMissionAttributes', + 'set3DENModelsVisible', + 'set3DENObjectType', + 'set3DENSelected', + 'setAccTime', + 'setActualCollectiveRTD', + 'setAirplaneThrottle', + 'setAirportSide', + 'setAmmo', + 'setAmmoCargo', + 'setAmmoOnPylon', + 'setAnimSpeedCoef', + 'setAperture', + 'setApertureNew', + 'setArmoryPoints', + 'setAttributes', + 'setAutonomous', + 'setBehaviour', + 'setBehaviourStrong', + 'setBleedingRemaining', + 'setBrakesRTD', + 'setCameraInterest', + 'setCamShakeDefParams', + 'setCamShakeParams', + 'setCamUseTi', + 'setCaptive', + 'setCenterOfMass', + 'setCollisionLight', + 'setCombatBehaviour', + 'setCombatMode', + 'setCompassOscillation', + 'setConvoySeparation', + 'setCruiseControl', + 'setCuratorCameraAreaCeiling', + 'setCuratorCoef', + 'setCuratorEditingAreaType', + 'setCuratorWaypointCost', + 'setCurrentChannel', + 'setCurrentTask', + 'setCurrentWaypoint', + 'setCustomAimCoef', + 'SetCustomMissionData', + 'setCustomSoundController', + 'setCustomWeightRTD', + 'setDamage', + 'setDammage', + 'setDate', + 'setDebriefingText', + 'setDefaultCamera', + 'setDestination', + 'setDetailMapBlendPars', + 'setDiaryRecordText', + 'setDiarySubjectPicture', + 'setDir', + 'setDirection', + 'setDrawIcon', + 'setDriveOnPath', + 'setDropInterval', + 'setDynamicSimulationDistance', + 'setDynamicSimulationDistanceCoef', + 'setEditorMode', + 'setEditorObjectScope', + 'setEffectCondition', + 'setEffectiveCommander', + 'setEngineRpmRTD', + 'setFace', + 'setFaceanimation', + 'setFatigue', + 'setFeatureType', + 'setFlagAnimationPhase', + 'setFlagOwner', + 'setFlagSide', + 'setFlagTexture', + 'setFog', + 'setForceGeneratorRTD', + 'setFormation', + 'setFormationTask', + 'setFormDir', + 'setFriend', + 'setFromEditor', + 'setFSMVariable', + 'setFuel', + 'setFuelCargo', + 'setGroupIcon', + 'setGroupIconParams', + 'setGroupIconsSelectable', + 'setGroupIconsVisible', + 'setGroupid', + 'setGroupIdGlobal', + 'setGroupOwner', + 'setGusts', + 'setHideBehind', + 'setHit', + 'setHitIndex', + 'setHitPointDamage', + 'setHorizonParallaxCoef', + 'setHUDMovementLevels', + 'setHumidity', + 'setIdentity', + 'setImportance', + 'setInfoPanel', + 'setLeader', + 'setLightAmbient', + 'setLightAttenuation', + 'setLightBrightness', + 'setLightColor', + 'setLightConePars', + 'setLightDayLight', + 'setLightFlareMaxDistance', + 'setLightFlareSize', + 'setLightIntensity', + 'setLightIR', + 'setLightnings', + 'setLightUseFlare', + 'setLightVolumeShape', + 'setLocalWindParams', + 'setMagazineTurretAmmo', + 'setMarkerAlpha', + 'setMarkerAlphaLocal', + 'setMarkerBrush', + 'setMarkerBrushLocal', + 'setMarkerColor', + 'setMarkerColorLocal', + 'setMarkerDir', + 'setMarkerDirLocal', + 'setMarkerPolyline', + 'setMarkerPolylineLocal', + 'setMarkerPos', + 'setMarkerPosLocal', + 'setMarkerShadow', + 'setMarkerShadowLocal', + 'setMarkerShape', + 'setMarkerShapeLocal', + 'setMarkerSize', + 'setMarkerSizeLocal', + 'setMarkerText', + 'setMarkerTextLocal', + 'setMarkerType', + 'setMarkerTypeLocal', + 'setMass', + 'setMaxLoad', + 'setMimic', + 'setMissileTarget', + 'setMissileTargetPos', + 'setMousePosition', + 'setMusicEffect', + 'setMusicEventHandler', + 'setName', + 'setNameSound', + 'setObjectArguments', + 'setObjectMaterial', + 'setObjectMaterialGlobal', + 'setObjectProxy', + 'setObjectScale', + 'setObjectTexture', + 'setObjectTextureGlobal', + 'setObjectViewDistance', + 'setOpticsMode', + 'setOvercast', + 'setOwner', + 'setOxygenRemaining', + 'setParticleCircle', + 'setParticleClass', + 'setParticleFire', + 'setParticleParams', + 'setParticleRandom', + 'setPilotCameraDirection', + 'setPilotCameraRotation', + 'setPilotCameraTarget', + 'setPilotLight', + 'setPiPEffect', + 'setPiPViewDistance', + 'setPitch', + 'setPlateNumber', + 'setPlayable', + 'setPlayerRespawnTime', + 'setPlayerVoNVolume', + 'setPos', + 'setPosASL', + 'setPosASL2', + 'setPosASLW', + 'setPosATL', + 'setPosition', + 'setPosWorld', + 'setPylonLoadout', + 'setPylonsPriority', + 'setRadioMsg', + 'setRain', + 'setRainbow', + 'setRandomLip', + 'setRank', + 'setRectangular', + 'setRepairCargo', + 'setRotorBrakeRTD', + 'setShadowDistance', + 'setShotParents', + 'setSide', + 'setSimpleTaskAlwaysVisible', + 'setSimpleTaskCustomData', + 'setSimpleTaskDescription', + 'setSimpleTaskDestination', + 'setSimpleTaskTarget', + 'setSimpleTaskType', + 'setSimulWeatherLayers', + 'setSize', + 'setSkill', + 'setSlingLoad', + 'setSoundEffect', + 'setSpeaker', + 'setSpeech', + 'setSpeedMode', + 'setStamina', + 'setStaminaScheme', + 'setStatValue', + 'setSuppression', + 'setSystemOfUnits', + 'setTargetAge', + 'setTaskMarkerOffset', + 'setTaskResult', + 'setTaskState', + 'setTerrainGrid', + 'setTerrainHeight', + 'setText', + 'setTimeMultiplier', + 'setTiParameter', + 'setTitleEffect', + 'setTowParent', + 'setTrafficDensity', + 'setTrafficDistance', + 'setTrafficGap', + 'setTrafficSpeed', + 'setTriggerActivation', + 'setTriggerArea', + 'setTriggerInterval', + 'setTriggerStatements', + 'setTriggerText', + 'setTriggerTimeout', + 'setTriggerType', + 'setTurretLimits', + 'setTurretOpticsMode', + 'setType', + 'setUnconscious', + 'setUnitAbility', + 'setUnitCombatMode', + 'setUnitFreefallHeight', + 'setUnitLoadout', + 'setUnitPos', + 'setUnitPosWeak', + 'setUnitRank', + 'setUnitRecoilCoefficient', + 'setUnitTrait', + 'setUnloadInCombat', + 'setUserActionText', + 'setUserMFDText', + 'setUserMFDValue', + 'setVariable', + 'setVectorDir', + 'setVectorDirAndUp', + 'setVectorUp', + 'setVehicleAmmo', + 'setVehicleAmmoDef', + 'setVehicleArmor', + 'setVehicleCargo', + 'setVehicleId', + 'setVehicleLock', + 'setVehiclePosition', + 'setVehicleRadar', + 'setVehicleReceiveRemoteTargets', + 'setVehicleReportOwnPosition', + 'setVehicleReportRemoteTargets', + 'setVehicleTiPars', + 'setVehicleVarName', + 'setVelocity', + 'setVelocityModelSpace', + 'setVelocityTransformation', + 'setViewDistance', + 'setVisibleIfTreeCollapsed', + 'setWantedRPMRTD', + 'setWaves', + 'setWaypointBehaviour', + 'setWaypointCombatMode', + 'setWaypointCompletionRadius', + 'setWaypointDescription', + 'setWaypointForceBehaviour', + 'setWaypointFormation', + 'setWaypointHousePosition', + 'setWaypointLoiterAltitude', + 'setWaypointLoiterRadius', + 'setWaypointLoiterType', + 'setWaypointName', + 'setWaypointPosition', + 'setWaypointScript', + 'setWaypointSpeed', + 'setWaypointStatements', + 'setWaypointTimeout', + 'setWaypointType', + 'setWaypointVisible', + 'setWeaponReloadingTime', + 'setWeaponZeroing', + 'setWind', + 'setWindDir', + 'setWindForce', + 'setWindStr', + 'setWingForceScaleRTD', + 'setWPPos', + 'show3DIcons', + 'showChat', + 'showCinemaBorder', + 'showCommandingMenu', + 'showCompass', + 'showCuratorCompass', + 'showGps', + 'showHUD', + 'showLegend', + 'showMap', + 'shownArtilleryComputer', + 'shownChat', + 'shownCompass', + 'shownCuratorCompass', + 'showNewEditorObject', + 'shownGps', + 'shownHUD', + 'shownMap', + 'shownPad', + 'shownRadio', + 'shownScoretable', + 'shownSubtitles', + 'shownUAVFeed', + 'shownWarrant', + 'shownWatch', + 'showPad', + 'showRadio', + 'showScoretable', + 'showSubtitles', + 'showUAVFeed', + 'showWarrant', + 'showWatch', + 'showWaypoint', + 'showWaypoints', + 'side', + 'sideChat', + 'sideRadio', + 'simpleTasks', + 'simulationEnabled', + 'simulCloudDensity', + 'simulCloudOcclusion', + 'simulInClouds', + 'simulWeatherSync', + 'sin', + 'size', + 'sizeOf', + 'skill', + 'skillFinal', + 'skipTime', + 'sleep', + 'sliderPosition', + 'sliderRange', + 'sliderSetPosition', + 'sliderSetRange', + 'sliderSetSpeed', + 'sliderSpeed', + 'slingLoadAssistantShown', + 'soldierMagazines', + 'someAmmo', + 'sort', + 'soundVolume', + 'spawn', + 'speaker', + 'speechVolume', + 'speed', + 'speedMode', + 'splitString', + 'sqrt', + 'squadParams', + 'stance', + 'startLoadingScreen', + 'stop', + 'stopEngineRTD', + 'stopped', + 'str', + 'sunOrMoon', + 'supportInfo', + 'suppressFor', + 'surfaceIsWater', + 'surfaceNormal', + 'surfaceTexture', + 'surfaceType', + 'swimInDepth', + 'switchableUnits', + 'switchAction', + 'switchCamera', + 'switchGesture', + 'switchLight', + 'switchMove', + 'synchronizedObjects', + 'synchronizedTriggers', + 'synchronizedWaypoints', + 'synchronizeObjectsAdd', + 'synchronizeObjectsRemove', + 'synchronizeTrigger', + 'synchronizeWaypoint', + 'systemChat', + 'systemOfUnits', + 'systemTime', + 'systemTimeUTC', + 'tan', + 'targetKnowledge', + 'targets', + 'targetsAggregate', + 'targetsQuery', + 'taskAlwaysVisible', + 'taskChildren', + 'taskCompleted', + 'taskCustomData', + 'taskDescription', + 'taskDestination', + 'taskHint', + 'taskMarkerOffset', + 'taskName', + 'taskParent', + 'taskResult', + 'taskState', + 'taskType', + 'teamMember', + 'teamName', + 'teams', + 'teamSwitch', + 'teamSwitchEnabled', + 'teamType', + 'terminate', + 'terrainIntersect', + 'terrainIntersectASL', + 'terrainIntersectAtASL', + 'text', + 'textLog', + 'textLogFormat', + 'tg', + 'time', + 'timeMultiplier', + 'titleCut', + 'titleFadeOut', + 'titleObj', + 'titleRsc', + 'titleText', + 'toArray', + 'toFixed', + 'toLower', + 'toLowerANSI', + 'toString', + 'toUpper', + 'toUpperANSI', + 'triggerActivated', + 'triggerActivation', + 'triggerAmmo', + 'triggerArea', + 'triggerAttachedVehicle', + 'triggerAttachObject', + 'triggerAttachVehicle', + 'triggerDynamicSimulation', + 'triggerInterval', + 'triggerStatements', + 'triggerText', + 'triggerTimeout', + 'triggerTimeoutCurrent', + 'triggerType', + 'trim', + 'turretLocal', + 'turretOwner', + 'turretUnit', + 'tvAdd', + 'tvClear', + 'tvCollapse', + 'tvCollapseAll', + 'tvCount', + 'tvCurSel', + 'tvData', + 'tvDelete', + 'tvExpand', + 'tvExpandAll', + 'tvIsSelected', + 'tvPicture', + 'tvPictureRight', + 'tvSelection', + 'tvSetColor', + 'tvSetCurSel', + 'tvSetData', + 'tvSetPicture', + 'tvSetPictureColor', + 'tvSetPictureColorDisabled', + 'tvSetPictureColorSelected', + 'tvSetPictureRight', + 'tvSetPictureRightColor', + 'tvSetPictureRightColorDisabled', + 'tvSetPictureRightColorSelected', + 'tvSetSelectColor', + 'tvSetSelected', + 'tvSetText', + 'tvSetTooltip', + 'tvSetValue', + 'tvSort', + 'tvSortAll', + 'tvSortByValue', + 'tvSortByValueAll', + 'tvText', + 'tvTooltip', + 'tvValue', + 'type', + 'typeName', + 'typeOf', + 'UAVControl', + 'uiNamespace', + 'uiSleep', + 'unassignCurator', + 'unassignItem', + 'unassignTeam', + 'unassignVehicle', + 'underwater', + 'uniform', + 'uniformContainer', + 'uniformItems', + 'uniformMagazines', + 'uniqueUnitItems', + 'unitAddons', + 'unitAimPosition', + 'unitAimPositionVisual', + 'unitBackpack', + 'unitCombatMode', + 'unitIsUAV', + 'unitPos', + 'unitReady', + 'unitRecoilCoefficient', + 'units', + 'unitsBelowHeight', + 'unitTurret', + 'unlinkItem', + 'unlockAchievement', + 'unregisterTask', + 'updateDrawIcon', + 'updateMenuItem', + 'updateObjectTree', + 'useAIOperMapObstructionTest', + 'useAISteeringComponent', + 'useAudioTimeForMoves', + 'userInputDisabled', + 'values', + 'vectorAdd', + 'vectorCos', + 'vectorCrossProduct', + 'vectorDiff', + 'vectorDir', + 'vectorDirVisual', + 'vectorDistance', + 'vectorDistanceSqr', + 'vectorDotProduct', + 'vectorFromTo', + 'vectorLinearConversion', + 'vectorMagnitude', + 'vectorMagnitudeSqr', + 'vectorModelToWorld', + 'vectorModelToWorldVisual', + 'vectorMultiply', + 'vectorNormalized', + 'vectorUp', + 'vectorUpVisual', + 'vectorWorldToModel', + 'vectorWorldToModelVisual', + 'vehicle', + 'vehicleCargoEnabled', + 'vehicleChat', + 'vehicleMoveInfo', + 'vehicleRadio', + 'vehicleReceiveRemoteTargets', + 'vehicleReportOwnPosition', + 'vehicleReportRemoteTargets', + 'vehicles', + 'vehicleVarName', + 'velocity', + 'velocityModelSpace', + 'verifySignature', + 'vest', + 'vestContainer', + 'vestItems', + 'vestMagazines', + 'viewDistance', + 'visibleCompass', + 'visibleGps', + 'visibleMap', + 'visiblePosition', + 'visiblePositionASL', + 'visibleScoretable', + 'visibleWatch', + 'waves', + 'waypointAttachedObject', + 'waypointAttachedVehicle', + 'waypointAttachObject', + 'waypointAttachVehicle', + 'waypointBehaviour', + 'waypointCombatMode', + 'waypointCompletionRadius', + 'waypointDescription', + 'waypointForceBehaviour', + 'waypointFormation', + 'waypointHousePosition', + 'waypointLoiterAltitude', + 'waypointLoiterRadius', + 'waypointLoiterType', + 'waypointName', + 'waypointPosition', + 'waypoints', + 'waypointScript', + 'waypointsEnabledUAV', + 'waypointShow', + 'waypointSpeed', + 'waypointStatements', + 'waypointTimeout', + 'waypointTimeoutCurrent', + 'waypointType', + 'waypointVisible', + 'weaponAccessories', + 'weaponAccessoriesCargo', + 'weaponCargo', + 'weaponDirection', + 'weaponInertia', + 'weaponLowered', + 'weaponReloadingTime', + 'weapons', + 'weaponsInfo', + 'weaponsItems', + 'weaponsItemsCargo', + 'weaponState', + 'weaponsTurret', + 'weightRTD', + 'WFSideText', + 'wind', + 'windDir', + 'windRTD', + 'windStr', + 'wingsForcesRTD', + 'worldName', + 'worldSize', + 'worldToModel', + 'worldToModelVisual', + 'worldToScreen' + ]; + + // list of keywords from: + // https://community.bistudio.com/wiki/PreProcessor_Commands + const PREPROCESSOR = { + className: 'meta', + begin: /#\s*[a-z]+\b/, + end: /$/, + keywords: 'define undef ifdef ifndef else endif include if', + contains: [ + { + begin: /\\\n/, + relevance: 0 + }, + hljs.inherit(STRINGS, { className: 'string' }), + { + begin: /<[^\n>]*>/, + end: /$/, + illegal: '\\n' + }, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }; + + return { + name: 'SQF', + case_insensitive: true, + keywords: { + keyword: KEYWORDS, + built_in: BUILT_IN, + literal: LITERAL + }, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.NUMBER_MODE, + VARIABLE, + FUNCTION, + STRINGS, + PREPROCESSOR + ], + illegal: [ + //$ is only valid when used with Hex numbers (e.g. $FF) + /\$[^a-fA-F0-9]/, + /\w\$/, + /\?/, //There's no ? in SQF + /@/, //There's no @ in SQF + // Brute-force-fixing the build error. See https://github.com/highlightjs/highlight.js/pull/3193#issuecomment-843088729 + / \| /, + // . is only used in numbers + /[a-zA-Z_]\./, + /\:\=/, + /\[\:/ + ] + }; +} + +export { sqf as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/sqf.js.js b/frontend/node_modules/highlight.js/es/languages/sqf.js.js new file mode 100644 index 0000000..46da754 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/sqf.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/sqf" instead of "highlight.js/lib/languages/sqf.js"' + ); + } + } + emitWarning(); + import lang from './sqf.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/sql.js b/frontend/node_modules/highlight.js/es/languages/sql.js new file mode 100644 index 0000000..f38d839 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/sql.js @@ -0,0 +1,693 @@ +/* + Language: SQL + Website: https://en.wikipedia.org/wiki/SQL + Category: common, database + */ + +/* + +Goals: + +SQL is intended to highlight basic/common SQL keywords and expressions + +- If pretty much every single SQL server includes supports, then it's a canidate. +- It is NOT intended to include tons of vendor specific keywords (Oracle, MySQL, + PostgreSQL) although the list of data types is purposely a bit more expansive. +- For more specific SQL grammars please see: + - PostgreSQL and PL/pgSQL - core + - T-SQL - https://github.com/highlightjs/highlightjs-tsql + - sql_more (core) + + */ + +function sql(hljs) { + const regex = hljs.regex; + const COMMENT_MODE = hljs.COMMENT('--', '$'); + const STRING = { + scope: 'string', + variants: [ + { + begin: /'/, + end: /'/, + contains: [ { match: /''/ } ] + } + ] + }; + const QUOTED_IDENTIFIER = { + begin: /"/, + end: /"/, + contains: [ { match: /""/ } ] + }; + + const LITERALS = [ + "true", + "false", + // Not sure it's correct to call NULL literal, and clauses like IS [NOT] NULL look strange that way. + // "null", + "unknown" + ]; + + const MULTI_WORD_TYPES = [ + "double precision", + "large object", + "with timezone", + "without timezone" + ]; + + const TYPES = [ + 'bigint', + 'binary', + 'blob', + 'boolean', + 'char', + 'character', + 'clob', + 'date', + 'dec', + 'decfloat', + 'decimal', + 'float', + 'int', + 'integer', + 'interval', + 'nchar', + 'nclob', + 'national', + 'numeric', + 'real', + 'row', + 'smallint', + 'time', + 'timestamp', + 'varchar', + 'varying', // modifier (character varying) + 'varbinary' + ]; + + const NON_RESERVED_WORDS = [ + "add", + "asc", + "collation", + "desc", + "final", + "first", + "last", + "view" + ]; + + // https://jakewheat.github.io/sql-overview/sql-2016-foundation-grammar.html#reserved-word + const RESERVED_WORDS = [ + "abs", + "acos", + "all", + "allocate", + "alter", + "and", + "any", + "are", + "array", + "array_agg", + "array_max_cardinality", + "as", + "asensitive", + "asin", + "asymmetric", + "at", + "atan", + "atomic", + "authorization", + "avg", + "begin", + "begin_frame", + "begin_partition", + "between", + "bigint", + "binary", + "blob", + "boolean", + "both", + "by", + "call", + "called", + "cardinality", + "cascaded", + "case", + "cast", + "ceil", + "ceiling", + "char", + "char_length", + "character", + "character_length", + "check", + "classifier", + "clob", + "close", + "coalesce", + "collate", + "collect", + "column", + "commit", + "condition", + "connect", + "constraint", + "contains", + "convert", + "copy", + "corr", + "corresponding", + "cos", + "cosh", + "count", + "covar_pop", + "covar_samp", + "create", + "cross", + "cube", + "cume_dist", + "current", + "current_catalog", + "current_date", + "current_default_transform_group", + "current_path", + "current_role", + "current_row", + "current_schema", + "current_time", + "current_timestamp", + "current_path", + "current_role", + "current_transform_group_for_type", + "current_user", + "cursor", + "cycle", + "date", + "day", + "deallocate", + "dec", + "decimal", + "decfloat", + "declare", + "default", + "define", + "delete", + "dense_rank", + "deref", + "describe", + "deterministic", + "disconnect", + "distinct", + "double", + "drop", + "dynamic", + "each", + "element", + "else", + "empty", + "end", + "end_frame", + "end_partition", + "end-exec", + "equals", + "escape", + "every", + "except", + "exec", + "execute", + "exists", + "exp", + "external", + "extract", + "false", + "fetch", + "filter", + "first_value", + "float", + "floor", + "for", + "foreign", + "frame_row", + "free", + "from", + "full", + "function", + "fusion", + "get", + "global", + "grant", + "group", + "grouping", + "groups", + "having", + "hold", + "hour", + "identity", + "in", + "indicator", + "initial", + "inner", + "inout", + "insensitive", + "insert", + "int", + "integer", + "intersect", + "intersection", + "interval", + "into", + "is", + "join", + "json_array", + "json_arrayagg", + "json_exists", + "json_object", + "json_objectagg", + "json_query", + "json_table", + "json_table_primitive", + "json_value", + "lag", + "language", + "large", + "last_value", + "lateral", + "lead", + "leading", + "left", + "like", + "like_regex", + "listagg", + "ln", + "local", + "localtime", + "localtimestamp", + "log", + "log10", + "lower", + "match", + "match_number", + "match_recognize", + "matches", + "max", + "member", + "merge", + "method", + "min", + "minute", + "mod", + "modifies", + "module", + "month", + "multiset", + "national", + "natural", + "nchar", + "nclob", + "new", + "no", + "none", + "normalize", + "not", + "nth_value", + "ntile", + "null", + "nullif", + "numeric", + "octet_length", + "occurrences_regex", + "of", + "offset", + "old", + "omit", + "on", + "one", + "only", + "open", + "or", + "order", + "out", + "outer", + "over", + "overlaps", + "overlay", + "parameter", + "partition", + "pattern", + "per", + "percent", + "percent_rank", + "percentile_cont", + "percentile_disc", + "period", + "portion", + "position", + "position_regex", + "power", + "precedes", + "precision", + "prepare", + "primary", + "procedure", + "ptf", + "range", + "rank", + "reads", + "real", + "recursive", + "ref", + "references", + "referencing", + "regr_avgx", + "regr_avgy", + "regr_count", + "regr_intercept", + "regr_r2", + "regr_slope", + "regr_sxx", + "regr_sxy", + "regr_syy", + "release", + "result", + "return", + "returns", + "revoke", + "right", + "rollback", + "rollup", + "row", + "row_number", + "rows", + "running", + "savepoint", + "scope", + "scroll", + "search", + "second", + "seek", + "select", + "sensitive", + "session_user", + "set", + "show", + "similar", + "sin", + "sinh", + "skip", + "smallint", + "some", + "specific", + "specifictype", + "sql", + "sqlexception", + "sqlstate", + "sqlwarning", + "sqrt", + "start", + "static", + "stddev_pop", + "stddev_samp", + "submultiset", + "subset", + "substring", + "substring_regex", + "succeeds", + "sum", + "symmetric", + "system", + "system_time", + "system_user", + "table", + "tablesample", + "tan", + "tanh", + "then", + "time", + "timestamp", + "timezone_hour", + "timezone_minute", + "to", + "trailing", + "translate", + "translate_regex", + "translation", + "treat", + "trigger", + "trim", + "trim_array", + "true", + "truncate", + "uescape", + "union", + "unique", + "unknown", + "unnest", + "update", + "upper", + "user", + "using", + "value", + "values", + "value_of", + "var_pop", + "var_samp", + "varbinary", + "varchar", + "varying", + "versioning", + "when", + "whenever", + "where", + "width_bucket", + "window", + "with", + "within", + "without", + "year", + ]; + + // these are reserved words we have identified to be functions + // and should only be highlighted in a dispatch-like context + // ie, array_agg(...), etc. + const RESERVED_FUNCTIONS = [ + "abs", + "acos", + "array_agg", + "asin", + "atan", + "avg", + "cast", + "ceil", + "ceiling", + "coalesce", + "corr", + "cos", + "cosh", + "count", + "covar_pop", + "covar_samp", + "cume_dist", + "dense_rank", + "deref", + "element", + "exp", + "extract", + "first_value", + "floor", + "json_array", + "json_arrayagg", + "json_exists", + "json_object", + "json_objectagg", + "json_query", + "json_table", + "json_table_primitive", + "json_value", + "lag", + "last_value", + "lead", + "listagg", + "ln", + "log", + "log10", + "lower", + "max", + "min", + "mod", + "nth_value", + "ntile", + "nullif", + "percent_rank", + "percentile_cont", + "percentile_disc", + "position", + "position_regex", + "power", + "rank", + "regr_avgx", + "regr_avgy", + "regr_count", + "regr_intercept", + "regr_r2", + "regr_slope", + "regr_sxx", + "regr_sxy", + "regr_syy", + "row_number", + "sin", + "sinh", + "sqrt", + "stddev_pop", + "stddev_samp", + "substring", + "substring_regex", + "sum", + "tan", + "tanh", + "translate", + "translate_regex", + "treat", + "trim", + "trim_array", + "unnest", + "upper", + "value_of", + "var_pop", + "var_samp", + "width_bucket", + ]; + + // these functions can + const POSSIBLE_WITHOUT_PARENS = [ + "current_catalog", + "current_date", + "current_default_transform_group", + "current_path", + "current_role", + "current_schema", + "current_transform_group_for_type", + "current_user", + "session_user", + "system_time", + "system_user", + "current_time", + "localtime", + "current_timestamp", + "localtimestamp" + ]; + + // those exist to boost relevance making these very + // "SQL like" keyword combos worth +1 extra relevance + const COMBOS = [ + "create table", + "insert into", + "primary key", + "foreign key", + "not null", + "alter table", + "add constraint", + "grouping sets", + "on overflow", + "character set", + "respect nulls", + "ignore nulls", + "nulls first", + "nulls last", + "depth first", + "breadth first" + ]; + + const FUNCTIONS = RESERVED_FUNCTIONS; + + const KEYWORDS = [ + ...RESERVED_WORDS, + ...NON_RESERVED_WORDS + ].filter((keyword) => { + return !RESERVED_FUNCTIONS.includes(keyword); + }); + + const VARIABLE = { + scope: "variable", + match: /@[a-z0-9][a-z0-9_]*/, + }; + + const OPERATOR = { + scope: "operator", + match: /[-+*/=%^~]|&&?|\|\|?|!=?|<(?:=>?|<|>)?|>[>=]?/, + relevance: 0, + }; + + const FUNCTION_CALL = { + match: regex.concat(/\b/, regex.either(...FUNCTIONS), /\s*\(/), + relevance: 0, + keywords: { built_in: FUNCTIONS } + }; + + // turns a multi-word keyword combo into a regex that doesn't + // care about extra whitespace etc. + // input: "START QUERY" + // output: /\bSTART\s+QUERY\b/ + function kws_to_regex(list) { + return regex.concat( + /\b/, + regex.either(...list.map((kw) => { + return kw.replace(/\s+/, "\\s+") + })), + /\b/ + ) + } + + const MULTI_WORD_KEYWORDS = { + scope: "keyword", + match: kws_to_regex(COMBOS), + relevance: 0, + }; + + // keywords with less than 3 letters are reduced in relevancy + function reduceRelevancy(list, { + exceptions, when + } = {}) { + const qualifyFn = when; + exceptions = exceptions || []; + return list.map((item) => { + if (item.match(/\|\d+$/) || exceptions.includes(item)) { + return item; + } else if (qualifyFn(item)) { + return `${item}|0`; + } else { + return item; + } + }); + } + + return { + name: 'SQL', + case_insensitive: true, + // does not include {} or HTML tags ` x.length < 3 }), + literal: LITERALS, + type: TYPES, + built_in: POSSIBLE_WITHOUT_PARENS + }, + contains: [ + { + scope: "type", + match: kws_to_regex(MULTI_WORD_TYPES) + }, + MULTI_WORD_KEYWORDS, + FUNCTION_CALL, + VARIABLE, + STRING, + QUOTED_IDENTIFIER, + hljs.C_NUMBER_MODE, + hljs.C_BLOCK_COMMENT_MODE, + COMMENT_MODE, + OPERATOR + ] + }; +} + +export { sql as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/sql.js.js b/frontend/node_modules/highlight.js/es/languages/sql.js.js new file mode 100644 index 0000000..4ca6964 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/sql.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/sql" instead of "highlight.js/lib/languages/sql.js"' + ); + } + } + emitWarning(); + import lang from './sql.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/stan.js b/frontend/node_modules/highlight.js/es/languages/stan.js new file mode 100644 index 0000000..e04d411 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/stan.js @@ -0,0 +1,521 @@ +/* +Language: Stan +Description: The Stan probabilistic programming language +Author: Sean Pinkney +Website: http://mc-stan.org/ +Category: scientific +*/ + +function stan(hljs) { + const regex = hljs.regex; + // variable names cannot conflict with block identifiers + const BLOCKS = [ + 'functions', + 'model', + 'data', + 'parameters', + 'quantities', + 'transformed', + 'generated' + ]; + + const STATEMENTS = [ + 'for', + 'in', + 'if', + 'else', + 'while', + 'break', + 'continue', + 'return' + ]; + + const TYPES = [ + 'array', + 'tuple', + 'complex', + 'int', + 'real', + 'vector', + 'complex_vector', + 'ordered', + 'positive_ordered', + 'simplex', + 'unit_vector', + 'row_vector', + 'complex_row_vector', + 'matrix', + 'complex_matrix', + 'cholesky_factor_corr|10', + 'cholesky_factor_cov|10', + 'corr_matrix|10', + 'cov_matrix|10', + 'void' + ]; + + // to get the functions list + // clone the [stan-docs repo](https://github.com/stan-dev/docs) + // then cd into it and run this bash script https://gist.github.com/joshgoebel/dcd33f82d4059a907c986049893843cf + // + // the output files are + // distributions_quoted.txt + // functions_quoted.txt + + const FUNCTIONS = [ + 'abs', + 'acos', + 'acosh', + 'add_diag', + 'algebra_solver', + 'algebra_solver_newton', + 'append_array', + 'append_col', + 'append_row', + 'asin', + 'asinh', + 'atan', + 'atan2', + 'atanh', + 'bessel_first_kind', + 'bessel_second_kind', + 'binary_log_loss', + 'block', + 'cbrt', + 'ceil', + 'chol2inv', + 'cholesky_decompose', + 'choose', + 'col', + 'cols', + 'columns_dot_product', + 'columns_dot_self', + 'complex_schur_decompose', + 'complex_schur_decompose_t', + 'complex_schur_decompose_u', + 'conj', + 'cos', + 'cosh', + 'cov_exp_quad', + 'crossprod', + 'csr_extract', + 'csr_extract_u', + 'csr_extract_v', + 'csr_extract_w', + 'csr_matrix_times_vector', + 'csr_to_dense_matrix', + 'cumulative_sum', + 'dae', + 'dae_tol', + 'determinant', + 'diag_matrix', + 'diagonal', + 'diag_post_multiply', + 'diag_pre_multiply', + 'digamma', + 'dims', + 'distance', + 'dot_product', + 'dot_self', + 'eigendecompose', + 'eigendecompose_sym', + 'eigenvalues', + 'eigenvalues_sym', + 'eigenvectors', + 'eigenvectors_sym', + 'erf', + 'erfc', + 'exp', + 'exp2', + 'expm1', + 'falling_factorial', + 'fdim', + 'fft', + 'fft2', + 'floor', + 'fma', + 'fmax', + 'fmin', + 'fmod', + 'gamma_p', + 'gamma_q', + 'generalized_inverse', + 'get_imag', + 'get_real', + 'head', + 'hmm_hidden_state_prob', + 'hmm_marginal', + 'hypot', + 'identity_matrix', + 'inc_beta', + 'integrate_1d', + 'integrate_ode', + 'integrate_ode_adams', + 'integrate_ode_bdf', + 'integrate_ode_rk45', + 'int_step', + 'inv', + 'inv_cloglog', + 'inv_erfc', + 'inverse', + 'inverse_spd', + 'inv_fft', + 'inv_fft2', + 'inv_inc_beta', + 'inv_logit', + 'inv_Phi', + 'inv_sqrt', + 'inv_square', + 'is_inf', + 'is_nan', + 'lambert_w0', + 'lambert_wm1', + 'lbeta', + 'lchoose', + 'ldexp', + 'lgamma', + 'linspaced_array', + 'linspaced_int_array', + 'linspaced_row_vector', + 'linspaced_vector', + 'lmgamma', + 'lmultiply', + 'log', + 'log1m', + 'log1m_exp', + 'log1m_inv_logit', + 'log1p', + 'log1p_exp', + 'log_determinant', + 'log_diff_exp', + 'log_falling_factorial', + 'log_inv_logit', + 'log_inv_logit_diff', + 'logit', + 'log_mix', + 'log_modified_bessel_first_kind', + 'log_rising_factorial', + 'log_softmax', + 'log_sum_exp', + 'machine_precision', + 'map_rect', + 'matrix_exp', + 'matrix_exp_multiply', + 'matrix_power', + 'max', + 'mdivide_left_spd', + 'mdivide_left_tri_low', + 'mdivide_right_spd', + 'mdivide_right_tri_low', + 'mean', + 'min', + 'modified_bessel_first_kind', + 'modified_bessel_second_kind', + 'multiply_lower_tri_self_transpose', + 'negative_infinity', + 'norm', + 'norm1', + 'norm2', + 'not_a_number', + 'num_elements', + 'ode_adams', + 'ode_adams_tol', + 'ode_adjoint_tol_ctl', + 'ode_bdf', + 'ode_bdf_tol', + 'ode_ckrk', + 'ode_ckrk_tol', + 'ode_rk45', + 'ode_rk45_tol', + 'one_hot_array', + 'one_hot_int_array', + 'one_hot_row_vector', + 'one_hot_vector', + 'ones_array', + 'ones_int_array', + 'ones_row_vector', + 'ones_vector', + 'owens_t', + 'Phi', + 'Phi_approx', + 'polar', + 'positive_infinity', + 'pow', + 'print', + 'prod', + 'proj', + 'qr', + 'qr_Q', + 'qr_R', + 'qr_thin', + 'qr_thin_Q', + 'qr_thin_R', + 'quad_form', + 'quad_form_diag', + 'quad_form_sym', + 'quantile', + 'rank', + 'reduce_sum', + 'reject', + 'rep_array', + 'rep_matrix', + 'rep_row_vector', + 'rep_vector', + 'reverse', + 'rising_factorial', + 'round', + 'row', + 'rows', + 'rows_dot_product', + 'rows_dot_self', + 'scale_matrix_exp_multiply', + 'sd', + 'segment', + 'sin', + 'singular_values', + 'sinh', + 'size', + 'softmax', + 'sort_asc', + 'sort_desc', + 'sort_indices_asc', + 'sort_indices_desc', + 'sqrt', + 'square', + 'squared_distance', + 'step', + 'sub_col', + 'sub_row', + 'sum', + 'svd', + 'svd_U', + 'svd_V', + 'symmetrize_from_lower_tri', + 'tail', + 'tan', + 'tanh', + 'target', + 'tcrossprod', + 'tgamma', + 'to_array_1d', + 'to_array_2d', + 'to_complex', + 'to_int', + 'to_matrix', + 'to_row_vector', + 'to_vector', + 'trace', + 'trace_gen_quad_form', + 'trace_quad_form', + 'trigamma', + 'trunc', + 'uniform_simplex', + 'variance', + 'zeros_array', + 'zeros_int_array', + 'zeros_row_vector' + ]; + + const DISTRIBUTIONS = [ + 'bernoulli', + 'bernoulli_logit', + 'bernoulli_logit_glm', + 'beta', + 'beta_binomial', + 'beta_proportion', + 'binomial', + 'binomial_logit', + 'categorical', + 'categorical_logit', + 'categorical_logit_glm', + 'cauchy', + 'chi_square', + 'dirichlet', + 'discrete_range', + 'double_exponential', + 'exp_mod_normal', + 'exponential', + 'frechet', + 'gamma', + 'gaussian_dlm_obs', + 'gumbel', + 'hmm_latent', + 'hypergeometric', + 'inv_chi_square', + 'inv_gamma', + 'inv_wishart', + 'inv_wishart_cholesky', + 'lkj_corr', + 'lkj_corr_cholesky', + 'logistic', + 'loglogistic', + 'lognormal', + 'multi_gp', + 'multi_gp_cholesky', + 'multinomial', + 'multinomial_logit', + 'multi_normal', + 'multi_normal_cholesky', + 'multi_normal_prec', + 'multi_student_cholesky_t', + 'multi_student_t', + 'multi_student_t_cholesky', + 'neg_binomial', + 'neg_binomial_2', + 'neg_binomial_2_log', + 'neg_binomial_2_log_glm', + 'normal', + 'normal_id_glm', + 'ordered_logistic', + 'ordered_logistic_glm', + 'ordered_probit', + 'pareto', + 'pareto_type_2', + 'poisson', + 'poisson_log', + 'poisson_log_glm', + 'rayleigh', + 'scaled_inv_chi_square', + 'skew_double_exponential', + 'skew_normal', + 'std_normal', + 'std_normal_log', + 'student_t', + 'uniform', + 'von_mises', + 'weibull', + 'wiener', + 'wishart', + 'wishart_cholesky' + ]; + + const BLOCK_COMMENT = hljs.COMMENT( + /\/\*/, + /\*\//, + { + relevance: 0, + contains: [ + { + scope: 'doctag', + match: /@(return|param)/ + } + ] + } + ); + + const INCLUDE = { + scope: 'meta', + begin: /#include\b/, + end: /$/, + contains: [ + { + match: /[a-z][a-z-._]+/, + scope: 'string' + }, + hljs.C_LINE_COMMENT_MODE + ] + }; + + const RANGE_CONSTRAINTS = [ + "lower", + "upper", + "offset", + "multiplier" + ]; + + return { + name: 'Stan', + aliases: [ 'stanfuncs' ], + keywords: { + $pattern: hljs.IDENT_RE, + title: BLOCKS, + type: TYPES, + keyword: STATEMENTS, + built_in: FUNCTIONS + }, + contains: [ + hljs.C_LINE_COMMENT_MODE, + INCLUDE, + hljs.HASH_COMMENT_MODE, + BLOCK_COMMENT, + { + scope: 'built_in', + match: /\s(pi|e|sqrt2|log2|log10)(?=\()/, + relevance: 0 + }, + { + match: regex.concat(/[<,]\s*/, regex.either(...RANGE_CONSTRAINTS), /\s*=/), + keywords: RANGE_CONSTRAINTS + }, + { + scope: 'keyword', + match: /\btarget(?=\s*\+=)/, + }, + { + // highlights the 'T' in T[,] for only Stan language distributrions + match: [ + /~\s*/, + regex.either(...DISTRIBUTIONS), + /(?:\(\))/, + /\s*T(?=\s*\[)/ + ], + scope: { + 2: "built_in", + 4: "keyword" + } + }, + { + // highlights distributions that end with special endings + scope: 'built_in', + keywords: DISTRIBUTIONS, + begin: regex.concat(/\w*/, regex.either(...DISTRIBUTIONS), /(_lpdf|_lupdf|_lpmf|_cdf|_lcdf|_lccdf|_qf)(?=\s*[\(.*\)])/) + }, + { + // highlights distributions after ~ + begin: [ + /~/, + /\s*/, + regex.concat(regex.either(...DISTRIBUTIONS), /(?=\s*[\(.*\)])/) + ], + scope: { 3: "built_in" } + }, + { + // highlights user defined distributions after ~ + begin: [ + /~/, + /\s*\w+(?=\s*[\(.*\)])/, + '(?!.*/\b(' + regex.either(...DISTRIBUTIONS) + ')\b)' + ], + scope: { 2: "title.function" } + }, + { + // highlights user defined distributions with special endings + scope: 'title.function', + begin: /\w*(_lpdf|_lupdf|_lpmf|_cdf|_lcdf|_lccdf|_qf)(?=\s*[\(.*\)])/ + }, + { + scope: 'number', + match: regex.concat( + // Comes from @RunDevelopment accessed 11/29/2021 at + // https://github.com/PrismJS/prism/blob/c53ad2e65b7193ab4f03a1797506a54bbb33d5a2/components/prism-stan.js#L56 + + // start of big noncapture group which + // 1. gets numbers that are by themselves + // 2. numbers that are separated by _ + // 3. numbers that are separted by . + /(?:\b\d+(?:_\d+)*(?:\.(?:\d+(?:_\d+)*)?)?|\B\.\d+(?:_\d+)*)/, + // grabs scientific notation + // grabs complex numbers with i + /(?:[eE][+-]?\d+(?:_\d+)*)?i?(?!\w)/ + ), + relevance: 0 + }, + { + scope: 'string', + begin: /"/, + end: /"/ + } + ] + }; +} + +export { stan as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/stan.js.js b/frontend/node_modules/highlight.js/es/languages/stan.js.js new file mode 100644 index 0000000..eba6eca --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/stan.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/stan" instead of "highlight.js/lib/languages/stan.js"' + ); + } + } + emitWarning(); + import lang from './stan.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/stata.js b/frontend/node_modules/highlight.js/es/languages/stata.js new file mode 100644 index 0000000..1bf06b3 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/stata.js @@ -0,0 +1,53 @@ +/* +Language: Stata +Author: Brian Quistorff +Contributors: Drew McDonald +Description: Stata is a general-purpose statistical software package created in 1985 by StataCorp. +Website: https://en.wikipedia.org/wiki/Stata +Category: scientific +*/ + +/* + This is a fork and modification of Drew McDonald's file (https://github.com/drewmcdonald/stata-highlighting). I have also included a list of builtin commands from https://bugs.kde.org/show_bug.cgi?id=135646. +*/ + +function stata(hljs) { + return { + name: 'Stata', + aliases: [ + 'do', + 'ado' + ], + case_insensitive: true, + keywords: 'if else in foreach for forv forva forval forvalu forvalue forvalues by bys bysort xi quietly qui capture about ac ac_7 acprplot acprplot_7 adjust ado adopath adoupdate alpha ameans an ano anov anova anova_estat anova_terms anovadef aorder ap app appe appen append arch arch_dr arch_estat arch_p archlm areg areg_p args arima arima_dr arima_estat arima_p as asmprobit asmprobit_estat asmprobit_lf asmprobit_mfx__dlg asmprobit_p ass asse asser assert avplot avplot_7 avplots avplots_7 bcskew0 bgodfrey bias binreg bip0_lf biplot bipp_lf bipr_lf bipr_p biprobit bitest bitesti bitowt blogit bmemsize boot bootsamp bootstrap bootstrap_8 boxco_l boxco_p boxcox boxcox_6 boxcox_p bprobit br break brier bro brow brows browse brr brrstat bs bs_7 bsampl_w bsample bsample_7 bsqreg bstat bstat_7 bstat_8 bstrap bstrap_7 bubble bubbleplot ca ca_estat ca_p cabiplot camat canon canon_8 canon_8_p canon_estat canon_p cap caprojection capt captu captur capture cat cc cchart cchart_7 cci cd censobs_table centile cf char chdir checkdlgfiles checkestimationsample checkhlpfiles checksum chelp ci cii cl class classutil clear cli clis clist clo clog clog_lf clog_p clogi clogi_sw clogit clogit_lf clogit_p clogitp clogl_sw cloglog clonevar clslistarray cluster cluster_measures cluster_stop cluster_tree cluster_tree_8 clustermat cmdlog cnr cnre cnreg cnreg_p cnreg_sw cnsreg codebook collaps4 collapse colormult_nb colormult_nw compare compress conf confi confir confirm conren cons const constr constra constrai constrain constraint continue contract copy copyright copysource cor corc corr corr2data corr_anti corr_kmo corr_smc corre correl correla correlat correlate corrgram cou coun count cox cox_p cox_sw coxbase coxhaz coxvar cprplot cprplot_7 crc cret cretu cretur creturn cross cs cscript cscript_log csi ct ct_is ctset ctst_5 ctst_st cttost cumsp cumsp_7 cumul cusum cusum_7 cutil d|0 datasig datasign datasigna datasignat datasignatu datasignatur datasignature datetof db dbeta de dec deco decod decode deff des desc descr descri describ describe destring dfbeta dfgls dfuller di di_g dir dirstats dis discard disp disp_res disp_s displ displa display distinct do doe doed doedi doedit dotplot dotplot_7 dprobit drawnorm drop ds ds_util dstdize duplicates durbina dwstat dydx e|0 ed edi edit egen eivreg emdef en enc enco encod encode eq erase ereg ereg_lf ereg_p ereg_sw ereghet ereghet_glf ereghet_glf_sh ereghet_gp ereghet_ilf ereghet_ilf_sh ereghet_ip eret eretu eretur ereturn err erro error esize est est_cfexist est_cfname est_clickable est_expand est_hold est_table est_unhold est_unholdok estat estat_default estat_summ estat_vce_only esti estimates etodow etof etomdy ex exi exit expand expandcl fac fact facto factor factor_estat factor_p factor_pca_rotated factor_rotate factormat fcast fcast_compute fcast_graph fdades fdadesc fdadescr fdadescri fdadescrib fdadescribe fdasav fdasave fdause fh_st file open file read file close file filefilter fillin find_hlp_file findfile findit findit_7 fit fl fli flis flist for5_0 forest forestplot form forma format fpredict frac_154 frac_adj frac_chk frac_cox frac_ddp frac_dis frac_dv frac_in frac_mun frac_pp frac_pq frac_pv frac_wgt frac_xo fracgen fracplot fracplot_7 fracpoly fracpred fron_ex fron_hn fron_p fron_tn fron_tn2 frontier ftodate ftoe ftomdy ftowdate funnel funnelplot g|0 gamhet_glf gamhet_gp gamhet_ilf gamhet_ip gamma gamma_d2 gamma_p gamma_sw gammahet gdi_hexagon gdi_spokes ge gen gene gener genera generat generate genrank genstd genvmean gettoken gl gladder gladder_7 glim_l01 glim_l02 glim_l03 glim_l04 glim_l05 glim_l06 glim_l07 glim_l08 glim_l09 glim_l10 glim_l11 glim_l12 glim_lf glim_mu glim_nw1 glim_nw2 glim_nw3 glim_p glim_v1 glim_v2 glim_v3 glim_v4 glim_v5 glim_v6 glim_v7 glm glm_6 glm_p glm_sw glmpred glo glob globa global glogit glogit_8 glogit_p gmeans gnbre_lf gnbreg gnbreg_5 gnbreg_p gomp_lf gompe_sw gomper_p gompertz gompertzhet gomphet_glf gomphet_glf_sh gomphet_gp gomphet_ilf gomphet_ilf_sh gomphet_ip gphdot gphpen gphprint gprefs gprobi_p gprobit gprobit_8 gr gr7 gr_copy gr_current gr_db gr_describe gr_dir gr_draw gr_draw_replay gr_drop gr_edit gr_editviewopts gr_example gr_example2 gr_export gr_print gr_qscheme gr_query gr_read gr_rename gr_replay gr_save gr_set gr_setscheme gr_table gr_undo gr_use graph graph7 grebar greigen greigen_7 greigen_8 grmeanby grmeanby_7 gs_fileinfo gs_filetype gs_graphinfo gs_stat gsort gwood h|0 hadimvo hareg hausman haver he heck_d2 heckma_p heckman heckp_lf heckpr_p heckprob hel help hereg hetpr_lf hetpr_p hetprob hettest hexdump hilite hist hist_7 histogram hlogit hlu hmeans hotel hotelling hprobit hreg hsearch icd9 icd9_ff icd9p iis impute imtest inbase include inf infi infil infile infix inp inpu input ins insheet insp inspe inspec inspect integ inten intreg intreg_7 intreg_p intrg2_ll intrg_ll intrg_ll2 ipolate iqreg ir irf irf_create irfm iri is_svy is_svysum isid istdize ivprob_1_lf ivprob_lf ivprobit ivprobit_p ivreg ivreg_footnote ivtob_1_lf ivtob_lf ivtobit ivtobit_p jackknife jacknife jknife jknife_6 jknife_8 jkstat joinby kalarma1 kap kap_3 kapmeier kappa kapwgt kdensity kdensity_7 keep ksm ksmirnov ktau kwallis l|0 la lab labbe labbeplot labe label labelbook ladder levels levelsof leverage lfit lfit_p li lincom line linktest lis list lloghet_glf lloghet_glf_sh lloghet_gp lloghet_ilf lloghet_ilf_sh lloghet_ip llogi_sw llogis_p llogist llogistic llogistichet lnorm_lf lnorm_sw lnorma_p lnormal lnormalhet lnormhet_glf lnormhet_glf_sh lnormhet_gp lnormhet_ilf lnormhet_ilf_sh lnormhet_ip lnskew0 loadingplot loc loca local log logi logis_lf logistic logistic_p logit logit_estat logit_p loglogs logrank loneway lookfor lookup lowess lowess_7 lpredict lrecomp lroc lroc_7 lrtest ls lsens lsens_7 lsens_x lstat ltable ltable_7 ltriang lv lvr2plot lvr2plot_7 m|0 ma mac macr macro makecns man manova manova_estat manova_p manovatest mantel mark markin markout marksample mat mat_capp mat_order mat_put_rr mat_rapp mata mata_clear mata_describe mata_drop mata_matdescribe mata_matsave mata_matuse mata_memory mata_mlib mata_mosave mata_rename mata_which matalabel matcproc matlist matname matr matri matrix matrix_input__dlg matstrik mcc mcci md0_ md1_ md1debug_ md2_ md2debug_ mds mds_estat mds_p mdsconfig mdslong mdsmat mdsshepard mdytoe mdytof me_derd mean means median memory memsize menl meqparse mer merg merge meta mfp mfx mhelp mhodds minbound mixed_ll mixed_ll_reparm mkassert mkdir mkmat mkspline ml ml_5 ml_adjs ml_bhhhs ml_c_d ml_check ml_clear ml_cnt ml_debug ml_defd ml_e0 ml_e0_bfgs ml_e0_cycle ml_e0_dfp ml_e0i ml_e1 ml_e1_bfgs ml_e1_bhhh ml_e1_cycle ml_e1_dfp ml_e2 ml_e2_cycle ml_ebfg0 ml_ebfr0 ml_ebfr1 ml_ebh0q ml_ebhh0 ml_ebhr0 ml_ebr0i ml_ecr0i ml_edfp0 ml_edfr0 ml_edfr1 ml_edr0i ml_eds ml_eer0i ml_egr0i ml_elf ml_elf_bfgs ml_elf_bhhh ml_elf_cycle ml_elf_dfp ml_elfi ml_elfs ml_enr0i ml_enrr0 ml_erdu0 ml_erdu0_bfgs ml_erdu0_bhhh ml_erdu0_bhhhq ml_erdu0_cycle ml_erdu0_dfp ml_erdu0_nrbfgs ml_exde ml_footnote ml_geqnr ml_grad0 ml_graph ml_hbhhh ml_hd0 ml_hold ml_init ml_inv ml_log ml_max ml_mlout ml_mlout_8 ml_model ml_nb0 ml_opt ml_p ml_plot ml_query ml_rdgrd ml_repor ml_s_e ml_score ml_searc ml_technique ml_unhold mleval mlf_ mlmatbysum mlmatsum mlog mlogi mlogit mlogit_footnote mlogit_p mlopts mlsum mlvecsum mnl0_ mor more mov move mprobit mprobit_lf mprobit_p mrdu0_ mrdu1_ mvdecode mvencode mvreg mvreg_estat n|0 nbreg nbreg_al nbreg_lf nbreg_p nbreg_sw nestreg net newey newey_7 newey_p news nl nl_7 nl_9 nl_9_p nl_p nl_p_7 nlcom nlcom_p nlexp2 nlexp2_7 nlexp2a nlexp2a_7 nlexp3 nlexp3_7 nlgom3 nlgom3_7 nlgom4 nlgom4_7 nlinit nllog3 nllog3_7 nllog4 nllog4_7 nlog_rd nlogit nlogit_p nlogitgen nlogittree nlpred no nobreak noi nois noisi noisil noisily note notes notes_dlg nptrend numlabel numlist odbc old_ver olo olog ologi ologi_sw ologit ologit_p ologitp on one onew onewa oneway op_colnm op_comp op_diff op_inv op_str opr opro oprob oprob_sw oprobi oprobi_p oprobit oprobitp opts_exclusive order orthog orthpoly ou out outf outfi outfil outfile outs outsh outshe outshee outsheet ovtest pac pac_7 palette parse parse_dissim pause pca pca_8 pca_display pca_estat pca_p pca_rotate pcamat pchart pchart_7 pchi pchi_7 pcorr pctile pentium pergram pergram_7 permute permute_8 personal peto_st pkcollapse pkcross pkequiv pkexamine pkexamine_7 pkshape pksumm pksumm_7 pl plo plot plugin pnorm pnorm_7 poisgof poiss_lf poiss_sw poisso_p poisson poisson_estat post postclose postfile postutil pperron pr prais prais_e prais_e2 prais_p predict predictnl preserve print pro prob probi probit probit_estat probit_p proc_time procoverlay procrustes procrustes_estat procrustes_p profiler prog progr progra program prop proportion prtest prtesti pwcorr pwd q\\s qby qbys qchi qchi_7 qladder qladder_7 qnorm qnorm_7 qqplot qqplot_7 qreg qreg_c qreg_p qreg_sw qu quadchk quantile quantile_7 que quer query range ranksum ratio rchart rchart_7 rcof recast reclink recode reg reg3 reg3_p regdw regr regre regre_p2 regres regres_p regress regress_estat regriv_p remap ren rena renam rename renpfix repeat replace report reshape restore ret retu retur return rm rmdir robvar roccomp roccomp_7 roccomp_8 rocf_lf rocfit rocfit_8 rocgold rocplot rocplot_7 roctab roctab_7 rolling rologit rologit_p rot rota rotat rotate rotatemat rreg rreg_p ru run runtest rvfplot rvfplot_7 rvpplot rvpplot_7 sa safesum sample sampsi sav save savedresults saveold sc sca scal scala scalar scatter scm_mine sco scob_lf scob_p scobi_sw scobit scor score scoreplot scoreplot_help scree screeplot screeplot_help sdtest sdtesti se search separate seperate serrbar serrbar_7 serset set set_defaults sfrancia sh she shel shell shewhart shewhart_7 signestimationsample signrank signtest simul simul_7 simulate simulate_8 sktest sleep slogit slogit_d2 slogit_p smooth snapspan so sor sort spearman spikeplot spikeplot_7 spikeplt spline_x split sqreg sqreg_p sret sretu sretur sreturn ssc st st_ct st_hc st_hcd st_hcd_sh st_is st_issys st_note st_promo st_set st_show st_smpl st_subid stack statsby statsby_8 stbase stci stci_7 stcox stcox_estat stcox_fr stcox_fr_ll stcox_p stcox_sw stcoxkm stcoxkm_7 stcstat stcurv stcurve stcurve_7 stdes stem stepwise stereg stfill stgen stir stjoin stmc stmh stphplot stphplot_7 stphtest stphtest_7 stptime strate strate_7 streg streg_sw streset sts sts_7 stset stsplit stsum sttocc sttoct stvary stweib su suest suest_8 sum summ summa summar summari summariz summarize sunflower sureg survcurv survsum svar svar_p svmat svy svy_disp svy_dreg svy_est svy_est_7 svy_estat svy_get svy_gnbreg_p svy_head svy_header svy_heckman_p svy_heckprob_p svy_intreg_p svy_ivreg_p svy_logistic_p svy_logit_p svy_mlogit_p svy_nbreg_p svy_ologit_p svy_oprobit_p svy_poisson_p svy_probit_p svy_regress_p svy_sub svy_sub_7 svy_x svy_x_7 svy_x_p svydes svydes_8 svygen svygnbreg svyheckman svyheckprob svyintreg svyintreg_7 svyintrg svyivreg svylc svylog_p svylogit svymarkout svymarkout_8 svymean svymlog svymlogit svynbreg svyolog svyologit svyoprob svyoprobit svyopts svypois svypois_7 svypoisson svyprobit svyprobt svyprop svyprop_7 svyratio svyreg svyreg_p svyregress svyset svyset_7 svyset_8 svytab svytab_7 svytest svytotal sw sw_8 swcnreg swcox swereg swilk swlogis swlogit swologit swoprbt swpois swprobit swqreg swtobit swweib symmetry symmi symplot symplot_7 syntax sysdescribe sysdir sysuse szroeter ta tab tab1 tab2 tab_or tabd tabdi tabdis tabdisp tabi table tabodds tabodds_7 tabstat tabu tabul tabula tabulat tabulate te tempfile tempname tempvar tes test testnl testparm teststd tetrachoric time_it timer tis tob tobi tobit tobit_p tobit_sw token tokeni tokeniz tokenize tostring total translate translator transmap treat_ll treatr_p treatreg trim trimfill trnb_cons trnb_mean trpoiss_d2 trunc_ll truncr_p truncreg tsappend tset tsfill tsline tsline_ex tsreport tsrevar tsrline tsset tssmooth tsunab ttest ttesti tut_chk tut_wait tutorial tw tware_st two twoway twoway__fpfit_serset twoway__function_gen twoway__histogram_gen twoway__ipoint_serset twoway__ipoints_serset twoway__kdensity_gen twoway__lfit_serset twoway__normgen_gen twoway__pci_serset twoway__qfit_serset twoway__scatteri_serset twoway__sunflower_gen twoway_ksm_serset ty typ type typeof u|0 unab unabbrev unabcmd update us use uselabel var var_mkcompanion var_p varbasic varfcast vargranger varirf varirf_add varirf_cgraph varirf_create varirf_ctable varirf_describe varirf_dir varirf_drop varirf_erase varirf_graph varirf_ograph varirf_rename varirf_set varirf_table varlist varlmar varnorm varsoc varstable varstable_w varstable_w2 varwle vce vec vec_fevd vec_mkphi vec_p vec_p_w vecirf_create veclmar veclmar_w vecnorm vecnorm_w vecrank vecstable verinst vers versi versio version view viewsource vif vwls wdatetof webdescribe webseek webuse weib1_lf weib2_lf weib_lf weib_lf0 weibhet_glf weibhet_glf_sh weibhet_glfa weibhet_glfa_sh weibhet_gp weibhet_ilf weibhet_ilf_sh weibhet_ilfa weibhet_ilfa_sh weibhet_ip weibu_sw weibul_p weibull weibull_c weibull_s weibullhet wh whelp whi which whil while wilc_st wilcoxon win wind windo window winexec wntestb wntestb_7 wntestq xchart xchart_7 xcorr xcorr_7 xi xi_6 xmlsav xmlsave xmluse xpose xsh xshe xshel xshell xt_iis xt_tis xtab_p xtabond xtbin_p xtclog xtcloglog xtcloglog_8 xtcloglog_d2 xtcloglog_pa_p xtcloglog_re_p xtcnt_p xtcorr xtdata xtdes xtfront_p xtfrontier xtgee xtgee_elink xtgee_estat xtgee_makeivar xtgee_p xtgee_plink xtgls xtgls_p xthaus xthausman xtht_p xthtaylor xtile xtint_p xtintreg xtintreg_8 xtintreg_d2 xtintreg_p xtivp_1 xtivp_2 xtivreg xtline xtline_ex xtlogit xtlogit_8 xtlogit_d2 xtlogit_fe_p xtlogit_pa_p xtlogit_re_p xtmixed xtmixed_estat xtmixed_p xtnb_fe xtnb_lf xtnbreg xtnbreg_pa_p xtnbreg_refe_p xtpcse xtpcse_p xtpois xtpoisson xtpoisson_d2 xtpoisson_pa_p xtpoisson_refe_p xtpred xtprobit xtprobit_8 xtprobit_d2 xtprobit_re_p xtps_fe xtps_lf xtps_ren xtps_ren_8 xtrar_p xtrc xtrc_p xtrchh xtrefe_p xtreg xtreg_be xtreg_fe xtreg_ml xtreg_pa_p xtreg_re xtregar xtrere_p xtset xtsf_ll xtsf_llti xtsum xttab xttest0 xttobit xttobit_8 xttobit_p xttrans yx yxview__barlike_draw yxview_area_draw yxview_bar_draw yxview_dot_draw yxview_dropline_draw yxview_function_draw yxview_iarrow_draw yxview_ilabels_draw yxview_normal_draw yxview_pcarrow_draw yxview_pcbarrow_draw yxview_pccapsym_draw yxview_pcscatter_draw yxview_pcspike_draw yxview_rarea_draw yxview_rbar_draw yxview_rbarm_draw yxview_rcap_draw yxview_rcapsym_draw yxview_rconnected_draw yxview_rline_draw yxview_rscatter_draw yxview_rspike_draw yxview_spike_draw yxview_sunflower_draw zap_s zinb zinb_llf zinb_plf zip zip_llf zip_p zip_plf zt_ct_5 zt_hc_5 zt_hcd_5 zt_is_5 zt_iss_5 zt_sho_5 zt_smp_5 ztbase_5 ztcox_5 ztdes_5 ztereg_5 ztfill_5 ztgen_5 ztir_5 ztjoin_5 ztnb ztnb_p ztp ztp_p zts_5 ztset_5 ztspli_5 ztsum_5 zttoct_5 ztvary_5 ztweib_5', + contains: [ + { + className: 'symbol', + begin: /`[a-zA-Z0-9_]+'/ + }, + { + className: 'variable', + begin: /\$\{?[a-zA-Z0-9_]+\}?/, + relevance: 0 + }, + { + className: 'string', + variants: [ + { begin: '`"[^\r\n]*?"\'' }, + { begin: '"[^\r\n"]*"' } + ] + }, + + { + className: 'built_in', + variants: [ { begin: '\\b(abs|acos|asin|atan|atan2|atanh|ceil|cloglog|comb|cos|digamma|exp|floor|invcloglog|invlogit|ln|lnfact|lnfactorial|lngamma|log|log10|max|min|mod|reldif|round|sign|sin|sqrt|sum|tan|tanh|trigamma|trunc|betaden|Binomial|binorm|binormal|chi2|chi2tail|dgammapda|dgammapdada|dgammapdadx|dgammapdx|dgammapdxdx|F|Fden|Ftail|gammaden|gammap|ibeta|invbinomial|invchi2|invchi2tail|invF|invFtail|invgammap|invibeta|invnchi2|invnFtail|invnibeta|invnorm|invnormal|invttail|nbetaden|nchi2|nFden|nFtail|nibeta|norm|normal|normalden|normd|npnchi2|tden|ttail|uniform|abbrev|char|index|indexnot|length|lower|ltrim|match|plural|proper|real|regexm|regexr|regexs|reverse|rtrim|string|strlen|strlower|strltrim|strmatch|strofreal|strpos|strproper|strreverse|strrtrim|strtrim|strupper|subinstr|subinword|substr|trim|upper|word|wordcount|_caller|autocode|byteorder|chop|clip|cond|e|epsdouble|epsfloat|group|inlist|inrange|irecode|matrix|maxbyte|maxdouble|maxfloat|maxint|maxlong|mi|minbyte|mindouble|minfloat|minint|minlong|missing|r|recode|replay|return|s|scalar|d|date|day|dow|doy|halfyear|mdy|month|quarter|week|year|d|daily|dofd|dofh|dofm|dofq|dofw|dofy|h|halfyearly|hofd|m|mofd|monthly|q|qofd|quarterly|tin|twithin|w|weekly|wofd|y|yearly|yh|ym|yofd|yq|yw|cholesky|colnumb|colsof|corr|det|diag|diag0cnt|el|get|hadamard|I|inv|invsym|issym|issymmetric|J|matmissing|matuniform|mreldif|nullmat|rownumb|rowsof|sweep|syminv|trace|vec|vecdiag)(?=\\()' } ] + }, + + hljs.COMMENT('^[ \t]*\\*.*$', false), + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE + ] + }; +} + +export { stata as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/stata.js.js b/frontend/node_modules/highlight.js/es/languages/stata.js.js new file mode 100644 index 0000000..6feb110 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/stata.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/stata" instead of "highlight.js/lib/languages/stata.js"' + ); + } + } + emitWarning(); + import lang from './stata.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/step21.js b/frontend/node_modules/highlight.js/es/languages/step21.js new file mode 100644 index 0000000..ace2e93 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/step21.js @@ -0,0 +1,67 @@ +/* +Language: STEP Part 21 +Contributors: Adam Joseph Cook +Description: Syntax highlighter for STEP Part 21 files (ISO 10303-21). +Website: https://en.wikipedia.org/wiki/ISO_10303-21 +Category: syntax +*/ + +function step21(hljs) { + const STEP21_IDENT_RE = '[A-Z_][A-Z0-9_.]*'; + const STEP21_KEYWORDS = { + $pattern: STEP21_IDENT_RE, + keyword: [ + "HEADER", + "ENDSEC", + "DATA" + ] + }; + const STEP21_START = { + className: 'meta', + begin: 'ISO-10303-21;', + relevance: 10 + }; + const STEP21_CLOSE = { + className: 'meta', + begin: 'END-ISO-10303-21;', + relevance: 10 + }; + + return { + name: 'STEP Part 21', + aliases: [ + 'p21', + 'step', + 'stp' + ], + case_insensitive: true, // STEP 21 is case insensitive in theory, in practice all non-comments are capitalized. + keywords: STEP21_KEYWORDS, + contains: [ + STEP21_START, + STEP21_CLOSE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + hljs.COMMENT('/\\*\\*!', '\\*/'), + hljs.C_NUMBER_MODE, + hljs.inherit(hljs.APOS_STRING_MODE, { illegal: null }), + hljs.inherit(hljs.QUOTE_STRING_MODE, { illegal: null }), + { + className: 'string', + begin: "'", + end: "'" + }, + { + className: 'symbol', + variants: [ + { + begin: '#', + end: '\\d+', + illegal: '\\W' + } + ] + } + ] + }; +} + +export { step21 as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/step21.js.js b/frontend/node_modules/highlight.js/es/languages/step21.js.js new file mode 100644 index 0000000..c6cd327 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/step21.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/step21" instead of "highlight.js/lib/languages/step21.js"' + ); + } + } + emitWarning(); + import lang from './step21.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/stylus.js b/frontend/node_modules/highlight.js/es/languages/stylus.js new file mode 100644 index 0000000..bd3f799 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/stylus.js @@ -0,0 +1,999 @@ +const MODES = (hljs) => { + return { + IMPORTANT: { + scope: 'meta', + begin: '!important' + }, + BLOCK_COMMENT: hljs.C_BLOCK_COMMENT_MODE, + HEXCOLOR: { + scope: 'number', + begin: /#(([0-9a-fA-F]{3,4})|(([0-9a-fA-F]{2}){3,4}))\b/ + }, + FUNCTION_DISPATCH: { + className: "built_in", + begin: /[\w-]+(?=\()/ + }, + ATTRIBUTE_SELECTOR_MODE: { + scope: 'selector-attr', + begin: /\[/, + end: /\]/, + illegal: '$', + contains: [ + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE + ] + }, + CSS_NUMBER_MODE: { + scope: 'number', + begin: hljs.NUMBER_RE + '(' + + '%|em|ex|ch|rem' + + '|vw|vh|vmin|vmax' + + '|cm|mm|in|pt|pc|px' + + '|deg|grad|rad|turn' + + '|s|ms' + + '|Hz|kHz' + + '|dpi|dpcm|dppx' + + ')?', + relevance: 0 + }, + CSS_VARIABLE: { + className: "attr", + begin: /--[A-Za-z_][A-Za-z0-9_-]*/ + } + }; +}; + +const HTML_TAGS = [ + 'a', + 'abbr', + 'address', + 'article', + 'aside', + 'audio', + 'b', + 'blockquote', + 'body', + 'button', + 'canvas', + 'caption', + 'cite', + 'code', + 'dd', + 'del', + 'details', + 'dfn', + 'div', + 'dl', + 'dt', + 'em', + 'fieldset', + 'figcaption', + 'figure', + 'footer', + 'form', + 'h1', + 'h2', + 'h3', + 'h4', + 'h5', + 'h6', + 'header', + 'hgroup', + 'html', + 'i', + 'iframe', + 'img', + 'input', + 'ins', + 'kbd', + 'label', + 'legend', + 'li', + 'main', + 'mark', + 'menu', + 'nav', + 'object', + 'ol', + 'optgroup', + 'option', + 'p', + 'picture', + 'q', + 'quote', + 'samp', + 'section', + 'select', + 'source', + 'span', + 'strong', + 'summary', + 'sup', + 'table', + 'tbody', + 'td', + 'textarea', + 'tfoot', + 'th', + 'thead', + 'time', + 'tr', + 'ul', + 'var', + 'video' +]; + +const SVG_TAGS = [ + 'defs', + 'g', + 'marker', + 'mask', + 'pattern', + 'svg', + 'switch', + 'symbol', + 'feBlend', + 'feColorMatrix', + 'feComponentTransfer', + 'feComposite', + 'feConvolveMatrix', + 'feDiffuseLighting', + 'feDisplacementMap', + 'feFlood', + 'feGaussianBlur', + 'feImage', + 'feMerge', + 'feMorphology', + 'feOffset', + 'feSpecularLighting', + 'feTile', + 'feTurbulence', + 'linearGradient', + 'radialGradient', + 'stop', + 'circle', + 'ellipse', + 'image', + 'line', + 'path', + 'polygon', + 'polyline', + 'rect', + 'text', + 'use', + 'textPath', + 'tspan', + 'foreignObject', + 'clipPath' +]; + +const TAGS = [ + ...HTML_TAGS, + ...SVG_TAGS, +]; + +// Sorting, then reversing makes sure longer attributes/elements like +// `font-weight` are matched fully instead of getting false positives on say `font` + +const MEDIA_FEATURES = [ + 'any-hover', + 'any-pointer', + 'aspect-ratio', + 'color', + 'color-gamut', + 'color-index', + 'device-aspect-ratio', + 'device-height', + 'device-width', + 'display-mode', + 'forced-colors', + 'grid', + 'height', + 'hover', + 'inverted-colors', + 'monochrome', + 'orientation', + 'overflow-block', + 'overflow-inline', + 'pointer', + 'prefers-color-scheme', + 'prefers-contrast', + 'prefers-reduced-motion', + 'prefers-reduced-transparency', + 'resolution', + 'scan', + 'scripting', + 'update', + 'width', + // TODO: find a better solution? + 'min-width', + 'max-width', + 'min-height', + 'max-height' +].sort().reverse(); + +// https://developer.mozilla.org/en-US/docs/Web/CSS/Pseudo-classes +const PSEUDO_CLASSES = [ + 'active', + 'any-link', + 'blank', + 'checked', + 'current', + 'default', + 'defined', + 'dir', // dir() + 'disabled', + 'drop', + 'empty', + 'enabled', + 'first', + 'first-child', + 'first-of-type', + 'fullscreen', + 'future', + 'focus', + 'focus-visible', + 'focus-within', + 'has', // has() + 'host', // host or host() + 'host-context', // host-context() + 'hover', + 'indeterminate', + 'in-range', + 'invalid', + 'is', // is() + 'lang', // lang() + 'last-child', + 'last-of-type', + 'left', + 'link', + 'local-link', + 'not', // not() + 'nth-child', // nth-child() + 'nth-col', // nth-col() + 'nth-last-child', // nth-last-child() + 'nth-last-col', // nth-last-col() + 'nth-last-of-type', //nth-last-of-type() + 'nth-of-type', //nth-of-type() + 'only-child', + 'only-of-type', + 'optional', + 'out-of-range', + 'past', + 'placeholder-shown', + 'read-only', + 'read-write', + 'required', + 'right', + 'root', + 'scope', + 'target', + 'target-within', + 'user-invalid', + 'valid', + 'visited', + 'where' // where() +].sort().reverse(); + +// https://developer.mozilla.org/en-US/docs/Web/CSS/Pseudo-elements +const PSEUDO_ELEMENTS = [ + 'after', + 'backdrop', + 'before', + 'cue', + 'cue-region', + 'first-letter', + 'first-line', + 'grammar-error', + 'marker', + 'part', + 'placeholder', + 'selection', + 'slotted', + 'spelling-error' +].sort().reverse(); + +const ATTRIBUTES = [ + 'accent-color', + 'align-content', + 'align-items', + 'align-self', + 'alignment-baseline', + 'all', + 'anchor-name', + 'animation', + 'animation-composition', + 'animation-delay', + 'animation-direction', + 'animation-duration', + 'animation-fill-mode', + 'animation-iteration-count', + 'animation-name', + 'animation-play-state', + 'animation-range', + 'animation-range-end', + 'animation-range-start', + 'animation-timeline', + 'animation-timing-function', + 'appearance', + 'aspect-ratio', + 'backdrop-filter', + 'backface-visibility', + 'background', + 'background-attachment', + 'background-blend-mode', + 'background-clip', + 'background-color', + 'background-image', + 'background-origin', + 'background-position', + 'background-position-x', + 'background-position-y', + 'background-repeat', + 'background-size', + 'baseline-shift', + 'block-size', + 'border', + 'border-block', + 'border-block-color', + 'border-block-end', + 'border-block-end-color', + 'border-block-end-style', + 'border-block-end-width', + 'border-block-start', + 'border-block-start-color', + 'border-block-start-style', + 'border-block-start-width', + 'border-block-style', + 'border-block-width', + 'border-bottom', + 'border-bottom-color', + 'border-bottom-left-radius', + 'border-bottom-right-radius', + 'border-bottom-style', + 'border-bottom-width', + 'border-collapse', + 'border-color', + 'border-end-end-radius', + 'border-end-start-radius', + 'border-image', + 'border-image-outset', + 'border-image-repeat', + 'border-image-slice', + 'border-image-source', + 'border-image-width', + 'border-inline', + 'border-inline-color', + 'border-inline-end', + 'border-inline-end-color', + 'border-inline-end-style', + 'border-inline-end-width', + 'border-inline-start', + 'border-inline-start-color', + 'border-inline-start-style', + 'border-inline-start-width', + 'border-inline-style', + 'border-inline-width', + 'border-left', + 'border-left-color', + 'border-left-style', + 'border-left-width', + 'border-radius', + 'border-right', + 'border-right-color', + 'border-right-style', + 'border-right-width', + 'border-spacing', + 'border-start-end-radius', + 'border-start-start-radius', + 'border-style', + 'border-top', + 'border-top-color', + 'border-top-left-radius', + 'border-top-right-radius', + 'border-top-style', + 'border-top-width', + 'border-width', + 'bottom', + 'box-align', + 'box-decoration-break', + 'box-direction', + 'box-flex', + 'box-flex-group', + 'box-lines', + 'box-ordinal-group', + 'box-orient', + 'box-pack', + 'box-shadow', + 'box-sizing', + 'break-after', + 'break-before', + 'break-inside', + 'caption-side', + 'caret-color', + 'clear', + 'clip', + 'clip-path', + 'clip-rule', + 'color', + 'color-interpolation', + 'color-interpolation-filters', + 'color-profile', + 'color-rendering', + 'color-scheme', + 'column-count', + 'column-fill', + 'column-gap', + 'column-rule', + 'column-rule-color', + 'column-rule-style', + 'column-rule-width', + 'column-span', + 'column-width', + 'columns', + 'contain', + 'contain-intrinsic-block-size', + 'contain-intrinsic-height', + 'contain-intrinsic-inline-size', + 'contain-intrinsic-size', + 'contain-intrinsic-width', + 'container', + 'container-name', + 'container-type', + 'content', + 'content-visibility', + 'counter-increment', + 'counter-reset', + 'counter-set', + 'cue', + 'cue-after', + 'cue-before', + 'cursor', + 'cx', + 'cy', + 'direction', + 'display', + 'dominant-baseline', + 'empty-cells', + 'enable-background', + 'field-sizing', + 'fill', + 'fill-opacity', + 'fill-rule', + 'filter', + 'flex', + 'flex-basis', + 'flex-direction', + 'flex-flow', + 'flex-grow', + 'flex-shrink', + 'flex-wrap', + 'float', + 'flood-color', + 'flood-opacity', + 'flow', + 'font', + 'font-display', + 'font-family', + 'font-feature-settings', + 'font-kerning', + 'font-language-override', + 'font-optical-sizing', + 'font-palette', + 'font-size', + 'font-size-adjust', + 'font-smooth', + 'font-smoothing', + 'font-stretch', + 'font-style', + 'font-synthesis', + 'font-synthesis-position', + 'font-synthesis-small-caps', + 'font-synthesis-style', + 'font-synthesis-weight', + 'font-variant', + 'font-variant-alternates', + 'font-variant-caps', + 'font-variant-east-asian', + 'font-variant-emoji', + 'font-variant-ligatures', + 'font-variant-numeric', + 'font-variant-position', + 'font-variation-settings', + 'font-weight', + 'forced-color-adjust', + 'gap', + 'glyph-orientation-horizontal', + 'glyph-orientation-vertical', + 'grid', + 'grid-area', + 'grid-auto-columns', + 'grid-auto-flow', + 'grid-auto-rows', + 'grid-column', + 'grid-column-end', + 'grid-column-start', + 'grid-gap', + 'grid-row', + 'grid-row-end', + 'grid-row-start', + 'grid-template', + 'grid-template-areas', + 'grid-template-columns', + 'grid-template-rows', + 'hanging-punctuation', + 'height', + 'hyphenate-character', + 'hyphenate-limit-chars', + 'hyphens', + 'icon', + 'image-orientation', + 'image-rendering', + 'image-resolution', + 'ime-mode', + 'initial-letter', + 'initial-letter-align', + 'inline-size', + 'inset', + 'inset-area', + 'inset-block', + 'inset-block-end', + 'inset-block-start', + 'inset-inline', + 'inset-inline-end', + 'inset-inline-start', + 'isolation', + 'justify-content', + 'justify-items', + 'justify-self', + 'kerning', + 'left', + 'letter-spacing', + 'lighting-color', + 'line-break', + 'line-height', + 'line-height-step', + 'list-style', + 'list-style-image', + 'list-style-position', + 'list-style-type', + 'margin', + 'margin-block', + 'margin-block-end', + 'margin-block-start', + 'margin-bottom', + 'margin-inline', + 'margin-inline-end', + 'margin-inline-start', + 'margin-left', + 'margin-right', + 'margin-top', + 'margin-trim', + 'marker', + 'marker-end', + 'marker-mid', + 'marker-start', + 'marks', + 'mask', + 'mask-border', + 'mask-border-mode', + 'mask-border-outset', + 'mask-border-repeat', + 'mask-border-slice', + 'mask-border-source', + 'mask-border-width', + 'mask-clip', + 'mask-composite', + 'mask-image', + 'mask-mode', + 'mask-origin', + 'mask-position', + 'mask-repeat', + 'mask-size', + 'mask-type', + 'masonry-auto-flow', + 'math-depth', + 'math-shift', + 'math-style', + 'max-block-size', + 'max-height', + 'max-inline-size', + 'max-width', + 'min-block-size', + 'min-height', + 'min-inline-size', + 'min-width', + 'mix-blend-mode', + 'nav-down', + 'nav-index', + 'nav-left', + 'nav-right', + 'nav-up', + 'none', + 'normal', + 'object-fit', + 'object-position', + 'offset', + 'offset-anchor', + 'offset-distance', + 'offset-path', + 'offset-position', + 'offset-rotate', + 'opacity', + 'order', + 'orphans', + 'outline', + 'outline-color', + 'outline-offset', + 'outline-style', + 'outline-width', + 'overflow', + 'overflow-anchor', + 'overflow-block', + 'overflow-clip-margin', + 'overflow-inline', + 'overflow-wrap', + 'overflow-x', + 'overflow-y', + 'overlay', + 'overscroll-behavior', + 'overscroll-behavior-block', + 'overscroll-behavior-inline', + 'overscroll-behavior-x', + 'overscroll-behavior-y', + 'padding', + 'padding-block', + 'padding-block-end', + 'padding-block-start', + 'padding-bottom', + 'padding-inline', + 'padding-inline-end', + 'padding-inline-start', + 'padding-left', + 'padding-right', + 'padding-top', + 'page', + 'page-break-after', + 'page-break-before', + 'page-break-inside', + 'paint-order', + 'pause', + 'pause-after', + 'pause-before', + 'perspective', + 'perspective-origin', + 'place-content', + 'place-items', + 'place-self', + 'pointer-events', + 'position', + 'position-anchor', + 'position-visibility', + 'print-color-adjust', + 'quotes', + 'r', + 'resize', + 'rest', + 'rest-after', + 'rest-before', + 'right', + 'rotate', + 'row-gap', + 'ruby-align', + 'ruby-position', + 'scale', + 'scroll-behavior', + 'scroll-margin', + 'scroll-margin-block', + 'scroll-margin-block-end', + 'scroll-margin-block-start', + 'scroll-margin-bottom', + 'scroll-margin-inline', + 'scroll-margin-inline-end', + 'scroll-margin-inline-start', + 'scroll-margin-left', + 'scroll-margin-right', + 'scroll-margin-top', + 'scroll-padding', + 'scroll-padding-block', + 'scroll-padding-block-end', + 'scroll-padding-block-start', + 'scroll-padding-bottom', + 'scroll-padding-inline', + 'scroll-padding-inline-end', + 'scroll-padding-inline-start', + 'scroll-padding-left', + 'scroll-padding-right', + 'scroll-padding-top', + 'scroll-snap-align', + 'scroll-snap-stop', + 'scroll-snap-type', + 'scroll-timeline', + 'scroll-timeline-axis', + 'scroll-timeline-name', + 'scrollbar-color', + 'scrollbar-gutter', + 'scrollbar-width', + 'shape-image-threshold', + 'shape-margin', + 'shape-outside', + 'shape-rendering', + 'speak', + 'speak-as', + 'src', // @font-face + 'stop-color', + 'stop-opacity', + 'stroke', + 'stroke-dasharray', + 'stroke-dashoffset', + 'stroke-linecap', + 'stroke-linejoin', + 'stroke-miterlimit', + 'stroke-opacity', + 'stroke-width', + 'tab-size', + 'table-layout', + 'text-align', + 'text-align-all', + 'text-align-last', + 'text-anchor', + 'text-combine-upright', + 'text-decoration', + 'text-decoration-color', + 'text-decoration-line', + 'text-decoration-skip', + 'text-decoration-skip-ink', + 'text-decoration-style', + 'text-decoration-thickness', + 'text-emphasis', + 'text-emphasis-color', + 'text-emphasis-position', + 'text-emphasis-style', + 'text-indent', + 'text-justify', + 'text-orientation', + 'text-overflow', + 'text-rendering', + 'text-shadow', + 'text-size-adjust', + 'text-transform', + 'text-underline-offset', + 'text-underline-position', + 'text-wrap', + 'text-wrap-mode', + 'text-wrap-style', + 'timeline-scope', + 'top', + 'touch-action', + 'transform', + 'transform-box', + 'transform-origin', + 'transform-style', + 'transition', + 'transition-behavior', + 'transition-delay', + 'transition-duration', + 'transition-property', + 'transition-timing-function', + 'translate', + 'unicode-bidi', + 'user-modify', + 'user-select', + 'vector-effect', + 'vertical-align', + 'view-timeline', + 'view-timeline-axis', + 'view-timeline-inset', + 'view-timeline-name', + 'view-transition-name', + 'visibility', + 'voice-balance', + 'voice-duration', + 'voice-family', + 'voice-pitch', + 'voice-range', + 'voice-rate', + 'voice-stress', + 'voice-volume', + 'white-space', + 'white-space-collapse', + 'widows', + 'width', + 'will-change', + 'word-break', + 'word-spacing', + 'word-wrap', + 'writing-mode', + 'x', + 'y', + 'z-index', + 'zoom' +].sort().reverse(); + +/* +Language: Stylus +Author: Bryant Williams +Description: Stylus is an expressive, robust, feature-rich CSS language built for nodejs. +Website: https://github.com/stylus/stylus +Category: css, web +*/ + + +/** @type LanguageFn */ +function stylus(hljs) { + const modes = MODES(hljs); + + const AT_MODIFIERS = "and or not only"; + const VARIABLE = { + className: 'variable', + begin: '\\$' + hljs.IDENT_RE + }; + + const AT_KEYWORDS = [ + 'charset', + 'css', + 'debug', + 'extend', + 'font-face', + 'for', + 'import', + 'include', + 'keyframes', + 'media', + 'mixin', + 'page', + 'warn', + 'while' + ]; + + const LOOKAHEAD_TAG_END = '(?=[.\\s\\n[:,(])'; + + // illegals + const ILLEGAL = [ + '\\?', + '(\\bReturn\\b)', // monkey + '(\\bEnd\\b)', // monkey + '(\\bend\\b)', // vbscript + '(\\bdef\\b)', // gradle + ';', // a whole lot of languages + '#\\s', // markdown + '\\*\\s', // markdown + '===\\s', // markdown + '\\|', + '%' // prolog + ]; + + return { + name: 'Stylus', + aliases: [ 'styl' ], + case_insensitive: false, + keywords: 'if else for in', + illegal: '(' + ILLEGAL.join('|') + ')', + contains: [ + + // strings + hljs.QUOTE_STRING_MODE, + hljs.APOS_STRING_MODE, + + // comments + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + + // hex colors + modes.HEXCOLOR, + + // class tag + { + begin: '\\.[a-zA-Z][a-zA-Z0-9_-]*' + LOOKAHEAD_TAG_END, + className: 'selector-class' + }, + + // id tag + { + begin: '#[a-zA-Z][a-zA-Z0-9_-]*' + LOOKAHEAD_TAG_END, + className: 'selector-id' + }, + + // tags + { + begin: '\\b(' + TAGS.join('|') + ')' + LOOKAHEAD_TAG_END, + className: 'selector-tag' + }, + + // psuedo selectors + { + className: 'selector-pseudo', + begin: '&?:(' + PSEUDO_CLASSES.join('|') + ')' + LOOKAHEAD_TAG_END + }, + { + className: 'selector-pseudo', + begin: '&?:(:)?(' + PSEUDO_ELEMENTS.join('|') + ')' + LOOKAHEAD_TAG_END + }, + + modes.ATTRIBUTE_SELECTOR_MODE, + + { + className: "keyword", + begin: /@media/, + starts: { + end: /[{;}]/, + keywords: { + $pattern: /[a-z-]+/, + keyword: AT_MODIFIERS, + attribute: MEDIA_FEATURES.join(" ") + }, + contains: [ modes.CSS_NUMBER_MODE ] + } + }, + + // @ keywords + { + className: 'keyword', + begin: '\@((-(o|moz|ms|webkit)-)?(' + AT_KEYWORDS.join('|') + '))\\b' + }, + + // variables + VARIABLE, + + // dimension + modes.CSS_NUMBER_MODE, + + // functions + // - only from beginning of line + whitespace + { + className: 'function', + begin: '^[a-zA-Z][a-zA-Z0-9_\-]*\\(.*\\)', + illegal: '[\\n]', + returnBegin: true, + contains: [ + { + className: 'title', + begin: '\\b[a-zA-Z][a-zA-Z0-9_\-]*' + }, + { + className: 'params', + begin: /\(/, + end: /\)/, + contains: [ + modes.HEXCOLOR, + VARIABLE, + hljs.APOS_STRING_MODE, + modes.CSS_NUMBER_MODE, + hljs.QUOTE_STRING_MODE + ] + } + ] + }, + + // css variables + modes.CSS_VARIABLE, + + // attributes + // - only from beginning of line + whitespace + // - must have whitespace after it + { + className: 'attribute', + begin: '\\b(' + ATTRIBUTES.join('|') + ')\\b', + starts: { + // value container + end: /;|$/, + contains: [ + modes.HEXCOLOR, + VARIABLE, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + modes.CSS_NUMBER_MODE, + hljs.C_BLOCK_COMMENT_MODE, + modes.IMPORTANT, + modes.FUNCTION_DISPATCH + ], + illegal: /\./, + relevance: 0 + } + }, + modes.FUNCTION_DISPATCH + ] + }; +} + +export { stylus as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/stylus.js.js b/frontend/node_modules/highlight.js/es/languages/stylus.js.js new file mode 100644 index 0000000..7a087ed --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/stylus.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/stylus" instead of "highlight.js/lib/languages/stylus.js"' + ); + } + } + emitWarning(); + import lang from './stylus.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/subunit.js b/frontend/node_modules/highlight.js/es/languages/subunit.js new file mode 100644 index 0000000..eae9165 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/subunit.js @@ -0,0 +1,44 @@ +/* +Language: SubUnit +Author: Sergey Bronnikov +Website: https://pypi.org/project/python-subunit/ +Category: protocols +*/ + +function subunit(hljs) { + const DETAILS = { + className: 'string', + begin: '\\[\n(multipart)?', + end: '\\]\n' + }; + const TIME = { + className: 'string', + begin: '\\d{4}-\\d{2}-\\d{2}(\\s+)\\d{2}:\\d{2}:\\d{2}\.\\d+Z' + }; + const PROGRESSVALUE = { + className: 'string', + begin: '(\\+|-)\\d+' + }; + const KEYWORDS = { + className: 'keyword', + relevance: 10, + variants: [ + { begin: '^(test|testing|success|successful|failure|error|skip|xfail|uxsuccess)(:?)\\s+(test)?' }, + { begin: '^progress(:?)(\\s+)?(pop|push)?' }, + { begin: '^tags:' }, + { begin: '^time:' } + ] + }; + return { + name: 'SubUnit', + case_insensitive: true, + contains: [ + DETAILS, + TIME, + PROGRESSVALUE, + KEYWORDS + ] + }; +} + +export { subunit as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/subunit.js.js b/frontend/node_modules/highlight.js/es/languages/subunit.js.js new file mode 100644 index 0000000..d9c15da --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/subunit.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/subunit" instead of "highlight.js/lib/languages/subunit.js"' + ); + } + } + emitWarning(); + import lang from './subunit.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/swift.js b/frontend/node_modules/highlight.js/es/languages/swift.js new file mode 100644 index 0000000..c4120ac --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/swift.js @@ -0,0 +1,972 @@ +/** + * @param {string} value + * @returns {RegExp} + * */ + +/** + * @param {RegExp | string } re + * @returns {string} + */ +function source(re) { + if (!re) return null; + if (typeof re === "string") return re; + + return re.source; +} + +/** + * @param {RegExp | string } re + * @returns {string} + */ +function lookahead(re) { + return concat('(?=', re, ')'); +} + +/** + * @param {...(RegExp | string) } args + * @returns {string} + */ +function concat(...args) { + const joined = args.map((x) => source(x)).join(""); + return joined; +} + +/** + * @param { Array } args + * @returns {object} + */ +function stripOptionsFromArgs(args) { + const opts = args[args.length - 1]; + + if (typeof opts === 'object' && opts.constructor === Object) { + args.splice(args.length - 1, 1); + return opts; + } else { + return {}; + } +} + +/** @typedef { {capture?: boolean} } RegexEitherOptions */ + +/** + * Any of the passed expresssions may match + * + * Creates a huge this | this | that | that match + * @param {(RegExp | string)[] | [...(RegExp | string)[], RegexEitherOptions]} args + * @returns {string} + */ +function either(...args) { + /** @type { object & {capture?: boolean} } */ + const opts = stripOptionsFromArgs(args); + const joined = '(' + + (opts.capture ? "" : "?:") + + args.map((x) => source(x)).join("|") + ")"; + return joined; +} + +const keywordWrapper = keyword => concat( + /\b/, + keyword, + /\w$/.test(keyword) ? /\b/ : /\B/ +); + +// Keywords that require a leading dot. +const dotKeywords = [ + 'Protocol', // contextual + 'Type' // contextual +].map(keywordWrapper); + +// Keywords that may have a leading dot. +const optionalDotKeywords = [ + 'init', + 'self' +].map(keywordWrapper); + +// should register as keyword, not type +const keywordTypes = [ + 'Any', + 'Self' +]; + +// Regular keywords and literals. +const keywords = [ + // strings below will be fed into the regular `keywords` engine while regex + // will result in additional modes being created to scan for those keywords to + // avoid conflicts with other rules + 'actor', + 'any', // contextual + 'associatedtype', + 'async', + 'await', + /as\?/, // operator + /as!/, // operator + 'as', // operator + 'borrowing', // contextual + 'break', + 'case', + 'catch', + 'class', + 'consume', // contextual + 'consuming', // contextual + 'continue', + 'convenience', // contextual + 'copy', // contextual + 'default', + 'defer', + 'deinit', + 'didSet', // contextual + 'distributed', + 'do', + 'dynamic', // contextual + 'each', + 'else', + 'enum', + 'extension', + 'fallthrough', + /fileprivate\(set\)/, + 'fileprivate', + 'final', // contextual + 'for', + 'func', + 'get', // contextual + 'guard', + 'if', + 'import', + 'indirect', // contextual + 'infix', // contextual + /init\?/, + /init!/, + 'inout', + /internal\(set\)/, + 'internal', + 'in', + 'is', // operator + 'isolated', // contextual + 'nonisolated', // contextual + 'lazy', // contextual + 'let', + 'macro', + 'mutating', // contextual + 'nonmutating', // contextual + /open\(set\)/, // contextual + 'open', // contextual + 'operator', + 'optional', // contextual + 'override', // contextual + 'package', + 'postfix', // contextual + 'precedencegroup', + 'prefix', // contextual + /private\(set\)/, + 'private', + 'protocol', + /public\(set\)/, + 'public', + 'repeat', + 'required', // contextual + 'rethrows', + 'return', + 'set', // contextual + 'some', // contextual + 'static', + 'struct', + 'subscript', + 'super', + 'switch', + 'throws', + 'throw', + /try\?/, // operator + /try!/, // operator + 'try', // operator + 'typealias', + /unowned\(safe\)/, // contextual + /unowned\(unsafe\)/, // contextual + 'unowned', // contextual + 'var', + 'weak', // contextual + 'where', + 'while', + 'willSet' // contextual +]; + +// NOTE: Contextual keywords are reserved only in specific contexts. +// Ideally, these should be matched using modes to avoid false positives. + +// Literals. +const literals = [ + 'false', + 'nil', + 'true' +]; + +// Keywords used in precedence groups. +const precedencegroupKeywords = [ + 'assignment', + 'associativity', + 'higherThan', + 'left', + 'lowerThan', + 'none', + 'right' +]; + +// Keywords that start with a number sign (#). +// #(un)available is handled separately. +const numberSignKeywords = [ + '#colorLiteral', + '#column', + '#dsohandle', + '#else', + '#elseif', + '#endif', + '#error', + '#file', + '#fileID', + '#fileLiteral', + '#filePath', + '#function', + '#if', + '#imageLiteral', + '#keyPath', + '#line', + '#selector', + '#sourceLocation', + '#warning' +]; + +// Global functions in the Standard Library. +const builtIns = [ + 'abs', + 'all', + 'any', + 'assert', + 'assertionFailure', + 'debugPrint', + 'dump', + 'fatalError', + 'getVaList', + 'isKnownUniquelyReferenced', + 'max', + 'min', + 'numericCast', + 'pointwiseMax', + 'pointwiseMin', + 'precondition', + 'preconditionFailure', + 'print', + 'readLine', + 'repeatElement', + 'sequence', + 'stride', + 'swap', + 'swift_unboxFromSwiftValueWithType', + 'transcode', + 'type', + 'unsafeBitCast', + 'unsafeDowncast', + 'withExtendedLifetime', + 'withUnsafeMutablePointer', + 'withUnsafePointer', + 'withVaList', + 'withoutActuallyEscaping', + 'zip' +]; + +// Valid first characters for operators. +const operatorHead = either( + /[/=\-+!*%<>&|^~?]/, + /[\u00A1-\u00A7]/, + /[\u00A9\u00AB]/, + /[\u00AC\u00AE]/, + /[\u00B0\u00B1]/, + /[\u00B6\u00BB\u00BF\u00D7\u00F7]/, + /[\u2016-\u2017]/, + /[\u2020-\u2027]/, + /[\u2030-\u203E]/, + /[\u2041-\u2053]/, + /[\u2055-\u205E]/, + /[\u2190-\u23FF]/, + /[\u2500-\u2775]/, + /[\u2794-\u2BFF]/, + /[\u2E00-\u2E7F]/, + /[\u3001-\u3003]/, + /[\u3008-\u3020]/, + /[\u3030]/ +); + +// Valid characters for operators. +const operatorCharacter = either( + operatorHead, + /[\u0300-\u036F]/, + /[\u1DC0-\u1DFF]/, + /[\u20D0-\u20FF]/, + /[\uFE00-\uFE0F]/, + /[\uFE20-\uFE2F]/ + // TODO: The following characters are also allowed, but the regex isn't supported yet. + // /[\u{E0100}-\u{E01EF}]/u +); + +// Valid operator. +const operator = concat(operatorHead, operatorCharacter, '*'); + +// Valid first characters for identifiers. +const identifierHead = either( + /[a-zA-Z_]/, + /[\u00A8\u00AA\u00AD\u00AF\u00B2-\u00B5\u00B7-\u00BA]/, + /[\u00BC-\u00BE\u00C0-\u00D6\u00D8-\u00F6\u00F8-\u00FF]/, + /[\u0100-\u02FF\u0370-\u167F\u1681-\u180D\u180F-\u1DBF]/, + /[\u1E00-\u1FFF]/, + /[\u200B-\u200D\u202A-\u202E\u203F-\u2040\u2054\u2060-\u206F]/, + /[\u2070-\u20CF\u2100-\u218F\u2460-\u24FF\u2776-\u2793]/, + /[\u2C00-\u2DFF\u2E80-\u2FFF]/, + /[\u3004-\u3007\u3021-\u302F\u3031-\u303F\u3040-\uD7FF]/, + /[\uF900-\uFD3D\uFD40-\uFDCF\uFDF0-\uFE1F\uFE30-\uFE44]/, + /[\uFE47-\uFEFE\uFF00-\uFFFD]/ // Should be /[\uFE47-\uFFFD]/, but we have to exclude FEFF. + // The following characters are also allowed, but the regexes aren't supported yet. + // /[\u{10000}-\u{1FFFD}\u{20000-\u{2FFFD}\u{30000}-\u{3FFFD}\u{40000}-\u{4FFFD}]/u, + // /[\u{50000}-\u{5FFFD}\u{60000-\u{6FFFD}\u{70000}-\u{7FFFD}\u{80000}-\u{8FFFD}]/u, + // /[\u{90000}-\u{9FFFD}\u{A0000-\u{AFFFD}\u{B0000}-\u{BFFFD}\u{C0000}-\u{CFFFD}]/u, + // /[\u{D0000}-\u{DFFFD}\u{E0000-\u{EFFFD}]/u +); + +// Valid characters for identifiers. +const identifierCharacter = either( + identifierHead, + /\d/, + /[\u0300-\u036F\u1DC0-\u1DFF\u20D0-\u20FF\uFE20-\uFE2F]/ +); + +// Valid identifier. +const identifier = concat(identifierHead, identifierCharacter, '*'); + +// Valid type identifier. +const typeIdentifier = concat(/[A-Z]/, identifierCharacter, '*'); + +// Built-in attributes, which are highlighted as keywords. +// @available is handled separately. +// https://docs.swift.org/swift-book/documentation/the-swift-programming-language/attributes +const keywordAttributes = [ + 'attached', + 'autoclosure', + concat(/convention\(/, either('swift', 'block', 'c'), /\)/), + 'discardableResult', + 'dynamicCallable', + 'dynamicMemberLookup', + 'escaping', + 'freestanding', + 'frozen', + 'GKInspectable', + 'IBAction', + 'IBDesignable', + 'IBInspectable', + 'IBOutlet', + 'IBSegueAction', + 'inlinable', + 'main', + 'nonobjc', + 'NSApplicationMain', + 'NSCopying', + 'NSManaged', + concat(/objc\(/, identifier, /\)/), + 'objc', + 'objcMembers', + 'propertyWrapper', + 'requires_stored_property_inits', + 'resultBuilder', + 'Sendable', + 'testable', + 'UIApplicationMain', + 'unchecked', + 'unknown', + 'usableFromInline', + 'warn_unqualified_access' +]; + +// Contextual keywords used in @available and #(un)available. +const availabilityKeywords = [ + 'iOS', + 'iOSApplicationExtension', + 'macOS', + 'macOSApplicationExtension', + 'macCatalyst', + 'macCatalystApplicationExtension', + 'watchOS', + 'watchOSApplicationExtension', + 'tvOS', + 'tvOSApplicationExtension', + 'swift' +]; + +/* +Language: Swift +Description: Swift is a general-purpose programming language built using a modern approach to safety, performance, and software design patterns. +Author: Steven Van Impe +Contributors: Chris Eidhof , Nate Cook , Alexander Lichter , Richard Gibson +Website: https://swift.org +Category: common, system +*/ + + +/** @type LanguageFn */ +function swift(hljs) { + const WHITESPACE = { + match: /\s+/, + relevance: 0 + }; + // https://docs.swift.org/swift-book/ReferenceManual/LexicalStructure.html#ID411 + const BLOCK_COMMENT = hljs.COMMENT( + '/\\*', + '\\*/', + { contains: [ 'self' ] } + ); + const COMMENTS = [ + hljs.C_LINE_COMMENT_MODE, + BLOCK_COMMENT + ]; + + // https://docs.swift.org/swift-book/ReferenceManual/LexicalStructure.html#ID413 + // https://docs.swift.org/swift-book/ReferenceManual/zzSummaryOfTheGrammar.html + const DOT_KEYWORD = { + match: [ + /\./, + either(...dotKeywords, ...optionalDotKeywords) + ], + className: { 2: "keyword" } + }; + const KEYWORD_GUARD = { + // Consume .keyword to prevent highlighting properties and methods as keywords. + match: concat(/\./, either(...keywords)), + relevance: 0 + }; + const PLAIN_KEYWORDS = keywords + .filter(kw => typeof kw === 'string') + .concat([ "_|0" ]); // seems common, so 0 relevance + const REGEX_KEYWORDS = keywords + .filter(kw => typeof kw !== 'string') // find regex + .concat(keywordTypes) + .map(keywordWrapper); + const KEYWORD = { variants: [ + { + className: 'keyword', + match: either(...REGEX_KEYWORDS, ...optionalDotKeywords) + } + ] }; + // find all the regular keywords + const KEYWORDS = { + $pattern: either( + /\b\w+/, // regular keywords + /#\w+/ // number keywords + ), + keyword: PLAIN_KEYWORDS + .concat(numberSignKeywords), + literal: literals + }; + const KEYWORD_MODES = [ + DOT_KEYWORD, + KEYWORD_GUARD, + KEYWORD + ]; + + // https://github.com/apple/swift/tree/main/stdlib/public/core + const BUILT_IN_GUARD = { + // Consume .built_in to prevent highlighting properties and methods. + match: concat(/\./, either(...builtIns)), + relevance: 0 + }; + const BUILT_IN = { + className: 'built_in', + match: concat(/\b/, either(...builtIns), /(?=\()/) + }; + const BUILT_INS = [ + BUILT_IN_GUARD, + BUILT_IN + ]; + + // https://docs.swift.org/swift-book/ReferenceManual/LexicalStructure.html#ID418 + const OPERATOR_GUARD = { + // Prevent -> from being highlighting as an operator. + match: /->/, + relevance: 0 + }; + const OPERATOR = { + className: 'operator', + relevance: 0, + variants: [ + { match: operator }, + { + // dot-operator: only operators that start with a dot are allowed to use dots as + // characters (..., ...<, .*, etc). So there rule here is: a dot followed by one or more + // characters that may also include dots. + match: `\\.(\\.|${operatorCharacter})+` } + ] + }; + const OPERATORS = [ + OPERATOR_GUARD, + OPERATOR + ]; + + // https://docs.swift.org/swift-book/ReferenceManual/LexicalStructure.html#grammar_numeric-literal + // TODO: Update for leading `-` after lookbehind is supported everywhere + const decimalDigits = '([0-9]_*)+'; + const hexDigits = '([0-9a-fA-F]_*)+'; + const NUMBER = { + className: 'number', + relevance: 0, + variants: [ + // decimal floating-point-literal (subsumes decimal-literal) + { match: `\\b(${decimalDigits})(\\.(${decimalDigits}))?` + `([eE][+-]?(${decimalDigits}))?\\b` }, + // hexadecimal floating-point-literal (subsumes hexadecimal-literal) + { match: `\\b0x(${hexDigits})(\\.(${hexDigits}))?` + `([pP][+-]?(${decimalDigits}))?\\b` }, + // octal-literal + { match: /\b0o([0-7]_*)+\b/ }, + // binary-literal + { match: /\b0b([01]_*)+\b/ } + ] + }; + + // https://docs.swift.org/swift-book/ReferenceManual/LexicalStructure.html#grammar_string-literal + const ESCAPED_CHARACTER = (rawDelimiter = "") => ({ + className: 'subst', + variants: [ + { match: concat(/\\/, rawDelimiter, /[0\\tnr"']/) }, + { match: concat(/\\/, rawDelimiter, /u\{[0-9a-fA-F]{1,8}\}/) } + ] + }); + const ESCAPED_NEWLINE = (rawDelimiter = "") => ({ + className: 'subst', + match: concat(/\\/, rawDelimiter, /[\t ]*(?:[\r\n]|\r\n)/) + }); + const INTERPOLATION = (rawDelimiter = "") => ({ + className: 'subst', + label: "interpol", + begin: concat(/\\/, rawDelimiter, /\(/), + end: /\)/ + }); + const MULTILINE_STRING = (rawDelimiter = "") => ({ + begin: concat(rawDelimiter, /"""/), + end: concat(/"""/, rawDelimiter), + contains: [ + ESCAPED_CHARACTER(rawDelimiter), + ESCAPED_NEWLINE(rawDelimiter), + INTERPOLATION(rawDelimiter) + ] + }); + const SINGLE_LINE_STRING = (rawDelimiter = "") => ({ + begin: concat(rawDelimiter, /"/), + end: concat(/"/, rawDelimiter), + contains: [ + ESCAPED_CHARACTER(rawDelimiter), + INTERPOLATION(rawDelimiter) + ] + }); + const STRING = { + className: 'string', + variants: [ + MULTILINE_STRING(), + MULTILINE_STRING("#"), + MULTILINE_STRING("##"), + MULTILINE_STRING("###"), + SINGLE_LINE_STRING(), + SINGLE_LINE_STRING("#"), + SINGLE_LINE_STRING("##"), + SINGLE_LINE_STRING("###") + ] + }; + + const REGEXP_CONTENTS = [ + hljs.BACKSLASH_ESCAPE, + { + begin: /\[/, + end: /\]/, + relevance: 0, + contains: [ hljs.BACKSLASH_ESCAPE ] + } + ]; + + const BARE_REGEXP_LITERAL = { + begin: /\/[^\s](?=[^/\n]*\/)/, + end: /\//, + contains: REGEXP_CONTENTS + }; + + const EXTENDED_REGEXP_LITERAL = (rawDelimiter) => { + const begin = concat(rawDelimiter, /\//); + const end = concat(/\//, rawDelimiter); + return { + begin, + end, + contains: [ + ...REGEXP_CONTENTS, + { + scope: "comment", + begin: `#(?!.*${end})`, + end: /$/, + }, + ], + }; + }; + + // https://docs.swift.org/swift-book/documentation/the-swift-programming-language/lexicalstructure/#Regular-Expression-Literals + const REGEXP = { + scope: "regexp", + variants: [ + EXTENDED_REGEXP_LITERAL('###'), + EXTENDED_REGEXP_LITERAL('##'), + EXTENDED_REGEXP_LITERAL('#'), + BARE_REGEXP_LITERAL + ] + }; + + // https://docs.swift.org/swift-book/ReferenceManual/LexicalStructure.html#ID412 + const QUOTED_IDENTIFIER = { match: concat(/`/, identifier, /`/) }; + const IMPLICIT_PARAMETER = { + className: 'variable', + match: /\$\d+/ + }; + const PROPERTY_WRAPPER_PROJECTION = { + className: 'variable', + match: `\\$${identifierCharacter}+` + }; + const IDENTIFIERS = [ + QUOTED_IDENTIFIER, + IMPLICIT_PARAMETER, + PROPERTY_WRAPPER_PROJECTION + ]; + + // https://docs.swift.org/swift-book/ReferenceManual/Attributes.html + const AVAILABLE_ATTRIBUTE = { + match: /(@|#(un)?)available/, + scope: 'keyword', + starts: { contains: [ + { + begin: /\(/, + end: /\)/, + keywords: availabilityKeywords, + contains: [ + ...OPERATORS, + NUMBER, + STRING + ] + } + ] } + }; + + const KEYWORD_ATTRIBUTE = { + scope: 'keyword', + match: concat(/@/, either(...keywordAttributes), lookahead(either(/\(/, /\s+/))), + }; + + const USER_DEFINED_ATTRIBUTE = { + scope: 'meta', + match: concat(/@/, identifier) + }; + + const ATTRIBUTES = [ + AVAILABLE_ATTRIBUTE, + KEYWORD_ATTRIBUTE, + USER_DEFINED_ATTRIBUTE + ]; + + // https://docs.swift.org/swift-book/ReferenceManual/Types.html + const TYPE = { + match: lookahead(/\b[A-Z]/), + relevance: 0, + contains: [ + { // Common Apple frameworks, for relevance boost + className: 'type', + match: concat(/(AV|CA|CF|CG|CI|CL|CM|CN|CT|MK|MP|MTK|MTL|NS|SCN|SK|UI|WK|XC)/, identifierCharacter, '+') + }, + { // Type identifier + className: 'type', + match: typeIdentifier, + relevance: 0 + }, + { // Optional type + match: /[?!]+/, + relevance: 0 + }, + { // Variadic parameter + match: /\.\.\./, + relevance: 0 + }, + { // Protocol composition + match: concat(/\s+&\s+/, lookahead(typeIdentifier)), + relevance: 0 + } + ] + }; + const GENERIC_ARGUMENTS = { + begin: //, + keywords: KEYWORDS, + contains: [ + ...COMMENTS, + ...KEYWORD_MODES, + ...ATTRIBUTES, + OPERATOR_GUARD, + TYPE + ] + }; + TYPE.contains.push(GENERIC_ARGUMENTS); + + // https://docs.swift.org/swift-book/ReferenceManual/Expressions.html#ID552 + // Prevents element names from being highlighted as keywords. + const TUPLE_ELEMENT_NAME = { + match: concat(identifier, /\s*:/), + keywords: "_|0", + relevance: 0 + }; + // Matches tuples as well as the parameter list of a function type. + const TUPLE = { + begin: /\(/, + end: /\)/, + relevance: 0, + keywords: KEYWORDS, + contains: [ + 'self', + TUPLE_ELEMENT_NAME, + ...COMMENTS, + REGEXP, + ...KEYWORD_MODES, + ...BUILT_INS, + ...OPERATORS, + NUMBER, + STRING, + ...IDENTIFIERS, + ...ATTRIBUTES, + TYPE + ] + }; + + const GENERIC_PARAMETERS = { + begin: //, + keywords: 'repeat each', + contains: [ + ...COMMENTS, + TYPE + ] + }; + const FUNCTION_PARAMETER_NAME = { + begin: either( + lookahead(concat(identifier, /\s*:/)), + lookahead(concat(identifier, /\s+/, identifier, /\s*:/)) + ), + end: /:/, + relevance: 0, + contains: [ + { + className: 'keyword', + match: /\b_\b/ + }, + { + className: 'params', + match: identifier + } + ] + }; + const FUNCTION_PARAMETERS = { + begin: /\(/, + end: /\)/, + keywords: KEYWORDS, + contains: [ + FUNCTION_PARAMETER_NAME, + ...COMMENTS, + ...KEYWORD_MODES, + ...OPERATORS, + NUMBER, + STRING, + ...ATTRIBUTES, + TYPE, + TUPLE + ], + endsParent: true, + illegal: /["']/ + }; + // https://docs.swift.org/swift-book/ReferenceManual/Declarations.html#ID362 + // https://docs.swift.org/swift-book/documentation/the-swift-programming-language/declarations/#Macro-Declaration + const FUNCTION_OR_MACRO = { + match: [ + /(func|macro)/, + /\s+/, + either(QUOTED_IDENTIFIER.match, identifier, operator) + ], + className: { + 1: "keyword", + 3: "title.function" + }, + contains: [ + GENERIC_PARAMETERS, + FUNCTION_PARAMETERS, + WHITESPACE + ], + illegal: [ + /\[/, + /%/ + ] + }; + + // https://docs.swift.org/swift-book/ReferenceManual/Declarations.html#ID375 + // https://docs.swift.org/swift-book/ReferenceManual/Declarations.html#ID379 + const INIT_SUBSCRIPT = { + match: [ + /\b(?:subscript|init[?!]?)/, + /\s*(?=[<(])/, + ], + className: { 1: "keyword" }, + contains: [ + GENERIC_PARAMETERS, + FUNCTION_PARAMETERS, + WHITESPACE + ], + illegal: /\[|%/ + }; + // https://docs.swift.org/swift-book/ReferenceManual/Declarations.html#ID380 + const OPERATOR_DECLARATION = { + match: [ + /operator/, + /\s+/, + operator + ], + className: { + 1: "keyword", + 3: "title" + } + }; + + // https://docs.swift.org/swift-book/ReferenceManual/Declarations.html#ID550 + const PRECEDENCEGROUP = { + begin: [ + /precedencegroup/, + /\s+/, + typeIdentifier + ], + className: { + 1: "keyword", + 3: "title" + }, + contains: [ TYPE ], + keywords: [ + ...precedencegroupKeywords, + ...literals + ], + end: /}/ + }; + + const CLASS_FUNC_DECLARATION = { + match: [ + /class\b/, + /\s+/, + /func\b/, + /\s+/, + /\b[A-Za-z_][A-Za-z0-9_]*\b/ + ], + scope: { + 1: "keyword", + 3: "keyword", + 5: "title.function" + } + }; + + const CLASS_VAR_DECLARATION = { + match: [ + /class\b/, + /\s+/, + /var\b/, + ], + scope: { + 1: "keyword", + 3: "keyword" + } + }; + + const TYPE_DECLARATION = { + begin: [ + /(struct|protocol|class|extension|enum|actor)/, + /\s+/, + identifier, + /\s*/, + ], + beginScope: { + 1: "keyword", + 3: "title.class" + }, + keywords: KEYWORDS, + contains: [ + GENERIC_PARAMETERS, + ...KEYWORD_MODES, + { + begin: /:/, + end: /\{/, + keywords: KEYWORDS, + contains: [ + { + scope: "title.class.inherited", + match: typeIdentifier, + }, + ...KEYWORD_MODES, + ], + relevance: 0, + }, + ] + }; + + // Add supported submodes to string interpolation. + for (const variant of STRING.variants) { + const interpolation = variant.contains.find(mode => mode.label === "interpol"); + // TODO: Interpolation can contain any expression, so there's room for improvement here. + interpolation.keywords = KEYWORDS; + const submodes = [ + ...KEYWORD_MODES, + ...BUILT_INS, + ...OPERATORS, + NUMBER, + STRING, + ...IDENTIFIERS + ]; + interpolation.contains = [ + ...submodes, + { + begin: /\(/, + end: /\)/, + contains: [ + 'self', + ...submodes + ] + } + ]; + } + + return { + name: 'Swift', + keywords: KEYWORDS, + contains: [ + ...COMMENTS, + FUNCTION_OR_MACRO, + INIT_SUBSCRIPT, + CLASS_FUNC_DECLARATION, + CLASS_VAR_DECLARATION, + TYPE_DECLARATION, + OPERATOR_DECLARATION, + PRECEDENCEGROUP, + { + beginKeywords: 'import', + end: /$/, + contains: [ ...COMMENTS ], + relevance: 0 + }, + REGEXP, + ...KEYWORD_MODES, + ...BUILT_INS, + ...OPERATORS, + NUMBER, + STRING, + ...IDENTIFIERS, + ...ATTRIBUTES, + TYPE, + TUPLE + ] + }; +} + +export { swift as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/swift.js.js b/frontend/node_modules/highlight.js/es/languages/swift.js.js new file mode 100644 index 0000000..d9bc549 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/swift.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/swift" instead of "highlight.js/lib/languages/swift.js"' + ); + } + } + emitWarning(); + import lang from './swift.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/taggerscript.js b/frontend/node_modules/highlight.js/es/languages/taggerscript.js new file mode 100644 index 0000000..567aceb --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/taggerscript.js @@ -0,0 +1,59 @@ +/* +Language: Tagger Script +Author: Philipp Wolfer +Description: Syntax Highlighting for the Tagger Script as used by MusicBrainz Picard. +Website: https://picard.musicbrainz.org +Category: scripting + */ +function taggerscript(hljs) { + const NOOP = { + className: 'comment', + begin: /\$noop\(/, + end: /\)/, + contains: [ + { begin: /\\[()]/ }, + { + begin: /\(/, + end: /\)/, + contains: [ + { begin: /\\[()]/ }, + 'self' + ] + } + ], + relevance: 10 + }; + + const FUNCTION = { + className: 'keyword', + begin: /\$[_a-zA-Z0-9]+(?=\()/ + }; + + const VARIABLE = { + className: 'variable', + begin: /%[_a-zA-Z0-9:]+%/ + }; + + const ESCAPE_SEQUENCE_UNICODE = { + className: 'symbol', + begin: /\\u[a-fA-F0-9]{4}/ + }; + + const ESCAPE_SEQUENCE = { + className: 'symbol', + begin: /\\[\\nt$%,()]/ + }; + + return { + name: 'Tagger Script', + contains: [ + NOOP, + FUNCTION, + VARIABLE, + ESCAPE_SEQUENCE, + ESCAPE_SEQUENCE_UNICODE + ] + }; +} + +export { taggerscript as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/taggerscript.js.js b/frontend/node_modules/highlight.js/es/languages/taggerscript.js.js new file mode 100644 index 0000000..75601e0 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/taggerscript.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/taggerscript" instead of "highlight.js/lib/languages/taggerscript.js"' + ); + } + } + emitWarning(); + import lang from './taggerscript.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/tap.js b/frontend/node_modules/highlight.js/es/languages/tap.js new file mode 100644 index 0000000..8cd8ba5 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/tap.js @@ -0,0 +1,47 @@ +/* +Language: Test Anything Protocol +Description: TAP, the Test Anything Protocol, is a simple text-based interface between testing modules in a test harness. +Requires: yaml.js +Author: Sergey Bronnikov +Website: https://testanything.org +*/ + +function tap(hljs) { + return { + name: 'Test Anything Protocol', + case_insensitive: true, + contains: [ + hljs.HASH_COMMENT_MODE, + // version of format and total amount of testcases + { + className: 'meta', + variants: [ + { begin: '^TAP version (\\d+)$' }, + { begin: '^1\\.\\.(\\d+)$' } + ] + }, + // YAML block + { + begin: /---$/, + end: '\\.\\.\\.$', + subLanguage: 'yaml', + relevance: 0 + }, + // testcase number + { + className: 'number', + begin: ' (\\d+) ' + }, + // testcase status and description + { + className: 'symbol', + variants: [ + { begin: '^ok' }, + { begin: '^not ok' } + ] + } + ] + }; +} + +export { tap as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/tap.js.js b/frontend/node_modules/highlight.js/es/languages/tap.js.js new file mode 100644 index 0000000..32962e5 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/tap.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/tap" instead of "highlight.js/lib/languages/tap.js"' + ); + } + } + emitWarning(); + import lang from './tap.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/tcl.js b/frontend/node_modules/highlight.js/es/languages/tcl.js new file mode 100644 index 0000000..da59442 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/tcl.js @@ -0,0 +1,191 @@ +/* +Language: Tcl +Description: Tcl is a very simple programming language. +Author: Radek Liska +Website: https://www.tcl.tk/about/language.html +Category: scripting +*/ + +function tcl(hljs) { + const regex = hljs.regex; + const TCL_IDENT = /[a-zA-Z_][a-zA-Z0-9_]*/; + + const NUMBER = { + className: 'number', + variants: [ + hljs.BINARY_NUMBER_MODE, + hljs.C_NUMBER_MODE + ] + }; + + const KEYWORDS = [ + "after", + "append", + "apply", + "array", + "auto_execok", + "auto_import", + "auto_load", + "auto_mkindex", + "auto_mkindex_old", + "auto_qualify", + "auto_reset", + "bgerror", + "binary", + "break", + "catch", + "cd", + "chan", + "clock", + "close", + "concat", + "continue", + "dde", + "dict", + "encoding", + "eof", + "error", + "eval", + "exec", + "exit", + "expr", + "fblocked", + "fconfigure", + "fcopy", + "file", + "fileevent", + "filename", + "flush", + "for", + "foreach", + "format", + "gets", + "glob", + "global", + "history", + "http", + "if", + "incr", + "info", + "interp", + "join", + "lappend|10", + "lassign|10", + "lindex|10", + "linsert|10", + "list", + "llength|10", + "load", + "lrange|10", + "lrepeat|10", + "lreplace|10", + "lreverse|10", + "lsearch|10", + "lset|10", + "lsort|10", + "mathfunc", + "mathop", + "memory", + "msgcat", + "namespace", + "open", + "package", + "parray", + "pid", + "pkg::create", + "pkg_mkIndex", + "platform", + "platform::shell", + "proc", + "puts", + "pwd", + "read", + "refchan", + "regexp", + "registry", + "regsub|10", + "rename", + "return", + "safe", + "scan", + "seek", + "set", + "socket", + "source", + "split", + "string", + "subst", + "switch", + "tcl_endOfWord", + "tcl_findLibrary", + "tcl_startOfNextWord", + "tcl_startOfPreviousWord", + "tcl_wordBreakAfter", + "tcl_wordBreakBefore", + "tcltest", + "tclvars", + "tell", + "time", + "tm", + "trace", + "unknown", + "unload", + "unset", + "update", + "uplevel", + "upvar", + "variable", + "vwait", + "while" + ]; + + return { + name: 'Tcl', + aliases: [ 'tk' ], + keywords: KEYWORDS, + contains: [ + hljs.COMMENT(';[ \\t]*#', '$'), + hljs.COMMENT('^[ \\t]*#', '$'), + { + beginKeywords: 'proc', + end: '[\\{]', + excludeEnd: true, + contains: [ + { + className: 'title', + begin: '[ \\t\\n\\r]+(::)?[a-zA-Z_]((::)?[a-zA-Z0-9_])*', + end: '[ \\t\\n\\r]', + endsWithParent: true, + excludeEnd: true + } + ] + }, + { + className: "variable", + variants: [ + { begin: regex.concat( + /\$/, + regex.optional(/::/), + TCL_IDENT, + '(::', + TCL_IDENT, + ')*' + ) }, + { + begin: '\\$\\{(::)?[a-zA-Z_]((::)?[a-zA-Z0-9_])*', + end: '\\}', + contains: [ NUMBER ] + } + ] + }, + { + className: 'string', + contains: [ hljs.BACKSLASH_ESCAPE ], + variants: [ hljs.inherit(hljs.QUOTE_STRING_MODE, { illegal: null }) ] + }, + NUMBER + ] + }; +} + +export { tcl as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/tcl.js.js b/frontend/node_modules/highlight.js/es/languages/tcl.js.js new file mode 100644 index 0000000..9e5a58f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/tcl.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/tcl" instead of "highlight.js/lib/languages/tcl.js"' + ); + } + } + emitWarning(); + import lang from './tcl.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/thrift.js b/frontend/node_modules/highlight.js/es/languages/thrift.js new file mode 100644 index 0000000..1287574 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/thrift.js @@ -0,0 +1,77 @@ +/* +Language: Thrift +Author: Oleg Efimov +Description: Thrift message definition format +Website: https://thrift.apache.org +Category: protocols +*/ + +function thrift(hljs) { + const TYPES = [ + "bool", + "byte", + "i16", + "i32", + "i64", + "double", + "string", + "binary" + ]; + const KEYWORDS = [ + "namespace", + "const", + "typedef", + "struct", + "enum", + "service", + "exception", + "void", + "oneway", + "set", + "list", + "map", + "required", + "optional" + ]; + return { + name: 'Thrift', + keywords: { + keyword: KEYWORDS, + type: TYPES, + literal: 'true false' + }, + contains: [ + hljs.QUOTE_STRING_MODE, + hljs.NUMBER_MODE, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + { + className: 'class', + beginKeywords: 'struct enum service exception', + end: /\{/, + illegal: /\n/, + contains: [ + hljs.inherit(hljs.TITLE_MODE, { + // hack: eating everything after the first title + starts: { + endsWithParent: true, + excludeEnd: true + } }) + ] + }, + { + begin: '\\b(set|list|map)\\s*<', + keywords: { type: [ + ...TYPES, + "set", + "list", + "map" + ] }, + end: '>', + contains: [ 'self' ] + } + ] + }; +} + +export { thrift as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/thrift.js.js b/frontend/node_modules/highlight.js/es/languages/thrift.js.js new file mode 100644 index 0000000..d214aa7 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/thrift.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/thrift" instead of "highlight.js/lib/languages/thrift.js"' + ); + } + } + emitWarning(); + import lang from './thrift.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/tp.js b/frontend/node_modules/highlight.js/es/languages/tp.js new file mode 100644 index 0000000..94e69d3 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/tp.js @@ -0,0 +1,172 @@ +/* +Language: TP +Author: Jay Strybis +Description: FANUC TP programming language (TPP). +Category: hardware +*/ + +function tp(hljs) { + const TPID = { + className: 'number', + begin: '[1-9][0-9]*', /* no leading zeros */ + relevance: 0 + }; + const TPLABEL = { + className: 'symbol', + begin: ':[^\\]]+' + }; + const TPDATA = { + className: 'built_in', + begin: '(AR|P|PAYLOAD|PR|R|SR|RSR|LBL|VR|UALM|MESSAGE|UTOOL|UFRAME|TIMER|' + + 'TIMER_OVERFLOW|JOINT_MAX_SPEED|RESUME_PROG|DIAG_REC)\\[', + end: '\\]', + contains: [ + 'self', + TPID, + TPLABEL + ] + }; + const TPIO = { + className: 'built_in', + begin: '(AI|AO|DI|DO|F|RI|RO|UI|UO|GI|GO|SI|SO)\\[', + end: '\\]', + contains: [ + 'self', + TPID, + hljs.QUOTE_STRING_MODE, /* for pos section at bottom */ + TPLABEL + ] + }; + + const KEYWORDS = [ + "ABORT", + "ACC", + "ADJUST", + "AND", + "AP_LD", + "BREAK", + "CALL", + "CNT", + "COL", + "CONDITION", + "CONFIG", + "DA", + "DB", + "DIV", + "DETECT", + "ELSE", + "END", + "ENDFOR", + "ERR_NUM", + "ERROR_PROG", + "FINE", + "FOR", + "GP", + "GUARD", + "INC", + "IF", + "JMP", + "LINEAR_MAX_SPEED", + "LOCK", + "MOD", + "MONITOR", + "OFFSET", + "Offset", + "OR", + "OVERRIDE", + "PAUSE", + "PREG", + "PTH", + "RT_LD", + "RUN", + "SELECT", + "SKIP", + "Skip", + "TA", + "TB", + "TO", + "TOOL_OFFSET", + "Tool_Offset", + "UF", + "UT", + "UFRAME_NUM", + "UTOOL_NUM", + "UNLOCK", + "WAIT", + "X", + "Y", + "Z", + "W", + "P", + "R", + "STRLEN", + "SUBSTR", + "FINDSTR", + "VOFFSET", + "PROG", + "ATTR", + "MN", + "POS" + ]; + const LITERALS = [ + "ON", + "OFF", + "max_speed", + "LPOS", + "JPOS", + "ENABLE", + "DISABLE", + "START", + "STOP", + "RESET" + ]; + + return { + name: 'TP', + keywords: { + keyword: KEYWORDS, + literal: LITERALS + }, + contains: [ + TPDATA, + TPIO, + { + className: 'keyword', + begin: '/(PROG|ATTR|MN|POS|END)\\b' + }, + { + /* this is for cases like ,CALL */ + className: 'keyword', + begin: '(CALL|RUN|POINT_LOGIC|LBL)\\b' + }, + { + /* this is for cases like CNT100 where the default lexemes do not + * separate the keyword and the number */ + className: 'keyword', + begin: '\\b(ACC|CNT|Skip|Offset|PSPD|RT_LD|AP_LD|Tool_Offset)' + }, + { + /* to catch numbers that do not have a word boundary on the left */ + className: 'number', + begin: '\\d+(sec|msec|mm/sec|cm/min|inch/min|deg/sec|mm|in|cm)?\\b', + relevance: 0 + }, + hljs.COMMENT('//', '[;$]'), + hljs.COMMENT('!', '[;$]'), + hljs.COMMENT('--eg:', '$'), + hljs.QUOTE_STRING_MODE, + { + className: 'string', + begin: '\'', + end: '\'' + }, + hljs.C_NUMBER_MODE, + { + className: 'variable', + begin: '\\$[A-Za-z0-9_]+' + } + ] + }; +} + +export { tp as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/tp.js.js b/frontend/node_modules/highlight.js/es/languages/tp.js.js new file mode 100644 index 0000000..c8cc883 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/tp.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/tp" instead of "highlight.js/lib/languages/tp.js"' + ); + } + } + emitWarning(); + import lang from './tp.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/twig.js b/frontend/node_modules/highlight.js/es/languages/twig.js new file mode 100644 index 0000000..f980340 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/twig.js @@ -0,0 +1,260 @@ +/* +Language: Twig +Requires: xml.js +Author: Luke Holder +Description: Twig is a templating language for PHP +Website: https://twig.symfony.com +Category: template +*/ + +function twig(hljs) { + const regex = hljs.regex; + const FUNCTION_NAMES = [ + "absolute_url", + "asset|0", + "asset_version", + "attribute", + "block", + "constant", + "controller|0", + "country_timezones", + "csrf_token", + "cycle", + "date", + "dump", + "expression", + "form|0", + "form_end", + "form_errors", + "form_help", + "form_label", + "form_rest", + "form_row", + "form_start", + "form_widget", + "html_classes", + "include", + "is_granted", + "logout_path", + "logout_url", + "max", + "min", + "parent", + "path|0", + "random", + "range", + "relative_path", + "render", + "render_esi", + "source", + "template_from_string", + "url|0" + ]; + + const FILTERS = [ + "abs", + "abbr_class", + "abbr_method", + "batch", + "capitalize", + "column", + "convert_encoding", + "country_name", + "currency_name", + "currency_symbol", + "data_uri", + "date", + "date_modify", + "default", + "escape", + "file_excerpt", + "file_link", + "file_relative", + "filter", + "first", + "format", + "format_args", + "format_args_as_text", + "format_currency", + "format_date", + "format_datetime", + "format_file", + "format_file_from_text", + "format_number", + "format_time", + "html_to_markdown", + "humanize", + "inky_to_html", + "inline_css", + "join", + "json_encode", + "keys", + "language_name", + "last", + "length", + "locale_name", + "lower", + "map", + "markdown", + "markdown_to_html", + "merge", + "nl2br", + "number_format", + "raw", + "reduce", + "replace", + "reverse", + "round", + "slice", + "slug", + "sort", + "spaceless", + "split", + "striptags", + "timezone_name", + "title", + "trans", + "transchoice", + "trim", + "u|0", + "upper", + "url_encode", + "yaml_dump", + "yaml_encode" + ]; + + let TAG_NAMES = [ + "apply", + "autoescape", + "block", + "cache", + "deprecated", + "do", + "embed", + "extends", + "filter", + "flush", + "for", + "form_theme", + "from", + "if", + "import", + "include", + "macro", + "sandbox", + "set", + "stopwatch", + "trans", + "trans_default_domain", + "transchoice", + "use", + "verbatim", + "with" + ]; + + TAG_NAMES = TAG_NAMES.concat(TAG_NAMES.map(t => `end${t}`)); + + const STRING = { + scope: 'string', + variants: [ + { + begin: /'/, + end: /'/ + }, + { + begin: /"/, + end: /"/ + }, + ] + }; + + const NUMBER = { + scope: "number", + match: /\d+/ + }; + + const PARAMS = { + begin: /\(/, + end: /\)/, + excludeBegin: true, + excludeEnd: true, + contains: [ + STRING, + NUMBER + ] + }; + + + const FUNCTIONS = { + beginKeywords: FUNCTION_NAMES.join(" "), + keywords: { name: FUNCTION_NAMES }, + relevance: 0, + contains: [ PARAMS ] + }; + + const FILTER = { + match: /\|(?=[A-Za-z_]+:?)/, + beginScope: "punctuation", + relevance: 0, + contains: [ + { + match: /[A-Za-z_]+:?/, + keywords: FILTERS + }, + ] + }; + + const tagNamed = (tagnames, { relevance }) => { + return { + beginScope: { + 1: 'template-tag', + 3: 'name' + }, + relevance: relevance || 2, + endScope: 'template-tag', + begin: [ + /\{%/, + /\s*/, + regex.either(...tagnames) + ], + end: /%\}/, + keywords: "in", + contains: [ + FILTER, + FUNCTIONS, + STRING, + NUMBER + ] + }; + }; + + const CUSTOM_TAG_RE = /[a-z_]+/; + const TAG = tagNamed(TAG_NAMES, { relevance: 2 }); + const CUSTOM_TAG = tagNamed([ CUSTOM_TAG_RE ], { relevance: 1 }); + + return { + name: 'Twig', + aliases: [ 'craftcms' ], + case_insensitive: true, + subLanguage: 'xml', + contains: [ + hljs.COMMENT(/\{#/, /#\}/), + TAG, + CUSTOM_TAG, + { + className: 'template-variable', + begin: /\{\{/, + end: /\}\}/, + contains: [ + 'self', + FILTER, + FUNCTIONS, + STRING, + NUMBER + ] + } + ] + }; +} + +export { twig as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/twig.js.js b/frontend/node_modules/highlight.js/es/languages/twig.js.js new file mode 100644 index 0000000..62b5701 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/twig.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/twig" instead of "highlight.js/lib/languages/twig.js"' + ); + } + } + emitWarning(); + import lang from './twig.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/typescript.js b/frontend/node_modules/highlight.js/es/languages/typescript.js new file mode 100644 index 0000000..23169f8 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/typescript.js @@ -0,0 +1,913 @@ +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", + // It's reached stage 3, which is "recommended for implementation": + "using" +]; +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 " { + const tag = "', + 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? + // `>`, etc. + nextChar === "<" || + // the , gives away that this is not HTML + // `` + nextChar === "," + ) { + response.ignoreMatch(); + return; + } + + // `` + // 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(); + } + } + + // `` (self-closing) + // handled by simpleSelfClosing rule + + let m; + const afterMatch = match.input.substring(afterMatchIndex); + + // some more template typing stuff + // (key?: string) => Modify< + if ((m = afterMatch.match(/^\s*=/))) { + response.ignoreMatch(); + return; + } + + // `` + // 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: /(\s*)\(/, + end: /\)/, + keywords: KEYWORDS$1, + contains: ["self"].concat(SUBST_AND_COMMENTS) + } + ]); + const PARAMS = { + className: 'params', + // convert this to negative lookbehind in v12 + begin: /(\s*)\(/, // to match the parms with + 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" + ].map(x => `${x}\\s*\\(`)), + IDENT_RE$1, regex.lookahead(/\s*\(/)), + 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, + { + scope: 'attr', + match: 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: /(\s*)\(/, + 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` + } + ] + }; +} + +/* +Language: TypeScript +Author: Panu Horsmalahti +Contributors: Ike Ku +Description: TypeScript is a strict superset of JavaScript +Website: https://www.typescriptlang.org +Category: common, scripting +*/ + + +/** @type LanguageFn */ +function typescript(hljs) { + const regex = hljs.regex; + const tsLanguage = javascript(hljs); + + const IDENT_RE$1 = IDENT_RE; + const TYPES = [ + "any", + "void", + "number", + "boolean", + "string", + "object", + "never", + "symbol", + "bigint", + "unknown" + ]; + const NAMESPACE = { + begin: [ + /namespace/, + /\s+/, + hljs.IDENT_RE + ], + beginScope: { + 1: "keyword", + 3: "title.class" + } + }; + const INTERFACE = { + beginKeywords: 'interface', + end: /\{/, + excludeEnd: true, + keywords: { + keyword: 'interface extends', + built_in: TYPES + }, + contains: [ tsLanguage.exports.CLASS_REFERENCE ] + }; + const USE_STRICT = { + className: 'meta', + relevance: 10, + begin: /^\s*['"]use strict['"]/ + }; + const TS_SPECIFIC_KEYWORDS = [ + "type", + // "namespace", + "interface", + "public", + "private", + "protected", + "implements", + "declare", + "abstract", + "readonly", + "enum", + "override", + "satisfies" + ]; + /* + namespace is a TS keyword but it's fine to use it as a variable name too. + const message = 'foo'; + const namespace = 'bar'; + */ + const KEYWORDS$1 = { + $pattern: IDENT_RE, + keyword: KEYWORDS.concat(TS_SPECIFIC_KEYWORDS), + literal: LITERALS, + built_in: BUILT_INS.concat(TYPES), + "variable.language": BUILT_IN_VARIABLES + }; + + const DECORATOR = { + className: 'meta', + begin: '@' + IDENT_RE$1, + }; + + const swapMode = (mode, label, replacement) => { + const indx = mode.contains.findIndex(m => m.label === label); + if (indx === -1) { throw new Error("can not find mode to replace"); } + + mode.contains.splice(indx, 1, replacement); + }; + + + // this should update anywhere keywords is used since + // it will be the same actual JS object + Object.assign(tsLanguage.keywords, KEYWORDS$1); + + tsLanguage.exports.PARAMS_CONTAINS.push(DECORATOR); + + // highlight the function params + const ATTRIBUTE_HIGHLIGHT = tsLanguage.contains.find(c => c.scope === "attr"); + + // take default attr rule and extend it to support optionals + const OPTIONAL_KEY_OR_ARGUMENT = Object.assign({}, + ATTRIBUTE_HIGHLIGHT, + { match: regex.concat(IDENT_RE$1, regex.lookahead(/\s*\?:/)) } + ); + tsLanguage.exports.PARAMS_CONTAINS.push([ + tsLanguage.exports.CLASS_REFERENCE, // class reference for highlighting the params types + ATTRIBUTE_HIGHLIGHT, // highlight the params key + OPTIONAL_KEY_OR_ARGUMENT, // Added for optional property assignment highlighting + ]); + + // Add the optional property assignment highlighting for objects or classes + tsLanguage.contains = tsLanguage.contains.concat([ + DECORATOR, + NAMESPACE, + INTERFACE, + OPTIONAL_KEY_OR_ARGUMENT, // Added for optional property assignment highlighting + ]); + + // TS gets a simpler shebang rule than JS + swapMode(tsLanguage, "shebang", hljs.SHEBANG()); + // JS use strict rule purposely excludes `asm` which makes no sense + swapMode(tsLanguage, "use_strict", USE_STRICT); + + const functionDeclaration = tsLanguage.contains.find(m => m.label === "func.def"); + functionDeclaration.relevance = 0; // () => {} is more typical in TypeScript + + Object.assign(tsLanguage, { + name: 'TypeScript', + aliases: [ + 'ts', + 'tsx', + 'mts', + 'cts' + ] + }); + + return tsLanguage; +} + +export { typescript as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/typescript.js.js b/frontend/node_modules/highlight.js/es/languages/typescript.js.js new file mode 100644 index 0000000..aefe18c --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/typescript.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/typescript" instead of "highlight.js/lib/languages/typescript.js"' + ); + } + } + emitWarning(); + import lang from './typescript.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/vala.js b/frontend/node_modules/highlight.js/es/languages/vala.js new file mode 100644 index 0000000..52c2796 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/vala.js @@ -0,0 +1,61 @@ +/* +Language: Vala +Author: Antono Vasiljev +Description: Vala is a new programming language that aims to bring modern programming language features to GNOME developers without imposing any additional runtime requirements and without using a different ABI compared to applications and libraries written in C. +Website: https://wiki.gnome.org/Projects/Vala +Category: system +*/ + +function vala(hljs) { + return { + name: 'Vala', + keywords: { + keyword: + // Value types + 'char uchar unichar int uint long ulong short ushort int8 int16 int32 int64 uint8 ' + + 'uint16 uint32 uint64 float double bool struct enum string void ' + // Reference types + + 'weak unowned owned ' + // Modifiers + + 'async signal static abstract interface override virtual delegate ' + // Control Structures + + 'if while do for foreach else switch case break default return try catch ' + // Visibility + + 'public private protected internal ' + // Other + + 'using new this get set const stdout stdin stderr var', + built_in: + 'DBus GLib CCode Gee Object Gtk Posix', + literal: + 'false true null' + }, + contains: [ + { + className: 'class', + beginKeywords: 'class interface namespace', + end: /\{/, + excludeEnd: true, + illegal: '[^,:\\n\\s\\.]', + contains: [ hljs.UNDERSCORE_TITLE_MODE ] + }, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + { + className: 'string', + begin: '"""', + end: '"""', + relevance: 5 + }, + hljs.APOS_STRING_MODE, + hljs.QUOTE_STRING_MODE, + hljs.C_NUMBER_MODE, + { + className: 'meta', + begin: '^#', + end: '$', + } + ] + }; +} + +export { vala as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/vala.js.js b/frontend/node_modules/highlight.js/es/languages/vala.js.js new file mode 100644 index 0000000..754999e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/vala.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/vala" instead of "highlight.js/lib/languages/vala.js"' + ); + } + } + emitWarning(); + import lang from './vala.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/vbnet.js b/frontend/node_modules/highlight.js/es/languages/vbnet.js new file mode 100644 index 0000000..ebd6dae --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/vbnet.js @@ -0,0 +1,157 @@ +/* +Language: Visual Basic .NET +Description: Visual Basic .NET (VB.NET) is a multi-paradigm, object-oriented programming language, implemented on the .NET Framework. +Authors: Poren Chiang , Jan Pilzer +Website: https://docs.microsoft.com/dotnet/visual-basic/getting-started +Category: common +*/ + +/** @type LanguageFn */ +function vbnet(hljs) { + const regex = hljs.regex; + /** + * Character Literal + * Either a single character ("a"C) or an escaped double quote (""""C). + */ + const CHARACTER = { + className: 'string', + begin: /"(""|[^/n])"C\b/ + }; + + const STRING = { + className: 'string', + begin: /"/, + end: /"/, + illegal: /\n/, + contains: [ + { + // double quote escape + begin: /""/ } + ] + }; + + /** Date Literals consist of a date, a time, or both separated by whitespace, surrounded by # */ + const MM_DD_YYYY = /\d{1,2}\/\d{1,2}\/\d{4}/; + const YYYY_MM_DD = /\d{4}-\d{1,2}-\d{1,2}/; + const TIME_12H = /(\d|1[012])(:\d+){0,2} *(AM|PM)/; + const TIME_24H = /\d{1,2}(:\d{1,2}){1,2}/; + const DATE = { + className: 'literal', + variants: [ + { + // #YYYY-MM-DD# (ISO-Date) or #M/D/YYYY# (US-Date) + begin: regex.concat(/# */, regex.either(YYYY_MM_DD, MM_DD_YYYY), / *#/) }, + { + // #H:mm[:ss]# (24h Time) + begin: regex.concat(/# */, TIME_24H, / *#/) }, + { + // #h[:mm[:ss]] A# (12h Time) + begin: regex.concat(/# */, TIME_12H, / *#/) }, + { + // date plus time + begin: regex.concat( + /# */, + regex.either(YYYY_MM_DD, MM_DD_YYYY), + / +/, + regex.either(TIME_12H, TIME_24H), + / *#/ + ) } + ] + }; + + const NUMBER = { + className: 'number', + relevance: 0, + variants: [ + { + // Float + begin: /\b\d[\d_]*((\.[\d_]+(E[+-]?[\d_]+)?)|(E[+-]?[\d_]+))[RFD@!#]?/ }, + { + // Integer (base 10) + begin: /\b\d[\d_]*((U?[SIL])|[%&])?/ }, + { + // Integer (base 16) + begin: /&H[\dA-F_]+((U?[SIL])|[%&])?/ }, + { + // Integer (base 8) + begin: /&O[0-7_]+((U?[SIL])|[%&])?/ }, + { + // Integer (base 2) + begin: /&B[01_]+((U?[SIL])|[%&])?/ } + ] + }; + + const LABEL = { + className: 'label', + begin: /^\w+:/ + }; + + const DOC_COMMENT = hljs.COMMENT(/'''/, /$/, { contains: [ + { + className: 'doctag', + begin: /<\/?/, + end: />/ + } + ] }); + + const COMMENT = hljs.COMMENT(null, /$/, { variants: [ + { begin: /'/ }, + { + // TODO: Use multi-class for leading spaces + begin: /([\t ]|^)REM(?=\s)/ } + ] }); + + const DIRECTIVES = { + className: 'meta', + // TODO: Use multi-class for indentation once available + begin: /[\t ]*#(const|disable|else|elseif|enable|end|externalsource|if|region)\b/, + end: /$/, + keywords: { keyword: + 'const disable else elseif enable end externalsource if region then' }, + contains: [ COMMENT ] + }; + + return { + name: 'Visual Basic .NET', + aliases: [ 'vb' ], + case_insensitive: true, + classNameAliases: { label: 'symbol' }, + keywords: { + keyword: + 'addhandler alias aggregate ansi as async assembly auto binary by byref byval ' /* a-b */ + + 'call case catch class compare const continue custom declare default delegate dim distinct do ' /* c-d */ + + 'each equals else elseif end enum erase error event exit explicit finally for friend from function ' /* e-f */ + + 'get global goto group handles if implements imports in inherits interface into iterator ' /* g-i */ + + 'join key let lib loop me mid module mustinherit mustoverride mybase myclass ' /* j-m */ + + 'namespace narrowing new next notinheritable notoverridable ' /* n */ + + 'of off on operator option optional order overloads overridable overrides ' /* o */ + + 'paramarray partial preserve private property protected public ' /* p */ + + 'raiseevent readonly redim removehandler resume return ' /* r */ + + 'select set shadows shared skip static step stop structure strict sub synclock ' /* s */ + + 'take text then throw to try unicode until using when where while widening with withevents writeonly yield' /* t-y */, + built_in: + // Operators https://docs.microsoft.com/dotnet/visual-basic/language-reference/operators + 'addressof and andalso await directcast gettype getxmlnamespace is isfalse isnot istrue like mod nameof new not or orelse trycast typeof xor ' + // Type Conversion Functions https://docs.microsoft.com/dotnet/visual-basic/language-reference/functions/type-conversion-functions + + 'cbool cbyte cchar cdate cdbl cdec cint clng cobj csbyte cshort csng cstr cuint culng cushort', + type: + // Data types https://docs.microsoft.com/dotnet/visual-basic/language-reference/data-types + 'boolean byte char date decimal double integer long object sbyte short single string uinteger ulong ushort', + literal: 'true false nothing' + }, + illegal: + '//|\\{|\\}|endif|gosub|variant|wend|^\\$ ' /* reserved deprecated keywords */, + contains: [ + CHARACTER, + STRING, + DATE, + NUMBER, + LABEL, + DOC_COMMENT, + COMMENT, + DIRECTIVES + ] + }; +} + +export { vbnet as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/vbnet.js.js b/frontend/node_modules/highlight.js/es/languages/vbnet.js.js new file mode 100644 index 0000000..e7a09c2 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/vbnet.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/vbnet" instead of "highlight.js/lib/languages/vbnet.js"' + ); + } + } + emitWarning(); + import lang from './vbnet.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/vbscript-html.js b/frontend/node_modules/highlight.js/es/languages/vbscript-html.js new file mode 100644 index 0000000..0c3c16e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/vbscript-html.js @@ -0,0 +1,24 @@ +/* +Language: VBScript in HTML +Requires: xml.js, vbscript.js +Author: Ivan Sagalaev +Description: "Bridge" language defining fragments of VBScript in HTML within <% .. %> +Website: https://en.wikipedia.org/wiki/VBScript +Category: scripting +*/ + +function vbscriptHtml(hljs) { + return { + name: 'VBScript in HTML', + subLanguage: 'xml', + contains: [ + { + begin: '<%', + end: '%>', + subLanguage: 'vbscript' + } + ] + }; +} + +export { vbscriptHtml as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/vbscript-html.js.js b/frontend/node_modules/highlight.js/es/languages/vbscript-html.js.js new file mode 100644 index 0000000..f13724b --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/vbscript-html.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/vbscript-html" instead of "highlight.js/lib/languages/vbscript-html.js"' + ); + } + } + emitWarning(); + import lang from './vbscript-html.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/vbscript.js b/frontend/node_modules/highlight.js/es/languages/vbscript.js new file mode 100644 index 0000000..691637d --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/vbscript.js @@ -0,0 +1,220 @@ +/* +Language: VBScript +Description: VBScript ("Microsoft Visual Basic Scripting Edition") is an Active Scripting language developed by Microsoft that is modeled on Visual Basic. +Author: Nikita Ledyaev +Contributors: Michal Gabrukiewicz +Website: https://en.wikipedia.org/wiki/VBScript +Category: scripting +*/ + +/** @type LanguageFn */ +function vbscript(hljs) { + const regex = hljs.regex; + const BUILT_IN_FUNCTIONS = [ + "lcase", + "month", + "vartype", + "instrrev", + "ubound", + "setlocale", + "getobject", + "rgb", + "getref", + "string", + "weekdayname", + "rnd", + "dateadd", + "monthname", + "now", + "day", + "minute", + "isarray", + "cbool", + "round", + "formatcurrency", + "conversions", + "csng", + "timevalue", + "second", + "year", + "space", + "abs", + "clng", + "timeserial", + "fixs", + "len", + "asc", + "isempty", + "maths", + "dateserial", + "atn", + "timer", + "isobject", + "filter", + "weekday", + "datevalue", + "ccur", + "isdate", + "instr", + "datediff", + "formatdatetime", + "replace", + "isnull", + "right", + "sgn", + "array", + "snumeric", + "log", + "cdbl", + "hex", + "chr", + "lbound", + "msgbox", + "ucase", + "getlocale", + "cos", + "cdate", + "cbyte", + "rtrim", + "join", + "hour", + "oct", + "typename", + "trim", + "strcomp", + "int", + "createobject", + "loadpicture", + "tan", + "formatnumber", + "mid", + "split", + "cint", + "sin", + "datepart", + "ltrim", + "sqr", + "time", + "derived", + "eval", + "date", + "formatpercent", + "exp", + "inputbox", + "left", + "ascw", + "chrw", + "regexp", + "cstr", + "err" + ]; + const BUILT_IN_OBJECTS = [ + "server", + "response", + "request", + // take no arguments so can be called without () + "scriptengine", + "scriptenginebuildversion", + "scriptengineminorversion", + "scriptenginemajorversion" + ]; + + const BUILT_IN_CALL = { + begin: regex.concat(regex.either(...BUILT_IN_FUNCTIONS), "\\s*\\("), + // relevance 0 because this is acting as a beginKeywords really + relevance: 0, + keywords: { built_in: BUILT_IN_FUNCTIONS } + }; + + const LITERALS = [ + "true", + "false", + "null", + "nothing", + "empty" + ]; + + const KEYWORDS = [ + "call", + "class", + "const", + "dim", + "do", + "loop", + "erase", + "execute", + "executeglobal", + "exit", + "for", + "each", + "next", + "function", + "if", + "then", + "else", + "on", + "error", + "option", + "explicit", + "new", + "private", + "property", + "let", + "get", + "public", + "randomize", + "redim", + "rem", + "select", + "case", + "set", + "stop", + "sub", + "while", + "wend", + "with", + "end", + "to", + "elseif", + "is", + "or", + "xor", + "and", + "not", + "class_initialize", + "class_terminate", + "default", + "preserve", + "in", + "me", + "byval", + "byref", + "step", + "resume", + "goto" + ]; + + return { + name: 'VBScript', + aliases: [ 'vbs' ], + case_insensitive: true, + keywords: { + keyword: KEYWORDS, + built_in: BUILT_IN_OBJECTS, + literal: LITERALS + }, + illegal: '//', + contains: [ + BUILT_IN_CALL, + hljs.inherit(hljs.QUOTE_STRING_MODE, { contains: [ { begin: '""' } ] }), + hljs.COMMENT( + /'/, + /$/, + { relevance: 0 } + ), + hljs.C_NUMBER_MODE + ] + }; +} + +export { vbscript as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/vbscript.js.js b/frontend/node_modules/highlight.js/es/languages/vbscript.js.js new file mode 100644 index 0000000..e3df308 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/vbscript.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/vbscript" instead of "highlight.js/lib/languages/vbscript.js"' + ); + } + } + emitWarning(); + import lang from './vbscript.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/verilog.js b/frontend/node_modules/highlight.js/es/languages/verilog.js new file mode 100644 index 0000000..3281813 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/verilog.js @@ -0,0 +1,550 @@ +/* +Language: Verilog +Author: Jon Evans +Contributors: Boone Severson +Description: Verilog is a hardware description language used in electronic design automation to describe digital and mixed-signal systems. This highlighter supports Verilog and SystemVerilog through IEEE 1800-2012. +Website: http://www.verilog.com +Category: hardware +*/ + +function verilog(hljs) { + const regex = hljs.regex; + const KEYWORDS = { + $pattern: /\$?[\w]+(\$[\w]+)*/, + keyword: [ + "accept_on", + "alias", + "always", + "always_comb", + "always_ff", + "always_latch", + "and", + "assert", + "assign", + "assume", + "automatic", + "before", + "begin", + "bind", + "bins", + "binsof", + "bit", + "break", + "buf|0", + "bufif0", + "bufif1", + "byte", + "case", + "casex", + "casez", + "cell", + "chandle", + "checker", + "class", + "clocking", + "cmos", + "config", + "const", + "constraint", + "context", + "continue", + "cover", + "covergroup", + "coverpoint", + "cross", + "deassign", + "default", + "defparam", + "design", + "disable", + "dist", + "do", + "edge", + "else", + "end", + "endcase", + "endchecker", + "endclass", + "endclocking", + "endconfig", + "endfunction", + "endgenerate", + "endgroup", + "endinterface", + "endmodule", + "endpackage", + "endprimitive", + "endprogram", + "endproperty", + "endspecify", + "endsequence", + "endtable", + "endtask", + "enum", + "event", + "eventually", + "expect", + "export", + "extends", + "extern", + "final", + "first_match", + "for", + "force", + "foreach", + "forever", + "fork", + "forkjoin", + "function", + "generate|5", + "genvar", + "global", + "highz0", + "highz1", + "if", + "iff", + "ifnone", + "ignore_bins", + "illegal_bins", + "implements", + "implies", + "import", + "incdir", + "include", + "initial", + "inout", + "input", + "inside", + "instance", + "int", + "integer", + "interconnect", + "interface", + "intersect", + "join", + "join_any", + "join_none", + "large", + "let", + "liblist", + "library", + "local", + "localparam", + "logic", + "longint", + "macromodule", + "matches", + "medium", + "modport", + "module", + "nand", + "negedge", + "nettype", + "new", + "nexttime", + "nmos", + "nor", + "noshowcancelled", + "not", + "notif0", + "notif1", + "or", + "output", + "package", + "packed", + "parameter", + "pmos", + "posedge", + "primitive", + "priority", + "program", + "property", + "protected", + "pull0", + "pull1", + "pulldown", + "pullup", + "pulsestyle_ondetect", + "pulsestyle_onevent", + "pure", + "rand", + "randc", + "randcase", + "randsequence", + "rcmos", + "real", + "realtime", + "ref", + "reg", + "reject_on", + "release", + "repeat", + "restrict", + "return", + "rnmos", + "rpmos", + "rtran", + "rtranif0", + "rtranif1", + "s_always", + "s_eventually", + "s_nexttime", + "s_until", + "s_until_with", + "scalared", + "sequence", + "shortint", + "shortreal", + "showcancelled", + "signed", + "small", + "soft", + "solve", + "specify", + "specparam", + "static", + "string", + "strong", + "strong0", + "strong1", + "struct", + "super", + "supply0", + "supply1", + "sync_accept_on", + "sync_reject_on", + "table", + "tagged", + "task", + "this", + "throughout", + "time", + "timeprecision", + "timeunit", + "tran", + "tranif0", + "tranif1", + "tri", + "tri0", + "tri1", + "triand", + "trior", + "trireg", + "type", + "typedef", + "union", + "unique", + "unique0", + "unsigned", + "until", + "until_with", + "untyped", + "use", + "uwire", + "var", + "vectored", + "virtual", + "void", + "wait", + "wait_order", + "wand", + "weak", + "weak0", + "weak1", + "while", + "wildcard", + "wire", + "with", + "within", + "wor", + "xnor", + "xor" + ], + literal: [ 'null' ], + built_in: [ + "$finish", + "$stop", + "$exit", + "$fatal", + "$error", + "$warning", + "$info", + "$realtime", + "$time", + "$printtimescale", + "$bitstoreal", + "$bitstoshortreal", + "$itor", + "$signed", + "$cast", + "$bits", + "$stime", + "$timeformat", + "$realtobits", + "$shortrealtobits", + "$rtoi", + "$unsigned", + "$asserton", + "$assertkill", + "$assertpasson", + "$assertfailon", + "$assertnonvacuouson", + "$assertoff", + "$assertcontrol", + "$assertpassoff", + "$assertfailoff", + "$assertvacuousoff", + "$isunbounded", + "$sampled", + "$fell", + "$changed", + "$past_gclk", + "$fell_gclk", + "$changed_gclk", + "$rising_gclk", + "$steady_gclk", + "$coverage_control", + "$coverage_get", + "$coverage_save", + "$set_coverage_db_name", + "$rose", + "$stable", + "$past", + "$rose_gclk", + "$stable_gclk", + "$future_gclk", + "$falling_gclk", + "$changing_gclk", + "$display", + "$coverage_get_max", + "$coverage_merge", + "$get_coverage", + "$load_coverage_db", + "$typename", + "$unpacked_dimensions", + "$left", + "$low", + "$increment", + "$clog2", + "$ln", + "$log10", + "$exp", + "$sqrt", + "$pow", + "$floor", + "$ceil", + "$sin", + "$cos", + "$tan", + "$countbits", + "$onehot", + "$isunknown", + "$fatal", + "$warning", + "$dimensions", + "$right", + "$high", + "$size", + "$asin", + "$acos", + "$atan", + "$atan2", + "$hypot", + "$sinh", + "$cosh", + "$tanh", + "$asinh", + "$acosh", + "$atanh", + "$countones", + "$onehot0", + "$error", + "$info", + "$random", + "$dist_chi_square", + "$dist_erlang", + "$dist_exponential", + "$dist_normal", + "$dist_poisson", + "$dist_t", + "$dist_uniform", + "$q_initialize", + "$q_remove", + "$q_exam", + "$async$and$array", + "$async$nand$array", + "$async$or$array", + "$async$nor$array", + "$sync$and$array", + "$sync$nand$array", + "$sync$or$array", + "$sync$nor$array", + "$q_add", + "$q_full", + "$psprintf", + "$async$and$plane", + "$async$nand$plane", + "$async$or$plane", + "$async$nor$plane", + "$sync$and$plane", + "$sync$nand$plane", + "$sync$or$plane", + "$sync$nor$plane", + "$system", + "$display", + "$displayb", + "$displayh", + "$displayo", + "$strobe", + "$strobeb", + "$strobeh", + "$strobeo", + "$write", + "$readmemb", + "$readmemh", + "$writememh", + "$value$plusargs", + "$dumpvars", + "$dumpon", + "$dumplimit", + "$dumpports", + "$dumpportson", + "$dumpportslimit", + "$writeb", + "$writeh", + "$writeo", + "$monitor", + "$monitorb", + "$monitorh", + "$monitoro", + "$writememb", + "$dumpfile", + "$dumpoff", + "$dumpall", + "$dumpflush", + "$dumpportsoff", + "$dumpportsall", + "$dumpportsflush", + "$fclose", + "$fdisplay", + "$fdisplayb", + "$fdisplayh", + "$fdisplayo", + "$fstrobe", + "$fstrobeb", + "$fstrobeh", + "$fstrobeo", + "$swrite", + "$swriteb", + "$swriteh", + "$swriteo", + "$fscanf", + "$fread", + "$fseek", + "$fflush", + "$feof", + "$fopen", + "$fwrite", + "$fwriteb", + "$fwriteh", + "$fwriteo", + "$fmonitor", + "$fmonitorb", + "$fmonitorh", + "$fmonitoro", + "$sformat", + "$sformatf", + "$fgetc", + "$ungetc", + "$fgets", + "$sscanf", + "$rewind", + "$ftell", + "$ferror" + ] + }; + const BUILT_IN_CONSTANTS = [ + "__FILE__", + "__LINE__" + ]; + const DIRECTIVES = [ + "begin_keywords", + "celldefine", + "default_nettype", + "default_decay_time", + "default_trireg_strength", + "define", + "delay_mode_distributed", + "delay_mode_path", + "delay_mode_unit", + "delay_mode_zero", + "else", + "elsif", + "end_keywords", + "endcelldefine", + "endif", + "ifdef", + "ifndef", + "include", + "line", + "nounconnected_drive", + "pragma", + "resetall", + "timescale", + "unconnected_drive", + "undef", + "undefineall" + ]; + + return { + name: 'Verilog', + aliases: [ + 'v', + 'sv', + 'svh' + ], + case_insensitive: false, + keywords: KEYWORDS, + contains: [ + hljs.C_BLOCK_COMMENT_MODE, + hljs.C_LINE_COMMENT_MODE, + hljs.QUOTE_STRING_MODE, + { + scope: 'number', + contains: [ hljs.BACKSLASH_ESCAPE ], + variants: [ + { begin: /\b((\d+'([bhodBHOD]))[0-9xzXZa-fA-F_]+)/ }, + { begin: /\B(('([bhodBHOD]))[0-9xzXZa-fA-F_]+)/ }, + { // decimal + begin: /\b[0-9][0-9_]*/, + relevance: 0 + } + ] + }, + /* parameters to instances */ + { + scope: 'variable', + variants: [ + { begin: '#\\((?!parameter).+\\)' }, + { + begin: '\\.\\w+', + relevance: 0 + } + ] + }, + { + scope: 'variable.constant', + match: regex.concat(/`/, regex.either(...BUILT_IN_CONSTANTS)), + }, + { + scope: 'meta', + begin: regex.concat(/`/, regex.either(...DIRECTIVES)), + end: /$|\/\/|\/\*/, + returnEnd: true, + keywords: DIRECTIVES + } + ] + }; +} + +export { verilog as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/verilog.js.js b/frontend/node_modules/highlight.js/es/languages/verilog.js.js new file mode 100644 index 0000000..2dc028f --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/verilog.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/verilog" instead of "highlight.js/lib/languages/verilog.js"' + ); + } + } + emitWarning(); + import lang from './verilog.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/vhdl.js b/frontend/node_modules/highlight.js/es/languages/vhdl.js new file mode 100644 index 0000000..89e2047 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/vhdl.js @@ -0,0 +1,216 @@ +/* +Language: VHDL +Author: Igor Kalnitsky +Contributors: Daniel C.K. Kho , Guillaume Savaton +Description: VHDL is a hardware description language used in electronic design automation to describe digital and mixed-signal systems. +Website: https://en.wikipedia.org/wiki/VHDL +Category: hardware +*/ + +function vhdl(hljs) { + // Regular expression for VHDL numeric literals. + + // Decimal literal: + const INTEGER_RE = '\\d(_|\\d)*'; + const EXPONENT_RE = '[eE][-+]?' + INTEGER_RE; + const DECIMAL_LITERAL_RE = INTEGER_RE + '(\\.' + INTEGER_RE + ')?' + '(' + EXPONENT_RE + ')?'; + // Based literal: + const BASED_INTEGER_RE = '\\w+'; + const BASED_LITERAL_RE = INTEGER_RE + '#' + BASED_INTEGER_RE + '(\\.' + BASED_INTEGER_RE + ')?' + '#' + '(' + EXPONENT_RE + ')?'; + + const NUMBER_RE = '\\b(' + BASED_LITERAL_RE + '|' + DECIMAL_LITERAL_RE + ')'; + + const KEYWORDS = [ + "abs", + "access", + "after", + "alias", + "all", + "and", + "architecture", + "array", + "assert", + "assume", + "assume_guarantee", + "attribute", + "begin", + "block", + "body", + "buffer", + "bus", + "case", + "component", + "configuration", + "constant", + "context", + "cover", + "disconnect", + "downto", + "default", + "else", + "elsif", + "end", + "entity", + "exit", + "fairness", + "file", + "for", + "force", + "function", + "generate", + "generic", + "group", + "guarded", + "if", + "impure", + "in", + "inertial", + "inout", + "is", + "label", + "library", + "linkage", + "literal", + "loop", + "map", + "mod", + "nand", + "new", + "next", + "nor", + "not", + "null", + "of", + "on", + "open", + "or", + "others", + "out", + "package", + "parameter", + "port", + "postponed", + "procedure", + "process", + "property", + "protected", + "pure", + "range", + "record", + "register", + "reject", + "release", + "rem", + "report", + "restrict", + "restrict_guarantee", + "return", + "rol", + "ror", + "select", + "sequence", + "severity", + "shared", + "signal", + "sla", + "sll", + "sra", + "srl", + "strong", + "subtype", + "then", + "to", + "transport", + "type", + "unaffected", + "units", + "until", + "use", + "variable", + "view", + "vmode", + "vprop", + "vunit", + "wait", + "when", + "while", + "with", + "xnor", + "xor" + ]; + const BUILT_INS = [ + "boolean", + "bit", + "character", + "integer", + "time", + "delay_length", + "natural", + "positive", + "string", + "bit_vector", + "file_open_kind", + "file_open_status", + "std_logic", + "std_logic_vector", + "unsigned", + "signed", + "boolean_vector", + "integer_vector", + "std_ulogic", + "std_ulogic_vector", + "unresolved_unsigned", + "u_unsigned", + "unresolved_signed", + "u_signed", + "real_vector", + "time_vector" + ]; + const LITERALS = [ + // severity_level + "false", + "true", + "note", + "warning", + "error", + "failure", + // textio + "line", + "text", + "side", + "width" + ]; + + return { + name: 'VHDL', + case_insensitive: true, + keywords: { + keyword: KEYWORDS, + built_in: BUILT_INS, + literal: LITERALS + }, + illegal: /\{/, + contains: [ + hljs.C_BLOCK_COMMENT_MODE, // VHDL-2008 block commenting. + hljs.COMMENT('--', '$'), + hljs.QUOTE_STRING_MODE, + { + className: 'number', + begin: NUMBER_RE, + relevance: 0 + }, + { + className: 'string', + begin: '\'(U|X|0|1|Z|W|L|H|-)\'', + contains: [ hljs.BACKSLASH_ESCAPE ] + }, + { + className: 'symbol', + begin: '\'[A-Za-z](_?[A-Za-z0-9])*', + contains: [ hljs.BACKSLASH_ESCAPE ] + } + ] + }; +} + +export { vhdl as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/vhdl.js.js b/frontend/node_modules/highlight.js/es/languages/vhdl.js.js new file mode 100644 index 0000000..237e2b3 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/vhdl.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/vhdl" instead of "highlight.js/lib/languages/vhdl.js"' + ); + } + } + emitWarning(); + import lang from './vhdl.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/vim.js b/frontend/node_modules/highlight.js/es/languages/vim.js new file mode 100644 index 0000000..bbc6ce0 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/vim.js @@ -0,0 +1,129 @@ +/* +Language: Vim Script +Author: Jun Yang +Description: full keyword and built-in from http://vimdoc.sourceforge.net/htmldoc/ +Website: https://www.vim.org +Category: scripting +*/ + +function vim(hljs) { + return { + name: 'Vim Script', + keywords: { + $pattern: /[!#@\w]+/, + keyword: + // express version except: ! & * < = > !! # @ @@ + 'N|0 P|0 X|0 a|0 ab abc abo al am an|0 ar arga argd arge argdo argg argl argu as au aug aun b|0 bN ba bad bd be bel bf bl bm bn bo bp br brea breaka breakd breakl bro bufdo buffers bun bw c|0 cN cNf ca cabc caddb cad caddf cal cat cb cc ccl cd ce cex cf cfir cgetb cgete cg changes chd che checkt cl cla clo cm cmapc cme cn cnew cnf cno cnorea cnoreme co col colo com comc comp con conf cope ' + + 'cp cpf cq cr cs cst cu cuna cunme cw delm deb debugg delc delf dif diffg diffo diffp diffpu diffs diffthis dig di dl dell dj dli do doautoa dp dr ds dsp e|0 ea ec echoe echoh echom echon el elsei em en endfo endf endt endw ene ex exe exi exu f|0 files filet fin fina fini fir fix fo foldc foldd folddoc foldo for fu go gr grepa gu gv ha helpf helpg helpt hi hid his ia iabc if ij il im imapc ' + + 'ime ino inorea inoreme int is isp iu iuna iunme j|0 ju k|0 keepa kee keepj lN lNf l|0 lad laddb laddf la lan lat lb lc lch lcl lcs le lefta let lex lf lfir lgetb lgete lg lgr lgrepa lh ll lla lli lmak lm lmapc lne lnew lnf ln loadk lo loc lockv lol lope lp lpf lr ls lt lu lua luad luaf lv lvimgrepa lw m|0 ma mak map mapc marks mat me menut mes mk mks mksp mkv mkvie mod mz mzf nbc nb nbs new nm nmapc nme nn nnoreme noa no noh norea noreme norm nu nun nunme ol o|0 om omapc ome on ono onoreme opt ou ounme ow p|0 ' + + 'profd prof pro promptr pc ped pe perld po popu pp pre prev ps pt ptN ptf ptj ptl ptn ptp ptr pts pu pw py3 python3 py3d py3f py pyd pyf quita qa rec red redi redr redraws reg res ret retu rew ri rightb rub rubyd rubyf rund ru rv sN san sa sal sav sb sbN sba sbf sbl sbm sbn sbp sbr scrip scripte scs se setf setg setl sf sfir sh sim sig sil sl sla sm smap smapc sme sn sni sno snor snoreme sor ' + + 'so spelld spe spelli spellr spellu spellw sp spr sre st sta startg startr star stopi stj sts sun sunm sunme sus sv sw sy synti sync tN tabN tabc tabdo tabe tabf tabfir tabl tabm tabnew ' + + 'tabn tabo tabp tabr tabs tab ta tags tc tcld tclf te tf th tj tl tm tn to tp tr try ts tu u|0 undoj undol una unh unl unlo unm unme uns up ve verb vert vim vimgrepa vi viu vie vm vmapc vme vne vn vnoreme vs vu vunme windo w|0 wN wa wh wi winc winp wn wp wq wqa ws wu wv x|0 xa xmapc xm xme xn xnoreme xu xunme y|0 z|0 ~ ' + // full version + + 'Next Print append abbreviate abclear aboveleft all amenu anoremenu args argadd argdelete argedit argglobal arglocal argument ascii autocmd augroup aunmenu buffer bNext ball badd bdelete behave belowright bfirst blast bmodified bnext botright bprevious brewind break breakadd breakdel breaklist browse bunload ' + + 'bwipeout change cNext cNfile cabbrev cabclear caddbuffer caddexpr caddfile call catch cbuffer cclose center cexpr cfile cfirst cgetbuffer cgetexpr cgetfile chdir checkpath checktime clist clast close cmap cmapclear cmenu cnext cnewer cnfile cnoremap cnoreabbrev cnoremenu copy colder colorscheme command comclear compiler continue confirm copen cprevious cpfile cquit crewind cscope cstag cunmap ' + + 'cunabbrev cunmenu cwindow delete delmarks debug debuggreedy delcommand delfunction diffupdate diffget diffoff diffpatch diffput diffsplit digraphs display deletel djump dlist doautocmd doautoall deletep drop dsearch dsplit edit earlier echo echoerr echohl echomsg else elseif emenu endif endfor ' + + 'endfunction endtry endwhile enew execute exit exusage file filetype find finally finish first fixdel fold foldclose folddoopen folddoclosed foldopen function global goto grep grepadd gui gvim hardcopy help helpfind helpgrep helptags highlight hide history insert iabbrev iabclear ijump ilist imap ' + + 'imapclear imenu inoremap inoreabbrev inoremenu intro isearch isplit iunmap iunabbrev iunmenu join jumps keepalt keepmarks keepjumps lNext lNfile list laddexpr laddbuffer laddfile last language later lbuffer lcd lchdir lclose lcscope left leftabove lexpr lfile lfirst lgetbuffer lgetexpr lgetfile lgrep lgrepadd lhelpgrep llast llist lmake lmap lmapclear lnext lnewer lnfile lnoremap loadkeymap loadview ' + + 'lockmarks lockvar lolder lopen lprevious lpfile lrewind ltag lunmap luado luafile lvimgrep lvimgrepadd lwindow move mark make mapclear match menu menutranslate messages mkexrc mksession mkspell mkvimrc mkview mode mzscheme mzfile nbclose nbkey nbsart next nmap nmapclear nmenu nnoremap ' + + 'nnoremenu noautocmd noremap nohlsearch noreabbrev noremenu normal number nunmap nunmenu oldfiles open omap omapclear omenu only onoremap onoremenu options ounmap ounmenu ownsyntax print profdel profile promptfind promptrepl pclose pedit perl perldo pop popup ppop preserve previous psearch ptag ptNext ' + + 'ptfirst ptjump ptlast ptnext ptprevious ptrewind ptselect put pwd py3do py3file python pydo pyfile quit quitall qall read recover redo redir redraw redrawstatus registers resize retab return rewind right rightbelow ruby rubydo rubyfile rundo runtime rviminfo substitute sNext sandbox sargument sall saveas sbuffer sbNext sball sbfirst sblast sbmodified sbnext sbprevious sbrewind scriptnames scriptencoding ' + + 'scscope set setfiletype setglobal setlocal sfind sfirst shell simalt sign silent sleep slast smagic smapclear smenu snext sniff snomagic snoremap snoremenu sort source spelldump spellgood spellinfo spellrepall spellundo spellwrong split sprevious srewind stop stag startgreplace startreplace ' + + 'startinsert stopinsert stjump stselect sunhide sunmap sunmenu suspend sview swapname syntax syntime syncbind tNext tabNext tabclose tabedit tabfind tabfirst tablast tabmove tabnext tabonly tabprevious tabrewind tag tcl tcldo tclfile tearoff tfirst throw tjump tlast tmenu tnext topleft tprevious ' + 'trewind tselect tunmenu undo undojoin undolist unabbreviate unhide unlet unlockvar unmap unmenu unsilent update vglobal version verbose vertical vimgrep vimgrepadd visual viusage view vmap vmapclear vmenu vnew ' + + 'vnoremap vnoremenu vsplit vunmap vunmenu write wNext wall while winsize wincmd winpos wnext wprevious wqall wsverb wundo wviminfo xit xall xmapclear xmap xmenu xnoremap xnoremenu xunmap xunmenu yank', + built_in: // built in func + 'synIDtrans atan2 range matcharg did_filetype asin feedkeys xor argv ' + + 'complete_check add getwinposx getqflist getwinposy screencol ' + + 'clearmatches empty extend getcmdpos mzeval garbagecollect setreg ' + + 'ceil sqrt diff_hlID inputsecret get getfperm getpid filewritable ' + + 'shiftwidth max sinh isdirectory synID system inputrestore winline ' + + 'atan visualmode inputlist tabpagewinnr round getregtype mapcheck ' + + 'hasmapto histdel argidx findfile sha256 exists toupper getcmdline ' + + 'taglist string getmatches bufnr strftime winwidth bufexists ' + + 'strtrans tabpagebuflist setcmdpos remote_read printf setloclist ' + + 'getpos getline bufwinnr float2nr len getcmdtype diff_filler luaeval ' + + 'resolve libcallnr foldclosedend reverse filter has_key bufname ' + + 'str2float strlen setline getcharmod setbufvar index searchpos ' + + 'shellescape undofile foldclosed setqflist buflisted strchars str2nr ' + + 'virtcol floor remove undotree remote_expr winheight gettabwinvar ' + + 'reltime cursor tabpagenr finddir localtime acos getloclist search ' + + 'tanh matchend rename gettabvar strdisplaywidth type abs py3eval ' + + 'setwinvar tolower wildmenumode log10 spellsuggest bufloaded ' + + 'synconcealed nextnonblank server2client complete settabwinvar ' + + 'executable input wincol setmatches getftype hlID inputsave ' + + 'searchpair or screenrow line settabvar histadd deepcopy strpart ' + + 'remote_peek and eval getftime submatch screenchar winsaveview ' + + 'matchadd mkdir screenattr getfontname libcall reltimestr getfsize ' + + 'winnr invert pow getbufline byte2line soundfold repeat fnameescape ' + + 'tagfiles sin strwidth spellbadword trunc maparg log lispindent ' + + 'hostname setpos globpath remote_foreground getchar synIDattr ' + + 'fnamemodify cscope_connection stridx winbufnr indent min ' + + 'complete_add nr2char searchpairpos inputdialog values matchlist ' + + 'items hlexists strridx browsedir expand fmod pathshorten line2byte ' + + 'argc count getwinvar glob foldtextresult getreg foreground cosh ' + + 'matchdelete has char2nr simplify histget searchdecl iconv ' + + 'winrestcmd pumvisible writefile foldlevel haslocaldir keys cos ' + + 'matchstr foldtext histnr tan tempname getcwd byteidx getbufvar ' + + 'islocked escape eventhandler remote_send serverlist winrestview ' + + 'synstack pyeval prevnonblank readfile cindent filereadable changenr ' + + 'exp' + }, + illegal: /;/, + contains: [ + hljs.NUMBER_MODE, + { + className: 'string', + begin: '\'', + end: '\'', + illegal: '\\n' + }, + + /* + A double quote can start either a string or a line comment. Strings are + ended before the end of a line by another double quote and can contain + escaped double-quotes and post-escaped line breaks. + + Also, any double quote at the beginning of a line is a comment but we + don't handle that properly at the moment: any double quote inside will + turn them into a string. Handling it properly will require a smarter + parser. + */ + { + className: 'string', + begin: /"(\\"|\n\\|[^"\n])*"/ + }, + hljs.COMMENT('"', '$'), + + { + className: 'variable', + begin: /[bwtglsav]:[\w\d_]+/ + }, + { + begin: [ + /\b(?:function|function!)/, + /\s+/, + hljs.IDENT_RE + ], + className: { + 1: "keyword", + 3: "title" + }, + end: '$', + relevance: 0, + contains: [ + { + className: 'params', + begin: '\\(', + end: '\\)' + } + ] + }, + { + className: 'symbol', + begin: /<[\w-]+>/ + } + ] + }; +} + +export { vim as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/vim.js.js b/frontend/node_modules/highlight.js/es/languages/vim.js.js new file mode 100644 index 0000000..e47c5c9 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/vim.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/vim" instead of "highlight.js/lib/languages/vim.js"' + ); + } + } + emitWarning(); + import lang from './vim.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/wasm.js b/frontend/node_modules/highlight.js/es/languages/wasm.js new file mode 100644 index 0000000..611f604 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/wasm.js @@ -0,0 +1,139 @@ +/* +Language: WebAssembly +Website: https://webassembly.org +Description: Wasm is designed as a portable compilation target for programming languages, enabling deployment on the web for client and server applications. +Category: web, common +Audit: 2020 +*/ + +/** @type LanguageFn */ +function wasm(hljs) { + hljs.regex; + const BLOCK_COMMENT = hljs.COMMENT(/\(;/, /;\)/); + BLOCK_COMMENT.contains.push("self"); + const LINE_COMMENT = hljs.COMMENT(/;;/, /$/); + + const KWS = [ + "anyfunc", + "block", + "br", + "br_if", + "br_table", + "call", + "call_indirect", + "data", + "drop", + "elem", + "else", + "end", + "export", + "func", + "global.get", + "global.set", + "local.get", + "local.set", + "local.tee", + "get_global", + "get_local", + "global", + "if", + "import", + "local", + "loop", + "memory", + "memory.grow", + "memory.size", + "module", + "mut", + "nop", + "offset", + "param", + "result", + "return", + "select", + "set_global", + "set_local", + "start", + "table", + "tee_local", + "then", + "type", + "unreachable" + ]; + + const FUNCTION_REFERENCE = { + begin: [ + /(?:func|call|call_indirect)/, + /\s+/, + /\$[^\s)]+/ + ], + className: { + 1: "keyword", + 3: "title.function" + } + }; + + const ARGUMENT = { + className: "variable", + begin: /\$[\w_]+/ + }; + + const PARENS = { + match: /(\((?!;)|\))+/, + className: "punctuation", + relevance: 0 + }; + + const NUMBER = { + className: "number", + relevance: 0, + // borrowed from Prism, TODO: split out into variants + match: /[+-]?\b(?:\d(?:_?\d)*(?:\.\d(?:_?\d)*)?(?:[eE][+-]?\d(?:_?\d)*)?|0x[\da-fA-F](?:_?[\da-fA-F])*(?:\.[\da-fA-F](?:_?[\da-fA-D])*)?(?:[pP][+-]?\d(?:_?\d)*)?)\b|\binf\b|\bnan(?::0x[\da-fA-F](?:_?[\da-fA-D])*)?\b/ + }; + + const TYPE = { + // look-ahead prevents us from gobbling up opcodes + match: /(i32|i64|f32|f64)(?!\.)/, + className: "type" + }; + + const MATH_OPERATIONS = { + className: "keyword", + // borrowed from Prism, TODO: split out into variants + match: /\b(f32|f64|i32|i64)(?:\.(?:abs|add|and|ceil|clz|const|convert_[su]\/i(?:32|64)|copysign|ctz|demote\/f64|div(?:_[su])?|eqz?|extend_[su]\/i32|floor|ge(?:_[su])?|gt(?:_[su])?|le(?:_[su])?|load(?:(?:8|16|32)_[su])?|lt(?:_[su])?|max|min|mul|nearest|neg?|or|popcnt|promote\/f32|reinterpret\/[fi](?:32|64)|rem_[su]|rot[lr]|shl|shr_[su]|store(?:8|16|32)?|sqrt|sub|trunc(?:_[su]\/f(?:32|64))?|wrap\/i64|xor))\b/ + }; + + const OFFSET_ALIGN = { + match: [ + /(?:offset|align)/, + /\s*/, + /=/ + ], + className: { + 1: "keyword", + 3: "operator" + } + }; + + return { + name: 'WebAssembly', + keywords: { + $pattern: /[\w.]+/, + keyword: KWS + }, + contains: [ + LINE_COMMENT, + BLOCK_COMMENT, + OFFSET_ALIGN, + ARGUMENT, + PARENS, + FUNCTION_REFERENCE, + hljs.QUOTE_STRING_MODE, + TYPE, + MATH_OPERATIONS, + NUMBER + ] + }; +} + +export { wasm as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/wasm.js.js b/frontend/node_modules/highlight.js/es/languages/wasm.js.js new file mode 100644 index 0000000..2eb9cda --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/wasm.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/wasm" instead of "highlight.js/lib/languages/wasm.js"' + ); + } + } + emitWarning(); + import lang from './wasm.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/wren.js b/frontend/node_modules/highlight.js/es/languages/wren.js new file mode 100644 index 0000000..8970c9e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/wren.js @@ -0,0 +1,302 @@ +/* +Language: Wren +Description: Think Smalltalk in a Lua-sized package with a dash of Erlang and wrapped up in a familiar, modern syntax. +Category: scripting +Author: @joshgoebel +Maintainer: @joshgoebel +Website: https://wren.io/ +*/ + +/** @type LanguageFn */ +function wren(hljs) { + const regex = hljs.regex; + const IDENT_RE = /[a-zA-Z]\w*/; + const KEYWORDS = [ + "as", + "break", + "class", + "construct", + "continue", + "else", + "for", + "foreign", + "if", + "import", + "in", + "is", + "return", + "static", + "var", + "while" + ]; + const LITERALS = [ + "true", + "false", + "null" + ]; + const LANGUAGE_VARS = [ + "this", + "super" + ]; + const CORE_CLASSES = [ + "Bool", + "Class", + "Fiber", + "Fn", + "List", + "Map", + "Null", + "Num", + "Object", + "Range", + "Sequence", + "String", + "System" + ]; + const OPERATORS = [ + "-", + "~", + /\*/, + "%", + /\.\.\./, + /\.\./, + /\+/, + "<<", + ">>", + ">=", + "<=", + "<", + ">", + /\^/, + /!=/, + /!/, + /\bis\b/, + "==", + "&&", + "&", + /\|\|/, + /\|/, + /\?:/, + "=" + ]; + const FUNCTION = { + relevance: 0, + match: regex.concat(/\b(?!(if|while|for|else|super)\b)/, IDENT_RE, /(?=\s*[({])/), + className: "title.function" + }; + const FUNCTION_DEFINITION = { + match: regex.concat( + regex.either( + regex.concat(/\b(?!(if|while|for|else|super)\b)/, IDENT_RE), + regex.either(...OPERATORS) + ), + /(?=\s*\([^)]+\)\s*\{)/), + className: "title.function", + starts: { contains: [ + { + begin: /\(/, + end: /\)/, + contains: [ + { + relevance: 0, + scope: "params", + match: IDENT_RE + } + ] + } + ] } + }; + const CLASS_DEFINITION = { + variants: [ + { match: [ + /class\s+/, + IDENT_RE, + /\s+is\s+/, + IDENT_RE + ] }, + { match: [ + /class\s+/, + IDENT_RE + ] } + ], + scope: { + 2: "title.class", + 4: "title.class.inherited" + }, + keywords: KEYWORDS + }; + + const OPERATOR = { + relevance: 0, + match: regex.either(...OPERATORS), + className: "operator" + }; + + const TRIPLE_STRING = { + className: "string", + begin: /"""/, + end: /"""/ + }; + + const PROPERTY = { + className: "property", + begin: regex.concat(/\./, regex.lookahead(IDENT_RE)), + end: IDENT_RE, + excludeBegin: true, + relevance: 0 + }; + + const FIELD = { + relevance: 0, + match: regex.concat(/\b_/, IDENT_RE), + scope: "variable" + }; + + // CamelCase + const CLASS_REFERENCE = { + relevance: 0, + match: /\b[A-Z]+[a-z]+([A-Z]+[a-z]+)*/, + scope: "title.class", + keywords: { _: CORE_CLASSES } + }; + + // TODO: add custom number modes + const NUMBER = hljs.C_NUMBER_MODE; + + const SETTER = { + match: [ + IDENT_RE, + /\s*/, + /=/, + /\s*/, + /\(/, + IDENT_RE, + /\)\s*\{/ + ], + scope: { + 1: "title.function", + 3: "operator", + 6: "params" + } + }; + + const COMMENT_DOCS = hljs.COMMENT( + /\/\*\*/, + /\*\//, + { contains: [ + { + match: /@[a-z]+/, + scope: "doctag" + }, + "self" + ] } + ); + const SUBST = { + scope: "subst", + begin: /%\(/, + end: /\)/, + contains: [ + NUMBER, + CLASS_REFERENCE, + FUNCTION, + FIELD, + OPERATOR + ] + }; + const STRING = { + scope: "string", + begin: /"/, + end: /"/, + contains: [ + SUBST, + { + scope: "char.escape", + variants: [ + { match: /\\\\|\\["0%abefnrtv]/ }, + { match: /\\x[0-9A-F]{2}/ }, + { match: /\\u[0-9A-F]{4}/ }, + { match: /\\U[0-9A-F]{8}/ } + ] + } + ] + }; + SUBST.contains.push(STRING); + + const ALL_KWS = [ + ...KEYWORDS, + ...LANGUAGE_VARS, + ...LITERALS + ]; + const VARIABLE = { + relevance: 0, + match: regex.concat( + "\\b(?!", + ALL_KWS.join("|"), + "\\b)", + /[a-zA-Z_]\w*(?:[?!]|\b)/ + ), + className: "variable" + }; + + // TODO: reconsider this in the future + const ATTRIBUTE = { + // scope: "meta", + scope: "comment", + variants: [ + { + begin: [ + /#!?/, + /[A-Za-z_]+(?=\()/ + ], + beginScope: { + // 2: "attr" + }, + keywords: { literal: LITERALS }, + contains: [ + // NUMBER, + // VARIABLE + ], + end: /\)/ + }, + { + begin: [ + /#!?/, + /[A-Za-z_]+/ + ], + beginScope: { + // 2: "attr" + }, + end: /$/ + } + ] + }; + + return { + name: "Wren", + keywords: { + keyword: KEYWORDS, + "variable.language": LANGUAGE_VARS, + literal: LITERALS + }, + contains: [ + ATTRIBUTE, + NUMBER, + STRING, + TRIPLE_STRING, + COMMENT_DOCS, + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + CLASS_REFERENCE, + CLASS_DEFINITION, + SETTER, + FUNCTION_DEFINITION, + FUNCTION, + OPERATOR, + FIELD, + PROPERTY, + VARIABLE + ] + }; +} + +export { wren as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/wren.js.js b/frontend/node_modules/highlight.js/es/languages/wren.js.js new file mode 100644 index 0000000..68eb881 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/wren.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/wren" instead of "highlight.js/lib/languages/wren.js"' + ); + } + } + emitWarning(); + import lang from './wren.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/x86asm.js b/frontend/node_modules/highlight.js/es/languages/x86asm.js new file mode 100644 index 0000000..5320933 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/x86asm.js @@ -0,0 +1,153 @@ +/* +Language: Intel x86 Assembly +Author: innocenat +Description: x86 assembly language using Intel's mnemonic and NASM syntax +Website: https://en.wikipedia.org/wiki/X86_assembly_language +Category: assembler +*/ + +function x86asm(hljs) { + return { + name: 'Intel x86 Assembly', + case_insensitive: true, + keywords: { + $pattern: '[.%]?' + hljs.IDENT_RE, + keyword: + 'lock rep repe repz repne repnz xaquire xrelease bnd nobnd ' + + 'aaa aad aam aas adc add and arpl bb0_reset bb1_reset bound bsf bsr bswap bt btc btr bts call cbw cdq cdqe clc cld cli clts cmc cmp cmpsb cmpsd cmpsq cmpsw cmpxchg cmpxchg486 cmpxchg8b cmpxchg16b cpuid cpu_read cpu_write cqo cwd cwde daa das dec div dmint emms enter equ f2xm1 fabs fadd faddp fbld fbstp fchs fclex fcmovb fcmovbe fcmove fcmovnb fcmovnbe fcmovne fcmovnu fcmovu fcom fcomi fcomip fcomp fcompp fcos fdecstp fdisi fdiv fdivp fdivr fdivrp femms feni ffree ffreep fiadd ficom ficomp fidiv fidivr fild fimul fincstp finit fist fistp fisttp fisub fisubr fld fld1 fldcw fldenv fldl2e fldl2t fldlg2 fldln2 fldpi fldz fmul fmulp fnclex fndisi fneni fninit fnop fnsave fnstcw fnstenv fnstsw fpatan fprem fprem1 fptan frndint frstor fsave fscale fsetpm fsin fsincos fsqrt fst fstcw fstenv fstp fstsw fsub fsubp fsubr fsubrp ftst fucom fucomi fucomip fucomp fucompp fxam fxch fxtract fyl2x fyl2xp1 hlt ibts icebp idiv imul in inc incbin insb insd insw int int01 int1 int03 int3 into invd invpcid invlpg invlpga iret iretd iretq iretw jcxz jecxz jrcxz jmp jmpe lahf lar lds lea leave les lfence lfs lgdt lgs lidt lldt lmsw loadall loadall286 lodsb lodsd lodsq lodsw loop loope loopne loopnz loopz lsl lss ltr mfence monitor mov movd movq movsb movsd movsq movsw movsx movsxd movzx mul mwait neg nop not or out outsb outsd outsw packssdw packsswb packuswb paddb paddd paddsb paddsiw paddsw paddusb paddusw paddw pand pandn pause paveb pavgusb pcmpeqb pcmpeqd pcmpeqw pcmpgtb pcmpgtd pcmpgtw pdistib pf2id pfacc pfadd pfcmpeq pfcmpge pfcmpgt pfmax pfmin pfmul pfrcp pfrcpit1 pfrcpit2 pfrsqit1 pfrsqrt pfsub pfsubr pi2fd pmachriw pmaddwd pmagw pmulhriw pmulhrwa pmulhrwc pmulhw pmullw pmvgezb pmvlzb pmvnzb pmvzb pop popa popad popaw popf popfd popfq popfw por prefetch prefetchw pslld psllq psllw psrad psraw psrld psrlq psrlw psubb psubd psubsb psubsiw psubsw psubusb psubusw psubw punpckhbw punpckhdq punpckhwd punpcklbw punpckldq punpcklwd push pusha pushad pushaw pushf pushfd pushfq pushfw pxor rcl rcr rdshr rdmsr rdpmc rdtsc rdtscp ret retf retn rol ror rdm rsdc rsldt rsm rsts sahf sal salc sar sbb scasb scasd scasq scasw sfence sgdt shl shld shr shrd sidt sldt skinit smi smint smintold smsw stc std sti stosb stosd stosq stosw str sub svdc svldt svts swapgs syscall sysenter sysexit sysret test ud0 ud1 ud2b ud2 ud2a umov verr verw fwait wbinvd wrshr wrmsr xadd xbts xchg xlatb xlat xor cmove cmovz cmovne cmovnz cmova cmovnbe cmovae cmovnb cmovb cmovnae cmovbe cmovna cmovg cmovnle cmovge cmovnl cmovl cmovnge cmovle cmovng cmovc cmovnc cmovo cmovno cmovs cmovns cmovp cmovpe cmovnp cmovpo je jz jne jnz ja jnbe jae jnb jb jnae jbe jna jg jnle jge jnl jl jnge jle jng jc jnc jo jno js jns jpo jnp jpe jp sete setz setne setnz seta setnbe setae setnb setnc setb setnae setcset setbe setna setg setnle setge setnl setl setnge setle setng sets setns seto setno setpe setp setpo setnp addps addss andnps andps cmpeqps cmpeqss cmpleps cmpless cmpltps cmpltss cmpneqps cmpneqss cmpnleps cmpnless cmpnltps cmpnltss cmpordps cmpordss cmpunordps cmpunordss cmpps cmpss comiss cvtpi2ps cvtps2pi cvtsi2ss cvtss2si cvttps2pi cvttss2si divps divss ldmxcsr maxps maxss minps minss movaps movhps movlhps movlps movhlps movmskps movntps movss movups mulps mulss orps rcpps rcpss rsqrtps rsqrtss shufps sqrtps sqrtss stmxcsr subps subss ucomiss unpckhps unpcklps xorps fxrstor fxrstor64 fxsave fxsave64 xgetbv xsetbv xsave xsave64 xsaveopt xsaveopt64 xrstor xrstor64 prefetchnta prefetcht0 prefetcht1 prefetcht2 maskmovq movntq pavgb pavgw pextrw pinsrw pmaxsw pmaxub pminsw pminub pmovmskb pmulhuw psadbw pshufw pf2iw pfnacc pfpnacc pi2fw pswapd maskmovdqu clflush movntdq movnti movntpd movdqa movdqu movdq2q movq2dq paddq pmuludq pshufd pshufhw pshuflw pslldq psrldq psubq punpckhqdq punpcklqdq addpd addsd andnpd andpd cmpeqpd cmpeqsd cmplepd cmplesd cmpltpd cmpltsd cmpneqpd cmpneqsd cmpnlepd cmpnlesd cmpnltpd cmpnltsd cmpordpd cmpordsd cmpunordpd cmpunordsd cmppd comisd cvtdq2pd cvtdq2ps cvtpd2dq cvtpd2pi cvtpd2ps cvtpi2pd cvtps2dq cvtps2pd cvtsd2si cvtsd2ss cvtsi2sd cvtss2sd cvttpd2pi cvttpd2dq cvttps2dq cvttsd2si divpd divsd maxpd maxsd minpd minsd movapd movhpd movlpd movmskpd movupd mulpd mulsd orpd shufpd sqrtpd sqrtsd subpd subsd ucomisd unpckhpd unpcklpd xorpd addsubpd addsubps haddpd haddps hsubpd hsubps lddqu movddup movshdup movsldup clgi stgi vmcall vmclear vmfunc vmlaunch vmload vmmcall vmptrld vmptrst vmread vmresume vmrun vmsave vmwrite vmxoff vmxon invept invvpid pabsb pabsw pabsd palignr phaddw phaddd phaddsw phsubw phsubd phsubsw pmaddubsw pmulhrsw pshufb psignb psignw psignd extrq insertq movntsd movntss lzcnt blendpd blendps blendvpd blendvps dppd dpps extractps insertps movntdqa mpsadbw packusdw pblendvb pblendw pcmpeqq pextrb pextrd pextrq phminposuw pinsrb pinsrd pinsrq pmaxsb pmaxsd pmaxud pmaxuw pminsb pminsd pminud pminuw pmovsxbw pmovsxbd pmovsxbq pmovsxwd pmovsxwq pmovsxdq pmovzxbw pmovzxbd pmovzxbq pmovzxwd pmovzxwq pmovzxdq pmuldq pmulld ptest roundpd roundps roundsd roundss crc32 pcmpestri pcmpestrm pcmpistri pcmpistrm pcmpgtq popcnt getsec pfrcpv pfrsqrtv movbe aesenc aesenclast aesdec aesdeclast aesimc aeskeygenassist vaesenc vaesenclast vaesdec vaesdeclast vaesimc vaeskeygenassist vaddpd vaddps vaddsd vaddss vaddsubpd vaddsubps vandpd vandps vandnpd vandnps vblendpd vblendps vblendvpd vblendvps vbroadcastss vbroadcastsd vbroadcastf128 vcmpeq_ospd vcmpeqpd vcmplt_ospd vcmpltpd vcmple_ospd vcmplepd vcmpunord_qpd vcmpunordpd vcmpneq_uqpd vcmpneqpd vcmpnlt_uspd vcmpnltpd vcmpnle_uspd vcmpnlepd vcmpord_qpd vcmpordpd vcmpeq_uqpd vcmpnge_uspd vcmpngepd vcmpngt_uspd vcmpngtpd vcmpfalse_oqpd vcmpfalsepd vcmpneq_oqpd vcmpge_ospd vcmpgepd vcmpgt_ospd vcmpgtpd vcmptrue_uqpd vcmptruepd vcmplt_oqpd vcmple_oqpd vcmpunord_spd vcmpneq_uspd vcmpnlt_uqpd vcmpnle_uqpd vcmpord_spd vcmpeq_uspd vcmpnge_uqpd vcmpngt_uqpd vcmpfalse_ospd vcmpneq_ospd vcmpge_oqpd vcmpgt_oqpd vcmptrue_uspd vcmppd vcmpeq_osps vcmpeqps vcmplt_osps vcmpltps vcmple_osps vcmpleps vcmpunord_qps vcmpunordps vcmpneq_uqps vcmpneqps vcmpnlt_usps vcmpnltps vcmpnle_usps vcmpnleps vcmpord_qps vcmpordps vcmpeq_uqps vcmpnge_usps vcmpngeps vcmpngt_usps vcmpngtps vcmpfalse_oqps vcmpfalseps vcmpneq_oqps vcmpge_osps vcmpgeps vcmpgt_osps vcmpgtps vcmptrue_uqps vcmptrueps vcmplt_oqps vcmple_oqps vcmpunord_sps vcmpneq_usps vcmpnlt_uqps vcmpnle_uqps vcmpord_sps vcmpeq_usps vcmpnge_uqps vcmpngt_uqps vcmpfalse_osps vcmpneq_osps vcmpge_oqps vcmpgt_oqps vcmptrue_usps vcmpps vcmpeq_ossd vcmpeqsd vcmplt_ossd vcmpltsd vcmple_ossd vcmplesd vcmpunord_qsd vcmpunordsd vcmpneq_uqsd vcmpneqsd vcmpnlt_ussd vcmpnltsd vcmpnle_ussd vcmpnlesd vcmpord_qsd vcmpordsd vcmpeq_uqsd vcmpnge_ussd vcmpngesd vcmpngt_ussd vcmpngtsd vcmpfalse_oqsd vcmpfalsesd vcmpneq_oqsd vcmpge_ossd vcmpgesd vcmpgt_ossd vcmpgtsd vcmptrue_uqsd vcmptruesd vcmplt_oqsd vcmple_oqsd vcmpunord_ssd vcmpneq_ussd vcmpnlt_uqsd vcmpnle_uqsd vcmpord_ssd vcmpeq_ussd vcmpnge_uqsd vcmpngt_uqsd vcmpfalse_ossd vcmpneq_ossd vcmpge_oqsd vcmpgt_oqsd vcmptrue_ussd vcmpsd vcmpeq_osss vcmpeqss vcmplt_osss vcmpltss vcmple_osss vcmpless vcmpunord_qss vcmpunordss vcmpneq_uqss vcmpneqss vcmpnlt_usss vcmpnltss vcmpnle_usss vcmpnless vcmpord_qss vcmpordss vcmpeq_uqss vcmpnge_usss vcmpngess vcmpngt_usss vcmpngtss vcmpfalse_oqss vcmpfalsess vcmpneq_oqss vcmpge_osss vcmpgess vcmpgt_osss vcmpgtss vcmptrue_uqss vcmptruess vcmplt_oqss vcmple_oqss vcmpunord_sss vcmpneq_usss vcmpnlt_uqss vcmpnle_uqss vcmpord_sss vcmpeq_usss vcmpnge_uqss vcmpngt_uqss vcmpfalse_osss vcmpneq_osss vcmpge_oqss vcmpgt_oqss vcmptrue_usss vcmpss vcomisd vcomiss vcvtdq2pd vcvtdq2ps vcvtpd2dq vcvtpd2ps vcvtps2dq vcvtps2pd vcvtsd2si vcvtsd2ss vcvtsi2sd vcvtsi2ss vcvtss2sd vcvtss2si vcvttpd2dq vcvttps2dq vcvttsd2si vcvttss2si vdivpd vdivps vdivsd vdivss vdppd vdpps vextractf128 vextractps vhaddpd vhaddps vhsubpd vhsubps vinsertf128 vinsertps vlddqu vldqqu vldmxcsr vmaskmovdqu vmaskmovps vmaskmovpd vmaxpd vmaxps vmaxsd vmaxss vminpd vminps vminsd vminss vmovapd vmovaps vmovd vmovq vmovddup vmovdqa vmovqqa vmovdqu vmovqqu vmovhlps vmovhpd vmovhps vmovlhps vmovlpd vmovlps vmovmskpd vmovmskps vmovntdq vmovntqq vmovntdqa vmovntpd vmovntps vmovsd vmovshdup vmovsldup vmovss vmovupd vmovups vmpsadbw vmulpd vmulps vmulsd vmulss vorpd vorps vpabsb vpabsw vpabsd vpacksswb vpackssdw vpackuswb vpackusdw vpaddb vpaddw vpaddd vpaddq vpaddsb vpaddsw vpaddusb vpaddusw vpalignr vpand vpandn vpavgb vpavgw vpblendvb vpblendw vpcmpestri vpcmpestrm vpcmpistri vpcmpistrm vpcmpeqb vpcmpeqw vpcmpeqd vpcmpeqq vpcmpgtb vpcmpgtw vpcmpgtd vpcmpgtq vpermilpd vpermilps vperm2f128 vpextrb vpextrw vpextrd vpextrq vphaddw vphaddd vphaddsw vphminposuw vphsubw vphsubd vphsubsw vpinsrb vpinsrw vpinsrd vpinsrq vpmaddwd vpmaddubsw vpmaxsb vpmaxsw vpmaxsd vpmaxub vpmaxuw vpmaxud vpminsb vpminsw vpminsd vpminub vpminuw vpminud vpmovmskb vpmovsxbw vpmovsxbd vpmovsxbq vpmovsxwd vpmovsxwq vpmovsxdq vpmovzxbw vpmovzxbd vpmovzxbq vpmovzxwd vpmovzxwq vpmovzxdq vpmulhuw vpmulhrsw vpmulhw vpmullw vpmulld vpmuludq vpmuldq vpor vpsadbw vpshufb vpshufd vpshufhw vpshuflw vpsignb vpsignw vpsignd vpslldq vpsrldq vpsllw vpslld vpsllq vpsraw vpsrad vpsrlw vpsrld vpsrlq vptest vpsubb vpsubw vpsubd vpsubq vpsubsb vpsubsw vpsubusb vpsubusw vpunpckhbw vpunpckhwd vpunpckhdq vpunpckhqdq vpunpcklbw vpunpcklwd vpunpckldq vpunpcklqdq vpxor vrcpps vrcpss vrsqrtps vrsqrtss vroundpd vroundps vroundsd vroundss vshufpd vshufps vsqrtpd vsqrtps vsqrtsd vsqrtss vstmxcsr vsubpd vsubps vsubsd vsubss vtestps vtestpd vucomisd vucomiss vunpckhpd vunpckhps vunpcklpd vunpcklps vxorpd vxorps vzeroall vzeroupper pclmullqlqdq pclmulhqlqdq pclmullqhqdq pclmulhqhqdq pclmulqdq vpclmullqlqdq vpclmulhqlqdq vpclmullqhqdq vpclmulhqhqdq vpclmulqdq vfmadd132ps vfmadd132pd vfmadd312ps vfmadd312pd vfmadd213ps vfmadd213pd vfmadd123ps vfmadd123pd vfmadd231ps vfmadd231pd vfmadd321ps vfmadd321pd vfmaddsub132ps vfmaddsub132pd vfmaddsub312ps vfmaddsub312pd vfmaddsub213ps vfmaddsub213pd vfmaddsub123ps vfmaddsub123pd vfmaddsub231ps vfmaddsub231pd vfmaddsub321ps vfmaddsub321pd vfmsub132ps vfmsub132pd vfmsub312ps vfmsub312pd vfmsub213ps vfmsub213pd vfmsub123ps vfmsub123pd vfmsub231ps vfmsub231pd vfmsub321ps vfmsub321pd vfmsubadd132ps vfmsubadd132pd vfmsubadd312ps vfmsubadd312pd vfmsubadd213ps vfmsubadd213pd vfmsubadd123ps vfmsubadd123pd vfmsubadd231ps vfmsubadd231pd vfmsubadd321ps vfmsubadd321pd vfnmadd132ps vfnmadd132pd vfnmadd312ps vfnmadd312pd vfnmadd213ps vfnmadd213pd vfnmadd123ps vfnmadd123pd vfnmadd231ps vfnmadd231pd vfnmadd321ps vfnmadd321pd vfnmsub132ps vfnmsub132pd vfnmsub312ps vfnmsub312pd vfnmsub213ps vfnmsub213pd vfnmsub123ps vfnmsub123pd vfnmsub231ps vfnmsub231pd vfnmsub321ps vfnmsub321pd vfmadd132ss vfmadd132sd vfmadd312ss vfmadd312sd vfmadd213ss vfmadd213sd vfmadd123ss vfmadd123sd vfmadd231ss vfmadd231sd vfmadd321ss vfmadd321sd vfmsub132ss vfmsub132sd vfmsub312ss vfmsub312sd vfmsub213ss vfmsub213sd vfmsub123ss vfmsub123sd vfmsub231ss vfmsub231sd vfmsub321ss vfmsub321sd vfnmadd132ss vfnmadd132sd vfnmadd312ss vfnmadd312sd vfnmadd213ss vfnmadd213sd vfnmadd123ss vfnmadd123sd vfnmadd231ss vfnmadd231sd vfnmadd321ss vfnmadd321sd vfnmsub132ss vfnmsub132sd vfnmsub312ss vfnmsub312sd vfnmsub213ss vfnmsub213sd vfnmsub123ss vfnmsub123sd vfnmsub231ss vfnmsub231sd vfnmsub321ss vfnmsub321sd rdfsbase rdgsbase rdrand wrfsbase wrgsbase vcvtph2ps vcvtps2ph adcx adox rdseed clac stac xstore xcryptecb xcryptcbc xcryptctr xcryptcfb xcryptofb montmul xsha1 xsha256 llwpcb slwpcb lwpval lwpins vfmaddpd vfmaddps vfmaddsd vfmaddss vfmaddsubpd vfmaddsubps vfmsubaddpd vfmsubaddps vfmsubpd vfmsubps vfmsubsd vfmsubss vfnmaddpd vfnmaddps vfnmaddsd vfnmaddss vfnmsubpd vfnmsubps vfnmsubsd vfnmsubss vfrczpd vfrczps vfrczsd vfrczss vpcmov vpcomb vpcomd vpcomq vpcomub vpcomud vpcomuq vpcomuw vpcomw vphaddbd vphaddbq vphaddbw vphadddq vphaddubd vphaddubq vphaddubw vphaddudq vphadduwd vphadduwq vphaddwd vphaddwq vphsubbw vphsubdq vphsubwd vpmacsdd vpmacsdqh vpmacsdql vpmacssdd vpmacssdqh vpmacssdql vpmacsswd vpmacssww vpmacswd vpmacsww vpmadcsswd vpmadcswd vpperm vprotb vprotd vprotq vprotw vpshab vpshad vpshaq vpshaw vpshlb vpshld vpshlq vpshlw vbroadcasti128 vpblendd vpbroadcastb vpbroadcastw vpbroadcastd vpbroadcastq vpermd vpermpd vpermps vpermq vperm2i128 vextracti128 vinserti128 vpmaskmovd vpmaskmovq vpsllvd vpsllvq vpsravd vpsrlvd vpsrlvq vgatherdpd vgatherqpd vgatherdps vgatherqps vpgatherdd vpgatherqd vpgatherdq vpgatherqq xabort xbegin xend xtest andn bextr blci blcic blsi blsic blcfill blsfill blcmsk blsmsk blsr blcs bzhi mulx pdep pext rorx sarx shlx shrx tzcnt tzmsk t1mskc valignd valignq vblendmpd vblendmps vbroadcastf32x4 vbroadcastf64x4 vbroadcasti32x4 vbroadcasti64x4 vcompresspd vcompressps vcvtpd2udq vcvtps2udq vcvtsd2usi vcvtss2usi vcvttpd2udq vcvttps2udq vcvttsd2usi vcvttss2usi vcvtudq2pd vcvtudq2ps vcvtusi2sd vcvtusi2ss vexpandpd vexpandps vextractf32x4 vextractf64x4 vextracti32x4 vextracti64x4 vfixupimmpd vfixupimmps vfixupimmsd vfixupimmss vgetexppd vgetexpps vgetexpsd vgetexpss vgetmantpd vgetmantps vgetmantsd vgetmantss vinsertf32x4 vinsertf64x4 vinserti32x4 vinserti64x4 vmovdqa32 vmovdqa64 vmovdqu32 vmovdqu64 vpabsq vpandd vpandnd vpandnq vpandq vpblendmd vpblendmq vpcmpltd vpcmpled vpcmpneqd vpcmpnltd vpcmpnled vpcmpd vpcmpltq vpcmpleq vpcmpneqq vpcmpnltq vpcmpnleq vpcmpq vpcmpequd vpcmpltud vpcmpleud vpcmpnequd vpcmpnltud vpcmpnleud vpcmpud vpcmpequq vpcmpltuq vpcmpleuq vpcmpnequq vpcmpnltuq vpcmpnleuq vpcmpuq vpcompressd vpcompressq vpermi2d vpermi2pd vpermi2ps vpermi2q vpermt2d vpermt2pd vpermt2ps vpermt2q vpexpandd vpexpandq vpmaxsq vpmaxuq vpminsq vpminuq vpmovdb vpmovdw vpmovqb vpmovqd vpmovqw vpmovsdb vpmovsdw vpmovsqb vpmovsqd vpmovsqw vpmovusdb vpmovusdw vpmovusqb vpmovusqd vpmovusqw vpord vporq vprold vprolq vprolvd vprolvq vprord vprorq vprorvd vprorvq vpscatterdd vpscatterdq vpscatterqd vpscatterqq vpsraq vpsravq vpternlogd vpternlogq vptestmd vptestmq vptestnmd vptestnmq vpxord vpxorq vrcp14pd vrcp14ps vrcp14sd vrcp14ss vrndscalepd vrndscaleps vrndscalesd vrndscaless vrsqrt14pd vrsqrt14ps vrsqrt14sd vrsqrt14ss vscalefpd vscalefps vscalefsd vscalefss vscatterdpd vscatterdps vscatterqpd vscatterqps vshuff32x4 vshuff64x2 vshufi32x4 vshufi64x2 kandnw kandw kmovw knotw kortestw korw kshiftlw kshiftrw kunpckbw kxnorw kxorw vpbroadcastmb2q vpbroadcastmw2d vpconflictd vpconflictq vplzcntd vplzcntq vexp2pd vexp2ps vrcp28pd vrcp28ps vrcp28sd vrcp28ss vrsqrt28pd vrsqrt28ps vrsqrt28sd vrsqrt28ss vgatherpf0dpd vgatherpf0dps vgatherpf0qpd vgatherpf0qps vgatherpf1dpd vgatherpf1dps vgatherpf1qpd vgatherpf1qps vscatterpf0dpd vscatterpf0dps vscatterpf0qpd vscatterpf0qps vscatterpf1dpd vscatterpf1dps vscatterpf1qpd vscatterpf1qps prefetchwt1 bndmk bndcl bndcu bndcn bndmov bndldx bndstx sha1rnds4 sha1nexte sha1msg1 sha1msg2 sha256rnds2 sha256msg1 sha256msg2 hint_nop0 hint_nop1 hint_nop2 hint_nop3 hint_nop4 hint_nop5 hint_nop6 hint_nop7 hint_nop8 hint_nop9 hint_nop10 hint_nop11 hint_nop12 hint_nop13 hint_nop14 hint_nop15 hint_nop16 hint_nop17 hint_nop18 hint_nop19 hint_nop20 hint_nop21 hint_nop22 hint_nop23 hint_nop24 hint_nop25 hint_nop26 hint_nop27 hint_nop28 hint_nop29 hint_nop30 hint_nop31 hint_nop32 hint_nop33 hint_nop34 hint_nop35 hint_nop36 hint_nop37 hint_nop38 hint_nop39 hint_nop40 hint_nop41 hint_nop42 hint_nop43 hint_nop44 hint_nop45 hint_nop46 hint_nop47 hint_nop48 hint_nop49 hint_nop50 hint_nop51 hint_nop52 hint_nop53 hint_nop54 hint_nop55 hint_nop56 hint_nop57 hint_nop58 hint_nop59 hint_nop60 hint_nop61 hint_nop62 hint_nop63', + built_in: + // Instruction pointer + 'ip eip rip ' + // 8-bit registers + + 'al ah bl bh cl ch dl dh sil dil bpl spl r8b r9b r10b r11b r12b r13b r14b r15b ' + // 16-bit registers + + 'ax bx cx dx si di bp sp r8w r9w r10w r11w r12w r13w r14w r15w ' + // 32-bit registers + + 'eax ebx ecx edx esi edi ebp esp eip r8d r9d r10d r11d r12d r13d r14d r15d ' + // 64-bit registers + + 'rax rbx rcx rdx rsi rdi rbp rsp r8 r9 r10 r11 r12 r13 r14 r15 ' + // Segment registers + + 'cs ds es fs gs ss ' + // Floating point stack registers + + 'st st0 st1 st2 st3 st4 st5 st6 st7 ' + // MMX Registers + + 'mm0 mm1 mm2 mm3 mm4 mm5 mm6 mm7 ' + // SSE registers + + 'xmm0 xmm1 xmm2 xmm3 xmm4 xmm5 xmm6 xmm7 xmm8 xmm9 xmm10 xmm11 xmm12 xmm13 xmm14 xmm15 ' + + 'xmm16 xmm17 xmm18 xmm19 xmm20 xmm21 xmm22 xmm23 xmm24 xmm25 xmm26 xmm27 xmm28 xmm29 xmm30 xmm31 ' + // AVX registers + + 'ymm0 ymm1 ymm2 ymm3 ymm4 ymm5 ymm6 ymm7 ymm8 ymm9 ymm10 ymm11 ymm12 ymm13 ymm14 ymm15 ' + + 'ymm16 ymm17 ymm18 ymm19 ymm20 ymm21 ymm22 ymm23 ymm24 ymm25 ymm26 ymm27 ymm28 ymm29 ymm30 ymm31 ' + // AVX-512F registers + + 'zmm0 zmm1 zmm2 zmm3 zmm4 zmm5 zmm6 zmm7 zmm8 zmm9 zmm10 zmm11 zmm12 zmm13 zmm14 zmm15 ' + + 'zmm16 zmm17 zmm18 zmm19 zmm20 zmm21 zmm22 zmm23 zmm24 zmm25 zmm26 zmm27 zmm28 zmm29 zmm30 zmm31 ' + // AVX-512F mask registers + + 'k0 k1 k2 k3 k4 k5 k6 k7 ' + // Bound (MPX) register + + 'bnd0 bnd1 bnd2 bnd3 ' + // Special register + + 'cr0 cr1 cr2 cr3 cr4 cr8 dr0 dr1 dr2 dr3 dr8 tr3 tr4 tr5 tr6 tr7 ' + // NASM altreg package + + 'r0 r1 r2 r3 r4 r5 r6 r7 r0b r1b r2b r3b r4b r5b r6b r7b ' + + 'r0w r1w r2w r3w r4w r5w r6w r7w r0d r1d r2d r3d r4d r5d r6d r7d ' + + 'r0h r1h r2h r3h ' + + 'r0l r1l r2l r3l r4l r5l r6l r7l r8l r9l r10l r11l r12l r13l r14l r15l ' + + + 'db dw dd dq dt ddq do dy dz ' + + 'resb resw resd resq rest resdq reso resy resz ' + + 'incbin equ times ' + + 'byte word dword qword nosplit rel abs seg wrt strict near far a32 ptr', + + meta: + '%define %xdefine %+ %undef %defstr %deftok %assign %strcat %strlen %substr %rotate %elif %else %endif ' + + '%if %ifmacro %ifctx %ifidn %ifidni %ifid %ifnum %ifstr %iftoken %ifempty %ifenv %error %warning %fatal %rep ' + + '%endrep %include %push %pop %repl %pathsearch %depend %use %arg %stacksize %local %line %comment %endcomment ' + + '.nolist ' + + '__FILE__ __LINE__ __SECT__ __BITS__ __OUTPUT_FORMAT__ __DATE__ __TIME__ __DATE_NUM__ __TIME_NUM__ ' + + '__UTC_DATE__ __UTC_TIME__ __UTC_DATE_NUM__ __UTC_TIME_NUM__ __PASS__ struc endstruc istruc at iend ' + + 'align alignb sectalign daz nodaz up down zero default option assume public ' + + + 'bits use16 use32 use64 default section segment absolute extern global common cpu float ' + + '__utf16__ __utf16le__ __utf16be__ __utf32__ __utf32le__ __utf32be__ ' + + '__float8__ __float16__ __float32__ __float64__ __float80m__ __float80e__ __float128l__ __float128h__ ' + + '__Infinity__ __QNaN__ __SNaN__ Inf NaN QNaN SNaN float8 float16 float32 float64 float80m float80e ' + + 'float128l float128h __FLOAT_DAZ__ __FLOAT_ROUND__ __FLOAT__' + }, + contains: [ + hljs.COMMENT( + ';', + '$', + { relevance: 0 } + ), + { + className: 'number', + variants: [ + // Float number and x87 BCD + { + begin: '\\b(?:([0-9][0-9_]*)?\\.[0-9_]*(?:[eE][+-]?[0-9_]+)?|' + + '(0[Xx])?[0-9][0-9_]*(\\.[0-9_]*)?(?:[pP](?:[+-]?[0-9_]+)?)?)\\b', + relevance: 0 + }, + + // Hex number in $ + { + begin: '\\$[0-9][0-9A-Fa-f]*', + relevance: 0 + }, + + // Number in H,D,T,Q,O,B,Y suffix + { begin: '\\b(?:[0-9A-Fa-f][0-9A-Fa-f_]*[Hh]|[0-9][0-9_]*[DdTt]?|[0-7][0-7_]*[QqOo]|[0-1][0-1_]*[BbYy])\\b' }, + + // Number in X,D,T,Q,O,B,Y prefix + { begin: '\\b(?:0[Xx][0-9A-Fa-f_]+|0[DdTt][0-9_]+|0[QqOo][0-7_]+|0[BbYy][0-1_]+)\\b' } + ] + }, + // Double quote string + hljs.QUOTE_STRING_MODE, + { + className: 'string', + variants: [ + // Single-quoted string + { + begin: '\'', + end: '[^\\\\]\'' + }, + // Backquoted string + { + begin: '`', + end: '[^\\\\]`' + } + ], + relevance: 0 + }, + { + className: 'symbol', + variants: [ + // Global label and local label + { begin: '^\\s*[A-Za-z._?][A-Za-z0-9_$#@~.?]*(:|\\s+label)' }, + // Macro-local label + { begin: '^\\s*%%[A-Za-z0-9_$#@~.?]*:' } + ], + relevance: 0 + }, + // Macro parameter + { + className: 'subst', + begin: '%[0-9]+', + relevance: 0 + }, + // Macro parameter + { + className: 'subst', + begin: '%!\S+', + relevance: 0 + }, + { + className: 'meta', + begin: /^\s*\.[\w_-]+/ + } + ] + }; +} + +export { x86asm as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/x86asm.js.js b/frontend/node_modules/highlight.js/es/languages/x86asm.js.js new file mode 100644 index 0000000..d52be08 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/x86asm.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/x86asm" instead of "highlight.js/lib/languages/x86asm.js"' + ); + } + } + emitWarning(); + import lang from './x86asm.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/xl.js b/frontend/node_modules/highlight.js/es/languages/xl.js new file mode 100644 index 0000000..b21085e --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/xl.js @@ -0,0 +1,205 @@ +/* +Language: XL +Author: Christophe de Dinechin +Description: An extensible programming language, based on parse tree rewriting +Website: http://xlr.sf.net +*/ + +function xl(hljs) { + const KWS = [ + "if", + "then", + "else", + "do", + "while", + "until", + "for", + "loop", + "import", + "with", + "is", + "as", + "where", + "when", + "by", + "data", + "constant", + "integer", + "real", + "text", + "name", + "boolean", + "symbol", + "infix", + "prefix", + "postfix", + "block", + "tree" + ]; + const BUILT_INS = [ + "in", + "mod", + "rem", + "and", + "or", + "xor", + "not", + "abs", + "sign", + "floor", + "ceil", + "sqrt", + "sin", + "cos", + "tan", + "asin", + "acos", + "atan", + "exp", + "expm1", + "log", + "log2", + "log10", + "log1p", + "pi", + "at", + "text_length", + "text_range", + "text_find", + "text_replace", + "contains", + "page", + "slide", + "basic_slide", + "title_slide", + "title", + "subtitle", + "fade_in", + "fade_out", + "fade_at", + "clear_color", + "color", + "line_color", + "line_width", + "texture_wrap", + "texture_transform", + "texture", + "scale_?x", + "scale_?y", + "scale_?z?", + "translate_?x", + "translate_?y", + "translate_?z?", + "rotate_?x", + "rotate_?y", + "rotate_?z?", + "rectangle", + "circle", + "ellipse", + "sphere", + "path", + "line_to", + "move_to", + "quad_to", + "curve_to", + "theme", + "background", + "contents", + "locally", + "time", + "mouse_?x", + "mouse_?y", + "mouse_buttons" + ]; + const BUILTIN_MODULES = [ + "ObjectLoader", + "Animate", + "MovieCredits", + "Slides", + "Filters", + "Shading", + "Materials", + "LensFlare", + "Mapping", + "VLCAudioVideo", + "StereoDecoder", + "PointCloud", + "NetworkAccess", + "RemoteControl", + "RegExp", + "ChromaKey", + "Snowfall", + "NodeJS", + "Speech", + "Charts" + ]; + const LITERALS = [ + "true", + "false", + "nil" + ]; + const KEYWORDS = { + $pattern: /[a-zA-Z][a-zA-Z0-9_?]*/, + keyword: KWS, + literal: LITERALS, + built_in: BUILT_INS.concat(BUILTIN_MODULES) + }; + + const DOUBLE_QUOTE_TEXT = { + className: 'string', + begin: '"', + end: '"', + illegal: '\\n' + }; + const SINGLE_QUOTE_TEXT = { + className: 'string', + begin: '\'', + end: '\'', + illegal: '\\n' + }; + const LONG_TEXT = { + className: 'string', + begin: '<<', + end: '>>' + }; + const BASED_NUMBER = { + className: 'number', + begin: '[0-9]+#[0-9A-Z_]+(\\.[0-9-A-Z_]+)?#?([Ee][+-]?[0-9]+)?' + }; + const IMPORT = { + beginKeywords: 'import', + end: '$', + keywords: KEYWORDS, + contains: [ DOUBLE_QUOTE_TEXT ] + }; + const FUNCTION_DEFINITION = { + className: 'function', + begin: /[a-z][^\n]*->/, + returnBegin: true, + end: /->/, + contains: [ + hljs.inherit(hljs.TITLE_MODE, { starts: { + endsWithParent: true, + keywords: KEYWORDS + } }) + ] + }; + return { + name: 'XL', + aliases: [ 'tao' ], + keywords: KEYWORDS, + contains: [ + hljs.C_LINE_COMMENT_MODE, + hljs.C_BLOCK_COMMENT_MODE, + DOUBLE_QUOTE_TEXT, + SINGLE_QUOTE_TEXT, + LONG_TEXT, + FUNCTION_DEFINITION, + IMPORT, + BASED_NUMBER, + hljs.NUMBER_MODE + ] + }; +} + +export { xl as default }; diff --git a/frontend/node_modules/highlight.js/es/languages/xl.js.js b/frontend/node_modules/highlight.js/es/languages/xl.js.js new file mode 100644 index 0000000..fa3d9dc --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/xl.js.js @@ -0,0 +1,11 @@ +function emitWarning() { + if (!emitWarning.warned) { + emitWarning.warned = true; + console.log( + 'Deprecation (warning): Using file extension in specifier is deprecated, use "highlight.js/lib/languages/xl" instead of "highlight.js/lib/languages/xl.js"' + ); + } + } + emitWarning(); + import lang from './xl.js'; + export default lang; \ No newline at end of file diff --git a/frontend/node_modules/highlight.js/es/languages/xml.js b/frontend/node_modules/highlight.js/es/languages/xml.js new file mode 100644 index 0000000..6df7c19 --- /dev/null +++ b/frontend/node_modules/highlight.js/es/languages/xml.js @@ -0,0 +1,241 @@ +/* +Language: HTML, XML +Website: https://www.w3.org/XML/ +Category: common, web +Audit: 2020 +*/ + +/** @type LanguageFn */ +function xml(hljs) { + const regex = hljs.regex; + // XML names can have the following additional letters: https://www.w3.org/TR/xml/#NT-NameChar + // OTHER_NAME_CHARS = /[:\-.0-9\u00B7\u0300-\u036F\u203F-\u2040]/; + // Element names start with NAME_START_CHAR followed by optional other Unicode letters, ASCII digits, hyphens, underscores, and periods + // const TAG_NAME_RE = regex.concat(/[A-Z_a-z\u00C0-\u00D6\u00D8-\u00F6\u00F8-\u02FF\u0370-\u037D\u037F-\u1FFF\u200C-\u200D\u2070-\u218F\u2C00-\u2FEF\u3001-\uD7FF\uF900-\uFDCF\uFDF0-\uFFFD]/, regex.optional(/[A-Z_a-z\u00C0-\u00D6\u00D8-\u00F6\u00F8-\u02FF\u0370-\u037D\u037F-\u1FFF\u200C-\u200D\u2070-\u218F\u2C00-\u2FEF\u3001-\uD7FF\uF900-\uFDCF\uFDF0-\uFFFD\-.0-9\u00B7\u0300-\u036F\u203F-\u2040]*:/), /[A-Z_a-z\u00C0-\u00D6\u00D8-\u00F6\u00F8-\u02FF\u0370-\u037D\u037F-\u1FFF\u200C-\u200D\u2070-\u218F\u2C00-\u2FEF\u3001-\uD7FF\uF900-\uFDCF\uFDF0-\uFFFD\-.0-9\u00B7\u0300-\u036F\u203F-\u2040]*/);; + // const XML_IDENT_RE = /[A-Z_a-z:\u00C0-\u00D6\u00D8-\u00F6\u00F8-\u02FF\u0370-\u037D\u037F-\u1FFF\u200C-\u200D\u2070-\u218F\u2C00-\u2FEF\u3001-\uD7FF\uF900-\uFDCF\uFDF0-\uFFFD\-.0-9\u00B7\u0300-\u036F\u203F-\u2040]+/; + // const TAG_NAME_RE = regex.concat(/[A-Z_a-z\u00C0-\u00D6\u00D8-\u00F6\u00F8-\u02FF\u0370-\u037D\u037F-\u1FFF\u200C-\u200D\u2070-\u218F\u2C00-\u2FEF\u3001-\uD7FF\uF900-\uFDCF\uFDF0-\uFFFD]/, regex.optional(/[A-Z_a-z\u00C0-\u00D6\u00D8-\u00F6\u00F8-\u02FF\u0370-\u037D\u037F-\u1FFF\u200C-\u200D\u2070-\u218F\u2C00-\u2FEF\u3001-\uD7FF\uF900-\uFDCF\uFDF0-\uFFFD\-.0-9\u00B7\u0300-\u036F\u203F-\u2040]*:/), /[A-Z_a-z\u00C0-\u00D6\u00D8-\u00F6\u00F8-\u02FF\u0370-\u037D\u037F-\u1FFF\u200C-\u200D\u2070-\u218F\u2C00-\u2FEF\u3001-\uD7FF\uF900-\uFDCF\uFDF0-\uFFFD\-.0-9\u00B7\u0300-\u036F\u203F-\u2040]*/); + // however, to cater for performance and more Unicode support rely simply on the Unicode letter class + const TAG_NAME_RE = regex.concat(/[\p{L}_]/u, regex.optional(/[\p{L}0-9_.-]*:/u), /[\p{L}0-9_.-]*/u); + const XML_IDENT_RE = /[\p{L}0-9._:-]+/u; + const XML_ENTITIES = { + className: 'symbol', + begin: /&[a-z]+;|&#[0-9]+;|&#x[a-f0-9]+;/ + }; + const XML_META_KEYWORDS = { + begin: /\s/, + contains: [ + { + className: 'keyword', + begin: /#?[a-z_][a-z1-9_-]+/, + illegal: /\n/ + } + ] + }; + const XML_META_PAR_KEYWORDS = hljs.inherit(XML_META_KEYWORDS, { + begin: /\(/, + end: /\)/ + }); + const APOS_META_STRING_MODE = hljs.inherit(hljs.APOS_STRING_MODE, { className: 'string' }); + const QUOTE_META_STRING_MODE = hljs.inherit(hljs.QUOTE_STRING_MODE, { className: 'string' }); + const TAG_INTERNALS = { + endsWithParent: true, + illegal: /`]+/ } + ] + } + ] + } + ] + }; + return { + name: 'HTML, XML', + aliases: [ + 'html', + 'xhtml', + 'rss', + 'atom', + 'xjb', + 'xsd', + 'xsl', + 'plist', + 'wsf', + 'svg' + ], + case_insensitive: true, + unicodeRegex: true, + contains: [ + { + className: 'meta', + begin: //, + relevance: 10, + contains: [ + XML_META_KEYWORDS, + QUOTE_META_STRING_MODE, + APOS_META_STRING_MODE, + XML_META_PAR_KEYWORDS, + { + begin: /\[/, + end: /\]/, + contains: [ + { + className: 'meta', + begin: //, + contains: [ + XML_META_KEYWORDS, + XML_META_PAR_KEYWORDS, + QUOTE_META_STRING_MODE, + APOS_META_STRING_MODE + ] + } + ] + } + ] + }, + hljs.COMMENT( + //, + { relevance: 10 } + ), + { + begin: //, + relevance: 10 + }, + XML_ENTITIES, + // xml processing instructions + { + className: 'meta', + end: /\?>/, + variants: [ + { + begin: /<\?xml/, + relevance: 10, + contains: [ + QUOTE_META_STRING_MODE + ] + }, + { + begin: /<\?[a-z][a-z0-9]+/, + } + ] + + }, + { + className: 'tag', + /* + The lookahead pattern (?=...) ensures that 'begin' only matches + ')/, + end: />/, + keywords: { name: 'style' }, + contains: [ TAG_INTERNALS ], + starts: { + end: /<\/style>/, + returnEnd: true, + subLanguage: [ + 'css', + 'xml' + ] + } + }, + { + className: 'tag', + // See the comment in the + + +
    + This is some text $math \frac12$ other text $\unsupported$ + + Other node \[ \text{displaymath} \frac{1}{2} \] blah $$ \int_2^3 $$ + + and some more text \(and math\) blah. And $math with a + \$ sign$. +
    +        Stuff in a $pre tag$
    +      
    +

    An AMS environment without $$…$$ delimiters.

    +

    \begin{equation} \begin{split} a &=b+c\\ &=e+f \end{split} \end{equation}

    +
    + + + diff --git a/frontend/node_modules/katex/contrib/auto-render/splitAtDelimiters.js b/frontend/node_modules/katex/contrib/auto-render/splitAtDelimiters.js new file mode 100644 index 0000000..21b5903 --- /dev/null +++ b/frontend/node_modules/katex/contrib/auto-render/splitAtDelimiters.js @@ -0,0 +1,85 @@ +/* eslint no-constant-condition:0 */ +const findEndOfMath = function(delimiter, text, startIndex) { + // Adapted from + // https://github.com/Khan/perseus/blob/master/src/perseus-markdown.jsx + let index = startIndex; + let braceLevel = 0; + + const delimLength = delimiter.length; + + while (index < text.length) { + const character = text[index]; + + if (braceLevel <= 0 && + text.slice(index, index + delimLength) === delimiter) { + return index; + } else if (character === "\\") { + index++; + } else if (character === "{") { + braceLevel++; + } else if (character === "}") { + braceLevel--; + } + + index++; + } + + return -1; +}; + +const escapeRegex = function(string) { + return string.replace(/[-/\\^$*+?.()|[\]{}]/g, "\\$&"); +}; + +const amsRegex = /^\\begin{/; + +const splitAtDelimiters = function(text, delimiters) { + let index; + const data = []; + + const regexLeft = new RegExp( + "(" + delimiters.map((x) => escapeRegex(x.left)).join("|") + ")" + ); + + while (true) { + index = text.search(regexLeft); + if (index === -1) { + break; + } + if (index > 0) { + data.push({ + type: "text", + data: text.slice(0, index), + }); + text = text.slice(index); // now text starts with delimiter + } + // ... so this always succeeds: + const i = delimiters.findIndex((delim) => text.startsWith(delim.left)); + index = findEndOfMath(delimiters[i].right, text, delimiters[i].left.length); + if (index === -1) { + break; + } + const rawData = text.slice(0, index + delimiters[i].right.length); + const math = amsRegex.test(rawData) + ? rawData + : text.slice(delimiters[i].left.length, index); + data.push({ + type: "math", + data: math, + rawData, + display: delimiters[i].display, + }); + text = text.slice(index + delimiters[i].right.length); + } + + if (text !== "") { + data.push({ + type: "text", + data: text, + }); + } + + return data; +}; + +export default splitAtDelimiters; diff --git a/frontend/node_modules/katex/contrib/auto-render/test/auto-render-spec.js b/frontend/node_modules/katex/contrib/auto-render/test/auto-render-spec.js new file mode 100644 index 0000000..e4038b5 --- /dev/null +++ b/frontend/node_modules/katex/contrib/auto-render/test/auto-render-spec.js @@ -0,0 +1,363 @@ +/** + * @jest-environment jsdom + */ +import splitAtDelimiters from "../splitAtDelimiters"; +import renderMathInElement from "../auto-render"; + +beforeEach(function() { + expect.extend({ + toSplitInto: function(actual, result, delimiters) { + const message = { + pass: true, + message: () => "'" + actual + "' split correctly", + }; + + const split = + splitAtDelimiters(actual, delimiters); + + if (split.length !== result.length) { + message.pass = false; + message.message = () => "Different number of splits: " + + split.length + " vs. " + result.length + " (" + + JSON.stringify(split) + " vs. " + + JSON.stringify(result) + ")"; + return message; + } + + for (let i = 0; i < split.length; i++) { + const real = split[i]; + const correct = result[i]; + + let good = true; + let diff; + + if (real.type !== correct.type) { + good = false; + diff = "type"; + } else if (real.data !== correct.data) { + good = false; + diff = "data"; + } else if (real.display !== correct.display) { + good = false; + diff = "display"; + } + + if (!good) { + message.pass = false; + message.message = () => "Difference at split " + + (i + 1) + ": " + JSON.stringify(real) + + " vs. " + JSON.stringify(correct) + + " (" + diff + " differs)"; + break; + } + } + + return message; + }, + }); +}); + +describe("A delimiter splitter", function() { + it("doesn't split when there are no delimiters", function() { + expect("hello").toSplitInto( + [ + {type: "text", data: "hello"}, + ], + [ + {left: "(", right: ")", display: false}, + ]); + }); + + it("doesn't create a math node with only one left delimiter", function() { + expect("hello ( world").toSplitInto( + [ + {type: "text", data: "hello "}, + {type: "text", data: "( world"}, + ], + [ + {left: "(", right: ")", display: false}, + ]); + }); + + it("doesn't split when there's only a right delimiter", function() { + expect("hello ) world").toSplitInto( + [ + {type: "text", data: "hello ) world"}, + ], + [ + {left: "(", right: ")", display: false}, + ]); + }); + + it("splits when there are both delimiters", function() { + expect("hello ( world ) boo").toSplitInto( + [ + {type: "text", data: "hello "}, + {type: "math", data: " world ", + rawData: "( world )", display: false}, + {type: "text", data: " boo"}, + ], + [ + {left: "(", right: ")", display: false}, + ]); + }); + + it("splits on multi-character delimiters", function() { + expect("hello [[ world ]] boo").toSplitInto( + [ + {type: "text", data: "hello "}, + {type: "math", data: " world ", + rawData: "[[ world ]]", display: false}, + {type: "text", data: " boo"}, + ], + [ + {left: "[[", right: "]]", display: false}, + ]); + expect("hello \\begin{equation} world \\end{equation} boo").toSplitInto( + [ + {type: "text", data: "hello "}, + {type: "math", data: "\\begin{equation} world \\end{equation}", + rawData: "\\begin{equation} world \\end{equation}", + display: false}, + {type: "text", data: " boo"}, + ], + [ + {left: "\\begin{equation}", right: "\\end{equation}", + display: false}, + ]); + }); + + it("splits multiple times", function() { + expect("hello ( world ) boo ( more ) stuff").toSplitInto( + [ + {type: "text", data: "hello "}, + {type: "math", data: " world ", + rawData: "( world )", display: false}, + {type: "text", data: " boo "}, + {type: "math", data: " more ", + rawData: "( more )", display: false}, + {type: "text", data: " stuff"}, + ], + [ + {left: "(", right: ")", display: false}, + ]); + }); + + it("leaves the ending when there's only a left delimiter", function() { + expect("hello ( world ) boo ( left").toSplitInto( + [ + {type: "text", data: "hello "}, + {type: "math", data: " world ", + rawData: "( world )", display: false}, + {type: "text", data: " boo "}, + {type: "text", data: "( left"}, + ], + [ + {left: "(", right: ")", display: false}, + ]); + }); + + it("doesn't split when close delimiters are in {}s", function() { + expect("hello ( world { ) } ) boo").toSplitInto( + [ + {type: "text", data: "hello "}, + {type: "math", data: " world { ) } ", + rawData: "( world { ) } )", display: false}, + {type: "text", data: " boo"}, + ], + [ + {left: "(", right: ")", display: false}, + ]); + + expect("hello ( world { { } ) } ) boo").toSplitInto( + [ + {type: "text", data: "hello "}, + {type: "math", data: " world { { } ) } ", + rawData: "( world { { } ) } )", display: false}, + {type: "text", data: " boo"}, + ], + [ + {left: "(", right: ")", display: false}, + ]); + }); + + it("correctly processes sequences of $..$", function() { + expect("$hello$$world$$boo$").toSplitInto( + [ + {type: "math", data: "hello", + rawData: "$hello$", display: false}, + {type: "math", data: "world", + rawData: "$world$", display: false}, + {type: "math", data: "boo", + rawData: "$boo$", display: false}, + ], + [ + {left: "$", right: "$", display: false}, + ]); + }); + + it("doesn't split at escaped delimiters", function() { + expect("hello ( world \\) ) boo").toSplitInto( + [ + {type: "text", data: "hello "}, + {type: "math", data: " world \\) ", + rawData: "( world \\) )", display: false}, + {type: "text", data: " boo"}, + ], + [ + {left: "(", right: ")", display: false}, + ]); + + /* TODO(emily): make this work maybe? + expect("hello \\( ( world ) boo").toSplitInto( + "(", ")", + [ + {type: "text", data: "hello \\( "}, + {type: "math", data: " world ", + rawData: "( world )", display: false}, + {type: "text", data: " boo"}, + ]); + */ + }); + + it("splits when the right and left delimiters are the same", function() { + expect("hello $ world $ boo").toSplitInto( + [ + {type: "text", data: "hello "}, + {type: "math", data: " world ", + rawData: "$ world $", display: false}, + {type: "text", data: " boo"}, + ], + [ + {left: "$", right: "$", display: false}, + ]); + }); + + it("ignores \\$", function() { + expect("$x = \\$5$").toSplitInto( + [ + {type: "math", data: "x = \\$5", + rawData: "$x = \\$5$", display: false}, + ], + [ + {left: "$", right: "$", display: false}, + ]); + }); + + it("remembers which delimiters are display-mode", function() { + const startData = "hello ( world ) boo"; + + expect(splitAtDelimiters(startData, + [{left:"(", right:")", display:true}])).toEqual( + [ + {type: "text", data: "hello "}, + {type: "math", data: " world ", + rawData: "( world )", display: true}, + {type: "text", data: " boo"}, + ]); + }); + + it("handles nested delimiters irrespective of order", function() { + expect(splitAtDelimiters("$\\fbox{\\(hi\\)}$", + [ + {left:"\\(", right:"\\)", display:false}, + {left:"$", right:"$", display:false}, + ])).toEqual( + [ + {type: "math", data: "\\fbox{\\(hi\\)}", + rawData: "$\\fbox{\\(hi\\)}$", display: false}, + ]); + expect(splitAtDelimiters("\\(\\fbox{$hi$}\\)", + [ + {left:"\\(", right:"\\)", display:false}, + {left:"$", right:"$", display:false}, + ])).toEqual( + [ + {type: "math", data: "\\fbox{$hi$}", + rawData: "\\(\\fbox{$hi$}\\)", display: false}, + ]); + }); + + it("handles a mix of $ and $$", function() { + expect(splitAtDelimiters("$hello$world$$boo$$", + [ + {left:"$$", right:"$$", display:true}, + {left:"$", right:"$", display:false}, + ])).toEqual( + [ + {type: "math", data: "hello", + rawData: "$hello$", display: false}, + {type: "text", data: "world"}, + {type: "math", data: "boo", + rawData: "$$boo$$", display: true}, + ]); + expect(splitAtDelimiters("$hello$$world$$$boo$$", + [ + {left:"$$", right:"$$", display:true}, + {left:"$", right:"$", display:false}, + ])).toEqual( + [ + {type: "math", data: "hello", + rawData: "$hello$", display: false}, + {type: "math", data: "world", + rawData: "$world$", display: false}, + {type: "math", data: "boo", + rawData: "$$boo$$", display: true}, + ]); + }); +}); + +describe("Pre-process callback", function() { + it("replace `-squared` with `^2 `", function() { + const el1 = document.createElement('div'); + el1.textContent = 'Circle equation: $x-squared + y-squared = r-squared$.'; + const el2 = document.createElement('div'); + el2.textContent = 'Circle equation: $x^2 + y^2 = r^2$.'; + const delimiters = [{left: "$", right: "$", display: false}]; + renderMathInElement(el1, { + delimiters, + preProcess: math => math.replace(/-squared/g, '^2'), + }); + renderMathInElement(el2, {delimiters}); + expect(el1.innerHTML).toEqual(el2.innerHTML); + }); +}); + +describe("Parse adjacent text nodes", function() { + it("parse adjacent text nodes with math", function() { + const textNodes = ['\\[', + 'x^2 + y^2 = r^2', + '\\]']; + const el = document.createElement('div'); + for (let i = 0; i < textNodes.length; i++) { + const txt = document.createTextNode(textNodes[i]); + el.appendChild(txt); + } + const el2 = document.createElement('div'); + const txt = document.createTextNode(textNodes.join('')); + el2.appendChild(txt); + const delimiters = [{left: "\\[", right: "\\]", display: true}]; + renderMathInElement(el, {delimiters}); + renderMathInElement(el2, {delimiters}); + expect(el).toStrictEqual(el2); + }); + + it("parse adjacent text nodes without math", function() { + const textNodes = ['Lorem ipsum dolor', + 'sit amet', + 'consectetur adipiscing elit']; + const el = document.createElement('div'); + for (let i = 0; i < textNodes.length; i++) { + const txt = document.createTextNode(textNodes[i]); + el.appendChild(txt); + } + const el2 = document.createElement('div'); + for (let i = 0; i < textNodes.length; i++) { + const txt = document.createTextNode(textNodes[i]); + el2.appendChild(txt); + } + const delimiters = [{left: "\\[", right: "\\]", display: true}]; + renderMathInElement(el, {delimiters}); + expect(el).toStrictEqual(el2); + }); +}); diff --git a/frontend/node_modules/katex/contrib/copy-tex/README.md b/frontend/node_modules/katex/contrib/copy-tex/README.md new file mode 100644 index 0000000..5506966 --- /dev/null +++ b/frontend/node_modules/katex/contrib/copy-tex/README.md @@ -0,0 +1,39 @@ +# Copy-tex extension + +This extension modifies the copy/paste behavior in any browser supporting the +[Clipboard API](https://developer.mozilla.org/en-US/docs/Web/API/ClipboardEvent) +so that, when selecting and copying KaTeX-rendered elements, the text +content of the resulting clipboard renders KaTeX elements as their LaTeX source +surrounded by specified delimiters. (The HTML content of the resulting +clipboard remains the selected HTML content, as it normally would.) +The default delimiters are `$...$` for inline math and `$$...$$` for display +math, but you can easy switch them to e.g. `\(...\)` and `\[...\]` by +modifying `copyDelimiters` in [the source code](copy-tex.js). +Note that a selection containing part of a KaTeX formula gets extended to +include the entire KaTeX formula. + +## Usage + +This extension isn't part of KaTeX proper, so the script should be separately +included in the page. + +```html + +``` + +(Note that, as of KaTeX 0.16.0, there is no longer a corresponding CSS file.) + +See [index.html](index.html) for an example. +(To run this example from a clone of the repository, run `yarn start` +in the root KaTeX directory, and then visit +http://localhost:7936/contrib/copy-tex/index.html +with your web browser.) + +If you want to build your own custom copy handler based on this one, +copy the `copy-tex.js` into your codebase and replace the `require` +statement with `require('katex/contrib/copy-tex/katex2tex.js')`. + +ECMAScript module is also available: +```html + +``` diff --git a/frontend/node_modules/katex/contrib/copy-tex/copy-tex.js b/frontend/node_modules/katex/contrib/copy-tex/copy-tex.js new file mode 100644 index 0000000..79c91d5 --- /dev/null +++ b/frontend/node_modules/katex/contrib/copy-tex/copy-tex.js @@ -0,0 +1,51 @@ +// @flow + +import katexReplaceWithTex from './katex2tex'; + +// Return
    element containing node, or null if not found. +function closestKatex(node: Node): ?Element { + // If node is a Text Node, for example, go up to containing Element, + // where we can apply the `closest` method. + const element: ?Element = + (node instanceof Element ? node : node.parentElement); + return element && element.closest('.katex'); +} + +// Global copy handler to modify behavior on/within .katex elements. +document.addEventListener('copy', function(event: ClipboardEvent) { + const selection = window.getSelection(); + if (selection.isCollapsed || !event.clipboardData) { + return; // default action OK if selection is empty or unchangeable + } + const clipboardData = event.clipboardData; + const range = selection.getRangeAt(0); + + // When start point is within a formula, expand to entire formula. + const startKatex = closestKatex(range.startContainer); + if (startKatex) { + range.setStartBefore(startKatex); + } + + // Similarly, when end point is within a formula, expand to entire formula. + const endKatex = closestKatex(range.endContainer); + if (endKatex) { + range.setEndAfter(endKatex); + } + + const fragment = range.cloneContents(); + if (!fragment.querySelector('.katex-mathml')) { + return; // default action OK if no .katex-mathml elements + } + + const htmlContents = Array.prototype.map.call(fragment.childNodes, + (el) => (el instanceof Text ? el.textContent : el.outerHTML) + ).join(''); + + // Preserve usual HTML copy/paste behavior. + clipboardData.setData('text/html', htmlContents); + // Rewrite plain-text version. + clipboardData.setData('text/plain', + katexReplaceWithTex(fragment).textContent); + // Prevent normal copy handling. + event.preventDefault(); +}); diff --git a/frontend/node_modules/katex/contrib/copy-tex/index.html b/frontend/node_modules/katex/contrib/copy-tex/index.html new file mode 100644 index 0000000..fa59d27 --- /dev/null +++ b/frontend/node_modules/katex/contrib/copy-tex/index.html @@ -0,0 +1,38 @@ + + + + + + Copy-tex test + + + + + + +

    Copy-tex test

    +

    Try copy/pasting some of the text below!

    +

    + Here is some \(\KaTeX\) math: $$ x^2+y^2=z^2 $$ + The variables are \(x\), \(y\), and \(z\), + which are all in \(\mathbb{R}^+\). + Q.E.D. +

    + + + diff --git a/frontend/node_modules/katex/contrib/copy-tex/katex2tex.js b/frontend/node_modules/katex/contrib/copy-tex/katex2tex.js new file mode 100644 index 0000000..927003c --- /dev/null +++ b/frontend/node_modules/katex/contrib/copy-tex/katex2tex.js @@ -0,0 +1,61 @@ +// @flow + +export interface CopyDelimiters { + inline: [string, string], + display: [string, string], +} + +// Set these to how you want inline and display math to be delimited. +export const defaultCopyDelimiters: CopyDelimiters = { + inline: ['$', '$'], // alternative: ['\(', '\)'] + display: ['$$', '$$'], // alternative: ['\[', '\]'] +}; + +// Replace .katex elements with their TeX source ( element). +// Modifies fragment in-place. Useful for writing your own 'copy' handler, +// as in copy-tex.js. +export function katexReplaceWithTex( + fragment: DocumentFragment, + copyDelimiters: CopyDelimiters = defaultCopyDelimiters +): DocumentFragment { + // Remove .katex-html blocks that are preceded by .katex-mathml blocks + // (which will get replaced below). + const katexHtml = fragment.querySelectorAll('.katex-mathml + .katex-html'); + for (let i = 0; i < katexHtml.length; i++) { + const element = katexHtml[i]; + if (element.remove) { + element.remove(); + } else if (element.parentNode) { + element.parentNode.removeChild(element); + } + } + // Replace .katex-mathml elements with their annotation (TeX source) + // descendant, with inline delimiters. + const katexMathml = fragment.querySelectorAll('.katex-mathml'); + for (let i = 0; i < katexMathml.length; i++) { + const element = katexMathml[i]; + const texSource = element.querySelector('annotation'); + if (texSource) { + if (element.replaceWith) { + element.replaceWith(texSource); + } else if (element.parentNode) { + element.parentNode.replaceChild(texSource, element); + } + texSource.innerHTML = copyDelimiters.inline[0] + + texSource.innerHTML + copyDelimiters.inline[1]; + } + } + // Switch display math to display delimiters. + const displays = fragment.querySelectorAll('.katex-display annotation'); + for (let i = 0; i < displays.length; i++) { + const element = displays[i]; + element.innerHTML = copyDelimiters.display[0] + + element.innerHTML.substr(copyDelimiters.inline[0].length, + element.innerHTML.length - copyDelimiters.inline[0].length + - copyDelimiters.inline[1].length) + + copyDelimiters.display[1]; + } + return fragment; +} + +export default katexReplaceWithTex; diff --git a/frontend/node_modules/katex/contrib/mathtex-script-type/README.md b/frontend/node_modules/katex/contrib/mathtex-script-type/README.md new file mode 100644 index 0000000..a3129dd --- /dev/null +++ b/frontend/node_modules/katex/contrib/mathtex-script-type/README.md @@ -0,0 +1,38 @@ +# `math/tex` Custom Script Type Extension + +This is an extension to automatically display code inside `script` tags with `type=math/tex` using KaTeX. +This script type is commonly used by MathJax, so this can be used to support compatibility with MathJax. + +### Usage + +This extension isn't part of KaTeX proper, so the script should be separately +included in the page, in addition to KaTeX. + +Load the extension by adding the following line to your HTML file. + +```html + +``` +You can download the script and use it locally, or from a local KaTeX installation instead. + +For example, in the following simple page, we first load KaTeX as usual. +Then, in the body, we use a `math/tex` script to typeset the equation `x+\sqrt{1-x^2}`. + + +```html + + + + + + + + + + + +``` + +ECMAScript module is also available: +```html + diff --git a/frontend/node_modules/katex/contrib/mathtex-script-type/mathtex-script-type.js b/frontend/node_modules/katex/contrib/mathtex-script-type/mathtex-script-type.js new file mode 100644 index 0000000..592b201 --- /dev/null +++ b/frontend/node_modules/katex/contrib/mathtex-script-type/mathtex-script-type.js @@ -0,0 +1,22 @@ +import katex from "katex"; + +let scripts = document.body.getElementsByTagName("script"); +scripts = Array.prototype.slice.call(scripts); +scripts.forEach(function(script) { + if (!script.type || !script.type.match(/math\/tex/i)) { + return -1; + } + const display = + (script.type.match(/mode\s*=\s*display(;|\s|\n|$)/) != null); + + const katexElement = document.createElement(display ? "div" : "span"); + katexElement.setAttribute("class", + display ? "equation" : "inline-equation"); + try { + katex.render(script.text, katexElement, {displayMode: display}); + } catch (err) { + //console.error(err); linter doesn't like this + katexElement.textContent = script.text; + } + script.parentNode.replaceChild(katexElement, script); +}); diff --git a/frontend/node_modules/katex/contrib/mhchem/README.md b/frontend/node_modules/katex/contrib/mhchem/README.md new file mode 100644 index 0000000..efa4ded --- /dev/null +++ b/frontend/node_modules/katex/contrib/mhchem/README.md @@ -0,0 +1,23 @@ +# mhchem extension + +This extension adds to KaTeX the `\ce` and `\pu` functions from the [mhchem](https://mhchem.github.io/MathJax-mhchem/) package. + +### Usage + +This extension isn't part of core KaTeX, so the script should be separately included. Write the following line into the HTML page's ``. Place it *after* the line that calls `katex.js`, and if you make use of the [auto-render](https://katex.org/docs/autorender.html) extension, place it *before* the line that calls `auto-render.js`. + +```html + +``` + +If you remove the `defer` attribute from this tag, then you must also remove the `defer` attribute from the ` + + + + + ... + +``` + +You can also [download KaTeX](https://github.com/KaTeX/KaTeX/releases) and host it yourself. + +For details on how to configure auto-render extension, refer to [the documentation](https://katex.org/docs/autorender.html). + +### API + +Call `katex.render` to render a TeX expression directly into a DOM element. +For example: + +```js +katex.render("c = \\pm\\sqrt{a^2 + b^2}", element, { + throwOnError: false +}); +``` + +Call `katex.renderToString` to generate an HTML string of the rendered math, +e.g., for server-side rendering. For example: + +```js +var html = katex.renderToString("c = \\pm\\sqrt{a^2 + b^2}", { + throwOnError: false +}); +// '...' +``` + +Make sure to include the CSS and font files in both cases. +If you are doing all rendering on the server, there is no need to include the +JavaScript on the client. + +The examples above use the `throwOnError: false` option, which renders invalid +inputs as the TeX source code in red (by default), with the error message as +hover text. For other available options, see the +[API documentation](https://katex.org/docs/api.html), +[options documentation](https://katex.org/docs/options.html), and +[handling errors documentation](https://katex.org/docs/error.html). + +## Demo and Documentation + +Learn more about using KaTeX [on the website](https://katex.org)! + +## Contributors + +### Code Contributors + +This project exists thanks to all the people who contribute code. If you'd like to help, see [our guide to contributing code](CONTRIBUTING.md). +Code contributors + +### Financial Contributors + +Become a financial contributor and help us sustain our community. + +#### Individuals + +Contribute on Open Collective + +#### Organizations + +Support this project with your organization. Your logo will show up here with a link to your website. + +Organization 1 +Organization 2 +Organization 3 +Organization 4 +Organization 5 +Organization 6 +Organization 7 +Organization 8 +Organization 9 +Organization 10 + +## License + +KaTeX is licensed under the [MIT License](https://opensource.org/licenses/MIT). diff --git a/frontend/node_modules/katex/dist/contrib/auto-render.js b/frontend/node_modules/katex/dist/contrib/auto-render.js new file mode 100644 index 0000000..842d92b --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/auto-render.js @@ -0,0 +1,338 @@ +(function webpackUniversalModuleDefinition(root, factory) { + if(typeof exports === 'object' && typeof module === 'object') + module.exports = factory(require("katex")); + else if(typeof define === 'function' && define.amd) + define(["katex"], factory); + else if(typeof exports === 'object') + exports["renderMathInElement"] = factory(require("katex")); + else + root["renderMathInElement"] = factory(root["katex"]); +})((typeof self !== 'undefined' ? self : this), function(__WEBPACK_EXTERNAL_MODULE__757__) { +return /******/ (function() { // webpackBootstrap +/******/ "use strict"; +/******/ var __webpack_modules__ = ({ + +/***/ 757: +/***/ (function(module) { + +module.exports = __WEBPACK_EXTERNAL_MODULE__757__; + +/***/ }) + +/******/ }); +/************************************************************************/ +/******/ // The module cache +/******/ var __webpack_module_cache__ = {}; +/******/ +/******/ // The require function +/******/ function __webpack_require__(moduleId) { +/******/ // Check if module is in cache +/******/ var cachedModule = __webpack_module_cache__[moduleId]; +/******/ if (cachedModule !== undefined) { +/******/ return cachedModule.exports; +/******/ } +/******/ // Create a new module (and put it into the cache) +/******/ var module = __webpack_module_cache__[moduleId] = { +/******/ // no module.id needed +/******/ // no module.loaded needed +/******/ exports: {} +/******/ }; +/******/ +/******/ // Execute the module function +/******/ __webpack_modules__[moduleId](module, module.exports, __webpack_require__); +/******/ +/******/ // Return the exports of the module +/******/ return module.exports; +/******/ } +/******/ +/************************************************************************/ +/******/ /* webpack/runtime/compat get default export */ +/******/ !function() { +/******/ // getDefaultExport function for compatibility with non-harmony modules +/******/ __webpack_require__.n = function(module) { +/******/ var getter = module && module.__esModule ? +/******/ function() { return module['default']; } : +/******/ function() { return module; }; +/******/ __webpack_require__.d(getter, { a: getter }); +/******/ return getter; +/******/ }; +/******/ }(); +/******/ +/******/ /* webpack/runtime/define property getters */ +/******/ !function() { +/******/ // define getter functions for harmony exports +/******/ __webpack_require__.d = function(exports, definition) { +/******/ for(var key in definition) { +/******/ if(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) { +/******/ Object.defineProperty(exports, key, { enumerable: true, get: definition[key] }); +/******/ } +/******/ } +/******/ }; +/******/ }(); +/******/ +/******/ /* webpack/runtime/hasOwnProperty shorthand */ +/******/ !function() { +/******/ __webpack_require__.o = function(obj, prop) { return Object.prototype.hasOwnProperty.call(obj, prop); } +/******/ }(); +/******/ +/************************************************************************/ +var __webpack_exports__ = {}; + +// EXPORTS +__webpack_require__.d(__webpack_exports__, { + "default": function() { return /* binding */ auto_render; } +}); + +// EXTERNAL MODULE: external "katex" +var external_katex_ = __webpack_require__(757); +var external_katex_default = /*#__PURE__*/__webpack_require__.n(external_katex_); +;// CONCATENATED MODULE: ./contrib/auto-render/splitAtDelimiters.js +/* eslint no-constant-condition:0 */ +const findEndOfMath = function (delimiter, text, startIndex) { + // Adapted from + // https://github.com/Khan/perseus/blob/master/src/perseus-markdown.jsx + let index = startIndex; + let braceLevel = 0; + const delimLength = delimiter.length; + + while (index < text.length) { + const character = text[index]; + + if (braceLevel <= 0 && text.slice(index, index + delimLength) === delimiter) { + return index; + } else if (character === "\\") { + index++; + } else if (character === "{") { + braceLevel++; + } else if (character === "}") { + braceLevel--; + } + + index++; + } + + return -1; +}; + +const escapeRegex = function (string) { + return string.replace(/[-/\\^$*+?.()|[\]{}]/g, "\\$&"); +}; + +const amsRegex = /^\\begin{/; + +const splitAtDelimiters = function (text, delimiters) { + let index; + const data = []; + const regexLeft = new RegExp("(" + delimiters.map(x => escapeRegex(x.left)).join("|") + ")"); + + while (true) { + index = text.search(regexLeft); + + if (index === -1) { + break; + } + + if (index > 0) { + data.push({ + type: "text", + data: text.slice(0, index) + }); + text = text.slice(index); // now text starts with delimiter + } // ... so this always succeeds: + + + const i = delimiters.findIndex(delim => text.startsWith(delim.left)); + index = findEndOfMath(delimiters[i].right, text, delimiters[i].left.length); + + if (index === -1) { + break; + } + + const rawData = text.slice(0, index + delimiters[i].right.length); + const math = amsRegex.test(rawData) ? rawData : text.slice(delimiters[i].left.length, index); + data.push({ + type: "math", + data: math, + rawData, + display: delimiters[i].display + }); + text = text.slice(index + delimiters[i].right.length); + } + + if (text !== "") { + data.push({ + type: "text", + data: text + }); + } + + return data; +}; + +/* harmony default export */ var auto_render_splitAtDelimiters = (splitAtDelimiters); +;// CONCATENATED MODULE: ./contrib/auto-render/auto-render.js +/* eslint no-console:0 */ + + +/* Note: optionsCopy is mutated by this method. If it is ever exposed in the + * API, we should copy it before mutating. + */ + +const renderMathInText = function (text, optionsCopy) { + const data = auto_render_splitAtDelimiters(text, optionsCopy.delimiters); + + if (data.length === 1 && data[0].type === 'text') { + // There is no formula in the text. + // Let's return null which means there is no need to replace + // the current text node with a new one. + return null; + } + + const fragment = document.createDocumentFragment(); + + for (let i = 0; i < data.length; i++) { + if (data[i].type === "text") { + fragment.appendChild(document.createTextNode(data[i].data)); + } else { + const span = document.createElement("span"); + let math = data[i].data; // Override any display mode defined in the settings with that + // defined by the text itself + + optionsCopy.displayMode = data[i].display; + + try { + if (optionsCopy.preProcess) { + math = optionsCopy.preProcess(math); + } + + external_katex_default().render(math, span, optionsCopy); + } catch (e) { + if (!(e instanceof (external_katex_default()).ParseError)) { + throw e; + } + + optionsCopy.errorCallback("KaTeX auto-render: Failed to parse `" + data[i].data + "` with ", e); + fragment.appendChild(document.createTextNode(data[i].rawData)); + continue; + } + + fragment.appendChild(span); + } + } + + return fragment; +}; + +const renderElem = function (elem, optionsCopy) { + for (let i = 0; i < elem.childNodes.length; i++) { + const childNode = elem.childNodes[i]; + + if (childNode.nodeType === 3) { + // Text node + // Concatenate all sibling text nodes. + // Webkit browsers split very large text nodes into smaller ones, + // so the delimiters may be split across different nodes. + let textContentConcat = childNode.textContent; + let sibling = childNode.nextSibling; + let nSiblings = 0; + + while (sibling && sibling.nodeType === Node.TEXT_NODE) { + textContentConcat += sibling.textContent; + sibling = sibling.nextSibling; + nSiblings++; + } + + const frag = renderMathInText(textContentConcat, optionsCopy); + + if (frag) { + // Remove extra text nodes + for (let j = 0; j < nSiblings; j++) { + childNode.nextSibling.remove(); + } + + i += frag.childNodes.length - 1; + elem.replaceChild(frag, childNode); + } else { + // If the concatenated text does not contain math + // the siblings will not either + i += nSiblings; + } + } else if (childNode.nodeType === 1) { + // Element node + const className = ' ' + childNode.className + ' '; + const shouldRender = optionsCopy.ignoredTags.indexOf(childNode.nodeName.toLowerCase()) === -1 && optionsCopy.ignoredClasses.every(x => className.indexOf(' ' + x + ' ') === -1); + + if (shouldRender) { + renderElem(childNode, optionsCopy); + } + } // Otherwise, it's something else, and ignore it. + + } +}; + +const renderMathInElement = function (elem, options) { + if (!elem) { + throw new Error("No element provided to render"); + } + + const optionsCopy = {}; // Object.assign(optionsCopy, option) + + for (const option in options) { + if (options.hasOwnProperty(option)) { + optionsCopy[option] = options[option]; + } + } // default options + + + optionsCopy.delimiters = optionsCopy.delimiters || [{ + left: "$$", + right: "$$", + display: true + }, { + left: "\\(", + right: "\\)", + display: false + }, // LaTeX uses $…$, but it ruins the display of normal `$` in text: + // {left: "$", right: "$", display: false}, + // $ must come after $$ + // Render AMS environments even if outside $$…$$ delimiters. + { + left: "\\begin{equation}", + right: "\\end{equation}", + display: true + }, { + left: "\\begin{align}", + right: "\\end{align}", + display: true + }, { + left: "\\begin{alignat}", + right: "\\end{alignat}", + display: true + }, { + left: "\\begin{gather}", + right: "\\end{gather}", + display: true + }, { + left: "\\begin{CD}", + right: "\\end{CD}", + display: true + }, { + left: "\\[", + right: "\\]", + display: true + }]; + optionsCopy.ignoredTags = optionsCopy.ignoredTags || ["script", "noscript", "style", "textarea", "pre", "code", "option"]; + optionsCopy.ignoredClasses = optionsCopy.ignoredClasses || []; + optionsCopy.errorCallback = optionsCopy.errorCallback || console.error; // Enable sharing of global macros defined via `\gdef` between different + // math elements within a single call to `renderMathInElement`. + + optionsCopy.macros = optionsCopy.macros || {}; + renderElem(elem, optionsCopy); +}; + +/* harmony default export */ var auto_render = (renderMathInElement); +__webpack_exports__ = __webpack_exports__["default"]; +/******/ return __webpack_exports__; +/******/ })() +; +}); \ No newline at end of file diff --git a/frontend/node_modules/katex/dist/contrib/auto-render.min.js b/frontend/node_modules/katex/dist/contrib/auto-render.min.js new file mode 100644 index 0000000..32a7dd8 --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/auto-render.min.js @@ -0,0 +1 @@ +!function(e,t){"object"==typeof exports&&"object"==typeof module?module.exports=t(require("katex")):"function"==typeof define&&define.amd?define(["katex"],t):"object"==typeof exports?exports.renderMathInElement=t(require("katex")):e.renderMathInElement=t(e.katex)}("undefined"!=typeof self?self:this,(function(e){return function(){"use strict";var t={757:function(t){t.exports=e}},n={};function r(e){var o=n[e];if(void 0!==o)return o.exports;var i=n[e]={exports:{}};return t[e](i,i.exports,r),i.exports}r.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return r.d(t,{a:t}),t},r.d=function(e,t){for(var n in t)r.o(t,n)&&!r.o(e,n)&&Object.defineProperty(e,n,{enumerable:!0,get:t[n]})},r.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)};var o={};r.d(o,{default:function(){return p}});var i=r(757),a=r.n(i);const l=function(e,t,n){let r=n,o=0;const i=e.length;for(;re.left.replace(/[-/\\^$*+?.()|[\]{}]/g,"\\$&"))).join("|")+")");for(;n=e.search(o),-1!==n;){n>0&&(r.push({type:"text",data:e.slice(0,n)}),e=e.slice(n));const o=t.findIndex((t=>e.startsWith(t.left)));if(n=l(t[o].right,e,t[o].left.length),-1===n)break;const i=e.slice(0,n+t[o].right.length),a=s.test(i)?i:e.slice(t[o].left.length,n);r.push({type:"math",data:a,rawData:i,display:t[o].display}),e=e.slice(n+t[o].right.length)}return""!==e&&r.push({type:"text",data:e}),r};const c=function(e,t){const n=d(e,t.delimiters);if(1===n.length&&"text"===n[0].type)return null;const r=document.createDocumentFragment();for(let e=0;e-1===e.indexOf(" "+t+" ")))&&f(r,t)}}};var p=function(e,t){if(!e)throw new Error("No element provided to render");const n={};for(const e in t)t.hasOwnProperty(e)&&(n[e]=t[e]);n.delimiters=n.delimiters||[{left:"$$",right:"$$",display:!0},{left:"\\(",right:"\\)",display:!1},{left:"\\begin{equation}",right:"\\end{equation}",display:!0},{left:"\\begin{align}",right:"\\end{align}",display:!0},{left:"\\begin{alignat}",right:"\\end{alignat}",display:!0},{left:"\\begin{gather}",right:"\\end{gather}",display:!0},{left:"\\begin{CD}",right:"\\end{CD}",display:!0},{left:"\\[",right:"\\]",display:!0}],n.ignoredTags=n.ignoredTags||["script","noscript","style","textarea","pre","code","option"],n.ignoredClasses=n.ignoredClasses||[],n.errorCallback=n.errorCallback||console.error,n.macros=n.macros||{},f(e,n)};return o=o.default}()})); \ No newline at end of file diff --git a/frontend/node_modules/katex/dist/contrib/auto-render.mjs b/frontend/node_modules/katex/dist/contrib/auto-render.mjs new file mode 100644 index 0000000..5ad25e6 --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/auto-render.mjs @@ -0,0 +1,244 @@ +import katex from '../katex.mjs'; + +/* eslint no-constant-condition:0 */ +var findEndOfMath = function findEndOfMath(delimiter, text, startIndex) { + // Adapted from + // https://github.com/Khan/perseus/blob/master/src/perseus-markdown.jsx + var index = startIndex; + var braceLevel = 0; + var delimLength = delimiter.length; + + while (index < text.length) { + var character = text[index]; + + if (braceLevel <= 0 && text.slice(index, index + delimLength) === delimiter) { + return index; + } else if (character === "\\") { + index++; + } else if (character === "{") { + braceLevel++; + } else if (character === "}") { + braceLevel--; + } + + index++; + } + + return -1; +}; + +var escapeRegex = function escapeRegex(string) { + return string.replace(/[-/\\^$*+?.()|[\]{}]/g, "\\$&"); +}; + +var amsRegex = /^\\begin{/; + +var splitAtDelimiters = function splitAtDelimiters(text, delimiters) { + var index; + var data = []; + var regexLeft = new RegExp("(" + delimiters.map(x => escapeRegex(x.left)).join("|") + ")"); + + while (true) { + index = text.search(regexLeft); + + if (index === -1) { + break; + } + + if (index > 0) { + data.push({ + type: "text", + data: text.slice(0, index) + }); + text = text.slice(index); // now text starts with delimiter + } // ... so this always succeeds: + + + var i = delimiters.findIndex(delim => text.startsWith(delim.left)); + index = findEndOfMath(delimiters[i].right, text, delimiters[i].left.length); + + if (index === -1) { + break; + } + + var rawData = text.slice(0, index + delimiters[i].right.length); + var math = amsRegex.test(rawData) ? rawData : text.slice(delimiters[i].left.length, index); + data.push({ + type: "math", + data: math, + rawData, + display: delimiters[i].display + }); + text = text.slice(index + delimiters[i].right.length); + } + + if (text !== "") { + data.push({ + type: "text", + data: text + }); + } + + return data; +}; + +/* eslint no-console:0 */ +/* Note: optionsCopy is mutated by this method. If it is ever exposed in the + * API, we should copy it before mutating. + */ + +var renderMathInText = function renderMathInText(text, optionsCopy) { + var data = splitAtDelimiters(text, optionsCopy.delimiters); + + if (data.length === 1 && data[0].type === 'text') { + // There is no formula in the text. + // Let's return null which means there is no need to replace + // the current text node with a new one. + return null; + } + + var fragment = document.createDocumentFragment(); + + for (var i = 0; i < data.length; i++) { + if (data[i].type === "text") { + fragment.appendChild(document.createTextNode(data[i].data)); + } else { + var span = document.createElement("span"); + var math = data[i].data; // Override any display mode defined in the settings with that + // defined by the text itself + + optionsCopy.displayMode = data[i].display; + + try { + if (optionsCopy.preProcess) { + math = optionsCopy.preProcess(math); + } + + katex.render(math, span, optionsCopy); + } catch (e) { + if (!(e instanceof katex.ParseError)) { + throw e; + } + + optionsCopy.errorCallback("KaTeX auto-render: Failed to parse `" + data[i].data + "` with ", e); + fragment.appendChild(document.createTextNode(data[i].rawData)); + continue; + } + + fragment.appendChild(span); + } + } + + return fragment; +}; + +var renderElem = function renderElem(elem, optionsCopy) { + for (var i = 0; i < elem.childNodes.length; i++) { + var childNode = elem.childNodes[i]; + + if (childNode.nodeType === 3) { + // Text node + // Concatenate all sibling text nodes. + // Webkit browsers split very large text nodes into smaller ones, + // so the delimiters may be split across different nodes. + var textContentConcat = childNode.textContent; + var sibling = childNode.nextSibling; + var nSiblings = 0; + + while (sibling && sibling.nodeType === Node.TEXT_NODE) { + textContentConcat += sibling.textContent; + sibling = sibling.nextSibling; + nSiblings++; + } + + var frag = renderMathInText(textContentConcat, optionsCopy); + + if (frag) { + // Remove extra text nodes + for (var j = 0; j < nSiblings; j++) { + childNode.nextSibling.remove(); + } + + i += frag.childNodes.length - 1; + elem.replaceChild(frag, childNode); + } else { + // If the concatenated text does not contain math + // the siblings will not either + i += nSiblings; + } + } else if (childNode.nodeType === 1) { + (function () { + // Element node + var className = ' ' + childNode.className + ' '; + var shouldRender = optionsCopy.ignoredTags.indexOf(childNode.nodeName.toLowerCase()) === -1 && optionsCopy.ignoredClasses.every(x => className.indexOf(' ' + x + ' ') === -1); + + if (shouldRender) { + renderElem(childNode, optionsCopy); + } + })(); + } // Otherwise, it's something else, and ignore it. + + } +}; + +var renderMathInElement = function renderMathInElement(elem, options) { + if (!elem) { + throw new Error("No element provided to render"); + } + + var optionsCopy = {}; // Object.assign(optionsCopy, option) + + for (var option in options) { + if (options.hasOwnProperty(option)) { + optionsCopy[option] = options[option]; + } + } // default options + + + optionsCopy.delimiters = optionsCopy.delimiters || [{ + left: "$$", + right: "$$", + display: true + }, { + left: "\\(", + right: "\\)", + display: false + }, // LaTeX uses $…$, but it ruins the display of normal `$` in text: + // {left: "$", right: "$", display: false}, + // $ must come after $$ + // Render AMS environments even if outside $$…$$ delimiters. + { + left: "\\begin{equation}", + right: "\\end{equation}", + display: true + }, { + left: "\\begin{align}", + right: "\\end{align}", + display: true + }, { + left: "\\begin{alignat}", + right: "\\end{alignat}", + display: true + }, { + left: "\\begin{gather}", + right: "\\end{gather}", + display: true + }, { + left: "\\begin{CD}", + right: "\\end{CD}", + display: true + }, { + left: "\\[", + right: "\\]", + display: true + }]; + optionsCopy.ignoredTags = optionsCopy.ignoredTags || ["script", "noscript", "style", "textarea", "pre", "code", "option"]; + optionsCopy.ignoredClasses = optionsCopy.ignoredClasses || []; + optionsCopy.errorCallback = optionsCopy.errorCallback || console.error; // Enable sharing of global macros defined via `\gdef` between different + // math elements within a single call to `renderMathInElement`. + + optionsCopy.macros = optionsCopy.macros || {}; + renderElem(elem, optionsCopy); +}; + +export { renderMathInElement as default }; diff --git a/frontend/node_modules/katex/dist/contrib/copy-tex.js b/frontend/node_modules/katex/dist/contrib/copy-tex.js new file mode 100644 index 0000000..8cfa7d6 --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/copy-tex.js @@ -0,0 +1,127 @@ +(function webpackUniversalModuleDefinition(root, factory) { + if(typeof exports === 'object' && typeof module === 'object') + module.exports = factory(); + else if(typeof define === 'function' && define.amd) + define([], factory); + else { + var a = factory(); + for(var i in a) (typeof exports === 'object' ? exports : root)[i] = a[i]; + } +})((typeof self !== 'undefined' ? self : this), function() { +return /******/ (function() { // webpackBootstrap +/******/ "use strict"; +var __webpack_exports__ = {}; + +;// CONCATENATED MODULE: ./contrib/copy-tex/katex2tex.js +// Set these to how you want inline and display math to be delimited. +const defaultCopyDelimiters = { + inline: ['$', '$'], + // alternative: ['\(', '\)'] + display: ['$$', '$$'] // alternative: ['\[', '\]'] + +}; // Replace .katex elements with their TeX source ( element). +// Modifies fragment in-place. Useful for writing your own 'copy' handler, +// as in copy-tex.js. + +function katexReplaceWithTex(fragment, copyDelimiters) { + if (copyDelimiters === void 0) { + copyDelimiters = defaultCopyDelimiters; + } + + // Remove .katex-html blocks that are preceded by .katex-mathml blocks + // (which will get replaced below). + const katexHtml = fragment.querySelectorAll('.katex-mathml + .katex-html'); + + for (let i = 0; i < katexHtml.length; i++) { + const element = katexHtml[i]; + + if (element.remove) { + element.remove(); + } else if (element.parentNode) { + element.parentNode.removeChild(element); + } + } // Replace .katex-mathml elements with their annotation (TeX source) + // descendant, with inline delimiters. + + + const katexMathml = fragment.querySelectorAll('.katex-mathml'); + + for (let i = 0; i < katexMathml.length; i++) { + const element = katexMathml[i]; + const texSource = element.querySelector('annotation'); + + if (texSource) { + if (element.replaceWith) { + element.replaceWith(texSource); + } else if (element.parentNode) { + element.parentNode.replaceChild(texSource, element); + } + + texSource.innerHTML = copyDelimiters.inline[0] + texSource.innerHTML + copyDelimiters.inline[1]; + } + } // Switch display math to display delimiters. + + + const displays = fragment.querySelectorAll('.katex-display annotation'); + + for (let i = 0; i < displays.length; i++) { + const element = displays[i]; + element.innerHTML = copyDelimiters.display[0] + element.innerHTML.substr(copyDelimiters.inline[0].length, element.innerHTML.length - copyDelimiters.inline[0].length - copyDelimiters.inline[1].length) + copyDelimiters.display[1]; + } + + return fragment; +} +/* harmony default export */ var katex2tex = (katexReplaceWithTex); +;// CONCATENATED MODULE: ./contrib/copy-tex/copy-tex.js + // Return
    element containing node, or null if not found. + +function closestKatex(node) { + // If node is a Text Node, for example, go up to containing Element, + // where we can apply the `closest` method. + const element = node instanceof Element ? node : node.parentElement; + return element && element.closest('.katex'); +} // Global copy handler to modify behavior on/within .katex elements. + + +document.addEventListener('copy', function (event) { + const selection = window.getSelection(); + + if (selection.isCollapsed || !event.clipboardData) { + return; // default action OK if selection is empty or unchangeable + } + + const clipboardData = event.clipboardData; + const range = selection.getRangeAt(0); // When start point is within a formula, expand to entire formula. + + const startKatex = closestKatex(range.startContainer); + + if (startKatex) { + range.setStartBefore(startKatex); + } // Similarly, when end point is within a formula, expand to entire formula. + + + const endKatex = closestKatex(range.endContainer); + + if (endKatex) { + range.setEndAfter(endKatex); + } + + const fragment = range.cloneContents(); + + if (!fragment.querySelector('.katex-mathml')) { + return; // default action OK if no .katex-mathml elements + } + + const htmlContents = Array.prototype.map.call(fragment.childNodes, el => el instanceof Text ? el.textContent : el.outerHTML).join(''); // Preserve usual HTML copy/paste behavior. + + clipboardData.setData('text/html', htmlContents); // Rewrite plain-text version. + + clipboardData.setData('text/plain', katex2tex(fragment).textContent); // Prevent normal copy handling. + + event.preventDefault(); +}); +__webpack_exports__ = __webpack_exports__["default"]; +/******/ return __webpack_exports__; +/******/ })() +; +}); \ No newline at end of file diff --git a/frontend/node_modules/katex/dist/contrib/copy-tex.min.js b/frontend/node_modules/katex/dist/contrib/copy-tex.min.js new file mode 100644 index 0000000..a826f4f --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/copy-tex.min.js @@ -0,0 +1 @@ +!function(e,t){if("object"==typeof exports&&"object"==typeof module)module.exports=t();else if("function"==typeof define&&define.amd)define([],t);else{var n=t();for(var o in n)("object"==typeof exports?exports:e)[o]=n[o]}}("undefined"!=typeof self?self:this,(function(){return function(){"use strict";var e={};const t={inline:["$","$"],display:["$$","$$"]};var n=function(e,n){void 0===n&&(n=t);const o=e.querySelectorAll(".katex-mathml + .katex-html");for(let e=0;ee instanceof Text?e.textContent:e.outerHTML)).join("");r.setData("text/html",c),r.setData("text/plain",n(s).textContent),e.preventDefault()})),e=e.default}()})); \ No newline at end of file diff --git a/frontend/node_modules/katex/dist/contrib/copy-tex.mjs b/frontend/node_modules/katex/dist/contrib/copy-tex.mjs new file mode 100644 index 0000000..cb9d657 --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/copy-tex.mjs @@ -0,0 +1,105 @@ +// Set these to how you want inline and display math to be delimited. +var defaultCopyDelimiters = { + inline: ['$', '$'], + // alternative: ['\(', '\)'] + display: ['$$', '$$'] // alternative: ['\[', '\]'] + +}; // Replace .katex elements with their TeX source ( element). +// Modifies fragment in-place. Useful for writing your own 'copy' handler, +// as in copy-tex.js. + +function katexReplaceWithTex(fragment, copyDelimiters) { + if (copyDelimiters === void 0) { + copyDelimiters = defaultCopyDelimiters; + } + + // Remove .katex-html blocks that are preceded by .katex-mathml blocks + // (which will get replaced below). + var katexHtml = fragment.querySelectorAll('.katex-mathml + .katex-html'); + + for (var i = 0; i < katexHtml.length; i++) { + var element = katexHtml[i]; + + if (element.remove) { + element.remove(); + } else if (element.parentNode) { + element.parentNode.removeChild(element); + } + } // Replace .katex-mathml elements with their annotation (TeX source) + // descendant, with inline delimiters. + + + var katexMathml = fragment.querySelectorAll('.katex-mathml'); + + for (var _i = 0; _i < katexMathml.length; _i++) { + var _element = katexMathml[_i]; + + var texSource = _element.querySelector('annotation'); + + if (texSource) { + if (_element.replaceWith) { + _element.replaceWith(texSource); + } else if (_element.parentNode) { + _element.parentNode.replaceChild(texSource, _element); + } + + texSource.innerHTML = copyDelimiters.inline[0] + texSource.innerHTML + copyDelimiters.inline[1]; + } + } // Switch display math to display delimiters. + + + var displays = fragment.querySelectorAll('.katex-display annotation'); + + for (var _i2 = 0; _i2 < displays.length; _i2++) { + var _element2 = displays[_i2]; + _element2.innerHTML = copyDelimiters.display[0] + _element2.innerHTML.substr(copyDelimiters.inline[0].length, _element2.innerHTML.length - copyDelimiters.inline[0].length - copyDelimiters.inline[1].length) + copyDelimiters.display[1]; + } + + return fragment; +} + +function closestKatex(node) { + // If node is a Text Node, for example, go up to containing Element, + // where we can apply the `closest` method. + var element = node instanceof Element ? node : node.parentElement; + return element && element.closest('.katex'); +} // Global copy handler to modify behavior on/within .katex elements. + + +document.addEventListener('copy', function (event) { + var selection = window.getSelection(); + + if (selection.isCollapsed || !event.clipboardData) { + return; // default action OK if selection is empty or unchangeable + } + + var clipboardData = event.clipboardData; + var range = selection.getRangeAt(0); // When start point is within a formula, expand to entire formula. + + var startKatex = closestKatex(range.startContainer); + + if (startKatex) { + range.setStartBefore(startKatex); + } // Similarly, when end point is within a formula, expand to entire formula. + + + var endKatex = closestKatex(range.endContainer); + + if (endKatex) { + range.setEndAfter(endKatex); + } + + var fragment = range.cloneContents(); + + if (!fragment.querySelector('.katex-mathml')) { + return; // default action OK if no .katex-mathml elements + } + + var htmlContents = Array.prototype.map.call(fragment.childNodes, el => el instanceof Text ? el.textContent : el.outerHTML).join(''); // Preserve usual HTML copy/paste behavior. + + clipboardData.setData('text/html', htmlContents); // Rewrite plain-text version. + + clipboardData.setData('text/plain', katexReplaceWithTex(fragment).textContent); // Prevent normal copy handling. + + event.preventDefault(); +}); diff --git a/frontend/node_modules/katex/dist/contrib/mathtex-script-type.js b/frontend/node_modules/katex/dist/contrib/mathtex-script-type.js new file mode 100644 index 0000000..f28af57 --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/mathtex-script-type.js @@ -0,0 +1,109 @@ +(function webpackUniversalModuleDefinition(root, factory) { + if(typeof exports === 'object' && typeof module === 'object') + module.exports = factory(require("katex")); + else if(typeof define === 'function' && define.amd) + define(["katex"], factory); + else { + var a = typeof exports === 'object' ? factory(require("katex")) : factory(root["katex"]); + for(var i in a) (typeof exports === 'object' ? exports : root)[i] = a[i]; + } +})((typeof self !== 'undefined' ? self : this), function(__WEBPACK_EXTERNAL_MODULE__757__) { +return /******/ (function() { // webpackBootstrap +/******/ "use strict"; +/******/ var __webpack_modules__ = ({ + +/***/ 757: +/***/ (function(module) { + +module.exports = __WEBPACK_EXTERNAL_MODULE__757__; + +/***/ }) + +/******/ }); +/************************************************************************/ +/******/ // The module cache +/******/ var __webpack_module_cache__ = {}; +/******/ +/******/ // The require function +/******/ function __webpack_require__(moduleId) { +/******/ // Check if module is in cache +/******/ var cachedModule = __webpack_module_cache__[moduleId]; +/******/ if (cachedModule !== undefined) { +/******/ return cachedModule.exports; +/******/ } +/******/ // Create a new module (and put it into the cache) +/******/ var module = __webpack_module_cache__[moduleId] = { +/******/ // no module.id needed +/******/ // no module.loaded needed +/******/ exports: {} +/******/ }; +/******/ +/******/ // Execute the module function +/******/ __webpack_modules__[moduleId](module, module.exports, __webpack_require__); +/******/ +/******/ // Return the exports of the module +/******/ return module.exports; +/******/ } +/******/ +/************************************************************************/ +/******/ /* webpack/runtime/compat get default export */ +/******/ !function() { +/******/ // getDefaultExport function for compatibility with non-harmony modules +/******/ __webpack_require__.n = function(module) { +/******/ var getter = module && module.__esModule ? +/******/ function() { return module['default']; } : +/******/ function() { return module; }; +/******/ __webpack_require__.d(getter, { a: getter }); +/******/ return getter; +/******/ }; +/******/ }(); +/******/ +/******/ /* webpack/runtime/define property getters */ +/******/ !function() { +/******/ // define getter functions for harmony exports +/******/ __webpack_require__.d = function(exports, definition) { +/******/ for(var key in definition) { +/******/ if(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) { +/******/ Object.defineProperty(exports, key, { enumerable: true, get: definition[key] }); +/******/ } +/******/ } +/******/ }; +/******/ }(); +/******/ +/******/ /* webpack/runtime/hasOwnProperty shorthand */ +/******/ !function() { +/******/ __webpack_require__.o = function(obj, prop) { return Object.prototype.hasOwnProperty.call(obj, prop); } +/******/ }(); +/******/ +/************************************************************************/ +var __webpack_exports__ = {}; +/* harmony import */ var katex__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(757); +/* harmony import */ var katex__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(katex__WEBPACK_IMPORTED_MODULE_0__); + +let scripts = document.body.getElementsByTagName("script"); +scripts = Array.prototype.slice.call(scripts); +scripts.forEach(function (script) { + if (!script.type || !script.type.match(/math\/tex/i)) { + return -1; + } + + const display = script.type.match(/mode\s*=\s*display(;|\s|\n|$)/) != null; + const katexElement = document.createElement(display ? "div" : "span"); + katexElement.setAttribute("class", display ? "equation" : "inline-equation"); + + try { + katex__WEBPACK_IMPORTED_MODULE_0___default().render(script.text, katexElement, { + displayMode: display + }); + } catch (err) { + //console.error(err); linter doesn't like this + katexElement.textContent = script.text; + } + + script.parentNode.replaceChild(katexElement, script); +}); +__webpack_exports__ = __webpack_exports__["default"]; +/******/ return __webpack_exports__; +/******/ })() +; +}); \ No newline at end of file diff --git a/frontend/node_modules/katex/dist/contrib/mathtex-script-type.min.js b/frontend/node_modules/katex/dist/contrib/mathtex-script-type.min.js new file mode 100644 index 0000000..fd747e4 --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/mathtex-script-type.min.js @@ -0,0 +1 @@ +!function(e,t){if("object"==typeof exports&&"object"==typeof module)module.exports=t(require("katex"));else if("function"==typeof define&&define.amd)define(["katex"],t);else{var n="object"==typeof exports?t(require("katex")):t(e.katex);for(var r in n)("object"==typeof exports?exports:e)[r]=n[r]}}("undefined"!=typeof self?self:this,(function(e){return function(){"use strict";var t={757:function(t){t.exports=e}},n={};function r(e){var o=n[e];if(void 0!==o)return o.exports;var i=n[e]={exports:{}};return t[e](i,i.exports,r),i.exports}r.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return r.d(t,{a:t}),t},r.d=function(e,t){for(var n in t)r.o(t,n)&&!r.o(e,n)&&Object.defineProperty(e,n,{enumerable:!0,get:t[n]})},r.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)};var o={},i=r(757),a=r.n(i);let u=document.body.getElementsByTagName("script");return u=Array.prototype.slice.call(u),u.forEach((function(e){if(!e.type||!e.type.match(/math\/tex/i))return-1;const t=null!=e.type.match(/mode\s*=\s*display(;|\s|\n|$)/),n=document.createElement(t?"div":"span");n.setAttribute("class",t?"equation":"inline-equation");try{a().render(e.text,n,{displayMode:t})}catch(t){n.textContent=e.text}e.parentNode.replaceChild(n,e)})),o=o.default}()})); \ No newline at end of file diff --git a/frontend/node_modules/katex/dist/contrib/mathtex-script-type.mjs b/frontend/node_modules/katex/dist/contrib/mathtex-script-type.mjs new file mode 100644 index 0000000..1083b92 --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/mathtex-script-type.mjs @@ -0,0 +1,24 @@ +import katex from '../katex.mjs'; + +var scripts = document.body.getElementsByTagName("script"); +scripts = Array.prototype.slice.call(scripts); +scripts.forEach(function (script) { + if (!script.type || !script.type.match(/math\/tex/i)) { + return -1; + } + + var display = script.type.match(/mode\s*=\s*display(;|\s|\n|$)/) != null; + var katexElement = document.createElement(display ? "div" : "span"); + katexElement.setAttribute("class", display ? "equation" : "inline-equation"); + + try { + katex.render(script.text, katexElement, { + displayMode: display + }); + } catch (err) { + //console.error(err); linter doesn't like this + katexElement.textContent = script.text; + } + + script.parentNode.replaceChild(katexElement, script); +}); diff --git a/frontend/node_modules/katex/dist/contrib/mhchem.js b/frontend/node_modules/katex/dist/contrib/mhchem.js new file mode 100644 index 0000000..2ddceaa --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/mhchem.js @@ -0,0 +1,3213 @@ +(function webpackUniversalModuleDefinition(root, factory) { + if(typeof exports === 'object' && typeof module === 'object') + module.exports = factory(require("katex")); + else if(typeof define === 'function' && define.amd) + define(["katex"], factory); + else { + var a = typeof exports === 'object' ? factory(require("katex")) : factory(root["katex"]); + for(var i in a) (typeof exports === 'object' ? exports : root)[i] = a[i]; + } +})((typeof self !== 'undefined' ? self : this), function(__WEBPACK_EXTERNAL_MODULE__757__) { +return /******/ (function() { // webpackBootstrap +/******/ "use strict"; +/******/ var __webpack_modules__ = ({ + +/***/ 757: +/***/ (function(module) { + +module.exports = __WEBPACK_EXTERNAL_MODULE__757__; + +/***/ }) + +/******/ }); +/************************************************************************/ +/******/ // The module cache +/******/ var __webpack_module_cache__ = {}; +/******/ +/******/ // The require function +/******/ function __webpack_require__(moduleId) { +/******/ // Check if module is in cache +/******/ var cachedModule = __webpack_module_cache__[moduleId]; +/******/ if (cachedModule !== undefined) { +/******/ return cachedModule.exports; +/******/ } +/******/ // Create a new module (and put it into the cache) +/******/ var module = __webpack_module_cache__[moduleId] = { +/******/ // no module.id needed +/******/ // no module.loaded needed +/******/ exports: {} +/******/ }; +/******/ +/******/ // Execute the module function +/******/ __webpack_modules__[moduleId](module, module.exports, __webpack_require__); +/******/ +/******/ // Return the exports of the module +/******/ return module.exports; +/******/ } +/******/ +/************************************************************************/ +/******/ /* webpack/runtime/compat get default export */ +/******/ !function() { +/******/ // getDefaultExport function for compatibility with non-harmony modules +/******/ __webpack_require__.n = function(module) { +/******/ var getter = module && module.__esModule ? +/******/ function() { return module['default']; } : +/******/ function() { return module; }; +/******/ __webpack_require__.d(getter, { a: getter }); +/******/ return getter; +/******/ }; +/******/ }(); +/******/ +/******/ /* webpack/runtime/define property getters */ +/******/ !function() { +/******/ // define getter functions for harmony exports +/******/ __webpack_require__.d = function(exports, definition) { +/******/ for(var key in definition) { +/******/ if(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) { +/******/ Object.defineProperty(exports, key, { enumerable: true, get: definition[key] }); +/******/ } +/******/ } +/******/ }; +/******/ }(); +/******/ +/******/ /* webpack/runtime/hasOwnProperty shorthand */ +/******/ !function() { +/******/ __webpack_require__.o = function(obj, prop) { return Object.prototype.hasOwnProperty.call(obj, prop); } +/******/ }(); +/******/ +/************************************************************************/ +var __webpack_exports__ = {}; +/* harmony import */ var katex__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(757); +/* harmony import */ var katex__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(katex__WEBPACK_IMPORTED_MODULE_0__); +/* eslint-disable */ + +/* -*- Mode: JavaScript; indent-tabs-mode:nil; js-indent-level: 2 -*- */ + +/* vim: set ts=2 et sw=2 tw=80: */ + +/************************************************************* + * + * KaTeX mhchem.js + * + * This file implements a KaTeX version of mhchem version 3.3.0. + * It is adapted from MathJax/extensions/TeX/mhchem.js + * It differs from the MathJax version as follows: + * 1. The interface is changed so that it can be called from KaTeX, not MathJax. + * 2. \rlap and \llap are replaced with \mathrlap and \mathllap. + * 3. Four lines of code are edited in order to use \raisebox instead of \raise. + * 4. The reaction arrow code is simplified. All reaction arrows are rendered + * using KaTeX extensible arrows instead of building non-extensible arrows. + * 5. \tripledash vertical alignment is slightly adjusted. + * + * This code, as other KaTeX code, is released under the MIT license. + * + * /************************************************************* + * + * MathJax/extensions/TeX/mhchem.js + * + * Implements the \ce command for handling chemical formulas + * from the mhchem LaTeX package. + * + * --------------------------------------------------------------------- + * + * Copyright (c) 2011-2015 The MathJax Consortium + * Copyright (c) 2015-2018 Martin Hensel + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +// +// Coding Style +// - use '' for identifiers that can by minified/uglified +// - use "" for strings that need to stay untouched +// version: "3.3.0" for MathJax and KaTeX +// Add \ce, \pu, and \tripledash to the KaTeX macros. +katex__WEBPACK_IMPORTED_MODULE_0___default().__defineMacro("\\ce", function (context) { + return chemParse(context.consumeArgs(1)[0], "ce"); +}); + +katex__WEBPACK_IMPORTED_MODULE_0___default().__defineMacro("\\pu", function (context) { + return chemParse(context.consumeArgs(1)[0], "pu"); +}); // Needed for \bond for the ~ forms +// Raise by 2.56mu, not 2mu. We're raising a hyphen-minus, U+002D, not +// a mathematical minus, U+2212. So we need that extra 0.56. + + +katex__WEBPACK_IMPORTED_MODULE_0___default().__defineMacro("\\tripledash", "{\\vphantom{-}\\raisebox{2.56mu}{$\\mkern2mu" + "\\tiny\\text{-}\\mkern1mu\\text{-}\\mkern1mu\\text{-}\\mkern2mu$}}"); + + // +// This is the main function for handing the \ce and \pu commands. +// It takes the argument to \ce or \pu and returns the corresponding TeX string. +// + +var chemParse = function (tokens, stateMachine) { + // Recreate the argument string from KaTeX's array of tokens. + var str = ""; + var expectedLoc = tokens.length && tokens[tokens.length - 1].loc.start; + + for (var i = tokens.length - 1; i >= 0; i--) { + if (tokens[i].loc.start > expectedLoc) { + // context.consumeArgs has eaten a space. + str += " "; + expectedLoc = tokens[i].loc.start; + } + + str += tokens[i].text; + expectedLoc += tokens[i].text.length; + } + + var tex = texify.go(mhchemParser.go(str, stateMachine)); + return tex; +}; // +// Core parser for mhchem syntax (recursive) +// + +/** @type {MhchemParser} */ + + +var mhchemParser = { + // + // Parses mchem \ce syntax + // + // Call like + // go("H2O"); + // + go: function (input, stateMachine) { + if (!input) { + return []; + } + + if (stateMachine === undefined) { + stateMachine = 'ce'; + } + + var state = '0'; // + // String buffers for parsing: + // + // buffer.a == amount + // buffer.o == element + // buffer.b == left-side superscript + // buffer.p == left-side subscript + // buffer.q == right-side subscript + // buffer.d == right-side superscript + // + // buffer.r == arrow + // buffer.rdt == arrow, script above, type + // buffer.rd == arrow, script above, content + // buffer.rqt == arrow, script below, type + // buffer.rq == arrow, script below, content + // + // buffer.text_ + // buffer.rm + // etc. + // + // buffer.parenthesisLevel == int, starting at 0 + // buffer.sb == bool, space before + // buffer.beginsWithBond == bool + // + // These letters are also used as state names. + // + // Other states: + // 0 == begin of main part (arrow/operator unlikely) + // 1 == next entity + // 2 == next entity (arrow/operator unlikely) + // 3 == next atom + // c == macro + // + + /** @type {Buffer} */ + + var buffer = {}; + buffer['parenthesisLevel'] = 0; + input = input.replace(/\n/g, " "); + input = input.replace(/[\u2212\u2013\u2014\u2010]/g, "-"); + input = input.replace(/[\u2026]/g, "..."); // + // Looks through mhchemParser.transitions, to execute a matching action + // (recursive) + // + + var lastInput; + var watchdog = 10; + /** @type {ParserOutput[]} */ + + var output = []; + + while (true) { + if (lastInput !== input) { + watchdog = 10; + lastInput = input; + } else { + watchdog--; + } // + // Find actions in transition table + // + + + var machine = mhchemParser.stateMachines[stateMachine]; + var t = machine.transitions[state] || machine.transitions['*']; + + iterateTransitions: for (var i = 0; i < t.length; i++) { + var matches = mhchemParser.patterns.match_(t[i].pattern, input); + + if (matches) { + // + // Execute actions + // + var task = t[i].task; + + for (var iA = 0; iA < task.action_.length; iA++) { + var o; // + // Find and execute action + // + + if (machine.actions[task.action_[iA].type_]) { + o = machine.actions[task.action_[iA].type_](buffer, matches.match_, task.action_[iA].option); + } else if (mhchemParser.actions[task.action_[iA].type_]) { + o = mhchemParser.actions[task.action_[iA].type_](buffer, matches.match_, task.action_[iA].option); + } else { + throw ["MhchemBugA", "mhchem bug A. Please report. (" + task.action_[iA].type_ + ")"]; // Trying to use non-existing action + } // + // Add output + // + + + mhchemParser.concatArray(output, o); + } // + // Set next state, + // Shorten input, + // Continue with next character + // (= apply only one transition per position) + // + + + state = task.nextState || state; + + if (input.length > 0) { + if (!task.revisit) { + input = matches.remainder; + } + + if (!task.toContinue) { + break iterateTransitions; + } + } else { + return output; + } + } + } // + // Prevent infinite loop + // + + + if (watchdog <= 0) { + throw ["MhchemBugU", "mhchem bug U. Please report."]; // Unexpected character + } + } + }, + concatArray: function (a, b) { + if (b) { + if (Array.isArray(b)) { + for (var iB = 0; iB < b.length; iB++) { + a.push(b[iB]); + } + } else { + a.push(b); + } + } + }, + patterns: { + // + // Matching patterns + // either regexps or function that return null or {match_:"a", remainder:"bc"} + // + patterns: { + // property names must not look like integers ("2") for correct property traversal order, later on + 'empty': /^$/, + 'else': /^./, + 'else2': /^./, + 'space': /^\s/, + 'space A': /^\s(?=[A-Z\\$])/, + 'space$': /^\s$/, + 'a-z': /^[a-z]/, + 'x': /^x/, + 'x$': /^x$/, + 'i$': /^i$/, + 'letters': /^(?:[a-zA-Z\u03B1-\u03C9\u0391-\u03A9?@]|(?:\\(?:alpha|beta|gamma|delta|epsilon|zeta|eta|theta|iota|kappa|lambda|mu|nu|xi|omicron|pi|rho|sigma|tau|upsilon|phi|chi|psi|omega|Gamma|Delta|Theta|Lambda|Xi|Pi|Sigma|Upsilon|Phi|Psi|Omega)(?:\s+|\{\}|(?![a-zA-Z]))))+/, + '\\greek': /^\\(?:alpha|beta|gamma|delta|epsilon|zeta|eta|theta|iota|kappa|lambda|mu|nu|xi|omicron|pi|rho|sigma|tau|upsilon|phi|chi|psi|omega|Gamma|Delta|Theta|Lambda|Xi|Pi|Sigma|Upsilon|Phi|Psi|Omega)(?:\s+|\{\}|(?![a-zA-Z]))/, + 'one lowercase latin letter $': /^(?:([a-z])(?:$|[^a-zA-Z]))$/, + '$one lowercase latin letter$ $': /^\$(?:([a-z])(?:$|[^a-zA-Z]))\$$/, + 'one lowercase greek letter $': /^(?:\$?[\u03B1-\u03C9]\$?|\$?\\(?:alpha|beta|gamma|delta|epsilon|zeta|eta|theta|iota|kappa|lambda|mu|nu|xi|omicron|pi|rho|sigma|tau|upsilon|phi|chi|psi|omega)\s*\$?)(?:\s+|\{\}|(?![a-zA-Z]))$/, + 'digits': /^[0-9]+/, + '-9.,9': /^[+\-]?(?:[0-9]+(?:[,.][0-9]+)?|[0-9]*(?:\.[0-9]+))/, + '-9.,9 no missing 0': /^[+\-]?[0-9]+(?:[.,][0-9]+)?/, + '(-)(9.,9)(e)(99)': function (input) { + var m = input.match(/^(\+\-|\+\/\-|\+|\-|\\pm\s?)?([0-9]+(?:[,.][0-9]+)?|[0-9]*(?:\.[0-9]+))?(\((?:[0-9]+(?:[,.][0-9]+)?|[0-9]*(?:\.[0-9]+))\))?(?:([eE]|\s*(\*|x|\\times|\u00D7)\s*10\^)([+\-]?[0-9]+|\{[+\-]?[0-9]+\}))?/); + + if (m && m[0]) { + return { + match_: m.splice(1), + remainder: input.substr(m[0].length) + }; + } + + return null; + }, + '(-)(9)^(-9)': function (input) { + var m = input.match(/^(\+\-|\+\/\-|\+|\-|\\pm\s?)?([0-9]+(?:[,.][0-9]+)?|[0-9]*(?:\.[0-9]+)?)\^([+\-]?[0-9]+|\{[+\-]?[0-9]+\})/); + + if (m && m[0]) { + return { + match_: m.splice(1), + remainder: input.substr(m[0].length) + }; + } + + return null; + }, + 'state of aggregation $': function (input) { + // ... or crystal system + var a = mhchemParser.patterns.findObserveGroups(input, "", /^\([a-z]{1,3}(?=[\),])/, ")", ""); // (aq), (aq,$\infty$), (aq, sat) + + if (a && a.remainder.match(/^($|[\s,;\)\]\}])/)) { + return a; + } // AND end of 'phrase' + + + var m = input.match(/^(?:\((?:\\ca\s?)?\$[amothc]\$\))/); // OR crystal system ($o$) (\ca$c$) + + if (m) { + return { + match_: m[0], + remainder: input.substr(m[0].length) + }; + } + + return null; + }, + '_{(state of aggregation)}$': /^_\{(\([a-z]{1,3}\))\}/, + '{[(': /^(?:\\\{|\[|\()/, + ')]}': /^(?:\)|\]|\\\})/, + ', ': /^[,;]\s*/, + ',': /^[,;]/, + '.': /^[.]/, + '. ': /^([.\u22C5\u00B7\u2022])\s*/, + '...': /^\.\.\.(?=$|[^.])/, + '* ': /^([*])\s*/, + '^{(...)}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "^{", "", "", "}"); + }, + '^($...$)': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "^", "$", "$", ""); + }, + '^a': /^\^([0-9]+|[^\\_])/, + '^\\x{}{}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "^", /^\\[a-zA-Z]+\{/, "}", "", "", "{", "}", "", true); + }, + '^\\x{}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "^", /^\\[a-zA-Z]+\{/, "}", ""); + }, + '^\\x': /^\^(\\[a-zA-Z]+)\s*/, + '^(-1)': /^\^(-?\d+)/, + '\'': /^'/, + '_{(...)}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "_{", "", "", "}"); + }, + '_($...$)': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "_", "$", "$", ""); + }, + '_9': /^_([+\-]?[0-9]+|[^\\])/, + '_\\x{}{}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "_", /^\\[a-zA-Z]+\{/, "}", "", "", "{", "}", "", true); + }, + '_\\x{}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "_", /^\\[a-zA-Z]+\{/, "}", ""); + }, + '_\\x': /^_(\\[a-zA-Z]+)\s*/, + '^_': /^(?:\^(?=_)|\_(?=\^)|[\^_]$)/, + '{}': /^\{\}/, + '{...}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "", "{", "}", ""); + }, + '{(...)}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "{", "", "", "}"); + }, + '$...$': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "", "$", "$", ""); + }, + '${(...)}$': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "${", "", "", "}$"); + }, + '$(...)$': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "$", "", "", "$"); + }, + '=<>': /^[=<>]/, + '#': /^[#\u2261]/, + '+': /^\+/, + '-$': /^-(?=[\s_},;\]/]|$|\([a-z]+\))/, + // -space -, -; -] -/ -$ -state-of-aggregation + '-9': /^-(?=[0-9])/, + '- orbital overlap': /^-(?=(?:[spd]|sp)(?:$|[\s,;\)\]\}]))/, + '-': /^-/, + 'pm-operator': /^(?:\\pm|\$\\pm\$|\+-|\+\/-)/, + 'operator': /^(?:\+|(?:[\-=<>]|<<|>>|\\approx|\$\\approx\$)(?=\s|$|-?[0-9]))/, + 'arrowUpDown': /^(?:v|\(v\)|\^|\(\^\))(?=$|[\s,;\)\]\}])/, + '\\bond{(...)}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "\\bond{", "", "", "}"); + }, + '->': /^(?:<->|<-->|->|<-|<=>>|<<=>|<=>|[\u2192\u27F6\u21CC])/, + 'CMT': /^[CMT](?=\[)/, + '[(...)]': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "[", "", "", "]"); + }, + '1st-level escape': /^(&|\\\\|\\hline)\s*/, + '\\,': /^(?:\\[,\ ;:])/, + // \\x - but output no space before + '\\x{}{}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "", /^\\[a-zA-Z]+\{/, "}", "", "", "{", "}", "", true); + }, + '\\x{}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "", /^\\[a-zA-Z]+\{/, "}", ""); + }, + '\\ca': /^\\ca(?:\s+|(?![a-zA-Z]))/, + '\\x': /^(?:\\[a-zA-Z]+\s*|\\[_&{}%])/, + 'orbital': /^(?:[0-9]{1,2}[spdfgh]|[0-9]{0,2}sp)(?=$|[^a-zA-Z])/, + // only those with numbers in front, because the others will be formatted correctly anyway + 'others': /^[\/~|]/, + '\\frac{(...)}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "\\frac{", "", "", "}", "{", "", "", "}"); + }, + '\\overset{(...)}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "\\overset{", "", "", "}", "{", "", "", "}"); + }, + '\\underset{(...)}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "\\underset{", "", "", "}", "{", "", "", "}"); + }, + '\\underbrace{(...)}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "\\underbrace{", "", "", "}_", "{", "", "", "}"); + }, + '\\color{(...)}0': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "\\color{", "", "", "}"); + }, + '\\color{(...)}{(...)}1': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "\\color{", "", "", "}", "{", "", "", "}"); + }, + '\\color(...){(...)}2': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "\\color", "\\", "", /^(?=\{)/, "{", "", "", "}"); + }, + '\\ce{(...)}': function (input) { + return mhchemParser.patterns.findObserveGroups(input, "\\ce{", "", "", "}"); + }, + 'oxidation$': /^(?:[+-][IVX]+|\\pm\s*0|\$\\pm\$\s*0)$/, + 'd-oxidation$': /^(?:[+-]?\s?[IVX]+|\\pm\s*0|\$\\pm\$\s*0)$/, + // 0 could be oxidation or charge + 'roman numeral': /^[IVX]+/, + '1/2$': /^[+\-]?(?:[0-9]+|\$[a-z]\$|[a-z])\/[0-9]+(?:\$[a-z]\$|[a-z])?$/, + 'amount': function (input) { + var match; // e.g. 2, 0.5, 1/2, -2, n/2, +; $a$ could be added later in parsing + + match = input.match(/^(?:(?:(?:\([+\-]?[0-9]+\/[0-9]+\)|[+\-]?(?:[0-9]+|\$[a-z]\$|[a-z])\/[0-9]+|[+\-]?[0-9]+[.,][0-9]+|[+\-]?\.[0-9]+|[+\-]?[0-9]+)(?:[a-z](?=\s*[A-Z]))?)|[+\-]?[a-z](?=\s*[A-Z])|\+(?!\s))/); + + if (match) { + return { + match_: match[0], + remainder: input.substr(match[0].length) + }; + } + + var a = mhchemParser.patterns.findObserveGroups(input, "", "$", "$", ""); + + if (a) { + // e.g. $2n-1$, $-$ + match = a.match_.match(/^\$(?:\(?[+\-]?(?:[0-9]*[a-z]?[+\-])?[0-9]*[a-z](?:[+\-][0-9]*[a-z]?)?\)?|\+|-)\$$/); + + if (match) { + return { + match_: match[0], + remainder: input.substr(match[0].length) + }; + } + } + + return null; + }, + 'amount2': function (input) { + return this['amount'](input); + }, + '(KV letters),': /^(?:[A-Z][a-z]{0,2}|i)(?=,)/, + 'formula$': function (input) { + if (input.match(/^\([a-z]+\)$/)) { + return null; + } // state of aggregation = no formula + + + var match = input.match(/^(?:[a-z]|(?:[0-9\ \+\-\,\.\(\)]+[a-z])+[0-9\ \+\-\,\.\(\)]*|(?:[a-z][0-9\ \+\-\,\.\(\)]+)+[a-z]?)$/); + + if (match) { + return { + match_: match[0], + remainder: input.substr(match[0].length) + }; + } + + return null; + }, + 'uprightEntities': /^(?:pH|pOH|pC|pK|iPr|iBu)(?=$|[^a-zA-Z])/, + '/': /^\s*(\/)\s*/, + '//': /^\s*(\/\/)\s*/, + '*': /^\s*[*.]\s*/ + }, + findObserveGroups: function (input, begExcl, begIncl, endIncl, endExcl, beg2Excl, beg2Incl, end2Incl, end2Excl, combine) { + /** @type {{(input: string, pattern: string | RegExp): string | string[] | null;}} */ + var _match = function (input, pattern) { + if (typeof pattern === "string") { + if (input.indexOf(pattern) !== 0) { + return null; + } + + return pattern; + } else { + var match = input.match(pattern); + + if (!match) { + return null; + } + + return match[0]; + } + }; + /** @type {{(input: string, i: number, endChars: string | RegExp): {endMatchBegin: number, endMatchEnd: number} | null;}} */ + + + var _findObserveGroups = function (input, i, endChars) { + var braces = 0; + + while (i < input.length) { + var a = input.charAt(i); + + var match = _match(input.substr(i), endChars); + + if (match !== null && braces === 0) { + return { + endMatchBegin: i, + endMatchEnd: i + match.length + }; + } else if (a === "{") { + braces++; + } else if (a === "}") { + if (braces === 0) { + throw ["ExtraCloseMissingOpen", "Extra close brace or missing open brace"]; + } else { + braces--; + } + } + + i++; + } + + if (braces > 0) { + return null; + } + + return null; + }; + + var match = _match(input, begExcl); + + if (match === null) { + return null; + } + + input = input.substr(match.length); + match = _match(input, begIncl); + + if (match === null) { + return null; + } + + var e = _findObserveGroups(input, match.length, endIncl || endExcl); + + if (e === null) { + return null; + } + + var match1 = input.substring(0, endIncl ? e.endMatchEnd : e.endMatchBegin); + + if (!(beg2Excl || beg2Incl)) { + return { + match_: match1, + remainder: input.substr(e.endMatchEnd) + }; + } else { + var group2 = this.findObserveGroups(input.substr(e.endMatchEnd), beg2Excl, beg2Incl, end2Incl, end2Excl); + + if (group2 === null) { + return null; + } + /** @type {string[]} */ + + + var matchRet = [match1, group2.match_]; + return { + match_: combine ? matchRet.join("") : matchRet, + remainder: group2.remainder + }; + } + }, + // + // Matching function + // e.g. match("a", input) will look for the regexp called "a" and see if it matches + // returns null or {match_:"a", remainder:"bc"} + // + match_: function (m, input) { + var pattern = mhchemParser.patterns.patterns[m]; + + if (pattern === undefined) { + throw ["MhchemBugP", "mhchem bug P. Please report. (" + m + ")"]; // Trying to use non-existing pattern + } else if (typeof pattern === "function") { + return mhchemParser.patterns.patterns[m](input); // cannot use cached var pattern here, because some pattern functions need this===mhchemParser + } else { + // RegExp + var match = input.match(pattern); + + if (match) { + var mm; + + if (match[2]) { + mm = [match[1], match[2]]; + } else if (match[1]) { + mm = match[1]; + } else { + mm = match[0]; + } + + return { + match_: mm, + remainder: input.substr(match[0].length) + }; + } + + return null; + } + } + }, + // + // Generic state machine actions + // + actions: { + 'a=': function (buffer, m) { + buffer.a = (buffer.a || "") + m; + }, + 'b=': function (buffer, m) { + buffer.b = (buffer.b || "") + m; + }, + 'p=': function (buffer, m) { + buffer.p = (buffer.p || "") + m; + }, + 'o=': function (buffer, m) { + buffer.o = (buffer.o || "") + m; + }, + 'q=': function (buffer, m) { + buffer.q = (buffer.q || "") + m; + }, + 'd=': function (buffer, m) { + buffer.d = (buffer.d || "") + m; + }, + 'rm=': function (buffer, m) { + buffer.rm = (buffer.rm || "") + m; + }, + 'text=': function (buffer, m) { + buffer.text_ = (buffer.text_ || "") + m; + }, + 'insert': function (buffer, m, a) { + return { + type_: a + }; + }, + 'insert+p1': function (buffer, m, a) { + return { + type_: a, + p1: m + }; + }, + 'insert+p1+p2': function (buffer, m, a) { + return { + type_: a, + p1: m[0], + p2: m[1] + }; + }, + 'copy': function (buffer, m) { + return m; + }, + 'rm': function (buffer, m) { + return { + type_: 'rm', + p1: m || "" + }; + }, + 'text': function (buffer, m) { + return mhchemParser.go(m, 'text'); + }, + '{text}': function (buffer, m) { + var ret = ["{"]; + mhchemParser.concatArray(ret, mhchemParser.go(m, 'text')); + ret.push("}"); + return ret; + }, + 'tex-math': function (buffer, m) { + return mhchemParser.go(m, 'tex-math'); + }, + 'tex-math tight': function (buffer, m) { + return mhchemParser.go(m, 'tex-math tight'); + }, + 'bond': function (buffer, m, k) { + return { + type_: 'bond', + kind_: k || m + }; + }, + 'color0-output': function (buffer, m) { + return { + type_: 'color0', + color: m[0] + }; + }, + 'ce': function (buffer, m) { + return mhchemParser.go(m); + }, + '1/2': function (buffer, m) { + /** @type {ParserOutput[]} */ + var ret = []; + + if (m.match(/^[+\-]/)) { + ret.push(m.substr(0, 1)); + m = m.substr(1); + } + + var n = m.match(/^([0-9]+|\$[a-z]\$|[a-z])\/([0-9]+)(\$[a-z]\$|[a-z])?$/); + n[1] = n[1].replace(/\$/g, ""); + ret.push({ + type_: 'frac', + p1: n[1], + p2: n[2] + }); + + if (n[3]) { + n[3] = n[3].replace(/\$/g, ""); + ret.push({ + type_: 'tex-math', + p1: n[3] + }); + } + + return ret; + }, + '9,9': function (buffer, m) { + return mhchemParser.go(m, '9,9'); + } + }, + // + // createTransitions + // convert { 'letter': { 'state': { action_: 'output' } } } to { 'state' => [ { pattern: 'letter', task: { action_: [{type_: 'output'}] } } ] } + // with expansion of 'a|b' to 'a' and 'b' (at 2 places) + // + createTransitions: function (o) { + var pattern, state; + /** @type {string[]} */ + + var stateArray; + var i; // + // 1. Collect all states + // + + /** @type {Transitions} */ + + var transitions = {}; + + for (pattern in o) { + for (state in o[pattern]) { + stateArray = state.split("|"); + o[pattern][state].stateArray = stateArray; + + for (i = 0; i < stateArray.length; i++) { + transitions[stateArray[i]] = []; + } + } + } // + // 2. Fill states + // + + + for (pattern in o) { + for (state in o[pattern]) { + stateArray = o[pattern][state].stateArray || []; + + for (i = 0; i < stateArray.length; i++) { + // + // 2a. Normalize actions into array: 'text=' ==> [{type_:'text='}] + // (Note to myself: Resolving the function here would be problematic. It would need .bind (for *this*) and currying (for *option*).) + // + + /** @type {any} */ + var p = o[pattern][state]; + + if (p.action_) { + p.action_ = [].concat(p.action_); + + for (var k = 0; k < p.action_.length; k++) { + if (typeof p.action_[k] === "string") { + p.action_[k] = { + type_: p.action_[k] + }; + } + } + } else { + p.action_ = []; + } // + // 2.b Multi-insert + // + + + var patternArray = pattern.split("|"); + + for (var j = 0; j < patternArray.length; j++) { + if (stateArray[i] === '*') { + // insert into all + for (var t in transitions) { + transitions[t].push({ + pattern: patternArray[j], + task: p + }); + } + } else { + transitions[stateArray[i]].push({ + pattern: patternArray[j], + task: p + }); + } + } + } + } + } + + return transitions; + }, + stateMachines: {} +}; // +// Definition of state machines +// + +mhchemParser.stateMachines = { + // + // \ce state machines + // + //#region ce + 'ce': { + // main parser + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': { + action_: 'output' + } + }, + 'else': { + '0|1|2': { + action_: 'beginsWithBond=false', + revisit: true, + toContinue: true + } + }, + 'oxidation$': { + '0': { + action_: 'oxidation-output' + } + }, + 'CMT': { + 'r': { + action_: 'rdt=', + nextState: 'rt' + }, + 'rd': { + action_: 'rqt=', + nextState: 'rdt' + } + }, + 'arrowUpDown': { + '0|1|2|as': { + action_: ['sb=false', 'output', 'operator'], + nextState: '1' + } + }, + 'uprightEntities': { + '0|1|2': { + action_: ['o=', 'output'], + nextState: '1' + } + }, + 'orbital': { + '0|1|2|3': { + action_: 'o=', + nextState: 'o' + } + }, + '->': { + '0|1|2|3': { + action_: 'r=', + nextState: 'r' + }, + 'a|as': { + action_: ['output', 'r='], + nextState: 'r' + }, + '*': { + action_: ['output', 'r='], + nextState: 'r' + } + }, + '+': { + 'o': { + action_: 'd= kv', + nextState: 'd' + }, + 'd|D': { + action_: 'd=', + nextState: 'd' + }, + 'q': { + action_: 'd=', + nextState: 'qd' + }, + 'qd|qD': { + action_: 'd=', + nextState: 'qd' + }, + 'dq': { + action_: ['output', 'd='], + nextState: 'd' + }, + '3': { + action_: ['sb=false', 'output', 'operator'], + nextState: '0' + } + }, + 'amount': { + '0|2': { + action_: 'a=', + nextState: 'a' + } + }, + 'pm-operator': { + '0|1|2|a|as': { + action_: ['sb=false', 'output', { + type_: 'operator', + option: '\\pm' + }], + nextState: '0' + } + }, + 'operator': { + '0|1|2|a|as': { + action_: ['sb=false', 'output', 'operator'], + nextState: '0' + } + }, + '-$': { + 'o|q': { + action_: ['charge or bond', 'output'], + nextState: 'qd' + }, + 'd': { + action_: 'd=', + nextState: 'd' + }, + 'D': { + action_: ['output', { + type_: 'bond', + option: "-" + }], + nextState: '3' + }, + 'q': { + action_: 'd=', + nextState: 'qd' + }, + 'qd': { + action_: 'd=', + nextState: 'qd' + }, + 'qD|dq': { + action_: ['output', { + type_: 'bond', + option: "-" + }], + nextState: '3' + } + }, + '-9': { + '3|o': { + action_: ['output', { + type_: 'insert', + option: 'hyphen' + }], + nextState: '3' + } + }, + '- orbital overlap': { + 'o': { + action_: ['output', { + type_: 'insert', + option: 'hyphen' + }], + nextState: '2' + }, + 'd': { + action_: ['output', { + type_: 'insert', + option: 'hyphen' + }], + nextState: '2' + } + }, + '-': { + '0|1|2': { + action_: [{ + type_: 'output', + option: 1 + }, 'beginsWithBond=true', { + type_: 'bond', + option: "-" + }], + nextState: '3' + }, + '3': { + action_: { + type_: 'bond', + option: "-" + } + }, + 'a': { + action_: ['output', { + type_: 'insert', + option: 'hyphen' + }], + nextState: '2' + }, + 'as': { + action_: [{ + type_: 'output', + option: 2 + }, { + type_: 'bond', + option: "-" + }], + nextState: '3' + }, + 'b': { + action_: 'b=' + }, + 'o': { + action_: { + type_: '- after o/d', + option: false + }, + nextState: '2' + }, + 'q': { + action_: { + type_: '- after o/d', + option: false + }, + nextState: '2' + }, + 'd|qd|dq': { + action_: { + type_: '- after o/d', + option: true + }, + nextState: '2' + }, + 'D|qD|p': { + action_: ['output', { + type_: 'bond', + option: "-" + }], + nextState: '3' + } + }, + 'amount2': { + '1|3': { + action_: 'a=', + nextState: 'a' + } + }, + 'letters': { + '0|1|2|3|a|as|b|p|bp|o': { + action_: 'o=', + nextState: 'o' + }, + 'q|dq': { + action_: ['output', 'o='], + nextState: 'o' + }, + 'd|D|qd|qD': { + action_: 'o after d', + nextState: 'o' + } + }, + 'digits': { + 'o': { + action_: 'q=', + nextState: 'q' + }, + 'd|D': { + action_: 'q=', + nextState: 'dq' + }, + 'q': { + action_: ['output', 'o='], + nextState: 'o' + }, + 'a': { + action_: 'o=', + nextState: 'o' + } + }, + 'space A': { + 'b|p|bp': {} + }, + 'space': { + 'a': { + nextState: 'as' + }, + '0': { + action_: 'sb=false' + }, + '1|2': { + action_: 'sb=true' + }, + 'r|rt|rd|rdt|rdq': { + action_: 'output', + nextState: '0' + }, + '*': { + action_: ['output', 'sb=true'], + nextState: '1' + } + }, + '1st-level escape': { + '1|2': { + action_: ['output', { + type_: 'insert+p1', + option: '1st-level escape' + }] + }, + '*': { + action_: ['output', { + type_: 'insert+p1', + option: '1st-level escape' + }], + nextState: '0' + } + }, + '[(...)]': { + 'r|rt': { + action_: 'rd=', + nextState: 'rd' + }, + 'rd|rdt': { + action_: 'rq=', + nextState: 'rdq' + } + }, + '...': { + 'o|d|D|dq|qd|qD': { + action_: ['output', { + type_: 'bond', + option: "..." + }], + nextState: '3' + }, + '*': { + action_: [{ + type_: 'output', + option: 1 + }, { + type_: 'insert', + option: 'ellipsis' + }], + nextState: '1' + } + }, + '. |* ': { + '*': { + action_: ['output', { + type_: 'insert', + option: 'addition compound' + }], + nextState: '1' + } + }, + 'state of aggregation $': { + '*': { + action_: ['output', 'state of aggregation'], + nextState: '1' + } + }, + '{[(': { + 'a|as|o': { + action_: ['o=', 'output', 'parenthesisLevel++'], + nextState: '2' + }, + '0|1|2|3': { + action_: ['o=', 'output', 'parenthesisLevel++'], + nextState: '2' + }, + '*': { + action_: ['output', 'o=', 'output', 'parenthesisLevel++'], + nextState: '2' + } + }, + ')]}': { + '0|1|2|3|b|p|bp|o': { + action_: ['o=', 'parenthesisLevel--'], + nextState: 'o' + }, + 'a|as|d|D|q|qd|qD|dq': { + action_: ['output', 'o=', 'parenthesisLevel--'], + nextState: 'o' + } + }, + ', ': { + '*': { + action_: ['output', 'comma'], + nextState: '0' + } + }, + '^_': { + // ^ and _ without a sensible argument + '*': {} + }, + '^{(...)}|^($...$)': { + '0|1|2|as': { + action_: 'b=', + nextState: 'b' + }, + 'p': { + action_: 'b=', + nextState: 'bp' + }, + '3|o': { + action_: 'd= kv', + nextState: 'D' + }, + 'q': { + action_: 'd=', + nextState: 'qD' + }, + 'd|D|qd|qD|dq': { + action_: ['output', 'd='], + nextState: 'D' + } + }, + '^a|^\\x{}{}|^\\x{}|^\\x|\'': { + '0|1|2|as': { + action_: 'b=', + nextState: 'b' + }, + 'p': { + action_: 'b=', + nextState: 'bp' + }, + '3|o': { + action_: 'd= kv', + nextState: 'd' + }, + 'q': { + action_: 'd=', + nextState: 'qd' + }, + 'd|qd|D|qD': { + action_: 'd=' + }, + 'dq': { + action_: ['output', 'd='], + nextState: 'd' + } + }, + '_{(state of aggregation)}$': { + 'd|D|q|qd|qD|dq': { + action_: ['output', 'q='], + nextState: 'q' + } + }, + '_{(...)}|_($...$)|_9|_\\x{}{}|_\\x{}|_\\x': { + '0|1|2|as': { + action_: 'p=', + nextState: 'p' + }, + 'b': { + action_: 'p=', + nextState: 'bp' + }, + '3|o': { + action_: 'q=', + nextState: 'q' + }, + 'd|D': { + action_: 'q=', + nextState: 'dq' + }, + 'q|qd|qD|dq': { + action_: ['output', 'q='], + nextState: 'q' + } + }, + '=<>': { + '0|1|2|3|a|as|o|q|d|D|qd|qD|dq': { + action_: [{ + type_: 'output', + option: 2 + }, 'bond'], + nextState: '3' + } + }, + '#': { + '0|1|2|3|a|as|o': { + action_: [{ + type_: 'output', + option: 2 + }, { + type_: 'bond', + option: "#" + }], + nextState: '3' + } + }, + '{}': { + '*': { + action_: { + type_: 'output', + option: 1 + }, + nextState: '1' + } + }, + '{...}': { + '0|1|2|3|a|as|b|p|bp': { + action_: 'o=', + nextState: 'o' + }, + 'o|d|D|q|qd|qD|dq': { + action_: ['output', 'o='], + nextState: 'o' + } + }, + '$...$': { + 'a': { + action_: 'a=' + }, + // 2$n$ + '0|1|2|3|as|b|p|bp|o': { + action_: 'o=', + nextState: 'o' + }, + // not 'amount' + 'as|o': { + action_: 'o=' + }, + 'q|d|D|qd|qD|dq': { + action_: ['output', 'o='], + nextState: 'o' + } + }, + '\\bond{(...)}': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'bond'], + nextState: "3" + } + }, + '\\frac{(...)}': { + '*': { + action_: [{ + type_: 'output', + option: 1 + }, 'frac-output'], + nextState: '3' + } + }, + '\\overset{(...)}': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'overset-output'], + nextState: '3' + } + }, + '\\underset{(...)}': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'underset-output'], + nextState: '3' + } + }, + '\\underbrace{(...)}': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'underbrace-output'], + nextState: '3' + } + }, + '\\color{(...)}{(...)}1|\\color(...){(...)}2': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'color-output'], + nextState: '3' + } + }, + '\\color{(...)}0': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'color0-output'] + } + }, + '\\ce{(...)}': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'ce'], + nextState: '3' + } + }, + '\\,': { + '*': { + action_: [{ + type_: 'output', + option: 1 + }, 'copy'], + nextState: '1' + } + }, + '\\x{}{}|\\x{}|\\x': { + '0|1|2|3|a|as|b|p|bp|o|c0': { + action_: ['o=', 'output'], + nextState: '3' + }, + '*': { + action_: ['output', 'o=', 'output'], + nextState: '3' + } + }, + 'others': { + '*': { + action_: [{ + type_: 'output', + option: 1 + }, 'copy'], + nextState: '3' + } + }, + 'else2': { + 'a': { + action_: 'a to o', + nextState: 'o', + revisit: true + }, + 'as': { + action_: ['output', 'sb=true'], + nextState: '1', + revisit: true + }, + 'r|rt|rd|rdt|rdq': { + action_: ['output'], + nextState: '0', + revisit: true + }, + '*': { + action_: ['output', 'copy'], + nextState: '3' + } + } + }), + actions: { + 'o after d': function (buffer, m) { + var ret; + + if ((buffer.d || "").match(/^[0-9]+$/)) { + var tmp = buffer.d; + buffer.d = undefined; + ret = this['output'](buffer); + buffer.b = tmp; + } else { + ret = this['output'](buffer); + } + + mhchemParser.actions['o='](buffer, m); + return ret; + }, + 'd= kv': function (buffer, m) { + buffer.d = m; + buffer.dType = 'kv'; + }, + 'charge or bond': function (buffer, m) { + if (buffer['beginsWithBond']) { + /** @type {ParserOutput[]} */ + var ret = []; + mhchemParser.concatArray(ret, this['output'](buffer)); + mhchemParser.concatArray(ret, mhchemParser.actions['bond'](buffer, m, "-")); + return ret; + } else { + buffer.d = m; + } + }, + '- after o/d': function (buffer, m, isAfterD) { + var c1 = mhchemParser.patterns.match_('orbital', buffer.o || ""); + var c2 = mhchemParser.patterns.match_('one lowercase greek letter $', buffer.o || ""); + var c3 = mhchemParser.patterns.match_('one lowercase latin letter $', buffer.o || ""); + var c4 = mhchemParser.patterns.match_('$one lowercase latin letter$ $', buffer.o || ""); + var hyphenFollows = m === "-" && (c1 && c1.remainder === "" || c2 || c3 || c4); + + if (hyphenFollows && !buffer.a && !buffer.b && !buffer.p && !buffer.d && !buffer.q && !c1 && c3) { + buffer.o = '$' + buffer.o + '$'; + } + /** @type {ParserOutput[]} */ + + + var ret = []; + + if (hyphenFollows) { + mhchemParser.concatArray(ret, this['output'](buffer)); + ret.push({ + type_: 'hyphen' + }); + } else { + c1 = mhchemParser.patterns.match_('digits', buffer.d || ""); + + if (isAfterD && c1 && c1.remainder === '') { + mhchemParser.concatArray(ret, mhchemParser.actions['d='](buffer, m)); + mhchemParser.concatArray(ret, this['output'](buffer)); + } else { + mhchemParser.concatArray(ret, this['output'](buffer)); + mhchemParser.concatArray(ret, mhchemParser.actions['bond'](buffer, m, "-")); + } + } + + return ret; + }, + 'a to o': function (buffer) { + buffer.o = buffer.a; + buffer.a = undefined; + }, + 'sb=true': function (buffer) { + buffer.sb = true; + }, + 'sb=false': function (buffer) { + buffer.sb = false; + }, + 'beginsWithBond=true': function (buffer) { + buffer['beginsWithBond'] = true; + }, + 'beginsWithBond=false': function (buffer) { + buffer['beginsWithBond'] = false; + }, + 'parenthesisLevel++': function (buffer) { + buffer['parenthesisLevel']++; + }, + 'parenthesisLevel--': function (buffer) { + buffer['parenthesisLevel']--; + }, + 'state of aggregation': function (buffer, m) { + return { + type_: 'state of aggregation', + p1: mhchemParser.go(m, 'o') + }; + }, + 'comma': function (buffer, m) { + var a = m.replace(/\s*$/, ''); + var withSpace = a !== m; + + if (withSpace && buffer['parenthesisLevel'] === 0) { + return { + type_: 'comma enumeration L', + p1: a + }; + } else { + return { + type_: 'comma enumeration M', + p1: a + }; + } + }, + 'output': function (buffer, m, entityFollows) { + // entityFollows: + // undefined = if we have nothing else to output, also ignore the just read space (buffer.sb) + // 1 = an entity follows, never omit the space if there was one just read before (can only apply to state 1) + // 2 = 1 + the entity can have an amount, so output a\, instead of converting it to o (can only apply to states a|as) + + /** @type {ParserOutput | ParserOutput[]} */ + var ret; + + if (!buffer.r) { + ret = []; + + if (!buffer.a && !buffer.b && !buffer.p && !buffer.o && !buffer.q && !buffer.d && !entityFollows) {//ret = []; + } else { + if (buffer.sb) { + ret.push({ + type_: 'entitySkip' + }); + } + + if (!buffer.o && !buffer.q && !buffer.d && !buffer.b && !buffer.p && entityFollows !== 2) { + buffer.o = buffer.a; + buffer.a = undefined; + } else if (!buffer.o && !buffer.q && !buffer.d && (buffer.b || buffer.p)) { + buffer.o = buffer.a; + buffer.d = buffer.b; + buffer.q = buffer.p; + buffer.a = buffer.b = buffer.p = undefined; + } else { + if (buffer.o && buffer.dType === 'kv' && mhchemParser.patterns.match_('d-oxidation$', buffer.d || "")) { + buffer.dType = 'oxidation'; + } else if (buffer.o && buffer.dType === 'kv' && !buffer.q) { + buffer.dType = undefined; + } + } + + ret.push({ + type_: 'chemfive', + a: mhchemParser.go(buffer.a, 'a'), + b: mhchemParser.go(buffer.b, 'bd'), + p: mhchemParser.go(buffer.p, 'pq'), + o: mhchemParser.go(buffer.o, 'o'), + q: mhchemParser.go(buffer.q, 'pq'), + d: mhchemParser.go(buffer.d, buffer.dType === 'oxidation' ? 'oxidation' : 'bd'), + dType: buffer.dType + }); + } + } else { + // r + + /** @type {ParserOutput[]} */ + var rd; + + if (buffer.rdt === 'M') { + rd = mhchemParser.go(buffer.rd, 'tex-math'); + } else if (buffer.rdt === 'T') { + rd = [{ + type_: 'text', + p1: buffer.rd || "" + }]; + } else { + rd = mhchemParser.go(buffer.rd); + } + /** @type {ParserOutput[]} */ + + + var rq; + + if (buffer.rqt === 'M') { + rq = mhchemParser.go(buffer.rq, 'tex-math'); + } else if (buffer.rqt === 'T') { + rq = [{ + type_: 'text', + p1: buffer.rq || "" + }]; + } else { + rq = mhchemParser.go(buffer.rq); + } + + ret = { + type_: 'arrow', + r: buffer.r, + rd: rd, + rq: rq + }; + } + + for (var p in buffer) { + if (p !== 'parenthesisLevel' && p !== 'beginsWithBond') { + delete buffer[p]; + } + } + + return ret; + }, + 'oxidation-output': function (buffer, m) { + var ret = ["{"]; + mhchemParser.concatArray(ret, mhchemParser.go(m, 'oxidation')); + ret.push("}"); + return ret; + }, + 'frac-output': function (buffer, m) { + return { + type_: 'frac-ce', + p1: mhchemParser.go(m[0]), + p2: mhchemParser.go(m[1]) + }; + }, + 'overset-output': function (buffer, m) { + return { + type_: 'overset', + p1: mhchemParser.go(m[0]), + p2: mhchemParser.go(m[1]) + }; + }, + 'underset-output': function (buffer, m) { + return { + type_: 'underset', + p1: mhchemParser.go(m[0]), + p2: mhchemParser.go(m[1]) + }; + }, + 'underbrace-output': function (buffer, m) { + return { + type_: 'underbrace', + p1: mhchemParser.go(m[0]), + p2: mhchemParser.go(m[1]) + }; + }, + 'color-output': function (buffer, m) { + return { + type_: 'color', + color1: m[0], + color2: mhchemParser.go(m[1]) + }; + }, + 'r=': function (buffer, m) { + buffer.r = m; + }, + 'rdt=': function (buffer, m) { + buffer.rdt = m; + }, + 'rd=': function (buffer, m) { + buffer.rd = m; + }, + 'rqt=': function (buffer, m) { + buffer.rqt = m; + }, + 'rq=': function (buffer, m) { + buffer.rq = m; + }, + 'operator': function (buffer, m, p1) { + return { + type_: 'operator', + kind_: p1 || m + }; + } + } + }, + 'a': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': {} + }, + '1/2$': { + '0': { + action_: '1/2' + } + }, + 'else': { + '0': { + nextState: '1', + revisit: true + } + }, + '$(...)$': { + '*': { + action_: 'tex-math tight', + nextState: '1' + } + }, + ',': { + '*': { + action_: { + type_: 'insert', + option: 'commaDecimal' + } + } + }, + 'else2': { + '*': { + action_: 'copy' + } + } + }), + actions: {} + }, + 'o': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': {} + }, + '1/2$': { + '0': { + action_: '1/2' + } + }, + 'else': { + '0': { + nextState: '1', + revisit: true + } + }, + 'letters': { + '*': { + action_: 'rm' + } + }, + '\\ca': { + '*': { + action_: { + type_: 'insert', + option: 'circa' + } + } + }, + '\\x{}{}|\\x{}|\\x': { + '*': { + action_: 'copy' + } + }, + '${(...)}$|$(...)$': { + '*': { + action_: 'tex-math' + } + }, + '{(...)}': { + '*': { + action_: '{text}' + } + }, + 'else2': { + '*': { + action_: 'copy' + } + } + }), + actions: {} + }, + 'text': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': { + action_: 'output' + } + }, + '{...}': { + '*': { + action_: 'text=' + } + }, + '${(...)}$|$(...)$': { + '*': { + action_: 'tex-math' + } + }, + '\\greek': { + '*': { + action_: ['output', 'rm'] + } + }, + '\\,|\\x{}{}|\\x{}|\\x': { + '*': { + action_: ['output', 'copy'] + } + }, + 'else': { + '*': { + action_: 'text=' + } + } + }), + actions: { + 'output': function (buffer) { + if (buffer.text_) { + /** @type {ParserOutput} */ + var ret = { + type_: 'text', + p1: buffer.text_ + }; + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + } + } + } + }, + 'pq': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': {} + }, + 'state of aggregation $': { + '*': { + action_: 'state of aggregation' + } + }, + 'i$': { + '0': { + nextState: '!f', + revisit: true + } + }, + '(KV letters),': { + '0': { + action_: 'rm', + nextState: '0' + } + }, + 'formula$': { + '0': { + nextState: 'f', + revisit: true + } + }, + '1/2$': { + '0': { + action_: '1/2' + } + }, + 'else': { + '0': { + nextState: '!f', + revisit: true + } + }, + '${(...)}$|$(...)$': { + '*': { + action_: 'tex-math' + } + }, + '{(...)}': { + '*': { + action_: 'text' + } + }, + 'a-z': { + 'f': { + action_: 'tex-math' + } + }, + 'letters': { + '*': { + action_: 'rm' + } + }, + '-9.,9': { + '*': { + action_: '9,9' + } + }, + ',': { + '*': { + action_: { + type_: 'insert+p1', + option: 'comma enumeration S' + } + } + }, + '\\color{(...)}{(...)}1|\\color(...){(...)}2': { + '*': { + action_: 'color-output' + } + }, + '\\color{(...)}0': { + '*': { + action_: 'color0-output' + } + }, + '\\ce{(...)}': { + '*': { + action_: 'ce' + } + }, + '\\,|\\x{}{}|\\x{}|\\x': { + '*': { + action_: 'copy' + } + }, + 'else2': { + '*': { + action_: 'copy' + } + } + }), + actions: { + 'state of aggregation': function (buffer, m) { + return { + type_: 'state of aggregation subscript', + p1: mhchemParser.go(m, 'o') + }; + }, + 'color-output': function (buffer, m) { + return { + type_: 'color', + color1: m[0], + color2: mhchemParser.go(m[1], 'pq') + }; + } + } + }, + 'bd': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': {} + }, + 'x$': { + '0': { + nextState: '!f', + revisit: true + } + }, + 'formula$': { + '0': { + nextState: 'f', + revisit: true + } + }, + 'else': { + '0': { + nextState: '!f', + revisit: true + } + }, + '-9.,9 no missing 0': { + '*': { + action_: '9,9' + } + }, + '.': { + '*': { + action_: { + type_: 'insert', + option: 'electron dot' + } + } + }, + 'a-z': { + 'f': { + action_: 'tex-math' + } + }, + 'x': { + '*': { + action_: { + type_: 'insert', + option: 'KV x' + } + } + }, + 'letters': { + '*': { + action_: 'rm' + } + }, + '\'': { + '*': { + action_: { + type_: 'insert', + option: 'prime' + } + } + }, + '${(...)}$|$(...)$': { + '*': { + action_: 'tex-math' + } + }, + '{(...)}': { + '*': { + action_: 'text' + } + }, + '\\color{(...)}{(...)}1|\\color(...){(...)}2': { + '*': { + action_: 'color-output' + } + }, + '\\color{(...)}0': { + '*': { + action_: 'color0-output' + } + }, + '\\ce{(...)}': { + '*': { + action_: 'ce' + } + }, + '\\,|\\x{}{}|\\x{}|\\x': { + '*': { + action_: 'copy' + } + }, + 'else2': { + '*': { + action_: 'copy' + } + } + }), + actions: { + 'color-output': function (buffer, m) { + return { + type_: 'color', + color1: m[0], + color2: mhchemParser.go(m[1], 'bd') + }; + } + } + }, + 'oxidation': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': {} + }, + 'roman numeral': { + '*': { + action_: 'roman-numeral' + } + }, + '${(...)}$|$(...)$': { + '*': { + action_: 'tex-math' + } + }, + 'else': { + '*': { + action_: 'copy' + } + } + }), + actions: { + 'roman-numeral': function (buffer, m) { + return { + type_: 'roman numeral', + p1: m || "" + }; + } + } + }, + 'tex-math': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': { + action_: 'output' + } + }, + '\\ce{(...)}': { + '*': { + action_: ['output', 'ce'] + } + }, + '{...}|\\,|\\x{}{}|\\x{}|\\x': { + '*': { + action_: 'o=' + } + }, + 'else': { + '*': { + action_: 'o=' + } + } + }), + actions: { + 'output': function (buffer) { + if (buffer.o) { + /** @type {ParserOutput} */ + var ret = { + type_: 'tex-math', + p1: buffer.o + }; + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + } + } + } + }, + 'tex-math tight': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': { + action_: 'output' + } + }, + '\\ce{(...)}': { + '*': { + action_: ['output', 'ce'] + } + }, + '{...}|\\,|\\x{}{}|\\x{}|\\x': { + '*': { + action_: 'o=' + } + }, + '-|+': { + '*': { + action_: 'tight operator' + } + }, + 'else': { + '*': { + action_: 'o=' + } + } + }), + actions: { + 'tight operator': function (buffer, m) { + buffer.o = (buffer.o || "") + "{" + m + "}"; + }, + 'output': function (buffer) { + if (buffer.o) { + /** @type {ParserOutput} */ + var ret = { + type_: 'tex-math', + p1: buffer.o + }; + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + } + } + } + }, + '9,9': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': {} + }, + ',': { + '*': { + action_: 'comma' + } + }, + 'else': { + '*': { + action_: 'copy' + } + } + }), + actions: { + 'comma': function () { + return { + type_: 'commaDecimal' + }; + } + } + }, + //#endregion + // + // \pu state machines + // + //#region pu + 'pu': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': { + action_: 'output' + } + }, + 'space$': { + '*': { + action_: ['output', 'space'] + } + }, + '{[(|)]}': { + '0|a': { + action_: 'copy' + } + }, + '(-)(9)^(-9)': { + '0': { + action_: 'number^', + nextState: 'a' + } + }, + '(-)(9.,9)(e)(99)': { + '0': { + action_: 'enumber', + nextState: 'a' + } + }, + 'space': { + '0|a': {} + }, + 'pm-operator': { + '0|a': { + action_: { + type_: 'operator', + option: '\\pm' + }, + nextState: '0' + } + }, + 'operator': { + '0|a': { + action_: 'copy', + nextState: '0' + } + }, + '//': { + 'd': { + action_: 'o=', + nextState: '/' + } + }, + '/': { + 'd': { + action_: 'o=', + nextState: '/' + } + }, + '{...}|else': { + '0|d': { + action_: 'd=', + nextState: 'd' + }, + 'a': { + action_: ['space', 'd='], + nextState: 'd' + }, + '/|q': { + action_: 'q=', + nextState: 'q' + } + } + }), + actions: { + 'enumber': function (buffer, m) { + /** @type {ParserOutput[]} */ + var ret = []; + + if (m[0] === "+-" || m[0] === "+/-") { + ret.push("\\pm "); + } else if (m[0]) { + ret.push(m[0]); + } + + if (m[1]) { + mhchemParser.concatArray(ret, mhchemParser.go(m[1], 'pu-9,9')); + + if (m[2]) { + if (m[2].match(/[,.]/)) { + mhchemParser.concatArray(ret, mhchemParser.go(m[2], 'pu-9,9')); + } else { + ret.push(m[2]); + } + } + + m[3] = m[4] || m[3]; + + if (m[3]) { + m[3] = m[3].trim(); + + if (m[3] === "e" || m[3].substr(0, 1) === "*") { + ret.push({ + type_: 'cdot' + }); + } else { + ret.push({ + type_: 'times' + }); + } + } + } + + if (m[3]) { + ret.push("10^{" + m[5] + "}"); + } + + return ret; + }, + 'number^': function (buffer, m) { + /** @type {ParserOutput[]} */ + var ret = []; + + if (m[0] === "+-" || m[0] === "+/-") { + ret.push("\\pm "); + } else if (m[0]) { + ret.push(m[0]); + } + + mhchemParser.concatArray(ret, mhchemParser.go(m[1], 'pu-9,9')); + ret.push("^{" + m[2] + "}"); + return ret; + }, + 'operator': function (buffer, m, p1) { + return { + type_: 'operator', + kind_: p1 || m + }; + }, + 'space': function () { + return { + type_: 'pu-space-1' + }; + }, + 'output': function (buffer) { + /** @type {ParserOutput | ParserOutput[]} */ + var ret; + var md = mhchemParser.patterns.match_('{(...)}', buffer.d || ""); + + if (md && md.remainder === '') { + buffer.d = md.match_; + } + + var mq = mhchemParser.patterns.match_('{(...)}', buffer.q || ""); + + if (mq && mq.remainder === '') { + buffer.q = mq.match_; + } + + if (buffer.d) { + buffer.d = buffer.d.replace(/\u00B0C|\^oC|\^{o}C/g, "{}^{\\circ}C"); + buffer.d = buffer.d.replace(/\u00B0F|\^oF|\^{o}F/g, "{}^{\\circ}F"); + } + + if (buffer.q) { + // fraction + buffer.q = buffer.q.replace(/\u00B0C|\^oC|\^{o}C/g, "{}^{\\circ}C"); + buffer.q = buffer.q.replace(/\u00B0F|\^oF|\^{o}F/g, "{}^{\\circ}F"); + var b5 = { + d: mhchemParser.go(buffer.d, 'pu'), + q: mhchemParser.go(buffer.q, 'pu') + }; + + if (buffer.o === '//') { + ret = { + type_: 'pu-frac', + p1: b5.d, + p2: b5.q + }; + } else { + ret = b5.d; + + if (b5.d.length > 1 || b5.q.length > 1) { + ret.push({ + type_: ' / ' + }); + } else { + ret.push({ + type_: '/' + }); + } + + mhchemParser.concatArray(ret, b5.q); + } + } else { + // no fraction + ret = mhchemParser.go(buffer.d, 'pu-2'); + } + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + } + } + }, + 'pu-2': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': { + action_: 'output' + } + }, + '*': { + '*': { + action_: ['output', 'cdot'], + nextState: '0' + } + }, + '\\x': { + '*': { + action_: 'rm=' + } + }, + 'space': { + '*': { + action_: ['output', 'space'], + nextState: '0' + } + }, + '^{(...)}|^(-1)': { + '1': { + action_: '^(-1)' + } + }, + '-9.,9': { + '0': { + action_: 'rm=', + nextState: '0' + }, + '1': { + action_: '^(-1)', + nextState: '0' + } + }, + '{...}|else': { + '*': { + action_: 'rm=', + nextState: '1' + } + } + }), + actions: { + 'cdot': function () { + return { + type_: 'tight cdot' + }; + }, + '^(-1)': function (buffer, m) { + buffer.rm += "^{" + m + "}"; + }, + 'space': function () { + return { + type_: 'pu-space-2' + }; + }, + 'output': function (buffer) { + /** @type {ParserOutput | ParserOutput[]} */ + var ret = []; + + if (buffer.rm) { + var mrm = mhchemParser.patterns.match_('{(...)}', buffer.rm || ""); + + if (mrm && mrm.remainder === '') { + ret = mhchemParser.go(mrm.match_, 'pu'); + } else { + ret = { + type_: 'rm', + p1: buffer.rm + }; + } + } + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + } + } + }, + 'pu-9,9': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '0': { + action_: 'output-0' + }, + 'o': { + action_: 'output-o' + } + }, + ',': { + '0': { + action_: ['output-0', 'comma'], + nextState: 'o' + } + }, + '.': { + '0': { + action_: ['output-0', 'copy'], + nextState: 'o' + } + }, + 'else': { + '*': { + action_: 'text=' + } + } + }), + actions: { + 'comma': function () { + return { + type_: 'commaDecimal' + }; + }, + 'output-0': function (buffer) { + /** @type {ParserOutput[]} */ + var ret = []; + buffer.text_ = buffer.text_ || ""; + + if (buffer.text_.length > 4) { + var a = buffer.text_.length % 3; + + if (a === 0) { + a = 3; + } + + for (var i = buffer.text_.length - 3; i > 0; i -= 3) { + ret.push(buffer.text_.substr(i, 3)); + ret.push({ + type_: '1000 separator' + }); + } + + ret.push(buffer.text_.substr(0, a)); + ret.reverse(); + } else { + ret.push(buffer.text_); + } + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + }, + 'output-o': function (buffer) { + /** @type {ParserOutput[]} */ + var ret = []; + buffer.text_ = buffer.text_ || ""; + + if (buffer.text_.length > 4) { + var a = buffer.text_.length - 3; + + for (var i = 0; i < a; i += 3) { + ret.push(buffer.text_.substr(i, 3)); + ret.push({ + type_: '1000 separator' + }); + } + + ret.push(buffer.text_.substr(i)); + } else { + ret.push(buffer.text_); + } + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + } + } + } //#endregion + +}; // +// texify: Take MhchemParser output and convert it to TeX +// + +/** @type {Texify} */ + +var texify = { + go: function (input, isInner) { + // (recursive, max 4 levels) + if (!input) { + return ""; + } + + var res = ""; + var cee = false; + + for (var i = 0; i < input.length; i++) { + var inputi = input[i]; + + if (typeof inputi === "string") { + res += inputi; + } else { + res += texify._go2(inputi); + + if (inputi.type_ === '1st-level escape') { + cee = true; + } + } + } + + if (!isInner && !cee && res) { + res = "{" + res + "}"; + } + + return res; + }, + _goInner: function (input) { + if (!input) { + return input; + } + + return texify.go(input, true); + }, + _go2: function (buf) { + /** @type {undefined | string} */ + var res; + + switch (buf.type_) { + case 'chemfive': + res = ""; + var b5 = { + a: texify._goInner(buf.a), + b: texify._goInner(buf.b), + p: texify._goInner(buf.p), + o: texify._goInner(buf.o), + q: texify._goInner(buf.q), + d: texify._goInner(buf.d) + }; // + // a + // + + if (b5.a) { + if (b5.a.match(/^[+\-]/)) { + b5.a = "{" + b5.a + "}"; + } + + res += b5.a + "\\,"; + } // + // b and p + // + + + if (b5.b || b5.p) { + res += "{\\vphantom{X}}"; + res += "^{\\hphantom{" + (b5.b || "") + "}}_{\\hphantom{" + (b5.p || "") + "}}"; + res += "{\\vphantom{X}}"; + res += "^{\\smash[t]{\\vphantom{2}}\\mathllap{" + (b5.b || "") + "}}"; + res += "_{\\vphantom{2}\\mathllap{\\smash[t]{" + (b5.p || "") + "}}}"; + } // + // o + // + + + if (b5.o) { + if (b5.o.match(/^[+\-]/)) { + b5.o = "{" + b5.o + "}"; + } + + res += b5.o; + } // + // q and d + // + + + if (buf.dType === 'kv') { + if (b5.d || b5.q) { + res += "{\\vphantom{X}}"; + } + + if (b5.d) { + res += "^{" + b5.d + "}"; + } + + if (b5.q) { + res += "_{\\smash[t]{" + b5.q + "}}"; + } + } else if (buf.dType === 'oxidation') { + if (b5.d) { + res += "{\\vphantom{X}}"; + res += "^{" + b5.d + "}"; + } + + if (b5.q) { + res += "{\\vphantom{X}}"; + res += "_{\\smash[t]{" + b5.q + "}}"; + } + } else { + if (b5.q) { + res += "{\\vphantom{X}}"; + res += "_{\\smash[t]{" + b5.q + "}}"; + } + + if (b5.d) { + res += "{\\vphantom{X}}"; + res += "^{" + b5.d + "}"; + } + } + + break; + + case 'rm': + res = "\\mathrm{" + buf.p1 + "}"; + break; + + case 'text': + if (buf.p1.match(/[\^_]/)) { + buf.p1 = buf.p1.replace(" ", "~").replace("-", "\\text{-}"); + res = "\\mathrm{" + buf.p1 + "}"; + } else { + res = "\\text{" + buf.p1 + "}"; + } + + break; + + case 'roman numeral': + res = "\\mathrm{" + buf.p1 + "}"; + break; + + case 'state of aggregation': + res = "\\mskip2mu " + texify._goInner(buf.p1); + break; + + case 'state of aggregation subscript': + res = "\\mskip1mu " + texify._goInner(buf.p1); + break; + + case 'bond': + res = texify._getBond(buf.kind_); + + if (!res) { + throw ["MhchemErrorBond", "mhchem Error. Unknown bond type (" + buf.kind_ + ")"]; + } + + break; + + case 'frac': + var c = "\\frac{" + buf.p1 + "}{" + buf.p2 + "}"; + res = "\\mathchoice{\\textstyle" + c + "}{" + c + "}{" + c + "}{" + c + "}"; + break; + + case 'pu-frac': + var d = "\\frac{" + texify._goInner(buf.p1) + "}{" + texify._goInner(buf.p2) + "}"; + res = "\\mathchoice{\\textstyle" + d + "}{" + d + "}{" + d + "}{" + d + "}"; + break; + + case 'tex-math': + res = buf.p1 + " "; + break; + + case 'frac-ce': + res = "\\frac{" + texify._goInner(buf.p1) + "}{" + texify._goInner(buf.p2) + "}"; + break; + + case 'overset': + res = "\\overset{" + texify._goInner(buf.p1) + "}{" + texify._goInner(buf.p2) + "}"; + break; + + case 'underset': + res = "\\underset{" + texify._goInner(buf.p1) + "}{" + texify._goInner(buf.p2) + "}"; + break; + + case 'underbrace': + res = "\\underbrace{" + texify._goInner(buf.p1) + "}_{" + texify._goInner(buf.p2) + "}"; + break; + + case 'color': + res = "{\\color{" + buf.color1 + "}{" + texify._goInner(buf.color2) + "}}"; + break; + + case 'color0': + res = "\\color{" + buf.color + "}"; + break; + + case 'arrow': + var b6 = { + rd: texify._goInner(buf.rd), + rq: texify._goInner(buf.rq) + }; + + var arrow = "\\x" + texify._getArrow(buf.r); + + if (b6.rq) { + arrow += "[{" + b6.rq + "}]"; + } + + if (b6.rd) { + arrow += "{" + b6.rd + "}"; + } else { + arrow += "{}"; + } + + res = arrow; + break; + + case 'operator': + res = texify._getOperator(buf.kind_); + break; + + case '1st-level escape': + res = buf.p1 + " "; // &, \\\\, \\hlin + + break; + + case 'space': + res = " "; + break; + + case 'entitySkip': + res = "~"; + break; + + case 'pu-space-1': + res = "~"; + break; + + case 'pu-space-2': + res = "\\mkern3mu "; + break; + + case '1000 separator': + res = "\\mkern2mu "; + break; + + case 'commaDecimal': + res = "{,}"; + break; + + case 'comma enumeration L': + res = "{" + buf.p1 + "}\\mkern6mu "; + break; + + case 'comma enumeration M': + res = "{" + buf.p1 + "}\\mkern3mu "; + break; + + case 'comma enumeration S': + res = "{" + buf.p1 + "}\\mkern1mu "; + break; + + case 'hyphen': + res = "\\text{-}"; + break; + + case 'addition compound': + res = "\\,{\\cdot}\\,"; + break; + + case 'electron dot': + res = "\\mkern1mu \\bullet\\mkern1mu "; + break; + + case 'KV x': + res = "{\\times}"; + break; + + case 'prime': + res = "\\prime "; + break; + + case 'cdot': + res = "\\cdot "; + break; + + case 'tight cdot': + res = "\\mkern1mu{\\cdot}\\mkern1mu "; + break; + + case 'times': + res = "\\times "; + break; + + case 'circa': + res = "{\\sim}"; + break; + + case '^': + res = "uparrow"; + break; + + case 'v': + res = "downarrow"; + break; + + case 'ellipsis': + res = "\\ldots "; + break; + + case '/': + res = "/"; + break; + + case ' / ': + res = "\\,/\\,"; + break; + + default: + assertNever(buf); + throw ["MhchemBugT", "mhchem bug T. Please report."]; + // Missing texify rule or unknown MhchemParser output + } + + assertString(res); + return res; + }, + _getArrow: function (a) { + switch (a) { + case "->": + return "rightarrow"; + + case "\u2192": + return "rightarrow"; + + case "\u27F6": + return "rightarrow"; + + case "<-": + return "leftarrow"; + + case "<->": + return "leftrightarrow"; + + case "<-->": + return "rightleftarrows"; + + case "<=>": + return "rightleftharpoons"; + + case "\u21CC": + return "rightleftharpoons"; + + case "<=>>": + return "rightequilibrium"; + + case "<<=>": + return "leftequilibrium"; + + default: + assertNever(a); + throw ["MhchemBugT", "mhchem bug T. Please report."]; + } + }, + _getBond: function (a) { + switch (a) { + case "-": + return "{-}"; + + case "1": + return "{-}"; + + case "=": + return "{=}"; + + case "2": + return "{=}"; + + case "#": + return "{\\equiv}"; + + case "3": + return "{\\equiv}"; + + case "~": + return "{\\tripledash}"; + + case "~-": + return "{\\mathrlap{\\raisebox{-.1em}{$-$}}\\raisebox{.1em}{$\\tripledash$}}"; + + case "~=": + return "{\\mathrlap{\\raisebox{-.2em}{$-$}}\\mathrlap{\\raisebox{.2em}{$\\tripledash$}}-}"; + + case "~--": + return "{\\mathrlap{\\raisebox{-.2em}{$-$}}\\mathrlap{\\raisebox{.2em}{$\\tripledash$}}-}"; + + case "-~-": + return "{\\mathrlap{\\raisebox{-.2em}{$-$}}\\mathrlap{\\raisebox{.2em}{$-$}}\\tripledash}"; + + case "...": + return "{{\\cdot}{\\cdot}{\\cdot}}"; + + case "....": + return "{{\\cdot}{\\cdot}{\\cdot}{\\cdot}}"; + + case "->": + return "{\\rightarrow}"; + + case "<-": + return "{\\leftarrow}"; + + case "<": + return "{<}"; + + case ">": + return "{>}"; + + default: + assertNever(a); + throw ["MhchemBugT", "mhchem bug T. Please report."]; + } + }, + _getOperator: function (a) { + switch (a) { + case "+": + return " {}+{} "; + + case "-": + return " {}-{} "; + + case "=": + return " {}={} "; + + case "<": + return " {}<{} "; + + case ">": + return " {}>{} "; + + case "<<": + return " {}\\ll{} "; + + case ">>": + return " {}\\gg{} "; + + case "\\pm": + return " {}\\pm{} "; + + case "\\approx": + return " {}\\approx{} "; + + case "$\\approx$": + return " {}\\approx{} "; + + case "v": + return " \\downarrow{} "; + + case "(v)": + return " \\downarrow{} "; + + case "^": + return " \\uparrow{} "; + + case "(^)": + return " \\uparrow{} "; + + default: + assertNever(a); + throw ["MhchemBugT", "mhchem bug T. Please report."]; + } + } +}; // +// Helpers for code analysis +// Will show type error at calling position +// + +/** @param {number} a */ + +function assertNever(a) {} +/** @param {string} a */ + + +function assertString(a) {} +__webpack_exports__ = __webpack_exports__["default"]; +/******/ return __webpack_exports__; +/******/ })() +; +}); \ No newline at end of file diff --git a/frontend/node_modules/katex/dist/contrib/mhchem.min.js b/frontend/node_modules/katex/dist/contrib/mhchem.min.js new file mode 100644 index 0000000..7e45d59 --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/mhchem.min.js @@ -0,0 +1 @@ +!function(t,e){if("object"==typeof exports&&"object"==typeof module)module.exports=e(require("katex"));else if("function"==typeof define&&define.amd)define(["katex"],e);else{var n="object"==typeof exports?e(require("katex")):e(t.katex);for(var o in n)("object"==typeof exports?exports:t)[o]=n[o]}}("undefined"!=typeof self?self:this,(function(t){return function(){"use strict";var e={757:function(e){e.exports=t}},n={};function o(t){var a=n[t];if(void 0!==a)return a.exports;var r=n[t]={exports:{}};return e[t](r,r.exports,o),r.exports}o.n=function(t){var e=t&&t.__esModule?function(){return t.default}:function(){return t};return o.d(e,{a:e}),e},o.d=function(t,e){for(var n in e)o.o(e,n)&&!o.o(t,n)&&Object.defineProperty(t,n,{enumerable:!0,get:e[n]})},o.o=function(t,e){return Object.prototype.hasOwnProperty.call(t,e)};var a={},r=o(757),i=o.n(r);i().__defineMacro("\\ce",(function(t){return c(t.consumeArgs(1)[0],"ce")})),i().__defineMacro("\\pu",(function(t){return c(t.consumeArgs(1)[0],"pu")})),i().__defineMacro("\\tripledash","{\\vphantom{-}\\raisebox{2.56mu}{$\\mkern2mu\\tiny\\text{-}\\mkern1mu\\text{-}\\mkern1mu\\text{-}\\mkern2mu$}}");var c=function(t,e){for(var n="",o=t.length&&t[t.length-1].loc.start,a=t.length-1;a>=0;a--)t[a].loc.start>o&&(n+=" ",o=t[a].loc.start),n+=t[a].text,o+=t[a].text.length;return p.go(u.go(n,e))},u={go:function(t,e){if(!t)return[];void 0===e&&(e="ce");var n,o="0",a={};a.parenthesisLevel=0,t=(t=(t=t.replace(/\n/g," ")).replace(/[\u2212\u2013\u2014\u2010]/g,"-")).replace(/[\u2026]/g,"...");for(var r=10,i=[];;){n!==t?(r=10,n=t):r--;var c=u.stateMachines[e],p=c.transitions[o]||c.transitions["*"];t:for(var s=0;s0))return i;if(d.revisit||(t=_.remainder),!d.toContinue)break t}}if(r<=0)throw["MhchemBugU","mhchem bug U. Please report."]}},concatArray:function(t,e){if(e)if(Array.isArray(e))for(var n=0;n":/^[=<>]/,"#":/^[#\u2261]/,"+":/^\+/,"-$":/^-(?=[\s_},;\]/]|$|\([a-z]+\))/,"-9":/^-(?=[0-9])/,"- orbital overlap":/^-(?=(?:[spd]|sp)(?:$|[\s,;\)\]\}]))/,"-":/^-/,"pm-operator":/^(?:\\pm|\$\\pm\$|\+-|\+\/-)/,operator:/^(?:\+|(?:[\-=<>]|<<|>>|\\approx|\$\\approx\$)(?=\s|$|-?[0-9]))/,arrowUpDown:/^(?:v|\(v\)|\^|\(\^\))(?=$|[\s,;\)\]\}])/,"\\bond{(...)}":function(t){return u.patterns.findObserveGroups(t,"\\bond{","","","}")},"->":/^(?:<->|<-->|->|<-|<=>>|<<=>|<=>|[\u2192\u27F6\u21CC])/,CMT:/^[CMT](?=\[)/,"[(...)]":function(t){return u.patterns.findObserveGroups(t,"[","","","]")},"1st-level escape":/^(&|\\\\|\\hline)\s*/,"\\,":/^(?:\\[,\ ;:])/,"\\x{}{}":function(t){return u.patterns.findObserveGroups(t,"",/^\\[a-zA-Z]+\{/,"}","","","{","}","",!0)},"\\x{}":function(t){return u.patterns.findObserveGroups(t,"",/^\\[a-zA-Z]+\{/,"}","")},"\\ca":/^\\ca(?:\s+|(?![a-zA-Z]))/,"\\x":/^(?:\\[a-zA-Z]+\s*|\\[_&{}%])/,orbital:/^(?:[0-9]{1,2}[spdfgh]|[0-9]{0,2}sp)(?=$|[^a-zA-Z])/,others:/^[\/~|]/,"\\frac{(...)}":function(t){return u.patterns.findObserveGroups(t,"\\frac{","","","}","{","","","}")},"\\overset{(...)}":function(t){return u.patterns.findObserveGroups(t,"\\overset{","","","}","{","","","}")},"\\underset{(...)}":function(t){return u.patterns.findObserveGroups(t,"\\underset{","","","}","{","","","}")},"\\underbrace{(...)}":function(t){return u.patterns.findObserveGroups(t,"\\underbrace{","","","}_","{","","","}")},"\\color{(...)}0":function(t){return u.patterns.findObserveGroups(t,"\\color{","","","}")},"\\color{(...)}{(...)}1":function(t){return u.patterns.findObserveGroups(t,"\\color{","","","}","{","","","}")},"\\color(...){(...)}2":function(t){return u.patterns.findObserveGroups(t,"\\color","\\","",/^(?=\{)/,"{","","","}")},"\\ce{(...)}":function(t){return u.patterns.findObserveGroups(t,"\\ce{","","","}")},oxidation$:/^(?:[+-][IVX]+|\\pm\s*0|\$\\pm\$\s*0)$/,"d-oxidation$":/^(?:[+-]?\s?[IVX]+|\\pm\s*0|\$\\pm\$\s*0)$/,"roman numeral":/^[IVX]+/,"1/2$":/^[+\-]?(?:[0-9]+|\$[a-z]\$|[a-z])\/[0-9]+(?:\$[a-z]\$|[a-z])?$/,amount:function(t){var e;if(e=t.match(/^(?:(?:(?:\([+\-]?[0-9]+\/[0-9]+\)|[+\-]?(?:[0-9]+|\$[a-z]\$|[a-z])\/[0-9]+|[+\-]?[0-9]+[.,][0-9]+|[+\-]?\.[0-9]+|[+\-]?[0-9]+)(?:[a-z](?=\s*[A-Z]))?)|[+\-]?[a-z](?=\s*[A-Z])|\+(?!\s))/))return{match_:e[0],remainder:t.substr(e[0].length)};var n=u.patterns.findObserveGroups(t,"","$","$","");return n&&(e=n.match_.match(/^\$(?:\(?[+\-]?(?:[0-9]*[a-z]?[+\-])?[0-9]*[a-z](?:[+\-][0-9]*[a-z]?)?\)?|\+|-)\$$/))?{match_:e[0],remainder:t.substr(e[0].length)}:null},amount2:function(t){return this.amount(t)},"(KV letters),":/^(?:[A-Z][a-z]{0,2}|i)(?=,)/,formula$:function(t){if(t.match(/^\([a-z]+\)$/))return null;var e=t.match(/^(?:[a-z]|(?:[0-9\ \+\-\,\.\(\)]+[a-z])+[0-9\ \+\-\,\.\(\)]*|(?:[a-z][0-9\ \+\-\,\.\(\)]+)+[a-z]?)$/);return e?{match_:e[0],remainder:t.substr(e[0].length)}:null},uprightEntities:/^(?:pH|pOH|pC|pK|iPr|iBu)(?=$|[^a-zA-Z])/,"/":/^\s*(\/)\s*/,"//":/^\s*(\/\/)\s*/,"*":/^\s*[*.]\s*/},findObserveGroups:function(t,e,n,o,a,r,i,c,u,p){var s=function(t,e){if("string"==typeof e)return 0!==t.indexOf(e)?null:e;var n=t.match(e);return n?n[0]:null},_=s(t,e);if(null===_)return null;if(t=t.substr(_.length),null===(_=s(t,n)))return null;var d=function(t,e,n){for(var o=0;e":{"0|1|2|3":{action_:"r=",nextState:"r"},"a|as":{action_:["output","r="],nextState:"r"},"*":{action_:["output","r="],nextState:"r"}},"+":{o:{action_:"d= kv",nextState:"d"},"d|D":{action_:"d=",nextState:"d"},q:{action_:"d=",nextState:"qd"},"qd|qD":{action_:"d=",nextState:"qd"},dq:{action_:["output","d="],nextState:"d"},3:{action_:["sb=false","output","operator"],nextState:"0"}},amount:{"0|2":{action_:"a=",nextState:"a"}},"pm-operator":{"0|1|2|a|as":{action_:["sb=false","output",{type_:"operator",option:"\\pm"}],nextState:"0"}},operator:{"0|1|2|a|as":{action_:["sb=false","output","operator"],nextState:"0"}},"-$":{"o|q":{action_:["charge or bond","output"],nextState:"qd"},d:{action_:"d=",nextState:"d"},D:{action_:["output",{type_:"bond",option:"-"}],nextState:"3"},q:{action_:"d=",nextState:"qd"},qd:{action_:"d=",nextState:"qd"},"qD|dq":{action_:["output",{type_:"bond",option:"-"}],nextState:"3"}},"-9":{"3|o":{action_:["output",{type_:"insert",option:"hyphen"}],nextState:"3"}},"- orbital overlap":{o:{action_:["output",{type_:"insert",option:"hyphen"}],nextState:"2"},d:{action_:["output",{type_:"insert",option:"hyphen"}],nextState:"2"}},"-":{"0|1|2":{action_:[{type_:"output",option:1},"beginsWithBond=true",{type_:"bond",option:"-"}],nextState:"3"},3:{action_:{type_:"bond",option:"-"}},a:{action_:["output",{type_:"insert",option:"hyphen"}],nextState:"2"},as:{action_:[{type_:"output",option:2},{type_:"bond",option:"-"}],nextState:"3"},b:{action_:"b="},o:{action_:{type_:"- after o/d",option:!1},nextState:"2"},q:{action_:{type_:"- after o/d",option:!1},nextState:"2"},"d|qd|dq":{action_:{type_:"- after o/d",option:!0},nextState:"2"},"D|qD|p":{action_:["output",{type_:"bond",option:"-"}],nextState:"3"}},amount2:{"1|3":{action_:"a=",nextState:"a"}},letters:{"0|1|2|3|a|as|b|p|bp|o":{action_:"o=",nextState:"o"},"q|dq":{action_:["output","o="],nextState:"o"},"d|D|qd|qD":{action_:"o after d",nextState:"o"}},digits:{o:{action_:"q=",nextState:"q"},"d|D":{action_:"q=",nextState:"dq"},q:{action_:["output","o="],nextState:"o"},a:{action_:"o=",nextState:"o"}},"space A":{"b|p|bp":{}},space:{a:{nextState:"as"},0:{action_:"sb=false"},"1|2":{action_:"sb=true"},"r|rt|rd|rdt|rdq":{action_:"output",nextState:"0"},"*":{action_:["output","sb=true"],nextState:"1"}},"1st-level escape":{"1|2":{action_:["output",{type_:"insert+p1",option:"1st-level escape"}]},"*":{action_:["output",{type_:"insert+p1",option:"1st-level escape"}],nextState:"0"}},"[(...)]":{"r|rt":{action_:"rd=",nextState:"rd"},"rd|rdt":{action_:"rq=",nextState:"rdq"}},"...":{"o|d|D|dq|qd|qD":{action_:["output",{type_:"bond",option:"..."}],nextState:"3"},"*":{action_:[{type_:"output",option:1},{type_:"insert",option:"ellipsis"}],nextState:"1"}},". |* ":{"*":{action_:["output",{type_:"insert",option:"addition compound"}],nextState:"1"}},"state of aggregation $":{"*":{action_:["output","state of aggregation"],nextState:"1"}},"{[(":{"a|as|o":{action_:["o=","output","parenthesisLevel++"],nextState:"2"},"0|1|2|3":{action_:["o=","output","parenthesisLevel++"],nextState:"2"},"*":{action_:["output","o=","output","parenthesisLevel++"],nextState:"2"}},")]}":{"0|1|2|3|b|p|bp|o":{action_:["o=","parenthesisLevel--"],nextState:"o"},"a|as|d|D|q|qd|qD|dq":{action_:["output","o=","parenthesisLevel--"],nextState:"o"}},", ":{"*":{action_:["output","comma"],nextState:"0"}},"^_":{"*":{}},"^{(...)}|^($...$)":{"0|1|2|as":{action_:"b=",nextState:"b"},p:{action_:"b=",nextState:"bp"},"3|o":{action_:"d= kv",nextState:"D"},q:{action_:"d=",nextState:"qD"},"d|D|qd|qD|dq":{action_:["output","d="],nextState:"D"}},"^a|^\\x{}{}|^\\x{}|^\\x|'":{"0|1|2|as":{action_:"b=",nextState:"b"},p:{action_:"b=",nextState:"bp"},"3|o":{action_:"d= kv",nextState:"d"},q:{action_:"d=",nextState:"qd"},"d|qd|D|qD":{action_:"d="},dq:{action_:["output","d="],nextState:"d"}},"_{(state of aggregation)}$":{"d|D|q|qd|qD|dq":{action_:["output","q="],nextState:"q"}},"_{(...)}|_($...$)|_9|_\\x{}{}|_\\x{}|_\\x":{"0|1|2|as":{action_:"p=",nextState:"p"},b:{action_:"p=",nextState:"bp"},"3|o":{action_:"q=",nextState:"q"},"d|D":{action_:"q=",nextState:"dq"},"q|qd|qD|dq":{action_:["output","q="],nextState:"q"}},"=<>":{"0|1|2|3|a|as|o|q|d|D|qd|qD|dq":{action_:[{type_:"output",option:2},"bond"],nextState:"3"}},"#":{"0|1|2|3|a|as|o":{action_:[{type_:"output",option:2},{type_:"bond",option:"#"}],nextState:"3"}},"{}":{"*":{action_:{type_:"output",option:1},nextState:"1"}},"{...}":{"0|1|2|3|a|as|b|p|bp":{action_:"o=",nextState:"o"},"o|d|D|q|qd|qD|dq":{action_:["output","o="],nextState:"o"}},"$...$":{a:{action_:"a="},"0|1|2|3|as|b|p|bp|o":{action_:"o=",nextState:"o"},"as|o":{action_:"o="},"q|d|D|qd|qD|dq":{action_:["output","o="],nextState:"o"}},"\\bond{(...)}":{"*":{action_:[{type_:"output",option:2},"bond"],nextState:"3"}},"\\frac{(...)}":{"*":{action_:[{type_:"output",option:1},"frac-output"],nextState:"3"}},"\\overset{(...)}":{"*":{action_:[{type_:"output",option:2},"overset-output"],nextState:"3"}},"\\underset{(...)}":{"*":{action_:[{type_:"output",option:2},"underset-output"],nextState:"3"}},"\\underbrace{(...)}":{"*":{action_:[{type_:"output",option:2},"underbrace-output"],nextState:"3"}},"\\color{(...)}{(...)}1|\\color(...){(...)}2":{"*":{action_:[{type_:"output",option:2},"color-output"],nextState:"3"}},"\\color{(...)}0":{"*":{action_:[{type_:"output",option:2},"color0-output"]}},"\\ce{(...)}":{"*":{action_:[{type_:"output",option:2},"ce"],nextState:"3"}},"\\,":{"*":{action_:[{type_:"output",option:1},"copy"],nextState:"1"}},"\\x{}{}|\\x{}|\\x":{"0|1|2|3|a|as|b|p|bp|o|c0":{action_:["o=","output"],nextState:"3"},"*":{action_:["output","o=","output"],nextState:"3"}},others:{"*":{action_:[{type_:"output",option:1},"copy"],nextState:"3"}},else2:{a:{action_:"a to o",nextState:"o",revisit:!0},as:{action_:["output","sb=true"],nextState:"1",revisit:!0},"r|rt|rd|rdt|rdq":{action_:["output"],nextState:"0",revisit:!0},"*":{action_:["output","copy"],nextState:"3"}}}),actions:{"o after d":function(t,e){var n;if((t.d||"").match(/^[0-9]+$/)){var o=t.d;t.d=void 0,n=this.output(t),t.b=o}else n=this.output(t);return u.actions["o="](t,e),n},"d= kv":function(t,e){t.d=e,t.dType="kv"},"charge or bond":function(t,e){if(t.beginsWithBond){var n=[];return u.concatArray(n,this.output(t)),u.concatArray(n,u.actions.bond(t,e,"-")),n}t.d=e},"- after o/d":function(t,e,n){var o=u.patterns.match_("orbital",t.o||""),a=u.patterns.match_("one lowercase greek letter $",t.o||""),r=u.patterns.match_("one lowercase latin letter $",t.o||""),i=u.patterns.match_("$one lowercase latin letter$ $",t.o||""),c="-"===e&&(o&&""===o.remainder||a||r||i);!c||t.a||t.b||t.p||t.d||t.q||o||!r||(t.o="$"+t.o+"$");var p=[];return c?(u.concatArray(p,this.output(t)),p.push({type_:"hyphen"})):(o=u.patterns.match_("digits",t.d||""),n&&o&&""===o.remainder?(u.concatArray(p,u.actions["d="](t,e)),u.concatArray(p,this.output(t))):(u.concatArray(p,this.output(t)),u.concatArray(p,u.actions.bond(t,e,"-")))),p},"a to o":function(t){t.o=t.a,t.a=void 0},"sb=true":function(t){t.sb=!0},"sb=false":function(t){t.sb=!1},"beginsWithBond=true":function(t){t.beginsWithBond=!0},"beginsWithBond=false":function(t){t.beginsWithBond=!1},"parenthesisLevel++":function(t){t.parenthesisLevel++},"parenthesisLevel--":function(t){t.parenthesisLevel--},"state of aggregation":function(t,e){return{type_:"state of aggregation",p1:u.go(e,"o")}},comma:function(t,e){var n=e.replace(/\s*$/,"");return n!==e&&0===t.parenthesisLevel?{type_:"comma enumeration L",p1:n}:{type_:"comma enumeration M",p1:n}},output:function(t,e,n){var o,a,r;t.r?(a="M"===t.rdt?u.go(t.rd,"tex-math"):"T"===t.rdt?[{type_:"text",p1:t.rd||""}]:u.go(t.rd),r="M"===t.rqt?u.go(t.rq,"tex-math"):"T"===t.rqt?[{type_:"text",p1:t.rq||""}]:u.go(t.rq),o={type_:"arrow",r:t.r,rd:a,rq:r}):(o=[],(t.a||t.b||t.p||t.o||t.q||t.d||n)&&(t.sb&&o.push({type_:"entitySkip"}),t.o||t.q||t.d||t.b||t.p||2===n?t.o||t.q||t.d||!t.b&&!t.p?t.o&&"kv"===t.dType&&u.patterns.match_("d-oxidation$",t.d||"")?t.dType="oxidation":t.o&&"kv"===t.dType&&!t.q&&(t.dType=void 0):(t.o=t.a,t.d=t.b,t.q=t.p,t.a=t.b=t.p=void 0):(t.o=t.a,t.a=void 0),o.push({type_:"chemfive",a:u.go(t.a,"a"),b:u.go(t.b,"bd"),p:u.go(t.p,"pq"),o:u.go(t.o,"o"),q:u.go(t.q,"pq"),d:u.go(t.d,"oxidation"===t.dType?"oxidation":"bd"),dType:t.dType})));for(var i in t)"parenthesisLevel"!==i&&"beginsWithBond"!==i&&delete t[i];return o},"oxidation-output":function(t,e){var n=["{"];return u.concatArray(n,u.go(e,"oxidation")),n.push("}"),n},"frac-output":function(t,e){return{type_:"frac-ce",p1:u.go(e[0]),p2:u.go(e[1])}},"overset-output":function(t,e){return{type_:"overset",p1:u.go(e[0]),p2:u.go(e[1])}},"underset-output":function(t,e){return{type_:"underset",p1:u.go(e[0]),p2:u.go(e[1])}},"underbrace-output":function(t,e){return{type_:"underbrace",p1:u.go(e[0]),p2:u.go(e[1])}},"color-output":function(t,e){return{type_:"color",color1:e[0],color2:u.go(e[1])}},"r=":function(t,e){t.r=e},"rdt=":function(t,e){t.rdt=e},"rd=":function(t,e){t.rd=e},"rqt=":function(t,e){t.rqt=e},"rq=":function(t,e){t.rq=e},operator:function(t,e,n){return{type_:"operator",kind_:n||e}}}},a:{transitions:u.createTransitions({empty:{"*":{}},"1/2$":{0:{action_:"1/2"}},else:{0:{nextState:"1",revisit:!0}},"$(...)$":{"*":{action_:"tex-math tight",nextState:"1"}},",":{"*":{action_:{type_:"insert",option:"commaDecimal"}}},else2:{"*":{action_:"copy"}}}),actions:{}},o:{transitions:u.createTransitions({empty:{"*":{}},"1/2$":{0:{action_:"1/2"}},else:{0:{nextState:"1",revisit:!0}},letters:{"*":{action_:"rm"}},"\\ca":{"*":{action_:{type_:"insert",option:"circa"}}},"\\x{}{}|\\x{}|\\x":{"*":{action_:"copy"}},"${(...)}$|$(...)$":{"*":{action_:"tex-math"}},"{(...)}":{"*":{action_:"{text}"}},else2:{"*":{action_:"copy"}}}),actions:{}},text:{transitions:u.createTransitions({empty:{"*":{action_:"output"}},"{...}":{"*":{action_:"text="}},"${(...)}$|$(...)$":{"*":{action_:"tex-math"}},"\\greek":{"*":{action_:["output","rm"]}},"\\,|\\x{}{}|\\x{}|\\x":{"*":{action_:["output","copy"]}},else:{"*":{action_:"text="}}}),actions:{output:function(t){if(t.text_){var e={type_:"text",p1:t.text_};for(var n in t)delete t[n];return e}}}},pq:{transitions:u.createTransitions({empty:{"*":{}},"state of aggregation $":{"*":{action_:"state of aggregation"}},i$:{0:{nextState:"!f",revisit:!0}},"(KV letters),":{0:{action_:"rm",nextState:"0"}},formula$:{0:{nextState:"f",revisit:!0}},"1/2$":{0:{action_:"1/2"}},else:{0:{nextState:"!f",revisit:!0}},"${(...)}$|$(...)$":{"*":{action_:"tex-math"}},"{(...)}":{"*":{action_:"text"}},"a-z":{f:{action_:"tex-math"}},letters:{"*":{action_:"rm"}},"-9.,9":{"*":{action_:"9,9"}},",":{"*":{action_:{type_:"insert+p1",option:"comma enumeration S"}}},"\\color{(...)}{(...)}1|\\color(...){(...)}2":{"*":{action_:"color-output"}},"\\color{(...)}0":{"*":{action_:"color0-output"}},"\\ce{(...)}":{"*":{action_:"ce"}},"\\,|\\x{}{}|\\x{}|\\x":{"*":{action_:"copy"}},else2:{"*":{action_:"copy"}}}),actions:{"state of aggregation":function(t,e){return{type_:"state of aggregation subscript",p1:u.go(e,"o")}},"color-output":function(t,e){return{type_:"color",color1:e[0],color2:u.go(e[1],"pq")}}}},bd:{transitions:u.createTransitions({empty:{"*":{}},x$:{0:{nextState:"!f",revisit:!0}},formula$:{0:{nextState:"f",revisit:!0}},else:{0:{nextState:"!f",revisit:!0}},"-9.,9 no missing 0":{"*":{action_:"9,9"}},".":{"*":{action_:{type_:"insert",option:"electron dot"}}},"a-z":{f:{action_:"tex-math"}},x:{"*":{action_:{type_:"insert",option:"KV x"}}},letters:{"*":{action_:"rm"}},"'":{"*":{action_:{type_:"insert",option:"prime"}}},"${(...)}$|$(...)$":{"*":{action_:"tex-math"}},"{(...)}":{"*":{action_:"text"}},"\\color{(...)}{(...)}1|\\color(...){(...)}2":{"*":{action_:"color-output"}},"\\color{(...)}0":{"*":{action_:"color0-output"}},"\\ce{(...)}":{"*":{action_:"ce"}},"\\,|\\x{}{}|\\x{}|\\x":{"*":{action_:"copy"}},else2:{"*":{action_:"copy"}}}),actions:{"color-output":function(t,e){return{type_:"color",color1:e[0],color2:u.go(e[1],"bd")}}}},oxidation:{transitions:u.createTransitions({empty:{"*":{}},"roman numeral":{"*":{action_:"roman-numeral"}},"${(...)}$|$(...)$":{"*":{action_:"tex-math"}},else:{"*":{action_:"copy"}}}),actions:{"roman-numeral":function(t,e){return{type_:"roman numeral",p1:e||""}}}},"tex-math":{transitions:u.createTransitions({empty:{"*":{action_:"output"}},"\\ce{(...)}":{"*":{action_:["output","ce"]}},"{...}|\\,|\\x{}{}|\\x{}|\\x":{"*":{action_:"o="}},else:{"*":{action_:"o="}}}),actions:{output:function(t){if(t.o){var e={type_:"tex-math",p1:t.o};for(var n in t)delete t[n];return e}}}},"tex-math tight":{transitions:u.createTransitions({empty:{"*":{action_:"output"}},"\\ce{(...)}":{"*":{action_:["output","ce"]}},"{...}|\\,|\\x{}{}|\\x{}|\\x":{"*":{action_:"o="}},"-|+":{"*":{action_:"tight operator"}},else:{"*":{action_:"o="}}}),actions:{"tight operator":function(t,e){t.o=(t.o||"")+"{"+e+"}"},output:function(t){if(t.o){var e={type_:"tex-math",p1:t.o};for(var n in t)delete t[n];return e}}}},"9,9":{transitions:u.createTransitions({empty:{"*":{}},",":{"*":{action_:"comma"}},else:{"*":{action_:"copy"}}}),actions:{comma:function(){return{type_:"commaDecimal"}}}},pu:{transitions:u.createTransitions({empty:{"*":{action_:"output"}},space$:{"*":{action_:["output","space"]}},"{[(|)]}":{"0|a":{action_:"copy"}},"(-)(9)^(-9)":{0:{action_:"number^",nextState:"a"}},"(-)(9.,9)(e)(99)":{0:{action_:"enumber",nextState:"a"}},space:{"0|a":{}},"pm-operator":{"0|a":{action_:{type_:"operator",option:"\\pm"},nextState:"0"}},operator:{"0|a":{action_:"copy",nextState:"0"}},"//":{d:{action_:"o=",nextState:"/"}},"/":{d:{action_:"o=",nextState:"/"}},"{...}|else":{"0|d":{action_:"d=",nextState:"d"},a:{action_:["space","d="],nextState:"d"},"/|q":{action_:"q=",nextState:"q"}}}),actions:{enumber:function(t,e){var n=[];return"+-"===e[0]||"+/-"===e[0]?n.push("\\pm "):e[0]&&n.push(e[0]),e[1]&&(u.concatArray(n,u.go(e[1],"pu-9,9")),e[2]&&(e[2].match(/[,.]/)?u.concatArray(n,u.go(e[2],"pu-9,9")):n.push(e[2])),e[3]=e[4]||e[3],e[3]&&(e[3]=e[3].trim(),"e"===e[3]||"*"===e[3].substr(0,1)?n.push({type_:"cdot"}):n.push({type_:"times"}))),e[3]&&n.push("10^{"+e[5]+"}"),n},"number^":function(t,e){var n=[];return"+-"===e[0]||"+/-"===e[0]?n.push("\\pm "):e[0]&&n.push(e[0]),u.concatArray(n,u.go(e[1],"pu-9,9")),n.push("^{"+e[2]+"}"),n},operator:function(t,e,n){return{type_:"operator",kind_:n||e}},space:function(){return{type_:"pu-space-1"}},output:function(t){var e,n=u.patterns.match_("{(...)}",t.d||"");n&&""===n.remainder&&(t.d=n.match_);var o=u.patterns.match_("{(...)}",t.q||"");if(o&&""===o.remainder&&(t.q=o.match_),t.d&&(t.d=t.d.replace(/\u00B0C|\^oC|\^{o}C/g,"{}^{\\circ}C"),t.d=t.d.replace(/\u00B0F|\^oF|\^{o}F/g,"{}^{\\circ}F")),t.q){t.q=t.q.replace(/\u00B0C|\^oC|\^{o}C/g,"{}^{\\circ}C"),t.q=t.q.replace(/\u00B0F|\^oF|\^{o}F/g,"{}^{\\circ}F");var a={d:u.go(t.d,"pu"),q:u.go(t.q,"pu")};"//"===t.o?e={type_:"pu-frac",p1:a.d,p2:a.q}:(e=a.d,a.d.length>1||a.q.length>1?e.push({type_:" / "}):e.push({type_:"/"}),u.concatArray(e,a.q))}else e=u.go(t.d,"pu-2");for(var r in t)delete t[r];return e}}},"pu-2":{transitions:u.createTransitions({empty:{"*":{action_:"output"}},"*":{"*":{action_:["output","cdot"],nextState:"0"}},"\\x":{"*":{action_:"rm="}},space:{"*":{action_:["output","space"],nextState:"0"}},"^{(...)}|^(-1)":{1:{action_:"^(-1)"}},"-9.,9":{0:{action_:"rm=",nextState:"0"},1:{action_:"^(-1)",nextState:"0"}},"{...}|else":{"*":{action_:"rm=",nextState:"1"}}}),actions:{cdot:function(){return{type_:"tight cdot"}},"^(-1)":function(t,e){t.rm+="^{"+e+"}"},space:function(){return{type_:"pu-space-2"}},output:function(t){var e=[];if(t.rm){var n=u.patterns.match_("{(...)}",t.rm||"");e=n&&""===n.remainder?u.go(n.match_,"pu"):{type_:"rm",p1:t.rm}}for(var o in t)delete t[o];return e}}},"pu-9,9":{transitions:u.createTransitions({empty:{0:{action_:"output-0"},o:{action_:"output-o"}},",":{0:{action_:["output-0","comma"],nextState:"o"}},".":{0:{action_:["output-0","copy"],nextState:"o"}},else:{"*":{action_:"text="}}}),actions:{comma:function(){return{type_:"commaDecimal"}},"output-0":function(t){var e=[];if(t.text_=t.text_||"",t.text_.length>4){var n=t.text_.length%3;0===n&&(n=3);for(var o=t.text_.length-3;o>0;o-=3)e.push(t.text_.substr(o,3)),e.push({type_:"1000 separator"});e.push(t.text_.substr(0,n)),e.reverse()}else e.push(t.text_);for(var a in t)delete t[a];return e},"output-o":function(t){var e=[];if(t.text_=t.text_||"",t.text_.length>4){for(var n=t.text_.length-3,o=0;o":case"\u2192":case"\u27f6":return"rightarrow";case"<-":return"leftarrow";case"<->":return"leftrightarrow";case"<--\x3e":return"rightleftarrows";case"<=>":case"\u21cc":return"rightleftharpoons";case"<=>>":return"rightequilibrium";case"<<=>":return"leftequilibrium";default:throw["MhchemBugT","mhchem bug T. Please report."]}},_getBond:function(t){switch(t){case"-":case"1":return"{-}";case"=":case"2":return"{=}";case"#":case"3":return"{\\equiv}";case"~":return"{\\tripledash}";case"~-":return"{\\mathrlap{\\raisebox{-.1em}{$-$}}\\raisebox{.1em}{$\\tripledash$}}";case"~=":case"~--":return"{\\mathrlap{\\raisebox{-.2em}{$-$}}\\mathrlap{\\raisebox{.2em}{$\\tripledash$}}-}";case"-~-":return"{\\mathrlap{\\raisebox{-.2em}{$-$}}\\mathrlap{\\raisebox{.2em}{$-$}}\\tripledash}";case"...":return"{{\\cdot}{\\cdot}{\\cdot}}";case"....":return"{{\\cdot}{\\cdot}{\\cdot}{\\cdot}}";case"->":return"{\\rightarrow}";case"<-":return"{\\leftarrow}";case"<":return"{<}";case">":return"{>}";default:throw["MhchemBugT","mhchem bug T. Please report."]}},_getOperator:function(t){switch(t){case"+":return" {}+{} ";case"-":return" {}-{} ";case"=":return" {}={} ";case"<":return" {}<{} ";case">":return" {}>{} ";case"<<":return" {}\\ll{} ";case">>":return" {}\\gg{} ";case"\\pm":return" {}\\pm{} ";case"\\approx":case"$\\approx$":return" {}\\approx{} ";case"v":case"(v)":return" \\downarrow{} ";case"^":case"(^)":return" \\uparrow{} ";default:throw["MhchemBugT","mhchem bug T. Please report."]}}};return a=a.default}()})); \ No newline at end of file diff --git a/frontend/node_modules/katex/dist/contrib/mhchem.mjs b/frontend/node_modules/katex/dist/contrib/mhchem.mjs new file mode 100644 index 0000000..7d93825 --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/mhchem.mjs @@ -0,0 +1,3109 @@ +import katex from '../katex.mjs'; + +/* eslint-disable */ + +/* -*- Mode: JavaScript; indent-tabs-mode:nil; js-indent-level: 2 -*- */ + +/* vim: set ts=2 et sw=2 tw=80: */ + +/************************************************************* + * + * KaTeX mhchem.js + * + * This file implements a KaTeX version of mhchem version 3.3.0. + * It is adapted from MathJax/extensions/TeX/mhchem.js + * It differs from the MathJax version as follows: + * 1. The interface is changed so that it can be called from KaTeX, not MathJax. + * 2. \rlap and \llap are replaced with \mathrlap and \mathllap. + * 3. Four lines of code are edited in order to use \raisebox instead of \raise. + * 4. The reaction arrow code is simplified. All reaction arrows are rendered + * using KaTeX extensible arrows instead of building non-extensible arrows. + * 5. \tripledash vertical alignment is slightly adjusted. + * + * This code, as other KaTeX code, is released under the MIT license. + * + * /************************************************************* + * + * MathJax/extensions/TeX/mhchem.js + * + * Implements the \ce command for handling chemical formulas + * from the mhchem LaTeX package. + * + * --------------------------------------------------------------------- + * + * Copyright (c) 2011-2015 The MathJax Consortium + * Copyright (c) 2015-2018 Martin Hensel + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +// +// Coding Style +// - use '' for identifiers that can by minified/uglified +// - use "" for strings that need to stay untouched +// version: "3.3.0" for MathJax and KaTeX +// Add \ce, \pu, and \tripledash to the KaTeX macros. +katex.__defineMacro("\\ce", function (context) { + return chemParse(context.consumeArgs(1)[0], "ce"); +}); + +katex.__defineMacro("\\pu", function (context) { + return chemParse(context.consumeArgs(1)[0], "pu"); +}); // Needed for \bond for the ~ forms +// Raise by 2.56mu, not 2mu. We're raising a hyphen-minus, U+002D, not +// a mathematical minus, U+2212. So we need that extra 0.56. + + +katex.__defineMacro("\\tripledash", "{\\vphantom{-}\\raisebox{2.56mu}{$\\mkern2mu" + "\\tiny\\text{-}\\mkern1mu\\text{-}\\mkern1mu\\text{-}\\mkern2mu$}}"); +// This is the main function for handing the \ce and \pu commands. +// It takes the argument to \ce or \pu and returns the corresponding TeX string. +// + +var chemParse = function chemParse(tokens, stateMachine) { + // Recreate the argument string from KaTeX's array of tokens. + var str = ""; + var expectedLoc = tokens.length && tokens[tokens.length - 1].loc.start; + + for (var i = tokens.length - 1; i >= 0; i--) { + if (tokens[i].loc.start > expectedLoc) { + // context.consumeArgs has eaten a space. + str += " "; + expectedLoc = tokens[i].loc.start; + } + + str += tokens[i].text; + expectedLoc += tokens[i].text.length; + } + + var tex = texify.go(mhchemParser.go(str, stateMachine)); + return tex; +}; // +// Core parser for mhchem syntax (recursive) +// + +/** @type {MhchemParser} */ + + +var mhchemParser = { + // + // Parses mchem \ce syntax + // + // Call like + // go("H2O"); + // + go: function go(input, stateMachine) { + if (!input) { + return []; + } + + if (stateMachine === undefined) { + stateMachine = 'ce'; + } + + var state = '0'; // + // String buffers for parsing: + // + // buffer.a == amount + // buffer.o == element + // buffer.b == left-side superscript + // buffer.p == left-side subscript + // buffer.q == right-side subscript + // buffer.d == right-side superscript + // + // buffer.r == arrow + // buffer.rdt == arrow, script above, type + // buffer.rd == arrow, script above, content + // buffer.rqt == arrow, script below, type + // buffer.rq == arrow, script below, content + // + // buffer.text_ + // buffer.rm + // etc. + // + // buffer.parenthesisLevel == int, starting at 0 + // buffer.sb == bool, space before + // buffer.beginsWithBond == bool + // + // These letters are also used as state names. + // + // Other states: + // 0 == begin of main part (arrow/operator unlikely) + // 1 == next entity + // 2 == next entity (arrow/operator unlikely) + // 3 == next atom + // c == macro + // + + /** @type {Buffer} */ + + var buffer = {}; + buffer['parenthesisLevel'] = 0; + input = input.replace(/\n/g, " "); + input = input.replace(/[\u2212\u2013\u2014\u2010]/g, "-"); + input = input.replace(/[\u2026]/g, "..."); // + // Looks through mhchemParser.transitions, to execute a matching action + // (recursive) + // + + var lastInput; + var watchdog = 10; + /** @type {ParserOutput[]} */ + + var output = []; + + while (true) { + if (lastInput !== input) { + watchdog = 10; + lastInput = input; + } else { + watchdog--; + } // + // Find actions in transition table + // + + + var machine = mhchemParser.stateMachines[stateMachine]; + var t = machine.transitions[state] || machine.transitions['*']; + + iterateTransitions: for (var i = 0; i < t.length; i++) { + var matches = mhchemParser.patterns.match_(t[i].pattern, input); + + if (matches) { + // + // Execute actions + // + var task = t[i].task; + + for (var iA = 0; iA < task.action_.length; iA++) { + var o; // + // Find and execute action + // + + if (machine.actions[task.action_[iA].type_]) { + o = machine.actions[task.action_[iA].type_](buffer, matches.match_, task.action_[iA].option); + } else if (mhchemParser.actions[task.action_[iA].type_]) { + o = mhchemParser.actions[task.action_[iA].type_](buffer, matches.match_, task.action_[iA].option); + } else { + throw ["MhchemBugA", "mhchem bug A. Please report. (" + task.action_[iA].type_ + ")"]; // Trying to use non-existing action + } // + // Add output + // + + + mhchemParser.concatArray(output, o); + } // + // Set next state, + // Shorten input, + // Continue with next character + // (= apply only one transition per position) + // + + + state = task.nextState || state; + + if (input.length > 0) { + if (!task.revisit) { + input = matches.remainder; + } + + if (!task.toContinue) { + break iterateTransitions; + } + } else { + return output; + } + } + } // + // Prevent infinite loop + // + + + if (watchdog <= 0) { + throw ["MhchemBugU", "mhchem bug U. Please report."]; // Unexpected character + } + } + }, + concatArray: function concatArray(a, b) { + if (b) { + if (Array.isArray(b)) { + for (var iB = 0; iB < b.length; iB++) { + a.push(b[iB]); + } + } else { + a.push(b); + } + } + }, + patterns: { + // + // Matching patterns + // either regexps or function that return null or {match_:"a", remainder:"bc"} + // + patterns: { + // property names must not look like integers ("2") for correct property traversal order, later on + 'empty': /^$/, + 'else': /^./, + 'else2': /^./, + 'space': /^\s/, + 'space A': /^\s(?=[A-Z\\$])/, + 'space$': /^\s$/, + 'a-z': /^[a-z]/, + 'x': /^x/, + 'x$': /^x$/, + 'i$': /^i$/, + 'letters': /^(?:[a-zA-Z\u03B1-\u03C9\u0391-\u03A9?@]|(?:\\(?:alpha|beta|gamma|delta|epsilon|zeta|eta|theta|iota|kappa|lambda|mu|nu|xi|omicron|pi|rho|sigma|tau|upsilon|phi|chi|psi|omega|Gamma|Delta|Theta|Lambda|Xi|Pi|Sigma|Upsilon|Phi|Psi|Omega)(?:\s+|\{\}|(?![a-zA-Z]))))+/, + '\\greek': /^\\(?:alpha|beta|gamma|delta|epsilon|zeta|eta|theta|iota|kappa|lambda|mu|nu|xi|omicron|pi|rho|sigma|tau|upsilon|phi|chi|psi|omega|Gamma|Delta|Theta|Lambda|Xi|Pi|Sigma|Upsilon|Phi|Psi|Omega)(?:\s+|\{\}|(?![a-zA-Z]))/, + 'one lowercase latin letter $': /^(?:([a-z])(?:$|[^a-zA-Z]))$/, + '$one lowercase latin letter$ $': /^\$(?:([a-z])(?:$|[^a-zA-Z]))\$$/, + 'one lowercase greek letter $': /^(?:\$?[\u03B1-\u03C9]\$?|\$?\\(?:alpha|beta|gamma|delta|epsilon|zeta|eta|theta|iota|kappa|lambda|mu|nu|xi|omicron|pi|rho|sigma|tau|upsilon|phi|chi|psi|omega)\s*\$?)(?:\s+|\{\}|(?![a-zA-Z]))$/, + 'digits': /^[0-9]+/, + '-9.,9': /^[+\-]?(?:[0-9]+(?:[,.][0-9]+)?|[0-9]*(?:\.[0-9]+))/, + '-9.,9 no missing 0': /^[+\-]?[0-9]+(?:[.,][0-9]+)?/, + '(-)(9.,9)(e)(99)': function e99(input) { + var m = input.match(/^(\+\-|\+\/\-|\+|\-|\\pm\s?)?([0-9]+(?:[,.][0-9]+)?|[0-9]*(?:\.[0-9]+))?(\((?:[0-9]+(?:[,.][0-9]+)?|[0-9]*(?:\.[0-9]+))\))?(?:([eE]|\s*(\*|x|\\times|\u00D7)\s*10\^)([+\-]?[0-9]+|\{[+\-]?[0-9]+\}))?/); + + if (m && m[0]) { + return { + match_: m.splice(1), + remainder: input.substr(m[0].length) + }; + } + + return null; + }, + '(-)(9)^(-9)': function _(input) { + var m = input.match(/^(\+\-|\+\/\-|\+|\-|\\pm\s?)?([0-9]+(?:[,.][0-9]+)?|[0-9]*(?:\.[0-9]+)?)\^([+\-]?[0-9]+|\{[+\-]?[0-9]+\})/); + + if (m && m[0]) { + return { + match_: m.splice(1), + remainder: input.substr(m[0].length) + }; + } + + return null; + }, + 'state of aggregation $': function stateOfAggregation$(input) { + // ... or crystal system + var a = mhchemParser.patterns.findObserveGroups(input, "", /^\([a-z]{1,3}(?=[\),])/, ")", ""); // (aq), (aq,$\infty$), (aq, sat) + + if (a && a.remainder.match(/^($|[\s,;\)\]\}])/)) { + return a; + } // AND end of 'phrase' + + + var m = input.match(/^(?:\((?:\\ca\s?)?\$[amothc]\$\))/); // OR crystal system ($o$) (\ca$c$) + + if (m) { + return { + match_: m[0], + remainder: input.substr(m[0].length) + }; + } + + return null; + }, + '_{(state of aggregation)}$': /^_\{(\([a-z]{1,3}\))\}/, + '{[(': /^(?:\\\{|\[|\()/, + ')]}': /^(?:\)|\]|\\\})/, + ', ': /^[,;]\s*/, + ',': /^[,;]/, + '.': /^[.]/, + '. ': /^([.\u22C5\u00B7\u2022])\s*/, + '...': /^\.\.\.(?=$|[^.])/, + '* ': /^([*])\s*/, + '^{(...)}': function _(input) { + return mhchemParser.patterns.findObserveGroups(input, "^{", "", "", "}"); + }, + '^($...$)': function $$(input) { + return mhchemParser.patterns.findObserveGroups(input, "^", "$", "$", ""); + }, + '^a': /^\^([0-9]+|[^\\_])/, + '^\\x{}{}': function x(input) { + return mhchemParser.patterns.findObserveGroups(input, "^", /^\\[a-zA-Z]+\{/, "}", "", "", "{", "}", "", true); + }, + '^\\x{}': function x(input) { + return mhchemParser.patterns.findObserveGroups(input, "^", /^\\[a-zA-Z]+\{/, "}", ""); + }, + '^\\x': /^\^(\\[a-zA-Z]+)\s*/, + '^(-1)': /^\^(-?\d+)/, + '\'': /^'/, + '_{(...)}': function _(input) { + return mhchemParser.patterns.findObserveGroups(input, "_{", "", "", "}"); + }, + '_($...$)': function _$$(input) { + return mhchemParser.patterns.findObserveGroups(input, "_", "$", "$", ""); + }, + '_9': /^_([+\-]?[0-9]+|[^\\])/, + '_\\x{}{}': function _X(input) { + return mhchemParser.patterns.findObserveGroups(input, "_", /^\\[a-zA-Z]+\{/, "}", "", "", "{", "}", "", true); + }, + '_\\x{}': function _X(input) { + return mhchemParser.patterns.findObserveGroups(input, "_", /^\\[a-zA-Z]+\{/, "}", ""); + }, + '_\\x': /^_(\\[a-zA-Z]+)\s*/, + '^_': /^(?:\^(?=_)|\_(?=\^)|[\^_]$)/, + '{}': /^\{\}/, + '{...}': function _(input) { + return mhchemParser.patterns.findObserveGroups(input, "", "{", "}", ""); + }, + '{(...)}': function _(input) { + return mhchemParser.patterns.findObserveGroups(input, "{", "", "", "}"); + }, + '$...$': function $$(input) { + return mhchemParser.patterns.findObserveGroups(input, "", "$", "$", ""); + }, + '${(...)}$': function $$(input) { + return mhchemParser.patterns.findObserveGroups(input, "${", "", "", "}$"); + }, + '$(...)$': function $$(input) { + return mhchemParser.patterns.findObserveGroups(input, "$", "", "", "$"); + }, + '=<>': /^[=<>]/, + '#': /^[#\u2261]/, + '+': /^\+/, + '-$': /^-(?=[\s_},;\]/]|$|\([a-z]+\))/, + // -space -, -; -] -/ -$ -state-of-aggregation + '-9': /^-(?=[0-9])/, + '- orbital overlap': /^-(?=(?:[spd]|sp)(?:$|[\s,;\)\]\}]))/, + '-': /^-/, + 'pm-operator': /^(?:\\pm|\$\\pm\$|\+-|\+\/-)/, + 'operator': /^(?:\+|(?:[\-=<>]|<<|>>|\\approx|\$\\approx\$)(?=\s|$|-?[0-9]))/, + 'arrowUpDown': /^(?:v|\(v\)|\^|\(\^\))(?=$|[\s,;\)\]\}])/, + '\\bond{(...)}': function bond(input) { + return mhchemParser.patterns.findObserveGroups(input, "\\bond{", "", "", "}"); + }, + '->': /^(?:<->|<-->|->|<-|<=>>|<<=>|<=>|[\u2192\u27F6\u21CC])/, + 'CMT': /^[CMT](?=\[)/, + '[(...)]': function _(input) { + return mhchemParser.patterns.findObserveGroups(input, "[", "", "", "]"); + }, + '1st-level escape': /^(&|\\\\|\\hline)\s*/, + '\\,': /^(?:\\[,\ ;:])/, + // \\x - but output no space before + '\\x{}{}': function x(input) { + return mhchemParser.patterns.findObserveGroups(input, "", /^\\[a-zA-Z]+\{/, "}", "", "", "{", "}", "", true); + }, + '\\x{}': function x(input) { + return mhchemParser.patterns.findObserveGroups(input, "", /^\\[a-zA-Z]+\{/, "}", ""); + }, + '\\ca': /^\\ca(?:\s+|(?![a-zA-Z]))/, + '\\x': /^(?:\\[a-zA-Z]+\s*|\\[_&{}%])/, + 'orbital': /^(?:[0-9]{1,2}[spdfgh]|[0-9]{0,2}sp)(?=$|[^a-zA-Z])/, + // only those with numbers in front, because the others will be formatted correctly anyway + 'others': /^[\/~|]/, + '\\frac{(...)}': function frac(input) { + return mhchemParser.patterns.findObserveGroups(input, "\\frac{", "", "", "}", "{", "", "", "}"); + }, + '\\overset{(...)}': function overset(input) { + return mhchemParser.patterns.findObserveGroups(input, "\\overset{", "", "", "}", "{", "", "", "}"); + }, + '\\underset{(...)}': function underset(input) { + return mhchemParser.patterns.findObserveGroups(input, "\\underset{", "", "", "}", "{", "", "", "}"); + }, + '\\underbrace{(...)}': function underbrace(input) { + return mhchemParser.patterns.findObserveGroups(input, "\\underbrace{", "", "", "}_", "{", "", "", "}"); + }, + '\\color{(...)}0': function color0(input) { + return mhchemParser.patterns.findObserveGroups(input, "\\color{", "", "", "}"); + }, + '\\color{(...)}{(...)}1': function color1(input) { + return mhchemParser.patterns.findObserveGroups(input, "\\color{", "", "", "}", "{", "", "", "}"); + }, + '\\color(...){(...)}2': function color2(input) { + return mhchemParser.patterns.findObserveGroups(input, "\\color", "\\", "", /^(?=\{)/, "{", "", "", "}"); + }, + '\\ce{(...)}': function ce(input) { + return mhchemParser.patterns.findObserveGroups(input, "\\ce{", "", "", "}"); + }, + 'oxidation$': /^(?:[+-][IVX]+|\\pm\s*0|\$\\pm\$\s*0)$/, + 'd-oxidation$': /^(?:[+-]?\s?[IVX]+|\\pm\s*0|\$\\pm\$\s*0)$/, + // 0 could be oxidation or charge + 'roman numeral': /^[IVX]+/, + '1/2$': /^[+\-]?(?:[0-9]+|\$[a-z]\$|[a-z])\/[0-9]+(?:\$[a-z]\$|[a-z])?$/, + 'amount': function amount(input) { + var match; // e.g. 2, 0.5, 1/2, -2, n/2, +; $a$ could be added later in parsing + + match = input.match(/^(?:(?:(?:\([+\-]?[0-9]+\/[0-9]+\)|[+\-]?(?:[0-9]+|\$[a-z]\$|[a-z])\/[0-9]+|[+\-]?[0-9]+[.,][0-9]+|[+\-]?\.[0-9]+|[+\-]?[0-9]+)(?:[a-z](?=\s*[A-Z]))?)|[+\-]?[a-z](?=\s*[A-Z])|\+(?!\s))/); + + if (match) { + return { + match_: match[0], + remainder: input.substr(match[0].length) + }; + } + + var a = mhchemParser.patterns.findObserveGroups(input, "", "$", "$", ""); + + if (a) { + // e.g. $2n-1$, $-$ + match = a.match_.match(/^\$(?:\(?[+\-]?(?:[0-9]*[a-z]?[+\-])?[0-9]*[a-z](?:[+\-][0-9]*[a-z]?)?\)?|\+|-)\$$/); + + if (match) { + return { + match_: match[0], + remainder: input.substr(match[0].length) + }; + } + } + + return null; + }, + 'amount2': function amount2(input) { + return this['amount'](input); + }, + '(KV letters),': /^(?:[A-Z][a-z]{0,2}|i)(?=,)/, + 'formula$': function formula$(input) { + if (input.match(/^\([a-z]+\)$/)) { + return null; + } // state of aggregation = no formula + + + var match = input.match(/^(?:[a-z]|(?:[0-9\ \+\-\,\.\(\)]+[a-z])+[0-9\ \+\-\,\.\(\)]*|(?:[a-z][0-9\ \+\-\,\.\(\)]+)+[a-z]?)$/); + + if (match) { + return { + match_: match[0], + remainder: input.substr(match[0].length) + }; + } + + return null; + }, + 'uprightEntities': /^(?:pH|pOH|pC|pK|iPr|iBu)(?=$|[^a-zA-Z])/, + '/': /^\s*(\/)\s*/, + '//': /^\s*(\/\/)\s*/, + '*': /^\s*[*.]\s*/ + }, + findObserveGroups: function findObserveGroups(input, begExcl, begIncl, endIncl, endExcl, beg2Excl, beg2Incl, end2Incl, end2Excl, combine) { + /** @type {{(input: string, pattern: string | RegExp): string | string[] | null;}} */ + var _match = function _match(input, pattern) { + if (typeof pattern === "string") { + if (input.indexOf(pattern) !== 0) { + return null; + } + + return pattern; + } else { + var match = input.match(pattern); + + if (!match) { + return null; + } + + return match[0]; + } + }; + /** @type {{(input: string, i: number, endChars: string | RegExp): {endMatchBegin: number, endMatchEnd: number} | null;}} */ + + + var _findObserveGroups = function _findObserveGroups(input, i, endChars) { + var braces = 0; + + while (i < input.length) { + var a = input.charAt(i); + + var match = _match(input.substr(i), endChars); + + if (match !== null && braces === 0) { + return { + endMatchBegin: i, + endMatchEnd: i + match.length + }; + } else if (a === "{") { + braces++; + } else if (a === "}") { + if (braces === 0) { + throw ["ExtraCloseMissingOpen", "Extra close brace or missing open brace"]; + } else { + braces--; + } + } + + i++; + } + + if (braces > 0) { + return null; + } + + return null; + }; + + var match = _match(input, begExcl); + + if (match === null) { + return null; + } + + input = input.substr(match.length); + match = _match(input, begIncl); + + if (match === null) { + return null; + } + + var e = _findObserveGroups(input, match.length, endIncl || endExcl); + + if (e === null) { + return null; + } + + var match1 = input.substring(0, endIncl ? e.endMatchEnd : e.endMatchBegin); + + if (!(beg2Excl || beg2Incl)) { + return { + match_: match1, + remainder: input.substr(e.endMatchEnd) + }; + } else { + var group2 = this.findObserveGroups(input.substr(e.endMatchEnd), beg2Excl, beg2Incl, end2Incl, end2Excl); + + if (group2 === null) { + return null; + } + /** @type {string[]} */ + + + var matchRet = [match1, group2.match_]; + return { + match_: combine ? matchRet.join("") : matchRet, + remainder: group2.remainder + }; + } + }, + // + // Matching function + // e.g. match("a", input) will look for the regexp called "a" and see if it matches + // returns null or {match_:"a", remainder:"bc"} + // + match_: function match_(m, input) { + var pattern = mhchemParser.patterns.patterns[m]; + + if (pattern === undefined) { + throw ["MhchemBugP", "mhchem bug P. Please report. (" + m + ")"]; // Trying to use non-existing pattern + } else if (typeof pattern === "function") { + return mhchemParser.patterns.patterns[m](input); // cannot use cached var pattern here, because some pattern functions need this===mhchemParser + } else { + // RegExp + var match = input.match(pattern); + + if (match) { + var mm; + + if (match[2]) { + mm = [match[1], match[2]]; + } else if (match[1]) { + mm = match[1]; + } else { + mm = match[0]; + } + + return { + match_: mm, + remainder: input.substr(match[0].length) + }; + } + + return null; + } + } + }, + // + // Generic state machine actions + // + actions: { + 'a=': function a(buffer, m) { + buffer.a = (buffer.a || "") + m; + }, + 'b=': function b(buffer, m) { + buffer.b = (buffer.b || "") + m; + }, + 'p=': function p(buffer, m) { + buffer.p = (buffer.p || "") + m; + }, + 'o=': function o(buffer, m) { + buffer.o = (buffer.o || "") + m; + }, + 'q=': function q(buffer, m) { + buffer.q = (buffer.q || "") + m; + }, + 'd=': function d(buffer, m) { + buffer.d = (buffer.d || "") + m; + }, + 'rm=': function rm(buffer, m) { + buffer.rm = (buffer.rm || "") + m; + }, + 'text=': function text(buffer, m) { + buffer.text_ = (buffer.text_ || "") + m; + }, + 'insert': function insert(buffer, m, a) { + return { + type_: a + }; + }, + 'insert+p1': function insertP1(buffer, m, a) { + return { + type_: a, + p1: m + }; + }, + 'insert+p1+p2': function insertP1P2(buffer, m, a) { + return { + type_: a, + p1: m[0], + p2: m[1] + }; + }, + 'copy': function copy(buffer, m) { + return m; + }, + 'rm': function rm(buffer, m) { + return { + type_: 'rm', + p1: m || "" + }; + }, + 'text': function text(buffer, m) { + return mhchemParser.go(m, 'text'); + }, + '{text}': function text(buffer, m) { + var ret = ["{"]; + mhchemParser.concatArray(ret, mhchemParser.go(m, 'text')); + ret.push("}"); + return ret; + }, + 'tex-math': function texMath(buffer, m) { + return mhchemParser.go(m, 'tex-math'); + }, + 'tex-math tight': function texMathTight(buffer, m) { + return mhchemParser.go(m, 'tex-math tight'); + }, + 'bond': function bond(buffer, m, k) { + return { + type_: 'bond', + kind_: k || m + }; + }, + 'color0-output': function color0Output(buffer, m) { + return { + type_: 'color0', + color: m[0] + }; + }, + 'ce': function ce(buffer, m) { + return mhchemParser.go(m); + }, + '1/2': function _(buffer, m) { + /** @type {ParserOutput[]} */ + var ret = []; + + if (m.match(/^[+\-]/)) { + ret.push(m.substr(0, 1)); + m = m.substr(1); + } + + var n = m.match(/^([0-9]+|\$[a-z]\$|[a-z])\/([0-9]+)(\$[a-z]\$|[a-z])?$/); + n[1] = n[1].replace(/\$/g, ""); + ret.push({ + type_: 'frac', + p1: n[1], + p2: n[2] + }); + + if (n[3]) { + n[3] = n[3].replace(/\$/g, ""); + ret.push({ + type_: 'tex-math', + p1: n[3] + }); + } + + return ret; + }, + '9,9': function _(buffer, m) { + return mhchemParser.go(m, '9,9'); + } + }, + // + // createTransitions + // convert { 'letter': { 'state': { action_: 'output' } } } to { 'state' => [ { pattern: 'letter', task: { action_: [{type_: 'output'}] } } ] } + // with expansion of 'a|b' to 'a' and 'b' (at 2 places) + // + createTransitions: function createTransitions(o) { + var pattern, state; + /** @type {string[]} */ + + var stateArray; + var i; // + // 1. Collect all states + // + + /** @type {Transitions} */ + + var transitions = {}; + + for (pattern in o) { + for (state in o[pattern]) { + stateArray = state.split("|"); + o[pattern][state].stateArray = stateArray; + + for (i = 0; i < stateArray.length; i++) { + transitions[stateArray[i]] = []; + } + } + } // + // 2. Fill states + // + + + for (pattern in o) { + for (state in o[pattern]) { + stateArray = o[pattern][state].stateArray || []; + + for (i = 0; i < stateArray.length; i++) { + // + // 2a. Normalize actions into array: 'text=' ==> [{type_:'text='}] + // (Note to myself: Resolving the function here would be problematic. It would need .bind (for *this*) and currying (for *option*).) + // + + /** @type {any} */ + var p = o[pattern][state]; + + if (p.action_) { + p.action_ = [].concat(p.action_); + + for (var k = 0; k < p.action_.length; k++) { + if (typeof p.action_[k] === "string") { + p.action_[k] = { + type_: p.action_[k] + }; + } + } + } else { + p.action_ = []; + } // + // 2.b Multi-insert + // + + + var patternArray = pattern.split("|"); + + for (var j = 0; j < patternArray.length; j++) { + if (stateArray[i] === '*') { + // insert into all + for (var t in transitions) { + transitions[t].push({ + pattern: patternArray[j], + task: p + }); + } + } else { + transitions[stateArray[i]].push({ + pattern: patternArray[j], + task: p + }); + } + } + } + } + } + + return transitions; + }, + stateMachines: {} +}; // +// Definition of state machines +// + +mhchemParser.stateMachines = { + // + // \ce state machines + // + //#region ce + 'ce': { + // main parser + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': { + action_: 'output' + } + }, + 'else': { + '0|1|2': { + action_: 'beginsWithBond=false', + revisit: true, + toContinue: true + } + }, + 'oxidation$': { + '0': { + action_: 'oxidation-output' + } + }, + 'CMT': { + 'r': { + action_: 'rdt=', + nextState: 'rt' + }, + 'rd': { + action_: 'rqt=', + nextState: 'rdt' + } + }, + 'arrowUpDown': { + '0|1|2|as': { + action_: ['sb=false', 'output', 'operator'], + nextState: '1' + } + }, + 'uprightEntities': { + '0|1|2': { + action_: ['o=', 'output'], + nextState: '1' + } + }, + 'orbital': { + '0|1|2|3': { + action_: 'o=', + nextState: 'o' + } + }, + '->': { + '0|1|2|3': { + action_: 'r=', + nextState: 'r' + }, + 'a|as': { + action_: ['output', 'r='], + nextState: 'r' + }, + '*': { + action_: ['output', 'r='], + nextState: 'r' + } + }, + '+': { + 'o': { + action_: 'd= kv', + nextState: 'd' + }, + 'd|D': { + action_: 'd=', + nextState: 'd' + }, + 'q': { + action_: 'd=', + nextState: 'qd' + }, + 'qd|qD': { + action_: 'd=', + nextState: 'qd' + }, + 'dq': { + action_: ['output', 'd='], + nextState: 'd' + }, + '3': { + action_: ['sb=false', 'output', 'operator'], + nextState: '0' + } + }, + 'amount': { + '0|2': { + action_: 'a=', + nextState: 'a' + } + }, + 'pm-operator': { + '0|1|2|a|as': { + action_: ['sb=false', 'output', { + type_: 'operator', + option: '\\pm' + }], + nextState: '0' + } + }, + 'operator': { + '0|1|2|a|as': { + action_: ['sb=false', 'output', 'operator'], + nextState: '0' + } + }, + '-$': { + 'o|q': { + action_: ['charge or bond', 'output'], + nextState: 'qd' + }, + 'd': { + action_: 'd=', + nextState: 'd' + }, + 'D': { + action_: ['output', { + type_: 'bond', + option: "-" + }], + nextState: '3' + }, + 'q': { + action_: 'd=', + nextState: 'qd' + }, + 'qd': { + action_: 'd=', + nextState: 'qd' + }, + 'qD|dq': { + action_: ['output', { + type_: 'bond', + option: "-" + }], + nextState: '3' + } + }, + '-9': { + '3|o': { + action_: ['output', { + type_: 'insert', + option: 'hyphen' + }], + nextState: '3' + } + }, + '- orbital overlap': { + 'o': { + action_: ['output', { + type_: 'insert', + option: 'hyphen' + }], + nextState: '2' + }, + 'd': { + action_: ['output', { + type_: 'insert', + option: 'hyphen' + }], + nextState: '2' + } + }, + '-': { + '0|1|2': { + action_: [{ + type_: 'output', + option: 1 + }, 'beginsWithBond=true', { + type_: 'bond', + option: "-" + }], + nextState: '3' + }, + '3': { + action_: { + type_: 'bond', + option: "-" + } + }, + 'a': { + action_: ['output', { + type_: 'insert', + option: 'hyphen' + }], + nextState: '2' + }, + 'as': { + action_: [{ + type_: 'output', + option: 2 + }, { + type_: 'bond', + option: "-" + }], + nextState: '3' + }, + 'b': { + action_: 'b=' + }, + 'o': { + action_: { + type_: '- after o/d', + option: false + }, + nextState: '2' + }, + 'q': { + action_: { + type_: '- after o/d', + option: false + }, + nextState: '2' + }, + 'd|qd|dq': { + action_: { + type_: '- after o/d', + option: true + }, + nextState: '2' + }, + 'D|qD|p': { + action_: ['output', { + type_: 'bond', + option: "-" + }], + nextState: '3' + } + }, + 'amount2': { + '1|3': { + action_: 'a=', + nextState: 'a' + } + }, + 'letters': { + '0|1|2|3|a|as|b|p|bp|o': { + action_: 'o=', + nextState: 'o' + }, + 'q|dq': { + action_: ['output', 'o='], + nextState: 'o' + }, + 'd|D|qd|qD': { + action_: 'o after d', + nextState: 'o' + } + }, + 'digits': { + 'o': { + action_: 'q=', + nextState: 'q' + }, + 'd|D': { + action_: 'q=', + nextState: 'dq' + }, + 'q': { + action_: ['output', 'o='], + nextState: 'o' + }, + 'a': { + action_: 'o=', + nextState: 'o' + } + }, + 'space A': { + 'b|p|bp': {} + }, + 'space': { + 'a': { + nextState: 'as' + }, + '0': { + action_: 'sb=false' + }, + '1|2': { + action_: 'sb=true' + }, + 'r|rt|rd|rdt|rdq': { + action_: 'output', + nextState: '0' + }, + '*': { + action_: ['output', 'sb=true'], + nextState: '1' + } + }, + '1st-level escape': { + '1|2': { + action_: ['output', { + type_: 'insert+p1', + option: '1st-level escape' + }] + }, + '*': { + action_: ['output', { + type_: 'insert+p1', + option: '1st-level escape' + }], + nextState: '0' + } + }, + '[(...)]': { + 'r|rt': { + action_: 'rd=', + nextState: 'rd' + }, + 'rd|rdt': { + action_: 'rq=', + nextState: 'rdq' + } + }, + '...': { + 'o|d|D|dq|qd|qD': { + action_: ['output', { + type_: 'bond', + option: "..." + }], + nextState: '3' + }, + '*': { + action_: [{ + type_: 'output', + option: 1 + }, { + type_: 'insert', + option: 'ellipsis' + }], + nextState: '1' + } + }, + '. |* ': { + '*': { + action_: ['output', { + type_: 'insert', + option: 'addition compound' + }], + nextState: '1' + } + }, + 'state of aggregation $': { + '*': { + action_: ['output', 'state of aggregation'], + nextState: '1' + } + }, + '{[(': { + 'a|as|o': { + action_: ['o=', 'output', 'parenthesisLevel++'], + nextState: '2' + }, + '0|1|2|3': { + action_: ['o=', 'output', 'parenthesisLevel++'], + nextState: '2' + }, + '*': { + action_: ['output', 'o=', 'output', 'parenthesisLevel++'], + nextState: '2' + } + }, + ')]}': { + '0|1|2|3|b|p|bp|o': { + action_: ['o=', 'parenthesisLevel--'], + nextState: 'o' + }, + 'a|as|d|D|q|qd|qD|dq': { + action_: ['output', 'o=', 'parenthesisLevel--'], + nextState: 'o' + } + }, + ', ': { + '*': { + action_: ['output', 'comma'], + nextState: '0' + } + }, + '^_': { + // ^ and _ without a sensible argument + '*': {} + }, + '^{(...)}|^($...$)': { + '0|1|2|as': { + action_: 'b=', + nextState: 'b' + }, + 'p': { + action_: 'b=', + nextState: 'bp' + }, + '3|o': { + action_: 'd= kv', + nextState: 'D' + }, + 'q': { + action_: 'd=', + nextState: 'qD' + }, + 'd|D|qd|qD|dq': { + action_: ['output', 'd='], + nextState: 'D' + } + }, + '^a|^\\x{}{}|^\\x{}|^\\x|\'': { + '0|1|2|as': { + action_: 'b=', + nextState: 'b' + }, + 'p': { + action_: 'b=', + nextState: 'bp' + }, + '3|o': { + action_: 'd= kv', + nextState: 'd' + }, + 'q': { + action_: 'd=', + nextState: 'qd' + }, + 'd|qd|D|qD': { + action_: 'd=' + }, + 'dq': { + action_: ['output', 'd='], + nextState: 'd' + } + }, + '_{(state of aggregation)}$': { + 'd|D|q|qd|qD|dq': { + action_: ['output', 'q='], + nextState: 'q' + } + }, + '_{(...)}|_($...$)|_9|_\\x{}{}|_\\x{}|_\\x': { + '0|1|2|as': { + action_: 'p=', + nextState: 'p' + }, + 'b': { + action_: 'p=', + nextState: 'bp' + }, + '3|o': { + action_: 'q=', + nextState: 'q' + }, + 'd|D': { + action_: 'q=', + nextState: 'dq' + }, + 'q|qd|qD|dq': { + action_: ['output', 'q='], + nextState: 'q' + } + }, + '=<>': { + '0|1|2|3|a|as|o|q|d|D|qd|qD|dq': { + action_: [{ + type_: 'output', + option: 2 + }, 'bond'], + nextState: '3' + } + }, + '#': { + '0|1|2|3|a|as|o': { + action_: [{ + type_: 'output', + option: 2 + }, { + type_: 'bond', + option: "#" + }], + nextState: '3' + } + }, + '{}': { + '*': { + action_: { + type_: 'output', + option: 1 + }, + nextState: '1' + } + }, + '{...}': { + '0|1|2|3|a|as|b|p|bp': { + action_: 'o=', + nextState: 'o' + }, + 'o|d|D|q|qd|qD|dq': { + action_: ['output', 'o='], + nextState: 'o' + } + }, + '$...$': { + 'a': { + action_: 'a=' + }, + // 2$n$ + '0|1|2|3|as|b|p|bp|o': { + action_: 'o=', + nextState: 'o' + }, + // not 'amount' + 'as|o': { + action_: 'o=' + }, + 'q|d|D|qd|qD|dq': { + action_: ['output', 'o='], + nextState: 'o' + } + }, + '\\bond{(...)}': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'bond'], + nextState: "3" + } + }, + '\\frac{(...)}': { + '*': { + action_: [{ + type_: 'output', + option: 1 + }, 'frac-output'], + nextState: '3' + } + }, + '\\overset{(...)}': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'overset-output'], + nextState: '3' + } + }, + '\\underset{(...)}': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'underset-output'], + nextState: '3' + } + }, + '\\underbrace{(...)}': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'underbrace-output'], + nextState: '3' + } + }, + '\\color{(...)}{(...)}1|\\color(...){(...)}2': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'color-output'], + nextState: '3' + } + }, + '\\color{(...)}0': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'color0-output'] + } + }, + '\\ce{(...)}': { + '*': { + action_: [{ + type_: 'output', + option: 2 + }, 'ce'], + nextState: '3' + } + }, + '\\,': { + '*': { + action_: [{ + type_: 'output', + option: 1 + }, 'copy'], + nextState: '1' + } + }, + '\\x{}{}|\\x{}|\\x': { + '0|1|2|3|a|as|b|p|bp|o|c0': { + action_: ['o=', 'output'], + nextState: '3' + }, + '*': { + action_: ['output', 'o=', 'output'], + nextState: '3' + } + }, + 'others': { + '*': { + action_: [{ + type_: 'output', + option: 1 + }, 'copy'], + nextState: '3' + } + }, + 'else2': { + 'a': { + action_: 'a to o', + nextState: 'o', + revisit: true + }, + 'as': { + action_: ['output', 'sb=true'], + nextState: '1', + revisit: true + }, + 'r|rt|rd|rdt|rdq': { + action_: ['output'], + nextState: '0', + revisit: true + }, + '*': { + action_: ['output', 'copy'], + nextState: '3' + } + } + }), + actions: { + 'o after d': function oAfterD(buffer, m) { + var ret; + + if ((buffer.d || "").match(/^[0-9]+$/)) { + var tmp = buffer.d; + buffer.d = undefined; + ret = this['output'](buffer); + buffer.b = tmp; + } else { + ret = this['output'](buffer); + } + + mhchemParser.actions['o='](buffer, m); + return ret; + }, + 'd= kv': function dKv(buffer, m) { + buffer.d = m; + buffer.dType = 'kv'; + }, + 'charge or bond': function chargeOrBond(buffer, m) { + if (buffer['beginsWithBond']) { + /** @type {ParserOutput[]} */ + var ret = []; + mhchemParser.concatArray(ret, this['output'](buffer)); + mhchemParser.concatArray(ret, mhchemParser.actions['bond'](buffer, m, "-")); + return ret; + } else { + buffer.d = m; + } + }, + '- after o/d': function afterOD(buffer, m, isAfterD) { + var c1 = mhchemParser.patterns.match_('orbital', buffer.o || ""); + var c2 = mhchemParser.patterns.match_('one lowercase greek letter $', buffer.o || ""); + var c3 = mhchemParser.patterns.match_('one lowercase latin letter $', buffer.o || ""); + var c4 = mhchemParser.patterns.match_('$one lowercase latin letter$ $', buffer.o || ""); + var hyphenFollows = m === "-" && (c1 && c1.remainder === "" || c2 || c3 || c4); + + if (hyphenFollows && !buffer.a && !buffer.b && !buffer.p && !buffer.d && !buffer.q && !c1 && c3) { + buffer.o = '$' + buffer.o + '$'; + } + /** @type {ParserOutput[]} */ + + + var ret = []; + + if (hyphenFollows) { + mhchemParser.concatArray(ret, this['output'](buffer)); + ret.push({ + type_: 'hyphen' + }); + } else { + c1 = mhchemParser.patterns.match_('digits', buffer.d || ""); + + if (isAfterD && c1 && c1.remainder === '') { + mhchemParser.concatArray(ret, mhchemParser.actions['d='](buffer, m)); + mhchemParser.concatArray(ret, this['output'](buffer)); + } else { + mhchemParser.concatArray(ret, this['output'](buffer)); + mhchemParser.concatArray(ret, mhchemParser.actions['bond'](buffer, m, "-")); + } + } + + return ret; + }, + 'a to o': function aToO(buffer) { + buffer.o = buffer.a; + buffer.a = undefined; + }, + 'sb=true': function sbTrue(buffer) { + buffer.sb = true; + }, + 'sb=false': function sbFalse(buffer) { + buffer.sb = false; + }, + 'beginsWithBond=true': function beginsWithBondTrue(buffer) { + buffer['beginsWithBond'] = true; + }, + 'beginsWithBond=false': function beginsWithBondFalse(buffer) { + buffer['beginsWithBond'] = false; + }, + 'parenthesisLevel++': function parenthesisLevel(buffer) { + buffer['parenthesisLevel']++; + }, + 'parenthesisLevel--': function parenthesisLevel(buffer) { + buffer['parenthesisLevel']--; + }, + 'state of aggregation': function stateOfAggregation(buffer, m) { + return { + type_: 'state of aggregation', + p1: mhchemParser.go(m, 'o') + }; + }, + 'comma': function comma(buffer, m) { + var a = m.replace(/\s*$/, ''); + var withSpace = a !== m; + + if (withSpace && buffer['parenthesisLevel'] === 0) { + return { + type_: 'comma enumeration L', + p1: a + }; + } else { + return { + type_: 'comma enumeration M', + p1: a + }; + } + }, + 'output': function output(buffer, m, entityFollows) { + // entityFollows: + // undefined = if we have nothing else to output, also ignore the just read space (buffer.sb) + // 1 = an entity follows, never omit the space if there was one just read before (can only apply to state 1) + // 2 = 1 + the entity can have an amount, so output a\, instead of converting it to o (can only apply to states a|as) + + /** @type {ParserOutput | ParserOutput[]} */ + var ret; + + if (!buffer.r) { + ret = []; + + if (!buffer.a && !buffer.b && !buffer.p && !buffer.o && !buffer.q && !buffer.d && !entityFollows) ; else { + if (buffer.sb) { + ret.push({ + type_: 'entitySkip' + }); + } + + if (!buffer.o && !buffer.q && !buffer.d && !buffer.b && !buffer.p && entityFollows !== 2) { + buffer.o = buffer.a; + buffer.a = undefined; + } else if (!buffer.o && !buffer.q && !buffer.d && (buffer.b || buffer.p)) { + buffer.o = buffer.a; + buffer.d = buffer.b; + buffer.q = buffer.p; + buffer.a = buffer.b = buffer.p = undefined; + } else { + if (buffer.o && buffer.dType === 'kv' && mhchemParser.patterns.match_('d-oxidation$', buffer.d || "")) { + buffer.dType = 'oxidation'; + } else if (buffer.o && buffer.dType === 'kv' && !buffer.q) { + buffer.dType = undefined; + } + } + + ret.push({ + type_: 'chemfive', + a: mhchemParser.go(buffer.a, 'a'), + b: mhchemParser.go(buffer.b, 'bd'), + p: mhchemParser.go(buffer.p, 'pq'), + o: mhchemParser.go(buffer.o, 'o'), + q: mhchemParser.go(buffer.q, 'pq'), + d: mhchemParser.go(buffer.d, buffer.dType === 'oxidation' ? 'oxidation' : 'bd'), + dType: buffer.dType + }); + } + } else { + // r + + /** @type {ParserOutput[]} */ + var rd; + + if (buffer.rdt === 'M') { + rd = mhchemParser.go(buffer.rd, 'tex-math'); + } else if (buffer.rdt === 'T') { + rd = [{ + type_: 'text', + p1: buffer.rd || "" + }]; + } else { + rd = mhchemParser.go(buffer.rd); + } + /** @type {ParserOutput[]} */ + + + var rq; + + if (buffer.rqt === 'M') { + rq = mhchemParser.go(buffer.rq, 'tex-math'); + } else if (buffer.rqt === 'T') { + rq = [{ + type_: 'text', + p1: buffer.rq || "" + }]; + } else { + rq = mhchemParser.go(buffer.rq); + } + + ret = { + type_: 'arrow', + r: buffer.r, + rd: rd, + rq: rq + }; + } + + for (var p in buffer) { + if (p !== 'parenthesisLevel' && p !== 'beginsWithBond') { + delete buffer[p]; + } + } + + return ret; + }, + 'oxidation-output': function oxidationOutput(buffer, m) { + var ret = ["{"]; + mhchemParser.concatArray(ret, mhchemParser.go(m, 'oxidation')); + ret.push("}"); + return ret; + }, + 'frac-output': function fracOutput(buffer, m) { + return { + type_: 'frac-ce', + p1: mhchemParser.go(m[0]), + p2: mhchemParser.go(m[1]) + }; + }, + 'overset-output': function oversetOutput(buffer, m) { + return { + type_: 'overset', + p1: mhchemParser.go(m[0]), + p2: mhchemParser.go(m[1]) + }; + }, + 'underset-output': function undersetOutput(buffer, m) { + return { + type_: 'underset', + p1: mhchemParser.go(m[0]), + p2: mhchemParser.go(m[1]) + }; + }, + 'underbrace-output': function underbraceOutput(buffer, m) { + return { + type_: 'underbrace', + p1: mhchemParser.go(m[0]), + p2: mhchemParser.go(m[1]) + }; + }, + 'color-output': function colorOutput(buffer, m) { + return { + type_: 'color', + color1: m[0], + color2: mhchemParser.go(m[1]) + }; + }, + 'r=': function r(buffer, m) { + buffer.r = m; + }, + 'rdt=': function rdt(buffer, m) { + buffer.rdt = m; + }, + 'rd=': function rd(buffer, m) { + buffer.rd = m; + }, + 'rqt=': function rqt(buffer, m) { + buffer.rqt = m; + }, + 'rq=': function rq(buffer, m) { + buffer.rq = m; + }, + 'operator': function operator(buffer, m, p1) { + return { + type_: 'operator', + kind_: p1 || m + }; + } + } + }, + 'a': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': {} + }, + '1/2$': { + '0': { + action_: '1/2' + } + }, + 'else': { + '0': { + nextState: '1', + revisit: true + } + }, + '$(...)$': { + '*': { + action_: 'tex-math tight', + nextState: '1' + } + }, + ',': { + '*': { + action_: { + type_: 'insert', + option: 'commaDecimal' + } + } + }, + 'else2': { + '*': { + action_: 'copy' + } + } + }), + actions: {} + }, + 'o': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': {} + }, + '1/2$': { + '0': { + action_: '1/2' + } + }, + 'else': { + '0': { + nextState: '1', + revisit: true + } + }, + 'letters': { + '*': { + action_: 'rm' + } + }, + '\\ca': { + '*': { + action_: { + type_: 'insert', + option: 'circa' + } + } + }, + '\\x{}{}|\\x{}|\\x': { + '*': { + action_: 'copy' + } + }, + '${(...)}$|$(...)$': { + '*': { + action_: 'tex-math' + } + }, + '{(...)}': { + '*': { + action_: '{text}' + } + }, + 'else2': { + '*': { + action_: 'copy' + } + } + }), + actions: {} + }, + 'text': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': { + action_: 'output' + } + }, + '{...}': { + '*': { + action_: 'text=' + } + }, + '${(...)}$|$(...)$': { + '*': { + action_: 'tex-math' + } + }, + '\\greek': { + '*': { + action_: ['output', 'rm'] + } + }, + '\\,|\\x{}{}|\\x{}|\\x': { + '*': { + action_: ['output', 'copy'] + } + }, + 'else': { + '*': { + action_: 'text=' + } + } + }), + actions: { + 'output': function output(buffer) { + if (buffer.text_) { + /** @type {ParserOutput} */ + var ret = { + type_: 'text', + p1: buffer.text_ + }; + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + } + } + } + }, + 'pq': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': {} + }, + 'state of aggregation $': { + '*': { + action_: 'state of aggregation' + } + }, + 'i$': { + '0': { + nextState: '!f', + revisit: true + } + }, + '(KV letters),': { + '0': { + action_: 'rm', + nextState: '0' + } + }, + 'formula$': { + '0': { + nextState: 'f', + revisit: true + } + }, + '1/2$': { + '0': { + action_: '1/2' + } + }, + 'else': { + '0': { + nextState: '!f', + revisit: true + } + }, + '${(...)}$|$(...)$': { + '*': { + action_: 'tex-math' + } + }, + '{(...)}': { + '*': { + action_: 'text' + } + }, + 'a-z': { + 'f': { + action_: 'tex-math' + } + }, + 'letters': { + '*': { + action_: 'rm' + } + }, + '-9.,9': { + '*': { + action_: '9,9' + } + }, + ',': { + '*': { + action_: { + type_: 'insert+p1', + option: 'comma enumeration S' + } + } + }, + '\\color{(...)}{(...)}1|\\color(...){(...)}2': { + '*': { + action_: 'color-output' + } + }, + '\\color{(...)}0': { + '*': { + action_: 'color0-output' + } + }, + '\\ce{(...)}': { + '*': { + action_: 'ce' + } + }, + '\\,|\\x{}{}|\\x{}|\\x': { + '*': { + action_: 'copy' + } + }, + 'else2': { + '*': { + action_: 'copy' + } + } + }), + actions: { + 'state of aggregation': function stateOfAggregation(buffer, m) { + return { + type_: 'state of aggregation subscript', + p1: mhchemParser.go(m, 'o') + }; + }, + 'color-output': function colorOutput(buffer, m) { + return { + type_: 'color', + color1: m[0], + color2: mhchemParser.go(m[1], 'pq') + }; + } + } + }, + 'bd': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': {} + }, + 'x$': { + '0': { + nextState: '!f', + revisit: true + } + }, + 'formula$': { + '0': { + nextState: 'f', + revisit: true + } + }, + 'else': { + '0': { + nextState: '!f', + revisit: true + } + }, + '-9.,9 no missing 0': { + '*': { + action_: '9,9' + } + }, + '.': { + '*': { + action_: { + type_: 'insert', + option: 'electron dot' + } + } + }, + 'a-z': { + 'f': { + action_: 'tex-math' + } + }, + 'x': { + '*': { + action_: { + type_: 'insert', + option: 'KV x' + } + } + }, + 'letters': { + '*': { + action_: 'rm' + } + }, + '\'': { + '*': { + action_: { + type_: 'insert', + option: 'prime' + } + } + }, + '${(...)}$|$(...)$': { + '*': { + action_: 'tex-math' + } + }, + '{(...)}': { + '*': { + action_: 'text' + } + }, + '\\color{(...)}{(...)}1|\\color(...){(...)}2': { + '*': { + action_: 'color-output' + } + }, + '\\color{(...)}0': { + '*': { + action_: 'color0-output' + } + }, + '\\ce{(...)}': { + '*': { + action_: 'ce' + } + }, + '\\,|\\x{}{}|\\x{}|\\x': { + '*': { + action_: 'copy' + } + }, + 'else2': { + '*': { + action_: 'copy' + } + } + }), + actions: { + 'color-output': function colorOutput(buffer, m) { + return { + type_: 'color', + color1: m[0], + color2: mhchemParser.go(m[1], 'bd') + }; + } + } + }, + 'oxidation': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': {} + }, + 'roman numeral': { + '*': { + action_: 'roman-numeral' + } + }, + '${(...)}$|$(...)$': { + '*': { + action_: 'tex-math' + } + }, + 'else': { + '*': { + action_: 'copy' + } + } + }), + actions: { + 'roman-numeral': function romanNumeral(buffer, m) { + return { + type_: 'roman numeral', + p1: m || "" + }; + } + } + }, + 'tex-math': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': { + action_: 'output' + } + }, + '\\ce{(...)}': { + '*': { + action_: ['output', 'ce'] + } + }, + '{...}|\\,|\\x{}{}|\\x{}|\\x': { + '*': { + action_: 'o=' + } + }, + 'else': { + '*': { + action_: 'o=' + } + } + }), + actions: { + 'output': function output(buffer) { + if (buffer.o) { + /** @type {ParserOutput} */ + var ret = { + type_: 'tex-math', + p1: buffer.o + }; + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + } + } + } + }, + 'tex-math tight': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': { + action_: 'output' + } + }, + '\\ce{(...)}': { + '*': { + action_: ['output', 'ce'] + } + }, + '{...}|\\,|\\x{}{}|\\x{}|\\x': { + '*': { + action_: 'o=' + } + }, + '-|+': { + '*': { + action_: 'tight operator' + } + }, + 'else': { + '*': { + action_: 'o=' + } + } + }), + actions: { + 'tight operator': function tightOperator(buffer, m) { + buffer.o = (buffer.o || "") + "{" + m + "}"; + }, + 'output': function output(buffer) { + if (buffer.o) { + /** @type {ParserOutput} */ + var ret = { + type_: 'tex-math', + p1: buffer.o + }; + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + } + } + } + }, + '9,9': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': {} + }, + ',': { + '*': { + action_: 'comma' + } + }, + 'else': { + '*': { + action_: 'copy' + } + } + }), + actions: { + 'comma': function comma() { + return { + type_: 'commaDecimal' + }; + } + } + }, + //#endregion + // + // \pu state machines + // + //#region pu + 'pu': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': { + action_: 'output' + } + }, + 'space$': { + '*': { + action_: ['output', 'space'] + } + }, + '{[(|)]}': { + '0|a': { + action_: 'copy' + } + }, + '(-)(9)^(-9)': { + '0': { + action_: 'number^', + nextState: 'a' + } + }, + '(-)(9.,9)(e)(99)': { + '0': { + action_: 'enumber', + nextState: 'a' + } + }, + 'space': { + '0|a': {} + }, + 'pm-operator': { + '0|a': { + action_: { + type_: 'operator', + option: '\\pm' + }, + nextState: '0' + } + }, + 'operator': { + '0|a': { + action_: 'copy', + nextState: '0' + } + }, + '//': { + 'd': { + action_: 'o=', + nextState: '/' + } + }, + '/': { + 'd': { + action_: 'o=', + nextState: '/' + } + }, + '{...}|else': { + '0|d': { + action_: 'd=', + nextState: 'd' + }, + 'a': { + action_: ['space', 'd='], + nextState: 'd' + }, + '/|q': { + action_: 'q=', + nextState: 'q' + } + } + }), + actions: { + 'enumber': function enumber(buffer, m) { + /** @type {ParserOutput[]} */ + var ret = []; + + if (m[0] === "+-" || m[0] === "+/-") { + ret.push("\\pm "); + } else if (m[0]) { + ret.push(m[0]); + } + + if (m[1]) { + mhchemParser.concatArray(ret, mhchemParser.go(m[1], 'pu-9,9')); + + if (m[2]) { + if (m[2].match(/[,.]/)) { + mhchemParser.concatArray(ret, mhchemParser.go(m[2], 'pu-9,9')); + } else { + ret.push(m[2]); + } + } + + m[3] = m[4] || m[3]; + + if (m[3]) { + m[3] = m[3].trim(); + + if (m[3] === "e" || m[3].substr(0, 1) === "*") { + ret.push({ + type_: 'cdot' + }); + } else { + ret.push({ + type_: 'times' + }); + } + } + } + + if (m[3]) { + ret.push("10^{" + m[5] + "}"); + } + + return ret; + }, + 'number^': function number(buffer, m) { + /** @type {ParserOutput[]} */ + var ret = []; + + if (m[0] === "+-" || m[0] === "+/-") { + ret.push("\\pm "); + } else if (m[0]) { + ret.push(m[0]); + } + + mhchemParser.concatArray(ret, mhchemParser.go(m[1], 'pu-9,9')); + ret.push("^{" + m[2] + "}"); + return ret; + }, + 'operator': function operator(buffer, m, p1) { + return { + type_: 'operator', + kind_: p1 || m + }; + }, + 'space': function space() { + return { + type_: 'pu-space-1' + }; + }, + 'output': function output(buffer) { + /** @type {ParserOutput | ParserOutput[]} */ + var ret; + var md = mhchemParser.patterns.match_('{(...)}', buffer.d || ""); + + if (md && md.remainder === '') { + buffer.d = md.match_; + } + + var mq = mhchemParser.patterns.match_('{(...)}', buffer.q || ""); + + if (mq && mq.remainder === '') { + buffer.q = mq.match_; + } + + if (buffer.d) { + buffer.d = buffer.d.replace(/\u00B0C|\^oC|\^{o}C/g, "{}^{\\circ}C"); + buffer.d = buffer.d.replace(/\u00B0F|\^oF|\^{o}F/g, "{}^{\\circ}F"); + } + + if (buffer.q) { + // fraction + buffer.q = buffer.q.replace(/\u00B0C|\^oC|\^{o}C/g, "{}^{\\circ}C"); + buffer.q = buffer.q.replace(/\u00B0F|\^oF|\^{o}F/g, "{}^{\\circ}F"); + var b5 = { + d: mhchemParser.go(buffer.d, 'pu'), + q: mhchemParser.go(buffer.q, 'pu') + }; + + if (buffer.o === '//') { + ret = { + type_: 'pu-frac', + p1: b5.d, + p2: b5.q + }; + } else { + ret = b5.d; + + if (b5.d.length > 1 || b5.q.length > 1) { + ret.push({ + type_: ' / ' + }); + } else { + ret.push({ + type_: '/' + }); + } + + mhchemParser.concatArray(ret, b5.q); + } + } else { + // no fraction + ret = mhchemParser.go(buffer.d, 'pu-2'); + } + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + } + } + }, + 'pu-2': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '*': { + action_: 'output' + } + }, + '*': { + '*': { + action_: ['output', 'cdot'], + nextState: '0' + } + }, + '\\x': { + '*': { + action_: 'rm=' + } + }, + 'space': { + '*': { + action_: ['output', 'space'], + nextState: '0' + } + }, + '^{(...)}|^(-1)': { + '1': { + action_: '^(-1)' + } + }, + '-9.,9': { + '0': { + action_: 'rm=', + nextState: '0' + }, + '1': { + action_: '^(-1)', + nextState: '0' + } + }, + '{...}|else': { + '*': { + action_: 'rm=', + nextState: '1' + } + } + }), + actions: { + 'cdot': function cdot() { + return { + type_: 'tight cdot' + }; + }, + '^(-1)': function _(buffer, m) { + buffer.rm += "^{" + m + "}"; + }, + 'space': function space() { + return { + type_: 'pu-space-2' + }; + }, + 'output': function output(buffer) { + /** @type {ParserOutput | ParserOutput[]} */ + var ret = []; + + if (buffer.rm) { + var mrm = mhchemParser.patterns.match_('{(...)}', buffer.rm || ""); + + if (mrm && mrm.remainder === '') { + ret = mhchemParser.go(mrm.match_, 'pu'); + } else { + ret = { + type_: 'rm', + p1: buffer.rm + }; + } + } + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + } + } + }, + 'pu-9,9': { + transitions: mhchemParser.createTransitions({ + 'empty': { + '0': { + action_: 'output-0' + }, + 'o': { + action_: 'output-o' + } + }, + ',': { + '0': { + action_: ['output-0', 'comma'], + nextState: 'o' + } + }, + '.': { + '0': { + action_: ['output-0', 'copy'], + nextState: 'o' + } + }, + 'else': { + '*': { + action_: 'text=' + } + } + }), + actions: { + 'comma': function comma() { + return { + type_: 'commaDecimal' + }; + }, + 'output-0': function output0(buffer) { + /** @type {ParserOutput[]} */ + var ret = []; + buffer.text_ = buffer.text_ || ""; + + if (buffer.text_.length > 4) { + var a = buffer.text_.length % 3; + + if (a === 0) { + a = 3; + } + + for (var i = buffer.text_.length - 3; i > 0; i -= 3) { + ret.push(buffer.text_.substr(i, 3)); + ret.push({ + type_: '1000 separator' + }); + } + + ret.push(buffer.text_.substr(0, a)); + ret.reverse(); + } else { + ret.push(buffer.text_); + } + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + }, + 'output-o': function outputO(buffer) { + /** @type {ParserOutput[]} */ + var ret = []; + buffer.text_ = buffer.text_ || ""; + + if (buffer.text_.length > 4) { + var a = buffer.text_.length - 3; + + for (var i = 0; i < a; i += 3) { + ret.push(buffer.text_.substr(i, 3)); + ret.push({ + type_: '1000 separator' + }); + } + + ret.push(buffer.text_.substr(i)); + } else { + ret.push(buffer.text_); + } + + for (var p in buffer) { + delete buffer[p]; + } + + return ret; + } + } + } //#endregion + +}; // +// texify: Take MhchemParser output and convert it to TeX +// + +/** @type {Texify} */ + +var texify = { + go: function go(input, isInner) { + // (recursive, max 4 levels) + if (!input) { + return ""; + } + + var res = ""; + var cee = false; + + for (var i = 0; i < input.length; i++) { + var inputi = input[i]; + + if (typeof inputi === "string") { + res += inputi; + } else { + res += texify._go2(inputi); + + if (inputi.type_ === '1st-level escape') { + cee = true; + } + } + } + + if (!isInner && !cee && res) { + res = "{" + res + "}"; + } + + return res; + }, + _goInner: function _goInner(input) { + if (!input) { + return input; + } + + return texify.go(input, true); + }, + _go2: function _go2(buf) { + /** @type {undefined | string} */ + var res; + + switch (buf.type_) { + case 'chemfive': + res = ""; + var b5 = { + a: texify._goInner(buf.a), + b: texify._goInner(buf.b), + p: texify._goInner(buf.p), + o: texify._goInner(buf.o), + q: texify._goInner(buf.q), + d: texify._goInner(buf.d) + }; // + // a + // + + if (b5.a) { + if (b5.a.match(/^[+\-]/)) { + b5.a = "{" + b5.a + "}"; + } + + res += b5.a + "\\,"; + } // + // b and p + // + + + if (b5.b || b5.p) { + res += "{\\vphantom{X}}"; + res += "^{\\hphantom{" + (b5.b || "") + "}}_{\\hphantom{" + (b5.p || "") + "}}"; + res += "{\\vphantom{X}}"; + res += "^{\\smash[t]{\\vphantom{2}}\\mathllap{" + (b5.b || "") + "}}"; + res += "_{\\vphantom{2}\\mathllap{\\smash[t]{" + (b5.p || "") + "}}}"; + } // + // o + // + + + if (b5.o) { + if (b5.o.match(/^[+\-]/)) { + b5.o = "{" + b5.o + "}"; + } + + res += b5.o; + } // + // q and d + // + + + if (buf.dType === 'kv') { + if (b5.d || b5.q) { + res += "{\\vphantom{X}}"; + } + + if (b5.d) { + res += "^{" + b5.d + "}"; + } + + if (b5.q) { + res += "_{\\smash[t]{" + b5.q + "}}"; + } + } else if (buf.dType === 'oxidation') { + if (b5.d) { + res += "{\\vphantom{X}}"; + res += "^{" + b5.d + "}"; + } + + if (b5.q) { + res += "{\\vphantom{X}}"; + res += "_{\\smash[t]{" + b5.q + "}}"; + } + } else { + if (b5.q) { + res += "{\\vphantom{X}}"; + res += "_{\\smash[t]{" + b5.q + "}}"; + } + + if (b5.d) { + res += "{\\vphantom{X}}"; + res += "^{" + b5.d + "}"; + } + } + + break; + + case 'rm': + res = "\\mathrm{" + buf.p1 + "}"; + break; + + case 'text': + if (buf.p1.match(/[\^_]/)) { + buf.p1 = buf.p1.replace(" ", "~").replace("-", "\\text{-}"); + res = "\\mathrm{" + buf.p1 + "}"; + } else { + res = "\\text{" + buf.p1 + "}"; + } + + break; + + case 'roman numeral': + res = "\\mathrm{" + buf.p1 + "}"; + break; + + case 'state of aggregation': + res = "\\mskip2mu " + texify._goInner(buf.p1); + break; + + case 'state of aggregation subscript': + res = "\\mskip1mu " + texify._goInner(buf.p1); + break; + + case 'bond': + res = texify._getBond(buf.kind_); + + if (!res) { + throw ["MhchemErrorBond", "mhchem Error. Unknown bond type (" + buf.kind_ + ")"]; + } + + break; + + case 'frac': + var c = "\\frac{" + buf.p1 + "}{" + buf.p2 + "}"; + res = "\\mathchoice{\\textstyle" + c + "}{" + c + "}{" + c + "}{" + c + "}"; + break; + + case 'pu-frac': + var d = "\\frac{" + texify._goInner(buf.p1) + "}{" + texify._goInner(buf.p2) + "}"; + res = "\\mathchoice{\\textstyle" + d + "}{" + d + "}{" + d + "}{" + d + "}"; + break; + + case 'tex-math': + res = buf.p1 + " "; + break; + + case 'frac-ce': + res = "\\frac{" + texify._goInner(buf.p1) + "}{" + texify._goInner(buf.p2) + "}"; + break; + + case 'overset': + res = "\\overset{" + texify._goInner(buf.p1) + "}{" + texify._goInner(buf.p2) + "}"; + break; + + case 'underset': + res = "\\underset{" + texify._goInner(buf.p1) + "}{" + texify._goInner(buf.p2) + "}"; + break; + + case 'underbrace': + res = "\\underbrace{" + texify._goInner(buf.p1) + "}_{" + texify._goInner(buf.p2) + "}"; + break; + + case 'color': + res = "{\\color{" + buf.color1 + "}{" + texify._goInner(buf.color2) + "}}"; + break; + + case 'color0': + res = "\\color{" + buf.color + "}"; + break; + + case 'arrow': + var b6 = { + rd: texify._goInner(buf.rd), + rq: texify._goInner(buf.rq) + }; + + var arrow = "\\x" + texify._getArrow(buf.r); + + if (b6.rq) { + arrow += "[{" + b6.rq + "}]"; + } + + if (b6.rd) { + arrow += "{" + b6.rd + "}"; + } else { + arrow += "{}"; + } + + res = arrow; + break; + + case 'operator': + res = texify._getOperator(buf.kind_); + break; + + case '1st-level escape': + res = buf.p1 + " "; // &, \\\\, \\hlin + + break; + + case 'space': + res = " "; + break; + + case 'entitySkip': + res = "~"; + break; + + case 'pu-space-1': + res = "~"; + break; + + case 'pu-space-2': + res = "\\mkern3mu "; + break; + + case '1000 separator': + res = "\\mkern2mu "; + break; + + case 'commaDecimal': + res = "{,}"; + break; + + case 'comma enumeration L': + res = "{" + buf.p1 + "}\\mkern6mu "; + break; + + case 'comma enumeration M': + res = "{" + buf.p1 + "}\\mkern3mu "; + break; + + case 'comma enumeration S': + res = "{" + buf.p1 + "}\\mkern1mu "; + break; + + case 'hyphen': + res = "\\text{-}"; + break; + + case 'addition compound': + res = "\\,{\\cdot}\\,"; + break; + + case 'electron dot': + res = "\\mkern1mu \\bullet\\mkern1mu "; + break; + + case 'KV x': + res = "{\\times}"; + break; + + case 'prime': + res = "\\prime "; + break; + + case 'cdot': + res = "\\cdot "; + break; + + case 'tight cdot': + res = "\\mkern1mu{\\cdot}\\mkern1mu "; + break; + + case 'times': + res = "\\times "; + break; + + case 'circa': + res = "{\\sim}"; + break; + + case '^': + res = "uparrow"; + break; + + case 'v': + res = "downarrow"; + break; + + case 'ellipsis': + res = "\\ldots "; + break; + + case '/': + res = "/"; + break; + + case ' / ': + res = "\\,/\\,"; + break; + + default: + throw ["MhchemBugT", "mhchem bug T. Please report."]; + // Missing texify rule or unknown MhchemParser output + } + return res; + }, + _getArrow: function _getArrow(a) { + switch (a) { + case "->": + return "rightarrow"; + + case "\u2192": + return "rightarrow"; + + case "\u27F6": + return "rightarrow"; + + case "<-": + return "leftarrow"; + + case "<->": + return "leftrightarrow"; + + case "<-->": + return "rightleftarrows"; + + case "<=>": + return "rightleftharpoons"; + + case "\u21CC": + return "rightleftharpoons"; + + case "<=>>": + return "rightequilibrium"; + + case "<<=>": + return "leftequilibrium"; + + default: + throw ["MhchemBugT", "mhchem bug T. Please report."]; + } + }, + _getBond: function _getBond(a) { + switch (a) { + case "-": + return "{-}"; + + case "1": + return "{-}"; + + case "=": + return "{=}"; + + case "2": + return "{=}"; + + case "#": + return "{\\equiv}"; + + case "3": + return "{\\equiv}"; + + case "~": + return "{\\tripledash}"; + + case "~-": + return "{\\mathrlap{\\raisebox{-.1em}{$-$}}\\raisebox{.1em}{$\\tripledash$}}"; + + case "~=": + return "{\\mathrlap{\\raisebox{-.2em}{$-$}}\\mathrlap{\\raisebox{.2em}{$\\tripledash$}}-}"; + + case "~--": + return "{\\mathrlap{\\raisebox{-.2em}{$-$}}\\mathrlap{\\raisebox{.2em}{$\\tripledash$}}-}"; + + case "-~-": + return "{\\mathrlap{\\raisebox{-.2em}{$-$}}\\mathrlap{\\raisebox{.2em}{$-$}}\\tripledash}"; + + case "...": + return "{{\\cdot}{\\cdot}{\\cdot}}"; + + case "....": + return "{{\\cdot}{\\cdot}{\\cdot}{\\cdot}}"; + + case "->": + return "{\\rightarrow}"; + + case "<-": + return "{\\leftarrow}"; + + case "<": + return "{<}"; + + case ">": + return "{>}"; + + default: + throw ["MhchemBugT", "mhchem bug T. Please report."]; + } + }, + _getOperator: function _getOperator(a) { + switch (a) { + case "+": + return " {}+{} "; + + case "-": + return " {}-{} "; + + case "=": + return " {}={} "; + + case "<": + return " {}<{} "; + + case ">": + return " {}>{} "; + + case "<<": + return " {}\\ll{} "; + + case ">>": + return " {}\\gg{} "; + + case "\\pm": + return " {}\\pm{} "; + + case "\\approx": + return " {}\\approx{} "; + + case "$\\approx$": + return " {}\\approx{} "; + + case "v": + return " \\downarrow{} "; + + case "(v)": + return " \\downarrow{} "; + + case "^": + return " \\uparrow{} "; + + case "(^)": + return " \\uparrow{} "; + + default: + throw ["MhchemBugT", "mhchem bug T. Please report."]; + } + } +}; // diff --git a/frontend/node_modules/katex/dist/contrib/render-a11y-string.js b/frontend/node_modules/katex/dist/contrib/render-a11y-string.js new file mode 100644 index 0000000..dc804c7 --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/render-a11y-string.js @@ -0,0 +1,887 @@ +(function webpackUniversalModuleDefinition(root, factory) { + if(typeof exports === 'object' && typeof module === 'object') + module.exports = factory(require("katex")); + else if(typeof define === 'function' && define.amd) + define(["katex"], factory); + else { + var a = typeof exports === 'object' ? factory(require("katex")) : factory(root["katex"]); + for(var i in a) (typeof exports === 'object' ? exports : root)[i] = a[i]; + } +})((typeof self !== 'undefined' ? self : this), function(__WEBPACK_EXTERNAL_MODULE__757__) { +return /******/ (function() { // webpackBootstrap +/******/ "use strict"; +/******/ var __webpack_modules__ = ({ + +/***/ 757: +/***/ (function(module) { + +module.exports = __WEBPACK_EXTERNAL_MODULE__757__; + +/***/ }) + +/******/ }); +/************************************************************************/ +/******/ // The module cache +/******/ var __webpack_module_cache__ = {}; +/******/ +/******/ // The require function +/******/ function __webpack_require__(moduleId) { +/******/ // Check if module is in cache +/******/ var cachedModule = __webpack_module_cache__[moduleId]; +/******/ if (cachedModule !== undefined) { +/******/ return cachedModule.exports; +/******/ } +/******/ // Create a new module (and put it into the cache) +/******/ var module = __webpack_module_cache__[moduleId] = { +/******/ // no module.id needed +/******/ // no module.loaded needed +/******/ exports: {} +/******/ }; +/******/ +/******/ // Execute the module function +/******/ __webpack_modules__[moduleId](module, module.exports, __webpack_require__); +/******/ +/******/ // Return the exports of the module +/******/ return module.exports; +/******/ } +/******/ +/************************************************************************/ +/******/ /* webpack/runtime/compat get default export */ +/******/ !function() { +/******/ // getDefaultExport function for compatibility with non-harmony modules +/******/ __webpack_require__.n = function(module) { +/******/ var getter = module && module.__esModule ? +/******/ function() { return module['default']; } : +/******/ function() { return module; }; +/******/ __webpack_require__.d(getter, { a: getter }); +/******/ return getter; +/******/ }; +/******/ }(); +/******/ +/******/ /* webpack/runtime/define property getters */ +/******/ !function() { +/******/ // define getter functions for harmony exports +/******/ __webpack_require__.d = function(exports, definition) { +/******/ for(var key in definition) { +/******/ if(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) { +/******/ Object.defineProperty(exports, key, { enumerable: true, get: definition[key] }); +/******/ } +/******/ } +/******/ }; +/******/ }(); +/******/ +/******/ /* webpack/runtime/hasOwnProperty shorthand */ +/******/ !function() { +/******/ __webpack_require__.o = function(obj, prop) { return Object.prototype.hasOwnProperty.call(obj, prop); } +/******/ }(); +/******/ +/************************************************************************/ +var __webpack_exports__ = {}; +/* harmony import */ var katex__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(757); +/* harmony import */ var katex__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(katex__WEBPACK_IMPORTED_MODULE_0__); +/** + * renderA11yString returns a readable string. + * + * In some cases the string will have the proper semantic math + * meaning,: + * renderA11yString("\\frac{1}{2}"") + * -> "start fraction, 1, divided by, 2, end fraction" + * + * However, other cases do not: + * renderA11yString("f(x) = x^2") + * -> "f, left parenthesis, x, right parenthesis, equals, x, squared" + * + * The commas in the string aim to increase ease of understanding + * when read by a screenreader. + */ +// NOTE: since we're importing types here these files won't actually be +// included in the build. +// $FlowIgnore: we import the types directly anyways + +const stringMap = { + "(": "left parenthesis", + ")": "right parenthesis", + "[": "open bracket", + "]": "close bracket", + "\\{": "left brace", + "\\}": "right brace", + "\\lvert": "open vertical bar", + "\\rvert": "close vertical bar", + "|": "vertical bar", + "\\uparrow": "up arrow", + "\\Uparrow": "up arrow", + "\\downarrow": "down arrow", + "\\Downarrow": "down arrow", + "\\updownarrow": "up down arrow", + "\\leftarrow": "left arrow", + "\\Leftarrow": "left arrow", + "\\rightarrow": "right arrow", + "\\Rightarrow": "right arrow", + "\\langle": "open angle", + "\\rangle": "close angle", + "\\lfloor": "open floor", + "\\rfloor": "close floor", + "\\int": "integral", + "\\intop": "integral", + "\\lim": "limit", + "\\ln": "natural log", + "\\log": "log", + "\\sin": "sine", + "\\cos": "cosine", + "\\tan": "tangent", + "\\cot": "cotangent", + "\\sum": "sum", + "/": "slash", + ",": "comma", + ".": "point", + "-": "negative", + "+": "plus", + "~": "tilde", + ":": "colon", + "?": "question mark", + "'": "apostrophe", + "\\%": "percent", + " ": "space", + "\\ ": "space", + "\\$": "dollar sign", + "\\angle": "angle", + "\\degree": "degree", + "\\circ": "circle", + "\\vec": "vector", + "\\triangle": "triangle", + "\\pi": "pi", + "\\prime": "prime", + "\\infty": "infinity", + "\\alpha": "alpha", + "\\beta": "beta", + "\\gamma": "gamma", + "\\omega": "omega", + "\\theta": "theta", + "\\sigma": "sigma", + "\\lambda": "lambda", + "\\tau": "tau", + "\\Delta": "delta", + "\\delta": "delta", + "\\mu": "mu", + "\\rho": "rho", + "\\nabla": "del", + "\\ell": "ell", + "\\ldots": "dots", + // TODO: add entries for all accents + "\\hat": "hat", + "\\acute": "acute" +}; +const powerMap = { + "prime": "prime", + "degree": "degrees", + "circle": "degrees", + "2": "squared", + "3": "cubed" +}; +const openMap = { + "|": "open vertical bar", + ".": "" +}; +const closeMap = { + "|": "close vertical bar", + ".": "" +}; +const binMap = { + "+": "plus", + "-": "minus", + "\\pm": "plus minus", + "\\cdot": "dot", + "*": "times", + "/": "divided by", + "\\times": "times", + "\\div": "divided by", + "\\circ": "circle", + "\\bullet": "bullet" +}; +const relMap = { + "=": "equals", + "\\approx": "approximately equals", + "≠": "does not equal", + "\\geq": "is greater than or equal to", + "\\ge": "is greater than or equal to", + "\\leq": "is less than or equal to", + "\\le": "is less than or equal to", + ">": "is greater than", + "<": "is less than", + "\\leftarrow": "left arrow", + "\\Leftarrow": "left arrow", + "\\rightarrow": "right arrow", + "\\Rightarrow": "right arrow", + ":": "colon" +}; +const accentUnderMap = { + "\\underleftarrow": "left arrow", + "\\underrightarrow": "right arrow", + "\\underleftrightarrow": "left-right arrow", + "\\undergroup": "group", + "\\underlinesegment": "line segment", + "\\utilde": "tilde" +}; + +const buildString = (str, type, a11yStrings) => { + if (!str) { + return; + } + + let ret; + + if (type === "open") { + ret = str in openMap ? openMap[str] : stringMap[str] || str; + } else if (type === "close") { + ret = str in closeMap ? closeMap[str] : stringMap[str] || str; + } else if (type === "bin") { + ret = binMap[str] || str; + } else if (type === "rel") { + ret = relMap[str] || str; + } else { + ret = stringMap[str] || str; + } // If the text to add is a number and there is already a string + // in the list and the last string is a number then we should + // combine them into a single number + + + if (/^\d+$/.test(ret) && a11yStrings.length > 0 && // TODO(kevinb): check that the last item in a11yStrings is a string + // I think we might be able to drop the nested arrays, which would make + // this easier to type + // $FlowFixMe + /^\d+$/.test(a11yStrings[a11yStrings.length - 1])) { + a11yStrings[a11yStrings.length - 1] += ret; + } else if (ret) { + a11yStrings.push(ret); + } +}; + +const buildRegion = (a11yStrings, callback) => { + const regionStrings = []; + a11yStrings.push(regionStrings); + callback(regionStrings); +}; + +const handleObject = (tree, a11yStrings, atomType) => { + // Everything else is assumed to be an object... + switch (tree.type) { + case "accent": + { + buildRegion(a11yStrings, a11yStrings => { + buildA11yStrings(tree.base, a11yStrings, atomType); + a11yStrings.push("with"); + buildString(tree.label, "normal", a11yStrings); + a11yStrings.push("on top"); + }); + break; + } + + case "accentUnder": + { + buildRegion(a11yStrings, a11yStrings => { + buildA11yStrings(tree.base, a11yStrings, atomType); + a11yStrings.push("with"); + buildString(accentUnderMap[tree.label], "normal", a11yStrings); + a11yStrings.push("underneath"); + }); + break; + } + + case "accent-token": + { + // Used internally by accent symbols. + break; + } + + case "atom": + { + const { + text + } = tree; + + switch (tree.family) { + case "bin": + { + buildString(text, "bin", a11yStrings); + break; + } + + case "close": + { + buildString(text, "close", a11yStrings); + break; + } + // TODO(kevinb): figure out what should be done for inner + + case "inner": + { + buildString(tree.text, "inner", a11yStrings); + break; + } + + case "open": + { + buildString(text, "open", a11yStrings); + break; + } + + case "punct": + { + buildString(text, "punct", a11yStrings); + break; + } + + case "rel": + { + buildString(text, "rel", a11yStrings); + break; + } + + default: + { + tree.family; + throw new Error("\"" + tree.family + "\" is not a valid atom type"); + } + } + + break; + } + + case "color": + { + const color = tree.color.replace(/katex-/, ""); + buildRegion(a11yStrings, regionStrings => { + regionStrings.push("start color " + color); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end color " + color); + }); + break; + } + + case "color-token": + { + // Used by \color, \colorbox, and \fcolorbox but not directly rendered. + // It's a leaf node and has no children so just break. + break; + } + + case "delimsizing": + { + if (tree.delim && tree.delim !== ".") { + buildString(tree.delim, "normal", a11yStrings); + } + + break; + } + + case "genfrac": + { + buildRegion(a11yStrings, regionStrings => { + // genfrac can have unbalanced delimiters + const { + leftDelim, + rightDelim + } = tree; // NOTE: Not sure if this is a safe assumption + // hasBarLine true -> fraction, false -> binomial + + if (tree.hasBarLine) { + regionStrings.push("start fraction"); + leftDelim && buildString(leftDelim, "open", regionStrings); + buildA11yStrings(tree.numer, regionStrings, atomType); + regionStrings.push("divided by"); + buildA11yStrings(tree.denom, regionStrings, atomType); + rightDelim && buildString(rightDelim, "close", regionStrings); + regionStrings.push("end fraction"); + } else { + regionStrings.push("start binomial"); + leftDelim && buildString(leftDelim, "open", regionStrings); + buildA11yStrings(tree.numer, regionStrings, atomType); + regionStrings.push("over"); + buildA11yStrings(tree.denom, regionStrings, atomType); + rightDelim && buildString(rightDelim, "close", regionStrings); + regionStrings.push("end binomial"); + } + }); + break; + } + + case "hbox": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "kern": + { + // No op: we don't attempt to present kerning information + // to the screen reader. + break; + } + + case "leftright": + { + buildRegion(a11yStrings, regionStrings => { + buildString(tree.left, "open", regionStrings); + buildA11yStrings(tree.body, regionStrings, atomType); + buildString(tree.right, "close", regionStrings); + }); + break; + } + + case "leftright-right": + { + // TODO: double check that this is a no-op + break; + } + + case "lap": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "mathord": + { + buildString(tree.text, "normal", a11yStrings); + break; + } + + case "op": + { + const { + body, + name + } = tree; + + if (body) { + buildA11yStrings(body, a11yStrings, atomType); + } else if (name) { + buildString(name, "normal", a11yStrings); + } + + break; + } + + case "op-token": + { + // Used internally by operator symbols. + buildString(tree.text, atomType, a11yStrings); + break; + } + + case "ordgroup": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "overline": + { + buildRegion(a11yStrings, function (a11yStrings) { + a11yStrings.push("start overline"); + buildA11yStrings(tree.body, a11yStrings, atomType); + a11yStrings.push("end overline"); + }); + break; + } + + case "pmb": + { + a11yStrings.push("bold"); + break; + } + + case "phantom": + { + a11yStrings.push("empty space"); + break; + } + + case "raisebox": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "rule": + { + a11yStrings.push("rectangle"); + break; + } + + case "sizing": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "spacing": + { + a11yStrings.push("space"); + break; + } + + case "styling": + { + // We ignore the styling and just pass through the contents + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "sqrt": + { + buildRegion(a11yStrings, regionStrings => { + const { + body, + index + } = tree; + + if (index) { + const indexString = flatten(buildA11yStrings(index, [], atomType)).join(","); + + if (indexString === "3") { + regionStrings.push("cube root of"); + buildA11yStrings(body, regionStrings, atomType); + regionStrings.push("end cube root"); + return; + } + + regionStrings.push("root"); + regionStrings.push("start index"); + buildA11yStrings(index, regionStrings, atomType); + regionStrings.push("end index"); + return; + } + + regionStrings.push("square root of"); + buildA11yStrings(body, regionStrings, atomType); + regionStrings.push("end square root"); + }); + break; + } + + case "supsub": + { + const { + base, + sub, + sup + } = tree; + let isLog = false; + + if (base) { + buildA11yStrings(base, a11yStrings, atomType); + isLog = base.type === "op" && base.name === "\\log"; + } + + if (sub) { + const regionName = isLog ? "base" : "subscript"; + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start " + regionName); + buildA11yStrings(sub, regionStrings, atomType); + regionStrings.push("end " + regionName); + }); + } + + if (sup) { + buildRegion(a11yStrings, function (regionStrings) { + const supString = flatten(buildA11yStrings(sup, [], atomType)).join(","); + + if (supString in powerMap) { + regionStrings.push(powerMap[supString]); + return; + } + + regionStrings.push("start superscript"); + buildA11yStrings(sup, regionStrings, atomType); + regionStrings.push("end superscript"); + }); + } + + break; + } + + case "text": + { + // TODO: handle other fonts + if (tree.font === "\\textbf") { + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start bold text"); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end bold text"); + }); + break; + } + + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start text"); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end text"); + }); + break; + } + + case "textord": + { + buildString(tree.text, atomType, a11yStrings); + break; + } + + case "smash": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "enclose": + { + // TODO: create a map for these. + // TODO: differentiate between a body with a single atom, e.g. + // "cancel a" instead of "start cancel, a, end cancel" + if (/cancel/.test(tree.label)) { + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start cancel"); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end cancel"); + }); + break; + } else if (/box/.test(tree.label)) { + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start box"); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end box"); + }); + break; + } else if (/sout/.test(tree.label)) { + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start strikeout"); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end strikeout"); + }); + break; + } else if (/phase/.test(tree.label)) { + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start phase angle"); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end phase angle"); + }); + break; + } + + throw new Error("KaTeX-a11y: enclose node with " + tree.label + " not supported yet"); + } + + case "vcenter": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "vphantom": + { + throw new Error("KaTeX-a11y: vphantom not implemented yet"); + } + + case "hphantom": + { + throw new Error("KaTeX-a11y: hphantom not implemented yet"); + } + + case "operatorname": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "array": + { + throw new Error("KaTeX-a11y: array not implemented yet"); + } + + case "raw": + { + throw new Error("KaTeX-a11y: raw not implemented yet"); + } + + case "size": + { + // Although there are nodes of type "size" in the parse tree, they have + // no semantic meaning and should be ignored. + break; + } + + case "url": + { + throw new Error("KaTeX-a11y: url not implemented yet"); + } + + case "tag": + { + throw new Error("KaTeX-a11y: tag not implemented yet"); + } + + case "verb": + { + buildString("start verbatim", "normal", a11yStrings); + buildString(tree.body, "normal", a11yStrings); + buildString("end verbatim", "normal", a11yStrings); + break; + } + + case "environment": + { + throw new Error("KaTeX-a11y: environment not implemented yet"); + } + + case "horizBrace": + { + buildString("start " + tree.label.slice(1), "normal", a11yStrings); + buildA11yStrings(tree.base, a11yStrings, atomType); + buildString("end " + tree.label.slice(1), "normal", a11yStrings); + break; + } + + case "infix": + { + // All infix nodes are replace with other nodes. + break; + } + + case "includegraphics": + { + throw new Error("KaTeX-a11y: includegraphics not implemented yet"); + } + + case "font": + { + // TODO: callout the start/end of specific fonts + // TODO: map \BBb{N} to "the naturals" or something like that + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "href": + { + throw new Error("KaTeX-a11y: href not implemented yet"); + } + + case "cr": + { + // This is used by environments. + throw new Error("KaTeX-a11y: cr not implemented yet"); + } + + case "underline": + { + buildRegion(a11yStrings, function (a11yStrings) { + a11yStrings.push("start underline"); + buildA11yStrings(tree.body, a11yStrings, atomType); + a11yStrings.push("end underline"); + }); + break; + } + + case "xArrow": + { + throw new Error("KaTeX-a11y: xArrow not implemented yet"); + } + + case "cdlabel": + { + throw new Error("KaTeX-a11y: cdlabel not implemented yet"); + } + + case "cdlabelparent": + { + throw new Error("KaTeX-a11y: cdlabelparent not implemented yet"); + } + + case "mclass": + { + // \neq and \ne are macros so we let "htmlmathml" render the mathmal + // side of things and extract the text from that. + const atomType = tree.mclass.slice(1); // $FlowFixMe: drop the leading "m" from the values in mclass + + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "mathchoice": + { + // TODO: track which style we're using, e.g. display, text, etc. + // default to text style if even that may not be the correct style + buildA11yStrings(tree.text, a11yStrings, atomType); + break; + } + + case "htmlmathml": + { + buildA11yStrings(tree.mathml, a11yStrings, atomType); + break; + } + + case "middle": + { + buildString(tree.delim, atomType, a11yStrings); + break; + } + + case "internal": + { + // internal nodes are never included in the parse tree + break; + } + + case "html": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + default: + tree.type; + throw new Error("KaTeX a11y un-recognized type: " + tree.type); + } +}; + +const buildA11yStrings = function (tree, a11yStrings, atomType) { + if (a11yStrings === void 0) { + a11yStrings = []; + } + + if (tree instanceof Array) { + for (let i = 0; i < tree.length; i++) { + buildA11yStrings(tree[i], a11yStrings, atomType); + } + } else { + handleObject(tree, a11yStrings, atomType); + } + + return a11yStrings; +}; + +const flatten = function (array) { + let result = []; + array.forEach(function (item) { + if (item instanceof Array) { + result = result.concat(flatten(item)); + } else { + result.push(item); + } + }); + return result; +}; + +const renderA11yString = function (text, settings) { + const tree = katex__WEBPACK_IMPORTED_MODULE_0___default().__parse(text, settings); + + const a11yStrings = buildA11yStrings(tree, [], "normal"); + return flatten(a11yStrings).join(", "); +}; + +/* harmony default export */ __webpack_exports__["default"] = (renderA11yString); +__webpack_exports__ = __webpack_exports__["default"]; +/******/ return __webpack_exports__; +/******/ })() +; +}); \ No newline at end of file diff --git a/frontend/node_modules/katex/dist/contrib/render-a11y-string.min.js b/frontend/node_modules/katex/dist/contrib/render-a11y-string.min.js new file mode 100644 index 0000000..314ce26 --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/render-a11y-string.min.js @@ -0,0 +1 @@ +!function(e,r){if("object"==typeof exports&&"object"==typeof module)module.exports=r(require("katex"));else if("function"==typeof define&&define.amd)define(["katex"],r);else{var t="object"==typeof exports?r(require("katex")):r(e.katex);for(var a in t)("object"==typeof exports?exports:e)[a]=t[a]}}("undefined"!=typeof self?self:this,(function(e){return function(){"use strict";var r={757:function(r){r.exports=e}},t={};function a(e){var o=t[e];if(void 0!==o)return o.exports;var n=t[e]={exports:{}};return r[e](n,n.exports,a),n.exports}a.n=function(e){var r=e&&e.__esModule?function(){return e.default}:function(){return e};return a.d(r,{a:r}),r},a.d=function(e,r){for(var t in r)a.o(r,t)&&!a.o(e,t)&&Object.defineProperty(e,t,{enumerable:!0,get:r[t]})},a.o=function(e,r){return Object.prototype.hasOwnProperty.call(e,r)};var o={},n=a(757),s=a.n(n);const l={"(":"left parenthesis",")":"right parenthesis","[":"open bracket","]":"close bracket","\\{":"left brace","\\}":"right brace","\\lvert":"open vertical bar","\\rvert":"close vertical bar","|":"vertical bar","\\uparrow":"up arrow","\\Uparrow":"up arrow","\\downarrow":"down arrow","\\Downarrow":"down arrow","\\updownarrow":"up down arrow","\\leftarrow":"left arrow","\\Leftarrow":"left arrow","\\rightarrow":"right arrow","\\Rightarrow":"right arrow","\\langle":"open angle","\\rangle":"close angle","\\lfloor":"open floor","\\rfloor":"close floor","\\int":"integral","\\intop":"integral","\\lim":"limit","\\ln":"natural log","\\log":"log","\\sin":"sine","\\cos":"cosine","\\tan":"tangent","\\cot":"cotangent","\\sum":"sum","/":"slash",",":"comma",".":"point","-":"negative","+":"plus","~":"tilde",":":"colon","?":"question mark","'":"apostrophe","\\%":"percent"," ":"space","\\ ":"space","\\$":"dollar sign","\\angle":"angle","\\degree":"degree","\\circ":"circle","\\vec":"vector","\\triangle":"triangle","\\pi":"pi","\\prime":"prime","\\infty":"infinity","\\alpha":"alpha","\\beta":"beta","\\gamma":"gamma","\\omega":"omega","\\theta":"theta","\\sigma":"sigma","\\lambda":"lambda","\\tau":"tau","\\Delta":"delta","\\delta":"delta","\\mu":"mu","\\rho":"rho","\\nabla":"del","\\ell":"ell","\\ldots":"dots","\\hat":"hat","\\acute":"acute"},i={prime:"prime",degree:"degrees",circle:"degrees",2:"squared",3:"cubed"},c={"|":"open vertical bar",".":""},p={"|":"close vertical bar",".":""},u={"+":"plus","-":"minus","\\pm":"plus minus","\\cdot":"dot","*":"times","/":"divided by","\\times":"times","\\div":"divided by","\\circ":"circle","\\bullet":"bullet"},d={"=":"equals","\\approx":"approximately equals","\u2260":"does not equal","\\geq":"is greater than or equal to","\\ge":"is greater than or equal to","\\leq":"is less than or equal to","\\le":"is less than or equal to",">":"is greater than","<":"is less than","\\leftarrow":"left arrow","\\Leftarrow":"left arrow","\\rightarrow":"right arrow","\\Rightarrow":"right arrow",":":"colon"},h={"\\underleftarrow":"left arrow","\\underrightarrow":"right arrow","\\underleftrightarrow":"left-right arrow","\\undergroup":"group","\\underlinesegment":"line segment","\\utilde":"tilde"},b=(e,r,t)=>{if(!e)return;let a;a="open"===r?e in c?c[e]:l[e]||e:"close"===r?e in p?p[e]:l[e]||e:"bin"===r?u[e]||e:"rel"===r?d[e]||e:l[e]||e,/^\d+$/.test(a)&&t.length>0&&/^\d+$/.test(t[t.length-1])?t[t.length-1]+=a:a&&t.push(a)},m=(e,r)=>{const t=[];e.push(t),r(t)},f=function(e,r,t){if(void 0===r&&(r=[]),e instanceof Array)for(let a=0;a{switch(e.type){case"accent":m(r,(r=>{f(e.base,r,t),r.push("with"),b(e.label,"normal",r),r.push("on top")}));break;case"accentUnder":m(r,(r=>{f(e.base,r,t),r.push("with"),b(h[e.label],"normal",r),r.push("underneath")}));break;case"accent-token":case"color-token":case"kern":case"leftright-right":case"size":case"infix":case"internal":break;case"atom":{const{text:t}=e;switch(e.family){case"bin":b(t,"bin",r);break;case"close":b(t,"close",r);break;case"inner":b(e.text,"inner",r);break;case"open":b(t,"open",r);break;case"punct":b(t,"punct",r);break;case"rel":b(t,"rel",r);break;default:throw e.family,new Error('"'+e.family+'" is not a valid atom type')}break}case"color":{const a=e.color.replace(/katex-/,"");m(r,(r=>{r.push("start color "+a),f(e.body,r,t),r.push("end color "+a)}));break}case"delimsizing":e.delim&&"."!==e.delim&&b(e.delim,"normal",r);break;case"genfrac":m(r,(r=>{const{leftDelim:a,rightDelim:o}=e;e.hasBarLine?(r.push("start fraction"),a&&b(a,"open",r),f(e.numer,r,t),r.push("divided by"),f(e.denom,r,t),o&&b(o,"close",r),r.push("end fraction")):(r.push("start binomial"),a&&b(a,"open",r),f(e.numer,r,t),r.push("over"),f(e.denom,r,t),o&&b(o,"close",r),r.push("end binomial"))}));break;case"hbox":case"lap":case"ordgroup":case"raisebox":case"sizing":case"styling":case"smash":case"vcenter":case"operatorname":case"font":case"html":f(e.body,r,t);break;case"leftright":m(r,(r=>{b(e.left,"open",r),f(e.body,r,t),b(e.right,"close",r)}));break;case"mathord":b(e.text,"normal",r);break;case"op":{const{body:a,name:o}=e;a?f(a,r,t):o&&b(o,"normal",r);break}case"op-token":case"textord":b(e.text,t,r);break;case"overline":m(r,(function(r){r.push("start overline"),f(e.body,r,t),r.push("end overline")}));break;case"pmb":r.push("bold");break;case"phantom":r.push("empty space");break;case"rule":r.push("rectangle");break;case"spacing":r.push("space");break;case"sqrt":m(r,(r=>{const{body:a,index:o}=e;if(o)return"3"===w(f(o,[],t)).join(",")?(r.push("cube root of"),f(a,r,t),void r.push("end cube root")):(r.push("root"),r.push("start index"),f(o,r,t),void r.push("end index"));r.push("square root of"),f(a,r,t),r.push("end square root")}));break;case"supsub":{const{base:a,sub:o,sup:n}=e;let s=!1;if(a&&(f(a,r,t),s="op"===a.type&&"\\log"===a.name),o){const e=s?"base":"subscript";m(r,(function(r){r.push("start "+e),f(o,r,t),r.push("end "+e)}))}n&&m(r,(function(e){const r=w(f(n,[],t)).join(",");r in i?e.push(i[r]):(e.push("start superscript"),f(n,e,t),e.push("end superscript"))}));break}case"text":if("\\textbf"===e.font){m(r,(function(r){r.push("start bold text"),f(e.body,r,t),r.push("end bold text")}));break}m(r,(function(r){r.push("start text"),f(e.body,r,t),r.push("end text")}));break;case"enclose":if(/cancel/.test(e.label)){m(r,(function(r){r.push("start cancel"),f(e.body,r,t),r.push("end cancel")}));break}if(/box/.test(e.label)){m(r,(function(r){r.push("start box"),f(e.body,r,t),r.push("end box")}));break}if(/sout/.test(e.label)){m(r,(function(r){r.push("start strikeout"),f(e.body,r,t),r.push("end strikeout")}));break}if(/phase/.test(e.label)){m(r,(function(r){r.push("start phase angle"),f(e.body,r,t),r.push("end phase angle")}));break}throw new Error("KaTeX-a11y: enclose node with "+e.label+" not supported yet");case"vphantom":throw new Error("KaTeX-a11y: vphantom not implemented yet");case"hphantom":throw new Error("KaTeX-a11y: hphantom not implemented yet");case"array":throw new Error("KaTeX-a11y: array not implemented yet");case"raw":throw new Error("KaTeX-a11y: raw not implemented yet");case"url":throw new Error("KaTeX-a11y: url not implemented yet");case"tag":throw new Error("KaTeX-a11y: tag not implemented yet");case"verb":b("start verbatim","normal",r),b(e.body,"normal",r),b("end verbatim","normal",r);break;case"environment":throw new Error("KaTeX-a11y: environment not implemented yet");case"horizBrace":b("start "+e.label.slice(1),"normal",r),f(e.base,r,t),b("end "+e.label.slice(1),"normal",r);break;case"includegraphics":throw new Error("KaTeX-a11y: includegraphics not implemented yet");case"href":throw new Error("KaTeX-a11y: href not implemented yet");case"cr":throw new Error("KaTeX-a11y: cr not implemented yet");case"underline":m(r,(function(r){r.push("start underline"),f(e.body,r,t),r.push("end underline")}));break;case"xArrow":throw new Error("KaTeX-a11y: xArrow not implemented yet");case"cdlabel":throw new Error("KaTeX-a11y: cdlabel not implemented yet");case"cdlabelparent":throw new Error("KaTeX-a11y: cdlabelparent not implemented yet");case"mclass":{const t=e.mclass.slice(1);f(e.body,r,t);break}case"mathchoice":f(e.text,r,t);break;case"htmlmathml":f(e.mathml,r,t);break;case"middle":b(e.delim,t,r);break;default:throw e.type,new Error("KaTeX a11y un-recognized type: "+e.type)}})(e,r,t);return r},w=function(e){let r=[];return e.forEach((function(e){e instanceof Array?r=r.concat(w(e)):r.push(e)})),r};return o.default=function(e,r){const t=s().__parse(e,r),a=f(t,[],"normal");return w(a).join(", ")},o=o.default}()})); \ No newline at end of file diff --git a/frontend/node_modules/katex/dist/contrib/render-a11y-string.mjs b/frontend/node_modules/katex/dist/contrib/render-a11y-string.mjs new file mode 100644 index 0000000..d23d20a --- /dev/null +++ b/frontend/node_modules/katex/dist/contrib/render-a11y-string.mjs @@ -0,0 +1,800 @@ +import katex from '../katex.mjs'; + +/** + * renderA11yString returns a readable string. + * + * In some cases the string will have the proper semantic math + * meaning,: + * renderA11yString("\\frac{1}{2}"") + * -> "start fraction, 1, divided by, 2, end fraction" + * + * However, other cases do not: + * renderA11yString("f(x) = x^2") + * -> "f, left parenthesis, x, right parenthesis, equals, x, squared" + * + * The commas in the string aim to increase ease of understanding + * when read by a screenreader. + */ +var stringMap = { + "(": "left parenthesis", + ")": "right parenthesis", + "[": "open bracket", + "]": "close bracket", + "\\{": "left brace", + "\\}": "right brace", + "\\lvert": "open vertical bar", + "\\rvert": "close vertical bar", + "|": "vertical bar", + "\\uparrow": "up arrow", + "\\Uparrow": "up arrow", + "\\downarrow": "down arrow", + "\\Downarrow": "down arrow", + "\\updownarrow": "up down arrow", + "\\leftarrow": "left arrow", + "\\Leftarrow": "left arrow", + "\\rightarrow": "right arrow", + "\\Rightarrow": "right arrow", + "\\langle": "open angle", + "\\rangle": "close angle", + "\\lfloor": "open floor", + "\\rfloor": "close floor", + "\\int": "integral", + "\\intop": "integral", + "\\lim": "limit", + "\\ln": "natural log", + "\\log": "log", + "\\sin": "sine", + "\\cos": "cosine", + "\\tan": "tangent", + "\\cot": "cotangent", + "\\sum": "sum", + "/": "slash", + ",": "comma", + ".": "point", + "-": "negative", + "+": "plus", + "~": "tilde", + ":": "colon", + "?": "question mark", + "'": "apostrophe", + "\\%": "percent", + " ": "space", + "\\ ": "space", + "\\$": "dollar sign", + "\\angle": "angle", + "\\degree": "degree", + "\\circ": "circle", + "\\vec": "vector", + "\\triangle": "triangle", + "\\pi": "pi", + "\\prime": "prime", + "\\infty": "infinity", + "\\alpha": "alpha", + "\\beta": "beta", + "\\gamma": "gamma", + "\\omega": "omega", + "\\theta": "theta", + "\\sigma": "sigma", + "\\lambda": "lambda", + "\\tau": "tau", + "\\Delta": "delta", + "\\delta": "delta", + "\\mu": "mu", + "\\rho": "rho", + "\\nabla": "del", + "\\ell": "ell", + "\\ldots": "dots", + // TODO: add entries for all accents + "\\hat": "hat", + "\\acute": "acute" +}; +var powerMap = { + "prime": "prime", + "degree": "degrees", + "circle": "degrees", + "2": "squared", + "3": "cubed" +}; +var openMap = { + "|": "open vertical bar", + ".": "" +}; +var closeMap = { + "|": "close vertical bar", + ".": "" +}; +var binMap = { + "+": "plus", + "-": "minus", + "\\pm": "plus minus", + "\\cdot": "dot", + "*": "times", + "/": "divided by", + "\\times": "times", + "\\div": "divided by", + "\\circ": "circle", + "\\bullet": "bullet" +}; +var relMap = { + "=": "equals", + "\\approx": "approximately equals", + "≠": "does not equal", + "\\geq": "is greater than or equal to", + "\\ge": "is greater than or equal to", + "\\leq": "is less than or equal to", + "\\le": "is less than or equal to", + ">": "is greater than", + "<": "is less than", + "\\leftarrow": "left arrow", + "\\Leftarrow": "left arrow", + "\\rightarrow": "right arrow", + "\\Rightarrow": "right arrow", + ":": "colon" +}; +var accentUnderMap = { + "\\underleftarrow": "left arrow", + "\\underrightarrow": "right arrow", + "\\underleftrightarrow": "left-right arrow", + "\\undergroup": "group", + "\\underlinesegment": "line segment", + "\\utilde": "tilde" +}; + +var buildString = (str, type, a11yStrings) => { + if (!str) { + return; + } + + var ret; + + if (type === "open") { + ret = str in openMap ? openMap[str] : stringMap[str] || str; + } else if (type === "close") { + ret = str in closeMap ? closeMap[str] : stringMap[str] || str; + } else if (type === "bin") { + ret = binMap[str] || str; + } else if (type === "rel") { + ret = relMap[str] || str; + } else { + ret = stringMap[str] || str; + } // If the text to add is a number and there is already a string + // in the list and the last string is a number then we should + // combine them into a single number + + + if (/^\d+$/.test(ret) && a11yStrings.length > 0 && // TODO(kevinb): check that the last item in a11yStrings is a string + // I think we might be able to drop the nested arrays, which would make + // this easier to type + // $FlowFixMe + /^\d+$/.test(a11yStrings[a11yStrings.length - 1])) { + a11yStrings[a11yStrings.length - 1] += ret; + } else if (ret) { + a11yStrings.push(ret); + } +}; + +var buildRegion = (a11yStrings, callback) => { + var regionStrings = []; + a11yStrings.push(regionStrings); + callback(regionStrings); +}; + +var handleObject = (tree, a11yStrings, atomType) => { + // Everything else is assumed to be an object... + switch (tree.type) { + case "accent": + { + buildRegion(a11yStrings, a11yStrings => { + buildA11yStrings(tree.base, a11yStrings, atomType); + a11yStrings.push("with"); + buildString(tree.label, "normal", a11yStrings); + a11yStrings.push("on top"); + }); + break; + } + + case "accentUnder": + { + buildRegion(a11yStrings, a11yStrings => { + buildA11yStrings(tree.base, a11yStrings, atomType); + a11yStrings.push("with"); + buildString(accentUnderMap[tree.label], "normal", a11yStrings); + a11yStrings.push("underneath"); + }); + break; + } + + case "accent-token": + { + // Used internally by accent symbols. + break; + } + + case "atom": + { + var { + text + } = tree; + + switch (tree.family) { + case "bin": + { + buildString(text, "bin", a11yStrings); + break; + } + + case "close": + { + buildString(text, "close", a11yStrings); + break; + } + // TODO(kevinb): figure out what should be done for inner + + case "inner": + { + buildString(tree.text, "inner", a11yStrings); + break; + } + + case "open": + { + buildString(text, "open", a11yStrings); + break; + } + + case "punct": + { + buildString(text, "punct", a11yStrings); + break; + } + + case "rel": + { + buildString(text, "rel", a11yStrings); + break; + } + + default: + { + tree.family; + throw new Error("\"" + tree.family + "\" is not a valid atom type"); + } + } + + break; + } + + case "color": + { + var color = tree.color.replace(/katex-/, ""); + buildRegion(a11yStrings, regionStrings => { + regionStrings.push("start color " + color); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end color " + color); + }); + break; + } + + case "color-token": + { + // Used by \color, \colorbox, and \fcolorbox but not directly rendered. + // It's a leaf node and has no children so just break. + break; + } + + case "delimsizing": + { + if (tree.delim && tree.delim !== ".") { + buildString(tree.delim, "normal", a11yStrings); + } + + break; + } + + case "genfrac": + { + buildRegion(a11yStrings, regionStrings => { + // genfrac can have unbalanced delimiters + var { + leftDelim, + rightDelim + } = tree; // NOTE: Not sure if this is a safe assumption + // hasBarLine true -> fraction, false -> binomial + + if (tree.hasBarLine) { + regionStrings.push("start fraction"); + leftDelim && buildString(leftDelim, "open", regionStrings); + buildA11yStrings(tree.numer, regionStrings, atomType); + regionStrings.push("divided by"); + buildA11yStrings(tree.denom, regionStrings, atomType); + rightDelim && buildString(rightDelim, "close", regionStrings); + regionStrings.push("end fraction"); + } else { + regionStrings.push("start binomial"); + leftDelim && buildString(leftDelim, "open", regionStrings); + buildA11yStrings(tree.numer, regionStrings, atomType); + regionStrings.push("over"); + buildA11yStrings(tree.denom, regionStrings, atomType); + rightDelim && buildString(rightDelim, "close", regionStrings); + regionStrings.push("end binomial"); + } + }); + break; + } + + case "hbox": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "kern": + { + // No op: we don't attempt to present kerning information + // to the screen reader. + break; + } + + case "leftright": + { + buildRegion(a11yStrings, regionStrings => { + buildString(tree.left, "open", regionStrings); + buildA11yStrings(tree.body, regionStrings, atomType); + buildString(tree.right, "close", regionStrings); + }); + break; + } + + case "leftright-right": + { + // TODO: double check that this is a no-op + break; + } + + case "lap": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "mathord": + { + buildString(tree.text, "normal", a11yStrings); + break; + } + + case "op": + { + var { + body, + name + } = tree; + + if (body) { + buildA11yStrings(body, a11yStrings, atomType); + } else if (name) { + buildString(name, "normal", a11yStrings); + } + + break; + } + + case "op-token": + { + // Used internally by operator symbols. + buildString(tree.text, atomType, a11yStrings); + break; + } + + case "ordgroup": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "overline": + { + buildRegion(a11yStrings, function (a11yStrings) { + a11yStrings.push("start overline"); + buildA11yStrings(tree.body, a11yStrings, atomType); + a11yStrings.push("end overline"); + }); + break; + } + + case "pmb": + { + a11yStrings.push("bold"); + break; + } + + case "phantom": + { + a11yStrings.push("empty space"); + break; + } + + case "raisebox": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "rule": + { + a11yStrings.push("rectangle"); + break; + } + + case "sizing": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "spacing": + { + a11yStrings.push("space"); + break; + } + + case "styling": + { + // We ignore the styling and just pass through the contents + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "sqrt": + { + buildRegion(a11yStrings, regionStrings => { + var { + body, + index + } = tree; + + if (index) { + var indexString = flatten(buildA11yStrings(index, [], atomType)).join(","); + + if (indexString === "3") { + regionStrings.push("cube root of"); + buildA11yStrings(body, regionStrings, atomType); + regionStrings.push("end cube root"); + return; + } + + regionStrings.push("root"); + regionStrings.push("start index"); + buildA11yStrings(index, regionStrings, atomType); + regionStrings.push("end index"); + return; + } + + regionStrings.push("square root of"); + buildA11yStrings(body, regionStrings, atomType); + regionStrings.push("end square root"); + }); + break; + } + + case "supsub": + { + var { + base, + sub, + sup + } = tree; + var isLog = false; + + if (base) { + buildA11yStrings(base, a11yStrings, atomType); + isLog = base.type === "op" && base.name === "\\log"; + } + + if (sub) { + var regionName = isLog ? "base" : "subscript"; + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start " + regionName); + buildA11yStrings(sub, regionStrings, atomType); + regionStrings.push("end " + regionName); + }); + } + + if (sup) { + buildRegion(a11yStrings, function (regionStrings) { + var supString = flatten(buildA11yStrings(sup, [], atomType)).join(","); + + if (supString in powerMap) { + regionStrings.push(powerMap[supString]); + return; + } + + regionStrings.push("start superscript"); + buildA11yStrings(sup, regionStrings, atomType); + regionStrings.push("end superscript"); + }); + } + + break; + } + + case "text": + { + // TODO: handle other fonts + if (tree.font === "\\textbf") { + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start bold text"); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end bold text"); + }); + break; + } + + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start text"); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end text"); + }); + break; + } + + case "textord": + { + buildString(tree.text, atomType, a11yStrings); + break; + } + + case "smash": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "enclose": + { + // TODO: create a map for these. + // TODO: differentiate between a body with a single atom, e.g. + // "cancel a" instead of "start cancel, a, end cancel" + if (/cancel/.test(tree.label)) { + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start cancel"); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end cancel"); + }); + break; + } else if (/box/.test(tree.label)) { + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start box"); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end box"); + }); + break; + } else if (/sout/.test(tree.label)) { + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start strikeout"); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end strikeout"); + }); + break; + } else if (/phase/.test(tree.label)) { + buildRegion(a11yStrings, function (regionStrings) { + regionStrings.push("start phase angle"); + buildA11yStrings(tree.body, regionStrings, atomType); + regionStrings.push("end phase angle"); + }); + break; + } + + throw new Error("KaTeX-a11y: enclose node with " + tree.label + " not supported yet"); + } + + case "vcenter": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "vphantom": + { + throw new Error("KaTeX-a11y: vphantom not implemented yet"); + } + + case "hphantom": + { + throw new Error("KaTeX-a11y: hphantom not implemented yet"); + } + + case "operatorname": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "array": + { + throw new Error("KaTeX-a11y: array not implemented yet"); + } + + case "raw": + { + throw new Error("KaTeX-a11y: raw not implemented yet"); + } + + case "size": + { + // Although there are nodes of type "size" in the parse tree, they have + // no semantic meaning and should be ignored. + break; + } + + case "url": + { + throw new Error("KaTeX-a11y: url not implemented yet"); + } + + case "tag": + { + throw new Error("KaTeX-a11y: tag not implemented yet"); + } + + case "verb": + { + buildString("start verbatim", "normal", a11yStrings); + buildString(tree.body, "normal", a11yStrings); + buildString("end verbatim", "normal", a11yStrings); + break; + } + + case "environment": + { + throw new Error("KaTeX-a11y: environment not implemented yet"); + } + + case "horizBrace": + { + buildString("start " + tree.label.slice(1), "normal", a11yStrings); + buildA11yStrings(tree.base, a11yStrings, atomType); + buildString("end " + tree.label.slice(1), "normal", a11yStrings); + break; + } + + case "infix": + { + // All infix nodes are replace with other nodes. + break; + } + + case "includegraphics": + { + throw new Error("KaTeX-a11y: includegraphics not implemented yet"); + } + + case "font": + { + // TODO: callout the start/end of specific fonts + // TODO: map \BBb{N} to "the naturals" or something like that + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + case "href": + { + throw new Error("KaTeX-a11y: href not implemented yet"); + } + + case "cr": + { + // This is used by environments. + throw new Error("KaTeX-a11y: cr not implemented yet"); + } + + case "underline": + { + buildRegion(a11yStrings, function (a11yStrings) { + a11yStrings.push("start underline"); + buildA11yStrings(tree.body, a11yStrings, atomType); + a11yStrings.push("end underline"); + }); + break; + } + + case "xArrow": + { + throw new Error("KaTeX-a11y: xArrow not implemented yet"); + } + + case "cdlabel": + { + throw new Error("KaTeX-a11y: cdlabel not implemented yet"); + } + + case "cdlabelparent": + { + throw new Error("KaTeX-a11y: cdlabelparent not implemented yet"); + } + + case "mclass": + { + // \neq and \ne are macros so we let "htmlmathml" render the mathmal + // side of things and extract the text from that. + var _atomType = tree.mclass.slice(1); // $FlowFixMe: drop the leading "m" from the values in mclass + + + buildA11yStrings(tree.body, a11yStrings, _atomType); + break; + } + + case "mathchoice": + { + // TODO: track which style we're using, e.g. display, text, etc. + // default to text style if even that may not be the correct style + buildA11yStrings(tree.text, a11yStrings, atomType); + break; + } + + case "htmlmathml": + { + buildA11yStrings(tree.mathml, a11yStrings, atomType); + break; + } + + case "middle": + { + buildString(tree.delim, atomType, a11yStrings); + break; + } + + case "internal": + { + // internal nodes are never included in the parse tree + break; + } + + case "html": + { + buildA11yStrings(tree.body, a11yStrings, atomType); + break; + } + + default: + tree.type; + throw new Error("KaTeX a11y un-recognized type: " + tree.type); + } +}; + +var buildA11yStrings = function buildA11yStrings(tree, a11yStrings, atomType) { + if (a11yStrings === void 0) { + a11yStrings = []; + } + + if (tree instanceof Array) { + for (var i = 0; i < tree.length; i++) { + buildA11yStrings(tree[i], a11yStrings, atomType); + } + } else { + handleObject(tree, a11yStrings, atomType); + } + + return a11yStrings; +}; + +var flatten = function flatten(array) { + var result = []; + array.forEach(function (item) { + if (item instanceof Array) { + result = result.concat(flatten(item)); + } else { + result.push(item); + } + }); + return result; +}; + +var renderA11yString = function renderA11yString(text, settings) { + var tree = katex.__parse(text, settings); + + var a11yStrings = buildA11yStrings(tree, [], "normal"); + return flatten(a11yStrings).join(", "); +}; + +export { renderA11yString as default }; diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_AMS-Regular.ttf b/frontend/node_modules/katex/dist/fonts/KaTeX_AMS-Regular.ttf new file mode 100644 index 0000000000000000000000000000000000000000..c6f9a5e7c03f9e64e9c7b4773a8e37ade8eaf406 GIT binary patch literal 63632 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_AMS-Regular.woff2 b/frontend/node_modules/katex/dist/fonts/KaTeX_AMS-Regular.woff2 new file mode 100644 index 0000000000000000000000000000000000000000..0acaaff03d4bb7606de02a827aeee338e5a86910 GIT binary patch literal 28076 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 G2<`xUL{2yW literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Caligraphic-Regular.ttf b/frontend/node_modules/katex/dist/fonts/KaTeX_Caligraphic-Regular.ttf new file mode 100644 index 0000000000000000000000000000000000000000..f522294ff0f3f8c52dfdaef7ebfaa06ebfcfaabf GIT binary patch literal 12344 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 Mepdy)y#Y}F4=Hd9=l}o! literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Caligraphic-Regular.woff2 b/frontend/node_modules/katex/dist/fonts/KaTeX_Caligraphic-Regular.woff2 new file mode 100644 index 0000000000000000000000000000000000000000..75344a1f98e37e2c631e178065854c3a81fb842f GIT binary patch literal 6908 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 CFgb+) literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Fraktur-Bold.ttf b/frontend/node_modules/katex/dist/fonts/KaTeX_Fraktur-Bold.ttf new file mode 100644 index 0000000000000000000000000000000000000000..4e98259c3b54076d684bf3459baeaeae8dbce97a GIT binary patch literal 19584 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Fraktur-Bold.woff2 b/frontend/node_modules/katex/dist/fonts/KaTeX_Fraktur-Bold.woff2 new file mode 100644 index 0000000000000000000000000000000000000000..395f28beac23c7b0f7f3a1e714bd8dac253dd3bc GIT binary patch literal 11348 zcmV-aEUVLZPew8T0RR9104!7h4gdfE08HQj04x0f0RR9100000000000000000000 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 Y{My=5Zj3WbM|mX<0#Lulu=APmKiR?A3IG5A literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Bold.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Bold.woff new file mode 100644 index 0000000000000000000000000000000000000000..f38136ac1cc2dcdc9d9b10b8521487468b1f768c GIT binary patch literal 29912 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 bnfbLfgSm6Day;iB;wah|00962|Nj6Fv8wea literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Bold.woff2 b/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Bold.woff2 new file mode 100644 index 0000000000000000000000000000000000000000..ab2ad21da6fbe6c171bb869240954d0ead8f68fd GIT binary patch literal 25324 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 PaXk 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Main-BoldItalic.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_Main-BoldItalic.woff new file mode 100644 index 0000000000000000000000000000000000000000..67807b0bd4f867853271f5917fb3adf377f93f53 GIT binary patch literal 19412 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Italic.ttf b/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Italic.ttf new file mode 100644 index 0000000000000000000000000000000000000000..0e9b0f354ad460202bba554359f5adcc8da666b7 GIT binary patch literal 33580 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Italic.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Italic.woff new file mode 100644 index 0000000000000000000000000000000000000000..6f43b594b6c1d863a0e3f93b001f8dd503316464 GIT binary patch literal 19676 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Italic.woff2 b/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Italic.woff2 new file mode 100644 index 0000000000000000000000000000000000000000..b50920e138807f385d0b0359f4f0f09891f18406 GIT binary patch literal 16988 zcmV(>K-j-`Pew8T0RR91076^<4gdfE0E4su073x(0RR9100000000000000000000 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Regular.ttf b/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Regular.ttf new file mode 100644 index 0000000000000000000000000000000000000000..dd45e1ed2e18b32c516d9b481ebed3cb8bffa711 GIT binary patch literal 53580 zcmd442bd&Rc`n@NRIci-?&_|t>YUT0p3ptrljF|J##wFDMrl{lYJ<`$AR#0nAqkX0 zB*_AcWPEL|Ot6Fyw%{5tV8CQ!urb%h27>@|eYu1m8*T6Zo>M&=KoUHD{`)-t&g@Kg zRdv<(edo*JjF0$yKGS!HPw*Yux?^x;=`S{p`+QG+5JwMPdez~Rm4EvFoX_`^?ehsc zFTL@G9K9;u_W3?l!})!epFDciCG}Ic`g|WchMV}09=`r0j)#1{udKsw_2`v1U;ang zqqx`bO~kGc*cp6`!wRHLPmGDvmsI z*~kcup8C-U`BPl8>Lb3tqM!E#eQBTiv=h=P9qEfSTa6JXYEwln7OE8*aqz}_J=$!o z7UQvUjZiC0No_WsO9mo67A?{@M+#7xRgd8%o*f;Adap z7`erk{R?~jMllgDR&oQ=t)6u71r7nWvC}hx2H1A^4g$7)yG9gFg?0n5F_>%`Rl2Vk zS@6aqNKsMjF33eiW)uPv;nDW_Z*UBE0+PjwgdglPjrN%N)7~CY^oQv-@=?5!bvbYW zc`~TW7hP;eZ@5m@gX{wD@HrQlp^w#qxue_+?)KiMBp9)GK>h2_pSM9N-iiqZLd zfhqyNBy8S71ljPe(3JowQ+`SJr4k5AxI&T%er^Wa``V{JLq0-j#9Xz|4Rs5=j&G^x88+PKDM3+Xqqt5z`Sj zn{mbT9x>RH=o#8Lp45f9d{HGU5Gmc8nWti;Sa0+SGNqH6K>DW}&pJ7wIwBGhC6p3- zXK&xk0oPFLbrP8D8@Hs0lXaaeq3aCtpMnui9U5IZ5!DCl;feZOSc

    viU|OFj=e4 z`Uxek5bnO)*l=hG;s=iTjG%%}ZQlmpKHt^8z?^>c!0y$B@v7KFUtox@44PgPo6#*c!mgM)V7_u8yDJFU<+E>Q< z=VsLG1*xEJrDJ6OkpnxLJ%YBWktwz|1P8s9o5mnqXSf9d&j~U83151~XwRJqpdeN^bFejq6nT zsi2R%ls>)jjD{=~pf!U@XwCCAWM*)-2@UDPeJ?sKlP%!xm`{GnB)G3+LwQvz7E{(O z$UL(SiX3tsvLzf)q907xk1Jsz;FpcJzSa1NCWqfm#$Ivc@k4S@kOk3r_o;{9ZQ#Cb z+_!@JCUM^&yKkgD(r94mEZhw%p)duCCxn=$m=Yz)f9BqPze4o4zEvmm#{{?UeCC!* z-^Ok)s>J_Jdc!;YL}ifAkvZ}do-l(aG@~9x7$da-J^RfVrP=~tIj%B8*?S-Y-s1Q$ zF?3z7#j0(_SeFH(M&yQ93%X+(;C9#X!*uj}_tp*XjG~Z;8H{+RWb&9B zG&QX~E2tsIkY&1qJYs|`|0AKgOJvz_Lh3?~tC^7yKeuUfeK^!w;n>54B3 z94r|)w3_YwC>I7R@7PM-k_%NUKW36XqH6(#^ag{SuPX_q^S3`vD33f6z&kajcD`GdK<3QzYtp9#SknMHu(BNAppG=ud6fz@7^4@}t7Bacb} z)lWKqD9Jj0AE4jWiC>YPU($6$)rF73o>x!*kbIuL#b^75Vb4oWfG~Rwq?zJe!<#GT zas_zHip>;+r$gG{Z)k}Mw8NpX!yDSkNVzZ7>g~IJv@cFbdS}K7Q9{L#lkDwDIw28n zLUhBnkwou~*S~f9L?U{8`&$p*Je$k83)|!c=TK#N+R0>`>E+5HXF=Y!z$mu^Kb`=5 zdEgjhw8=Bg4zd@rG}_nACE+Kj)eo%R!DFp zpMWyKYEelDle$pU1A^T7+s@a5b@nWHf#lVU=~S{;o`6ryE>J-YV+=E1GJdhRhpaJ{J1X4qFzgN9-?H&RoTU*nTZk=1u34* zllPVq>yIAX6b?=_dN*XJ$B0C1V_XoP5hAug58hnezj(=B!n-ciI2Pd1mW5uz-=vc9obPEz47|pMukip|iPq>SlX%E{!?j@NxToYcqE$<9$rsJ*Uv6sI zK3x?_=hUN*Q5p%$2M!QP9Zo;_4_AR1hzJAS9I1c*IYQ-5v)<@2C56=ghOBm&r20lc zZN?Kzp!QS&)Nb>@5qSH$v# zs3HVsdRMZMWTLWK6BWaP=LL@}Jil&bUX|2sw`Sw|_*BGM+;#iG+5U)G&3!!|cXLv% zcdESqXeqx=5oGa+%ywgp%88U14jh*0pVTGm#;yDBF8ZT`(+DRh=atTGOmpJ{|16=ic1jS((~)(xL)1dLNg^ zxA-c)acFY=nT=DUeMyD;Wgs1>#VjZ&$@BvgLH3$c*#i+F9av(GzOKu3Dq&t1ely9$ zYEKl)T8fvX$q5pZTb*C- z9`9MStfIQf%xkKD)>g^Z-12x|dZ4{BCWjq$VF=6*Cu3^ww(Iwm8m_vzC7Mt5O{t{h z=KA7Nxk7?+U+0^XTMEfUx-YK|Yf(sP&t&2ZSH0CYq zdGIOhjYB`AnVoOG?qNlx)25;+WP9hI-c4glL=N7+Zb{M&iG+i)DwFDctEXk)Hs*UZ z{VKV}r{mtBUqJOTB<(!oekosx!a2(bc%83|ne?`x+4)506QK~jl_-J`Jaw1J0(2!{ zs6=`yC=p3eM7%#2X6Ba#m|qrVG!k7GKAtQ|MJ{M%c&?@DPEA%w<>A*U3hn%3=i72v z5J~QrC-3ci8_aG7805A@@4J_VC0V-n#?kqECARi$A0h9cABTRK1MK6CxCVX>v(*Ou zM_^pQyWW~WdOfxtWun@K{bYewp)1)Drsuooo2|R+*{SLP9wolI7HnUH2aAG%bs$08 zNr&~mp|NsA5PN3MriN(RU0+N{WNSJz+q-xmR!R9Ok!b(aTu*NtCZ`WXy8P49dT-w{CNPm4*bB2mb34(vAc27P%xv^ZoP>$?r3$Zv0gC#W_ z)GNiIeN)p@Q(G<$xVP=L^V1IxE0emcY`poETh?v9+)tjoU9~o|SG4ojMi7~cR z_?vlI&Xa>fE9*)l1UE~i{q9v;R+}3vvI9 zoGa*(mh3N7-f&pYzu~X^1g{P`?|>V4VsXbvQ!vN$&+B900hWCG0wU~&ZweHgXq!y_ z8w^j+#|(#oJ&VD@jBxNVirsS~AYK)jEYCtVq7kODS?=m|`0!r85?pVSV@HV)(rl4@ zEQTnrnbCqLUlr5?%dyxGY+I14j`VwJ#~x`Mxtw{ZRb&T9gQ!F%r#`&`-x1ELP!H4f zE0dG5BnGTH*?-~OB)cgvw>D&!u4-o(3g)O zS_oXS6!`kr^F0xr+&bDz;t;_E4G6-How}gN)se*1;E~IaQ<5(l?hW@f=+!X0bwV{8 zEY~}?M7l!{FP6Y;xR~^pfEFS_PMu>m}L=_g5GjG?S!F3P{`X*Vra#y-k zPMmx!Oo;WCleq}>3o(5|E09TwL7#Z zw`zsF{)+dwGRQLOua@zt&U1)jx4%51EN}gzo0lio9bbt@6vTuSHpWLkiB(JZM!{`; z87K#MHGqw+7-){~^VjL@B3Vc$FsbE`1DQMd!aPxPE_t;HdcF3_z-K?pS45+3K9hIY zdJw9s7tU`gt@e-gcNc+3(f@X}UAM1!C+r9#J)Pxr?>yJ}9+JG&PR~Di$p=o-0?ap&{Z;vXG*WAN6hbRN}@>Cq@KB4m~?)vL%m|X(Q7Jym%H!!P9 z;1#CnIASw`hZZEXh@>rBgtJ=U3@QUaMU?$PH}51a9_o{!@0-1qyuq+B@|E5uQ9~)C zob)Fiygg$48W!0?J)R6nk|c=qRkst-E*GMm=c0u&bjKZc02!_duvnfH{E+?=q+l;# z?@ci&U|fN3=&2|N+Y3P;$^Qk}@ED9OF7k-va)gwEmjG6i$^a<0^joIQX%EHNznU#e|1Z5K_6)vMBouSW#ixX9l%3vIN=DiX< z^CqHqzC+G??}?VjU9Wh>&lq!hZ%%#b>}wLd=iamLAYD-`<__S|13YXm%aLR1nY+;z z%kg=s+#ExTGh*#k|lpInjSLTf$Zjz2ACVmXme(-yRe z9+DlI+FXc_*82+yRY7h6sT;72Njr`@yPaw?{gR$7t;z7W0sCPF`)}|8qZkWy@zq2{ zrkfN$BPNgx**;^^QL(`#oH>|ThvXo=scqK!}k-R3_@yb!tjc z9Y2xHP5si7{~+sTxHqcOVAd{auZW_kA{eU|N@gNZ7u3l$zJe;_rV&_L^!MNT+SiGK z>L3%rQ5H+mpU}=TT2O^202&DOge-?%ewS#*{R0u!tV_ z$coT4AZ%5es3t*M$mi>0BYel3!v190NQIa&7UboX#N?PE2)0dQ^whs|t+fU)bL?O= zo)egTwpKStaT^)7&S^nnRs}G@ga|hQCT2an%$g^Z@Iu2;tP8%G!h*p5hICHR(JEDt z#ucKnZAT;L`d#o-?q;HS;YLmj&Mt0?agvYk4-^qd$mm!S#YG?yDkU2~|YS0wwA*$u9}?iCw!Qi`I z(yXiYIhlnZJ>65Ol}DF!>FDsRBd=>NNKvxu(XWZtJFkuR-gBZ9n$gI5tGNA!FiC{N zi7Pgx#{Xt}4>9NV{Ly&ou{AH~BsinOeePyY>Krc!Fae}9-s*42AgO@HXZ=>DqY#R5 zXXx3FDO+v|Q0hN4>m0f0JTW7C678vkKOQEgAgpYW7u$iZKP2y4RGp|gz9S%!m)~?& zsA$$Pm_Pc^LquNKFxX%|_t@!K`gfq~sBgFLGWgsFF5I@#??={0>c)&H;fk0@gk8~OBAQPo z4cqzJqj~M*?sFDxD1772;k--|>PWQ^kisj6bsA4hP6erdUwK4}jQiEZu6Mm|=dJ)5 zFr7V*e{y$Npj4U5MxrTQ6ZFUs^K-$0-@*!C06M8pAJ{Q+&I*Gb-WLz5VXpaG{J=Ml zIiQ_*N`lb}Hidl;QqT2b+St?6P#=sH3UW7qVSX{F$Qj}Ne;yI^f#Ss`*)@SuFBR1F z7O`QoEioVk3|m0$UoFN%i8s4QzG^)QePO|~=%H8M-qjz+^b7X}D+EsT#HRI0%jmKT zTxu;cv_mq+b|NB&judJO;;mw-AXCGx8H%KrCQ;HlVcZ%`R#i&wy6ddXC;vEAVJvm` z-GQXlTgyR5vJB_Xz){)*?S~WUFci!mx+C3aq1%1F6fc05|R+@{8*N)SN4P!M+@U2 z$&OIx_{#QcgLDGPoGeO0^2=_b$hHtfsy_N&Wc8=71^>l zFJQ6Hctp%0Vv_F(6*9Xe5~i1uFyaR#ZdIaVN!JjFYL!}u!bhU2}rBg8R2qTGp~NRV?^tQ_(AeSFDm}l zCA$rzY@B~4sN7Nk&OE&m2|-3V0#A*0Z1QC#5@qju$f9Kop)rto>I*dH%Ilr%A>EPp>cyg z!Pvl2Wu^1Q&ey1$h9X=y zJ}ywxExMOMa!iNTvFZkB@Gqdj+zZfP6p6$0XaExM1!jiuEKf2Lcy2h0xv3nwP@mn@Z(;Ep7@_y85m;GhHOi6I?3@!t0dCg;;2 zefV{E+=W(@G+#(@fV|@^$Bv5(X~2wrMmhwT>wq~aKp&&YXq2b2WuH94YR>rfG8s@> zEPp=Q3Wr&90AGyal0p6!eA0Q4rpEVb^Xme#QX`?C`~<@B(LaAUuz8aq+T>a7^GPfT z5l+1iL4-Cop4_0R6zK_-Q1lasWB{s)NXzSEHU&&KBF}yr6@LXV@je1x@)LSGuuzOG zS@kAA*;Zi?K}Mm^3&7b zKiex2g<&8+ohg^GAil!spOYVxk0I~372d?g`6}x_?B?lPa1|gSOc0n-f&N8U12C9{ z9A&G*O{JFrM>8I@MWtAX;(C`i*>Mr#?%4zNj2c)STR4m=1X}*gfGoqdXhZpURT0AC z@O*Q-saD;>x)Y|XkCYdkH=zV`U&R=Z)ziW*Ei@0uXmdOKdI4;4`n^4ZAc>!527x^vX0n|(H~q#(0{ zdMD#NwwQpM;|5BbG)RlwDnekI1Xw{-m@B}j;5n3z_$DgAMQLvj2Ujkpf$Mi|X)8Ka zV3}>32yQ-1+A(FhSC%q^f$&^eRsH@beZqM3_b4RYym?O~wC$Qn*14ona8xfD5F-KV zx}EO}6Y5WtA*`<96z4XUXW1IEReC#CiB)U+v)~_}=M`6~3^u00yPyFhj)!LwS+&%2 zYjBWU-=6{fwS?P94`zFo;*nnTa|BE|KC*vg;8GijgX3FBNPd+A;mkO0P@+W44PL!{ za9WR!tD-DKYU|y`O>$FNJ*ks*n(2D{LtRj|hH91ibfY)O;~_>_mQi6E6i!F6Te##& z4A7dh3M1_~^-9JlZPM?N738CDM)TnKhUM0bNp9V}ae~uy)4;mnO5Ezr4i@JkBFNeK za_5VJ9iVlcw3VU3_Fgr4_|D(Hy8|=&hX6)fW0(psFi8jdFmCpC<(w@GwZ3uF}79u;QBJuHk5&xB2MScIp z+qHScZ02qGi$7PC;Ks_voSiddUDTS3lCgcFR6cOKPOezE$`!~^Zk*TS5?JIL;H!>d zeb4L4@x%^Vd$iqMOU9?XiJ)DqfM21-qp)BMetaSLwZd0jVj>gNtCE!!Gze{AT)pUs%-J>rnshEx4(a8+IradouQ>h59?*#k(!* z&>iX1BjjJnr;u^j>${G1OCH#{d59oBLywf#!2x=;o9$5s5f99|WjoHC3^shNNf@Uq zB&p4+XY79qH$emkCWd%Hk8n>FxqI%EuHAvrf=eIS&_5o}*rA+6B_c{O8->w)a`4bl z!$@e>?9SM=kZ<#qtJ|k%OqvZ^Mk(E&jBXxm^najG&($PB@Gqo$CE*87yOCZD*sh?C zmBaa5xI7M@&8;e;2puN{3Xo@(>BvB8c4EEZU&0=6 ziD6U#kzCex)lH~2Mn<`7#^qeGS+|(&*wN^Dm$Z>ZY$1!-Y_eP;*cPIdl%Pasw%_6> zMC~;~YT(lWHKdLLd?lM3KyB*W+E1o>_k{r+UUqTT28pd15A* z`DtfDbkEwtBlvZ8L7Q^3g(M%#D|cDJvsF`5q8yd9zzN0mqqryqmIgQ8u9(HFA^SI7 z5>S$p^h^vl0VZToExa6DAN6Uz#W_L z_~r%KgD~zO3h?d&-l)T`@jWaB=XlSL2Q&O84k_u4u(uqt@Bu)}72FzVolkZC@+F@O zc@rAs&wa1Nb5m!Y3)>If?zk?r%5RlC*^Z_t!s+t_?{|_-tOrCB?rc{u#n%H9(z^7p zLt{c?-EF^%c2fA6fD&bXT{B6c#KNsbvblH2eKDe(3EcjlfFi{~$N-PIKRMhU%d03?^UHrx#~)XMIzI<%};qyUE<`YV~&zcd4L6 z0U`5KVQ4+!SEsi)`tn6o-!h%at!t|1*o3o`Os_P1R(cDqnLZIzO(c|lYQEyaNND~d zSMOJLUAQJGkQHxFIv-i42?E<+0>S?eevA#Xm2H>EcVD~JS_hj20~_? z;HOhP>9Ic93d&3Q;i;+qvHPz~*d)+atJTiGbiUn%pYA8S_M+);ad>&*3TUCw#;!)b z5-_vMXYW}K=Z*>J?|EFX#LT-E-^HcGgwnnhZo=%9RYe?4(nUWuR^+t4d{0wVDc~ov83vU889<=dF_jNV`wY{>#+`Kq(dvD zIyQWOYW?-`=xmtm+C0^-YG}e>`AdKO)U{=V`vooS`Jz6e;s)9`K-7?D& zh9RL_=uzZ2<)_?k?95$Wh8bsbgr#2S1|&vD;VeUXAFADR4-%wiv0o=O$r$Zx&7lcQ zD<|r7Pw>O_hi}UVt1BuTj=EhNnQSNz-B%XUL(DeE5i4fE2~&7p&sk2u!}!yn8(0aA zFE6}RJerZX8|HvHIG3~2+?h#=k1}O170_iip?7^OL^ht~dV{F+RwISEWt_o9`iKD* zc>2R~GOVSxk=$_qa3};FjNsjY&5!{E zS-cb=%lZ|nv|6X|2^$OnejH8`QY}13Nw!OUrSTZD?qPZtMUq*1kcdHlEGFw0UK~`- zs?ca;rxGEk1SIE#ve$X&)0=_pR?xLpICugh9Q(05q$hUMj$#0TYH< zei6#(EC{@|ATZb})hef2Rp2B&10(3_VoavZ`SQ#M$tQ>Q(VpJ4ttx@->(D(*3}G;I zqZp2eWT?JNm+<0FC6shzW7|GJU+M2BMp!G#nxGYIS>Jd7e*LRL>S>>J(<@{v0*sKw zQu;dYR~2&aYo4nrD!IO!ccnpc$1BC`Na}JcA!-~~#vd&A24eUw0)|mW?{hlZy5JT( zOgXi=?*?IF**D;N1``&y192H65R8w{x^^rJS!JhqwIUk*Y;fmBLpE3P;$VGZl49C2 zlTu2H{iCv4npNXTh!7P;NeS%Uj8@IzT+oRrX&RcDr@=`})^{HWYl7iyBh!Ky)X}U{ zm-6Dw)ao{5;wj6wN`|mUEfhpW3$c)g5yVoQtX>hKyY^5oNr{+|Y-huKXLzp3d2Svw zm~ue_hsS`dw}DAy3v@Uy1zCtjn(Z#bompX|S)h%Wz>GGBdQ%}o6fqTQW=auj{U&8V z3o6F0i!4qi^^7j0qh>-xxGMX{8hy_^%Yn5{`^a_I zX`u*5u1Np>N6wU=3|C#O9h-i5J=Sg*aA$a(1op^FLV8QV%nhLDjquR(JPiqj=xclV zbR6l0tnQSFWi96J8k&jq*-?esc8I+H{j4Vpt)&x-R@{ssH>uFK3aYI8Nz6Ua_Z0H_ ziPQxlq`E)C(%o>xarNbxAC-gd1sY(RM~?AHw!)+de-?7#Sp5-`u9>-wq=2u zV`W>Gh<^1o8kEqw9+L{+56F#{a(^_p7nR!VfSiyAvi`)4_bIt(KhpJn)b50IFcP@u zPID9W9vP4mVbgV(y{U5Q%!|5q!3h%zS6}XD$X1si z%N*I(wP<84jlvzd>SEO<8+cV6pTb=+bBD=P(V;I*?CXzM`{Onoo4| z<>!ePJP14t+46{ln1*o#)Jjn?F@GT=zG3=>OJxgCu9?b8wb})9E&l>y!*a5;5-WY; zW#yC~E<{ACAI&>sQ*#y6?d1)%~(M(-mi;NFh;`{ zO~;3mX}3PFMFx>c)HaPEuY`_qnvBlLZKn_&EGEh3uuZmaHD6vfHcuTd#tM`uN7fA~ zPqVQdAxnfERxKC}A*(LQNep3Pe!&n`s*djr1;c@QfTsPbpqCnKiBIg3f1a>H!l1?| zw{*HmZloVWPWuojxBG%Vfm4pTG$01Z!sL%$vGo zava8Z0vMl(LUj}~qtsN?fTC-pW01v!BIrK}1g^LOP`wfU)*<@WKFe1CRLQWn69i*c zwkAxLKy6G-am$D$!#Ah=o784$Ga9!NE7g`tj+PTyDJBI-+%f$0o^-Vx2uA|#N(Rk7 zbCC?|jB}G|9p;O&XLW4;XJ*HyZ(GC2St5aWBJuKXu9iO72cuN3JXC=WjI%6?+L z0%Ne9za?`C<;`yvb-jG!8`&i6zheLvzlnwCw9(bFjC@B0&x!EaLPlS-__5hzjv6wG zP>=j4L>NL0zQZ!SWikr3a$*J%;WT@!WEH}35jV|Ntdur=;s$spn`Xy?-H!jq5Zs{e{FUU3MSkxqO@eQ zo&(H+!oPtJ6J_?Q+q#Us7$7f98L|0iuhhqzmYHeW;YDS&=FFj721jLR>()oS_F;1 zgK_EiG*=?SLyPO+-Bi#z7_N&jLE^&V5X^v%Bxi1pbp_AmZoUPHk)XG zJ`ryR%`l>eD@`IjcrRhq!#DagdL#J}?+i>bj)xg#yoypCXIjQko<|6k!I;^FAIw;c z>t`4@dZS;H3R{jHKY>m^H9%2&J$6)}eihBYCypQ6Qjj#icntraPZUyr!&^UV+amw zRW8C%ac7%dg)auL0!j0dk8p{?p=z~&iYH&dR+|nyu({Y0I|v?7DK`R7dD+C1ab74hy4{_;49( zfeIhyTD{KgGMm0{^On;tXQ6(A#!Qd+3~L!qH~-~jq&+RqjGkvExjyG9VSI#(33EUM zt5{^stat7Ad+Ep3RRq9+0~6yH+Qxic8{crr%7P=uBjI>dz{H|kR^-Wi4Y96&s15EZ z51{oKeiPaPz=gc>vSHOA(%@vHCy{P$2}`+~w{AWzjs{IT5sM@-Or{VC)rg)~PUP8E zDl!q)jqPxxzM|6kR_A{*m5%i;!%KJu8LSHsk(|VOUv*^P_8t@KeYT2=rS|yFmDfsL ze2v)>vq*z!Xqo+lmi5-2Azk4f3@~TJVpQ`+lo&%aQ05?BNDHRB5p?uYW@` zYj5g{ZRy{-AAOdce?6E@<(i04goGf={_#>Gwtr4Z9GcuU5SyI7B9=kiTT3f$QkIY) z1ARz{yw{nm6mkkZdbIN#cBn9BFEPdbLUX-W2##kl43e&0xhqUX|9w6FdKFc6L9(h7 zesx7H^^K%U6Ft3}7%i%~LDX|twi@N+pzDasg(5-$Drf$?T1FSKNyNdLVP=P>y$-~0 zL2lx(Ur|g)>(69kc1WXKZn!XXy#kS0HB<~;Po%p?$xJ2Fw1i4-I4pGj)1%vFZeZzL30h)SeK zDk&_Shu6o#0={A#KFBr8_jwZQw%Zi-G%OpJ0IViCFh@f{s#!`_aK)KB4z_#NiGrpH z!h$4K`>VM_t$L3j6T522@ztVT*mvWfQY|3aspD}aE|T|LO{t=Zp_Dm_n)~vBi(eJJ z0bvYUjL3CVl(GjK8zzQZ5h7IB{tYX&U6=JfeplynaOGs8T$XF^@8i2<@cIz4E6nm@ zKxwT407%b9z-u70YEbS)YCuSoyinc8w~T(MzlZ0yA5}{A>0<|D%x8u>iO3Cn%2^#m z>gqU_;R1>9Xl}IN-{Bl++U`Y`gbnc3JzO!-xhR6Y*g;j(!>yy|!%T2B#Hc?%=z-N^(Zi!SIOnVA@2a zn#D`9F=W$qddtmJ>KSJ9JHtH^z2{zLx*@E^V2k0rkpM2dICBN>Cq+ z)Siz3bwYovbiRA58itt{n5K}d3nr891^x2;Wiz8YEI@m7tABOe^`qb`&h6j6w{xI8 zSeptMk#xRqs5C&z%8VEcn{$?Y?C394#sAI(-RbFt#=IO^)OHrzC)8L*-*Q|XutSO{ zZ#`Knj+FE37B(g_rJ<{?ZeE3*nj~kdW3s+FuYL$VWm(5__>?I-U_c_m1iJ%B~@0G zYNdg32n^sKgx(<7QOG2XmKdhbB2+WU%mh^M;);wcn(qYeQN=xY=hIpi0NbBsDC_Lz zx2jf7q^zJ(>4i^- z6W+qqRRfhOOB_3Qs&n$HHhHm? zmVKY*b!GV}WCHk|y%>cDh7X-77oS%VMz}#jh;shtuSYqA*=5fUd$A~oSpT&!2U!X_ ziW%(R|NkOOL0|i#S&CPX4tY2I2zEE*`}hUD34D(O&~my~X<$TJd;6tGN<;FG}CliO6t^h-?*BDxZf&QRn?J3r|B@VqHO3M=gs!kB9|;VGz3quS)nHIFuZ zp4$v3S*bP!Fs+N+#127>xspJ3NRR$vY~3xtU|sVc78ON2wH`0`3*;BqKJYyE+) z9i)#}j)ZhH=#A%cjRTqCWOUzu)P7Z~{p!U=Px>+HedCV7rTOZXD_sBh$c|SZ-aNUh zbJN=k1$;A&!6v`oOuv8~Jdh)2I)`-$!3?-gIGhnj9E87TS{X)0D;TK17aaRW#&~m{fx&&^#SjPu@VB<(Nz5YD`kCOSTzuU@=HOMn8!ViFQ8T z`5&@`@d=*MMtR`t-?{EOK@5ahf?GoS;Zf+bUch-0ee*6nzG+arT8blt1jQrF@6Sb9 zkWk=hpB%UsuURCGDO(UV9~Izyv3we*d#=s&9CoW|;JQKNe*1}1Qx&tbimXTNK#eqO zwa({XMHJgs1X)j!`%^kbpwTO+kW-P@!t-T6Xk=VKz&akGzx=aC1K*wJ?Z*^4kn+P$ zW2(TP8lX7Pm4~lE9#}W6b*?8`7GC0 z&yHKrY1C8y`RseP<}J|jEyxbAHFsEUy$ndA`CQdOK7&yQIWv|F&397-qddT1`~G0t z3GDB}3CQwKqYd0AMmzu9`A1~b1tAogOW*R!Td;ox$&qZTX3p-a-gW#~tc8AF;peBK z(=)LOvedQzNBFTIiYNw1k?{KbgHOEAM2n#33mw{~iLc9Vj)WDl^BfVvvDyLbp~$k; ztSgz#bFBx|4Q?rT3=cTDVs>4uswZwNUW9+cwj}Cm8Z?7AT}`t#O9AL1d&~=$kLUqY zBg)2c+rF*>MB?qi`D`LTq=X{ajiA`fj$q?BZ*Do#`Fe!U2AYN#zFZC$M`=kFrLZ!+ zDrKGy67#zDV8B|%v;f*mNv2Y0-X8vgcb?Hom==7~`*I%&lM0VxfYD=EhYjd1yBIuu zaM#u?H6M67e`ewXP!<6s`&v^d=-)+WI;&YWoVBS~EFW7PAg(YAyoN1y({bSuL)pqM z6BBlyqD9Sc=bPSyqlw5hxPE3g5&+ijne{wVt1>K5l zdb{&5wh|F^du;UQON&#}0ZcriGzZ-FqF7NF+K5?KdE-z4RmZ)UsJ<6Q04D@;mm4#bFEu5%zC4wvbNN~6kje{J6?bi zY`0a$37i{{OG8={wuXOosl-*+Iefs#Qd!a@A_R(kO3{yPWm?IsMqY>(K-1X|2g6@f z`umaBkzFHz&kejOu*M?i5clsC5-`Xq*}+6R)p}zSx3?0S@QrVrPnBej$y?+MO{vFmNv0>`Q&85sxwH?FZNVA>yV(kb_x98I}veyd_WAfh=GT$`E4w z!UV#LoET^DFGNZnZAMXGmcc7sZ>Dh;YRHoMTLDqPRmkfFLkBjxKv~V^bmeGo@8zwmtmiO(q5L`By$i$I zk~x4{11O#xaR-jJ%DGH((^V?jGP01&4*8AlP33RJv+W8bDm^@v!H66PZ#2qXo&g;kkB@C|GY>-cA`K&94}R~0}*rc zc!r7wY!lyCnDvnU-`Rna`tHDP$zKK3-aZ;VX_NIM`CbC@7e7VhB9ID_bC9wkiGP2g zgXAkCCCt(#l=BhA{*Nzk6uIdC|L*C`vi>#lYSsQH;LI19Yv6j>zZMg*3YHUqvLl=Za`CtshRe(U+k6T-Y-7eo=FuIE#QW&m|vq( zdTxEm&VaV<(+v*)lJ5@qx0f!Ln137Ql|z;y``o{h$_# z-1!F<8QQ=>=#CJ-2O8F)N`He2-B15I1(0fFYUkLMVydQF@v<6)6Yn>i z3hF)lR5@m)Vv+Db_r!L;g8BI_Q8>Ls#gD6B=rH~GV5&WB5kaCT-!WpdJuR_+%4|FB z#N$r7J;hHNW+LJ+(}W#qX4|RG(ZTd&Ey0M$shg-xdY5+(g0i4FJIX9G_Cphw_`ak` zOrq$|6jN+ZG+5?FH`na)q;&oz-ksgEjQr8rEz-`uJa>1r7kdrek@58)CpN?*cJv;= z4tnt#Rb-~(!|m3m6BSC{OT}2?8VNH+C0Ejw&IJ@*B4}RvgboLvbb6?C`a7skmw+5T zg&jk?+MU@1Q(%+ioFj_tp6yFx0VrMUFk#3>Uk+MWpfF&nfAEPX0s(qUC93)*F^J@n zf$lN~@FBUbYmpj3QY!$MhmeozLri~>&&O)u-0>(@u$>z?lDXm7ER@&OiYOd0?(%FC zoE9GV;|TX+JlSGqiLt372PxxJ24v!jJ`9cXpL=8>PXy{ItMJr8;egkH5iuF3LB@dRL(QTY_)K*%Df)* zUSg>@MV$t6FVI^|+&!lj%gE##cXOfh+c)oA-PD>4nMQV4g@c7UhoHm{_1AjGn#pJ^ zW%o{~WPD^!!Qklahg2Ndklj(tIqEJFW&Pg>Uob5=O0MhnH5WvWYg ztJ!B@qMG`Y)Bi>u0=3yL>%I~+HYZUPxn8gcYXAVz88Pt1*sp8KnValI;@n&GHk)VU zjoOTiNQCWGL)Nb8JyC&7izs{PJ$d3*whUo6a60IxH2o)P1pQ1@ibgAStq^x*F_z8t zhl93qMN&Ez(L-Bb6P)y`s$RuLuZA$O_ifk1(;ZOb3Ga+nvJxxclSUep01&(C)PP_xw;fZzGsnQt67a+74=8cJ=MLlxpG|z z9$BqniazCU>+!_Il`6Sp^_W#2+xLDyRRexe=t&=`R^HQ&s>PEh_VroXKy~u8FO{Um zR4(AB7g9l)n#8V8)K|k4`d=fT^N{atK3|*l&Ol~hqRxbJ-58&>GB9E=-NI|wJk;aL zjq5&M)%Lg{%&j_VHlQOujk+(B8tf&_saj=a8+Q9Dax*x>cnh-WDPP7}U?{frbi{G7 zeVi9#@uKqWkdZ)sRh3X6cKb7>ToV1Y;^tHq6{WBdL>7T6<$^{VvCZYYE0_Us!>vLD z#RK{fl^#HvpXStDQIKQEi|iJN*~&R-)NrmMnl)Ug_00y+m~5z)jZ6!w(ZNq!blbMj zp6N`+KU?g*0zQT)xr5uPfAxV}uYY|bkIm2qGHT)tgE!4?cc2isZ6l7-7IRVH>-4mJzz9xS%5 ziK;A$wu#Ce`PB5rJ|a~V;rjL%HDhsD0~WXU(Pw-&K^KlNH;TBBuu)XTm{j7un-Sr7 zc+0?u3xxHbeYGYgyrO8ks zqbQM>>>n~nXeh__Jfa^84EGz@V>9-Qr7PiJ$(i+IFQCAbihV!=Vo1;0VJCppmtk9B zMf1PMvJolHq~fVTSHnkzTi%$G#EGjzqFXA~Lg^ylL9H5lF;IUb91a!xi*{yaXPAb@ zs#(cQ2U!ihefsCZ2gqsk?fZPJ!pX_RIkQ?}xP!3X-;v;^Rmlq<2%Zv!qd7V1SFmK^ zBP&56ymBOr^~UD-*qI@7T%gYrIi?C*Z*c?zE`+|}x|A#h#ME^g1V1LjsUbKw?GRWj zWu2ZS-$4ZcyM{-Qb3@$#k_N?t?{>>YEi=kAlLJ-kU;xhMX0FP+XP5vbQPGm1M7Nv_ z5IF$%%(`+D-eQJTm$e(_6|~PN_09!sg-J6B{t}S zU8gQzr)ldhcNCE-{-~V2@|1wh@<%s8>5CYk*X-!xaTi5X_xNHog1>$tIJaHE=`jv^ zd6Z{=Q3-O;^I=31}Y( zoZNCQO)&lI2UWHX?LI@4$n~r60Z9-khHW?7=Me=hz}H|8AM;d!6XqO#S-|qKbXk`z z0M$#9=Y{#I1#2dQJd9`Fc7?}NFGRabUWnnyPju1aqzi6ijP`;weIX{~`%YP%|4qIl zh}iAy1vn3MeKFo+L}pn3`qFULe4)iTmr*xeW1{It#CSWkuG)C+val6#&s{p~;Eqd! zSD(+&jGO=M?84o!8Wsheb2D~_I**%?AFH@$uk@B!7sSYx8_wr@+UfFq`t-E$0s3Xu zC+B6zc=*Th)T&`nbQq(8j(&)hZgmaIz`b+E5afWNt&wS~rF)j%_XN zutO!6KGY!(V*4

    BY{=wtTlfAdMMhvn`ujFIpPcu`>wC2}V)FW-5a~_rT`xNgLaRaH3Q6 zozG0?gG*!II!i?Ipa^Y*bWZ1GBd_1OvxHrf^~~`LtuEaSGy^2iPRpQ81KJM&+8L(v zIBa~mZS2>{Yg~Nw;eoTvl_$~%c3D9pg-|< z9CWq>9*sRs-2~S%3bIa4EHF>mzl6GmizZ{2!qMh9cG860efK4GcZ%p?w1K|I(Cz6> zFRjEkP20L&x&MhSY+@a@722HT(tf*f1%L3=I#Z=$edqY^U}>ik!O7l4Vw^m5+2RW+ zyK^nBlnXnBnn1&B6q#9m4jr~)<2!+S!p*uheis53+PlW%3I6ooX86WQ&t;2tn06ok z()8ny`M$@kFOt-#AF)7$_3^cNcL@}b!g{grw_-&7-YGNyXcG2Ll8257LLeCYo~&Z8 zp>1y@0(xK&f!}q305|!J-7-=21D|-^T+EKMX1FzPr;Q!FE)52s|EZK!HkU9X5yBtT zn0+-WUOqT-F;z+`tA{Q86%zAJ7hwBg)=})i=>X_8-@t{VqU2Fv$TMR=pR#d}sT<*_ z3Ci=2qi@%2Y)4n>&kQN>&}Ki8Bs3Z%l*)B8EZgCE9VVL;XI@8F-Et{w!zF@`AzZ2$ z4@^n2pP}q-Z#@5h;8iGS`rq}2fCO}BudVQ`0c3){-RH2X^@~78UW5oQ0`aN4UyL~P zO}~jt=b9HH7{~BAKo(%0JnJYr&ntjm!8^^Zxkil zP{fU|>#d`URKNW3I{eG9RBY(mh+M2e{H@sln$kpL&s|AotdR(ll6UPfLf9zbR>z45f*(MxFw}p##YX88$|;2m$@F-1p8)5d@+RW?lNuK9&nn)ZDPq`BLYL z0gFE9A6^ip@gaZb!{<<%dDh@1fCFX6^dqDBn*Rz&x%UcY#qT_1jH%8l|I-4OGAc(E zxYHN>VJ>A^ATma-Y)0f$kDDR-&>D$PT_0k9a{vTp{+OV=eaTd$kd(N4za}8i=j07a zYt+Sbkk6y+hZz?T_7{inTxL^v`T<0P=>r&SD=2PgZ~@L^`K<^b$4hJs+9I#_YsBB2 z^9Z{4RVh3%^{TxdEoWQU?h_3>sGe(OM$U?c4G03*f$U4haLyxT|Kpc4occW~W-*01 zOh!ZnGj$^P=g$Je^PuIhpFV`YP=?CG>F*1lrY0)Jdjazqzt?V{k)cakmN@HD7VBdq9U7q09YPIz0T2X+&y2N5XDwe zJGD>izM}sP^zb2z)X#g)Kpv}`pT&ZrP4xfm?#tubDz5$STwh)`-nfkcEq^vevrte9gAf;urf> zhN>=DrLm3})xFDXHY+=sZPlA_>7a^b+_-bay2sXa7ne$2olA1=Y+Y$mY8n1xmOJexY*+nA}>-P8bbqLl}%cRr4B3o{aoe-0S=g)Tb0nS4a$Iyrai zv4QZTmmx)XD0vuv4P;Fk8uOPQ9*jz4Y%Z%1wu@iFWIqPi!!&SNEC7wK(-?Aw* zY(RX%RG5LC486tUH|F{`-TS$Xk4fA+|l(N?ow+&VN+CjKDsx1 zrRMq?R?vLAclO!b!u<1wH7m2L4%ZnCups$s>a~?~$057+5SMc2qXFukqD&PDJi&G) zE_(chD)}&sO@kmG7H>>y#lNxl#V>Ar%G+2I^;tdnXwPty^l$?&fyHxu06Tk7g(Vjiwgx?)z%BUTzhtz zGUB_P=ig{my?@E)j7(#K>KIem;%!b7v{zyF&e=L*!37eyV^*1Q5NDokHL=s1wW0%u@NyE`r#a(sEHbmxRT$uK3$s1cE^ZjN1VeXN!gAzyE@ql>Uv6T zyk25pfgv@7h znClFf#WpAiJc$XLJR_~2+l-rj-V+K_)Q&jveT#e?qy=CKTq1ki^n+^_Q;KLRwHEv5 z$)5r~(nb3T&oTK9fVk!2VioRDz3n#Y0=TT1=9KCC4KZ$Ed-)%^*-%bR_w$+ww}jdc zZT+xW@L~${GM%LGyH&A8E^myZ@1%MmI=6j(69F3tv~EY=3)P|N_^iAZd^FV|IUoCt z$q9u-lg*@Rbh*@O6V8IKR#$G;;V?(3m@?6omu4aXk{9Zh8mTCL%bB7)WJTmP-h z&?&yzqO!KMLAXw%dYJv-hYF2CGHBGv{3O&e*?r40)ymo$9H}P{u`jWN3VMFD9sz}Z z4ZE}Lyq6OJU@W2BWl2uz=zM1#6^95A(d;tlACv0~FPt->tNHjQLH)?O(SZ!7rhI&b z)~nQ7torpUb5~Rba$MP>BG=jx@dhB{rP6G?(&MgPRouEFTf4Clwz8Yd5R$80@ygH* zBQ~G0t5fBNt+(M4oocWd2lF-R+T191-L=L~WH=`~x^|0}IDOlI14?}y54xXh*> zc3TXNi+k4W&(*lYx?T1s3Al@lHM$*!>rsAX5 z{DuwYp-hF#YwpOHeaeCj$9gqcAyBgR8(NZoW_lQ*&7$kVM73VL5fZ*ym;~ti-0I|u zoQo}J^$Ta!=NEE_sI|>e;F<|+rxf^nG<};Pb70O%!0uwzDK+b*1pAI zaU)3{ldLfb8uQ~iked(Ij}@4O1B6L6l%Y}!rJ>K!P7~^5bznxpmw>Q6$Y*+@ z7*=H%bss2zVWLOHw_2@+ZzYq9a!>voN_{Aud0FY=Qt$$t*VWQ2nI4n~8st-Js*_0T z4&JF~tQ`cmS2A6p@6yh7*ST@g5{;XpzOe9u|_`-Q5u%UzvT38gpbvUL>XLeqfN*8dL z=08}h2A#!OZS}Z{{DF(?Q2nsx;$%qA^jfvk^W{Sq-Lvgr2CK-=U;Ig@EBAbQ_RpLB zE=416qtqRJ*g0eT00ba-iRsagX4&-4mw$j9Fw09rLK#Mfkoax0Qd?JCkf+VFSN4RQ zW&Vn&MTavwGt;hFp*Pr!xgn{5!UGg?jAZLZK)ec$jUaSFD zLd)`>X|FV(OD|vi2U~IW($iknDE5BH#!Y@6dp$<%QqAA$NY#_)CBXl$q4|xItTg^p zq$rQNOK6cZF5U_>iq(eHGX18B_nawE?Ugkym%F&I-D|EW(b$6iYHBQ{uAw|DQ#2~e zgW^X5rD}v%Vk!pzVklyxt z$zrKreTGQ6T8czifs`At@+Rii*uArb<}1v_I505q4l4IonU~9aMee`!mHG)S7b8Z? zWrvM94)gVw87(lYfgyDB*3OlyI=5~%h`JxNE$?jKx;evOF-Iq6n5%VnaLOI_QFmWOEc;zigo)!6j_=dcYum_^E*I!PnLVi zQUb&cjMS}AH)4r=h48_+c|r7+dO_~ZI@sla8X)Z)5)X0vvd9OI zW7cAbcR_F}!y{UT-GYL1;sgoy?Ge9TK5(Bf(W{6SngePIIK{R3c zg?m)#I#RXDDjvQ8S9y_*cFiofzRVCn8)+yUxDOpQM2}FSctEmn2Wqizq2}v#Fb`JD z3NT17z6^EtP27c^E_zIDy5R;I;}`Bkozu*gr3J)9EJ9_meIta! zc6q;>368UT60b69VT290Yb41?g;)fU28CIzn4KeIbK$dmEP<6R)u(S#;zD2*D~EiF z%8Vn#K(m`|bu@#iKJ?wadD{zD4cu z9gsAcPUpeKYA`wM7&47>=dz{@qau54{rP^UsL5>HjiWr;sgX;jiLN|1A@M9uN$B+a z>;Y4flvoQ2#xEEW@4>jI^xqcyn_Xqel8ems9B^x`N-SEm{tbWXZq?hF*`SAM97R^` zLr$k$tS)24geSwUP}!Q6?Q~*>&Fe1T+nnCDTCmDPaDW-fQzc%u{R6vJwnBf{ z^ABV)P5%TGtMxr$cYapUk(VT#q%<-vf|rTOn>zj z974+bR*zxds)F-bzM$Z2h!8?j^z-{xz)gC`3foq+X_YFAHm$UG-JSwSlEU4vqNMK* zd-FI*v}MKgS8Z9mWd)eD=Dh7IEmoUlWeO^+^+ZsG%$qAorw?3lvBjcu;f8P4VsN0H zy$^#U+^1ZPt*{@m%?o>cXF*o7UEVTF@$Sbkg6tIboC#|ymSe6-lzb}M(omiTeduE; z9*|}QX?OlZx*INh;2{@6)Aa+0hl)C{pSbIT4S+qv51@axP_7_xTzN%Xf|Dlnkq@~B zW1L!O*P2riOjuwzgV_q|S?Eu7=U$^FH&`t9h%_!J**)9~Jxhp-o^$1vd|qeJ8T!{@ zsjkXy>DSqH{ryUVLD}D*qN(qpwdA=(>cAO$oP0*%S19HO`K{1L?gd4>DAr;uKZbpL zy+zyz@BL~M*k7<>_e-te77Z~ip;HO? z-J=jZ*VC*3wmit2tb(Nj3j{s$AjYbheE~0G0s8r(Txxu2tBCGQNDm_;RWB?vl6gej z^n^WRLvl`Oq%2Gsv%kVM1{t$202yG^m_a;@IbjFRMhYRTSuHFF{qyFgW+s+_mIm_# z4X83@q1WtU3h;U}-3-^W+QHLmSe-kQFGD}Q^O}#3#zf}g*(4_4O}@Y^+{?6D92c5yrg`N&^j^MCe+I}oz$8rs9pY^0+;O03*?c;9#W-NI z6y!P1zt$jj&3?u3$sL+pmuAN&PY2``1e?lsWdT;)sXph{>y2ZZxOF|AZn+Z75Lm{KPRMDeEu zmlMUVXmd{9-uAqeF8Fk|Q0wcyTxL|dOUpe$Tt|EwIz9pgjP+}Gt*UR{44ozN78R{- z=t};fAb_38GB@m>;}`@xRp1JwlLWy4nJWMuhkSCgjrf2bHu~7pIIf8jKM+40G0 z?P9gGunU}$%<Q-K5y$4pzyUQ4UyQug#-?YNE?7n9_8XT>@F-s6dI*T zlROGet`~4l!G15;Xdjza?BG|t3v#vw7U1w>J{tP7PNST``bV6BR+{RUr2GHN7oUE5 zODx8I3;&E#tHpN;#qNXZmv24&bZpBOs>K@N8R2=>fb$z6ykzCPpk4ROlEpC6D1;35 zC)oPKY>{R}wKV`Mn-1GiS!^O`pb>@HGe0t*Wvh>-(wM#0{J4NA4a$ONaq-eBr3&Uv zhR)Y(+{Nwf#cn7xomW!58G=WQ<%-{gZk_SlOfsqpA&9OND~>@h-R*C0_q(y5tb8Qf zSpi`mBlYdvxxXvM*xv*-=TkzF#iPtpIvm9JAy$$a0HENXi4G#q101B90$!%VcaNne zRHSGTlMk>>VktDY)Z!Pvo6nwl8JhL5)}?|?ZFsaVf3C3bJNMzEQJbu(PV9n8smL}3 z+0p04=U55!7Pd`gvWWu_UNW#514KLzoNu#E#$Y?~-Mk%5y5wH=9KpI~?hWC2#r427 z={yRKCHPjH3qio~t&0$#D=KmLM%OzB@xYWgd zg5aPqqPzmKvnecaX$>$kP&W2!mhRpxef#Eo-A}LYDL%EhsN{d1`3*Gu2u^11opO8%T>A?3f8@v9+w?EQ(JjX_^V9 z#Y~hY7E>6FiizEN#eX9Wb_>)np9}@9r6oIvE{W06&`RY$18F31x>$@#AAetIRJ;Iw zb8;;&erd@z&L45IN&FHeXNLZcg`Q#epi6I5#A15!Z6pj~mV_;QNP{U71bJAv6cVJ@ z(X5cSJdGe>0DvEmPt|Zs8g-A>q%ZG0cyHC^Q)A6~lU8RulzcDwmqW%&O=_Jf5*}8o znww%Ko!Vr5`e{r8Dc?iL_i{S3=Q~GeOo_K?Y8EEX!(^7F*BSLqKW6%un~Vl4Q#Lqu z+*H%t61;hbqXC_Iht`= z^<){GaKL|bzYKrF5MIOOuQcj+81q&3>I~QrQfwxLM{wAIW=N=L2W=v|ax70Y?wRV0 z^!P;Ri8Hox(tOn4RKWC8*Q$D_iWCYQ3^q>5V;nF4Es|Uh6UOKo95pm>2!C`vgv{w+ zjF7Gz3elxQ#QEq)CVz-L5D(zspJj_yku_N1!~#!#)!>c`rKnp|;hP0@ttoMq=i;1Q zDSmX7(xg*V3{?fyqy9-zdxf)1{&00OM7Y47^uF$n)+vk?fJ)H_OG6ft6k2@d8FJWd zHh(RH$x=n5c{ZOU0LQSus!@LRiMr%tEcrN2J9P#~(!oqSOjwJ_FC`y>P49 zcr1GrJk|-D#ME2TjFc8E3mmpM%};aFT=OMb13aJRrReKM(FhrkOfHwq*F)LZV}3(S?uN4^3rgBNEn zV5>#8n!TaJVnvNge2Ioc7GWDqS~Huy3q$@wZLIucn1~*Ih_4We__zQSG#WzKt27+2 z7r&>};SBaDj5`{&CGtR_&k!%3QmE`I#qXezm+X|s0oq@$2iytBq2+U#EqU2VT}!iQ zDMAzx4&j^!h4Rz?`3aqTcnF1z@krA^;}!R1ica7CdzaOh=WV*ZCX&G%-rK~F{^)jH z>9W%O_hqY$&a2PsSYx-`dtonb8hp%dFMIiByQ_QkzPs~`s*K_8_(u%BH60h+k=%Lz z+cst>c;X6gX+!n)J0MAGJs7(d_r+peeWmyl@fD(+l)YXoi?KqMVFtDdR31Xi5%2gB z@YL0K?TB+=C+sIJt+nmAEfY54lo6#te0f4Rdf;AT6dNeUsRTvn@NULGt2tQ+OGTgop#EUM^Z7*u5w88XiWkXSW?&TMWHuaiu zB)5IBr>%Ly@AMSGaA<+k-y7O;-qWQe4Nil(x(CV?yyja`^PhveE(5cro%sRRshO~vpoE2-X4Fu`~rJ7TTl()z4Sr5j42U&Zt zVZVa-2HJzOLySg#1vC#y-yKZ>DFie`k3p*|sjtDcz0Cf7iwWw7OgSCOsRC!|F3lC+ zRwuuwc140}XRhv!n<3qC8M|E6BnP(HGqq*cexdukMwHqz=Vqb&Eo&)+K*aR;r#Y zHfdg5zq^Cof1lq*(oJEM(<}Z&*dkzoRE)hgq9=@X8Z|mfU7cD(0o+dosmb^*ils{z zmb?*gn9`y4Bp!i1W1t5o+#riohIr9nx}|~8daI~`R!N4Eq!-yh83b-%!-bkTgRUxu zMUh3`bR=d1(?cYvbjzvXTb1uwHLy)JfSVH4t*wwTRfw52%~Hk@C>20ZCbM>xh-;)u zJVqQ8sqVjT(aR2)5J&8sHQS|(T{|)KIoEF2$Qj*#pT@z~7)*}jF%qZ|CNTT!MeAo{ z4uCf2G%u2wkZ>4dJe2J|v-v!wRi{>bu=rx2JyOnN7M`PB8|FDpaTA!&*=aKa2lOBy;&f($Ie2C60mP|i5lb)Xd z;SL-wj+V_v7v>y`ra&|q`BQp|vG3H0&&}7B+|sY2X$XheD7-7aMN$p6rPCT19ijV< zi8#;)`t&etwpNC6v;QX&DA??GWyGPtAhF*U~eZ;`%&=W$(4BRpA~VwBd}( zrhVBrTzks=htEFe{;K+`tgCI~r?C#+898hB6LUXBTl-#BOGd`~Uq7Al?1Hv7Gh?IR z9GYXm$H3fQ)tM+8C$}F`BYMEBikwZW?)_&zj7BtM_cR8Siw!Q@htW$rCrbWyR+u#B zLe|-}*UpW{`nfmNnb3funMi8eWC_Svw4lEhf|v_=hlb9Ns+7(h1MsiD`mYcsNyXs3i&-=NF`wMbZ!NsdW*`ipfZF` zko;Ein-;V3S7+8U`g@`I_65x$EM_v!u4W|9Oy9(n+$M}3n+U_`nA9))ZVoAWEP9ON z+|Zt*NtjiYzqBq-&LcRa{LWcwwBpR|^>A86Y98@lJBv=$+1f9~D|mnXzv;!Q+RoZr zp8V(ZVsRrEtnNR=b%-$FV!{mzzPJw-J8Saf0tQ6+j2r>s5Z%en=j51f)!6yaO6%cN zvP^gCyRS*48Ka$sUVFCqvNkKb9Ge2V@@yx@KQZ}m@)0$Jeqt)Ed+_sb4T8 z&{7pUzNy3ca@ zk91d@u=yhh1!iok@_$y$OX$}j+{SWY^L(B7Cq=%ZOL3XvmoPtErCg;vPx%q$_hD;q zqw4!=lX^n^vZg?DI~MeH+KaVc(Edorbldd`{WkrphUJD&7?Q^GjlVQCo31gPFz+xY zGF%zEGoH5OSRToYWIkcdvhKD%W~;O%vh-O4S-Y|hXWfgn)i6#Z2m<4y9GT3cN8QG?S*>_zfkxE zsabkSdLO2F`rOyKzwZ8T&pyvH-UjdEMVpI0Q*0`3Dt^Nk_ub`t&i6at|N3+M&Hml~ zBmQss|EHw1WKYSRr9$aI>2&G)WgE(#DeozNH86V0Zz^zY;8J>K-z%HEYv zt$b@`a#h2sy{o>k>Q~K$&HJ0b+5GpG?v^Jb?U8#UZ$vYr1JRqJZ?*nsTV~t3w$HR3 zZx6QL)1m8F-Z9qkv5qfynmadlexu9UHP!XWuIa8HcKu;>;p(-k$5wy2Th-mseYpF@ z?zeihJ-(jyp2?p3dVbqm*BkG>qxXg0|5>wU%@^0Y*X~*SR$o!yVBeelrvA$Qo&D4O z@2o3dcgwoB*GJbsKaf4}v4LM~DBA#eQlc+%n5mwK`dIdu& z4aN84S&t`(rwmWtB0r@o=iyWa9^|o}@*$VKg0kSp>|7GRE#!$mhX17C5+4+D#E%O( zicJ13hm8r@qKJ1r!Y_h*n~;w*^j?p+F7BQ{x_}Ty9!2yGk4>o*tZ*H84B{~AU>7b1 zEK~Jh9&I2fm@tTMZFt`%-pO%)3$F{o`jl`5 zT1~<`4?~5MNOIZh=mO`#~@Ctmk+Wh}w{UGajO!tML&22==h@ zR)pDL_fde=M(D>Ozc9O7(171Z;V+@~KzgE&Ot@4ha?|hm3u!HM)~2L%1xI)?^3?0Z_V&G(SvtNzvLmjaonZL8s;>m zPql$UfpZ7)6aH1Aa1d?r2p)Ud7s|X;Sb;j{!lk|7Tn=YCZ`sY`{r@27 zmiWLyVS>AN2@g|xbr+r;!hj~q{q^wIYa#-yz&an>Ep7>D)6K z1Ls~Kru09ShdV3&ogJmoQapnD9R%THvdc~g)m-y49aXqm5Z)zbU?;xKHt* zq?YtjmXssqOK!<01*M<6Gu)YOo7?HmbJw|Vci-p!lKW}*H{36|f9e6N^{6~rkHKT} z>Q_LO@XJGkw^;+|2@g`Uej*Ltq^+~m34bFb$C&vTv^Jnwk^ zl8=H-}nDkjtmq+>hEMQnmRx zug(9WHtSHE=fv-duZX`?+_I=P_bMKcL`f&vB&U=oNvEmJQPk!^_fzg?QJWv3HX>@H zL2ay_Y)^iwHvSLPX2f%W=Q7VVoZ_IsT?(1_;&3$$5@wsDj({o>(yLIlSxx;e@=9=fEWYg@IXCIlpXZG%s ze>nNp$={v)&B^~d`Nqj#ojh^k@QFhwt~_!1iAzsha$?_!UB|zD{Nu+zcKpWU*B`&` z`1o<_arJTK%wJ~yH1oTe|C;&Q%vWcgnEA@gV>4f#d1U6_XC9h)aOQ!T`)58qbL-3} zXFf4=^URGiH_Ti*bIHuUnbDbTGh1dh&1{(Io#~#bnprlZpV7Vkm)Bo^z5lho*ScTp zd@cH#^A`{N;`6WiU-iCP@M`|gUi;a&G|TA@jr0G?^uiO3k0g|R2abuNh-?z> z(L6VW9y4dNNS*|*H*(CzZ20C)2z`U2L&xllVpb%SfrO$wksTeR@)GuFG!?-mjYx@S z`w~ju=3^zy6m1)BOQ_oh-3dkU(7N*m5!rQQP)hXmA*gxCB_-;~S3fi)P0O(XQ3--l zZ&IR)zE@GqXZr>vVB<(!O6dCrV+fJxo1T0j@`Ylq*wE0B3)o5+qr(Yd-C#oKrpRu* zySftvvP4|4GnsS+(S~LdHo>1xd<;QP%09dKtdNSKZa>1$GR4;-iR0E;*G=;;`SX0 zHVi-#nzD+7E+7%KW>iZlY)2Hp+Z-FBD6v)!tv+x}XBMJukuvu@;TQr-3CSqu!pZ?c z6jhH&ZAZLuYE+JF!9@*{kX!&V4JDe^8*i11Fr6WJ0<-Z16337`s+l*ov#rkcTn7D`y?Z5`e$yuC7!k%c2g0uF`& zcp@_zla9osL?+Nyk+2532L`8=BdtS43DcTPTYA2B)bX0$q_KXkipa*#x-HX`!WX!Tuk7v~6AKt)H%C*;LmM@PP`PHcbqjC0<{V2nQ-1jTMRd zb43MV4_#D>&TG~ZwFY=AO=2gU5rTejAds5!^^?D>;1bMDl8cnK{^Gm3`k#uY+5hI?`+&}oJQc_8-N0mNR?ofm{ ztsYDp9+i~Q*oZfw!k`Lfr;Ns3@W+P0A5KjZ2Wa5`-u8IC z%Zn1)QBOF$6y$fBLI4P{WHp!w8bbww!w7N;B*-yNqZI+6z~2-nT__90(wN2tCZ!3L zFNF(lBhb_||0$sdGm)frZwD1ht++D%jaNp-bV3*ytdtrtpcC|>9EeQknr+opy14r>2Mo63fdMM@T117uXs|tSCPM@*^5Mf}VaR*wCPr zi7J5D#;Z(Z?2|Dc#{?}RSDnb&i=I}Ao+nqRJut1uSVPp$DgPfM>5kJ8*gr$Xgm24ay5;*e*Q;*e(t#Uam54p%FDyEt6r z8{=@1?*a}N`7Y#ek#C&CMZVn}F7i!qxX8B$IBuM8z`gt}(Tool$=()tCkg2kEfK-n zK8&^SQk*H-OL6w|IP`(yT#Up`^SNHa-*}1xvX@d^DtjsVWyq&V&hm2EOA)S+y%gai zh`Vw=zbpA0&+jVPOVO{Ey%hbUNV!tZ?;6=l5w4ZJ6yZ9=T{WNILH@?`J0yE4`t`Dx zq8~=eRdRke$X<$YMD|jI8w1A-d}f??YD6uxw(?oQnf^F&T7w_%JQPI8p@`prejHrfWU(ER2tL|X zf}O1|!w%m{{{3-$f1Eu#_t&`^9*^?X;Z|tuG%0oP--Ac?Z32UH>qLlR!X zo_`g74bb@{Uo{>H<&6sac-#rRtw+o;giOF4g$$qsi$&zGgoebqa;_F?=X0({%5Ib% zM`}rEK@M@qIgJXt0a-Wv1Mm-GudNsUF~nJi_npFiVI1$1LObd(0m#XnMEEH32m%Iz zcRA1bgE>^3lE>*vIW^8kj1F-Cey9f0k7-dXe%wyFfW({z9 zE}SgIHsSNb;+tBn5qC|{uM&8Rqx@aM1#l1GUB=5wK=7|?m!&0Mm}1lyrTYzk7xwN->F`h9_ zwcGKRN?pK6oR`=l^uwjrTaLV_KTZLj<&ZI52Iz+Y@fhBx;IG6(d8Ki@43M{@2LDVN zkysD-(zWO}r}>97X$|-752R~*qqY=K7(L{#)ug@UKT9Atyq3%K>`nU7r+N| zpwHlf^^AO+=@g<)Zpf*7A)8qYUg!t4mf{@096X}}HCV>^OAvje7BXzGG66~L2Gn{5 zXu3&Q2~EdlaD@nZLmTSY0e#~xVKu0u2OMDy>fHydtwReA2piBco4_lEgw4Wv!ugPw z+zP%C6XG}zI4B$vZW6vITr1on92RDTqr$twCxjcYRX7f#3R>tu!2lUEG7~dH{nWxTnU&dC7RzS1*@ZcUW5T20%U==xLwHQM zM);=i5X->{y^G~RL$-hwGKsmFhk02M>~r{-pOwH=R~aj30an2(*)mo|HhozQt7Ua8 z#KNqeH3*+!%h?Ln$eP$n;T^V$HM17T%|}_Qa4%~UKFQiy2kT^A5U%fLJ;GhAm#txI zS)Xt}>u2lOdf`?`2@J3eY$Mym2H6nX%+6!yvn^~Z+s0xn&bG5*Ho`{P4z`o+Vq@$A zb|D*QyV(THnC)d3u}QX%O|kv#Vs;5Tz%C^TSat>b2)mM9#ja)_W!JE4*>&t7JH)PM zhuID62)hyYCVZUTglox;vQOap<6GFRn*9@FRaGrj+zr-*WjET8a$8bvMAZ@By*tj| zY8q-)1G`42;_9CG?(HLSad1rR8&j+czdBXyMrftEz(Z z4!0)d)~4LLlp9L9>G&<`-D4B`r$*)ARt{aTx~g5v3}tmo>U*k|)h!%p!RkmM|ba?x^&;@ zly>K2d}IuPn$hvm-Eg)0_7Crx+7+MT83e24<_K2H%@C{(8RN)ga%|s)yW^=+g4J@Z zgVhbjy_0+P?wOn#+cOa#SH&lGj?3*645so4*6GLh>>L}8kH;rQbSdwiN#ocAGTk>i zOes|WdC!Dq-`MW4@wnWK!CDzX&;r#B@0r*+xt~BLf(h2jC=AwB8AdPKKXx%1c49bH zYDh+RFcgvFhEwn12nQ4;?%xh1mvqg1rY}_G=^=+qP}nwr$(?9^1C|*tX7p>YkU|Rjay_TB|yF>U1UU@?v5D zAi#gig9QNpzx#sB|Fi%1{Qoa`WqKw6z~bmXukwE|5bcxVG`2N#001mG003Yt002aV zZ0}US*v*9i0C1}KkHhsJw190f+07ixZ2@XBpBBLOzc5i3*0K1{`Clx<|JelpfdmQz z0^Y*b#p6F-%zv@`#{+elC*ydxu{ZvYXM*vckNZFH^=qeE+ZuZOcdzl=|7i(;=HTb; z3~f#Si}}CYfb##-dgxdCCOFtTy8r+#A^+u71^_^asJbaN9Tqy4u;eOgen$MYFMjKr&ti>na+jqz-Ybx;jUT7rpi=M zufa(yA-TkdCn1q)EGvM2_hiax`gmi(0EflrdclzrY4)wlE?XoOGM65Zbzu31KryOv zDKlP~=VUIvYc(&_n4V2Nx|(ZkU{Ya`SLxl|_7eInvM;JKdC-~hF59%J{8gZ8s*xA(-Zy@VkPzVn;oDCiUoZ~y zd`=a4_!T~VIKf`-zr{LHRR`Z6oArG{z)^ZL&nGLA+uSoxbS8Ol`V7aokBT3Xo(hP( z+9AA$K0@4d8K?G(+Z{kE=#z$hPB}TJAG|HIE* zTQ)h#44y8HVIs_R_t=|UHjp!==565A(?KYTQlro?#(5^lyUz(WLb73Dy7B!}-xD1P zBH1c+Te}vNYtBs%bFya8%x)LtSejr>!emav;;Tc**d7miFAk0r&T!Ij7OY$jnucxy z%HMehZ4oCYujr8myR;h2H!=^$hH>=^?wg_l19r=c?+gwXnd~g$Cboc^n#T;Gt@e15 zn;uQUSO<7RPYBQesCs?#bF7jh#u$!u`;-2GfOQ>eAgjw|dNTNpOt#&dof28b+4b-D z1fmEtM39qlX9b~H_kRdEv@cz%FS=d&YVOA|qbvJy8))2-CdMgS5Wl}~c^%9v&l3l- zS+#zbDbs7Mcu{2*_CV!qJn2B{UA9m%FVT}&&KZ`nx4;WB%$(@KPfUVSfPtjFo-EwJfkt27^E z8Z)JXmXhG|m;gy3`tV#s08jr&+bll_DV@5LksaIScMWbwYM|7_m z*q7eiB(rN%wd`+50sA4=p8%zW24;l;l4=}Qre-<E_K3s81mK+|tN8@qM z@~FGC@FbM5wrjISp(V$f=I=6`o)0`4&8lfVAS#R~s{pImvBny$#a@WXCicNcM3rwr z`-uMJHht8Q6Am=sG#SWExcG^#6K@)Ywm`%UXh>yIZIxgkcN<5=Rp4C$Hy4XsKO|q6 z8Ah@dL1L9~vD(b4?ty|*nqYZL65V+vT2wCqWK=vUKmSi}pA38d*ZRRP<9Ny^nKR_g zJ!Mr2PCX~Dn0GYi;7d{_r@d3urdBG|ab=$i%To_h)LHWcu9_x}06{$Beo8A2s6@(^4B_=o#4

    Yqh7OdB% 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�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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Regular.woff2 b/frontend/node_modules/katex/dist/fonts/KaTeX_Main-Regular.woff2 new file mode 100644 index 0000000000000000000000000000000000000000..eb24a7ba282b03d830fa6c63ee897d92a5188736 GIT binary patch literal 26272 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�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 bkH82T%!~T~dOL3iZSfI!+IWoKhyte*`46Vs literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Math-BoldItalic.ttf b/frontend/node_modules/katex/dist/fonts/KaTeX_Math-BoldItalic.ttf new file mode 100644 index 0000000000000000000000000000000000000000..728ce7a1e2cb689df32c3a6c26e1bd072dcf2acb GIT binary patch literal 31196 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 T)YS6}E-Q5R&CfXgJ?`xQe`ny2 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Math-BoldItalic.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_Math-BoldItalic.woff new file mode 100644 index 0000000000000000000000000000000000000000..0ae390d74c9f665cf8b1e5ea5483395da7513444 GIT binary patch literal 18668 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�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 J00IC101u*7EU^Fp literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Math-BoldItalic.woff2 b/frontend/node_modules/katex/dist/fonts/KaTeX_Math-BoldItalic.woff2 new file mode 100644 index 0000000000000000000000000000000000000000..29657023adc09956249f6295746c8ce4469b50d3 GIT binary patch literal 16400 zcmV+rK<~eIPew8T0RR9106-7`4gdfE0D43K06(+<0RR9100000000000000000000 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Math-Italic.ttf b/frontend/node_modules/katex/dist/fonts/KaTeX_Math-Italic.ttf new file mode 100644 index 0000000000000000000000000000000000000000..70d559b4e937ca1b805eb39f544cbebe3c58ca6f GIT binary patch literal 31308 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 G#ECDig^RoZ literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Math-Italic.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_Math-Italic.woff new file mode 100644 index 0000000000000000000000000000000000000000..eb5159d4c1ca83fb92b3190223698427df0e010c GIT binary patch literal 18748 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Bold.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Bold.woff new file mode 100644 index 0000000000000000000000000000000000000000..8d47c02d9408d34b2a9d566c0fe0d42bf82fb735 GIT binary patch literal 14408 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Bold.woff2 b/frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Bold.woff2 new file mode 100644 index 0000000000000000000000000000000000000000..cfaa3bda59246b49e94298478d6de3b3208066c8 GIT binary patch literal 12216 zcmV;pFGtXKPew8T0RR91057-z4gdfE0AMHp054wv0RR9100000000000000000000 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 G>;nKVNojrn literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Italic.ttf b/frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Italic.ttf new file mode 100644 index 0000000000000000000000000000000000000000..d5850df98ec19de2eee9ff922ef59586efe471d0 GIT binary patch literal 22364 zcmd6PcVJuBdG9^vPV7BM5a0zs03-+kBme^316-mwMQV_eD3RK-wJa|=@m{eNuh>qL z=aJY>?K*KBgO=rZq>hvJ#p$c<)JfAgZQ|#|X`0upX4rj6CGh>u1t?37owo1wk0%JY z=iYnnIp1FATylitI5T%O$8(EQv#IpZiJL#laeYtW>f+9WOGkPV+hmUGcXAvNc3yIk zO8>0tLmW5#I__`Yb7b$q9m&&|b6mlTL5zEsE)D5ExqY}GtMm()?+%>T?K^nUu~Q?-W4QkS=KIBg!#kJ0cl9f; za$NTT-2eT-rDI1(%6u=*$8oM6S~|FU*SD_v8po~6a-49_k;4~WwEf8VOB}c1Z}9vz zM~?13viqy_M!;K#{!en0OXK);>H@aFDr3voVi{XF{U^K9Y3e%t(==H|pF?9ELzrW+mkOxh*MayZnQ<8%3J+9kWfuQj){R0lg^G4~oL+2Ptjo;^*D-hyxG z+Y5x!Z4{&3K)yp>$7midh0&TqEtiOgRZ58 z5|QeS8B>+_tM9p%HCB1a>(xDBLiuEh$WoOdd2tjq4@7DA;EgW6}RcqS1u~?WwJw(;0Mz`|syvlcEq) z6)88xkAIx#^d@=I)~MH0DwzxtCHLJ=MS&MBa_ReoCwJXXZ6=-avAYSCj5<*uWP17m zIyp(p&v1~Lww15bR{9HWl-s~9a{4cBo}V3Sck=1Rd=G7n#-gB4E)Vq6j6|BeI6ZEU zhp`uT!!cQ2C5eTyi%up@xz=nr8p9Ll>d1p!E~ne$Zq0eJ(U{Ce%H@7UeI8y&_brUp z$b=A{3XwX67&}u2Vi3*YdaptBdhDSBH6K``7k~?i)DfMyJukULLwfjfst-5&93tIT z<4zI1kq<_PO&>mpkxWw^Ls$9qqTb*k^#Y-~I)(bpbz!4I4jytfZS@((FSAjPXcBlr zNduv#yeV(iHyda`5-i;fRrLy`^zZyB`3+H~u0c-Z9$xu6p8|~>T$pR;rn&8$rO&u^ zW~4J23AhYIOg9oxs4N*w(8^-ufj}`)1MZnLFplIhn(S~|mn;*!T%P04db0eicEbb7 zVh^=uV^PqLc%o{sswLA}FiOFixZ-^x=ylr7dXv*^_J+v)qGadk>4&MLvxxMm$uwzs zG~1H$SL>ba;d;gDF{=^D(HrCqW^d4`GpbGWTh-Rs^wPw%fmX-H{ox~B!?nKNls8ag zs#`nEuPLtEGgfnD3|4QziPZ}x6&X*YjeIy)F6kR?VQ4R={~Ll8U=fL4z?14Y6GG=OOaO-8yh4PuNo z5I9hhkqPZGH8pa2oNkxL$vWitXbex3uevkrkytiLo)vZ34qNyp2XV=bfy<}$b#-KhxNipV)7}JX} z9XuN|8;fN;jLpnYY9BeA&pC1=F{zB}sGd$l(!0E&klQdWygcY8-+1giy`DGm2R?i0 zN1whXP#3i6gfEbp^BBbUku+_izl3#?PSkO1bWM(AW|1la#paR1unyn4K1BqG6k?It1D3*TF^$qE4`=7P}hF+5}#2 zwOQqnrUhNtF6xD7m=cHJr@yqDl&3Szs{<>K^D-TQHIYtK8-P`w0UT`Yp%uKSE9iF0!Bq_GFsGMW ztt3fmRGwO8Q#XlNETwODNTOLWbl>@7<{v1z`7VP+ujooYqKa23y=gKU6oCYIf*E^P zuH#?&yjJ$b2>aN zGP!ZI23;&}$mR+}ugEvtU?zwSA|cw3-kTARu(=fUmd~2Y71k!%Q5hXQr4@XcKxylhlNp69I1Qqv0HW{sPbiforvmNwOqov*0*X5Ljb!=3H4oA%~gg%;d><=NRk_Q6#G8 z-Jz*YgOOa--EDd7F>0h&WN5P;4ooMT#5y7wQ&c?tc{)mr&BotgHpGN9hS^#%TZ4to zmIbm-(CwPKg+avn(NeHEicB-A1jCsuYDjN8*uBCizy-FGPS#7xdofg zy=m6WXwn9bsep0_P)5!`37ZjvCNp+0r>f~UAcKD>vypKy1}(-NH^630Lw`gat?UH< z$qV(N_y#}13X54cv0FCxG}ujEqKtY~UcZT2@7#5;PbM|I;Mv@gozjzTC6%&@1=={Q zqcji*CL$0#fHr$DCZl3@6t0O6Ex$1ab|Ph%%Be zLk6KPR7daNs<{wk(C@SHkik5{PS{y0yE4$YFd|2$b3q1cB?4R!tx?@xzG)i5pX;3;@KHC>mO5=Eyj5+>_}bt|<@!_%N;BWCUb zE&Y_~s3V)nz%+txhokHP8toA_w5)h zbahP`Xq%x%AUeAol-5(jy6%`g3z@LynAUCs+;xzFCaw<@>qzN1P|TxQaK=j}0dCkD zCt^(ondD+fWZrczxa80REp`u~sisP~cP7{RYc3jX%lSN(prRO}$)@;V+&H^Mw36zO z*(TWX{+asf`=@O}%UVfjGTVETUW?9sXv^Y`t#?OiMBYflVIo+4iJi6lAQ8i%#zd9p zV1HdFY--;&qTk(96&Ul$gLRW}Q2+Lox9NINKLF}mGz-bp8Dxh$Vv>uXxE#^Qp;j>Z zapiBm!Pu)*-#FV>!>3!!h0itT|LhUw!S}=o<89P;(}P!i*g|yaAAdQQA_OrsBCH8e zD-LSaL$ikvVfDAA<4z6{R)u0rX`l?6?bO&^v3#;q3r{P=(ntkLKynpky z$&{^5R$Ibr+~F!jv7$IJ*Wh;h435J1r`JZ*Mo)EZ4Ka&DEm8XL*9sdyy?0Z}olyKu zfy6K`QOXNFZpUP@zH#fo+Q$xf)Q++CXhtTJOvRaxBh}Y=lGMWz*aD8BQe#TqBXV6u@P2M|p#e>5)a@X=Tvq+u+b$*Jjopsw zJ#CFW;R0w}0~%k6Y`}&1K{<)cndwL-=Wt{kFohl$=p1bg$}l&i6%_VlT5%q&5x)N4 z_hk)!Svo+er}UFLN6^+pu5jK_ee@_Hbu!sZHk2M6dp_RC+vQKly=rF-p%bp$N|Nxr zUiby84?xoCGnhGmm|_?fXDDAEbQoDq2fGZ}0Xgx}tXkfYahLryuD}YF-Hxklk(rZ* z5tE%POT&N7X~S)kx4XCShSBD9zwVwt(d(kNwKv~hb5PY)r4B@tiM7bndA=}T*B=i^ zRi&3`hHTudv~9BKYD2xIsVQ>4ZZhXGrl!5sdZcVki6>@(l<1jod7{yw+S7y_@^+cc zRA-H=s>#w)dW*gTTR@c7I)^J(qatdC^}Za^@(oB!6RdZ5H4gQ7+<>+s3c#`KTmZR? z8TC~e!a3QydHeb?3#miprE6nt)y(xyX;(PaK9@wQ6=JV$BorCYPsvk{%5;Tc4Yd>A(MU@6^91!+wU@I`l``)mFjRQ zAS8)~!#v1ZrYp0EjIa-_{rI0K+YgQ<@0nAMegRY^8>N}a4s$?OHf%6{Xl=?uy$xh5 zNJVV79k}M;=zc{b9@$MwKkvU4o{v!1;o&{@>O#{Li_|s(o+3Q~zayQ935YIOOp|31 zE7Ru~%Oh6(T?nz77EXFtG`W%9L4NcWRRq5H1aW&FdQfwF4?fgFp7w1r=MX_6^QNCi z_CV{LPGr~T?PKmwsUzf{C>S*%A+|5i{~+eC!Ti-{=2t7zo2d(NGe8Nl`cs(ANuHq! zFFg7v@p|sMn>WzX>uNBYJ$owQf&&zW!}!U2v>C2|2mgD>Kn61eSbQFVanjs&KEtNL zN6Rr=S45X0MuWYhQ&GN2T8Xf!ziZcxZvF6)TZXAaT0c@7HH3z; zF8!XnEOc>Q&HCJWICV9`OTQy}ukFCbSks0Fj*f~%weUOiwKdds@{rfE?ZOK7Q23`2 zQ%WanIt?~^Yc8ZklB=4B+`$#hv*N3ZMVetMk^$0j-e-`cWi_?hOS;Jjsjc06C)o$W zc2n};LluSLN$CwD2zT7hlhd<21-&<6+8NAf!iJnK=>I=`VTNH45m|PGP8a?3@jY^DZ zuCkKAFd>?tE(E)*A<5*mEzPNXesYT3MH4ig)(F&+Ub}F?EA9CQrpceuSI$3=eBlXl z6(Rosdr`3~wDbs_T6%(5Z|W}7hzgjSWv?1n2%7?Oc-FLJ=Gx))_n7%tUj?mfYxmL< z;KY;lrTt^} zLGrEEG8-WpagyXko(PH3@OI*`6v!PT6-Dym3k4y}9n5@0s`(q~5`4rd3&JR}YKH1itiCi*#??*=GOaFUf zkBLgXnS-}aA2RW&>HD%3YyBiBI4O=ZbfdUNvlXiZ>h%CxWES~k~)`N7ely1YSzsl54`GTHujOHLv; z9S5InGa=?ZE?K!wqmznCta7p^TgxIcan)rpsXB*da)7epA7Dbp2)Cz!)T)7q5bj;# zk+0ULW(pd;#?BD&;z?Q1yY!LEHg%EKR*#1yjpJ52+$A}j((X?W^+_(bq$uW90_s+Y z`dnI&Tn&!3&(UiLNi@-fdE0fy*wpz(Ld@U4ZR&i~Ct;V%p71%))~~HKHH55;w#0#e z2k`~VtIA3OdxHPa34HQd?Isux`XXe5i~iNIY<6wru3#`z*7c9xsvFp9M0!2il-aV+ zG&|!J%>q9*=h+oDkp9w_$*X(rxp!6ViJ_2H;__%)(Dt=)2PGGK3uX%ytZP{D3K*%%1yPz{fgDZi>CBe zn|=5quc=oii$u3J5b6?*ebv0lE<4AV7C#JY`*o?Lw;UF@+DzP_&XTIn?y6rOG(0*jrl1O6;hiD5i{CG%z4|8Bel z2EcUT%Bl}7FMT|d*}I$2DW|t_lc&~1(=A&UC3jt*dT#H=!v?JPk-z#mPfKBHwJmw& zWU#(X{OOPRQeU7y8FmaWO<;w>V>U629t1|UnuNdyXb|wQ^2}&5n*i=t);W0y3v9#p zI`cV6&KONZ3QhivJC$6x;MH7CRsx!W)g?-QyJKU(AlQ5FAX_8kzAu*^A&JCtc^)B) zd9uK?O7p@_In68$#>aGQGOg|8d8~p$1T`}R4U#2Z#uduy;&u`dh_&gFc5uzk3+h)p zH$DFN9;<{kCkVV8?zuL*lqO^kt$JpSkIMCj$>fEi^2O5n4vT)C+;|BoJyLpDAb&gg z88zLeh+_5lM@qljhqBQ9Rv}P&g3$w|HTn+VWYuM_W~ZZ6(`0mzNaiX$op(xd1W#<#! zUGjAbB^Dy+S~I14WaW<(1D#I@i{9eEu zEEcTNs^?rQQ#3?65Hwacka<3n!|IYN*qR$4KT@idh5DjS{>^Vh@i)JIcK3Q)NjByv z)}2wUh)~|`E&aIkPsA`tX$IprU`6Azl@$#Q2Q7SnA=Gq)MVc;&+41b%`!{aX!r6Fy z^X7Qmx^d$v^6N_UTH0J%5Gn0L3ILc_etf ze%`tva4ZmSqy~QDM*4GFYA6}2^?md<+IlN7rHzaNFHj40fdW>Hrq$yaZQWWD2#zv_ zlGe=Hbjx_HxtdJJ#zXoZdVP9!mb5q<=-OyV*Ud&ruVBoTzkfHz^MHB?jw+Eyr~Lch zS;+5yhje8uLPtP<#O2H)cdxudzDr(3m7P`WIy03zJIXI`aR~lh;d6^L;619@T3(`+ z1fuLhj%TZ)IO4kIqDfA4caM?!s?AD9%yqiuK%J=T43D1Y6vdeA*whb1^`y$#d@!!Y z3MQ&IBzAae$jg+DbO~nuYshfxs;QGI*=Uv1mooUosw!)XjV5_ANlmh&^o1&aeL$>7 zP1R<=b`HvoA>#LGdeQ{#Y5zoVISk{2x#{@XcyArv3SI$ zRewOL3Nu&Bqh(_eJQLx7tPDIkLmndvQ966=uBjc}0|x|Ie}_U#uklTFI`_m(HBH2- zs#4+a9;8E93GgfYo|!GPo89CS;d)DuBztr;^;|4vc6Wh~+n{Q{sN|Jt2mEb5t8GGQ zg{{Iq6Q%)WQS&g>1LYV1ESW}98%8co5i@R^B%z=phk`t6?2f&ilGX35p;n^v2SMD7O zTZbJD7ooOu{?gXTcONQ&l%G%LU)<4Tj>+}98e4XDWfXtOI7hIcTkajbU|k=Utj zPrvL;)B!zWc8|D?pS4L$w}vbzNN`)j6&7w>WfugDB~T8=B`0 zg3N(k{nU|p+tb)d}bwpj{foZ)yrJ4dYn&q&;tnfOM*F3ZKkVtyTg3>|yJE*D0f9tiY z$s?hbMEiyPT}$37vGg6d8?Iyi|nAw4tzcu56pLB(#thOA5 zY5$x!$v*aVZC*e*h!%EHx{KaOX=wuEVJ8Azd0-_=rnS+c7|m_^gS}%iR+3r72Yxcn zBP7aemJv0gHw>99SdfJg*nE(hMw%p7OWbR>$?kAaQieg_J4S=F5C~9VV0D`fQg#~j=b&zUO7i+)+g2c=`l8biI`UZ<79@o<0 zja$v84)1|nE7`fDCfwKZ&ARZ=a3!?oOVh+?NIMq@*|4E|>?4HvMMk|m=KFx!$K7jT zxSEk0i>}2)AgJk@sDigov1zJG;@eF86V~W&*472AX9uzN>~Vf z)@f*zY)`;TK(~3JYAVw1@uONNCEIJ%RmoVD90E` z_L4@6?re$CuSyjYpEDSldEd^8(S5#T=tb60mohCdj*MD{ExeisbN z4Z%+v$Sa&pt9|>O@4G_i#42Ffcr$CxoZ-Jt?h1yE73_+|+dKN$bT(B}HRILiQfr!1 zhTT&=y#t#SDwvnX4t<`4TH5vMj!-bu+27CfC$!Q-tHDRLl5=`QmUCk1@x4KTOOja1 zq!mNcmF)zY=p%b3u*u@=7Lz`bh@_^&k?}NXP9+V7H4U2&n{BC_%gej6h4Z51`6%1n zNR@TnTSvA>?P;F8Mfr4^%)LNHXyU+rDRt>&91$Dk)>PmMYH-EF+A095MJ!^=@ zY$HspQvYDUvaMEmStCrDEcqO*rZ**1DM}UpT-0bch2nKpofQEvbly%h3Ffx6)72@`W)h1ka(%s`h*CUm zG7k(u(gp^^I6oK=3WDen_>CUF{vVMPMnWVQ@&{;dPucP7{?=;7))4H`K^#|w^-EUE z(=nS`UO(=ktfr4@Iy4Bv4l`8Vw*c6(5UxiW!pNBFQpwSpaPx?s^dWgBn-w8=zCKuQ zmW(GJMQHIE#cD`~1QLfE)SL)BwyPR*V!t!3!JJOaiFglG;Ng!DF~EM8Q*uN zj5;22K_ITaCYzPWQh3&Mi2qO>)(nua4UX9gCO zbTI?vY{~cVjI3wDzRP?nG0le(g>j z`Q|OCYNV3HUGJLNX*Ty&UGm$iU88htEYvWjdxgF!kWF*M8~4na%{^5|8IQ?IMx!^Y zEBnsm;;c-jMQNbAMk1DzYmS>~NmkodlVMd!Rx3G}!p;MMhGZ%Ta$S73W^?JUjfFnJ z=(3AeNzw~~8nk+wxF3BYDQ;{r^xA&W4{i%g2ZAH^fl@uQ}V$B z-(%2WMU(sj9IOI#*gXcD!59R=N6LgqSc{baA66D~*T^SMh+^r*tFE$;=bx8^1Alky zQl5Mga^?1vUL^BeB9tP6*`}*a!`CjL8H+TONS+ zF*`syYjxwM!E}``>@w;s`Y7Z~7x($Rir}hI|E)vFP7+To(ja{TsT&FRm@P!|YMI7c zbePs4HqvS9>TWa2I1CfWHAw0Vp&E|1?9^%pZ@G5p^<>9iILHoU4HR1f=$dVm!W0WE z@`4qq(l;?NAy^6|zosXV-`61Ga@izpM?`r~%$clIim}=v^fUvLMvg=}ywP5t=#N?K zePSTmBG_p?wM2peZ=6Ws8n>&e<_ceRfEpq}&}eC;k5sSx1Q8-C2%7$DJJDdMZ*oWJJL;whs`|aJtccCXRem3m+i_tAQiY;>G}avs#e0 z66APqoCw(mPnfCs%hl+xL5;f%D4IATRSi1w{JT-1(JJu~8Q*b zy}lB|jA-%$#8wxwVI86PWKYjDkKLV(7I$oojvuo&50g_fJ!YFhG`72Roe@Ro$!a?o zU!#54k<79R@KeJS5yomp@tQ$j&Le06@0}opU~+sdu-y5dlj9%!=j8Y$S_}R?{I0H( z|0i9i^B<_}l>2stXZmthWz_N@wu2gEWG1`pVYDVu8j?wGAU7_OZ=Gq;^T$XeIjiHR zD@Sk%>#Rt&PH2@pi{{5r4$Q8uYqPLv6S)I#b+85Wd+xcK?n5wiX0iPA1C+gu6W1#G zPjeEgi^@qPd*v09jNKKCkZ5ZR%Y;GLa_n8V{rvpLOUFyc$*)lBFMY#BzRL3^ag=N# z+fR?fUH7_p*;ndOji#)JgfT34>B>Lzb@Z8XxS9NH=wq7lGpLNXcp3Ar9 zCia_YX^}Q(KX}=~)~Tz5sQp~lJKf%~^yx&DUT-(LTWdTAuWD;*ZTHoGYOlTO zj_+4CS23ModuE2A0e;9U&om&D<5)yscd?kAMFCo>s-<1LEZ6YlFu#{f4&9%G|1#jQ1;T`O$6J? zEv`VQsim`)gmpS{`Z+pJHoyWm#!GMIYT=~T2&D9NEYxGoHjavpwod{{!3k}3N3%v+ zY7)fMt4Ufuh~)`whlG(Buu)AHCFO^;?y^JwYZ|9ppN4B0& zV`i2FF+|1npvW!B89#=#H5S2yw3#7FXCzE3o3Pa@ zOsyr)*j39i0Txec4Ho-hZOZSfcK1gN$jJ5?#w?9yo9r?rOba@xdROP=a-^lEwZ3zd zr;U1@KWqqGAN%!56o(Lb&8ev9%ARb%lr4NAXj@2Ddq?sv6F7c3IQ~zdNEUlAXTb5P z@&24Dg5wc5PzV>>hJmDGRm4CRq(jKiv3}eL~N#^tQQm zBpiC9H;wH_WQbgzwx8#04IsjxnG9%cZfu|Rx;yp+{RWD7pYXd7pP6PlZN7*)aiNvm zPKb4WK(vLuNxSmUgI8wz*domH#IqCuPaXqLHUjqv@MJs!X^23cb7fs(+(D*=kf*ZU zj~M}vyM8RG>3)^y3% z&_bl@&Vt?PP!n;458 zsKpJu$jFn4ul&U5Ke}}*G8VTaVLvrr8|eMm#0XZF@i^0>1aKsfJFSjmXA)nQx(b_I zz=bVxWHX*tteUTy5{A;*+v;5`veCSQE6lLABlrH~_BF1W!fuDrS0$aYubV+NCg4?+ zSFTeW+phQMCQX@ez^}8&QR6x*JwgtTL{VZV-=Vu9 z%}#Bfo$7%`d;pxD_XYmuKLq}(e|YJA@WG3;@5S){&-ZHK;$ZJC##@l=AHq89zQNWj zPBkN~)&AMB1B!jxx$8+SS*Anur@V{rcs`|YZ5PQm%b{! zBQMI&$v;r+N}qCE`L!;kdryxynxUD@>Y9Wz2n{wdq3s{h>WylyI$3>7^@~2q*X%p!d$uND^I5;$pY)IWFYk8c+B@4EnZWt)F+?wSi2Rnjf$!%w;n;@b!}J|) zgt#H|H*ov#rMP|{ujdZnS}&f<;J6vrBz)&8-!zVG`1at-+S~BG9p4G<%lhM4j4?-E z=N_l`a>wwk!FMygio2YClbfR(xQ(=yqgub;azi+V@LfYTqR&-anC$14aK0J! zzytI#(B~CoSL}Pj29`AhEiD#zWvjcq*m5_rdPsx}`R1=nEf5DjZbf%_L6+i+iiR(EpU zcz1p~_aW{|?g8#muE;$@T4{|{D=Qd5 z#go0<0;qfLlV78MMPH}i)VEH(cIt0Vy?W}EQ!l@{^UcLKw`s6r(*OLwB9~B$ z+=jWKc~u>IhBL1lD@wDQ=ZaZhv3`DWk9vH=T#-hWo>ic#J9mb6_=3SAH(%ri!h=s@ z)`7)BQ;{T!>f)ZJB29#Y;b2pdPpG?2V0nit3=|y$>f&NynK}mw%MpH{NC(y*Q;Wth z8Ustaio*1m|}2uO^{uE((EFI8WqiO;Ylp*;$FDOP0#I~f6`4@&!(b~DDsU( z*T5W`ujn2asC4kDyVT-~(?ub=`N?|h_#E0fRFsD1f<-k$yQgQZ9BbtkeT(z+ z^FC0kXdKvCT&fr=2~tRBcRZ_xy5PU(#-r^cs@9<7W-!BaL>o+QURr@C?|@#fkyV{ zG&HI!I1LxV5SMUasYrM1DUzK4q$tOmin@f#pfv+6f!l#DfVXdPo^@Fq)S%TTp46GS zfuTY?ct&sxiE{YkeSJUxNyQ`+d>;&LN+rXlFd{HghK(?l$Ju$X^ZduqhIA2#Z?G7JnDmoHl z>*mI0%NKn?Tz6>Ko!DDvAJ{OrY_|^-$x@+cYh)@1(JCxk*pC%IMdAi8_{j9!GSfql zt8g3~#?$|Jx?N%*5tvJ z;P7WuhStv&?csttR5U~UOi=8_g1Y!cua{tP(!mu91x5iU?vbTsr_xybXrnI#@pc18 zS7TGrlUOF~=movmu`035vtxB)Szt$BVp(Lzn#8iij{d~5%#MM?vcitFiDex-HYPxg zGX0CvA}AeJlSQ(?w56$-IP0eS%*_kRH=EA789j6JX!)j^;EI;U55yBloh+lu@H`v8 zAn;QGR|xpAV;K0cV;%5g#|ZFa$0+b)#~AQq$9mw$jt#(%9pk`{9g_*QOH-s&LR~C+ z7gZQNvdCm&3CCiR$!v3?m})GhppPw3g%L>X`zmC3sV&S5`ycHAacnB4S6RGlmWG(b z6j1gy{dLd&jm?x!@*HrNwxTh0;} z!!-wb0D<>?W)aG=)YeqYCz777refQ_*A;@j6W!avBF-IAlj;aF2_Wt0@#7=m5tyJk zI6hcic%(K$TuxB91GdXu^q`vna~jdQEgQK)(J;`s`*<>}s$Iu1X6L!x)MR!(>qUt*#M8)d)0<*Mw7;VfC2*SgQMG4$KS6!i5q_OOkgn`9f;i3qq z3S%b>Ecwu0oQHjQ?=wpP4fa1gywv6kV}@biiGwx^#(SSh00=Y55{w9#AwuBbLEZxi zMqFaviUGmnw_-`(oeRR!wMq*W5QxzVEy7(OQ}>x$MLmp(st$)o*rbe$J*)RLWXhB- za_i@kY8M}Wi@ z!|Fq;6AmVdosGvKeoV%WL(@M9HZU|DhNdNk7B|f@jG~aJ~ZP2n=vX<0@6w;H&2G)l)HnKjfu_EU3o6#y?+rs)0c5N%`r?nPXKdrTm_0wA0*_=b@w#epWjU_fGYwTci zvc^ugac(SKF-nHc>>u_DU$vRw*zP)G0yFokC#=EiHWZgefZnEw-;mO|ecsG}uti$ng zlXduL;z@%R*%l?=lLF<3kTk)U%@-Pr%I+dxH+^i?p*L|z0KYziaFW~xUsq1~jx2L> z;Y2-hfH-TN^eGmB>dWnj$RS^!Tz1}D>i|e9UrXxaQI7r9DNyY<=}{%d;yjE304K5Pow_9t+Z+PpT_;C$;&Hm zm(R74b=*-_84z?hdkEihn_#c^LzOngD))<(HjmoO%ayi(+K0E&7P$f$thA-GuAAr~ za%1JXnalFOF%~~z^s(6!sH+P}d z_Ylrz(Q`kp9KvxoD)uVsMy#F0I^4fEatl^&R!3&lk1@=?gr`-mA0sSryD;KGKsJW< zdbH0~04R2H!@%Vb&e`!Ou-T2V(tw4*-J#9!$3|*8XRJRy z>$!b5YS1vMu=!O`Dv56=S{LE72k>2t<6+>pUxSZP_!6yG8+v9y>wk|{=W>D3`9I1B zHdhySsrE^No=bpaA9o&($1r!9PCbC&zm8w$&Uk)>t4rtb^z4}vnEO&thQXy`C6CD$ zeGhK@3k7^^8dz9se$uXOo z&3ZA~OahOh%^+j5&O$=Qah!t2u)b%*HjcTN4wOe=9D0ALV6eRl*}3zofa(%__d}kS zxE=Uqv%X84C2hujyeYtXUc~kS05T?HN6=2;b0J`0ntTM;E(Cv>OddGH=M*3x1_u8( z&%ktP_KCyaFiV$P@A<`gEMfx+>ms0nia#HQ0-g>K8ep$XcpuJ!{S`K>P&iQgbYU-p z2ez^b`;vUvBjAU9Q?YY3jK5zJ!F%K}NNoew@f%@NngD-Fvp;F*N)~@}2RjH*FKq|T zosjKr{Jp0>*o*>nVhH$+aBIM)wUCi zuP3;txi4~0aVO=A5AAPm?r+wP=}f+S9B8i``zyzSII?u`;F5NhY0rx5_wBxDNg7`| vxMSB6o!d{R_lvXp_oBmwBNy&JaQF~Ey>CB1ec}G{1O4rc+z6#m>$UtJcd~8T literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Italic.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Italic.woff new file mode 100644 index 0000000000000000000000000000000000000000..7e02df963621a5e26d53d510f0b4992eebde1c60 GIT binary patch literal 14112 zcmY*N8~_CPAr3+S{C}f{&j02AoB#i$pu)fm0MN|+NL7AdAl4WWWo&Ec007XE{_u?e z01zlYtsaE2n+qWTz)JfgcWoyao=sRDu?!h9&?2HRX>E`+qQc5#F%)5&pzd_rnwXfE0od zxW>ZP#p6fM;KyG62iG4G^d2_$#y@&g|Hbn5AGQLfXKW2Ue*99w{_uqV0f+%U)6US= z^e5&YKS22a0BDBEqW_44y|c@YyPw#Aeli0TsP7;<>fmJhW6P5CW0&@W2GarHP>+r2 zPOvQ8)ntxeCtH87D@LrYbIh<$E%C{vSg`S@!;9l-Q*6egaae|DGKlupa2~j`FbA@Z z;8++y{c$uMIMpwyIGw#9Oxu55V$nS$q-xc#^>Enxr_(D|dhT?j@_{75~WN_3|aPTGGq58J(aIg^OOHo-GCHG(hHg}!cV4u&8m+k z$04Z_&s=;A+V9WiV0NBPcC))+zD_Z3sJ66Z0V(<4Gpp%wO|8z#Rg`pA)2bO=iQkZWTE70kL;F?jgHXr z=}mWw7KLIH5yY9^08O>KNSYI~`DyF$R-mdH`RRfpDs{q4cKcoG3g8s|s>wM2B>?21TAD|Dp&{xHS82!llIT?pV8{$O~y z_?sRC#U^TCgu13jMtWL<2fWxf+1>QsLF%u_%;OeEbH{TC_nTkoSMG_*=DwhnXR;Yq zL#Vw&L#&^}S5F?@Q_+v55z(a0YDOZ@bJJbr>eZwRSa0B;6_xV-W^H_W3eCsWMJ&jL zs+FIRL3#tJBkH9h$NylEzsOmtX#p*L$hQE;6Kv8i7#uTLJg?o z^dhVZI8Kor^v6^H%hE9=Xg4H$4uFb2zk>Xq7PCm4-kb05mB?S;kS=pU{Uxw0qNx&*dFjDv4+R5w$ z%yAm8b#t&UrNm%iAdBV8lC`b=47K2RmW$MTQ+v0IlF2Vm9CL6!(4al=xW-m>ulu$B zYv{D;QLQ#vQ1#!FlQ8}=YUegYGtTe2^tPWmaXYU#UUAjO#YYyU=wDRGD_aBgamxoC zE~Oq8=FIDON6}ipUM{4XXTv5z-^OsJS+U^oV>6hg#Y@v~Fd$^Xkk1leT}Q&DdnG2C z?tP>BEiXh`Dn`5x5PF;MXKJfqn%_*miaKn4BCA?5H23n2|3p}I-Q6+j6(gKbTS_gN z`M~+Y6&RIs;AvM`N{zkLT~7mAP*qS79~Z&vm%+7oBs6lQ z3K71>F{;gym1?jluWFEV;yV_Ip>Z>8>!H$R#I*5pY3C}h9YKP}eBoX&60zTrh$t#-UEO~fnK08j4`HhY50xHZa4lt zp;&XFCiaa~Cyhciok=A}P<%!lZAO+z<;|DFR%(V; zqUXGvXDyVYqB#6d^{kEo|3&lob=LN=4`bJ}r2;u7%jezH|10o*Lg9?E5Ue4P9Wi&fg4p@LYDL|t%fNxEzG<%by%$OMa7u}8oC7%ZK@TkKz}A% z+_s~1f@`Z>*6dYc0li*B7+Qv{r_jEwQYK4A4W~!J2A-Q`g}0g%Cs?uq1)`1*=J$5_ zxX2*NkgfCjP?ERcf{tU9zSFG_C3{gY9{Y)uf~uH-K&nxW-@KvAEhe0PtU5vR`C+;{ z3RGzuXfm|{P=+;DX8k#2%b_sIv7=0V3#fdCd~MTaK7_E+Z#OBN(4^^=*NFhi(+1Pm zoZPy%0Edfi^h|1+7=rxEM4ay`EjnfdBw&}}c@_=_{bP71_KpJKwa95N1+{boQ^uZ5 zw0GHxvh@LW9Cn(|Q%Opufhxsgeqd)o&X68Dz{9ZBltEj*awb46#jZmNLQrI1*{Bd)kqd7XbeXJkd^-boI^;Vo{A^zyPwv7kygvUr9}28q%lAZm zaAbCfv55J0x2?!dv*GQr3dnlaU}CJTmmPC&{FwvA=S5>uCuU=N&^Wbp@&sgqMNK`Z z1-b?}Wf5p)))Ds<+zc_|A2HPkiXKjj`T@4V!4~%(lxhz(EbnYk#duaCsDkEzfiw4g zR!#5fS?4}RBC}H~wT@piX5wUM>JsH-ACoS`9atz;Z8-HClq=`Q5MLE5ICSQ4Je*hk zA(I?8sz7u{uU1P|-4w+1#rRFe2f#TRPtFM?pa z`3c&)58!(%v<}uQsN=?f1L6!)*$dwZd<1eqze(BQk&D>%bfn$rpnq#ikr}}B9?3#5 zMycq!EhLAP(GQLpEvZqZmY-|Bu~mxM(pmOEvSOB5uk5DaqnJsO+HKs=xFg~hv(W32 zjlpCm!)gDme;B!nz4Ap*H9-L(_3EQb9ideYTc-EaX@5m`=uZ~x`7U&;*Tz93RgUvZmaD^!Z}}g=sx(P}J%StFIU$aaA{q)}4e|(89=}aE{gY3`=i+wdy-kg)fd^WvkV1qw;klHl!HTTIKc~I{&k%sV=9z zC16l=r{6GFN&S6R%XMHosYgtN&B2K#oeuKuJkCcXL)zi&_;DUNCPkDd~13eJep0L zv)FM`gq56s`NnthvUIR1qUPir-?{C;W0i@ze1)dRK(Zy6{QahFe&;~TSyQ}#iDEWZ zT^8M?q-yo*T8VK6p!J;uDiEC#fm7+MwQl?TJxS?#Bcn!&eTX9I?A`PSkKgF4LtC3> z%JcH}c_g46b>(Rz6kldW@0+n#lpY<24(>(P3E|@|+Hpz71mF31* zS30MT>_eKJo1G$rhzI0amZMgaal@)?DK}-}GAiwFf8eR&&bhEp6MlwTp}vFAg7SW$ zq+nHn4^++Tsm1U47Qz;z=Xc!ts`bIDalo#eGxEO8oC%h6e&jk{n{BWXDc!mJRI)if z@>rQdd703@>bn`*8XlqID{WB4+3Z{5FzM4`{Vv_-eKGY_^|aurz_^l+CRQuM-@$r> ztRTpkeG8#Hykuf@;2|ifYQjj&QQdRBbw*-08PC_L?ym1in8Nc~r?3>o4mvtR7sgZY zP9M}hW2mubp?@N2^m_uOfV(Hd4Fnvc@P2M4eOR*n*eO|;70oLK6oryJB1t$IZNe#e zr&Q!)_w(s4l8iQj0;xMDmrR#Qf+xj->t?7*FCA5P5eICU+wneL$Mu zebuHNeBO52g%4XmB3MSp*vB=^H`9cX=?Q=aZ0p|W<_kmZcn)UD+n;m7In>xot}4}^ z6e>-t+k7DU!$1;hB+`?hME?4-JVR67>J#rJ!!f-R!4CiA#h0W#aUc^3bF^h3)qN%M zh#z~k)9bndE`|DSi=bXFU| zmGtJ))uWKOjn~tw{~#BWjWf*U-YOE8|VKa<612P~Aq@KGVyV z=50RxeV6h^fNk@kPyXM)i(>VFo1>?pV4UQAi|vX)Ce_+pYEZYT+Fskip=)W0!dS`u z9we(Dm!CH=P{4?1qC|FJ#I;!HQj3b;PS~u2Rz*H6f}E_1AynkBbEs*FTX)oAk?DXG zgGl1$9sTP(g3|H$`wk5LO<`P`=}o*u)NSA%e7D)CI0kVK3?kE+8%Td+T;n|j1(07P zBqM{7_ou|^8&PP^>PlQo%IbVxTe{vTX=v?Q#w}42)c2Cg-ouVJLA}9&_Pl0sgCEt` z??lL7>u<*pQ)o2>XdgUF5ECvTkb@^wD|VyPZkcq(R#|H5q3bf!!Q$CnS9oSXVwJ;O zjFgl5fz-D=BVq8nmr4|~y|&1@e^<(5o5*^~jmji$n)kJ|g|)4KA>c{`7zRt=+k(Lcjvxe_+;k-NouU198OC#2H|;1G z@#18hH;Jlg-yva1k}fVNvpg1^ZpEZ~Gef98)=ObH&8)zZA-A{oTs3Juww3p_unnLA zhaV&}*yXFi$plw!xD+G=%tt)HdPDGnaU&^w2M}nry?=k&m93SM8r1SMZRanDc7)?H2WUcRZIaT}{|HbMoGOdbB=4NUvxS{whS2Df_q zE;A-bzO}hYfUVb2urUrkcg(_Nh62Yu7v+J#v&OzHtHb5Kx;A%b`StTd32u1)zMLm@ zW?9nktY4Z&TR@Ht<&c|7zr5^j!iJ7alg6xRDcP!FB(gBQks!PMfZlU4r{{J@Z+3rK zatv1M_0d8uBNJW>9i#a`%bP`4+s!s>C#gysl+feCRj&E7M-yc~g@Z89m}@58tD}EO zB`GuSBU+UklNe=XFemj?Hj)tMODV@Ung`oce(9uyZv+Ewj z*60z7Ciwk@7j$zgY*0g>2h)Vh;Otx*)%ur!Njff#bE&WAVy&TBbNVm#ceIfw1D`e_^c=G z!2VbVGWC_*1?T=5i+!?EDVJB!bz7p4*y?#34TX1Z`9L<1+>TM;f|pf=#ED76`0EOL9AIvDhQ~axx^iPAHw_k3Uwb~ z(L8L#PrJ!RY*E||e{wj?Z>##dQ7}DXC=B#MGr&TAoNuz=6)MA)_mzLfU_F%4j|!qb z4Gsm=a=~!D_*Zg{gCN7_*gcG~v0`~&v&MlI2|VGt$-!g{0|;?HULQ!YJ4kXaQ8H{M z51`QexZKqv!tazMX@jk)`ROkIzMdo?%1-|T-aag}`0q}mr~)(cny1aXC%Pc8|F_KV z7|;zo2p?qy+D(d&4~iltbgUbxHgbfiLY3Qd?8H+fY9)vVM0F5Zc*%AXa=8-64xh?I z;w7!Jj9w1S+6d+Kia<>L*M!o!Mz4MhD>kXvG@z7AE1#>q=kO5s*c~u$mD@cE90g&G z)%VPcTeJ@OkeUOI$~tXoCaJU`xrdBZJ7MG!B{`;P{@;?1Pz~*ED9XHRow=8#>dwgg zZ|VJbH-0Zlos=ZNc}bY;EJVx@8HtW72k&`PW_6&5zGmGveiFNN{MGLoJ$I2SQcJN=_xpt2e6mV}G2)@-*_a#nx=a`t;QEY8N2mDCz8O7`Fk6*;c< zE^$PmzX7RU_UvRP{MN0da6Tpf+RAtnlqtT1sDW3n{buO-iacxj#QkRGHM6y~3zQoi8QrQ}$-jLxfVj&V_)wh!~%ChY>Mb1c)0Ul!IS)!VCF$YqYlpa+{ z;$duQ3Kn^dJ5zKp!DucIOEt~1>xp#Wxt`<%=LswA{}BZD^$G#%#~z{*Aj_N*A2$1e z-UFw<=QSO%ZP3nU{*v-5=vSoTIfHe>#gSPKiv+MG3k9M(3(wq%Swv{Y9#&3Bm4B-a zx>XQ9RRU^K|Ip*QozR$M4c-B80JNX`O}P&%OMbr98TTn%{|RDgs7Ln4wA7FZV4G57 z!Oy+U01Dc#xBIjY9~h=gs%FIdW8X$}>>d(6Dtnws2FZUeI*~ZJkYc-L!$$c+4~MVD z_KbOaV>uH_I5!jO`YXNWnn-cE9Zf{qHPF=a;8L}g)F?l!|G=x9F)7gosb3|FXN(z^ z-7mTi21~W|W%KaDUDiz+5owyc=K1+(Xxg1pxAq{w5n^`mqz$-PzO+3`*^pn@IITq8 z>@?N2q$;h=cI=vLrF5$2F1*{GkZi*i61W5fY0#{CO0(|Vr4nXQJ@BhEv3@%09nIsT z%iXd=Vax;&APBKP-_bE&qX3Z<9llPBj3jJg+9>GCF2{4kg|e-&HXfHYmzp{wX@ix|D93gi0B zpKOU<$B$!A6tjWbZ`$B0hrI#CI_y^}t@m*77?jdezDcORGhN75<$ah0x}13Z3>j)w z*e53x)+ComeW|*9?#o2h(uVaCN2T>4Rhi=xS&DtPDEq8f)=1GQ!OK48x61|(!NR@r zg-7>Nb&dvFk-d=Ij&XGrH`)arGHyVPLvm0$gAnsx!xQGA++TB1tUF((j{oNbhVDkv zN99ZbuWE^tEiTyy1KG%nNRvc6ShyF>11WrNnaHJNpho$MCA|92{@ozoQQ}-v(U4%C=ej88XGHfT|-Lv`#SxXn{I}78&N8?tR!H?FC7}X z-Xm-kMUtE(q@T>Q>r{CFT}YL}xx16LYx&<@76tCOozn&nBq8B>*T92R7>F3)jRI@A z3MGt{5ujKr2^i`r&B#ckJEE+${%}wSRm5xAfFN;VgySGI0)fL{rB$Ej~NJ zZ<{aY8v!>a)zD$^p~%L=wWKJSE4 z**529{%oF84x``pIborjSv}<5y2%;`5nd1Eze?$DJ!cGOdIqmGwuxM#nzsGNJu7$V zaASuVavdhvcTXRAQmI4!_^+3)KxcZxq>x0B6ymr|j$J^Q&H7>tMSWU58t|&);}V$P zp$M@22C^Eps62Uub`e92(Fgz*LDiZxfhUpKIewdZ(t3eqrGTOFW@TGWrluuRb|yQe zd(@=Obncv8#0$yTClNROd&%m<3Mc8MxWnA#ZsotBMSLqlT8w=80V->_I*wwr-w^V_ zcwp@uRhu@h!7s#_$iOg@cnmaBpo0r{cG(kx@qnuMa{-A{9oZQ_*Jn_ znj9^}$5ayFb-q?PAL!OpCper@L#e=*jrIA+F+U6>c})o^%UL$=5cd&!5^ zrJJt2**5ayt;W&ACI=xQ2A`L-@m)8#N#nyU@*SP`Y_aD?8!CbyOTaM|9WDs3n+C4O z$Jo)(0*LS$Sguz{vA}?T>DyK5JaKwDW~AO{qi@&3G(^`_jn*m0A}GcZ^a(i+V5n>2 zCZFRET5!i(R=S4g%_zQlf%Xmklhfd+eM#OL$qVTIBQ>eaPBZyCZPxlN6mDse-3IaA z#5g#24~#*f#e48PE+PWN=*|IDLLwtX|6hhKL;cu}oMRRNzuC+^D*VPB>u;NqIB}TF z#Xt0|&|=-f*%#wFz>L|nkFsIN-73`4^T$|jlRlTYY$?lP7c2@ytoVsnDLI@7p222F zQoz_iZs!pl4&gOtCDt8(ECc7f4vQl#T2I+!yZjd`(u7tE!Ck|xYb#YnJ z8HHtrqog`J04OjUNLE`D2gx0UimGXJ7>a;`Q(=Wx_Z7BXZ{Hfc;y2>}MgIYN2r zNgrzncjA0oWMdvwhpN;?6-+$Lr)}fpEw^lp+2nG%Y z^Z^5YEiVgHLJxmK@S=4DXol=nKu60-0)&#<<+osWzB z7`NB)!wTe}0OI?(i~tJo8|fWx3o>j5 zVGYbn#p9+JGJi%xO|;Amc@WBf26Ge-;*@WtKs^nB9eC1$jgUSOBhl8tQx={Wg1@Ap zlWx`i3jB;TEKyOhf8&v`!C+4Q^Q!Qo+qAz`ZUM3K3=1bBzW|c8u{b zMYX8X{+$d;gY<;;Kdmqz{GFmYH6>|`$oarBGe8b$_K`_3?~+smk{8x=j(g5ueM|Lt zxIH zKQE1_vZ>MTVvpa`hly!x6`=|8t!nm6vyzqeutJck*j3~{NC+oq`6eGG8fOjRm9YS& z@n-*EtdicDkM#6LeOYezd*Hl_@o1bo@EF!e=@?GsM@|&xz!BzeDs87bnN35_BNZ3OoPj(A7kwMVK`-XZ|gWXE#4KnxA3PHWYo3yPREb~xlWrrnKRLt zt#7h}F;XO4!o=#HaV89;k0q#&p+*=EFlih31J)Oln!b!A?o6XLE=e2;RE_9B9}X_c zlfu3>KVJ3!>+I`;Hf|y?jPbt0jPTsM&FV;Ao>Hcl%rs2d-U%&Ugj}jI7=&h?9$$%@ zxqx~)+(J&Kge%O&h-9k$wY|eR4p>SsHudUjr-iK{wnA6dqii%{uNB;jHgy!vKmoIYOoMXGNGeE#_H!hT#w*j+XsA;QnK|}^qE7>2V1TI zy(`QT?Ue}?85omVEmP}BDmHAHnt#QR-Vu~zJUM{42rFL5{X=!zk<|?AUA?kxTfxh^ z^U~whq^z>W*x#VJK9|*HX?0{J+hIm+hOpmi_K+xG!6K*yyK0o5o$+dB_ZJ==p?}iK zcv;uak*Lw!?)0#w1+JkHPkn=c@2aMW;oz>$u^RI}&*-_f@@IU<7|r_X?Ahf8ELSjc zu5Vxv(gIJg#S#IR?#r_(1z;go19hVkJK%GHKQwpjxnvx8=n-6X(#(vkhYG1VI@T5B!ik+~dd z;rDF-s7ALQBapmnQHUQ4$71|#Kh}u*N9Vv}Vp;=&PHe?VcXV+t1A+_s&f@my*T5mO z|BWD6;{hhj@Ui_NCL#aKg4ATAdW>vs*H`^hiKgGSTR3MD&Y&QzGRXhN4YRJl+mEC`@8qPK5#Jr6zrA=nVZJpZSb`3MJ(A}sY28Tz` zqbiQfw{mmHFet4EMoAfqN&ohON2I#nz$!-39oLSqNRD_J!mZ>3+Ev}2EBjqrg#KOL zj?xsNU4pKkg;OgAW_6cjcb#8vj2Y3!Rj8X8kXmuI2odVO4WzC_ocxTqDyrxDkXm$# zZiqXroA?5Qjua_Yr|1j~EufZzXzR@mD}QH@4>=G-`FDy*w=NW)7gL>spdny+^+bsf z>AT+oDguzXH<9pQ|$98)n`Xbz!f z9$&9snt+&ASm%YKlfH_Jcr&2EB$PzZGRc%#kt`+#yK2!Icwh~~cQ}kB1P7Ot!tZRrql7P>bX_z z+*aXLC@_|1KVkQHew&f7Iu4n_y$xezX{P`MhbyEA_y=8XxEE?@%}qo|YSv3xUZC^z z0H7TOPLTI|*{7gak^^<>ea>G4@SzE70ElL9A1&jmJqPFRzYIK8C>ySTS4G{;5fF|I zy%Un&`q}UpU%cA%4ba|JrknJvYaw*3Gx?@pUbkd+qr}#|>n$GmUfFo70yZ>%K z+cUOn(KA~&9@@cQY3e>RyGrjMtHN2aBP|P#-;j05!LHkA?uJoD05$*Fgl@oH4BPV` zw-+Vi+|TqFI*iY5jPjxjuk9~=QA_WAN}lpR{!Zn6jimT?|I)kq2D#^7;QM*a2lN9U zfGYs(X9NI%e}D;y`RNJa|9dO=A0hv5;{pT&5dhT#iveGNpn(X0*nzBrB7-u4N`mTw z27@kwL4)anjevuI>w^z~KSLNmbU^GwB0~y7Mnc|0F+k-*okKH2J3$vh-@#DBNWl2P zbiwSwvckH;_QOHJ*~9h1W55f*2f#NWKq81Ecp#J^EFkQVnnlJ# z9z}sdVMK92DMJ}Xr9*WZb)STI}c#h9B>>)99x`rTn^lFJY+n2JXt&!yd1nE ze8!)h|CgH|xQ4ld=_Bwy0T4h=|4YdKOW%3l;GnF)H$O7S|H9*!e#fZMYiUw2vPCLi3W$en>TMr^CBMGYui;{sUN zWv+O*qoRz6$i*eXP>ex%%>I-YTg$(U8K2*LtHc78Vrv6BYIrjO#XSQ8I_mNMC8N9K z=&!Kuw9DN4ySEWp`tRLJdwf*LfQHpl``pqye za2~A*E$F}seICyL<(VlQ1TccFfio_$h{dy+(O(SOO|Px&C+7s8#pG64nzRLIBw#9XDm>a{5g zk5|#Ik&IdrkUn<778bd<4Kv!rzWww*R$WAP;`c&5+vkg=c;^0Y0rMxp`(LISV-Ry6 zSKpj)K47@#1`J^D7e0T*p}Fx{88<7N1wRmnc=MiCDIxGK)@#vx7-*?Q35@#7&Lx=0 z<&@ikGWfPIh>MKQk}FMP?klTSHKek>iU@X_RAb&wdDeRBtXm;qFae$0%GmHig(7uw zp2-4lr(Sats~YG0G69Ah!2mJa%xj^ng3)kV?`GNWh3Bwb6{Xe zpJ#C-{P`Dt3h(ZK58v9qOobV={v3GLODMo zjw2{%+fi5%Pz&7sIasY;uo)(3pp?yion8Lgol=*fdDQbUPSuKxgx5+zgqaTN(FKg){FecFffF zy0qGbEbot9aC=akMN=8#Wu~KpAdm)+bRG0xz$>T@42T;P$AT4vnz@0h#cXzcEV#L3 zHh$6mCF)>G5ydHyM}2hOHko$X79uFhYAj^o%7g`p43m=-Cw~#8kP-%1Oa@4Ld#x#jWp; zlPd?-L9OGPa3Oi%ADe$rixM8&oZ#|2{Kity7uC~K@7 zKa8nJOUPK~ULkhTA(o+xuf|?)rcSdMUk#};q$0(aAIyVLj~1hIXnb?1 zJaW{(bRufv-1#Z6*_WN_^_F@dzcw}FoyS=UCp7gD3Ff+r{7|_woNtS*wltj_uDLZ> zU81&5%Eb!Q!@yaUBzx#;|F%(OG6R1Hyb6kRWOEIcsfX`_iJ9)hIngYgWp|Jb4h$37 z5{$q>)uAq?N0n~p#b<|+ojrE}iTIUN*}mt(D1tsX8&-JmIOsxgmJy{`25-UE7tQLe zB8KN&_9_d7*+z)rHIM7e#YwG8Wn-L4DTRH%i)XqA0B1#P}Im(G(EPa++KP=iBPR^kNOJs^M znzipsXp&ucOmaC@qN!6Y-L6dR)omcxW4+q8lfwVEjFNn+*D3rJ=#1`EJ8Ug29Hg~1 zgtM{B><&zj@>`tQTJ?0NCb!`_O}n(}I;37h%pwHlSq+Kmn@Zj6KCaP&IpDcx$`a(R!=d@nyKl_7ArjQRDY9 zk0XI1yjTb#H`*XH5Q&lyFs2$LX5pD~^kM)MHlq|sNr4e$z8qUMvI;eIq(Y`rgk_5S z9B#H{&PS>@&eQM_(sk1luHQb$l-Eq)}WKoaXaW(g~TZEMfbZs`xgp)pVSMVm-!t zF6OzDw%{E7GpE0M*j^4Gd~M4uOj$j~z>0;exSWWg^BgPKsl%4(tVo|=L!7gyf8dP@Q<%JA#0hdUe1i&NL9(Gm z!xh88gDaj8u!k|ZZvOJgOj3RA>z{$jEK35StR>r-i?Q>4uF}8^07gD47vlO1weL); z;dcbi`l8eUusbomn$W{clr3HAo9#%c4^;dOkGk`vGcehFn5^N$mb{SdfcycPKR>lc z9~>#+A4?VxkVHzv+<)KDqAWwe`3yk}KlQ>I`v@N_>^EKC{pMFM@crz^H}pOTAXx~J z`DZ@{274xyMh0dECi|cb7(h(H(_@4XheB(zu)MGkgf@g{gAU*mW`=WyNdXO7SXr35 zc{c2%j(R1$BkYu!as9#nVDi)&G;1&;4NtXtYsYG)erVejpXFiqB`KZ99d|OeCaHc9 zT1>jhRW6ZKEG9s{z$HBl>rr+-ES!kMAemF`P`Qqqh&nc^kl*{thNvWWE_FgAnx9%> zV>2E_TrDL$(un%FyO)F?P2Z_F7q;S<^E_d$){KE7wxPzjf8%nq2siuGe2!P{Hbi;X zxthRnwq8N4s+V8n5r?H9gMz5mjy@qlsV!FoL`xQ%#O2cgrdwbwhb$T*ooR_-&p z-PD(()YJFNUY`N4(Vg~y>!jVec1MoSni(Y4RMjzuHGC2QzlC~(;_~V>HS?0P~0 z|J3O={fmaA08~Jqr}cr&W~(_){T2Ux>-QPiHK`ey6i9kJAT|SAo;m8zpQMD8_~b+l zMO9^WB{dcI2}|=V*BMU?9hY%a4IS5MxYjMVQQeoVmp+j=-sd5eS>Bfc8MxZ6=Mn9j zu9tp^T%YG*jor`NMSK5`r&)ixU(J@Q`6{V)d|ppy90qfL3`xXeus96Kk&jugwBm~3 z!r~)cOl&smtrz`FNHG3UiZV$n#Y(FdqPxPNS8Fz#aCvtvbjgB%NPsZfn%KbSXVc|3 zktDepxhhOe%Yi;b)5&RyFe}R-ulpc7Cn_VS6Emj+GiwF0ECxag!$h(;-#?^*Ff*rv ZM6wWJ659DkbG}7@mjJD1@jO-Eqc8pH1xbNXy>V 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Regular.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Regular.woff new file mode 100644 index 0000000000000000000000000000000000000000..31b84829b42edae20d0148eeec0d922dad2108c4 GIT binary patch literal 12316 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 DqysK0 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Regular.woff2 b/frontend/node_modules/katex/dist/fonts/KaTeX_SansSerif-Regular.woff2 new file mode 100644 index 0000000000000000000000000000000000000000..a90eea85f6f7bded69ff5d40114447a6d8b48cfe GIT binary patch literal 10344 zcmV-uD3{lFPew8T0RR9104Qhx4gdfE08C&204NXu0RR9100000000000000000000 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 GG{*pT{>~Tx literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Script-Regular.ttf b/frontend/node_modules/katex/dist/fonts/KaTeX_Script-Regular.ttf new file mode 100644 index 0000000000000000000000000000000000000000..fd679bf374af72f2a183b97b40c9c7e9e51fbe5e GIT binary patch literal 16648 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Script-Regular.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_Script-Regular.woff new file mode 100644 index 0000000000000000000000000000000000000000..0e7da821eee0dd05a0a6f0b16c2c1345dc573a84 GIT binary patch literal 10588 zcmY+q1yCJL6E1uXdI;|B?(Xhx!7aeS-Q5Wm+}&M*yIXJz?i$=ZSm5%0_g4M&_trBz zPft&GPi@uCPW5^yOGyEMfKQ>-2O#}-7X|%a{$Kz9FUo4nYybeU>!()r6Gl=nR(&RR z#*Ux5(NE6t2?;=l>`8wmigqQpJ4f729P&*w6OcMdjkMqIspJA1TfR9kA<rRxv8rv&YZSD_>s2I^bx-<*Hf@NhBW^1m%w;1|%>F5}B~X9ZF5G={X29M;BxMFhTbd z5`k!!-|pWIGK3?5+d%Q;xdw}5py&CWUuMe=#Uy{rhAtwA2&MJ=W;J;sF75W zoBj*ZxN!!FwLHC^H#fQt6ZQ9Cmim!j`aBYC73x`KAXxlPEF{JjubWk^yUIuu7T=pI zrgwcA&=OP~g}-hqi!u;pL_Ot;D49K9rb)U^3Nmg#O^^Uy&$|>#mh|z=+hhQ?nP?p~ zpEC`5t1FP)9CqfX^%d{es2ZhY22_3w6{dbYrnCzAfY5DNVN6e(9rPdvs9&}ICu+pL zBS2j4Dw=iJwZYm&8*lvw+(u4E{ry*M?~fCgy{~)qO94cI+teNNL@KFgGhXz5dv<9Z zg`Jb|puA%D`uGWN_E< zs(!mgbkvdOH5!s*&dG!7NyTKuLir2*y#8Q%t%-G)PPd?=g(9=&PL@t?xu*J3bc$(R z|93=og_)7VumP+2im*M;8nW^vo96bUPNlqL_Ui8k=S%X{Pax!|KSfI2LqX!6@n76` zQTU7(4pa>05a)Drs0qd#(Nb_Ai7H?e(InzBemaqQ#KF;sdr8m#7?lq#y*XTimgdE$k$E)CQP*@Z2QccijMdOo7zv#T$ISv@ePU_^W(cL|N4_(vm7Vrc0G^? zYUr=X>fZ06aJaWFNU6^L(sveCtrTOH*!Y)yH50x>O%}gZiRc#y69objn27qN4KME7 z3;ss%Hv9&rCtY8_bApf3NPi5}1SNmgooBrOxMK?FFl9f{;%A*sEtsbsN1ldj7#;oX zu(y*?mZ1ct_aSv<|%VUkoUpC3Eo%pE5TWV`x?zg)c&a2?95c z%Obts)SD_y=J7K{7KFFcLXme_NC=RtOGNrc;@utpFyaNf4#cL0)nutd+nD%P^QtGG zFUh4`i{eiVxr?RYLh3AKo3`*U?siz$t$Ercg*Okm+WxDHrAkbhZqAVjV~W6x4zYm`peZWA(M3ZZzJ0_BQ z(|`RXh(($rL@|iDg2G&R`+a9l{R`3Xi}#AIVZjSUA^PeN<^Zb*h`r9EH(6b1hC#zx z$i3934hX?MBILF{#0*%CeMykFp9;=H=;FJU;yyL>enjmden=Bv3_q<@I1;>qYH^|T zV?Fis^@1MHdyu#uTBJ!@3&0Mk8Cw1`MF2^gw#s3O)?rqdi-QgfR>O)} z_C%nOOE)eFYnVL0+(T^l5^Q10Bn-z(G$j6>cA94`HNpR3?+wG>xiyp>S z$SN-k1j-itq~*)xAmHHCiy}2{^RC0#cZ|no7&#nxjCnAXP`60xH-IZ0*N502iVPOn zzYwF$!OTx5Ph_gy+W4t68*(>{OGp|52&#(PD-j+DfC#`#NA#t+rqv=Qe!bSSKSlg& zlROel{LfFpPp+jg4)!r$|C!}=wM;l(Ig&bULqu8VCg)Owm5A1#3-6x30QiwyQTK1^ z@{wM34jC=Zf8UKcde2acA&G=kQ%TV-d8pvz(az;$^~CRnL<(g%B#x}ve}4;I1}F3B z(b$|qY;mZ<^#%5dvc$Jl--;RIEE=nE0tt~$JxXYGQPHOh=Op$T!=y-^4(U5avzcy1 zmGhS$1-X%RK?NKk>Gno7mK^>!VG{0_o3N<@_1S8{@?++`I2p?4D2D!I{OE(Jo+LmQB85(ZXNk zpZg7NyrJ!pdsBwrVXZnVN4b2mSMN}5vFYS`#T|Jo!}uN^5R3Qad;sAP2x(|DxeLpF zNg)2KMME-nW!Lhty=3e=olEk?u-F_b2}2DRgAkrPl9t`hFXwNVr%5>L88&#hK9&!o z!2?lUL^CU*a2d6!Y_`y$p~t6#PXXyb++WuD8E7npaig> zqF@V$8ga>mo73@gl!w&kt!ciU0g_RF=o;t8vNx-eAl%TxG?OXgWk@-Bdf5h1CszJa zn&DC?2}RPY_GJ42LdyCGrJf#5{VEYA>qYK8x4zY5k~e&xG%m>F79@I0JP1DG@Tmr} zLSmX3C^QYMeigIs?)uP$Zv|qMChDp|!E#6XgAbF0R(U~^f zDRotzeeS28CMge8j*itH&OPBVhvMFjD?D-9JygCp7(CO)Yd`$l&{45-kXwecCf21P z2J^+}goNmDJXlDpo2D$Sv%@PEM_1<2>o*WdC&xJBtaOfaXKApExBZgNtRLTSjEz># z`?wV)A_*KpkwfAQB{nT4a>*7gD}=0=LaM(hpNvE~G>PrLll)r2x6nK0PbAlcEdy8f z&3p)n-B#tP8SAF;C;i0%A?8dHSTD5Cr=tN-N}QXhfgUatngoqnDo}!A|1!%&^Q;W3 zg=Rx92rghTZ^s@>{TgPsi6BpoZLT~E8BE5FBR1Q0XjbWZ*CHVLd4hSPc{zPYLI#eA zwfQ{^h>bB4!d<-6^wbNiOCK?jLpPge+kGHC_F}wt0@UX zP)hsZb{w`e<_(dOXRGn&e6ZdUrdvEl zvovwJG~-(<=Zho3HsJ@GR zq@jAwB*22`h6186C7x zM@=knfezpTzv0xN(jG$r_hr_aCTGt$eqK+gAxtKU;}(cErtj803~>JW!l1{{iB?&{ z8Qv%)38Y0&F?HXT=)s-fBu%WQtf>kKmXz=R^OsoQ>3eMq37`KVmFcps_d3P5+*k2i zv$VV!sGhYM7ek(dhwxSZ&fVqcoQyFC+OGY>@OzC68jFK2!Jas$gSNAaHi6Y+&Q`bi z_4l7Af-6lc0UmkyanJOA$4D>#go?9@zH_&BII_bVr*C#RZeC6^wIycBIIOT$O|9Kt za$>R8rOyn3JAT57ckQWTurTaX9NA5lMN$zHU$KRoSFBY72BO`zA#ox!f1@&I^JMjy zU`P-w!BLWp@_3N-Q)>U|mql$!xRd_tGDLnzclLd+bX(7iL(4Va>iA z%g?8J*+h*GmO)SkCI6|i35#wk?i->Mp`ib5obpvdMl)$pO0KeDT!D^R+sDu}o8ATL zz|~oc4O2D}l%_W@c4@n^c6E#)&HPRse%D!M-j)^ssY6D6+d%-z7rC9Qjn4}-^q85t zk1FHX&x+QP>h1FM4b(dM7v`W>H~Hr`KIH85j(OFAvyaB<`9l}9qlU}eokzva{270u z&tlwLXCyswmmjO5ctnIFY*?==Up>fi^->Q@>AYF;Jt-aePlZ+UT6S*Mfc7XO z#a=o|>@6Ro9=yT2?s?P5og7#~@820J)&7XEfH(>rp7hzSU{r~zF(2jXJeQ3*LYeI{ zqKe1CBOxQBu%{6j6GYig8PM>}*1S0@aze`XoUtPdV?Zg8sizpbvJ>I$_cIOa={ z0uB+!r6ke)>2+C`i-mNIkYU+1^Eem1~|R53BhQ`1%?$eW!M&hj?=)>diYoan@& ztl=P@H!Sj_zIGcv&nf4s>x{G*!lRS3Ftr}yAD&aY5WD*-!PLW9Ewk-*!Rkrq<8J$T zqECCi&c<#m+iBTf!r>t7RY%=!7BomcorLP+hi(^YD4RP_BGTsHisx-#y+RZ&F890@ zVXn%tq0?XY1$88qCz*i6NR4^8n?R8)&5+3iIR^!*zy=%|_$i_;&NQs11S?eZ&H?hL zv4jgtG)3x%IQJI%zD3v#zb<<{WW4)6WPuIln5m4xD|0{POXn@PbGbKK^|>wJvT#l zHtVsb(}W5KU0c`IjW%VFC$WU@H;ZQVN9_Qmzj7w0E}T3$`WIT^Er@6DKb&6ezCTti zD^Ds_oprveL|D$1+}rO_fGQv!V(mi$g*XYQQrrLx#-#4%~6A7t8(5X7w~EQXXRZl(#aMe8d8n+k?7KH|DGU-Vh9 z3=C~&LUYP1M~*IymAi=ws!!bO1A?zQ%7T10#=Sa^D7IaU9kzt=UpA}Kh~F-k!oADj zht(~^1lYOyJ#&er+a>#EE3fz`FS>CCbcW`VXbG?kOs+xoQ^ zaiD^m<@5Cse0&S>$mF-?WhVmB7&l4A%OC8Jb(4!1B`5I}KMC2_56AVd`fe>7^?$}v z4pCnUp#Rcy$vF0d9g%n{MN=4_ujopSDxo?Y$d1g#mtiyCUSH@m z@A}$q(>z}EXxR`?xAjJ?hhu^P>=C30++gG5!Utp3-)878p_a5sac{q@7;m1sYVS=y zqaSD9fd#6B&r{Pieutuu#E~Xlc7q{f4 ze;MyncU{?ZkdY6fhwvGvPO9Ly$Ou2D7%gyn_g`VB($=4%ZGOI1%j~dd8j)DG`~nR7 zUsM6fkicU(wzj4ybQ`OO2HX+B6NG&`*rH#BbhP;zgu1#*`8rno= zi$>BQ>HS!?Qu5&#BffFO6;bz71W=uhX#zuJs{;uI&y(kg|8jG%q7PcD>}cB7wSbsP zD^!~QXqk-JYHeN7fh(_IWwj@u+EiIUOxT};RTf%PJ& zq$a|-`8Dt-3lQJoAoo)!r-gHXf6t9pz#qlPT88W`IE1& ztqSG%N*C(xg37i&Q)SdOm9gn?5A_Ou?Yr=Nnfo)W}f6xdomO3zQhU{|Rkgs{{s za6`7fk3bQ>oB*nB>?7e3DCT&8EAbS1B!USVsOPqSE59!Cay=yPoYURH%p3Mf>yl$foaOdem7pBJwi5 z7B#=4)f2Fd{QPb3eg{zZ2k+Uw9>ueCShr(ste-yLT2X56kXThOH~%W1 z(b|L8)M?9bLzW|bmfB!a!E16RtTDCQ+bn91=9Zuv52Desj2fri`1SAyg%FI~=Bw=V zh5Vs2nBI@O=beq>pG?&aQ6E#asT%oeW)T7VF0kwoq#`VD^TfOuHuMpBbBshhbYTsR zx7pKrVh@g0V}efhtlWRd1P{r&wBMDc#oQEtsBhz;NFH|_L#M|h!yMDPNq8gqFEXv(wUVt1asKR--d;R@)*8O44d&o;ncU&^D<2sH* zmXzx{hcoPJZ?@fsU_e?W7p0fI#uDQ%i;30QS+&>UxC?N;jXEx2wT3hjtH|kCR@JIK z<<>XZTM^z6^5SN;>^ilS1fMHQYo_znwx&3Cy$)d9+eQYDSV!o}q~cH;N20Jb?-FLC zcj**FcR_j}xNPL}potjX$t~M<$ zh7496LOpp_wL&+W^XYZD6t9&l*}a+5aUiT;ABiM%Ks;Bf( zIV0T0+ELW-TzD*e*`_dQ)+%gka4Bc#gt~p{-qmnS%=i05Ob2mWK-j=XU=XK2ium{z zm72i*7h;xUfoWlLb6K(l)>1r>MSx*E>b|^$@d^`k0D_33M_9LUQ@T=;2S98!T7W~s zmK(g;ELWjftjU-|M-W_2b{v_}xD_D9x#Vrlx|S_-=;P$dD{eJ6aMb{!1aJ^bm->6N zC(c|68T@H-`ZmlZm|f3>fhd-d8V#IuXcN{yH&;YuhDk-_u3tEvgh$Y@O@k?%itUwd zK*|qcc2ELa2Fmg@HX%ht4cXYTcz2l?=0EV)I$a>#0XI6YVXFzl3LZWEW8{5gCxUnB zKp4Bx-%Tm-U)mVrI(bi}H|KX6nI@9RI!>7>TH;)oQhVZki~kW{naFu8t@R6DJnAqX zc?{W`>ifYSpPge$Pq?2|PDH(XT2w>!YfTAp7j3F=seem;g4ZUoo;&9r8wiiNmT?O* zfg{c?e3~e{9kv4Pbjd*(|9+7=rilbluN&2hoN|!!S#Ep7x_wxxhhita zNZe^*wR4nB{joj(7D@kwd%!31^+%sW$JR0P+X8owtHN;4?c2Tk>P|}zVT!Rx=*N+F zHHBsnBE=}dI=gJaqRq37$2;844rs5rY)EXoIVV0%8Cwgb1gBaj*Sg>4*8s~Fkj`SV=bL_hG1f(Fc^WrNUYGR8Bep6 zoRU33K1BISNeeDh9g5yqi&YMw3Wr%yc(Q3mw8fE(FAq~RDzg-(3-kBZ+!?GX88wAB z03m+tTK~JZ`3j>2DtSfsh~*n7Qy_m&n*co;MHGhzX#yk|@O3|U z&}j#BiQSWc2^Tmc<6B^uEUpn6alxMjax(92(w)~4XDy5+Vw&J{do0l+3qeH3Q&i-{ z2vLa9Vqm8X7xR{ePLA3$Wl|MaP!WedILJ##1exNKMgsl?Fk=vue3nZ;tDwYy1pw6N z9RPs%1P&nPvn4|MuWtIEp#8t=40sDs4QU4@2+aip2a5t*4f2EY{vr?m1wIae9}ydI z9_b7@4uv1(8ubU7GP)QB2$Kzy?SKA1V{AW@tQsNaR|F8Xce;T&sz0odW!$+10cx(iD?A5yyxc`Uv=#Zrp&1%!lv-3<-ds{x=TBGRyAk z8}I8|7-|X+3MzmVV;3@FF*OB?Kp-L@TtVY(b%owQ&grY+5a3|oV6o7@wHif$J7z3P z`uctok02zP@xf7G;NSq~bdjw-m-t^yBO?f~ISCdpG1@3Iv>zbj0w9%93L=d(?*I5O zN+pkY__+BP{5T7=E&u?|?%?Y^*M4d)d#@`X5mvTqrC^i>W{jS3hDXkC!jCj@Z9cq? zRu@wq`TwPx>GQ)?Iq`V4gpW`3dCt;c`OenI+xJ_n05H^Z1r2cUkC?sS)?WKp6*r@h zjWiI4a`l>CB`y3a*=yOnA7rIN1A(Dy?;1ktddz1@6LMYjotKi)iZ@;B_j`7&dT3Ss zPf~YQ|Q`nA?7$xL9({H zb@l}-H>zF67EzCf_+2AaJ`RP%e+q|)gd_JzKx?XjVT4cyP{1a*I9Ev6s4wNgVuEA} ze%=!!LMPx}*9u4sG(K&)6Dq3woO{ByKB+Jp^MgC?XD>#EX>HR56mf<2#8q$(&f4Q3 zBl{YhFRnIlXRSt=E6MXDWzQ&Y0BGkS!DQniY*#`L40R=+B=nUil7y>s814r`>tE3H z(?vk;pgS@mtWa*qR1vD@1gRDXdJOa7Ws|yj$A>klA?PLM=7;YLu?4%Q*%~{GqbTU} zlSS*&7sW6PjZ*GD#TPLxXP1$!QYAHg59l>me*h%-F zg8d!L7xJfTy@f0ixiMiuy#ApSho-{9SN z(Yrd8Tq^nETv=N#p>XOaoRM9OCB>w)0u&!#+%%2u9X^4N$%GPXIG|P_-gWzf!*lTz zO-cK+m5ZG}^f&b)R7kPx1GlVChfZ1(3u+<559Szfi3yI>T6HDbk5MllAtgC%0fH2! zSQ+qm==JMVR#-ZU*=`3Dy9#L*DrJg4{)bH#azqWD@y|7+EtMbrw^TP%x2bZs3=UPr zeRJxv2?vBJ$=X{QvcwZUbSD;GhLn&Dc9cGECbSf#lpMdGV7IYg7vW4UMxU-GkF!~n z2ys7>a7Ez=8kvV=^LxxyaF1ktv34OV&w#rov~a`|;URHmIoI{sWWEd^5>MJn=t8Lh zRK5%rAmWLz;1X9OVp=&LcBm;zOM6;b+v~|`I$zU2GxH-%v048ob~AJE2bbo) z{_SKr+Yw#6J?bxtgP3QRbsW(^C zWgxti#}rTNixILyk|Z)IL!uI8rpd<85`TdO3uknw`4XbaT~NJVE`?;{T%eJd9@+qN zSY;jhqm+eK?G|K{6@F@5ytE!pB^L7irV2$XcldP_j7c1Vl!V?3UlGPX2ei%jO-o z2Ag(yC&sOwRL8TlBCAOxXfv@`dhv%>eXxCwVoC&b=g7FBWviuL!$edzzhXaqVSc8; zYwQmGH~Ss$kb1&5cUT9b8l5xjjQ`%C3EnDsV^bN3(8T%%D~#BMig{1fTAxz6Apt& zCp;EWNGhv7b#(;NrixMxu$-jijTJi`>(m@vW)b_;d8;8M|H8uO@M7%e3hxX^XWocEV%U8fB%Of*9wiadL~O z+w|}DMVf>;5?(*D)Q+bzIMKL|_*}#r7T~3Xq+wnN(th938z>RzizD0T!?vz*QB8E3 z>^}?MzX849%Uy>1(eHO~y{`-H)Ec_9q;h*jXSNHDi1{oCe8rG^@?p1C3+8%kT_`m| z0|MUNkCl^zVAQHP+Z$Xj9UdGH|C$-RLP{ik{vP(Z-(7F@JCf0W$;nL&_hE)}2oMMm z#-QV$#+S<@;U*G87?*syfBtXy<1Vgm1ELl4HXSNS^Gd%C`3RIc@d0&0VtKjH2-gp z1{)den9_ia%#BQUp&GD(tRYjQB*1;q6$J!egiaD$l9PT%h;eh{-$odL4LZ2lIE?wW zTog{IG}9)|K*_l2-U}+N{Tg}LA#{c>{lhduCVR%HCSWJrA^CO(V_Wr0HXQnG zksCa0#!6(?*=!?Jr*Rt&!@8&bnGgTMw6C{t@Zpgtiqq_9V7c}~9__uk#K~3_dX1XN zQ`?x=Fi9pwio|yLD5h4`G8H;D|qR%B5FScRexJ|K zwjUZ8A_4%^b+>wYKq9reLWM)vruOlG4hib&nw;HS{$AhTKHfasVgH~ER;SXU(Xfuu eEHh;An3ua_Lqs4z1Q@J82nT2kfhQYDH$_Kij|0iTRZ#qY zNZ@1)o(`sckdP20P$0OrPQ{=ic2J5&*+!ChSkp2Rs1rz~I>ZN2PfZP|%j9GmD|WTN@oMZAt6{_tM4>FlNS+!xZI%6m@k(BVdqZ9U7OrP@-QZ zDBh>VZ61-poc=-&g!PsJ<)aAAxd%3xm6)*>1gS0Utr4p)ZAlI?JXYBXhb0M2Hmv4w z`qBcVMq}{1F}fMHSKVYN=uS;BpHyJ$R^uB+H$eF=QH}<*T-c2$aJ@P^7yu2 z-Mtiyoie=cd}N5*+qb!V5<%xkrWzK*;WFon#7YEP0wS@>?8G$DaA^vQhs4lIcYeY# zOaSMYc~2@i9Fed&Z5E%+$CDe(5OhuY1SC}40@d3`7Kb8(>z*gq9R_5(Bg+YzLpT%d zbc8If70x*rfWJQkUFOdur@Q-)w4?wTitCmXB7+f#7!2_Yfdqy^BEukw;gHNIkiw{t z%4j!bLxQj<@wU3>1r@=2&hUIs<(xwW#_yGL4pkU`ZXqbkE3N%bd!wfXcM8hn!k_xEf7SyRgQA1A=+4C%=qEsPwNCU*q>FpVo)B+eG zq>;oqDev=VlLi9N^_`>4o~pQOMeQ(Sx;gN#)mBIEr1>+Ja)A%}-YcKQXCG@`mymo&W)5^&tLay~LFf+whwCM3(5 z@^YFQ`4va_BSXC_yK7CVo7Z3Z`T`IVP`DS+xS6xtXQtT5VD~tw9H^7YTutFHDxph= zyW`Pd6S1spx%M;EuA1R-xw@y0ZmV=6$@n}O2D(ostqhdc*P0eU85$wR*vvNi5Jr%J z?q=omqhKUaWEkhnr0E>CtsQ8ei5EiJ6HKNTI25v?W(=G~NPtqOz+a1Gx^n=<>9T?vmCQ*=yO8M< z;a#H$?prRMCCIg`MNFW%^sH|gV9ahhj&0&BwFqMsxalo3evKTs9 zGgb+0VMGsWMGtF34{Jw{>d+1ynNDkXbZN7-pPnnAN)XT(p7?^o<>qT-5@WU2mOVpln?dBqxix!{90&jvh+{Y+)nUa}VFIzwAo2+s4r4m& z9t4{}A>hjZJV64jNks1nz7Ad>AhcF_>kA!43M@jz`UR;=W%_G3XS z>1n4OV5C$2U0)*N5h)AsqYygj2i+$91GmQ0P`V^ySFToDK^Y2B1jQqm^5q}#Q4ooE zcTOrk#BoK6l70p{mWOMMQxA!D`xA#6iMb{9*7|rU@*EeyD3>vo0XQhIEl;LvI#9aG zuu#a1i9Yh3t2R%~vx_{&NWT->!y#SLtc;P>&KJpho=5W(t0ifvA_GBG6C7m6d35?X zMoTaf*wZ?TU1=)vL9STkWAdXQN#qRaFUDurr!F7)X-qU+dN4ijZcn4NxJ0bBhq(s>o4Xihjly3+c!zuuaj&87ZD9$goQs^~YQsr^m@rGJWG?qzezS^Q0-+@tXZ;ejd z)tF(TponK$x@pp0#1n{C+vh=!L?j-O=e;pCE*+(s8-ZyXOS30xOG$CDm3+uh+i&z{ z2>C7G2SJ|2s%02|y^xWRM?5Kavd}F$;D!Ol=g^VZvN=KfYfXVKGUZ*)!S zq5#|%8Wq+u!&GSD@)*iK5e=uG37#&Z5ij<{MH)vFbtg1Zm^t9EIy-U()4)GaKsTvixfM3|dWjNyLC+>nh80JPP972#z5W{Iwr|?`K|AQN@@rygHVwGw zGjiHaB1?Nkgvrd451uHAB2kArBu4%e#xY8ir3%5n><2ONxZhi9%5#zhh={bb?r#X1 z?Pc(e+LM@prZkqR)0ngpK?GjmQk){*LD3eFNgjdk{5C_x*;JNFrUm7H6qYMwNj%c; z=RZuL@V7DQyCWkm9{EHW^&DC4^4QgM_p6I4AL!B3{Q@!z(18y}Z6k(wGpU#NLH8F~ zCemotWn#oWHuj6)x$N=}z5p)*fgo=)24d6G$LaW&e~K;BU%z zvlMP`aG?&=J(u~?p4{hI%Ec|Ccv^$=#+P-X?AJFjX|pi~4qq+`^$vrxdQEb8LQ!5k zN+Hlx1W)jmiV>bTfrN0=VcWVk39e8UqmUa^&@~=z9G@Ir3<4oOFp9x6BG#z?q!$^4 zG%!Qj5ew~!?4%~pA)K_0!vgBLEP>w}@I)EyJD>iIL|KzsYJDi?dDNg?Sd6#mS4@HE zkZzYZ=_k}u^HPudxOLFO1uWj5y9Tz4pywwXhRq<0Wc>^l*k!DppXx(A|G zfc=leU3WUo)VBwWEb*BK$i+OnR#J!42`qmqFr!!EM)=m`gJq=N!7f#47&3p-zH&&U zt*3<+LTU__&gY7&+=FR21Tm3QY72?@OSms&@N7|$rOMp(X}EB0K(Tt&94!F->jd$f z+$f@4PEx@U<=oYmNvNy+AI?)|<{3v|MbT)P784gF(7^h3Q5m3YTbFsYYp%L$B{(!) zVCKv)s(#4oe}dXO@!E!>tJ|e|Q8A;D^f(cS30RWYz$GQLN)>_ib_wOY&8j-TDF4Mgkk_bf zblNF1*Cf8;Rv)+2+;;4QRlWc9`x}c|Hxp6ZC&UprfRjt>jLX!{-Eq>c5F8xV0pRkv zDerr9z0P8-z8+O76IsP4rf;}Z{nAIMoty<*^3XB|Zfhe!bG2Yf)pA5r)lCpdjYk#s z+oh6ylND?pt8;gsCW+>!sS|12c;rqHhk06UBQ1kZlcTJXuDJuR9N|eH54OZol^s&p z?ua?^l&k@Hh!nKXRN9C6tuuG$O0}&~@QF4IC9j}VmXzp9Glz2P$xYs_Rq5vdW#9t9 z$GWFm*KLbfI)lot$dN3;nLcQ#Pim=iM8bCzAmpsN zuTQYta*L{!p>gwMNHj~y<7R_8(K`(5&IWEBac^`i+kcB=x)jAeHHJo&645-AJVujC+Cd|1`ua-u|)WswBqFie%u;LaR1v|YKR5T?s{6m$K z%eh=~%B_$(N7HW8!=aZ3Sh4C%>XIlC!n#BiF(~F!jU)C_iw`zW$qF|RoiouNdHzxrTctQyH*djI0mA)w__Wv3&6vKc~oI6da(fH)qf z7Y_Pvoap%otehAq*O5bHgOWzV)mr+zm|L$!_;uXR2zl6;mhP$YT=3Fr#ckD|VYPi9 z?5Jm2$rD9%)p*8bp4S3hpv0Q_xb#F2sF;%$9w4;!f036uH$x@Y-V^oy-A)tfhfa7( zoIw-#JK1J6RE=V3Id@4&#Y3x0bOG+g0_*51tQJIcxy)tA(x})S^59Wr1vKG##Vau} zIlRYO|7+(Hgw)}>J5vW)+HEVp%p6Kd&R-0ng8HcDm&1qs07=-hA+R(jefmi_(1%^} zMrs0#hYs(h0@97KCzE$EN~yJ}U`sl12Xpl*VyL-|ut~ZPG7I|+tB~w!?Iep@-huJX zQiTdTv|In~$SK1m!5Y<`JU!_Lwr-i$agxEcEdi&_B9hiWN;F5-+A*L-tDDt9rG@>u zMz8*{2()GAjN4|cRN9)_K3RQ!@6?;CuB_h=5d;h~trX;x@Hyj4HOpRIqh*B)Cf@aM z&T*^LNI+x=2@oFx0)lBac0Rpf}X(eM5@Z+|s&t;4ijacmFz&N1Sv>9Q5~F9Ssa}pKf7rE{@BCR6ig>|*IB}d2Gd{`2F_@r zkc%KT2)+X}bmLKkA_?NCbnkt=rvauSwI}fzDu7QHheN(cw-2$whuBBzWWnyw?*wA6 z6y#9RJGs6$9KRVd0u1W4B)NU{a#jHv}r-EfxIb_q_ghN)Kp#bwcV#_Zhxo= z&f`-5E`mDf^T0iy7md! zOun*+UvW`so2MkeZj?e5VENx`MKP|yr5HvSM0T9}RC~zXto^$sA-O$g%M<2391uK& zen>3c1Vbd%%$;UYu)=sfL`z)r`FUUJ%FS}Kwl}S$@n4Cu#2n21Z+aq}29rZ#&DiD) zHunCPRqpY+GB!3%+yrof%2CBL&lU6 zOU!^m#eSnAmNrP;c>Rf%_*bNs+Ke2HW5wa@w79t<;sioJ%Y)H16#8rC)LA%Vapi|y z3+{H;+ZeNSZy{UQy`g$+Ds0WTD;_4qcn(_H6-$xiR@!<&l$Z#AcH}GZMD>ib(I=*KHt&6 zjmStql4R}F7w1>emy!c$M|}6H2QTa0B9QQ5{(Np>*xfRuNbLf$5Jd{?~Dp4&;10vzcI4O|d$fxh3tbpo;{J(A5nTTHSE zPNXy8bS0G{z$tt3e0N1GYH~Co?$0Af7N#las5^1dVZDW%oIKLBMOYkEQ$PE#Cb^oG z`b71jHJ*W#N!jF+2p-7h9UZJJZ3(5Hl61_d7Sr3;)aE(ML;j#YJuW+~5erHgpwq5EHes4%5h z$rqd^Uvo5;^?Is0r%~C~Qd#2hhnJX)2ibIH9Q8`muIFJu>JY5=|CYQ;F*UU}UX-v9 zXC>uVv~*N)tKN_7CLn~;OhxkC`)?xeOpK;k8auh+`dpHhG{PY0}_m zBzeuYuN`!)BKc4iBBiC({nKVJMw*U>0lfLU8yz?Mr>?u+N|;)7AdRLc0%tdblU=z7 zYV} zXb{h7InS@PDpr>;=>gTvbV2O0!^O1(UDX{<$B}t`AzS`mxEJK^;|?sBa6b+<<(3}a zz{Nz-?K9TWXnnvF+Bg6BE`&NyffRa*{CBeK+E~$8$(+J!6L6fDog6^ zF8{9N&;o`}Th8Sh|J=Z@T%%^Q%b|IsPtkH@?G7g;7NK zp_#ReURAoy;57CzN^=R2jKC3?-p6k*t`E=e@hE;@%28e4k%hq8=+1cv_53pk9VRJK z0a+t6@F^(!_<3yJ;ez?i$J=+-)X00X-Jw%i-X1G6At{A1>ss{TPNPfIf^!M-I7~|* zMe$3&Q#m*Hz4IeAN12__mfAB`J>7GNB`|*2PruUg#J32=oP~#9BY}QFkyYbnP1qg` ziFnUB12q+QV)dP64*V~BQou~Ma^lv;OXR$S{Ir6NUbn5~f5P!Db4ib@M9z3Hs(_o8 zb!>v@hk}0Qa$H39E;D)RETPep#hk>O?R=#AGtDb+Kb?{|rWo6%{XQqOa%obQ*EGD^ z9n1<+2FcP6z2!AU>Z8f+|9fw(-)7SR@Vk$7tD{_hu9Jijrj_||(4PCUi_7xX$OL+x zlV>r8 zF_y_Dn6u>4x{TVLB#nerFpWeLYn-vS#dfQUW})X4W%GsXii(OzWP!RtUODEJzj7T9 z!~^V$D|7iuLH0>{sZ)N;e2Vf~8WsODU{9J!Yw1rB62v~HE z^SN=(;$@XtD=&P;V+Ki5!1rIAkdUoskINp){vPtxsr`4wR4D>BhZ6N=kbl{8Bq?!D zy;A8&jH4qGNV1^Jza*vw5Fl8#f~3s24$yq#GO;(+>)DP8pyX1GUIHPZw)STnE~Izx?>qNu9SWz>a|hh*Q(J=3tO{yY8GIIDrTTbT`Z8gK zp*89!FkbZjxrOW?nZl*GQg>c4rL4q$`<&-je1f2;ulkPdcxE(ct9ojFfbp>~KeR$Q z*vMV;Q&Y-`3TfM_BzLc^`6}zyS8%AAD0ZX>H>G6W^{|#Sa(?8-_q?2x?64DA&Qs}d z5(Sqv%74ya21Ar51`VMV2L%L&eXzun#`>v(@3MG-dj)f6hGcLT<=BqF5`CCs2D9F4(?ni>g+qBA! z;E5YvyV++5RV-Xf1XrS1xDdxi?wmQ`XjM6n?Q(dmO;sO!u=<2J0;BKOSoa7AShlbE z!nkkKo3n&_FXNv-V5VjZj?I)bxIGsMJ%Y{^W&|V-%{r)`zgKCnSPTBM_|+nq|@3gXH|CT3&HPpzc*Gt z5Fx%J1UNRIIDahoq?e}){YHToZocwqW6Na#E&OYAm>q5ZDjJ_X`c7I+Cd<&pCHdO} zW^+V4L`wDv6HcDM8yXaAq{%mzw0BxkUd@>lH?=tiilnyE!y9S_hpO1PO_C{U!)d7K>jFqLzB!bA$}N#T}rhO%WzB$tNZ z5<)69R=jL#DNzk*^quCF8p|1!snW5B3{MXj%b6BL0K?=nfVQ0EsMyZIemipr-y_WN zXY+*I`k~hQ)3$q@)-}-kiMXL{N9XtNPupO4N06MtH8giNtvmKJzWB`()(nhdMiIW$ zcD*j%Gi@GUVe}nY;EyL%wy+`yeJ1>r>AYS&kJ^k-XdYn>(=vxKzWyenfp1ZLJa0BL z{;Dz0?`Yg|TU=C6{1{{&?8z-ZlbJ9_!rl0i#-Vjx63|2dJPTuA1~LU~lx{P5d|#H8 z;QEHldx}q>pWF&(hrg9daL}9;()gl74D!^9`9HUWhOkb*@`l_tt$USC?IrT}S5102iBo!l%tW&a7FX==nDe`5uJQ z+|^eBo#*Io&RNJif2U^93KBQ1nB_W2DT*eD@0=WZ?$yb8LPB_zNyw7N8U$s*hgnV& zLQxj7mgik-IH6`i;CUE*-&oJ*9;kci{zG!GhPFx*bh1UamHPl7?_D*^G5@*zw@Y$C z{yzlw?7EjB@ePPU^cDm`kgWP0`8{4=is|doj^U0$?YO2&T*m^CWKhog=!Bc1FaQ2v5 zv0z*Yg|j&vzz^56;*%W7^@2Ovy0P0kI(=*)n6}V2`la7<$B*n;>qcv*cQut7^em76 zy4$Pyene%)5k6Wbba){>b$0#h_gW*O0)XxdKhfVe(8wwJr*e=loJ$tY_dhq9;@^Mw zYj4E||8_t}laGsB3q@-t1TJWL<`Ad)Q*@id!4CfX5RoZau9F&jBqR=5Lr0ZMp!8^l zn0ZZdW-6>Dsn0FK#k(PP%_JpPZ9{ylDSs8s5y+6ChyNn2oA?^uUNK|zL#9ll${8K; ziu}wImRN*<9w+=CLQTzmk@fuelmU~5W}0CLP@_3GVoh`aB1bx4Y!^BZ9#=b18HMP; z*ox_%_|pznbb|T&%9fiSvl}pIo?%@&bQ&d=p+#ol>u9bZU(Q%)sZq?K%?O9+PZ;J7 z+e8Z&N?CcgPfdj`{#318G>KAB#YCgkk7*^p&peeUQ7Hs98l{p@F_=V1>DggSubA&L z@BuYC62q!$lciLeKe+;8QTLH^x@(w4m86E@$PD;eDkcg`F}jL&P>eZ$KSerf@W zY!uKBNAlrj>iPom9DqSUI})<2_Zvb$j%PVob5S#6SyM9!tt>-7O@$6LFFGa8rk@fQ isFOeq9&M@oI}Pp55h!41eSwD&UH=U4=~t{3ha6jZwt}$$ literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Size1-Regular.ttf b/frontend/node_modules/katex/dist/fonts/KaTeX_Size1-Regular.ttf new file mode 100644 index 0000000000000000000000000000000000000000..871fd7d19d8658f64d8696ed9cdfc82c821ed76d GIT binary patch literal 12228 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Size1-Regular.woff2 b/frontend/node_modules/katex/dist/fonts/KaTeX_Size1-Regular.woff2 new file mode 100644 index 0000000000000000000000000000000000000000..c5a8462fbfe2c39a7c1857b9e296e62500a8a8a5 GIT binary patch literal 5468 zcmV-i6{G5RPew8T0RR9102N#S4gdfE059|a02KrP0RR9100000000000000000000 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 a^|k5z`r34UeQg~YeP3G~_EX$#+W!Ytlnjvo literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Size2-Regular.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_Size2-Regular.woff new file mode 100644 index 0000000000000000000000000000000000000000..d241d9be2d317f7b39b401d96c8b18836acea0fa GIT binary patch literal 6188 zcmY*-Wmr^E*Y+6(7?70iZijA=W+(wk0YMlTS~>(q>268sE(N4Zy1PrdK^jF-K;Rvp z=lSt{_rC7ytaa}d`}UB~OWk`e#{P@sSU`2U{Jpa1p$+5bPD>+%W!0A3qP)kF~v zGf(-2a5Q%T0DN4OACF>RPDHl~;*AFb0Fch1{6{GMr>eD!jU&p;0su@@K0dAm&o$D< z+#Qum!Gemx`X32x9DJ++0Hg>2IAW+8_@PV_{kB%-mH>czfr=6NM~ffwi?%2cbrw`T zfF4B_>~|nPTSpIXl*WPb-B8SVa|#-Fa7LiwaR0^W{G$;}kJ!=N8`T&09m=OgkpXDM zA9XT!v_kdUMD@-C0Q3N}S-)BrXLk<(AP)clARnc(xRhi$xVTxNa!CzQ8WP1UzedSM z@8vxMjCU(Tbqgnt9F`KfjW_$^_)}<|prbsODe39-$!}w=Z^G^6KH7JQ`UxinfWyt4l!nK!=qM~h7r zCW1QJjz6U?x32rkgr6RZo8Ur@3sZuzs`i%rG@qWnI|~y}(!#h!WMWWS*@!oKzD6yB z+a}~X!E*Ka`F1|-(xi-ggYR#VWiXTFG*Hd(D#^pri#bh(p%#NFGp|?;2I20nDb%l* z8A!B0jp9!)y!ookAFp?RNwYuvvc%1$EJ!f7VGE!Zz z7;RS+D~RsBntPrb5pMUzM+M3`zkUg_iJ2vgZ70E4=~QI%!X{;nHJUF(bk=;6Y zbripTbq(eu)8~9Vcuwccr?<%9vNiEa+$cX!I7U6{UUS9aA-=j&IEc()M4xcFi>bmA1+YIQCMWjLzWfr*g(x9Gi`5Jly?pcDOh3|*{^ZYZeZ6n2 zIqSI_dCN`DxyY1}htDc?D`!_XFlw54wV;|s61HQB176>{bdEA5I#+)^k-DIp24A>_ zlT9zHl4|>L`5HmmSz8I}lE0m5YHwL^7568kx?-Ov&Twe#$%-W6Z|n+S-Ky7S{iTIy zFQEm3m*jb4N(v99LM(xU<_xB;1@>5hKk0e;BEQ&%R;=9kAr|bO+j5tVYnP| zkX=(;m=$R7`I8DMmnXvv{1#D3vRUZ4!-N;jG#r{iSavB`GHSO9Uy+P`s(yWG>=^Q@ z&Sgvnuf*El6!;RgQ_~m7&>L-2TyyEs>(u6GwY4;U@En)xGN)~ngf`^F@LCS&_+mX1 zI6(jS(wc?jEclsX&5@E6BU|}-guWZ&YEE-4hRrf1TS0G1kZoGcm%~i`%4wA%A|-m7 zczac11RX>kSFJ>+#k+sCLABwTuR>>7#}H*hfhW^|0M-Ecv5W$v9>43~5?6amS$Al5 z%v_|<6$4$HV9AEh5dT6_YPYgzkL*1N$>myI%;;a>sdLIS`c54IMyxbgv6NIY|R=&m; z+2sT#AQ1=)@pOrf{O&&^;dGw`V$zOo2JZb*Qe>>Y-0MoC9*+~ zLZ3Es@y1RUS1ws(!I4fa=2S{8rYg6)y4#Y_>_y^`fH|yd{F|{`ip2+`+>d-I zKE;HKkNJKVh|{xB+LE+gQW8!KGlofeiK);$XOjC6#A31BBfC6pgb&@-#<>qRz|UnD z00Iz)9C%%w9!J&PqYsN;)NbxbBmW&a9;*hi1Q^`Ee>Ubaed+kH~()pz0czvxYA zseIzo+9?&0su%ln{ZZ4k)2e$ybcOTM{bx#?MICJv4)S&m- z4Y8S=oXi-E=E;-x zCkh*e&SLDa!nVJc$iho|8zHMks;kR|r4xnSvV#g!yVFQ?0aH0`RzVsrWsFjIX&+uV zX~P(Xsn7QsZD(1mywp`1eMdXcH2DQA{!S$X2i}yu3rsE{_B-{U%Y`R3S-cGA=&jDZKFaMGHeXwLMTZc9W2 z5A)@U)$m8bgPiIIztRY-?|2%eyrwnBlnk*n7LKEo9J%9rb^1^kKW#+?W6F0z`xycw zs#Jj@hdlZf&W&C`!q;1_?1BPl=hZQM?C0QE4jE`{I>4(j-Tv2R>dHQk-+rV zp9pcYd&o$mD4AMWwBW!Zao7!hq?dJ3RSFs71~>#s}^{l$3<4j4)U4H!5s}A^I?< zT$_w^kLyV&p;4GQnVul{0vK*JK_V+4dw8> z^t6%u0$Q9Jc3^OS5@LNs&Dr6H#b!tdNx$Oj!MkaXudY7tbxyN5_=^T?U!;R1oWsa*FzPa+X$>Uz#WTr1z#V3J2Bak4fRFtv9$>A7QdnC0iF=H7zfC+Z_Ja*h z#otCi*~NO4>)qLZJ$OlpXnQXs;FfUs6#VOG*9d^74zDFwy!alV0?;vlQc%M+3Pk@~ z(traH0i**>zz|3pRE1j8XtZcDXwhhWU;u0eP6Gcx|Af(siNvhJ+=lQ%{2+0V97rXk z9de9CffbESf?f4U=21ARBIv)=Q^D*rBY64?AOL^+*XaMnU*f+7kTwi0l!gVM{dWg- z)<6C5J^($Y0~c3T1gy)^OUCfRdcnFH-qw8qsAPidKqX7KdknZby??hKocGBYUipUv z8V2pr2V-E>@tE^Lq7DQP`O@mXqG-gI7QD1omZlo81tP@hIu3O z54R7$?Dksg`^}Pedt&?JZg3gXRuym?bq#4WfALv-*2wTE?-KmL$6y~ocD=uuQT=ef(5$7 zyQbvxf&Pwj48YkhV)|6naQUu0eo{RPzbBsX{5GvzS>_hjY1^4V;kg;x;b<$#Bko}M`~ z$=QL3tCw`CPd9qrNqxP}d_G})0(Nptu#atXjWckU1621lNHvl^wSu#(ZlOLiAEgPY zUD3sw_ri-njd(wfFse*LtSQg~RUNjfo$|ka*KRYniN4yWZW}Cr>s&y;Q_xQ*6Sd8N zwX7WwMvMLm9aN7U?*WEHKPn57mts=)MUD}@ZHTBxub%3cbjKX3hWsK~&Z>o{rDScXVbF}Lbu=vKeHofmz6$#{)1mCum+07{P z*6ztGY>pyo^RrE6DsC?HTWcB`t*-evqKY6fKpM2z6Y#1hwtiV|o|1xe+1;k1u$xk+ z6k;bP*gTDg)-ZE4U@5nqIdT-F!z)-2rLij#F!Ap5pb$$&B5dfxiEhESQ_q1 zjaaBXNy}%X(^cg;Fqd3*aWP4F0>m9Iz5}?+6vQT4X_sS5?=rON)l@;-d9ZX>`EbJU z0Aj_=;H0DRoLrJ+>TU%Z@#I_@Xu0Uhede0F-OD20(wiu?zM}QtNyDnKO1s-3w0uP- zYZ?Q8UT1Yom8mkY82k17d~7Nj7dRU?X_(l9d@Wd~i{-1MA*+(1=buzxn(3*EL(Djm z_-BUWg+!Qn(b^}jgov!BgPkIe?q2P~?FhxkUkLp=eP#)X3!o;8R+wCtf(1o0&O82& zm!N5V<{15zZfY)m!*!MpqjeqCoIS@B62lBG&f2!ZM557Fu0w>+bJjcPdAVgkaiwLv zKQy$jJ_M8MVRL0WPr|%{mhvH+GMjkdBlC{G05eA*;;L8-du|bzYv*a?B-1-tPbr3X zP}VKP_4|vO3S#M0-H`abTrB!gyPm-xlPDW^3$dhCos56N46}0%%VTvEZc1hm@wT=h zm9G8%cx`a-Q6BaO4_zhqMEVm0WLnI#^sQ|V|!%choG@@3zN}KeA^tLKZf;JTMkNDg2%Ajp>PN5R*x=ogb&0V1#|L*%6x@$Tozxlf`3VRj+$RwGK9e!^=h871 z+H}&L0oS)`?wYbfk#rmh0Xy0sNoNk~EP-vMyKKJg39H8*>8rc|tBqfR$(IFI96JV%a9DcJC1Y4my4GG%Hx0a^_A*mn!ThL8Dsb!E zLHrxEr=^FLughOS$VWuV5}+L#z@Nd>FNT+v2TBrxb8&?cF6+&5@fQ~q{Hdo*NwYpg zAD>R&KUBx@D1j|3r@Qe^V8`Gh>W9sv=UZh?0uk=QJi{*Uc z`e!!Fg@UKE>G(e>7TMV^rj%N&_Y&%0K4WrC+U0SY1#NxfoIm%+s3J4nvs)OAjxd;W znZdqs&%Rx!@UY{5&WDIj1sgk3C+)5A|M*LXya%NG=frn5v5^zoJQ+Um?t;# z4$h}839<$8rSlGDN%?=g>2ahU| z4#agu;NjCgX7Gy|Rl+0mhd{tuKm~&ivQR?BmRuPOW{y@+cEeIfLl+UausenS-S`q% z?8QtRJZil_B7#Xy4kXiXLH=`(%c8~{{C~5K_i|+-hP{IviQ;54!M&^ZkQWNk`R1!@ zHsW?)*Ewwko)=$+R>pect4L8A#QoWpD!SJ zca_VUeWxI47VG?2M(3J`KqMvC_Po_zpyVbsi-Wg6Y{H*>GV+6As#)mAKXea5A1Jig znZuv|u%BsaD8CExS*@j(nf+?Ev#*(gc)_hTRe?J;yTj8YloNep51YrWZ{#R1IP5^$ z>OU7cbN>~Rz9Hs!RB{=V&|s{_t6+AcUx{#PaWHlLMPp`DiWt|oYFs>V>5wx?A#MF& zGkgV|%-?T&v-&K`FJbzyC$Os2U)^!S?d(+S+Dwlm_N2XNlk4cEd#dqd3tpek}xRYYUJNBwvb8Tj3Zp#|_ zo921N0XCAoWVH$m)XMD{G25d wY{_LX=H;XpKCoO0;vIG=&MNPm!DONaTgB3E>)@~e@w0#9F9-lVJOBj$2Tjs3JOBUy literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Size2-Regular.woff2 b/frontend/node_modules/katex/dist/fonts/KaTeX_Size2-Regular.woff2 new file mode 100644 index 0000000000000000000000000000000000000000..e1bccfe2403a4ed770c1697ae7c15b9e1cd9bc4e GIT binary patch literal 5208 zcmV-e6sPNVPew8T0RR9102EjN4gdfE04)>%02BcL0RR9100000000000000000000 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 CPy?p` literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Size3-Regular.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_Size3-Regular.woff new file mode 100644 index 0000000000000000000000000000000000000000..e6e9b658dcf1cd031ac82b6b8f312444c55d4fc0 GIT binary patch literal 4420 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Size4-Regular.ttf b/frontend/node_modules/katex/dist/fonts/KaTeX_Size4-Regular.ttf new file mode 100644 index 0000000000000000000000000000000000000000..74f08921f00f71f413ca42c9d1c90202e672ef38 GIT binary patch literal 10364 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Size4-Regular.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_Size4-Regular.woff new file mode 100644 index 0000000000000000000000000000000000000000..e1ec5457664f438ce5a1cc6dd8409bf60ca7804b GIT binary patch literal 5980 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 literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Typewriter-Regular.ttf b/frontend/node_modules/katex/dist/fonts/KaTeX_Typewriter-Regular.ttf new file mode 100644 index 0000000000000000000000000000000000000000..c83252c5714c71a3e0ec62195884167339a0129b GIT binary patch literal 27556 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 MzaRX}iWL5T03x1QQ2+n{ literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/dist/fonts/KaTeX_Typewriter-Regular.woff b/frontend/node_modules/katex/dist/fonts/KaTeX_Typewriter-Regular.woff new file mode 100644 index 0000000000000000000000000000000000000000..2432419f28936aff53ddfa2a732d027e6a6648fd GIT binary patch literal 16028 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 G0ssIW .newline { + display: block; +} +.katex .base { + position: relative; + display: inline-block; + white-space: nowrap; + width: -webkit-min-content; + width: -moz-min-content; + width: min-content; +} +.katex .strut { + display: inline-block; +} +.katex .textbf { + font-weight: bold; +} +.katex .textit { + font-style: italic; +} +.katex .textrm { + font-family: KaTeX_Main; +} +.katex .textsf { + font-family: KaTeX_SansSerif; +} +.katex .texttt { + font-family: KaTeX_Typewriter; +} +.katex .mathnormal { + font-family: KaTeX_Math; + font-style: italic; +} +.katex .mathit { + font-family: KaTeX_Main; + font-style: italic; +} +.katex .mathrm { + font-style: normal; +} +.katex .mathbf { + font-family: KaTeX_Main; + font-weight: bold; +} +.katex .boldsymbol { + font-family: KaTeX_Math; + font-weight: bold; + font-style: italic; +} +.katex .amsrm { + font-family: KaTeX_AMS; +} +.katex .mathbb, +.katex .textbb { + font-family: KaTeX_AMS; +} +.katex .mathcal { + font-family: KaTeX_Caligraphic; +} +.katex .mathfrak, +.katex .textfrak { + font-family: KaTeX_Fraktur; +} +.katex .mathboldfrak, +.katex .textboldfrak { + font-family: KaTeX_Fraktur; + font-weight: bold; +} +.katex .mathtt { + font-family: KaTeX_Typewriter; +} +.katex .mathscr, +.katex .textscr { + font-family: KaTeX_Script; +} +.katex .mathsf, +.katex .textsf { + font-family: KaTeX_SansSerif; +} +.katex .mathboldsf, +.katex .textboldsf { + font-family: KaTeX_SansSerif; + font-weight: bold; +} +.katex .mathsfit, +.katex .mathitsf, +.katex .textitsf { + font-family: KaTeX_SansSerif; + font-style: italic; +} +.katex .mainrm { + font-family: KaTeX_Main; + font-style: normal; +} +.katex .vlist-t { + display: inline-table; + table-layout: fixed; + border-collapse: collapse; +} +.katex .vlist-r { + display: table-row; +} +.katex .vlist { + display: table-cell; + vertical-align: bottom; + position: relative; +} +.katex .vlist > span { + display: block; + height: 0; + position: relative; +} +.katex .vlist > span > span { + display: inline-block; +} +.katex .vlist > span > .pstrut { + overflow: hidden; + width: 0; +} +.katex .vlist-t2 { + margin-right: -2px; +} +.katex .vlist-s { + display: table-cell; + vertical-align: bottom; + font-size: 1px; + width: 2px; + min-width: 2px; +} +.katex .vbox { + display: inline-flex; + flex-direction: column; + align-items: baseline; +} +.katex .hbox { + display: inline-flex; + flex-direction: row; + width: 100%; +} +.katex .thinbox { + display: inline-flex; + flex-direction: row; + width: 0; + max-width: 0; +} +.katex .msupsub { + text-align: left; +} +.katex .mfrac > span > span { + text-align: center; +} +.katex .mfrac .frac-line { + display: inline-block; + width: 100%; + border-bottom-style: solid; +} +.katex .mfrac .frac-line, +.katex .overline .overline-line, +.katex .underline .underline-line, +.katex .hline, +.katex .hdashline, +.katex .rule { + min-height: 1px; +} +.katex .mspace { + display: inline-block; +} +.katex .llap, +.katex .rlap, +.katex .clap { + width: 0; + position: relative; +} +.katex .llap > .inner, +.katex .rlap > .inner, +.katex .clap > .inner { + position: absolute; +} +.katex .llap > .fix, +.katex .rlap > .fix, +.katex .clap > .fix { + display: inline-block; +} +.katex .llap > .inner { + right: 0; +} +.katex .rlap > .inner, +.katex .clap > .inner { + left: 0; +} +.katex .clap > .inner > span { + margin-left: -50%; + margin-right: 50%; +} +.katex .rule { + display: inline-block; + border: solid 0; + position: relative; +} +.katex .overline .overline-line, +.katex .underline .underline-line, +.katex .hline { + display: inline-block; + width: 100%; + border-bottom-style: solid; +} +.katex .hdashline { + display: inline-block; + width: 100%; + border-bottom-style: dashed; +} +.katex .sqrt > .root { + /* These values are taken from the definition of `\r@@t`, + `\mkern 5mu` and `\mkern -10mu`. */ + margin-left: 0.2777777778em; + margin-right: -0.5555555556em; +} +.katex .sizing.reset-size1.size1, +.katex .fontsize-ensurer.reset-size1.size1 { + /* stylelint-disable-next-line */ + font-size: 1em; +} +.katex .sizing.reset-size1.size2, +.katex .fontsize-ensurer.reset-size1.size2 { + /* stylelint-disable-next-line */ + font-size: 1.2em; +} +.katex .sizing.reset-size1.size3, +.katex .fontsize-ensurer.reset-size1.size3 { + /* stylelint-disable-next-line */ + font-size: 1.4em; +} +.katex .sizing.reset-size1.size4, +.katex .fontsize-ensurer.reset-size1.size4 { + /* stylelint-disable-next-line */ + font-size: 1.6em; +} +.katex .sizing.reset-size1.size5, +.katex .fontsize-ensurer.reset-size1.size5 { + /* stylelint-disable-next-line */ + font-size: 1.8em; +} +.katex .sizing.reset-size1.size6, +.katex .fontsize-ensurer.reset-size1.size6 { + /* stylelint-disable-next-line */ + font-size: 2em; +} +.katex .sizing.reset-size1.size7, +.katex .fontsize-ensurer.reset-size1.size7 { + /* stylelint-disable-next-line */ + font-size: 2.4em; +} +.katex .sizing.reset-size1.size8, +.katex .fontsize-ensurer.reset-size1.size8 { + /* stylelint-disable-next-line */ + font-size: 2.88em; +} +.katex .sizing.reset-size1.size9, +.katex .fontsize-ensurer.reset-size1.size9 { + /* stylelint-disable-next-line */ + font-size: 3.456em; +} +.katex .sizing.reset-size1.size10, +.katex .fontsize-ensurer.reset-size1.size10 { + /* stylelint-disable-next-line */ + font-size: 4.148em; +} +.katex .sizing.reset-size1.size11, +.katex .fontsize-ensurer.reset-size1.size11 { + /* stylelint-disable-next-line */ + font-size: 4.976em; +} +.katex .sizing.reset-size2.size1, +.katex .fontsize-ensurer.reset-size2.size1 { + /* stylelint-disable-next-line */ + font-size: 0.8333333333em; +} +.katex .sizing.reset-size2.size2, +.katex .fontsize-ensurer.reset-size2.size2 { + /* stylelint-disable-next-line */ + font-size: 1em; +} +.katex .sizing.reset-size2.size3, +.katex .fontsize-ensurer.reset-size2.size3 { + /* stylelint-disable-next-line */ + font-size: 1.1666666667em; +} +.katex .sizing.reset-size2.size4, +.katex .fontsize-ensurer.reset-size2.size4 { + /* stylelint-disable-next-line */ + font-size: 1.3333333333em; +} +.katex .sizing.reset-size2.size5, +.katex .fontsize-ensurer.reset-size2.size5 { + /* stylelint-disable-next-line */ + font-size: 1.5em; +} +.katex .sizing.reset-size2.size6, +.katex .fontsize-ensurer.reset-size2.size6 { + /* stylelint-disable-next-line */ + font-size: 1.6666666667em; +} +.katex .sizing.reset-size2.size7, +.katex .fontsize-ensurer.reset-size2.size7 { + /* stylelint-disable-next-line */ + font-size: 2em; +} +.katex .sizing.reset-size2.size8, +.katex .fontsize-ensurer.reset-size2.size8 { + /* stylelint-disable-next-line */ + font-size: 2.4em; +} +.katex .sizing.reset-size2.size9, +.katex .fontsize-ensurer.reset-size2.size9 { + /* stylelint-disable-next-line */ + font-size: 2.88em; +} +.katex .sizing.reset-size2.size10, +.katex .fontsize-ensurer.reset-size2.size10 { + /* stylelint-disable-next-line */ + font-size: 3.4566666667em; +} +.katex .sizing.reset-size2.size11, +.katex .fontsize-ensurer.reset-size2.size11 { + /* stylelint-disable-next-line */ + font-size: 4.1466666667em; +} +.katex .sizing.reset-size3.size1, +.katex .fontsize-ensurer.reset-size3.size1 { + /* stylelint-disable-next-line */ + font-size: 0.7142857143em; +} +.katex .sizing.reset-size3.size2, +.katex .fontsize-ensurer.reset-size3.size2 { + /* stylelint-disable-next-line */ + font-size: 0.8571428571em; +} +.katex .sizing.reset-size3.size3, +.katex .fontsize-ensurer.reset-size3.size3 { + /* stylelint-disable-next-line */ + font-size: 1em; +} +.katex .sizing.reset-size3.size4, +.katex .fontsize-ensurer.reset-size3.size4 { + /* stylelint-disable-next-line */ + font-size: 1.1428571429em; +} +.katex .sizing.reset-size3.size5, +.katex .fontsize-ensurer.reset-size3.size5 { + /* stylelint-disable-next-line */ + font-size: 1.2857142857em; +} +.katex .sizing.reset-size3.size6, +.katex .fontsize-ensurer.reset-size3.size6 { + /* stylelint-disable-next-line */ + font-size: 1.4285714286em; +} +.katex .sizing.reset-size3.size7, +.katex .fontsize-ensurer.reset-size3.size7 { + /* stylelint-disable-next-line */ + font-size: 1.7142857143em; +} +.katex .sizing.reset-size3.size8, +.katex .fontsize-ensurer.reset-size3.size8 { + /* stylelint-disable-next-line */ + font-size: 2.0571428571em; +} +.katex .sizing.reset-size3.size9, +.katex .fontsize-ensurer.reset-size3.size9 { + /* stylelint-disable-next-line */ + font-size: 2.4685714286em; +} +.katex .sizing.reset-size3.size10, +.katex .fontsize-ensurer.reset-size3.size10 { + /* stylelint-disable-next-line */ + font-size: 2.9628571429em; +} +.katex .sizing.reset-size3.size11, +.katex .fontsize-ensurer.reset-size3.size11 { + /* stylelint-disable-next-line */ + font-size: 3.5542857143em; +} +.katex .sizing.reset-size4.size1, +.katex .fontsize-ensurer.reset-size4.size1 { + /* stylelint-disable-next-line */ + font-size: 0.625em; +} +.katex .sizing.reset-size4.size2, +.katex .fontsize-ensurer.reset-size4.size2 { + /* stylelint-disable-next-line */ + font-size: 0.75em; +} +.katex .sizing.reset-size4.size3, +.katex .fontsize-ensurer.reset-size4.size3 { + /* stylelint-disable-next-line */ + font-size: 0.875em; +} +.katex .sizing.reset-size4.size4, +.katex .fontsize-ensurer.reset-size4.size4 { + /* stylelint-disable-next-line */ + font-size: 1em; +} +.katex .sizing.reset-size4.size5, +.katex .fontsize-ensurer.reset-size4.size5 { + /* stylelint-disable-next-line */ + font-size: 1.125em; +} +.katex .sizing.reset-size4.size6, +.katex .fontsize-ensurer.reset-size4.size6 { + /* stylelint-disable-next-line */ + font-size: 1.25em; +} +.katex .sizing.reset-size4.size7, +.katex .fontsize-ensurer.reset-size4.size7 { + /* stylelint-disable-next-line */ + font-size: 1.5em; +} +.katex .sizing.reset-size4.size8, +.katex .fontsize-ensurer.reset-size4.size8 { + /* stylelint-disable-next-line */ + font-size: 1.8em; +} +.katex .sizing.reset-size4.size9, +.katex .fontsize-ensurer.reset-size4.size9 { + /* stylelint-disable-next-line */ + font-size: 2.16em; +} +.katex .sizing.reset-size4.size10, +.katex .fontsize-ensurer.reset-size4.size10 { + /* stylelint-disable-next-line */ + font-size: 2.5925em; +} +.katex .sizing.reset-size4.size11, +.katex .fontsize-ensurer.reset-size4.size11 { + /* stylelint-disable-next-line */ + font-size: 3.11em; +} +.katex .sizing.reset-size5.size1, +.katex .fontsize-ensurer.reset-size5.size1 { + /* stylelint-disable-next-line */ + font-size: 0.5555555556em; +} +.katex .sizing.reset-size5.size2, +.katex .fontsize-ensurer.reset-size5.size2 { + /* stylelint-disable-next-line */ + font-size: 0.6666666667em; +} +.katex .sizing.reset-size5.size3, +.katex .fontsize-ensurer.reset-size5.size3 { + /* stylelint-disable-next-line */ + font-size: 0.7777777778em; +} +.katex .sizing.reset-size5.size4, +.katex .fontsize-ensurer.reset-size5.size4 { + /* stylelint-disable-next-line */ + font-size: 0.8888888889em; +} +.katex .sizing.reset-size5.size5, +.katex .fontsize-ensurer.reset-size5.size5 { + /* stylelint-disable-next-line */ + font-size: 1em; +} +.katex .sizing.reset-size5.size6, +.katex .fontsize-ensurer.reset-size5.size6 { + /* stylelint-disable-next-line */ + font-size: 1.1111111111em; +} +.katex .sizing.reset-size5.size7, +.katex .fontsize-ensurer.reset-size5.size7 { + /* stylelint-disable-next-line */ + font-size: 1.3333333333em; +} +.katex .sizing.reset-size5.size8, +.katex .fontsize-ensurer.reset-size5.size8 { + /* stylelint-disable-next-line */ + font-size: 1.6em; +} +.katex .sizing.reset-size5.size9, +.katex .fontsize-ensurer.reset-size5.size9 { + /* stylelint-disable-next-line */ + font-size: 1.92em; +} +.katex .sizing.reset-size5.size10, +.katex .fontsize-ensurer.reset-size5.size10 { + /* stylelint-disable-next-line */ + font-size: 2.3044444444em; +} +.katex .sizing.reset-size5.size11, +.katex .fontsize-ensurer.reset-size5.size11 { + /* stylelint-disable-next-line */ + font-size: 2.7644444444em; +} +.katex .sizing.reset-size6.size1, +.katex .fontsize-ensurer.reset-size6.size1 { + /* stylelint-disable-next-line */ + font-size: 0.5em; +} +.katex .sizing.reset-size6.size2, +.katex .fontsize-ensurer.reset-size6.size2 { + /* stylelint-disable-next-line */ + font-size: 0.6em; +} +.katex .sizing.reset-size6.size3, +.katex .fontsize-ensurer.reset-size6.size3 { + /* stylelint-disable-next-line */ + font-size: 0.7em; +} +.katex .sizing.reset-size6.size4, +.katex .fontsize-ensurer.reset-size6.size4 { + /* stylelint-disable-next-line */ + font-size: 0.8em; +} +.katex .sizing.reset-size6.size5, +.katex .fontsize-ensurer.reset-size6.size5 { + /* stylelint-disable-next-line */ + font-size: 0.9em; +} +.katex .sizing.reset-size6.size6, +.katex .fontsize-ensurer.reset-size6.size6 { + /* stylelint-disable-next-line */ + font-size: 1em; +} +.katex .sizing.reset-size6.size7, +.katex .fontsize-ensurer.reset-size6.size7 { + /* stylelint-disable-next-line */ + font-size: 1.2em; +} +.katex .sizing.reset-size6.size8, +.katex .fontsize-ensurer.reset-size6.size8 { + /* stylelint-disable-next-line */ + font-size: 1.44em; +} +.katex .sizing.reset-size6.size9, +.katex .fontsize-ensurer.reset-size6.size9 { + /* stylelint-disable-next-line */ + font-size: 1.728em; +} +.katex .sizing.reset-size6.size10, +.katex .fontsize-ensurer.reset-size6.size10 { + /* stylelint-disable-next-line */ + font-size: 2.074em; +} +.katex .sizing.reset-size6.size11, +.katex .fontsize-ensurer.reset-size6.size11 { + /* stylelint-disable-next-line */ + font-size: 2.488em; +} +.katex .sizing.reset-size7.size1, +.katex .fontsize-ensurer.reset-size7.size1 { + /* stylelint-disable-next-line */ + font-size: 0.4166666667em; +} +.katex .sizing.reset-size7.size2, +.katex .fontsize-ensurer.reset-size7.size2 { + /* stylelint-disable-next-line */ + font-size: 0.5em; +} +.katex .sizing.reset-size7.size3, +.katex .fontsize-ensurer.reset-size7.size3 { + /* stylelint-disable-next-line */ + font-size: 0.5833333333em; +} +.katex .sizing.reset-size7.size4, +.katex .fontsize-ensurer.reset-size7.size4 { + /* stylelint-disable-next-line */ + font-size: 0.6666666667em; +} +.katex .sizing.reset-size7.size5, +.katex .fontsize-ensurer.reset-size7.size5 { + /* stylelint-disable-next-line */ + font-size: 0.75em; +} +.katex .sizing.reset-size7.size6, +.katex .fontsize-ensurer.reset-size7.size6 { + /* stylelint-disable-next-line */ + font-size: 0.8333333333em; +} +.katex .sizing.reset-size7.size7, +.katex .fontsize-ensurer.reset-size7.size7 { + /* stylelint-disable-next-line */ + font-size: 1em; +} +.katex .sizing.reset-size7.size8, +.katex .fontsize-ensurer.reset-size7.size8 { + /* stylelint-disable-next-line */ + font-size: 1.2em; +} +.katex .sizing.reset-size7.size9, +.katex .fontsize-ensurer.reset-size7.size9 { + /* stylelint-disable-next-line */ + font-size: 1.44em; +} +.katex .sizing.reset-size7.size10, +.katex .fontsize-ensurer.reset-size7.size10 { + /* stylelint-disable-next-line */ + font-size: 1.7283333333em; +} +.katex .sizing.reset-size7.size11, +.katex .fontsize-ensurer.reset-size7.size11 { + /* stylelint-disable-next-line */ + font-size: 2.0733333333em; +} +.katex .sizing.reset-size8.size1, +.katex .fontsize-ensurer.reset-size8.size1 { + /* stylelint-disable-next-line */ + font-size: 0.3472222222em; +} +.katex .sizing.reset-size8.size2, +.katex .fontsize-ensurer.reset-size8.size2 { + /* stylelint-disable-next-line */ + font-size: 0.4166666667em; +} +.katex .sizing.reset-size8.size3, +.katex .fontsize-ensurer.reset-size8.size3 { + /* stylelint-disable-next-line */ + font-size: 0.4861111111em; +} +.katex .sizing.reset-size8.size4, +.katex .fontsize-ensurer.reset-size8.size4 { + /* stylelint-disable-next-line */ + font-size: 0.5555555556em; +} +.katex .sizing.reset-size8.size5, +.katex .fontsize-ensurer.reset-size8.size5 { + /* stylelint-disable-next-line */ + font-size: 0.625em; +} +.katex .sizing.reset-size8.size6, +.katex .fontsize-ensurer.reset-size8.size6 { + /* stylelint-disable-next-line */ + font-size: 0.6944444444em; +} +.katex .sizing.reset-size8.size7, +.katex .fontsize-ensurer.reset-size8.size7 { + /* stylelint-disable-next-line */ + font-size: 0.8333333333em; +} +.katex .sizing.reset-size8.size8, +.katex .fontsize-ensurer.reset-size8.size8 { + /* stylelint-disable-next-line */ + font-size: 1em; +} +.katex .sizing.reset-size8.size9, +.katex .fontsize-ensurer.reset-size8.size9 { + /* stylelint-disable-next-line */ + font-size: 1.2em; +} +.katex .sizing.reset-size8.size10, +.katex .fontsize-ensurer.reset-size8.size10 { + /* stylelint-disable-next-line */ + font-size: 1.4402777778em; +} +.katex .sizing.reset-size8.size11, +.katex .fontsize-ensurer.reset-size8.size11 { + /* stylelint-disable-next-line */ + font-size: 1.7277777778em; +} +.katex .sizing.reset-size9.size1, +.katex .fontsize-ensurer.reset-size9.size1 { + /* stylelint-disable-next-line */ + font-size: 0.2893518519em; +} +.katex .sizing.reset-size9.size2, +.katex .fontsize-ensurer.reset-size9.size2 { + /* stylelint-disable-next-line */ + font-size: 0.3472222222em; +} +.katex .sizing.reset-size9.size3, +.katex .fontsize-ensurer.reset-size9.size3 { + /* stylelint-disable-next-line */ + font-size: 0.4050925926em; +} +.katex .sizing.reset-size9.size4, +.katex .fontsize-ensurer.reset-size9.size4 { + /* stylelint-disable-next-line */ + font-size: 0.462962963em; +} +.katex .sizing.reset-size9.size5, +.katex .fontsize-ensurer.reset-size9.size5 { + /* stylelint-disable-next-line */ + font-size: 0.5208333333em; +} +.katex .sizing.reset-size9.size6, +.katex .fontsize-ensurer.reset-size9.size6 { + /* stylelint-disable-next-line */ + font-size: 0.5787037037em; +} +.katex .sizing.reset-size9.size7, +.katex .fontsize-ensurer.reset-size9.size7 { + /* stylelint-disable-next-line */ + font-size: 0.6944444444em; +} +.katex .sizing.reset-size9.size8, +.katex .fontsize-ensurer.reset-size9.size8 { + /* stylelint-disable-next-line */ + font-size: 0.8333333333em; +} +.katex .sizing.reset-size9.size9, +.katex .fontsize-ensurer.reset-size9.size9 { + /* stylelint-disable-next-line */ + font-size: 1em; +} +.katex .sizing.reset-size9.size10, +.katex .fontsize-ensurer.reset-size9.size10 { + /* stylelint-disable-next-line */ + font-size: 1.2002314815em; +} +.katex .sizing.reset-size9.size11, +.katex .fontsize-ensurer.reset-size9.size11 { + /* stylelint-disable-next-line */ + font-size: 1.4398148148em; +} +.katex .sizing.reset-size10.size1, +.katex .fontsize-ensurer.reset-size10.size1 { + /* stylelint-disable-next-line */ + font-size: 0.2410800386em; +} +.katex .sizing.reset-size10.size2, +.katex .fontsize-ensurer.reset-size10.size2 { + /* stylelint-disable-next-line */ + font-size: 0.2892960463em; +} +.katex .sizing.reset-size10.size3, +.katex .fontsize-ensurer.reset-size10.size3 { + /* stylelint-disable-next-line */ + font-size: 0.337512054em; +} +.katex .sizing.reset-size10.size4, +.katex .fontsize-ensurer.reset-size10.size4 { + /* stylelint-disable-next-line */ + font-size: 0.3857280617em; +} +.katex .sizing.reset-size10.size5, +.katex .fontsize-ensurer.reset-size10.size5 { + /* stylelint-disable-next-line */ + font-size: 0.4339440694em; +} +.katex .sizing.reset-size10.size6, +.katex .fontsize-ensurer.reset-size10.size6 { + /* stylelint-disable-next-line */ + font-size: 0.4821600771em; +} +.katex .sizing.reset-size10.size7, +.katex .fontsize-ensurer.reset-size10.size7 { + /* stylelint-disable-next-line */ + font-size: 0.5785920926em; +} +.katex .sizing.reset-size10.size8, +.katex .fontsize-ensurer.reset-size10.size8 { + /* stylelint-disable-next-line */ + font-size: 0.6943105111em; +} +.katex .sizing.reset-size10.size9, +.katex .fontsize-ensurer.reset-size10.size9 { + /* stylelint-disable-next-line */ + font-size: 0.8331726133em; +} +.katex .sizing.reset-size10.size10, +.katex .fontsize-ensurer.reset-size10.size10 { + /* stylelint-disable-next-line */ + font-size: 1em; +} +.katex .sizing.reset-size10.size11, +.katex .fontsize-ensurer.reset-size10.size11 { + /* stylelint-disable-next-line */ + font-size: 1.1996142719em; +} +.katex .sizing.reset-size11.size1, +.katex .fontsize-ensurer.reset-size11.size1 { + /* stylelint-disable-next-line */ + font-size: 0.2009646302em; +} +.katex .sizing.reset-size11.size2, +.katex .fontsize-ensurer.reset-size11.size2 { + /* stylelint-disable-next-line */ + font-size: 0.2411575563em; +} +.katex .sizing.reset-size11.size3, +.katex .fontsize-ensurer.reset-size11.size3 { + /* stylelint-disable-next-line */ + font-size: 0.2813504823em; +} +.katex .sizing.reset-size11.size4, +.katex .fontsize-ensurer.reset-size11.size4 { + /* stylelint-disable-next-line */ + font-size: 0.3215434084em; +} +.katex .sizing.reset-size11.size5, +.katex .fontsize-ensurer.reset-size11.size5 { + /* stylelint-disable-next-line */ + font-size: 0.3617363344em; +} +.katex .sizing.reset-size11.size6, +.katex .fontsize-ensurer.reset-size11.size6 { + /* stylelint-disable-next-line */ + font-size: 0.4019292605em; +} +.katex .sizing.reset-size11.size7, +.katex .fontsize-ensurer.reset-size11.size7 { + /* stylelint-disable-next-line */ + font-size: 0.4823151125em; +} +.katex .sizing.reset-size11.size8, +.katex .fontsize-ensurer.reset-size11.size8 { + /* stylelint-disable-next-line */ + font-size: 0.578778135em; +} +.katex .sizing.reset-size11.size9, +.katex .fontsize-ensurer.reset-size11.size9 { + /* stylelint-disable-next-line */ + font-size: 0.6945337621em; +} +.katex .sizing.reset-size11.size10, +.katex .fontsize-ensurer.reset-size11.size10 { + /* stylelint-disable-next-line */ + font-size: 0.8336012862em; +} +.katex .sizing.reset-size11.size11, +.katex .fontsize-ensurer.reset-size11.size11 { + /* stylelint-disable-next-line */ + font-size: 1em; +} +.katex .delimsizing.size1 { + font-family: KaTeX_Size1; +} +.katex .delimsizing.size2 { + font-family: KaTeX_Size2; +} +.katex .delimsizing.size3 { + font-family: KaTeX_Size3; +} +.katex .delimsizing.size4 { + font-family: KaTeX_Size4; +} +.katex .delimsizing.mult .delim-size1 > span { + font-family: KaTeX_Size1; +} +.katex .delimsizing.mult .delim-size4 > span { + font-family: KaTeX_Size4; +} +.katex .nulldelimiter { + display: inline-block; + width: 0.12em; +} +.katex .delimcenter { + position: relative; +} +.katex .op-symbol { + position: relative; +} +.katex .op-symbol.small-op { + font-family: KaTeX_Size1; +} +.katex .op-symbol.large-op { + font-family: KaTeX_Size2; +} +.katex .op-limits > .vlist-t { + text-align: center; +} +.katex .accent > .vlist-t { + text-align: center; +} +.katex .accent .accent-body { + position: relative; +} +.katex .accent .accent-body:not(.accent-full) { + width: 0; +} +.katex .overlay { + display: block; +} +.katex .mtable .vertical-separator { + display: inline-block; + min-width: 1px; +} +.katex .mtable .arraycolsep { + display: inline-block; +} +.katex .mtable .col-align-c > .vlist-t { + text-align: center; +} +.katex .mtable .col-align-l > .vlist-t { + text-align: left; +} +.katex .mtable .col-align-r > .vlist-t { + text-align: right; +} +.katex .svg-align { + text-align: left; +} +.katex svg { + display: block; + position: absolute; + width: 100%; + height: inherit; + fill: currentColor; + stroke: currentColor; + fill-rule: nonzero; + fill-opacity: 1; + stroke-width: 1; + stroke-linecap: butt; + stroke-linejoin: miter; + stroke-miterlimit: 4; + stroke-dasharray: none; + stroke-dashoffset: 0; + stroke-opacity: 1; +} +.katex svg path { + stroke: none; +} +.katex img { + border-style: none; + min-width: 0; + min-height: 0; + max-width: none; + max-height: none; +} +.katex .stretchy { + width: 100%; + display: block; + position: relative; + overflow: hidden; +} +.katex .stretchy::before, .katex .stretchy::after { + content: ""; +} +.katex .hide-tail { + width: 100%; + position: relative; + overflow: hidden; +} +.katex .halfarrow-left { + position: absolute; + left: 0; + width: 50.2%; + overflow: hidden; +} +.katex .halfarrow-right { + position: absolute; + right: 0; + width: 50.2%; + overflow: hidden; +} +.katex .brace-left { + position: absolute; + left: 0; + width: 25.1%; + overflow: hidden; +} +.katex .brace-center { + position: absolute; + left: 25%; + width: 50%; + overflow: hidden; +} +.katex .brace-right { + position: absolute; + right: 0; + width: 25.1%; + overflow: hidden; +} +.katex .x-arrow-pad { + padding: 0 0.5em; +} +.katex .cd-arrow-pad { + padding: 0 0.55556em 0 0.27778em; +} +.katex .x-arrow, +.katex .mover, +.katex .munder { + text-align: center; +} +.katex .boxpad { + padding: 0 0.3em; +} +.katex .fbox, +.katex .fcolorbox { + box-sizing: border-box; + border: 0.04em solid; +} +.katex .cancel-pad { + padding: 0 0.2em; +} +.katex .cancel-lap { + margin-left: -0.2em; + margin-right: -0.2em; +} +.katex .sout { + border-bottom-style: solid; + border-bottom-width: 0.08em; +} +.katex .angl { + box-sizing: border-box; + border-top: 0.049em solid; + border-right: 0.049em solid; + margin-right: 0.03889em; +} +.katex .anglpad { + padding: 0 0.03889em; +} +.katex .eqn-num::before { + counter-increment: katexEqnNo; + content: "(" counter(katexEqnNo) ")"; +} +.katex .mml-eqn-num::before { + counter-increment: mmlEqnNo; + content: "(" counter(mmlEqnNo) ")"; +} +.katex .mtr-glue { + width: 50%; +} +.katex .cd-vert-arrow { + display: inline-block; + position: relative; +} +.katex .cd-label-left { + display: inline-block; + position: absolute; + right: calc(50% + 0.3em); + text-align: left; +} +.katex .cd-label-right { + display: inline-block; + position: absolute; + left: calc(50% + 0.3em); + text-align: right; +} + +.katex-display { + display: block; + margin: 1em 0; + text-align: center; +} +.katex-display > .katex { + display: block; + text-align: center; + white-space: nowrap; +} +.katex-display > .katex > .katex-html { + display: block; + position: relative; +} +.katex-display > .katex > .katex-html > .tag { + position: absolute; + right: 0; +} + +.katex-display.leqno > .katex > .katex-html > .tag { + left: 0; + right: auto; +} + +.katex-display.fleqn > .katex { + text-align: left; + padding-left: 2em; +} + +body { + counter-reset: katexEqnNo mmlEqnNo; +} diff --git a/frontend/node_modules/katex/dist/katex.js b/frontend/node_modules/katex/dist/katex.js new file mode 100644 index 0000000..4759411 --- /dev/null +++ b/frontend/node_modules/katex/dist/katex.js @@ -0,0 +1,19092 @@ +(function webpackUniversalModuleDefinition(root, factory) { + if(typeof exports === 'object' && typeof module === 'object') + module.exports = factory(); + else if(typeof define === 'function' && define.amd) + define([], factory); + else if(typeof exports === 'object') + exports["katex"] = factory(); + else + root["katex"] = factory(); +})((typeof self !== 'undefined' ? self : this), function() { +return /******/ (function() { // webpackBootstrap +/******/ "use strict"; +/******/ // The require scope +/******/ var __webpack_require__ = {}; +/******/ +/************************************************************************/ +/******/ /* webpack/runtime/define property getters */ +/******/ !function() { +/******/ // define getter functions for harmony exports +/******/ __webpack_require__.d = function(exports, definition) { +/******/ for(var key in definition) { +/******/ if(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) { +/******/ Object.defineProperty(exports, key, { enumerable: true, get: definition[key] }); +/******/ } +/******/ } +/******/ }; +/******/ }(); +/******/ +/******/ /* webpack/runtime/hasOwnProperty shorthand */ +/******/ !function() { +/******/ __webpack_require__.o = function(obj, prop) { return Object.prototype.hasOwnProperty.call(obj, prop); } +/******/ }(); +/******/ +/************************************************************************/ +var __webpack_exports__ = {}; + +// EXPORTS +__webpack_require__.d(__webpack_exports__, { + "default": function() { return /* binding */ katex_webpack; } +}); + +;// CONCATENATED MODULE: ./src/ParseError.js + + +/** + * This is the ParseError class, which is the main error thrown by KaTeX + * functions when something has gone wrong. This is used to distinguish internal + * errors from errors in the expression that the user provided. + * + * If possible, a caller should provide a Token or ParseNode with information + * about where in the source string the problem occurred. + */ +class ParseError { + // Error start position based on passed-in Token or ParseNode. + // Length of affected text based on passed-in Token or ParseNode. + // The underlying error message without any context added. + constructor(message, // The error message + token // An object providing position information + ) { + this.name = void 0; + this.position = void 0; + this.length = void 0; + this.rawMessage = void 0; + let error = "KaTeX parse error: " + message; + let start; + let end; + const loc = token && token.loc; + + if (loc && loc.start <= loc.end) { + // If we have the input and a position, make the error a bit fancier + // Get the input + const input = loc.lexer.input; // Prepend some information + + start = loc.start; + end = loc.end; + + if (start === input.length) { + error += " at end of input: "; + } else { + error += " at position " + (start + 1) + ": "; + } // Underline token in question using combining underscores + + + const underlined = input.slice(start, end).replace(/[^]/g, "$&\u0332"); // Extract some context from the input and add it to the error + + let left; + + if (start > 15) { + left = "…" + input.slice(start - 15, start); + } else { + left = input.slice(0, start); + } + + let right; + + if (end + 15 < input.length) { + right = input.slice(end, end + 15) + "…"; + } else { + right = input.slice(end); + } + + error += left + underlined + right; + } // Some hackery to make ParseError a prototype of Error + // See http://stackoverflow.com/a/8460753 + // $FlowFixMe + + + const self = new Error(error); + self.name = "ParseError"; // $FlowFixMe + + self.__proto__ = ParseError.prototype; + self.position = start; + + if (start != null && end != null) { + self.length = end - start; + } + + self.rawMessage = message; + return self; + } + +} // $FlowFixMe More hackery + + +ParseError.prototype.__proto__ = Error.prototype; +/* harmony default export */ var src_ParseError = (ParseError); +;// CONCATENATED MODULE: ./src/utils.js +/** + * This file contains a list of utility functions which are useful in other + * files. + */ + +/** + * Return whether an element is contained in a list + */ +const contains = function (list, elem) { + return list.indexOf(elem) !== -1; +}; +/** + * Provide a default value if a setting is undefined + * NOTE: Couldn't use `T` as the output type due to facebook/flow#5022. + */ + + +const deflt = function (setting, defaultIfUndefined) { + return setting === undefined ? defaultIfUndefined : setting; +}; // hyphenate and escape adapted from Facebook's React under Apache 2 license + + +const uppercase = /([A-Z])/g; + +const hyphenate = function (str) { + return str.replace(uppercase, "-$1").toLowerCase(); +}; + +const ESCAPE_LOOKUP = { + "&": "&", + ">": ">", + "<": "<", + "\"": """, + "'": "'" +}; +const ESCAPE_REGEX = /[&><"']/g; +/** + * Escapes text to prevent scripting attacks. + */ + +function utils_escape(text) { + return String(text).replace(ESCAPE_REGEX, match => ESCAPE_LOOKUP[match]); +} +/** + * Sometimes we want to pull out the innermost element of a group. In most + * cases, this will just be the group itself, but when ordgroups and colors have + * a single element, we want to pull that out. + */ + + +const getBaseElem = function (group) { + if (group.type === "ordgroup") { + if (group.body.length === 1) { + return getBaseElem(group.body[0]); + } else { + return group; + } + } else if (group.type === "color") { + if (group.body.length === 1) { + return getBaseElem(group.body[0]); + } else { + return group; + } + } else if (group.type === "font") { + return getBaseElem(group.body); + } else { + return group; + } +}; +/** + * TeXbook algorithms often reference "character boxes", which are simply groups + * with a single character in them. To decide if something is a character box, + * we find its innermost group, and see if it is a single character. + */ + + +const isCharacterBox = function (group) { + const baseElem = getBaseElem(group); // These are all they types of groups which hold single characters + + return baseElem.type === "mathord" || baseElem.type === "textord" || baseElem.type === "atom"; +}; + +const assert = function (value) { + if (!value) { + throw new Error('Expected non-null, but got ' + String(value)); + } + + return value; +}; +/** + * Return the protocol of a URL, or "_relative" if the URL does not specify a + * protocol (and thus is relative), or `null` if URL has invalid protocol + * (so should be outright rejected). + */ + +const protocolFromUrl = function (url) { + // Check for possible leading protocol. + // https://url.spec.whatwg.org/#url-parsing strips leading whitespace + // (U+20) or C0 control (U+00-U+1F) characters. + // eslint-disable-next-line no-control-regex + const protocol = /^[\x00-\x20]*([^\\/#?]*?)(:|�*58|�*3a|&colon)/i.exec(url); + + if (!protocol) { + return "_relative"; + } // Reject weird colons + + + if (protocol[2] !== ":") { + return null; + } // Reject invalid characters in scheme according to + // https://datatracker.ietf.org/doc/html/rfc3986#section-3.1 + + + if (!/^[a-zA-Z][a-zA-Z0-9+\-.]*$/.test(protocol[1])) { + return null; + } // Lowercase the protocol + + + return protocol[1].toLowerCase(); +}; +/* harmony default export */ var utils = ({ + contains, + deflt, + escape: utils_escape, + hyphenate, + getBaseElem, + isCharacterBox, + protocolFromUrl +}); +;// CONCATENATED MODULE: ./src/Settings.js +/* eslint no-console:0 */ + +/** + * This is a module for storing settings passed into KaTeX. It correctly handles + * default settings. + */ + + + +// TODO: automatically generate documentation +// TODO: check all properties on Settings exist +// TODO: check the type of a property on Settings matches +const SETTINGS_SCHEMA = { + displayMode: { + type: "boolean", + description: "Render math in display mode, which puts the math in " + "display style (so \\int and \\sum are large, for example), and " + "centers the math on the page on its own line.", + cli: "-d, --display-mode" + }, + output: { + type: { + enum: ["htmlAndMathml", "html", "mathml"] + }, + description: "Determines the markup language of the output.", + cli: "-F, --format " + }, + leqno: { + type: "boolean", + description: "Render display math in leqno style (left-justified tags)." + }, + fleqn: { + type: "boolean", + description: "Render display math flush left." + }, + throwOnError: { + type: "boolean", + default: true, + cli: "-t, --no-throw-on-error", + cliDescription: "Render errors (in the color given by --error-color) ins" + "tead of throwing a ParseError exception when encountering an error." + }, + errorColor: { + type: "string", + default: "#cc0000", + cli: "-c, --error-color ", + cliDescription: "A color string given in the format 'rgb' or 'rrggbb' " + "(no #). This option determines the color of errors rendered by the " + "-t option.", + cliProcessor: color => "#" + color + }, + macros: { + type: "object", + cli: "-m, --macro ", + cliDescription: "Define custom macro of the form '\\foo:expansion' (use " + "multiple -m arguments for multiple macros).", + cliDefault: [], + cliProcessor: (def, defs) => { + defs.push(def); + return defs; + } + }, + minRuleThickness: { + type: "number", + description: "Specifies a minimum thickness, in ems, for fraction lines," + " `\\sqrt` top lines, `{array}` vertical lines, `\\hline`, " + "`\\hdashline`, `\\underline`, `\\overline`, and the borders of " + "`\\fbox`, `\\boxed`, and `\\fcolorbox`.", + processor: t => Math.max(0, t), + cli: "--min-rule-thickness ", + cliProcessor: parseFloat + }, + colorIsTextColor: { + type: "boolean", + description: "Makes \\color behave like LaTeX's 2-argument \\textcolor, " + "instead of LaTeX's one-argument \\color mode change.", + cli: "-b, --color-is-text-color" + }, + strict: { + type: [{ + enum: ["warn", "ignore", "error"] + }, "boolean", "function"], + description: "Turn on strict / LaTeX faithfulness mode, which throws an " + "error if the input uses features that are not supported by LaTeX.", + cli: "-S, --strict", + cliDefault: false + }, + trust: { + type: ["boolean", "function"], + description: "Trust the input, enabling all HTML features such as \\url.", + cli: "-T, --trust" + }, + maxSize: { + type: "number", + default: Infinity, + description: "If non-zero, all user-specified sizes, e.g. in " + "\\rule{500em}{500em}, will be capped to maxSize ems. Otherwise, " + "elements and spaces can be arbitrarily large", + processor: s => Math.max(0, s), + cli: "-s, --max-size ", + cliProcessor: parseInt + }, + maxExpand: { + type: "number", + default: 1000, + description: "Limit the number of macro expansions to the specified " + "number, to prevent e.g. infinite macro loops. If set to Infinity, " + "the macro expander will try to fully expand as in LaTeX.", + processor: n => Math.max(0, n), + cli: "-e, --max-expand ", + cliProcessor: n => n === "Infinity" ? Infinity : parseInt(n) + }, + globalGroup: { + type: "boolean", + cli: false + } +}; + +function getDefaultValue(schema) { + if (schema.default) { + return schema.default; + } + + const type = schema.type; + const defaultType = Array.isArray(type) ? type[0] : type; + + if (typeof defaultType !== 'string') { + return defaultType.enum[0]; + } + + switch (defaultType) { + case 'boolean': + return false; + + case 'string': + return ''; + + case 'number': + return 0; + + case 'object': + return {}; + } +} +/** + * The main Settings object + * + * The current options stored are: + * - displayMode: Whether the expression should be typeset as inline math + * (false, the default), meaning that the math starts in + * \textstyle and is placed in an inline-block); or as display + * math (true), meaning that the math starts in \displaystyle + * and is placed in a block with vertical margin. + */ + + +class Settings { + constructor(options) { + this.displayMode = void 0; + this.output = void 0; + this.leqno = void 0; + this.fleqn = void 0; + this.throwOnError = void 0; + this.errorColor = void 0; + this.macros = void 0; + this.minRuleThickness = void 0; + this.colorIsTextColor = void 0; + this.strict = void 0; + this.trust = void 0; + this.maxSize = void 0; + this.maxExpand = void 0; + this.globalGroup = void 0; + // allow null options + options = options || {}; + + for (const prop in SETTINGS_SCHEMA) { + if (SETTINGS_SCHEMA.hasOwnProperty(prop)) { + // $FlowFixMe + const schema = SETTINGS_SCHEMA[prop]; // TODO: validate options + // $FlowFixMe + + this[prop] = options[prop] !== undefined ? schema.processor ? schema.processor(options[prop]) : options[prop] : getDefaultValue(schema); + } + } + } + /** + * Report nonstrict (non-LaTeX-compatible) input. + * Can safely not be called if `this.strict` is false in JavaScript. + */ + + + reportNonstrict(errorCode, errorMsg, token) { + let strict = this.strict; + + if (typeof strict === "function") { + // Allow return value of strict function to be boolean or string + // (or null/undefined, meaning no further processing). + strict = strict(errorCode, errorMsg, token); + } + + if (!strict || strict === "ignore") { + return; + } else if (strict === true || strict === "error") { + throw new src_ParseError("LaTeX-incompatible input and strict mode is set to 'error': " + (errorMsg + " [" + errorCode + "]"), token); + } else if (strict === "warn") { + typeof console !== "undefined" && console.warn("LaTeX-incompatible input and strict mode is set to 'warn': " + (errorMsg + " [" + errorCode + "]")); + } else { + // won't happen in type-safe code + typeof console !== "undefined" && console.warn("LaTeX-incompatible input and strict mode is set to " + ("unrecognized '" + strict + "': " + errorMsg + " [" + errorCode + "]")); + } + } + /** + * Check whether to apply strict (LaTeX-adhering) behavior for unusual + * input (like `\\`). Unlike `nonstrict`, will not throw an error; + * instead, "error" translates to a return value of `true`, while "ignore" + * translates to a return value of `false`. May still print a warning: + * "warn" prints a warning and returns `false`. + * This is for the second category of `errorCode`s listed in the README. + */ + + + useStrictBehavior(errorCode, errorMsg, token) { + let strict = this.strict; + + if (typeof strict === "function") { + // Allow return value of strict function to be boolean or string + // (or null/undefined, meaning no further processing). + // But catch any exceptions thrown by function, treating them + // like "error". + try { + strict = strict(errorCode, errorMsg, token); + } catch (error) { + strict = "error"; + } + } + + if (!strict || strict === "ignore") { + return false; + } else if (strict === true || strict === "error") { + return true; + } else if (strict === "warn") { + typeof console !== "undefined" && console.warn("LaTeX-incompatible input and strict mode is set to 'warn': " + (errorMsg + " [" + errorCode + "]")); + return false; + } else { + // won't happen in type-safe code + typeof console !== "undefined" && console.warn("LaTeX-incompatible input and strict mode is set to " + ("unrecognized '" + strict + "': " + errorMsg + " [" + errorCode + "]")); + return false; + } + } + /** + * Check whether to test potentially dangerous input, and return + * `true` (trusted) or `false` (untrusted). The sole argument `context` + * should be an object with `command` field specifying the relevant LaTeX + * command (as a string starting with `\`), and any other arguments, etc. + * If `context` has a `url` field, a `protocol` field will automatically + * get added by this function (changing the specified object). + */ + + + isTrusted(context) { + if (context.url && !context.protocol) { + const protocol = utils.protocolFromUrl(context.url); + + if (protocol == null) { + return false; + } + + context.protocol = protocol; + } + + const trust = typeof this.trust === "function" ? this.trust(context) : this.trust; + return Boolean(trust); + } + +} +;// CONCATENATED MODULE: ./src/Style.js +/** + * This file contains information and classes for the various kinds of styles + * used in TeX. It provides a generic `Style` class, which holds information + * about a specific style. It then provides instances of all the different kinds + * of styles possible, and provides functions to move between them and get + * information about them. + */ + +/** + * The main style class. Contains a unique id for the style, a size (which is + * the same for cramped and uncramped version of a style), and a cramped flag. + */ +class Style { + constructor(id, size, cramped) { + this.id = void 0; + this.size = void 0; + this.cramped = void 0; + this.id = id; + this.size = size; + this.cramped = cramped; + } + /** + * Get the style of a superscript given a base in the current style. + */ + + + sup() { + return styles[sup[this.id]]; + } + /** + * Get the style of a subscript given a base in the current style. + */ + + + sub() { + return styles[sub[this.id]]; + } + /** + * Get the style of a fraction numerator given the fraction in the current + * style. + */ + + + fracNum() { + return styles[fracNum[this.id]]; + } + /** + * Get the style of a fraction denominator given the fraction in the current + * style. + */ + + + fracDen() { + return styles[fracDen[this.id]]; + } + /** + * Get the cramped version of a style (in particular, cramping a cramped style + * doesn't change the style). + */ + + + cramp() { + return styles[cramp[this.id]]; + } + /** + * Get a text or display version of this style. + */ + + + text() { + return styles[Style_text[this.id]]; + } + /** + * Return true if this style is tightly spaced (scriptstyle/scriptscriptstyle) + */ + + + isTight() { + return this.size >= 2; + } + +} // Export an interface for type checking, but don't expose the implementation. +// This way, no more styles can be generated. + + +// IDs of the different styles +const D = 0; +const Dc = 1; +const T = 2; +const Tc = 3; +const S = 4; +const Sc = 5; +const SS = 6; +const SSc = 7; // Instances of the different styles + +const styles = [new Style(D, 0, false), new Style(Dc, 0, true), new Style(T, 1, false), new Style(Tc, 1, true), new Style(S, 2, false), new Style(Sc, 2, true), new Style(SS, 3, false), new Style(SSc, 3, true)]; // Lookup tables for switching from one style to another + +const sup = [S, Sc, S, Sc, SS, SSc, SS, SSc]; +const sub = [Sc, Sc, Sc, Sc, SSc, SSc, SSc, SSc]; +const fracNum = [T, Tc, S, Sc, SS, SSc, SS, SSc]; +const fracDen = [Tc, Tc, Sc, Sc, SSc, SSc, SSc, SSc]; +const cramp = [Dc, Dc, Tc, Tc, Sc, Sc, SSc, SSc]; +const Style_text = [D, Dc, T, Tc, T, Tc, T, Tc]; // We only export some of the styles. + +/* harmony default export */ var src_Style = ({ + DISPLAY: styles[D], + TEXT: styles[T], + SCRIPT: styles[S], + SCRIPTSCRIPT: styles[SS] +}); +;// CONCATENATED MODULE: ./src/unicodeScripts.js +/* + * This file defines the Unicode scripts and script families that we + * support. To add new scripts or families, just add a new entry to the + * scriptData array below. Adding scripts to the scriptData array allows + * characters from that script to appear in \text{} environments. + */ + +/** + * Each script or script family has a name and an array of blocks. + * Each block is an array of two numbers which specify the start and + * end points (inclusive) of a block of Unicode codepoints. + */ + +/** + * Unicode block data for the families of scripts we support in \text{}. + * Scripts only need to appear here if they do not have font metrics. + */ +const scriptData = [{ + // Latin characters beyond the Latin-1 characters we have metrics for. + // Needed for Czech, Hungarian and Turkish text, for example. + name: 'latin', + blocks: [[0x0100, 0x024f], // Latin Extended-A and Latin Extended-B + [0x0300, 0x036f] // Combining Diacritical marks + ] +}, { + // The Cyrillic script used by Russian and related languages. + // A Cyrillic subset used to be supported as explicitly defined + // symbols in symbols.js + name: 'cyrillic', + blocks: [[0x0400, 0x04ff]] +}, { + // Armenian + name: 'armenian', + blocks: [[0x0530, 0x058F]] +}, { + // The Brahmic scripts of South and Southeast Asia + // Devanagari (0900–097F) + // Bengali (0980–09FF) + // Gurmukhi (0A00–0A7F) + // Gujarati (0A80–0AFF) + // Oriya (0B00–0B7F) + // Tamil (0B80–0BFF) + // Telugu (0C00–0C7F) + // Kannada (0C80–0CFF) + // Malayalam (0D00–0D7F) + // Sinhala (0D80–0DFF) + // Thai (0E00–0E7F) + // Lao (0E80–0EFF) + // Tibetan (0F00–0FFF) + // Myanmar (1000–109F) + name: 'brahmic', + blocks: [[0x0900, 0x109F]] +}, { + name: 'georgian', + blocks: [[0x10A0, 0x10ff]] +}, { + // Chinese and Japanese. + // The "k" in cjk is for Korean, but we've separated Korean out + name: "cjk", + blocks: [[0x3000, 0x30FF], // CJK symbols and punctuation, Hiragana, Katakana + [0x4E00, 0x9FAF], // CJK ideograms + [0xFF00, 0xFF60] // Fullwidth punctuation + // TODO: add halfwidth Katakana and Romanji glyphs + ] +}, { + // Korean + name: 'hangul', + blocks: [[0xAC00, 0xD7AF]] +}]; +/** + * Given a codepoint, return the name of the script or script family + * it is from, or null if it is not part of a known block + */ + +function scriptFromCodepoint(codepoint) { + for (let i = 0; i < scriptData.length; i++) { + const script = scriptData[i]; + + for (let i = 0; i < script.blocks.length; i++) { + const block = script.blocks[i]; + + if (codepoint >= block[0] && codepoint <= block[1]) { + return script.name; + } + } + } + + return null; +} +/** + * A flattened version of all the supported blocks in a single array. + * This is an optimization to make supportedCodepoint() fast. + */ + +const allBlocks = []; +scriptData.forEach(s => s.blocks.forEach(b => allBlocks.push(...b))); +/** + * Given a codepoint, return true if it falls within one of the + * scripts or script families defined above and false otherwise. + * + * Micro benchmarks shows that this is faster than + * /[\u3000-\u30FF\u4E00-\u9FAF\uFF00-\uFF60\uAC00-\uD7AF\u0900-\u109F]/.test() + * in Firefox, Chrome and Node. + */ + +function supportedCodepoint(codepoint) { + for (let i = 0; i < allBlocks.length; i += 2) { + if (codepoint >= allBlocks[i] && codepoint <= allBlocks[i + 1]) { + return true; + } + } + + return false; +} +;// CONCATENATED MODULE: ./src/svgGeometry.js +/** + * This file provides support to domTree.js and delimiter.js. + * It's a storehouse of path geometry for SVG images. + */ +// In all paths below, the viewBox-to-em scale is 1000:1. +const hLinePad = 80; // padding above a sqrt vinculum. Prevents image cropping. +// The vinculum of a \sqrt can be made thicker by a KaTeX rendering option. +// Think of variable extraVinculum as two detours in the SVG path. +// The detour begins at the lower left of the area labeled extraVinculum below. +// The detour proceeds one extraVinculum distance up and slightly to the right, +// displacing the radiused corner between surd and vinculum. The radius is +// traversed as usual, then the detour resumes. It goes right, to the end of +// the very long vinculum, then down one extraVinculum distance, +// after which it resumes regular path geometry for the radical. + +/* vinculum + / + /▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒←extraVinculum + / █████████████████████←0.04em (40 unit) std vinculum thickness + / / + / / + / /\ + / / surd +*/ + +const sqrtMain = function (extraVinculum, hLinePad) { + // sqrtMain path geometry is from glyph U221A in the font KaTeX Main + return "M95," + (622 + extraVinculum + hLinePad) + "\nc-2.7,0,-7.17,-2.7,-13.5,-8c-5.8,-5.3,-9.5,-10,-9.5,-14\nc0,-2,0.3,-3.3,1,-4c1.3,-2.7,23.83,-20.7,67.5,-54\nc44.2,-33.3,65.8,-50.3,66.5,-51c1.3,-1.3,3,-2,5,-2c4.7,0,8.7,3.3,12,10\ns173,378,173,378c0.7,0,35.3,-71,104,-213c68.7,-142,137.5,-285,206.5,-429\nc69,-144,104.5,-217.7,106.5,-221\nl" + extraVinculum / 2.075 + " -" + extraVinculum + "\nc5.3,-9.3,12,-14,20,-14\nH400000v" + (40 + extraVinculum) + "H845.2724\ns-225.272,467,-225.272,467s-235,486,-235,486c-2.7,4.7,-9,7,-19,7\nc-6,0,-10,-1,-12,-3s-194,-422,-194,-422s-65,47,-65,47z\nM" + (834 + extraVinculum) + " " + hLinePad + "h400000v" + (40 + extraVinculum) + "h-400000z"; +}; + +const sqrtSize1 = function (extraVinculum, hLinePad) { + // size1 is from glyph U221A in the font KaTeX_Size1-Regular + return "M263," + (601 + extraVinculum + hLinePad) + "c0.7,0,18,39.7,52,119\nc34,79.3,68.167,158.7,102.5,238c34.3,79.3,51.8,119.3,52.5,120\nc340,-704.7,510.7,-1060.3,512,-1067\nl" + extraVinculum / 2.084 + " -" + extraVinculum + "\nc4.7,-7.3,11,-11,19,-11\nH40000v" + (40 + extraVinculum) + "H1012.3\ns-271.3,567,-271.3,567c-38.7,80.7,-84,175,-136,283c-52,108,-89.167,185.3,-111.5,232\nc-22.3,46.7,-33.8,70.3,-34.5,71c-4.7,4.7,-12.3,7,-23,7s-12,-1,-12,-1\ns-109,-253,-109,-253c-72.7,-168,-109.3,-252,-110,-252c-10.7,8,-22,16.7,-34,26\nc-22,17.3,-33.3,26,-34,26s-26,-26,-26,-26s76,-59,76,-59s76,-60,76,-60z\nM" + (1001 + extraVinculum) + " " + hLinePad + "h400000v" + (40 + extraVinculum) + "h-400000z"; +}; + +const sqrtSize2 = function (extraVinculum, hLinePad) { + // size2 is from glyph U221A in the font KaTeX_Size2-Regular + return "M983 " + (10 + extraVinculum + hLinePad) + "\nl" + extraVinculum / 3.13 + " -" + extraVinculum + "\nc4,-6.7,10,-10,18,-10 H400000v" + (40 + extraVinculum) + "\nH1013.1s-83.4,268,-264.1,840c-180.7,572,-277,876.3,-289,913c-4.7,4.7,-12.7,7,-24,7\ns-12,0,-12,0c-1.3,-3.3,-3.7,-11.7,-7,-25c-35.3,-125.3,-106.7,-373.3,-214,-744\nc-10,12,-21,25,-33,39s-32,39,-32,39c-6,-5.3,-15,-14,-27,-26s25,-30,25,-30\nc26.7,-32.7,52,-63,76,-91s52,-60,52,-60s208,722,208,722\nc56,-175.3,126.3,-397.3,211,-666c84.7,-268.7,153.8,-488.2,207.5,-658.5\nc53.7,-170.3,84.5,-266.8,92.5,-289.5z\nM" + (1001 + extraVinculum) + " " + hLinePad + "h400000v" + (40 + extraVinculum) + "h-400000z"; +}; + +const sqrtSize3 = function (extraVinculum, hLinePad) { + // size3 is from glyph U221A in the font KaTeX_Size3-Regular + return "M424," + (2398 + extraVinculum + hLinePad) + "\nc-1.3,-0.7,-38.5,-172,-111.5,-514c-73,-342,-109.8,-513.3,-110.5,-514\nc0,-2,-10.7,14.3,-32,49c-4.7,7.3,-9.8,15.7,-15.5,25c-5.7,9.3,-9.8,16,-12.5,20\ns-5,7,-5,7c-4,-3.3,-8.3,-7.7,-13,-13s-13,-13,-13,-13s76,-122,76,-122s77,-121,77,-121\ns209,968,209,968c0,-2,84.7,-361.7,254,-1079c169.3,-717.3,254.7,-1077.7,256,-1081\nl" + extraVinculum / 4.223 + " -" + extraVinculum + "c4,-6.7,10,-10,18,-10 H400000\nv" + (40 + extraVinculum) + "H1014.6\ns-87.3,378.7,-272.6,1166c-185.3,787.3,-279.3,1182.3,-282,1185\nc-2,6,-10,9,-24,9\nc-8,0,-12,-0.7,-12,-2z M" + (1001 + extraVinculum) + " " + hLinePad + "\nh400000v" + (40 + extraVinculum) + "h-400000z"; +}; + +const sqrtSize4 = function (extraVinculum, hLinePad) { + // size4 is from glyph U221A in the font KaTeX_Size4-Regular + return "M473," + (2713 + extraVinculum + hLinePad) + "\nc339.3,-1799.3,509.3,-2700,510,-2702 l" + extraVinculum / 5.298 + " -" + extraVinculum + "\nc3.3,-7.3,9.3,-11,18,-11 H400000v" + (40 + extraVinculum) + "H1017.7\ns-90.5,478,-276.2,1466c-185.7,988,-279.5,1483,-281.5,1485c-2,6,-10,9,-24,9\nc-8,0,-12,-0.7,-12,-2c0,-1.3,-5.3,-32,-16,-92c-50.7,-293.3,-119.7,-693.3,-207,-1200\nc0,-1.3,-5.3,8.7,-16,30c-10.7,21.3,-21.3,42.7,-32,64s-16,33,-16,33s-26,-26,-26,-26\ns76,-153,76,-153s77,-151,77,-151c0.7,0.7,35.7,202,105,604c67.3,400.7,102,602.7,104,\n606zM" + (1001 + extraVinculum) + " " + hLinePad + "h400000v" + (40 + extraVinculum) + "H1017.7z"; +}; + +const phasePath = function (y) { + const x = y / 2; // x coordinate at top of angle + + return "M400000 " + y + " H0 L" + x + " 0 l65 45 L145 " + (y - 80) + " H400000z"; +}; + +const sqrtTall = function (extraVinculum, hLinePad, viewBoxHeight) { + // sqrtTall is from glyph U23B7 in the font KaTeX_Size4-Regular + // One path edge has a variable length. It runs vertically from the vinculum + // to a point near (14 units) the bottom of the surd. The vinculum + // is normally 40 units thick. So the length of the line in question is: + const vertSegment = viewBoxHeight - 54 - hLinePad - extraVinculum; + return "M702 " + (extraVinculum + hLinePad) + "H400000" + (40 + extraVinculum) + "\nH742v" + vertSegment + "l-4 4-4 4c-.667.7 -2 1.5-4 2.5s-4.167 1.833-6.5 2.5-5.5 1-9.5 1\nh-12l-28-84c-16.667-52-96.667 -294.333-240-727l-212 -643 -85 170\nc-4-3.333-8.333-7.667-13 -13l-13-13l77-155 77-156c66 199.333 139 419.667\n219 661 l218 661zM702 " + hLinePad + "H400000v" + (40 + extraVinculum) + "H742z"; +}; + +const sqrtPath = function (size, extraVinculum, viewBoxHeight) { + extraVinculum = 1000 * extraVinculum; // Convert from document ems to viewBox. + + let path = ""; + + switch (size) { + case "sqrtMain": + path = sqrtMain(extraVinculum, hLinePad); + break; + + case "sqrtSize1": + path = sqrtSize1(extraVinculum, hLinePad); + break; + + case "sqrtSize2": + path = sqrtSize2(extraVinculum, hLinePad); + break; + + case "sqrtSize3": + path = sqrtSize3(extraVinculum, hLinePad); + break; + + case "sqrtSize4": + path = sqrtSize4(extraVinculum, hLinePad); + break; + + case "sqrtTall": + path = sqrtTall(extraVinculum, hLinePad, viewBoxHeight); + } + + return path; +}; +const innerPath = function (name, height) { + // The inner part of stretchy tall delimiters + switch (name) { + case "\u239c": + return "M291 0 H417 V" + height + " H291z M291 0 H417 V" + height + " H291z"; + + case "\u2223": + return "M145 0 H188 V" + height + " H145z M145 0 H188 V" + height + " H145z"; + + case "\u2225": + return "M145 0 H188 V" + height + " H145z M145 0 H188 V" + height + " H145z" + ("M367 0 H410 V" + height + " H367z M367 0 H410 V" + height + " H367z"); + + case "\u239f": + return "M457 0 H583 V" + height + " H457z M457 0 H583 V" + height + " H457z"; + + case "\u23a2": + return "M319 0 H403 V" + height + " H319z M319 0 H403 V" + height + " H319z"; + + case "\u23a5": + return "M263 0 H347 V" + height + " H263z M263 0 H347 V" + height + " H263z"; + + case "\u23aa": + return "M384 0 H504 V" + height + " H384z M384 0 H504 V" + height + " H384z"; + + case "\u23d0": + return "M312 0 H355 V" + height + " H312z M312 0 H355 V" + height + " H312z"; + + case "\u2016": + return "M257 0 H300 V" + height + " H257z M257 0 H300 V" + height + " H257z" + ("M478 0 H521 V" + height + " H478z M478 0 H521 V" + height + " H478z"); + + default: + return ""; + } +}; +const path = { + // The doubleleftarrow geometry is from glyph U+21D0 in the font KaTeX Main + doubleleftarrow: "M262 157\nl10-10c34-36 62.7-77 86-123 3.3-8 5-13.3 5-16 0-5.3-6.7-8-20-8-7.3\n 0-12.2.5-14.5 1.5-2.3 1-4.8 4.5-7.5 10.5-49.3 97.3-121.7 169.3-217 216-28\n 14-57.3 25-88 33-6.7 2-11 3.8-13 5.5-2 1.7-3 4.2-3 7.5s1 5.8 3 7.5\nc2 1.7 6.3 3.5 13 5.5 68 17.3 128.2 47.8 180.5 91.5 52.3 43.7 93.8 96.2 124.5\n 157.5 9.3 8 15.3 12.3 18 13h6c12-.7 18-4 18-10 0-2-1.7-7-5-15-23.3-46-52-87\n-86-123l-10-10h399738v-40H218c328 0 0 0 0 0l-10-8c-26.7-20-65.7-43-117-69 2.7\n-2 6-3.7 10-5 36.7-16 72.3-37.3 107-64l10-8h399782v-40z\nm8 0v40h399730v-40zm0 194v40h399730v-40z", + // doublerightarrow is from glyph U+21D2 in font KaTeX Main + doublerightarrow: "M399738 392l\n-10 10c-34 36-62.7 77-86 123-3.3 8-5 13.3-5 16 0 5.3 6.7 8 20 8 7.3 0 12.2-.5\n 14.5-1.5 2.3-1 4.8-4.5 7.5-10.5 49.3-97.3 121.7-169.3 217-216 28-14 57.3-25 88\n-33 6.7-2 11-3.8 13-5.5 2-1.7 3-4.2 3-7.5s-1-5.8-3-7.5c-2-1.7-6.3-3.5-13-5.5-68\n-17.3-128.2-47.8-180.5-91.5-52.3-43.7-93.8-96.2-124.5-157.5-9.3-8-15.3-12.3-18\n-13h-6c-12 .7-18 4-18 10 0 2 1.7 7 5 15 23.3 46 52 87 86 123l10 10H0v40h399782\nc-328 0 0 0 0 0l10 8c26.7 20 65.7 43 117 69-2.7 2-6 3.7-10 5-36.7 16-72.3 37.3\n-107 64l-10 8H0v40zM0 157v40h399730v-40zm0 194v40h399730v-40z", + // leftarrow is from glyph U+2190 in font KaTeX Main + leftarrow: "M400000 241H110l3-3c68.7-52.7 113.7-120\n 135-202 4-14.7 6-23 6-25 0-7.3-7-11-21-11-8 0-13.2.8-15.5 2.5-2.3 1.7-4.2 5.8\n-5.5 12.5-1.3 4.7-2.7 10.3-4 17-12 48.7-34.8 92-68.5 130S65.3 228.3 18 247\nc-10 4-16 7.7-18 11 0 8.7 6 14.3 18 17 47.3 18.7 87.8 47 121.5 85S196 441.3 208\n 490c.7 2 1.3 5 2 9s1.2 6.7 1.5 8c.3 1.3 1 3.3 2 6s2.2 4.5 3.5 5.5c1.3 1 3.3\n 1.8 6 2.5s6 1 10 1c14 0 21-3.7 21-11 0-2-2-10.3-6-25-20-79.3-65-146.7-135-202\n l-3-3h399890zM100 241v40h399900v-40z", + // overbrace is from glyphs U+23A9/23A8/23A7 in font KaTeX_Size4-Regular + leftbrace: "M6 548l-6-6v-35l6-11c56-104 135.3-181.3 238-232 57.3-28.7 117\n-45 179-50h399577v120H403c-43.3 7-81 15-113 26-100.7 33-179.7 91-237 174-2.7\n 5-6 9-10 13-.7 1-7.3 1-20 1H6z", + leftbraceunder: "M0 6l6-6h17c12.688 0 19.313.3 20 1 4 4 7.313 8.3 10 13\n 35.313 51.3 80.813 93.8 136.5 127.5 55.688 33.7 117.188 55.8 184.5 66.5.688\n 0 2 .3 4 1 18.688 2.7 76 4.3 172 5h399450v120H429l-6-1c-124.688-8-235-61.7\n-331-161C60.687 138.7 32.312 99.3 7 54L0 41V6z", + // overgroup is from the MnSymbol package (public domain) + leftgroup: "M400000 80\nH435C64 80 168.3 229.4 21 260c-5.9 1.2-18 0-18 0-2 0-3-1-3-3v-38C76 61 257 0\n 435 0h399565z", + leftgroupunder: "M400000 262\nH435C64 262 168.3 112.6 21 82c-5.9-1.2-18 0-18 0-2 0-3 1-3 3v38c76 158 257 219\n 435 219h399565z", + // Harpoons are from glyph U+21BD in font KaTeX Main + leftharpoon: "M0 267c.7 5.3 3 10 7 14h399993v-40H93c3.3\n-3.3 10.2-9.5 20.5-18.5s17.8-15.8 22.5-20.5c50.7-52 88-110.3 112-175 4-11.3 5\n-18.3 3-21-1.3-4-7.3-6-18-6-8 0-13 .7-15 2s-4.7 6.7-8 16c-42 98.7-107.3 174.7\n-196 228-6.7 4.7-10.7 8-12 10-1.3 2-2 5.7-2 11zm100-26v40h399900v-40z", + leftharpoonplus: "M0 267c.7 5.3 3 10 7 14h399993v-40H93c3.3-3.3 10.2-9.5\n 20.5-18.5s17.8-15.8 22.5-20.5c50.7-52 88-110.3 112-175 4-11.3 5-18.3 3-21-1.3\n-4-7.3-6-18-6-8 0-13 .7-15 2s-4.7 6.7-8 16c-42 98.7-107.3 174.7-196 228-6.7 4.7\n-10.7 8-12 10-1.3 2-2 5.7-2 11zm100-26v40h399900v-40zM0 435v40h400000v-40z\nm0 0v40h400000v-40z", + leftharpoondown: "M7 241c-4 4-6.333 8.667-7 14 0 5.333.667 9 2 11s5.333\n 5.333 12 10c90.667 54 156 130 196 228 3.333 10.667 6.333 16.333 9 17 2 .667 5\n 1 9 1h5c10.667 0 16.667-2 18-6 2-2.667 1-9.667-3-21-32-87.333-82.667-157.667\n-152-211l-3-3h399907v-40zM93 281 H400000 v-40L7 241z", + leftharpoondownplus: "M7 435c-4 4-6.3 8.7-7 14 0 5.3.7 9 2 11s5.3 5.3 12\n 10c90.7 54 156 130 196 228 3.3 10.7 6.3 16.3 9 17 2 .7 5 1 9 1h5c10.7 0 16.7\n-2 18-6 2-2.7 1-9.7-3-21-32-87.3-82.7-157.7-152-211l-3-3h399907v-40H7zm93 0\nv40h399900v-40zM0 241v40h399900v-40zm0 0v40h399900v-40z", + // hook is from glyph U+21A9 in font KaTeX Main + lefthook: "M400000 281 H103s-33-11.2-61-33.5S0 197.3 0 164s14.2-61.2 42.5\n-83.5C70.8 58.2 104 47 142 47 c16.7 0 25 6.7 25 20 0 12-8.7 18.7-26 20-40 3.3\n-68.7 15.7-86 37-10 12-15 25.3-15 40 0 22.7 9.8 40.7 29.5 54 19.7 13.3 43.5 21\n 71.5 23h399859zM103 281v-40h399897v40z", + leftlinesegment: "M40 281 V428 H0 V94 H40 V241 H400000 v40z\nM40 281 V428 H0 V94 H40 V241 H400000 v40z", + leftmapsto: "M40 281 V448H0V74H40V241H400000v40z\nM40 281 V448H0V74H40V241H400000v40z", + // tofrom is from glyph U+21C4 in font KaTeX AMS Regular + leftToFrom: "M0 147h400000v40H0zm0 214c68 40 115.7 95.7 143 167h22c15.3 0 23\n-.3 23-1 0-1.3-5.3-13.7-16-37-18-35.3-41.3-69-70-101l-7-8h399905v-40H95l7-8\nc28.7-32 52-65.7 70-101 10.7-23.3 16-35.7 16-37 0-.7-7.7-1-23-1h-22C115.7 265.3\n 68 321 0 361zm0-174v-40h399900v40zm100 154v40h399900v-40z", + longequal: "M0 50 h400000 v40H0z m0 194h40000v40H0z\nM0 50 h400000 v40H0z m0 194h40000v40H0z", + midbrace: "M200428 334\nc-100.7-8.3-195.3-44-280-108-55.3-42-101.7-93-139-153l-9-14c-2.7 4-5.7 8.7-9 14\n-53.3 86.7-123.7 153-211 199-66.7 36-137.3 56.3-212 62H0V214h199568c178.3-11.7\n 311.7-78.3 403-201 6-8 9.7-12 11-12 .7-.7 6.7-1 18-1s17.3.3 18 1c1.3 0 5 4 11\n 12 44.7 59.3 101.3 106.3 170 141s145.3 54.3 229 60h199572v120z", + midbraceunder: "M199572 214\nc100.7 8.3 195.3 44 280 108 55.3 42 101.7 93 139 153l9 14c2.7-4 5.7-8.7 9-14\n 53.3-86.7 123.7-153 211-199 66.7-36 137.3-56.3 212-62h199568v120H200432c-178.3\n 11.7-311.7 78.3-403 201-6 8-9.7 12-11 12-.7.7-6.7 1-18 1s-17.3-.3-18-1c-1.3 0\n-5-4-11-12-44.7-59.3-101.3-106.3-170-141s-145.3-54.3-229-60H0V214z", + oiintSize1: "M512.6 71.6c272.6 0 320.3 106.8 320.3 178.2 0 70.8-47.7 177.6\n-320.3 177.6S193.1 320.6 193.1 249.8c0-71.4 46.9-178.2 319.5-178.2z\nm368.1 178.2c0-86.4-60.9-215.4-368.1-215.4-306.4 0-367.3 129-367.3 215.4 0 85.8\n60.9 214.8 367.3 214.8 307.2 0 368.1-129 368.1-214.8z", + oiintSize2: "M757.8 100.1c384.7 0 451.1 137.6 451.1 230 0 91.3-66.4 228.8\n-451.1 228.8-386.3 0-452.7-137.5-452.7-228.8 0-92.4 66.4-230 452.7-230z\nm502.4 230c0-111.2-82.4-277.2-502.4-277.2s-504 166-504 277.2\nc0 110 84 276 504 276s502.4-166 502.4-276z", + oiiintSize1: "M681.4 71.6c408.9 0 480.5 106.8 480.5 178.2 0 70.8-71.6 177.6\n-480.5 177.6S202.1 320.6 202.1 249.8c0-71.4 70.5-178.2 479.3-178.2z\nm525.8 178.2c0-86.4-86.8-215.4-525.7-215.4-437.9 0-524.7 129-524.7 215.4 0\n85.8 86.8 214.8 524.7 214.8 438.9 0 525.7-129 525.7-214.8z", + oiiintSize2: "M1021.2 53c603.6 0 707.8 165.8 707.8 277.2 0 110-104.2 275.8\n-707.8 275.8-606 0-710.2-165.8-710.2-275.8C311 218.8 415.2 53 1021.2 53z\nm770.4 277.1c0-131.2-126.4-327.6-770.5-327.6S248.4 198.9 248.4 330.1\nc0 130 128.8 326.4 772.7 326.4s770.5-196.4 770.5-326.4z", + rightarrow: "M0 241v40h399891c-47.3 35.3-84 78-110 128\n-16.7 32-27.7 63.7-33 95 0 1.3-.2 2.7-.5 4-.3 1.3-.5 2.3-.5 3 0 7.3 6.7 11 20\n 11 8 0 13.2-.8 15.5-2.5 2.3-1.7 4.2-5.5 5.5-11.5 2-13.3 5.7-27 11-41 14.7-44.7\n 39-84.5 73-119.5s73.7-60.2 119-75.5c6-2 9-5.7 9-11s-3-9-9-11c-45.3-15.3-85\n-40.5-119-75.5s-58.3-74.8-73-119.5c-4.7-14-8.3-27.3-11-40-1.3-6.7-3.2-10.8-5.5\n-12.5-2.3-1.7-7.5-2.5-15.5-2.5-14 0-21 3.7-21 11 0 2 2 10.3 6 25 20.7 83.3 67\n 151.7 139 205zm0 0v40h399900v-40z", + rightbrace: "M400000 542l\n-6 6h-17c-12.7 0-19.3-.3-20-1-4-4-7.3-8.3-10-13-35.3-51.3-80.8-93.8-136.5-127.5\ns-117.2-55.8-184.5-66.5c-.7 0-2-.3-4-1-18.7-2.7-76-4.3-172-5H0V214h399571l6 1\nc124.7 8 235 61.7 331 161 31.3 33.3 59.7 72.7 85 118l7 13v35z", + rightbraceunder: "M399994 0l6 6v35l-6 11c-56 104-135.3 181.3-238 232-57.3\n 28.7-117 45-179 50H-300V214h399897c43.3-7 81-15 113-26 100.7-33 179.7-91 237\n-174 2.7-5 6-9 10-13 .7-1 7.3-1 20-1h17z", + rightgroup: "M0 80h399565c371 0 266.7 149.4 414 180 5.9 1.2 18 0 18 0 2 0\n 3-1 3-3v-38c-76-158-257-219-435-219H0z", + rightgroupunder: "M0 262h399565c371 0 266.7-149.4 414-180 5.9-1.2 18 0 18\n 0 2 0 3 1 3 3v38c-76 158-257 219-435 219H0z", + rightharpoon: "M0 241v40h399993c4.7-4.7 7-9.3 7-14 0-9.3\n-3.7-15.3-11-18-92.7-56.7-159-133.7-199-231-3.3-9.3-6-14.7-8-16-2-1.3-7-2-15-2\n-10.7 0-16.7 2-18 6-2 2.7-1 9.7 3 21 15.3 42 36.7 81.8 64 119.5 27.3 37.7 58\n 69.2 92 94.5zm0 0v40h399900v-40z", + rightharpoonplus: "M0 241v40h399993c4.7-4.7 7-9.3 7-14 0-9.3-3.7-15.3-11\n-18-92.7-56.7-159-133.7-199-231-3.3-9.3-6-14.7-8-16-2-1.3-7-2-15-2-10.7 0-16.7\n 2-18 6-2 2.7-1 9.7 3 21 15.3 42 36.7 81.8 64 119.5 27.3 37.7 58 69.2 92 94.5z\nm0 0v40h399900v-40z m100 194v40h399900v-40zm0 0v40h399900v-40z", + rightharpoondown: "M399747 511c0 7.3 6.7 11 20 11 8 0 13-.8 15-2.5s4.7-6.8\n 8-15.5c40-94 99.3-166.3 178-217 13.3-8 20.3-12.3 21-13 5.3-3.3 8.5-5.8 9.5\n-7.5 1-1.7 1.5-5.2 1.5-10.5s-2.3-10.3-7-15H0v40h399908c-34 25.3-64.7 57-92 95\n-27.3 38-48.7 77.7-64 119-3.3 8.7-5 14-5 16zM0 241v40h399900v-40z", + rightharpoondownplus: "M399747 705c0 7.3 6.7 11 20 11 8 0 13-.8\n 15-2.5s4.7-6.8 8-15.5c40-94 99.3-166.3 178-217 13.3-8 20.3-12.3 21-13 5.3-3.3\n 8.5-5.8 9.5-7.5 1-1.7 1.5-5.2 1.5-10.5s-2.3-10.3-7-15H0v40h399908c-34 25.3\n-64.7 57-92 95-27.3 38-48.7 77.7-64 119-3.3 8.7-5 14-5 16zM0 435v40h399900v-40z\nm0-194v40h400000v-40zm0 0v40h400000v-40z", + righthook: "M399859 241c-764 0 0 0 0 0 40-3.3 68.7-15.7 86-37 10-12 15-25.3\n 15-40 0-22.7-9.8-40.7-29.5-54-19.7-13.3-43.5-21-71.5-23-17.3-1.3-26-8-26-20 0\n-13.3 8.7-20 26-20 38 0 71 11.2 99 33.5 0 0 7 5.6 21 16.7 14 11.2 21 33.5 21\n 66.8s-14 61.2-42 83.5c-28 22.3-61 33.5-99 33.5L0 241z M0 281v-40h399859v40z", + rightlinesegment: "M399960 241 V94 h40 V428 h-40 V281 H0 v-40z\nM399960 241 V94 h40 V428 h-40 V281 H0 v-40z", + rightToFrom: "M400000 167c-70.7-42-118-97.7-142-167h-23c-15.3 0-23 .3-23\n 1 0 1.3 5.3 13.7 16 37 18 35.3 41.3 69 70 101l7 8H0v40h399905l-7 8c-28.7 32\n-52 65.7-70 101-10.7 23.3-16 35.7-16 37 0 .7 7.7 1 23 1h23c24-69.3 71.3-125 142\n-167z M100 147v40h399900v-40zM0 341v40h399900v-40z", + // twoheadleftarrow is from glyph U+219E in font KaTeX AMS Regular + twoheadleftarrow: "M0 167c68 40\n 115.7 95.7 143 167h22c15.3 0 23-.3 23-1 0-1.3-5.3-13.7-16-37-18-35.3-41.3-69\n-70-101l-7-8h125l9 7c50.7 39.3 85 86 103 140h46c0-4.7-6.3-18.7-19-42-18-35.3\n-40-67.3-66-96l-9-9h399716v-40H284l9-9c26-28.7 48-60.7 66-96 12.7-23.333 19\n-37.333 19-42h-46c-18 54-52.3 100.7-103 140l-9 7H95l7-8c28.7-32 52-65.7 70-101\n 10.7-23.333 16-35.7 16-37 0-.7-7.7-1-23-1h-22C115.7 71.3 68 127 0 167z", + twoheadrightarrow: "M400000 167\nc-68-40-115.7-95.7-143-167h-22c-15.3 0-23 .3-23 1 0 1.3 5.3 13.7 16 37 18 35.3\n 41.3 69 70 101l7 8h-125l-9-7c-50.7-39.3-85-86-103-140h-46c0 4.7 6.3 18.7 19 42\n 18 35.3 40 67.3 66 96l9 9H0v40h399716l-9 9c-26 28.7-48 60.7-66 96-12.7 23.333\n-19 37.333-19 42h46c18-54 52.3-100.7 103-140l9-7h125l-7 8c-28.7 32-52 65.7-70\n 101-10.7 23.333-16 35.7-16 37 0 .7 7.7 1 23 1h22c27.3-71.3 75-127 143-167z", + // tilde1 is a modified version of a glyph from the MnSymbol package + tilde1: "M200 55.538c-77 0-168 73.953-177 73.953-3 0-7\n-2.175-9-5.437L2 97c-1-2-2-4-2-6 0-4 2-7 5-9l20-12C116 12 171 0 207 0c86 0\n 114 68 191 68 78 0 168-68 177-68 4 0 7 2 9 5l12 19c1 2.175 2 4.35 2 6.525 0\n 4.35-2 7.613-5 9.788l-19 13.05c-92 63.077-116.937 75.308-183 76.128\n-68.267.847-113-73.952-191-73.952z", + // ditto tilde2, tilde3, & tilde4 + tilde2: "M344 55.266c-142 0-300.638 81.316-311.5 86.418\n-8.01 3.762-22.5 10.91-23.5 5.562L1 120c-1-2-1-3-1-4 0-5 3-9 8-10l18.4-9C160.9\n 31.9 283 0 358 0c148 0 188 122 331 122s314-97 326-97c4 0 8 2 10 7l7 21.114\nc1 2.14 1 3.21 1 4.28 0 5.347-3 9.626-7 10.696l-22.3 12.622C852.6 158.372 751\n 181.476 676 181.476c-149 0-189-126.21-332-126.21z", + tilde3: "M786 59C457 59 32 175.242 13 175.242c-6 0-10-3.457\n-11-10.37L.15 138c-1-7 3-12 10-13l19.2-6.4C378.4 40.7 634.3 0 804.3 0c337 0\n 411.8 157 746.8 157 328 0 754-112 773-112 5 0 10 3 11 9l1 14.075c1 8.066-.697\n 16.595-6.697 17.492l-21.052 7.31c-367.9 98.146-609.15 122.696-778.15 122.696\n -338 0-409-156.573-744-156.573z", + tilde4: "M786 58C457 58 32 177.487 13 177.487c-6 0-10-3.345\n-11-10.035L.15 143c-1-7 3-12 10-13l22-6.7C381.2 35 637.15 0 807.15 0c337 0 409\n 177 744 177 328 0 754-127 773-127 5 0 10 3 11 9l1 14.794c1 7.805-3 13.38-9\n 14.495l-20.7 5.574c-366.85 99.79-607.3 139.372-776.3 139.372-338 0-409\n -175.236-744-175.236z", + // vec is from glyph U+20D7 in font KaTeX Main + vec: "M377 20c0-5.333 1.833-10 5.5-14S391 0 397 0c4.667 0 8.667 1.667 12 5\n3.333 2.667 6.667 9 10 19 6.667 24.667 20.333 43.667 41 57 7.333 4.667 11\n10.667 11 18 0 6-1 10-3 12s-6.667 5-14 9c-28.667 14.667-53.667 35.667-75 63\n-1.333 1.333-3.167 3.5-5.5 6.5s-4 4.833-5 5.5c-1 .667-2.5 1.333-4.5 2s-4.333 1\n-7 1c-4.667 0-9.167-1.833-13.5-5.5S337 184 337 178c0-12.667 15.667-32.333 47-59\nH213l-171-1c-8.667-6-13-12.333-13-19 0-4.667 4.333-11.333 13-20h359\nc-16-25.333-24-45-24-59z", + // widehat1 is a modified version of a glyph from the MnSymbol package + widehat1: "M529 0h5l519 115c5 1 9 5 9 10 0 1-1 2-1 3l-4 22\nc-1 5-5 9-11 9h-2L532 67 19 159h-2c-5 0-9-4-11-9l-5-22c-1-6 2-12 8-13z", + // ditto widehat2, widehat3, & widehat4 + widehat2: "M1181 0h2l1171 176c6 0 10 5 10 11l-2 23c-1 6-5 10\n-11 10h-1L1182 67 15 220h-1c-6 0-10-4-11-10l-2-23c-1-6 4-11 10-11z", + widehat3: "M1181 0h2l1171 236c6 0 10 5 10 11l-2 23c-1 6-5 10\n-11 10h-1L1182 67 15 280h-1c-6 0-10-4-11-10l-2-23c-1-6 4-11 10-11z", + widehat4: "M1181 0h2l1171 296c6 0 10 5 10 11l-2 23c-1 6-5 10\n-11 10h-1L1182 67 15 340h-1c-6 0-10-4-11-10l-2-23c-1-6 4-11 10-11z", + // widecheck paths are all inverted versions of widehat + widecheck1: "M529,159h5l519,-115c5,-1,9,-5,9,-10c0,-1,-1,-2,-1,-3l-4,-22c-1,\n-5,-5,-9,-11,-9h-2l-512,92l-513,-92h-2c-5,0,-9,4,-11,9l-5,22c-1,6,2,12,8,13z", + widecheck2: "M1181,220h2l1171,-176c6,0,10,-5,10,-11l-2,-23c-1,-6,-5,-10,\n-11,-10h-1l-1168,153l-1167,-153h-1c-6,0,-10,4,-11,10l-2,23c-1,6,4,11,10,11z", + widecheck3: "M1181,280h2l1171,-236c6,0,10,-5,10,-11l-2,-23c-1,-6,-5,-10,\n-11,-10h-1l-1168,213l-1167,-213h-1c-6,0,-10,4,-11,10l-2,23c-1,6,4,11,10,11z", + widecheck4: "M1181,340h2l1171,-296c6,0,10,-5,10,-11l-2,-23c-1,-6,-5,-10,\n-11,-10h-1l-1168,273l-1167,-273h-1c-6,0,-10,4,-11,10l-2,23c-1,6,4,11,10,11z", + // The next ten paths support reaction arrows from the mhchem package. + // Arrows for \ce{<-->} are offset from xAxis by 0.22ex, per mhchem in LaTeX + // baraboveleftarrow is mostly from glyph U+2190 in font KaTeX Main + baraboveleftarrow: "M400000 620h-399890l3 -3c68.7 -52.7 113.7 -120 135 -202\nc4 -14.7 6 -23 6 -25c0 -7.3 -7 -11 -21 -11c-8 0 -13.2 0.8 -15.5 2.5\nc-2.3 1.7 -4.2 5.8 -5.5 12.5c-1.3 4.7 -2.7 10.3 -4 17c-12 48.7 -34.8 92 -68.5 130\ns-74.2 66.3 -121.5 85c-10 4 -16 7.7 -18 11c0 8.7 6 14.3 18 17c47.3 18.7 87.8 47\n121.5 85s56.5 81.3 68.5 130c0.7 2 1.3 5 2 9s1.2 6.7 1.5 8c0.3 1.3 1 3.3 2 6\ns2.2 4.5 3.5 5.5c1.3 1 3.3 1.8 6 2.5s6 1 10 1c14 0 21 -3.7 21 -11\nc0 -2 -2 -10.3 -6 -25c-20 -79.3 -65 -146.7 -135 -202l-3 -3h399890z\nM100 620v40h399900v-40z M0 241v40h399900v-40zM0 241v40h399900v-40z", + // rightarrowabovebar is mostly from glyph U+2192, KaTeX Main + rightarrowabovebar: "M0 241v40h399891c-47.3 35.3-84 78-110 128-16.7 32\n-27.7 63.7-33 95 0 1.3-.2 2.7-.5 4-.3 1.3-.5 2.3-.5 3 0 7.3 6.7 11 20 11 8 0\n13.2-.8 15.5-2.5 2.3-1.7 4.2-5.5 5.5-11.5 2-13.3 5.7-27 11-41 14.7-44.7 39\n-84.5 73-119.5s73.7-60.2 119-75.5c6-2 9-5.7 9-11s-3-9-9-11c-45.3-15.3-85-40.5\n-119-75.5s-58.3-74.8-73-119.5c-4.7-14-8.3-27.3-11-40-1.3-6.7-3.2-10.8-5.5\n-12.5-2.3-1.7-7.5-2.5-15.5-2.5-14 0-21 3.7-21 11 0 2 2 10.3 6 25 20.7 83.3 67\n151.7 139 205zm96 379h399894v40H0zm0 0h399904v40H0z", + // The short left harpoon has 0.5em (i.e. 500 units) kern on the left end. + // Ref from mhchem.sty: \rlap{\raisebox{-.22ex}{$\kern0.5em + baraboveshortleftharpoon: "M507,435c-4,4,-6.3,8.7,-7,14c0,5.3,0.7,9,2,11\nc1.3,2,5.3,5.3,12,10c90.7,54,156,130,196,228c3.3,10.7,6.3,16.3,9,17\nc2,0.7,5,1,9,1c0,0,5,0,5,0c10.7,0,16.7,-2,18,-6c2,-2.7,1,-9.7,-3,-21\nc-32,-87.3,-82.7,-157.7,-152,-211c0,0,-3,-3,-3,-3l399351,0l0,-40\nc-398570,0,-399437,0,-399437,0z M593 435 v40 H399500 v-40z\nM0 281 v-40 H399908 v40z M0 281 v-40 H399908 v40z", + rightharpoonaboveshortbar: "M0,241 l0,40c399126,0,399993,0,399993,0\nc4.7,-4.7,7,-9.3,7,-14c0,-9.3,-3.7,-15.3,-11,-18c-92.7,-56.7,-159,-133.7,-199,\n-231c-3.3,-9.3,-6,-14.7,-8,-16c-2,-1.3,-7,-2,-15,-2c-10.7,0,-16.7,2,-18,6\nc-2,2.7,-1,9.7,3,21c15.3,42,36.7,81.8,64,119.5c27.3,37.7,58,69.2,92,94.5z\nM0 241 v40 H399908 v-40z M0 475 v-40 H399500 v40z M0 475 v-40 H399500 v40z", + shortbaraboveleftharpoon: "M7,435c-4,4,-6.3,8.7,-7,14c0,5.3,0.7,9,2,11\nc1.3,2,5.3,5.3,12,10c90.7,54,156,130,196,228c3.3,10.7,6.3,16.3,9,17c2,0.7,5,1,9,\n1c0,0,5,0,5,0c10.7,0,16.7,-2,18,-6c2,-2.7,1,-9.7,-3,-21c-32,-87.3,-82.7,-157.7,\n-152,-211c0,0,-3,-3,-3,-3l399907,0l0,-40c-399126,0,-399993,0,-399993,0z\nM93 435 v40 H400000 v-40z M500 241 v40 H400000 v-40z M500 241 v40 H400000 v-40z", + shortrightharpoonabovebar: "M53,241l0,40c398570,0,399437,0,399437,0\nc4.7,-4.7,7,-9.3,7,-14c0,-9.3,-3.7,-15.3,-11,-18c-92.7,-56.7,-159,-133.7,-199,\n-231c-3.3,-9.3,-6,-14.7,-8,-16c-2,-1.3,-7,-2,-15,-2c-10.7,0,-16.7,2,-18,6\nc-2,2.7,-1,9.7,3,21c15.3,42,36.7,81.8,64,119.5c27.3,37.7,58,69.2,92,94.5z\nM500 241 v40 H399408 v-40z M500 435 v40 H400000 v-40z" +}; +const tallDelim = function (label, midHeight) { + switch (label) { + case "lbrack": + return "M403 1759 V84 H666 V0 H319 V1759 v" + midHeight + " v1759 h347 v-84\nH403z M403 1759 V0 H319 V1759 v" + midHeight + " v1759 h84z"; + + case "rbrack": + return "M347 1759 V0 H0 V84 H263 V1759 v" + midHeight + " v1759 H0 v84 H347z\nM347 1759 V0 H263 V1759 v" + midHeight + " v1759 h84z"; + + case "vert": + return "M145 15 v585 v" + midHeight + " v585 c2.667,10,9.667,15,21,15\nc10,0,16.667,-5,20,-15 v-585 v" + -midHeight + " v-585 c-2.667,-10,-9.667,-15,-21,-15\nc-10,0,-16.667,5,-20,15z M188 15 H145 v585 v" + midHeight + " v585 h43z"; + + case "doublevert": + return "M145 15 v585 v" + midHeight + " v585 c2.667,10,9.667,15,21,15\nc10,0,16.667,-5,20,-15 v-585 v" + -midHeight + " v-585 c-2.667,-10,-9.667,-15,-21,-15\nc-10,0,-16.667,5,-20,15z M188 15 H145 v585 v" + midHeight + " v585 h43z\nM367 15 v585 v" + midHeight + " v585 c2.667,10,9.667,15,21,15\nc10,0,16.667,-5,20,-15 v-585 v" + -midHeight + " v-585 c-2.667,-10,-9.667,-15,-21,-15\nc-10,0,-16.667,5,-20,15z M410 15 H367 v585 v" + midHeight + " v585 h43z"; + + case "lfloor": + return "M319 602 V0 H403 V602 v" + midHeight + " v1715 h263 v84 H319z\nMM319 602 V0 H403 V602 v" + midHeight + " v1715 H319z"; + + case "rfloor": + return "M319 602 V0 H403 V602 v" + midHeight + " v1799 H0 v-84 H319z\nMM319 602 V0 H403 V602 v" + midHeight + " v1715 H319z"; + + case "lceil": + return "M403 1759 V84 H666 V0 H319 V1759 v" + midHeight + " v602 h84z\nM403 1759 V0 H319 V1759 v" + midHeight + " v602 h84z"; + + case "rceil": + return "M347 1759 V0 H0 V84 H263 V1759 v" + midHeight + " v602 h84z\nM347 1759 V0 h-84 V1759 v" + midHeight + " v602 h84z"; + + case "lparen": + return "M863,9c0,-2,-2,-5,-6,-9c0,0,-17,0,-17,0c-12.7,0,-19.3,0.3,-20,1\nc-5.3,5.3,-10.3,11,-15,17c-242.7,294.7,-395.3,682,-458,1162c-21.3,163.3,-33.3,349,\n-36,557 l0," + (midHeight + 84) + "c0.2,6,0,26,0,60c2,159.3,10,310.7,24,454c53.3,528,210,\n949.7,470,1265c4.7,6,9.7,11.7,15,17c0.7,0.7,7,1,19,1c0,0,18,0,18,0c4,-4,6,-7,6,-9\nc0,-2.7,-3.3,-8.7,-10,-18c-135.3,-192.7,-235.5,-414.3,-300.5,-665c-65,-250.7,-102.5,\n-544.7,-112.5,-882c-2,-104,-3,-167,-3,-189\nl0,-" + (midHeight + 92) + "c0,-162.7,5.7,-314,17,-454c20.7,-272,63.7,-513,129,-723c65.3,\n-210,155.3,-396.3,270,-559c6.7,-9.3,10,-15.3,10,-18z"; + + case "rparen": + return "M76,0c-16.7,0,-25,3,-25,9c0,2,2,6.3,6,13c21.3,28.7,42.3,60.3,\n63,95c96.7,156.7,172.8,332.5,228.5,527.5c55.7,195,92.8,416.5,111.5,664.5\nc11.3,139.3,17,290.7,17,454c0,28,1.7,43,3.3,45l0," + (midHeight + 9) + "\nc-3,4,-3.3,16.7,-3.3,38c0,162,-5.7,313.7,-17,455c-18.7,248,-55.8,469.3,-111.5,664\nc-55.7,194.7,-131.8,370.3,-228.5,527c-20.7,34.7,-41.7,66.3,-63,95c-2,3.3,-4,7,-6,11\nc0,7.3,5.7,11,17,11c0,0,11,0,11,0c9.3,0,14.3,-0.3,15,-1c5.3,-5.3,10.3,-11,15,-17\nc242.7,-294.7,395.3,-681.7,458,-1161c21.3,-164.7,33.3,-350.7,36,-558\nl0,-" + (midHeight + 144) + "c-2,-159.3,-10,-310.7,-24,-454c-53.3,-528,-210,-949.7,\n-470,-1265c-4.7,-6,-9.7,-11.7,-15,-17c-0.7,-0.7,-6.7,-1,-18,-1z"; + + default: + // We should not ever get here. + throw new Error("Unknown stretchy delimiter."); + } +}; +;// CONCATENATED MODULE: ./src/tree.js + + +/** + * This node represents a document fragment, which contains elements, but when + * placed into the DOM doesn't have any representation itself. It only contains + * children and doesn't have any DOM node properties. + */ +class DocumentFragment { + // HtmlDomNode + // Never used; needed for satisfying interface. + constructor(children) { + this.children = void 0; + this.classes = void 0; + this.height = void 0; + this.depth = void 0; + this.maxFontSize = void 0; + this.style = void 0; + this.children = children; + this.classes = []; + this.height = 0; + this.depth = 0; + this.maxFontSize = 0; + this.style = {}; + } + + hasClass(className) { + return utils.contains(this.classes, className); + } + /** Convert the fragment into a node. */ + + + toNode() { + const frag = document.createDocumentFragment(); + + for (let i = 0; i < this.children.length; i++) { + frag.appendChild(this.children[i].toNode()); + } + + return frag; + } + /** Convert the fragment into HTML markup. */ + + + toMarkup() { + let markup = ""; // Simply concatenate the markup for the children together. + + for (let i = 0; i < this.children.length; i++) { + markup += this.children[i].toMarkup(); + } + + return markup; + } + /** + * Converts the math node into a string, similar to innerText. Applies to + * MathDomNode's only. + */ + + + toText() { + // To avoid this, we would subclass documentFragment separately for + // MathML, but polyfills for subclassing is expensive per PR 1469. + // $FlowFixMe: Only works for ChildType = MathDomNode. + const toText = child => child.toText(); + + return this.children.map(toText).join(""); + } + +} +;// CONCATENATED MODULE: ./src/fontMetricsData.js +// This file is GENERATED by buildMetrics.sh. DO NOT MODIFY. +/* harmony default export */ var fontMetricsData = ({ + "AMS-Regular": { + "32": [0, 0, 0, 0, 0.25], + "65": [0, 0.68889, 0, 0, 0.72222], + "66": [0, 0.68889, 0, 0, 0.66667], + "67": [0, 0.68889, 0, 0, 0.72222], + "68": [0, 0.68889, 0, 0, 0.72222], + "69": [0, 0.68889, 0, 0, 0.66667], + "70": [0, 0.68889, 0, 0, 0.61111], + "71": [0, 0.68889, 0, 0, 0.77778], + "72": [0, 0.68889, 0, 0, 0.77778], + "73": [0, 0.68889, 0, 0, 0.38889], + "74": [0.16667, 0.68889, 0, 0, 0.5], + "75": [0, 0.68889, 0, 0, 0.77778], + "76": [0, 0.68889, 0, 0, 0.66667], + "77": [0, 0.68889, 0, 0, 0.94445], + "78": [0, 0.68889, 0, 0, 0.72222], + "79": [0.16667, 0.68889, 0, 0, 0.77778], + "80": [0, 0.68889, 0, 0, 0.61111], + "81": [0.16667, 0.68889, 0, 0, 0.77778], + "82": [0, 0.68889, 0, 0, 0.72222], + "83": [0, 0.68889, 0, 0, 0.55556], + "84": [0, 0.68889, 0, 0, 0.66667], + "85": [0, 0.68889, 0, 0, 0.72222], + "86": [0, 0.68889, 0, 0, 0.72222], + "87": [0, 0.68889, 0, 0, 1.0], + "88": [0, 0.68889, 0, 0, 0.72222], + "89": [0, 0.68889, 0, 0, 0.72222], + "90": [0, 0.68889, 0, 0, 0.66667], + "107": [0, 0.68889, 0, 0, 0.55556], + "160": [0, 0, 0, 0, 0.25], + "165": [0, 0.675, 0.025, 0, 0.75], + "174": [0.15559, 0.69224, 0, 0, 0.94666], + "240": [0, 0.68889, 0, 0, 0.55556], + "295": [0, 0.68889, 0, 0, 0.54028], + "710": [0, 0.825, 0, 0, 2.33334], + "732": [0, 0.9, 0, 0, 2.33334], + "770": [0, 0.825, 0, 0, 2.33334], + "771": [0, 0.9, 0, 0, 2.33334], + "989": [0.08167, 0.58167, 0, 0, 0.77778], + "1008": [0, 0.43056, 0.04028, 0, 0.66667], + "8245": [0, 0.54986, 0, 0, 0.275], + "8463": [0, 0.68889, 0, 0, 0.54028], + "8487": [0, 0.68889, 0, 0, 0.72222], + "8498": [0, 0.68889, 0, 0, 0.55556], + "8502": [0, 0.68889, 0, 0, 0.66667], + "8503": [0, 0.68889, 0, 0, 0.44445], + "8504": [0, 0.68889, 0, 0, 0.66667], + "8513": [0, 0.68889, 0, 0, 0.63889], + "8592": [-0.03598, 0.46402, 0, 0, 0.5], + "8594": [-0.03598, 0.46402, 0, 0, 0.5], + "8602": [-0.13313, 0.36687, 0, 0, 1.0], + "8603": [-0.13313, 0.36687, 0, 0, 1.0], + "8606": [0.01354, 0.52239, 0, 0, 1.0], + "8608": [0.01354, 0.52239, 0, 0, 1.0], + "8610": [0.01354, 0.52239, 0, 0, 1.11111], + "8611": [0.01354, 0.52239, 0, 0, 1.11111], + "8619": [0, 0.54986, 0, 0, 1.0], + "8620": [0, 0.54986, 0, 0, 1.0], + "8621": [-0.13313, 0.37788, 0, 0, 1.38889], + "8622": [-0.13313, 0.36687, 0, 0, 1.0], + "8624": [0, 0.69224, 0, 0, 0.5], + "8625": [0, 0.69224, 0, 0, 0.5], + "8630": [0, 0.43056, 0, 0, 1.0], + "8631": [0, 0.43056, 0, 0, 1.0], + "8634": [0.08198, 0.58198, 0, 0, 0.77778], + "8635": [0.08198, 0.58198, 0, 0, 0.77778], + "8638": [0.19444, 0.69224, 0, 0, 0.41667], + "8639": [0.19444, 0.69224, 0, 0, 0.41667], + "8642": [0.19444, 0.69224, 0, 0, 0.41667], + "8643": [0.19444, 0.69224, 0, 0, 0.41667], + "8644": [0.1808, 0.675, 0, 0, 1.0], + "8646": [0.1808, 0.675, 0, 0, 1.0], + "8647": [0.1808, 0.675, 0, 0, 1.0], + "8648": [0.19444, 0.69224, 0, 0, 0.83334], + "8649": [0.1808, 0.675, 0, 0, 1.0], + "8650": [0.19444, 0.69224, 0, 0, 0.83334], + "8651": [0.01354, 0.52239, 0, 0, 1.0], + "8652": [0.01354, 0.52239, 0, 0, 1.0], + "8653": [-0.13313, 0.36687, 0, 0, 1.0], + "8654": [-0.13313, 0.36687, 0, 0, 1.0], + "8655": [-0.13313, 0.36687, 0, 0, 1.0], + "8666": [0.13667, 0.63667, 0, 0, 1.0], + "8667": [0.13667, 0.63667, 0, 0, 1.0], + "8669": [-0.13313, 0.37788, 0, 0, 1.0], + "8672": [-0.064, 0.437, 0, 0, 1.334], + "8674": [-0.064, 0.437, 0, 0, 1.334], + "8705": [0, 0.825, 0, 0, 0.5], + "8708": [0, 0.68889, 0, 0, 0.55556], + "8709": [0.08167, 0.58167, 0, 0, 0.77778], + "8717": [0, 0.43056, 0, 0, 0.42917], + "8722": [-0.03598, 0.46402, 0, 0, 0.5], + "8724": [0.08198, 0.69224, 0, 0, 0.77778], + "8726": [0.08167, 0.58167, 0, 0, 0.77778], + "8733": [0, 0.69224, 0, 0, 0.77778], + "8736": [0, 0.69224, 0, 0, 0.72222], + "8737": [0, 0.69224, 0, 0, 0.72222], + "8738": [0.03517, 0.52239, 0, 0, 0.72222], + "8739": [0.08167, 0.58167, 0, 0, 0.22222], + "8740": [0.25142, 0.74111, 0, 0, 0.27778], + "8741": [0.08167, 0.58167, 0, 0, 0.38889], + "8742": [0.25142, 0.74111, 0, 0, 0.5], + "8756": [0, 0.69224, 0, 0, 0.66667], + "8757": [0, 0.69224, 0, 0, 0.66667], + "8764": [-0.13313, 0.36687, 0, 0, 0.77778], + "8765": [-0.13313, 0.37788, 0, 0, 0.77778], + "8769": [-0.13313, 0.36687, 0, 0, 0.77778], + "8770": [-0.03625, 0.46375, 0, 0, 0.77778], + "8774": [0.30274, 0.79383, 0, 0, 0.77778], + "8776": [-0.01688, 0.48312, 0, 0, 0.77778], + "8778": [0.08167, 0.58167, 0, 0, 0.77778], + "8782": [0.06062, 0.54986, 0, 0, 0.77778], + "8783": [0.06062, 0.54986, 0, 0, 0.77778], + "8785": [0.08198, 0.58198, 0, 0, 0.77778], + "8786": [0.08198, 0.58198, 0, 0, 0.77778], + "8787": [0.08198, 0.58198, 0, 0, 0.77778], + "8790": [0, 0.69224, 0, 0, 0.77778], + "8791": [0.22958, 0.72958, 0, 0, 0.77778], + "8796": [0.08198, 0.91667, 0, 0, 0.77778], + "8806": [0.25583, 0.75583, 0, 0, 0.77778], + "8807": [0.25583, 0.75583, 0, 0, 0.77778], + "8808": [0.25142, 0.75726, 0, 0, 0.77778], + "8809": [0.25142, 0.75726, 0, 0, 0.77778], + "8812": [0.25583, 0.75583, 0, 0, 0.5], + "8814": [0.20576, 0.70576, 0, 0, 0.77778], + "8815": [0.20576, 0.70576, 0, 0, 0.77778], + "8816": [0.30274, 0.79383, 0, 0, 0.77778], + "8817": [0.30274, 0.79383, 0, 0, 0.77778], + "8818": [0.22958, 0.72958, 0, 0, 0.77778], + "8819": [0.22958, 0.72958, 0, 0, 0.77778], + "8822": [0.1808, 0.675, 0, 0, 0.77778], + "8823": [0.1808, 0.675, 0, 0, 0.77778], + "8828": [0.13667, 0.63667, 0, 0, 0.77778], + "8829": [0.13667, 0.63667, 0, 0, 0.77778], + "8830": [0.22958, 0.72958, 0, 0, 0.77778], + "8831": [0.22958, 0.72958, 0, 0, 0.77778], + "8832": [0.20576, 0.70576, 0, 0, 0.77778], + "8833": [0.20576, 0.70576, 0, 0, 0.77778], + "8840": [0.30274, 0.79383, 0, 0, 0.77778], + "8841": [0.30274, 0.79383, 0, 0, 0.77778], + "8842": [0.13597, 0.63597, 0, 0, 0.77778], + "8843": [0.13597, 0.63597, 0, 0, 0.77778], + "8847": [0.03517, 0.54986, 0, 0, 0.77778], + "8848": [0.03517, 0.54986, 0, 0, 0.77778], + "8858": [0.08198, 0.58198, 0, 0, 0.77778], + "8859": [0.08198, 0.58198, 0, 0, 0.77778], + "8861": [0.08198, 0.58198, 0, 0, 0.77778], + "8862": [0, 0.675, 0, 0, 0.77778], + "8863": [0, 0.675, 0, 0, 0.77778], + "8864": [0, 0.675, 0, 0, 0.77778], + "8865": [0, 0.675, 0, 0, 0.77778], + "8872": [0, 0.69224, 0, 0, 0.61111], + "8873": [0, 0.69224, 0, 0, 0.72222], + "8874": [0, 0.69224, 0, 0, 0.88889], + "8876": [0, 0.68889, 0, 0, 0.61111], + "8877": [0, 0.68889, 0, 0, 0.61111], + "8878": [0, 0.68889, 0, 0, 0.72222], + "8879": [0, 0.68889, 0, 0, 0.72222], + "8882": [0.03517, 0.54986, 0, 0, 0.77778], + "8883": [0.03517, 0.54986, 0, 0, 0.77778], + "8884": [0.13667, 0.63667, 0, 0, 0.77778], + "8885": [0.13667, 0.63667, 0, 0, 0.77778], + "8888": [0, 0.54986, 0, 0, 1.11111], + "8890": [0.19444, 0.43056, 0, 0, 0.55556], + "8891": [0.19444, 0.69224, 0, 0, 0.61111], + "8892": [0.19444, 0.69224, 0, 0, 0.61111], + "8901": [0, 0.54986, 0, 0, 0.27778], + "8903": [0.08167, 0.58167, 0, 0, 0.77778], + "8905": [0.08167, 0.58167, 0, 0, 0.77778], + "8906": [0.08167, 0.58167, 0, 0, 0.77778], + "8907": [0, 0.69224, 0, 0, 0.77778], + "8908": [0, 0.69224, 0, 0, 0.77778], + "8909": [-0.03598, 0.46402, 0, 0, 0.77778], + "8910": [0, 0.54986, 0, 0, 0.76042], + "8911": [0, 0.54986, 0, 0, 0.76042], + "8912": [0.03517, 0.54986, 0, 0, 0.77778], + "8913": [0.03517, 0.54986, 0, 0, 0.77778], + "8914": [0, 0.54986, 0, 0, 0.66667], + "8915": [0, 0.54986, 0, 0, 0.66667], + "8916": [0, 0.69224, 0, 0, 0.66667], + "8918": [0.0391, 0.5391, 0, 0, 0.77778], + "8919": [0.0391, 0.5391, 0, 0, 0.77778], + "8920": [0.03517, 0.54986, 0, 0, 1.33334], + "8921": [0.03517, 0.54986, 0, 0, 1.33334], + "8922": [0.38569, 0.88569, 0, 0, 0.77778], + "8923": [0.38569, 0.88569, 0, 0, 0.77778], + "8926": [0.13667, 0.63667, 0, 0, 0.77778], + "8927": [0.13667, 0.63667, 0, 0, 0.77778], + "8928": [0.30274, 0.79383, 0, 0, 0.77778], + "8929": [0.30274, 0.79383, 0, 0, 0.77778], + "8934": [0.23222, 0.74111, 0, 0, 0.77778], + "8935": [0.23222, 0.74111, 0, 0, 0.77778], + "8936": [0.23222, 0.74111, 0, 0, 0.77778], + "8937": [0.23222, 0.74111, 0, 0, 0.77778], + "8938": [0.20576, 0.70576, 0, 0, 0.77778], + "8939": [0.20576, 0.70576, 0, 0, 0.77778], + "8940": [0.30274, 0.79383, 0, 0, 0.77778], + "8941": [0.30274, 0.79383, 0, 0, 0.77778], + "8994": [0.19444, 0.69224, 0, 0, 0.77778], + "8995": [0.19444, 0.69224, 0, 0, 0.77778], + "9416": [0.15559, 0.69224, 0, 0, 0.90222], + "9484": [0, 0.69224, 0, 0, 0.5], + "9488": [0, 0.69224, 0, 0, 0.5], + "9492": [0, 0.37788, 0, 0, 0.5], + "9496": [0, 0.37788, 0, 0, 0.5], + "9585": [0.19444, 0.68889, 0, 0, 0.88889], + "9586": [0.19444, 0.74111, 0, 0, 0.88889], + "9632": [0, 0.675, 0, 0, 0.77778], + "9633": [0, 0.675, 0, 0, 0.77778], + "9650": [0, 0.54986, 0, 0, 0.72222], + "9651": [0, 0.54986, 0, 0, 0.72222], + "9654": [0.03517, 0.54986, 0, 0, 0.77778], + "9660": [0, 0.54986, 0, 0, 0.72222], + "9661": [0, 0.54986, 0, 0, 0.72222], + "9664": [0.03517, 0.54986, 0, 0, 0.77778], + "9674": [0.11111, 0.69224, 0, 0, 0.66667], + "9733": [0.19444, 0.69224, 0, 0, 0.94445], + "10003": [0, 0.69224, 0, 0, 0.83334], + "10016": [0, 0.69224, 0, 0, 0.83334], + "10731": [0.11111, 0.69224, 0, 0, 0.66667], + "10846": [0.19444, 0.75583, 0, 0, 0.61111], + "10877": [0.13667, 0.63667, 0, 0, 0.77778], + "10878": [0.13667, 0.63667, 0, 0, 0.77778], + "10885": [0.25583, 0.75583, 0, 0, 0.77778], + "10886": [0.25583, 0.75583, 0, 0, 0.77778], + "10887": [0.13597, 0.63597, 0, 0, 0.77778], + "10888": [0.13597, 0.63597, 0, 0, 0.77778], + "10889": [0.26167, 0.75726, 0, 0, 0.77778], + "10890": [0.26167, 0.75726, 0, 0, 0.77778], + "10891": [0.48256, 0.98256, 0, 0, 0.77778], + "10892": [0.48256, 0.98256, 0, 0, 0.77778], + "10901": [0.13667, 0.63667, 0, 0, 0.77778], + "10902": [0.13667, 0.63667, 0, 0, 0.77778], + "10933": [0.25142, 0.75726, 0, 0, 0.77778], + "10934": [0.25142, 0.75726, 0, 0, 0.77778], + "10935": [0.26167, 0.75726, 0, 0, 0.77778], + "10936": [0.26167, 0.75726, 0, 0, 0.77778], + "10937": [0.26167, 0.75726, 0, 0, 0.77778], + "10938": [0.26167, 0.75726, 0, 0, 0.77778], + "10949": [0.25583, 0.75583, 0, 0, 0.77778], + "10950": [0.25583, 0.75583, 0, 0, 0.77778], + "10955": [0.28481, 0.79383, 0, 0, 0.77778], + "10956": [0.28481, 0.79383, 0, 0, 0.77778], + "57350": [0.08167, 0.58167, 0, 0, 0.22222], + "57351": [0.08167, 0.58167, 0, 0, 0.38889], + "57352": [0.08167, 0.58167, 0, 0, 0.77778], + "57353": [0, 0.43056, 0.04028, 0, 0.66667], + "57356": [0.25142, 0.75726, 0, 0, 0.77778], + "57357": [0.25142, 0.75726, 0, 0, 0.77778], + "57358": [0.41951, 0.91951, 0, 0, 0.77778], + "57359": [0.30274, 0.79383, 0, 0, 0.77778], + "57360": [0.30274, 0.79383, 0, 0, 0.77778], + "57361": [0.41951, 0.91951, 0, 0, 0.77778], + "57366": [0.25142, 0.75726, 0, 0, 0.77778], + "57367": [0.25142, 0.75726, 0, 0, 0.77778], + "57368": [0.25142, 0.75726, 0, 0, 0.77778], + "57369": [0.25142, 0.75726, 0, 0, 0.77778], + "57370": [0.13597, 0.63597, 0, 0, 0.77778], + "57371": [0.13597, 0.63597, 0, 0, 0.77778] + }, + "Caligraphic-Regular": { + "32": [0, 0, 0, 0, 0.25], + "65": [0, 0.68333, 0, 0.19445, 0.79847], + "66": [0, 0.68333, 0.03041, 0.13889, 0.65681], + "67": [0, 0.68333, 0.05834, 0.13889, 0.52653], + "68": [0, 0.68333, 0.02778, 0.08334, 0.77139], + "69": [0, 0.68333, 0.08944, 0.11111, 0.52778], + "70": [0, 0.68333, 0.09931, 0.11111, 0.71875], + "71": [0.09722, 0.68333, 0.0593, 0.11111, 0.59487], + "72": [0, 0.68333, 0.00965, 0.11111, 0.84452], + "73": [0, 0.68333, 0.07382, 0, 0.54452], + "74": [0.09722, 0.68333, 0.18472, 0.16667, 0.67778], + "75": [0, 0.68333, 0.01445, 0.05556, 0.76195], + "76": [0, 0.68333, 0, 0.13889, 0.68972], + "77": [0, 0.68333, 0, 0.13889, 1.2009], + "78": [0, 0.68333, 0.14736, 0.08334, 0.82049], + "79": [0, 0.68333, 0.02778, 0.11111, 0.79611], + "80": [0, 0.68333, 0.08222, 0.08334, 0.69556], + "81": [0.09722, 0.68333, 0, 0.11111, 0.81667], + "82": [0, 0.68333, 0, 0.08334, 0.8475], + "83": [0, 0.68333, 0.075, 0.13889, 0.60556], + "84": [0, 0.68333, 0.25417, 0, 0.54464], + "85": [0, 0.68333, 0.09931, 0.08334, 0.62583], + "86": [0, 0.68333, 0.08222, 0, 0.61278], + "87": [0, 0.68333, 0.08222, 0.08334, 0.98778], + "88": [0, 0.68333, 0.14643, 0.13889, 0.7133], + "89": [0.09722, 0.68333, 0.08222, 0.08334, 0.66834], + "90": [0, 0.68333, 0.07944, 0.13889, 0.72473], + "160": [0, 0, 0, 0, 0.25] + }, + "Fraktur-Regular": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69141, 0, 0, 0.29574], + "34": [0, 0.69141, 0, 0, 0.21471], + "38": [0, 0.69141, 0, 0, 0.73786], + "39": [0, 0.69141, 0, 0, 0.21201], + "40": [0.24982, 0.74947, 0, 0, 0.38865], + "41": [0.24982, 0.74947, 0, 0, 0.38865], + "42": [0, 0.62119, 0, 0, 0.27764], + "43": [0.08319, 0.58283, 0, 0, 0.75623], + "44": [0, 0.10803, 0, 0, 0.27764], + "45": [0.08319, 0.58283, 0, 0, 0.75623], + "46": [0, 0.10803, 0, 0, 0.27764], + "47": [0.24982, 0.74947, 0, 0, 0.50181], + "48": [0, 0.47534, 0, 0, 0.50181], + "49": [0, 0.47534, 0, 0, 0.50181], + "50": [0, 0.47534, 0, 0, 0.50181], + "51": [0.18906, 0.47534, 0, 0, 0.50181], + "52": [0.18906, 0.47534, 0, 0, 0.50181], + "53": [0.18906, 0.47534, 0, 0, 0.50181], + "54": [0, 0.69141, 0, 0, 0.50181], + "55": [0.18906, 0.47534, 0, 0, 0.50181], + "56": [0, 0.69141, 0, 0, 0.50181], + "57": [0.18906, 0.47534, 0, 0, 0.50181], + "58": [0, 0.47534, 0, 0, 0.21606], + "59": [0.12604, 0.47534, 0, 0, 0.21606], + "61": [-0.13099, 0.36866, 0, 0, 0.75623], + "63": [0, 0.69141, 0, 0, 0.36245], + "65": [0, 0.69141, 0, 0, 0.7176], + "66": [0, 0.69141, 0, 0, 0.88397], + "67": [0, 0.69141, 0, 0, 0.61254], + "68": [0, 0.69141, 0, 0, 0.83158], + "69": [0, 0.69141, 0, 0, 0.66278], + "70": [0.12604, 0.69141, 0, 0, 0.61119], + "71": [0, 0.69141, 0, 0, 0.78539], + "72": [0.06302, 0.69141, 0, 0, 0.7203], + "73": [0, 0.69141, 0, 0, 0.55448], + "74": [0.12604, 0.69141, 0, 0, 0.55231], + "75": [0, 0.69141, 0, 0, 0.66845], + "76": [0, 0.69141, 0, 0, 0.66602], + "77": [0, 0.69141, 0, 0, 1.04953], + "78": [0, 0.69141, 0, 0, 0.83212], + "79": [0, 0.69141, 0, 0, 0.82699], + "80": [0.18906, 0.69141, 0, 0, 0.82753], + "81": [0.03781, 0.69141, 0, 0, 0.82699], + "82": [0, 0.69141, 0, 0, 0.82807], + "83": [0, 0.69141, 0, 0, 0.82861], + "84": [0, 0.69141, 0, 0, 0.66899], + "85": [0, 0.69141, 0, 0, 0.64576], + "86": [0, 0.69141, 0, 0, 0.83131], + "87": [0, 0.69141, 0, 0, 1.04602], + "88": [0, 0.69141, 0, 0, 0.71922], + "89": [0.18906, 0.69141, 0, 0, 0.83293], + "90": [0.12604, 0.69141, 0, 0, 0.60201], + "91": [0.24982, 0.74947, 0, 0, 0.27764], + "93": [0.24982, 0.74947, 0, 0, 0.27764], + "94": [0, 0.69141, 0, 0, 0.49965], + "97": [0, 0.47534, 0, 0, 0.50046], + "98": [0, 0.69141, 0, 0, 0.51315], + "99": [0, 0.47534, 0, 0, 0.38946], + "100": [0, 0.62119, 0, 0, 0.49857], + "101": [0, 0.47534, 0, 0, 0.40053], + "102": [0.18906, 0.69141, 0, 0, 0.32626], + "103": [0.18906, 0.47534, 0, 0, 0.5037], + "104": [0.18906, 0.69141, 0, 0, 0.52126], + "105": [0, 0.69141, 0, 0, 0.27899], + "106": [0, 0.69141, 0, 0, 0.28088], + "107": [0, 0.69141, 0, 0, 0.38946], + "108": [0, 0.69141, 0, 0, 0.27953], + "109": [0, 0.47534, 0, 0, 0.76676], + "110": [0, 0.47534, 0, 0, 0.52666], + "111": [0, 0.47534, 0, 0, 0.48885], + "112": [0.18906, 0.52396, 0, 0, 0.50046], + "113": [0.18906, 0.47534, 0, 0, 0.48912], + "114": [0, 0.47534, 0, 0, 0.38919], + "115": [0, 0.47534, 0, 0, 0.44266], + "116": [0, 0.62119, 0, 0, 0.33301], + "117": [0, 0.47534, 0, 0, 0.5172], + "118": [0, 0.52396, 0, 0, 0.5118], + "119": [0, 0.52396, 0, 0, 0.77351], + "120": [0.18906, 0.47534, 0, 0, 0.38865], + "121": [0.18906, 0.47534, 0, 0, 0.49884], + "122": [0.18906, 0.47534, 0, 0, 0.39054], + "160": [0, 0, 0, 0, 0.25], + "8216": [0, 0.69141, 0, 0, 0.21471], + "8217": [0, 0.69141, 0, 0, 0.21471], + "58112": [0, 0.62119, 0, 0, 0.49749], + "58113": [0, 0.62119, 0, 0, 0.4983], + "58114": [0.18906, 0.69141, 0, 0, 0.33328], + "58115": [0.18906, 0.69141, 0, 0, 0.32923], + "58116": [0.18906, 0.47534, 0, 0, 0.50343], + "58117": [0, 0.69141, 0, 0, 0.33301], + "58118": [0, 0.62119, 0, 0, 0.33409], + "58119": [0, 0.47534, 0, 0, 0.50073] + }, + "Main-Bold": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0, 0, 0.35], + "34": [0, 0.69444, 0, 0, 0.60278], + "35": [0.19444, 0.69444, 0, 0, 0.95833], + "36": [0.05556, 0.75, 0, 0, 0.575], + "37": [0.05556, 0.75, 0, 0, 0.95833], + "38": [0, 0.69444, 0, 0, 0.89444], + "39": [0, 0.69444, 0, 0, 0.31944], + "40": [0.25, 0.75, 0, 0, 0.44722], + "41": [0.25, 0.75, 0, 0, 0.44722], + "42": [0, 0.75, 0, 0, 0.575], + "43": [0.13333, 0.63333, 0, 0, 0.89444], + "44": [0.19444, 0.15556, 0, 0, 0.31944], + "45": [0, 0.44444, 0, 0, 0.38333], + "46": [0, 0.15556, 0, 0, 0.31944], + "47": [0.25, 0.75, 0, 0, 0.575], + "48": [0, 0.64444, 0, 0, 0.575], + "49": [0, 0.64444, 0, 0, 0.575], + "50": [0, 0.64444, 0, 0, 0.575], + "51": [0, 0.64444, 0, 0, 0.575], + "52": [0, 0.64444, 0, 0, 0.575], + "53": [0, 0.64444, 0, 0, 0.575], + "54": [0, 0.64444, 0, 0, 0.575], + "55": [0, 0.64444, 0, 0, 0.575], + "56": [0, 0.64444, 0, 0, 0.575], + "57": [0, 0.64444, 0, 0, 0.575], + "58": [0, 0.44444, 0, 0, 0.31944], + "59": [0.19444, 0.44444, 0, 0, 0.31944], + "60": [0.08556, 0.58556, 0, 0, 0.89444], + "61": [-0.10889, 0.39111, 0, 0, 0.89444], + "62": [0.08556, 0.58556, 0, 0, 0.89444], + "63": [0, 0.69444, 0, 0, 0.54305], + "64": [0, 0.69444, 0, 0, 0.89444], + "65": [0, 0.68611, 0, 0, 0.86944], + "66": [0, 0.68611, 0, 0, 0.81805], + "67": [0, 0.68611, 0, 0, 0.83055], + "68": [0, 0.68611, 0, 0, 0.88194], + "69": [0, 0.68611, 0, 0, 0.75555], + "70": [0, 0.68611, 0, 0, 0.72361], + "71": [0, 0.68611, 0, 0, 0.90416], + "72": [0, 0.68611, 0, 0, 0.9], + "73": [0, 0.68611, 0, 0, 0.43611], + "74": [0, 0.68611, 0, 0, 0.59444], + "75": [0, 0.68611, 0, 0, 0.90138], + "76": [0, 0.68611, 0, 0, 0.69166], + "77": [0, 0.68611, 0, 0, 1.09166], + "78": [0, 0.68611, 0, 0, 0.9], + "79": [0, 0.68611, 0, 0, 0.86388], + "80": [0, 0.68611, 0, 0, 0.78611], + "81": [0.19444, 0.68611, 0, 0, 0.86388], + "82": [0, 0.68611, 0, 0, 0.8625], + "83": [0, 0.68611, 0, 0, 0.63889], + "84": [0, 0.68611, 0, 0, 0.8], + "85": [0, 0.68611, 0, 0, 0.88472], + "86": [0, 0.68611, 0.01597, 0, 0.86944], + "87": [0, 0.68611, 0.01597, 0, 1.18888], + "88": [0, 0.68611, 0, 0, 0.86944], + "89": [0, 0.68611, 0.02875, 0, 0.86944], + "90": [0, 0.68611, 0, 0, 0.70277], + "91": [0.25, 0.75, 0, 0, 0.31944], + "92": [0.25, 0.75, 0, 0, 0.575], + "93": [0.25, 0.75, 0, 0, 0.31944], + "94": [0, 0.69444, 0, 0, 0.575], + "95": [0.31, 0.13444, 0.03194, 0, 0.575], + "97": [0, 0.44444, 0, 0, 0.55902], + "98": [0, 0.69444, 0, 0, 0.63889], + "99": [0, 0.44444, 0, 0, 0.51111], + "100": [0, 0.69444, 0, 0, 0.63889], + "101": [0, 0.44444, 0, 0, 0.52708], + "102": [0, 0.69444, 0.10903, 0, 0.35139], + "103": [0.19444, 0.44444, 0.01597, 0, 0.575], + "104": [0, 0.69444, 0, 0, 0.63889], + "105": [0, 0.69444, 0, 0, 0.31944], + "106": [0.19444, 0.69444, 0, 0, 0.35139], + "107": [0, 0.69444, 0, 0, 0.60694], + "108": [0, 0.69444, 0, 0, 0.31944], + "109": [0, 0.44444, 0, 0, 0.95833], + "110": [0, 0.44444, 0, 0, 0.63889], + "111": [0, 0.44444, 0, 0, 0.575], + "112": [0.19444, 0.44444, 0, 0, 0.63889], + "113": [0.19444, 0.44444, 0, 0, 0.60694], + "114": [0, 0.44444, 0, 0, 0.47361], + "115": [0, 0.44444, 0, 0, 0.45361], + "116": [0, 0.63492, 0, 0, 0.44722], + "117": [0, 0.44444, 0, 0, 0.63889], + "118": [0, 0.44444, 0.01597, 0, 0.60694], + "119": [0, 0.44444, 0.01597, 0, 0.83055], + "120": [0, 0.44444, 0, 0, 0.60694], + "121": [0.19444, 0.44444, 0.01597, 0, 0.60694], + "122": [0, 0.44444, 0, 0, 0.51111], + "123": [0.25, 0.75, 0, 0, 0.575], + "124": [0.25, 0.75, 0, 0, 0.31944], + "125": [0.25, 0.75, 0, 0, 0.575], + "126": [0.35, 0.34444, 0, 0, 0.575], + "160": [0, 0, 0, 0, 0.25], + "163": [0, 0.69444, 0, 0, 0.86853], + "168": [0, 0.69444, 0, 0, 0.575], + "172": [0, 0.44444, 0, 0, 0.76666], + "176": [0, 0.69444, 0, 0, 0.86944], + "177": [0.13333, 0.63333, 0, 0, 0.89444], + "184": [0.17014, 0, 0, 0, 0.51111], + "198": [0, 0.68611, 0, 0, 1.04166], + "215": [0.13333, 0.63333, 0, 0, 0.89444], + "216": [0.04861, 0.73472, 0, 0, 0.89444], + "223": [0, 0.69444, 0, 0, 0.59722], + "230": [0, 0.44444, 0, 0, 0.83055], + "247": [0.13333, 0.63333, 0, 0, 0.89444], + "248": [0.09722, 0.54167, 0, 0, 0.575], + "305": [0, 0.44444, 0, 0, 0.31944], + "338": [0, 0.68611, 0, 0, 1.16944], + "339": [0, 0.44444, 0, 0, 0.89444], + "567": [0.19444, 0.44444, 0, 0, 0.35139], + "710": [0, 0.69444, 0, 0, 0.575], + "711": [0, 0.63194, 0, 0, 0.575], + "713": [0, 0.59611, 0, 0, 0.575], + "714": [0, 0.69444, 0, 0, 0.575], + "715": [0, 0.69444, 0, 0, 0.575], + "728": [0, 0.69444, 0, 0, 0.575], + "729": [0, 0.69444, 0, 0, 0.31944], + "730": [0, 0.69444, 0, 0, 0.86944], + "732": [0, 0.69444, 0, 0, 0.575], + "733": [0, 0.69444, 0, 0, 0.575], + "915": [0, 0.68611, 0, 0, 0.69166], + "916": [0, 0.68611, 0, 0, 0.95833], + "920": [0, 0.68611, 0, 0, 0.89444], + "923": [0, 0.68611, 0, 0, 0.80555], + "926": [0, 0.68611, 0, 0, 0.76666], + "928": [0, 0.68611, 0, 0, 0.9], + "931": [0, 0.68611, 0, 0, 0.83055], + "933": [0, 0.68611, 0, 0, 0.89444], + "934": [0, 0.68611, 0, 0, 0.83055], + "936": [0, 0.68611, 0, 0, 0.89444], + "937": [0, 0.68611, 0, 0, 0.83055], + "8211": [0, 0.44444, 0.03194, 0, 0.575], + "8212": [0, 0.44444, 0.03194, 0, 1.14999], + "8216": [0, 0.69444, 0, 0, 0.31944], + "8217": [0, 0.69444, 0, 0, 0.31944], + "8220": [0, 0.69444, 0, 0, 0.60278], + "8221": [0, 0.69444, 0, 0, 0.60278], + "8224": [0.19444, 0.69444, 0, 0, 0.51111], + "8225": [0.19444, 0.69444, 0, 0, 0.51111], + "8242": [0, 0.55556, 0, 0, 0.34444], + "8407": [0, 0.72444, 0.15486, 0, 0.575], + "8463": [0, 0.69444, 0, 0, 0.66759], + "8465": [0, 0.69444, 0, 0, 0.83055], + "8467": [0, 0.69444, 0, 0, 0.47361], + "8472": [0.19444, 0.44444, 0, 0, 0.74027], + "8476": [0, 0.69444, 0, 0, 0.83055], + "8501": [0, 0.69444, 0, 0, 0.70277], + "8592": [-0.10889, 0.39111, 0, 0, 1.14999], + "8593": [0.19444, 0.69444, 0, 0, 0.575], + "8594": [-0.10889, 0.39111, 0, 0, 1.14999], + "8595": [0.19444, 0.69444, 0, 0, 0.575], + "8596": [-0.10889, 0.39111, 0, 0, 1.14999], + "8597": [0.25, 0.75, 0, 0, 0.575], + "8598": [0.19444, 0.69444, 0, 0, 1.14999], + "8599": [0.19444, 0.69444, 0, 0, 1.14999], + "8600": [0.19444, 0.69444, 0, 0, 1.14999], + "8601": [0.19444, 0.69444, 0, 0, 1.14999], + "8636": [-0.10889, 0.39111, 0, 0, 1.14999], + "8637": [-0.10889, 0.39111, 0, 0, 1.14999], + "8640": [-0.10889, 0.39111, 0, 0, 1.14999], + "8641": [-0.10889, 0.39111, 0, 0, 1.14999], + "8656": [-0.10889, 0.39111, 0, 0, 1.14999], + "8657": [0.19444, 0.69444, 0, 0, 0.70277], + "8658": [-0.10889, 0.39111, 0, 0, 1.14999], + "8659": [0.19444, 0.69444, 0, 0, 0.70277], + "8660": [-0.10889, 0.39111, 0, 0, 1.14999], + "8661": [0.25, 0.75, 0, 0, 0.70277], + "8704": [0, 0.69444, 0, 0, 0.63889], + "8706": [0, 0.69444, 0.06389, 0, 0.62847], + "8707": [0, 0.69444, 0, 0, 0.63889], + "8709": [0.05556, 0.75, 0, 0, 0.575], + "8711": [0, 0.68611, 0, 0, 0.95833], + "8712": [0.08556, 0.58556, 0, 0, 0.76666], + "8715": [0.08556, 0.58556, 0, 0, 0.76666], + "8722": [0.13333, 0.63333, 0, 0, 0.89444], + "8723": [0.13333, 0.63333, 0, 0, 0.89444], + "8725": [0.25, 0.75, 0, 0, 0.575], + "8726": [0.25, 0.75, 0, 0, 0.575], + "8727": [-0.02778, 0.47222, 0, 0, 0.575], + "8728": [-0.02639, 0.47361, 0, 0, 0.575], + "8729": [-0.02639, 0.47361, 0, 0, 0.575], + "8730": [0.18, 0.82, 0, 0, 0.95833], + "8733": [0, 0.44444, 0, 0, 0.89444], + "8734": [0, 0.44444, 0, 0, 1.14999], + "8736": [0, 0.69224, 0, 0, 0.72222], + "8739": [0.25, 0.75, 0, 0, 0.31944], + "8741": [0.25, 0.75, 0, 0, 0.575], + "8743": [0, 0.55556, 0, 0, 0.76666], + "8744": [0, 0.55556, 0, 0, 0.76666], + "8745": [0, 0.55556, 0, 0, 0.76666], + "8746": [0, 0.55556, 0, 0, 0.76666], + "8747": [0.19444, 0.69444, 0.12778, 0, 0.56875], + "8764": [-0.10889, 0.39111, 0, 0, 0.89444], + "8768": [0.19444, 0.69444, 0, 0, 0.31944], + "8771": [0.00222, 0.50222, 0, 0, 0.89444], + "8773": [0.027, 0.638, 0, 0, 0.894], + "8776": [0.02444, 0.52444, 0, 0, 0.89444], + "8781": [0.00222, 0.50222, 0, 0, 0.89444], + "8801": [0.00222, 0.50222, 0, 0, 0.89444], + "8804": [0.19667, 0.69667, 0, 0, 0.89444], + "8805": [0.19667, 0.69667, 0, 0, 0.89444], + "8810": [0.08556, 0.58556, 0, 0, 1.14999], + "8811": [0.08556, 0.58556, 0, 0, 1.14999], + "8826": [0.08556, 0.58556, 0, 0, 0.89444], + "8827": [0.08556, 0.58556, 0, 0, 0.89444], + "8834": [0.08556, 0.58556, 0, 0, 0.89444], + "8835": [0.08556, 0.58556, 0, 0, 0.89444], + "8838": [0.19667, 0.69667, 0, 0, 0.89444], + "8839": [0.19667, 0.69667, 0, 0, 0.89444], + "8846": [0, 0.55556, 0, 0, 0.76666], + "8849": [0.19667, 0.69667, 0, 0, 0.89444], + "8850": [0.19667, 0.69667, 0, 0, 0.89444], + "8851": [0, 0.55556, 0, 0, 0.76666], + "8852": [0, 0.55556, 0, 0, 0.76666], + "8853": [0.13333, 0.63333, 0, 0, 0.89444], + "8854": [0.13333, 0.63333, 0, 0, 0.89444], + "8855": [0.13333, 0.63333, 0, 0, 0.89444], + "8856": [0.13333, 0.63333, 0, 0, 0.89444], + "8857": [0.13333, 0.63333, 0, 0, 0.89444], + "8866": [0, 0.69444, 0, 0, 0.70277], + "8867": [0, 0.69444, 0, 0, 0.70277], + "8868": [0, 0.69444, 0, 0, 0.89444], + "8869": [0, 0.69444, 0, 0, 0.89444], + "8900": [-0.02639, 0.47361, 0, 0, 0.575], + "8901": [-0.02639, 0.47361, 0, 0, 0.31944], + "8902": [-0.02778, 0.47222, 0, 0, 0.575], + "8968": [0.25, 0.75, 0, 0, 0.51111], + "8969": [0.25, 0.75, 0, 0, 0.51111], + "8970": [0.25, 0.75, 0, 0, 0.51111], + "8971": [0.25, 0.75, 0, 0, 0.51111], + "8994": [-0.13889, 0.36111, 0, 0, 1.14999], + "8995": [-0.13889, 0.36111, 0, 0, 1.14999], + "9651": [0.19444, 0.69444, 0, 0, 1.02222], + "9657": [-0.02778, 0.47222, 0, 0, 0.575], + "9661": [0.19444, 0.69444, 0, 0, 1.02222], + "9667": [-0.02778, 0.47222, 0, 0, 0.575], + "9711": [0.19444, 0.69444, 0, 0, 1.14999], + "9824": [0.12963, 0.69444, 0, 0, 0.89444], + "9825": [0.12963, 0.69444, 0, 0, 0.89444], + "9826": [0.12963, 0.69444, 0, 0, 0.89444], + "9827": [0.12963, 0.69444, 0, 0, 0.89444], + "9837": [0, 0.75, 0, 0, 0.44722], + "9838": [0.19444, 0.69444, 0, 0, 0.44722], + "9839": [0.19444, 0.69444, 0, 0, 0.44722], + "10216": [0.25, 0.75, 0, 0, 0.44722], + "10217": [0.25, 0.75, 0, 0, 0.44722], + "10815": [0, 0.68611, 0, 0, 0.9], + "10927": [0.19667, 0.69667, 0, 0, 0.89444], + "10928": [0.19667, 0.69667, 0, 0, 0.89444], + "57376": [0.19444, 0.69444, 0, 0, 0] + }, + "Main-BoldItalic": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0.11417, 0, 0.38611], + "34": [0, 0.69444, 0.07939, 0, 0.62055], + "35": [0.19444, 0.69444, 0.06833, 0, 0.94444], + "37": [0.05556, 0.75, 0.12861, 0, 0.94444], + "38": [0, 0.69444, 0.08528, 0, 0.88555], + "39": [0, 0.69444, 0.12945, 0, 0.35555], + "40": [0.25, 0.75, 0.15806, 0, 0.47333], + "41": [0.25, 0.75, 0.03306, 0, 0.47333], + "42": [0, 0.75, 0.14333, 0, 0.59111], + "43": [0.10333, 0.60333, 0.03306, 0, 0.88555], + "44": [0.19444, 0.14722, 0, 0, 0.35555], + "45": [0, 0.44444, 0.02611, 0, 0.41444], + "46": [0, 0.14722, 0, 0, 0.35555], + "47": [0.25, 0.75, 0.15806, 0, 0.59111], + "48": [0, 0.64444, 0.13167, 0, 0.59111], + "49": [0, 0.64444, 0.13167, 0, 0.59111], + "50": [0, 0.64444, 0.13167, 0, 0.59111], + "51": [0, 0.64444, 0.13167, 0, 0.59111], + "52": [0.19444, 0.64444, 0.13167, 0, 0.59111], + "53": [0, 0.64444, 0.13167, 0, 0.59111], + "54": [0, 0.64444, 0.13167, 0, 0.59111], + "55": [0.19444, 0.64444, 0.13167, 0, 0.59111], + "56": [0, 0.64444, 0.13167, 0, 0.59111], + "57": [0, 0.64444, 0.13167, 0, 0.59111], + "58": [0, 0.44444, 0.06695, 0, 0.35555], + "59": [0.19444, 0.44444, 0.06695, 0, 0.35555], + "61": [-0.10889, 0.39111, 0.06833, 0, 0.88555], + "63": [0, 0.69444, 0.11472, 0, 0.59111], + "64": [0, 0.69444, 0.09208, 0, 0.88555], + "65": [0, 0.68611, 0, 0, 0.86555], + "66": [0, 0.68611, 0.0992, 0, 0.81666], + "67": [0, 0.68611, 0.14208, 0, 0.82666], + "68": [0, 0.68611, 0.09062, 0, 0.87555], + "69": [0, 0.68611, 0.11431, 0, 0.75666], + "70": [0, 0.68611, 0.12903, 0, 0.72722], + "71": [0, 0.68611, 0.07347, 0, 0.89527], + "72": [0, 0.68611, 0.17208, 0, 0.8961], + "73": [0, 0.68611, 0.15681, 0, 0.47166], + "74": [0, 0.68611, 0.145, 0, 0.61055], + "75": [0, 0.68611, 0.14208, 0, 0.89499], + "76": [0, 0.68611, 0, 0, 0.69777], + "77": [0, 0.68611, 0.17208, 0, 1.07277], + "78": [0, 0.68611, 0.17208, 0, 0.8961], + "79": [0, 0.68611, 0.09062, 0, 0.85499], + "80": [0, 0.68611, 0.0992, 0, 0.78721], + "81": [0.19444, 0.68611, 0.09062, 0, 0.85499], + "82": [0, 0.68611, 0.02559, 0, 0.85944], + "83": [0, 0.68611, 0.11264, 0, 0.64999], + "84": [0, 0.68611, 0.12903, 0, 0.7961], + "85": [0, 0.68611, 0.17208, 0, 0.88083], + "86": [0, 0.68611, 0.18625, 0, 0.86555], + "87": [0, 0.68611, 0.18625, 0, 1.15999], + "88": [0, 0.68611, 0.15681, 0, 0.86555], + "89": [0, 0.68611, 0.19803, 0, 0.86555], + "90": [0, 0.68611, 0.14208, 0, 0.70888], + "91": [0.25, 0.75, 0.1875, 0, 0.35611], + "93": [0.25, 0.75, 0.09972, 0, 0.35611], + "94": [0, 0.69444, 0.06709, 0, 0.59111], + "95": [0.31, 0.13444, 0.09811, 0, 0.59111], + "97": [0, 0.44444, 0.09426, 0, 0.59111], + "98": [0, 0.69444, 0.07861, 0, 0.53222], + "99": [0, 0.44444, 0.05222, 0, 0.53222], + "100": [0, 0.69444, 0.10861, 0, 0.59111], + "101": [0, 0.44444, 0.085, 0, 0.53222], + "102": [0.19444, 0.69444, 0.21778, 0, 0.4], + "103": [0.19444, 0.44444, 0.105, 0, 0.53222], + "104": [0, 0.69444, 0.09426, 0, 0.59111], + "105": [0, 0.69326, 0.11387, 0, 0.35555], + "106": [0.19444, 0.69326, 0.1672, 0, 0.35555], + "107": [0, 0.69444, 0.11111, 0, 0.53222], + "108": [0, 0.69444, 0.10861, 0, 0.29666], + "109": [0, 0.44444, 0.09426, 0, 0.94444], + "110": [0, 0.44444, 0.09426, 0, 0.64999], + "111": [0, 0.44444, 0.07861, 0, 0.59111], + "112": [0.19444, 0.44444, 0.07861, 0, 0.59111], + "113": [0.19444, 0.44444, 0.105, 0, 0.53222], + "114": [0, 0.44444, 0.11111, 0, 0.50167], + "115": [0, 0.44444, 0.08167, 0, 0.48694], + "116": [0, 0.63492, 0.09639, 0, 0.385], + "117": [0, 0.44444, 0.09426, 0, 0.62055], + "118": [0, 0.44444, 0.11111, 0, 0.53222], + "119": [0, 0.44444, 0.11111, 0, 0.76777], + "120": [0, 0.44444, 0.12583, 0, 0.56055], + "121": [0.19444, 0.44444, 0.105, 0, 0.56166], + "122": [0, 0.44444, 0.13889, 0, 0.49055], + "126": [0.35, 0.34444, 0.11472, 0, 0.59111], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.69444, 0.11473, 0, 0.59111], + "176": [0, 0.69444, 0, 0, 0.94888], + "184": [0.17014, 0, 0, 0, 0.53222], + "198": [0, 0.68611, 0.11431, 0, 1.02277], + "216": [0.04861, 0.73472, 0.09062, 0, 0.88555], + "223": [0.19444, 0.69444, 0.09736, 0, 0.665], + "230": [0, 0.44444, 0.085, 0, 0.82666], + "248": [0.09722, 0.54167, 0.09458, 0, 0.59111], + "305": [0, 0.44444, 0.09426, 0, 0.35555], + "338": [0, 0.68611, 0.11431, 0, 1.14054], + "339": [0, 0.44444, 0.085, 0, 0.82666], + "567": [0.19444, 0.44444, 0.04611, 0, 0.385], + "710": [0, 0.69444, 0.06709, 0, 0.59111], + "711": [0, 0.63194, 0.08271, 0, 0.59111], + "713": [0, 0.59444, 0.10444, 0, 0.59111], + "714": [0, 0.69444, 0.08528, 0, 0.59111], + "715": [0, 0.69444, 0, 0, 0.59111], + "728": [0, 0.69444, 0.10333, 0, 0.59111], + "729": [0, 0.69444, 0.12945, 0, 0.35555], + "730": [0, 0.69444, 0, 0, 0.94888], + "732": [0, 0.69444, 0.11472, 0, 0.59111], + "733": [0, 0.69444, 0.11472, 0, 0.59111], + "915": [0, 0.68611, 0.12903, 0, 0.69777], + "916": [0, 0.68611, 0, 0, 0.94444], + "920": [0, 0.68611, 0.09062, 0, 0.88555], + "923": [0, 0.68611, 0, 0, 0.80666], + "926": [0, 0.68611, 0.15092, 0, 0.76777], + "928": [0, 0.68611, 0.17208, 0, 0.8961], + "931": [0, 0.68611, 0.11431, 0, 0.82666], + "933": [0, 0.68611, 0.10778, 0, 0.88555], + "934": [0, 0.68611, 0.05632, 0, 0.82666], + "936": [0, 0.68611, 0.10778, 0, 0.88555], + "937": [0, 0.68611, 0.0992, 0, 0.82666], + "8211": [0, 0.44444, 0.09811, 0, 0.59111], + "8212": [0, 0.44444, 0.09811, 0, 1.18221], + "8216": [0, 0.69444, 0.12945, 0, 0.35555], + "8217": [0, 0.69444, 0.12945, 0, 0.35555], + "8220": [0, 0.69444, 0.16772, 0, 0.62055], + "8221": [0, 0.69444, 0.07939, 0, 0.62055] + }, + "Main-Italic": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0.12417, 0, 0.30667], + "34": [0, 0.69444, 0.06961, 0, 0.51444], + "35": [0.19444, 0.69444, 0.06616, 0, 0.81777], + "37": [0.05556, 0.75, 0.13639, 0, 0.81777], + "38": [0, 0.69444, 0.09694, 0, 0.76666], + "39": [0, 0.69444, 0.12417, 0, 0.30667], + "40": [0.25, 0.75, 0.16194, 0, 0.40889], + "41": [0.25, 0.75, 0.03694, 0, 0.40889], + "42": [0, 0.75, 0.14917, 0, 0.51111], + "43": [0.05667, 0.56167, 0.03694, 0, 0.76666], + "44": [0.19444, 0.10556, 0, 0, 0.30667], + "45": [0, 0.43056, 0.02826, 0, 0.35778], + "46": [0, 0.10556, 0, 0, 0.30667], + "47": [0.25, 0.75, 0.16194, 0, 0.51111], + "48": [0, 0.64444, 0.13556, 0, 0.51111], + "49": [0, 0.64444, 0.13556, 0, 0.51111], + "50": [0, 0.64444, 0.13556, 0, 0.51111], + "51": [0, 0.64444, 0.13556, 0, 0.51111], + "52": [0.19444, 0.64444, 0.13556, 0, 0.51111], + "53": [0, 0.64444, 0.13556, 0, 0.51111], + "54": [0, 0.64444, 0.13556, 0, 0.51111], + "55": [0.19444, 0.64444, 0.13556, 0, 0.51111], + "56": [0, 0.64444, 0.13556, 0, 0.51111], + "57": [0, 0.64444, 0.13556, 0, 0.51111], + "58": [0, 0.43056, 0.0582, 0, 0.30667], + "59": [0.19444, 0.43056, 0.0582, 0, 0.30667], + "61": [-0.13313, 0.36687, 0.06616, 0, 0.76666], + "63": [0, 0.69444, 0.1225, 0, 0.51111], + "64": [0, 0.69444, 0.09597, 0, 0.76666], + "65": [0, 0.68333, 0, 0, 0.74333], + "66": [0, 0.68333, 0.10257, 0, 0.70389], + "67": [0, 0.68333, 0.14528, 0, 0.71555], + "68": [0, 0.68333, 0.09403, 0, 0.755], + "69": [0, 0.68333, 0.12028, 0, 0.67833], + "70": [0, 0.68333, 0.13305, 0, 0.65277], + "71": [0, 0.68333, 0.08722, 0, 0.77361], + "72": [0, 0.68333, 0.16389, 0, 0.74333], + "73": [0, 0.68333, 0.15806, 0, 0.38555], + "74": [0, 0.68333, 0.14028, 0, 0.525], + "75": [0, 0.68333, 0.14528, 0, 0.76888], + "76": [0, 0.68333, 0, 0, 0.62722], + "77": [0, 0.68333, 0.16389, 0, 0.89666], + "78": [0, 0.68333, 0.16389, 0, 0.74333], + "79": [0, 0.68333, 0.09403, 0, 0.76666], + "80": [0, 0.68333, 0.10257, 0, 0.67833], + "81": [0.19444, 0.68333, 0.09403, 0, 0.76666], + "82": [0, 0.68333, 0.03868, 0, 0.72944], + "83": [0, 0.68333, 0.11972, 0, 0.56222], + "84": [0, 0.68333, 0.13305, 0, 0.71555], + "85": [0, 0.68333, 0.16389, 0, 0.74333], + "86": [0, 0.68333, 0.18361, 0, 0.74333], + "87": [0, 0.68333, 0.18361, 0, 0.99888], + "88": [0, 0.68333, 0.15806, 0, 0.74333], + "89": [0, 0.68333, 0.19383, 0, 0.74333], + "90": [0, 0.68333, 0.14528, 0, 0.61333], + "91": [0.25, 0.75, 0.1875, 0, 0.30667], + "93": [0.25, 0.75, 0.10528, 0, 0.30667], + "94": [0, 0.69444, 0.06646, 0, 0.51111], + "95": [0.31, 0.12056, 0.09208, 0, 0.51111], + "97": [0, 0.43056, 0.07671, 0, 0.51111], + "98": [0, 0.69444, 0.06312, 0, 0.46], + "99": [0, 0.43056, 0.05653, 0, 0.46], + "100": [0, 0.69444, 0.10333, 0, 0.51111], + "101": [0, 0.43056, 0.07514, 0, 0.46], + "102": [0.19444, 0.69444, 0.21194, 0, 0.30667], + "103": [0.19444, 0.43056, 0.08847, 0, 0.46], + "104": [0, 0.69444, 0.07671, 0, 0.51111], + "105": [0, 0.65536, 0.1019, 0, 0.30667], + "106": [0.19444, 0.65536, 0.14467, 0, 0.30667], + "107": [0, 0.69444, 0.10764, 0, 0.46], + "108": [0, 0.69444, 0.10333, 0, 0.25555], + "109": [0, 0.43056, 0.07671, 0, 0.81777], + "110": [0, 0.43056, 0.07671, 0, 0.56222], + "111": [0, 0.43056, 0.06312, 0, 0.51111], + "112": [0.19444, 0.43056, 0.06312, 0, 0.51111], + "113": [0.19444, 0.43056, 0.08847, 0, 0.46], + "114": [0, 0.43056, 0.10764, 0, 0.42166], + "115": [0, 0.43056, 0.08208, 0, 0.40889], + "116": [0, 0.61508, 0.09486, 0, 0.33222], + "117": [0, 0.43056, 0.07671, 0, 0.53666], + "118": [0, 0.43056, 0.10764, 0, 0.46], + "119": [0, 0.43056, 0.10764, 0, 0.66444], + "120": [0, 0.43056, 0.12042, 0, 0.46389], + "121": [0.19444, 0.43056, 0.08847, 0, 0.48555], + "122": [0, 0.43056, 0.12292, 0, 0.40889], + "126": [0.35, 0.31786, 0.11585, 0, 0.51111], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.66786, 0.10474, 0, 0.51111], + "176": [0, 0.69444, 0, 0, 0.83129], + "184": [0.17014, 0, 0, 0, 0.46], + "198": [0, 0.68333, 0.12028, 0, 0.88277], + "216": [0.04861, 0.73194, 0.09403, 0, 0.76666], + "223": [0.19444, 0.69444, 0.10514, 0, 0.53666], + "230": [0, 0.43056, 0.07514, 0, 0.71555], + "248": [0.09722, 0.52778, 0.09194, 0, 0.51111], + "338": [0, 0.68333, 0.12028, 0, 0.98499], + "339": [0, 0.43056, 0.07514, 0, 0.71555], + "710": [0, 0.69444, 0.06646, 0, 0.51111], + "711": [0, 0.62847, 0.08295, 0, 0.51111], + "713": [0, 0.56167, 0.10333, 0, 0.51111], + "714": [0, 0.69444, 0.09694, 0, 0.51111], + "715": [0, 0.69444, 0, 0, 0.51111], + "728": [0, 0.69444, 0.10806, 0, 0.51111], + "729": [0, 0.66786, 0.11752, 0, 0.30667], + "730": [0, 0.69444, 0, 0, 0.83129], + "732": [0, 0.66786, 0.11585, 0, 0.51111], + "733": [0, 0.69444, 0.1225, 0, 0.51111], + "915": [0, 0.68333, 0.13305, 0, 0.62722], + "916": [0, 0.68333, 0, 0, 0.81777], + "920": [0, 0.68333, 0.09403, 0, 0.76666], + "923": [0, 0.68333, 0, 0, 0.69222], + "926": [0, 0.68333, 0.15294, 0, 0.66444], + "928": [0, 0.68333, 0.16389, 0, 0.74333], + "931": [0, 0.68333, 0.12028, 0, 0.71555], + "933": [0, 0.68333, 0.11111, 0, 0.76666], + "934": [0, 0.68333, 0.05986, 0, 0.71555], + "936": [0, 0.68333, 0.11111, 0, 0.76666], + "937": [0, 0.68333, 0.10257, 0, 0.71555], + "8211": [0, 0.43056, 0.09208, 0, 0.51111], + "8212": [0, 0.43056, 0.09208, 0, 1.02222], + "8216": [0, 0.69444, 0.12417, 0, 0.30667], + "8217": [0, 0.69444, 0.12417, 0, 0.30667], + "8220": [0, 0.69444, 0.1685, 0, 0.51444], + "8221": [0, 0.69444, 0.06961, 0, 0.51444], + "8463": [0, 0.68889, 0, 0, 0.54028] + }, + "Main-Regular": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0, 0, 0.27778], + "34": [0, 0.69444, 0, 0, 0.5], + "35": [0.19444, 0.69444, 0, 0, 0.83334], + "36": [0.05556, 0.75, 0, 0, 0.5], + "37": [0.05556, 0.75, 0, 0, 0.83334], + "38": [0, 0.69444, 0, 0, 0.77778], + "39": [0, 0.69444, 0, 0, 0.27778], + "40": [0.25, 0.75, 0, 0, 0.38889], + "41": [0.25, 0.75, 0, 0, 0.38889], + "42": [0, 0.75, 0, 0, 0.5], + "43": [0.08333, 0.58333, 0, 0, 0.77778], + "44": [0.19444, 0.10556, 0, 0, 0.27778], + "45": [0, 0.43056, 0, 0, 0.33333], + "46": [0, 0.10556, 0, 0, 0.27778], + "47": [0.25, 0.75, 0, 0, 0.5], + "48": [0, 0.64444, 0, 0, 0.5], + "49": [0, 0.64444, 0, 0, 0.5], + "50": [0, 0.64444, 0, 0, 0.5], + "51": [0, 0.64444, 0, 0, 0.5], + "52": [0, 0.64444, 0, 0, 0.5], + "53": [0, 0.64444, 0, 0, 0.5], + "54": [0, 0.64444, 0, 0, 0.5], + "55": [0, 0.64444, 0, 0, 0.5], + "56": [0, 0.64444, 0, 0, 0.5], + "57": [0, 0.64444, 0, 0, 0.5], + "58": [0, 0.43056, 0, 0, 0.27778], + "59": [0.19444, 0.43056, 0, 0, 0.27778], + "60": [0.0391, 0.5391, 0, 0, 0.77778], + "61": [-0.13313, 0.36687, 0, 0, 0.77778], + "62": [0.0391, 0.5391, 0, 0, 0.77778], + "63": [0, 0.69444, 0, 0, 0.47222], + "64": [0, 0.69444, 0, 0, 0.77778], + "65": [0, 0.68333, 0, 0, 0.75], + "66": [0, 0.68333, 0, 0, 0.70834], + "67": [0, 0.68333, 0, 0, 0.72222], + "68": [0, 0.68333, 0, 0, 0.76389], + "69": [0, 0.68333, 0, 0, 0.68056], + "70": [0, 0.68333, 0, 0, 0.65278], + "71": [0, 0.68333, 0, 0, 0.78472], + "72": [0, 0.68333, 0, 0, 0.75], + "73": [0, 0.68333, 0, 0, 0.36111], + "74": [0, 0.68333, 0, 0, 0.51389], + "75": [0, 0.68333, 0, 0, 0.77778], + "76": [0, 0.68333, 0, 0, 0.625], + "77": [0, 0.68333, 0, 0, 0.91667], + "78": [0, 0.68333, 0, 0, 0.75], + "79": [0, 0.68333, 0, 0, 0.77778], + "80": [0, 0.68333, 0, 0, 0.68056], + "81": [0.19444, 0.68333, 0, 0, 0.77778], + "82": [0, 0.68333, 0, 0, 0.73611], + "83": [0, 0.68333, 0, 0, 0.55556], + "84": [0, 0.68333, 0, 0, 0.72222], + "85": [0, 0.68333, 0, 0, 0.75], + "86": [0, 0.68333, 0.01389, 0, 0.75], + "87": [0, 0.68333, 0.01389, 0, 1.02778], + "88": [0, 0.68333, 0, 0, 0.75], + "89": [0, 0.68333, 0.025, 0, 0.75], + "90": [0, 0.68333, 0, 0, 0.61111], + "91": [0.25, 0.75, 0, 0, 0.27778], + "92": [0.25, 0.75, 0, 0, 0.5], + "93": [0.25, 0.75, 0, 0, 0.27778], + "94": [0, 0.69444, 0, 0, 0.5], + "95": [0.31, 0.12056, 0.02778, 0, 0.5], + "97": [0, 0.43056, 0, 0, 0.5], + "98": [0, 0.69444, 0, 0, 0.55556], + "99": [0, 0.43056, 0, 0, 0.44445], + "100": [0, 0.69444, 0, 0, 0.55556], + "101": [0, 0.43056, 0, 0, 0.44445], + "102": [0, 0.69444, 0.07778, 0, 0.30556], + "103": [0.19444, 0.43056, 0.01389, 0, 0.5], + "104": [0, 0.69444, 0, 0, 0.55556], + "105": [0, 0.66786, 0, 0, 0.27778], + "106": [0.19444, 0.66786, 0, 0, 0.30556], + "107": [0, 0.69444, 0, 0, 0.52778], + "108": [0, 0.69444, 0, 0, 0.27778], + "109": [0, 0.43056, 0, 0, 0.83334], + "110": [0, 0.43056, 0, 0, 0.55556], + "111": [0, 0.43056, 0, 0, 0.5], + "112": [0.19444, 0.43056, 0, 0, 0.55556], + "113": [0.19444, 0.43056, 0, 0, 0.52778], + "114": [0, 0.43056, 0, 0, 0.39167], + "115": [0, 0.43056, 0, 0, 0.39445], + "116": [0, 0.61508, 0, 0, 0.38889], + "117": [0, 0.43056, 0, 0, 0.55556], + "118": [0, 0.43056, 0.01389, 0, 0.52778], + "119": [0, 0.43056, 0.01389, 0, 0.72222], + "120": [0, 0.43056, 0, 0, 0.52778], + "121": [0.19444, 0.43056, 0.01389, 0, 0.52778], + "122": [0, 0.43056, 0, 0, 0.44445], + "123": [0.25, 0.75, 0, 0, 0.5], + "124": [0.25, 0.75, 0, 0, 0.27778], + "125": [0.25, 0.75, 0, 0, 0.5], + "126": [0.35, 0.31786, 0, 0, 0.5], + "160": [0, 0, 0, 0, 0.25], + "163": [0, 0.69444, 0, 0, 0.76909], + "167": [0.19444, 0.69444, 0, 0, 0.44445], + "168": [0, 0.66786, 0, 0, 0.5], + "172": [0, 0.43056, 0, 0, 0.66667], + "176": [0, 0.69444, 0, 0, 0.75], + "177": [0.08333, 0.58333, 0, 0, 0.77778], + "182": [0.19444, 0.69444, 0, 0, 0.61111], + "184": [0.17014, 0, 0, 0, 0.44445], + "198": [0, 0.68333, 0, 0, 0.90278], + "215": [0.08333, 0.58333, 0, 0, 0.77778], + "216": [0.04861, 0.73194, 0, 0, 0.77778], + "223": [0, 0.69444, 0, 0, 0.5], + "230": [0, 0.43056, 0, 0, 0.72222], + "247": [0.08333, 0.58333, 0, 0, 0.77778], + "248": [0.09722, 0.52778, 0, 0, 0.5], + "305": [0, 0.43056, 0, 0, 0.27778], + "338": [0, 0.68333, 0, 0, 1.01389], + "339": [0, 0.43056, 0, 0, 0.77778], + "567": [0.19444, 0.43056, 0, 0, 0.30556], + "710": [0, 0.69444, 0, 0, 0.5], + "711": [0, 0.62847, 0, 0, 0.5], + "713": [0, 0.56778, 0, 0, 0.5], + "714": [0, 0.69444, 0, 0, 0.5], + "715": [0, 0.69444, 0, 0, 0.5], + "728": [0, 0.69444, 0, 0, 0.5], + "729": [0, 0.66786, 0, 0, 0.27778], + "730": [0, 0.69444, 0, 0, 0.75], + "732": [0, 0.66786, 0, 0, 0.5], + "733": [0, 0.69444, 0, 0, 0.5], + "915": [0, 0.68333, 0, 0, 0.625], + "916": [0, 0.68333, 0, 0, 0.83334], + "920": [0, 0.68333, 0, 0, 0.77778], + "923": [0, 0.68333, 0, 0, 0.69445], + "926": [0, 0.68333, 0, 0, 0.66667], + "928": [0, 0.68333, 0, 0, 0.75], + "931": [0, 0.68333, 0, 0, 0.72222], + "933": [0, 0.68333, 0, 0, 0.77778], + "934": [0, 0.68333, 0, 0, 0.72222], + "936": [0, 0.68333, 0, 0, 0.77778], + "937": [0, 0.68333, 0, 0, 0.72222], + "8211": [0, 0.43056, 0.02778, 0, 0.5], + "8212": [0, 0.43056, 0.02778, 0, 1.0], + "8216": [0, 0.69444, 0, 0, 0.27778], + "8217": [0, 0.69444, 0, 0, 0.27778], + "8220": [0, 0.69444, 0, 0, 0.5], + "8221": [0, 0.69444, 0, 0, 0.5], + "8224": [0.19444, 0.69444, 0, 0, 0.44445], + "8225": [0.19444, 0.69444, 0, 0, 0.44445], + "8230": [0, 0.123, 0, 0, 1.172], + "8242": [0, 0.55556, 0, 0, 0.275], + "8407": [0, 0.71444, 0.15382, 0, 0.5], + "8463": [0, 0.68889, 0, 0, 0.54028], + "8465": [0, 0.69444, 0, 0, 0.72222], + "8467": [0, 0.69444, 0, 0.11111, 0.41667], + "8472": [0.19444, 0.43056, 0, 0.11111, 0.63646], + "8476": [0, 0.69444, 0, 0, 0.72222], + "8501": [0, 0.69444, 0, 0, 0.61111], + "8592": [-0.13313, 0.36687, 0, 0, 1.0], + "8593": [0.19444, 0.69444, 0, 0, 0.5], + "8594": [-0.13313, 0.36687, 0, 0, 1.0], + "8595": [0.19444, 0.69444, 0, 0, 0.5], + "8596": [-0.13313, 0.36687, 0, 0, 1.0], + "8597": [0.25, 0.75, 0, 0, 0.5], + "8598": [0.19444, 0.69444, 0, 0, 1.0], + "8599": [0.19444, 0.69444, 0, 0, 1.0], + "8600": [0.19444, 0.69444, 0, 0, 1.0], + "8601": [0.19444, 0.69444, 0, 0, 1.0], + "8614": [0.011, 0.511, 0, 0, 1.0], + "8617": [0.011, 0.511, 0, 0, 1.126], + "8618": [0.011, 0.511, 0, 0, 1.126], + "8636": [-0.13313, 0.36687, 0, 0, 1.0], + "8637": [-0.13313, 0.36687, 0, 0, 1.0], + "8640": [-0.13313, 0.36687, 0, 0, 1.0], + "8641": [-0.13313, 0.36687, 0, 0, 1.0], + "8652": [0.011, 0.671, 0, 0, 1.0], + "8656": [-0.13313, 0.36687, 0, 0, 1.0], + "8657": [0.19444, 0.69444, 0, 0, 0.61111], + "8658": [-0.13313, 0.36687, 0, 0, 1.0], + "8659": [0.19444, 0.69444, 0, 0, 0.61111], + "8660": [-0.13313, 0.36687, 0, 0, 1.0], + "8661": [0.25, 0.75, 0, 0, 0.61111], + "8704": [0, 0.69444, 0, 0, 0.55556], + "8706": [0, 0.69444, 0.05556, 0.08334, 0.5309], + "8707": [0, 0.69444, 0, 0, 0.55556], + "8709": [0.05556, 0.75, 0, 0, 0.5], + "8711": [0, 0.68333, 0, 0, 0.83334], + "8712": [0.0391, 0.5391, 0, 0, 0.66667], + "8715": [0.0391, 0.5391, 0, 0, 0.66667], + "8722": [0.08333, 0.58333, 0, 0, 0.77778], + "8723": [0.08333, 0.58333, 0, 0, 0.77778], + "8725": [0.25, 0.75, 0, 0, 0.5], + "8726": [0.25, 0.75, 0, 0, 0.5], + "8727": [-0.03472, 0.46528, 0, 0, 0.5], + "8728": [-0.05555, 0.44445, 0, 0, 0.5], + "8729": [-0.05555, 0.44445, 0, 0, 0.5], + "8730": [0.2, 0.8, 0, 0, 0.83334], + "8733": [0, 0.43056, 0, 0, 0.77778], + "8734": [0, 0.43056, 0, 0, 1.0], + "8736": [0, 0.69224, 0, 0, 0.72222], + "8739": [0.25, 0.75, 0, 0, 0.27778], + "8741": [0.25, 0.75, 0, 0, 0.5], + "8743": [0, 0.55556, 0, 0, 0.66667], + "8744": [0, 0.55556, 0, 0, 0.66667], + "8745": [0, 0.55556, 0, 0, 0.66667], + "8746": [0, 0.55556, 0, 0, 0.66667], + "8747": [0.19444, 0.69444, 0.11111, 0, 0.41667], + "8764": [-0.13313, 0.36687, 0, 0, 0.77778], + "8768": [0.19444, 0.69444, 0, 0, 0.27778], + "8771": [-0.03625, 0.46375, 0, 0, 0.77778], + "8773": [-0.022, 0.589, 0, 0, 0.778], + "8776": [-0.01688, 0.48312, 0, 0, 0.77778], + "8781": [-0.03625, 0.46375, 0, 0, 0.77778], + "8784": [-0.133, 0.673, 0, 0, 0.778], + "8801": [-0.03625, 0.46375, 0, 0, 0.77778], + "8804": [0.13597, 0.63597, 0, 0, 0.77778], + "8805": [0.13597, 0.63597, 0, 0, 0.77778], + "8810": [0.0391, 0.5391, 0, 0, 1.0], + "8811": [0.0391, 0.5391, 0, 0, 1.0], + "8826": [0.0391, 0.5391, 0, 0, 0.77778], + "8827": [0.0391, 0.5391, 0, 0, 0.77778], + "8834": [0.0391, 0.5391, 0, 0, 0.77778], + "8835": [0.0391, 0.5391, 0, 0, 0.77778], + "8838": [0.13597, 0.63597, 0, 0, 0.77778], + "8839": [0.13597, 0.63597, 0, 0, 0.77778], + "8846": [0, 0.55556, 0, 0, 0.66667], + "8849": [0.13597, 0.63597, 0, 0, 0.77778], + "8850": [0.13597, 0.63597, 0, 0, 0.77778], + "8851": [0, 0.55556, 0, 0, 0.66667], + "8852": [0, 0.55556, 0, 0, 0.66667], + "8853": [0.08333, 0.58333, 0, 0, 0.77778], + "8854": [0.08333, 0.58333, 0, 0, 0.77778], + "8855": [0.08333, 0.58333, 0, 0, 0.77778], + "8856": [0.08333, 0.58333, 0, 0, 0.77778], + "8857": [0.08333, 0.58333, 0, 0, 0.77778], + "8866": [0, 0.69444, 0, 0, 0.61111], + "8867": [0, 0.69444, 0, 0, 0.61111], + "8868": [0, 0.69444, 0, 0, 0.77778], + "8869": [0, 0.69444, 0, 0, 0.77778], + "8872": [0.249, 0.75, 0, 0, 0.867], + "8900": [-0.05555, 0.44445, 0, 0, 0.5], + "8901": [-0.05555, 0.44445, 0, 0, 0.27778], + "8902": [-0.03472, 0.46528, 0, 0, 0.5], + "8904": [0.005, 0.505, 0, 0, 0.9], + "8942": [0.03, 0.903, 0, 0, 0.278], + "8943": [-0.19, 0.313, 0, 0, 1.172], + "8945": [-0.1, 0.823, 0, 0, 1.282], + "8968": [0.25, 0.75, 0, 0, 0.44445], + "8969": [0.25, 0.75, 0, 0, 0.44445], + "8970": [0.25, 0.75, 0, 0, 0.44445], + "8971": [0.25, 0.75, 0, 0, 0.44445], + "8994": [-0.14236, 0.35764, 0, 0, 1.0], + "8995": [-0.14236, 0.35764, 0, 0, 1.0], + "9136": [0.244, 0.744, 0, 0, 0.412], + "9137": [0.244, 0.745, 0, 0, 0.412], + "9651": [0.19444, 0.69444, 0, 0, 0.88889], + "9657": [-0.03472, 0.46528, 0, 0, 0.5], + "9661": [0.19444, 0.69444, 0, 0, 0.88889], + "9667": [-0.03472, 0.46528, 0, 0, 0.5], + "9711": [0.19444, 0.69444, 0, 0, 1.0], + "9824": [0.12963, 0.69444, 0, 0, 0.77778], + "9825": [0.12963, 0.69444, 0, 0, 0.77778], + "9826": [0.12963, 0.69444, 0, 0, 0.77778], + "9827": [0.12963, 0.69444, 0, 0, 0.77778], + "9837": [0, 0.75, 0, 0, 0.38889], + "9838": [0.19444, 0.69444, 0, 0, 0.38889], + "9839": [0.19444, 0.69444, 0, 0, 0.38889], + "10216": [0.25, 0.75, 0, 0, 0.38889], + "10217": [0.25, 0.75, 0, 0, 0.38889], + "10222": [0.244, 0.744, 0, 0, 0.412], + "10223": [0.244, 0.745, 0, 0, 0.412], + "10229": [0.011, 0.511, 0, 0, 1.609], + "10230": [0.011, 0.511, 0, 0, 1.638], + "10231": [0.011, 0.511, 0, 0, 1.859], + "10232": [0.024, 0.525, 0, 0, 1.609], + "10233": [0.024, 0.525, 0, 0, 1.638], + "10234": [0.024, 0.525, 0, 0, 1.858], + "10236": [0.011, 0.511, 0, 0, 1.638], + "10815": [0, 0.68333, 0, 0, 0.75], + "10927": [0.13597, 0.63597, 0, 0, 0.77778], + "10928": [0.13597, 0.63597, 0, 0, 0.77778], + "57376": [0.19444, 0.69444, 0, 0, 0] + }, + "Math-BoldItalic": { + "32": [0, 0, 0, 0, 0.25], + "48": [0, 0.44444, 0, 0, 0.575], + "49": [0, 0.44444, 0, 0, 0.575], + "50": [0, 0.44444, 0, 0, 0.575], + "51": [0.19444, 0.44444, 0, 0, 0.575], + "52": [0.19444, 0.44444, 0, 0, 0.575], + "53": [0.19444, 0.44444, 0, 0, 0.575], + "54": [0, 0.64444, 0, 0, 0.575], + "55": [0.19444, 0.44444, 0, 0, 0.575], + "56": [0, 0.64444, 0, 0, 0.575], + "57": [0.19444, 0.44444, 0, 0, 0.575], + "65": [0, 0.68611, 0, 0, 0.86944], + "66": [0, 0.68611, 0.04835, 0, 0.8664], + "67": [0, 0.68611, 0.06979, 0, 0.81694], + "68": [0, 0.68611, 0.03194, 0, 0.93812], + "69": [0, 0.68611, 0.05451, 0, 0.81007], + "70": [0, 0.68611, 0.15972, 0, 0.68889], + "71": [0, 0.68611, 0, 0, 0.88673], + "72": [0, 0.68611, 0.08229, 0, 0.98229], + "73": [0, 0.68611, 0.07778, 0, 0.51111], + "74": [0, 0.68611, 0.10069, 0, 0.63125], + "75": [0, 0.68611, 0.06979, 0, 0.97118], + "76": [0, 0.68611, 0, 0, 0.75555], + "77": [0, 0.68611, 0.11424, 0, 1.14201], + "78": [0, 0.68611, 0.11424, 0, 0.95034], + "79": [0, 0.68611, 0.03194, 0, 0.83666], + "80": [0, 0.68611, 0.15972, 0, 0.72309], + "81": [0.19444, 0.68611, 0, 0, 0.86861], + "82": [0, 0.68611, 0.00421, 0, 0.87235], + "83": [0, 0.68611, 0.05382, 0, 0.69271], + "84": [0, 0.68611, 0.15972, 0, 0.63663], + "85": [0, 0.68611, 0.11424, 0, 0.80027], + "86": [0, 0.68611, 0.25555, 0, 0.67778], + "87": [0, 0.68611, 0.15972, 0, 1.09305], + "88": [0, 0.68611, 0.07778, 0, 0.94722], + "89": [0, 0.68611, 0.25555, 0, 0.67458], + "90": [0, 0.68611, 0.06979, 0, 0.77257], + "97": [0, 0.44444, 0, 0, 0.63287], + "98": [0, 0.69444, 0, 0, 0.52083], + "99": [0, 0.44444, 0, 0, 0.51342], + "100": [0, 0.69444, 0, 0, 0.60972], + "101": [0, 0.44444, 0, 0, 0.55361], + "102": [0.19444, 0.69444, 0.11042, 0, 0.56806], + "103": [0.19444, 0.44444, 0.03704, 0, 0.5449], + "104": [0, 0.69444, 0, 0, 0.66759], + "105": [0, 0.69326, 0, 0, 0.4048], + "106": [0.19444, 0.69326, 0.0622, 0, 0.47083], + "107": [0, 0.69444, 0.01852, 0, 0.6037], + "108": [0, 0.69444, 0.0088, 0, 0.34815], + "109": [0, 0.44444, 0, 0, 1.0324], + "110": [0, 0.44444, 0, 0, 0.71296], + "111": [0, 0.44444, 0, 0, 0.58472], + "112": [0.19444, 0.44444, 0, 0, 0.60092], + "113": [0.19444, 0.44444, 0.03704, 0, 0.54213], + "114": [0, 0.44444, 0.03194, 0, 0.5287], + "115": [0, 0.44444, 0, 0, 0.53125], + "116": [0, 0.63492, 0, 0, 0.41528], + "117": [0, 0.44444, 0, 0, 0.68102], + "118": [0, 0.44444, 0.03704, 0, 0.56666], + "119": [0, 0.44444, 0.02778, 0, 0.83148], + "120": [0, 0.44444, 0, 0, 0.65903], + "121": [0.19444, 0.44444, 0.03704, 0, 0.59028], + "122": [0, 0.44444, 0.04213, 0, 0.55509], + "160": [0, 0, 0, 0, 0.25], + "915": [0, 0.68611, 0.15972, 0, 0.65694], + "916": [0, 0.68611, 0, 0, 0.95833], + "920": [0, 0.68611, 0.03194, 0, 0.86722], + "923": [0, 0.68611, 0, 0, 0.80555], + "926": [0, 0.68611, 0.07458, 0, 0.84125], + "928": [0, 0.68611, 0.08229, 0, 0.98229], + "931": [0, 0.68611, 0.05451, 0, 0.88507], + "933": [0, 0.68611, 0.15972, 0, 0.67083], + "934": [0, 0.68611, 0, 0, 0.76666], + "936": [0, 0.68611, 0.11653, 0, 0.71402], + "937": [0, 0.68611, 0.04835, 0, 0.8789], + "945": [0, 0.44444, 0, 0, 0.76064], + "946": [0.19444, 0.69444, 0.03403, 0, 0.65972], + "947": [0.19444, 0.44444, 0.06389, 0, 0.59003], + "948": [0, 0.69444, 0.03819, 0, 0.52222], + "949": [0, 0.44444, 0, 0, 0.52882], + "950": [0.19444, 0.69444, 0.06215, 0, 0.50833], + "951": [0.19444, 0.44444, 0.03704, 0, 0.6], + "952": [0, 0.69444, 0.03194, 0, 0.5618], + "953": [0, 0.44444, 0, 0, 0.41204], + "954": [0, 0.44444, 0, 0, 0.66759], + "955": [0, 0.69444, 0, 0, 0.67083], + "956": [0.19444, 0.44444, 0, 0, 0.70787], + "957": [0, 0.44444, 0.06898, 0, 0.57685], + "958": [0.19444, 0.69444, 0.03021, 0, 0.50833], + "959": [0, 0.44444, 0, 0, 0.58472], + "960": [0, 0.44444, 0.03704, 0, 0.68241], + "961": [0.19444, 0.44444, 0, 0, 0.6118], + "962": [0.09722, 0.44444, 0.07917, 0, 0.42361], + "963": [0, 0.44444, 0.03704, 0, 0.68588], + "964": [0, 0.44444, 0.13472, 0, 0.52083], + "965": [0, 0.44444, 0.03704, 0, 0.63055], + "966": [0.19444, 0.44444, 0, 0, 0.74722], + "967": [0.19444, 0.44444, 0, 0, 0.71805], + "968": [0.19444, 0.69444, 0.03704, 0, 0.75833], + "969": [0, 0.44444, 0.03704, 0, 0.71782], + "977": [0, 0.69444, 0, 0, 0.69155], + "981": [0.19444, 0.69444, 0, 0, 0.7125], + "982": [0, 0.44444, 0.03194, 0, 0.975], + "1009": [0.19444, 0.44444, 0, 0, 0.6118], + "1013": [0, 0.44444, 0, 0, 0.48333], + "57649": [0, 0.44444, 0, 0, 0.39352], + "57911": [0.19444, 0.44444, 0, 0, 0.43889] + }, + "Math-Italic": { + "32": [0, 0, 0, 0, 0.25], + "48": [0, 0.43056, 0, 0, 0.5], + "49": [0, 0.43056, 0, 0, 0.5], + "50": [0, 0.43056, 0, 0, 0.5], + "51": [0.19444, 0.43056, 0, 0, 0.5], + "52": [0.19444, 0.43056, 0, 0, 0.5], + "53": [0.19444, 0.43056, 0, 0, 0.5], + "54": [0, 0.64444, 0, 0, 0.5], + "55": [0.19444, 0.43056, 0, 0, 0.5], + "56": [0, 0.64444, 0, 0, 0.5], + "57": [0.19444, 0.43056, 0, 0, 0.5], + "65": [0, 0.68333, 0, 0.13889, 0.75], + "66": [0, 0.68333, 0.05017, 0.08334, 0.75851], + "67": [0, 0.68333, 0.07153, 0.08334, 0.71472], + "68": [0, 0.68333, 0.02778, 0.05556, 0.82792], + "69": [0, 0.68333, 0.05764, 0.08334, 0.7382], + "70": [0, 0.68333, 0.13889, 0.08334, 0.64306], + "71": [0, 0.68333, 0, 0.08334, 0.78625], + "72": [0, 0.68333, 0.08125, 0.05556, 0.83125], + "73": [0, 0.68333, 0.07847, 0.11111, 0.43958], + "74": [0, 0.68333, 0.09618, 0.16667, 0.55451], + "75": [0, 0.68333, 0.07153, 0.05556, 0.84931], + "76": [0, 0.68333, 0, 0.02778, 0.68056], + "77": [0, 0.68333, 0.10903, 0.08334, 0.97014], + "78": [0, 0.68333, 0.10903, 0.08334, 0.80347], + "79": [0, 0.68333, 0.02778, 0.08334, 0.76278], + "80": [0, 0.68333, 0.13889, 0.08334, 0.64201], + "81": [0.19444, 0.68333, 0, 0.08334, 0.79056], + "82": [0, 0.68333, 0.00773, 0.08334, 0.75929], + "83": [0, 0.68333, 0.05764, 0.08334, 0.6132], + "84": [0, 0.68333, 0.13889, 0.08334, 0.58438], + "85": [0, 0.68333, 0.10903, 0.02778, 0.68278], + "86": [0, 0.68333, 0.22222, 0, 0.58333], + "87": [0, 0.68333, 0.13889, 0, 0.94445], + "88": [0, 0.68333, 0.07847, 0.08334, 0.82847], + "89": [0, 0.68333, 0.22222, 0, 0.58056], + "90": [0, 0.68333, 0.07153, 0.08334, 0.68264], + "97": [0, 0.43056, 0, 0, 0.52859], + "98": [0, 0.69444, 0, 0, 0.42917], + "99": [0, 0.43056, 0, 0.05556, 0.43276], + "100": [0, 0.69444, 0, 0.16667, 0.52049], + "101": [0, 0.43056, 0, 0.05556, 0.46563], + "102": [0.19444, 0.69444, 0.10764, 0.16667, 0.48959], + "103": [0.19444, 0.43056, 0.03588, 0.02778, 0.47697], + "104": [0, 0.69444, 0, 0, 0.57616], + "105": [0, 0.65952, 0, 0, 0.34451], + "106": [0.19444, 0.65952, 0.05724, 0, 0.41181], + "107": [0, 0.69444, 0.03148, 0, 0.5206], + "108": [0, 0.69444, 0.01968, 0.08334, 0.29838], + "109": [0, 0.43056, 0, 0, 0.87801], + "110": [0, 0.43056, 0, 0, 0.60023], + "111": [0, 0.43056, 0, 0.05556, 0.48472], + "112": [0.19444, 0.43056, 0, 0.08334, 0.50313], + "113": [0.19444, 0.43056, 0.03588, 0.08334, 0.44641], + "114": [0, 0.43056, 0.02778, 0.05556, 0.45116], + "115": [0, 0.43056, 0, 0.05556, 0.46875], + "116": [0, 0.61508, 0, 0.08334, 0.36111], + "117": [0, 0.43056, 0, 0.02778, 0.57246], + "118": [0, 0.43056, 0.03588, 0.02778, 0.48472], + "119": [0, 0.43056, 0.02691, 0.08334, 0.71592], + "120": [0, 0.43056, 0, 0.02778, 0.57153], + "121": [0.19444, 0.43056, 0.03588, 0.05556, 0.49028], + "122": [0, 0.43056, 0.04398, 0.05556, 0.46505], + "160": [0, 0, 0, 0, 0.25], + "915": [0, 0.68333, 0.13889, 0.08334, 0.61528], + "916": [0, 0.68333, 0, 0.16667, 0.83334], + "920": [0, 0.68333, 0.02778, 0.08334, 0.76278], + "923": [0, 0.68333, 0, 0.16667, 0.69445], + "926": [0, 0.68333, 0.07569, 0.08334, 0.74236], + "928": [0, 0.68333, 0.08125, 0.05556, 0.83125], + "931": [0, 0.68333, 0.05764, 0.08334, 0.77986], + "933": [0, 0.68333, 0.13889, 0.05556, 0.58333], + "934": [0, 0.68333, 0, 0.08334, 0.66667], + "936": [0, 0.68333, 0.11, 0.05556, 0.61222], + "937": [0, 0.68333, 0.05017, 0.08334, 0.7724], + "945": [0, 0.43056, 0.0037, 0.02778, 0.6397], + "946": [0.19444, 0.69444, 0.05278, 0.08334, 0.56563], + "947": [0.19444, 0.43056, 0.05556, 0, 0.51773], + "948": [0, 0.69444, 0.03785, 0.05556, 0.44444], + "949": [0, 0.43056, 0, 0.08334, 0.46632], + "950": [0.19444, 0.69444, 0.07378, 0.08334, 0.4375], + "951": [0.19444, 0.43056, 0.03588, 0.05556, 0.49653], + "952": [0, 0.69444, 0.02778, 0.08334, 0.46944], + "953": [0, 0.43056, 0, 0.05556, 0.35394], + "954": [0, 0.43056, 0, 0, 0.57616], + "955": [0, 0.69444, 0, 0, 0.58334], + "956": [0.19444, 0.43056, 0, 0.02778, 0.60255], + "957": [0, 0.43056, 0.06366, 0.02778, 0.49398], + "958": [0.19444, 0.69444, 0.04601, 0.11111, 0.4375], + "959": [0, 0.43056, 0, 0.05556, 0.48472], + "960": [0, 0.43056, 0.03588, 0, 0.57003], + "961": [0.19444, 0.43056, 0, 0.08334, 0.51702], + "962": [0.09722, 0.43056, 0.07986, 0.08334, 0.36285], + "963": [0, 0.43056, 0.03588, 0, 0.57141], + "964": [0, 0.43056, 0.1132, 0.02778, 0.43715], + "965": [0, 0.43056, 0.03588, 0.02778, 0.54028], + "966": [0.19444, 0.43056, 0, 0.08334, 0.65417], + "967": [0.19444, 0.43056, 0, 0.05556, 0.62569], + "968": [0.19444, 0.69444, 0.03588, 0.11111, 0.65139], + "969": [0, 0.43056, 0.03588, 0, 0.62245], + "977": [0, 0.69444, 0, 0.08334, 0.59144], + "981": [0.19444, 0.69444, 0, 0.08334, 0.59583], + "982": [0, 0.43056, 0.02778, 0, 0.82813], + "1009": [0.19444, 0.43056, 0, 0.08334, 0.51702], + "1013": [0, 0.43056, 0, 0.05556, 0.4059], + "57649": [0, 0.43056, 0, 0.02778, 0.32246], + "57911": [0.19444, 0.43056, 0, 0.08334, 0.38403] + }, + "SansSerif-Bold": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0, 0, 0.36667], + "34": [0, 0.69444, 0, 0, 0.55834], + "35": [0.19444, 0.69444, 0, 0, 0.91667], + "36": [0.05556, 0.75, 0, 0, 0.55], + "37": [0.05556, 0.75, 0, 0, 1.02912], + "38": [0, 0.69444, 0, 0, 0.83056], + "39": [0, 0.69444, 0, 0, 0.30556], + "40": [0.25, 0.75, 0, 0, 0.42778], + "41": [0.25, 0.75, 0, 0, 0.42778], + "42": [0, 0.75, 0, 0, 0.55], + "43": [0.11667, 0.61667, 0, 0, 0.85556], + "44": [0.10556, 0.13056, 0, 0, 0.30556], + "45": [0, 0.45833, 0, 0, 0.36667], + "46": [0, 0.13056, 0, 0, 0.30556], + "47": [0.25, 0.75, 0, 0, 0.55], + "48": [0, 0.69444, 0, 0, 0.55], + "49": [0, 0.69444, 0, 0, 0.55], + "50": [0, 0.69444, 0, 0, 0.55], + "51": [0, 0.69444, 0, 0, 0.55], + "52": [0, 0.69444, 0, 0, 0.55], + "53": [0, 0.69444, 0, 0, 0.55], + "54": [0, 0.69444, 0, 0, 0.55], + "55": [0, 0.69444, 0, 0, 0.55], + "56": [0, 0.69444, 0, 0, 0.55], + "57": [0, 0.69444, 0, 0, 0.55], + "58": [0, 0.45833, 0, 0, 0.30556], + "59": [0.10556, 0.45833, 0, 0, 0.30556], + "61": [-0.09375, 0.40625, 0, 0, 0.85556], + "63": [0, 0.69444, 0, 0, 0.51945], + "64": [0, 0.69444, 0, 0, 0.73334], + "65": [0, 0.69444, 0, 0, 0.73334], + "66": [0, 0.69444, 0, 0, 0.73334], + "67": [0, 0.69444, 0, 0, 0.70278], + "68": [0, 0.69444, 0, 0, 0.79445], + "69": [0, 0.69444, 0, 0, 0.64167], + "70": [0, 0.69444, 0, 0, 0.61111], + "71": [0, 0.69444, 0, 0, 0.73334], + "72": [0, 0.69444, 0, 0, 0.79445], + "73": [0, 0.69444, 0, 0, 0.33056], + "74": [0, 0.69444, 0, 0, 0.51945], + "75": [0, 0.69444, 0, 0, 0.76389], + "76": [0, 0.69444, 0, 0, 0.58056], + "77": [0, 0.69444, 0, 0, 0.97778], + "78": [0, 0.69444, 0, 0, 0.79445], + "79": [0, 0.69444, 0, 0, 0.79445], + "80": [0, 0.69444, 0, 0, 0.70278], + "81": [0.10556, 0.69444, 0, 0, 0.79445], + "82": [0, 0.69444, 0, 0, 0.70278], + "83": [0, 0.69444, 0, 0, 0.61111], + "84": [0, 0.69444, 0, 0, 0.73334], + "85": [0, 0.69444, 0, 0, 0.76389], + "86": [0, 0.69444, 0.01528, 0, 0.73334], + "87": [0, 0.69444, 0.01528, 0, 1.03889], + "88": [0, 0.69444, 0, 0, 0.73334], + "89": [0, 0.69444, 0.0275, 0, 0.73334], + "90": [0, 0.69444, 0, 0, 0.67223], + "91": [0.25, 0.75, 0, 0, 0.34306], + "93": [0.25, 0.75, 0, 0, 0.34306], + "94": [0, 0.69444, 0, 0, 0.55], + "95": [0.35, 0.10833, 0.03056, 0, 0.55], + "97": [0, 0.45833, 0, 0, 0.525], + "98": [0, 0.69444, 0, 0, 0.56111], + "99": [0, 0.45833, 0, 0, 0.48889], + "100": [0, 0.69444, 0, 0, 0.56111], + "101": [0, 0.45833, 0, 0, 0.51111], + "102": [0, 0.69444, 0.07639, 0, 0.33611], + "103": [0.19444, 0.45833, 0.01528, 0, 0.55], + "104": [0, 0.69444, 0, 0, 0.56111], + "105": [0, 0.69444, 0, 0, 0.25556], + "106": [0.19444, 0.69444, 0, 0, 0.28611], + "107": [0, 0.69444, 0, 0, 0.53056], + "108": [0, 0.69444, 0, 0, 0.25556], + "109": [0, 0.45833, 0, 0, 0.86667], + "110": [0, 0.45833, 0, 0, 0.56111], + "111": [0, 0.45833, 0, 0, 0.55], + "112": [0.19444, 0.45833, 0, 0, 0.56111], + "113": [0.19444, 0.45833, 0, 0, 0.56111], + "114": [0, 0.45833, 0.01528, 0, 0.37222], + "115": [0, 0.45833, 0, 0, 0.42167], + "116": [0, 0.58929, 0, 0, 0.40417], + "117": [0, 0.45833, 0, 0, 0.56111], + "118": [0, 0.45833, 0.01528, 0, 0.5], + "119": [0, 0.45833, 0.01528, 0, 0.74445], + "120": [0, 0.45833, 0, 0, 0.5], + "121": [0.19444, 0.45833, 0.01528, 0, 0.5], + "122": [0, 0.45833, 0, 0, 0.47639], + "126": [0.35, 0.34444, 0, 0, 0.55], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.69444, 0, 0, 0.55], + "176": [0, 0.69444, 0, 0, 0.73334], + "180": [0, 0.69444, 0, 0, 0.55], + "184": [0.17014, 0, 0, 0, 0.48889], + "305": [0, 0.45833, 0, 0, 0.25556], + "567": [0.19444, 0.45833, 0, 0, 0.28611], + "710": [0, 0.69444, 0, 0, 0.55], + "711": [0, 0.63542, 0, 0, 0.55], + "713": [0, 0.63778, 0, 0, 0.55], + "728": [0, 0.69444, 0, 0, 0.55], + "729": [0, 0.69444, 0, 0, 0.30556], + "730": [0, 0.69444, 0, 0, 0.73334], + "732": [0, 0.69444, 0, 0, 0.55], + "733": [0, 0.69444, 0, 0, 0.55], + "915": [0, 0.69444, 0, 0, 0.58056], + "916": [0, 0.69444, 0, 0, 0.91667], + "920": [0, 0.69444, 0, 0, 0.85556], + "923": [0, 0.69444, 0, 0, 0.67223], + "926": [0, 0.69444, 0, 0, 0.73334], + "928": [0, 0.69444, 0, 0, 0.79445], + "931": [0, 0.69444, 0, 0, 0.79445], + "933": [0, 0.69444, 0, 0, 0.85556], + "934": [0, 0.69444, 0, 0, 0.79445], + "936": [0, 0.69444, 0, 0, 0.85556], + "937": [0, 0.69444, 0, 0, 0.79445], + "8211": [0, 0.45833, 0.03056, 0, 0.55], + "8212": [0, 0.45833, 0.03056, 0, 1.10001], + "8216": [0, 0.69444, 0, 0, 0.30556], + "8217": [0, 0.69444, 0, 0, 0.30556], + "8220": [0, 0.69444, 0, 0, 0.55834], + "8221": [0, 0.69444, 0, 0, 0.55834] + }, + "SansSerif-Italic": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0.05733, 0, 0.31945], + "34": [0, 0.69444, 0.00316, 0, 0.5], + "35": [0.19444, 0.69444, 0.05087, 0, 0.83334], + "36": [0.05556, 0.75, 0.11156, 0, 0.5], + "37": [0.05556, 0.75, 0.03126, 0, 0.83334], + "38": [0, 0.69444, 0.03058, 0, 0.75834], + "39": [0, 0.69444, 0.07816, 0, 0.27778], + "40": [0.25, 0.75, 0.13164, 0, 0.38889], + "41": [0.25, 0.75, 0.02536, 0, 0.38889], + "42": [0, 0.75, 0.11775, 0, 0.5], + "43": [0.08333, 0.58333, 0.02536, 0, 0.77778], + "44": [0.125, 0.08333, 0, 0, 0.27778], + "45": [0, 0.44444, 0.01946, 0, 0.33333], + "46": [0, 0.08333, 0, 0, 0.27778], + "47": [0.25, 0.75, 0.13164, 0, 0.5], + "48": [0, 0.65556, 0.11156, 0, 0.5], + "49": [0, 0.65556, 0.11156, 0, 0.5], + "50": [0, 0.65556, 0.11156, 0, 0.5], + "51": [0, 0.65556, 0.11156, 0, 0.5], + "52": [0, 0.65556, 0.11156, 0, 0.5], + "53": [0, 0.65556, 0.11156, 0, 0.5], + "54": [0, 0.65556, 0.11156, 0, 0.5], + "55": [0, 0.65556, 0.11156, 0, 0.5], + "56": [0, 0.65556, 0.11156, 0, 0.5], + "57": [0, 0.65556, 0.11156, 0, 0.5], + "58": [0, 0.44444, 0.02502, 0, 0.27778], + "59": [0.125, 0.44444, 0.02502, 0, 0.27778], + "61": [-0.13, 0.37, 0.05087, 0, 0.77778], + "63": [0, 0.69444, 0.11809, 0, 0.47222], + "64": [0, 0.69444, 0.07555, 0, 0.66667], + "65": [0, 0.69444, 0, 0, 0.66667], + "66": [0, 0.69444, 0.08293, 0, 0.66667], + "67": [0, 0.69444, 0.11983, 0, 0.63889], + "68": [0, 0.69444, 0.07555, 0, 0.72223], + "69": [0, 0.69444, 0.11983, 0, 0.59722], + "70": [0, 0.69444, 0.13372, 0, 0.56945], + "71": [0, 0.69444, 0.11983, 0, 0.66667], + "72": [0, 0.69444, 0.08094, 0, 0.70834], + "73": [0, 0.69444, 0.13372, 0, 0.27778], + "74": [0, 0.69444, 0.08094, 0, 0.47222], + "75": [0, 0.69444, 0.11983, 0, 0.69445], + "76": [0, 0.69444, 0, 0, 0.54167], + "77": [0, 0.69444, 0.08094, 0, 0.875], + "78": [0, 0.69444, 0.08094, 0, 0.70834], + "79": [0, 0.69444, 0.07555, 0, 0.73611], + "80": [0, 0.69444, 0.08293, 0, 0.63889], + "81": [0.125, 0.69444, 0.07555, 0, 0.73611], + "82": [0, 0.69444, 0.08293, 0, 0.64584], + "83": [0, 0.69444, 0.09205, 0, 0.55556], + "84": [0, 0.69444, 0.13372, 0, 0.68056], + "85": [0, 0.69444, 0.08094, 0, 0.6875], + "86": [0, 0.69444, 0.1615, 0, 0.66667], + "87": [0, 0.69444, 0.1615, 0, 0.94445], + "88": [0, 0.69444, 0.13372, 0, 0.66667], + "89": [0, 0.69444, 0.17261, 0, 0.66667], + "90": [0, 0.69444, 0.11983, 0, 0.61111], + "91": [0.25, 0.75, 0.15942, 0, 0.28889], + "93": [0.25, 0.75, 0.08719, 0, 0.28889], + "94": [0, 0.69444, 0.0799, 0, 0.5], + "95": [0.35, 0.09444, 0.08616, 0, 0.5], + "97": [0, 0.44444, 0.00981, 0, 0.48056], + "98": [0, 0.69444, 0.03057, 0, 0.51667], + "99": [0, 0.44444, 0.08336, 0, 0.44445], + "100": [0, 0.69444, 0.09483, 0, 0.51667], + "101": [0, 0.44444, 0.06778, 0, 0.44445], + "102": [0, 0.69444, 0.21705, 0, 0.30556], + "103": [0.19444, 0.44444, 0.10836, 0, 0.5], + "104": [0, 0.69444, 0.01778, 0, 0.51667], + "105": [0, 0.67937, 0.09718, 0, 0.23889], + "106": [0.19444, 0.67937, 0.09162, 0, 0.26667], + "107": [0, 0.69444, 0.08336, 0, 0.48889], + "108": [0, 0.69444, 0.09483, 0, 0.23889], + "109": [0, 0.44444, 0.01778, 0, 0.79445], + "110": [0, 0.44444, 0.01778, 0, 0.51667], + "111": [0, 0.44444, 0.06613, 0, 0.5], + "112": [0.19444, 0.44444, 0.0389, 0, 0.51667], + "113": [0.19444, 0.44444, 0.04169, 0, 0.51667], + "114": [0, 0.44444, 0.10836, 0, 0.34167], + "115": [0, 0.44444, 0.0778, 0, 0.38333], + "116": [0, 0.57143, 0.07225, 0, 0.36111], + "117": [0, 0.44444, 0.04169, 0, 0.51667], + "118": [0, 0.44444, 0.10836, 0, 0.46111], + "119": [0, 0.44444, 0.10836, 0, 0.68334], + "120": [0, 0.44444, 0.09169, 0, 0.46111], + "121": [0.19444, 0.44444, 0.10836, 0, 0.46111], + "122": [0, 0.44444, 0.08752, 0, 0.43472], + "126": [0.35, 0.32659, 0.08826, 0, 0.5], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.67937, 0.06385, 0, 0.5], + "176": [0, 0.69444, 0, 0, 0.73752], + "184": [0.17014, 0, 0, 0, 0.44445], + "305": [0, 0.44444, 0.04169, 0, 0.23889], + "567": [0.19444, 0.44444, 0.04169, 0, 0.26667], + "710": [0, 0.69444, 0.0799, 0, 0.5], + "711": [0, 0.63194, 0.08432, 0, 0.5], + "713": [0, 0.60889, 0.08776, 0, 0.5], + "714": [0, 0.69444, 0.09205, 0, 0.5], + "715": [0, 0.69444, 0, 0, 0.5], + "728": [0, 0.69444, 0.09483, 0, 0.5], + "729": [0, 0.67937, 0.07774, 0, 0.27778], + "730": [0, 0.69444, 0, 0, 0.73752], + "732": [0, 0.67659, 0.08826, 0, 0.5], + "733": [0, 0.69444, 0.09205, 0, 0.5], + "915": [0, 0.69444, 0.13372, 0, 0.54167], + "916": [0, 0.69444, 0, 0, 0.83334], + "920": [0, 0.69444, 0.07555, 0, 0.77778], + "923": [0, 0.69444, 0, 0, 0.61111], + "926": [0, 0.69444, 0.12816, 0, 0.66667], + "928": [0, 0.69444, 0.08094, 0, 0.70834], + "931": [0, 0.69444, 0.11983, 0, 0.72222], + "933": [0, 0.69444, 0.09031, 0, 0.77778], + "934": [0, 0.69444, 0.04603, 0, 0.72222], + "936": [0, 0.69444, 0.09031, 0, 0.77778], + "937": [0, 0.69444, 0.08293, 0, 0.72222], + "8211": [0, 0.44444, 0.08616, 0, 0.5], + "8212": [0, 0.44444, 0.08616, 0, 1.0], + "8216": [0, 0.69444, 0.07816, 0, 0.27778], + "8217": [0, 0.69444, 0.07816, 0, 0.27778], + "8220": [0, 0.69444, 0.14205, 0, 0.5], + "8221": [0, 0.69444, 0.00316, 0, 0.5] + }, + "SansSerif-Regular": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0, 0, 0.31945], + "34": [0, 0.69444, 0, 0, 0.5], + "35": [0.19444, 0.69444, 0, 0, 0.83334], + "36": [0.05556, 0.75, 0, 0, 0.5], + "37": [0.05556, 0.75, 0, 0, 0.83334], + "38": [0, 0.69444, 0, 0, 0.75834], + "39": [0, 0.69444, 0, 0, 0.27778], + "40": [0.25, 0.75, 0, 0, 0.38889], + "41": [0.25, 0.75, 0, 0, 0.38889], + "42": [0, 0.75, 0, 0, 0.5], + "43": [0.08333, 0.58333, 0, 0, 0.77778], + "44": [0.125, 0.08333, 0, 0, 0.27778], + "45": [0, 0.44444, 0, 0, 0.33333], + "46": [0, 0.08333, 0, 0, 0.27778], + "47": [0.25, 0.75, 0, 0, 0.5], + "48": [0, 0.65556, 0, 0, 0.5], + "49": [0, 0.65556, 0, 0, 0.5], + "50": [0, 0.65556, 0, 0, 0.5], + "51": [0, 0.65556, 0, 0, 0.5], + "52": [0, 0.65556, 0, 0, 0.5], + "53": [0, 0.65556, 0, 0, 0.5], + "54": [0, 0.65556, 0, 0, 0.5], + "55": [0, 0.65556, 0, 0, 0.5], + "56": [0, 0.65556, 0, 0, 0.5], + "57": [0, 0.65556, 0, 0, 0.5], + "58": [0, 0.44444, 0, 0, 0.27778], + "59": [0.125, 0.44444, 0, 0, 0.27778], + "61": [-0.13, 0.37, 0, 0, 0.77778], + "63": [0, 0.69444, 0, 0, 0.47222], + "64": [0, 0.69444, 0, 0, 0.66667], + "65": [0, 0.69444, 0, 0, 0.66667], + "66": [0, 0.69444, 0, 0, 0.66667], + "67": [0, 0.69444, 0, 0, 0.63889], + "68": [0, 0.69444, 0, 0, 0.72223], + "69": [0, 0.69444, 0, 0, 0.59722], + "70": [0, 0.69444, 0, 0, 0.56945], + "71": [0, 0.69444, 0, 0, 0.66667], + "72": [0, 0.69444, 0, 0, 0.70834], + "73": [0, 0.69444, 0, 0, 0.27778], + "74": [0, 0.69444, 0, 0, 0.47222], + "75": [0, 0.69444, 0, 0, 0.69445], + "76": [0, 0.69444, 0, 0, 0.54167], + "77": [0, 0.69444, 0, 0, 0.875], + "78": [0, 0.69444, 0, 0, 0.70834], + "79": [0, 0.69444, 0, 0, 0.73611], + "80": [0, 0.69444, 0, 0, 0.63889], + "81": [0.125, 0.69444, 0, 0, 0.73611], + "82": [0, 0.69444, 0, 0, 0.64584], + "83": [0, 0.69444, 0, 0, 0.55556], + "84": [0, 0.69444, 0, 0, 0.68056], + "85": [0, 0.69444, 0, 0, 0.6875], + "86": [0, 0.69444, 0.01389, 0, 0.66667], + "87": [0, 0.69444, 0.01389, 0, 0.94445], + "88": [0, 0.69444, 0, 0, 0.66667], + "89": [0, 0.69444, 0.025, 0, 0.66667], + "90": [0, 0.69444, 0, 0, 0.61111], + "91": [0.25, 0.75, 0, 0, 0.28889], + "93": [0.25, 0.75, 0, 0, 0.28889], + "94": [0, 0.69444, 0, 0, 0.5], + "95": [0.35, 0.09444, 0.02778, 0, 0.5], + "97": [0, 0.44444, 0, 0, 0.48056], + "98": [0, 0.69444, 0, 0, 0.51667], + "99": [0, 0.44444, 0, 0, 0.44445], + "100": [0, 0.69444, 0, 0, 0.51667], + "101": [0, 0.44444, 0, 0, 0.44445], + "102": [0, 0.69444, 0.06944, 0, 0.30556], + "103": [0.19444, 0.44444, 0.01389, 0, 0.5], + "104": [0, 0.69444, 0, 0, 0.51667], + "105": [0, 0.67937, 0, 0, 0.23889], + "106": [0.19444, 0.67937, 0, 0, 0.26667], + "107": [0, 0.69444, 0, 0, 0.48889], + "108": [0, 0.69444, 0, 0, 0.23889], + "109": [0, 0.44444, 0, 0, 0.79445], + "110": [0, 0.44444, 0, 0, 0.51667], + "111": [0, 0.44444, 0, 0, 0.5], + "112": [0.19444, 0.44444, 0, 0, 0.51667], + "113": [0.19444, 0.44444, 0, 0, 0.51667], + "114": [0, 0.44444, 0.01389, 0, 0.34167], + "115": [0, 0.44444, 0, 0, 0.38333], + "116": [0, 0.57143, 0, 0, 0.36111], + "117": [0, 0.44444, 0, 0, 0.51667], + "118": [0, 0.44444, 0.01389, 0, 0.46111], + "119": [0, 0.44444, 0.01389, 0, 0.68334], + "120": [0, 0.44444, 0, 0, 0.46111], + "121": [0.19444, 0.44444, 0.01389, 0, 0.46111], + "122": [0, 0.44444, 0, 0, 0.43472], + "126": [0.35, 0.32659, 0, 0, 0.5], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.67937, 0, 0, 0.5], + "176": [0, 0.69444, 0, 0, 0.66667], + "184": [0.17014, 0, 0, 0, 0.44445], + "305": [0, 0.44444, 0, 0, 0.23889], + "567": [0.19444, 0.44444, 0, 0, 0.26667], + "710": [0, 0.69444, 0, 0, 0.5], + "711": [0, 0.63194, 0, 0, 0.5], + "713": [0, 0.60889, 0, 0, 0.5], + "714": [0, 0.69444, 0, 0, 0.5], + "715": [0, 0.69444, 0, 0, 0.5], + "728": [0, 0.69444, 0, 0, 0.5], + "729": [0, 0.67937, 0, 0, 0.27778], + "730": [0, 0.69444, 0, 0, 0.66667], + "732": [0, 0.67659, 0, 0, 0.5], + "733": [0, 0.69444, 0, 0, 0.5], + "915": [0, 0.69444, 0, 0, 0.54167], + "916": [0, 0.69444, 0, 0, 0.83334], + "920": [0, 0.69444, 0, 0, 0.77778], + "923": [0, 0.69444, 0, 0, 0.61111], + "926": [0, 0.69444, 0, 0, 0.66667], + "928": [0, 0.69444, 0, 0, 0.70834], + "931": [0, 0.69444, 0, 0, 0.72222], + "933": [0, 0.69444, 0, 0, 0.77778], + "934": [0, 0.69444, 0, 0, 0.72222], + "936": [0, 0.69444, 0, 0, 0.77778], + "937": [0, 0.69444, 0, 0, 0.72222], + "8211": [0, 0.44444, 0.02778, 0, 0.5], + "8212": [0, 0.44444, 0.02778, 0, 1.0], + "8216": [0, 0.69444, 0, 0, 0.27778], + "8217": [0, 0.69444, 0, 0, 0.27778], + "8220": [0, 0.69444, 0, 0, 0.5], + "8221": [0, 0.69444, 0, 0, 0.5] + }, + "Script-Regular": { + "32": [0, 0, 0, 0, 0.25], + "65": [0, 0.7, 0.22925, 0, 0.80253], + "66": [0, 0.7, 0.04087, 0, 0.90757], + "67": [0, 0.7, 0.1689, 0, 0.66619], + "68": [0, 0.7, 0.09371, 0, 0.77443], + "69": [0, 0.7, 0.18583, 0, 0.56162], + "70": [0, 0.7, 0.13634, 0, 0.89544], + "71": [0, 0.7, 0.17322, 0, 0.60961], + "72": [0, 0.7, 0.29694, 0, 0.96919], + "73": [0, 0.7, 0.19189, 0, 0.80907], + "74": [0.27778, 0.7, 0.19189, 0, 1.05159], + "75": [0, 0.7, 0.31259, 0, 0.91364], + "76": [0, 0.7, 0.19189, 0, 0.87373], + "77": [0, 0.7, 0.15981, 0, 1.08031], + "78": [0, 0.7, 0.3525, 0, 0.9015], + "79": [0, 0.7, 0.08078, 0, 0.73787], + "80": [0, 0.7, 0.08078, 0, 1.01262], + "81": [0, 0.7, 0.03305, 0, 0.88282], + "82": [0, 0.7, 0.06259, 0, 0.85], + "83": [0, 0.7, 0.19189, 0, 0.86767], + "84": [0, 0.7, 0.29087, 0, 0.74697], + "85": [0, 0.7, 0.25815, 0, 0.79996], + "86": [0, 0.7, 0.27523, 0, 0.62204], + "87": [0, 0.7, 0.27523, 0, 0.80532], + "88": [0, 0.7, 0.26006, 0, 0.94445], + "89": [0, 0.7, 0.2939, 0, 0.70961], + "90": [0, 0.7, 0.24037, 0, 0.8212], + "160": [0, 0, 0, 0, 0.25] + }, + "Size1-Regular": { + "32": [0, 0, 0, 0, 0.25], + "40": [0.35001, 0.85, 0, 0, 0.45834], + "41": [0.35001, 0.85, 0, 0, 0.45834], + "47": [0.35001, 0.85, 0, 0, 0.57778], + "91": [0.35001, 0.85, 0, 0, 0.41667], + "92": [0.35001, 0.85, 0, 0, 0.57778], + "93": [0.35001, 0.85, 0, 0, 0.41667], + "123": [0.35001, 0.85, 0, 0, 0.58334], + "125": [0.35001, 0.85, 0, 0, 0.58334], + "160": [0, 0, 0, 0, 0.25], + "710": [0, 0.72222, 0, 0, 0.55556], + "732": [0, 0.72222, 0, 0, 0.55556], + "770": [0, 0.72222, 0, 0, 0.55556], + "771": [0, 0.72222, 0, 0, 0.55556], + "8214": [-0.00099, 0.601, 0, 0, 0.77778], + "8593": [1e-05, 0.6, 0, 0, 0.66667], + "8595": [1e-05, 0.6, 0, 0, 0.66667], + "8657": [1e-05, 0.6, 0, 0, 0.77778], + "8659": [1e-05, 0.6, 0, 0, 0.77778], + "8719": [0.25001, 0.75, 0, 0, 0.94445], + "8720": [0.25001, 0.75, 0, 0, 0.94445], + "8721": [0.25001, 0.75, 0, 0, 1.05556], + "8730": [0.35001, 0.85, 0, 0, 1.0], + "8739": [-0.00599, 0.606, 0, 0, 0.33333], + "8741": [-0.00599, 0.606, 0, 0, 0.55556], + "8747": [0.30612, 0.805, 0.19445, 0, 0.47222], + "8748": [0.306, 0.805, 0.19445, 0, 0.47222], + "8749": [0.306, 0.805, 0.19445, 0, 0.47222], + "8750": [0.30612, 0.805, 0.19445, 0, 0.47222], + "8896": [0.25001, 0.75, 0, 0, 0.83334], + "8897": [0.25001, 0.75, 0, 0, 0.83334], + "8898": [0.25001, 0.75, 0, 0, 0.83334], + "8899": [0.25001, 0.75, 0, 0, 0.83334], + "8968": [0.35001, 0.85, 0, 0, 0.47222], + "8969": [0.35001, 0.85, 0, 0, 0.47222], + "8970": [0.35001, 0.85, 0, 0, 0.47222], + "8971": [0.35001, 0.85, 0, 0, 0.47222], + "9168": [-0.00099, 0.601, 0, 0, 0.66667], + "10216": [0.35001, 0.85, 0, 0, 0.47222], + "10217": [0.35001, 0.85, 0, 0, 0.47222], + "10752": [0.25001, 0.75, 0, 0, 1.11111], + "10753": [0.25001, 0.75, 0, 0, 1.11111], + "10754": [0.25001, 0.75, 0, 0, 1.11111], + "10756": [0.25001, 0.75, 0, 0, 0.83334], + "10758": [0.25001, 0.75, 0, 0, 0.83334] + }, + "Size2-Regular": { + "32": [0, 0, 0, 0, 0.25], + "40": [0.65002, 1.15, 0, 0, 0.59722], + "41": [0.65002, 1.15, 0, 0, 0.59722], + "47": [0.65002, 1.15, 0, 0, 0.81111], + "91": [0.65002, 1.15, 0, 0, 0.47222], + "92": [0.65002, 1.15, 0, 0, 0.81111], + "93": [0.65002, 1.15, 0, 0, 0.47222], + "123": [0.65002, 1.15, 0, 0, 0.66667], + "125": [0.65002, 1.15, 0, 0, 0.66667], + "160": [0, 0, 0, 0, 0.25], + "710": [0, 0.75, 0, 0, 1.0], + "732": [0, 0.75, 0, 0, 1.0], + "770": [0, 0.75, 0, 0, 1.0], + "771": [0, 0.75, 0, 0, 1.0], + "8719": [0.55001, 1.05, 0, 0, 1.27778], + "8720": [0.55001, 1.05, 0, 0, 1.27778], + "8721": [0.55001, 1.05, 0, 0, 1.44445], + "8730": [0.65002, 1.15, 0, 0, 1.0], + "8747": [0.86225, 1.36, 0.44445, 0, 0.55556], + "8748": [0.862, 1.36, 0.44445, 0, 0.55556], + "8749": [0.862, 1.36, 0.44445, 0, 0.55556], + "8750": [0.86225, 1.36, 0.44445, 0, 0.55556], + "8896": [0.55001, 1.05, 0, 0, 1.11111], + "8897": [0.55001, 1.05, 0, 0, 1.11111], + "8898": [0.55001, 1.05, 0, 0, 1.11111], + "8899": [0.55001, 1.05, 0, 0, 1.11111], + "8968": [0.65002, 1.15, 0, 0, 0.52778], + "8969": [0.65002, 1.15, 0, 0, 0.52778], + "8970": [0.65002, 1.15, 0, 0, 0.52778], + "8971": [0.65002, 1.15, 0, 0, 0.52778], + "10216": [0.65002, 1.15, 0, 0, 0.61111], + "10217": [0.65002, 1.15, 0, 0, 0.61111], + "10752": [0.55001, 1.05, 0, 0, 1.51112], + "10753": [0.55001, 1.05, 0, 0, 1.51112], + "10754": [0.55001, 1.05, 0, 0, 1.51112], + "10756": [0.55001, 1.05, 0, 0, 1.11111], + "10758": [0.55001, 1.05, 0, 0, 1.11111] + }, + "Size3-Regular": { + "32": [0, 0, 0, 0, 0.25], + "40": [0.95003, 1.45, 0, 0, 0.73611], + "41": [0.95003, 1.45, 0, 0, 0.73611], + "47": [0.95003, 1.45, 0, 0, 1.04445], + "91": [0.95003, 1.45, 0, 0, 0.52778], + "92": [0.95003, 1.45, 0, 0, 1.04445], + "93": [0.95003, 1.45, 0, 0, 0.52778], + "123": [0.95003, 1.45, 0, 0, 0.75], + "125": [0.95003, 1.45, 0, 0, 0.75], + "160": [0, 0, 0, 0, 0.25], + "710": [0, 0.75, 0, 0, 1.44445], + "732": [0, 0.75, 0, 0, 1.44445], + "770": [0, 0.75, 0, 0, 1.44445], + "771": [0, 0.75, 0, 0, 1.44445], + "8730": [0.95003, 1.45, 0, 0, 1.0], + "8968": [0.95003, 1.45, 0, 0, 0.58334], + "8969": [0.95003, 1.45, 0, 0, 0.58334], + "8970": [0.95003, 1.45, 0, 0, 0.58334], + "8971": [0.95003, 1.45, 0, 0, 0.58334], + "10216": [0.95003, 1.45, 0, 0, 0.75], + "10217": [0.95003, 1.45, 0, 0, 0.75] + }, + "Size4-Regular": { + "32": [0, 0, 0, 0, 0.25], + "40": [1.25003, 1.75, 0, 0, 0.79167], + "41": [1.25003, 1.75, 0, 0, 0.79167], + "47": [1.25003, 1.75, 0, 0, 1.27778], + "91": [1.25003, 1.75, 0, 0, 0.58334], + "92": [1.25003, 1.75, 0, 0, 1.27778], + "93": [1.25003, 1.75, 0, 0, 0.58334], + "123": [1.25003, 1.75, 0, 0, 0.80556], + "125": [1.25003, 1.75, 0, 0, 0.80556], + "160": [0, 0, 0, 0, 0.25], + "710": [0, 0.825, 0, 0, 1.8889], + "732": [0, 0.825, 0, 0, 1.8889], + "770": [0, 0.825, 0, 0, 1.8889], + "771": [0, 0.825, 0, 0, 1.8889], + "8730": [1.25003, 1.75, 0, 0, 1.0], + "8968": [1.25003, 1.75, 0, 0, 0.63889], + "8969": [1.25003, 1.75, 0, 0, 0.63889], + "8970": [1.25003, 1.75, 0, 0, 0.63889], + "8971": [1.25003, 1.75, 0, 0, 0.63889], + "9115": [0.64502, 1.155, 0, 0, 0.875], + "9116": [1e-05, 0.6, 0, 0, 0.875], + "9117": [0.64502, 1.155, 0, 0, 0.875], + "9118": [0.64502, 1.155, 0, 0, 0.875], + "9119": [1e-05, 0.6, 0, 0, 0.875], + "9120": [0.64502, 1.155, 0, 0, 0.875], + "9121": [0.64502, 1.155, 0, 0, 0.66667], + "9122": [-0.00099, 0.601, 0, 0, 0.66667], + "9123": [0.64502, 1.155, 0, 0, 0.66667], + "9124": [0.64502, 1.155, 0, 0, 0.66667], + "9125": [-0.00099, 0.601, 0, 0, 0.66667], + "9126": [0.64502, 1.155, 0, 0, 0.66667], + "9127": [1e-05, 0.9, 0, 0, 0.88889], + "9128": [0.65002, 1.15, 0, 0, 0.88889], + "9129": [0.90001, 0, 0, 0, 0.88889], + "9130": [0, 0.3, 0, 0, 0.88889], + "9131": [1e-05, 0.9, 0, 0, 0.88889], + "9132": [0.65002, 1.15, 0, 0, 0.88889], + "9133": [0.90001, 0, 0, 0, 0.88889], + "9143": [0.88502, 0.915, 0, 0, 1.05556], + "10216": [1.25003, 1.75, 0, 0, 0.80556], + "10217": [1.25003, 1.75, 0, 0, 0.80556], + "57344": [-0.00499, 0.605, 0, 0, 1.05556], + "57345": [-0.00499, 0.605, 0, 0, 1.05556], + "57680": [0, 0.12, 0, 0, 0.45], + "57681": [0, 0.12, 0, 0, 0.45], + "57682": [0, 0.12, 0, 0, 0.45], + "57683": [0, 0.12, 0, 0, 0.45] + }, + "Typewriter-Regular": { + "32": [0, 0, 0, 0, 0.525], + "33": [0, 0.61111, 0, 0, 0.525], + "34": [0, 0.61111, 0, 0, 0.525], + "35": [0, 0.61111, 0, 0, 0.525], + "36": [0.08333, 0.69444, 0, 0, 0.525], + "37": [0.08333, 0.69444, 0, 0, 0.525], + "38": [0, 0.61111, 0, 0, 0.525], + "39": [0, 0.61111, 0, 0, 0.525], + "40": [0.08333, 0.69444, 0, 0, 0.525], + "41": [0.08333, 0.69444, 0, 0, 0.525], + "42": [0, 0.52083, 0, 0, 0.525], + "43": [-0.08056, 0.53055, 0, 0, 0.525], + "44": [0.13889, 0.125, 0, 0, 0.525], + "45": [-0.08056, 0.53055, 0, 0, 0.525], + "46": [0, 0.125, 0, 0, 0.525], + "47": [0.08333, 0.69444, 0, 0, 0.525], + "48": [0, 0.61111, 0, 0, 0.525], + "49": [0, 0.61111, 0, 0, 0.525], + "50": [0, 0.61111, 0, 0, 0.525], + "51": [0, 0.61111, 0, 0, 0.525], + "52": [0, 0.61111, 0, 0, 0.525], + "53": [0, 0.61111, 0, 0, 0.525], + "54": [0, 0.61111, 0, 0, 0.525], + "55": [0, 0.61111, 0, 0, 0.525], + "56": [0, 0.61111, 0, 0, 0.525], + "57": [0, 0.61111, 0, 0, 0.525], + "58": [0, 0.43056, 0, 0, 0.525], + "59": [0.13889, 0.43056, 0, 0, 0.525], + "60": [-0.05556, 0.55556, 0, 0, 0.525], + "61": [-0.19549, 0.41562, 0, 0, 0.525], + "62": [-0.05556, 0.55556, 0, 0, 0.525], + "63": [0, 0.61111, 0, 0, 0.525], + "64": [0, 0.61111, 0, 0, 0.525], + "65": [0, 0.61111, 0, 0, 0.525], + "66": [0, 0.61111, 0, 0, 0.525], + "67": [0, 0.61111, 0, 0, 0.525], + "68": [0, 0.61111, 0, 0, 0.525], + "69": [0, 0.61111, 0, 0, 0.525], + "70": [0, 0.61111, 0, 0, 0.525], + "71": [0, 0.61111, 0, 0, 0.525], + "72": [0, 0.61111, 0, 0, 0.525], + "73": [0, 0.61111, 0, 0, 0.525], + "74": [0, 0.61111, 0, 0, 0.525], + "75": [0, 0.61111, 0, 0, 0.525], + "76": [0, 0.61111, 0, 0, 0.525], + "77": [0, 0.61111, 0, 0, 0.525], + "78": [0, 0.61111, 0, 0, 0.525], + "79": [0, 0.61111, 0, 0, 0.525], + "80": [0, 0.61111, 0, 0, 0.525], + "81": [0.13889, 0.61111, 0, 0, 0.525], + "82": [0, 0.61111, 0, 0, 0.525], + "83": [0, 0.61111, 0, 0, 0.525], + "84": [0, 0.61111, 0, 0, 0.525], + "85": [0, 0.61111, 0, 0, 0.525], + "86": [0, 0.61111, 0, 0, 0.525], + "87": [0, 0.61111, 0, 0, 0.525], + "88": [0, 0.61111, 0, 0, 0.525], + "89": [0, 0.61111, 0, 0, 0.525], + "90": [0, 0.61111, 0, 0, 0.525], + "91": [0.08333, 0.69444, 0, 0, 0.525], + "92": [0.08333, 0.69444, 0, 0, 0.525], + "93": [0.08333, 0.69444, 0, 0, 0.525], + "94": [0, 0.61111, 0, 0, 0.525], + "95": [0.09514, 0, 0, 0, 0.525], + "96": [0, 0.61111, 0, 0, 0.525], + "97": [0, 0.43056, 0, 0, 0.525], + "98": [0, 0.61111, 0, 0, 0.525], + "99": [0, 0.43056, 0, 0, 0.525], + "100": [0, 0.61111, 0, 0, 0.525], + "101": [0, 0.43056, 0, 0, 0.525], + "102": [0, 0.61111, 0, 0, 0.525], + "103": [0.22222, 0.43056, 0, 0, 0.525], + "104": [0, 0.61111, 0, 0, 0.525], + "105": [0, 0.61111, 0, 0, 0.525], + "106": [0.22222, 0.61111, 0, 0, 0.525], + "107": [0, 0.61111, 0, 0, 0.525], + "108": [0, 0.61111, 0, 0, 0.525], + "109": [0, 0.43056, 0, 0, 0.525], + "110": [0, 0.43056, 0, 0, 0.525], + "111": [0, 0.43056, 0, 0, 0.525], + "112": [0.22222, 0.43056, 0, 0, 0.525], + "113": [0.22222, 0.43056, 0, 0, 0.525], + "114": [0, 0.43056, 0, 0, 0.525], + "115": [0, 0.43056, 0, 0, 0.525], + "116": [0, 0.55358, 0, 0, 0.525], + "117": [0, 0.43056, 0, 0, 0.525], + "118": [0, 0.43056, 0, 0, 0.525], + "119": [0, 0.43056, 0, 0, 0.525], + "120": [0, 0.43056, 0, 0, 0.525], + "121": [0.22222, 0.43056, 0, 0, 0.525], + "122": [0, 0.43056, 0, 0, 0.525], + "123": [0.08333, 0.69444, 0, 0, 0.525], + "124": [0.08333, 0.69444, 0, 0, 0.525], + "125": [0.08333, 0.69444, 0, 0, 0.525], + "126": [0, 0.61111, 0, 0, 0.525], + "127": [0, 0.61111, 0, 0, 0.525], + "160": [0, 0, 0, 0, 0.525], + "176": [0, 0.61111, 0, 0, 0.525], + "184": [0.19445, 0, 0, 0, 0.525], + "305": [0, 0.43056, 0, 0, 0.525], + "567": [0.22222, 0.43056, 0, 0, 0.525], + "711": [0, 0.56597, 0, 0, 0.525], + "713": [0, 0.56555, 0, 0, 0.525], + "714": [0, 0.61111, 0, 0, 0.525], + "715": [0, 0.61111, 0, 0, 0.525], + "728": [0, 0.61111, 0, 0, 0.525], + "730": [0, 0.61111, 0, 0, 0.525], + "770": [0, 0.61111, 0, 0, 0.525], + "771": [0, 0.61111, 0, 0, 0.525], + "776": [0, 0.61111, 0, 0, 0.525], + "915": [0, 0.61111, 0, 0, 0.525], + "916": [0, 0.61111, 0, 0, 0.525], + "920": [0, 0.61111, 0, 0, 0.525], + "923": [0, 0.61111, 0, 0, 0.525], + "926": [0, 0.61111, 0, 0, 0.525], + "928": [0, 0.61111, 0, 0, 0.525], + "931": [0, 0.61111, 0, 0, 0.525], + "933": [0, 0.61111, 0, 0, 0.525], + "934": [0, 0.61111, 0, 0, 0.525], + "936": [0, 0.61111, 0, 0, 0.525], + "937": [0, 0.61111, 0, 0, 0.525], + "8216": [0, 0.61111, 0, 0, 0.525], + "8217": [0, 0.61111, 0, 0, 0.525], + "8242": [0, 0.61111, 0, 0, 0.525], + "9251": [0.11111, 0.21944, 0, 0, 0.525] + } +}); +;// CONCATENATED MODULE: ./src/fontMetrics.js + + +/** + * This file contains metrics regarding fonts and individual symbols. The sigma + * and xi variables, as well as the metricMap map contain data extracted from + * TeX, TeX font metrics, and the TTF files. These data are then exposed via the + * `metrics` variable and the getCharacterMetrics function. + */ +// In TeX, there are actually three sets of dimensions, one for each of +// textstyle (size index 5 and higher: >=9pt), scriptstyle (size index 3 and 4: +// 7-8pt), and scriptscriptstyle (size index 1 and 2: 5-6pt). These are +// provided in the arrays below, in that order. +// +// The font metrics are stored in fonts cmsy10, cmsy7, and cmsy5 respectively. +// This was determined by running the following script: +// +// latex -interaction=nonstopmode \ +// '\documentclass{article}\usepackage{amsmath}\begin{document}' \ +// '$a$ \expandafter\show\the\textfont2' \ +// '\expandafter\show\the\scriptfont2' \ +// '\expandafter\show\the\scriptscriptfont2' \ +// '\stop' +// +// The metrics themselves were retrieved using the following commands: +// +// tftopl cmsy10 +// tftopl cmsy7 +// tftopl cmsy5 +// +// The output of each of these commands is quite lengthy. The only part we +// care about is the FONTDIMEN section. Each value is measured in EMs. +const sigmasAndXis = { + slant: [0.250, 0.250, 0.250], + // sigma1 + space: [0.000, 0.000, 0.000], + // sigma2 + stretch: [0.000, 0.000, 0.000], + // sigma3 + shrink: [0.000, 0.000, 0.000], + // sigma4 + xHeight: [0.431, 0.431, 0.431], + // sigma5 + quad: [1.000, 1.171, 1.472], + // sigma6 + extraSpace: [0.000, 0.000, 0.000], + // sigma7 + num1: [0.677, 0.732, 0.925], + // sigma8 + num2: [0.394, 0.384, 0.387], + // sigma9 + num3: [0.444, 0.471, 0.504], + // sigma10 + denom1: [0.686, 0.752, 1.025], + // sigma11 + denom2: [0.345, 0.344, 0.532], + // sigma12 + sup1: [0.413, 0.503, 0.504], + // sigma13 + sup2: [0.363, 0.431, 0.404], + // sigma14 + sup3: [0.289, 0.286, 0.294], + // sigma15 + sub1: [0.150, 0.143, 0.200], + // sigma16 + sub2: [0.247, 0.286, 0.400], + // sigma17 + supDrop: [0.386, 0.353, 0.494], + // sigma18 + subDrop: [0.050, 0.071, 0.100], + // sigma19 + delim1: [2.390, 1.700, 1.980], + // sigma20 + delim2: [1.010, 1.157, 1.420], + // sigma21 + axisHeight: [0.250, 0.250, 0.250], + // sigma22 + // These font metrics are extracted from TeX by using tftopl on cmex10.tfm; + // they correspond to the font parameters of the extension fonts (family 3). + // See the TeXbook, page 441. In AMSTeX, the extension fonts scale; to + // match cmex7, we'd use cmex7.tfm values for script and scriptscript + // values. + defaultRuleThickness: [0.04, 0.049, 0.049], + // xi8; cmex7: 0.049 + bigOpSpacing1: [0.111, 0.111, 0.111], + // xi9 + bigOpSpacing2: [0.166, 0.166, 0.166], + // xi10 + bigOpSpacing3: [0.2, 0.2, 0.2], + // xi11 + bigOpSpacing4: [0.6, 0.611, 0.611], + // xi12; cmex7: 0.611 + bigOpSpacing5: [0.1, 0.143, 0.143], + // xi13; cmex7: 0.143 + // The \sqrt rule width is taken from the height of the surd character. + // Since we use the same font at all sizes, this thickness doesn't scale. + sqrtRuleThickness: [0.04, 0.04, 0.04], + // This value determines how large a pt is, for metrics which are defined + // in terms of pts. + // This value is also used in katex.scss; if you change it make sure the + // values match. + ptPerEm: [10.0, 10.0, 10.0], + // The space between adjacent `|` columns in an array definition. From + // `\showthe\doublerulesep` in LaTeX. Equals 2.0 / ptPerEm. + doubleRuleSep: [0.2, 0.2, 0.2], + // The width of separator lines in {array} environments. From + // `\showthe\arrayrulewidth` in LaTeX. Equals 0.4 / ptPerEm. + arrayRuleWidth: [0.04, 0.04, 0.04], + // Two values from LaTeX source2e: + fboxsep: [0.3, 0.3, 0.3], + // 3 pt / ptPerEm + fboxrule: [0.04, 0.04, 0.04] // 0.4 pt / ptPerEm + +}; // This map contains a mapping from font name and character code to character +// metrics, including height, depth, italic correction, and skew (kern from the +// character to the corresponding \skewchar) +// This map is generated via `make metrics`. It should not be changed manually. + + // These are very rough approximations. We default to Times New Roman which +// should have Latin-1 and Cyrillic characters, but may not depending on the +// operating system. The metrics do not account for extra height from the +// accents. In the case of Cyrillic characters which have both ascenders and +// descenders we prefer approximations with ascenders, primarily to prevent +// the fraction bar or root line from intersecting the glyph. +// TODO(kevinb) allow union of multiple glyph metrics for better accuracy. + +const extraCharacterMap = { + // Latin-1 + 'Å': 'A', + 'Ð': 'D', + 'Þ': 'o', + 'å': 'a', + 'ð': 'd', + 'þ': 'o', + // Cyrillic + 'А': 'A', + 'Б': 'B', + 'В': 'B', + 'Г': 'F', + 'Д': 'A', + 'Е': 'E', + 'Ж': 'K', + 'З': '3', + 'И': 'N', + 'Й': 'N', + 'К': 'K', + 'Л': 'N', + 'М': 'M', + 'Н': 'H', + 'О': 'O', + 'П': 'N', + 'Р': 'P', + 'С': 'C', + 'Т': 'T', + 'У': 'y', + 'Ф': 'O', + 'Х': 'X', + 'Ц': 'U', + 'Ч': 'h', + 'Ш': 'W', + 'Щ': 'W', + 'Ъ': 'B', + 'Ы': 'X', + 'Ь': 'B', + 'Э': '3', + 'Ю': 'X', + 'Я': 'R', + 'а': 'a', + 'б': 'b', + 'в': 'a', + 'г': 'r', + 'д': 'y', + 'е': 'e', + 'ж': 'm', + 'з': 'e', + 'и': 'n', + 'й': 'n', + 'к': 'n', + 'л': 'n', + 'м': 'm', + 'н': 'n', + 'о': 'o', + 'п': 'n', + 'р': 'p', + 'с': 'c', + 'т': 'o', + 'у': 'y', + 'ф': 'b', + 'х': 'x', + 'ц': 'n', + 'ч': 'n', + 'ш': 'w', + 'щ': 'w', + 'ъ': 'a', + 'ы': 'm', + 'ь': 'a', + 'э': 'e', + 'ю': 'm', + 'я': 'r' +}; + +/** + * This function adds new font metrics to default metricMap + * It can also override existing metrics + */ +function setFontMetrics(fontName, metrics) { + fontMetricsData[fontName] = metrics; +} +/** + * This function is a convenience function for looking up information in the + * metricMap table. It takes a character as a string, and a font. + * + * Note: the `width` property may be undefined if fontMetricsData.js wasn't + * built using `Make extended_metrics`. + */ + +function getCharacterMetrics(character, font, mode) { + if (!fontMetricsData[font]) { + throw new Error("Font metrics not found for font: " + font + "."); + } + + let ch = character.charCodeAt(0); + let metrics = fontMetricsData[font][ch]; + + if (!metrics && character[0] in extraCharacterMap) { + ch = extraCharacterMap[character[0]].charCodeAt(0); + metrics = fontMetricsData[font][ch]; + } + + if (!metrics && mode === 'text') { + // We don't typically have font metrics for Asian scripts. + // But since we support them in text mode, we need to return + // some sort of metrics. + // So if the character is in a script we support but we + // don't have metrics for it, just use the metrics for + // the Latin capital letter M. This is close enough because + // we (currently) only care about the height of the glyph + // not its width. + if (supportedCodepoint(ch)) { + metrics = fontMetricsData[font][77]; // 77 is the charcode for 'M' + } + } + + if (metrics) { + return { + depth: metrics[0], + height: metrics[1], + italic: metrics[2], + skew: metrics[3], + width: metrics[4] + }; + } +} +const fontMetricsBySizeIndex = {}; +/** + * Get the font metrics for a given size. + */ + +function getGlobalMetrics(size) { + let sizeIndex; + + if (size >= 5) { + sizeIndex = 0; + } else if (size >= 3) { + sizeIndex = 1; + } else { + sizeIndex = 2; + } + + if (!fontMetricsBySizeIndex[sizeIndex]) { + const metrics = fontMetricsBySizeIndex[sizeIndex] = { + cssEmPerMu: sigmasAndXis.quad[sizeIndex] / 18 + }; + + for (const key in sigmasAndXis) { + if (sigmasAndXis.hasOwnProperty(key)) { + metrics[key] = sigmasAndXis[key][sizeIndex]; + } + } + } + + return fontMetricsBySizeIndex[sizeIndex]; +} +;// CONCATENATED MODULE: ./src/Options.js +/** + * This file contains information about the options that the Parser carries + * around with it while parsing. Data is held in an `Options` object, and when + * recursing, a new `Options` object can be created with the `.with*` and + * `.reset` functions. + */ + +const sizeStyleMap = [// Each element contains [textsize, scriptsize, scriptscriptsize]. +// The size mappings are taken from TeX with \normalsize=10pt. +[1, 1, 1], // size1: [5, 5, 5] \tiny +[2, 1, 1], // size2: [6, 5, 5] +[3, 1, 1], // size3: [7, 5, 5] \scriptsize +[4, 2, 1], // size4: [8, 6, 5] \footnotesize +[5, 2, 1], // size5: [9, 6, 5] \small +[6, 3, 1], // size6: [10, 7, 5] \normalsize +[7, 4, 2], // size7: [12, 8, 6] \large +[8, 6, 3], // size8: [14.4, 10, 7] \Large +[9, 7, 6], // size9: [17.28, 12, 10] \LARGE +[10, 8, 7], // size10: [20.74, 14.4, 12] \huge +[11, 10, 9] // size11: [24.88, 20.74, 17.28] \HUGE +]; +const sizeMultipliers = [// fontMetrics.js:getGlobalMetrics also uses size indexes, so if +// you change size indexes, change that function. +0.5, 0.6, 0.7, 0.8, 0.9, 1.0, 1.2, 1.44, 1.728, 2.074, 2.488]; + +const sizeAtStyle = function (size, style) { + return style.size < 2 ? size : sizeStyleMap[size - 1][style.size - 1]; +}; // In these types, "" (empty string) means "no change". + + +/** + * This is the main options class. It contains the current style, size, color, + * and font. + * + * Options objects should not be modified. To create a new Options with + * different properties, call a `.having*` method. + */ +class Options { + // A font family applies to a group of fonts (i.e. SansSerif), while a font + // represents a specific font (i.e. SansSerif Bold). + // See: https://tex.stackexchange.com/questions/22350/difference-between-textrm-and-mathrm + + /** + * The base size index. + */ + constructor(data) { + this.style = void 0; + this.color = void 0; + this.size = void 0; + this.textSize = void 0; + this.phantom = void 0; + this.font = void 0; + this.fontFamily = void 0; + this.fontWeight = void 0; + this.fontShape = void 0; + this.sizeMultiplier = void 0; + this.maxSize = void 0; + this.minRuleThickness = void 0; + this._fontMetrics = void 0; + this.style = data.style; + this.color = data.color; + this.size = data.size || Options.BASESIZE; + this.textSize = data.textSize || this.size; + this.phantom = !!data.phantom; + this.font = data.font || ""; + this.fontFamily = data.fontFamily || ""; + this.fontWeight = data.fontWeight || ''; + this.fontShape = data.fontShape || ''; + this.sizeMultiplier = sizeMultipliers[this.size - 1]; + this.maxSize = data.maxSize; + this.minRuleThickness = data.minRuleThickness; + this._fontMetrics = undefined; + } + /** + * Returns a new options object with the same properties as "this". Properties + * from "extension" will be copied to the new options object. + */ + + + extend(extension) { + const data = { + style: this.style, + size: this.size, + textSize: this.textSize, + color: this.color, + phantom: this.phantom, + font: this.font, + fontFamily: this.fontFamily, + fontWeight: this.fontWeight, + fontShape: this.fontShape, + maxSize: this.maxSize, + minRuleThickness: this.minRuleThickness + }; + + for (const key in extension) { + if (extension.hasOwnProperty(key)) { + data[key] = extension[key]; + } + } + + return new Options(data); + } + /** + * Return an options object with the given style. If `this.style === style`, + * returns `this`. + */ + + + havingStyle(style) { + if (this.style === style) { + return this; + } else { + return this.extend({ + style: style, + size: sizeAtStyle(this.textSize, style) + }); + } + } + /** + * Return an options object with a cramped version of the current style. If + * the current style is cramped, returns `this`. + */ + + + havingCrampedStyle() { + return this.havingStyle(this.style.cramp()); + } + /** + * Return an options object with the given size and in at least `\textstyle`. + * Returns `this` if appropriate. + */ + + + havingSize(size) { + if (this.size === size && this.textSize === size) { + return this; + } else { + return this.extend({ + style: this.style.text(), + size: size, + textSize: size, + sizeMultiplier: sizeMultipliers[size - 1] + }); + } + } + /** + * Like `this.havingSize(BASESIZE).havingStyle(style)`. If `style` is omitted, + * changes to at least `\textstyle`. + */ + + + havingBaseStyle(style) { + style = style || this.style.text(); + const wantSize = sizeAtStyle(Options.BASESIZE, style); + + if (this.size === wantSize && this.textSize === Options.BASESIZE && this.style === style) { + return this; + } else { + return this.extend({ + style: style, + size: wantSize + }); + } + } + /** + * Remove the effect of sizing changes such as \Huge. + * Keep the effect of the current style, such as \scriptstyle. + */ + + + havingBaseSizing() { + let size; + + switch (this.style.id) { + case 4: + case 5: + size = 3; // normalsize in scriptstyle + + break; + + case 6: + case 7: + size = 1; // normalsize in scriptscriptstyle + + break; + + default: + size = 6; + // normalsize in textstyle or displaystyle + } + + return this.extend({ + style: this.style.text(), + size: size + }); + } + /** + * Create a new options object with the given color. + */ + + + withColor(color) { + return this.extend({ + color: color + }); + } + /** + * Create a new options object with "phantom" set to true. + */ + + + withPhantom() { + return this.extend({ + phantom: true + }); + } + /** + * Creates a new options object with the given math font or old text font. + * @type {[type]} + */ + + + withFont(font) { + return this.extend({ + font + }); + } + /** + * Create a new options objects with the given fontFamily. + */ + + + withTextFontFamily(fontFamily) { + return this.extend({ + fontFamily, + font: "" + }); + } + /** + * Creates a new options object with the given font weight + */ + + + withTextFontWeight(fontWeight) { + return this.extend({ + fontWeight, + font: "" + }); + } + /** + * Creates a new options object with the given font weight + */ + + + withTextFontShape(fontShape) { + return this.extend({ + fontShape, + font: "" + }); + } + /** + * Return the CSS sizing classes required to switch from enclosing options + * `oldOptions` to `this`. Returns an array of classes. + */ + + + sizingClasses(oldOptions) { + if (oldOptions.size !== this.size) { + return ["sizing", "reset-size" + oldOptions.size, "size" + this.size]; + } else { + return []; + } + } + /** + * Return the CSS sizing classes required to switch to the base size. Like + * `this.havingSize(BASESIZE).sizingClasses(this)`. + */ + + + baseSizingClasses() { + if (this.size !== Options.BASESIZE) { + return ["sizing", "reset-size" + this.size, "size" + Options.BASESIZE]; + } else { + return []; + } + } + /** + * Return the font metrics for this size. + */ + + + fontMetrics() { + if (!this._fontMetrics) { + this._fontMetrics = getGlobalMetrics(this.size); + } + + return this._fontMetrics; + } + /** + * Gets the CSS color of the current options object + */ + + + getColor() { + if (this.phantom) { + return "transparent"; + } else { + return this.color; + } + } + +} + +Options.BASESIZE = 6; +/* harmony default export */ var src_Options = (Options); +;// CONCATENATED MODULE: ./src/units.js +/** + * This file does conversion between units. In particular, it provides + * calculateSize to convert other units into ems. + */ + + // This table gives the number of TeX pts in one of each *absolute* TeX unit. +// Thus, multiplying a length by this number converts the length from units +// into pts. Dividing the result by ptPerEm gives the number of ems +// *assuming* a font size of ptPerEm (normal size, normal style). + +const ptPerUnit = { + // https://en.wikibooks.org/wiki/LaTeX/Lengths and + // https://tex.stackexchange.com/a/8263 + "pt": 1, + // TeX point + "mm": 7227 / 2540, + // millimeter + "cm": 7227 / 254, + // centimeter + "in": 72.27, + // inch + "bp": 803 / 800, + // big (PostScript) points + "pc": 12, + // pica + "dd": 1238 / 1157, + // didot + "cc": 14856 / 1157, + // cicero (12 didot) + "nd": 685 / 642, + // new didot + "nc": 1370 / 107, + // new cicero (12 new didot) + "sp": 1 / 65536, + // scaled point (TeX's internal smallest unit) + // https://tex.stackexchange.com/a/41371 + "px": 803 / 800 // \pdfpxdimen defaults to 1 bp in pdfTeX and LuaTeX + +}; // Dictionary of relative units, for fast validity testing. + +const relativeUnit = { + "ex": true, + "em": true, + "mu": true +}; + +/** + * Determine whether the specified unit (either a string defining the unit + * or a "size" parse node containing a unit field) is valid. + */ +const validUnit = function (unit) { + if (typeof unit !== "string") { + unit = unit.unit; + } + + return unit in ptPerUnit || unit in relativeUnit || unit === "ex"; +}; +/* + * Convert a "size" parse node (with numeric "number" and string "unit" fields, + * as parsed by functions.js argType "size") into a CSS em value for the + * current style/scale. `options` gives the current options. + */ + +const calculateSize = function (sizeValue, options) { + let scale; + + if (sizeValue.unit in ptPerUnit) { + // Absolute units + scale = ptPerUnit[sizeValue.unit] // Convert unit to pt + / options.fontMetrics().ptPerEm // Convert pt to CSS em + / options.sizeMultiplier; // Unscale to make absolute units + } else if (sizeValue.unit === "mu") { + // `mu` units scale with scriptstyle/scriptscriptstyle. + scale = options.fontMetrics().cssEmPerMu; + } else { + // Other relative units always refer to the *textstyle* font + // in the current size. + let unitOptions; + + if (options.style.isTight()) { + // isTight() means current style is script/scriptscript. + unitOptions = options.havingStyle(options.style.text()); + } else { + unitOptions = options; + } // TODO: In TeX these units are relative to the quad of the current + // *text* font, e.g. cmr10. KaTeX instead uses values from the + // comparably-sized *Computer Modern symbol* font. At 10pt, these + // match. At 7pt and 5pt, they differ: cmr7=1.138894, cmsy7=1.170641; + // cmr5=1.361133, cmsy5=1.472241. Consider $\scriptsize a\kern1emb$. + // TeX \showlists shows a kern of 1.13889 * fontsize; + // KaTeX shows a kern of 1.171 * fontsize. + + + if (sizeValue.unit === "ex") { + scale = unitOptions.fontMetrics().xHeight; + } else if (sizeValue.unit === "em") { + scale = unitOptions.fontMetrics().quad; + } else { + throw new src_ParseError("Invalid unit: '" + sizeValue.unit + "'"); + } + + if (unitOptions !== options) { + scale *= unitOptions.sizeMultiplier / options.sizeMultiplier; + } + } + + return Math.min(sizeValue.number * scale, options.maxSize); +}; +/** + * Round `n` to 4 decimal places, or to the nearest 1/10,000th em. See + * https://github.com/KaTeX/KaTeX/pull/2460. + */ + +const makeEm = function (n) { + return +n.toFixed(4) + "em"; +}; +;// CONCATENATED MODULE: ./src/domTree.js +/** + * These objects store the data about the DOM nodes we create, as well as some + * extra data. They can then be transformed into real DOM nodes with the + * `toNode` function or HTML markup using `toMarkup`. They are useful for both + * storing extra properties on the nodes, as well as providing a way to easily + * work with the DOM. + * + * Similar functions for working with MathML nodes exist in mathMLTree.js. + * + * TODO: refactor `span` and `anchor` into common superclass when + * target environments support class inheritance + */ + + + + + + + +/** + * Create an HTML className based on a list of classes. In addition to joining + * with spaces, we also remove empty classes. + */ +const createClass = function (classes) { + return classes.filter(cls => cls).join(" "); +}; + +const initNode = function (classes, options, style) { + this.classes = classes || []; + this.attributes = {}; + this.height = 0; + this.depth = 0; + this.maxFontSize = 0; + this.style = style || {}; + + if (options) { + if (options.style.isTight()) { + this.classes.push("mtight"); + } + + const color = options.getColor(); + + if (color) { + this.style.color = color; + } + } +}; +/** + * Convert into an HTML node + */ + + +const toNode = function (tagName) { + const node = document.createElement(tagName); // Apply the class + + node.className = createClass(this.classes); // Apply inline styles + + for (const style in this.style) { + if (this.style.hasOwnProperty(style)) { + // $FlowFixMe Flow doesn't seem to understand span.style's type. + node.style[style] = this.style[style]; + } + } // Apply attributes + + + for (const attr in this.attributes) { + if (this.attributes.hasOwnProperty(attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } // Append the children, also as HTML nodes + + + for (let i = 0; i < this.children.length; i++) { + node.appendChild(this.children[i].toNode()); + } + + return node; +}; +/** + * https://w3c.github.io/html-reference/syntax.html#syntax-attributes + * + * > Attribute Names must consist of one or more characters + * other than the space characters, U+0000 NULL, + * '"', "'", ">", "/", "=", the control characters, + * and any characters that are not defined by Unicode. + */ + + +const invalidAttributeNameRegex = /[\s"'>/=\x00-\x1f]/; +/** + * Convert into an HTML markup string + */ + +const toMarkup = function (tagName) { + let markup = "<" + tagName; // Add the class + + if (this.classes.length) { + markup += " class=\"" + utils.escape(createClass(this.classes)) + "\""; + } + + let styles = ""; // Add the styles, after hyphenation + + for (const style in this.style) { + if (this.style.hasOwnProperty(style)) { + styles += utils.hyphenate(style) + ":" + this.style[style] + ";"; + } + } + + if (styles) { + markup += " style=\"" + utils.escape(styles) + "\""; + } // Add the attributes + + + for (const attr in this.attributes) { + if (this.attributes.hasOwnProperty(attr)) { + if (invalidAttributeNameRegex.test(attr)) { + throw new src_ParseError("Invalid attribute name '" + attr + "'"); + } + + markup += " " + attr + "=\"" + utils.escape(this.attributes[attr]) + "\""; + } + } + + markup += ">"; // Add the markup of the children, also as markup + + for (let i = 0; i < this.children.length; i++) { + markup += this.children[i].toMarkup(); + } + + markup += ""; + return markup; +}; // Making the type below exact with all optional fields doesn't work due to +// - https://github.com/facebook/flow/issues/4582 +// - https://github.com/facebook/flow/issues/5688 +// However, since *all* fields are optional, $Shape<> works as suggested in 5688 +// above. +// This type does not include all CSS properties. Additional properties should +// be added as needed. + + +/** + * This node represents a span node, with a className, a list of children, and + * an inline style. It also contains information about its height, depth, and + * maxFontSize. + * + * Represents two types with different uses: SvgSpan to wrap an SVG and DomSpan + * otherwise. This typesafety is important when HTML builders access a span's + * children. + */ +class Span { + constructor(classes, children, options, style) { + this.children = void 0; + this.attributes = void 0; + this.classes = void 0; + this.height = void 0; + this.depth = void 0; + this.width = void 0; + this.maxFontSize = void 0; + this.style = void 0; + initNode.call(this, classes, options, style); + this.children = children || []; + } + /** + * Sets an arbitrary attribute on the span. Warning: use this wisely. Not + * all browsers support attributes the same, and having too many custom + * attributes is probably bad. + */ + + + setAttribute(attribute, value) { + this.attributes[attribute] = value; + } + + hasClass(className) { + return utils.contains(this.classes, className); + } + + toNode() { + return toNode.call(this, "span"); + } + + toMarkup() { + return toMarkup.call(this, "span"); + } + +} +/** + * This node represents an anchor () element with a hyperlink. See `span` + * for further details. + */ + +class Anchor { + constructor(href, classes, children, options) { + this.children = void 0; + this.attributes = void 0; + this.classes = void 0; + this.height = void 0; + this.depth = void 0; + this.maxFontSize = void 0; + this.style = void 0; + initNode.call(this, classes, options); + this.children = children || []; + this.setAttribute('href', href); + } + + setAttribute(attribute, value) { + this.attributes[attribute] = value; + } + + hasClass(className) { + return utils.contains(this.classes, className); + } + + toNode() { + return toNode.call(this, "a"); + } + + toMarkup() { + return toMarkup.call(this, "a"); + } + +} +/** + * This node represents an image embed () element. + */ + +class Img { + constructor(src, alt, style) { + this.src = void 0; + this.alt = void 0; + this.classes = void 0; + this.height = void 0; + this.depth = void 0; + this.maxFontSize = void 0; + this.style = void 0; + this.alt = alt; + this.src = src; + this.classes = ["mord"]; + this.style = style; + } + + hasClass(className) { + return utils.contains(this.classes, className); + } + + toNode() { + const node = document.createElement("img"); + node.src = this.src; + node.alt = this.alt; + node.className = "mord"; // Apply inline styles + + for (const style in this.style) { + if (this.style.hasOwnProperty(style)) { + // $FlowFixMe + node.style[style] = this.style[style]; + } + } + + return node; + } + + toMarkup() { + let markup = "\"" 0) { + span = document.createElement("span"); + span.style.marginRight = makeEm(this.italic); + } + + if (this.classes.length > 0) { + span = span || document.createElement("span"); + span.className = createClass(this.classes); + } + + for (const style in this.style) { + if (this.style.hasOwnProperty(style)) { + span = span || document.createElement("span"); // $FlowFixMe Flow doesn't seem to understand span.style's type. + + span.style[style] = this.style[style]; + } + } + + if (span) { + span.appendChild(node); + return span; + } else { + return node; + } + } + /** + * Creates markup for a symbol node. + */ + + + toMarkup() { + // TODO(alpert): More duplication than I'd like from + // span.prototype.toMarkup and symbolNode.prototype.toNode... + let needsSpan = false; + let markup = " 0) { + styles += "margin-right:" + this.italic + "em;"; + } + + for (const style in this.style) { + if (this.style.hasOwnProperty(style)) { + styles += utils.hyphenate(style) + ":" + this.style[style] + ";"; + } + } + + if (styles) { + needsSpan = true; + markup += " style=\"" + utils.escape(styles) + "\""; + } + + const escaped = utils.escape(this.text); + + if (needsSpan) { + markup += ">"; + markup += escaped; + markup += ""; + return markup; + } else { + return escaped; + } + } + +} +/** + * SVG nodes are used to render stretchy wide elements. + */ + +class SvgNode { + constructor(children, attributes) { + this.children = void 0; + this.attributes = void 0; + this.children = children || []; + this.attributes = attributes || {}; + } + + toNode() { + const svgNS = "http://www.w3.org/2000/svg"; + const node = document.createElementNS(svgNS, "svg"); // Apply attributes + + for (const attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } + + for (let i = 0; i < this.children.length; i++) { + node.appendChild(this.children[i].toNode()); + } + + return node; + } + + toMarkup() { + let markup = ""; + } else { + return ""; + } + } + +} +class LineNode { + constructor(attributes) { + this.attributes = void 0; + this.attributes = attributes || {}; + } + + toNode() { + const svgNS = "http://www.w3.org/2000/svg"; + const node = document.createElementNS(svgNS, "line"); // Apply attributes + + for (const attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } + + return node; + } + + toMarkup() { + let markup = " but got " + String(group) + "."); + } +} +;// CONCATENATED MODULE: ./src/symbols.js +/** + * This file holds a list of all no-argument functions and single-character + * symbols (like 'a' or ';'). + * + * For each of the symbols, there are three properties they can have: + * - font (required): the font to be used for this symbol. Either "main" (the + normal font), or "ams" (the ams fonts). + * - group (required): the ParseNode group type the symbol should have (i.e. + "textord", "mathord", etc). + See https://github.com/KaTeX/KaTeX/wiki/Examining-TeX#group-types + * - replace: the character that this symbol or function should be + * replaced with (i.e. "\phi" has a replace value of "\u03d5", the phi + * character in the main font). + * + * The outermost map in the table indicates what mode the symbols should be + * accepted in (e.g. "math" or "text"). + */ +// Some of these have a "-token" suffix since these are also used as `ParseNode` +// types for raw text tokens, and we want to avoid conflicts with higher-level +// `ParseNode` types. These `ParseNode`s are constructed within `Parser` by +// looking up the `symbols` map. +const ATOMS = { + "bin": 1, + "close": 1, + "inner": 1, + "open": 1, + "punct": 1, + "rel": 1 +}; +const NON_ATOMS = { + "accent-token": 1, + "mathord": 1, + "op-token": 1, + "spacing": 1, + "textord": 1 +}; +const symbols = { + "math": {}, + "text": {} +}; +/* harmony default export */ var src_symbols = (symbols); +/** `acceptUnicodeChar = true` is only applicable if `replace` is set. */ + +function defineSymbol(mode, font, group, replace, name, acceptUnicodeChar) { + symbols[mode][name] = { + font, + group, + replace + }; + + if (acceptUnicodeChar && replace) { + symbols[mode][replace] = symbols[mode][name]; + } +} // Some abbreviations for commonly used strings. +// This helps minify the code, and also spotting typos using jshint. +// modes: + +const math = "math"; +const symbols_text = "text"; // fonts: + +const main = "main"; +const ams = "ams"; // groups: + +const accent = "accent-token"; +const bin = "bin"; +const symbols_close = "close"; +const inner = "inner"; +const mathord = "mathord"; +const op = "op-token"; +const symbols_open = "open"; +const punct = "punct"; +const rel = "rel"; +const spacing = "spacing"; +const textord = "textord"; // Now comes the symbol table +// Relation Symbols + +defineSymbol(math, main, rel, "\u2261", "\\equiv", true); +defineSymbol(math, main, rel, "\u227a", "\\prec", true); +defineSymbol(math, main, rel, "\u227b", "\\succ", true); +defineSymbol(math, main, rel, "\u223c", "\\sim", true); +defineSymbol(math, main, rel, "\u22a5", "\\perp"); +defineSymbol(math, main, rel, "\u2aaf", "\\preceq", true); +defineSymbol(math, main, rel, "\u2ab0", "\\succeq", true); +defineSymbol(math, main, rel, "\u2243", "\\simeq", true); +defineSymbol(math, main, rel, "\u2223", "\\mid", true); +defineSymbol(math, main, rel, "\u226a", "\\ll", true); +defineSymbol(math, main, rel, "\u226b", "\\gg", true); +defineSymbol(math, main, rel, "\u224d", "\\asymp", true); +defineSymbol(math, main, rel, "\u2225", "\\parallel"); +defineSymbol(math, main, rel, "\u22c8", "\\bowtie", true); +defineSymbol(math, main, rel, "\u2323", "\\smile", true); +defineSymbol(math, main, rel, "\u2291", "\\sqsubseteq", true); +defineSymbol(math, main, rel, "\u2292", "\\sqsupseteq", true); +defineSymbol(math, main, rel, "\u2250", "\\doteq", true); +defineSymbol(math, main, rel, "\u2322", "\\frown", true); +defineSymbol(math, main, rel, "\u220b", "\\ni", true); +defineSymbol(math, main, rel, "\u221d", "\\propto", true); +defineSymbol(math, main, rel, "\u22a2", "\\vdash", true); +defineSymbol(math, main, rel, "\u22a3", "\\dashv", true); +defineSymbol(math, main, rel, "\u220b", "\\owns"); // Punctuation + +defineSymbol(math, main, punct, "\u002e", "\\ldotp"); +defineSymbol(math, main, punct, "\u22c5", "\\cdotp"); // Misc Symbols + +defineSymbol(math, main, textord, "\u0023", "\\#"); +defineSymbol(symbols_text, main, textord, "\u0023", "\\#"); +defineSymbol(math, main, textord, "\u0026", "\\&"); +defineSymbol(symbols_text, main, textord, "\u0026", "\\&"); +defineSymbol(math, main, textord, "\u2135", "\\aleph", true); +defineSymbol(math, main, textord, "\u2200", "\\forall", true); +defineSymbol(math, main, textord, "\u210f", "\\hbar", true); +defineSymbol(math, main, textord, "\u2203", "\\exists", true); +defineSymbol(math, main, textord, "\u2207", "\\nabla", true); +defineSymbol(math, main, textord, "\u266d", "\\flat", true); +defineSymbol(math, main, textord, "\u2113", "\\ell", true); +defineSymbol(math, main, textord, "\u266e", "\\natural", true); +defineSymbol(math, main, textord, "\u2663", "\\clubsuit", true); +defineSymbol(math, main, textord, "\u2118", "\\wp", true); +defineSymbol(math, main, textord, "\u266f", "\\sharp", true); +defineSymbol(math, main, textord, "\u2662", "\\diamondsuit", true); +defineSymbol(math, main, textord, "\u211c", "\\Re", true); +defineSymbol(math, main, textord, "\u2661", "\\heartsuit", true); +defineSymbol(math, main, textord, "\u2111", "\\Im", true); +defineSymbol(math, main, textord, "\u2660", "\\spadesuit", true); +defineSymbol(math, main, textord, "\u00a7", "\\S", true); +defineSymbol(symbols_text, main, textord, "\u00a7", "\\S"); +defineSymbol(math, main, textord, "\u00b6", "\\P", true); +defineSymbol(symbols_text, main, textord, "\u00b6", "\\P"); // Math and Text + +defineSymbol(math, main, textord, "\u2020", "\\dag"); +defineSymbol(symbols_text, main, textord, "\u2020", "\\dag"); +defineSymbol(symbols_text, main, textord, "\u2020", "\\textdagger"); +defineSymbol(math, main, textord, "\u2021", "\\ddag"); +defineSymbol(symbols_text, main, textord, "\u2021", "\\ddag"); +defineSymbol(symbols_text, main, textord, "\u2021", "\\textdaggerdbl"); // Large Delimiters + +defineSymbol(math, main, symbols_close, "\u23b1", "\\rmoustache", true); +defineSymbol(math, main, symbols_open, "\u23b0", "\\lmoustache", true); +defineSymbol(math, main, symbols_close, "\u27ef", "\\rgroup", true); +defineSymbol(math, main, symbols_open, "\u27ee", "\\lgroup", true); // Binary Operators + +defineSymbol(math, main, bin, "\u2213", "\\mp", true); +defineSymbol(math, main, bin, "\u2296", "\\ominus", true); +defineSymbol(math, main, bin, "\u228e", "\\uplus", true); +defineSymbol(math, main, bin, "\u2293", "\\sqcap", true); +defineSymbol(math, main, bin, "\u2217", "\\ast"); +defineSymbol(math, main, bin, "\u2294", "\\sqcup", true); +defineSymbol(math, main, bin, "\u25ef", "\\bigcirc", true); +defineSymbol(math, main, bin, "\u2219", "\\bullet", true); +defineSymbol(math, main, bin, "\u2021", "\\ddagger"); +defineSymbol(math, main, bin, "\u2240", "\\wr", true); +defineSymbol(math, main, bin, "\u2a3f", "\\amalg"); +defineSymbol(math, main, bin, "\u0026", "\\And"); // from amsmath +// Arrow Symbols + +defineSymbol(math, main, rel, "\u27f5", "\\longleftarrow", true); +defineSymbol(math, main, rel, "\u21d0", "\\Leftarrow", true); +defineSymbol(math, main, rel, "\u27f8", "\\Longleftarrow", true); +defineSymbol(math, main, rel, "\u27f6", "\\longrightarrow", true); +defineSymbol(math, main, rel, "\u21d2", "\\Rightarrow", true); +defineSymbol(math, main, rel, "\u27f9", "\\Longrightarrow", true); +defineSymbol(math, main, rel, "\u2194", "\\leftrightarrow", true); +defineSymbol(math, main, rel, "\u27f7", "\\longleftrightarrow", true); +defineSymbol(math, main, rel, "\u21d4", "\\Leftrightarrow", true); +defineSymbol(math, main, rel, "\u27fa", "\\Longleftrightarrow", true); +defineSymbol(math, main, rel, "\u21a6", "\\mapsto", true); +defineSymbol(math, main, rel, "\u27fc", "\\longmapsto", true); +defineSymbol(math, main, rel, "\u2197", "\\nearrow", true); +defineSymbol(math, main, rel, "\u21a9", "\\hookleftarrow", true); +defineSymbol(math, main, rel, "\u21aa", "\\hookrightarrow", true); +defineSymbol(math, main, rel, "\u2198", "\\searrow", true); +defineSymbol(math, main, rel, "\u21bc", "\\leftharpoonup", true); +defineSymbol(math, main, rel, "\u21c0", "\\rightharpoonup", true); +defineSymbol(math, main, rel, "\u2199", "\\swarrow", true); +defineSymbol(math, main, rel, "\u21bd", "\\leftharpoondown", true); +defineSymbol(math, main, rel, "\u21c1", "\\rightharpoondown", true); +defineSymbol(math, main, rel, "\u2196", "\\nwarrow", true); +defineSymbol(math, main, rel, "\u21cc", "\\rightleftharpoons", true); // AMS Negated Binary Relations + +defineSymbol(math, ams, rel, "\u226e", "\\nless", true); // Symbol names preceded by "@" each have a corresponding macro. + +defineSymbol(math, ams, rel, "\ue010", "\\@nleqslant"); +defineSymbol(math, ams, rel, "\ue011", "\\@nleqq"); +defineSymbol(math, ams, rel, "\u2a87", "\\lneq", true); +defineSymbol(math, ams, rel, "\u2268", "\\lneqq", true); +defineSymbol(math, ams, rel, "\ue00c", "\\@lvertneqq"); +defineSymbol(math, ams, rel, "\u22e6", "\\lnsim", true); +defineSymbol(math, ams, rel, "\u2a89", "\\lnapprox", true); +defineSymbol(math, ams, rel, "\u2280", "\\nprec", true); // unicode-math maps \u22e0 to \npreccurlyeq. We'll use the AMS synonym. + +defineSymbol(math, ams, rel, "\u22e0", "\\npreceq", true); +defineSymbol(math, ams, rel, "\u22e8", "\\precnsim", true); +defineSymbol(math, ams, rel, "\u2ab9", "\\precnapprox", true); +defineSymbol(math, ams, rel, "\u2241", "\\nsim", true); +defineSymbol(math, ams, rel, "\ue006", "\\@nshortmid"); +defineSymbol(math, ams, rel, "\u2224", "\\nmid", true); +defineSymbol(math, ams, rel, "\u22ac", "\\nvdash", true); +defineSymbol(math, ams, rel, "\u22ad", "\\nvDash", true); +defineSymbol(math, ams, rel, "\u22ea", "\\ntriangleleft"); +defineSymbol(math, ams, rel, "\u22ec", "\\ntrianglelefteq", true); +defineSymbol(math, ams, rel, "\u228a", "\\subsetneq", true); +defineSymbol(math, ams, rel, "\ue01a", "\\@varsubsetneq"); +defineSymbol(math, ams, rel, "\u2acb", "\\subsetneqq", true); +defineSymbol(math, ams, rel, "\ue017", "\\@varsubsetneqq"); +defineSymbol(math, ams, rel, "\u226f", "\\ngtr", true); +defineSymbol(math, ams, rel, "\ue00f", "\\@ngeqslant"); +defineSymbol(math, ams, rel, "\ue00e", "\\@ngeqq"); +defineSymbol(math, ams, rel, "\u2a88", "\\gneq", true); +defineSymbol(math, ams, rel, "\u2269", "\\gneqq", true); +defineSymbol(math, ams, rel, "\ue00d", "\\@gvertneqq"); +defineSymbol(math, ams, rel, "\u22e7", "\\gnsim", true); +defineSymbol(math, ams, rel, "\u2a8a", "\\gnapprox", true); +defineSymbol(math, ams, rel, "\u2281", "\\nsucc", true); // unicode-math maps \u22e1 to \nsucccurlyeq. We'll use the AMS synonym. + +defineSymbol(math, ams, rel, "\u22e1", "\\nsucceq", true); +defineSymbol(math, ams, rel, "\u22e9", "\\succnsim", true); +defineSymbol(math, ams, rel, "\u2aba", "\\succnapprox", true); // unicode-math maps \u2246 to \simneqq. We'll use the AMS synonym. + +defineSymbol(math, ams, rel, "\u2246", "\\ncong", true); +defineSymbol(math, ams, rel, "\ue007", "\\@nshortparallel"); +defineSymbol(math, ams, rel, "\u2226", "\\nparallel", true); +defineSymbol(math, ams, rel, "\u22af", "\\nVDash", true); +defineSymbol(math, ams, rel, "\u22eb", "\\ntriangleright"); +defineSymbol(math, ams, rel, "\u22ed", "\\ntrianglerighteq", true); +defineSymbol(math, ams, rel, "\ue018", "\\@nsupseteqq"); +defineSymbol(math, ams, rel, "\u228b", "\\supsetneq", true); +defineSymbol(math, ams, rel, "\ue01b", "\\@varsupsetneq"); +defineSymbol(math, ams, rel, "\u2acc", "\\supsetneqq", true); +defineSymbol(math, ams, rel, "\ue019", "\\@varsupsetneqq"); +defineSymbol(math, ams, rel, "\u22ae", "\\nVdash", true); +defineSymbol(math, ams, rel, "\u2ab5", "\\precneqq", true); +defineSymbol(math, ams, rel, "\u2ab6", "\\succneqq", true); +defineSymbol(math, ams, rel, "\ue016", "\\@nsubseteqq"); +defineSymbol(math, ams, bin, "\u22b4", "\\unlhd"); +defineSymbol(math, ams, bin, "\u22b5", "\\unrhd"); // AMS Negated Arrows + +defineSymbol(math, ams, rel, "\u219a", "\\nleftarrow", true); +defineSymbol(math, ams, rel, "\u219b", "\\nrightarrow", true); +defineSymbol(math, ams, rel, "\u21cd", "\\nLeftarrow", true); +defineSymbol(math, ams, rel, "\u21cf", "\\nRightarrow", true); +defineSymbol(math, ams, rel, "\u21ae", "\\nleftrightarrow", true); +defineSymbol(math, ams, rel, "\u21ce", "\\nLeftrightarrow", true); // AMS Misc + +defineSymbol(math, ams, rel, "\u25b3", "\\vartriangle"); +defineSymbol(math, ams, textord, "\u210f", "\\hslash"); +defineSymbol(math, ams, textord, "\u25bd", "\\triangledown"); +defineSymbol(math, ams, textord, "\u25ca", "\\lozenge"); +defineSymbol(math, ams, textord, "\u24c8", "\\circledS"); +defineSymbol(math, ams, textord, "\u00ae", "\\circledR"); +defineSymbol(symbols_text, ams, textord, "\u00ae", "\\circledR"); +defineSymbol(math, ams, textord, "\u2221", "\\measuredangle", true); +defineSymbol(math, ams, textord, "\u2204", "\\nexists"); +defineSymbol(math, ams, textord, "\u2127", "\\mho"); +defineSymbol(math, ams, textord, "\u2132", "\\Finv", true); +defineSymbol(math, ams, textord, "\u2141", "\\Game", true); +defineSymbol(math, ams, textord, "\u2035", "\\backprime"); +defineSymbol(math, ams, textord, "\u25b2", "\\blacktriangle"); +defineSymbol(math, ams, textord, "\u25bc", "\\blacktriangledown"); +defineSymbol(math, ams, textord, "\u25a0", "\\blacksquare"); +defineSymbol(math, ams, textord, "\u29eb", "\\blacklozenge"); +defineSymbol(math, ams, textord, "\u2605", "\\bigstar"); +defineSymbol(math, ams, textord, "\u2222", "\\sphericalangle", true); +defineSymbol(math, ams, textord, "\u2201", "\\complement", true); // unicode-math maps U+F0 to \matheth. We map to AMS function \eth + +defineSymbol(math, ams, textord, "\u00f0", "\\eth", true); +defineSymbol(symbols_text, main, textord, "\u00f0", "\u00f0"); +defineSymbol(math, ams, textord, "\u2571", "\\diagup"); +defineSymbol(math, ams, textord, "\u2572", "\\diagdown"); +defineSymbol(math, ams, textord, "\u25a1", "\\square"); +defineSymbol(math, ams, textord, "\u25a1", "\\Box"); +defineSymbol(math, ams, textord, "\u25ca", "\\Diamond"); // unicode-math maps U+A5 to \mathyen. We map to AMS function \yen + +defineSymbol(math, ams, textord, "\u00a5", "\\yen", true); +defineSymbol(symbols_text, ams, textord, "\u00a5", "\\yen", true); +defineSymbol(math, ams, textord, "\u2713", "\\checkmark", true); +defineSymbol(symbols_text, ams, textord, "\u2713", "\\checkmark"); // AMS Hebrew + +defineSymbol(math, ams, textord, "\u2136", "\\beth", true); +defineSymbol(math, ams, textord, "\u2138", "\\daleth", true); +defineSymbol(math, ams, textord, "\u2137", "\\gimel", true); // AMS Greek + +defineSymbol(math, ams, textord, "\u03dd", "\\digamma", true); +defineSymbol(math, ams, textord, "\u03f0", "\\varkappa"); // AMS Delimiters + +defineSymbol(math, ams, symbols_open, "\u250c", "\\@ulcorner", true); +defineSymbol(math, ams, symbols_close, "\u2510", "\\@urcorner", true); +defineSymbol(math, ams, symbols_open, "\u2514", "\\@llcorner", true); +defineSymbol(math, ams, symbols_close, "\u2518", "\\@lrcorner", true); // AMS Binary Relations + +defineSymbol(math, ams, rel, "\u2266", "\\leqq", true); +defineSymbol(math, ams, rel, "\u2a7d", "\\leqslant", true); +defineSymbol(math, ams, rel, "\u2a95", "\\eqslantless", true); +defineSymbol(math, ams, rel, "\u2272", "\\lesssim", true); +defineSymbol(math, ams, rel, "\u2a85", "\\lessapprox", true); +defineSymbol(math, ams, rel, "\u224a", "\\approxeq", true); +defineSymbol(math, ams, bin, "\u22d6", "\\lessdot"); +defineSymbol(math, ams, rel, "\u22d8", "\\lll", true); +defineSymbol(math, ams, rel, "\u2276", "\\lessgtr", true); +defineSymbol(math, ams, rel, "\u22da", "\\lesseqgtr", true); +defineSymbol(math, ams, rel, "\u2a8b", "\\lesseqqgtr", true); +defineSymbol(math, ams, rel, "\u2251", "\\doteqdot"); +defineSymbol(math, ams, rel, "\u2253", "\\risingdotseq", true); +defineSymbol(math, ams, rel, "\u2252", "\\fallingdotseq", true); +defineSymbol(math, ams, rel, "\u223d", "\\backsim", true); +defineSymbol(math, ams, rel, "\u22cd", "\\backsimeq", true); +defineSymbol(math, ams, rel, "\u2ac5", "\\subseteqq", true); +defineSymbol(math, ams, rel, "\u22d0", "\\Subset", true); +defineSymbol(math, ams, rel, "\u228f", "\\sqsubset", true); +defineSymbol(math, ams, rel, "\u227c", "\\preccurlyeq", true); +defineSymbol(math, ams, rel, "\u22de", "\\curlyeqprec", true); +defineSymbol(math, ams, rel, "\u227e", "\\precsim", true); +defineSymbol(math, ams, rel, "\u2ab7", "\\precapprox", true); +defineSymbol(math, ams, rel, "\u22b2", "\\vartriangleleft"); +defineSymbol(math, ams, rel, "\u22b4", "\\trianglelefteq"); +defineSymbol(math, ams, rel, "\u22a8", "\\vDash", true); +defineSymbol(math, ams, rel, "\u22aa", "\\Vvdash", true); +defineSymbol(math, ams, rel, "\u2323", "\\smallsmile"); +defineSymbol(math, ams, rel, "\u2322", "\\smallfrown"); +defineSymbol(math, ams, rel, "\u224f", "\\bumpeq", true); +defineSymbol(math, ams, rel, "\u224e", "\\Bumpeq", true); +defineSymbol(math, ams, rel, "\u2267", "\\geqq", true); +defineSymbol(math, ams, rel, "\u2a7e", "\\geqslant", true); +defineSymbol(math, ams, rel, "\u2a96", "\\eqslantgtr", true); +defineSymbol(math, ams, rel, "\u2273", "\\gtrsim", true); +defineSymbol(math, ams, rel, "\u2a86", "\\gtrapprox", true); +defineSymbol(math, ams, bin, "\u22d7", "\\gtrdot"); +defineSymbol(math, ams, rel, "\u22d9", "\\ggg", true); +defineSymbol(math, ams, rel, "\u2277", "\\gtrless", true); +defineSymbol(math, ams, rel, "\u22db", "\\gtreqless", true); +defineSymbol(math, ams, rel, "\u2a8c", "\\gtreqqless", true); +defineSymbol(math, ams, rel, "\u2256", "\\eqcirc", true); +defineSymbol(math, ams, rel, "\u2257", "\\circeq", true); +defineSymbol(math, ams, rel, "\u225c", "\\triangleq", true); +defineSymbol(math, ams, rel, "\u223c", "\\thicksim"); +defineSymbol(math, ams, rel, "\u2248", "\\thickapprox"); +defineSymbol(math, ams, rel, "\u2ac6", "\\supseteqq", true); +defineSymbol(math, ams, rel, "\u22d1", "\\Supset", true); +defineSymbol(math, ams, rel, "\u2290", "\\sqsupset", true); +defineSymbol(math, ams, rel, "\u227d", "\\succcurlyeq", true); +defineSymbol(math, ams, rel, "\u22df", "\\curlyeqsucc", true); +defineSymbol(math, ams, rel, "\u227f", "\\succsim", true); +defineSymbol(math, ams, rel, "\u2ab8", "\\succapprox", true); +defineSymbol(math, ams, rel, "\u22b3", "\\vartriangleright"); +defineSymbol(math, ams, rel, "\u22b5", "\\trianglerighteq"); +defineSymbol(math, ams, rel, "\u22a9", "\\Vdash", true); +defineSymbol(math, ams, rel, "\u2223", "\\shortmid"); +defineSymbol(math, ams, rel, "\u2225", "\\shortparallel"); +defineSymbol(math, ams, rel, "\u226c", "\\between", true); +defineSymbol(math, ams, rel, "\u22d4", "\\pitchfork", true); +defineSymbol(math, ams, rel, "\u221d", "\\varpropto"); +defineSymbol(math, ams, rel, "\u25c0", "\\blacktriangleleft"); // unicode-math says that \therefore is a mathord atom. +// We kept the amssymb atom type, which is rel. + +defineSymbol(math, ams, rel, "\u2234", "\\therefore", true); +defineSymbol(math, ams, rel, "\u220d", "\\backepsilon"); +defineSymbol(math, ams, rel, "\u25b6", "\\blacktriangleright"); // unicode-math says that \because is a mathord atom. +// We kept the amssymb atom type, which is rel. + +defineSymbol(math, ams, rel, "\u2235", "\\because", true); +defineSymbol(math, ams, rel, "\u22d8", "\\llless"); +defineSymbol(math, ams, rel, "\u22d9", "\\gggtr"); +defineSymbol(math, ams, bin, "\u22b2", "\\lhd"); +defineSymbol(math, ams, bin, "\u22b3", "\\rhd"); +defineSymbol(math, ams, rel, "\u2242", "\\eqsim", true); +defineSymbol(math, main, rel, "\u22c8", "\\Join"); +defineSymbol(math, ams, rel, "\u2251", "\\Doteq", true); // AMS Binary Operators + +defineSymbol(math, ams, bin, "\u2214", "\\dotplus", true); +defineSymbol(math, ams, bin, "\u2216", "\\smallsetminus"); +defineSymbol(math, ams, bin, "\u22d2", "\\Cap", true); +defineSymbol(math, ams, bin, "\u22d3", "\\Cup", true); +defineSymbol(math, ams, bin, "\u2a5e", "\\doublebarwedge", true); +defineSymbol(math, ams, bin, "\u229f", "\\boxminus", true); +defineSymbol(math, ams, bin, "\u229e", "\\boxplus", true); +defineSymbol(math, ams, bin, "\u22c7", "\\divideontimes", true); +defineSymbol(math, ams, bin, "\u22c9", "\\ltimes", true); +defineSymbol(math, ams, bin, "\u22ca", "\\rtimes", true); +defineSymbol(math, ams, bin, "\u22cb", "\\leftthreetimes", true); +defineSymbol(math, ams, bin, "\u22cc", "\\rightthreetimes", true); +defineSymbol(math, ams, bin, "\u22cf", "\\curlywedge", true); +defineSymbol(math, ams, bin, "\u22ce", "\\curlyvee", true); +defineSymbol(math, ams, bin, "\u229d", "\\circleddash", true); +defineSymbol(math, ams, bin, "\u229b", "\\circledast", true); +defineSymbol(math, ams, bin, "\u22c5", "\\centerdot"); +defineSymbol(math, ams, bin, "\u22ba", "\\intercal", true); +defineSymbol(math, ams, bin, "\u22d2", "\\doublecap"); +defineSymbol(math, ams, bin, "\u22d3", "\\doublecup"); +defineSymbol(math, ams, bin, "\u22a0", "\\boxtimes", true); // AMS Arrows +// Note: unicode-math maps \u21e2 to their own function \rightdasharrow. +// We'll map it to AMS function \dashrightarrow. It produces the same atom. + +defineSymbol(math, ams, rel, "\u21e2", "\\dashrightarrow", true); // unicode-math maps \u21e0 to \leftdasharrow. We'll use the AMS synonym. + +defineSymbol(math, ams, rel, "\u21e0", "\\dashleftarrow", true); +defineSymbol(math, ams, rel, "\u21c7", "\\leftleftarrows", true); +defineSymbol(math, ams, rel, "\u21c6", "\\leftrightarrows", true); +defineSymbol(math, ams, rel, "\u21da", "\\Lleftarrow", true); +defineSymbol(math, ams, rel, "\u219e", "\\twoheadleftarrow", true); +defineSymbol(math, ams, rel, "\u21a2", "\\leftarrowtail", true); +defineSymbol(math, ams, rel, "\u21ab", "\\looparrowleft", true); +defineSymbol(math, ams, rel, "\u21cb", "\\leftrightharpoons", true); +defineSymbol(math, ams, rel, "\u21b6", "\\curvearrowleft", true); // unicode-math maps \u21ba to \acwopencirclearrow. We'll use the AMS synonym. + +defineSymbol(math, ams, rel, "\u21ba", "\\circlearrowleft", true); +defineSymbol(math, ams, rel, "\u21b0", "\\Lsh", true); +defineSymbol(math, ams, rel, "\u21c8", "\\upuparrows", true); +defineSymbol(math, ams, rel, "\u21bf", "\\upharpoonleft", true); +defineSymbol(math, ams, rel, "\u21c3", "\\downharpoonleft", true); +defineSymbol(math, main, rel, "\u22b6", "\\origof", true); // not in font + +defineSymbol(math, main, rel, "\u22b7", "\\imageof", true); // not in font + +defineSymbol(math, ams, rel, "\u22b8", "\\multimap", true); +defineSymbol(math, ams, rel, "\u21ad", "\\leftrightsquigarrow", true); +defineSymbol(math, ams, rel, "\u21c9", "\\rightrightarrows", true); +defineSymbol(math, ams, rel, "\u21c4", "\\rightleftarrows", true); +defineSymbol(math, ams, rel, "\u21a0", "\\twoheadrightarrow", true); +defineSymbol(math, ams, rel, "\u21a3", "\\rightarrowtail", true); +defineSymbol(math, ams, rel, "\u21ac", "\\looparrowright", true); +defineSymbol(math, ams, rel, "\u21b7", "\\curvearrowright", true); // unicode-math maps \u21bb to \cwopencirclearrow. We'll use the AMS synonym. + +defineSymbol(math, ams, rel, "\u21bb", "\\circlearrowright", true); +defineSymbol(math, ams, rel, "\u21b1", "\\Rsh", true); +defineSymbol(math, ams, rel, "\u21ca", "\\downdownarrows", true); +defineSymbol(math, ams, rel, "\u21be", "\\upharpoonright", true); +defineSymbol(math, ams, rel, "\u21c2", "\\downharpoonright", true); +defineSymbol(math, ams, rel, "\u21dd", "\\rightsquigarrow", true); +defineSymbol(math, ams, rel, "\u21dd", "\\leadsto"); +defineSymbol(math, ams, rel, "\u21db", "\\Rrightarrow", true); +defineSymbol(math, ams, rel, "\u21be", "\\restriction"); +defineSymbol(math, main, textord, "\u2018", "`"); +defineSymbol(math, main, textord, "$", "\\$"); +defineSymbol(symbols_text, main, textord, "$", "\\$"); +defineSymbol(symbols_text, main, textord, "$", "\\textdollar"); +defineSymbol(math, main, textord, "%", "\\%"); +defineSymbol(symbols_text, main, textord, "%", "\\%"); +defineSymbol(math, main, textord, "_", "\\_"); +defineSymbol(symbols_text, main, textord, "_", "\\_"); +defineSymbol(symbols_text, main, textord, "_", "\\textunderscore"); +defineSymbol(math, main, textord, "\u2220", "\\angle", true); +defineSymbol(math, main, textord, "\u221e", "\\infty", true); +defineSymbol(math, main, textord, "\u2032", "\\prime"); +defineSymbol(math, main, textord, "\u25b3", "\\triangle"); +defineSymbol(math, main, textord, "\u0393", "\\Gamma", true); +defineSymbol(math, main, textord, "\u0394", "\\Delta", true); +defineSymbol(math, main, textord, "\u0398", "\\Theta", true); +defineSymbol(math, main, textord, "\u039b", "\\Lambda", true); +defineSymbol(math, main, textord, "\u039e", "\\Xi", true); +defineSymbol(math, main, textord, "\u03a0", "\\Pi", true); +defineSymbol(math, main, textord, "\u03a3", "\\Sigma", true); +defineSymbol(math, main, textord, "\u03a5", "\\Upsilon", true); +defineSymbol(math, main, textord, "\u03a6", "\\Phi", true); +defineSymbol(math, main, textord, "\u03a8", "\\Psi", true); +defineSymbol(math, main, textord, "\u03a9", "\\Omega", true); +defineSymbol(math, main, textord, "A", "\u0391"); +defineSymbol(math, main, textord, "B", "\u0392"); +defineSymbol(math, main, textord, "E", "\u0395"); +defineSymbol(math, main, textord, "Z", "\u0396"); +defineSymbol(math, main, textord, "H", "\u0397"); +defineSymbol(math, main, textord, "I", "\u0399"); +defineSymbol(math, main, textord, "K", "\u039A"); +defineSymbol(math, main, textord, "M", "\u039C"); +defineSymbol(math, main, textord, "N", "\u039D"); +defineSymbol(math, main, textord, "O", "\u039F"); +defineSymbol(math, main, textord, "P", "\u03A1"); +defineSymbol(math, main, textord, "T", "\u03A4"); +defineSymbol(math, main, textord, "X", "\u03A7"); +defineSymbol(math, main, textord, "\u00ac", "\\neg", true); +defineSymbol(math, main, textord, "\u00ac", "\\lnot"); +defineSymbol(math, main, textord, "\u22a4", "\\top"); +defineSymbol(math, main, textord, "\u22a5", "\\bot"); +defineSymbol(math, main, textord, "\u2205", "\\emptyset"); +defineSymbol(math, ams, textord, "\u2205", "\\varnothing"); +defineSymbol(math, main, mathord, "\u03b1", "\\alpha", true); +defineSymbol(math, main, mathord, "\u03b2", "\\beta", true); +defineSymbol(math, main, mathord, "\u03b3", "\\gamma", true); +defineSymbol(math, main, mathord, "\u03b4", "\\delta", true); +defineSymbol(math, main, mathord, "\u03f5", "\\epsilon", true); +defineSymbol(math, main, mathord, "\u03b6", "\\zeta", true); +defineSymbol(math, main, mathord, "\u03b7", "\\eta", true); +defineSymbol(math, main, mathord, "\u03b8", "\\theta", true); +defineSymbol(math, main, mathord, "\u03b9", "\\iota", true); +defineSymbol(math, main, mathord, "\u03ba", "\\kappa", true); +defineSymbol(math, main, mathord, "\u03bb", "\\lambda", true); +defineSymbol(math, main, mathord, "\u03bc", "\\mu", true); +defineSymbol(math, main, mathord, "\u03bd", "\\nu", true); +defineSymbol(math, main, mathord, "\u03be", "\\xi", true); +defineSymbol(math, main, mathord, "\u03bf", "\\omicron", true); +defineSymbol(math, main, mathord, "\u03c0", "\\pi", true); +defineSymbol(math, main, mathord, "\u03c1", "\\rho", true); +defineSymbol(math, main, mathord, "\u03c3", "\\sigma", true); +defineSymbol(math, main, mathord, "\u03c4", "\\tau", true); +defineSymbol(math, main, mathord, "\u03c5", "\\upsilon", true); +defineSymbol(math, main, mathord, "\u03d5", "\\phi", true); +defineSymbol(math, main, mathord, "\u03c7", "\\chi", true); +defineSymbol(math, main, mathord, "\u03c8", "\\psi", true); +defineSymbol(math, main, mathord, "\u03c9", "\\omega", true); +defineSymbol(math, main, mathord, "\u03b5", "\\varepsilon", true); +defineSymbol(math, main, mathord, "\u03d1", "\\vartheta", true); +defineSymbol(math, main, mathord, "\u03d6", "\\varpi", true); +defineSymbol(math, main, mathord, "\u03f1", "\\varrho", true); +defineSymbol(math, main, mathord, "\u03c2", "\\varsigma", true); +defineSymbol(math, main, mathord, "\u03c6", "\\varphi", true); +defineSymbol(math, main, bin, "\u2217", "*", true); +defineSymbol(math, main, bin, "+", "+"); +defineSymbol(math, main, bin, "\u2212", "-", true); +defineSymbol(math, main, bin, "\u22c5", "\\cdot", true); +defineSymbol(math, main, bin, "\u2218", "\\circ", true); +defineSymbol(math, main, bin, "\u00f7", "\\div", true); +defineSymbol(math, main, bin, "\u00b1", "\\pm", true); +defineSymbol(math, main, bin, "\u00d7", "\\times", true); +defineSymbol(math, main, bin, "\u2229", "\\cap", true); +defineSymbol(math, main, bin, "\u222a", "\\cup", true); +defineSymbol(math, main, bin, "\u2216", "\\setminus", true); +defineSymbol(math, main, bin, "\u2227", "\\land"); +defineSymbol(math, main, bin, "\u2228", "\\lor"); +defineSymbol(math, main, bin, "\u2227", "\\wedge", true); +defineSymbol(math, main, bin, "\u2228", "\\vee", true); +defineSymbol(math, main, textord, "\u221a", "\\surd"); +defineSymbol(math, main, symbols_open, "\u27e8", "\\langle", true); +defineSymbol(math, main, symbols_open, "\u2223", "\\lvert"); +defineSymbol(math, main, symbols_open, "\u2225", "\\lVert"); +defineSymbol(math, main, symbols_close, "?", "?"); +defineSymbol(math, main, symbols_close, "!", "!"); +defineSymbol(math, main, symbols_close, "\u27e9", "\\rangle", true); +defineSymbol(math, main, symbols_close, "\u2223", "\\rvert"); +defineSymbol(math, main, symbols_close, "\u2225", "\\rVert"); +defineSymbol(math, main, rel, "=", "="); +defineSymbol(math, main, rel, ":", ":"); +defineSymbol(math, main, rel, "\u2248", "\\approx", true); +defineSymbol(math, main, rel, "\u2245", "\\cong", true); +defineSymbol(math, main, rel, "\u2265", "\\ge"); +defineSymbol(math, main, rel, "\u2265", "\\geq", true); +defineSymbol(math, main, rel, "\u2190", "\\gets"); +defineSymbol(math, main, rel, ">", "\\gt", true); +defineSymbol(math, main, rel, "\u2208", "\\in", true); +defineSymbol(math, main, rel, "\ue020", "\\@not"); +defineSymbol(math, main, rel, "\u2282", "\\subset", true); +defineSymbol(math, main, rel, "\u2283", "\\supset", true); +defineSymbol(math, main, rel, "\u2286", "\\subseteq", true); +defineSymbol(math, main, rel, "\u2287", "\\supseteq", true); +defineSymbol(math, ams, rel, "\u2288", "\\nsubseteq", true); +defineSymbol(math, ams, rel, "\u2289", "\\nsupseteq", true); +defineSymbol(math, main, rel, "\u22a8", "\\models"); +defineSymbol(math, main, rel, "\u2190", "\\leftarrow", true); +defineSymbol(math, main, rel, "\u2264", "\\le"); +defineSymbol(math, main, rel, "\u2264", "\\leq", true); +defineSymbol(math, main, rel, "<", "\\lt", true); +defineSymbol(math, main, rel, "\u2192", "\\rightarrow", true); +defineSymbol(math, main, rel, "\u2192", "\\to"); +defineSymbol(math, ams, rel, "\u2271", "\\ngeq", true); +defineSymbol(math, ams, rel, "\u2270", "\\nleq", true); +defineSymbol(math, main, spacing, "\u00a0", "\\ "); +defineSymbol(math, main, spacing, "\u00a0", "\\space"); // Ref: LaTeX Source 2e: \DeclareRobustCommand{\nobreakspace}{% + +defineSymbol(math, main, spacing, "\u00a0", "\\nobreakspace"); +defineSymbol(symbols_text, main, spacing, "\u00a0", "\\ "); +defineSymbol(symbols_text, main, spacing, "\u00a0", " "); +defineSymbol(symbols_text, main, spacing, "\u00a0", "\\space"); +defineSymbol(symbols_text, main, spacing, "\u00a0", "\\nobreakspace"); +defineSymbol(math, main, spacing, null, "\\nobreak"); +defineSymbol(math, main, spacing, null, "\\allowbreak"); +defineSymbol(math, main, punct, ",", ","); +defineSymbol(math, main, punct, ";", ";"); +defineSymbol(math, ams, bin, "\u22bc", "\\barwedge", true); +defineSymbol(math, ams, bin, "\u22bb", "\\veebar", true); +defineSymbol(math, main, bin, "\u2299", "\\odot", true); +defineSymbol(math, main, bin, "\u2295", "\\oplus", true); +defineSymbol(math, main, bin, "\u2297", "\\otimes", true); +defineSymbol(math, main, textord, "\u2202", "\\partial", true); +defineSymbol(math, main, bin, "\u2298", "\\oslash", true); +defineSymbol(math, ams, bin, "\u229a", "\\circledcirc", true); +defineSymbol(math, ams, bin, "\u22a1", "\\boxdot", true); +defineSymbol(math, main, bin, "\u25b3", "\\bigtriangleup"); +defineSymbol(math, main, bin, "\u25bd", "\\bigtriangledown"); +defineSymbol(math, main, bin, "\u2020", "\\dagger"); +defineSymbol(math, main, bin, "\u22c4", "\\diamond"); +defineSymbol(math, main, bin, "\u22c6", "\\star"); +defineSymbol(math, main, bin, "\u25c3", "\\triangleleft"); +defineSymbol(math, main, bin, "\u25b9", "\\triangleright"); +defineSymbol(math, main, symbols_open, "{", "\\{"); +defineSymbol(symbols_text, main, textord, "{", "\\{"); +defineSymbol(symbols_text, main, textord, "{", "\\textbraceleft"); +defineSymbol(math, main, symbols_close, "}", "\\}"); +defineSymbol(symbols_text, main, textord, "}", "\\}"); +defineSymbol(symbols_text, main, textord, "}", "\\textbraceright"); +defineSymbol(math, main, symbols_open, "{", "\\lbrace"); +defineSymbol(math, main, symbols_close, "}", "\\rbrace"); +defineSymbol(math, main, symbols_open, "[", "\\lbrack", true); +defineSymbol(symbols_text, main, textord, "[", "\\lbrack", true); +defineSymbol(math, main, symbols_close, "]", "\\rbrack", true); +defineSymbol(symbols_text, main, textord, "]", "\\rbrack", true); +defineSymbol(math, main, symbols_open, "(", "\\lparen", true); +defineSymbol(math, main, symbols_close, ")", "\\rparen", true); +defineSymbol(symbols_text, main, textord, "<", "\\textless", true); // in T1 fontenc + +defineSymbol(symbols_text, main, textord, ">", "\\textgreater", true); // in T1 fontenc + +defineSymbol(math, main, symbols_open, "\u230a", "\\lfloor", true); +defineSymbol(math, main, symbols_close, "\u230b", "\\rfloor", true); +defineSymbol(math, main, symbols_open, "\u2308", "\\lceil", true); +defineSymbol(math, main, symbols_close, "\u2309", "\\rceil", true); +defineSymbol(math, main, textord, "\\", "\\backslash"); +defineSymbol(math, main, textord, "\u2223", "|"); +defineSymbol(math, main, textord, "\u2223", "\\vert"); +defineSymbol(symbols_text, main, textord, "|", "\\textbar", true); // in T1 fontenc + +defineSymbol(math, main, textord, "\u2225", "\\|"); +defineSymbol(math, main, textord, "\u2225", "\\Vert"); +defineSymbol(symbols_text, main, textord, "\u2225", "\\textbardbl"); +defineSymbol(symbols_text, main, textord, "~", "\\textasciitilde"); +defineSymbol(symbols_text, main, textord, "\\", "\\textbackslash"); +defineSymbol(symbols_text, main, textord, "^", "\\textasciicircum"); +defineSymbol(math, main, rel, "\u2191", "\\uparrow", true); +defineSymbol(math, main, rel, "\u21d1", "\\Uparrow", true); +defineSymbol(math, main, rel, "\u2193", "\\downarrow", true); +defineSymbol(math, main, rel, "\u21d3", "\\Downarrow", true); +defineSymbol(math, main, rel, "\u2195", "\\updownarrow", true); +defineSymbol(math, main, rel, "\u21d5", "\\Updownarrow", true); +defineSymbol(math, main, op, "\u2210", "\\coprod"); +defineSymbol(math, main, op, "\u22c1", "\\bigvee"); +defineSymbol(math, main, op, "\u22c0", "\\bigwedge"); +defineSymbol(math, main, op, "\u2a04", "\\biguplus"); +defineSymbol(math, main, op, "\u22c2", "\\bigcap"); +defineSymbol(math, main, op, "\u22c3", "\\bigcup"); +defineSymbol(math, main, op, "\u222b", "\\int"); +defineSymbol(math, main, op, "\u222b", "\\intop"); +defineSymbol(math, main, op, "\u222c", "\\iint"); +defineSymbol(math, main, op, "\u222d", "\\iiint"); +defineSymbol(math, main, op, "\u220f", "\\prod"); +defineSymbol(math, main, op, "\u2211", "\\sum"); +defineSymbol(math, main, op, "\u2a02", "\\bigotimes"); +defineSymbol(math, main, op, "\u2a01", "\\bigoplus"); +defineSymbol(math, main, op, "\u2a00", "\\bigodot"); +defineSymbol(math, main, op, "\u222e", "\\oint"); +defineSymbol(math, main, op, "\u222f", "\\oiint"); +defineSymbol(math, main, op, "\u2230", "\\oiiint"); +defineSymbol(math, main, op, "\u2a06", "\\bigsqcup"); +defineSymbol(math, main, op, "\u222b", "\\smallint"); +defineSymbol(symbols_text, main, inner, "\u2026", "\\textellipsis"); +defineSymbol(math, main, inner, "\u2026", "\\mathellipsis"); +defineSymbol(symbols_text, main, inner, "\u2026", "\\ldots", true); +defineSymbol(math, main, inner, "\u2026", "\\ldots", true); +defineSymbol(math, main, inner, "\u22ef", "\\@cdots", true); +defineSymbol(math, main, inner, "\u22f1", "\\ddots", true); // \vdots is a macro that uses one of these two symbols (with made-up names): + +defineSymbol(math, main, textord, "\u22ee", "\\varvdots"); +defineSymbol(symbols_text, main, textord, "\u22ee", "\\varvdots"); +defineSymbol(math, main, accent, "\u02ca", "\\acute"); +defineSymbol(math, main, accent, "\u02cb", "\\grave"); +defineSymbol(math, main, accent, "\u00a8", "\\ddot"); +defineSymbol(math, main, accent, "\u007e", "\\tilde"); +defineSymbol(math, main, accent, "\u02c9", "\\bar"); +defineSymbol(math, main, accent, "\u02d8", "\\breve"); +defineSymbol(math, main, accent, "\u02c7", "\\check"); +defineSymbol(math, main, accent, "\u005e", "\\hat"); +defineSymbol(math, main, accent, "\u20d7", "\\vec"); +defineSymbol(math, main, accent, "\u02d9", "\\dot"); +defineSymbol(math, main, accent, "\u02da", "\\mathring"); // \imath and \jmath should be invariant to \mathrm, \mathbf, etc., so use PUA + +defineSymbol(math, main, mathord, "\ue131", "\\@imath"); +defineSymbol(math, main, mathord, "\ue237", "\\@jmath"); +defineSymbol(math, main, textord, "\u0131", "\u0131"); +defineSymbol(math, main, textord, "\u0237", "\u0237"); +defineSymbol(symbols_text, main, textord, "\u0131", "\\i", true); +defineSymbol(symbols_text, main, textord, "\u0237", "\\j", true); +defineSymbol(symbols_text, main, textord, "\u00df", "\\ss", true); +defineSymbol(symbols_text, main, textord, "\u00e6", "\\ae", true); +defineSymbol(symbols_text, main, textord, "\u0153", "\\oe", true); +defineSymbol(symbols_text, main, textord, "\u00f8", "\\o", true); +defineSymbol(symbols_text, main, textord, "\u00c6", "\\AE", true); +defineSymbol(symbols_text, main, textord, "\u0152", "\\OE", true); +defineSymbol(symbols_text, main, textord, "\u00d8", "\\O", true); +defineSymbol(symbols_text, main, accent, "\u02ca", "\\'"); // acute + +defineSymbol(symbols_text, main, accent, "\u02cb", "\\`"); // grave + +defineSymbol(symbols_text, main, accent, "\u02c6", "\\^"); // circumflex + +defineSymbol(symbols_text, main, accent, "\u02dc", "\\~"); // tilde + +defineSymbol(symbols_text, main, accent, "\u02c9", "\\="); // macron + +defineSymbol(symbols_text, main, accent, "\u02d8", "\\u"); // breve + +defineSymbol(symbols_text, main, accent, "\u02d9", "\\."); // dot above + +defineSymbol(symbols_text, main, accent, "\u00b8", "\\c"); // cedilla + +defineSymbol(symbols_text, main, accent, "\u02da", "\\r"); // ring above + +defineSymbol(symbols_text, main, accent, "\u02c7", "\\v"); // caron + +defineSymbol(symbols_text, main, accent, "\u00a8", '\\"'); // diaeresis + +defineSymbol(symbols_text, main, accent, "\u02dd", "\\H"); // double acute + +defineSymbol(symbols_text, main, accent, "\u25ef", "\\textcircled"); // \bigcirc glyph +// These ligatures are detected and created in Parser.js's `formLigatures`. + +const ligatures = { + "--": true, + "---": true, + "``": true, + "''": true +}; +defineSymbol(symbols_text, main, textord, "\u2013", "--", true); +defineSymbol(symbols_text, main, textord, "\u2013", "\\textendash"); +defineSymbol(symbols_text, main, textord, "\u2014", "---", true); +defineSymbol(symbols_text, main, textord, "\u2014", "\\textemdash"); +defineSymbol(symbols_text, main, textord, "\u2018", "`", true); +defineSymbol(symbols_text, main, textord, "\u2018", "\\textquoteleft"); +defineSymbol(symbols_text, main, textord, "\u2019", "'", true); +defineSymbol(symbols_text, main, textord, "\u2019", "\\textquoteright"); +defineSymbol(symbols_text, main, textord, "\u201c", "``", true); +defineSymbol(symbols_text, main, textord, "\u201c", "\\textquotedblleft"); +defineSymbol(symbols_text, main, textord, "\u201d", "''", true); +defineSymbol(symbols_text, main, textord, "\u201d", "\\textquotedblright"); // \degree from gensymb package + +defineSymbol(math, main, textord, "\u00b0", "\\degree", true); +defineSymbol(symbols_text, main, textord, "\u00b0", "\\degree"); // \textdegree from inputenc package + +defineSymbol(symbols_text, main, textord, "\u00b0", "\\textdegree", true); // TODO: In LaTeX, \pounds can generate a different character in text and math +// mode, but among our fonts, only Main-Regular defines this character "163". + +defineSymbol(math, main, textord, "\u00a3", "\\pounds"); +defineSymbol(math, main, textord, "\u00a3", "\\mathsterling", true); +defineSymbol(symbols_text, main, textord, "\u00a3", "\\pounds"); +defineSymbol(symbols_text, main, textord, "\u00a3", "\\textsterling", true); +defineSymbol(math, ams, textord, "\u2720", "\\maltese"); +defineSymbol(symbols_text, ams, textord, "\u2720", "\\maltese"); // There are lots of symbols which are the same, so we add them in afterwards. +// All of these are textords in math mode + +const mathTextSymbols = "0123456789/@.\""; + +for (let i = 0; i < mathTextSymbols.length; i++) { + const ch = mathTextSymbols.charAt(i); + defineSymbol(math, main, textord, ch, ch); +} // All of these are textords in text mode + + +const textSymbols = "0123456789!@*()-=+\";:?/.,"; + +for (let i = 0; i < textSymbols.length; i++) { + const ch = textSymbols.charAt(i); + defineSymbol(symbols_text, main, textord, ch, ch); +} // All of these are textords in text mode, and mathords in math mode + + +const letters = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; + +for (let i = 0; i < letters.length; i++) { + const ch = letters.charAt(i); + defineSymbol(math, main, mathord, ch, ch); + defineSymbol(symbols_text, main, textord, ch, ch); +} // Blackboard bold and script letters in Unicode range + + +defineSymbol(math, ams, textord, "C", "\u2102"); // blackboard bold + +defineSymbol(symbols_text, ams, textord, "C", "\u2102"); +defineSymbol(math, ams, textord, "H", "\u210D"); +defineSymbol(symbols_text, ams, textord, "H", "\u210D"); +defineSymbol(math, ams, textord, "N", "\u2115"); +defineSymbol(symbols_text, ams, textord, "N", "\u2115"); +defineSymbol(math, ams, textord, "P", "\u2119"); +defineSymbol(symbols_text, ams, textord, "P", "\u2119"); +defineSymbol(math, ams, textord, "Q", "\u211A"); +defineSymbol(symbols_text, ams, textord, "Q", "\u211A"); +defineSymbol(math, ams, textord, "R", "\u211D"); +defineSymbol(symbols_text, ams, textord, "R", "\u211D"); +defineSymbol(math, ams, textord, "Z", "\u2124"); +defineSymbol(symbols_text, ams, textord, "Z", "\u2124"); +defineSymbol(math, main, mathord, "h", "\u210E"); // italic h, Planck constant + +defineSymbol(symbols_text, main, mathord, "h", "\u210E"); // The next loop loads wide (surrogate pair) characters. +// We support some letters in the Unicode range U+1D400 to U+1D7FF, +// Mathematical Alphanumeric Symbols. +// Some editors do not deal well with wide characters. So don't write the +// string into this file. Instead, create the string from the surrogate pair. + +let wideChar = ""; + +for (let i = 0; i < letters.length; i++) { + const ch = letters.charAt(i); // The hex numbers in the next line are a surrogate pair. + // 0xD835 is the high surrogate for all letters in the range we support. + // 0xDC00 is the low surrogate for bold A. + + wideChar = String.fromCharCode(0xD835, 0xDC00 + i); // A-Z a-z bold + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDC34 + i); // A-Z a-z italic + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDC68 + i); // A-Z a-z bold italic + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDD04 + i); // A-Z a-z Fraktur + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDD6C + i); // A-Z a-z bold Fraktur + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDDA0 + i); // A-Z a-z sans-serif + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDDD4 + i); // A-Z a-z sans bold + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDE08 + i); // A-Z a-z sans italic + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDE70 + i); // A-Z a-z monospace + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + + if (i < 26) { + // KaTeX fonts have only capital letters for blackboard bold and script. + // See exception for k below. + wideChar = String.fromCharCode(0xD835, 0xDD38 + i); // A-Z double struck + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDC9C + i); // A-Z script + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + } // TODO: Add bold script when it is supported by a KaTeX font. + +} // "k" is the only double struck lower case letter in the KaTeX fonts. + + +wideChar = String.fromCharCode(0xD835, 0xDD5C); // k double struck + +defineSymbol(math, main, mathord, "k", wideChar); +defineSymbol(symbols_text, main, textord, "k", wideChar); // Next, some wide character numerals + +for (let i = 0; i < 10; i++) { + const ch = i.toString(); + wideChar = String.fromCharCode(0xD835, 0xDFCE + i); // 0-9 bold + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDFE2 + i); // 0-9 sans serif + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDFEC + i); // 0-9 bold sans + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDFF6 + i); // 0-9 monospace + + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(symbols_text, main, textord, ch, wideChar); +} // We add these Latin-1 letters as symbols for backwards-compatibility, +// but they are not actually in the font, nor are they supported by the +// Unicode accent mechanism, so they fall back to Times font and look ugly. +// TODO(edemaine): Fix this. + + +const extraLatin = "\u00d0\u00de\u00fe"; + +for (let i = 0; i < extraLatin.length; i++) { + const ch = extraLatin.charAt(i); + defineSymbol(math, main, mathord, ch, ch); + defineSymbol(symbols_text, main, textord, ch, ch); +} +;// CONCATENATED MODULE: ./src/wide-character.js +/** + * This file provides support for Unicode range U+1D400 to U+1D7FF, + * Mathematical Alphanumeric Symbols. + * + * Function wideCharacterFont takes a wide character as input and returns + * the font information necessary to render it properly. + */ + +/** + * Data below is from https://www.unicode.org/charts/PDF/U1D400.pdf + * That document sorts characters into groups by font type, say bold or italic. + * + * In the arrays below, each subarray consists three elements: + * * The CSS class of that group when in math mode. + * * The CSS class of that group when in text mode. + * * The font name, so that KaTeX can get font metrics. + */ + +const wideLatinLetterData = [["mathbf", "textbf", "Main-Bold"], // A-Z bold upright +["mathbf", "textbf", "Main-Bold"], // a-z bold upright +["mathnormal", "textit", "Math-Italic"], // A-Z italic +["mathnormal", "textit", "Math-Italic"], // a-z italic +["boldsymbol", "boldsymbol", "Main-BoldItalic"], // A-Z bold italic +["boldsymbol", "boldsymbol", "Main-BoldItalic"], // a-z bold italic +// Map fancy A-Z letters to script, not calligraphic. +// This aligns with unicode-math and math fonts (except Cambria Math). +["mathscr", "textscr", "Script-Regular"], // A-Z script +["", "", ""], // a-z script. No font +["", "", ""], // A-Z bold script. No font +["", "", ""], // a-z bold script. No font +["mathfrak", "textfrak", "Fraktur-Regular"], // A-Z Fraktur +["mathfrak", "textfrak", "Fraktur-Regular"], // a-z Fraktur +["mathbb", "textbb", "AMS-Regular"], // A-Z double-struck +["mathbb", "textbb", "AMS-Regular"], // k double-struck +// Note that we are using a bold font, but font metrics for regular Fraktur. +["mathboldfrak", "textboldfrak", "Fraktur-Regular"], // A-Z bold Fraktur +["mathboldfrak", "textboldfrak", "Fraktur-Regular"], // a-z bold Fraktur +["mathsf", "textsf", "SansSerif-Regular"], // A-Z sans-serif +["mathsf", "textsf", "SansSerif-Regular"], // a-z sans-serif +["mathboldsf", "textboldsf", "SansSerif-Bold"], // A-Z bold sans-serif +["mathboldsf", "textboldsf", "SansSerif-Bold"], // a-z bold sans-serif +["mathitsf", "textitsf", "SansSerif-Italic"], // A-Z italic sans-serif +["mathitsf", "textitsf", "SansSerif-Italic"], // a-z italic sans-serif +["", "", ""], // A-Z bold italic sans. No font +["", "", ""], // a-z bold italic sans. No font +["mathtt", "texttt", "Typewriter-Regular"], // A-Z monospace +["mathtt", "texttt", "Typewriter-Regular"] // a-z monospace +]; +const wideNumeralData = [["mathbf", "textbf", "Main-Bold"], // 0-9 bold +["", "", ""], // 0-9 double-struck. No KaTeX font. +["mathsf", "textsf", "SansSerif-Regular"], // 0-9 sans-serif +["mathboldsf", "textboldsf", "SansSerif-Bold"], // 0-9 bold sans-serif +["mathtt", "texttt", "Typewriter-Regular"] // 0-9 monospace +]; +const wideCharacterFont = function (wideChar, mode) { + // IE doesn't support codePointAt(). So work with the surrogate pair. + const H = wideChar.charCodeAt(0); // high surrogate + + const L = wideChar.charCodeAt(1); // low surrogate + + const codePoint = (H - 0xD800) * 0x400 + (L - 0xDC00) + 0x10000; + const j = mode === "math" ? 0 : 1; // column index for CSS class. + + if (0x1D400 <= codePoint && codePoint < 0x1D6A4) { + // wideLatinLetterData contains exactly 26 chars on each row. + // So we can calculate the relevant row. No traverse necessary. + const i = Math.floor((codePoint - 0x1D400) / 26); + return [wideLatinLetterData[i][2], wideLatinLetterData[i][j]]; + } else if (0x1D7CE <= codePoint && codePoint <= 0x1D7FF) { + // Numerals, ten per row. + const i = Math.floor((codePoint - 0x1D7CE) / 10); + return [wideNumeralData[i][2], wideNumeralData[i][j]]; + } else if (codePoint === 0x1D6A5 || codePoint === 0x1D6A6) { + // dotless i or j + return [wideLatinLetterData[0][2], wideLatinLetterData[0][j]]; + } else if (0x1D6A6 < codePoint && codePoint < 0x1D7CE) { + // Greek letters. Not supported, yet. + return ["", ""]; + } else { + // We don't support any wide characters outside 1D400–1D7FF. + throw new src_ParseError("Unsupported character: " + wideChar); + } +}; +;// CONCATENATED MODULE: ./src/buildCommon.js +/* eslint no-console:0 */ + +/** + * This module contains general functions that can be used for building + * different kinds of domTree nodes in a consistent manner. + */ + + + + + + + +/** + * Looks up the given symbol in fontMetrics, after applying any symbol + * replacements defined in symbol.js + */ +const lookupSymbol = function (value, // TODO(#963): Use a union type for this. +fontName, mode) { + // Replace the value with its replaced value from symbol.js + if (src_symbols[mode][value] && src_symbols[mode][value].replace) { + value = src_symbols[mode][value].replace; + } + + return { + value: value, + metrics: getCharacterMetrics(value, fontName, mode) + }; +}; +/** + * Makes a symbolNode after translation via the list of symbols in symbols.js. + * Correctly pulls out metrics for the character, and optionally takes a list of + * classes to be attached to the node. + * + * TODO: make argument order closer to makeSpan + * TODO: add a separate argument for math class (e.g. `mop`, `mbin`), which + * should if present come first in `classes`. + * TODO(#953): Make `options` mandatory and always pass it in. + */ + + +const makeSymbol = function (value, fontName, mode, options, classes) { + const lookup = lookupSymbol(value, fontName, mode); + const metrics = lookup.metrics; + value = lookup.value; + let symbolNode; + + if (metrics) { + let italic = metrics.italic; + + if (mode === "text" || options && options.font === "mathit") { + italic = 0; + } + + symbolNode = new SymbolNode(value, metrics.height, metrics.depth, italic, metrics.skew, metrics.width, classes); + } else { + // TODO(emily): Figure out a good way to only print this in development + typeof console !== "undefined" && console.warn("No character metrics " + ("for '" + value + "' in style '" + fontName + "' and mode '" + mode + "'")); + symbolNode = new SymbolNode(value, 0, 0, 0, 0, 0, classes); + } + + if (options) { + symbolNode.maxFontSize = options.sizeMultiplier; + + if (options.style.isTight()) { + symbolNode.classes.push("mtight"); + } + + const color = options.getColor(); + + if (color) { + symbolNode.style.color = color; + } + } + + return symbolNode; +}; +/** + * Makes a symbol in Main-Regular or AMS-Regular. + * Used for rel, bin, open, close, inner, and punct. + */ + + +const mathsym = function (value, mode, options, classes) { + if (classes === void 0) { + classes = []; + } + + // Decide what font to render the symbol in by its entry in the symbols + // table. + // Have a special case for when the value = \ because the \ is used as a + // textord in unsupported command errors but cannot be parsed as a regular + // text ordinal and is therefore not present as a symbol in the symbols + // table for text, as well as a special case for boldsymbol because it + // can be used for bold + and - + if (options.font === "boldsymbol" && lookupSymbol(value, "Main-Bold", mode).metrics) { + return makeSymbol(value, "Main-Bold", mode, options, classes.concat(["mathbf"])); + } else if (value === "\\" || src_symbols[mode][value].font === "main") { + return makeSymbol(value, "Main-Regular", mode, options, classes); + } else { + return makeSymbol(value, "AMS-Regular", mode, options, classes.concat(["amsrm"])); + } +}; +/** + * Determines which of the two font names (Main-Bold and Math-BoldItalic) and + * corresponding style tags (mathbf or boldsymbol) to use for font "boldsymbol", + * depending on the symbol. Use this function instead of fontMap for font + * "boldsymbol". + */ + + +const boldsymbol = function (value, mode, options, classes, type) { + if (type !== "textord" && lookupSymbol(value, "Math-BoldItalic", mode).metrics) { + return { + fontName: "Math-BoldItalic", + fontClass: "boldsymbol" + }; + } else { + // Some glyphs do not exist in Math-BoldItalic so we need to use + // Main-Bold instead. + return { + fontName: "Main-Bold", + fontClass: "mathbf" + }; + } +}; +/** + * Makes either a mathord or textord in the correct font and color. + */ + + +const makeOrd = function (group, options, type) { + const mode = group.mode; + const text = group.text; + const classes = ["mord"]; // Math mode or Old font (i.e. \rm) + + const isFont = mode === "math" || mode === "text" && options.font; + const fontOrFamily = isFont ? options.font : options.fontFamily; + let wideFontName = ""; + let wideFontClass = ""; + + if (text.charCodeAt(0) === 0xD835) { + [wideFontName, wideFontClass] = wideCharacterFont(text, mode); + } + + if (wideFontName.length > 0) { + // surrogate pairs get special treatment + return makeSymbol(text, wideFontName, mode, options, classes.concat(wideFontClass)); + } else if (fontOrFamily) { + let fontName; + let fontClasses; + + if (fontOrFamily === "boldsymbol") { + const fontData = boldsymbol(text, mode, options, classes, type); + fontName = fontData.fontName; + fontClasses = [fontData.fontClass]; + } else if (isFont) { + fontName = fontMap[fontOrFamily].fontName; + fontClasses = [fontOrFamily]; + } else { + fontName = retrieveTextFontName(fontOrFamily, options.fontWeight, options.fontShape); + fontClasses = [fontOrFamily, options.fontWeight, options.fontShape]; + } + + if (lookupSymbol(text, fontName, mode).metrics) { + return makeSymbol(text, fontName, mode, options, classes.concat(fontClasses)); + } else if (ligatures.hasOwnProperty(text) && fontName.slice(0, 10) === "Typewriter") { + // Deconstruct ligatures in monospace fonts (\texttt, \tt). + const parts = []; + + for (let i = 0; i < text.length; i++) { + parts.push(makeSymbol(text[i], fontName, mode, options, classes.concat(fontClasses))); + } + + return makeFragment(parts); + } + } // Makes a symbol in the default font for mathords and textords. + + + if (type === "mathord") { + return makeSymbol(text, "Math-Italic", mode, options, classes.concat(["mathnormal"])); + } else if (type === "textord") { + const font = src_symbols[mode][text] && src_symbols[mode][text].font; + + if (font === "ams") { + const fontName = retrieveTextFontName("amsrm", options.fontWeight, options.fontShape); + return makeSymbol(text, fontName, mode, options, classes.concat("amsrm", options.fontWeight, options.fontShape)); + } else if (font === "main" || !font) { + const fontName = retrieveTextFontName("textrm", options.fontWeight, options.fontShape); + return makeSymbol(text, fontName, mode, options, classes.concat(options.fontWeight, options.fontShape)); + } else { + // fonts added by plugins + const fontName = retrieveTextFontName(font, options.fontWeight, options.fontShape); // We add font name as a css class + + return makeSymbol(text, fontName, mode, options, classes.concat(fontName, options.fontWeight, options.fontShape)); + } + } else { + throw new Error("unexpected type: " + type + " in makeOrd"); + } +}; +/** + * Returns true if subsequent symbolNodes have the same classes, skew, maxFont, + * and styles. + */ + + +const canCombine = (prev, next) => { + if (createClass(prev.classes) !== createClass(next.classes) || prev.skew !== next.skew || prev.maxFontSize !== next.maxFontSize) { + return false; + } // If prev and next both are just "mbin"s or "mord"s we don't combine them + // so that the proper spacing can be preserved. + + + if (prev.classes.length === 1) { + const cls = prev.classes[0]; + + if (cls === "mbin" || cls === "mord") { + return false; + } + } + + for (const style in prev.style) { + if (prev.style.hasOwnProperty(style) && prev.style[style] !== next.style[style]) { + return false; + } + } + + for (const style in next.style) { + if (next.style.hasOwnProperty(style) && prev.style[style] !== next.style[style]) { + return false; + } + } + + return true; +}; +/** + * Combine consecutive domTree.symbolNodes into a single symbolNode. + * Note: this function mutates the argument. + */ + + +const tryCombineChars = chars => { + for (let i = 0; i < chars.length - 1; i++) { + const prev = chars[i]; + const next = chars[i + 1]; + + if (prev instanceof SymbolNode && next instanceof SymbolNode && canCombine(prev, next)) { + prev.text += next.text; + prev.height = Math.max(prev.height, next.height); + prev.depth = Math.max(prev.depth, next.depth); // Use the last character's italic correction since we use + // it to add padding to the right of the span created from + // the combined characters. + + prev.italic = next.italic; + chars.splice(i + 1, 1); + i--; + } + } + + return chars; +}; +/** + * Calculate the height, depth, and maxFontSize of an element based on its + * children. + */ + + +const sizeElementFromChildren = function (elem) { + let height = 0; + let depth = 0; + let maxFontSize = 0; + + for (let i = 0; i < elem.children.length; i++) { + const child = elem.children[i]; + + if (child.height > height) { + height = child.height; + } + + if (child.depth > depth) { + depth = child.depth; + } + + if (child.maxFontSize > maxFontSize) { + maxFontSize = child.maxFontSize; + } + } + + elem.height = height; + elem.depth = depth; + elem.maxFontSize = maxFontSize; +}; +/** + * Makes a span with the given list of classes, list of children, and options. + * + * TODO(#953): Ensure that `options` is always provided (currently some call + * sites don't pass it) and make the type below mandatory. + * TODO: add a separate argument for math class (e.g. `mop`, `mbin`), which + * should if present come first in `classes`. + */ + + +const makeSpan = function (classes, children, options, style) { + const span = new Span(classes, children, options, style); + sizeElementFromChildren(span); + return span; +}; // SVG one is simpler -- doesn't require height, depth, max-font setting. +// This is also a separate method for typesafety. + + +const makeSvgSpan = (classes, children, options, style) => new Span(classes, children, options, style); + +const makeLineSpan = function (className, options, thickness) { + const line = makeSpan([className], [], options); + line.height = Math.max(thickness || options.fontMetrics().defaultRuleThickness, options.minRuleThickness); + line.style.borderBottomWidth = makeEm(line.height); + line.maxFontSize = 1.0; + return line; +}; +/** + * Makes an anchor with the given href, list of classes, list of children, + * and options. + */ + + +const makeAnchor = function (href, classes, children, options) { + const anchor = new Anchor(href, classes, children, options); + sizeElementFromChildren(anchor); + return anchor; +}; +/** + * Makes a document fragment with the given list of children. + */ + + +const makeFragment = function (children) { + const fragment = new DocumentFragment(children); + sizeElementFromChildren(fragment); + return fragment; +}; +/** + * Wraps group in a span if it's a document fragment, allowing to apply classes + * and styles + */ + + +const wrapFragment = function (group, options) { + if (group instanceof DocumentFragment) { + return makeSpan([], [group], options); + } + + return group; +}; // These are exact object types to catch typos in the names of the optional fields. + + +// Computes the updated `children` list and the overall depth. +// +// This helper function for makeVList makes it easier to enforce type safety by +// allowing early exits (returns) in the logic. +const getVListChildrenAndDepth = function (params) { + if (params.positionType === "individualShift") { + const oldChildren = params.children; + const children = [oldChildren[0]]; // Add in kerns to the list of params.children to get each element to be + // shifted to the correct specified shift + + const depth = -oldChildren[0].shift - oldChildren[0].elem.depth; + let currPos = depth; + + for (let i = 1; i < oldChildren.length; i++) { + const diff = -oldChildren[i].shift - currPos - oldChildren[i].elem.depth; + const size = diff - (oldChildren[i - 1].elem.height + oldChildren[i - 1].elem.depth); + currPos = currPos + diff; + children.push({ + type: "kern", + size + }); + children.push(oldChildren[i]); + } + + return { + children, + depth + }; + } + + let depth; + + if (params.positionType === "top") { + // We always start at the bottom, so calculate the bottom by adding up + // all the sizes + let bottom = params.positionData; + + for (let i = 0; i < params.children.length; i++) { + const child = params.children[i]; + bottom -= child.type === "kern" ? child.size : child.elem.height + child.elem.depth; + } + + depth = bottom; + } else if (params.positionType === "bottom") { + depth = -params.positionData; + } else { + const firstChild = params.children[0]; + + if (firstChild.type !== "elem") { + throw new Error('First child must have type "elem".'); + } + + if (params.positionType === "shift") { + depth = -firstChild.elem.depth - params.positionData; + } else if (params.positionType === "firstBaseline") { + depth = -firstChild.elem.depth; + } else { + throw new Error("Invalid positionType " + params.positionType + "."); + } + } + + return { + children: params.children, + depth + }; +}; +/** + * Makes a vertical list by stacking elements and kerns on top of each other. + * Allows for many different ways of specifying the positioning method. + * + * See VListParam documentation above. + */ + + +const makeVList = function (params, options) { + const { + children, + depth + } = getVListChildrenAndDepth(params); // Create a strut that is taller than any list item. The strut is added to + // each item, where it will determine the item's baseline. Since it has + // `overflow:hidden`, the strut's top edge will sit on the item's line box's + // top edge and the strut's bottom edge will sit on the item's baseline, + // with no additional line-height spacing. This allows the item baseline to + // be positioned precisely without worrying about font ascent and + // line-height. + + let pstrutSize = 0; + + for (let i = 0; i < children.length; i++) { + const child = children[i]; + + if (child.type === "elem") { + const elem = child.elem; + pstrutSize = Math.max(pstrutSize, elem.maxFontSize, elem.height); + } + } + + pstrutSize += 2; + const pstrut = makeSpan(["pstrut"], []); + pstrut.style.height = makeEm(pstrutSize); // Create a new list of actual children at the correct offsets + + const realChildren = []; + let minPos = depth; + let maxPos = depth; + let currPos = depth; + + for (let i = 0; i < children.length; i++) { + const child = children[i]; + + if (child.type === "kern") { + currPos += child.size; + } else { + const elem = child.elem; + const classes = child.wrapperClasses || []; + const style = child.wrapperStyle || {}; + const childWrap = makeSpan(classes, [pstrut, elem], undefined, style); + childWrap.style.top = makeEm(-pstrutSize - currPos - elem.depth); + + if (child.marginLeft) { + childWrap.style.marginLeft = child.marginLeft; + } + + if (child.marginRight) { + childWrap.style.marginRight = child.marginRight; + } + + realChildren.push(childWrap); + currPos += elem.height + elem.depth; + } + + minPos = Math.min(minPos, currPos); + maxPos = Math.max(maxPos, currPos); + } // The vlist contents go in a table-cell with `vertical-align:bottom`. + // This cell's bottom edge will determine the containing table's baseline + // without overly expanding the containing line-box. + + + const vlist = makeSpan(["vlist"], realChildren); + vlist.style.height = makeEm(maxPos); // A second row is used if necessary to represent the vlist's depth. + + let rows; + + if (minPos < 0) { + // We will define depth in an empty span with display: table-cell. + // It should render with the height that we define. But Chrome, in + // contenteditable mode only, treats that span as if it contains some + // text content. And that min-height over-rides our desired height. + // So we put another empty span inside the depth strut span. + const emptySpan = makeSpan([], []); + const depthStrut = makeSpan(["vlist"], [emptySpan]); + depthStrut.style.height = makeEm(-minPos); // Safari wants the first row to have inline content; otherwise it + // puts the bottom of the *second* row on the baseline. + + const topStrut = makeSpan(["vlist-s"], [new SymbolNode("\u200b")]); + rows = [makeSpan(["vlist-r"], [vlist, topStrut]), makeSpan(["vlist-r"], [depthStrut])]; + } else { + rows = [makeSpan(["vlist-r"], [vlist])]; + } + + const vtable = makeSpan(["vlist-t"], rows); + + if (rows.length === 2) { + vtable.classes.push("vlist-t2"); + } + + vtable.height = maxPos; + vtable.depth = -minPos; + return vtable; +}; // Glue is a concept from TeX which is a flexible space between elements in +// either a vertical or horizontal list. In KaTeX, at least for now, it's +// static space between elements in a horizontal layout. + + +const makeGlue = (measurement, options) => { + // Make an empty span for the space + const rule = makeSpan(["mspace"], [], options); + const size = calculateSize(measurement, options); + rule.style.marginRight = makeEm(size); + return rule; +}; // Takes font options, and returns the appropriate fontLookup name + + +const retrieveTextFontName = function (fontFamily, fontWeight, fontShape) { + let baseFontName = ""; + + switch (fontFamily) { + case "amsrm": + baseFontName = "AMS"; + break; + + case "textrm": + baseFontName = "Main"; + break; + + case "textsf": + baseFontName = "SansSerif"; + break; + + case "texttt": + baseFontName = "Typewriter"; + break; + + default: + baseFontName = fontFamily; + // use fonts added by a plugin + } + + let fontStylesName; + + if (fontWeight === "textbf" && fontShape === "textit") { + fontStylesName = "BoldItalic"; + } else if (fontWeight === "textbf") { + fontStylesName = "Bold"; + } else if (fontWeight === "textit") { + fontStylesName = "Italic"; + } else { + fontStylesName = "Regular"; + } + + return baseFontName + "-" + fontStylesName; +}; +/** + * Maps TeX font commands to objects containing: + * - variant: string used for "mathvariant" attribute in buildMathML.js + * - fontName: the "style" parameter to fontMetrics.getCharacterMetrics + */ +// A map between tex font commands an MathML mathvariant attribute values + + +const fontMap = { + // styles + "mathbf": { + variant: "bold", + fontName: "Main-Bold" + }, + "mathrm": { + variant: "normal", + fontName: "Main-Regular" + }, + "textit": { + variant: "italic", + fontName: "Main-Italic" + }, + "mathit": { + variant: "italic", + fontName: "Main-Italic" + }, + "mathnormal": { + variant: "italic", + fontName: "Math-Italic" + }, + "mathsfit": { + variant: "sans-serif-italic", + fontName: "SansSerif-Italic" + }, + // "boldsymbol" is missing because they require the use of multiple fonts: + // Math-BoldItalic and Main-Bold. This is handled by a special case in + // makeOrd which ends up calling boldsymbol. + // families + "mathbb": { + variant: "double-struck", + fontName: "AMS-Regular" + }, + "mathcal": { + variant: "script", + fontName: "Caligraphic-Regular" + }, + "mathfrak": { + variant: "fraktur", + fontName: "Fraktur-Regular" + }, + "mathscr": { + variant: "script", + fontName: "Script-Regular" + }, + "mathsf": { + variant: "sans-serif", + fontName: "SansSerif-Regular" + }, + "mathtt": { + variant: "monospace", + fontName: "Typewriter-Regular" + } +}; +const svgData = { + // path, width, height + vec: ["vec", 0.471, 0.714], + // values from the font glyph + oiintSize1: ["oiintSize1", 0.957, 0.499], + // oval to overlay the integrand + oiintSize2: ["oiintSize2", 1.472, 0.659], + oiiintSize1: ["oiiintSize1", 1.304, 0.499], + oiiintSize2: ["oiiintSize2", 1.98, 0.659] +}; + +const staticSvg = function (value, options) { + // Create a span with inline SVG for the element. + const [pathName, width, height] = svgData[value]; + const path = new PathNode(pathName); + const svgNode = new SvgNode([path], { + "width": makeEm(width), + "height": makeEm(height), + // Override CSS rule `.katex svg { width: 100% }` + "style": "width:" + makeEm(width), + "viewBox": "0 0 " + 1000 * width + " " + 1000 * height, + "preserveAspectRatio": "xMinYMin" + }); + const span = makeSvgSpan(["overlay"], [svgNode], options); + span.height = height; + span.style.height = makeEm(height); + span.style.width = makeEm(width); + return span; +}; + +/* harmony default export */ var buildCommon = ({ + fontMap, + makeSymbol, + mathsym, + makeSpan, + makeSvgSpan, + makeLineSpan, + makeAnchor, + makeFragment, + wrapFragment, + makeVList, + makeOrd, + makeGlue, + staticSvg, + svgData, + tryCombineChars +}); +;// CONCATENATED MODULE: ./src/spacingData.js +/** + * Describes spaces between different classes of atoms. + */ +const thinspace = { + number: 3, + unit: "mu" +}; +const mediumspace = { + number: 4, + unit: "mu" +}; +const thickspace = { + number: 5, + unit: "mu" +}; // Making the type below exact with all optional fields doesn't work due to +// - https://github.com/facebook/flow/issues/4582 +// - https://github.com/facebook/flow/issues/5688 +// However, since *all* fields are optional, $Shape<> works as suggested in 5688 +// above. + +// Spacing relationships for display and text styles +const spacings = { + mord: { + mop: thinspace, + mbin: mediumspace, + mrel: thickspace, + minner: thinspace + }, + mop: { + mord: thinspace, + mop: thinspace, + mrel: thickspace, + minner: thinspace + }, + mbin: { + mord: mediumspace, + mop: mediumspace, + mopen: mediumspace, + minner: mediumspace + }, + mrel: { + mord: thickspace, + mop: thickspace, + mopen: thickspace, + minner: thickspace + }, + mopen: {}, + mclose: { + mop: thinspace, + mbin: mediumspace, + mrel: thickspace, + minner: thinspace + }, + mpunct: { + mord: thinspace, + mop: thinspace, + mrel: thickspace, + mopen: thinspace, + mclose: thinspace, + mpunct: thinspace, + minner: thinspace + }, + minner: { + mord: thinspace, + mop: thinspace, + mbin: mediumspace, + mrel: thickspace, + mopen: thinspace, + mpunct: thinspace, + minner: thinspace + } +}; // Spacing relationships for script and scriptscript styles + +const tightSpacings = { + mord: { + mop: thinspace + }, + mop: { + mord: thinspace, + mop: thinspace + }, + mbin: {}, + mrel: {}, + mopen: {}, + mclose: { + mop: thinspace + }, + mpunct: {}, + minner: { + mop: thinspace + } +}; +;// CONCATENATED MODULE: ./src/defineFunction.js +/** Context provided to function handlers for error messages. */ +// Note: reverse the order of the return type union will cause a flow error. +// See https://github.com/facebook/flow/issues/3663. +// More general version of `HtmlBuilder` for nodes (e.g. \sum, accent types) +// whose presence impacts super/subscripting. In this case, ParseNode<"supsub"> +// delegates its HTML building to the HtmlBuilder corresponding to these nodes. + +/** + * Final function spec for use at parse time. + * This is almost identical to `FunctionPropSpec`, except it + * 1. includes the function handler, and + * 2. requires all arguments except argTypes. + * It is generated by `defineFunction()` below. + */ + +/** + * All registered functions. + * `functions.js` just exports this same dictionary again and makes it public. + * `Parser.js` requires this dictionary. + */ +const _functions = {}; +/** + * All HTML builders. Should be only used in the `define*` and the `build*ML` + * functions. + */ + +const _htmlGroupBuilders = {}; +/** + * All MathML builders. Should be only used in the `define*` and the `build*ML` + * functions. + */ + +const _mathmlGroupBuilders = {}; +function defineFunction(_ref) { + let { + type, + names, + props, + handler, + htmlBuilder, + mathmlBuilder + } = _ref; + // Set default values of functions + const data = { + type, + numArgs: props.numArgs, + argTypes: props.argTypes, + allowedInArgument: !!props.allowedInArgument, + allowedInText: !!props.allowedInText, + allowedInMath: props.allowedInMath === undefined ? true : props.allowedInMath, + numOptionalArgs: props.numOptionalArgs || 0, + infix: !!props.infix, + primitive: !!props.primitive, + handler: handler + }; + + for (let i = 0; i < names.length; ++i) { + _functions[names[i]] = data; + } + + if (type) { + if (htmlBuilder) { + _htmlGroupBuilders[type] = htmlBuilder; + } + + if (mathmlBuilder) { + _mathmlGroupBuilders[type] = mathmlBuilder; + } + } +} +/** + * Use this to register only the HTML and MathML builders for a function (e.g. + * if the function's ParseNode is generated in Parser.js rather than via a + * stand-alone handler provided to `defineFunction`). + */ + +function defineFunctionBuilders(_ref2) { + let { + type, + htmlBuilder, + mathmlBuilder + } = _ref2; + defineFunction({ + type, + names: [], + props: { + numArgs: 0 + }, + + handler() { + throw new Error('Should never be called.'); + }, + + htmlBuilder, + mathmlBuilder + }); +} +const normalizeArgument = function (arg) { + return arg.type === "ordgroup" && arg.body.length === 1 ? arg.body[0] : arg; +}; // Since the corresponding buildHTML/buildMathML function expects a +// list of elements, we normalize for different kinds of arguments + +const ordargument = function (arg) { + return arg.type === "ordgroup" ? arg.body : [arg]; +}; +;// CONCATENATED MODULE: ./src/buildHTML.js +/** + * This file does the main work of building a domTree structure from a parse + * tree. The entry point is the `buildHTML` function, which takes a parse tree. + * Then, the buildExpression, buildGroup, and various groupBuilders functions + * are called, to produce a final HTML tree. + */ + + + + + + + + + +const buildHTML_makeSpan = buildCommon.makeSpan; // Binary atoms (first class `mbin`) change into ordinary atoms (`mord`) +// depending on their surroundings. See TeXbook pg. 442-446, Rules 5 and 6, +// and the text before Rule 19. + +const binLeftCanceller = ["leftmost", "mbin", "mopen", "mrel", "mop", "mpunct"]; +const binRightCanceller = ["rightmost", "mrel", "mclose", "mpunct"]; +const styleMap = { + "display": src_Style.DISPLAY, + "text": src_Style.TEXT, + "script": src_Style.SCRIPT, + "scriptscript": src_Style.SCRIPTSCRIPT +}; +const DomEnum = { + mord: "mord", + mop: "mop", + mbin: "mbin", + mrel: "mrel", + mopen: "mopen", + mclose: "mclose", + mpunct: "mpunct", + minner: "minner" +}; + +/** + * Take a list of nodes, build them in order, and return a list of the built + * nodes. documentFragments are flattened into their contents, so the + * returned list contains no fragments. `isRealGroup` is true if `expression` + * is a real group (no atoms will be added on either side), as opposed to + * a partial group (e.g. one created by \color). `surrounding` is an array + * consisting type of nodes that will be added to the left and right. + */ +const buildExpression = function (expression, options, isRealGroup, surrounding) { + if (surrounding === void 0) { + surrounding = [null, null]; + } + + // Parse expressions into `groups`. + const groups = []; + + for (let i = 0; i < expression.length; i++) { + const output = buildGroup(expression[i], options); + + if (output instanceof DocumentFragment) { + const children = output.children; + groups.push(...children); + } else { + groups.push(output); + } + } // Combine consecutive domTree.symbolNodes into a single symbolNode. + + + buildCommon.tryCombineChars(groups); // If `expression` is a partial group, let the parent handle spacings + // to avoid processing groups multiple times. + + if (!isRealGroup) { + return groups; + } + + let glueOptions = options; + + if (expression.length === 1) { + const node = expression[0]; + + if (node.type === "sizing") { + glueOptions = options.havingSize(node.size); + } else if (node.type === "styling") { + glueOptions = options.havingStyle(styleMap[node.style]); + } + } // Dummy spans for determining spacings between surrounding atoms. + // If `expression` has no atoms on the left or right, class "leftmost" + // or "rightmost", respectively, is used to indicate it. + + + const dummyPrev = buildHTML_makeSpan([surrounding[0] || "leftmost"], [], options); + const dummyNext = buildHTML_makeSpan([surrounding[1] || "rightmost"], [], options); // TODO: These code assumes that a node's math class is the first element + // of its `classes` array. A later cleanup should ensure this, for + // instance by changing the signature of `makeSpan`. + // Before determining what spaces to insert, perform bin cancellation. + // Binary operators change to ordinary symbols in some contexts. + + const isRoot = isRealGroup === "root"; + traverseNonSpaceNodes(groups, (node, prev) => { + const prevType = prev.classes[0]; + const type = node.classes[0]; + + if (prevType === "mbin" && utils.contains(binRightCanceller, type)) { + prev.classes[0] = "mord"; + } else if (type === "mbin" && utils.contains(binLeftCanceller, prevType)) { + node.classes[0] = "mord"; + } + }, { + node: dummyPrev + }, dummyNext, isRoot); + traverseNonSpaceNodes(groups, (node, prev) => { + const prevType = getTypeOfDomTree(prev); + const type = getTypeOfDomTree(node); // 'mtight' indicates that the node is script or scriptscript style. + + const space = prevType && type ? node.hasClass("mtight") ? tightSpacings[prevType][type] : spacings[prevType][type] : null; + + if (space) { + // Insert glue (spacing) after the `prev`. + return buildCommon.makeGlue(space, glueOptions); + } + }, { + node: dummyPrev + }, dummyNext, isRoot); + return groups; +}; // Depth-first traverse non-space `nodes`, calling `callback` with the current and +// previous node as arguments, optionally returning a node to insert after the +// previous node. `prev` is an object with the previous node and `insertAfter` +// function to insert after it. `next` is a node that will be added to the right. +// Used for bin cancellation and inserting spacings. + +const traverseNonSpaceNodes = function (nodes, callback, prev, next, isRoot) { + if (next) { + // temporarily append the right node, if exists + nodes.push(next); + } + + let i = 0; + + for (; i < nodes.length; i++) { + const node = nodes[i]; + const partialGroup = checkPartialGroup(node); + + if (partialGroup) { + // Recursive DFS + // $FlowFixMe: make nodes a $ReadOnlyArray by returning a new array + traverseNonSpaceNodes(partialGroup.children, callback, prev, null, isRoot); + continue; + } // Ignore explicit spaces (e.g., \;, \,) when determining what implicit + // spacing should go between atoms of different classes + + + const nonspace = !node.hasClass("mspace"); + + if (nonspace) { + const result = callback(node, prev.node); + + if (result) { + if (prev.insertAfter) { + prev.insertAfter(result); + } else { + // insert at front + nodes.unshift(result); + i++; + } + } + } + + if (nonspace) { + prev.node = node; + } else if (isRoot && node.hasClass("newline")) { + prev.node = buildHTML_makeSpan(["leftmost"]); // treat like beginning of line + } + + prev.insertAfter = (index => n => { + nodes.splice(index + 1, 0, n); + i++; + })(i); + } + + if (next) { + nodes.pop(); + } +}; // Check if given node is a partial group, i.e., does not affect spacing around. + + +const checkPartialGroup = function (node) { + if (node instanceof DocumentFragment || node instanceof Anchor || node instanceof Span && node.hasClass("enclosing")) { + return node; + } + + return null; +}; // Return the outermost node of a domTree. + + +const getOutermostNode = function (node, side) { + const partialGroup = checkPartialGroup(node); + + if (partialGroup) { + const children = partialGroup.children; + + if (children.length) { + if (side === "right") { + return getOutermostNode(children[children.length - 1], "right"); + } else if (side === "left") { + return getOutermostNode(children[0], "left"); + } + } + } + + return node; +}; // Return math atom class (mclass) of a domTree. +// If `side` is given, it will get the type of the outermost node at given side. + + +const getTypeOfDomTree = function (node, side) { + if (!node) { + return null; + } + + if (side) { + node = getOutermostNode(node, side); + } // This makes a lot of assumptions as to where the type of atom + // appears. We should do a better job of enforcing this. + + + return DomEnum[node.classes[0]] || null; +}; +const makeNullDelimiter = function (options, classes) { + const moreClasses = ["nulldelimiter"].concat(options.baseSizingClasses()); + return buildHTML_makeSpan(classes.concat(moreClasses)); +}; +/** + * buildGroup is the function that takes a group and calls the correct groupType + * function for it. It also handles the interaction of size and style changes + * between parents and children. + */ + +const buildGroup = function (group, options, baseOptions) { + if (!group) { + return buildHTML_makeSpan(); + } + + if (_htmlGroupBuilders[group.type]) { + // Call the groupBuilders function + // $FlowFixMe + let groupNode = _htmlGroupBuilders[group.type](group, options); // If the size changed between the parent and the current group, account + // for that size difference. + + if (baseOptions && options.size !== baseOptions.size) { + groupNode = buildHTML_makeSpan(options.sizingClasses(baseOptions), [groupNode], options); + const multiplier = options.sizeMultiplier / baseOptions.sizeMultiplier; + groupNode.height *= multiplier; + groupNode.depth *= multiplier; + } + + return groupNode; + } else { + throw new src_ParseError("Got group of unknown type: '" + group.type + "'"); + } +}; +/** + * Combine an array of HTML DOM nodes (e.g., the output of `buildExpression`) + * into an unbreakable HTML node of class .base, with proper struts to + * guarantee correct vertical extent. `buildHTML` calls this repeatedly to + * make up the entire expression as a sequence of unbreakable units. + */ + +function buildHTMLUnbreakable(children, options) { + // Compute height and depth of this chunk. + const body = buildHTML_makeSpan(["base"], children, options); // Add strut, which ensures that the top of the HTML element falls at + // the height of the expression, and the bottom of the HTML element + // falls at the depth of the expression. + + const strut = buildHTML_makeSpan(["strut"]); + strut.style.height = makeEm(body.height + body.depth); + + if (body.depth) { + strut.style.verticalAlign = makeEm(-body.depth); + } + + body.children.unshift(strut); + return body; +} +/** + * Take an entire parse tree, and build it into an appropriate set of HTML + * nodes. + */ + + +function buildHTML(tree, options) { + // Strip off outer tag wrapper for processing below. + let tag = null; + + if (tree.length === 1 && tree[0].type === "tag") { + tag = tree[0].tag; + tree = tree[0].body; + } // Build the expression contained in the tree + + + const expression = buildExpression(tree, options, "root"); + let eqnNum; + + if (expression.length === 2 && expression[1].hasClass("tag")) { + // An environment with automatic equation numbers, e.g. {gather}. + eqnNum = expression.pop(); + } + + const children = []; // Create one base node for each chunk between potential line breaks. + // The TeXBook [p.173] says "A formula will be broken only after a + // relation symbol like $=$ or $<$ or $\rightarrow$, or after a binary + // operation symbol like $+$ or $-$ or $\times$, where the relation or + // binary operation is on the ``outer level'' of the formula (i.e., not + // enclosed in {...} and not part of an \over construction)." + + let parts = []; + + for (let i = 0; i < expression.length; i++) { + parts.push(expression[i]); + + if (expression[i].hasClass("mbin") || expression[i].hasClass("mrel") || expression[i].hasClass("allowbreak")) { + // Put any post-operator glue on same line as operator. + // Watch for \nobreak along the way, and stop at \newline. + let nobreak = false; + + while (i < expression.length - 1 && expression[i + 1].hasClass("mspace") && !expression[i + 1].hasClass("newline")) { + i++; + parts.push(expression[i]); + + if (expression[i].hasClass("nobreak")) { + nobreak = true; + } + } // Don't allow break if \nobreak among the post-operator glue. + + + if (!nobreak) { + children.push(buildHTMLUnbreakable(parts, options)); + parts = []; + } + } else if (expression[i].hasClass("newline")) { + // Write the line except the newline + parts.pop(); + + if (parts.length > 0) { + children.push(buildHTMLUnbreakable(parts, options)); + parts = []; + } // Put the newline at the top level + + + children.push(expression[i]); + } + } + + if (parts.length > 0) { + children.push(buildHTMLUnbreakable(parts, options)); + } // Now, if there was a tag, build it too and append it as a final child. + + + let tagChild; + + if (tag) { + tagChild = buildHTMLUnbreakable(buildExpression(tag, options, true)); + tagChild.classes = ["tag"]; + children.push(tagChild); + } else if (eqnNum) { + children.push(eqnNum); + } + + const htmlNode = buildHTML_makeSpan(["katex-html"], children); + htmlNode.setAttribute("aria-hidden", "true"); // Adjust the strut of the tag to be the maximum height of all children + // (the height of the enclosing htmlNode) for proper vertical alignment. + + if (tagChild) { + const strut = tagChild.children[0]; + strut.style.height = makeEm(htmlNode.height + htmlNode.depth); + + if (htmlNode.depth) { + strut.style.verticalAlign = makeEm(-htmlNode.depth); + } + } + + return htmlNode; +} +;// CONCATENATED MODULE: ./src/mathMLTree.js +/** + * These objects store data about MathML nodes. This is the MathML equivalent + * of the types in domTree.js. Since MathML handles its own rendering, and + * since we're mainly using MathML to improve accessibility, we don't manage + * any of the styling state that the plain DOM nodes do. + * + * The `toNode` and `toMarkup` functions work similarly to how they do in + * domTree.js, creating namespaced DOM nodes and HTML text markup respectively. + */ + + + + +function newDocumentFragment(children) { + return new DocumentFragment(children); +} +/** + * This node represents a general purpose MathML node of any type. The + * constructor requires the type of node to create (for example, `"mo"` or + * `"mspace"`, corresponding to `` and `` tags). + */ + +class MathNode { + constructor(type, children, classes) { + this.type = void 0; + this.attributes = void 0; + this.children = void 0; + this.classes = void 0; + this.type = type; + this.attributes = {}; + this.children = children || []; + this.classes = classes || []; + } + /** + * Sets an attribute on a MathML node. MathML depends on attributes to convey a + * semantic content, so this is used heavily. + */ + + + setAttribute(name, value) { + this.attributes[name] = value; + } + /** + * Gets an attribute on a MathML node. + */ + + + getAttribute(name) { + return this.attributes[name]; + } + /** + * Converts the math node into a MathML-namespaced DOM element. + */ + + + toNode() { + const node = document.createElementNS("http://www.w3.org/1998/Math/MathML", this.type); + + for (const attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } + + if (this.classes.length > 0) { + node.className = createClass(this.classes); + } + + for (let i = 0; i < this.children.length; i++) { + // Combine multiple TextNodes into one TextNode, to prevent + // screen readers from reading each as a separate word [#3995] + if (this.children[i] instanceof TextNode && this.children[i + 1] instanceof TextNode) { + let text = this.children[i].toText() + this.children[++i].toText(); + + while (this.children[i + 1] instanceof TextNode) { + text += this.children[++i].toText(); + } + + node.appendChild(new TextNode(text).toNode()); + } else { + node.appendChild(this.children[i].toNode()); + } + } + + return node; + } + /** + * Converts the math node into an HTML markup string. + */ + + + toMarkup() { + let markup = "<" + this.type; // Add the attributes + + for (const attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + markup += " " + attr + "=\""; + markup += utils.escape(this.attributes[attr]); + markup += "\""; + } + } + + if (this.classes.length > 0) { + markup += " class =\"" + utils.escape(createClass(this.classes)) + "\""; + } + + markup += ">"; + + for (let i = 0; i < this.children.length; i++) { + markup += this.children[i].toMarkup(); + } + + markup += ""; + return markup; + } + /** + * Converts the math node into a string, similar to innerText, but escaped. + */ + + + toText() { + return this.children.map(child => child.toText()).join(""); + } + +} +/** + * This node represents a piece of text. + */ + +class TextNode { + constructor(text) { + this.text = void 0; + this.text = text; + } + /** + * Converts the text node into a DOM text node. + */ + + + toNode() { + return document.createTextNode(this.text); + } + /** + * Converts the text node into escaped HTML markup + * (representing the text itself). + */ + + + toMarkup() { + return utils.escape(this.toText()); + } + /** + * Converts the text node into a string + * (representing the text itself). + */ + + + toText() { + return this.text; + } + +} +/** + * This node represents a space, but may render as or as text, + * depending on the width. + */ + +class SpaceNode { + /** + * Create a Space node with width given in CSS ems. + */ + constructor(width) { + this.width = void 0; + this.character = void 0; + this.width = width; // See https://www.w3.org/TR/2000/WD-MathML2-20000328/chapter6.html + // for a table of space-like characters. We use Unicode + // representations instead of &LongNames; as it's not clear how to + // make the latter via document.createTextNode. + + if (width >= 0.05555 && width <= 0.05556) { + this.character = "\u200a"; //   + } else if (width >= 0.1666 && width <= 0.1667) { + this.character = "\u2009"; //   + } else if (width >= 0.2222 && width <= 0.2223) { + this.character = "\u2005"; //   + } else if (width >= 0.2777 && width <= 0.2778) { + this.character = "\u2005\u200a"; //    + } else if (width >= -0.05556 && width <= -0.05555) { + this.character = "\u200a\u2063"; // ​ + } else if (width >= -0.1667 && width <= -0.1666) { + this.character = "\u2009\u2063"; // ​ + } else if (width >= -0.2223 && width <= -0.2222) { + this.character = "\u205f\u2063"; // ​ + } else if (width >= -0.2778 && width <= -0.2777) { + this.character = "\u2005\u2063"; // ​ + } else { + this.character = null; + } + } + /** + * Converts the math node into a MathML-namespaced DOM element. + */ + + + toNode() { + if (this.character) { + return document.createTextNode(this.character); + } else { + const node = document.createElementNS("http://www.w3.org/1998/Math/MathML", "mspace"); + node.setAttribute("width", makeEm(this.width)); + return node; + } + } + /** + * Converts the math node into an HTML markup string. + */ + + + toMarkup() { + if (this.character) { + return "" + this.character + ""; + } else { + return ""; + } + } + /** + * Converts the math node into a string, similar to innerText. + */ + + + toText() { + if (this.character) { + return this.character; + } else { + return " "; + } + } + +} + +/* harmony default export */ var mathMLTree = ({ + MathNode, + TextNode, + SpaceNode, + newDocumentFragment +}); +;// CONCATENATED MODULE: ./src/buildMathML.js +/** + * This file converts a parse tree into a corresponding MathML tree. The main + * entry point is the `buildMathML` function, which takes a parse tree from the + * parser. + */ + + + + + + + + + +/** + * Takes a symbol and converts it into a MathML text node after performing + * optional replacement from symbols.js. + */ +const makeText = function (text, mode, options) { + if (src_symbols[mode][text] && src_symbols[mode][text].replace && text.charCodeAt(0) !== 0xD835 && !(ligatures.hasOwnProperty(text) && options && (options.fontFamily && options.fontFamily.slice(4, 6) === "tt" || options.font && options.font.slice(4, 6) === "tt"))) { + text = src_symbols[mode][text].replace; + } + + return new mathMLTree.TextNode(text); +}; +/** + * Wrap the given array of nodes in an node if needed, i.e., + * unless the array has length 1. Always returns a single node. + */ + +const makeRow = function (body) { + if (body.length === 1) { + return body[0]; + } else { + return new mathMLTree.MathNode("mrow", body); + } +}; +/** + * Returns the math variant as a string or null if none is required. + */ + +const getVariant = function (group, options) { + // Handle \text... font specifiers as best we can. + // MathML has a limited list of allowable mathvariant specifiers; see + // https://www.w3.org/TR/MathML3/chapter3.html#presm.commatt + if (options.fontFamily === "texttt") { + return "monospace"; + } else if (options.fontFamily === "textsf") { + if (options.fontShape === "textit" && options.fontWeight === "textbf") { + return "sans-serif-bold-italic"; + } else if (options.fontShape === "textit") { + return "sans-serif-italic"; + } else if (options.fontWeight === "textbf") { + return "bold-sans-serif"; + } else { + return "sans-serif"; + } + } else if (options.fontShape === "textit" && options.fontWeight === "textbf") { + return "bold-italic"; + } else if (options.fontShape === "textit") { + return "italic"; + } else if (options.fontWeight === "textbf") { + return "bold"; + } + + const font = options.font; + + if (!font || font === "mathnormal") { + return null; + } + + const mode = group.mode; + + if (font === "mathit") { + return "italic"; + } else if (font === "boldsymbol") { + return group.type === "textord" ? "bold" : "bold-italic"; + } else if (font === "mathbf") { + return "bold"; + } else if (font === "mathbb") { + return "double-struck"; + } else if (font === "mathsfit") { + return "sans-serif-italic"; + } else if (font === "mathfrak") { + return "fraktur"; + } else if (font === "mathscr" || font === "mathcal") { + // MathML makes no distinction between script and calligraphic + return "script"; + } else if (font === "mathsf") { + return "sans-serif"; + } else if (font === "mathtt") { + return "monospace"; + } + + let text = group.text; + + if (utils.contains(["\\imath", "\\jmath"], text)) { + return null; + } + + if (src_symbols[mode][text] && src_symbols[mode][text].replace) { + text = src_symbols[mode][text].replace; + } + + const fontName = buildCommon.fontMap[font].fontName; + + if (getCharacterMetrics(text, fontName, mode)) { + return buildCommon.fontMap[font].variant; + } + + return null; +}; +/** + * Check for . which is how a dot renders in MathML, + * or , + * which is how a braced comma {,} renders in MathML + */ + +function isNumberPunctuation(group) { + if (!group) { + return false; + } + + if (group.type === 'mi' && group.children.length === 1) { + const child = group.children[0]; + return child instanceof TextNode && child.text === '.'; + } else if (group.type === 'mo' && group.children.length === 1 && group.getAttribute('separator') === 'true' && group.getAttribute('lspace') === '0em' && group.getAttribute('rspace') === '0em') { + const child = group.children[0]; + return child instanceof TextNode && child.text === ','; + } else { + return false; + } +} +/** + * Takes a list of nodes, builds them, and returns a list of the generated + * MathML nodes. Also combine consecutive outputs into a single + * tag. + */ + + +const buildMathML_buildExpression = function (expression, options, isOrdgroup) { + if (expression.length === 1) { + const group = buildMathML_buildGroup(expression[0], options); + + if (isOrdgroup && group instanceof MathNode && group.type === "mo") { + // When TeX writers want to suppress spacing on an operator, + // they often put the operator by itself inside braces. + group.setAttribute("lspace", "0em"); + group.setAttribute("rspace", "0em"); + } + + return [group]; + } + + const groups = []; + let lastGroup; + + for (let i = 0; i < expression.length; i++) { + const group = buildMathML_buildGroup(expression[i], options); + + if (group instanceof MathNode && lastGroup instanceof MathNode) { + // Concatenate adjacent s + if (group.type === 'mtext' && lastGroup.type === 'mtext' && group.getAttribute('mathvariant') === lastGroup.getAttribute('mathvariant')) { + lastGroup.children.push(...group.children); + continue; // Concatenate adjacent s + } else if (group.type === 'mn' && lastGroup.type === 'mn') { + lastGroup.children.push(...group.children); + continue; // Concatenate ... followed by . + } else if (isNumberPunctuation(group) && lastGroup.type === 'mn') { + lastGroup.children.push(...group.children); + continue; // Concatenate . followed by ... + } else if (group.type === 'mn' && isNumberPunctuation(lastGroup)) { + group.children = [...lastGroup.children, ...group.children]; + groups.pop(); // Put preceding ... or . inside base of + // ...base......exponent... (or ) + } else if ((group.type === 'msup' || group.type === 'msub') && group.children.length >= 1 && (lastGroup.type === 'mn' || isNumberPunctuation(lastGroup))) { + const base = group.children[0]; + + if (base instanceof MathNode && base.type === 'mn') { + base.children = [...lastGroup.children, ...base.children]; + groups.pop(); + } // \not + + } else if (lastGroup.type === 'mi' && lastGroup.children.length === 1) { + const lastChild = lastGroup.children[0]; + + if (lastChild instanceof TextNode && lastChild.text === '\u0338' && (group.type === 'mo' || group.type === 'mi' || group.type === 'mn')) { + const child = group.children[0]; + + if (child instanceof TextNode && child.text.length > 0) { + // Overlay with combining character long solidus + child.text = child.text.slice(0, 1) + "\u0338" + child.text.slice(1); + groups.pop(); + } + } + } + } + + groups.push(group); + lastGroup = group; + } + + return groups; +}; +/** + * Equivalent to buildExpression, but wraps the elements in an + * if there's more than one. Returns a single node instead of an array. + */ + +const buildExpressionRow = function (expression, options, isOrdgroup) { + return makeRow(buildMathML_buildExpression(expression, options, isOrdgroup)); +}; +/** + * Takes a group from the parser and calls the appropriate groupBuilders function + * on it to produce a MathML node. + */ + +const buildMathML_buildGroup = function (group, options) { + if (!group) { + return new mathMLTree.MathNode("mrow"); + } + + if (_mathmlGroupBuilders[group.type]) { + // Call the groupBuilders function + // $FlowFixMe + const result = _mathmlGroupBuilders[group.type](group, options); // $FlowFixMe + + return result; + } else { + throw new src_ParseError("Got group of unknown type: '" + group.type + "'"); + } +}; +/** + * Takes a full parse tree and settings and builds a MathML representation of + * it. In particular, we put the elements from building the parse tree into a + * tag so we can also include that TeX source as an annotation. + * + * Note that we actually return a domTree element with a `` inside it so + * we can do appropriate styling. + */ + +function buildMathML(tree, texExpression, options, isDisplayMode, forMathmlOnly) { + const expression = buildMathML_buildExpression(tree, options); // TODO: Make a pass thru the MathML similar to buildHTML.traverseNonSpaceNodes + // and add spacing nodes. This is necessary only adjacent to math operators + // like \sin or \lim or to subsup elements that contain math operators. + // MathML takes care of the other spacing issues. + // Wrap up the expression in an mrow so it is presented in the semantics + // tag correctly, unless it's a single or . + + let wrapper; + + if (expression.length === 1 && expression[0] instanceof MathNode && utils.contains(["mrow", "mtable"], expression[0].type)) { + wrapper = expression[0]; + } else { + wrapper = new mathMLTree.MathNode("mrow", expression); + } // Build a TeX annotation of the source + + + const annotation = new mathMLTree.MathNode("annotation", [new mathMLTree.TextNode(texExpression)]); + annotation.setAttribute("encoding", "application/x-tex"); + const semantics = new mathMLTree.MathNode("semantics", [wrapper, annotation]); + const math = new mathMLTree.MathNode("math", [semantics]); + math.setAttribute("xmlns", "http://www.w3.org/1998/Math/MathML"); + + if (isDisplayMode) { + math.setAttribute("display", "block"); + } // You can't style nodes, so we wrap the node in a span. + // NOTE: The span class is not typed to have nodes as children, and + // we don't want to make the children type more generic since the children + // of span are expected to have more fields in `buildHtml` contexts. + + + const wrapperClass = forMathmlOnly ? "katex" : "katex-mathml"; // $FlowFixMe + + return buildCommon.makeSpan([wrapperClass], [math]); +} +;// CONCATENATED MODULE: ./src/buildTree.js + + + + + + + +const optionsFromSettings = function (settings) { + return new src_Options({ + style: settings.displayMode ? src_Style.DISPLAY : src_Style.TEXT, + maxSize: settings.maxSize, + minRuleThickness: settings.minRuleThickness + }); +}; + +const displayWrap = function (node, settings) { + if (settings.displayMode) { + const classes = ["katex-display"]; + + if (settings.leqno) { + classes.push("leqno"); + } + + if (settings.fleqn) { + classes.push("fleqn"); + } + + node = buildCommon.makeSpan(classes, [node]); + } + + return node; +}; + +const buildTree = function (tree, expression, settings) { + const options = optionsFromSettings(settings); + let katexNode; + + if (settings.output === "mathml") { + return buildMathML(tree, expression, options, settings.displayMode, true); + } else if (settings.output === "html") { + const htmlNode = buildHTML(tree, options); + katexNode = buildCommon.makeSpan(["katex"], [htmlNode]); + } else { + const mathMLNode = buildMathML(tree, expression, options, settings.displayMode, false); + const htmlNode = buildHTML(tree, options); + katexNode = buildCommon.makeSpan(["katex"], [mathMLNode, htmlNode]); + } + + return displayWrap(katexNode, settings); +}; +const buildHTMLTree = function (tree, expression, settings) { + const options = optionsFromSettings(settings); + const htmlNode = buildHTML(tree, options); + const katexNode = buildCommon.makeSpan(["katex"], [htmlNode]); + return displayWrap(katexNode, settings); +}; +/* harmony default export */ var src_buildTree = ((/* unused pure expression or super */ null && (buildTree))); +;// CONCATENATED MODULE: ./src/stretchy.js +/** + * This file provides support to buildMathML.js and buildHTML.js + * for stretchy wide elements rendered from SVG files + * and other CSS trickery. + */ + + + + + +const stretchyCodePoint = { + widehat: "^", + widecheck: "ˇ", + widetilde: "~", + utilde: "~", + overleftarrow: "\u2190", + underleftarrow: "\u2190", + xleftarrow: "\u2190", + overrightarrow: "\u2192", + underrightarrow: "\u2192", + xrightarrow: "\u2192", + underbrace: "\u23df", + overbrace: "\u23de", + overgroup: "\u23e0", + undergroup: "\u23e1", + overleftrightarrow: "\u2194", + underleftrightarrow: "\u2194", + xleftrightarrow: "\u2194", + Overrightarrow: "\u21d2", + xRightarrow: "\u21d2", + overleftharpoon: "\u21bc", + xleftharpoonup: "\u21bc", + overrightharpoon: "\u21c0", + xrightharpoonup: "\u21c0", + xLeftarrow: "\u21d0", + xLeftrightarrow: "\u21d4", + xhookleftarrow: "\u21a9", + xhookrightarrow: "\u21aa", + xmapsto: "\u21a6", + xrightharpoondown: "\u21c1", + xleftharpoondown: "\u21bd", + xrightleftharpoons: "\u21cc", + xleftrightharpoons: "\u21cb", + xtwoheadleftarrow: "\u219e", + xtwoheadrightarrow: "\u21a0", + xlongequal: "=", + xtofrom: "\u21c4", + xrightleftarrows: "\u21c4", + xrightequilibrium: "\u21cc", + // Not a perfect match. + xleftequilibrium: "\u21cb", + // None better available. + "\\cdrightarrow": "\u2192", + "\\cdleftarrow": "\u2190", + "\\cdlongequal": "=" +}; + +const mathMLnode = function (label) { + const node = new mathMLTree.MathNode("mo", [new mathMLTree.TextNode(stretchyCodePoint[label.replace(/^\\/, '')])]); + node.setAttribute("stretchy", "true"); + return node; +}; // Many of the KaTeX SVG images have been adapted from glyphs in KaTeX fonts. +// Copyright (c) 2009-2010, Design Science, Inc. () +// Copyright (c) 2014-2017 Khan Academy () +// Licensed under the SIL Open Font License, Version 1.1. +// See \nhttp://scripts.sil.org/OFL +// Very Long SVGs +// Many of the KaTeX stretchy wide elements use a long SVG image and an +// overflow: hidden tactic to achieve a stretchy image while avoiding +// distortion of arrowheads or brace corners. +// The SVG typically contains a very long (400 em) arrow. +// The SVG is in a container span that has overflow: hidden, so the span +// acts like a window that exposes only part of the SVG. +// The SVG always has a longer, thinner aspect ratio than the container span. +// After the SVG fills 100% of the height of the container span, +// there is a long arrow shaft left over. That left-over shaft is not shown. +// Instead, it is sliced off because the span's CSS has overflow: hidden. +// Thus, the reader sees an arrow that matches the subject matter width +// without distortion. +// Some functions, such as \cancel, need to vary their aspect ratio. These +// functions do not get the overflow SVG treatment. +// Second Brush Stroke +// Low resolution monitors struggle to display images in fine detail. +// So browsers apply anti-aliasing. A long straight arrow shaft therefore +// will sometimes appear as if it has a blurred edge. +// To mitigate this, these SVG files contain a second "brush-stroke" on the +// arrow shafts. That is, a second long thin rectangular SVG path has been +// written directly on top of each arrow shaft. This reinforcement causes +// some of the screen pixels to display as black instead of the anti-aliased +// gray pixel that a single path would generate. So we get arrow shafts +// whose edges appear to be sharper. +// In the katexImagesData object just below, the dimensions all +// correspond to path geometry inside the relevant SVG. +// For example, \overrightarrow uses the same arrowhead as glyph U+2192 +// from the KaTeX Main font. The scaling factor is 1000. +// That is, inside the font, that arrowhead is 522 units tall, which +// corresponds to 0.522 em inside the document. + + +const katexImagesData = { + // path(s), minWidth, height, align + overrightarrow: [["rightarrow"], 0.888, 522, "xMaxYMin"], + overleftarrow: [["leftarrow"], 0.888, 522, "xMinYMin"], + underrightarrow: [["rightarrow"], 0.888, 522, "xMaxYMin"], + underleftarrow: [["leftarrow"], 0.888, 522, "xMinYMin"], + xrightarrow: [["rightarrow"], 1.469, 522, "xMaxYMin"], + "\\cdrightarrow": [["rightarrow"], 3.0, 522, "xMaxYMin"], + // CD minwwidth2.5pc + xleftarrow: [["leftarrow"], 1.469, 522, "xMinYMin"], + "\\cdleftarrow": [["leftarrow"], 3.0, 522, "xMinYMin"], + Overrightarrow: [["doublerightarrow"], 0.888, 560, "xMaxYMin"], + xRightarrow: [["doublerightarrow"], 1.526, 560, "xMaxYMin"], + xLeftarrow: [["doubleleftarrow"], 1.526, 560, "xMinYMin"], + overleftharpoon: [["leftharpoon"], 0.888, 522, "xMinYMin"], + xleftharpoonup: [["leftharpoon"], 0.888, 522, "xMinYMin"], + xleftharpoondown: [["leftharpoondown"], 0.888, 522, "xMinYMin"], + overrightharpoon: [["rightharpoon"], 0.888, 522, "xMaxYMin"], + xrightharpoonup: [["rightharpoon"], 0.888, 522, "xMaxYMin"], + xrightharpoondown: [["rightharpoondown"], 0.888, 522, "xMaxYMin"], + xlongequal: [["longequal"], 0.888, 334, "xMinYMin"], + "\\cdlongequal": [["longequal"], 3.0, 334, "xMinYMin"], + xtwoheadleftarrow: [["twoheadleftarrow"], 0.888, 334, "xMinYMin"], + xtwoheadrightarrow: [["twoheadrightarrow"], 0.888, 334, "xMaxYMin"], + overleftrightarrow: [["leftarrow", "rightarrow"], 0.888, 522], + overbrace: [["leftbrace", "midbrace", "rightbrace"], 1.6, 548], + underbrace: [["leftbraceunder", "midbraceunder", "rightbraceunder"], 1.6, 548], + underleftrightarrow: [["leftarrow", "rightarrow"], 0.888, 522], + xleftrightarrow: [["leftarrow", "rightarrow"], 1.75, 522], + xLeftrightarrow: [["doubleleftarrow", "doublerightarrow"], 1.75, 560], + xrightleftharpoons: [["leftharpoondownplus", "rightharpoonplus"], 1.75, 716], + xleftrightharpoons: [["leftharpoonplus", "rightharpoondownplus"], 1.75, 716], + xhookleftarrow: [["leftarrow", "righthook"], 1.08, 522], + xhookrightarrow: [["lefthook", "rightarrow"], 1.08, 522], + overlinesegment: [["leftlinesegment", "rightlinesegment"], 0.888, 522], + underlinesegment: [["leftlinesegment", "rightlinesegment"], 0.888, 522], + overgroup: [["leftgroup", "rightgroup"], 0.888, 342], + undergroup: [["leftgroupunder", "rightgroupunder"], 0.888, 342], + xmapsto: [["leftmapsto", "rightarrow"], 1.5, 522], + xtofrom: [["leftToFrom", "rightToFrom"], 1.75, 528], + // The next three arrows are from the mhchem package. + // In mhchem.sty, min-length is 2.0em. But these arrows might appear in the + // document as \xrightarrow or \xrightleftharpoons. Those have + // min-length = 1.75em, so we set min-length on these next three to match. + xrightleftarrows: [["baraboveleftarrow", "rightarrowabovebar"], 1.75, 901], + xrightequilibrium: [["baraboveshortleftharpoon", "rightharpoonaboveshortbar"], 1.75, 716], + xleftequilibrium: [["shortbaraboveleftharpoon", "shortrightharpoonabovebar"], 1.75, 716] +}; + +const groupLength = function (arg) { + if (arg.type === "ordgroup") { + return arg.body.length; + } else { + return 1; + } +}; + +const svgSpan = function (group, options) { + // Create a span with inline SVG for the element. + function buildSvgSpan_() { + let viewBoxWidth = 400000; // default + + const label = group.label.slice(1); + + if (utils.contains(["widehat", "widecheck", "widetilde", "utilde"], label)) { + // Each type in the `if` statement corresponds to one of the ParseNode + // types below. This narrowing is required to access `grp.base`. + // $FlowFixMe + const grp = group; // There are four SVG images available for each function. + // Choose a taller image when there are more characters. + + const numChars = groupLength(grp.base); + let viewBoxHeight; + let pathName; + let height; + + if (numChars > 5) { + if (label === "widehat" || label === "widecheck") { + viewBoxHeight = 420; + viewBoxWidth = 2364; + height = 0.42; + pathName = label + "4"; + } else { + viewBoxHeight = 312; + viewBoxWidth = 2340; + height = 0.34; + pathName = "tilde4"; + } + } else { + const imgIndex = [1, 1, 2, 2, 3, 3][numChars]; + + if (label === "widehat" || label === "widecheck") { + viewBoxWidth = [0, 1062, 2364, 2364, 2364][imgIndex]; + viewBoxHeight = [0, 239, 300, 360, 420][imgIndex]; + height = [0, 0.24, 0.3, 0.3, 0.36, 0.42][imgIndex]; + pathName = label + imgIndex; + } else { + viewBoxWidth = [0, 600, 1033, 2339, 2340][imgIndex]; + viewBoxHeight = [0, 260, 286, 306, 312][imgIndex]; + height = [0, 0.26, 0.286, 0.3, 0.306, 0.34][imgIndex]; + pathName = "tilde" + imgIndex; + } + } + + const path = new PathNode(pathName); + const svgNode = new SvgNode([path], { + "width": "100%", + "height": makeEm(height), + "viewBox": "0 0 " + viewBoxWidth + " " + viewBoxHeight, + "preserveAspectRatio": "none" + }); + return { + span: buildCommon.makeSvgSpan([], [svgNode], options), + minWidth: 0, + height + }; + } else { + const spans = []; + const data = katexImagesData[label]; + const [paths, minWidth, viewBoxHeight] = data; + const height = viewBoxHeight / 1000; + const numSvgChildren = paths.length; + let widthClasses; + let aligns; + + if (numSvgChildren === 1) { + // $FlowFixMe: All these cases must be of the 4-tuple type. + const align1 = data[3]; + widthClasses = ["hide-tail"]; + aligns = [align1]; + } else if (numSvgChildren === 2) { + widthClasses = ["halfarrow-left", "halfarrow-right"]; + aligns = ["xMinYMin", "xMaxYMin"]; + } else if (numSvgChildren === 3) { + widthClasses = ["brace-left", "brace-center", "brace-right"]; + aligns = ["xMinYMin", "xMidYMin", "xMaxYMin"]; + } else { + throw new Error("Correct katexImagesData or update code here to support\n " + numSvgChildren + " children."); + } + + for (let i = 0; i < numSvgChildren; i++) { + const path = new PathNode(paths[i]); + const svgNode = new SvgNode([path], { + "width": "400em", + "height": makeEm(height), + "viewBox": "0 0 " + viewBoxWidth + " " + viewBoxHeight, + "preserveAspectRatio": aligns[i] + " slice" + }); + const span = buildCommon.makeSvgSpan([widthClasses[i]], [svgNode], options); + + if (numSvgChildren === 1) { + return { + span, + minWidth, + height + }; + } else { + span.style.height = makeEm(height); + spans.push(span); + } + } + + return { + span: buildCommon.makeSpan(["stretchy"], spans, options), + minWidth, + height + }; + } + } // buildSvgSpan_() + + + const { + span, + minWidth, + height + } = buildSvgSpan_(); // Note that we are returning span.depth = 0. + // Any adjustments relative to the baseline must be done in buildHTML. + + span.height = height; + span.style.height = makeEm(height); + + if (minWidth > 0) { + span.style.minWidth = makeEm(minWidth); + } + + return span; +}; + +const encloseSpan = function (inner, label, topPad, bottomPad, options) { + // Return an image span for \cancel, \bcancel, \xcancel, \fbox, or \angl + let img; + const totalHeight = inner.height + inner.depth + topPad + bottomPad; + + if (/fbox|color|angl/.test(label)) { + img = buildCommon.makeSpan(["stretchy", label], [], options); + + if (label === "fbox") { + const color = options.color && options.getColor(); + + if (color) { + img.style.borderColor = color; + } + } + } else { + // \cancel, \bcancel, or \xcancel + // Since \cancel's SVG is inline and it omits the viewBox attribute, + // its stroke-width will not vary with span area. + const lines = []; + + if (/^[bx]cancel$/.test(label)) { + lines.push(new LineNode({ + "x1": "0", + "y1": "0", + "x2": "100%", + "y2": "100%", + "stroke-width": "0.046em" + })); + } + + if (/^x?cancel$/.test(label)) { + lines.push(new LineNode({ + "x1": "0", + "y1": "100%", + "x2": "100%", + "y2": "0", + "stroke-width": "0.046em" + })); + } + + const svgNode = new SvgNode(lines, { + "width": "100%", + "height": makeEm(totalHeight) + }); + img = buildCommon.makeSvgSpan([], [svgNode], options); + } + + img.height = totalHeight; + img.style.height = makeEm(totalHeight); + return img; +}; + +/* harmony default export */ var stretchy = ({ + encloseSpan, + mathMLnode, + svgSpan +}); +;// CONCATENATED MODULE: ./src/parseNode.js + + +/** + * Asserts that the node is of the given type and returns it with stricter + * typing. Throws if the node's type does not match. + */ +function assertNodeType(node, type) { + if (!node || node.type !== type) { + throw new Error("Expected node of type " + type + ", but got " + (node ? "node of type " + node.type : String(node))); + } // $FlowFixMe, >=0.125 + + + return node; +} +/** + * Returns the node more strictly typed iff it is of the given type. Otherwise, + * returns null. + */ + +function assertSymbolNodeType(node) { + const typedNode = checkSymbolNodeType(node); + + if (!typedNode) { + throw new Error("Expected node of symbol group type, but got " + (node ? "node of type " + node.type : String(node))); + } + + return typedNode; +} +/** + * Returns the node more strictly typed iff it is of the given type. Otherwise, + * returns null. + */ + +function checkSymbolNodeType(node) { + if (node && (node.type === "atom" || NON_ATOMS.hasOwnProperty(node.type))) { + // $FlowFixMe + return node; + } + + return null; +} +;// CONCATENATED MODULE: ./src/functions/accent.js + + + + + + + + + + +// NOTE: Unlike most `htmlBuilder`s, this one handles not only "accent", but +// also "supsub" since an accent can affect super/subscripting. +const htmlBuilder = (grp, options) => { + // Accents are handled in the TeXbook pg. 443, rule 12. + let base; + let group; + let supSubGroup; + + if (grp && grp.type === "supsub") { + // If our base is a character box, and we have superscripts and + // subscripts, the supsub will defer to us. In particular, we want + // to attach the superscripts and subscripts to the inner body (so + // that the position of the superscripts and subscripts won't be + // affected by the height of the accent). We accomplish this by + // sticking the base of the accent into the base of the supsub, and + // rendering that, while keeping track of where the accent is. + // The real accent group is the base of the supsub group + group = assertNodeType(grp.base, "accent"); // The character box is the base of the accent group + + base = group.base; // Stick the character box into the base of the supsub group + + grp.base = base; // Rerender the supsub group with its new base, and store that + // result. + + supSubGroup = assertSpan(buildGroup(grp, options)); // reset original base + + grp.base = group; + } else { + group = assertNodeType(grp, "accent"); + base = group.base; + } // Build the base group + + + const body = buildGroup(base, options.havingCrampedStyle()); // Does the accent need to shift for the skew of a character? + + const mustShift = group.isShifty && utils.isCharacterBox(base); // Calculate the skew of the accent. This is based on the line "If the + // nucleus is not a single character, let s = 0; otherwise set s to the + // kern amount for the nucleus followed by the \skewchar of its font." + // Note that our skew metrics are just the kern between each character + // and the skewchar. + + let skew = 0; + + if (mustShift) { + // If the base is a character box, then we want the skew of the + // innermost character. To do that, we find the innermost character: + const baseChar = utils.getBaseElem(base); // Then, we render its group to get the symbol inside it + + const baseGroup = buildGroup(baseChar, options.havingCrampedStyle()); // Finally, we pull the skew off of the symbol. + + skew = assertSymbolDomNode(baseGroup).skew; // Note that we now throw away baseGroup, because the layers we + // removed with getBaseElem might contain things like \color which + // we can't get rid of. + // TODO(emily): Find a better way to get the skew + } + + const accentBelow = group.label === "\\c"; // calculate the amount of space between the body and the accent + + let clearance = accentBelow ? body.height + body.depth : Math.min(body.height, options.fontMetrics().xHeight); // Build the accent + + let accentBody; + + if (!group.isStretchy) { + let accent; + let width; + + if (group.label === "\\vec") { + // Before version 0.9, \vec used the combining font glyph U+20D7. + // But browsers, especially Safari, are not consistent in how they + // render combining characters when not preceded by a character. + // So now we use an SVG. + // If Safari reforms, we should consider reverting to the glyph. + accent = buildCommon.staticSvg("vec", options); + width = buildCommon.svgData.vec[1]; + } else { + accent = buildCommon.makeOrd({ + mode: group.mode, + text: group.label + }, options, "textord"); + accent = assertSymbolDomNode(accent); // Remove the italic correction of the accent, because it only serves to + // shift the accent over to a place we don't want. + + accent.italic = 0; + width = accent.width; + + if (accentBelow) { + clearance += accent.depth; + } + } + + accentBody = buildCommon.makeSpan(["accent-body"], [accent]); // "Full" accents expand the width of the resulting symbol to be + // at least the width of the accent, and overlap directly onto the + // character without any vertical offset. + + const accentFull = group.label === "\\textcircled"; + + if (accentFull) { + accentBody.classes.push('accent-full'); + clearance = body.height; + } // Shift the accent over by the skew. + + + let left = skew; // CSS defines `.katex .accent .accent-body:not(.accent-full) { width: 0 }` + // so that the accent doesn't contribute to the bounding box. + // We need to shift the character by its width (effectively half + // its width) to compensate. + + if (!accentFull) { + left -= width / 2; + } + + accentBody.style.left = makeEm(left); // \textcircled uses the \bigcirc glyph, so it needs some + // vertical adjustment to match LaTeX. + + if (group.label === "\\textcircled") { + accentBody.style.top = ".2em"; + } + + accentBody = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: body + }, { + type: "kern", + size: -clearance + }, { + type: "elem", + elem: accentBody + }] + }, options); + } else { + accentBody = stretchy.svgSpan(group, options); + accentBody = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: body + }, { + type: "elem", + elem: accentBody, + wrapperClasses: ["svg-align"], + wrapperStyle: skew > 0 ? { + width: "calc(100% - " + makeEm(2 * skew) + ")", + marginLeft: makeEm(2 * skew) + } : undefined + }] + }, options); + } + + const accentWrap = buildCommon.makeSpan(["mord", "accent"], [accentBody], options); + + if (supSubGroup) { + // Here, we replace the "base" child of the supsub with our newly + // generated accent. + supSubGroup.children[0] = accentWrap; // Since we don't rerun the height calculation after replacing the + // accent, we manually recalculate height. + + supSubGroup.height = Math.max(accentWrap.height, supSubGroup.height); // Accents should always be ords, even when their innards are not. + + supSubGroup.classes[0] = "mord"; + return supSubGroup; + } else { + return accentWrap; + } +}; + +const mathmlBuilder = (group, options) => { + const accentNode = group.isStretchy ? stretchy.mathMLnode(group.label) : new mathMLTree.MathNode("mo", [makeText(group.label, group.mode)]); + const node = new mathMLTree.MathNode("mover", [buildMathML_buildGroup(group.base, options), accentNode]); + node.setAttribute("accent", "true"); + return node; +}; + +const NON_STRETCHY_ACCENT_REGEX = new RegExp(["\\acute", "\\grave", "\\ddot", "\\tilde", "\\bar", "\\breve", "\\check", "\\hat", "\\vec", "\\dot", "\\mathring"].map(accent => "\\" + accent).join("|")); // Accents + +defineFunction({ + type: "accent", + names: ["\\acute", "\\grave", "\\ddot", "\\tilde", "\\bar", "\\breve", "\\check", "\\hat", "\\vec", "\\dot", "\\mathring", "\\widecheck", "\\widehat", "\\widetilde", "\\overrightarrow", "\\overleftarrow", "\\Overrightarrow", "\\overleftrightarrow", "\\overgroup", "\\overlinesegment", "\\overleftharpoon", "\\overrightharpoon"], + props: { + numArgs: 1 + }, + handler: (context, args) => { + const base = normalizeArgument(args[0]); + const isStretchy = !NON_STRETCHY_ACCENT_REGEX.test(context.funcName); + const isShifty = !isStretchy || context.funcName === "\\widehat" || context.funcName === "\\widetilde" || context.funcName === "\\widecheck"; + return { + type: "accent", + mode: context.parser.mode, + label: context.funcName, + isStretchy: isStretchy, + isShifty: isShifty, + base: base + }; + }, + htmlBuilder, + mathmlBuilder +}); // Text-mode accents + +defineFunction({ + type: "accent", + names: ["\\'", "\\`", "\\^", "\\~", "\\=", "\\u", "\\.", '\\"', "\\c", "\\r", "\\H", "\\v", "\\textcircled"], + props: { + numArgs: 1, + allowedInText: true, + allowedInMath: true, + // unless in strict mode + argTypes: ["primitive"] + }, + handler: (context, args) => { + const base = args[0]; + let mode = context.parser.mode; + + if (mode === "math") { + context.parser.settings.reportNonstrict("mathVsTextAccents", "LaTeX's accent " + context.funcName + " works only in text mode"); + mode = "text"; + } + + return { + type: "accent", + mode: mode, + label: context.funcName, + isStretchy: false, + isShifty: true, + base: base + }; + }, + htmlBuilder, + mathmlBuilder +}); +;// CONCATENATED MODULE: ./src/functions/accentunder.js +// Horizontal overlap functions + + + + + + +defineFunction({ + type: "accentUnder", + names: ["\\underleftarrow", "\\underrightarrow", "\\underleftrightarrow", "\\undergroup", "\\underlinesegment", "\\utilde"], + props: { + numArgs: 1 + }, + handler: (_ref, args) => { + let { + parser, + funcName + } = _ref; + const base = args[0]; + return { + type: "accentUnder", + mode: parser.mode, + label: funcName, + base: base + }; + }, + htmlBuilder: (group, options) => { + // Treat under accents much like underlines. + const innerGroup = buildGroup(group.base, options); + const accentBody = stretchy.svgSpan(group, options); + const kern = group.label === "\\utilde" ? 0.12 : 0; // Generate the vlist, with the appropriate kerns + + const vlist = buildCommon.makeVList({ + positionType: "top", + positionData: innerGroup.height, + children: [{ + type: "elem", + elem: accentBody, + wrapperClasses: ["svg-align"] + }, { + type: "kern", + size: kern + }, { + type: "elem", + elem: innerGroup + }] + }, options); + return buildCommon.makeSpan(["mord", "accentunder"], [vlist], options); + }, + mathmlBuilder: (group, options) => { + const accentNode = stretchy.mathMLnode(group.label); + const node = new mathMLTree.MathNode("munder", [buildMathML_buildGroup(group.base, options), accentNode]); + node.setAttribute("accentunder", "true"); + return node; + } +}); +;// CONCATENATED MODULE: ./src/functions/arrow.js + + + + + + + +// Helper function +const paddedNode = group => { + const node = new mathMLTree.MathNode("mpadded", group ? [group] : []); + node.setAttribute("width", "+0.6em"); + node.setAttribute("lspace", "0.3em"); + return node; +}; // Stretchy arrows with an optional argument + + +defineFunction({ + type: "xArrow", + names: ["\\xleftarrow", "\\xrightarrow", "\\xLeftarrow", "\\xRightarrow", "\\xleftrightarrow", "\\xLeftrightarrow", "\\xhookleftarrow", "\\xhookrightarrow", "\\xmapsto", "\\xrightharpoondown", "\\xrightharpoonup", "\\xleftharpoondown", "\\xleftharpoonup", "\\xrightleftharpoons", "\\xleftrightharpoons", "\\xlongequal", "\\xtwoheadrightarrow", "\\xtwoheadleftarrow", "\\xtofrom", // The next 3 functions are here to support the mhchem extension. + // Direct use of these functions is discouraged and may break someday. + "\\xrightleftarrows", "\\xrightequilibrium", "\\xleftequilibrium", // The next 3 functions are here only to support the {CD} environment. + "\\\\cdrightarrow", "\\\\cdleftarrow", "\\\\cdlongequal"], + props: { + numArgs: 1, + numOptionalArgs: 1 + }, + + handler(_ref, args, optArgs) { + let { + parser, + funcName + } = _ref; + return { + type: "xArrow", + mode: parser.mode, + label: funcName, + body: args[0], + below: optArgs[0] + }; + }, + + // Flow is unable to correctly infer the type of `group`, even though it's + // unambiguously determined from the passed-in `type` above. + htmlBuilder(group, options) { + const style = options.style; // Build the argument groups in the appropriate style. + // Ref: amsmath.dtx: \hbox{$\scriptstyle\mkern#3mu{#6}\mkern#4mu$}% + // Some groups can return document fragments. Handle those by wrapping + // them in a span. + + let newOptions = options.havingStyle(style.sup()); + const upperGroup = buildCommon.wrapFragment(buildGroup(group.body, newOptions, options), options); + const arrowPrefix = group.label.slice(0, 2) === "\\x" ? "x" : "cd"; + upperGroup.classes.push(arrowPrefix + "-arrow-pad"); + let lowerGroup; + + if (group.below) { + // Build the lower group + newOptions = options.havingStyle(style.sub()); + lowerGroup = buildCommon.wrapFragment(buildGroup(group.below, newOptions, options), options); + lowerGroup.classes.push(arrowPrefix + "-arrow-pad"); + } + + const arrowBody = stretchy.svgSpan(group, options); // Re shift: Note that stretchy.svgSpan returned arrowBody.depth = 0. + // The point we want on the math axis is at 0.5 * arrowBody.height. + + const arrowShift = -options.fontMetrics().axisHeight + 0.5 * arrowBody.height; // 2 mu kern. Ref: amsmath.dtx: #7\if0#2\else\mkern#2mu\fi + + let upperShift = -options.fontMetrics().axisHeight - 0.5 * arrowBody.height - 0.111; // 0.111 em = 2 mu + + if (upperGroup.depth > 0.25 || group.label === "\\xleftequilibrium") { + upperShift -= upperGroup.depth; // shift up if depth encroaches + } // Generate the vlist + + + let vlist; + + if (lowerGroup) { + const lowerShift = -options.fontMetrics().axisHeight + lowerGroup.height + 0.5 * arrowBody.height + 0.111; + vlist = buildCommon.makeVList({ + positionType: "individualShift", + children: [{ + type: "elem", + elem: upperGroup, + shift: upperShift + }, { + type: "elem", + elem: arrowBody, + shift: arrowShift + }, { + type: "elem", + elem: lowerGroup, + shift: lowerShift + }] + }, options); + } else { + vlist = buildCommon.makeVList({ + positionType: "individualShift", + children: [{ + type: "elem", + elem: upperGroup, + shift: upperShift + }, { + type: "elem", + elem: arrowBody, + shift: arrowShift + }] + }, options); + } // $FlowFixMe: Replace this with passing "svg-align" into makeVList. + + + vlist.children[0].children[0].children[1].classes.push("svg-align"); + return buildCommon.makeSpan(["mrel", "x-arrow"], [vlist], options); + }, + + mathmlBuilder(group, options) { + const arrowNode = stretchy.mathMLnode(group.label); + arrowNode.setAttribute("minsize", group.label.charAt(0) === "x" ? "1.75em" : "3.0em"); + let node; + + if (group.body) { + const upperNode = paddedNode(buildMathML_buildGroup(group.body, options)); + + if (group.below) { + const lowerNode = paddedNode(buildMathML_buildGroup(group.below, options)); + node = new mathMLTree.MathNode("munderover", [arrowNode, lowerNode, upperNode]); + } else { + node = new mathMLTree.MathNode("mover", [arrowNode, upperNode]); + } + } else if (group.below) { + const lowerNode = paddedNode(buildMathML_buildGroup(group.below, options)); + node = new mathMLTree.MathNode("munder", [arrowNode, lowerNode]); + } else { + // This should never happen. + // Parser.js throws an error if there is no argument. + node = paddedNode(); + node = new mathMLTree.MathNode("mover", [arrowNode, node]); + } + + return node; + } + +}); +;// CONCATENATED MODULE: ./src/functions/mclass.js + + + + + + +const mclass_makeSpan = buildCommon.makeSpan; + +function mclass_htmlBuilder(group, options) { + const elements = buildExpression(group.body, options, true); + return mclass_makeSpan([group.mclass], elements, options); +} + +function mclass_mathmlBuilder(group, options) { + let node; + const inner = buildMathML_buildExpression(group.body, options); + + if (group.mclass === "minner") { + node = new mathMLTree.MathNode("mpadded", inner); + } else if (group.mclass === "mord") { + if (group.isCharacterBox) { + node = inner[0]; + node.type = "mi"; + } else { + node = new mathMLTree.MathNode("mi", inner); + } + } else { + if (group.isCharacterBox) { + node = inner[0]; + node.type = "mo"; + } else { + node = new mathMLTree.MathNode("mo", inner); + } // Set spacing based on what is the most likely adjacent atom type. + // See TeXbook p170. + + + if (group.mclass === "mbin") { + node.attributes.lspace = "0.22em"; // medium space + + node.attributes.rspace = "0.22em"; + } else if (group.mclass === "mpunct") { + node.attributes.lspace = "0em"; + node.attributes.rspace = "0.17em"; // thinspace + } else if (group.mclass === "mopen" || group.mclass === "mclose") { + node.attributes.lspace = "0em"; + node.attributes.rspace = "0em"; + } else if (group.mclass === "minner") { + node.attributes.lspace = "0.0556em"; // 1 mu is the most likely option + + node.attributes.width = "+0.1111em"; + } // MathML default space is 5/18 em, so needs no action. + // Ref: https://developer.mozilla.org/en-US/docs/Web/MathML/Element/mo + + } + + return node; +} // Math class commands except \mathop + + +defineFunction({ + type: "mclass", + names: ["\\mathord", "\\mathbin", "\\mathrel", "\\mathopen", "\\mathclose", "\\mathpunct", "\\mathinner"], + props: { + numArgs: 1, + primitive: true + }, + + handler(_ref, args) { + let { + parser, + funcName + } = _ref; + const body = args[0]; + return { + type: "mclass", + mode: parser.mode, + mclass: "m" + funcName.slice(5), + // TODO(kevinb): don't prefix with 'm' + body: ordargument(body), + isCharacterBox: utils.isCharacterBox(body) + }; + }, + + htmlBuilder: mclass_htmlBuilder, + mathmlBuilder: mclass_mathmlBuilder +}); +const binrelClass = arg => { + // \binrel@ spacing varies with (bin|rel|ord) of the atom in the argument. + // (by rendering separately and with {}s before and after, and measuring + // the change in spacing). We'll do roughly the same by detecting the + // atom type directly. + const atom = arg.type === "ordgroup" && arg.body.length ? arg.body[0] : arg; + + if (atom.type === "atom" && (atom.family === "bin" || atom.family === "rel")) { + return "m" + atom.family; + } else { + return "mord"; + } +}; // \@binrel{x}{y} renders like y but as mbin/mrel/mord if x is mbin/mrel/mord. +// This is equivalent to \binrel@{x}\binrel@@{y} in AMSTeX. + +defineFunction({ + type: "mclass", + names: ["\\@binrel"], + props: { + numArgs: 2 + }, + + handler(_ref2, args) { + let { + parser + } = _ref2; + return { + type: "mclass", + mode: parser.mode, + mclass: binrelClass(args[0]), + body: ordargument(args[1]), + isCharacterBox: utils.isCharacterBox(args[1]) + }; + } + +}); // Build a relation or stacked op by placing one symbol on top of another + +defineFunction({ + type: "mclass", + names: ["\\stackrel", "\\overset", "\\underset"], + props: { + numArgs: 2 + }, + + handler(_ref3, args) { + let { + parser, + funcName + } = _ref3; + const baseArg = args[1]; + const shiftedArg = args[0]; + let mclass; + + if (funcName !== "\\stackrel") { + // LaTeX applies \binrel spacing to \overset and \underset. + mclass = binrelClass(baseArg); + } else { + mclass = "mrel"; // for \stackrel + } + + const baseOp = { + type: "op", + mode: baseArg.mode, + limits: true, + alwaysHandleSupSub: true, + parentIsSupSub: false, + symbol: false, + suppressBaseShift: funcName !== "\\stackrel", + body: ordargument(baseArg) + }; + const supsub = { + type: "supsub", + mode: shiftedArg.mode, + base: baseOp, + sup: funcName === "\\underset" ? null : shiftedArg, + sub: funcName === "\\underset" ? shiftedArg : null + }; + return { + type: "mclass", + mode: parser.mode, + mclass, + body: [supsub], + isCharacterBox: utils.isCharacterBox(supsub) + }; + }, + + htmlBuilder: mclass_htmlBuilder, + mathmlBuilder: mclass_mathmlBuilder +}); +;// CONCATENATED MODULE: ./src/functions/pmb.js + + + + + + +// \pmb is a simulation of bold font. +// The version of \pmb in ambsy.sty works by typesetting three copies +// with small offsets. We use CSS text-shadow. +// It's a hack. Not as good as a real bold font. Better than nothing. +defineFunction({ + type: "pmb", + names: ["\\pmb"], + props: { + numArgs: 1, + allowedInText: true + }, + + handler(_ref, args) { + let { + parser + } = _ref; + return { + type: "pmb", + mode: parser.mode, + mclass: binrelClass(args[0]), + body: ordargument(args[0]) + }; + }, + + htmlBuilder(group, options) { + const elements = buildExpression(group.body, options, true); + const node = buildCommon.makeSpan([group.mclass], elements, options); + node.style.textShadow = "0.02em 0.01em 0.04px"; + return node; + }, + + mathmlBuilder(group, style) { + const inner = buildMathML_buildExpression(group.body, style); // Wrap with an element. + + const node = new mathMLTree.MathNode("mstyle", inner); + node.setAttribute("style", "text-shadow: 0.02em 0.01em 0.04px"); + return node; + } + +}); +;// CONCATENATED MODULE: ./src/environments/cd.js + + + + + + + + +const cdArrowFunctionName = { + ">": "\\\\cdrightarrow", + "<": "\\\\cdleftarrow", + "=": "\\\\cdlongequal", + "A": "\\uparrow", + "V": "\\downarrow", + "|": "\\Vert", + ".": "no arrow" +}; + +const newCell = () => { + // Create an empty cell, to be filled below with parse nodes. + // The parseTree from this module must be constructed like the + // one created by parseArray(), so an empty CD cell must + // be a ParseNode<"styling">. And CD is always displaystyle. + // So these values are fixed and flow can do implicit typing. + return { + type: "styling", + body: [], + mode: "math", + style: "display" + }; +}; + +const isStartOfArrow = node => { + return node.type === "textord" && node.text === "@"; +}; + +const isLabelEnd = (node, endChar) => { + return (node.type === "mathord" || node.type === "atom") && node.text === endChar; +}; + +function cdArrow(arrowChar, labels, parser) { + // Return a parse tree of an arrow and its labels. + // This acts in a way similar to a macro expansion. + const funcName = cdArrowFunctionName[arrowChar]; + + switch (funcName) { + case "\\\\cdrightarrow": + case "\\\\cdleftarrow": + return parser.callFunction(funcName, [labels[0]], [labels[1]]); + + case "\\uparrow": + case "\\downarrow": + { + const leftLabel = parser.callFunction("\\\\cdleft", [labels[0]], []); + const bareArrow = { + type: "atom", + text: funcName, + mode: "math", + family: "rel" + }; + const sizedArrow = parser.callFunction("\\Big", [bareArrow], []); + const rightLabel = parser.callFunction("\\\\cdright", [labels[1]], []); + const arrowGroup = { + type: "ordgroup", + mode: "math", + body: [leftLabel, sizedArrow, rightLabel] + }; + return parser.callFunction("\\\\cdparent", [arrowGroup], []); + } + + case "\\\\cdlongequal": + return parser.callFunction("\\\\cdlongequal", [], []); + + case "\\Vert": + { + const arrow = { + type: "textord", + text: "\\Vert", + mode: "math" + }; + return parser.callFunction("\\Big", [arrow], []); + } + + default: + return { + type: "textord", + text: " ", + mode: "math" + }; + } +} + +function parseCD(parser) { + // Get the array's parse nodes with \\ temporarily mapped to \cr. + const parsedRows = []; + parser.gullet.beginGroup(); + parser.gullet.macros.set("\\cr", "\\\\\\relax"); + parser.gullet.beginGroup(); + + while (true) { + // eslint-disable-line no-constant-condition + // Get the parse nodes for the next row. + parsedRows.push(parser.parseExpression(false, "\\\\")); + parser.gullet.endGroup(); + parser.gullet.beginGroup(); + const next = parser.fetch().text; + + if (next === "&" || next === "\\\\") { + parser.consume(); + } else if (next === "\\end") { + if (parsedRows[parsedRows.length - 1].length === 0) { + parsedRows.pop(); // final row ended in \\ + } + + break; + } else { + throw new src_ParseError("Expected \\\\ or \\cr or \\end", parser.nextToken); + } + } + + let row = []; + const body = [row]; // Loop thru the parse nodes. Collect them into cells and arrows. + + for (let i = 0; i < parsedRows.length; i++) { + // Start a new row. + const rowNodes = parsedRows[i]; // Create the first cell. + + let cell = newCell(); + + for (let j = 0; j < rowNodes.length; j++) { + if (!isStartOfArrow(rowNodes[j])) { + // If a parseNode is not an arrow, it goes into a cell. + cell.body.push(rowNodes[j]); + } else { + // Parse node j is an "@", the start of an arrow. + // Before starting on the arrow, push the cell into `row`. + row.push(cell); // Now collect parseNodes into an arrow. + // The character after "@" defines the arrow type. + + j += 1; + const arrowChar = assertSymbolNodeType(rowNodes[j]).text; // Create two empty label nodes. We may or may not use them. + + const labels = new Array(2); + labels[0] = { + type: "ordgroup", + mode: "math", + body: [] + }; + labels[1] = { + type: "ordgroup", + mode: "math", + body: [] + }; // Process the arrow. + + if ("=|.".indexOf(arrowChar) > -1) {// Three "arrows", ``@=`, `@|`, and `@.`, do not take labels. + // Do nothing here. + } else if ("<>AV".indexOf(arrowChar) > -1) { + // Four arrows, `@>>>`, `@<<<`, `@AAA`, and `@VVV`, each take + // two optional labels. E.g. the right-point arrow syntax is + // really: @>{optional label}>{optional label}> + // Collect parseNodes into labels. + for (let labelNum = 0; labelNum < 2; labelNum++) { + let inLabel = true; + + for (let k = j + 1; k < rowNodes.length; k++) { + if (isLabelEnd(rowNodes[k], arrowChar)) { + inLabel = false; + j = k; + break; + } + + if (isStartOfArrow(rowNodes[k])) { + throw new src_ParseError("Missing a " + arrowChar + " character to complete a CD arrow.", rowNodes[k]); + } + + labels[labelNum].body.push(rowNodes[k]); + } + + if (inLabel) { + // isLabelEnd never returned a true. + throw new src_ParseError("Missing a " + arrowChar + " character to complete a CD arrow.", rowNodes[j]); + } + } + } else { + throw new src_ParseError("Expected one of \"<>AV=|.\" after @", rowNodes[j]); + } // Now join the arrow to its labels. + + + const arrow = cdArrow(arrowChar, labels, parser); // Wrap the arrow in ParseNode<"styling">. + // This is done to match parseArray() behavior. + + const wrappedArrow = { + type: "styling", + body: [arrow], + mode: "math", + style: "display" // CD is always displaystyle. + + }; + row.push(wrappedArrow); // In CD's syntax, cells are implicit. That is, everything that + // is not an arrow gets collected into a cell. So create an empty + // cell now. It will collect upcoming parseNodes. + + cell = newCell(); + } + } + + if (i % 2 === 0) { + // Even-numbered rows consist of: cell, arrow, cell, arrow, ... cell + // The last cell is not yet pushed into `row`, so: + row.push(cell); + } else { + // Odd-numbered rows consist of: vert arrow, empty cell, ... vert arrow + // Remove the empty cell that was placed at the beginning of `row`. + row.shift(); + } + + row = []; + body.push(row); + } // End row group + + + parser.gullet.endGroup(); // End array group defining \\ + + parser.gullet.endGroup(); // define column separation. + + const cols = new Array(body[0].length).fill({ + type: "align", + align: "c", + pregap: 0.25, + // CD package sets \enskip between columns. + postgap: 0.25 // So pre and post each get half an \enskip, i.e. 0.25em. + + }); + return { + type: "array", + mode: "math", + body, + arraystretch: 1, + addJot: true, + rowGaps: [null], + cols, + colSeparationType: "CD", + hLinesBeforeRow: new Array(body.length + 1).fill([]) + }; +} // The functions below are not available for general use. +// They are here only for internal use by the {CD} environment in placing labels +// next to vertical arrows. +// We don't need any such functions for horizontal arrows because we can reuse +// the functionality that already exists for extensible arrows. + +defineFunction({ + type: "cdlabel", + names: ["\\\\cdleft", "\\\\cdright"], + props: { + numArgs: 1 + }, + + handler(_ref, args) { + let { + parser, + funcName + } = _ref; + return { + type: "cdlabel", + mode: parser.mode, + side: funcName.slice(4), + label: args[0] + }; + }, + + htmlBuilder(group, options) { + const newOptions = options.havingStyle(options.style.sup()); + const label = buildCommon.wrapFragment(buildGroup(group.label, newOptions, options), options); + label.classes.push("cd-label-" + group.side); + label.style.bottom = makeEm(0.8 - label.depth); // Zero out label height & depth, so vertical align of arrow is set + // by the arrow height, not by the label. + + label.height = 0; + label.depth = 0; + return label; + }, + + mathmlBuilder(group, options) { + let label = new mathMLTree.MathNode("mrow", [buildMathML_buildGroup(group.label, options)]); + label = new mathMLTree.MathNode("mpadded", [label]); + label.setAttribute("width", "0"); + + if (group.side === "left") { + label.setAttribute("lspace", "-1width"); + } // We have to guess at vertical alignment. We know the arrow is 1.8em tall, + // But we don't know the height or depth of the label. + + + label.setAttribute("voffset", "0.7em"); + label = new mathMLTree.MathNode("mstyle", [label]); + label.setAttribute("displaystyle", "false"); + label.setAttribute("scriptlevel", "1"); + return label; + } + +}); +defineFunction({ + type: "cdlabelparent", + names: ["\\\\cdparent"], + props: { + numArgs: 1 + }, + + handler(_ref2, args) { + let { + parser + } = _ref2; + return { + type: "cdlabelparent", + mode: parser.mode, + fragment: args[0] + }; + }, + + htmlBuilder(group, options) { + // Wrap the vertical arrow and its labels. + // The parent gets position: relative. The child gets position: absolute. + // So CSS can locate the label correctly. + const parent = buildCommon.wrapFragment(buildGroup(group.fragment, options), options); + parent.classes.push("cd-vert-arrow"); + return parent; + }, + + mathmlBuilder(group, options) { + return new mathMLTree.MathNode("mrow", [buildMathML_buildGroup(group.fragment, options)]); + } + +}); +;// CONCATENATED MODULE: ./src/functions/char.js + + + // \@char is an internal function that takes a grouped decimal argument like +// {123} and converts into symbol with code 123. It is used by the *macro* +// \char defined in macros.js. + +defineFunction({ + type: "textord", + names: ["\\@char"], + props: { + numArgs: 1, + allowedInText: true + }, + + handler(_ref, args) { + let { + parser + } = _ref; + const arg = assertNodeType(args[0], "ordgroup"); + const group = arg.body; + let number = ""; + + for (let i = 0; i < group.length; i++) { + const node = assertNodeType(group[i], "textord"); + number += node.text; + } + + let code = parseInt(number); + let text; + + if (isNaN(code)) { + throw new src_ParseError("\\@char has non-numeric argument " + number); // If we drop IE support, the following code could be replaced with + // text = String.fromCodePoint(code) + } else if (code < 0 || code >= 0x10ffff) { + throw new src_ParseError("\\@char with invalid code point " + number); + } else if (code <= 0xffff) { + text = String.fromCharCode(code); + } else { + // Astral code point; split into surrogate halves + code -= 0x10000; + text = String.fromCharCode((code >> 10) + 0xd800, (code & 0x3ff) + 0xdc00); + } + + return { + type: "textord", + mode: parser.mode, + text: text + }; + } + +}); +;// CONCATENATED MODULE: ./src/functions/color.js + + + + + + + +const color_htmlBuilder = (group, options) => { + const elements = buildExpression(group.body, options.withColor(group.color), false); // \color isn't supposed to affect the type of the elements it contains. + // To accomplish this, we wrap the results in a fragment, so the inner + // elements will be able to directly interact with their neighbors. For + // example, `\color{red}{2 +} 3` has the same spacing as `2 + 3` + + return buildCommon.makeFragment(elements); +}; + +const color_mathmlBuilder = (group, options) => { + const inner = buildMathML_buildExpression(group.body, options.withColor(group.color)); + const node = new mathMLTree.MathNode("mstyle", inner); + node.setAttribute("mathcolor", group.color); + return node; +}; + +defineFunction({ + type: "color", + names: ["\\textcolor"], + props: { + numArgs: 2, + allowedInText: true, + argTypes: ["color", "original"] + }, + + handler(_ref, args) { + let { + parser + } = _ref; + const color = assertNodeType(args[0], "color-token").color; + const body = args[1]; + return { + type: "color", + mode: parser.mode, + color, + body: ordargument(body) + }; + }, + + htmlBuilder: color_htmlBuilder, + mathmlBuilder: color_mathmlBuilder +}); +defineFunction({ + type: "color", + names: ["\\color"], + props: { + numArgs: 1, + allowedInText: true, + argTypes: ["color"] + }, + + handler(_ref2, args) { + let { + parser, + breakOnTokenText + } = _ref2; + const color = assertNodeType(args[0], "color-token").color; // Set macro \current@color in current namespace to store the current + // color, mimicking the behavior of color.sty. + // This is currently used just to correctly color a \right + // that follows a \color command. + + parser.gullet.macros.set("\\current@color", color); // Parse out the implicit body that should be colored. + + const body = parser.parseExpression(true, breakOnTokenText); + return { + type: "color", + mode: parser.mode, + color, + body + }; + }, + + htmlBuilder: color_htmlBuilder, + mathmlBuilder: color_mathmlBuilder +}); +;// CONCATENATED MODULE: ./src/functions/cr.js +// Row breaks within tabular environments, and line breaks at top level + + + + + // \DeclareRobustCommand\\{...\@xnewline} + +defineFunction({ + type: "cr", + names: ["\\\\"], + props: { + numArgs: 0, + numOptionalArgs: 0, + allowedInText: true + }, + + handler(_ref, args, optArgs) { + let { + parser + } = _ref; + const size = parser.gullet.future().text === "[" ? parser.parseSizeGroup(true) : null; + const newLine = !parser.settings.displayMode || !parser.settings.useStrictBehavior("newLineInDisplayMode", "In LaTeX, \\\\ or \\newline " + "does nothing in display mode"); + return { + type: "cr", + mode: parser.mode, + newLine, + size: size && assertNodeType(size, "size").value + }; + }, + + // The following builders are called only at the top level, + // not within tabular/array environments. + htmlBuilder(group, options) { + const span = buildCommon.makeSpan(["mspace"], [], options); + + if (group.newLine) { + span.classes.push("newline"); + + if (group.size) { + span.style.marginTop = makeEm(calculateSize(group.size, options)); + } + } + + return span; + }, + + mathmlBuilder(group, options) { + const node = new mathMLTree.MathNode("mspace"); + + if (group.newLine) { + node.setAttribute("linebreak", "newline"); + + if (group.size) { + node.setAttribute("height", makeEm(calculateSize(group.size, options))); + } + } + + return node; + } + +}); +;// CONCATENATED MODULE: ./src/functions/def.js + + + +const globalMap = { + "\\global": "\\global", + "\\long": "\\\\globallong", + "\\\\globallong": "\\\\globallong", + "\\def": "\\gdef", + "\\gdef": "\\gdef", + "\\edef": "\\xdef", + "\\xdef": "\\xdef", + "\\let": "\\\\globallet", + "\\futurelet": "\\\\globalfuture" +}; + +const checkControlSequence = tok => { + const name = tok.text; + + if (/^(?:[\\{}$&#^_]|EOF)$/.test(name)) { + throw new src_ParseError("Expected a control sequence", tok); + } + + return name; +}; + +const getRHS = parser => { + let tok = parser.gullet.popToken(); + + if (tok.text === "=") { + // consume optional equals + tok = parser.gullet.popToken(); + + if (tok.text === " ") { + // consume one optional space + tok = parser.gullet.popToken(); + } + } + + return tok; +}; + +const letCommand = (parser, name, tok, global) => { + let macro = parser.gullet.macros.get(tok.text); + + if (macro == null) { + // don't expand it later even if a macro with the same name is defined + // e.g., \let\foo=\frac \def\frac{\relax} \frac12 + tok.noexpand = true; + macro = { + tokens: [tok], + numArgs: 0, + // reproduce the same behavior in expansion + unexpandable: !parser.gullet.isExpandable(tok.text) + }; + } + + parser.gullet.macros.set(name, macro, global); +}; // -> | +// -> |\global +// -> | +// -> \global|\long|\outer + + +defineFunction({ + type: "internal", + names: ["\\global", "\\long", "\\\\globallong" // can’t be entered directly + ], + props: { + numArgs: 0, + allowedInText: true + }, + + handler(_ref) { + let { + parser, + funcName + } = _ref; + parser.consumeSpaces(); + const token = parser.fetch(); + + if (globalMap[token.text]) { + // KaTeX doesn't have \par, so ignore \long + if (funcName === "\\global" || funcName === "\\\\globallong") { + token.text = globalMap[token.text]; + } + + return assertNodeType(parser.parseFunction(), "internal"); + } + + throw new src_ParseError("Invalid token after macro prefix", token); + } + +}); // Basic support for macro definitions: \def, \gdef, \edef, \xdef +// -> +// -> \def|\gdef|\edef|\xdef +// -> + +defineFunction({ + type: "internal", + names: ["\\def", "\\gdef", "\\edef", "\\xdef"], + props: { + numArgs: 0, + allowedInText: true, + primitive: true + }, + + handler(_ref2) { + let { + parser, + funcName + } = _ref2; + let tok = parser.gullet.popToken(); + const name = tok.text; + + if (/^(?:[\\{}$&#^_]|EOF)$/.test(name)) { + throw new src_ParseError("Expected a control sequence", tok); + } + + let numArgs = 0; + let insert; + const delimiters = [[]]; // contains no braces + + while (parser.gullet.future().text !== "{") { + tok = parser.gullet.popToken(); + + if (tok.text === "#") { + // If the very last character of the is #, so that + // this # is immediately followed by {, TeX will behave as if the { + // had been inserted at the right end of both the parameter text + // and the replacement text. + if (parser.gullet.future().text === "{") { + insert = parser.gullet.future(); + delimiters[numArgs].push("{"); + break; + } // A parameter, the first appearance of # must be followed by 1, + // the next by 2, and so on; up to nine #’s are allowed + + + tok = parser.gullet.popToken(); + + if (!/^[1-9]$/.test(tok.text)) { + throw new src_ParseError("Invalid argument number \"" + tok.text + "\""); + } + + if (parseInt(tok.text) !== numArgs + 1) { + throw new src_ParseError("Argument number \"" + tok.text + "\" out of order"); + } + + numArgs++; + delimiters.push([]); + } else if (tok.text === "EOF") { + throw new src_ParseError("Expected a macro definition"); + } else { + delimiters[numArgs].push(tok.text); + } + } // replacement text, enclosed in '{' and '}' and properly nested + + + let { + tokens + } = parser.gullet.consumeArg(); + + if (insert) { + tokens.unshift(insert); + } + + if (funcName === "\\edef" || funcName === "\\xdef") { + tokens = parser.gullet.expandTokens(tokens); + tokens.reverse(); // to fit in with stack order + } // Final arg is the expansion of the macro + + + parser.gullet.macros.set(name, { + tokens, + numArgs, + delimiters + }, funcName === globalMap[funcName]); + return { + type: "internal", + mode: parser.mode + }; + } + +}); // -> +// -> \futurelet +// | \let +// -> |= + +defineFunction({ + type: "internal", + names: ["\\let", "\\\\globallet" // can’t be entered directly + ], + props: { + numArgs: 0, + allowedInText: true, + primitive: true + }, + + handler(_ref3) { + let { + parser, + funcName + } = _ref3; + const name = checkControlSequence(parser.gullet.popToken()); + parser.gullet.consumeSpaces(); + const tok = getRHS(parser); + letCommand(parser, name, tok, funcName === "\\\\globallet"); + return { + type: "internal", + mode: parser.mode + }; + } + +}); // ref: https://www.tug.org/TUGboat/tb09-3/tb22bechtolsheim.pdf + +defineFunction({ + type: "internal", + names: ["\\futurelet", "\\\\globalfuture" // can’t be entered directly + ], + props: { + numArgs: 0, + allowedInText: true, + primitive: true + }, + + handler(_ref4) { + let { + parser, + funcName + } = _ref4; + const name = checkControlSequence(parser.gullet.popToken()); + const middle = parser.gullet.popToken(); + const tok = parser.gullet.popToken(); + letCommand(parser, name, tok, funcName === "\\\\globalfuture"); + parser.gullet.pushToken(tok); + parser.gullet.pushToken(middle); + return { + type: "internal", + mode: parser.mode + }; + } + +}); +;// CONCATENATED MODULE: ./src/delimiter.js +/** + * This file deals with creating delimiters of various sizes. The TeXbook + * discusses these routines on page 441-442, in the "Another subroutine sets box + * x to a specified variable delimiter" paragraph. + * + * There are three main routines here. `makeSmallDelim` makes a delimiter in the + * normal font, but in either text, script, or scriptscript style. + * `makeLargeDelim` makes a delimiter in textstyle, but in one of the Size1, + * Size2, Size3, or Size4 fonts. `makeStackedDelim` makes a delimiter out of + * smaller pieces that are stacked on top of one another. + * + * The functions take a parameter `center`, which determines if the delimiter + * should be centered around the axis. + * + * Then, there are three exposed functions. `sizedDelim` makes a delimiter in + * one of the given sizes. This is used for things like `\bigl`. + * `customSizedDelim` makes a delimiter with a given total height+depth. It is + * called in places like `\sqrt`. `leftRightDelim` makes an appropriate + * delimiter which surrounds an expression of a given height an depth. It is + * used in `\left` and `\right`. + */ + + + + + + + + + + + +/** + * Get the metrics for a given symbol and font, after transformation (i.e. + * after following replacement from symbols.js) + */ +const getMetrics = function (symbol, font, mode) { + const replace = src_symbols.math[symbol] && src_symbols.math[symbol].replace; + const metrics = getCharacterMetrics(replace || symbol, font, mode); + + if (!metrics) { + throw new Error("Unsupported symbol " + symbol + " and font size " + font + "."); + } + + return metrics; +}; +/** + * Puts a delimiter span in a given style, and adds appropriate height, depth, + * and maxFontSizes. + */ + + +const styleWrap = function (delim, toStyle, options, classes) { + const newOptions = options.havingBaseStyle(toStyle); + const span = buildCommon.makeSpan(classes.concat(newOptions.sizingClasses(options)), [delim], options); + const delimSizeMultiplier = newOptions.sizeMultiplier / options.sizeMultiplier; + span.height *= delimSizeMultiplier; + span.depth *= delimSizeMultiplier; + span.maxFontSize = newOptions.sizeMultiplier; + return span; +}; + +const centerSpan = function (span, options, style) { + const newOptions = options.havingBaseStyle(style); + const shift = (1 - options.sizeMultiplier / newOptions.sizeMultiplier) * options.fontMetrics().axisHeight; + span.classes.push("delimcenter"); + span.style.top = makeEm(shift); + span.height -= shift; + span.depth += shift; +}; +/** + * Makes a small delimiter. This is a delimiter that comes in the Main-Regular + * font, but is restyled to either be in textstyle, scriptstyle, or + * scriptscriptstyle. + */ + + +const makeSmallDelim = function (delim, style, center, options, mode, classes) { + const text = buildCommon.makeSymbol(delim, "Main-Regular", mode, options); + const span = styleWrap(text, style, options, classes); + + if (center) { + centerSpan(span, options, style); + } + + return span; +}; +/** + * Builds a symbol in the given font size (note size is an integer) + */ + + +const mathrmSize = function (value, size, mode, options) { + return buildCommon.makeSymbol(value, "Size" + size + "-Regular", mode, options); +}; +/** + * Makes a large delimiter. This is a delimiter that comes in the Size1, Size2, + * Size3, or Size4 fonts. It is always rendered in textstyle. + */ + + +const makeLargeDelim = function (delim, size, center, options, mode, classes) { + const inner = mathrmSize(delim, size, mode, options); + const span = styleWrap(buildCommon.makeSpan(["delimsizing", "size" + size], [inner], options), src_Style.TEXT, options, classes); + + if (center) { + centerSpan(span, options, src_Style.TEXT); + } + + return span; +}; +/** + * Make a span from a font glyph with the given offset and in the given font. + * This is used in makeStackedDelim to make the stacking pieces for the delimiter. + */ + + +const makeGlyphSpan = function (symbol, font, mode) { + let sizeClass; // Apply the correct CSS class to choose the right font. + + if (font === "Size1-Regular") { + sizeClass = "delim-size1"; + } else + /* if (font === "Size4-Regular") */ + { + sizeClass = "delim-size4"; + } + + const corner = buildCommon.makeSpan(["delimsizinginner", sizeClass], [buildCommon.makeSpan([], [buildCommon.makeSymbol(symbol, font, mode)])]); // Since this will be passed into `makeVList` in the end, wrap the element + // in the appropriate tag that VList uses. + + return { + type: "elem", + elem: corner + }; +}; + +const makeInner = function (ch, height, options) { + // Create a span with inline SVG for the inner part of a tall stacked delimiter. + const width = fontMetricsData['Size4-Regular'][ch.charCodeAt(0)] ? fontMetricsData['Size4-Regular'][ch.charCodeAt(0)][4] : fontMetricsData['Size1-Regular'][ch.charCodeAt(0)][4]; + const path = new PathNode("inner", innerPath(ch, Math.round(1000 * height))); + const svgNode = new SvgNode([path], { + "width": makeEm(width), + "height": makeEm(height), + // Override CSS rule `.katex svg { width: 100% }` + "style": "width:" + makeEm(width), + "viewBox": "0 0 " + 1000 * width + " " + Math.round(1000 * height), + "preserveAspectRatio": "xMinYMin" + }); + const span = buildCommon.makeSvgSpan([], [svgNode], options); + span.height = height; + span.style.height = makeEm(height); + span.style.width = makeEm(width); + return { + type: "elem", + elem: span + }; +}; // Helpers for makeStackedDelim + + +const lapInEms = 0.008; +const lap = { + type: "kern", + size: -1 * lapInEms +}; +const verts = ["|", "\\lvert", "\\rvert", "\\vert"]; +const doubleVerts = ["\\|", "\\lVert", "\\rVert", "\\Vert"]; +/** + * Make a stacked delimiter out of a given delimiter, with the total height at + * least `heightTotal`. This routine is mentioned on page 442 of the TeXbook. + */ + +const makeStackedDelim = function (delim, heightTotal, center, options, mode, classes) { + // There are four parts, the top, an optional middle, a repeated part, and a + // bottom. + let top; + let middle; + let repeat; + let bottom; + let svgLabel = ""; + let viewBoxWidth = 0; + top = repeat = bottom = delim; + middle = null; // Also keep track of what font the delimiters are in + + let font = "Size1-Regular"; // We set the parts and font based on the symbol. Note that we use + // '\u23d0' instead of '|' and '\u2016' instead of '\\|' for the + // repeats of the arrows + + if (delim === "\\uparrow") { + repeat = bottom = "\u23d0"; + } else if (delim === "\\Uparrow") { + repeat = bottom = "\u2016"; + } else if (delim === "\\downarrow") { + top = repeat = "\u23d0"; + } else if (delim === "\\Downarrow") { + top = repeat = "\u2016"; + } else if (delim === "\\updownarrow") { + top = "\\uparrow"; + repeat = "\u23d0"; + bottom = "\\downarrow"; + } else if (delim === "\\Updownarrow") { + top = "\\Uparrow"; + repeat = "\u2016"; + bottom = "\\Downarrow"; + } else if (utils.contains(verts, delim)) { + repeat = "\u2223"; + svgLabel = "vert"; + viewBoxWidth = 333; + } else if (utils.contains(doubleVerts, delim)) { + repeat = "\u2225"; + svgLabel = "doublevert"; + viewBoxWidth = 556; + } else if (delim === "[" || delim === "\\lbrack") { + top = "\u23a1"; + repeat = "\u23a2"; + bottom = "\u23a3"; + font = "Size4-Regular"; + svgLabel = "lbrack"; + viewBoxWidth = 667; + } else if (delim === "]" || delim === "\\rbrack") { + top = "\u23a4"; + repeat = "\u23a5"; + bottom = "\u23a6"; + font = "Size4-Regular"; + svgLabel = "rbrack"; + viewBoxWidth = 667; + } else if (delim === "\\lfloor" || delim === "\u230a") { + repeat = top = "\u23a2"; + bottom = "\u23a3"; + font = "Size4-Regular"; + svgLabel = "lfloor"; + viewBoxWidth = 667; + } else if (delim === "\\lceil" || delim === "\u2308") { + top = "\u23a1"; + repeat = bottom = "\u23a2"; + font = "Size4-Regular"; + svgLabel = "lceil"; + viewBoxWidth = 667; + } else if (delim === "\\rfloor" || delim === "\u230b") { + repeat = top = "\u23a5"; + bottom = "\u23a6"; + font = "Size4-Regular"; + svgLabel = "rfloor"; + viewBoxWidth = 667; + } else if (delim === "\\rceil" || delim === "\u2309") { + top = "\u23a4"; + repeat = bottom = "\u23a5"; + font = "Size4-Regular"; + svgLabel = "rceil"; + viewBoxWidth = 667; + } else if (delim === "(" || delim === "\\lparen") { + top = "\u239b"; + repeat = "\u239c"; + bottom = "\u239d"; + font = "Size4-Regular"; + svgLabel = "lparen"; + viewBoxWidth = 875; + } else if (delim === ")" || delim === "\\rparen") { + top = "\u239e"; + repeat = "\u239f"; + bottom = "\u23a0"; + font = "Size4-Regular"; + svgLabel = "rparen"; + viewBoxWidth = 875; + } else if (delim === "\\{" || delim === "\\lbrace") { + top = "\u23a7"; + middle = "\u23a8"; + bottom = "\u23a9"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\}" || delim === "\\rbrace") { + top = "\u23ab"; + middle = "\u23ac"; + bottom = "\u23ad"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\lgroup" || delim === "\u27ee") { + top = "\u23a7"; + bottom = "\u23a9"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\rgroup" || delim === "\u27ef") { + top = "\u23ab"; + bottom = "\u23ad"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\lmoustache" || delim === "\u23b0") { + top = "\u23a7"; + bottom = "\u23ad"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\rmoustache" || delim === "\u23b1") { + top = "\u23ab"; + bottom = "\u23a9"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } // Get the metrics of the four sections + + + const topMetrics = getMetrics(top, font, mode); + const topHeightTotal = topMetrics.height + topMetrics.depth; + const repeatMetrics = getMetrics(repeat, font, mode); + const repeatHeightTotal = repeatMetrics.height + repeatMetrics.depth; + const bottomMetrics = getMetrics(bottom, font, mode); + const bottomHeightTotal = bottomMetrics.height + bottomMetrics.depth; + let middleHeightTotal = 0; + let middleFactor = 1; + + if (middle !== null) { + const middleMetrics = getMetrics(middle, font, mode); + middleHeightTotal = middleMetrics.height + middleMetrics.depth; + middleFactor = 2; // repeat symmetrically above and below middle + } // Calculate the minimal height that the delimiter can have. + // It is at least the size of the top, bottom, and optional middle combined. + + + const minHeight = topHeightTotal + bottomHeightTotal + middleHeightTotal; // Compute the number of copies of the repeat symbol we will need + + const repeatCount = Math.max(0, Math.ceil((heightTotal - minHeight) / (middleFactor * repeatHeightTotal))); // Compute the total height of the delimiter including all the symbols + + const realHeightTotal = minHeight + repeatCount * middleFactor * repeatHeightTotal; // The center of the delimiter is placed at the center of the axis. Note + // that in this context, "center" means that the delimiter should be + // centered around the axis in the current style, while normally it is + // centered around the axis in textstyle. + + let axisHeight = options.fontMetrics().axisHeight; + + if (center) { + axisHeight *= options.sizeMultiplier; + } // Calculate the depth + + + const depth = realHeightTotal / 2 - axisHeight; // Now, we start building the pieces that will go into the vlist + // Keep a list of the pieces of the stacked delimiter + + const stack = []; + + if (svgLabel.length > 0) { + // Instead of stacking glyphs, create a single SVG. + // This evades browser problems with imprecise positioning of spans. + const midHeight = realHeightTotal - topHeightTotal - bottomHeightTotal; + const viewBoxHeight = Math.round(realHeightTotal * 1000); + const pathStr = tallDelim(svgLabel, Math.round(midHeight * 1000)); + const path = new PathNode(svgLabel, pathStr); + const width = (viewBoxWidth / 1000).toFixed(3) + "em"; + const height = (viewBoxHeight / 1000).toFixed(3) + "em"; + const svg = new SvgNode([path], { + "width": width, + "height": height, + "viewBox": "0 0 " + viewBoxWidth + " " + viewBoxHeight + }); + const wrapper = buildCommon.makeSvgSpan([], [svg], options); + wrapper.height = viewBoxHeight / 1000; + wrapper.style.width = width; + wrapper.style.height = height; + stack.push({ + type: "elem", + elem: wrapper + }); + } else { + // Stack glyphs + // Start by adding the bottom symbol + stack.push(makeGlyphSpan(bottom, font, mode)); + stack.push(lap); // overlap + + if (middle === null) { + // The middle section will be an SVG. Make it an extra 0.016em tall. + // We'll overlap by 0.008em at top and bottom. + const innerHeight = realHeightTotal - topHeightTotal - bottomHeightTotal + 2 * lapInEms; + stack.push(makeInner(repeat, innerHeight, options)); + } else { + // When there is a middle bit, we need the middle part and two repeated + // sections + const innerHeight = (realHeightTotal - topHeightTotal - bottomHeightTotal - middleHeightTotal) / 2 + 2 * lapInEms; + stack.push(makeInner(repeat, innerHeight, options)); // Now insert the middle of the brace. + + stack.push(lap); + stack.push(makeGlyphSpan(middle, font, mode)); + stack.push(lap); + stack.push(makeInner(repeat, innerHeight, options)); + } // Add the top symbol + + + stack.push(lap); + stack.push(makeGlyphSpan(top, font, mode)); + } // Finally, build the vlist + + + const newOptions = options.havingBaseStyle(src_Style.TEXT); + const inner = buildCommon.makeVList({ + positionType: "bottom", + positionData: depth, + children: stack + }, newOptions); + return styleWrap(buildCommon.makeSpan(["delimsizing", "mult"], [inner], newOptions), src_Style.TEXT, options, classes); +}; // All surds have 0.08em padding above the vinculum inside the SVG. +// That keeps browser span height rounding error from pinching the line. + + +const vbPad = 80; // padding above the surd, measured inside the viewBox. + +const emPad = 0.08; // padding, in ems, measured in the document. + +const sqrtSvg = function (sqrtName, height, viewBoxHeight, extraVinculum, options) { + const path = sqrtPath(sqrtName, extraVinculum, viewBoxHeight); + const pathNode = new PathNode(sqrtName, path); + const svg = new SvgNode([pathNode], { + // Note: 1000:1 ratio of viewBox to document em width. + "width": "400em", + "height": makeEm(height), + "viewBox": "0 0 400000 " + viewBoxHeight, + "preserveAspectRatio": "xMinYMin slice" + }); + return buildCommon.makeSvgSpan(["hide-tail"], [svg], options); +}; +/** + * Make a sqrt image of the given height, + */ + + +const makeSqrtImage = function (height, options) { + // Define a newOptions that removes the effect of size changes such as \Huge. + // We don't pick different a height surd for \Huge. For it, we scale up. + const newOptions = options.havingBaseSizing(); // Pick the desired surd glyph from a sequence of surds. + + const delim = traverseSequence("\\surd", height * newOptions.sizeMultiplier, stackLargeDelimiterSequence, newOptions); + let sizeMultiplier = newOptions.sizeMultiplier; // default + // The standard sqrt SVGs each have a 0.04em thick vinculum. + // If Settings.minRuleThickness is larger than that, we add extraVinculum. + + const extraVinculum = Math.max(0, options.minRuleThickness - options.fontMetrics().sqrtRuleThickness); // Create a span containing an SVG image of a sqrt symbol. + + let span; + let spanHeight = 0; + let texHeight = 0; + let viewBoxHeight = 0; + let advanceWidth; // We create viewBoxes with 80 units of "padding" above each surd. + // Then browser rounding error on the parent span height will not + // encroach on the ink of the vinculum. But that padding is not + // included in the TeX-like `height` used for calculation of + // vertical alignment. So texHeight = span.height < span.style.height. + + if (delim.type === "small") { + // Get an SVG that is derived from glyph U+221A in font KaTeX-Main. + // 1000 unit normal glyph height. + viewBoxHeight = 1000 + 1000 * extraVinculum + vbPad; + + if (height < 1.0) { + sizeMultiplier = 1.0; // mimic a \textfont radical + } else if (height < 1.4) { + sizeMultiplier = 0.7; // mimic a \scriptfont radical + } + + spanHeight = (1.0 + extraVinculum + emPad) / sizeMultiplier; + texHeight = (1.00 + extraVinculum) / sizeMultiplier; + span = sqrtSvg("sqrtMain", spanHeight, viewBoxHeight, extraVinculum, options); + span.style.minWidth = "0.853em"; + advanceWidth = 0.833 / sizeMultiplier; // from the font. + } else if (delim.type === "large") { + // These SVGs come from fonts: KaTeX_Size1, _Size2, etc. + viewBoxHeight = (1000 + vbPad) * sizeToMaxHeight[delim.size]; + texHeight = (sizeToMaxHeight[delim.size] + extraVinculum) / sizeMultiplier; + spanHeight = (sizeToMaxHeight[delim.size] + extraVinculum + emPad) / sizeMultiplier; + span = sqrtSvg("sqrtSize" + delim.size, spanHeight, viewBoxHeight, extraVinculum, options); + span.style.minWidth = "1.02em"; + advanceWidth = 1.0 / sizeMultiplier; // 1.0 from the font. + } else { + // Tall sqrt. In TeX, this would be stacked using multiple glyphs. + // We'll use a single SVG to accomplish the same thing. + spanHeight = height + extraVinculum + emPad; + texHeight = height + extraVinculum; + viewBoxHeight = Math.floor(1000 * height + extraVinculum) + vbPad; + span = sqrtSvg("sqrtTall", spanHeight, viewBoxHeight, extraVinculum, options); + span.style.minWidth = "0.742em"; + advanceWidth = 1.056; + } + + span.height = texHeight; + span.style.height = makeEm(spanHeight); + return { + span, + advanceWidth, + // Calculate the actual line width. + // This actually should depend on the chosen font -- e.g. \boldmath + // should use the thicker surd symbols from e.g. KaTeX_Main-Bold, and + // have thicker rules. + ruleWidth: (options.fontMetrics().sqrtRuleThickness + extraVinculum) * sizeMultiplier + }; +}; // There are three kinds of delimiters, delimiters that stack when they become +// too large + + +const stackLargeDelimiters = ["(", "\\lparen", ")", "\\rparen", "[", "\\lbrack", "]", "\\rbrack", "\\{", "\\lbrace", "\\}", "\\rbrace", "\\lfloor", "\\rfloor", "\u230a", "\u230b", "\\lceil", "\\rceil", "\u2308", "\u2309", "\\surd"]; // delimiters that always stack + +const stackAlwaysDelimiters = ["\\uparrow", "\\downarrow", "\\updownarrow", "\\Uparrow", "\\Downarrow", "\\Updownarrow", "|", "\\|", "\\vert", "\\Vert", "\\lvert", "\\rvert", "\\lVert", "\\rVert", "\\lgroup", "\\rgroup", "\u27ee", "\u27ef", "\\lmoustache", "\\rmoustache", "\u23b0", "\u23b1"]; // and delimiters that never stack + +const stackNeverDelimiters = ["<", ">", "\\langle", "\\rangle", "/", "\\backslash", "\\lt", "\\gt"]; // Metrics of the different sizes. Found by looking at TeX's output of +// $\bigl| // \Bigl| \biggl| \Biggl| \showlists$ +// Used to create stacked delimiters of appropriate sizes in makeSizedDelim. + +const sizeToMaxHeight = [0, 1.2, 1.8, 2.4, 3.0]; +/** + * Used to create a delimiter of a specific size, where `size` is 1, 2, 3, or 4. + */ + +const makeSizedDelim = function (delim, size, options, mode, classes) { + // < and > turn into \langle and \rangle in delimiters + if (delim === "<" || delim === "\\lt" || delim === "\u27e8") { + delim = "\\langle"; + } else if (delim === ">" || delim === "\\gt" || delim === "\u27e9") { + delim = "\\rangle"; + } // Sized delimiters are never centered. + + + if (utils.contains(stackLargeDelimiters, delim) || utils.contains(stackNeverDelimiters, delim)) { + return makeLargeDelim(delim, size, false, options, mode, classes); + } else if (utils.contains(stackAlwaysDelimiters, delim)) { + return makeStackedDelim(delim, sizeToMaxHeight[size], false, options, mode, classes); + } else { + throw new src_ParseError("Illegal delimiter: '" + delim + "'"); + } +}; +/** + * There are three different sequences of delimiter sizes that the delimiters + * follow depending on the kind of delimiter. This is used when creating custom + * sized delimiters to decide whether to create a small, large, or stacked + * delimiter. + * + * In real TeX, these sequences aren't explicitly defined, but are instead + * defined inside the font metrics. Since there are only three sequences that + * are possible for the delimiters that TeX defines, it is easier to just encode + * them explicitly here. + */ + + +// Delimiters that never stack try small delimiters and large delimiters only +const stackNeverDelimiterSequence = [{ + type: "small", + style: src_Style.SCRIPTSCRIPT +}, { + type: "small", + style: src_Style.SCRIPT +}, { + type: "small", + style: src_Style.TEXT +}, { + type: "large", + size: 1 +}, { + type: "large", + size: 2 +}, { + type: "large", + size: 3 +}, { + type: "large", + size: 4 +}]; // Delimiters that always stack try the small delimiters first, then stack + +const stackAlwaysDelimiterSequence = [{ + type: "small", + style: src_Style.SCRIPTSCRIPT +}, { + type: "small", + style: src_Style.SCRIPT +}, { + type: "small", + style: src_Style.TEXT +}, { + type: "stack" +}]; // Delimiters that stack when large try the small and then large delimiters, and +// stack afterwards + +const stackLargeDelimiterSequence = [{ + type: "small", + style: src_Style.SCRIPTSCRIPT +}, { + type: "small", + style: src_Style.SCRIPT +}, { + type: "small", + style: src_Style.TEXT +}, { + type: "large", + size: 1 +}, { + type: "large", + size: 2 +}, { + type: "large", + size: 3 +}, { + type: "large", + size: 4 +}, { + type: "stack" +}]; +/** + * Get the font used in a delimiter based on what kind of delimiter it is. + * TODO(#963) Use more specific font family return type once that is introduced. + */ + +const delimTypeToFont = function (type) { + if (type.type === "small") { + return "Main-Regular"; + } else if (type.type === "large") { + return "Size" + type.size + "-Regular"; + } else if (type.type === "stack") { + return "Size4-Regular"; + } else { + throw new Error("Add support for delim type '" + type.type + "' here."); + } +}; +/** + * Traverse a sequence of types of delimiters to decide what kind of delimiter + * should be used to create a delimiter of the given height+depth. + */ + + +const traverseSequence = function (delim, height, sequence, options) { + // Here, we choose the index we should start at in the sequences. In smaller + // sizes (which correspond to larger numbers in style.size) we start earlier + // in the sequence. Thus, scriptscript starts at index 3-3=0, script starts + // at index 3-2=1, text starts at 3-1=2, and display starts at min(2,3-0)=2 + const start = Math.min(2, 3 - options.style.size); + + for (let i = start; i < sequence.length; i++) { + if (sequence[i].type === "stack") { + // This is always the last delimiter, so we just break the loop now. + break; + } + + const metrics = getMetrics(delim, delimTypeToFont(sequence[i]), "math"); + let heightDepth = metrics.height + metrics.depth; // Small delimiters are scaled down versions of the same font, so we + // account for the style change size. + + if (sequence[i].type === "small") { + const newOptions = options.havingBaseStyle(sequence[i].style); + heightDepth *= newOptions.sizeMultiplier; + } // Check if the delimiter at this size works for the given height. + + + if (heightDepth > height) { + return sequence[i]; + } + } // If we reached the end of the sequence, return the last sequence element. + + + return sequence[sequence.length - 1]; +}; +/** + * Make a delimiter of a given height+depth, with optional centering. Here, we + * traverse the sequences, and create a delimiter that the sequence tells us to. + */ + + +const makeCustomSizedDelim = function (delim, height, center, options, mode, classes) { + if (delim === "<" || delim === "\\lt" || delim === "\u27e8") { + delim = "\\langle"; + } else if (delim === ">" || delim === "\\gt" || delim === "\u27e9") { + delim = "\\rangle"; + } // Decide what sequence to use + + + let sequence; + + if (utils.contains(stackNeverDelimiters, delim)) { + sequence = stackNeverDelimiterSequence; + } else if (utils.contains(stackLargeDelimiters, delim)) { + sequence = stackLargeDelimiterSequence; + } else { + sequence = stackAlwaysDelimiterSequence; + } // Look through the sequence + + + const delimType = traverseSequence(delim, height, sequence, options); // Get the delimiter from font glyphs. + // Depending on the sequence element we decided on, call the + // appropriate function. + + if (delimType.type === "small") { + return makeSmallDelim(delim, delimType.style, center, options, mode, classes); + } else if (delimType.type === "large") { + return makeLargeDelim(delim, delimType.size, center, options, mode, classes); + } else + /* if (delimType.type === "stack") */ + { + return makeStackedDelim(delim, height, center, options, mode, classes); + } +}; +/** + * Make a delimiter for use with `\left` and `\right`, given a height and depth + * of an expression that the delimiters surround. + */ + + +const makeLeftRightDelim = function (delim, height, depth, options, mode, classes) { + // We always center \left/\right delimiters, so the axis is always shifted + const axisHeight = options.fontMetrics().axisHeight * options.sizeMultiplier; // Taken from TeX source, tex.web, function make_left_right + + const delimiterFactor = 901; + const delimiterExtend = 5.0 / options.fontMetrics().ptPerEm; + const maxDistFromAxis = Math.max(height - axisHeight, depth + axisHeight); + const totalHeight = Math.max( // In real TeX, calculations are done using integral values which are + // 65536 per pt, or 655360 per em. So, the division here truncates in + // TeX but doesn't here, producing different results. If we wanted to + // exactly match TeX's calculation, we could do + // Math.floor(655360 * maxDistFromAxis / 500) * + // delimiterFactor / 655360 + // (To see the difference, compare + // x^{x^{\left(\rule{0.1em}{0.68em}\right)}} + // in TeX and KaTeX) + maxDistFromAxis / 500 * delimiterFactor, 2 * maxDistFromAxis - delimiterExtend); // Finally, we defer to `makeCustomSizedDelim` with our calculated total + // height + + return makeCustomSizedDelim(delim, totalHeight, true, options, mode, classes); +}; + +/* harmony default export */ var delimiter = ({ + sqrtImage: makeSqrtImage, + sizedDelim: makeSizedDelim, + sizeToMaxHeight: sizeToMaxHeight, + customSizedDelim: makeCustomSizedDelim, + leftRightDelim: makeLeftRightDelim +}); +;// CONCATENATED MODULE: ./src/functions/delimsizing.js + + + + + + + + + + +// Extra data needed for the delimiter handler down below +const delimiterSizes = { + "\\bigl": { + mclass: "mopen", + size: 1 + }, + "\\Bigl": { + mclass: "mopen", + size: 2 + }, + "\\biggl": { + mclass: "mopen", + size: 3 + }, + "\\Biggl": { + mclass: "mopen", + size: 4 + }, + "\\bigr": { + mclass: "mclose", + size: 1 + }, + "\\Bigr": { + mclass: "mclose", + size: 2 + }, + "\\biggr": { + mclass: "mclose", + size: 3 + }, + "\\Biggr": { + mclass: "mclose", + size: 4 + }, + "\\bigm": { + mclass: "mrel", + size: 1 + }, + "\\Bigm": { + mclass: "mrel", + size: 2 + }, + "\\biggm": { + mclass: "mrel", + size: 3 + }, + "\\Biggm": { + mclass: "mrel", + size: 4 + }, + "\\big": { + mclass: "mord", + size: 1 + }, + "\\Big": { + mclass: "mord", + size: 2 + }, + "\\bigg": { + mclass: "mord", + size: 3 + }, + "\\Bigg": { + mclass: "mord", + size: 4 + } +}; +const delimiters = ["(", "\\lparen", ")", "\\rparen", "[", "\\lbrack", "]", "\\rbrack", "\\{", "\\lbrace", "\\}", "\\rbrace", "\\lfloor", "\\rfloor", "\u230a", "\u230b", "\\lceil", "\\rceil", "\u2308", "\u2309", "<", ">", "\\langle", "\u27e8", "\\rangle", "\u27e9", "\\lt", "\\gt", "\\lvert", "\\rvert", "\\lVert", "\\rVert", "\\lgroup", "\\rgroup", "\u27ee", "\u27ef", "\\lmoustache", "\\rmoustache", "\u23b0", "\u23b1", "/", "\\backslash", "|", "\\vert", "\\|", "\\Vert", "\\uparrow", "\\Uparrow", "\\downarrow", "\\Downarrow", "\\updownarrow", "\\Updownarrow", "."]; + +// Delimiter functions +function checkDelimiter(delim, context) { + const symDelim = checkSymbolNodeType(delim); + + if (symDelim && utils.contains(delimiters, symDelim.text)) { + return symDelim; + } else if (symDelim) { + throw new src_ParseError("Invalid delimiter '" + symDelim.text + "' after '" + context.funcName + "'", delim); + } else { + throw new src_ParseError("Invalid delimiter type '" + delim.type + "'", delim); + } +} + +defineFunction({ + type: "delimsizing", + names: ["\\bigl", "\\Bigl", "\\biggl", "\\Biggl", "\\bigr", "\\Bigr", "\\biggr", "\\Biggr", "\\bigm", "\\Bigm", "\\biggm", "\\Biggm", "\\big", "\\Big", "\\bigg", "\\Bigg"], + props: { + numArgs: 1, + argTypes: ["primitive"] + }, + handler: (context, args) => { + const delim = checkDelimiter(args[0], context); + return { + type: "delimsizing", + mode: context.parser.mode, + size: delimiterSizes[context.funcName].size, + mclass: delimiterSizes[context.funcName].mclass, + delim: delim.text + }; + }, + htmlBuilder: (group, options) => { + if (group.delim === ".") { + // Empty delimiters still count as elements, even though they don't + // show anything. + return buildCommon.makeSpan([group.mclass]); + } // Use delimiter.sizedDelim to generate the delimiter. + + + return delimiter.sizedDelim(group.delim, group.size, options, group.mode, [group.mclass]); + }, + mathmlBuilder: group => { + const children = []; + + if (group.delim !== ".") { + children.push(makeText(group.delim, group.mode)); + } + + const node = new mathMLTree.MathNode("mo", children); + + if (group.mclass === "mopen" || group.mclass === "mclose") { + // Only some of the delimsizing functions act as fences, and they + // return "mopen" or "mclose" mclass. + node.setAttribute("fence", "true"); + } else { + // Explicitly disable fencing if it's not a fence, to override the + // defaults. + node.setAttribute("fence", "false"); + } + + node.setAttribute("stretchy", "true"); + const size = makeEm(delimiter.sizeToMaxHeight[group.size]); + node.setAttribute("minsize", size); + node.setAttribute("maxsize", size); + return node; + } +}); + +function assertParsed(group) { + if (!group.body) { + throw new Error("Bug: The leftright ParseNode wasn't fully parsed."); + } +} + +defineFunction({ + type: "leftright-right", + names: ["\\right"], + props: { + numArgs: 1, + primitive: true + }, + handler: (context, args) => { + // \left case below triggers parsing of \right in + // `const right = parser.parseFunction();` + // uses this return value. + const color = context.parser.gullet.macros.get("\\current@color"); + + if (color && typeof color !== "string") { + throw new src_ParseError("\\current@color set to non-string in \\right"); + } + + return { + type: "leftright-right", + mode: context.parser.mode, + delim: checkDelimiter(args[0], context).text, + color // undefined if not set via \color + + }; + } +}); +defineFunction({ + type: "leftright", + names: ["\\left"], + props: { + numArgs: 1, + primitive: true + }, + handler: (context, args) => { + const delim = checkDelimiter(args[0], context); + const parser = context.parser; // Parse out the implicit body + + ++parser.leftrightDepth; // parseExpression stops before '\\right' + + const body = parser.parseExpression(false); + --parser.leftrightDepth; // Check the next token + + parser.expect("\\right", false); + const right = assertNodeType(parser.parseFunction(), "leftright-right"); + return { + type: "leftright", + mode: parser.mode, + body, + left: delim.text, + right: right.delim, + rightColor: right.color + }; + }, + htmlBuilder: (group, options) => { + assertParsed(group); // Build the inner expression + + const inner = buildExpression(group.body, options, true, ["mopen", "mclose"]); + let innerHeight = 0; + let innerDepth = 0; + let hadMiddle = false; // Calculate its height and depth + + for (let i = 0; i < inner.length; i++) { + // Property `isMiddle` not defined on `span`. See comment in + // "middle"'s htmlBuilder. + // $FlowFixMe + if (inner[i].isMiddle) { + hadMiddle = true; + } else { + innerHeight = Math.max(inner[i].height, innerHeight); + innerDepth = Math.max(inner[i].depth, innerDepth); + } + } // The size of delimiters is the same, regardless of what style we are + // in. Thus, to correctly calculate the size of delimiter we need around + // a group, we scale down the inner size based on the size. + + + innerHeight *= options.sizeMultiplier; + innerDepth *= options.sizeMultiplier; + let leftDelim; + + if (group.left === ".") { + // Empty delimiters in \left and \right make null delimiter spaces. + leftDelim = makeNullDelimiter(options, ["mopen"]); + } else { + // Otherwise, use leftRightDelim to generate the correct sized + // delimiter. + leftDelim = delimiter.leftRightDelim(group.left, innerHeight, innerDepth, options, group.mode, ["mopen"]); + } // Add it to the beginning of the expression + + + inner.unshift(leftDelim); // Handle middle delimiters + + if (hadMiddle) { + for (let i = 1; i < inner.length; i++) { + const middleDelim = inner[i]; // Property `isMiddle` not defined on `span`. See comment in + // "middle"'s htmlBuilder. + // $FlowFixMe + + const isMiddle = middleDelim.isMiddle; + + if (isMiddle) { + // Apply the options that were active when \middle was called + inner[i] = delimiter.leftRightDelim(isMiddle.delim, innerHeight, innerDepth, isMiddle.options, group.mode, []); + } + } + } + + let rightDelim; // Same for the right delimiter, but using color specified by \color + + if (group.right === ".") { + rightDelim = makeNullDelimiter(options, ["mclose"]); + } else { + const colorOptions = group.rightColor ? options.withColor(group.rightColor) : options; + rightDelim = delimiter.leftRightDelim(group.right, innerHeight, innerDepth, colorOptions, group.mode, ["mclose"]); + } // Add it to the end of the expression. + + + inner.push(rightDelim); + return buildCommon.makeSpan(["minner"], inner, options); + }, + mathmlBuilder: (group, options) => { + assertParsed(group); + const inner = buildMathML_buildExpression(group.body, options); + + if (group.left !== ".") { + const leftNode = new mathMLTree.MathNode("mo", [makeText(group.left, group.mode)]); + leftNode.setAttribute("fence", "true"); + inner.unshift(leftNode); + } + + if (group.right !== ".") { + const rightNode = new mathMLTree.MathNode("mo", [makeText(group.right, group.mode)]); + rightNode.setAttribute("fence", "true"); + + if (group.rightColor) { + rightNode.setAttribute("mathcolor", group.rightColor); + } + + inner.push(rightNode); + } + + return makeRow(inner); + } +}); +defineFunction({ + type: "middle", + names: ["\\middle"], + props: { + numArgs: 1, + primitive: true + }, + handler: (context, args) => { + const delim = checkDelimiter(args[0], context); + + if (!context.parser.leftrightDepth) { + throw new src_ParseError("\\middle without preceding \\left", delim); + } + + return { + type: "middle", + mode: context.parser.mode, + delim: delim.text + }; + }, + htmlBuilder: (group, options) => { + let middleDelim; + + if (group.delim === ".") { + middleDelim = makeNullDelimiter(options, []); + } else { + middleDelim = delimiter.sizedDelim(group.delim, 1, options, group.mode, []); + const isMiddle = { + delim: group.delim, + options + }; // Property `isMiddle` not defined on `span`. It is only used in + // this file above. + // TODO: Fix this violation of the `span` type and possibly rename + // things since `isMiddle` sounds like a boolean, but is a struct. + // $FlowFixMe + + middleDelim.isMiddle = isMiddle; + } + + return middleDelim; + }, + mathmlBuilder: (group, options) => { + // A Firefox \middle will stretch a character vertically only if it + // is in the fence part of the operator dictionary at: + // https://www.w3.org/TR/MathML3/appendixc.html. + // So we need to avoid U+2223 and use plain "|" instead. + const textNode = group.delim === "\\vert" || group.delim === "|" ? makeText("|", "text") : makeText(group.delim, group.mode); + const middleNode = new mathMLTree.MathNode("mo", [textNode]); + middleNode.setAttribute("fence", "true"); // MathML gives 5/18em spacing to each element. + // \middle should get delimiter spacing instead. + + middleNode.setAttribute("lspace", "0.05em"); + middleNode.setAttribute("rspace", "0.05em"); + return middleNode; + } +}); +;// CONCATENATED MODULE: ./src/functions/enclose.js + + + + + + + + + + + + +const enclose_htmlBuilder = (group, options) => { + // \cancel, \bcancel, \xcancel, \sout, \fbox, \colorbox, \fcolorbox, \phase + // Some groups can return document fragments. Handle those by wrapping + // them in a span. + const inner = buildCommon.wrapFragment(buildGroup(group.body, options), options); + const label = group.label.slice(1); + let scale = options.sizeMultiplier; + let img; + let imgShift = 0; // In the LaTeX cancel package, line geometry is slightly different + // depending on whether the subject is wider than it is tall, or vice versa. + // We don't know the width of a group, so as a proxy, we test if + // the subject is a single character. This captures most of the + // subjects that should get the "tall" treatment. + + const isSingleChar = utils.isCharacterBox(group.body); + + if (label === "sout") { + img = buildCommon.makeSpan(["stretchy", "sout"]); + img.height = options.fontMetrics().defaultRuleThickness / scale; + imgShift = -0.5 * options.fontMetrics().xHeight; + } else if (label === "phase") { + // Set a couple of dimensions from the steinmetz package. + const lineWeight = calculateSize({ + number: 0.6, + unit: "pt" + }, options); + const clearance = calculateSize({ + number: 0.35, + unit: "ex" + }, options); // Prevent size changes like \Huge from affecting line thickness + + const newOptions = options.havingBaseSizing(); + scale = scale / newOptions.sizeMultiplier; + const angleHeight = inner.height + inner.depth + lineWeight + clearance; // Reserve a left pad for the angle. + + inner.style.paddingLeft = makeEm(angleHeight / 2 + lineWeight); // Create an SVG + + const viewBoxHeight = Math.floor(1000 * angleHeight * scale); + const path = phasePath(viewBoxHeight); + const svgNode = new SvgNode([new PathNode("phase", path)], { + "width": "400em", + "height": makeEm(viewBoxHeight / 1000), + "viewBox": "0 0 400000 " + viewBoxHeight, + "preserveAspectRatio": "xMinYMin slice" + }); // Wrap it in a span with overflow: hidden. + + img = buildCommon.makeSvgSpan(["hide-tail"], [svgNode], options); + img.style.height = makeEm(angleHeight); + imgShift = inner.depth + lineWeight + clearance; + } else { + // Add horizontal padding + if (/cancel/.test(label)) { + if (!isSingleChar) { + inner.classes.push("cancel-pad"); + } + } else if (label === "angl") { + inner.classes.push("anglpad"); + } else { + inner.classes.push("boxpad"); + } // Add vertical padding + + + let topPad = 0; + let bottomPad = 0; + let ruleThickness = 0; // ref: cancel package: \advance\totalheight2\p@ % "+2" + + if (/box/.test(label)) { + ruleThickness = Math.max(options.fontMetrics().fboxrule, // default + options.minRuleThickness // User override. + ); + topPad = options.fontMetrics().fboxsep + (label === "colorbox" ? 0 : ruleThickness); + bottomPad = topPad; + } else if (label === "angl") { + ruleThickness = Math.max(options.fontMetrics().defaultRuleThickness, options.minRuleThickness); + topPad = 4 * ruleThickness; // gap = 3 × line, plus the line itself. + + bottomPad = Math.max(0, 0.25 - inner.depth); + } else { + topPad = isSingleChar ? 0.2 : 0; + bottomPad = topPad; + } + + img = stretchy.encloseSpan(inner, label, topPad, bottomPad, options); + + if (/fbox|boxed|fcolorbox/.test(label)) { + img.style.borderStyle = "solid"; + img.style.borderWidth = makeEm(ruleThickness); + } else if (label === "angl" && ruleThickness !== 0.049) { + img.style.borderTopWidth = makeEm(ruleThickness); + img.style.borderRightWidth = makeEm(ruleThickness); + } + + imgShift = inner.depth + bottomPad; + + if (group.backgroundColor) { + img.style.backgroundColor = group.backgroundColor; + + if (group.borderColor) { + img.style.borderColor = group.borderColor; + } + } + } + + let vlist; + + if (group.backgroundColor) { + vlist = buildCommon.makeVList({ + positionType: "individualShift", + children: [// Put the color background behind inner; + { + type: "elem", + elem: img, + shift: imgShift + }, { + type: "elem", + elem: inner, + shift: 0 + }] + }, options); + } else { + const classes = /cancel|phase/.test(label) ? ["svg-align"] : []; + vlist = buildCommon.makeVList({ + positionType: "individualShift", + children: [// Write the \cancel stroke on top of inner. + { + type: "elem", + elem: inner, + shift: 0 + }, { + type: "elem", + elem: img, + shift: imgShift, + wrapperClasses: classes + }] + }, options); + } + + if (/cancel/.test(label)) { + // The cancel package documentation says that cancel lines add their height + // to the expression, but tests show that isn't how it actually works. + vlist.height = inner.height; + vlist.depth = inner.depth; + } + + if (/cancel/.test(label) && !isSingleChar) { + // cancel does not create horiz space for its line extension. + return buildCommon.makeSpan(["mord", "cancel-lap"], [vlist], options); + } else { + return buildCommon.makeSpan(["mord"], [vlist], options); + } +}; + +const enclose_mathmlBuilder = (group, options) => { + let fboxsep = 0; + const node = new mathMLTree.MathNode(group.label.indexOf("colorbox") > -1 ? "mpadded" : "menclose", [buildMathML_buildGroup(group.body, options)]); + + switch (group.label) { + case "\\cancel": + node.setAttribute("notation", "updiagonalstrike"); + break; + + case "\\bcancel": + node.setAttribute("notation", "downdiagonalstrike"); + break; + + case "\\phase": + node.setAttribute("notation", "phasorangle"); + break; + + case "\\sout": + node.setAttribute("notation", "horizontalstrike"); + break; + + case "\\fbox": + node.setAttribute("notation", "box"); + break; + + case "\\angl": + node.setAttribute("notation", "actuarial"); + break; + + case "\\fcolorbox": + case "\\colorbox": + // doesn't have a good notation option. So use + // instead. Set some attributes that come included with . + fboxsep = options.fontMetrics().fboxsep * options.fontMetrics().ptPerEm; + node.setAttribute("width", "+" + 2 * fboxsep + "pt"); + node.setAttribute("height", "+" + 2 * fboxsep + "pt"); + node.setAttribute("lspace", fboxsep + "pt"); // + + node.setAttribute("voffset", fboxsep + "pt"); + + if (group.label === "\\fcolorbox") { + const thk = Math.max(options.fontMetrics().fboxrule, // default + options.minRuleThickness // user override + ); + node.setAttribute("style", "border: " + thk + "em solid " + String(group.borderColor)); + } + + break; + + case "\\xcancel": + node.setAttribute("notation", "updiagonalstrike downdiagonalstrike"); + break; + } + + if (group.backgroundColor) { + node.setAttribute("mathbackground", group.backgroundColor); + } + + return node; +}; + +defineFunction({ + type: "enclose", + names: ["\\colorbox"], + props: { + numArgs: 2, + allowedInText: true, + argTypes: ["color", "text"] + }, + + handler(_ref, args, optArgs) { + let { + parser, + funcName + } = _ref; + const color = assertNodeType(args[0], "color-token").color; + const body = args[1]; + return { + type: "enclose", + mode: parser.mode, + label: funcName, + backgroundColor: color, + body + }; + }, + + htmlBuilder: enclose_htmlBuilder, + mathmlBuilder: enclose_mathmlBuilder +}); +defineFunction({ + type: "enclose", + names: ["\\fcolorbox"], + props: { + numArgs: 3, + allowedInText: true, + argTypes: ["color", "color", "text"] + }, + + handler(_ref2, args, optArgs) { + let { + parser, + funcName + } = _ref2; + const borderColor = assertNodeType(args[0], "color-token").color; + const backgroundColor = assertNodeType(args[1], "color-token").color; + const body = args[2]; + return { + type: "enclose", + mode: parser.mode, + label: funcName, + backgroundColor, + borderColor, + body + }; + }, + + htmlBuilder: enclose_htmlBuilder, + mathmlBuilder: enclose_mathmlBuilder +}); +defineFunction({ + type: "enclose", + names: ["\\fbox"], + props: { + numArgs: 1, + argTypes: ["hbox"], + allowedInText: true + }, + + handler(_ref3, args) { + let { + parser + } = _ref3; + return { + type: "enclose", + mode: parser.mode, + label: "\\fbox", + body: args[0] + }; + } + +}); +defineFunction({ + type: "enclose", + names: ["\\cancel", "\\bcancel", "\\xcancel", "\\sout", "\\phase"], + props: { + numArgs: 1 + }, + + handler(_ref4, args) { + let { + parser, + funcName + } = _ref4; + const body = args[0]; + return { + type: "enclose", + mode: parser.mode, + label: funcName, + body + }; + }, + + htmlBuilder: enclose_htmlBuilder, + mathmlBuilder: enclose_mathmlBuilder +}); +defineFunction({ + type: "enclose", + names: ["\\angl"], + props: { + numArgs: 1, + argTypes: ["hbox"], + allowedInText: false + }, + + handler(_ref5, args) { + let { + parser + } = _ref5; + return { + type: "enclose", + mode: parser.mode, + label: "\\angl", + body: args[0] + }; + } + +}); +;// CONCATENATED MODULE: ./src/defineEnvironment.js + + +/** + * All registered environments. + * `environments.js` exports this same dictionary again and makes it public. + * `Parser.js` requires this dictionary via `environments.js`. + */ +const _environments = {}; +function defineEnvironment(_ref) { + let { + type, + names, + props, + handler, + htmlBuilder, + mathmlBuilder + } = _ref; + // Set default values of environments. + const data = { + type, + numArgs: props.numArgs || 0, + allowedInText: false, + numOptionalArgs: 0, + handler + }; + + for (let i = 0; i < names.length; ++i) { + // TODO: The value type of _environments should be a type union of all + // possible `EnvSpec<>` possibilities instead of `EnvSpec<*>`, which is + // an existential type. + _environments[names[i]] = data; + } + + if (htmlBuilder) { + _htmlGroupBuilders[type] = htmlBuilder; + } + + if (mathmlBuilder) { + _mathmlGroupBuilders[type] = mathmlBuilder; + } +} +;// CONCATENATED MODULE: ./src/defineMacro.js + + +/** + * All registered global/built-in macros. + * `macros.js` exports this same dictionary again and makes it public. + * `Parser.js` requires this dictionary via `macros.js`. + */ +const _macros = {}; // This function might one day accept an additional argument and do more things. + +function defineMacro(name, body) { + _macros[name] = body; +} +;// CONCATENATED MODULE: ./src/SourceLocation.js +/** + * Lexing or parsing positional information for error reporting. + * This object is immutable. + */ +class SourceLocation { + // The + prefix indicates that these fields aren't writeable + // Lexer holding the input string. + // Start offset, zero-based inclusive. + // End offset, zero-based exclusive. + constructor(lexer, start, end) { + this.lexer = void 0; + this.start = void 0; + this.end = void 0; + this.lexer = lexer; + this.start = start; + this.end = end; + } + /** + * Merges two `SourceLocation`s from location providers, given they are + * provided in order of appearance. + * - Returns the first one's location if only the first is provided. + * - Returns a merged range of the first and the last if both are provided + * and their lexers match. + * - Otherwise, returns null. + */ + + + static range(first, second) { + if (!second) { + return first && first.loc; + } else if (!first || !first.loc || !second.loc || first.loc.lexer !== second.loc.lexer) { + return null; + } else { + return new SourceLocation(first.loc.lexer, first.loc.start, second.loc.end); + } + } + +} +;// CONCATENATED MODULE: ./src/Token.js + +/** + * Interface required to break circular dependency between Token, Lexer, and + * ParseError. + */ + +/** + * The resulting token returned from `lex`. + * + * It consists of the token text plus some position information. + * The position information is essentially a range in an input string, + * but instead of referencing the bare input string, we refer to the lexer. + * That way it is possible to attach extra metadata to the input string, + * like for example a file name or similar. + * + * The position information is optional, so it is OK to construct synthetic + * tokens if appropriate. Not providing available position information may + * lead to degraded error reporting, though. + */ +class Token { + // don't expand the token + // used in \noexpand + constructor(text, // the text of this token + loc) { + this.text = void 0; + this.loc = void 0; + this.noexpand = void 0; + this.treatAsRelax = void 0; + this.text = text; + this.loc = loc; + } + /** + * Given a pair of tokens (this and endToken), compute a `Token` encompassing + * the whole input range enclosed by these two. + */ + + + range(endToken, // last token of the range, inclusive + text // the text of the newly constructed token + ) { + return new Token(text, SourceLocation.range(this, endToken)); + } + +} +;// CONCATENATED MODULE: ./src/environments/array.js + + + + + + + + + + + + + + + + +// Helper functions +function getHLines(parser) { + // Return an array. The array length = number of hlines. + // Each element in the array tells if the line is dashed. + const hlineInfo = []; + parser.consumeSpaces(); + let nxt = parser.fetch().text; + + if (nxt === "\\relax") { + // \relax is an artifact of the \cr macro below + parser.consume(); + parser.consumeSpaces(); + nxt = parser.fetch().text; + } + + while (nxt === "\\hline" || nxt === "\\hdashline") { + parser.consume(); + hlineInfo.push(nxt === "\\hdashline"); + parser.consumeSpaces(); + nxt = parser.fetch().text; + } + + return hlineInfo; +} + +const validateAmsEnvironmentContext = context => { + const settings = context.parser.settings; + + if (!settings.displayMode) { + throw new src_ParseError("{" + context.envName + "} can be used only in" + " display mode."); + } +}; // autoTag (an argument to parseArray) can be one of three values: +// * undefined: Regular (not-top-level) array; no tags on each row +// * true: Automatic equation numbering, overridable by \tag +// * false: Tags allowed on each row, but no automatic numbering +// This function *doesn't* work with the "split" environment name. + + +function getAutoTag(name) { + if (name.indexOf("ed") === -1) { + return name.indexOf("*") === -1; + } // return undefined; + +} +/** + * Parse the body of the environment, with rows delimited by \\ and + * columns delimited by &, and create a nested list in row-major order + * with one group per cell. If given an optional argument style + * ("text", "display", etc.), then each cell is cast into that style. + */ + + +function parseArray(parser, _ref, style) { + let { + hskipBeforeAndAfter, + addJot, + cols, + arraystretch, + colSeparationType, + autoTag, + singleRow, + emptySingleRow, + maxNumCols, + leqno + } = _ref; + parser.gullet.beginGroup(); + + if (!singleRow) { + // \cr is equivalent to \\ without the optional size argument (see below) + // TODO: provide helpful error when \cr is used outside array environment + parser.gullet.macros.set("\\cr", "\\\\\\relax"); + } // Get current arraystretch if it's not set by the environment + + + if (!arraystretch) { + const stretch = parser.gullet.expandMacroAsText("\\arraystretch"); + + if (stretch == null) { + // Default \arraystretch from lttab.dtx + arraystretch = 1; + } else { + arraystretch = parseFloat(stretch); + + if (!arraystretch || arraystretch < 0) { + throw new src_ParseError("Invalid \\arraystretch: " + stretch); + } + } + } // Start group for first cell + + + parser.gullet.beginGroup(); + let row = []; + const body = [row]; + const rowGaps = []; + const hLinesBeforeRow = []; + const tags = autoTag != null ? [] : undefined; // amsmath uses \global\@eqnswtrue and \global\@eqnswfalse to represent + // whether this row should have an equation number. Simulate this with + // a \@eqnsw macro set to 1 or 0. + + function beginRow() { + if (autoTag) { + parser.gullet.macros.set("\\@eqnsw", "1", true); + } + } + + function endRow() { + if (tags) { + if (parser.gullet.macros.get("\\df@tag")) { + tags.push(parser.subparse([new Token("\\df@tag")])); + parser.gullet.macros.set("\\df@tag", undefined, true); + } else { + tags.push(Boolean(autoTag) && parser.gullet.macros.get("\\@eqnsw") === "1"); + } + } + } + + beginRow(); // Test for \hline at the top of the array. + + hLinesBeforeRow.push(getHLines(parser)); + + while (true) { + // eslint-disable-line no-constant-condition + // Parse each cell in its own group (namespace) + let cell = parser.parseExpression(false, singleRow ? "\\end" : "\\\\"); + parser.gullet.endGroup(); + parser.gullet.beginGroup(); + cell = { + type: "ordgroup", + mode: parser.mode, + body: cell + }; + + if (style) { + cell = { + type: "styling", + mode: parser.mode, + style, + body: [cell] + }; + } + + row.push(cell); + const next = parser.fetch().text; + + if (next === "&") { + if (maxNumCols && row.length === maxNumCols) { + if (singleRow || colSeparationType) { + // {equation} or {split} + throw new src_ParseError("Too many tab characters: &", parser.nextToken); + } else { + // {array} environment + parser.settings.reportNonstrict("textEnv", "Too few columns " + "specified in the {array} column argument."); + } + } + + parser.consume(); + } else if (next === "\\end") { + endRow(); // Arrays terminate newlines with `\crcr` which consumes a `\cr` if + // the last line is empty. However, AMS environments keep the + // empty row if it's the only one. + // NOTE: Currently, `cell` is the last item added into `row`. + + if (row.length === 1 && cell.type === "styling" && cell.body[0].body.length === 0 && (body.length > 1 || !emptySingleRow)) { + body.pop(); + } + + if (hLinesBeforeRow.length < body.length + 1) { + hLinesBeforeRow.push([]); + } + + break; + } else if (next === "\\\\") { + parser.consume(); + let size; // \def\Let@{\let\\\math@cr} + // \def\math@cr{...\math@cr@} + // \def\math@cr@{\new@ifnextchar[\math@cr@@{\math@cr@@[\z@]}} + // \def\math@cr@@[#1]{...\math@cr@@@...} + // \def\math@cr@@@{\cr} + + if (parser.gullet.future().text !== " ") { + size = parser.parseSizeGroup(true); + } + + rowGaps.push(size ? size.value : null); + endRow(); // check for \hline(s) following the row separator + + hLinesBeforeRow.push(getHLines(parser)); + row = []; + body.push(row); + beginRow(); + } else { + throw new src_ParseError("Expected & or \\\\ or \\cr or \\end", parser.nextToken); + } + } // End cell group + + + parser.gullet.endGroup(); // End array group defining \cr + + parser.gullet.endGroup(); + return { + type: "array", + mode: parser.mode, + addJot, + arraystretch, + body, + cols, + rowGaps, + hskipBeforeAndAfter, + hLinesBeforeRow, + colSeparationType, + tags, + leqno + }; +} // Decides on a style for cells in an array according to whether the given +// environment name starts with the letter 'd'. + + +function dCellStyle(envName) { + if (envName.slice(0, 1) === "d") { + return "display"; + } else { + return "text"; + } +} + +const array_htmlBuilder = function (group, options) { + let r; + let c; + const nr = group.body.length; + const hLinesBeforeRow = group.hLinesBeforeRow; + let nc = 0; + let body = new Array(nr); + const hlines = []; + const ruleThickness = Math.max( // From LaTeX \showthe\arrayrulewidth. Equals 0.04 em. + options.fontMetrics().arrayRuleWidth, options.minRuleThickness // User override. + ); // Horizontal spacing + + const pt = 1 / options.fontMetrics().ptPerEm; + let arraycolsep = 5 * pt; // default value, i.e. \arraycolsep in article.cls + + if (group.colSeparationType && group.colSeparationType === "small") { + // We're in a {smallmatrix}. Default column space is \thickspace, + // i.e. 5/18em = 0.2778em, per amsmath.dtx for {smallmatrix}. + // But that needs adjustment because LaTeX applies \scriptstyle to the + // entire array, including the colspace, but this function applies + // \scriptstyle only inside each element. + const localMultiplier = options.havingStyle(src_Style.SCRIPT).sizeMultiplier; + arraycolsep = 0.2778 * (localMultiplier / options.sizeMultiplier); + } // Vertical spacing + + + const baselineskip = group.colSeparationType === "CD" ? calculateSize({ + number: 3, + unit: "ex" + }, options) : 12 * pt; // see size10.clo + // Default \jot from ltmath.dtx + // TODO(edemaine): allow overriding \jot via \setlength (#687) + + const jot = 3 * pt; + const arrayskip = group.arraystretch * baselineskip; + const arstrutHeight = 0.7 * arrayskip; // \strutbox in ltfsstrc.dtx and + + const arstrutDepth = 0.3 * arrayskip; // \@arstrutbox in lttab.dtx + + let totalHeight = 0; // Set a position for \hline(s) at the top of the array, if any. + + function setHLinePos(hlinesInGap) { + for (let i = 0; i < hlinesInGap.length; ++i) { + if (i > 0) { + totalHeight += 0.25; + } + + hlines.push({ + pos: totalHeight, + isDashed: hlinesInGap[i] + }); + } + } + + setHLinePos(hLinesBeforeRow[0]); + + for (r = 0; r < group.body.length; ++r) { + const inrow = group.body[r]; + let height = arstrutHeight; // \@array adds an \@arstrut + + let depth = arstrutDepth; // to each tow (via the template) + + if (nc < inrow.length) { + nc = inrow.length; + } + + const outrow = new Array(inrow.length); + + for (c = 0; c < inrow.length; ++c) { + const elt = buildGroup(inrow[c], options); + + if (depth < elt.depth) { + depth = elt.depth; + } + + if (height < elt.height) { + height = elt.height; + } + + outrow[c] = elt; + } + + const rowGap = group.rowGaps[r]; + let gap = 0; + + if (rowGap) { + gap = calculateSize(rowGap, options); + + if (gap > 0) { + // \@argarraycr + gap += arstrutDepth; + + if (depth < gap) { + depth = gap; // \@xargarraycr + } + + gap = 0; + } + } // In AMS multiline environments such as aligned and gathered, rows + // correspond to lines that have additional \jot added to the + // \baselineskip via \openup. + + + if (group.addJot) { + depth += jot; + } + + outrow.height = height; + outrow.depth = depth; + totalHeight += height; + outrow.pos = totalHeight; + totalHeight += depth + gap; // \@yargarraycr + + body[r] = outrow; // Set a position for \hline(s), if any. + + setHLinePos(hLinesBeforeRow[r + 1]); + } + + const offset = totalHeight / 2 + options.fontMetrics().axisHeight; + const colDescriptions = group.cols || []; + const cols = []; + let colSep; + let colDescrNum; + const tagSpans = []; + + if (group.tags && group.tags.some(tag => tag)) { + // An environment with manual tags and/or automatic equation numbers. + // Create node(s), the latter of which trigger CSS counter increment. + for (r = 0; r < nr; ++r) { + const rw = body[r]; + const shift = rw.pos - offset; + const tag = group.tags[r]; + let tagSpan; + + if (tag === true) { + // automatic numbering + tagSpan = buildCommon.makeSpan(["eqn-num"], [], options); + } else if (tag === false) { + // \nonumber/\notag or starred environment + tagSpan = buildCommon.makeSpan([], [], options); + } else { + // manual \tag + tagSpan = buildCommon.makeSpan([], buildExpression(tag, options, true), options); + } + + tagSpan.depth = rw.depth; + tagSpan.height = rw.height; + tagSpans.push({ + type: "elem", + elem: tagSpan, + shift + }); + } + } + + for (c = 0, colDescrNum = 0; // Continue while either there are more columns or more column + // descriptions, so trailing separators don't get lost. + c < nc || colDescrNum < colDescriptions.length; ++c, ++colDescrNum) { + let colDescr = colDescriptions[colDescrNum] || {}; + let firstSeparator = true; + + while (colDescr.type === "separator") { + // If there is more than one separator in a row, add a space + // between them. + if (!firstSeparator) { + colSep = buildCommon.makeSpan(["arraycolsep"], []); + colSep.style.width = makeEm(options.fontMetrics().doubleRuleSep); + cols.push(colSep); + } + + if (colDescr.separator === "|" || colDescr.separator === ":") { + const lineType = colDescr.separator === "|" ? "solid" : "dashed"; + const separator = buildCommon.makeSpan(["vertical-separator"], [], options); + separator.style.height = makeEm(totalHeight); + separator.style.borderRightWidth = makeEm(ruleThickness); + separator.style.borderRightStyle = lineType; + separator.style.margin = "0 " + makeEm(-ruleThickness / 2); + const shift = totalHeight - offset; + + if (shift) { + separator.style.verticalAlign = makeEm(-shift); + } + + cols.push(separator); + } else { + throw new src_ParseError("Invalid separator type: " + colDescr.separator); + } + + colDescrNum++; + colDescr = colDescriptions[colDescrNum] || {}; + firstSeparator = false; + } + + if (c >= nc) { + continue; + } + + let sepwidth; + + if (c > 0 || group.hskipBeforeAndAfter) { + sepwidth = utils.deflt(colDescr.pregap, arraycolsep); + + if (sepwidth !== 0) { + colSep = buildCommon.makeSpan(["arraycolsep"], []); + colSep.style.width = makeEm(sepwidth); + cols.push(colSep); + } + } + + let col = []; + + for (r = 0; r < nr; ++r) { + const row = body[r]; + const elem = row[c]; + + if (!elem) { + continue; + } + + const shift = row.pos - offset; + elem.depth = row.depth; + elem.height = row.height; + col.push({ + type: "elem", + elem: elem, + shift: shift + }); + } + + col = buildCommon.makeVList({ + positionType: "individualShift", + children: col + }, options); + col = buildCommon.makeSpan(["col-align-" + (colDescr.align || "c")], [col]); + cols.push(col); + + if (c < nc - 1 || group.hskipBeforeAndAfter) { + sepwidth = utils.deflt(colDescr.postgap, arraycolsep); + + if (sepwidth !== 0) { + colSep = buildCommon.makeSpan(["arraycolsep"], []); + colSep.style.width = makeEm(sepwidth); + cols.push(colSep); + } + } + } + + body = buildCommon.makeSpan(["mtable"], cols); // Add \hline(s), if any. + + if (hlines.length > 0) { + const line = buildCommon.makeLineSpan("hline", options, ruleThickness); + const dashes = buildCommon.makeLineSpan("hdashline", options, ruleThickness); + const vListElems = [{ + type: "elem", + elem: body, + shift: 0 + }]; + + while (hlines.length > 0) { + const hline = hlines.pop(); + const lineShift = hline.pos - offset; + + if (hline.isDashed) { + vListElems.push({ + type: "elem", + elem: dashes, + shift: lineShift + }); + } else { + vListElems.push({ + type: "elem", + elem: line, + shift: lineShift + }); + } + } + + body = buildCommon.makeVList({ + positionType: "individualShift", + children: vListElems + }, options); + } + + if (tagSpans.length === 0) { + return buildCommon.makeSpan(["mord"], [body], options); + } else { + let eqnNumCol = buildCommon.makeVList({ + positionType: "individualShift", + children: tagSpans + }, options); + eqnNumCol = buildCommon.makeSpan(["tag"], [eqnNumCol], options); + return buildCommon.makeFragment([body, eqnNumCol]); + } +}; + +const alignMap = { + c: "center ", + l: "left ", + r: "right " +}; + +const array_mathmlBuilder = function (group, options) { + const tbl = []; + const glue = new mathMLTree.MathNode("mtd", [], ["mtr-glue"]); + const tag = new mathMLTree.MathNode("mtd", [], ["mml-eqn-num"]); + + for (let i = 0; i < group.body.length; i++) { + const rw = group.body[i]; + const row = []; + + for (let j = 0; j < rw.length; j++) { + row.push(new mathMLTree.MathNode("mtd", [buildMathML_buildGroup(rw[j], options)])); + } + + if (group.tags && group.tags[i]) { + row.unshift(glue); + row.push(glue); + + if (group.leqno) { + row.unshift(tag); + } else { + row.push(tag); + } + } + + tbl.push(new mathMLTree.MathNode("mtr", row)); + } + + let table = new mathMLTree.MathNode("mtable", tbl); // Set column alignment, row spacing, column spacing, and + // array lines by setting attributes on the table element. + // Set the row spacing. In MathML, we specify a gap distance. + // We do not use rowGap[] because MathML automatically increases + // cell height with the height/depth of the element content. + // LaTeX \arraystretch multiplies the row baseline-to-baseline distance. + // We simulate this by adding (arraystretch - 1)em to the gap. This + // does a reasonable job of adjusting arrays containing 1 em tall content. + // The 0.16 and 0.09 values are found empirically. They produce an array + // similar to LaTeX and in which content does not interfere with \hlines. + + const gap = group.arraystretch === 0.5 ? 0.1 // {smallmatrix}, {subarray} + : 0.16 + group.arraystretch - 1 + (group.addJot ? 0.09 : 0); + table.setAttribute("rowspacing", makeEm(gap)); // MathML table lines go only between cells. + // To place a line on an edge we'll use , if necessary. + + let menclose = ""; + let align = ""; + + if (group.cols && group.cols.length > 0) { + // Find column alignment, column spacing, and vertical lines. + const cols = group.cols; + let columnLines = ""; + let prevTypeWasAlign = false; + let iStart = 0; + let iEnd = cols.length; + + if (cols[0].type === "separator") { + menclose += "top "; + iStart = 1; + } + + if (cols[cols.length - 1].type === "separator") { + menclose += "bottom "; + iEnd -= 1; + } + + for (let i = iStart; i < iEnd; i++) { + if (cols[i].type === "align") { + align += alignMap[cols[i].align]; + + if (prevTypeWasAlign) { + columnLines += "none "; + } + + prevTypeWasAlign = true; + } else if (cols[i].type === "separator") { + // MathML accepts only single lines between cells. + // So we read only the first of consecutive separators. + if (prevTypeWasAlign) { + columnLines += cols[i].separator === "|" ? "solid " : "dashed "; + prevTypeWasAlign = false; + } + } + } + + table.setAttribute("columnalign", align.trim()); + + if (/[sd]/.test(columnLines)) { + table.setAttribute("columnlines", columnLines.trim()); + } + } // Set column spacing. + + + if (group.colSeparationType === "align") { + const cols = group.cols || []; + let spacing = ""; + + for (let i = 1; i < cols.length; i++) { + spacing += i % 2 ? "0em " : "1em "; + } + + table.setAttribute("columnspacing", spacing.trim()); + } else if (group.colSeparationType === "alignat" || group.colSeparationType === "gather") { + table.setAttribute("columnspacing", "0em"); + } else if (group.colSeparationType === "small") { + table.setAttribute("columnspacing", "0.2778em"); + } else if (group.colSeparationType === "CD") { + table.setAttribute("columnspacing", "0.5em"); + } else { + table.setAttribute("columnspacing", "1em"); + } // Address \hline and \hdashline + + + let rowLines = ""; + const hlines = group.hLinesBeforeRow; + menclose += hlines[0].length > 0 ? "left " : ""; + menclose += hlines[hlines.length - 1].length > 0 ? "right " : ""; + + for (let i = 1; i < hlines.length - 1; i++) { + rowLines += hlines[i].length === 0 ? "none " // MathML accepts only a single line between rows. Read one element. + : hlines[i][0] ? "dashed " : "solid "; + } + + if (/[sd]/.test(rowLines)) { + table.setAttribute("rowlines", rowLines.trim()); + } + + if (menclose !== "") { + table = new mathMLTree.MathNode("menclose", [table]); + table.setAttribute("notation", menclose.trim()); + } + + if (group.arraystretch && group.arraystretch < 1) { + // A small array. Wrap in scriptstyle so row gap is not too large. + table = new mathMLTree.MathNode("mstyle", [table]); + table.setAttribute("scriptlevel", "1"); + } + + return table; +}; // Convenience function for align, align*, aligned, alignat, alignat*, alignedat. + + +const alignedHandler = function (context, args) { + if (context.envName.indexOf("ed") === -1) { + validateAmsEnvironmentContext(context); + } + + const cols = []; + const separationType = context.envName.indexOf("at") > -1 ? "alignat" : "align"; + const isSplit = context.envName === "split"; + const res = parseArray(context.parser, { + cols, + addJot: true, + autoTag: isSplit ? undefined : getAutoTag(context.envName), + emptySingleRow: true, + colSeparationType: separationType, + maxNumCols: isSplit ? 2 : undefined, + leqno: context.parser.settings.leqno + }, "display"); // Determining number of columns. + // 1. If the first argument is given, we use it as a number of columns, + // and makes sure that each row doesn't exceed that number. + // 2. Otherwise, just count number of columns = maximum number + // of cells in each row ("aligned" mode -- isAligned will be true). + // + // At the same time, prepend empty group {} at beginning of every second + // cell in each row (starting with second cell) so that operators become + // binary. This behavior is implemented in amsmath's \start@aligned. + + let numMaths; + let numCols = 0; + const emptyGroup = { + type: "ordgroup", + mode: context.mode, + body: [] + }; + + if (args[0] && args[0].type === "ordgroup") { + let arg0 = ""; + + for (let i = 0; i < args[0].body.length; i++) { + const textord = assertNodeType(args[0].body[i], "textord"); + arg0 += textord.text; + } + + numMaths = Number(arg0); + numCols = numMaths * 2; + } + + const isAligned = !numCols; + res.body.forEach(function (row) { + for (let i = 1; i < row.length; i += 2) { + // Modify ordgroup node within styling node + const styling = assertNodeType(row[i], "styling"); + const ordgroup = assertNodeType(styling.body[0], "ordgroup"); + ordgroup.body.unshift(emptyGroup); + } + + if (!isAligned) { + // Case 1 + const curMaths = row.length / 2; + + if (numMaths < curMaths) { + throw new src_ParseError("Too many math in a row: " + ("expected " + numMaths + ", but got " + curMaths), row[0]); + } + } else if (numCols < row.length) { + // Case 2 + numCols = row.length; + } + }); // Adjusting alignment. + // In aligned mode, we add one \qquad between columns; + // otherwise we add nothing. + + for (let i = 0; i < numCols; ++i) { + let align = "r"; + let pregap = 0; + + if (i % 2 === 1) { + align = "l"; + } else if (i > 0 && isAligned) { + // "aligned" mode. + pregap = 1; // add one \quad + } + + cols[i] = { + type: "align", + align: align, + pregap: pregap, + postgap: 0 + }; + } + + res.colSeparationType = isAligned ? "align" : "alignat"; + return res; +}; // Arrays are part of LaTeX, defined in lttab.dtx so its documentation +// is part of the source2e.pdf file of LaTeX2e source documentation. +// {darray} is an {array} environment where cells are set in \displaystyle, +// as defined in nccmath.sty. + + +defineEnvironment({ + type: "array", + names: ["array", "darray"], + props: { + numArgs: 1 + }, + + handler(context, args) { + // Since no types are specified above, the two possibilities are + // - The argument is wrapped in {} or [], in which case Parser's + // parseGroup() returns an "ordgroup" wrapping some symbol node. + // - The argument is a bare symbol node. + const symNode = checkSymbolNodeType(args[0]); + const colalign = symNode ? [args[0]] : assertNodeType(args[0], "ordgroup").body; + const cols = colalign.map(function (nde) { + const node = assertSymbolNodeType(nde); + const ca = node.text; + + if ("lcr".indexOf(ca) !== -1) { + return { + type: "align", + align: ca + }; + } else if (ca === "|") { + return { + type: "separator", + separator: "|" + }; + } else if (ca === ":") { + return { + type: "separator", + separator: ":" + }; + } + + throw new src_ParseError("Unknown column alignment: " + ca, nde); + }); + const res = { + cols, + hskipBeforeAndAfter: true, + // \@preamble in lttab.dtx + maxNumCols: cols.length + }; + return parseArray(context.parser, res, dCellStyle(context.envName)); + }, + + htmlBuilder: array_htmlBuilder, + mathmlBuilder: array_mathmlBuilder +}); // The matrix environments of amsmath builds on the array environment +// of LaTeX, which is discussed above. +// The mathtools package adds starred versions of the same environments. +// These have an optional argument to choose left|center|right justification. + +defineEnvironment({ + type: "array", + names: ["matrix", "pmatrix", "bmatrix", "Bmatrix", "vmatrix", "Vmatrix", "matrix*", "pmatrix*", "bmatrix*", "Bmatrix*", "vmatrix*", "Vmatrix*"], + props: { + numArgs: 0 + }, + + handler(context) { + const delimiters = { + "matrix": null, + "pmatrix": ["(", ")"], + "bmatrix": ["[", "]"], + "Bmatrix": ["\\{", "\\}"], + "vmatrix": ["|", "|"], + "Vmatrix": ["\\Vert", "\\Vert"] + }[context.envName.replace("*", "")]; // \hskip -\arraycolsep in amsmath + + let colAlign = "c"; + const payload = { + hskipBeforeAndAfter: false, + cols: [{ + type: "align", + align: colAlign + }] + }; + + if (context.envName.charAt(context.envName.length - 1) === "*") { + // It's one of the mathtools starred functions. + // Parse the optional alignment argument. + const parser = context.parser; + parser.consumeSpaces(); + + if (parser.fetch().text === "[") { + parser.consume(); + parser.consumeSpaces(); + colAlign = parser.fetch().text; + + if ("lcr".indexOf(colAlign) === -1) { + throw new src_ParseError("Expected l or c or r", parser.nextToken); + } + + parser.consume(); + parser.consumeSpaces(); + parser.expect("]"); + parser.consume(); + payload.cols = [{ + type: "align", + align: colAlign + }]; + } + } + + const res = parseArray(context.parser, payload, dCellStyle(context.envName)); // Populate cols with the correct number of column alignment specs. + + const numCols = Math.max(0, ...res.body.map(row => row.length)); + res.cols = new Array(numCols).fill({ + type: "align", + align: colAlign + }); + return delimiters ? { + type: "leftright", + mode: context.mode, + body: [res], + left: delimiters[0], + right: delimiters[1], + rightColor: undefined // \right uninfluenced by \color in array + + } : res; + }, + + htmlBuilder: array_htmlBuilder, + mathmlBuilder: array_mathmlBuilder +}); +defineEnvironment({ + type: "array", + names: ["smallmatrix"], + props: { + numArgs: 0 + }, + + handler(context) { + const payload = { + arraystretch: 0.5 + }; + const res = parseArray(context.parser, payload, "script"); + res.colSeparationType = "small"; + return res; + }, + + htmlBuilder: array_htmlBuilder, + mathmlBuilder: array_mathmlBuilder +}); +defineEnvironment({ + type: "array", + names: ["subarray"], + props: { + numArgs: 1 + }, + + handler(context, args) { + // Parsing of {subarray} is similar to {array} + const symNode = checkSymbolNodeType(args[0]); + const colalign = symNode ? [args[0]] : assertNodeType(args[0], "ordgroup").body; + const cols = colalign.map(function (nde) { + const node = assertSymbolNodeType(nde); + const ca = node.text; // {subarray} only recognizes "l" & "c" + + if ("lc".indexOf(ca) !== -1) { + return { + type: "align", + align: ca + }; + } + + throw new src_ParseError("Unknown column alignment: " + ca, nde); + }); + + if (cols.length > 1) { + throw new src_ParseError("{subarray} can contain only one column"); + } + + let res = { + cols, + hskipBeforeAndAfter: false, + arraystretch: 0.5 + }; + res = parseArray(context.parser, res, "script"); + + if (res.body.length > 0 && res.body[0].length > 1) { + throw new src_ParseError("{subarray} can contain only one column"); + } + + return res; + }, + + htmlBuilder: array_htmlBuilder, + mathmlBuilder: array_mathmlBuilder +}); // A cases environment (in amsmath.sty) is almost equivalent to +// \def\arraystretch{1.2}% +// \left\{\begin{array}{@{}l@{\quad}l@{}} … \end{array}\right. +// {dcases} is a {cases} environment where cells are set in \displaystyle, +// as defined in mathtools.sty. +// {rcases} is another mathtools environment. It's brace is on the right side. + +defineEnvironment({ + type: "array", + names: ["cases", "dcases", "rcases", "drcases"], + props: { + numArgs: 0 + }, + + handler(context) { + const payload = { + arraystretch: 1.2, + cols: [{ + type: "align", + align: "l", + pregap: 0, + // TODO(kevinb) get the current style. + // For now we use the metrics for TEXT style which is what we were + // doing before. Before attempting to get the current style we + // should look at TeX's behavior especially for \over and matrices. + postgap: 1.0 + /* 1em quad */ + + }, { + type: "align", + align: "l", + pregap: 0, + postgap: 0 + }] + }; + const res = parseArray(context.parser, payload, dCellStyle(context.envName)); + return { + type: "leftright", + mode: context.mode, + body: [res], + left: context.envName.indexOf("r") > -1 ? "." : "\\{", + right: context.envName.indexOf("r") > -1 ? "\\}" : ".", + rightColor: undefined + }; + }, + + htmlBuilder: array_htmlBuilder, + mathmlBuilder: array_mathmlBuilder +}); // In the align environment, one uses ampersands, &, to specify number of +// columns in each row, and to locate spacing between each column. +// align gets automatic numbering. align* and aligned do not. +// The alignedat environment can be used in math mode. +// Note that we assume \nomallineskiplimit to be zero, +// so that \strut@ is the same as \strut. + +defineEnvironment({ + type: "array", + names: ["align", "align*", "aligned", "split"], + props: { + numArgs: 0 + }, + handler: alignedHandler, + htmlBuilder: array_htmlBuilder, + mathmlBuilder: array_mathmlBuilder +}); // A gathered environment is like an array environment with one centered +// column, but where rows are considered lines so get \jot line spacing +// and contents are set in \displaystyle. + +defineEnvironment({ + type: "array", + names: ["gathered", "gather", "gather*"], + props: { + numArgs: 0 + }, + + handler(context) { + if (utils.contains(["gather", "gather*"], context.envName)) { + validateAmsEnvironmentContext(context); + } + + const res = { + cols: [{ + type: "align", + align: "c" + }], + addJot: true, + colSeparationType: "gather", + autoTag: getAutoTag(context.envName), + emptySingleRow: true, + leqno: context.parser.settings.leqno + }; + return parseArray(context.parser, res, "display"); + }, + + htmlBuilder: array_htmlBuilder, + mathmlBuilder: array_mathmlBuilder +}); // alignat environment is like an align environment, but one must explicitly +// specify maximum number of columns in each row, and can adjust spacing between +// each columns. + +defineEnvironment({ + type: "array", + names: ["alignat", "alignat*", "alignedat"], + props: { + numArgs: 1 + }, + handler: alignedHandler, + htmlBuilder: array_htmlBuilder, + mathmlBuilder: array_mathmlBuilder +}); +defineEnvironment({ + type: "array", + names: ["equation", "equation*"], + props: { + numArgs: 0 + }, + + handler(context) { + validateAmsEnvironmentContext(context); + const res = { + autoTag: getAutoTag(context.envName), + emptySingleRow: true, + singleRow: true, + maxNumCols: 1, + leqno: context.parser.settings.leqno + }; + return parseArray(context.parser, res, "display"); + }, + + htmlBuilder: array_htmlBuilder, + mathmlBuilder: array_mathmlBuilder +}); +defineEnvironment({ + type: "array", + names: ["CD"], + props: { + numArgs: 0 + }, + + handler(context) { + validateAmsEnvironmentContext(context); + return parseCD(context.parser); + }, + + htmlBuilder: array_htmlBuilder, + mathmlBuilder: array_mathmlBuilder +}); +defineMacro("\\nonumber", "\\gdef\\@eqnsw{0}"); +defineMacro("\\notag", "\\nonumber"); // Catch \hline outside array environment + +defineFunction({ + type: "text", + // Doesn't matter what this is. + names: ["\\hline", "\\hdashline"], + props: { + numArgs: 0, + allowedInText: true, + allowedInMath: true + }, + + handler(context, args) { + throw new src_ParseError(context.funcName + " valid only within array environment"); + } + +}); +;// CONCATENATED MODULE: ./src/environments.js + +const environments = _environments; +/* harmony default export */ var src_environments = (environments); // All environment definitions should be imported below + + +;// CONCATENATED MODULE: ./src/functions/environment.js + + + + // Environment delimiters. HTML/MathML rendering is defined in the corresponding +// defineEnvironment definitions. + +defineFunction({ + type: "environment", + names: ["\\begin", "\\end"], + props: { + numArgs: 1, + argTypes: ["text"] + }, + + handler(_ref, args) { + let { + parser, + funcName + } = _ref; + const nameGroup = args[0]; + + if (nameGroup.type !== "ordgroup") { + throw new src_ParseError("Invalid environment name", nameGroup); + } + + let envName = ""; + + for (let i = 0; i < nameGroup.body.length; ++i) { + envName += assertNodeType(nameGroup.body[i], "textord").text; + } + + if (funcName === "\\begin") { + // begin...end is similar to left...right + if (!src_environments.hasOwnProperty(envName)) { + throw new src_ParseError("No such environment: " + envName, nameGroup); + } // Build the environment object. Arguments and other information will + // be made available to the begin and end methods using properties. + + + const env = src_environments[envName]; + const { + args, + optArgs + } = parser.parseArguments("\\begin{" + envName + "}", env); + const context = { + mode: parser.mode, + envName, + parser + }; + const result = env.handler(context, args, optArgs); + parser.expect("\\end", false); + const endNameToken = parser.nextToken; + const end = assertNodeType(parser.parseFunction(), "environment"); + + if (end.name !== envName) { + throw new src_ParseError("Mismatch: \\begin{" + envName + "} matched by \\end{" + end.name + "}", endNameToken); + } // $FlowFixMe, "environment" handler returns an environment ParseNode + + + return result; + } + + return { + type: "environment", + mode: parser.mode, + name: envName, + nameGroup + }; + } + +}); +;// CONCATENATED MODULE: ./src/functions/font.js +// TODO(kevinb): implement \\sl and \\sc + + + + + + +const font_htmlBuilder = (group, options) => { + const font = group.font; + const newOptions = options.withFont(font); + return buildGroup(group.body, newOptions); +}; + +const font_mathmlBuilder = (group, options) => { + const font = group.font; + const newOptions = options.withFont(font); + return buildMathML_buildGroup(group.body, newOptions); +}; + +const fontAliases = { + "\\Bbb": "\\mathbb", + "\\bold": "\\mathbf", + "\\frak": "\\mathfrak", + "\\bm": "\\boldsymbol" +}; +defineFunction({ + type: "font", + names: [// styles, except \boldsymbol defined below + "\\mathrm", "\\mathit", "\\mathbf", "\\mathnormal", "\\mathsfit", // families + "\\mathbb", "\\mathcal", "\\mathfrak", "\\mathscr", "\\mathsf", "\\mathtt", // aliases, except \bm defined below + "\\Bbb", "\\bold", "\\frak"], + props: { + numArgs: 1, + allowedInArgument: true + }, + handler: (_ref, args) => { + let { + parser, + funcName + } = _ref; + const body = normalizeArgument(args[0]); + let func = funcName; + + if (func in fontAliases) { + func = fontAliases[func]; + } + + return { + type: "font", + mode: parser.mode, + font: func.slice(1), + body + }; + }, + htmlBuilder: font_htmlBuilder, + mathmlBuilder: font_mathmlBuilder +}); +defineFunction({ + type: "mclass", + names: ["\\boldsymbol", "\\bm"], + props: { + numArgs: 1 + }, + handler: (_ref2, args) => { + let { + parser + } = _ref2; + const body = args[0]; + const isCharacterBox = utils.isCharacterBox(body); // amsbsy.sty's \boldsymbol uses \binrel spacing to inherit the + // argument's bin|rel|ord status + + return { + type: "mclass", + mode: parser.mode, + mclass: binrelClass(body), + body: [{ + type: "font", + mode: parser.mode, + font: "boldsymbol", + body + }], + isCharacterBox: isCharacterBox + }; + } +}); // Old font changing functions + +defineFunction({ + type: "font", + names: ["\\rm", "\\sf", "\\tt", "\\bf", "\\it", "\\cal"], + props: { + numArgs: 0, + allowedInText: true + }, + handler: (_ref3, args) => { + let { + parser, + funcName, + breakOnTokenText + } = _ref3; + const { + mode + } = parser; + const body = parser.parseExpression(true, breakOnTokenText); + const style = "math" + funcName.slice(1); + return { + type: "font", + mode: mode, + font: style, + body: { + type: "ordgroup", + mode: parser.mode, + body + } + }; + }, + htmlBuilder: font_htmlBuilder, + mathmlBuilder: font_mathmlBuilder +}); +;// CONCATENATED MODULE: ./src/functions/genfrac.js + + + + + + + + + + + +const adjustStyle = (size, originalStyle) => { + // Figure out what style this fraction should be in based on the + // function used + let style = originalStyle; + + if (size === "display") { + // Get display style as a default. + // If incoming style is sub/sup, use style.text() to get correct size. + style = style.id >= src_Style.SCRIPT.id ? style.text() : src_Style.DISPLAY; + } else if (size === "text" && style.size === src_Style.DISPLAY.size) { + // We're in a \tfrac but incoming style is displaystyle, so: + style = src_Style.TEXT; + } else if (size === "script") { + style = src_Style.SCRIPT; + } else if (size === "scriptscript") { + style = src_Style.SCRIPTSCRIPT; + } + + return style; +}; + +const genfrac_htmlBuilder = (group, options) => { + // Fractions are handled in the TeXbook on pages 444-445, rules 15(a-e). + const style = adjustStyle(group.size, options.style); + const nstyle = style.fracNum(); + const dstyle = style.fracDen(); + let newOptions; + newOptions = options.havingStyle(nstyle); + const numerm = buildGroup(group.numer, newOptions, options); + + if (group.continued) { + // \cfrac inserts a \strut into the numerator. + // Get \strut dimensions from TeXbook page 353. + const hStrut = 8.5 / options.fontMetrics().ptPerEm; + const dStrut = 3.5 / options.fontMetrics().ptPerEm; + numerm.height = numerm.height < hStrut ? hStrut : numerm.height; + numerm.depth = numerm.depth < dStrut ? dStrut : numerm.depth; + } + + newOptions = options.havingStyle(dstyle); + const denomm = buildGroup(group.denom, newOptions, options); + let rule; + let ruleWidth; + let ruleSpacing; + + if (group.hasBarLine) { + if (group.barSize) { + ruleWidth = calculateSize(group.barSize, options); + rule = buildCommon.makeLineSpan("frac-line", options, ruleWidth); + } else { + rule = buildCommon.makeLineSpan("frac-line", options); + } + + ruleWidth = rule.height; + ruleSpacing = rule.height; + } else { + rule = null; + ruleWidth = 0; + ruleSpacing = options.fontMetrics().defaultRuleThickness; + } // Rule 15b + + + let numShift; + let clearance; + let denomShift; + + if (style.size === src_Style.DISPLAY.size || group.size === "display") { + numShift = options.fontMetrics().num1; + + if (ruleWidth > 0) { + clearance = 3 * ruleSpacing; + } else { + clearance = 7 * ruleSpacing; + } + + denomShift = options.fontMetrics().denom1; + } else { + if (ruleWidth > 0) { + numShift = options.fontMetrics().num2; + clearance = ruleSpacing; + } else { + numShift = options.fontMetrics().num3; + clearance = 3 * ruleSpacing; + } + + denomShift = options.fontMetrics().denom2; + } + + let frac; + + if (!rule) { + // Rule 15c + const candidateClearance = numShift - numerm.depth - (denomm.height - denomShift); + + if (candidateClearance < clearance) { + numShift += 0.5 * (clearance - candidateClearance); + denomShift += 0.5 * (clearance - candidateClearance); + } + + frac = buildCommon.makeVList({ + positionType: "individualShift", + children: [{ + type: "elem", + elem: denomm, + shift: denomShift + }, { + type: "elem", + elem: numerm, + shift: -numShift + }] + }, options); + } else { + // Rule 15d + const axisHeight = options.fontMetrics().axisHeight; + + if (numShift - numerm.depth - (axisHeight + 0.5 * ruleWidth) < clearance) { + numShift += clearance - (numShift - numerm.depth - (axisHeight + 0.5 * ruleWidth)); + } + + if (axisHeight - 0.5 * ruleWidth - (denomm.height - denomShift) < clearance) { + denomShift += clearance - (axisHeight - 0.5 * ruleWidth - (denomm.height - denomShift)); + } + + const midShift = -(axisHeight - 0.5 * ruleWidth); + frac = buildCommon.makeVList({ + positionType: "individualShift", + children: [{ + type: "elem", + elem: denomm, + shift: denomShift + }, { + type: "elem", + elem: rule, + shift: midShift + }, { + type: "elem", + elem: numerm, + shift: -numShift + }] + }, options); + } // Since we manually change the style sometimes (with \dfrac or \tfrac), + // account for the possible size change here. + + + newOptions = options.havingStyle(style); + frac.height *= newOptions.sizeMultiplier / options.sizeMultiplier; + frac.depth *= newOptions.sizeMultiplier / options.sizeMultiplier; // Rule 15e + + let delimSize; + + if (style.size === src_Style.DISPLAY.size) { + delimSize = options.fontMetrics().delim1; + } else if (style.size === src_Style.SCRIPTSCRIPT.size) { + delimSize = options.havingStyle(src_Style.SCRIPT).fontMetrics().delim2; + } else { + delimSize = options.fontMetrics().delim2; + } + + let leftDelim; + let rightDelim; + + if (group.leftDelim == null) { + leftDelim = makeNullDelimiter(options, ["mopen"]); + } else { + leftDelim = delimiter.customSizedDelim(group.leftDelim, delimSize, true, options.havingStyle(style), group.mode, ["mopen"]); + } + + if (group.continued) { + rightDelim = buildCommon.makeSpan([]); // zero width for \cfrac + } else if (group.rightDelim == null) { + rightDelim = makeNullDelimiter(options, ["mclose"]); + } else { + rightDelim = delimiter.customSizedDelim(group.rightDelim, delimSize, true, options.havingStyle(style), group.mode, ["mclose"]); + } + + return buildCommon.makeSpan(["mord"].concat(newOptions.sizingClasses(options)), [leftDelim, buildCommon.makeSpan(["mfrac"], [frac]), rightDelim], options); +}; + +const genfrac_mathmlBuilder = (group, options) => { + let node = new mathMLTree.MathNode("mfrac", [buildMathML_buildGroup(group.numer, options), buildMathML_buildGroup(group.denom, options)]); + + if (!group.hasBarLine) { + node.setAttribute("linethickness", "0px"); + } else if (group.barSize) { + const ruleWidth = calculateSize(group.barSize, options); + node.setAttribute("linethickness", makeEm(ruleWidth)); + } + + const style = adjustStyle(group.size, options.style); + + if (style.size !== options.style.size) { + node = new mathMLTree.MathNode("mstyle", [node]); + const isDisplay = style.size === src_Style.DISPLAY.size ? "true" : "false"; + node.setAttribute("displaystyle", isDisplay); + node.setAttribute("scriptlevel", "0"); + } + + if (group.leftDelim != null || group.rightDelim != null) { + const withDelims = []; + + if (group.leftDelim != null) { + const leftOp = new mathMLTree.MathNode("mo", [new mathMLTree.TextNode(group.leftDelim.replace("\\", ""))]); + leftOp.setAttribute("fence", "true"); + withDelims.push(leftOp); + } + + withDelims.push(node); + + if (group.rightDelim != null) { + const rightOp = new mathMLTree.MathNode("mo", [new mathMLTree.TextNode(group.rightDelim.replace("\\", ""))]); + rightOp.setAttribute("fence", "true"); + withDelims.push(rightOp); + } + + return makeRow(withDelims); + } + + return node; +}; + +defineFunction({ + type: "genfrac", + names: ["\\dfrac", "\\frac", "\\tfrac", "\\dbinom", "\\binom", "\\tbinom", "\\\\atopfrac", // can’t be entered directly + "\\\\bracefrac", "\\\\brackfrac" // ditto + ], + props: { + numArgs: 2, + allowedInArgument: true + }, + handler: (_ref, args) => { + let { + parser, + funcName + } = _ref; + const numer = args[0]; + const denom = args[1]; + let hasBarLine; + let leftDelim = null; + let rightDelim = null; + let size = "auto"; + + switch (funcName) { + case "\\dfrac": + case "\\frac": + case "\\tfrac": + hasBarLine = true; + break; + + case "\\\\atopfrac": + hasBarLine = false; + break; + + case "\\dbinom": + case "\\binom": + case "\\tbinom": + hasBarLine = false; + leftDelim = "("; + rightDelim = ")"; + break; + + case "\\\\bracefrac": + hasBarLine = false; + leftDelim = "\\{"; + rightDelim = "\\}"; + break; + + case "\\\\brackfrac": + hasBarLine = false; + leftDelim = "["; + rightDelim = "]"; + break; + + default: + throw new Error("Unrecognized genfrac command"); + } + + switch (funcName) { + case "\\dfrac": + case "\\dbinom": + size = "display"; + break; + + case "\\tfrac": + case "\\tbinom": + size = "text"; + break; + } + + return { + type: "genfrac", + mode: parser.mode, + continued: false, + numer, + denom, + hasBarLine, + leftDelim, + rightDelim, + size, + barSize: null + }; + }, + htmlBuilder: genfrac_htmlBuilder, + mathmlBuilder: genfrac_mathmlBuilder +}); +defineFunction({ + type: "genfrac", + names: ["\\cfrac"], + props: { + numArgs: 2 + }, + handler: (_ref2, args) => { + let { + parser, + funcName + } = _ref2; + const numer = args[0]; + const denom = args[1]; + return { + type: "genfrac", + mode: parser.mode, + continued: true, + numer, + denom, + hasBarLine: true, + leftDelim: null, + rightDelim: null, + size: "display", + barSize: null + }; + } +}); // Infix generalized fractions -- these are not rendered directly, but replaced +// immediately by one of the variants above. + +defineFunction({ + type: "infix", + names: ["\\over", "\\choose", "\\atop", "\\brace", "\\brack"], + props: { + numArgs: 0, + infix: true + }, + + handler(_ref3) { + let { + parser, + funcName, + token + } = _ref3; + let replaceWith; + + switch (funcName) { + case "\\over": + replaceWith = "\\frac"; + break; + + case "\\choose": + replaceWith = "\\binom"; + break; + + case "\\atop": + replaceWith = "\\\\atopfrac"; + break; + + case "\\brace": + replaceWith = "\\\\bracefrac"; + break; + + case "\\brack": + replaceWith = "\\\\brackfrac"; + break; + + default: + throw new Error("Unrecognized infix genfrac command"); + } + + return { + type: "infix", + mode: parser.mode, + replaceWith, + token + }; + } + +}); +const stylArray = ["display", "text", "script", "scriptscript"]; + +const delimFromValue = function (delimString) { + let delim = null; + + if (delimString.length > 0) { + delim = delimString; + delim = delim === "." ? null : delim; + } + + return delim; +}; + +defineFunction({ + type: "genfrac", + names: ["\\genfrac"], + props: { + numArgs: 6, + allowedInArgument: true, + argTypes: ["math", "math", "size", "text", "math", "math"] + }, + + handler(_ref4, args) { + let { + parser + } = _ref4; + const numer = args[4]; + const denom = args[5]; // Look into the parse nodes to get the desired delimiters. + + const leftNode = normalizeArgument(args[0]); + const leftDelim = leftNode.type === "atom" && leftNode.family === "open" ? delimFromValue(leftNode.text) : null; + const rightNode = normalizeArgument(args[1]); + const rightDelim = rightNode.type === "atom" && rightNode.family === "close" ? delimFromValue(rightNode.text) : null; + const barNode = assertNodeType(args[2], "size"); + let hasBarLine; + let barSize = null; + + if (barNode.isBlank) { + // \genfrac acts differently than \above. + // \genfrac treats an empty size group as a signal to use a + // standard bar size. \above would see size = 0 and omit the bar. + hasBarLine = true; + } else { + barSize = barNode.value; + hasBarLine = barSize.number > 0; + } // Find out if we want displaystyle, textstyle, etc. + + + let size = "auto"; + let styl = args[3]; + + if (styl.type === "ordgroup") { + if (styl.body.length > 0) { + const textOrd = assertNodeType(styl.body[0], "textord"); + size = stylArray[Number(textOrd.text)]; + } + } else { + styl = assertNodeType(styl, "textord"); + size = stylArray[Number(styl.text)]; + } + + return { + type: "genfrac", + mode: parser.mode, + numer, + denom, + continued: false, + hasBarLine, + barSize, + leftDelim, + rightDelim, + size + }; + }, + + htmlBuilder: genfrac_htmlBuilder, + mathmlBuilder: genfrac_mathmlBuilder +}); // \above is an infix fraction that also defines a fraction bar size. + +defineFunction({ + type: "infix", + names: ["\\above"], + props: { + numArgs: 1, + argTypes: ["size"], + infix: true + }, + + handler(_ref5, args) { + let { + parser, + funcName, + token + } = _ref5; + return { + type: "infix", + mode: parser.mode, + replaceWith: "\\\\abovefrac", + size: assertNodeType(args[0], "size").value, + token + }; + } + +}); +defineFunction({ + type: "genfrac", + names: ["\\\\abovefrac"], + props: { + numArgs: 3, + argTypes: ["math", "size", "math"] + }, + handler: (_ref6, args) => { + let { + parser, + funcName + } = _ref6; + const numer = args[0]; + const barSize = assert(assertNodeType(args[1], "infix").size); + const denom = args[2]; + const hasBarLine = barSize.number > 0; + return { + type: "genfrac", + mode: parser.mode, + numer, + denom, + continued: false, + hasBarLine, + barSize, + leftDelim: null, + rightDelim: null, + size: "auto" + }; + }, + htmlBuilder: genfrac_htmlBuilder, + mathmlBuilder: genfrac_mathmlBuilder +}); +;// CONCATENATED MODULE: ./src/functions/horizBrace.js + + + + + + + + +// NOTE: Unlike most `htmlBuilder`s, this one handles not only "horizBrace", but +// also "supsub" since an over/underbrace can affect super/subscripting. +const horizBrace_htmlBuilder = (grp, options) => { + const style = options.style; // Pull out the `ParseNode<"horizBrace">` if `grp` is a "supsub" node. + + let supSubGroup; + let group; + + if (grp.type === "supsub") { + // Ref: LaTeX source2e: }}}}\limits} + // i.e. LaTeX treats the brace similar to an op and passes it + // with \limits, so we need to assign supsub style. + supSubGroup = grp.sup ? buildGroup(grp.sup, options.havingStyle(style.sup()), options) : buildGroup(grp.sub, options.havingStyle(style.sub()), options); + group = assertNodeType(grp.base, "horizBrace"); + } else { + group = assertNodeType(grp, "horizBrace"); + } // Build the base group + + + const body = buildGroup(group.base, options.havingBaseStyle(src_Style.DISPLAY)); // Create the stretchy element + + const braceBody = stretchy.svgSpan(group, options); // Generate the vlist, with the appropriate kerns ┏━━━━━━━━┓ + // This first vlist contains the content and the brace: equation + + let vlist; + + if (group.isOver) { + vlist = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: body + }, { + type: "kern", + size: 0.1 + }, { + type: "elem", + elem: braceBody + }] + }, options); // $FlowFixMe: Replace this with passing "svg-align" into makeVList. + + vlist.children[0].children[0].children[1].classes.push("svg-align"); + } else { + vlist = buildCommon.makeVList({ + positionType: "bottom", + positionData: body.depth + 0.1 + braceBody.height, + children: [{ + type: "elem", + elem: braceBody + }, { + type: "kern", + size: 0.1 + }, { + type: "elem", + elem: body + }] + }, options); // $FlowFixMe: Replace this with passing "svg-align" into makeVList. + + vlist.children[0].children[0].children[0].classes.push("svg-align"); + } + + if (supSubGroup) { + // To write the supsub, wrap the first vlist in another vlist: + // They can't all go in the same vlist, because the note might be + // wider than the equation. We want the equation to control the + // brace width. + // note long note long note + // ┏━━━━━━━━┓ or ┏━━━┓ not ┏━━━━━━━━━┓ + // equation eqn eqn + const vSpan = buildCommon.makeSpan(["mord", group.isOver ? "mover" : "munder"], [vlist], options); + + if (group.isOver) { + vlist = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: vSpan + }, { + type: "kern", + size: 0.2 + }, { + type: "elem", + elem: supSubGroup + }] + }, options); + } else { + vlist = buildCommon.makeVList({ + positionType: "bottom", + positionData: vSpan.depth + 0.2 + supSubGroup.height + supSubGroup.depth, + children: [{ + type: "elem", + elem: supSubGroup + }, { + type: "kern", + size: 0.2 + }, { + type: "elem", + elem: vSpan + }] + }, options); + } + } + + return buildCommon.makeSpan(["mord", group.isOver ? "mover" : "munder"], [vlist], options); +}; + +const horizBrace_mathmlBuilder = (group, options) => { + const accentNode = stretchy.mathMLnode(group.label); + return new mathMLTree.MathNode(group.isOver ? "mover" : "munder", [buildMathML_buildGroup(group.base, options), accentNode]); +}; // Horizontal stretchy braces + + +defineFunction({ + type: "horizBrace", + names: ["\\overbrace", "\\underbrace"], + props: { + numArgs: 1 + }, + + handler(_ref, args) { + let { + parser, + funcName + } = _ref; + return { + type: "horizBrace", + mode: parser.mode, + label: funcName, + isOver: /^\\over/.test(funcName), + base: args[0] + }; + }, + + htmlBuilder: horizBrace_htmlBuilder, + mathmlBuilder: horizBrace_mathmlBuilder +}); +;// CONCATENATED MODULE: ./src/functions/href.js + + + + + + +defineFunction({ + type: "href", + names: ["\\href"], + props: { + numArgs: 2, + argTypes: ["url", "original"], + allowedInText: true + }, + handler: (_ref, args) => { + let { + parser + } = _ref; + const body = args[1]; + const href = assertNodeType(args[0], "url").url; + + if (!parser.settings.isTrusted({ + command: "\\href", + url: href + })) { + return parser.formatUnsupportedCmd("\\href"); + } + + return { + type: "href", + mode: parser.mode, + href, + body: ordargument(body) + }; + }, + htmlBuilder: (group, options) => { + const elements = buildExpression(group.body, options, false); + return buildCommon.makeAnchor(group.href, [], elements, options); + }, + mathmlBuilder: (group, options) => { + let math = buildExpressionRow(group.body, options); + + if (!(math instanceof MathNode)) { + math = new MathNode("mrow", [math]); + } + + math.setAttribute("href", group.href); + return math; + } +}); +defineFunction({ + type: "href", + names: ["\\url"], + props: { + numArgs: 1, + argTypes: ["url"], + allowedInText: true + }, + handler: (_ref2, args) => { + let { + parser + } = _ref2; + const href = assertNodeType(args[0], "url").url; + + if (!parser.settings.isTrusted({ + command: "\\url", + url: href + })) { + return parser.formatUnsupportedCmd("\\url"); + } + + const chars = []; + + for (let i = 0; i < href.length; i++) { + let c = href[i]; + + if (c === "~") { + c = "\\textasciitilde"; + } + + chars.push({ + type: "textord", + mode: "text", + text: c + }); + } + + const body = { + type: "text", + mode: parser.mode, + font: "\\texttt", + body: chars + }; + return { + type: "href", + mode: parser.mode, + href, + body: ordargument(body) + }; + } +}); +;// CONCATENATED MODULE: ./src/functions/hbox.js + + + + + // \hbox is provided for compatibility with LaTeX \vcenter. +// In LaTeX, \vcenter can act only on a box, as in +// \vcenter{\hbox{$\frac{a+b}{\dfrac{c}{d}}$}} +// This function by itself doesn't do anything but prevent a soft line break. + +defineFunction({ + type: "hbox", + names: ["\\hbox"], + props: { + numArgs: 1, + argTypes: ["text"], + allowedInText: true, + primitive: true + }, + + handler(_ref, args) { + let { + parser + } = _ref; + return { + type: "hbox", + mode: parser.mode, + body: ordargument(args[0]) + }; + }, + + htmlBuilder(group, options) { + const elements = buildExpression(group.body, options, false); + return buildCommon.makeFragment(elements); + }, + + mathmlBuilder(group, options) { + return new mathMLTree.MathNode("mrow", buildMathML_buildExpression(group.body, options)); + } + +}); +;// CONCATENATED MODULE: ./src/functions/html.js + + + + + + +defineFunction({ + type: "html", + names: ["\\htmlClass", "\\htmlId", "\\htmlStyle", "\\htmlData"], + props: { + numArgs: 2, + argTypes: ["raw", "original"], + allowedInText: true + }, + handler: (_ref, args) => { + let { + parser, + funcName, + token + } = _ref; + const value = assertNodeType(args[0], "raw").string; + const body = args[1]; + + if (parser.settings.strict) { + parser.settings.reportNonstrict("htmlExtension", "HTML extension is disabled on strict mode"); + } + + let trustContext; + const attributes = {}; + + switch (funcName) { + case "\\htmlClass": + attributes.class = value; + trustContext = { + command: "\\htmlClass", + class: value + }; + break; + + case "\\htmlId": + attributes.id = value; + trustContext = { + command: "\\htmlId", + id: value + }; + break; + + case "\\htmlStyle": + attributes.style = value; + trustContext = { + command: "\\htmlStyle", + style: value + }; + break; + + case "\\htmlData": + { + const data = value.split(","); + + for (let i = 0; i < data.length; i++) { + const keyVal = data[i].split("="); + + if (keyVal.length !== 2) { + throw new src_ParseError("Error parsing key-value for \\htmlData"); + } + + attributes["data-" + keyVal[0].trim()] = keyVal[1].trim(); + } + + trustContext = { + command: "\\htmlData", + attributes + }; + break; + } + + default: + throw new Error("Unrecognized html command"); + } + + if (!parser.settings.isTrusted(trustContext)) { + return parser.formatUnsupportedCmd(funcName); + } + + return { + type: "html", + mode: parser.mode, + attributes, + body: ordargument(body) + }; + }, + htmlBuilder: (group, options) => { + const elements = buildExpression(group.body, options, false); + const classes = ["enclosing"]; + + if (group.attributes.class) { + classes.push(...group.attributes.class.trim().split(/\s+/)); + } + + const span = buildCommon.makeSpan(classes, elements, options); + + for (const attr in group.attributes) { + if (attr !== "class" && group.attributes.hasOwnProperty(attr)) { + span.setAttribute(attr, group.attributes[attr]); + } + } + + return span; + }, + mathmlBuilder: (group, options) => { + return buildExpressionRow(group.body, options); + } +}); +;// CONCATENATED MODULE: ./src/functions/htmlmathml.js + + + + +defineFunction({ + type: "htmlmathml", + names: ["\\html@mathml"], + props: { + numArgs: 2, + allowedInText: true + }, + handler: (_ref, args) => { + let { + parser + } = _ref; + return { + type: "htmlmathml", + mode: parser.mode, + html: ordargument(args[0]), + mathml: ordargument(args[1]) + }; + }, + htmlBuilder: (group, options) => { + const elements = buildExpression(group.html, options, false); + return buildCommon.makeFragment(elements); + }, + mathmlBuilder: (group, options) => { + return buildExpressionRow(group.mathml, options); + } +}); +;// CONCATENATED MODULE: ./src/functions/includegraphics.js + + + + + + + +const sizeData = function (str) { + if (/^[-+]? *(\d+(\.\d*)?|\.\d+)$/.test(str)) { + // str is a number with no unit specified. + // default unit is bp, per graphix package. + return { + number: +str, + unit: "bp" + }; + } else { + const match = /([-+]?) *(\d+(?:\.\d*)?|\.\d+) *([a-z]{2})/.exec(str); + + if (!match) { + throw new src_ParseError("Invalid size: '" + str + "' in \\includegraphics"); + } + + const data = { + number: +(match[1] + match[2]), + // sign + magnitude, cast to number + unit: match[3] + }; + + if (!validUnit(data)) { + throw new src_ParseError("Invalid unit: '" + data.unit + "' in \\includegraphics."); + } + + return data; + } +}; + +defineFunction({ + type: "includegraphics", + names: ["\\includegraphics"], + props: { + numArgs: 1, + numOptionalArgs: 1, + argTypes: ["raw", "url"], + allowedInText: false + }, + handler: (_ref, args, optArgs) => { + let { + parser + } = _ref; + let width = { + number: 0, + unit: "em" + }; + let height = { + number: 0.9, + unit: "em" + }; // sorta character sized. + + let totalheight = { + number: 0, + unit: "em" + }; + let alt = ""; + + if (optArgs[0]) { + const attributeStr = assertNodeType(optArgs[0], "raw").string; // Parser.js does not parse key/value pairs. We get a string. + + const attributes = attributeStr.split(","); + + for (let i = 0; i < attributes.length; i++) { + const keyVal = attributes[i].split("="); + + if (keyVal.length === 2) { + const str = keyVal[1].trim(); + + switch (keyVal[0].trim()) { + case "alt": + alt = str; + break; + + case "width": + width = sizeData(str); + break; + + case "height": + height = sizeData(str); + break; + + case "totalheight": + totalheight = sizeData(str); + break; + + default: + throw new src_ParseError("Invalid key: '" + keyVal[0] + "' in \\includegraphics."); + } + } + } + } + + const src = assertNodeType(args[0], "url").url; + + if (alt === "") { + // No alt given. Use the file name. Strip away the path. + alt = src; + alt = alt.replace(/^.*[\\/]/, ''); + alt = alt.substring(0, alt.lastIndexOf('.')); + } + + if (!parser.settings.isTrusted({ + command: "\\includegraphics", + url: src + })) { + return parser.formatUnsupportedCmd("\\includegraphics"); + } + + return { + type: "includegraphics", + mode: parser.mode, + alt: alt, + width: width, + height: height, + totalheight: totalheight, + src: src + }; + }, + htmlBuilder: (group, options) => { + const height = calculateSize(group.height, options); + let depth = 0; + + if (group.totalheight.number > 0) { + depth = calculateSize(group.totalheight, options) - height; + } + + let width = 0; + + if (group.width.number > 0) { + width = calculateSize(group.width, options); + } + + const style = { + height: makeEm(height + depth) + }; + + if (width > 0) { + style.width = makeEm(width); + } + + if (depth > 0) { + style.verticalAlign = makeEm(-depth); + } + + const node = new Img(group.src, group.alt, style); + node.height = height; + node.depth = depth; + return node; + }, + mathmlBuilder: (group, options) => { + const node = new mathMLTree.MathNode("mglyph", []); + node.setAttribute("alt", group.alt); + const height = calculateSize(group.height, options); + let depth = 0; + + if (group.totalheight.number > 0) { + depth = calculateSize(group.totalheight, options) - height; + node.setAttribute("valign", makeEm(-depth)); + } + + node.setAttribute("height", makeEm(height + depth)); + + if (group.width.number > 0) { + const width = calculateSize(group.width, options); + node.setAttribute("width", makeEm(width)); + } + + node.setAttribute("src", group.src); + return node; + } +}); +;// CONCATENATED MODULE: ./src/functions/kern.js +// Horizontal spacing commands + + + + + // TODO: \hskip and \mskip should support plus and minus in lengths + +defineFunction({ + type: "kern", + names: ["\\kern", "\\mkern", "\\hskip", "\\mskip"], + props: { + numArgs: 1, + argTypes: ["size"], + primitive: true, + allowedInText: true + }, + + handler(_ref, args) { + let { + parser, + funcName + } = _ref; + const size = assertNodeType(args[0], "size"); + + if (parser.settings.strict) { + const mathFunction = funcName[1] === 'm'; // \mkern, \mskip + + const muUnit = size.value.unit === 'mu'; + + if (mathFunction) { + if (!muUnit) { + parser.settings.reportNonstrict("mathVsTextUnits", "LaTeX's " + funcName + " supports only mu units, " + ("not " + size.value.unit + " units")); + } + + if (parser.mode !== "math") { + parser.settings.reportNonstrict("mathVsTextUnits", "LaTeX's " + funcName + " works only in math mode"); + } + } else { + // !mathFunction + if (muUnit) { + parser.settings.reportNonstrict("mathVsTextUnits", "LaTeX's " + funcName + " doesn't support mu units"); + } + } + } + + return { + type: "kern", + mode: parser.mode, + dimension: size.value + }; + }, + + htmlBuilder(group, options) { + return buildCommon.makeGlue(group.dimension, options); + }, + + mathmlBuilder(group, options) { + const dimension = calculateSize(group.dimension, options); + return new mathMLTree.SpaceNode(dimension); + } + +}); +;// CONCATENATED MODULE: ./src/functions/lap.js +// Horizontal overlap functions + + + + + + +defineFunction({ + type: "lap", + names: ["\\mathllap", "\\mathrlap", "\\mathclap"], + props: { + numArgs: 1, + allowedInText: true + }, + handler: (_ref, args) => { + let { + parser, + funcName + } = _ref; + const body = args[0]; + return { + type: "lap", + mode: parser.mode, + alignment: funcName.slice(5), + body + }; + }, + htmlBuilder: (group, options) => { + // mathllap, mathrlap, mathclap + let inner; + + if (group.alignment === "clap") { + // ref: https://www.math.lsu.edu/~aperlis/publications/mathclap/ + inner = buildCommon.makeSpan([], [buildGroup(group.body, options)]); // wrap, since CSS will center a .clap > .inner > span + + inner = buildCommon.makeSpan(["inner"], [inner], options); + } else { + inner = buildCommon.makeSpan(["inner"], [buildGroup(group.body, options)]); + } + + const fix = buildCommon.makeSpan(["fix"], []); + let node = buildCommon.makeSpan([group.alignment], [inner, fix], options); // At this point, we have correctly set horizontal alignment of the + // two items involved in the lap. + // Next, use a strut to set the height of the HTML bounding box. + // Otherwise, a tall argument may be misplaced. + // This code resolved issue #1153 + + const strut = buildCommon.makeSpan(["strut"]); + strut.style.height = makeEm(node.height + node.depth); + + if (node.depth) { + strut.style.verticalAlign = makeEm(-node.depth); + } + + node.children.unshift(strut); // Next, prevent vertical misplacement when next to something tall. + // This code resolves issue #1234 + + node = buildCommon.makeSpan(["thinbox"], [node], options); + return buildCommon.makeSpan(["mord", "vbox"], [node], options); + }, + mathmlBuilder: (group, options) => { + // mathllap, mathrlap, mathclap + const node = new mathMLTree.MathNode("mpadded", [buildMathML_buildGroup(group.body, options)]); + + if (group.alignment !== "rlap") { + const offset = group.alignment === "llap" ? "-1" : "-0.5"; + node.setAttribute("lspace", offset + "width"); + } + + node.setAttribute("width", "0px"); + return node; + } +}); +;// CONCATENATED MODULE: ./src/functions/math.js + + // Switching from text mode back to math mode + +defineFunction({ + type: "styling", + names: ["\\(", "$"], + props: { + numArgs: 0, + allowedInText: true, + allowedInMath: false + }, + + handler(_ref, args) { + let { + funcName, + parser + } = _ref; + const outerMode = parser.mode; + parser.switchMode("math"); + const close = funcName === "\\(" ? "\\)" : "$"; + const body = parser.parseExpression(false, close); + parser.expect(close); + parser.switchMode(outerMode); + return { + type: "styling", + mode: parser.mode, + style: "text", + body + }; + } + +}); // Check for extra closing math delimiters + +defineFunction({ + type: "text", + // Doesn't matter what this is. + names: ["\\)", "\\]"], + props: { + numArgs: 0, + allowedInText: true, + allowedInMath: false + }, + + handler(context, args) { + throw new src_ParseError("Mismatched " + context.funcName); + } + +}); +;// CONCATENATED MODULE: ./src/functions/mathchoice.js + + + + + + +const chooseMathStyle = (group, options) => { + switch (options.style.size) { + case src_Style.DISPLAY.size: + return group.display; + + case src_Style.TEXT.size: + return group.text; + + case src_Style.SCRIPT.size: + return group.script; + + case src_Style.SCRIPTSCRIPT.size: + return group.scriptscript; + + default: + return group.text; + } +}; + +defineFunction({ + type: "mathchoice", + names: ["\\mathchoice"], + props: { + numArgs: 4, + primitive: true + }, + handler: (_ref, args) => { + let { + parser + } = _ref; + return { + type: "mathchoice", + mode: parser.mode, + display: ordargument(args[0]), + text: ordargument(args[1]), + script: ordargument(args[2]), + scriptscript: ordargument(args[3]) + }; + }, + htmlBuilder: (group, options) => { + const body = chooseMathStyle(group, options); + const elements = buildExpression(body, options, false); + return buildCommon.makeFragment(elements); + }, + mathmlBuilder: (group, options) => { + const body = chooseMathStyle(group, options); + return buildExpressionRow(body, options); + } +}); +;// CONCATENATED MODULE: ./src/functions/utils/assembleSupSub.js + + + + // For an operator with limits, assemble the base, sup, and sub into a span. + +const assembleSupSub = (base, supGroup, subGroup, options, style, slant, baseShift) => { + base = buildCommon.makeSpan([], [base]); + const subIsSingleCharacter = subGroup && utils.isCharacterBox(subGroup); + let sub; + let sup; // We manually have to handle the superscripts and subscripts. This, + // aside from the kern calculations, is copied from supsub. + + if (supGroup) { + const elem = buildGroup(supGroup, options.havingStyle(style.sup()), options); + sup = { + elem, + kern: Math.max(options.fontMetrics().bigOpSpacing1, options.fontMetrics().bigOpSpacing3 - elem.depth) + }; + } + + if (subGroup) { + const elem = buildGroup(subGroup, options.havingStyle(style.sub()), options); + sub = { + elem, + kern: Math.max(options.fontMetrics().bigOpSpacing2, options.fontMetrics().bigOpSpacing4 - elem.height) + }; + } // Build the final group as a vlist of the possible subscript, base, + // and possible superscript. + + + let finalGroup; + + if (sup && sub) { + const bottom = options.fontMetrics().bigOpSpacing5 + sub.elem.height + sub.elem.depth + sub.kern + base.depth + baseShift; + finalGroup = buildCommon.makeVList({ + positionType: "bottom", + positionData: bottom, + children: [{ + type: "kern", + size: options.fontMetrics().bigOpSpacing5 + }, { + type: "elem", + elem: sub.elem, + marginLeft: makeEm(-slant) + }, { + type: "kern", + size: sub.kern + }, { + type: "elem", + elem: base + }, { + type: "kern", + size: sup.kern + }, { + type: "elem", + elem: sup.elem, + marginLeft: makeEm(slant) + }, { + type: "kern", + size: options.fontMetrics().bigOpSpacing5 + }] + }, options); + } else if (sub) { + const top = base.height - baseShift; // Shift the limits by the slant of the symbol. Note + // that we are supposed to shift the limits by 1/2 of the slant, + // but since we are centering the limits adding a full slant of + // margin will shift by 1/2 that. + + finalGroup = buildCommon.makeVList({ + positionType: "top", + positionData: top, + children: [{ + type: "kern", + size: options.fontMetrics().bigOpSpacing5 + }, { + type: "elem", + elem: sub.elem, + marginLeft: makeEm(-slant) + }, { + type: "kern", + size: sub.kern + }, { + type: "elem", + elem: base + }] + }, options); + } else if (sup) { + const bottom = base.depth + baseShift; + finalGroup = buildCommon.makeVList({ + positionType: "bottom", + positionData: bottom, + children: [{ + type: "elem", + elem: base + }, { + type: "kern", + size: sup.kern + }, { + type: "elem", + elem: sup.elem, + marginLeft: makeEm(slant) + }, { + type: "kern", + size: options.fontMetrics().bigOpSpacing5 + }] + }, options); + } else { + // This case probably shouldn't occur (this would mean the + // supsub was sending us a group with no superscript or + // subscript) but be safe. + return base; + } + + const parts = [finalGroup]; + + if (sub && slant !== 0 && !subIsSingleCharacter) { + // A negative margin-left was applied to the lower limit. + // Avoid an overlap by placing a spacer on the left on the group. + const spacer = buildCommon.makeSpan(["mspace"], [], options); + spacer.style.marginRight = makeEm(slant); + parts.unshift(spacer); + } + + return buildCommon.makeSpan(["mop", "op-limits"], parts, options); +}; +;// CONCATENATED MODULE: ./src/functions/op.js +// Limits, symbols + + + + + + + + + + + +// Most operators have a large successor symbol, but these don't. +const noSuccessor = ["\\smallint"]; // NOTE: Unlike most `htmlBuilder`s, this one handles not only "op", but also +// "supsub" since some of them (like \int) can affect super/subscripting. + +const op_htmlBuilder = (grp, options) => { + // Operators are handled in the TeXbook pg. 443-444, rule 13(a). + let supGroup; + let subGroup; + let hasLimits = false; + let group; + + if (grp.type === "supsub") { + // If we have limits, supsub will pass us its group to handle. Pull + // out the superscript and subscript and set the group to the op in + // its base. + supGroup = grp.sup; + subGroup = grp.sub; + group = assertNodeType(grp.base, "op"); + hasLimits = true; + } else { + group = assertNodeType(grp, "op"); + } + + const style = options.style; + let large = false; + + if (style.size === src_Style.DISPLAY.size && group.symbol && !utils.contains(noSuccessor, group.name)) { + // Most symbol operators get larger in displaystyle (rule 13) + large = true; + } + + let base; + + if (group.symbol) { + // If this is a symbol, create the symbol. + const fontName = large ? "Size2-Regular" : "Size1-Regular"; + let stash = ""; + + if (group.name === "\\oiint" || group.name === "\\oiiint") { + // No font glyphs yet, so use a glyph w/o the oval. + // TODO: When font glyphs are available, delete this code. + stash = group.name.slice(1); + group.name = stash === "oiint" ? "\\iint" : "\\iiint"; + } + + base = buildCommon.makeSymbol(group.name, fontName, "math", options, ["mop", "op-symbol", large ? "large-op" : "small-op"]); + + if (stash.length > 0) { + // We're in \oiint or \oiiint. Overlay the oval. + // TODO: When font glyphs are available, delete this code. + const italic = base.italic; + const oval = buildCommon.staticSvg(stash + "Size" + (large ? "2" : "1"), options); + base = buildCommon.makeVList({ + positionType: "individualShift", + children: [{ + type: "elem", + elem: base, + shift: 0 + }, { + type: "elem", + elem: oval, + shift: large ? 0.08 : 0 + }] + }, options); + group.name = "\\" + stash; + base.classes.unshift("mop"); // $FlowFixMe + + base.italic = italic; + } + } else if (group.body) { + // If this is a list, compose that list. + const inner = buildExpression(group.body, options, true); + + if (inner.length === 1 && inner[0] instanceof SymbolNode) { + base = inner[0]; + base.classes[0] = "mop"; // replace old mclass + } else { + base = buildCommon.makeSpan(["mop"], inner, options); + } + } else { + // Otherwise, this is a text operator. Build the text from the + // operator's name. + const output = []; + + for (let i = 1; i < group.name.length; i++) { + output.push(buildCommon.mathsym(group.name[i], group.mode, options)); + } + + base = buildCommon.makeSpan(["mop"], output, options); + } // If content of op is a single symbol, shift it vertically. + + + let baseShift = 0; + let slant = 0; + + if ((base instanceof SymbolNode || group.name === "\\oiint" || group.name === "\\oiiint") && !group.suppressBaseShift) { + // We suppress the shift of the base of \overset and \underset. Otherwise, + // shift the symbol so its center lies on the axis (rule 13). It + // appears that our fonts have the centers of the symbols already + // almost on the axis, so these numbers are very small. Note we + // don't actually apply this here, but instead it is used either in + // the vlist creation or separately when there are no limits. + baseShift = (base.height - base.depth) / 2 - options.fontMetrics().axisHeight; // The slant of the symbol is just its italic correction. + // $FlowFixMe + + slant = base.italic; + } + + if (hasLimits) { + return assembleSupSub(base, supGroup, subGroup, options, style, slant, baseShift); + } else { + if (baseShift) { + base.style.position = "relative"; + base.style.top = makeEm(baseShift); + } + + return base; + } +}; + +const op_mathmlBuilder = (group, options) => { + let node; + + if (group.symbol) { + // This is a symbol. Just add the symbol. + node = new MathNode("mo", [makeText(group.name, group.mode)]); + + if (utils.contains(noSuccessor, group.name)) { + node.setAttribute("largeop", "false"); + } + } else if (group.body) { + // This is an operator with children. Add them. + node = new MathNode("mo", buildMathML_buildExpression(group.body, options)); + } else { + // This is a text operator. Add all of the characters from the + // operator's name. + node = new MathNode("mi", [new TextNode(group.name.slice(1))]); // Append an . + // ref: https://www.w3.org/TR/REC-MathML/chap3_2.html#sec3.2.4 + + const operator = new MathNode("mo", [makeText("\u2061", "text")]); + + if (group.parentIsSupSub) { + node = new MathNode("mrow", [node, operator]); + } else { + node = newDocumentFragment([node, operator]); + } + } + + return node; +}; + +const singleCharBigOps = { + "\u220F": "\\prod", + "\u2210": "\\coprod", + "\u2211": "\\sum", + "\u22c0": "\\bigwedge", + "\u22c1": "\\bigvee", + "\u22c2": "\\bigcap", + "\u22c3": "\\bigcup", + "\u2a00": "\\bigodot", + "\u2a01": "\\bigoplus", + "\u2a02": "\\bigotimes", + "\u2a04": "\\biguplus", + "\u2a06": "\\bigsqcup" +}; +defineFunction({ + type: "op", + names: ["\\coprod", "\\bigvee", "\\bigwedge", "\\biguplus", "\\bigcap", "\\bigcup", "\\intop", "\\prod", "\\sum", "\\bigotimes", "\\bigoplus", "\\bigodot", "\\bigsqcup", "\\smallint", "\u220F", "\u2210", "\u2211", "\u22c0", "\u22c1", "\u22c2", "\u22c3", "\u2a00", "\u2a01", "\u2a02", "\u2a04", "\u2a06"], + props: { + numArgs: 0 + }, + handler: (_ref, args) => { + let { + parser, + funcName + } = _ref; + let fName = funcName; + + if (fName.length === 1) { + fName = singleCharBigOps[fName]; + } + + return { + type: "op", + mode: parser.mode, + limits: true, + parentIsSupSub: false, + symbol: true, + name: fName + }; + }, + htmlBuilder: op_htmlBuilder, + mathmlBuilder: op_mathmlBuilder +}); // Note: calling defineFunction with a type that's already been defined only +// works because the same htmlBuilder and mathmlBuilder are being used. + +defineFunction({ + type: "op", + names: ["\\mathop"], + props: { + numArgs: 1, + primitive: true + }, + handler: (_ref2, args) => { + let { + parser + } = _ref2; + const body = args[0]; + return { + type: "op", + mode: parser.mode, + limits: false, + parentIsSupSub: false, + symbol: false, + body: ordargument(body) + }; + }, + htmlBuilder: op_htmlBuilder, + mathmlBuilder: op_mathmlBuilder +}); // There are 2 flags for operators; whether they produce limits in +// displaystyle, and whether they are symbols and should grow in +// displaystyle. These four groups cover the four possible choices. + +const singleCharIntegrals = { + "\u222b": "\\int", + "\u222c": "\\iint", + "\u222d": "\\iiint", + "\u222e": "\\oint", + "\u222f": "\\oiint", + "\u2230": "\\oiiint" +}; // No limits, not symbols + +defineFunction({ + type: "op", + names: ["\\arcsin", "\\arccos", "\\arctan", "\\arctg", "\\arcctg", "\\arg", "\\ch", "\\cos", "\\cosec", "\\cosh", "\\cot", "\\cotg", "\\coth", "\\csc", "\\ctg", "\\cth", "\\deg", "\\dim", "\\exp", "\\hom", "\\ker", "\\lg", "\\ln", "\\log", "\\sec", "\\sin", "\\sinh", "\\sh", "\\tan", "\\tanh", "\\tg", "\\th"], + props: { + numArgs: 0 + }, + + handler(_ref3) { + let { + parser, + funcName + } = _ref3; + return { + type: "op", + mode: parser.mode, + limits: false, + parentIsSupSub: false, + symbol: false, + name: funcName + }; + }, + + htmlBuilder: op_htmlBuilder, + mathmlBuilder: op_mathmlBuilder +}); // Limits, not symbols + +defineFunction({ + type: "op", + names: ["\\det", "\\gcd", "\\inf", "\\lim", "\\max", "\\min", "\\Pr", "\\sup"], + props: { + numArgs: 0 + }, + + handler(_ref4) { + let { + parser, + funcName + } = _ref4; + return { + type: "op", + mode: parser.mode, + limits: true, + parentIsSupSub: false, + symbol: false, + name: funcName + }; + }, + + htmlBuilder: op_htmlBuilder, + mathmlBuilder: op_mathmlBuilder +}); // No limits, symbols + +defineFunction({ + type: "op", + names: ["\\int", "\\iint", "\\iiint", "\\oint", "\\oiint", "\\oiiint", "\u222b", "\u222c", "\u222d", "\u222e", "\u222f", "\u2230"], + props: { + numArgs: 0 + }, + + handler(_ref5) { + let { + parser, + funcName + } = _ref5; + let fName = funcName; + + if (fName.length === 1) { + fName = singleCharIntegrals[fName]; + } + + return { + type: "op", + mode: parser.mode, + limits: false, + parentIsSupSub: false, + symbol: true, + name: fName + }; + }, + + htmlBuilder: op_htmlBuilder, + mathmlBuilder: op_mathmlBuilder +}); +;// CONCATENATED MODULE: ./src/functions/operatorname.js + + + + + + + + + +// NOTE: Unlike most `htmlBuilder`s, this one handles not only +// "operatorname", but also "supsub" since \operatorname* can +// affect super/subscripting. +const operatorname_htmlBuilder = (grp, options) => { + // Operators are handled in the TeXbook pg. 443-444, rule 13(a). + let supGroup; + let subGroup; + let hasLimits = false; + let group; + + if (grp.type === "supsub") { + // If we have limits, supsub will pass us its group to handle. Pull + // out the superscript and subscript and set the group to the op in + // its base. + supGroup = grp.sup; + subGroup = grp.sub; + group = assertNodeType(grp.base, "operatorname"); + hasLimits = true; + } else { + group = assertNodeType(grp, "operatorname"); + } + + let base; + + if (group.body.length > 0) { + const body = group.body.map(child => { + // $FlowFixMe: Check if the node has a string `text` property. + const childText = child.text; + + if (typeof childText === "string") { + return { + type: "textord", + mode: child.mode, + text: childText + }; + } else { + return child; + } + }); // Consolidate function names into symbol characters. + + const expression = buildExpression(body, options.withFont("mathrm"), true); + + for (let i = 0; i < expression.length; i++) { + const child = expression[i]; + + if (child instanceof SymbolNode) { + // Per amsopn package, + // change minus to hyphen and \ast to asterisk + child.text = child.text.replace(/\u2212/, "-").replace(/\u2217/, "*"); + } + } + + base = buildCommon.makeSpan(["mop"], expression, options); + } else { + base = buildCommon.makeSpan(["mop"], [], options); + } + + if (hasLimits) { + return assembleSupSub(base, supGroup, subGroup, options, options.style, 0, 0); + } else { + return base; + } +}; + +const operatorname_mathmlBuilder = (group, options) => { + // The steps taken here are similar to the html version. + let expression = buildMathML_buildExpression(group.body, options.withFont("mathrm")); // Is expression a string or has it something like a fraction? + + let isAllString = true; // default + + for (let i = 0; i < expression.length; i++) { + const node = expression[i]; + + if (node instanceof mathMLTree.SpaceNode) {// Do nothing + } else if (node instanceof mathMLTree.MathNode) { + switch (node.type) { + case "mi": + case "mn": + case "ms": + case "mspace": + case "mtext": + break; + // Do nothing yet. + + case "mo": + { + const child = node.children[0]; + + if (node.children.length === 1 && child instanceof mathMLTree.TextNode) { + child.text = child.text.replace(/\u2212/, "-").replace(/\u2217/, "*"); + } else { + isAllString = false; + } + + break; + } + + default: + isAllString = false; + } + } else { + isAllString = false; + } + } + + if (isAllString) { + // Write a single TextNode instead of multiple nested tags. + const word = expression.map(node => node.toText()).join(""); + expression = [new mathMLTree.TextNode(word)]; + } + + const identifier = new mathMLTree.MathNode("mi", expression); + identifier.setAttribute("mathvariant", "normal"); // \u2061 is the same as ⁡ + // ref: https://www.w3schools.com/charsets/ref_html_entities_a.asp + + const operator = new mathMLTree.MathNode("mo", [makeText("\u2061", "text")]); + + if (group.parentIsSupSub) { + return new mathMLTree.MathNode("mrow", [identifier, operator]); + } else { + return mathMLTree.newDocumentFragment([identifier, operator]); + } +}; // \operatorname +// amsopn.dtx: \mathop{#1\kern\z@\operator@font#3}\newmcodes@ + + +defineFunction({ + type: "operatorname", + names: ["\\operatorname@", "\\operatornamewithlimits"], + props: { + numArgs: 1 + }, + handler: (_ref, args) => { + let { + parser, + funcName + } = _ref; + const body = args[0]; + return { + type: "operatorname", + mode: parser.mode, + body: ordargument(body), + alwaysHandleSupSub: funcName === "\\operatornamewithlimits", + limits: false, + parentIsSupSub: false + }; + }, + htmlBuilder: operatorname_htmlBuilder, + mathmlBuilder: operatorname_mathmlBuilder +}); +defineMacro("\\operatorname", "\\@ifstar\\operatornamewithlimits\\operatorname@"); +;// CONCATENATED MODULE: ./src/functions/ordgroup.js + + + + +defineFunctionBuilders({ + type: "ordgroup", + + htmlBuilder(group, options) { + if (group.semisimple) { + return buildCommon.makeFragment(buildExpression(group.body, options, false)); + } + + return buildCommon.makeSpan(["mord"], buildExpression(group.body, options, true), options); + }, + + mathmlBuilder(group, options) { + return buildExpressionRow(group.body, options, true); + } + +}); +;// CONCATENATED MODULE: ./src/functions/overline.js + + + + + +defineFunction({ + type: "overline", + names: ["\\overline"], + props: { + numArgs: 1 + }, + + handler(_ref, args) { + let { + parser + } = _ref; + const body = args[0]; + return { + type: "overline", + mode: parser.mode, + body + }; + }, + + htmlBuilder(group, options) { + // Overlines are handled in the TeXbook pg 443, Rule 9. + // Build the inner group in the cramped style. + const innerGroup = buildGroup(group.body, options.havingCrampedStyle()); // Create the line above the body + + const line = buildCommon.makeLineSpan("overline-line", options); // Generate the vlist, with the appropriate kerns + + const defaultRuleThickness = options.fontMetrics().defaultRuleThickness; + const vlist = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: innerGroup + }, { + type: "kern", + size: 3 * defaultRuleThickness + }, { + type: "elem", + elem: line + }, { + type: "kern", + size: defaultRuleThickness + }] + }, options); + return buildCommon.makeSpan(["mord", "overline"], [vlist], options); + }, + + mathmlBuilder(group, options) { + const operator = new mathMLTree.MathNode("mo", [new mathMLTree.TextNode("\u203e")]); + operator.setAttribute("stretchy", "true"); + const node = new mathMLTree.MathNode("mover", [buildMathML_buildGroup(group.body, options), operator]); + node.setAttribute("accent", "true"); + return node; + } + +}); +;// CONCATENATED MODULE: ./src/functions/phantom.js + + + + + +defineFunction({ + type: "phantom", + names: ["\\phantom"], + props: { + numArgs: 1, + allowedInText: true + }, + handler: (_ref, args) => { + let { + parser + } = _ref; + const body = args[0]; + return { + type: "phantom", + mode: parser.mode, + body: ordargument(body) + }; + }, + htmlBuilder: (group, options) => { + const elements = buildExpression(group.body, options.withPhantom(), false); // \phantom isn't supposed to affect the elements it contains. + // See "color" for more details. + + return buildCommon.makeFragment(elements); + }, + mathmlBuilder: (group, options) => { + const inner = buildMathML_buildExpression(group.body, options); + return new mathMLTree.MathNode("mphantom", inner); + } +}); +defineFunction({ + type: "hphantom", + names: ["\\hphantom"], + props: { + numArgs: 1, + allowedInText: true + }, + handler: (_ref2, args) => { + let { + parser + } = _ref2; + const body = args[0]; + return { + type: "hphantom", + mode: parser.mode, + body + }; + }, + htmlBuilder: (group, options) => { + let node = buildCommon.makeSpan([], [buildGroup(group.body, options.withPhantom())]); + node.height = 0; + node.depth = 0; + + if (node.children) { + for (let i = 0; i < node.children.length; i++) { + node.children[i].height = 0; + node.children[i].depth = 0; + } + } // See smash for comment re: use of makeVList + + + node = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: node + }] + }, options); // For spacing, TeX treats \smash as a math group (same spacing as ord). + + return buildCommon.makeSpan(["mord"], [node], options); + }, + mathmlBuilder: (group, options) => { + const inner = buildMathML_buildExpression(ordargument(group.body), options); + const phantom = new mathMLTree.MathNode("mphantom", inner); + const node = new mathMLTree.MathNode("mpadded", [phantom]); + node.setAttribute("height", "0px"); + node.setAttribute("depth", "0px"); + return node; + } +}); +defineFunction({ + type: "vphantom", + names: ["\\vphantom"], + props: { + numArgs: 1, + allowedInText: true + }, + handler: (_ref3, args) => { + let { + parser + } = _ref3; + const body = args[0]; + return { + type: "vphantom", + mode: parser.mode, + body + }; + }, + htmlBuilder: (group, options) => { + const inner = buildCommon.makeSpan(["inner"], [buildGroup(group.body, options.withPhantom())]); + const fix = buildCommon.makeSpan(["fix"], []); + return buildCommon.makeSpan(["mord", "rlap"], [inner, fix], options); + }, + mathmlBuilder: (group, options) => { + const inner = buildMathML_buildExpression(ordargument(group.body), options); + const phantom = new mathMLTree.MathNode("mphantom", inner); + const node = new mathMLTree.MathNode("mpadded", [phantom]); + node.setAttribute("width", "0px"); + return node; + } +}); +;// CONCATENATED MODULE: ./src/functions/raisebox.js + + + + + + + // Box manipulation + +defineFunction({ + type: "raisebox", + names: ["\\raisebox"], + props: { + numArgs: 2, + argTypes: ["size", "hbox"], + allowedInText: true + }, + + handler(_ref, args) { + let { + parser + } = _ref; + const amount = assertNodeType(args[0], "size").value; + const body = args[1]; + return { + type: "raisebox", + mode: parser.mode, + dy: amount, + body + }; + }, + + htmlBuilder(group, options) { + const body = buildGroup(group.body, options); + const dy = calculateSize(group.dy, options); + return buildCommon.makeVList({ + positionType: "shift", + positionData: -dy, + children: [{ + type: "elem", + elem: body + }] + }, options); + }, + + mathmlBuilder(group, options) { + const node = new mathMLTree.MathNode("mpadded", [buildMathML_buildGroup(group.body, options)]); + const dy = group.dy.number + group.dy.unit; + node.setAttribute("voffset", dy); + return node; + } + +}); +;// CONCATENATED MODULE: ./src/functions/relax.js + +defineFunction({ + type: "internal", + names: ["\\relax"], + props: { + numArgs: 0, + allowedInText: true, + allowedInArgument: true + }, + + handler(_ref) { + let { + parser + } = _ref; + return { + type: "internal", + mode: parser.mode + }; + } + +}); +;// CONCATENATED MODULE: ./src/functions/rule.js + + + + + +defineFunction({ + type: "rule", + names: ["\\rule"], + props: { + numArgs: 2, + numOptionalArgs: 1, + allowedInText: true, + allowedInMath: true, + argTypes: ["size", "size", "size"] + }, + + handler(_ref, args, optArgs) { + let { + parser + } = _ref; + const shift = optArgs[0]; + const width = assertNodeType(args[0], "size"); + const height = assertNodeType(args[1], "size"); + return { + type: "rule", + mode: parser.mode, + shift: shift && assertNodeType(shift, "size").value, + width: width.value, + height: height.value + }; + }, + + htmlBuilder(group, options) { + // Make an empty span for the rule + const rule = buildCommon.makeSpan(["mord", "rule"], [], options); // Calculate the shift, width, and height of the rule, and account for units + + const width = calculateSize(group.width, options); + const height = calculateSize(group.height, options); + const shift = group.shift ? calculateSize(group.shift, options) : 0; // Style the rule to the right size + + rule.style.borderRightWidth = makeEm(width); + rule.style.borderTopWidth = makeEm(height); + rule.style.bottom = makeEm(shift); // Record the height and width + + rule.width = width; + rule.height = height + shift; + rule.depth = -shift; // Font size is the number large enough that the browser will + // reserve at least `absHeight` space above the baseline. + // The 1.125 factor was empirically determined + + rule.maxFontSize = height * 1.125 * options.sizeMultiplier; + return rule; + }, + + mathmlBuilder(group, options) { + const width = calculateSize(group.width, options); + const height = calculateSize(group.height, options); + const shift = group.shift ? calculateSize(group.shift, options) : 0; + const color = options.color && options.getColor() || "black"; + const rule = new mathMLTree.MathNode("mspace"); + rule.setAttribute("mathbackground", color); + rule.setAttribute("width", makeEm(width)); + rule.setAttribute("height", makeEm(height)); + const wrapper = new mathMLTree.MathNode("mpadded", [rule]); + + if (shift >= 0) { + wrapper.setAttribute("height", makeEm(shift)); + } else { + wrapper.setAttribute("height", makeEm(shift)); + wrapper.setAttribute("depth", makeEm(-shift)); + } + + wrapper.setAttribute("voffset", makeEm(shift)); + return wrapper; + } + +}); +;// CONCATENATED MODULE: ./src/functions/sizing.js + + + + + + +function sizingGroup(value, options, baseOptions) { + const inner = buildExpression(value, options, false); + const multiplier = options.sizeMultiplier / baseOptions.sizeMultiplier; // Add size-resetting classes to the inner list and set maxFontSize + // manually. Handle nested size changes. + + for (let i = 0; i < inner.length; i++) { + const pos = inner[i].classes.indexOf("sizing"); + + if (pos < 0) { + Array.prototype.push.apply(inner[i].classes, options.sizingClasses(baseOptions)); + } else if (inner[i].classes[pos + 1] === "reset-size" + options.size) { + // This is a nested size change: e.g., inner[i] is the "b" in + // `\Huge a \small b`. Override the old size (the `reset-` class) + // but not the new size. + inner[i].classes[pos + 1] = "reset-size" + baseOptions.size; + } + + inner[i].height *= multiplier; + inner[i].depth *= multiplier; + } + + return buildCommon.makeFragment(inner); +} +const sizeFuncs = ["\\tiny", "\\sixptsize", "\\scriptsize", "\\footnotesize", "\\small", "\\normalsize", "\\large", "\\Large", "\\LARGE", "\\huge", "\\Huge"]; +const sizing_htmlBuilder = (group, options) => { + // Handle sizing operators like \Huge. Real TeX doesn't actually allow + // these functions inside of math expressions, so we do some special + // handling. + const newOptions = options.havingSize(group.size); + return sizingGroup(group.body, newOptions, options); +}; +defineFunction({ + type: "sizing", + names: sizeFuncs, + props: { + numArgs: 0, + allowedInText: true + }, + handler: (_ref, args) => { + let { + breakOnTokenText, + funcName, + parser + } = _ref; + const body = parser.parseExpression(false, breakOnTokenText); + return { + type: "sizing", + mode: parser.mode, + // Figure out what size to use based on the list of functions above + size: sizeFuncs.indexOf(funcName) + 1, + body + }; + }, + htmlBuilder: sizing_htmlBuilder, + mathmlBuilder: (group, options) => { + const newOptions = options.havingSize(group.size); + const inner = buildMathML_buildExpression(group.body, newOptions); + const node = new mathMLTree.MathNode("mstyle", inner); // TODO(emily): This doesn't produce the correct size for nested size + // changes, because we don't keep state of what style we're currently + // in, so we can't reset the size to normal before changing it. Now + // that we're passing an options parameter we should be able to fix + // this. + + node.setAttribute("mathsize", makeEm(newOptions.sizeMultiplier)); + return node; + } +}); +;// CONCATENATED MODULE: ./src/functions/smash.js +// smash, with optional [tb], as in AMS + + + + + + +defineFunction({ + type: "smash", + names: ["\\smash"], + props: { + numArgs: 1, + numOptionalArgs: 1, + allowedInText: true + }, + handler: (_ref, args, optArgs) => { + let { + parser + } = _ref; + let smashHeight = false; + let smashDepth = false; + const tbArg = optArgs[0] && assertNodeType(optArgs[0], "ordgroup"); + + if (tbArg) { + // Optional [tb] argument is engaged. + // ref: amsmath: \renewcommand{\smash}[1][tb]{% + // def\mb@t{\ht}\def\mb@b{\dp}\def\mb@tb{\ht\z@\z@\dp}% + let letter = ""; + + for (let i = 0; i < tbArg.body.length; ++i) { + const node = tbArg.body[i]; // $FlowFixMe: Not every node type has a `text` property. + + letter = node.text; + + if (letter === "t") { + smashHeight = true; + } else if (letter === "b") { + smashDepth = true; + } else { + smashHeight = false; + smashDepth = false; + break; + } + } + } else { + smashHeight = true; + smashDepth = true; + } + + const body = args[0]; + return { + type: "smash", + mode: parser.mode, + body, + smashHeight, + smashDepth + }; + }, + htmlBuilder: (group, options) => { + const node = buildCommon.makeSpan([], [buildGroup(group.body, options)]); + + if (!group.smashHeight && !group.smashDepth) { + return node; + } + + if (group.smashHeight) { + node.height = 0; // In order to influence makeVList, we have to reset the children. + + if (node.children) { + for (let i = 0; i < node.children.length; i++) { + node.children[i].height = 0; + } + } + } + + if (group.smashDepth) { + node.depth = 0; + + if (node.children) { + for (let i = 0; i < node.children.length; i++) { + node.children[i].depth = 0; + } + } + } // At this point, we've reset the TeX-like height and depth values. + // But the span still has an HTML line height. + // makeVList applies "display: table-cell", which prevents the browser + // from acting on that line height. So we'll call makeVList now. + + + const smashedNode = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: node + }] + }, options); // For spacing, TeX treats \hphantom as a math group (same spacing as ord). + + return buildCommon.makeSpan(["mord"], [smashedNode], options); + }, + mathmlBuilder: (group, options) => { + const node = new mathMLTree.MathNode("mpadded", [buildMathML_buildGroup(group.body, options)]); + + if (group.smashHeight) { + node.setAttribute("height", "0px"); + } + + if (group.smashDepth) { + node.setAttribute("depth", "0px"); + } + + return node; + } +}); +;// CONCATENATED MODULE: ./src/functions/sqrt.js + + + + + + + + +defineFunction({ + type: "sqrt", + names: ["\\sqrt"], + props: { + numArgs: 1, + numOptionalArgs: 1 + }, + + handler(_ref, args, optArgs) { + let { + parser + } = _ref; + const index = optArgs[0]; + const body = args[0]; + return { + type: "sqrt", + mode: parser.mode, + body, + index + }; + }, + + htmlBuilder(group, options) { + // Square roots are handled in the TeXbook pg. 443, Rule 11. + // First, we do the same steps as in overline to build the inner group + // and line + let inner = buildGroup(group.body, options.havingCrampedStyle()); + + if (inner.height === 0) { + // Render a small surd. + inner.height = options.fontMetrics().xHeight; + } // Some groups can return document fragments. Handle those by wrapping + // them in a span. + + + inner = buildCommon.wrapFragment(inner, options); // Calculate the minimum size for the \surd delimiter + + const metrics = options.fontMetrics(); + const theta = metrics.defaultRuleThickness; + let phi = theta; + + if (options.style.id < src_Style.TEXT.id) { + phi = options.fontMetrics().xHeight; + } // Calculate the clearance between the body and line + + + let lineClearance = theta + phi / 4; + const minDelimiterHeight = inner.height + inner.depth + lineClearance + theta; // Create a sqrt SVG of the required minimum size + + const { + span: img, + ruleWidth, + advanceWidth + } = delimiter.sqrtImage(minDelimiterHeight, options); + const delimDepth = img.height - ruleWidth; // Adjust the clearance based on the delimiter size + + if (delimDepth > inner.height + inner.depth + lineClearance) { + lineClearance = (lineClearance + delimDepth - inner.height - inner.depth) / 2; + } // Shift the sqrt image + + + const imgShift = img.height - inner.height - lineClearance - ruleWidth; + inner.style.paddingLeft = makeEm(advanceWidth); // Overlay the image and the argument. + + const body = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: inner, + wrapperClasses: ["svg-align"] + }, { + type: "kern", + size: -(inner.height + imgShift) + }, { + type: "elem", + elem: img + }, { + type: "kern", + size: ruleWidth + }] + }, options); + + if (!group.index) { + return buildCommon.makeSpan(["mord", "sqrt"], [body], options); + } else { + // Handle the optional root index + // The index is always in scriptscript style + const newOptions = options.havingStyle(src_Style.SCRIPTSCRIPT); + const rootm = buildGroup(group.index, newOptions, options); // The amount the index is shifted by. This is taken from the TeX + // source, in the definition of `\r@@t`. + + const toShift = 0.6 * (body.height - body.depth); // Build a VList with the superscript shifted up correctly + + const rootVList = buildCommon.makeVList({ + positionType: "shift", + positionData: -toShift, + children: [{ + type: "elem", + elem: rootm + }] + }, options); // Add a class surrounding it so we can add on the appropriate + // kerning + + const rootVListWrap = buildCommon.makeSpan(["root"], [rootVList]); + return buildCommon.makeSpan(["mord", "sqrt"], [rootVListWrap, body], options); + } + }, + + mathmlBuilder(group, options) { + const { + body, + index + } = group; + return index ? new mathMLTree.MathNode("mroot", [buildMathML_buildGroup(body, options), buildMathML_buildGroup(index, options)]) : new mathMLTree.MathNode("msqrt", [buildMathML_buildGroup(body, options)]); + } + +}); +;// CONCATENATED MODULE: ./src/functions/styling.js + + + + + +const styling_styleMap = { + "display": src_Style.DISPLAY, + "text": src_Style.TEXT, + "script": src_Style.SCRIPT, + "scriptscript": src_Style.SCRIPTSCRIPT +}; +defineFunction({ + type: "styling", + names: ["\\displaystyle", "\\textstyle", "\\scriptstyle", "\\scriptscriptstyle"], + props: { + numArgs: 0, + allowedInText: true, + primitive: true + }, + + handler(_ref, args) { + let { + breakOnTokenText, + funcName, + parser + } = _ref; + // parse out the implicit body + const body = parser.parseExpression(true, breakOnTokenText); // TODO: Refactor to avoid duplicating styleMap in multiple places (e.g. + // here and in buildHTML and de-dupe the enumeration of all the styles). + // $FlowFixMe: The names above exactly match the styles. + + const style = funcName.slice(1, funcName.length - 5); + return { + type: "styling", + mode: parser.mode, + // Figure out what style to use by pulling out the style from + // the function name + style, + body + }; + }, + + htmlBuilder(group, options) { + // Style changes are handled in the TeXbook on pg. 442, Rule 3. + const newStyle = styling_styleMap[group.style]; + const newOptions = options.havingStyle(newStyle).withFont(''); + return sizingGroup(group.body, newOptions, options); + }, + + mathmlBuilder(group, options) { + // Figure out what style we're changing to. + const newStyle = styling_styleMap[group.style]; + const newOptions = options.havingStyle(newStyle); + const inner = buildMathML_buildExpression(group.body, newOptions); + const node = new mathMLTree.MathNode("mstyle", inner); + const styleAttributes = { + "display": ["0", "true"], + "text": ["0", "false"], + "script": ["1", "false"], + "scriptscript": ["2", "false"] + }; + const attr = styleAttributes[group.style]; + node.setAttribute("scriptlevel", attr[0]); + node.setAttribute("displaystyle", attr[1]); + return node; + } + +}); +;// CONCATENATED MODULE: ./src/functions/supsub.js + + + + + + + + + + + + + + +/** + * Sometimes, groups perform special rules when they have superscripts or + * subscripts attached to them. This function lets the `supsub` group know that + * Sometimes, groups perform special rules when they have superscripts or + * its inner element should handle the superscripts and subscripts instead of + * handling them itself. + */ +const htmlBuilderDelegate = function (group, options) { + const base = group.base; + + if (!base) { + return null; + } else if (base.type === "op") { + // Operators handle supsubs differently when they have limits + // (e.g. `\displaystyle\sum_2^3`) + const delegate = base.limits && (options.style.size === src_Style.DISPLAY.size || base.alwaysHandleSupSub); + return delegate ? op_htmlBuilder : null; + } else if (base.type === "operatorname") { + const delegate = base.alwaysHandleSupSub && (options.style.size === src_Style.DISPLAY.size || base.limits); + return delegate ? operatorname_htmlBuilder : null; + } else if (base.type === "accent") { + return utils.isCharacterBox(base.base) ? htmlBuilder : null; + } else if (base.type === "horizBrace") { + const isSup = !group.sub; + return isSup === base.isOver ? horizBrace_htmlBuilder : null; + } else { + return null; + } +}; // Super scripts and subscripts, whose precise placement can depend on other +// functions that precede them. + + +defineFunctionBuilders({ + type: "supsub", + + htmlBuilder(group, options) { + // Superscript and subscripts are handled in the TeXbook on page + // 445-446, rules 18(a-f). + // Here is where we defer to the inner group if it should handle + // superscripts and subscripts itself. + const builderDelegate = htmlBuilderDelegate(group, options); + + if (builderDelegate) { + return builderDelegate(group, options); + } + + const { + base: valueBase, + sup: valueSup, + sub: valueSub + } = group; + const base = buildGroup(valueBase, options); + let supm; + let subm; + const metrics = options.fontMetrics(); // Rule 18a + + let supShift = 0; + let subShift = 0; + const isCharacterBox = valueBase && utils.isCharacterBox(valueBase); + + if (valueSup) { + const newOptions = options.havingStyle(options.style.sup()); + supm = buildGroup(valueSup, newOptions, options); + + if (!isCharacterBox) { + supShift = base.height - newOptions.fontMetrics().supDrop * newOptions.sizeMultiplier / options.sizeMultiplier; + } + } + + if (valueSub) { + const newOptions = options.havingStyle(options.style.sub()); + subm = buildGroup(valueSub, newOptions, options); + + if (!isCharacterBox) { + subShift = base.depth + newOptions.fontMetrics().subDrop * newOptions.sizeMultiplier / options.sizeMultiplier; + } + } // Rule 18c + + + let minSupShift; + + if (options.style === src_Style.DISPLAY) { + minSupShift = metrics.sup1; + } else if (options.style.cramped) { + minSupShift = metrics.sup3; + } else { + minSupShift = metrics.sup2; + } // scriptspace is a font-size-independent size, so scale it + // appropriately for use as the marginRight. + + + const multiplier = options.sizeMultiplier; + const marginRight = makeEm(0.5 / metrics.ptPerEm / multiplier); + let marginLeft = null; + + if (subm) { + // Subscripts shouldn't be shifted by the base's italic correction. + // Account for that by shifting the subscript back the appropriate + // amount. Note we only do this when the base is a single symbol. + const isOiint = group.base && group.base.type === "op" && group.base.name && (group.base.name === "\\oiint" || group.base.name === "\\oiiint"); + + if (base instanceof SymbolNode || isOiint) { + // $FlowFixMe + marginLeft = makeEm(-base.italic); + } + } + + let supsub; + + if (supm && subm) { + supShift = Math.max(supShift, minSupShift, supm.depth + 0.25 * metrics.xHeight); + subShift = Math.max(subShift, metrics.sub2); + const ruleWidth = metrics.defaultRuleThickness; // Rule 18e + + const maxWidth = 4 * ruleWidth; + + if (supShift - supm.depth - (subm.height - subShift) < maxWidth) { + subShift = maxWidth - (supShift - supm.depth) + subm.height; + const psi = 0.8 * metrics.xHeight - (supShift - supm.depth); + + if (psi > 0) { + supShift += psi; + subShift -= psi; + } + } + + const vlistElem = [{ + type: "elem", + elem: subm, + shift: subShift, + marginRight, + marginLeft + }, { + type: "elem", + elem: supm, + shift: -supShift, + marginRight + }]; + supsub = buildCommon.makeVList({ + positionType: "individualShift", + children: vlistElem + }, options); + } else if (subm) { + // Rule 18b + subShift = Math.max(subShift, metrics.sub1, subm.height - 0.8 * metrics.xHeight); + const vlistElem = [{ + type: "elem", + elem: subm, + marginLeft, + marginRight + }]; + supsub = buildCommon.makeVList({ + positionType: "shift", + positionData: subShift, + children: vlistElem + }, options); + } else if (supm) { + // Rule 18c, d + supShift = Math.max(supShift, minSupShift, supm.depth + 0.25 * metrics.xHeight); + supsub = buildCommon.makeVList({ + positionType: "shift", + positionData: -supShift, + children: [{ + type: "elem", + elem: supm, + marginRight + }] + }, options); + } else { + throw new Error("supsub must have either sup or sub."); + } // Wrap the supsub vlist in a span.msupsub to reset text-align. + + + const mclass = getTypeOfDomTree(base, "right") || "mord"; + return buildCommon.makeSpan([mclass], [base, buildCommon.makeSpan(["msupsub"], [supsub])], options); + }, + + mathmlBuilder(group, options) { + // Is the inner group a relevant horizontal brace? + let isBrace = false; + let isOver; + let isSup; + + if (group.base && group.base.type === "horizBrace") { + isSup = !!group.sup; + + if (isSup === group.base.isOver) { + isBrace = true; + isOver = group.base.isOver; + } + } + + if (group.base && (group.base.type === "op" || group.base.type === "operatorname")) { + group.base.parentIsSupSub = true; + } + + const children = [buildMathML_buildGroup(group.base, options)]; + + if (group.sub) { + children.push(buildMathML_buildGroup(group.sub, options)); + } + + if (group.sup) { + children.push(buildMathML_buildGroup(group.sup, options)); + } + + let nodeType; + + if (isBrace) { + nodeType = isOver ? "mover" : "munder"; + } else if (!group.sub) { + const base = group.base; + + if (base && base.type === "op" && base.limits && (options.style === src_Style.DISPLAY || base.alwaysHandleSupSub)) { + nodeType = "mover"; + } else if (base && base.type === "operatorname" && base.alwaysHandleSupSub && (base.limits || options.style === src_Style.DISPLAY)) { + nodeType = "mover"; + } else { + nodeType = "msup"; + } + } else if (!group.sup) { + const base = group.base; + + if (base && base.type === "op" && base.limits && (options.style === src_Style.DISPLAY || base.alwaysHandleSupSub)) { + nodeType = "munder"; + } else if (base && base.type === "operatorname" && base.alwaysHandleSupSub && (base.limits || options.style === src_Style.DISPLAY)) { + nodeType = "munder"; + } else { + nodeType = "msub"; + } + } else { + const base = group.base; + + if (base && base.type === "op" && base.limits && options.style === src_Style.DISPLAY) { + nodeType = "munderover"; + } else if (base && base.type === "operatorname" && base.alwaysHandleSupSub && (options.style === src_Style.DISPLAY || base.limits)) { + nodeType = "munderover"; + } else { + nodeType = "msubsup"; + } + } + + return new mathMLTree.MathNode(nodeType, children); + } + +}); +;// CONCATENATED MODULE: ./src/functions/symbolsOp.js + + + + // Operator ParseNodes created in Parser.js from symbol Groups in src/symbols.js. + +defineFunctionBuilders({ + type: "atom", + + htmlBuilder(group, options) { + return buildCommon.mathsym(group.text, group.mode, options, ["m" + group.family]); + }, + + mathmlBuilder(group, options) { + const node = new mathMLTree.MathNode("mo", [makeText(group.text, group.mode)]); + + if (group.family === "bin") { + const variant = getVariant(group, options); + + if (variant === "bold-italic") { + node.setAttribute("mathvariant", variant); + } + } else if (group.family === "punct") { + node.setAttribute("separator", "true"); + } else if (group.family === "open" || group.family === "close") { + // Delims built here should not stretch vertically. + // See delimsizing.js for stretchy delims. + node.setAttribute("stretchy", "false"); + } + + return node; + } + +}); +;// CONCATENATED MODULE: ./src/functions/symbolsOrd.js + + + + +// "mathord" and "textord" ParseNodes created in Parser.js from symbol Groups in +// src/symbols.js. +const defaultVariant = { + "mi": "italic", + "mn": "normal", + "mtext": "normal" +}; +defineFunctionBuilders({ + type: "mathord", + + htmlBuilder(group, options) { + return buildCommon.makeOrd(group, options, "mathord"); + }, + + mathmlBuilder(group, options) { + const node = new mathMLTree.MathNode("mi", [makeText(group.text, group.mode, options)]); + const variant = getVariant(group, options) || "italic"; + + if (variant !== defaultVariant[node.type]) { + node.setAttribute("mathvariant", variant); + } + + return node; + } + +}); +defineFunctionBuilders({ + type: "textord", + + htmlBuilder(group, options) { + return buildCommon.makeOrd(group, options, "textord"); + }, + + mathmlBuilder(group, options) { + const text = makeText(group.text, group.mode, options); + const variant = getVariant(group, options) || "normal"; + let node; + + if (group.mode === 'text') { + node = new mathMLTree.MathNode("mtext", [text]); + } else if (/[0-9]/.test(group.text)) { + node = new mathMLTree.MathNode("mn", [text]); + } else if (group.text === "\\prime") { + node = new mathMLTree.MathNode("mo", [text]); + } else { + node = new mathMLTree.MathNode("mi", [text]); + } + + if (variant !== defaultVariant[node.type]) { + node.setAttribute("mathvariant", variant); + } + + return node; + } + +}); +;// CONCATENATED MODULE: ./src/functions/symbolsSpacing.js + + + + // A map of CSS-based spacing functions to their CSS class. + +const cssSpace = { + "\\nobreak": "nobreak", + "\\allowbreak": "allowbreak" +}; // A lookup table to determine whether a spacing function/symbol should be +// treated like a regular space character. If a symbol or command is a key +// in this table, then it should be a regular space character. Furthermore, +// the associated value may have a `className` specifying an extra CSS class +// to add to the created `span`. + +const regularSpace = { + " ": {}, + "\\ ": {}, + "~": { + className: "nobreak" + }, + "\\space": {}, + "\\nobreakspace": { + className: "nobreak" + } +}; // ParseNode<"spacing"> created in Parser.js from the "spacing" symbol Groups in +// src/symbols.js. + +defineFunctionBuilders({ + type: "spacing", + + htmlBuilder(group, options) { + if (regularSpace.hasOwnProperty(group.text)) { + const className = regularSpace[group.text].className || ""; // Spaces are generated by adding an actual space. Each of these + // things has an entry in the symbols table, so these will be turned + // into appropriate outputs. + + if (group.mode === "text") { + const ord = buildCommon.makeOrd(group, options, "textord"); + ord.classes.push(className); + return ord; + } else { + return buildCommon.makeSpan(["mspace", className], [buildCommon.mathsym(group.text, group.mode, options)], options); + } + } else if (cssSpace.hasOwnProperty(group.text)) { + // Spaces based on just a CSS class. + return buildCommon.makeSpan(["mspace", cssSpace[group.text]], [], options); + } else { + throw new src_ParseError("Unknown type of space \"" + group.text + "\""); + } + }, + + mathmlBuilder(group, options) { + let node; + + if (regularSpace.hasOwnProperty(group.text)) { + node = new mathMLTree.MathNode("mtext", [new mathMLTree.TextNode("\u00a0")]); + } else if (cssSpace.hasOwnProperty(group.text)) { + // CSS-based MathML spaces (\nobreak, \allowbreak) are ignored + return new mathMLTree.MathNode("mspace"); + } else { + throw new src_ParseError("Unknown type of space \"" + group.text + "\""); + } + + return node; + } + +}); +;// CONCATENATED MODULE: ./src/functions/tag.js + + + + +const pad = () => { + const padNode = new mathMLTree.MathNode("mtd", []); + padNode.setAttribute("width", "50%"); + return padNode; +}; + +defineFunctionBuilders({ + type: "tag", + + mathmlBuilder(group, options) { + const table = new mathMLTree.MathNode("mtable", [new mathMLTree.MathNode("mtr", [pad(), new mathMLTree.MathNode("mtd", [buildExpressionRow(group.body, options)]), pad(), new mathMLTree.MathNode("mtd", [buildExpressionRow(group.tag, options)])])]); + table.setAttribute("width", "100%"); + return table; // TODO: Left-aligned tags. + // Currently, the group and options passed here do not contain + // enough info to set tag alignment. `leqno` is in Settings but it is + // not passed to Options. On the HTML side, leqno is + // set by a CSS class applied in buildTree.js. That would have worked + // in MathML if browsers supported . Since they don't, we + // need to rewrite the way this function is called. + } + +}); +;// CONCATENATED MODULE: ./src/functions/text.js + + + + // Non-mathy text, possibly in a font + +const textFontFamilies = { + "\\text": undefined, + "\\textrm": "textrm", + "\\textsf": "textsf", + "\\texttt": "texttt", + "\\textnormal": "textrm" +}; +const textFontWeights = { + "\\textbf": "textbf", + "\\textmd": "textmd" +}; +const textFontShapes = { + "\\textit": "textit", + "\\textup": "textup" +}; + +const optionsWithFont = (group, options) => { + const font = group.font; // Checks if the argument is a font family or a font style. + + if (!font) { + return options; + } else if (textFontFamilies[font]) { + return options.withTextFontFamily(textFontFamilies[font]); + } else if (textFontWeights[font]) { + return options.withTextFontWeight(textFontWeights[font]); + } else if (font === "\\emph") { + return options.fontShape === "textit" ? options.withTextFontShape("textup") : options.withTextFontShape("textit"); + } + + return options.withTextFontShape(textFontShapes[font]); +}; + +defineFunction({ + type: "text", + names: [// Font families + "\\text", "\\textrm", "\\textsf", "\\texttt", "\\textnormal", // Font weights + "\\textbf", "\\textmd", // Font Shapes + "\\textit", "\\textup", "\\emph"], + props: { + numArgs: 1, + argTypes: ["text"], + allowedInArgument: true, + allowedInText: true + }, + + handler(_ref, args) { + let { + parser, + funcName + } = _ref; + const body = args[0]; + return { + type: "text", + mode: parser.mode, + body: ordargument(body), + font: funcName + }; + }, + + htmlBuilder(group, options) { + const newOptions = optionsWithFont(group, options); + const inner = buildExpression(group.body, newOptions, true); + return buildCommon.makeSpan(["mord", "text"], inner, newOptions); + }, + + mathmlBuilder(group, options) { + const newOptions = optionsWithFont(group, options); + return buildExpressionRow(group.body, newOptions); + } + +}); +;// CONCATENATED MODULE: ./src/functions/underline.js + + + + + +defineFunction({ + type: "underline", + names: ["\\underline"], + props: { + numArgs: 1, + allowedInText: true + }, + + handler(_ref, args) { + let { + parser + } = _ref; + return { + type: "underline", + mode: parser.mode, + body: args[0] + }; + }, + + htmlBuilder(group, options) { + // Underlines are handled in the TeXbook pg 443, Rule 10. + // Build the inner group. + const innerGroup = buildGroup(group.body, options); // Create the line to go below the body + + const line = buildCommon.makeLineSpan("underline-line", options); // Generate the vlist, with the appropriate kerns + + const defaultRuleThickness = options.fontMetrics().defaultRuleThickness; + const vlist = buildCommon.makeVList({ + positionType: "top", + positionData: innerGroup.height, + children: [{ + type: "kern", + size: defaultRuleThickness + }, { + type: "elem", + elem: line + }, { + type: "kern", + size: 3 * defaultRuleThickness + }, { + type: "elem", + elem: innerGroup + }] + }, options); + return buildCommon.makeSpan(["mord", "underline"], [vlist], options); + }, + + mathmlBuilder(group, options) { + const operator = new mathMLTree.MathNode("mo", [new mathMLTree.TextNode("\u203e")]); + operator.setAttribute("stretchy", "true"); + const node = new mathMLTree.MathNode("munder", [buildMathML_buildGroup(group.body, options), operator]); + node.setAttribute("accentunder", "true"); + return node; + } + +}); +;// CONCATENATED MODULE: ./src/functions/vcenter.js + + + + + // \vcenter: Vertically center the argument group on the math axis. + +defineFunction({ + type: "vcenter", + names: ["\\vcenter"], + props: { + numArgs: 1, + argTypes: ["original"], + // In LaTeX, \vcenter can act only on a box. + allowedInText: false + }, + + handler(_ref, args) { + let { + parser + } = _ref; + return { + type: "vcenter", + mode: parser.mode, + body: args[0] + }; + }, + + htmlBuilder(group, options) { + const body = buildGroup(group.body, options); + const axisHeight = options.fontMetrics().axisHeight; + const dy = 0.5 * (body.height - axisHeight - (body.depth + axisHeight)); + return buildCommon.makeVList({ + positionType: "shift", + positionData: dy, + children: [{ + type: "elem", + elem: body + }] + }, options); + }, + + mathmlBuilder(group, options) { + // There is no way to do this in MathML. + // Write a class as a breadcrumb in case some post-processor wants + // to perform a vcenter adjustment. + return new mathMLTree.MathNode("mpadded", [buildMathML_buildGroup(group.body, options)], ["vcenter"]); + } + +}); +;// CONCATENATED MODULE: ./src/functions/verb.js + + + + +defineFunction({ + type: "verb", + names: ["\\verb"], + props: { + numArgs: 0, + allowedInText: true + }, + + handler(context, args, optArgs) { + // \verb and \verb* are dealt with directly in Parser.js. + // If we end up here, it's because of a failure to match the two delimiters + // in the regex in Lexer.js. LaTeX raises the following error when \verb is + // terminated by end of line (or file). + throw new src_ParseError("\\verb ended by end of line instead of matching delimiter"); + }, + + htmlBuilder(group, options) { + const text = makeVerb(group); + const body = []; // \verb enters text mode and therefore is sized like \textstyle + + const newOptions = options.havingStyle(options.style.text()); + + for (let i = 0; i < text.length; i++) { + let c = text[i]; + + if (c === '~') { + c = '\\textasciitilde'; + } + + body.push(buildCommon.makeSymbol(c, "Typewriter-Regular", group.mode, newOptions, ["mord", "texttt"])); + } + + return buildCommon.makeSpan(["mord", "text"].concat(newOptions.sizingClasses(options)), buildCommon.tryCombineChars(body), newOptions); + }, + + mathmlBuilder(group, options) { + const text = new mathMLTree.TextNode(makeVerb(group)); + const node = new mathMLTree.MathNode("mtext", [text]); + node.setAttribute("mathvariant", "monospace"); + return node; + } + +}); +/** + * Converts verb group into body string. + * + * \verb* replaces each space with an open box \u2423 + * \verb replaces each space with a no-break space \xA0 + */ + +const makeVerb = group => group.body.replace(/ /g, group.star ? '\u2423' : '\xA0'); +;// CONCATENATED MODULE: ./src/functions.js +/** Include this to ensure that all functions are defined. */ + +const functions = _functions; +/* harmony default export */ var src_functions = (functions); // TODO(kevinb): have functions return an object and call defineFunction with +// that object in this file instead of relying on side-effects. + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +;// CONCATENATED MODULE: ./src/Lexer.js +/** + * The Lexer class handles tokenizing the input in various ways. Since our + * parser expects us to be able to backtrack, the lexer allows lexing from any + * given starting point. + * + * Its main exposed function is the `lex` function, which takes a position to + * lex from and a type of token to lex. It defers to the appropriate `_innerLex` + * function. + * + * The various `_innerLex` functions perform the actual lexing of different + * kinds. + */ + + + + +/* The following tokenRegex + * - matches typical whitespace (but not NBSP etc.) using its first group + * - does not match any control character \x00-\x1f except whitespace + * - does not match a bare backslash + * - matches any ASCII character except those just mentioned + * - does not match the BMP private use area \uE000-\uF8FF + * - does not match bare surrogate code units + * - matches any BMP character except for those just described + * - matches any valid Unicode surrogate pair + * - matches a backslash followed by one or more whitespace characters + * - matches a backslash followed by one or more letters then whitespace + * - matches a backslash followed by any BMP character + * Capturing groups: + * [1] regular whitespace + * [2] backslash followed by whitespace + * [3] anything else, which may include: + * [4] left character of \verb* + * [5] left character of \verb + * [6] backslash followed by word, excluding any trailing whitespace + * Just because the Lexer matches something doesn't mean it's valid input: + * If there is no matching function or symbol definition, the Parser will + * still reject the input. + */ +const spaceRegexString = "[ \r\n\t]"; +const controlWordRegexString = "\\\\[a-zA-Z@]+"; +const controlSymbolRegexString = "\\\\[^\uD800-\uDFFF]"; +const controlWordWhitespaceRegexString = "(" + controlWordRegexString + ")" + spaceRegexString + "*"; +const controlSpaceRegexString = "\\\\(\n|[ \r\t]+\n?)[ \r\t]*"; +const combiningDiacriticalMarkString = "[\u0300-\u036f]"; +const combiningDiacriticalMarksEndRegex = new RegExp(combiningDiacriticalMarkString + "+$"); +const tokenRegexString = "(" + spaceRegexString + "+)|" + ( // whitespace +controlSpaceRegexString + "|") + // \whitespace +"([!-\\[\\]-\u2027\u202A-\uD7FF\uF900-\uFFFF]" + ( // single codepoint +combiningDiacriticalMarkString + "*") + // ...plus accents +"|[\uD800-\uDBFF][\uDC00-\uDFFF]" + ( // surrogate pair +combiningDiacriticalMarkString + "*") + // ...plus accents +"|\\\\verb\\*([^]).*?\\4" + // \verb* +"|\\\\verb([^*a-zA-Z]).*?\\5" + ( // \verb unstarred +"|" + controlWordWhitespaceRegexString) + ( // \macroName + spaces +"|" + controlSymbolRegexString + ")"); // \\, \', etc. + +/** Main Lexer class */ + +class Lexer { + // Category codes. The lexer only supports comment characters (14) for now. + // MacroExpander additionally distinguishes active (13). + constructor(input, settings) { + this.input = void 0; + this.settings = void 0; + this.tokenRegex = void 0; + this.catcodes = void 0; + // Separate accents from characters + this.input = input; + this.settings = settings; + this.tokenRegex = new RegExp(tokenRegexString, 'g'); + this.catcodes = { + "%": 14, + // comment character + "~": 13 // active character + + }; + } + + setCatcode(char, code) { + this.catcodes[char] = code; + } + /** + * This function lexes a single token. + */ + + + lex() { + const input = this.input; + const pos = this.tokenRegex.lastIndex; + + if (pos === input.length) { + return new Token("EOF", new SourceLocation(this, pos, pos)); + } + + const match = this.tokenRegex.exec(input); + + if (match === null || match.index !== pos) { + throw new src_ParseError("Unexpected character: '" + input[pos] + "'", new Token(input[pos], new SourceLocation(this, pos, pos + 1))); + } + + const text = match[6] || match[3] || (match[2] ? "\\ " : " "); + + if (this.catcodes[text] === 14) { + // comment character + const nlIndex = input.indexOf('\n', this.tokenRegex.lastIndex); + + if (nlIndex === -1) { + this.tokenRegex.lastIndex = input.length; // EOF + + this.settings.reportNonstrict("commentAtEnd", "% comment has no terminating newline; LaTeX would " + "fail because of commenting the end of math mode (e.g. $)"); + } else { + this.tokenRegex.lastIndex = nlIndex + 1; + } + + return this.lex(); + } + + return new Token(text, new SourceLocation(this, pos, this.tokenRegex.lastIndex)); + } + +} +;// CONCATENATED MODULE: ./src/Namespace.js +/** + * A `Namespace` refers to a space of nameable things like macros or lengths, + * which can be `set` either globally or local to a nested group, using an + * undo stack similar to how TeX implements this functionality. + * Performance-wise, `get` and local `set` take constant time, while global + * `set` takes time proportional to the depth of group nesting. + */ + +class Namespace { + /** + * Both arguments are optional. The first argument is an object of + * built-in mappings which never change. The second argument is an object + * of initial (global-level) mappings, which will constantly change + * according to any global/top-level `set`s done. + */ + constructor(builtins, globalMacros) { + if (builtins === void 0) { + builtins = {}; + } + + if (globalMacros === void 0) { + globalMacros = {}; + } + + this.current = void 0; + this.builtins = void 0; + this.undefStack = void 0; + this.current = globalMacros; + this.builtins = builtins; + this.undefStack = []; + } + /** + * Start a new nested group, affecting future local `set`s. + */ + + + beginGroup() { + this.undefStack.push({}); + } + /** + * End current nested group, restoring values before the group began. + */ + + + endGroup() { + if (this.undefStack.length === 0) { + throw new src_ParseError("Unbalanced namespace destruction: attempt " + "to pop global namespace; please report this as a bug"); + } + + const undefs = this.undefStack.pop(); + + for (const undef in undefs) { + if (undefs.hasOwnProperty(undef)) { + if (undefs[undef] == null) { + delete this.current[undef]; + } else { + this.current[undef] = undefs[undef]; + } + } + } + } + /** + * Ends all currently nested groups (if any), restoring values before the + * groups began. Useful in case of an error in the middle of parsing. + */ + + + endGroups() { + while (this.undefStack.length > 0) { + this.endGroup(); + } + } + /** + * Detect whether `name` has a definition. Equivalent to + * `get(name) != null`. + */ + + + has(name) { + return this.current.hasOwnProperty(name) || this.builtins.hasOwnProperty(name); + } + /** + * Get the current value of a name, or `undefined` if there is no value. + * + * Note: Do not use `if (namespace.get(...))` to detect whether a macro + * is defined, as the definition may be the empty string which evaluates + * to `false` in JavaScript. Use `if (namespace.get(...) != null)` or + * `if (namespace.has(...))`. + */ + + + get(name) { + if (this.current.hasOwnProperty(name)) { + return this.current[name]; + } else { + return this.builtins[name]; + } + } + /** + * Set the current value of a name, and optionally set it globally too. + * Local set() sets the current value and (when appropriate) adds an undo + * operation to the undo stack. Global set() may change the undo + * operation at every level, so takes time linear in their number. + * A value of undefined means to delete existing definitions. + */ + + + set(name, value, global) { + if (global === void 0) { + global = false; + } + + if (global) { + // Global set is equivalent to setting in all groups. Simulate this + // by destroying any undos currently scheduled for this name, + // and adding an undo with the *new* value (in case it later gets + // locally reset within this environment). + for (let i = 0; i < this.undefStack.length; i++) { + delete this.undefStack[i][name]; + } + + if (this.undefStack.length > 0) { + this.undefStack[this.undefStack.length - 1][name] = value; + } + } else { + // Undo this set at end of this group (possibly to `undefined`), + // unless an undo is already in place, in which case that older + // value is the correct one. + const top = this.undefStack[this.undefStack.length - 1]; + + if (top && !top.hasOwnProperty(name)) { + top[name] = this.current[name]; + } + } + + if (value == null) { + delete this.current[name]; + } else { + this.current[name] = value; + } + } + +} +;// CONCATENATED MODULE: ./src/macros.js +/** + * Predefined macros for KaTeX. + * This can be used to define some commands in terms of others. + */ +// Export global macros object from defineMacro + +const macros = _macros; +/* harmony default export */ var src_macros = (macros); + + + + + + ////////////////////////////////////////////////////////////////////// +// macro tools + +defineMacro("\\noexpand", function (context) { + // The expansion is the token itself; but that token is interpreted + // as if its meaning were ‘\relax’ if it is a control sequence that + // would ordinarily be expanded by TeX’s expansion rules. + const t = context.popToken(); + + if (context.isExpandable(t.text)) { + t.noexpand = true; + t.treatAsRelax = true; + } + + return { + tokens: [t], + numArgs: 0 + }; +}); +defineMacro("\\expandafter", function (context) { + // TeX first reads the token that comes immediately after \expandafter, + // without expanding it; let’s call this token t. Then TeX reads the + // token that comes after t (and possibly more tokens, if that token + // has an argument), replacing it by its expansion. Finally TeX puts + // t back in front of that expansion. + const t = context.popToken(); + context.expandOnce(true); // expand only an expandable token + + return { + tokens: [t], + numArgs: 0 + }; +}); // LaTeX's \@firstoftwo{#1}{#2} expands to #1, skipping #2 +// TeX source: \long\def\@firstoftwo#1#2{#1} + +defineMacro("\\@firstoftwo", function (context) { + const args = context.consumeArgs(2); + return { + tokens: args[0], + numArgs: 0 + }; +}); // LaTeX's \@secondoftwo{#1}{#2} expands to #2, skipping #1 +// TeX source: \long\def\@secondoftwo#1#2{#2} + +defineMacro("\\@secondoftwo", function (context) { + const args = context.consumeArgs(2); + return { + tokens: args[1], + numArgs: 0 + }; +}); // LaTeX's \@ifnextchar{#1}{#2}{#3} looks ahead to the next (unexpanded) +// symbol that isn't a space, consuming any spaces but not consuming the +// first nonspace character. If that nonspace character matches #1, then +// the macro expands to #2; otherwise, it expands to #3. + +defineMacro("\\@ifnextchar", function (context) { + const args = context.consumeArgs(3); // symbol, if, else + + context.consumeSpaces(); + const nextToken = context.future(); + + if (args[0].length === 1 && args[0][0].text === nextToken.text) { + return { + tokens: args[1], + numArgs: 0 + }; + } else { + return { + tokens: args[2], + numArgs: 0 + }; + } +}); // LaTeX's \@ifstar{#1}{#2} looks ahead to the next (unexpanded) symbol. +// If it is `*`, then it consumes the symbol, and the macro expands to #1; +// otherwise, the macro expands to #2 (without consuming the symbol). +// TeX source: \def\@ifstar#1{\@ifnextchar *{\@firstoftwo{#1}}} + +defineMacro("\\@ifstar", "\\@ifnextchar *{\\@firstoftwo{#1}}"); // LaTeX's \TextOrMath{#1}{#2} expands to #1 in text mode, #2 in math mode + +defineMacro("\\TextOrMath", function (context) { + const args = context.consumeArgs(2); + + if (context.mode === 'text') { + return { + tokens: args[0], + numArgs: 0 + }; + } else { + return { + tokens: args[1], + numArgs: 0 + }; + } +}); // Lookup table for parsing numbers in base 8 through 16 + +const digitToNumber = { + "0": 0, + "1": 1, + "2": 2, + "3": 3, + "4": 4, + "5": 5, + "6": 6, + "7": 7, + "8": 8, + "9": 9, + "a": 10, + "A": 10, + "b": 11, + "B": 11, + "c": 12, + "C": 12, + "d": 13, + "D": 13, + "e": 14, + "E": 14, + "f": 15, + "F": 15 +}; // TeX \char makes a literal character (catcode 12) using the following forms: +// (see The TeXBook, p. 43) +// \char123 -- decimal +// \char'123 -- octal +// \char"123 -- hex +// \char`x -- character that can be written (i.e. isn't active) +// \char`\x -- character that cannot be written (e.g. %) +// These all refer to characters from the font, so we turn them into special +// calls to a function \@char dealt with in the Parser. + +defineMacro("\\char", function (context) { + let token = context.popToken(); + let base; + let number = ''; + + if (token.text === "'") { + base = 8; + token = context.popToken(); + } else if (token.text === '"') { + base = 16; + token = context.popToken(); + } else if (token.text === "`") { + token = context.popToken(); + + if (token.text[0] === "\\") { + number = token.text.charCodeAt(1); + } else if (token.text === "EOF") { + throw new src_ParseError("\\char` missing argument"); + } else { + number = token.text.charCodeAt(0); + } + } else { + base = 10; + } + + if (base) { + // Parse a number in the given base, starting with first `token`. + number = digitToNumber[token.text]; + + if (number == null || number >= base) { + throw new src_ParseError("Invalid base-" + base + " digit " + token.text); + } + + let digit; + + while ((digit = digitToNumber[context.future().text]) != null && digit < base) { + number *= base; + number += digit; + context.popToken(); + } + } + + return "\\@char{" + number + "}"; +}); // \newcommand{\macro}[args]{definition} +// \renewcommand{\macro}[args]{definition} +// TODO: Optional arguments: \newcommand{\macro}[args][default]{definition} + +const newcommand = (context, existsOK, nonexistsOK, skipIfExists) => { + let arg = context.consumeArg().tokens; + + if (arg.length !== 1) { + throw new src_ParseError("\\newcommand's first argument must be a macro name"); + } + + const name = arg[0].text; + const exists = context.isDefined(name); + + if (exists && !existsOK) { + throw new src_ParseError("\\newcommand{" + name + "} attempting to redefine " + (name + "; use \\renewcommand")); + } + + if (!exists && !nonexistsOK) { + throw new src_ParseError("\\renewcommand{" + name + "} when command " + name + " " + "does not yet exist; use \\newcommand"); + } + + let numArgs = 0; + arg = context.consumeArg().tokens; + + if (arg.length === 1 && arg[0].text === "[") { + let argText = ''; + let token = context.expandNextToken(); + + while (token.text !== "]" && token.text !== "EOF") { + // TODO: Should properly expand arg, e.g., ignore {}s + argText += token.text; + token = context.expandNextToken(); + } + + if (!argText.match(/^\s*[0-9]+\s*$/)) { + throw new src_ParseError("Invalid number of arguments: " + argText); + } + + numArgs = parseInt(argText); + arg = context.consumeArg().tokens; + } + + if (!(exists && skipIfExists)) { + // Final arg is the expansion of the macro + context.macros.set(name, { + tokens: arg, + numArgs + }); + } + + return ''; +}; + +defineMacro("\\newcommand", context => newcommand(context, false, true, false)); +defineMacro("\\renewcommand", context => newcommand(context, true, false, false)); +defineMacro("\\providecommand", context => newcommand(context, true, true, true)); // terminal (console) tools + +defineMacro("\\message", context => { + const arg = context.consumeArgs(1)[0]; // eslint-disable-next-line no-console + + console.log(arg.reverse().map(token => token.text).join("")); + return ''; +}); +defineMacro("\\errmessage", context => { + const arg = context.consumeArgs(1)[0]; // eslint-disable-next-line no-console + + console.error(arg.reverse().map(token => token.text).join("")); + return ''; +}); +defineMacro("\\show", context => { + const tok = context.popToken(); + const name = tok.text; // eslint-disable-next-line no-console + + console.log(tok, context.macros.get(name), src_functions[name], src_symbols.math[name], src_symbols.text[name]); + return ''; +}); ////////////////////////////////////////////////////////////////////// +// Grouping +// \let\bgroup={ \let\egroup=} + +defineMacro("\\bgroup", "{"); +defineMacro("\\egroup", "}"); // Symbols from latex.ltx: +// \def~{\nobreakspace{}} +// \def\lq{`} +// \def\rq{'} +// \def \aa {\r a} +// \def \AA {\r A} + +defineMacro("~", "\\nobreakspace"); +defineMacro("\\lq", "`"); +defineMacro("\\rq", "'"); +defineMacro("\\aa", "\\r a"); +defineMacro("\\AA", "\\r A"); // Copyright (C) and registered (R) symbols. Use raw symbol in MathML. +// \DeclareTextCommandDefault{\textcopyright}{\textcircled{c}} +// \DeclareTextCommandDefault{\textregistered}{\textcircled{% +// \check@mathfonts\fontsize\sf@size\z@\math@fontsfalse\selectfont R}} +// \DeclareRobustCommand{\copyright}{% +// \ifmmode{\nfss@text{\textcopyright}}\else\textcopyright\fi} + +defineMacro("\\textcopyright", "\\html@mathml{\\textcircled{c}}{\\char`©}"); +defineMacro("\\copyright", "\\TextOrMath{\\textcopyright}{\\text{\\textcopyright}}"); +defineMacro("\\textregistered", "\\html@mathml{\\textcircled{\\scriptsize R}}{\\char`®}"); // Characters omitted from Unicode range 1D400–1D7FF + +defineMacro("\u212C", "\\mathscr{B}"); // script + +defineMacro("\u2130", "\\mathscr{E}"); +defineMacro("\u2131", "\\mathscr{F}"); +defineMacro("\u210B", "\\mathscr{H}"); +defineMacro("\u2110", "\\mathscr{I}"); +defineMacro("\u2112", "\\mathscr{L}"); +defineMacro("\u2133", "\\mathscr{M}"); +defineMacro("\u211B", "\\mathscr{R}"); +defineMacro("\u212D", "\\mathfrak{C}"); // Fraktur + +defineMacro("\u210C", "\\mathfrak{H}"); +defineMacro("\u2128", "\\mathfrak{Z}"); // Define \Bbbk with a macro that works in both HTML and MathML. + +defineMacro("\\Bbbk", "\\Bbb{k}"); // Unicode middle dot +// The KaTeX fonts do not contain U+00B7. Instead, \cdotp displays +// the dot at U+22C5 and gives it punct spacing. + +defineMacro("\u00b7", "\\cdotp"); // \llap and \rlap render their contents in text mode + +defineMacro("\\llap", "\\mathllap{\\textrm{#1}}"); +defineMacro("\\rlap", "\\mathrlap{\\textrm{#1}}"); +defineMacro("\\clap", "\\mathclap{\\textrm{#1}}"); // \mathstrut from the TeXbook, p 360 + +defineMacro("\\mathstrut", "\\vphantom{(}"); // \underbar from TeXbook p 353 + +defineMacro("\\underbar", "\\underline{\\text{#1}}"); // \not is defined by base/fontmath.ltx via +// \DeclareMathSymbol{\not}{\mathrel}{symbols}{"36} +// It's thus treated like a \mathrel, but defined by a symbol that has zero +// width but extends to the right. We use \rlap to get that spacing. +// For MathML we write U+0338 here. buildMathML.js will then do the overlay. + +defineMacro("\\not", '\\html@mathml{\\mathrel{\\mathrlap\\@not}}{\\char"338}'); // Negated symbols from base/fontmath.ltx: +// \def\neq{\not=} \let\ne=\neq +// \DeclareRobustCommand +// \notin{\mathrel{\m@th\mathpalette\c@ncel\in}} +// \def\c@ncel#1#2{\m@th\ooalign{$\hfil#1\mkern1mu/\hfil$\crcr$#1#2$}} + +defineMacro("\\neq", "\\html@mathml{\\mathrel{\\not=}}{\\mathrel{\\char`≠}}"); +defineMacro("\\ne", "\\neq"); +defineMacro("\u2260", "\\neq"); +defineMacro("\\notin", "\\html@mathml{\\mathrel{{\\in}\\mathllap{/\\mskip1mu}}}" + "{\\mathrel{\\char`∉}}"); +defineMacro("\u2209", "\\notin"); // Unicode stacked relations + +defineMacro("\u2258", "\\html@mathml{" + "\\mathrel{=\\kern{-1em}\\raisebox{0.4em}{$\\scriptsize\\frown$}}" + "}{\\mathrel{\\char`\u2258}}"); +defineMacro("\u2259", "\\html@mathml{\\stackrel{\\tiny\\wedge}{=}}{\\mathrel{\\char`\u2258}}"); +defineMacro("\u225A", "\\html@mathml{\\stackrel{\\tiny\\vee}{=}}{\\mathrel{\\char`\u225A}}"); +defineMacro("\u225B", "\\html@mathml{\\stackrel{\\scriptsize\\star}{=}}" + "{\\mathrel{\\char`\u225B}}"); +defineMacro("\u225D", "\\html@mathml{\\stackrel{\\tiny\\mathrm{def}}{=}}" + "{\\mathrel{\\char`\u225D}}"); +defineMacro("\u225E", "\\html@mathml{\\stackrel{\\tiny\\mathrm{m}}{=}}" + "{\\mathrel{\\char`\u225E}}"); +defineMacro("\u225F", "\\html@mathml{\\stackrel{\\tiny?}{=}}{\\mathrel{\\char`\u225F}}"); // Misc Unicode + +defineMacro("\u27C2", "\\perp"); +defineMacro("\u203C", "\\mathclose{!\\mkern-0.8mu!}"); +defineMacro("\u220C", "\\notni"); +defineMacro("\u231C", "\\ulcorner"); +defineMacro("\u231D", "\\urcorner"); +defineMacro("\u231E", "\\llcorner"); +defineMacro("\u231F", "\\lrcorner"); +defineMacro("\u00A9", "\\copyright"); +defineMacro("\u00AE", "\\textregistered"); +defineMacro("\uFE0F", "\\textregistered"); // The KaTeX fonts have corners at codepoints that don't match Unicode. +// For MathML purposes, use the Unicode code point. + +defineMacro("\\ulcorner", "\\html@mathml{\\@ulcorner}{\\mathop{\\char\"231c}}"); +defineMacro("\\urcorner", "\\html@mathml{\\@urcorner}{\\mathop{\\char\"231d}}"); +defineMacro("\\llcorner", "\\html@mathml{\\@llcorner}{\\mathop{\\char\"231e}}"); +defineMacro("\\lrcorner", "\\html@mathml{\\@lrcorner}{\\mathop{\\char\"231f}}"); ////////////////////////////////////////////////////////////////////// +// LaTeX_2ε +// \vdots{\vbox{\baselineskip4\p@ \lineskiplimit\z@ +// \kern6\p@\hbox{.}\hbox{.}\hbox{.}}} +// We'll call \varvdots, which gets a glyph from symbols.js. +// The zero-width rule gets us an equivalent to the vertical 6pt kern. + +defineMacro("\\vdots", "{\\varvdots\\rule{0pt}{15pt}}"); +defineMacro("\u22ee", "\\vdots"); ////////////////////////////////////////////////////////////////////// +// amsmath.sty +// http://mirrors.concertpass.com/tex-archive/macros/latex/required/amsmath/amsmath.pdf +// Italic Greek capital letters. AMS defines these with \DeclareMathSymbol, +// but they are equivalent to \mathit{\Letter}. + +defineMacro("\\varGamma", "\\mathit{\\Gamma}"); +defineMacro("\\varDelta", "\\mathit{\\Delta}"); +defineMacro("\\varTheta", "\\mathit{\\Theta}"); +defineMacro("\\varLambda", "\\mathit{\\Lambda}"); +defineMacro("\\varXi", "\\mathit{\\Xi}"); +defineMacro("\\varPi", "\\mathit{\\Pi}"); +defineMacro("\\varSigma", "\\mathit{\\Sigma}"); +defineMacro("\\varUpsilon", "\\mathit{\\Upsilon}"); +defineMacro("\\varPhi", "\\mathit{\\Phi}"); +defineMacro("\\varPsi", "\\mathit{\\Psi}"); +defineMacro("\\varOmega", "\\mathit{\\Omega}"); //\newcommand{\substack}[1]{\subarray{c}#1\endsubarray} + +defineMacro("\\substack", "\\begin{subarray}{c}#1\\end{subarray}"); // \renewcommand{\colon}{\nobreak\mskip2mu\mathpunct{}\nonscript +// \mkern-\thinmuskip{:}\mskip6muplus1mu\relax} + +defineMacro("\\colon", "\\nobreak\\mskip2mu\\mathpunct{}" + "\\mathchoice{\\mkern-3mu}{\\mkern-3mu}{}{}{:}\\mskip6mu\\relax"); // \newcommand{\boxed}[1]{\fbox{\m@th$\displaystyle#1$}} + +defineMacro("\\boxed", "\\fbox{$\\displaystyle{#1}$}"); // \def\iff{\DOTSB\;\Longleftrightarrow\;} +// \def\implies{\DOTSB\;\Longrightarrow\;} +// \def\impliedby{\DOTSB\;\Longleftarrow\;} + +defineMacro("\\iff", "\\DOTSB\\;\\Longleftrightarrow\\;"); +defineMacro("\\implies", "\\DOTSB\\;\\Longrightarrow\\;"); +defineMacro("\\impliedby", "\\DOTSB\\;\\Longleftarrow\\;"); // \def\dddot#1{{\mathop{#1}\limits^{\vbox to-1.4\ex@{\kern-\tw@\ex@ +// \hbox{\normalfont ...}\vss}}}} +// We use \overset which avoids the vertical shift of \mathop. + +defineMacro("\\dddot", "{\\overset{\\raisebox{-0.1ex}{\\normalsize ...}}{#1}}"); +defineMacro("\\ddddot", "{\\overset{\\raisebox{-0.1ex}{\\normalsize ....}}{#1}}"); // AMSMath's automatic \dots, based on \mdots@@ macro. + +const dotsByToken = { + ',': '\\dotsc', + '\\not': '\\dotsb', + // \keybin@ checks for the following: + '+': '\\dotsb', + '=': '\\dotsb', + '<': '\\dotsb', + '>': '\\dotsb', + '-': '\\dotsb', + '*': '\\dotsb', + ':': '\\dotsb', + // Symbols whose definition starts with \DOTSB: + '\\DOTSB': '\\dotsb', + '\\coprod': '\\dotsb', + '\\bigvee': '\\dotsb', + '\\bigwedge': '\\dotsb', + '\\biguplus': '\\dotsb', + '\\bigcap': '\\dotsb', + '\\bigcup': '\\dotsb', + '\\prod': '\\dotsb', + '\\sum': '\\dotsb', + '\\bigotimes': '\\dotsb', + '\\bigoplus': '\\dotsb', + '\\bigodot': '\\dotsb', + '\\bigsqcup': '\\dotsb', + '\\And': '\\dotsb', + '\\longrightarrow': '\\dotsb', + '\\Longrightarrow': '\\dotsb', + '\\longleftarrow': '\\dotsb', + '\\Longleftarrow': '\\dotsb', + '\\longleftrightarrow': '\\dotsb', + '\\Longleftrightarrow': '\\dotsb', + '\\mapsto': '\\dotsb', + '\\longmapsto': '\\dotsb', + '\\hookrightarrow': '\\dotsb', + '\\doteq': '\\dotsb', + // Symbols whose definition starts with \mathbin: + '\\mathbin': '\\dotsb', + // Symbols whose definition starts with \mathrel: + '\\mathrel': '\\dotsb', + '\\relbar': '\\dotsb', + '\\Relbar': '\\dotsb', + '\\xrightarrow': '\\dotsb', + '\\xleftarrow': '\\dotsb', + // Symbols whose definition starts with \DOTSI: + '\\DOTSI': '\\dotsi', + '\\int': '\\dotsi', + '\\oint': '\\dotsi', + '\\iint': '\\dotsi', + '\\iiint': '\\dotsi', + '\\iiiint': '\\dotsi', + '\\idotsint': '\\dotsi', + // Symbols whose definition starts with \DOTSX: + '\\DOTSX': '\\dotsx' +}; +defineMacro("\\dots", function (context) { + // TODO: If used in text mode, should expand to \textellipsis. + // However, in KaTeX, \textellipsis and \ldots behave the same + // (in text mode), and it's unlikely we'd see any of the math commands + // that affect the behavior of \dots when in text mode. So fine for now + // (until we support \ifmmode ... \else ... \fi). + let thedots = '\\dotso'; + const next = context.expandAfterFuture().text; + + if (next in dotsByToken) { + thedots = dotsByToken[next]; + } else if (next.slice(0, 4) === '\\not') { + thedots = '\\dotsb'; + } else if (next in src_symbols.math) { + if (utils.contains(['bin', 'rel'], src_symbols.math[next].group)) { + thedots = '\\dotsb'; + } + } + + return thedots; +}); +const spaceAfterDots = { + // \rightdelim@ checks for the following: + ')': true, + ']': true, + '\\rbrack': true, + '\\}': true, + '\\rbrace': true, + '\\rangle': true, + '\\rceil': true, + '\\rfloor': true, + '\\rgroup': true, + '\\rmoustache': true, + '\\right': true, + '\\bigr': true, + '\\biggr': true, + '\\Bigr': true, + '\\Biggr': true, + // \extra@ also tests for the following: + '$': true, + // \extrap@ checks for the following: + ';': true, + '.': true, + ',': true +}; +defineMacro("\\dotso", function (context) { + const next = context.future().text; + + if (next in spaceAfterDots) { + return "\\ldots\\,"; + } else { + return "\\ldots"; + } +}); +defineMacro("\\dotsc", function (context) { + const next = context.future().text; // \dotsc uses \extra@ but not \extrap@, instead specially checking for + // ';' and '.', but doesn't check for ','. + + if (next in spaceAfterDots && next !== ',') { + return "\\ldots\\,"; + } else { + return "\\ldots"; + } +}); +defineMacro("\\cdots", function (context) { + const next = context.future().text; + + if (next in spaceAfterDots) { + return "\\@cdots\\,"; + } else { + return "\\@cdots"; + } +}); +defineMacro("\\dotsb", "\\cdots"); +defineMacro("\\dotsm", "\\cdots"); +defineMacro("\\dotsi", "\\!\\cdots"); // amsmath doesn't actually define \dotsx, but \dots followed by a macro +// starting with \DOTSX implies \dotso, and then \extra@ detects this case +// and forces the added `\,`. + +defineMacro("\\dotsx", "\\ldots\\,"); // \let\DOTSI\relax +// \let\DOTSB\relax +// \let\DOTSX\relax + +defineMacro("\\DOTSI", "\\relax"); +defineMacro("\\DOTSB", "\\relax"); +defineMacro("\\DOTSX", "\\relax"); // Spacing, based on amsmath.sty's override of LaTeX defaults +// \DeclareRobustCommand{\tmspace}[3]{% +// \ifmmode\mskip#1#2\else\kern#1#3\fi\relax} + +defineMacro("\\tmspace", "\\TextOrMath{\\kern#1#3}{\\mskip#1#2}\\relax"); // \renewcommand{\,}{\tmspace+\thinmuskip{.1667em}} +// TODO: math mode should use \thinmuskip + +defineMacro("\\,", "\\tmspace+{3mu}{.1667em}"); // \let\thinspace\, + +defineMacro("\\thinspace", "\\,"); // \def\>{\mskip\medmuskip} +// \renewcommand{\:}{\tmspace+\medmuskip{.2222em}} +// TODO: \> and math mode of \: should use \medmuskip = 4mu plus 2mu minus 4mu + +defineMacro("\\>", "\\mskip{4mu}"); +defineMacro("\\:", "\\tmspace+{4mu}{.2222em}"); // \let\medspace\: + +defineMacro("\\medspace", "\\:"); // \renewcommand{\;}{\tmspace+\thickmuskip{.2777em}} +// TODO: math mode should use \thickmuskip = 5mu plus 5mu + +defineMacro("\\;", "\\tmspace+{5mu}{.2777em}"); // \let\thickspace\; + +defineMacro("\\thickspace", "\\;"); // \renewcommand{\!}{\tmspace-\thinmuskip{.1667em}} +// TODO: math mode should use \thinmuskip + +defineMacro("\\!", "\\tmspace-{3mu}{.1667em}"); // \let\negthinspace\! + +defineMacro("\\negthinspace", "\\!"); // \newcommand{\negmedspace}{\tmspace-\medmuskip{.2222em}} +// TODO: math mode should use \medmuskip + +defineMacro("\\negmedspace", "\\tmspace-{4mu}{.2222em}"); // \newcommand{\negthickspace}{\tmspace-\thickmuskip{.2777em}} +// TODO: math mode should use \thickmuskip + +defineMacro("\\negthickspace", "\\tmspace-{5mu}{.277em}"); // \def\enspace{\kern.5em } + +defineMacro("\\enspace", "\\kern.5em "); // \def\enskip{\hskip.5em\relax} + +defineMacro("\\enskip", "\\hskip.5em\\relax"); // \def\quad{\hskip1em\relax} + +defineMacro("\\quad", "\\hskip1em\\relax"); // \def\qquad{\hskip2em\relax} + +defineMacro("\\qquad", "\\hskip2em\\relax"); // \tag@in@display form of \tag + +defineMacro("\\tag", "\\@ifstar\\tag@literal\\tag@paren"); +defineMacro("\\tag@paren", "\\tag@literal{({#1})}"); +defineMacro("\\tag@literal", context => { + if (context.macros.get("\\df@tag")) { + throw new src_ParseError("Multiple \\tag"); + } + + return "\\gdef\\df@tag{\\text{#1}}"; +}); // \renewcommand{\bmod}{\nonscript\mskip-\medmuskip\mkern5mu\mathbin +// {\operator@font mod}\penalty900 +// \mkern5mu\nonscript\mskip-\medmuskip} +// \newcommand{\pod}[1]{\allowbreak +// \if@display\mkern18mu\else\mkern8mu\fi(#1)} +// \renewcommand{\pmod}[1]{\pod{{\operator@font mod}\mkern6mu#1}} +// \newcommand{\mod}[1]{\allowbreak\if@display\mkern18mu +// \else\mkern12mu\fi{\operator@font mod}\,\,#1} +// TODO: math mode should use \medmuskip = 4mu plus 2mu minus 4mu + +defineMacro("\\bmod", "\\mathchoice{\\mskip1mu}{\\mskip1mu}{\\mskip5mu}{\\mskip5mu}" + "\\mathbin{\\rm mod}" + "\\mathchoice{\\mskip1mu}{\\mskip1mu}{\\mskip5mu}{\\mskip5mu}"); +defineMacro("\\pod", "\\allowbreak" + "\\mathchoice{\\mkern18mu}{\\mkern8mu}{\\mkern8mu}{\\mkern8mu}(#1)"); +defineMacro("\\pmod", "\\pod{{\\rm mod}\\mkern6mu#1}"); +defineMacro("\\mod", "\\allowbreak" + "\\mathchoice{\\mkern18mu}{\\mkern12mu}{\\mkern12mu}{\\mkern12mu}" + "{\\rm mod}\\,\\,#1"); ////////////////////////////////////////////////////////////////////// +// LaTeX source2e +// \expandafter\let\expandafter\@normalcr +// \csname\expandafter\@gobble\string\\ \endcsname +// \DeclareRobustCommand\newline{\@normalcr\relax} + +defineMacro("\\newline", "\\\\\\relax"); // \def\TeX{T\kern-.1667em\lower.5ex\hbox{E}\kern-.125emX\@} +// TODO: Doesn't normally work in math mode because \@ fails. KaTeX doesn't +// support \@ yet, so that's omitted, and we add \text so that the result +// doesn't look funny in math mode. + +defineMacro("\\TeX", "\\textrm{\\html@mathml{" + "T\\kern-.1667em\\raisebox{-.5ex}{E}\\kern-.125emX" + "}{TeX}}"); // \DeclareRobustCommand{\LaTeX}{L\kern-.36em% +// {\sbox\z@ T% +// \vbox to\ht\z@{\hbox{\check@mathfonts +// \fontsize\sf@size\z@ +// \math@fontsfalse\selectfont +// A}% +// \vss}% +// }% +// \kern-.15em% +// \TeX} +// This code aligns the top of the A with the T (from the perspective of TeX's +// boxes, though visually the A appears to extend above slightly). +// We compute the corresponding \raisebox when A is rendered in \normalsize +// \scriptstyle, which has a scale factor of 0.7 (see Options.js). + +const latexRaiseA = makeEm(fontMetricsData['Main-Regular']["T".charCodeAt(0)][1] - 0.7 * fontMetricsData['Main-Regular']["A".charCodeAt(0)][1]); +defineMacro("\\LaTeX", "\\textrm{\\html@mathml{" + ("L\\kern-.36em\\raisebox{" + latexRaiseA + "}{\\scriptstyle A}") + "\\kern-.15em\\TeX}{LaTeX}}"); // New KaTeX logo based on tweaking LaTeX logo + +defineMacro("\\KaTeX", "\\textrm{\\html@mathml{" + ("K\\kern-.17em\\raisebox{" + latexRaiseA + "}{\\scriptstyle A}") + "\\kern-.15em\\TeX}{KaTeX}}"); // \DeclareRobustCommand\hspace{\@ifstar\@hspacer\@hspace} +// \def\@hspace#1{\hskip #1\relax} +// \def\@hspacer#1{\vrule \@width\z@\nobreak +// \hskip #1\hskip \z@skip} + +defineMacro("\\hspace", "\\@ifstar\\@hspacer\\@hspace"); +defineMacro("\\@hspace", "\\hskip #1\\relax"); +defineMacro("\\@hspacer", "\\rule{0pt}{0pt}\\hskip #1\\relax"); ////////////////////////////////////////////////////////////////////// +// mathtools.sty +//\providecommand\ordinarycolon{:} + +defineMacro("\\ordinarycolon", ":"); //\def\vcentcolon{\mathrel{\mathop\ordinarycolon}} +//TODO(edemaine): Not yet centered. Fix via \raisebox or #726 + +defineMacro("\\vcentcolon", "\\mathrel{\\mathop\\ordinarycolon}"); // \providecommand*\dblcolon{\vcentcolon\mathrel{\mkern-.9mu}\vcentcolon} + +defineMacro("\\dblcolon", "\\html@mathml{" + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-.9mu}\\vcentcolon}}" + "{\\mathop{\\char\"2237}}"); // \providecommand*\coloneqq{\vcentcolon\mathrel{\mkern-1.2mu}=} + +defineMacro("\\coloneqq", "\\html@mathml{" + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}=}}" + "{\\mathop{\\char\"2254}}"); // ≔ +// \providecommand*\Coloneqq{\dblcolon\mathrel{\mkern-1.2mu}=} + +defineMacro("\\Coloneqq", "\\html@mathml{" + "\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}=}}" + "{\\mathop{\\char\"2237\\char\"3d}}"); // \providecommand*\coloneq{\vcentcolon\mathrel{\mkern-1.2mu}\mathrel{-}} + +defineMacro("\\coloneq", "\\html@mathml{" + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}\\mathrel{-}}}" + "{\\mathop{\\char\"3a\\char\"2212}}"); // \providecommand*\Coloneq{\dblcolon\mathrel{\mkern-1.2mu}\mathrel{-}} + +defineMacro("\\Coloneq", "\\html@mathml{" + "\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}\\mathrel{-}}}" + "{\\mathop{\\char\"2237\\char\"2212}}"); // \providecommand*\eqqcolon{=\mathrel{\mkern-1.2mu}\vcentcolon} + +defineMacro("\\eqqcolon", "\\html@mathml{" + "\\mathrel{=\\mathrel{\\mkern-1.2mu}\\vcentcolon}}" + "{\\mathop{\\char\"2255}}"); // ≕ +// \providecommand*\Eqqcolon{=\mathrel{\mkern-1.2mu}\dblcolon} + +defineMacro("\\Eqqcolon", "\\html@mathml{" + "\\mathrel{=\\mathrel{\\mkern-1.2mu}\\dblcolon}}" + "{\\mathop{\\char\"3d\\char\"2237}}"); // \providecommand*\eqcolon{\mathrel{-}\mathrel{\mkern-1.2mu}\vcentcolon} + +defineMacro("\\eqcolon", "\\html@mathml{" + "\\mathrel{\\mathrel{-}\\mathrel{\\mkern-1.2mu}\\vcentcolon}}" + "{\\mathop{\\char\"2239}}"); // \providecommand*\Eqcolon{\mathrel{-}\mathrel{\mkern-1.2mu}\dblcolon} + +defineMacro("\\Eqcolon", "\\html@mathml{" + "\\mathrel{\\mathrel{-}\\mathrel{\\mkern-1.2mu}\\dblcolon}}" + "{\\mathop{\\char\"2212\\char\"2237}}"); // \providecommand*\colonapprox{\vcentcolon\mathrel{\mkern-1.2mu}\approx} + +defineMacro("\\colonapprox", "\\html@mathml{" + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}\\approx}}" + "{\\mathop{\\char\"3a\\char\"2248}}"); // \providecommand*\Colonapprox{\dblcolon\mathrel{\mkern-1.2mu}\approx} + +defineMacro("\\Colonapprox", "\\html@mathml{" + "\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}\\approx}}" + "{\\mathop{\\char\"2237\\char\"2248}}"); // \providecommand*\colonsim{\vcentcolon\mathrel{\mkern-1.2mu}\sim} + +defineMacro("\\colonsim", "\\html@mathml{" + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}\\sim}}" + "{\\mathop{\\char\"3a\\char\"223c}}"); // \providecommand*\Colonsim{\dblcolon\mathrel{\mkern-1.2mu}\sim} + +defineMacro("\\Colonsim", "\\html@mathml{" + "\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}\\sim}}" + "{\\mathop{\\char\"2237\\char\"223c}}"); // Some Unicode characters are implemented with macros to mathtools functions. + +defineMacro("\u2237", "\\dblcolon"); // :: + +defineMacro("\u2239", "\\eqcolon"); // -: + +defineMacro("\u2254", "\\coloneqq"); // := + +defineMacro("\u2255", "\\eqqcolon"); // =: + +defineMacro("\u2A74", "\\Coloneqq"); // ::= +////////////////////////////////////////////////////////////////////// +// colonequals.sty +// Alternate names for mathtools's macros: + +defineMacro("\\ratio", "\\vcentcolon"); +defineMacro("\\coloncolon", "\\dblcolon"); +defineMacro("\\colonequals", "\\coloneqq"); +defineMacro("\\coloncolonequals", "\\Coloneqq"); +defineMacro("\\equalscolon", "\\eqqcolon"); +defineMacro("\\equalscoloncolon", "\\Eqqcolon"); +defineMacro("\\colonminus", "\\coloneq"); +defineMacro("\\coloncolonminus", "\\Coloneq"); +defineMacro("\\minuscolon", "\\eqcolon"); +defineMacro("\\minuscoloncolon", "\\Eqcolon"); // \colonapprox name is same in mathtools and colonequals. + +defineMacro("\\coloncolonapprox", "\\Colonapprox"); // \colonsim name is same in mathtools and colonequals. + +defineMacro("\\coloncolonsim", "\\Colonsim"); // Additional macros, implemented by analogy with mathtools definitions: + +defineMacro("\\simcolon", "\\mathrel{\\sim\\mathrel{\\mkern-1.2mu}\\vcentcolon}"); +defineMacro("\\simcoloncolon", "\\mathrel{\\sim\\mathrel{\\mkern-1.2mu}\\dblcolon}"); +defineMacro("\\approxcolon", "\\mathrel{\\approx\\mathrel{\\mkern-1.2mu}\\vcentcolon}"); +defineMacro("\\approxcoloncolon", "\\mathrel{\\approx\\mathrel{\\mkern-1.2mu}\\dblcolon}"); // Present in newtxmath, pxfonts and txfonts + +defineMacro("\\notni", "\\html@mathml{\\not\\ni}{\\mathrel{\\char`\u220C}}"); +defineMacro("\\limsup", "\\DOTSB\\operatorname*{lim\\,sup}"); +defineMacro("\\liminf", "\\DOTSB\\operatorname*{lim\\,inf}"); ////////////////////////////////////////////////////////////////////// +// From amsopn.sty + +defineMacro("\\injlim", "\\DOTSB\\operatorname*{inj\\,lim}"); +defineMacro("\\projlim", "\\DOTSB\\operatorname*{proj\\,lim}"); +defineMacro("\\varlimsup", "\\DOTSB\\operatorname*{\\overline{lim}}"); +defineMacro("\\varliminf", "\\DOTSB\\operatorname*{\\underline{lim}}"); +defineMacro("\\varinjlim", "\\DOTSB\\operatorname*{\\underrightarrow{lim}}"); +defineMacro("\\varprojlim", "\\DOTSB\\operatorname*{\\underleftarrow{lim}}"); ////////////////////////////////////////////////////////////////////// +// MathML alternates for KaTeX glyphs in the Unicode private area + +defineMacro("\\gvertneqq", "\\html@mathml{\\@gvertneqq}{\u2269}"); +defineMacro("\\lvertneqq", "\\html@mathml{\\@lvertneqq}{\u2268}"); +defineMacro("\\ngeqq", "\\html@mathml{\\@ngeqq}{\u2271}"); +defineMacro("\\ngeqslant", "\\html@mathml{\\@ngeqslant}{\u2271}"); +defineMacro("\\nleqq", "\\html@mathml{\\@nleqq}{\u2270}"); +defineMacro("\\nleqslant", "\\html@mathml{\\@nleqslant}{\u2270}"); +defineMacro("\\nshortmid", "\\html@mathml{\\@nshortmid}{∤}"); +defineMacro("\\nshortparallel", "\\html@mathml{\\@nshortparallel}{∦}"); +defineMacro("\\nsubseteqq", "\\html@mathml{\\@nsubseteqq}{\u2288}"); +defineMacro("\\nsupseteqq", "\\html@mathml{\\@nsupseteqq}{\u2289}"); +defineMacro("\\varsubsetneq", "\\html@mathml{\\@varsubsetneq}{⊊}"); +defineMacro("\\varsubsetneqq", "\\html@mathml{\\@varsubsetneqq}{⫋}"); +defineMacro("\\varsupsetneq", "\\html@mathml{\\@varsupsetneq}{⊋}"); +defineMacro("\\varsupsetneqq", "\\html@mathml{\\@varsupsetneqq}{⫌}"); +defineMacro("\\imath", "\\html@mathml{\\@imath}{\u0131}"); +defineMacro("\\jmath", "\\html@mathml{\\@jmath}{\u0237}"); ////////////////////////////////////////////////////////////////////// +// stmaryrd and semantic +// The stmaryrd and semantic packages render the next four items by calling a +// glyph. Those glyphs do not exist in the KaTeX fonts. Hence the macros. + +defineMacro("\\llbracket", "\\html@mathml{" + "\\mathopen{[\\mkern-3.2mu[}}" + "{\\mathopen{\\char`\u27e6}}"); +defineMacro("\\rrbracket", "\\html@mathml{" + "\\mathclose{]\\mkern-3.2mu]}}" + "{\\mathclose{\\char`\u27e7}}"); +defineMacro("\u27e6", "\\llbracket"); // blackboard bold [ + +defineMacro("\u27e7", "\\rrbracket"); // blackboard bold ] + +defineMacro("\\lBrace", "\\html@mathml{" + "\\mathopen{\\{\\mkern-3.2mu[}}" + "{\\mathopen{\\char`\u2983}}"); +defineMacro("\\rBrace", "\\html@mathml{" + "\\mathclose{]\\mkern-3.2mu\\}}}" + "{\\mathclose{\\char`\u2984}}"); +defineMacro("\u2983", "\\lBrace"); // blackboard bold { + +defineMacro("\u2984", "\\rBrace"); // blackboard bold } +// TODO: Create variable sized versions of the last two items. I believe that +// will require new font glyphs. +// The stmaryrd function `\minuso` provides a "Plimsoll" symbol that +// superimposes the characters \circ and \mathminus. Used in chemistry. + +defineMacro("\\minuso", "\\mathbin{\\html@mathml{" + "{\\mathrlap{\\mathchoice{\\kern{0.145em}}{\\kern{0.145em}}" + "{\\kern{0.1015em}}{\\kern{0.0725em}}\\circ}{-}}}" + "{\\char`⦵}}"); +defineMacro("⦵", "\\minuso"); ////////////////////////////////////////////////////////////////////// +// texvc.sty +// The texvc package contains macros available in mediawiki pages. +// We omit the functions deprecated at +// https://en.wikipedia.org/wiki/Help:Displaying_a_formula#Deprecated_syntax +// We also omit texvc's \O, which conflicts with \text{\O} + +defineMacro("\\darr", "\\downarrow"); +defineMacro("\\dArr", "\\Downarrow"); +defineMacro("\\Darr", "\\Downarrow"); +defineMacro("\\lang", "\\langle"); +defineMacro("\\rang", "\\rangle"); +defineMacro("\\uarr", "\\uparrow"); +defineMacro("\\uArr", "\\Uparrow"); +defineMacro("\\Uarr", "\\Uparrow"); +defineMacro("\\N", "\\mathbb{N}"); +defineMacro("\\R", "\\mathbb{R}"); +defineMacro("\\Z", "\\mathbb{Z}"); +defineMacro("\\alef", "\\aleph"); +defineMacro("\\alefsym", "\\aleph"); +defineMacro("\\Alpha", "\\mathrm{A}"); +defineMacro("\\Beta", "\\mathrm{B}"); +defineMacro("\\bull", "\\bullet"); +defineMacro("\\Chi", "\\mathrm{X}"); +defineMacro("\\clubs", "\\clubsuit"); +defineMacro("\\cnums", "\\mathbb{C}"); +defineMacro("\\Complex", "\\mathbb{C}"); +defineMacro("\\Dagger", "\\ddagger"); +defineMacro("\\diamonds", "\\diamondsuit"); +defineMacro("\\empty", "\\emptyset"); +defineMacro("\\Epsilon", "\\mathrm{E}"); +defineMacro("\\Eta", "\\mathrm{H}"); +defineMacro("\\exist", "\\exists"); +defineMacro("\\harr", "\\leftrightarrow"); +defineMacro("\\hArr", "\\Leftrightarrow"); +defineMacro("\\Harr", "\\Leftrightarrow"); +defineMacro("\\hearts", "\\heartsuit"); +defineMacro("\\image", "\\Im"); +defineMacro("\\infin", "\\infty"); +defineMacro("\\Iota", "\\mathrm{I}"); +defineMacro("\\isin", "\\in"); +defineMacro("\\Kappa", "\\mathrm{K}"); +defineMacro("\\larr", "\\leftarrow"); +defineMacro("\\lArr", "\\Leftarrow"); +defineMacro("\\Larr", "\\Leftarrow"); +defineMacro("\\lrarr", "\\leftrightarrow"); +defineMacro("\\lrArr", "\\Leftrightarrow"); +defineMacro("\\Lrarr", "\\Leftrightarrow"); +defineMacro("\\Mu", "\\mathrm{M}"); +defineMacro("\\natnums", "\\mathbb{N}"); +defineMacro("\\Nu", "\\mathrm{N}"); +defineMacro("\\Omicron", "\\mathrm{O}"); +defineMacro("\\plusmn", "\\pm"); +defineMacro("\\rarr", "\\rightarrow"); +defineMacro("\\rArr", "\\Rightarrow"); +defineMacro("\\Rarr", "\\Rightarrow"); +defineMacro("\\real", "\\Re"); +defineMacro("\\reals", "\\mathbb{R}"); +defineMacro("\\Reals", "\\mathbb{R}"); +defineMacro("\\Rho", "\\mathrm{P}"); +defineMacro("\\sdot", "\\cdot"); +defineMacro("\\sect", "\\S"); +defineMacro("\\spades", "\\spadesuit"); +defineMacro("\\sub", "\\subset"); +defineMacro("\\sube", "\\subseteq"); +defineMacro("\\supe", "\\supseteq"); +defineMacro("\\Tau", "\\mathrm{T}"); +defineMacro("\\thetasym", "\\vartheta"); // TODO: defineMacro("\\varcoppa", "\\\mbox{\\coppa}"); + +defineMacro("\\weierp", "\\wp"); +defineMacro("\\Zeta", "\\mathrm{Z}"); ////////////////////////////////////////////////////////////////////// +// statmath.sty +// https://ctan.math.illinois.edu/macros/latex/contrib/statmath/statmath.pdf + +defineMacro("\\argmin", "\\DOTSB\\operatorname*{arg\\,min}"); +defineMacro("\\argmax", "\\DOTSB\\operatorname*{arg\\,max}"); +defineMacro("\\plim", "\\DOTSB\\mathop{\\operatorname{plim}}\\limits"); ////////////////////////////////////////////////////////////////////// +// braket.sty +// http://ctan.math.washington.edu/tex-archive/macros/latex/contrib/braket/braket.pdf + +defineMacro("\\bra", "\\mathinner{\\langle{#1}|}"); +defineMacro("\\ket", "\\mathinner{|{#1}\\rangle}"); +defineMacro("\\braket", "\\mathinner{\\langle{#1}\\rangle}"); +defineMacro("\\Bra", "\\left\\langle#1\\right|"); +defineMacro("\\Ket", "\\left|#1\\right\\rangle"); + +const braketHelper = one => context => { + const left = context.consumeArg().tokens; + const middle = context.consumeArg().tokens; + const middleDouble = context.consumeArg().tokens; + const right = context.consumeArg().tokens; + const oldMiddle = context.macros.get("|"); + const oldMiddleDouble = context.macros.get("\\|"); + context.macros.beginGroup(); + + const midMacro = double => context => { + if (one) { + // Only modify the first instance of | or \| + context.macros.set("|", oldMiddle); + + if (middleDouble.length) { + context.macros.set("\\|", oldMiddleDouble); + } + } + + let doubled = double; + + if (!double && middleDouble.length) { + // Mimic \@ifnextchar + const nextToken = context.future(); + + if (nextToken.text === "|") { + context.popToken(); + doubled = true; + } + } + + return { + tokens: doubled ? middleDouble : middle, + numArgs: 0 + }; + }; + + context.macros.set("|", midMacro(false)); + + if (middleDouble.length) { + context.macros.set("\\|", midMacro(true)); + } + + const arg = context.consumeArg().tokens; + const expanded = context.expandTokens([...right, ...arg, ...left // reversed + ]); + context.macros.endGroup(); + return { + tokens: expanded.reverse(), + numArgs: 0 + }; +}; + +defineMacro("\\bra@ket", braketHelper(false)); +defineMacro("\\bra@set", braketHelper(true)); +defineMacro("\\Braket", "\\bra@ket{\\left\\langle}" + "{\\,\\middle\\vert\\,}{\\,\\middle\\vert\\,}{\\right\\rangle}"); +defineMacro("\\Set", "\\bra@set{\\left\\{\\:}" + "{\\;\\middle\\vert\\;}{\\;\\middle\\Vert\\;}{\\:\\right\\}}"); +defineMacro("\\set", "\\bra@set{\\{\\,}{\\mid}{}{\\,\\}}"); // has no support for special || or \| +////////////////////////////////////////////////////////////////////// +// actuarialangle.dtx + +defineMacro("\\angln", "{\\angl n}"); // Custom Khan Academy colors, should be moved to an optional package + +defineMacro("\\blue", "\\textcolor{##6495ed}{#1}"); +defineMacro("\\orange", "\\textcolor{##ffa500}{#1}"); +defineMacro("\\pink", "\\textcolor{##ff00af}{#1}"); +defineMacro("\\red", "\\textcolor{##df0030}{#1}"); +defineMacro("\\green", "\\textcolor{##28ae7b}{#1}"); +defineMacro("\\gray", "\\textcolor{gray}{#1}"); +defineMacro("\\purple", "\\textcolor{##9d38bd}{#1}"); +defineMacro("\\blueA", "\\textcolor{##ccfaff}{#1}"); +defineMacro("\\blueB", "\\textcolor{##80f6ff}{#1}"); +defineMacro("\\blueC", "\\textcolor{##63d9ea}{#1}"); +defineMacro("\\blueD", "\\textcolor{##11accd}{#1}"); +defineMacro("\\blueE", "\\textcolor{##0c7f99}{#1}"); +defineMacro("\\tealA", "\\textcolor{##94fff5}{#1}"); +defineMacro("\\tealB", "\\textcolor{##26edd5}{#1}"); +defineMacro("\\tealC", "\\textcolor{##01d1c1}{#1}"); +defineMacro("\\tealD", "\\textcolor{##01a995}{#1}"); +defineMacro("\\tealE", "\\textcolor{##208170}{#1}"); +defineMacro("\\greenA", "\\textcolor{##b6ffb0}{#1}"); +defineMacro("\\greenB", "\\textcolor{##8af281}{#1}"); +defineMacro("\\greenC", "\\textcolor{##74cf70}{#1}"); +defineMacro("\\greenD", "\\textcolor{##1fab54}{#1}"); +defineMacro("\\greenE", "\\textcolor{##0d923f}{#1}"); +defineMacro("\\goldA", "\\textcolor{##ffd0a9}{#1}"); +defineMacro("\\goldB", "\\textcolor{##ffbb71}{#1}"); +defineMacro("\\goldC", "\\textcolor{##ff9c39}{#1}"); +defineMacro("\\goldD", "\\textcolor{##e07d10}{#1}"); +defineMacro("\\goldE", "\\textcolor{##a75a05}{#1}"); +defineMacro("\\redA", "\\textcolor{##fca9a9}{#1}"); +defineMacro("\\redB", "\\textcolor{##ff8482}{#1}"); +defineMacro("\\redC", "\\textcolor{##f9685d}{#1}"); +defineMacro("\\redD", "\\textcolor{##e84d39}{#1}"); +defineMacro("\\redE", "\\textcolor{##bc2612}{#1}"); +defineMacro("\\maroonA", "\\textcolor{##ffbde0}{#1}"); +defineMacro("\\maroonB", "\\textcolor{##ff92c6}{#1}"); +defineMacro("\\maroonC", "\\textcolor{##ed5fa6}{#1}"); +defineMacro("\\maroonD", "\\textcolor{##ca337c}{#1}"); +defineMacro("\\maroonE", "\\textcolor{##9e034e}{#1}"); +defineMacro("\\purpleA", "\\textcolor{##ddd7ff}{#1}"); +defineMacro("\\purpleB", "\\textcolor{##c6b9fc}{#1}"); +defineMacro("\\purpleC", "\\textcolor{##aa87ff}{#1}"); +defineMacro("\\purpleD", "\\textcolor{##7854ab}{#1}"); +defineMacro("\\purpleE", "\\textcolor{##543b78}{#1}"); +defineMacro("\\mintA", "\\textcolor{##f5f9e8}{#1}"); +defineMacro("\\mintB", "\\textcolor{##edf2df}{#1}"); +defineMacro("\\mintC", "\\textcolor{##e0e5cc}{#1}"); +defineMacro("\\grayA", "\\textcolor{##f6f7f7}{#1}"); +defineMacro("\\grayB", "\\textcolor{##f0f1f2}{#1}"); +defineMacro("\\grayC", "\\textcolor{##e3e5e6}{#1}"); +defineMacro("\\grayD", "\\textcolor{##d6d8da}{#1}"); +defineMacro("\\grayE", "\\textcolor{##babec2}{#1}"); +defineMacro("\\grayF", "\\textcolor{##888d93}{#1}"); +defineMacro("\\grayG", "\\textcolor{##626569}{#1}"); +defineMacro("\\grayH", "\\textcolor{##3b3e40}{#1}"); +defineMacro("\\grayI", "\\textcolor{##21242c}{#1}"); +defineMacro("\\kaBlue", "\\textcolor{##314453}{#1}"); +defineMacro("\\kaGreen", "\\textcolor{##71B307}{#1}"); +;// CONCATENATED MODULE: ./src/MacroExpander.js +/** + * This file contains the “gullet” where macros are expanded + * until only non-macro tokens remain. + */ + + + + + + + +// List of commands that act like macros but aren't defined as a macro, +// function, or symbol. Used in `isDefined`. +const implicitCommands = { + "^": true, + // Parser.js + "_": true, + // Parser.js + "\\limits": true, + // Parser.js + "\\nolimits": true // Parser.js + +}; +class MacroExpander { + constructor(input, settings, mode) { + this.settings = void 0; + this.expansionCount = void 0; + this.lexer = void 0; + this.macros = void 0; + this.stack = void 0; + this.mode = void 0; + this.settings = settings; + this.expansionCount = 0; + this.feed(input); // Make new global namespace + + this.macros = new Namespace(src_macros, settings.macros); + this.mode = mode; + this.stack = []; // contains tokens in REVERSE order + } + /** + * Feed a new input string to the same MacroExpander + * (with existing macros etc.). + */ + + + feed(input) { + this.lexer = new Lexer(input, this.settings); + } + /** + * Switches between "text" and "math" modes. + */ + + + switchMode(newMode) { + this.mode = newMode; + } + /** + * Start a new group nesting within all namespaces. + */ + + + beginGroup() { + this.macros.beginGroup(); + } + /** + * End current group nesting within all namespaces. + */ + + + endGroup() { + this.macros.endGroup(); + } + /** + * Ends all currently nested groups (if any), restoring values before the + * groups began. Useful in case of an error in the middle of parsing. + */ + + + endGroups() { + this.macros.endGroups(); + } + /** + * Returns the topmost token on the stack, without expanding it. + * Similar in behavior to TeX's `\futurelet`. + */ + + + future() { + if (this.stack.length === 0) { + this.pushToken(this.lexer.lex()); + } + + return this.stack[this.stack.length - 1]; + } + /** + * Remove and return the next unexpanded token. + */ + + + popToken() { + this.future(); // ensure non-empty stack + + return this.stack.pop(); + } + /** + * Add a given token to the token stack. In particular, this get be used + * to put back a token returned from one of the other methods. + */ + + + pushToken(token) { + this.stack.push(token); + } + /** + * Append an array of tokens to the token stack. + */ + + + pushTokens(tokens) { + this.stack.push(...tokens); + } + /** + * Find an macro argument without expanding tokens and append the array of + * tokens to the token stack. Uses Token as a container for the result. + */ + + + scanArgument(isOptional) { + let start; + let end; + let tokens; + + if (isOptional) { + this.consumeSpaces(); // \@ifnextchar gobbles any space following it + + if (this.future().text !== "[") { + return null; + } + + start = this.popToken(); // don't include [ in tokens + + ({ + tokens, + end + } = this.consumeArg(["]"])); + } else { + ({ + tokens, + start, + end + } = this.consumeArg()); + } // indicate the end of an argument + + + this.pushToken(new Token("EOF", end.loc)); + this.pushTokens(tokens); + return start.range(end, ""); + } + /** + * Consume all following space tokens, without expansion. + */ + + + consumeSpaces() { + for (;;) { + const token = this.future(); + + if (token.text === " ") { + this.stack.pop(); + } else { + break; + } + } + } + /** + * Consume an argument from the token stream, and return the resulting array + * of tokens and start/end token. + */ + + + consumeArg(delims) { + // The argument for a delimited parameter is the shortest (possibly + // empty) sequence of tokens with properly nested {...} groups that is + // followed ... by this particular list of non-parameter tokens. + // The argument for an undelimited parameter is the next nonblank + // token, unless that token is ‘{’, when the argument will be the + // entire {...} group that follows. + const tokens = []; + const isDelimited = delims && delims.length > 0; + + if (!isDelimited) { + // Ignore spaces between arguments. As the TeXbook says: + // "After you have said ‘\def\row#1#2{...}’, you are allowed to + // put spaces between the arguments (e.g., ‘\row x n’), because + // TeX doesn’t use single spaces as undelimited arguments." + this.consumeSpaces(); + } + + const start = this.future(); + let tok; + let depth = 0; + let match = 0; + + do { + tok = this.popToken(); + tokens.push(tok); + + if (tok.text === "{") { + ++depth; + } else if (tok.text === "}") { + --depth; + + if (depth === -1) { + throw new src_ParseError("Extra }", tok); + } + } else if (tok.text === "EOF") { + throw new src_ParseError("Unexpected end of input in a macro argument" + ", expected '" + (delims && isDelimited ? delims[match] : "}") + "'", tok); + } + + if (delims && isDelimited) { + if ((depth === 0 || depth === 1 && delims[match] === "{") && tok.text === delims[match]) { + ++match; + + if (match === delims.length) { + // don't include delims in tokens + tokens.splice(-match, match); + break; + } + } else { + match = 0; + } + } + } while (depth !== 0 || isDelimited); // If the argument found ... has the form ‘{}’, + // ... the outermost braces enclosing the argument are removed + + + if (start.text === "{" && tokens[tokens.length - 1].text === "}") { + tokens.pop(); + tokens.shift(); + } + + tokens.reverse(); // to fit in with stack order + + return { + tokens, + start, + end: tok + }; + } + /** + * Consume the specified number of (delimited) arguments from the token + * stream and return the resulting array of arguments. + */ + + + consumeArgs(numArgs, delimiters) { + if (delimiters) { + if (delimiters.length !== numArgs + 1) { + throw new src_ParseError("The length of delimiters doesn't match the number of args!"); + } + + const delims = delimiters[0]; + + for (let i = 0; i < delims.length; i++) { + const tok = this.popToken(); + + if (delims[i] !== tok.text) { + throw new src_ParseError("Use of the macro doesn't match its definition", tok); + } + } + } + + const args = []; + + for (let i = 0; i < numArgs; i++) { + args.push(this.consumeArg(delimiters && delimiters[i + 1]).tokens); + } + + return args; + } + /** + * Increment `expansionCount` by the specified amount. + * Throw an error if it exceeds `maxExpand`. + */ + + + countExpansion(amount) { + this.expansionCount += amount; + + if (this.expansionCount > this.settings.maxExpand) { + throw new src_ParseError("Too many expansions: infinite loop or " + "need to increase maxExpand setting"); + } + } + /** + * Expand the next token only once if possible. + * + * If the token is expanded, the resulting tokens will be pushed onto + * the stack in reverse order, and the number of such tokens will be + * returned. This number might be zero or positive. + * + * If not, the return value is `false`, and the next token remains at the + * top of the stack. + * + * In either case, the next token will be on the top of the stack, + * or the stack will be empty (in case of empty expansion + * and no other tokens). + * + * Used to implement `expandAfterFuture` and `expandNextToken`. + * + * If expandableOnly, only expandable tokens are expanded and + * an undefined control sequence results in an error. + */ + + + expandOnce(expandableOnly) { + const topToken = this.popToken(); + const name = topToken.text; + const expansion = !topToken.noexpand ? this._getExpansion(name) : null; + + if (expansion == null || expandableOnly && expansion.unexpandable) { + if (expandableOnly && expansion == null && name[0] === "\\" && !this.isDefined(name)) { + throw new src_ParseError("Undefined control sequence: " + name); + } + + this.pushToken(topToken); + return false; + } + + this.countExpansion(1); + let tokens = expansion.tokens; + const args = this.consumeArgs(expansion.numArgs, expansion.delimiters); + + if (expansion.numArgs) { + // paste arguments in place of the placeholders + tokens = tokens.slice(); // make a shallow copy + + for (let i = tokens.length - 1; i >= 0; --i) { + let tok = tokens[i]; + + if (tok.text === "#") { + if (i === 0) { + throw new src_ParseError("Incomplete placeholder at end of macro body", tok); + } + + tok = tokens[--i]; // next token on stack + + if (tok.text === "#") { + // ## → # + tokens.splice(i + 1, 1); // drop first # + } else if (/^[1-9]$/.test(tok.text)) { + // replace the placeholder with the indicated argument + tokens.splice(i, 2, ...args[+tok.text - 1]); + } else { + throw new src_ParseError("Not a valid argument number", tok); + } + } + } + } // Concatenate expansion onto top of stack. + + + this.pushTokens(tokens); + return tokens.length; + } + /** + * Expand the next token only once (if possible), and return the resulting + * top token on the stack (without removing anything from the stack). + * Similar in behavior to TeX's `\expandafter\futurelet`. + * Equivalent to expandOnce() followed by future(). + */ + + + expandAfterFuture() { + this.expandOnce(); + return this.future(); + } + /** + * Recursively expand first token, then return first non-expandable token. + */ + + + expandNextToken() { + for (;;) { + if (this.expandOnce() === false) { + // fully expanded + const token = this.stack.pop(); // the token after \noexpand is interpreted as if its meaning + // were ‘\relax’ + + if (token.treatAsRelax) { + token.text = "\\relax"; + } + + return token; + } + } // Flow unable to figure out that this pathway is impossible. + // https://github.com/facebook/flow/issues/4808 + + + throw new Error(); // eslint-disable-line no-unreachable + } + /** + * Fully expand the given macro name and return the resulting list of + * tokens, or return `undefined` if no such macro is defined. + */ + + + expandMacro(name) { + return this.macros.has(name) ? this.expandTokens([new Token(name)]) : undefined; + } + /** + * Fully expand the given token stream and return the resulting list of + * tokens. Note that the input tokens are in reverse order, but the + * output tokens are in forward order. + */ + + + expandTokens(tokens) { + const output = []; + const oldStackLength = this.stack.length; + this.pushTokens(tokens); + + while (this.stack.length > oldStackLength) { + // Expand only expandable tokens + if (this.expandOnce(true) === false) { + // fully expanded + const token = this.stack.pop(); + + if (token.treatAsRelax) { + // the expansion of \noexpand is the token itself + token.noexpand = false; + token.treatAsRelax = false; + } + + output.push(token); + } + } // Count all of these tokens as additional expansions, to prevent + // exponential blowup from linearly many \edef's. + + + this.countExpansion(output.length); + return output; + } + /** + * Fully expand the given macro name and return the result as a string, + * or return `undefined` if no such macro is defined. + */ + + + expandMacroAsText(name) { + const tokens = this.expandMacro(name); + + if (tokens) { + return tokens.map(token => token.text).join(""); + } else { + return tokens; + } + } + /** + * Returns the expanded macro as a reversed array of tokens and a macro + * argument count. Or returns `null` if no such macro. + */ + + + _getExpansion(name) { + const definition = this.macros.get(name); + + if (definition == null) { + // mainly checking for undefined here + return definition; + } // If a single character has an associated catcode other than 13 + // (active character), then don't expand it. + + + if (name.length === 1) { + const catcode = this.lexer.catcodes[name]; + + if (catcode != null && catcode !== 13) { + return; + } + } + + const expansion = typeof definition === "function" ? definition(this) : definition; + + if (typeof expansion === "string") { + let numArgs = 0; + + if (expansion.indexOf("#") !== -1) { + const stripped = expansion.replace(/##/g, ""); + + while (stripped.indexOf("#" + (numArgs + 1)) !== -1) { + ++numArgs; + } + } + + const bodyLexer = new Lexer(expansion, this.settings); + const tokens = []; + let tok = bodyLexer.lex(); + + while (tok.text !== "EOF") { + tokens.push(tok); + tok = bodyLexer.lex(); + } + + tokens.reverse(); // to fit in with stack using push and pop + + const expanded = { + tokens, + numArgs + }; + return expanded; + } + + return expansion; + } + /** + * Determine whether a command is currently "defined" (has some + * functionality), meaning that it's a macro (in the current group), + * a function, a symbol, or one of the special commands listed in + * `implicitCommands`. + */ + + + isDefined(name) { + return this.macros.has(name) || src_functions.hasOwnProperty(name) || src_symbols.math.hasOwnProperty(name) || src_symbols.text.hasOwnProperty(name) || implicitCommands.hasOwnProperty(name); + } + /** + * Determine whether a command is expandable. + */ + + + isExpandable(name) { + const macro = this.macros.get(name); + return macro != null ? typeof macro === "string" || typeof macro === "function" || !macro.unexpandable : src_functions.hasOwnProperty(name) && !src_functions[name].primitive; + } + +} +;// CONCATENATED MODULE: ./src/unicodeSupOrSub.js +// Helpers for Parser.js handling of Unicode (sub|super)script characters. +const unicodeSubRegEx = /^[₊₋₌₍₎₀₁₂₃₄₅₆₇₈₉ₐₑₕᵢⱼₖₗₘₙₒₚᵣₛₜᵤᵥₓᵦᵧᵨᵩᵪ]/; +const uSubsAndSups = Object.freeze({ + '₊': '+', + '₋': '-', + '₌': '=', + '₍': '(', + '₎': ')', + '₀': '0', + '₁': '1', + '₂': '2', + '₃': '3', + '₄': '4', + '₅': '5', + '₆': '6', + '₇': '7', + '₈': '8', + '₉': '9', + '\u2090': 'a', + '\u2091': 'e', + '\u2095': 'h', + '\u1D62': 'i', + '\u2C7C': 'j', + '\u2096': 'k', + '\u2097': 'l', + '\u2098': 'm', + '\u2099': 'n', + '\u2092': 'o', + '\u209A': 'p', + '\u1D63': 'r', + '\u209B': 's', + '\u209C': 't', + '\u1D64': 'u', + '\u1D65': 'v', + '\u2093': 'x', + '\u1D66': 'β', + '\u1D67': 'γ', + '\u1D68': 'ρ', + '\u1D69': '\u03d5', + '\u1D6A': 'χ', + '⁺': '+', + '⁻': '-', + '⁼': '=', + '⁽': '(', + '⁾': ')', + '⁰': '0', + '¹': '1', + '²': '2', + '³': '3', + '⁴': '4', + '⁵': '5', + '⁶': '6', + '⁷': '7', + '⁸': '8', + '⁹': '9', + '\u1D2C': 'A', + '\u1D2E': 'B', + '\u1D30': 'D', + '\u1D31': 'E', + '\u1D33': 'G', + '\u1D34': 'H', + '\u1D35': 'I', + '\u1D36': 'J', + '\u1D37': 'K', + '\u1D38': 'L', + '\u1D39': 'M', + '\u1D3A': 'N', + '\u1D3C': 'O', + '\u1D3E': 'P', + '\u1D3F': 'R', + '\u1D40': 'T', + '\u1D41': 'U', + '\u2C7D': 'V', + '\u1D42': 'W', + '\u1D43': 'a', + '\u1D47': 'b', + '\u1D9C': 'c', + '\u1D48': 'd', + '\u1D49': 'e', + '\u1DA0': 'f', + '\u1D4D': 'g', + '\u02B0': 'h', + '\u2071': 'i', + '\u02B2': 'j', + '\u1D4F': 'k', + '\u02E1': 'l', + '\u1D50': 'm', + '\u207F': 'n', + '\u1D52': 'o', + '\u1D56': 'p', + '\u02B3': 'r', + '\u02E2': 's', + '\u1D57': 't', + '\u1D58': 'u', + '\u1D5B': 'v', + '\u02B7': 'w', + '\u02E3': 'x', + '\u02B8': 'y', + '\u1DBB': 'z', + '\u1D5D': 'β', + '\u1D5E': 'γ', + '\u1D5F': 'δ', + '\u1D60': '\u03d5', + '\u1D61': 'χ', + '\u1DBF': 'θ' +}); +;// CONCATENATED MODULE: ./src/Parser.js +/* eslint no-constant-condition:0 */ + + + + + + + + + + + // Pre-evaluate both modules as unicodeSymbols require String.normalize() + +const unicodeAccents = { + "́": { + "text": "\\'", + "math": "\\acute" + }, + "̀": { + "text": "\\`", + "math": "\\grave" + }, + "̈": { + "text": "\\\"", + "math": "\\ddot" + }, + "̃": { + "text": "\\~", + "math": "\\tilde" + }, + "̄": { + "text": "\\=", + "math": "\\bar" + }, + "̆": { + "text": "\\u", + "math": "\\breve" + }, + "̌": { + "text": "\\v", + "math": "\\check" + }, + "̂": { + "text": "\\^", + "math": "\\hat" + }, + "̇": { + "text": "\\.", + "math": "\\dot" + }, + "̊": { + "text": "\\r", + "math": "\\mathring" + }, + "̋": { + "text": "\\H" + }, + "̧": { + "text": "\\c" + } +}; +const unicodeSymbols = { + "á": "á", + "à": "à", + "ä": "ä", + "ǟ": "ǟ", + "ã": "ã", + "ā": "ā", + "ă": "ă", + "ắ": "ắ", + "ằ": "ằ", + "ẵ": "ẵ", + "ǎ": "ǎ", + "â": "â", + "ấ": "ấ", + "ầ": "ầ", + "ẫ": "ẫ", + "ȧ": "ȧ", + "ǡ": "ǡ", + "å": "å", + "ǻ": "ǻ", + "ḃ": "ḃ", + "ć": "ć", + "ḉ": "ḉ", + "č": "č", + "ĉ": "ĉ", + "ċ": "ċ", + "ç": "ç", + "ď": "ď", + "ḋ": "ḋ", + "ḑ": "ḑ", + "é": "é", + "è": "è", + "ë": "ë", + "ẽ": "ẽ", + "ē": "ē", + "ḗ": "ḗ", + "ḕ": "ḕ", + "ĕ": "ĕ", + "ḝ": "ḝ", + "ě": "ě", + "ê": "ê", + "ế": "ế", + "ề": "ề", + "ễ": "ễ", + "ė": "ė", + "ȩ": "ȩ", + "ḟ": "ḟ", + "ǵ": "ǵ", + "ḡ": "ḡ", + "ğ": "ğ", + "ǧ": "ǧ", + "ĝ": "ĝ", + "ġ": "ġ", + "ģ": "ģ", + "ḧ": "ḧ", + "ȟ": "ȟ", + "ĥ": "ĥ", + "ḣ": "ḣ", + "ḩ": "ḩ", + "í": "í", + "ì": "ì", + "ï": "ï", + "ḯ": "ḯ", + "ĩ": "ĩ", + "ī": "ī", + "ĭ": "ĭ", + "ǐ": "ǐ", + "î": "î", + "ǰ": "ǰ", + "ĵ": "ĵ", + "ḱ": "ḱ", + "ǩ": "ǩ", + "ķ": "ķ", + "ĺ": "ĺ", + "ľ": "ľ", + "ļ": "ļ", + "ḿ": "ḿ", + "ṁ": "ṁ", + "ń": "ń", + "ǹ": "ǹ", + "ñ": "ñ", + "ň": "ň", + "ṅ": "ṅ", + "ņ": "ņ", + "ó": "ó", + "ò": "ò", + "ö": "ö", + "ȫ": "ȫ", + "õ": "õ", + "ṍ": "ṍ", + "ṏ": "ṏ", + "ȭ": "ȭ", + "ō": "ō", + "ṓ": "ṓ", + "ṑ": "ṑ", + "ŏ": "ŏ", + "ǒ": "ǒ", + "ô": "ô", + "ố": "ố", + "ồ": "ồ", + "ỗ": "ỗ", + "ȯ": "ȯ", + "ȱ": "ȱ", + "ő": "ő", + "ṕ": "ṕ", + "ṗ": "ṗ", + "ŕ": "ŕ", + "ř": "ř", + "ṙ": "ṙ", + "ŗ": "ŗ", + "ś": "ś", + "ṥ": "ṥ", + "š": "š", + "ṧ": "ṧ", + "ŝ": "ŝ", + "ṡ": "ṡ", + "ş": "ş", + "ẗ": "ẗ", + "ť": "ť", + "ṫ": "ṫ", + "ţ": "ţ", + "ú": "ú", + "ù": "ù", + "ü": "ü", + "ǘ": "ǘ", + "ǜ": "ǜ", + "ǖ": "ǖ", + "ǚ": "ǚ", + "ũ": "ũ", + "ṹ": "ṹ", + "ū": "ū", + "ṻ": "ṻ", + "ŭ": "ŭ", + "ǔ": "ǔ", + "û": "û", + "ů": "ů", + "ű": "ű", + "ṽ": "ṽ", + "ẃ": "ẃ", + "ẁ": "ẁ", + "ẅ": "ẅ", + "ŵ": "ŵ", + "ẇ": "ẇ", + "ẘ": "ẘ", + "ẍ": "ẍ", + "ẋ": "ẋ", + "ý": "ý", + "ỳ": "ỳ", + "ÿ": "ÿ", + "ỹ": "ỹ", + "ȳ": "ȳ", + "ŷ": "ŷ", + "ẏ": "ẏ", + "ẙ": "ẙ", + "ź": "ź", + "ž": "ž", + "ẑ": "ẑ", + "ż": "ż", + "Á": "Á", + "À": "À", + "Ä": "Ä", + "Ǟ": "Ǟ", + "Ã": "Ã", + "Ā": "Ā", + "Ă": "Ă", + "Ắ": "Ắ", + "Ằ": "Ằ", + "Ẵ": "Ẵ", + "Ǎ": "Ǎ", + "Â": "Â", + "Ấ": "Ấ", + "Ầ": "Ầ", + "Ẫ": "Ẫ", + "Ȧ": "Ȧ", + "Ǡ": "Ǡ", + "Å": "Å", + "Ǻ": "Ǻ", + "Ḃ": "Ḃ", + "Ć": "Ć", + "Ḉ": "Ḉ", + "Č": "Č", + "Ĉ": "Ĉ", + "Ċ": "Ċ", + "Ç": "Ç", + "Ď": "Ď", + "Ḋ": "Ḋ", + "Ḑ": "Ḑ", + "É": "É", + "È": "È", + "Ë": "Ë", + "Ẽ": "Ẽ", + "Ē": "Ē", + "Ḗ": "Ḗ", + "Ḕ": "Ḕ", + "Ĕ": "Ĕ", + "Ḝ": "Ḝ", + "Ě": "Ě", + "Ê": "Ê", + "Ế": "Ế", + "Ề": "Ề", + "Ễ": "Ễ", + "Ė": "Ė", + "Ȩ": "Ȩ", + "Ḟ": "Ḟ", + "Ǵ": "Ǵ", + "Ḡ": "Ḡ", + "Ğ": "Ğ", + "Ǧ": "Ǧ", + "Ĝ": "Ĝ", + "Ġ": "Ġ", + "Ģ": "Ģ", + "Ḧ": "Ḧ", + "Ȟ": "Ȟ", + "Ĥ": "Ĥ", + "Ḣ": "Ḣ", + "Ḩ": "Ḩ", + "Í": "Í", + "Ì": "Ì", + "Ï": "Ï", + "Ḯ": "Ḯ", + "Ĩ": "Ĩ", + "Ī": "Ī", + "Ĭ": "Ĭ", + "Ǐ": "Ǐ", + "Î": "Î", + "İ": "İ", + "Ĵ": "Ĵ", + "Ḱ": "Ḱ", + "Ǩ": "Ǩ", + "Ķ": "Ķ", + "Ĺ": "Ĺ", + "Ľ": "Ľ", + "Ļ": "Ļ", + "Ḿ": "Ḿ", + "Ṁ": "Ṁ", + "Ń": "Ń", + "Ǹ": "Ǹ", + "Ñ": "Ñ", + "Ň": "Ň", + "Ṅ": "Ṅ", + "Ņ": "Ņ", + "Ó": "Ó", + "Ò": "Ò", + "Ö": "Ö", + "Ȫ": "Ȫ", + "Õ": "Õ", + "Ṍ": "Ṍ", + "Ṏ": "Ṏ", + "Ȭ": "Ȭ", + "Ō": "Ō", + "Ṓ": "Ṓ", + "Ṑ": "Ṑ", + "Ŏ": "Ŏ", + "Ǒ": "Ǒ", + "Ô": "Ô", + "Ố": "Ố", + "Ồ": "Ồ", + "Ỗ": "Ỗ", + "Ȯ": "Ȯ", + "Ȱ": "Ȱ", + "Ő": "Ő", + "Ṕ": "Ṕ", + "Ṗ": "Ṗ", + "Ŕ": "Ŕ", + "Ř": "Ř", + "Ṙ": "Ṙ", + "Ŗ": "Ŗ", + "Ś": "Ś", + "Ṥ": "Ṥ", + "Š": "Š", + "Ṧ": "Ṧ", + "Ŝ": "Ŝ", + "Ṡ": "Ṡ", + "Ş": "Ş", + "Ť": "Ť", + "Ṫ": "Ṫ", + "Ţ": "Ţ", + "Ú": "Ú", + "Ù": "Ù", + "Ü": "Ü", + "Ǘ": "Ǘ", + "Ǜ": "Ǜ", + "Ǖ": "Ǖ", + "Ǚ": "Ǚ", + "Ũ": "Ũ", + "Ṹ": "Ṹ", + "Ū": "Ū", + "Ṻ": "Ṻ", + "Ŭ": "Ŭ", + "Ǔ": "Ǔ", + "Û": "Û", + "Ů": "Ů", + "Ű": "Ű", + "Ṽ": "Ṽ", + "Ẃ": "Ẃ", + "Ẁ": "Ẁ", + "Ẅ": "Ẅ", + "Ŵ": "Ŵ", + "Ẇ": "Ẇ", + "Ẍ": "Ẍ", + "Ẋ": "Ẋ", + "Ý": "Ý", + "Ỳ": "Ỳ", + "Ÿ": "Ÿ", + "Ỹ": "Ỹ", + "Ȳ": "Ȳ", + "Ŷ": "Ŷ", + "Ẏ": "Ẏ", + "Ź": "Ź", + "Ž": "Ž", + "Ẑ": "Ẑ", + "Ż": "Ż", + "ά": "ά", + "ὰ": "ὰ", + "ᾱ": "ᾱ", + "ᾰ": "ᾰ", + "έ": "έ", + "ὲ": "ὲ", + "ή": "ή", + "ὴ": "ὴ", + "ί": "ί", + "ὶ": "ὶ", + "ϊ": "ϊ", + "ΐ": "ΐ", + "ῒ": "ῒ", + "ῑ": "ῑ", + "ῐ": "ῐ", + "ό": "ό", + "ὸ": "ὸ", + "ύ": "ύ", + "ὺ": "ὺ", + "ϋ": "ϋ", + "ΰ": "ΰ", + "ῢ": "ῢ", + "ῡ": "ῡ", + "ῠ": "ῠ", + "ώ": "ώ", + "ὼ": "ὼ", + "Ύ": "Ύ", + "Ὺ": "Ὺ", + "Ϋ": "Ϋ", + "Ῡ": "Ῡ", + "Ῠ": "Ῠ", + "Ώ": "Ώ", + "Ὼ": "Ὼ" +}; + +/** + * This file contains the parser used to parse out a TeX expression from the + * input. Since TeX isn't context-free, standard parsers don't work particularly + * well. + * + * The strategy of this parser is as such: + * + * The main functions (the `.parse...` ones) take a position in the current + * parse string to parse tokens from. The lexer (found in Lexer.js, stored at + * this.gullet.lexer) also supports pulling out tokens at arbitrary places. When + * individual tokens are needed at a position, the lexer is called to pull out a + * token, which is then used. + * + * The parser has a property called "mode" indicating the mode that + * the parser is currently in. Currently it has to be one of "math" or + * "text", which denotes whether the current environment is a math-y + * one or a text-y one (e.g. inside \text). Currently, this serves to + * limit the functions which can be used in text mode. + * + * The main functions then return an object which contains the useful data that + * was parsed at its given point, and a new position at the end of the parsed + * data. The main functions can call each other and continue the parsing by + * using the returned position as a new starting point. + * + * There are also extra `.handle...` functions, which pull out some reused + * functionality into self-contained functions. + * + * The functions return ParseNodes. + */ +class Parser { + constructor(input, settings) { + this.mode = void 0; + this.gullet = void 0; + this.settings = void 0; + this.leftrightDepth = void 0; + this.nextToken = void 0; + // Start in math mode + this.mode = "math"; // Create a new macro expander (gullet) and (indirectly via that) also a + // new lexer (mouth) for this parser (stomach, in the language of TeX) + + this.gullet = new MacroExpander(input, settings, this.mode); // Store the settings for use in parsing + + this.settings = settings; // Count leftright depth (for \middle errors) + + this.leftrightDepth = 0; + } + /** + * Checks a result to make sure it has the right type, and throws an + * appropriate error otherwise. + */ + + + expect(text, consume) { + if (consume === void 0) { + consume = true; + } + + if (this.fetch().text !== text) { + throw new src_ParseError("Expected '" + text + "', got '" + this.fetch().text + "'", this.fetch()); + } + + if (consume) { + this.consume(); + } + } + /** + * Discards the current lookahead token, considering it consumed. + */ + + + consume() { + this.nextToken = null; + } + /** + * Return the current lookahead token, or if there isn't one (at the + * beginning, or if the previous lookahead token was consume()d), + * fetch the next token as the new lookahead token and return it. + */ + + + fetch() { + if (this.nextToken == null) { + this.nextToken = this.gullet.expandNextToken(); + } + + return this.nextToken; + } + /** + * Switches between "text" and "math" modes. + */ + + + switchMode(newMode) { + this.mode = newMode; + this.gullet.switchMode(newMode); + } + /** + * Main parsing function, which parses an entire input. + */ + + + parse() { + if (!this.settings.globalGroup) { + // Create a group namespace for the math expression. + // (LaTeX creates a new group for every $...$, $$...$$, \[...\].) + this.gullet.beginGroup(); + } // Use old \color behavior (same as LaTeX's \textcolor) if requested. + // We do this within the group for the math expression, so it doesn't + // pollute settings.macros. + + + if (this.settings.colorIsTextColor) { + this.gullet.macros.set("\\color", "\\textcolor"); + } + + try { + // Try to parse the input + const parse = this.parseExpression(false); // If we succeeded, make sure there's an EOF at the end + + this.expect("EOF"); // End the group namespace for the expression + + if (!this.settings.globalGroup) { + this.gullet.endGroup(); + } + + return parse; // Close any leftover groups in case of a parse error. + } finally { + this.gullet.endGroups(); + } + } + /** + * Fully parse a separate sequence of tokens as a separate job. + * Tokens should be specified in reverse order, as in a MacroDefinition. + */ + + + subparse(tokens) { + // Save the next token from the current job. + const oldToken = this.nextToken; + this.consume(); // Run the new job, terminating it with an excess '}' + + this.gullet.pushToken(new Token("}")); + this.gullet.pushTokens(tokens); + const parse = this.parseExpression(false); + this.expect("}"); // Restore the next token from the current job. + + this.nextToken = oldToken; + return parse; + } + + /** + * Parses an "expression", which is a list of atoms. + * + * `breakOnInfix`: Should the parsing stop when we hit infix nodes? This + * happens when functions have higher precedence han infix + * nodes in implicit parses. + * + * `breakOnTokenText`: The text of the token that the expression should end + * with, or `null` if something else should end the + * expression. + */ + parseExpression(breakOnInfix, breakOnTokenText) { + const body = []; // Keep adding atoms to the body until we can't parse any more atoms (either + // we reached the end, a }, or a \right) + + while (true) { + // Ignore spaces in math mode + if (this.mode === "math") { + this.consumeSpaces(); + } + + const lex = this.fetch(); + + if (Parser.endOfExpression.indexOf(lex.text) !== -1) { + break; + } + + if (breakOnTokenText && lex.text === breakOnTokenText) { + break; + } + + if (breakOnInfix && src_functions[lex.text] && src_functions[lex.text].infix) { + break; + } + + const atom = this.parseAtom(breakOnTokenText); + + if (!atom) { + break; + } else if (atom.type === "internal") { + // Internal nodes do not appear in parse tree + continue; + } + + body.push(atom); + } + + if (this.mode === "text") { + this.formLigatures(body); + } + + return this.handleInfixNodes(body); + } + /** + * Rewrites infix operators such as \over with corresponding commands such + * as \frac. + * + * There can only be one infix operator per group. If there's more than one + * then the expression is ambiguous. This can be resolved by adding {}. + */ + + + handleInfixNodes(body) { + let overIndex = -1; + let funcName; + + for (let i = 0; i < body.length; i++) { + if (body[i].type === "infix") { + if (overIndex !== -1) { + throw new src_ParseError("only one infix operator per group", body[i].token); + } + + overIndex = i; + funcName = body[i].replaceWith; + } + } + + if (overIndex !== -1 && funcName) { + let numerNode; + let denomNode; + const numerBody = body.slice(0, overIndex); + const denomBody = body.slice(overIndex + 1); + + if (numerBody.length === 1 && numerBody[0].type === "ordgroup") { + numerNode = numerBody[0]; + } else { + numerNode = { + type: "ordgroup", + mode: this.mode, + body: numerBody + }; + } + + if (denomBody.length === 1 && denomBody[0].type === "ordgroup") { + denomNode = denomBody[0]; + } else { + denomNode = { + type: "ordgroup", + mode: this.mode, + body: denomBody + }; + } + + let node; + + if (funcName === "\\\\abovefrac") { + node = this.callFunction(funcName, [numerNode, body[overIndex], denomNode], []); + } else { + node = this.callFunction(funcName, [numerNode, denomNode], []); + } + + return [node]; + } else { + return body; + } + } + /** + * Handle a subscript or superscript with nice errors. + */ + + + handleSupSubscript(name // For error reporting. + ) { + const symbolToken = this.fetch(); + const symbol = symbolToken.text; + this.consume(); + this.consumeSpaces(); // ignore spaces before sup/subscript argument + // Skip over allowed internal nodes such as \relax + + let group; + + do { + var _group; + + group = this.parseGroup(name); + } while (((_group = group) == null ? void 0 : _group.type) === "internal"); + + if (!group) { + throw new src_ParseError("Expected group after '" + symbol + "'", symbolToken); + } + + return group; + } + /** + * Converts the textual input of an unsupported command into a text node + * contained within a color node whose color is determined by errorColor + */ + + + formatUnsupportedCmd(text) { + const textordArray = []; + + for (let i = 0; i < text.length; i++) { + textordArray.push({ + type: "textord", + mode: "text", + text: text[i] + }); + } + + const textNode = { + type: "text", + mode: this.mode, + body: textordArray + }; + const colorNode = { + type: "color", + mode: this.mode, + color: this.settings.errorColor, + body: [textNode] + }; + return colorNode; + } + /** + * Parses a group with optional super/subscripts. + */ + + + parseAtom(breakOnTokenText) { + // The body of an atom is an implicit group, so that things like + // \left(x\right)^2 work correctly. + const base = this.parseGroup("atom", breakOnTokenText); // Internal nodes (e.g. \relax) cannot support super/subscripts. + // Instead we will pick up super/subscripts with blank base next round. + + if ((base == null ? void 0 : base.type) === "internal") { + return base; + } // In text mode, we don't have superscripts or subscripts + + + if (this.mode === "text") { + return base; + } // Note that base may be empty (i.e. null) at this point. + + + let superscript; + let subscript; + + while (true) { + // Guaranteed in math mode, so eat any spaces first. + this.consumeSpaces(); // Lex the first token + + const lex = this.fetch(); + + if (lex.text === "\\limits" || lex.text === "\\nolimits") { + // We got a limit control + if (base && base.type === "op") { + const limits = lex.text === "\\limits"; + base.limits = limits; + base.alwaysHandleSupSub = true; + } else if (base && base.type === "operatorname") { + if (base.alwaysHandleSupSub) { + base.limits = lex.text === "\\limits"; + } + } else { + throw new src_ParseError("Limit controls must follow a math operator", lex); + } + + this.consume(); + } else if (lex.text === "^") { + // We got a superscript start + if (superscript) { + throw new src_ParseError("Double superscript", lex); + } + + superscript = this.handleSupSubscript("superscript"); + } else if (lex.text === "_") { + // We got a subscript start + if (subscript) { + throw new src_ParseError("Double subscript", lex); + } + + subscript = this.handleSupSubscript("subscript"); + } else if (lex.text === "'") { + // We got a prime + if (superscript) { + throw new src_ParseError("Double superscript", lex); + } + + const prime = { + type: "textord", + mode: this.mode, + text: "\\prime" + }; // Many primes can be grouped together, so we handle this here + + const primes = [prime]; + this.consume(); // Keep lexing tokens until we get something that's not a prime + + while (this.fetch().text === "'") { + // For each one, add another prime to the list + primes.push(prime); + this.consume(); + } // If there's a superscript following the primes, combine that + // superscript in with the primes. + + + if (this.fetch().text === "^") { + primes.push(this.handleSupSubscript("superscript")); + } // Put everything into an ordgroup as the superscript + + + superscript = { + type: "ordgroup", + mode: this.mode, + body: primes + }; + } else if (uSubsAndSups[lex.text]) { + // A Unicode subscript or superscript character. + // We treat these similarly to the unicode-math package. + // So we render a string of Unicode (sub|super)scripts the + // same as a (sub|super)script of regular characters. + const isSub = unicodeSubRegEx.test(lex.text); + const subsupTokens = []; + subsupTokens.push(new Token(uSubsAndSups[lex.text])); + this.consume(); // Continue fetching tokens to fill out the string. + + while (true) { + const token = this.fetch().text; + + if (!uSubsAndSups[token]) { + break; + } + + if (unicodeSubRegEx.test(token) !== isSub) { + break; + } + + subsupTokens.unshift(new Token(uSubsAndSups[token])); + this.consume(); + } // Now create a (sub|super)script. + + + const body = this.subparse(subsupTokens); + + if (isSub) { + subscript = { + type: "ordgroup", + mode: "math", + body + }; + } else { + superscript = { + type: "ordgroup", + mode: "math", + body + }; + } + } else { + // If it wasn't ^, _, or ', stop parsing super/subscripts + break; + } + } // Base must be set if superscript or subscript are set per logic above, + // but need to check here for type check to pass. + + + if (superscript || subscript) { + // If we got either a superscript or subscript, create a supsub + return { + type: "supsub", + mode: this.mode, + base: base, + sup: superscript, + sub: subscript + }; + } else { + // Otherwise return the original body + return base; + } + } + /** + * Parses an entire function, including its base and all of its arguments. + */ + + + parseFunction(breakOnTokenText, name // For determining its context + ) { + const token = this.fetch(); + const func = token.text; + const funcData = src_functions[func]; + + if (!funcData) { + return null; + } + + this.consume(); // consume command token + + if (name && name !== "atom" && !funcData.allowedInArgument) { + throw new src_ParseError("Got function '" + func + "' with no arguments" + (name ? " as " + name : ""), token); + } else if (this.mode === "text" && !funcData.allowedInText) { + throw new src_ParseError("Can't use function '" + func + "' in text mode", token); + } else if (this.mode === "math" && funcData.allowedInMath === false) { + throw new src_ParseError("Can't use function '" + func + "' in math mode", token); + } + + const { + args, + optArgs + } = this.parseArguments(func, funcData); + return this.callFunction(func, args, optArgs, token, breakOnTokenText); + } + /** + * Call a function handler with a suitable context and arguments. + */ + + + callFunction(name, args, optArgs, token, breakOnTokenText) { + const context = { + funcName: name, + parser: this, + token, + breakOnTokenText + }; + const func = src_functions[name]; + + if (func && func.handler) { + return func.handler(context, args, optArgs); + } else { + throw new src_ParseError("No function handler for " + name); + } + } + /** + * Parses the arguments of a function or environment + */ + + + parseArguments(func, // Should look like "\name" or "\begin{name}". + funcData) { + const totalArgs = funcData.numArgs + funcData.numOptionalArgs; + + if (totalArgs === 0) { + return { + args: [], + optArgs: [] + }; + } + + const args = []; + const optArgs = []; + + for (let i = 0; i < totalArgs; i++) { + let argType = funcData.argTypes && funcData.argTypes[i]; + const isOptional = i < funcData.numOptionalArgs; + + if (funcData.primitive && argType == null || // \sqrt expands into primitive if optional argument doesn't exist + funcData.type === "sqrt" && i === 1 && optArgs[0] == null) { + argType = "primitive"; + } + + const arg = this.parseGroupOfType("argument to '" + func + "'", argType, isOptional); + + if (isOptional) { + optArgs.push(arg); + } else if (arg != null) { + args.push(arg); + } else { + // should be unreachable + throw new src_ParseError("Null argument, please report this as a bug"); + } + } + + return { + args, + optArgs + }; + } + /** + * Parses a group when the mode is changing. + */ + + + parseGroupOfType(name, type, optional) { + switch (type) { + case "color": + return this.parseColorGroup(optional); + + case "size": + return this.parseSizeGroup(optional); + + case "url": + return this.parseUrlGroup(optional); + + case "math": + case "text": + return this.parseArgumentGroup(optional, type); + + case "hbox": + { + // hbox argument type wraps the argument in the equivalent of + // \hbox, which is like \text but switching to \textstyle size. + const group = this.parseArgumentGroup(optional, "text"); + return group != null ? { + type: "styling", + mode: group.mode, + body: [group], + style: "text" // simulate \textstyle + + } : null; + } + + case "raw": + { + const token = this.parseStringGroup("raw", optional); + return token != null ? { + type: "raw", + mode: "text", + string: token.text + } : null; + } + + case "primitive": + { + if (optional) { + throw new src_ParseError("A primitive argument cannot be optional"); + } + + const group = this.parseGroup(name); + + if (group == null) { + throw new src_ParseError("Expected group as " + name, this.fetch()); + } + + return group; + } + + case "original": + case null: + case undefined: + return this.parseArgumentGroup(optional); + + default: + throw new src_ParseError("Unknown group type as " + name, this.fetch()); + } + } + /** + * Discard any space tokens, fetching the next non-space token. + */ + + + consumeSpaces() { + while (this.fetch().text === " ") { + this.consume(); + } + } + /** + * Parses a group, essentially returning the string formed by the + * brace-enclosed tokens plus some position information. + */ + + + parseStringGroup(modeName, // Used to describe the mode in error messages. + optional) { + const argToken = this.gullet.scanArgument(optional); + + if (argToken == null) { + return null; + } + + let str = ""; + let nextToken; + + while ((nextToken = this.fetch()).text !== "EOF") { + str += nextToken.text; + this.consume(); + } + + this.consume(); // consume the end of the argument + + argToken.text = str; + return argToken; + } + /** + * Parses a regex-delimited group: the largest sequence of tokens + * whose concatenated strings match `regex`. Returns the string + * formed by the tokens plus some position information. + */ + + + parseRegexGroup(regex, modeName // Used to describe the mode in error messages. + ) { + const firstToken = this.fetch(); + let lastToken = firstToken; + let str = ""; + let nextToken; + + while ((nextToken = this.fetch()).text !== "EOF" && regex.test(str + nextToken.text)) { + lastToken = nextToken; + str += lastToken.text; + this.consume(); + } + + if (str === "") { + throw new src_ParseError("Invalid " + modeName + ": '" + firstToken.text + "'", firstToken); + } + + return firstToken.range(lastToken, str); + } + /** + * Parses a color description. + */ + + + parseColorGroup(optional) { + const res = this.parseStringGroup("color", optional); + + if (res == null) { + return null; + } + + const match = /^(#[a-f0-9]{3}|#?[a-f0-9]{6}|[a-z]+)$/i.exec(res.text); + + if (!match) { + throw new src_ParseError("Invalid color: '" + res.text + "'", res); + } + + let color = match[0]; + + if (/^[0-9a-f]{6}$/i.test(color)) { + // We allow a 6-digit HTML color spec without a leading "#". + // This follows the xcolor package's HTML color model. + // Predefined color names are all missed by this RegEx pattern. + color = "#" + color; + } + + return { + type: "color-token", + mode: this.mode, + color + }; + } + /** + * Parses a size specification, consisting of magnitude and unit. + */ + + + parseSizeGroup(optional) { + let res; + let isBlank = false; // don't expand before parseStringGroup + + this.gullet.consumeSpaces(); + + if (!optional && this.gullet.future().text !== "{") { + res = this.parseRegexGroup(/^[-+]? *(?:$|\d+|\d+\.\d*|\.\d*) *[a-z]{0,2} *$/, "size"); + } else { + res = this.parseStringGroup("size", optional); + } + + if (!res) { + return null; + } + + if (!optional && res.text.length === 0) { + // Because we've tested for what is !optional, this block won't + // affect \kern, \hspace, etc. It will capture the mandatory arguments + // to \genfrac and \above. + res.text = "0pt"; // Enable \above{} + + isBlank = true; // This is here specifically for \genfrac + } + + const match = /([-+]?) *(\d+(?:\.\d*)?|\.\d+) *([a-z]{2})/.exec(res.text); + + if (!match) { + throw new src_ParseError("Invalid size: '" + res.text + "'", res); + } + + const data = { + number: +(match[1] + match[2]), + // sign + magnitude, cast to number + unit: match[3] + }; + + if (!validUnit(data)) { + throw new src_ParseError("Invalid unit: '" + data.unit + "'", res); + } + + return { + type: "size", + mode: this.mode, + value: data, + isBlank + }; + } + /** + * Parses an URL, checking escaped letters and allowed protocols, + * and setting the catcode of % as an active character (as in \hyperref). + */ + + + parseUrlGroup(optional) { + this.gullet.lexer.setCatcode("%", 13); // active character + + this.gullet.lexer.setCatcode("~", 12); // other character + + const res = this.parseStringGroup("url", optional); + this.gullet.lexer.setCatcode("%", 14); // comment character + + this.gullet.lexer.setCatcode("~", 13); // active character + + if (res == null) { + return null; + } // hyperref package allows backslashes alone in href, but doesn't + // generate valid links in such cases; we interpret this as + // "undefined" behaviour, and keep them as-is. Some browser will + // replace backslashes with forward slashes. + + + const url = res.text.replace(/\\([#$%&~_^{}])/g, '$1'); + return { + type: "url", + mode: this.mode, + url + }; + } + /** + * Parses an argument with the mode specified. + */ + + + parseArgumentGroup(optional, mode) { + const argToken = this.gullet.scanArgument(optional); + + if (argToken == null) { + return null; + } + + const outerMode = this.mode; + + if (mode) { + // Switch to specified mode + this.switchMode(mode); + } + + this.gullet.beginGroup(); + const expression = this.parseExpression(false, "EOF"); // TODO: find an alternative way to denote the end + + this.expect("EOF"); // expect the end of the argument + + this.gullet.endGroup(); + const result = { + type: "ordgroup", + mode: this.mode, + loc: argToken.loc, + body: expression + }; + + if (mode) { + // Switch mode back + this.switchMode(outerMode); + } + + return result; + } + /** + * Parses an ordinary group, which is either a single nucleus (like "x") + * or an expression in braces (like "{x+y}") or an implicit group, a group + * that starts at the current position, and ends right before a higher explicit + * group ends, or at EOF. + */ + + + parseGroup(name, // For error reporting. + breakOnTokenText) { + const firstToken = this.fetch(); + const text = firstToken.text; + let result; // Try to parse an open brace or \begingroup + + if (text === "{" || text === "\\begingroup") { + this.consume(); + const groupEnd = text === "{" ? "}" : "\\endgroup"; + this.gullet.beginGroup(); // If we get a brace, parse an expression + + const expression = this.parseExpression(false, groupEnd); + const lastToken = this.fetch(); + this.expect(groupEnd); // Check that we got a matching closing brace + + this.gullet.endGroup(); + result = { + type: "ordgroup", + mode: this.mode, + loc: SourceLocation.range(firstToken, lastToken), + body: expression, + // A group formed by \begingroup...\endgroup is a semi-simple group + // which doesn't affect spacing in math mode, i.e., is transparent. + // https://tex.stackexchange.com/questions/1930/when-should-one- + // use-begingroup-instead-of-bgroup + semisimple: text === "\\begingroup" || undefined + }; + } else { + // If there exists a function with this name, parse the function. + // Otherwise, just return a nucleus + result = this.parseFunction(breakOnTokenText, name) || this.parseSymbol(); + + if (result == null && text[0] === "\\" && !implicitCommands.hasOwnProperty(text)) { + if (this.settings.throwOnError) { + throw new src_ParseError("Undefined control sequence: " + text, firstToken); + } + + result = this.formatUnsupportedCmd(text); + this.consume(); + } + } + + return result; + } + /** + * Form ligature-like combinations of characters for text mode. + * This includes inputs like "--", "---", "``" and "''". + * The result will simply replace multiple textord nodes with a single + * character in each value by a single textord node having multiple + * characters in its value. The representation is still ASCII source. + * The group will be modified in place. + */ + + + formLigatures(group) { + let n = group.length - 1; + + for (let i = 0; i < n; ++i) { + const a = group[i]; // $FlowFixMe: Not every node type has a `text` property. + + const v = a.text; + + if (v === "-" && group[i + 1].text === "-") { + if (i + 1 < n && group[i + 2].text === "-") { + group.splice(i, 3, { + type: "textord", + mode: "text", + loc: SourceLocation.range(a, group[i + 2]), + text: "---" + }); + n -= 2; + } else { + group.splice(i, 2, { + type: "textord", + mode: "text", + loc: SourceLocation.range(a, group[i + 1]), + text: "--" + }); + n -= 1; + } + } + + if ((v === "'" || v === "`") && group[i + 1].text === v) { + group.splice(i, 2, { + type: "textord", + mode: "text", + loc: SourceLocation.range(a, group[i + 1]), + text: v + v + }); + n -= 1; + } + } + } + /** + * Parse a single symbol out of the string. Here, we handle single character + * symbols and special functions like \verb. + */ + + + parseSymbol() { + const nucleus = this.fetch(); + let text = nucleus.text; + + if (/^\\verb[^a-zA-Z]/.test(text)) { + this.consume(); + let arg = text.slice(5); + const star = arg.charAt(0) === "*"; + + if (star) { + arg = arg.slice(1); + } // Lexer's tokenRegex is constructed to always have matching + // first/last characters. + + + if (arg.length < 2 || arg.charAt(0) !== arg.slice(-1)) { + throw new src_ParseError("\\verb assertion failed --\n please report what input caused this bug"); + } + + arg = arg.slice(1, -1); // remove first and last char + + return { + type: "verb", + mode: "text", + body: arg, + star + }; + } // At this point, we should have a symbol, possibly with accents. + // First expand any accented base symbol according to unicodeSymbols. + + + if (unicodeSymbols.hasOwnProperty(text[0]) && !src_symbols[this.mode][text[0]]) { + // This behavior is not strict (XeTeX-compatible) in math mode. + if (this.settings.strict && this.mode === "math") { + this.settings.reportNonstrict("unicodeTextInMathMode", "Accented Unicode text character \"" + text[0] + "\" used in " + "math mode", nucleus); + } + + text = unicodeSymbols[text[0]] + text.slice(1); + } // Strip off any combining characters + + + const match = combiningDiacriticalMarksEndRegex.exec(text); + + if (match) { + text = text.substring(0, match.index); + + if (text === 'i') { + text = '\u0131'; // dotless i, in math and text mode + } else if (text === 'j') { + text = '\u0237'; // dotless j, in math and text mode + } + } // Recognize base symbol + + + let symbol; + + if (src_symbols[this.mode][text]) { + if (this.settings.strict && this.mode === 'math' && extraLatin.indexOf(text) >= 0) { + this.settings.reportNonstrict("unicodeTextInMathMode", "Latin-1/Unicode text character \"" + text[0] + "\" used in " + "math mode", nucleus); + } + + const group = src_symbols[this.mode][text].group; + const loc = SourceLocation.range(nucleus); + let s; + + if (ATOMS.hasOwnProperty(group)) { + // $FlowFixMe + const family = group; + s = { + type: "atom", + mode: this.mode, + family, + loc, + text + }; + } else { + // $FlowFixMe + s = { + type: group, + mode: this.mode, + loc, + text + }; + } // $FlowFixMe + + + symbol = s; + } else if (text.charCodeAt(0) >= 0x80) { + // no symbol for e.g. ^ + if (this.settings.strict) { + if (!supportedCodepoint(text.charCodeAt(0))) { + this.settings.reportNonstrict("unknownSymbol", "Unrecognized Unicode character \"" + text[0] + "\"" + (" (" + text.charCodeAt(0) + ")"), nucleus); + } else if (this.mode === "math") { + this.settings.reportNonstrict("unicodeTextInMathMode", "Unicode text character \"" + text[0] + "\" used in math mode", nucleus); + } + } // All nonmathematical Unicode characters are rendered as if they + // are in text mode (wrapped in \text) because that's what it + // takes to render them in LaTeX. Setting `mode: this.mode` is + // another natural choice (the user requested math mode), but + // this makes it more difficult for getCharacterMetrics() to + // distinguish Unicode characters without metrics and those for + // which we want to simulate the letter M. + + + symbol = { + type: "textord", + mode: "text", + loc: SourceLocation.range(nucleus), + text + }; + } else { + return null; // EOF, ^, _, {, }, etc. + } + + this.consume(); // Transform combining characters into accents + + if (match) { + for (let i = 0; i < match[0].length; i++) { + const accent = match[0][i]; + + if (!unicodeAccents[accent]) { + throw new src_ParseError("Unknown accent ' " + accent + "'", nucleus); + } + + const command = unicodeAccents[accent][this.mode] || unicodeAccents[accent].text; + + if (!command) { + throw new src_ParseError("Accent " + accent + " unsupported in " + this.mode + " mode", nucleus); + } + + symbol = { + type: "accent", + mode: this.mode, + loc: SourceLocation.range(nucleus), + label: command, + isStretchy: false, + isShifty: true, + // $FlowFixMe + base: symbol + }; + } + } // $FlowFixMe + + + return symbol; + } + +} +Parser.endOfExpression = ["}", "\\endgroup", "\\end", "\\right", "&"]; +;// CONCATENATED MODULE: ./src/parseTree.js +/** + * Provides a single function for parsing an expression using a Parser + * TODO(emily): Remove this + */ + + + + +/** + * Parses an expression using a Parser, then returns the parsed result. + */ +const parseTree = function (toParse, settings) { + if (!(typeof toParse === 'string' || toParse instanceof String)) { + throw new TypeError('KaTeX can only parse string typed expression'); + } + + const parser = new Parser(toParse, settings); // Blank out any \df@tag to avoid spurious "Duplicate \tag" errors + + delete parser.gullet.macros.current["\\df@tag"]; + let tree = parser.parse(); // Prevent a color definition from persisting between calls to katex.render(). + + delete parser.gullet.macros.current["\\current@color"]; + delete parser.gullet.macros.current["\\color"]; // If the input used \tag, it will set the \df@tag macro to the tag. + // In this case, we separately parse the tag and wrap the tree. + + if (parser.gullet.macros.get("\\df@tag")) { + if (!settings.displayMode) { + throw new src_ParseError("\\tag works only in display equations"); + } + + tree = [{ + type: "tag", + mode: "text", + body: tree, + tag: parser.subparse([new Token("\\df@tag")]) + }]; + } + + return tree; +}; + +/* harmony default export */ var src_parseTree = (parseTree); +;// CONCATENATED MODULE: ./katex.js +/* eslint no-console:0 */ + +/** + * This is the main entry point for KaTeX. Here, we expose functions for + * rendering expressions either to DOM nodes or to markup strings. + * + * We also expose the ParseError class to check if errors thrown from KaTeX are + * errors in the expression, or errors in javascript handling. + */ + + + + + + + + + + + +/** + * Parse and build an expression, and place that expression in the DOM node + * given. + */ +let render = function (expression, baseNode, options) { + baseNode.textContent = ""; + const node = renderToDomTree(expression, options).toNode(); + baseNode.appendChild(node); +}; // KaTeX's styles don't work properly in quirks mode. Print out an error, and +// disable rendering. + + +if (typeof document !== "undefined") { + if (document.compatMode !== "CSS1Compat") { + typeof console !== "undefined" && console.warn("Warning: KaTeX doesn't work in quirks mode. Make sure your " + "website has a suitable doctype."); + + render = function () { + throw new src_ParseError("KaTeX doesn't work in quirks mode."); + }; + } +} +/** + * Parse and build an expression, and return the markup for that. + */ + + +const renderToString = function (expression, options) { + const markup = renderToDomTree(expression, options).toMarkup(); + return markup; +}; +/** + * Parse an expression and return the parse tree. + */ + + +const generateParseTree = function (expression, options) { + const settings = new Settings(options); + return src_parseTree(expression, settings); +}; +/** + * If the given error is a KaTeX ParseError and options.throwOnError is false, + * renders the invalid LaTeX as a span with hover title giving the KaTeX + * error message. Otherwise, simply throws the error. + */ + + +const renderError = function (error, expression, options) { + if (options.throwOnError || !(error instanceof src_ParseError)) { + throw error; + } + + const node = buildCommon.makeSpan(["katex-error"], [new SymbolNode(expression)]); + node.setAttribute("title", error.toString()); + node.setAttribute("style", "color:" + options.errorColor); + return node; +}; +/** + * Generates and returns the katex build tree. This is used for advanced + * use cases (like rendering to custom output). + */ + + +const renderToDomTree = function (expression, options) { + const settings = new Settings(options); + + try { + const tree = src_parseTree(expression, settings); + return buildTree(tree, expression, settings); + } catch (error) { + return renderError(error, expression, settings); + } +}; +/** + * Generates and returns the katex build tree, with just HTML (no MathML). + * This is used for advanced use cases (like rendering to custom output). + */ + + +const renderToHTMLTree = function (expression, options) { + const settings = new Settings(options); + + try { + const tree = src_parseTree(expression, settings); + return buildHTMLTree(tree, expression, settings); + } catch (error) { + return renderError(error, expression, settings); + } +}; + +const version = "0.16.22"; +const __domTree = { + Span: Span, + Anchor: Anchor, + SymbolNode: SymbolNode, + SvgNode: SvgNode, + PathNode: PathNode, + LineNode: LineNode +}; // ESM exports + + // CJS exports and ESM default export + +/* harmony default export */ var katex = ({ + /** + * Current KaTeX version + */ + version, + + /** + * Renders the given LaTeX into an HTML+MathML combination, and adds + * it as a child to the specified DOM node. + */ + render, + + /** + * Renders the given LaTeX into an HTML+MathML combination string, + * for sending to the client. + */ + renderToString, + + /** + * KaTeX error, usually during parsing. + */ + ParseError: src_ParseError, + + /** + * The schema of Settings + */ + SETTINGS_SCHEMA: SETTINGS_SCHEMA, + + /** + * Parses the given LaTeX into KaTeX's internal parse tree structure, + * without rendering to HTML or MathML. + * + * NOTE: This method is not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __parse: generateParseTree, + + /** + * Renders the given LaTeX into an HTML+MathML internal DOM tree + * representation, without flattening that representation to a string. + * + * NOTE: This method is not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __renderToDomTree: renderToDomTree, + + /** + * Renders the given LaTeX into an HTML internal DOM tree representation, + * without MathML and without flattening that representation to a string. + * + * NOTE: This method is not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __renderToHTMLTree: renderToHTMLTree, + + /** + * extends internal font metrics object with a new object + * each key in the new object represents a font name + */ + __setFontMetrics: setFontMetrics, + + /** + * adds a new symbol to builtin symbols table + */ + __defineSymbol: defineSymbol, + + /** + * adds a new function to builtin function list, + * which directly produce parse tree elements + * and have their own html/mathml builders + */ + __defineFunction: defineFunction, + + /** + * adds a new macro to builtin macro list + */ + __defineMacro: defineMacro, + + /** + * Expose the dom tree node types, which can be useful for type checking nodes. + * + * NOTE: These methods are not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __domTree +}); +;// CONCATENATED MODULE: ./katex.webpack.js +/** + * This is the webpack entry point for KaTeX. As ECMAScript, flow[1] and jest[2] + * doesn't support CSS modules natively, a separate entry point is used and + * it is not flowtyped. + * + * [1] https://gist.github.com/lambdahands/d19e0da96285b749f0ef + * [2] https://facebook.github.io/jest/docs/en/webpack.html + */ + + +/* harmony default export */ var katex_webpack = (katex); +__webpack_exports__ = __webpack_exports__["default"]; +/******/ return __webpack_exports__; +/******/ })() +; +}); \ No newline at end of file diff --git a/frontend/node_modules/katex/dist/katex.min.css b/frontend/node_modules/katex/dist/katex.min.css new file mode 100644 index 0000000..3d176ab --- /dev/null +++ b/frontend/node_modules/katex/dist/katex.min.css @@ -0,0 +1 @@ +@font-face{font-family:KaTeX_AMS;font-style:normal;font-weight:400;src:url(fonts/KaTeX_AMS-Regular.woff2) format("woff2"),url(fonts/KaTeX_AMS-Regular.woff) format("woff"),url(fonts/KaTeX_AMS-Regular.ttf) format("truetype")}@font-face{font-family:KaTeX_Caligraphic;font-style:normal;font-weight:700;src:url(fonts/KaTeX_Caligraphic-Bold.woff2) format("woff2"),url(fonts/KaTeX_Caligraphic-Bold.woff) format("woff"),url(fonts/KaTeX_Caligraphic-Bold.ttf) format("truetype")}@font-face{font-family:KaTeX_Caligraphic;font-style:normal;font-weight:400;src:url(fonts/KaTeX_Caligraphic-Regular.woff2) format("woff2"),url(fonts/KaTeX_Caligraphic-Regular.woff) format("woff"),url(fonts/KaTeX_Caligraphic-Regular.ttf) format("truetype")}@font-face{font-family:KaTeX_Fraktur;font-style:normal;font-weight:700;src:url(fonts/KaTeX_Fraktur-Bold.woff2) format("woff2"),url(fonts/KaTeX_Fraktur-Bold.woff) format("woff"),url(fonts/KaTeX_Fraktur-Bold.ttf) format("truetype")}@font-face{font-family:KaTeX_Fraktur;font-style:normal;font-weight:400;src:url(fonts/KaTeX_Fraktur-Regular.woff2) format("woff2"),url(fonts/KaTeX_Fraktur-Regular.woff) format("woff"),url(fonts/KaTeX_Fraktur-Regular.ttf) format("truetype")}@font-face{font-family:KaTeX_Main;font-style:normal;font-weight:700;src:url(fonts/KaTeX_Main-Bold.woff2) format("woff2"),url(fonts/KaTeX_Main-Bold.woff) format("woff"),url(fonts/KaTeX_Main-Bold.ttf) format("truetype")}@font-face{font-family:KaTeX_Main;font-style:italic;font-weight:700;src:url(fonts/KaTeX_Main-BoldItalic.woff2) format("woff2"),url(fonts/KaTeX_Main-BoldItalic.woff) format("woff"),url(fonts/KaTeX_Main-BoldItalic.ttf) format("truetype")}@font-face{font-family:KaTeX_Main;font-style:italic;font-weight:400;src:url(fonts/KaTeX_Main-Italic.woff2) format("woff2"),url(fonts/KaTeX_Main-Italic.woff) format("woff"),url(fonts/KaTeX_Main-Italic.ttf) format("truetype")}@font-face{font-family:KaTeX_Main;font-style:normal;font-weight:400;src:url(fonts/KaTeX_Main-Regular.woff2) format("woff2"),url(fonts/KaTeX_Main-Regular.woff) format("woff"),url(fonts/KaTeX_Main-Regular.ttf) format("truetype")}@font-face{font-family:KaTeX_Math;font-style:italic;font-weight:700;src:url(fonts/KaTeX_Math-BoldItalic.woff2) format("woff2"),url(fonts/KaTeX_Math-BoldItalic.woff) format("woff"),url(fonts/KaTeX_Math-BoldItalic.ttf) format("truetype")}@font-face{font-family:KaTeX_Math;font-style:italic;font-weight:400;src:url(fonts/KaTeX_Math-Italic.woff2) format("woff2"),url(fonts/KaTeX_Math-Italic.woff) format("woff"),url(fonts/KaTeX_Math-Italic.ttf) format("truetype")}@font-face{font-family:"KaTeX_SansSerif";font-style:normal;font-weight:700;src:url(fonts/KaTeX_SansSerif-Bold.woff2) format("woff2"),url(fonts/KaTeX_SansSerif-Bold.woff) format("woff"),url(fonts/KaTeX_SansSerif-Bold.ttf) format("truetype")}@font-face{font-family:"KaTeX_SansSerif";font-style:italic;font-weight:400;src:url(fonts/KaTeX_SansSerif-Italic.woff2) format("woff2"),url(fonts/KaTeX_SansSerif-Italic.woff) format("woff"),url(fonts/KaTeX_SansSerif-Italic.ttf) format("truetype")}@font-face{font-family:"KaTeX_SansSerif";font-style:normal;font-weight:400;src:url(fonts/KaTeX_SansSerif-Regular.woff2) format("woff2"),url(fonts/KaTeX_SansSerif-Regular.woff) format("woff"),url(fonts/KaTeX_SansSerif-Regular.ttf) format("truetype")}@font-face{font-family:KaTeX_Script;font-style:normal;font-weight:400;src:url(fonts/KaTeX_Script-Regular.woff2) format("woff2"),url(fonts/KaTeX_Script-Regular.woff) format("woff"),url(fonts/KaTeX_Script-Regular.ttf) format("truetype")}@font-face{font-family:KaTeX_Size1;font-style:normal;font-weight:400;src:url(fonts/KaTeX_Size1-Regular.woff2) format("woff2"),url(fonts/KaTeX_Size1-Regular.woff) format("woff"),url(fonts/KaTeX_Size1-Regular.ttf) format("truetype")}@font-face{font-family:KaTeX_Size2;font-style:normal;font-weight:400;src:url(fonts/KaTeX_Size2-Regular.woff2) format("woff2"),url(fonts/KaTeX_Size2-Regular.woff) format("woff"),url(fonts/KaTeX_Size2-Regular.ttf) format("truetype")}@font-face{font-family:KaTeX_Size3;font-style:normal;font-weight:400;src:url(fonts/KaTeX_Size3-Regular.woff2) format("woff2"),url(fonts/KaTeX_Size3-Regular.woff) format("woff"),url(fonts/KaTeX_Size3-Regular.ttf) format("truetype")}@font-face{font-family:KaTeX_Size4;font-style:normal;font-weight:400;src:url(fonts/KaTeX_Size4-Regular.woff2) format("woff2"),url(fonts/KaTeX_Size4-Regular.woff) format("woff"),url(fonts/KaTeX_Size4-Regular.ttf) format("truetype")}@font-face{font-family:KaTeX_Typewriter;font-style:normal;font-weight:400;src:url(fonts/KaTeX_Typewriter-Regular.woff2) format("woff2"),url(fonts/KaTeX_Typewriter-Regular.woff) format("woff"),url(fonts/KaTeX_Typewriter-Regular.ttf) format("truetype")}.katex{font:normal 1.21em KaTeX_Main,Times New Roman,serif;line-height:1.2;text-indent:0;text-rendering:auto}.katex *{-ms-high-contrast-adjust:none!important;border-color:currentColor}.katex .katex-version:after{content:"0.16.22"}.katex .katex-mathml{clip:rect(1px,1px,1px,1px);border:0;height:1px;overflow:hidden;padding:0;position:absolute;width:1px}.katex .katex-html>.newline{display:block}.katex .base{position:relative;white-space:nowrap;width:-webkit-min-content;width:-moz-min-content;width:min-content}.katex .base,.katex .strut{display:inline-block}.katex .textbf{font-weight:700}.katex .textit{font-style:italic}.katex .textrm{font-family:KaTeX_Main}.katex .textsf{font-family:KaTeX_SansSerif}.katex .texttt{font-family:KaTeX_Typewriter}.katex .mathnormal{font-family:KaTeX_Math;font-style:italic}.katex .mathit{font-family:KaTeX_Main;font-style:italic}.katex .mathrm{font-style:normal}.katex .mathbf{font-family:KaTeX_Main;font-weight:700}.katex .boldsymbol{font-family:KaTeX_Math;font-style:italic;font-weight:700}.katex .amsrm,.katex .mathbb,.katex .textbb{font-family:KaTeX_AMS}.katex .mathcal{font-family:KaTeX_Caligraphic}.katex .mathfrak,.katex .textfrak{font-family:KaTeX_Fraktur}.katex .mathboldfrak,.katex .textboldfrak{font-family:KaTeX_Fraktur;font-weight:700}.katex .mathtt{font-family:KaTeX_Typewriter}.katex .mathscr,.katex .textscr{font-family:KaTeX_Script}.katex .mathsf,.katex .textsf{font-family:KaTeX_SansSerif}.katex .mathboldsf,.katex .textboldsf{font-family:KaTeX_SansSerif;font-weight:700}.katex .mathitsf,.katex .mathsfit,.katex .textitsf{font-family:KaTeX_SansSerif;font-style:italic}.katex .mainrm{font-family:KaTeX_Main;font-style:normal}.katex .vlist-t{border-collapse:collapse;display:inline-table;table-layout:fixed}.katex .vlist-r{display:table-row}.katex .vlist{display:table-cell;position:relative;vertical-align:bottom}.katex .vlist>span{display:block;height:0;position:relative}.katex .vlist>span>span{display:inline-block}.katex .vlist>span>.pstrut{overflow:hidden;width:0}.katex .vlist-t2{margin-right:-2px}.katex .vlist-s{display:table-cell;font-size:1px;min-width:2px;vertical-align:bottom;width:2px}.katex .vbox{align-items:baseline;display:inline-flex;flex-direction:column}.katex .hbox{width:100%}.katex .hbox,.katex .thinbox{display:inline-flex;flex-direction:row}.katex .thinbox{max-width:0;width:0}.katex .msupsub{text-align:left}.katex .mfrac>span>span{text-align:center}.katex .mfrac .frac-line{border-bottom-style:solid;display:inline-block;width:100%}.katex .hdashline,.katex .hline,.katex .mfrac .frac-line,.katex .overline .overline-line,.katex .rule,.katex .underline .underline-line{min-height:1px}.katex .mspace{display:inline-block}.katex .clap,.katex .llap,.katex .rlap{position:relative;width:0}.katex .clap>.inner,.katex .llap>.inner,.katex .rlap>.inner{position:absolute}.katex .clap>.fix,.katex .llap>.fix,.katex .rlap>.fix{display:inline-block}.katex .llap>.inner{right:0}.katex .clap>.inner,.katex .rlap>.inner{left:0}.katex .clap>.inner>span{margin-left:-50%;margin-right:50%}.katex .rule{border:0 solid;display:inline-block;position:relative}.katex .hline,.katex .overline .overline-line,.katex .underline .underline-line{border-bottom-style:solid;display:inline-block;width:100%}.katex .hdashline{border-bottom-style:dashed;display:inline-block;width:100%}.katex .sqrt>.root{margin-left:.2777777778em;margin-right:-.5555555556em}.katex .fontsize-ensurer.reset-size1.size1,.katex .sizing.reset-size1.size1{font-size:1em}.katex .fontsize-ensurer.reset-size1.size2,.katex .sizing.reset-size1.size2{font-size:1.2em}.katex .fontsize-ensurer.reset-size1.size3,.katex .sizing.reset-size1.size3{font-size:1.4em}.katex .fontsize-ensurer.reset-size1.size4,.katex .sizing.reset-size1.size4{font-size:1.6em}.katex .fontsize-ensurer.reset-size1.size5,.katex .sizing.reset-size1.size5{font-size:1.8em}.katex .fontsize-ensurer.reset-size1.size6,.katex .sizing.reset-size1.size6{font-size:2em}.katex .fontsize-ensurer.reset-size1.size7,.katex .sizing.reset-size1.size7{font-size:2.4em}.katex .fontsize-ensurer.reset-size1.size8,.katex .sizing.reset-size1.size8{font-size:2.88em}.katex .fontsize-ensurer.reset-size1.size9,.katex .sizing.reset-size1.size9{font-size:3.456em}.katex .fontsize-ensurer.reset-size1.size10,.katex .sizing.reset-size1.size10{font-size:4.148em}.katex .fontsize-ensurer.reset-size1.size11,.katex .sizing.reset-size1.size11{font-size:4.976em}.katex .fontsize-ensurer.reset-size2.size1,.katex .sizing.reset-size2.size1{font-size:.8333333333em}.katex .fontsize-ensurer.reset-size2.size2,.katex .sizing.reset-size2.size2{font-size:1em}.katex .fontsize-ensurer.reset-size2.size3,.katex .sizing.reset-size2.size3{font-size:1.1666666667em}.katex .fontsize-ensurer.reset-size2.size4,.katex .sizing.reset-size2.size4{font-size:1.3333333333em}.katex .fontsize-ensurer.reset-size2.size5,.katex .sizing.reset-size2.size5{font-size:1.5em}.katex .fontsize-ensurer.reset-size2.size6,.katex .sizing.reset-size2.size6{font-size:1.6666666667em}.katex .fontsize-ensurer.reset-size2.size7,.katex .sizing.reset-size2.size7{font-size:2em}.katex .fontsize-ensurer.reset-size2.size8,.katex .sizing.reset-size2.size8{font-size:2.4em}.katex .fontsize-ensurer.reset-size2.size9,.katex .sizing.reset-size2.size9{font-size:2.88em}.katex .fontsize-ensurer.reset-size2.size10,.katex .sizing.reset-size2.size10{font-size:3.4566666667em}.katex .fontsize-ensurer.reset-size2.size11,.katex .sizing.reset-size2.size11{font-size:4.1466666667em}.katex .fontsize-ensurer.reset-size3.size1,.katex .sizing.reset-size3.size1{font-size:.7142857143em}.katex .fontsize-ensurer.reset-size3.size2,.katex .sizing.reset-size3.size2{font-size:.8571428571em}.katex .fontsize-ensurer.reset-size3.size3,.katex .sizing.reset-size3.size3{font-size:1em}.katex .fontsize-ensurer.reset-size3.size4,.katex .sizing.reset-size3.size4{font-size:1.1428571429em}.katex .fontsize-ensurer.reset-size3.size5,.katex .sizing.reset-size3.size5{font-size:1.2857142857em}.katex .fontsize-ensurer.reset-size3.size6,.katex .sizing.reset-size3.size6{font-size:1.4285714286em}.katex .fontsize-ensurer.reset-size3.size7,.katex .sizing.reset-size3.size7{font-size:1.7142857143em}.katex .fontsize-ensurer.reset-size3.size8,.katex .sizing.reset-size3.size8{font-size:2.0571428571em}.katex .fontsize-ensurer.reset-size3.size9,.katex .sizing.reset-size3.size9{font-size:2.4685714286em}.katex .fontsize-ensurer.reset-size3.size10,.katex .sizing.reset-size3.size10{font-size:2.9628571429em}.katex .fontsize-ensurer.reset-size3.size11,.katex .sizing.reset-size3.size11{font-size:3.5542857143em}.katex .fontsize-ensurer.reset-size4.size1,.katex .sizing.reset-size4.size1{font-size:.625em}.katex .fontsize-ensurer.reset-size4.size2,.katex .sizing.reset-size4.size2{font-size:.75em}.katex .fontsize-ensurer.reset-size4.size3,.katex .sizing.reset-size4.size3{font-size:.875em}.katex .fontsize-ensurer.reset-size4.size4,.katex .sizing.reset-size4.size4{font-size:1em}.katex .fontsize-ensurer.reset-size4.size5,.katex .sizing.reset-size4.size5{font-size:1.125em}.katex .fontsize-ensurer.reset-size4.size6,.katex .sizing.reset-size4.size6{font-size:1.25em}.katex .fontsize-ensurer.reset-size4.size7,.katex .sizing.reset-size4.size7{font-size:1.5em}.katex .fontsize-ensurer.reset-size4.size8,.katex .sizing.reset-size4.size8{font-size:1.8em}.katex .fontsize-ensurer.reset-size4.size9,.katex .sizing.reset-size4.size9{font-size:2.16em}.katex .fontsize-ensurer.reset-size4.size10,.katex .sizing.reset-size4.size10{font-size:2.5925em}.katex .fontsize-ensurer.reset-size4.size11,.katex .sizing.reset-size4.size11{font-size:3.11em}.katex .fontsize-ensurer.reset-size5.size1,.katex .sizing.reset-size5.size1{font-size:.5555555556em}.katex .fontsize-ensurer.reset-size5.size2,.katex .sizing.reset-size5.size2{font-size:.6666666667em}.katex .fontsize-ensurer.reset-size5.size3,.katex .sizing.reset-size5.size3{font-size:.7777777778em}.katex .fontsize-ensurer.reset-size5.size4,.katex .sizing.reset-size5.size4{font-size:.8888888889em}.katex .fontsize-ensurer.reset-size5.size5,.katex .sizing.reset-size5.size5{font-size:1em}.katex .fontsize-ensurer.reset-size5.size6,.katex .sizing.reset-size5.size6{font-size:1.1111111111em}.katex .fontsize-ensurer.reset-size5.size7,.katex .sizing.reset-size5.size7{font-size:1.3333333333em}.katex .fontsize-ensurer.reset-size5.size8,.katex .sizing.reset-size5.size8{font-size:1.6em}.katex .fontsize-ensurer.reset-size5.size9,.katex .sizing.reset-size5.size9{font-size:1.92em}.katex .fontsize-ensurer.reset-size5.size10,.katex .sizing.reset-size5.size10{font-size:2.3044444444em}.katex .fontsize-ensurer.reset-size5.size11,.katex .sizing.reset-size5.size11{font-size:2.7644444444em}.katex .fontsize-ensurer.reset-size6.size1,.katex .sizing.reset-size6.size1{font-size:.5em}.katex .fontsize-ensurer.reset-size6.size2,.katex .sizing.reset-size6.size2{font-size:.6em}.katex .fontsize-ensurer.reset-size6.size3,.katex .sizing.reset-size6.size3{font-size:.7em}.katex .fontsize-ensurer.reset-size6.size4,.katex .sizing.reset-size6.size4{font-size:.8em}.katex .fontsize-ensurer.reset-size6.size5,.katex .sizing.reset-size6.size5{font-size:.9em}.katex .fontsize-ensurer.reset-size6.size6,.katex .sizing.reset-size6.size6{font-size:1em}.katex .fontsize-ensurer.reset-size6.size7,.katex .sizing.reset-size6.size7{font-size:1.2em}.katex .fontsize-ensurer.reset-size6.size8,.katex .sizing.reset-size6.size8{font-size:1.44em}.katex .fontsize-ensurer.reset-size6.size9,.katex .sizing.reset-size6.size9{font-size:1.728em}.katex .fontsize-ensurer.reset-size6.size10,.katex .sizing.reset-size6.size10{font-size:2.074em}.katex .fontsize-ensurer.reset-size6.size11,.katex .sizing.reset-size6.size11{font-size:2.488em}.katex .fontsize-ensurer.reset-size7.size1,.katex .sizing.reset-size7.size1{font-size:.4166666667em}.katex .fontsize-ensurer.reset-size7.size2,.katex .sizing.reset-size7.size2{font-size:.5em}.katex .fontsize-ensurer.reset-size7.size3,.katex .sizing.reset-size7.size3{font-size:.5833333333em}.katex .fontsize-ensurer.reset-size7.size4,.katex .sizing.reset-size7.size4{font-size:.6666666667em}.katex .fontsize-ensurer.reset-size7.size5,.katex .sizing.reset-size7.size5{font-size:.75em}.katex .fontsize-ensurer.reset-size7.size6,.katex .sizing.reset-size7.size6{font-size:.8333333333em}.katex .fontsize-ensurer.reset-size7.size7,.katex .sizing.reset-size7.size7{font-size:1em}.katex .fontsize-ensurer.reset-size7.size8,.katex .sizing.reset-size7.size8{font-size:1.2em}.katex .fontsize-ensurer.reset-size7.size9,.katex .sizing.reset-size7.size9{font-size:1.44em}.katex .fontsize-ensurer.reset-size7.size10,.katex .sizing.reset-size7.size10{font-size:1.7283333333em}.katex .fontsize-ensurer.reset-size7.size11,.katex .sizing.reset-size7.size11{font-size:2.0733333333em}.katex .fontsize-ensurer.reset-size8.size1,.katex .sizing.reset-size8.size1{font-size:.3472222222em}.katex .fontsize-ensurer.reset-size8.size2,.katex .sizing.reset-size8.size2{font-size:.4166666667em}.katex .fontsize-ensurer.reset-size8.size3,.katex .sizing.reset-size8.size3{font-size:.4861111111em}.katex .fontsize-ensurer.reset-size8.size4,.katex .sizing.reset-size8.size4{font-size:.5555555556em}.katex .fontsize-ensurer.reset-size8.size5,.katex .sizing.reset-size8.size5{font-size:.625em}.katex .fontsize-ensurer.reset-size8.size6,.katex .sizing.reset-size8.size6{font-size:.6944444444em}.katex .fontsize-ensurer.reset-size8.size7,.katex .sizing.reset-size8.size7{font-size:.8333333333em}.katex .fontsize-ensurer.reset-size8.size8,.katex .sizing.reset-size8.size8{font-size:1em}.katex .fontsize-ensurer.reset-size8.size9,.katex .sizing.reset-size8.size9{font-size:1.2em}.katex .fontsize-ensurer.reset-size8.size10,.katex .sizing.reset-size8.size10{font-size:1.4402777778em}.katex .fontsize-ensurer.reset-size8.size11,.katex .sizing.reset-size8.size11{font-size:1.7277777778em}.katex .fontsize-ensurer.reset-size9.size1,.katex .sizing.reset-size9.size1{font-size:.2893518519em}.katex .fontsize-ensurer.reset-size9.size2,.katex .sizing.reset-size9.size2{font-size:.3472222222em}.katex .fontsize-ensurer.reset-size9.size3,.katex .sizing.reset-size9.size3{font-size:.4050925926em}.katex .fontsize-ensurer.reset-size9.size4,.katex .sizing.reset-size9.size4{font-size:.462962963em}.katex .fontsize-ensurer.reset-size9.size5,.katex .sizing.reset-size9.size5{font-size:.5208333333em}.katex .fontsize-ensurer.reset-size9.size6,.katex .sizing.reset-size9.size6{font-size:.5787037037em}.katex .fontsize-ensurer.reset-size9.size7,.katex .sizing.reset-size9.size7{font-size:.6944444444em}.katex .fontsize-ensurer.reset-size9.size8,.katex .sizing.reset-size9.size8{font-size:.8333333333em}.katex .fontsize-ensurer.reset-size9.size9,.katex .sizing.reset-size9.size9{font-size:1em}.katex .fontsize-ensurer.reset-size9.size10,.katex .sizing.reset-size9.size10{font-size:1.2002314815em}.katex .fontsize-ensurer.reset-size9.size11,.katex .sizing.reset-size9.size11{font-size:1.4398148148em}.katex .fontsize-ensurer.reset-size10.size1,.katex .sizing.reset-size10.size1{font-size:.2410800386em}.katex .fontsize-ensurer.reset-size10.size2,.katex .sizing.reset-size10.size2{font-size:.2892960463em}.katex .fontsize-ensurer.reset-size10.size3,.katex .sizing.reset-size10.size3{font-size:.337512054em}.katex .fontsize-ensurer.reset-size10.size4,.katex .sizing.reset-size10.size4{font-size:.3857280617em}.katex .fontsize-ensurer.reset-size10.size5,.katex .sizing.reset-size10.size5{font-size:.4339440694em}.katex .fontsize-ensurer.reset-size10.size6,.katex .sizing.reset-size10.size6{font-size:.4821600771em}.katex .fontsize-ensurer.reset-size10.size7,.katex .sizing.reset-size10.size7{font-size:.5785920926em}.katex .fontsize-ensurer.reset-size10.size8,.katex .sizing.reset-size10.size8{font-size:.6943105111em}.katex .fontsize-ensurer.reset-size10.size9,.katex .sizing.reset-size10.size9{font-size:.8331726133em}.katex .fontsize-ensurer.reset-size10.size10,.katex .sizing.reset-size10.size10{font-size:1em}.katex .fontsize-ensurer.reset-size10.size11,.katex .sizing.reset-size10.size11{font-size:1.1996142719em}.katex .fontsize-ensurer.reset-size11.size1,.katex .sizing.reset-size11.size1{font-size:.2009646302em}.katex .fontsize-ensurer.reset-size11.size2,.katex .sizing.reset-size11.size2{font-size:.2411575563em}.katex .fontsize-ensurer.reset-size11.size3,.katex .sizing.reset-size11.size3{font-size:.2813504823em}.katex .fontsize-ensurer.reset-size11.size4,.katex .sizing.reset-size11.size4{font-size:.3215434084em}.katex .fontsize-ensurer.reset-size11.size5,.katex .sizing.reset-size11.size5{font-size:.3617363344em}.katex .fontsize-ensurer.reset-size11.size6,.katex .sizing.reset-size11.size6{font-size:.4019292605em}.katex .fontsize-ensurer.reset-size11.size7,.katex .sizing.reset-size11.size7{font-size:.4823151125em}.katex .fontsize-ensurer.reset-size11.size8,.katex .sizing.reset-size11.size8{font-size:.578778135em}.katex .fontsize-ensurer.reset-size11.size9,.katex .sizing.reset-size11.size9{font-size:.6945337621em}.katex .fontsize-ensurer.reset-size11.size10,.katex .sizing.reset-size11.size10{font-size:.8336012862em}.katex .fontsize-ensurer.reset-size11.size11,.katex .sizing.reset-size11.size11{font-size:1em}.katex .delimsizing.size1{font-family:KaTeX_Size1}.katex .delimsizing.size2{font-family:KaTeX_Size2}.katex .delimsizing.size3{font-family:KaTeX_Size3}.katex .delimsizing.size4{font-family:KaTeX_Size4}.katex .delimsizing.mult .delim-size1>span{font-family:KaTeX_Size1}.katex .delimsizing.mult .delim-size4>span{font-family:KaTeX_Size4}.katex .nulldelimiter{display:inline-block;width:.12em}.katex .delimcenter,.katex .op-symbol{position:relative}.katex .op-symbol.small-op{font-family:KaTeX_Size1}.katex .op-symbol.large-op{font-family:KaTeX_Size2}.katex .accent>.vlist-t,.katex .op-limits>.vlist-t{text-align:center}.katex .accent .accent-body{position:relative}.katex .accent .accent-body:not(.accent-full){width:0}.katex .overlay{display:block}.katex .mtable .vertical-separator{display:inline-block;min-width:1px}.katex .mtable .arraycolsep{display:inline-block}.katex .mtable .col-align-c>.vlist-t{text-align:center}.katex .mtable .col-align-l>.vlist-t{text-align:left}.katex .mtable .col-align-r>.vlist-t{text-align:right}.katex .svg-align{text-align:left}.katex svg{fill:currentColor;stroke:currentColor;fill-rule:nonzero;fill-opacity:1;stroke-width:1;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;display:block;height:inherit;position:absolute;width:100%}.katex svg path{stroke:none}.katex img{border-style:none;max-height:none;max-width:none;min-height:0;min-width:0}.katex .stretchy{display:block;overflow:hidden;position:relative;width:100%}.katex .stretchy:after,.katex .stretchy:before{content:""}.katex .hide-tail{overflow:hidden;position:relative;width:100%}.katex .halfarrow-left{left:0;overflow:hidden;position:absolute;width:50.2%}.katex .halfarrow-right{overflow:hidden;position:absolute;right:0;width:50.2%}.katex .brace-left{left:0;overflow:hidden;position:absolute;width:25.1%}.katex .brace-center{left:25%;overflow:hidden;position:absolute;width:50%}.katex .brace-right{overflow:hidden;position:absolute;right:0;width:25.1%}.katex .x-arrow-pad{padding:0 .5em}.katex .cd-arrow-pad{padding:0 .55556em 0 .27778em}.katex .mover,.katex .munder,.katex .x-arrow{text-align:center}.katex .boxpad{padding:0 .3em}.katex .fbox,.katex .fcolorbox{border:.04em solid;box-sizing:border-box}.katex .cancel-pad{padding:0 .2em}.katex .cancel-lap{margin-left:-.2em;margin-right:-.2em}.katex .sout{border-bottom-style:solid;border-bottom-width:.08em}.katex .angl{border-right:.049em solid;border-top:.049em solid;box-sizing:border-box;margin-right:.03889em}.katex .anglpad{padding:0 .03889em}.katex .eqn-num:before{content:"(" counter(katexEqnNo) ")";counter-increment:katexEqnNo}.katex .mml-eqn-num:before{content:"(" counter(mmlEqnNo) ")";counter-increment:mmlEqnNo}.katex .mtr-glue{width:50%}.katex .cd-vert-arrow{display:inline-block;position:relative}.katex .cd-label-left{display:inline-block;position:absolute;right:calc(50% + .3em);text-align:left}.katex .cd-label-right{display:inline-block;left:calc(50% + .3em);position:absolute;text-align:right}.katex-display{display:block;margin:1em 0;text-align:center}.katex-display>.katex{display:block;text-align:center;white-space:nowrap}.katex-display>.katex>.katex-html{display:block;position:relative}.katex-display>.katex>.katex-html>.tag{position:absolute;right:0}.katex-display.leqno>.katex>.katex-html>.tag{left:0;right:auto}.katex-display.fleqn>.katex{padding-left:2em;text-align:left}body{counter-reset:katexEqnNo mmlEqnNo} diff --git a/frontend/node_modules/katex/dist/katex.min.js b/frontend/node_modules/katex/dist/katex.min.js new file mode 100644 index 0000000..f59062a --- /dev/null +++ b/frontend/node_modules/katex/dist/katex.min.js @@ -0,0 +1 @@ +!function(e,t){"object"==typeof exports&&"object"==typeof module?module.exports=t():"function"==typeof define&&define.amd?define([],t):"object"==typeof exports?exports.katex=t():e.katex=t()}("undefined"!=typeof self?self:this,(function(){return function(){"use strict";var e={d:function(t,r){for(var n in r)e.o(r,n)&&!e.o(t,n)&&Object.defineProperty(t,n,{enumerable:!0,get:r[n]})},o:function(e,t){return Object.prototype.hasOwnProperty.call(e,t)}},t={};e.d(t,{default:function(){return Wn}});class r{constructor(e,t){this.name=void 0,this.position=void 0,this.length=void 0,this.rawMessage=void 0;let n,o,s="KaTeX parse error: "+e;const i=t&&t.loc;if(i&&i.start<=i.end){const e=i.lexer.input;n=i.start,o=i.end,n===e.length?s+=" at end of input: ":s+=" at position "+(n+1)+": ";const t=e.slice(n,o).replace(/[^]/g,"$&\u0332");let r,a;r=n>15?"\u2026"+e.slice(n-15,n):e.slice(0,n),a=o+15":">","<":"<",'"':""","'":"'"},i=/[&><"']/g;const a=function(e){return"ordgroup"===e.type||"color"===e.type?1===e.body.length?a(e.body[0]):e:"font"===e.type?a(e.body):e};var l={contains:function(e,t){return-1!==e.indexOf(t)},deflt:function(e,t){return void 0===e?t:e},escape:function(e){return String(e).replace(i,(e=>s[e]))},hyphenate:function(e){return e.replace(o,"-$1").toLowerCase()},getBaseElem:a,isCharacterBox:function(e){const t=a(e);return"mathord"===t.type||"textord"===t.type||"atom"===t.type},protocolFromUrl:function(e){const t=/^[\x00-\x20]*([^\\/#?]*?)(:|�*58|�*3a|&colon)/i.exec(e);return t?":"!==t[2]?null:/^[a-zA-Z][a-zA-Z0-9+\-.]*$/.test(t[1])?t[1].toLowerCase():null:"_relative"}};const h={displayMode:{type:"boolean",description:"Render math in display mode, which puts the math in display style (so \\int and \\sum are large, for example), and centers the math on the page on its own line.",cli:"-d, --display-mode"},output:{type:{enum:["htmlAndMathml","html","mathml"]},description:"Determines the markup language of the output.",cli:"-F, --format "},leqno:{type:"boolean",description:"Render display math in leqno style (left-justified tags)."},fleqn:{type:"boolean",description:"Render display math flush left."},throwOnError:{type:"boolean",default:!0,cli:"-t, --no-throw-on-error",cliDescription:"Render errors (in the color given by --error-color) instead of throwing a ParseError exception when encountering an error."},errorColor:{type:"string",default:"#cc0000",cli:"-c, --error-color ",cliDescription:"A color string given in the format 'rgb' or 'rrggbb' (no #). This option determines the color of errors rendered by the -t option.",cliProcessor:e=>"#"+e},macros:{type:"object",cli:"-m, --macro ",cliDescription:"Define custom macro of the form '\\foo:expansion' (use multiple -m arguments for multiple macros).",cliDefault:[],cliProcessor:(e,t)=>(t.push(e),t)},minRuleThickness:{type:"number",description:"Specifies a minimum thickness, in ems, for fraction lines, `\\sqrt` top lines, `{array}` vertical lines, `\\hline`, `\\hdashline`, `\\underline`, `\\overline`, and the borders of `\\fbox`, `\\boxed`, and `\\fcolorbox`.",processor:e=>Math.max(0,e),cli:"--min-rule-thickness ",cliProcessor:parseFloat},colorIsTextColor:{type:"boolean",description:"Makes \\color behave like LaTeX's 2-argument \\textcolor, instead of LaTeX's one-argument \\color mode change.",cli:"-b, --color-is-text-color"},strict:{type:[{enum:["warn","ignore","error"]},"boolean","function"],description:"Turn on strict / LaTeX faithfulness mode, which throws an error if the input uses features that are not supported by LaTeX.",cli:"-S, --strict",cliDefault:!1},trust:{type:["boolean","function"],description:"Trust the input, enabling all HTML features such as \\url.",cli:"-T, --trust"},maxSize:{type:"number",default:1/0,description:"If non-zero, all user-specified sizes, e.g. in \\rule{500em}{500em}, will be capped to maxSize ems. Otherwise, elements and spaces can be arbitrarily large",processor:e=>Math.max(0,e),cli:"-s, --max-size ",cliProcessor:parseInt},maxExpand:{type:"number",default:1e3,description:"Limit the number of macro expansions to the specified number, to prevent e.g. infinite macro loops. If set to Infinity, the macro expander will try to fully expand as in LaTeX.",processor:e=>Math.max(0,e),cli:"-e, --max-expand ",cliProcessor:e=>"Infinity"===e?1/0:parseInt(e)},globalGroup:{type:"boolean",cli:!1}};function c(e){if(e.default)return e.default;const t=e.type,r=Array.isArray(t)?t[0]:t;if("string"!=typeof r)return r.enum[0];switch(r){case"boolean":return!1;case"string":return"";case"number":return 0;case"object":return{}}}class m{constructor(e){this.displayMode=void 0,this.output=void 0,this.leqno=void 0,this.fleqn=void 0,this.throwOnError=void 0,this.errorColor=void 0,this.macros=void 0,this.minRuleThickness=void 0,this.colorIsTextColor=void 0,this.strict=void 0,this.trust=void 0,this.maxSize=void 0,this.maxExpand=void 0,this.globalGroup=void 0,e=e||{};for(const t in h)if(h.hasOwnProperty(t)){const r=h[t];this[t]=void 0!==e[t]?r.processor?r.processor(e[t]):e[t]:c(r)}}reportNonstrict(e,t,r){let o=this.strict;if("function"==typeof o&&(o=o(e,t,r)),o&&"ignore"!==o){if(!0===o||"error"===o)throw new n("LaTeX-incompatible input and strict mode is set to 'error': "+t+" ["+e+"]",r);"warn"===o?"undefined"!=typeof console&&console.warn("LaTeX-incompatible input and strict mode is set to 'warn': "+t+" ["+e+"]"):"undefined"!=typeof console&&console.warn("LaTeX-incompatible input and strict mode is set to unrecognized '"+o+"': "+t+" ["+e+"]")}}useStrictBehavior(e,t,r){let n=this.strict;if("function"==typeof n)try{n=n(e,t,r)}catch(e){n="error"}return!(!n||"ignore"===n)&&(!0===n||"error"===n||("warn"===n?("undefined"!=typeof console&&console.warn("LaTeX-incompatible input and strict mode is set to 'warn': "+t+" ["+e+"]"),!1):("undefined"!=typeof console&&console.warn("LaTeX-incompatible input and strict mode is set to unrecognized '"+n+"': "+t+" ["+e+"]"),!1)))}isTrusted(e){if(e.url&&!e.protocol){const t=l.protocolFromUrl(e.url);if(null==t)return!1;e.protocol=t}const t="function"==typeof this.trust?this.trust(e):this.trust;return Boolean(t)}}class p{constructor(e,t,r){this.id=void 0,this.size=void 0,this.cramped=void 0,this.id=e,this.size=t,this.cramped=r}sup(){return u[d[this.id]]}sub(){return u[g[this.id]]}fracNum(){return u[f[this.id]]}fracDen(){return u[b[this.id]]}cramp(){return u[y[this.id]]}text(){return u[x[this.id]]}isTight(){return this.size>=2}}const u=[new p(0,0,!1),new p(1,0,!0),new p(2,1,!1),new p(3,1,!0),new p(4,2,!1),new p(5,2,!0),new p(6,3,!1),new p(7,3,!0)],d=[4,5,4,5,6,7,6,7],g=[5,5,5,5,7,7,7,7],f=[2,3,4,5,6,7,6,7],b=[3,3,5,5,7,7,7,7],y=[1,1,3,3,5,5,7,7],x=[0,1,2,3,2,3,2,3];var w={DISPLAY:u[0],TEXT:u[2],SCRIPT:u[4],SCRIPTSCRIPT:u[6]};const v=[{name:"latin",blocks:[[256,591],[768,879]]},{name:"cyrillic",blocks:[[1024,1279]]},{name:"armenian",blocks:[[1328,1423]]},{name:"brahmic",blocks:[[2304,4255]]},{name:"georgian",blocks:[[4256,4351]]},{name:"cjk",blocks:[[12288,12543],[19968,40879],[65280,65376]]},{name:"hangul",blocks:[[44032,55215]]}];const k=[];function S(e){for(let t=0;t=k[t]&&e<=k[t+1])return!0;return!1}v.forEach((e=>e.blocks.forEach((e=>k.push(...e)))));const M=80,z={doubleleftarrow:"M262 157\nl10-10c34-36 62.7-77 86-123 3.3-8 5-13.3 5-16 0-5.3-6.7-8-20-8-7.3\n 0-12.2.5-14.5 1.5-2.3 1-4.8 4.5-7.5 10.5-49.3 97.3-121.7 169.3-217 216-28\n 14-57.3 25-88 33-6.7 2-11 3.8-13 5.5-2 1.7-3 4.2-3 7.5s1 5.8 3 7.5\nc2 1.7 6.3 3.5 13 5.5 68 17.3 128.2 47.8 180.5 91.5 52.3 43.7 93.8 96.2 124.5\n 157.5 9.3 8 15.3 12.3 18 13h6c12-.7 18-4 18-10 0-2-1.7-7-5-15-23.3-46-52-87\n-86-123l-10-10h399738v-40H218c328 0 0 0 0 0l-10-8c-26.7-20-65.7-43-117-69 2.7\n-2 6-3.7 10-5 36.7-16 72.3-37.3 107-64l10-8h399782v-40z\nm8 0v40h399730v-40zm0 194v40h399730v-40z",doublerightarrow:"M399738 392l\n-10 10c-34 36-62.7 77-86 123-3.3 8-5 13.3-5 16 0 5.3 6.7 8 20 8 7.3 0 12.2-.5\n 14.5-1.5 2.3-1 4.8-4.5 7.5-10.5 49.3-97.3 121.7-169.3 217-216 28-14 57.3-25 88\n-33 6.7-2 11-3.8 13-5.5 2-1.7 3-4.2 3-7.5s-1-5.8-3-7.5c-2-1.7-6.3-3.5-13-5.5-68\n-17.3-128.2-47.8-180.5-91.5-52.3-43.7-93.8-96.2-124.5-157.5-9.3-8-15.3-12.3-18\n-13h-6c-12 .7-18 4-18 10 0 2 1.7 7 5 15 23.3 46 52 87 86 123l10 10H0v40h399782\nc-328 0 0 0 0 0l10 8c26.7 20 65.7 43 117 69-2.7 2-6 3.7-10 5-36.7 16-72.3 37.3\n-107 64l-10 8H0v40zM0 157v40h399730v-40zm0 194v40h399730v-40z",leftarrow:"M400000 241H110l3-3c68.7-52.7 113.7-120\n 135-202 4-14.7 6-23 6-25 0-7.3-7-11-21-11-8 0-13.2.8-15.5 2.5-2.3 1.7-4.2 5.8\n-5.5 12.5-1.3 4.7-2.7 10.3-4 17-12 48.7-34.8 92-68.5 130S65.3 228.3 18 247\nc-10 4-16 7.7-18 11 0 8.7 6 14.3 18 17 47.3 18.7 87.8 47 121.5 85S196 441.3 208\n 490c.7 2 1.3 5 2 9s1.2 6.7 1.5 8c.3 1.3 1 3.3 2 6s2.2 4.5 3.5 5.5c1.3 1 3.3\n 1.8 6 2.5s6 1 10 1c14 0 21-3.7 21-11 0-2-2-10.3-6-25-20-79.3-65-146.7-135-202\n l-3-3h399890zM100 241v40h399900v-40z",leftbrace:"M6 548l-6-6v-35l6-11c56-104 135.3-181.3 238-232 57.3-28.7 117\n-45 179-50h399577v120H403c-43.3 7-81 15-113 26-100.7 33-179.7 91-237 174-2.7\n 5-6 9-10 13-.7 1-7.3 1-20 1H6z",leftbraceunder:"M0 6l6-6h17c12.688 0 19.313.3 20 1 4 4 7.313 8.3 10 13\n 35.313 51.3 80.813 93.8 136.5 127.5 55.688 33.7 117.188 55.8 184.5 66.5.688\n 0 2 .3 4 1 18.688 2.7 76 4.3 172 5h399450v120H429l-6-1c-124.688-8-235-61.7\n-331-161C60.687 138.7 32.312 99.3 7 54L0 41V6z",leftgroup:"M400000 80\nH435C64 80 168.3 229.4 21 260c-5.9 1.2-18 0-18 0-2 0-3-1-3-3v-38C76 61 257 0\n 435 0h399565z",leftgroupunder:"M400000 262\nH435C64 262 168.3 112.6 21 82c-5.9-1.2-18 0-18 0-2 0-3 1-3 3v38c76 158 257 219\n 435 219h399565z",leftharpoon:"M0 267c.7 5.3 3 10 7 14h399993v-40H93c3.3\n-3.3 10.2-9.5 20.5-18.5s17.8-15.8 22.5-20.5c50.7-52 88-110.3 112-175 4-11.3 5\n-18.3 3-21-1.3-4-7.3-6-18-6-8 0-13 .7-15 2s-4.7 6.7-8 16c-42 98.7-107.3 174.7\n-196 228-6.7 4.7-10.7 8-12 10-1.3 2-2 5.7-2 11zm100-26v40h399900v-40z",leftharpoonplus:"M0 267c.7 5.3 3 10 7 14h399993v-40H93c3.3-3.3 10.2-9.5\n 20.5-18.5s17.8-15.8 22.5-20.5c50.7-52 88-110.3 112-175 4-11.3 5-18.3 3-21-1.3\n-4-7.3-6-18-6-8 0-13 .7-15 2s-4.7 6.7-8 16c-42 98.7-107.3 174.7-196 228-6.7 4.7\n-10.7 8-12 10-1.3 2-2 5.7-2 11zm100-26v40h399900v-40zM0 435v40h400000v-40z\nm0 0v40h400000v-40z",leftharpoondown:"M7 241c-4 4-6.333 8.667-7 14 0 5.333.667 9 2 11s5.333\n 5.333 12 10c90.667 54 156 130 196 228 3.333 10.667 6.333 16.333 9 17 2 .667 5\n 1 9 1h5c10.667 0 16.667-2 18-6 2-2.667 1-9.667-3-21-32-87.333-82.667-157.667\n-152-211l-3-3h399907v-40zM93 281 H400000 v-40L7 241z",leftharpoondownplus:"M7 435c-4 4-6.3 8.7-7 14 0 5.3.7 9 2 11s5.3 5.3 12\n 10c90.7 54 156 130 196 228 3.3 10.7 6.3 16.3 9 17 2 .7 5 1 9 1h5c10.7 0 16.7\n-2 18-6 2-2.7 1-9.7-3-21-32-87.3-82.7-157.7-152-211l-3-3h399907v-40H7zm93 0\nv40h399900v-40zM0 241v40h399900v-40zm0 0v40h399900v-40z",lefthook:"M400000 281 H103s-33-11.2-61-33.5S0 197.3 0 164s14.2-61.2 42.5\n-83.5C70.8 58.2 104 47 142 47 c16.7 0 25 6.7 25 20 0 12-8.7 18.7-26 20-40 3.3\n-68.7 15.7-86 37-10 12-15 25.3-15 40 0 22.7 9.8 40.7 29.5 54 19.7 13.3 43.5 21\n 71.5 23h399859zM103 281v-40h399897v40z",leftlinesegment:"M40 281 V428 H0 V94 H40 V241 H400000 v40z\nM40 281 V428 H0 V94 H40 V241 H400000 v40z",leftmapsto:"M40 281 V448H0V74H40V241H400000v40z\nM40 281 V448H0V74H40V241H400000v40z",leftToFrom:"M0 147h400000v40H0zm0 214c68 40 115.7 95.7 143 167h22c15.3 0 23\n-.3 23-1 0-1.3-5.3-13.7-16-37-18-35.3-41.3-69-70-101l-7-8h399905v-40H95l7-8\nc28.7-32 52-65.7 70-101 10.7-23.3 16-35.7 16-37 0-.7-7.7-1-23-1h-22C115.7 265.3\n 68 321 0 361zm0-174v-40h399900v40zm100 154v40h399900v-40z",longequal:"M0 50 h400000 v40H0z m0 194h40000v40H0z\nM0 50 h400000 v40H0z m0 194h40000v40H0z",midbrace:"M200428 334\nc-100.7-8.3-195.3-44-280-108-55.3-42-101.7-93-139-153l-9-14c-2.7 4-5.7 8.7-9 14\n-53.3 86.7-123.7 153-211 199-66.7 36-137.3 56.3-212 62H0V214h199568c178.3-11.7\n 311.7-78.3 403-201 6-8 9.7-12 11-12 .7-.7 6.7-1 18-1s17.3.3 18 1c1.3 0 5 4 11\n 12 44.7 59.3 101.3 106.3 170 141s145.3 54.3 229 60h199572v120z",midbraceunder:"M199572 214\nc100.7 8.3 195.3 44 280 108 55.3 42 101.7 93 139 153l9 14c2.7-4 5.7-8.7 9-14\n 53.3-86.7 123.7-153 211-199 66.7-36 137.3-56.3 212-62h199568v120H200432c-178.3\n 11.7-311.7 78.3-403 201-6 8-9.7 12-11 12-.7.7-6.7 1-18 1s-17.3-.3-18-1c-1.3 0\n-5-4-11-12-44.7-59.3-101.3-106.3-170-141s-145.3-54.3-229-60H0V214z",oiintSize1:"M512.6 71.6c272.6 0 320.3 106.8 320.3 178.2 0 70.8-47.7 177.6\n-320.3 177.6S193.1 320.6 193.1 249.8c0-71.4 46.9-178.2 319.5-178.2z\nm368.1 178.2c0-86.4-60.9-215.4-368.1-215.4-306.4 0-367.3 129-367.3 215.4 0 85.8\n60.9 214.8 367.3 214.8 307.2 0 368.1-129 368.1-214.8z",oiintSize2:"M757.8 100.1c384.7 0 451.1 137.6 451.1 230 0 91.3-66.4 228.8\n-451.1 228.8-386.3 0-452.7-137.5-452.7-228.8 0-92.4 66.4-230 452.7-230z\nm502.4 230c0-111.2-82.4-277.2-502.4-277.2s-504 166-504 277.2\nc0 110 84 276 504 276s502.4-166 502.4-276z",oiiintSize1:"M681.4 71.6c408.9 0 480.5 106.8 480.5 178.2 0 70.8-71.6 177.6\n-480.5 177.6S202.1 320.6 202.1 249.8c0-71.4 70.5-178.2 479.3-178.2z\nm525.8 178.2c0-86.4-86.8-215.4-525.7-215.4-437.9 0-524.7 129-524.7 215.4 0\n85.8 86.8 214.8 524.7 214.8 438.9 0 525.7-129 525.7-214.8z",oiiintSize2:"M1021.2 53c603.6 0 707.8 165.8 707.8 277.2 0 110-104.2 275.8\n-707.8 275.8-606 0-710.2-165.8-710.2-275.8C311 218.8 415.2 53 1021.2 53z\nm770.4 277.1c0-131.2-126.4-327.6-770.5-327.6S248.4 198.9 248.4 330.1\nc0 130 128.8 326.4 772.7 326.4s770.5-196.4 770.5-326.4z",rightarrow:"M0 241v40h399891c-47.3 35.3-84 78-110 128\n-16.7 32-27.7 63.7-33 95 0 1.3-.2 2.7-.5 4-.3 1.3-.5 2.3-.5 3 0 7.3 6.7 11 20\n 11 8 0 13.2-.8 15.5-2.5 2.3-1.7 4.2-5.5 5.5-11.5 2-13.3 5.7-27 11-41 14.7-44.7\n 39-84.5 73-119.5s73.7-60.2 119-75.5c6-2 9-5.7 9-11s-3-9-9-11c-45.3-15.3-85\n-40.5-119-75.5s-58.3-74.8-73-119.5c-4.7-14-8.3-27.3-11-40-1.3-6.7-3.2-10.8-5.5\n-12.5-2.3-1.7-7.5-2.5-15.5-2.5-14 0-21 3.7-21 11 0 2 2 10.3 6 25 20.7 83.3 67\n 151.7 139 205zm0 0v40h399900v-40z",rightbrace:"M400000 542l\n-6 6h-17c-12.7 0-19.3-.3-20-1-4-4-7.3-8.3-10-13-35.3-51.3-80.8-93.8-136.5-127.5\ns-117.2-55.8-184.5-66.5c-.7 0-2-.3-4-1-18.7-2.7-76-4.3-172-5H0V214h399571l6 1\nc124.7 8 235 61.7 331 161 31.3 33.3 59.7 72.7 85 118l7 13v35z",rightbraceunder:"M399994 0l6 6v35l-6 11c-56 104-135.3 181.3-238 232-57.3\n 28.7-117 45-179 50H-300V214h399897c43.3-7 81-15 113-26 100.7-33 179.7-91 237\n-174 2.7-5 6-9 10-13 .7-1 7.3-1 20-1h17z",rightgroup:"M0 80h399565c371 0 266.7 149.4 414 180 5.9 1.2 18 0 18 0 2 0\n 3-1 3-3v-38c-76-158-257-219-435-219H0z",rightgroupunder:"M0 262h399565c371 0 266.7-149.4 414-180 5.9-1.2 18 0 18\n 0 2 0 3 1 3 3v38c-76 158-257 219-435 219H0z",rightharpoon:"M0 241v40h399993c4.7-4.7 7-9.3 7-14 0-9.3\n-3.7-15.3-11-18-92.7-56.7-159-133.7-199-231-3.3-9.3-6-14.7-8-16-2-1.3-7-2-15-2\n-10.7 0-16.7 2-18 6-2 2.7-1 9.7 3 21 15.3 42 36.7 81.8 64 119.5 27.3 37.7 58\n 69.2 92 94.5zm0 0v40h399900v-40z",rightharpoonplus:"M0 241v40h399993c4.7-4.7 7-9.3 7-14 0-9.3-3.7-15.3-11\n-18-92.7-56.7-159-133.7-199-231-3.3-9.3-6-14.7-8-16-2-1.3-7-2-15-2-10.7 0-16.7\n 2-18 6-2 2.7-1 9.7 3 21 15.3 42 36.7 81.8 64 119.5 27.3 37.7 58 69.2 92 94.5z\nm0 0v40h399900v-40z m100 194v40h399900v-40zm0 0v40h399900v-40z",rightharpoondown:"M399747 511c0 7.3 6.7 11 20 11 8 0 13-.8 15-2.5s4.7-6.8\n 8-15.5c40-94 99.3-166.3 178-217 13.3-8 20.3-12.3 21-13 5.3-3.3 8.5-5.8 9.5\n-7.5 1-1.7 1.5-5.2 1.5-10.5s-2.3-10.3-7-15H0v40h399908c-34 25.3-64.7 57-92 95\n-27.3 38-48.7 77.7-64 119-3.3 8.7-5 14-5 16zM0 241v40h399900v-40z",rightharpoondownplus:"M399747 705c0 7.3 6.7 11 20 11 8 0 13-.8\n 15-2.5s4.7-6.8 8-15.5c40-94 99.3-166.3 178-217 13.3-8 20.3-12.3 21-13 5.3-3.3\n 8.5-5.8 9.5-7.5 1-1.7 1.5-5.2 1.5-10.5s-2.3-10.3-7-15H0v40h399908c-34 25.3\n-64.7 57-92 95-27.3 38-48.7 77.7-64 119-3.3 8.7-5 14-5 16zM0 435v40h399900v-40z\nm0-194v40h400000v-40zm0 0v40h400000v-40z",righthook:"M399859 241c-764 0 0 0 0 0 40-3.3 68.7-15.7 86-37 10-12 15-25.3\n 15-40 0-22.7-9.8-40.7-29.5-54-19.7-13.3-43.5-21-71.5-23-17.3-1.3-26-8-26-20 0\n-13.3 8.7-20 26-20 38 0 71 11.2 99 33.5 0 0 7 5.6 21 16.7 14 11.2 21 33.5 21\n 66.8s-14 61.2-42 83.5c-28 22.3-61 33.5-99 33.5L0 241z M0 281v-40h399859v40z",rightlinesegment:"M399960 241 V94 h40 V428 h-40 V281 H0 v-40z\nM399960 241 V94 h40 V428 h-40 V281 H0 v-40z",rightToFrom:"M400000 167c-70.7-42-118-97.7-142-167h-23c-15.3 0-23 .3-23\n 1 0 1.3 5.3 13.7 16 37 18 35.3 41.3 69 70 101l7 8H0v40h399905l-7 8c-28.7 32\n-52 65.7-70 101-10.7 23.3-16 35.7-16 37 0 .7 7.7 1 23 1h23c24-69.3 71.3-125 142\n-167z M100 147v40h399900v-40zM0 341v40h399900v-40z",twoheadleftarrow:"M0 167c68 40\n 115.7 95.7 143 167h22c15.3 0 23-.3 23-1 0-1.3-5.3-13.7-16-37-18-35.3-41.3-69\n-70-101l-7-8h125l9 7c50.7 39.3 85 86 103 140h46c0-4.7-6.3-18.7-19-42-18-35.3\n-40-67.3-66-96l-9-9h399716v-40H284l9-9c26-28.7 48-60.7 66-96 12.7-23.333 19\n-37.333 19-42h-46c-18 54-52.3 100.7-103 140l-9 7H95l7-8c28.7-32 52-65.7 70-101\n 10.7-23.333 16-35.7 16-37 0-.7-7.7-1-23-1h-22C115.7 71.3 68 127 0 167z",twoheadrightarrow:"M400000 167\nc-68-40-115.7-95.7-143-167h-22c-15.3 0-23 .3-23 1 0 1.3 5.3 13.7 16 37 18 35.3\n 41.3 69 70 101l7 8h-125l-9-7c-50.7-39.3-85-86-103-140h-46c0 4.7 6.3 18.7 19 42\n 18 35.3 40 67.3 66 96l9 9H0v40h399716l-9 9c-26 28.7-48 60.7-66 96-12.7 23.333\n-19 37.333-19 42h46c18-54 52.3-100.7 103-140l9-7h125l-7 8c-28.7 32-52 65.7-70\n 101-10.7 23.333-16 35.7-16 37 0 .7 7.7 1 23 1h22c27.3-71.3 75-127 143-167z",tilde1:"M200 55.538c-77 0-168 73.953-177 73.953-3 0-7\n-2.175-9-5.437L2 97c-1-2-2-4-2-6 0-4 2-7 5-9l20-12C116 12 171 0 207 0c86 0\n 114 68 191 68 78 0 168-68 177-68 4 0 7 2 9 5l12 19c1 2.175 2 4.35 2 6.525 0\n 4.35-2 7.613-5 9.788l-19 13.05c-92 63.077-116.937 75.308-183 76.128\n-68.267.847-113-73.952-191-73.952z",tilde2:"M344 55.266c-142 0-300.638 81.316-311.5 86.418\n-8.01 3.762-22.5 10.91-23.5 5.562L1 120c-1-2-1-3-1-4 0-5 3-9 8-10l18.4-9C160.9\n 31.9 283 0 358 0c148 0 188 122 331 122s314-97 326-97c4 0 8 2 10 7l7 21.114\nc1 2.14 1 3.21 1 4.28 0 5.347-3 9.626-7 10.696l-22.3 12.622C852.6 158.372 751\n 181.476 676 181.476c-149 0-189-126.21-332-126.21z",tilde3:"M786 59C457 59 32 175.242 13 175.242c-6 0-10-3.457\n-11-10.37L.15 138c-1-7 3-12 10-13l19.2-6.4C378.4 40.7 634.3 0 804.3 0c337 0\n 411.8 157 746.8 157 328 0 754-112 773-112 5 0 10 3 11 9l1 14.075c1 8.066-.697\n 16.595-6.697 17.492l-21.052 7.31c-367.9 98.146-609.15 122.696-778.15 122.696\n -338 0-409-156.573-744-156.573z",tilde4:"M786 58C457 58 32 177.487 13 177.487c-6 0-10-3.345\n-11-10.035L.15 143c-1-7 3-12 10-13l22-6.7C381.2 35 637.15 0 807.15 0c337 0 409\n 177 744 177 328 0 754-127 773-127 5 0 10 3 11 9l1 14.794c1 7.805-3 13.38-9\n 14.495l-20.7 5.574c-366.85 99.79-607.3 139.372-776.3 139.372-338 0-409\n -175.236-744-175.236z",vec:"M377 20c0-5.333 1.833-10 5.5-14S391 0 397 0c4.667 0 8.667 1.667 12 5\n3.333 2.667 6.667 9 10 19 6.667 24.667 20.333 43.667 41 57 7.333 4.667 11\n10.667 11 18 0 6-1 10-3 12s-6.667 5-14 9c-28.667 14.667-53.667 35.667-75 63\n-1.333 1.333-3.167 3.5-5.5 6.5s-4 4.833-5 5.5c-1 .667-2.5 1.333-4.5 2s-4.333 1\n-7 1c-4.667 0-9.167-1.833-13.5-5.5S337 184 337 178c0-12.667 15.667-32.333 47-59\nH213l-171-1c-8.667-6-13-12.333-13-19 0-4.667 4.333-11.333 13-20h359\nc-16-25.333-24-45-24-59z",widehat1:"M529 0h5l519 115c5 1 9 5 9 10 0 1-1 2-1 3l-4 22\nc-1 5-5 9-11 9h-2L532 67 19 159h-2c-5 0-9-4-11-9l-5-22c-1-6 2-12 8-13z",widehat2:"M1181 0h2l1171 176c6 0 10 5 10 11l-2 23c-1 6-5 10\n-11 10h-1L1182 67 15 220h-1c-6 0-10-4-11-10l-2-23c-1-6 4-11 10-11z",widehat3:"M1181 0h2l1171 236c6 0 10 5 10 11l-2 23c-1 6-5 10\n-11 10h-1L1182 67 15 280h-1c-6 0-10-4-11-10l-2-23c-1-6 4-11 10-11z",widehat4:"M1181 0h2l1171 296c6 0 10 5 10 11l-2 23c-1 6-5 10\n-11 10h-1L1182 67 15 340h-1c-6 0-10-4-11-10l-2-23c-1-6 4-11 10-11z",widecheck1:"M529,159h5l519,-115c5,-1,9,-5,9,-10c0,-1,-1,-2,-1,-3l-4,-22c-1,\n-5,-5,-9,-11,-9h-2l-512,92l-513,-92h-2c-5,0,-9,4,-11,9l-5,22c-1,6,2,12,8,13z",widecheck2:"M1181,220h2l1171,-176c6,0,10,-5,10,-11l-2,-23c-1,-6,-5,-10,\n-11,-10h-1l-1168,153l-1167,-153h-1c-6,0,-10,4,-11,10l-2,23c-1,6,4,11,10,11z",widecheck3:"M1181,280h2l1171,-236c6,0,10,-5,10,-11l-2,-23c-1,-6,-5,-10,\n-11,-10h-1l-1168,213l-1167,-213h-1c-6,0,-10,4,-11,10l-2,23c-1,6,4,11,10,11z",widecheck4:"M1181,340h2l1171,-296c6,0,10,-5,10,-11l-2,-23c-1,-6,-5,-10,\n-11,-10h-1l-1168,273l-1167,-273h-1c-6,0,-10,4,-11,10l-2,23c-1,6,4,11,10,11z",baraboveleftarrow:"M400000 620h-399890l3 -3c68.7 -52.7 113.7 -120 135 -202\nc4 -14.7 6 -23 6 -25c0 -7.3 -7 -11 -21 -11c-8 0 -13.2 0.8 -15.5 2.5\nc-2.3 1.7 -4.2 5.8 -5.5 12.5c-1.3 4.7 -2.7 10.3 -4 17c-12 48.7 -34.8 92 -68.5 130\ns-74.2 66.3 -121.5 85c-10 4 -16 7.7 -18 11c0 8.7 6 14.3 18 17c47.3 18.7 87.8 47\n121.5 85s56.5 81.3 68.5 130c0.7 2 1.3 5 2 9s1.2 6.7 1.5 8c0.3 1.3 1 3.3 2 6\ns2.2 4.5 3.5 5.5c1.3 1 3.3 1.8 6 2.5s6 1 10 1c14 0 21 -3.7 21 -11\nc0 -2 -2 -10.3 -6 -25c-20 -79.3 -65 -146.7 -135 -202l-3 -3h399890z\nM100 620v40h399900v-40z M0 241v40h399900v-40zM0 241v40h399900v-40z",rightarrowabovebar:"M0 241v40h399891c-47.3 35.3-84 78-110 128-16.7 32\n-27.7 63.7-33 95 0 1.3-.2 2.7-.5 4-.3 1.3-.5 2.3-.5 3 0 7.3 6.7 11 20 11 8 0\n13.2-.8 15.5-2.5 2.3-1.7 4.2-5.5 5.5-11.5 2-13.3 5.7-27 11-41 14.7-44.7 39\n-84.5 73-119.5s73.7-60.2 119-75.5c6-2 9-5.7 9-11s-3-9-9-11c-45.3-15.3-85-40.5\n-119-75.5s-58.3-74.8-73-119.5c-4.7-14-8.3-27.3-11-40-1.3-6.7-3.2-10.8-5.5\n-12.5-2.3-1.7-7.5-2.5-15.5-2.5-14 0-21 3.7-21 11 0 2 2 10.3 6 25 20.7 83.3 67\n151.7 139 205zm96 379h399894v40H0zm0 0h399904v40H0z",baraboveshortleftharpoon:"M507,435c-4,4,-6.3,8.7,-7,14c0,5.3,0.7,9,2,11\nc1.3,2,5.3,5.3,12,10c90.7,54,156,130,196,228c3.3,10.7,6.3,16.3,9,17\nc2,0.7,5,1,9,1c0,0,5,0,5,0c10.7,0,16.7,-2,18,-6c2,-2.7,1,-9.7,-3,-21\nc-32,-87.3,-82.7,-157.7,-152,-211c0,0,-3,-3,-3,-3l399351,0l0,-40\nc-398570,0,-399437,0,-399437,0z M593 435 v40 H399500 v-40z\nM0 281 v-40 H399908 v40z M0 281 v-40 H399908 v40z",rightharpoonaboveshortbar:"M0,241 l0,40c399126,0,399993,0,399993,0\nc4.7,-4.7,7,-9.3,7,-14c0,-9.3,-3.7,-15.3,-11,-18c-92.7,-56.7,-159,-133.7,-199,\n-231c-3.3,-9.3,-6,-14.7,-8,-16c-2,-1.3,-7,-2,-15,-2c-10.7,0,-16.7,2,-18,6\nc-2,2.7,-1,9.7,3,21c15.3,42,36.7,81.8,64,119.5c27.3,37.7,58,69.2,92,94.5z\nM0 241 v40 H399908 v-40z M0 475 v-40 H399500 v40z M0 475 v-40 H399500 v40z",shortbaraboveleftharpoon:"M7,435c-4,4,-6.3,8.7,-7,14c0,5.3,0.7,9,2,11\nc1.3,2,5.3,5.3,12,10c90.7,54,156,130,196,228c3.3,10.7,6.3,16.3,9,17c2,0.7,5,1,9,\n1c0,0,5,0,5,0c10.7,0,16.7,-2,18,-6c2,-2.7,1,-9.7,-3,-21c-32,-87.3,-82.7,-157.7,\n-152,-211c0,0,-3,-3,-3,-3l399907,0l0,-40c-399126,0,-399993,0,-399993,0z\nM93 435 v40 H400000 v-40z M500 241 v40 H400000 v-40z M500 241 v40 H400000 v-40z",shortrightharpoonabovebar:"M53,241l0,40c398570,0,399437,0,399437,0\nc4.7,-4.7,7,-9.3,7,-14c0,-9.3,-3.7,-15.3,-11,-18c-92.7,-56.7,-159,-133.7,-199,\n-231c-3.3,-9.3,-6,-14.7,-8,-16c-2,-1.3,-7,-2,-15,-2c-10.7,0,-16.7,2,-18,6\nc-2,2.7,-1,9.7,3,21c15.3,42,36.7,81.8,64,119.5c27.3,37.7,58,69.2,92,94.5z\nM500 241 v40 H399408 v-40z M500 435 v40 H400000 v-40z"};class A{constructor(e){this.children=void 0,this.classes=void 0,this.height=void 0,this.depth=void 0,this.maxFontSize=void 0,this.style=void 0,this.children=e,this.classes=[],this.height=0,this.depth=0,this.maxFontSize=0,this.style={}}hasClass(e){return l.contains(this.classes,e)}toNode(){const e=document.createDocumentFragment();for(let t=0;te.toText())).join("")}}var T={"AMS-Regular":{32:[0,0,0,0,.25],65:[0,.68889,0,0,.72222],66:[0,.68889,0,0,.66667],67:[0,.68889,0,0,.72222],68:[0,.68889,0,0,.72222],69:[0,.68889,0,0,.66667],70:[0,.68889,0,0,.61111],71:[0,.68889,0,0,.77778],72:[0,.68889,0,0,.77778],73:[0,.68889,0,0,.38889],74:[.16667,.68889,0,0,.5],75:[0,.68889,0,0,.77778],76:[0,.68889,0,0,.66667],77:[0,.68889,0,0,.94445],78:[0,.68889,0,0,.72222],79:[.16667,.68889,0,0,.77778],80:[0,.68889,0,0,.61111],81:[.16667,.68889,0,0,.77778],82:[0,.68889,0,0,.72222],83:[0,.68889,0,0,.55556],84:[0,.68889,0,0,.66667],85:[0,.68889,0,0,.72222],86:[0,.68889,0,0,.72222],87:[0,.68889,0,0,1],88:[0,.68889,0,0,.72222],89:[0,.68889,0,0,.72222],90:[0,.68889,0,0,.66667],107:[0,.68889,0,0,.55556],160:[0,0,0,0,.25],165:[0,.675,.025,0,.75],174:[.15559,.69224,0,0,.94666],240:[0,.68889,0,0,.55556],295:[0,.68889,0,0,.54028],710:[0,.825,0,0,2.33334],732:[0,.9,0,0,2.33334],770:[0,.825,0,0,2.33334],771:[0,.9,0,0,2.33334],989:[.08167,.58167,0,0,.77778],1008:[0,.43056,.04028,0,.66667],8245:[0,.54986,0,0,.275],8463:[0,.68889,0,0,.54028],8487:[0,.68889,0,0,.72222],8498:[0,.68889,0,0,.55556],8502:[0,.68889,0,0,.66667],8503:[0,.68889,0,0,.44445],8504:[0,.68889,0,0,.66667],8513:[0,.68889,0,0,.63889],8592:[-.03598,.46402,0,0,.5],8594:[-.03598,.46402,0,0,.5],8602:[-.13313,.36687,0,0,1],8603:[-.13313,.36687,0,0,1],8606:[.01354,.52239,0,0,1],8608:[.01354,.52239,0,0,1],8610:[.01354,.52239,0,0,1.11111],8611:[.01354,.52239,0,0,1.11111],8619:[0,.54986,0,0,1],8620:[0,.54986,0,0,1],8621:[-.13313,.37788,0,0,1.38889],8622:[-.13313,.36687,0,0,1],8624:[0,.69224,0,0,.5],8625:[0,.69224,0,0,.5],8630:[0,.43056,0,0,1],8631:[0,.43056,0,0,1],8634:[.08198,.58198,0,0,.77778],8635:[.08198,.58198,0,0,.77778],8638:[.19444,.69224,0,0,.41667],8639:[.19444,.69224,0,0,.41667],8642:[.19444,.69224,0,0,.41667],8643:[.19444,.69224,0,0,.41667],8644:[.1808,.675,0,0,1],8646:[.1808,.675,0,0,1],8647:[.1808,.675,0,0,1],8648:[.19444,.69224,0,0,.83334],8649:[.1808,.675,0,0,1],8650:[.19444,.69224,0,0,.83334],8651:[.01354,.52239,0,0,1],8652:[.01354,.52239,0,0,1],8653:[-.13313,.36687,0,0,1],8654:[-.13313,.36687,0,0,1],8655:[-.13313,.36687,0,0,1],8666:[.13667,.63667,0,0,1],8667:[.13667,.63667,0,0,1],8669:[-.13313,.37788,0,0,1],8672:[-.064,.437,0,0,1.334],8674:[-.064,.437,0,0,1.334],8705:[0,.825,0,0,.5],8708:[0,.68889,0,0,.55556],8709:[.08167,.58167,0,0,.77778],8717:[0,.43056,0,0,.42917],8722:[-.03598,.46402,0,0,.5],8724:[.08198,.69224,0,0,.77778],8726:[.08167,.58167,0,0,.77778],8733:[0,.69224,0,0,.77778],8736:[0,.69224,0,0,.72222],8737:[0,.69224,0,0,.72222],8738:[.03517,.52239,0,0,.72222],8739:[.08167,.58167,0,0,.22222],8740:[.25142,.74111,0,0,.27778],8741:[.08167,.58167,0,0,.38889],8742:[.25142,.74111,0,0,.5],8756:[0,.69224,0,0,.66667],8757:[0,.69224,0,0,.66667],8764:[-.13313,.36687,0,0,.77778],8765:[-.13313,.37788,0,0,.77778],8769:[-.13313,.36687,0,0,.77778],8770:[-.03625,.46375,0,0,.77778],8774:[.30274,.79383,0,0,.77778],8776:[-.01688,.48312,0,0,.77778],8778:[.08167,.58167,0,0,.77778],8782:[.06062,.54986,0,0,.77778],8783:[.06062,.54986,0,0,.77778],8785:[.08198,.58198,0,0,.77778],8786:[.08198,.58198,0,0,.77778],8787:[.08198,.58198,0,0,.77778],8790:[0,.69224,0,0,.77778],8791:[.22958,.72958,0,0,.77778],8796:[.08198,.91667,0,0,.77778],8806:[.25583,.75583,0,0,.77778],8807:[.25583,.75583,0,0,.77778],8808:[.25142,.75726,0,0,.77778],8809:[.25142,.75726,0,0,.77778],8812:[.25583,.75583,0,0,.5],8814:[.20576,.70576,0,0,.77778],8815:[.20576,.70576,0,0,.77778],8816:[.30274,.79383,0,0,.77778],8817:[.30274,.79383,0,0,.77778],8818:[.22958,.72958,0,0,.77778],8819:[.22958,.72958,0,0,.77778],8822:[.1808,.675,0,0,.77778],8823:[.1808,.675,0,0,.77778],8828:[.13667,.63667,0,0,.77778],8829:[.13667,.63667,0,0,.77778],8830:[.22958,.72958,0,0,.77778],8831:[.22958,.72958,0,0,.77778],8832:[.20576,.70576,0,0,.77778],8833:[.20576,.70576,0,0,.77778],8840:[.30274,.79383,0,0,.77778],8841:[.30274,.79383,0,0,.77778],8842:[.13597,.63597,0,0,.77778],8843:[.13597,.63597,0,0,.77778],8847:[.03517,.54986,0,0,.77778],8848:[.03517,.54986,0,0,.77778],8858:[.08198,.58198,0,0,.77778],8859:[.08198,.58198,0,0,.77778],8861:[.08198,.58198,0,0,.77778],8862:[0,.675,0,0,.77778],8863:[0,.675,0,0,.77778],8864:[0,.675,0,0,.77778],8865:[0,.675,0,0,.77778],8872:[0,.69224,0,0,.61111],8873:[0,.69224,0,0,.72222],8874:[0,.69224,0,0,.88889],8876:[0,.68889,0,0,.61111],8877:[0,.68889,0,0,.61111],8878:[0,.68889,0,0,.72222],8879:[0,.68889,0,0,.72222],8882:[.03517,.54986,0,0,.77778],8883:[.03517,.54986,0,0,.77778],8884:[.13667,.63667,0,0,.77778],8885:[.13667,.63667,0,0,.77778],8888:[0,.54986,0,0,1.11111],8890:[.19444,.43056,0,0,.55556],8891:[.19444,.69224,0,0,.61111],8892:[.19444,.69224,0,0,.61111],8901:[0,.54986,0,0,.27778],8903:[.08167,.58167,0,0,.77778],8905:[.08167,.58167,0,0,.77778],8906:[.08167,.58167,0,0,.77778],8907:[0,.69224,0,0,.77778],8908:[0,.69224,0,0,.77778],8909:[-.03598,.46402,0,0,.77778],8910:[0,.54986,0,0,.76042],8911:[0,.54986,0,0,.76042],8912:[.03517,.54986,0,0,.77778],8913:[.03517,.54986,0,0,.77778],8914:[0,.54986,0,0,.66667],8915:[0,.54986,0,0,.66667],8916:[0,.69224,0,0,.66667],8918:[.0391,.5391,0,0,.77778],8919:[.0391,.5391,0,0,.77778],8920:[.03517,.54986,0,0,1.33334],8921:[.03517,.54986,0,0,1.33334],8922:[.38569,.88569,0,0,.77778],8923:[.38569,.88569,0,0,.77778],8926:[.13667,.63667,0,0,.77778],8927:[.13667,.63667,0,0,.77778],8928:[.30274,.79383,0,0,.77778],8929:[.30274,.79383,0,0,.77778],8934:[.23222,.74111,0,0,.77778],8935:[.23222,.74111,0,0,.77778],8936:[.23222,.74111,0,0,.77778],8937:[.23222,.74111,0,0,.77778],8938:[.20576,.70576,0,0,.77778],8939:[.20576,.70576,0,0,.77778],8940:[.30274,.79383,0,0,.77778],8941:[.30274,.79383,0,0,.77778],8994:[.19444,.69224,0,0,.77778],8995:[.19444,.69224,0,0,.77778],9416:[.15559,.69224,0,0,.90222],9484:[0,.69224,0,0,.5],9488:[0,.69224,0,0,.5],9492:[0,.37788,0,0,.5],9496:[0,.37788,0,0,.5],9585:[.19444,.68889,0,0,.88889],9586:[.19444,.74111,0,0,.88889],9632:[0,.675,0,0,.77778],9633:[0,.675,0,0,.77778],9650:[0,.54986,0,0,.72222],9651:[0,.54986,0,0,.72222],9654:[.03517,.54986,0,0,.77778],9660:[0,.54986,0,0,.72222],9661:[0,.54986,0,0,.72222],9664:[.03517,.54986,0,0,.77778],9674:[.11111,.69224,0,0,.66667],9733:[.19444,.69224,0,0,.94445],10003:[0,.69224,0,0,.83334],10016:[0,.69224,0,0,.83334],10731:[.11111,.69224,0,0,.66667],10846:[.19444,.75583,0,0,.61111],10877:[.13667,.63667,0,0,.77778],10878:[.13667,.63667,0,0,.77778],10885:[.25583,.75583,0,0,.77778],10886:[.25583,.75583,0,0,.77778],10887:[.13597,.63597,0,0,.77778],10888:[.13597,.63597,0,0,.77778],10889:[.26167,.75726,0,0,.77778],10890:[.26167,.75726,0,0,.77778],10891:[.48256,.98256,0,0,.77778],10892:[.48256,.98256,0,0,.77778],10901:[.13667,.63667,0,0,.77778],10902:[.13667,.63667,0,0,.77778],10933:[.25142,.75726,0,0,.77778],10934:[.25142,.75726,0,0,.77778],10935:[.26167,.75726,0,0,.77778],10936:[.26167,.75726,0,0,.77778],10937:[.26167,.75726,0,0,.77778],10938:[.26167,.75726,0,0,.77778],10949:[.25583,.75583,0,0,.77778],10950:[.25583,.75583,0,0,.77778],10955:[.28481,.79383,0,0,.77778],10956:[.28481,.79383,0,0,.77778],57350:[.08167,.58167,0,0,.22222],57351:[.08167,.58167,0,0,.38889],57352:[.08167,.58167,0,0,.77778],57353:[0,.43056,.04028,0,.66667],57356:[.25142,.75726,0,0,.77778],57357:[.25142,.75726,0,0,.77778],57358:[.41951,.91951,0,0,.77778],57359:[.30274,.79383,0,0,.77778],57360:[.30274,.79383,0,0,.77778],57361:[.41951,.91951,0,0,.77778],57366:[.25142,.75726,0,0,.77778],57367:[.25142,.75726,0,0,.77778],57368:[.25142,.75726,0,0,.77778],57369:[.25142,.75726,0,0,.77778],57370:[.13597,.63597,0,0,.77778],57371:[.13597,.63597,0,0,.77778]},"Caligraphic-Regular":{32:[0,0,0,0,.25],65:[0,.68333,0,.19445,.79847],66:[0,.68333,.03041,.13889,.65681],67:[0,.68333,.05834,.13889,.52653],68:[0,.68333,.02778,.08334,.77139],69:[0,.68333,.08944,.11111,.52778],70:[0,.68333,.09931,.11111,.71875],71:[.09722,.68333,.0593,.11111,.59487],72:[0,.68333,.00965,.11111,.84452],73:[0,.68333,.07382,0,.54452],74:[.09722,.68333,.18472,.16667,.67778],75:[0,.68333,.01445,.05556,.76195],76:[0,.68333,0,.13889,.68972],77:[0,.68333,0,.13889,1.2009],78:[0,.68333,.14736,.08334,.82049],79:[0,.68333,.02778,.11111,.79611],80:[0,.68333,.08222,.08334,.69556],81:[.09722,.68333,0,.11111,.81667],82:[0,.68333,0,.08334,.8475],83:[0,.68333,.075,.13889,.60556],84:[0,.68333,.25417,0,.54464],85:[0,.68333,.09931,.08334,.62583],86:[0,.68333,.08222,0,.61278],87:[0,.68333,.08222,.08334,.98778],88:[0,.68333,.14643,.13889,.7133],89:[.09722,.68333,.08222,.08334,.66834],90:[0,.68333,.07944,.13889,.72473],160:[0,0,0,0,.25]},"Fraktur-Regular":{32:[0,0,0,0,.25],33:[0,.69141,0,0,.29574],34:[0,.69141,0,0,.21471],38:[0,.69141,0,0,.73786],39:[0,.69141,0,0,.21201],40:[.24982,.74947,0,0,.38865],41:[.24982,.74947,0,0,.38865],42:[0,.62119,0,0,.27764],43:[.08319,.58283,0,0,.75623],44:[0,.10803,0,0,.27764],45:[.08319,.58283,0,0,.75623],46:[0,.10803,0,0,.27764],47:[.24982,.74947,0,0,.50181],48:[0,.47534,0,0,.50181],49:[0,.47534,0,0,.50181],50:[0,.47534,0,0,.50181],51:[.18906,.47534,0,0,.50181],52:[.18906,.47534,0,0,.50181],53:[.18906,.47534,0,0,.50181],54:[0,.69141,0,0,.50181],55:[.18906,.47534,0,0,.50181],56:[0,.69141,0,0,.50181],57:[.18906,.47534,0,0,.50181],58:[0,.47534,0,0,.21606],59:[.12604,.47534,0,0,.21606],61:[-.13099,.36866,0,0,.75623],63:[0,.69141,0,0,.36245],65:[0,.69141,0,0,.7176],66:[0,.69141,0,0,.88397],67:[0,.69141,0,0,.61254],68:[0,.69141,0,0,.83158],69:[0,.69141,0,0,.66278],70:[.12604,.69141,0,0,.61119],71:[0,.69141,0,0,.78539],72:[.06302,.69141,0,0,.7203],73:[0,.69141,0,0,.55448],74:[.12604,.69141,0,0,.55231],75:[0,.69141,0,0,.66845],76:[0,.69141,0,0,.66602],77:[0,.69141,0,0,1.04953],78:[0,.69141,0,0,.83212],79:[0,.69141,0,0,.82699],80:[.18906,.69141,0,0,.82753],81:[.03781,.69141,0,0,.82699],82:[0,.69141,0,0,.82807],83:[0,.69141,0,0,.82861],84:[0,.69141,0,0,.66899],85:[0,.69141,0,0,.64576],86:[0,.69141,0,0,.83131],87:[0,.69141,0,0,1.04602],88:[0,.69141,0,0,.71922],89:[.18906,.69141,0,0,.83293],90:[.12604,.69141,0,0,.60201],91:[.24982,.74947,0,0,.27764],93:[.24982,.74947,0,0,.27764],94:[0,.69141,0,0,.49965],97:[0,.47534,0,0,.50046],98:[0,.69141,0,0,.51315],99:[0,.47534,0,0,.38946],100:[0,.62119,0,0,.49857],101:[0,.47534,0,0,.40053],102:[.18906,.69141,0,0,.32626],103:[.18906,.47534,0,0,.5037],104:[.18906,.69141,0,0,.52126],105:[0,.69141,0,0,.27899],106:[0,.69141,0,0,.28088],107:[0,.69141,0,0,.38946],108:[0,.69141,0,0,.27953],109:[0,.47534,0,0,.76676],110:[0,.47534,0,0,.52666],111:[0,.47534,0,0,.48885],112:[.18906,.52396,0,0,.50046],113:[.18906,.47534,0,0,.48912],114:[0,.47534,0,0,.38919],115:[0,.47534,0,0,.44266],116:[0,.62119,0,0,.33301],117:[0,.47534,0,0,.5172],118:[0,.52396,0,0,.5118],119:[0,.52396,0,0,.77351],120:[.18906,.47534,0,0,.38865],121:[.18906,.47534,0,0,.49884],122:[.18906,.47534,0,0,.39054],160:[0,0,0,0,.25],8216:[0,.69141,0,0,.21471],8217:[0,.69141,0,0,.21471],58112:[0,.62119,0,0,.49749],58113:[0,.62119,0,0,.4983],58114:[.18906,.69141,0,0,.33328],58115:[.18906,.69141,0,0,.32923],58116:[.18906,.47534,0,0,.50343],58117:[0,.69141,0,0,.33301],58118:[0,.62119,0,0,.33409],58119:[0,.47534,0,0,.50073]},"Main-Bold":{32:[0,0,0,0,.25],33:[0,.69444,0,0,.35],34:[0,.69444,0,0,.60278],35:[.19444,.69444,0,0,.95833],36:[.05556,.75,0,0,.575],37:[.05556,.75,0,0,.95833],38:[0,.69444,0,0,.89444],39:[0,.69444,0,0,.31944],40:[.25,.75,0,0,.44722],41:[.25,.75,0,0,.44722],42:[0,.75,0,0,.575],43:[.13333,.63333,0,0,.89444],44:[.19444,.15556,0,0,.31944],45:[0,.44444,0,0,.38333],46:[0,.15556,0,0,.31944],47:[.25,.75,0,0,.575],48:[0,.64444,0,0,.575],49:[0,.64444,0,0,.575],50:[0,.64444,0,0,.575],51:[0,.64444,0,0,.575],52:[0,.64444,0,0,.575],53:[0,.64444,0,0,.575],54:[0,.64444,0,0,.575],55:[0,.64444,0,0,.575],56:[0,.64444,0,0,.575],57:[0,.64444,0,0,.575],58:[0,.44444,0,0,.31944],59:[.19444,.44444,0,0,.31944],60:[.08556,.58556,0,0,.89444],61:[-.10889,.39111,0,0,.89444],62:[.08556,.58556,0,0,.89444],63:[0,.69444,0,0,.54305],64:[0,.69444,0,0,.89444],65:[0,.68611,0,0,.86944],66:[0,.68611,0,0,.81805],67:[0,.68611,0,0,.83055],68:[0,.68611,0,0,.88194],69:[0,.68611,0,0,.75555],70:[0,.68611,0,0,.72361],71:[0,.68611,0,0,.90416],72:[0,.68611,0,0,.9],73:[0,.68611,0,0,.43611],74:[0,.68611,0,0,.59444],75:[0,.68611,0,0,.90138],76:[0,.68611,0,0,.69166],77:[0,.68611,0,0,1.09166],78:[0,.68611,0,0,.9],79:[0,.68611,0,0,.86388],80:[0,.68611,0,0,.78611],81:[.19444,.68611,0,0,.86388],82:[0,.68611,0,0,.8625],83:[0,.68611,0,0,.63889],84:[0,.68611,0,0,.8],85:[0,.68611,0,0,.88472],86:[0,.68611,.01597,0,.86944],87:[0,.68611,.01597,0,1.18888],88:[0,.68611,0,0,.86944],89:[0,.68611,.02875,0,.86944],90:[0,.68611,0,0,.70277],91:[.25,.75,0,0,.31944],92:[.25,.75,0,0,.575],93:[.25,.75,0,0,.31944],94:[0,.69444,0,0,.575],95:[.31,.13444,.03194,0,.575],97:[0,.44444,0,0,.55902],98:[0,.69444,0,0,.63889],99:[0,.44444,0,0,.51111],100:[0,.69444,0,0,.63889],101:[0,.44444,0,0,.52708],102:[0,.69444,.10903,0,.35139],103:[.19444,.44444,.01597,0,.575],104:[0,.69444,0,0,.63889],105:[0,.69444,0,0,.31944],106:[.19444,.69444,0,0,.35139],107:[0,.69444,0,0,.60694],108:[0,.69444,0,0,.31944],109:[0,.44444,0,0,.95833],110:[0,.44444,0,0,.63889],111:[0,.44444,0,0,.575],112:[.19444,.44444,0,0,.63889],113:[.19444,.44444,0,0,.60694],114:[0,.44444,0,0,.47361],115:[0,.44444,0,0,.45361],116:[0,.63492,0,0,.44722],117:[0,.44444,0,0,.63889],118:[0,.44444,.01597,0,.60694],119:[0,.44444,.01597,0,.83055],120:[0,.44444,0,0,.60694],121:[.19444,.44444,.01597,0,.60694],122:[0,.44444,0,0,.51111],123:[.25,.75,0,0,.575],124:[.25,.75,0,0,.31944],125:[.25,.75,0,0,.575],126:[.35,.34444,0,0,.575],160:[0,0,0,0,.25],163:[0,.69444,0,0,.86853],168:[0,.69444,0,0,.575],172:[0,.44444,0,0,.76666],176:[0,.69444,0,0,.86944],177:[.13333,.63333,0,0,.89444],184:[.17014,0,0,0,.51111],198:[0,.68611,0,0,1.04166],215:[.13333,.63333,0,0,.89444],216:[.04861,.73472,0,0,.89444],223:[0,.69444,0,0,.59722],230:[0,.44444,0,0,.83055],247:[.13333,.63333,0,0,.89444],248:[.09722,.54167,0,0,.575],305:[0,.44444,0,0,.31944],338:[0,.68611,0,0,1.16944],339:[0,.44444,0,0,.89444],567:[.19444,.44444,0,0,.35139],710:[0,.69444,0,0,.575],711:[0,.63194,0,0,.575],713:[0,.59611,0,0,.575],714:[0,.69444,0,0,.575],715:[0,.69444,0,0,.575],728:[0,.69444,0,0,.575],729:[0,.69444,0,0,.31944],730:[0,.69444,0,0,.86944],732:[0,.69444,0,0,.575],733:[0,.69444,0,0,.575],915:[0,.68611,0,0,.69166],916:[0,.68611,0,0,.95833],920:[0,.68611,0,0,.89444],923:[0,.68611,0,0,.80555],926:[0,.68611,0,0,.76666],928:[0,.68611,0,0,.9],931:[0,.68611,0,0,.83055],933:[0,.68611,0,0,.89444],934:[0,.68611,0,0,.83055],936:[0,.68611,0,0,.89444],937:[0,.68611,0,0,.83055],8211:[0,.44444,.03194,0,.575],8212:[0,.44444,.03194,0,1.14999],8216:[0,.69444,0,0,.31944],8217:[0,.69444,0,0,.31944],8220:[0,.69444,0,0,.60278],8221:[0,.69444,0,0,.60278],8224:[.19444,.69444,0,0,.51111],8225:[.19444,.69444,0,0,.51111],8242:[0,.55556,0,0,.34444],8407:[0,.72444,.15486,0,.575],8463:[0,.69444,0,0,.66759],8465:[0,.69444,0,0,.83055],8467:[0,.69444,0,0,.47361],8472:[.19444,.44444,0,0,.74027],8476:[0,.69444,0,0,.83055],8501:[0,.69444,0,0,.70277],8592:[-.10889,.39111,0,0,1.14999],8593:[.19444,.69444,0,0,.575],8594:[-.10889,.39111,0,0,1.14999],8595:[.19444,.69444,0,0,.575],8596:[-.10889,.39111,0,0,1.14999],8597:[.25,.75,0,0,.575],8598:[.19444,.69444,0,0,1.14999],8599:[.19444,.69444,0,0,1.14999],8600:[.19444,.69444,0,0,1.14999],8601:[.19444,.69444,0,0,1.14999],8636:[-.10889,.39111,0,0,1.14999],8637:[-.10889,.39111,0,0,1.14999],8640:[-.10889,.39111,0,0,1.14999],8641:[-.10889,.39111,0,0,1.14999],8656:[-.10889,.39111,0,0,1.14999],8657:[.19444,.69444,0,0,.70277],8658:[-.10889,.39111,0,0,1.14999],8659:[.19444,.69444,0,0,.70277],8660:[-.10889,.39111,0,0,1.14999],8661:[.25,.75,0,0,.70277],8704:[0,.69444,0,0,.63889],8706:[0,.69444,.06389,0,.62847],8707:[0,.69444,0,0,.63889],8709:[.05556,.75,0,0,.575],8711:[0,.68611,0,0,.95833],8712:[.08556,.58556,0,0,.76666],8715:[.08556,.58556,0,0,.76666],8722:[.13333,.63333,0,0,.89444],8723:[.13333,.63333,0,0,.89444],8725:[.25,.75,0,0,.575],8726:[.25,.75,0,0,.575],8727:[-.02778,.47222,0,0,.575],8728:[-.02639,.47361,0,0,.575],8729:[-.02639,.47361,0,0,.575],8730:[.18,.82,0,0,.95833],8733:[0,.44444,0,0,.89444],8734:[0,.44444,0,0,1.14999],8736:[0,.69224,0,0,.72222],8739:[.25,.75,0,0,.31944],8741:[.25,.75,0,0,.575],8743:[0,.55556,0,0,.76666],8744:[0,.55556,0,0,.76666],8745:[0,.55556,0,0,.76666],8746:[0,.55556,0,0,.76666],8747:[.19444,.69444,.12778,0,.56875],8764:[-.10889,.39111,0,0,.89444],8768:[.19444,.69444,0,0,.31944],8771:[.00222,.50222,0,0,.89444],8773:[.027,.638,0,0,.894],8776:[.02444,.52444,0,0,.89444],8781:[.00222,.50222,0,0,.89444],8801:[.00222,.50222,0,0,.89444],8804:[.19667,.69667,0,0,.89444],8805:[.19667,.69667,0,0,.89444],8810:[.08556,.58556,0,0,1.14999],8811:[.08556,.58556,0,0,1.14999],8826:[.08556,.58556,0,0,.89444],8827:[.08556,.58556,0,0,.89444],8834:[.08556,.58556,0,0,.89444],8835:[.08556,.58556,0,0,.89444],8838:[.19667,.69667,0,0,.89444],8839:[.19667,.69667,0,0,.89444],8846:[0,.55556,0,0,.76666],8849:[.19667,.69667,0,0,.89444],8850:[.19667,.69667,0,0,.89444],8851:[0,.55556,0,0,.76666],8852:[0,.55556,0,0,.76666],8853:[.13333,.63333,0,0,.89444],8854:[.13333,.63333,0,0,.89444],8855:[.13333,.63333,0,0,.89444],8856:[.13333,.63333,0,0,.89444],8857:[.13333,.63333,0,0,.89444],8866:[0,.69444,0,0,.70277],8867:[0,.69444,0,0,.70277],8868:[0,.69444,0,0,.89444],8869:[0,.69444,0,0,.89444],8900:[-.02639,.47361,0,0,.575],8901:[-.02639,.47361,0,0,.31944],8902:[-.02778,.47222,0,0,.575],8968:[.25,.75,0,0,.51111],8969:[.25,.75,0,0,.51111],8970:[.25,.75,0,0,.51111],8971:[.25,.75,0,0,.51111],8994:[-.13889,.36111,0,0,1.14999],8995:[-.13889,.36111,0,0,1.14999],9651:[.19444,.69444,0,0,1.02222],9657:[-.02778,.47222,0,0,.575],9661:[.19444,.69444,0,0,1.02222],9667:[-.02778,.47222,0,0,.575],9711:[.19444,.69444,0,0,1.14999],9824:[.12963,.69444,0,0,.89444],9825:[.12963,.69444,0,0,.89444],9826:[.12963,.69444,0,0,.89444],9827:[.12963,.69444,0,0,.89444],9837:[0,.75,0,0,.44722],9838:[.19444,.69444,0,0,.44722],9839:[.19444,.69444,0,0,.44722],10216:[.25,.75,0,0,.44722],10217:[.25,.75,0,0,.44722],10815:[0,.68611,0,0,.9],10927:[.19667,.69667,0,0,.89444],10928:[.19667,.69667,0,0,.89444],57376:[.19444,.69444,0,0,0]},"Main-BoldItalic":{32:[0,0,0,0,.25],33:[0,.69444,.11417,0,.38611],34:[0,.69444,.07939,0,.62055],35:[.19444,.69444,.06833,0,.94444],37:[.05556,.75,.12861,0,.94444],38:[0,.69444,.08528,0,.88555],39:[0,.69444,.12945,0,.35555],40:[.25,.75,.15806,0,.47333],41:[.25,.75,.03306,0,.47333],42:[0,.75,.14333,0,.59111],43:[.10333,.60333,.03306,0,.88555],44:[.19444,.14722,0,0,.35555],45:[0,.44444,.02611,0,.41444],46:[0,.14722,0,0,.35555],47:[.25,.75,.15806,0,.59111],48:[0,.64444,.13167,0,.59111],49:[0,.64444,.13167,0,.59111],50:[0,.64444,.13167,0,.59111],51:[0,.64444,.13167,0,.59111],52:[.19444,.64444,.13167,0,.59111],53:[0,.64444,.13167,0,.59111],54:[0,.64444,.13167,0,.59111],55:[.19444,.64444,.13167,0,.59111],56:[0,.64444,.13167,0,.59111],57:[0,.64444,.13167,0,.59111],58:[0,.44444,.06695,0,.35555],59:[.19444,.44444,.06695,0,.35555],61:[-.10889,.39111,.06833,0,.88555],63:[0,.69444,.11472,0,.59111],64:[0,.69444,.09208,0,.88555],65:[0,.68611,0,0,.86555],66:[0,.68611,.0992,0,.81666],67:[0,.68611,.14208,0,.82666],68:[0,.68611,.09062,0,.87555],69:[0,.68611,.11431,0,.75666],70:[0,.68611,.12903,0,.72722],71:[0,.68611,.07347,0,.89527],72:[0,.68611,.17208,0,.8961],73:[0,.68611,.15681,0,.47166],74:[0,.68611,.145,0,.61055],75:[0,.68611,.14208,0,.89499],76:[0,.68611,0,0,.69777],77:[0,.68611,.17208,0,1.07277],78:[0,.68611,.17208,0,.8961],79:[0,.68611,.09062,0,.85499],80:[0,.68611,.0992,0,.78721],81:[.19444,.68611,.09062,0,.85499],82:[0,.68611,.02559,0,.85944],83:[0,.68611,.11264,0,.64999],84:[0,.68611,.12903,0,.7961],85:[0,.68611,.17208,0,.88083],86:[0,.68611,.18625,0,.86555],87:[0,.68611,.18625,0,1.15999],88:[0,.68611,.15681,0,.86555],89:[0,.68611,.19803,0,.86555],90:[0,.68611,.14208,0,.70888],91:[.25,.75,.1875,0,.35611],93:[.25,.75,.09972,0,.35611],94:[0,.69444,.06709,0,.59111],95:[.31,.13444,.09811,0,.59111],97:[0,.44444,.09426,0,.59111],98:[0,.69444,.07861,0,.53222],99:[0,.44444,.05222,0,.53222],100:[0,.69444,.10861,0,.59111],101:[0,.44444,.085,0,.53222],102:[.19444,.69444,.21778,0,.4],103:[.19444,.44444,.105,0,.53222],104:[0,.69444,.09426,0,.59111],105:[0,.69326,.11387,0,.35555],106:[.19444,.69326,.1672,0,.35555],107:[0,.69444,.11111,0,.53222],108:[0,.69444,.10861,0,.29666],109:[0,.44444,.09426,0,.94444],110:[0,.44444,.09426,0,.64999],111:[0,.44444,.07861,0,.59111],112:[.19444,.44444,.07861,0,.59111],113:[.19444,.44444,.105,0,.53222],114:[0,.44444,.11111,0,.50167],115:[0,.44444,.08167,0,.48694],116:[0,.63492,.09639,0,.385],117:[0,.44444,.09426,0,.62055],118:[0,.44444,.11111,0,.53222],119:[0,.44444,.11111,0,.76777],120:[0,.44444,.12583,0,.56055],121:[.19444,.44444,.105,0,.56166],122:[0,.44444,.13889,0,.49055],126:[.35,.34444,.11472,0,.59111],160:[0,0,0,0,.25],168:[0,.69444,.11473,0,.59111],176:[0,.69444,0,0,.94888],184:[.17014,0,0,0,.53222],198:[0,.68611,.11431,0,1.02277],216:[.04861,.73472,.09062,0,.88555],223:[.19444,.69444,.09736,0,.665],230:[0,.44444,.085,0,.82666],248:[.09722,.54167,.09458,0,.59111],305:[0,.44444,.09426,0,.35555],338:[0,.68611,.11431,0,1.14054],339:[0,.44444,.085,0,.82666],567:[.19444,.44444,.04611,0,.385],710:[0,.69444,.06709,0,.59111],711:[0,.63194,.08271,0,.59111],713:[0,.59444,.10444,0,.59111],714:[0,.69444,.08528,0,.59111],715:[0,.69444,0,0,.59111],728:[0,.69444,.10333,0,.59111],729:[0,.69444,.12945,0,.35555],730:[0,.69444,0,0,.94888],732:[0,.69444,.11472,0,.59111],733:[0,.69444,.11472,0,.59111],915:[0,.68611,.12903,0,.69777],916:[0,.68611,0,0,.94444],920:[0,.68611,.09062,0,.88555],923:[0,.68611,0,0,.80666],926:[0,.68611,.15092,0,.76777],928:[0,.68611,.17208,0,.8961],931:[0,.68611,.11431,0,.82666],933:[0,.68611,.10778,0,.88555],934:[0,.68611,.05632,0,.82666],936:[0,.68611,.10778,0,.88555],937:[0,.68611,.0992,0,.82666],8211:[0,.44444,.09811,0,.59111],8212:[0,.44444,.09811,0,1.18221],8216:[0,.69444,.12945,0,.35555],8217:[0,.69444,.12945,0,.35555],8220:[0,.69444,.16772,0,.62055],8221:[0,.69444,.07939,0,.62055]},"Main-Italic":{32:[0,0,0,0,.25],33:[0,.69444,.12417,0,.30667],34:[0,.69444,.06961,0,.51444],35:[.19444,.69444,.06616,0,.81777],37:[.05556,.75,.13639,0,.81777],38:[0,.69444,.09694,0,.76666],39:[0,.69444,.12417,0,.30667],40:[.25,.75,.16194,0,.40889],41:[.25,.75,.03694,0,.40889],42:[0,.75,.14917,0,.51111],43:[.05667,.56167,.03694,0,.76666],44:[.19444,.10556,0,0,.30667],45:[0,.43056,.02826,0,.35778],46:[0,.10556,0,0,.30667],47:[.25,.75,.16194,0,.51111],48:[0,.64444,.13556,0,.51111],49:[0,.64444,.13556,0,.51111],50:[0,.64444,.13556,0,.51111],51:[0,.64444,.13556,0,.51111],52:[.19444,.64444,.13556,0,.51111],53:[0,.64444,.13556,0,.51111],54:[0,.64444,.13556,0,.51111],55:[.19444,.64444,.13556,0,.51111],56:[0,.64444,.13556,0,.51111],57:[0,.64444,.13556,0,.51111],58:[0,.43056,.0582,0,.30667],59:[.19444,.43056,.0582,0,.30667],61:[-.13313,.36687,.06616,0,.76666],63:[0,.69444,.1225,0,.51111],64:[0,.69444,.09597,0,.76666],65:[0,.68333,0,0,.74333],66:[0,.68333,.10257,0,.70389],67:[0,.68333,.14528,0,.71555],68:[0,.68333,.09403,0,.755],69:[0,.68333,.12028,0,.67833],70:[0,.68333,.13305,0,.65277],71:[0,.68333,.08722,0,.77361],72:[0,.68333,.16389,0,.74333],73:[0,.68333,.15806,0,.38555],74:[0,.68333,.14028,0,.525],75:[0,.68333,.14528,0,.76888],76:[0,.68333,0,0,.62722],77:[0,.68333,.16389,0,.89666],78:[0,.68333,.16389,0,.74333],79:[0,.68333,.09403,0,.76666],80:[0,.68333,.10257,0,.67833],81:[.19444,.68333,.09403,0,.76666],82:[0,.68333,.03868,0,.72944],83:[0,.68333,.11972,0,.56222],84:[0,.68333,.13305,0,.71555],85:[0,.68333,.16389,0,.74333],86:[0,.68333,.18361,0,.74333],87:[0,.68333,.18361,0,.99888],88:[0,.68333,.15806,0,.74333],89:[0,.68333,.19383,0,.74333],90:[0,.68333,.14528,0,.61333],91:[.25,.75,.1875,0,.30667],93:[.25,.75,.10528,0,.30667],94:[0,.69444,.06646,0,.51111],95:[.31,.12056,.09208,0,.51111],97:[0,.43056,.07671,0,.51111],98:[0,.69444,.06312,0,.46],99:[0,.43056,.05653,0,.46],100:[0,.69444,.10333,0,.51111],101:[0,.43056,.07514,0,.46],102:[.19444,.69444,.21194,0,.30667],103:[.19444,.43056,.08847,0,.46],104:[0,.69444,.07671,0,.51111],105:[0,.65536,.1019,0,.30667],106:[.19444,.65536,.14467,0,.30667],107:[0,.69444,.10764,0,.46],108:[0,.69444,.10333,0,.25555],109:[0,.43056,.07671,0,.81777],110:[0,.43056,.07671,0,.56222],111:[0,.43056,.06312,0,.51111],112:[.19444,.43056,.06312,0,.51111],113:[.19444,.43056,.08847,0,.46],114:[0,.43056,.10764,0,.42166],115:[0,.43056,.08208,0,.40889],116:[0,.61508,.09486,0,.33222],117:[0,.43056,.07671,0,.53666],118:[0,.43056,.10764,0,.46],119:[0,.43056,.10764,0,.66444],120:[0,.43056,.12042,0,.46389],121:[.19444,.43056,.08847,0,.48555],122:[0,.43056,.12292,0,.40889],126:[.35,.31786,.11585,0,.51111],160:[0,0,0,0,.25],168:[0,.66786,.10474,0,.51111],176:[0,.69444,0,0,.83129],184:[.17014,0,0,0,.46],198:[0,.68333,.12028,0,.88277],216:[.04861,.73194,.09403,0,.76666],223:[.19444,.69444,.10514,0,.53666],230:[0,.43056,.07514,0,.71555],248:[.09722,.52778,.09194,0,.51111],338:[0,.68333,.12028,0,.98499],339:[0,.43056,.07514,0,.71555],710:[0,.69444,.06646,0,.51111],711:[0,.62847,.08295,0,.51111],713:[0,.56167,.10333,0,.51111],714:[0,.69444,.09694,0,.51111],715:[0,.69444,0,0,.51111],728:[0,.69444,.10806,0,.51111],729:[0,.66786,.11752,0,.30667],730:[0,.69444,0,0,.83129],732:[0,.66786,.11585,0,.51111],733:[0,.69444,.1225,0,.51111],915:[0,.68333,.13305,0,.62722],916:[0,.68333,0,0,.81777],920:[0,.68333,.09403,0,.76666],923:[0,.68333,0,0,.69222],926:[0,.68333,.15294,0,.66444],928:[0,.68333,.16389,0,.74333],931:[0,.68333,.12028,0,.71555],933:[0,.68333,.11111,0,.76666],934:[0,.68333,.05986,0,.71555],936:[0,.68333,.11111,0,.76666],937:[0,.68333,.10257,0,.71555],8211:[0,.43056,.09208,0,.51111],8212:[0,.43056,.09208,0,1.02222],8216:[0,.69444,.12417,0,.30667],8217:[0,.69444,.12417,0,.30667],8220:[0,.69444,.1685,0,.51444],8221:[0,.69444,.06961,0,.51444],8463:[0,.68889,0,0,.54028]},"Main-Regular":{32:[0,0,0,0,.25],33:[0,.69444,0,0,.27778],34:[0,.69444,0,0,.5],35:[.19444,.69444,0,0,.83334],36:[.05556,.75,0,0,.5],37:[.05556,.75,0,0,.83334],38:[0,.69444,0,0,.77778],39:[0,.69444,0,0,.27778],40:[.25,.75,0,0,.38889],41:[.25,.75,0,0,.38889],42:[0,.75,0,0,.5],43:[.08333,.58333,0,0,.77778],44:[.19444,.10556,0,0,.27778],45:[0,.43056,0,0,.33333],46:[0,.10556,0,0,.27778],47:[.25,.75,0,0,.5],48:[0,.64444,0,0,.5],49:[0,.64444,0,0,.5],50:[0,.64444,0,0,.5],51:[0,.64444,0,0,.5],52:[0,.64444,0,0,.5],53:[0,.64444,0,0,.5],54:[0,.64444,0,0,.5],55:[0,.64444,0,0,.5],56:[0,.64444,0,0,.5],57:[0,.64444,0,0,.5],58:[0,.43056,0,0,.27778],59:[.19444,.43056,0,0,.27778],60:[.0391,.5391,0,0,.77778],61:[-.13313,.36687,0,0,.77778],62:[.0391,.5391,0,0,.77778],63:[0,.69444,0,0,.47222],64:[0,.69444,0,0,.77778],65:[0,.68333,0,0,.75],66:[0,.68333,0,0,.70834],67:[0,.68333,0,0,.72222],68:[0,.68333,0,0,.76389],69:[0,.68333,0,0,.68056],70:[0,.68333,0,0,.65278],71:[0,.68333,0,0,.78472],72:[0,.68333,0,0,.75],73:[0,.68333,0,0,.36111],74:[0,.68333,0,0,.51389],75:[0,.68333,0,0,.77778],76:[0,.68333,0,0,.625],77:[0,.68333,0,0,.91667],78:[0,.68333,0,0,.75],79:[0,.68333,0,0,.77778],80:[0,.68333,0,0,.68056],81:[.19444,.68333,0,0,.77778],82:[0,.68333,0,0,.73611],83:[0,.68333,0,0,.55556],84:[0,.68333,0,0,.72222],85:[0,.68333,0,0,.75],86:[0,.68333,.01389,0,.75],87:[0,.68333,.01389,0,1.02778],88:[0,.68333,0,0,.75],89:[0,.68333,.025,0,.75],90:[0,.68333,0,0,.61111],91:[.25,.75,0,0,.27778],92:[.25,.75,0,0,.5],93:[.25,.75,0,0,.27778],94:[0,.69444,0,0,.5],95:[.31,.12056,.02778,0,.5],97:[0,.43056,0,0,.5],98:[0,.69444,0,0,.55556],99:[0,.43056,0,0,.44445],100:[0,.69444,0,0,.55556],101:[0,.43056,0,0,.44445],102:[0,.69444,.07778,0,.30556],103:[.19444,.43056,.01389,0,.5],104:[0,.69444,0,0,.55556],105:[0,.66786,0,0,.27778],106:[.19444,.66786,0,0,.30556],107:[0,.69444,0,0,.52778],108:[0,.69444,0,0,.27778],109:[0,.43056,0,0,.83334],110:[0,.43056,0,0,.55556],111:[0,.43056,0,0,.5],112:[.19444,.43056,0,0,.55556],113:[.19444,.43056,0,0,.52778],114:[0,.43056,0,0,.39167],115:[0,.43056,0,0,.39445],116:[0,.61508,0,0,.38889],117:[0,.43056,0,0,.55556],118:[0,.43056,.01389,0,.52778],119:[0,.43056,.01389,0,.72222],120:[0,.43056,0,0,.52778],121:[.19444,.43056,.01389,0,.52778],122:[0,.43056,0,0,.44445],123:[.25,.75,0,0,.5],124:[.25,.75,0,0,.27778],125:[.25,.75,0,0,.5],126:[.35,.31786,0,0,.5],160:[0,0,0,0,.25],163:[0,.69444,0,0,.76909],167:[.19444,.69444,0,0,.44445],168:[0,.66786,0,0,.5],172:[0,.43056,0,0,.66667],176:[0,.69444,0,0,.75],177:[.08333,.58333,0,0,.77778],182:[.19444,.69444,0,0,.61111],184:[.17014,0,0,0,.44445],198:[0,.68333,0,0,.90278],215:[.08333,.58333,0,0,.77778],216:[.04861,.73194,0,0,.77778],223:[0,.69444,0,0,.5],230:[0,.43056,0,0,.72222],247:[.08333,.58333,0,0,.77778],248:[.09722,.52778,0,0,.5],305:[0,.43056,0,0,.27778],338:[0,.68333,0,0,1.01389],339:[0,.43056,0,0,.77778],567:[.19444,.43056,0,0,.30556],710:[0,.69444,0,0,.5],711:[0,.62847,0,0,.5],713:[0,.56778,0,0,.5],714:[0,.69444,0,0,.5],715:[0,.69444,0,0,.5],728:[0,.69444,0,0,.5],729:[0,.66786,0,0,.27778],730:[0,.69444,0,0,.75],732:[0,.66786,0,0,.5],733:[0,.69444,0,0,.5],915:[0,.68333,0,0,.625],916:[0,.68333,0,0,.83334],920:[0,.68333,0,0,.77778],923:[0,.68333,0,0,.69445],926:[0,.68333,0,0,.66667],928:[0,.68333,0,0,.75],931:[0,.68333,0,0,.72222],933:[0,.68333,0,0,.77778],934:[0,.68333,0,0,.72222],936:[0,.68333,0,0,.77778],937:[0,.68333,0,0,.72222],8211:[0,.43056,.02778,0,.5],8212:[0,.43056,.02778,0,1],8216:[0,.69444,0,0,.27778],8217:[0,.69444,0,0,.27778],8220:[0,.69444,0,0,.5],8221:[0,.69444,0,0,.5],8224:[.19444,.69444,0,0,.44445],8225:[.19444,.69444,0,0,.44445],8230:[0,.123,0,0,1.172],8242:[0,.55556,0,0,.275],8407:[0,.71444,.15382,0,.5],8463:[0,.68889,0,0,.54028],8465:[0,.69444,0,0,.72222],8467:[0,.69444,0,.11111,.41667],8472:[.19444,.43056,0,.11111,.63646],8476:[0,.69444,0,0,.72222],8501:[0,.69444,0,0,.61111],8592:[-.13313,.36687,0,0,1],8593:[.19444,.69444,0,0,.5],8594:[-.13313,.36687,0,0,1],8595:[.19444,.69444,0,0,.5],8596:[-.13313,.36687,0,0,1],8597:[.25,.75,0,0,.5],8598:[.19444,.69444,0,0,1],8599:[.19444,.69444,0,0,1],8600:[.19444,.69444,0,0,1],8601:[.19444,.69444,0,0,1],8614:[.011,.511,0,0,1],8617:[.011,.511,0,0,1.126],8618:[.011,.511,0,0,1.126],8636:[-.13313,.36687,0,0,1],8637:[-.13313,.36687,0,0,1],8640:[-.13313,.36687,0,0,1],8641:[-.13313,.36687,0,0,1],8652:[.011,.671,0,0,1],8656:[-.13313,.36687,0,0,1],8657:[.19444,.69444,0,0,.61111],8658:[-.13313,.36687,0,0,1],8659:[.19444,.69444,0,0,.61111],8660:[-.13313,.36687,0,0,1],8661:[.25,.75,0,0,.61111],8704:[0,.69444,0,0,.55556],8706:[0,.69444,.05556,.08334,.5309],8707:[0,.69444,0,0,.55556],8709:[.05556,.75,0,0,.5],8711:[0,.68333,0,0,.83334],8712:[.0391,.5391,0,0,.66667],8715:[.0391,.5391,0,0,.66667],8722:[.08333,.58333,0,0,.77778],8723:[.08333,.58333,0,0,.77778],8725:[.25,.75,0,0,.5],8726:[.25,.75,0,0,.5],8727:[-.03472,.46528,0,0,.5],8728:[-.05555,.44445,0,0,.5],8729:[-.05555,.44445,0,0,.5],8730:[.2,.8,0,0,.83334],8733:[0,.43056,0,0,.77778],8734:[0,.43056,0,0,1],8736:[0,.69224,0,0,.72222],8739:[.25,.75,0,0,.27778],8741:[.25,.75,0,0,.5],8743:[0,.55556,0,0,.66667],8744:[0,.55556,0,0,.66667],8745:[0,.55556,0,0,.66667],8746:[0,.55556,0,0,.66667],8747:[.19444,.69444,.11111,0,.41667],8764:[-.13313,.36687,0,0,.77778],8768:[.19444,.69444,0,0,.27778],8771:[-.03625,.46375,0,0,.77778],8773:[-.022,.589,0,0,.778],8776:[-.01688,.48312,0,0,.77778],8781:[-.03625,.46375,0,0,.77778],8784:[-.133,.673,0,0,.778],8801:[-.03625,.46375,0,0,.77778],8804:[.13597,.63597,0,0,.77778],8805:[.13597,.63597,0,0,.77778],8810:[.0391,.5391,0,0,1],8811:[.0391,.5391,0,0,1],8826:[.0391,.5391,0,0,.77778],8827:[.0391,.5391,0,0,.77778],8834:[.0391,.5391,0,0,.77778],8835:[.0391,.5391,0,0,.77778],8838:[.13597,.63597,0,0,.77778],8839:[.13597,.63597,0,0,.77778],8846:[0,.55556,0,0,.66667],8849:[.13597,.63597,0,0,.77778],8850:[.13597,.63597,0,0,.77778],8851:[0,.55556,0,0,.66667],8852:[0,.55556,0,0,.66667],8853:[.08333,.58333,0,0,.77778],8854:[.08333,.58333,0,0,.77778],8855:[.08333,.58333,0,0,.77778],8856:[.08333,.58333,0,0,.77778],8857:[.08333,.58333,0,0,.77778],8866:[0,.69444,0,0,.61111],8867:[0,.69444,0,0,.61111],8868:[0,.69444,0,0,.77778],8869:[0,.69444,0,0,.77778],8872:[.249,.75,0,0,.867],8900:[-.05555,.44445,0,0,.5],8901:[-.05555,.44445,0,0,.27778],8902:[-.03472,.46528,0,0,.5],8904:[.005,.505,0,0,.9],8942:[.03,.903,0,0,.278],8943:[-.19,.313,0,0,1.172],8945:[-.1,.823,0,0,1.282],8968:[.25,.75,0,0,.44445],8969:[.25,.75,0,0,.44445],8970:[.25,.75,0,0,.44445],8971:[.25,.75,0,0,.44445],8994:[-.14236,.35764,0,0,1],8995:[-.14236,.35764,0,0,1],9136:[.244,.744,0,0,.412],9137:[.244,.745,0,0,.412],9651:[.19444,.69444,0,0,.88889],9657:[-.03472,.46528,0,0,.5],9661:[.19444,.69444,0,0,.88889],9667:[-.03472,.46528,0,0,.5],9711:[.19444,.69444,0,0,1],9824:[.12963,.69444,0,0,.77778],9825:[.12963,.69444,0,0,.77778],9826:[.12963,.69444,0,0,.77778],9827:[.12963,.69444,0,0,.77778],9837:[0,.75,0,0,.38889],9838:[.19444,.69444,0,0,.38889],9839:[.19444,.69444,0,0,.38889],10216:[.25,.75,0,0,.38889],10217:[.25,.75,0,0,.38889],10222:[.244,.744,0,0,.412],10223:[.244,.745,0,0,.412],10229:[.011,.511,0,0,1.609],10230:[.011,.511,0,0,1.638],10231:[.011,.511,0,0,1.859],10232:[.024,.525,0,0,1.609],10233:[.024,.525,0,0,1.638],10234:[.024,.525,0,0,1.858],10236:[.011,.511,0,0,1.638],10815:[0,.68333,0,0,.75],10927:[.13597,.63597,0,0,.77778],10928:[.13597,.63597,0,0,.77778],57376:[.19444,.69444,0,0,0]},"Math-BoldItalic":{32:[0,0,0,0,.25],48:[0,.44444,0,0,.575],49:[0,.44444,0,0,.575],50:[0,.44444,0,0,.575],51:[.19444,.44444,0,0,.575],52:[.19444,.44444,0,0,.575],53:[.19444,.44444,0,0,.575],54:[0,.64444,0,0,.575],55:[.19444,.44444,0,0,.575],56:[0,.64444,0,0,.575],57:[.19444,.44444,0,0,.575],65:[0,.68611,0,0,.86944],66:[0,.68611,.04835,0,.8664],67:[0,.68611,.06979,0,.81694],68:[0,.68611,.03194,0,.93812],69:[0,.68611,.05451,0,.81007],70:[0,.68611,.15972,0,.68889],71:[0,.68611,0,0,.88673],72:[0,.68611,.08229,0,.98229],73:[0,.68611,.07778,0,.51111],74:[0,.68611,.10069,0,.63125],75:[0,.68611,.06979,0,.97118],76:[0,.68611,0,0,.75555],77:[0,.68611,.11424,0,1.14201],78:[0,.68611,.11424,0,.95034],79:[0,.68611,.03194,0,.83666],80:[0,.68611,.15972,0,.72309],81:[.19444,.68611,0,0,.86861],82:[0,.68611,.00421,0,.87235],83:[0,.68611,.05382,0,.69271],84:[0,.68611,.15972,0,.63663],85:[0,.68611,.11424,0,.80027],86:[0,.68611,.25555,0,.67778],87:[0,.68611,.15972,0,1.09305],88:[0,.68611,.07778,0,.94722],89:[0,.68611,.25555,0,.67458],90:[0,.68611,.06979,0,.77257],97:[0,.44444,0,0,.63287],98:[0,.69444,0,0,.52083],99:[0,.44444,0,0,.51342],100:[0,.69444,0,0,.60972],101:[0,.44444,0,0,.55361],102:[.19444,.69444,.11042,0,.56806],103:[.19444,.44444,.03704,0,.5449],104:[0,.69444,0,0,.66759],105:[0,.69326,0,0,.4048],106:[.19444,.69326,.0622,0,.47083],107:[0,.69444,.01852,0,.6037],108:[0,.69444,.0088,0,.34815],109:[0,.44444,0,0,1.0324],110:[0,.44444,0,0,.71296],111:[0,.44444,0,0,.58472],112:[.19444,.44444,0,0,.60092],113:[.19444,.44444,.03704,0,.54213],114:[0,.44444,.03194,0,.5287],115:[0,.44444,0,0,.53125],116:[0,.63492,0,0,.41528],117:[0,.44444,0,0,.68102],118:[0,.44444,.03704,0,.56666],119:[0,.44444,.02778,0,.83148],120:[0,.44444,0,0,.65903],121:[.19444,.44444,.03704,0,.59028],122:[0,.44444,.04213,0,.55509],160:[0,0,0,0,.25],915:[0,.68611,.15972,0,.65694],916:[0,.68611,0,0,.95833],920:[0,.68611,.03194,0,.86722],923:[0,.68611,0,0,.80555],926:[0,.68611,.07458,0,.84125],928:[0,.68611,.08229,0,.98229],931:[0,.68611,.05451,0,.88507],933:[0,.68611,.15972,0,.67083],934:[0,.68611,0,0,.76666],936:[0,.68611,.11653,0,.71402],937:[0,.68611,.04835,0,.8789],945:[0,.44444,0,0,.76064],946:[.19444,.69444,.03403,0,.65972],947:[.19444,.44444,.06389,0,.59003],948:[0,.69444,.03819,0,.52222],949:[0,.44444,0,0,.52882],950:[.19444,.69444,.06215,0,.50833],951:[.19444,.44444,.03704,0,.6],952:[0,.69444,.03194,0,.5618],953:[0,.44444,0,0,.41204],954:[0,.44444,0,0,.66759],955:[0,.69444,0,0,.67083],956:[.19444,.44444,0,0,.70787],957:[0,.44444,.06898,0,.57685],958:[.19444,.69444,.03021,0,.50833],959:[0,.44444,0,0,.58472],960:[0,.44444,.03704,0,.68241],961:[.19444,.44444,0,0,.6118],962:[.09722,.44444,.07917,0,.42361],963:[0,.44444,.03704,0,.68588],964:[0,.44444,.13472,0,.52083],965:[0,.44444,.03704,0,.63055],966:[.19444,.44444,0,0,.74722],967:[.19444,.44444,0,0,.71805],968:[.19444,.69444,.03704,0,.75833],969:[0,.44444,.03704,0,.71782],977:[0,.69444,0,0,.69155],981:[.19444,.69444,0,0,.7125],982:[0,.44444,.03194,0,.975],1009:[.19444,.44444,0,0,.6118],1013:[0,.44444,0,0,.48333],57649:[0,.44444,0,0,.39352],57911:[.19444,.44444,0,0,.43889]},"Math-Italic":{32:[0,0,0,0,.25],48:[0,.43056,0,0,.5],49:[0,.43056,0,0,.5],50:[0,.43056,0,0,.5],51:[.19444,.43056,0,0,.5],52:[.19444,.43056,0,0,.5],53:[.19444,.43056,0,0,.5],54:[0,.64444,0,0,.5],55:[.19444,.43056,0,0,.5],56:[0,.64444,0,0,.5],57:[.19444,.43056,0,0,.5],65:[0,.68333,0,.13889,.75],66:[0,.68333,.05017,.08334,.75851],67:[0,.68333,.07153,.08334,.71472],68:[0,.68333,.02778,.05556,.82792],69:[0,.68333,.05764,.08334,.7382],70:[0,.68333,.13889,.08334,.64306],71:[0,.68333,0,.08334,.78625],72:[0,.68333,.08125,.05556,.83125],73:[0,.68333,.07847,.11111,.43958],74:[0,.68333,.09618,.16667,.55451],75:[0,.68333,.07153,.05556,.84931],76:[0,.68333,0,.02778,.68056],77:[0,.68333,.10903,.08334,.97014],78:[0,.68333,.10903,.08334,.80347],79:[0,.68333,.02778,.08334,.76278],80:[0,.68333,.13889,.08334,.64201],81:[.19444,.68333,0,.08334,.79056],82:[0,.68333,.00773,.08334,.75929],83:[0,.68333,.05764,.08334,.6132],84:[0,.68333,.13889,.08334,.58438],85:[0,.68333,.10903,.02778,.68278],86:[0,.68333,.22222,0,.58333],87:[0,.68333,.13889,0,.94445],88:[0,.68333,.07847,.08334,.82847],89:[0,.68333,.22222,0,.58056],90:[0,.68333,.07153,.08334,.68264],97:[0,.43056,0,0,.52859],98:[0,.69444,0,0,.42917],99:[0,.43056,0,.05556,.43276],100:[0,.69444,0,.16667,.52049],101:[0,.43056,0,.05556,.46563],102:[.19444,.69444,.10764,.16667,.48959],103:[.19444,.43056,.03588,.02778,.47697],104:[0,.69444,0,0,.57616],105:[0,.65952,0,0,.34451],106:[.19444,.65952,.05724,0,.41181],107:[0,.69444,.03148,0,.5206],108:[0,.69444,.01968,.08334,.29838],109:[0,.43056,0,0,.87801],110:[0,.43056,0,0,.60023],111:[0,.43056,0,.05556,.48472],112:[.19444,.43056,0,.08334,.50313],113:[.19444,.43056,.03588,.08334,.44641],114:[0,.43056,.02778,.05556,.45116],115:[0,.43056,0,.05556,.46875],116:[0,.61508,0,.08334,.36111],117:[0,.43056,0,.02778,.57246],118:[0,.43056,.03588,.02778,.48472],119:[0,.43056,.02691,.08334,.71592],120:[0,.43056,0,.02778,.57153],121:[.19444,.43056,.03588,.05556,.49028],122:[0,.43056,.04398,.05556,.46505],160:[0,0,0,0,.25],915:[0,.68333,.13889,.08334,.61528],916:[0,.68333,0,.16667,.83334],920:[0,.68333,.02778,.08334,.76278],923:[0,.68333,0,.16667,.69445],926:[0,.68333,.07569,.08334,.74236],928:[0,.68333,.08125,.05556,.83125],931:[0,.68333,.05764,.08334,.77986],933:[0,.68333,.13889,.05556,.58333],934:[0,.68333,0,.08334,.66667],936:[0,.68333,.11,.05556,.61222],937:[0,.68333,.05017,.08334,.7724],945:[0,.43056,.0037,.02778,.6397],946:[.19444,.69444,.05278,.08334,.56563],947:[.19444,.43056,.05556,0,.51773],948:[0,.69444,.03785,.05556,.44444],949:[0,.43056,0,.08334,.46632],950:[.19444,.69444,.07378,.08334,.4375],951:[.19444,.43056,.03588,.05556,.49653],952:[0,.69444,.02778,.08334,.46944],953:[0,.43056,0,.05556,.35394],954:[0,.43056,0,0,.57616],955:[0,.69444,0,0,.58334],956:[.19444,.43056,0,.02778,.60255],957:[0,.43056,.06366,.02778,.49398],958:[.19444,.69444,.04601,.11111,.4375],959:[0,.43056,0,.05556,.48472],960:[0,.43056,.03588,0,.57003],961:[.19444,.43056,0,.08334,.51702],962:[.09722,.43056,.07986,.08334,.36285],963:[0,.43056,.03588,0,.57141],964:[0,.43056,.1132,.02778,.43715],965:[0,.43056,.03588,.02778,.54028],966:[.19444,.43056,0,.08334,.65417],967:[.19444,.43056,0,.05556,.62569],968:[.19444,.69444,.03588,.11111,.65139],969:[0,.43056,.03588,0,.62245],977:[0,.69444,0,.08334,.59144],981:[.19444,.69444,0,.08334,.59583],982:[0,.43056,.02778,0,.82813],1009:[.19444,.43056,0,.08334,.51702],1013:[0,.43056,0,.05556,.4059],57649:[0,.43056,0,.02778,.32246],57911:[.19444,.43056,0,.08334,.38403]},"SansSerif-Bold":{32:[0,0,0,0,.25],33:[0,.69444,0,0,.36667],34:[0,.69444,0,0,.55834],35:[.19444,.69444,0,0,.91667],36:[.05556,.75,0,0,.55],37:[.05556,.75,0,0,1.02912],38:[0,.69444,0,0,.83056],39:[0,.69444,0,0,.30556],40:[.25,.75,0,0,.42778],41:[.25,.75,0,0,.42778],42:[0,.75,0,0,.55],43:[.11667,.61667,0,0,.85556],44:[.10556,.13056,0,0,.30556],45:[0,.45833,0,0,.36667],46:[0,.13056,0,0,.30556],47:[.25,.75,0,0,.55],48:[0,.69444,0,0,.55],49:[0,.69444,0,0,.55],50:[0,.69444,0,0,.55],51:[0,.69444,0,0,.55],52:[0,.69444,0,0,.55],53:[0,.69444,0,0,.55],54:[0,.69444,0,0,.55],55:[0,.69444,0,0,.55],56:[0,.69444,0,0,.55],57:[0,.69444,0,0,.55],58:[0,.45833,0,0,.30556],59:[.10556,.45833,0,0,.30556],61:[-.09375,.40625,0,0,.85556],63:[0,.69444,0,0,.51945],64:[0,.69444,0,0,.73334],65:[0,.69444,0,0,.73334],66:[0,.69444,0,0,.73334],67:[0,.69444,0,0,.70278],68:[0,.69444,0,0,.79445],69:[0,.69444,0,0,.64167],70:[0,.69444,0,0,.61111],71:[0,.69444,0,0,.73334],72:[0,.69444,0,0,.79445],73:[0,.69444,0,0,.33056],74:[0,.69444,0,0,.51945],75:[0,.69444,0,0,.76389],76:[0,.69444,0,0,.58056],77:[0,.69444,0,0,.97778],78:[0,.69444,0,0,.79445],79:[0,.69444,0,0,.79445],80:[0,.69444,0,0,.70278],81:[.10556,.69444,0,0,.79445],82:[0,.69444,0,0,.70278],83:[0,.69444,0,0,.61111],84:[0,.69444,0,0,.73334],85:[0,.69444,0,0,.76389],86:[0,.69444,.01528,0,.73334],87:[0,.69444,.01528,0,1.03889],88:[0,.69444,0,0,.73334],89:[0,.69444,.0275,0,.73334],90:[0,.69444,0,0,.67223],91:[.25,.75,0,0,.34306],93:[.25,.75,0,0,.34306],94:[0,.69444,0,0,.55],95:[.35,.10833,.03056,0,.55],97:[0,.45833,0,0,.525],98:[0,.69444,0,0,.56111],99:[0,.45833,0,0,.48889],100:[0,.69444,0,0,.56111],101:[0,.45833,0,0,.51111],102:[0,.69444,.07639,0,.33611],103:[.19444,.45833,.01528,0,.55],104:[0,.69444,0,0,.56111],105:[0,.69444,0,0,.25556],106:[.19444,.69444,0,0,.28611],107:[0,.69444,0,0,.53056],108:[0,.69444,0,0,.25556],109:[0,.45833,0,0,.86667],110:[0,.45833,0,0,.56111],111:[0,.45833,0,0,.55],112:[.19444,.45833,0,0,.56111],113:[.19444,.45833,0,0,.56111],114:[0,.45833,.01528,0,.37222],115:[0,.45833,0,0,.42167],116:[0,.58929,0,0,.40417],117:[0,.45833,0,0,.56111],118:[0,.45833,.01528,0,.5],119:[0,.45833,.01528,0,.74445],120:[0,.45833,0,0,.5],121:[.19444,.45833,.01528,0,.5],122:[0,.45833,0,0,.47639],126:[.35,.34444,0,0,.55],160:[0,0,0,0,.25],168:[0,.69444,0,0,.55],176:[0,.69444,0,0,.73334],180:[0,.69444,0,0,.55],184:[.17014,0,0,0,.48889],305:[0,.45833,0,0,.25556],567:[.19444,.45833,0,0,.28611],710:[0,.69444,0,0,.55],711:[0,.63542,0,0,.55],713:[0,.63778,0,0,.55],728:[0,.69444,0,0,.55],729:[0,.69444,0,0,.30556],730:[0,.69444,0,0,.73334],732:[0,.69444,0,0,.55],733:[0,.69444,0,0,.55],915:[0,.69444,0,0,.58056],916:[0,.69444,0,0,.91667],920:[0,.69444,0,0,.85556],923:[0,.69444,0,0,.67223],926:[0,.69444,0,0,.73334],928:[0,.69444,0,0,.79445],931:[0,.69444,0,0,.79445],933:[0,.69444,0,0,.85556],934:[0,.69444,0,0,.79445],936:[0,.69444,0,0,.85556],937:[0,.69444,0,0,.79445],8211:[0,.45833,.03056,0,.55],8212:[0,.45833,.03056,0,1.10001],8216:[0,.69444,0,0,.30556],8217:[0,.69444,0,0,.30556],8220:[0,.69444,0,0,.55834],8221:[0,.69444,0,0,.55834]},"SansSerif-Italic":{32:[0,0,0,0,.25],33:[0,.69444,.05733,0,.31945],34:[0,.69444,.00316,0,.5],35:[.19444,.69444,.05087,0,.83334],36:[.05556,.75,.11156,0,.5],37:[.05556,.75,.03126,0,.83334],38:[0,.69444,.03058,0,.75834],39:[0,.69444,.07816,0,.27778],40:[.25,.75,.13164,0,.38889],41:[.25,.75,.02536,0,.38889],42:[0,.75,.11775,0,.5],43:[.08333,.58333,.02536,0,.77778],44:[.125,.08333,0,0,.27778],45:[0,.44444,.01946,0,.33333],46:[0,.08333,0,0,.27778],47:[.25,.75,.13164,0,.5],48:[0,.65556,.11156,0,.5],49:[0,.65556,.11156,0,.5],50:[0,.65556,.11156,0,.5],51:[0,.65556,.11156,0,.5],52:[0,.65556,.11156,0,.5],53:[0,.65556,.11156,0,.5],54:[0,.65556,.11156,0,.5],55:[0,.65556,.11156,0,.5],56:[0,.65556,.11156,0,.5],57:[0,.65556,.11156,0,.5],58:[0,.44444,.02502,0,.27778],59:[.125,.44444,.02502,0,.27778],61:[-.13,.37,.05087,0,.77778],63:[0,.69444,.11809,0,.47222],64:[0,.69444,.07555,0,.66667],65:[0,.69444,0,0,.66667],66:[0,.69444,.08293,0,.66667],67:[0,.69444,.11983,0,.63889],68:[0,.69444,.07555,0,.72223],69:[0,.69444,.11983,0,.59722],70:[0,.69444,.13372,0,.56945],71:[0,.69444,.11983,0,.66667],72:[0,.69444,.08094,0,.70834],73:[0,.69444,.13372,0,.27778],74:[0,.69444,.08094,0,.47222],75:[0,.69444,.11983,0,.69445],76:[0,.69444,0,0,.54167],77:[0,.69444,.08094,0,.875],78:[0,.69444,.08094,0,.70834],79:[0,.69444,.07555,0,.73611],80:[0,.69444,.08293,0,.63889],81:[.125,.69444,.07555,0,.73611],82:[0,.69444,.08293,0,.64584],83:[0,.69444,.09205,0,.55556],84:[0,.69444,.13372,0,.68056],85:[0,.69444,.08094,0,.6875],86:[0,.69444,.1615,0,.66667],87:[0,.69444,.1615,0,.94445],88:[0,.69444,.13372,0,.66667],89:[0,.69444,.17261,0,.66667],90:[0,.69444,.11983,0,.61111],91:[.25,.75,.15942,0,.28889],93:[.25,.75,.08719,0,.28889],94:[0,.69444,.0799,0,.5],95:[.35,.09444,.08616,0,.5],97:[0,.44444,.00981,0,.48056],98:[0,.69444,.03057,0,.51667],99:[0,.44444,.08336,0,.44445],100:[0,.69444,.09483,0,.51667],101:[0,.44444,.06778,0,.44445],102:[0,.69444,.21705,0,.30556],103:[.19444,.44444,.10836,0,.5],104:[0,.69444,.01778,0,.51667],105:[0,.67937,.09718,0,.23889],106:[.19444,.67937,.09162,0,.26667],107:[0,.69444,.08336,0,.48889],108:[0,.69444,.09483,0,.23889],109:[0,.44444,.01778,0,.79445],110:[0,.44444,.01778,0,.51667],111:[0,.44444,.06613,0,.5],112:[.19444,.44444,.0389,0,.51667],113:[.19444,.44444,.04169,0,.51667],114:[0,.44444,.10836,0,.34167],115:[0,.44444,.0778,0,.38333],116:[0,.57143,.07225,0,.36111],117:[0,.44444,.04169,0,.51667],118:[0,.44444,.10836,0,.46111],119:[0,.44444,.10836,0,.68334],120:[0,.44444,.09169,0,.46111],121:[.19444,.44444,.10836,0,.46111],122:[0,.44444,.08752,0,.43472],126:[.35,.32659,.08826,0,.5],160:[0,0,0,0,.25],168:[0,.67937,.06385,0,.5],176:[0,.69444,0,0,.73752],184:[.17014,0,0,0,.44445],305:[0,.44444,.04169,0,.23889],567:[.19444,.44444,.04169,0,.26667],710:[0,.69444,.0799,0,.5],711:[0,.63194,.08432,0,.5],713:[0,.60889,.08776,0,.5],714:[0,.69444,.09205,0,.5],715:[0,.69444,0,0,.5],728:[0,.69444,.09483,0,.5],729:[0,.67937,.07774,0,.27778],730:[0,.69444,0,0,.73752],732:[0,.67659,.08826,0,.5],733:[0,.69444,.09205,0,.5],915:[0,.69444,.13372,0,.54167],916:[0,.69444,0,0,.83334],920:[0,.69444,.07555,0,.77778],923:[0,.69444,0,0,.61111],926:[0,.69444,.12816,0,.66667],928:[0,.69444,.08094,0,.70834],931:[0,.69444,.11983,0,.72222],933:[0,.69444,.09031,0,.77778],934:[0,.69444,.04603,0,.72222],936:[0,.69444,.09031,0,.77778],937:[0,.69444,.08293,0,.72222],8211:[0,.44444,.08616,0,.5],8212:[0,.44444,.08616,0,1],8216:[0,.69444,.07816,0,.27778],8217:[0,.69444,.07816,0,.27778],8220:[0,.69444,.14205,0,.5],8221:[0,.69444,.00316,0,.5]},"SansSerif-Regular":{32:[0,0,0,0,.25],33:[0,.69444,0,0,.31945],34:[0,.69444,0,0,.5],35:[.19444,.69444,0,0,.83334],36:[.05556,.75,0,0,.5],37:[.05556,.75,0,0,.83334],38:[0,.69444,0,0,.75834],39:[0,.69444,0,0,.27778],40:[.25,.75,0,0,.38889],41:[.25,.75,0,0,.38889],42:[0,.75,0,0,.5],43:[.08333,.58333,0,0,.77778],44:[.125,.08333,0,0,.27778],45:[0,.44444,0,0,.33333],46:[0,.08333,0,0,.27778],47:[.25,.75,0,0,.5],48:[0,.65556,0,0,.5],49:[0,.65556,0,0,.5],50:[0,.65556,0,0,.5],51:[0,.65556,0,0,.5],52:[0,.65556,0,0,.5],53:[0,.65556,0,0,.5],54:[0,.65556,0,0,.5],55:[0,.65556,0,0,.5],56:[0,.65556,0,0,.5],57:[0,.65556,0,0,.5],58:[0,.44444,0,0,.27778],59:[.125,.44444,0,0,.27778],61:[-.13,.37,0,0,.77778],63:[0,.69444,0,0,.47222],64:[0,.69444,0,0,.66667],65:[0,.69444,0,0,.66667],66:[0,.69444,0,0,.66667],67:[0,.69444,0,0,.63889],68:[0,.69444,0,0,.72223],69:[0,.69444,0,0,.59722],70:[0,.69444,0,0,.56945],71:[0,.69444,0,0,.66667],72:[0,.69444,0,0,.70834],73:[0,.69444,0,0,.27778],74:[0,.69444,0,0,.47222],75:[0,.69444,0,0,.69445],76:[0,.69444,0,0,.54167],77:[0,.69444,0,0,.875],78:[0,.69444,0,0,.70834],79:[0,.69444,0,0,.73611],80:[0,.69444,0,0,.63889],81:[.125,.69444,0,0,.73611],82:[0,.69444,0,0,.64584],83:[0,.69444,0,0,.55556],84:[0,.69444,0,0,.68056],85:[0,.69444,0,0,.6875],86:[0,.69444,.01389,0,.66667],87:[0,.69444,.01389,0,.94445],88:[0,.69444,0,0,.66667],89:[0,.69444,.025,0,.66667],90:[0,.69444,0,0,.61111],91:[.25,.75,0,0,.28889],93:[.25,.75,0,0,.28889],94:[0,.69444,0,0,.5],95:[.35,.09444,.02778,0,.5],97:[0,.44444,0,0,.48056],98:[0,.69444,0,0,.51667],99:[0,.44444,0,0,.44445],100:[0,.69444,0,0,.51667],101:[0,.44444,0,0,.44445],102:[0,.69444,.06944,0,.30556],103:[.19444,.44444,.01389,0,.5],104:[0,.69444,0,0,.51667],105:[0,.67937,0,0,.23889],106:[.19444,.67937,0,0,.26667],107:[0,.69444,0,0,.48889],108:[0,.69444,0,0,.23889],109:[0,.44444,0,0,.79445],110:[0,.44444,0,0,.51667],111:[0,.44444,0,0,.5],112:[.19444,.44444,0,0,.51667],113:[.19444,.44444,0,0,.51667],114:[0,.44444,.01389,0,.34167],115:[0,.44444,0,0,.38333],116:[0,.57143,0,0,.36111],117:[0,.44444,0,0,.51667],118:[0,.44444,.01389,0,.46111],119:[0,.44444,.01389,0,.68334],120:[0,.44444,0,0,.46111],121:[.19444,.44444,.01389,0,.46111],122:[0,.44444,0,0,.43472],126:[.35,.32659,0,0,.5],160:[0,0,0,0,.25],168:[0,.67937,0,0,.5],176:[0,.69444,0,0,.66667],184:[.17014,0,0,0,.44445],305:[0,.44444,0,0,.23889],567:[.19444,.44444,0,0,.26667],710:[0,.69444,0,0,.5],711:[0,.63194,0,0,.5],713:[0,.60889,0,0,.5],714:[0,.69444,0,0,.5],715:[0,.69444,0,0,.5],728:[0,.69444,0,0,.5],729:[0,.67937,0,0,.27778],730:[0,.69444,0,0,.66667],732:[0,.67659,0,0,.5],733:[0,.69444,0,0,.5],915:[0,.69444,0,0,.54167],916:[0,.69444,0,0,.83334],920:[0,.69444,0,0,.77778],923:[0,.69444,0,0,.61111],926:[0,.69444,0,0,.66667],928:[0,.69444,0,0,.70834],931:[0,.69444,0,0,.72222],933:[0,.69444,0,0,.77778],934:[0,.69444,0,0,.72222],936:[0,.69444,0,0,.77778],937:[0,.69444,0,0,.72222],8211:[0,.44444,.02778,0,.5],8212:[0,.44444,.02778,0,1],8216:[0,.69444,0,0,.27778],8217:[0,.69444,0,0,.27778],8220:[0,.69444,0,0,.5],8221:[0,.69444,0,0,.5]},"Script-Regular":{32:[0,0,0,0,.25],65:[0,.7,.22925,0,.80253],66:[0,.7,.04087,0,.90757],67:[0,.7,.1689,0,.66619],68:[0,.7,.09371,0,.77443],69:[0,.7,.18583,0,.56162],70:[0,.7,.13634,0,.89544],71:[0,.7,.17322,0,.60961],72:[0,.7,.29694,0,.96919],73:[0,.7,.19189,0,.80907],74:[.27778,.7,.19189,0,1.05159],75:[0,.7,.31259,0,.91364],76:[0,.7,.19189,0,.87373],77:[0,.7,.15981,0,1.08031],78:[0,.7,.3525,0,.9015],79:[0,.7,.08078,0,.73787],80:[0,.7,.08078,0,1.01262],81:[0,.7,.03305,0,.88282],82:[0,.7,.06259,0,.85],83:[0,.7,.19189,0,.86767],84:[0,.7,.29087,0,.74697],85:[0,.7,.25815,0,.79996],86:[0,.7,.27523,0,.62204],87:[0,.7,.27523,0,.80532],88:[0,.7,.26006,0,.94445],89:[0,.7,.2939,0,.70961],90:[0,.7,.24037,0,.8212],160:[0,0,0,0,.25]},"Size1-Regular":{32:[0,0,0,0,.25],40:[.35001,.85,0,0,.45834],41:[.35001,.85,0,0,.45834],47:[.35001,.85,0,0,.57778],91:[.35001,.85,0,0,.41667],92:[.35001,.85,0,0,.57778],93:[.35001,.85,0,0,.41667],123:[.35001,.85,0,0,.58334],125:[.35001,.85,0,0,.58334],160:[0,0,0,0,.25],710:[0,.72222,0,0,.55556],732:[0,.72222,0,0,.55556],770:[0,.72222,0,0,.55556],771:[0,.72222,0,0,.55556],8214:[-99e-5,.601,0,0,.77778],8593:[1e-5,.6,0,0,.66667],8595:[1e-5,.6,0,0,.66667],8657:[1e-5,.6,0,0,.77778],8659:[1e-5,.6,0,0,.77778],8719:[.25001,.75,0,0,.94445],8720:[.25001,.75,0,0,.94445],8721:[.25001,.75,0,0,1.05556],8730:[.35001,.85,0,0,1],8739:[-.00599,.606,0,0,.33333],8741:[-.00599,.606,0,0,.55556],8747:[.30612,.805,.19445,0,.47222],8748:[.306,.805,.19445,0,.47222],8749:[.306,.805,.19445,0,.47222],8750:[.30612,.805,.19445,0,.47222],8896:[.25001,.75,0,0,.83334],8897:[.25001,.75,0,0,.83334],8898:[.25001,.75,0,0,.83334],8899:[.25001,.75,0,0,.83334],8968:[.35001,.85,0,0,.47222],8969:[.35001,.85,0,0,.47222],8970:[.35001,.85,0,0,.47222],8971:[.35001,.85,0,0,.47222],9168:[-99e-5,.601,0,0,.66667],10216:[.35001,.85,0,0,.47222],10217:[.35001,.85,0,0,.47222],10752:[.25001,.75,0,0,1.11111],10753:[.25001,.75,0,0,1.11111],10754:[.25001,.75,0,0,1.11111],10756:[.25001,.75,0,0,.83334],10758:[.25001,.75,0,0,.83334]},"Size2-Regular":{32:[0,0,0,0,.25],40:[.65002,1.15,0,0,.59722],41:[.65002,1.15,0,0,.59722],47:[.65002,1.15,0,0,.81111],91:[.65002,1.15,0,0,.47222],92:[.65002,1.15,0,0,.81111],93:[.65002,1.15,0,0,.47222],123:[.65002,1.15,0,0,.66667],125:[.65002,1.15,0,0,.66667],160:[0,0,0,0,.25],710:[0,.75,0,0,1],732:[0,.75,0,0,1],770:[0,.75,0,0,1],771:[0,.75,0,0,1],8719:[.55001,1.05,0,0,1.27778],8720:[.55001,1.05,0,0,1.27778],8721:[.55001,1.05,0,0,1.44445],8730:[.65002,1.15,0,0,1],8747:[.86225,1.36,.44445,0,.55556],8748:[.862,1.36,.44445,0,.55556],8749:[.862,1.36,.44445,0,.55556],8750:[.86225,1.36,.44445,0,.55556],8896:[.55001,1.05,0,0,1.11111],8897:[.55001,1.05,0,0,1.11111],8898:[.55001,1.05,0,0,1.11111],8899:[.55001,1.05,0,0,1.11111],8968:[.65002,1.15,0,0,.52778],8969:[.65002,1.15,0,0,.52778],8970:[.65002,1.15,0,0,.52778],8971:[.65002,1.15,0,0,.52778],10216:[.65002,1.15,0,0,.61111],10217:[.65002,1.15,0,0,.61111],10752:[.55001,1.05,0,0,1.51112],10753:[.55001,1.05,0,0,1.51112],10754:[.55001,1.05,0,0,1.51112],10756:[.55001,1.05,0,0,1.11111],10758:[.55001,1.05,0,0,1.11111]},"Size3-Regular":{32:[0,0,0,0,.25],40:[.95003,1.45,0,0,.73611],41:[.95003,1.45,0,0,.73611],47:[.95003,1.45,0,0,1.04445],91:[.95003,1.45,0,0,.52778],92:[.95003,1.45,0,0,1.04445],93:[.95003,1.45,0,0,.52778],123:[.95003,1.45,0,0,.75],125:[.95003,1.45,0,0,.75],160:[0,0,0,0,.25],710:[0,.75,0,0,1.44445],732:[0,.75,0,0,1.44445],770:[0,.75,0,0,1.44445],771:[0,.75,0,0,1.44445],8730:[.95003,1.45,0,0,1],8968:[.95003,1.45,0,0,.58334],8969:[.95003,1.45,0,0,.58334],8970:[.95003,1.45,0,0,.58334],8971:[.95003,1.45,0,0,.58334],10216:[.95003,1.45,0,0,.75],10217:[.95003,1.45,0,0,.75]},"Size4-Regular":{32:[0,0,0,0,.25],40:[1.25003,1.75,0,0,.79167],41:[1.25003,1.75,0,0,.79167],47:[1.25003,1.75,0,0,1.27778],91:[1.25003,1.75,0,0,.58334],92:[1.25003,1.75,0,0,1.27778],93:[1.25003,1.75,0,0,.58334],123:[1.25003,1.75,0,0,.80556],125:[1.25003,1.75,0,0,.80556],160:[0,0,0,0,.25],710:[0,.825,0,0,1.8889],732:[0,.825,0,0,1.8889],770:[0,.825,0,0,1.8889],771:[0,.825,0,0,1.8889],8730:[1.25003,1.75,0,0,1],8968:[1.25003,1.75,0,0,.63889],8969:[1.25003,1.75,0,0,.63889],8970:[1.25003,1.75,0,0,.63889],8971:[1.25003,1.75,0,0,.63889],9115:[.64502,1.155,0,0,.875],9116:[1e-5,.6,0,0,.875],9117:[.64502,1.155,0,0,.875],9118:[.64502,1.155,0,0,.875],9119:[1e-5,.6,0,0,.875],9120:[.64502,1.155,0,0,.875],9121:[.64502,1.155,0,0,.66667],9122:[-99e-5,.601,0,0,.66667],9123:[.64502,1.155,0,0,.66667],9124:[.64502,1.155,0,0,.66667],9125:[-99e-5,.601,0,0,.66667],9126:[.64502,1.155,0,0,.66667],9127:[1e-5,.9,0,0,.88889],9128:[.65002,1.15,0,0,.88889],9129:[.90001,0,0,0,.88889],9130:[0,.3,0,0,.88889],9131:[1e-5,.9,0,0,.88889],9132:[.65002,1.15,0,0,.88889],9133:[.90001,0,0,0,.88889],9143:[.88502,.915,0,0,1.05556],10216:[1.25003,1.75,0,0,.80556],10217:[1.25003,1.75,0,0,.80556],57344:[-.00499,.605,0,0,1.05556],57345:[-.00499,.605,0,0,1.05556],57680:[0,.12,0,0,.45],57681:[0,.12,0,0,.45],57682:[0,.12,0,0,.45],57683:[0,.12,0,0,.45]},"Typewriter-Regular":{32:[0,0,0,0,.525],33:[0,.61111,0,0,.525],34:[0,.61111,0,0,.525],35:[0,.61111,0,0,.525],36:[.08333,.69444,0,0,.525],37:[.08333,.69444,0,0,.525],38:[0,.61111,0,0,.525],39:[0,.61111,0,0,.525],40:[.08333,.69444,0,0,.525],41:[.08333,.69444,0,0,.525],42:[0,.52083,0,0,.525],43:[-.08056,.53055,0,0,.525],44:[.13889,.125,0,0,.525],45:[-.08056,.53055,0,0,.525],46:[0,.125,0,0,.525],47:[.08333,.69444,0,0,.525],48:[0,.61111,0,0,.525],49:[0,.61111,0,0,.525],50:[0,.61111,0,0,.525],51:[0,.61111,0,0,.525],52:[0,.61111,0,0,.525],53:[0,.61111,0,0,.525],54:[0,.61111,0,0,.525],55:[0,.61111,0,0,.525],56:[0,.61111,0,0,.525],57:[0,.61111,0,0,.525],58:[0,.43056,0,0,.525],59:[.13889,.43056,0,0,.525],60:[-.05556,.55556,0,0,.525],61:[-.19549,.41562,0,0,.525],62:[-.05556,.55556,0,0,.525],63:[0,.61111,0,0,.525],64:[0,.61111,0,0,.525],65:[0,.61111,0,0,.525],66:[0,.61111,0,0,.525],67:[0,.61111,0,0,.525],68:[0,.61111,0,0,.525],69:[0,.61111,0,0,.525],70:[0,.61111,0,0,.525],71:[0,.61111,0,0,.525],72:[0,.61111,0,0,.525],73:[0,.61111,0,0,.525],74:[0,.61111,0,0,.525],75:[0,.61111,0,0,.525],76:[0,.61111,0,0,.525],77:[0,.61111,0,0,.525],78:[0,.61111,0,0,.525],79:[0,.61111,0,0,.525],80:[0,.61111,0,0,.525],81:[.13889,.61111,0,0,.525],82:[0,.61111,0,0,.525],83:[0,.61111,0,0,.525],84:[0,.61111,0,0,.525],85:[0,.61111,0,0,.525],86:[0,.61111,0,0,.525],87:[0,.61111,0,0,.525],88:[0,.61111,0,0,.525],89:[0,.61111,0,0,.525],90:[0,.61111,0,0,.525],91:[.08333,.69444,0,0,.525],92:[.08333,.69444,0,0,.525],93:[.08333,.69444,0,0,.525],94:[0,.61111,0,0,.525],95:[.09514,0,0,0,.525],96:[0,.61111,0,0,.525],97:[0,.43056,0,0,.525],98:[0,.61111,0,0,.525],99:[0,.43056,0,0,.525],100:[0,.61111,0,0,.525],101:[0,.43056,0,0,.525],102:[0,.61111,0,0,.525],103:[.22222,.43056,0,0,.525],104:[0,.61111,0,0,.525],105:[0,.61111,0,0,.525],106:[.22222,.61111,0,0,.525],107:[0,.61111,0,0,.525],108:[0,.61111,0,0,.525],109:[0,.43056,0,0,.525],110:[0,.43056,0,0,.525],111:[0,.43056,0,0,.525],112:[.22222,.43056,0,0,.525],113:[.22222,.43056,0,0,.525],114:[0,.43056,0,0,.525],115:[0,.43056,0,0,.525],116:[0,.55358,0,0,.525],117:[0,.43056,0,0,.525],118:[0,.43056,0,0,.525],119:[0,.43056,0,0,.525],120:[0,.43056,0,0,.525],121:[.22222,.43056,0,0,.525],122:[0,.43056,0,0,.525],123:[.08333,.69444,0,0,.525],124:[.08333,.69444,0,0,.525],125:[.08333,.69444,0,0,.525],126:[0,.61111,0,0,.525],127:[0,.61111,0,0,.525],160:[0,0,0,0,.525],176:[0,.61111,0,0,.525],184:[.19445,0,0,0,.525],305:[0,.43056,0,0,.525],567:[.22222,.43056,0,0,.525],711:[0,.56597,0,0,.525],713:[0,.56555,0,0,.525],714:[0,.61111,0,0,.525],715:[0,.61111,0,0,.525],728:[0,.61111,0,0,.525],730:[0,.61111,0,0,.525],770:[0,.61111,0,0,.525],771:[0,.61111,0,0,.525],776:[0,.61111,0,0,.525],915:[0,.61111,0,0,.525],916:[0,.61111,0,0,.525],920:[0,.61111,0,0,.525],923:[0,.61111,0,0,.525],926:[0,.61111,0,0,.525],928:[0,.61111,0,0,.525],931:[0,.61111,0,0,.525],933:[0,.61111,0,0,.525],934:[0,.61111,0,0,.525],936:[0,.61111,0,0,.525],937:[0,.61111,0,0,.525],8216:[0,.61111,0,0,.525],8217:[0,.61111,0,0,.525],8242:[0,.61111,0,0,.525],9251:[.11111,.21944,0,0,.525]}};const B={slant:[.25,.25,.25],space:[0,0,0],stretch:[0,0,0],shrink:[0,0,0],xHeight:[.431,.431,.431],quad:[1,1.171,1.472],extraSpace:[0,0,0],num1:[.677,.732,.925],num2:[.394,.384,.387],num3:[.444,.471,.504],denom1:[.686,.752,1.025],denom2:[.345,.344,.532],sup1:[.413,.503,.504],sup2:[.363,.431,.404],sup3:[.289,.286,.294],sub1:[.15,.143,.2],sub2:[.247,.286,.4],supDrop:[.386,.353,.494],subDrop:[.05,.071,.1],delim1:[2.39,1.7,1.98],delim2:[1.01,1.157,1.42],axisHeight:[.25,.25,.25],defaultRuleThickness:[.04,.049,.049],bigOpSpacing1:[.111,.111,.111],bigOpSpacing2:[.166,.166,.166],bigOpSpacing3:[.2,.2,.2],bigOpSpacing4:[.6,.611,.611],bigOpSpacing5:[.1,.143,.143],sqrtRuleThickness:[.04,.04,.04],ptPerEm:[10,10,10],doubleRuleSep:[.2,.2,.2],arrayRuleWidth:[.04,.04,.04],fboxsep:[.3,.3,.3],fboxrule:[.04,.04,.04]},C={"\xc5":"A","\xd0":"D","\xde":"o","\xe5":"a","\xf0":"d","\xfe":"o","\u0410":"A","\u0411":"B","\u0412":"B","\u0413":"F","\u0414":"A","\u0415":"E","\u0416":"K","\u0417":"3","\u0418":"N","\u0419":"N","\u041a":"K","\u041b":"N","\u041c":"M","\u041d":"H","\u041e":"O","\u041f":"N","\u0420":"P","\u0421":"C","\u0422":"T","\u0423":"y","\u0424":"O","\u0425":"X","\u0426":"U","\u0427":"h","\u0428":"W","\u0429":"W","\u042a":"B","\u042b":"X","\u042c":"B","\u042d":"3","\u042e":"X","\u042f":"R","\u0430":"a","\u0431":"b","\u0432":"a","\u0433":"r","\u0434":"y","\u0435":"e","\u0436":"m","\u0437":"e","\u0438":"n","\u0439":"n","\u043a":"n","\u043b":"n","\u043c":"m","\u043d":"n","\u043e":"o","\u043f":"n","\u0440":"p","\u0441":"c","\u0442":"o","\u0443":"y","\u0444":"b","\u0445":"x","\u0446":"n","\u0447":"n","\u0448":"w","\u0449":"w","\u044a":"a","\u044b":"m","\u044c":"a","\u044d":"e","\u044e":"m","\u044f":"r"};function N(e,t,r){if(!T[t])throw new Error("Font metrics not found for font: "+t+".");let n=e.charCodeAt(0),o=T[t][n];if(!o&&e[0]in C&&(n=C[e[0]].charCodeAt(0),o=T[t][n]),o||"text"!==r||S(n)&&(o=T[t][77]),o)return{depth:o[0],height:o[1],italic:o[2],skew:o[3],width:o[4]}}const q={};const I=[[1,1,1],[2,1,1],[3,1,1],[4,2,1],[5,2,1],[6,3,1],[7,4,2],[8,6,3],[9,7,6],[10,8,7],[11,10,9]],R=[.5,.6,.7,.8,.9,1,1.2,1.44,1.728,2.074,2.488],H=function(e,t){return t.size<2?e:I[e-1][t.size-1]};class O{constructor(e){this.style=void 0,this.color=void 0,this.size=void 0,this.textSize=void 0,this.phantom=void 0,this.font=void 0,this.fontFamily=void 0,this.fontWeight=void 0,this.fontShape=void 0,this.sizeMultiplier=void 0,this.maxSize=void 0,this.minRuleThickness=void 0,this._fontMetrics=void 0,this.style=e.style,this.color=e.color,this.size=e.size||O.BASESIZE,this.textSize=e.textSize||this.size,this.phantom=!!e.phantom,this.font=e.font||"",this.fontFamily=e.fontFamily||"",this.fontWeight=e.fontWeight||"",this.fontShape=e.fontShape||"",this.sizeMultiplier=R[this.size-1],this.maxSize=e.maxSize,this.minRuleThickness=e.minRuleThickness,this._fontMetrics=void 0}extend(e){const t={style:this.style,size:this.size,textSize:this.textSize,color:this.color,phantom:this.phantom,font:this.font,fontFamily:this.fontFamily,fontWeight:this.fontWeight,fontShape:this.fontShape,maxSize:this.maxSize,minRuleThickness:this.minRuleThickness};for(const r in e)e.hasOwnProperty(r)&&(t[r]=e[r]);return new O(t)}havingStyle(e){return this.style===e?this:this.extend({style:e,size:H(this.textSize,e)})}havingCrampedStyle(){return this.havingStyle(this.style.cramp())}havingSize(e){return this.size===e&&this.textSize===e?this:this.extend({style:this.style.text(),size:e,textSize:e,sizeMultiplier:R[e-1]})}havingBaseStyle(e){e=e||this.style.text();const t=H(O.BASESIZE,e);return this.size===t&&this.textSize===O.BASESIZE&&this.style===e?this:this.extend({style:e,size:t})}havingBaseSizing(){let e;switch(this.style.id){case 4:case 5:e=3;break;case 6:case 7:e=1;break;default:e=6}return this.extend({style:this.style.text(),size:e})}withColor(e){return this.extend({color:e})}withPhantom(){return this.extend({phantom:!0})}withFont(e){return this.extend({font:e})}withTextFontFamily(e){return this.extend({fontFamily:e,font:""})}withTextFontWeight(e){return this.extend({fontWeight:e,font:""})}withTextFontShape(e){return this.extend({fontShape:e,font:""})}sizingClasses(e){return e.size!==this.size?["sizing","reset-size"+e.size,"size"+this.size]:[]}baseSizingClasses(){return this.size!==O.BASESIZE?["sizing","reset-size"+this.size,"size"+O.BASESIZE]:[]}fontMetrics(){return this._fontMetrics||(this._fontMetrics=function(e){let t;if(t=e>=5?0:e>=3?1:2,!q[t]){const e=q[t]={cssEmPerMu:B.quad[t]/18};for(const r in B)B.hasOwnProperty(r)&&(e[r]=B[r][t])}return q[t]}(this.size)),this._fontMetrics}getColor(){return this.phantom?"transparent":this.color}}O.BASESIZE=6;var E=O;const L={pt:1,mm:7227/2540,cm:7227/254,in:72.27,bp:1.00375,pc:12,dd:1238/1157,cc:14856/1157,nd:685/642,nc:1370/107,sp:1/65536,px:1.00375},D={ex:!0,em:!0,mu:!0},V=function(e){return"string"!=typeof e&&(e=e.unit),e in L||e in D||"ex"===e},P=function(e,t){let r;if(e.unit in L)r=L[e.unit]/t.fontMetrics().ptPerEm/t.sizeMultiplier;else if("mu"===e.unit)r=t.fontMetrics().cssEmPerMu;else{let o;if(o=t.style.isTight()?t.havingStyle(t.style.text()):t,"ex"===e.unit)r=o.fontMetrics().xHeight;else{if("em"!==e.unit)throw new n("Invalid unit: '"+e.unit+"'");r=o.fontMetrics().quad}o!==t&&(r*=o.sizeMultiplier/t.sizeMultiplier)}return Math.min(e.number*r,t.maxSize)},F=function(e){return+e.toFixed(4)+"em"},G=function(e){return e.filter((e=>e)).join(" ")},U=function(e,t,r){if(this.classes=e||[],this.attributes={},this.height=0,this.depth=0,this.maxFontSize=0,this.style=r||{},t){t.style.isTight()&&this.classes.push("mtight");const e=t.getColor();e&&(this.style.color=e)}},Y=function(e){const t=document.createElement(e);t.className=G(this.classes);for(const e in this.style)this.style.hasOwnProperty(e)&&(t.style[e]=this.style[e]);for(const e in this.attributes)this.attributes.hasOwnProperty(e)&&t.setAttribute(e,this.attributes[e]);for(let e=0;e/=\x00-\x1f]/,W=function(e){let t="<"+e;this.classes.length&&(t+=' class="'+l.escape(G(this.classes))+'"');let r="";for(const e in this.style)this.style.hasOwnProperty(e)&&(r+=l.hyphenate(e)+":"+this.style[e]+";");r&&(t+=' style="'+l.escape(r)+'"');for(const e in this.attributes)if(this.attributes.hasOwnProperty(e)){if(X.test(e))throw new n("Invalid attribute name '"+e+"'");t+=" "+e+'="'+l.escape(this.attributes[e])+'"'}t+=">";for(let e=0;e",t};class _{constructor(e,t,r,n){this.children=void 0,this.attributes=void 0,this.classes=void 0,this.height=void 0,this.depth=void 0,this.width=void 0,this.maxFontSize=void 0,this.style=void 0,U.call(this,e,r,n),this.children=t||[]}setAttribute(e,t){this.attributes[e]=t}hasClass(e){return l.contains(this.classes,e)}toNode(){return Y.call(this,"span")}toMarkup(){return W.call(this,"span")}}class j{constructor(e,t,r,n){this.children=void 0,this.attributes=void 0,this.classes=void 0,this.height=void 0,this.depth=void 0,this.maxFontSize=void 0,this.style=void 0,U.call(this,t,n),this.children=r||[],this.setAttribute("href",e)}setAttribute(e,t){this.attributes[e]=t}hasClass(e){return l.contains(this.classes,e)}toNode(){return Y.call(this,"a")}toMarkup(){return W.call(this,"a")}}class ${constructor(e,t,r){this.src=void 0,this.alt=void 0,this.classes=void 0,this.height=void 0,this.depth=void 0,this.maxFontSize=void 0,this.style=void 0,this.alt=t,this.src=e,this.classes=["mord"],this.style=r}hasClass(e){return l.contains(this.classes,e)}toNode(){const e=document.createElement("img");e.src=this.src,e.alt=this.alt,e.className="mord";for(const t in this.style)this.style.hasOwnProperty(t)&&(e.style[t]=this.style[t]);return e}toMarkup(){let e=''+l.escape(this.alt)+'=n[0]&&e<=n[1])return r.name}}return null}(this.text.charCodeAt(0));l&&this.classes.push(l+"_fallback"),/[\xee\xef\xed\xec]/.test(this.text)&&(this.text=Z[this.text])}hasClass(e){return l.contains(this.classes,e)}toNode(){const e=document.createTextNode(this.text);let t=null;this.italic>0&&(t=document.createElement("span"),t.style.marginRight=F(this.italic)),this.classes.length>0&&(t=t||document.createElement("span"),t.className=G(this.classes));for(const e in this.style)this.style.hasOwnProperty(e)&&(t=t||document.createElement("span"),t.style[e]=this.style[e]);return t?(t.appendChild(e),t):e}toMarkup(){let e=!1,t="0&&(r+="margin-right:"+this.italic+"em;");for(const e in this.style)this.style.hasOwnProperty(e)&&(r+=l.hyphenate(e)+":"+this.style[e]+";");r&&(e=!0,t+=' style="'+l.escape(r)+'"');const n=l.escape(this.text);return e?(t+=">",t+=n,t+="",t):n}}class J{constructor(e,t){this.children=void 0,this.attributes=void 0,this.children=e||[],this.attributes=t||{}}toNode(){const e=document.createElementNS("http://www.w3.org/2000/svg","svg");for(const t in this.attributes)Object.prototype.hasOwnProperty.call(this.attributes,t)&&e.setAttribute(t,this.attributes[t]);for(let t=0;t':''}}class ee{constructor(e){this.attributes=void 0,this.attributes=e||{}}toNode(){const e=document.createElementNS("http://www.w3.org/2000/svg","line");for(const t in this.attributes)Object.prototype.hasOwnProperty.call(this.attributes,t)&&e.setAttribute(t,this.attributes[t]);return e}toMarkup(){let e="","\\gt",!0),ie(ae,he,xe,"\u2208","\\in",!0),ie(ae,he,xe,"\ue020","\\@not"),ie(ae,he,xe,"\u2282","\\subset",!0),ie(ae,he,xe,"\u2283","\\supset",!0),ie(ae,he,xe,"\u2286","\\subseteq",!0),ie(ae,he,xe,"\u2287","\\supseteq",!0),ie(ae,ce,xe,"\u2288","\\nsubseteq",!0),ie(ae,ce,xe,"\u2289","\\nsupseteq",!0),ie(ae,he,xe,"\u22a8","\\models"),ie(ae,he,xe,"\u2190","\\leftarrow",!0),ie(ae,he,xe,"\u2264","\\le"),ie(ae,he,xe,"\u2264","\\leq",!0),ie(ae,he,xe,"<","\\lt",!0),ie(ae,he,xe,"\u2192","\\rightarrow",!0),ie(ae,he,xe,"\u2192","\\to"),ie(ae,ce,xe,"\u2271","\\ngeq",!0),ie(ae,ce,xe,"\u2270","\\nleq",!0),ie(ae,he,we,"\xa0","\\ "),ie(ae,he,we,"\xa0","\\space"),ie(ae,he,we,"\xa0","\\nobreakspace"),ie(le,he,we,"\xa0","\\ "),ie(le,he,we,"\xa0"," "),ie(le,he,we,"\xa0","\\space"),ie(le,he,we,"\xa0","\\nobreakspace"),ie(ae,he,we,null,"\\nobreak"),ie(ae,he,we,null,"\\allowbreak"),ie(ae,he,ye,",",","),ie(ae,he,ye,";",";"),ie(ae,ce,pe,"\u22bc","\\barwedge",!0),ie(ae,ce,pe,"\u22bb","\\veebar",!0),ie(ae,he,pe,"\u2299","\\odot",!0),ie(ae,he,pe,"\u2295","\\oplus",!0),ie(ae,he,pe,"\u2297","\\otimes",!0),ie(ae,he,ve,"\u2202","\\partial",!0),ie(ae,he,pe,"\u2298","\\oslash",!0),ie(ae,ce,pe,"\u229a","\\circledcirc",!0),ie(ae,ce,pe,"\u22a1","\\boxdot",!0),ie(ae,he,pe,"\u25b3","\\bigtriangleup"),ie(ae,he,pe,"\u25bd","\\bigtriangledown"),ie(ae,he,pe,"\u2020","\\dagger"),ie(ae,he,pe,"\u22c4","\\diamond"),ie(ae,he,pe,"\u22c6","\\star"),ie(ae,he,pe,"\u25c3","\\triangleleft"),ie(ae,he,pe,"\u25b9","\\triangleright"),ie(ae,he,be,"{","\\{"),ie(le,he,ve,"{","\\{"),ie(le,he,ve,"{","\\textbraceleft"),ie(ae,he,ue,"}","\\}"),ie(le,he,ve,"}","\\}"),ie(le,he,ve,"}","\\textbraceright"),ie(ae,he,be,"{","\\lbrace"),ie(ae,he,ue,"}","\\rbrace"),ie(ae,he,be,"[","\\lbrack",!0),ie(le,he,ve,"[","\\lbrack",!0),ie(ae,he,ue,"]","\\rbrack",!0),ie(le,he,ve,"]","\\rbrack",!0),ie(ae,he,be,"(","\\lparen",!0),ie(ae,he,ue,")","\\rparen",!0),ie(le,he,ve,"<","\\textless",!0),ie(le,he,ve,">","\\textgreater",!0),ie(ae,he,be,"\u230a","\\lfloor",!0),ie(ae,he,ue,"\u230b","\\rfloor",!0),ie(ae,he,be,"\u2308","\\lceil",!0),ie(ae,he,ue,"\u2309","\\rceil",!0),ie(ae,he,ve,"\\","\\backslash"),ie(ae,he,ve,"\u2223","|"),ie(ae,he,ve,"\u2223","\\vert"),ie(le,he,ve,"|","\\textbar",!0),ie(ae,he,ve,"\u2225","\\|"),ie(ae,he,ve,"\u2225","\\Vert"),ie(le,he,ve,"\u2225","\\textbardbl"),ie(le,he,ve,"~","\\textasciitilde"),ie(le,he,ve,"\\","\\textbackslash"),ie(le,he,ve,"^","\\textasciicircum"),ie(ae,he,xe,"\u2191","\\uparrow",!0),ie(ae,he,xe,"\u21d1","\\Uparrow",!0),ie(ae,he,xe,"\u2193","\\downarrow",!0),ie(ae,he,xe,"\u21d3","\\Downarrow",!0),ie(ae,he,xe,"\u2195","\\updownarrow",!0),ie(ae,he,xe,"\u21d5","\\Updownarrow",!0),ie(ae,he,fe,"\u2210","\\coprod"),ie(ae,he,fe,"\u22c1","\\bigvee"),ie(ae,he,fe,"\u22c0","\\bigwedge"),ie(ae,he,fe,"\u2a04","\\biguplus"),ie(ae,he,fe,"\u22c2","\\bigcap"),ie(ae,he,fe,"\u22c3","\\bigcup"),ie(ae,he,fe,"\u222b","\\int"),ie(ae,he,fe,"\u222b","\\intop"),ie(ae,he,fe,"\u222c","\\iint"),ie(ae,he,fe,"\u222d","\\iiint"),ie(ae,he,fe,"\u220f","\\prod"),ie(ae,he,fe,"\u2211","\\sum"),ie(ae,he,fe,"\u2a02","\\bigotimes"),ie(ae,he,fe,"\u2a01","\\bigoplus"),ie(ae,he,fe,"\u2a00","\\bigodot"),ie(ae,he,fe,"\u222e","\\oint"),ie(ae,he,fe,"\u222f","\\oiint"),ie(ae,he,fe,"\u2230","\\oiiint"),ie(ae,he,fe,"\u2a06","\\bigsqcup"),ie(ae,he,fe,"\u222b","\\smallint"),ie(le,he,de,"\u2026","\\textellipsis"),ie(ae,he,de,"\u2026","\\mathellipsis"),ie(le,he,de,"\u2026","\\ldots",!0),ie(ae,he,de,"\u2026","\\ldots",!0),ie(ae,he,de,"\u22ef","\\@cdots",!0),ie(ae,he,de,"\u22f1","\\ddots",!0),ie(ae,he,ve,"\u22ee","\\varvdots"),ie(le,he,ve,"\u22ee","\\varvdots"),ie(ae,he,me,"\u02ca","\\acute"),ie(ae,he,me,"\u02cb","\\grave"),ie(ae,he,me,"\xa8","\\ddot"),ie(ae,he,me,"~","\\tilde"),ie(ae,he,me,"\u02c9","\\bar"),ie(ae,he,me,"\u02d8","\\breve"),ie(ae,he,me,"\u02c7","\\check"),ie(ae,he,me,"^","\\hat"),ie(ae,he,me,"\u20d7","\\vec"),ie(ae,he,me,"\u02d9","\\dot"),ie(ae,he,me,"\u02da","\\mathring"),ie(ae,he,ge,"\ue131","\\@imath"),ie(ae,he,ge,"\ue237","\\@jmath"),ie(ae,he,ve,"\u0131","\u0131"),ie(ae,he,ve,"\u0237","\u0237"),ie(le,he,ve,"\u0131","\\i",!0),ie(le,he,ve,"\u0237","\\j",!0),ie(le,he,ve,"\xdf","\\ss",!0),ie(le,he,ve,"\xe6","\\ae",!0),ie(le,he,ve,"\u0153","\\oe",!0),ie(le,he,ve,"\xf8","\\o",!0),ie(le,he,ve,"\xc6","\\AE",!0),ie(le,he,ve,"\u0152","\\OE",!0),ie(le,he,ve,"\xd8","\\O",!0),ie(le,he,me,"\u02ca","\\'"),ie(le,he,me,"\u02cb","\\`"),ie(le,he,me,"\u02c6","\\^"),ie(le,he,me,"\u02dc","\\~"),ie(le,he,me,"\u02c9","\\="),ie(le,he,me,"\u02d8","\\u"),ie(le,he,me,"\u02d9","\\."),ie(le,he,me,"\xb8","\\c"),ie(le,he,me,"\u02da","\\r"),ie(le,he,me,"\u02c7","\\v"),ie(le,he,me,"\xa8",'\\"'),ie(le,he,me,"\u02dd","\\H"),ie(le,he,me,"\u25ef","\\textcircled");const ke={"--":!0,"---":!0,"``":!0,"''":!0};ie(le,he,ve,"\u2013","--",!0),ie(le,he,ve,"\u2013","\\textendash"),ie(le,he,ve,"\u2014","---",!0),ie(le,he,ve,"\u2014","\\textemdash"),ie(le,he,ve,"\u2018","`",!0),ie(le,he,ve,"\u2018","\\textquoteleft"),ie(le,he,ve,"\u2019","'",!0),ie(le,he,ve,"\u2019","\\textquoteright"),ie(le,he,ve,"\u201c","``",!0),ie(le,he,ve,"\u201c","\\textquotedblleft"),ie(le,he,ve,"\u201d","''",!0),ie(le,he,ve,"\u201d","\\textquotedblright"),ie(ae,he,ve,"\xb0","\\degree",!0),ie(le,he,ve,"\xb0","\\degree"),ie(le,he,ve,"\xb0","\\textdegree",!0),ie(ae,he,ve,"\xa3","\\pounds"),ie(ae,he,ve,"\xa3","\\mathsterling",!0),ie(le,he,ve,"\xa3","\\pounds"),ie(le,he,ve,"\xa3","\\textsterling",!0),ie(ae,ce,ve,"\u2720","\\maltese"),ie(le,ce,ve,"\u2720","\\maltese");const Se='0123456789/@."';for(let e=0;e<14;e++){const t=Se.charAt(e);ie(ae,he,ve,t,t)}const Me='0123456789!@*()-=+";:?/.,';for(let e=0;e<25;e++){const t=Me.charAt(e);ie(le,he,ve,t,t)}const ze="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";for(let e=0;e<52;e++){const t=ze.charAt(e);ie(ae,he,ge,t,t),ie(le,he,ve,t,t)}ie(ae,ce,ve,"C","\u2102"),ie(le,ce,ve,"C","\u2102"),ie(ae,ce,ve,"H","\u210d"),ie(le,ce,ve,"H","\u210d"),ie(ae,ce,ve,"N","\u2115"),ie(le,ce,ve,"N","\u2115"),ie(ae,ce,ve,"P","\u2119"),ie(le,ce,ve,"P","\u2119"),ie(ae,ce,ve,"Q","\u211a"),ie(le,ce,ve,"Q","\u211a"),ie(ae,ce,ve,"R","\u211d"),ie(le,ce,ve,"R","\u211d"),ie(ae,ce,ve,"Z","\u2124"),ie(le,ce,ve,"Z","\u2124"),ie(ae,he,ge,"h","\u210e"),ie(le,he,ge,"h","\u210e");let Ae="";for(let e=0;e<52;e++){const t=ze.charAt(e);Ae=String.fromCharCode(55349,56320+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),Ae=String.fromCharCode(55349,56372+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),Ae=String.fromCharCode(55349,56424+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),Ae=String.fromCharCode(55349,56580+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),Ae=String.fromCharCode(55349,56684+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),Ae=String.fromCharCode(55349,56736+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),Ae=String.fromCharCode(55349,56788+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),Ae=String.fromCharCode(55349,56840+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),Ae=String.fromCharCode(55349,56944+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),e<26&&(Ae=String.fromCharCode(55349,56632+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),Ae=String.fromCharCode(55349,56476+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae))}Ae=String.fromCharCode(55349,56668),ie(ae,he,ge,"k",Ae),ie(le,he,ve,"k",Ae);for(let e=0;e<10;e++){const t=e.toString();Ae=String.fromCharCode(55349,57294+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),Ae=String.fromCharCode(55349,57314+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),Ae=String.fromCharCode(55349,57324+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae),Ae=String.fromCharCode(55349,57334+e),ie(ae,he,ge,t,Ae),ie(le,he,ve,t,Ae)}const Te="\xd0\xde\xfe";for(let e=0;e<3;e++){const t=Te.charAt(e);ie(ae,he,ge,t,t),ie(le,he,ve,t,t)}const Be=[["mathbf","textbf","Main-Bold"],["mathbf","textbf","Main-Bold"],["mathnormal","textit","Math-Italic"],["mathnormal","textit","Math-Italic"],["boldsymbol","boldsymbol","Main-BoldItalic"],["boldsymbol","boldsymbol","Main-BoldItalic"],["mathscr","textscr","Script-Regular"],["","",""],["","",""],["","",""],["mathfrak","textfrak","Fraktur-Regular"],["mathfrak","textfrak","Fraktur-Regular"],["mathbb","textbb","AMS-Regular"],["mathbb","textbb","AMS-Regular"],["mathboldfrak","textboldfrak","Fraktur-Regular"],["mathboldfrak","textboldfrak","Fraktur-Regular"],["mathsf","textsf","SansSerif-Regular"],["mathsf","textsf","SansSerif-Regular"],["mathboldsf","textboldsf","SansSerif-Bold"],["mathboldsf","textboldsf","SansSerif-Bold"],["mathitsf","textitsf","SansSerif-Italic"],["mathitsf","textitsf","SansSerif-Italic"],["","",""],["","",""],["mathtt","texttt","Typewriter-Regular"],["mathtt","texttt","Typewriter-Regular"]],Ce=[["mathbf","textbf","Main-Bold"],["","",""],["mathsf","textsf","SansSerif-Regular"],["mathboldsf","textboldsf","SansSerif-Bold"],["mathtt","texttt","Typewriter-Regular"]],Ne=function(e,t,r){return se[r][e]&&se[r][e].replace&&(e=se[r][e].replace),{value:e,metrics:N(e,t,r)}},qe=function(e,t,r,n,o){const s=Ne(e,t,r),i=s.metrics;let a;if(e=s.value,i){let t=i.italic;("text"===r||n&&"mathit"===n.font)&&(t=0),a=new K(e,i.height,i.depth,t,i.skew,i.width,o)}else"undefined"!=typeof console&&console.warn("No character metrics for '"+e+"' in style '"+t+"' and mode '"+r+"'"),a=new K(e,0,0,0,0,0,o);if(n){a.maxFontSize=n.sizeMultiplier,n.style.isTight()&&a.classes.push("mtight");const e=n.getColor();e&&(a.style.color=e)}return a},Ie=(e,t)=>{if(G(e.classes)!==G(t.classes)||e.skew!==t.skew||e.maxFontSize!==t.maxFontSize)return!1;if(1===e.classes.length){const t=e.classes[0];if("mbin"===t||"mord"===t)return!1}for(const r in e.style)if(e.style.hasOwnProperty(r)&&e.style[r]!==t.style[r])return!1;for(const r in t.style)if(t.style.hasOwnProperty(r)&&e.style[r]!==t.style[r])return!1;return!0},Re=function(e){let t=0,r=0,n=0;for(let o=0;ot&&(t=s.height),s.depth>r&&(r=s.depth),s.maxFontSize>n&&(n=s.maxFontSize)}e.height=t,e.depth=r,e.maxFontSize=n},He=function(e,t,r,n){const o=new _(e,t,r,n);return Re(o),o},Oe=(e,t,r,n)=>new _(e,t,r,n),Ee=function(e){const t=new A(e);return Re(t),t},Le=function(e,t,r){let n,o="";switch(e){case"amsrm":o="AMS";break;case"textrm":o="Main";break;case"textsf":o="SansSerif";break;case"texttt":o="Typewriter";break;default:o=e}return n="textbf"===t&&"textit"===r?"BoldItalic":"textbf"===t?"Bold":"textit"===t?"Italic":"Regular",o+"-"+n},De={mathbf:{variant:"bold",fontName:"Main-Bold"},mathrm:{variant:"normal",fontName:"Main-Regular"},textit:{variant:"italic",fontName:"Main-Italic"},mathit:{variant:"italic",fontName:"Main-Italic"},mathnormal:{variant:"italic",fontName:"Math-Italic"},mathsfit:{variant:"sans-serif-italic",fontName:"SansSerif-Italic"},mathbb:{variant:"double-struck",fontName:"AMS-Regular"},mathcal:{variant:"script",fontName:"Caligraphic-Regular"},mathfrak:{variant:"fraktur",fontName:"Fraktur-Regular"},mathscr:{variant:"script",fontName:"Script-Regular"},mathsf:{variant:"sans-serif",fontName:"SansSerif-Regular"},mathtt:{variant:"monospace",fontName:"Typewriter-Regular"}},Ve={vec:["vec",.471,.714],oiintSize1:["oiintSize1",.957,.499],oiintSize2:["oiintSize2",1.472,.659],oiiintSize1:["oiiintSize1",1.304,.499],oiiintSize2:["oiiintSize2",1.98,.659]};var Pe={fontMap:De,makeSymbol:qe,mathsym:function(e,t,r,n){return void 0===n&&(n=[]),"boldsymbol"===r.font&&Ne(e,"Main-Bold",t).metrics?qe(e,"Main-Bold",t,r,n.concat(["mathbf"])):"\\"===e||"main"===se[t][e].font?qe(e,"Main-Regular",t,r,n):qe(e,"AMS-Regular",t,r,n.concat(["amsrm"]))},makeSpan:He,makeSvgSpan:Oe,makeLineSpan:function(e,t,r){const n=He([e],[],t);return n.height=Math.max(r||t.fontMetrics().defaultRuleThickness,t.minRuleThickness),n.style.borderBottomWidth=F(n.height),n.maxFontSize=1,n},makeAnchor:function(e,t,r,n){const o=new j(e,t,r,n);return Re(o),o},makeFragment:Ee,wrapFragment:function(e,t){return e instanceof A?He([],[e],t):e},makeVList:function(e,t){const{children:r,depth:n}=function(e){if("individualShift"===e.positionType){const t=e.children,r=[t[0]],n=-t[0].shift-t[0].elem.depth;let o=n;for(let e=1;e0)return qe(s,h,o,t,i.concat(c));if(l){let e,n;if("boldsymbol"===l){const t=function(e,t,r,n,o){return"textord"!==o&&Ne(e,"Math-BoldItalic",t).metrics?{fontName:"Math-BoldItalic",fontClass:"boldsymbol"}:{fontName:"Main-Bold",fontClass:"mathbf"}}(s,o,0,0,r);e=t.fontName,n=[t.fontClass]}else a?(e=De[l].fontName,n=[l]):(e=Le(l,t.fontWeight,t.fontShape),n=[l,t.fontWeight,t.fontShape]);if(Ne(s,e,o).metrics)return qe(s,e,o,t,i.concat(n));if(ke.hasOwnProperty(s)&&"Typewriter"===e.slice(0,10)){const r=[];for(let a=0;a{const r=He(["mspace"],[],t),n=P(e,t);return r.style.marginRight=F(n),r},staticSvg:function(e,t){const[r,n,o]=Ve[e],s=new Q(r),i=new J([s],{width:F(n),height:F(o),style:"width:"+F(n),viewBox:"0 0 "+1e3*n+" "+1e3*o,preserveAspectRatio:"xMinYMin"}),a=Oe(["overlay"],[i],t);return a.height=o,a.style.height=F(o),a.style.width=F(n),a},svgData:Ve,tryCombineChars:e=>{for(let t=0;t{const r=t.classes[0],n=e.classes[0];"mbin"===r&&l.contains(tt,n)?t.classes[0]="mord":"mbin"===n&&l.contains(et,r)&&(e.classes[0]="mord")}),{node:i},a,h),st(o,((e,t)=>{const r=lt(t),n=lt(e),o=r&&n?e.hasClass("mtight")?Xe[r][n]:Ye[r][n]:null;if(o)return Pe.makeGlue(o,s)}),{node:i},a,h),o},st=function(e,t,r,n,o){n&&e.push(n);let s=0;for(;sr=>{e.splice(t+1,0,r),s++})(s)}n&&e.pop()},it=function(e){return e instanceof A||e instanceof j||e instanceof _&&e.hasClass("enclosing")?e:null},at=function(e,t){const r=it(e);if(r){const e=r.children;if(e.length){if("right"===t)return at(e[e.length-1],"right");if("left"===t)return at(e[0],"left")}}return e},lt=function(e,t){return e?(t&&(e=at(e,t)),nt[e.classes[0]]||null):null},ht=function(e,t){const r=["nulldelimiter"].concat(e.baseSizingClasses());return Qe(t.concat(r))},ct=function(e,t,r){if(!e)return Qe();if(_e[e.type]){let n=_e[e.type](e,t);if(r&&t.size!==r.size){n=Qe(t.sizingClasses(r),[n],t);const e=t.sizeMultiplier/r.sizeMultiplier;n.height*=e,n.depth*=e}return n}throw new n("Got group of unknown type: '"+e.type+"'")};function mt(e,t){const r=Qe(["base"],e,t),n=Qe(["strut"]);return n.style.height=F(r.height+r.depth),r.depth&&(n.style.verticalAlign=F(-r.depth)),r.children.unshift(n),r}function pt(e,t){let r=null;1===e.length&&"tag"===e[0].type&&(r=e[0].tag,e=e[0].body);const n=ot(e,t,"root");let o;2===n.length&&n[1].hasClass("tag")&&(o=n.pop());const s=[];let i,a=[];for(let e=0;e0&&(s.push(mt(a,t)),a=[]),s.push(n[e]));a.length>0&&s.push(mt(a,t)),r?(i=mt(ot(r,t,!0)),i.classes=["tag"],s.push(i)):o&&s.push(o);const l=Qe(["katex-html"],s);if(l.setAttribute("aria-hidden","true"),i){const e=i.children[0];e.style.height=F(l.height+l.depth),l.depth&&(e.style.verticalAlign=F(-l.depth))}return l}function ut(e){return new A(e)}class dt{constructor(e,t,r){this.type=void 0,this.attributes=void 0,this.children=void 0,this.classes=void 0,this.type=e,this.attributes={},this.children=t||[],this.classes=r||[]}setAttribute(e,t){this.attributes[e]=t}getAttribute(e){return this.attributes[e]}toNode(){const e=document.createElementNS("http://www.w3.org/1998/Math/MathML",this.type);for(const t in this.attributes)Object.prototype.hasOwnProperty.call(this.attributes,t)&&e.setAttribute(t,this.attributes[t]);this.classes.length>0&&(e.className=G(this.classes));for(let t=0;t0&&(e+=' class ="'+l.escape(G(this.classes))+'"'),e+=">";for(let t=0;t",e}toText(){return this.children.map((e=>e.toText())).join("")}}class gt{constructor(e){this.text=void 0,this.text=e}toNode(){return document.createTextNode(this.text)}toMarkup(){return l.escape(this.toText())}toText(){return this.text}}var ft={MathNode:dt,TextNode:gt,SpaceNode:class{constructor(e){this.width=void 0,this.character=void 0,this.width=e,this.character=e>=.05555&&e<=.05556?"\u200a":e>=.1666&&e<=.1667?"\u2009":e>=.2222&&e<=.2223?"\u2005":e>=.2777&&e<=.2778?"\u2005\u200a":e>=-.05556&&e<=-.05555?"\u200a\u2063":e>=-.1667&&e<=-.1666?"\u2009\u2063":e>=-.2223&&e<=-.2222?"\u205f\u2063":e>=-.2778&&e<=-.2777?"\u2005\u2063":null}toNode(){if(this.character)return document.createTextNode(this.character);{const e=document.createElementNS("http://www.w3.org/1998/Math/MathML","mspace");return e.setAttribute("width",F(this.width)),e}}toMarkup(){return this.character?""+this.character+"":''}toText(){return this.character?this.character:" "}},newDocumentFragment:ut};const bt=function(e,t,r){return!se[t][e]||!se[t][e].replace||55349===e.charCodeAt(0)||ke.hasOwnProperty(e)&&r&&(r.fontFamily&&"tt"===r.fontFamily.slice(4,6)||r.font&&"tt"===r.font.slice(4,6))||(e=se[t][e].replace),new ft.TextNode(e)},yt=function(e){return 1===e.length?e[0]:new ft.MathNode("mrow",e)},xt=function(e,t){if("texttt"===t.fontFamily)return"monospace";if("textsf"===t.fontFamily)return"textit"===t.fontShape&&"textbf"===t.fontWeight?"sans-serif-bold-italic":"textit"===t.fontShape?"sans-serif-italic":"textbf"===t.fontWeight?"bold-sans-serif":"sans-serif";if("textit"===t.fontShape&&"textbf"===t.fontWeight)return"bold-italic";if("textit"===t.fontShape)return"italic";if("textbf"===t.fontWeight)return"bold";const r=t.font;if(!r||"mathnormal"===r)return null;const n=e.mode;if("mathit"===r)return"italic";if("boldsymbol"===r)return"textord"===e.type?"bold":"bold-italic";if("mathbf"===r)return"bold";if("mathbb"===r)return"double-struck";if("mathsfit"===r)return"sans-serif-italic";if("mathfrak"===r)return"fraktur";if("mathscr"===r||"mathcal"===r)return"script";if("mathsf"===r)return"sans-serif";if("mathtt"===r)return"monospace";let o=e.text;if(l.contains(["\\imath","\\jmath"],o))return null;se[n][o]&&se[n][o].replace&&(o=se[n][o].replace);return N(o,Pe.fontMap[r].fontName,n)?Pe.fontMap[r].variant:null};function wt(e){if(!e)return!1;if("mi"===e.type&&1===e.children.length){const t=e.children[0];return t instanceof gt&&"."===t.text}if("mo"===e.type&&1===e.children.length&&"true"===e.getAttribute("separator")&&"0em"===e.getAttribute("lspace")&&"0em"===e.getAttribute("rspace")){const t=e.children[0];return t instanceof gt&&","===t.text}return!1}const vt=function(e,t,r){if(1===e.length){const n=St(e[0],t);return r&&n instanceof dt&&"mo"===n.type&&(n.setAttribute("lspace","0em"),n.setAttribute("rspace","0em")),[n]}const n=[];let o;for(let r=0;r=1&&("mn"===o.type||wt(o))){const e=s.children[0];e instanceof dt&&"mn"===e.type&&(e.children=[...o.children,...e.children],n.pop())}else if("mi"===o.type&&1===o.children.length){const e=o.children[0];if(e instanceof gt&&"\u0338"===e.text&&("mo"===s.type||"mi"===s.type||"mn"===s.type)){const e=s.children[0];e instanceof gt&&e.text.length>0&&(e.text=e.text.slice(0,1)+"\u0338"+e.text.slice(1),n.pop())}}}n.push(s),o=s}return n},kt=function(e,t,r){return yt(vt(e,t,r))},St=function(e,t){if(!e)return new ft.MathNode("mrow");if(je[e.type]){return je[e.type](e,t)}throw new n("Got group of unknown type: '"+e.type+"'")};function Mt(e,t,r,n,o){const s=vt(e,r);let i;i=1===s.length&&s[0]instanceof dt&&l.contains(["mrow","mtable"],s[0].type)?s[0]:new ft.MathNode("mrow",s);const a=new ft.MathNode("annotation",[new ft.TextNode(t)]);a.setAttribute("encoding","application/x-tex");const h=new ft.MathNode("semantics",[i,a]),c=new ft.MathNode("math",[h]);c.setAttribute("xmlns","http://www.w3.org/1998/Math/MathML"),n&&c.setAttribute("display","block");const m=o?"katex":"katex-mathml";return Pe.makeSpan([m],[c])}const zt=function(e){return new E({style:e.displayMode?w.DISPLAY:w.TEXT,maxSize:e.maxSize,minRuleThickness:e.minRuleThickness})},At=function(e,t){if(t.displayMode){const r=["katex-display"];t.leqno&&r.push("leqno"),t.fleqn&&r.push("fleqn"),e=Pe.makeSpan(r,[e])}return e},Tt=function(e,t,r){const n=zt(r);let o;if("mathml"===r.output)return Mt(e,t,n,r.displayMode,!0);if("html"===r.output){const t=pt(e,n);o=Pe.makeSpan(["katex"],[t])}else{const s=Mt(e,t,n,r.displayMode,!1),i=pt(e,n);o=Pe.makeSpan(["katex"],[s,i])}return At(o,r)};const Bt={widehat:"^",widecheck:"\u02c7",widetilde:"~",utilde:"~",overleftarrow:"\u2190",underleftarrow:"\u2190",xleftarrow:"\u2190",overrightarrow:"\u2192",underrightarrow:"\u2192",xrightarrow:"\u2192",underbrace:"\u23df",overbrace:"\u23de",overgroup:"\u23e0",undergroup:"\u23e1",overleftrightarrow:"\u2194",underleftrightarrow:"\u2194",xleftrightarrow:"\u2194",Overrightarrow:"\u21d2",xRightarrow:"\u21d2",overleftharpoon:"\u21bc",xleftharpoonup:"\u21bc",overrightharpoon:"\u21c0",xrightharpoonup:"\u21c0",xLeftarrow:"\u21d0",xLeftrightarrow:"\u21d4",xhookleftarrow:"\u21a9",xhookrightarrow:"\u21aa",xmapsto:"\u21a6",xrightharpoondown:"\u21c1",xleftharpoondown:"\u21bd",xrightleftharpoons:"\u21cc",xleftrightharpoons:"\u21cb",xtwoheadleftarrow:"\u219e",xtwoheadrightarrow:"\u21a0",xlongequal:"=",xtofrom:"\u21c4",xrightleftarrows:"\u21c4",xrightequilibrium:"\u21cc",xleftequilibrium:"\u21cb","\\cdrightarrow":"\u2192","\\cdleftarrow":"\u2190","\\cdlongequal":"="},Ct={overrightarrow:[["rightarrow"],.888,522,"xMaxYMin"],overleftarrow:[["leftarrow"],.888,522,"xMinYMin"],underrightarrow:[["rightarrow"],.888,522,"xMaxYMin"],underleftarrow:[["leftarrow"],.888,522,"xMinYMin"],xrightarrow:[["rightarrow"],1.469,522,"xMaxYMin"],"\\cdrightarrow":[["rightarrow"],3,522,"xMaxYMin"],xleftarrow:[["leftarrow"],1.469,522,"xMinYMin"],"\\cdleftarrow":[["leftarrow"],3,522,"xMinYMin"],Overrightarrow:[["doublerightarrow"],.888,560,"xMaxYMin"],xRightarrow:[["doublerightarrow"],1.526,560,"xMaxYMin"],xLeftarrow:[["doubleleftarrow"],1.526,560,"xMinYMin"],overleftharpoon:[["leftharpoon"],.888,522,"xMinYMin"],xleftharpoonup:[["leftharpoon"],.888,522,"xMinYMin"],xleftharpoondown:[["leftharpoondown"],.888,522,"xMinYMin"],overrightharpoon:[["rightharpoon"],.888,522,"xMaxYMin"],xrightharpoonup:[["rightharpoon"],.888,522,"xMaxYMin"],xrightharpoondown:[["rightharpoondown"],.888,522,"xMaxYMin"],xlongequal:[["longequal"],.888,334,"xMinYMin"],"\\cdlongequal":[["longequal"],3,334,"xMinYMin"],xtwoheadleftarrow:[["twoheadleftarrow"],.888,334,"xMinYMin"],xtwoheadrightarrow:[["twoheadrightarrow"],.888,334,"xMaxYMin"],overleftrightarrow:[["leftarrow","rightarrow"],.888,522],overbrace:[["leftbrace","midbrace","rightbrace"],1.6,548],underbrace:[["leftbraceunder","midbraceunder","rightbraceunder"],1.6,548],underleftrightarrow:[["leftarrow","rightarrow"],.888,522],xleftrightarrow:[["leftarrow","rightarrow"],1.75,522],xLeftrightarrow:[["doubleleftarrow","doublerightarrow"],1.75,560],xrightleftharpoons:[["leftharpoondownplus","rightharpoonplus"],1.75,716],xleftrightharpoons:[["leftharpoonplus","rightharpoondownplus"],1.75,716],xhookleftarrow:[["leftarrow","righthook"],1.08,522],xhookrightarrow:[["lefthook","rightarrow"],1.08,522],overlinesegment:[["leftlinesegment","rightlinesegment"],.888,522],underlinesegment:[["leftlinesegment","rightlinesegment"],.888,522],overgroup:[["leftgroup","rightgroup"],.888,342],undergroup:[["leftgroupunder","rightgroupunder"],.888,342],xmapsto:[["leftmapsto","rightarrow"],1.5,522],xtofrom:[["leftToFrom","rightToFrom"],1.75,528],xrightleftarrows:[["baraboveleftarrow","rightarrowabovebar"],1.75,901],xrightequilibrium:[["baraboveshortleftharpoon","rightharpoonaboveshortbar"],1.75,716],xleftequilibrium:[["shortbaraboveleftharpoon","shortrightharpoonabovebar"],1.75,716]};var Nt=function(e,t,r,n,o){let s;const i=e.height+e.depth+r+n;if(/fbox|color|angl/.test(t)){if(s=Pe.makeSpan(["stretchy",t],[],o),"fbox"===t){const e=o.color&&o.getColor();e&&(s.style.borderColor=e)}}else{const e=[];/^[bx]cancel$/.test(t)&&e.push(new ee({x1:"0",y1:"0",x2:"100%",y2:"100%","stroke-width":"0.046em"})),/^x?cancel$/.test(t)&&e.push(new ee({x1:"0",y1:"100%",x2:"100%",y2:"0","stroke-width":"0.046em"}));const r=new J(e,{width:"100%",height:F(i)});s=Pe.makeSvgSpan([],[r],o)}return s.height=i,s.style.height=F(i),s},qt=function(e){const t=new ft.MathNode("mo",[new ft.TextNode(Bt[e.replace(/^\\/,"")])]);return t.setAttribute("stretchy","true"),t},It=function(e,t){const{span:r,minWidth:n,height:o}=function(){let r=4e5;const n=e.label.slice(1);if(l.contains(["widehat","widecheck","widetilde","utilde"],n)){const s="ordgroup"===(o=e.base).type?o.body.length:1;let i,a,l;if(s>5)"widehat"===n||"widecheck"===n?(i=420,r=2364,l=.42,a=n+"4"):(i=312,r=2340,l=.34,a="tilde4");else{const e=[1,1,2,2,3,3][s];"widehat"===n||"widecheck"===n?(r=[0,1062,2364,2364,2364][e],i=[0,239,300,360,420][e],l=[0,.24,.3,.3,.36,.42][e],a=n+e):(r=[0,600,1033,2339,2340][e],i=[0,260,286,306,312][e],l=[0,.26,.286,.3,.306,.34][e],a="tilde"+e)}const h=new Q(a),c=new J([h],{width:"100%",height:F(l),viewBox:"0 0 "+r+" "+i,preserveAspectRatio:"none"});return{span:Pe.makeSvgSpan([],[c],t),minWidth:0,height:l}}{const e=[],o=Ct[n],[s,i,a]=o,l=a/1e3,h=s.length;let c,m;if(1===h){c=["hide-tail"],m=[o[3]]}else if(2===h)c=["halfarrow-left","halfarrow-right"],m=["xMinYMin","xMaxYMin"];else{if(3!==h)throw new Error("Correct katexImagesData or update code here to support\n "+h+" children.");c=["brace-left","brace-center","brace-right"],m=["xMinYMin","xMidYMin","xMaxYMin"]}for(let n=0;n0&&(r.style.minWidth=F(n)),r};function Rt(e,t){if(!e||e.type!==t)throw new Error("Expected node of type "+t+", but got "+(e?"node of type "+e.type:String(e)));return e}function Ht(e){const t=Ot(e);if(!t)throw new Error("Expected node of symbol group type, but got "+(e?"node of type "+e.type:String(e)));return t}function Ot(e){return e&&("atom"===e.type||ne.hasOwnProperty(e.type))?e:null}const Et=(e,t)=>{let r,n,o;e&&"supsub"===e.type?(n=Rt(e.base,"accent"),r=n.base,e.base=r,o=function(e){if(e instanceof _)return e;throw new Error("Expected span but got "+String(e)+".")}(ct(e,t)),e.base=n):(n=Rt(e,"accent"),r=n.base);const s=ct(r,t.havingCrampedStyle());let i=0;if(n.isShifty&&l.isCharacterBox(r)){const e=l.getBaseElem(r);i=te(ct(e,t.havingCrampedStyle())).skew}const a="\\c"===n.label;let h,c=a?s.height+s.depth:Math.min(s.height,t.fontMetrics().xHeight);if(n.isStretchy)h=It(n,t),h=Pe.makeVList({positionType:"firstBaseline",children:[{type:"elem",elem:s},{type:"elem",elem:h,wrapperClasses:["svg-align"],wrapperStyle:i>0?{width:"calc(100% - "+F(2*i)+")",marginLeft:F(2*i)}:void 0}]},t);else{let e,r;"\\vec"===n.label?(e=Pe.staticSvg("vec",t),r=Pe.svgData.vec[1]):(e=Pe.makeOrd({mode:n.mode,text:n.label},t,"textord"),e=te(e),e.italic=0,r=e.width,a&&(c+=e.depth)),h=Pe.makeSpan(["accent-body"],[e]);const o="\\textcircled"===n.label;o&&(h.classes.push("accent-full"),c=s.height);let l=i;o||(l-=r/2),h.style.left=F(l),"\\textcircled"===n.label&&(h.style.top=".2em"),h=Pe.makeVList({positionType:"firstBaseline",children:[{type:"elem",elem:s},{type:"kern",size:-c},{type:"elem",elem:h}]},t)}const m=Pe.makeSpan(["mord","accent"],[h],t);return o?(o.children[0]=m,o.height=Math.max(m.height,o.height),o.classes[0]="mord",o):m},Lt=(e,t)=>{const r=e.isStretchy?qt(e.label):new ft.MathNode("mo",[bt(e.label,e.mode)]),n=new ft.MathNode("mover",[St(e.base,t),r]);return n.setAttribute("accent","true"),n},Dt=new RegExp(["\\acute","\\grave","\\ddot","\\tilde","\\bar","\\breve","\\check","\\hat","\\vec","\\dot","\\mathring"].map((e=>"\\"+e)).join("|"));$e({type:"accent",names:["\\acute","\\grave","\\ddot","\\tilde","\\bar","\\breve","\\check","\\hat","\\vec","\\dot","\\mathring","\\widecheck","\\widehat","\\widetilde","\\overrightarrow","\\overleftarrow","\\Overrightarrow","\\overleftrightarrow","\\overgroup","\\overlinesegment","\\overleftharpoon","\\overrightharpoon"],props:{numArgs:1},handler:(e,t)=>{const r=Ke(t[0]),n=!Dt.test(e.funcName),o=!n||"\\widehat"===e.funcName||"\\widetilde"===e.funcName||"\\widecheck"===e.funcName;return{type:"accent",mode:e.parser.mode,label:e.funcName,isStretchy:n,isShifty:o,base:r}},htmlBuilder:Et,mathmlBuilder:Lt}),$e({type:"accent",names:["\\'","\\`","\\^","\\~","\\=","\\u","\\.",'\\"',"\\c","\\r","\\H","\\v","\\textcircled"],props:{numArgs:1,allowedInText:!0,allowedInMath:!0,argTypes:["primitive"]},handler:(e,t)=>{const r=t[0];let n=e.parser.mode;return"math"===n&&(e.parser.settings.reportNonstrict("mathVsTextAccents","LaTeX's accent "+e.funcName+" works only in text mode"),n="text"),{type:"accent",mode:n,label:e.funcName,isStretchy:!1,isShifty:!0,base:r}},htmlBuilder:Et,mathmlBuilder:Lt}),$e({type:"accentUnder",names:["\\underleftarrow","\\underrightarrow","\\underleftrightarrow","\\undergroup","\\underlinesegment","\\utilde"],props:{numArgs:1},handler:(e,t)=>{let{parser:r,funcName:n}=e;const o=t[0];return{type:"accentUnder",mode:r.mode,label:n,base:o}},htmlBuilder:(e,t)=>{const r=ct(e.base,t),n=It(e,t),o="\\utilde"===e.label?.12:0,s=Pe.makeVList({positionType:"top",positionData:r.height,children:[{type:"elem",elem:n,wrapperClasses:["svg-align"]},{type:"kern",size:o},{type:"elem",elem:r}]},t);return Pe.makeSpan(["mord","accentunder"],[s],t)},mathmlBuilder:(e,t)=>{const r=qt(e.label),n=new ft.MathNode("munder",[St(e.base,t),r]);return n.setAttribute("accentunder","true"),n}});const Vt=e=>{const t=new ft.MathNode("mpadded",e?[e]:[]);return t.setAttribute("width","+0.6em"),t.setAttribute("lspace","0.3em"),t};$e({type:"xArrow",names:["\\xleftarrow","\\xrightarrow","\\xLeftarrow","\\xRightarrow","\\xleftrightarrow","\\xLeftrightarrow","\\xhookleftarrow","\\xhookrightarrow","\\xmapsto","\\xrightharpoondown","\\xrightharpoonup","\\xleftharpoondown","\\xleftharpoonup","\\xrightleftharpoons","\\xleftrightharpoons","\\xlongequal","\\xtwoheadrightarrow","\\xtwoheadleftarrow","\\xtofrom","\\xrightleftarrows","\\xrightequilibrium","\\xleftequilibrium","\\\\cdrightarrow","\\\\cdleftarrow","\\\\cdlongequal"],props:{numArgs:1,numOptionalArgs:1},handler(e,t,r){let{parser:n,funcName:o}=e;return{type:"xArrow",mode:n.mode,label:o,body:t[0],below:r[0]}},htmlBuilder(e,t){const r=t.style;let n=t.havingStyle(r.sup());const o=Pe.wrapFragment(ct(e.body,n,t),t),s="\\x"===e.label.slice(0,2)?"x":"cd";let i;o.classes.push(s+"-arrow-pad"),e.below&&(n=t.havingStyle(r.sub()),i=Pe.wrapFragment(ct(e.below,n,t),t),i.classes.push(s+"-arrow-pad"));const a=It(e,t),l=-t.fontMetrics().axisHeight+.5*a.height;let h,c=-t.fontMetrics().axisHeight-.5*a.height-.111;if((o.depth>.25||"\\xleftequilibrium"===e.label)&&(c-=o.depth),i){const e=-t.fontMetrics().axisHeight+i.height+.5*a.height+.111;h=Pe.makeVList({positionType:"individualShift",children:[{type:"elem",elem:o,shift:c},{type:"elem",elem:a,shift:l},{type:"elem",elem:i,shift:e}]},t)}else h=Pe.makeVList({positionType:"individualShift",children:[{type:"elem",elem:o,shift:c},{type:"elem",elem:a,shift:l}]},t);return h.children[0].children[0].children[1].classes.push("svg-align"),Pe.makeSpan(["mrel","x-arrow"],[h],t)},mathmlBuilder(e,t){const r=qt(e.label);let n;if(r.setAttribute("minsize","x"===e.label.charAt(0)?"1.75em":"3.0em"),e.body){const o=Vt(St(e.body,t));if(e.below){const s=Vt(St(e.below,t));n=new ft.MathNode("munderover",[r,s,o])}else n=new ft.MathNode("mover",[r,o])}else if(e.below){const o=Vt(St(e.below,t));n=new ft.MathNode("munder",[r,o])}else n=Vt(),n=new ft.MathNode("mover",[r,n]);return n}});const Pt=Pe.makeSpan;function Ft(e,t){const r=ot(e.body,t,!0);return Pt([e.mclass],r,t)}function Gt(e,t){let r;const n=vt(e.body,t);return"minner"===e.mclass?r=new ft.MathNode("mpadded",n):"mord"===e.mclass?e.isCharacterBox?(r=n[0],r.type="mi"):r=new ft.MathNode("mi",n):(e.isCharacterBox?(r=n[0],r.type="mo"):r=new ft.MathNode("mo",n),"mbin"===e.mclass?(r.attributes.lspace="0.22em",r.attributes.rspace="0.22em"):"mpunct"===e.mclass?(r.attributes.lspace="0em",r.attributes.rspace="0.17em"):"mopen"===e.mclass||"mclose"===e.mclass?(r.attributes.lspace="0em",r.attributes.rspace="0em"):"minner"===e.mclass&&(r.attributes.lspace="0.0556em",r.attributes.width="+0.1111em")),r}$e({type:"mclass",names:["\\mathord","\\mathbin","\\mathrel","\\mathopen","\\mathclose","\\mathpunct","\\mathinner"],props:{numArgs:1,primitive:!0},handler(e,t){let{parser:r,funcName:n}=e;const o=t[0];return{type:"mclass",mode:r.mode,mclass:"m"+n.slice(5),body:Je(o),isCharacterBox:l.isCharacterBox(o)}},htmlBuilder:Ft,mathmlBuilder:Gt});const Ut=e=>{const t="ordgroup"===e.type&&e.body.length?e.body[0]:e;return"atom"!==t.type||"bin"!==t.family&&"rel"!==t.family?"mord":"m"+t.family};$e({type:"mclass",names:["\\@binrel"],props:{numArgs:2},handler(e,t){let{parser:r}=e;return{type:"mclass",mode:r.mode,mclass:Ut(t[0]),body:Je(t[1]),isCharacterBox:l.isCharacterBox(t[1])}}}),$e({type:"mclass",names:["\\stackrel","\\overset","\\underset"],props:{numArgs:2},handler(e,t){let{parser:r,funcName:n}=e;const o=t[1],s=t[0];let i;i="\\stackrel"!==n?Ut(o):"mrel";const a={type:"op",mode:o.mode,limits:!0,alwaysHandleSupSub:!0,parentIsSupSub:!1,symbol:!1,suppressBaseShift:"\\stackrel"!==n,body:Je(o)},h={type:"supsub",mode:s.mode,base:a,sup:"\\underset"===n?null:s,sub:"\\underset"===n?s:null};return{type:"mclass",mode:r.mode,mclass:i,body:[h],isCharacterBox:l.isCharacterBox(h)}},htmlBuilder:Ft,mathmlBuilder:Gt}),$e({type:"pmb",names:["\\pmb"],props:{numArgs:1,allowedInText:!0},handler(e,t){let{parser:r}=e;return{type:"pmb",mode:r.mode,mclass:Ut(t[0]),body:Je(t[0])}},htmlBuilder(e,t){const r=ot(e.body,t,!0),n=Pe.makeSpan([e.mclass],r,t);return n.style.textShadow="0.02em 0.01em 0.04px",n},mathmlBuilder(e,t){const r=vt(e.body,t),n=new ft.MathNode("mstyle",r);return n.setAttribute("style","text-shadow: 0.02em 0.01em 0.04px"),n}});const Yt={">":"\\\\cdrightarrow","<":"\\\\cdleftarrow","=":"\\\\cdlongequal",A:"\\uparrow",V:"\\downarrow","|":"\\Vert",".":"no arrow"},Xt=e=>"textord"===e.type&&"@"===e.text;function Wt(e,t,r){const n=Yt[e];switch(n){case"\\\\cdrightarrow":case"\\\\cdleftarrow":return r.callFunction(n,[t[0]],[t[1]]);case"\\uparrow":case"\\downarrow":{const e={type:"atom",text:n,mode:"math",family:"rel"},o={type:"ordgroup",mode:"math",body:[r.callFunction("\\\\cdleft",[t[0]],[]),r.callFunction("\\Big",[e],[]),r.callFunction("\\\\cdright",[t[1]],[])]};return r.callFunction("\\\\cdparent",[o],[])}case"\\\\cdlongequal":return r.callFunction("\\\\cdlongequal",[],[]);case"\\Vert":{const e={type:"textord",text:"\\Vert",mode:"math"};return r.callFunction("\\Big",[e],[])}default:return{type:"textord",text:" ",mode:"math"}}}$e({type:"cdlabel",names:["\\\\cdleft","\\\\cdright"],props:{numArgs:1},handler(e,t){let{parser:r,funcName:n}=e;return{type:"cdlabel",mode:r.mode,side:n.slice(4),label:t[0]}},htmlBuilder(e,t){const r=t.havingStyle(t.style.sup()),n=Pe.wrapFragment(ct(e.label,r,t),t);return n.classes.push("cd-label-"+e.side),n.style.bottom=F(.8-n.depth),n.height=0,n.depth=0,n},mathmlBuilder(e,t){let r=new ft.MathNode("mrow",[St(e.label,t)]);return r=new ft.MathNode("mpadded",[r]),r.setAttribute("width","0"),"left"===e.side&&r.setAttribute("lspace","-1width"),r.setAttribute("voffset","0.7em"),r=new ft.MathNode("mstyle",[r]),r.setAttribute("displaystyle","false"),r.setAttribute("scriptlevel","1"),r}}),$e({type:"cdlabelparent",names:["\\\\cdparent"],props:{numArgs:1},handler(e,t){let{parser:r}=e;return{type:"cdlabelparent",mode:r.mode,fragment:t[0]}},htmlBuilder(e,t){const r=Pe.wrapFragment(ct(e.fragment,t),t);return r.classes.push("cd-vert-arrow"),r},mathmlBuilder(e,t){return new ft.MathNode("mrow",[St(e.fragment,t)])}}),$e({type:"textord",names:["\\@char"],props:{numArgs:1,allowedInText:!0},handler(e,t){let{parser:r}=e;const o=Rt(t[0],"ordgroup").body;let s="";for(let e=0;e=1114111)throw new n("\\@char with invalid code point "+s);return a<=65535?i=String.fromCharCode(a):(a-=65536,i=String.fromCharCode(55296+(a>>10),56320+(1023&a))),{type:"textord",mode:r.mode,text:i}}});const _t=(e,t)=>{const r=ot(e.body,t.withColor(e.color),!1);return Pe.makeFragment(r)},jt=(e,t)=>{const r=vt(e.body,t.withColor(e.color)),n=new ft.MathNode("mstyle",r);return n.setAttribute("mathcolor",e.color),n};$e({type:"color",names:["\\textcolor"],props:{numArgs:2,allowedInText:!0,argTypes:["color","original"]},handler(e,t){let{parser:r}=e;const n=Rt(t[0],"color-token").color,o=t[1];return{type:"color",mode:r.mode,color:n,body:Je(o)}},htmlBuilder:_t,mathmlBuilder:jt}),$e({type:"color",names:["\\color"],props:{numArgs:1,allowedInText:!0,argTypes:["color"]},handler(e,t){let{parser:r,breakOnTokenText:n}=e;const o=Rt(t[0],"color-token").color;r.gullet.macros.set("\\current@color",o);const s=r.parseExpression(!0,n);return{type:"color",mode:r.mode,color:o,body:s}},htmlBuilder:_t,mathmlBuilder:jt}),$e({type:"cr",names:["\\\\"],props:{numArgs:0,numOptionalArgs:0,allowedInText:!0},handler(e,t,r){let{parser:n}=e;const o="["===n.gullet.future().text?n.parseSizeGroup(!0):null,s=!n.settings.displayMode||!n.settings.useStrictBehavior("newLineInDisplayMode","In LaTeX, \\\\ or \\newline does nothing in display mode");return{type:"cr",mode:n.mode,newLine:s,size:o&&Rt(o,"size").value}},htmlBuilder(e,t){const r=Pe.makeSpan(["mspace"],[],t);return e.newLine&&(r.classes.push("newline"),e.size&&(r.style.marginTop=F(P(e.size,t)))),r},mathmlBuilder(e,t){const r=new ft.MathNode("mspace");return e.newLine&&(r.setAttribute("linebreak","newline"),e.size&&r.setAttribute("height",F(P(e.size,t)))),r}});const $t={"\\global":"\\global","\\long":"\\\\globallong","\\\\globallong":"\\\\globallong","\\def":"\\gdef","\\gdef":"\\gdef","\\edef":"\\xdef","\\xdef":"\\xdef","\\let":"\\\\globallet","\\futurelet":"\\\\globalfuture"},Zt=e=>{const t=e.text;if(/^(?:[\\{}$&#^_]|EOF)$/.test(t))throw new n("Expected a control sequence",e);return t},Kt=(e,t,r,n)=>{let o=e.gullet.macros.get(r.text);null==o&&(r.noexpand=!0,o={tokens:[r],numArgs:0,unexpandable:!e.gullet.isExpandable(r.text)}),e.gullet.macros.set(t,o,n)};$e({type:"internal",names:["\\global","\\long","\\\\globallong"],props:{numArgs:0,allowedInText:!0},handler(e){let{parser:t,funcName:r}=e;t.consumeSpaces();const o=t.fetch();if($t[o.text])return"\\global"!==r&&"\\\\globallong"!==r||(o.text=$t[o.text]),Rt(t.parseFunction(),"internal");throw new n("Invalid token after macro prefix",o)}}),$e({type:"internal",names:["\\def","\\gdef","\\edef","\\xdef"],props:{numArgs:0,allowedInText:!0,primitive:!0},handler(e){let{parser:t,funcName:r}=e,o=t.gullet.popToken();const s=o.text;if(/^(?:[\\{}$&#^_]|EOF)$/.test(s))throw new n("Expected a control sequence",o);let i,a=0;const l=[[]];for(;"{"!==t.gullet.future().text;)if(o=t.gullet.popToken(),"#"===o.text){if("{"===t.gullet.future().text){i=t.gullet.future(),l[a].push("{");break}if(o=t.gullet.popToken(),!/^[1-9]$/.test(o.text))throw new n('Invalid argument number "'+o.text+'"');if(parseInt(o.text)!==a+1)throw new n('Argument number "'+o.text+'" out of order');a++,l.push([])}else{if("EOF"===o.text)throw new n("Expected a macro definition");l[a].push(o.text)}let{tokens:h}=t.gullet.consumeArg();return i&&h.unshift(i),"\\edef"!==r&&"\\xdef"!==r||(h=t.gullet.expandTokens(h),h.reverse()),t.gullet.macros.set(s,{tokens:h,numArgs:a,delimiters:l},r===$t[r]),{type:"internal",mode:t.mode}}}),$e({type:"internal",names:["\\let","\\\\globallet"],props:{numArgs:0,allowedInText:!0,primitive:!0},handler(e){let{parser:t,funcName:r}=e;const n=Zt(t.gullet.popToken());t.gullet.consumeSpaces();const o=(e=>{let t=e.gullet.popToken();return"="===t.text&&(t=e.gullet.popToken()," "===t.text&&(t=e.gullet.popToken())),t})(t);return Kt(t,n,o,"\\\\globallet"===r),{type:"internal",mode:t.mode}}}),$e({type:"internal",names:["\\futurelet","\\\\globalfuture"],props:{numArgs:0,allowedInText:!0,primitive:!0},handler(e){let{parser:t,funcName:r}=e;const n=Zt(t.gullet.popToken()),o=t.gullet.popToken(),s=t.gullet.popToken();return Kt(t,n,s,"\\\\globalfuture"===r),t.gullet.pushToken(s),t.gullet.pushToken(o),{type:"internal",mode:t.mode}}});const Jt=function(e,t,r){const n=N(se.math[e]&&se.math[e].replace||e,t,r);if(!n)throw new Error("Unsupported symbol "+e+" and font size "+t+".");return n},Qt=function(e,t,r,n){const o=r.havingBaseStyle(t),s=Pe.makeSpan(n.concat(o.sizingClasses(r)),[e],r),i=o.sizeMultiplier/r.sizeMultiplier;return s.height*=i,s.depth*=i,s.maxFontSize=o.sizeMultiplier,s},er=function(e,t,r){const n=t.havingBaseStyle(r),o=(1-t.sizeMultiplier/n.sizeMultiplier)*t.fontMetrics().axisHeight;e.classes.push("delimcenter"),e.style.top=F(o),e.height-=o,e.depth+=o},tr=function(e,t,r,n,o,s){const i=function(e,t,r,n){return Pe.makeSymbol(e,"Size"+t+"-Regular",r,n)}(e,t,o,n),a=Qt(Pe.makeSpan(["delimsizing","size"+t],[i],n),w.TEXT,n,s);return r&&er(a,n,w.TEXT),a},rr=function(e,t,r){let n;n="Size1-Regular"===t?"delim-size1":"delim-size4";return{type:"elem",elem:Pe.makeSpan(["delimsizinginner",n],[Pe.makeSpan([],[Pe.makeSymbol(e,t,r)])])}},nr=function(e,t,r){const n=T["Size4-Regular"][e.charCodeAt(0)]?T["Size4-Regular"][e.charCodeAt(0)][4]:T["Size1-Regular"][e.charCodeAt(0)][4],o=new Q("inner",function(e,t){switch(e){case"\u239c":return"M291 0 H417 V"+t+" H291z M291 0 H417 V"+t+" H291z";case"\u2223":return"M145 0 H188 V"+t+" H145z M145 0 H188 V"+t+" H145z";case"\u2225":return"M145 0 H188 V"+t+" H145z M145 0 H188 V"+t+" H145zM367 0 H410 V"+t+" H367z M367 0 H410 V"+t+" H367z";case"\u239f":return"M457 0 H583 V"+t+" H457z M457 0 H583 V"+t+" H457z";case"\u23a2":return"M319 0 H403 V"+t+" H319z M319 0 H403 V"+t+" H319z";case"\u23a5":return"M263 0 H347 V"+t+" H263z M263 0 H347 V"+t+" H263z";case"\u23aa":return"M384 0 H504 V"+t+" H384z M384 0 H504 V"+t+" H384z";case"\u23d0":return"M312 0 H355 V"+t+" H312z M312 0 H355 V"+t+" H312z";case"\u2016":return"M257 0 H300 V"+t+" H257z M257 0 H300 V"+t+" H257zM478 0 H521 V"+t+" H478z M478 0 H521 V"+t+" H478z";default:return""}}(e,Math.round(1e3*t))),s=new J([o],{width:F(n),height:F(t),style:"width:"+F(n),viewBox:"0 0 "+1e3*n+" "+Math.round(1e3*t),preserveAspectRatio:"xMinYMin"}),i=Pe.makeSvgSpan([],[s],r);return i.height=t,i.style.height=F(t),i.style.width=F(n),{type:"elem",elem:i}},or={type:"kern",size:-.008},sr=["|","\\lvert","\\rvert","\\vert"],ir=["\\|","\\lVert","\\rVert","\\Vert"],ar=function(e,t,r,n,o,s){let i,a,h,c,m="",p=0;i=h=c=e,a=null;let u="Size1-Regular";"\\uparrow"===e?h=c="\u23d0":"\\Uparrow"===e?h=c="\u2016":"\\downarrow"===e?i=h="\u23d0":"\\Downarrow"===e?i=h="\u2016":"\\updownarrow"===e?(i="\\uparrow",h="\u23d0",c="\\downarrow"):"\\Updownarrow"===e?(i="\\Uparrow",h="\u2016",c="\\Downarrow"):l.contains(sr,e)?(h="\u2223",m="vert",p=333):l.contains(ir,e)?(h="\u2225",m="doublevert",p=556):"["===e||"\\lbrack"===e?(i="\u23a1",h="\u23a2",c="\u23a3",u="Size4-Regular",m="lbrack",p=667):"]"===e||"\\rbrack"===e?(i="\u23a4",h="\u23a5",c="\u23a6",u="Size4-Regular",m="rbrack",p=667):"\\lfloor"===e||"\u230a"===e?(h=i="\u23a2",c="\u23a3",u="Size4-Regular",m="lfloor",p=667):"\\lceil"===e||"\u2308"===e?(i="\u23a1",h=c="\u23a2",u="Size4-Regular",m="lceil",p=667):"\\rfloor"===e||"\u230b"===e?(h=i="\u23a5",c="\u23a6",u="Size4-Regular",m="rfloor",p=667):"\\rceil"===e||"\u2309"===e?(i="\u23a4",h=c="\u23a5",u="Size4-Regular",m="rceil",p=667):"("===e||"\\lparen"===e?(i="\u239b",h="\u239c",c="\u239d",u="Size4-Regular",m="lparen",p=875):")"===e||"\\rparen"===e?(i="\u239e",h="\u239f",c="\u23a0",u="Size4-Regular",m="rparen",p=875):"\\{"===e||"\\lbrace"===e?(i="\u23a7",a="\u23a8",c="\u23a9",h="\u23aa",u="Size4-Regular"):"\\}"===e||"\\rbrace"===e?(i="\u23ab",a="\u23ac",c="\u23ad",h="\u23aa",u="Size4-Regular"):"\\lgroup"===e||"\u27ee"===e?(i="\u23a7",c="\u23a9",h="\u23aa",u="Size4-Regular"):"\\rgroup"===e||"\u27ef"===e?(i="\u23ab",c="\u23ad",h="\u23aa",u="Size4-Regular"):"\\lmoustache"===e||"\u23b0"===e?(i="\u23a7",c="\u23ad",h="\u23aa",u="Size4-Regular"):"\\rmoustache"!==e&&"\u23b1"!==e||(i="\u23ab",c="\u23a9",h="\u23aa",u="Size4-Regular");const d=Jt(i,u,o),g=d.height+d.depth,f=Jt(h,u,o),b=f.height+f.depth,y=Jt(c,u,o),x=y.height+y.depth;let v=0,k=1;if(null!==a){const e=Jt(a,u,o);v=e.height+e.depth,k=2}const S=g+x+v,M=S+Math.max(0,Math.ceil((t-S)/(k*b)))*k*b;let z=n.fontMetrics().axisHeight;r&&(z*=n.sizeMultiplier);const A=M/2-z,T=[];if(m.length>0){const e=M-g-x,t=Math.round(1e3*M),r=function(e,t){switch(e){case"lbrack":return"M403 1759 V84 H666 V0 H319 V1759 v"+t+" v1759 h347 v-84\nH403z M403 1759 V0 H319 V1759 v"+t+" v1759 h84z";case"rbrack":return"M347 1759 V0 H0 V84 H263 V1759 v"+t+" v1759 H0 v84 H347z\nM347 1759 V0 H263 V1759 v"+t+" v1759 h84z";case"vert":return"M145 15 v585 v"+t+" v585 c2.667,10,9.667,15,21,15\nc10,0,16.667,-5,20,-15 v-585 v"+-t+" v-585 c-2.667,-10,-9.667,-15,-21,-15\nc-10,0,-16.667,5,-20,15z M188 15 H145 v585 v"+t+" v585 h43z";case"doublevert":return"M145 15 v585 v"+t+" v585 c2.667,10,9.667,15,21,15\nc10,0,16.667,-5,20,-15 v-585 v"+-t+" v-585 c-2.667,-10,-9.667,-15,-21,-15\nc-10,0,-16.667,5,-20,15z M188 15 H145 v585 v"+t+" v585 h43z\nM367 15 v585 v"+t+" v585 c2.667,10,9.667,15,21,15\nc10,0,16.667,-5,20,-15 v-585 v"+-t+" v-585 c-2.667,-10,-9.667,-15,-21,-15\nc-10,0,-16.667,5,-20,15z M410 15 H367 v585 v"+t+" v585 h43z";case"lfloor":return"M319 602 V0 H403 V602 v"+t+" v1715 h263 v84 H319z\nMM319 602 V0 H403 V602 v"+t+" v1715 H319z";case"rfloor":return"M319 602 V0 H403 V602 v"+t+" v1799 H0 v-84 H319z\nMM319 602 V0 H403 V602 v"+t+" v1715 H319z";case"lceil":return"M403 1759 V84 H666 V0 H319 V1759 v"+t+" v602 h84z\nM403 1759 V0 H319 V1759 v"+t+" v602 h84z";case"rceil":return"M347 1759 V0 H0 V84 H263 V1759 v"+t+" v602 h84z\nM347 1759 V0 h-84 V1759 v"+t+" v602 h84z";case"lparen":return"M863,9c0,-2,-2,-5,-6,-9c0,0,-17,0,-17,0c-12.7,0,-19.3,0.3,-20,1\nc-5.3,5.3,-10.3,11,-15,17c-242.7,294.7,-395.3,682,-458,1162c-21.3,163.3,-33.3,349,\n-36,557 l0,"+(t+84)+"c0.2,6,0,26,0,60c2,159.3,10,310.7,24,454c53.3,528,210,\n949.7,470,1265c4.7,6,9.7,11.7,15,17c0.7,0.7,7,1,19,1c0,0,18,0,18,0c4,-4,6,-7,6,-9\nc0,-2.7,-3.3,-8.7,-10,-18c-135.3,-192.7,-235.5,-414.3,-300.5,-665c-65,-250.7,-102.5,\n-544.7,-112.5,-882c-2,-104,-3,-167,-3,-189\nl0,-"+(t+92)+"c0,-162.7,5.7,-314,17,-454c20.7,-272,63.7,-513,129,-723c65.3,\n-210,155.3,-396.3,270,-559c6.7,-9.3,10,-15.3,10,-18z";case"rparen":return"M76,0c-16.7,0,-25,3,-25,9c0,2,2,6.3,6,13c21.3,28.7,42.3,60.3,\n63,95c96.7,156.7,172.8,332.5,228.5,527.5c55.7,195,92.8,416.5,111.5,664.5\nc11.3,139.3,17,290.7,17,454c0,28,1.7,43,3.3,45l0,"+(t+9)+"\nc-3,4,-3.3,16.7,-3.3,38c0,162,-5.7,313.7,-17,455c-18.7,248,-55.8,469.3,-111.5,664\nc-55.7,194.7,-131.8,370.3,-228.5,527c-20.7,34.7,-41.7,66.3,-63,95c-2,3.3,-4,7,-6,11\nc0,7.3,5.7,11,17,11c0,0,11,0,11,0c9.3,0,14.3,-0.3,15,-1c5.3,-5.3,10.3,-11,15,-17\nc242.7,-294.7,395.3,-681.7,458,-1161c21.3,-164.7,33.3,-350.7,36,-558\nl0,-"+(t+144)+"c-2,-159.3,-10,-310.7,-24,-454c-53.3,-528,-210,-949.7,\n-470,-1265c-4.7,-6,-9.7,-11.7,-15,-17c-0.7,-0.7,-6.7,-1,-18,-1z";default:throw new Error("Unknown stretchy delimiter.")}}(m,Math.round(1e3*e)),o=new Q(m,r),s=(p/1e3).toFixed(3)+"em",i=(t/1e3).toFixed(3)+"em",a=new J([o],{width:s,height:i,viewBox:"0 0 "+p+" "+t}),l=Pe.makeSvgSpan([],[a],n);l.height=t/1e3,l.style.width=s,l.style.height=i,T.push({type:"elem",elem:l})}else{if(T.push(rr(c,u,o)),T.push(or),null===a){const e=M-g-x+.016;T.push(nr(h,e,n))}else{const e=(M-g-x-v)/2+.016;T.push(nr(h,e,n)),T.push(or),T.push(rr(a,u,o)),T.push(or),T.push(nr(h,e,n))}T.push(or),T.push(rr(i,u,o))}const B=n.havingBaseStyle(w.TEXT),C=Pe.makeVList({positionType:"bottom",positionData:A,children:T},B);return Qt(Pe.makeSpan(["delimsizing","mult"],[C],B),w.TEXT,n,s)},lr=.08,hr=function(e,t,r,n,o){const s=function(e,t,r){t*=1e3;let n="";switch(e){case"sqrtMain":n=function(e,t){return"M95,"+(622+e+t)+"\nc-2.7,0,-7.17,-2.7,-13.5,-8c-5.8,-5.3,-9.5,-10,-9.5,-14\nc0,-2,0.3,-3.3,1,-4c1.3,-2.7,23.83,-20.7,67.5,-54\nc44.2,-33.3,65.8,-50.3,66.5,-51c1.3,-1.3,3,-2,5,-2c4.7,0,8.7,3.3,12,10\ns173,378,173,378c0.7,0,35.3,-71,104,-213c68.7,-142,137.5,-285,206.5,-429\nc69,-144,104.5,-217.7,106.5,-221\nl"+e/2.075+" -"+e+"\nc5.3,-9.3,12,-14,20,-14\nH400000v"+(40+e)+"H845.2724\ns-225.272,467,-225.272,467s-235,486,-235,486c-2.7,4.7,-9,7,-19,7\nc-6,0,-10,-1,-12,-3s-194,-422,-194,-422s-65,47,-65,47z\nM"+(834+e)+" "+t+"h400000v"+(40+e)+"h-400000z"}(t,M);break;case"sqrtSize1":n=function(e,t){return"M263,"+(601+e+t)+"c0.7,0,18,39.7,52,119\nc34,79.3,68.167,158.7,102.5,238c34.3,79.3,51.8,119.3,52.5,120\nc340,-704.7,510.7,-1060.3,512,-1067\nl"+e/2.084+" -"+e+"\nc4.7,-7.3,11,-11,19,-11\nH40000v"+(40+e)+"H1012.3\ns-271.3,567,-271.3,567c-38.7,80.7,-84,175,-136,283c-52,108,-89.167,185.3,-111.5,232\nc-22.3,46.7,-33.8,70.3,-34.5,71c-4.7,4.7,-12.3,7,-23,7s-12,-1,-12,-1\ns-109,-253,-109,-253c-72.7,-168,-109.3,-252,-110,-252c-10.7,8,-22,16.7,-34,26\nc-22,17.3,-33.3,26,-34,26s-26,-26,-26,-26s76,-59,76,-59s76,-60,76,-60z\nM"+(1001+e)+" "+t+"h400000v"+(40+e)+"h-400000z"}(t,M);break;case"sqrtSize2":n=function(e,t){return"M983 "+(10+e+t)+"\nl"+e/3.13+" -"+e+"\nc4,-6.7,10,-10,18,-10 H400000v"+(40+e)+"\nH1013.1s-83.4,268,-264.1,840c-180.7,572,-277,876.3,-289,913c-4.7,4.7,-12.7,7,-24,7\ns-12,0,-12,0c-1.3,-3.3,-3.7,-11.7,-7,-25c-35.3,-125.3,-106.7,-373.3,-214,-744\nc-10,12,-21,25,-33,39s-32,39,-32,39c-6,-5.3,-15,-14,-27,-26s25,-30,25,-30\nc26.7,-32.7,52,-63,76,-91s52,-60,52,-60s208,722,208,722\nc56,-175.3,126.3,-397.3,211,-666c84.7,-268.7,153.8,-488.2,207.5,-658.5\nc53.7,-170.3,84.5,-266.8,92.5,-289.5z\nM"+(1001+e)+" "+t+"h400000v"+(40+e)+"h-400000z"}(t,M);break;case"sqrtSize3":n=function(e,t){return"M424,"+(2398+e+t)+"\nc-1.3,-0.7,-38.5,-172,-111.5,-514c-73,-342,-109.8,-513.3,-110.5,-514\nc0,-2,-10.7,14.3,-32,49c-4.7,7.3,-9.8,15.7,-15.5,25c-5.7,9.3,-9.8,16,-12.5,20\ns-5,7,-5,7c-4,-3.3,-8.3,-7.7,-13,-13s-13,-13,-13,-13s76,-122,76,-122s77,-121,77,-121\ns209,968,209,968c0,-2,84.7,-361.7,254,-1079c169.3,-717.3,254.7,-1077.7,256,-1081\nl"+e/4.223+" -"+e+"c4,-6.7,10,-10,18,-10 H400000\nv"+(40+e)+"H1014.6\ns-87.3,378.7,-272.6,1166c-185.3,787.3,-279.3,1182.3,-282,1185\nc-2,6,-10,9,-24,9\nc-8,0,-12,-0.7,-12,-2z M"+(1001+e)+" "+t+"\nh400000v"+(40+e)+"h-400000z"}(t,M);break;case"sqrtSize4":n=function(e,t){return"M473,"+(2713+e+t)+"\nc339.3,-1799.3,509.3,-2700,510,-2702 l"+e/5.298+" -"+e+"\nc3.3,-7.3,9.3,-11,18,-11 H400000v"+(40+e)+"H1017.7\ns-90.5,478,-276.2,1466c-185.7,988,-279.5,1483,-281.5,1485c-2,6,-10,9,-24,9\nc-8,0,-12,-0.7,-12,-2c0,-1.3,-5.3,-32,-16,-92c-50.7,-293.3,-119.7,-693.3,-207,-1200\nc0,-1.3,-5.3,8.7,-16,30c-10.7,21.3,-21.3,42.7,-32,64s-16,33,-16,33s-26,-26,-26,-26\ns76,-153,76,-153s77,-151,77,-151c0.7,0.7,35.7,202,105,604c67.3,400.7,102,602.7,104,\n606zM"+(1001+e)+" "+t+"h400000v"+(40+e)+"H1017.7z"}(t,M);break;case"sqrtTall":n=function(e,t,r){return"M702 "+(e+t)+"H400000"+(40+e)+"\nH742v"+(r-54-t-e)+"l-4 4-4 4c-.667.7 -2 1.5-4 2.5s-4.167 1.833-6.5 2.5-5.5 1-9.5 1\nh-12l-28-84c-16.667-52-96.667 -294.333-240-727l-212 -643 -85 170\nc-4-3.333-8.333-7.667-13 -13l-13-13l77-155 77-156c66 199.333 139 419.667\n219 661 l218 661zM702 "+t+"H400000v"+(40+e)+"H742z"}(t,M,r)}return n}(e,n,r),i=new Q(e,s),a=new J([i],{width:"400em",height:F(t),viewBox:"0 0 400000 "+r,preserveAspectRatio:"xMinYMin slice"});return Pe.makeSvgSpan(["hide-tail"],[a],o)},cr=["(","\\lparen",")","\\rparen","[","\\lbrack","]","\\rbrack","\\{","\\lbrace","\\}","\\rbrace","\\lfloor","\\rfloor","\u230a","\u230b","\\lceil","\\rceil","\u2308","\u2309","\\surd"],mr=["\\uparrow","\\downarrow","\\updownarrow","\\Uparrow","\\Downarrow","\\Updownarrow","|","\\|","\\vert","\\Vert","\\lvert","\\rvert","\\lVert","\\rVert","\\lgroup","\\rgroup","\u27ee","\u27ef","\\lmoustache","\\rmoustache","\u23b0","\u23b1"],pr=["<",">","\\langle","\\rangle","/","\\backslash","\\lt","\\gt"],ur=[0,1.2,1.8,2.4,3],dr=[{type:"small",style:w.SCRIPTSCRIPT},{type:"small",style:w.SCRIPT},{type:"small",style:w.TEXT},{type:"large",size:1},{type:"large",size:2},{type:"large",size:3},{type:"large",size:4}],gr=[{type:"small",style:w.SCRIPTSCRIPT},{type:"small",style:w.SCRIPT},{type:"small",style:w.TEXT},{type:"stack"}],fr=[{type:"small",style:w.SCRIPTSCRIPT},{type:"small",style:w.SCRIPT},{type:"small",style:w.TEXT},{type:"large",size:1},{type:"large",size:2},{type:"large",size:3},{type:"large",size:4},{type:"stack"}],br=function(e){if("small"===e.type)return"Main-Regular";if("large"===e.type)return"Size"+e.size+"-Regular";if("stack"===e.type)return"Size4-Regular";throw new Error("Add support for delim type '"+e.type+"' here.")},yr=function(e,t,r,n){for(let o=Math.min(2,3-n.style.size);ot)return r[o]}return r[r.length-1]},xr=function(e,t,r,n,o,s){let i;"<"===e||"\\lt"===e||"\u27e8"===e?e="\\langle":">"!==e&&"\\gt"!==e&&"\u27e9"!==e||(e="\\rangle"),i=l.contains(pr,e)?dr:l.contains(cr,e)?fr:gr;const a=yr(e,t,i,n);return"small"===a.type?function(e,t,r,n,o,s){const i=Pe.makeSymbol(e,"Main-Regular",o,n),a=Qt(i,t,n,s);return r&&er(a,n,t),a}(e,a.style,r,n,o,s):"large"===a.type?tr(e,a.size,r,n,o,s):ar(e,t,r,n,o,s)};var wr={sqrtImage:function(e,t){const r=t.havingBaseSizing(),n=yr("\\surd",e*r.sizeMultiplier,fr,r);let o=r.sizeMultiplier;const s=Math.max(0,t.minRuleThickness-t.fontMetrics().sqrtRuleThickness);let i,a,l=0,h=0,c=0;return"small"===n.type?(c=1e3+1e3*s+80,e<1?o=1:e<1.4&&(o=.7),l=(1+s+lr)/o,h=(1+s)/o,i=hr("sqrtMain",l,c,s,t),i.style.minWidth="0.853em",a=.833/o):"large"===n.type?(c=1080*ur[n.size],h=(ur[n.size]+s)/o,l=(ur[n.size]+s+lr)/o,i=hr("sqrtSize"+n.size,l,c,s,t),i.style.minWidth="1.02em",a=1/o):(l=e+s+lr,h=e+s,c=Math.floor(1e3*e+s)+80,i=hr("sqrtTall",l,c,s,t),i.style.minWidth="0.742em",a=1.056),i.height=h,i.style.height=F(l),{span:i,advanceWidth:a,ruleWidth:(t.fontMetrics().sqrtRuleThickness+s)*o}},sizedDelim:function(e,t,r,o,s){if("<"===e||"\\lt"===e||"\u27e8"===e?e="\\langle":">"!==e&&"\\gt"!==e&&"\u27e9"!==e||(e="\\rangle"),l.contains(cr,e)||l.contains(pr,e))return tr(e,t,!1,r,o,s);if(l.contains(mr,e))return ar(e,ur[t],!1,r,o,s);throw new n("Illegal delimiter: '"+e+"'")},sizeToMaxHeight:ur,customSizedDelim:xr,leftRightDelim:function(e,t,r,n,o,s){const i=n.fontMetrics().axisHeight*n.sizeMultiplier,a=5/n.fontMetrics().ptPerEm,l=Math.max(t-i,r+i),h=Math.max(l/500*901,2*l-a);return xr(e,h,!0,n,o,s)}};const vr={"\\bigl":{mclass:"mopen",size:1},"\\Bigl":{mclass:"mopen",size:2},"\\biggl":{mclass:"mopen",size:3},"\\Biggl":{mclass:"mopen",size:4},"\\bigr":{mclass:"mclose",size:1},"\\Bigr":{mclass:"mclose",size:2},"\\biggr":{mclass:"mclose",size:3},"\\Biggr":{mclass:"mclose",size:4},"\\bigm":{mclass:"mrel",size:1},"\\Bigm":{mclass:"mrel",size:2},"\\biggm":{mclass:"mrel",size:3},"\\Biggm":{mclass:"mrel",size:4},"\\big":{mclass:"mord",size:1},"\\Big":{mclass:"mord",size:2},"\\bigg":{mclass:"mord",size:3},"\\Bigg":{mclass:"mord",size:4}},kr=["(","\\lparen",")","\\rparen","[","\\lbrack","]","\\rbrack","\\{","\\lbrace","\\}","\\rbrace","\\lfloor","\\rfloor","\u230a","\u230b","\\lceil","\\rceil","\u2308","\u2309","<",">","\\langle","\u27e8","\\rangle","\u27e9","\\lt","\\gt","\\lvert","\\rvert","\\lVert","\\rVert","\\lgroup","\\rgroup","\u27ee","\u27ef","\\lmoustache","\\rmoustache","\u23b0","\u23b1","/","\\backslash","|","\\vert","\\|","\\Vert","\\uparrow","\\Uparrow","\\downarrow","\\Downarrow","\\updownarrow","\\Updownarrow","."];function Sr(e,t){const r=Ot(e);if(r&&l.contains(kr,r.text))return r;throw new n(r?"Invalid delimiter '"+r.text+"' after '"+t.funcName+"'":"Invalid delimiter type '"+e.type+"'",e)}function Mr(e){if(!e.body)throw new Error("Bug: The leftright ParseNode wasn't fully parsed.")}$e({type:"delimsizing",names:["\\bigl","\\Bigl","\\biggl","\\Biggl","\\bigr","\\Bigr","\\biggr","\\Biggr","\\bigm","\\Bigm","\\biggm","\\Biggm","\\big","\\Big","\\bigg","\\Bigg"],props:{numArgs:1,argTypes:["primitive"]},handler:(e,t)=>{const r=Sr(t[0],e);return{type:"delimsizing",mode:e.parser.mode,size:vr[e.funcName].size,mclass:vr[e.funcName].mclass,delim:r.text}},htmlBuilder:(e,t)=>"."===e.delim?Pe.makeSpan([e.mclass]):wr.sizedDelim(e.delim,e.size,t,e.mode,[e.mclass]),mathmlBuilder:e=>{const t=[];"."!==e.delim&&t.push(bt(e.delim,e.mode));const r=new ft.MathNode("mo",t);"mopen"===e.mclass||"mclose"===e.mclass?r.setAttribute("fence","true"):r.setAttribute("fence","false"),r.setAttribute("stretchy","true");const n=F(wr.sizeToMaxHeight[e.size]);return r.setAttribute("minsize",n),r.setAttribute("maxsize",n),r}}),$e({type:"leftright-right",names:["\\right"],props:{numArgs:1,primitive:!0},handler:(e,t)=>{const r=e.parser.gullet.macros.get("\\current@color");if(r&&"string"!=typeof r)throw new n("\\current@color set to non-string in \\right");return{type:"leftright-right",mode:e.parser.mode,delim:Sr(t[0],e).text,color:r}}}),$e({type:"leftright",names:["\\left"],props:{numArgs:1,primitive:!0},handler:(e,t)=>{const r=Sr(t[0],e),n=e.parser;++n.leftrightDepth;const o=n.parseExpression(!1);--n.leftrightDepth,n.expect("\\right",!1);const s=Rt(n.parseFunction(),"leftright-right");return{type:"leftright",mode:n.mode,body:o,left:r.text,right:s.delim,rightColor:s.color}},htmlBuilder:(e,t)=>{Mr(e);const r=ot(e.body,t,!0,["mopen","mclose"]);let n,o,s=0,i=0,a=!1;for(let e=0;e{Mr(e);const r=vt(e.body,t);if("."!==e.left){const t=new ft.MathNode("mo",[bt(e.left,e.mode)]);t.setAttribute("fence","true"),r.unshift(t)}if("."!==e.right){const t=new ft.MathNode("mo",[bt(e.right,e.mode)]);t.setAttribute("fence","true"),e.rightColor&&t.setAttribute("mathcolor",e.rightColor),r.push(t)}return yt(r)}}),$e({type:"middle",names:["\\middle"],props:{numArgs:1,primitive:!0},handler:(e,t)=>{const r=Sr(t[0],e);if(!e.parser.leftrightDepth)throw new n("\\middle without preceding \\left",r);return{type:"middle",mode:e.parser.mode,delim:r.text}},htmlBuilder:(e,t)=>{let r;if("."===e.delim)r=ht(t,[]);else{r=wr.sizedDelim(e.delim,1,t,e.mode,[]);const n={delim:e.delim,options:t};r.isMiddle=n}return r},mathmlBuilder:(e,t)=>{const r="\\vert"===e.delim||"|"===e.delim?bt("|","text"):bt(e.delim,e.mode),n=new ft.MathNode("mo",[r]);return n.setAttribute("fence","true"),n.setAttribute("lspace","0.05em"),n.setAttribute("rspace","0.05em"),n}});const zr=(e,t)=>{const r=Pe.wrapFragment(ct(e.body,t),t),n=e.label.slice(1);let o,s=t.sizeMultiplier,i=0;const a=l.isCharacterBox(e.body);if("sout"===n)o=Pe.makeSpan(["stretchy","sout"]),o.height=t.fontMetrics().defaultRuleThickness/s,i=-.5*t.fontMetrics().xHeight;else if("phase"===n){const e=P({number:.6,unit:"pt"},t),n=P({number:.35,unit:"ex"},t);s/=t.havingBaseSizing().sizeMultiplier;const a=r.height+r.depth+e+n;r.style.paddingLeft=F(a/2+e);const l=Math.floor(1e3*a*s),c="M400000 "+(h=l)+" H0 L"+h/2+" 0 l65 45 L145 "+(h-80)+" H400000z",m=new J([new Q("phase",c)],{width:"400em",height:F(l/1e3),viewBox:"0 0 400000 "+l,preserveAspectRatio:"xMinYMin slice"});o=Pe.makeSvgSpan(["hide-tail"],[m],t),o.style.height=F(a),i=r.depth+e+n}else{/cancel/.test(n)?a||r.classes.push("cancel-pad"):"angl"===n?r.classes.push("anglpad"):r.classes.push("boxpad");let s=0,l=0,h=0;/box/.test(n)?(h=Math.max(t.fontMetrics().fboxrule,t.minRuleThickness),s=t.fontMetrics().fboxsep+("colorbox"===n?0:h),l=s):"angl"===n?(h=Math.max(t.fontMetrics().defaultRuleThickness,t.minRuleThickness),s=4*h,l=Math.max(0,.25-r.depth)):(s=a?.2:0,l=s),o=Nt(r,n,s,l,t),/fbox|boxed|fcolorbox/.test(n)?(o.style.borderStyle="solid",o.style.borderWidth=F(h)):"angl"===n&&.049!==h&&(o.style.borderTopWidth=F(h),o.style.borderRightWidth=F(h)),i=r.depth+l,e.backgroundColor&&(o.style.backgroundColor=e.backgroundColor,e.borderColor&&(o.style.borderColor=e.borderColor))}var h;let c;if(e.backgroundColor)c=Pe.makeVList({positionType:"individualShift",children:[{type:"elem",elem:o,shift:i},{type:"elem",elem:r,shift:0}]},t);else{const e=/cancel|phase/.test(n)?["svg-align"]:[];c=Pe.makeVList({positionType:"individualShift",children:[{type:"elem",elem:r,shift:0},{type:"elem",elem:o,shift:i,wrapperClasses:e}]},t)}return/cancel/.test(n)&&(c.height=r.height,c.depth=r.depth),/cancel/.test(n)&&!a?Pe.makeSpan(["mord","cancel-lap"],[c],t):Pe.makeSpan(["mord"],[c],t)},Ar=(e,t)=>{let r=0;const n=new ft.MathNode(e.label.indexOf("colorbox")>-1?"mpadded":"menclose",[St(e.body,t)]);switch(e.label){case"\\cancel":n.setAttribute("notation","updiagonalstrike");break;case"\\bcancel":n.setAttribute("notation","downdiagonalstrike");break;case"\\phase":n.setAttribute("notation","phasorangle");break;case"\\sout":n.setAttribute("notation","horizontalstrike");break;case"\\fbox":n.setAttribute("notation","box");break;case"\\angl":n.setAttribute("notation","actuarial");break;case"\\fcolorbox":case"\\colorbox":if(r=t.fontMetrics().fboxsep*t.fontMetrics().ptPerEm,n.setAttribute("width","+"+2*r+"pt"),n.setAttribute("height","+"+2*r+"pt"),n.setAttribute("lspace",r+"pt"),n.setAttribute("voffset",r+"pt"),"\\fcolorbox"===e.label){const r=Math.max(t.fontMetrics().fboxrule,t.minRuleThickness);n.setAttribute("style","border: "+r+"em solid "+String(e.borderColor))}break;case"\\xcancel":n.setAttribute("notation","updiagonalstrike downdiagonalstrike")}return e.backgroundColor&&n.setAttribute("mathbackground",e.backgroundColor),n};$e({type:"enclose",names:["\\colorbox"],props:{numArgs:2,allowedInText:!0,argTypes:["color","text"]},handler(e,t,r){let{parser:n,funcName:o}=e;const s=Rt(t[0],"color-token").color,i=t[1];return{type:"enclose",mode:n.mode,label:o,backgroundColor:s,body:i}},htmlBuilder:zr,mathmlBuilder:Ar}),$e({type:"enclose",names:["\\fcolorbox"],props:{numArgs:3,allowedInText:!0,argTypes:["color","color","text"]},handler(e,t,r){let{parser:n,funcName:o}=e;const s=Rt(t[0],"color-token").color,i=Rt(t[1],"color-token").color,a=t[2];return{type:"enclose",mode:n.mode,label:o,backgroundColor:i,borderColor:s,body:a}},htmlBuilder:zr,mathmlBuilder:Ar}),$e({type:"enclose",names:["\\fbox"],props:{numArgs:1,argTypes:["hbox"],allowedInText:!0},handler(e,t){let{parser:r}=e;return{type:"enclose",mode:r.mode,label:"\\fbox",body:t[0]}}}),$e({type:"enclose",names:["\\cancel","\\bcancel","\\xcancel","\\sout","\\phase"],props:{numArgs:1},handler(e,t){let{parser:r,funcName:n}=e;const o=t[0];return{type:"enclose",mode:r.mode,label:n,body:o}},htmlBuilder:zr,mathmlBuilder:Ar}),$e({type:"enclose",names:["\\angl"],props:{numArgs:1,argTypes:["hbox"],allowedInText:!1},handler(e,t){let{parser:r}=e;return{type:"enclose",mode:r.mode,label:"\\angl",body:t[0]}}});const Tr={};function Br(e){let{type:t,names:r,props:n,handler:o,htmlBuilder:s,mathmlBuilder:i}=e;const a={type:t,numArgs:n.numArgs||0,allowedInText:!1,numOptionalArgs:0,handler:o};for(let e=0;e{if(!e.parser.settings.displayMode)throw new n("{"+e.envName+"} can be used only in display mode.")};function Or(e){if(-1===e.indexOf("ed"))return-1===e.indexOf("*")}function Er(e,t,r){let{hskipBeforeAndAfter:o,addJot:s,cols:i,arraystretch:a,colSeparationType:l,autoTag:h,singleRow:c,emptySingleRow:m,maxNumCols:p,leqno:u}=t;if(e.gullet.beginGroup(),c||e.gullet.macros.set("\\cr","\\\\\\relax"),!a){const t=e.gullet.expandMacroAsText("\\arraystretch");if(null==t)a=1;else if(a=parseFloat(t),!a||a<0)throw new n("Invalid \\arraystretch: "+t)}e.gullet.beginGroup();let d=[];const g=[d],f=[],b=[],y=null!=h?[]:void 0;function x(){h&&e.gullet.macros.set("\\@eqnsw","1",!0)}function w(){y&&(e.gullet.macros.get("\\df@tag")?(y.push(e.subparse([new Ir("\\df@tag")])),e.gullet.macros.set("\\df@tag",void 0,!0)):y.push(Boolean(h)&&"1"===e.gullet.macros.get("\\@eqnsw")))}for(x(),b.push(Rr(e));;){let t=e.parseExpression(!1,c?"\\end":"\\\\");e.gullet.endGroup(),e.gullet.beginGroup(),t={type:"ordgroup",mode:e.mode,body:t},r&&(t={type:"styling",mode:e.mode,style:r,body:[t]}),d.push(t);const o=e.fetch().text;if("&"===o){if(p&&d.length===p){if(c||l)throw new n("Too many tab characters: &",e.nextToken);e.settings.reportNonstrict("textEnv","Too few columns specified in the {array} column argument.")}e.consume()}else{if("\\end"===o){w(),1===d.length&&"styling"===t.type&&0===t.body[0].body.length&&(g.length>1||!m)&&g.pop(),b.length0&&(x+=.25),c.push({pos:x,isDashed:e[t]})}for(v(i[0]),r=0;r0&&(p+=y,le)))for(r=0;r=a)continue;(o>0||e.hskipBeforeAndAfter)&&(i=l.deflt(c.pregap,u),0!==i&&(z=Pe.makeSpan(["arraycolsep"],[]),z.style.width=F(i),M.push(z)));let d=[];for(r=0;r0){const e=Pe.makeLineSpan("hline",t,m),r=Pe.makeLineSpan("hdashline",t,m),n=[{type:"elem",elem:h,shift:0}];for(;c.length>0;){const t=c.pop(),o=t.pos-k;t.isDashed?n.push({type:"elem",elem:r,shift:o}):n.push({type:"elem",elem:e,shift:o})}h=Pe.makeVList({positionType:"individualShift",children:n},t)}if(0===T.length)return Pe.makeSpan(["mord"],[h],t);{let e=Pe.makeVList({positionType:"individualShift",children:T},t);return e=Pe.makeSpan(["tag"],[e],t),Pe.makeFragment([h,e])}},Vr={c:"center ",l:"left ",r:"right "},Pr=function(e,t){const r=[],n=new ft.MathNode("mtd",[],["mtr-glue"]),o=new ft.MathNode("mtd",[],["mml-eqn-num"]);for(let s=0;s0){const t=e.cols;let r="",n=!1,o=0,i=t.length;"separator"===t[0].type&&(a+="top ",o=1),"separator"===t[t.length-1].type&&(a+="bottom ",i-=1);for(let e=o;e0?"left ":"",a+=c[c.length-1].length>0?"right ":"";for(let e=1;e-1?"alignat":"align",s="split"===e.envName,i=Er(e.parser,{cols:r,addJot:!0,autoTag:s?void 0:Or(e.envName),emptySingleRow:!0,colSeparationType:o,maxNumCols:s?2:void 0,leqno:e.parser.settings.leqno},"display");let a,l=0;const h={type:"ordgroup",mode:e.mode,body:[]};if(t[0]&&"ordgroup"===t[0].type){let e="";for(let r=0;r0&&c&&(n=1),r[e]={type:"align",align:t,pregap:n,postgap:0}}return i.colSeparationType=c?"align":"alignat",i};Br({type:"array",names:["array","darray"],props:{numArgs:1},handler(e,t){const r=(Ot(t[0])?[t[0]]:Rt(t[0],"ordgroup").body).map((function(e){const t=Ht(e).text;if(-1!=="lcr".indexOf(t))return{type:"align",align:t};if("|"===t)return{type:"separator",separator:"|"};if(":"===t)return{type:"separator",separator:":"};throw new n("Unknown column alignment: "+t,e)})),o={cols:r,hskipBeforeAndAfter:!0,maxNumCols:r.length};return Er(e.parser,o,Lr(e.envName))},htmlBuilder:Dr,mathmlBuilder:Pr}),Br({type:"array",names:["matrix","pmatrix","bmatrix","Bmatrix","vmatrix","Vmatrix","matrix*","pmatrix*","bmatrix*","Bmatrix*","vmatrix*","Vmatrix*"],props:{numArgs:0},handler(e){const t={matrix:null,pmatrix:["(",")"],bmatrix:["[","]"],Bmatrix:["\\{","\\}"],vmatrix:["|","|"],Vmatrix:["\\Vert","\\Vert"]}[e.envName.replace("*","")];let r="c";const o={hskipBeforeAndAfter:!1,cols:[{type:"align",align:r}]};if("*"===e.envName.charAt(e.envName.length-1)){const t=e.parser;if(t.consumeSpaces(),"["===t.fetch().text){if(t.consume(),t.consumeSpaces(),r=t.fetch().text,-1==="lcr".indexOf(r))throw new n("Expected l or c or r",t.nextToken);t.consume(),t.consumeSpaces(),t.expect("]"),t.consume(),o.cols=[{type:"align",align:r}]}}const s=Er(e.parser,o,Lr(e.envName)),i=Math.max(0,...s.body.map((e=>e.length)));return s.cols=new Array(i).fill({type:"align",align:r}),t?{type:"leftright",mode:e.mode,body:[s],left:t[0],right:t[1],rightColor:void 0}:s},htmlBuilder:Dr,mathmlBuilder:Pr}),Br({type:"array",names:["smallmatrix"],props:{numArgs:0},handler(e){const t=Er(e.parser,{arraystretch:.5},"script");return t.colSeparationType="small",t},htmlBuilder:Dr,mathmlBuilder:Pr}),Br({type:"array",names:["subarray"],props:{numArgs:1},handler(e,t){const r=(Ot(t[0])?[t[0]]:Rt(t[0],"ordgroup").body).map((function(e){const t=Ht(e).text;if(-1!=="lc".indexOf(t))return{type:"align",align:t};throw new n("Unknown column alignment: "+t,e)}));if(r.length>1)throw new n("{subarray} can contain only one column");let o={cols:r,hskipBeforeAndAfter:!1,arraystretch:.5};if(o=Er(e.parser,o,"script"),o.body.length>0&&o.body[0].length>1)throw new n("{subarray} can contain only one column");return o},htmlBuilder:Dr,mathmlBuilder:Pr}),Br({type:"array",names:["cases","dcases","rcases","drcases"],props:{numArgs:0},handler(e){const t=Er(e.parser,{arraystretch:1.2,cols:[{type:"align",align:"l",pregap:0,postgap:1},{type:"align",align:"l",pregap:0,postgap:0}]},Lr(e.envName));return{type:"leftright",mode:e.mode,body:[t],left:e.envName.indexOf("r")>-1?".":"\\{",right:e.envName.indexOf("r")>-1?"\\}":".",rightColor:void 0}},htmlBuilder:Dr,mathmlBuilder:Pr}),Br({type:"array",names:["align","align*","aligned","split"],props:{numArgs:0},handler:Fr,htmlBuilder:Dr,mathmlBuilder:Pr}),Br({type:"array",names:["gathered","gather","gather*"],props:{numArgs:0},handler(e){l.contains(["gather","gather*"],e.envName)&&Hr(e);const t={cols:[{type:"align",align:"c"}],addJot:!0,colSeparationType:"gather",autoTag:Or(e.envName),emptySingleRow:!0,leqno:e.parser.settings.leqno};return Er(e.parser,t,"display")},htmlBuilder:Dr,mathmlBuilder:Pr}),Br({type:"array",names:["alignat","alignat*","alignedat"],props:{numArgs:1},handler:Fr,htmlBuilder:Dr,mathmlBuilder:Pr}),Br({type:"array",names:["equation","equation*"],props:{numArgs:0},handler(e){Hr(e);const t={autoTag:Or(e.envName),emptySingleRow:!0,singleRow:!0,maxNumCols:1,leqno:e.parser.settings.leqno};return Er(e.parser,t,"display")},htmlBuilder:Dr,mathmlBuilder:Pr}),Br({type:"array",names:["CD"],props:{numArgs:0},handler(e){return Hr(e),function(e){const t=[];for(e.gullet.beginGroup(),e.gullet.macros.set("\\cr","\\\\\\relax"),e.gullet.beginGroup();;){t.push(e.parseExpression(!1,"\\\\")),e.gullet.endGroup(),e.gullet.beginGroup();const r=e.fetch().text;if("&"!==r&&"\\\\"!==r){if("\\end"===r){0===t[t.length-1].length&&t.pop();break}throw new n("Expected \\\\ or \\cr or \\end",e.nextToken)}e.consume()}let r=[];const o=[r];for(let a=0;a-1);else{if(!("<>AV".indexOf(o)>-1))throw new n('Expected one of "<>AV=|." after @',l[t]);for(let e=0;e<2;e++){let r=!0;for(let h=t+1;h{const r=e.font,n=t.withFont(r);return ct(e.body,n)},Yr=(e,t)=>{const r=e.font,n=t.withFont(r);return St(e.body,n)},Xr={"\\Bbb":"\\mathbb","\\bold":"\\mathbf","\\frak":"\\mathfrak","\\bm":"\\boldsymbol"};$e({type:"font",names:["\\mathrm","\\mathit","\\mathbf","\\mathnormal","\\mathsfit","\\mathbb","\\mathcal","\\mathfrak","\\mathscr","\\mathsf","\\mathtt","\\Bbb","\\bold","\\frak"],props:{numArgs:1,allowedInArgument:!0},handler:(e,t)=>{let{parser:r,funcName:n}=e;const o=Ke(t[0]);let s=n;return s in Xr&&(s=Xr[s]),{type:"font",mode:r.mode,font:s.slice(1),body:o}},htmlBuilder:Ur,mathmlBuilder:Yr}),$e({type:"mclass",names:["\\boldsymbol","\\bm"],props:{numArgs:1},handler:(e,t)=>{let{parser:r}=e;const n=t[0],o=l.isCharacterBox(n);return{type:"mclass",mode:r.mode,mclass:Ut(n),body:[{type:"font",mode:r.mode,font:"boldsymbol",body:n}],isCharacterBox:o}}}),$e({type:"font",names:["\\rm","\\sf","\\tt","\\bf","\\it","\\cal"],props:{numArgs:0,allowedInText:!0},handler:(e,t)=>{let{parser:r,funcName:n,breakOnTokenText:o}=e;const{mode:s}=r,i=r.parseExpression(!0,o);return{type:"font",mode:s,font:"math"+n.slice(1),body:{type:"ordgroup",mode:r.mode,body:i}}},htmlBuilder:Ur,mathmlBuilder:Yr});const Wr=(e,t)=>{let r=t;return"display"===e?r=r.id>=w.SCRIPT.id?r.text():w.DISPLAY:"text"===e&&r.size===w.DISPLAY.size?r=w.TEXT:"script"===e?r=w.SCRIPT:"scriptscript"===e&&(r=w.SCRIPTSCRIPT),r},_r=(e,t)=>{const r=Wr(e.size,t.style),n=r.fracNum(),o=r.fracDen();let s;s=t.havingStyle(n);const i=ct(e.numer,s,t);if(e.continued){const e=8.5/t.fontMetrics().ptPerEm,r=3.5/t.fontMetrics().ptPerEm;i.height=i.height0?3*c:7*c,u=t.fontMetrics().denom1):(h>0?(m=t.fontMetrics().num2,p=c):(m=t.fontMetrics().num3,p=3*c),u=t.fontMetrics().denom2),l){const e=t.fontMetrics().axisHeight;m-i.depth-(e+.5*h){let r=new ft.MathNode("mfrac",[St(e.numer,t),St(e.denom,t)]);if(e.hasBarLine){if(e.barSize){const n=P(e.barSize,t);r.setAttribute("linethickness",F(n))}}else r.setAttribute("linethickness","0px");const n=Wr(e.size,t.style);if(n.size!==t.style.size){r=new ft.MathNode("mstyle",[r]);const e=n.size===w.DISPLAY.size?"true":"false";r.setAttribute("displaystyle",e),r.setAttribute("scriptlevel","0")}if(null!=e.leftDelim||null!=e.rightDelim){const t=[];if(null!=e.leftDelim){const r=new ft.MathNode("mo",[new ft.TextNode(e.leftDelim.replace("\\",""))]);r.setAttribute("fence","true"),t.push(r)}if(t.push(r),null!=e.rightDelim){const r=new ft.MathNode("mo",[new ft.TextNode(e.rightDelim.replace("\\",""))]);r.setAttribute("fence","true"),t.push(r)}return yt(t)}return r};$e({type:"genfrac",names:["\\dfrac","\\frac","\\tfrac","\\dbinom","\\binom","\\tbinom","\\\\atopfrac","\\\\bracefrac","\\\\brackfrac"],props:{numArgs:2,allowedInArgument:!0},handler:(e,t)=>{let{parser:r,funcName:n}=e;const o=t[0],s=t[1];let i,a=null,l=null,h="auto";switch(n){case"\\dfrac":case"\\frac":case"\\tfrac":i=!0;break;case"\\\\atopfrac":i=!1;break;case"\\dbinom":case"\\binom":case"\\tbinom":i=!1,a="(",l=")";break;case"\\\\bracefrac":i=!1,a="\\{",l="\\}";break;case"\\\\brackfrac":i=!1,a="[",l="]";break;default:throw new Error("Unrecognized genfrac command")}switch(n){case"\\dfrac":case"\\dbinom":h="display";break;case"\\tfrac":case"\\tbinom":h="text"}return{type:"genfrac",mode:r.mode,continued:!1,numer:o,denom:s,hasBarLine:i,leftDelim:a,rightDelim:l,size:h,barSize:null}},htmlBuilder:_r,mathmlBuilder:jr}),$e({type:"genfrac",names:["\\cfrac"],props:{numArgs:2},handler:(e,t)=>{let{parser:r,funcName:n}=e;const o=t[0],s=t[1];return{type:"genfrac",mode:r.mode,continued:!0,numer:o,denom:s,hasBarLine:!0,leftDelim:null,rightDelim:null,size:"display",barSize:null}}}),$e({type:"infix",names:["\\over","\\choose","\\atop","\\brace","\\brack"],props:{numArgs:0,infix:!0},handler(e){let t,{parser:r,funcName:n,token:o}=e;switch(n){case"\\over":t="\\frac";break;case"\\choose":t="\\binom";break;case"\\atop":t="\\\\atopfrac";break;case"\\brace":t="\\\\bracefrac";break;case"\\brack":t="\\\\brackfrac";break;default:throw new Error("Unrecognized infix genfrac command")}return{type:"infix",mode:r.mode,replaceWith:t,token:o}}});const $r=["display","text","script","scriptscript"],Zr=function(e){let t=null;return e.length>0&&(t=e,t="."===t?null:t),t};$e({type:"genfrac",names:["\\genfrac"],props:{numArgs:6,allowedInArgument:!0,argTypes:["math","math","size","text","math","math"]},handler(e,t){let{parser:r}=e;const n=t[4],o=t[5],s=Ke(t[0]),i="atom"===s.type&&"open"===s.family?Zr(s.text):null,a=Ke(t[1]),l="atom"===a.type&&"close"===a.family?Zr(a.text):null,h=Rt(t[2],"size");let c,m=null;h.isBlank?c=!0:(m=h.value,c=m.number>0);let p="auto",u=t[3];if("ordgroup"===u.type){if(u.body.length>0){const e=Rt(u.body[0],"textord");p=$r[Number(e.text)]}}else u=Rt(u,"textord"),p=$r[Number(u.text)];return{type:"genfrac",mode:r.mode,numer:n,denom:o,continued:!1,hasBarLine:c,barSize:m,leftDelim:i,rightDelim:l,size:p}},htmlBuilder:_r,mathmlBuilder:jr}),$e({type:"infix",names:["\\above"],props:{numArgs:1,argTypes:["size"],infix:!0},handler(e,t){let{parser:r,funcName:n,token:o}=e;return{type:"infix",mode:r.mode,replaceWith:"\\\\abovefrac",size:Rt(t[0],"size").value,token:o}}}),$e({type:"genfrac",names:["\\\\abovefrac"],props:{numArgs:3,argTypes:["math","size","math"]},handler:(e,t)=>{let{parser:r,funcName:n}=e;const o=t[0],s=function(e){if(!e)throw new Error("Expected non-null, but got "+String(e));return e}(Rt(t[1],"infix").size),i=t[2],a=s.number>0;return{type:"genfrac",mode:r.mode,numer:o,denom:i,continued:!1,hasBarLine:a,barSize:s,leftDelim:null,rightDelim:null,size:"auto"}},htmlBuilder:_r,mathmlBuilder:jr});const Kr=(e,t)=>{const r=t.style;let n,o;"supsub"===e.type?(n=e.sup?ct(e.sup,t.havingStyle(r.sup()),t):ct(e.sub,t.havingStyle(r.sub()),t),o=Rt(e.base,"horizBrace")):o=Rt(e,"horizBrace");const s=ct(o.base,t.havingBaseStyle(w.DISPLAY)),i=It(o,t);let a;if(o.isOver?(a=Pe.makeVList({positionType:"firstBaseline",children:[{type:"elem",elem:s},{type:"kern",size:.1},{type:"elem",elem:i}]},t),a.children[0].children[0].children[1].classes.push("svg-align")):(a=Pe.makeVList({positionType:"bottom",positionData:s.depth+.1+i.height,children:[{type:"elem",elem:i},{type:"kern",size:.1},{type:"elem",elem:s}]},t),a.children[0].children[0].children[0].classes.push("svg-align")),n){const e=Pe.makeSpan(["mord",o.isOver?"mover":"munder"],[a],t);a=o.isOver?Pe.makeVList({positionType:"firstBaseline",children:[{type:"elem",elem:e},{type:"kern",size:.2},{type:"elem",elem:n}]},t):Pe.makeVList({positionType:"bottom",positionData:e.depth+.2+n.height+n.depth,children:[{type:"elem",elem:n},{type:"kern",size:.2},{type:"elem",elem:e}]},t)}return Pe.makeSpan(["mord",o.isOver?"mover":"munder"],[a],t)};$e({type:"horizBrace",names:["\\overbrace","\\underbrace"],props:{numArgs:1},handler(e,t){let{parser:r,funcName:n}=e;return{type:"horizBrace",mode:r.mode,label:n,isOver:/^\\over/.test(n),base:t[0]}},htmlBuilder:Kr,mathmlBuilder:(e,t)=>{const r=qt(e.label);return new ft.MathNode(e.isOver?"mover":"munder",[St(e.base,t),r])}}),$e({type:"href",names:["\\href"],props:{numArgs:2,argTypes:["url","original"],allowedInText:!0},handler:(e,t)=>{let{parser:r}=e;const n=t[1],o=Rt(t[0],"url").url;return r.settings.isTrusted({command:"\\href",url:o})?{type:"href",mode:r.mode,href:o,body:Je(n)}:r.formatUnsupportedCmd("\\href")},htmlBuilder:(e,t)=>{const r=ot(e.body,t,!1);return Pe.makeAnchor(e.href,[],r,t)},mathmlBuilder:(e,t)=>{let r=kt(e.body,t);return r instanceof dt||(r=new dt("mrow",[r])),r.setAttribute("href",e.href),r}}),$e({type:"href",names:["\\url"],props:{numArgs:1,argTypes:["url"],allowedInText:!0},handler:(e,t)=>{let{parser:r}=e;const n=Rt(t[0],"url").url;if(!r.settings.isTrusted({command:"\\url",url:n}))return r.formatUnsupportedCmd("\\url");const o=[];for(let e=0;e{let{parser:r,funcName:o,token:s}=e;const i=Rt(t[0],"raw").string,a=t[1];let l;r.settings.strict&&r.settings.reportNonstrict("htmlExtension","HTML extension is disabled on strict mode");const h={};switch(o){case"\\htmlClass":h.class=i,l={command:"\\htmlClass",class:i};break;case"\\htmlId":h.id=i,l={command:"\\htmlId",id:i};break;case"\\htmlStyle":h.style=i,l={command:"\\htmlStyle",style:i};break;case"\\htmlData":{const e=i.split(",");for(let t=0;t{const r=ot(e.body,t,!1),n=["enclosing"];e.attributes.class&&n.push(...e.attributes.class.trim().split(/\s+/));const o=Pe.makeSpan(n,r,t);for(const t in e.attributes)"class"!==t&&e.attributes.hasOwnProperty(t)&&o.setAttribute(t,e.attributes[t]);return o},mathmlBuilder:(e,t)=>kt(e.body,t)}),$e({type:"htmlmathml",names:["\\html@mathml"],props:{numArgs:2,allowedInText:!0},handler:(e,t)=>{let{parser:r}=e;return{type:"htmlmathml",mode:r.mode,html:Je(t[0]),mathml:Je(t[1])}},htmlBuilder:(e,t)=>{const r=ot(e.html,t,!1);return Pe.makeFragment(r)},mathmlBuilder:(e,t)=>kt(e.mathml,t)});const Jr=function(e){if(/^[-+]? *(\d+(\.\d*)?|\.\d+)$/.test(e))return{number:+e,unit:"bp"};{const t=/([-+]?) *(\d+(?:\.\d*)?|\.\d+) *([a-z]{2})/.exec(e);if(!t)throw new n("Invalid size: '"+e+"' in \\includegraphics");const r={number:+(t[1]+t[2]),unit:t[3]};if(!V(r))throw new n("Invalid unit: '"+r.unit+"' in \\includegraphics.");return r}};$e({type:"includegraphics",names:["\\includegraphics"],props:{numArgs:1,numOptionalArgs:1,argTypes:["raw","url"],allowedInText:!1},handler:(e,t,r)=>{let{parser:o}=e,s={number:0,unit:"em"},i={number:.9,unit:"em"},a={number:0,unit:"em"},l="";if(r[0]){const e=Rt(r[0],"raw").string.split(",");for(let t=0;t{const r=P(e.height,t);let n=0;e.totalheight.number>0&&(n=P(e.totalheight,t)-r);let o=0;e.width.number>0&&(o=P(e.width,t));const s={height:F(r+n)};o>0&&(s.width=F(o)),n>0&&(s.verticalAlign=F(-n));const i=new $(e.src,e.alt,s);return i.height=r,i.depth=n,i},mathmlBuilder:(e,t)=>{const r=new ft.MathNode("mglyph",[]);r.setAttribute("alt",e.alt);const n=P(e.height,t);let o=0;if(e.totalheight.number>0&&(o=P(e.totalheight,t)-n,r.setAttribute("valign",F(-o))),r.setAttribute("height",F(n+o)),e.width.number>0){const n=P(e.width,t);r.setAttribute("width",F(n))}return r.setAttribute("src",e.src),r}}),$e({type:"kern",names:["\\kern","\\mkern","\\hskip","\\mskip"],props:{numArgs:1,argTypes:["size"],primitive:!0,allowedInText:!0},handler(e,t){let{parser:r,funcName:n}=e;const o=Rt(t[0],"size");if(r.settings.strict){const e="m"===n[1],t="mu"===o.value.unit;e?(t||r.settings.reportNonstrict("mathVsTextUnits","LaTeX's "+n+" supports only mu units, not "+o.value.unit+" units"),"math"!==r.mode&&r.settings.reportNonstrict("mathVsTextUnits","LaTeX's "+n+" works only in math mode")):t&&r.settings.reportNonstrict("mathVsTextUnits","LaTeX's "+n+" doesn't support mu units")}return{type:"kern",mode:r.mode,dimension:o.value}},htmlBuilder(e,t){return Pe.makeGlue(e.dimension,t)},mathmlBuilder(e,t){const r=P(e.dimension,t);return new ft.SpaceNode(r)}}),$e({type:"lap",names:["\\mathllap","\\mathrlap","\\mathclap"],props:{numArgs:1,allowedInText:!0},handler:(e,t)=>{let{parser:r,funcName:n}=e;const o=t[0];return{type:"lap",mode:r.mode,alignment:n.slice(5),body:o}},htmlBuilder:(e,t)=>{let r;"clap"===e.alignment?(r=Pe.makeSpan([],[ct(e.body,t)]),r=Pe.makeSpan(["inner"],[r],t)):r=Pe.makeSpan(["inner"],[ct(e.body,t)]);const n=Pe.makeSpan(["fix"],[]);let o=Pe.makeSpan([e.alignment],[r,n],t);const s=Pe.makeSpan(["strut"]);return s.style.height=F(o.height+o.depth),o.depth&&(s.style.verticalAlign=F(-o.depth)),o.children.unshift(s),o=Pe.makeSpan(["thinbox"],[o],t),Pe.makeSpan(["mord","vbox"],[o],t)},mathmlBuilder:(e,t)=>{const r=new ft.MathNode("mpadded",[St(e.body,t)]);if("rlap"!==e.alignment){const t="llap"===e.alignment?"-1":"-0.5";r.setAttribute("lspace",t+"width")}return r.setAttribute("width","0px"),r}}),$e({type:"styling",names:["\\(","$"],props:{numArgs:0,allowedInText:!0,allowedInMath:!1},handler(e,t){let{funcName:r,parser:n}=e;const o=n.mode;n.switchMode("math");const s="\\("===r?"\\)":"$",i=n.parseExpression(!1,s);return n.expect(s),n.switchMode(o),{type:"styling",mode:n.mode,style:"text",body:i}}}),$e({type:"text",names:["\\)","\\]"],props:{numArgs:0,allowedInText:!0,allowedInMath:!1},handler(e,t){throw new n("Mismatched "+e.funcName)}});const Qr=(e,t)=>{switch(t.style.size){case w.DISPLAY.size:return e.display;case w.TEXT.size:return e.text;case w.SCRIPT.size:return e.script;case w.SCRIPTSCRIPT.size:return e.scriptscript;default:return e.text}};$e({type:"mathchoice",names:["\\mathchoice"],props:{numArgs:4,primitive:!0},handler:(e,t)=>{let{parser:r}=e;return{type:"mathchoice",mode:r.mode,display:Je(t[0]),text:Je(t[1]),script:Je(t[2]),scriptscript:Je(t[3])}},htmlBuilder:(e,t)=>{const r=Qr(e,t),n=ot(r,t,!1);return Pe.makeFragment(n)},mathmlBuilder:(e,t)=>{const r=Qr(e,t);return kt(r,t)}});const en=(e,t,r,n,o,s,i)=>{e=Pe.makeSpan([],[e]);const a=r&&l.isCharacterBox(r);let h,c,m;if(t){const e=ct(t,n.havingStyle(o.sup()),n);c={elem:e,kern:Math.max(n.fontMetrics().bigOpSpacing1,n.fontMetrics().bigOpSpacing3-e.depth)}}if(r){const e=ct(r,n.havingStyle(o.sub()),n);h={elem:e,kern:Math.max(n.fontMetrics().bigOpSpacing2,n.fontMetrics().bigOpSpacing4-e.height)}}if(c&&h){const t=n.fontMetrics().bigOpSpacing5+h.elem.height+h.elem.depth+h.kern+e.depth+i;m=Pe.makeVList({positionType:"bottom",positionData:t,children:[{type:"kern",size:n.fontMetrics().bigOpSpacing5},{type:"elem",elem:h.elem,marginLeft:F(-s)},{type:"kern",size:h.kern},{type:"elem",elem:e},{type:"kern",size:c.kern},{type:"elem",elem:c.elem,marginLeft:F(s)},{type:"kern",size:n.fontMetrics().bigOpSpacing5}]},n)}else if(h){const t=e.height-i;m=Pe.makeVList({positionType:"top",positionData:t,children:[{type:"kern",size:n.fontMetrics().bigOpSpacing5},{type:"elem",elem:h.elem,marginLeft:F(-s)},{type:"kern",size:h.kern},{type:"elem",elem:e}]},n)}else{if(!c)return e;{const t=e.depth+i;m=Pe.makeVList({positionType:"bottom",positionData:t,children:[{type:"elem",elem:e},{type:"kern",size:c.kern},{type:"elem",elem:c.elem,marginLeft:F(s)},{type:"kern",size:n.fontMetrics().bigOpSpacing5}]},n)}}const p=[m];if(h&&0!==s&&!a){const e=Pe.makeSpan(["mspace"],[],n);e.style.marginRight=F(s),p.unshift(e)}return Pe.makeSpan(["mop","op-limits"],p,n)},tn=["\\smallint"],rn=(e,t)=>{let r,n,o,s=!1;"supsub"===e.type?(r=e.sup,n=e.sub,o=Rt(e.base,"op"),s=!0):o=Rt(e,"op");const i=t.style;let a,h=!1;if(i.size===w.DISPLAY.size&&o.symbol&&!l.contains(tn,o.name)&&(h=!0),o.symbol){const e=h?"Size2-Regular":"Size1-Regular";let r="";if("\\oiint"!==o.name&&"\\oiiint"!==o.name||(r=o.name.slice(1),o.name="oiint"===r?"\\iint":"\\iiint"),a=Pe.makeSymbol(o.name,e,"math",t,["mop","op-symbol",h?"large-op":"small-op"]),r.length>0){const e=a.italic,n=Pe.staticSvg(r+"Size"+(h?"2":"1"),t);a=Pe.makeVList({positionType:"individualShift",children:[{type:"elem",elem:a,shift:0},{type:"elem",elem:n,shift:h?.08:0}]},t),o.name="\\"+r,a.classes.unshift("mop"),a.italic=e}}else if(o.body){const e=ot(o.body,t,!0);1===e.length&&e[0]instanceof K?(a=e[0],a.classes[0]="mop"):a=Pe.makeSpan(["mop"],e,t)}else{const e=[];for(let r=1;r{let r;if(e.symbol)r=new dt("mo",[bt(e.name,e.mode)]),l.contains(tn,e.name)&&r.setAttribute("largeop","false");else if(e.body)r=new dt("mo",vt(e.body,t));else{r=new dt("mi",[new gt(e.name.slice(1))]);const t=new dt("mo",[bt("\u2061","text")]);r=e.parentIsSupSub?new dt("mrow",[r,t]):ut([r,t])}return r},on={"\u220f":"\\prod","\u2210":"\\coprod","\u2211":"\\sum","\u22c0":"\\bigwedge","\u22c1":"\\bigvee","\u22c2":"\\bigcap","\u22c3":"\\bigcup","\u2a00":"\\bigodot","\u2a01":"\\bigoplus","\u2a02":"\\bigotimes","\u2a04":"\\biguplus","\u2a06":"\\bigsqcup"};$e({type:"op",names:["\\coprod","\\bigvee","\\bigwedge","\\biguplus","\\bigcap","\\bigcup","\\intop","\\prod","\\sum","\\bigotimes","\\bigoplus","\\bigodot","\\bigsqcup","\\smallint","\u220f","\u2210","\u2211","\u22c0","\u22c1","\u22c2","\u22c3","\u2a00","\u2a01","\u2a02","\u2a04","\u2a06"],props:{numArgs:0},handler:(e,t)=>{let{parser:r,funcName:n}=e,o=n;return 1===o.length&&(o=on[o]),{type:"op",mode:r.mode,limits:!0,parentIsSupSub:!1,symbol:!0,name:o}},htmlBuilder:rn,mathmlBuilder:nn}),$e({type:"op",names:["\\mathop"],props:{numArgs:1,primitive:!0},handler:(e,t)=>{let{parser:r}=e;const n=t[0];return{type:"op",mode:r.mode,limits:!1,parentIsSupSub:!1,symbol:!1,body:Je(n)}},htmlBuilder:rn,mathmlBuilder:nn});const sn={"\u222b":"\\int","\u222c":"\\iint","\u222d":"\\iiint","\u222e":"\\oint","\u222f":"\\oiint","\u2230":"\\oiiint"};$e({type:"op",names:["\\arcsin","\\arccos","\\arctan","\\arctg","\\arcctg","\\arg","\\ch","\\cos","\\cosec","\\cosh","\\cot","\\cotg","\\coth","\\csc","\\ctg","\\cth","\\deg","\\dim","\\exp","\\hom","\\ker","\\lg","\\ln","\\log","\\sec","\\sin","\\sinh","\\sh","\\tan","\\tanh","\\tg","\\th"],props:{numArgs:0},handler(e){let{parser:t,funcName:r}=e;return{type:"op",mode:t.mode,limits:!1,parentIsSupSub:!1,symbol:!1,name:r}},htmlBuilder:rn,mathmlBuilder:nn}),$e({type:"op",names:["\\det","\\gcd","\\inf","\\lim","\\max","\\min","\\Pr","\\sup"],props:{numArgs:0},handler(e){let{parser:t,funcName:r}=e;return{type:"op",mode:t.mode,limits:!0,parentIsSupSub:!1,symbol:!1,name:r}},htmlBuilder:rn,mathmlBuilder:nn}),$e({type:"op",names:["\\int","\\iint","\\iiint","\\oint","\\oiint","\\oiiint","\u222b","\u222c","\u222d","\u222e","\u222f","\u2230"],props:{numArgs:0},handler(e){let{parser:t,funcName:r}=e,n=r;return 1===n.length&&(n=sn[n]),{type:"op",mode:t.mode,limits:!1,parentIsSupSub:!1,symbol:!0,name:n}},htmlBuilder:rn,mathmlBuilder:nn});const an=(e,t)=>{let r,n,o,s,i=!1;if("supsub"===e.type?(r=e.sup,n=e.sub,o=Rt(e.base,"operatorname"),i=!0):o=Rt(e,"operatorname"),o.body.length>0){const e=o.body.map((e=>{const t=e.text;return"string"==typeof t?{type:"textord",mode:e.mode,text:t}:e})),r=ot(e,t.withFont("mathrm"),!0);for(let e=0;e{let{parser:r,funcName:n}=e;const o=t[0];return{type:"operatorname",mode:r.mode,body:Je(o),alwaysHandleSupSub:"\\operatornamewithlimits"===n,limits:!1,parentIsSupSub:!1}},htmlBuilder:an,mathmlBuilder:(e,t)=>{let r=vt(e.body,t.withFont("mathrm")),n=!0;for(let e=0;ee.toText())).join("");r=[new ft.TextNode(e)]}const o=new ft.MathNode("mi",r);o.setAttribute("mathvariant","normal");const s=new ft.MathNode("mo",[bt("\u2061","text")]);return e.parentIsSupSub?new ft.MathNode("mrow",[o,s]):ft.newDocumentFragment([o,s])}}),Nr("\\operatorname","\\@ifstar\\operatornamewithlimits\\operatorname@"),Ze({type:"ordgroup",htmlBuilder(e,t){return e.semisimple?Pe.makeFragment(ot(e.body,t,!1)):Pe.makeSpan(["mord"],ot(e.body,t,!0),t)},mathmlBuilder(e,t){return kt(e.body,t,!0)}}),$e({type:"overline",names:["\\overline"],props:{numArgs:1},handler(e,t){let{parser:r}=e;const n=t[0];return{type:"overline",mode:r.mode,body:n}},htmlBuilder(e,t){const r=ct(e.body,t.havingCrampedStyle()),n=Pe.makeLineSpan("overline-line",t),o=t.fontMetrics().defaultRuleThickness,s=Pe.makeVList({positionType:"firstBaseline",children:[{type:"elem",elem:r},{type:"kern",size:3*o},{type:"elem",elem:n},{type:"kern",size:o}]},t);return Pe.makeSpan(["mord","overline"],[s],t)},mathmlBuilder(e,t){const r=new ft.MathNode("mo",[new ft.TextNode("\u203e")]);r.setAttribute("stretchy","true");const n=new ft.MathNode("mover",[St(e.body,t),r]);return n.setAttribute("accent","true"),n}}),$e({type:"phantom",names:["\\phantom"],props:{numArgs:1,allowedInText:!0},handler:(e,t)=>{let{parser:r}=e;const n=t[0];return{type:"phantom",mode:r.mode,body:Je(n)}},htmlBuilder:(e,t)=>{const r=ot(e.body,t.withPhantom(),!1);return Pe.makeFragment(r)},mathmlBuilder:(e,t)=>{const r=vt(e.body,t);return new ft.MathNode("mphantom",r)}}),$e({type:"hphantom",names:["\\hphantom"],props:{numArgs:1,allowedInText:!0},handler:(e,t)=>{let{parser:r}=e;const n=t[0];return{type:"hphantom",mode:r.mode,body:n}},htmlBuilder:(e,t)=>{let r=Pe.makeSpan([],[ct(e.body,t.withPhantom())]);if(r.height=0,r.depth=0,r.children)for(let e=0;e{const r=vt(Je(e.body),t),n=new ft.MathNode("mphantom",r),o=new ft.MathNode("mpadded",[n]);return o.setAttribute("height","0px"),o.setAttribute("depth","0px"),o}}),$e({type:"vphantom",names:["\\vphantom"],props:{numArgs:1,allowedInText:!0},handler:(e,t)=>{let{parser:r}=e;const n=t[0];return{type:"vphantom",mode:r.mode,body:n}},htmlBuilder:(e,t)=>{const r=Pe.makeSpan(["inner"],[ct(e.body,t.withPhantom())]),n=Pe.makeSpan(["fix"],[]);return Pe.makeSpan(["mord","rlap"],[r,n],t)},mathmlBuilder:(e,t)=>{const r=vt(Je(e.body),t),n=new ft.MathNode("mphantom",r),o=new ft.MathNode("mpadded",[n]);return o.setAttribute("width","0px"),o}}),$e({type:"raisebox",names:["\\raisebox"],props:{numArgs:2,argTypes:["size","hbox"],allowedInText:!0},handler(e,t){let{parser:r}=e;const n=Rt(t[0],"size").value,o=t[1];return{type:"raisebox",mode:r.mode,dy:n,body:o}},htmlBuilder(e,t){const r=ct(e.body,t),n=P(e.dy,t);return Pe.makeVList({positionType:"shift",positionData:-n,children:[{type:"elem",elem:r}]},t)},mathmlBuilder(e,t){const r=new ft.MathNode("mpadded",[St(e.body,t)]),n=e.dy.number+e.dy.unit;return r.setAttribute("voffset",n),r}}),$e({type:"internal",names:["\\relax"],props:{numArgs:0,allowedInText:!0,allowedInArgument:!0},handler(e){let{parser:t}=e;return{type:"internal",mode:t.mode}}}),$e({type:"rule",names:["\\rule"],props:{numArgs:2,numOptionalArgs:1,allowedInText:!0,allowedInMath:!0,argTypes:["size","size","size"]},handler(e,t,r){let{parser:n}=e;const o=r[0],s=Rt(t[0],"size"),i=Rt(t[1],"size");return{type:"rule",mode:n.mode,shift:o&&Rt(o,"size").value,width:s.value,height:i.value}},htmlBuilder(e,t){const r=Pe.makeSpan(["mord","rule"],[],t),n=P(e.width,t),o=P(e.height,t),s=e.shift?P(e.shift,t):0;return r.style.borderRightWidth=F(n),r.style.borderTopWidth=F(o),r.style.bottom=F(s),r.width=n,r.height=o+s,r.depth=-s,r.maxFontSize=1.125*o*t.sizeMultiplier,r},mathmlBuilder(e,t){const r=P(e.width,t),n=P(e.height,t),o=e.shift?P(e.shift,t):0,s=t.color&&t.getColor()||"black",i=new ft.MathNode("mspace");i.setAttribute("mathbackground",s),i.setAttribute("width",F(r)),i.setAttribute("height",F(n));const a=new ft.MathNode("mpadded",[i]);return o>=0?a.setAttribute("height",F(o)):(a.setAttribute("height",F(o)),a.setAttribute("depth",F(-o))),a.setAttribute("voffset",F(o)),a}});const hn=["\\tiny","\\sixptsize","\\scriptsize","\\footnotesize","\\small","\\normalsize","\\large","\\Large","\\LARGE","\\huge","\\Huge"];$e({type:"sizing",names:hn,props:{numArgs:0,allowedInText:!0},handler:(e,t)=>{let{breakOnTokenText:r,funcName:n,parser:o}=e;const s=o.parseExpression(!1,r);return{type:"sizing",mode:o.mode,size:hn.indexOf(n)+1,body:s}},htmlBuilder:(e,t)=>{const r=t.havingSize(e.size);return ln(e.body,r,t)},mathmlBuilder:(e,t)=>{const r=t.havingSize(e.size),n=vt(e.body,r),o=new ft.MathNode("mstyle",n);return o.setAttribute("mathsize",F(r.sizeMultiplier)),o}}),$e({type:"smash",names:["\\smash"],props:{numArgs:1,numOptionalArgs:1,allowedInText:!0},handler:(e,t,r)=>{let{parser:n}=e,o=!1,s=!1;const i=r[0]&&Rt(r[0],"ordgroup");if(i){let e="";for(let t=0;t{const r=Pe.makeSpan([],[ct(e.body,t)]);if(!e.smashHeight&&!e.smashDepth)return r;if(e.smashHeight&&(r.height=0,r.children))for(let e=0;e{const r=new ft.MathNode("mpadded",[St(e.body,t)]);return e.smashHeight&&r.setAttribute("height","0px"),e.smashDepth&&r.setAttribute("depth","0px"),r}}),$e({type:"sqrt",names:["\\sqrt"],props:{numArgs:1,numOptionalArgs:1},handler(e,t,r){let{parser:n}=e;const o=r[0],s=t[0];return{type:"sqrt",mode:n.mode,body:s,index:o}},htmlBuilder(e,t){let r=ct(e.body,t.havingCrampedStyle());0===r.height&&(r.height=t.fontMetrics().xHeight),r=Pe.wrapFragment(r,t);const n=t.fontMetrics().defaultRuleThickness;let o=n;t.style.idr.height+r.depth+s&&(s=(s+c-r.height-r.depth)/2);const m=a.height-r.height-s-l;r.style.paddingLeft=F(h);const p=Pe.makeVList({positionType:"firstBaseline",children:[{type:"elem",elem:r,wrapperClasses:["svg-align"]},{type:"kern",size:-(r.height+m)},{type:"elem",elem:a},{type:"kern",size:l}]},t);if(e.index){const r=t.havingStyle(w.SCRIPTSCRIPT),n=ct(e.index,r,t),o=.6*(p.height-p.depth),s=Pe.makeVList({positionType:"shift",positionData:-o,children:[{type:"elem",elem:n}]},t),i=Pe.makeSpan(["root"],[s]);return Pe.makeSpan(["mord","sqrt"],[i,p],t)}return Pe.makeSpan(["mord","sqrt"],[p],t)},mathmlBuilder(e,t){const{body:r,index:n}=e;return n?new ft.MathNode("mroot",[St(r,t),St(n,t)]):new ft.MathNode("msqrt",[St(r,t)])}});const cn={display:w.DISPLAY,text:w.TEXT,script:w.SCRIPT,scriptscript:w.SCRIPTSCRIPT};$e({type:"styling",names:["\\displaystyle","\\textstyle","\\scriptstyle","\\scriptscriptstyle"],props:{numArgs:0,allowedInText:!0,primitive:!0},handler(e,t){let{breakOnTokenText:r,funcName:n,parser:o}=e;const s=o.parseExpression(!0,r),i=n.slice(1,n.length-5);return{type:"styling",mode:o.mode,style:i,body:s}},htmlBuilder(e,t){const r=cn[e.style],n=t.havingStyle(r).withFont("");return ln(e.body,n,t)},mathmlBuilder(e,t){const r=cn[e.style],n=t.havingStyle(r),o=vt(e.body,n),s=new ft.MathNode("mstyle",o),i={display:["0","true"],text:["0","false"],script:["1","false"],scriptscript:["2","false"]}[e.style];return s.setAttribute("scriptlevel",i[0]),s.setAttribute("displaystyle",i[1]),s}});Ze({type:"supsub",htmlBuilder(e,t){const r=function(e,t){const r=e.base;if(r)return"op"===r.type?r.limits&&(t.style.size===w.DISPLAY.size||r.alwaysHandleSupSub)?rn:null:"operatorname"===r.type?r.alwaysHandleSupSub&&(t.style.size===w.DISPLAY.size||r.limits)?an:null:"accent"===r.type?l.isCharacterBox(r.base)?Et:null:"horizBrace"===r.type&&!e.sub===r.isOver?Kr:null;return null}(e,t);if(r)return r(e,t);const{base:n,sup:o,sub:s}=e,i=ct(n,t);let a,h;const c=t.fontMetrics();let m=0,p=0;const u=n&&l.isCharacterBox(n);if(o){const e=t.havingStyle(t.style.sup());a=ct(o,e,t),u||(m=i.height-e.fontMetrics().supDrop*e.sizeMultiplier/t.sizeMultiplier)}if(s){const e=t.havingStyle(t.style.sub());h=ct(s,e,t),u||(p=i.depth+e.fontMetrics().subDrop*e.sizeMultiplier/t.sizeMultiplier)}let d;d=t.style===w.DISPLAY?c.sup1:t.style.cramped?c.sup3:c.sup2;const g=t.sizeMultiplier,f=F(.5/c.ptPerEm/g);let b,y=null;if(h){const t=e.base&&"op"===e.base.type&&e.base.name&&("\\oiint"===e.base.name||"\\oiiint"===e.base.name);(i instanceof K||t)&&(y=F(-i.italic))}if(a&&h){m=Math.max(m,d,a.depth+.25*c.xHeight),p=Math.max(p,c.sub2);const e=4*c.defaultRuleThickness;if(m-a.depth-(h.height-p)0&&(m+=t,p-=t)}const r=[{type:"elem",elem:h,shift:p,marginRight:f,marginLeft:y},{type:"elem",elem:a,shift:-m,marginRight:f}];b=Pe.makeVList({positionType:"individualShift",children:r},t)}else if(h){p=Math.max(p,c.sub1,h.height-.8*c.xHeight);const e=[{type:"elem",elem:h,marginLeft:y,marginRight:f}];b=Pe.makeVList({positionType:"shift",positionData:p,children:e},t)}else{if(!a)throw new Error("supsub must have either sup or sub.");m=Math.max(m,d,a.depth+.25*c.xHeight),b=Pe.makeVList({positionType:"shift",positionData:-m,children:[{type:"elem",elem:a,marginRight:f}]},t)}const x=lt(i,"right")||"mord";return Pe.makeSpan([x],[i,Pe.makeSpan(["msupsub"],[b])],t)},mathmlBuilder(e,t){let r,n,o=!1;e.base&&"horizBrace"===e.base.type&&(n=!!e.sup,n===e.base.isOver&&(o=!0,r=e.base.isOver)),!e.base||"op"!==e.base.type&&"operatorname"!==e.base.type||(e.base.parentIsSupSub=!0);const s=[St(e.base,t)];let i;if(e.sub&&s.push(St(e.sub,t)),e.sup&&s.push(St(e.sup,t)),o)i=r?"mover":"munder";else if(e.sub)if(e.sup){const r=e.base;i=r&&"op"===r.type&&r.limits&&t.style===w.DISPLAY||r&&"operatorname"===r.type&&r.alwaysHandleSupSub&&(t.style===w.DISPLAY||r.limits)?"munderover":"msubsup"}else{const r=e.base;i=r&&"op"===r.type&&r.limits&&(t.style===w.DISPLAY||r.alwaysHandleSupSub)||r&&"operatorname"===r.type&&r.alwaysHandleSupSub&&(r.limits||t.style===w.DISPLAY)?"munder":"msub"}else{const r=e.base;i=r&&"op"===r.type&&r.limits&&(t.style===w.DISPLAY||r.alwaysHandleSupSub)||r&&"operatorname"===r.type&&r.alwaysHandleSupSub&&(r.limits||t.style===w.DISPLAY)?"mover":"msup"}return new ft.MathNode(i,s)}}),Ze({type:"atom",htmlBuilder(e,t){return Pe.mathsym(e.text,e.mode,t,["m"+e.family])},mathmlBuilder(e,t){const r=new ft.MathNode("mo",[bt(e.text,e.mode)]);if("bin"===e.family){const n=xt(e,t);"bold-italic"===n&&r.setAttribute("mathvariant",n)}else"punct"===e.family?r.setAttribute("separator","true"):"open"!==e.family&&"close"!==e.family||r.setAttribute("stretchy","false");return r}});const mn={mi:"italic",mn:"normal",mtext:"normal"};Ze({type:"mathord",htmlBuilder(e,t){return Pe.makeOrd(e,t,"mathord")},mathmlBuilder(e,t){const r=new ft.MathNode("mi",[bt(e.text,e.mode,t)]),n=xt(e,t)||"italic";return n!==mn[r.type]&&r.setAttribute("mathvariant",n),r}}),Ze({type:"textord",htmlBuilder(e,t){return Pe.makeOrd(e,t,"textord")},mathmlBuilder(e,t){const r=bt(e.text,e.mode,t),n=xt(e,t)||"normal";let o;return o="text"===e.mode?new ft.MathNode("mtext",[r]):/[0-9]/.test(e.text)?new ft.MathNode("mn",[r]):"\\prime"===e.text?new ft.MathNode("mo",[r]):new ft.MathNode("mi",[r]),n!==mn[o.type]&&o.setAttribute("mathvariant",n),o}});const pn={"\\nobreak":"nobreak","\\allowbreak":"allowbreak"},un={" ":{},"\\ ":{},"~":{className:"nobreak"},"\\space":{},"\\nobreakspace":{className:"nobreak"}};Ze({type:"spacing",htmlBuilder(e,t){if(un.hasOwnProperty(e.text)){const r=un[e.text].className||"";if("text"===e.mode){const n=Pe.makeOrd(e,t,"textord");return n.classes.push(r),n}return Pe.makeSpan(["mspace",r],[Pe.mathsym(e.text,e.mode,t)],t)}if(pn.hasOwnProperty(e.text))return Pe.makeSpan(["mspace",pn[e.text]],[],t);throw new n('Unknown type of space "'+e.text+'"')},mathmlBuilder(e,t){let r;if(!un.hasOwnProperty(e.text)){if(pn.hasOwnProperty(e.text))return new ft.MathNode("mspace");throw new n('Unknown type of space "'+e.text+'"')}return r=new ft.MathNode("mtext",[new ft.TextNode("\xa0")]),r}});const dn=()=>{const e=new ft.MathNode("mtd",[]);return e.setAttribute("width","50%"),e};Ze({type:"tag",mathmlBuilder(e,t){const r=new ft.MathNode("mtable",[new ft.MathNode("mtr",[dn(),new ft.MathNode("mtd",[kt(e.body,t)]),dn(),new ft.MathNode("mtd",[kt(e.tag,t)])])]);return r.setAttribute("width","100%"),r}});const gn={"\\text":void 0,"\\textrm":"textrm","\\textsf":"textsf","\\texttt":"texttt","\\textnormal":"textrm"},fn={"\\textbf":"textbf","\\textmd":"textmd"},bn={"\\textit":"textit","\\textup":"textup"},yn=(e,t)=>{const r=e.font;return r?gn[r]?t.withTextFontFamily(gn[r]):fn[r]?t.withTextFontWeight(fn[r]):"\\emph"===r?"textit"===t.fontShape?t.withTextFontShape("textup"):t.withTextFontShape("textit"):t.withTextFontShape(bn[r]):t};$e({type:"text",names:["\\text","\\textrm","\\textsf","\\texttt","\\textnormal","\\textbf","\\textmd","\\textit","\\textup","\\emph"],props:{numArgs:1,argTypes:["text"],allowedInArgument:!0,allowedInText:!0},handler(e,t){let{parser:r,funcName:n}=e;const o=t[0];return{type:"text",mode:r.mode,body:Je(o),font:n}},htmlBuilder(e,t){const r=yn(e,t),n=ot(e.body,r,!0);return Pe.makeSpan(["mord","text"],n,r)},mathmlBuilder(e,t){const r=yn(e,t);return kt(e.body,r)}}),$e({type:"underline",names:["\\underline"],props:{numArgs:1,allowedInText:!0},handler(e,t){let{parser:r}=e;return{type:"underline",mode:r.mode,body:t[0]}},htmlBuilder(e,t){const r=ct(e.body,t),n=Pe.makeLineSpan("underline-line",t),o=t.fontMetrics().defaultRuleThickness,s=Pe.makeVList({positionType:"top",positionData:r.height,children:[{type:"kern",size:o},{type:"elem",elem:n},{type:"kern",size:3*o},{type:"elem",elem:r}]},t);return Pe.makeSpan(["mord","underline"],[s],t)},mathmlBuilder(e,t){const r=new ft.MathNode("mo",[new ft.TextNode("\u203e")]);r.setAttribute("stretchy","true");const n=new ft.MathNode("munder",[St(e.body,t),r]);return n.setAttribute("accentunder","true"),n}}),$e({type:"vcenter",names:["\\vcenter"],props:{numArgs:1,argTypes:["original"],allowedInText:!1},handler(e,t){let{parser:r}=e;return{type:"vcenter",mode:r.mode,body:t[0]}},htmlBuilder(e,t){const r=ct(e.body,t),n=t.fontMetrics().axisHeight,o=.5*(r.height-n-(r.depth+n));return Pe.makeVList({positionType:"shift",positionData:o,children:[{type:"elem",elem:r}]},t)},mathmlBuilder(e,t){return new ft.MathNode("mpadded",[St(e.body,t)],["vcenter"])}}),$e({type:"verb",names:["\\verb"],props:{numArgs:0,allowedInText:!0},handler(e,t,r){throw new n("\\verb ended by end of line instead of matching delimiter")},htmlBuilder(e,t){const r=xn(e),n=[],o=t.havingStyle(t.style.text());for(let t=0;te.body.replace(/ /g,e.star?"\u2423":"\xa0");var wn=We;const vn="[ \r\n\t]",kn="(\\\\[a-zA-Z@]+)"+vn+"*",Sn="[\u0300-\u036f]",Mn=new RegExp(Sn+"+$"),zn="("+vn+"+)|\\\\(\n|[ \r\t]+\n?)[ \r\t]*|([!-\\[\\]-\u2027\u202a-\ud7ff\uf900-\uffff]"+Sn+"*|[\ud800-\udbff][\udc00-\udfff]"+Sn+"*|\\\\verb\\*([^]).*?\\4|\\\\verb([^*a-zA-Z]).*?\\5|"+kn+"|\\\\[^\ud800-\udfff])";class An{constructor(e,t){this.input=void 0,this.settings=void 0,this.tokenRegex=void 0,this.catcodes=void 0,this.input=e,this.settings=t,this.tokenRegex=new RegExp(zn,"g"),this.catcodes={"%":14,"~":13}}setCatcode(e,t){this.catcodes[e]=t}lex(){const e=this.input,t=this.tokenRegex.lastIndex;if(t===e.length)return new Ir("EOF",new qr(this,t,t));const r=this.tokenRegex.exec(e);if(null===r||r.index!==t)throw new n("Unexpected character: '"+e[t]+"'",new Ir(e[t],new qr(this,t,t+1)));const o=r[6]||r[3]||(r[2]?"\\ ":" ");if(14===this.catcodes[o]){const t=e.indexOf("\n",this.tokenRegex.lastIndex);return-1===t?(this.tokenRegex.lastIndex=e.length,this.settings.reportNonstrict("commentAtEnd","% comment has no terminating newline; LaTeX would fail because of commenting the end of math mode (e.g. $)")):this.tokenRegex.lastIndex=t+1,this.lex()}return new Ir(o,new qr(this,t,this.tokenRegex.lastIndex))}}class Tn{constructor(e,t){void 0===e&&(e={}),void 0===t&&(t={}),this.current=void 0,this.builtins=void 0,this.undefStack=void 0,this.current=t,this.builtins=e,this.undefStack=[]}beginGroup(){this.undefStack.push({})}endGroup(){if(0===this.undefStack.length)throw new n("Unbalanced namespace destruction: attempt to pop global namespace; please report this as a bug");const e=this.undefStack.pop();for(const t in e)e.hasOwnProperty(t)&&(null==e[t]?delete this.current[t]:this.current[t]=e[t])}endGroups(){for(;this.undefStack.length>0;)this.endGroup()}has(e){return this.current.hasOwnProperty(e)||this.builtins.hasOwnProperty(e)}get(e){return this.current.hasOwnProperty(e)?this.current[e]:this.builtins[e]}set(e,t,r){if(void 0===r&&(r=!1),r){for(let t=0;t0&&(this.undefStack[this.undefStack.length-1][e]=t)}else{const t=this.undefStack[this.undefStack.length-1];t&&!t.hasOwnProperty(e)&&(t[e]=this.current[e])}null==t?delete this.current[e]:this.current[e]=t}}var Bn=Cr;Nr("\\noexpand",(function(e){const t=e.popToken();return e.isExpandable(t.text)&&(t.noexpand=!0,t.treatAsRelax=!0),{tokens:[t],numArgs:0}})),Nr("\\expandafter",(function(e){const t=e.popToken();return e.expandOnce(!0),{tokens:[t],numArgs:0}})),Nr("\\@firstoftwo",(function(e){return{tokens:e.consumeArgs(2)[0],numArgs:0}})),Nr("\\@secondoftwo",(function(e){return{tokens:e.consumeArgs(2)[1],numArgs:0}})),Nr("\\@ifnextchar",(function(e){const t=e.consumeArgs(3);e.consumeSpaces();const r=e.future();return 1===t[0].length&&t[0][0].text===r.text?{tokens:t[1],numArgs:0}:{tokens:t[2],numArgs:0}})),Nr("\\@ifstar","\\@ifnextchar *{\\@firstoftwo{#1}}"),Nr("\\TextOrMath",(function(e){const t=e.consumeArgs(2);return"text"===e.mode?{tokens:t[0],numArgs:0}:{tokens:t[1],numArgs:0}}));const Cn={0:0,1:1,2:2,3:3,4:4,5:5,6:6,7:7,8:8,9:9,a:10,A:10,b:11,B:11,c:12,C:12,d:13,D:13,e:14,E:14,f:15,F:15};Nr("\\char",(function(e){let t,r=e.popToken(),o="";if("'"===r.text)t=8,r=e.popToken();else if('"'===r.text)t=16,r=e.popToken();else if("`"===r.text)if(r=e.popToken(),"\\"===r.text[0])o=r.text.charCodeAt(1);else{if("EOF"===r.text)throw new n("\\char` missing argument");o=r.text.charCodeAt(0)}else t=10;if(t){if(o=Cn[r.text],null==o||o>=t)throw new n("Invalid base-"+t+" digit "+r.text);let s;for(;null!=(s=Cn[e.future().text])&&s{let s=e.consumeArg().tokens;if(1!==s.length)throw new n("\\newcommand's first argument must be a macro name");const i=s[0].text,a=e.isDefined(i);if(a&&!t)throw new n("\\newcommand{"+i+"} attempting to redefine "+i+"; use \\renewcommand");if(!a&&!r)throw new n("\\renewcommand{"+i+"} when command "+i+" does not yet exist; use \\newcommand");let l=0;if(s=e.consumeArg().tokens,1===s.length&&"["===s[0].text){let t="",r=e.expandNextToken();for(;"]"!==r.text&&"EOF"!==r.text;)t+=r.text,r=e.expandNextToken();if(!t.match(/^\s*[0-9]+\s*$/))throw new n("Invalid number of arguments: "+t);l=parseInt(t),s=e.consumeArg().tokens}return a&&o||e.macros.set(i,{tokens:s,numArgs:l}),""};Nr("\\newcommand",(e=>Nn(e,!1,!0,!1))),Nr("\\renewcommand",(e=>Nn(e,!0,!1,!1))),Nr("\\providecommand",(e=>Nn(e,!0,!0,!0))),Nr("\\message",(e=>{const t=e.consumeArgs(1)[0];return console.log(t.reverse().map((e=>e.text)).join("")),""})),Nr("\\errmessage",(e=>{const t=e.consumeArgs(1)[0];return console.error(t.reverse().map((e=>e.text)).join("")),""})),Nr("\\show",(e=>{const t=e.popToken(),r=t.text;return console.log(t,e.macros.get(r),wn[r],se.math[r],se.text[r]),""})),Nr("\\bgroup","{"),Nr("\\egroup","}"),Nr("~","\\nobreakspace"),Nr("\\lq","`"),Nr("\\rq","'"),Nr("\\aa","\\r a"),Nr("\\AA","\\r A"),Nr("\\textcopyright","\\html@mathml{\\textcircled{c}}{\\char`\xa9}"),Nr("\\copyright","\\TextOrMath{\\textcopyright}{\\text{\\textcopyright}}"),Nr("\\textregistered","\\html@mathml{\\textcircled{\\scriptsize R}}{\\char`\xae}"),Nr("\u212c","\\mathscr{B}"),Nr("\u2130","\\mathscr{E}"),Nr("\u2131","\\mathscr{F}"),Nr("\u210b","\\mathscr{H}"),Nr("\u2110","\\mathscr{I}"),Nr("\u2112","\\mathscr{L}"),Nr("\u2133","\\mathscr{M}"),Nr("\u211b","\\mathscr{R}"),Nr("\u212d","\\mathfrak{C}"),Nr("\u210c","\\mathfrak{H}"),Nr("\u2128","\\mathfrak{Z}"),Nr("\\Bbbk","\\Bbb{k}"),Nr("\xb7","\\cdotp"),Nr("\\llap","\\mathllap{\\textrm{#1}}"),Nr("\\rlap","\\mathrlap{\\textrm{#1}}"),Nr("\\clap","\\mathclap{\\textrm{#1}}"),Nr("\\mathstrut","\\vphantom{(}"),Nr("\\underbar","\\underline{\\text{#1}}"),Nr("\\not",'\\html@mathml{\\mathrel{\\mathrlap\\@not}}{\\char"338}'),Nr("\\neq","\\html@mathml{\\mathrel{\\not=}}{\\mathrel{\\char`\u2260}}"),Nr("\\ne","\\neq"),Nr("\u2260","\\neq"),Nr("\\notin","\\html@mathml{\\mathrel{{\\in}\\mathllap{/\\mskip1mu}}}{\\mathrel{\\char`\u2209}}"),Nr("\u2209","\\notin"),Nr("\u2258","\\html@mathml{\\mathrel{=\\kern{-1em}\\raisebox{0.4em}{$\\scriptsize\\frown$}}}{\\mathrel{\\char`\u2258}}"),Nr("\u2259","\\html@mathml{\\stackrel{\\tiny\\wedge}{=}}{\\mathrel{\\char`\u2258}}"),Nr("\u225a","\\html@mathml{\\stackrel{\\tiny\\vee}{=}}{\\mathrel{\\char`\u225a}}"),Nr("\u225b","\\html@mathml{\\stackrel{\\scriptsize\\star}{=}}{\\mathrel{\\char`\u225b}}"),Nr("\u225d","\\html@mathml{\\stackrel{\\tiny\\mathrm{def}}{=}}{\\mathrel{\\char`\u225d}}"),Nr("\u225e","\\html@mathml{\\stackrel{\\tiny\\mathrm{m}}{=}}{\\mathrel{\\char`\u225e}}"),Nr("\u225f","\\html@mathml{\\stackrel{\\tiny?}{=}}{\\mathrel{\\char`\u225f}}"),Nr("\u27c2","\\perp"),Nr("\u203c","\\mathclose{!\\mkern-0.8mu!}"),Nr("\u220c","\\notni"),Nr("\u231c","\\ulcorner"),Nr("\u231d","\\urcorner"),Nr("\u231e","\\llcorner"),Nr("\u231f","\\lrcorner"),Nr("\xa9","\\copyright"),Nr("\xae","\\textregistered"),Nr("\ufe0f","\\textregistered"),Nr("\\ulcorner",'\\html@mathml{\\@ulcorner}{\\mathop{\\char"231c}}'),Nr("\\urcorner",'\\html@mathml{\\@urcorner}{\\mathop{\\char"231d}}'),Nr("\\llcorner",'\\html@mathml{\\@llcorner}{\\mathop{\\char"231e}}'),Nr("\\lrcorner",'\\html@mathml{\\@lrcorner}{\\mathop{\\char"231f}}'),Nr("\\vdots","{\\varvdots\\rule{0pt}{15pt}}"),Nr("\u22ee","\\vdots"),Nr("\\varGamma","\\mathit{\\Gamma}"),Nr("\\varDelta","\\mathit{\\Delta}"),Nr("\\varTheta","\\mathit{\\Theta}"),Nr("\\varLambda","\\mathit{\\Lambda}"),Nr("\\varXi","\\mathit{\\Xi}"),Nr("\\varPi","\\mathit{\\Pi}"),Nr("\\varSigma","\\mathit{\\Sigma}"),Nr("\\varUpsilon","\\mathit{\\Upsilon}"),Nr("\\varPhi","\\mathit{\\Phi}"),Nr("\\varPsi","\\mathit{\\Psi}"),Nr("\\varOmega","\\mathit{\\Omega}"),Nr("\\substack","\\begin{subarray}{c}#1\\end{subarray}"),Nr("\\colon","\\nobreak\\mskip2mu\\mathpunct{}\\mathchoice{\\mkern-3mu}{\\mkern-3mu}{}{}{:}\\mskip6mu\\relax"),Nr("\\boxed","\\fbox{$\\displaystyle{#1}$}"),Nr("\\iff","\\DOTSB\\;\\Longleftrightarrow\\;"),Nr("\\implies","\\DOTSB\\;\\Longrightarrow\\;"),Nr("\\impliedby","\\DOTSB\\;\\Longleftarrow\\;"),Nr("\\dddot","{\\overset{\\raisebox{-0.1ex}{\\normalsize ...}}{#1}}"),Nr("\\ddddot","{\\overset{\\raisebox{-0.1ex}{\\normalsize ....}}{#1}}");const qn={",":"\\dotsc","\\not":"\\dotsb","+":"\\dotsb","=":"\\dotsb","<":"\\dotsb",">":"\\dotsb","-":"\\dotsb","*":"\\dotsb",":":"\\dotsb","\\DOTSB":"\\dotsb","\\coprod":"\\dotsb","\\bigvee":"\\dotsb","\\bigwedge":"\\dotsb","\\biguplus":"\\dotsb","\\bigcap":"\\dotsb","\\bigcup":"\\dotsb","\\prod":"\\dotsb","\\sum":"\\dotsb","\\bigotimes":"\\dotsb","\\bigoplus":"\\dotsb","\\bigodot":"\\dotsb","\\bigsqcup":"\\dotsb","\\And":"\\dotsb","\\longrightarrow":"\\dotsb","\\Longrightarrow":"\\dotsb","\\longleftarrow":"\\dotsb","\\Longleftarrow":"\\dotsb","\\longleftrightarrow":"\\dotsb","\\Longleftrightarrow":"\\dotsb","\\mapsto":"\\dotsb","\\longmapsto":"\\dotsb","\\hookrightarrow":"\\dotsb","\\doteq":"\\dotsb","\\mathbin":"\\dotsb","\\mathrel":"\\dotsb","\\relbar":"\\dotsb","\\Relbar":"\\dotsb","\\xrightarrow":"\\dotsb","\\xleftarrow":"\\dotsb","\\DOTSI":"\\dotsi","\\int":"\\dotsi","\\oint":"\\dotsi","\\iint":"\\dotsi","\\iiint":"\\dotsi","\\iiiint":"\\dotsi","\\idotsint":"\\dotsi","\\DOTSX":"\\dotsx"};Nr("\\dots",(function(e){let t="\\dotso";const r=e.expandAfterFuture().text;return r in qn?t=qn[r]:("\\not"===r.slice(0,4)||r in se.math&&l.contains(["bin","rel"],se.math[r].group))&&(t="\\dotsb"),t}));const In={")":!0,"]":!0,"\\rbrack":!0,"\\}":!0,"\\rbrace":!0,"\\rangle":!0,"\\rceil":!0,"\\rfloor":!0,"\\rgroup":!0,"\\rmoustache":!0,"\\right":!0,"\\bigr":!0,"\\biggr":!0,"\\Bigr":!0,"\\Biggr":!0,$:!0,";":!0,".":!0,",":!0};Nr("\\dotso",(function(e){return e.future().text in In?"\\ldots\\,":"\\ldots"})),Nr("\\dotsc",(function(e){const t=e.future().text;return t in In&&","!==t?"\\ldots\\,":"\\ldots"})),Nr("\\cdots",(function(e){return e.future().text in In?"\\@cdots\\,":"\\@cdots"})),Nr("\\dotsb","\\cdots"),Nr("\\dotsm","\\cdots"),Nr("\\dotsi","\\!\\cdots"),Nr("\\dotsx","\\ldots\\,"),Nr("\\DOTSI","\\relax"),Nr("\\DOTSB","\\relax"),Nr("\\DOTSX","\\relax"),Nr("\\tmspace","\\TextOrMath{\\kern#1#3}{\\mskip#1#2}\\relax"),Nr("\\,","\\tmspace+{3mu}{.1667em}"),Nr("\\thinspace","\\,"),Nr("\\>","\\mskip{4mu}"),Nr("\\:","\\tmspace+{4mu}{.2222em}"),Nr("\\medspace","\\:"),Nr("\\;","\\tmspace+{5mu}{.2777em}"),Nr("\\thickspace","\\;"),Nr("\\!","\\tmspace-{3mu}{.1667em}"),Nr("\\negthinspace","\\!"),Nr("\\negmedspace","\\tmspace-{4mu}{.2222em}"),Nr("\\negthickspace","\\tmspace-{5mu}{.277em}"),Nr("\\enspace","\\kern.5em "),Nr("\\enskip","\\hskip.5em\\relax"),Nr("\\quad","\\hskip1em\\relax"),Nr("\\qquad","\\hskip2em\\relax"),Nr("\\tag","\\@ifstar\\tag@literal\\tag@paren"),Nr("\\tag@paren","\\tag@literal{({#1})}"),Nr("\\tag@literal",(e=>{if(e.macros.get("\\df@tag"))throw new n("Multiple \\tag");return"\\gdef\\df@tag{\\text{#1}}"})),Nr("\\bmod","\\mathchoice{\\mskip1mu}{\\mskip1mu}{\\mskip5mu}{\\mskip5mu}\\mathbin{\\rm mod}\\mathchoice{\\mskip1mu}{\\mskip1mu}{\\mskip5mu}{\\mskip5mu}"),Nr("\\pod","\\allowbreak\\mathchoice{\\mkern18mu}{\\mkern8mu}{\\mkern8mu}{\\mkern8mu}(#1)"),Nr("\\pmod","\\pod{{\\rm mod}\\mkern6mu#1}"),Nr("\\mod","\\allowbreak\\mathchoice{\\mkern18mu}{\\mkern12mu}{\\mkern12mu}{\\mkern12mu}{\\rm mod}\\,\\,#1"),Nr("\\newline","\\\\\\relax"),Nr("\\TeX","\\textrm{\\html@mathml{T\\kern-.1667em\\raisebox{-.5ex}{E}\\kern-.125emX}{TeX}}");const Rn=F(T["Main-Regular"]["T".charCodeAt(0)][1]-.7*T["Main-Regular"]["A".charCodeAt(0)][1]);Nr("\\LaTeX","\\textrm{\\html@mathml{L\\kern-.36em\\raisebox{"+Rn+"}{\\scriptstyle A}\\kern-.15em\\TeX}{LaTeX}}"),Nr("\\KaTeX","\\textrm{\\html@mathml{K\\kern-.17em\\raisebox{"+Rn+"}{\\scriptstyle A}\\kern-.15em\\TeX}{KaTeX}}"),Nr("\\hspace","\\@ifstar\\@hspacer\\@hspace"),Nr("\\@hspace","\\hskip #1\\relax"),Nr("\\@hspacer","\\rule{0pt}{0pt}\\hskip #1\\relax"),Nr("\\ordinarycolon",":"),Nr("\\vcentcolon","\\mathrel{\\mathop\\ordinarycolon}"),Nr("\\dblcolon",'\\html@mathml{\\mathrel{\\vcentcolon\\mathrel{\\mkern-.9mu}\\vcentcolon}}{\\mathop{\\char"2237}}'),Nr("\\coloneqq",'\\html@mathml{\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}=}}{\\mathop{\\char"2254}}'),Nr("\\Coloneqq",'\\html@mathml{\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}=}}{\\mathop{\\char"2237\\char"3d}}'),Nr("\\coloneq",'\\html@mathml{\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}\\mathrel{-}}}{\\mathop{\\char"3a\\char"2212}}'),Nr("\\Coloneq",'\\html@mathml{\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}\\mathrel{-}}}{\\mathop{\\char"2237\\char"2212}}'),Nr("\\eqqcolon",'\\html@mathml{\\mathrel{=\\mathrel{\\mkern-1.2mu}\\vcentcolon}}{\\mathop{\\char"2255}}'),Nr("\\Eqqcolon",'\\html@mathml{\\mathrel{=\\mathrel{\\mkern-1.2mu}\\dblcolon}}{\\mathop{\\char"3d\\char"2237}}'),Nr("\\eqcolon",'\\html@mathml{\\mathrel{\\mathrel{-}\\mathrel{\\mkern-1.2mu}\\vcentcolon}}{\\mathop{\\char"2239}}'),Nr("\\Eqcolon",'\\html@mathml{\\mathrel{\\mathrel{-}\\mathrel{\\mkern-1.2mu}\\dblcolon}}{\\mathop{\\char"2212\\char"2237}}'),Nr("\\colonapprox",'\\html@mathml{\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}\\approx}}{\\mathop{\\char"3a\\char"2248}}'),Nr("\\Colonapprox",'\\html@mathml{\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}\\approx}}{\\mathop{\\char"2237\\char"2248}}'),Nr("\\colonsim",'\\html@mathml{\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}\\sim}}{\\mathop{\\char"3a\\char"223c}}'),Nr("\\Colonsim",'\\html@mathml{\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}\\sim}}{\\mathop{\\char"2237\\char"223c}}'),Nr("\u2237","\\dblcolon"),Nr("\u2239","\\eqcolon"),Nr("\u2254","\\coloneqq"),Nr("\u2255","\\eqqcolon"),Nr("\u2a74","\\Coloneqq"),Nr("\\ratio","\\vcentcolon"),Nr("\\coloncolon","\\dblcolon"),Nr("\\colonequals","\\coloneqq"),Nr("\\coloncolonequals","\\Coloneqq"),Nr("\\equalscolon","\\eqqcolon"),Nr("\\equalscoloncolon","\\Eqqcolon"),Nr("\\colonminus","\\coloneq"),Nr("\\coloncolonminus","\\Coloneq"),Nr("\\minuscolon","\\eqcolon"),Nr("\\minuscoloncolon","\\Eqcolon"),Nr("\\coloncolonapprox","\\Colonapprox"),Nr("\\coloncolonsim","\\Colonsim"),Nr("\\simcolon","\\mathrel{\\sim\\mathrel{\\mkern-1.2mu}\\vcentcolon}"),Nr("\\simcoloncolon","\\mathrel{\\sim\\mathrel{\\mkern-1.2mu}\\dblcolon}"),Nr("\\approxcolon","\\mathrel{\\approx\\mathrel{\\mkern-1.2mu}\\vcentcolon}"),Nr("\\approxcoloncolon","\\mathrel{\\approx\\mathrel{\\mkern-1.2mu}\\dblcolon}"),Nr("\\notni","\\html@mathml{\\not\\ni}{\\mathrel{\\char`\u220c}}"),Nr("\\limsup","\\DOTSB\\operatorname*{lim\\,sup}"),Nr("\\liminf","\\DOTSB\\operatorname*{lim\\,inf}"),Nr("\\injlim","\\DOTSB\\operatorname*{inj\\,lim}"),Nr("\\projlim","\\DOTSB\\operatorname*{proj\\,lim}"),Nr("\\varlimsup","\\DOTSB\\operatorname*{\\overline{lim}}"),Nr("\\varliminf","\\DOTSB\\operatorname*{\\underline{lim}}"),Nr("\\varinjlim","\\DOTSB\\operatorname*{\\underrightarrow{lim}}"),Nr("\\varprojlim","\\DOTSB\\operatorname*{\\underleftarrow{lim}}"),Nr("\\gvertneqq","\\html@mathml{\\@gvertneqq}{\u2269}"),Nr("\\lvertneqq","\\html@mathml{\\@lvertneqq}{\u2268}"),Nr("\\ngeqq","\\html@mathml{\\@ngeqq}{\u2271}"),Nr("\\ngeqslant","\\html@mathml{\\@ngeqslant}{\u2271}"),Nr("\\nleqq","\\html@mathml{\\@nleqq}{\u2270}"),Nr("\\nleqslant","\\html@mathml{\\@nleqslant}{\u2270}"),Nr("\\nshortmid","\\html@mathml{\\@nshortmid}{\u2224}"),Nr("\\nshortparallel","\\html@mathml{\\@nshortparallel}{\u2226}"),Nr("\\nsubseteqq","\\html@mathml{\\@nsubseteqq}{\u2288}"),Nr("\\nsupseteqq","\\html@mathml{\\@nsupseteqq}{\u2289}"),Nr("\\varsubsetneq","\\html@mathml{\\@varsubsetneq}{\u228a}"),Nr("\\varsubsetneqq","\\html@mathml{\\@varsubsetneqq}{\u2acb}"),Nr("\\varsupsetneq","\\html@mathml{\\@varsupsetneq}{\u228b}"),Nr("\\varsupsetneqq","\\html@mathml{\\@varsupsetneqq}{\u2acc}"),Nr("\\imath","\\html@mathml{\\@imath}{\u0131}"),Nr("\\jmath","\\html@mathml{\\@jmath}{\u0237}"),Nr("\\llbracket","\\html@mathml{\\mathopen{[\\mkern-3.2mu[}}{\\mathopen{\\char`\u27e6}}"),Nr("\\rrbracket","\\html@mathml{\\mathclose{]\\mkern-3.2mu]}}{\\mathclose{\\char`\u27e7}}"),Nr("\u27e6","\\llbracket"),Nr("\u27e7","\\rrbracket"),Nr("\\lBrace","\\html@mathml{\\mathopen{\\{\\mkern-3.2mu[}}{\\mathopen{\\char`\u2983}}"),Nr("\\rBrace","\\html@mathml{\\mathclose{]\\mkern-3.2mu\\}}}{\\mathclose{\\char`\u2984}}"),Nr("\u2983","\\lBrace"),Nr("\u2984","\\rBrace"),Nr("\\minuso","\\mathbin{\\html@mathml{{\\mathrlap{\\mathchoice{\\kern{0.145em}}{\\kern{0.145em}}{\\kern{0.1015em}}{\\kern{0.0725em}}\\circ}{-}}}{\\char`\u29b5}}"),Nr("\u29b5","\\minuso"),Nr("\\darr","\\downarrow"),Nr("\\dArr","\\Downarrow"),Nr("\\Darr","\\Downarrow"),Nr("\\lang","\\langle"),Nr("\\rang","\\rangle"),Nr("\\uarr","\\uparrow"),Nr("\\uArr","\\Uparrow"),Nr("\\Uarr","\\Uparrow"),Nr("\\N","\\mathbb{N}"),Nr("\\R","\\mathbb{R}"),Nr("\\Z","\\mathbb{Z}"),Nr("\\alef","\\aleph"),Nr("\\alefsym","\\aleph"),Nr("\\Alpha","\\mathrm{A}"),Nr("\\Beta","\\mathrm{B}"),Nr("\\bull","\\bullet"),Nr("\\Chi","\\mathrm{X}"),Nr("\\clubs","\\clubsuit"),Nr("\\cnums","\\mathbb{C}"),Nr("\\Complex","\\mathbb{C}"),Nr("\\Dagger","\\ddagger"),Nr("\\diamonds","\\diamondsuit"),Nr("\\empty","\\emptyset"),Nr("\\Epsilon","\\mathrm{E}"),Nr("\\Eta","\\mathrm{H}"),Nr("\\exist","\\exists"),Nr("\\harr","\\leftrightarrow"),Nr("\\hArr","\\Leftrightarrow"),Nr("\\Harr","\\Leftrightarrow"),Nr("\\hearts","\\heartsuit"),Nr("\\image","\\Im"),Nr("\\infin","\\infty"),Nr("\\Iota","\\mathrm{I}"),Nr("\\isin","\\in"),Nr("\\Kappa","\\mathrm{K}"),Nr("\\larr","\\leftarrow"),Nr("\\lArr","\\Leftarrow"),Nr("\\Larr","\\Leftarrow"),Nr("\\lrarr","\\leftrightarrow"),Nr("\\lrArr","\\Leftrightarrow"),Nr("\\Lrarr","\\Leftrightarrow"),Nr("\\Mu","\\mathrm{M}"),Nr("\\natnums","\\mathbb{N}"),Nr("\\Nu","\\mathrm{N}"),Nr("\\Omicron","\\mathrm{O}"),Nr("\\plusmn","\\pm"),Nr("\\rarr","\\rightarrow"),Nr("\\rArr","\\Rightarrow"),Nr("\\Rarr","\\Rightarrow"),Nr("\\real","\\Re"),Nr("\\reals","\\mathbb{R}"),Nr("\\Reals","\\mathbb{R}"),Nr("\\Rho","\\mathrm{P}"),Nr("\\sdot","\\cdot"),Nr("\\sect","\\S"),Nr("\\spades","\\spadesuit"),Nr("\\sub","\\subset"),Nr("\\sube","\\subseteq"),Nr("\\supe","\\supseteq"),Nr("\\Tau","\\mathrm{T}"),Nr("\\thetasym","\\vartheta"),Nr("\\weierp","\\wp"),Nr("\\Zeta","\\mathrm{Z}"),Nr("\\argmin","\\DOTSB\\operatorname*{arg\\,min}"),Nr("\\argmax","\\DOTSB\\operatorname*{arg\\,max}"),Nr("\\plim","\\DOTSB\\mathop{\\operatorname{plim}}\\limits"),Nr("\\bra","\\mathinner{\\langle{#1}|}"),Nr("\\ket","\\mathinner{|{#1}\\rangle}"),Nr("\\braket","\\mathinner{\\langle{#1}\\rangle}"),Nr("\\Bra","\\left\\langle#1\\right|"),Nr("\\Ket","\\left|#1\\right\\rangle");const Hn=e=>t=>{const r=t.consumeArg().tokens,n=t.consumeArg().tokens,o=t.consumeArg().tokens,s=t.consumeArg().tokens,i=t.macros.get("|"),a=t.macros.get("\\|");t.macros.beginGroup();const l=t=>r=>{e&&(r.macros.set("|",i),o.length&&r.macros.set("\\|",a));let s=t;if(!t&&o.length){"|"===r.future().text&&(r.popToken(),s=!0)}return{tokens:s?o:n,numArgs:0}};t.macros.set("|",l(!1)),o.length&&t.macros.set("\\|",l(!0));const h=t.consumeArg().tokens,c=t.expandTokens([...s,...h,...r]);return t.macros.endGroup(),{tokens:c.reverse(),numArgs:0}};Nr("\\bra@ket",Hn(!1)),Nr("\\bra@set",Hn(!0)),Nr("\\Braket","\\bra@ket{\\left\\langle}{\\,\\middle\\vert\\,}{\\,\\middle\\vert\\,}{\\right\\rangle}"),Nr("\\Set","\\bra@set{\\left\\{\\:}{\\;\\middle\\vert\\;}{\\;\\middle\\Vert\\;}{\\:\\right\\}}"),Nr("\\set","\\bra@set{\\{\\,}{\\mid}{}{\\,\\}}"),Nr("\\angln","{\\angl n}"),Nr("\\blue","\\textcolor{##6495ed}{#1}"),Nr("\\orange","\\textcolor{##ffa500}{#1}"),Nr("\\pink","\\textcolor{##ff00af}{#1}"),Nr("\\red","\\textcolor{##df0030}{#1}"),Nr("\\green","\\textcolor{##28ae7b}{#1}"),Nr("\\gray","\\textcolor{gray}{#1}"),Nr("\\purple","\\textcolor{##9d38bd}{#1}"),Nr("\\blueA","\\textcolor{##ccfaff}{#1}"),Nr("\\blueB","\\textcolor{##80f6ff}{#1}"),Nr("\\blueC","\\textcolor{##63d9ea}{#1}"),Nr("\\blueD","\\textcolor{##11accd}{#1}"),Nr("\\blueE","\\textcolor{##0c7f99}{#1}"),Nr("\\tealA","\\textcolor{##94fff5}{#1}"),Nr("\\tealB","\\textcolor{##26edd5}{#1}"),Nr("\\tealC","\\textcolor{##01d1c1}{#1}"),Nr("\\tealD","\\textcolor{##01a995}{#1}"),Nr("\\tealE","\\textcolor{##208170}{#1}"),Nr("\\greenA","\\textcolor{##b6ffb0}{#1}"),Nr("\\greenB","\\textcolor{##8af281}{#1}"),Nr("\\greenC","\\textcolor{##74cf70}{#1}"),Nr("\\greenD","\\textcolor{##1fab54}{#1}"),Nr("\\greenE","\\textcolor{##0d923f}{#1}"),Nr("\\goldA","\\textcolor{##ffd0a9}{#1}"),Nr("\\goldB","\\textcolor{##ffbb71}{#1}"),Nr("\\goldC","\\textcolor{##ff9c39}{#1}"),Nr("\\goldD","\\textcolor{##e07d10}{#1}"),Nr("\\goldE","\\textcolor{##a75a05}{#1}"),Nr("\\redA","\\textcolor{##fca9a9}{#1}"),Nr("\\redB","\\textcolor{##ff8482}{#1}"),Nr("\\redC","\\textcolor{##f9685d}{#1}"),Nr("\\redD","\\textcolor{##e84d39}{#1}"),Nr("\\redE","\\textcolor{##bc2612}{#1}"),Nr("\\maroonA","\\textcolor{##ffbde0}{#1}"),Nr("\\maroonB","\\textcolor{##ff92c6}{#1}"),Nr("\\maroonC","\\textcolor{##ed5fa6}{#1}"),Nr("\\maroonD","\\textcolor{##ca337c}{#1}"),Nr("\\maroonE","\\textcolor{##9e034e}{#1}"),Nr("\\purpleA","\\textcolor{##ddd7ff}{#1}"),Nr("\\purpleB","\\textcolor{##c6b9fc}{#1}"),Nr("\\purpleC","\\textcolor{##aa87ff}{#1}"),Nr("\\purpleD","\\textcolor{##7854ab}{#1}"),Nr("\\purpleE","\\textcolor{##543b78}{#1}"),Nr("\\mintA","\\textcolor{##f5f9e8}{#1}"),Nr("\\mintB","\\textcolor{##edf2df}{#1}"),Nr("\\mintC","\\textcolor{##e0e5cc}{#1}"),Nr("\\grayA","\\textcolor{##f6f7f7}{#1}"),Nr("\\grayB","\\textcolor{##f0f1f2}{#1}"),Nr("\\grayC","\\textcolor{##e3e5e6}{#1}"),Nr("\\grayD","\\textcolor{##d6d8da}{#1}"),Nr("\\grayE","\\textcolor{##babec2}{#1}"),Nr("\\grayF","\\textcolor{##888d93}{#1}"),Nr("\\grayG","\\textcolor{##626569}{#1}"),Nr("\\grayH","\\textcolor{##3b3e40}{#1}"),Nr("\\grayI","\\textcolor{##21242c}{#1}"),Nr("\\kaBlue","\\textcolor{##314453}{#1}"),Nr("\\kaGreen","\\textcolor{##71B307}{#1}");const On={"^":!0,_:!0,"\\limits":!0,"\\nolimits":!0};class En{constructor(e,t,r){this.settings=void 0,this.expansionCount=void 0,this.lexer=void 0,this.macros=void 0,this.stack=void 0,this.mode=void 0,this.settings=t,this.expansionCount=0,this.feed(e),this.macros=new Tn(Bn,t.macros),this.mode=r,this.stack=[]}feed(e){this.lexer=new An(e,this.settings)}switchMode(e){this.mode=e}beginGroup(){this.macros.beginGroup()}endGroup(){this.macros.endGroup()}endGroups(){this.macros.endGroups()}future(){return 0===this.stack.length&&this.pushToken(this.lexer.lex()),this.stack[this.stack.length-1]}popToken(){return this.future(),this.stack.pop()}pushToken(e){this.stack.push(e)}pushTokens(e){this.stack.push(...e)}scanArgument(e){let t,r,n;if(e){if(this.consumeSpaces(),"["!==this.future().text)return null;t=this.popToken(),({tokens:n,end:r}=this.consumeArg(["]"]))}else({tokens:n,start:t,end:r}=this.consumeArg());return this.pushToken(new Ir("EOF",r.loc)),this.pushTokens(n),t.range(r,"")}consumeSpaces(){for(;;){if(" "!==this.future().text)break;this.stack.pop()}}consumeArg(e){const t=[],r=e&&e.length>0;r||this.consumeSpaces();const o=this.future();let s,i=0,a=0;do{if(s=this.popToken(),t.push(s),"{"===s.text)++i;else if("}"===s.text){if(--i,-1===i)throw new n("Extra }",s)}else if("EOF"===s.text)throw new n("Unexpected end of input in a macro argument, expected '"+(e&&r?e[a]:"}")+"'",s);if(e&&r)if((0===i||1===i&&"{"===e[a])&&s.text===e[a]){if(++a,a===e.length){t.splice(-a,a);break}}else a=0}while(0!==i||r);return"{"===o.text&&"}"===t[t.length-1].text&&(t.pop(),t.shift()),t.reverse(),{tokens:t,start:o,end:s}}consumeArgs(e,t){if(t){if(t.length!==e+1)throw new n("The length of delimiters doesn't match the number of args!");const r=t[0];for(let e=0;ethis.settings.maxExpand)throw new n("Too many expansions: infinite loop or need to increase maxExpand setting")}expandOnce(e){const t=this.popToken(),r=t.text,o=t.noexpand?null:this._getExpansion(r);if(null==o||e&&o.unexpandable){if(e&&null==o&&"\\"===r[0]&&!this.isDefined(r))throw new n("Undefined control sequence: "+r);return this.pushToken(t),!1}this.countExpansion(1);let s=o.tokens;const i=this.consumeArgs(o.numArgs,o.delimiters);if(o.numArgs){s=s.slice();for(let e=s.length-1;e>=0;--e){let t=s[e];if("#"===t.text){if(0===e)throw new n("Incomplete placeholder at end of macro body",t);if(t=s[--e],"#"===t.text)s.splice(e+1,1);else{if(!/^[1-9]$/.test(t.text))throw new n("Not a valid argument number",t);s.splice(e,2,...i[+t.text-1])}}}}return this.pushTokens(s),s.length}expandAfterFuture(){return this.expandOnce(),this.future()}expandNextToken(){for(;;)if(!1===this.expandOnce()){const e=this.stack.pop();return e.treatAsRelax&&(e.text="\\relax"),e}throw new Error}expandMacro(e){return this.macros.has(e)?this.expandTokens([new Ir(e)]):void 0}expandTokens(e){const t=[],r=this.stack.length;for(this.pushTokens(e);this.stack.length>r;)if(!1===this.expandOnce(!0)){const e=this.stack.pop();e.treatAsRelax&&(e.noexpand=!1,e.treatAsRelax=!1),t.push(e)}return this.countExpansion(t.length),t}expandMacroAsText(e){const t=this.expandMacro(e);return t?t.map((e=>e.text)).join(""):t}_getExpansion(e){const t=this.macros.get(e);if(null==t)return t;if(1===e.length){const t=this.lexer.catcodes[e];if(null!=t&&13!==t)return}const r="function"==typeof t?t(this):t;if("string"==typeof r){let e=0;if(-1!==r.indexOf("#")){const t=r.replace(/##/g,"");for(;-1!==t.indexOf("#"+(e+1));)++e}const t=new An(r,this.settings),n=[];let o=t.lex();for(;"EOF"!==o.text;)n.push(o),o=t.lex();n.reverse();return{tokens:n,numArgs:e}}return r}isDefined(e){return this.macros.has(e)||wn.hasOwnProperty(e)||se.math.hasOwnProperty(e)||se.text.hasOwnProperty(e)||On.hasOwnProperty(e)}isExpandable(e){const t=this.macros.get(e);return null!=t?"string"==typeof t||"function"==typeof t||!t.unexpandable:wn.hasOwnProperty(e)&&!wn[e].primitive}}const Ln=/^[\u208a\u208b\u208c\u208d\u208e\u2080\u2081\u2082\u2083\u2084\u2085\u2086\u2087\u2088\u2089\u2090\u2091\u2095\u1d62\u2c7c\u2096\u2097\u2098\u2099\u2092\u209a\u1d63\u209b\u209c\u1d64\u1d65\u2093\u1d66\u1d67\u1d68\u1d69\u1d6a]/,Dn=Object.freeze({"\u208a":"+","\u208b":"-","\u208c":"=","\u208d":"(","\u208e":")","\u2080":"0","\u2081":"1","\u2082":"2","\u2083":"3","\u2084":"4","\u2085":"5","\u2086":"6","\u2087":"7","\u2088":"8","\u2089":"9","\u2090":"a","\u2091":"e","\u2095":"h","\u1d62":"i","\u2c7c":"j","\u2096":"k","\u2097":"l","\u2098":"m","\u2099":"n","\u2092":"o","\u209a":"p","\u1d63":"r","\u209b":"s","\u209c":"t","\u1d64":"u","\u1d65":"v","\u2093":"x","\u1d66":"\u03b2","\u1d67":"\u03b3","\u1d68":"\u03c1","\u1d69":"\u03d5","\u1d6a":"\u03c7","\u207a":"+","\u207b":"-","\u207c":"=","\u207d":"(","\u207e":")","\u2070":"0","\xb9":"1","\xb2":"2","\xb3":"3","\u2074":"4","\u2075":"5","\u2076":"6","\u2077":"7","\u2078":"8","\u2079":"9","\u1d2c":"A","\u1d2e":"B","\u1d30":"D","\u1d31":"E","\u1d33":"G","\u1d34":"H","\u1d35":"I","\u1d36":"J","\u1d37":"K","\u1d38":"L","\u1d39":"M","\u1d3a":"N","\u1d3c":"O","\u1d3e":"P","\u1d3f":"R","\u1d40":"T","\u1d41":"U","\u2c7d":"V","\u1d42":"W","\u1d43":"a","\u1d47":"b","\u1d9c":"c","\u1d48":"d","\u1d49":"e","\u1da0":"f","\u1d4d":"g","\u02b0":"h","\u2071":"i","\u02b2":"j","\u1d4f":"k","\u02e1":"l","\u1d50":"m","\u207f":"n","\u1d52":"o","\u1d56":"p","\u02b3":"r","\u02e2":"s","\u1d57":"t","\u1d58":"u","\u1d5b":"v","\u02b7":"w","\u02e3":"x","\u02b8":"y","\u1dbb":"z","\u1d5d":"\u03b2","\u1d5e":"\u03b3","\u1d5f":"\u03b4","\u1d60":"\u03d5","\u1d61":"\u03c7","\u1dbf":"\u03b8"}),Vn={"\u0301":{text:"\\'",math:"\\acute"},"\u0300":{text:"\\`",math:"\\grave"},"\u0308":{text:'\\"',math:"\\ddot"},"\u0303":{text:"\\~",math:"\\tilde"},"\u0304":{text:"\\=",math:"\\bar"},"\u0306":{text:"\\u",math:"\\breve"},"\u030c":{text:"\\v",math:"\\check"},"\u0302":{text:"\\^",math:"\\hat"},"\u0307":{text:"\\.",math:"\\dot"},"\u030a":{text:"\\r",math:"\\mathring"},"\u030b":{text:"\\H"},"\u0327":{text:"\\c"}},Pn={"\xe1":"a\u0301","\xe0":"a\u0300","\xe4":"a\u0308","\u01df":"a\u0308\u0304","\xe3":"a\u0303","\u0101":"a\u0304","\u0103":"a\u0306","\u1eaf":"a\u0306\u0301","\u1eb1":"a\u0306\u0300","\u1eb5":"a\u0306\u0303","\u01ce":"a\u030c","\xe2":"a\u0302","\u1ea5":"a\u0302\u0301","\u1ea7":"a\u0302\u0300","\u1eab":"a\u0302\u0303","\u0227":"a\u0307","\u01e1":"a\u0307\u0304","\xe5":"a\u030a","\u01fb":"a\u030a\u0301","\u1e03":"b\u0307","\u0107":"c\u0301","\u1e09":"c\u0327\u0301","\u010d":"c\u030c","\u0109":"c\u0302","\u010b":"c\u0307","\xe7":"c\u0327","\u010f":"d\u030c","\u1e0b":"d\u0307","\u1e11":"d\u0327","\xe9":"e\u0301","\xe8":"e\u0300","\xeb":"e\u0308","\u1ebd":"e\u0303","\u0113":"e\u0304","\u1e17":"e\u0304\u0301","\u1e15":"e\u0304\u0300","\u0115":"e\u0306","\u1e1d":"e\u0327\u0306","\u011b":"e\u030c","\xea":"e\u0302","\u1ebf":"e\u0302\u0301","\u1ec1":"e\u0302\u0300","\u1ec5":"e\u0302\u0303","\u0117":"e\u0307","\u0229":"e\u0327","\u1e1f":"f\u0307","\u01f5":"g\u0301","\u1e21":"g\u0304","\u011f":"g\u0306","\u01e7":"g\u030c","\u011d":"g\u0302","\u0121":"g\u0307","\u0123":"g\u0327","\u1e27":"h\u0308","\u021f":"h\u030c","\u0125":"h\u0302","\u1e23":"h\u0307","\u1e29":"h\u0327","\xed":"i\u0301","\xec":"i\u0300","\xef":"i\u0308","\u1e2f":"i\u0308\u0301","\u0129":"i\u0303","\u012b":"i\u0304","\u012d":"i\u0306","\u01d0":"i\u030c","\xee":"i\u0302","\u01f0":"j\u030c","\u0135":"j\u0302","\u1e31":"k\u0301","\u01e9":"k\u030c","\u0137":"k\u0327","\u013a":"l\u0301","\u013e":"l\u030c","\u013c":"l\u0327","\u1e3f":"m\u0301","\u1e41":"m\u0307","\u0144":"n\u0301","\u01f9":"n\u0300","\xf1":"n\u0303","\u0148":"n\u030c","\u1e45":"n\u0307","\u0146":"n\u0327","\xf3":"o\u0301","\xf2":"o\u0300","\xf6":"o\u0308","\u022b":"o\u0308\u0304","\xf5":"o\u0303","\u1e4d":"o\u0303\u0301","\u1e4f":"o\u0303\u0308","\u022d":"o\u0303\u0304","\u014d":"o\u0304","\u1e53":"o\u0304\u0301","\u1e51":"o\u0304\u0300","\u014f":"o\u0306","\u01d2":"o\u030c","\xf4":"o\u0302","\u1ed1":"o\u0302\u0301","\u1ed3":"o\u0302\u0300","\u1ed7":"o\u0302\u0303","\u022f":"o\u0307","\u0231":"o\u0307\u0304","\u0151":"o\u030b","\u1e55":"p\u0301","\u1e57":"p\u0307","\u0155":"r\u0301","\u0159":"r\u030c","\u1e59":"r\u0307","\u0157":"r\u0327","\u015b":"s\u0301","\u1e65":"s\u0301\u0307","\u0161":"s\u030c","\u1e67":"s\u030c\u0307","\u015d":"s\u0302","\u1e61":"s\u0307","\u015f":"s\u0327","\u1e97":"t\u0308","\u0165":"t\u030c","\u1e6b":"t\u0307","\u0163":"t\u0327","\xfa":"u\u0301","\xf9":"u\u0300","\xfc":"u\u0308","\u01d8":"u\u0308\u0301","\u01dc":"u\u0308\u0300","\u01d6":"u\u0308\u0304","\u01da":"u\u0308\u030c","\u0169":"u\u0303","\u1e79":"u\u0303\u0301","\u016b":"u\u0304","\u1e7b":"u\u0304\u0308","\u016d":"u\u0306","\u01d4":"u\u030c","\xfb":"u\u0302","\u016f":"u\u030a","\u0171":"u\u030b","\u1e7d":"v\u0303","\u1e83":"w\u0301","\u1e81":"w\u0300","\u1e85":"w\u0308","\u0175":"w\u0302","\u1e87":"w\u0307","\u1e98":"w\u030a","\u1e8d":"x\u0308","\u1e8b":"x\u0307","\xfd":"y\u0301","\u1ef3":"y\u0300","\xff":"y\u0308","\u1ef9":"y\u0303","\u0233":"y\u0304","\u0177":"y\u0302","\u1e8f":"y\u0307","\u1e99":"y\u030a","\u017a":"z\u0301","\u017e":"z\u030c","\u1e91":"z\u0302","\u017c":"z\u0307","\xc1":"A\u0301","\xc0":"A\u0300","\xc4":"A\u0308","\u01de":"A\u0308\u0304","\xc3":"A\u0303","\u0100":"A\u0304","\u0102":"A\u0306","\u1eae":"A\u0306\u0301","\u1eb0":"A\u0306\u0300","\u1eb4":"A\u0306\u0303","\u01cd":"A\u030c","\xc2":"A\u0302","\u1ea4":"A\u0302\u0301","\u1ea6":"A\u0302\u0300","\u1eaa":"A\u0302\u0303","\u0226":"A\u0307","\u01e0":"A\u0307\u0304","\xc5":"A\u030a","\u01fa":"A\u030a\u0301","\u1e02":"B\u0307","\u0106":"C\u0301","\u1e08":"C\u0327\u0301","\u010c":"C\u030c","\u0108":"C\u0302","\u010a":"C\u0307","\xc7":"C\u0327","\u010e":"D\u030c","\u1e0a":"D\u0307","\u1e10":"D\u0327","\xc9":"E\u0301","\xc8":"E\u0300","\xcb":"E\u0308","\u1ebc":"E\u0303","\u0112":"E\u0304","\u1e16":"E\u0304\u0301","\u1e14":"E\u0304\u0300","\u0114":"E\u0306","\u1e1c":"E\u0327\u0306","\u011a":"E\u030c","\xca":"E\u0302","\u1ebe":"E\u0302\u0301","\u1ec0":"E\u0302\u0300","\u1ec4":"E\u0302\u0303","\u0116":"E\u0307","\u0228":"E\u0327","\u1e1e":"F\u0307","\u01f4":"G\u0301","\u1e20":"G\u0304","\u011e":"G\u0306","\u01e6":"G\u030c","\u011c":"G\u0302","\u0120":"G\u0307","\u0122":"G\u0327","\u1e26":"H\u0308","\u021e":"H\u030c","\u0124":"H\u0302","\u1e22":"H\u0307","\u1e28":"H\u0327","\xcd":"I\u0301","\xcc":"I\u0300","\xcf":"I\u0308","\u1e2e":"I\u0308\u0301","\u0128":"I\u0303","\u012a":"I\u0304","\u012c":"I\u0306","\u01cf":"I\u030c","\xce":"I\u0302","\u0130":"I\u0307","\u0134":"J\u0302","\u1e30":"K\u0301","\u01e8":"K\u030c","\u0136":"K\u0327","\u0139":"L\u0301","\u013d":"L\u030c","\u013b":"L\u0327","\u1e3e":"M\u0301","\u1e40":"M\u0307","\u0143":"N\u0301","\u01f8":"N\u0300","\xd1":"N\u0303","\u0147":"N\u030c","\u1e44":"N\u0307","\u0145":"N\u0327","\xd3":"O\u0301","\xd2":"O\u0300","\xd6":"O\u0308","\u022a":"O\u0308\u0304","\xd5":"O\u0303","\u1e4c":"O\u0303\u0301","\u1e4e":"O\u0303\u0308","\u022c":"O\u0303\u0304","\u014c":"O\u0304","\u1e52":"O\u0304\u0301","\u1e50":"O\u0304\u0300","\u014e":"O\u0306","\u01d1":"O\u030c","\xd4":"O\u0302","\u1ed0":"O\u0302\u0301","\u1ed2":"O\u0302\u0300","\u1ed6":"O\u0302\u0303","\u022e":"O\u0307","\u0230":"O\u0307\u0304","\u0150":"O\u030b","\u1e54":"P\u0301","\u1e56":"P\u0307","\u0154":"R\u0301","\u0158":"R\u030c","\u1e58":"R\u0307","\u0156":"R\u0327","\u015a":"S\u0301","\u1e64":"S\u0301\u0307","\u0160":"S\u030c","\u1e66":"S\u030c\u0307","\u015c":"S\u0302","\u1e60":"S\u0307","\u015e":"S\u0327","\u0164":"T\u030c","\u1e6a":"T\u0307","\u0162":"T\u0327","\xda":"U\u0301","\xd9":"U\u0300","\xdc":"U\u0308","\u01d7":"U\u0308\u0301","\u01db":"U\u0308\u0300","\u01d5":"U\u0308\u0304","\u01d9":"U\u0308\u030c","\u0168":"U\u0303","\u1e78":"U\u0303\u0301","\u016a":"U\u0304","\u1e7a":"U\u0304\u0308","\u016c":"U\u0306","\u01d3":"U\u030c","\xdb":"U\u0302","\u016e":"U\u030a","\u0170":"U\u030b","\u1e7c":"V\u0303","\u1e82":"W\u0301","\u1e80":"W\u0300","\u1e84":"W\u0308","\u0174":"W\u0302","\u1e86":"W\u0307","\u1e8c":"X\u0308","\u1e8a":"X\u0307","\xdd":"Y\u0301","\u1ef2":"Y\u0300","\u0178":"Y\u0308","\u1ef8":"Y\u0303","\u0232":"Y\u0304","\u0176":"Y\u0302","\u1e8e":"Y\u0307","\u0179":"Z\u0301","\u017d":"Z\u030c","\u1e90":"Z\u0302","\u017b":"Z\u0307","\u03ac":"\u03b1\u0301","\u1f70":"\u03b1\u0300","\u1fb1":"\u03b1\u0304","\u1fb0":"\u03b1\u0306","\u03ad":"\u03b5\u0301","\u1f72":"\u03b5\u0300","\u03ae":"\u03b7\u0301","\u1f74":"\u03b7\u0300","\u03af":"\u03b9\u0301","\u1f76":"\u03b9\u0300","\u03ca":"\u03b9\u0308","\u0390":"\u03b9\u0308\u0301","\u1fd2":"\u03b9\u0308\u0300","\u1fd1":"\u03b9\u0304","\u1fd0":"\u03b9\u0306","\u03cc":"\u03bf\u0301","\u1f78":"\u03bf\u0300","\u03cd":"\u03c5\u0301","\u1f7a":"\u03c5\u0300","\u03cb":"\u03c5\u0308","\u03b0":"\u03c5\u0308\u0301","\u1fe2":"\u03c5\u0308\u0300","\u1fe1":"\u03c5\u0304","\u1fe0":"\u03c5\u0306","\u03ce":"\u03c9\u0301","\u1f7c":"\u03c9\u0300","\u038e":"\u03a5\u0301","\u1fea":"\u03a5\u0300","\u03ab":"\u03a5\u0308","\u1fe9":"\u03a5\u0304","\u1fe8":"\u03a5\u0306","\u038f":"\u03a9\u0301","\u1ffa":"\u03a9\u0300"};class Fn{constructor(e,t){this.mode=void 0,this.gullet=void 0,this.settings=void 0,this.leftrightDepth=void 0,this.nextToken=void 0,this.mode="math",this.gullet=new En(e,t,this.mode),this.settings=t,this.leftrightDepth=0}expect(e,t){if(void 0===t&&(t=!0),this.fetch().text!==e)throw new n("Expected '"+e+"', got '"+this.fetch().text+"'",this.fetch());t&&this.consume()}consume(){this.nextToken=null}fetch(){return null==this.nextToken&&(this.nextToken=this.gullet.expandNextToken()),this.nextToken}switchMode(e){this.mode=e,this.gullet.switchMode(e)}parse(){this.settings.globalGroup||this.gullet.beginGroup(),this.settings.colorIsTextColor&&this.gullet.macros.set("\\color","\\textcolor");try{const e=this.parseExpression(!1);return this.expect("EOF"),this.settings.globalGroup||this.gullet.endGroup(),e}finally{this.gullet.endGroups()}}subparse(e){const t=this.nextToken;this.consume(),this.gullet.pushToken(new Ir("}")),this.gullet.pushTokens(e);const r=this.parseExpression(!1);return this.expect("}"),this.nextToken=t,r}parseExpression(e,t){const r=[];for(;;){"math"===this.mode&&this.consumeSpaces();const n=this.fetch();if(-1!==Fn.endOfExpression.indexOf(n.text))break;if(t&&n.text===t)break;if(e&&wn[n.text]&&wn[n.text].infix)break;const o=this.parseAtom(t);if(!o)break;"internal"!==o.type&&r.push(o)}return"text"===this.mode&&this.formLigatures(r),this.handleInfixNodes(r)}handleInfixNodes(e){let t,r=-1;for(let o=0;o=0&&this.settings.reportNonstrict("unicodeTextInMathMode",'Latin-1/Unicode text character "'+t[0]+'" used in math mode',e);const r=se[this.mode][t].group,n=qr.range(e);let s;if(re.hasOwnProperty(r)){const e=r;s={type:"atom",mode:this.mode,family:e,loc:n,text:t}}else s={type:r,mode:this.mode,loc:n,text:t};o=s}else{if(!(t.charCodeAt(0)>=128))return null;this.settings.strict&&(S(t.charCodeAt(0))?"math"===this.mode&&this.settings.reportNonstrict("unicodeTextInMathMode",'Unicode text character "'+t[0]+'" used in math mode',e):this.settings.reportNonstrict("unknownSymbol",'Unrecognized Unicode character "'+t[0]+'" ('+t.charCodeAt(0)+")",e)),o={type:"textord",mode:"text",loc:qr.range(e),text:t}}if(this.consume(),r)for(let t=0;t 15) { + left = "…" + input.slice(start - 15, start); + } else { + left = input.slice(0, start); + } + + var right; + + if (end + 15 < input.length) { + right = input.slice(end, end + 15) + "…"; + } else { + right = input.slice(end); + } + + error += left + underlined + right; + } // Some hackery to make ParseError a prototype of Error + // See http://stackoverflow.com/a/8460753 + // $FlowFixMe + + + var self = new Error(error); + self.name = "ParseError"; // $FlowFixMe + + self.__proto__ = ParseError.prototype; + self.position = start; + + if (start != null && end != null) { + self.length = end - start; + } + + self.rawMessage = message; + return self; + } + +} // $FlowFixMe More hackery + + +ParseError.prototype.__proto__ = Error.prototype; + +/** + * This file contains a list of utility functions which are useful in other + * files. + */ + +/** + * Return whether an element is contained in a list + */ +var contains = function contains(list, elem) { + return list.indexOf(elem) !== -1; +}; +/** + * Provide a default value if a setting is undefined + * NOTE: Couldn't use `T` as the output type due to facebook/flow#5022. + */ + + +var deflt = function deflt(setting, defaultIfUndefined) { + return setting === undefined ? defaultIfUndefined : setting; +}; // hyphenate and escape adapted from Facebook's React under Apache 2 license + + +var uppercase = /([A-Z])/g; + +var hyphenate = function hyphenate(str) { + return str.replace(uppercase, "-$1").toLowerCase(); +}; + +var ESCAPE_LOOKUP = { + "&": "&", + ">": ">", + "<": "<", + "\"": """, + "'": "'" +}; +var ESCAPE_REGEX = /[&><"']/g; +/** + * Escapes text to prevent scripting attacks. + */ + +function escape(text) { + return String(text).replace(ESCAPE_REGEX, match => ESCAPE_LOOKUP[match]); +} +/** + * Sometimes we want to pull out the innermost element of a group. In most + * cases, this will just be the group itself, but when ordgroups and colors have + * a single element, we want to pull that out. + */ + + +var getBaseElem = function getBaseElem(group) { + if (group.type === "ordgroup") { + if (group.body.length === 1) { + return getBaseElem(group.body[0]); + } else { + return group; + } + } else if (group.type === "color") { + if (group.body.length === 1) { + return getBaseElem(group.body[0]); + } else { + return group; + } + } else if (group.type === "font") { + return getBaseElem(group.body); + } else { + return group; + } +}; +/** + * TeXbook algorithms often reference "character boxes", which are simply groups + * with a single character in them. To decide if something is a character box, + * we find its innermost group, and see if it is a single character. + */ + + +var isCharacterBox = function isCharacterBox(group) { + var baseElem = getBaseElem(group); // These are all they types of groups which hold single characters + + return baseElem.type === "mathord" || baseElem.type === "textord" || baseElem.type === "atom"; +}; + +var assert = function assert(value) { + if (!value) { + throw new Error('Expected non-null, but got ' + String(value)); + } + + return value; +}; +/** + * Return the protocol of a URL, or "_relative" if the URL does not specify a + * protocol (and thus is relative), or `null` if URL has invalid protocol + * (so should be outright rejected). + */ + +var protocolFromUrl = function protocolFromUrl(url) { + // Check for possible leading protocol. + // https://url.spec.whatwg.org/#url-parsing strips leading whitespace + // (U+20) or C0 control (U+00-U+1F) characters. + // eslint-disable-next-line no-control-regex + var protocol = /^[\x00-\x20]*([^\\/#?]*?)(:|�*58|�*3a|&colon)/i.exec(url); + + if (!protocol) { + return "_relative"; + } // Reject weird colons + + + if (protocol[2] !== ":") { + return null; + } // Reject invalid characters in scheme according to + // https://datatracker.ietf.org/doc/html/rfc3986#section-3.1 + + + if (!/^[a-zA-Z][a-zA-Z0-9+\-.]*$/.test(protocol[1])) { + return null; + } // Lowercase the protocol + + + return protocol[1].toLowerCase(); +}; +var utils = { + contains, + deflt, + escape, + hyphenate, + getBaseElem, + isCharacterBox, + protocolFromUrl +}; + +/* eslint no-console:0 */ +// TODO: automatically generate documentation +// TODO: check all properties on Settings exist +// TODO: check the type of a property on Settings matches +var SETTINGS_SCHEMA = { + displayMode: { + type: "boolean", + description: "Render math in display mode, which puts the math in " + "display style (so \\int and \\sum are large, for example), and " + "centers the math on the page on its own line.", + cli: "-d, --display-mode" + }, + output: { + type: { + enum: ["htmlAndMathml", "html", "mathml"] + }, + description: "Determines the markup language of the output.", + cli: "-F, --format " + }, + leqno: { + type: "boolean", + description: "Render display math in leqno style (left-justified tags)." + }, + fleqn: { + type: "boolean", + description: "Render display math flush left." + }, + throwOnError: { + type: "boolean", + default: true, + cli: "-t, --no-throw-on-error", + cliDescription: "Render errors (in the color given by --error-color) ins" + "tead of throwing a ParseError exception when encountering an error." + }, + errorColor: { + type: "string", + default: "#cc0000", + cli: "-c, --error-color ", + cliDescription: "A color string given in the format 'rgb' or 'rrggbb' " + "(no #). This option determines the color of errors rendered by the " + "-t option.", + cliProcessor: color => "#" + color + }, + macros: { + type: "object", + cli: "-m, --macro ", + cliDescription: "Define custom macro of the form '\\foo:expansion' (use " + "multiple -m arguments for multiple macros).", + cliDefault: [], + cliProcessor: (def, defs) => { + defs.push(def); + return defs; + } + }, + minRuleThickness: { + type: "number", + description: "Specifies a minimum thickness, in ems, for fraction lines," + " `\\sqrt` top lines, `{array}` vertical lines, `\\hline`, " + "`\\hdashline`, `\\underline`, `\\overline`, and the borders of " + "`\\fbox`, `\\boxed`, and `\\fcolorbox`.", + processor: t => Math.max(0, t), + cli: "--min-rule-thickness ", + cliProcessor: parseFloat + }, + colorIsTextColor: { + type: "boolean", + description: "Makes \\color behave like LaTeX's 2-argument \\textcolor, " + "instead of LaTeX's one-argument \\color mode change.", + cli: "-b, --color-is-text-color" + }, + strict: { + type: [{ + enum: ["warn", "ignore", "error"] + }, "boolean", "function"], + description: "Turn on strict / LaTeX faithfulness mode, which throws an " + "error if the input uses features that are not supported by LaTeX.", + cli: "-S, --strict", + cliDefault: false + }, + trust: { + type: ["boolean", "function"], + description: "Trust the input, enabling all HTML features such as \\url.", + cli: "-T, --trust" + }, + maxSize: { + type: "number", + default: Infinity, + description: "If non-zero, all user-specified sizes, e.g. in " + "\\rule{500em}{500em}, will be capped to maxSize ems. Otherwise, " + "elements and spaces can be arbitrarily large", + processor: s => Math.max(0, s), + cli: "-s, --max-size ", + cliProcessor: parseInt + }, + maxExpand: { + type: "number", + default: 1000, + description: "Limit the number of macro expansions to the specified " + "number, to prevent e.g. infinite macro loops. If set to Infinity, " + "the macro expander will try to fully expand as in LaTeX.", + processor: n => Math.max(0, n), + cli: "-e, --max-expand ", + cliProcessor: n => n === "Infinity" ? Infinity : parseInt(n) + }, + globalGroup: { + type: "boolean", + cli: false + } +}; + +function getDefaultValue(schema) { + if (schema.default) { + return schema.default; + } + + var type = schema.type; + var defaultType = Array.isArray(type) ? type[0] : type; + + if (typeof defaultType !== 'string') { + return defaultType.enum[0]; + } + + switch (defaultType) { + case 'boolean': + return false; + + case 'string': + return ''; + + case 'number': + return 0; + + case 'object': + return {}; + } +} +/** + * The main Settings object + * + * The current options stored are: + * - displayMode: Whether the expression should be typeset as inline math + * (false, the default), meaning that the math starts in + * \textstyle and is placed in an inline-block); or as display + * math (true), meaning that the math starts in \displaystyle + * and is placed in a block with vertical margin. + */ + + +class Settings { + constructor(options) { + this.displayMode = void 0; + this.output = void 0; + this.leqno = void 0; + this.fleqn = void 0; + this.throwOnError = void 0; + this.errorColor = void 0; + this.macros = void 0; + this.minRuleThickness = void 0; + this.colorIsTextColor = void 0; + this.strict = void 0; + this.trust = void 0; + this.maxSize = void 0; + this.maxExpand = void 0; + this.globalGroup = void 0; + // allow null options + options = options || {}; + + for (var prop in SETTINGS_SCHEMA) { + if (SETTINGS_SCHEMA.hasOwnProperty(prop)) { + // $FlowFixMe + var schema = SETTINGS_SCHEMA[prop]; // TODO: validate options + // $FlowFixMe + + this[prop] = options[prop] !== undefined ? schema.processor ? schema.processor(options[prop]) : options[prop] : getDefaultValue(schema); + } + } + } + /** + * Report nonstrict (non-LaTeX-compatible) input. + * Can safely not be called if `this.strict` is false in JavaScript. + */ + + + reportNonstrict(errorCode, errorMsg, token) { + var strict = this.strict; + + if (typeof strict === "function") { + // Allow return value of strict function to be boolean or string + // (or null/undefined, meaning no further processing). + strict = strict(errorCode, errorMsg, token); + } + + if (!strict || strict === "ignore") { + return; + } else if (strict === true || strict === "error") { + throw new ParseError("LaTeX-incompatible input and strict mode is set to 'error': " + (errorMsg + " [" + errorCode + "]"), token); + } else if (strict === "warn") { + typeof console !== "undefined" && console.warn("LaTeX-incompatible input and strict mode is set to 'warn': " + (errorMsg + " [" + errorCode + "]")); + } else { + // won't happen in type-safe code + typeof console !== "undefined" && console.warn("LaTeX-incompatible input and strict mode is set to " + ("unrecognized '" + strict + "': " + errorMsg + " [" + errorCode + "]")); + } + } + /** + * Check whether to apply strict (LaTeX-adhering) behavior for unusual + * input (like `\\`). Unlike `nonstrict`, will not throw an error; + * instead, "error" translates to a return value of `true`, while "ignore" + * translates to a return value of `false`. May still print a warning: + * "warn" prints a warning and returns `false`. + * This is for the second category of `errorCode`s listed in the README. + */ + + + useStrictBehavior(errorCode, errorMsg, token) { + var strict = this.strict; + + if (typeof strict === "function") { + // Allow return value of strict function to be boolean or string + // (or null/undefined, meaning no further processing). + // But catch any exceptions thrown by function, treating them + // like "error". + try { + strict = strict(errorCode, errorMsg, token); + } catch (error) { + strict = "error"; + } + } + + if (!strict || strict === "ignore") { + return false; + } else if (strict === true || strict === "error") { + return true; + } else if (strict === "warn") { + typeof console !== "undefined" && console.warn("LaTeX-incompatible input and strict mode is set to 'warn': " + (errorMsg + " [" + errorCode + "]")); + return false; + } else { + // won't happen in type-safe code + typeof console !== "undefined" && console.warn("LaTeX-incompatible input and strict mode is set to " + ("unrecognized '" + strict + "': " + errorMsg + " [" + errorCode + "]")); + return false; + } + } + /** + * Check whether to test potentially dangerous input, and return + * `true` (trusted) or `false` (untrusted). The sole argument `context` + * should be an object with `command` field specifying the relevant LaTeX + * command (as a string starting with `\`), and any other arguments, etc. + * If `context` has a `url` field, a `protocol` field will automatically + * get added by this function (changing the specified object). + */ + + + isTrusted(context) { + if (context.url && !context.protocol) { + var protocol = utils.protocolFromUrl(context.url); + + if (protocol == null) { + return false; + } + + context.protocol = protocol; + } + + var trust = typeof this.trust === "function" ? this.trust(context) : this.trust; + return Boolean(trust); + } + +} + +/** + * This file contains information and classes for the various kinds of styles + * used in TeX. It provides a generic `Style` class, which holds information + * about a specific style. It then provides instances of all the different kinds + * of styles possible, and provides functions to move between them and get + * information about them. + */ + +/** + * The main style class. Contains a unique id for the style, a size (which is + * the same for cramped and uncramped version of a style), and a cramped flag. + */ +class Style { + constructor(id, size, cramped) { + this.id = void 0; + this.size = void 0; + this.cramped = void 0; + this.id = id; + this.size = size; + this.cramped = cramped; + } + /** + * Get the style of a superscript given a base in the current style. + */ + + + sup() { + return styles[sup[this.id]]; + } + /** + * Get the style of a subscript given a base in the current style. + */ + + + sub() { + return styles[sub[this.id]]; + } + /** + * Get the style of a fraction numerator given the fraction in the current + * style. + */ + + + fracNum() { + return styles[fracNum[this.id]]; + } + /** + * Get the style of a fraction denominator given the fraction in the current + * style. + */ + + + fracDen() { + return styles[fracDen[this.id]]; + } + /** + * Get the cramped version of a style (in particular, cramping a cramped style + * doesn't change the style). + */ + + + cramp() { + return styles[cramp[this.id]]; + } + /** + * Get a text or display version of this style. + */ + + + text() { + return styles[text$1[this.id]]; + } + /** + * Return true if this style is tightly spaced (scriptstyle/scriptscriptstyle) + */ + + + isTight() { + return this.size >= 2; + } + +} // Export an interface for type checking, but don't expose the implementation. +// This way, no more styles can be generated. + + +// IDs of the different styles +var D = 0; +var Dc = 1; +var T = 2; +var Tc = 3; +var S = 4; +var Sc = 5; +var SS = 6; +var SSc = 7; // Instances of the different styles + +var styles = [new Style(D, 0, false), new Style(Dc, 0, true), new Style(T, 1, false), new Style(Tc, 1, true), new Style(S, 2, false), new Style(Sc, 2, true), new Style(SS, 3, false), new Style(SSc, 3, true)]; // Lookup tables for switching from one style to another + +var sup = [S, Sc, S, Sc, SS, SSc, SS, SSc]; +var sub = [Sc, Sc, Sc, Sc, SSc, SSc, SSc, SSc]; +var fracNum = [T, Tc, S, Sc, SS, SSc, SS, SSc]; +var fracDen = [Tc, Tc, Sc, Sc, SSc, SSc, SSc, SSc]; +var cramp = [Dc, Dc, Tc, Tc, Sc, Sc, SSc, SSc]; +var text$1 = [D, Dc, T, Tc, T, Tc, T, Tc]; // We only export some of the styles. + +var Style$1 = { + DISPLAY: styles[D], + TEXT: styles[T], + SCRIPT: styles[S], + SCRIPTSCRIPT: styles[SS] +}; + +/* + * This file defines the Unicode scripts and script families that we + * support. To add new scripts or families, just add a new entry to the + * scriptData array below. Adding scripts to the scriptData array allows + * characters from that script to appear in \text{} environments. + */ + +/** + * Each script or script family has a name and an array of blocks. + * Each block is an array of two numbers which specify the start and + * end points (inclusive) of a block of Unicode codepoints. + */ + +/** + * Unicode block data for the families of scripts we support in \text{}. + * Scripts only need to appear here if they do not have font metrics. + */ +var scriptData = [{ + // Latin characters beyond the Latin-1 characters we have metrics for. + // Needed for Czech, Hungarian and Turkish text, for example. + name: 'latin', + blocks: [[0x0100, 0x024f], // Latin Extended-A and Latin Extended-B + [0x0300, 0x036f] // Combining Diacritical marks + ] +}, { + // The Cyrillic script used by Russian and related languages. + // A Cyrillic subset used to be supported as explicitly defined + // symbols in symbols.js + name: 'cyrillic', + blocks: [[0x0400, 0x04ff]] +}, { + // Armenian + name: 'armenian', + blocks: [[0x0530, 0x058F]] +}, { + // The Brahmic scripts of South and Southeast Asia + // Devanagari (0900–097F) + // Bengali (0980–09FF) + // Gurmukhi (0A00–0A7F) + // Gujarati (0A80–0AFF) + // Oriya (0B00–0B7F) + // Tamil (0B80–0BFF) + // Telugu (0C00–0C7F) + // Kannada (0C80–0CFF) + // Malayalam (0D00–0D7F) + // Sinhala (0D80–0DFF) + // Thai (0E00–0E7F) + // Lao (0E80–0EFF) + // Tibetan (0F00–0FFF) + // Myanmar (1000–109F) + name: 'brahmic', + blocks: [[0x0900, 0x109F]] +}, { + name: 'georgian', + blocks: [[0x10A0, 0x10ff]] +}, { + // Chinese and Japanese. + // The "k" in cjk is for Korean, but we've separated Korean out + name: "cjk", + blocks: [[0x3000, 0x30FF], // CJK symbols and punctuation, Hiragana, Katakana + [0x4E00, 0x9FAF], // CJK ideograms + [0xFF00, 0xFF60] // Fullwidth punctuation + // TODO: add halfwidth Katakana and Romanji glyphs + ] +}, { + // Korean + name: 'hangul', + blocks: [[0xAC00, 0xD7AF]] +}]; +/** + * Given a codepoint, return the name of the script or script family + * it is from, or null if it is not part of a known block + */ + +function scriptFromCodepoint(codepoint) { + for (var i = 0; i < scriptData.length; i++) { + var script = scriptData[i]; + + for (var _i = 0; _i < script.blocks.length; _i++) { + var block = script.blocks[_i]; + + if (codepoint >= block[0] && codepoint <= block[1]) { + return script.name; + } + } + } + + return null; +} +/** + * A flattened version of all the supported blocks in a single array. + * This is an optimization to make supportedCodepoint() fast. + */ + +var allBlocks = []; +scriptData.forEach(s => s.blocks.forEach(b => allBlocks.push(...b))); +/** + * Given a codepoint, return true if it falls within one of the + * scripts or script families defined above and false otherwise. + * + * Micro benchmarks shows that this is faster than + * /[\u3000-\u30FF\u4E00-\u9FAF\uFF00-\uFF60\uAC00-\uD7AF\u0900-\u109F]/.test() + * in Firefox, Chrome and Node. + */ + +function supportedCodepoint(codepoint) { + for (var i = 0; i < allBlocks.length; i += 2) { + if (codepoint >= allBlocks[i] && codepoint <= allBlocks[i + 1]) { + return true; + } + } + + return false; +} + +/** + * This file provides support to domTree.js and delimiter.js. + * It's a storehouse of path geometry for SVG images. + */ +// In all paths below, the viewBox-to-em scale is 1000:1. +var hLinePad = 80; // padding above a sqrt vinculum. Prevents image cropping. +// The vinculum of a \sqrt can be made thicker by a KaTeX rendering option. +// Think of variable extraVinculum as two detours in the SVG path. +// The detour begins at the lower left of the area labeled extraVinculum below. +// The detour proceeds one extraVinculum distance up and slightly to the right, +// displacing the radiused corner between surd and vinculum. The radius is +// traversed as usual, then the detour resumes. It goes right, to the end of +// the very long vinculum, then down one extraVinculum distance, +// after which it resumes regular path geometry for the radical. + +/* vinculum + / + /▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒←extraVinculum + / █████████████████████←0.04em (40 unit) std vinculum thickness + / / + / / + / /\ + / / surd +*/ + +var sqrtMain = function sqrtMain(extraVinculum, hLinePad) { + // sqrtMain path geometry is from glyph U221A in the font KaTeX Main + return "M95," + (622 + extraVinculum + hLinePad) + "\nc-2.7,0,-7.17,-2.7,-13.5,-8c-5.8,-5.3,-9.5,-10,-9.5,-14\nc0,-2,0.3,-3.3,1,-4c1.3,-2.7,23.83,-20.7,67.5,-54\nc44.2,-33.3,65.8,-50.3,66.5,-51c1.3,-1.3,3,-2,5,-2c4.7,0,8.7,3.3,12,10\ns173,378,173,378c0.7,0,35.3,-71,104,-213c68.7,-142,137.5,-285,206.5,-429\nc69,-144,104.5,-217.7,106.5,-221\nl" + extraVinculum / 2.075 + " -" + extraVinculum + "\nc5.3,-9.3,12,-14,20,-14\nH400000v" + (40 + extraVinculum) + "H845.2724\ns-225.272,467,-225.272,467s-235,486,-235,486c-2.7,4.7,-9,7,-19,7\nc-6,0,-10,-1,-12,-3s-194,-422,-194,-422s-65,47,-65,47z\nM" + (834 + extraVinculum) + " " + hLinePad + "h400000v" + (40 + extraVinculum) + "h-400000z"; +}; + +var sqrtSize1 = function sqrtSize1(extraVinculum, hLinePad) { + // size1 is from glyph U221A in the font KaTeX_Size1-Regular + return "M263," + (601 + extraVinculum + hLinePad) + "c0.7,0,18,39.7,52,119\nc34,79.3,68.167,158.7,102.5,238c34.3,79.3,51.8,119.3,52.5,120\nc340,-704.7,510.7,-1060.3,512,-1067\nl" + extraVinculum / 2.084 + " -" + extraVinculum + "\nc4.7,-7.3,11,-11,19,-11\nH40000v" + (40 + extraVinculum) + "H1012.3\ns-271.3,567,-271.3,567c-38.7,80.7,-84,175,-136,283c-52,108,-89.167,185.3,-111.5,232\nc-22.3,46.7,-33.8,70.3,-34.5,71c-4.7,4.7,-12.3,7,-23,7s-12,-1,-12,-1\ns-109,-253,-109,-253c-72.7,-168,-109.3,-252,-110,-252c-10.7,8,-22,16.7,-34,26\nc-22,17.3,-33.3,26,-34,26s-26,-26,-26,-26s76,-59,76,-59s76,-60,76,-60z\nM" + (1001 + extraVinculum) + " " + hLinePad + "h400000v" + (40 + extraVinculum) + "h-400000z"; +}; + +var sqrtSize2 = function sqrtSize2(extraVinculum, hLinePad) { + // size2 is from glyph U221A in the font KaTeX_Size2-Regular + return "M983 " + (10 + extraVinculum + hLinePad) + "\nl" + extraVinculum / 3.13 + " -" + extraVinculum + "\nc4,-6.7,10,-10,18,-10 H400000v" + (40 + extraVinculum) + "\nH1013.1s-83.4,268,-264.1,840c-180.7,572,-277,876.3,-289,913c-4.7,4.7,-12.7,7,-24,7\ns-12,0,-12,0c-1.3,-3.3,-3.7,-11.7,-7,-25c-35.3,-125.3,-106.7,-373.3,-214,-744\nc-10,12,-21,25,-33,39s-32,39,-32,39c-6,-5.3,-15,-14,-27,-26s25,-30,25,-30\nc26.7,-32.7,52,-63,76,-91s52,-60,52,-60s208,722,208,722\nc56,-175.3,126.3,-397.3,211,-666c84.7,-268.7,153.8,-488.2,207.5,-658.5\nc53.7,-170.3,84.5,-266.8,92.5,-289.5z\nM" + (1001 + extraVinculum) + " " + hLinePad + "h400000v" + (40 + extraVinculum) + "h-400000z"; +}; + +var sqrtSize3 = function sqrtSize3(extraVinculum, hLinePad) { + // size3 is from glyph U221A in the font KaTeX_Size3-Regular + return "M424," + (2398 + extraVinculum + hLinePad) + "\nc-1.3,-0.7,-38.5,-172,-111.5,-514c-73,-342,-109.8,-513.3,-110.5,-514\nc0,-2,-10.7,14.3,-32,49c-4.7,7.3,-9.8,15.7,-15.5,25c-5.7,9.3,-9.8,16,-12.5,20\ns-5,7,-5,7c-4,-3.3,-8.3,-7.7,-13,-13s-13,-13,-13,-13s76,-122,76,-122s77,-121,77,-121\ns209,968,209,968c0,-2,84.7,-361.7,254,-1079c169.3,-717.3,254.7,-1077.7,256,-1081\nl" + extraVinculum / 4.223 + " -" + extraVinculum + "c4,-6.7,10,-10,18,-10 H400000\nv" + (40 + extraVinculum) + "H1014.6\ns-87.3,378.7,-272.6,1166c-185.3,787.3,-279.3,1182.3,-282,1185\nc-2,6,-10,9,-24,9\nc-8,0,-12,-0.7,-12,-2z M" + (1001 + extraVinculum) + " " + hLinePad + "\nh400000v" + (40 + extraVinculum) + "h-400000z"; +}; + +var sqrtSize4 = function sqrtSize4(extraVinculum, hLinePad) { + // size4 is from glyph U221A in the font KaTeX_Size4-Regular + return "M473," + (2713 + extraVinculum + hLinePad) + "\nc339.3,-1799.3,509.3,-2700,510,-2702 l" + extraVinculum / 5.298 + " -" + extraVinculum + "\nc3.3,-7.3,9.3,-11,18,-11 H400000v" + (40 + extraVinculum) + "H1017.7\ns-90.5,478,-276.2,1466c-185.7,988,-279.5,1483,-281.5,1485c-2,6,-10,9,-24,9\nc-8,0,-12,-0.7,-12,-2c0,-1.3,-5.3,-32,-16,-92c-50.7,-293.3,-119.7,-693.3,-207,-1200\nc0,-1.3,-5.3,8.7,-16,30c-10.7,21.3,-21.3,42.7,-32,64s-16,33,-16,33s-26,-26,-26,-26\ns76,-153,76,-153s77,-151,77,-151c0.7,0.7,35.7,202,105,604c67.3,400.7,102,602.7,104,\n606zM" + (1001 + extraVinculum) + " " + hLinePad + "h400000v" + (40 + extraVinculum) + "H1017.7z"; +}; + +var phasePath = function phasePath(y) { + var x = y / 2; // x coordinate at top of angle + + return "M400000 " + y + " H0 L" + x + " 0 l65 45 L145 " + (y - 80) + " H400000z"; +}; + +var sqrtTall = function sqrtTall(extraVinculum, hLinePad, viewBoxHeight) { + // sqrtTall is from glyph U23B7 in the font KaTeX_Size4-Regular + // One path edge has a variable length. It runs vertically from the vinculum + // to a point near (14 units) the bottom of the surd. The vinculum + // is normally 40 units thick. So the length of the line in question is: + var vertSegment = viewBoxHeight - 54 - hLinePad - extraVinculum; + return "M702 " + (extraVinculum + hLinePad) + "H400000" + (40 + extraVinculum) + "\nH742v" + vertSegment + "l-4 4-4 4c-.667.7 -2 1.5-4 2.5s-4.167 1.833-6.5 2.5-5.5 1-9.5 1\nh-12l-28-84c-16.667-52-96.667 -294.333-240-727l-212 -643 -85 170\nc-4-3.333-8.333-7.667-13 -13l-13-13l77-155 77-156c66 199.333 139 419.667\n219 661 l218 661zM702 " + hLinePad + "H400000v" + (40 + extraVinculum) + "H742z"; +}; + +var sqrtPath = function sqrtPath(size, extraVinculum, viewBoxHeight) { + extraVinculum = 1000 * extraVinculum; // Convert from document ems to viewBox. + + var path = ""; + + switch (size) { + case "sqrtMain": + path = sqrtMain(extraVinculum, hLinePad); + break; + + case "sqrtSize1": + path = sqrtSize1(extraVinculum, hLinePad); + break; + + case "sqrtSize2": + path = sqrtSize2(extraVinculum, hLinePad); + break; + + case "sqrtSize3": + path = sqrtSize3(extraVinculum, hLinePad); + break; + + case "sqrtSize4": + path = sqrtSize4(extraVinculum, hLinePad); + break; + + case "sqrtTall": + path = sqrtTall(extraVinculum, hLinePad, viewBoxHeight); + } + + return path; +}; +var innerPath = function innerPath(name, height) { + // The inner part of stretchy tall delimiters + switch (name) { + case "\u239c": + return "M291 0 H417 V" + height + " H291z M291 0 H417 V" + height + " H291z"; + + case "\u2223": + return "M145 0 H188 V" + height + " H145z M145 0 H188 V" + height + " H145z"; + + case "\u2225": + return "M145 0 H188 V" + height + " H145z M145 0 H188 V" + height + " H145z" + ("M367 0 H410 V" + height + " H367z M367 0 H410 V" + height + " H367z"); + + case "\u239f": + return "M457 0 H583 V" + height + " H457z M457 0 H583 V" + height + " H457z"; + + case "\u23a2": + return "M319 0 H403 V" + height + " H319z M319 0 H403 V" + height + " H319z"; + + case "\u23a5": + return "M263 0 H347 V" + height + " H263z M263 0 H347 V" + height + " H263z"; + + case "\u23aa": + return "M384 0 H504 V" + height + " H384z M384 0 H504 V" + height + " H384z"; + + case "\u23d0": + return "M312 0 H355 V" + height + " H312z M312 0 H355 V" + height + " H312z"; + + case "\u2016": + return "M257 0 H300 V" + height + " H257z M257 0 H300 V" + height + " H257z" + ("M478 0 H521 V" + height + " H478z M478 0 H521 V" + height + " H478z"); + + default: + return ""; + } +}; +var path = { + // The doubleleftarrow geometry is from glyph U+21D0 in the font KaTeX Main + doubleleftarrow: "M262 157\nl10-10c34-36 62.7-77 86-123 3.3-8 5-13.3 5-16 0-5.3-6.7-8-20-8-7.3\n 0-12.2.5-14.5 1.5-2.3 1-4.8 4.5-7.5 10.5-49.3 97.3-121.7 169.3-217 216-28\n 14-57.3 25-88 33-6.7 2-11 3.8-13 5.5-2 1.7-3 4.2-3 7.5s1 5.8 3 7.5\nc2 1.7 6.3 3.5 13 5.5 68 17.3 128.2 47.8 180.5 91.5 52.3 43.7 93.8 96.2 124.5\n 157.5 9.3 8 15.3 12.3 18 13h6c12-.7 18-4 18-10 0-2-1.7-7-5-15-23.3-46-52-87\n-86-123l-10-10h399738v-40H218c328 0 0 0 0 0l-10-8c-26.7-20-65.7-43-117-69 2.7\n-2 6-3.7 10-5 36.7-16 72.3-37.3 107-64l10-8h399782v-40z\nm8 0v40h399730v-40zm0 194v40h399730v-40z", + // doublerightarrow is from glyph U+21D2 in font KaTeX Main + doublerightarrow: "M399738 392l\n-10 10c-34 36-62.7 77-86 123-3.3 8-5 13.3-5 16 0 5.3 6.7 8 20 8 7.3 0 12.2-.5\n 14.5-1.5 2.3-1 4.8-4.5 7.5-10.5 49.3-97.3 121.7-169.3 217-216 28-14 57.3-25 88\n-33 6.7-2 11-3.8 13-5.5 2-1.7 3-4.2 3-7.5s-1-5.8-3-7.5c-2-1.7-6.3-3.5-13-5.5-68\n-17.3-128.2-47.8-180.5-91.5-52.3-43.7-93.8-96.2-124.5-157.5-9.3-8-15.3-12.3-18\n-13h-6c-12 .7-18 4-18 10 0 2 1.7 7 5 15 23.3 46 52 87 86 123l10 10H0v40h399782\nc-328 0 0 0 0 0l10 8c26.7 20 65.7 43 117 69-2.7 2-6 3.7-10 5-36.7 16-72.3 37.3\n-107 64l-10 8H0v40zM0 157v40h399730v-40zm0 194v40h399730v-40z", + // leftarrow is from glyph U+2190 in font KaTeX Main + leftarrow: "M400000 241H110l3-3c68.7-52.7 113.7-120\n 135-202 4-14.7 6-23 6-25 0-7.3-7-11-21-11-8 0-13.2.8-15.5 2.5-2.3 1.7-4.2 5.8\n-5.5 12.5-1.3 4.7-2.7 10.3-4 17-12 48.7-34.8 92-68.5 130S65.3 228.3 18 247\nc-10 4-16 7.7-18 11 0 8.7 6 14.3 18 17 47.3 18.7 87.8 47 121.5 85S196 441.3 208\n 490c.7 2 1.3 5 2 9s1.2 6.7 1.5 8c.3 1.3 1 3.3 2 6s2.2 4.5 3.5 5.5c1.3 1 3.3\n 1.8 6 2.5s6 1 10 1c14 0 21-3.7 21-11 0-2-2-10.3-6-25-20-79.3-65-146.7-135-202\n l-3-3h399890zM100 241v40h399900v-40z", + // overbrace is from glyphs U+23A9/23A8/23A7 in font KaTeX_Size4-Regular + leftbrace: "M6 548l-6-6v-35l6-11c56-104 135.3-181.3 238-232 57.3-28.7 117\n-45 179-50h399577v120H403c-43.3 7-81 15-113 26-100.7 33-179.7 91-237 174-2.7\n 5-6 9-10 13-.7 1-7.3 1-20 1H6z", + leftbraceunder: "M0 6l6-6h17c12.688 0 19.313.3 20 1 4 4 7.313 8.3 10 13\n 35.313 51.3 80.813 93.8 136.5 127.5 55.688 33.7 117.188 55.8 184.5 66.5.688\n 0 2 .3 4 1 18.688 2.7 76 4.3 172 5h399450v120H429l-6-1c-124.688-8-235-61.7\n-331-161C60.687 138.7 32.312 99.3 7 54L0 41V6z", + // overgroup is from the MnSymbol package (public domain) + leftgroup: "M400000 80\nH435C64 80 168.3 229.4 21 260c-5.9 1.2-18 0-18 0-2 0-3-1-3-3v-38C76 61 257 0\n 435 0h399565z", + leftgroupunder: "M400000 262\nH435C64 262 168.3 112.6 21 82c-5.9-1.2-18 0-18 0-2 0-3 1-3 3v38c76 158 257 219\n 435 219h399565z", + // Harpoons are from glyph U+21BD in font KaTeX Main + leftharpoon: "M0 267c.7 5.3 3 10 7 14h399993v-40H93c3.3\n-3.3 10.2-9.5 20.5-18.5s17.8-15.8 22.5-20.5c50.7-52 88-110.3 112-175 4-11.3 5\n-18.3 3-21-1.3-4-7.3-6-18-6-8 0-13 .7-15 2s-4.7 6.7-8 16c-42 98.7-107.3 174.7\n-196 228-6.7 4.7-10.7 8-12 10-1.3 2-2 5.7-2 11zm100-26v40h399900v-40z", + leftharpoonplus: "M0 267c.7 5.3 3 10 7 14h399993v-40H93c3.3-3.3 10.2-9.5\n 20.5-18.5s17.8-15.8 22.5-20.5c50.7-52 88-110.3 112-175 4-11.3 5-18.3 3-21-1.3\n-4-7.3-6-18-6-8 0-13 .7-15 2s-4.7 6.7-8 16c-42 98.7-107.3 174.7-196 228-6.7 4.7\n-10.7 8-12 10-1.3 2-2 5.7-2 11zm100-26v40h399900v-40zM0 435v40h400000v-40z\nm0 0v40h400000v-40z", + leftharpoondown: "M7 241c-4 4-6.333 8.667-7 14 0 5.333.667 9 2 11s5.333\n 5.333 12 10c90.667 54 156 130 196 228 3.333 10.667 6.333 16.333 9 17 2 .667 5\n 1 9 1h5c10.667 0 16.667-2 18-6 2-2.667 1-9.667-3-21-32-87.333-82.667-157.667\n-152-211l-3-3h399907v-40zM93 281 H400000 v-40L7 241z", + leftharpoondownplus: "M7 435c-4 4-6.3 8.7-7 14 0 5.3.7 9 2 11s5.3 5.3 12\n 10c90.7 54 156 130 196 228 3.3 10.7 6.3 16.3 9 17 2 .7 5 1 9 1h5c10.7 0 16.7\n-2 18-6 2-2.7 1-9.7-3-21-32-87.3-82.7-157.7-152-211l-3-3h399907v-40H7zm93 0\nv40h399900v-40zM0 241v40h399900v-40zm0 0v40h399900v-40z", + // hook is from glyph U+21A9 in font KaTeX Main + lefthook: "M400000 281 H103s-33-11.2-61-33.5S0 197.3 0 164s14.2-61.2 42.5\n-83.5C70.8 58.2 104 47 142 47 c16.7 0 25 6.7 25 20 0 12-8.7 18.7-26 20-40 3.3\n-68.7 15.7-86 37-10 12-15 25.3-15 40 0 22.7 9.8 40.7 29.5 54 19.7 13.3 43.5 21\n 71.5 23h399859zM103 281v-40h399897v40z", + leftlinesegment: "M40 281 V428 H0 V94 H40 V241 H400000 v40z\nM40 281 V428 H0 V94 H40 V241 H400000 v40z", + leftmapsto: "M40 281 V448H0V74H40V241H400000v40z\nM40 281 V448H0V74H40V241H400000v40z", + // tofrom is from glyph U+21C4 in font KaTeX AMS Regular + leftToFrom: "M0 147h400000v40H0zm0 214c68 40 115.7 95.7 143 167h22c15.3 0 23\n-.3 23-1 0-1.3-5.3-13.7-16-37-18-35.3-41.3-69-70-101l-7-8h399905v-40H95l7-8\nc28.7-32 52-65.7 70-101 10.7-23.3 16-35.7 16-37 0-.7-7.7-1-23-1h-22C115.7 265.3\n 68 321 0 361zm0-174v-40h399900v40zm100 154v40h399900v-40z", + longequal: "M0 50 h400000 v40H0z m0 194h40000v40H0z\nM0 50 h400000 v40H0z m0 194h40000v40H0z", + midbrace: "M200428 334\nc-100.7-8.3-195.3-44-280-108-55.3-42-101.7-93-139-153l-9-14c-2.7 4-5.7 8.7-9 14\n-53.3 86.7-123.7 153-211 199-66.7 36-137.3 56.3-212 62H0V214h199568c178.3-11.7\n 311.7-78.3 403-201 6-8 9.7-12 11-12 .7-.7 6.7-1 18-1s17.3.3 18 1c1.3 0 5 4 11\n 12 44.7 59.3 101.3 106.3 170 141s145.3 54.3 229 60h199572v120z", + midbraceunder: "M199572 214\nc100.7 8.3 195.3 44 280 108 55.3 42 101.7 93 139 153l9 14c2.7-4 5.7-8.7 9-14\n 53.3-86.7 123.7-153 211-199 66.7-36 137.3-56.3 212-62h199568v120H200432c-178.3\n 11.7-311.7 78.3-403 201-6 8-9.7 12-11 12-.7.7-6.7 1-18 1s-17.3-.3-18-1c-1.3 0\n-5-4-11-12-44.7-59.3-101.3-106.3-170-141s-145.3-54.3-229-60H0V214z", + oiintSize1: "M512.6 71.6c272.6 0 320.3 106.8 320.3 178.2 0 70.8-47.7 177.6\n-320.3 177.6S193.1 320.6 193.1 249.8c0-71.4 46.9-178.2 319.5-178.2z\nm368.1 178.2c0-86.4-60.9-215.4-368.1-215.4-306.4 0-367.3 129-367.3 215.4 0 85.8\n60.9 214.8 367.3 214.8 307.2 0 368.1-129 368.1-214.8z", + oiintSize2: "M757.8 100.1c384.7 0 451.1 137.6 451.1 230 0 91.3-66.4 228.8\n-451.1 228.8-386.3 0-452.7-137.5-452.7-228.8 0-92.4 66.4-230 452.7-230z\nm502.4 230c0-111.2-82.4-277.2-502.4-277.2s-504 166-504 277.2\nc0 110 84 276 504 276s502.4-166 502.4-276z", + oiiintSize1: "M681.4 71.6c408.9 0 480.5 106.8 480.5 178.2 0 70.8-71.6 177.6\n-480.5 177.6S202.1 320.6 202.1 249.8c0-71.4 70.5-178.2 479.3-178.2z\nm525.8 178.2c0-86.4-86.8-215.4-525.7-215.4-437.9 0-524.7 129-524.7 215.4 0\n85.8 86.8 214.8 524.7 214.8 438.9 0 525.7-129 525.7-214.8z", + oiiintSize2: "M1021.2 53c603.6 0 707.8 165.8 707.8 277.2 0 110-104.2 275.8\n-707.8 275.8-606 0-710.2-165.8-710.2-275.8C311 218.8 415.2 53 1021.2 53z\nm770.4 277.1c0-131.2-126.4-327.6-770.5-327.6S248.4 198.9 248.4 330.1\nc0 130 128.8 326.4 772.7 326.4s770.5-196.4 770.5-326.4z", + rightarrow: "M0 241v40h399891c-47.3 35.3-84 78-110 128\n-16.7 32-27.7 63.7-33 95 0 1.3-.2 2.7-.5 4-.3 1.3-.5 2.3-.5 3 0 7.3 6.7 11 20\n 11 8 0 13.2-.8 15.5-2.5 2.3-1.7 4.2-5.5 5.5-11.5 2-13.3 5.7-27 11-41 14.7-44.7\n 39-84.5 73-119.5s73.7-60.2 119-75.5c6-2 9-5.7 9-11s-3-9-9-11c-45.3-15.3-85\n-40.5-119-75.5s-58.3-74.8-73-119.5c-4.7-14-8.3-27.3-11-40-1.3-6.7-3.2-10.8-5.5\n-12.5-2.3-1.7-7.5-2.5-15.5-2.5-14 0-21 3.7-21 11 0 2 2 10.3 6 25 20.7 83.3 67\n 151.7 139 205zm0 0v40h399900v-40z", + rightbrace: "M400000 542l\n-6 6h-17c-12.7 0-19.3-.3-20-1-4-4-7.3-8.3-10-13-35.3-51.3-80.8-93.8-136.5-127.5\ns-117.2-55.8-184.5-66.5c-.7 0-2-.3-4-1-18.7-2.7-76-4.3-172-5H0V214h399571l6 1\nc124.7 8 235 61.7 331 161 31.3 33.3 59.7 72.7 85 118l7 13v35z", + rightbraceunder: "M399994 0l6 6v35l-6 11c-56 104-135.3 181.3-238 232-57.3\n 28.7-117 45-179 50H-300V214h399897c43.3-7 81-15 113-26 100.7-33 179.7-91 237\n-174 2.7-5 6-9 10-13 .7-1 7.3-1 20-1h17z", + rightgroup: "M0 80h399565c371 0 266.7 149.4 414 180 5.9 1.2 18 0 18 0 2 0\n 3-1 3-3v-38c-76-158-257-219-435-219H0z", + rightgroupunder: "M0 262h399565c371 0 266.7-149.4 414-180 5.9-1.2 18 0 18\n 0 2 0 3 1 3 3v38c-76 158-257 219-435 219H0z", + rightharpoon: "M0 241v40h399993c4.7-4.7 7-9.3 7-14 0-9.3\n-3.7-15.3-11-18-92.7-56.7-159-133.7-199-231-3.3-9.3-6-14.7-8-16-2-1.3-7-2-15-2\n-10.7 0-16.7 2-18 6-2 2.7-1 9.7 3 21 15.3 42 36.7 81.8 64 119.5 27.3 37.7 58\n 69.2 92 94.5zm0 0v40h399900v-40z", + rightharpoonplus: "M0 241v40h399993c4.7-4.7 7-9.3 7-14 0-9.3-3.7-15.3-11\n-18-92.7-56.7-159-133.7-199-231-3.3-9.3-6-14.7-8-16-2-1.3-7-2-15-2-10.7 0-16.7\n 2-18 6-2 2.7-1 9.7 3 21 15.3 42 36.7 81.8 64 119.5 27.3 37.7 58 69.2 92 94.5z\nm0 0v40h399900v-40z m100 194v40h399900v-40zm0 0v40h399900v-40z", + rightharpoondown: "M399747 511c0 7.3 6.7 11 20 11 8 0 13-.8 15-2.5s4.7-6.8\n 8-15.5c40-94 99.3-166.3 178-217 13.3-8 20.3-12.3 21-13 5.3-3.3 8.5-5.8 9.5\n-7.5 1-1.7 1.5-5.2 1.5-10.5s-2.3-10.3-7-15H0v40h399908c-34 25.3-64.7 57-92 95\n-27.3 38-48.7 77.7-64 119-3.3 8.7-5 14-5 16zM0 241v40h399900v-40z", + rightharpoondownplus: "M399747 705c0 7.3 6.7 11 20 11 8 0 13-.8\n 15-2.5s4.7-6.8 8-15.5c40-94 99.3-166.3 178-217 13.3-8 20.3-12.3 21-13 5.3-3.3\n 8.5-5.8 9.5-7.5 1-1.7 1.5-5.2 1.5-10.5s-2.3-10.3-7-15H0v40h399908c-34 25.3\n-64.7 57-92 95-27.3 38-48.7 77.7-64 119-3.3 8.7-5 14-5 16zM0 435v40h399900v-40z\nm0-194v40h400000v-40zm0 0v40h400000v-40z", + righthook: "M399859 241c-764 0 0 0 0 0 40-3.3 68.7-15.7 86-37 10-12 15-25.3\n 15-40 0-22.7-9.8-40.7-29.5-54-19.7-13.3-43.5-21-71.5-23-17.3-1.3-26-8-26-20 0\n-13.3 8.7-20 26-20 38 0 71 11.2 99 33.5 0 0 7 5.6 21 16.7 14 11.2 21 33.5 21\n 66.8s-14 61.2-42 83.5c-28 22.3-61 33.5-99 33.5L0 241z M0 281v-40h399859v40z", + rightlinesegment: "M399960 241 V94 h40 V428 h-40 V281 H0 v-40z\nM399960 241 V94 h40 V428 h-40 V281 H0 v-40z", + rightToFrom: "M400000 167c-70.7-42-118-97.7-142-167h-23c-15.3 0-23 .3-23\n 1 0 1.3 5.3 13.7 16 37 18 35.3 41.3 69 70 101l7 8H0v40h399905l-7 8c-28.7 32\n-52 65.7-70 101-10.7 23.3-16 35.7-16 37 0 .7 7.7 1 23 1h23c24-69.3 71.3-125 142\n-167z M100 147v40h399900v-40zM0 341v40h399900v-40z", + // twoheadleftarrow is from glyph U+219E in font KaTeX AMS Regular + twoheadleftarrow: "M0 167c68 40\n 115.7 95.7 143 167h22c15.3 0 23-.3 23-1 0-1.3-5.3-13.7-16-37-18-35.3-41.3-69\n-70-101l-7-8h125l9 7c50.7 39.3 85 86 103 140h46c0-4.7-6.3-18.7-19-42-18-35.3\n-40-67.3-66-96l-9-9h399716v-40H284l9-9c26-28.7 48-60.7 66-96 12.7-23.333 19\n-37.333 19-42h-46c-18 54-52.3 100.7-103 140l-9 7H95l7-8c28.7-32 52-65.7 70-101\n 10.7-23.333 16-35.7 16-37 0-.7-7.7-1-23-1h-22C115.7 71.3 68 127 0 167z", + twoheadrightarrow: "M400000 167\nc-68-40-115.7-95.7-143-167h-22c-15.3 0-23 .3-23 1 0 1.3 5.3 13.7 16 37 18 35.3\n 41.3 69 70 101l7 8h-125l-9-7c-50.7-39.3-85-86-103-140h-46c0 4.7 6.3 18.7 19 42\n 18 35.3 40 67.3 66 96l9 9H0v40h399716l-9 9c-26 28.7-48 60.7-66 96-12.7 23.333\n-19 37.333-19 42h46c18-54 52.3-100.7 103-140l9-7h125l-7 8c-28.7 32-52 65.7-70\n 101-10.7 23.333-16 35.7-16 37 0 .7 7.7 1 23 1h22c27.3-71.3 75-127 143-167z", + // tilde1 is a modified version of a glyph from the MnSymbol package + tilde1: "M200 55.538c-77 0-168 73.953-177 73.953-3 0-7\n-2.175-9-5.437L2 97c-1-2-2-4-2-6 0-4 2-7 5-9l20-12C116 12 171 0 207 0c86 0\n 114 68 191 68 78 0 168-68 177-68 4 0 7 2 9 5l12 19c1 2.175 2 4.35 2 6.525 0\n 4.35-2 7.613-5 9.788l-19 13.05c-92 63.077-116.937 75.308-183 76.128\n-68.267.847-113-73.952-191-73.952z", + // ditto tilde2, tilde3, & tilde4 + tilde2: "M344 55.266c-142 0-300.638 81.316-311.5 86.418\n-8.01 3.762-22.5 10.91-23.5 5.562L1 120c-1-2-1-3-1-4 0-5 3-9 8-10l18.4-9C160.9\n 31.9 283 0 358 0c148 0 188 122 331 122s314-97 326-97c4 0 8 2 10 7l7 21.114\nc1 2.14 1 3.21 1 4.28 0 5.347-3 9.626-7 10.696l-22.3 12.622C852.6 158.372 751\n 181.476 676 181.476c-149 0-189-126.21-332-126.21z", + tilde3: "M786 59C457 59 32 175.242 13 175.242c-6 0-10-3.457\n-11-10.37L.15 138c-1-7 3-12 10-13l19.2-6.4C378.4 40.7 634.3 0 804.3 0c337 0\n 411.8 157 746.8 157 328 0 754-112 773-112 5 0 10 3 11 9l1 14.075c1 8.066-.697\n 16.595-6.697 17.492l-21.052 7.31c-367.9 98.146-609.15 122.696-778.15 122.696\n -338 0-409-156.573-744-156.573z", + tilde4: "M786 58C457 58 32 177.487 13 177.487c-6 0-10-3.345\n-11-10.035L.15 143c-1-7 3-12 10-13l22-6.7C381.2 35 637.15 0 807.15 0c337 0 409\n 177 744 177 328 0 754-127 773-127 5 0 10 3 11 9l1 14.794c1 7.805-3 13.38-9\n 14.495l-20.7 5.574c-366.85 99.79-607.3 139.372-776.3 139.372-338 0-409\n -175.236-744-175.236z", + // vec is from glyph U+20D7 in font KaTeX Main + vec: "M377 20c0-5.333 1.833-10 5.5-14S391 0 397 0c4.667 0 8.667 1.667 12 5\n3.333 2.667 6.667 9 10 19 6.667 24.667 20.333 43.667 41 57 7.333 4.667 11\n10.667 11 18 0 6-1 10-3 12s-6.667 5-14 9c-28.667 14.667-53.667 35.667-75 63\n-1.333 1.333-3.167 3.5-5.5 6.5s-4 4.833-5 5.5c-1 .667-2.5 1.333-4.5 2s-4.333 1\n-7 1c-4.667 0-9.167-1.833-13.5-5.5S337 184 337 178c0-12.667 15.667-32.333 47-59\nH213l-171-1c-8.667-6-13-12.333-13-19 0-4.667 4.333-11.333 13-20h359\nc-16-25.333-24-45-24-59z", + // widehat1 is a modified version of a glyph from the MnSymbol package + widehat1: "M529 0h5l519 115c5 1 9 5 9 10 0 1-1 2-1 3l-4 22\nc-1 5-5 9-11 9h-2L532 67 19 159h-2c-5 0-9-4-11-9l-5-22c-1-6 2-12 8-13z", + // ditto widehat2, widehat3, & widehat4 + widehat2: "M1181 0h2l1171 176c6 0 10 5 10 11l-2 23c-1 6-5 10\n-11 10h-1L1182 67 15 220h-1c-6 0-10-4-11-10l-2-23c-1-6 4-11 10-11z", + widehat3: "M1181 0h2l1171 236c6 0 10 5 10 11l-2 23c-1 6-5 10\n-11 10h-1L1182 67 15 280h-1c-6 0-10-4-11-10l-2-23c-1-6 4-11 10-11z", + widehat4: "M1181 0h2l1171 296c6 0 10 5 10 11l-2 23c-1 6-5 10\n-11 10h-1L1182 67 15 340h-1c-6 0-10-4-11-10l-2-23c-1-6 4-11 10-11z", + // widecheck paths are all inverted versions of widehat + widecheck1: "M529,159h5l519,-115c5,-1,9,-5,9,-10c0,-1,-1,-2,-1,-3l-4,-22c-1,\n-5,-5,-9,-11,-9h-2l-512,92l-513,-92h-2c-5,0,-9,4,-11,9l-5,22c-1,6,2,12,8,13z", + widecheck2: "M1181,220h2l1171,-176c6,0,10,-5,10,-11l-2,-23c-1,-6,-5,-10,\n-11,-10h-1l-1168,153l-1167,-153h-1c-6,0,-10,4,-11,10l-2,23c-1,6,4,11,10,11z", + widecheck3: "M1181,280h2l1171,-236c6,0,10,-5,10,-11l-2,-23c-1,-6,-5,-10,\n-11,-10h-1l-1168,213l-1167,-213h-1c-6,0,-10,4,-11,10l-2,23c-1,6,4,11,10,11z", + widecheck4: "M1181,340h2l1171,-296c6,0,10,-5,10,-11l-2,-23c-1,-6,-5,-10,\n-11,-10h-1l-1168,273l-1167,-273h-1c-6,0,-10,4,-11,10l-2,23c-1,6,4,11,10,11z", + // The next ten paths support reaction arrows from the mhchem package. + // Arrows for \ce{<-->} are offset from xAxis by 0.22ex, per mhchem in LaTeX + // baraboveleftarrow is mostly from glyph U+2190 in font KaTeX Main + baraboveleftarrow: "M400000 620h-399890l3 -3c68.7 -52.7 113.7 -120 135 -202\nc4 -14.7 6 -23 6 -25c0 -7.3 -7 -11 -21 -11c-8 0 -13.2 0.8 -15.5 2.5\nc-2.3 1.7 -4.2 5.8 -5.5 12.5c-1.3 4.7 -2.7 10.3 -4 17c-12 48.7 -34.8 92 -68.5 130\ns-74.2 66.3 -121.5 85c-10 4 -16 7.7 -18 11c0 8.7 6 14.3 18 17c47.3 18.7 87.8 47\n121.5 85s56.5 81.3 68.5 130c0.7 2 1.3 5 2 9s1.2 6.7 1.5 8c0.3 1.3 1 3.3 2 6\ns2.2 4.5 3.5 5.5c1.3 1 3.3 1.8 6 2.5s6 1 10 1c14 0 21 -3.7 21 -11\nc0 -2 -2 -10.3 -6 -25c-20 -79.3 -65 -146.7 -135 -202l-3 -3h399890z\nM100 620v40h399900v-40z M0 241v40h399900v-40zM0 241v40h399900v-40z", + // rightarrowabovebar is mostly from glyph U+2192, KaTeX Main + rightarrowabovebar: "M0 241v40h399891c-47.3 35.3-84 78-110 128-16.7 32\n-27.7 63.7-33 95 0 1.3-.2 2.7-.5 4-.3 1.3-.5 2.3-.5 3 0 7.3 6.7 11 20 11 8 0\n13.2-.8 15.5-2.5 2.3-1.7 4.2-5.5 5.5-11.5 2-13.3 5.7-27 11-41 14.7-44.7 39\n-84.5 73-119.5s73.7-60.2 119-75.5c6-2 9-5.7 9-11s-3-9-9-11c-45.3-15.3-85-40.5\n-119-75.5s-58.3-74.8-73-119.5c-4.7-14-8.3-27.3-11-40-1.3-6.7-3.2-10.8-5.5\n-12.5-2.3-1.7-7.5-2.5-15.5-2.5-14 0-21 3.7-21 11 0 2 2 10.3 6 25 20.7 83.3 67\n151.7 139 205zm96 379h399894v40H0zm0 0h399904v40H0z", + // The short left harpoon has 0.5em (i.e. 500 units) kern on the left end. + // Ref from mhchem.sty: \rlap{\raisebox{-.22ex}{$\kern0.5em + baraboveshortleftharpoon: "M507,435c-4,4,-6.3,8.7,-7,14c0,5.3,0.7,9,2,11\nc1.3,2,5.3,5.3,12,10c90.7,54,156,130,196,228c3.3,10.7,6.3,16.3,9,17\nc2,0.7,5,1,9,1c0,0,5,0,5,0c10.7,0,16.7,-2,18,-6c2,-2.7,1,-9.7,-3,-21\nc-32,-87.3,-82.7,-157.7,-152,-211c0,0,-3,-3,-3,-3l399351,0l0,-40\nc-398570,0,-399437,0,-399437,0z M593 435 v40 H399500 v-40z\nM0 281 v-40 H399908 v40z M0 281 v-40 H399908 v40z", + rightharpoonaboveshortbar: "M0,241 l0,40c399126,0,399993,0,399993,0\nc4.7,-4.7,7,-9.3,7,-14c0,-9.3,-3.7,-15.3,-11,-18c-92.7,-56.7,-159,-133.7,-199,\n-231c-3.3,-9.3,-6,-14.7,-8,-16c-2,-1.3,-7,-2,-15,-2c-10.7,0,-16.7,2,-18,6\nc-2,2.7,-1,9.7,3,21c15.3,42,36.7,81.8,64,119.5c27.3,37.7,58,69.2,92,94.5z\nM0 241 v40 H399908 v-40z M0 475 v-40 H399500 v40z M0 475 v-40 H399500 v40z", + shortbaraboveleftharpoon: "M7,435c-4,4,-6.3,8.7,-7,14c0,5.3,0.7,9,2,11\nc1.3,2,5.3,5.3,12,10c90.7,54,156,130,196,228c3.3,10.7,6.3,16.3,9,17c2,0.7,5,1,9,\n1c0,0,5,0,5,0c10.7,0,16.7,-2,18,-6c2,-2.7,1,-9.7,-3,-21c-32,-87.3,-82.7,-157.7,\n-152,-211c0,0,-3,-3,-3,-3l399907,0l0,-40c-399126,0,-399993,0,-399993,0z\nM93 435 v40 H400000 v-40z M500 241 v40 H400000 v-40z M500 241 v40 H400000 v-40z", + shortrightharpoonabovebar: "M53,241l0,40c398570,0,399437,0,399437,0\nc4.7,-4.7,7,-9.3,7,-14c0,-9.3,-3.7,-15.3,-11,-18c-92.7,-56.7,-159,-133.7,-199,\n-231c-3.3,-9.3,-6,-14.7,-8,-16c-2,-1.3,-7,-2,-15,-2c-10.7,0,-16.7,2,-18,6\nc-2,2.7,-1,9.7,3,21c15.3,42,36.7,81.8,64,119.5c27.3,37.7,58,69.2,92,94.5z\nM500 241 v40 H399408 v-40z M500 435 v40 H400000 v-40z" +}; +var tallDelim = function tallDelim(label, midHeight) { + switch (label) { + case "lbrack": + return "M403 1759 V84 H666 V0 H319 V1759 v" + midHeight + " v1759 h347 v-84\nH403z M403 1759 V0 H319 V1759 v" + midHeight + " v1759 h84z"; + + case "rbrack": + return "M347 1759 V0 H0 V84 H263 V1759 v" + midHeight + " v1759 H0 v84 H347z\nM347 1759 V0 H263 V1759 v" + midHeight + " v1759 h84z"; + + case "vert": + return "M145 15 v585 v" + midHeight + " v585 c2.667,10,9.667,15,21,15\nc10,0,16.667,-5,20,-15 v-585 v" + -midHeight + " v-585 c-2.667,-10,-9.667,-15,-21,-15\nc-10,0,-16.667,5,-20,15z M188 15 H145 v585 v" + midHeight + " v585 h43z"; + + case "doublevert": + return "M145 15 v585 v" + midHeight + " v585 c2.667,10,9.667,15,21,15\nc10,0,16.667,-5,20,-15 v-585 v" + -midHeight + " v-585 c-2.667,-10,-9.667,-15,-21,-15\nc-10,0,-16.667,5,-20,15z M188 15 H145 v585 v" + midHeight + " v585 h43z\nM367 15 v585 v" + midHeight + " v585 c2.667,10,9.667,15,21,15\nc10,0,16.667,-5,20,-15 v-585 v" + -midHeight + " v-585 c-2.667,-10,-9.667,-15,-21,-15\nc-10,0,-16.667,5,-20,15z M410 15 H367 v585 v" + midHeight + " v585 h43z"; + + case "lfloor": + return "M319 602 V0 H403 V602 v" + midHeight + " v1715 h263 v84 H319z\nMM319 602 V0 H403 V602 v" + midHeight + " v1715 H319z"; + + case "rfloor": + return "M319 602 V0 H403 V602 v" + midHeight + " v1799 H0 v-84 H319z\nMM319 602 V0 H403 V602 v" + midHeight + " v1715 H319z"; + + case "lceil": + return "M403 1759 V84 H666 V0 H319 V1759 v" + midHeight + " v602 h84z\nM403 1759 V0 H319 V1759 v" + midHeight + " v602 h84z"; + + case "rceil": + return "M347 1759 V0 H0 V84 H263 V1759 v" + midHeight + " v602 h84z\nM347 1759 V0 h-84 V1759 v" + midHeight + " v602 h84z"; + + case "lparen": + return "M863,9c0,-2,-2,-5,-6,-9c0,0,-17,0,-17,0c-12.7,0,-19.3,0.3,-20,1\nc-5.3,5.3,-10.3,11,-15,17c-242.7,294.7,-395.3,682,-458,1162c-21.3,163.3,-33.3,349,\n-36,557 l0," + (midHeight + 84) + "c0.2,6,0,26,0,60c2,159.3,10,310.7,24,454c53.3,528,210,\n949.7,470,1265c4.7,6,9.7,11.7,15,17c0.7,0.7,7,1,19,1c0,0,18,0,18,0c4,-4,6,-7,6,-9\nc0,-2.7,-3.3,-8.7,-10,-18c-135.3,-192.7,-235.5,-414.3,-300.5,-665c-65,-250.7,-102.5,\n-544.7,-112.5,-882c-2,-104,-3,-167,-3,-189\nl0,-" + (midHeight + 92) + "c0,-162.7,5.7,-314,17,-454c20.7,-272,63.7,-513,129,-723c65.3,\n-210,155.3,-396.3,270,-559c6.7,-9.3,10,-15.3,10,-18z"; + + case "rparen": + return "M76,0c-16.7,0,-25,3,-25,9c0,2,2,6.3,6,13c21.3,28.7,42.3,60.3,\n63,95c96.7,156.7,172.8,332.5,228.5,527.5c55.7,195,92.8,416.5,111.5,664.5\nc11.3,139.3,17,290.7,17,454c0,28,1.7,43,3.3,45l0," + (midHeight + 9) + "\nc-3,4,-3.3,16.7,-3.3,38c0,162,-5.7,313.7,-17,455c-18.7,248,-55.8,469.3,-111.5,664\nc-55.7,194.7,-131.8,370.3,-228.5,527c-20.7,34.7,-41.7,66.3,-63,95c-2,3.3,-4,7,-6,11\nc0,7.3,5.7,11,17,11c0,0,11,0,11,0c9.3,0,14.3,-0.3,15,-1c5.3,-5.3,10.3,-11,15,-17\nc242.7,-294.7,395.3,-681.7,458,-1161c21.3,-164.7,33.3,-350.7,36,-558\nl0,-" + (midHeight + 144) + "c-2,-159.3,-10,-310.7,-24,-454c-53.3,-528,-210,-949.7,\n-470,-1265c-4.7,-6,-9.7,-11.7,-15,-17c-0.7,-0.7,-6.7,-1,-18,-1z"; + + default: + // We should not ever get here. + throw new Error("Unknown stretchy delimiter."); + } +}; + +/** + * This node represents a document fragment, which contains elements, but when + * placed into the DOM doesn't have any representation itself. It only contains + * children and doesn't have any DOM node properties. + */ +class DocumentFragment { + // HtmlDomNode + // Never used; needed for satisfying interface. + constructor(children) { + this.children = void 0; + this.classes = void 0; + this.height = void 0; + this.depth = void 0; + this.maxFontSize = void 0; + this.style = void 0; + this.children = children; + this.classes = []; + this.height = 0; + this.depth = 0; + this.maxFontSize = 0; + this.style = {}; + } + + hasClass(className) { + return utils.contains(this.classes, className); + } + /** Convert the fragment into a node. */ + + + toNode() { + var frag = document.createDocumentFragment(); + + for (var i = 0; i < this.children.length; i++) { + frag.appendChild(this.children[i].toNode()); + } + + return frag; + } + /** Convert the fragment into HTML markup. */ + + + toMarkup() { + var markup = ""; // Simply concatenate the markup for the children together. + + for (var i = 0; i < this.children.length; i++) { + markup += this.children[i].toMarkup(); + } + + return markup; + } + /** + * Converts the math node into a string, similar to innerText. Applies to + * MathDomNode's only. + */ + + + toText() { + // To avoid this, we would subclass documentFragment separately for + // MathML, but polyfills for subclassing is expensive per PR 1469. + // $FlowFixMe: Only works for ChildType = MathDomNode. + var toText = child => child.toText(); + + return this.children.map(toText).join(""); + } + +} + +// This file is GENERATED by buildMetrics.sh. DO NOT MODIFY. +var fontMetricsData = { + "AMS-Regular": { + "32": [0, 0, 0, 0, 0.25], + "65": [0, 0.68889, 0, 0, 0.72222], + "66": [0, 0.68889, 0, 0, 0.66667], + "67": [0, 0.68889, 0, 0, 0.72222], + "68": [0, 0.68889, 0, 0, 0.72222], + "69": [0, 0.68889, 0, 0, 0.66667], + "70": [0, 0.68889, 0, 0, 0.61111], + "71": [0, 0.68889, 0, 0, 0.77778], + "72": [0, 0.68889, 0, 0, 0.77778], + "73": [0, 0.68889, 0, 0, 0.38889], + "74": [0.16667, 0.68889, 0, 0, 0.5], + "75": [0, 0.68889, 0, 0, 0.77778], + "76": [0, 0.68889, 0, 0, 0.66667], + "77": [0, 0.68889, 0, 0, 0.94445], + "78": [0, 0.68889, 0, 0, 0.72222], + "79": [0.16667, 0.68889, 0, 0, 0.77778], + "80": [0, 0.68889, 0, 0, 0.61111], + "81": [0.16667, 0.68889, 0, 0, 0.77778], + "82": [0, 0.68889, 0, 0, 0.72222], + "83": [0, 0.68889, 0, 0, 0.55556], + "84": [0, 0.68889, 0, 0, 0.66667], + "85": [0, 0.68889, 0, 0, 0.72222], + "86": [0, 0.68889, 0, 0, 0.72222], + "87": [0, 0.68889, 0, 0, 1.0], + "88": [0, 0.68889, 0, 0, 0.72222], + "89": [0, 0.68889, 0, 0, 0.72222], + "90": [0, 0.68889, 0, 0, 0.66667], + "107": [0, 0.68889, 0, 0, 0.55556], + "160": [0, 0, 0, 0, 0.25], + "165": [0, 0.675, 0.025, 0, 0.75], + "174": [0.15559, 0.69224, 0, 0, 0.94666], + "240": [0, 0.68889, 0, 0, 0.55556], + "295": [0, 0.68889, 0, 0, 0.54028], + "710": [0, 0.825, 0, 0, 2.33334], + "732": [0, 0.9, 0, 0, 2.33334], + "770": [0, 0.825, 0, 0, 2.33334], + "771": [0, 0.9, 0, 0, 2.33334], + "989": [0.08167, 0.58167, 0, 0, 0.77778], + "1008": [0, 0.43056, 0.04028, 0, 0.66667], + "8245": [0, 0.54986, 0, 0, 0.275], + "8463": [0, 0.68889, 0, 0, 0.54028], + "8487": [0, 0.68889, 0, 0, 0.72222], + "8498": [0, 0.68889, 0, 0, 0.55556], + "8502": [0, 0.68889, 0, 0, 0.66667], + "8503": [0, 0.68889, 0, 0, 0.44445], + "8504": [0, 0.68889, 0, 0, 0.66667], + "8513": [0, 0.68889, 0, 0, 0.63889], + "8592": [-0.03598, 0.46402, 0, 0, 0.5], + "8594": [-0.03598, 0.46402, 0, 0, 0.5], + "8602": [-0.13313, 0.36687, 0, 0, 1.0], + "8603": [-0.13313, 0.36687, 0, 0, 1.0], + "8606": [0.01354, 0.52239, 0, 0, 1.0], + "8608": [0.01354, 0.52239, 0, 0, 1.0], + "8610": [0.01354, 0.52239, 0, 0, 1.11111], + "8611": [0.01354, 0.52239, 0, 0, 1.11111], + "8619": [0, 0.54986, 0, 0, 1.0], + "8620": [0, 0.54986, 0, 0, 1.0], + "8621": [-0.13313, 0.37788, 0, 0, 1.38889], + "8622": [-0.13313, 0.36687, 0, 0, 1.0], + "8624": [0, 0.69224, 0, 0, 0.5], + "8625": [0, 0.69224, 0, 0, 0.5], + "8630": [0, 0.43056, 0, 0, 1.0], + "8631": [0, 0.43056, 0, 0, 1.0], + "8634": [0.08198, 0.58198, 0, 0, 0.77778], + "8635": [0.08198, 0.58198, 0, 0, 0.77778], + "8638": [0.19444, 0.69224, 0, 0, 0.41667], + "8639": [0.19444, 0.69224, 0, 0, 0.41667], + "8642": [0.19444, 0.69224, 0, 0, 0.41667], + "8643": [0.19444, 0.69224, 0, 0, 0.41667], + "8644": [0.1808, 0.675, 0, 0, 1.0], + "8646": [0.1808, 0.675, 0, 0, 1.0], + "8647": [0.1808, 0.675, 0, 0, 1.0], + "8648": [0.19444, 0.69224, 0, 0, 0.83334], + "8649": [0.1808, 0.675, 0, 0, 1.0], + "8650": [0.19444, 0.69224, 0, 0, 0.83334], + "8651": [0.01354, 0.52239, 0, 0, 1.0], + "8652": [0.01354, 0.52239, 0, 0, 1.0], + "8653": [-0.13313, 0.36687, 0, 0, 1.0], + "8654": [-0.13313, 0.36687, 0, 0, 1.0], + "8655": [-0.13313, 0.36687, 0, 0, 1.0], + "8666": [0.13667, 0.63667, 0, 0, 1.0], + "8667": [0.13667, 0.63667, 0, 0, 1.0], + "8669": [-0.13313, 0.37788, 0, 0, 1.0], + "8672": [-0.064, 0.437, 0, 0, 1.334], + "8674": [-0.064, 0.437, 0, 0, 1.334], + "8705": [0, 0.825, 0, 0, 0.5], + "8708": [0, 0.68889, 0, 0, 0.55556], + "8709": [0.08167, 0.58167, 0, 0, 0.77778], + "8717": [0, 0.43056, 0, 0, 0.42917], + "8722": [-0.03598, 0.46402, 0, 0, 0.5], + "8724": [0.08198, 0.69224, 0, 0, 0.77778], + "8726": [0.08167, 0.58167, 0, 0, 0.77778], + "8733": [0, 0.69224, 0, 0, 0.77778], + "8736": [0, 0.69224, 0, 0, 0.72222], + "8737": [0, 0.69224, 0, 0, 0.72222], + "8738": [0.03517, 0.52239, 0, 0, 0.72222], + "8739": [0.08167, 0.58167, 0, 0, 0.22222], + "8740": [0.25142, 0.74111, 0, 0, 0.27778], + "8741": [0.08167, 0.58167, 0, 0, 0.38889], + "8742": [0.25142, 0.74111, 0, 0, 0.5], + "8756": [0, 0.69224, 0, 0, 0.66667], + "8757": [0, 0.69224, 0, 0, 0.66667], + "8764": [-0.13313, 0.36687, 0, 0, 0.77778], + "8765": [-0.13313, 0.37788, 0, 0, 0.77778], + "8769": [-0.13313, 0.36687, 0, 0, 0.77778], + "8770": [-0.03625, 0.46375, 0, 0, 0.77778], + "8774": [0.30274, 0.79383, 0, 0, 0.77778], + "8776": [-0.01688, 0.48312, 0, 0, 0.77778], + "8778": [0.08167, 0.58167, 0, 0, 0.77778], + "8782": [0.06062, 0.54986, 0, 0, 0.77778], + "8783": [0.06062, 0.54986, 0, 0, 0.77778], + "8785": [0.08198, 0.58198, 0, 0, 0.77778], + "8786": [0.08198, 0.58198, 0, 0, 0.77778], + "8787": [0.08198, 0.58198, 0, 0, 0.77778], + "8790": [0, 0.69224, 0, 0, 0.77778], + "8791": [0.22958, 0.72958, 0, 0, 0.77778], + "8796": [0.08198, 0.91667, 0, 0, 0.77778], + "8806": [0.25583, 0.75583, 0, 0, 0.77778], + "8807": [0.25583, 0.75583, 0, 0, 0.77778], + "8808": [0.25142, 0.75726, 0, 0, 0.77778], + "8809": [0.25142, 0.75726, 0, 0, 0.77778], + "8812": [0.25583, 0.75583, 0, 0, 0.5], + "8814": [0.20576, 0.70576, 0, 0, 0.77778], + "8815": [0.20576, 0.70576, 0, 0, 0.77778], + "8816": [0.30274, 0.79383, 0, 0, 0.77778], + "8817": [0.30274, 0.79383, 0, 0, 0.77778], + "8818": [0.22958, 0.72958, 0, 0, 0.77778], + "8819": [0.22958, 0.72958, 0, 0, 0.77778], + "8822": [0.1808, 0.675, 0, 0, 0.77778], + "8823": [0.1808, 0.675, 0, 0, 0.77778], + "8828": [0.13667, 0.63667, 0, 0, 0.77778], + "8829": [0.13667, 0.63667, 0, 0, 0.77778], + "8830": [0.22958, 0.72958, 0, 0, 0.77778], + "8831": [0.22958, 0.72958, 0, 0, 0.77778], + "8832": [0.20576, 0.70576, 0, 0, 0.77778], + "8833": [0.20576, 0.70576, 0, 0, 0.77778], + "8840": [0.30274, 0.79383, 0, 0, 0.77778], + "8841": [0.30274, 0.79383, 0, 0, 0.77778], + "8842": [0.13597, 0.63597, 0, 0, 0.77778], + "8843": [0.13597, 0.63597, 0, 0, 0.77778], + "8847": [0.03517, 0.54986, 0, 0, 0.77778], + "8848": [0.03517, 0.54986, 0, 0, 0.77778], + "8858": [0.08198, 0.58198, 0, 0, 0.77778], + "8859": [0.08198, 0.58198, 0, 0, 0.77778], + "8861": [0.08198, 0.58198, 0, 0, 0.77778], + "8862": [0, 0.675, 0, 0, 0.77778], + "8863": [0, 0.675, 0, 0, 0.77778], + "8864": [0, 0.675, 0, 0, 0.77778], + "8865": [0, 0.675, 0, 0, 0.77778], + "8872": [0, 0.69224, 0, 0, 0.61111], + "8873": [0, 0.69224, 0, 0, 0.72222], + "8874": [0, 0.69224, 0, 0, 0.88889], + "8876": [0, 0.68889, 0, 0, 0.61111], + "8877": [0, 0.68889, 0, 0, 0.61111], + "8878": [0, 0.68889, 0, 0, 0.72222], + "8879": [0, 0.68889, 0, 0, 0.72222], + "8882": [0.03517, 0.54986, 0, 0, 0.77778], + "8883": [0.03517, 0.54986, 0, 0, 0.77778], + "8884": [0.13667, 0.63667, 0, 0, 0.77778], + "8885": [0.13667, 0.63667, 0, 0, 0.77778], + "8888": [0, 0.54986, 0, 0, 1.11111], + "8890": [0.19444, 0.43056, 0, 0, 0.55556], + "8891": [0.19444, 0.69224, 0, 0, 0.61111], + "8892": [0.19444, 0.69224, 0, 0, 0.61111], + "8901": [0, 0.54986, 0, 0, 0.27778], + "8903": [0.08167, 0.58167, 0, 0, 0.77778], + "8905": [0.08167, 0.58167, 0, 0, 0.77778], + "8906": [0.08167, 0.58167, 0, 0, 0.77778], + "8907": [0, 0.69224, 0, 0, 0.77778], + "8908": [0, 0.69224, 0, 0, 0.77778], + "8909": [-0.03598, 0.46402, 0, 0, 0.77778], + "8910": [0, 0.54986, 0, 0, 0.76042], + "8911": [0, 0.54986, 0, 0, 0.76042], + "8912": [0.03517, 0.54986, 0, 0, 0.77778], + "8913": [0.03517, 0.54986, 0, 0, 0.77778], + "8914": [0, 0.54986, 0, 0, 0.66667], + "8915": [0, 0.54986, 0, 0, 0.66667], + "8916": [0, 0.69224, 0, 0, 0.66667], + "8918": [0.0391, 0.5391, 0, 0, 0.77778], + "8919": [0.0391, 0.5391, 0, 0, 0.77778], + "8920": [0.03517, 0.54986, 0, 0, 1.33334], + "8921": [0.03517, 0.54986, 0, 0, 1.33334], + "8922": [0.38569, 0.88569, 0, 0, 0.77778], + "8923": [0.38569, 0.88569, 0, 0, 0.77778], + "8926": [0.13667, 0.63667, 0, 0, 0.77778], + "8927": [0.13667, 0.63667, 0, 0, 0.77778], + "8928": [0.30274, 0.79383, 0, 0, 0.77778], + "8929": [0.30274, 0.79383, 0, 0, 0.77778], + "8934": [0.23222, 0.74111, 0, 0, 0.77778], + "8935": [0.23222, 0.74111, 0, 0, 0.77778], + "8936": [0.23222, 0.74111, 0, 0, 0.77778], + "8937": [0.23222, 0.74111, 0, 0, 0.77778], + "8938": [0.20576, 0.70576, 0, 0, 0.77778], + "8939": [0.20576, 0.70576, 0, 0, 0.77778], + "8940": [0.30274, 0.79383, 0, 0, 0.77778], + "8941": [0.30274, 0.79383, 0, 0, 0.77778], + "8994": [0.19444, 0.69224, 0, 0, 0.77778], + "8995": [0.19444, 0.69224, 0, 0, 0.77778], + "9416": [0.15559, 0.69224, 0, 0, 0.90222], + "9484": [0, 0.69224, 0, 0, 0.5], + "9488": [0, 0.69224, 0, 0, 0.5], + "9492": [0, 0.37788, 0, 0, 0.5], + "9496": [0, 0.37788, 0, 0, 0.5], + "9585": [0.19444, 0.68889, 0, 0, 0.88889], + "9586": [0.19444, 0.74111, 0, 0, 0.88889], + "9632": [0, 0.675, 0, 0, 0.77778], + "9633": [0, 0.675, 0, 0, 0.77778], + "9650": [0, 0.54986, 0, 0, 0.72222], + "9651": [0, 0.54986, 0, 0, 0.72222], + "9654": [0.03517, 0.54986, 0, 0, 0.77778], + "9660": [0, 0.54986, 0, 0, 0.72222], + "9661": [0, 0.54986, 0, 0, 0.72222], + "9664": [0.03517, 0.54986, 0, 0, 0.77778], + "9674": [0.11111, 0.69224, 0, 0, 0.66667], + "9733": [0.19444, 0.69224, 0, 0, 0.94445], + "10003": [0, 0.69224, 0, 0, 0.83334], + "10016": [0, 0.69224, 0, 0, 0.83334], + "10731": [0.11111, 0.69224, 0, 0, 0.66667], + "10846": [0.19444, 0.75583, 0, 0, 0.61111], + "10877": [0.13667, 0.63667, 0, 0, 0.77778], + "10878": [0.13667, 0.63667, 0, 0, 0.77778], + "10885": [0.25583, 0.75583, 0, 0, 0.77778], + "10886": [0.25583, 0.75583, 0, 0, 0.77778], + "10887": [0.13597, 0.63597, 0, 0, 0.77778], + "10888": [0.13597, 0.63597, 0, 0, 0.77778], + "10889": [0.26167, 0.75726, 0, 0, 0.77778], + "10890": [0.26167, 0.75726, 0, 0, 0.77778], + "10891": [0.48256, 0.98256, 0, 0, 0.77778], + "10892": [0.48256, 0.98256, 0, 0, 0.77778], + "10901": [0.13667, 0.63667, 0, 0, 0.77778], + "10902": [0.13667, 0.63667, 0, 0, 0.77778], + "10933": [0.25142, 0.75726, 0, 0, 0.77778], + "10934": [0.25142, 0.75726, 0, 0, 0.77778], + "10935": [0.26167, 0.75726, 0, 0, 0.77778], + "10936": [0.26167, 0.75726, 0, 0, 0.77778], + "10937": [0.26167, 0.75726, 0, 0, 0.77778], + "10938": [0.26167, 0.75726, 0, 0, 0.77778], + "10949": [0.25583, 0.75583, 0, 0, 0.77778], + "10950": [0.25583, 0.75583, 0, 0, 0.77778], + "10955": [0.28481, 0.79383, 0, 0, 0.77778], + "10956": [0.28481, 0.79383, 0, 0, 0.77778], + "57350": [0.08167, 0.58167, 0, 0, 0.22222], + "57351": [0.08167, 0.58167, 0, 0, 0.38889], + "57352": [0.08167, 0.58167, 0, 0, 0.77778], + "57353": [0, 0.43056, 0.04028, 0, 0.66667], + "57356": [0.25142, 0.75726, 0, 0, 0.77778], + "57357": [0.25142, 0.75726, 0, 0, 0.77778], + "57358": [0.41951, 0.91951, 0, 0, 0.77778], + "57359": [0.30274, 0.79383, 0, 0, 0.77778], + "57360": [0.30274, 0.79383, 0, 0, 0.77778], + "57361": [0.41951, 0.91951, 0, 0, 0.77778], + "57366": [0.25142, 0.75726, 0, 0, 0.77778], + "57367": [0.25142, 0.75726, 0, 0, 0.77778], + "57368": [0.25142, 0.75726, 0, 0, 0.77778], + "57369": [0.25142, 0.75726, 0, 0, 0.77778], + "57370": [0.13597, 0.63597, 0, 0, 0.77778], + "57371": [0.13597, 0.63597, 0, 0, 0.77778] + }, + "Caligraphic-Regular": { + "32": [0, 0, 0, 0, 0.25], + "65": [0, 0.68333, 0, 0.19445, 0.79847], + "66": [0, 0.68333, 0.03041, 0.13889, 0.65681], + "67": [0, 0.68333, 0.05834, 0.13889, 0.52653], + "68": [0, 0.68333, 0.02778, 0.08334, 0.77139], + "69": [0, 0.68333, 0.08944, 0.11111, 0.52778], + "70": [0, 0.68333, 0.09931, 0.11111, 0.71875], + "71": [0.09722, 0.68333, 0.0593, 0.11111, 0.59487], + "72": [0, 0.68333, 0.00965, 0.11111, 0.84452], + "73": [0, 0.68333, 0.07382, 0, 0.54452], + "74": [0.09722, 0.68333, 0.18472, 0.16667, 0.67778], + "75": [0, 0.68333, 0.01445, 0.05556, 0.76195], + "76": [0, 0.68333, 0, 0.13889, 0.68972], + "77": [0, 0.68333, 0, 0.13889, 1.2009], + "78": [0, 0.68333, 0.14736, 0.08334, 0.82049], + "79": [0, 0.68333, 0.02778, 0.11111, 0.79611], + "80": [0, 0.68333, 0.08222, 0.08334, 0.69556], + "81": [0.09722, 0.68333, 0, 0.11111, 0.81667], + "82": [0, 0.68333, 0, 0.08334, 0.8475], + "83": [0, 0.68333, 0.075, 0.13889, 0.60556], + "84": [0, 0.68333, 0.25417, 0, 0.54464], + "85": [0, 0.68333, 0.09931, 0.08334, 0.62583], + "86": [0, 0.68333, 0.08222, 0, 0.61278], + "87": [0, 0.68333, 0.08222, 0.08334, 0.98778], + "88": [0, 0.68333, 0.14643, 0.13889, 0.7133], + "89": [0.09722, 0.68333, 0.08222, 0.08334, 0.66834], + "90": [0, 0.68333, 0.07944, 0.13889, 0.72473], + "160": [0, 0, 0, 0, 0.25] + }, + "Fraktur-Regular": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69141, 0, 0, 0.29574], + "34": [0, 0.69141, 0, 0, 0.21471], + "38": [0, 0.69141, 0, 0, 0.73786], + "39": [0, 0.69141, 0, 0, 0.21201], + "40": [0.24982, 0.74947, 0, 0, 0.38865], + "41": [0.24982, 0.74947, 0, 0, 0.38865], + "42": [0, 0.62119, 0, 0, 0.27764], + "43": [0.08319, 0.58283, 0, 0, 0.75623], + "44": [0, 0.10803, 0, 0, 0.27764], + "45": [0.08319, 0.58283, 0, 0, 0.75623], + "46": [0, 0.10803, 0, 0, 0.27764], + "47": [0.24982, 0.74947, 0, 0, 0.50181], + "48": [0, 0.47534, 0, 0, 0.50181], + "49": [0, 0.47534, 0, 0, 0.50181], + "50": [0, 0.47534, 0, 0, 0.50181], + "51": [0.18906, 0.47534, 0, 0, 0.50181], + "52": [0.18906, 0.47534, 0, 0, 0.50181], + "53": [0.18906, 0.47534, 0, 0, 0.50181], + "54": [0, 0.69141, 0, 0, 0.50181], + "55": [0.18906, 0.47534, 0, 0, 0.50181], + "56": [0, 0.69141, 0, 0, 0.50181], + "57": [0.18906, 0.47534, 0, 0, 0.50181], + "58": [0, 0.47534, 0, 0, 0.21606], + "59": [0.12604, 0.47534, 0, 0, 0.21606], + "61": [-0.13099, 0.36866, 0, 0, 0.75623], + "63": [0, 0.69141, 0, 0, 0.36245], + "65": [0, 0.69141, 0, 0, 0.7176], + "66": [0, 0.69141, 0, 0, 0.88397], + "67": [0, 0.69141, 0, 0, 0.61254], + "68": [0, 0.69141, 0, 0, 0.83158], + "69": [0, 0.69141, 0, 0, 0.66278], + "70": [0.12604, 0.69141, 0, 0, 0.61119], + "71": [0, 0.69141, 0, 0, 0.78539], + "72": [0.06302, 0.69141, 0, 0, 0.7203], + "73": [0, 0.69141, 0, 0, 0.55448], + "74": [0.12604, 0.69141, 0, 0, 0.55231], + "75": [0, 0.69141, 0, 0, 0.66845], + "76": [0, 0.69141, 0, 0, 0.66602], + "77": [0, 0.69141, 0, 0, 1.04953], + "78": [0, 0.69141, 0, 0, 0.83212], + "79": [0, 0.69141, 0, 0, 0.82699], + "80": [0.18906, 0.69141, 0, 0, 0.82753], + "81": [0.03781, 0.69141, 0, 0, 0.82699], + "82": [0, 0.69141, 0, 0, 0.82807], + "83": [0, 0.69141, 0, 0, 0.82861], + "84": [0, 0.69141, 0, 0, 0.66899], + "85": [0, 0.69141, 0, 0, 0.64576], + "86": [0, 0.69141, 0, 0, 0.83131], + "87": [0, 0.69141, 0, 0, 1.04602], + "88": [0, 0.69141, 0, 0, 0.71922], + "89": [0.18906, 0.69141, 0, 0, 0.83293], + "90": [0.12604, 0.69141, 0, 0, 0.60201], + "91": [0.24982, 0.74947, 0, 0, 0.27764], + "93": [0.24982, 0.74947, 0, 0, 0.27764], + "94": [0, 0.69141, 0, 0, 0.49965], + "97": [0, 0.47534, 0, 0, 0.50046], + "98": [0, 0.69141, 0, 0, 0.51315], + "99": [0, 0.47534, 0, 0, 0.38946], + "100": [0, 0.62119, 0, 0, 0.49857], + "101": [0, 0.47534, 0, 0, 0.40053], + "102": [0.18906, 0.69141, 0, 0, 0.32626], + "103": [0.18906, 0.47534, 0, 0, 0.5037], + "104": [0.18906, 0.69141, 0, 0, 0.52126], + "105": [0, 0.69141, 0, 0, 0.27899], + "106": [0, 0.69141, 0, 0, 0.28088], + "107": [0, 0.69141, 0, 0, 0.38946], + "108": [0, 0.69141, 0, 0, 0.27953], + "109": [0, 0.47534, 0, 0, 0.76676], + "110": [0, 0.47534, 0, 0, 0.52666], + "111": [0, 0.47534, 0, 0, 0.48885], + "112": [0.18906, 0.52396, 0, 0, 0.50046], + "113": [0.18906, 0.47534, 0, 0, 0.48912], + "114": [0, 0.47534, 0, 0, 0.38919], + "115": [0, 0.47534, 0, 0, 0.44266], + "116": [0, 0.62119, 0, 0, 0.33301], + "117": [0, 0.47534, 0, 0, 0.5172], + "118": [0, 0.52396, 0, 0, 0.5118], + "119": [0, 0.52396, 0, 0, 0.77351], + "120": [0.18906, 0.47534, 0, 0, 0.38865], + "121": [0.18906, 0.47534, 0, 0, 0.49884], + "122": [0.18906, 0.47534, 0, 0, 0.39054], + "160": [0, 0, 0, 0, 0.25], + "8216": [0, 0.69141, 0, 0, 0.21471], + "8217": [0, 0.69141, 0, 0, 0.21471], + "58112": [0, 0.62119, 0, 0, 0.49749], + "58113": [0, 0.62119, 0, 0, 0.4983], + "58114": [0.18906, 0.69141, 0, 0, 0.33328], + "58115": [0.18906, 0.69141, 0, 0, 0.32923], + "58116": [0.18906, 0.47534, 0, 0, 0.50343], + "58117": [0, 0.69141, 0, 0, 0.33301], + "58118": [0, 0.62119, 0, 0, 0.33409], + "58119": [0, 0.47534, 0, 0, 0.50073] + }, + "Main-Bold": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0, 0, 0.35], + "34": [0, 0.69444, 0, 0, 0.60278], + "35": [0.19444, 0.69444, 0, 0, 0.95833], + "36": [0.05556, 0.75, 0, 0, 0.575], + "37": [0.05556, 0.75, 0, 0, 0.95833], + "38": [0, 0.69444, 0, 0, 0.89444], + "39": [0, 0.69444, 0, 0, 0.31944], + "40": [0.25, 0.75, 0, 0, 0.44722], + "41": [0.25, 0.75, 0, 0, 0.44722], + "42": [0, 0.75, 0, 0, 0.575], + "43": [0.13333, 0.63333, 0, 0, 0.89444], + "44": [0.19444, 0.15556, 0, 0, 0.31944], + "45": [0, 0.44444, 0, 0, 0.38333], + "46": [0, 0.15556, 0, 0, 0.31944], + "47": [0.25, 0.75, 0, 0, 0.575], + "48": [0, 0.64444, 0, 0, 0.575], + "49": [0, 0.64444, 0, 0, 0.575], + "50": [0, 0.64444, 0, 0, 0.575], + "51": [0, 0.64444, 0, 0, 0.575], + "52": [0, 0.64444, 0, 0, 0.575], + "53": [0, 0.64444, 0, 0, 0.575], + "54": [0, 0.64444, 0, 0, 0.575], + "55": [0, 0.64444, 0, 0, 0.575], + "56": [0, 0.64444, 0, 0, 0.575], + "57": [0, 0.64444, 0, 0, 0.575], + "58": [0, 0.44444, 0, 0, 0.31944], + "59": [0.19444, 0.44444, 0, 0, 0.31944], + "60": [0.08556, 0.58556, 0, 0, 0.89444], + "61": [-0.10889, 0.39111, 0, 0, 0.89444], + "62": [0.08556, 0.58556, 0, 0, 0.89444], + "63": [0, 0.69444, 0, 0, 0.54305], + "64": [0, 0.69444, 0, 0, 0.89444], + "65": [0, 0.68611, 0, 0, 0.86944], + "66": [0, 0.68611, 0, 0, 0.81805], + "67": [0, 0.68611, 0, 0, 0.83055], + "68": [0, 0.68611, 0, 0, 0.88194], + "69": [0, 0.68611, 0, 0, 0.75555], + "70": [0, 0.68611, 0, 0, 0.72361], + "71": [0, 0.68611, 0, 0, 0.90416], + "72": [0, 0.68611, 0, 0, 0.9], + "73": [0, 0.68611, 0, 0, 0.43611], + "74": [0, 0.68611, 0, 0, 0.59444], + "75": [0, 0.68611, 0, 0, 0.90138], + "76": [0, 0.68611, 0, 0, 0.69166], + "77": [0, 0.68611, 0, 0, 1.09166], + "78": [0, 0.68611, 0, 0, 0.9], + "79": [0, 0.68611, 0, 0, 0.86388], + "80": [0, 0.68611, 0, 0, 0.78611], + "81": [0.19444, 0.68611, 0, 0, 0.86388], + "82": [0, 0.68611, 0, 0, 0.8625], + "83": [0, 0.68611, 0, 0, 0.63889], + "84": [0, 0.68611, 0, 0, 0.8], + "85": [0, 0.68611, 0, 0, 0.88472], + "86": [0, 0.68611, 0.01597, 0, 0.86944], + "87": [0, 0.68611, 0.01597, 0, 1.18888], + "88": [0, 0.68611, 0, 0, 0.86944], + "89": [0, 0.68611, 0.02875, 0, 0.86944], + "90": [0, 0.68611, 0, 0, 0.70277], + "91": [0.25, 0.75, 0, 0, 0.31944], + "92": [0.25, 0.75, 0, 0, 0.575], + "93": [0.25, 0.75, 0, 0, 0.31944], + "94": [0, 0.69444, 0, 0, 0.575], + "95": [0.31, 0.13444, 0.03194, 0, 0.575], + "97": [0, 0.44444, 0, 0, 0.55902], + "98": [0, 0.69444, 0, 0, 0.63889], + "99": [0, 0.44444, 0, 0, 0.51111], + "100": [0, 0.69444, 0, 0, 0.63889], + "101": [0, 0.44444, 0, 0, 0.52708], + "102": [0, 0.69444, 0.10903, 0, 0.35139], + "103": [0.19444, 0.44444, 0.01597, 0, 0.575], + "104": [0, 0.69444, 0, 0, 0.63889], + "105": [0, 0.69444, 0, 0, 0.31944], + "106": [0.19444, 0.69444, 0, 0, 0.35139], + "107": [0, 0.69444, 0, 0, 0.60694], + "108": [0, 0.69444, 0, 0, 0.31944], + "109": [0, 0.44444, 0, 0, 0.95833], + "110": [0, 0.44444, 0, 0, 0.63889], + "111": [0, 0.44444, 0, 0, 0.575], + "112": [0.19444, 0.44444, 0, 0, 0.63889], + "113": [0.19444, 0.44444, 0, 0, 0.60694], + "114": [0, 0.44444, 0, 0, 0.47361], + "115": [0, 0.44444, 0, 0, 0.45361], + "116": [0, 0.63492, 0, 0, 0.44722], + "117": [0, 0.44444, 0, 0, 0.63889], + "118": [0, 0.44444, 0.01597, 0, 0.60694], + "119": [0, 0.44444, 0.01597, 0, 0.83055], + "120": [0, 0.44444, 0, 0, 0.60694], + "121": [0.19444, 0.44444, 0.01597, 0, 0.60694], + "122": [0, 0.44444, 0, 0, 0.51111], + "123": [0.25, 0.75, 0, 0, 0.575], + "124": [0.25, 0.75, 0, 0, 0.31944], + "125": [0.25, 0.75, 0, 0, 0.575], + "126": [0.35, 0.34444, 0, 0, 0.575], + "160": [0, 0, 0, 0, 0.25], + "163": [0, 0.69444, 0, 0, 0.86853], + "168": [0, 0.69444, 0, 0, 0.575], + "172": [0, 0.44444, 0, 0, 0.76666], + "176": [0, 0.69444, 0, 0, 0.86944], + "177": [0.13333, 0.63333, 0, 0, 0.89444], + "184": [0.17014, 0, 0, 0, 0.51111], + "198": [0, 0.68611, 0, 0, 1.04166], + "215": [0.13333, 0.63333, 0, 0, 0.89444], + "216": [0.04861, 0.73472, 0, 0, 0.89444], + "223": [0, 0.69444, 0, 0, 0.59722], + "230": [0, 0.44444, 0, 0, 0.83055], + "247": [0.13333, 0.63333, 0, 0, 0.89444], + "248": [0.09722, 0.54167, 0, 0, 0.575], + "305": [0, 0.44444, 0, 0, 0.31944], + "338": [0, 0.68611, 0, 0, 1.16944], + "339": [0, 0.44444, 0, 0, 0.89444], + "567": [0.19444, 0.44444, 0, 0, 0.35139], + "710": [0, 0.69444, 0, 0, 0.575], + "711": [0, 0.63194, 0, 0, 0.575], + "713": [0, 0.59611, 0, 0, 0.575], + "714": [0, 0.69444, 0, 0, 0.575], + "715": [0, 0.69444, 0, 0, 0.575], + "728": [0, 0.69444, 0, 0, 0.575], + "729": [0, 0.69444, 0, 0, 0.31944], + "730": [0, 0.69444, 0, 0, 0.86944], + "732": [0, 0.69444, 0, 0, 0.575], + "733": [0, 0.69444, 0, 0, 0.575], + "915": [0, 0.68611, 0, 0, 0.69166], + "916": [0, 0.68611, 0, 0, 0.95833], + "920": [0, 0.68611, 0, 0, 0.89444], + "923": [0, 0.68611, 0, 0, 0.80555], + "926": [0, 0.68611, 0, 0, 0.76666], + "928": [0, 0.68611, 0, 0, 0.9], + "931": [0, 0.68611, 0, 0, 0.83055], + "933": [0, 0.68611, 0, 0, 0.89444], + "934": [0, 0.68611, 0, 0, 0.83055], + "936": [0, 0.68611, 0, 0, 0.89444], + "937": [0, 0.68611, 0, 0, 0.83055], + "8211": [0, 0.44444, 0.03194, 0, 0.575], + "8212": [0, 0.44444, 0.03194, 0, 1.14999], + "8216": [0, 0.69444, 0, 0, 0.31944], + "8217": [0, 0.69444, 0, 0, 0.31944], + "8220": [0, 0.69444, 0, 0, 0.60278], + "8221": [0, 0.69444, 0, 0, 0.60278], + "8224": [0.19444, 0.69444, 0, 0, 0.51111], + "8225": [0.19444, 0.69444, 0, 0, 0.51111], + "8242": [0, 0.55556, 0, 0, 0.34444], + "8407": [0, 0.72444, 0.15486, 0, 0.575], + "8463": [0, 0.69444, 0, 0, 0.66759], + "8465": [0, 0.69444, 0, 0, 0.83055], + "8467": [0, 0.69444, 0, 0, 0.47361], + "8472": [0.19444, 0.44444, 0, 0, 0.74027], + "8476": [0, 0.69444, 0, 0, 0.83055], + "8501": [0, 0.69444, 0, 0, 0.70277], + "8592": [-0.10889, 0.39111, 0, 0, 1.14999], + "8593": [0.19444, 0.69444, 0, 0, 0.575], + "8594": [-0.10889, 0.39111, 0, 0, 1.14999], + "8595": [0.19444, 0.69444, 0, 0, 0.575], + "8596": [-0.10889, 0.39111, 0, 0, 1.14999], + "8597": [0.25, 0.75, 0, 0, 0.575], + "8598": [0.19444, 0.69444, 0, 0, 1.14999], + "8599": [0.19444, 0.69444, 0, 0, 1.14999], + "8600": [0.19444, 0.69444, 0, 0, 1.14999], + "8601": [0.19444, 0.69444, 0, 0, 1.14999], + "8636": [-0.10889, 0.39111, 0, 0, 1.14999], + "8637": [-0.10889, 0.39111, 0, 0, 1.14999], + "8640": [-0.10889, 0.39111, 0, 0, 1.14999], + "8641": [-0.10889, 0.39111, 0, 0, 1.14999], + "8656": [-0.10889, 0.39111, 0, 0, 1.14999], + "8657": [0.19444, 0.69444, 0, 0, 0.70277], + "8658": [-0.10889, 0.39111, 0, 0, 1.14999], + "8659": [0.19444, 0.69444, 0, 0, 0.70277], + "8660": [-0.10889, 0.39111, 0, 0, 1.14999], + "8661": [0.25, 0.75, 0, 0, 0.70277], + "8704": [0, 0.69444, 0, 0, 0.63889], + "8706": [0, 0.69444, 0.06389, 0, 0.62847], + "8707": [0, 0.69444, 0, 0, 0.63889], + "8709": [0.05556, 0.75, 0, 0, 0.575], + "8711": [0, 0.68611, 0, 0, 0.95833], + "8712": [0.08556, 0.58556, 0, 0, 0.76666], + "8715": [0.08556, 0.58556, 0, 0, 0.76666], + "8722": [0.13333, 0.63333, 0, 0, 0.89444], + "8723": [0.13333, 0.63333, 0, 0, 0.89444], + "8725": [0.25, 0.75, 0, 0, 0.575], + "8726": [0.25, 0.75, 0, 0, 0.575], + "8727": [-0.02778, 0.47222, 0, 0, 0.575], + "8728": [-0.02639, 0.47361, 0, 0, 0.575], + "8729": [-0.02639, 0.47361, 0, 0, 0.575], + "8730": [0.18, 0.82, 0, 0, 0.95833], + "8733": [0, 0.44444, 0, 0, 0.89444], + "8734": [0, 0.44444, 0, 0, 1.14999], + "8736": [0, 0.69224, 0, 0, 0.72222], + "8739": [0.25, 0.75, 0, 0, 0.31944], + "8741": [0.25, 0.75, 0, 0, 0.575], + "8743": [0, 0.55556, 0, 0, 0.76666], + "8744": [0, 0.55556, 0, 0, 0.76666], + "8745": [0, 0.55556, 0, 0, 0.76666], + "8746": [0, 0.55556, 0, 0, 0.76666], + "8747": [0.19444, 0.69444, 0.12778, 0, 0.56875], + "8764": [-0.10889, 0.39111, 0, 0, 0.89444], + "8768": [0.19444, 0.69444, 0, 0, 0.31944], + "8771": [0.00222, 0.50222, 0, 0, 0.89444], + "8773": [0.027, 0.638, 0, 0, 0.894], + "8776": [0.02444, 0.52444, 0, 0, 0.89444], + "8781": [0.00222, 0.50222, 0, 0, 0.89444], + "8801": [0.00222, 0.50222, 0, 0, 0.89444], + "8804": [0.19667, 0.69667, 0, 0, 0.89444], + "8805": [0.19667, 0.69667, 0, 0, 0.89444], + "8810": [0.08556, 0.58556, 0, 0, 1.14999], + "8811": [0.08556, 0.58556, 0, 0, 1.14999], + "8826": [0.08556, 0.58556, 0, 0, 0.89444], + "8827": [0.08556, 0.58556, 0, 0, 0.89444], + "8834": [0.08556, 0.58556, 0, 0, 0.89444], + "8835": [0.08556, 0.58556, 0, 0, 0.89444], + "8838": [0.19667, 0.69667, 0, 0, 0.89444], + "8839": [0.19667, 0.69667, 0, 0, 0.89444], + "8846": [0, 0.55556, 0, 0, 0.76666], + "8849": [0.19667, 0.69667, 0, 0, 0.89444], + "8850": [0.19667, 0.69667, 0, 0, 0.89444], + "8851": [0, 0.55556, 0, 0, 0.76666], + "8852": [0, 0.55556, 0, 0, 0.76666], + "8853": [0.13333, 0.63333, 0, 0, 0.89444], + "8854": [0.13333, 0.63333, 0, 0, 0.89444], + "8855": [0.13333, 0.63333, 0, 0, 0.89444], + "8856": [0.13333, 0.63333, 0, 0, 0.89444], + "8857": [0.13333, 0.63333, 0, 0, 0.89444], + "8866": [0, 0.69444, 0, 0, 0.70277], + "8867": [0, 0.69444, 0, 0, 0.70277], + "8868": [0, 0.69444, 0, 0, 0.89444], + "8869": [0, 0.69444, 0, 0, 0.89444], + "8900": [-0.02639, 0.47361, 0, 0, 0.575], + "8901": [-0.02639, 0.47361, 0, 0, 0.31944], + "8902": [-0.02778, 0.47222, 0, 0, 0.575], + "8968": [0.25, 0.75, 0, 0, 0.51111], + "8969": [0.25, 0.75, 0, 0, 0.51111], + "8970": [0.25, 0.75, 0, 0, 0.51111], + "8971": [0.25, 0.75, 0, 0, 0.51111], + "8994": [-0.13889, 0.36111, 0, 0, 1.14999], + "8995": [-0.13889, 0.36111, 0, 0, 1.14999], + "9651": [0.19444, 0.69444, 0, 0, 1.02222], + "9657": [-0.02778, 0.47222, 0, 0, 0.575], + "9661": [0.19444, 0.69444, 0, 0, 1.02222], + "9667": [-0.02778, 0.47222, 0, 0, 0.575], + "9711": [0.19444, 0.69444, 0, 0, 1.14999], + "9824": [0.12963, 0.69444, 0, 0, 0.89444], + "9825": [0.12963, 0.69444, 0, 0, 0.89444], + "9826": [0.12963, 0.69444, 0, 0, 0.89444], + "9827": [0.12963, 0.69444, 0, 0, 0.89444], + "9837": [0, 0.75, 0, 0, 0.44722], + "9838": [0.19444, 0.69444, 0, 0, 0.44722], + "9839": [0.19444, 0.69444, 0, 0, 0.44722], + "10216": [0.25, 0.75, 0, 0, 0.44722], + "10217": [0.25, 0.75, 0, 0, 0.44722], + "10815": [0, 0.68611, 0, 0, 0.9], + "10927": [0.19667, 0.69667, 0, 0, 0.89444], + "10928": [0.19667, 0.69667, 0, 0, 0.89444], + "57376": [0.19444, 0.69444, 0, 0, 0] + }, + "Main-BoldItalic": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0.11417, 0, 0.38611], + "34": [0, 0.69444, 0.07939, 0, 0.62055], + "35": [0.19444, 0.69444, 0.06833, 0, 0.94444], + "37": [0.05556, 0.75, 0.12861, 0, 0.94444], + "38": [0, 0.69444, 0.08528, 0, 0.88555], + "39": [0, 0.69444, 0.12945, 0, 0.35555], + "40": [0.25, 0.75, 0.15806, 0, 0.47333], + "41": [0.25, 0.75, 0.03306, 0, 0.47333], + "42": [0, 0.75, 0.14333, 0, 0.59111], + "43": [0.10333, 0.60333, 0.03306, 0, 0.88555], + "44": [0.19444, 0.14722, 0, 0, 0.35555], + "45": [0, 0.44444, 0.02611, 0, 0.41444], + "46": [0, 0.14722, 0, 0, 0.35555], + "47": [0.25, 0.75, 0.15806, 0, 0.59111], + "48": [0, 0.64444, 0.13167, 0, 0.59111], + "49": [0, 0.64444, 0.13167, 0, 0.59111], + "50": [0, 0.64444, 0.13167, 0, 0.59111], + "51": [0, 0.64444, 0.13167, 0, 0.59111], + "52": [0.19444, 0.64444, 0.13167, 0, 0.59111], + "53": [0, 0.64444, 0.13167, 0, 0.59111], + "54": [0, 0.64444, 0.13167, 0, 0.59111], + "55": [0.19444, 0.64444, 0.13167, 0, 0.59111], + "56": [0, 0.64444, 0.13167, 0, 0.59111], + "57": [0, 0.64444, 0.13167, 0, 0.59111], + "58": [0, 0.44444, 0.06695, 0, 0.35555], + "59": [0.19444, 0.44444, 0.06695, 0, 0.35555], + "61": [-0.10889, 0.39111, 0.06833, 0, 0.88555], + "63": [0, 0.69444, 0.11472, 0, 0.59111], + "64": [0, 0.69444, 0.09208, 0, 0.88555], + "65": [0, 0.68611, 0, 0, 0.86555], + "66": [0, 0.68611, 0.0992, 0, 0.81666], + "67": [0, 0.68611, 0.14208, 0, 0.82666], + "68": [0, 0.68611, 0.09062, 0, 0.87555], + "69": [0, 0.68611, 0.11431, 0, 0.75666], + "70": [0, 0.68611, 0.12903, 0, 0.72722], + "71": [0, 0.68611, 0.07347, 0, 0.89527], + "72": [0, 0.68611, 0.17208, 0, 0.8961], + "73": [0, 0.68611, 0.15681, 0, 0.47166], + "74": [0, 0.68611, 0.145, 0, 0.61055], + "75": [0, 0.68611, 0.14208, 0, 0.89499], + "76": [0, 0.68611, 0, 0, 0.69777], + "77": [0, 0.68611, 0.17208, 0, 1.07277], + "78": [0, 0.68611, 0.17208, 0, 0.8961], + "79": [0, 0.68611, 0.09062, 0, 0.85499], + "80": [0, 0.68611, 0.0992, 0, 0.78721], + "81": [0.19444, 0.68611, 0.09062, 0, 0.85499], + "82": [0, 0.68611, 0.02559, 0, 0.85944], + "83": [0, 0.68611, 0.11264, 0, 0.64999], + "84": [0, 0.68611, 0.12903, 0, 0.7961], + "85": [0, 0.68611, 0.17208, 0, 0.88083], + "86": [0, 0.68611, 0.18625, 0, 0.86555], + "87": [0, 0.68611, 0.18625, 0, 1.15999], + "88": [0, 0.68611, 0.15681, 0, 0.86555], + "89": [0, 0.68611, 0.19803, 0, 0.86555], + "90": [0, 0.68611, 0.14208, 0, 0.70888], + "91": [0.25, 0.75, 0.1875, 0, 0.35611], + "93": [0.25, 0.75, 0.09972, 0, 0.35611], + "94": [0, 0.69444, 0.06709, 0, 0.59111], + "95": [0.31, 0.13444, 0.09811, 0, 0.59111], + "97": [0, 0.44444, 0.09426, 0, 0.59111], + "98": [0, 0.69444, 0.07861, 0, 0.53222], + "99": [0, 0.44444, 0.05222, 0, 0.53222], + "100": [0, 0.69444, 0.10861, 0, 0.59111], + "101": [0, 0.44444, 0.085, 0, 0.53222], + "102": [0.19444, 0.69444, 0.21778, 0, 0.4], + "103": [0.19444, 0.44444, 0.105, 0, 0.53222], + "104": [0, 0.69444, 0.09426, 0, 0.59111], + "105": [0, 0.69326, 0.11387, 0, 0.35555], + "106": [0.19444, 0.69326, 0.1672, 0, 0.35555], + "107": [0, 0.69444, 0.11111, 0, 0.53222], + "108": [0, 0.69444, 0.10861, 0, 0.29666], + "109": [0, 0.44444, 0.09426, 0, 0.94444], + "110": [0, 0.44444, 0.09426, 0, 0.64999], + "111": [0, 0.44444, 0.07861, 0, 0.59111], + "112": [0.19444, 0.44444, 0.07861, 0, 0.59111], + "113": [0.19444, 0.44444, 0.105, 0, 0.53222], + "114": [0, 0.44444, 0.11111, 0, 0.50167], + "115": [0, 0.44444, 0.08167, 0, 0.48694], + "116": [0, 0.63492, 0.09639, 0, 0.385], + "117": [0, 0.44444, 0.09426, 0, 0.62055], + "118": [0, 0.44444, 0.11111, 0, 0.53222], + "119": [0, 0.44444, 0.11111, 0, 0.76777], + "120": [0, 0.44444, 0.12583, 0, 0.56055], + "121": [0.19444, 0.44444, 0.105, 0, 0.56166], + "122": [0, 0.44444, 0.13889, 0, 0.49055], + "126": [0.35, 0.34444, 0.11472, 0, 0.59111], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.69444, 0.11473, 0, 0.59111], + "176": [0, 0.69444, 0, 0, 0.94888], + "184": [0.17014, 0, 0, 0, 0.53222], + "198": [0, 0.68611, 0.11431, 0, 1.02277], + "216": [0.04861, 0.73472, 0.09062, 0, 0.88555], + "223": [0.19444, 0.69444, 0.09736, 0, 0.665], + "230": [0, 0.44444, 0.085, 0, 0.82666], + "248": [0.09722, 0.54167, 0.09458, 0, 0.59111], + "305": [0, 0.44444, 0.09426, 0, 0.35555], + "338": [0, 0.68611, 0.11431, 0, 1.14054], + "339": [0, 0.44444, 0.085, 0, 0.82666], + "567": [0.19444, 0.44444, 0.04611, 0, 0.385], + "710": [0, 0.69444, 0.06709, 0, 0.59111], + "711": [0, 0.63194, 0.08271, 0, 0.59111], + "713": [0, 0.59444, 0.10444, 0, 0.59111], + "714": [0, 0.69444, 0.08528, 0, 0.59111], + "715": [0, 0.69444, 0, 0, 0.59111], + "728": [0, 0.69444, 0.10333, 0, 0.59111], + "729": [0, 0.69444, 0.12945, 0, 0.35555], + "730": [0, 0.69444, 0, 0, 0.94888], + "732": [0, 0.69444, 0.11472, 0, 0.59111], + "733": [0, 0.69444, 0.11472, 0, 0.59111], + "915": [0, 0.68611, 0.12903, 0, 0.69777], + "916": [0, 0.68611, 0, 0, 0.94444], + "920": [0, 0.68611, 0.09062, 0, 0.88555], + "923": [0, 0.68611, 0, 0, 0.80666], + "926": [0, 0.68611, 0.15092, 0, 0.76777], + "928": [0, 0.68611, 0.17208, 0, 0.8961], + "931": [0, 0.68611, 0.11431, 0, 0.82666], + "933": [0, 0.68611, 0.10778, 0, 0.88555], + "934": [0, 0.68611, 0.05632, 0, 0.82666], + "936": [0, 0.68611, 0.10778, 0, 0.88555], + "937": [0, 0.68611, 0.0992, 0, 0.82666], + "8211": [0, 0.44444, 0.09811, 0, 0.59111], + "8212": [0, 0.44444, 0.09811, 0, 1.18221], + "8216": [0, 0.69444, 0.12945, 0, 0.35555], + "8217": [0, 0.69444, 0.12945, 0, 0.35555], + "8220": [0, 0.69444, 0.16772, 0, 0.62055], + "8221": [0, 0.69444, 0.07939, 0, 0.62055] + }, + "Main-Italic": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0.12417, 0, 0.30667], + "34": [0, 0.69444, 0.06961, 0, 0.51444], + "35": [0.19444, 0.69444, 0.06616, 0, 0.81777], + "37": [0.05556, 0.75, 0.13639, 0, 0.81777], + "38": [0, 0.69444, 0.09694, 0, 0.76666], + "39": [0, 0.69444, 0.12417, 0, 0.30667], + "40": [0.25, 0.75, 0.16194, 0, 0.40889], + "41": [0.25, 0.75, 0.03694, 0, 0.40889], + "42": [0, 0.75, 0.14917, 0, 0.51111], + "43": [0.05667, 0.56167, 0.03694, 0, 0.76666], + "44": [0.19444, 0.10556, 0, 0, 0.30667], + "45": [0, 0.43056, 0.02826, 0, 0.35778], + "46": [0, 0.10556, 0, 0, 0.30667], + "47": [0.25, 0.75, 0.16194, 0, 0.51111], + "48": [0, 0.64444, 0.13556, 0, 0.51111], + "49": [0, 0.64444, 0.13556, 0, 0.51111], + "50": [0, 0.64444, 0.13556, 0, 0.51111], + "51": [0, 0.64444, 0.13556, 0, 0.51111], + "52": [0.19444, 0.64444, 0.13556, 0, 0.51111], + "53": [0, 0.64444, 0.13556, 0, 0.51111], + "54": [0, 0.64444, 0.13556, 0, 0.51111], + "55": [0.19444, 0.64444, 0.13556, 0, 0.51111], + "56": [0, 0.64444, 0.13556, 0, 0.51111], + "57": [0, 0.64444, 0.13556, 0, 0.51111], + "58": [0, 0.43056, 0.0582, 0, 0.30667], + "59": [0.19444, 0.43056, 0.0582, 0, 0.30667], + "61": [-0.13313, 0.36687, 0.06616, 0, 0.76666], + "63": [0, 0.69444, 0.1225, 0, 0.51111], + "64": [0, 0.69444, 0.09597, 0, 0.76666], + "65": [0, 0.68333, 0, 0, 0.74333], + "66": [0, 0.68333, 0.10257, 0, 0.70389], + "67": [0, 0.68333, 0.14528, 0, 0.71555], + "68": [0, 0.68333, 0.09403, 0, 0.755], + "69": [0, 0.68333, 0.12028, 0, 0.67833], + "70": [0, 0.68333, 0.13305, 0, 0.65277], + "71": [0, 0.68333, 0.08722, 0, 0.77361], + "72": [0, 0.68333, 0.16389, 0, 0.74333], + "73": [0, 0.68333, 0.15806, 0, 0.38555], + "74": [0, 0.68333, 0.14028, 0, 0.525], + "75": [0, 0.68333, 0.14528, 0, 0.76888], + "76": [0, 0.68333, 0, 0, 0.62722], + "77": [0, 0.68333, 0.16389, 0, 0.89666], + "78": [0, 0.68333, 0.16389, 0, 0.74333], + "79": [0, 0.68333, 0.09403, 0, 0.76666], + "80": [0, 0.68333, 0.10257, 0, 0.67833], + "81": [0.19444, 0.68333, 0.09403, 0, 0.76666], + "82": [0, 0.68333, 0.03868, 0, 0.72944], + "83": [0, 0.68333, 0.11972, 0, 0.56222], + "84": [0, 0.68333, 0.13305, 0, 0.71555], + "85": [0, 0.68333, 0.16389, 0, 0.74333], + "86": [0, 0.68333, 0.18361, 0, 0.74333], + "87": [0, 0.68333, 0.18361, 0, 0.99888], + "88": [0, 0.68333, 0.15806, 0, 0.74333], + "89": [0, 0.68333, 0.19383, 0, 0.74333], + "90": [0, 0.68333, 0.14528, 0, 0.61333], + "91": [0.25, 0.75, 0.1875, 0, 0.30667], + "93": [0.25, 0.75, 0.10528, 0, 0.30667], + "94": [0, 0.69444, 0.06646, 0, 0.51111], + "95": [0.31, 0.12056, 0.09208, 0, 0.51111], + "97": [0, 0.43056, 0.07671, 0, 0.51111], + "98": [0, 0.69444, 0.06312, 0, 0.46], + "99": [0, 0.43056, 0.05653, 0, 0.46], + "100": [0, 0.69444, 0.10333, 0, 0.51111], + "101": [0, 0.43056, 0.07514, 0, 0.46], + "102": [0.19444, 0.69444, 0.21194, 0, 0.30667], + "103": [0.19444, 0.43056, 0.08847, 0, 0.46], + "104": [0, 0.69444, 0.07671, 0, 0.51111], + "105": [0, 0.65536, 0.1019, 0, 0.30667], + "106": [0.19444, 0.65536, 0.14467, 0, 0.30667], + "107": [0, 0.69444, 0.10764, 0, 0.46], + "108": [0, 0.69444, 0.10333, 0, 0.25555], + "109": [0, 0.43056, 0.07671, 0, 0.81777], + "110": [0, 0.43056, 0.07671, 0, 0.56222], + "111": [0, 0.43056, 0.06312, 0, 0.51111], + "112": [0.19444, 0.43056, 0.06312, 0, 0.51111], + "113": [0.19444, 0.43056, 0.08847, 0, 0.46], + "114": [0, 0.43056, 0.10764, 0, 0.42166], + "115": [0, 0.43056, 0.08208, 0, 0.40889], + "116": [0, 0.61508, 0.09486, 0, 0.33222], + "117": [0, 0.43056, 0.07671, 0, 0.53666], + "118": [0, 0.43056, 0.10764, 0, 0.46], + "119": [0, 0.43056, 0.10764, 0, 0.66444], + "120": [0, 0.43056, 0.12042, 0, 0.46389], + "121": [0.19444, 0.43056, 0.08847, 0, 0.48555], + "122": [0, 0.43056, 0.12292, 0, 0.40889], + "126": [0.35, 0.31786, 0.11585, 0, 0.51111], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.66786, 0.10474, 0, 0.51111], + "176": [0, 0.69444, 0, 0, 0.83129], + "184": [0.17014, 0, 0, 0, 0.46], + "198": [0, 0.68333, 0.12028, 0, 0.88277], + "216": [0.04861, 0.73194, 0.09403, 0, 0.76666], + "223": [0.19444, 0.69444, 0.10514, 0, 0.53666], + "230": [0, 0.43056, 0.07514, 0, 0.71555], + "248": [0.09722, 0.52778, 0.09194, 0, 0.51111], + "338": [0, 0.68333, 0.12028, 0, 0.98499], + "339": [0, 0.43056, 0.07514, 0, 0.71555], + "710": [0, 0.69444, 0.06646, 0, 0.51111], + "711": [0, 0.62847, 0.08295, 0, 0.51111], + "713": [0, 0.56167, 0.10333, 0, 0.51111], + "714": [0, 0.69444, 0.09694, 0, 0.51111], + "715": [0, 0.69444, 0, 0, 0.51111], + "728": [0, 0.69444, 0.10806, 0, 0.51111], + "729": [0, 0.66786, 0.11752, 0, 0.30667], + "730": [0, 0.69444, 0, 0, 0.83129], + "732": [0, 0.66786, 0.11585, 0, 0.51111], + "733": [0, 0.69444, 0.1225, 0, 0.51111], + "915": [0, 0.68333, 0.13305, 0, 0.62722], + "916": [0, 0.68333, 0, 0, 0.81777], + "920": [0, 0.68333, 0.09403, 0, 0.76666], + "923": [0, 0.68333, 0, 0, 0.69222], + "926": [0, 0.68333, 0.15294, 0, 0.66444], + "928": [0, 0.68333, 0.16389, 0, 0.74333], + "931": [0, 0.68333, 0.12028, 0, 0.71555], + "933": [0, 0.68333, 0.11111, 0, 0.76666], + "934": [0, 0.68333, 0.05986, 0, 0.71555], + "936": [0, 0.68333, 0.11111, 0, 0.76666], + "937": [0, 0.68333, 0.10257, 0, 0.71555], + "8211": [0, 0.43056, 0.09208, 0, 0.51111], + "8212": [0, 0.43056, 0.09208, 0, 1.02222], + "8216": [0, 0.69444, 0.12417, 0, 0.30667], + "8217": [0, 0.69444, 0.12417, 0, 0.30667], + "8220": [0, 0.69444, 0.1685, 0, 0.51444], + "8221": [0, 0.69444, 0.06961, 0, 0.51444], + "8463": [0, 0.68889, 0, 0, 0.54028] + }, + "Main-Regular": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0, 0, 0.27778], + "34": [0, 0.69444, 0, 0, 0.5], + "35": [0.19444, 0.69444, 0, 0, 0.83334], + "36": [0.05556, 0.75, 0, 0, 0.5], + "37": [0.05556, 0.75, 0, 0, 0.83334], + "38": [0, 0.69444, 0, 0, 0.77778], + "39": [0, 0.69444, 0, 0, 0.27778], + "40": [0.25, 0.75, 0, 0, 0.38889], + "41": [0.25, 0.75, 0, 0, 0.38889], + "42": [0, 0.75, 0, 0, 0.5], + "43": [0.08333, 0.58333, 0, 0, 0.77778], + "44": [0.19444, 0.10556, 0, 0, 0.27778], + "45": [0, 0.43056, 0, 0, 0.33333], + "46": [0, 0.10556, 0, 0, 0.27778], + "47": [0.25, 0.75, 0, 0, 0.5], + "48": [0, 0.64444, 0, 0, 0.5], + "49": [0, 0.64444, 0, 0, 0.5], + "50": [0, 0.64444, 0, 0, 0.5], + "51": [0, 0.64444, 0, 0, 0.5], + "52": [0, 0.64444, 0, 0, 0.5], + "53": [0, 0.64444, 0, 0, 0.5], + "54": [0, 0.64444, 0, 0, 0.5], + "55": [0, 0.64444, 0, 0, 0.5], + "56": [0, 0.64444, 0, 0, 0.5], + "57": [0, 0.64444, 0, 0, 0.5], + "58": [0, 0.43056, 0, 0, 0.27778], + "59": [0.19444, 0.43056, 0, 0, 0.27778], + "60": [0.0391, 0.5391, 0, 0, 0.77778], + "61": [-0.13313, 0.36687, 0, 0, 0.77778], + "62": [0.0391, 0.5391, 0, 0, 0.77778], + "63": [0, 0.69444, 0, 0, 0.47222], + "64": [0, 0.69444, 0, 0, 0.77778], + "65": [0, 0.68333, 0, 0, 0.75], + "66": [0, 0.68333, 0, 0, 0.70834], + "67": [0, 0.68333, 0, 0, 0.72222], + "68": [0, 0.68333, 0, 0, 0.76389], + "69": [0, 0.68333, 0, 0, 0.68056], + "70": [0, 0.68333, 0, 0, 0.65278], + "71": [0, 0.68333, 0, 0, 0.78472], + "72": [0, 0.68333, 0, 0, 0.75], + "73": [0, 0.68333, 0, 0, 0.36111], + "74": [0, 0.68333, 0, 0, 0.51389], + "75": [0, 0.68333, 0, 0, 0.77778], + "76": [0, 0.68333, 0, 0, 0.625], + "77": [0, 0.68333, 0, 0, 0.91667], + "78": [0, 0.68333, 0, 0, 0.75], + "79": [0, 0.68333, 0, 0, 0.77778], + "80": [0, 0.68333, 0, 0, 0.68056], + "81": [0.19444, 0.68333, 0, 0, 0.77778], + "82": [0, 0.68333, 0, 0, 0.73611], + "83": [0, 0.68333, 0, 0, 0.55556], + "84": [0, 0.68333, 0, 0, 0.72222], + "85": [0, 0.68333, 0, 0, 0.75], + "86": [0, 0.68333, 0.01389, 0, 0.75], + "87": [0, 0.68333, 0.01389, 0, 1.02778], + "88": [0, 0.68333, 0, 0, 0.75], + "89": [0, 0.68333, 0.025, 0, 0.75], + "90": [0, 0.68333, 0, 0, 0.61111], + "91": [0.25, 0.75, 0, 0, 0.27778], + "92": [0.25, 0.75, 0, 0, 0.5], + "93": [0.25, 0.75, 0, 0, 0.27778], + "94": [0, 0.69444, 0, 0, 0.5], + "95": [0.31, 0.12056, 0.02778, 0, 0.5], + "97": [0, 0.43056, 0, 0, 0.5], + "98": [0, 0.69444, 0, 0, 0.55556], + "99": [0, 0.43056, 0, 0, 0.44445], + "100": [0, 0.69444, 0, 0, 0.55556], + "101": [0, 0.43056, 0, 0, 0.44445], + "102": [0, 0.69444, 0.07778, 0, 0.30556], + "103": [0.19444, 0.43056, 0.01389, 0, 0.5], + "104": [0, 0.69444, 0, 0, 0.55556], + "105": [0, 0.66786, 0, 0, 0.27778], + "106": [0.19444, 0.66786, 0, 0, 0.30556], + "107": [0, 0.69444, 0, 0, 0.52778], + "108": [0, 0.69444, 0, 0, 0.27778], + "109": [0, 0.43056, 0, 0, 0.83334], + "110": [0, 0.43056, 0, 0, 0.55556], + "111": [0, 0.43056, 0, 0, 0.5], + "112": [0.19444, 0.43056, 0, 0, 0.55556], + "113": [0.19444, 0.43056, 0, 0, 0.52778], + "114": [0, 0.43056, 0, 0, 0.39167], + "115": [0, 0.43056, 0, 0, 0.39445], + "116": [0, 0.61508, 0, 0, 0.38889], + "117": [0, 0.43056, 0, 0, 0.55556], + "118": [0, 0.43056, 0.01389, 0, 0.52778], + "119": [0, 0.43056, 0.01389, 0, 0.72222], + "120": [0, 0.43056, 0, 0, 0.52778], + "121": [0.19444, 0.43056, 0.01389, 0, 0.52778], + "122": [0, 0.43056, 0, 0, 0.44445], + "123": [0.25, 0.75, 0, 0, 0.5], + "124": [0.25, 0.75, 0, 0, 0.27778], + "125": [0.25, 0.75, 0, 0, 0.5], + "126": [0.35, 0.31786, 0, 0, 0.5], + "160": [0, 0, 0, 0, 0.25], + "163": [0, 0.69444, 0, 0, 0.76909], + "167": [0.19444, 0.69444, 0, 0, 0.44445], + "168": [0, 0.66786, 0, 0, 0.5], + "172": [0, 0.43056, 0, 0, 0.66667], + "176": [0, 0.69444, 0, 0, 0.75], + "177": [0.08333, 0.58333, 0, 0, 0.77778], + "182": [0.19444, 0.69444, 0, 0, 0.61111], + "184": [0.17014, 0, 0, 0, 0.44445], + "198": [0, 0.68333, 0, 0, 0.90278], + "215": [0.08333, 0.58333, 0, 0, 0.77778], + "216": [0.04861, 0.73194, 0, 0, 0.77778], + "223": [0, 0.69444, 0, 0, 0.5], + "230": [0, 0.43056, 0, 0, 0.72222], + "247": [0.08333, 0.58333, 0, 0, 0.77778], + "248": [0.09722, 0.52778, 0, 0, 0.5], + "305": [0, 0.43056, 0, 0, 0.27778], + "338": [0, 0.68333, 0, 0, 1.01389], + "339": [0, 0.43056, 0, 0, 0.77778], + "567": [0.19444, 0.43056, 0, 0, 0.30556], + "710": [0, 0.69444, 0, 0, 0.5], + "711": [0, 0.62847, 0, 0, 0.5], + "713": [0, 0.56778, 0, 0, 0.5], + "714": [0, 0.69444, 0, 0, 0.5], + "715": [0, 0.69444, 0, 0, 0.5], + "728": [0, 0.69444, 0, 0, 0.5], + "729": [0, 0.66786, 0, 0, 0.27778], + "730": [0, 0.69444, 0, 0, 0.75], + "732": [0, 0.66786, 0, 0, 0.5], + "733": [0, 0.69444, 0, 0, 0.5], + "915": [0, 0.68333, 0, 0, 0.625], + "916": [0, 0.68333, 0, 0, 0.83334], + "920": [0, 0.68333, 0, 0, 0.77778], + "923": [0, 0.68333, 0, 0, 0.69445], + "926": [0, 0.68333, 0, 0, 0.66667], + "928": [0, 0.68333, 0, 0, 0.75], + "931": [0, 0.68333, 0, 0, 0.72222], + "933": [0, 0.68333, 0, 0, 0.77778], + "934": [0, 0.68333, 0, 0, 0.72222], + "936": [0, 0.68333, 0, 0, 0.77778], + "937": [0, 0.68333, 0, 0, 0.72222], + "8211": [0, 0.43056, 0.02778, 0, 0.5], + "8212": [0, 0.43056, 0.02778, 0, 1.0], + "8216": [0, 0.69444, 0, 0, 0.27778], + "8217": [0, 0.69444, 0, 0, 0.27778], + "8220": [0, 0.69444, 0, 0, 0.5], + "8221": [0, 0.69444, 0, 0, 0.5], + "8224": [0.19444, 0.69444, 0, 0, 0.44445], + "8225": [0.19444, 0.69444, 0, 0, 0.44445], + "8230": [0, 0.123, 0, 0, 1.172], + "8242": [0, 0.55556, 0, 0, 0.275], + "8407": [0, 0.71444, 0.15382, 0, 0.5], + "8463": [0, 0.68889, 0, 0, 0.54028], + "8465": [0, 0.69444, 0, 0, 0.72222], + "8467": [0, 0.69444, 0, 0.11111, 0.41667], + "8472": [0.19444, 0.43056, 0, 0.11111, 0.63646], + "8476": [0, 0.69444, 0, 0, 0.72222], + "8501": [0, 0.69444, 0, 0, 0.61111], + "8592": [-0.13313, 0.36687, 0, 0, 1.0], + "8593": [0.19444, 0.69444, 0, 0, 0.5], + "8594": [-0.13313, 0.36687, 0, 0, 1.0], + "8595": [0.19444, 0.69444, 0, 0, 0.5], + "8596": [-0.13313, 0.36687, 0, 0, 1.0], + "8597": [0.25, 0.75, 0, 0, 0.5], + "8598": [0.19444, 0.69444, 0, 0, 1.0], + "8599": [0.19444, 0.69444, 0, 0, 1.0], + "8600": [0.19444, 0.69444, 0, 0, 1.0], + "8601": [0.19444, 0.69444, 0, 0, 1.0], + "8614": [0.011, 0.511, 0, 0, 1.0], + "8617": [0.011, 0.511, 0, 0, 1.126], + "8618": [0.011, 0.511, 0, 0, 1.126], + "8636": [-0.13313, 0.36687, 0, 0, 1.0], + "8637": [-0.13313, 0.36687, 0, 0, 1.0], + "8640": [-0.13313, 0.36687, 0, 0, 1.0], + "8641": [-0.13313, 0.36687, 0, 0, 1.0], + "8652": [0.011, 0.671, 0, 0, 1.0], + "8656": [-0.13313, 0.36687, 0, 0, 1.0], + "8657": [0.19444, 0.69444, 0, 0, 0.61111], + "8658": [-0.13313, 0.36687, 0, 0, 1.0], + "8659": [0.19444, 0.69444, 0, 0, 0.61111], + "8660": [-0.13313, 0.36687, 0, 0, 1.0], + "8661": [0.25, 0.75, 0, 0, 0.61111], + "8704": [0, 0.69444, 0, 0, 0.55556], + "8706": [0, 0.69444, 0.05556, 0.08334, 0.5309], + "8707": [0, 0.69444, 0, 0, 0.55556], + "8709": [0.05556, 0.75, 0, 0, 0.5], + "8711": [0, 0.68333, 0, 0, 0.83334], + "8712": [0.0391, 0.5391, 0, 0, 0.66667], + "8715": [0.0391, 0.5391, 0, 0, 0.66667], + "8722": [0.08333, 0.58333, 0, 0, 0.77778], + "8723": [0.08333, 0.58333, 0, 0, 0.77778], + "8725": [0.25, 0.75, 0, 0, 0.5], + "8726": [0.25, 0.75, 0, 0, 0.5], + "8727": [-0.03472, 0.46528, 0, 0, 0.5], + "8728": [-0.05555, 0.44445, 0, 0, 0.5], + "8729": [-0.05555, 0.44445, 0, 0, 0.5], + "8730": [0.2, 0.8, 0, 0, 0.83334], + "8733": [0, 0.43056, 0, 0, 0.77778], + "8734": [0, 0.43056, 0, 0, 1.0], + "8736": [0, 0.69224, 0, 0, 0.72222], + "8739": [0.25, 0.75, 0, 0, 0.27778], + "8741": [0.25, 0.75, 0, 0, 0.5], + "8743": [0, 0.55556, 0, 0, 0.66667], + "8744": [0, 0.55556, 0, 0, 0.66667], + "8745": [0, 0.55556, 0, 0, 0.66667], + "8746": [0, 0.55556, 0, 0, 0.66667], + "8747": [0.19444, 0.69444, 0.11111, 0, 0.41667], + "8764": [-0.13313, 0.36687, 0, 0, 0.77778], + "8768": [0.19444, 0.69444, 0, 0, 0.27778], + "8771": [-0.03625, 0.46375, 0, 0, 0.77778], + "8773": [-0.022, 0.589, 0, 0, 0.778], + "8776": [-0.01688, 0.48312, 0, 0, 0.77778], + "8781": [-0.03625, 0.46375, 0, 0, 0.77778], + "8784": [-0.133, 0.673, 0, 0, 0.778], + "8801": [-0.03625, 0.46375, 0, 0, 0.77778], + "8804": [0.13597, 0.63597, 0, 0, 0.77778], + "8805": [0.13597, 0.63597, 0, 0, 0.77778], + "8810": [0.0391, 0.5391, 0, 0, 1.0], + "8811": [0.0391, 0.5391, 0, 0, 1.0], + "8826": [0.0391, 0.5391, 0, 0, 0.77778], + "8827": [0.0391, 0.5391, 0, 0, 0.77778], + "8834": [0.0391, 0.5391, 0, 0, 0.77778], + "8835": [0.0391, 0.5391, 0, 0, 0.77778], + "8838": [0.13597, 0.63597, 0, 0, 0.77778], + "8839": [0.13597, 0.63597, 0, 0, 0.77778], + "8846": [0, 0.55556, 0, 0, 0.66667], + "8849": [0.13597, 0.63597, 0, 0, 0.77778], + "8850": [0.13597, 0.63597, 0, 0, 0.77778], + "8851": [0, 0.55556, 0, 0, 0.66667], + "8852": [0, 0.55556, 0, 0, 0.66667], + "8853": [0.08333, 0.58333, 0, 0, 0.77778], + "8854": [0.08333, 0.58333, 0, 0, 0.77778], + "8855": [0.08333, 0.58333, 0, 0, 0.77778], + "8856": [0.08333, 0.58333, 0, 0, 0.77778], + "8857": [0.08333, 0.58333, 0, 0, 0.77778], + "8866": [0, 0.69444, 0, 0, 0.61111], + "8867": [0, 0.69444, 0, 0, 0.61111], + "8868": [0, 0.69444, 0, 0, 0.77778], + "8869": [0, 0.69444, 0, 0, 0.77778], + "8872": [0.249, 0.75, 0, 0, 0.867], + "8900": [-0.05555, 0.44445, 0, 0, 0.5], + "8901": [-0.05555, 0.44445, 0, 0, 0.27778], + "8902": [-0.03472, 0.46528, 0, 0, 0.5], + "8904": [0.005, 0.505, 0, 0, 0.9], + "8942": [0.03, 0.903, 0, 0, 0.278], + "8943": [-0.19, 0.313, 0, 0, 1.172], + "8945": [-0.1, 0.823, 0, 0, 1.282], + "8968": [0.25, 0.75, 0, 0, 0.44445], + "8969": [0.25, 0.75, 0, 0, 0.44445], + "8970": [0.25, 0.75, 0, 0, 0.44445], + "8971": [0.25, 0.75, 0, 0, 0.44445], + "8994": [-0.14236, 0.35764, 0, 0, 1.0], + "8995": [-0.14236, 0.35764, 0, 0, 1.0], + "9136": [0.244, 0.744, 0, 0, 0.412], + "9137": [0.244, 0.745, 0, 0, 0.412], + "9651": [0.19444, 0.69444, 0, 0, 0.88889], + "9657": [-0.03472, 0.46528, 0, 0, 0.5], + "9661": [0.19444, 0.69444, 0, 0, 0.88889], + "9667": [-0.03472, 0.46528, 0, 0, 0.5], + "9711": [0.19444, 0.69444, 0, 0, 1.0], + "9824": [0.12963, 0.69444, 0, 0, 0.77778], + "9825": [0.12963, 0.69444, 0, 0, 0.77778], + "9826": [0.12963, 0.69444, 0, 0, 0.77778], + "9827": [0.12963, 0.69444, 0, 0, 0.77778], + "9837": [0, 0.75, 0, 0, 0.38889], + "9838": [0.19444, 0.69444, 0, 0, 0.38889], + "9839": [0.19444, 0.69444, 0, 0, 0.38889], + "10216": [0.25, 0.75, 0, 0, 0.38889], + "10217": [0.25, 0.75, 0, 0, 0.38889], + "10222": [0.244, 0.744, 0, 0, 0.412], + "10223": [0.244, 0.745, 0, 0, 0.412], + "10229": [0.011, 0.511, 0, 0, 1.609], + "10230": [0.011, 0.511, 0, 0, 1.638], + "10231": [0.011, 0.511, 0, 0, 1.859], + "10232": [0.024, 0.525, 0, 0, 1.609], + "10233": [0.024, 0.525, 0, 0, 1.638], + "10234": [0.024, 0.525, 0, 0, 1.858], + "10236": [0.011, 0.511, 0, 0, 1.638], + "10815": [0, 0.68333, 0, 0, 0.75], + "10927": [0.13597, 0.63597, 0, 0, 0.77778], + "10928": [0.13597, 0.63597, 0, 0, 0.77778], + "57376": [0.19444, 0.69444, 0, 0, 0] + }, + "Math-BoldItalic": { + "32": [0, 0, 0, 0, 0.25], + "48": [0, 0.44444, 0, 0, 0.575], + "49": [0, 0.44444, 0, 0, 0.575], + "50": [0, 0.44444, 0, 0, 0.575], + "51": [0.19444, 0.44444, 0, 0, 0.575], + "52": [0.19444, 0.44444, 0, 0, 0.575], + "53": [0.19444, 0.44444, 0, 0, 0.575], + "54": [0, 0.64444, 0, 0, 0.575], + "55": [0.19444, 0.44444, 0, 0, 0.575], + "56": [0, 0.64444, 0, 0, 0.575], + "57": [0.19444, 0.44444, 0, 0, 0.575], + "65": [0, 0.68611, 0, 0, 0.86944], + "66": [0, 0.68611, 0.04835, 0, 0.8664], + "67": [0, 0.68611, 0.06979, 0, 0.81694], + "68": [0, 0.68611, 0.03194, 0, 0.93812], + "69": [0, 0.68611, 0.05451, 0, 0.81007], + "70": [0, 0.68611, 0.15972, 0, 0.68889], + "71": [0, 0.68611, 0, 0, 0.88673], + "72": [0, 0.68611, 0.08229, 0, 0.98229], + "73": [0, 0.68611, 0.07778, 0, 0.51111], + "74": [0, 0.68611, 0.10069, 0, 0.63125], + "75": [0, 0.68611, 0.06979, 0, 0.97118], + "76": [0, 0.68611, 0, 0, 0.75555], + "77": [0, 0.68611, 0.11424, 0, 1.14201], + "78": [0, 0.68611, 0.11424, 0, 0.95034], + "79": [0, 0.68611, 0.03194, 0, 0.83666], + "80": [0, 0.68611, 0.15972, 0, 0.72309], + "81": [0.19444, 0.68611, 0, 0, 0.86861], + "82": [0, 0.68611, 0.00421, 0, 0.87235], + "83": [0, 0.68611, 0.05382, 0, 0.69271], + "84": [0, 0.68611, 0.15972, 0, 0.63663], + "85": [0, 0.68611, 0.11424, 0, 0.80027], + "86": [0, 0.68611, 0.25555, 0, 0.67778], + "87": [0, 0.68611, 0.15972, 0, 1.09305], + "88": [0, 0.68611, 0.07778, 0, 0.94722], + "89": [0, 0.68611, 0.25555, 0, 0.67458], + "90": [0, 0.68611, 0.06979, 0, 0.77257], + "97": [0, 0.44444, 0, 0, 0.63287], + "98": [0, 0.69444, 0, 0, 0.52083], + "99": [0, 0.44444, 0, 0, 0.51342], + "100": [0, 0.69444, 0, 0, 0.60972], + "101": [0, 0.44444, 0, 0, 0.55361], + "102": [0.19444, 0.69444, 0.11042, 0, 0.56806], + "103": [0.19444, 0.44444, 0.03704, 0, 0.5449], + "104": [0, 0.69444, 0, 0, 0.66759], + "105": [0, 0.69326, 0, 0, 0.4048], + "106": [0.19444, 0.69326, 0.0622, 0, 0.47083], + "107": [0, 0.69444, 0.01852, 0, 0.6037], + "108": [0, 0.69444, 0.0088, 0, 0.34815], + "109": [0, 0.44444, 0, 0, 1.0324], + "110": [0, 0.44444, 0, 0, 0.71296], + "111": [0, 0.44444, 0, 0, 0.58472], + "112": [0.19444, 0.44444, 0, 0, 0.60092], + "113": [0.19444, 0.44444, 0.03704, 0, 0.54213], + "114": [0, 0.44444, 0.03194, 0, 0.5287], + "115": [0, 0.44444, 0, 0, 0.53125], + "116": [0, 0.63492, 0, 0, 0.41528], + "117": [0, 0.44444, 0, 0, 0.68102], + "118": [0, 0.44444, 0.03704, 0, 0.56666], + "119": [0, 0.44444, 0.02778, 0, 0.83148], + "120": [0, 0.44444, 0, 0, 0.65903], + "121": [0.19444, 0.44444, 0.03704, 0, 0.59028], + "122": [0, 0.44444, 0.04213, 0, 0.55509], + "160": [0, 0, 0, 0, 0.25], + "915": [0, 0.68611, 0.15972, 0, 0.65694], + "916": [0, 0.68611, 0, 0, 0.95833], + "920": [0, 0.68611, 0.03194, 0, 0.86722], + "923": [0, 0.68611, 0, 0, 0.80555], + "926": [0, 0.68611, 0.07458, 0, 0.84125], + "928": [0, 0.68611, 0.08229, 0, 0.98229], + "931": [0, 0.68611, 0.05451, 0, 0.88507], + "933": [0, 0.68611, 0.15972, 0, 0.67083], + "934": [0, 0.68611, 0, 0, 0.76666], + "936": [0, 0.68611, 0.11653, 0, 0.71402], + "937": [0, 0.68611, 0.04835, 0, 0.8789], + "945": [0, 0.44444, 0, 0, 0.76064], + "946": [0.19444, 0.69444, 0.03403, 0, 0.65972], + "947": [0.19444, 0.44444, 0.06389, 0, 0.59003], + "948": [0, 0.69444, 0.03819, 0, 0.52222], + "949": [0, 0.44444, 0, 0, 0.52882], + "950": [0.19444, 0.69444, 0.06215, 0, 0.50833], + "951": [0.19444, 0.44444, 0.03704, 0, 0.6], + "952": [0, 0.69444, 0.03194, 0, 0.5618], + "953": [0, 0.44444, 0, 0, 0.41204], + "954": [0, 0.44444, 0, 0, 0.66759], + "955": [0, 0.69444, 0, 0, 0.67083], + "956": [0.19444, 0.44444, 0, 0, 0.70787], + "957": [0, 0.44444, 0.06898, 0, 0.57685], + "958": [0.19444, 0.69444, 0.03021, 0, 0.50833], + "959": [0, 0.44444, 0, 0, 0.58472], + "960": [0, 0.44444, 0.03704, 0, 0.68241], + "961": [0.19444, 0.44444, 0, 0, 0.6118], + "962": [0.09722, 0.44444, 0.07917, 0, 0.42361], + "963": [0, 0.44444, 0.03704, 0, 0.68588], + "964": [0, 0.44444, 0.13472, 0, 0.52083], + "965": [0, 0.44444, 0.03704, 0, 0.63055], + "966": [0.19444, 0.44444, 0, 0, 0.74722], + "967": [0.19444, 0.44444, 0, 0, 0.71805], + "968": [0.19444, 0.69444, 0.03704, 0, 0.75833], + "969": [0, 0.44444, 0.03704, 0, 0.71782], + "977": [0, 0.69444, 0, 0, 0.69155], + "981": [0.19444, 0.69444, 0, 0, 0.7125], + "982": [0, 0.44444, 0.03194, 0, 0.975], + "1009": [0.19444, 0.44444, 0, 0, 0.6118], + "1013": [0, 0.44444, 0, 0, 0.48333], + "57649": [0, 0.44444, 0, 0, 0.39352], + "57911": [0.19444, 0.44444, 0, 0, 0.43889] + }, + "Math-Italic": { + "32": [0, 0, 0, 0, 0.25], + "48": [0, 0.43056, 0, 0, 0.5], + "49": [0, 0.43056, 0, 0, 0.5], + "50": [0, 0.43056, 0, 0, 0.5], + "51": [0.19444, 0.43056, 0, 0, 0.5], + "52": [0.19444, 0.43056, 0, 0, 0.5], + "53": [0.19444, 0.43056, 0, 0, 0.5], + "54": [0, 0.64444, 0, 0, 0.5], + "55": [0.19444, 0.43056, 0, 0, 0.5], + "56": [0, 0.64444, 0, 0, 0.5], + "57": [0.19444, 0.43056, 0, 0, 0.5], + "65": [0, 0.68333, 0, 0.13889, 0.75], + "66": [0, 0.68333, 0.05017, 0.08334, 0.75851], + "67": [0, 0.68333, 0.07153, 0.08334, 0.71472], + "68": [0, 0.68333, 0.02778, 0.05556, 0.82792], + "69": [0, 0.68333, 0.05764, 0.08334, 0.7382], + "70": [0, 0.68333, 0.13889, 0.08334, 0.64306], + "71": [0, 0.68333, 0, 0.08334, 0.78625], + "72": [0, 0.68333, 0.08125, 0.05556, 0.83125], + "73": [0, 0.68333, 0.07847, 0.11111, 0.43958], + "74": [0, 0.68333, 0.09618, 0.16667, 0.55451], + "75": [0, 0.68333, 0.07153, 0.05556, 0.84931], + "76": [0, 0.68333, 0, 0.02778, 0.68056], + "77": [0, 0.68333, 0.10903, 0.08334, 0.97014], + "78": [0, 0.68333, 0.10903, 0.08334, 0.80347], + "79": [0, 0.68333, 0.02778, 0.08334, 0.76278], + "80": [0, 0.68333, 0.13889, 0.08334, 0.64201], + "81": [0.19444, 0.68333, 0, 0.08334, 0.79056], + "82": [0, 0.68333, 0.00773, 0.08334, 0.75929], + "83": [0, 0.68333, 0.05764, 0.08334, 0.6132], + "84": [0, 0.68333, 0.13889, 0.08334, 0.58438], + "85": [0, 0.68333, 0.10903, 0.02778, 0.68278], + "86": [0, 0.68333, 0.22222, 0, 0.58333], + "87": [0, 0.68333, 0.13889, 0, 0.94445], + "88": [0, 0.68333, 0.07847, 0.08334, 0.82847], + "89": [0, 0.68333, 0.22222, 0, 0.58056], + "90": [0, 0.68333, 0.07153, 0.08334, 0.68264], + "97": [0, 0.43056, 0, 0, 0.52859], + "98": [0, 0.69444, 0, 0, 0.42917], + "99": [0, 0.43056, 0, 0.05556, 0.43276], + "100": [0, 0.69444, 0, 0.16667, 0.52049], + "101": [0, 0.43056, 0, 0.05556, 0.46563], + "102": [0.19444, 0.69444, 0.10764, 0.16667, 0.48959], + "103": [0.19444, 0.43056, 0.03588, 0.02778, 0.47697], + "104": [0, 0.69444, 0, 0, 0.57616], + "105": [0, 0.65952, 0, 0, 0.34451], + "106": [0.19444, 0.65952, 0.05724, 0, 0.41181], + "107": [0, 0.69444, 0.03148, 0, 0.5206], + "108": [0, 0.69444, 0.01968, 0.08334, 0.29838], + "109": [0, 0.43056, 0, 0, 0.87801], + "110": [0, 0.43056, 0, 0, 0.60023], + "111": [0, 0.43056, 0, 0.05556, 0.48472], + "112": [0.19444, 0.43056, 0, 0.08334, 0.50313], + "113": [0.19444, 0.43056, 0.03588, 0.08334, 0.44641], + "114": [0, 0.43056, 0.02778, 0.05556, 0.45116], + "115": [0, 0.43056, 0, 0.05556, 0.46875], + "116": [0, 0.61508, 0, 0.08334, 0.36111], + "117": [0, 0.43056, 0, 0.02778, 0.57246], + "118": [0, 0.43056, 0.03588, 0.02778, 0.48472], + "119": [0, 0.43056, 0.02691, 0.08334, 0.71592], + "120": [0, 0.43056, 0, 0.02778, 0.57153], + "121": [0.19444, 0.43056, 0.03588, 0.05556, 0.49028], + "122": [0, 0.43056, 0.04398, 0.05556, 0.46505], + "160": [0, 0, 0, 0, 0.25], + "915": [0, 0.68333, 0.13889, 0.08334, 0.61528], + "916": [0, 0.68333, 0, 0.16667, 0.83334], + "920": [0, 0.68333, 0.02778, 0.08334, 0.76278], + "923": [0, 0.68333, 0, 0.16667, 0.69445], + "926": [0, 0.68333, 0.07569, 0.08334, 0.74236], + "928": [0, 0.68333, 0.08125, 0.05556, 0.83125], + "931": [0, 0.68333, 0.05764, 0.08334, 0.77986], + "933": [0, 0.68333, 0.13889, 0.05556, 0.58333], + "934": [0, 0.68333, 0, 0.08334, 0.66667], + "936": [0, 0.68333, 0.11, 0.05556, 0.61222], + "937": [0, 0.68333, 0.05017, 0.08334, 0.7724], + "945": [0, 0.43056, 0.0037, 0.02778, 0.6397], + "946": [0.19444, 0.69444, 0.05278, 0.08334, 0.56563], + "947": [0.19444, 0.43056, 0.05556, 0, 0.51773], + "948": [0, 0.69444, 0.03785, 0.05556, 0.44444], + "949": [0, 0.43056, 0, 0.08334, 0.46632], + "950": [0.19444, 0.69444, 0.07378, 0.08334, 0.4375], + "951": [0.19444, 0.43056, 0.03588, 0.05556, 0.49653], + "952": [0, 0.69444, 0.02778, 0.08334, 0.46944], + "953": [0, 0.43056, 0, 0.05556, 0.35394], + "954": [0, 0.43056, 0, 0, 0.57616], + "955": [0, 0.69444, 0, 0, 0.58334], + "956": [0.19444, 0.43056, 0, 0.02778, 0.60255], + "957": [0, 0.43056, 0.06366, 0.02778, 0.49398], + "958": [0.19444, 0.69444, 0.04601, 0.11111, 0.4375], + "959": [0, 0.43056, 0, 0.05556, 0.48472], + "960": [0, 0.43056, 0.03588, 0, 0.57003], + "961": [0.19444, 0.43056, 0, 0.08334, 0.51702], + "962": [0.09722, 0.43056, 0.07986, 0.08334, 0.36285], + "963": [0, 0.43056, 0.03588, 0, 0.57141], + "964": [0, 0.43056, 0.1132, 0.02778, 0.43715], + "965": [0, 0.43056, 0.03588, 0.02778, 0.54028], + "966": [0.19444, 0.43056, 0, 0.08334, 0.65417], + "967": [0.19444, 0.43056, 0, 0.05556, 0.62569], + "968": [0.19444, 0.69444, 0.03588, 0.11111, 0.65139], + "969": [0, 0.43056, 0.03588, 0, 0.62245], + "977": [0, 0.69444, 0, 0.08334, 0.59144], + "981": [0.19444, 0.69444, 0, 0.08334, 0.59583], + "982": [0, 0.43056, 0.02778, 0, 0.82813], + "1009": [0.19444, 0.43056, 0, 0.08334, 0.51702], + "1013": [0, 0.43056, 0, 0.05556, 0.4059], + "57649": [0, 0.43056, 0, 0.02778, 0.32246], + "57911": [0.19444, 0.43056, 0, 0.08334, 0.38403] + }, + "SansSerif-Bold": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0, 0, 0.36667], + "34": [0, 0.69444, 0, 0, 0.55834], + "35": [0.19444, 0.69444, 0, 0, 0.91667], + "36": [0.05556, 0.75, 0, 0, 0.55], + "37": [0.05556, 0.75, 0, 0, 1.02912], + "38": [0, 0.69444, 0, 0, 0.83056], + "39": [0, 0.69444, 0, 0, 0.30556], + "40": [0.25, 0.75, 0, 0, 0.42778], + "41": [0.25, 0.75, 0, 0, 0.42778], + "42": [0, 0.75, 0, 0, 0.55], + "43": [0.11667, 0.61667, 0, 0, 0.85556], + "44": [0.10556, 0.13056, 0, 0, 0.30556], + "45": [0, 0.45833, 0, 0, 0.36667], + "46": [0, 0.13056, 0, 0, 0.30556], + "47": [0.25, 0.75, 0, 0, 0.55], + "48": [0, 0.69444, 0, 0, 0.55], + "49": [0, 0.69444, 0, 0, 0.55], + "50": [0, 0.69444, 0, 0, 0.55], + "51": [0, 0.69444, 0, 0, 0.55], + "52": [0, 0.69444, 0, 0, 0.55], + "53": [0, 0.69444, 0, 0, 0.55], + "54": [0, 0.69444, 0, 0, 0.55], + "55": [0, 0.69444, 0, 0, 0.55], + "56": [0, 0.69444, 0, 0, 0.55], + "57": [0, 0.69444, 0, 0, 0.55], + "58": [0, 0.45833, 0, 0, 0.30556], + "59": [0.10556, 0.45833, 0, 0, 0.30556], + "61": [-0.09375, 0.40625, 0, 0, 0.85556], + "63": [0, 0.69444, 0, 0, 0.51945], + "64": [0, 0.69444, 0, 0, 0.73334], + "65": [0, 0.69444, 0, 0, 0.73334], + "66": [0, 0.69444, 0, 0, 0.73334], + "67": [0, 0.69444, 0, 0, 0.70278], + "68": [0, 0.69444, 0, 0, 0.79445], + "69": [0, 0.69444, 0, 0, 0.64167], + "70": [0, 0.69444, 0, 0, 0.61111], + "71": [0, 0.69444, 0, 0, 0.73334], + "72": [0, 0.69444, 0, 0, 0.79445], + "73": [0, 0.69444, 0, 0, 0.33056], + "74": [0, 0.69444, 0, 0, 0.51945], + "75": [0, 0.69444, 0, 0, 0.76389], + "76": [0, 0.69444, 0, 0, 0.58056], + "77": [0, 0.69444, 0, 0, 0.97778], + "78": [0, 0.69444, 0, 0, 0.79445], + "79": [0, 0.69444, 0, 0, 0.79445], + "80": [0, 0.69444, 0, 0, 0.70278], + "81": [0.10556, 0.69444, 0, 0, 0.79445], + "82": [0, 0.69444, 0, 0, 0.70278], + "83": [0, 0.69444, 0, 0, 0.61111], + "84": [0, 0.69444, 0, 0, 0.73334], + "85": [0, 0.69444, 0, 0, 0.76389], + "86": [0, 0.69444, 0.01528, 0, 0.73334], + "87": [0, 0.69444, 0.01528, 0, 1.03889], + "88": [0, 0.69444, 0, 0, 0.73334], + "89": [0, 0.69444, 0.0275, 0, 0.73334], + "90": [0, 0.69444, 0, 0, 0.67223], + "91": [0.25, 0.75, 0, 0, 0.34306], + "93": [0.25, 0.75, 0, 0, 0.34306], + "94": [0, 0.69444, 0, 0, 0.55], + "95": [0.35, 0.10833, 0.03056, 0, 0.55], + "97": [0, 0.45833, 0, 0, 0.525], + "98": [0, 0.69444, 0, 0, 0.56111], + "99": [0, 0.45833, 0, 0, 0.48889], + "100": [0, 0.69444, 0, 0, 0.56111], + "101": [0, 0.45833, 0, 0, 0.51111], + "102": [0, 0.69444, 0.07639, 0, 0.33611], + "103": [0.19444, 0.45833, 0.01528, 0, 0.55], + "104": [0, 0.69444, 0, 0, 0.56111], + "105": [0, 0.69444, 0, 0, 0.25556], + "106": [0.19444, 0.69444, 0, 0, 0.28611], + "107": [0, 0.69444, 0, 0, 0.53056], + "108": [0, 0.69444, 0, 0, 0.25556], + "109": [0, 0.45833, 0, 0, 0.86667], + "110": [0, 0.45833, 0, 0, 0.56111], + "111": [0, 0.45833, 0, 0, 0.55], + "112": [0.19444, 0.45833, 0, 0, 0.56111], + "113": [0.19444, 0.45833, 0, 0, 0.56111], + "114": [0, 0.45833, 0.01528, 0, 0.37222], + "115": [0, 0.45833, 0, 0, 0.42167], + "116": [0, 0.58929, 0, 0, 0.40417], + "117": [0, 0.45833, 0, 0, 0.56111], + "118": [0, 0.45833, 0.01528, 0, 0.5], + "119": [0, 0.45833, 0.01528, 0, 0.74445], + "120": [0, 0.45833, 0, 0, 0.5], + "121": [0.19444, 0.45833, 0.01528, 0, 0.5], + "122": [0, 0.45833, 0, 0, 0.47639], + "126": [0.35, 0.34444, 0, 0, 0.55], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.69444, 0, 0, 0.55], + "176": [0, 0.69444, 0, 0, 0.73334], + "180": [0, 0.69444, 0, 0, 0.55], + "184": [0.17014, 0, 0, 0, 0.48889], + "305": [0, 0.45833, 0, 0, 0.25556], + "567": [0.19444, 0.45833, 0, 0, 0.28611], + "710": [0, 0.69444, 0, 0, 0.55], + "711": [0, 0.63542, 0, 0, 0.55], + "713": [0, 0.63778, 0, 0, 0.55], + "728": [0, 0.69444, 0, 0, 0.55], + "729": [0, 0.69444, 0, 0, 0.30556], + "730": [0, 0.69444, 0, 0, 0.73334], + "732": [0, 0.69444, 0, 0, 0.55], + "733": [0, 0.69444, 0, 0, 0.55], + "915": [0, 0.69444, 0, 0, 0.58056], + "916": [0, 0.69444, 0, 0, 0.91667], + "920": [0, 0.69444, 0, 0, 0.85556], + "923": [0, 0.69444, 0, 0, 0.67223], + "926": [0, 0.69444, 0, 0, 0.73334], + "928": [0, 0.69444, 0, 0, 0.79445], + "931": [0, 0.69444, 0, 0, 0.79445], + "933": [0, 0.69444, 0, 0, 0.85556], + "934": [0, 0.69444, 0, 0, 0.79445], + "936": [0, 0.69444, 0, 0, 0.85556], + "937": [0, 0.69444, 0, 0, 0.79445], + "8211": [0, 0.45833, 0.03056, 0, 0.55], + "8212": [0, 0.45833, 0.03056, 0, 1.10001], + "8216": [0, 0.69444, 0, 0, 0.30556], + "8217": [0, 0.69444, 0, 0, 0.30556], + "8220": [0, 0.69444, 0, 0, 0.55834], + "8221": [0, 0.69444, 0, 0, 0.55834] + }, + "SansSerif-Italic": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0.05733, 0, 0.31945], + "34": [0, 0.69444, 0.00316, 0, 0.5], + "35": [0.19444, 0.69444, 0.05087, 0, 0.83334], + "36": [0.05556, 0.75, 0.11156, 0, 0.5], + "37": [0.05556, 0.75, 0.03126, 0, 0.83334], + "38": [0, 0.69444, 0.03058, 0, 0.75834], + "39": [0, 0.69444, 0.07816, 0, 0.27778], + "40": [0.25, 0.75, 0.13164, 0, 0.38889], + "41": [0.25, 0.75, 0.02536, 0, 0.38889], + "42": [0, 0.75, 0.11775, 0, 0.5], + "43": [0.08333, 0.58333, 0.02536, 0, 0.77778], + "44": [0.125, 0.08333, 0, 0, 0.27778], + "45": [0, 0.44444, 0.01946, 0, 0.33333], + "46": [0, 0.08333, 0, 0, 0.27778], + "47": [0.25, 0.75, 0.13164, 0, 0.5], + "48": [0, 0.65556, 0.11156, 0, 0.5], + "49": [0, 0.65556, 0.11156, 0, 0.5], + "50": [0, 0.65556, 0.11156, 0, 0.5], + "51": [0, 0.65556, 0.11156, 0, 0.5], + "52": [0, 0.65556, 0.11156, 0, 0.5], + "53": [0, 0.65556, 0.11156, 0, 0.5], + "54": [0, 0.65556, 0.11156, 0, 0.5], + "55": [0, 0.65556, 0.11156, 0, 0.5], + "56": [0, 0.65556, 0.11156, 0, 0.5], + "57": [0, 0.65556, 0.11156, 0, 0.5], + "58": [0, 0.44444, 0.02502, 0, 0.27778], + "59": [0.125, 0.44444, 0.02502, 0, 0.27778], + "61": [-0.13, 0.37, 0.05087, 0, 0.77778], + "63": [0, 0.69444, 0.11809, 0, 0.47222], + "64": [0, 0.69444, 0.07555, 0, 0.66667], + "65": [0, 0.69444, 0, 0, 0.66667], + "66": [0, 0.69444, 0.08293, 0, 0.66667], + "67": [0, 0.69444, 0.11983, 0, 0.63889], + "68": [0, 0.69444, 0.07555, 0, 0.72223], + "69": [0, 0.69444, 0.11983, 0, 0.59722], + "70": [0, 0.69444, 0.13372, 0, 0.56945], + "71": [0, 0.69444, 0.11983, 0, 0.66667], + "72": [0, 0.69444, 0.08094, 0, 0.70834], + "73": [0, 0.69444, 0.13372, 0, 0.27778], + "74": [0, 0.69444, 0.08094, 0, 0.47222], + "75": [0, 0.69444, 0.11983, 0, 0.69445], + "76": [0, 0.69444, 0, 0, 0.54167], + "77": [0, 0.69444, 0.08094, 0, 0.875], + "78": [0, 0.69444, 0.08094, 0, 0.70834], + "79": [0, 0.69444, 0.07555, 0, 0.73611], + "80": [0, 0.69444, 0.08293, 0, 0.63889], + "81": [0.125, 0.69444, 0.07555, 0, 0.73611], + "82": [0, 0.69444, 0.08293, 0, 0.64584], + "83": [0, 0.69444, 0.09205, 0, 0.55556], + "84": [0, 0.69444, 0.13372, 0, 0.68056], + "85": [0, 0.69444, 0.08094, 0, 0.6875], + "86": [0, 0.69444, 0.1615, 0, 0.66667], + "87": [0, 0.69444, 0.1615, 0, 0.94445], + "88": [0, 0.69444, 0.13372, 0, 0.66667], + "89": [0, 0.69444, 0.17261, 0, 0.66667], + "90": [0, 0.69444, 0.11983, 0, 0.61111], + "91": [0.25, 0.75, 0.15942, 0, 0.28889], + "93": [0.25, 0.75, 0.08719, 0, 0.28889], + "94": [0, 0.69444, 0.0799, 0, 0.5], + "95": [0.35, 0.09444, 0.08616, 0, 0.5], + "97": [0, 0.44444, 0.00981, 0, 0.48056], + "98": [0, 0.69444, 0.03057, 0, 0.51667], + "99": [0, 0.44444, 0.08336, 0, 0.44445], + "100": [0, 0.69444, 0.09483, 0, 0.51667], + "101": [0, 0.44444, 0.06778, 0, 0.44445], + "102": [0, 0.69444, 0.21705, 0, 0.30556], + "103": [0.19444, 0.44444, 0.10836, 0, 0.5], + "104": [0, 0.69444, 0.01778, 0, 0.51667], + "105": [0, 0.67937, 0.09718, 0, 0.23889], + "106": [0.19444, 0.67937, 0.09162, 0, 0.26667], + "107": [0, 0.69444, 0.08336, 0, 0.48889], + "108": [0, 0.69444, 0.09483, 0, 0.23889], + "109": [0, 0.44444, 0.01778, 0, 0.79445], + "110": [0, 0.44444, 0.01778, 0, 0.51667], + "111": [0, 0.44444, 0.06613, 0, 0.5], + "112": [0.19444, 0.44444, 0.0389, 0, 0.51667], + "113": [0.19444, 0.44444, 0.04169, 0, 0.51667], + "114": [0, 0.44444, 0.10836, 0, 0.34167], + "115": [0, 0.44444, 0.0778, 0, 0.38333], + "116": [0, 0.57143, 0.07225, 0, 0.36111], + "117": [0, 0.44444, 0.04169, 0, 0.51667], + "118": [0, 0.44444, 0.10836, 0, 0.46111], + "119": [0, 0.44444, 0.10836, 0, 0.68334], + "120": [0, 0.44444, 0.09169, 0, 0.46111], + "121": [0.19444, 0.44444, 0.10836, 0, 0.46111], + "122": [0, 0.44444, 0.08752, 0, 0.43472], + "126": [0.35, 0.32659, 0.08826, 0, 0.5], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.67937, 0.06385, 0, 0.5], + "176": [0, 0.69444, 0, 0, 0.73752], + "184": [0.17014, 0, 0, 0, 0.44445], + "305": [0, 0.44444, 0.04169, 0, 0.23889], + "567": [0.19444, 0.44444, 0.04169, 0, 0.26667], + "710": [0, 0.69444, 0.0799, 0, 0.5], + "711": [0, 0.63194, 0.08432, 0, 0.5], + "713": [0, 0.60889, 0.08776, 0, 0.5], + "714": [0, 0.69444, 0.09205, 0, 0.5], + "715": [0, 0.69444, 0, 0, 0.5], + "728": [0, 0.69444, 0.09483, 0, 0.5], + "729": [0, 0.67937, 0.07774, 0, 0.27778], + "730": [0, 0.69444, 0, 0, 0.73752], + "732": [0, 0.67659, 0.08826, 0, 0.5], + "733": [0, 0.69444, 0.09205, 0, 0.5], + "915": [0, 0.69444, 0.13372, 0, 0.54167], + "916": [0, 0.69444, 0, 0, 0.83334], + "920": [0, 0.69444, 0.07555, 0, 0.77778], + "923": [0, 0.69444, 0, 0, 0.61111], + "926": [0, 0.69444, 0.12816, 0, 0.66667], + "928": [0, 0.69444, 0.08094, 0, 0.70834], + "931": [0, 0.69444, 0.11983, 0, 0.72222], + "933": [0, 0.69444, 0.09031, 0, 0.77778], + "934": [0, 0.69444, 0.04603, 0, 0.72222], + "936": [0, 0.69444, 0.09031, 0, 0.77778], + "937": [0, 0.69444, 0.08293, 0, 0.72222], + "8211": [0, 0.44444, 0.08616, 0, 0.5], + "8212": [0, 0.44444, 0.08616, 0, 1.0], + "8216": [0, 0.69444, 0.07816, 0, 0.27778], + "8217": [0, 0.69444, 0.07816, 0, 0.27778], + "8220": [0, 0.69444, 0.14205, 0, 0.5], + "8221": [0, 0.69444, 0.00316, 0, 0.5] + }, + "SansSerif-Regular": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0, 0, 0.31945], + "34": [0, 0.69444, 0, 0, 0.5], + "35": [0.19444, 0.69444, 0, 0, 0.83334], + "36": [0.05556, 0.75, 0, 0, 0.5], + "37": [0.05556, 0.75, 0, 0, 0.83334], + "38": [0, 0.69444, 0, 0, 0.75834], + "39": [0, 0.69444, 0, 0, 0.27778], + "40": [0.25, 0.75, 0, 0, 0.38889], + "41": [0.25, 0.75, 0, 0, 0.38889], + "42": [0, 0.75, 0, 0, 0.5], + "43": [0.08333, 0.58333, 0, 0, 0.77778], + "44": [0.125, 0.08333, 0, 0, 0.27778], + "45": [0, 0.44444, 0, 0, 0.33333], + "46": [0, 0.08333, 0, 0, 0.27778], + "47": [0.25, 0.75, 0, 0, 0.5], + "48": [0, 0.65556, 0, 0, 0.5], + "49": [0, 0.65556, 0, 0, 0.5], + "50": [0, 0.65556, 0, 0, 0.5], + "51": [0, 0.65556, 0, 0, 0.5], + "52": [0, 0.65556, 0, 0, 0.5], + "53": [0, 0.65556, 0, 0, 0.5], + "54": [0, 0.65556, 0, 0, 0.5], + "55": [0, 0.65556, 0, 0, 0.5], + "56": [0, 0.65556, 0, 0, 0.5], + "57": [0, 0.65556, 0, 0, 0.5], + "58": [0, 0.44444, 0, 0, 0.27778], + "59": [0.125, 0.44444, 0, 0, 0.27778], + "61": [-0.13, 0.37, 0, 0, 0.77778], + "63": [0, 0.69444, 0, 0, 0.47222], + "64": [0, 0.69444, 0, 0, 0.66667], + "65": [0, 0.69444, 0, 0, 0.66667], + "66": [0, 0.69444, 0, 0, 0.66667], + "67": [0, 0.69444, 0, 0, 0.63889], + "68": [0, 0.69444, 0, 0, 0.72223], + "69": [0, 0.69444, 0, 0, 0.59722], + "70": [0, 0.69444, 0, 0, 0.56945], + "71": [0, 0.69444, 0, 0, 0.66667], + "72": [0, 0.69444, 0, 0, 0.70834], + "73": [0, 0.69444, 0, 0, 0.27778], + "74": [0, 0.69444, 0, 0, 0.47222], + "75": [0, 0.69444, 0, 0, 0.69445], + "76": [0, 0.69444, 0, 0, 0.54167], + "77": [0, 0.69444, 0, 0, 0.875], + "78": [0, 0.69444, 0, 0, 0.70834], + "79": [0, 0.69444, 0, 0, 0.73611], + "80": [0, 0.69444, 0, 0, 0.63889], + "81": [0.125, 0.69444, 0, 0, 0.73611], + "82": [0, 0.69444, 0, 0, 0.64584], + "83": [0, 0.69444, 0, 0, 0.55556], + "84": [0, 0.69444, 0, 0, 0.68056], + "85": [0, 0.69444, 0, 0, 0.6875], + "86": [0, 0.69444, 0.01389, 0, 0.66667], + "87": [0, 0.69444, 0.01389, 0, 0.94445], + "88": [0, 0.69444, 0, 0, 0.66667], + "89": [0, 0.69444, 0.025, 0, 0.66667], + "90": [0, 0.69444, 0, 0, 0.61111], + "91": [0.25, 0.75, 0, 0, 0.28889], + "93": [0.25, 0.75, 0, 0, 0.28889], + "94": [0, 0.69444, 0, 0, 0.5], + "95": [0.35, 0.09444, 0.02778, 0, 0.5], + "97": [0, 0.44444, 0, 0, 0.48056], + "98": [0, 0.69444, 0, 0, 0.51667], + "99": [0, 0.44444, 0, 0, 0.44445], + "100": [0, 0.69444, 0, 0, 0.51667], + "101": [0, 0.44444, 0, 0, 0.44445], + "102": [0, 0.69444, 0.06944, 0, 0.30556], + "103": [0.19444, 0.44444, 0.01389, 0, 0.5], + "104": [0, 0.69444, 0, 0, 0.51667], + "105": [0, 0.67937, 0, 0, 0.23889], + "106": [0.19444, 0.67937, 0, 0, 0.26667], + "107": [0, 0.69444, 0, 0, 0.48889], + "108": [0, 0.69444, 0, 0, 0.23889], + "109": [0, 0.44444, 0, 0, 0.79445], + "110": [0, 0.44444, 0, 0, 0.51667], + "111": [0, 0.44444, 0, 0, 0.5], + "112": [0.19444, 0.44444, 0, 0, 0.51667], + "113": [0.19444, 0.44444, 0, 0, 0.51667], + "114": [0, 0.44444, 0.01389, 0, 0.34167], + "115": [0, 0.44444, 0, 0, 0.38333], + "116": [0, 0.57143, 0, 0, 0.36111], + "117": [0, 0.44444, 0, 0, 0.51667], + "118": [0, 0.44444, 0.01389, 0, 0.46111], + "119": [0, 0.44444, 0.01389, 0, 0.68334], + "120": [0, 0.44444, 0, 0, 0.46111], + "121": [0.19444, 0.44444, 0.01389, 0, 0.46111], + "122": [0, 0.44444, 0, 0, 0.43472], + "126": [0.35, 0.32659, 0, 0, 0.5], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.67937, 0, 0, 0.5], + "176": [0, 0.69444, 0, 0, 0.66667], + "184": [0.17014, 0, 0, 0, 0.44445], + "305": [0, 0.44444, 0, 0, 0.23889], + "567": [0.19444, 0.44444, 0, 0, 0.26667], + "710": [0, 0.69444, 0, 0, 0.5], + "711": [0, 0.63194, 0, 0, 0.5], + "713": [0, 0.60889, 0, 0, 0.5], + "714": [0, 0.69444, 0, 0, 0.5], + "715": [0, 0.69444, 0, 0, 0.5], + "728": [0, 0.69444, 0, 0, 0.5], + "729": [0, 0.67937, 0, 0, 0.27778], + "730": [0, 0.69444, 0, 0, 0.66667], + "732": [0, 0.67659, 0, 0, 0.5], + "733": [0, 0.69444, 0, 0, 0.5], + "915": [0, 0.69444, 0, 0, 0.54167], + "916": [0, 0.69444, 0, 0, 0.83334], + "920": [0, 0.69444, 0, 0, 0.77778], + "923": [0, 0.69444, 0, 0, 0.61111], + "926": [0, 0.69444, 0, 0, 0.66667], + "928": [0, 0.69444, 0, 0, 0.70834], + "931": [0, 0.69444, 0, 0, 0.72222], + "933": [0, 0.69444, 0, 0, 0.77778], + "934": [0, 0.69444, 0, 0, 0.72222], + "936": [0, 0.69444, 0, 0, 0.77778], + "937": [0, 0.69444, 0, 0, 0.72222], + "8211": [0, 0.44444, 0.02778, 0, 0.5], + "8212": [0, 0.44444, 0.02778, 0, 1.0], + "8216": [0, 0.69444, 0, 0, 0.27778], + "8217": [0, 0.69444, 0, 0, 0.27778], + "8220": [0, 0.69444, 0, 0, 0.5], + "8221": [0, 0.69444, 0, 0, 0.5] + }, + "Script-Regular": { + "32": [0, 0, 0, 0, 0.25], + "65": [0, 0.7, 0.22925, 0, 0.80253], + "66": [0, 0.7, 0.04087, 0, 0.90757], + "67": [0, 0.7, 0.1689, 0, 0.66619], + "68": [0, 0.7, 0.09371, 0, 0.77443], + "69": [0, 0.7, 0.18583, 0, 0.56162], + "70": [0, 0.7, 0.13634, 0, 0.89544], + "71": [0, 0.7, 0.17322, 0, 0.60961], + "72": [0, 0.7, 0.29694, 0, 0.96919], + "73": [0, 0.7, 0.19189, 0, 0.80907], + "74": [0.27778, 0.7, 0.19189, 0, 1.05159], + "75": [0, 0.7, 0.31259, 0, 0.91364], + "76": [0, 0.7, 0.19189, 0, 0.87373], + "77": [0, 0.7, 0.15981, 0, 1.08031], + "78": [0, 0.7, 0.3525, 0, 0.9015], + "79": [0, 0.7, 0.08078, 0, 0.73787], + "80": [0, 0.7, 0.08078, 0, 1.01262], + "81": [0, 0.7, 0.03305, 0, 0.88282], + "82": [0, 0.7, 0.06259, 0, 0.85], + "83": [0, 0.7, 0.19189, 0, 0.86767], + "84": [0, 0.7, 0.29087, 0, 0.74697], + "85": [0, 0.7, 0.25815, 0, 0.79996], + "86": [0, 0.7, 0.27523, 0, 0.62204], + "87": [0, 0.7, 0.27523, 0, 0.80532], + "88": [0, 0.7, 0.26006, 0, 0.94445], + "89": [0, 0.7, 0.2939, 0, 0.70961], + "90": [0, 0.7, 0.24037, 0, 0.8212], + "160": [0, 0, 0, 0, 0.25] + }, + "Size1-Regular": { + "32": [0, 0, 0, 0, 0.25], + "40": [0.35001, 0.85, 0, 0, 0.45834], + "41": [0.35001, 0.85, 0, 0, 0.45834], + "47": [0.35001, 0.85, 0, 0, 0.57778], + "91": [0.35001, 0.85, 0, 0, 0.41667], + "92": [0.35001, 0.85, 0, 0, 0.57778], + "93": [0.35001, 0.85, 0, 0, 0.41667], + "123": [0.35001, 0.85, 0, 0, 0.58334], + "125": [0.35001, 0.85, 0, 0, 0.58334], + "160": [0, 0, 0, 0, 0.25], + "710": [0, 0.72222, 0, 0, 0.55556], + "732": [0, 0.72222, 0, 0, 0.55556], + "770": [0, 0.72222, 0, 0, 0.55556], + "771": [0, 0.72222, 0, 0, 0.55556], + "8214": [-0.00099, 0.601, 0, 0, 0.77778], + "8593": [1e-05, 0.6, 0, 0, 0.66667], + "8595": [1e-05, 0.6, 0, 0, 0.66667], + "8657": [1e-05, 0.6, 0, 0, 0.77778], + "8659": [1e-05, 0.6, 0, 0, 0.77778], + "8719": [0.25001, 0.75, 0, 0, 0.94445], + "8720": [0.25001, 0.75, 0, 0, 0.94445], + "8721": [0.25001, 0.75, 0, 0, 1.05556], + "8730": [0.35001, 0.85, 0, 0, 1.0], + "8739": [-0.00599, 0.606, 0, 0, 0.33333], + "8741": [-0.00599, 0.606, 0, 0, 0.55556], + "8747": [0.30612, 0.805, 0.19445, 0, 0.47222], + "8748": [0.306, 0.805, 0.19445, 0, 0.47222], + "8749": [0.306, 0.805, 0.19445, 0, 0.47222], + "8750": [0.30612, 0.805, 0.19445, 0, 0.47222], + "8896": [0.25001, 0.75, 0, 0, 0.83334], + "8897": [0.25001, 0.75, 0, 0, 0.83334], + "8898": [0.25001, 0.75, 0, 0, 0.83334], + "8899": [0.25001, 0.75, 0, 0, 0.83334], + "8968": [0.35001, 0.85, 0, 0, 0.47222], + "8969": [0.35001, 0.85, 0, 0, 0.47222], + "8970": [0.35001, 0.85, 0, 0, 0.47222], + "8971": [0.35001, 0.85, 0, 0, 0.47222], + "9168": [-0.00099, 0.601, 0, 0, 0.66667], + "10216": [0.35001, 0.85, 0, 0, 0.47222], + "10217": [0.35001, 0.85, 0, 0, 0.47222], + "10752": [0.25001, 0.75, 0, 0, 1.11111], + "10753": [0.25001, 0.75, 0, 0, 1.11111], + "10754": [0.25001, 0.75, 0, 0, 1.11111], + "10756": [0.25001, 0.75, 0, 0, 0.83334], + "10758": [0.25001, 0.75, 0, 0, 0.83334] + }, + "Size2-Regular": { + "32": [0, 0, 0, 0, 0.25], + "40": [0.65002, 1.15, 0, 0, 0.59722], + "41": [0.65002, 1.15, 0, 0, 0.59722], + "47": [0.65002, 1.15, 0, 0, 0.81111], + "91": [0.65002, 1.15, 0, 0, 0.47222], + "92": [0.65002, 1.15, 0, 0, 0.81111], + "93": [0.65002, 1.15, 0, 0, 0.47222], + "123": [0.65002, 1.15, 0, 0, 0.66667], + "125": [0.65002, 1.15, 0, 0, 0.66667], + "160": [0, 0, 0, 0, 0.25], + "710": [0, 0.75, 0, 0, 1.0], + "732": [0, 0.75, 0, 0, 1.0], + "770": [0, 0.75, 0, 0, 1.0], + "771": [0, 0.75, 0, 0, 1.0], + "8719": [0.55001, 1.05, 0, 0, 1.27778], + "8720": [0.55001, 1.05, 0, 0, 1.27778], + "8721": [0.55001, 1.05, 0, 0, 1.44445], + "8730": [0.65002, 1.15, 0, 0, 1.0], + "8747": [0.86225, 1.36, 0.44445, 0, 0.55556], + "8748": [0.862, 1.36, 0.44445, 0, 0.55556], + "8749": [0.862, 1.36, 0.44445, 0, 0.55556], + "8750": [0.86225, 1.36, 0.44445, 0, 0.55556], + "8896": [0.55001, 1.05, 0, 0, 1.11111], + "8897": [0.55001, 1.05, 0, 0, 1.11111], + "8898": [0.55001, 1.05, 0, 0, 1.11111], + "8899": [0.55001, 1.05, 0, 0, 1.11111], + "8968": [0.65002, 1.15, 0, 0, 0.52778], + "8969": [0.65002, 1.15, 0, 0, 0.52778], + "8970": [0.65002, 1.15, 0, 0, 0.52778], + "8971": [0.65002, 1.15, 0, 0, 0.52778], + "10216": [0.65002, 1.15, 0, 0, 0.61111], + "10217": [0.65002, 1.15, 0, 0, 0.61111], + "10752": [0.55001, 1.05, 0, 0, 1.51112], + "10753": [0.55001, 1.05, 0, 0, 1.51112], + "10754": [0.55001, 1.05, 0, 0, 1.51112], + "10756": [0.55001, 1.05, 0, 0, 1.11111], + "10758": [0.55001, 1.05, 0, 0, 1.11111] + }, + "Size3-Regular": { + "32": [0, 0, 0, 0, 0.25], + "40": [0.95003, 1.45, 0, 0, 0.73611], + "41": [0.95003, 1.45, 0, 0, 0.73611], + "47": [0.95003, 1.45, 0, 0, 1.04445], + "91": [0.95003, 1.45, 0, 0, 0.52778], + "92": [0.95003, 1.45, 0, 0, 1.04445], + "93": [0.95003, 1.45, 0, 0, 0.52778], + "123": [0.95003, 1.45, 0, 0, 0.75], + "125": [0.95003, 1.45, 0, 0, 0.75], + "160": [0, 0, 0, 0, 0.25], + "710": [0, 0.75, 0, 0, 1.44445], + "732": [0, 0.75, 0, 0, 1.44445], + "770": [0, 0.75, 0, 0, 1.44445], + "771": [0, 0.75, 0, 0, 1.44445], + "8730": [0.95003, 1.45, 0, 0, 1.0], + "8968": [0.95003, 1.45, 0, 0, 0.58334], + "8969": [0.95003, 1.45, 0, 0, 0.58334], + "8970": [0.95003, 1.45, 0, 0, 0.58334], + "8971": [0.95003, 1.45, 0, 0, 0.58334], + "10216": [0.95003, 1.45, 0, 0, 0.75], + "10217": [0.95003, 1.45, 0, 0, 0.75] + }, + "Size4-Regular": { + "32": [0, 0, 0, 0, 0.25], + "40": [1.25003, 1.75, 0, 0, 0.79167], + "41": [1.25003, 1.75, 0, 0, 0.79167], + "47": [1.25003, 1.75, 0, 0, 1.27778], + "91": [1.25003, 1.75, 0, 0, 0.58334], + "92": [1.25003, 1.75, 0, 0, 1.27778], + "93": [1.25003, 1.75, 0, 0, 0.58334], + "123": [1.25003, 1.75, 0, 0, 0.80556], + "125": [1.25003, 1.75, 0, 0, 0.80556], + "160": [0, 0, 0, 0, 0.25], + "710": [0, 0.825, 0, 0, 1.8889], + "732": [0, 0.825, 0, 0, 1.8889], + "770": [0, 0.825, 0, 0, 1.8889], + "771": [0, 0.825, 0, 0, 1.8889], + "8730": [1.25003, 1.75, 0, 0, 1.0], + "8968": [1.25003, 1.75, 0, 0, 0.63889], + "8969": [1.25003, 1.75, 0, 0, 0.63889], + "8970": [1.25003, 1.75, 0, 0, 0.63889], + "8971": [1.25003, 1.75, 0, 0, 0.63889], + "9115": [0.64502, 1.155, 0, 0, 0.875], + "9116": [1e-05, 0.6, 0, 0, 0.875], + "9117": [0.64502, 1.155, 0, 0, 0.875], + "9118": [0.64502, 1.155, 0, 0, 0.875], + "9119": [1e-05, 0.6, 0, 0, 0.875], + "9120": [0.64502, 1.155, 0, 0, 0.875], + "9121": [0.64502, 1.155, 0, 0, 0.66667], + "9122": [-0.00099, 0.601, 0, 0, 0.66667], + "9123": [0.64502, 1.155, 0, 0, 0.66667], + "9124": [0.64502, 1.155, 0, 0, 0.66667], + "9125": [-0.00099, 0.601, 0, 0, 0.66667], + "9126": [0.64502, 1.155, 0, 0, 0.66667], + "9127": [1e-05, 0.9, 0, 0, 0.88889], + "9128": [0.65002, 1.15, 0, 0, 0.88889], + "9129": [0.90001, 0, 0, 0, 0.88889], + "9130": [0, 0.3, 0, 0, 0.88889], + "9131": [1e-05, 0.9, 0, 0, 0.88889], + "9132": [0.65002, 1.15, 0, 0, 0.88889], + "9133": [0.90001, 0, 0, 0, 0.88889], + "9143": [0.88502, 0.915, 0, 0, 1.05556], + "10216": [1.25003, 1.75, 0, 0, 0.80556], + "10217": [1.25003, 1.75, 0, 0, 0.80556], + "57344": [-0.00499, 0.605, 0, 0, 1.05556], + "57345": [-0.00499, 0.605, 0, 0, 1.05556], + "57680": [0, 0.12, 0, 0, 0.45], + "57681": [0, 0.12, 0, 0, 0.45], + "57682": [0, 0.12, 0, 0, 0.45], + "57683": [0, 0.12, 0, 0, 0.45] + }, + "Typewriter-Regular": { + "32": [0, 0, 0, 0, 0.525], + "33": [0, 0.61111, 0, 0, 0.525], + "34": [0, 0.61111, 0, 0, 0.525], + "35": [0, 0.61111, 0, 0, 0.525], + "36": [0.08333, 0.69444, 0, 0, 0.525], + "37": [0.08333, 0.69444, 0, 0, 0.525], + "38": [0, 0.61111, 0, 0, 0.525], + "39": [0, 0.61111, 0, 0, 0.525], + "40": [0.08333, 0.69444, 0, 0, 0.525], + "41": [0.08333, 0.69444, 0, 0, 0.525], + "42": [0, 0.52083, 0, 0, 0.525], + "43": [-0.08056, 0.53055, 0, 0, 0.525], + "44": [0.13889, 0.125, 0, 0, 0.525], + "45": [-0.08056, 0.53055, 0, 0, 0.525], + "46": [0, 0.125, 0, 0, 0.525], + "47": [0.08333, 0.69444, 0, 0, 0.525], + "48": [0, 0.61111, 0, 0, 0.525], + "49": [0, 0.61111, 0, 0, 0.525], + "50": [0, 0.61111, 0, 0, 0.525], + "51": [0, 0.61111, 0, 0, 0.525], + "52": [0, 0.61111, 0, 0, 0.525], + "53": [0, 0.61111, 0, 0, 0.525], + "54": [0, 0.61111, 0, 0, 0.525], + "55": [0, 0.61111, 0, 0, 0.525], + "56": [0, 0.61111, 0, 0, 0.525], + "57": [0, 0.61111, 0, 0, 0.525], + "58": [0, 0.43056, 0, 0, 0.525], + "59": [0.13889, 0.43056, 0, 0, 0.525], + "60": [-0.05556, 0.55556, 0, 0, 0.525], + "61": [-0.19549, 0.41562, 0, 0, 0.525], + "62": [-0.05556, 0.55556, 0, 0, 0.525], + "63": [0, 0.61111, 0, 0, 0.525], + "64": [0, 0.61111, 0, 0, 0.525], + "65": [0, 0.61111, 0, 0, 0.525], + "66": [0, 0.61111, 0, 0, 0.525], + "67": [0, 0.61111, 0, 0, 0.525], + "68": [0, 0.61111, 0, 0, 0.525], + "69": [0, 0.61111, 0, 0, 0.525], + "70": [0, 0.61111, 0, 0, 0.525], + "71": [0, 0.61111, 0, 0, 0.525], + "72": [0, 0.61111, 0, 0, 0.525], + "73": [0, 0.61111, 0, 0, 0.525], + "74": [0, 0.61111, 0, 0, 0.525], + "75": [0, 0.61111, 0, 0, 0.525], + "76": [0, 0.61111, 0, 0, 0.525], + "77": [0, 0.61111, 0, 0, 0.525], + "78": [0, 0.61111, 0, 0, 0.525], + "79": [0, 0.61111, 0, 0, 0.525], + "80": [0, 0.61111, 0, 0, 0.525], + "81": [0.13889, 0.61111, 0, 0, 0.525], + "82": [0, 0.61111, 0, 0, 0.525], + "83": [0, 0.61111, 0, 0, 0.525], + "84": [0, 0.61111, 0, 0, 0.525], + "85": [0, 0.61111, 0, 0, 0.525], + "86": [0, 0.61111, 0, 0, 0.525], + "87": [0, 0.61111, 0, 0, 0.525], + "88": [0, 0.61111, 0, 0, 0.525], + "89": [0, 0.61111, 0, 0, 0.525], + "90": [0, 0.61111, 0, 0, 0.525], + "91": [0.08333, 0.69444, 0, 0, 0.525], + "92": [0.08333, 0.69444, 0, 0, 0.525], + "93": [0.08333, 0.69444, 0, 0, 0.525], + "94": [0, 0.61111, 0, 0, 0.525], + "95": [0.09514, 0, 0, 0, 0.525], + "96": [0, 0.61111, 0, 0, 0.525], + "97": [0, 0.43056, 0, 0, 0.525], + "98": [0, 0.61111, 0, 0, 0.525], + "99": [0, 0.43056, 0, 0, 0.525], + "100": [0, 0.61111, 0, 0, 0.525], + "101": [0, 0.43056, 0, 0, 0.525], + "102": [0, 0.61111, 0, 0, 0.525], + "103": [0.22222, 0.43056, 0, 0, 0.525], + "104": [0, 0.61111, 0, 0, 0.525], + "105": [0, 0.61111, 0, 0, 0.525], + "106": [0.22222, 0.61111, 0, 0, 0.525], + "107": [0, 0.61111, 0, 0, 0.525], + "108": [0, 0.61111, 0, 0, 0.525], + "109": [0, 0.43056, 0, 0, 0.525], + "110": [0, 0.43056, 0, 0, 0.525], + "111": [0, 0.43056, 0, 0, 0.525], + "112": [0.22222, 0.43056, 0, 0, 0.525], + "113": [0.22222, 0.43056, 0, 0, 0.525], + "114": [0, 0.43056, 0, 0, 0.525], + "115": [0, 0.43056, 0, 0, 0.525], + "116": [0, 0.55358, 0, 0, 0.525], + "117": [0, 0.43056, 0, 0, 0.525], + "118": [0, 0.43056, 0, 0, 0.525], + "119": [0, 0.43056, 0, 0, 0.525], + "120": [0, 0.43056, 0, 0, 0.525], + "121": [0.22222, 0.43056, 0, 0, 0.525], + "122": [0, 0.43056, 0, 0, 0.525], + "123": [0.08333, 0.69444, 0, 0, 0.525], + "124": [0.08333, 0.69444, 0, 0, 0.525], + "125": [0.08333, 0.69444, 0, 0, 0.525], + "126": [0, 0.61111, 0, 0, 0.525], + "127": [0, 0.61111, 0, 0, 0.525], + "160": [0, 0, 0, 0, 0.525], + "176": [0, 0.61111, 0, 0, 0.525], + "184": [0.19445, 0, 0, 0, 0.525], + "305": [0, 0.43056, 0, 0, 0.525], + "567": [0.22222, 0.43056, 0, 0, 0.525], + "711": [0, 0.56597, 0, 0, 0.525], + "713": [0, 0.56555, 0, 0, 0.525], + "714": [0, 0.61111, 0, 0, 0.525], + "715": [0, 0.61111, 0, 0, 0.525], + "728": [0, 0.61111, 0, 0, 0.525], + "730": [0, 0.61111, 0, 0, 0.525], + "770": [0, 0.61111, 0, 0, 0.525], + "771": [0, 0.61111, 0, 0, 0.525], + "776": [0, 0.61111, 0, 0, 0.525], + "915": [0, 0.61111, 0, 0, 0.525], + "916": [0, 0.61111, 0, 0, 0.525], + "920": [0, 0.61111, 0, 0, 0.525], + "923": [0, 0.61111, 0, 0, 0.525], + "926": [0, 0.61111, 0, 0, 0.525], + "928": [0, 0.61111, 0, 0, 0.525], + "931": [0, 0.61111, 0, 0, 0.525], + "933": [0, 0.61111, 0, 0, 0.525], + "934": [0, 0.61111, 0, 0, 0.525], + "936": [0, 0.61111, 0, 0, 0.525], + "937": [0, 0.61111, 0, 0, 0.525], + "8216": [0, 0.61111, 0, 0, 0.525], + "8217": [0, 0.61111, 0, 0, 0.525], + "8242": [0, 0.61111, 0, 0, 0.525], + "9251": [0.11111, 0.21944, 0, 0, 0.525] + } +}; + +/** + * This file contains metrics regarding fonts and individual symbols. The sigma + * and xi variables, as well as the metricMap map contain data extracted from + * TeX, TeX font metrics, and the TTF files. These data are then exposed via the + * `metrics` variable and the getCharacterMetrics function. + */ +// In TeX, there are actually three sets of dimensions, one for each of +// textstyle (size index 5 and higher: >=9pt), scriptstyle (size index 3 and 4: +// 7-8pt), and scriptscriptstyle (size index 1 and 2: 5-6pt). These are +// provided in the arrays below, in that order. +// +// The font metrics are stored in fonts cmsy10, cmsy7, and cmsy5 respectively. +// This was determined by running the following script: +// +// latex -interaction=nonstopmode \ +// '\documentclass{article}\usepackage{amsmath}\begin{document}' \ +// '$a$ \expandafter\show\the\textfont2' \ +// '\expandafter\show\the\scriptfont2' \ +// '\expandafter\show\the\scriptscriptfont2' \ +// '\stop' +// +// The metrics themselves were retrieved using the following commands: +// +// tftopl cmsy10 +// tftopl cmsy7 +// tftopl cmsy5 +// +// The output of each of these commands is quite lengthy. The only part we +// care about is the FONTDIMEN section. Each value is measured in EMs. +var sigmasAndXis = { + slant: [0.250, 0.250, 0.250], + // sigma1 + space: [0.000, 0.000, 0.000], + // sigma2 + stretch: [0.000, 0.000, 0.000], + // sigma3 + shrink: [0.000, 0.000, 0.000], + // sigma4 + xHeight: [0.431, 0.431, 0.431], + // sigma5 + quad: [1.000, 1.171, 1.472], + // sigma6 + extraSpace: [0.000, 0.000, 0.000], + // sigma7 + num1: [0.677, 0.732, 0.925], + // sigma8 + num2: [0.394, 0.384, 0.387], + // sigma9 + num3: [0.444, 0.471, 0.504], + // sigma10 + denom1: [0.686, 0.752, 1.025], + // sigma11 + denom2: [0.345, 0.344, 0.532], + // sigma12 + sup1: [0.413, 0.503, 0.504], + // sigma13 + sup2: [0.363, 0.431, 0.404], + // sigma14 + sup3: [0.289, 0.286, 0.294], + // sigma15 + sub1: [0.150, 0.143, 0.200], + // sigma16 + sub2: [0.247, 0.286, 0.400], + // sigma17 + supDrop: [0.386, 0.353, 0.494], + // sigma18 + subDrop: [0.050, 0.071, 0.100], + // sigma19 + delim1: [2.390, 1.700, 1.980], + // sigma20 + delim2: [1.010, 1.157, 1.420], + // sigma21 + axisHeight: [0.250, 0.250, 0.250], + // sigma22 + // These font metrics are extracted from TeX by using tftopl on cmex10.tfm; + // they correspond to the font parameters of the extension fonts (family 3). + // See the TeXbook, page 441. In AMSTeX, the extension fonts scale; to + // match cmex7, we'd use cmex7.tfm values for script and scriptscript + // values. + defaultRuleThickness: [0.04, 0.049, 0.049], + // xi8; cmex7: 0.049 + bigOpSpacing1: [0.111, 0.111, 0.111], + // xi9 + bigOpSpacing2: [0.166, 0.166, 0.166], + // xi10 + bigOpSpacing3: [0.2, 0.2, 0.2], + // xi11 + bigOpSpacing4: [0.6, 0.611, 0.611], + // xi12; cmex7: 0.611 + bigOpSpacing5: [0.1, 0.143, 0.143], + // xi13; cmex7: 0.143 + // The \sqrt rule width is taken from the height of the surd character. + // Since we use the same font at all sizes, this thickness doesn't scale. + sqrtRuleThickness: [0.04, 0.04, 0.04], + // This value determines how large a pt is, for metrics which are defined + // in terms of pts. + // This value is also used in katex.scss; if you change it make sure the + // values match. + ptPerEm: [10.0, 10.0, 10.0], + // The space between adjacent `|` columns in an array definition. From + // `\showthe\doublerulesep` in LaTeX. Equals 2.0 / ptPerEm. + doubleRuleSep: [0.2, 0.2, 0.2], + // The width of separator lines in {array} environments. From + // `\showthe\arrayrulewidth` in LaTeX. Equals 0.4 / ptPerEm. + arrayRuleWidth: [0.04, 0.04, 0.04], + // Two values from LaTeX source2e: + fboxsep: [0.3, 0.3, 0.3], + // 3 pt / ptPerEm + fboxrule: [0.04, 0.04, 0.04] // 0.4 pt / ptPerEm + +}; // This map contains a mapping from font name and character code to character +// should have Latin-1 and Cyrillic characters, but may not depending on the +// operating system. The metrics do not account for extra height from the +// accents. In the case of Cyrillic characters which have both ascenders and +// descenders we prefer approximations with ascenders, primarily to prevent +// the fraction bar or root line from intersecting the glyph. +// TODO(kevinb) allow union of multiple glyph metrics for better accuracy. + +var extraCharacterMap = { + // Latin-1 + 'Å': 'A', + 'Ð': 'D', + 'Þ': 'o', + 'å': 'a', + 'ð': 'd', + 'þ': 'o', + // Cyrillic + 'А': 'A', + 'Б': 'B', + 'В': 'B', + 'Г': 'F', + 'Д': 'A', + 'Е': 'E', + 'Ж': 'K', + 'З': '3', + 'И': 'N', + 'Й': 'N', + 'К': 'K', + 'Л': 'N', + 'М': 'M', + 'Н': 'H', + 'О': 'O', + 'П': 'N', + 'Р': 'P', + 'С': 'C', + 'Т': 'T', + 'У': 'y', + 'Ф': 'O', + 'Х': 'X', + 'Ц': 'U', + 'Ч': 'h', + 'Ш': 'W', + 'Щ': 'W', + 'Ъ': 'B', + 'Ы': 'X', + 'Ь': 'B', + 'Э': '3', + 'Ю': 'X', + 'Я': 'R', + 'а': 'a', + 'б': 'b', + 'в': 'a', + 'г': 'r', + 'д': 'y', + 'е': 'e', + 'ж': 'm', + 'з': 'e', + 'и': 'n', + 'й': 'n', + 'к': 'n', + 'л': 'n', + 'м': 'm', + 'н': 'n', + 'о': 'o', + 'п': 'n', + 'р': 'p', + 'с': 'c', + 'т': 'o', + 'у': 'y', + 'ф': 'b', + 'х': 'x', + 'ц': 'n', + 'ч': 'n', + 'ш': 'w', + 'щ': 'w', + 'ъ': 'a', + 'ы': 'm', + 'ь': 'a', + 'э': 'e', + 'ю': 'm', + 'я': 'r' +}; + +/** + * This function adds new font metrics to default metricMap + * It can also override existing metrics + */ +function setFontMetrics(fontName, metrics) { + fontMetricsData[fontName] = metrics; +} +/** + * This function is a convenience function for looking up information in the + * metricMap table. It takes a character as a string, and a font. + * + * Note: the `width` property may be undefined if fontMetricsData.js wasn't + * built using `Make extended_metrics`. + */ + +function getCharacterMetrics(character, font, mode) { + if (!fontMetricsData[font]) { + throw new Error("Font metrics not found for font: " + font + "."); + } + + var ch = character.charCodeAt(0); + var metrics = fontMetricsData[font][ch]; + + if (!metrics && character[0] in extraCharacterMap) { + ch = extraCharacterMap[character[0]].charCodeAt(0); + metrics = fontMetricsData[font][ch]; + } + + if (!metrics && mode === 'text') { + // We don't typically have font metrics for Asian scripts. + // But since we support them in text mode, we need to return + // some sort of metrics. + // So if the character is in a script we support but we + // don't have metrics for it, just use the metrics for + // the Latin capital letter M. This is close enough because + // we (currently) only care about the height of the glyph + // not its width. + if (supportedCodepoint(ch)) { + metrics = fontMetricsData[font][77]; // 77 is the charcode for 'M' + } + } + + if (metrics) { + return { + depth: metrics[0], + height: metrics[1], + italic: metrics[2], + skew: metrics[3], + width: metrics[4] + }; + } +} +var fontMetricsBySizeIndex = {}; +/** + * Get the font metrics for a given size. + */ + +function getGlobalMetrics(size) { + var sizeIndex; + + if (size >= 5) { + sizeIndex = 0; + } else if (size >= 3) { + sizeIndex = 1; + } else { + sizeIndex = 2; + } + + if (!fontMetricsBySizeIndex[sizeIndex]) { + var metrics = fontMetricsBySizeIndex[sizeIndex] = { + cssEmPerMu: sigmasAndXis.quad[sizeIndex] / 18 + }; + + for (var key in sigmasAndXis) { + if (sigmasAndXis.hasOwnProperty(key)) { + metrics[key] = sigmasAndXis[key][sizeIndex]; + } + } + } + + return fontMetricsBySizeIndex[sizeIndex]; +} + +/** + * This file contains information about the options that the Parser carries + * around with it while parsing. Data is held in an `Options` object, and when + * recursing, a new `Options` object can be created with the `.with*` and + * `.reset` functions. + */ +var sizeStyleMap = [// Each element contains [textsize, scriptsize, scriptscriptsize]. +// The size mappings are taken from TeX with \normalsize=10pt. +[1, 1, 1], // size1: [5, 5, 5] \tiny +[2, 1, 1], // size2: [6, 5, 5] +[3, 1, 1], // size3: [7, 5, 5] \scriptsize +[4, 2, 1], // size4: [8, 6, 5] \footnotesize +[5, 2, 1], // size5: [9, 6, 5] \small +[6, 3, 1], // size6: [10, 7, 5] \normalsize +[7, 4, 2], // size7: [12, 8, 6] \large +[8, 6, 3], // size8: [14.4, 10, 7] \Large +[9, 7, 6], // size9: [17.28, 12, 10] \LARGE +[10, 8, 7], // size10: [20.74, 14.4, 12] \huge +[11, 10, 9] // size11: [24.88, 20.74, 17.28] \HUGE +]; +var sizeMultipliers = [// fontMetrics.js:getGlobalMetrics also uses size indexes, so if +// you change size indexes, change that function. +0.5, 0.6, 0.7, 0.8, 0.9, 1.0, 1.2, 1.44, 1.728, 2.074, 2.488]; + +var sizeAtStyle = function sizeAtStyle(size, style) { + return style.size < 2 ? size : sizeStyleMap[size - 1][style.size - 1]; +}; // In these types, "" (empty string) means "no change". + + +/** + * This is the main options class. It contains the current style, size, color, + * and font. + * + * Options objects should not be modified. To create a new Options with + * different properties, call a `.having*` method. + */ +class Options { + // A font family applies to a group of fonts (i.e. SansSerif), while a font + // represents a specific font (i.e. SansSerif Bold). + // See: https://tex.stackexchange.com/questions/22350/difference-between-textrm-and-mathrm + + /** + * The base size index. + */ + constructor(data) { + this.style = void 0; + this.color = void 0; + this.size = void 0; + this.textSize = void 0; + this.phantom = void 0; + this.font = void 0; + this.fontFamily = void 0; + this.fontWeight = void 0; + this.fontShape = void 0; + this.sizeMultiplier = void 0; + this.maxSize = void 0; + this.minRuleThickness = void 0; + this._fontMetrics = void 0; + this.style = data.style; + this.color = data.color; + this.size = data.size || Options.BASESIZE; + this.textSize = data.textSize || this.size; + this.phantom = !!data.phantom; + this.font = data.font || ""; + this.fontFamily = data.fontFamily || ""; + this.fontWeight = data.fontWeight || ''; + this.fontShape = data.fontShape || ''; + this.sizeMultiplier = sizeMultipliers[this.size - 1]; + this.maxSize = data.maxSize; + this.minRuleThickness = data.minRuleThickness; + this._fontMetrics = undefined; + } + /** + * Returns a new options object with the same properties as "this". Properties + * from "extension" will be copied to the new options object. + */ + + + extend(extension) { + var data = { + style: this.style, + size: this.size, + textSize: this.textSize, + color: this.color, + phantom: this.phantom, + font: this.font, + fontFamily: this.fontFamily, + fontWeight: this.fontWeight, + fontShape: this.fontShape, + maxSize: this.maxSize, + minRuleThickness: this.minRuleThickness + }; + + for (var key in extension) { + if (extension.hasOwnProperty(key)) { + data[key] = extension[key]; + } + } + + return new Options(data); + } + /** + * Return an options object with the given style. If `this.style === style`, + * returns `this`. + */ + + + havingStyle(style) { + if (this.style === style) { + return this; + } else { + return this.extend({ + style: style, + size: sizeAtStyle(this.textSize, style) + }); + } + } + /** + * Return an options object with a cramped version of the current style. If + * the current style is cramped, returns `this`. + */ + + + havingCrampedStyle() { + return this.havingStyle(this.style.cramp()); + } + /** + * Return an options object with the given size and in at least `\textstyle`. + * Returns `this` if appropriate. + */ + + + havingSize(size) { + if (this.size === size && this.textSize === size) { + return this; + } else { + return this.extend({ + style: this.style.text(), + size: size, + textSize: size, + sizeMultiplier: sizeMultipliers[size - 1] + }); + } + } + /** + * Like `this.havingSize(BASESIZE).havingStyle(style)`. If `style` is omitted, + * changes to at least `\textstyle`. + */ + + + havingBaseStyle(style) { + style = style || this.style.text(); + var wantSize = sizeAtStyle(Options.BASESIZE, style); + + if (this.size === wantSize && this.textSize === Options.BASESIZE && this.style === style) { + return this; + } else { + return this.extend({ + style: style, + size: wantSize + }); + } + } + /** + * Remove the effect of sizing changes such as \Huge. + * Keep the effect of the current style, such as \scriptstyle. + */ + + + havingBaseSizing() { + var size; + + switch (this.style.id) { + case 4: + case 5: + size = 3; // normalsize in scriptstyle + + break; + + case 6: + case 7: + size = 1; // normalsize in scriptscriptstyle + + break; + + default: + size = 6; + // normalsize in textstyle or displaystyle + } + + return this.extend({ + style: this.style.text(), + size: size + }); + } + /** + * Create a new options object with the given color. + */ + + + withColor(color) { + return this.extend({ + color: color + }); + } + /** + * Create a new options object with "phantom" set to true. + */ + + + withPhantom() { + return this.extend({ + phantom: true + }); + } + /** + * Creates a new options object with the given math font or old text font. + * @type {[type]} + */ + + + withFont(font) { + return this.extend({ + font + }); + } + /** + * Create a new options objects with the given fontFamily. + */ + + + withTextFontFamily(fontFamily) { + return this.extend({ + fontFamily, + font: "" + }); + } + /** + * Creates a new options object with the given font weight + */ + + + withTextFontWeight(fontWeight) { + return this.extend({ + fontWeight, + font: "" + }); + } + /** + * Creates a new options object with the given font weight + */ + + + withTextFontShape(fontShape) { + return this.extend({ + fontShape, + font: "" + }); + } + /** + * Return the CSS sizing classes required to switch from enclosing options + * `oldOptions` to `this`. Returns an array of classes. + */ + + + sizingClasses(oldOptions) { + if (oldOptions.size !== this.size) { + return ["sizing", "reset-size" + oldOptions.size, "size" + this.size]; + } else { + return []; + } + } + /** + * Return the CSS sizing classes required to switch to the base size. Like + * `this.havingSize(BASESIZE).sizingClasses(this)`. + */ + + + baseSizingClasses() { + if (this.size !== Options.BASESIZE) { + return ["sizing", "reset-size" + this.size, "size" + Options.BASESIZE]; + } else { + return []; + } + } + /** + * Return the font metrics for this size. + */ + + + fontMetrics() { + if (!this._fontMetrics) { + this._fontMetrics = getGlobalMetrics(this.size); + } + + return this._fontMetrics; + } + /** + * Gets the CSS color of the current options object + */ + + + getColor() { + if (this.phantom) { + return "transparent"; + } else { + return this.color; + } + } + +} + +Options.BASESIZE = 6; + +/** + * This file does conversion between units. In particular, it provides + * calculateSize to convert other units into ems. + */ +// Thus, multiplying a length by this number converts the length from units +// into pts. Dividing the result by ptPerEm gives the number of ems +// *assuming* a font size of ptPerEm (normal size, normal style). + +var ptPerUnit = { + // https://en.wikibooks.org/wiki/LaTeX/Lengths and + // https://tex.stackexchange.com/a/8263 + "pt": 1, + // TeX point + "mm": 7227 / 2540, + // millimeter + "cm": 7227 / 254, + // centimeter + "in": 72.27, + // inch + "bp": 803 / 800, + // big (PostScript) points + "pc": 12, + // pica + "dd": 1238 / 1157, + // didot + "cc": 14856 / 1157, + // cicero (12 didot) + "nd": 685 / 642, + // new didot + "nc": 1370 / 107, + // new cicero (12 new didot) + "sp": 1 / 65536, + // scaled point (TeX's internal smallest unit) + // https://tex.stackexchange.com/a/41371 + "px": 803 / 800 // \pdfpxdimen defaults to 1 bp in pdfTeX and LuaTeX + +}; // Dictionary of relative units, for fast validity testing. + +var relativeUnit = { + "ex": true, + "em": true, + "mu": true +}; + +/** + * Determine whether the specified unit (either a string defining the unit + * or a "size" parse node containing a unit field) is valid. + */ +var validUnit = function validUnit(unit) { + if (typeof unit !== "string") { + unit = unit.unit; + } + + return unit in ptPerUnit || unit in relativeUnit || unit === "ex"; +}; +/* + * Convert a "size" parse node (with numeric "number" and string "unit" fields, + * as parsed by functions.js argType "size") into a CSS em value for the + * current style/scale. `options` gives the current options. + */ + +var calculateSize = function calculateSize(sizeValue, options) { + var scale; + + if (sizeValue.unit in ptPerUnit) { + // Absolute units + scale = ptPerUnit[sizeValue.unit] // Convert unit to pt + / options.fontMetrics().ptPerEm // Convert pt to CSS em + / options.sizeMultiplier; // Unscale to make absolute units + } else if (sizeValue.unit === "mu") { + // `mu` units scale with scriptstyle/scriptscriptstyle. + scale = options.fontMetrics().cssEmPerMu; + } else { + // Other relative units always refer to the *textstyle* font + // in the current size. + var unitOptions; + + if (options.style.isTight()) { + // isTight() means current style is script/scriptscript. + unitOptions = options.havingStyle(options.style.text()); + } else { + unitOptions = options; + } // TODO: In TeX these units are relative to the quad of the current + // *text* font, e.g. cmr10. KaTeX instead uses values from the + // comparably-sized *Computer Modern symbol* font. At 10pt, these + // match. At 7pt and 5pt, they differ: cmr7=1.138894, cmsy7=1.170641; + // cmr5=1.361133, cmsy5=1.472241. Consider $\scriptsize a\kern1emb$. + // TeX \showlists shows a kern of 1.13889 * fontsize; + // KaTeX shows a kern of 1.171 * fontsize. + + + if (sizeValue.unit === "ex") { + scale = unitOptions.fontMetrics().xHeight; + } else if (sizeValue.unit === "em") { + scale = unitOptions.fontMetrics().quad; + } else { + throw new ParseError("Invalid unit: '" + sizeValue.unit + "'"); + } + + if (unitOptions !== options) { + scale *= unitOptions.sizeMultiplier / options.sizeMultiplier; + } + } + + return Math.min(sizeValue.number * scale, options.maxSize); +}; +/** + * Round `n` to 4 decimal places, or to the nearest 1/10,000th em. See + * https://github.com/KaTeX/KaTeX/pull/2460. + */ + +var makeEm = function makeEm(n) { + return +n.toFixed(4) + "em"; +}; + +/** + * These objects store the data about the DOM nodes we create, as well as some + * extra data. They can then be transformed into real DOM nodes with the + * `toNode` function or HTML markup using `toMarkup`. They are useful for both + * storing extra properties on the nodes, as well as providing a way to easily + * work with the DOM. + * + * Similar functions for working with MathML nodes exist in mathMLTree.js. + * + * TODO: refactor `span` and `anchor` into common superclass when + * target environments support class inheritance + */ + +/** + * Create an HTML className based on a list of classes. In addition to joining + * with spaces, we also remove empty classes. + */ +var createClass = function createClass(classes) { + return classes.filter(cls => cls).join(" "); +}; + +var initNode = function initNode(classes, options, style) { + this.classes = classes || []; + this.attributes = {}; + this.height = 0; + this.depth = 0; + this.maxFontSize = 0; + this.style = style || {}; + + if (options) { + if (options.style.isTight()) { + this.classes.push("mtight"); + } + + var color = options.getColor(); + + if (color) { + this.style.color = color; + } + } +}; +/** + * Convert into an HTML node + */ + + +var toNode = function toNode(tagName) { + var node = document.createElement(tagName); // Apply the class + + node.className = createClass(this.classes); // Apply inline styles + + for (var style in this.style) { + if (this.style.hasOwnProperty(style)) { + // $FlowFixMe Flow doesn't seem to understand span.style's type. + node.style[style] = this.style[style]; + } + } // Apply attributes + + + for (var attr in this.attributes) { + if (this.attributes.hasOwnProperty(attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } // Append the children, also as HTML nodes + + + for (var i = 0; i < this.children.length; i++) { + node.appendChild(this.children[i].toNode()); + } + + return node; +}; +/** + * https://w3c.github.io/html-reference/syntax.html#syntax-attributes + * + * > Attribute Names must consist of one or more characters + * other than the space characters, U+0000 NULL, + * '"', "'", ">", "/", "=", the control characters, + * and any characters that are not defined by Unicode. + */ + + +var invalidAttributeNameRegex = /[\s"'>/=\x00-\x1f]/; +/** + * Convert into an HTML markup string + */ + +var toMarkup = function toMarkup(tagName) { + var markup = "<" + tagName; // Add the class + + if (this.classes.length) { + markup += " class=\"" + utils.escape(createClass(this.classes)) + "\""; + } + + var styles = ""; // Add the styles, after hyphenation + + for (var style in this.style) { + if (this.style.hasOwnProperty(style)) { + styles += utils.hyphenate(style) + ":" + this.style[style] + ";"; + } + } + + if (styles) { + markup += " style=\"" + utils.escape(styles) + "\""; + } // Add the attributes + + + for (var attr in this.attributes) { + if (this.attributes.hasOwnProperty(attr)) { + if (invalidAttributeNameRegex.test(attr)) { + throw new ParseError("Invalid attribute name '" + attr + "'"); + } + + markup += " " + attr + "=\"" + utils.escape(this.attributes[attr]) + "\""; + } + } + + markup += ">"; // Add the markup of the children, also as markup + + for (var i = 0; i < this.children.length; i++) { + markup += this.children[i].toMarkup(); + } + + markup += ""; + return markup; +}; // Making the type below exact with all optional fields doesn't work due to +// - https://github.com/facebook/flow/issues/4582 +// - https://github.com/facebook/flow/issues/5688 +// However, since *all* fields are optional, $Shape<> works as suggested in 5688 +// above. +// This type does not include all CSS properties. Additional properties should +// be added as needed. + + +/** + * This node represents a span node, with a className, a list of children, and + * an inline style. It also contains information about its height, depth, and + * maxFontSize. + * + * Represents two types with different uses: SvgSpan to wrap an SVG and DomSpan + * otherwise. This typesafety is important when HTML builders access a span's + * children. + */ +class Span { + constructor(classes, children, options, style) { + this.children = void 0; + this.attributes = void 0; + this.classes = void 0; + this.height = void 0; + this.depth = void 0; + this.width = void 0; + this.maxFontSize = void 0; + this.style = void 0; + initNode.call(this, classes, options, style); + this.children = children || []; + } + /** + * Sets an arbitrary attribute on the span. Warning: use this wisely. Not + * all browsers support attributes the same, and having too many custom + * attributes is probably bad. + */ + + + setAttribute(attribute, value) { + this.attributes[attribute] = value; + } + + hasClass(className) { + return utils.contains(this.classes, className); + } + + toNode() { + return toNode.call(this, "span"); + } + + toMarkup() { + return toMarkup.call(this, "span"); + } + +} +/** + * This node represents an anchor () element with a hyperlink. See `span` + * for further details. + */ + +class Anchor { + constructor(href, classes, children, options) { + this.children = void 0; + this.attributes = void 0; + this.classes = void 0; + this.height = void 0; + this.depth = void 0; + this.maxFontSize = void 0; + this.style = void 0; + initNode.call(this, classes, options); + this.children = children || []; + this.setAttribute('href', href); + } + + setAttribute(attribute, value) { + this.attributes[attribute] = value; + } + + hasClass(className) { + return utils.contains(this.classes, className); + } + + toNode() { + return toNode.call(this, "a"); + } + + toMarkup() { + return toMarkup.call(this, "a"); + } + +} +/** + * This node represents an image embed () element. + */ + +class Img { + constructor(src, alt, style) { + this.src = void 0; + this.alt = void 0; + this.classes = void 0; + this.height = void 0; + this.depth = void 0; + this.maxFontSize = void 0; + this.style = void 0; + this.alt = alt; + this.src = src; + this.classes = ["mord"]; + this.style = style; + } + + hasClass(className) { + return utils.contains(this.classes, className); + } + + toNode() { + var node = document.createElement("img"); + node.src = this.src; + node.alt = this.alt; + node.className = "mord"; // Apply inline styles + + for (var style in this.style) { + if (this.style.hasOwnProperty(style)) { + // $FlowFixMe + node.style[style] = this.style[style]; + } + } + + return node; + } + + toMarkup() { + var markup = "\"" 0) { + span = document.createElement("span"); + span.style.marginRight = makeEm(this.italic); + } + + if (this.classes.length > 0) { + span = span || document.createElement("span"); + span.className = createClass(this.classes); + } + + for (var style in this.style) { + if (this.style.hasOwnProperty(style)) { + span = span || document.createElement("span"); // $FlowFixMe Flow doesn't seem to understand span.style's type. + + span.style[style] = this.style[style]; + } + } + + if (span) { + span.appendChild(node); + return span; + } else { + return node; + } + } + /** + * Creates markup for a symbol node. + */ + + + toMarkup() { + // TODO(alpert): More duplication than I'd like from + // span.prototype.toMarkup and symbolNode.prototype.toNode... + var needsSpan = false; + var markup = " 0) { + styles += "margin-right:" + this.italic + "em;"; + } + + for (var style in this.style) { + if (this.style.hasOwnProperty(style)) { + styles += utils.hyphenate(style) + ":" + this.style[style] + ";"; + } + } + + if (styles) { + needsSpan = true; + markup += " style=\"" + utils.escape(styles) + "\""; + } + + var escaped = utils.escape(this.text); + + if (needsSpan) { + markup += ">"; + markup += escaped; + markup += ""; + return markup; + } else { + return escaped; + } + } + +} +/** + * SVG nodes are used to render stretchy wide elements. + */ + +class SvgNode { + constructor(children, attributes) { + this.children = void 0; + this.attributes = void 0; + this.children = children || []; + this.attributes = attributes || {}; + } + + toNode() { + var svgNS = "http://www.w3.org/2000/svg"; + var node = document.createElementNS(svgNS, "svg"); // Apply attributes + + for (var attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } + + for (var i = 0; i < this.children.length; i++) { + node.appendChild(this.children[i].toNode()); + } + + return node; + } + + toMarkup() { + var markup = ""; + } else { + return ""; + } + } + +} +class LineNode { + constructor(attributes) { + this.attributes = void 0; + this.attributes = attributes || {}; + } + + toNode() { + var svgNS = "http://www.w3.org/2000/svg"; + var node = document.createElementNS(svgNS, "line"); // Apply attributes + + for (var attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } + + return node; + } + + toMarkup() { + var markup = " but got " + String(group) + "."); + } +} + +/** + * This file holds a list of all no-argument functions and single-character + * symbols (like 'a' or ';'). + * + * For each of the symbols, there are three properties they can have: + * - font (required): the font to be used for this symbol. Either "main" (the + normal font), or "ams" (the ams fonts). + * - group (required): the ParseNode group type the symbol should have (i.e. + "textord", "mathord", etc). + See https://github.com/KaTeX/KaTeX/wiki/Examining-TeX#group-types + * - replace: the character that this symbol or function should be + * replaced with (i.e. "\phi" has a replace value of "\u03d5", the phi + * character in the main font). + * + * The outermost map in the table indicates what mode the symbols should be + * accepted in (e.g. "math" or "text"). + */ +// Some of these have a "-token" suffix since these are also used as `ParseNode` +// types for raw text tokens, and we want to avoid conflicts with higher-level +// `ParseNode` types. These `ParseNode`s are constructed within `Parser` by +// looking up the `symbols` map. +var ATOMS = { + "bin": 1, + "close": 1, + "inner": 1, + "open": 1, + "punct": 1, + "rel": 1 +}; +var NON_ATOMS = { + "accent-token": 1, + "mathord": 1, + "op-token": 1, + "spacing": 1, + "textord": 1 +}; +var symbols = { + "math": {}, + "text": {} +}; +/** `acceptUnicodeChar = true` is only applicable if `replace` is set. */ + +function defineSymbol(mode, font, group, replace, name, acceptUnicodeChar) { + symbols[mode][name] = { + font, + group, + replace + }; + + if (acceptUnicodeChar && replace) { + symbols[mode][replace] = symbols[mode][name]; + } +} // Some abbreviations for commonly used strings. +// This helps minify the code, and also spotting typos using jshint. +// modes: + +var math = "math"; +var text = "text"; // fonts: + +var main = "main"; +var ams = "ams"; // groups: + +var accent = "accent-token"; +var bin = "bin"; +var close = "close"; +var inner = "inner"; +var mathord = "mathord"; +var op = "op-token"; +var open = "open"; +var punct = "punct"; +var rel = "rel"; +var spacing = "spacing"; +var textord = "textord"; // Now comes the symbol table +// Relation Symbols + +defineSymbol(math, main, rel, "\u2261", "\\equiv", true); +defineSymbol(math, main, rel, "\u227a", "\\prec", true); +defineSymbol(math, main, rel, "\u227b", "\\succ", true); +defineSymbol(math, main, rel, "\u223c", "\\sim", true); +defineSymbol(math, main, rel, "\u22a5", "\\perp"); +defineSymbol(math, main, rel, "\u2aaf", "\\preceq", true); +defineSymbol(math, main, rel, "\u2ab0", "\\succeq", true); +defineSymbol(math, main, rel, "\u2243", "\\simeq", true); +defineSymbol(math, main, rel, "\u2223", "\\mid", true); +defineSymbol(math, main, rel, "\u226a", "\\ll", true); +defineSymbol(math, main, rel, "\u226b", "\\gg", true); +defineSymbol(math, main, rel, "\u224d", "\\asymp", true); +defineSymbol(math, main, rel, "\u2225", "\\parallel"); +defineSymbol(math, main, rel, "\u22c8", "\\bowtie", true); +defineSymbol(math, main, rel, "\u2323", "\\smile", true); +defineSymbol(math, main, rel, "\u2291", "\\sqsubseteq", true); +defineSymbol(math, main, rel, "\u2292", "\\sqsupseteq", true); +defineSymbol(math, main, rel, "\u2250", "\\doteq", true); +defineSymbol(math, main, rel, "\u2322", "\\frown", true); +defineSymbol(math, main, rel, "\u220b", "\\ni", true); +defineSymbol(math, main, rel, "\u221d", "\\propto", true); +defineSymbol(math, main, rel, "\u22a2", "\\vdash", true); +defineSymbol(math, main, rel, "\u22a3", "\\dashv", true); +defineSymbol(math, main, rel, "\u220b", "\\owns"); // Punctuation + +defineSymbol(math, main, punct, "\u002e", "\\ldotp"); +defineSymbol(math, main, punct, "\u22c5", "\\cdotp"); // Misc Symbols + +defineSymbol(math, main, textord, "\u0023", "\\#"); +defineSymbol(text, main, textord, "\u0023", "\\#"); +defineSymbol(math, main, textord, "\u0026", "\\&"); +defineSymbol(text, main, textord, "\u0026", "\\&"); +defineSymbol(math, main, textord, "\u2135", "\\aleph", true); +defineSymbol(math, main, textord, "\u2200", "\\forall", true); +defineSymbol(math, main, textord, "\u210f", "\\hbar", true); +defineSymbol(math, main, textord, "\u2203", "\\exists", true); +defineSymbol(math, main, textord, "\u2207", "\\nabla", true); +defineSymbol(math, main, textord, "\u266d", "\\flat", true); +defineSymbol(math, main, textord, "\u2113", "\\ell", true); +defineSymbol(math, main, textord, "\u266e", "\\natural", true); +defineSymbol(math, main, textord, "\u2663", "\\clubsuit", true); +defineSymbol(math, main, textord, "\u2118", "\\wp", true); +defineSymbol(math, main, textord, "\u266f", "\\sharp", true); +defineSymbol(math, main, textord, "\u2662", "\\diamondsuit", true); +defineSymbol(math, main, textord, "\u211c", "\\Re", true); +defineSymbol(math, main, textord, "\u2661", "\\heartsuit", true); +defineSymbol(math, main, textord, "\u2111", "\\Im", true); +defineSymbol(math, main, textord, "\u2660", "\\spadesuit", true); +defineSymbol(math, main, textord, "\u00a7", "\\S", true); +defineSymbol(text, main, textord, "\u00a7", "\\S"); +defineSymbol(math, main, textord, "\u00b6", "\\P", true); +defineSymbol(text, main, textord, "\u00b6", "\\P"); // Math and Text + +defineSymbol(math, main, textord, "\u2020", "\\dag"); +defineSymbol(text, main, textord, "\u2020", "\\dag"); +defineSymbol(text, main, textord, "\u2020", "\\textdagger"); +defineSymbol(math, main, textord, "\u2021", "\\ddag"); +defineSymbol(text, main, textord, "\u2021", "\\ddag"); +defineSymbol(text, main, textord, "\u2021", "\\textdaggerdbl"); // Large Delimiters + +defineSymbol(math, main, close, "\u23b1", "\\rmoustache", true); +defineSymbol(math, main, open, "\u23b0", "\\lmoustache", true); +defineSymbol(math, main, close, "\u27ef", "\\rgroup", true); +defineSymbol(math, main, open, "\u27ee", "\\lgroup", true); // Binary Operators + +defineSymbol(math, main, bin, "\u2213", "\\mp", true); +defineSymbol(math, main, bin, "\u2296", "\\ominus", true); +defineSymbol(math, main, bin, "\u228e", "\\uplus", true); +defineSymbol(math, main, bin, "\u2293", "\\sqcap", true); +defineSymbol(math, main, bin, "\u2217", "\\ast"); +defineSymbol(math, main, bin, "\u2294", "\\sqcup", true); +defineSymbol(math, main, bin, "\u25ef", "\\bigcirc", true); +defineSymbol(math, main, bin, "\u2219", "\\bullet", true); +defineSymbol(math, main, bin, "\u2021", "\\ddagger"); +defineSymbol(math, main, bin, "\u2240", "\\wr", true); +defineSymbol(math, main, bin, "\u2a3f", "\\amalg"); +defineSymbol(math, main, bin, "\u0026", "\\And"); // from amsmath +// Arrow Symbols + +defineSymbol(math, main, rel, "\u27f5", "\\longleftarrow", true); +defineSymbol(math, main, rel, "\u21d0", "\\Leftarrow", true); +defineSymbol(math, main, rel, "\u27f8", "\\Longleftarrow", true); +defineSymbol(math, main, rel, "\u27f6", "\\longrightarrow", true); +defineSymbol(math, main, rel, "\u21d2", "\\Rightarrow", true); +defineSymbol(math, main, rel, "\u27f9", "\\Longrightarrow", true); +defineSymbol(math, main, rel, "\u2194", "\\leftrightarrow", true); +defineSymbol(math, main, rel, "\u27f7", "\\longleftrightarrow", true); +defineSymbol(math, main, rel, "\u21d4", "\\Leftrightarrow", true); +defineSymbol(math, main, rel, "\u27fa", "\\Longleftrightarrow", true); +defineSymbol(math, main, rel, "\u21a6", "\\mapsto", true); +defineSymbol(math, main, rel, "\u27fc", "\\longmapsto", true); +defineSymbol(math, main, rel, "\u2197", "\\nearrow", true); +defineSymbol(math, main, rel, "\u21a9", "\\hookleftarrow", true); +defineSymbol(math, main, rel, "\u21aa", "\\hookrightarrow", true); +defineSymbol(math, main, rel, "\u2198", "\\searrow", true); +defineSymbol(math, main, rel, "\u21bc", "\\leftharpoonup", true); +defineSymbol(math, main, rel, "\u21c0", "\\rightharpoonup", true); +defineSymbol(math, main, rel, "\u2199", "\\swarrow", true); +defineSymbol(math, main, rel, "\u21bd", "\\leftharpoondown", true); +defineSymbol(math, main, rel, "\u21c1", "\\rightharpoondown", true); +defineSymbol(math, main, rel, "\u2196", "\\nwarrow", true); +defineSymbol(math, main, rel, "\u21cc", "\\rightleftharpoons", true); // AMS Negated Binary Relations + +defineSymbol(math, ams, rel, "\u226e", "\\nless", true); // Symbol names preceded by "@" each have a corresponding macro. + +defineSymbol(math, ams, rel, "\ue010", "\\@nleqslant"); +defineSymbol(math, ams, rel, "\ue011", "\\@nleqq"); +defineSymbol(math, ams, rel, "\u2a87", "\\lneq", true); +defineSymbol(math, ams, rel, "\u2268", "\\lneqq", true); +defineSymbol(math, ams, rel, "\ue00c", "\\@lvertneqq"); +defineSymbol(math, ams, rel, "\u22e6", "\\lnsim", true); +defineSymbol(math, ams, rel, "\u2a89", "\\lnapprox", true); +defineSymbol(math, ams, rel, "\u2280", "\\nprec", true); // unicode-math maps \u22e0 to \npreccurlyeq. We'll use the AMS synonym. + +defineSymbol(math, ams, rel, "\u22e0", "\\npreceq", true); +defineSymbol(math, ams, rel, "\u22e8", "\\precnsim", true); +defineSymbol(math, ams, rel, "\u2ab9", "\\precnapprox", true); +defineSymbol(math, ams, rel, "\u2241", "\\nsim", true); +defineSymbol(math, ams, rel, "\ue006", "\\@nshortmid"); +defineSymbol(math, ams, rel, "\u2224", "\\nmid", true); +defineSymbol(math, ams, rel, "\u22ac", "\\nvdash", true); +defineSymbol(math, ams, rel, "\u22ad", "\\nvDash", true); +defineSymbol(math, ams, rel, "\u22ea", "\\ntriangleleft"); +defineSymbol(math, ams, rel, "\u22ec", "\\ntrianglelefteq", true); +defineSymbol(math, ams, rel, "\u228a", "\\subsetneq", true); +defineSymbol(math, ams, rel, "\ue01a", "\\@varsubsetneq"); +defineSymbol(math, ams, rel, "\u2acb", "\\subsetneqq", true); +defineSymbol(math, ams, rel, "\ue017", "\\@varsubsetneqq"); +defineSymbol(math, ams, rel, "\u226f", "\\ngtr", true); +defineSymbol(math, ams, rel, "\ue00f", "\\@ngeqslant"); +defineSymbol(math, ams, rel, "\ue00e", "\\@ngeqq"); +defineSymbol(math, ams, rel, "\u2a88", "\\gneq", true); +defineSymbol(math, ams, rel, "\u2269", "\\gneqq", true); +defineSymbol(math, ams, rel, "\ue00d", "\\@gvertneqq"); +defineSymbol(math, ams, rel, "\u22e7", "\\gnsim", true); +defineSymbol(math, ams, rel, "\u2a8a", "\\gnapprox", true); +defineSymbol(math, ams, rel, "\u2281", "\\nsucc", true); // unicode-math maps \u22e1 to \nsucccurlyeq. We'll use the AMS synonym. + +defineSymbol(math, ams, rel, "\u22e1", "\\nsucceq", true); +defineSymbol(math, ams, rel, "\u22e9", "\\succnsim", true); +defineSymbol(math, ams, rel, "\u2aba", "\\succnapprox", true); // unicode-math maps \u2246 to \simneqq. We'll use the AMS synonym. + +defineSymbol(math, ams, rel, "\u2246", "\\ncong", true); +defineSymbol(math, ams, rel, "\ue007", "\\@nshortparallel"); +defineSymbol(math, ams, rel, "\u2226", "\\nparallel", true); +defineSymbol(math, ams, rel, "\u22af", "\\nVDash", true); +defineSymbol(math, ams, rel, "\u22eb", "\\ntriangleright"); +defineSymbol(math, ams, rel, "\u22ed", "\\ntrianglerighteq", true); +defineSymbol(math, ams, rel, "\ue018", "\\@nsupseteqq"); +defineSymbol(math, ams, rel, "\u228b", "\\supsetneq", true); +defineSymbol(math, ams, rel, "\ue01b", "\\@varsupsetneq"); +defineSymbol(math, ams, rel, "\u2acc", "\\supsetneqq", true); +defineSymbol(math, ams, rel, "\ue019", "\\@varsupsetneqq"); +defineSymbol(math, ams, rel, "\u22ae", "\\nVdash", true); +defineSymbol(math, ams, rel, "\u2ab5", "\\precneqq", true); +defineSymbol(math, ams, rel, "\u2ab6", "\\succneqq", true); +defineSymbol(math, ams, rel, "\ue016", "\\@nsubseteqq"); +defineSymbol(math, ams, bin, "\u22b4", "\\unlhd"); +defineSymbol(math, ams, bin, "\u22b5", "\\unrhd"); // AMS Negated Arrows + +defineSymbol(math, ams, rel, "\u219a", "\\nleftarrow", true); +defineSymbol(math, ams, rel, "\u219b", "\\nrightarrow", true); +defineSymbol(math, ams, rel, "\u21cd", "\\nLeftarrow", true); +defineSymbol(math, ams, rel, "\u21cf", "\\nRightarrow", true); +defineSymbol(math, ams, rel, "\u21ae", "\\nleftrightarrow", true); +defineSymbol(math, ams, rel, "\u21ce", "\\nLeftrightarrow", true); // AMS Misc + +defineSymbol(math, ams, rel, "\u25b3", "\\vartriangle"); +defineSymbol(math, ams, textord, "\u210f", "\\hslash"); +defineSymbol(math, ams, textord, "\u25bd", "\\triangledown"); +defineSymbol(math, ams, textord, "\u25ca", "\\lozenge"); +defineSymbol(math, ams, textord, "\u24c8", "\\circledS"); +defineSymbol(math, ams, textord, "\u00ae", "\\circledR"); +defineSymbol(text, ams, textord, "\u00ae", "\\circledR"); +defineSymbol(math, ams, textord, "\u2221", "\\measuredangle", true); +defineSymbol(math, ams, textord, "\u2204", "\\nexists"); +defineSymbol(math, ams, textord, "\u2127", "\\mho"); +defineSymbol(math, ams, textord, "\u2132", "\\Finv", true); +defineSymbol(math, ams, textord, "\u2141", "\\Game", true); +defineSymbol(math, ams, textord, "\u2035", "\\backprime"); +defineSymbol(math, ams, textord, "\u25b2", "\\blacktriangle"); +defineSymbol(math, ams, textord, "\u25bc", "\\blacktriangledown"); +defineSymbol(math, ams, textord, "\u25a0", "\\blacksquare"); +defineSymbol(math, ams, textord, "\u29eb", "\\blacklozenge"); +defineSymbol(math, ams, textord, "\u2605", "\\bigstar"); +defineSymbol(math, ams, textord, "\u2222", "\\sphericalangle", true); +defineSymbol(math, ams, textord, "\u2201", "\\complement", true); // unicode-math maps U+F0 to \matheth. We map to AMS function \eth + +defineSymbol(math, ams, textord, "\u00f0", "\\eth", true); +defineSymbol(text, main, textord, "\u00f0", "\u00f0"); +defineSymbol(math, ams, textord, "\u2571", "\\diagup"); +defineSymbol(math, ams, textord, "\u2572", "\\diagdown"); +defineSymbol(math, ams, textord, "\u25a1", "\\square"); +defineSymbol(math, ams, textord, "\u25a1", "\\Box"); +defineSymbol(math, ams, textord, "\u25ca", "\\Diamond"); // unicode-math maps U+A5 to \mathyen. We map to AMS function \yen + +defineSymbol(math, ams, textord, "\u00a5", "\\yen", true); +defineSymbol(text, ams, textord, "\u00a5", "\\yen", true); +defineSymbol(math, ams, textord, "\u2713", "\\checkmark", true); +defineSymbol(text, ams, textord, "\u2713", "\\checkmark"); // AMS Hebrew + +defineSymbol(math, ams, textord, "\u2136", "\\beth", true); +defineSymbol(math, ams, textord, "\u2138", "\\daleth", true); +defineSymbol(math, ams, textord, "\u2137", "\\gimel", true); // AMS Greek + +defineSymbol(math, ams, textord, "\u03dd", "\\digamma", true); +defineSymbol(math, ams, textord, "\u03f0", "\\varkappa"); // AMS Delimiters + +defineSymbol(math, ams, open, "\u250c", "\\@ulcorner", true); +defineSymbol(math, ams, close, "\u2510", "\\@urcorner", true); +defineSymbol(math, ams, open, "\u2514", "\\@llcorner", true); +defineSymbol(math, ams, close, "\u2518", "\\@lrcorner", true); // AMS Binary Relations + +defineSymbol(math, ams, rel, "\u2266", "\\leqq", true); +defineSymbol(math, ams, rel, "\u2a7d", "\\leqslant", true); +defineSymbol(math, ams, rel, "\u2a95", "\\eqslantless", true); +defineSymbol(math, ams, rel, "\u2272", "\\lesssim", true); +defineSymbol(math, ams, rel, "\u2a85", "\\lessapprox", true); +defineSymbol(math, ams, rel, "\u224a", "\\approxeq", true); +defineSymbol(math, ams, bin, "\u22d6", "\\lessdot"); +defineSymbol(math, ams, rel, "\u22d8", "\\lll", true); +defineSymbol(math, ams, rel, "\u2276", "\\lessgtr", true); +defineSymbol(math, ams, rel, "\u22da", "\\lesseqgtr", true); +defineSymbol(math, ams, rel, "\u2a8b", "\\lesseqqgtr", true); +defineSymbol(math, ams, rel, "\u2251", "\\doteqdot"); +defineSymbol(math, ams, rel, "\u2253", "\\risingdotseq", true); +defineSymbol(math, ams, rel, "\u2252", "\\fallingdotseq", true); +defineSymbol(math, ams, rel, "\u223d", "\\backsim", true); +defineSymbol(math, ams, rel, "\u22cd", "\\backsimeq", true); +defineSymbol(math, ams, rel, "\u2ac5", "\\subseteqq", true); +defineSymbol(math, ams, rel, "\u22d0", "\\Subset", true); +defineSymbol(math, ams, rel, "\u228f", "\\sqsubset", true); +defineSymbol(math, ams, rel, "\u227c", "\\preccurlyeq", true); +defineSymbol(math, ams, rel, "\u22de", "\\curlyeqprec", true); +defineSymbol(math, ams, rel, "\u227e", "\\precsim", true); +defineSymbol(math, ams, rel, "\u2ab7", "\\precapprox", true); +defineSymbol(math, ams, rel, "\u22b2", "\\vartriangleleft"); +defineSymbol(math, ams, rel, "\u22b4", "\\trianglelefteq"); +defineSymbol(math, ams, rel, "\u22a8", "\\vDash", true); +defineSymbol(math, ams, rel, "\u22aa", "\\Vvdash", true); +defineSymbol(math, ams, rel, "\u2323", "\\smallsmile"); +defineSymbol(math, ams, rel, "\u2322", "\\smallfrown"); +defineSymbol(math, ams, rel, "\u224f", "\\bumpeq", true); +defineSymbol(math, ams, rel, "\u224e", "\\Bumpeq", true); +defineSymbol(math, ams, rel, "\u2267", "\\geqq", true); +defineSymbol(math, ams, rel, "\u2a7e", "\\geqslant", true); +defineSymbol(math, ams, rel, "\u2a96", "\\eqslantgtr", true); +defineSymbol(math, ams, rel, "\u2273", "\\gtrsim", true); +defineSymbol(math, ams, rel, "\u2a86", "\\gtrapprox", true); +defineSymbol(math, ams, bin, "\u22d7", "\\gtrdot"); +defineSymbol(math, ams, rel, "\u22d9", "\\ggg", true); +defineSymbol(math, ams, rel, "\u2277", "\\gtrless", true); +defineSymbol(math, ams, rel, "\u22db", "\\gtreqless", true); +defineSymbol(math, ams, rel, "\u2a8c", "\\gtreqqless", true); +defineSymbol(math, ams, rel, "\u2256", "\\eqcirc", true); +defineSymbol(math, ams, rel, "\u2257", "\\circeq", true); +defineSymbol(math, ams, rel, "\u225c", "\\triangleq", true); +defineSymbol(math, ams, rel, "\u223c", "\\thicksim"); +defineSymbol(math, ams, rel, "\u2248", "\\thickapprox"); +defineSymbol(math, ams, rel, "\u2ac6", "\\supseteqq", true); +defineSymbol(math, ams, rel, "\u22d1", "\\Supset", true); +defineSymbol(math, ams, rel, "\u2290", "\\sqsupset", true); +defineSymbol(math, ams, rel, "\u227d", "\\succcurlyeq", true); +defineSymbol(math, ams, rel, "\u22df", "\\curlyeqsucc", true); +defineSymbol(math, ams, rel, "\u227f", "\\succsim", true); +defineSymbol(math, ams, rel, "\u2ab8", "\\succapprox", true); +defineSymbol(math, ams, rel, "\u22b3", "\\vartriangleright"); +defineSymbol(math, ams, rel, "\u22b5", "\\trianglerighteq"); +defineSymbol(math, ams, rel, "\u22a9", "\\Vdash", true); +defineSymbol(math, ams, rel, "\u2223", "\\shortmid"); +defineSymbol(math, ams, rel, "\u2225", "\\shortparallel"); +defineSymbol(math, ams, rel, "\u226c", "\\between", true); +defineSymbol(math, ams, rel, "\u22d4", "\\pitchfork", true); +defineSymbol(math, ams, rel, "\u221d", "\\varpropto"); +defineSymbol(math, ams, rel, "\u25c0", "\\blacktriangleleft"); // unicode-math says that \therefore is a mathord atom. +// We kept the amssymb atom type, which is rel. + +defineSymbol(math, ams, rel, "\u2234", "\\therefore", true); +defineSymbol(math, ams, rel, "\u220d", "\\backepsilon"); +defineSymbol(math, ams, rel, "\u25b6", "\\blacktriangleright"); // unicode-math says that \because is a mathord atom. +// We kept the amssymb atom type, which is rel. + +defineSymbol(math, ams, rel, "\u2235", "\\because", true); +defineSymbol(math, ams, rel, "\u22d8", "\\llless"); +defineSymbol(math, ams, rel, "\u22d9", "\\gggtr"); +defineSymbol(math, ams, bin, "\u22b2", "\\lhd"); +defineSymbol(math, ams, bin, "\u22b3", "\\rhd"); +defineSymbol(math, ams, rel, "\u2242", "\\eqsim", true); +defineSymbol(math, main, rel, "\u22c8", "\\Join"); +defineSymbol(math, ams, rel, "\u2251", "\\Doteq", true); // AMS Binary Operators + +defineSymbol(math, ams, bin, "\u2214", "\\dotplus", true); +defineSymbol(math, ams, bin, "\u2216", "\\smallsetminus"); +defineSymbol(math, ams, bin, "\u22d2", "\\Cap", true); +defineSymbol(math, ams, bin, "\u22d3", "\\Cup", true); +defineSymbol(math, ams, bin, "\u2a5e", "\\doublebarwedge", true); +defineSymbol(math, ams, bin, "\u229f", "\\boxminus", true); +defineSymbol(math, ams, bin, "\u229e", "\\boxplus", true); +defineSymbol(math, ams, bin, "\u22c7", "\\divideontimes", true); +defineSymbol(math, ams, bin, "\u22c9", "\\ltimes", true); +defineSymbol(math, ams, bin, "\u22ca", "\\rtimes", true); +defineSymbol(math, ams, bin, "\u22cb", "\\leftthreetimes", true); +defineSymbol(math, ams, bin, "\u22cc", "\\rightthreetimes", true); +defineSymbol(math, ams, bin, "\u22cf", "\\curlywedge", true); +defineSymbol(math, ams, bin, "\u22ce", "\\curlyvee", true); +defineSymbol(math, ams, bin, "\u229d", "\\circleddash", true); +defineSymbol(math, ams, bin, "\u229b", "\\circledast", true); +defineSymbol(math, ams, bin, "\u22c5", "\\centerdot"); +defineSymbol(math, ams, bin, "\u22ba", "\\intercal", true); +defineSymbol(math, ams, bin, "\u22d2", "\\doublecap"); +defineSymbol(math, ams, bin, "\u22d3", "\\doublecup"); +defineSymbol(math, ams, bin, "\u22a0", "\\boxtimes", true); // AMS Arrows +// Note: unicode-math maps \u21e2 to their own function \rightdasharrow. +// We'll map it to AMS function \dashrightarrow. It produces the same atom. + +defineSymbol(math, ams, rel, "\u21e2", "\\dashrightarrow", true); // unicode-math maps \u21e0 to \leftdasharrow. We'll use the AMS synonym. + +defineSymbol(math, ams, rel, "\u21e0", "\\dashleftarrow", true); +defineSymbol(math, ams, rel, "\u21c7", "\\leftleftarrows", true); +defineSymbol(math, ams, rel, "\u21c6", "\\leftrightarrows", true); +defineSymbol(math, ams, rel, "\u21da", "\\Lleftarrow", true); +defineSymbol(math, ams, rel, "\u219e", "\\twoheadleftarrow", true); +defineSymbol(math, ams, rel, "\u21a2", "\\leftarrowtail", true); +defineSymbol(math, ams, rel, "\u21ab", "\\looparrowleft", true); +defineSymbol(math, ams, rel, "\u21cb", "\\leftrightharpoons", true); +defineSymbol(math, ams, rel, "\u21b6", "\\curvearrowleft", true); // unicode-math maps \u21ba to \acwopencirclearrow. We'll use the AMS synonym. + +defineSymbol(math, ams, rel, "\u21ba", "\\circlearrowleft", true); +defineSymbol(math, ams, rel, "\u21b0", "\\Lsh", true); +defineSymbol(math, ams, rel, "\u21c8", "\\upuparrows", true); +defineSymbol(math, ams, rel, "\u21bf", "\\upharpoonleft", true); +defineSymbol(math, ams, rel, "\u21c3", "\\downharpoonleft", true); +defineSymbol(math, main, rel, "\u22b6", "\\origof", true); // not in font + +defineSymbol(math, main, rel, "\u22b7", "\\imageof", true); // not in font + +defineSymbol(math, ams, rel, "\u22b8", "\\multimap", true); +defineSymbol(math, ams, rel, "\u21ad", "\\leftrightsquigarrow", true); +defineSymbol(math, ams, rel, "\u21c9", "\\rightrightarrows", true); +defineSymbol(math, ams, rel, "\u21c4", "\\rightleftarrows", true); +defineSymbol(math, ams, rel, "\u21a0", "\\twoheadrightarrow", true); +defineSymbol(math, ams, rel, "\u21a3", "\\rightarrowtail", true); +defineSymbol(math, ams, rel, "\u21ac", "\\looparrowright", true); +defineSymbol(math, ams, rel, "\u21b7", "\\curvearrowright", true); // unicode-math maps \u21bb to \cwopencirclearrow. We'll use the AMS synonym. + +defineSymbol(math, ams, rel, "\u21bb", "\\circlearrowright", true); +defineSymbol(math, ams, rel, "\u21b1", "\\Rsh", true); +defineSymbol(math, ams, rel, "\u21ca", "\\downdownarrows", true); +defineSymbol(math, ams, rel, "\u21be", "\\upharpoonright", true); +defineSymbol(math, ams, rel, "\u21c2", "\\downharpoonright", true); +defineSymbol(math, ams, rel, "\u21dd", "\\rightsquigarrow", true); +defineSymbol(math, ams, rel, "\u21dd", "\\leadsto"); +defineSymbol(math, ams, rel, "\u21db", "\\Rrightarrow", true); +defineSymbol(math, ams, rel, "\u21be", "\\restriction"); +defineSymbol(math, main, textord, "\u2018", "`"); +defineSymbol(math, main, textord, "$", "\\$"); +defineSymbol(text, main, textord, "$", "\\$"); +defineSymbol(text, main, textord, "$", "\\textdollar"); +defineSymbol(math, main, textord, "%", "\\%"); +defineSymbol(text, main, textord, "%", "\\%"); +defineSymbol(math, main, textord, "_", "\\_"); +defineSymbol(text, main, textord, "_", "\\_"); +defineSymbol(text, main, textord, "_", "\\textunderscore"); +defineSymbol(math, main, textord, "\u2220", "\\angle", true); +defineSymbol(math, main, textord, "\u221e", "\\infty", true); +defineSymbol(math, main, textord, "\u2032", "\\prime"); +defineSymbol(math, main, textord, "\u25b3", "\\triangle"); +defineSymbol(math, main, textord, "\u0393", "\\Gamma", true); +defineSymbol(math, main, textord, "\u0394", "\\Delta", true); +defineSymbol(math, main, textord, "\u0398", "\\Theta", true); +defineSymbol(math, main, textord, "\u039b", "\\Lambda", true); +defineSymbol(math, main, textord, "\u039e", "\\Xi", true); +defineSymbol(math, main, textord, "\u03a0", "\\Pi", true); +defineSymbol(math, main, textord, "\u03a3", "\\Sigma", true); +defineSymbol(math, main, textord, "\u03a5", "\\Upsilon", true); +defineSymbol(math, main, textord, "\u03a6", "\\Phi", true); +defineSymbol(math, main, textord, "\u03a8", "\\Psi", true); +defineSymbol(math, main, textord, "\u03a9", "\\Omega", true); +defineSymbol(math, main, textord, "A", "\u0391"); +defineSymbol(math, main, textord, "B", "\u0392"); +defineSymbol(math, main, textord, "E", "\u0395"); +defineSymbol(math, main, textord, "Z", "\u0396"); +defineSymbol(math, main, textord, "H", "\u0397"); +defineSymbol(math, main, textord, "I", "\u0399"); +defineSymbol(math, main, textord, "K", "\u039A"); +defineSymbol(math, main, textord, "M", "\u039C"); +defineSymbol(math, main, textord, "N", "\u039D"); +defineSymbol(math, main, textord, "O", "\u039F"); +defineSymbol(math, main, textord, "P", "\u03A1"); +defineSymbol(math, main, textord, "T", "\u03A4"); +defineSymbol(math, main, textord, "X", "\u03A7"); +defineSymbol(math, main, textord, "\u00ac", "\\neg", true); +defineSymbol(math, main, textord, "\u00ac", "\\lnot"); +defineSymbol(math, main, textord, "\u22a4", "\\top"); +defineSymbol(math, main, textord, "\u22a5", "\\bot"); +defineSymbol(math, main, textord, "\u2205", "\\emptyset"); +defineSymbol(math, ams, textord, "\u2205", "\\varnothing"); +defineSymbol(math, main, mathord, "\u03b1", "\\alpha", true); +defineSymbol(math, main, mathord, "\u03b2", "\\beta", true); +defineSymbol(math, main, mathord, "\u03b3", "\\gamma", true); +defineSymbol(math, main, mathord, "\u03b4", "\\delta", true); +defineSymbol(math, main, mathord, "\u03f5", "\\epsilon", true); +defineSymbol(math, main, mathord, "\u03b6", "\\zeta", true); +defineSymbol(math, main, mathord, "\u03b7", "\\eta", true); +defineSymbol(math, main, mathord, "\u03b8", "\\theta", true); +defineSymbol(math, main, mathord, "\u03b9", "\\iota", true); +defineSymbol(math, main, mathord, "\u03ba", "\\kappa", true); +defineSymbol(math, main, mathord, "\u03bb", "\\lambda", true); +defineSymbol(math, main, mathord, "\u03bc", "\\mu", true); +defineSymbol(math, main, mathord, "\u03bd", "\\nu", true); +defineSymbol(math, main, mathord, "\u03be", "\\xi", true); +defineSymbol(math, main, mathord, "\u03bf", "\\omicron", true); +defineSymbol(math, main, mathord, "\u03c0", "\\pi", true); +defineSymbol(math, main, mathord, "\u03c1", "\\rho", true); +defineSymbol(math, main, mathord, "\u03c3", "\\sigma", true); +defineSymbol(math, main, mathord, "\u03c4", "\\tau", true); +defineSymbol(math, main, mathord, "\u03c5", "\\upsilon", true); +defineSymbol(math, main, mathord, "\u03d5", "\\phi", true); +defineSymbol(math, main, mathord, "\u03c7", "\\chi", true); +defineSymbol(math, main, mathord, "\u03c8", "\\psi", true); +defineSymbol(math, main, mathord, "\u03c9", "\\omega", true); +defineSymbol(math, main, mathord, "\u03b5", "\\varepsilon", true); +defineSymbol(math, main, mathord, "\u03d1", "\\vartheta", true); +defineSymbol(math, main, mathord, "\u03d6", "\\varpi", true); +defineSymbol(math, main, mathord, "\u03f1", "\\varrho", true); +defineSymbol(math, main, mathord, "\u03c2", "\\varsigma", true); +defineSymbol(math, main, mathord, "\u03c6", "\\varphi", true); +defineSymbol(math, main, bin, "\u2217", "*", true); +defineSymbol(math, main, bin, "+", "+"); +defineSymbol(math, main, bin, "\u2212", "-", true); +defineSymbol(math, main, bin, "\u22c5", "\\cdot", true); +defineSymbol(math, main, bin, "\u2218", "\\circ", true); +defineSymbol(math, main, bin, "\u00f7", "\\div", true); +defineSymbol(math, main, bin, "\u00b1", "\\pm", true); +defineSymbol(math, main, bin, "\u00d7", "\\times", true); +defineSymbol(math, main, bin, "\u2229", "\\cap", true); +defineSymbol(math, main, bin, "\u222a", "\\cup", true); +defineSymbol(math, main, bin, "\u2216", "\\setminus", true); +defineSymbol(math, main, bin, "\u2227", "\\land"); +defineSymbol(math, main, bin, "\u2228", "\\lor"); +defineSymbol(math, main, bin, "\u2227", "\\wedge", true); +defineSymbol(math, main, bin, "\u2228", "\\vee", true); +defineSymbol(math, main, textord, "\u221a", "\\surd"); +defineSymbol(math, main, open, "\u27e8", "\\langle", true); +defineSymbol(math, main, open, "\u2223", "\\lvert"); +defineSymbol(math, main, open, "\u2225", "\\lVert"); +defineSymbol(math, main, close, "?", "?"); +defineSymbol(math, main, close, "!", "!"); +defineSymbol(math, main, close, "\u27e9", "\\rangle", true); +defineSymbol(math, main, close, "\u2223", "\\rvert"); +defineSymbol(math, main, close, "\u2225", "\\rVert"); +defineSymbol(math, main, rel, "=", "="); +defineSymbol(math, main, rel, ":", ":"); +defineSymbol(math, main, rel, "\u2248", "\\approx", true); +defineSymbol(math, main, rel, "\u2245", "\\cong", true); +defineSymbol(math, main, rel, "\u2265", "\\ge"); +defineSymbol(math, main, rel, "\u2265", "\\geq", true); +defineSymbol(math, main, rel, "\u2190", "\\gets"); +defineSymbol(math, main, rel, ">", "\\gt", true); +defineSymbol(math, main, rel, "\u2208", "\\in", true); +defineSymbol(math, main, rel, "\ue020", "\\@not"); +defineSymbol(math, main, rel, "\u2282", "\\subset", true); +defineSymbol(math, main, rel, "\u2283", "\\supset", true); +defineSymbol(math, main, rel, "\u2286", "\\subseteq", true); +defineSymbol(math, main, rel, "\u2287", "\\supseteq", true); +defineSymbol(math, ams, rel, "\u2288", "\\nsubseteq", true); +defineSymbol(math, ams, rel, "\u2289", "\\nsupseteq", true); +defineSymbol(math, main, rel, "\u22a8", "\\models"); +defineSymbol(math, main, rel, "\u2190", "\\leftarrow", true); +defineSymbol(math, main, rel, "\u2264", "\\le"); +defineSymbol(math, main, rel, "\u2264", "\\leq", true); +defineSymbol(math, main, rel, "<", "\\lt", true); +defineSymbol(math, main, rel, "\u2192", "\\rightarrow", true); +defineSymbol(math, main, rel, "\u2192", "\\to"); +defineSymbol(math, ams, rel, "\u2271", "\\ngeq", true); +defineSymbol(math, ams, rel, "\u2270", "\\nleq", true); +defineSymbol(math, main, spacing, "\u00a0", "\\ "); +defineSymbol(math, main, spacing, "\u00a0", "\\space"); // Ref: LaTeX Source 2e: \DeclareRobustCommand{\nobreakspace}{% + +defineSymbol(math, main, spacing, "\u00a0", "\\nobreakspace"); +defineSymbol(text, main, spacing, "\u00a0", "\\ "); +defineSymbol(text, main, spacing, "\u00a0", " "); +defineSymbol(text, main, spacing, "\u00a0", "\\space"); +defineSymbol(text, main, spacing, "\u00a0", "\\nobreakspace"); +defineSymbol(math, main, spacing, null, "\\nobreak"); +defineSymbol(math, main, spacing, null, "\\allowbreak"); +defineSymbol(math, main, punct, ",", ","); +defineSymbol(math, main, punct, ";", ";"); +defineSymbol(math, ams, bin, "\u22bc", "\\barwedge", true); +defineSymbol(math, ams, bin, "\u22bb", "\\veebar", true); +defineSymbol(math, main, bin, "\u2299", "\\odot", true); +defineSymbol(math, main, bin, "\u2295", "\\oplus", true); +defineSymbol(math, main, bin, "\u2297", "\\otimes", true); +defineSymbol(math, main, textord, "\u2202", "\\partial", true); +defineSymbol(math, main, bin, "\u2298", "\\oslash", true); +defineSymbol(math, ams, bin, "\u229a", "\\circledcirc", true); +defineSymbol(math, ams, bin, "\u22a1", "\\boxdot", true); +defineSymbol(math, main, bin, "\u25b3", "\\bigtriangleup"); +defineSymbol(math, main, bin, "\u25bd", "\\bigtriangledown"); +defineSymbol(math, main, bin, "\u2020", "\\dagger"); +defineSymbol(math, main, bin, "\u22c4", "\\diamond"); +defineSymbol(math, main, bin, "\u22c6", "\\star"); +defineSymbol(math, main, bin, "\u25c3", "\\triangleleft"); +defineSymbol(math, main, bin, "\u25b9", "\\triangleright"); +defineSymbol(math, main, open, "{", "\\{"); +defineSymbol(text, main, textord, "{", "\\{"); +defineSymbol(text, main, textord, "{", "\\textbraceleft"); +defineSymbol(math, main, close, "}", "\\}"); +defineSymbol(text, main, textord, "}", "\\}"); +defineSymbol(text, main, textord, "}", "\\textbraceright"); +defineSymbol(math, main, open, "{", "\\lbrace"); +defineSymbol(math, main, close, "}", "\\rbrace"); +defineSymbol(math, main, open, "[", "\\lbrack", true); +defineSymbol(text, main, textord, "[", "\\lbrack", true); +defineSymbol(math, main, close, "]", "\\rbrack", true); +defineSymbol(text, main, textord, "]", "\\rbrack", true); +defineSymbol(math, main, open, "(", "\\lparen", true); +defineSymbol(math, main, close, ")", "\\rparen", true); +defineSymbol(text, main, textord, "<", "\\textless", true); // in T1 fontenc + +defineSymbol(text, main, textord, ">", "\\textgreater", true); // in T1 fontenc + +defineSymbol(math, main, open, "\u230a", "\\lfloor", true); +defineSymbol(math, main, close, "\u230b", "\\rfloor", true); +defineSymbol(math, main, open, "\u2308", "\\lceil", true); +defineSymbol(math, main, close, "\u2309", "\\rceil", true); +defineSymbol(math, main, textord, "\\", "\\backslash"); +defineSymbol(math, main, textord, "\u2223", "|"); +defineSymbol(math, main, textord, "\u2223", "\\vert"); +defineSymbol(text, main, textord, "|", "\\textbar", true); // in T1 fontenc + +defineSymbol(math, main, textord, "\u2225", "\\|"); +defineSymbol(math, main, textord, "\u2225", "\\Vert"); +defineSymbol(text, main, textord, "\u2225", "\\textbardbl"); +defineSymbol(text, main, textord, "~", "\\textasciitilde"); +defineSymbol(text, main, textord, "\\", "\\textbackslash"); +defineSymbol(text, main, textord, "^", "\\textasciicircum"); +defineSymbol(math, main, rel, "\u2191", "\\uparrow", true); +defineSymbol(math, main, rel, "\u21d1", "\\Uparrow", true); +defineSymbol(math, main, rel, "\u2193", "\\downarrow", true); +defineSymbol(math, main, rel, "\u21d3", "\\Downarrow", true); +defineSymbol(math, main, rel, "\u2195", "\\updownarrow", true); +defineSymbol(math, main, rel, "\u21d5", "\\Updownarrow", true); +defineSymbol(math, main, op, "\u2210", "\\coprod"); +defineSymbol(math, main, op, "\u22c1", "\\bigvee"); +defineSymbol(math, main, op, "\u22c0", "\\bigwedge"); +defineSymbol(math, main, op, "\u2a04", "\\biguplus"); +defineSymbol(math, main, op, "\u22c2", "\\bigcap"); +defineSymbol(math, main, op, "\u22c3", "\\bigcup"); +defineSymbol(math, main, op, "\u222b", "\\int"); +defineSymbol(math, main, op, "\u222b", "\\intop"); +defineSymbol(math, main, op, "\u222c", "\\iint"); +defineSymbol(math, main, op, "\u222d", "\\iiint"); +defineSymbol(math, main, op, "\u220f", "\\prod"); +defineSymbol(math, main, op, "\u2211", "\\sum"); +defineSymbol(math, main, op, "\u2a02", "\\bigotimes"); +defineSymbol(math, main, op, "\u2a01", "\\bigoplus"); +defineSymbol(math, main, op, "\u2a00", "\\bigodot"); +defineSymbol(math, main, op, "\u222e", "\\oint"); +defineSymbol(math, main, op, "\u222f", "\\oiint"); +defineSymbol(math, main, op, "\u2230", "\\oiiint"); +defineSymbol(math, main, op, "\u2a06", "\\bigsqcup"); +defineSymbol(math, main, op, "\u222b", "\\smallint"); +defineSymbol(text, main, inner, "\u2026", "\\textellipsis"); +defineSymbol(math, main, inner, "\u2026", "\\mathellipsis"); +defineSymbol(text, main, inner, "\u2026", "\\ldots", true); +defineSymbol(math, main, inner, "\u2026", "\\ldots", true); +defineSymbol(math, main, inner, "\u22ef", "\\@cdots", true); +defineSymbol(math, main, inner, "\u22f1", "\\ddots", true); // \vdots is a macro that uses one of these two symbols (with made-up names): + +defineSymbol(math, main, textord, "\u22ee", "\\varvdots"); +defineSymbol(text, main, textord, "\u22ee", "\\varvdots"); +defineSymbol(math, main, accent, "\u02ca", "\\acute"); +defineSymbol(math, main, accent, "\u02cb", "\\grave"); +defineSymbol(math, main, accent, "\u00a8", "\\ddot"); +defineSymbol(math, main, accent, "\u007e", "\\tilde"); +defineSymbol(math, main, accent, "\u02c9", "\\bar"); +defineSymbol(math, main, accent, "\u02d8", "\\breve"); +defineSymbol(math, main, accent, "\u02c7", "\\check"); +defineSymbol(math, main, accent, "\u005e", "\\hat"); +defineSymbol(math, main, accent, "\u20d7", "\\vec"); +defineSymbol(math, main, accent, "\u02d9", "\\dot"); +defineSymbol(math, main, accent, "\u02da", "\\mathring"); // \imath and \jmath should be invariant to \mathrm, \mathbf, etc., so use PUA + +defineSymbol(math, main, mathord, "\ue131", "\\@imath"); +defineSymbol(math, main, mathord, "\ue237", "\\@jmath"); +defineSymbol(math, main, textord, "\u0131", "\u0131"); +defineSymbol(math, main, textord, "\u0237", "\u0237"); +defineSymbol(text, main, textord, "\u0131", "\\i", true); +defineSymbol(text, main, textord, "\u0237", "\\j", true); +defineSymbol(text, main, textord, "\u00df", "\\ss", true); +defineSymbol(text, main, textord, "\u00e6", "\\ae", true); +defineSymbol(text, main, textord, "\u0153", "\\oe", true); +defineSymbol(text, main, textord, "\u00f8", "\\o", true); +defineSymbol(text, main, textord, "\u00c6", "\\AE", true); +defineSymbol(text, main, textord, "\u0152", "\\OE", true); +defineSymbol(text, main, textord, "\u00d8", "\\O", true); +defineSymbol(text, main, accent, "\u02ca", "\\'"); // acute + +defineSymbol(text, main, accent, "\u02cb", "\\`"); // grave + +defineSymbol(text, main, accent, "\u02c6", "\\^"); // circumflex + +defineSymbol(text, main, accent, "\u02dc", "\\~"); // tilde + +defineSymbol(text, main, accent, "\u02c9", "\\="); // macron + +defineSymbol(text, main, accent, "\u02d8", "\\u"); // breve + +defineSymbol(text, main, accent, "\u02d9", "\\."); // dot above + +defineSymbol(text, main, accent, "\u00b8", "\\c"); // cedilla + +defineSymbol(text, main, accent, "\u02da", "\\r"); // ring above + +defineSymbol(text, main, accent, "\u02c7", "\\v"); // caron + +defineSymbol(text, main, accent, "\u00a8", '\\"'); // diaeresis + +defineSymbol(text, main, accent, "\u02dd", "\\H"); // double acute + +defineSymbol(text, main, accent, "\u25ef", "\\textcircled"); // \bigcirc glyph +// These ligatures are detected and created in Parser.js's `formLigatures`. + +var ligatures = { + "--": true, + "---": true, + "``": true, + "''": true +}; +defineSymbol(text, main, textord, "\u2013", "--", true); +defineSymbol(text, main, textord, "\u2013", "\\textendash"); +defineSymbol(text, main, textord, "\u2014", "---", true); +defineSymbol(text, main, textord, "\u2014", "\\textemdash"); +defineSymbol(text, main, textord, "\u2018", "`", true); +defineSymbol(text, main, textord, "\u2018", "\\textquoteleft"); +defineSymbol(text, main, textord, "\u2019", "'", true); +defineSymbol(text, main, textord, "\u2019", "\\textquoteright"); +defineSymbol(text, main, textord, "\u201c", "``", true); +defineSymbol(text, main, textord, "\u201c", "\\textquotedblleft"); +defineSymbol(text, main, textord, "\u201d", "''", true); +defineSymbol(text, main, textord, "\u201d", "\\textquotedblright"); // \degree from gensymb package + +defineSymbol(math, main, textord, "\u00b0", "\\degree", true); +defineSymbol(text, main, textord, "\u00b0", "\\degree"); // \textdegree from inputenc package + +defineSymbol(text, main, textord, "\u00b0", "\\textdegree", true); // TODO: In LaTeX, \pounds can generate a different character in text and math +// mode, but among our fonts, only Main-Regular defines this character "163". + +defineSymbol(math, main, textord, "\u00a3", "\\pounds"); +defineSymbol(math, main, textord, "\u00a3", "\\mathsterling", true); +defineSymbol(text, main, textord, "\u00a3", "\\pounds"); +defineSymbol(text, main, textord, "\u00a3", "\\textsterling", true); +defineSymbol(math, ams, textord, "\u2720", "\\maltese"); +defineSymbol(text, ams, textord, "\u2720", "\\maltese"); // There are lots of symbols which are the same, so we add them in afterwards. +// All of these are textords in math mode + +var mathTextSymbols = "0123456789/@.\""; + +for (var i = 0; i < mathTextSymbols.length; i++) { + var ch = mathTextSymbols.charAt(i); + defineSymbol(math, main, textord, ch, ch); +} // All of these are textords in text mode + + +var textSymbols = "0123456789!@*()-=+\";:?/.,"; + +for (var _i = 0; _i < textSymbols.length; _i++) { + var _ch = textSymbols.charAt(_i); + + defineSymbol(text, main, textord, _ch, _ch); +} // All of these are textords in text mode, and mathords in math mode + + +var letters = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; + +for (var _i2 = 0; _i2 < letters.length; _i2++) { + var _ch2 = letters.charAt(_i2); + + defineSymbol(math, main, mathord, _ch2, _ch2); + defineSymbol(text, main, textord, _ch2, _ch2); +} // Blackboard bold and script letters in Unicode range + + +defineSymbol(math, ams, textord, "C", "\u2102"); // blackboard bold + +defineSymbol(text, ams, textord, "C", "\u2102"); +defineSymbol(math, ams, textord, "H", "\u210D"); +defineSymbol(text, ams, textord, "H", "\u210D"); +defineSymbol(math, ams, textord, "N", "\u2115"); +defineSymbol(text, ams, textord, "N", "\u2115"); +defineSymbol(math, ams, textord, "P", "\u2119"); +defineSymbol(text, ams, textord, "P", "\u2119"); +defineSymbol(math, ams, textord, "Q", "\u211A"); +defineSymbol(text, ams, textord, "Q", "\u211A"); +defineSymbol(math, ams, textord, "R", "\u211D"); +defineSymbol(text, ams, textord, "R", "\u211D"); +defineSymbol(math, ams, textord, "Z", "\u2124"); +defineSymbol(text, ams, textord, "Z", "\u2124"); +defineSymbol(math, main, mathord, "h", "\u210E"); // italic h, Planck constant + +defineSymbol(text, main, mathord, "h", "\u210E"); // The next loop loads wide (surrogate pair) characters. +// We support some letters in the Unicode range U+1D400 to U+1D7FF, +// Mathematical Alphanumeric Symbols. +// Some editors do not deal well with wide characters. So don't write the +// string into this file. Instead, create the string from the surrogate pair. + +var wideChar = ""; + +for (var _i3 = 0; _i3 < letters.length; _i3++) { + var _ch3 = letters.charAt(_i3); // The hex numbers in the next line are a surrogate pair. + // 0xD835 is the high surrogate for all letters in the range we support. + // 0xDC00 is the low surrogate for bold A. + + + wideChar = String.fromCharCode(0xD835, 0xDC00 + _i3); // A-Z a-z bold + + defineSymbol(math, main, mathord, _ch3, wideChar); + defineSymbol(text, main, textord, _ch3, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDC34 + _i3); // A-Z a-z italic + + defineSymbol(math, main, mathord, _ch3, wideChar); + defineSymbol(text, main, textord, _ch3, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDC68 + _i3); // A-Z a-z bold italic + + defineSymbol(math, main, mathord, _ch3, wideChar); + defineSymbol(text, main, textord, _ch3, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDD04 + _i3); // A-Z a-z Fraktur + + defineSymbol(math, main, mathord, _ch3, wideChar); + defineSymbol(text, main, textord, _ch3, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDD6C + _i3); // A-Z a-z bold Fraktur + + defineSymbol(math, main, mathord, _ch3, wideChar); + defineSymbol(text, main, textord, _ch3, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDDA0 + _i3); // A-Z a-z sans-serif + + defineSymbol(math, main, mathord, _ch3, wideChar); + defineSymbol(text, main, textord, _ch3, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDDD4 + _i3); // A-Z a-z sans bold + + defineSymbol(math, main, mathord, _ch3, wideChar); + defineSymbol(text, main, textord, _ch3, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDE08 + _i3); // A-Z a-z sans italic + + defineSymbol(math, main, mathord, _ch3, wideChar); + defineSymbol(text, main, textord, _ch3, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDE70 + _i3); // A-Z a-z monospace + + defineSymbol(math, main, mathord, _ch3, wideChar); + defineSymbol(text, main, textord, _ch3, wideChar); + + if (_i3 < 26) { + // KaTeX fonts have only capital letters for blackboard bold and script. + // See exception for k below. + wideChar = String.fromCharCode(0xD835, 0xDD38 + _i3); // A-Z double struck + + defineSymbol(math, main, mathord, _ch3, wideChar); + defineSymbol(text, main, textord, _ch3, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDC9C + _i3); // A-Z script + + defineSymbol(math, main, mathord, _ch3, wideChar); + defineSymbol(text, main, textord, _ch3, wideChar); + } // TODO: Add bold script when it is supported by a KaTeX font. + +} // "k" is the only double struck lower case letter in the KaTeX fonts. + + +wideChar = String.fromCharCode(0xD835, 0xDD5C); // k double struck + +defineSymbol(math, main, mathord, "k", wideChar); +defineSymbol(text, main, textord, "k", wideChar); // Next, some wide character numerals + +for (var _i4 = 0; _i4 < 10; _i4++) { + var _ch4 = _i4.toString(); + + wideChar = String.fromCharCode(0xD835, 0xDFCE + _i4); // 0-9 bold + + defineSymbol(math, main, mathord, _ch4, wideChar); + defineSymbol(text, main, textord, _ch4, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDFE2 + _i4); // 0-9 sans serif + + defineSymbol(math, main, mathord, _ch4, wideChar); + defineSymbol(text, main, textord, _ch4, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDFEC + _i4); // 0-9 bold sans + + defineSymbol(math, main, mathord, _ch4, wideChar); + defineSymbol(text, main, textord, _ch4, wideChar); + wideChar = String.fromCharCode(0xD835, 0xDFF6 + _i4); // 0-9 monospace + + defineSymbol(math, main, mathord, _ch4, wideChar); + defineSymbol(text, main, textord, _ch4, wideChar); +} // We add these Latin-1 letters as symbols for backwards-compatibility, +// but they are not actually in the font, nor are they supported by the +// Unicode accent mechanism, so they fall back to Times font and look ugly. +// TODO(edemaine): Fix this. + + +var extraLatin = "\u00d0\u00de\u00fe"; + +for (var _i5 = 0; _i5 < extraLatin.length; _i5++) { + var _ch5 = extraLatin.charAt(_i5); + + defineSymbol(math, main, mathord, _ch5, _ch5); + defineSymbol(text, main, textord, _ch5, _ch5); +} + +/** + * This file provides support for Unicode range U+1D400 to U+1D7FF, + * Mathematical Alphanumeric Symbols. + * + * Function wideCharacterFont takes a wide character as input and returns + * the font information necessary to render it properly. + */ +/** + * Data below is from https://www.unicode.org/charts/PDF/U1D400.pdf + * That document sorts characters into groups by font type, say bold or italic. + * + * In the arrays below, each subarray consists three elements: + * * The CSS class of that group when in math mode. + * * The CSS class of that group when in text mode. + * * The font name, so that KaTeX can get font metrics. + */ + +var wideLatinLetterData = [["mathbf", "textbf", "Main-Bold"], // A-Z bold upright +["mathbf", "textbf", "Main-Bold"], // a-z bold upright +["mathnormal", "textit", "Math-Italic"], // A-Z italic +["mathnormal", "textit", "Math-Italic"], // a-z italic +["boldsymbol", "boldsymbol", "Main-BoldItalic"], // A-Z bold italic +["boldsymbol", "boldsymbol", "Main-BoldItalic"], // a-z bold italic +// Map fancy A-Z letters to script, not calligraphic. +// This aligns with unicode-math and math fonts (except Cambria Math). +["mathscr", "textscr", "Script-Regular"], // A-Z script +["", "", ""], // a-z script. No font +["", "", ""], // A-Z bold script. No font +["", "", ""], // a-z bold script. No font +["mathfrak", "textfrak", "Fraktur-Regular"], // A-Z Fraktur +["mathfrak", "textfrak", "Fraktur-Regular"], // a-z Fraktur +["mathbb", "textbb", "AMS-Regular"], // A-Z double-struck +["mathbb", "textbb", "AMS-Regular"], // k double-struck +// Note that we are using a bold font, but font metrics for regular Fraktur. +["mathboldfrak", "textboldfrak", "Fraktur-Regular"], // A-Z bold Fraktur +["mathboldfrak", "textboldfrak", "Fraktur-Regular"], // a-z bold Fraktur +["mathsf", "textsf", "SansSerif-Regular"], // A-Z sans-serif +["mathsf", "textsf", "SansSerif-Regular"], // a-z sans-serif +["mathboldsf", "textboldsf", "SansSerif-Bold"], // A-Z bold sans-serif +["mathboldsf", "textboldsf", "SansSerif-Bold"], // a-z bold sans-serif +["mathitsf", "textitsf", "SansSerif-Italic"], // A-Z italic sans-serif +["mathitsf", "textitsf", "SansSerif-Italic"], // a-z italic sans-serif +["", "", ""], // A-Z bold italic sans. No font +["", "", ""], // a-z bold italic sans. No font +["mathtt", "texttt", "Typewriter-Regular"], // A-Z monospace +["mathtt", "texttt", "Typewriter-Regular"] // a-z monospace +]; +var wideNumeralData = [["mathbf", "textbf", "Main-Bold"], // 0-9 bold +["", "", ""], // 0-9 double-struck. No KaTeX font. +["mathsf", "textsf", "SansSerif-Regular"], // 0-9 sans-serif +["mathboldsf", "textboldsf", "SansSerif-Bold"], // 0-9 bold sans-serif +["mathtt", "texttt", "Typewriter-Regular"] // 0-9 monospace +]; +var wideCharacterFont = function wideCharacterFont(wideChar, mode) { + // IE doesn't support codePointAt(). So work with the surrogate pair. + var H = wideChar.charCodeAt(0); // high surrogate + + var L = wideChar.charCodeAt(1); // low surrogate + + var codePoint = (H - 0xD800) * 0x400 + (L - 0xDC00) + 0x10000; + var j = mode === "math" ? 0 : 1; // column index for CSS class. + + if (0x1D400 <= codePoint && codePoint < 0x1D6A4) { + // wideLatinLetterData contains exactly 26 chars on each row. + // So we can calculate the relevant row. No traverse necessary. + var i = Math.floor((codePoint - 0x1D400) / 26); + return [wideLatinLetterData[i][2], wideLatinLetterData[i][j]]; + } else if (0x1D7CE <= codePoint && codePoint <= 0x1D7FF) { + // Numerals, ten per row. + var _i = Math.floor((codePoint - 0x1D7CE) / 10); + + return [wideNumeralData[_i][2], wideNumeralData[_i][j]]; + } else if (codePoint === 0x1D6A5 || codePoint === 0x1D6A6) { + // dotless i or j + return [wideLatinLetterData[0][2], wideLatinLetterData[0][j]]; + } else if (0x1D6A6 < codePoint && codePoint < 0x1D7CE) { + // Greek letters. Not supported, yet. + return ["", ""]; + } else { + // We don't support any wide characters outside 1D400–1D7FF. + throw new ParseError("Unsupported character: " + wideChar); + } +}; + +/* eslint no-console:0 */ + +/** + * Looks up the given symbol in fontMetrics, after applying any symbol + * replacements defined in symbol.js + */ +var lookupSymbol = function lookupSymbol(value, // TODO(#963): Use a union type for this. +fontName, mode) { + // Replace the value with its replaced value from symbol.js + if (symbols[mode][value] && symbols[mode][value].replace) { + value = symbols[mode][value].replace; + } + + return { + value: value, + metrics: getCharacterMetrics(value, fontName, mode) + }; +}; +/** + * Makes a symbolNode after translation via the list of symbols in symbols.js. + * Correctly pulls out metrics for the character, and optionally takes a list of + * classes to be attached to the node. + * + * TODO: make argument order closer to makeSpan + * TODO: add a separate argument for math class (e.g. `mop`, `mbin`), which + * should if present come first in `classes`. + * TODO(#953): Make `options` mandatory and always pass it in. + */ + + +var makeSymbol = function makeSymbol(value, fontName, mode, options, classes) { + var lookup = lookupSymbol(value, fontName, mode); + var metrics = lookup.metrics; + value = lookup.value; + var symbolNode; + + if (metrics) { + var italic = metrics.italic; + + if (mode === "text" || options && options.font === "mathit") { + italic = 0; + } + + symbolNode = new SymbolNode(value, metrics.height, metrics.depth, italic, metrics.skew, metrics.width, classes); + } else { + // TODO(emily): Figure out a good way to only print this in development + typeof console !== "undefined" && console.warn("No character metrics " + ("for '" + value + "' in style '" + fontName + "' and mode '" + mode + "'")); + symbolNode = new SymbolNode(value, 0, 0, 0, 0, 0, classes); + } + + if (options) { + symbolNode.maxFontSize = options.sizeMultiplier; + + if (options.style.isTight()) { + symbolNode.classes.push("mtight"); + } + + var color = options.getColor(); + + if (color) { + symbolNode.style.color = color; + } + } + + return symbolNode; +}; +/** + * Makes a symbol in Main-Regular or AMS-Regular. + * Used for rel, bin, open, close, inner, and punct. + */ + + +var mathsym = function mathsym(value, mode, options, classes) { + if (classes === void 0) { + classes = []; + } + + // Decide what font to render the symbol in by its entry in the symbols + // table. + // Have a special case for when the value = \ because the \ is used as a + // textord in unsupported command errors but cannot be parsed as a regular + // text ordinal and is therefore not present as a symbol in the symbols + // table for text, as well as a special case for boldsymbol because it + // can be used for bold + and - + if (options.font === "boldsymbol" && lookupSymbol(value, "Main-Bold", mode).metrics) { + return makeSymbol(value, "Main-Bold", mode, options, classes.concat(["mathbf"])); + } else if (value === "\\" || symbols[mode][value].font === "main") { + return makeSymbol(value, "Main-Regular", mode, options, classes); + } else { + return makeSymbol(value, "AMS-Regular", mode, options, classes.concat(["amsrm"])); + } +}; +/** + * Determines which of the two font names (Main-Bold and Math-BoldItalic) and + * corresponding style tags (mathbf or boldsymbol) to use for font "boldsymbol", + * depending on the symbol. Use this function instead of fontMap for font + * "boldsymbol". + */ + + +var boldsymbol = function boldsymbol(value, mode, options, classes, type) { + if (type !== "textord" && lookupSymbol(value, "Math-BoldItalic", mode).metrics) { + return { + fontName: "Math-BoldItalic", + fontClass: "boldsymbol" + }; + } else { + // Some glyphs do not exist in Math-BoldItalic so we need to use + // Main-Bold instead. + return { + fontName: "Main-Bold", + fontClass: "mathbf" + }; + } +}; +/** + * Makes either a mathord or textord in the correct font and color. + */ + + +var makeOrd = function makeOrd(group, options, type) { + var mode = group.mode; + var text = group.text; + var classes = ["mord"]; // Math mode or Old font (i.e. \rm) + + var isFont = mode === "math" || mode === "text" && options.font; + var fontOrFamily = isFont ? options.font : options.fontFamily; + var wideFontName = ""; + var wideFontClass = ""; + + if (text.charCodeAt(0) === 0xD835) { + [wideFontName, wideFontClass] = wideCharacterFont(text, mode); + } + + if (wideFontName.length > 0) { + // surrogate pairs get special treatment + return makeSymbol(text, wideFontName, mode, options, classes.concat(wideFontClass)); + } else if (fontOrFamily) { + var fontName; + var fontClasses; + + if (fontOrFamily === "boldsymbol") { + var fontData = boldsymbol(text, mode, options, classes, type); + fontName = fontData.fontName; + fontClasses = [fontData.fontClass]; + } else if (isFont) { + fontName = fontMap[fontOrFamily].fontName; + fontClasses = [fontOrFamily]; + } else { + fontName = retrieveTextFontName(fontOrFamily, options.fontWeight, options.fontShape); + fontClasses = [fontOrFamily, options.fontWeight, options.fontShape]; + } + + if (lookupSymbol(text, fontName, mode).metrics) { + return makeSymbol(text, fontName, mode, options, classes.concat(fontClasses)); + } else if (ligatures.hasOwnProperty(text) && fontName.slice(0, 10) === "Typewriter") { + // Deconstruct ligatures in monospace fonts (\texttt, \tt). + var parts = []; + + for (var i = 0; i < text.length; i++) { + parts.push(makeSymbol(text[i], fontName, mode, options, classes.concat(fontClasses))); + } + + return makeFragment(parts); + } + } // Makes a symbol in the default font for mathords and textords. + + + if (type === "mathord") { + return makeSymbol(text, "Math-Italic", mode, options, classes.concat(["mathnormal"])); + } else if (type === "textord") { + var font = symbols[mode][text] && symbols[mode][text].font; + + if (font === "ams") { + var _fontName = retrieveTextFontName("amsrm", options.fontWeight, options.fontShape); + + return makeSymbol(text, _fontName, mode, options, classes.concat("amsrm", options.fontWeight, options.fontShape)); + } else if (font === "main" || !font) { + var _fontName2 = retrieveTextFontName("textrm", options.fontWeight, options.fontShape); + + return makeSymbol(text, _fontName2, mode, options, classes.concat(options.fontWeight, options.fontShape)); + } else { + // fonts added by plugins + var _fontName3 = retrieveTextFontName(font, options.fontWeight, options.fontShape); // We add font name as a css class + + + return makeSymbol(text, _fontName3, mode, options, classes.concat(_fontName3, options.fontWeight, options.fontShape)); + } + } else { + throw new Error("unexpected type: " + type + " in makeOrd"); + } +}; +/** + * Returns true if subsequent symbolNodes have the same classes, skew, maxFont, + * and styles. + */ + + +var canCombine = (prev, next) => { + if (createClass(prev.classes) !== createClass(next.classes) || prev.skew !== next.skew || prev.maxFontSize !== next.maxFontSize) { + return false; + } // If prev and next both are just "mbin"s or "mord"s we don't combine them + // so that the proper spacing can be preserved. + + + if (prev.classes.length === 1) { + var cls = prev.classes[0]; + + if (cls === "mbin" || cls === "mord") { + return false; + } + } + + for (var style in prev.style) { + if (prev.style.hasOwnProperty(style) && prev.style[style] !== next.style[style]) { + return false; + } + } + + for (var _style in next.style) { + if (next.style.hasOwnProperty(_style) && prev.style[_style] !== next.style[_style]) { + return false; + } + } + + return true; +}; +/** + * Combine consecutive domTree.symbolNodes into a single symbolNode. + * Note: this function mutates the argument. + */ + + +var tryCombineChars = chars => { + for (var i = 0; i < chars.length - 1; i++) { + var prev = chars[i]; + var next = chars[i + 1]; + + if (prev instanceof SymbolNode && next instanceof SymbolNode && canCombine(prev, next)) { + prev.text += next.text; + prev.height = Math.max(prev.height, next.height); + prev.depth = Math.max(prev.depth, next.depth); // Use the last character's italic correction since we use + // it to add padding to the right of the span created from + // the combined characters. + + prev.italic = next.italic; + chars.splice(i + 1, 1); + i--; + } + } + + return chars; +}; +/** + * Calculate the height, depth, and maxFontSize of an element based on its + * children. + */ + + +var sizeElementFromChildren = function sizeElementFromChildren(elem) { + var height = 0; + var depth = 0; + var maxFontSize = 0; + + for (var i = 0; i < elem.children.length; i++) { + var child = elem.children[i]; + + if (child.height > height) { + height = child.height; + } + + if (child.depth > depth) { + depth = child.depth; + } + + if (child.maxFontSize > maxFontSize) { + maxFontSize = child.maxFontSize; + } + } + + elem.height = height; + elem.depth = depth; + elem.maxFontSize = maxFontSize; +}; +/** + * Makes a span with the given list of classes, list of children, and options. + * + * TODO(#953): Ensure that `options` is always provided (currently some call + * sites don't pass it) and make the type below mandatory. + * TODO: add a separate argument for math class (e.g. `mop`, `mbin`), which + * should if present come first in `classes`. + */ + + +var makeSpan$2 = function makeSpan(classes, children, options, style) { + var span = new Span(classes, children, options, style); + sizeElementFromChildren(span); + return span; +}; // SVG one is simpler -- doesn't require height, depth, max-font setting. +// This is also a separate method for typesafety. + + +var makeSvgSpan = (classes, children, options, style) => new Span(classes, children, options, style); + +var makeLineSpan = function makeLineSpan(className, options, thickness) { + var line = makeSpan$2([className], [], options); + line.height = Math.max(thickness || options.fontMetrics().defaultRuleThickness, options.minRuleThickness); + line.style.borderBottomWidth = makeEm(line.height); + line.maxFontSize = 1.0; + return line; +}; +/** + * Makes an anchor with the given href, list of classes, list of children, + * and options. + */ + + +var makeAnchor = function makeAnchor(href, classes, children, options) { + var anchor = new Anchor(href, classes, children, options); + sizeElementFromChildren(anchor); + return anchor; +}; +/** + * Makes a document fragment with the given list of children. + */ + + +var makeFragment = function makeFragment(children) { + var fragment = new DocumentFragment(children); + sizeElementFromChildren(fragment); + return fragment; +}; +/** + * Wraps group in a span if it's a document fragment, allowing to apply classes + * and styles + */ + + +var wrapFragment = function wrapFragment(group, options) { + if (group instanceof DocumentFragment) { + return makeSpan$2([], [group], options); + } + + return group; +}; // These are exact object types to catch typos in the names of the optional fields. + + +// Computes the updated `children` list and the overall depth. +// +// This helper function for makeVList makes it easier to enforce type safety by +// allowing early exits (returns) in the logic. +var getVListChildrenAndDepth = function getVListChildrenAndDepth(params) { + if (params.positionType === "individualShift") { + var oldChildren = params.children; + var children = [oldChildren[0]]; // Add in kerns to the list of params.children to get each element to be + // shifted to the correct specified shift + + var _depth = -oldChildren[0].shift - oldChildren[0].elem.depth; + + var currPos = _depth; + + for (var i = 1; i < oldChildren.length; i++) { + var diff = -oldChildren[i].shift - currPos - oldChildren[i].elem.depth; + var size = diff - (oldChildren[i - 1].elem.height + oldChildren[i - 1].elem.depth); + currPos = currPos + diff; + children.push({ + type: "kern", + size + }); + children.push(oldChildren[i]); + } + + return { + children, + depth: _depth + }; + } + + var depth; + + if (params.positionType === "top") { + // We always start at the bottom, so calculate the bottom by adding up + // all the sizes + var bottom = params.positionData; + + for (var _i = 0; _i < params.children.length; _i++) { + var child = params.children[_i]; + bottom -= child.type === "kern" ? child.size : child.elem.height + child.elem.depth; + } + + depth = bottom; + } else if (params.positionType === "bottom") { + depth = -params.positionData; + } else { + var firstChild = params.children[0]; + + if (firstChild.type !== "elem") { + throw new Error('First child must have type "elem".'); + } + + if (params.positionType === "shift") { + depth = -firstChild.elem.depth - params.positionData; + } else if (params.positionType === "firstBaseline") { + depth = -firstChild.elem.depth; + } else { + throw new Error("Invalid positionType " + params.positionType + "."); + } + } + + return { + children: params.children, + depth + }; +}; +/** + * Makes a vertical list by stacking elements and kerns on top of each other. + * Allows for many different ways of specifying the positioning method. + * + * See VListParam documentation above. + */ + + +var makeVList = function makeVList(params, options) { + var { + children, + depth + } = getVListChildrenAndDepth(params); // Create a strut that is taller than any list item. The strut is added to + // each item, where it will determine the item's baseline. Since it has + // `overflow:hidden`, the strut's top edge will sit on the item's line box's + // top edge and the strut's bottom edge will sit on the item's baseline, + // with no additional line-height spacing. This allows the item baseline to + // be positioned precisely without worrying about font ascent and + // line-height. + + var pstrutSize = 0; + + for (var i = 0; i < children.length; i++) { + var child = children[i]; + + if (child.type === "elem") { + var elem = child.elem; + pstrutSize = Math.max(pstrutSize, elem.maxFontSize, elem.height); + } + } + + pstrutSize += 2; + var pstrut = makeSpan$2(["pstrut"], []); + pstrut.style.height = makeEm(pstrutSize); // Create a new list of actual children at the correct offsets + + var realChildren = []; + var minPos = depth; + var maxPos = depth; + var currPos = depth; + + for (var _i2 = 0; _i2 < children.length; _i2++) { + var _child = children[_i2]; + + if (_child.type === "kern") { + currPos += _child.size; + } else { + var _elem = _child.elem; + var classes = _child.wrapperClasses || []; + var style = _child.wrapperStyle || {}; + var childWrap = makeSpan$2(classes, [pstrut, _elem], undefined, style); + childWrap.style.top = makeEm(-pstrutSize - currPos - _elem.depth); + + if (_child.marginLeft) { + childWrap.style.marginLeft = _child.marginLeft; + } + + if (_child.marginRight) { + childWrap.style.marginRight = _child.marginRight; + } + + realChildren.push(childWrap); + currPos += _elem.height + _elem.depth; + } + + minPos = Math.min(minPos, currPos); + maxPos = Math.max(maxPos, currPos); + } // The vlist contents go in a table-cell with `vertical-align:bottom`. + // This cell's bottom edge will determine the containing table's baseline + // without overly expanding the containing line-box. + + + var vlist = makeSpan$2(["vlist"], realChildren); + vlist.style.height = makeEm(maxPos); // A second row is used if necessary to represent the vlist's depth. + + var rows; + + if (minPos < 0) { + // We will define depth in an empty span with display: table-cell. + // It should render with the height that we define. But Chrome, in + // contenteditable mode only, treats that span as if it contains some + // text content. And that min-height over-rides our desired height. + // So we put another empty span inside the depth strut span. + var emptySpan = makeSpan$2([], []); + var depthStrut = makeSpan$2(["vlist"], [emptySpan]); + depthStrut.style.height = makeEm(-minPos); // Safari wants the first row to have inline content; otherwise it + // puts the bottom of the *second* row on the baseline. + + var topStrut = makeSpan$2(["vlist-s"], [new SymbolNode("\u200b")]); + rows = [makeSpan$2(["vlist-r"], [vlist, topStrut]), makeSpan$2(["vlist-r"], [depthStrut])]; + } else { + rows = [makeSpan$2(["vlist-r"], [vlist])]; + } + + var vtable = makeSpan$2(["vlist-t"], rows); + + if (rows.length === 2) { + vtable.classes.push("vlist-t2"); + } + + vtable.height = maxPos; + vtable.depth = -minPos; + return vtable; +}; // Glue is a concept from TeX which is a flexible space between elements in +// either a vertical or horizontal list. In KaTeX, at least for now, it's +// static space between elements in a horizontal layout. + + +var makeGlue = (measurement, options) => { + // Make an empty span for the space + var rule = makeSpan$2(["mspace"], [], options); + var size = calculateSize(measurement, options); + rule.style.marginRight = makeEm(size); + return rule; +}; // Takes font options, and returns the appropriate fontLookup name + + +var retrieveTextFontName = function retrieveTextFontName(fontFamily, fontWeight, fontShape) { + var baseFontName = ""; + + switch (fontFamily) { + case "amsrm": + baseFontName = "AMS"; + break; + + case "textrm": + baseFontName = "Main"; + break; + + case "textsf": + baseFontName = "SansSerif"; + break; + + case "texttt": + baseFontName = "Typewriter"; + break; + + default: + baseFontName = fontFamily; + // use fonts added by a plugin + } + + var fontStylesName; + + if (fontWeight === "textbf" && fontShape === "textit") { + fontStylesName = "BoldItalic"; + } else if (fontWeight === "textbf") { + fontStylesName = "Bold"; + } else if (fontWeight === "textit") { + fontStylesName = "Italic"; + } else { + fontStylesName = "Regular"; + } + + return baseFontName + "-" + fontStylesName; +}; +/** + * Maps TeX font commands to objects containing: + * - variant: string used for "mathvariant" attribute in buildMathML.js + * - fontName: the "style" parameter to fontMetrics.getCharacterMetrics + */ +// A map between tex font commands an MathML mathvariant attribute values + + +var fontMap = { + // styles + "mathbf": { + variant: "bold", + fontName: "Main-Bold" + }, + "mathrm": { + variant: "normal", + fontName: "Main-Regular" + }, + "textit": { + variant: "italic", + fontName: "Main-Italic" + }, + "mathit": { + variant: "italic", + fontName: "Main-Italic" + }, + "mathnormal": { + variant: "italic", + fontName: "Math-Italic" + }, + "mathsfit": { + variant: "sans-serif-italic", + fontName: "SansSerif-Italic" + }, + // "boldsymbol" is missing because they require the use of multiple fonts: + // Math-BoldItalic and Main-Bold. This is handled by a special case in + // makeOrd which ends up calling boldsymbol. + // families + "mathbb": { + variant: "double-struck", + fontName: "AMS-Regular" + }, + "mathcal": { + variant: "script", + fontName: "Caligraphic-Regular" + }, + "mathfrak": { + variant: "fraktur", + fontName: "Fraktur-Regular" + }, + "mathscr": { + variant: "script", + fontName: "Script-Regular" + }, + "mathsf": { + variant: "sans-serif", + fontName: "SansSerif-Regular" + }, + "mathtt": { + variant: "monospace", + fontName: "Typewriter-Regular" + } +}; +var svgData = { + // path, width, height + vec: ["vec", 0.471, 0.714], + // values from the font glyph + oiintSize1: ["oiintSize1", 0.957, 0.499], + // oval to overlay the integrand + oiintSize2: ["oiintSize2", 1.472, 0.659], + oiiintSize1: ["oiiintSize1", 1.304, 0.499], + oiiintSize2: ["oiiintSize2", 1.98, 0.659] +}; + +var staticSvg = function staticSvg(value, options) { + // Create a span with inline SVG for the element. + var [pathName, width, height] = svgData[value]; + var path = new PathNode(pathName); + var svgNode = new SvgNode([path], { + "width": makeEm(width), + "height": makeEm(height), + // Override CSS rule `.katex svg { width: 100% }` + "style": "width:" + makeEm(width), + "viewBox": "0 0 " + 1000 * width + " " + 1000 * height, + "preserveAspectRatio": "xMinYMin" + }); + var span = makeSvgSpan(["overlay"], [svgNode], options); + span.height = height; + span.style.height = makeEm(height); + span.style.width = makeEm(width); + return span; +}; + +var buildCommon = { + fontMap, + makeSymbol, + mathsym, + makeSpan: makeSpan$2, + makeSvgSpan, + makeLineSpan, + makeAnchor, + makeFragment, + wrapFragment, + makeVList, + makeOrd, + makeGlue, + staticSvg, + svgData, + tryCombineChars +}; + +/** + * Describes spaces between different classes of atoms. + */ +var thinspace = { + number: 3, + unit: "mu" +}; +var mediumspace = { + number: 4, + unit: "mu" +}; +var thickspace = { + number: 5, + unit: "mu" +}; // Making the type below exact with all optional fields doesn't work due to +// - https://github.com/facebook/flow/issues/4582 +// - https://github.com/facebook/flow/issues/5688 +// However, since *all* fields are optional, $Shape<> works as suggested in 5688 +// above. + +// Spacing relationships for display and text styles +var spacings = { + mord: { + mop: thinspace, + mbin: mediumspace, + mrel: thickspace, + minner: thinspace + }, + mop: { + mord: thinspace, + mop: thinspace, + mrel: thickspace, + minner: thinspace + }, + mbin: { + mord: mediumspace, + mop: mediumspace, + mopen: mediumspace, + minner: mediumspace + }, + mrel: { + mord: thickspace, + mop: thickspace, + mopen: thickspace, + minner: thickspace + }, + mopen: {}, + mclose: { + mop: thinspace, + mbin: mediumspace, + mrel: thickspace, + minner: thinspace + }, + mpunct: { + mord: thinspace, + mop: thinspace, + mrel: thickspace, + mopen: thinspace, + mclose: thinspace, + mpunct: thinspace, + minner: thinspace + }, + minner: { + mord: thinspace, + mop: thinspace, + mbin: mediumspace, + mrel: thickspace, + mopen: thinspace, + mpunct: thinspace, + minner: thinspace + } +}; // Spacing relationships for script and scriptscript styles + +var tightSpacings = { + mord: { + mop: thinspace + }, + mop: { + mord: thinspace, + mop: thinspace + }, + mbin: {}, + mrel: {}, + mopen: {}, + mclose: { + mop: thinspace + }, + mpunct: {}, + minner: { + mop: thinspace + } +}; + +/** Context provided to function handlers for error messages. */ +// Note: reverse the order of the return type union will cause a flow error. +// See https://github.com/facebook/flow/issues/3663. +// More general version of `HtmlBuilder` for nodes (e.g. \sum, accent types) +// whose presence impacts super/subscripting. In this case, ParseNode<"supsub"> +// delegates its HTML building to the HtmlBuilder corresponding to these nodes. + +/** + * Final function spec for use at parse time. + * This is almost identical to `FunctionPropSpec`, except it + * 1. includes the function handler, and + * 2. requires all arguments except argTypes. + * It is generated by `defineFunction()` below. + */ + +/** + * All registered functions. + * `functions.js` just exports this same dictionary again and makes it public. + * `Parser.js` requires this dictionary. + */ +var _functions = {}; +/** + * All HTML builders. Should be only used in the `define*` and the `build*ML` + * functions. + */ + +var _htmlGroupBuilders = {}; +/** + * All MathML builders. Should be only used in the `define*` and the `build*ML` + * functions. + */ + +var _mathmlGroupBuilders = {}; +function defineFunction(_ref) { + var { + type, + names, + props, + handler, + htmlBuilder, + mathmlBuilder + } = _ref; + // Set default values of functions + var data = { + type, + numArgs: props.numArgs, + argTypes: props.argTypes, + allowedInArgument: !!props.allowedInArgument, + allowedInText: !!props.allowedInText, + allowedInMath: props.allowedInMath === undefined ? true : props.allowedInMath, + numOptionalArgs: props.numOptionalArgs || 0, + infix: !!props.infix, + primitive: !!props.primitive, + handler: handler + }; + + for (var i = 0; i < names.length; ++i) { + _functions[names[i]] = data; + } + + if (type) { + if (htmlBuilder) { + _htmlGroupBuilders[type] = htmlBuilder; + } + + if (mathmlBuilder) { + _mathmlGroupBuilders[type] = mathmlBuilder; + } + } +} +/** + * Use this to register only the HTML and MathML builders for a function (e.g. + * if the function's ParseNode is generated in Parser.js rather than via a + * stand-alone handler provided to `defineFunction`). + */ + +function defineFunctionBuilders(_ref2) { + var { + type, + htmlBuilder, + mathmlBuilder + } = _ref2; + defineFunction({ + type, + names: [], + props: { + numArgs: 0 + }, + + handler() { + throw new Error('Should never be called.'); + }, + + htmlBuilder, + mathmlBuilder + }); +} +var normalizeArgument = function normalizeArgument(arg) { + return arg.type === "ordgroup" && arg.body.length === 1 ? arg.body[0] : arg; +}; // Since the corresponding buildHTML/buildMathML function expects a +// list of elements, we normalize for different kinds of arguments + +var ordargument = function ordargument(arg) { + return arg.type === "ordgroup" ? arg.body : [arg]; +}; + +/** + * This file does the main work of building a domTree structure from a parse + * tree. The entry point is the `buildHTML` function, which takes a parse tree. + * Then, the buildExpression, buildGroup, and various groupBuilders functions + * are called, to produce a final HTML tree. + */ +var makeSpan$1 = buildCommon.makeSpan; // Binary atoms (first class `mbin`) change into ordinary atoms (`mord`) +// depending on their surroundings. See TeXbook pg. 442-446, Rules 5 and 6, +// and the text before Rule 19. + +var binLeftCanceller = ["leftmost", "mbin", "mopen", "mrel", "mop", "mpunct"]; +var binRightCanceller = ["rightmost", "mrel", "mclose", "mpunct"]; +var styleMap$1 = { + "display": Style$1.DISPLAY, + "text": Style$1.TEXT, + "script": Style$1.SCRIPT, + "scriptscript": Style$1.SCRIPTSCRIPT +}; +var DomEnum = { + mord: "mord", + mop: "mop", + mbin: "mbin", + mrel: "mrel", + mopen: "mopen", + mclose: "mclose", + mpunct: "mpunct", + minner: "minner" +}; + +/** + * Take a list of nodes, build them in order, and return a list of the built + * nodes. documentFragments are flattened into their contents, so the + * returned list contains no fragments. `isRealGroup` is true if `expression` + * is a real group (no atoms will be added on either side), as opposed to + * a partial group (e.g. one created by \color). `surrounding` is an array + * consisting type of nodes that will be added to the left and right. + */ +var buildExpression$1 = function buildExpression(expression, options, isRealGroup, surrounding) { + if (surrounding === void 0) { + surrounding = [null, null]; + } + + // Parse expressions into `groups`. + var groups = []; + + for (var i = 0; i < expression.length; i++) { + var output = buildGroup$1(expression[i], options); + + if (output instanceof DocumentFragment) { + var children = output.children; + groups.push(...children); + } else { + groups.push(output); + } + } // Combine consecutive domTree.symbolNodes into a single symbolNode. + + + buildCommon.tryCombineChars(groups); // If `expression` is a partial group, let the parent handle spacings + // to avoid processing groups multiple times. + + if (!isRealGroup) { + return groups; + } + + var glueOptions = options; + + if (expression.length === 1) { + var node = expression[0]; + + if (node.type === "sizing") { + glueOptions = options.havingSize(node.size); + } else if (node.type === "styling") { + glueOptions = options.havingStyle(styleMap$1[node.style]); + } + } // Dummy spans for determining spacings between surrounding atoms. + // If `expression` has no atoms on the left or right, class "leftmost" + // or "rightmost", respectively, is used to indicate it. + + + var dummyPrev = makeSpan$1([surrounding[0] || "leftmost"], [], options); + var dummyNext = makeSpan$1([surrounding[1] || "rightmost"], [], options); // TODO: These code assumes that a node's math class is the first element + // of its `classes` array. A later cleanup should ensure this, for + // instance by changing the signature of `makeSpan`. + // Before determining what spaces to insert, perform bin cancellation. + // Binary operators change to ordinary symbols in some contexts. + + var isRoot = isRealGroup === "root"; + traverseNonSpaceNodes(groups, (node, prev) => { + var prevType = prev.classes[0]; + var type = node.classes[0]; + + if (prevType === "mbin" && utils.contains(binRightCanceller, type)) { + prev.classes[0] = "mord"; + } else if (type === "mbin" && utils.contains(binLeftCanceller, prevType)) { + node.classes[0] = "mord"; + } + }, { + node: dummyPrev + }, dummyNext, isRoot); + traverseNonSpaceNodes(groups, (node, prev) => { + var prevType = getTypeOfDomTree(prev); + var type = getTypeOfDomTree(node); // 'mtight' indicates that the node is script or scriptscript style. + + var space = prevType && type ? node.hasClass("mtight") ? tightSpacings[prevType][type] : spacings[prevType][type] : null; + + if (space) { + // Insert glue (spacing) after the `prev`. + return buildCommon.makeGlue(space, glueOptions); + } + }, { + node: dummyPrev + }, dummyNext, isRoot); + return groups; +}; // Depth-first traverse non-space `nodes`, calling `callback` with the current and +// previous node as arguments, optionally returning a node to insert after the +// previous node. `prev` is an object with the previous node and `insertAfter` +// function to insert after it. `next` is a node that will be added to the right. +// Used for bin cancellation and inserting spacings. + +var traverseNonSpaceNodes = function traverseNonSpaceNodes(nodes, callback, prev, next, isRoot) { + if (next) { + // temporarily append the right node, if exists + nodes.push(next); + } + + var i = 0; + + for (; i < nodes.length; i++) { + var node = nodes[i]; + var partialGroup = checkPartialGroup(node); + + if (partialGroup) { + // Recursive DFS + // $FlowFixMe: make nodes a $ReadOnlyArray by returning a new array + traverseNonSpaceNodes(partialGroup.children, callback, prev, null, isRoot); + continue; + } // Ignore explicit spaces (e.g., \;, \,) when determining what implicit + // spacing should go between atoms of different classes + + + var nonspace = !node.hasClass("mspace"); + + if (nonspace) { + var result = callback(node, prev.node); + + if (result) { + if (prev.insertAfter) { + prev.insertAfter(result); + } else { + // insert at front + nodes.unshift(result); + i++; + } + } + } + + if (nonspace) { + prev.node = node; + } else if (isRoot && node.hasClass("newline")) { + prev.node = makeSpan$1(["leftmost"]); // treat like beginning of line + } + + prev.insertAfter = (index => n => { + nodes.splice(index + 1, 0, n); + i++; + })(i); + } + + if (next) { + nodes.pop(); + } +}; // Check if given node is a partial group, i.e., does not affect spacing around. + + +var checkPartialGroup = function checkPartialGroup(node) { + if (node instanceof DocumentFragment || node instanceof Anchor || node instanceof Span && node.hasClass("enclosing")) { + return node; + } + + return null; +}; // Return the outermost node of a domTree. + + +var getOutermostNode = function getOutermostNode(node, side) { + var partialGroup = checkPartialGroup(node); + + if (partialGroup) { + var children = partialGroup.children; + + if (children.length) { + if (side === "right") { + return getOutermostNode(children[children.length - 1], "right"); + } else if (side === "left") { + return getOutermostNode(children[0], "left"); + } + } + } + + return node; +}; // Return math atom class (mclass) of a domTree. +// If `side` is given, it will get the type of the outermost node at given side. + + +var getTypeOfDomTree = function getTypeOfDomTree(node, side) { + if (!node) { + return null; + } + + if (side) { + node = getOutermostNode(node, side); + } // This makes a lot of assumptions as to where the type of atom + // appears. We should do a better job of enforcing this. + + + return DomEnum[node.classes[0]] || null; +}; +var makeNullDelimiter = function makeNullDelimiter(options, classes) { + var moreClasses = ["nulldelimiter"].concat(options.baseSizingClasses()); + return makeSpan$1(classes.concat(moreClasses)); +}; +/** + * buildGroup is the function that takes a group and calls the correct groupType + * function for it. It also handles the interaction of size and style changes + * between parents and children. + */ + +var buildGroup$1 = function buildGroup(group, options, baseOptions) { + if (!group) { + return makeSpan$1(); + } + + if (_htmlGroupBuilders[group.type]) { + // Call the groupBuilders function + // $FlowFixMe + var groupNode = _htmlGroupBuilders[group.type](group, options); // If the size changed between the parent and the current group, account + // for that size difference. + + if (baseOptions && options.size !== baseOptions.size) { + groupNode = makeSpan$1(options.sizingClasses(baseOptions), [groupNode], options); + var multiplier = options.sizeMultiplier / baseOptions.sizeMultiplier; + groupNode.height *= multiplier; + groupNode.depth *= multiplier; + } + + return groupNode; + } else { + throw new ParseError("Got group of unknown type: '" + group.type + "'"); + } +}; +/** + * Combine an array of HTML DOM nodes (e.g., the output of `buildExpression`) + * into an unbreakable HTML node of class .base, with proper struts to + * guarantee correct vertical extent. `buildHTML` calls this repeatedly to + * make up the entire expression as a sequence of unbreakable units. + */ + +function buildHTMLUnbreakable(children, options) { + // Compute height and depth of this chunk. + var body = makeSpan$1(["base"], children, options); // Add strut, which ensures that the top of the HTML element falls at + // the height of the expression, and the bottom of the HTML element + // falls at the depth of the expression. + + var strut = makeSpan$1(["strut"]); + strut.style.height = makeEm(body.height + body.depth); + + if (body.depth) { + strut.style.verticalAlign = makeEm(-body.depth); + } + + body.children.unshift(strut); + return body; +} +/** + * Take an entire parse tree, and build it into an appropriate set of HTML + * nodes. + */ + + +function buildHTML(tree, options) { + // Strip off outer tag wrapper for processing below. + var tag = null; + + if (tree.length === 1 && tree[0].type === "tag") { + tag = tree[0].tag; + tree = tree[0].body; + } // Build the expression contained in the tree + + + var expression = buildExpression$1(tree, options, "root"); + var eqnNum; + + if (expression.length === 2 && expression[1].hasClass("tag")) { + // An environment with automatic equation numbers, e.g. {gather}. + eqnNum = expression.pop(); + } + + var children = []; // Create one base node for each chunk between potential line breaks. + // The TeXBook [p.173] says "A formula will be broken only after a + // relation symbol like $=$ or $<$ or $\rightarrow$, or after a binary + // operation symbol like $+$ or $-$ or $\times$, where the relation or + // binary operation is on the ``outer level'' of the formula (i.e., not + // enclosed in {...} and not part of an \over construction)." + + var parts = []; + + for (var i = 0; i < expression.length; i++) { + parts.push(expression[i]); + + if (expression[i].hasClass("mbin") || expression[i].hasClass("mrel") || expression[i].hasClass("allowbreak")) { + // Put any post-operator glue on same line as operator. + // Watch for \nobreak along the way, and stop at \newline. + var nobreak = false; + + while (i < expression.length - 1 && expression[i + 1].hasClass("mspace") && !expression[i + 1].hasClass("newline")) { + i++; + parts.push(expression[i]); + + if (expression[i].hasClass("nobreak")) { + nobreak = true; + } + } // Don't allow break if \nobreak among the post-operator glue. + + + if (!nobreak) { + children.push(buildHTMLUnbreakable(parts, options)); + parts = []; + } + } else if (expression[i].hasClass("newline")) { + // Write the line except the newline + parts.pop(); + + if (parts.length > 0) { + children.push(buildHTMLUnbreakable(parts, options)); + parts = []; + } // Put the newline at the top level + + + children.push(expression[i]); + } + } + + if (parts.length > 0) { + children.push(buildHTMLUnbreakable(parts, options)); + } // Now, if there was a tag, build it too and append it as a final child. + + + var tagChild; + + if (tag) { + tagChild = buildHTMLUnbreakable(buildExpression$1(tag, options, true)); + tagChild.classes = ["tag"]; + children.push(tagChild); + } else if (eqnNum) { + children.push(eqnNum); + } + + var htmlNode = makeSpan$1(["katex-html"], children); + htmlNode.setAttribute("aria-hidden", "true"); // Adjust the strut of the tag to be the maximum height of all children + // (the height of the enclosing htmlNode) for proper vertical alignment. + + if (tagChild) { + var strut = tagChild.children[0]; + strut.style.height = makeEm(htmlNode.height + htmlNode.depth); + + if (htmlNode.depth) { + strut.style.verticalAlign = makeEm(-htmlNode.depth); + } + } + + return htmlNode; +} + +/** + * These objects store data about MathML nodes. This is the MathML equivalent + * of the types in domTree.js. Since MathML handles its own rendering, and + * since we're mainly using MathML to improve accessibility, we don't manage + * any of the styling state that the plain DOM nodes do. + * + * The `toNode` and `toMarkup` functions work similarly to how they do in + * domTree.js, creating namespaced DOM nodes and HTML text markup respectively. + */ +function newDocumentFragment(children) { + return new DocumentFragment(children); +} +/** + * This node represents a general purpose MathML node of any type. The + * constructor requires the type of node to create (for example, `"mo"` or + * `"mspace"`, corresponding to `` and `` tags). + */ + +class MathNode { + constructor(type, children, classes) { + this.type = void 0; + this.attributes = void 0; + this.children = void 0; + this.classes = void 0; + this.type = type; + this.attributes = {}; + this.children = children || []; + this.classes = classes || []; + } + /** + * Sets an attribute on a MathML node. MathML depends on attributes to convey a + * semantic content, so this is used heavily. + */ + + + setAttribute(name, value) { + this.attributes[name] = value; + } + /** + * Gets an attribute on a MathML node. + */ + + + getAttribute(name) { + return this.attributes[name]; + } + /** + * Converts the math node into a MathML-namespaced DOM element. + */ + + + toNode() { + var node = document.createElementNS("http://www.w3.org/1998/Math/MathML", this.type); + + for (var attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } + + if (this.classes.length > 0) { + node.className = createClass(this.classes); + } + + for (var i = 0; i < this.children.length; i++) { + // Combine multiple TextNodes into one TextNode, to prevent + // screen readers from reading each as a separate word [#3995] + if (this.children[i] instanceof TextNode && this.children[i + 1] instanceof TextNode) { + var text = this.children[i].toText() + this.children[++i].toText(); + + while (this.children[i + 1] instanceof TextNode) { + text += this.children[++i].toText(); + } + + node.appendChild(new TextNode(text).toNode()); + } else { + node.appendChild(this.children[i].toNode()); + } + } + + return node; + } + /** + * Converts the math node into an HTML markup string. + */ + + + toMarkup() { + var markup = "<" + this.type; // Add the attributes + + for (var attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + markup += " " + attr + "=\""; + markup += utils.escape(this.attributes[attr]); + markup += "\""; + } + } + + if (this.classes.length > 0) { + markup += " class =\"" + utils.escape(createClass(this.classes)) + "\""; + } + + markup += ">"; + + for (var i = 0; i < this.children.length; i++) { + markup += this.children[i].toMarkup(); + } + + markup += ""; + return markup; + } + /** + * Converts the math node into a string, similar to innerText, but escaped. + */ + + + toText() { + return this.children.map(child => child.toText()).join(""); + } + +} +/** + * This node represents a piece of text. + */ + +class TextNode { + constructor(text) { + this.text = void 0; + this.text = text; + } + /** + * Converts the text node into a DOM text node. + */ + + + toNode() { + return document.createTextNode(this.text); + } + /** + * Converts the text node into escaped HTML markup + * (representing the text itself). + */ + + + toMarkup() { + return utils.escape(this.toText()); + } + /** + * Converts the text node into a string + * (representing the text itself). + */ + + + toText() { + return this.text; + } + +} +/** + * This node represents a space, but may render as or as text, + * depending on the width. + */ + +class SpaceNode { + /** + * Create a Space node with width given in CSS ems. + */ + constructor(width) { + this.width = void 0; + this.character = void 0; + this.width = width; // See https://www.w3.org/TR/2000/WD-MathML2-20000328/chapter6.html + // for a table of space-like characters. We use Unicode + // representations instead of &LongNames; as it's not clear how to + // make the latter via document.createTextNode. + + if (width >= 0.05555 && width <= 0.05556) { + this.character = "\u200a"; //   + } else if (width >= 0.1666 && width <= 0.1667) { + this.character = "\u2009"; //   + } else if (width >= 0.2222 && width <= 0.2223) { + this.character = "\u2005"; //   + } else if (width >= 0.2777 && width <= 0.2778) { + this.character = "\u2005\u200a"; //    + } else if (width >= -0.05556 && width <= -0.05555) { + this.character = "\u200a\u2063"; // ​ + } else if (width >= -0.1667 && width <= -0.1666) { + this.character = "\u2009\u2063"; // ​ + } else if (width >= -0.2223 && width <= -0.2222) { + this.character = "\u205f\u2063"; // ​ + } else if (width >= -0.2778 && width <= -0.2777) { + this.character = "\u2005\u2063"; // ​ + } else { + this.character = null; + } + } + /** + * Converts the math node into a MathML-namespaced DOM element. + */ + + + toNode() { + if (this.character) { + return document.createTextNode(this.character); + } else { + var node = document.createElementNS("http://www.w3.org/1998/Math/MathML", "mspace"); + node.setAttribute("width", makeEm(this.width)); + return node; + } + } + /** + * Converts the math node into an HTML markup string. + */ + + + toMarkup() { + if (this.character) { + return "" + this.character + ""; + } else { + return ""; + } + } + /** + * Converts the math node into a string, similar to innerText. + */ + + + toText() { + if (this.character) { + return this.character; + } else { + return " "; + } + } + +} + +var mathMLTree = { + MathNode, + TextNode, + SpaceNode, + newDocumentFragment +}; + +/** + * This file converts a parse tree into a corresponding MathML tree. The main + * entry point is the `buildMathML` function, which takes a parse tree from the + * parser. + */ + +/** + * Takes a symbol and converts it into a MathML text node after performing + * optional replacement from symbols.js. + */ +var makeText = function makeText(text, mode, options) { + if (symbols[mode][text] && symbols[mode][text].replace && text.charCodeAt(0) !== 0xD835 && !(ligatures.hasOwnProperty(text) && options && (options.fontFamily && options.fontFamily.slice(4, 6) === "tt" || options.font && options.font.slice(4, 6) === "tt"))) { + text = symbols[mode][text].replace; + } + + return new mathMLTree.TextNode(text); +}; +/** + * Wrap the given array of nodes in an node if needed, i.e., + * unless the array has length 1. Always returns a single node. + */ + +var makeRow = function makeRow(body) { + if (body.length === 1) { + return body[0]; + } else { + return new mathMLTree.MathNode("mrow", body); + } +}; +/** + * Returns the math variant as a string or null if none is required. + */ + +var getVariant = function getVariant(group, options) { + // Handle \text... font specifiers as best we can. + // MathML has a limited list of allowable mathvariant specifiers; see + // https://www.w3.org/TR/MathML3/chapter3.html#presm.commatt + if (options.fontFamily === "texttt") { + return "monospace"; + } else if (options.fontFamily === "textsf") { + if (options.fontShape === "textit" && options.fontWeight === "textbf") { + return "sans-serif-bold-italic"; + } else if (options.fontShape === "textit") { + return "sans-serif-italic"; + } else if (options.fontWeight === "textbf") { + return "bold-sans-serif"; + } else { + return "sans-serif"; + } + } else if (options.fontShape === "textit" && options.fontWeight === "textbf") { + return "bold-italic"; + } else if (options.fontShape === "textit") { + return "italic"; + } else if (options.fontWeight === "textbf") { + return "bold"; + } + + var font = options.font; + + if (!font || font === "mathnormal") { + return null; + } + + var mode = group.mode; + + if (font === "mathit") { + return "italic"; + } else if (font === "boldsymbol") { + return group.type === "textord" ? "bold" : "bold-italic"; + } else if (font === "mathbf") { + return "bold"; + } else if (font === "mathbb") { + return "double-struck"; + } else if (font === "mathsfit") { + return "sans-serif-italic"; + } else if (font === "mathfrak") { + return "fraktur"; + } else if (font === "mathscr" || font === "mathcal") { + // MathML makes no distinction between script and calligraphic + return "script"; + } else if (font === "mathsf") { + return "sans-serif"; + } else if (font === "mathtt") { + return "monospace"; + } + + var text = group.text; + + if (utils.contains(["\\imath", "\\jmath"], text)) { + return null; + } + + if (symbols[mode][text] && symbols[mode][text].replace) { + text = symbols[mode][text].replace; + } + + var fontName = buildCommon.fontMap[font].fontName; + + if (getCharacterMetrics(text, fontName, mode)) { + return buildCommon.fontMap[font].variant; + } + + return null; +}; +/** + * Check for . which is how a dot renders in MathML, + * or , + * which is how a braced comma {,} renders in MathML + */ + +function isNumberPunctuation(group) { + if (!group) { + return false; + } + + if (group.type === 'mi' && group.children.length === 1) { + var child = group.children[0]; + return child instanceof TextNode && child.text === '.'; + } else if (group.type === 'mo' && group.children.length === 1 && group.getAttribute('separator') === 'true' && group.getAttribute('lspace') === '0em' && group.getAttribute('rspace') === '0em') { + var _child = group.children[0]; + return _child instanceof TextNode && _child.text === ','; + } else { + return false; + } +} +/** + * Takes a list of nodes, builds them, and returns a list of the generated + * MathML nodes. Also combine consecutive outputs into a single + * tag. + */ + + +var buildExpression = function buildExpression(expression, options, isOrdgroup) { + if (expression.length === 1) { + var group = buildGroup(expression[0], options); + + if (isOrdgroup && group instanceof MathNode && group.type === "mo") { + // When TeX writers want to suppress spacing on an operator, + // they often put the operator by itself inside braces. + group.setAttribute("lspace", "0em"); + group.setAttribute("rspace", "0em"); + } + + return [group]; + } + + var groups = []; + var lastGroup; + + for (var i = 0; i < expression.length; i++) { + var _group = buildGroup(expression[i], options); + + if (_group instanceof MathNode && lastGroup instanceof MathNode) { + // Concatenate adjacent s + if (_group.type === 'mtext' && lastGroup.type === 'mtext' && _group.getAttribute('mathvariant') === lastGroup.getAttribute('mathvariant')) { + lastGroup.children.push(..._group.children); + continue; // Concatenate adjacent s + } else if (_group.type === 'mn' && lastGroup.type === 'mn') { + lastGroup.children.push(..._group.children); + continue; // Concatenate ... followed by . + } else if (isNumberPunctuation(_group) && lastGroup.type === 'mn') { + lastGroup.children.push(..._group.children); + continue; // Concatenate . followed by ... + } else if (_group.type === 'mn' && isNumberPunctuation(lastGroup)) { + _group.children = [...lastGroup.children, ..._group.children]; + groups.pop(); // Put preceding ... or . inside base of + // ...base......exponent... (or ) + } else if ((_group.type === 'msup' || _group.type === 'msub') && _group.children.length >= 1 && (lastGroup.type === 'mn' || isNumberPunctuation(lastGroup))) { + var base = _group.children[0]; + + if (base instanceof MathNode && base.type === 'mn') { + base.children = [...lastGroup.children, ...base.children]; + groups.pop(); + } // \not + + } else if (lastGroup.type === 'mi' && lastGroup.children.length === 1) { + var lastChild = lastGroup.children[0]; + + if (lastChild instanceof TextNode && lastChild.text === '\u0338' && (_group.type === 'mo' || _group.type === 'mi' || _group.type === 'mn')) { + var child = _group.children[0]; + + if (child instanceof TextNode && child.text.length > 0) { + // Overlay with combining character long solidus + child.text = child.text.slice(0, 1) + "\u0338" + child.text.slice(1); + groups.pop(); + } + } + } + } + + groups.push(_group); + lastGroup = _group; + } + + return groups; +}; +/** + * Equivalent to buildExpression, but wraps the elements in an + * if there's more than one. Returns a single node instead of an array. + */ + +var buildExpressionRow = function buildExpressionRow(expression, options, isOrdgroup) { + return makeRow(buildExpression(expression, options, isOrdgroup)); +}; +/** + * Takes a group from the parser and calls the appropriate groupBuilders function + * on it to produce a MathML node. + */ + +var buildGroup = function buildGroup(group, options) { + if (!group) { + return new mathMLTree.MathNode("mrow"); + } + + if (_mathmlGroupBuilders[group.type]) { + // Call the groupBuilders function + // $FlowFixMe + var result = _mathmlGroupBuilders[group.type](group, options); // $FlowFixMe + + return result; + } else { + throw new ParseError("Got group of unknown type: '" + group.type + "'"); + } +}; +/** + * Takes a full parse tree and settings and builds a MathML representation of + * it. In particular, we put the elements from building the parse tree into a + * tag so we can also include that TeX source as an annotation. + * + * Note that we actually return a domTree element with a `` inside it so + * we can do appropriate styling. + */ + +function buildMathML(tree, texExpression, options, isDisplayMode, forMathmlOnly) { + var expression = buildExpression(tree, options); // TODO: Make a pass thru the MathML similar to buildHTML.traverseNonSpaceNodes + // and add spacing nodes. This is necessary only adjacent to math operators + // like \sin or \lim or to subsup elements that contain math operators. + // MathML takes care of the other spacing issues. + // Wrap up the expression in an mrow so it is presented in the semantics + // tag correctly, unless it's a single or . + + var wrapper; + + if (expression.length === 1 && expression[0] instanceof MathNode && utils.contains(["mrow", "mtable"], expression[0].type)) { + wrapper = expression[0]; + } else { + wrapper = new mathMLTree.MathNode("mrow", expression); + } // Build a TeX annotation of the source + + + var annotation = new mathMLTree.MathNode("annotation", [new mathMLTree.TextNode(texExpression)]); + annotation.setAttribute("encoding", "application/x-tex"); + var semantics = new mathMLTree.MathNode("semantics", [wrapper, annotation]); + var math = new mathMLTree.MathNode("math", [semantics]); + math.setAttribute("xmlns", "http://www.w3.org/1998/Math/MathML"); + + if (isDisplayMode) { + math.setAttribute("display", "block"); + } // You can't style nodes, so we wrap the node in a span. + // NOTE: The span class is not typed to have nodes as children, and + // we don't want to make the children type more generic since the children + // of span are expected to have more fields in `buildHtml` contexts. + + + var wrapperClass = forMathmlOnly ? "katex" : "katex-mathml"; // $FlowFixMe + + return buildCommon.makeSpan([wrapperClass], [math]); +} + +var optionsFromSettings = function optionsFromSettings(settings) { + return new Options({ + style: settings.displayMode ? Style$1.DISPLAY : Style$1.TEXT, + maxSize: settings.maxSize, + minRuleThickness: settings.minRuleThickness + }); +}; + +var displayWrap = function displayWrap(node, settings) { + if (settings.displayMode) { + var classes = ["katex-display"]; + + if (settings.leqno) { + classes.push("leqno"); + } + + if (settings.fleqn) { + classes.push("fleqn"); + } + + node = buildCommon.makeSpan(classes, [node]); + } + + return node; +}; + +var buildTree = function buildTree(tree, expression, settings) { + var options = optionsFromSettings(settings); + var katexNode; + + if (settings.output === "mathml") { + return buildMathML(tree, expression, options, settings.displayMode, true); + } else if (settings.output === "html") { + var htmlNode = buildHTML(tree, options); + katexNode = buildCommon.makeSpan(["katex"], [htmlNode]); + } else { + var mathMLNode = buildMathML(tree, expression, options, settings.displayMode, false); + + var _htmlNode = buildHTML(tree, options); + + katexNode = buildCommon.makeSpan(["katex"], [mathMLNode, _htmlNode]); + } + + return displayWrap(katexNode, settings); +}; +var buildHTMLTree = function buildHTMLTree(tree, expression, settings) { + var options = optionsFromSettings(settings); + var htmlNode = buildHTML(tree, options); + var katexNode = buildCommon.makeSpan(["katex"], [htmlNode]); + return displayWrap(katexNode, settings); +}; + +/** + * This file provides support to buildMathML.js and buildHTML.js + * for stretchy wide elements rendered from SVG files + * and other CSS trickery. + */ +var stretchyCodePoint = { + widehat: "^", + widecheck: "ˇ", + widetilde: "~", + utilde: "~", + overleftarrow: "\u2190", + underleftarrow: "\u2190", + xleftarrow: "\u2190", + overrightarrow: "\u2192", + underrightarrow: "\u2192", + xrightarrow: "\u2192", + underbrace: "\u23df", + overbrace: "\u23de", + overgroup: "\u23e0", + undergroup: "\u23e1", + overleftrightarrow: "\u2194", + underleftrightarrow: "\u2194", + xleftrightarrow: "\u2194", + Overrightarrow: "\u21d2", + xRightarrow: "\u21d2", + overleftharpoon: "\u21bc", + xleftharpoonup: "\u21bc", + overrightharpoon: "\u21c0", + xrightharpoonup: "\u21c0", + xLeftarrow: "\u21d0", + xLeftrightarrow: "\u21d4", + xhookleftarrow: "\u21a9", + xhookrightarrow: "\u21aa", + xmapsto: "\u21a6", + xrightharpoondown: "\u21c1", + xleftharpoondown: "\u21bd", + xrightleftharpoons: "\u21cc", + xleftrightharpoons: "\u21cb", + xtwoheadleftarrow: "\u219e", + xtwoheadrightarrow: "\u21a0", + xlongequal: "=", + xtofrom: "\u21c4", + xrightleftarrows: "\u21c4", + xrightequilibrium: "\u21cc", + // Not a perfect match. + xleftequilibrium: "\u21cb", + // None better available. + "\\cdrightarrow": "\u2192", + "\\cdleftarrow": "\u2190", + "\\cdlongequal": "=" +}; + +var mathMLnode = function mathMLnode(label) { + var node = new mathMLTree.MathNode("mo", [new mathMLTree.TextNode(stretchyCodePoint[label.replace(/^\\/, '')])]); + node.setAttribute("stretchy", "true"); + return node; +}; // Many of the KaTeX SVG images have been adapted from glyphs in KaTeX fonts. +// Copyright (c) 2009-2010, Design Science, Inc. () +// Copyright (c) 2014-2017 Khan Academy () +// Licensed under the SIL Open Font License, Version 1.1. +// See \nhttp://scripts.sil.org/OFL +// Very Long SVGs +// Many of the KaTeX stretchy wide elements use a long SVG image and an +// overflow: hidden tactic to achieve a stretchy image while avoiding +// distortion of arrowheads or brace corners. +// The SVG typically contains a very long (400 em) arrow. +// The SVG is in a container span that has overflow: hidden, so the span +// acts like a window that exposes only part of the SVG. +// The SVG always has a longer, thinner aspect ratio than the container span. +// After the SVG fills 100% of the height of the container span, +// there is a long arrow shaft left over. That left-over shaft is not shown. +// Instead, it is sliced off because the span's CSS has overflow: hidden. +// Thus, the reader sees an arrow that matches the subject matter width +// without distortion. +// Some functions, such as \cancel, need to vary their aspect ratio. These +// functions do not get the overflow SVG treatment. +// Second Brush Stroke +// Low resolution monitors struggle to display images in fine detail. +// So browsers apply anti-aliasing. A long straight arrow shaft therefore +// will sometimes appear as if it has a blurred edge. +// To mitigate this, these SVG files contain a second "brush-stroke" on the +// arrow shafts. That is, a second long thin rectangular SVG path has been +// written directly on top of each arrow shaft. This reinforcement causes +// some of the screen pixels to display as black instead of the anti-aliased +// gray pixel that a single path would generate. So we get arrow shafts +// whose edges appear to be sharper. +// In the katexImagesData object just below, the dimensions all +// correspond to path geometry inside the relevant SVG. +// For example, \overrightarrow uses the same arrowhead as glyph U+2192 +// from the KaTeX Main font. The scaling factor is 1000. +// That is, inside the font, that arrowhead is 522 units tall, which +// corresponds to 0.522 em inside the document. + + +var katexImagesData = { + // path(s), minWidth, height, align + overrightarrow: [["rightarrow"], 0.888, 522, "xMaxYMin"], + overleftarrow: [["leftarrow"], 0.888, 522, "xMinYMin"], + underrightarrow: [["rightarrow"], 0.888, 522, "xMaxYMin"], + underleftarrow: [["leftarrow"], 0.888, 522, "xMinYMin"], + xrightarrow: [["rightarrow"], 1.469, 522, "xMaxYMin"], + "\\cdrightarrow": [["rightarrow"], 3.0, 522, "xMaxYMin"], + // CD minwwidth2.5pc + xleftarrow: [["leftarrow"], 1.469, 522, "xMinYMin"], + "\\cdleftarrow": [["leftarrow"], 3.0, 522, "xMinYMin"], + Overrightarrow: [["doublerightarrow"], 0.888, 560, "xMaxYMin"], + xRightarrow: [["doublerightarrow"], 1.526, 560, "xMaxYMin"], + xLeftarrow: [["doubleleftarrow"], 1.526, 560, "xMinYMin"], + overleftharpoon: [["leftharpoon"], 0.888, 522, "xMinYMin"], + xleftharpoonup: [["leftharpoon"], 0.888, 522, "xMinYMin"], + xleftharpoondown: [["leftharpoondown"], 0.888, 522, "xMinYMin"], + overrightharpoon: [["rightharpoon"], 0.888, 522, "xMaxYMin"], + xrightharpoonup: [["rightharpoon"], 0.888, 522, "xMaxYMin"], + xrightharpoondown: [["rightharpoondown"], 0.888, 522, "xMaxYMin"], + xlongequal: [["longequal"], 0.888, 334, "xMinYMin"], + "\\cdlongequal": [["longequal"], 3.0, 334, "xMinYMin"], + xtwoheadleftarrow: [["twoheadleftarrow"], 0.888, 334, "xMinYMin"], + xtwoheadrightarrow: [["twoheadrightarrow"], 0.888, 334, "xMaxYMin"], + overleftrightarrow: [["leftarrow", "rightarrow"], 0.888, 522], + overbrace: [["leftbrace", "midbrace", "rightbrace"], 1.6, 548], + underbrace: [["leftbraceunder", "midbraceunder", "rightbraceunder"], 1.6, 548], + underleftrightarrow: [["leftarrow", "rightarrow"], 0.888, 522], + xleftrightarrow: [["leftarrow", "rightarrow"], 1.75, 522], + xLeftrightarrow: [["doubleleftarrow", "doublerightarrow"], 1.75, 560], + xrightleftharpoons: [["leftharpoondownplus", "rightharpoonplus"], 1.75, 716], + xleftrightharpoons: [["leftharpoonplus", "rightharpoondownplus"], 1.75, 716], + xhookleftarrow: [["leftarrow", "righthook"], 1.08, 522], + xhookrightarrow: [["lefthook", "rightarrow"], 1.08, 522], + overlinesegment: [["leftlinesegment", "rightlinesegment"], 0.888, 522], + underlinesegment: [["leftlinesegment", "rightlinesegment"], 0.888, 522], + overgroup: [["leftgroup", "rightgroup"], 0.888, 342], + undergroup: [["leftgroupunder", "rightgroupunder"], 0.888, 342], + xmapsto: [["leftmapsto", "rightarrow"], 1.5, 522], + xtofrom: [["leftToFrom", "rightToFrom"], 1.75, 528], + // The next three arrows are from the mhchem package. + // In mhchem.sty, min-length is 2.0em. But these arrows might appear in the + // document as \xrightarrow or \xrightleftharpoons. Those have + // min-length = 1.75em, so we set min-length on these next three to match. + xrightleftarrows: [["baraboveleftarrow", "rightarrowabovebar"], 1.75, 901], + xrightequilibrium: [["baraboveshortleftharpoon", "rightharpoonaboveshortbar"], 1.75, 716], + xleftequilibrium: [["shortbaraboveleftharpoon", "shortrightharpoonabovebar"], 1.75, 716] +}; + +var groupLength = function groupLength(arg) { + if (arg.type === "ordgroup") { + return arg.body.length; + } else { + return 1; + } +}; + +var svgSpan = function svgSpan(group, options) { + // Create a span with inline SVG for the element. + function buildSvgSpan_() { + var viewBoxWidth = 400000; // default + + var label = group.label.slice(1); + + if (utils.contains(["widehat", "widecheck", "widetilde", "utilde"], label)) { + // Each type in the `if` statement corresponds to one of the ParseNode + // types below. This narrowing is required to access `grp.base`. + // $FlowFixMe + var grp = group; // There are four SVG images available for each function. + // Choose a taller image when there are more characters. + + var numChars = groupLength(grp.base); + var viewBoxHeight; + var pathName; + + var _height; + + if (numChars > 5) { + if (label === "widehat" || label === "widecheck") { + viewBoxHeight = 420; + viewBoxWidth = 2364; + _height = 0.42; + pathName = label + "4"; + } else { + viewBoxHeight = 312; + viewBoxWidth = 2340; + _height = 0.34; + pathName = "tilde4"; + } + } else { + var imgIndex = [1, 1, 2, 2, 3, 3][numChars]; + + if (label === "widehat" || label === "widecheck") { + viewBoxWidth = [0, 1062, 2364, 2364, 2364][imgIndex]; + viewBoxHeight = [0, 239, 300, 360, 420][imgIndex]; + _height = [0, 0.24, 0.3, 0.3, 0.36, 0.42][imgIndex]; + pathName = label + imgIndex; + } else { + viewBoxWidth = [0, 600, 1033, 2339, 2340][imgIndex]; + viewBoxHeight = [0, 260, 286, 306, 312][imgIndex]; + _height = [0, 0.26, 0.286, 0.3, 0.306, 0.34][imgIndex]; + pathName = "tilde" + imgIndex; + } + } + + var path = new PathNode(pathName); + var svgNode = new SvgNode([path], { + "width": "100%", + "height": makeEm(_height), + "viewBox": "0 0 " + viewBoxWidth + " " + viewBoxHeight, + "preserveAspectRatio": "none" + }); + return { + span: buildCommon.makeSvgSpan([], [svgNode], options), + minWidth: 0, + height: _height + }; + } else { + var spans = []; + var data = katexImagesData[label]; + var [paths, _minWidth, _viewBoxHeight] = data; + + var _height2 = _viewBoxHeight / 1000; + + var numSvgChildren = paths.length; + var widthClasses; + var aligns; + + if (numSvgChildren === 1) { + // $FlowFixMe: All these cases must be of the 4-tuple type. + var align1 = data[3]; + widthClasses = ["hide-tail"]; + aligns = [align1]; + } else if (numSvgChildren === 2) { + widthClasses = ["halfarrow-left", "halfarrow-right"]; + aligns = ["xMinYMin", "xMaxYMin"]; + } else if (numSvgChildren === 3) { + widthClasses = ["brace-left", "brace-center", "brace-right"]; + aligns = ["xMinYMin", "xMidYMin", "xMaxYMin"]; + } else { + throw new Error("Correct katexImagesData or update code here to support\n " + numSvgChildren + " children."); + } + + for (var i = 0; i < numSvgChildren; i++) { + var _path = new PathNode(paths[i]); + + var _svgNode = new SvgNode([_path], { + "width": "400em", + "height": makeEm(_height2), + "viewBox": "0 0 " + viewBoxWidth + " " + _viewBoxHeight, + "preserveAspectRatio": aligns[i] + " slice" + }); + + var _span = buildCommon.makeSvgSpan([widthClasses[i]], [_svgNode], options); + + if (numSvgChildren === 1) { + return { + span: _span, + minWidth: _minWidth, + height: _height2 + }; + } else { + _span.style.height = makeEm(_height2); + spans.push(_span); + } + } + + return { + span: buildCommon.makeSpan(["stretchy"], spans, options), + minWidth: _minWidth, + height: _height2 + }; + } + } // buildSvgSpan_() + + + var { + span, + minWidth, + height + } = buildSvgSpan_(); // Note that we are returning span.depth = 0. + // Any adjustments relative to the baseline must be done in buildHTML. + + span.height = height; + span.style.height = makeEm(height); + + if (minWidth > 0) { + span.style.minWidth = makeEm(minWidth); + } + + return span; +}; + +var encloseSpan = function encloseSpan(inner, label, topPad, bottomPad, options) { + // Return an image span for \cancel, \bcancel, \xcancel, \fbox, or \angl + var img; + var totalHeight = inner.height + inner.depth + topPad + bottomPad; + + if (/fbox|color|angl/.test(label)) { + img = buildCommon.makeSpan(["stretchy", label], [], options); + + if (label === "fbox") { + var color = options.color && options.getColor(); + + if (color) { + img.style.borderColor = color; + } + } + } else { + // \cancel, \bcancel, or \xcancel + // Since \cancel's SVG is inline and it omits the viewBox attribute, + // its stroke-width will not vary with span area. + var lines = []; + + if (/^[bx]cancel$/.test(label)) { + lines.push(new LineNode({ + "x1": "0", + "y1": "0", + "x2": "100%", + "y2": "100%", + "stroke-width": "0.046em" + })); + } + + if (/^x?cancel$/.test(label)) { + lines.push(new LineNode({ + "x1": "0", + "y1": "100%", + "x2": "100%", + "y2": "0", + "stroke-width": "0.046em" + })); + } + + var svgNode = new SvgNode(lines, { + "width": "100%", + "height": makeEm(totalHeight) + }); + img = buildCommon.makeSvgSpan([], [svgNode], options); + } + + img.height = totalHeight; + img.style.height = makeEm(totalHeight); + return img; +}; + +var stretchy = { + encloseSpan, + mathMLnode, + svgSpan +}; + +/** + * Asserts that the node is of the given type and returns it with stricter + * typing. Throws if the node's type does not match. + */ +function assertNodeType(node, type) { + if (!node || node.type !== type) { + throw new Error("Expected node of type " + type + ", but got " + (node ? "node of type " + node.type : String(node))); + } // $FlowFixMe, >=0.125 + + + return node; +} +/** + * Returns the node more strictly typed iff it is of the given type. Otherwise, + * returns null. + */ + +function assertSymbolNodeType(node) { + var typedNode = checkSymbolNodeType(node); + + if (!typedNode) { + throw new Error("Expected node of symbol group type, but got " + (node ? "node of type " + node.type : String(node))); + } + + return typedNode; +} +/** + * Returns the node more strictly typed iff it is of the given type. Otherwise, + * returns null. + */ + +function checkSymbolNodeType(node) { + if (node && (node.type === "atom" || NON_ATOMS.hasOwnProperty(node.type))) { + // $FlowFixMe + return node; + } + + return null; +} + +// NOTE: Unlike most `htmlBuilder`s, this one handles not only "accent", but +// also "supsub" since an accent can affect super/subscripting. +var htmlBuilder$a = (grp, options) => { + // Accents are handled in the TeXbook pg. 443, rule 12. + var base; + var group; + var supSubGroup; + + if (grp && grp.type === "supsub") { + // If our base is a character box, and we have superscripts and + // subscripts, the supsub will defer to us. In particular, we want + // to attach the superscripts and subscripts to the inner body (so + // that the position of the superscripts and subscripts won't be + // affected by the height of the accent). We accomplish this by + // sticking the base of the accent into the base of the supsub, and + // rendering that, while keeping track of where the accent is. + // The real accent group is the base of the supsub group + group = assertNodeType(grp.base, "accent"); // The character box is the base of the accent group + + base = group.base; // Stick the character box into the base of the supsub group + + grp.base = base; // Rerender the supsub group with its new base, and store that + // result. + + supSubGroup = assertSpan(buildGroup$1(grp, options)); // reset original base + + grp.base = group; + } else { + group = assertNodeType(grp, "accent"); + base = group.base; + } // Build the base group + + + var body = buildGroup$1(base, options.havingCrampedStyle()); // Does the accent need to shift for the skew of a character? + + var mustShift = group.isShifty && utils.isCharacterBox(base); // Calculate the skew of the accent. This is based on the line "If the + // nucleus is not a single character, let s = 0; otherwise set s to the + // kern amount for the nucleus followed by the \skewchar of its font." + // Note that our skew metrics are just the kern between each character + // and the skewchar. + + var skew = 0; + + if (mustShift) { + // If the base is a character box, then we want the skew of the + // innermost character. To do that, we find the innermost character: + var baseChar = utils.getBaseElem(base); // Then, we render its group to get the symbol inside it + + var baseGroup = buildGroup$1(baseChar, options.havingCrampedStyle()); // Finally, we pull the skew off of the symbol. + + skew = assertSymbolDomNode(baseGroup).skew; // Note that we now throw away baseGroup, because the layers we + // removed with getBaseElem might contain things like \color which + // we can't get rid of. + // TODO(emily): Find a better way to get the skew + } + + var accentBelow = group.label === "\\c"; // calculate the amount of space between the body and the accent + + var clearance = accentBelow ? body.height + body.depth : Math.min(body.height, options.fontMetrics().xHeight); // Build the accent + + var accentBody; + + if (!group.isStretchy) { + var accent; + var width; + + if (group.label === "\\vec") { + // Before version 0.9, \vec used the combining font glyph U+20D7. + // But browsers, especially Safari, are not consistent in how they + // render combining characters when not preceded by a character. + // So now we use an SVG. + // If Safari reforms, we should consider reverting to the glyph. + accent = buildCommon.staticSvg("vec", options); + width = buildCommon.svgData.vec[1]; + } else { + accent = buildCommon.makeOrd({ + mode: group.mode, + text: group.label + }, options, "textord"); + accent = assertSymbolDomNode(accent); // Remove the italic correction of the accent, because it only serves to + // shift the accent over to a place we don't want. + + accent.italic = 0; + width = accent.width; + + if (accentBelow) { + clearance += accent.depth; + } + } + + accentBody = buildCommon.makeSpan(["accent-body"], [accent]); // "Full" accents expand the width of the resulting symbol to be + // at least the width of the accent, and overlap directly onto the + // character without any vertical offset. + + var accentFull = group.label === "\\textcircled"; + + if (accentFull) { + accentBody.classes.push('accent-full'); + clearance = body.height; + } // Shift the accent over by the skew. + + + var left = skew; // CSS defines `.katex .accent .accent-body:not(.accent-full) { width: 0 }` + // so that the accent doesn't contribute to the bounding box. + // We need to shift the character by its width (effectively half + // its width) to compensate. + + if (!accentFull) { + left -= width / 2; + } + + accentBody.style.left = makeEm(left); // \textcircled uses the \bigcirc glyph, so it needs some + // vertical adjustment to match LaTeX. + + if (group.label === "\\textcircled") { + accentBody.style.top = ".2em"; + } + + accentBody = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: body + }, { + type: "kern", + size: -clearance + }, { + type: "elem", + elem: accentBody + }] + }, options); + } else { + accentBody = stretchy.svgSpan(group, options); + accentBody = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: body + }, { + type: "elem", + elem: accentBody, + wrapperClasses: ["svg-align"], + wrapperStyle: skew > 0 ? { + width: "calc(100% - " + makeEm(2 * skew) + ")", + marginLeft: makeEm(2 * skew) + } : undefined + }] + }, options); + } + + var accentWrap = buildCommon.makeSpan(["mord", "accent"], [accentBody], options); + + if (supSubGroup) { + // Here, we replace the "base" child of the supsub with our newly + // generated accent. + supSubGroup.children[0] = accentWrap; // Since we don't rerun the height calculation after replacing the + // accent, we manually recalculate height. + + supSubGroup.height = Math.max(accentWrap.height, supSubGroup.height); // Accents should always be ords, even when their innards are not. + + supSubGroup.classes[0] = "mord"; + return supSubGroup; + } else { + return accentWrap; + } +}; + +var mathmlBuilder$9 = (group, options) => { + var accentNode = group.isStretchy ? stretchy.mathMLnode(group.label) : new mathMLTree.MathNode("mo", [makeText(group.label, group.mode)]); + var node = new mathMLTree.MathNode("mover", [buildGroup(group.base, options), accentNode]); + node.setAttribute("accent", "true"); + return node; +}; + +var NON_STRETCHY_ACCENT_REGEX = new RegExp(["\\acute", "\\grave", "\\ddot", "\\tilde", "\\bar", "\\breve", "\\check", "\\hat", "\\vec", "\\dot", "\\mathring"].map(accent => "\\" + accent).join("|")); // Accents + +defineFunction({ + type: "accent", + names: ["\\acute", "\\grave", "\\ddot", "\\tilde", "\\bar", "\\breve", "\\check", "\\hat", "\\vec", "\\dot", "\\mathring", "\\widecheck", "\\widehat", "\\widetilde", "\\overrightarrow", "\\overleftarrow", "\\Overrightarrow", "\\overleftrightarrow", "\\overgroup", "\\overlinesegment", "\\overleftharpoon", "\\overrightharpoon"], + props: { + numArgs: 1 + }, + handler: (context, args) => { + var base = normalizeArgument(args[0]); + var isStretchy = !NON_STRETCHY_ACCENT_REGEX.test(context.funcName); + var isShifty = !isStretchy || context.funcName === "\\widehat" || context.funcName === "\\widetilde" || context.funcName === "\\widecheck"; + return { + type: "accent", + mode: context.parser.mode, + label: context.funcName, + isStretchy: isStretchy, + isShifty: isShifty, + base: base + }; + }, + htmlBuilder: htmlBuilder$a, + mathmlBuilder: mathmlBuilder$9 +}); // Text-mode accents + +defineFunction({ + type: "accent", + names: ["\\'", "\\`", "\\^", "\\~", "\\=", "\\u", "\\.", '\\"', "\\c", "\\r", "\\H", "\\v", "\\textcircled"], + props: { + numArgs: 1, + allowedInText: true, + allowedInMath: true, + // unless in strict mode + argTypes: ["primitive"] + }, + handler: (context, args) => { + var base = args[0]; + var mode = context.parser.mode; + + if (mode === "math") { + context.parser.settings.reportNonstrict("mathVsTextAccents", "LaTeX's accent " + context.funcName + " works only in text mode"); + mode = "text"; + } + + return { + type: "accent", + mode: mode, + label: context.funcName, + isStretchy: false, + isShifty: true, + base: base + }; + }, + htmlBuilder: htmlBuilder$a, + mathmlBuilder: mathmlBuilder$9 +}); + +// Horizontal overlap functions +defineFunction({ + type: "accentUnder", + names: ["\\underleftarrow", "\\underrightarrow", "\\underleftrightarrow", "\\undergroup", "\\underlinesegment", "\\utilde"], + props: { + numArgs: 1 + }, + handler: (_ref, args) => { + var { + parser, + funcName + } = _ref; + var base = args[0]; + return { + type: "accentUnder", + mode: parser.mode, + label: funcName, + base: base + }; + }, + htmlBuilder: (group, options) => { + // Treat under accents much like underlines. + var innerGroup = buildGroup$1(group.base, options); + var accentBody = stretchy.svgSpan(group, options); + var kern = group.label === "\\utilde" ? 0.12 : 0; // Generate the vlist, with the appropriate kerns + + var vlist = buildCommon.makeVList({ + positionType: "top", + positionData: innerGroup.height, + children: [{ + type: "elem", + elem: accentBody, + wrapperClasses: ["svg-align"] + }, { + type: "kern", + size: kern + }, { + type: "elem", + elem: innerGroup + }] + }, options); + return buildCommon.makeSpan(["mord", "accentunder"], [vlist], options); + }, + mathmlBuilder: (group, options) => { + var accentNode = stretchy.mathMLnode(group.label); + var node = new mathMLTree.MathNode("munder", [buildGroup(group.base, options), accentNode]); + node.setAttribute("accentunder", "true"); + return node; + } +}); + +// Helper function +var paddedNode = group => { + var node = new mathMLTree.MathNode("mpadded", group ? [group] : []); + node.setAttribute("width", "+0.6em"); + node.setAttribute("lspace", "0.3em"); + return node; +}; // Stretchy arrows with an optional argument + + +defineFunction({ + type: "xArrow", + names: ["\\xleftarrow", "\\xrightarrow", "\\xLeftarrow", "\\xRightarrow", "\\xleftrightarrow", "\\xLeftrightarrow", "\\xhookleftarrow", "\\xhookrightarrow", "\\xmapsto", "\\xrightharpoondown", "\\xrightharpoonup", "\\xleftharpoondown", "\\xleftharpoonup", "\\xrightleftharpoons", "\\xleftrightharpoons", "\\xlongequal", "\\xtwoheadrightarrow", "\\xtwoheadleftarrow", "\\xtofrom", // The next 3 functions are here to support the mhchem extension. + // Direct use of these functions is discouraged and may break someday. + "\\xrightleftarrows", "\\xrightequilibrium", "\\xleftequilibrium", // The next 3 functions are here only to support the {CD} environment. + "\\\\cdrightarrow", "\\\\cdleftarrow", "\\\\cdlongequal"], + props: { + numArgs: 1, + numOptionalArgs: 1 + }, + + handler(_ref, args, optArgs) { + var { + parser, + funcName + } = _ref; + return { + type: "xArrow", + mode: parser.mode, + label: funcName, + body: args[0], + below: optArgs[0] + }; + }, + + // Flow is unable to correctly infer the type of `group`, even though it's + // unambiguously determined from the passed-in `type` above. + htmlBuilder(group, options) { + var style = options.style; // Build the argument groups in the appropriate style. + // Ref: amsmath.dtx: \hbox{$\scriptstyle\mkern#3mu{#6}\mkern#4mu$}% + // Some groups can return document fragments. Handle those by wrapping + // them in a span. + + var newOptions = options.havingStyle(style.sup()); + var upperGroup = buildCommon.wrapFragment(buildGroup$1(group.body, newOptions, options), options); + var arrowPrefix = group.label.slice(0, 2) === "\\x" ? "x" : "cd"; + upperGroup.classes.push(arrowPrefix + "-arrow-pad"); + var lowerGroup; + + if (group.below) { + // Build the lower group + newOptions = options.havingStyle(style.sub()); + lowerGroup = buildCommon.wrapFragment(buildGroup$1(group.below, newOptions, options), options); + lowerGroup.classes.push(arrowPrefix + "-arrow-pad"); + } + + var arrowBody = stretchy.svgSpan(group, options); // Re shift: Note that stretchy.svgSpan returned arrowBody.depth = 0. + // The point we want on the math axis is at 0.5 * arrowBody.height. + + var arrowShift = -options.fontMetrics().axisHeight + 0.5 * arrowBody.height; // 2 mu kern. Ref: amsmath.dtx: #7\if0#2\else\mkern#2mu\fi + + var upperShift = -options.fontMetrics().axisHeight - 0.5 * arrowBody.height - 0.111; // 0.111 em = 2 mu + + if (upperGroup.depth > 0.25 || group.label === "\\xleftequilibrium") { + upperShift -= upperGroup.depth; // shift up if depth encroaches + } // Generate the vlist + + + var vlist; + + if (lowerGroup) { + var lowerShift = -options.fontMetrics().axisHeight + lowerGroup.height + 0.5 * arrowBody.height + 0.111; + vlist = buildCommon.makeVList({ + positionType: "individualShift", + children: [{ + type: "elem", + elem: upperGroup, + shift: upperShift + }, { + type: "elem", + elem: arrowBody, + shift: arrowShift + }, { + type: "elem", + elem: lowerGroup, + shift: lowerShift + }] + }, options); + } else { + vlist = buildCommon.makeVList({ + positionType: "individualShift", + children: [{ + type: "elem", + elem: upperGroup, + shift: upperShift + }, { + type: "elem", + elem: arrowBody, + shift: arrowShift + }] + }, options); + } // $FlowFixMe: Replace this with passing "svg-align" into makeVList. + + + vlist.children[0].children[0].children[1].classes.push("svg-align"); + return buildCommon.makeSpan(["mrel", "x-arrow"], [vlist], options); + }, + + mathmlBuilder(group, options) { + var arrowNode = stretchy.mathMLnode(group.label); + arrowNode.setAttribute("minsize", group.label.charAt(0) === "x" ? "1.75em" : "3.0em"); + var node; + + if (group.body) { + var upperNode = paddedNode(buildGroup(group.body, options)); + + if (group.below) { + var lowerNode = paddedNode(buildGroup(group.below, options)); + node = new mathMLTree.MathNode("munderover", [arrowNode, lowerNode, upperNode]); + } else { + node = new mathMLTree.MathNode("mover", [arrowNode, upperNode]); + } + } else if (group.below) { + var _lowerNode = paddedNode(buildGroup(group.below, options)); + + node = new mathMLTree.MathNode("munder", [arrowNode, _lowerNode]); + } else { + // This should never happen. + // Parser.js throws an error if there is no argument. + node = paddedNode(); + node = new mathMLTree.MathNode("mover", [arrowNode, node]); + } + + return node; + } + +}); + +var makeSpan = buildCommon.makeSpan; + +function htmlBuilder$9(group, options) { + var elements = buildExpression$1(group.body, options, true); + return makeSpan([group.mclass], elements, options); +} + +function mathmlBuilder$8(group, options) { + var node; + var inner = buildExpression(group.body, options); + + if (group.mclass === "minner") { + node = new mathMLTree.MathNode("mpadded", inner); + } else if (group.mclass === "mord") { + if (group.isCharacterBox) { + node = inner[0]; + node.type = "mi"; + } else { + node = new mathMLTree.MathNode("mi", inner); + } + } else { + if (group.isCharacterBox) { + node = inner[0]; + node.type = "mo"; + } else { + node = new mathMLTree.MathNode("mo", inner); + } // Set spacing based on what is the most likely adjacent atom type. + // See TeXbook p170. + + + if (group.mclass === "mbin") { + node.attributes.lspace = "0.22em"; // medium space + + node.attributes.rspace = "0.22em"; + } else if (group.mclass === "mpunct") { + node.attributes.lspace = "0em"; + node.attributes.rspace = "0.17em"; // thinspace + } else if (group.mclass === "mopen" || group.mclass === "mclose") { + node.attributes.lspace = "0em"; + node.attributes.rspace = "0em"; + } else if (group.mclass === "minner") { + node.attributes.lspace = "0.0556em"; // 1 mu is the most likely option + + node.attributes.width = "+0.1111em"; + } // MathML default space is 5/18 em, so needs no action. + // Ref: https://developer.mozilla.org/en-US/docs/Web/MathML/Element/mo + + } + + return node; +} // Math class commands except \mathop + + +defineFunction({ + type: "mclass", + names: ["\\mathord", "\\mathbin", "\\mathrel", "\\mathopen", "\\mathclose", "\\mathpunct", "\\mathinner"], + props: { + numArgs: 1, + primitive: true + }, + + handler(_ref, args) { + var { + parser, + funcName + } = _ref; + var body = args[0]; + return { + type: "mclass", + mode: parser.mode, + mclass: "m" + funcName.slice(5), + // TODO(kevinb): don't prefix with 'm' + body: ordargument(body), + isCharacterBox: utils.isCharacterBox(body) + }; + }, + + htmlBuilder: htmlBuilder$9, + mathmlBuilder: mathmlBuilder$8 +}); +var binrelClass = arg => { + // \binrel@ spacing varies with (bin|rel|ord) of the atom in the argument. + // (by rendering separately and with {}s before and after, and measuring + // the change in spacing). We'll do roughly the same by detecting the + // atom type directly. + var atom = arg.type === "ordgroup" && arg.body.length ? arg.body[0] : arg; + + if (atom.type === "atom" && (atom.family === "bin" || atom.family === "rel")) { + return "m" + atom.family; + } else { + return "mord"; + } +}; // \@binrel{x}{y} renders like y but as mbin/mrel/mord if x is mbin/mrel/mord. +// This is equivalent to \binrel@{x}\binrel@@{y} in AMSTeX. + +defineFunction({ + type: "mclass", + names: ["\\@binrel"], + props: { + numArgs: 2 + }, + + handler(_ref2, args) { + var { + parser + } = _ref2; + return { + type: "mclass", + mode: parser.mode, + mclass: binrelClass(args[0]), + body: ordargument(args[1]), + isCharacterBox: utils.isCharacterBox(args[1]) + }; + } + +}); // Build a relation or stacked op by placing one symbol on top of another + +defineFunction({ + type: "mclass", + names: ["\\stackrel", "\\overset", "\\underset"], + props: { + numArgs: 2 + }, + + handler(_ref3, args) { + var { + parser, + funcName + } = _ref3; + var baseArg = args[1]; + var shiftedArg = args[0]; + var mclass; + + if (funcName !== "\\stackrel") { + // LaTeX applies \binrel spacing to \overset and \underset. + mclass = binrelClass(baseArg); + } else { + mclass = "mrel"; // for \stackrel + } + + var baseOp = { + type: "op", + mode: baseArg.mode, + limits: true, + alwaysHandleSupSub: true, + parentIsSupSub: false, + symbol: false, + suppressBaseShift: funcName !== "\\stackrel", + body: ordargument(baseArg) + }; + var supsub = { + type: "supsub", + mode: shiftedArg.mode, + base: baseOp, + sup: funcName === "\\underset" ? null : shiftedArg, + sub: funcName === "\\underset" ? shiftedArg : null + }; + return { + type: "mclass", + mode: parser.mode, + mclass, + body: [supsub], + isCharacterBox: utils.isCharacterBox(supsub) + }; + }, + + htmlBuilder: htmlBuilder$9, + mathmlBuilder: mathmlBuilder$8 +}); + +// \pmb is a simulation of bold font. +// The version of \pmb in ambsy.sty works by typesetting three copies +// with small offsets. We use CSS text-shadow. +// It's a hack. Not as good as a real bold font. Better than nothing. +defineFunction({ + type: "pmb", + names: ["\\pmb"], + props: { + numArgs: 1, + allowedInText: true + }, + + handler(_ref, args) { + var { + parser + } = _ref; + return { + type: "pmb", + mode: parser.mode, + mclass: binrelClass(args[0]), + body: ordargument(args[0]) + }; + }, + + htmlBuilder(group, options) { + var elements = buildExpression$1(group.body, options, true); + var node = buildCommon.makeSpan([group.mclass], elements, options); + node.style.textShadow = "0.02em 0.01em 0.04px"; + return node; + }, + + mathmlBuilder(group, style) { + var inner = buildExpression(group.body, style); // Wrap with an element. + + var node = new mathMLTree.MathNode("mstyle", inner); + node.setAttribute("style", "text-shadow: 0.02em 0.01em 0.04px"); + return node; + } + +}); + +var cdArrowFunctionName = { + ">": "\\\\cdrightarrow", + "<": "\\\\cdleftarrow", + "=": "\\\\cdlongequal", + "A": "\\uparrow", + "V": "\\downarrow", + "|": "\\Vert", + ".": "no arrow" +}; + +var newCell = () => { + // Create an empty cell, to be filled below with parse nodes. + // The parseTree from this module must be constructed like the + // one created by parseArray(), so an empty CD cell must + // be a ParseNode<"styling">. And CD is always displaystyle. + // So these values are fixed and flow can do implicit typing. + return { + type: "styling", + body: [], + mode: "math", + style: "display" + }; +}; + +var isStartOfArrow = node => { + return node.type === "textord" && node.text === "@"; +}; + +var isLabelEnd = (node, endChar) => { + return (node.type === "mathord" || node.type === "atom") && node.text === endChar; +}; + +function cdArrow(arrowChar, labels, parser) { + // Return a parse tree of an arrow and its labels. + // This acts in a way similar to a macro expansion. + var funcName = cdArrowFunctionName[arrowChar]; + + switch (funcName) { + case "\\\\cdrightarrow": + case "\\\\cdleftarrow": + return parser.callFunction(funcName, [labels[0]], [labels[1]]); + + case "\\uparrow": + case "\\downarrow": + { + var leftLabel = parser.callFunction("\\\\cdleft", [labels[0]], []); + var bareArrow = { + type: "atom", + text: funcName, + mode: "math", + family: "rel" + }; + var sizedArrow = parser.callFunction("\\Big", [bareArrow], []); + var rightLabel = parser.callFunction("\\\\cdright", [labels[1]], []); + var arrowGroup = { + type: "ordgroup", + mode: "math", + body: [leftLabel, sizedArrow, rightLabel] + }; + return parser.callFunction("\\\\cdparent", [arrowGroup], []); + } + + case "\\\\cdlongequal": + return parser.callFunction("\\\\cdlongequal", [], []); + + case "\\Vert": + { + var arrow = { + type: "textord", + text: "\\Vert", + mode: "math" + }; + return parser.callFunction("\\Big", [arrow], []); + } + + default: + return { + type: "textord", + text: " ", + mode: "math" + }; + } +} + +function parseCD(parser) { + // Get the array's parse nodes with \\ temporarily mapped to \cr. + var parsedRows = []; + parser.gullet.beginGroup(); + parser.gullet.macros.set("\\cr", "\\\\\\relax"); + parser.gullet.beginGroup(); + + while (true) { + // eslint-disable-line no-constant-condition + // Get the parse nodes for the next row. + parsedRows.push(parser.parseExpression(false, "\\\\")); + parser.gullet.endGroup(); + parser.gullet.beginGroup(); + var next = parser.fetch().text; + + if (next === "&" || next === "\\\\") { + parser.consume(); + } else if (next === "\\end") { + if (parsedRows[parsedRows.length - 1].length === 0) { + parsedRows.pop(); // final row ended in \\ + } + + break; + } else { + throw new ParseError("Expected \\\\ or \\cr or \\end", parser.nextToken); + } + } + + var row = []; + var body = [row]; // Loop thru the parse nodes. Collect them into cells and arrows. + + for (var i = 0; i < parsedRows.length; i++) { + // Start a new row. + var rowNodes = parsedRows[i]; // Create the first cell. + + var cell = newCell(); + + for (var j = 0; j < rowNodes.length; j++) { + if (!isStartOfArrow(rowNodes[j])) { + // If a parseNode is not an arrow, it goes into a cell. + cell.body.push(rowNodes[j]); + } else { + // Parse node j is an "@", the start of an arrow. + // Before starting on the arrow, push the cell into `row`. + row.push(cell); // Now collect parseNodes into an arrow. + // The character after "@" defines the arrow type. + + j += 1; + var arrowChar = assertSymbolNodeType(rowNodes[j]).text; // Create two empty label nodes. We may or may not use them. + + var labels = new Array(2); + labels[0] = { + type: "ordgroup", + mode: "math", + body: [] + }; + labels[1] = { + type: "ordgroup", + mode: "math", + body: [] + }; // Process the arrow. + + if ("=|.".indexOf(arrowChar) > -1) ; else if ("<>AV".indexOf(arrowChar) > -1) { + // Four arrows, `@>>>`, `@<<<`, `@AAA`, and `@VVV`, each take + // two optional labels. E.g. the right-point arrow syntax is + // really: @>{optional label}>{optional label}> + // Collect parseNodes into labels. + for (var labelNum = 0; labelNum < 2; labelNum++) { + var inLabel = true; + + for (var k = j + 1; k < rowNodes.length; k++) { + if (isLabelEnd(rowNodes[k], arrowChar)) { + inLabel = false; + j = k; + break; + } + + if (isStartOfArrow(rowNodes[k])) { + throw new ParseError("Missing a " + arrowChar + " character to complete a CD arrow.", rowNodes[k]); + } + + labels[labelNum].body.push(rowNodes[k]); + } + + if (inLabel) { + // isLabelEnd never returned a true. + throw new ParseError("Missing a " + arrowChar + " character to complete a CD arrow.", rowNodes[j]); + } + } + } else { + throw new ParseError("Expected one of \"<>AV=|.\" after @", rowNodes[j]); + } // Now join the arrow to its labels. + + + var arrow = cdArrow(arrowChar, labels, parser); // Wrap the arrow in ParseNode<"styling">. + // This is done to match parseArray() behavior. + + var wrappedArrow = { + type: "styling", + body: [arrow], + mode: "math", + style: "display" // CD is always displaystyle. + + }; + row.push(wrappedArrow); // In CD's syntax, cells are implicit. That is, everything that + // is not an arrow gets collected into a cell. So create an empty + // cell now. It will collect upcoming parseNodes. + + cell = newCell(); + } + } + + if (i % 2 === 0) { + // Even-numbered rows consist of: cell, arrow, cell, arrow, ... cell + // The last cell is not yet pushed into `row`, so: + row.push(cell); + } else { + // Odd-numbered rows consist of: vert arrow, empty cell, ... vert arrow + // Remove the empty cell that was placed at the beginning of `row`. + row.shift(); + } + + row = []; + body.push(row); + } // End row group + + + parser.gullet.endGroup(); // End array group defining \\ + + parser.gullet.endGroup(); // define column separation. + + var cols = new Array(body[0].length).fill({ + type: "align", + align: "c", + pregap: 0.25, + // CD package sets \enskip between columns. + postgap: 0.25 // So pre and post each get half an \enskip, i.e. 0.25em. + + }); + return { + type: "array", + mode: "math", + body, + arraystretch: 1, + addJot: true, + rowGaps: [null], + cols, + colSeparationType: "CD", + hLinesBeforeRow: new Array(body.length + 1).fill([]) + }; +} // The functions below are not available for general use. +// They are here only for internal use by the {CD} environment in placing labels +// next to vertical arrows. +// We don't need any such functions for horizontal arrows because we can reuse +// the functionality that already exists for extensible arrows. + +defineFunction({ + type: "cdlabel", + names: ["\\\\cdleft", "\\\\cdright"], + props: { + numArgs: 1 + }, + + handler(_ref, args) { + var { + parser, + funcName + } = _ref; + return { + type: "cdlabel", + mode: parser.mode, + side: funcName.slice(4), + label: args[0] + }; + }, + + htmlBuilder(group, options) { + var newOptions = options.havingStyle(options.style.sup()); + var label = buildCommon.wrapFragment(buildGroup$1(group.label, newOptions, options), options); + label.classes.push("cd-label-" + group.side); + label.style.bottom = makeEm(0.8 - label.depth); // Zero out label height & depth, so vertical align of arrow is set + // by the arrow height, not by the label. + + label.height = 0; + label.depth = 0; + return label; + }, + + mathmlBuilder(group, options) { + var label = new mathMLTree.MathNode("mrow", [buildGroup(group.label, options)]); + label = new mathMLTree.MathNode("mpadded", [label]); + label.setAttribute("width", "0"); + + if (group.side === "left") { + label.setAttribute("lspace", "-1width"); + } // We have to guess at vertical alignment. We know the arrow is 1.8em tall, + // But we don't know the height or depth of the label. + + + label.setAttribute("voffset", "0.7em"); + label = new mathMLTree.MathNode("mstyle", [label]); + label.setAttribute("displaystyle", "false"); + label.setAttribute("scriptlevel", "1"); + return label; + } + +}); +defineFunction({ + type: "cdlabelparent", + names: ["\\\\cdparent"], + props: { + numArgs: 1 + }, + + handler(_ref2, args) { + var { + parser + } = _ref2; + return { + type: "cdlabelparent", + mode: parser.mode, + fragment: args[0] + }; + }, + + htmlBuilder(group, options) { + // Wrap the vertical arrow and its labels. + // The parent gets position: relative. The child gets position: absolute. + // So CSS can locate the label correctly. + var parent = buildCommon.wrapFragment(buildGroup$1(group.fragment, options), options); + parent.classes.push("cd-vert-arrow"); + return parent; + }, + + mathmlBuilder(group, options) { + return new mathMLTree.MathNode("mrow", [buildGroup(group.fragment, options)]); + } + +}); + +// {123} and converts into symbol with code 123. It is used by the *macro* +// \char defined in macros.js. + +defineFunction({ + type: "textord", + names: ["\\@char"], + props: { + numArgs: 1, + allowedInText: true + }, + + handler(_ref, args) { + var { + parser + } = _ref; + var arg = assertNodeType(args[0], "ordgroup"); + var group = arg.body; + var number = ""; + + for (var i = 0; i < group.length; i++) { + var node = assertNodeType(group[i], "textord"); + number += node.text; + } + + var code = parseInt(number); + var text; + + if (isNaN(code)) { + throw new ParseError("\\@char has non-numeric argument " + number); // If we drop IE support, the following code could be replaced with + // text = String.fromCodePoint(code) + } else if (code < 0 || code >= 0x10ffff) { + throw new ParseError("\\@char with invalid code point " + number); + } else if (code <= 0xffff) { + text = String.fromCharCode(code); + } else { + // Astral code point; split into surrogate halves + code -= 0x10000; + text = String.fromCharCode((code >> 10) + 0xd800, (code & 0x3ff) + 0xdc00); + } + + return { + type: "textord", + mode: parser.mode, + text: text + }; + } + +}); + +var htmlBuilder$8 = (group, options) => { + var elements = buildExpression$1(group.body, options.withColor(group.color), false); // \color isn't supposed to affect the type of the elements it contains. + // To accomplish this, we wrap the results in a fragment, so the inner + // elements will be able to directly interact with their neighbors. For + // example, `\color{red}{2 +} 3` has the same spacing as `2 + 3` + + return buildCommon.makeFragment(elements); +}; + +var mathmlBuilder$7 = (group, options) => { + var inner = buildExpression(group.body, options.withColor(group.color)); + var node = new mathMLTree.MathNode("mstyle", inner); + node.setAttribute("mathcolor", group.color); + return node; +}; + +defineFunction({ + type: "color", + names: ["\\textcolor"], + props: { + numArgs: 2, + allowedInText: true, + argTypes: ["color", "original"] + }, + + handler(_ref, args) { + var { + parser + } = _ref; + var color = assertNodeType(args[0], "color-token").color; + var body = args[1]; + return { + type: "color", + mode: parser.mode, + color, + body: ordargument(body) + }; + }, + + htmlBuilder: htmlBuilder$8, + mathmlBuilder: mathmlBuilder$7 +}); +defineFunction({ + type: "color", + names: ["\\color"], + props: { + numArgs: 1, + allowedInText: true, + argTypes: ["color"] + }, + + handler(_ref2, args) { + var { + parser, + breakOnTokenText + } = _ref2; + var color = assertNodeType(args[0], "color-token").color; // Set macro \current@color in current namespace to store the current + // color, mimicking the behavior of color.sty. + // This is currently used just to correctly color a \right + // that follows a \color command. + + parser.gullet.macros.set("\\current@color", color); // Parse out the implicit body that should be colored. + + var body = parser.parseExpression(true, breakOnTokenText); + return { + type: "color", + mode: parser.mode, + color, + body + }; + }, + + htmlBuilder: htmlBuilder$8, + mathmlBuilder: mathmlBuilder$7 +}); + +// Row breaks within tabular environments, and line breaks at top level + +defineFunction({ + type: "cr", + names: ["\\\\"], + props: { + numArgs: 0, + numOptionalArgs: 0, + allowedInText: true + }, + + handler(_ref, args, optArgs) { + var { + parser + } = _ref; + var size = parser.gullet.future().text === "[" ? parser.parseSizeGroup(true) : null; + var newLine = !parser.settings.displayMode || !parser.settings.useStrictBehavior("newLineInDisplayMode", "In LaTeX, \\\\ or \\newline " + "does nothing in display mode"); + return { + type: "cr", + mode: parser.mode, + newLine, + size: size && assertNodeType(size, "size").value + }; + }, + + // The following builders are called only at the top level, + // not within tabular/array environments. + htmlBuilder(group, options) { + var span = buildCommon.makeSpan(["mspace"], [], options); + + if (group.newLine) { + span.classes.push("newline"); + + if (group.size) { + span.style.marginTop = makeEm(calculateSize(group.size, options)); + } + } + + return span; + }, + + mathmlBuilder(group, options) { + var node = new mathMLTree.MathNode("mspace"); + + if (group.newLine) { + node.setAttribute("linebreak", "newline"); + + if (group.size) { + node.setAttribute("height", makeEm(calculateSize(group.size, options))); + } + } + + return node; + } + +}); + +var globalMap = { + "\\global": "\\global", + "\\long": "\\\\globallong", + "\\\\globallong": "\\\\globallong", + "\\def": "\\gdef", + "\\gdef": "\\gdef", + "\\edef": "\\xdef", + "\\xdef": "\\xdef", + "\\let": "\\\\globallet", + "\\futurelet": "\\\\globalfuture" +}; + +var checkControlSequence = tok => { + var name = tok.text; + + if (/^(?:[\\{}$&#^_]|EOF)$/.test(name)) { + throw new ParseError("Expected a control sequence", tok); + } + + return name; +}; + +var getRHS = parser => { + var tok = parser.gullet.popToken(); + + if (tok.text === "=") { + // consume optional equals + tok = parser.gullet.popToken(); + + if (tok.text === " ") { + // consume one optional space + tok = parser.gullet.popToken(); + } + } + + return tok; +}; + +var letCommand = (parser, name, tok, global) => { + var macro = parser.gullet.macros.get(tok.text); + + if (macro == null) { + // don't expand it later even if a macro with the same name is defined + // e.g., \let\foo=\frac \def\frac{\relax} \frac12 + tok.noexpand = true; + macro = { + tokens: [tok], + numArgs: 0, + // reproduce the same behavior in expansion + unexpandable: !parser.gullet.isExpandable(tok.text) + }; + } + + parser.gullet.macros.set(name, macro, global); +}; // -> | +// -> |\global +// -> | +// -> \global|\long|\outer + + +defineFunction({ + type: "internal", + names: ["\\global", "\\long", "\\\\globallong" // can’t be entered directly + ], + props: { + numArgs: 0, + allowedInText: true + }, + + handler(_ref) { + var { + parser, + funcName + } = _ref; + parser.consumeSpaces(); + var token = parser.fetch(); + + if (globalMap[token.text]) { + // KaTeX doesn't have \par, so ignore \long + if (funcName === "\\global" || funcName === "\\\\globallong") { + token.text = globalMap[token.text]; + } + + return assertNodeType(parser.parseFunction(), "internal"); + } + + throw new ParseError("Invalid token after macro prefix", token); + } + +}); // Basic support for macro definitions: \def, \gdef, \edef, \xdef +// -> +// -> \def|\gdef|\edef|\xdef +// -> + +defineFunction({ + type: "internal", + names: ["\\def", "\\gdef", "\\edef", "\\xdef"], + props: { + numArgs: 0, + allowedInText: true, + primitive: true + }, + + handler(_ref2) { + var { + parser, + funcName + } = _ref2; + var tok = parser.gullet.popToken(); + var name = tok.text; + + if (/^(?:[\\{}$&#^_]|EOF)$/.test(name)) { + throw new ParseError("Expected a control sequence", tok); + } + + var numArgs = 0; + var insert; + var delimiters = [[]]; // contains no braces + + while (parser.gullet.future().text !== "{") { + tok = parser.gullet.popToken(); + + if (tok.text === "#") { + // If the very last character of the is #, so that + // this # is immediately followed by {, TeX will behave as if the { + // had been inserted at the right end of both the parameter text + // and the replacement text. + if (parser.gullet.future().text === "{") { + insert = parser.gullet.future(); + delimiters[numArgs].push("{"); + break; + } // A parameter, the first appearance of # must be followed by 1, + // the next by 2, and so on; up to nine #’s are allowed + + + tok = parser.gullet.popToken(); + + if (!/^[1-9]$/.test(tok.text)) { + throw new ParseError("Invalid argument number \"" + tok.text + "\""); + } + + if (parseInt(tok.text) !== numArgs + 1) { + throw new ParseError("Argument number \"" + tok.text + "\" out of order"); + } + + numArgs++; + delimiters.push([]); + } else if (tok.text === "EOF") { + throw new ParseError("Expected a macro definition"); + } else { + delimiters[numArgs].push(tok.text); + } + } // replacement text, enclosed in '{' and '}' and properly nested + + + var { + tokens + } = parser.gullet.consumeArg(); + + if (insert) { + tokens.unshift(insert); + } + + if (funcName === "\\edef" || funcName === "\\xdef") { + tokens = parser.gullet.expandTokens(tokens); + tokens.reverse(); // to fit in with stack order + } // Final arg is the expansion of the macro + + + parser.gullet.macros.set(name, { + tokens, + numArgs, + delimiters + }, funcName === globalMap[funcName]); + return { + type: "internal", + mode: parser.mode + }; + } + +}); // -> +// -> \futurelet +// | \let +// -> |= + +defineFunction({ + type: "internal", + names: ["\\let", "\\\\globallet" // can’t be entered directly + ], + props: { + numArgs: 0, + allowedInText: true, + primitive: true + }, + + handler(_ref3) { + var { + parser, + funcName + } = _ref3; + var name = checkControlSequence(parser.gullet.popToken()); + parser.gullet.consumeSpaces(); + var tok = getRHS(parser); + letCommand(parser, name, tok, funcName === "\\\\globallet"); + return { + type: "internal", + mode: parser.mode + }; + } + +}); // ref: https://www.tug.org/TUGboat/tb09-3/tb22bechtolsheim.pdf + +defineFunction({ + type: "internal", + names: ["\\futurelet", "\\\\globalfuture" // can’t be entered directly + ], + props: { + numArgs: 0, + allowedInText: true, + primitive: true + }, + + handler(_ref4) { + var { + parser, + funcName + } = _ref4; + var name = checkControlSequence(parser.gullet.popToken()); + var middle = parser.gullet.popToken(); + var tok = parser.gullet.popToken(); + letCommand(parser, name, tok, funcName === "\\\\globalfuture"); + parser.gullet.pushToken(tok); + parser.gullet.pushToken(middle); + return { + type: "internal", + mode: parser.mode + }; + } + +}); + +/** + * This file deals with creating delimiters of various sizes. The TeXbook + * discusses these routines on page 441-442, in the "Another subroutine sets box + * x to a specified variable delimiter" paragraph. + * + * There are three main routines here. `makeSmallDelim` makes a delimiter in the + * normal font, but in either text, script, or scriptscript style. + * `makeLargeDelim` makes a delimiter in textstyle, but in one of the Size1, + * Size2, Size3, or Size4 fonts. `makeStackedDelim` makes a delimiter out of + * smaller pieces that are stacked on top of one another. + * + * The functions take a parameter `center`, which determines if the delimiter + * should be centered around the axis. + * + * Then, there are three exposed functions. `sizedDelim` makes a delimiter in + * one of the given sizes. This is used for things like `\bigl`. + * `customSizedDelim` makes a delimiter with a given total height+depth. It is + * called in places like `\sqrt`. `leftRightDelim` makes an appropriate + * delimiter which surrounds an expression of a given height an depth. It is + * used in `\left` and `\right`. + */ + +/** + * Get the metrics for a given symbol and font, after transformation (i.e. + * after following replacement from symbols.js) + */ +var getMetrics = function getMetrics(symbol, font, mode) { + var replace = symbols.math[symbol] && symbols.math[symbol].replace; + var metrics = getCharacterMetrics(replace || symbol, font, mode); + + if (!metrics) { + throw new Error("Unsupported symbol " + symbol + " and font size " + font + "."); + } + + return metrics; +}; +/** + * Puts a delimiter span in a given style, and adds appropriate height, depth, + * and maxFontSizes. + */ + + +var styleWrap = function styleWrap(delim, toStyle, options, classes) { + var newOptions = options.havingBaseStyle(toStyle); + var span = buildCommon.makeSpan(classes.concat(newOptions.sizingClasses(options)), [delim], options); + var delimSizeMultiplier = newOptions.sizeMultiplier / options.sizeMultiplier; + span.height *= delimSizeMultiplier; + span.depth *= delimSizeMultiplier; + span.maxFontSize = newOptions.sizeMultiplier; + return span; +}; + +var centerSpan = function centerSpan(span, options, style) { + var newOptions = options.havingBaseStyle(style); + var shift = (1 - options.sizeMultiplier / newOptions.sizeMultiplier) * options.fontMetrics().axisHeight; + span.classes.push("delimcenter"); + span.style.top = makeEm(shift); + span.height -= shift; + span.depth += shift; +}; +/** + * Makes a small delimiter. This is a delimiter that comes in the Main-Regular + * font, but is restyled to either be in textstyle, scriptstyle, or + * scriptscriptstyle. + */ + + +var makeSmallDelim = function makeSmallDelim(delim, style, center, options, mode, classes) { + var text = buildCommon.makeSymbol(delim, "Main-Regular", mode, options); + var span = styleWrap(text, style, options, classes); + + if (center) { + centerSpan(span, options, style); + } + + return span; +}; +/** + * Builds a symbol in the given font size (note size is an integer) + */ + + +var mathrmSize = function mathrmSize(value, size, mode, options) { + return buildCommon.makeSymbol(value, "Size" + size + "-Regular", mode, options); +}; +/** + * Makes a large delimiter. This is a delimiter that comes in the Size1, Size2, + * Size3, or Size4 fonts. It is always rendered in textstyle. + */ + + +var makeLargeDelim = function makeLargeDelim(delim, size, center, options, mode, classes) { + var inner = mathrmSize(delim, size, mode, options); + var span = styleWrap(buildCommon.makeSpan(["delimsizing", "size" + size], [inner], options), Style$1.TEXT, options, classes); + + if (center) { + centerSpan(span, options, Style$1.TEXT); + } + + return span; +}; +/** + * Make a span from a font glyph with the given offset and in the given font. + * This is used in makeStackedDelim to make the stacking pieces for the delimiter. + */ + + +var makeGlyphSpan = function makeGlyphSpan(symbol, font, mode) { + var sizeClass; // Apply the correct CSS class to choose the right font. + + if (font === "Size1-Regular") { + sizeClass = "delim-size1"; + } else + /* if (font === "Size4-Regular") */ + { + sizeClass = "delim-size4"; + } + + var corner = buildCommon.makeSpan(["delimsizinginner", sizeClass], [buildCommon.makeSpan([], [buildCommon.makeSymbol(symbol, font, mode)])]); // Since this will be passed into `makeVList` in the end, wrap the element + // in the appropriate tag that VList uses. + + return { + type: "elem", + elem: corner + }; +}; + +var makeInner = function makeInner(ch, height, options) { + // Create a span with inline SVG for the inner part of a tall stacked delimiter. + var width = fontMetricsData['Size4-Regular'][ch.charCodeAt(0)] ? fontMetricsData['Size4-Regular'][ch.charCodeAt(0)][4] : fontMetricsData['Size1-Regular'][ch.charCodeAt(0)][4]; + var path = new PathNode("inner", innerPath(ch, Math.round(1000 * height))); + var svgNode = new SvgNode([path], { + "width": makeEm(width), + "height": makeEm(height), + // Override CSS rule `.katex svg { width: 100% }` + "style": "width:" + makeEm(width), + "viewBox": "0 0 " + 1000 * width + " " + Math.round(1000 * height), + "preserveAspectRatio": "xMinYMin" + }); + var span = buildCommon.makeSvgSpan([], [svgNode], options); + span.height = height; + span.style.height = makeEm(height); + span.style.width = makeEm(width); + return { + type: "elem", + elem: span + }; +}; // Helpers for makeStackedDelim + + +var lapInEms = 0.008; +var lap = { + type: "kern", + size: -1 * lapInEms +}; +var verts = ["|", "\\lvert", "\\rvert", "\\vert"]; +var doubleVerts = ["\\|", "\\lVert", "\\rVert", "\\Vert"]; +/** + * Make a stacked delimiter out of a given delimiter, with the total height at + * least `heightTotal`. This routine is mentioned on page 442 of the TeXbook. + */ + +var makeStackedDelim = function makeStackedDelim(delim, heightTotal, center, options, mode, classes) { + // There are four parts, the top, an optional middle, a repeated part, and a + // bottom. + var top; + var middle; + var repeat; + var bottom; + var svgLabel = ""; + var viewBoxWidth = 0; + top = repeat = bottom = delim; + middle = null; // Also keep track of what font the delimiters are in + + var font = "Size1-Regular"; // We set the parts and font based on the symbol. Note that we use + // '\u23d0' instead of '|' and '\u2016' instead of '\\|' for the + // repeats of the arrows + + if (delim === "\\uparrow") { + repeat = bottom = "\u23d0"; + } else if (delim === "\\Uparrow") { + repeat = bottom = "\u2016"; + } else if (delim === "\\downarrow") { + top = repeat = "\u23d0"; + } else if (delim === "\\Downarrow") { + top = repeat = "\u2016"; + } else if (delim === "\\updownarrow") { + top = "\\uparrow"; + repeat = "\u23d0"; + bottom = "\\downarrow"; + } else if (delim === "\\Updownarrow") { + top = "\\Uparrow"; + repeat = "\u2016"; + bottom = "\\Downarrow"; + } else if (utils.contains(verts, delim)) { + repeat = "\u2223"; + svgLabel = "vert"; + viewBoxWidth = 333; + } else if (utils.contains(doubleVerts, delim)) { + repeat = "\u2225"; + svgLabel = "doublevert"; + viewBoxWidth = 556; + } else if (delim === "[" || delim === "\\lbrack") { + top = "\u23a1"; + repeat = "\u23a2"; + bottom = "\u23a3"; + font = "Size4-Regular"; + svgLabel = "lbrack"; + viewBoxWidth = 667; + } else if (delim === "]" || delim === "\\rbrack") { + top = "\u23a4"; + repeat = "\u23a5"; + bottom = "\u23a6"; + font = "Size4-Regular"; + svgLabel = "rbrack"; + viewBoxWidth = 667; + } else if (delim === "\\lfloor" || delim === "\u230a") { + repeat = top = "\u23a2"; + bottom = "\u23a3"; + font = "Size4-Regular"; + svgLabel = "lfloor"; + viewBoxWidth = 667; + } else if (delim === "\\lceil" || delim === "\u2308") { + top = "\u23a1"; + repeat = bottom = "\u23a2"; + font = "Size4-Regular"; + svgLabel = "lceil"; + viewBoxWidth = 667; + } else if (delim === "\\rfloor" || delim === "\u230b") { + repeat = top = "\u23a5"; + bottom = "\u23a6"; + font = "Size4-Regular"; + svgLabel = "rfloor"; + viewBoxWidth = 667; + } else if (delim === "\\rceil" || delim === "\u2309") { + top = "\u23a4"; + repeat = bottom = "\u23a5"; + font = "Size4-Regular"; + svgLabel = "rceil"; + viewBoxWidth = 667; + } else if (delim === "(" || delim === "\\lparen") { + top = "\u239b"; + repeat = "\u239c"; + bottom = "\u239d"; + font = "Size4-Regular"; + svgLabel = "lparen"; + viewBoxWidth = 875; + } else if (delim === ")" || delim === "\\rparen") { + top = "\u239e"; + repeat = "\u239f"; + bottom = "\u23a0"; + font = "Size4-Regular"; + svgLabel = "rparen"; + viewBoxWidth = 875; + } else if (delim === "\\{" || delim === "\\lbrace") { + top = "\u23a7"; + middle = "\u23a8"; + bottom = "\u23a9"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\}" || delim === "\\rbrace") { + top = "\u23ab"; + middle = "\u23ac"; + bottom = "\u23ad"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\lgroup" || delim === "\u27ee") { + top = "\u23a7"; + bottom = "\u23a9"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\rgroup" || delim === "\u27ef") { + top = "\u23ab"; + bottom = "\u23ad"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\lmoustache" || delim === "\u23b0") { + top = "\u23a7"; + bottom = "\u23ad"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\rmoustache" || delim === "\u23b1") { + top = "\u23ab"; + bottom = "\u23a9"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } // Get the metrics of the four sections + + + var topMetrics = getMetrics(top, font, mode); + var topHeightTotal = topMetrics.height + topMetrics.depth; + var repeatMetrics = getMetrics(repeat, font, mode); + var repeatHeightTotal = repeatMetrics.height + repeatMetrics.depth; + var bottomMetrics = getMetrics(bottom, font, mode); + var bottomHeightTotal = bottomMetrics.height + bottomMetrics.depth; + var middleHeightTotal = 0; + var middleFactor = 1; + + if (middle !== null) { + var middleMetrics = getMetrics(middle, font, mode); + middleHeightTotal = middleMetrics.height + middleMetrics.depth; + middleFactor = 2; // repeat symmetrically above and below middle + } // Calculate the minimal height that the delimiter can have. + // It is at least the size of the top, bottom, and optional middle combined. + + + var minHeight = topHeightTotal + bottomHeightTotal + middleHeightTotal; // Compute the number of copies of the repeat symbol we will need + + var repeatCount = Math.max(0, Math.ceil((heightTotal - minHeight) / (middleFactor * repeatHeightTotal))); // Compute the total height of the delimiter including all the symbols + + var realHeightTotal = minHeight + repeatCount * middleFactor * repeatHeightTotal; // The center of the delimiter is placed at the center of the axis. Note + // that in this context, "center" means that the delimiter should be + // centered around the axis in the current style, while normally it is + // centered around the axis in textstyle. + + var axisHeight = options.fontMetrics().axisHeight; + + if (center) { + axisHeight *= options.sizeMultiplier; + } // Calculate the depth + + + var depth = realHeightTotal / 2 - axisHeight; // Now, we start building the pieces that will go into the vlist + // Keep a list of the pieces of the stacked delimiter + + var stack = []; + + if (svgLabel.length > 0) { + // Instead of stacking glyphs, create a single SVG. + // This evades browser problems with imprecise positioning of spans. + var midHeight = realHeightTotal - topHeightTotal - bottomHeightTotal; + var viewBoxHeight = Math.round(realHeightTotal * 1000); + var pathStr = tallDelim(svgLabel, Math.round(midHeight * 1000)); + var path = new PathNode(svgLabel, pathStr); + var width = (viewBoxWidth / 1000).toFixed(3) + "em"; + var height = (viewBoxHeight / 1000).toFixed(3) + "em"; + var svg = new SvgNode([path], { + "width": width, + "height": height, + "viewBox": "0 0 " + viewBoxWidth + " " + viewBoxHeight + }); + var wrapper = buildCommon.makeSvgSpan([], [svg], options); + wrapper.height = viewBoxHeight / 1000; + wrapper.style.width = width; + wrapper.style.height = height; + stack.push({ + type: "elem", + elem: wrapper + }); + } else { + // Stack glyphs + // Start by adding the bottom symbol + stack.push(makeGlyphSpan(bottom, font, mode)); + stack.push(lap); // overlap + + if (middle === null) { + // The middle section will be an SVG. Make it an extra 0.016em tall. + // We'll overlap by 0.008em at top and bottom. + var innerHeight = realHeightTotal - topHeightTotal - bottomHeightTotal + 2 * lapInEms; + stack.push(makeInner(repeat, innerHeight, options)); + } else { + // When there is a middle bit, we need the middle part and two repeated + // sections + var _innerHeight = (realHeightTotal - topHeightTotal - bottomHeightTotal - middleHeightTotal) / 2 + 2 * lapInEms; + + stack.push(makeInner(repeat, _innerHeight, options)); // Now insert the middle of the brace. + + stack.push(lap); + stack.push(makeGlyphSpan(middle, font, mode)); + stack.push(lap); + stack.push(makeInner(repeat, _innerHeight, options)); + } // Add the top symbol + + + stack.push(lap); + stack.push(makeGlyphSpan(top, font, mode)); + } // Finally, build the vlist + + + var newOptions = options.havingBaseStyle(Style$1.TEXT); + var inner = buildCommon.makeVList({ + positionType: "bottom", + positionData: depth, + children: stack + }, newOptions); + return styleWrap(buildCommon.makeSpan(["delimsizing", "mult"], [inner], newOptions), Style$1.TEXT, options, classes); +}; // All surds have 0.08em padding above the vinculum inside the SVG. +// That keeps browser span height rounding error from pinching the line. + + +var vbPad = 80; // padding above the surd, measured inside the viewBox. + +var emPad = 0.08; // padding, in ems, measured in the document. + +var sqrtSvg = function sqrtSvg(sqrtName, height, viewBoxHeight, extraVinculum, options) { + var path = sqrtPath(sqrtName, extraVinculum, viewBoxHeight); + var pathNode = new PathNode(sqrtName, path); + var svg = new SvgNode([pathNode], { + // Note: 1000:1 ratio of viewBox to document em width. + "width": "400em", + "height": makeEm(height), + "viewBox": "0 0 400000 " + viewBoxHeight, + "preserveAspectRatio": "xMinYMin slice" + }); + return buildCommon.makeSvgSpan(["hide-tail"], [svg], options); +}; +/** + * Make a sqrt image of the given height, + */ + + +var makeSqrtImage = function makeSqrtImage(height, options) { + // Define a newOptions that removes the effect of size changes such as \Huge. + // We don't pick different a height surd for \Huge. For it, we scale up. + var newOptions = options.havingBaseSizing(); // Pick the desired surd glyph from a sequence of surds. + + var delim = traverseSequence("\\surd", height * newOptions.sizeMultiplier, stackLargeDelimiterSequence, newOptions); + var sizeMultiplier = newOptions.sizeMultiplier; // default + // The standard sqrt SVGs each have a 0.04em thick vinculum. + // If Settings.minRuleThickness is larger than that, we add extraVinculum. + + var extraVinculum = Math.max(0, options.minRuleThickness - options.fontMetrics().sqrtRuleThickness); // Create a span containing an SVG image of a sqrt symbol. + + var span; + var spanHeight = 0; + var texHeight = 0; + var viewBoxHeight = 0; + var advanceWidth; // We create viewBoxes with 80 units of "padding" above each surd. + // Then browser rounding error on the parent span height will not + // encroach on the ink of the vinculum. But that padding is not + // included in the TeX-like `height` used for calculation of + // vertical alignment. So texHeight = span.height < span.style.height. + + if (delim.type === "small") { + // Get an SVG that is derived from glyph U+221A in font KaTeX-Main. + // 1000 unit normal glyph height. + viewBoxHeight = 1000 + 1000 * extraVinculum + vbPad; + + if (height < 1.0) { + sizeMultiplier = 1.0; // mimic a \textfont radical + } else if (height < 1.4) { + sizeMultiplier = 0.7; // mimic a \scriptfont radical + } + + spanHeight = (1.0 + extraVinculum + emPad) / sizeMultiplier; + texHeight = (1.00 + extraVinculum) / sizeMultiplier; + span = sqrtSvg("sqrtMain", spanHeight, viewBoxHeight, extraVinculum, options); + span.style.minWidth = "0.853em"; + advanceWidth = 0.833 / sizeMultiplier; // from the font. + } else if (delim.type === "large") { + // These SVGs come from fonts: KaTeX_Size1, _Size2, etc. + viewBoxHeight = (1000 + vbPad) * sizeToMaxHeight[delim.size]; + texHeight = (sizeToMaxHeight[delim.size] + extraVinculum) / sizeMultiplier; + spanHeight = (sizeToMaxHeight[delim.size] + extraVinculum + emPad) / sizeMultiplier; + span = sqrtSvg("sqrtSize" + delim.size, spanHeight, viewBoxHeight, extraVinculum, options); + span.style.minWidth = "1.02em"; + advanceWidth = 1.0 / sizeMultiplier; // 1.0 from the font. + } else { + // Tall sqrt. In TeX, this would be stacked using multiple glyphs. + // We'll use a single SVG to accomplish the same thing. + spanHeight = height + extraVinculum + emPad; + texHeight = height + extraVinculum; + viewBoxHeight = Math.floor(1000 * height + extraVinculum) + vbPad; + span = sqrtSvg("sqrtTall", spanHeight, viewBoxHeight, extraVinculum, options); + span.style.minWidth = "0.742em"; + advanceWidth = 1.056; + } + + span.height = texHeight; + span.style.height = makeEm(spanHeight); + return { + span, + advanceWidth, + // Calculate the actual line width. + // This actually should depend on the chosen font -- e.g. \boldmath + // should use the thicker surd symbols from e.g. KaTeX_Main-Bold, and + // have thicker rules. + ruleWidth: (options.fontMetrics().sqrtRuleThickness + extraVinculum) * sizeMultiplier + }; +}; // There are three kinds of delimiters, delimiters that stack when they become +// too large + + +var stackLargeDelimiters = ["(", "\\lparen", ")", "\\rparen", "[", "\\lbrack", "]", "\\rbrack", "\\{", "\\lbrace", "\\}", "\\rbrace", "\\lfloor", "\\rfloor", "\u230a", "\u230b", "\\lceil", "\\rceil", "\u2308", "\u2309", "\\surd"]; // delimiters that always stack + +var stackAlwaysDelimiters = ["\\uparrow", "\\downarrow", "\\updownarrow", "\\Uparrow", "\\Downarrow", "\\Updownarrow", "|", "\\|", "\\vert", "\\Vert", "\\lvert", "\\rvert", "\\lVert", "\\rVert", "\\lgroup", "\\rgroup", "\u27ee", "\u27ef", "\\lmoustache", "\\rmoustache", "\u23b0", "\u23b1"]; // and delimiters that never stack + +var stackNeverDelimiters = ["<", ">", "\\langle", "\\rangle", "/", "\\backslash", "\\lt", "\\gt"]; // Metrics of the different sizes. Found by looking at TeX's output of +// $\bigl| // \Bigl| \biggl| \Biggl| \showlists$ +// Used to create stacked delimiters of appropriate sizes in makeSizedDelim. + +var sizeToMaxHeight = [0, 1.2, 1.8, 2.4, 3.0]; +/** + * Used to create a delimiter of a specific size, where `size` is 1, 2, 3, or 4. + */ + +var makeSizedDelim = function makeSizedDelim(delim, size, options, mode, classes) { + // < and > turn into \langle and \rangle in delimiters + if (delim === "<" || delim === "\\lt" || delim === "\u27e8") { + delim = "\\langle"; + } else if (delim === ">" || delim === "\\gt" || delim === "\u27e9") { + delim = "\\rangle"; + } // Sized delimiters are never centered. + + + if (utils.contains(stackLargeDelimiters, delim) || utils.contains(stackNeverDelimiters, delim)) { + return makeLargeDelim(delim, size, false, options, mode, classes); + } else if (utils.contains(stackAlwaysDelimiters, delim)) { + return makeStackedDelim(delim, sizeToMaxHeight[size], false, options, mode, classes); + } else { + throw new ParseError("Illegal delimiter: '" + delim + "'"); + } +}; +/** + * There are three different sequences of delimiter sizes that the delimiters + * follow depending on the kind of delimiter. This is used when creating custom + * sized delimiters to decide whether to create a small, large, or stacked + * delimiter. + * + * In real TeX, these sequences aren't explicitly defined, but are instead + * defined inside the font metrics. Since there are only three sequences that + * are possible for the delimiters that TeX defines, it is easier to just encode + * them explicitly here. + */ + + +// Delimiters that never stack try small delimiters and large delimiters only +var stackNeverDelimiterSequence = [{ + type: "small", + style: Style$1.SCRIPTSCRIPT +}, { + type: "small", + style: Style$1.SCRIPT +}, { + type: "small", + style: Style$1.TEXT +}, { + type: "large", + size: 1 +}, { + type: "large", + size: 2 +}, { + type: "large", + size: 3 +}, { + type: "large", + size: 4 +}]; // Delimiters that always stack try the small delimiters first, then stack + +var stackAlwaysDelimiterSequence = [{ + type: "small", + style: Style$1.SCRIPTSCRIPT +}, { + type: "small", + style: Style$1.SCRIPT +}, { + type: "small", + style: Style$1.TEXT +}, { + type: "stack" +}]; // Delimiters that stack when large try the small and then large delimiters, and +// stack afterwards + +var stackLargeDelimiterSequence = [{ + type: "small", + style: Style$1.SCRIPTSCRIPT +}, { + type: "small", + style: Style$1.SCRIPT +}, { + type: "small", + style: Style$1.TEXT +}, { + type: "large", + size: 1 +}, { + type: "large", + size: 2 +}, { + type: "large", + size: 3 +}, { + type: "large", + size: 4 +}, { + type: "stack" +}]; +/** + * Get the font used in a delimiter based on what kind of delimiter it is. + * TODO(#963) Use more specific font family return type once that is introduced. + */ + +var delimTypeToFont = function delimTypeToFont(type) { + if (type.type === "small") { + return "Main-Regular"; + } else if (type.type === "large") { + return "Size" + type.size + "-Regular"; + } else if (type.type === "stack") { + return "Size4-Regular"; + } else { + throw new Error("Add support for delim type '" + type.type + "' here."); + } +}; +/** + * Traverse a sequence of types of delimiters to decide what kind of delimiter + * should be used to create a delimiter of the given height+depth. + */ + + +var traverseSequence = function traverseSequence(delim, height, sequence, options) { + // Here, we choose the index we should start at in the sequences. In smaller + // sizes (which correspond to larger numbers in style.size) we start earlier + // in the sequence. Thus, scriptscript starts at index 3-3=0, script starts + // at index 3-2=1, text starts at 3-1=2, and display starts at min(2,3-0)=2 + var start = Math.min(2, 3 - options.style.size); + + for (var i = start; i < sequence.length; i++) { + if (sequence[i].type === "stack") { + // This is always the last delimiter, so we just break the loop now. + break; + } + + var metrics = getMetrics(delim, delimTypeToFont(sequence[i]), "math"); + var heightDepth = metrics.height + metrics.depth; // Small delimiters are scaled down versions of the same font, so we + // account for the style change size. + + if (sequence[i].type === "small") { + var newOptions = options.havingBaseStyle(sequence[i].style); + heightDepth *= newOptions.sizeMultiplier; + } // Check if the delimiter at this size works for the given height. + + + if (heightDepth > height) { + return sequence[i]; + } + } // If we reached the end of the sequence, return the last sequence element. + + + return sequence[sequence.length - 1]; +}; +/** + * Make a delimiter of a given height+depth, with optional centering. Here, we + * traverse the sequences, and create a delimiter that the sequence tells us to. + */ + + +var makeCustomSizedDelim = function makeCustomSizedDelim(delim, height, center, options, mode, classes) { + if (delim === "<" || delim === "\\lt" || delim === "\u27e8") { + delim = "\\langle"; + } else if (delim === ">" || delim === "\\gt" || delim === "\u27e9") { + delim = "\\rangle"; + } // Decide what sequence to use + + + var sequence; + + if (utils.contains(stackNeverDelimiters, delim)) { + sequence = stackNeverDelimiterSequence; + } else if (utils.contains(stackLargeDelimiters, delim)) { + sequence = stackLargeDelimiterSequence; + } else { + sequence = stackAlwaysDelimiterSequence; + } // Look through the sequence + + + var delimType = traverseSequence(delim, height, sequence, options); // Get the delimiter from font glyphs. + // Depending on the sequence element we decided on, call the + // appropriate function. + + if (delimType.type === "small") { + return makeSmallDelim(delim, delimType.style, center, options, mode, classes); + } else if (delimType.type === "large") { + return makeLargeDelim(delim, delimType.size, center, options, mode, classes); + } else + /* if (delimType.type === "stack") */ + { + return makeStackedDelim(delim, height, center, options, mode, classes); + } +}; +/** + * Make a delimiter for use with `\left` and `\right`, given a height and depth + * of an expression that the delimiters surround. + */ + + +var makeLeftRightDelim = function makeLeftRightDelim(delim, height, depth, options, mode, classes) { + // We always center \left/\right delimiters, so the axis is always shifted + var axisHeight = options.fontMetrics().axisHeight * options.sizeMultiplier; // Taken from TeX source, tex.web, function make_left_right + + var delimiterFactor = 901; + var delimiterExtend = 5.0 / options.fontMetrics().ptPerEm; + var maxDistFromAxis = Math.max(height - axisHeight, depth + axisHeight); + var totalHeight = Math.max( // In real TeX, calculations are done using integral values which are + // 65536 per pt, or 655360 per em. So, the division here truncates in + // TeX but doesn't here, producing different results. If we wanted to + // exactly match TeX's calculation, we could do + // Math.floor(655360 * maxDistFromAxis / 500) * + // delimiterFactor / 655360 + // (To see the difference, compare + // x^{x^{\left(\rule{0.1em}{0.68em}\right)}} + // in TeX and KaTeX) + maxDistFromAxis / 500 * delimiterFactor, 2 * maxDistFromAxis - delimiterExtend); // Finally, we defer to `makeCustomSizedDelim` with our calculated total + // height + + return makeCustomSizedDelim(delim, totalHeight, true, options, mode, classes); +}; + +var delimiter = { + sqrtImage: makeSqrtImage, + sizedDelim: makeSizedDelim, + sizeToMaxHeight: sizeToMaxHeight, + customSizedDelim: makeCustomSizedDelim, + leftRightDelim: makeLeftRightDelim +}; + +// Extra data needed for the delimiter handler down below +var delimiterSizes = { + "\\bigl": { + mclass: "mopen", + size: 1 + }, + "\\Bigl": { + mclass: "mopen", + size: 2 + }, + "\\biggl": { + mclass: "mopen", + size: 3 + }, + "\\Biggl": { + mclass: "mopen", + size: 4 + }, + "\\bigr": { + mclass: "mclose", + size: 1 + }, + "\\Bigr": { + mclass: "mclose", + size: 2 + }, + "\\biggr": { + mclass: "mclose", + size: 3 + }, + "\\Biggr": { + mclass: "mclose", + size: 4 + }, + "\\bigm": { + mclass: "mrel", + size: 1 + }, + "\\Bigm": { + mclass: "mrel", + size: 2 + }, + "\\biggm": { + mclass: "mrel", + size: 3 + }, + "\\Biggm": { + mclass: "mrel", + size: 4 + }, + "\\big": { + mclass: "mord", + size: 1 + }, + "\\Big": { + mclass: "mord", + size: 2 + }, + "\\bigg": { + mclass: "mord", + size: 3 + }, + "\\Bigg": { + mclass: "mord", + size: 4 + } +}; +var delimiters = ["(", "\\lparen", ")", "\\rparen", "[", "\\lbrack", "]", "\\rbrack", "\\{", "\\lbrace", "\\}", "\\rbrace", "\\lfloor", "\\rfloor", "\u230a", "\u230b", "\\lceil", "\\rceil", "\u2308", "\u2309", "<", ">", "\\langle", "\u27e8", "\\rangle", "\u27e9", "\\lt", "\\gt", "\\lvert", "\\rvert", "\\lVert", "\\rVert", "\\lgroup", "\\rgroup", "\u27ee", "\u27ef", "\\lmoustache", "\\rmoustache", "\u23b0", "\u23b1", "/", "\\backslash", "|", "\\vert", "\\|", "\\Vert", "\\uparrow", "\\Uparrow", "\\downarrow", "\\Downarrow", "\\updownarrow", "\\Updownarrow", "."]; + +// Delimiter functions +function checkDelimiter(delim, context) { + var symDelim = checkSymbolNodeType(delim); + + if (symDelim && utils.contains(delimiters, symDelim.text)) { + return symDelim; + } else if (symDelim) { + throw new ParseError("Invalid delimiter '" + symDelim.text + "' after '" + context.funcName + "'", delim); + } else { + throw new ParseError("Invalid delimiter type '" + delim.type + "'", delim); + } +} + +defineFunction({ + type: "delimsizing", + names: ["\\bigl", "\\Bigl", "\\biggl", "\\Biggl", "\\bigr", "\\Bigr", "\\biggr", "\\Biggr", "\\bigm", "\\Bigm", "\\biggm", "\\Biggm", "\\big", "\\Big", "\\bigg", "\\Bigg"], + props: { + numArgs: 1, + argTypes: ["primitive"] + }, + handler: (context, args) => { + var delim = checkDelimiter(args[0], context); + return { + type: "delimsizing", + mode: context.parser.mode, + size: delimiterSizes[context.funcName].size, + mclass: delimiterSizes[context.funcName].mclass, + delim: delim.text + }; + }, + htmlBuilder: (group, options) => { + if (group.delim === ".") { + // Empty delimiters still count as elements, even though they don't + // show anything. + return buildCommon.makeSpan([group.mclass]); + } // Use delimiter.sizedDelim to generate the delimiter. + + + return delimiter.sizedDelim(group.delim, group.size, options, group.mode, [group.mclass]); + }, + mathmlBuilder: group => { + var children = []; + + if (group.delim !== ".") { + children.push(makeText(group.delim, group.mode)); + } + + var node = new mathMLTree.MathNode("mo", children); + + if (group.mclass === "mopen" || group.mclass === "mclose") { + // Only some of the delimsizing functions act as fences, and they + // return "mopen" or "mclose" mclass. + node.setAttribute("fence", "true"); + } else { + // Explicitly disable fencing if it's not a fence, to override the + // defaults. + node.setAttribute("fence", "false"); + } + + node.setAttribute("stretchy", "true"); + var size = makeEm(delimiter.sizeToMaxHeight[group.size]); + node.setAttribute("minsize", size); + node.setAttribute("maxsize", size); + return node; + } +}); + +function assertParsed(group) { + if (!group.body) { + throw new Error("Bug: The leftright ParseNode wasn't fully parsed."); + } +} + +defineFunction({ + type: "leftright-right", + names: ["\\right"], + props: { + numArgs: 1, + primitive: true + }, + handler: (context, args) => { + // \left case below triggers parsing of \right in + // `const right = parser.parseFunction();` + // uses this return value. + var color = context.parser.gullet.macros.get("\\current@color"); + + if (color && typeof color !== "string") { + throw new ParseError("\\current@color set to non-string in \\right"); + } + + return { + type: "leftright-right", + mode: context.parser.mode, + delim: checkDelimiter(args[0], context).text, + color // undefined if not set via \color + + }; + } +}); +defineFunction({ + type: "leftright", + names: ["\\left"], + props: { + numArgs: 1, + primitive: true + }, + handler: (context, args) => { + var delim = checkDelimiter(args[0], context); + var parser = context.parser; // Parse out the implicit body + + ++parser.leftrightDepth; // parseExpression stops before '\\right' + + var body = parser.parseExpression(false); + --parser.leftrightDepth; // Check the next token + + parser.expect("\\right", false); + var right = assertNodeType(parser.parseFunction(), "leftright-right"); + return { + type: "leftright", + mode: parser.mode, + body, + left: delim.text, + right: right.delim, + rightColor: right.color + }; + }, + htmlBuilder: (group, options) => { + assertParsed(group); // Build the inner expression + + var inner = buildExpression$1(group.body, options, true, ["mopen", "mclose"]); + var innerHeight = 0; + var innerDepth = 0; + var hadMiddle = false; // Calculate its height and depth + + for (var i = 0; i < inner.length; i++) { + // Property `isMiddle` not defined on `span`. See comment in + // "middle"'s htmlBuilder. + // $FlowFixMe + if (inner[i].isMiddle) { + hadMiddle = true; + } else { + innerHeight = Math.max(inner[i].height, innerHeight); + innerDepth = Math.max(inner[i].depth, innerDepth); + } + } // The size of delimiters is the same, regardless of what style we are + // in. Thus, to correctly calculate the size of delimiter we need around + // a group, we scale down the inner size based on the size. + + + innerHeight *= options.sizeMultiplier; + innerDepth *= options.sizeMultiplier; + var leftDelim; + + if (group.left === ".") { + // Empty delimiters in \left and \right make null delimiter spaces. + leftDelim = makeNullDelimiter(options, ["mopen"]); + } else { + // Otherwise, use leftRightDelim to generate the correct sized + // delimiter. + leftDelim = delimiter.leftRightDelim(group.left, innerHeight, innerDepth, options, group.mode, ["mopen"]); + } // Add it to the beginning of the expression + + + inner.unshift(leftDelim); // Handle middle delimiters + + if (hadMiddle) { + for (var _i = 1; _i < inner.length; _i++) { + var middleDelim = inner[_i]; // Property `isMiddle` not defined on `span`. See comment in + // "middle"'s htmlBuilder. + // $FlowFixMe + + var isMiddle = middleDelim.isMiddle; + + if (isMiddle) { + // Apply the options that were active when \middle was called + inner[_i] = delimiter.leftRightDelim(isMiddle.delim, innerHeight, innerDepth, isMiddle.options, group.mode, []); + } + } + } + + var rightDelim; // Same for the right delimiter, but using color specified by \color + + if (group.right === ".") { + rightDelim = makeNullDelimiter(options, ["mclose"]); + } else { + var colorOptions = group.rightColor ? options.withColor(group.rightColor) : options; + rightDelim = delimiter.leftRightDelim(group.right, innerHeight, innerDepth, colorOptions, group.mode, ["mclose"]); + } // Add it to the end of the expression. + + + inner.push(rightDelim); + return buildCommon.makeSpan(["minner"], inner, options); + }, + mathmlBuilder: (group, options) => { + assertParsed(group); + var inner = buildExpression(group.body, options); + + if (group.left !== ".") { + var leftNode = new mathMLTree.MathNode("mo", [makeText(group.left, group.mode)]); + leftNode.setAttribute("fence", "true"); + inner.unshift(leftNode); + } + + if (group.right !== ".") { + var rightNode = new mathMLTree.MathNode("mo", [makeText(group.right, group.mode)]); + rightNode.setAttribute("fence", "true"); + + if (group.rightColor) { + rightNode.setAttribute("mathcolor", group.rightColor); + } + + inner.push(rightNode); + } + + return makeRow(inner); + } +}); +defineFunction({ + type: "middle", + names: ["\\middle"], + props: { + numArgs: 1, + primitive: true + }, + handler: (context, args) => { + var delim = checkDelimiter(args[0], context); + + if (!context.parser.leftrightDepth) { + throw new ParseError("\\middle without preceding \\left", delim); + } + + return { + type: "middle", + mode: context.parser.mode, + delim: delim.text + }; + }, + htmlBuilder: (group, options) => { + var middleDelim; + + if (group.delim === ".") { + middleDelim = makeNullDelimiter(options, []); + } else { + middleDelim = delimiter.sizedDelim(group.delim, 1, options, group.mode, []); + var isMiddle = { + delim: group.delim, + options + }; // Property `isMiddle` not defined on `span`. It is only used in + // this file above. + // TODO: Fix this violation of the `span` type and possibly rename + // things since `isMiddle` sounds like a boolean, but is a struct. + // $FlowFixMe + + middleDelim.isMiddle = isMiddle; + } + + return middleDelim; + }, + mathmlBuilder: (group, options) => { + // A Firefox \middle will stretch a character vertically only if it + // is in the fence part of the operator dictionary at: + // https://www.w3.org/TR/MathML3/appendixc.html. + // So we need to avoid U+2223 and use plain "|" instead. + var textNode = group.delim === "\\vert" || group.delim === "|" ? makeText("|", "text") : makeText(group.delim, group.mode); + var middleNode = new mathMLTree.MathNode("mo", [textNode]); + middleNode.setAttribute("fence", "true"); // MathML gives 5/18em spacing to each element. + // \middle should get delimiter spacing instead. + + middleNode.setAttribute("lspace", "0.05em"); + middleNode.setAttribute("rspace", "0.05em"); + return middleNode; + } +}); + +var htmlBuilder$7 = (group, options) => { + // \cancel, \bcancel, \xcancel, \sout, \fbox, \colorbox, \fcolorbox, \phase + // Some groups can return document fragments. Handle those by wrapping + // them in a span. + var inner = buildCommon.wrapFragment(buildGroup$1(group.body, options), options); + var label = group.label.slice(1); + var scale = options.sizeMultiplier; + var img; + var imgShift = 0; // In the LaTeX cancel package, line geometry is slightly different + // depending on whether the subject is wider than it is tall, or vice versa. + // We don't know the width of a group, so as a proxy, we test if + // the subject is a single character. This captures most of the + // subjects that should get the "tall" treatment. + + var isSingleChar = utils.isCharacterBox(group.body); + + if (label === "sout") { + img = buildCommon.makeSpan(["stretchy", "sout"]); + img.height = options.fontMetrics().defaultRuleThickness / scale; + imgShift = -0.5 * options.fontMetrics().xHeight; + } else if (label === "phase") { + // Set a couple of dimensions from the steinmetz package. + var lineWeight = calculateSize({ + number: 0.6, + unit: "pt" + }, options); + var clearance = calculateSize({ + number: 0.35, + unit: "ex" + }, options); // Prevent size changes like \Huge from affecting line thickness + + var newOptions = options.havingBaseSizing(); + scale = scale / newOptions.sizeMultiplier; + var angleHeight = inner.height + inner.depth + lineWeight + clearance; // Reserve a left pad for the angle. + + inner.style.paddingLeft = makeEm(angleHeight / 2 + lineWeight); // Create an SVG + + var viewBoxHeight = Math.floor(1000 * angleHeight * scale); + var path = phasePath(viewBoxHeight); + var svgNode = new SvgNode([new PathNode("phase", path)], { + "width": "400em", + "height": makeEm(viewBoxHeight / 1000), + "viewBox": "0 0 400000 " + viewBoxHeight, + "preserveAspectRatio": "xMinYMin slice" + }); // Wrap it in a span with overflow: hidden. + + img = buildCommon.makeSvgSpan(["hide-tail"], [svgNode], options); + img.style.height = makeEm(angleHeight); + imgShift = inner.depth + lineWeight + clearance; + } else { + // Add horizontal padding + if (/cancel/.test(label)) { + if (!isSingleChar) { + inner.classes.push("cancel-pad"); + } + } else if (label === "angl") { + inner.classes.push("anglpad"); + } else { + inner.classes.push("boxpad"); + } // Add vertical padding + + + var topPad = 0; + var bottomPad = 0; + var ruleThickness = 0; // ref: cancel package: \advance\totalheight2\p@ % "+2" + + if (/box/.test(label)) { + ruleThickness = Math.max(options.fontMetrics().fboxrule, // default + options.minRuleThickness // User override. + ); + topPad = options.fontMetrics().fboxsep + (label === "colorbox" ? 0 : ruleThickness); + bottomPad = topPad; + } else if (label === "angl") { + ruleThickness = Math.max(options.fontMetrics().defaultRuleThickness, options.minRuleThickness); + topPad = 4 * ruleThickness; // gap = 3 × line, plus the line itself. + + bottomPad = Math.max(0, 0.25 - inner.depth); + } else { + topPad = isSingleChar ? 0.2 : 0; + bottomPad = topPad; + } + + img = stretchy.encloseSpan(inner, label, topPad, bottomPad, options); + + if (/fbox|boxed|fcolorbox/.test(label)) { + img.style.borderStyle = "solid"; + img.style.borderWidth = makeEm(ruleThickness); + } else if (label === "angl" && ruleThickness !== 0.049) { + img.style.borderTopWidth = makeEm(ruleThickness); + img.style.borderRightWidth = makeEm(ruleThickness); + } + + imgShift = inner.depth + bottomPad; + + if (group.backgroundColor) { + img.style.backgroundColor = group.backgroundColor; + + if (group.borderColor) { + img.style.borderColor = group.borderColor; + } + } + } + + var vlist; + + if (group.backgroundColor) { + vlist = buildCommon.makeVList({ + positionType: "individualShift", + children: [// Put the color background behind inner; + { + type: "elem", + elem: img, + shift: imgShift + }, { + type: "elem", + elem: inner, + shift: 0 + }] + }, options); + } else { + var classes = /cancel|phase/.test(label) ? ["svg-align"] : []; + vlist = buildCommon.makeVList({ + positionType: "individualShift", + children: [// Write the \cancel stroke on top of inner. + { + type: "elem", + elem: inner, + shift: 0 + }, { + type: "elem", + elem: img, + shift: imgShift, + wrapperClasses: classes + }] + }, options); + } + + if (/cancel/.test(label)) { + // The cancel package documentation says that cancel lines add their height + // to the expression, but tests show that isn't how it actually works. + vlist.height = inner.height; + vlist.depth = inner.depth; + } + + if (/cancel/.test(label) && !isSingleChar) { + // cancel does not create horiz space for its line extension. + return buildCommon.makeSpan(["mord", "cancel-lap"], [vlist], options); + } else { + return buildCommon.makeSpan(["mord"], [vlist], options); + } +}; + +var mathmlBuilder$6 = (group, options) => { + var fboxsep = 0; + var node = new mathMLTree.MathNode(group.label.indexOf("colorbox") > -1 ? "mpadded" : "menclose", [buildGroup(group.body, options)]); + + switch (group.label) { + case "\\cancel": + node.setAttribute("notation", "updiagonalstrike"); + break; + + case "\\bcancel": + node.setAttribute("notation", "downdiagonalstrike"); + break; + + case "\\phase": + node.setAttribute("notation", "phasorangle"); + break; + + case "\\sout": + node.setAttribute("notation", "horizontalstrike"); + break; + + case "\\fbox": + node.setAttribute("notation", "box"); + break; + + case "\\angl": + node.setAttribute("notation", "actuarial"); + break; + + case "\\fcolorbox": + case "\\colorbox": + // doesn't have a good notation option. So use + // instead. Set some attributes that come included with . + fboxsep = options.fontMetrics().fboxsep * options.fontMetrics().ptPerEm; + node.setAttribute("width", "+" + 2 * fboxsep + "pt"); + node.setAttribute("height", "+" + 2 * fboxsep + "pt"); + node.setAttribute("lspace", fboxsep + "pt"); // + + node.setAttribute("voffset", fboxsep + "pt"); + + if (group.label === "\\fcolorbox") { + var thk = Math.max(options.fontMetrics().fboxrule, // default + options.minRuleThickness // user override + ); + node.setAttribute("style", "border: " + thk + "em solid " + String(group.borderColor)); + } + + break; + + case "\\xcancel": + node.setAttribute("notation", "updiagonalstrike downdiagonalstrike"); + break; + } + + if (group.backgroundColor) { + node.setAttribute("mathbackground", group.backgroundColor); + } + + return node; +}; + +defineFunction({ + type: "enclose", + names: ["\\colorbox"], + props: { + numArgs: 2, + allowedInText: true, + argTypes: ["color", "text"] + }, + + handler(_ref, args, optArgs) { + var { + parser, + funcName + } = _ref; + var color = assertNodeType(args[0], "color-token").color; + var body = args[1]; + return { + type: "enclose", + mode: parser.mode, + label: funcName, + backgroundColor: color, + body + }; + }, + + htmlBuilder: htmlBuilder$7, + mathmlBuilder: mathmlBuilder$6 +}); +defineFunction({ + type: "enclose", + names: ["\\fcolorbox"], + props: { + numArgs: 3, + allowedInText: true, + argTypes: ["color", "color", "text"] + }, + + handler(_ref2, args, optArgs) { + var { + parser, + funcName + } = _ref2; + var borderColor = assertNodeType(args[0], "color-token").color; + var backgroundColor = assertNodeType(args[1], "color-token").color; + var body = args[2]; + return { + type: "enclose", + mode: parser.mode, + label: funcName, + backgroundColor, + borderColor, + body + }; + }, + + htmlBuilder: htmlBuilder$7, + mathmlBuilder: mathmlBuilder$6 +}); +defineFunction({ + type: "enclose", + names: ["\\fbox"], + props: { + numArgs: 1, + argTypes: ["hbox"], + allowedInText: true + }, + + handler(_ref3, args) { + var { + parser + } = _ref3; + return { + type: "enclose", + mode: parser.mode, + label: "\\fbox", + body: args[0] + }; + } + +}); +defineFunction({ + type: "enclose", + names: ["\\cancel", "\\bcancel", "\\xcancel", "\\sout", "\\phase"], + props: { + numArgs: 1 + }, + + handler(_ref4, args) { + var { + parser, + funcName + } = _ref4; + var body = args[0]; + return { + type: "enclose", + mode: parser.mode, + label: funcName, + body + }; + }, + + htmlBuilder: htmlBuilder$7, + mathmlBuilder: mathmlBuilder$6 +}); +defineFunction({ + type: "enclose", + names: ["\\angl"], + props: { + numArgs: 1, + argTypes: ["hbox"], + allowedInText: false + }, + + handler(_ref5, args) { + var { + parser + } = _ref5; + return { + type: "enclose", + mode: parser.mode, + label: "\\angl", + body: args[0] + }; + } + +}); + +/** + * All registered environments. + * `environments.js` exports this same dictionary again and makes it public. + * `Parser.js` requires this dictionary via `environments.js`. + */ +var _environments = {}; +function defineEnvironment(_ref) { + var { + type, + names, + props, + handler, + htmlBuilder, + mathmlBuilder + } = _ref; + // Set default values of environments. + var data = { + type, + numArgs: props.numArgs || 0, + allowedInText: false, + numOptionalArgs: 0, + handler + }; + + for (var i = 0; i < names.length; ++i) { + // TODO: The value type of _environments should be a type union of all + // possible `EnvSpec<>` possibilities instead of `EnvSpec<*>`, which is + // an existential type. + _environments[names[i]] = data; + } + + if (htmlBuilder) { + _htmlGroupBuilders[type] = htmlBuilder; + } + + if (mathmlBuilder) { + _mathmlGroupBuilders[type] = mathmlBuilder; + } +} + +/** + * All registered global/built-in macros. + * `macros.js` exports this same dictionary again and makes it public. + * `Parser.js` requires this dictionary via `macros.js`. + */ +var _macros = {}; // This function might one day accept an additional argument and do more things. + +function defineMacro(name, body) { + _macros[name] = body; +} + +// Helper functions +function getHLines(parser) { + // Return an array. The array length = number of hlines. + // Each element in the array tells if the line is dashed. + var hlineInfo = []; + parser.consumeSpaces(); + var nxt = parser.fetch().text; + + if (nxt === "\\relax") { + // \relax is an artifact of the \cr macro below + parser.consume(); + parser.consumeSpaces(); + nxt = parser.fetch().text; + } + + while (nxt === "\\hline" || nxt === "\\hdashline") { + parser.consume(); + hlineInfo.push(nxt === "\\hdashline"); + parser.consumeSpaces(); + nxt = parser.fetch().text; + } + + return hlineInfo; +} + +var validateAmsEnvironmentContext = context => { + var settings = context.parser.settings; + + if (!settings.displayMode) { + throw new ParseError("{" + context.envName + "} can be used only in" + " display mode."); + } +}; // autoTag (an argument to parseArray) can be one of three values: +// * undefined: Regular (not-top-level) array; no tags on each row +// * true: Automatic equation numbering, overridable by \tag +// * false: Tags allowed on each row, but no automatic numbering +// This function *doesn't* work with the "split" environment name. + + +function getAutoTag(name) { + if (name.indexOf("ed") === -1) { + return name.indexOf("*") === -1; + } // return undefined; + +} +/** + * Parse the body of the environment, with rows delimited by \\ and + * columns delimited by &, and create a nested list in row-major order + * with one group per cell. If given an optional argument style + * ("text", "display", etc.), then each cell is cast into that style. + */ + + +function parseArray(parser, _ref, style) { + var { + hskipBeforeAndAfter, + addJot, + cols, + arraystretch, + colSeparationType, + autoTag, + singleRow, + emptySingleRow, + maxNumCols, + leqno + } = _ref; + parser.gullet.beginGroup(); + + if (!singleRow) { + // \cr is equivalent to \\ without the optional size argument (see below) + // TODO: provide helpful error when \cr is used outside array environment + parser.gullet.macros.set("\\cr", "\\\\\\relax"); + } // Get current arraystretch if it's not set by the environment + + + if (!arraystretch) { + var stretch = parser.gullet.expandMacroAsText("\\arraystretch"); + + if (stretch == null) { + // Default \arraystretch from lttab.dtx + arraystretch = 1; + } else { + arraystretch = parseFloat(stretch); + + if (!arraystretch || arraystretch < 0) { + throw new ParseError("Invalid \\arraystretch: " + stretch); + } + } + } // Start group for first cell + + + parser.gullet.beginGroup(); + var row = []; + var body = [row]; + var rowGaps = []; + var hLinesBeforeRow = []; + var tags = autoTag != null ? [] : undefined; // amsmath uses \global\@eqnswtrue and \global\@eqnswfalse to represent + // whether this row should have an equation number. Simulate this with + // a \@eqnsw macro set to 1 or 0. + + function beginRow() { + if (autoTag) { + parser.gullet.macros.set("\\@eqnsw", "1", true); + } + } + + function endRow() { + if (tags) { + if (parser.gullet.macros.get("\\df@tag")) { + tags.push(parser.subparse([new Token("\\df@tag")])); + parser.gullet.macros.set("\\df@tag", undefined, true); + } else { + tags.push(Boolean(autoTag) && parser.gullet.macros.get("\\@eqnsw") === "1"); + } + } + } + + beginRow(); // Test for \hline at the top of the array. + + hLinesBeforeRow.push(getHLines(parser)); + + while (true) { + // eslint-disable-line no-constant-condition + // Parse each cell in its own group (namespace) + var cell = parser.parseExpression(false, singleRow ? "\\end" : "\\\\"); + parser.gullet.endGroup(); + parser.gullet.beginGroup(); + cell = { + type: "ordgroup", + mode: parser.mode, + body: cell + }; + + if (style) { + cell = { + type: "styling", + mode: parser.mode, + style, + body: [cell] + }; + } + + row.push(cell); + var next = parser.fetch().text; + + if (next === "&") { + if (maxNumCols && row.length === maxNumCols) { + if (singleRow || colSeparationType) { + // {equation} or {split} + throw new ParseError("Too many tab characters: &", parser.nextToken); + } else { + // {array} environment + parser.settings.reportNonstrict("textEnv", "Too few columns " + "specified in the {array} column argument."); + } + } + + parser.consume(); + } else if (next === "\\end") { + endRow(); // Arrays terminate newlines with `\crcr` which consumes a `\cr` if + // the last line is empty. However, AMS environments keep the + // empty row if it's the only one. + // NOTE: Currently, `cell` is the last item added into `row`. + + if (row.length === 1 && cell.type === "styling" && cell.body[0].body.length === 0 && (body.length > 1 || !emptySingleRow)) { + body.pop(); + } + + if (hLinesBeforeRow.length < body.length + 1) { + hLinesBeforeRow.push([]); + } + + break; + } else if (next === "\\\\") { + parser.consume(); + var size = void 0; // \def\Let@{\let\\\math@cr} + // \def\math@cr{...\math@cr@} + // \def\math@cr@{\new@ifnextchar[\math@cr@@{\math@cr@@[\z@]}} + // \def\math@cr@@[#1]{...\math@cr@@@...} + // \def\math@cr@@@{\cr} + + if (parser.gullet.future().text !== " ") { + size = parser.parseSizeGroup(true); + } + + rowGaps.push(size ? size.value : null); + endRow(); // check for \hline(s) following the row separator + + hLinesBeforeRow.push(getHLines(parser)); + row = []; + body.push(row); + beginRow(); + } else { + throw new ParseError("Expected & or \\\\ or \\cr or \\end", parser.nextToken); + } + } // End cell group + + + parser.gullet.endGroup(); // End array group defining \cr + + parser.gullet.endGroup(); + return { + type: "array", + mode: parser.mode, + addJot, + arraystretch, + body, + cols, + rowGaps, + hskipBeforeAndAfter, + hLinesBeforeRow, + colSeparationType, + tags, + leqno + }; +} // Decides on a style for cells in an array according to whether the given +// environment name starts with the letter 'd'. + + +function dCellStyle(envName) { + if (envName.slice(0, 1) === "d") { + return "display"; + } else { + return "text"; + } +} + +var htmlBuilder$6 = function htmlBuilder(group, options) { + var r; + var c; + var nr = group.body.length; + var hLinesBeforeRow = group.hLinesBeforeRow; + var nc = 0; + var body = new Array(nr); + var hlines = []; + var ruleThickness = Math.max( // From LaTeX \showthe\arrayrulewidth. Equals 0.04 em. + options.fontMetrics().arrayRuleWidth, options.minRuleThickness // User override. + ); // Horizontal spacing + + var pt = 1 / options.fontMetrics().ptPerEm; + var arraycolsep = 5 * pt; // default value, i.e. \arraycolsep in article.cls + + if (group.colSeparationType && group.colSeparationType === "small") { + // We're in a {smallmatrix}. Default column space is \thickspace, + // i.e. 5/18em = 0.2778em, per amsmath.dtx for {smallmatrix}. + // But that needs adjustment because LaTeX applies \scriptstyle to the + // entire array, including the colspace, but this function applies + // \scriptstyle only inside each element. + var localMultiplier = options.havingStyle(Style$1.SCRIPT).sizeMultiplier; + arraycolsep = 0.2778 * (localMultiplier / options.sizeMultiplier); + } // Vertical spacing + + + var baselineskip = group.colSeparationType === "CD" ? calculateSize({ + number: 3, + unit: "ex" + }, options) : 12 * pt; // see size10.clo + // Default \jot from ltmath.dtx + // TODO(edemaine): allow overriding \jot via \setlength (#687) + + var jot = 3 * pt; + var arrayskip = group.arraystretch * baselineskip; + var arstrutHeight = 0.7 * arrayskip; // \strutbox in ltfsstrc.dtx and + + var arstrutDepth = 0.3 * arrayskip; // \@arstrutbox in lttab.dtx + + var totalHeight = 0; // Set a position for \hline(s) at the top of the array, if any. + + function setHLinePos(hlinesInGap) { + for (var i = 0; i < hlinesInGap.length; ++i) { + if (i > 0) { + totalHeight += 0.25; + } + + hlines.push({ + pos: totalHeight, + isDashed: hlinesInGap[i] + }); + } + } + + setHLinePos(hLinesBeforeRow[0]); + + for (r = 0; r < group.body.length; ++r) { + var inrow = group.body[r]; + var height = arstrutHeight; // \@array adds an \@arstrut + + var depth = arstrutDepth; // to each tow (via the template) + + if (nc < inrow.length) { + nc = inrow.length; + } + + var outrow = new Array(inrow.length); + + for (c = 0; c < inrow.length; ++c) { + var elt = buildGroup$1(inrow[c], options); + + if (depth < elt.depth) { + depth = elt.depth; + } + + if (height < elt.height) { + height = elt.height; + } + + outrow[c] = elt; + } + + var rowGap = group.rowGaps[r]; + var gap = 0; + + if (rowGap) { + gap = calculateSize(rowGap, options); + + if (gap > 0) { + // \@argarraycr + gap += arstrutDepth; + + if (depth < gap) { + depth = gap; // \@xargarraycr + } + + gap = 0; + } + } // In AMS multiline environments such as aligned and gathered, rows + // correspond to lines that have additional \jot added to the + // \baselineskip via \openup. + + + if (group.addJot) { + depth += jot; + } + + outrow.height = height; + outrow.depth = depth; + totalHeight += height; + outrow.pos = totalHeight; + totalHeight += depth + gap; // \@yargarraycr + + body[r] = outrow; // Set a position for \hline(s), if any. + + setHLinePos(hLinesBeforeRow[r + 1]); + } + + var offset = totalHeight / 2 + options.fontMetrics().axisHeight; + var colDescriptions = group.cols || []; + var cols = []; + var colSep; + var colDescrNum; + var tagSpans = []; + + if (group.tags && group.tags.some(tag => tag)) { + // An environment with manual tags and/or automatic equation numbers. + // Create node(s), the latter of which trigger CSS counter increment. + for (r = 0; r < nr; ++r) { + var rw = body[r]; + var shift = rw.pos - offset; + var tag = group.tags[r]; + var tagSpan = void 0; + + if (tag === true) { + // automatic numbering + tagSpan = buildCommon.makeSpan(["eqn-num"], [], options); + } else if (tag === false) { + // \nonumber/\notag or starred environment + tagSpan = buildCommon.makeSpan([], [], options); + } else { + // manual \tag + tagSpan = buildCommon.makeSpan([], buildExpression$1(tag, options, true), options); + } + + tagSpan.depth = rw.depth; + tagSpan.height = rw.height; + tagSpans.push({ + type: "elem", + elem: tagSpan, + shift + }); + } + } + + for (c = 0, colDescrNum = 0; // Continue while either there are more columns or more column + // descriptions, so trailing separators don't get lost. + c < nc || colDescrNum < colDescriptions.length; ++c, ++colDescrNum) { + var colDescr = colDescriptions[colDescrNum] || {}; + var firstSeparator = true; + + while (colDescr.type === "separator") { + // If there is more than one separator in a row, add a space + // between them. + if (!firstSeparator) { + colSep = buildCommon.makeSpan(["arraycolsep"], []); + colSep.style.width = makeEm(options.fontMetrics().doubleRuleSep); + cols.push(colSep); + } + + if (colDescr.separator === "|" || colDescr.separator === ":") { + var lineType = colDescr.separator === "|" ? "solid" : "dashed"; + var separator = buildCommon.makeSpan(["vertical-separator"], [], options); + separator.style.height = makeEm(totalHeight); + separator.style.borderRightWidth = makeEm(ruleThickness); + separator.style.borderRightStyle = lineType; + separator.style.margin = "0 " + makeEm(-ruleThickness / 2); + + var _shift = totalHeight - offset; + + if (_shift) { + separator.style.verticalAlign = makeEm(-_shift); + } + + cols.push(separator); + } else { + throw new ParseError("Invalid separator type: " + colDescr.separator); + } + + colDescrNum++; + colDescr = colDescriptions[colDescrNum] || {}; + firstSeparator = false; + } + + if (c >= nc) { + continue; + } + + var sepwidth = void 0; + + if (c > 0 || group.hskipBeforeAndAfter) { + sepwidth = utils.deflt(colDescr.pregap, arraycolsep); + + if (sepwidth !== 0) { + colSep = buildCommon.makeSpan(["arraycolsep"], []); + colSep.style.width = makeEm(sepwidth); + cols.push(colSep); + } + } + + var col = []; + + for (r = 0; r < nr; ++r) { + var row = body[r]; + var elem = row[c]; + + if (!elem) { + continue; + } + + var _shift2 = row.pos - offset; + + elem.depth = row.depth; + elem.height = row.height; + col.push({ + type: "elem", + elem: elem, + shift: _shift2 + }); + } + + col = buildCommon.makeVList({ + positionType: "individualShift", + children: col + }, options); + col = buildCommon.makeSpan(["col-align-" + (colDescr.align || "c")], [col]); + cols.push(col); + + if (c < nc - 1 || group.hskipBeforeAndAfter) { + sepwidth = utils.deflt(colDescr.postgap, arraycolsep); + + if (sepwidth !== 0) { + colSep = buildCommon.makeSpan(["arraycolsep"], []); + colSep.style.width = makeEm(sepwidth); + cols.push(colSep); + } + } + } + + body = buildCommon.makeSpan(["mtable"], cols); // Add \hline(s), if any. + + if (hlines.length > 0) { + var line = buildCommon.makeLineSpan("hline", options, ruleThickness); + var dashes = buildCommon.makeLineSpan("hdashline", options, ruleThickness); + var vListElems = [{ + type: "elem", + elem: body, + shift: 0 + }]; + + while (hlines.length > 0) { + var hline = hlines.pop(); + var lineShift = hline.pos - offset; + + if (hline.isDashed) { + vListElems.push({ + type: "elem", + elem: dashes, + shift: lineShift + }); + } else { + vListElems.push({ + type: "elem", + elem: line, + shift: lineShift + }); + } + } + + body = buildCommon.makeVList({ + positionType: "individualShift", + children: vListElems + }, options); + } + + if (tagSpans.length === 0) { + return buildCommon.makeSpan(["mord"], [body], options); + } else { + var eqnNumCol = buildCommon.makeVList({ + positionType: "individualShift", + children: tagSpans + }, options); + eqnNumCol = buildCommon.makeSpan(["tag"], [eqnNumCol], options); + return buildCommon.makeFragment([body, eqnNumCol]); + } +}; + +var alignMap = { + c: "center ", + l: "left ", + r: "right " +}; + +var mathmlBuilder$5 = function mathmlBuilder(group, options) { + var tbl = []; + var glue = new mathMLTree.MathNode("mtd", [], ["mtr-glue"]); + var tag = new mathMLTree.MathNode("mtd", [], ["mml-eqn-num"]); + + for (var i = 0; i < group.body.length; i++) { + var rw = group.body[i]; + var row = []; + + for (var j = 0; j < rw.length; j++) { + row.push(new mathMLTree.MathNode("mtd", [buildGroup(rw[j], options)])); + } + + if (group.tags && group.tags[i]) { + row.unshift(glue); + row.push(glue); + + if (group.leqno) { + row.unshift(tag); + } else { + row.push(tag); + } + } + + tbl.push(new mathMLTree.MathNode("mtr", row)); + } + + var table = new mathMLTree.MathNode("mtable", tbl); // Set column alignment, row spacing, column spacing, and + // array lines by setting attributes on the table element. + // Set the row spacing. In MathML, we specify a gap distance. + // We do not use rowGap[] because MathML automatically increases + // cell height with the height/depth of the element content. + // LaTeX \arraystretch multiplies the row baseline-to-baseline distance. + // We simulate this by adding (arraystretch - 1)em to the gap. This + // does a reasonable job of adjusting arrays containing 1 em tall content. + // The 0.16 and 0.09 values are found empirically. They produce an array + // similar to LaTeX and in which content does not interfere with \hlines. + + var gap = group.arraystretch === 0.5 ? 0.1 // {smallmatrix}, {subarray} + : 0.16 + group.arraystretch - 1 + (group.addJot ? 0.09 : 0); + table.setAttribute("rowspacing", makeEm(gap)); // MathML table lines go only between cells. + // To place a line on an edge we'll use , if necessary. + + var menclose = ""; + var align = ""; + + if (group.cols && group.cols.length > 0) { + // Find column alignment, column spacing, and vertical lines. + var cols = group.cols; + var columnLines = ""; + var prevTypeWasAlign = false; + var iStart = 0; + var iEnd = cols.length; + + if (cols[0].type === "separator") { + menclose += "top "; + iStart = 1; + } + + if (cols[cols.length - 1].type === "separator") { + menclose += "bottom "; + iEnd -= 1; + } + + for (var _i = iStart; _i < iEnd; _i++) { + if (cols[_i].type === "align") { + align += alignMap[cols[_i].align]; + + if (prevTypeWasAlign) { + columnLines += "none "; + } + + prevTypeWasAlign = true; + } else if (cols[_i].type === "separator") { + // MathML accepts only single lines between cells. + // So we read only the first of consecutive separators. + if (prevTypeWasAlign) { + columnLines += cols[_i].separator === "|" ? "solid " : "dashed "; + prevTypeWasAlign = false; + } + } + } + + table.setAttribute("columnalign", align.trim()); + + if (/[sd]/.test(columnLines)) { + table.setAttribute("columnlines", columnLines.trim()); + } + } // Set column spacing. + + + if (group.colSeparationType === "align") { + var _cols = group.cols || []; + + var spacing = ""; + + for (var _i2 = 1; _i2 < _cols.length; _i2++) { + spacing += _i2 % 2 ? "0em " : "1em "; + } + + table.setAttribute("columnspacing", spacing.trim()); + } else if (group.colSeparationType === "alignat" || group.colSeparationType === "gather") { + table.setAttribute("columnspacing", "0em"); + } else if (group.colSeparationType === "small") { + table.setAttribute("columnspacing", "0.2778em"); + } else if (group.colSeparationType === "CD") { + table.setAttribute("columnspacing", "0.5em"); + } else { + table.setAttribute("columnspacing", "1em"); + } // Address \hline and \hdashline + + + var rowLines = ""; + var hlines = group.hLinesBeforeRow; + menclose += hlines[0].length > 0 ? "left " : ""; + menclose += hlines[hlines.length - 1].length > 0 ? "right " : ""; + + for (var _i3 = 1; _i3 < hlines.length - 1; _i3++) { + rowLines += hlines[_i3].length === 0 ? "none " // MathML accepts only a single line between rows. Read one element. + : hlines[_i3][0] ? "dashed " : "solid "; + } + + if (/[sd]/.test(rowLines)) { + table.setAttribute("rowlines", rowLines.trim()); + } + + if (menclose !== "") { + table = new mathMLTree.MathNode("menclose", [table]); + table.setAttribute("notation", menclose.trim()); + } + + if (group.arraystretch && group.arraystretch < 1) { + // A small array. Wrap in scriptstyle so row gap is not too large. + table = new mathMLTree.MathNode("mstyle", [table]); + table.setAttribute("scriptlevel", "1"); + } + + return table; +}; // Convenience function for align, align*, aligned, alignat, alignat*, alignedat. + + +var alignedHandler = function alignedHandler(context, args) { + if (context.envName.indexOf("ed") === -1) { + validateAmsEnvironmentContext(context); + } + + var cols = []; + var separationType = context.envName.indexOf("at") > -1 ? "alignat" : "align"; + var isSplit = context.envName === "split"; + var res = parseArray(context.parser, { + cols, + addJot: true, + autoTag: isSplit ? undefined : getAutoTag(context.envName), + emptySingleRow: true, + colSeparationType: separationType, + maxNumCols: isSplit ? 2 : undefined, + leqno: context.parser.settings.leqno + }, "display"); // Determining number of columns. + // 1. If the first argument is given, we use it as a number of columns, + // and makes sure that each row doesn't exceed that number. + // 2. Otherwise, just count number of columns = maximum number + // of cells in each row ("aligned" mode -- isAligned will be true). + // + // At the same time, prepend empty group {} at beginning of every second + // cell in each row (starting with second cell) so that operators become + // binary. This behavior is implemented in amsmath's \start@aligned. + + var numMaths; + var numCols = 0; + var emptyGroup = { + type: "ordgroup", + mode: context.mode, + body: [] + }; + + if (args[0] && args[0].type === "ordgroup") { + var arg0 = ""; + + for (var i = 0; i < args[0].body.length; i++) { + var textord = assertNodeType(args[0].body[i], "textord"); + arg0 += textord.text; + } + + numMaths = Number(arg0); + numCols = numMaths * 2; + } + + var isAligned = !numCols; + res.body.forEach(function (row) { + for (var _i4 = 1; _i4 < row.length; _i4 += 2) { + // Modify ordgroup node within styling node + var styling = assertNodeType(row[_i4], "styling"); + var ordgroup = assertNodeType(styling.body[0], "ordgroup"); + ordgroup.body.unshift(emptyGroup); + } + + if (!isAligned) { + // Case 1 + var curMaths = row.length / 2; + + if (numMaths < curMaths) { + throw new ParseError("Too many math in a row: " + ("expected " + numMaths + ", but got " + curMaths), row[0]); + } + } else if (numCols < row.length) { + // Case 2 + numCols = row.length; + } + }); // Adjusting alignment. + // In aligned mode, we add one \qquad between columns; + // otherwise we add nothing. + + for (var _i5 = 0; _i5 < numCols; ++_i5) { + var align = "r"; + var pregap = 0; + + if (_i5 % 2 === 1) { + align = "l"; + } else if (_i5 > 0 && isAligned) { + // "aligned" mode. + pregap = 1; // add one \quad + } + + cols[_i5] = { + type: "align", + align: align, + pregap: pregap, + postgap: 0 + }; + } + + res.colSeparationType = isAligned ? "align" : "alignat"; + return res; +}; // Arrays are part of LaTeX, defined in lttab.dtx so its documentation +// is part of the source2e.pdf file of LaTeX2e source documentation. +// {darray} is an {array} environment where cells are set in \displaystyle, +// as defined in nccmath.sty. + + +defineEnvironment({ + type: "array", + names: ["array", "darray"], + props: { + numArgs: 1 + }, + + handler(context, args) { + // Since no types are specified above, the two possibilities are + // - The argument is wrapped in {} or [], in which case Parser's + // parseGroup() returns an "ordgroup" wrapping some symbol node. + // - The argument is a bare symbol node. + var symNode = checkSymbolNodeType(args[0]); + var colalign = symNode ? [args[0]] : assertNodeType(args[0], "ordgroup").body; + var cols = colalign.map(function (nde) { + var node = assertSymbolNodeType(nde); + var ca = node.text; + + if ("lcr".indexOf(ca) !== -1) { + return { + type: "align", + align: ca + }; + } else if (ca === "|") { + return { + type: "separator", + separator: "|" + }; + } else if (ca === ":") { + return { + type: "separator", + separator: ":" + }; + } + + throw new ParseError("Unknown column alignment: " + ca, nde); + }); + var res = { + cols, + hskipBeforeAndAfter: true, + // \@preamble in lttab.dtx + maxNumCols: cols.length + }; + return parseArray(context.parser, res, dCellStyle(context.envName)); + }, + + htmlBuilder: htmlBuilder$6, + mathmlBuilder: mathmlBuilder$5 +}); // The matrix environments of amsmath builds on the array environment +// of LaTeX, which is discussed above. +// The mathtools package adds starred versions of the same environments. +// These have an optional argument to choose left|center|right justification. + +defineEnvironment({ + type: "array", + names: ["matrix", "pmatrix", "bmatrix", "Bmatrix", "vmatrix", "Vmatrix", "matrix*", "pmatrix*", "bmatrix*", "Bmatrix*", "vmatrix*", "Vmatrix*"], + props: { + numArgs: 0 + }, + + handler(context) { + var delimiters = { + "matrix": null, + "pmatrix": ["(", ")"], + "bmatrix": ["[", "]"], + "Bmatrix": ["\\{", "\\}"], + "vmatrix": ["|", "|"], + "Vmatrix": ["\\Vert", "\\Vert"] + }[context.envName.replace("*", "")]; // \hskip -\arraycolsep in amsmath + + var colAlign = "c"; + var payload = { + hskipBeforeAndAfter: false, + cols: [{ + type: "align", + align: colAlign + }] + }; + + if (context.envName.charAt(context.envName.length - 1) === "*") { + // It's one of the mathtools starred functions. + // Parse the optional alignment argument. + var parser = context.parser; + parser.consumeSpaces(); + + if (parser.fetch().text === "[") { + parser.consume(); + parser.consumeSpaces(); + colAlign = parser.fetch().text; + + if ("lcr".indexOf(colAlign) === -1) { + throw new ParseError("Expected l or c or r", parser.nextToken); + } + + parser.consume(); + parser.consumeSpaces(); + parser.expect("]"); + parser.consume(); + payload.cols = [{ + type: "align", + align: colAlign + }]; + } + } + + var res = parseArray(context.parser, payload, dCellStyle(context.envName)); // Populate cols with the correct number of column alignment specs. + + var numCols = Math.max(0, ...res.body.map(row => row.length)); + res.cols = new Array(numCols).fill({ + type: "align", + align: colAlign + }); + return delimiters ? { + type: "leftright", + mode: context.mode, + body: [res], + left: delimiters[0], + right: delimiters[1], + rightColor: undefined // \right uninfluenced by \color in array + + } : res; + }, + + htmlBuilder: htmlBuilder$6, + mathmlBuilder: mathmlBuilder$5 +}); +defineEnvironment({ + type: "array", + names: ["smallmatrix"], + props: { + numArgs: 0 + }, + + handler(context) { + var payload = { + arraystretch: 0.5 + }; + var res = parseArray(context.parser, payload, "script"); + res.colSeparationType = "small"; + return res; + }, + + htmlBuilder: htmlBuilder$6, + mathmlBuilder: mathmlBuilder$5 +}); +defineEnvironment({ + type: "array", + names: ["subarray"], + props: { + numArgs: 1 + }, + + handler(context, args) { + // Parsing of {subarray} is similar to {array} + var symNode = checkSymbolNodeType(args[0]); + var colalign = symNode ? [args[0]] : assertNodeType(args[0], "ordgroup").body; + var cols = colalign.map(function (nde) { + var node = assertSymbolNodeType(nde); + var ca = node.text; // {subarray} only recognizes "l" & "c" + + if ("lc".indexOf(ca) !== -1) { + return { + type: "align", + align: ca + }; + } + + throw new ParseError("Unknown column alignment: " + ca, nde); + }); + + if (cols.length > 1) { + throw new ParseError("{subarray} can contain only one column"); + } + + var res = { + cols, + hskipBeforeAndAfter: false, + arraystretch: 0.5 + }; + res = parseArray(context.parser, res, "script"); + + if (res.body.length > 0 && res.body[0].length > 1) { + throw new ParseError("{subarray} can contain only one column"); + } + + return res; + }, + + htmlBuilder: htmlBuilder$6, + mathmlBuilder: mathmlBuilder$5 +}); // A cases environment (in amsmath.sty) is almost equivalent to +// \def\arraystretch{1.2}% +// \left\{\begin{array}{@{}l@{\quad}l@{}} … \end{array}\right. +// {dcases} is a {cases} environment where cells are set in \displaystyle, +// as defined in mathtools.sty. +// {rcases} is another mathtools environment. It's brace is on the right side. + +defineEnvironment({ + type: "array", + names: ["cases", "dcases", "rcases", "drcases"], + props: { + numArgs: 0 + }, + + handler(context) { + var payload = { + arraystretch: 1.2, + cols: [{ + type: "align", + align: "l", + pregap: 0, + // TODO(kevinb) get the current style. + // For now we use the metrics for TEXT style which is what we were + // doing before. Before attempting to get the current style we + // should look at TeX's behavior especially for \over and matrices. + postgap: 1.0 + /* 1em quad */ + + }, { + type: "align", + align: "l", + pregap: 0, + postgap: 0 + }] + }; + var res = parseArray(context.parser, payload, dCellStyle(context.envName)); + return { + type: "leftright", + mode: context.mode, + body: [res], + left: context.envName.indexOf("r") > -1 ? "." : "\\{", + right: context.envName.indexOf("r") > -1 ? "\\}" : ".", + rightColor: undefined + }; + }, + + htmlBuilder: htmlBuilder$6, + mathmlBuilder: mathmlBuilder$5 +}); // In the align environment, one uses ampersands, &, to specify number of +// columns in each row, and to locate spacing between each column. +// align gets automatic numbering. align* and aligned do not. +// The alignedat environment can be used in math mode. +// Note that we assume \nomallineskiplimit to be zero, +// so that \strut@ is the same as \strut. + +defineEnvironment({ + type: "array", + names: ["align", "align*", "aligned", "split"], + props: { + numArgs: 0 + }, + handler: alignedHandler, + htmlBuilder: htmlBuilder$6, + mathmlBuilder: mathmlBuilder$5 +}); // A gathered environment is like an array environment with one centered +// column, but where rows are considered lines so get \jot line spacing +// and contents are set in \displaystyle. + +defineEnvironment({ + type: "array", + names: ["gathered", "gather", "gather*"], + props: { + numArgs: 0 + }, + + handler(context) { + if (utils.contains(["gather", "gather*"], context.envName)) { + validateAmsEnvironmentContext(context); + } + + var res = { + cols: [{ + type: "align", + align: "c" + }], + addJot: true, + colSeparationType: "gather", + autoTag: getAutoTag(context.envName), + emptySingleRow: true, + leqno: context.parser.settings.leqno + }; + return parseArray(context.parser, res, "display"); + }, + + htmlBuilder: htmlBuilder$6, + mathmlBuilder: mathmlBuilder$5 +}); // alignat environment is like an align environment, but one must explicitly +// specify maximum number of columns in each row, and can adjust spacing between +// each columns. + +defineEnvironment({ + type: "array", + names: ["alignat", "alignat*", "alignedat"], + props: { + numArgs: 1 + }, + handler: alignedHandler, + htmlBuilder: htmlBuilder$6, + mathmlBuilder: mathmlBuilder$5 +}); +defineEnvironment({ + type: "array", + names: ["equation", "equation*"], + props: { + numArgs: 0 + }, + + handler(context) { + validateAmsEnvironmentContext(context); + var res = { + autoTag: getAutoTag(context.envName), + emptySingleRow: true, + singleRow: true, + maxNumCols: 1, + leqno: context.parser.settings.leqno + }; + return parseArray(context.parser, res, "display"); + }, + + htmlBuilder: htmlBuilder$6, + mathmlBuilder: mathmlBuilder$5 +}); +defineEnvironment({ + type: "array", + names: ["CD"], + props: { + numArgs: 0 + }, + + handler(context) { + validateAmsEnvironmentContext(context); + return parseCD(context.parser); + }, + + htmlBuilder: htmlBuilder$6, + mathmlBuilder: mathmlBuilder$5 +}); +defineMacro("\\nonumber", "\\gdef\\@eqnsw{0}"); +defineMacro("\\notag", "\\nonumber"); // Catch \hline outside array environment + +defineFunction({ + type: "text", + // Doesn't matter what this is. + names: ["\\hline", "\\hdashline"], + props: { + numArgs: 0, + allowedInText: true, + allowedInMath: true + }, + + handler(context, args) { + throw new ParseError(context.funcName + " valid only within array environment"); + } + +}); + +var environments = _environments; + +// defineEnvironment definitions. + +defineFunction({ + type: "environment", + names: ["\\begin", "\\end"], + props: { + numArgs: 1, + argTypes: ["text"] + }, + + handler(_ref, args) { + var { + parser, + funcName + } = _ref; + var nameGroup = args[0]; + + if (nameGroup.type !== "ordgroup") { + throw new ParseError("Invalid environment name", nameGroup); + } + + var envName = ""; + + for (var i = 0; i < nameGroup.body.length; ++i) { + envName += assertNodeType(nameGroup.body[i], "textord").text; + } + + if (funcName === "\\begin") { + // begin...end is similar to left...right + if (!environments.hasOwnProperty(envName)) { + throw new ParseError("No such environment: " + envName, nameGroup); + } // Build the environment object. Arguments and other information will + // be made available to the begin and end methods using properties. + + + var env = environments[envName]; + var { + args: _args, + optArgs + } = parser.parseArguments("\\begin{" + envName + "}", env); + var context = { + mode: parser.mode, + envName, + parser + }; + var result = env.handler(context, _args, optArgs); + parser.expect("\\end", false); + var endNameToken = parser.nextToken; + var end = assertNodeType(parser.parseFunction(), "environment"); + + if (end.name !== envName) { + throw new ParseError("Mismatch: \\begin{" + envName + "} matched by \\end{" + end.name + "}", endNameToken); + } // $FlowFixMe, "environment" handler returns an environment ParseNode + + + return result; + } + + return { + type: "environment", + mode: parser.mode, + name: envName, + nameGroup + }; + } + +}); + +// TODO(kevinb): implement \\sl and \\sc + +var htmlBuilder$5 = (group, options) => { + var font = group.font; + var newOptions = options.withFont(font); + return buildGroup$1(group.body, newOptions); +}; + +var mathmlBuilder$4 = (group, options) => { + var font = group.font; + var newOptions = options.withFont(font); + return buildGroup(group.body, newOptions); +}; + +var fontAliases = { + "\\Bbb": "\\mathbb", + "\\bold": "\\mathbf", + "\\frak": "\\mathfrak", + "\\bm": "\\boldsymbol" +}; +defineFunction({ + type: "font", + names: [// styles, except \boldsymbol defined below + "\\mathrm", "\\mathit", "\\mathbf", "\\mathnormal", "\\mathsfit", // families + "\\mathbb", "\\mathcal", "\\mathfrak", "\\mathscr", "\\mathsf", "\\mathtt", // aliases, except \bm defined below + "\\Bbb", "\\bold", "\\frak"], + props: { + numArgs: 1, + allowedInArgument: true + }, + handler: (_ref, args) => { + var { + parser, + funcName + } = _ref; + var body = normalizeArgument(args[0]); + var func = funcName; + + if (func in fontAliases) { + func = fontAliases[func]; + } + + return { + type: "font", + mode: parser.mode, + font: func.slice(1), + body + }; + }, + htmlBuilder: htmlBuilder$5, + mathmlBuilder: mathmlBuilder$4 +}); +defineFunction({ + type: "mclass", + names: ["\\boldsymbol", "\\bm"], + props: { + numArgs: 1 + }, + handler: (_ref2, args) => { + var { + parser + } = _ref2; + var body = args[0]; + var isCharacterBox = utils.isCharacterBox(body); // amsbsy.sty's \boldsymbol uses \binrel spacing to inherit the + // argument's bin|rel|ord status + + return { + type: "mclass", + mode: parser.mode, + mclass: binrelClass(body), + body: [{ + type: "font", + mode: parser.mode, + font: "boldsymbol", + body + }], + isCharacterBox: isCharacterBox + }; + } +}); // Old font changing functions + +defineFunction({ + type: "font", + names: ["\\rm", "\\sf", "\\tt", "\\bf", "\\it", "\\cal"], + props: { + numArgs: 0, + allowedInText: true + }, + handler: (_ref3, args) => { + var { + parser, + funcName, + breakOnTokenText + } = _ref3; + var { + mode + } = parser; + var body = parser.parseExpression(true, breakOnTokenText); + var style = "math" + funcName.slice(1); + return { + type: "font", + mode: mode, + font: style, + body: { + type: "ordgroup", + mode: parser.mode, + body + } + }; + }, + htmlBuilder: htmlBuilder$5, + mathmlBuilder: mathmlBuilder$4 +}); + +var adjustStyle = (size, originalStyle) => { + // Figure out what style this fraction should be in based on the + // function used + var style = originalStyle; + + if (size === "display") { + // Get display style as a default. + // If incoming style is sub/sup, use style.text() to get correct size. + style = style.id >= Style$1.SCRIPT.id ? style.text() : Style$1.DISPLAY; + } else if (size === "text" && style.size === Style$1.DISPLAY.size) { + // We're in a \tfrac but incoming style is displaystyle, so: + style = Style$1.TEXT; + } else if (size === "script") { + style = Style$1.SCRIPT; + } else if (size === "scriptscript") { + style = Style$1.SCRIPTSCRIPT; + } + + return style; +}; + +var htmlBuilder$4 = (group, options) => { + // Fractions are handled in the TeXbook on pages 444-445, rules 15(a-e). + var style = adjustStyle(group.size, options.style); + var nstyle = style.fracNum(); + var dstyle = style.fracDen(); + var newOptions; + newOptions = options.havingStyle(nstyle); + var numerm = buildGroup$1(group.numer, newOptions, options); + + if (group.continued) { + // \cfrac inserts a \strut into the numerator. + // Get \strut dimensions from TeXbook page 353. + var hStrut = 8.5 / options.fontMetrics().ptPerEm; + var dStrut = 3.5 / options.fontMetrics().ptPerEm; + numerm.height = numerm.height < hStrut ? hStrut : numerm.height; + numerm.depth = numerm.depth < dStrut ? dStrut : numerm.depth; + } + + newOptions = options.havingStyle(dstyle); + var denomm = buildGroup$1(group.denom, newOptions, options); + var rule; + var ruleWidth; + var ruleSpacing; + + if (group.hasBarLine) { + if (group.barSize) { + ruleWidth = calculateSize(group.barSize, options); + rule = buildCommon.makeLineSpan("frac-line", options, ruleWidth); + } else { + rule = buildCommon.makeLineSpan("frac-line", options); + } + + ruleWidth = rule.height; + ruleSpacing = rule.height; + } else { + rule = null; + ruleWidth = 0; + ruleSpacing = options.fontMetrics().defaultRuleThickness; + } // Rule 15b + + + var numShift; + var clearance; + var denomShift; + + if (style.size === Style$1.DISPLAY.size || group.size === "display") { + numShift = options.fontMetrics().num1; + + if (ruleWidth > 0) { + clearance = 3 * ruleSpacing; + } else { + clearance = 7 * ruleSpacing; + } + + denomShift = options.fontMetrics().denom1; + } else { + if (ruleWidth > 0) { + numShift = options.fontMetrics().num2; + clearance = ruleSpacing; + } else { + numShift = options.fontMetrics().num3; + clearance = 3 * ruleSpacing; + } + + denomShift = options.fontMetrics().denom2; + } + + var frac; + + if (!rule) { + // Rule 15c + var candidateClearance = numShift - numerm.depth - (denomm.height - denomShift); + + if (candidateClearance < clearance) { + numShift += 0.5 * (clearance - candidateClearance); + denomShift += 0.5 * (clearance - candidateClearance); + } + + frac = buildCommon.makeVList({ + positionType: "individualShift", + children: [{ + type: "elem", + elem: denomm, + shift: denomShift + }, { + type: "elem", + elem: numerm, + shift: -numShift + }] + }, options); + } else { + // Rule 15d + var axisHeight = options.fontMetrics().axisHeight; + + if (numShift - numerm.depth - (axisHeight + 0.5 * ruleWidth) < clearance) { + numShift += clearance - (numShift - numerm.depth - (axisHeight + 0.5 * ruleWidth)); + } + + if (axisHeight - 0.5 * ruleWidth - (denomm.height - denomShift) < clearance) { + denomShift += clearance - (axisHeight - 0.5 * ruleWidth - (denomm.height - denomShift)); + } + + var midShift = -(axisHeight - 0.5 * ruleWidth); + frac = buildCommon.makeVList({ + positionType: "individualShift", + children: [{ + type: "elem", + elem: denomm, + shift: denomShift + }, { + type: "elem", + elem: rule, + shift: midShift + }, { + type: "elem", + elem: numerm, + shift: -numShift + }] + }, options); + } // Since we manually change the style sometimes (with \dfrac or \tfrac), + // account for the possible size change here. + + + newOptions = options.havingStyle(style); + frac.height *= newOptions.sizeMultiplier / options.sizeMultiplier; + frac.depth *= newOptions.sizeMultiplier / options.sizeMultiplier; // Rule 15e + + var delimSize; + + if (style.size === Style$1.DISPLAY.size) { + delimSize = options.fontMetrics().delim1; + } else if (style.size === Style$1.SCRIPTSCRIPT.size) { + delimSize = options.havingStyle(Style$1.SCRIPT).fontMetrics().delim2; + } else { + delimSize = options.fontMetrics().delim2; + } + + var leftDelim; + var rightDelim; + + if (group.leftDelim == null) { + leftDelim = makeNullDelimiter(options, ["mopen"]); + } else { + leftDelim = delimiter.customSizedDelim(group.leftDelim, delimSize, true, options.havingStyle(style), group.mode, ["mopen"]); + } + + if (group.continued) { + rightDelim = buildCommon.makeSpan([]); // zero width for \cfrac + } else if (group.rightDelim == null) { + rightDelim = makeNullDelimiter(options, ["mclose"]); + } else { + rightDelim = delimiter.customSizedDelim(group.rightDelim, delimSize, true, options.havingStyle(style), group.mode, ["mclose"]); + } + + return buildCommon.makeSpan(["mord"].concat(newOptions.sizingClasses(options)), [leftDelim, buildCommon.makeSpan(["mfrac"], [frac]), rightDelim], options); +}; + +var mathmlBuilder$3 = (group, options) => { + var node = new mathMLTree.MathNode("mfrac", [buildGroup(group.numer, options), buildGroup(group.denom, options)]); + + if (!group.hasBarLine) { + node.setAttribute("linethickness", "0px"); + } else if (group.barSize) { + var ruleWidth = calculateSize(group.barSize, options); + node.setAttribute("linethickness", makeEm(ruleWidth)); + } + + var style = adjustStyle(group.size, options.style); + + if (style.size !== options.style.size) { + node = new mathMLTree.MathNode("mstyle", [node]); + var isDisplay = style.size === Style$1.DISPLAY.size ? "true" : "false"; + node.setAttribute("displaystyle", isDisplay); + node.setAttribute("scriptlevel", "0"); + } + + if (group.leftDelim != null || group.rightDelim != null) { + var withDelims = []; + + if (group.leftDelim != null) { + var leftOp = new mathMLTree.MathNode("mo", [new mathMLTree.TextNode(group.leftDelim.replace("\\", ""))]); + leftOp.setAttribute("fence", "true"); + withDelims.push(leftOp); + } + + withDelims.push(node); + + if (group.rightDelim != null) { + var rightOp = new mathMLTree.MathNode("mo", [new mathMLTree.TextNode(group.rightDelim.replace("\\", ""))]); + rightOp.setAttribute("fence", "true"); + withDelims.push(rightOp); + } + + return makeRow(withDelims); + } + + return node; +}; + +defineFunction({ + type: "genfrac", + names: ["\\dfrac", "\\frac", "\\tfrac", "\\dbinom", "\\binom", "\\tbinom", "\\\\atopfrac", // can’t be entered directly + "\\\\bracefrac", "\\\\brackfrac" // ditto + ], + props: { + numArgs: 2, + allowedInArgument: true + }, + handler: (_ref, args) => { + var { + parser, + funcName + } = _ref; + var numer = args[0]; + var denom = args[1]; + var hasBarLine; + var leftDelim = null; + var rightDelim = null; + var size = "auto"; + + switch (funcName) { + case "\\dfrac": + case "\\frac": + case "\\tfrac": + hasBarLine = true; + break; + + case "\\\\atopfrac": + hasBarLine = false; + break; + + case "\\dbinom": + case "\\binom": + case "\\tbinom": + hasBarLine = false; + leftDelim = "("; + rightDelim = ")"; + break; + + case "\\\\bracefrac": + hasBarLine = false; + leftDelim = "\\{"; + rightDelim = "\\}"; + break; + + case "\\\\brackfrac": + hasBarLine = false; + leftDelim = "["; + rightDelim = "]"; + break; + + default: + throw new Error("Unrecognized genfrac command"); + } + + switch (funcName) { + case "\\dfrac": + case "\\dbinom": + size = "display"; + break; + + case "\\tfrac": + case "\\tbinom": + size = "text"; + break; + } + + return { + type: "genfrac", + mode: parser.mode, + continued: false, + numer, + denom, + hasBarLine, + leftDelim, + rightDelim, + size, + barSize: null + }; + }, + htmlBuilder: htmlBuilder$4, + mathmlBuilder: mathmlBuilder$3 +}); +defineFunction({ + type: "genfrac", + names: ["\\cfrac"], + props: { + numArgs: 2 + }, + handler: (_ref2, args) => { + var { + parser, + funcName + } = _ref2; + var numer = args[0]; + var denom = args[1]; + return { + type: "genfrac", + mode: parser.mode, + continued: true, + numer, + denom, + hasBarLine: true, + leftDelim: null, + rightDelim: null, + size: "display", + barSize: null + }; + } +}); // Infix generalized fractions -- these are not rendered directly, but replaced +// immediately by one of the variants above. + +defineFunction({ + type: "infix", + names: ["\\over", "\\choose", "\\atop", "\\brace", "\\brack"], + props: { + numArgs: 0, + infix: true + }, + + handler(_ref3) { + var { + parser, + funcName, + token + } = _ref3; + var replaceWith; + + switch (funcName) { + case "\\over": + replaceWith = "\\frac"; + break; + + case "\\choose": + replaceWith = "\\binom"; + break; + + case "\\atop": + replaceWith = "\\\\atopfrac"; + break; + + case "\\brace": + replaceWith = "\\\\bracefrac"; + break; + + case "\\brack": + replaceWith = "\\\\brackfrac"; + break; + + default: + throw new Error("Unrecognized infix genfrac command"); + } + + return { + type: "infix", + mode: parser.mode, + replaceWith, + token + }; + } + +}); +var stylArray = ["display", "text", "script", "scriptscript"]; + +var delimFromValue = function delimFromValue(delimString) { + var delim = null; + + if (delimString.length > 0) { + delim = delimString; + delim = delim === "." ? null : delim; + } + + return delim; +}; + +defineFunction({ + type: "genfrac", + names: ["\\genfrac"], + props: { + numArgs: 6, + allowedInArgument: true, + argTypes: ["math", "math", "size", "text", "math", "math"] + }, + + handler(_ref4, args) { + var { + parser + } = _ref4; + var numer = args[4]; + var denom = args[5]; // Look into the parse nodes to get the desired delimiters. + + var leftNode = normalizeArgument(args[0]); + var leftDelim = leftNode.type === "atom" && leftNode.family === "open" ? delimFromValue(leftNode.text) : null; + var rightNode = normalizeArgument(args[1]); + var rightDelim = rightNode.type === "atom" && rightNode.family === "close" ? delimFromValue(rightNode.text) : null; + var barNode = assertNodeType(args[2], "size"); + var hasBarLine; + var barSize = null; + + if (barNode.isBlank) { + // \genfrac acts differently than \above. + // \genfrac treats an empty size group as a signal to use a + // standard bar size. \above would see size = 0 and omit the bar. + hasBarLine = true; + } else { + barSize = barNode.value; + hasBarLine = barSize.number > 0; + } // Find out if we want displaystyle, textstyle, etc. + + + var size = "auto"; + var styl = args[3]; + + if (styl.type === "ordgroup") { + if (styl.body.length > 0) { + var textOrd = assertNodeType(styl.body[0], "textord"); + size = stylArray[Number(textOrd.text)]; + } + } else { + styl = assertNodeType(styl, "textord"); + size = stylArray[Number(styl.text)]; + } + + return { + type: "genfrac", + mode: parser.mode, + numer, + denom, + continued: false, + hasBarLine, + barSize, + leftDelim, + rightDelim, + size + }; + }, + + htmlBuilder: htmlBuilder$4, + mathmlBuilder: mathmlBuilder$3 +}); // \above is an infix fraction that also defines a fraction bar size. + +defineFunction({ + type: "infix", + names: ["\\above"], + props: { + numArgs: 1, + argTypes: ["size"], + infix: true + }, + + handler(_ref5, args) { + var { + parser, + funcName, + token + } = _ref5; + return { + type: "infix", + mode: parser.mode, + replaceWith: "\\\\abovefrac", + size: assertNodeType(args[0], "size").value, + token + }; + } + +}); +defineFunction({ + type: "genfrac", + names: ["\\\\abovefrac"], + props: { + numArgs: 3, + argTypes: ["math", "size", "math"] + }, + handler: (_ref6, args) => { + var { + parser, + funcName + } = _ref6; + var numer = args[0]; + var barSize = assert(assertNodeType(args[1], "infix").size); + var denom = args[2]; + var hasBarLine = barSize.number > 0; + return { + type: "genfrac", + mode: parser.mode, + numer, + denom, + continued: false, + hasBarLine, + barSize, + leftDelim: null, + rightDelim: null, + size: "auto" + }; + }, + htmlBuilder: htmlBuilder$4, + mathmlBuilder: mathmlBuilder$3 +}); + +// NOTE: Unlike most `htmlBuilder`s, this one handles not only "horizBrace", but +// also "supsub" since an over/underbrace can affect super/subscripting. +var htmlBuilder$3 = (grp, options) => { + var style = options.style; // Pull out the `ParseNode<"horizBrace">` if `grp` is a "supsub" node. + + var supSubGroup; + var group; + + if (grp.type === "supsub") { + // Ref: LaTeX source2e: }}}}\limits} + // i.e. LaTeX treats the brace similar to an op and passes it + // with \limits, so we need to assign supsub style. + supSubGroup = grp.sup ? buildGroup$1(grp.sup, options.havingStyle(style.sup()), options) : buildGroup$1(grp.sub, options.havingStyle(style.sub()), options); + group = assertNodeType(grp.base, "horizBrace"); + } else { + group = assertNodeType(grp, "horizBrace"); + } // Build the base group + + + var body = buildGroup$1(group.base, options.havingBaseStyle(Style$1.DISPLAY)); // Create the stretchy element + + var braceBody = stretchy.svgSpan(group, options); // Generate the vlist, with the appropriate kerns ┏━━━━━━━━┓ + // This first vlist contains the content and the brace: equation + + var vlist; + + if (group.isOver) { + vlist = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: body + }, { + type: "kern", + size: 0.1 + }, { + type: "elem", + elem: braceBody + }] + }, options); // $FlowFixMe: Replace this with passing "svg-align" into makeVList. + + vlist.children[0].children[0].children[1].classes.push("svg-align"); + } else { + vlist = buildCommon.makeVList({ + positionType: "bottom", + positionData: body.depth + 0.1 + braceBody.height, + children: [{ + type: "elem", + elem: braceBody + }, { + type: "kern", + size: 0.1 + }, { + type: "elem", + elem: body + }] + }, options); // $FlowFixMe: Replace this with passing "svg-align" into makeVList. + + vlist.children[0].children[0].children[0].classes.push("svg-align"); + } + + if (supSubGroup) { + // To write the supsub, wrap the first vlist in another vlist: + // They can't all go in the same vlist, because the note might be + // wider than the equation. We want the equation to control the + // brace width. + // note long note long note + // ┏━━━━━━━━┓ or ┏━━━┓ not ┏━━━━━━━━━┓ + // equation eqn eqn + var vSpan = buildCommon.makeSpan(["mord", group.isOver ? "mover" : "munder"], [vlist], options); + + if (group.isOver) { + vlist = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: vSpan + }, { + type: "kern", + size: 0.2 + }, { + type: "elem", + elem: supSubGroup + }] + }, options); + } else { + vlist = buildCommon.makeVList({ + positionType: "bottom", + positionData: vSpan.depth + 0.2 + supSubGroup.height + supSubGroup.depth, + children: [{ + type: "elem", + elem: supSubGroup + }, { + type: "kern", + size: 0.2 + }, { + type: "elem", + elem: vSpan + }] + }, options); + } + } + + return buildCommon.makeSpan(["mord", group.isOver ? "mover" : "munder"], [vlist], options); +}; + +var mathmlBuilder$2 = (group, options) => { + var accentNode = stretchy.mathMLnode(group.label); + return new mathMLTree.MathNode(group.isOver ? "mover" : "munder", [buildGroup(group.base, options), accentNode]); +}; // Horizontal stretchy braces + + +defineFunction({ + type: "horizBrace", + names: ["\\overbrace", "\\underbrace"], + props: { + numArgs: 1 + }, + + handler(_ref, args) { + var { + parser, + funcName + } = _ref; + return { + type: "horizBrace", + mode: parser.mode, + label: funcName, + isOver: /^\\over/.test(funcName), + base: args[0] + }; + }, + + htmlBuilder: htmlBuilder$3, + mathmlBuilder: mathmlBuilder$2 +}); + +defineFunction({ + type: "href", + names: ["\\href"], + props: { + numArgs: 2, + argTypes: ["url", "original"], + allowedInText: true + }, + handler: (_ref, args) => { + var { + parser + } = _ref; + var body = args[1]; + var href = assertNodeType(args[0], "url").url; + + if (!parser.settings.isTrusted({ + command: "\\href", + url: href + })) { + return parser.formatUnsupportedCmd("\\href"); + } + + return { + type: "href", + mode: parser.mode, + href, + body: ordargument(body) + }; + }, + htmlBuilder: (group, options) => { + var elements = buildExpression$1(group.body, options, false); + return buildCommon.makeAnchor(group.href, [], elements, options); + }, + mathmlBuilder: (group, options) => { + var math = buildExpressionRow(group.body, options); + + if (!(math instanceof MathNode)) { + math = new MathNode("mrow", [math]); + } + + math.setAttribute("href", group.href); + return math; + } +}); +defineFunction({ + type: "href", + names: ["\\url"], + props: { + numArgs: 1, + argTypes: ["url"], + allowedInText: true + }, + handler: (_ref2, args) => { + var { + parser + } = _ref2; + var href = assertNodeType(args[0], "url").url; + + if (!parser.settings.isTrusted({ + command: "\\url", + url: href + })) { + return parser.formatUnsupportedCmd("\\url"); + } + + var chars = []; + + for (var i = 0; i < href.length; i++) { + var c = href[i]; + + if (c === "~") { + c = "\\textasciitilde"; + } + + chars.push({ + type: "textord", + mode: "text", + text: c + }); + } + + var body = { + type: "text", + mode: parser.mode, + font: "\\texttt", + body: chars + }; + return { + type: "href", + mode: parser.mode, + href, + body: ordargument(body) + }; + } +}); + +// In LaTeX, \vcenter can act only on a box, as in +// \vcenter{\hbox{$\frac{a+b}{\dfrac{c}{d}}$}} +// This function by itself doesn't do anything but prevent a soft line break. + +defineFunction({ + type: "hbox", + names: ["\\hbox"], + props: { + numArgs: 1, + argTypes: ["text"], + allowedInText: true, + primitive: true + }, + + handler(_ref, args) { + var { + parser + } = _ref; + return { + type: "hbox", + mode: parser.mode, + body: ordargument(args[0]) + }; + }, + + htmlBuilder(group, options) { + var elements = buildExpression$1(group.body, options, false); + return buildCommon.makeFragment(elements); + }, + + mathmlBuilder(group, options) { + return new mathMLTree.MathNode("mrow", buildExpression(group.body, options)); + } + +}); + +defineFunction({ + type: "html", + names: ["\\htmlClass", "\\htmlId", "\\htmlStyle", "\\htmlData"], + props: { + numArgs: 2, + argTypes: ["raw", "original"], + allowedInText: true + }, + handler: (_ref, args) => { + var { + parser, + funcName, + token + } = _ref; + var value = assertNodeType(args[0], "raw").string; + var body = args[1]; + + if (parser.settings.strict) { + parser.settings.reportNonstrict("htmlExtension", "HTML extension is disabled on strict mode"); + } + + var trustContext; + var attributes = {}; + + switch (funcName) { + case "\\htmlClass": + attributes.class = value; + trustContext = { + command: "\\htmlClass", + class: value + }; + break; + + case "\\htmlId": + attributes.id = value; + trustContext = { + command: "\\htmlId", + id: value + }; + break; + + case "\\htmlStyle": + attributes.style = value; + trustContext = { + command: "\\htmlStyle", + style: value + }; + break; + + case "\\htmlData": + { + var data = value.split(","); + + for (var i = 0; i < data.length; i++) { + var keyVal = data[i].split("="); + + if (keyVal.length !== 2) { + throw new ParseError("Error parsing key-value for \\htmlData"); + } + + attributes["data-" + keyVal[0].trim()] = keyVal[1].trim(); + } + + trustContext = { + command: "\\htmlData", + attributes + }; + break; + } + + default: + throw new Error("Unrecognized html command"); + } + + if (!parser.settings.isTrusted(trustContext)) { + return parser.formatUnsupportedCmd(funcName); + } + + return { + type: "html", + mode: parser.mode, + attributes, + body: ordargument(body) + }; + }, + htmlBuilder: (group, options) => { + var elements = buildExpression$1(group.body, options, false); + var classes = ["enclosing"]; + + if (group.attributes.class) { + classes.push(...group.attributes.class.trim().split(/\s+/)); + } + + var span = buildCommon.makeSpan(classes, elements, options); + + for (var attr in group.attributes) { + if (attr !== "class" && group.attributes.hasOwnProperty(attr)) { + span.setAttribute(attr, group.attributes[attr]); + } + } + + return span; + }, + mathmlBuilder: (group, options) => { + return buildExpressionRow(group.body, options); + } +}); + +defineFunction({ + type: "htmlmathml", + names: ["\\html@mathml"], + props: { + numArgs: 2, + allowedInText: true + }, + handler: (_ref, args) => { + var { + parser + } = _ref; + return { + type: "htmlmathml", + mode: parser.mode, + html: ordargument(args[0]), + mathml: ordargument(args[1]) + }; + }, + htmlBuilder: (group, options) => { + var elements = buildExpression$1(group.html, options, false); + return buildCommon.makeFragment(elements); + }, + mathmlBuilder: (group, options) => { + return buildExpressionRow(group.mathml, options); + } +}); + +var sizeData = function sizeData(str) { + if (/^[-+]? *(\d+(\.\d*)?|\.\d+)$/.test(str)) { + // str is a number with no unit specified. + // default unit is bp, per graphix package. + return { + number: +str, + unit: "bp" + }; + } else { + var match = /([-+]?) *(\d+(?:\.\d*)?|\.\d+) *([a-z]{2})/.exec(str); + + if (!match) { + throw new ParseError("Invalid size: '" + str + "' in \\includegraphics"); + } + + var data = { + number: +(match[1] + match[2]), + // sign + magnitude, cast to number + unit: match[3] + }; + + if (!validUnit(data)) { + throw new ParseError("Invalid unit: '" + data.unit + "' in \\includegraphics."); + } + + return data; + } +}; + +defineFunction({ + type: "includegraphics", + names: ["\\includegraphics"], + props: { + numArgs: 1, + numOptionalArgs: 1, + argTypes: ["raw", "url"], + allowedInText: false + }, + handler: (_ref, args, optArgs) => { + var { + parser + } = _ref; + var width = { + number: 0, + unit: "em" + }; + var height = { + number: 0.9, + unit: "em" + }; // sorta character sized. + + var totalheight = { + number: 0, + unit: "em" + }; + var alt = ""; + + if (optArgs[0]) { + var attributeStr = assertNodeType(optArgs[0], "raw").string; // Parser.js does not parse key/value pairs. We get a string. + + var attributes = attributeStr.split(","); + + for (var i = 0; i < attributes.length; i++) { + var keyVal = attributes[i].split("="); + + if (keyVal.length === 2) { + var str = keyVal[1].trim(); + + switch (keyVal[0].trim()) { + case "alt": + alt = str; + break; + + case "width": + width = sizeData(str); + break; + + case "height": + height = sizeData(str); + break; + + case "totalheight": + totalheight = sizeData(str); + break; + + default: + throw new ParseError("Invalid key: '" + keyVal[0] + "' in \\includegraphics."); + } + } + } + } + + var src = assertNodeType(args[0], "url").url; + + if (alt === "") { + // No alt given. Use the file name. Strip away the path. + alt = src; + alt = alt.replace(/^.*[\\/]/, ''); + alt = alt.substring(0, alt.lastIndexOf('.')); + } + + if (!parser.settings.isTrusted({ + command: "\\includegraphics", + url: src + })) { + return parser.formatUnsupportedCmd("\\includegraphics"); + } + + return { + type: "includegraphics", + mode: parser.mode, + alt: alt, + width: width, + height: height, + totalheight: totalheight, + src: src + }; + }, + htmlBuilder: (group, options) => { + var height = calculateSize(group.height, options); + var depth = 0; + + if (group.totalheight.number > 0) { + depth = calculateSize(group.totalheight, options) - height; + } + + var width = 0; + + if (group.width.number > 0) { + width = calculateSize(group.width, options); + } + + var style = { + height: makeEm(height + depth) + }; + + if (width > 0) { + style.width = makeEm(width); + } + + if (depth > 0) { + style.verticalAlign = makeEm(-depth); + } + + var node = new Img(group.src, group.alt, style); + node.height = height; + node.depth = depth; + return node; + }, + mathmlBuilder: (group, options) => { + var node = new mathMLTree.MathNode("mglyph", []); + node.setAttribute("alt", group.alt); + var height = calculateSize(group.height, options); + var depth = 0; + + if (group.totalheight.number > 0) { + depth = calculateSize(group.totalheight, options) - height; + node.setAttribute("valign", makeEm(-depth)); + } + + node.setAttribute("height", makeEm(height + depth)); + + if (group.width.number > 0) { + var width = calculateSize(group.width, options); + node.setAttribute("width", makeEm(width)); + } + + node.setAttribute("src", group.src); + return node; + } +}); + +// Horizontal spacing commands + +defineFunction({ + type: "kern", + names: ["\\kern", "\\mkern", "\\hskip", "\\mskip"], + props: { + numArgs: 1, + argTypes: ["size"], + primitive: true, + allowedInText: true + }, + + handler(_ref, args) { + var { + parser, + funcName + } = _ref; + var size = assertNodeType(args[0], "size"); + + if (parser.settings.strict) { + var mathFunction = funcName[1] === 'm'; // \mkern, \mskip + + var muUnit = size.value.unit === 'mu'; + + if (mathFunction) { + if (!muUnit) { + parser.settings.reportNonstrict("mathVsTextUnits", "LaTeX's " + funcName + " supports only mu units, " + ("not " + size.value.unit + " units")); + } + + if (parser.mode !== "math") { + parser.settings.reportNonstrict("mathVsTextUnits", "LaTeX's " + funcName + " works only in math mode"); + } + } else { + // !mathFunction + if (muUnit) { + parser.settings.reportNonstrict("mathVsTextUnits", "LaTeX's " + funcName + " doesn't support mu units"); + } + } + } + + return { + type: "kern", + mode: parser.mode, + dimension: size.value + }; + }, + + htmlBuilder(group, options) { + return buildCommon.makeGlue(group.dimension, options); + }, + + mathmlBuilder(group, options) { + var dimension = calculateSize(group.dimension, options); + return new mathMLTree.SpaceNode(dimension); + } + +}); + +// Horizontal overlap functions +defineFunction({ + type: "lap", + names: ["\\mathllap", "\\mathrlap", "\\mathclap"], + props: { + numArgs: 1, + allowedInText: true + }, + handler: (_ref, args) => { + var { + parser, + funcName + } = _ref; + var body = args[0]; + return { + type: "lap", + mode: parser.mode, + alignment: funcName.slice(5), + body + }; + }, + htmlBuilder: (group, options) => { + // mathllap, mathrlap, mathclap + var inner; + + if (group.alignment === "clap") { + // ref: https://www.math.lsu.edu/~aperlis/publications/mathclap/ + inner = buildCommon.makeSpan([], [buildGroup$1(group.body, options)]); // wrap, since CSS will center a .clap > .inner > span + + inner = buildCommon.makeSpan(["inner"], [inner], options); + } else { + inner = buildCommon.makeSpan(["inner"], [buildGroup$1(group.body, options)]); + } + + var fix = buildCommon.makeSpan(["fix"], []); + var node = buildCommon.makeSpan([group.alignment], [inner, fix], options); // At this point, we have correctly set horizontal alignment of the + // two items involved in the lap. + // Next, use a strut to set the height of the HTML bounding box. + // Otherwise, a tall argument may be misplaced. + // This code resolved issue #1153 + + var strut = buildCommon.makeSpan(["strut"]); + strut.style.height = makeEm(node.height + node.depth); + + if (node.depth) { + strut.style.verticalAlign = makeEm(-node.depth); + } + + node.children.unshift(strut); // Next, prevent vertical misplacement when next to something tall. + // This code resolves issue #1234 + + node = buildCommon.makeSpan(["thinbox"], [node], options); + return buildCommon.makeSpan(["mord", "vbox"], [node], options); + }, + mathmlBuilder: (group, options) => { + // mathllap, mathrlap, mathclap + var node = new mathMLTree.MathNode("mpadded", [buildGroup(group.body, options)]); + + if (group.alignment !== "rlap") { + var offset = group.alignment === "llap" ? "-1" : "-0.5"; + node.setAttribute("lspace", offset + "width"); + } + + node.setAttribute("width", "0px"); + return node; + } +}); + +defineFunction({ + type: "styling", + names: ["\\(", "$"], + props: { + numArgs: 0, + allowedInText: true, + allowedInMath: false + }, + + handler(_ref, args) { + var { + funcName, + parser + } = _ref; + var outerMode = parser.mode; + parser.switchMode("math"); + var close = funcName === "\\(" ? "\\)" : "$"; + var body = parser.parseExpression(false, close); + parser.expect(close); + parser.switchMode(outerMode); + return { + type: "styling", + mode: parser.mode, + style: "text", + body + }; + } + +}); // Check for extra closing math delimiters + +defineFunction({ + type: "text", + // Doesn't matter what this is. + names: ["\\)", "\\]"], + props: { + numArgs: 0, + allowedInText: true, + allowedInMath: false + }, + + handler(context, args) { + throw new ParseError("Mismatched " + context.funcName); + } + +}); + +var chooseMathStyle = (group, options) => { + switch (options.style.size) { + case Style$1.DISPLAY.size: + return group.display; + + case Style$1.TEXT.size: + return group.text; + + case Style$1.SCRIPT.size: + return group.script; + + case Style$1.SCRIPTSCRIPT.size: + return group.scriptscript; + + default: + return group.text; + } +}; + +defineFunction({ + type: "mathchoice", + names: ["\\mathchoice"], + props: { + numArgs: 4, + primitive: true + }, + handler: (_ref, args) => { + var { + parser + } = _ref; + return { + type: "mathchoice", + mode: parser.mode, + display: ordargument(args[0]), + text: ordargument(args[1]), + script: ordargument(args[2]), + scriptscript: ordargument(args[3]) + }; + }, + htmlBuilder: (group, options) => { + var body = chooseMathStyle(group, options); + var elements = buildExpression$1(body, options, false); + return buildCommon.makeFragment(elements); + }, + mathmlBuilder: (group, options) => { + var body = chooseMathStyle(group, options); + return buildExpressionRow(body, options); + } +}); + +var assembleSupSub = (base, supGroup, subGroup, options, style, slant, baseShift) => { + base = buildCommon.makeSpan([], [base]); + var subIsSingleCharacter = subGroup && utils.isCharacterBox(subGroup); + var sub; + var sup; // We manually have to handle the superscripts and subscripts. This, + // aside from the kern calculations, is copied from supsub. + + if (supGroup) { + var elem = buildGroup$1(supGroup, options.havingStyle(style.sup()), options); + sup = { + elem, + kern: Math.max(options.fontMetrics().bigOpSpacing1, options.fontMetrics().bigOpSpacing3 - elem.depth) + }; + } + + if (subGroup) { + var _elem = buildGroup$1(subGroup, options.havingStyle(style.sub()), options); + + sub = { + elem: _elem, + kern: Math.max(options.fontMetrics().bigOpSpacing2, options.fontMetrics().bigOpSpacing4 - _elem.height) + }; + } // Build the final group as a vlist of the possible subscript, base, + // and possible superscript. + + + var finalGroup; + + if (sup && sub) { + var bottom = options.fontMetrics().bigOpSpacing5 + sub.elem.height + sub.elem.depth + sub.kern + base.depth + baseShift; + finalGroup = buildCommon.makeVList({ + positionType: "bottom", + positionData: bottom, + children: [{ + type: "kern", + size: options.fontMetrics().bigOpSpacing5 + }, { + type: "elem", + elem: sub.elem, + marginLeft: makeEm(-slant) + }, { + type: "kern", + size: sub.kern + }, { + type: "elem", + elem: base + }, { + type: "kern", + size: sup.kern + }, { + type: "elem", + elem: sup.elem, + marginLeft: makeEm(slant) + }, { + type: "kern", + size: options.fontMetrics().bigOpSpacing5 + }] + }, options); + } else if (sub) { + var top = base.height - baseShift; // Shift the limits by the slant of the symbol. Note + // that we are supposed to shift the limits by 1/2 of the slant, + // but since we are centering the limits adding a full slant of + // margin will shift by 1/2 that. + + finalGroup = buildCommon.makeVList({ + positionType: "top", + positionData: top, + children: [{ + type: "kern", + size: options.fontMetrics().bigOpSpacing5 + }, { + type: "elem", + elem: sub.elem, + marginLeft: makeEm(-slant) + }, { + type: "kern", + size: sub.kern + }, { + type: "elem", + elem: base + }] + }, options); + } else if (sup) { + var _bottom = base.depth + baseShift; + + finalGroup = buildCommon.makeVList({ + positionType: "bottom", + positionData: _bottom, + children: [{ + type: "elem", + elem: base + }, { + type: "kern", + size: sup.kern + }, { + type: "elem", + elem: sup.elem, + marginLeft: makeEm(slant) + }, { + type: "kern", + size: options.fontMetrics().bigOpSpacing5 + }] + }, options); + } else { + // This case probably shouldn't occur (this would mean the + // supsub was sending us a group with no superscript or + // subscript) but be safe. + return base; + } + + var parts = [finalGroup]; + + if (sub && slant !== 0 && !subIsSingleCharacter) { + // A negative margin-left was applied to the lower limit. + // Avoid an overlap by placing a spacer on the left on the group. + var spacer = buildCommon.makeSpan(["mspace"], [], options); + spacer.style.marginRight = makeEm(slant); + parts.unshift(spacer); + } + + return buildCommon.makeSpan(["mop", "op-limits"], parts, options); +}; + +// Limits, symbols +// Most operators have a large successor symbol, but these don't. +var noSuccessor = ["\\smallint"]; // NOTE: Unlike most `htmlBuilder`s, this one handles not only "op", but also +// "supsub" since some of them (like \int) can affect super/subscripting. + +var htmlBuilder$2 = (grp, options) => { + // Operators are handled in the TeXbook pg. 443-444, rule 13(a). + var supGroup; + var subGroup; + var hasLimits = false; + var group; + + if (grp.type === "supsub") { + // If we have limits, supsub will pass us its group to handle. Pull + // out the superscript and subscript and set the group to the op in + // its base. + supGroup = grp.sup; + subGroup = grp.sub; + group = assertNodeType(grp.base, "op"); + hasLimits = true; + } else { + group = assertNodeType(grp, "op"); + } + + var style = options.style; + var large = false; + + if (style.size === Style$1.DISPLAY.size && group.symbol && !utils.contains(noSuccessor, group.name)) { + // Most symbol operators get larger in displaystyle (rule 13) + large = true; + } + + var base; + + if (group.symbol) { + // If this is a symbol, create the symbol. + var fontName = large ? "Size2-Regular" : "Size1-Regular"; + var stash = ""; + + if (group.name === "\\oiint" || group.name === "\\oiiint") { + // No font glyphs yet, so use a glyph w/o the oval. + // TODO: When font glyphs are available, delete this code. + stash = group.name.slice(1); + group.name = stash === "oiint" ? "\\iint" : "\\iiint"; + } + + base = buildCommon.makeSymbol(group.name, fontName, "math", options, ["mop", "op-symbol", large ? "large-op" : "small-op"]); + + if (stash.length > 0) { + // We're in \oiint or \oiiint. Overlay the oval. + // TODO: When font glyphs are available, delete this code. + var italic = base.italic; + var oval = buildCommon.staticSvg(stash + "Size" + (large ? "2" : "1"), options); + base = buildCommon.makeVList({ + positionType: "individualShift", + children: [{ + type: "elem", + elem: base, + shift: 0 + }, { + type: "elem", + elem: oval, + shift: large ? 0.08 : 0 + }] + }, options); + group.name = "\\" + stash; + base.classes.unshift("mop"); // $FlowFixMe + + base.italic = italic; + } + } else if (group.body) { + // If this is a list, compose that list. + var inner = buildExpression$1(group.body, options, true); + + if (inner.length === 1 && inner[0] instanceof SymbolNode) { + base = inner[0]; + base.classes[0] = "mop"; // replace old mclass + } else { + base = buildCommon.makeSpan(["mop"], inner, options); + } + } else { + // Otherwise, this is a text operator. Build the text from the + // operator's name. + var output = []; + + for (var i = 1; i < group.name.length; i++) { + output.push(buildCommon.mathsym(group.name[i], group.mode, options)); + } + + base = buildCommon.makeSpan(["mop"], output, options); + } // If content of op is a single symbol, shift it vertically. + + + var baseShift = 0; + var slant = 0; + + if ((base instanceof SymbolNode || group.name === "\\oiint" || group.name === "\\oiiint") && !group.suppressBaseShift) { + // We suppress the shift of the base of \overset and \underset. Otherwise, + // shift the symbol so its center lies on the axis (rule 13). It + // appears that our fonts have the centers of the symbols already + // almost on the axis, so these numbers are very small. Note we + // don't actually apply this here, but instead it is used either in + // the vlist creation or separately when there are no limits. + baseShift = (base.height - base.depth) / 2 - options.fontMetrics().axisHeight; // The slant of the symbol is just its italic correction. + // $FlowFixMe + + slant = base.italic; + } + + if (hasLimits) { + return assembleSupSub(base, supGroup, subGroup, options, style, slant, baseShift); + } else { + if (baseShift) { + base.style.position = "relative"; + base.style.top = makeEm(baseShift); + } + + return base; + } +}; + +var mathmlBuilder$1 = (group, options) => { + var node; + + if (group.symbol) { + // This is a symbol. Just add the symbol. + node = new MathNode("mo", [makeText(group.name, group.mode)]); + + if (utils.contains(noSuccessor, group.name)) { + node.setAttribute("largeop", "false"); + } + } else if (group.body) { + // This is an operator with children. Add them. + node = new MathNode("mo", buildExpression(group.body, options)); + } else { + // This is a text operator. Add all of the characters from the + // operator's name. + node = new MathNode("mi", [new TextNode(group.name.slice(1))]); // Append an . + // ref: https://www.w3.org/TR/REC-MathML/chap3_2.html#sec3.2.4 + + var operator = new MathNode("mo", [makeText("\u2061", "text")]); + + if (group.parentIsSupSub) { + node = new MathNode("mrow", [node, operator]); + } else { + node = newDocumentFragment([node, operator]); + } + } + + return node; +}; + +var singleCharBigOps = { + "\u220F": "\\prod", + "\u2210": "\\coprod", + "\u2211": "\\sum", + "\u22c0": "\\bigwedge", + "\u22c1": "\\bigvee", + "\u22c2": "\\bigcap", + "\u22c3": "\\bigcup", + "\u2a00": "\\bigodot", + "\u2a01": "\\bigoplus", + "\u2a02": "\\bigotimes", + "\u2a04": "\\biguplus", + "\u2a06": "\\bigsqcup" +}; +defineFunction({ + type: "op", + names: ["\\coprod", "\\bigvee", "\\bigwedge", "\\biguplus", "\\bigcap", "\\bigcup", "\\intop", "\\prod", "\\sum", "\\bigotimes", "\\bigoplus", "\\bigodot", "\\bigsqcup", "\\smallint", "\u220F", "\u2210", "\u2211", "\u22c0", "\u22c1", "\u22c2", "\u22c3", "\u2a00", "\u2a01", "\u2a02", "\u2a04", "\u2a06"], + props: { + numArgs: 0 + }, + handler: (_ref, args) => { + var { + parser, + funcName + } = _ref; + var fName = funcName; + + if (fName.length === 1) { + fName = singleCharBigOps[fName]; + } + + return { + type: "op", + mode: parser.mode, + limits: true, + parentIsSupSub: false, + symbol: true, + name: fName + }; + }, + htmlBuilder: htmlBuilder$2, + mathmlBuilder: mathmlBuilder$1 +}); // Note: calling defineFunction with a type that's already been defined only +// works because the same htmlBuilder and mathmlBuilder are being used. + +defineFunction({ + type: "op", + names: ["\\mathop"], + props: { + numArgs: 1, + primitive: true + }, + handler: (_ref2, args) => { + var { + parser + } = _ref2; + var body = args[0]; + return { + type: "op", + mode: parser.mode, + limits: false, + parentIsSupSub: false, + symbol: false, + body: ordargument(body) + }; + }, + htmlBuilder: htmlBuilder$2, + mathmlBuilder: mathmlBuilder$1 +}); // There are 2 flags for operators; whether they produce limits in +// displaystyle, and whether they are symbols and should grow in +// displaystyle. These four groups cover the four possible choices. + +var singleCharIntegrals = { + "\u222b": "\\int", + "\u222c": "\\iint", + "\u222d": "\\iiint", + "\u222e": "\\oint", + "\u222f": "\\oiint", + "\u2230": "\\oiiint" +}; // No limits, not symbols + +defineFunction({ + type: "op", + names: ["\\arcsin", "\\arccos", "\\arctan", "\\arctg", "\\arcctg", "\\arg", "\\ch", "\\cos", "\\cosec", "\\cosh", "\\cot", "\\cotg", "\\coth", "\\csc", "\\ctg", "\\cth", "\\deg", "\\dim", "\\exp", "\\hom", "\\ker", "\\lg", "\\ln", "\\log", "\\sec", "\\sin", "\\sinh", "\\sh", "\\tan", "\\tanh", "\\tg", "\\th"], + props: { + numArgs: 0 + }, + + handler(_ref3) { + var { + parser, + funcName + } = _ref3; + return { + type: "op", + mode: parser.mode, + limits: false, + parentIsSupSub: false, + symbol: false, + name: funcName + }; + }, + + htmlBuilder: htmlBuilder$2, + mathmlBuilder: mathmlBuilder$1 +}); // Limits, not symbols + +defineFunction({ + type: "op", + names: ["\\det", "\\gcd", "\\inf", "\\lim", "\\max", "\\min", "\\Pr", "\\sup"], + props: { + numArgs: 0 + }, + + handler(_ref4) { + var { + parser, + funcName + } = _ref4; + return { + type: "op", + mode: parser.mode, + limits: true, + parentIsSupSub: false, + symbol: false, + name: funcName + }; + }, + + htmlBuilder: htmlBuilder$2, + mathmlBuilder: mathmlBuilder$1 +}); // No limits, symbols + +defineFunction({ + type: "op", + names: ["\\int", "\\iint", "\\iiint", "\\oint", "\\oiint", "\\oiiint", "\u222b", "\u222c", "\u222d", "\u222e", "\u222f", "\u2230"], + props: { + numArgs: 0 + }, + + handler(_ref5) { + var { + parser, + funcName + } = _ref5; + var fName = funcName; + + if (fName.length === 1) { + fName = singleCharIntegrals[fName]; + } + + return { + type: "op", + mode: parser.mode, + limits: false, + parentIsSupSub: false, + symbol: true, + name: fName + }; + }, + + htmlBuilder: htmlBuilder$2, + mathmlBuilder: mathmlBuilder$1 +}); + +// NOTE: Unlike most `htmlBuilder`s, this one handles not only +// "operatorname", but also "supsub" since \operatorname* can +// affect super/subscripting. +var htmlBuilder$1 = (grp, options) => { + // Operators are handled in the TeXbook pg. 443-444, rule 13(a). + var supGroup; + var subGroup; + var hasLimits = false; + var group; + + if (grp.type === "supsub") { + // If we have limits, supsub will pass us its group to handle. Pull + // out the superscript and subscript and set the group to the op in + // its base. + supGroup = grp.sup; + subGroup = grp.sub; + group = assertNodeType(grp.base, "operatorname"); + hasLimits = true; + } else { + group = assertNodeType(grp, "operatorname"); + } + + var base; + + if (group.body.length > 0) { + var body = group.body.map(child => { + // $FlowFixMe: Check if the node has a string `text` property. + var childText = child.text; + + if (typeof childText === "string") { + return { + type: "textord", + mode: child.mode, + text: childText + }; + } else { + return child; + } + }); // Consolidate function names into symbol characters. + + var expression = buildExpression$1(body, options.withFont("mathrm"), true); + + for (var i = 0; i < expression.length; i++) { + var child = expression[i]; + + if (child instanceof SymbolNode) { + // Per amsopn package, + // change minus to hyphen and \ast to asterisk + child.text = child.text.replace(/\u2212/, "-").replace(/\u2217/, "*"); + } + } + + base = buildCommon.makeSpan(["mop"], expression, options); + } else { + base = buildCommon.makeSpan(["mop"], [], options); + } + + if (hasLimits) { + return assembleSupSub(base, supGroup, subGroup, options, options.style, 0, 0); + } else { + return base; + } +}; + +var mathmlBuilder = (group, options) => { + // The steps taken here are similar to the html version. + var expression = buildExpression(group.body, options.withFont("mathrm")); // Is expression a string or has it something like a fraction? + + var isAllString = true; // default + + for (var i = 0; i < expression.length; i++) { + var node = expression[i]; + + if (node instanceof mathMLTree.SpaceNode) ; else if (node instanceof mathMLTree.MathNode) { + switch (node.type) { + case "mi": + case "mn": + case "ms": + case "mspace": + case "mtext": + break; + // Do nothing yet. + + case "mo": + { + var child = node.children[0]; + + if (node.children.length === 1 && child instanceof mathMLTree.TextNode) { + child.text = child.text.replace(/\u2212/, "-").replace(/\u2217/, "*"); + } else { + isAllString = false; + } + + break; + } + + default: + isAllString = false; + } + } else { + isAllString = false; + } + } + + if (isAllString) { + // Write a single TextNode instead of multiple nested tags. + var word = expression.map(node => node.toText()).join(""); + expression = [new mathMLTree.TextNode(word)]; + } + + var identifier = new mathMLTree.MathNode("mi", expression); + identifier.setAttribute("mathvariant", "normal"); // \u2061 is the same as ⁡ + // ref: https://www.w3schools.com/charsets/ref_html_entities_a.asp + + var operator = new mathMLTree.MathNode("mo", [makeText("\u2061", "text")]); + + if (group.parentIsSupSub) { + return new mathMLTree.MathNode("mrow", [identifier, operator]); + } else { + return mathMLTree.newDocumentFragment([identifier, operator]); + } +}; // \operatorname +// amsopn.dtx: \mathop{#1\kern\z@\operator@font#3}\newmcodes@ + + +defineFunction({ + type: "operatorname", + names: ["\\operatorname@", "\\operatornamewithlimits"], + props: { + numArgs: 1 + }, + handler: (_ref, args) => { + var { + parser, + funcName + } = _ref; + var body = args[0]; + return { + type: "operatorname", + mode: parser.mode, + body: ordargument(body), + alwaysHandleSupSub: funcName === "\\operatornamewithlimits", + limits: false, + parentIsSupSub: false + }; + }, + htmlBuilder: htmlBuilder$1, + mathmlBuilder +}); +defineMacro("\\operatorname", "\\@ifstar\\operatornamewithlimits\\operatorname@"); + +defineFunctionBuilders({ + type: "ordgroup", + + htmlBuilder(group, options) { + if (group.semisimple) { + return buildCommon.makeFragment(buildExpression$1(group.body, options, false)); + } + + return buildCommon.makeSpan(["mord"], buildExpression$1(group.body, options, true), options); + }, + + mathmlBuilder(group, options) { + return buildExpressionRow(group.body, options, true); + } + +}); + +defineFunction({ + type: "overline", + names: ["\\overline"], + props: { + numArgs: 1 + }, + + handler(_ref, args) { + var { + parser + } = _ref; + var body = args[0]; + return { + type: "overline", + mode: parser.mode, + body + }; + }, + + htmlBuilder(group, options) { + // Overlines are handled in the TeXbook pg 443, Rule 9. + // Build the inner group in the cramped style. + var innerGroup = buildGroup$1(group.body, options.havingCrampedStyle()); // Create the line above the body + + var line = buildCommon.makeLineSpan("overline-line", options); // Generate the vlist, with the appropriate kerns + + var defaultRuleThickness = options.fontMetrics().defaultRuleThickness; + var vlist = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: innerGroup + }, { + type: "kern", + size: 3 * defaultRuleThickness + }, { + type: "elem", + elem: line + }, { + type: "kern", + size: defaultRuleThickness + }] + }, options); + return buildCommon.makeSpan(["mord", "overline"], [vlist], options); + }, + + mathmlBuilder(group, options) { + var operator = new mathMLTree.MathNode("mo", [new mathMLTree.TextNode("\u203e")]); + operator.setAttribute("stretchy", "true"); + var node = new mathMLTree.MathNode("mover", [buildGroup(group.body, options), operator]); + node.setAttribute("accent", "true"); + return node; + } + +}); + +defineFunction({ + type: "phantom", + names: ["\\phantom"], + props: { + numArgs: 1, + allowedInText: true + }, + handler: (_ref, args) => { + var { + parser + } = _ref; + var body = args[0]; + return { + type: "phantom", + mode: parser.mode, + body: ordargument(body) + }; + }, + htmlBuilder: (group, options) => { + var elements = buildExpression$1(group.body, options.withPhantom(), false); // \phantom isn't supposed to affect the elements it contains. + // See "color" for more details. + + return buildCommon.makeFragment(elements); + }, + mathmlBuilder: (group, options) => { + var inner = buildExpression(group.body, options); + return new mathMLTree.MathNode("mphantom", inner); + } +}); +defineFunction({ + type: "hphantom", + names: ["\\hphantom"], + props: { + numArgs: 1, + allowedInText: true + }, + handler: (_ref2, args) => { + var { + parser + } = _ref2; + var body = args[0]; + return { + type: "hphantom", + mode: parser.mode, + body + }; + }, + htmlBuilder: (group, options) => { + var node = buildCommon.makeSpan([], [buildGroup$1(group.body, options.withPhantom())]); + node.height = 0; + node.depth = 0; + + if (node.children) { + for (var i = 0; i < node.children.length; i++) { + node.children[i].height = 0; + node.children[i].depth = 0; + } + } // See smash for comment re: use of makeVList + + + node = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: node + }] + }, options); // For spacing, TeX treats \smash as a math group (same spacing as ord). + + return buildCommon.makeSpan(["mord"], [node], options); + }, + mathmlBuilder: (group, options) => { + var inner = buildExpression(ordargument(group.body), options); + var phantom = new mathMLTree.MathNode("mphantom", inner); + var node = new mathMLTree.MathNode("mpadded", [phantom]); + node.setAttribute("height", "0px"); + node.setAttribute("depth", "0px"); + return node; + } +}); +defineFunction({ + type: "vphantom", + names: ["\\vphantom"], + props: { + numArgs: 1, + allowedInText: true + }, + handler: (_ref3, args) => { + var { + parser + } = _ref3; + var body = args[0]; + return { + type: "vphantom", + mode: parser.mode, + body + }; + }, + htmlBuilder: (group, options) => { + var inner = buildCommon.makeSpan(["inner"], [buildGroup$1(group.body, options.withPhantom())]); + var fix = buildCommon.makeSpan(["fix"], []); + return buildCommon.makeSpan(["mord", "rlap"], [inner, fix], options); + }, + mathmlBuilder: (group, options) => { + var inner = buildExpression(ordargument(group.body), options); + var phantom = new mathMLTree.MathNode("mphantom", inner); + var node = new mathMLTree.MathNode("mpadded", [phantom]); + node.setAttribute("width", "0px"); + return node; + } +}); + +defineFunction({ + type: "raisebox", + names: ["\\raisebox"], + props: { + numArgs: 2, + argTypes: ["size", "hbox"], + allowedInText: true + }, + + handler(_ref, args) { + var { + parser + } = _ref; + var amount = assertNodeType(args[0], "size").value; + var body = args[1]; + return { + type: "raisebox", + mode: parser.mode, + dy: amount, + body + }; + }, + + htmlBuilder(group, options) { + var body = buildGroup$1(group.body, options); + var dy = calculateSize(group.dy, options); + return buildCommon.makeVList({ + positionType: "shift", + positionData: -dy, + children: [{ + type: "elem", + elem: body + }] + }, options); + }, + + mathmlBuilder(group, options) { + var node = new mathMLTree.MathNode("mpadded", [buildGroup(group.body, options)]); + var dy = group.dy.number + group.dy.unit; + node.setAttribute("voffset", dy); + return node; + } + +}); + +defineFunction({ + type: "internal", + names: ["\\relax"], + props: { + numArgs: 0, + allowedInText: true, + allowedInArgument: true + }, + + handler(_ref) { + var { + parser + } = _ref; + return { + type: "internal", + mode: parser.mode + }; + } + +}); + +defineFunction({ + type: "rule", + names: ["\\rule"], + props: { + numArgs: 2, + numOptionalArgs: 1, + allowedInText: true, + allowedInMath: true, + argTypes: ["size", "size", "size"] + }, + + handler(_ref, args, optArgs) { + var { + parser + } = _ref; + var shift = optArgs[0]; + var width = assertNodeType(args[0], "size"); + var height = assertNodeType(args[1], "size"); + return { + type: "rule", + mode: parser.mode, + shift: shift && assertNodeType(shift, "size").value, + width: width.value, + height: height.value + }; + }, + + htmlBuilder(group, options) { + // Make an empty span for the rule + var rule = buildCommon.makeSpan(["mord", "rule"], [], options); // Calculate the shift, width, and height of the rule, and account for units + + var width = calculateSize(group.width, options); + var height = calculateSize(group.height, options); + var shift = group.shift ? calculateSize(group.shift, options) : 0; // Style the rule to the right size + + rule.style.borderRightWidth = makeEm(width); + rule.style.borderTopWidth = makeEm(height); + rule.style.bottom = makeEm(shift); // Record the height and width + + rule.width = width; + rule.height = height + shift; + rule.depth = -shift; // Font size is the number large enough that the browser will + // reserve at least `absHeight` space above the baseline. + // The 1.125 factor was empirically determined + + rule.maxFontSize = height * 1.125 * options.sizeMultiplier; + return rule; + }, + + mathmlBuilder(group, options) { + var width = calculateSize(group.width, options); + var height = calculateSize(group.height, options); + var shift = group.shift ? calculateSize(group.shift, options) : 0; + var color = options.color && options.getColor() || "black"; + var rule = new mathMLTree.MathNode("mspace"); + rule.setAttribute("mathbackground", color); + rule.setAttribute("width", makeEm(width)); + rule.setAttribute("height", makeEm(height)); + var wrapper = new mathMLTree.MathNode("mpadded", [rule]); + + if (shift >= 0) { + wrapper.setAttribute("height", makeEm(shift)); + } else { + wrapper.setAttribute("height", makeEm(shift)); + wrapper.setAttribute("depth", makeEm(-shift)); + } + + wrapper.setAttribute("voffset", makeEm(shift)); + return wrapper; + } + +}); + +function sizingGroup(value, options, baseOptions) { + var inner = buildExpression$1(value, options, false); + var multiplier = options.sizeMultiplier / baseOptions.sizeMultiplier; // Add size-resetting classes to the inner list and set maxFontSize + // manually. Handle nested size changes. + + for (var i = 0; i < inner.length; i++) { + var pos = inner[i].classes.indexOf("sizing"); + + if (pos < 0) { + Array.prototype.push.apply(inner[i].classes, options.sizingClasses(baseOptions)); + } else if (inner[i].classes[pos + 1] === "reset-size" + options.size) { + // This is a nested size change: e.g., inner[i] is the "b" in + // `\Huge a \small b`. Override the old size (the `reset-` class) + // but not the new size. + inner[i].classes[pos + 1] = "reset-size" + baseOptions.size; + } + + inner[i].height *= multiplier; + inner[i].depth *= multiplier; + } + + return buildCommon.makeFragment(inner); +} +var sizeFuncs = ["\\tiny", "\\sixptsize", "\\scriptsize", "\\footnotesize", "\\small", "\\normalsize", "\\large", "\\Large", "\\LARGE", "\\huge", "\\Huge"]; +var htmlBuilder = (group, options) => { + // Handle sizing operators like \Huge. Real TeX doesn't actually allow + // these functions inside of math expressions, so we do some special + // handling. + var newOptions = options.havingSize(group.size); + return sizingGroup(group.body, newOptions, options); +}; +defineFunction({ + type: "sizing", + names: sizeFuncs, + props: { + numArgs: 0, + allowedInText: true + }, + handler: (_ref, args) => { + var { + breakOnTokenText, + funcName, + parser + } = _ref; + var body = parser.parseExpression(false, breakOnTokenText); + return { + type: "sizing", + mode: parser.mode, + // Figure out what size to use based on the list of functions above + size: sizeFuncs.indexOf(funcName) + 1, + body + }; + }, + htmlBuilder, + mathmlBuilder: (group, options) => { + var newOptions = options.havingSize(group.size); + var inner = buildExpression(group.body, newOptions); + var node = new mathMLTree.MathNode("mstyle", inner); // TODO(emily): This doesn't produce the correct size for nested size + // changes, because we don't keep state of what style we're currently + // in, so we can't reset the size to normal before changing it. Now + // that we're passing an options parameter we should be able to fix + // this. + + node.setAttribute("mathsize", makeEm(newOptions.sizeMultiplier)); + return node; + } +}); + +// smash, with optional [tb], as in AMS +defineFunction({ + type: "smash", + names: ["\\smash"], + props: { + numArgs: 1, + numOptionalArgs: 1, + allowedInText: true + }, + handler: (_ref, args, optArgs) => { + var { + parser + } = _ref; + var smashHeight = false; + var smashDepth = false; + var tbArg = optArgs[0] && assertNodeType(optArgs[0], "ordgroup"); + + if (tbArg) { + // Optional [tb] argument is engaged. + // ref: amsmath: \renewcommand{\smash}[1][tb]{% + // def\mb@t{\ht}\def\mb@b{\dp}\def\mb@tb{\ht\z@\z@\dp}% + var letter = ""; + + for (var i = 0; i < tbArg.body.length; ++i) { + var node = tbArg.body[i]; // $FlowFixMe: Not every node type has a `text` property. + + letter = node.text; + + if (letter === "t") { + smashHeight = true; + } else if (letter === "b") { + smashDepth = true; + } else { + smashHeight = false; + smashDepth = false; + break; + } + } + } else { + smashHeight = true; + smashDepth = true; + } + + var body = args[0]; + return { + type: "smash", + mode: parser.mode, + body, + smashHeight, + smashDepth + }; + }, + htmlBuilder: (group, options) => { + var node = buildCommon.makeSpan([], [buildGroup$1(group.body, options)]); + + if (!group.smashHeight && !group.smashDepth) { + return node; + } + + if (group.smashHeight) { + node.height = 0; // In order to influence makeVList, we have to reset the children. + + if (node.children) { + for (var i = 0; i < node.children.length; i++) { + node.children[i].height = 0; + } + } + } + + if (group.smashDepth) { + node.depth = 0; + + if (node.children) { + for (var _i = 0; _i < node.children.length; _i++) { + node.children[_i].depth = 0; + } + } + } // At this point, we've reset the TeX-like height and depth values. + // But the span still has an HTML line height. + // makeVList applies "display: table-cell", which prevents the browser + // from acting on that line height. So we'll call makeVList now. + + + var smashedNode = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: node + }] + }, options); // For spacing, TeX treats \hphantom as a math group (same spacing as ord). + + return buildCommon.makeSpan(["mord"], [smashedNode], options); + }, + mathmlBuilder: (group, options) => { + var node = new mathMLTree.MathNode("mpadded", [buildGroup(group.body, options)]); + + if (group.smashHeight) { + node.setAttribute("height", "0px"); + } + + if (group.smashDepth) { + node.setAttribute("depth", "0px"); + } + + return node; + } +}); + +defineFunction({ + type: "sqrt", + names: ["\\sqrt"], + props: { + numArgs: 1, + numOptionalArgs: 1 + }, + + handler(_ref, args, optArgs) { + var { + parser + } = _ref; + var index = optArgs[0]; + var body = args[0]; + return { + type: "sqrt", + mode: parser.mode, + body, + index + }; + }, + + htmlBuilder(group, options) { + // Square roots are handled in the TeXbook pg. 443, Rule 11. + // First, we do the same steps as in overline to build the inner group + // and line + var inner = buildGroup$1(group.body, options.havingCrampedStyle()); + + if (inner.height === 0) { + // Render a small surd. + inner.height = options.fontMetrics().xHeight; + } // Some groups can return document fragments. Handle those by wrapping + // them in a span. + + + inner = buildCommon.wrapFragment(inner, options); // Calculate the minimum size for the \surd delimiter + + var metrics = options.fontMetrics(); + var theta = metrics.defaultRuleThickness; + var phi = theta; + + if (options.style.id < Style$1.TEXT.id) { + phi = options.fontMetrics().xHeight; + } // Calculate the clearance between the body and line + + + var lineClearance = theta + phi / 4; + var minDelimiterHeight = inner.height + inner.depth + lineClearance + theta; // Create a sqrt SVG of the required minimum size + + var { + span: img, + ruleWidth, + advanceWidth + } = delimiter.sqrtImage(minDelimiterHeight, options); + var delimDepth = img.height - ruleWidth; // Adjust the clearance based on the delimiter size + + if (delimDepth > inner.height + inner.depth + lineClearance) { + lineClearance = (lineClearance + delimDepth - inner.height - inner.depth) / 2; + } // Shift the sqrt image + + + var imgShift = img.height - inner.height - lineClearance - ruleWidth; + inner.style.paddingLeft = makeEm(advanceWidth); // Overlay the image and the argument. + + var body = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{ + type: "elem", + elem: inner, + wrapperClasses: ["svg-align"] + }, { + type: "kern", + size: -(inner.height + imgShift) + }, { + type: "elem", + elem: img + }, { + type: "kern", + size: ruleWidth + }] + }, options); + + if (!group.index) { + return buildCommon.makeSpan(["mord", "sqrt"], [body], options); + } else { + // Handle the optional root index + // The index is always in scriptscript style + var newOptions = options.havingStyle(Style$1.SCRIPTSCRIPT); + var rootm = buildGroup$1(group.index, newOptions, options); // The amount the index is shifted by. This is taken from the TeX + // source, in the definition of `\r@@t`. + + var toShift = 0.6 * (body.height - body.depth); // Build a VList with the superscript shifted up correctly + + var rootVList = buildCommon.makeVList({ + positionType: "shift", + positionData: -toShift, + children: [{ + type: "elem", + elem: rootm + }] + }, options); // Add a class surrounding it so we can add on the appropriate + // kerning + + var rootVListWrap = buildCommon.makeSpan(["root"], [rootVList]); + return buildCommon.makeSpan(["mord", "sqrt"], [rootVListWrap, body], options); + } + }, + + mathmlBuilder(group, options) { + var { + body, + index + } = group; + return index ? new mathMLTree.MathNode("mroot", [buildGroup(body, options), buildGroup(index, options)]) : new mathMLTree.MathNode("msqrt", [buildGroup(body, options)]); + } + +}); + +var styleMap = { + "display": Style$1.DISPLAY, + "text": Style$1.TEXT, + "script": Style$1.SCRIPT, + "scriptscript": Style$1.SCRIPTSCRIPT +}; +defineFunction({ + type: "styling", + names: ["\\displaystyle", "\\textstyle", "\\scriptstyle", "\\scriptscriptstyle"], + props: { + numArgs: 0, + allowedInText: true, + primitive: true + }, + + handler(_ref, args) { + var { + breakOnTokenText, + funcName, + parser + } = _ref; + // parse out the implicit body + var body = parser.parseExpression(true, breakOnTokenText); // TODO: Refactor to avoid duplicating styleMap in multiple places (e.g. + // here and in buildHTML and de-dupe the enumeration of all the styles). + // $FlowFixMe: The names above exactly match the styles. + + var style = funcName.slice(1, funcName.length - 5); + return { + type: "styling", + mode: parser.mode, + // Figure out what style to use by pulling out the style from + // the function name + style, + body + }; + }, + + htmlBuilder(group, options) { + // Style changes are handled in the TeXbook on pg. 442, Rule 3. + var newStyle = styleMap[group.style]; + var newOptions = options.havingStyle(newStyle).withFont(''); + return sizingGroup(group.body, newOptions, options); + }, + + mathmlBuilder(group, options) { + // Figure out what style we're changing to. + var newStyle = styleMap[group.style]; + var newOptions = options.havingStyle(newStyle); + var inner = buildExpression(group.body, newOptions); + var node = new mathMLTree.MathNode("mstyle", inner); + var styleAttributes = { + "display": ["0", "true"], + "text": ["0", "false"], + "script": ["1", "false"], + "scriptscript": ["2", "false"] + }; + var attr = styleAttributes[group.style]; + node.setAttribute("scriptlevel", attr[0]); + node.setAttribute("displaystyle", attr[1]); + return node; + } + +}); + +/** + * Sometimes, groups perform special rules when they have superscripts or + * subscripts attached to them. This function lets the `supsub` group know that + * Sometimes, groups perform special rules when they have superscripts or + * its inner element should handle the superscripts and subscripts instead of + * handling them itself. + */ +var htmlBuilderDelegate = function htmlBuilderDelegate(group, options) { + var base = group.base; + + if (!base) { + return null; + } else if (base.type === "op") { + // Operators handle supsubs differently when they have limits + // (e.g. `\displaystyle\sum_2^3`) + var delegate = base.limits && (options.style.size === Style$1.DISPLAY.size || base.alwaysHandleSupSub); + return delegate ? htmlBuilder$2 : null; + } else if (base.type === "operatorname") { + var _delegate = base.alwaysHandleSupSub && (options.style.size === Style$1.DISPLAY.size || base.limits); + + return _delegate ? htmlBuilder$1 : null; + } else if (base.type === "accent") { + return utils.isCharacterBox(base.base) ? htmlBuilder$a : null; + } else if (base.type === "horizBrace") { + var isSup = !group.sub; + return isSup === base.isOver ? htmlBuilder$3 : null; + } else { + return null; + } +}; // Super scripts and subscripts, whose precise placement can depend on other +// functions that precede them. + + +defineFunctionBuilders({ + type: "supsub", + + htmlBuilder(group, options) { + // Superscript and subscripts are handled in the TeXbook on page + // 445-446, rules 18(a-f). + // Here is where we defer to the inner group if it should handle + // superscripts and subscripts itself. + var builderDelegate = htmlBuilderDelegate(group, options); + + if (builderDelegate) { + return builderDelegate(group, options); + } + + var { + base: valueBase, + sup: valueSup, + sub: valueSub + } = group; + var base = buildGroup$1(valueBase, options); + var supm; + var subm; + var metrics = options.fontMetrics(); // Rule 18a + + var supShift = 0; + var subShift = 0; + var isCharacterBox = valueBase && utils.isCharacterBox(valueBase); + + if (valueSup) { + var newOptions = options.havingStyle(options.style.sup()); + supm = buildGroup$1(valueSup, newOptions, options); + + if (!isCharacterBox) { + supShift = base.height - newOptions.fontMetrics().supDrop * newOptions.sizeMultiplier / options.sizeMultiplier; + } + } + + if (valueSub) { + var _newOptions = options.havingStyle(options.style.sub()); + + subm = buildGroup$1(valueSub, _newOptions, options); + + if (!isCharacterBox) { + subShift = base.depth + _newOptions.fontMetrics().subDrop * _newOptions.sizeMultiplier / options.sizeMultiplier; + } + } // Rule 18c + + + var minSupShift; + + if (options.style === Style$1.DISPLAY) { + minSupShift = metrics.sup1; + } else if (options.style.cramped) { + minSupShift = metrics.sup3; + } else { + minSupShift = metrics.sup2; + } // scriptspace is a font-size-independent size, so scale it + // appropriately for use as the marginRight. + + + var multiplier = options.sizeMultiplier; + var marginRight = makeEm(0.5 / metrics.ptPerEm / multiplier); + var marginLeft = null; + + if (subm) { + // Subscripts shouldn't be shifted by the base's italic correction. + // Account for that by shifting the subscript back the appropriate + // amount. Note we only do this when the base is a single symbol. + var isOiint = group.base && group.base.type === "op" && group.base.name && (group.base.name === "\\oiint" || group.base.name === "\\oiiint"); + + if (base instanceof SymbolNode || isOiint) { + // $FlowFixMe + marginLeft = makeEm(-base.italic); + } + } + + var supsub; + + if (supm && subm) { + supShift = Math.max(supShift, minSupShift, supm.depth + 0.25 * metrics.xHeight); + subShift = Math.max(subShift, metrics.sub2); + var ruleWidth = metrics.defaultRuleThickness; // Rule 18e + + var maxWidth = 4 * ruleWidth; + + if (supShift - supm.depth - (subm.height - subShift) < maxWidth) { + subShift = maxWidth - (supShift - supm.depth) + subm.height; + var psi = 0.8 * metrics.xHeight - (supShift - supm.depth); + + if (psi > 0) { + supShift += psi; + subShift -= psi; + } + } + + var vlistElem = [{ + type: "elem", + elem: subm, + shift: subShift, + marginRight, + marginLeft + }, { + type: "elem", + elem: supm, + shift: -supShift, + marginRight + }]; + supsub = buildCommon.makeVList({ + positionType: "individualShift", + children: vlistElem + }, options); + } else if (subm) { + // Rule 18b + subShift = Math.max(subShift, metrics.sub1, subm.height - 0.8 * metrics.xHeight); + var _vlistElem = [{ + type: "elem", + elem: subm, + marginLeft, + marginRight + }]; + supsub = buildCommon.makeVList({ + positionType: "shift", + positionData: subShift, + children: _vlistElem + }, options); + } else if (supm) { + // Rule 18c, d + supShift = Math.max(supShift, minSupShift, supm.depth + 0.25 * metrics.xHeight); + supsub = buildCommon.makeVList({ + positionType: "shift", + positionData: -supShift, + children: [{ + type: "elem", + elem: supm, + marginRight + }] + }, options); + } else { + throw new Error("supsub must have either sup or sub."); + } // Wrap the supsub vlist in a span.msupsub to reset text-align. + + + var mclass = getTypeOfDomTree(base, "right") || "mord"; + return buildCommon.makeSpan([mclass], [base, buildCommon.makeSpan(["msupsub"], [supsub])], options); + }, + + mathmlBuilder(group, options) { + // Is the inner group a relevant horizontal brace? + var isBrace = false; + var isOver; + var isSup; + + if (group.base && group.base.type === "horizBrace") { + isSup = !!group.sup; + + if (isSup === group.base.isOver) { + isBrace = true; + isOver = group.base.isOver; + } + } + + if (group.base && (group.base.type === "op" || group.base.type === "operatorname")) { + group.base.parentIsSupSub = true; + } + + var children = [buildGroup(group.base, options)]; + + if (group.sub) { + children.push(buildGroup(group.sub, options)); + } + + if (group.sup) { + children.push(buildGroup(group.sup, options)); + } + + var nodeType; + + if (isBrace) { + nodeType = isOver ? "mover" : "munder"; + } else if (!group.sub) { + var base = group.base; + + if (base && base.type === "op" && base.limits && (options.style === Style$1.DISPLAY || base.alwaysHandleSupSub)) { + nodeType = "mover"; + } else if (base && base.type === "operatorname" && base.alwaysHandleSupSub && (base.limits || options.style === Style$1.DISPLAY)) { + nodeType = "mover"; + } else { + nodeType = "msup"; + } + } else if (!group.sup) { + var _base = group.base; + + if (_base && _base.type === "op" && _base.limits && (options.style === Style$1.DISPLAY || _base.alwaysHandleSupSub)) { + nodeType = "munder"; + } else if (_base && _base.type === "operatorname" && _base.alwaysHandleSupSub && (_base.limits || options.style === Style$1.DISPLAY)) { + nodeType = "munder"; + } else { + nodeType = "msub"; + } + } else { + var _base2 = group.base; + + if (_base2 && _base2.type === "op" && _base2.limits && options.style === Style$1.DISPLAY) { + nodeType = "munderover"; + } else if (_base2 && _base2.type === "operatorname" && _base2.alwaysHandleSupSub && (options.style === Style$1.DISPLAY || _base2.limits)) { + nodeType = "munderover"; + } else { + nodeType = "msubsup"; + } + } + + return new mathMLTree.MathNode(nodeType, children); + } + +}); + +defineFunctionBuilders({ + type: "atom", + + htmlBuilder(group, options) { + return buildCommon.mathsym(group.text, group.mode, options, ["m" + group.family]); + }, + + mathmlBuilder(group, options) { + var node = new mathMLTree.MathNode("mo", [makeText(group.text, group.mode)]); + + if (group.family === "bin") { + var variant = getVariant(group, options); + + if (variant === "bold-italic") { + node.setAttribute("mathvariant", variant); + } + } else if (group.family === "punct") { + node.setAttribute("separator", "true"); + } else if (group.family === "open" || group.family === "close") { + // Delims built here should not stretch vertically. + // See delimsizing.js for stretchy delims. + node.setAttribute("stretchy", "false"); + } + + return node; + } + +}); + +// "mathord" and "textord" ParseNodes created in Parser.js from symbol Groups in +// src/symbols.js. +var defaultVariant = { + "mi": "italic", + "mn": "normal", + "mtext": "normal" +}; +defineFunctionBuilders({ + type: "mathord", + + htmlBuilder(group, options) { + return buildCommon.makeOrd(group, options, "mathord"); + }, + + mathmlBuilder(group, options) { + var node = new mathMLTree.MathNode("mi", [makeText(group.text, group.mode, options)]); + var variant = getVariant(group, options) || "italic"; + + if (variant !== defaultVariant[node.type]) { + node.setAttribute("mathvariant", variant); + } + + return node; + } + +}); +defineFunctionBuilders({ + type: "textord", + + htmlBuilder(group, options) { + return buildCommon.makeOrd(group, options, "textord"); + }, + + mathmlBuilder(group, options) { + var text = makeText(group.text, group.mode, options); + var variant = getVariant(group, options) || "normal"; + var node; + + if (group.mode === 'text') { + node = new mathMLTree.MathNode("mtext", [text]); + } else if (/[0-9]/.test(group.text)) { + node = new mathMLTree.MathNode("mn", [text]); + } else if (group.text === "\\prime") { + node = new mathMLTree.MathNode("mo", [text]); + } else { + node = new mathMLTree.MathNode("mi", [text]); + } + + if (variant !== defaultVariant[node.type]) { + node.setAttribute("mathvariant", variant); + } + + return node; + } + +}); + +var cssSpace = { + "\\nobreak": "nobreak", + "\\allowbreak": "allowbreak" +}; // A lookup table to determine whether a spacing function/symbol should be +// treated like a regular space character. If a symbol or command is a key +// in this table, then it should be a regular space character. Furthermore, +// the associated value may have a `className` specifying an extra CSS class +// to add to the created `span`. + +var regularSpace = { + " ": {}, + "\\ ": {}, + "~": { + className: "nobreak" + }, + "\\space": {}, + "\\nobreakspace": { + className: "nobreak" + } +}; // ParseNode<"spacing"> created in Parser.js from the "spacing" symbol Groups in +// src/symbols.js. + +defineFunctionBuilders({ + type: "spacing", + + htmlBuilder(group, options) { + if (regularSpace.hasOwnProperty(group.text)) { + var className = regularSpace[group.text].className || ""; // Spaces are generated by adding an actual space. Each of these + // things has an entry in the symbols table, so these will be turned + // into appropriate outputs. + + if (group.mode === "text") { + var ord = buildCommon.makeOrd(group, options, "textord"); + ord.classes.push(className); + return ord; + } else { + return buildCommon.makeSpan(["mspace", className], [buildCommon.mathsym(group.text, group.mode, options)], options); + } + } else if (cssSpace.hasOwnProperty(group.text)) { + // Spaces based on just a CSS class. + return buildCommon.makeSpan(["mspace", cssSpace[group.text]], [], options); + } else { + throw new ParseError("Unknown type of space \"" + group.text + "\""); + } + }, + + mathmlBuilder(group, options) { + var node; + + if (regularSpace.hasOwnProperty(group.text)) { + node = new mathMLTree.MathNode("mtext", [new mathMLTree.TextNode("\u00a0")]); + } else if (cssSpace.hasOwnProperty(group.text)) { + // CSS-based MathML spaces (\nobreak, \allowbreak) are ignored + return new mathMLTree.MathNode("mspace"); + } else { + throw new ParseError("Unknown type of space \"" + group.text + "\""); + } + + return node; + } + +}); + +var pad = () => { + var padNode = new mathMLTree.MathNode("mtd", []); + padNode.setAttribute("width", "50%"); + return padNode; +}; + +defineFunctionBuilders({ + type: "tag", + + mathmlBuilder(group, options) { + var table = new mathMLTree.MathNode("mtable", [new mathMLTree.MathNode("mtr", [pad(), new mathMLTree.MathNode("mtd", [buildExpressionRow(group.body, options)]), pad(), new mathMLTree.MathNode("mtd", [buildExpressionRow(group.tag, options)])])]); + table.setAttribute("width", "100%"); + return table; // TODO: Left-aligned tags. + // Currently, the group and options passed here do not contain + // enough info to set tag alignment. `leqno` is in Settings but it is + // not passed to Options. On the HTML side, leqno is + // set by a CSS class applied in buildTree.js. That would have worked + // in MathML if browsers supported . Since they don't, we + // need to rewrite the way this function is called. + } + +}); + +var textFontFamilies = { + "\\text": undefined, + "\\textrm": "textrm", + "\\textsf": "textsf", + "\\texttt": "texttt", + "\\textnormal": "textrm" +}; +var textFontWeights = { + "\\textbf": "textbf", + "\\textmd": "textmd" +}; +var textFontShapes = { + "\\textit": "textit", + "\\textup": "textup" +}; + +var optionsWithFont = (group, options) => { + var font = group.font; // Checks if the argument is a font family or a font style. + + if (!font) { + return options; + } else if (textFontFamilies[font]) { + return options.withTextFontFamily(textFontFamilies[font]); + } else if (textFontWeights[font]) { + return options.withTextFontWeight(textFontWeights[font]); + } else if (font === "\\emph") { + return options.fontShape === "textit" ? options.withTextFontShape("textup") : options.withTextFontShape("textit"); + } + + return options.withTextFontShape(textFontShapes[font]); +}; + +defineFunction({ + type: "text", + names: [// Font families + "\\text", "\\textrm", "\\textsf", "\\texttt", "\\textnormal", // Font weights + "\\textbf", "\\textmd", // Font Shapes + "\\textit", "\\textup", "\\emph"], + props: { + numArgs: 1, + argTypes: ["text"], + allowedInArgument: true, + allowedInText: true + }, + + handler(_ref, args) { + var { + parser, + funcName + } = _ref; + var body = args[0]; + return { + type: "text", + mode: parser.mode, + body: ordargument(body), + font: funcName + }; + }, + + htmlBuilder(group, options) { + var newOptions = optionsWithFont(group, options); + var inner = buildExpression$1(group.body, newOptions, true); + return buildCommon.makeSpan(["mord", "text"], inner, newOptions); + }, + + mathmlBuilder(group, options) { + var newOptions = optionsWithFont(group, options); + return buildExpressionRow(group.body, newOptions); + } + +}); + +defineFunction({ + type: "underline", + names: ["\\underline"], + props: { + numArgs: 1, + allowedInText: true + }, + + handler(_ref, args) { + var { + parser + } = _ref; + return { + type: "underline", + mode: parser.mode, + body: args[0] + }; + }, + + htmlBuilder(group, options) { + // Underlines are handled in the TeXbook pg 443, Rule 10. + // Build the inner group. + var innerGroup = buildGroup$1(group.body, options); // Create the line to go below the body + + var line = buildCommon.makeLineSpan("underline-line", options); // Generate the vlist, with the appropriate kerns + + var defaultRuleThickness = options.fontMetrics().defaultRuleThickness; + var vlist = buildCommon.makeVList({ + positionType: "top", + positionData: innerGroup.height, + children: [{ + type: "kern", + size: defaultRuleThickness + }, { + type: "elem", + elem: line + }, { + type: "kern", + size: 3 * defaultRuleThickness + }, { + type: "elem", + elem: innerGroup + }] + }, options); + return buildCommon.makeSpan(["mord", "underline"], [vlist], options); + }, + + mathmlBuilder(group, options) { + var operator = new mathMLTree.MathNode("mo", [new mathMLTree.TextNode("\u203e")]); + operator.setAttribute("stretchy", "true"); + var node = new mathMLTree.MathNode("munder", [buildGroup(group.body, options), operator]); + node.setAttribute("accentunder", "true"); + return node; + } + +}); + +defineFunction({ + type: "vcenter", + names: ["\\vcenter"], + props: { + numArgs: 1, + argTypes: ["original"], + // In LaTeX, \vcenter can act only on a box. + allowedInText: false + }, + + handler(_ref, args) { + var { + parser + } = _ref; + return { + type: "vcenter", + mode: parser.mode, + body: args[0] + }; + }, + + htmlBuilder(group, options) { + var body = buildGroup$1(group.body, options); + var axisHeight = options.fontMetrics().axisHeight; + var dy = 0.5 * (body.height - axisHeight - (body.depth + axisHeight)); + return buildCommon.makeVList({ + positionType: "shift", + positionData: dy, + children: [{ + type: "elem", + elem: body + }] + }, options); + }, + + mathmlBuilder(group, options) { + // There is no way to do this in MathML. + // Write a class as a breadcrumb in case some post-processor wants + // to perform a vcenter adjustment. + return new mathMLTree.MathNode("mpadded", [buildGroup(group.body, options)], ["vcenter"]); + } + +}); + +defineFunction({ + type: "verb", + names: ["\\verb"], + props: { + numArgs: 0, + allowedInText: true + }, + + handler(context, args, optArgs) { + // \verb and \verb* are dealt with directly in Parser.js. + // If we end up here, it's because of a failure to match the two delimiters + // in the regex in Lexer.js. LaTeX raises the following error when \verb is + // terminated by end of line (or file). + throw new ParseError("\\verb ended by end of line instead of matching delimiter"); + }, + + htmlBuilder(group, options) { + var text = makeVerb(group); + var body = []; // \verb enters text mode and therefore is sized like \textstyle + + var newOptions = options.havingStyle(options.style.text()); + + for (var i = 0; i < text.length; i++) { + var c = text[i]; + + if (c === '~') { + c = '\\textasciitilde'; + } + + body.push(buildCommon.makeSymbol(c, "Typewriter-Regular", group.mode, newOptions, ["mord", "texttt"])); + } + + return buildCommon.makeSpan(["mord", "text"].concat(newOptions.sizingClasses(options)), buildCommon.tryCombineChars(body), newOptions); + }, + + mathmlBuilder(group, options) { + var text = new mathMLTree.TextNode(makeVerb(group)); + var node = new mathMLTree.MathNode("mtext", [text]); + node.setAttribute("mathvariant", "monospace"); + return node; + } + +}); +/** + * Converts verb group into body string. + * + * \verb* replaces each space with an open box \u2423 + * \verb replaces each space with a no-break space \xA0 + */ + +var makeVerb = group => group.body.replace(/ /g, group.star ? '\u2423' : '\xA0'); + +/** Include this to ensure that all functions are defined. */ +var functions = _functions; + +/** + * The Lexer class handles tokenizing the input in various ways. Since our + * parser expects us to be able to backtrack, the lexer allows lexing from any + * given starting point. + * + * Its main exposed function is the `lex` function, which takes a position to + * lex from and a type of token to lex. It defers to the appropriate `_innerLex` + * function. + * + * The various `_innerLex` functions perform the actual lexing of different + * kinds. + */ + +/* The following tokenRegex + * - matches typical whitespace (but not NBSP etc.) using its first group + * - does not match any control character \x00-\x1f except whitespace + * - does not match a bare backslash + * - matches any ASCII character except those just mentioned + * - does not match the BMP private use area \uE000-\uF8FF + * - does not match bare surrogate code units + * - matches any BMP character except for those just described + * - matches any valid Unicode surrogate pair + * - matches a backslash followed by one or more whitespace characters + * - matches a backslash followed by one or more letters then whitespace + * - matches a backslash followed by any BMP character + * Capturing groups: + * [1] regular whitespace + * [2] backslash followed by whitespace + * [3] anything else, which may include: + * [4] left character of \verb* + * [5] left character of \verb + * [6] backslash followed by word, excluding any trailing whitespace + * Just because the Lexer matches something doesn't mean it's valid input: + * If there is no matching function or symbol definition, the Parser will + * still reject the input. + */ +var spaceRegexString = "[ \r\n\t]"; +var controlWordRegexString = "\\\\[a-zA-Z@]+"; +var controlSymbolRegexString = "\\\\[^\uD800-\uDFFF]"; +var controlWordWhitespaceRegexString = "(" + controlWordRegexString + ")" + spaceRegexString + "*"; +var controlSpaceRegexString = "\\\\(\n|[ \r\t]+\n?)[ \r\t]*"; +var combiningDiacriticalMarkString = "[\u0300-\u036f]"; +var combiningDiacriticalMarksEndRegex = new RegExp(combiningDiacriticalMarkString + "+$"); +var tokenRegexString = "(" + spaceRegexString + "+)|" + ( // whitespace +controlSpaceRegexString + "|") + // \whitespace +"([!-\\[\\]-\u2027\u202A-\uD7FF\uF900-\uFFFF]" + ( // single codepoint +combiningDiacriticalMarkString + "*") + // ...plus accents +"|[\uD800-\uDBFF][\uDC00-\uDFFF]" + ( // surrogate pair +combiningDiacriticalMarkString + "*") + // ...plus accents +"|\\\\verb\\*([^]).*?\\4" + // \verb* +"|\\\\verb([^*a-zA-Z]).*?\\5" + ( // \verb unstarred +"|" + controlWordWhitespaceRegexString) + ( // \macroName + spaces +"|" + controlSymbolRegexString + ")"); // \\, \', etc. + +/** Main Lexer class */ + +class Lexer { + // Category codes. The lexer only supports comment characters (14) for now. + // MacroExpander additionally distinguishes active (13). + constructor(input, settings) { + this.input = void 0; + this.settings = void 0; + this.tokenRegex = void 0; + this.catcodes = void 0; + // Separate accents from characters + this.input = input; + this.settings = settings; + this.tokenRegex = new RegExp(tokenRegexString, 'g'); + this.catcodes = { + "%": 14, + // comment character + "~": 13 // active character + + }; + } + + setCatcode(char, code) { + this.catcodes[char] = code; + } + /** + * This function lexes a single token. + */ + + + lex() { + var input = this.input; + var pos = this.tokenRegex.lastIndex; + + if (pos === input.length) { + return new Token("EOF", new SourceLocation(this, pos, pos)); + } + + var match = this.tokenRegex.exec(input); + + if (match === null || match.index !== pos) { + throw new ParseError("Unexpected character: '" + input[pos] + "'", new Token(input[pos], new SourceLocation(this, pos, pos + 1))); + } + + var text = match[6] || match[3] || (match[2] ? "\\ " : " "); + + if (this.catcodes[text] === 14) { + // comment character + var nlIndex = input.indexOf('\n', this.tokenRegex.lastIndex); + + if (nlIndex === -1) { + this.tokenRegex.lastIndex = input.length; // EOF + + this.settings.reportNonstrict("commentAtEnd", "% comment has no terminating newline; LaTeX would " + "fail because of commenting the end of math mode (e.g. $)"); + } else { + this.tokenRegex.lastIndex = nlIndex + 1; + } + + return this.lex(); + } + + return new Token(text, new SourceLocation(this, pos, this.tokenRegex.lastIndex)); + } + +} + +/** + * A `Namespace` refers to a space of nameable things like macros or lengths, + * which can be `set` either globally or local to a nested group, using an + * undo stack similar to how TeX implements this functionality. + * Performance-wise, `get` and local `set` take constant time, while global + * `set` takes time proportional to the depth of group nesting. + */ +class Namespace { + /** + * Both arguments are optional. The first argument is an object of + * built-in mappings which never change. The second argument is an object + * of initial (global-level) mappings, which will constantly change + * according to any global/top-level `set`s done. + */ + constructor(builtins, globalMacros) { + if (builtins === void 0) { + builtins = {}; + } + + if (globalMacros === void 0) { + globalMacros = {}; + } + + this.current = void 0; + this.builtins = void 0; + this.undefStack = void 0; + this.current = globalMacros; + this.builtins = builtins; + this.undefStack = []; + } + /** + * Start a new nested group, affecting future local `set`s. + */ + + + beginGroup() { + this.undefStack.push({}); + } + /** + * End current nested group, restoring values before the group began. + */ + + + endGroup() { + if (this.undefStack.length === 0) { + throw new ParseError("Unbalanced namespace destruction: attempt " + "to pop global namespace; please report this as a bug"); + } + + var undefs = this.undefStack.pop(); + + for (var undef in undefs) { + if (undefs.hasOwnProperty(undef)) { + if (undefs[undef] == null) { + delete this.current[undef]; + } else { + this.current[undef] = undefs[undef]; + } + } + } + } + /** + * Ends all currently nested groups (if any), restoring values before the + * groups began. Useful in case of an error in the middle of parsing. + */ + + + endGroups() { + while (this.undefStack.length > 0) { + this.endGroup(); + } + } + /** + * Detect whether `name` has a definition. Equivalent to + * `get(name) != null`. + */ + + + has(name) { + return this.current.hasOwnProperty(name) || this.builtins.hasOwnProperty(name); + } + /** + * Get the current value of a name, or `undefined` if there is no value. + * + * Note: Do not use `if (namespace.get(...))` to detect whether a macro + * is defined, as the definition may be the empty string which evaluates + * to `false` in JavaScript. Use `if (namespace.get(...) != null)` or + * `if (namespace.has(...))`. + */ + + + get(name) { + if (this.current.hasOwnProperty(name)) { + return this.current[name]; + } else { + return this.builtins[name]; + } + } + /** + * Set the current value of a name, and optionally set it globally too. + * Local set() sets the current value and (when appropriate) adds an undo + * operation to the undo stack. Global set() may change the undo + * operation at every level, so takes time linear in their number. + * A value of undefined means to delete existing definitions. + */ + + + set(name, value, global) { + if (global === void 0) { + global = false; + } + + if (global) { + // Global set is equivalent to setting in all groups. Simulate this + // by destroying any undos currently scheduled for this name, + // and adding an undo with the *new* value (in case it later gets + // locally reset within this environment). + for (var i = 0; i < this.undefStack.length; i++) { + delete this.undefStack[i][name]; + } + + if (this.undefStack.length > 0) { + this.undefStack[this.undefStack.length - 1][name] = value; + } + } else { + // Undo this set at end of this group (possibly to `undefined`), + // unless an undo is already in place, in which case that older + // value is the correct one. + var top = this.undefStack[this.undefStack.length - 1]; + + if (top && !top.hasOwnProperty(name)) { + top[name] = this.current[name]; + } + } + + if (value == null) { + delete this.current[name]; + } else { + this.current[name] = value; + } + } + +} + +/** + * Predefined macros for KaTeX. + * This can be used to define some commands in terms of others. + */ +var macros = _macros; +// macro tools + +defineMacro("\\noexpand", function (context) { + // The expansion is the token itself; but that token is interpreted + // as if its meaning were ‘\relax’ if it is a control sequence that + // would ordinarily be expanded by TeX’s expansion rules. + var t = context.popToken(); + + if (context.isExpandable(t.text)) { + t.noexpand = true; + t.treatAsRelax = true; + } + + return { + tokens: [t], + numArgs: 0 + }; +}); +defineMacro("\\expandafter", function (context) { + // TeX first reads the token that comes immediately after \expandafter, + // without expanding it; let’s call this token t. Then TeX reads the + // token that comes after t (and possibly more tokens, if that token + // has an argument), replacing it by its expansion. Finally TeX puts + // t back in front of that expansion. + var t = context.popToken(); + context.expandOnce(true); // expand only an expandable token + + return { + tokens: [t], + numArgs: 0 + }; +}); // LaTeX's \@firstoftwo{#1}{#2} expands to #1, skipping #2 +// TeX source: \long\def\@firstoftwo#1#2{#1} + +defineMacro("\\@firstoftwo", function (context) { + var args = context.consumeArgs(2); + return { + tokens: args[0], + numArgs: 0 + }; +}); // LaTeX's \@secondoftwo{#1}{#2} expands to #2, skipping #1 +// TeX source: \long\def\@secondoftwo#1#2{#2} + +defineMacro("\\@secondoftwo", function (context) { + var args = context.consumeArgs(2); + return { + tokens: args[1], + numArgs: 0 + }; +}); // LaTeX's \@ifnextchar{#1}{#2}{#3} looks ahead to the next (unexpanded) +// symbol that isn't a space, consuming any spaces but not consuming the +// first nonspace character. If that nonspace character matches #1, then +// the macro expands to #2; otherwise, it expands to #3. + +defineMacro("\\@ifnextchar", function (context) { + var args = context.consumeArgs(3); // symbol, if, else + + context.consumeSpaces(); + var nextToken = context.future(); + + if (args[0].length === 1 && args[0][0].text === nextToken.text) { + return { + tokens: args[1], + numArgs: 0 + }; + } else { + return { + tokens: args[2], + numArgs: 0 + }; + } +}); // LaTeX's \@ifstar{#1}{#2} looks ahead to the next (unexpanded) symbol. +// If it is `*`, then it consumes the symbol, and the macro expands to #1; +// otherwise, the macro expands to #2 (without consuming the symbol). +// TeX source: \def\@ifstar#1{\@ifnextchar *{\@firstoftwo{#1}}} + +defineMacro("\\@ifstar", "\\@ifnextchar *{\\@firstoftwo{#1}}"); // LaTeX's \TextOrMath{#1}{#2} expands to #1 in text mode, #2 in math mode + +defineMacro("\\TextOrMath", function (context) { + var args = context.consumeArgs(2); + + if (context.mode === 'text') { + return { + tokens: args[0], + numArgs: 0 + }; + } else { + return { + tokens: args[1], + numArgs: 0 + }; + } +}); // Lookup table for parsing numbers in base 8 through 16 + +var digitToNumber = { + "0": 0, + "1": 1, + "2": 2, + "3": 3, + "4": 4, + "5": 5, + "6": 6, + "7": 7, + "8": 8, + "9": 9, + "a": 10, + "A": 10, + "b": 11, + "B": 11, + "c": 12, + "C": 12, + "d": 13, + "D": 13, + "e": 14, + "E": 14, + "f": 15, + "F": 15 +}; // TeX \char makes a literal character (catcode 12) using the following forms: +// (see The TeXBook, p. 43) +// \char123 -- decimal +// \char'123 -- octal +// \char"123 -- hex +// \char`x -- character that can be written (i.e. isn't active) +// \char`\x -- character that cannot be written (e.g. %) +// These all refer to characters from the font, so we turn them into special +// calls to a function \@char dealt with in the Parser. + +defineMacro("\\char", function (context) { + var token = context.popToken(); + var base; + var number = ''; + + if (token.text === "'") { + base = 8; + token = context.popToken(); + } else if (token.text === '"') { + base = 16; + token = context.popToken(); + } else if (token.text === "`") { + token = context.popToken(); + + if (token.text[0] === "\\") { + number = token.text.charCodeAt(1); + } else if (token.text === "EOF") { + throw new ParseError("\\char` missing argument"); + } else { + number = token.text.charCodeAt(0); + } + } else { + base = 10; + } + + if (base) { + // Parse a number in the given base, starting with first `token`. + number = digitToNumber[token.text]; + + if (number == null || number >= base) { + throw new ParseError("Invalid base-" + base + " digit " + token.text); + } + + var digit; + + while ((digit = digitToNumber[context.future().text]) != null && digit < base) { + number *= base; + number += digit; + context.popToken(); + } + } + + return "\\@char{" + number + "}"; +}); // \newcommand{\macro}[args]{definition} +// \renewcommand{\macro}[args]{definition} +// TODO: Optional arguments: \newcommand{\macro}[args][default]{definition} + +var newcommand = (context, existsOK, nonexistsOK, skipIfExists) => { + var arg = context.consumeArg().tokens; + + if (arg.length !== 1) { + throw new ParseError("\\newcommand's first argument must be a macro name"); + } + + var name = arg[0].text; + var exists = context.isDefined(name); + + if (exists && !existsOK) { + throw new ParseError("\\newcommand{" + name + "} attempting to redefine " + (name + "; use \\renewcommand")); + } + + if (!exists && !nonexistsOK) { + throw new ParseError("\\renewcommand{" + name + "} when command " + name + " " + "does not yet exist; use \\newcommand"); + } + + var numArgs = 0; + arg = context.consumeArg().tokens; + + if (arg.length === 1 && arg[0].text === "[") { + var argText = ''; + var token = context.expandNextToken(); + + while (token.text !== "]" && token.text !== "EOF") { + // TODO: Should properly expand arg, e.g., ignore {}s + argText += token.text; + token = context.expandNextToken(); + } + + if (!argText.match(/^\s*[0-9]+\s*$/)) { + throw new ParseError("Invalid number of arguments: " + argText); + } + + numArgs = parseInt(argText); + arg = context.consumeArg().tokens; + } + + if (!(exists && skipIfExists)) { + // Final arg is the expansion of the macro + context.macros.set(name, { + tokens: arg, + numArgs + }); + } + + return ''; +}; + +defineMacro("\\newcommand", context => newcommand(context, false, true, false)); +defineMacro("\\renewcommand", context => newcommand(context, true, false, false)); +defineMacro("\\providecommand", context => newcommand(context, true, true, true)); // terminal (console) tools + +defineMacro("\\message", context => { + var arg = context.consumeArgs(1)[0]; // eslint-disable-next-line no-console + + console.log(arg.reverse().map(token => token.text).join("")); + return ''; +}); +defineMacro("\\errmessage", context => { + var arg = context.consumeArgs(1)[0]; // eslint-disable-next-line no-console + + console.error(arg.reverse().map(token => token.text).join("")); + return ''; +}); +defineMacro("\\show", context => { + var tok = context.popToken(); + var name = tok.text; // eslint-disable-next-line no-console + + console.log(tok, context.macros.get(name), functions[name], symbols.math[name], symbols.text[name]); + return ''; +}); ////////////////////////////////////////////////////////////////////// +// Grouping +// \let\bgroup={ \let\egroup=} + +defineMacro("\\bgroup", "{"); +defineMacro("\\egroup", "}"); // Symbols from latex.ltx: +// \def~{\nobreakspace{}} +// \def\lq{`} +// \def\rq{'} +// \def \aa {\r a} +// \def \AA {\r A} + +defineMacro("~", "\\nobreakspace"); +defineMacro("\\lq", "`"); +defineMacro("\\rq", "'"); +defineMacro("\\aa", "\\r a"); +defineMacro("\\AA", "\\r A"); // Copyright (C) and registered (R) symbols. Use raw symbol in MathML. +// \DeclareTextCommandDefault{\textcopyright}{\textcircled{c}} +// \DeclareTextCommandDefault{\textregistered}{\textcircled{% +// \check@mathfonts\fontsize\sf@size\z@\math@fontsfalse\selectfont R}} +// \DeclareRobustCommand{\copyright}{% +// \ifmmode{\nfss@text{\textcopyright}}\else\textcopyright\fi} + +defineMacro("\\textcopyright", "\\html@mathml{\\textcircled{c}}{\\char`©}"); +defineMacro("\\copyright", "\\TextOrMath{\\textcopyright}{\\text{\\textcopyright}}"); +defineMacro("\\textregistered", "\\html@mathml{\\textcircled{\\scriptsize R}}{\\char`®}"); // Characters omitted from Unicode range 1D400–1D7FF + +defineMacro("\u212C", "\\mathscr{B}"); // script + +defineMacro("\u2130", "\\mathscr{E}"); +defineMacro("\u2131", "\\mathscr{F}"); +defineMacro("\u210B", "\\mathscr{H}"); +defineMacro("\u2110", "\\mathscr{I}"); +defineMacro("\u2112", "\\mathscr{L}"); +defineMacro("\u2133", "\\mathscr{M}"); +defineMacro("\u211B", "\\mathscr{R}"); +defineMacro("\u212D", "\\mathfrak{C}"); // Fraktur + +defineMacro("\u210C", "\\mathfrak{H}"); +defineMacro("\u2128", "\\mathfrak{Z}"); // Define \Bbbk with a macro that works in both HTML and MathML. + +defineMacro("\\Bbbk", "\\Bbb{k}"); // Unicode middle dot +// The KaTeX fonts do not contain U+00B7. Instead, \cdotp displays +// the dot at U+22C5 and gives it punct spacing. + +defineMacro("\u00b7", "\\cdotp"); // \llap and \rlap render their contents in text mode + +defineMacro("\\llap", "\\mathllap{\\textrm{#1}}"); +defineMacro("\\rlap", "\\mathrlap{\\textrm{#1}}"); +defineMacro("\\clap", "\\mathclap{\\textrm{#1}}"); // \mathstrut from the TeXbook, p 360 + +defineMacro("\\mathstrut", "\\vphantom{(}"); // \underbar from TeXbook p 353 + +defineMacro("\\underbar", "\\underline{\\text{#1}}"); // \not is defined by base/fontmath.ltx via +// \DeclareMathSymbol{\not}{\mathrel}{symbols}{"36} +// It's thus treated like a \mathrel, but defined by a symbol that has zero +// width but extends to the right. We use \rlap to get that spacing. +// For MathML we write U+0338 here. buildMathML.js will then do the overlay. + +defineMacro("\\not", '\\html@mathml{\\mathrel{\\mathrlap\\@not}}{\\char"338}'); // Negated symbols from base/fontmath.ltx: +// \def\neq{\not=} \let\ne=\neq +// \DeclareRobustCommand +// \notin{\mathrel{\m@th\mathpalette\c@ncel\in}} +// \def\c@ncel#1#2{\m@th\ooalign{$\hfil#1\mkern1mu/\hfil$\crcr$#1#2$}} + +defineMacro("\\neq", "\\html@mathml{\\mathrel{\\not=}}{\\mathrel{\\char`≠}}"); +defineMacro("\\ne", "\\neq"); +defineMacro("\u2260", "\\neq"); +defineMacro("\\notin", "\\html@mathml{\\mathrel{{\\in}\\mathllap{/\\mskip1mu}}}" + "{\\mathrel{\\char`∉}}"); +defineMacro("\u2209", "\\notin"); // Unicode stacked relations + +defineMacro("\u2258", "\\html@mathml{" + "\\mathrel{=\\kern{-1em}\\raisebox{0.4em}{$\\scriptsize\\frown$}}" + "}{\\mathrel{\\char`\u2258}}"); +defineMacro("\u2259", "\\html@mathml{\\stackrel{\\tiny\\wedge}{=}}{\\mathrel{\\char`\u2258}}"); +defineMacro("\u225A", "\\html@mathml{\\stackrel{\\tiny\\vee}{=}}{\\mathrel{\\char`\u225A}}"); +defineMacro("\u225B", "\\html@mathml{\\stackrel{\\scriptsize\\star}{=}}" + "{\\mathrel{\\char`\u225B}}"); +defineMacro("\u225D", "\\html@mathml{\\stackrel{\\tiny\\mathrm{def}}{=}}" + "{\\mathrel{\\char`\u225D}}"); +defineMacro("\u225E", "\\html@mathml{\\stackrel{\\tiny\\mathrm{m}}{=}}" + "{\\mathrel{\\char`\u225E}}"); +defineMacro("\u225F", "\\html@mathml{\\stackrel{\\tiny?}{=}}{\\mathrel{\\char`\u225F}}"); // Misc Unicode + +defineMacro("\u27C2", "\\perp"); +defineMacro("\u203C", "\\mathclose{!\\mkern-0.8mu!}"); +defineMacro("\u220C", "\\notni"); +defineMacro("\u231C", "\\ulcorner"); +defineMacro("\u231D", "\\urcorner"); +defineMacro("\u231E", "\\llcorner"); +defineMacro("\u231F", "\\lrcorner"); +defineMacro("\u00A9", "\\copyright"); +defineMacro("\u00AE", "\\textregistered"); +defineMacro("\uFE0F", "\\textregistered"); // The KaTeX fonts have corners at codepoints that don't match Unicode. +// For MathML purposes, use the Unicode code point. + +defineMacro("\\ulcorner", "\\html@mathml{\\@ulcorner}{\\mathop{\\char\"231c}}"); +defineMacro("\\urcorner", "\\html@mathml{\\@urcorner}{\\mathop{\\char\"231d}}"); +defineMacro("\\llcorner", "\\html@mathml{\\@llcorner}{\\mathop{\\char\"231e}}"); +defineMacro("\\lrcorner", "\\html@mathml{\\@lrcorner}{\\mathop{\\char\"231f}}"); ////////////////////////////////////////////////////////////////////// +// LaTeX_2ε +// \vdots{\vbox{\baselineskip4\p@ \lineskiplimit\z@ +// \kern6\p@\hbox{.}\hbox{.}\hbox{.}}} +// We'll call \varvdots, which gets a glyph from symbols.js. +// The zero-width rule gets us an equivalent to the vertical 6pt kern. + +defineMacro("\\vdots", "{\\varvdots\\rule{0pt}{15pt}}"); +defineMacro("\u22ee", "\\vdots"); ////////////////////////////////////////////////////////////////////// +// amsmath.sty +// http://mirrors.concertpass.com/tex-archive/macros/latex/required/amsmath/amsmath.pdf +// Italic Greek capital letters. AMS defines these with \DeclareMathSymbol, +// but they are equivalent to \mathit{\Letter}. + +defineMacro("\\varGamma", "\\mathit{\\Gamma}"); +defineMacro("\\varDelta", "\\mathit{\\Delta}"); +defineMacro("\\varTheta", "\\mathit{\\Theta}"); +defineMacro("\\varLambda", "\\mathit{\\Lambda}"); +defineMacro("\\varXi", "\\mathit{\\Xi}"); +defineMacro("\\varPi", "\\mathit{\\Pi}"); +defineMacro("\\varSigma", "\\mathit{\\Sigma}"); +defineMacro("\\varUpsilon", "\\mathit{\\Upsilon}"); +defineMacro("\\varPhi", "\\mathit{\\Phi}"); +defineMacro("\\varPsi", "\\mathit{\\Psi}"); +defineMacro("\\varOmega", "\\mathit{\\Omega}"); //\newcommand{\substack}[1]{\subarray{c}#1\endsubarray} + +defineMacro("\\substack", "\\begin{subarray}{c}#1\\end{subarray}"); // \renewcommand{\colon}{\nobreak\mskip2mu\mathpunct{}\nonscript +// \mkern-\thinmuskip{:}\mskip6muplus1mu\relax} + +defineMacro("\\colon", "\\nobreak\\mskip2mu\\mathpunct{}" + "\\mathchoice{\\mkern-3mu}{\\mkern-3mu}{}{}{:}\\mskip6mu\\relax"); // \newcommand{\boxed}[1]{\fbox{\m@th$\displaystyle#1$}} + +defineMacro("\\boxed", "\\fbox{$\\displaystyle{#1}$}"); // \def\iff{\DOTSB\;\Longleftrightarrow\;} +// \def\implies{\DOTSB\;\Longrightarrow\;} +// \def\impliedby{\DOTSB\;\Longleftarrow\;} + +defineMacro("\\iff", "\\DOTSB\\;\\Longleftrightarrow\\;"); +defineMacro("\\implies", "\\DOTSB\\;\\Longrightarrow\\;"); +defineMacro("\\impliedby", "\\DOTSB\\;\\Longleftarrow\\;"); // \def\dddot#1{{\mathop{#1}\limits^{\vbox to-1.4\ex@{\kern-\tw@\ex@ +// \hbox{\normalfont ...}\vss}}}} +// We use \overset which avoids the vertical shift of \mathop. + +defineMacro("\\dddot", "{\\overset{\\raisebox{-0.1ex}{\\normalsize ...}}{#1}}"); +defineMacro("\\ddddot", "{\\overset{\\raisebox{-0.1ex}{\\normalsize ....}}{#1}}"); // AMSMath's automatic \dots, based on \mdots@@ macro. + +var dotsByToken = { + ',': '\\dotsc', + '\\not': '\\dotsb', + // \keybin@ checks for the following: + '+': '\\dotsb', + '=': '\\dotsb', + '<': '\\dotsb', + '>': '\\dotsb', + '-': '\\dotsb', + '*': '\\dotsb', + ':': '\\dotsb', + // Symbols whose definition starts with \DOTSB: + '\\DOTSB': '\\dotsb', + '\\coprod': '\\dotsb', + '\\bigvee': '\\dotsb', + '\\bigwedge': '\\dotsb', + '\\biguplus': '\\dotsb', + '\\bigcap': '\\dotsb', + '\\bigcup': '\\dotsb', + '\\prod': '\\dotsb', + '\\sum': '\\dotsb', + '\\bigotimes': '\\dotsb', + '\\bigoplus': '\\dotsb', + '\\bigodot': '\\dotsb', + '\\bigsqcup': '\\dotsb', + '\\And': '\\dotsb', + '\\longrightarrow': '\\dotsb', + '\\Longrightarrow': '\\dotsb', + '\\longleftarrow': '\\dotsb', + '\\Longleftarrow': '\\dotsb', + '\\longleftrightarrow': '\\dotsb', + '\\Longleftrightarrow': '\\dotsb', + '\\mapsto': '\\dotsb', + '\\longmapsto': '\\dotsb', + '\\hookrightarrow': '\\dotsb', + '\\doteq': '\\dotsb', + // Symbols whose definition starts with \mathbin: + '\\mathbin': '\\dotsb', + // Symbols whose definition starts with \mathrel: + '\\mathrel': '\\dotsb', + '\\relbar': '\\dotsb', + '\\Relbar': '\\dotsb', + '\\xrightarrow': '\\dotsb', + '\\xleftarrow': '\\dotsb', + // Symbols whose definition starts with \DOTSI: + '\\DOTSI': '\\dotsi', + '\\int': '\\dotsi', + '\\oint': '\\dotsi', + '\\iint': '\\dotsi', + '\\iiint': '\\dotsi', + '\\iiiint': '\\dotsi', + '\\idotsint': '\\dotsi', + // Symbols whose definition starts with \DOTSX: + '\\DOTSX': '\\dotsx' +}; +defineMacro("\\dots", function (context) { + // TODO: If used in text mode, should expand to \textellipsis. + // However, in KaTeX, \textellipsis and \ldots behave the same + // (in text mode), and it's unlikely we'd see any of the math commands + // that affect the behavior of \dots when in text mode. So fine for now + // (until we support \ifmmode ... \else ... \fi). + var thedots = '\\dotso'; + var next = context.expandAfterFuture().text; + + if (next in dotsByToken) { + thedots = dotsByToken[next]; + } else if (next.slice(0, 4) === '\\not') { + thedots = '\\dotsb'; + } else if (next in symbols.math) { + if (utils.contains(['bin', 'rel'], symbols.math[next].group)) { + thedots = '\\dotsb'; + } + } + + return thedots; +}); +var spaceAfterDots = { + // \rightdelim@ checks for the following: + ')': true, + ']': true, + '\\rbrack': true, + '\\}': true, + '\\rbrace': true, + '\\rangle': true, + '\\rceil': true, + '\\rfloor': true, + '\\rgroup': true, + '\\rmoustache': true, + '\\right': true, + '\\bigr': true, + '\\biggr': true, + '\\Bigr': true, + '\\Biggr': true, + // \extra@ also tests for the following: + '$': true, + // \extrap@ checks for the following: + ';': true, + '.': true, + ',': true +}; +defineMacro("\\dotso", function (context) { + var next = context.future().text; + + if (next in spaceAfterDots) { + return "\\ldots\\,"; + } else { + return "\\ldots"; + } +}); +defineMacro("\\dotsc", function (context) { + var next = context.future().text; // \dotsc uses \extra@ but not \extrap@, instead specially checking for + // ';' and '.', but doesn't check for ','. + + if (next in spaceAfterDots && next !== ',') { + return "\\ldots\\,"; + } else { + return "\\ldots"; + } +}); +defineMacro("\\cdots", function (context) { + var next = context.future().text; + + if (next in spaceAfterDots) { + return "\\@cdots\\,"; + } else { + return "\\@cdots"; + } +}); +defineMacro("\\dotsb", "\\cdots"); +defineMacro("\\dotsm", "\\cdots"); +defineMacro("\\dotsi", "\\!\\cdots"); // amsmath doesn't actually define \dotsx, but \dots followed by a macro +// starting with \DOTSX implies \dotso, and then \extra@ detects this case +// and forces the added `\,`. + +defineMacro("\\dotsx", "\\ldots\\,"); // \let\DOTSI\relax +// \let\DOTSB\relax +// \let\DOTSX\relax + +defineMacro("\\DOTSI", "\\relax"); +defineMacro("\\DOTSB", "\\relax"); +defineMacro("\\DOTSX", "\\relax"); // Spacing, based on amsmath.sty's override of LaTeX defaults +// \DeclareRobustCommand{\tmspace}[3]{% +// \ifmmode\mskip#1#2\else\kern#1#3\fi\relax} + +defineMacro("\\tmspace", "\\TextOrMath{\\kern#1#3}{\\mskip#1#2}\\relax"); // \renewcommand{\,}{\tmspace+\thinmuskip{.1667em}} +// TODO: math mode should use \thinmuskip + +defineMacro("\\,", "\\tmspace+{3mu}{.1667em}"); // \let\thinspace\, + +defineMacro("\\thinspace", "\\,"); // \def\>{\mskip\medmuskip} +// \renewcommand{\:}{\tmspace+\medmuskip{.2222em}} +// TODO: \> and math mode of \: should use \medmuskip = 4mu plus 2mu minus 4mu + +defineMacro("\\>", "\\mskip{4mu}"); +defineMacro("\\:", "\\tmspace+{4mu}{.2222em}"); // \let\medspace\: + +defineMacro("\\medspace", "\\:"); // \renewcommand{\;}{\tmspace+\thickmuskip{.2777em}} +// TODO: math mode should use \thickmuskip = 5mu plus 5mu + +defineMacro("\\;", "\\tmspace+{5mu}{.2777em}"); // \let\thickspace\; + +defineMacro("\\thickspace", "\\;"); // \renewcommand{\!}{\tmspace-\thinmuskip{.1667em}} +// TODO: math mode should use \thinmuskip + +defineMacro("\\!", "\\tmspace-{3mu}{.1667em}"); // \let\negthinspace\! + +defineMacro("\\negthinspace", "\\!"); // \newcommand{\negmedspace}{\tmspace-\medmuskip{.2222em}} +// TODO: math mode should use \medmuskip + +defineMacro("\\negmedspace", "\\tmspace-{4mu}{.2222em}"); // \newcommand{\negthickspace}{\tmspace-\thickmuskip{.2777em}} +// TODO: math mode should use \thickmuskip + +defineMacro("\\negthickspace", "\\tmspace-{5mu}{.277em}"); // \def\enspace{\kern.5em } + +defineMacro("\\enspace", "\\kern.5em "); // \def\enskip{\hskip.5em\relax} + +defineMacro("\\enskip", "\\hskip.5em\\relax"); // \def\quad{\hskip1em\relax} + +defineMacro("\\quad", "\\hskip1em\\relax"); // \def\qquad{\hskip2em\relax} + +defineMacro("\\qquad", "\\hskip2em\\relax"); // \tag@in@display form of \tag + +defineMacro("\\tag", "\\@ifstar\\tag@literal\\tag@paren"); +defineMacro("\\tag@paren", "\\tag@literal{({#1})}"); +defineMacro("\\tag@literal", context => { + if (context.macros.get("\\df@tag")) { + throw new ParseError("Multiple \\tag"); + } + + return "\\gdef\\df@tag{\\text{#1}}"; +}); // \renewcommand{\bmod}{\nonscript\mskip-\medmuskip\mkern5mu\mathbin +// {\operator@font mod}\penalty900 +// \mkern5mu\nonscript\mskip-\medmuskip} +// \newcommand{\pod}[1]{\allowbreak +// \if@display\mkern18mu\else\mkern8mu\fi(#1)} +// \renewcommand{\pmod}[1]{\pod{{\operator@font mod}\mkern6mu#1}} +// \newcommand{\mod}[1]{\allowbreak\if@display\mkern18mu +// \else\mkern12mu\fi{\operator@font mod}\,\,#1} +// TODO: math mode should use \medmuskip = 4mu plus 2mu minus 4mu + +defineMacro("\\bmod", "\\mathchoice{\\mskip1mu}{\\mskip1mu}{\\mskip5mu}{\\mskip5mu}" + "\\mathbin{\\rm mod}" + "\\mathchoice{\\mskip1mu}{\\mskip1mu}{\\mskip5mu}{\\mskip5mu}"); +defineMacro("\\pod", "\\allowbreak" + "\\mathchoice{\\mkern18mu}{\\mkern8mu}{\\mkern8mu}{\\mkern8mu}(#1)"); +defineMacro("\\pmod", "\\pod{{\\rm mod}\\mkern6mu#1}"); +defineMacro("\\mod", "\\allowbreak" + "\\mathchoice{\\mkern18mu}{\\mkern12mu}{\\mkern12mu}{\\mkern12mu}" + "{\\rm mod}\\,\\,#1"); ////////////////////////////////////////////////////////////////////// +// LaTeX source2e +// \expandafter\let\expandafter\@normalcr +// \csname\expandafter\@gobble\string\\ \endcsname +// \DeclareRobustCommand\newline{\@normalcr\relax} + +defineMacro("\\newline", "\\\\\\relax"); // \def\TeX{T\kern-.1667em\lower.5ex\hbox{E}\kern-.125emX\@} +// TODO: Doesn't normally work in math mode because \@ fails. KaTeX doesn't +// support \@ yet, so that's omitted, and we add \text so that the result +// doesn't look funny in math mode. + +defineMacro("\\TeX", "\\textrm{\\html@mathml{" + "T\\kern-.1667em\\raisebox{-.5ex}{E}\\kern-.125emX" + "}{TeX}}"); // \DeclareRobustCommand{\LaTeX}{L\kern-.36em% +// {\sbox\z@ T% +// \vbox to\ht\z@{\hbox{\check@mathfonts +// \fontsize\sf@size\z@ +// \math@fontsfalse\selectfont +// A}% +// \vss}% +// }% +// \kern-.15em% +// \TeX} +// This code aligns the top of the A with the T (from the perspective of TeX's +// boxes, though visually the A appears to extend above slightly). +// We compute the corresponding \raisebox when A is rendered in \normalsize +// \scriptstyle, which has a scale factor of 0.7 (see Options.js). + +var latexRaiseA = makeEm(fontMetricsData['Main-Regular']["T".charCodeAt(0)][1] - 0.7 * fontMetricsData['Main-Regular']["A".charCodeAt(0)][1]); +defineMacro("\\LaTeX", "\\textrm{\\html@mathml{" + ("L\\kern-.36em\\raisebox{" + latexRaiseA + "}{\\scriptstyle A}") + "\\kern-.15em\\TeX}{LaTeX}}"); // New KaTeX logo based on tweaking LaTeX logo + +defineMacro("\\KaTeX", "\\textrm{\\html@mathml{" + ("K\\kern-.17em\\raisebox{" + latexRaiseA + "}{\\scriptstyle A}") + "\\kern-.15em\\TeX}{KaTeX}}"); // \DeclareRobustCommand\hspace{\@ifstar\@hspacer\@hspace} +// \def\@hspace#1{\hskip #1\relax} +// \def\@hspacer#1{\vrule \@width\z@\nobreak +// \hskip #1\hskip \z@skip} + +defineMacro("\\hspace", "\\@ifstar\\@hspacer\\@hspace"); +defineMacro("\\@hspace", "\\hskip #1\\relax"); +defineMacro("\\@hspacer", "\\rule{0pt}{0pt}\\hskip #1\\relax"); ////////////////////////////////////////////////////////////////////// +// mathtools.sty +//\providecommand\ordinarycolon{:} + +defineMacro("\\ordinarycolon", ":"); //\def\vcentcolon{\mathrel{\mathop\ordinarycolon}} +//TODO(edemaine): Not yet centered. Fix via \raisebox or #726 + +defineMacro("\\vcentcolon", "\\mathrel{\\mathop\\ordinarycolon}"); // \providecommand*\dblcolon{\vcentcolon\mathrel{\mkern-.9mu}\vcentcolon} + +defineMacro("\\dblcolon", "\\html@mathml{" + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-.9mu}\\vcentcolon}}" + "{\\mathop{\\char\"2237}}"); // \providecommand*\coloneqq{\vcentcolon\mathrel{\mkern-1.2mu}=} + +defineMacro("\\coloneqq", "\\html@mathml{" + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}=}}" + "{\\mathop{\\char\"2254}}"); // ≔ +// \providecommand*\Coloneqq{\dblcolon\mathrel{\mkern-1.2mu}=} + +defineMacro("\\Coloneqq", "\\html@mathml{" + "\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}=}}" + "{\\mathop{\\char\"2237\\char\"3d}}"); // \providecommand*\coloneq{\vcentcolon\mathrel{\mkern-1.2mu}\mathrel{-}} + +defineMacro("\\coloneq", "\\html@mathml{" + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}\\mathrel{-}}}" + "{\\mathop{\\char\"3a\\char\"2212}}"); // \providecommand*\Coloneq{\dblcolon\mathrel{\mkern-1.2mu}\mathrel{-}} + +defineMacro("\\Coloneq", "\\html@mathml{" + "\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}\\mathrel{-}}}" + "{\\mathop{\\char\"2237\\char\"2212}}"); // \providecommand*\eqqcolon{=\mathrel{\mkern-1.2mu}\vcentcolon} + +defineMacro("\\eqqcolon", "\\html@mathml{" + "\\mathrel{=\\mathrel{\\mkern-1.2mu}\\vcentcolon}}" + "{\\mathop{\\char\"2255}}"); // ≕ +// \providecommand*\Eqqcolon{=\mathrel{\mkern-1.2mu}\dblcolon} + +defineMacro("\\Eqqcolon", "\\html@mathml{" + "\\mathrel{=\\mathrel{\\mkern-1.2mu}\\dblcolon}}" + "{\\mathop{\\char\"3d\\char\"2237}}"); // \providecommand*\eqcolon{\mathrel{-}\mathrel{\mkern-1.2mu}\vcentcolon} + +defineMacro("\\eqcolon", "\\html@mathml{" + "\\mathrel{\\mathrel{-}\\mathrel{\\mkern-1.2mu}\\vcentcolon}}" + "{\\mathop{\\char\"2239}}"); // \providecommand*\Eqcolon{\mathrel{-}\mathrel{\mkern-1.2mu}\dblcolon} + +defineMacro("\\Eqcolon", "\\html@mathml{" + "\\mathrel{\\mathrel{-}\\mathrel{\\mkern-1.2mu}\\dblcolon}}" + "{\\mathop{\\char\"2212\\char\"2237}}"); // \providecommand*\colonapprox{\vcentcolon\mathrel{\mkern-1.2mu}\approx} + +defineMacro("\\colonapprox", "\\html@mathml{" + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}\\approx}}" + "{\\mathop{\\char\"3a\\char\"2248}}"); // \providecommand*\Colonapprox{\dblcolon\mathrel{\mkern-1.2mu}\approx} + +defineMacro("\\Colonapprox", "\\html@mathml{" + "\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}\\approx}}" + "{\\mathop{\\char\"2237\\char\"2248}}"); // \providecommand*\colonsim{\vcentcolon\mathrel{\mkern-1.2mu}\sim} + +defineMacro("\\colonsim", "\\html@mathml{" + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}\\sim}}" + "{\\mathop{\\char\"3a\\char\"223c}}"); // \providecommand*\Colonsim{\dblcolon\mathrel{\mkern-1.2mu}\sim} + +defineMacro("\\Colonsim", "\\html@mathml{" + "\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}\\sim}}" + "{\\mathop{\\char\"2237\\char\"223c}}"); // Some Unicode characters are implemented with macros to mathtools functions. + +defineMacro("\u2237", "\\dblcolon"); // :: + +defineMacro("\u2239", "\\eqcolon"); // -: + +defineMacro("\u2254", "\\coloneqq"); // := + +defineMacro("\u2255", "\\eqqcolon"); // =: + +defineMacro("\u2A74", "\\Coloneqq"); // ::= +////////////////////////////////////////////////////////////////////// +// colonequals.sty +// Alternate names for mathtools's macros: + +defineMacro("\\ratio", "\\vcentcolon"); +defineMacro("\\coloncolon", "\\dblcolon"); +defineMacro("\\colonequals", "\\coloneqq"); +defineMacro("\\coloncolonequals", "\\Coloneqq"); +defineMacro("\\equalscolon", "\\eqqcolon"); +defineMacro("\\equalscoloncolon", "\\Eqqcolon"); +defineMacro("\\colonminus", "\\coloneq"); +defineMacro("\\coloncolonminus", "\\Coloneq"); +defineMacro("\\minuscolon", "\\eqcolon"); +defineMacro("\\minuscoloncolon", "\\Eqcolon"); // \colonapprox name is same in mathtools and colonequals. + +defineMacro("\\coloncolonapprox", "\\Colonapprox"); // \colonsim name is same in mathtools and colonequals. + +defineMacro("\\coloncolonsim", "\\Colonsim"); // Additional macros, implemented by analogy with mathtools definitions: + +defineMacro("\\simcolon", "\\mathrel{\\sim\\mathrel{\\mkern-1.2mu}\\vcentcolon}"); +defineMacro("\\simcoloncolon", "\\mathrel{\\sim\\mathrel{\\mkern-1.2mu}\\dblcolon}"); +defineMacro("\\approxcolon", "\\mathrel{\\approx\\mathrel{\\mkern-1.2mu}\\vcentcolon}"); +defineMacro("\\approxcoloncolon", "\\mathrel{\\approx\\mathrel{\\mkern-1.2mu}\\dblcolon}"); // Present in newtxmath, pxfonts and txfonts + +defineMacro("\\notni", "\\html@mathml{\\not\\ni}{\\mathrel{\\char`\u220C}}"); +defineMacro("\\limsup", "\\DOTSB\\operatorname*{lim\\,sup}"); +defineMacro("\\liminf", "\\DOTSB\\operatorname*{lim\\,inf}"); ////////////////////////////////////////////////////////////////////// +// From amsopn.sty + +defineMacro("\\injlim", "\\DOTSB\\operatorname*{inj\\,lim}"); +defineMacro("\\projlim", "\\DOTSB\\operatorname*{proj\\,lim}"); +defineMacro("\\varlimsup", "\\DOTSB\\operatorname*{\\overline{lim}}"); +defineMacro("\\varliminf", "\\DOTSB\\operatorname*{\\underline{lim}}"); +defineMacro("\\varinjlim", "\\DOTSB\\operatorname*{\\underrightarrow{lim}}"); +defineMacro("\\varprojlim", "\\DOTSB\\operatorname*{\\underleftarrow{lim}}"); ////////////////////////////////////////////////////////////////////// +// MathML alternates for KaTeX glyphs in the Unicode private area + +defineMacro("\\gvertneqq", "\\html@mathml{\\@gvertneqq}{\u2269}"); +defineMacro("\\lvertneqq", "\\html@mathml{\\@lvertneqq}{\u2268}"); +defineMacro("\\ngeqq", "\\html@mathml{\\@ngeqq}{\u2271}"); +defineMacro("\\ngeqslant", "\\html@mathml{\\@ngeqslant}{\u2271}"); +defineMacro("\\nleqq", "\\html@mathml{\\@nleqq}{\u2270}"); +defineMacro("\\nleqslant", "\\html@mathml{\\@nleqslant}{\u2270}"); +defineMacro("\\nshortmid", "\\html@mathml{\\@nshortmid}{∤}"); +defineMacro("\\nshortparallel", "\\html@mathml{\\@nshortparallel}{∦}"); +defineMacro("\\nsubseteqq", "\\html@mathml{\\@nsubseteqq}{\u2288}"); +defineMacro("\\nsupseteqq", "\\html@mathml{\\@nsupseteqq}{\u2289}"); +defineMacro("\\varsubsetneq", "\\html@mathml{\\@varsubsetneq}{⊊}"); +defineMacro("\\varsubsetneqq", "\\html@mathml{\\@varsubsetneqq}{⫋}"); +defineMacro("\\varsupsetneq", "\\html@mathml{\\@varsupsetneq}{⊋}"); +defineMacro("\\varsupsetneqq", "\\html@mathml{\\@varsupsetneqq}{⫌}"); +defineMacro("\\imath", "\\html@mathml{\\@imath}{\u0131}"); +defineMacro("\\jmath", "\\html@mathml{\\@jmath}{\u0237}"); ////////////////////////////////////////////////////////////////////// +// stmaryrd and semantic +// The stmaryrd and semantic packages render the next four items by calling a +// glyph. Those glyphs do not exist in the KaTeX fonts. Hence the macros. + +defineMacro("\\llbracket", "\\html@mathml{" + "\\mathopen{[\\mkern-3.2mu[}}" + "{\\mathopen{\\char`\u27e6}}"); +defineMacro("\\rrbracket", "\\html@mathml{" + "\\mathclose{]\\mkern-3.2mu]}}" + "{\\mathclose{\\char`\u27e7}}"); +defineMacro("\u27e6", "\\llbracket"); // blackboard bold [ + +defineMacro("\u27e7", "\\rrbracket"); // blackboard bold ] + +defineMacro("\\lBrace", "\\html@mathml{" + "\\mathopen{\\{\\mkern-3.2mu[}}" + "{\\mathopen{\\char`\u2983}}"); +defineMacro("\\rBrace", "\\html@mathml{" + "\\mathclose{]\\mkern-3.2mu\\}}}" + "{\\mathclose{\\char`\u2984}}"); +defineMacro("\u2983", "\\lBrace"); // blackboard bold { + +defineMacro("\u2984", "\\rBrace"); // blackboard bold } +// TODO: Create variable sized versions of the last two items. I believe that +// will require new font glyphs. +// The stmaryrd function `\minuso` provides a "Plimsoll" symbol that +// superimposes the characters \circ and \mathminus. Used in chemistry. + +defineMacro("\\minuso", "\\mathbin{\\html@mathml{" + "{\\mathrlap{\\mathchoice{\\kern{0.145em}}{\\kern{0.145em}}" + "{\\kern{0.1015em}}{\\kern{0.0725em}}\\circ}{-}}}" + "{\\char`⦵}}"); +defineMacro("⦵", "\\minuso"); ////////////////////////////////////////////////////////////////////// +// texvc.sty +// The texvc package contains macros available in mediawiki pages. +// We omit the functions deprecated at +// https://en.wikipedia.org/wiki/Help:Displaying_a_formula#Deprecated_syntax +// We also omit texvc's \O, which conflicts with \text{\O} + +defineMacro("\\darr", "\\downarrow"); +defineMacro("\\dArr", "\\Downarrow"); +defineMacro("\\Darr", "\\Downarrow"); +defineMacro("\\lang", "\\langle"); +defineMacro("\\rang", "\\rangle"); +defineMacro("\\uarr", "\\uparrow"); +defineMacro("\\uArr", "\\Uparrow"); +defineMacro("\\Uarr", "\\Uparrow"); +defineMacro("\\N", "\\mathbb{N}"); +defineMacro("\\R", "\\mathbb{R}"); +defineMacro("\\Z", "\\mathbb{Z}"); +defineMacro("\\alef", "\\aleph"); +defineMacro("\\alefsym", "\\aleph"); +defineMacro("\\Alpha", "\\mathrm{A}"); +defineMacro("\\Beta", "\\mathrm{B}"); +defineMacro("\\bull", "\\bullet"); +defineMacro("\\Chi", "\\mathrm{X}"); +defineMacro("\\clubs", "\\clubsuit"); +defineMacro("\\cnums", "\\mathbb{C}"); +defineMacro("\\Complex", "\\mathbb{C}"); +defineMacro("\\Dagger", "\\ddagger"); +defineMacro("\\diamonds", "\\diamondsuit"); +defineMacro("\\empty", "\\emptyset"); +defineMacro("\\Epsilon", "\\mathrm{E}"); +defineMacro("\\Eta", "\\mathrm{H}"); +defineMacro("\\exist", "\\exists"); +defineMacro("\\harr", "\\leftrightarrow"); +defineMacro("\\hArr", "\\Leftrightarrow"); +defineMacro("\\Harr", "\\Leftrightarrow"); +defineMacro("\\hearts", "\\heartsuit"); +defineMacro("\\image", "\\Im"); +defineMacro("\\infin", "\\infty"); +defineMacro("\\Iota", "\\mathrm{I}"); +defineMacro("\\isin", "\\in"); +defineMacro("\\Kappa", "\\mathrm{K}"); +defineMacro("\\larr", "\\leftarrow"); +defineMacro("\\lArr", "\\Leftarrow"); +defineMacro("\\Larr", "\\Leftarrow"); +defineMacro("\\lrarr", "\\leftrightarrow"); +defineMacro("\\lrArr", "\\Leftrightarrow"); +defineMacro("\\Lrarr", "\\Leftrightarrow"); +defineMacro("\\Mu", "\\mathrm{M}"); +defineMacro("\\natnums", "\\mathbb{N}"); +defineMacro("\\Nu", "\\mathrm{N}"); +defineMacro("\\Omicron", "\\mathrm{O}"); +defineMacro("\\plusmn", "\\pm"); +defineMacro("\\rarr", "\\rightarrow"); +defineMacro("\\rArr", "\\Rightarrow"); +defineMacro("\\Rarr", "\\Rightarrow"); +defineMacro("\\real", "\\Re"); +defineMacro("\\reals", "\\mathbb{R}"); +defineMacro("\\Reals", "\\mathbb{R}"); +defineMacro("\\Rho", "\\mathrm{P}"); +defineMacro("\\sdot", "\\cdot"); +defineMacro("\\sect", "\\S"); +defineMacro("\\spades", "\\spadesuit"); +defineMacro("\\sub", "\\subset"); +defineMacro("\\sube", "\\subseteq"); +defineMacro("\\supe", "\\supseteq"); +defineMacro("\\Tau", "\\mathrm{T}"); +defineMacro("\\thetasym", "\\vartheta"); // TODO: defineMacro("\\varcoppa", "\\\mbox{\\coppa}"); + +defineMacro("\\weierp", "\\wp"); +defineMacro("\\Zeta", "\\mathrm{Z}"); ////////////////////////////////////////////////////////////////////// +// statmath.sty +// https://ctan.math.illinois.edu/macros/latex/contrib/statmath/statmath.pdf + +defineMacro("\\argmin", "\\DOTSB\\operatorname*{arg\\,min}"); +defineMacro("\\argmax", "\\DOTSB\\operatorname*{arg\\,max}"); +defineMacro("\\plim", "\\DOTSB\\mathop{\\operatorname{plim}}\\limits"); ////////////////////////////////////////////////////////////////////// +// braket.sty +// http://ctan.math.washington.edu/tex-archive/macros/latex/contrib/braket/braket.pdf + +defineMacro("\\bra", "\\mathinner{\\langle{#1}|}"); +defineMacro("\\ket", "\\mathinner{|{#1}\\rangle}"); +defineMacro("\\braket", "\\mathinner{\\langle{#1}\\rangle}"); +defineMacro("\\Bra", "\\left\\langle#1\\right|"); +defineMacro("\\Ket", "\\left|#1\\right\\rangle"); + +var braketHelper = one => context => { + var left = context.consumeArg().tokens; + var middle = context.consumeArg().tokens; + var middleDouble = context.consumeArg().tokens; + var right = context.consumeArg().tokens; + var oldMiddle = context.macros.get("|"); + var oldMiddleDouble = context.macros.get("\\|"); + context.macros.beginGroup(); + + var midMacro = double => context => { + if (one) { + // Only modify the first instance of | or \| + context.macros.set("|", oldMiddle); + + if (middleDouble.length) { + context.macros.set("\\|", oldMiddleDouble); + } + } + + var doubled = double; + + if (!double && middleDouble.length) { + // Mimic \@ifnextchar + var nextToken = context.future(); + + if (nextToken.text === "|") { + context.popToken(); + doubled = true; + } + } + + return { + tokens: doubled ? middleDouble : middle, + numArgs: 0 + }; + }; + + context.macros.set("|", midMacro(false)); + + if (middleDouble.length) { + context.macros.set("\\|", midMacro(true)); + } + + var arg = context.consumeArg().tokens; + var expanded = context.expandTokens([...right, ...arg, ...left // reversed + ]); + context.macros.endGroup(); + return { + tokens: expanded.reverse(), + numArgs: 0 + }; +}; + +defineMacro("\\bra@ket", braketHelper(false)); +defineMacro("\\bra@set", braketHelper(true)); +defineMacro("\\Braket", "\\bra@ket{\\left\\langle}" + "{\\,\\middle\\vert\\,}{\\,\\middle\\vert\\,}{\\right\\rangle}"); +defineMacro("\\Set", "\\bra@set{\\left\\{\\:}" + "{\\;\\middle\\vert\\;}{\\;\\middle\\Vert\\;}{\\:\\right\\}}"); +defineMacro("\\set", "\\bra@set{\\{\\,}{\\mid}{}{\\,\\}}"); // has no support for special || or \| +////////////////////////////////////////////////////////////////////// +// actuarialangle.dtx + +defineMacro("\\angln", "{\\angl n}"); // Custom Khan Academy colors, should be moved to an optional package + +defineMacro("\\blue", "\\textcolor{##6495ed}{#1}"); +defineMacro("\\orange", "\\textcolor{##ffa500}{#1}"); +defineMacro("\\pink", "\\textcolor{##ff00af}{#1}"); +defineMacro("\\red", "\\textcolor{##df0030}{#1}"); +defineMacro("\\green", "\\textcolor{##28ae7b}{#1}"); +defineMacro("\\gray", "\\textcolor{gray}{#1}"); +defineMacro("\\purple", "\\textcolor{##9d38bd}{#1}"); +defineMacro("\\blueA", "\\textcolor{##ccfaff}{#1}"); +defineMacro("\\blueB", "\\textcolor{##80f6ff}{#1}"); +defineMacro("\\blueC", "\\textcolor{##63d9ea}{#1}"); +defineMacro("\\blueD", "\\textcolor{##11accd}{#1}"); +defineMacro("\\blueE", "\\textcolor{##0c7f99}{#1}"); +defineMacro("\\tealA", "\\textcolor{##94fff5}{#1}"); +defineMacro("\\tealB", "\\textcolor{##26edd5}{#1}"); +defineMacro("\\tealC", "\\textcolor{##01d1c1}{#1}"); +defineMacro("\\tealD", "\\textcolor{##01a995}{#1}"); +defineMacro("\\tealE", "\\textcolor{##208170}{#1}"); +defineMacro("\\greenA", "\\textcolor{##b6ffb0}{#1}"); +defineMacro("\\greenB", "\\textcolor{##8af281}{#1}"); +defineMacro("\\greenC", "\\textcolor{##74cf70}{#1}"); +defineMacro("\\greenD", "\\textcolor{##1fab54}{#1}"); +defineMacro("\\greenE", "\\textcolor{##0d923f}{#1}"); +defineMacro("\\goldA", "\\textcolor{##ffd0a9}{#1}"); +defineMacro("\\goldB", "\\textcolor{##ffbb71}{#1}"); +defineMacro("\\goldC", "\\textcolor{##ff9c39}{#1}"); +defineMacro("\\goldD", "\\textcolor{##e07d10}{#1}"); +defineMacro("\\goldE", "\\textcolor{##a75a05}{#1}"); +defineMacro("\\redA", "\\textcolor{##fca9a9}{#1}"); +defineMacro("\\redB", "\\textcolor{##ff8482}{#1}"); +defineMacro("\\redC", "\\textcolor{##f9685d}{#1}"); +defineMacro("\\redD", "\\textcolor{##e84d39}{#1}"); +defineMacro("\\redE", "\\textcolor{##bc2612}{#1}"); +defineMacro("\\maroonA", "\\textcolor{##ffbde0}{#1}"); +defineMacro("\\maroonB", "\\textcolor{##ff92c6}{#1}"); +defineMacro("\\maroonC", "\\textcolor{##ed5fa6}{#1}"); +defineMacro("\\maroonD", "\\textcolor{##ca337c}{#1}"); +defineMacro("\\maroonE", "\\textcolor{##9e034e}{#1}"); +defineMacro("\\purpleA", "\\textcolor{##ddd7ff}{#1}"); +defineMacro("\\purpleB", "\\textcolor{##c6b9fc}{#1}"); +defineMacro("\\purpleC", "\\textcolor{##aa87ff}{#1}"); +defineMacro("\\purpleD", "\\textcolor{##7854ab}{#1}"); +defineMacro("\\purpleE", "\\textcolor{##543b78}{#1}"); +defineMacro("\\mintA", "\\textcolor{##f5f9e8}{#1}"); +defineMacro("\\mintB", "\\textcolor{##edf2df}{#1}"); +defineMacro("\\mintC", "\\textcolor{##e0e5cc}{#1}"); +defineMacro("\\grayA", "\\textcolor{##f6f7f7}{#1}"); +defineMacro("\\grayB", "\\textcolor{##f0f1f2}{#1}"); +defineMacro("\\grayC", "\\textcolor{##e3e5e6}{#1}"); +defineMacro("\\grayD", "\\textcolor{##d6d8da}{#1}"); +defineMacro("\\grayE", "\\textcolor{##babec2}{#1}"); +defineMacro("\\grayF", "\\textcolor{##888d93}{#1}"); +defineMacro("\\grayG", "\\textcolor{##626569}{#1}"); +defineMacro("\\grayH", "\\textcolor{##3b3e40}{#1}"); +defineMacro("\\grayI", "\\textcolor{##21242c}{#1}"); +defineMacro("\\kaBlue", "\\textcolor{##314453}{#1}"); +defineMacro("\\kaGreen", "\\textcolor{##71B307}{#1}"); + +/** + * This file contains the “gullet” where macros are expanded + * until only non-macro tokens remain. + */ +// List of commands that act like macros but aren't defined as a macro, +// function, or symbol. Used in `isDefined`. +var implicitCommands = { + "^": true, + // Parser.js + "_": true, + // Parser.js + "\\limits": true, + // Parser.js + "\\nolimits": true // Parser.js + +}; +class MacroExpander { + constructor(input, settings, mode) { + this.settings = void 0; + this.expansionCount = void 0; + this.lexer = void 0; + this.macros = void 0; + this.stack = void 0; + this.mode = void 0; + this.settings = settings; + this.expansionCount = 0; + this.feed(input); // Make new global namespace + + this.macros = new Namespace(macros, settings.macros); + this.mode = mode; + this.stack = []; // contains tokens in REVERSE order + } + /** + * Feed a new input string to the same MacroExpander + * (with existing macros etc.). + */ + + + feed(input) { + this.lexer = new Lexer(input, this.settings); + } + /** + * Switches between "text" and "math" modes. + */ + + + switchMode(newMode) { + this.mode = newMode; + } + /** + * Start a new group nesting within all namespaces. + */ + + + beginGroup() { + this.macros.beginGroup(); + } + /** + * End current group nesting within all namespaces. + */ + + + endGroup() { + this.macros.endGroup(); + } + /** + * Ends all currently nested groups (if any), restoring values before the + * groups began. Useful in case of an error in the middle of parsing. + */ + + + endGroups() { + this.macros.endGroups(); + } + /** + * Returns the topmost token on the stack, without expanding it. + * Similar in behavior to TeX's `\futurelet`. + */ + + + future() { + if (this.stack.length === 0) { + this.pushToken(this.lexer.lex()); + } + + return this.stack[this.stack.length - 1]; + } + /** + * Remove and return the next unexpanded token. + */ + + + popToken() { + this.future(); // ensure non-empty stack + + return this.stack.pop(); + } + /** + * Add a given token to the token stack. In particular, this get be used + * to put back a token returned from one of the other methods. + */ + + + pushToken(token) { + this.stack.push(token); + } + /** + * Append an array of tokens to the token stack. + */ + + + pushTokens(tokens) { + this.stack.push(...tokens); + } + /** + * Find an macro argument without expanding tokens and append the array of + * tokens to the token stack. Uses Token as a container for the result. + */ + + + scanArgument(isOptional) { + var start; + var end; + var tokens; + + if (isOptional) { + this.consumeSpaces(); // \@ifnextchar gobbles any space following it + + if (this.future().text !== "[") { + return null; + } + + start = this.popToken(); // don't include [ in tokens + + ({ + tokens, + end + } = this.consumeArg(["]"])); + } else { + ({ + tokens, + start, + end + } = this.consumeArg()); + } // indicate the end of an argument + + + this.pushToken(new Token("EOF", end.loc)); + this.pushTokens(tokens); + return start.range(end, ""); + } + /** + * Consume all following space tokens, without expansion. + */ + + + consumeSpaces() { + for (;;) { + var token = this.future(); + + if (token.text === " ") { + this.stack.pop(); + } else { + break; + } + } + } + /** + * Consume an argument from the token stream, and return the resulting array + * of tokens and start/end token. + */ + + + consumeArg(delims) { + // The argument for a delimited parameter is the shortest (possibly + // empty) sequence of tokens with properly nested {...} groups that is + // followed ... by this particular list of non-parameter tokens. + // The argument for an undelimited parameter is the next nonblank + // token, unless that token is ‘{’, when the argument will be the + // entire {...} group that follows. + var tokens = []; + var isDelimited = delims && delims.length > 0; + + if (!isDelimited) { + // Ignore spaces between arguments. As the TeXbook says: + // "After you have said ‘\def\row#1#2{...}’, you are allowed to + // put spaces between the arguments (e.g., ‘\row x n’), because + // TeX doesn’t use single spaces as undelimited arguments." + this.consumeSpaces(); + } + + var start = this.future(); + var tok; + var depth = 0; + var match = 0; + + do { + tok = this.popToken(); + tokens.push(tok); + + if (tok.text === "{") { + ++depth; + } else if (tok.text === "}") { + --depth; + + if (depth === -1) { + throw new ParseError("Extra }", tok); + } + } else if (tok.text === "EOF") { + throw new ParseError("Unexpected end of input in a macro argument" + ", expected '" + (delims && isDelimited ? delims[match] : "}") + "'", tok); + } + + if (delims && isDelimited) { + if ((depth === 0 || depth === 1 && delims[match] === "{") && tok.text === delims[match]) { + ++match; + + if (match === delims.length) { + // don't include delims in tokens + tokens.splice(-match, match); + break; + } + } else { + match = 0; + } + } + } while (depth !== 0 || isDelimited); // If the argument found ... has the form ‘{}’, + // ... the outermost braces enclosing the argument are removed + + + if (start.text === "{" && tokens[tokens.length - 1].text === "}") { + tokens.pop(); + tokens.shift(); + } + + tokens.reverse(); // to fit in with stack order + + return { + tokens, + start, + end: tok + }; + } + /** + * Consume the specified number of (delimited) arguments from the token + * stream and return the resulting array of arguments. + */ + + + consumeArgs(numArgs, delimiters) { + if (delimiters) { + if (delimiters.length !== numArgs + 1) { + throw new ParseError("The length of delimiters doesn't match the number of args!"); + } + + var delims = delimiters[0]; + + for (var i = 0; i < delims.length; i++) { + var tok = this.popToken(); + + if (delims[i] !== tok.text) { + throw new ParseError("Use of the macro doesn't match its definition", tok); + } + } + } + + var args = []; + + for (var _i = 0; _i < numArgs; _i++) { + args.push(this.consumeArg(delimiters && delimiters[_i + 1]).tokens); + } + + return args; + } + /** + * Increment `expansionCount` by the specified amount. + * Throw an error if it exceeds `maxExpand`. + */ + + + countExpansion(amount) { + this.expansionCount += amount; + + if (this.expansionCount > this.settings.maxExpand) { + throw new ParseError("Too many expansions: infinite loop or " + "need to increase maxExpand setting"); + } + } + /** + * Expand the next token only once if possible. + * + * If the token is expanded, the resulting tokens will be pushed onto + * the stack in reverse order, and the number of such tokens will be + * returned. This number might be zero or positive. + * + * If not, the return value is `false`, and the next token remains at the + * top of the stack. + * + * In either case, the next token will be on the top of the stack, + * or the stack will be empty (in case of empty expansion + * and no other tokens). + * + * Used to implement `expandAfterFuture` and `expandNextToken`. + * + * If expandableOnly, only expandable tokens are expanded and + * an undefined control sequence results in an error. + */ + + + expandOnce(expandableOnly) { + var topToken = this.popToken(); + var name = topToken.text; + var expansion = !topToken.noexpand ? this._getExpansion(name) : null; + + if (expansion == null || expandableOnly && expansion.unexpandable) { + if (expandableOnly && expansion == null && name[0] === "\\" && !this.isDefined(name)) { + throw new ParseError("Undefined control sequence: " + name); + } + + this.pushToken(topToken); + return false; + } + + this.countExpansion(1); + var tokens = expansion.tokens; + var args = this.consumeArgs(expansion.numArgs, expansion.delimiters); + + if (expansion.numArgs) { + // paste arguments in place of the placeholders + tokens = tokens.slice(); // make a shallow copy + + for (var i = tokens.length - 1; i >= 0; --i) { + var tok = tokens[i]; + + if (tok.text === "#") { + if (i === 0) { + throw new ParseError("Incomplete placeholder at end of macro body", tok); + } + + tok = tokens[--i]; // next token on stack + + if (tok.text === "#") { + // ## → # + tokens.splice(i + 1, 1); // drop first # + } else if (/^[1-9]$/.test(tok.text)) { + // replace the placeholder with the indicated argument + tokens.splice(i, 2, ...args[+tok.text - 1]); + } else { + throw new ParseError("Not a valid argument number", tok); + } + } + } + } // Concatenate expansion onto top of stack. + + + this.pushTokens(tokens); + return tokens.length; + } + /** + * Expand the next token only once (if possible), and return the resulting + * top token on the stack (without removing anything from the stack). + * Similar in behavior to TeX's `\expandafter\futurelet`. + * Equivalent to expandOnce() followed by future(). + */ + + + expandAfterFuture() { + this.expandOnce(); + return this.future(); + } + /** + * Recursively expand first token, then return first non-expandable token. + */ + + + expandNextToken() { + for (;;) { + if (this.expandOnce() === false) { + // fully expanded + var token = this.stack.pop(); // the token after \noexpand is interpreted as if its meaning + // were ‘\relax’ + + if (token.treatAsRelax) { + token.text = "\\relax"; + } + + return token; + } + } // Flow unable to figure out that this pathway is impossible. + // https://github.com/facebook/flow/issues/4808 + + + throw new Error(); // eslint-disable-line no-unreachable + } + /** + * Fully expand the given macro name and return the resulting list of + * tokens, or return `undefined` if no such macro is defined. + */ + + + expandMacro(name) { + return this.macros.has(name) ? this.expandTokens([new Token(name)]) : undefined; + } + /** + * Fully expand the given token stream and return the resulting list of + * tokens. Note that the input tokens are in reverse order, but the + * output tokens are in forward order. + */ + + + expandTokens(tokens) { + var output = []; + var oldStackLength = this.stack.length; + this.pushTokens(tokens); + + while (this.stack.length > oldStackLength) { + // Expand only expandable tokens + if (this.expandOnce(true) === false) { + // fully expanded + var token = this.stack.pop(); + + if (token.treatAsRelax) { + // the expansion of \noexpand is the token itself + token.noexpand = false; + token.treatAsRelax = false; + } + + output.push(token); + } + } // Count all of these tokens as additional expansions, to prevent + // exponential blowup from linearly many \edef's. + + + this.countExpansion(output.length); + return output; + } + /** + * Fully expand the given macro name and return the result as a string, + * or return `undefined` if no such macro is defined. + */ + + + expandMacroAsText(name) { + var tokens = this.expandMacro(name); + + if (tokens) { + return tokens.map(token => token.text).join(""); + } else { + return tokens; + } + } + /** + * Returns the expanded macro as a reversed array of tokens and a macro + * argument count. Or returns `null` if no such macro. + */ + + + _getExpansion(name) { + var definition = this.macros.get(name); + + if (definition == null) { + // mainly checking for undefined here + return definition; + } // If a single character has an associated catcode other than 13 + // (active character), then don't expand it. + + + if (name.length === 1) { + var catcode = this.lexer.catcodes[name]; + + if (catcode != null && catcode !== 13) { + return; + } + } + + var expansion = typeof definition === "function" ? definition(this) : definition; + + if (typeof expansion === "string") { + var numArgs = 0; + + if (expansion.indexOf("#") !== -1) { + var stripped = expansion.replace(/##/g, ""); + + while (stripped.indexOf("#" + (numArgs + 1)) !== -1) { + ++numArgs; + } + } + + var bodyLexer = new Lexer(expansion, this.settings); + var tokens = []; + var tok = bodyLexer.lex(); + + while (tok.text !== "EOF") { + tokens.push(tok); + tok = bodyLexer.lex(); + } + + tokens.reverse(); // to fit in with stack using push and pop + + var expanded = { + tokens, + numArgs + }; + return expanded; + } + + return expansion; + } + /** + * Determine whether a command is currently "defined" (has some + * functionality), meaning that it's a macro (in the current group), + * a function, a symbol, or one of the special commands listed in + * `implicitCommands`. + */ + + + isDefined(name) { + return this.macros.has(name) || functions.hasOwnProperty(name) || symbols.math.hasOwnProperty(name) || symbols.text.hasOwnProperty(name) || implicitCommands.hasOwnProperty(name); + } + /** + * Determine whether a command is expandable. + */ + + + isExpandable(name) { + var macro = this.macros.get(name); + return macro != null ? typeof macro === "string" || typeof macro === "function" || !macro.unexpandable : functions.hasOwnProperty(name) && !functions[name].primitive; + } + +} + +// Helpers for Parser.js handling of Unicode (sub|super)script characters. +var unicodeSubRegEx = /^[₊₋₌₍₎₀₁₂₃₄₅₆₇₈₉ₐₑₕᵢⱼₖₗₘₙₒₚᵣₛₜᵤᵥₓᵦᵧᵨᵩᵪ]/; +var uSubsAndSups = Object.freeze({ + '₊': '+', + '₋': '-', + '₌': '=', + '₍': '(', + '₎': ')', + '₀': '0', + '₁': '1', + '₂': '2', + '₃': '3', + '₄': '4', + '₅': '5', + '₆': '6', + '₇': '7', + '₈': '8', + '₉': '9', + '\u2090': 'a', + '\u2091': 'e', + '\u2095': 'h', + '\u1D62': 'i', + '\u2C7C': 'j', + '\u2096': 'k', + '\u2097': 'l', + '\u2098': 'm', + '\u2099': 'n', + '\u2092': 'o', + '\u209A': 'p', + '\u1D63': 'r', + '\u209B': 's', + '\u209C': 't', + '\u1D64': 'u', + '\u1D65': 'v', + '\u2093': 'x', + '\u1D66': 'β', + '\u1D67': 'γ', + '\u1D68': 'ρ', + '\u1D69': '\u03d5', + '\u1D6A': 'χ', + '⁺': '+', + '⁻': '-', + '⁼': '=', + '⁽': '(', + '⁾': ')', + '⁰': '0', + '¹': '1', + '²': '2', + '³': '3', + '⁴': '4', + '⁵': '5', + '⁶': '6', + '⁷': '7', + '⁸': '8', + '⁹': '9', + '\u1D2C': 'A', + '\u1D2E': 'B', + '\u1D30': 'D', + '\u1D31': 'E', + '\u1D33': 'G', + '\u1D34': 'H', + '\u1D35': 'I', + '\u1D36': 'J', + '\u1D37': 'K', + '\u1D38': 'L', + '\u1D39': 'M', + '\u1D3A': 'N', + '\u1D3C': 'O', + '\u1D3E': 'P', + '\u1D3F': 'R', + '\u1D40': 'T', + '\u1D41': 'U', + '\u2C7D': 'V', + '\u1D42': 'W', + '\u1D43': 'a', + '\u1D47': 'b', + '\u1D9C': 'c', + '\u1D48': 'd', + '\u1D49': 'e', + '\u1DA0': 'f', + '\u1D4D': 'g', + '\u02B0': 'h', + '\u2071': 'i', + '\u02B2': 'j', + '\u1D4F': 'k', + '\u02E1': 'l', + '\u1D50': 'm', + '\u207F': 'n', + '\u1D52': 'o', + '\u1D56': 'p', + '\u02B3': 'r', + '\u02E2': 's', + '\u1D57': 't', + '\u1D58': 'u', + '\u1D5B': 'v', + '\u02B7': 'w', + '\u02E3': 'x', + '\u02B8': 'y', + '\u1DBB': 'z', + '\u1D5D': 'β', + '\u1D5E': 'γ', + '\u1D5F': 'δ', + '\u1D60': '\u03d5', + '\u1D61': 'χ', + '\u1DBF': 'θ' +}); + +/* eslint no-constant-condition:0 */ + +var unicodeAccents = { + "́": { + "text": "\\'", + "math": "\\acute" + }, + "̀": { + "text": "\\`", + "math": "\\grave" + }, + "̈": { + "text": "\\\"", + "math": "\\ddot" + }, + "̃": { + "text": "\\~", + "math": "\\tilde" + }, + "̄": { + "text": "\\=", + "math": "\\bar" + }, + "̆": { + "text": "\\u", + "math": "\\breve" + }, + "̌": { + "text": "\\v", + "math": "\\check" + }, + "̂": { + "text": "\\^", + "math": "\\hat" + }, + "̇": { + "text": "\\.", + "math": "\\dot" + }, + "̊": { + "text": "\\r", + "math": "\\mathring" + }, + "̋": { + "text": "\\H" + }, + "̧": { + "text": "\\c" + } +}; +var unicodeSymbols = { + "á": "á", + "à": "à", + "ä": "ä", + "ǟ": "ǟ", + "ã": "ã", + "ā": "ā", + "ă": "ă", + "ắ": "ắ", + "ằ": "ằ", + "ẵ": "ẵ", + "ǎ": "ǎ", + "â": "â", + "ấ": "ấ", + "ầ": "ầ", + "ẫ": "ẫ", + "ȧ": "ȧ", + "ǡ": "ǡ", + "å": "å", + "ǻ": "ǻ", + "ḃ": "ḃ", + "ć": "ć", + "ḉ": "ḉ", + "č": "č", + "ĉ": "ĉ", + "ċ": "ċ", + "ç": "ç", + "ď": "ď", + "ḋ": "ḋ", + "ḑ": "ḑ", + "é": "é", + "è": "è", + "ë": "ë", + "ẽ": "ẽ", + "ē": "ē", + "ḗ": "ḗ", + "ḕ": "ḕ", + "ĕ": "ĕ", + "ḝ": "ḝ", + "ě": "ě", + "ê": "ê", + "ế": "ế", + "ề": "ề", + "ễ": "ễ", + "ė": "ė", + "ȩ": "ȩ", + "ḟ": "ḟ", + "ǵ": "ǵ", + "ḡ": "ḡ", + "ğ": "ğ", + "ǧ": "ǧ", + "ĝ": "ĝ", + "ġ": "ġ", + "ģ": "ģ", + "ḧ": "ḧ", + "ȟ": "ȟ", + "ĥ": "ĥ", + "ḣ": "ḣ", + "ḩ": "ḩ", + "í": "í", + "ì": "ì", + "ï": "ï", + "ḯ": "ḯ", + "ĩ": "ĩ", + "ī": "ī", + "ĭ": "ĭ", + "ǐ": "ǐ", + "î": "î", + "ǰ": "ǰ", + "ĵ": "ĵ", + "ḱ": "ḱ", + "ǩ": "ǩ", + "ķ": "ķ", + "ĺ": "ĺ", + "ľ": "ľ", + "ļ": "ļ", + "ḿ": "ḿ", + "ṁ": "ṁ", + "ń": "ń", + "ǹ": "ǹ", + "ñ": "ñ", + "ň": "ň", + "ṅ": "ṅ", + "ņ": "ņ", + "ó": "ó", + "ò": "ò", + "ö": "ö", + "ȫ": "ȫ", + "õ": "õ", + "ṍ": "ṍ", + "ṏ": "ṏ", + "ȭ": "ȭ", + "ō": "ō", + "ṓ": "ṓ", + "ṑ": "ṑ", + "ŏ": "ŏ", + "ǒ": "ǒ", + "ô": "ô", + "ố": "ố", + "ồ": "ồ", + "ỗ": "ỗ", + "ȯ": "ȯ", + "ȱ": "ȱ", + "ő": "ő", + "ṕ": "ṕ", + "ṗ": "ṗ", + "ŕ": "ŕ", + "ř": "ř", + "ṙ": "ṙ", + "ŗ": "ŗ", + "ś": "ś", + "ṥ": "ṥ", + "š": "š", + "ṧ": "ṧ", + "ŝ": "ŝ", + "ṡ": "ṡ", + "ş": "ş", + "ẗ": "ẗ", + "ť": "ť", + "ṫ": "ṫ", + "ţ": "ţ", + "ú": "ú", + "ù": "ù", + "ü": "ü", + "ǘ": "ǘ", + "ǜ": "ǜ", + "ǖ": "ǖ", + "ǚ": "ǚ", + "ũ": "ũ", + "ṹ": "ṹ", + "ū": "ū", + "ṻ": "ṻ", + "ŭ": "ŭ", + "ǔ": "ǔ", + "û": "û", + "ů": "ů", + "ű": "ű", + "ṽ": "ṽ", + "ẃ": "ẃ", + "ẁ": "ẁ", + "ẅ": "ẅ", + "ŵ": "ŵ", + "ẇ": "ẇ", + "ẘ": "ẘ", + "ẍ": "ẍ", + "ẋ": "ẋ", + "ý": "ý", + "ỳ": "ỳ", + "ÿ": "ÿ", + "ỹ": "ỹ", + "ȳ": "ȳ", + "ŷ": "ŷ", + "ẏ": "ẏ", + "ẙ": "ẙ", + "ź": "ź", + "ž": "ž", + "ẑ": "ẑ", + "ż": "ż", + "Á": "Á", + "À": "À", + "Ä": "Ä", + "Ǟ": "Ǟ", + "Ã": "Ã", + "Ā": "Ā", + "Ă": "Ă", + "Ắ": "Ắ", + "Ằ": "Ằ", + "Ẵ": "Ẵ", + "Ǎ": "Ǎ", + "Â": "Â", + "Ấ": "Ấ", + "Ầ": "Ầ", + "Ẫ": "Ẫ", + "Ȧ": "Ȧ", + "Ǡ": "Ǡ", + "Å": "Å", + "Ǻ": "Ǻ", + "Ḃ": "Ḃ", + "Ć": "Ć", + "Ḉ": "Ḉ", + "Č": "Č", + "Ĉ": "Ĉ", + "Ċ": "Ċ", + "Ç": "Ç", + "Ď": "Ď", + "Ḋ": "Ḋ", + "Ḑ": "Ḑ", + "É": "É", + "È": "È", + "Ë": "Ë", + "Ẽ": "Ẽ", + "Ē": "Ē", + "Ḗ": "Ḗ", + "Ḕ": "Ḕ", + "Ĕ": "Ĕ", + "Ḝ": "Ḝ", + "Ě": "Ě", + "Ê": "Ê", + "Ế": "Ế", + "Ề": "Ề", + "Ễ": "Ễ", + "Ė": "Ė", + "Ȩ": "Ȩ", + "Ḟ": "Ḟ", + "Ǵ": "Ǵ", + "Ḡ": "Ḡ", + "Ğ": "Ğ", + "Ǧ": "Ǧ", + "Ĝ": "Ĝ", + "Ġ": "Ġ", + "Ģ": "Ģ", + "Ḧ": "Ḧ", + "Ȟ": "Ȟ", + "Ĥ": "Ĥ", + "Ḣ": "Ḣ", + "Ḩ": "Ḩ", + "Í": "Í", + "Ì": "Ì", + "Ï": "Ï", + "Ḯ": "Ḯ", + "Ĩ": "Ĩ", + "Ī": "Ī", + "Ĭ": "Ĭ", + "Ǐ": "Ǐ", + "Î": "Î", + "İ": "İ", + "Ĵ": "Ĵ", + "Ḱ": "Ḱ", + "Ǩ": "Ǩ", + "Ķ": "Ķ", + "Ĺ": "Ĺ", + "Ľ": "Ľ", + "Ļ": "Ļ", + "Ḿ": "Ḿ", + "Ṁ": "Ṁ", + "Ń": "Ń", + "Ǹ": "Ǹ", + "Ñ": "Ñ", + "Ň": "Ň", + "Ṅ": "Ṅ", + "Ņ": "Ņ", + "Ó": "Ó", + "Ò": "Ò", + "Ö": "Ö", + "Ȫ": "Ȫ", + "Õ": "Õ", + "Ṍ": "Ṍ", + "Ṏ": "Ṏ", + "Ȭ": "Ȭ", + "Ō": "Ō", + "Ṓ": "Ṓ", + "Ṑ": "Ṑ", + "Ŏ": "Ŏ", + "Ǒ": "Ǒ", + "Ô": "Ô", + "Ố": "Ố", + "Ồ": "Ồ", + "Ỗ": "Ỗ", + "Ȯ": "Ȯ", + "Ȱ": "Ȱ", + "Ő": "Ő", + "Ṕ": "Ṕ", + "Ṗ": "Ṗ", + "Ŕ": "Ŕ", + "Ř": "Ř", + "Ṙ": "Ṙ", + "Ŗ": "Ŗ", + "Ś": "Ś", + "Ṥ": "Ṥ", + "Š": "Š", + "Ṧ": "Ṧ", + "Ŝ": "Ŝ", + "Ṡ": "Ṡ", + "Ş": "Ş", + "Ť": "Ť", + "Ṫ": "Ṫ", + "Ţ": "Ţ", + "Ú": "Ú", + "Ù": "Ù", + "Ü": "Ü", + "Ǘ": "Ǘ", + "Ǜ": "Ǜ", + "Ǖ": "Ǖ", + "Ǚ": "Ǚ", + "Ũ": "Ũ", + "Ṹ": "Ṹ", + "Ū": "Ū", + "Ṻ": "Ṻ", + "Ŭ": "Ŭ", + "Ǔ": "Ǔ", + "Û": "Û", + "Ů": "Ů", + "Ű": "Ű", + "Ṽ": "Ṽ", + "Ẃ": "Ẃ", + "Ẁ": "Ẁ", + "Ẅ": "Ẅ", + "Ŵ": "Ŵ", + "Ẇ": "Ẇ", + "Ẍ": "Ẍ", + "Ẋ": "Ẋ", + "Ý": "Ý", + "Ỳ": "Ỳ", + "Ÿ": "Ÿ", + "Ỹ": "Ỹ", + "Ȳ": "Ȳ", + "Ŷ": "Ŷ", + "Ẏ": "Ẏ", + "Ź": "Ź", + "Ž": "Ž", + "Ẑ": "Ẑ", + "Ż": "Ż", + "ά": "ά", + "ὰ": "ὰ", + "ᾱ": "ᾱ", + "ᾰ": "ᾰ", + "έ": "έ", + "ὲ": "ὲ", + "ή": "ή", + "ὴ": "ὴ", + "ί": "ί", + "ὶ": "ὶ", + "ϊ": "ϊ", + "ΐ": "ΐ", + "ῒ": "ῒ", + "ῑ": "ῑ", + "ῐ": "ῐ", + "ό": "ό", + "ὸ": "ὸ", + "ύ": "ύ", + "ὺ": "ὺ", + "ϋ": "ϋ", + "ΰ": "ΰ", + "ῢ": "ῢ", + "ῡ": "ῡ", + "ῠ": "ῠ", + "ώ": "ώ", + "ὼ": "ὼ", + "Ύ": "Ύ", + "Ὺ": "Ὺ", + "Ϋ": "Ϋ", + "Ῡ": "Ῡ", + "Ῠ": "Ῠ", + "Ώ": "Ώ", + "Ὼ": "Ὼ" +}; + +/** + * This file contains the parser used to parse out a TeX expression from the + * input. Since TeX isn't context-free, standard parsers don't work particularly + * well. + * + * The strategy of this parser is as such: + * + * The main functions (the `.parse...` ones) take a position in the current + * parse string to parse tokens from. The lexer (found in Lexer.js, stored at + * this.gullet.lexer) also supports pulling out tokens at arbitrary places. When + * individual tokens are needed at a position, the lexer is called to pull out a + * token, which is then used. + * + * The parser has a property called "mode" indicating the mode that + * the parser is currently in. Currently it has to be one of "math" or + * "text", which denotes whether the current environment is a math-y + * one or a text-y one (e.g. inside \text). Currently, this serves to + * limit the functions which can be used in text mode. + * + * The main functions then return an object which contains the useful data that + * was parsed at its given point, and a new position at the end of the parsed + * data. The main functions can call each other and continue the parsing by + * using the returned position as a new starting point. + * + * There are also extra `.handle...` functions, which pull out some reused + * functionality into self-contained functions. + * + * The functions return ParseNodes. + */ +class Parser { + constructor(input, settings) { + this.mode = void 0; + this.gullet = void 0; + this.settings = void 0; + this.leftrightDepth = void 0; + this.nextToken = void 0; + // Start in math mode + this.mode = "math"; // Create a new macro expander (gullet) and (indirectly via that) also a + // new lexer (mouth) for this parser (stomach, in the language of TeX) + + this.gullet = new MacroExpander(input, settings, this.mode); // Store the settings for use in parsing + + this.settings = settings; // Count leftright depth (for \middle errors) + + this.leftrightDepth = 0; + } + /** + * Checks a result to make sure it has the right type, and throws an + * appropriate error otherwise. + */ + + + expect(text, consume) { + if (consume === void 0) { + consume = true; + } + + if (this.fetch().text !== text) { + throw new ParseError("Expected '" + text + "', got '" + this.fetch().text + "'", this.fetch()); + } + + if (consume) { + this.consume(); + } + } + /** + * Discards the current lookahead token, considering it consumed. + */ + + + consume() { + this.nextToken = null; + } + /** + * Return the current lookahead token, or if there isn't one (at the + * beginning, or if the previous lookahead token was consume()d), + * fetch the next token as the new lookahead token and return it. + */ + + + fetch() { + if (this.nextToken == null) { + this.nextToken = this.gullet.expandNextToken(); + } + + return this.nextToken; + } + /** + * Switches between "text" and "math" modes. + */ + + + switchMode(newMode) { + this.mode = newMode; + this.gullet.switchMode(newMode); + } + /** + * Main parsing function, which parses an entire input. + */ + + + parse() { + if (!this.settings.globalGroup) { + // Create a group namespace for the math expression. + // (LaTeX creates a new group for every $...$, $$...$$, \[...\].) + this.gullet.beginGroup(); + } // Use old \color behavior (same as LaTeX's \textcolor) if requested. + // We do this within the group for the math expression, so it doesn't + // pollute settings.macros. + + + if (this.settings.colorIsTextColor) { + this.gullet.macros.set("\\color", "\\textcolor"); + } + + try { + // Try to parse the input + var parse = this.parseExpression(false); // If we succeeded, make sure there's an EOF at the end + + this.expect("EOF"); // End the group namespace for the expression + + if (!this.settings.globalGroup) { + this.gullet.endGroup(); + } + + return parse; // Close any leftover groups in case of a parse error. + } finally { + this.gullet.endGroups(); + } + } + /** + * Fully parse a separate sequence of tokens as a separate job. + * Tokens should be specified in reverse order, as in a MacroDefinition. + */ + + + subparse(tokens) { + // Save the next token from the current job. + var oldToken = this.nextToken; + this.consume(); // Run the new job, terminating it with an excess '}' + + this.gullet.pushToken(new Token("}")); + this.gullet.pushTokens(tokens); + var parse = this.parseExpression(false); + this.expect("}"); // Restore the next token from the current job. + + this.nextToken = oldToken; + return parse; + } + + /** + * Parses an "expression", which is a list of atoms. + * + * `breakOnInfix`: Should the parsing stop when we hit infix nodes? This + * happens when functions have higher precedence han infix + * nodes in implicit parses. + * + * `breakOnTokenText`: The text of the token that the expression should end + * with, or `null` if something else should end the + * expression. + */ + parseExpression(breakOnInfix, breakOnTokenText) { + var body = []; // Keep adding atoms to the body until we can't parse any more atoms (either + // we reached the end, a }, or a \right) + + while (true) { + // Ignore spaces in math mode + if (this.mode === "math") { + this.consumeSpaces(); + } + + var lex = this.fetch(); + + if (Parser.endOfExpression.indexOf(lex.text) !== -1) { + break; + } + + if (breakOnTokenText && lex.text === breakOnTokenText) { + break; + } + + if (breakOnInfix && functions[lex.text] && functions[lex.text].infix) { + break; + } + + var atom = this.parseAtom(breakOnTokenText); + + if (!atom) { + break; + } else if (atom.type === "internal") { + // Internal nodes do not appear in parse tree + continue; + } + + body.push(atom); + } + + if (this.mode === "text") { + this.formLigatures(body); + } + + return this.handleInfixNodes(body); + } + /** + * Rewrites infix operators such as \over with corresponding commands such + * as \frac. + * + * There can only be one infix operator per group. If there's more than one + * then the expression is ambiguous. This can be resolved by adding {}. + */ + + + handleInfixNodes(body) { + var overIndex = -1; + var funcName; + + for (var i = 0; i < body.length; i++) { + if (body[i].type === "infix") { + if (overIndex !== -1) { + throw new ParseError("only one infix operator per group", body[i].token); + } + + overIndex = i; + funcName = body[i].replaceWith; + } + } + + if (overIndex !== -1 && funcName) { + var numerNode; + var denomNode; + var numerBody = body.slice(0, overIndex); + var denomBody = body.slice(overIndex + 1); + + if (numerBody.length === 1 && numerBody[0].type === "ordgroup") { + numerNode = numerBody[0]; + } else { + numerNode = { + type: "ordgroup", + mode: this.mode, + body: numerBody + }; + } + + if (denomBody.length === 1 && denomBody[0].type === "ordgroup") { + denomNode = denomBody[0]; + } else { + denomNode = { + type: "ordgroup", + mode: this.mode, + body: denomBody + }; + } + + var node; + + if (funcName === "\\\\abovefrac") { + node = this.callFunction(funcName, [numerNode, body[overIndex], denomNode], []); + } else { + node = this.callFunction(funcName, [numerNode, denomNode], []); + } + + return [node]; + } else { + return body; + } + } + /** + * Handle a subscript or superscript with nice errors. + */ + + + handleSupSubscript(name // For error reporting. + ) { + var symbolToken = this.fetch(); + var symbol = symbolToken.text; + this.consume(); + this.consumeSpaces(); // ignore spaces before sup/subscript argument + // Skip over allowed internal nodes such as \relax + + var group; + + do { + var _group; + + group = this.parseGroup(name); + } while (((_group = group) == null ? void 0 : _group.type) === "internal"); + + if (!group) { + throw new ParseError("Expected group after '" + symbol + "'", symbolToken); + } + + return group; + } + /** + * Converts the textual input of an unsupported command into a text node + * contained within a color node whose color is determined by errorColor + */ + + + formatUnsupportedCmd(text) { + var textordArray = []; + + for (var i = 0; i < text.length; i++) { + textordArray.push({ + type: "textord", + mode: "text", + text: text[i] + }); + } + + var textNode = { + type: "text", + mode: this.mode, + body: textordArray + }; + var colorNode = { + type: "color", + mode: this.mode, + color: this.settings.errorColor, + body: [textNode] + }; + return colorNode; + } + /** + * Parses a group with optional super/subscripts. + */ + + + parseAtom(breakOnTokenText) { + // The body of an atom is an implicit group, so that things like + // \left(x\right)^2 work correctly. + var base = this.parseGroup("atom", breakOnTokenText); // Internal nodes (e.g. \relax) cannot support super/subscripts. + // Instead we will pick up super/subscripts with blank base next round. + + if ((base == null ? void 0 : base.type) === "internal") { + return base; + } // In text mode, we don't have superscripts or subscripts + + + if (this.mode === "text") { + return base; + } // Note that base may be empty (i.e. null) at this point. + + + var superscript; + var subscript; + + while (true) { + // Guaranteed in math mode, so eat any spaces first. + this.consumeSpaces(); // Lex the first token + + var lex = this.fetch(); + + if (lex.text === "\\limits" || lex.text === "\\nolimits") { + // We got a limit control + if (base && base.type === "op") { + var limits = lex.text === "\\limits"; + base.limits = limits; + base.alwaysHandleSupSub = true; + } else if (base && base.type === "operatorname") { + if (base.alwaysHandleSupSub) { + base.limits = lex.text === "\\limits"; + } + } else { + throw new ParseError("Limit controls must follow a math operator", lex); + } + + this.consume(); + } else if (lex.text === "^") { + // We got a superscript start + if (superscript) { + throw new ParseError("Double superscript", lex); + } + + superscript = this.handleSupSubscript("superscript"); + } else if (lex.text === "_") { + // We got a subscript start + if (subscript) { + throw new ParseError("Double subscript", lex); + } + + subscript = this.handleSupSubscript("subscript"); + } else if (lex.text === "'") { + // We got a prime + if (superscript) { + throw new ParseError("Double superscript", lex); + } + + var prime = { + type: "textord", + mode: this.mode, + text: "\\prime" + }; // Many primes can be grouped together, so we handle this here + + var primes = [prime]; + this.consume(); // Keep lexing tokens until we get something that's not a prime + + while (this.fetch().text === "'") { + // For each one, add another prime to the list + primes.push(prime); + this.consume(); + } // If there's a superscript following the primes, combine that + // superscript in with the primes. + + + if (this.fetch().text === "^") { + primes.push(this.handleSupSubscript("superscript")); + } // Put everything into an ordgroup as the superscript + + + superscript = { + type: "ordgroup", + mode: this.mode, + body: primes + }; + } else if (uSubsAndSups[lex.text]) { + // A Unicode subscript or superscript character. + // We treat these similarly to the unicode-math package. + // So we render a string of Unicode (sub|super)scripts the + // same as a (sub|super)script of regular characters. + var isSub = unicodeSubRegEx.test(lex.text); + var subsupTokens = []; + subsupTokens.push(new Token(uSubsAndSups[lex.text])); + this.consume(); // Continue fetching tokens to fill out the string. + + while (true) { + var token = this.fetch().text; + + if (!uSubsAndSups[token]) { + break; + } + + if (unicodeSubRegEx.test(token) !== isSub) { + break; + } + + subsupTokens.unshift(new Token(uSubsAndSups[token])); + this.consume(); + } // Now create a (sub|super)script. + + + var body = this.subparse(subsupTokens); + + if (isSub) { + subscript = { + type: "ordgroup", + mode: "math", + body + }; + } else { + superscript = { + type: "ordgroup", + mode: "math", + body + }; + } + } else { + // If it wasn't ^, _, or ', stop parsing super/subscripts + break; + } + } // Base must be set if superscript or subscript are set per logic above, + // but need to check here for type check to pass. + + + if (superscript || subscript) { + // If we got either a superscript or subscript, create a supsub + return { + type: "supsub", + mode: this.mode, + base: base, + sup: superscript, + sub: subscript + }; + } else { + // Otherwise return the original body + return base; + } + } + /** + * Parses an entire function, including its base and all of its arguments. + */ + + + parseFunction(breakOnTokenText, name // For determining its context + ) { + var token = this.fetch(); + var func = token.text; + var funcData = functions[func]; + + if (!funcData) { + return null; + } + + this.consume(); // consume command token + + if (name && name !== "atom" && !funcData.allowedInArgument) { + throw new ParseError("Got function '" + func + "' with no arguments" + (name ? " as " + name : ""), token); + } else if (this.mode === "text" && !funcData.allowedInText) { + throw new ParseError("Can't use function '" + func + "' in text mode", token); + } else if (this.mode === "math" && funcData.allowedInMath === false) { + throw new ParseError("Can't use function '" + func + "' in math mode", token); + } + + var { + args, + optArgs + } = this.parseArguments(func, funcData); + return this.callFunction(func, args, optArgs, token, breakOnTokenText); + } + /** + * Call a function handler with a suitable context and arguments. + */ + + + callFunction(name, args, optArgs, token, breakOnTokenText) { + var context = { + funcName: name, + parser: this, + token, + breakOnTokenText + }; + var func = functions[name]; + + if (func && func.handler) { + return func.handler(context, args, optArgs); + } else { + throw new ParseError("No function handler for " + name); + } + } + /** + * Parses the arguments of a function or environment + */ + + + parseArguments(func, // Should look like "\name" or "\begin{name}". + funcData) { + var totalArgs = funcData.numArgs + funcData.numOptionalArgs; + + if (totalArgs === 0) { + return { + args: [], + optArgs: [] + }; + } + + var args = []; + var optArgs = []; + + for (var i = 0; i < totalArgs; i++) { + var argType = funcData.argTypes && funcData.argTypes[i]; + var isOptional = i < funcData.numOptionalArgs; + + if (funcData.primitive && argType == null || // \sqrt expands into primitive if optional argument doesn't exist + funcData.type === "sqrt" && i === 1 && optArgs[0] == null) { + argType = "primitive"; + } + + var arg = this.parseGroupOfType("argument to '" + func + "'", argType, isOptional); + + if (isOptional) { + optArgs.push(arg); + } else if (arg != null) { + args.push(arg); + } else { + // should be unreachable + throw new ParseError("Null argument, please report this as a bug"); + } + } + + return { + args, + optArgs + }; + } + /** + * Parses a group when the mode is changing. + */ + + + parseGroupOfType(name, type, optional) { + switch (type) { + case "color": + return this.parseColorGroup(optional); + + case "size": + return this.parseSizeGroup(optional); + + case "url": + return this.parseUrlGroup(optional); + + case "math": + case "text": + return this.parseArgumentGroup(optional, type); + + case "hbox": + { + // hbox argument type wraps the argument in the equivalent of + // \hbox, which is like \text but switching to \textstyle size. + var group = this.parseArgumentGroup(optional, "text"); + return group != null ? { + type: "styling", + mode: group.mode, + body: [group], + style: "text" // simulate \textstyle + + } : null; + } + + case "raw": + { + var token = this.parseStringGroup("raw", optional); + return token != null ? { + type: "raw", + mode: "text", + string: token.text + } : null; + } + + case "primitive": + { + if (optional) { + throw new ParseError("A primitive argument cannot be optional"); + } + + var _group2 = this.parseGroup(name); + + if (_group2 == null) { + throw new ParseError("Expected group as " + name, this.fetch()); + } + + return _group2; + } + + case "original": + case null: + case undefined: + return this.parseArgumentGroup(optional); + + default: + throw new ParseError("Unknown group type as " + name, this.fetch()); + } + } + /** + * Discard any space tokens, fetching the next non-space token. + */ + + + consumeSpaces() { + while (this.fetch().text === " ") { + this.consume(); + } + } + /** + * Parses a group, essentially returning the string formed by the + * brace-enclosed tokens plus some position information. + */ + + + parseStringGroup(modeName, // Used to describe the mode in error messages. + optional) { + var argToken = this.gullet.scanArgument(optional); + + if (argToken == null) { + return null; + } + + var str = ""; + var nextToken; + + while ((nextToken = this.fetch()).text !== "EOF") { + str += nextToken.text; + this.consume(); + } + + this.consume(); // consume the end of the argument + + argToken.text = str; + return argToken; + } + /** + * Parses a regex-delimited group: the largest sequence of tokens + * whose concatenated strings match `regex`. Returns the string + * formed by the tokens plus some position information. + */ + + + parseRegexGroup(regex, modeName // Used to describe the mode in error messages. + ) { + var firstToken = this.fetch(); + var lastToken = firstToken; + var str = ""; + var nextToken; + + while ((nextToken = this.fetch()).text !== "EOF" && regex.test(str + nextToken.text)) { + lastToken = nextToken; + str += lastToken.text; + this.consume(); + } + + if (str === "") { + throw new ParseError("Invalid " + modeName + ": '" + firstToken.text + "'", firstToken); + } + + return firstToken.range(lastToken, str); + } + /** + * Parses a color description. + */ + + + parseColorGroup(optional) { + var res = this.parseStringGroup("color", optional); + + if (res == null) { + return null; + } + + var match = /^(#[a-f0-9]{3}|#?[a-f0-9]{6}|[a-z]+)$/i.exec(res.text); + + if (!match) { + throw new ParseError("Invalid color: '" + res.text + "'", res); + } + + var color = match[0]; + + if (/^[0-9a-f]{6}$/i.test(color)) { + // We allow a 6-digit HTML color spec without a leading "#". + // This follows the xcolor package's HTML color model. + // Predefined color names are all missed by this RegEx pattern. + color = "#" + color; + } + + return { + type: "color-token", + mode: this.mode, + color + }; + } + /** + * Parses a size specification, consisting of magnitude and unit. + */ + + + parseSizeGroup(optional) { + var res; + var isBlank = false; // don't expand before parseStringGroup + + this.gullet.consumeSpaces(); + + if (!optional && this.gullet.future().text !== "{") { + res = this.parseRegexGroup(/^[-+]? *(?:$|\d+|\d+\.\d*|\.\d*) *[a-z]{0,2} *$/, "size"); + } else { + res = this.parseStringGroup("size", optional); + } + + if (!res) { + return null; + } + + if (!optional && res.text.length === 0) { + // Because we've tested for what is !optional, this block won't + // affect \kern, \hspace, etc. It will capture the mandatory arguments + // to \genfrac and \above. + res.text = "0pt"; // Enable \above{} + + isBlank = true; // This is here specifically for \genfrac + } + + var match = /([-+]?) *(\d+(?:\.\d*)?|\.\d+) *([a-z]{2})/.exec(res.text); + + if (!match) { + throw new ParseError("Invalid size: '" + res.text + "'", res); + } + + var data = { + number: +(match[1] + match[2]), + // sign + magnitude, cast to number + unit: match[3] + }; + + if (!validUnit(data)) { + throw new ParseError("Invalid unit: '" + data.unit + "'", res); + } + + return { + type: "size", + mode: this.mode, + value: data, + isBlank + }; + } + /** + * Parses an URL, checking escaped letters and allowed protocols, + * and setting the catcode of % as an active character (as in \hyperref). + */ + + + parseUrlGroup(optional) { + this.gullet.lexer.setCatcode("%", 13); // active character + + this.gullet.lexer.setCatcode("~", 12); // other character + + var res = this.parseStringGroup("url", optional); + this.gullet.lexer.setCatcode("%", 14); // comment character + + this.gullet.lexer.setCatcode("~", 13); // active character + + if (res == null) { + return null; + } // hyperref package allows backslashes alone in href, but doesn't + // generate valid links in such cases; we interpret this as + // "undefined" behaviour, and keep them as-is. Some browser will + // replace backslashes with forward slashes. + + + var url = res.text.replace(/\\([#$%&~_^{}])/g, '$1'); + return { + type: "url", + mode: this.mode, + url + }; + } + /** + * Parses an argument with the mode specified. + */ + + + parseArgumentGroup(optional, mode) { + var argToken = this.gullet.scanArgument(optional); + + if (argToken == null) { + return null; + } + + var outerMode = this.mode; + + if (mode) { + // Switch to specified mode + this.switchMode(mode); + } + + this.gullet.beginGroup(); + var expression = this.parseExpression(false, "EOF"); // TODO: find an alternative way to denote the end + + this.expect("EOF"); // expect the end of the argument + + this.gullet.endGroup(); + var result = { + type: "ordgroup", + mode: this.mode, + loc: argToken.loc, + body: expression + }; + + if (mode) { + // Switch mode back + this.switchMode(outerMode); + } + + return result; + } + /** + * Parses an ordinary group, which is either a single nucleus (like "x") + * or an expression in braces (like "{x+y}") or an implicit group, a group + * that starts at the current position, and ends right before a higher explicit + * group ends, or at EOF. + */ + + + parseGroup(name, // For error reporting. + breakOnTokenText) { + var firstToken = this.fetch(); + var text = firstToken.text; + var result; // Try to parse an open brace or \begingroup + + if (text === "{" || text === "\\begingroup") { + this.consume(); + var groupEnd = text === "{" ? "}" : "\\endgroup"; + this.gullet.beginGroup(); // If we get a brace, parse an expression + + var expression = this.parseExpression(false, groupEnd); + var lastToken = this.fetch(); + this.expect(groupEnd); // Check that we got a matching closing brace + + this.gullet.endGroup(); + result = { + type: "ordgroup", + mode: this.mode, + loc: SourceLocation.range(firstToken, lastToken), + body: expression, + // A group formed by \begingroup...\endgroup is a semi-simple group + // which doesn't affect spacing in math mode, i.e., is transparent. + // https://tex.stackexchange.com/questions/1930/when-should-one- + // use-begingroup-instead-of-bgroup + semisimple: text === "\\begingroup" || undefined + }; + } else { + // If there exists a function with this name, parse the function. + // Otherwise, just return a nucleus + result = this.parseFunction(breakOnTokenText, name) || this.parseSymbol(); + + if (result == null && text[0] === "\\" && !implicitCommands.hasOwnProperty(text)) { + if (this.settings.throwOnError) { + throw new ParseError("Undefined control sequence: " + text, firstToken); + } + + result = this.formatUnsupportedCmd(text); + this.consume(); + } + } + + return result; + } + /** + * Form ligature-like combinations of characters for text mode. + * This includes inputs like "--", "---", "``" and "''". + * The result will simply replace multiple textord nodes with a single + * character in each value by a single textord node having multiple + * characters in its value. The representation is still ASCII source. + * The group will be modified in place. + */ + + + formLigatures(group) { + var n = group.length - 1; + + for (var i = 0; i < n; ++i) { + var a = group[i]; // $FlowFixMe: Not every node type has a `text` property. + + var v = a.text; + + if (v === "-" && group[i + 1].text === "-") { + if (i + 1 < n && group[i + 2].text === "-") { + group.splice(i, 3, { + type: "textord", + mode: "text", + loc: SourceLocation.range(a, group[i + 2]), + text: "---" + }); + n -= 2; + } else { + group.splice(i, 2, { + type: "textord", + mode: "text", + loc: SourceLocation.range(a, group[i + 1]), + text: "--" + }); + n -= 1; + } + } + + if ((v === "'" || v === "`") && group[i + 1].text === v) { + group.splice(i, 2, { + type: "textord", + mode: "text", + loc: SourceLocation.range(a, group[i + 1]), + text: v + v + }); + n -= 1; + } + } + } + /** + * Parse a single symbol out of the string. Here, we handle single character + * symbols and special functions like \verb. + */ + + + parseSymbol() { + var nucleus = this.fetch(); + var text = nucleus.text; + + if (/^\\verb[^a-zA-Z]/.test(text)) { + this.consume(); + var arg = text.slice(5); + var star = arg.charAt(0) === "*"; + + if (star) { + arg = arg.slice(1); + } // Lexer's tokenRegex is constructed to always have matching + // first/last characters. + + + if (arg.length < 2 || arg.charAt(0) !== arg.slice(-1)) { + throw new ParseError("\\verb assertion failed --\n please report what input caused this bug"); + } + + arg = arg.slice(1, -1); // remove first and last char + + return { + type: "verb", + mode: "text", + body: arg, + star + }; + } // At this point, we should have a symbol, possibly with accents. + // First expand any accented base symbol according to unicodeSymbols. + + + if (unicodeSymbols.hasOwnProperty(text[0]) && !symbols[this.mode][text[0]]) { + // This behavior is not strict (XeTeX-compatible) in math mode. + if (this.settings.strict && this.mode === "math") { + this.settings.reportNonstrict("unicodeTextInMathMode", "Accented Unicode text character \"" + text[0] + "\" used in " + "math mode", nucleus); + } + + text = unicodeSymbols[text[0]] + text.slice(1); + } // Strip off any combining characters + + + var match = combiningDiacriticalMarksEndRegex.exec(text); + + if (match) { + text = text.substring(0, match.index); + + if (text === 'i') { + text = '\u0131'; // dotless i, in math and text mode + } else if (text === 'j') { + text = '\u0237'; // dotless j, in math and text mode + } + } // Recognize base symbol + + + var symbol; + + if (symbols[this.mode][text]) { + if (this.settings.strict && this.mode === 'math' && extraLatin.indexOf(text) >= 0) { + this.settings.reportNonstrict("unicodeTextInMathMode", "Latin-1/Unicode text character \"" + text[0] + "\" used in " + "math mode", nucleus); + } + + var group = symbols[this.mode][text].group; + var loc = SourceLocation.range(nucleus); + var s; + + if (ATOMS.hasOwnProperty(group)) { + // $FlowFixMe + var family = group; + s = { + type: "atom", + mode: this.mode, + family, + loc, + text + }; + } else { + // $FlowFixMe + s = { + type: group, + mode: this.mode, + loc, + text + }; + } // $FlowFixMe + + + symbol = s; + } else if (text.charCodeAt(0) >= 0x80) { + // no symbol for e.g. ^ + if (this.settings.strict) { + if (!supportedCodepoint(text.charCodeAt(0))) { + this.settings.reportNonstrict("unknownSymbol", "Unrecognized Unicode character \"" + text[0] + "\"" + (" (" + text.charCodeAt(0) + ")"), nucleus); + } else if (this.mode === "math") { + this.settings.reportNonstrict("unicodeTextInMathMode", "Unicode text character \"" + text[0] + "\" used in math mode", nucleus); + } + } // All nonmathematical Unicode characters are rendered as if they + // are in text mode (wrapped in \text) because that's what it + // takes to render them in LaTeX. Setting `mode: this.mode` is + // another natural choice (the user requested math mode), but + // this makes it more difficult for getCharacterMetrics() to + // distinguish Unicode characters without metrics and those for + // which we want to simulate the letter M. + + + symbol = { + type: "textord", + mode: "text", + loc: SourceLocation.range(nucleus), + text + }; + } else { + return null; // EOF, ^, _, {, }, etc. + } + + this.consume(); // Transform combining characters into accents + + if (match) { + for (var i = 0; i < match[0].length; i++) { + var accent = match[0][i]; + + if (!unicodeAccents[accent]) { + throw new ParseError("Unknown accent ' " + accent + "'", nucleus); + } + + var command = unicodeAccents[accent][this.mode] || unicodeAccents[accent].text; + + if (!command) { + throw new ParseError("Accent " + accent + " unsupported in " + this.mode + " mode", nucleus); + } + + symbol = { + type: "accent", + mode: this.mode, + loc: SourceLocation.range(nucleus), + label: command, + isStretchy: false, + isShifty: true, + // $FlowFixMe + base: symbol + }; + } + } // $FlowFixMe + + + return symbol; + } + +} +Parser.endOfExpression = ["}", "\\endgroup", "\\end", "\\right", "&"]; + +/** + * Provides a single function for parsing an expression using a Parser + * TODO(emily): Remove this + */ + +/** + * Parses an expression using a Parser, then returns the parsed result. + */ +var parseTree = function parseTree(toParse, settings) { + if (!(typeof toParse === 'string' || toParse instanceof String)) { + throw new TypeError('KaTeX can only parse string typed expression'); + } + + var parser = new Parser(toParse, settings); // Blank out any \df@tag to avoid spurious "Duplicate \tag" errors + + delete parser.gullet.macros.current["\\df@tag"]; + var tree = parser.parse(); // Prevent a color definition from persisting between calls to katex.render(). + + delete parser.gullet.macros.current["\\current@color"]; + delete parser.gullet.macros.current["\\color"]; // If the input used \tag, it will set the \df@tag macro to the tag. + // In this case, we separately parse the tag and wrap the tree. + + if (parser.gullet.macros.get("\\df@tag")) { + if (!settings.displayMode) { + throw new ParseError("\\tag works only in display equations"); + } + + tree = [{ + type: "tag", + mode: "text", + body: tree, + tag: parser.subparse([new Token("\\df@tag")]) + }]; + } + + return tree; +}; + +/* eslint no-console:0 */ + +/** + * Parse and build an expression, and place that expression in the DOM node + * given. + */ +var render = function render(expression, baseNode, options) { + baseNode.textContent = ""; + var node = renderToDomTree(expression, options).toNode(); + baseNode.appendChild(node); +}; // KaTeX's styles don't work properly in quirks mode. Print out an error, and +// disable rendering. + + +if (typeof document !== "undefined") { + if (document.compatMode !== "CSS1Compat") { + typeof console !== "undefined" && console.warn("Warning: KaTeX doesn't work in quirks mode. Make sure your " + "website has a suitable doctype."); + + render = function render() { + throw new ParseError("KaTeX doesn't work in quirks mode."); + }; + } +} +/** + * Parse and build an expression, and return the markup for that. + */ + + +var renderToString = function renderToString(expression, options) { + var markup = renderToDomTree(expression, options).toMarkup(); + return markup; +}; +/** + * Parse an expression and return the parse tree. + */ + + +var generateParseTree = function generateParseTree(expression, options) { + var settings = new Settings(options); + return parseTree(expression, settings); +}; +/** + * If the given error is a KaTeX ParseError and options.throwOnError is false, + * renders the invalid LaTeX as a span with hover title giving the KaTeX + * error message. Otherwise, simply throws the error. + */ + + +var renderError = function renderError(error, expression, options) { + if (options.throwOnError || !(error instanceof ParseError)) { + throw error; + } + + var node = buildCommon.makeSpan(["katex-error"], [new SymbolNode(expression)]); + node.setAttribute("title", error.toString()); + node.setAttribute("style", "color:" + options.errorColor); + return node; +}; +/** + * Generates and returns the katex build tree. This is used for advanced + * use cases (like rendering to custom output). + */ + + +var renderToDomTree = function renderToDomTree(expression, options) { + var settings = new Settings(options); + + try { + var tree = parseTree(expression, settings); + return buildTree(tree, expression, settings); + } catch (error) { + return renderError(error, expression, settings); + } +}; +/** + * Generates and returns the katex build tree, with just HTML (no MathML). + * This is used for advanced use cases (like rendering to custom output). + */ + + +var renderToHTMLTree = function renderToHTMLTree(expression, options) { + var settings = new Settings(options); + + try { + var tree = parseTree(expression, settings); + return buildHTMLTree(tree, expression, settings); + } catch (error) { + return renderError(error, expression, settings); + } +}; + +var version = "0.16.22"; +var __domTree = { + Span, + Anchor, + SymbolNode, + SvgNode, + PathNode, + LineNode +}; // ESM exports + +var katex = { + /** + * Current KaTeX version + */ + version, + + /** + * Renders the given LaTeX into an HTML+MathML combination, and adds + * it as a child to the specified DOM node. + */ + render, + + /** + * Renders the given LaTeX into an HTML+MathML combination string, + * for sending to the client. + */ + renderToString, + + /** + * KaTeX error, usually during parsing. + */ + ParseError, + + /** + * The schema of Settings + */ + SETTINGS_SCHEMA, + + /** + * Parses the given LaTeX into KaTeX's internal parse tree structure, + * without rendering to HTML or MathML. + * + * NOTE: This method is not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __parse: generateParseTree, + + /** + * Renders the given LaTeX into an HTML+MathML internal DOM tree + * representation, without flattening that representation to a string. + * + * NOTE: This method is not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __renderToDomTree: renderToDomTree, + + /** + * Renders the given LaTeX into an HTML internal DOM tree representation, + * without MathML and without flattening that representation to a string. + * + * NOTE: This method is not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __renderToHTMLTree: renderToHTMLTree, + + /** + * extends internal font metrics object with a new object + * each key in the new object represents a font name + */ + __setFontMetrics: setFontMetrics, + + /** + * adds a new symbol to builtin symbols table + */ + __defineSymbol: defineSymbol, + + /** + * adds a new function to builtin function list, + * which directly produce parse tree elements + * and have their own html/mathml builders + */ + __defineFunction: defineFunction, + + /** + * adds a new macro to builtin macro list + */ + __defineMacro: defineMacro, + + /** + * Expose the dom tree node types, which can be useful for type checking nodes. + * + * NOTE: These methods are not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __domTree +}; + +export { ParseError, SETTINGS_SCHEMA, defineFunction as __defineFunction, defineMacro as __defineMacro, defineSymbol as __defineSymbol, __domTree, generateParseTree as __parse, renderToDomTree as __renderToDomTree, renderToHTMLTree as __renderToHTMLTree, setFontMetrics as __setFontMetrics, katex as default, render, renderToString, version }; diff --git a/frontend/node_modules/katex/katex.js b/frontend/node_modules/katex/katex.js new file mode 100644 index 0000000..cc15572 --- /dev/null +++ b/frontend/node_modules/katex/katex.js @@ -0,0 +1,247 @@ +// @flow +/* eslint no-console:0 */ +/** + * This is the main entry point for KaTeX. Here, we expose functions for + * rendering expressions either to DOM nodes or to markup strings. + * + * We also expose the ParseError class to check if errors thrown from KaTeX are + * errors in the expression, or errors in javascript handling. + */ + +import ParseError from "./src/ParseError"; +import Settings, {SETTINGS_SCHEMA} from "./src/Settings"; + +import {buildTree, buildHTMLTree} from "./src/buildTree"; +import parseTree from "./src/parseTree"; +import buildCommon from "./src/buildCommon"; +import { + Span, + Anchor, + SymbolNode, + SvgNode, + PathNode, + LineNode, +} from "./src/domTree"; + +import type {SettingsOptions} from "./src/Settings"; +import type {AnyParseNode} from "./src/parseNode"; +import type {DomSpan} from "./src/domTree"; + +import {defineSymbol} from './src/symbols'; +import defineFunction from './src/defineFunction'; +import defineMacro from './src/defineMacro'; +import {setFontMetrics} from './src/fontMetrics'; + +declare var __VERSION__: string; + +/** + * Parse and build an expression, and place that expression in the DOM node + * given. + */ +let render: (string, Node, SettingsOptions) => void = function( + expression: string, + baseNode: Node, + options: SettingsOptions, +) { + baseNode.textContent = ""; + const node = renderToDomTree(expression, options).toNode(); + baseNode.appendChild(node); +}; + +// KaTeX's styles don't work properly in quirks mode. Print out an error, and +// disable rendering. +if (typeof document !== "undefined") { + if (document.compatMode !== "CSS1Compat") { + typeof console !== "undefined" && console.warn( + "Warning: KaTeX doesn't work in quirks mode. Make sure your " + + "website has a suitable doctype."); + + render = function() { + throw new ParseError("KaTeX doesn't work in quirks mode."); + }; + } +} + +/** + * Parse and build an expression, and return the markup for that. + */ +const renderToString = function( + expression: string, + options: SettingsOptions, +): string { + const markup = renderToDomTree(expression, options).toMarkup(); + return markup; +}; + +/** + * Parse an expression and return the parse tree. + */ +const generateParseTree = function( + expression: string, + options: SettingsOptions, +): AnyParseNode[] { + const settings = new Settings(options); + return parseTree(expression, settings); +}; + +/** + * If the given error is a KaTeX ParseError and options.throwOnError is false, + * renders the invalid LaTeX as a span with hover title giving the KaTeX + * error message. Otherwise, simply throws the error. + */ +const renderError = function( + error, + expression: string, + options: Settings, +) { + if (options.throwOnError || !(error instanceof ParseError)) { + throw error; + } + const node = buildCommon.makeSpan(["katex-error"], + [new SymbolNode(expression)]); + node.setAttribute("title", error.toString()); + node.setAttribute("style", `color:${options.errorColor}`); + return node; +}; + +/** + * Generates and returns the katex build tree. This is used for advanced + * use cases (like rendering to custom output). + */ +const renderToDomTree = function( + expression: string, + options: SettingsOptions, +): DomSpan { + const settings = new Settings(options); + try { + const tree = parseTree(expression, settings); + return buildTree(tree, expression, settings); + } catch (error) { + return renderError(error, expression, settings); + } +}; + +/** + * Generates and returns the katex build tree, with just HTML (no MathML). + * This is used for advanced use cases (like rendering to custom output). + */ +const renderToHTMLTree = function( + expression: string, + options: SettingsOptions, +): DomSpan { + const settings = new Settings(options); + try { + const tree = parseTree(expression, settings); + return buildHTMLTree(tree, expression, settings); + } catch (error) { + return renderError(error, expression, settings); + } +}; + +const version = __VERSION__; + +const __domTree = { + Span, + Anchor, + SymbolNode, + SvgNode, + PathNode, + LineNode, +}; + +// ESM exports +export { + version, + render, + renderToString, + ParseError, + SETTINGS_SCHEMA, + generateParseTree as __parse, + renderToDomTree as __renderToDomTree, + renderToHTMLTree as __renderToHTMLTree, + setFontMetrics as __setFontMetrics, + defineSymbol as __defineSymbol, + defineFunction as __defineFunction, + defineMacro as __defineMacro, + __domTree, +}; + +// CJS exports and ESM default export +export default { + /** + * Current KaTeX version + */ + version, + /** + * Renders the given LaTeX into an HTML+MathML combination, and adds + * it as a child to the specified DOM node. + */ + render, + /** + * Renders the given LaTeX into an HTML+MathML combination string, + * for sending to the client. + */ + renderToString, + /** + * KaTeX error, usually during parsing. + */ + ParseError, + /** + * The schema of Settings + */ + SETTINGS_SCHEMA, + /** + * Parses the given LaTeX into KaTeX's internal parse tree structure, + * without rendering to HTML or MathML. + * + * NOTE: This method is not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __parse: generateParseTree, + /** + * Renders the given LaTeX into an HTML+MathML internal DOM tree + * representation, without flattening that representation to a string. + * + * NOTE: This method is not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __renderToDomTree: renderToDomTree, + /** + * Renders the given LaTeX into an HTML internal DOM tree representation, + * without MathML and without flattening that representation to a string. + * + * NOTE: This method is not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __renderToHTMLTree: renderToHTMLTree, + /** + * extends internal font metrics object with a new object + * each key in the new object represents a font name + */ + __setFontMetrics: setFontMetrics, + /** + * adds a new symbol to builtin symbols table + */ + __defineSymbol: defineSymbol, + /** + * adds a new function to builtin function list, + * which directly produce parse tree elements + * and have their own html/mathml builders + */ + __defineFunction: defineFunction, + /** + * adds a new macro to builtin macro list + */ + __defineMacro: defineMacro, + /** + * Expose the dom tree node types, which can be useful for type checking nodes. + * + * NOTE: These methods are not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __domTree, +}; diff --git a/frontend/node_modules/katex/package.json b/frontend/node_modules/katex/package.json new file mode 100644 index 0000000..ebab4fa --- /dev/null +++ b/frontend/node_modules/katex/package.json @@ -0,0 +1,195 @@ +{ + "name": "katex", + "version": "0.16.22", + "description": "Fast math typesetting for the web.", + "main": "dist/katex.js", + "exports": { + ".": { + "require": { + "types": "./types/katex.d.ts", + "default": "./dist/katex.js" + }, + "import": { + "types": "./types/katex.d.ts", + "default": "./dist/katex.mjs" + } + }, + "./contrib/auto-render": { + "require": "./dist/contrib/auto-render.js", + "import": "./dist/contrib/auto-render.mjs" + }, + "./contrib/mhchem": { + "require": "./dist/contrib/mhchem.js", + "import": "./dist/contrib/mhchem.mjs" + }, + "./contrib/copy-tex": { + "require": "./dist/contrib/copy-tex.js", + "import": "./dist/contrib/copy-tex.mjs" + }, + "./contrib/mathtex-script-type": { + "require": "./dist/contrib/mathtex-script-type.js", + "import": "./dist/contrib/mathtex-script-type.mjs" + }, + "./contrib/render-a11y-string": { + "require": "./dist/contrib/render-a11y-string.js", + "import": "./dist/contrib/render-a11y-string.mjs" + }, + "./*": "./*" + }, + "homepage": "https://katex.org", + "repository": { + "type": "git", + "url": "https://github.com/KaTeX/KaTeX.git" + }, + "funding": [ + "https://opencollective.com/katex", + "https://github.com/sponsors/katex" + ], + "files": [ + "katex.js", + "cli.js", + "src/", + "contrib/", + "dist/", + "types/" + ], + "license": "MIT", + "packageManager": "yarn@4.1.1", + "devDependencies": { + "@babel/core": "^7.18.13", + "@babel/eslint-parser": "^7.18.9", + "@babel/plugin-proposal-class-properties": "^7.18.6", + "@babel/plugin-syntax-flow": "^7.18.6", + "@babel/plugin-transform-react-jsx": "^7.18.10", + "@babel/plugin-transform-runtime": "^7.18.10", + "@babel/preset-env": "^7.18.10", + "@babel/preset-flow": "^7.18.6", + "@babel/preset-react": "^7.18.6", + "@babel/register": "^7.18.9", + "@babel/runtime": "^7.18.9", + "@rollup/plugin-alias": "^3.1.9", + "@rollup/plugin-babel": "^5.3.1", + "@semantic-release/changelog": "^6.0.1", + "@semantic-release/git": "^10.0.1", + "babel-jest": "^29.0.1", + "babel-loader": "^8.2.5", + "babel-plugin-istanbul": "^6.1.1", + "babel-plugin-preval": "^5.1.0", + "babel-plugin-version-inline": "^1.0.0", + "benchmark": "^2.1.4", + "browserslist": "^4.21.3", + "browserstack-local": "^1.5.1", + "caniuse-lite": "^1.0.30001384", + "css-loader": "^6.7.1", + "cssnano": "^5.1.13", + "eslint": "^8.23.0", + "eslint-import-resolver-webpack": "^0.13.2", + "eslint-plugin-actions": "^2.0.0", + "eslint-plugin-flowtype": "^8.0.3", + "eslint-plugin-import": "^2.26.0", + "eslint-plugin-react": "^7.31.1", + "flow-bin": "^0.135.0", + "fs-extra": "^10.1.0", + "got": "^11.8.5", + "husky": "^4.3.8", + "istanbul-lib-coverage": "^3.2.0", + "istanbul-lib-report": "^3.0.0", + "istanbul-reports": "^3.1.5", + "jest": "^29.0.1", + "jest-diff": "^29.0.1", + "jest-environment-jsdom": "^29.0.1", + "jest-matcher-utils": "^29.0.1", + "jest-message-util": "^29.0.1", + "jest-serializer-html": "^7.1.0", + "js-yaml": "^4.1.0", + "json-stable-stringify": "^1.0.1", + "jspngopt": "^0.2.0", + "mini-css-extract-plugin": "^2.6.1", + "mkdirp": "^1.0.4", + "p-retry": "^4.6.2", + "pako": "^2.0.4", + "postcss": "^8.4.16", + "postcss-loader": "^7.0.1", + "postcss-preset-env": "^7.8.0", + "postcss-scss": "^4.0.9", + "prettier": "^2.7.1", + "query-string": "^7.1.1", + "rimraf": "^3.0.2", + "rollup": "^2.79.2", + "sass": "^1.75.6", + "sass-loader": "^14.2.1", + "selenium-webdriver": "^4.4.0", + "semantic-release": "^19.0.5", + "sri-toolbox": "^0.2.0", + "style-loader": "^3.3.1", + "stylelint": "^14.11.0", + "stylelint-config-standard": "^28.0.0", + "stylelint-scss": "^6.3.2", + "terser-webpack-plugin": "^5.3.6", + "webpack": "^5.74.0", + "webpack-bundle-analyzer": "^4.6.1", + "webpack-cli": "^4.10.0", + "webpack-dev-server": "^4.10.1" + }, + "bin": "cli.js", + "scripts": { + "test": "yarn test:lint && yarn test:flow && yarn test:jest", + "test:lint": "yarn test:lint:js && yarn test:lint:css", + "test:lint:js": "eslint .", + "test:lint:css": "stylelint src/styles/katex.scss static/main.css website/static/**/*.css", + "test:flow": "flow", + "test:jest": "jest", + "test:jest:watch": "jest --watch", + "test:jest:update": "jest --updateSnapshot", + "test:jest:coverage": "jest --coverage", + "test:screenshots": "yarn test:screenshots:update --verify", + "test:screenshots:update": "dockers/screenshotter/screenshotter.sh", + "test:perf": "NODE_ENV=test node test/perf-test.js", + "clean": "rm -rf dist/ node_modules/", + "clean-install": "yarn clean && yarn", + "start": "webpack serve --config webpack.dev.js", + "analyze": "webpack --config webpack.analyze.js", + "build": "rimraf dist/ && mkdirp dist && cp README.md dist && rollup -c --failAfterWarnings && webpack && node update-sri.js package dist/README.md", + "build:fonts": "dockers/fonts/buildFonts.sh", + "build:metrics": "dockers/fonts/buildMetrics.sh", + "watch": "yarn build --watch", + "postversion": "yarn dist && node update-sri.js package README.md contrib/*/README.md docs/*.md website/pages/index.html", + "semantic-release": "semantic-release", + "dist": "yarn build && yarn dist:zip", + "dist:zip": "rimraf katex/ katex.tar.gz katex.zip && cp -R dist katex && tar czf katex.tar.gz katex && zip -rq katex.zip katex && rimraf katex/" + }, + "dependencies": { + "commander": "^8.3.0" + }, + "husky": { + "hooks": { + "pre-commit": "yarn test:lint" + } + }, + "jest": { + "collectCoverageFrom": [ + "src/**/*.js", + "contrib/**/*.js", + "!src/unicodeSymbols.js", + "!contrib/mhchem/**" + ], + "setupFilesAfterEnv": [ + "/test/setup.js" + ], + "snapshotSerializers": [ + "jest-serializer-html" + ], + "testMatch": [ + "**/test/*-spec.js" + ], + "testEnvironmentOptions": { + "url": "http://localhost/" + }, + "transform": { + "^.+\\.js$": "babel-jest" + }, + "moduleNameMapper": { + "^katex$": "/katex.js" + } + } +} diff --git a/frontend/node_modules/katex/src/Lexer.js b/frontend/node_modules/katex/src/Lexer.js new file mode 100644 index 0000000..7bd9023 --- /dev/null +++ b/frontend/node_modules/katex/src/Lexer.js @@ -0,0 +1,122 @@ +// @flow +/** + * The Lexer class handles tokenizing the input in various ways. Since our + * parser expects us to be able to backtrack, the lexer allows lexing from any + * given starting point. + * + * Its main exposed function is the `lex` function, which takes a position to + * lex from and a type of token to lex. It defers to the appropriate `_innerLex` + * function. + * + * The various `_innerLex` functions perform the actual lexing of different + * kinds. + */ + +import ParseError from "./ParseError"; +import SourceLocation from "./SourceLocation"; +import {Token} from "./Token"; + +import type {LexerInterface} from "./Token"; +import type Settings from "./Settings"; + +/* The following tokenRegex + * - matches typical whitespace (but not NBSP etc.) using its first group + * - does not match any control character \x00-\x1f except whitespace + * - does not match a bare backslash + * - matches any ASCII character except those just mentioned + * - does not match the BMP private use area \uE000-\uF8FF + * - does not match bare surrogate code units + * - matches any BMP character except for those just described + * - matches any valid Unicode surrogate pair + * - matches a backslash followed by one or more whitespace characters + * - matches a backslash followed by one or more letters then whitespace + * - matches a backslash followed by any BMP character + * Capturing groups: + * [1] regular whitespace + * [2] backslash followed by whitespace + * [3] anything else, which may include: + * [4] left character of \verb* + * [5] left character of \verb + * [6] backslash followed by word, excluding any trailing whitespace + * Just because the Lexer matches something doesn't mean it's valid input: + * If there is no matching function or symbol definition, the Parser will + * still reject the input. + */ +const spaceRegexString = "[ \r\n\t]"; +const controlWordRegexString = "\\\\[a-zA-Z@]+"; +const controlSymbolRegexString = "\\\\[^\uD800-\uDFFF]"; +const controlWordWhitespaceRegexString = + `(${controlWordRegexString})${spaceRegexString}*`; +const controlSpaceRegexString = "\\\\(\n|[ \r\t]+\n?)[ \r\t]*"; +const combiningDiacriticalMarkString = "[\u0300-\u036f]"; +export const combiningDiacriticalMarksEndRegex: RegExp = + new RegExp(`${combiningDiacriticalMarkString}+$`); +const tokenRegexString = `(${spaceRegexString}+)|` + // whitespace + `${controlSpaceRegexString}|` + // \whitespace + "([!-\\[\\]-\u2027\u202A-\uD7FF\uF900-\uFFFF]" + // single codepoint + `${combiningDiacriticalMarkString}*` + // ...plus accents + "|[\uD800-\uDBFF][\uDC00-\uDFFF]" + // surrogate pair + `${combiningDiacriticalMarkString}*` + // ...plus accents + "|\\\\verb\\*([^]).*?\\4" + // \verb* + "|\\\\verb([^*a-zA-Z]).*?\\5" + // \verb unstarred + `|${controlWordWhitespaceRegexString}` + // \macroName + spaces + `|${controlSymbolRegexString})`; // \\, \', etc. + +/** Main Lexer class */ +export default class Lexer implements LexerInterface { + input: string; + settings: Settings; + tokenRegex: RegExp; + // Category codes. The lexer only supports comment characters (14) for now. + // MacroExpander additionally distinguishes active (13). + catcodes: {[string]: number}; + + constructor(input: string, settings: Settings) { + // Separate accents from characters + this.input = input; + this.settings = settings; + this.tokenRegex = new RegExp(tokenRegexString, 'g'); + this.catcodes = { + "%": 14, // comment character + "~": 13, // active character + }; + } + + setCatcode(char: string, code: number) { + this.catcodes[char] = code; + } + + /** + * This function lexes a single token. + */ + lex(): Token { + const input = this.input; + const pos = this.tokenRegex.lastIndex; + if (pos === input.length) { + return new Token("EOF", new SourceLocation(this, pos, pos)); + } + const match = this.tokenRegex.exec(input); + if (match === null || match.index !== pos) { + throw new ParseError( + `Unexpected character: '${input[pos]}'`, + new Token(input[pos], new SourceLocation(this, pos, pos + 1))); + } + const text = match[6] || match[3] || (match[2] ? "\\ " : " "); + + if (this.catcodes[text] === 14) { // comment character + const nlIndex = input.indexOf('\n', this.tokenRegex.lastIndex); + if (nlIndex === -1) { + this.tokenRegex.lastIndex = input.length; // EOF + this.settings.reportNonstrict("commentAtEnd", + "% comment has no terminating newline; LaTeX would " + + "fail because of commenting the end of math mode (e.g. $)"); + } else { + this.tokenRegex.lastIndex = nlIndex + 1; + } + return this.lex(); + } + + return new Token(text, new SourceLocation(this, pos, + this.tokenRegex.lastIndex)); + } +} diff --git a/frontend/node_modules/katex/src/MacroExpander.js b/frontend/node_modules/katex/src/MacroExpander.js new file mode 100644 index 0000000..18dadc3 --- /dev/null +++ b/frontend/node_modules/katex/src/MacroExpander.js @@ -0,0 +1,470 @@ +// @flow +/** + * This file contains the “gullet” where macros are expanded + * until only non-macro tokens remain. + */ + +import functions from "./functions"; +import symbols from "./symbols"; +import Lexer from "./Lexer"; +import {Token} from "./Token"; +import type {Mode} from "./types"; +import ParseError from "./ParseError"; +import Namespace from "./Namespace"; +import macros from "./macros"; + +import type {MacroContextInterface, MacroDefinition, MacroExpansion, MacroArg} + from "./defineMacro"; +import type Settings from "./Settings"; + +// List of commands that act like macros but aren't defined as a macro, +// function, or symbol. Used in `isDefined`. +export const implicitCommands = { + "^": true, // Parser.js + "_": true, // Parser.js + "\\limits": true, // Parser.js + "\\nolimits": true, // Parser.js +}; + +export default class MacroExpander implements MacroContextInterface { + settings: Settings; + expansionCount: number; + lexer: Lexer; + macros: Namespace; + stack: Token[]; + mode: Mode; + + constructor(input: string, settings: Settings, mode: Mode) { + this.settings = settings; + this.expansionCount = 0; + this.feed(input); + // Make new global namespace + this.macros = new Namespace(macros, settings.macros); + this.mode = mode; + this.stack = []; // contains tokens in REVERSE order + } + + /** + * Feed a new input string to the same MacroExpander + * (with existing macros etc.). + */ + feed(input: string) { + this.lexer = new Lexer(input, this.settings); + } + + /** + * Switches between "text" and "math" modes. + */ + switchMode(newMode: Mode) { + this.mode = newMode; + } + + /** + * Start a new group nesting within all namespaces. + */ + beginGroup() { + this.macros.beginGroup(); + } + + /** + * End current group nesting within all namespaces. + */ + endGroup() { + this.macros.endGroup(); + } + + /** + * Ends all currently nested groups (if any), restoring values before the + * groups began. Useful in case of an error in the middle of parsing. + */ + endGroups() { + this.macros.endGroups(); + } + + /** + * Returns the topmost token on the stack, without expanding it. + * Similar in behavior to TeX's `\futurelet`. + */ + future(): Token { + if (this.stack.length === 0) { + this.pushToken(this.lexer.lex()); + } + return this.stack[this.stack.length - 1]; + } + + /** + * Remove and return the next unexpanded token. + */ + popToken(): Token { + this.future(); // ensure non-empty stack + return this.stack.pop(); + } + + /** + * Add a given token to the token stack. In particular, this get be used + * to put back a token returned from one of the other methods. + */ + pushToken(token: Token) { + this.stack.push(token); + } + + /** + * Append an array of tokens to the token stack. + */ + pushTokens(tokens: Token[]) { + this.stack.push(...tokens); + } + + /** + * Find an macro argument without expanding tokens and append the array of + * tokens to the token stack. Uses Token as a container for the result. + */ + scanArgument(isOptional: boolean): ?Token { + let start; + let end; + let tokens; + if (isOptional) { + this.consumeSpaces(); // \@ifnextchar gobbles any space following it + if (this.future().text !== "[") { + return null; + } + start = this.popToken(); // don't include [ in tokens + ({tokens, end} = this.consumeArg(["]"])); + } else { + ({tokens, start, end} = this.consumeArg()); + } + + // indicate the end of an argument + this.pushToken(new Token("EOF", end.loc)); + + this.pushTokens(tokens); + return start.range(end, ""); + } + + /** + * Consume all following space tokens, without expansion. + */ + consumeSpaces() { + for (;;) { + const token = this.future(); + if (token.text === " ") { + this.stack.pop(); + } else { + break; + } + } + } + + /** + * Consume an argument from the token stream, and return the resulting array + * of tokens and start/end token. + */ + consumeArg(delims?: ?string[]): MacroArg { + // The argument for a delimited parameter is the shortest (possibly + // empty) sequence of tokens with properly nested {...} groups that is + // followed ... by this particular list of non-parameter tokens. + // The argument for an undelimited parameter is the next nonblank + // token, unless that token is ‘{’, when the argument will be the + // entire {...} group that follows. + const tokens: Token[] = []; + const isDelimited = delims && delims.length > 0; + if (!isDelimited) { + // Ignore spaces between arguments. As the TeXbook says: + // "After you have said ‘\def\row#1#2{...}’, you are allowed to + // put spaces between the arguments (e.g., ‘\row x n’), because + // TeX doesn’t use single spaces as undelimited arguments." + this.consumeSpaces(); + } + const start = this.future(); + let tok; + let depth = 0; + let match = 0; + do { + tok = this.popToken(); + tokens.push(tok); + if (tok.text === "{") { + ++depth; + } else if (tok.text === "}") { + --depth; + if (depth === -1) { + throw new ParseError("Extra }", tok); + } + } else if (tok.text === "EOF") { + throw new ParseError("Unexpected end of input in a macro argument" + + ", expected '" + (delims && isDelimited ? delims[match] : "}") + + "'", tok); + } + if (delims && isDelimited) { + if ((depth === 0 || (depth === 1 && delims[match] === "{")) && + tok.text === delims[match]) { + ++match; + if (match === delims.length) { + // don't include delims in tokens + tokens.splice(-match, match); + break; + } + } else { + match = 0; + } + } + } while (depth !== 0 || isDelimited); + // If the argument found ... has the form ‘{}’, + // ... the outermost braces enclosing the argument are removed + if (start.text === "{" && tokens[tokens.length - 1].text === "}") { + tokens.pop(); + tokens.shift(); + } + tokens.reverse(); // to fit in with stack order + return {tokens, start, end: tok}; + } + + /** + * Consume the specified number of (delimited) arguments from the token + * stream and return the resulting array of arguments. + */ + consumeArgs(numArgs: number, delimiters?: string[][]): Token[][] { + if (delimiters) { + if (delimiters.length !== numArgs + 1) { + throw new ParseError( + "The length of delimiters doesn't match the number of args!"); + } + const delims = delimiters[0]; + for (let i = 0; i < delims.length; i++) { + const tok = this.popToken(); + if (delims[i] !== tok.text) { + throw new ParseError( + "Use of the macro doesn't match its definition", tok); + } + } + } + + const args: Token[][] = []; + for (let i = 0; i < numArgs; i++) { + args.push(this.consumeArg(delimiters && delimiters[i + 1]).tokens); + } + return args; + } + + /** + * Increment `expansionCount` by the specified amount. + * Throw an error if it exceeds `maxExpand`. + */ + countExpansion(amount: number): void { + this.expansionCount += amount; + if (this.expansionCount > this.settings.maxExpand) { + throw new ParseError("Too many expansions: infinite loop or " + + "need to increase maxExpand setting"); + } + } + + /** + * Expand the next token only once if possible. + * + * If the token is expanded, the resulting tokens will be pushed onto + * the stack in reverse order, and the number of such tokens will be + * returned. This number might be zero or positive. + * + * If not, the return value is `false`, and the next token remains at the + * top of the stack. + * + * In either case, the next token will be on the top of the stack, + * or the stack will be empty (in case of empty expansion + * and no other tokens). + * + * Used to implement `expandAfterFuture` and `expandNextToken`. + * + * If expandableOnly, only expandable tokens are expanded and + * an undefined control sequence results in an error. + */ + expandOnce(expandableOnly?: boolean): number | boolean { + const topToken = this.popToken(); + const name = topToken.text; + const expansion = !topToken.noexpand ? this._getExpansion(name) : null; + if (expansion == null || (expandableOnly && expansion.unexpandable)) { + if (expandableOnly && expansion == null && + name[0] === "\\" && !this.isDefined(name)) { + throw new ParseError("Undefined control sequence: " + name); + } + this.pushToken(topToken); + return false; + } + this.countExpansion(1); + let tokens = expansion.tokens; + const args = this.consumeArgs(expansion.numArgs, expansion.delimiters); + if (expansion.numArgs) { + // paste arguments in place of the placeholders + tokens = tokens.slice(); // make a shallow copy + for (let i = tokens.length - 1; i >= 0; --i) { + let tok = tokens[i]; + if (tok.text === "#") { + if (i === 0) { + throw new ParseError( + "Incomplete placeholder at end of macro body", + tok); + } + tok = tokens[--i]; // next token on stack + if (tok.text === "#") { // ## → # + tokens.splice(i + 1, 1); // drop first # + } else if (/^[1-9]$/.test(tok.text)) { + // replace the placeholder with the indicated argument + tokens.splice(i, 2, ...args[+tok.text - 1]); + } else { + throw new ParseError( + "Not a valid argument number", + tok); + } + } + } + } + // Concatenate expansion onto top of stack. + this.pushTokens(tokens); + return tokens.length; + } + + /** + * Expand the next token only once (if possible), and return the resulting + * top token on the stack (without removing anything from the stack). + * Similar in behavior to TeX's `\expandafter\futurelet`. + * Equivalent to expandOnce() followed by future(). + */ + expandAfterFuture(): Token { + this.expandOnce(); + return this.future(); + } + + /** + * Recursively expand first token, then return first non-expandable token. + */ + expandNextToken(): Token { + for (;;) { + if (this.expandOnce() === false) { // fully expanded + const token = this.stack.pop(); + // the token after \noexpand is interpreted as if its meaning + // were ‘\relax’ + if (token.treatAsRelax) { + token.text = "\\relax"; + } + return token; + } + } + + // Flow unable to figure out that this pathway is impossible. + // https://github.com/facebook/flow/issues/4808 + throw new Error(); // eslint-disable-line no-unreachable + } + + /** + * Fully expand the given macro name and return the resulting list of + * tokens, or return `undefined` if no such macro is defined. + */ + expandMacro(name: string): Token[] | void { + return this.macros.has(name) + ? this.expandTokens([new Token(name)]) : undefined; + } + + /** + * Fully expand the given token stream and return the resulting list of + * tokens. Note that the input tokens are in reverse order, but the + * output tokens are in forward order. + */ + expandTokens(tokens: Token[]): Token[] { + const output = []; + const oldStackLength = this.stack.length; + this.pushTokens(tokens); + while (this.stack.length > oldStackLength) { + // Expand only expandable tokens + if (this.expandOnce(true) === false) { // fully expanded + const token = this.stack.pop(); + if (token.treatAsRelax) { + // the expansion of \noexpand is the token itself + token.noexpand = false; + token.treatAsRelax = false; + } + output.push(token); + } + } + // Count all of these tokens as additional expansions, to prevent + // exponential blowup from linearly many \edef's. + this.countExpansion(output.length); + return output; + } + + /** + * Fully expand the given macro name and return the result as a string, + * or return `undefined` if no such macro is defined. + */ + expandMacroAsText(name: string): string | void { + const tokens = this.expandMacro(name); + if (tokens) { + return tokens.map((token) => token.text).join(""); + } else { + return tokens; + } + } + + /** + * Returns the expanded macro as a reversed array of tokens and a macro + * argument count. Or returns `null` if no such macro. + */ + _getExpansion(name: string): ?MacroExpansion { + const definition = this.macros.get(name); + if (definition == null) { // mainly checking for undefined here + return definition; + } + // If a single character has an associated catcode other than 13 + // (active character), then don't expand it. + if (name.length === 1) { + const catcode = this.lexer.catcodes[name]; + if (catcode != null && catcode !== 13) { + return; + } + } + const expansion = + typeof definition === "function" ? definition(this) : definition; + if (typeof expansion === "string") { + let numArgs = 0; + if (expansion.indexOf("#") !== -1) { + const stripped = expansion.replace(/##/g, ""); + while (stripped.indexOf("#" + (numArgs + 1)) !== -1) { + ++numArgs; + } + } + const bodyLexer = new Lexer(expansion, this.settings); + const tokens = []; + let tok = bodyLexer.lex(); + while (tok.text !== "EOF") { + tokens.push(tok); + tok = bodyLexer.lex(); + } + tokens.reverse(); // to fit in with stack using push and pop + const expanded = {tokens, numArgs}; + return expanded; + } + + return expansion; + } + + /** + * Determine whether a command is currently "defined" (has some + * functionality), meaning that it's a macro (in the current group), + * a function, a symbol, or one of the special commands listed in + * `implicitCommands`. + */ + isDefined(name: string): boolean { + return this.macros.has(name) || + functions.hasOwnProperty(name) || + symbols.math.hasOwnProperty(name) || + symbols.text.hasOwnProperty(name) || + implicitCommands.hasOwnProperty(name); + } + + /** + * Determine whether a command is expandable. + */ + isExpandable(name: string): boolean { + const macro = this.macros.get(name); + return macro != null ? typeof macro === "string" + || typeof macro === "function" || !macro.unexpandable + : functions.hasOwnProperty(name) && !functions[name].primitive; + } +} diff --git a/frontend/node_modules/katex/src/Namespace.js b/frontend/node_modules/katex/src/Namespace.js new file mode 100644 index 0000000..958a13a --- /dev/null +++ b/frontend/node_modules/katex/src/Namespace.js @@ -0,0 +1,129 @@ +// @flow + +/** + * A `Namespace` refers to a space of nameable things like macros or lengths, + * which can be `set` either globally or local to a nested group, using an + * undo stack similar to how TeX implements this functionality. + * Performance-wise, `get` and local `set` take constant time, while global + * `set` takes time proportional to the depth of group nesting. + */ + +import ParseError from "./ParseError"; + +export type Mapping = {[string]: Value}; + +export default class Namespace { + current: Mapping; + builtins: Mapping; + undefStack: Mapping[]; + + /** + * Both arguments are optional. The first argument is an object of + * built-in mappings which never change. The second argument is an object + * of initial (global-level) mappings, which will constantly change + * according to any global/top-level `set`s done. + */ + constructor(builtins: Mapping = {}, + globalMacros: Mapping = {}) { + this.current = globalMacros; + this.builtins = builtins; + this.undefStack = []; + } + + /** + * Start a new nested group, affecting future local `set`s. + */ + beginGroup() { + this.undefStack.push({}); + } + + /** + * End current nested group, restoring values before the group began. + */ + endGroup() { + if (this.undefStack.length === 0) { + throw new ParseError("Unbalanced namespace destruction: attempt " + + "to pop global namespace; please report this as a bug"); + } + const undefs = this.undefStack.pop(); + for (const undef in undefs) { + if (undefs.hasOwnProperty(undef)) { + if (undefs[undef] == null) { + delete this.current[undef]; + } else { + this.current[undef] = undefs[undef]; + } + } + } + } + + /** + * Ends all currently nested groups (if any), restoring values before the + * groups began. Useful in case of an error in the middle of parsing. + */ + endGroups() { + while (this.undefStack.length > 0) { + this.endGroup(); + } + } + + /** + * Detect whether `name` has a definition. Equivalent to + * `get(name) != null`. + */ + has(name: string): boolean { + return this.current.hasOwnProperty(name) || + this.builtins.hasOwnProperty(name); + } + + /** + * Get the current value of a name, or `undefined` if there is no value. + * + * Note: Do not use `if (namespace.get(...))` to detect whether a macro + * is defined, as the definition may be the empty string which evaluates + * to `false` in JavaScript. Use `if (namespace.get(...) != null)` or + * `if (namespace.has(...))`. + */ + get(name: string): ?Value { + if (this.current.hasOwnProperty(name)) { + return this.current[name]; + } else { + return this.builtins[name]; + } + } + + /** + * Set the current value of a name, and optionally set it globally too. + * Local set() sets the current value and (when appropriate) adds an undo + * operation to the undo stack. Global set() may change the undo + * operation at every level, so takes time linear in their number. + * A value of undefined means to delete existing definitions. + */ + set(name: string, value: ?Value, global: boolean = false) { + if (global) { + // Global set is equivalent to setting in all groups. Simulate this + // by destroying any undos currently scheduled for this name, + // and adding an undo with the *new* value (in case it later gets + // locally reset within this environment). + for (let i = 0; i < this.undefStack.length; i++) { + delete this.undefStack[i][name]; + } + if (this.undefStack.length > 0) { + this.undefStack[this.undefStack.length - 1][name] = value; + } + } else { + // Undo this set at end of this group (possibly to `undefined`), + // unless an undo is already in place, in which case that older + // value is the correct one. + const top = this.undefStack[this.undefStack.length - 1]; + if (top && !top.hasOwnProperty(name)) { + top[name] = this.current[name]; + } + } + if (value == null) { + delete this.current[name]; + } else { + this.current[name] = value; + } + } +} diff --git a/frontend/node_modules/katex/src/Options.js b/frontend/node_modules/katex/src/Options.js new file mode 100644 index 0000000..060b922 --- /dev/null +++ b/frontend/node_modules/katex/src/Options.js @@ -0,0 +1,319 @@ +// @flow +/** + * This file contains information about the options that the Parser carries + * around with it while parsing. Data is held in an `Options` object, and when + * recursing, a new `Options` object can be created with the `.with*` and + * `.reset` functions. + */ + +import {getGlobalMetrics} from "./fontMetrics"; +import type {FontMetrics} from "./fontMetrics"; +import type {StyleInterface} from "./Style"; + +const sizeStyleMap = [ + // Each element contains [textsize, scriptsize, scriptscriptsize]. + // The size mappings are taken from TeX with \normalsize=10pt. + [1, 1, 1], // size1: [5, 5, 5] \tiny + [2, 1, 1], // size2: [6, 5, 5] + [3, 1, 1], // size3: [7, 5, 5] \scriptsize + [4, 2, 1], // size4: [8, 6, 5] \footnotesize + [5, 2, 1], // size5: [9, 6, 5] \small + [6, 3, 1], // size6: [10, 7, 5] \normalsize + [7, 4, 2], // size7: [12, 8, 6] \large + [8, 6, 3], // size8: [14.4, 10, 7] \Large + [9, 7, 6], // size9: [17.28, 12, 10] \LARGE + [10, 8, 7], // size10: [20.74, 14.4, 12] \huge + [11, 10, 9], // size11: [24.88, 20.74, 17.28] \HUGE +]; + +const sizeMultipliers = [ + // fontMetrics.js:getGlobalMetrics also uses size indexes, so if + // you change size indexes, change that function. + 0.5, 0.6, 0.7, 0.8, 0.9, 1.0, 1.2, 1.44, 1.728, 2.074, 2.488, +]; + +const sizeAtStyle = function(size: number, style: StyleInterface): number { + return style.size < 2 ? size : sizeStyleMap[size - 1][style.size - 1]; +}; + +// In these types, "" (empty string) means "no change". +export type FontWeight = "textbf" | "textmd" | ""; +export type FontShape = "textit" | "textup" | ""; + +export type OptionsData = { + style: StyleInterface; + color?: string | void; + size?: number; + textSize?: number; + phantom?: boolean; + font?: string; + fontFamily?: string; + fontWeight?: FontWeight; + fontShape?: FontShape; + sizeMultiplier?: number; + maxSize: number; + minRuleThickness: number; +}; + +/** + * This is the main options class. It contains the current style, size, color, + * and font. + * + * Options objects should not be modified. To create a new Options with + * different properties, call a `.having*` method. + */ +class Options { + style: StyleInterface; + color: string | void; + size: number; + textSize: number; + phantom: boolean; + // A font family applies to a group of fonts (i.e. SansSerif), while a font + // represents a specific font (i.e. SansSerif Bold). + // See: https://tex.stackexchange.com/questions/22350/difference-between-textrm-and-mathrm + font: string; + fontFamily: string; + fontWeight: FontWeight; + fontShape: FontShape; + sizeMultiplier: number; + maxSize: number; + minRuleThickness: number; + _fontMetrics: FontMetrics | void; + + /** + * The base size index. + */ + static BASESIZE: number = 6; + + constructor(data: OptionsData) { + this.style = data.style; + this.color = data.color; + this.size = data.size || Options.BASESIZE; + this.textSize = data.textSize || this.size; + this.phantom = !!data.phantom; + this.font = data.font || ""; + this.fontFamily = data.fontFamily || ""; + this.fontWeight = data.fontWeight || ''; + this.fontShape = data.fontShape || ''; + this.sizeMultiplier = sizeMultipliers[this.size - 1]; + this.maxSize = data.maxSize; + this.minRuleThickness = data.minRuleThickness; + this._fontMetrics = undefined; + } + + /** + * Returns a new options object with the same properties as "this". Properties + * from "extension" will be copied to the new options object. + */ + extend(extension: $Shape): Options { + const data = { + style: this.style, + size: this.size, + textSize: this.textSize, + color: this.color, + phantom: this.phantom, + font: this.font, + fontFamily: this.fontFamily, + fontWeight: this.fontWeight, + fontShape: this.fontShape, + maxSize: this.maxSize, + minRuleThickness: this.minRuleThickness, + }; + + for (const key in extension) { + if (extension.hasOwnProperty(key)) { + data[key] = extension[key]; + } + } + + return new Options(data); + } + + /** + * Return an options object with the given style. If `this.style === style`, + * returns `this`. + */ + havingStyle(style: StyleInterface): Options { + if (this.style === style) { + return this; + } else { + return this.extend({ + style: style, + size: sizeAtStyle(this.textSize, style), + }); + } + } + + /** + * Return an options object with a cramped version of the current style. If + * the current style is cramped, returns `this`. + */ + havingCrampedStyle(): Options { + return this.havingStyle(this.style.cramp()); + } + + /** + * Return an options object with the given size and in at least `\textstyle`. + * Returns `this` if appropriate. + */ + havingSize(size: number): Options { + if (this.size === size && this.textSize === size) { + return this; + } else { + return this.extend({ + style: this.style.text(), + size: size, + textSize: size, + sizeMultiplier: sizeMultipliers[size - 1], + }); + } + } + + /** + * Like `this.havingSize(BASESIZE).havingStyle(style)`. If `style` is omitted, + * changes to at least `\textstyle`. + */ + havingBaseStyle(style: StyleInterface): Options { + style = style || this.style.text(); + const wantSize = sizeAtStyle(Options.BASESIZE, style); + if (this.size === wantSize && this.textSize === Options.BASESIZE + && this.style === style) { + return this; + } else { + return this.extend({ + style: style, + size: wantSize, + }); + } + } + + /** + * Remove the effect of sizing changes such as \Huge. + * Keep the effect of the current style, such as \scriptstyle. + */ + havingBaseSizing(): Options { + let size; + switch (this.style.id) { + case 4: + case 5: + size = 3; // normalsize in scriptstyle + break; + case 6: + case 7: + size = 1; // normalsize in scriptscriptstyle + break; + default: + size = 6; // normalsize in textstyle or displaystyle + } + return this.extend({ + style: this.style.text(), + size: size, + }); + } + + /** + * Create a new options object with the given color. + */ + withColor(color: string): Options { + return this.extend({ + color: color, + }); + } + + /** + * Create a new options object with "phantom" set to true. + */ + withPhantom(): Options { + return this.extend({ + phantom: true, + }); + } + + /** + * Creates a new options object with the given math font or old text font. + * @type {[type]} + */ + withFont(font: string): Options { + return this.extend({ + font, + }); + } + + /** + * Create a new options objects with the given fontFamily. + */ + withTextFontFamily(fontFamily: string): Options { + return this.extend({ + fontFamily, + font: "", + }); + } + + /** + * Creates a new options object with the given font weight + */ + withTextFontWeight(fontWeight: FontWeight): Options { + return this.extend({ + fontWeight, + font: "", + }); + } + + /** + * Creates a new options object with the given font weight + */ + withTextFontShape(fontShape: FontShape): Options { + return this.extend({ + fontShape, + font: "", + }); + } + + /** + * Return the CSS sizing classes required to switch from enclosing options + * `oldOptions` to `this`. Returns an array of classes. + */ + sizingClasses(oldOptions: Options): Array { + if (oldOptions.size !== this.size) { + return ["sizing", "reset-size" + oldOptions.size, "size" + this.size]; + } else { + return []; + } + } + + /** + * Return the CSS sizing classes required to switch to the base size. Like + * `this.havingSize(BASESIZE).sizingClasses(this)`. + */ + baseSizingClasses(): Array { + if (this.size !== Options.BASESIZE) { + return ["sizing", "reset-size" + this.size, "size" + Options.BASESIZE]; + } else { + return []; + } + } + + /** + * Return the font metrics for this size. + */ + fontMetrics(): FontMetrics { + if (!this._fontMetrics) { + this._fontMetrics = getGlobalMetrics(this.size); + } + return this._fontMetrics; + } + + + /** + * Gets the CSS color of the current options object + */ + getColor(): string | void { + if (this.phantom) { + return "transparent"; + } else { + return this.color; + } + } +} + +export default Options; diff --git a/frontend/node_modules/katex/src/ParseError.js b/frontend/node_modules/katex/src/ParseError.js new file mode 100644 index 0000000..2b8d174 --- /dev/null +++ b/frontend/node_modules/katex/src/ParseError.js @@ -0,0 +1,86 @@ +// @flow +import {Token} from "./Token"; + +import type {AnyParseNode} from "./parseNode"; + +/** + * This is the ParseError class, which is the main error thrown by KaTeX + * functions when something has gone wrong. This is used to distinguish internal + * errors from errors in the expression that the user provided. + * + * If possible, a caller should provide a Token or ParseNode with information + * about where in the source string the problem occurred. + */ +class ParseError { + name: "ParseError"; + position: number | void; + // Error start position based on passed-in Token or ParseNode. + length: number | void; + // Length of affected text based on passed-in Token or ParseNode. + rawMessage: string | void; + // The underlying error message without any context added. + + constructor( + message: string, // The error message + token?: ?Token | AnyParseNode, // An object providing position information + ): ParseError { + let error = "KaTeX parse error: " + message; + let start; + let end; + + const loc = token && token.loc; + if (loc && loc.start <= loc.end) { + // If we have the input and a position, make the error a bit fancier + + // Get the input + const input = loc.lexer.input; + + // Prepend some information + start = loc.start; + end = loc.end; + if (start === input.length) { + error += " at end of input: "; + } else { + error += " at position " + (start + 1) + ": "; + } + + // Underline token in question using combining underscores + const underlined = input.slice(start, end).replace(/[^]/g, "$&\u0332"); + + // Extract some context from the input and add it to the error + let left; + if (start > 15) { + left = "…" + input.slice(start - 15, start); + } else { + left = input.slice(0, start); + } + let right; + if (end + 15 < input.length) { + right = input.slice(end, end + 15) + "…"; + } else { + right = input.slice(end); + } + error += left + underlined + right; + + } + + // Some hackery to make ParseError a prototype of Error + // See http://stackoverflow.com/a/8460753 + // $FlowFixMe + const self: ParseError = new Error(error); + self.name = "ParseError"; + // $FlowFixMe + self.__proto__ = ParseError.prototype; + self.position = start; + if (start != null && end != null) { + self.length = end - start; + } + self.rawMessage = message; + return self; + } +} + +// $FlowFixMe More hackery +ParseError.prototype.__proto__ = Error.prototype; + +export default ParseError; diff --git a/frontend/node_modules/katex/src/Parser.js b/frontend/node_modules/katex/src/Parser.js new file mode 100644 index 0000000..51d8db5 --- /dev/null +++ b/frontend/node_modules/katex/src/Parser.js @@ -0,0 +1,1041 @@ +// @flow +/* eslint no-constant-condition:0 */ +import functions from "./functions"; +import MacroExpander, {implicitCommands} from "./MacroExpander"; +import symbols, {ATOMS, extraLatin} from "./symbols"; +import {validUnit} from "./units"; +import {supportedCodepoint} from "./unicodeScripts"; +import ParseError from "./ParseError"; +import {combiningDiacriticalMarksEndRegex} from "./Lexer"; +import Settings from "./Settings"; +import SourceLocation from "./SourceLocation"; +import {uSubsAndSups, unicodeSubRegEx} from "./unicodeSupOrSub"; +import {Token} from "./Token"; + +// Pre-evaluate both modules as unicodeSymbols require String.normalize() +import unicodeAccents from /*preval*/ "./unicodeAccents"; +import unicodeSymbols from /*preval*/ "./unicodeSymbols"; + +import type {ParseNode, AnyParseNode, SymbolParseNode, UnsupportedCmdParseNode} + from "./parseNode"; +import type {Atom, Group} from "./symbols"; +import type {Mode, ArgType, BreakToken} from "./types"; +import type {FunctionContext, FunctionSpec} from "./defineFunction"; +import type {EnvSpec} from "./defineEnvironment"; + +/** + * This file contains the parser used to parse out a TeX expression from the + * input. Since TeX isn't context-free, standard parsers don't work particularly + * well. + * + * The strategy of this parser is as such: + * + * The main functions (the `.parse...` ones) take a position in the current + * parse string to parse tokens from. The lexer (found in Lexer.js, stored at + * this.gullet.lexer) also supports pulling out tokens at arbitrary places. When + * individual tokens are needed at a position, the lexer is called to pull out a + * token, which is then used. + * + * The parser has a property called "mode" indicating the mode that + * the parser is currently in. Currently it has to be one of "math" or + * "text", which denotes whether the current environment is a math-y + * one or a text-y one (e.g. inside \text). Currently, this serves to + * limit the functions which can be used in text mode. + * + * The main functions then return an object which contains the useful data that + * was parsed at its given point, and a new position at the end of the parsed + * data. The main functions can call each other and continue the parsing by + * using the returned position as a new starting point. + * + * There are also extra `.handle...` functions, which pull out some reused + * functionality into self-contained functions. + * + * The functions return ParseNodes. + */ + +export default class Parser { + mode: Mode; + gullet: MacroExpander; + settings: Settings; + leftrightDepth: number; + nextToken: ?Token; + + constructor(input: string, settings: Settings) { + // Start in math mode + this.mode = "math"; + // Create a new macro expander (gullet) and (indirectly via that) also a + // new lexer (mouth) for this parser (stomach, in the language of TeX) + this.gullet = new MacroExpander(input, settings, this.mode); + // Store the settings for use in parsing + this.settings = settings; + // Count leftright depth (for \middle errors) + this.leftrightDepth = 0; + } + + /** + * Checks a result to make sure it has the right type, and throws an + * appropriate error otherwise. + */ + expect(text: string, consume?: boolean = true) { + if (this.fetch().text !== text) { + throw new ParseError( + `Expected '${text}', got '${this.fetch().text}'`, this.fetch() + ); + } + if (consume) { + this.consume(); + } + } + + /** + * Discards the current lookahead token, considering it consumed. + */ + consume() { + this.nextToken = null; + } + + /** + * Return the current lookahead token, or if there isn't one (at the + * beginning, or if the previous lookahead token was consume()d), + * fetch the next token as the new lookahead token and return it. + */ + fetch(): Token { + if (this.nextToken == null) { + this.nextToken = this.gullet.expandNextToken(); + } + return this.nextToken; + } + + /** + * Switches between "text" and "math" modes. + */ + switchMode(newMode: Mode) { + this.mode = newMode; + this.gullet.switchMode(newMode); + } + + /** + * Main parsing function, which parses an entire input. + */ + parse(): AnyParseNode[] { + if (!this.settings.globalGroup) { + // Create a group namespace for the math expression. + // (LaTeX creates a new group for every $...$, $$...$$, \[...\].) + this.gullet.beginGroup(); + } + + // Use old \color behavior (same as LaTeX's \textcolor) if requested. + // We do this within the group for the math expression, so it doesn't + // pollute settings.macros. + if (this.settings.colorIsTextColor) { + this.gullet.macros.set("\\color", "\\textcolor"); + } + + try { + // Try to parse the input + const parse = this.parseExpression(false); + + // If we succeeded, make sure there's an EOF at the end + this.expect("EOF"); + + // End the group namespace for the expression + if (!this.settings.globalGroup) { + this.gullet.endGroup(); + } + + return parse; + + // Close any leftover groups in case of a parse error. + } finally { + this.gullet.endGroups(); + } + } + + /** + * Fully parse a separate sequence of tokens as a separate job. + * Tokens should be specified in reverse order, as in a MacroDefinition. + */ + subparse(tokens: Token[]): AnyParseNode[] { + // Save the next token from the current job. + const oldToken = this.nextToken; + this.consume(); + + // Run the new job, terminating it with an excess '}' + this.gullet.pushToken(new Token("}")); + this.gullet.pushTokens(tokens); + const parse = this.parseExpression(false); + this.expect("}"); + + // Restore the next token from the current job. + this.nextToken = oldToken; + + return parse; + } + + static endOfExpression: string[] = ["}", "\\endgroup", "\\end", "\\right", "&"]; + + /** + * Parses an "expression", which is a list of atoms. + * + * `breakOnInfix`: Should the parsing stop when we hit infix nodes? This + * happens when functions have higher precedence han infix + * nodes in implicit parses. + * + * `breakOnTokenText`: The text of the token that the expression should end + * with, or `null` if something else should end the + * expression. + */ + parseExpression( + breakOnInfix: boolean, + breakOnTokenText?: BreakToken, + ): AnyParseNode[] { + const body = []; + // Keep adding atoms to the body until we can't parse any more atoms (either + // we reached the end, a }, or a \right) + while (true) { + // Ignore spaces in math mode + if (this.mode === "math") { + this.consumeSpaces(); + } + const lex = this.fetch(); + if (Parser.endOfExpression.indexOf(lex.text) !== -1) { + break; + } + if (breakOnTokenText && lex.text === breakOnTokenText) { + break; + } + if (breakOnInfix && functions[lex.text] && functions[lex.text].infix) { + break; + } + const atom = this.parseAtom(breakOnTokenText); + if (!atom) { + break; + } else if (atom.type === "internal") { + // Internal nodes do not appear in parse tree + continue; + } + body.push(atom); + } + if (this.mode === "text") { + this.formLigatures(body); + } + return this.handleInfixNodes(body); + } + + /** + * Rewrites infix operators such as \over with corresponding commands such + * as \frac. + * + * There can only be one infix operator per group. If there's more than one + * then the expression is ambiguous. This can be resolved by adding {}. + */ + handleInfixNodes(body: AnyParseNode[]): AnyParseNode[] { + let overIndex = -1; + let funcName; + + for (let i = 0; i < body.length; i++) { + if (body[i].type === "infix") { + if (overIndex !== -1) { + throw new ParseError( + "only one infix operator per group", + body[i].token); + } + overIndex = i; + funcName = body[i].replaceWith; + } + } + + if (overIndex !== -1 && funcName) { + let numerNode; + let denomNode; + + const numerBody = body.slice(0, overIndex); + const denomBody = body.slice(overIndex + 1); + + if (numerBody.length === 1 && numerBody[0].type === "ordgroup") { + numerNode = numerBody[0]; + } else { + numerNode = {type: "ordgroup", mode: this.mode, body: numerBody}; + } + + if (denomBody.length === 1 && denomBody[0].type === "ordgroup") { + denomNode = denomBody[0]; + } else { + denomNode = {type: "ordgroup", mode: this.mode, body: denomBody}; + } + + let node; + if (funcName === "\\\\abovefrac") { + node = this.callFunction(funcName, + [numerNode, body[overIndex], denomNode], []); + } else { + node = this.callFunction(funcName, [numerNode, denomNode], []); + } + return [node]; + } else { + return body; + } + } + + /** + * Handle a subscript or superscript with nice errors. + */ + handleSupSubscript( + name: string, // For error reporting. + ): AnyParseNode { + const symbolToken = this.fetch(); + const symbol = symbolToken.text; + this.consume(); + this.consumeSpaces(); // ignore spaces before sup/subscript argument + + // Skip over allowed internal nodes such as \relax + let group: ?AnyParseNode; + do { + group = this.parseGroup(name); + } while (group?.type === "internal"); + + if (!group) { + throw new ParseError( + "Expected group after '" + symbol + "'", + symbolToken + ); + } + + return group; + } + + /** + * Converts the textual input of an unsupported command into a text node + * contained within a color node whose color is determined by errorColor + */ + formatUnsupportedCmd(text: string): UnsupportedCmdParseNode { + const textordArray = []; + + for (let i = 0; i < text.length; i++) { + textordArray.push({type: "textord", mode: "text", text: text[i]}); + } + + const textNode = { + type: "text", + mode: this.mode, + body: textordArray, + }; + + const colorNode = { + type: "color", + mode: this.mode, + color: this.settings.errorColor, + body: [textNode], + }; + + return colorNode; + } + + /** + * Parses a group with optional super/subscripts. + */ + parseAtom(breakOnTokenText?: BreakToken): ?AnyParseNode { + // The body of an atom is an implicit group, so that things like + // \left(x\right)^2 work correctly. + const base = this.parseGroup("atom", breakOnTokenText); + + // Internal nodes (e.g. \relax) cannot support super/subscripts. + // Instead we will pick up super/subscripts with blank base next round. + if (base?.type === "internal") { + return base; + } + + // In text mode, we don't have superscripts or subscripts + if (this.mode === "text") { + return base; + } + + // Note that base may be empty (i.e. null) at this point. + + let superscript; + let subscript; + while (true) { + // Guaranteed in math mode, so eat any spaces first. + this.consumeSpaces(); + + // Lex the first token + const lex = this.fetch(); + + if (lex.text === "\\limits" || lex.text === "\\nolimits") { + // We got a limit control + if (base && base.type === "op") { + const limits = lex.text === "\\limits"; + base.limits = limits; + base.alwaysHandleSupSub = true; + } else if (base && base.type === "operatorname") { + if (base.alwaysHandleSupSub) { + base.limits = lex.text === "\\limits"; + } + } else { + throw new ParseError( + "Limit controls must follow a math operator", + lex); + } + this.consume(); + } else if (lex.text === "^") { + // We got a superscript start + if (superscript) { + throw new ParseError("Double superscript", lex); + } + superscript = this.handleSupSubscript("superscript"); + } else if (lex.text === "_") { + // We got a subscript start + if (subscript) { + throw new ParseError("Double subscript", lex); + } + subscript = this.handleSupSubscript("subscript"); + } else if (lex.text === "'") { + // We got a prime + if (superscript) { + throw new ParseError("Double superscript", lex); + } + const prime = {type: "textord", mode: this.mode, text: "\\prime"}; + + // Many primes can be grouped together, so we handle this here + const primes = [prime]; + this.consume(); + // Keep lexing tokens until we get something that's not a prime + while (this.fetch().text === "'") { + // For each one, add another prime to the list + primes.push(prime); + this.consume(); + } + // If there's a superscript following the primes, combine that + // superscript in with the primes. + if (this.fetch().text === "^") { + primes.push(this.handleSupSubscript("superscript")); + } + // Put everything into an ordgroup as the superscript + superscript = {type: "ordgroup", mode: this.mode, body: primes}; + } else if (uSubsAndSups[lex.text]) { + // A Unicode subscript or superscript character. + // We treat these similarly to the unicode-math package. + // So we render a string of Unicode (sub|super)scripts the + // same as a (sub|super)script of regular characters. + const isSub = unicodeSubRegEx.test(lex.text); + const subsupTokens = []; + subsupTokens.push(new Token(uSubsAndSups[lex.text])); + this.consume(); + // Continue fetching tokens to fill out the string. + while (true) { + const token = this.fetch().text; + if (!(uSubsAndSups[token])) { break; } + if (unicodeSubRegEx.test(token) !== isSub) { break; } + subsupTokens.unshift(new Token(uSubsAndSups[token])); + this.consume(); + } + // Now create a (sub|super)script. + const body = this.subparse(subsupTokens); + if (isSub) { + subscript = {type: "ordgroup", mode: "math", body}; + } else { + superscript = {type: "ordgroup", mode: "math", body}; + } + } else { + // If it wasn't ^, _, or ', stop parsing super/subscripts + break; + } + } + + // Base must be set if superscript or subscript are set per logic above, + // but need to check here for type check to pass. + if (superscript || subscript) { + // If we got either a superscript or subscript, create a supsub + return { + type: "supsub", + mode: this.mode, + base: base, + sup: superscript, + sub: subscript, + }; + } else { + // Otherwise return the original body + return base; + } + } + + /** + * Parses an entire function, including its base and all of its arguments. + */ + parseFunction( + breakOnTokenText?: BreakToken, + name?: string, // For determining its context + ): ?AnyParseNode { + const token = this.fetch(); + const func = token.text; + const funcData = functions[func]; + if (!funcData) { + return null; + } + this.consume(); // consume command token + + if (name && name !== "atom" && !funcData.allowedInArgument) { + throw new ParseError( + "Got function '" + func + "' with no arguments" + + (name ? " as " + name : ""), token); + } else if (this.mode === "text" && !funcData.allowedInText) { + throw new ParseError( + "Can't use function '" + func + "' in text mode", token); + } else if (this.mode === "math" && funcData.allowedInMath === false) { + throw new ParseError( + "Can't use function '" + func + "' in math mode", token); + } + + const {args, optArgs} = this.parseArguments(func, funcData); + return this.callFunction(func, args, optArgs, token, breakOnTokenText); + } + + /** + * Call a function handler with a suitable context and arguments. + */ + callFunction( + name: string, + args: AnyParseNode[], + optArgs: (?AnyParseNode)[], + token?: Token, + breakOnTokenText?: BreakToken, + ): AnyParseNode { + const context: FunctionContext = { + funcName: name, + parser: this, + token, + breakOnTokenText, + }; + const func = functions[name]; + if (func && func.handler) { + return func.handler(context, args, optArgs); + } else { + throw new ParseError(`No function handler for ${name}`); + } + } + + /** + * Parses the arguments of a function or environment + */ + parseArguments( + func: string, // Should look like "\name" or "\begin{name}". + funcData: FunctionSpec<*> | EnvSpec<*>, + ): { + args: AnyParseNode[], + optArgs: (?AnyParseNode)[], + } { + const totalArgs = funcData.numArgs + funcData.numOptionalArgs; + if (totalArgs === 0) { + return {args: [], optArgs: []}; + } + + const args = []; + const optArgs = []; + + for (let i = 0; i < totalArgs; i++) { + let argType = funcData.argTypes && funcData.argTypes[i]; + const isOptional = i < funcData.numOptionalArgs; + + if ((funcData.primitive && argType == null) || + // \sqrt expands into primitive if optional argument doesn't exist + (funcData.type === "sqrt" && i === 1 && optArgs[0] == null)) { + argType = "primitive"; + } + + const arg = this.parseGroupOfType(`argument to '${func}'`, + argType, isOptional); + if (isOptional) { + optArgs.push(arg); + } else if (arg != null) { + args.push(arg); + } else { // should be unreachable + throw new ParseError("Null argument, please report this as a bug"); + } + } + + return {args, optArgs}; + } + + /** + * Parses a group when the mode is changing. + */ + parseGroupOfType( + name: string, + type: ?ArgType, + optional: boolean, + ): ?AnyParseNode { + switch (type) { + case "color": + return this.parseColorGroup(optional); + case "size": + return this.parseSizeGroup(optional); + case "url": + return this.parseUrlGroup(optional); + case "math": + case "text": + return this.parseArgumentGroup(optional, type); + case "hbox": { + // hbox argument type wraps the argument in the equivalent of + // \hbox, which is like \text but switching to \textstyle size. + const group = this.parseArgumentGroup(optional, "text"); + return group != null ? { + type: "styling", + mode: group.mode, + body: [group], + style: "text", // simulate \textstyle + } : null; + } + case "raw": { + const token = this.parseStringGroup("raw", optional); + return token != null ? { + type: "raw", + mode: "text", + string: token.text, + } : null; + } + case "primitive": { + if (optional) { + throw new ParseError("A primitive argument cannot be optional"); + } + const group = this.parseGroup(name); + if (group == null) { + throw new ParseError("Expected group as " + name, this.fetch()); + } + return group; + } + case "original": + case null: + case undefined: + return this.parseArgumentGroup(optional); + default: + throw new ParseError( + "Unknown group type as " + name, this.fetch()); + } + } + + /** + * Discard any space tokens, fetching the next non-space token. + */ + consumeSpaces() { + while (this.fetch().text === " ") { + this.consume(); + } + } + + /** + * Parses a group, essentially returning the string formed by the + * brace-enclosed tokens plus some position information. + */ + parseStringGroup( + modeName: ArgType, // Used to describe the mode in error messages. + optional: boolean, + ): ?Token { + const argToken = this.gullet.scanArgument(optional); + if (argToken == null) { + return null; + } + let str = ""; + let nextToken; + while ((nextToken = this.fetch()).text !== "EOF") { + str += nextToken.text; + this.consume(); + } + this.consume(); // consume the end of the argument + argToken.text = str; + return argToken; + } + + /** + * Parses a regex-delimited group: the largest sequence of tokens + * whose concatenated strings match `regex`. Returns the string + * formed by the tokens plus some position information. + */ + parseRegexGroup( + regex: RegExp, + modeName: string, // Used to describe the mode in error messages. + ): Token { + const firstToken = this.fetch(); + let lastToken = firstToken; + let str = ""; + let nextToken; + while ((nextToken = this.fetch()).text !== "EOF" && + regex.test(str + nextToken.text)) { + lastToken = nextToken; + str += lastToken.text; + this.consume(); + } + if (str === "") { + throw new ParseError( + "Invalid " + modeName + ": '" + firstToken.text + "'", + firstToken); + } + return firstToken.range(lastToken, str); + } + + /** + * Parses a color description. + */ + parseColorGroup(optional: boolean): ?ParseNode<"color-token"> { + const res = this.parseStringGroup("color", optional); + if (res == null) { + return null; + } + const match = (/^(#[a-f0-9]{3}|#?[a-f0-9]{6}|[a-z]+)$/i).exec(res.text); + if (!match) { + throw new ParseError("Invalid color: '" + res.text + "'", res); + } + let color = match[0]; + if (/^[0-9a-f]{6}$/i.test(color)) { + // We allow a 6-digit HTML color spec without a leading "#". + // This follows the xcolor package's HTML color model. + // Predefined color names are all missed by this RegEx pattern. + color = "#" + color; + } + return { + type: "color-token", + mode: this.mode, + color, + }; + } + + /** + * Parses a size specification, consisting of magnitude and unit. + */ + parseSizeGroup(optional: boolean): ?ParseNode<"size"> { + let res; + let isBlank = false; + // don't expand before parseStringGroup + this.gullet.consumeSpaces(); + if (!optional && this.gullet.future().text !== "{") { + res = this.parseRegexGroup( + /^[-+]? *(?:$|\d+|\d+\.\d*|\.\d*) *[a-z]{0,2} *$/, "size"); + } else { + res = this.parseStringGroup("size", optional); + } + if (!res) { + return null; + } + if (!optional && res.text.length === 0) { + // Because we've tested for what is !optional, this block won't + // affect \kern, \hspace, etc. It will capture the mandatory arguments + // to \genfrac and \above. + res.text = "0pt"; // Enable \above{} + isBlank = true; // This is here specifically for \genfrac + } + const match = (/([-+]?) *(\d+(?:\.\d*)?|\.\d+) *([a-z]{2})/).exec(res.text); + if (!match) { + throw new ParseError("Invalid size: '" + res.text + "'", res); + } + const data = { + number: +(match[1] + match[2]), // sign + magnitude, cast to number + unit: match[3], + }; + if (!validUnit(data)) { + throw new ParseError("Invalid unit: '" + data.unit + "'", res); + } + return { + type: "size", + mode: this.mode, + value: data, + isBlank, + }; + } + + /** + * Parses an URL, checking escaped letters and allowed protocols, + * and setting the catcode of % as an active character (as in \hyperref). + */ + parseUrlGroup(optional: boolean): ?ParseNode<"url"> { + this.gullet.lexer.setCatcode("%", 13); // active character + this.gullet.lexer.setCatcode("~", 12); // other character + const res = this.parseStringGroup("url", optional); + this.gullet.lexer.setCatcode("%", 14); // comment character + this.gullet.lexer.setCatcode("~", 13); // active character + if (res == null) { + return null; + } + // hyperref package allows backslashes alone in href, but doesn't + // generate valid links in such cases; we interpret this as + // "undefined" behaviour, and keep them as-is. Some browser will + // replace backslashes with forward slashes. + const url = res.text.replace(/\\([#$%&~_^{}])/g, '$1'); + return { + type: "url", + mode: this.mode, + url, + }; + } + + /** + * Parses an argument with the mode specified. + */ + parseArgumentGroup(optional: boolean, mode?: Mode): ?ParseNode<"ordgroup"> { + const argToken = this.gullet.scanArgument(optional); + if (argToken == null) { + return null; + } + const outerMode = this.mode; + if (mode) { // Switch to specified mode + this.switchMode(mode); + } + + this.gullet.beginGroup(); + const expression = this.parseExpression(false, "EOF"); + // TODO: find an alternative way to denote the end + this.expect("EOF"); // expect the end of the argument + this.gullet.endGroup(); + const result = { + type: "ordgroup", + mode: this.mode, + loc: argToken.loc, + body: expression, + }; + + if (mode) { // Switch mode back + this.switchMode(outerMode); + } + return result; + } + + /** + * Parses an ordinary group, which is either a single nucleus (like "x") + * or an expression in braces (like "{x+y}") or an implicit group, a group + * that starts at the current position, and ends right before a higher explicit + * group ends, or at EOF. + */ + parseGroup( + name: string, // For error reporting. + breakOnTokenText?: BreakToken, + ): ?AnyParseNode { + const firstToken = this.fetch(); + const text = firstToken.text; + + let result; + // Try to parse an open brace or \begingroup + if (text === "{" || text === "\\begingroup") { + this.consume(); + const groupEnd = text === "{" ? "}" : "\\endgroup"; + + this.gullet.beginGroup(); + // If we get a brace, parse an expression + const expression = this.parseExpression(false, groupEnd); + const lastToken = this.fetch(); + this.expect(groupEnd); // Check that we got a matching closing brace + this.gullet.endGroup(); + result = { + type: "ordgroup", + mode: this.mode, + loc: SourceLocation.range(firstToken, lastToken), + body: expression, + // A group formed by \begingroup...\endgroup is a semi-simple group + // which doesn't affect spacing in math mode, i.e., is transparent. + // https://tex.stackexchange.com/questions/1930/when-should-one- + // use-begingroup-instead-of-bgroup + semisimple: text === "\\begingroup" || undefined, + }; + } else { + // If there exists a function with this name, parse the function. + // Otherwise, just return a nucleus + result = this.parseFunction(breakOnTokenText, name) || + this.parseSymbol(); + if (result == null && text[0] === "\\" && + !implicitCommands.hasOwnProperty(text)) { + if (this.settings.throwOnError) { + throw new ParseError( + "Undefined control sequence: " + text, firstToken); + } + result = this.formatUnsupportedCmd(text); + this.consume(); + } + } + return result; + } + + /** + * Form ligature-like combinations of characters for text mode. + * This includes inputs like "--", "---", "``" and "''". + * The result will simply replace multiple textord nodes with a single + * character in each value by a single textord node having multiple + * characters in its value. The representation is still ASCII source. + * The group will be modified in place. + */ + formLigatures(group: AnyParseNode[]) { + let n = group.length - 1; + for (let i = 0; i < n; ++i) { + const a = group[i]; + // $FlowFixMe: Not every node type has a `text` property. + const v = a.text; + if (v === "-" && group[i + 1].text === "-") { + if (i + 1 < n && group[i + 2].text === "-") { + group.splice(i, 3, { + type: "textord", + mode: "text", + loc: SourceLocation.range(a, group[i + 2]), + text: "---", + }); + n -= 2; + } else { + group.splice(i, 2, { + type: "textord", + mode: "text", + loc: SourceLocation.range(a, group[i + 1]), + text: "--", + }); + n -= 1; + } + } + if ((v === "'" || v === "`") && group[i + 1].text === v) { + group.splice(i, 2, { + type: "textord", + mode: "text", + loc: SourceLocation.range(a, group[i + 1]), + text: v + v, + }); + n -= 1; + } + } + } + + /** + * Parse a single symbol out of the string. Here, we handle single character + * symbols and special functions like \verb. + */ + parseSymbol(): ?AnyParseNode { + const nucleus = this.fetch(); + let text = nucleus.text; + + if (/^\\verb[^a-zA-Z]/.test(text)) { + this.consume(); + let arg = text.slice(5); + const star = (arg.charAt(0) === "*"); + if (star) { + arg = arg.slice(1); + } + // Lexer's tokenRegex is constructed to always have matching + // first/last characters. + if (arg.length < 2 || arg.charAt(0) !== arg.slice(-1)) { + throw new ParseError(`\\verb assertion failed -- + please report what input caused this bug`); + } + arg = arg.slice(1, -1); // remove first and last char + return { + type: "verb", + mode: "text", + body: arg, + star, + }; + } + // At this point, we should have a symbol, possibly with accents. + // First expand any accented base symbol according to unicodeSymbols. + if (unicodeSymbols.hasOwnProperty(text[0]) && + !symbols[this.mode][text[0]]) { + // This behavior is not strict (XeTeX-compatible) in math mode. + if (this.settings.strict && this.mode === "math") { + this.settings.reportNonstrict("unicodeTextInMathMode", + `Accented Unicode text character "${text[0]}" used in ` + + `math mode`, nucleus); + } + text = unicodeSymbols[text[0]] + text.slice(1); + } + // Strip off any combining characters + const match = combiningDiacriticalMarksEndRegex.exec(text); + if (match) { + text = text.substring(0, match.index); + if (text === 'i') { + text = '\u0131'; // dotless i, in math and text mode + } else if (text === 'j') { + text = '\u0237'; // dotless j, in math and text mode + } + } + // Recognize base symbol + let symbol: AnyParseNode; + if (symbols[this.mode][text]) { + if (this.settings.strict && this.mode === 'math' && + extraLatin.indexOf(text) >= 0) { + this.settings.reportNonstrict("unicodeTextInMathMode", + `Latin-1/Unicode text character "${text[0]}" used in ` + + `math mode`, nucleus); + } + const group: Group = symbols[this.mode][text].group; + const loc = SourceLocation.range(nucleus); + let s: SymbolParseNode; + if (ATOMS.hasOwnProperty(group)) { + // $FlowFixMe + const family: Atom = group; + s = { + type: "atom", + mode: this.mode, + family, + loc, + text, + }; + } else { + // $FlowFixMe + s = { + type: group, + mode: this.mode, + loc, + text, + }; + } + // $FlowFixMe + symbol = s; + } else if (text.charCodeAt(0) >= 0x80) { // no symbol for e.g. ^ + if (this.settings.strict) { + if (!supportedCodepoint(text.charCodeAt(0))) { + this.settings.reportNonstrict("unknownSymbol", + `Unrecognized Unicode character "${text[0]}"` + + ` (${text.charCodeAt(0)})`, nucleus); + } else if (this.mode === "math") { + this.settings.reportNonstrict("unicodeTextInMathMode", + `Unicode text character "${text[0]}" used in math mode`, + nucleus); + } + } + // All nonmathematical Unicode characters are rendered as if they + // are in text mode (wrapped in \text) because that's what it + // takes to render them in LaTeX. Setting `mode: this.mode` is + // another natural choice (the user requested math mode), but + // this makes it more difficult for getCharacterMetrics() to + // distinguish Unicode characters without metrics and those for + // which we want to simulate the letter M. + symbol = { + type: "textord", + mode: "text", + loc: SourceLocation.range(nucleus), + text, + }; + } else { + return null; // EOF, ^, _, {, }, etc. + } + this.consume(); + // Transform combining characters into accents + if (match) { + for (let i = 0; i < match[0].length; i++) { + const accent: string = match[0][i]; + if (!unicodeAccents[accent]) { + throw new ParseError(`Unknown accent ' ${accent}'`, nucleus); + } + const command = unicodeAccents[accent][this.mode] || + unicodeAccents[accent].text; + if (!command) { + throw new ParseError( + `Accent ${accent} unsupported in ${this.mode} mode`, + nucleus); + } + symbol = { + type: "accent", + mode: this.mode, + loc: SourceLocation.range(nucleus), + label: command, + isStretchy: false, + isShifty: true, + // $FlowFixMe + base: symbol, + }; + } + } + // $FlowFixMe + return symbol; + } +} diff --git a/frontend/node_modules/katex/src/Settings.js b/frontend/node_modules/katex/src/Settings.js new file mode 100644 index 0000000..304a7d1 --- /dev/null +++ b/frontend/node_modules/katex/src/Settings.js @@ -0,0 +1,360 @@ +// @flow +/* eslint no-console:0 */ +/** + * This is a module for storing settings passed into KaTeX. It correctly handles + * default settings. + */ + +import utils from "./utils"; +import ParseError from "./ParseError"; +import {Token} from "./Token"; + +import type {AnyParseNode} from "./parseNode"; +import type {MacroMap} from "./defineMacro"; + +export type StrictFunction = + (errorCode: string, errorMsg: string, token?: Token | AnyParseNode) => + ?(boolean | string); + +export type TrustContextTypes = { + "\\href": {| + command: "\\href", + url: string, + protocol?: string, + |}, + "\\includegraphics": {| + command: "\\includegraphics", + url: string, + protocol?: string, + |}, + "\\url": {| + command: "\\url", + url: string, + protocol?: string, + |}, + "\\htmlClass": {| + command: "\\htmlClass", + class: string, + |}, + "\\htmlId": {| + command: "\\htmlId", + id: string, + |}, + "\\htmlStyle": {| + command: "\\htmlStyle", + style: string, + |}, + "\\htmlData": {| + command: "\\htmlData", + attributes: {[string]: string}, + |}, +}; +export type AnyTrustContext = $Values; +export type TrustFunction = (context: AnyTrustContext) => ?boolean; + +export type SettingsOptions = $Shape; + +type EnumType = {| enum: string[] |}; +type Type = "boolean" | "string" | "number" | "object" | "function" | EnumType; +type Schema = { + [$Keys]: { + /** + * Allowed type(s) of the value. + */ + type: Type | Type[]; + /** + * The default value. If not specified, false for boolean, an empty string + * for string, 0 for number, an empty object for object, or the first item + * for enum will be used. If multiple types are allowed, the first allowed + * type will be used for determining the default value. + */ + default?: any; + /** + * The description. + */ + description?: string; + /** + * The function to process the option. + */ + processor?: (any) => any, + /** + * The command line argument. See Commander.js docs for more information. + * If not specified, the name prefixed with -- will be used. Set false not + * to add to the CLI. + */ + cli?: string | false; + /** + * The default value for the CLI. + */ + cliDefault?: any; + /** + * The description for the CLI. If not specified, the description for the + * option will be used. + */ + cliDescription?: string; + /** + * The custom argument processor for the CLI. See Commander.js docs for + * more information. + */ + cliProcessor?: (any, any) => any; + }; +}; + +// TODO: automatically generate documentation +// TODO: check all properties on Settings exist +// TODO: check the type of a property on Settings matches +export const SETTINGS_SCHEMA: Schema = { + displayMode: { + type: "boolean", + description: "Render math in display mode, which puts the math in " + + "display style (so \\int and \\sum are large, for example), and " + + "centers the math on the page on its own line.", + cli: "-d, --display-mode", + }, + output: { + type: {enum: ["htmlAndMathml", "html", "mathml"]}, + description: "Determines the markup language of the output.", + cli: "-F, --format ", + }, + leqno: { + type: "boolean", + description: "Render display math in leqno style (left-justified tags).", + }, + fleqn: { + type: "boolean", + description: "Render display math flush left.", + }, + throwOnError: { + type: "boolean", + default: true, + cli: "-t, --no-throw-on-error", + cliDescription: "Render errors (in the color given by --error-color) ins" + + "tead of throwing a ParseError exception when encountering an error.", + }, + errorColor: { + type: "string", + default: "#cc0000", + cli: "-c, --error-color ", + cliDescription: "A color string given in the format 'rgb' or 'rrggbb' " + + "(no #). This option determines the color of errors rendered by the " + + "-t option.", + cliProcessor: (color) => "#" + color, + }, + macros: { + type: "object", + cli: "-m, --macro ", + cliDescription: "Define custom macro of the form '\\foo:expansion' (use " + + "multiple -m arguments for multiple macros).", + cliDefault: [], + cliProcessor: (def, defs) => { + defs.push(def); + return defs; + }, + }, + minRuleThickness: { + type: "number", + description: "Specifies a minimum thickness, in ems, for fraction lines," + + " `\\sqrt` top lines, `{array}` vertical lines, `\\hline`, " + + "`\\hdashline`, `\\underline`, `\\overline`, and the borders of " + + "`\\fbox`, `\\boxed`, and `\\fcolorbox`.", + processor: (t) => Math.max(0, t), + cli: "--min-rule-thickness ", + cliProcessor: parseFloat, + }, + colorIsTextColor: { + type: "boolean", + description: "Makes \\color behave like LaTeX's 2-argument \\textcolor, " + + "instead of LaTeX's one-argument \\color mode change.", + cli: "-b, --color-is-text-color", + }, + strict: { + type: [{enum: ["warn", "ignore", "error"]}, "boolean", "function"], + description: "Turn on strict / LaTeX faithfulness mode, which throws an " + + "error if the input uses features that are not supported by LaTeX.", + cli: "-S, --strict", + cliDefault: false, + }, + trust: { + type: ["boolean", "function"], + description: "Trust the input, enabling all HTML features such as \\url.", + cli: "-T, --trust", + }, + maxSize: { + type: "number", + default: Infinity, + description: "If non-zero, all user-specified sizes, e.g. in " + + "\\rule{500em}{500em}, will be capped to maxSize ems. Otherwise, " + + "elements and spaces can be arbitrarily large", + processor: (s) => Math.max(0, s), + cli: "-s, --max-size ", + cliProcessor: parseInt, + }, + maxExpand: { + type: "number", + default: 1000, + description: "Limit the number of macro expansions to the specified " + + "number, to prevent e.g. infinite macro loops. If set to Infinity, " + + "the macro expander will try to fully expand as in LaTeX.", + processor: (n) => Math.max(0, n), + cli: "-e, --max-expand ", + cliProcessor: (n) => (n === "Infinity" ? Infinity : parseInt(n)), + }, + globalGroup: { + type: "boolean", + cli: false, + }, +}; + +function getDefaultValue(schema): any { + if (schema.default) { + return schema.default; + } + const type = schema.type; + const defaultType = Array.isArray(type) ? type[0] : type; + if (typeof defaultType !== 'string') { + return defaultType.enum[0]; + } + switch (defaultType) { + case 'boolean': + return false; + case 'string': + return ''; + case 'number': + return 0; + case 'object': + return {}; + } +} + +/** + * The main Settings object + * + * The current options stored are: + * - displayMode: Whether the expression should be typeset as inline math + * (false, the default), meaning that the math starts in + * \textstyle and is placed in an inline-block); or as display + * math (true), meaning that the math starts in \displaystyle + * and is placed in a block with vertical margin. + */ +export default class Settings { + displayMode: boolean; + output: "html" | "mathml" | "htmlAndMathml"; + leqno: boolean; + fleqn: boolean; + throwOnError: boolean; + errorColor: string; + macros: MacroMap; + minRuleThickness: number; + colorIsTextColor: boolean; + strict: boolean | "ignore" | "warn" | "error" | StrictFunction; + trust: boolean | TrustFunction; + maxSize: number; + maxExpand: number; + globalGroup: boolean; + + constructor(options: SettingsOptions) { + // allow null options + options = options || {}; + for (const prop in SETTINGS_SCHEMA) { + if (SETTINGS_SCHEMA.hasOwnProperty(prop)) { + // $FlowFixMe + const schema = SETTINGS_SCHEMA[prop]; + // TODO: validate options + // $FlowFixMe + this[prop] = options[prop] !== undefined ? (schema.processor + ? schema.processor(options[prop]) : options[prop]) + : getDefaultValue(schema); + } + } + } + + /** + * Report nonstrict (non-LaTeX-compatible) input. + * Can safely not be called if `this.strict` is false in JavaScript. + */ + reportNonstrict(errorCode: string, errorMsg: string, + token?: Token | AnyParseNode) { + let strict = this.strict; + if (typeof strict === "function") { + // Allow return value of strict function to be boolean or string + // (or null/undefined, meaning no further processing). + strict = strict(errorCode, errorMsg, token); + } + if (!strict || strict === "ignore") { + return; + } else if (strict === true || strict === "error") { + throw new ParseError( + "LaTeX-incompatible input and strict mode is set to 'error': " + + `${errorMsg} [${errorCode}]`, token); + } else if (strict === "warn") { + typeof console !== "undefined" && console.warn( + "LaTeX-incompatible input and strict mode is set to 'warn': " + + `${errorMsg} [${errorCode}]`); + } else { // won't happen in type-safe code + typeof console !== "undefined" && console.warn( + "LaTeX-incompatible input and strict mode is set to " + + `unrecognized '${strict}': ${errorMsg} [${errorCode}]`); + } + } + + /** + * Check whether to apply strict (LaTeX-adhering) behavior for unusual + * input (like `\\`). Unlike `nonstrict`, will not throw an error; + * instead, "error" translates to a return value of `true`, while "ignore" + * translates to a return value of `false`. May still print a warning: + * "warn" prints a warning and returns `false`. + * This is for the second category of `errorCode`s listed in the README. + */ + useStrictBehavior(errorCode: string, errorMsg: string, + token?: Token | AnyParseNode): boolean { + let strict = this.strict; + if (typeof strict === "function") { + // Allow return value of strict function to be boolean or string + // (or null/undefined, meaning no further processing). + // But catch any exceptions thrown by function, treating them + // like "error". + try { + strict = strict(errorCode, errorMsg, token); + } catch (error) { + strict = "error"; + } + } + if (!strict || strict === "ignore") { + return false; + } else if (strict === true || strict === "error") { + return true; + } else if (strict === "warn") { + typeof console !== "undefined" && console.warn( + "LaTeX-incompatible input and strict mode is set to 'warn': " + + `${errorMsg} [${errorCode}]`); + return false; + } else { // won't happen in type-safe code + typeof console !== "undefined" && console.warn( + "LaTeX-incompatible input and strict mode is set to " + + `unrecognized '${strict}': ${errorMsg} [${errorCode}]`); + return false; + } + } + + /** + * Check whether to test potentially dangerous input, and return + * `true` (trusted) or `false` (untrusted). The sole argument `context` + * should be an object with `command` field specifying the relevant LaTeX + * command (as a string starting with `\`), and any other arguments, etc. + * If `context` has a `url` field, a `protocol` field will automatically + * get added by this function (changing the specified object). + */ + isTrusted(context: AnyTrustContext): boolean { + if (context.url && !context.protocol) { + const protocol = utils.protocolFromUrl(context.url); + if (protocol == null) { + return false; + } + context.protocol = protocol; + } + const trust = typeof this.trust === "function" + ? this.trust(context) + : this.trust; + return Boolean(trust); + } +} diff --git a/frontend/node_modules/katex/src/SourceLocation.js b/frontend/node_modules/katex/src/SourceLocation.js new file mode 100644 index 0000000..6fb74b6 --- /dev/null +++ b/frontend/node_modules/katex/src/SourceLocation.js @@ -0,0 +1,42 @@ +// @flow +import type {LexerInterface} from "./Token"; + +/** + * Lexing or parsing positional information for error reporting. + * This object is immutable. + */ +export default class SourceLocation { + // The + prefix indicates that these fields aren't writeable + +lexer: LexerInterface; // Lexer holding the input string. + +start: number; // Start offset, zero-based inclusive. + +end: number; // End offset, zero-based exclusive. + + constructor(lexer: LexerInterface, start: number, end: number) { + this.lexer = lexer; + this.start = start; + this.end = end; + } + + /** + * Merges two `SourceLocation`s from location providers, given they are + * provided in order of appearance. + * - Returns the first one's location if only the first is provided. + * - Returns a merged range of the first and the last if both are provided + * and their lexers match. + * - Otherwise, returns null. + */ + static range( + first?: {loc: ?SourceLocation}, + second?: {loc: ?SourceLocation}, + ): ?SourceLocation { + if (!second) { + return first && first.loc; + } else if (!first || !first.loc || !second.loc || + first.loc.lexer !== second.loc.lexer) { + return null; + } else { + return new SourceLocation( + first.loc.lexer, first.loc.start, second.loc.end); + } + } +} diff --git a/frontend/node_modules/katex/src/Style.js b/frontend/node_modules/katex/src/Style.js new file mode 100644 index 0000000..b77d645 --- /dev/null +++ b/frontend/node_modules/katex/src/Style.js @@ -0,0 +1,130 @@ +// @flow +/** + * This file contains information and classes for the various kinds of styles + * used in TeX. It provides a generic `Style` class, which holds information + * about a specific style. It then provides instances of all the different kinds + * of styles possible, and provides functions to move between them and get + * information about them. + */ + +/** + * The main style class. Contains a unique id for the style, a size (which is + * the same for cramped and uncramped version of a style), and a cramped flag. + */ +class Style implements StyleInterface { + id: number; + size: number; + cramped: boolean; + + constructor(id: number, size: number, cramped: boolean) { + this.id = id; + this.size = size; + this.cramped = cramped; + } + + /** + * Get the style of a superscript given a base in the current style. + */ + sup(): Style { + return styles[sup[this.id]]; + } + + /** + * Get the style of a subscript given a base in the current style. + */ + sub(): Style { + return styles[sub[this.id]]; + } + + /** + * Get the style of a fraction numerator given the fraction in the current + * style. + */ + fracNum(): Style { + return styles[fracNum[this.id]]; + } + + /** + * Get the style of a fraction denominator given the fraction in the current + * style. + */ + fracDen(): Style { + return styles[fracDen[this.id]]; + } + + /** + * Get the cramped version of a style (in particular, cramping a cramped style + * doesn't change the style). + */ + cramp(): Style { + return styles[cramp[this.id]]; + } + + /** + * Get a text or display version of this style. + */ + text(): Style { + return styles[text[this.id]]; + } + + /** + * Return true if this style is tightly spaced (scriptstyle/scriptscriptstyle) + */ + isTight(): boolean { + return this.size >= 2; + } +} + +// Export an interface for type checking, but don't expose the implementation. +// This way, no more styles can be generated. +export interface StyleInterface { + id: number; + size: number; + cramped: boolean; + + sup(): StyleInterface; + sub(): StyleInterface; + fracNum(): StyleInterface; + fracDen(): StyleInterface; + cramp(): StyleInterface; + text(): StyleInterface; + isTight(): boolean; +} + +// IDs of the different styles +const D = 0; +const Dc = 1; +const T = 2; +const Tc = 3; +const S = 4; +const Sc = 5; +const SS = 6; +const SSc = 7; + +// Instances of the different styles +const styles = [ + new Style(D, 0, false), + new Style(Dc, 0, true), + new Style(T, 1, false), + new Style(Tc, 1, true), + new Style(S, 2, false), + new Style(Sc, 2, true), + new Style(SS, 3, false), + new Style(SSc, 3, true), +]; + +// Lookup tables for switching from one style to another +const sup = [S, Sc, S, Sc, SS, SSc, SS, SSc]; +const sub = [Sc, Sc, Sc, Sc, SSc, SSc, SSc, SSc]; +const fracNum = [T, Tc, S, Sc, SS, SSc, SS, SSc]; +const fracDen = [Tc, Tc, Sc, Sc, SSc, SSc, SSc, SSc]; +const cramp = [Dc, Dc, Tc, Tc, Sc, Sc, SSc, SSc]; +const text = [D, Dc, T, Tc, T, Tc, T, Tc]; + +// We only export some of the styles. +export default { + DISPLAY: (styles[D]: Style), + TEXT: (styles[T]: Style), + SCRIPT: (styles[S]: Style), + SCRIPTSCRIPT: (styles[SS]: Style), +}; diff --git a/frontend/node_modules/katex/src/Token.js b/frontend/node_modules/katex/src/Token.js new file mode 100644 index 0000000..2a84b4e --- /dev/null +++ b/frontend/node_modules/katex/src/Token.js @@ -0,0 +1,47 @@ +// @flow +import SourceLocation from "./SourceLocation"; + +/** + * Interface required to break circular dependency between Token, Lexer, and + * ParseError. + */ +export interface LexerInterface {input: string, tokenRegex: RegExp} + +/** + * The resulting token returned from `lex`. + * + * It consists of the token text plus some position information. + * The position information is essentially a range in an input string, + * but instead of referencing the bare input string, we refer to the lexer. + * That way it is possible to attach extra metadata to the input string, + * like for example a file name or similar. + * + * The position information is optional, so it is OK to construct synthetic + * tokens if appropriate. Not providing available position information may + * lead to degraded error reporting, though. + */ +export class Token { + text: string; + loc: ?SourceLocation; + noexpand: ?boolean; // don't expand the token + treatAsRelax: ?boolean; // used in \noexpand + + constructor( + text: string, // the text of this token + loc: ?SourceLocation, + ) { + this.text = text; + this.loc = loc; + } + + /** + * Given a pair of tokens (this and endToken), compute a `Token` encompassing + * the whole input range enclosed by these two. + */ + range( + endToken: Token, // last token of the range, inclusive + text: string, // the text of the newly constructed token + ): Token { + return new Token(text, SourceLocation.range(this, endToken)); + } +} diff --git a/frontend/node_modules/katex/src/buildCommon.js b/frontend/node_modules/katex/src/buildCommon.js new file mode 100644 index 0000000..8902933 --- /dev/null +++ b/frontend/node_modules/katex/src/buildCommon.js @@ -0,0 +1,784 @@ +// @flow +/* eslint no-console:0 */ +/** + * This module contains general functions that can be used for building + * different kinds of domTree nodes in a consistent manner. + */ + +import {SymbolNode, Anchor, Span, PathNode, SvgNode, createClass} from "./domTree"; +import {getCharacterMetrics} from "./fontMetrics"; +import symbols, {ligatures} from "./symbols"; +import {wideCharacterFont} from "./wide-character"; +import {calculateSize, makeEm} from "./units"; +import {DocumentFragment} from "./tree"; + +import type Options from "./Options"; +import type {ParseNode} from "./parseNode"; +import type {CharacterMetrics} from "./fontMetrics"; +import type {FontVariant, Mode} from "./types"; +import type {documentFragment as HtmlDocumentFragment} from "./domTree"; +import type {HtmlDomNode, DomSpan, SvgSpan, CssStyle} from "./domTree"; +import type {Measurement} from "./units"; + +/** + * Looks up the given symbol in fontMetrics, after applying any symbol + * replacements defined in symbol.js + */ +const lookupSymbol = function( + value: string, + // TODO(#963): Use a union type for this. + fontName: string, + mode: Mode, +): {value: string, metrics: ?CharacterMetrics} { + // Replace the value with its replaced value from symbol.js + if (symbols[mode][value] && symbols[mode][value].replace) { + value = symbols[mode][value].replace; + } + return { + value: value, + metrics: getCharacterMetrics(value, fontName, mode), + }; +}; + +/** + * Makes a symbolNode after translation via the list of symbols in symbols.js. + * Correctly pulls out metrics for the character, and optionally takes a list of + * classes to be attached to the node. + * + * TODO: make argument order closer to makeSpan + * TODO: add a separate argument for math class (e.g. `mop`, `mbin`), which + * should if present come first in `classes`. + * TODO(#953): Make `options` mandatory and always pass it in. + */ +const makeSymbol = function( + value: string, + fontName: string, + mode: Mode, + options?: Options, + classes?: string[], +): SymbolNode { + const lookup = lookupSymbol(value, fontName, mode); + const metrics = lookup.metrics; + value = lookup.value; + + let symbolNode; + if (metrics) { + let italic = metrics.italic; + if (mode === "text" || (options && options.font === "mathit")) { + italic = 0; + } + symbolNode = new SymbolNode( + value, metrics.height, metrics.depth, italic, metrics.skew, + metrics.width, classes); + } else { + // TODO(emily): Figure out a good way to only print this in development + typeof console !== "undefined" && console.warn("No character metrics " + + `for '${value}' in style '${fontName}' and mode '${mode}'`); + symbolNode = new SymbolNode(value, 0, 0, 0, 0, 0, classes); + } + + if (options) { + symbolNode.maxFontSize = options.sizeMultiplier; + if (options.style.isTight()) { + symbolNode.classes.push("mtight"); + } + const color = options.getColor(); + if (color) { + symbolNode.style.color = color; + } + } + + return symbolNode; +}; + +/** + * Makes a symbol in Main-Regular or AMS-Regular. + * Used for rel, bin, open, close, inner, and punct. + */ +const mathsym = function( + value: string, + mode: Mode, + options: Options, + classes?: string[] = [], +): SymbolNode { + // Decide what font to render the symbol in by its entry in the symbols + // table. + // Have a special case for when the value = \ because the \ is used as a + // textord in unsupported command errors but cannot be parsed as a regular + // text ordinal and is therefore not present as a symbol in the symbols + // table for text, as well as a special case for boldsymbol because it + // can be used for bold + and - + if (options.font === "boldsymbol" && + lookupSymbol(value, "Main-Bold", mode).metrics) { + return makeSymbol(value, "Main-Bold", mode, options, + classes.concat(["mathbf"])); + } else if (value === "\\" || symbols[mode][value].font === "main") { + return makeSymbol(value, "Main-Regular", mode, options, classes); + } else { + return makeSymbol( + value, "AMS-Regular", mode, options, classes.concat(["amsrm"])); + } +}; + +/** + * Determines which of the two font names (Main-Bold and Math-BoldItalic) and + * corresponding style tags (mathbf or boldsymbol) to use for font "boldsymbol", + * depending on the symbol. Use this function instead of fontMap for font + * "boldsymbol". + */ +const boldsymbol = function( + value: string, + mode: Mode, + options: Options, + classes: string[], + type: "mathord" | "textord", +): {| fontName: string, fontClass: string |} { + if (type !== "textord" && + lookupSymbol(value, "Math-BoldItalic", mode).metrics) { + return { + fontName: "Math-BoldItalic", + fontClass: "boldsymbol", + }; + } else { + // Some glyphs do not exist in Math-BoldItalic so we need to use + // Main-Bold instead. + return { + fontName: "Main-Bold", + fontClass: "mathbf", + }; + } +}; + +/** + * Makes either a mathord or textord in the correct font and color. + */ +const makeOrd = function( + group: ParseNode, + options: Options, + type: "mathord" | "textord", +): HtmlDocumentFragment | SymbolNode { + const mode = group.mode; + const text = group.text; + + const classes = ["mord"]; + + // Math mode or Old font (i.e. \rm) + const isFont = mode === "math" || (mode === "text" && options.font); + const fontOrFamily = isFont ? options.font : options.fontFamily; + let wideFontName = ""; + let wideFontClass = ""; + if (text.charCodeAt(0) === 0xD835) { + [wideFontName, wideFontClass] = wideCharacterFont(text, mode); + } + if (wideFontName.length > 0) { + // surrogate pairs get special treatment + return makeSymbol(text, wideFontName, mode, options, + classes.concat(wideFontClass)); + } else if (fontOrFamily) { + let fontName; + let fontClasses; + if (fontOrFamily === "boldsymbol") { + const fontData = boldsymbol(text, mode, options, classes, type); + fontName = fontData.fontName; + fontClasses = [fontData.fontClass]; + } else if (isFont) { + fontName = fontMap[fontOrFamily].fontName; + fontClasses = [fontOrFamily]; + } else { + fontName = retrieveTextFontName(fontOrFamily, options.fontWeight, + options.fontShape); + fontClasses = [fontOrFamily, options.fontWeight, options.fontShape]; + } + + if (lookupSymbol(text, fontName, mode).metrics) { + return makeSymbol(text, fontName, mode, options, + classes.concat(fontClasses)); + } else if (ligatures.hasOwnProperty(text) && + fontName.slice(0, 10) === "Typewriter") { + // Deconstruct ligatures in monospace fonts (\texttt, \tt). + const parts = []; + for (let i = 0; i < text.length; i++) { + parts.push(makeSymbol(text[i], fontName, mode, options, + classes.concat(fontClasses))); + } + return makeFragment(parts); + } + } + + // Makes a symbol in the default font for mathords and textords. + if (type === "mathord") { + return makeSymbol(text, "Math-Italic", mode, options, + classes.concat(["mathnormal"])); + } else if (type === "textord") { + const font = symbols[mode][text] && symbols[mode][text].font; + if (font === "ams") { + const fontName = retrieveTextFontName("amsrm", options.fontWeight, + options.fontShape); + return makeSymbol( + text, fontName, mode, options, + classes.concat("amsrm", options.fontWeight, options.fontShape)); + } else if (font === "main" || !font) { + const fontName = retrieveTextFontName("textrm", options.fontWeight, + options.fontShape); + return makeSymbol( + text, fontName, mode, options, + classes.concat(options.fontWeight, options.fontShape)); + } else { // fonts added by plugins + const fontName = retrieveTextFontName(font, options.fontWeight, + options.fontShape); + // We add font name as a css class + return makeSymbol( + text, fontName, mode, options, + classes.concat(fontName, options.fontWeight, options.fontShape)); + } + } else { + throw new Error("unexpected type: " + type + " in makeOrd"); + } +}; + +/** + * Returns true if subsequent symbolNodes have the same classes, skew, maxFont, + * and styles. + */ +const canCombine = (prev: SymbolNode, next: SymbolNode) => { + if (createClass(prev.classes) !== createClass(next.classes) + || prev.skew !== next.skew + || prev.maxFontSize !== next.maxFontSize) { + return false; + } + + // If prev and next both are just "mbin"s or "mord"s we don't combine them + // so that the proper spacing can be preserved. + if (prev.classes.length === 1) { + const cls = prev.classes[0]; + if (cls === "mbin" || cls === "mord") { + return false; + } + } + + for (const style in prev.style) { + if (prev.style.hasOwnProperty(style) + && prev.style[style] !== next.style[style]) { + return false; + } + } + + for (const style in next.style) { + if (next.style.hasOwnProperty(style) + && prev.style[style] !== next.style[style]) { + return false; + } + } + + return true; +}; + +/** + * Combine consecutive domTree.symbolNodes into a single symbolNode. + * Note: this function mutates the argument. + */ +const tryCombineChars = (chars: HtmlDomNode[]): HtmlDomNode[] => { + for (let i = 0; i < chars.length - 1; i++) { + const prev = chars[i]; + const next = chars[i + 1]; + if (prev instanceof SymbolNode + && next instanceof SymbolNode + && canCombine(prev, next)) { + + prev.text += next.text; + prev.height = Math.max(prev.height, next.height); + prev.depth = Math.max(prev.depth, next.depth); + // Use the last character's italic correction since we use + // it to add padding to the right of the span created from + // the combined characters. + prev.italic = next.italic; + chars.splice(i + 1, 1); + i--; + } + } + return chars; +}; + +/** + * Calculate the height, depth, and maxFontSize of an element based on its + * children. + */ +const sizeElementFromChildren = function( + elem: DomSpan | Anchor | HtmlDocumentFragment, +) { + let height = 0; + let depth = 0; + let maxFontSize = 0; + + for (let i = 0; i < elem.children.length; i++) { + const child = elem.children[i]; + if (child.height > height) { + height = child.height; + } + if (child.depth > depth) { + depth = child.depth; + } + if (child.maxFontSize > maxFontSize) { + maxFontSize = child.maxFontSize; + } + } + + elem.height = height; + elem.depth = depth; + elem.maxFontSize = maxFontSize; +}; + +/** + * Makes a span with the given list of classes, list of children, and options. + * + * TODO(#953): Ensure that `options` is always provided (currently some call + * sites don't pass it) and make the type below mandatory. + * TODO: add a separate argument for math class (e.g. `mop`, `mbin`), which + * should if present come first in `classes`. + */ +const makeSpan = function( + classes?: string[], + children?: HtmlDomNode[], + options?: Options, + style?: CssStyle, +): DomSpan { + const span = new Span(classes, children, options, style); + + sizeElementFromChildren(span); + + return span; +}; + +// SVG one is simpler -- doesn't require height, depth, max-font setting. +// This is also a separate method for typesafety. +const makeSvgSpan = ( + classes?: string[], + children?: SvgNode[], + options?: Options, + style?: CssStyle, +): SvgSpan => new Span(classes, children, options, style); + +const makeLineSpan = function( + className: string, + options: Options, + thickness?: number, +): DomSpan { + const line = makeSpan([className], [], options); + line.height = Math.max( + thickness || options.fontMetrics().defaultRuleThickness, + options.minRuleThickness, + ); + line.style.borderBottomWidth = makeEm(line.height); + line.maxFontSize = 1.0; + return line; +}; + +/** + * Makes an anchor with the given href, list of classes, list of children, + * and options. + */ +const makeAnchor = function( + href: string, + classes: string[], + children: HtmlDomNode[], + options: Options, +): Anchor { + const anchor = new Anchor(href, classes, children, options); + + sizeElementFromChildren(anchor); + + return anchor; +}; + +/** + * Makes a document fragment with the given list of children. + */ +const makeFragment = function( + children: HtmlDomNode[], +): HtmlDocumentFragment { + const fragment = new DocumentFragment(children); + + sizeElementFromChildren(fragment); + + return fragment; +}; + +/** + * Wraps group in a span if it's a document fragment, allowing to apply classes + * and styles + */ +const wrapFragment = function( + group: HtmlDomNode, + options: Options, +): HtmlDomNode { + if (group instanceof DocumentFragment) { + return makeSpan([], [group], options); + } + return group; +}; + + +// These are exact object types to catch typos in the names of the optional fields. +export type VListElem = {| + type: "elem", + elem: HtmlDomNode, + marginLeft?: ?string, + marginRight?: string, + wrapperClasses?: string[], + wrapperStyle?: CssStyle, +|}; +type VListElemAndShift = {| + type: "elem", + elem: HtmlDomNode, + shift: number, + marginLeft?: ?string, + marginRight?: string, + wrapperClasses?: string[], + wrapperStyle?: CssStyle, +|}; +type VListKern = {| type: "kern", size: number |}; + +// A list of child or kern nodes to be stacked on top of each other (i.e. the +// first element will be at the bottom, and the last at the top). +type VListChild = VListElem | VListKern; + +type VListParam = {| + // Each child contains how much it should be shifted downward. + positionType: "individualShift", + children: VListElemAndShift[], +|} | {| + // "top": The positionData specifies the topmost point of the vlist (note this + // is expected to be a height, so positive values move up). + // "bottom": The positionData specifies the bottommost point of the vlist (note + // this is expected to be a depth, so positive values move down). + // "shift": The vlist will be positioned such that its baseline is positionData + // away from the baseline of the first child which MUST be an + // "elem". Positive values move downwards. + positionType: "top" | "bottom" | "shift", + positionData: number, + children: VListChild[], +|} | {| + // The vlist is positioned so that its baseline is aligned with the baseline + // of the first child which MUST be an "elem". This is equivalent to "shift" + // with positionData=0. + positionType: "firstBaseline", + children: VListChild[], +|}; + + +// Computes the updated `children` list and the overall depth. +// +// This helper function for makeVList makes it easier to enforce type safety by +// allowing early exits (returns) in the logic. +const getVListChildrenAndDepth = function(params: VListParam): { + children: (VListChild | VListElemAndShift)[] | VListChild[], + depth: number, +} { + if (params.positionType === "individualShift") { + const oldChildren = params.children; + const children: (VListChild | VListElemAndShift)[] = [oldChildren[0]]; + + // Add in kerns to the list of params.children to get each element to be + // shifted to the correct specified shift + const depth = -oldChildren[0].shift - oldChildren[0].elem.depth; + let currPos = depth; + for (let i = 1; i < oldChildren.length; i++) { + const diff = -oldChildren[i].shift - currPos - + oldChildren[i].elem.depth; + const size = diff - + (oldChildren[i - 1].elem.height + + oldChildren[i - 1].elem.depth); + + currPos = currPos + diff; + + children.push({type: "kern", size}); + children.push(oldChildren[i]); + } + + return {children, depth}; + } + + let depth; + if (params.positionType === "top") { + // We always start at the bottom, so calculate the bottom by adding up + // all the sizes + let bottom = params.positionData; + for (let i = 0; i < params.children.length; i++) { + const child = params.children[i]; + bottom -= child.type === "kern" + ? child.size + : child.elem.height + child.elem.depth; + } + depth = bottom; + } else if (params.positionType === "bottom") { + depth = -params.positionData; + } else { + const firstChild = params.children[0]; + if (firstChild.type !== "elem") { + throw new Error('First child must have type "elem".'); + } + if (params.positionType === "shift") { + depth = -firstChild.elem.depth - params.positionData; + } else if (params.positionType === "firstBaseline") { + depth = -firstChild.elem.depth; + } else { + throw new Error(`Invalid positionType ${params.positionType}.`); + } + } + return {children: params.children, depth}; +}; + +/** + * Makes a vertical list by stacking elements and kerns on top of each other. + * Allows for many different ways of specifying the positioning method. + * + * See VListParam documentation above. + */ +const makeVList = function(params: VListParam, options: Options): DomSpan { + const {children, depth} = getVListChildrenAndDepth(params); + + // Create a strut that is taller than any list item. The strut is added to + // each item, where it will determine the item's baseline. Since it has + // `overflow:hidden`, the strut's top edge will sit on the item's line box's + // top edge and the strut's bottom edge will sit on the item's baseline, + // with no additional line-height spacing. This allows the item baseline to + // be positioned precisely without worrying about font ascent and + // line-height. + let pstrutSize = 0; + for (let i = 0; i < children.length; i++) { + const child = children[i]; + if (child.type === "elem") { + const elem = child.elem; + pstrutSize = Math.max(pstrutSize, elem.maxFontSize, elem.height); + } + } + pstrutSize += 2; + const pstrut = makeSpan(["pstrut"], []); + pstrut.style.height = makeEm(pstrutSize); + + // Create a new list of actual children at the correct offsets + const realChildren = []; + let minPos = depth; + let maxPos = depth; + let currPos = depth; + for (let i = 0; i < children.length; i++) { + const child = children[i]; + if (child.type === "kern") { + currPos += child.size; + } else { + const elem = child.elem; + const classes = child.wrapperClasses || []; + const style = child.wrapperStyle || {}; + + const childWrap = makeSpan(classes, [pstrut, elem], undefined, style); + childWrap.style.top = makeEm(-pstrutSize - currPos - elem.depth); + if (child.marginLeft) { + childWrap.style.marginLeft = child.marginLeft; + } + if (child.marginRight) { + childWrap.style.marginRight = child.marginRight; + } + + realChildren.push(childWrap); + currPos += elem.height + elem.depth; + } + minPos = Math.min(minPos, currPos); + maxPos = Math.max(maxPos, currPos); + } + + // The vlist contents go in a table-cell with `vertical-align:bottom`. + // This cell's bottom edge will determine the containing table's baseline + // without overly expanding the containing line-box. + const vlist = makeSpan(["vlist"], realChildren); + vlist.style.height = makeEm(maxPos); + + // A second row is used if necessary to represent the vlist's depth. + let rows; + if (minPos < 0) { + // We will define depth in an empty span with display: table-cell. + // It should render with the height that we define. But Chrome, in + // contenteditable mode only, treats that span as if it contains some + // text content. And that min-height over-rides our desired height. + // So we put another empty span inside the depth strut span. + const emptySpan = makeSpan([], []); + const depthStrut = makeSpan(["vlist"], [emptySpan]); + depthStrut.style.height = makeEm(-minPos); + + // Safari wants the first row to have inline content; otherwise it + // puts the bottom of the *second* row on the baseline. + const topStrut = makeSpan(["vlist-s"], [new SymbolNode("\u200b")]); + + rows = [makeSpan(["vlist-r"], [vlist, topStrut]), + makeSpan(["vlist-r"], [depthStrut])]; + } else { + rows = [makeSpan(["vlist-r"], [vlist])]; + } + + const vtable = makeSpan(["vlist-t"], rows); + if (rows.length === 2) { + vtable.classes.push("vlist-t2"); + } + vtable.height = maxPos; + vtable.depth = -minPos; + return vtable; +}; + +// Glue is a concept from TeX which is a flexible space between elements in +// either a vertical or horizontal list. In KaTeX, at least for now, it's +// static space between elements in a horizontal layout. +const makeGlue = (measurement: Measurement, options: Options): DomSpan => { + // Make an empty span for the space + const rule = makeSpan(["mspace"], [], options); + const size = calculateSize(measurement, options); + rule.style.marginRight = makeEm(size); + return rule; +}; + +// Takes font options, and returns the appropriate fontLookup name +const retrieveTextFontName = function( + fontFamily: string, + fontWeight: string, + fontShape: string, +): string { + let baseFontName = ""; + switch (fontFamily) { + case "amsrm": + baseFontName = "AMS"; + break; + case "textrm": + baseFontName = "Main"; + break; + case "textsf": + baseFontName = "SansSerif"; + break; + case "texttt": + baseFontName = "Typewriter"; + break; + default: + baseFontName = fontFamily; // use fonts added by a plugin + } + + let fontStylesName; + if (fontWeight === "textbf" && fontShape === "textit") { + fontStylesName = "BoldItalic"; + } else if (fontWeight === "textbf") { + fontStylesName = "Bold"; + } else if (fontWeight === "textit") { + fontStylesName = "Italic"; + } else { + fontStylesName = "Regular"; + } + + return `${baseFontName}-${fontStylesName}`; +}; + +/** + * Maps TeX font commands to objects containing: + * - variant: string used for "mathvariant" attribute in buildMathML.js + * - fontName: the "style" parameter to fontMetrics.getCharacterMetrics + */ +// A map between tex font commands an MathML mathvariant attribute values +const fontMap: {[string]: {| variant: FontVariant, fontName: string |}} = { + // styles + "mathbf": { + variant: "bold", + fontName: "Main-Bold", + }, + "mathrm": { + variant: "normal", + fontName: "Main-Regular", + }, + "textit": { + variant: "italic", + fontName: "Main-Italic", + }, + "mathit": { + variant: "italic", + fontName: "Main-Italic", + }, + "mathnormal": { + variant: "italic", + fontName: "Math-Italic", + }, + "mathsfit": { + variant: "sans-serif-italic", + fontName: "SansSerif-Italic", + }, + // "boldsymbol" is missing because they require the use of multiple fonts: + // Math-BoldItalic and Main-Bold. This is handled by a special case in + // makeOrd which ends up calling boldsymbol. + + // families + "mathbb": { + variant: "double-struck", + fontName: "AMS-Regular", + }, + "mathcal": { + variant: "script", + fontName: "Caligraphic-Regular", + }, + "mathfrak": { + variant: "fraktur", + fontName: "Fraktur-Regular", + }, + "mathscr": { + variant: "script", + fontName: "Script-Regular", + }, + "mathsf": { + variant: "sans-serif", + fontName: "SansSerif-Regular", + }, + "mathtt": { + variant: "monospace", + fontName: "Typewriter-Regular", + }, +}; + +const svgData: { + [string]: ([string, number, number]) +} = { + // path, width, height + vec: ["vec", 0.471, 0.714], // values from the font glyph + oiintSize1: ["oiintSize1", 0.957, 0.499], // oval to overlay the integrand + oiintSize2: ["oiintSize2", 1.472, 0.659], + oiiintSize1: ["oiiintSize1", 1.304, 0.499], + oiiintSize2: ["oiiintSize2", 1.98, 0.659], +}; + +const staticSvg = function(value: string, options: Options): SvgSpan { + // Create a span with inline SVG for the element. + const [pathName, width, height] = svgData[value]; + const path = new PathNode(pathName); + const svgNode = new SvgNode([path], { + "width": makeEm(width), + "height": makeEm(height), + // Override CSS rule `.katex svg { width: 100% }` + "style": "width:" + makeEm(width), + "viewBox": "0 0 " + 1000 * width + " " + 1000 * height, + "preserveAspectRatio": "xMinYMin", + }); + const span = makeSvgSpan(["overlay"], [svgNode], options); + span.height = height; + span.style.height = makeEm(height); + span.style.width = makeEm(width); + return span; +}; + +export default { + fontMap, + makeSymbol, + mathsym, + makeSpan, + makeSvgSpan, + makeLineSpan, + makeAnchor, + makeFragment, + wrapFragment, + makeVList, + makeOrd, + makeGlue, + staticSvg, + svgData, + tryCombineChars, +}; diff --git a/frontend/node_modules/katex/src/buildHTML.js b/frontend/node_modules/katex/src/buildHTML.js new file mode 100644 index 0000000..95cae23 --- /dev/null +++ b/frontend/node_modules/katex/src/buildHTML.js @@ -0,0 +1,406 @@ +// @flow +/** + * This file does the main work of building a domTree structure from a parse + * tree. The entry point is the `buildHTML` function, which takes a parse tree. + * Then, the buildExpression, buildGroup, and various groupBuilders functions + * are called, to produce a final HTML tree. + */ + +import ParseError from "./ParseError"; +import Style from "./Style"; +import buildCommon from "./buildCommon"; +import {Span, Anchor} from "./domTree"; +import utils from "./utils"; +import {makeEm} from "./units"; +import {spacings, tightSpacings} from "./spacingData"; +import {_htmlGroupBuilders as groupBuilders} from "./defineFunction"; +import {DocumentFragment} from "./tree"; + +import type Options from "./Options"; +import type {AnyParseNode} from "./parseNode"; +import type {HtmlDomNode, DomSpan} from "./domTree"; + +const makeSpan = buildCommon.makeSpan; + +// Binary atoms (first class `mbin`) change into ordinary atoms (`mord`) +// depending on their surroundings. See TeXbook pg. 442-446, Rules 5 and 6, +// and the text before Rule 19. +const binLeftCanceller = ["leftmost", "mbin", "mopen", "mrel", "mop", "mpunct"]; +const binRightCanceller = ["rightmost", "mrel", "mclose", "mpunct"]; + +const styleMap = { + "display": Style.DISPLAY, + "text": Style.TEXT, + "script": Style.SCRIPT, + "scriptscript": Style.SCRIPTSCRIPT, +}; + +type Side = "left" | "right"; + +const DomEnum = { + mord: "mord", + mop: "mop", + mbin: "mbin", + mrel: "mrel", + mopen: "mopen", + mclose: "mclose", + mpunct: "mpunct", + minner: "minner", +}; +type DomType = $Keys; + +/** + * Take a list of nodes, build them in order, and return a list of the built + * nodes. documentFragments are flattened into their contents, so the + * returned list contains no fragments. `isRealGroup` is true if `expression` + * is a real group (no atoms will be added on either side), as opposed to + * a partial group (e.g. one created by \color). `surrounding` is an array + * consisting type of nodes that will be added to the left and right. + */ +export const buildExpression = function( + expression: AnyParseNode[], + options: Options, + isRealGroup: boolean | "root", + surrounding: [?DomType, ?DomType] = [null, null], +): HtmlDomNode[] { + // Parse expressions into `groups`. + const groups: HtmlDomNode[] = []; + for (let i = 0; i < expression.length; i++) { + const output = buildGroup(expression[i], options); + if (output instanceof DocumentFragment) { + const children: $ReadOnlyArray = output.children; + groups.push(...children); + } else { + groups.push(output); + } + } + + // Combine consecutive domTree.symbolNodes into a single symbolNode. + buildCommon.tryCombineChars(groups); + + // If `expression` is a partial group, let the parent handle spacings + // to avoid processing groups multiple times. + if (!isRealGroup) { + return groups; + } + + let glueOptions = options; + if (expression.length === 1) { + const node = expression[0]; + if (node.type === "sizing") { + glueOptions = options.havingSize(node.size); + } else if (node.type === "styling") { + glueOptions = options.havingStyle(styleMap[node.style]); + } + } + + // Dummy spans for determining spacings between surrounding atoms. + // If `expression` has no atoms on the left or right, class "leftmost" + // or "rightmost", respectively, is used to indicate it. + const dummyPrev = makeSpan([surrounding[0] || "leftmost"], [], options); + const dummyNext = makeSpan([surrounding[1] || "rightmost"], [], options); + + // TODO: These code assumes that a node's math class is the first element + // of its `classes` array. A later cleanup should ensure this, for + // instance by changing the signature of `makeSpan`. + + // Before determining what spaces to insert, perform bin cancellation. + // Binary operators change to ordinary symbols in some contexts. + const isRoot = (isRealGroup === "root"); + traverseNonSpaceNodes(groups, (node, prev) => { + const prevType = prev.classes[0]; + const type = node.classes[0]; + if (prevType === "mbin" && utils.contains(binRightCanceller, type)) { + prev.classes[0] = "mord"; + } else if (type === "mbin" && utils.contains(binLeftCanceller, prevType)) { + node.classes[0] = "mord"; + } + }, {node: dummyPrev}, dummyNext, isRoot); + + traverseNonSpaceNodes(groups, (node, prev) => { + const prevType = getTypeOfDomTree(prev); + const type = getTypeOfDomTree(node); + + // 'mtight' indicates that the node is script or scriptscript style. + const space = prevType && type ? (node.hasClass("mtight") + ? tightSpacings[prevType][type] + : spacings[prevType][type]) : null; + if (space) { // Insert glue (spacing) after the `prev`. + return buildCommon.makeGlue(space, glueOptions); + } + }, {node: dummyPrev}, dummyNext, isRoot); + + return groups; +}; + +// Depth-first traverse non-space `nodes`, calling `callback` with the current and +// previous node as arguments, optionally returning a node to insert after the +// previous node. `prev` is an object with the previous node and `insertAfter` +// function to insert after it. `next` is a node that will be added to the right. +// Used for bin cancellation and inserting spacings. +const traverseNonSpaceNodes = function( + nodes: HtmlDomNode[], + callback: (HtmlDomNode, HtmlDomNode) => ?HtmlDomNode, + prev: {| + node: HtmlDomNode, + insertAfter?: HtmlDomNode => void, + |}, + next: ?HtmlDomNode, + isRoot: boolean, +) { + if (next) { // temporarily append the right node, if exists + nodes.push(next); + } + let i = 0; + for (; i < nodes.length; i++) { + const node = nodes[i]; + const partialGroup = checkPartialGroup(node); + if (partialGroup) { // Recursive DFS + // $FlowFixMe: make nodes a $ReadOnlyArray by returning a new array + traverseNonSpaceNodes(partialGroup.children, + callback, prev, null, isRoot); + continue; + } + + // Ignore explicit spaces (e.g., \;, \,) when determining what implicit + // spacing should go between atoms of different classes + const nonspace = !node.hasClass("mspace"); + if (nonspace) { + const result = callback(node, prev.node); + if (result) { + if (prev.insertAfter) { + prev.insertAfter(result); + } else { // insert at front + nodes.unshift(result); + i++; + } + } + } + + if (nonspace) { + prev.node = node; + } else if (isRoot && node.hasClass("newline")) { + prev.node = makeSpan(["leftmost"]); // treat like beginning of line + } + prev.insertAfter = (index => n => { + nodes.splice(index + 1, 0, n); + i++; + })(i); + } + if (next) { + nodes.pop(); + } +}; + +// Check if given node is a partial group, i.e., does not affect spacing around. +const checkPartialGroup = function( + node: HtmlDomNode, +): ?(DocumentFragment | Anchor | DomSpan) { + if (node instanceof DocumentFragment || node instanceof Anchor + || (node instanceof Span && node.hasClass("enclosing"))) { + return node; + } + return null; +}; + +// Return the outermost node of a domTree. +const getOutermostNode = function( + node: HtmlDomNode, + side: Side, +): HtmlDomNode { + const partialGroup = checkPartialGroup(node); + if (partialGroup) { + const children = partialGroup.children; + if (children.length) { + if (side === "right") { + return getOutermostNode(children[children.length - 1], "right"); + } else if (side === "left") { + return getOutermostNode(children[0], "left"); + } + } + } + return node; +}; + +// Return math atom class (mclass) of a domTree. +// If `side` is given, it will get the type of the outermost node at given side. +export const getTypeOfDomTree = function( + node: ?HtmlDomNode, + side: ?Side, +): ?DomType { + if (!node) { + return null; + } + if (side) { + node = getOutermostNode(node, side); + } + // This makes a lot of assumptions as to where the type of atom + // appears. We should do a better job of enforcing this. + return DomEnum[node.classes[0]] || null; +}; + +export const makeNullDelimiter = function( + options: Options, + classes: string[], +): DomSpan { + const moreClasses = ["nulldelimiter"].concat(options.baseSizingClasses()); + return makeSpan(classes.concat(moreClasses)); +}; + +/** + * buildGroup is the function that takes a group and calls the correct groupType + * function for it. It also handles the interaction of size and style changes + * between parents and children. + */ +export const buildGroup = function( + group: ?AnyParseNode, + options: Options, + baseOptions?: Options, +): HtmlDomNode { + if (!group) { + return makeSpan(); + } + + if (groupBuilders[group.type]) { + // Call the groupBuilders function + // $FlowFixMe + let groupNode: HtmlDomNode = groupBuilders[group.type](group, options); + + // If the size changed between the parent and the current group, account + // for that size difference. + if (baseOptions && options.size !== baseOptions.size) { + groupNode = makeSpan(options.sizingClasses(baseOptions), + [groupNode], options); + + const multiplier = + options.sizeMultiplier / baseOptions.sizeMultiplier; + + groupNode.height *= multiplier; + groupNode.depth *= multiplier; + } + + return groupNode; + } else { + throw new ParseError( + "Got group of unknown type: '" + group.type + "'"); + } +}; + +/** + * Combine an array of HTML DOM nodes (e.g., the output of `buildExpression`) + * into an unbreakable HTML node of class .base, with proper struts to + * guarantee correct vertical extent. `buildHTML` calls this repeatedly to + * make up the entire expression as a sequence of unbreakable units. + */ +function buildHTMLUnbreakable(children, options) { + // Compute height and depth of this chunk. + const body = makeSpan(["base"], children, options); + + // Add strut, which ensures that the top of the HTML element falls at + // the height of the expression, and the bottom of the HTML element + // falls at the depth of the expression. + const strut = makeSpan(["strut"]); + strut.style.height = makeEm(body.height + body.depth); + if (body.depth) { + strut.style.verticalAlign = makeEm(-body.depth); + } + body.children.unshift(strut); + + return body; +} + +/** + * Take an entire parse tree, and build it into an appropriate set of HTML + * nodes. + */ +export default function buildHTML(tree: AnyParseNode[], options: Options): DomSpan { + // Strip off outer tag wrapper for processing below. + let tag = null; + if (tree.length === 1 && tree[0].type === "tag") { + tag = tree[0].tag; + tree = tree[0].body; + } + + // Build the expression contained in the tree + const expression = buildExpression(tree, options, "root"); + + let eqnNum; + if (expression.length === 2 && expression[1].hasClass("tag")) { + // An environment with automatic equation numbers, e.g. {gather}. + eqnNum = expression.pop(); + } + + const children = []; + + // Create one base node for each chunk between potential line breaks. + // The TeXBook [p.173] says "A formula will be broken only after a + // relation symbol like $=$ or $<$ or $\rightarrow$, or after a binary + // operation symbol like $+$ or $-$ or $\times$, where the relation or + // binary operation is on the ``outer level'' of the formula (i.e., not + // enclosed in {...} and not part of an \over construction)." + + let parts = []; + for (let i = 0; i < expression.length; i++) { + parts.push(expression[i]); + if (expression[i].hasClass("mbin") || + expression[i].hasClass("mrel") || + expression[i].hasClass("allowbreak")) { + // Put any post-operator glue on same line as operator. + // Watch for \nobreak along the way, and stop at \newline. + let nobreak = false; + while (i < expression.length - 1 && + expression[i + 1].hasClass("mspace") && + !expression[i + 1].hasClass("newline")) { + i++; + parts.push(expression[i]); + if (expression[i].hasClass("nobreak")) { + nobreak = true; + } + } + // Don't allow break if \nobreak among the post-operator glue. + if (!nobreak) { + children.push(buildHTMLUnbreakable(parts, options)); + parts = []; + } + } else if (expression[i].hasClass("newline")) { + // Write the line except the newline + parts.pop(); + if (parts.length > 0) { + children.push(buildHTMLUnbreakable(parts, options)); + parts = []; + } + // Put the newline at the top level + children.push(expression[i]); + } + } + if (parts.length > 0) { + children.push(buildHTMLUnbreakable(parts, options)); + } + + // Now, if there was a tag, build it too and append it as a final child. + let tagChild; + if (tag) { + tagChild = buildHTMLUnbreakable( + buildExpression(tag, options, true) + ); + tagChild.classes = ["tag"]; + children.push(tagChild); + } else if (eqnNum) { + children.push(eqnNum); + } + + const htmlNode = makeSpan(["katex-html"], children); + htmlNode.setAttribute("aria-hidden", "true"); + + // Adjust the strut of the tag to be the maximum height of all children + // (the height of the enclosing htmlNode) for proper vertical alignment. + if (tagChild) { + const strut = tagChild.children[0]; + strut.style.height = makeEm(htmlNode.height + htmlNode.depth); + if (htmlNode.depth) { + strut.style.verticalAlign = makeEm(-htmlNode.depth); + } + } + + return htmlNode; +} diff --git a/frontend/node_modules/katex/src/buildMathML.js b/frontend/node_modules/katex/src/buildMathML.js new file mode 100644 index 0000000..376814e --- /dev/null +++ b/frontend/node_modules/katex/src/buildMathML.js @@ -0,0 +1,322 @@ +// @flow +/** + * This file converts a parse tree into a corresponding MathML tree. The main + * entry point is the `buildMathML` function, which takes a parse tree from the + * parser. + */ + +import buildCommon from "./buildCommon"; +import {getCharacterMetrics} from "./fontMetrics"; +import mathMLTree from "./mathMLTree"; +import ParseError from "./ParseError"; +import symbols, {ligatures} from "./symbols"; +import utils from "./utils"; +import {_mathmlGroupBuilders as groupBuilders} from "./defineFunction"; +import {MathNode, TextNode} from "./mathMLTree"; + +import type Options from "./Options"; +import type {AnyParseNode, SymbolParseNode} from "./parseNode"; +import type {DomSpan} from "./domTree"; +import type {MathDomNode} from "./mathMLTree"; +import type {FontVariant, Mode} from "./types"; + +/** + * Takes a symbol and converts it into a MathML text node after performing + * optional replacement from symbols.js. + */ +export const makeText = function( + text: string, + mode: Mode, + options?: Options, +): TextNode { + if (symbols[mode][text] && symbols[mode][text].replace && + text.charCodeAt(0) !== 0xD835 && + !(ligatures.hasOwnProperty(text) && options && + ((options.fontFamily && options.fontFamily.slice(4, 6) === "tt") || + (options.font && options.font.slice(4, 6) === "tt")))) { + text = symbols[mode][text].replace; + } + + return new mathMLTree.TextNode(text); +}; + +/** + * Wrap the given array of nodes in an node if needed, i.e., + * unless the array has length 1. Always returns a single node. + */ +export const makeRow = function(body: $ReadOnlyArray): MathDomNode { + if (body.length === 1) { + return body[0]; + } else { + return new mathMLTree.MathNode("mrow", body); + } +}; + +/** + * Returns the math variant as a string or null if none is required. + */ +export const getVariant = function( + group: SymbolParseNode, + options: Options, +): ?FontVariant { + // Handle \text... font specifiers as best we can. + // MathML has a limited list of allowable mathvariant specifiers; see + // https://www.w3.org/TR/MathML3/chapter3.html#presm.commatt + if (options.fontFamily === "texttt") { + return "monospace"; + } else if (options.fontFamily === "textsf") { + if (options.fontShape === "textit" && + options.fontWeight === "textbf") { + return "sans-serif-bold-italic"; + } else if (options.fontShape === "textit") { + return "sans-serif-italic"; + } else if (options.fontWeight === "textbf") { + return "bold-sans-serif"; + } else { + return "sans-serif"; + } + } else if (options.fontShape === "textit" && + options.fontWeight === "textbf") { + return "bold-italic"; + } else if (options.fontShape === "textit") { + return "italic"; + } else if (options.fontWeight === "textbf") { + return "bold"; + } + + const font = options.font; + if (!font || font === "mathnormal") { + return null; + } + + const mode = group.mode; + if (font === "mathit") { + return "italic"; + } else if (font === "boldsymbol") { + return group.type === "textord" ? "bold" : "bold-italic"; + } else if (font === "mathbf") { + return "bold"; + } else if (font === "mathbb") { + return "double-struck"; + } else if (font === "mathsfit") { + return "sans-serif-italic"; + } else if (font === "mathfrak") { + return "fraktur"; + } else if (font === "mathscr" || font === "mathcal") { + // MathML makes no distinction between script and calligraphic + return "script"; + } else if (font === "mathsf") { + return "sans-serif"; + } else if (font === "mathtt") { + return "monospace"; + } + + let text = group.text; + if (utils.contains(["\\imath", "\\jmath"], text)) { + return null; + } + + if (symbols[mode][text] && symbols[mode][text].replace) { + text = symbols[mode][text].replace; + } + + const fontName = buildCommon.fontMap[font].fontName; + if (getCharacterMetrics(text, fontName, mode)) { + return buildCommon.fontMap[font].variant; + } + + return null; +}; + +/** + * Check for . which is how a dot renders in MathML, + * or , + * which is how a braced comma {,} renders in MathML + */ +function isNumberPunctuation(group: ?MathNode): boolean { + if (!group) { + return false; + } + if (group.type === 'mi' && group.children.length === 1) { + const child = group.children[0]; + return child instanceof TextNode && child.text === '.'; + } else if (group.type === 'mo' && group.children.length === 1 && + group.getAttribute('separator') === 'true' && + group.getAttribute('lspace') === '0em' && + group.getAttribute('rspace') === '0em' + ) { + const child = group.children[0]; + return child instanceof TextNode && child.text === ','; + } else { + return false; + } +} + +/** + * Takes a list of nodes, builds them, and returns a list of the generated + * MathML nodes. Also combine consecutive outputs into a single + * tag. + */ +export const buildExpression = function( + expression: AnyParseNode[], + options: Options, + isOrdgroup?: boolean, +): MathNode[] { + if (expression.length === 1) { + const group = buildGroup(expression[0], options); + if (isOrdgroup && group instanceof MathNode && group.type === "mo") { + // When TeX writers want to suppress spacing on an operator, + // they often put the operator by itself inside braces. + group.setAttribute("lspace", "0em"); + group.setAttribute("rspace", "0em"); + } + return [group]; + } + + const groups = []; + let lastGroup; + for (let i = 0; i < expression.length; i++) { + const group = buildGroup(expression[i], options); + if (group instanceof MathNode && lastGroup instanceof MathNode) { + // Concatenate adjacent s + if (group.type === 'mtext' && lastGroup.type === 'mtext' + && group.getAttribute('mathvariant') === + lastGroup.getAttribute('mathvariant')) { + lastGroup.children.push(...group.children); + continue; + // Concatenate adjacent s + } else if (group.type === 'mn' && lastGroup.type === 'mn') { + lastGroup.children.push(...group.children); + continue; + // Concatenate ... followed by . + } else if (isNumberPunctuation(group) && lastGroup.type === 'mn') { + lastGroup.children.push(...group.children); + continue; + // Concatenate . followed by ... + } else if (group.type === 'mn' && isNumberPunctuation(lastGroup)) { + group.children = [...lastGroup.children, ...group.children]; + groups.pop(); + // Put preceding ... or . inside base of + // ...base......exponent... (or ) + } else if ((group.type === 'msup' || group.type === 'msub') && + group.children.length >= 1 && + (lastGroup.type === 'mn' || isNumberPunctuation(lastGroup)) + ) { + const base = group.children[0]; + if (base instanceof MathNode && base.type === 'mn') { + base.children = [...lastGroup.children, ...base.children]; + groups.pop(); + } + // \not + } else if (lastGroup.type === 'mi' && lastGroup.children.length === 1) { + const lastChild = lastGroup.children[0]; + if (lastChild instanceof TextNode && lastChild.text === '\u0338' && + (group.type === 'mo' || group.type === 'mi' || + group.type === 'mn')) { + const child = group.children[0]; + if (child instanceof TextNode && child.text.length > 0) { + // Overlay with combining character long solidus + child.text = child.text.slice(0, 1) + "\u0338" + + child.text.slice(1); + groups.pop(); + } + } + } + } + groups.push(group); + lastGroup = group; + } + return groups; +}; + +/** + * Equivalent to buildExpression, but wraps the elements in an + * if there's more than one. Returns a single node instead of an array. + */ +export const buildExpressionRow = function( + expression: AnyParseNode[], + options: Options, + isOrdgroup?: boolean, +): MathDomNode { + return makeRow(buildExpression(expression, options, isOrdgroup)); +}; + +/** + * Takes a group from the parser and calls the appropriate groupBuilders function + * on it to produce a MathML node. + */ +export const buildGroup = function( + group: ?AnyParseNode, + options: Options, +): MathNode { + if (!group) { + return new mathMLTree.MathNode("mrow"); + } + + if (groupBuilders[group.type]) { + // Call the groupBuilders function + // $FlowFixMe + const result: MathDomNode = groupBuilders[group.type](group, options); + // $FlowFixMe + return result; + } else { + throw new ParseError( + "Got group of unknown type: '" + group.type + "'"); + } +}; + +/** + * Takes a full parse tree and settings and builds a MathML representation of + * it. In particular, we put the elements from building the parse tree into a + * tag so we can also include that TeX source as an annotation. + * + * Note that we actually return a domTree element with a `` inside it so + * we can do appropriate styling. + */ +export default function buildMathML( + tree: AnyParseNode[], + texExpression: string, + options: Options, + isDisplayMode: boolean, + forMathmlOnly: boolean, +): DomSpan { + const expression = buildExpression(tree, options); + + // TODO: Make a pass thru the MathML similar to buildHTML.traverseNonSpaceNodes + // and add spacing nodes. This is necessary only adjacent to math operators + // like \sin or \lim or to subsup elements that contain math operators. + // MathML takes care of the other spacing issues. + + // Wrap up the expression in an mrow so it is presented in the semantics + // tag correctly, unless it's a single or . + let wrapper; + if (expression.length === 1 && expression[0] instanceof MathNode && + utils.contains(["mrow", "mtable"], expression[0].type)) { + wrapper = expression[0]; + } else { + wrapper = new mathMLTree.MathNode("mrow", expression); + } + + // Build a TeX annotation of the source + const annotation = new mathMLTree.MathNode( + "annotation", [new mathMLTree.TextNode(texExpression)]); + + annotation.setAttribute("encoding", "application/x-tex"); + + const semantics = new mathMLTree.MathNode( + "semantics", [wrapper, annotation]); + + const math = new mathMLTree.MathNode("math", [semantics]); + math.setAttribute("xmlns", "http://www.w3.org/1998/Math/MathML"); + if (isDisplayMode) { + math.setAttribute("display", "block"); + } + + // You can't style nodes, so we wrap the node in a span. + // NOTE: The span class is not typed to have nodes as children, and + // we don't want to make the children type more generic since the children + // of span are expected to have more fields in `buildHtml` contexts. + const wrapperClass = forMathmlOnly ? "katex" : "katex-mathml"; + // $FlowFixMe + return buildCommon.makeSpan([wrapperClass], [math]); +} diff --git a/frontend/node_modules/katex/src/buildTree.js b/frontend/node_modules/katex/src/buildTree.js new file mode 100644 index 0000000..d7ad29c --- /dev/null +++ b/frontend/node_modules/katex/src/buildTree.js @@ -0,0 +1,67 @@ +// @flow +import buildHTML from "./buildHTML"; +import buildMathML from "./buildMathML"; +import buildCommon from "./buildCommon"; +import Options from "./Options"; +import Settings from "./Settings"; +import Style from "./Style"; + +import type {AnyParseNode} from "./parseNode"; +import type {DomSpan} from "./domTree"; + +const optionsFromSettings = function(settings: Settings) { + return new Options({ + style: (settings.displayMode ? Style.DISPLAY : Style.TEXT), + maxSize: settings.maxSize, + minRuleThickness: settings.minRuleThickness, + }); +}; + +const displayWrap = function(node: DomSpan, settings: Settings): DomSpan { + if (settings.displayMode) { + const classes = ["katex-display"]; + if (settings.leqno) { + classes.push("leqno"); + } + if (settings.fleqn) { + classes.push("fleqn"); + } + node = buildCommon.makeSpan(classes, [node]); + } + return node; +}; + +export const buildTree = function( + tree: AnyParseNode[], + expression: string, + settings: Settings, +): DomSpan { + const options = optionsFromSettings(settings); + let katexNode; + if (settings.output === "mathml") { + return buildMathML(tree, expression, options, settings.displayMode, true); + } else if (settings.output === "html") { + const htmlNode = buildHTML(tree, options); + katexNode = buildCommon.makeSpan(["katex"], [htmlNode]); + } else { + const mathMLNode = buildMathML(tree, expression, options, + settings.displayMode, false); + const htmlNode = buildHTML(tree, options); + katexNode = buildCommon.makeSpan(["katex"], [mathMLNode, htmlNode]); + } + + return displayWrap(katexNode, settings); +}; + +export const buildHTMLTree = function( + tree: AnyParseNode[], + expression: string, + settings: Settings, +): DomSpan { + const options = optionsFromSettings(settings); + const htmlNode = buildHTML(tree, options); + const katexNode = buildCommon.makeSpan(["katex"], [htmlNode]); + return displayWrap(katexNode, settings); +}; + +export default buildTree; diff --git a/frontend/node_modules/katex/src/defineEnvironment.js b/frontend/node_modules/katex/src/defineEnvironment.js new file mode 100644 index 0000000..337dad1 --- /dev/null +++ b/frontend/node_modules/katex/src/defineEnvironment.js @@ -0,0 +1,117 @@ +// @flow +import {_htmlGroupBuilders, _mathmlGroupBuilders} from "./defineFunction"; + +import type Parser from "./Parser"; +import type {AnyParseNode} from "./parseNode"; +import type {ArgType, Mode} from "./types"; +import type {NodeType} from "./parseNode"; +import type {HtmlBuilder, MathMLBuilder} from "./defineFunction"; + +/** + * The context contains the following properties: + * - mode: current parsing mode. + * - envName: the name of the environment, one of the listed names. + * - parser: the parser object. + */ +type EnvContext = {| + mode: Mode, + envName: string, + parser: Parser, +|}; + +/** + * - context: information and references provided by the parser + * - args: an array of arguments passed to \begin{name} + * - optArgs: an array of optional arguments passed to \begin{name} + */ +type EnvHandler = ( + context: EnvContext, + args: AnyParseNode[], + optArgs: (?AnyParseNode)[], +) => AnyParseNode; + +/** + * - numArgs: (default 0) The number of arguments after the \begin{name} function. + * - argTypes: (optional) Just like for a function + * - allowedInText: (default false) Whether or not the environment is allowed + * inside text mode (not enforced yet). + * - numOptionalArgs: (default 0) Just like for a function + */ +type EnvProps = { + numArgs: number, +}; + +/** + * Final environment spec for use at parse time. + * This is almost identical to `EnvDefSpec`, except it + * 1. includes the function handler + * 2. requires all arguments except argType + * It is generated by `defineEnvironment()` below. + */ +export type EnvSpec = {| + type: NODETYPE, // Need to use the type to avoid error. See NOTES below. + numArgs: number, + argTypes?: ArgType[], + allowedInText: boolean, + numOptionalArgs: number, + handler: EnvHandler, +|}; + +/** + * All registered environments. + * `environments.js` exports this same dictionary again and makes it public. + * `Parser.js` requires this dictionary via `environments.js`. + */ +export const _environments: {[string]: EnvSpec<*>} = {}; + +type EnvDefSpec = {| + // Unique string to differentiate parse nodes. + type: NODETYPE, + + // List of functions which use the give handler, htmlBuilder, + // and mathmlBuilder. + names: Array, + + // Properties that control how the environments are parsed. + props: EnvProps, + + handler: EnvHandler, + + // This function returns an object representing the DOM structure to be + // created when rendering the defined LaTeX function. + htmlBuilder: HtmlBuilder, + + // This function returns an object representing the MathML structure to be + // created when rendering the defined LaTeX function. + mathmlBuilder: MathMLBuilder, +|}; + +export default function defineEnvironment({ + type, + names, + props, + handler, + htmlBuilder, + mathmlBuilder, +}: EnvDefSpec) { + // Set default values of environments. + const data = { + type, + numArgs: props.numArgs || 0, + allowedInText: false, + numOptionalArgs: 0, + handler, + }; + for (let i = 0; i < names.length; ++i) { + // TODO: The value type of _environments should be a type union of all + // possible `EnvSpec<>` possibilities instead of `EnvSpec<*>`, which is + // an existential type. + _environments[names[i]] = data; + } + if (htmlBuilder) { + _htmlGroupBuilders[type] = htmlBuilder; + } + if (mathmlBuilder) { + _mathmlGroupBuilders[type] = mathmlBuilder; + } +} diff --git a/frontend/node_modules/katex/src/defineFunction.js b/frontend/node_modules/katex/src/defineFunction.js new file mode 100644 index 0000000..79cd919 --- /dev/null +++ b/frontend/node_modules/katex/src/defineFunction.js @@ -0,0 +1,223 @@ +// @flow +import type Parser from "./Parser"; +import type {ParseNode, AnyParseNode, NodeType, UnsupportedCmdParseNode} + from "./parseNode"; +import type Options from "./Options"; +import type {ArgType, BreakToken} from "./types"; +import type {HtmlDomNode} from "./domTree"; +import type {Token} from "./Token"; +import type {MathDomNode} from "./mathMLTree"; + +/** Context provided to function handlers for error messages. */ +export type FunctionContext = {| + funcName: string, + parser: Parser, + token?: Token, + breakOnTokenText?: BreakToken, +|}; + +export type FunctionHandler = ( + context: FunctionContext, + args: AnyParseNode[], + optArgs: (?AnyParseNode)[], +) => UnsupportedCmdParseNode | ParseNode; +// Note: reverse the order of the return type union will cause a flow error. +// See https://github.com/facebook/flow/issues/3663. + +export type HtmlBuilder = (ParseNode, Options) => HtmlDomNode; +export type MathMLBuilder = ( + group: ParseNode, + options: Options, +) => MathDomNode; + +// More general version of `HtmlBuilder` for nodes (e.g. \sum, accent types) +// whose presence impacts super/subscripting. In this case, ParseNode<"supsub"> +// delegates its HTML building to the HtmlBuilder corresponding to these nodes. +export type HtmlBuilderSupSub = + (ParseNode<"supsub"> | ParseNode, Options) => HtmlDomNode; + +export type FunctionPropSpec = { + // The number of arguments the function takes. + numArgs: number, + + // An array corresponding to each argument of the function, giving the + // type of argument that should be parsed. Its length should be equal + // to `numOptionalArgs + numArgs`, and types for optional arguments + // should appear before types for mandatory arguments. + argTypes?: ArgType[], + + // Whether it expands to a single token or a braced group of tokens. + // If it's grouped, it can be used as an argument to primitive commands, + // such as \sqrt (without the optional argument) and super/subscript. + allowedInArgument?: boolean, + + // Whether or not the function is allowed inside text mode + // (default false) + allowedInText?: boolean, + + // Whether or not the function is allowed inside text mode + // (default true) + allowedInMath?: boolean, + + // (optional) The number of optional arguments the function + // should parse. If the optional arguments aren't found, + // `null` will be passed to the handler in their place. + // (default 0) + numOptionalArgs?: number, + + // Must be true if the function is an infix operator. + infix?: boolean, + + // Whether or not the function is a TeX primitive. + primitive?: boolean, +}; + +type FunctionDefSpec = {| + // Unique string to differentiate parse nodes. + // Also determines the type of the value returned by `handler`. + type: NODETYPE, + + // The first argument to defineFunction is a single name or a list of names. + // All functions named in such a list will share a single implementation. + names: Array, + + // Properties that control how the functions are parsed. + props: FunctionPropSpec, + + // The handler is called to handle these functions and their arguments and + // returns a `ParseNode`. + handler: ?FunctionHandler, + + // This function returns an object representing the DOM structure to be + // created when rendering the defined LaTeX function. + // This should not modify the `ParseNode`. + htmlBuilder?: HtmlBuilder, + + // This function returns an object representing the MathML structure to be + // created when rendering the defined LaTeX function. + // This should not modify the `ParseNode`. + mathmlBuilder?: MathMLBuilder, +|}; + +/** + * Final function spec for use at parse time. + * This is almost identical to `FunctionPropSpec`, except it + * 1. includes the function handler, and + * 2. requires all arguments except argTypes. + * It is generated by `defineFunction()` below. + */ +export type FunctionSpec = {| + type: NODETYPE, // Need to use the type to avoid error. See NOTES below. + numArgs: number, + argTypes?: ArgType[], + allowedInArgument: boolean, + allowedInText: boolean, + allowedInMath: boolean, + numOptionalArgs: number, + infix: boolean, + primitive: boolean, + + // FLOW TYPE NOTES: Doing either one of the following two + // + // - removing the NODETYPE type parameter in FunctionSpec above; + // - using ?FunctionHandler below; + // + // results in a confusing flow typing error: + // "string literal `styling`. This type is incompatible with..." + // pointing to the definition of `defineFunction` and finishing with + // "some incompatible instantiation of `NODETYPE`" + // + // Having FunctionSpec above and FunctionHandler<*> below seems to + // circumvent this error. This is not harmful for catching errors since + // _functions is typed FunctionSpec<*> (it stores all TeX function specs). + + // Must be specified unless it's handled directly in the parser. + handler: ?FunctionHandler<*>, +|}; + +/** + * All registered functions. + * `functions.js` just exports this same dictionary again and makes it public. + * `Parser.js` requires this dictionary. + */ +export const _functions: {[string]: FunctionSpec<*>} = {}; + +/** + * All HTML builders. Should be only used in the `define*` and the `build*ML` + * functions. + */ +export const _htmlGroupBuilders: {[string]: HtmlBuilder<*>} = {}; + +/** + * All MathML builders. Should be only used in the `define*` and the `build*ML` + * functions. + */ +export const _mathmlGroupBuilders: {[string]: MathMLBuilder<*>} = {}; + +export default function defineFunction({ + type, + names, + props, + handler, + htmlBuilder, + mathmlBuilder, +}: FunctionDefSpec) { + // Set default values of functions + const data = { + type, + numArgs: props.numArgs, + argTypes: props.argTypes, + allowedInArgument: !!props.allowedInArgument, + allowedInText: !!props.allowedInText, + allowedInMath: (props.allowedInMath === undefined) + ? true + : props.allowedInMath, + numOptionalArgs: props.numOptionalArgs || 0, + infix: !!props.infix, + primitive: !!props.primitive, + handler: handler, + }; + for (let i = 0; i < names.length; ++i) { + _functions[names[i]] = data; + } + if (type) { + if (htmlBuilder) { + _htmlGroupBuilders[type] = htmlBuilder; + } + if (mathmlBuilder) { + _mathmlGroupBuilders[type] = mathmlBuilder; + } + } +} + +/** + * Use this to register only the HTML and MathML builders for a function (e.g. + * if the function's ParseNode is generated in Parser.js rather than via a + * stand-alone handler provided to `defineFunction`). + */ +export function defineFunctionBuilders({ + type, htmlBuilder, mathmlBuilder, +}: {| + type: NODETYPE, + htmlBuilder?: HtmlBuilder, + mathmlBuilder: MathMLBuilder, +|}) { + defineFunction({ + type, + names: [], + props: {numArgs: 0}, + handler() { throw new Error('Should never be called.'); }, + htmlBuilder, + mathmlBuilder, + }); +} + +export const normalizeArgument = function(arg: AnyParseNode): AnyParseNode { + return arg.type === "ordgroup" && arg.body.length === 1 ? arg.body[0] : arg; +}; + +// Since the corresponding buildHTML/buildMathML function expects a +// list of elements, we normalize for different kinds of arguments +export const ordargument = function(arg: AnyParseNode): AnyParseNode[] { + return arg.type === "ordgroup" ? arg.body : [arg]; +}; diff --git a/frontend/node_modules/katex/src/defineMacro.js b/frontend/node_modules/katex/src/defineMacro.js new file mode 100644 index 0000000..c829f38 --- /dev/null +++ b/frontend/node_modules/katex/src/defineMacro.js @@ -0,0 +1,125 @@ +// @flow + +import {Token} from "./Token"; +import type Namespace from "./Namespace"; +import type {Mode} from "./types"; + +/** + * Provides context to macros defined by functions. Implemented by + * MacroExpander. + */ +export interface MacroContextInterface { + mode: Mode; + + /** + * Object mapping macros to their expansions. + */ + macros: Namespace; + + /** + * Returns the topmost token on the stack, without expanding it. + * Similar in behavior to TeX's `\futurelet`. + */ + future(): Token; + + /** + * Remove and return the next unexpanded token. + */ + popToken(): Token; + + /** + * Consume all following space tokens, without expansion. + */ + consumeSpaces(): void; + + /** + * Expand the next token only once if possible. + */ + expandOnce(expandableOnly?: boolean): number | boolean; + + /** + * Expand the next token only once (if possible), and return the resulting + * top token on the stack (without removing anything from the stack). + * Similar in behavior to TeX's `\expandafter\futurelet`. + */ + expandAfterFuture(): Token; + + /** + * Recursively expand first token, then return first non-expandable token. + */ + expandNextToken(): Token; + + /** + * Fully expand the given macro name and return the resulting list of + * tokens, or return `undefined` if no such macro is defined. + */ + expandMacro(name: string): Token[] | void; + + /** + * Fully expand the given macro name and return the result as a string, + * or return `undefined` if no such macro is defined. + */ + expandMacroAsText(name: string): string | void; + + /** + * Fully expand the given token stream and return the resulting list of + * tokens. Note that the input tokens are in reverse order, but the + * output tokens are in forward order. + */ + expandTokens(tokens: Token[]): Token[]; + + /** + * Consume an argument from the token stream, and return the resulting array + * of tokens and start/end token. + */ + consumeArg(delims?: ?string[]): MacroArg; + + /** + * Consume the specified number of arguments from the token stream, + * and return the resulting array of arguments. + */ + consumeArgs(numArgs: number): Token[][]; + + /** + * Determine whether a command is currently "defined" (has some + * functionality), meaning that it's a macro (in the current group), + * a function, a symbol, or one of the special commands listed in + * `implicitCommands`. + */ + isDefined(name: string): boolean; + + /** + * Determine whether a command is expandable. + */ + isExpandable(name: string): boolean; +} + +export type MacroArg = { + tokens: Token[], + start: Token, + end: Token +}; + +/** Macro tokens (in reverse order). */ +export type MacroExpansion = { + tokens: Token[], + numArgs: number, + delimiters?: string[][], + unexpandable?: boolean, // used in \let +}; + +export type MacroDefinition = string | MacroExpansion | + (MacroContextInterface => (string | MacroExpansion)); +export type MacroMap = {[string]: MacroDefinition}; + +/** + * All registered global/built-in macros. + * `macros.js` exports this same dictionary again and makes it public. + * `Parser.js` requires this dictionary via `macros.js`. + */ +export const _macros: MacroMap = {}; + +// This function might one day accept an additional argument and do more things. +export default function defineMacro(name: string, body: MacroDefinition) { + _macros[name] = body; +} diff --git a/frontend/node_modules/katex/src/delimiter.js b/frontend/node_modules/katex/src/delimiter.js new file mode 100644 index 0000000..beac30a --- /dev/null +++ b/frontend/node_modules/katex/src/delimiter.js @@ -0,0 +1,835 @@ +// @flow +/** + * This file deals with creating delimiters of various sizes. The TeXbook + * discusses these routines on page 441-442, in the "Another subroutine sets box + * x to a specified variable delimiter" paragraph. + * + * There are three main routines here. `makeSmallDelim` makes a delimiter in the + * normal font, but in either text, script, or scriptscript style. + * `makeLargeDelim` makes a delimiter in textstyle, but in one of the Size1, + * Size2, Size3, or Size4 fonts. `makeStackedDelim` makes a delimiter out of + * smaller pieces that are stacked on top of one another. + * + * The functions take a parameter `center`, which determines if the delimiter + * should be centered around the axis. + * + * Then, there are three exposed functions. `sizedDelim` makes a delimiter in + * one of the given sizes. This is used for things like `\bigl`. + * `customSizedDelim` makes a delimiter with a given total height+depth. It is + * called in places like `\sqrt`. `leftRightDelim` makes an appropriate + * delimiter which surrounds an expression of a given height an depth. It is + * used in `\left` and `\right`. + */ + +import ParseError from "./ParseError"; +import Style from "./Style"; + +import {PathNode, SvgNode, SymbolNode} from "./domTree"; +import {sqrtPath, innerPath, tallDelim} from "./svgGeometry"; +import buildCommon from "./buildCommon"; +import {getCharacterMetrics} from "./fontMetrics"; +import symbols from "./symbols"; +import utils from "./utils"; +import {makeEm} from "./units"; +import fontMetricsData from "./fontMetricsData"; + +import type Options from "./Options"; +import type {CharacterMetrics} from "./fontMetrics"; +import type {HtmlDomNode, DomSpan, SvgSpan} from "./domTree"; +import type {Mode} from "./types"; +import type {StyleInterface} from "./Style"; +import type {VListElem} from "./buildCommon"; + +/** + * Get the metrics for a given symbol and font, after transformation (i.e. + * after following replacement from symbols.js) + */ +const getMetrics = function( + symbol: string, + font: string, + mode: Mode, +): CharacterMetrics { + const replace = symbols.math[symbol] && symbols.math[symbol].replace; + const metrics = + getCharacterMetrics(replace || symbol, font, mode); + if (!metrics) { + throw new Error(`Unsupported symbol ${symbol} and font size ${font}.`); + } + return metrics; +}; + +/** + * Puts a delimiter span in a given style, and adds appropriate height, depth, + * and maxFontSizes. + */ +const styleWrap = function( + delim: HtmlDomNode, + toStyle: StyleInterface, + options: Options, + classes: string[], +): DomSpan { + const newOptions = options.havingBaseStyle(toStyle); + + const span = buildCommon.makeSpan( + classes.concat(newOptions.sizingClasses(options)), + [delim], options); + + const delimSizeMultiplier = + newOptions.sizeMultiplier / options.sizeMultiplier; + span.height *= delimSizeMultiplier; + span.depth *= delimSizeMultiplier; + span.maxFontSize = newOptions.sizeMultiplier; + + return span; +}; + +const centerSpan = function( + span: DomSpan, + options: Options, + style: StyleInterface, +) { + const newOptions = options.havingBaseStyle(style); + const shift = + (1 - options.sizeMultiplier / newOptions.sizeMultiplier) * + options.fontMetrics().axisHeight; + + span.classes.push("delimcenter"); + span.style.top = makeEm(shift); + span.height -= shift; + span.depth += shift; +}; + +/** + * Makes a small delimiter. This is a delimiter that comes in the Main-Regular + * font, but is restyled to either be in textstyle, scriptstyle, or + * scriptscriptstyle. + */ +const makeSmallDelim = function( + delim: string, + style: StyleInterface, + center: boolean, + options: Options, + mode: Mode, + classes: string[], +): DomSpan { + const text = buildCommon.makeSymbol(delim, "Main-Regular", mode, options); + const span = styleWrap(text, style, options, classes); + if (center) { + centerSpan(span, options, style); + } + return span; +}; + +/** + * Builds a symbol in the given font size (note size is an integer) + */ +const mathrmSize = function( + value: string, + size: number, + mode: Mode, + options: Options, +): SymbolNode { + return buildCommon.makeSymbol(value, "Size" + size + "-Regular", + mode, options); +}; + +/** + * Makes a large delimiter. This is a delimiter that comes in the Size1, Size2, + * Size3, or Size4 fonts. It is always rendered in textstyle. + */ +const makeLargeDelim = function(delim, + size: number, + center: boolean, + options: Options, + mode: Mode, + classes: string[], +): DomSpan { + const inner = mathrmSize(delim, size, mode, options); + const span = styleWrap( + buildCommon.makeSpan(["delimsizing", "size" + size], [inner], options), + Style.TEXT, options, classes); + if (center) { + centerSpan(span, options, Style.TEXT); + } + return span; +}; + +/** + * Make a span from a font glyph with the given offset and in the given font. + * This is used in makeStackedDelim to make the stacking pieces for the delimiter. + */ +const makeGlyphSpan = function( + symbol: string, + font: "Size1-Regular" | "Size4-Regular", + mode: Mode, +): VListElem { + let sizeClass; + // Apply the correct CSS class to choose the right font. + if (font === "Size1-Regular") { + sizeClass = "delim-size1"; + } else /* if (font === "Size4-Regular") */ { + sizeClass = "delim-size4"; + } + + const corner = buildCommon.makeSpan( + ["delimsizinginner", sizeClass], + [buildCommon.makeSpan([], [buildCommon.makeSymbol(symbol, font, mode)])]); + + // Since this will be passed into `makeVList` in the end, wrap the element + // in the appropriate tag that VList uses. + return {type: "elem", elem: corner}; +}; + +const makeInner = function( + ch: string, + height: number, + options: Options +): VListElem { + // Create a span with inline SVG for the inner part of a tall stacked delimiter. + const width = fontMetricsData['Size4-Regular'][ch.charCodeAt(0)] + ? fontMetricsData['Size4-Regular'][ch.charCodeAt(0)][4] + : fontMetricsData['Size1-Regular'][ch.charCodeAt(0)][4]; + const path = new PathNode("inner", innerPath(ch, Math.round(1000 * height))); + const svgNode = new SvgNode([path], { + "width": makeEm(width), + "height": makeEm(height), + // Override CSS rule `.katex svg { width: 100% }` + "style": "width:" + makeEm(width), + "viewBox": "0 0 " + 1000 * width + " " + Math.round(1000 * height), + "preserveAspectRatio": "xMinYMin", + }); + const span = buildCommon.makeSvgSpan([], [svgNode], options); + span.height = height; + span.style.height = makeEm(height); + span.style.width = makeEm(width); + return {type: "elem", elem: span}; +}; + +// Helpers for makeStackedDelim +const lapInEms = 0.008; +const lap = {type: "kern", size: -1 * lapInEms}; +const verts = ["|", "\\lvert", "\\rvert", "\\vert"]; +const doubleVerts = ["\\|", "\\lVert", "\\rVert", "\\Vert"]; + +/** + * Make a stacked delimiter out of a given delimiter, with the total height at + * least `heightTotal`. This routine is mentioned on page 442 of the TeXbook. + */ +const makeStackedDelim = function( + delim: string, + heightTotal: number, + center: boolean, + options: Options, + mode: Mode, + classes: string[], +): DomSpan { + // There are four parts, the top, an optional middle, a repeated part, and a + // bottom. + let top; + let middle; + let repeat; + let bottom; + let svgLabel = ""; + let viewBoxWidth = 0; + top = repeat = bottom = delim; + middle = null; + // Also keep track of what font the delimiters are in + let font = "Size1-Regular"; + + // We set the parts and font based on the symbol. Note that we use + // '\u23d0' instead of '|' and '\u2016' instead of '\\|' for the + // repeats of the arrows + if (delim === "\\uparrow") { + repeat = bottom = "\u23d0"; + } else if (delim === "\\Uparrow") { + repeat = bottom = "\u2016"; + } else if (delim === "\\downarrow") { + top = repeat = "\u23d0"; + } else if (delim === "\\Downarrow") { + top = repeat = "\u2016"; + } else if (delim === "\\updownarrow") { + top = "\\uparrow"; + repeat = "\u23d0"; + bottom = "\\downarrow"; + } else if (delim === "\\Updownarrow") { + top = "\\Uparrow"; + repeat = "\u2016"; + bottom = "\\Downarrow"; + } else if (utils.contains(verts, delim)) { + repeat = "\u2223"; + svgLabel = "vert"; + viewBoxWidth = 333; + } else if (utils.contains(doubleVerts, delim)) { + repeat = "\u2225"; + svgLabel = "doublevert"; + viewBoxWidth = 556; + } else if (delim === "[" || delim === "\\lbrack") { + top = "\u23a1"; + repeat = "\u23a2"; + bottom = "\u23a3"; + font = "Size4-Regular"; + svgLabel = "lbrack"; + viewBoxWidth = 667; + } else if (delim === "]" || delim === "\\rbrack") { + top = "\u23a4"; + repeat = "\u23a5"; + bottom = "\u23a6"; + font = "Size4-Regular"; + svgLabel = "rbrack"; + viewBoxWidth = 667; + } else if (delim === "\\lfloor" || delim === "\u230a") { + repeat = top = "\u23a2"; + bottom = "\u23a3"; + font = "Size4-Regular"; + svgLabel = "lfloor"; + viewBoxWidth = 667; + } else if (delim === "\\lceil" || delim === "\u2308") { + top = "\u23a1"; + repeat = bottom = "\u23a2"; + font = "Size4-Regular"; + svgLabel = "lceil"; + viewBoxWidth = 667; + } else if (delim === "\\rfloor" || delim === "\u230b") { + repeat = top = "\u23a5"; + bottom = "\u23a6"; + font = "Size4-Regular"; + svgLabel = "rfloor"; + viewBoxWidth = 667; + } else if (delim === "\\rceil" || delim === "\u2309") { + top = "\u23a4"; + repeat = bottom = "\u23a5"; + font = "Size4-Regular"; + svgLabel = "rceil"; + viewBoxWidth = 667; + } else if (delim === "(" || delim === "\\lparen") { + top = "\u239b"; + repeat = "\u239c"; + bottom = "\u239d"; + font = "Size4-Regular"; + svgLabel = "lparen"; + viewBoxWidth = 875; + } else if (delim === ")" || delim === "\\rparen") { + top = "\u239e"; + repeat = "\u239f"; + bottom = "\u23a0"; + font = "Size4-Regular"; + svgLabel = "rparen"; + viewBoxWidth = 875; + } else if (delim === "\\{" || delim === "\\lbrace") { + top = "\u23a7"; + middle = "\u23a8"; + bottom = "\u23a9"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\}" || delim === "\\rbrace") { + top = "\u23ab"; + middle = "\u23ac"; + bottom = "\u23ad"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\lgroup" || delim === "\u27ee") { + top = "\u23a7"; + bottom = "\u23a9"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\rgroup" || delim === "\u27ef") { + top = "\u23ab"; + bottom = "\u23ad"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\lmoustache" || delim === "\u23b0") { + top = "\u23a7"; + bottom = "\u23ad"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\rmoustache" || delim === "\u23b1") { + top = "\u23ab"; + bottom = "\u23a9"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } + + // Get the metrics of the four sections + const topMetrics = getMetrics(top, font, mode); + const topHeightTotal = topMetrics.height + topMetrics.depth; + const repeatMetrics = getMetrics(repeat, font, mode); + const repeatHeightTotal = repeatMetrics.height + repeatMetrics.depth; + const bottomMetrics = getMetrics(bottom, font, mode); + const bottomHeightTotal = bottomMetrics.height + bottomMetrics.depth; + let middleHeightTotal = 0; + let middleFactor = 1; + if (middle !== null) { + const middleMetrics = getMetrics(middle, font, mode); + middleHeightTotal = middleMetrics.height + middleMetrics.depth; + middleFactor = 2; // repeat symmetrically above and below middle + } + + // Calculate the minimal height that the delimiter can have. + // It is at least the size of the top, bottom, and optional middle combined. + const minHeight = topHeightTotal + bottomHeightTotal + middleHeightTotal; + + // Compute the number of copies of the repeat symbol we will need + const repeatCount = Math.max(0, Math.ceil( + (heightTotal - minHeight) / (middleFactor * repeatHeightTotal))); + + // Compute the total height of the delimiter including all the symbols + const realHeightTotal = + minHeight + repeatCount * middleFactor * repeatHeightTotal; + + // The center of the delimiter is placed at the center of the axis. Note + // that in this context, "center" means that the delimiter should be + // centered around the axis in the current style, while normally it is + // centered around the axis in textstyle. + let axisHeight = options.fontMetrics().axisHeight; + if (center) { + axisHeight *= options.sizeMultiplier; + } + // Calculate the depth + const depth = realHeightTotal / 2 - axisHeight; + + // Now, we start building the pieces that will go into the vlist + // Keep a list of the pieces of the stacked delimiter + const stack = []; + + if (svgLabel.length > 0) { + // Instead of stacking glyphs, create a single SVG. + // This evades browser problems with imprecise positioning of spans. + const midHeight = realHeightTotal - topHeightTotal - bottomHeightTotal; + const viewBoxHeight = Math.round(realHeightTotal * 1000); + const pathStr = tallDelim(svgLabel, Math.round(midHeight * 1000)); + const path = new PathNode(svgLabel, pathStr); + const width = (viewBoxWidth / 1000).toFixed(3) + "em"; + const height = (viewBoxHeight / 1000).toFixed(3) + "em"; + const svg = new SvgNode([path], { + "width": width, + "height": height, + "viewBox": `0 0 ${viewBoxWidth} ${viewBoxHeight}`, + }); + const wrapper = buildCommon.makeSvgSpan([], [svg], options); + wrapper.height = viewBoxHeight / 1000; + wrapper.style.width = width; + wrapper.style.height = height; + stack.push({type: "elem", elem: wrapper}); + } else { + // Stack glyphs + // Start by adding the bottom symbol + stack.push(makeGlyphSpan(bottom, font, mode)); + stack.push(lap); // overlap + + if (middle === null) { + // The middle section will be an SVG. Make it an extra 0.016em tall. + // We'll overlap by 0.008em at top and bottom. + const innerHeight = realHeightTotal - topHeightTotal - bottomHeightTotal + + 2 * lapInEms; + stack.push(makeInner(repeat, innerHeight, options)); + } else { + // When there is a middle bit, we need the middle part and two repeated + // sections + const innerHeight = (realHeightTotal - topHeightTotal - + bottomHeightTotal - middleHeightTotal) / 2 + 2 * lapInEms; + stack.push(makeInner(repeat, innerHeight, options)); + // Now insert the middle of the brace. + stack.push(lap); + stack.push(makeGlyphSpan(middle, font, mode)); + stack.push(lap); + stack.push(makeInner(repeat, innerHeight, options)); + } + + // Add the top symbol + stack.push(lap); + stack.push(makeGlyphSpan(top, font, mode)); + } + + // Finally, build the vlist + const newOptions = options.havingBaseStyle(Style.TEXT); + const inner = buildCommon.makeVList({ + positionType: "bottom", + positionData: depth, + children: stack, + }, newOptions); + + return styleWrap( + buildCommon.makeSpan(["delimsizing", "mult"], [inner], newOptions), + Style.TEXT, options, classes); +}; + +// All surds have 0.08em padding above the vinculum inside the SVG. +// That keeps browser span height rounding error from pinching the line. +const vbPad = 80; // padding above the surd, measured inside the viewBox. +const emPad = 0.08; // padding, in ems, measured in the document. + +const sqrtSvg = function( + sqrtName: string, + height: number, + viewBoxHeight: number, + extraVinculum: number, + options: Options, +): SvgSpan { + const path = sqrtPath(sqrtName, extraVinculum, viewBoxHeight); + const pathNode = new PathNode(sqrtName, path); + + const svg = new SvgNode([pathNode], { + // Note: 1000:1 ratio of viewBox to document em width. + "width": "400em", + "height": makeEm(height), + "viewBox": "0 0 400000 " + viewBoxHeight, + "preserveAspectRatio": "xMinYMin slice", + }); + + return buildCommon.makeSvgSpan(["hide-tail"], [svg], options); +}; + +/** + * Make a sqrt image of the given height, + */ +const makeSqrtImage = function( + height: number, + options: Options, +): { + span: SvgSpan, + ruleWidth: number, + advanceWidth: number, +} { + // Define a newOptions that removes the effect of size changes such as \Huge. + // We don't pick different a height surd for \Huge. For it, we scale up. + const newOptions = options.havingBaseSizing(); + + // Pick the desired surd glyph from a sequence of surds. + const delim = traverseSequence("\\surd", height * newOptions.sizeMultiplier, + stackLargeDelimiterSequence, newOptions); + + let sizeMultiplier = newOptions.sizeMultiplier; // default + + // The standard sqrt SVGs each have a 0.04em thick vinculum. + // If Settings.minRuleThickness is larger than that, we add extraVinculum. + const extraVinculum = Math.max(0, + options.minRuleThickness - options.fontMetrics().sqrtRuleThickness); + + // Create a span containing an SVG image of a sqrt symbol. + let span; + let spanHeight = 0; + let texHeight = 0; + let viewBoxHeight = 0; + let advanceWidth; + + // We create viewBoxes with 80 units of "padding" above each surd. + // Then browser rounding error on the parent span height will not + // encroach on the ink of the vinculum. But that padding is not + // included in the TeX-like `height` used for calculation of + // vertical alignment. So texHeight = span.height < span.style.height. + + if (delim.type === "small") { + // Get an SVG that is derived from glyph U+221A in font KaTeX-Main. + // 1000 unit normal glyph height. + viewBoxHeight = 1000 + 1000 * extraVinculum + vbPad; + if (height < 1.0) { + sizeMultiplier = 1.0; // mimic a \textfont radical + } else if (height < 1.4) { + sizeMultiplier = 0.7; // mimic a \scriptfont radical + } + spanHeight = (1.0 + extraVinculum + emPad) / sizeMultiplier; + texHeight = (1.00 + extraVinculum) / sizeMultiplier; + span = sqrtSvg("sqrtMain", spanHeight, viewBoxHeight, extraVinculum, + options); + span.style.minWidth = "0.853em"; + advanceWidth = 0.833 / sizeMultiplier; // from the font. + + } else if (delim.type === "large") { + // These SVGs come from fonts: KaTeX_Size1, _Size2, etc. + viewBoxHeight = (1000 + vbPad) * sizeToMaxHeight[delim.size]; + texHeight = (sizeToMaxHeight[delim.size] + extraVinculum) / sizeMultiplier; + spanHeight = (sizeToMaxHeight[delim.size] + extraVinculum + emPad) + / sizeMultiplier; + span = sqrtSvg("sqrtSize" + delim.size, spanHeight, viewBoxHeight, + extraVinculum, options); + span.style.minWidth = "1.02em"; + advanceWidth = 1.0 / sizeMultiplier; // 1.0 from the font. + + } else { + // Tall sqrt. In TeX, this would be stacked using multiple glyphs. + // We'll use a single SVG to accomplish the same thing. + spanHeight = height + extraVinculum + emPad; + texHeight = height + extraVinculum; + viewBoxHeight = Math.floor(1000 * height + extraVinculum) + vbPad; + span = sqrtSvg("sqrtTall", spanHeight, viewBoxHeight, extraVinculum, + options); + span.style.minWidth = "0.742em"; + advanceWidth = 1.056; + } + + span.height = texHeight; + span.style.height = makeEm(spanHeight); + + return { + span, + advanceWidth, + // Calculate the actual line width. + // This actually should depend on the chosen font -- e.g. \boldmath + // should use the thicker surd symbols from e.g. KaTeX_Main-Bold, and + // have thicker rules. + ruleWidth: (options.fontMetrics().sqrtRuleThickness + extraVinculum) + * sizeMultiplier, + }; +}; + +// There are three kinds of delimiters, delimiters that stack when they become +// too large +const stackLargeDelimiters = [ + "(", "\\lparen", ")", "\\rparen", + "[", "\\lbrack", "]", "\\rbrack", + "\\{", "\\lbrace", "\\}", "\\rbrace", + "\\lfloor", "\\rfloor", "\u230a", "\u230b", + "\\lceil", "\\rceil", "\u2308", "\u2309", + "\\surd", +]; + +// delimiters that always stack +const stackAlwaysDelimiters = [ + "\\uparrow", "\\downarrow", "\\updownarrow", + "\\Uparrow", "\\Downarrow", "\\Updownarrow", + "|", "\\|", "\\vert", "\\Vert", + "\\lvert", "\\rvert", "\\lVert", "\\rVert", + "\\lgroup", "\\rgroup", "\u27ee", "\u27ef", + "\\lmoustache", "\\rmoustache", "\u23b0", "\u23b1", +]; + +// and delimiters that never stack +const stackNeverDelimiters = [ + "<", ">", "\\langle", "\\rangle", "/", "\\backslash", "\\lt", "\\gt", +]; + +// Metrics of the different sizes. Found by looking at TeX's output of +// $\bigl| // \Bigl| \biggl| \Biggl| \showlists$ +// Used to create stacked delimiters of appropriate sizes in makeSizedDelim. +const sizeToMaxHeight = [0, 1.2, 1.8, 2.4, 3.0]; + +/** + * Used to create a delimiter of a specific size, where `size` is 1, 2, 3, or 4. + */ +const makeSizedDelim = function( + delim: string, + size: number, + options: Options, + mode: Mode, + classes: string[], +): DomSpan { + // < and > turn into \langle and \rangle in delimiters + if (delim === "<" || delim === "\\lt" || delim === "\u27e8") { + delim = "\\langle"; + } else if (delim === ">" || delim === "\\gt" || delim === "\u27e9") { + delim = "\\rangle"; + } + + // Sized delimiters are never centered. + if (utils.contains(stackLargeDelimiters, delim) || + utils.contains(stackNeverDelimiters, delim)) { + return makeLargeDelim(delim, size, false, options, mode, classes); + } else if (utils.contains(stackAlwaysDelimiters, delim)) { + return makeStackedDelim( + delim, sizeToMaxHeight[size], false, options, mode, classes); + } else { + throw new ParseError("Illegal delimiter: '" + delim + "'"); + } +}; + +/** + * There are three different sequences of delimiter sizes that the delimiters + * follow depending on the kind of delimiter. This is used when creating custom + * sized delimiters to decide whether to create a small, large, or stacked + * delimiter. + * + * In real TeX, these sequences aren't explicitly defined, but are instead + * defined inside the font metrics. Since there are only three sequences that + * are possible for the delimiters that TeX defines, it is easier to just encode + * them explicitly here. + */ + +type Delimiter = + {type: "small", style: StyleInterface} | + {type: "large", size: 1 | 2 | 3 | 4} | + {type: "stack"}; + +// Delimiters that never stack try small delimiters and large delimiters only +const stackNeverDelimiterSequence = [ + {type: "small", style: Style.SCRIPTSCRIPT}, + {type: "small", style: Style.SCRIPT}, + {type: "small", style: Style.TEXT}, + {type: "large", size: 1}, + {type: "large", size: 2}, + {type: "large", size: 3}, + {type: "large", size: 4}, +]; + +// Delimiters that always stack try the small delimiters first, then stack +const stackAlwaysDelimiterSequence = [ + {type: "small", style: Style.SCRIPTSCRIPT}, + {type: "small", style: Style.SCRIPT}, + {type: "small", style: Style.TEXT}, + {type: "stack"}, +]; + +// Delimiters that stack when large try the small and then large delimiters, and +// stack afterwards +const stackLargeDelimiterSequence = [ + {type: "small", style: Style.SCRIPTSCRIPT}, + {type: "small", style: Style.SCRIPT}, + {type: "small", style: Style.TEXT}, + {type: "large", size: 1}, + {type: "large", size: 2}, + {type: "large", size: 3}, + {type: "large", size: 4}, + {type: "stack"}, +]; + +/** + * Get the font used in a delimiter based on what kind of delimiter it is. + * TODO(#963) Use more specific font family return type once that is introduced. + */ +const delimTypeToFont = function(type: Delimiter): string { + if (type.type === "small") { + return "Main-Regular"; + } else if (type.type === "large") { + return "Size" + type.size + "-Regular"; + } else if (type.type === "stack") { + return "Size4-Regular"; + } else { + throw new Error(`Add support for delim type '${type.type}' here.`); + } +}; + +/** + * Traverse a sequence of types of delimiters to decide what kind of delimiter + * should be used to create a delimiter of the given height+depth. + */ +const traverseSequence = function( + delim: string, + height: number, + sequence: Delimiter[], + options: Options, +): Delimiter { + // Here, we choose the index we should start at in the sequences. In smaller + // sizes (which correspond to larger numbers in style.size) we start earlier + // in the sequence. Thus, scriptscript starts at index 3-3=0, script starts + // at index 3-2=1, text starts at 3-1=2, and display starts at min(2,3-0)=2 + const start = Math.min(2, 3 - options.style.size); + for (let i = start; i < sequence.length; i++) { + if (sequence[i].type === "stack") { + // This is always the last delimiter, so we just break the loop now. + break; + } + + const metrics = getMetrics(delim, delimTypeToFont(sequence[i]), "math"); + let heightDepth = metrics.height + metrics.depth; + + // Small delimiters are scaled down versions of the same font, so we + // account for the style change size. + + if (sequence[i].type === "small") { + const newOptions = options.havingBaseStyle(sequence[i].style); + heightDepth *= newOptions.sizeMultiplier; + } + + // Check if the delimiter at this size works for the given height. + if (heightDepth > height) { + return sequence[i]; + } + } + + // If we reached the end of the sequence, return the last sequence element. + return sequence[sequence.length - 1]; +}; + +/** + * Make a delimiter of a given height+depth, with optional centering. Here, we + * traverse the sequences, and create a delimiter that the sequence tells us to. + */ +const makeCustomSizedDelim = function( + delim: string, + height: number, + center: boolean, + options: Options, + mode: Mode, + classes: string[], +): DomSpan { + if (delim === "<" || delim === "\\lt" || delim === "\u27e8") { + delim = "\\langle"; + } else if (delim === ">" || delim === "\\gt" || delim === "\u27e9") { + delim = "\\rangle"; + } + + // Decide what sequence to use + let sequence; + if (utils.contains(stackNeverDelimiters, delim)) { + sequence = stackNeverDelimiterSequence; + } else if (utils.contains(stackLargeDelimiters, delim)) { + sequence = stackLargeDelimiterSequence; + } else { + sequence = stackAlwaysDelimiterSequence; + } + + // Look through the sequence + const delimType = traverseSequence(delim, height, sequence, options); + + // Get the delimiter from font glyphs. + // Depending on the sequence element we decided on, call the + // appropriate function. + if (delimType.type === "small") { + return makeSmallDelim(delim, delimType.style, center, options, + mode, classes); + } else if (delimType.type === "large") { + return makeLargeDelim(delim, delimType.size, center, options, mode, + classes); + } else /* if (delimType.type === "stack") */ { + return makeStackedDelim(delim, height, center, options, mode, + classes); + } +}; + +/** + * Make a delimiter for use with `\left` and `\right`, given a height and depth + * of an expression that the delimiters surround. + */ +const makeLeftRightDelim = function( + delim: string, + height: number, + depth: number, + options: Options, + mode: Mode, + classes: string[], +): DomSpan { + // We always center \left/\right delimiters, so the axis is always shifted + const axisHeight = + options.fontMetrics().axisHeight * options.sizeMultiplier; + + // Taken from TeX source, tex.web, function make_left_right + const delimiterFactor = 901; + const delimiterExtend = 5.0 / options.fontMetrics().ptPerEm; + + const maxDistFromAxis = Math.max( + height - axisHeight, depth + axisHeight); + + const totalHeight = Math.max( + // In real TeX, calculations are done using integral values which are + // 65536 per pt, or 655360 per em. So, the division here truncates in + // TeX but doesn't here, producing different results. If we wanted to + // exactly match TeX's calculation, we could do + // Math.floor(655360 * maxDistFromAxis / 500) * + // delimiterFactor / 655360 + // (To see the difference, compare + // x^{x^{\left(\rule{0.1em}{0.68em}\right)}} + // in TeX and KaTeX) + maxDistFromAxis / 500 * delimiterFactor, + 2 * maxDistFromAxis - delimiterExtend); + + // Finally, we defer to `makeCustomSizedDelim` with our calculated total + // height + return makeCustomSizedDelim(delim, totalHeight, true, options, mode, classes); +}; + +export default { + sqrtImage: makeSqrtImage, + sizedDelim: makeSizedDelim, + sizeToMaxHeight: sizeToMaxHeight, + customSizedDelim: makeCustomSizedDelim, + leftRightDelim: makeLeftRightDelim, +}; diff --git a/frontend/node_modules/katex/src/domTree.js b/frontend/node_modules/katex/src/domTree.js new file mode 100644 index 0000000..b931578 --- /dev/null +++ b/frontend/node_modules/katex/src/domTree.js @@ -0,0 +1,632 @@ +// @flow +/** + * These objects store the data about the DOM nodes we create, as well as some + * extra data. They can then be transformed into real DOM nodes with the + * `toNode` function or HTML markup using `toMarkup`. They are useful for both + * storing extra properties on the nodes, as well as providing a way to easily + * work with the DOM. + * + * Similar functions for working with MathML nodes exist in mathMLTree.js. + * + * TODO: refactor `span` and `anchor` into common superclass when + * target environments support class inheritance + */ +import {scriptFromCodepoint} from "./unicodeScripts"; +import utils from "./utils"; +import {path} from "./svgGeometry"; +import type Options from "./Options"; +import {DocumentFragment} from "./tree"; +import {makeEm} from "./units"; +import ParseError from "./ParseError"; + +import type {VirtualNode} from "./tree"; + + +/** + * Create an HTML className based on a list of classes. In addition to joining + * with spaces, we also remove empty classes. + */ +export const createClass = function(classes: string[]): string { + return classes.filter(cls => cls).join(" "); +}; + +const initNode = function( + classes?: string[], + options?: Options, + style?: CssStyle, +) { + this.classes = classes || []; + this.attributes = {}; + this.height = 0; + this.depth = 0; + this.maxFontSize = 0; + this.style = style || {}; + if (options) { + if (options.style.isTight()) { + this.classes.push("mtight"); + } + const color = options.getColor(); + if (color) { + this.style.color = color; + } + } +}; + +/** + * Convert into an HTML node + */ +const toNode = function(tagName: string): HTMLElement { + const node = document.createElement(tagName); + + // Apply the class + node.className = createClass(this.classes); + + // Apply inline styles + for (const style in this.style) { + if (this.style.hasOwnProperty(style)) { + // $FlowFixMe Flow doesn't seem to understand span.style's type. + node.style[style] = this.style[style]; + } + } + + // Apply attributes + for (const attr in this.attributes) { + if (this.attributes.hasOwnProperty(attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } + + // Append the children, also as HTML nodes + for (let i = 0; i < this.children.length; i++) { + node.appendChild(this.children[i].toNode()); + } + + return node; +}; + +/** + * https://w3c.github.io/html-reference/syntax.html#syntax-attributes + * + * > Attribute Names must consist of one or more characters + * other than the space characters, U+0000 NULL, + * '"', "'", ">", "/", "=", the control characters, + * and any characters that are not defined by Unicode. + */ +const invalidAttributeNameRegex = /[\s"'>/=\x00-\x1f]/; + +/** + * Convert into an HTML markup string + */ +const toMarkup = function(tagName: string): string { + let markup = `<${tagName}`; + + // Add the class + if (this.classes.length) { + markup += ` class="${utils.escape(createClass(this.classes))}"`; + } + + let styles = ""; + + // Add the styles, after hyphenation + for (const style in this.style) { + if (this.style.hasOwnProperty(style)) { + styles += `${utils.hyphenate(style)}:${this.style[style]};`; + } + } + + if (styles) { + markup += ` style="${utils.escape(styles)}"`; + } + + // Add the attributes + for (const attr in this.attributes) { + if (this.attributes.hasOwnProperty(attr)) { + if (invalidAttributeNameRegex.test(attr)) { + throw new ParseError(`Invalid attribute name '${attr}'`); + } + markup += ` ${attr}="${utils.escape(this.attributes[attr])}"`; + } + } + + markup += ">"; + + // Add the markup of the children, also as markup + for (let i = 0; i < this.children.length; i++) { + markup += this.children[i].toMarkup(); + } + + markup += ``; + + return markup; +}; + +// Making the type below exact with all optional fields doesn't work due to +// - https://github.com/facebook/flow/issues/4582 +// - https://github.com/facebook/flow/issues/5688 +// However, since *all* fields are optional, $Shape<> works as suggested in 5688 +// above. +// This type does not include all CSS properties. Additional properties should +// be added as needed. +export type CssStyle = $Shape<{ + backgroundColor: string, + borderBottomWidth: string, + borderColor: string, + borderRightStyle: string, + borderRightWidth: string, + borderTopWidth: string, + borderStyle: string; + borderWidth: string, + bottom: string, + color: string, + height: string, + left: string, + margin: string, + marginLeft: string, + marginRight: string, + marginTop: string, + minWidth: string, + paddingLeft: string, + position: string, + textShadow: string, + top: string, + width: string, + verticalAlign: string, +}> & {}; + +export interface HtmlDomNode extends VirtualNode { + classes: string[]; + height: number; + depth: number; + maxFontSize: number; + style: CssStyle; + + hasClass(className: string): boolean; +} + +// Span wrapping other DOM nodes. +export type DomSpan = Span; +// Span wrapping an SVG node. +export type SvgSpan = Span; + +export type SvgChildNode = PathNode | LineNode; +export type documentFragment = DocumentFragment; + + +/** + * This node represents a span node, with a className, a list of children, and + * an inline style. It also contains information about its height, depth, and + * maxFontSize. + * + * Represents two types with different uses: SvgSpan to wrap an SVG and DomSpan + * otherwise. This typesafety is important when HTML builders access a span's + * children. + */ +export class Span implements HtmlDomNode { + children: ChildType[]; + attributes: {[string]: string}; + classes: string[]; + height: number; + depth: number; + width: ?number; + maxFontSize: number; + style: CssStyle; + + constructor( + classes?: string[], + children?: ChildType[], + options?: Options, + style?: CssStyle, + ) { + initNode.call(this, classes, options, style); + this.children = children || []; + } + + /** + * Sets an arbitrary attribute on the span. Warning: use this wisely. Not + * all browsers support attributes the same, and having too many custom + * attributes is probably bad. + */ + setAttribute(attribute: string, value: string) { + this.attributes[attribute] = value; + } + + hasClass(className: string): boolean { + return utils.contains(this.classes, className); + } + + toNode(): HTMLElement { + return toNode.call(this, "span"); + } + + toMarkup(): string { + return toMarkup.call(this, "span"); + } +} + +/** + * This node represents an anchor () element with a hyperlink. See `span` + * for further details. + */ +export class Anchor implements HtmlDomNode { + children: HtmlDomNode[]; + attributes: {[string]: string}; + classes: string[]; + height: number; + depth: number; + maxFontSize: number; + style: CssStyle; + + constructor( + href: string, + classes: string[], + children: HtmlDomNode[], + options: Options, + ) { + initNode.call(this, classes, options); + this.children = children || []; + this.setAttribute('href', href); + } + + setAttribute(attribute: string, value: string) { + this.attributes[attribute] = value; + } + + hasClass(className: string): boolean { + return utils.contains(this.classes, className); + } + + toNode(): HTMLElement { + return toNode.call(this, "a"); + } + + toMarkup(): string { + return toMarkup.call(this, "a"); + } +} + +/** + * This node represents an image embed () element. + */ +export class Img implements VirtualNode { + src: string; + alt: string; + classes: string[]; + height: number; + depth: number; + maxFontSize: number; + style: CssStyle; + + constructor( + src: string, + alt: string, + style: CssStyle, + ) { + this.alt = alt; + this.src = src; + this.classes = ["mord"]; + this.style = style; + } + + hasClass(className: string): boolean { + return utils.contains(this.classes, className); + } + + toNode(): Node { + const node = document.createElement("img"); + node.src = this.src; + node.alt = this.alt; + node.className = "mord"; + + // Apply inline styles + for (const style in this.style) { + if (this.style.hasOwnProperty(style)) { + // $FlowFixMe + node.style[style] = this.style[style]; + } + } + + return node; + } + + toMarkup(): string { + let markup = `${utils.escape(this.alt)} 0) { + span = document.createElement("span"); + span.style.marginRight = makeEm(this.italic); + } + + if (this.classes.length > 0) { + span = span || document.createElement("span"); + span.className = createClass(this.classes); + } + + for (const style in this.style) { + if (this.style.hasOwnProperty(style)) { + span = span || document.createElement("span"); + // $FlowFixMe Flow doesn't seem to understand span.style's type. + span.style[style] = this.style[style]; + } + } + + if (span) { + span.appendChild(node); + return span; + } else { + return node; + } + } + + /** + * Creates markup for a symbol node. + */ + toMarkup(): string { + // TODO(alpert): More duplication than I'd like from + // span.prototype.toMarkup and symbolNode.prototype.toNode... + let needsSpan = false; + + let markup = " 0) { + styles += "margin-right:" + this.italic + "em;"; + } + for (const style in this.style) { + if (this.style.hasOwnProperty(style)) { + styles += utils.hyphenate(style) + ":" + this.style[style] + ";"; + } + } + + if (styles) { + needsSpan = true; + markup += " style=\"" + utils.escape(styles) + "\""; + } + + const escaped = utils.escape(this.text); + if (needsSpan) { + markup += ">"; + markup += escaped; + markup += ""; + return markup; + } else { + return escaped; + } + } +} + +/** + * SVG nodes are used to render stretchy wide elements. + */ +export class SvgNode implements VirtualNode { + children: SvgChildNode[]; + attributes: {[string]: string}; + + constructor(children?: SvgChildNode[], attributes?: {[string]: string}) { + this.children = children || []; + this.attributes = attributes || {}; + } + + toNode(): Node { + const svgNS = "http://www.w3.org/2000/svg"; + const node = document.createElementNS(svgNS, "svg"); + + // Apply attributes + for (const attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } + + for (let i = 0; i < this.children.length; i++) { + node.appendChild(this.children[i].toNode()); + } + return node; + } + + toMarkup(): string { + let markup = ``; + } else { + return ``; + } + } +} + +export class LineNode implements VirtualNode { + attributes: {[string]: string}; + + constructor(attributes?: {[string]: string}) { + this.attributes = attributes || {}; + } + + toNode(): Node { + const svgNS = "http://www.w3.org/2000/svg"; + const node = document.createElementNS(svgNS, "line"); + + // Apply attributes + for (const attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } + + return node; + } + + toMarkup(): string { + let markup = " { + if (group instanceof Span) { + return group; + } else { + throw new Error(`Expected span but got ${String(group)}.`); + } +} diff --git a/frontend/node_modules/katex/src/environments.js b/frontend/node_modules/katex/src/environments.js new file mode 100644 index 0000000..733aa45 --- /dev/null +++ b/frontend/node_modules/katex/src/environments.js @@ -0,0 +1,9 @@ +// @flow +import {_environments} from "./defineEnvironment"; + +const environments = _environments; + +export default environments; + +// All environment definitions should be imported below +import "./environments/array"; diff --git a/frontend/node_modules/katex/src/environments/array.js b/frontend/node_modules/katex/src/environments/array.js new file mode 100644 index 0000000..c2968fa --- /dev/null +++ b/frontend/node_modules/katex/src/environments/array.js @@ -0,0 +1,1118 @@ +// @flow +import buildCommon from "../buildCommon"; +import Style from "../Style"; +import defineEnvironment from "../defineEnvironment"; +import {parseCD} from "./cd"; +import defineFunction from "../defineFunction"; +import defineMacro from "../defineMacro"; +import mathMLTree from "../mathMLTree"; +import ParseError from "../ParseError"; +import {assertNodeType, assertSymbolNodeType} from "../parseNode"; +import {checkSymbolNodeType} from "../parseNode"; +import {Token} from "../Token"; +import {calculateSize, makeEm} from "../units"; +import utils from "../utils"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +import type Parser from "../Parser"; +import type {ParseNode, AnyParseNode} from "../parseNode"; +import type {StyleStr} from "../types"; +import type {HtmlBuilder, MathMLBuilder} from "../defineFunction"; + +// Data stored in the ParseNode associated with the environment. +export type AlignSpec = { type: "separator", separator: string } | { + type: "align", + align: string, + pregap?: number, + postgap?: number, +}; + +// Type to indicate column separation in MathML +export type ColSeparationType = "align" | "alignat" | "gather" | "small" | "CD"; + +// Helper functions +function getHLines(parser: Parser): boolean[] { + // Return an array. The array length = number of hlines. + // Each element in the array tells if the line is dashed. + const hlineInfo = []; + parser.consumeSpaces(); + let nxt = parser.fetch().text; + if (nxt === "\\relax") { // \relax is an artifact of the \cr macro below + parser.consume(); + parser.consumeSpaces(); + nxt = parser.fetch().text; + } + while (nxt === "\\hline" || nxt === "\\hdashline") { + parser.consume(); + hlineInfo.push(nxt === "\\hdashline"); + parser.consumeSpaces(); + nxt = parser.fetch().text; + } + return hlineInfo; +} + +const validateAmsEnvironmentContext = context => { + const settings = context.parser.settings; + if (!settings.displayMode) { + throw new ParseError(`{${context.envName}} can be used only in` + + ` display mode.`); + } +}; + +// autoTag (an argument to parseArray) can be one of three values: +// * undefined: Regular (not-top-level) array; no tags on each row +// * true: Automatic equation numbering, overridable by \tag +// * false: Tags allowed on each row, but no automatic numbering +// This function *doesn't* work with the "split" environment name. +function getAutoTag(name): ?boolean { + if (name.indexOf("ed") === -1) { + return name.indexOf("*") === -1; + } + // return undefined; +} + +/** + * Parse the body of the environment, with rows delimited by \\ and + * columns delimited by &, and create a nested list in row-major order + * with one group per cell. If given an optional argument style + * ("text", "display", etc.), then each cell is cast into that style. + */ +function parseArray( + parser: Parser, + { + hskipBeforeAndAfter, + addJot, + cols, + arraystretch, + colSeparationType, + autoTag, + singleRow, + emptySingleRow, + maxNumCols, + leqno, + }: {| + hskipBeforeAndAfter?: boolean, + addJot?: boolean, + cols?: AlignSpec[], + arraystretch?: number, + colSeparationType?: ColSeparationType, + autoTag?: ?boolean, + singleRow?: boolean, + emptySingleRow?: boolean, + maxNumCols?: number, + leqno?: boolean, + |}, + style: StyleStr, +): ParseNode<"array"> { + parser.gullet.beginGroup(); + if (!singleRow) { + // \cr is equivalent to \\ without the optional size argument (see below) + // TODO: provide helpful error when \cr is used outside array environment + parser.gullet.macros.set("\\cr", "\\\\\\relax"); + } + + // Get current arraystretch if it's not set by the environment + if (!arraystretch) { + const stretch = parser.gullet.expandMacroAsText("\\arraystretch"); + if (stretch == null) { + // Default \arraystretch from lttab.dtx + arraystretch = 1; + } else { + arraystretch = parseFloat(stretch); + if (!arraystretch || arraystretch < 0) { + throw new ParseError(`Invalid \\arraystretch: ${stretch}`); + } + } + } + + // Start group for first cell + parser.gullet.beginGroup(); + + let row = []; + const body = [row]; + const rowGaps = []; + const hLinesBeforeRow = []; + + const tags = (autoTag != null ? [] : undefined); + + // amsmath uses \global\@eqnswtrue and \global\@eqnswfalse to represent + // whether this row should have an equation number. Simulate this with + // a \@eqnsw macro set to 1 or 0. + function beginRow() { + if (autoTag) { + parser.gullet.macros.set("\\@eqnsw", "1", true); + } + } + function endRow() { + if (tags) { + if (parser.gullet.macros.get("\\df@tag")) { + tags.push(parser.subparse([new Token("\\df@tag")])); + parser.gullet.macros.set("\\df@tag", undefined, true); + } else { + tags.push(Boolean(autoTag) && + parser.gullet.macros.get("\\@eqnsw") === "1"); + } + } + } + beginRow(); + + // Test for \hline at the top of the array. + hLinesBeforeRow.push(getHLines(parser)); + + while (true) { // eslint-disable-line no-constant-condition + // Parse each cell in its own group (namespace) + let cell = parser.parseExpression(false, singleRow ? "\\end" : "\\\\"); + parser.gullet.endGroup(); + parser.gullet.beginGroup(); + + cell = { + type: "ordgroup", + mode: parser.mode, + body: cell, + }; + if (style) { + cell = { + type: "styling", + mode: parser.mode, + style, + body: [cell], + }; + } + row.push(cell); + const next = parser.fetch().text; + if (next === "&") { + if (maxNumCols && row.length === maxNumCols) { + if (singleRow || colSeparationType) { + // {equation} or {split} + throw new ParseError("Too many tab characters: &", + parser.nextToken); + } else { + // {array} environment + parser.settings.reportNonstrict("textEnv", "Too few columns " + + "specified in the {array} column argument."); + } + } + parser.consume(); + } else if (next === "\\end") { + endRow(); + // Arrays terminate newlines with `\crcr` which consumes a `\cr` if + // the last line is empty. However, AMS environments keep the + // empty row if it's the only one. + // NOTE: Currently, `cell` is the last item added into `row`. + if (row.length === 1 && cell.type === "styling" && + cell.body[0].body.length === 0 && + (body.length > 1 || !emptySingleRow)) { + body.pop(); + } + if (hLinesBeforeRow.length < body.length + 1) { + hLinesBeforeRow.push([]); + } + break; + } else if (next === "\\\\") { + parser.consume(); + let size; + // \def\Let@{\let\\\math@cr} + // \def\math@cr{...\math@cr@} + // \def\math@cr@{\new@ifnextchar[\math@cr@@{\math@cr@@[\z@]}} + // \def\math@cr@@[#1]{...\math@cr@@@...} + // \def\math@cr@@@{\cr} + if (parser.gullet.future().text !== " ") { + size = parser.parseSizeGroup(true); + } + rowGaps.push(size ? size.value : null); + endRow(); + + // check for \hline(s) following the row separator + hLinesBeforeRow.push(getHLines(parser)); + + row = []; + body.push(row); + beginRow(); + } else { + throw new ParseError("Expected & or \\\\ or \\cr or \\end", + parser.nextToken); + } + } + + // End cell group + parser.gullet.endGroup(); + // End array group defining \cr + parser.gullet.endGroup(); + + return { + type: "array", + mode: parser.mode, + addJot, + arraystretch, + body, + cols, + rowGaps, + hskipBeforeAndAfter, + hLinesBeforeRow, + colSeparationType, + tags, + leqno, + }; +} + + +// Decides on a style for cells in an array according to whether the given +// environment name starts with the letter 'd'. +function dCellStyle(envName): StyleStr { + if (envName.slice(0, 1) === "d") { + return "display"; + } else { + return "text"; + } +} + +type Outrow = { + [idx: number]: *, + height: number, + depth: number, + pos: number, +}; + +const htmlBuilder: HtmlBuilder<"array"> = function(group, options) { + let r; + let c; + const nr = group.body.length; + const hLinesBeforeRow = group.hLinesBeforeRow; + let nc = 0; + let body = new Array(nr); + const hlines = []; + + const ruleThickness = Math.max( + // From LaTeX \showthe\arrayrulewidth. Equals 0.04 em. + (options.fontMetrics().arrayRuleWidth), + options.minRuleThickness, // User override. + ); + + // Horizontal spacing + const pt = 1 / options.fontMetrics().ptPerEm; + let arraycolsep = 5 * pt; // default value, i.e. \arraycolsep in article.cls + if (group.colSeparationType && group.colSeparationType === "small") { + // We're in a {smallmatrix}. Default column space is \thickspace, + // i.e. 5/18em = 0.2778em, per amsmath.dtx for {smallmatrix}. + // But that needs adjustment because LaTeX applies \scriptstyle to the + // entire array, including the colspace, but this function applies + // \scriptstyle only inside each element. + const localMultiplier = options.havingStyle(Style.SCRIPT).sizeMultiplier; + arraycolsep = 0.2778 * (localMultiplier / options.sizeMultiplier); + } + + // Vertical spacing + const baselineskip = group.colSeparationType === "CD" + ? calculateSize({number: 3, unit: "ex"}, options) + : 12 * pt; // see size10.clo + // Default \jot from ltmath.dtx + // TODO(edemaine): allow overriding \jot via \setlength (#687) + const jot = 3 * pt; + const arrayskip = group.arraystretch * baselineskip; + const arstrutHeight = 0.7 * arrayskip; // \strutbox in ltfsstrc.dtx and + const arstrutDepth = 0.3 * arrayskip; // \@arstrutbox in lttab.dtx + + let totalHeight = 0; + + // Set a position for \hline(s) at the top of the array, if any. + function setHLinePos(hlinesInGap: boolean[]) { + for (let i = 0; i < hlinesInGap.length; ++i) { + if (i > 0) { + totalHeight += 0.25; + } + hlines.push({pos: totalHeight, isDashed: hlinesInGap[i]}); + } + } + setHLinePos(hLinesBeforeRow[0]); + + for (r = 0; r < group.body.length; ++r) { + const inrow = group.body[r]; + let height = arstrutHeight; // \@array adds an \@arstrut + let depth = arstrutDepth; // to each tow (via the template) + + if (nc < inrow.length) { + nc = inrow.length; + } + + const outrow: Outrow = (new Array(inrow.length): any); + for (c = 0; c < inrow.length; ++c) { + const elt = html.buildGroup(inrow[c], options); + if (depth < elt.depth) { + depth = elt.depth; + } + if (height < elt.height) { + height = elt.height; + } + outrow[c] = elt; + } + + const rowGap = group.rowGaps[r]; + let gap = 0; + if (rowGap) { + gap = calculateSize(rowGap, options); + if (gap > 0) { // \@argarraycr + gap += arstrutDepth; + if (depth < gap) { + depth = gap; // \@xargarraycr + } + gap = 0; + } + } + // In AMS multiline environments such as aligned and gathered, rows + // correspond to lines that have additional \jot added to the + // \baselineskip via \openup. + if (group.addJot) { + depth += jot; + } + + outrow.height = height; + outrow.depth = depth; + totalHeight += height; + outrow.pos = totalHeight; + totalHeight += depth + gap; // \@yargarraycr + body[r] = outrow; + + // Set a position for \hline(s), if any. + setHLinePos(hLinesBeforeRow[r + 1]); + } + + const offset = totalHeight / 2 + options.fontMetrics().axisHeight; + const colDescriptions = group.cols || []; + const cols = []; + let colSep; + let colDescrNum; + + const tagSpans = []; + if (group.tags && group.tags.some((tag) => tag)) { + // An environment with manual tags and/or automatic equation numbers. + // Create node(s), the latter of which trigger CSS counter increment. + for (r = 0; r < nr; ++r) { + const rw = body[r]; + const shift = rw.pos - offset; + const tag = group.tags[r]; + let tagSpan; + if (tag === true) { // automatic numbering + tagSpan = buildCommon.makeSpan(["eqn-num"], [], options); + } else if (tag === false) { + // \nonumber/\notag or starred environment + tagSpan = buildCommon.makeSpan([], [], options); + } else { // manual \tag + tagSpan = buildCommon.makeSpan([], + html.buildExpression(tag, options, true), options); + } + tagSpan.depth = rw.depth; + tagSpan.height = rw.height; + tagSpans.push({type: "elem", elem: tagSpan, shift}); + } + } + + for (c = 0, colDescrNum = 0; + // Continue while either there are more columns or more column + // descriptions, so trailing separators don't get lost. + c < nc || colDescrNum < colDescriptions.length; + ++c, ++colDescrNum) { + + let colDescr = colDescriptions[colDescrNum] || {}; + + let firstSeparator = true; + while (colDescr.type === "separator") { + // If there is more than one separator in a row, add a space + // between them. + if (!firstSeparator) { + colSep = buildCommon.makeSpan(["arraycolsep"], []); + colSep.style.width = + makeEm(options.fontMetrics().doubleRuleSep); + cols.push(colSep); + } + + if (colDescr.separator === "|" || colDescr.separator === ":") { + const lineType = (colDescr.separator === "|") ? "solid" : "dashed"; + const separator = buildCommon.makeSpan( + ["vertical-separator"], [], options + ); + separator.style.height = makeEm(totalHeight); + separator.style.borderRightWidth = makeEm(ruleThickness); + separator.style.borderRightStyle = lineType; + separator.style.margin = `0 ${makeEm(-ruleThickness / 2)}`; + const shift = totalHeight - offset; + if (shift) { + separator.style.verticalAlign = makeEm(-shift); + } + + cols.push(separator); + } else { + throw new ParseError( + "Invalid separator type: " + colDescr.separator); + } + + colDescrNum++; + colDescr = colDescriptions[colDescrNum] || {}; + firstSeparator = false; + } + + if (c >= nc) { + continue; + } + + let sepwidth; + if (c > 0 || group.hskipBeforeAndAfter) { + sepwidth = utils.deflt(colDescr.pregap, arraycolsep); + if (sepwidth !== 0) { + colSep = buildCommon.makeSpan(["arraycolsep"], []); + colSep.style.width = makeEm(sepwidth); + cols.push(colSep); + } + } + + let col = []; + for (r = 0; r < nr; ++r) { + const row = body[r]; + const elem = row[c]; + if (!elem) { + continue; + } + const shift = row.pos - offset; + elem.depth = row.depth; + elem.height = row.height; + col.push({type: "elem", elem: elem, shift: shift}); + } + + col = buildCommon.makeVList({ + positionType: "individualShift", + children: col, + }, options); + col = buildCommon.makeSpan( + ["col-align-" + (colDescr.align || "c")], + [col]); + cols.push(col); + + if (c < nc - 1 || group.hskipBeforeAndAfter) { + sepwidth = utils.deflt(colDescr.postgap, arraycolsep); + if (sepwidth !== 0) { + colSep = buildCommon.makeSpan(["arraycolsep"], []); + colSep.style.width = makeEm(sepwidth); + cols.push(colSep); + } + } + } + body = buildCommon.makeSpan(["mtable"], cols); + + // Add \hline(s), if any. + if (hlines.length > 0) { + const line = buildCommon.makeLineSpan("hline", options, ruleThickness); + const dashes = buildCommon.makeLineSpan("hdashline", options, + ruleThickness); + const vListElems = [{type: "elem", elem: body, shift: 0}]; + while (hlines.length > 0) { + const hline = hlines.pop(); + const lineShift = hline.pos - offset; + if (hline.isDashed) { + vListElems.push({type: "elem", elem: dashes, shift: lineShift}); + } else { + vListElems.push({type: "elem", elem: line, shift: lineShift}); + } + } + body = buildCommon.makeVList({ + positionType: "individualShift", + children: vListElems, + }, options); + } + + if (tagSpans.length === 0) { + return buildCommon.makeSpan(["mord"], [body], options); + } else { + let eqnNumCol = buildCommon.makeVList({ + positionType: "individualShift", + children: tagSpans, + }, options); + eqnNumCol = buildCommon.makeSpan(["tag"], [eqnNumCol], options); + return buildCommon.makeFragment([body, eqnNumCol]); + } +}; + +const alignMap = { + c: "center ", + l: "left ", + r: "right ", +}; + +const mathmlBuilder: MathMLBuilder<"array"> = function(group, options) { + const tbl = []; + const glue = new mathMLTree.MathNode("mtd", [], ["mtr-glue"]); + const tag = new mathMLTree.MathNode("mtd", [], ["mml-eqn-num"]); + for (let i = 0; i < group.body.length; i++) { + const rw = group.body[i]; + const row = []; + for (let j = 0; j < rw.length; j++) { + row.push(new mathMLTree.MathNode("mtd", + [mml.buildGroup(rw[j], options)])); + } + if (group.tags && group.tags[i]) { + row.unshift(glue); + row.push(glue); + if (group.leqno) { + row.unshift(tag); + } else { + row.push(tag); + } + } + tbl.push(new mathMLTree.MathNode("mtr", row)); + } + let table = new mathMLTree.MathNode("mtable", tbl); + + // Set column alignment, row spacing, column spacing, and + // array lines by setting attributes on the table element. + + // Set the row spacing. In MathML, we specify a gap distance. + // We do not use rowGap[] because MathML automatically increases + // cell height with the height/depth of the element content. + + // LaTeX \arraystretch multiplies the row baseline-to-baseline distance. + // We simulate this by adding (arraystretch - 1)em to the gap. This + // does a reasonable job of adjusting arrays containing 1 em tall content. + + // The 0.16 and 0.09 values are found empirically. They produce an array + // similar to LaTeX and in which content does not interfere with \hlines. + const gap = (group.arraystretch === 0.5) + ? 0.1 // {smallmatrix}, {subarray} + : 0.16 + group.arraystretch - 1 + (group.addJot ? 0.09 : 0); + table.setAttribute("rowspacing", makeEm(gap)); + + // MathML table lines go only between cells. + // To place a line on an edge we'll use , if necessary. + let menclose = ""; + let align = ""; + + if (group.cols && group.cols.length > 0) { + // Find column alignment, column spacing, and vertical lines. + const cols = group.cols; + let columnLines = ""; + let prevTypeWasAlign = false; + let iStart = 0; + let iEnd = cols.length; + + if (cols[0].type === "separator") { + menclose += "top "; + iStart = 1; + } + if (cols[cols.length - 1].type === "separator") { + menclose += "bottom "; + iEnd -= 1; + } + + for (let i = iStart; i < iEnd; i++) { + if (cols[i].type === "align") { + align += alignMap[cols[i].align]; + + if (prevTypeWasAlign) { + columnLines += "none "; + } + prevTypeWasAlign = true; + } else if (cols[i].type === "separator") { + // MathML accepts only single lines between cells. + // So we read only the first of consecutive separators. + if (prevTypeWasAlign) { + columnLines += cols[i].separator === "|" + ? "solid " + : "dashed "; + prevTypeWasAlign = false; + } + } + } + + table.setAttribute("columnalign", align.trim()); + + if (/[sd]/.test(columnLines)) { + table.setAttribute("columnlines", columnLines.trim()); + } + } + + // Set column spacing. + if (group.colSeparationType === "align") { + const cols = group.cols || []; + let spacing = ""; + for (let i = 1; i < cols.length; i++) { + spacing += i % 2 ? "0em " : "1em "; + } + table.setAttribute("columnspacing", spacing.trim()); + } else if (group.colSeparationType === "alignat" || + group.colSeparationType === "gather") { + table.setAttribute("columnspacing", "0em"); + } else if (group.colSeparationType === "small") { + table.setAttribute("columnspacing", "0.2778em"); + } else if (group.colSeparationType === "CD") { + table.setAttribute("columnspacing", "0.5em"); + } else { + table.setAttribute("columnspacing", "1em"); + } + + // Address \hline and \hdashline + let rowLines = ""; + const hlines = group.hLinesBeforeRow; + + menclose += hlines[0].length > 0 ? "left " : ""; + menclose += hlines[hlines.length - 1].length > 0 ? "right " : ""; + + for (let i = 1; i < hlines.length - 1; i++) { + rowLines += (hlines[i].length === 0) + ? "none " + // MathML accepts only a single line between rows. Read one element. + : hlines[i][0] ? "dashed " : "solid "; + } + if (/[sd]/.test(rowLines)) { + table.setAttribute("rowlines", rowLines.trim()); + } + + if (menclose !== "") { + table = new mathMLTree.MathNode("menclose", [table]); + table.setAttribute("notation", menclose.trim()); + } + + if (group.arraystretch && group.arraystretch < 1) { + // A small array. Wrap in scriptstyle so row gap is not too large. + table = new mathMLTree.MathNode("mstyle", [table]); + table.setAttribute("scriptlevel", "1"); + } + + return table; +}; + +// Convenience function for align, align*, aligned, alignat, alignat*, alignedat. +const alignedHandler = function(context, args) { + if (context.envName.indexOf("ed") === -1) { + validateAmsEnvironmentContext(context); + } + const cols = []; + const separationType = context.envName.indexOf("at") > -1 ? "alignat" : "align"; + const isSplit = context.envName === "split"; + const res = parseArray(context.parser, + { + cols, + addJot: true, + autoTag: isSplit ? undefined : getAutoTag(context.envName), + emptySingleRow: true, + colSeparationType: separationType, + maxNumCols: isSplit ? 2 : undefined, + leqno: context.parser.settings.leqno, + }, + "display" + ); + + // Determining number of columns. + // 1. If the first argument is given, we use it as a number of columns, + // and makes sure that each row doesn't exceed that number. + // 2. Otherwise, just count number of columns = maximum number + // of cells in each row ("aligned" mode -- isAligned will be true). + // + // At the same time, prepend empty group {} at beginning of every second + // cell in each row (starting with second cell) so that operators become + // binary. This behavior is implemented in amsmath's \start@aligned. + let numMaths; + let numCols = 0; + const emptyGroup = { + type: "ordgroup", + mode: context.mode, + body: [], + }; + if (args[0] && args[0].type === "ordgroup") { + let arg0 = ""; + for (let i = 0; i < args[0].body.length; i++) { + const textord = assertNodeType(args[0].body[i], "textord"); + arg0 += textord.text; + } + numMaths = Number(arg0); + numCols = numMaths * 2; + } + const isAligned = !numCols; + res.body.forEach(function(row) { + for (let i = 1; i < row.length; i += 2) { + // Modify ordgroup node within styling node + const styling = assertNodeType(row[i], "styling"); + const ordgroup = assertNodeType(styling.body[0], "ordgroup"); + ordgroup.body.unshift(emptyGroup); + } + if (!isAligned) { // Case 1 + const curMaths = row.length / 2; + if (numMaths < curMaths) { + throw new ParseError( + "Too many math in a row: " + + `expected ${numMaths}, but got ${curMaths}`, + row[0]); + } + } else if (numCols < row.length) { // Case 2 + numCols = row.length; + } + }); + + // Adjusting alignment. + // In aligned mode, we add one \qquad between columns; + // otherwise we add nothing. + for (let i = 0; i < numCols; ++i) { + let align = "r"; + let pregap = 0; + if (i % 2 === 1) { + align = "l"; + } else if (i > 0 && isAligned) { // "aligned" mode. + pregap = 1; // add one \quad + } + cols[i] = { + type: "align", + align: align, + pregap: pregap, + postgap: 0, + }; + } + res.colSeparationType = isAligned ? "align" : "alignat"; + return res; +}; + +// Arrays are part of LaTeX, defined in lttab.dtx so its documentation +// is part of the source2e.pdf file of LaTeX2e source documentation. +// {darray} is an {array} environment where cells are set in \displaystyle, +// as defined in nccmath.sty. +defineEnvironment({ + type: "array", + names: ["array", "darray"], + props: { + numArgs: 1, + }, + handler(context, args) { + // Since no types are specified above, the two possibilities are + // - The argument is wrapped in {} or [], in which case Parser's + // parseGroup() returns an "ordgroup" wrapping some symbol node. + // - The argument is a bare symbol node. + const symNode = checkSymbolNodeType(args[0]); + const colalign: AnyParseNode[] = + symNode ? [args[0]] : assertNodeType(args[0], "ordgroup").body; + const cols = colalign.map(function(nde) { + const node = assertSymbolNodeType(nde); + const ca = node.text; + if ("lcr".indexOf(ca) !== -1) { + return { + type: "align", + align: ca, + }; + } else if (ca === "|") { + return { + type: "separator", + separator: "|", + }; + } else if (ca === ":") { + return { + type: "separator", + separator: ":", + }; + } + throw new ParseError("Unknown column alignment: " + ca, nde); + }); + const res = { + cols, + hskipBeforeAndAfter: true, // \@preamble in lttab.dtx + maxNumCols: cols.length, + }; + return parseArray(context.parser, res, dCellStyle(context.envName)); + }, + htmlBuilder, + mathmlBuilder, +}); + +// The matrix environments of amsmath builds on the array environment +// of LaTeX, which is discussed above. +// The mathtools package adds starred versions of the same environments. +// These have an optional argument to choose left|center|right justification. +defineEnvironment({ + type: "array", + names: [ + "matrix", + "pmatrix", + "bmatrix", + "Bmatrix", + "vmatrix", + "Vmatrix", + "matrix*", + "pmatrix*", + "bmatrix*", + "Bmatrix*", + "vmatrix*", + "Vmatrix*", + ], + props: { + numArgs: 0, + }, + handler(context) { + const delimiters = { + "matrix": null, + "pmatrix": ["(", ")"], + "bmatrix": ["[", "]"], + "Bmatrix": ["\\{", "\\}"], + "vmatrix": ["|", "|"], + "Vmatrix": ["\\Vert", "\\Vert"], + }[context.envName.replace("*", "")]; + // \hskip -\arraycolsep in amsmath + let colAlign = "c"; + const payload = { + hskipBeforeAndAfter: false, + cols: [{type: "align", align: colAlign}], + }; + if (context.envName.charAt(context.envName.length - 1) === "*") { + // It's one of the mathtools starred functions. + // Parse the optional alignment argument. + const parser = context.parser; + parser.consumeSpaces(); + if (parser.fetch().text === "[") { + parser.consume(); + parser.consumeSpaces(); + colAlign = parser.fetch().text; + if ("lcr".indexOf(colAlign) === -1) { + throw new ParseError("Expected l or c or r", parser.nextToken); + } + parser.consume(); + parser.consumeSpaces(); + parser.expect("]"); + parser.consume(); + payload.cols = [{type: "align", align: colAlign}]; + } + } + const res: ParseNode<"array"> = + parseArray(context.parser, payload, dCellStyle(context.envName)); + // Populate cols with the correct number of column alignment specs. + const numCols = Math.max(0, ...res.body.map((row) => row.length)); + res.cols = new Array(numCols).fill( + {type: "align", align: colAlign} + ); + return delimiters ? { + type: "leftright", + mode: context.mode, + body: [res], + left: delimiters[0], + right: delimiters[1], + rightColor: undefined, // \right uninfluenced by \color in array + } : res; + }, + htmlBuilder, + mathmlBuilder, +}); + +defineEnvironment({ + type: "array", + names: ["smallmatrix"], + props: { + numArgs: 0, + }, + handler(context) { + const payload = {arraystretch: 0.5}; + const res = parseArray(context.parser, payload, "script"); + res.colSeparationType = "small"; + return res; + }, + htmlBuilder, + mathmlBuilder, +}); + +defineEnvironment({ + type: "array", + names: ["subarray"], + props: { + numArgs: 1, + }, + handler(context, args) { + // Parsing of {subarray} is similar to {array} + const symNode = checkSymbolNodeType(args[0]); + const colalign: AnyParseNode[] = + symNode ? [args[0]] : assertNodeType(args[0], "ordgroup").body; + const cols = colalign.map(function(nde) { + const node = assertSymbolNodeType(nde); + const ca = node.text; + // {subarray} only recognizes "l" & "c" + if ("lc".indexOf(ca) !== -1) { + return { + type: "align", + align: ca, + }; + } + throw new ParseError("Unknown column alignment: " + ca, nde); + }); + if (cols.length > 1) { + throw new ParseError("{subarray} can contain only one column"); + } + let res = { + cols, + hskipBeforeAndAfter: false, + arraystretch: 0.5, + }; + res = parseArray(context.parser, res, "script"); + if (res.body.length > 0 && res.body[0].length > 1) { + throw new ParseError("{subarray} can contain only one column"); + } + return res; + }, + htmlBuilder, + mathmlBuilder, +}); + +// A cases environment (in amsmath.sty) is almost equivalent to +// \def\arraystretch{1.2}% +// \left\{\begin{array}{@{}l@{\quad}l@{}} … \end{array}\right. +// {dcases} is a {cases} environment where cells are set in \displaystyle, +// as defined in mathtools.sty. +// {rcases} is another mathtools environment. It's brace is on the right side. +defineEnvironment({ + type: "array", + names: [ + "cases", + "dcases", + "rcases", + "drcases", + ], + props: { + numArgs: 0, + }, + handler(context) { + const payload = { + arraystretch: 1.2, + cols: [{ + type: "align", + align: "l", + pregap: 0, + // TODO(kevinb) get the current style. + // For now we use the metrics for TEXT style which is what we were + // doing before. Before attempting to get the current style we + // should look at TeX's behavior especially for \over and matrices. + postgap: 1.0, /* 1em quad */ + }, { + type: "align", + align: "l", + pregap: 0, + postgap: 0, + }], + }; + const res: ParseNode<"array"> = + parseArray(context.parser, payload, dCellStyle(context.envName)); + return { + type: "leftright", + mode: context.mode, + body: [res], + left: context.envName.indexOf("r") > -1 ? "." : "\\{", + right: context.envName.indexOf("r") > -1 ? "\\}" : ".", + rightColor: undefined, + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +// In the align environment, one uses ampersands, &, to specify number of +// columns in each row, and to locate spacing between each column. +// align gets automatic numbering. align* and aligned do not. +// The alignedat environment can be used in math mode. +// Note that we assume \nomallineskiplimit to be zero, +// so that \strut@ is the same as \strut. +defineEnvironment({ + type: "array", + names: ["align", "align*", "aligned", "split"], + props: { + numArgs: 0, + }, + handler: alignedHandler, + htmlBuilder, + mathmlBuilder, +}); + +// A gathered environment is like an array environment with one centered +// column, but where rows are considered lines so get \jot line spacing +// and contents are set in \displaystyle. +defineEnvironment({ + type: "array", + names: ["gathered", "gather", "gather*"], + props: { + numArgs: 0, + }, + handler(context) { + if (utils.contains(["gather", "gather*"], context.envName)) { + validateAmsEnvironmentContext(context); + } + const res = { + cols: [{ + type: "align", + align: "c", + }], + addJot: true, + colSeparationType: "gather", + autoTag: getAutoTag(context.envName), + emptySingleRow: true, + leqno: context.parser.settings.leqno, + }; + return parseArray(context.parser, res, "display"); + }, + htmlBuilder, + mathmlBuilder, +}); + +// alignat environment is like an align environment, but one must explicitly +// specify maximum number of columns in each row, and can adjust spacing between +// each columns. +defineEnvironment({ + type: "array", + names: ["alignat", "alignat*", "alignedat"], + props: { + numArgs: 1, + }, + handler: alignedHandler, + htmlBuilder, + mathmlBuilder, +}); + +defineEnvironment({ + type: "array", + names: ["equation", "equation*"], + props: { + numArgs: 0, + }, + handler(context) { + validateAmsEnvironmentContext(context); + const res = { + autoTag: getAutoTag(context.envName), + emptySingleRow: true, + singleRow: true, + maxNumCols: 1, + leqno: context.parser.settings.leqno, + }; + return parseArray(context.parser, res, "display"); + }, + htmlBuilder, + mathmlBuilder, +}); + +defineEnvironment({ + type: "array", + names: ["CD"], + props: { + numArgs: 0, + }, + handler(context) { + validateAmsEnvironmentContext(context); + return parseCD(context.parser); + }, + htmlBuilder, + mathmlBuilder, +}); + +defineMacro("\\nonumber", "\\gdef\\@eqnsw{0}"); +defineMacro("\\notag", "\\nonumber"); + +// Catch \hline outside array environment +defineFunction({ + type: "text", // Doesn't matter what this is. + names: ["\\hline", "\\hdashline"], + props: { + numArgs: 0, + allowedInText: true, + allowedInMath: true, + }, + handler(context, args) { + throw new ParseError( + `${context.funcName} valid only within array environment`); + }, +}); diff --git a/frontend/node_modules/katex/src/environments/cd.js b/frontend/node_modules/katex/src/environments/cd.js new file mode 100644 index 0000000..159ca6b --- /dev/null +++ b/frontend/node_modules/katex/src/environments/cd.js @@ -0,0 +1,313 @@ +// @flow +import buildCommon from "../buildCommon"; +import defineFunction from "../defineFunction"; +import mathMLTree from "../mathMLTree"; +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; +import {assertSymbolNodeType} from "../parseNode"; +import ParseError from "../ParseError"; +import {makeEm} from "../units"; + +import type Parser from "../Parser"; +import type {ParseNode, AnyParseNode} from "../parseNode"; + +const cdArrowFunctionName = { + ">": "\\\\cdrightarrow", + "<": "\\\\cdleftarrow", + "=": "\\\\cdlongequal", + "A": "\\uparrow", + "V": "\\downarrow", + "|": "\\Vert", + ".": "no arrow", +}; + +const newCell = () => { + // Create an empty cell, to be filled below with parse nodes. + // The parseTree from this module must be constructed like the + // one created by parseArray(), so an empty CD cell must + // be a ParseNode<"styling">. And CD is always displaystyle. + // So these values are fixed and flow can do implicit typing. + return {type: "styling", body: [], mode: "math", style: "display"}; +}; + +const isStartOfArrow = (node: AnyParseNode) => { + return (node.type === "textord" && node.text === "@"); +}; + +const isLabelEnd = (node: AnyParseNode, endChar: string): boolean => { + return ((node.type === "mathord" || node.type === "atom") && + node.text === endChar); +}; + +function cdArrow( + arrowChar: string, + labels: ParseNode<"ordgroup">[], + parser: Parser +): AnyParseNode { + // Return a parse tree of an arrow and its labels. + // This acts in a way similar to a macro expansion. + const funcName = cdArrowFunctionName[arrowChar]; + switch (funcName) { + case "\\\\cdrightarrow": + case "\\\\cdleftarrow": + return parser.callFunction( + funcName, [labels[0]], [labels[1]] + ); + case "\\uparrow": + case "\\downarrow": { + const leftLabel = parser.callFunction( + "\\\\cdleft", [labels[0]], [] + ); + const bareArrow = { + type: "atom", + text: funcName, + mode: "math", + family: "rel", + }; + const sizedArrow = parser.callFunction("\\Big", [bareArrow], []); + const rightLabel = parser.callFunction( + "\\\\cdright", [labels[1]], [] + ); + const arrowGroup = { + type: "ordgroup", + mode: "math", + body: [leftLabel, sizedArrow, rightLabel], + }; + return parser.callFunction("\\\\cdparent", [arrowGroup], []); + } + case "\\\\cdlongequal": + return parser.callFunction("\\\\cdlongequal", [], []); + case "\\Vert": { + const arrow = {type: "textord", text: "\\Vert", mode: "math"}; + return parser.callFunction("\\Big", [arrow], []); + } + default: + return {type: "textord", text: " ", mode: "math"}; + } +} + +export function parseCD(parser: Parser): ParseNode<"array"> { + // Get the array's parse nodes with \\ temporarily mapped to \cr. + const parsedRows: AnyParseNode[][] = []; + parser.gullet.beginGroup(); + parser.gullet.macros.set("\\cr", "\\\\\\relax"); + parser.gullet.beginGroup(); + while (true) { // eslint-disable-line no-constant-condition + // Get the parse nodes for the next row. + parsedRows.push(parser.parseExpression(false, "\\\\")); + parser.gullet.endGroup(); + parser.gullet.beginGroup(); + const next = parser.fetch().text; + if (next === "&" || next === "\\\\") { + parser.consume(); + } else if (next === "\\end") { + if (parsedRows[parsedRows.length - 1].length === 0) { + parsedRows.pop(); // final row ended in \\ + } + break; + } else { + throw new ParseError("Expected \\\\ or \\cr or \\end", + parser.nextToken); + } + } + + let row = []; + const body = [row]; + + // Loop thru the parse nodes. Collect them into cells and arrows. + for (let i = 0; i < parsedRows.length; i++) { + // Start a new row. + const rowNodes = parsedRows[i]; + // Create the first cell. + let cell = newCell(); + + for (let j = 0; j < rowNodes.length; j++) { + if (!isStartOfArrow(rowNodes[j])) { + // If a parseNode is not an arrow, it goes into a cell. + cell.body.push(rowNodes[j]); + } else { + // Parse node j is an "@", the start of an arrow. + // Before starting on the arrow, push the cell into `row`. + row.push(cell); + + // Now collect parseNodes into an arrow. + // The character after "@" defines the arrow type. + j += 1; + const arrowChar = assertSymbolNodeType(rowNodes[j]).text; + + // Create two empty label nodes. We may or may not use them. + const labels: ParseNode<"ordgroup">[] = new Array(2); + labels[0] = {type: "ordgroup", mode: "math", body: []}; + labels[1] = {type: "ordgroup", mode: "math", body: []}; + + // Process the arrow. + if ("=|.".indexOf(arrowChar) > -1) { + // Three "arrows", ``@=`, `@|`, and `@.`, do not take labels. + // Do nothing here. + } else if ("<>AV".indexOf(arrowChar) > -1) { + // Four arrows, `@>>>`, `@<<<`, `@AAA`, and `@VVV`, each take + // two optional labels. E.g. the right-point arrow syntax is + // really: @>{optional label}>{optional label}> + // Collect parseNodes into labels. + for (let labelNum = 0; labelNum < 2; labelNum++) { + let inLabel = true; + for (let k = j + 1; k < rowNodes.length; k++) { + if (isLabelEnd(rowNodes[k], arrowChar)) { + inLabel = false; + j = k; + break; + } + if (isStartOfArrow(rowNodes[k])) { + throw new ParseError("Missing a " + arrowChar + + " character to complete a CD arrow.", rowNodes[k]); + } + + labels[labelNum].body.push(rowNodes[k]); + } + if (inLabel) { + // isLabelEnd never returned a true. + throw new ParseError("Missing a " + arrowChar + + " character to complete a CD arrow.", rowNodes[j]); + } + } + } else { + throw new ParseError(`Expected one of "<>AV=|." after @`, + rowNodes[j]); + } + + // Now join the arrow to its labels. + const arrow: AnyParseNode = cdArrow(arrowChar, labels, parser); + + // Wrap the arrow in ParseNode<"styling">. + // This is done to match parseArray() behavior. + const wrappedArrow = { + type: "styling", + body: [arrow], + mode: "math", + style: "display", // CD is always displaystyle. + }; + row.push(wrappedArrow); + // In CD's syntax, cells are implicit. That is, everything that + // is not an arrow gets collected into a cell. So create an empty + // cell now. It will collect upcoming parseNodes. + cell = newCell(); + } + } + if (i % 2 === 0) { + // Even-numbered rows consist of: cell, arrow, cell, arrow, ... cell + // The last cell is not yet pushed into `row`, so: + row.push(cell); + } else { + // Odd-numbered rows consist of: vert arrow, empty cell, ... vert arrow + // Remove the empty cell that was placed at the beginning of `row`. + row.shift(); + } + row = []; + body.push(row); + } + + // End row group + parser.gullet.endGroup(); + // End array group defining \\ + parser.gullet.endGroup(); + + // define column separation. + const cols = new Array(body[0].length).fill({ + type: "align", + align: "c", + pregap: 0.25, // CD package sets \enskip between columns. + postgap: 0.25, // So pre and post each get half an \enskip, i.e. 0.25em. + }); + + return { + type: "array", + mode: "math", + body, + arraystretch: 1, + addJot: true, + rowGaps: [null], + cols, + colSeparationType: "CD", + hLinesBeforeRow: new Array(body.length + 1).fill([]), + }; +} + +// The functions below are not available for general use. +// They are here only for internal use by the {CD} environment in placing labels +// next to vertical arrows. + +// We don't need any such functions for horizontal arrows because we can reuse +// the functionality that already exists for extensible arrows. + +defineFunction({ + type: "cdlabel", + names: ["\\\\cdleft", "\\\\cdright"], + props: { + numArgs: 1, + }, + handler({parser, funcName}, args) { + return { + type: "cdlabel", + mode: parser.mode, + side: funcName.slice(4), + label: args[0], + }; + }, + htmlBuilder(group, options) { + const newOptions = options.havingStyle(options.style.sup()); + const label = buildCommon.wrapFragment( + html.buildGroup(group.label, newOptions, options), options); + label.classes.push("cd-label-" + group.side); + label.style.bottom = makeEm(0.8 - label.depth); + // Zero out label height & depth, so vertical align of arrow is set + // by the arrow height, not by the label. + label.height = 0; + label.depth = 0; + return label; + }, + mathmlBuilder(group, options) { + let label = new mathMLTree.MathNode("mrow", + [mml.buildGroup(group.label, options)]); + label = new mathMLTree.MathNode("mpadded", [label]); + label.setAttribute("width", "0"); + if (group.side === "left") { + label.setAttribute("lspace", "-1width"); + } + // We have to guess at vertical alignment. We know the arrow is 1.8em tall, + // But we don't know the height or depth of the label. + label.setAttribute("voffset", "0.7em"); + label = new mathMLTree.MathNode("mstyle", [label]); + label.setAttribute("displaystyle", "false"); + label.setAttribute("scriptlevel", "1"); + return label; + }, +}); + +defineFunction({ + type: "cdlabelparent", + names: ["\\\\cdparent"], + props: { + numArgs: 1, + }, + handler({parser}, args) { + return { + type: "cdlabelparent", + mode: parser.mode, + fragment: args[0], + }; + }, + htmlBuilder(group, options) { + // Wrap the vertical arrow and its labels. + // The parent gets position: relative. The child gets position: absolute. + // So CSS can locate the label correctly. + const parent = buildCommon.wrapFragment( + html.buildGroup(group.fragment, options), options + ); + parent.classes.push("cd-vert-arrow"); + return parent; + }, + mathmlBuilder(group, options) { + return new mathMLTree.MathNode("mrow", + [mml.buildGroup(group.fragment, options)]); + }, +}); diff --git a/frontend/node_modules/katex/src/fontMetrics.js b/frontend/node_modules/katex/src/fontMetrics.js new file mode 100644 index 0000000..1c3162c --- /dev/null +++ b/frontend/node_modules/katex/src/fontMetrics.js @@ -0,0 +1,282 @@ +// @flow +import {supportedCodepoint} from "./unicodeScripts"; + +import type {Mode} from "./types"; + +/** + * This file contains metrics regarding fonts and individual symbols. The sigma + * and xi variables, as well as the metricMap map contain data extracted from + * TeX, TeX font metrics, and the TTF files. These data are then exposed via the + * `metrics` variable and the getCharacterMetrics function. + */ + +// In TeX, there are actually three sets of dimensions, one for each of +// textstyle (size index 5 and higher: >=9pt), scriptstyle (size index 3 and 4: +// 7-8pt), and scriptscriptstyle (size index 1 and 2: 5-6pt). These are +// provided in the arrays below, in that order. +// +// The font metrics are stored in fonts cmsy10, cmsy7, and cmsy5 respectively. +// This was determined by running the following script: +// +// latex -interaction=nonstopmode \ +// '\documentclass{article}\usepackage{amsmath}\begin{document}' \ +// '$a$ \expandafter\show\the\textfont2' \ +// '\expandafter\show\the\scriptfont2' \ +// '\expandafter\show\the\scriptscriptfont2' \ +// '\stop' +// +// The metrics themselves were retrieved using the following commands: +// +// tftopl cmsy10 +// tftopl cmsy7 +// tftopl cmsy5 +// +// The output of each of these commands is quite lengthy. The only part we +// care about is the FONTDIMEN section. Each value is measured in EMs. +const sigmasAndXis = { + slant: [0.250, 0.250, 0.250], // sigma1 + space: [0.000, 0.000, 0.000], // sigma2 + stretch: [0.000, 0.000, 0.000], // sigma3 + shrink: [0.000, 0.000, 0.000], // sigma4 + xHeight: [0.431, 0.431, 0.431], // sigma5 + quad: [1.000, 1.171, 1.472], // sigma6 + extraSpace: [0.000, 0.000, 0.000], // sigma7 + num1: [0.677, 0.732, 0.925], // sigma8 + num2: [0.394, 0.384, 0.387], // sigma9 + num3: [0.444, 0.471, 0.504], // sigma10 + denom1: [0.686, 0.752, 1.025], // sigma11 + denom2: [0.345, 0.344, 0.532], // sigma12 + sup1: [0.413, 0.503, 0.504], // sigma13 + sup2: [0.363, 0.431, 0.404], // sigma14 + sup3: [0.289, 0.286, 0.294], // sigma15 + sub1: [0.150, 0.143, 0.200], // sigma16 + sub2: [0.247, 0.286, 0.400], // sigma17 + supDrop: [0.386, 0.353, 0.494], // sigma18 + subDrop: [0.050, 0.071, 0.100], // sigma19 + delim1: [2.390, 1.700, 1.980], // sigma20 + delim2: [1.010, 1.157, 1.420], // sigma21 + axisHeight: [0.250, 0.250, 0.250], // sigma22 + + // These font metrics are extracted from TeX by using tftopl on cmex10.tfm; + // they correspond to the font parameters of the extension fonts (family 3). + // See the TeXbook, page 441. In AMSTeX, the extension fonts scale; to + // match cmex7, we'd use cmex7.tfm values for script and scriptscript + // values. + defaultRuleThickness: [0.04, 0.049, 0.049], // xi8; cmex7: 0.049 + bigOpSpacing1: [0.111, 0.111, 0.111], // xi9 + bigOpSpacing2: [0.166, 0.166, 0.166], // xi10 + bigOpSpacing3: [0.2, 0.2, 0.2], // xi11 + bigOpSpacing4: [0.6, 0.611, 0.611], // xi12; cmex7: 0.611 + bigOpSpacing5: [0.1, 0.143, 0.143], // xi13; cmex7: 0.143 + + // The \sqrt rule width is taken from the height of the surd character. + // Since we use the same font at all sizes, this thickness doesn't scale. + sqrtRuleThickness: [0.04, 0.04, 0.04], + + // This value determines how large a pt is, for metrics which are defined + // in terms of pts. + // This value is also used in katex.scss; if you change it make sure the + // values match. + ptPerEm: [10.0, 10.0, 10.0], + + // The space between adjacent `|` columns in an array definition. From + // `\showthe\doublerulesep` in LaTeX. Equals 2.0 / ptPerEm. + doubleRuleSep: [0.2, 0.2, 0.2], + + // The width of separator lines in {array} environments. From + // `\showthe\arrayrulewidth` in LaTeX. Equals 0.4 / ptPerEm. + arrayRuleWidth: [0.04, 0.04, 0.04], + + // Two values from LaTeX source2e: + fboxsep: [0.3, 0.3, 0.3], // 3 pt / ptPerEm + fboxrule: [0.04, 0.04, 0.04], // 0.4 pt / ptPerEm +}; + +// This map contains a mapping from font name and character code to character +// metrics, including height, depth, italic correction, and skew (kern from the +// character to the corresponding \skewchar) +// This map is generated via `make metrics`. It should not be changed manually. +import metricMap from "./fontMetricsData"; + +// These are very rough approximations. We default to Times New Roman which +// should have Latin-1 and Cyrillic characters, but may not depending on the +// operating system. The metrics do not account for extra height from the +// accents. In the case of Cyrillic characters which have both ascenders and +// descenders we prefer approximations with ascenders, primarily to prevent +// the fraction bar or root line from intersecting the glyph. +// TODO(kevinb) allow union of multiple glyph metrics for better accuracy. +const extraCharacterMap = { + // Latin-1 + 'Å': 'A', + 'Ð': 'D', + 'Þ': 'o', + 'å': 'a', + 'ð': 'd', + 'þ': 'o', + + // Cyrillic + 'А': 'A', + 'Б': 'B', + 'В': 'B', + 'Г': 'F', + 'Д': 'A', + 'Е': 'E', + 'Ж': 'K', + 'З': '3', + 'И': 'N', + 'Й': 'N', + 'К': 'K', + 'Л': 'N', + 'М': 'M', + 'Н': 'H', + 'О': 'O', + 'П': 'N', + 'Р': 'P', + 'С': 'C', + 'Т': 'T', + 'У': 'y', + 'Ф': 'O', + 'Х': 'X', + 'Ц': 'U', + 'Ч': 'h', + 'Ш': 'W', + 'Щ': 'W', + 'Ъ': 'B', + 'Ы': 'X', + 'Ь': 'B', + 'Э': '3', + 'Ю': 'X', + 'Я': 'R', + 'а': 'a', + 'б': 'b', + 'в': 'a', + 'г': 'r', + 'д': 'y', + 'е': 'e', + 'ж': 'm', + 'з': 'e', + 'и': 'n', + 'й': 'n', + 'к': 'n', + 'л': 'n', + 'м': 'm', + 'н': 'n', + 'о': 'o', + 'п': 'n', + 'р': 'p', + 'с': 'c', + 'т': 'o', + 'у': 'y', + 'ф': 'b', + 'х': 'x', + 'ц': 'n', + 'ч': 'n', + 'ш': 'w', + 'щ': 'w', + 'ъ': 'a', + 'ы': 'm', + 'ь': 'a', + 'э': 'e', + 'ю': 'm', + 'я': 'r', +}; + +export type CharacterMetrics = { + depth: number; + height: number; + italic: number; + skew: number; + width: number; +}; + +export type MetricMap = { + [string]: number[] +} + +/** + * This function adds new font metrics to default metricMap + * It can also override existing metrics + */ +export function setFontMetrics(fontName: string, metrics: MetricMap) { + metricMap[fontName] = metrics; +} + +/** + * This function is a convenience function for looking up information in the + * metricMap table. It takes a character as a string, and a font. + * + * Note: the `width` property may be undefined if fontMetricsData.js wasn't + * built using `Make extended_metrics`. + */ +export function getCharacterMetrics( + character: string, + font: string, + mode: Mode, +): ?CharacterMetrics { + if (!metricMap[font]) { + throw new Error(`Font metrics not found for font: ${font}.`); + } + let ch = character.charCodeAt(0); + let metrics = metricMap[font][ch]; + if (!metrics && character[0] in extraCharacterMap) { + ch = extraCharacterMap[character[0]].charCodeAt(0); + metrics = metricMap[font][ch]; + } + + if (!metrics && mode === 'text') { + // We don't typically have font metrics for Asian scripts. + // But since we support them in text mode, we need to return + // some sort of metrics. + // So if the character is in a script we support but we + // don't have metrics for it, just use the metrics for + // the Latin capital letter M. This is close enough because + // we (currently) only care about the height of the glyph + // not its width. + if (supportedCodepoint(ch)) { + metrics = metricMap[font][77]; // 77 is the charcode for 'M' + } + } + + if (metrics) { + return { + depth: metrics[0], + height: metrics[1], + italic: metrics[2], + skew: metrics[3], + width: metrics[4], + }; + } +} + +type FontSizeIndex = 0 | 1 | 2; +export type FontMetrics = { + cssEmPerMu: number, + [string]: number, +}; + +const fontMetricsBySizeIndex: {[FontSizeIndex]: FontMetrics} = {}; + +/** + * Get the font metrics for a given size. + */ +export function getGlobalMetrics(size: number): FontMetrics { + let sizeIndex: FontSizeIndex; + if (size >= 5) { + sizeIndex = 0; + } else if (size >= 3) { + sizeIndex = 1; + } else { + sizeIndex = 2; + } + if (!fontMetricsBySizeIndex[sizeIndex]) { + const metrics = fontMetricsBySizeIndex[sizeIndex] = { + cssEmPerMu: sigmasAndXis.quad[sizeIndex] / 18, + }; + for (const key in sigmasAndXis) { + if (sigmasAndXis.hasOwnProperty(key)) { + metrics[key] = sigmasAndXis[key][sizeIndex]; + } + } + } + return fontMetricsBySizeIndex[sizeIndex]; +} diff --git a/frontend/node_modules/katex/src/fontMetricsData.js b/frontend/node_modules/katex/src/fontMetricsData.js new file mode 100644 index 0000000..2557245 --- /dev/null +++ b/frontend/node_modules/katex/src/fontMetricsData.js @@ -0,0 +1,2077 @@ +// This file is GENERATED by buildMetrics.sh. DO NOT MODIFY. +export default { + "AMS-Regular": { + "32": [0, 0, 0, 0, 0.25], + "65": [0, 0.68889, 0, 0, 0.72222], + "66": [0, 0.68889, 0, 0, 0.66667], + "67": [0, 0.68889, 0, 0, 0.72222], + "68": [0, 0.68889, 0, 0, 0.72222], + "69": [0, 0.68889, 0, 0, 0.66667], + "70": [0, 0.68889, 0, 0, 0.61111], + "71": [0, 0.68889, 0, 0, 0.77778], + "72": [0, 0.68889, 0, 0, 0.77778], + "73": [0, 0.68889, 0, 0, 0.38889], + "74": [0.16667, 0.68889, 0, 0, 0.5], + "75": [0, 0.68889, 0, 0, 0.77778], + "76": [0, 0.68889, 0, 0, 0.66667], + "77": [0, 0.68889, 0, 0, 0.94445], + "78": [0, 0.68889, 0, 0, 0.72222], + "79": [0.16667, 0.68889, 0, 0, 0.77778], + "80": [0, 0.68889, 0, 0, 0.61111], + "81": [0.16667, 0.68889, 0, 0, 0.77778], + "82": [0, 0.68889, 0, 0, 0.72222], + "83": [0, 0.68889, 0, 0, 0.55556], + "84": [0, 0.68889, 0, 0, 0.66667], + "85": [0, 0.68889, 0, 0, 0.72222], + "86": [0, 0.68889, 0, 0, 0.72222], + "87": [0, 0.68889, 0, 0, 1.0], + "88": [0, 0.68889, 0, 0, 0.72222], + "89": [0, 0.68889, 0, 0, 0.72222], + "90": [0, 0.68889, 0, 0, 0.66667], + "107": [0, 0.68889, 0, 0, 0.55556], + "160": [0, 0, 0, 0, 0.25], + "165": [0, 0.675, 0.025, 0, 0.75], + "174": [0.15559, 0.69224, 0, 0, 0.94666], + "240": [0, 0.68889, 0, 0, 0.55556], + "295": [0, 0.68889, 0, 0, 0.54028], + "710": [0, 0.825, 0, 0, 2.33334], + "732": [0, 0.9, 0, 0, 2.33334], + "770": [0, 0.825, 0, 0, 2.33334], + "771": [0, 0.9, 0, 0, 2.33334], + "989": [0.08167, 0.58167, 0, 0, 0.77778], + "1008": [0, 0.43056, 0.04028, 0, 0.66667], + "8245": [0, 0.54986, 0, 0, 0.275], + "8463": [0, 0.68889, 0, 0, 0.54028], + "8487": [0, 0.68889, 0, 0, 0.72222], + "8498": [0, 0.68889, 0, 0, 0.55556], + "8502": [0, 0.68889, 0, 0, 0.66667], + "8503": [0, 0.68889, 0, 0, 0.44445], + "8504": [0, 0.68889, 0, 0, 0.66667], + "8513": [0, 0.68889, 0, 0, 0.63889], + "8592": [-0.03598, 0.46402, 0, 0, 0.5], + "8594": [-0.03598, 0.46402, 0, 0, 0.5], + "8602": [-0.13313, 0.36687, 0, 0, 1.0], + "8603": [-0.13313, 0.36687, 0, 0, 1.0], + "8606": [0.01354, 0.52239, 0, 0, 1.0], + "8608": [0.01354, 0.52239, 0, 0, 1.0], + "8610": [0.01354, 0.52239, 0, 0, 1.11111], + "8611": [0.01354, 0.52239, 0, 0, 1.11111], + "8619": [0, 0.54986, 0, 0, 1.0], + "8620": [0, 0.54986, 0, 0, 1.0], + "8621": [-0.13313, 0.37788, 0, 0, 1.38889], + "8622": [-0.13313, 0.36687, 0, 0, 1.0], + "8624": [0, 0.69224, 0, 0, 0.5], + "8625": [0, 0.69224, 0, 0, 0.5], + "8630": [0, 0.43056, 0, 0, 1.0], + "8631": [0, 0.43056, 0, 0, 1.0], + "8634": [0.08198, 0.58198, 0, 0, 0.77778], + "8635": [0.08198, 0.58198, 0, 0, 0.77778], + "8638": [0.19444, 0.69224, 0, 0, 0.41667], + "8639": [0.19444, 0.69224, 0, 0, 0.41667], + "8642": [0.19444, 0.69224, 0, 0, 0.41667], + "8643": [0.19444, 0.69224, 0, 0, 0.41667], + "8644": [0.1808, 0.675, 0, 0, 1.0], + "8646": [0.1808, 0.675, 0, 0, 1.0], + "8647": [0.1808, 0.675, 0, 0, 1.0], + "8648": [0.19444, 0.69224, 0, 0, 0.83334], + "8649": [0.1808, 0.675, 0, 0, 1.0], + "8650": [0.19444, 0.69224, 0, 0, 0.83334], + "8651": [0.01354, 0.52239, 0, 0, 1.0], + "8652": [0.01354, 0.52239, 0, 0, 1.0], + "8653": [-0.13313, 0.36687, 0, 0, 1.0], + "8654": [-0.13313, 0.36687, 0, 0, 1.0], + "8655": [-0.13313, 0.36687, 0, 0, 1.0], + "8666": [0.13667, 0.63667, 0, 0, 1.0], + "8667": [0.13667, 0.63667, 0, 0, 1.0], + "8669": [-0.13313, 0.37788, 0, 0, 1.0], + "8672": [-0.064, 0.437, 0, 0, 1.334], + "8674": [-0.064, 0.437, 0, 0, 1.334], + "8705": [0, 0.825, 0, 0, 0.5], + "8708": [0, 0.68889, 0, 0, 0.55556], + "8709": [0.08167, 0.58167, 0, 0, 0.77778], + "8717": [0, 0.43056, 0, 0, 0.42917], + "8722": [-0.03598, 0.46402, 0, 0, 0.5], + "8724": [0.08198, 0.69224, 0, 0, 0.77778], + "8726": [0.08167, 0.58167, 0, 0, 0.77778], + "8733": [0, 0.69224, 0, 0, 0.77778], + "8736": [0, 0.69224, 0, 0, 0.72222], + "8737": [0, 0.69224, 0, 0, 0.72222], + "8738": [0.03517, 0.52239, 0, 0, 0.72222], + "8739": [0.08167, 0.58167, 0, 0, 0.22222], + "8740": [0.25142, 0.74111, 0, 0, 0.27778], + "8741": [0.08167, 0.58167, 0, 0, 0.38889], + "8742": [0.25142, 0.74111, 0, 0, 0.5], + "8756": [0, 0.69224, 0, 0, 0.66667], + "8757": [0, 0.69224, 0, 0, 0.66667], + "8764": [-0.13313, 0.36687, 0, 0, 0.77778], + "8765": [-0.13313, 0.37788, 0, 0, 0.77778], + "8769": [-0.13313, 0.36687, 0, 0, 0.77778], + "8770": [-0.03625, 0.46375, 0, 0, 0.77778], + "8774": [0.30274, 0.79383, 0, 0, 0.77778], + "8776": [-0.01688, 0.48312, 0, 0, 0.77778], + "8778": [0.08167, 0.58167, 0, 0, 0.77778], + "8782": [0.06062, 0.54986, 0, 0, 0.77778], + "8783": [0.06062, 0.54986, 0, 0, 0.77778], + "8785": [0.08198, 0.58198, 0, 0, 0.77778], + "8786": [0.08198, 0.58198, 0, 0, 0.77778], + "8787": [0.08198, 0.58198, 0, 0, 0.77778], + "8790": [0, 0.69224, 0, 0, 0.77778], + "8791": [0.22958, 0.72958, 0, 0, 0.77778], + "8796": [0.08198, 0.91667, 0, 0, 0.77778], + "8806": [0.25583, 0.75583, 0, 0, 0.77778], + "8807": [0.25583, 0.75583, 0, 0, 0.77778], + "8808": [0.25142, 0.75726, 0, 0, 0.77778], + "8809": [0.25142, 0.75726, 0, 0, 0.77778], + "8812": [0.25583, 0.75583, 0, 0, 0.5], + "8814": [0.20576, 0.70576, 0, 0, 0.77778], + "8815": [0.20576, 0.70576, 0, 0, 0.77778], + "8816": [0.30274, 0.79383, 0, 0, 0.77778], + "8817": [0.30274, 0.79383, 0, 0, 0.77778], + "8818": [0.22958, 0.72958, 0, 0, 0.77778], + "8819": [0.22958, 0.72958, 0, 0, 0.77778], + "8822": [0.1808, 0.675, 0, 0, 0.77778], + "8823": [0.1808, 0.675, 0, 0, 0.77778], + "8828": [0.13667, 0.63667, 0, 0, 0.77778], + "8829": [0.13667, 0.63667, 0, 0, 0.77778], + "8830": [0.22958, 0.72958, 0, 0, 0.77778], + "8831": [0.22958, 0.72958, 0, 0, 0.77778], + "8832": [0.20576, 0.70576, 0, 0, 0.77778], + "8833": [0.20576, 0.70576, 0, 0, 0.77778], + "8840": [0.30274, 0.79383, 0, 0, 0.77778], + "8841": [0.30274, 0.79383, 0, 0, 0.77778], + "8842": [0.13597, 0.63597, 0, 0, 0.77778], + "8843": [0.13597, 0.63597, 0, 0, 0.77778], + "8847": [0.03517, 0.54986, 0, 0, 0.77778], + "8848": [0.03517, 0.54986, 0, 0, 0.77778], + "8858": [0.08198, 0.58198, 0, 0, 0.77778], + "8859": [0.08198, 0.58198, 0, 0, 0.77778], + "8861": [0.08198, 0.58198, 0, 0, 0.77778], + "8862": [0, 0.675, 0, 0, 0.77778], + "8863": [0, 0.675, 0, 0, 0.77778], + "8864": [0, 0.675, 0, 0, 0.77778], + "8865": [0, 0.675, 0, 0, 0.77778], + "8872": [0, 0.69224, 0, 0, 0.61111], + "8873": [0, 0.69224, 0, 0, 0.72222], + "8874": [0, 0.69224, 0, 0, 0.88889], + "8876": [0, 0.68889, 0, 0, 0.61111], + "8877": [0, 0.68889, 0, 0, 0.61111], + "8878": [0, 0.68889, 0, 0, 0.72222], + "8879": [0, 0.68889, 0, 0, 0.72222], + "8882": [0.03517, 0.54986, 0, 0, 0.77778], + "8883": [0.03517, 0.54986, 0, 0, 0.77778], + "8884": [0.13667, 0.63667, 0, 0, 0.77778], + "8885": [0.13667, 0.63667, 0, 0, 0.77778], + "8888": [0, 0.54986, 0, 0, 1.11111], + "8890": [0.19444, 0.43056, 0, 0, 0.55556], + "8891": [0.19444, 0.69224, 0, 0, 0.61111], + "8892": [0.19444, 0.69224, 0, 0, 0.61111], + "8901": [0, 0.54986, 0, 0, 0.27778], + "8903": [0.08167, 0.58167, 0, 0, 0.77778], + "8905": [0.08167, 0.58167, 0, 0, 0.77778], + "8906": [0.08167, 0.58167, 0, 0, 0.77778], + "8907": [0, 0.69224, 0, 0, 0.77778], + "8908": [0, 0.69224, 0, 0, 0.77778], + "8909": [-0.03598, 0.46402, 0, 0, 0.77778], + "8910": [0, 0.54986, 0, 0, 0.76042], + "8911": [0, 0.54986, 0, 0, 0.76042], + "8912": [0.03517, 0.54986, 0, 0, 0.77778], + "8913": [0.03517, 0.54986, 0, 0, 0.77778], + "8914": [0, 0.54986, 0, 0, 0.66667], + "8915": [0, 0.54986, 0, 0, 0.66667], + "8916": [0, 0.69224, 0, 0, 0.66667], + "8918": [0.0391, 0.5391, 0, 0, 0.77778], + "8919": [0.0391, 0.5391, 0, 0, 0.77778], + "8920": [0.03517, 0.54986, 0, 0, 1.33334], + "8921": [0.03517, 0.54986, 0, 0, 1.33334], + "8922": [0.38569, 0.88569, 0, 0, 0.77778], + "8923": [0.38569, 0.88569, 0, 0, 0.77778], + "8926": [0.13667, 0.63667, 0, 0, 0.77778], + "8927": [0.13667, 0.63667, 0, 0, 0.77778], + "8928": [0.30274, 0.79383, 0, 0, 0.77778], + "8929": [0.30274, 0.79383, 0, 0, 0.77778], + "8934": [0.23222, 0.74111, 0, 0, 0.77778], + "8935": [0.23222, 0.74111, 0, 0, 0.77778], + "8936": [0.23222, 0.74111, 0, 0, 0.77778], + "8937": [0.23222, 0.74111, 0, 0, 0.77778], + "8938": [0.20576, 0.70576, 0, 0, 0.77778], + "8939": [0.20576, 0.70576, 0, 0, 0.77778], + "8940": [0.30274, 0.79383, 0, 0, 0.77778], + "8941": [0.30274, 0.79383, 0, 0, 0.77778], + "8994": [0.19444, 0.69224, 0, 0, 0.77778], + "8995": [0.19444, 0.69224, 0, 0, 0.77778], + "9416": [0.15559, 0.69224, 0, 0, 0.90222], + "9484": [0, 0.69224, 0, 0, 0.5], + "9488": [0, 0.69224, 0, 0, 0.5], + "9492": [0, 0.37788, 0, 0, 0.5], + "9496": [0, 0.37788, 0, 0, 0.5], + "9585": [0.19444, 0.68889, 0, 0, 0.88889], + "9586": [0.19444, 0.74111, 0, 0, 0.88889], + "9632": [0, 0.675, 0, 0, 0.77778], + "9633": [0, 0.675, 0, 0, 0.77778], + "9650": [0, 0.54986, 0, 0, 0.72222], + "9651": [0, 0.54986, 0, 0, 0.72222], + "9654": [0.03517, 0.54986, 0, 0, 0.77778], + "9660": [0, 0.54986, 0, 0, 0.72222], + "9661": [0, 0.54986, 0, 0, 0.72222], + "9664": [0.03517, 0.54986, 0, 0, 0.77778], + "9674": [0.11111, 0.69224, 0, 0, 0.66667], + "9733": [0.19444, 0.69224, 0, 0, 0.94445], + "10003": [0, 0.69224, 0, 0, 0.83334], + "10016": [0, 0.69224, 0, 0, 0.83334], + "10731": [0.11111, 0.69224, 0, 0, 0.66667], + "10846": [0.19444, 0.75583, 0, 0, 0.61111], + "10877": [0.13667, 0.63667, 0, 0, 0.77778], + "10878": [0.13667, 0.63667, 0, 0, 0.77778], + "10885": [0.25583, 0.75583, 0, 0, 0.77778], + "10886": [0.25583, 0.75583, 0, 0, 0.77778], + "10887": [0.13597, 0.63597, 0, 0, 0.77778], + "10888": [0.13597, 0.63597, 0, 0, 0.77778], + "10889": [0.26167, 0.75726, 0, 0, 0.77778], + "10890": [0.26167, 0.75726, 0, 0, 0.77778], + "10891": [0.48256, 0.98256, 0, 0, 0.77778], + "10892": [0.48256, 0.98256, 0, 0, 0.77778], + "10901": [0.13667, 0.63667, 0, 0, 0.77778], + "10902": [0.13667, 0.63667, 0, 0, 0.77778], + "10933": [0.25142, 0.75726, 0, 0, 0.77778], + "10934": [0.25142, 0.75726, 0, 0, 0.77778], + "10935": [0.26167, 0.75726, 0, 0, 0.77778], + "10936": [0.26167, 0.75726, 0, 0, 0.77778], + "10937": [0.26167, 0.75726, 0, 0, 0.77778], + "10938": [0.26167, 0.75726, 0, 0, 0.77778], + "10949": [0.25583, 0.75583, 0, 0, 0.77778], + "10950": [0.25583, 0.75583, 0, 0, 0.77778], + "10955": [0.28481, 0.79383, 0, 0, 0.77778], + "10956": [0.28481, 0.79383, 0, 0, 0.77778], + "57350": [0.08167, 0.58167, 0, 0, 0.22222], + "57351": [0.08167, 0.58167, 0, 0, 0.38889], + "57352": [0.08167, 0.58167, 0, 0, 0.77778], + "57353": [0, 0.43056, 0.04028, 0, 0.66667], + "57356": [0.25142, 0.75726, 0, 0, 0.77778], + "57357": [0.25142, 0.75726, 0, 0, 0.77778], + "57358": [0.41951, 0.91951, 0, 0, 0.77778], + "57359": [0.30274, 0.79383, 0, 0, 0.77778], + "57360": [0.30274, 0.79383, 0, 0, 0.77778], + "57361": [0.41951, 0.91951, 0, 0, 0.77778], + "57366": [0.25142, 0.75726, 0, 0, 0.77778], + "57367": [0.25142, 0.75726, 0, 0, 0.77778], + "57368": [0.25142, 0.75726, 0, 0, 0.77778], + "57369": [0.25142, 0.75726, 0, 0, 0.77778], + "57370": [0.13597, 0.63597, 0, 0, 0.77778], + "57371": [0.13597, 0.63597, 0, 0, 0.77778], + }, + "Caligraphic-Regular": { + "32": [0, 0, 0, 0, 0.25], + "65": [0, 0.68333, 0, 0.19445, 0.79847], + "66": [0, 0.68333, 0.03041, 0.13889, 0.65681], + "67": [0, 0.68333, 0.05834, 0.13889, 0.52653], + "68": [0, 0.68333, 0.02778, 0.08334, 0.77139], + "69": [0, 0.68333, 0.08944, 0.11111, 0.52778], + "70": [0, 0.68333, 0.09931, 0.11111, 0.71875], + "71": [0.09722, 0.68333, 0.0593, 0.11111, 0.59487], + "72": [0, 0.68333, 0.00965, 0.11111, 0.84452], + "73": [0, 0.68333, 0.07382, 0, 0.54452], + "74": [0.09722, 0.68333, 0.18472, 0.16667, 0.67778], + "75": [0, 0.68333, 0.01445, 0.05556, 0.76195], + "76": [0, 0.68333, 0, 0.13889, 0.68972], + "77": [0, 0.68333, 0, 0.13889, 1.2009], + "78": [0, 0.68333, 0.14736, 0.08334, 0.82049], + "79": [0, 0.68333, 0.02778, 0.11111, 0.79611], + "80": [0, 0.68333, 0.08222, 0.08334, 0.69556], + "81": [0.09722, 0.68333, 0, 0.11111, 0.81667], + "82": [0, 0.68333, 0, 0.08334, 0.8475], + "83": [0, 0.68333, 0.075, 0.13889, 0.60556], + "84": [0, 0.68333, 0.25417, 0, 0.54464], + "85": [0, 0.68333, 0.09931, 0.08334, 0.62583], + "86": [0, 0.68333, 0.08222, 0, 0.61278], + "87": [0, 0.68333, 0.08222, 0.08334, 0.98778], + "88": [0, 0.68333, 0.14643, 0.13889, 0.7133], + "89": [0.09722, 0.68333, 0.08222, 0.08334, 0.66834], + "90": [0, 0.68333, 0.07944, 0.13889, 0.72473], + "160": [0, 0, 0, 0, 0.25], + }, + "Fraktur-Regular": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69141, 0, 0, 0.29574], + "34": [0, 0.69141, 0, 0, 0.21471], + "38": [0, 0.69141, 0, 0, 0.73786], + "39": [0, 0.69141, 0, 0, 0.21201], + "40": [0.24982, 0.74947, 0, 0, 0.38865], + "41": [0.24982, 0.74947, 0, 0, 0.38865], + "42": [0, 0.62119, 0, 0, 0.27764], + "43": [0.08319, 0.58283, 0, 0, 0.75623], + "44": [0, 0.10803, 0, 0, 0.27764], + "45": [0.08319, 0.58283, 0, 0, 0.75623], + "46": [0, 0.10803, 0, 0, 0.27764], + "47": [0.24982, 0.74947, 0, 0, 0.50181], + "48": [0, 0.47534, 0, 0, 0.50181], + "49": [0, 0.47534, 0, 0, 0.50181], + "50": [0, 0.47534, 0, 0, 0.50181], + "51": [0.18906, 0.47534, 0, 0, 0.50181], + "52": [0.18906, 0.47534, 0, 0, 0.50181], + "53": [0.18906, 0.47534, 0, 0, 0.50181], + "54": [0, 0.69141, 0, 0, 0.50181], + "55": [0.18906, 0.47534, 0, 0, 0.50181], + "56": [0, 0.69141, 0, 0, 0.50181], + "57": [0.18906, 0.47534, 0, 0, 0.50181], + "58": [0, 0.47534, 0, 0, 0.21606], + "59": [0.12604, 0.47534, 0, 0, 0.21606], + "61": [-0.13099, 0.36866, 0, 0, 0.75623], + "63": [0, 0.69141, 0, 0, 0.36245], + "65": [0, 0.69141, 0, 0, 0.7176], + "66": [0, 0.69141, 0, 0, 0.88397], + "67": [0, 0.69141, 0, 0, 0.61254], + "68": [0, 0.69141, 0, 0, 0.83158], + "69": [0, 0.69141, 0, 0, 0.66278], + "70": [0.12604, 0.69141, 0, 0, 0.61119], + "71": [0, 0.69141, 0, 0, 0.78539], + "72": [0.06302, 0.69141, 0, 0, 0.7203], + "73": [0, 0.69141, 0, 0, 0.55448], + "74": [0.12604, 0.69141, 0, 0, 0.55231], + "75": [0, 0.69141, 0, 0, 0.66845], + "76": [0, 0.69141, 0, 0, 0.66602], + "77": [0, 0.69141, 0, 0, 1.04953], + "78": [0, 0.69141, 0, 0, 0.83212], + "79": [0, 0.69141, 0, 0, 0.82699], + "80": [0.18906, 0.69141, 0, 0, 0.82753], + "81": [0.03781, 0.69141, 0, 0, 0.82699], + "82": [0, 0.69141, 0, 0, 0.82807], + "83": [0, 0.69141, 0, 0, 0.82861], + "84": [0, 0.69141, 0, 0, 0.66899], + "85": [0, 0.69141, 0, 0, 0.64576], + "86": [0, 0.69141, 0, 0, 0.83131], + "87": [0, 0.69141, 0, 0, 1.04602], + "88": [0, 0.69141, 0, 0, 0.71922], + "89": [0.18906, 0.69141, 0, 0, 0.83293], + "90": [0.12604, 0.69141, 0, 0, 0.60201], + "91": [0.24982, 0.74947, 0, 0, 0.27764], + "93": [0.24982, 0.74947, 0, 0, 0.27764], + "94": [0, 0.69141, 0, 0, 0.49965], + "97": [0, 0.47534, 0, 0, 0.50046], + "98": [0, 0.69141, 0, 0, 0.51315], + "99": [0, 0.47534, 0, 0, 0.38946], + "100": [0, 0.62119, 0, 0, 0.49857], + "101": [0, 0.47534, 0, 0, 0.40053], + "102": [0.18906, 0.69141, 0, 0, 0.32626], + "103": [0.18906, 0.47534, 0, 0, 0.5037], + "104": [0.18906, 0.69141, 0, 0, 0.52126], + "105": [0, 0.69141, 0, 0, 0.27899], + "106": [0, 0.69141, 0, 0, 0.28088], + "107": [0, 0.69141, 0, 0, 0.38946], + "108": [0, 0.69141, 0, 0, 0.27953], + "109": [0, 0.47534, 0, 0, 0.76676], + "110": [0, 0.47534, 0, 0, 0.52666], + "111": [0, 0.47534, 0, 0, 0.48885], + "112": [0.18906, 0.52396, 0, 0, 0.50046], + "113": [0.18906, 0.47534, 0, 0, 0.48912], + "114": [0, 0.47534, 0, 0, 0.38919], + "115": [0, 0.47534, 0, 0, 0.44266], + "116": [0, 0.62119, 0, 0, 0.33301], + "117": [0, 0.47534, 0, 0, 0.5172], + "118": [0, 0.52396, 0, 0, 0.5118], + "119": [0, 0.52396, 0, 0, 0.77351], + "120": [0.18906, 0.47534, 0, 0, 0.38865], + "121": [0.18906, 0.47534, 0, 0, 0.49884], + "122": [0.18906, 0.47534, 0, 0, 0.39054], + "160": [0, 0, 0, 0, 0.25], + "8216": [0, 0.69141, 0, 0, 0.21471], + "8217": [0, 0.69141, 0, 0, 0.21471], + "58112": [0, 0.62119, 0, 0, 0.49749], + "58113": [0, 0.62119, 0, 0, 0.4983], + "58114": [0.18906, 0.69141, 0, 0, 0.33328], + "58115": [0.18906, 0.69141, 0, 0, 0.32923], + "58116": [0.18906, 0.47534, 0, 0, 0.50343], + "58117": [0, 0.69141, 0, 0, 0.33301], + "58118": [0, 0.62119, 0, 0, 0.33409], + "58119": [0, 0.47534, 0, 0, 0.50073], + }, + "Main-Bold": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0, 0, 0.35], + "34": [0, 0.69444, 0, 0, 0.60278], + "35": [0.19444, 0.69444, 0, 0, 0.95833], + "36": [0.05556, 0.75, 0, 0, 0.575], + "37": [0.05556, 0.75, 0, 0, 0.95833], + "38": [0, 0.69444, 0, 0, 0.89444], + "39": [0, 0.69444, 0, 0, 0.31944], + "40": [0.25, 0.75, 0, 0, 0.44722], + "41": [0.25, 0.75, 0, 0, 0.44722], + "42": [0, 0.75, 0, 0, 0.575], + "43": [0.13333, 0.63333, 0, 0, 0.89444], + "44": [0.19444, 0.15556, 0, 0, 0.31944], + "45": [0, 0.44444, 0, 0, 0.38333], + "46": [0, 0.15556, 0, 0, 0.31944], + "47": [0.25, 0.75, 0, 0, 0.575], + "48": [0, 0.64444, 0, 0, 0.575], + "49": [0, 0.64444, 0, 0, 0.575], + "50": [0, 0.64444, 0, 0, 0.575], + "51": [0, 0.64444, 0, 0, 0.575], + "52": [0, 0.64444, 0, 0, 0.575], + "53": [0, 0.64444, 0, 0, 0.575], + "54": [0, 0.64444, 0, 0, 0.575], + "55": [0, 0.64444, 0, 0, 0.575], + "56": [0, 0.64444, 0, 0, 0.575], + "57": [0, 0.64444, 0, 0, 0.575], + "58": [0, 0.44444, 0, 0, 0.31944], + "59": [0.19444, 0.44444, 0, 0, 0.31944], + "60": [0.08556, 0.58556, 0, 0, 0.89444], + "61": [-0.10889, 0.39111, 0, 0, 0.89444], + "62": [0.08556, 0.58556, 0, 0, 0.89444], + "63": [0, 0.69444, 0, 0, 0.54305], + "64": [0, 0.69444, 0, 0, 0.89444], + "65": [0, 0.68611, 0, 0, 0.86944], + "66": [0, 0.68611, 0, 0, 0.81805], + "67": [0, 0.68611, 0, 0, 0.83055], + "68": [0, 0.68611, 0, 0, 0.88194], + "69": [0, 0.68611, 0, 0, 0.75555], + "70": [0, 0.68611, 0, 0, 0.72361], + "71": [0, 0.68611, 0, 0, 0.90416], + "72": [0, 0.68611, 0, 0, 0.9], + "73": [0, 0.68611, 0, 0, 0.43611], + "74": [0, 0.68611, 0, 0, 0.59444], + "75": [0, 0.68611, 0, 0, 0.90138], + "76": [0, 0.68611, 0, 0, 0.69166], + "77": [0, 0.68611, 0, 0, 1.09166], + "78": [0, 0.68611, 0, 0, 0.9], + "79": [0, 0.68611, 0, 0, 0.86388], + "80": [0, 0.68611, 0, 0, 0.78611], + "81": [0.19444, 0.68611, 0, 0, 0.86388], + "82": [0, 0.68611, 0, 0, 0.8625], + "83": [0, 0.68611, 0, 0, 0.63889], + "84": [0, 0.68611, 0, 0, 0.8], + "85": [0, 0.68611, 0, 0, 0.88472], + "86": [0, 0.68611, 0.01597, 0, 0.86944], + "87": [0, 0.68611, 0.01597, 0, 1.18888], + "88": [0, 0.68611, 0, 0, 0.86944], + "89": [0, 0.68611, 0.02875, 0, 0.86944], + "90": [0, 0.68611, 0, 0, 0.70277], + "91": [0.25, 0.75, 0, 0, 0.31944], + "92": [0.25, 0.75, 0, 0, 0.575], + "93": [0.25, 0.75, 0, 0, 0.31944], + "94": [0, 0.69444, 0, 0, 0.575], + "95": [0.31, 0.13444, 0.03194, 0, 0.575], + "97": [0, 0.44444, 0, 0, 0.55902], + "98": [0, 0.69444, 0, 0, 0.63889], + "99": [0, 0.44444, 0, 0, 0.51111], + "100": [0, 0.69444, 0, 0, 0.63889], + "101": [0, 0.44444, 0, 0, 0.52708], + "102": [0, 0.69444, 0.10903, 0, 0.35139], + "103": [0.19444, 0.44444, 0.01597, 0, 0.575], + "104": [0, 0.69444, 0, 0, 0.63889], + "105": [0, 0.69444, 0, 0, 0.31944], + "106": [0.19444, 0.69444, 0, 0, 0.35139], + "107": [0, 0.69444, 0, 0, 0.60694], + "108": [0, 0.69444, 0, 0, 0.31944], + "109": [0, 0.44444, 0, 0, 0.95833], + "110": [0, 0.44444, 0, 0, 0.63889], + "111": [0, 0.44444, 0, 0, 0.575], + "112": [0.19444, 0.44444, 0, 0, 0.63889], + "113": [0.19444, 0.44444, 0, 0, 0.60694], + "114": [0, 0.44444, 0, 0, 0.47361], + "115": [0, 0.44444, 0, 0, 0.45361], + "116": [0, 0.63492, 0, 0, 0.44722], + "117": [0, 0.44444, 0, 0, 0.63889], + "118": [0, 0.44444, 0.01597, 0, 0.60694], + "119": [0, 0.44444, 0.01597, 0, 0.83055], + "120": [0, 0.44444, 0, 0, 0.60694], + "121": [0.19444, 0.44444, 0.01597, 0, 0.60694], + "122": [0, 0.44444, 0, 0, 0.51111], + "123": [0.25, 0.75, 0, 0, 0.575], + "124": [0.25, 0.75, 0, 0, 0.31944], + "125": [0.25, 0.75, 0, 0, 0.575], + "126": [0.35, 0.34444, 0, 0, 0.575], + "160": [0, 0, 0, 0, 0.25], + "163": [0, 0.69444, 0, 0, 0.86853], + "168": [0, 0.69444, 0, 0, 0.575], + "172": [0, 0.44444, 0, 0, 0.76666], + "176": [0, 0.69444, 0, 0, 0.86944], + "177": [0.13333, 0.63333, 0, 0, 0.89444], + "184": [0.17014, 0, 0, 0, 0.51111], + "198": [0, 0.68611, 0, 0, 1.04166], + "215": [0.13333, 0.63333, 0, 0, 0.89444], + "216": [0.04861, 0.73472, 0, 0, 0.89444], + "223": [0, 0.69444, 0, 0, 0.59722], + "230": [0, 0.44444, 0, 0, 0.83055], + "247": [0.13333, 0.63333, 0, 0, 0.89444], + "248": [0.09722, 0.54167, 0, 0, 0.575], + "305": [0, 0.44444, 0, 0, 0.31944], + "338": [0, 0.68611, 0, 0, 1.16944], + "339": [0, 0.44444, 0, 0, 0.89444], + "567": [0.19444, 0.44444, 0, 0, 0.35139], + "710": [0, 0.69444, 0, 0, 0.575], + "711": [0, 0.63194, 0, 0, 0.575], + "713": [0, 0.59611, 0, 0, 0.575], + "714": [0, 0.69444, 0, 0, 0.575], + "715": [0, 0.69444, 0, 0, 0.575], + "728": [0, 0.69444, 0, 0, 0.575], + "729": [0, 0.69444, 0, 0, 0.31944], + "730": [0, 0.69444, 0, 0, 0.86944], + "732": [0, 0.69444, 0, 0, 0.575], + "733": [0, 0.69444, 0, 0, 0.575], + "915": [0, 0.68611, 0, 0, 0.69166], + "916": [0, 0.68611, 0, 0, 0.95833], + "920": [0, 0.68611, 0, 0, 0.89444], + "923": [0, 0.68611, 0, 0, 0.80555], + "926": [0, 0.68611, 0, 0, 0.76666], + "928": [0, 0.68611, 0, 0, 0.9], + "931": [0, 0.68611, 0, 0, 0.83055], + "933": [0, 0.68611, 0, 0, 0.89444], + "934": [0, 0.68611, 0, 0, 0.83055], + "936": [0, 0.68611, 0, 0, 0.89444], + "937": [0, 0.68611, 0, 0, 0.83055], + "8211": [0, 0.44444, 0.03194, 0, 0.575], + "8212": [0, 0.44444, 0.03194, 0, 1.14999], + "8216": [0, 0.69444, 0, 0, 0.31944], + "8217": [0, 0.69444, 0, 0, 0.31944], + "8220": [0, 0.69444, 0, 0, 0.60278], + "8221": [0, 0.69444, 0, 0, 0.60278], + "8224": [0.19444, 0.69444, 0, 0, 0.51111], + "8225": [0.19444, 0.69444, 0, 0, 0.51111], + "8242": [0, 0.55556, 0, 0, 0.34444], + "8407": [0, 0.72444, 0.15486, 0, 0.575], + "8463": [0, 0.69444, 0, 0, 0.66759], + "8465": [0, 0.69444, 0, 0, 0.83055], + "8467": [0, 0.69444, 0, 0, 0.47361], + "8472": [0.19444, 0.44444, 0, 0, 0.74027], + "8476": [0, 0.69444, 0, 0, 0.83055], + "8501": [0, 0.69444, 0, 0, 0.70277], + "8592": [-0.10889, 0.39111, 0, 0, 1.14999], + "8593": [0.19444, 0.69444, 0, 0, 0.575], + "8594": [-0.10889, 0.39111, 0, 0, 1.14999], + "8595": [0.19444, 0.69444, 0, 0, 0.575], + "8596": [-0.10889, 0.39111, 0, 0, 1.14999], + "8597": [0.25, 0.75, 0, 0, 0.575], + "8598": [0.19444, 0.69444, 0, 0, 1.14999], + "8599": [0.19444, 0.69444, 0, 0, 1.14999], + "8600": [0.19444, 0.69444, 0, 0, 1.14999], + "8601": [0.19444, 0.69444, 0, 0, 1.14999], + "8636": [-0.10889, 0.39111, 0, 0, 1.14999], + "8637": [-0.10889, 0.39111, 0, 0, 1.14999], + "8640": [-0.10889, 0.39111, 0, 0, 1.14999], + "8641": [-0.10889, 0.39111, 0, 0, 1.14999], + "8656": [-0.10889, 0.39111, 0, 0, 1.14999], + "8657": [0.19444, 0.69444, 0, 0, 0.70277], + "8658": [-0.10889, 0.39111, 0, 0, 1.14999], + "8659": [0.19444, 0.69444, 0, 0, 0.70277], + "8660": [-0.10889, 0.39111, 0, 0, 1.14999], + "8661": [0.25, 0.75, 0, 0, 0.70277], + "8704": [0, 0.69444, 0, 0, 0.63889], + "8706": [0, 0.69444, 0.06389, 0, 0.62847], + "8707": [0, 0.69444, 0, 0, 0.63889], + "8709": [0.05556, 0.75, 0, 0, 0.575], + "8711": [0, 0.68611, 0, 0, 0.95833], + "8712": [0.08556, 0.58556, 0, 0, 0.76666], + "8715": [0.08556, 0.58556, 0, 0, 0.76666], + "8722": [0.13333, 0.63333, 0, 0, 0.89444], + "8723": [0.13333, 0.63333, 0, 0, 0.89444], + "8725": [0.25, 0.75, 0, 0, 0.575], + "8726": [0.25, 0.75, 0, 0, 0.575], + "8727": [-0.02778, 0.47222, 0, 0, 0.575], + "8728": [-0.02639, 0.47361, 0, 0, 0.575], + "8729": [-0.02639, 0.47361, 0, 0, 0.575], + "8730": [0.18, 0.82, 0, 0, 0.95833], + "8733": [0, 0.44444, 0, 0, 0.89444], + "8734": [0, 0.44444, 0, 0, 1.14999], + "8736": [0, 0.69224, 0, 0, 0.72222], + "8739": [0.25, 0.75, 0, 0, 0.31944], + "8741": [0.25, 0.75, 0, 0, 0.575], + "8743": [0, 0.55556, 0, 0, 0.76666], + "8744": [0, 0.55556, 0, 0, 0.76666], + "8745": [0, 0.55556, 0, 0, 0.76666], + "8746": [0, 0.55556, 0, 0, 0.76666], + "8747": [0.19444, 0.69444, 0.12778, 0, 0.56875], + "8764": [-0.10889, 0.39111, 0, 0, 0.89444], + "8768": [0.19444, 0.69444, 0, 0, 0.31944], + "8771": [0.00222, 0.50222, 0, 0, 0.89444], + "8773": [0.027, 0.638, 0, 0, 0.894], + "8776": [0.02444, 0.52444, 0, 0, 0.89444], + "8781": [0.00222, 0.50222, 0, 0, 0.89444], + "8801": [0.00222, 0.50222, 0, 0, 0.89444], + "8804": [0.19667, 0.69667, 0, 0, 0.89444], + "8805": [0.19667, 0.69667, 0, 0, 0.89444], + "8810": [0.08556, 0.58556, 0, 0, 1.14999], + "8811": [0.08556, 0.58556, 0, 0, 1.14999], + "8826": [0.08556, 0.58556, 0, 0, 0.89444], + "8827": [0.08556, 0.58556, 0, 0, 0.89444], + "8834": [0.08556, 0.58556, 0, 0, 0.89444], + "8835": [0.08556, 0.58556, 0, 0, 0.89444], + "8838": [0.19667, 0.69667, 0, 0, 0.89444], + "8839": [0.19667, 0.69667, 0, 0, 0.89444], + "8846": [0, 0.55556, 0, 0, 0.76666], + "8849": [0.19667, 0.69667, 0, 0, 0.89444], + "8850": [0.19667, 0.69667, 0, 0, 0.89444], + "8851": [0, 0.55556, 0, 0, 0.76666], + "8852": [0, 0.55556, 0, 0, 0.76666], + "8853": [0.13333, 0.63333, 0, 0, 0.89444], + "8854": [0.13333, 0.63333, 0, 0, 0.89444], + "8855": [0.13333, 0.63333, 0, 0, 0.89444], + "8856": [0.13333, 0.63333, 0, 0, 0.89444], + "8857": [0.13333, 0.63333, 0, 0, 0.89444], + "8866": [0, 0.69444, 0, 0, 0.70277], + "8867": [0, 0.69444, 0, 0, 0.70277], + "8868": [0, 0.69444, 0, 0, 0.89444], + "8869": [0, 0.69444, 0, 0, 0.89444], + "8900": [-0.02639, 0.47361, 0, 0, 0.575], + "8901": [-0.02639, 0.47361, 0, 0, 0.31944], + "8902": [-0.02778, 0.47222, 0, 0, 0.575], + "8968": [0.25, 0.75, 0, 0, 0.51111], + "8969": [0.25, 0.75, 0, 0, 0.51111], + "8970": [0.25, 0.75, 0, 0, 0.51111], + "8971": [0.25, 0.75, 0, 0, 0.51111], + "8994": [-0.13889, 0.36111, 0, 0, 1.14999], + "8995": [-0.13889, 0.36111, 0, 0, 1.14999], + "9651": [0.19444, 0.69444, 0, 0, 1.02222], + "9657": [-0.02778, 0.47222, 0, 0, 0.575], + "9661": [0.19444, 0.69444, 0, 0, 1.02222], + "9667": [-0.02778, 0.47222, 0, 0, 0.575], + "9711": [0.19444, 0.69444, 0, 0, 1.14999], + "9824": [0.12963, 0.69444, 0, 0, 0.89444], + "9825": [0.12963, 0.69444, 0, 0, 0.89444], + "9826": [0.12963, 0.69444, 0, 0, 0.89444], + "9827": [0.12963, 0.69444, 0, 0, 0.89444], + "9837": [0, 0.75, 0, 0, 0.44722], + "9838": [0.19444, 0.69444, 0, 0, 0.44722], + "9839": [0.19444, 0.69444, 0, 0, 0.44722], + "10216": [0.25, 0.75, 0, 0, 0.44722], + "10217": [0.25, 0.75, 0, 0, 0.44722], + "10815": [0, 0.68611, 0, 0, 0.9], + "10927": [0.19667, 0.69667, 0, 0, 0.89444], + "10928": [0.19667, 0.69667, 0, 0, 0.89444], + "57376": [0.19444, 0.69444, 0, 0, 0], + }, + "Main-BoldItalic": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0.11417, 0, 0.38611], + "34": [0, 0.69444, 0.07939, 0, 0.62055], + "35": [0.19444, 0.69444, 0.06833, 0, 0.94444], + "37": [0.05556, 0.75, 0.12861, 0, 0.94444], + "38": [0, 0.69444, 0.08528, 0, 0.88555], + "39": [0, 0.69444, 0.12945, 0, 0.35555], + "40": [0.25, 0.75, 0.15806, 0, 0.47333], + "41": [0.25, 0.75, 0.03306, 0, 0.47333], + "42": [0, 0.75, 0.14333, 0, 0.59111], + "43": [0.10333, 0.60333, 0.03306, 0, 0.88555], + "44": [0.19444, 0.14722, 0, 0, 0.35555], + "45": [0, 0.44444, 0.02611, 0, 0.41444], + "46": [0, 0.14722, 0, 0, 0.35555], + "47": [0.25, 0.75, 0.15806, 0, 0.59111], + "48": [0, 0.64444, 0.13167, 0, 0.59111], + "49": [0, 0.64444, 0.13167, 0, 0.59111], + "50": [0, 0.64444, 0.13167, 0, 0.59111], + "51": [0, 0.64444, 0.13167, 0, 0.59111], + "52": [0.19444, 0.64444, 0.13167, 0, 0.59111], + "53": [0, 0.64444, 0.13167, 0, 0.59111], + "54": [0, 0.64444, 0.13167, 0, 0.59111], + "55": [0.19444, 0.64444, 0.13167, 0, 0.59111], + "56": [0, 0.64444, 0.13167, 0, 0.59111], + "57": [0, 0.64444, 0.13167, 0, 0.59111], + "58": [0, 0.44444, 0.06695, 0, 0.35555], + "59": [0.19444, 0.44444, 0.06695, 0, 0.35555], + "61": [-0.10889, 0.39111, 0.06833, 0, 0.88555], + "63": [0, 0.69444, 0.11472, 0, 0.59111], + "64": [0, 0.69444, 0.09208, 0, 0.88555], + "65": [0, 0.68611, 0, 0, 0.86555], + "66": [0, 0.68611, 0.0992, 0, 0.81666], + "67": [0, 0.68611, 0.14208, 0, 0.82666], + "68": [0, 0.68611, 0.09062, 0, 0.87555], + "69": [0, 0.68611, 0.11431, 0, 0.75666], + "70": [0, 0.68611, 0.12903, 0, 0.72722], + "71": [0, 0.68611, 0.07347, 0, 0.89527], + "72": [0, 0.68611, 0.17208, 0, 0.8961], + "73": [0, 0.68611, 0.15681, 0, 0.47166], + "74": [0, 0.68611, 0.145, 0, 0.61055], + "75": [0, 0.68611, 0.14208, 0, 0.89499], + "76": [0, 0.68611, 0, 0, 0.69777], + "77": [0, 0.68611, 0.17208, 0, 1.07277], + "78": [0, 0.68611, 0.17208, 0, 0.8961], + "79": [0, 0.68611, 0.09062, 0, 0.85499], + "80": [0, 0.68611, 0.0992, 0, 0.78721], + "81": [0.19444, 0.68611, 0.09062, 0, 0.85499], + "82": [0, 0.68611, 0.02559, 0, 0.85944], + "83": [0, 0.68611, 0.11264, 0, 0.64999], + "84": [0, 0.68611, 0.12903, 0, 0.7961], + "85": [0, 0.68611, 0.17208, 0, 0.88083], + "86": [0, 0.68611, 0.18625, 0, 0.86555], + "87": [0, 0.68611, 0.18625, 0, 1.15999], + "88": [0, 0.68611, 0.15681, 0, 0.86555], + "89": [0, 0.68611, 0.19803, 0, 0.86555], + "90": [0, 0.68611, 0.14208, 0, 0.70888], + "91": [0.25, 0.75, 0.1875, 0, 0.35611], + "93": [0.25, 0.75, 0.09972, 0, 0.35611], + "94": [0, 0.69444, 0.06709, 0, 0.59111], + "95": [0.31, 0.13444, 0.09811, 0, 0.59111], + "97": [0, 0.44444, 0.09426, 0, 0.59111], + "98": [0, 0.69444, 0.07861, 0, 0.53222], + "99": [0, 0.44444, 0.05222, 0, 0.53222], + "100": [0, 0.69444, 0.10861, 0, 0.59111], + "101": [0, 0.44444, 0.085, 0, 0.53222], + "102": [0.19444, 0.69444, 0.21778, 0, 0.4], + "103": [0.19444, 0.44444, 0.105, 0, 0.53222], + "104": [0, 0.69444, 0.09426, 0, 0.59111], + "105": [0, 0.69326, 0.11387, 0, 0.35555], + "106": [0.19444, 0.69326, 0.1672, 0, 0.35555], + "107": [0, 0.69444, 0.11111, 0, 0.53222], + "108": [0, 0.69444, 0.10861, 0, 0.29666], + "109": [0, 0.44444, 0.09426, 0, 0.94444], + "110": [0, 0.44444, 0.09426, 0, 0.64999], + "111": [0, 0.44444, 0.07861, 0, 0.59111], + "112": [0.19444, 0.44444, 0.07861, 0, 0.59111], + "113": [0.19444, 0.44444, 0.105, 0, 0.53222], + "114": [0, 0.44444, 0.11111, 0, 0.50167], + "115": [0, 0.44444, 0.08167, 0, 0.48694], + "116": [0, 0.63492, 0.09639, 0, 0.385], + "117": [0, 0.44444, 0.09426, 0, 0.62055], + "118": [0, 0.44444, 0.11111, 0, 0.53222], + "119": [0, 0.44444, 0.11111, 0, 0.76777], + "120": [0, 0.44444, 0.12583, 0, 0.56055], + "121": [0.19444, 0.44444, 0.105, 0, 0.56166], + "122": [0, 0.44444, 0.13889, 0, 0.49055], + "126": [0.35, 0.34444, 0.11472, 0, 0.59111], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.69444, 0.11473, 0, 0.59111], + "176": [0, 0.69444, 0, 0, 0.94888], + "184": [0.17014, 0, 0, 0, 0.53222], + "198": [0, 0.68611, 0.11431, 0, 1.02277], + "216": [0.04861, 0.73472, 0.09062, 0, 0.88555], + "223": [0.19444, 0.69444, 0.09736, 0, 0.665], + "230": [0, 0.44444, 0.085, 0, 0.82666], + "248": [0.09722, 0.54167, 0.09458, 0, 0.59111], + "305": [0, 0.44444, 0.09426, 0, 0.35555], + "338": [0, 0.68611, 0.11431, 0, 1.14054], + "339": [0, 0.44444, 0.085, 0, 0.82666], + "567": [0.19444, 0.44444, 0.04611, 0, 0.385], + "710": [0, 0.69444, 0.06709, 0, 0.59111], + "711": [0, 0.63194, 0.08271, 0, 0.59111], + "713": [0, 0.59444, 0.10444, 0, 0.59111], + "714": [0, 0.69444, 0.08528, 0, 0.59111], + "715": [0, 0.69444, 0, 0, 0.59111], + "728": [0, 0.69444, 0.10333, 0, 0.59111], + "729": [0, 0.69444, 0.12945, 0, 0.35555], + "730": [0, 0.69444, 0, 0, 0.94888], + "732": [0, 0.69444, 0.11472, 0, 0.59111], + "733": [0, 0.69444, 0.11472, 0, 0.59111], + "915": [0, 0.68611, 0.12903, 0, 0.69777], + "916": [0, 0.68611, 0, 0, 0.94444], + "920": [0, 0.68611, 0.09062, 0, 0.88555], + "923": [0, 0.68611, 0, 0, 0.80666], + "926": [0, 0.68611, 0.15092, 0, 0.76777], + "928": [0, 0.68611, 0.17208, 0, 0.8961], + "931": [0, 0.68611, 0.11431, 0, 0.82666], + "933": [0, 0.68611, 0.10778, 0, 0.88555], + "934": [0, 0.68611, 0.05632, 0, 0.82666], + "936": [0, 0.68611, 0.10778, 0, 0.88555], + "937": [0, 0.68611, 0.0992, 0, 0.82666], + "8211": [0, 0.44444, 0.09811, 0, 0.59111], + "8212": [0, 0.44444, 0.09811, 0, 1.18221], + "8216": [0, 0.69444, 0.12945, 0, 0.35555], + "8217": [0, 0.69444, 0.12945, 0, 0.35555], + "8220": [0, 0.69444, 0.16772, 0, 0.62055], + "8221": [0, 0.69444, 0.07939, 0, 0.62055], + }, + "Main-Italic": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0.12417, 0, 0.30667], + "34": [0, 0.69444, 0.06961, 0, 0.51444], + "35": [0.19444, 0.69444, 0.06616, 0, 0.81777], + "37": [0.05556, 0.75, 0.13639, 0, 0.81777], + "38": [0, 0.69444, 0.09694, 0, 0.76666], + "39": [0, 0.69444, 0.12417, 0, 0.30667], + "40": [0.25, 0.75, 0.16194, 0, 0.40889], + "41": [0.25, 0.75, 0.03694, 0, 0.40889], + "42": [0, 0.75, 0.14917, 0, 0.51111], + "43": [0.05667, 0.56167, 0.03694, 0, 0.76666], + "44": [0.19444, 0.10556, 0, 0, 0.30667], + "45": [0, 0.43056, 0.02826, 0, 0.35778], + "46": [0, 0.10556, 0, 0, 0.30667], + "47": [0.25, 0.75, 0.16194, 0, 0.51111], + "48": [0, 0.64444, 0.13556, 0, 0.51111], + "49": [0, 0.64444, 0.13556, 0, 0.51111], + "50": [0, 0.64444, 0.13556, 0, 0.51111], + "51": [0, 0.64444, 0.13556, 0, 0.51111], + "52": [0.19444, 0.64444, 0.13556, 0, 0.51111], + "53": [0, 0.64444, 0.13556, 0, 0.51111], + "54": [0, 0.64444, 0.13556, 0, 0.51111], + "55": [0.19444, 0.64444, 0.13556, 0, 0.51111], + "56": [0, 0.64444, 0.13556, 0, 0.51111], + "57": [0, 0.64444, 0.13556, 0, 0.51111], + "58": [0, 0.43056, 0.0582, 0, 0.30667], + "59": [0.19444, 0.43056, 0.0582, 0, 0.30667], + "61": [-0.13313, 0.36687, 0.06616, 0, 0.76666], + "63": [0, 0.69444, 0.1225, 0, 0.51111], + "64": [0, 0.69444, 0.09597, 0, 0.76666], + "65": [0, 0.68333, 0, 0, 0.74333], + "66": [0, 0.68333, 0.10257, 0, 0.70389], + "67": [0, 0.68333, 0.14528, 0, 0.71555], + "68": [0, 0.68333, 0.09403, 0, 0.755], + "69": [0, 0.68333, 0.12028, 0, 0.67833], + "70": [0, 0.68333, 0.13305, 0, 0.65277], + "71": [0, 0.68333, 0.08722, 0, 0.77361], + "72": [0, 0.68333, 0.16389, 0, 0.74333], + "73": [0, 0.68333, 0.15806, 0, 0.38555], + "74": [0, 0.68333, 0.14028, 0, 0.525], + "75": [0, 0.68333, 0.14528, 0, 0.76888], + "76": [0, 0.68333, 0, 0, 0.62722], + "77": [0, 0.68333, 0.16389, 0, 0.89666], + "78": [0, 0.68333, 0.16389, 0, 0.74333], + "79": [0, 0.68333, 0.09403, 0, 0.76666], + "80": [0, 0.68333, 0.10257, 0, 0.67833], + "81": [0.19444, 0.68333, 0.09403, 0, 0.76666], + "82": [0, 0.68333, 0.03868, 0, 0.72944], + "83": [0, 0.68333, 0.11972, 0, 0.56222], + "84": [0, 0.68333, 0.13305, 0, 0.71555], + "85": [0, 0.68333, 0.16389, 0, 0.74333], + "86": [0, 0.68333, 0.18361, 0, 0.74333], + "87": [0, 0.68333, 0.18361, 0, 0.99888], + "88": [0, 0.68333, 0.15806, 0, 0.74333], + "89": [0, 0.68333, 0.19383, 0, 0.74333], + "90": [0, 0.68333, 0.14528, 0, 0.61333], + "91": [0.25, 0.75, 0.1875, 0, 0.30667], + "93": [0.25, 0.75, 0.10528, 0, 0.30667], + "94": [0, 0.69444, 0.06646, 0, 0.51111], + "95": [0.31, 0.12056, 0.09208, 0, 0.51111], + "97": [0, 0.43056, 0.07671, 0, 0.51111], + "98": [0, 0.69444, 0.06312, 0, 0.46], + "99": [0, 0.43056, 0.05653, 0, 0.46], + "100": [0, 0.69444, 0.10333, 0, 0.51111], + "101": [0, 0.43056, 0.07514, 0, 0.46], + "102": [0.19444, 0.69444, 0.21194, 0, 0.30667], + "103": [0.19444, 0.43056, 0.08847, 0, 0.46], + "104": [0, 0.69444, 0.07671, 0, 0.51111], + "105": [0, 0.65536, 0.1019, 0, 0.30667], + "106": [0.19444, 0.65536, 0.14467, 0, 0.30667], + "107": [0, 0.69444, 0.10764, 0, 0.46], + "108": [0, 0.69444, 0.10333, 0, 0.25555], + "109": [0, 0.43056, 0.07671, 0, 0.81777], + "110": [0, 0.43056, 0.07671, 0, 0.56222], + "111": [0, 0.43056, 0.06312, 0, 0.51111], + "112": [0.19444, 0.43056, 0.06312, 0, 0.51111], + "113": [0.19444, 0.43056, 0.08847, 0, 0.46], + "114": [0, 0.43056, 0.10764, 0, 0.42166], + "115": [0, 0.43056, 0.08208, 0, 0.40889], + "116": [0, 0.61508, 0.09486, 0, 0.33222], + "117": [0, 0.43056, 0.07671, 0, 0.53666], + "118": [0, 0.43056, 0.10764, 0, 0.46], + "119": [0, 0.43056, 0.10764, 0, 0.66444], + "120": [0, 0.43056, 0.12042, 0, 0.46389], + "121": [0.19444, 0.43056, 0.08847, 0, 0.48555], + "122": [0, 0.43056, 0.12292, 0, 0.40889], + "126": [0.35, 0.31786, 0.11585, 0, 0.51111], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.66786, 0.10474, 0, 0.51111], + "176": [0, 0.69444, 0, 0, 0.83129], + "184": [0.17014, 0, 0, 0, 0.46], + "198": [0, 0.68333, 0.12028, 0, 0.88277], + "216": [0.04861, 0.73194, 0.09403, 0, 0.76666], + "223": [0.19444, 0.69444, 0.10514, 0, 0.53666], + "230": [0, 0.43056, 0.07514, 0, 0.71555], + "248": [0.09722, 0.52778, 0.09194, 0, 0.51111], + "338": [0, 0.68333, 0.12028, 0, 0.98499], + "339": [0, 0.43056, 0.07514, 0, 0.71555], + "710": [0, 0.69444, 0.06646, 0, 0.51111], + "711": [0, 0.62847, 0.08295, 0, 0.51111], + "713": [0, 0.56167, 0.10333, 0, 0.51111], + "714": [0, 0.69444, 0.09694, 0, 0.51111], + "715": [0, 0.69444, 0, 0, 0.51111], + "728": [0, 0.69444, 0.10806, 0, 0.51111], + "729": [0, 0.66786, 0.11752, 0, 0.30667], + "730": [0, 0.69444, 0, 0, 0.83129], + "732": [0, 0.66786, 0.11585, 0, 0.51111], + "733": [0, 0.69444, 0.1225, 0, 0.51111], + "915": [0, 0.68333, 0.13305, 0, 0.62722], + "916": [0, 0.68333, 0, 0, 0.81777], + "920": [0, 0.68333, 0.09403, 0, 0.76666], + "923": [0, 0.68333, 0, 0, 0.69222], + "926": [0, 0.68333, 0.15294, 0, 0.66444], + "928": [0, 0.68333, 0.16389, 0, 0.74333], + "931": [0, 0.68333, 0.12028, 0, 0.71555], + "933": [0, 0.68333, 0.11111, 0, 0.76666], + "934": [0, 0.68333, 0.05986, 0, 0.71555], + "936": [0, 0.68333, 0.11111, 0, 0.76666], + "937": [0, 0.68333, 0.10257, 0, 0.71555], + "8211": [0, 0.43056, 0.09208, 0, 0.51111], + "8212": [0, 0.43056, 0.09208, 0, 1.02222], + "8216": [0, 0.69444, 0.12417, 0, 0.30667], + "8217": [0, 0.69444, 0.12417, 0, 0.30667], + "8220": [0, 0.69444, 0.1685, 0, 0.51444], + "8221": [0, 0.69444, 0.06961, 0, 0.51444], + "8463": [0, 0.68889, 0, 0, 0.54028], + }, + "Main-Regular": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0, 0, 0.27778], + "34": [0, 0.69444, 0, 0, 0.5], + "35": [0.19444, 0.69444, 0, 0, 0.83334], + "36": [0.05556, 0.75, 0, 0, 0.5], + "37": [0.05556, 0.75, 0, 0, 0.83334], + "38": [0, 0.69444, 0, 0, 0.77778], + "39": [0, 0.69444, 0, 0, 0.27778], + "40": [0.25, 0.75, 0, 0, 0.38889], + "41": [0.25, 0.75, 0, 0, 0.38889], + "42": [0, 0.75, 0, 0, 0.5], + "43": [0.08333, 0.58333, 0, 0, 0.77778], + "44": [0.19444, 0.10556, 0, 0, 0.27778], + "45": [0, 0.43056, 0, 0, 0.33333], + "46": [0, 0.10556, 0, 0, 0.27778], + "47": [0.25, 0.75, 0, 0, 0.5], + "48": [0, 0.64444, 0, 0, 0.5], + "49": [0, 0.64444, 0, 0, 0.5], + "50": [0, 0.64444, 0, 0, 0.5], + "51": [0, 0.64444, 0, 0, 0.5], + "52": [0, 0.64444, 0, 0, 0.5], + "53": [0, 0.64444, 0, 0, 0.5], + "54": [0, 0.64444, 0, 0, 0.5], + "55": [0, 0.64444, 0, 0, 0.5], + "56": [0, 0.64444, 0, 0, 0.5], + "57": [0, 0.64444, 0, 0, 0.5], + "58": [0, 0.43056, 0, 0, 0.27778], + "59": [0.19444, 0.43056, 0, 0, 0.27778], + "60": [0.0391, 0.5391, 0, 0, 0.77778], + "61": [-0.13313, 0.36687, 0, 0, 0.77778], + "62": [0.0391, 0.5391, 0, 0, 0.77778], + "63": [0, 0.69444, 0, 0, 0.47222], + "64": [0, 0.69444, 0, 0, 0.77778], + "65": [0, 0.68333, 0, 0, 0.75], + "66": [0, 0.68333, 0, 0, 0.70834], + "67": [0, 0.68333, 0, 0, 0.72222], + "68": [0, 0.68333, 0, 0, 0.76389], + "69": [0, 0.68333, 0, 0, 0.68056], + "70": [0, 0.68333, 0, 0, 0.65278], + "71": [0, 0.68333, 0, 0, 0.78472], + "72": [0, 0.68333, 0, 0, 0.75], + "73": [0, 0.68333, 0, 0, 0.36111], + "74": [0, 0.68333, 0, 0, 0.51389], + "75": [0, 0.68333, 0, 0, 0.77778], + "76": [0, 0.68333, 0, 0, 0.625], + "77": [0, 0.68333, 0, 0, 0.91667], + "78": [0, 0.68333, 0, 0, 0.75], + "79": [0, 0.68333, 0, 0, 0.77778], + "80": [0, 0.68333, 0, 0, 0.68056], + "81": [0.19444, 0.68333, 0, 0, 0.77778], + "82": [0, 0.68333, 0, 0, 0.73611], + "83": [0, 0.68333, 0, 0, 0.55556], + "84": [0, 0.68333, 0, 0, 0.72222], + "85": [0, 0.68333, 0, 0, 0.75], + "86": [0, 0.68333, 0.01389, 0, 0.75], + "87": [0, 0.68333, 0.01389, 0, 1.02778], + "88": [0, 0.68333, 0, 0, 0.75], + "89": [0, 0.68333, 0.025, 0, 0.75], + "90": [0, 0.68333, 0, 0, 0.61111], + "91": [0.25, 0.75, 0, 0, 0.27778], + "92": [0.25, 0.75, 0, 0, 0.5], + "93": [0.25, 0.75, 0, 0, 0.27778], + "94": [0, 0.69444, 0, 0, 0.5], + "95": [0.31, 0.12056, 0.02778, 0, 0.5], + "97": [0, 0.43056, 0, 0, 0.5], + "98": [0, 0.69444, 0, 0, 0.55556], + "99": [0, 0.43056, 0, 0, 0.44445], + "100": [0, 0.69444, 0, 0, 0.55556], + "101": [0, 0.43056, 0, 0, 0.44445], + "102": [0, 0.69444, 0.07778, 0, 0.30556], + "103": [0.19444, 0.43056, 0.01389, 0, 0.5], + "104": [0, 0.69444, 0, 0, 0.55556], + "105": [0, 0.66786, 0, 0, 0.27778], + "106": [0.19444, 0.66786, 0, 0, 0.30556], + "107": [0, 0.69444, 0, 0, 0.52778], + "108": [0, 0.69444, 0, 0, 0.27778], + "109": [0, 0.43056, 0, 0, 0.83334], + "110": [0, 0.43056, 0, 0, 0.55556], + "111": [0, 0.43056, 0, 0, 0.5], + "112": [0.19444, 0.43056, 0, 0, 0.55556], + "113": [0.19444, 0.43056, 0, 0, 0.52778], + "114": [0, 0.43056, 0, 0, 0.39167], + "115": [0, 0.43056, 0, 0, 0.39445], + "116": [0, 0.61508, 0, 0, 0.38889], + "117": [0, 0.43056, 0, 0, 0.55556], + "118": [0, 0.43056, 0.01389, 0, 0.52778], + "119": [0, 0.43056, 0.01389, 0, 0.72222], + "120": [0, 0.43056, 0, 0, 0.52778], + "121": [0.19444, 0.43056, 0.01389, 0, 0.52778], + "122": [0, 0.43056, 0, 0, 0.44445], + "123": [0.25, 0.75, 0, 0, 0.5], + "124": [0.25, 0.75, 0, 0, 0.27778], + "125": [0.25, 0.75, 0, 0, 0.5], + "126": [0.35, 0.31786, 0, 0, 0.5], + "160": [0, 0, 0, 0, 0.25], + "163": [0, 0.69444, 0, 0, 0.76909], + "167": [0.19444, 0.69444, 0, 0, 0.44445], + "168": [0, 0.66786, 0, 0, 0.5], + "172": [0, 0.43056, 0, 0, 0.66667], + "176": [0, 0.69444, 0, 0, 0.75], + "177": [0.08333, 0.58333, 0, 0, 0.77778], + "182": [0.19444, 0.69444, 0, 0, 0.61111], + "184": [0.17014, 0, 0, 0, 0.44445], + "198": [0, 0.68333, 0, 0, 0.90278], + "215": [0.08333, 0.58333, 0, 0, 0.77778], + "216": [0.04861, 0.73194, 0, 0, 0.77778], + "223": [0, 0.69444, 0, 0, 0.5], + "230": [0, 0.43056, 0, 0, 0.72222], + "247": [0.08333, 0.58333, 0, 0, 0.77778], + "248": [0.09722, 0.52778, 0, 0, 0.5], + "305": [0, 0.43056, 0, 0, 0.27778], + "338": [0, 0.68333, 0, 0, 1.01389], + "339": [0, 0.43056, 0, 0, 0.77778], + "567": [0.19444, 0.43056, 0, 0, 0.30556], + "710": [0, 0.69444, 0, 0, 0.5], + "711": [0, 0.62847, 0, 0, 0.5], + "713": [0, 0.56778, 0, 0, 0.5], + "714": [0, 0.69444, 0, 0, 0.5], + "715": [0, 0.69444, 0, 0, 0.5], + "728": [0, 0.69444, 0, 0, 0.5], + "729": [0, 0.66786, 0, 0, 0.27778], + "730": [0, 0.69444, 0, 0, 0.75], + "732": [0, 0.66786, 0, 0, 0.5], + "733": [0, 0.69444, 0, 0, 0.5], + "915": [0, 0.68333, 0, 0, 0.625], + "916": [0, 0.68333, 0, 0, 0.83334], + "920": [0, 0.68333, 0, 0, 0.77778], + "923": [0, 0.68333, 0, 0, 0.69445], + "926": [0, 0.68333, 0, 0, 0.66667], + "928": [0, 0.68333, 0, 0, 0.75], + "931": [0, 0.68333, 0, 0, 0.72222], + "933": [0, 0.68333, 0, 0, 0.77778], + "934": [0, 0.68333, 0, 0, 0.72222], + "936": [0, 0.68333, 0, 0, 0.77778], + "937": [0, 0.68333, 0, 0, 0.72222], + "8211": [0, 0.43056, 0.02778, 0, 0.5], + "8212": [0, 0.43056, 0.02778, 0, 1.0], + "8216": [0, 0.69444, 0, 0, 0.27778], + "8217": [0, 0.69444, 0, 0, 0.27778], + "8220": [0, 0.69444, 0, 0, 0.5], + "8221": [0, 0.69444, 0, 0, 0.5], + "8224": [0.19444, 0.69444, 0, 0, 0.44445], + "8225": [0.19444, 0.69444, 0, 0, 0.44445], + "8230": [0, 0.123, 0, 0, 1.172], + "8242": [0, 0.55556, 0, 0, 0.275], + "8407": [0, 0.71444, 0.15382, 0, 0.5], + "8463": [0, 0.68889, 0, 0, 0.54028], + "8465": [0, 0.69444, 0, 0, 0.72222], + "8467": [0, 0.69444, 0, 0.11111, 0.41667], + "8472": [0.19444, 0.43056, 0, 0.11111, 0.63646], + "8476": [0, 0.69444, 0, 0, 0.72222], + "8501": [0, 0.69444, 0, 0, 0.61111], + "8592": [-0.13313, 0.36687, 0, 0, 1.0], + "8593": [0.19444, 0.69444, 0, 0, 0.5], + "8594": [-0.13313, 0.36687, 0, 0, 1.0], + "8595": [0.19444, 0.69444, 0, 0, 0.5], + "8596": [-0.13313, 0.36687, 0, 0, 1.0], + "8597": [0.25, 0.75, 0, 0, 0.5], + "8598": [0.19444, 0.69444, 0, 0, 1.0], + "8599": [0.19444, 0.69444, 0, 0, 1.0], + "8600": [0.19444, 0.69444, 0, 0, 1.0], + "8601": [0.19444, 0.69444, 0, 0, 1.0], + "8614": [0.011, 0.511, 0, 0, 1.0], + "8617": [0.011, 0.511, 0, 0, 1.126], + "8618": [0.011, 0.511, 0, 0, 1.126], + "8636": [-0.13313, 0.36687, 0, 0, 1.0], + "8637": [-0.13313, 0.36687, 0, 0, 1.0], + "8640": [-0.13313, 0.36687, 0, 0, 1.0], + "8641": [-0.13313, 0.36687, 0, 0, 1.0], + "8652": [0.011, 0.671, 0, 0, 1.0], + "8656": [-0.13313, 0.36687, 0, 0, 1.0], + "8657": [0.19444, 0.69444, 0, 0, 0.61111], + "8658": [-0.13313, 0.36687, 0, 0, 1.0], + "8659": [0.19444, 0.69444, 0, 0, 0.61111], + "8660": [-0.13313, 0.36687, 0, 0, 1.0], + "8661": [0.25, 0.75, 0, 0, 0.61111], + "8704": [0, 0.69444, 0, 0, 0.55556], + "8706": [0, 0.69444, 0.05556, 0.08334, 0.5309], + "8707": [0, 0.69444, 0, 0, 0.55556], + "8709": [0.05556, 0.75, 0, 0, 0.5], + "8711": [0, 0.68333, 0, 0, 0.83334], + "8712": [0.0391, 0.5391, 0, 0, 0.66667], + "8715": [0.0391, 0.5391, 0, 0, 0.66667], + "8722": [0.08333, 0.58333, 0, 0, 0.77778], + "8723": [0.08333, 0.58333, 0, 0, 0.77778], + "8725": [0.25, 0.75, 0, 0, 0.5], + "8726": [0.25, 0.75, 0, 0, 0.5], + "8727": [-0.03472, 0.46528, 0, 0, 0.5], + "8728": [-0.05555, 0.44445, 0, 0, 0.5], + "8729": [-0.05555, 0.44445, 0, 0, 0.5], + "8730": [0.2, 0.8, 0, 0, 0.83334], + "8733": [0, 0.43056, 0, 0, 0.77778], + "8734": [0, 0.43056, 0, 0, 1.0], + "8736": [0, 0.69224, 0, 0, 0.72222], + "8739": [0.25, 0.75, 0, 0, 0.27778], + "8741": [0.25, 0.75, 0, 0, 0.5], + "8743": [0, 0.55556, 0, 0, 0.66667], + "8744": [0, 0.55556, 0, 0, 0.66667], + "8745": [0, 0.55556, 0, 0, 0.66667], + "8746": [0, 0.55556, 0, 0, 0.66667], + "8747": [0.19444, 0.69444, 0.11111, 0, 0.41667], + "8764": [-0.13313, 0.36687, 0, 0, 0.77778], + "8768": [0.19444, 0.69444, 0, 0, 0.27778], + "8771": [-0.03625, 0.46375, 0, 0, 0.77778], + "8773": [-0.022, 0.589, 0, 0, 0.778], + "8776": [-0.01688, 0.48312, 0, 0, 0.77778], + "8781": [-0.03625, 0.46375, 0, 0, 0.77778], + "8784": [-0.133, 0.673, 0, 0, 0.778], + "8801": [-0.03625, 0.46375, 0, 0, 0.77778], + "8804": [0.13597, 0.63597, 0, 0, 0.77778], + "8805": [0.13597, 0.63597, 0, 0, 0.77778], + "8810": [0.0391, 0.5391, 0, 0, 1.0], + "8811": [0.0391, 0.5391, 0, 0, 1.0], + "8826": [0.0391, 0.5391, 0, 0, 0.77778], + "8827": [0.0391, 0.5391, 0, 0, 0.77778], + "8834": [0.0391, 0.5391, 0, 0, 0.77778], + "8835": [0.0391, 0.5391, 0, 0, 0.77778], + "8838": [0.13597, 0.63597, 0, 0, 0.77778], + "8839": [0.13597, 0.63597, 0, 0, 0.77778], + "8846": [0, 0.55556, 0, 0, 0.66667], + "8849": [0.13597, 0.63597, 0, 0, 0.77778], + "8850": [0.13597, 0.63597, 0, 0, 0.77778], + "8851": [0, 0.55556, 0, 0, 0.66667], + "8852": [0, 0.55556, 0, 0, 0.66667], + "8853": [0.08333, 0.58333, 0, 0, 0.77778], + "8854": [0.08333, 0.58333, 0, 0, 0.77778], + "8855": [0.08333, 0.58333, 0, 0, 0.77778], + "8856": [0.08333, 0.58333, 0, 0, 0.77778], + "8857": [0.08333, 0.58333, 0, 0, 0.77778], + "8866": [0, 0.69444, 0, 0, 0.61111], + "8867": [0, 0.69444, 0, 0, 0.61111], + "8868": [0, 0.69444, 0, 0, 0.77778], + "8869": [0, 0.69444, 0, 0, 0.77778], + "8872": [0.249, 0.75, 0, 0, 0.867], + "8900": [-0.05555, 0.44445, 0, 0, 0.5], + "8901": [-0.05555, 0.44445, 0, 0, 0.27778], + "8902": [-0.03472, 0.46528, 0, 0, 0.5], + "8904": [0.005, 0.505, 0, 0, 0.9], + "8942": [0.03, 0.903, 0, 0, 0.278], + "8943": [-0.19, 0.313, 0, 0, 1.172], + "8945": [-0.1, 0.823, 0, 0, 1.282], + "8968": [0.25, 0.75, 0, 0, 0.44445], + "8969": [0.25, 0.75, 0, 0, 0.44445], + "8970": [0.25, 0.75, 0, 0, 0.44445], + "8971": [0.25, 0.75, 0, 0, 0.44445], + "8994": [-0.14236, 0.35764, 0, 0, 1.0], + "8995": [-0.14236, 0.35764, 0, 0, 1.0], + "9136": [0.244, 0.744, 0, 0, 0.412], + "9137": [0.244, 0.745, 0, 0, 0.412], + "9651": [0.19444, 0.69444, 0, 0, 0.88889], + "9657": [-0.03472, 0.46528, 0, 0, 0.5], + "9661": [0.19444, 0.69444, 0, 0, 0.88889], + "9667": [-0.03472, 0.46528, 0, 0, 0.5], + "9711": [0.19444, 0.69444, 0, 0, 1.0], + "9824": [0.12963, 0.69444, 0, 0, 0.77778], + "9825": [0.12963, 0.69444, 0, 0, 0.77778], + "9826": [0.12963, 0.69444, 0, 0, 0.77778], + "9827": [0.12963, 0.69444, 0, 0, 0.77778], + "9837": [0, 0.75, 0, 0, 0.38889], + "9838": [0.19444, 0.69444, 0, 0, 0.38889], + "9839": [0.19444, 0.69444, 0, 0, 0.38889], + "10216": [0.25, 0.75, 0, 0, 0.38889], + "10217": [0.25, 0.75, 0, 0, 0.38889], + "10222": [0.244, 0.744, 0, 0, 0.412], + "10223": [0.244, 0.745, 0, 0, 0.412], + "10229": [0.011, 0.511, 0, 0, 1.609], + "10230": [0.011, 0.511, 0, 0, 1.638], + "10231": [0.011, 0.511, 0, 0, 1.859], + "10232": [0.024, 0.525, 0, 0, 1.609], + "10233": [0.024, 0.525, 0, 0, 1.638], + "10234": [0.024, 0.525, 0, 0, 1.858], + "10236": [0.011, 0.511, 0, 0, 1.638], + "10815": [0, 0.68333, 0, 0, 0.75], + "10927": [0.13597, 0.63597, 0, 0, 0.77778], + "10928": [0.13597, 0.63597, 0, 0, 0.77778], + "57376": [0.19444, 0.69444, 0, 0, 0], + }, + "Math-BoldItalic": { + "32": [0, 0, 0, 0, 0.25], + "48": [0, 0.44444, 0, 0, 0.575], + "49": [0, 0.44444, 0, 0, 0.575], + "50": [0, 0.44444, 0, 0, 0.575], + "51": [0.19444, 0.44444, 0, 0, 0.575], + "52": [0.19444, 0.44444, 0, 0, 0.575], + "53": [0.19444, 0.44444, 0, 0, 0.575], + "54": [0, 0.64444, 0, 0, 0.575], + "55": [0.19444, 0.44444, 0, 0, 0.575], + "56": [0, 0.64444, 0, 0, 0.575], + "57": [0.19444, 0.44444, 0, 0, 0.575], + "65": [0, 0.68611, 0, 0, 0.86944], + "66": [0, 0.68611, 0.04835, 0, 0.8664], + "67": [0, 0.68611, 0.06979, 0, 0.81694], + "68": [0, 0.68611, 0.03194, 0, 0.93812], + "69": [0, 0.68611, 0.05451, 0, 0.81007], + "70": [0, 0.68611, 0.15972, 0, 0.68889], + "71": [0, 0.68611, 0, 0, 0.88673], + "72": [0, 0.68611, 0.08229, 0, 0.98229], + "73": [0, 0.68611, 0.07778, 0, 0.51111], + "74": [0, 0.68611, 0.10069, 0, 0.63125], + "75": [0, 0.68611, 0.06979, 0, 0.97118], + "76": [0, 0.68611, 0, 0, 0.75555], + "77": [0, 0.68611, 0.11424, 0, 1.14201], + "78": [0, 0.68611, 0.11424, 0, 0.95034], + "79": [0, 0.68611, 0.03194, 0, 0.83666], + "80": [0, 0.68611, 0.15972, 0, 0.72309], + "81": [0.19444, 0.68611, 0, 0, 0.86861], + "82": [0, 0.68611, 0.00421, 0, 0.87235], + "83": [0, 0.68611, 0.05382, 0, 0.69271], + "84": [0, 0.68611, 0.15972, 0, 0.63663], + "85": [0, 0.68611, 0.11424, 0, 0.80027], + "86": [0, 0.68611, 0.25555, 0, 0.67778], + "87": [0, 0.68611, 0.15972, 0, 1.09305], + "88": [0, 0.68611, 0.07778, 0, 0.94722], + "89": [0, 0.68611, 0.25555, 0, 0.67458], + "90": [0, 0.68611, 0.06979, 0, 0.77257], + "97": [0, 0.44444, 0, 0, 0.63287], + "98": [0, 0.69444, 0, 0, 0.52083], + "99": [0, 0.44444, 0, 0, 0.51342], + "100": [0, 0.69444, 0, 0, 0.60972], + "101": [0, 0.44444, 0, 0, 0.55361], + "102": [0.19444, 0.69444, 0.11042, 0, 0.56806], + "103": [0.19444, 0.44444, 0.03704, 0, 0.5449], + "104": [0, 0.69444, 0, 0, 0.66759], + "105": [0, 0.69326, 0, 0, 0.4048], + "106": [0.19444, 0.69326, 0.0622, 0, 0.47083], + "107": [0, 0.69444, 0.01852, 0, 0.6037], + "108": [0, 0.69444, 0.0088, 0, 0.34815], + "109": [0, 0.44444, 0, 0, 1.0324], + "110": [0, 0.44444, 0, 0, 0.71296], + "111": [0, 0.44444, 0, 0, 0.58472], + "112": [0.19444, 0.44444, 0, 0, 0.60092], + "113": [0.19444, 0.44444, 0.03704, 0, 0.54213], + "114": [0, 0.44444, 0.03194, 0, 0.5287], + "115": [0, 0.44444, 0, 0, 0.53125], + "116": [0, 0.63492, 0, 0, 0.41528], + "117": [0, 0.44444, 0, 0, 0.68102], + "118": [0, 0.44444, 0.03704, 0, 0.56666], + "119": [0, 0.44444, 0.02778, 0, 0.83148], + "120": [0, 0.44444, 0, 0, 0.65903], + "121": [0.19444, 0.44444, 0.03704, 0, 0.59028], + "122": [0, 0.44444, 0.04213, 0, 0.55509], + "160": [0, 0, 0, 0, 0.25], + "915": [0, 0.68611, 0.15972, 0, 0.65694], + "916": [0, 0.68611, 0, 0, 0.95833], + "920": [0, 0.68611, 0.03194, 0, 0.86722], + "923": [0, 0.68611, 0, 0, 0.80555], + "926": [0, 0.68611, 0.07458, 0, 0.84125], + "928": [0, 0.68611, 0.08229, 0, 0.98229], + "931": [0, 0.68611, 0.05451, 0, 0.88507], + "933": [0, 0.68611, 0.15972, 0, 0.67083], + "934": [0, 0.68611, 0, 0, 0.76666], + "936": [0, 0.68611, 0.11653, 0, 0.71402], + "937": [0, 0.68611, 0.04835, 0, 0.8789], + "945": [0, 0.44444, 0, 0, 0.76064], + "946": [0.19444, 0.69444, 0.03403, 0, 0.65972], + "947": [0.19444, 0.44444, 0.06389, 0, 0.59003], + "948": [0, 0.69444, 0.03819, 0, 0.52222], + "949": [0, 0.44444, 0, 0, 0.52882], + "950": [0.19444, 0.69444, 0.06215, 0, 0.50833], + "951": [0.19444, 0.44444, 0.03704, 0, 0.6], + "952": [0, 0.69444, 0.03194, 0, 0.5618], + "953": [0, 0.44444, 0, 0, 0.41204], + "954": [0, 0.44444, 0, 0, 0.66759], + "955": [0, 0.69444, 0, 0, 0.67083], + "956": [0.19444, 0.44444, 0, 0, 0.70787], + "957": [0, 0.44444, 0.06898, 0, 0.57685], + "958": [0.19444, 0.69444, 0.03021, 0, 0.50833], + "959": [0, 0.44444, 0, 0, 0.58472], + "960": [0, 0.44444, 0.03704, 0, 0.68241], + "961": [0.19444, 0.44444, 0, 0, 0.6118], + "962": [0.09722, 0.44444, 0.07917, 0, 0.42361], + "963": [0, 0.44444, 0.03704, 0, 0.68588], + "964": [0, 0.44444, 0.13472, 0, 0.52083], + "965": [0, 0.44444, 0.03704, 0, 0.63055], + "966": [0.19444, 0.44444, 0, 0, 0.74722], + "967": [0.19444, 0.44444, 0, 0, 0.71805], + "968": [0.19444, 0.69444, 0.03704, 0, 0.75833], + "969": [0, 0.44444, 0.03704, 0, 0.71782], + "977": [0, 0.69444, 0, 0, 0.69155], + "981": [0.19444, 0.69444, 0, 0, 0.7125], + "982": [0, 0.44444, 0.03194, 0, 0.975], + "1009": [0.19444, 0.44444, 0, 0, 0.6118], + "1013": [0, 0.44444, 0, 0, 0.48333], + "57649": [0, 0.44444, 0, 0, 0.39352], + "57911": [0.19444, 0.44444, 0, 0, 0.43889], + }, + "Math-Italic": { + "32": [0, 0, 0, 0, 0.25], + "48": [0, 0.43056, 0, 0, 0.5], + "49": [0, 0.43056, 0, 0, 0.5], + "50": [0, 0.43056, 0, 0, 0.5], + "51": [0.19444, 0.43056, 0, 0, 0.5], + "52": [0.19444, 0.43056, 0, 0, 0.5], + "53": [0.19444, 0.43056, 0, 0, 0.5], + "54": [0, 0.64444, 0, 0, 0.5], + "55": [0.19444, 0.43056, 0, 0, 0.5], + "56": [0, 0.64444, 0, 0, 0.5], + "57": [0.19444, 0.43056, 0, 0, 0.5], + "65": [0, 0.68333, 0, 0.13889, 0.75], + "66": [0, 0.68333, 0.05017, 0.08334, 0.75851], + "67": [0, 0.68333, 0.07153, 0.08334, 0.71472], + "68": [0, 0.68333, 0.02778, 0.05556, 0.82792], + "69": [0, 0.68333, 0.05764, 0.08334, 0.7382], + "70": [0, 0.68333, 0.13889, 0.08334, 0.64306], + "71": [0, 0.68333, 0, 0.08334, 0.78625], + "72": [0, 0.68333, 0.08125, 0.05556, 0.83125], + "73": [0, 0.68333, 0.07847, 0.11111, 0.43958], + "74": [0, 0.68333, 0.09618, 0.16667, 0.55451], + "75": [0, 0.68333, 0.07153, 0.05556, 0.84931], + "76": [0, 0.68333, 0, 0.02778, 0.68056], + "77": [0, 0.68333, 0.10903, 0.08334, 0.97014], + "78": [0, 0.68333, 0.10903, 0.08334, 0.80347], + "79": [0, 0.68333, 0.02778, 0.08334, 0.76278], + "80": [0, 0.68333, 0.13889, 0.08334, 0.64201], + "81": [0.19444, 0.68333, 0, 0.08334, 0.79056], + "82": [0, 0.68333, 0.00773, 0.08334, 0.75929], + "83": [0, 0.68333, 0.05764, 0.08334, 0.6132], + "84": [0, 0.68333, 0.13889, 0.08334, 0.58438], + "85": [0, 0.68333, 0.10903, 0.02778, 0.68278], + "86": [0, 0.68333, 0.22222, 0, 0.58333], + "87": [0, 0.68333, 0.13889, 0, 0.94445], + "88": [0, 0.68333, 0.07847, 0.08334, 0.82847], + "89": [0, 0.68333, 0.22222, 0, 0.58056], + "90": [0, 0.68333, 0.07153, 0.08334, 0.68264], + "97": [0, 0.43056, 0, 0, 0.52859], + "98": [0, 0.69444, 0, 0, 0.42917], + "99": [0, 0.43056, 0, 0.05556, 0.43276], + "100": [0, 0.69444, 0, 0.16667, 0.52049], + "101": [0, 0.43056, 0, 0.05556, 0.46563], + "102": [0.19444, 0.69444, 0.10764, 0.16667, 0.48959], + "103": [0.19444, 0.43056, 0.03588, 0.02778, 0.47697], + "104": [0, 0.69444, 0, 0, 0.57616], + "105": [0, 0.65952, 0, 0, 0.34451], + "106": [0.19444, 0.65952, 0.05724, 0, 0.41181], + "107": [0, 0.69444, 0.03148, 0, 0.5206], + "108": [0, 0.69444, 0.01968, 0.08334, 0.29838], + "109": [0, 0.43056, 0, 0, 0.87801], + "110": [0, 0.43056, 0, 0, 0.60023], + "111": [0, 0.43056, 0, 0.05556, 0.48472], + "112": [0.19444, 0.43056, 0, 0.08334, 0.50313], + "113": [0.19444, 0.43056, 0.03588, 0.08334, 0.44641], + "114": [0, 0.43056, 0.02778, 0.05556, 0.45116], + "115": [0, 0.43056, 0, 0.05556, 0.46875], + "116": [0, 0.61508, 0, 0.08334, 0.36111], + "117": [0, 0.43056, 0, 0.02778, 0.57246], + "118": [0, 0.43056, 0.03588, 0.02778, 0.48472], + "119": [0, 0.43056, 0.02691, 0.08334, 0.71592], + "120": [0, 0.43056, 0, 0.02778, 0.57153], + "121": [0.19444, 0.43056, 0.03588, 0.05556, 0.49028], + "122": [0, 0.43056, 0.04398, 0.05556, 0.46505], + "160": [0, 0, 0, 0, 0.25], + "915": [0, 0.68333, 0.13889, 0.08334, 0.61528], + "916": [0, 0.68333, 0, 0.16667, 0.83334], + "920": [0, 0.68333, 0.02778, 0.08334, 0.76278], + "923": [0, 0.68333, 0, 0.16667, 0.69445], + "926": [0, 0.68333, 0.07569, 0.08334, 0.74236], + "928": [0, 0.68333, 0.08125, 0.05556, 0.83125], + "931": [0, 0.68333, 0.05764, 0.08334, 0.77986], + "933": [0, 0.68333, 0.13889, 0.05556, 0.58333], + "934": [0, 0.68333, 0, 0.08334, 0.66667], + "936": [0, 0.68333, 0.11, 0.05556, 0.61222], + "937": [0, 0.68333, 0.05017, 0.08334, 0.7724], + "945": [0, 0.43056, 0.0037, 0.02778, 0.6397], + "946": [0.19444, 0.69444, 0.05278, 0.08334, 0.56563], + "947": [0.19444, 0.43056, 0.05556, 0, 0.51773], + "948": [0, 0.69444, 0.03785, 0.05556, 0.44444], + "949": [0, 0.43056, 0, 0.08334, 0.46632], + "950": [0.19444, 0.69444, 0.07378, 0.08334, 0.4375], + "951": [0.19444, 0.43056, 0.03588, 0.05556, 0.49653], + "952": [0, 0.69444, 0.02778, 0.08334, 0.46944], + "953": [0, 0.43056, 0, 0.05556, 0.35394], + "954": [0, 0.43056, 0, 0, 0.57616], + "955": [0, 0.69444, 0, 0, 0.58334], + "956": [0.19444, 0.43056, 0, 0.02778, 0.60255], + "957": [0, 0.43056, 0.06366, 0.02778, 0.49398], + "958": [0.19444, 0.69444, 0.04601, 0.11111, 0.4375], + "959": [0, 0.43056, 0, 0.05556, 0.48472], + "960": [0, 0.43056, 0.03588, 0, 0.57003], + "961": [0.19444, 0.43056, 0, 0.08334, 0.51702], + "962": [0.09722, 0.43056, 0.07986, 0.08334, 0.36285], + "963": [0, 0.43056, 0.03588, 0, 0.57141], + "964": [0, 0.43056, 0.1132, 0.02778, 0.43715], + "965": [0, 0.43056, 0.03588, 0.02778, 0.54028], + "966": [0.19444, 0.43056, 0, 0.08334, 0.65417], + "967": [0.19444, 0.43056, 0, 0.05556, 0.62569], + "968": [0.19444, 0.69444, 0.03588, 0.11111, 0.65139], + "969": [0, 0.43056, 0.03588, 0, 0.62245], + "977": [0, 0.69444, 0, 0.08334, 0.59144], + "981": [0.19444, 0.69444, 0, 0.08334, 0.59583], + "982": [0, 0.43056, 0.02778, 0, 0.82813], + "1009": [0.19444, 0.43056, 0, 0.08334, 0.51702], + "1013": [0, 0.43056, 0, 0.05556, 0.4059], + "57649": [0, 0.43056, 0, 0.02778, 0.32246], + "57911": [0.19444, 0.43056, 0, 0.08334, 0.38403], + }, + "SansSerif-Bold": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0, 0, 0.36667], + "34": [0, 0.69444, 0, 0, 0.55834], + "35": [0.19444, 0.69444, 0, 0, 0.91667], + "36": [0.05556, 0.75, 0, 0, 0.55], + "37": [0.05556, 0.75, 0, 0, 1.02912], + "38": [0, 0.69444, 0, 0, 0.83056], + "39": [0, 0.69444, 0, 0, 0.30556], + "40": [0.25, 0.75, 0, 0, 0.42778], + "41": [0.25, 0.75, 0, 0, 0.42778], + "42": [0, 0.75, 0, 0, 0.55], + "43": [0.11667, 0.61667, 0, 0, 0.85556], + "44": [0.10556, 0.13056, 0, 0, 0.30556], + "45": [0, 0.45833, 0, 0, 0.36667], + "46": [0, 0.13056, 0, 0, 0.30556], + "47": [0.25, 0.75, 0, 0, 0.55], + "48": [0, 0.69444, 0, 0, 0.55], + "49": [0, 0.69444, 0, 0, 0.55], + "50": [0, 0.69444, 0, 0, 0.55], + "51": [0, 0.69444, 0, 0, 0.55], + "52": [0, 0.69444, 0, 0, 0.55], + "53": [0, 0.69444, 0, 0, 0.55], + "54": [0, 0.69444, 0, 0, 0.55], + "55": [0, 0.69444, 0, 0, 0.55], + "56": [0, 0.69444, 0, 0, 0.55], + "57": [0, 0.69444, 0, 0, 0.55], + "58": [0, 0.45833, 0, 0, 0.30556], + "59": [0.10556, 0.45833, 0, 0, 0.30556], + "61": [-0.09375, 0.40625, 0, 0, 0.85556], + "63": [0, 0.69444, 0, 0, 0.51945], + "64": [0, 0.69444, 0, 0, 0.73334], + "65": [0, 0.69444, 0, 0, 0.73334], + "66": [0, 0.69444, 0, 0, 0.73334], + "67": [0, 0.69444, 0, 0, 0.70278], + "68": [0, 0.69444, 0, 0, 0.79445], + "69": [0, 0.69444, 0, 0, 0.64167], + "70": [0, 0.69444, 0, 0, 0.61111], + "71": [0, 0.69444, 0, 0, 0.73334], + "72": [0, 0.69444, 0, 0, 0.79445], + "73": [0, 0.69444, 0, 0, 0.33056], + "74": [0, 0.69444, 0, 0, 0.51945], + "75": [0, 0.69444, 0, 0, 0.76389], + "76": [0, 0.69444, 0, 0, 0.58056], + "77": [0, 0.69444, 0, 0, 0.97778], + "78": [0, 0.69444, 0, 0, 0.79445], + "79": [0, 0.69444, 0, 0, 0.79445], + "80": [0, 0.69444, 0, 0, 0.70278], + "81": [0.10556, 0.69444, 0, 0, 0.79445], + "82": [0, 0.69444, 0, 0, 0.70278], + "83": [0, 0.69444, 0, 0, 0.61111], + "84": [0, 0.69444, 0, 0, 0.73334], + "85": [0, 0.69444, 0, 0, 0.76389], + "86": [0, 0.69444, 0.01528, 0, 0.73334], + "87": [0, 0.69444, 0.01528, 0, 1.03889], + "88": [0, 0.69444, 0, 0, 0.73334], + "89": [0, 0.69444, 0.0275, 0, 0.73334], + "90": [0, 0.69444, 0, 0, 0.67223], + "91": [0.25, 0.75, 0, 0, 0.34306], + "93": [0.25, 0.75, 0, 0, 0.34306], + "94": [0, 0.69444, 0, 0, 0.55], + "95": [0.35, 0.10833, 0.03056, 0, 0.55], + "97": [0, 0.45833, 0, 0, 0.525], + "98": [0, 0.69444, 0, 0, 0.56111], + "99": [0, 0.45833, 0, 0, 0.48889], + "100": [0, 0.69444, 0, 0, 0.56111], + "101": [0, 0.45833, 0, 0, 0.51111], + "102": [0, 0.69444, 0.07639, 0, 0.33611], + "103": [0.19444, 0.45833, 0.01528, 0, 0.55], + "104": [0, 0.69444, 0, 0, 0.56111], + "105": [0, 0.69444, 0, 0, 0.25556], + "106": [0.19444, 0.69444, 0, 0, 0.28611], + "107": [0, 0.69444, 0, 0, 0.53056], + "108": [0, 0.69444, 0, 0, 0.25556], + "109": [0, 0.45833, 0, 0, 0.86667], + "110": [0, 0.45833, 0, 0, 0.56111], + "111": [0, 0.45833, 0, 0, 0.55], + "112": [0.19444, 0.45833, 0, 0, 0.56111], + "113": [0.19444, 0.45833, 0, 0, 0.56111], + "114": [0, 0.45833, 0.01528, 0, 0.37222], + "115": [0, 0.45833, 0, 0, 0.42167], + "116": [0, 0.58929, 0, 0, 0.40417], + "117": [0, 0.45833, 0, 0, 0.56111], + "118": [0, 0.45833, 0.01528, 0, 0.5], + "119": [0, 0.45833, 0.01528, 0, 0.74445], + "120": [0, 0.45833, 0, 0, 0.5], + "121": [0.19444, 0.45833, 0.01528, 0, 0.5], + "122": [0, 0.45833, 0, 0, 0.47639], + "126": [0.35, 0.34444, 0, 0, 0.55], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.69444, 0, 0, 0.55], + "176": [0, 0.69444, 0, 0, 0.73334], + "180": [0, 0.69444, 0, 0, 0.55], + "184": [0.17014, 0, 0, 0, 0.48889], + "305": [0, 0.45833, 0, 0, 0.25556], + "567": [0.19444, 0.45833, 0, 0, 0.28611], + "710": [0, 0.69444, 0, 0, 0.55], + "711": [0, 0.63542, 0, 0, 0.55], + "713": [0, 0.63778, 0, 0, 0.55], + "728": [0, 0.69444, 0, 0, 0.55], + "729": [0, 0.69444, 0, 0, 0.30556], + "730": [0, 0.69444, 0, 0, 0.73334], + "732": [0, 0.69444, 0, 0, 0.55], + "733": [0, 0.69444, 0, 0, 0.55], + "915": [0, 0.69444, 0, 0, 0.58056], + "916": [0, 0.69444, 0, 0, 0.91667], + "920": [0, 0.69444, 0, 0, 0.85556], + "923": [0, 0.69444, 0, 0, 0.67223], + "926": [0, 0.69444, 0, 0, 0.73334], + "928": [0, 0.69444, 0, 0, 0.79445], + "931": [0, 0.69444, 0, 0, 0.79445], + "933": [0, 0.69444, 0, 0, 0.85556], + "934": [0, 0.69444, 0, 0, 0.79445], + "936": [0, 0.69444, 0, 0, 0.85556], + "937": [0, 0.69444, 0, 0, 0.79445], + "8211": [0, 0.45833, 0.03056, 0, 0.55], + "8212": [0, 0.45833, 0.03056, 0, 1.10001], + "8216": [0, 0.69444, 0, 0, 0.30556], + "8217": [0, 0.69444, 0, 0, 0.30556], + "8220": [0, 0.69444, 0, 0, 0.55834], + "8221": [0, 0.69444, 0, 0, 0.55834], + }, + "SansSerif-Italic": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0.05733, 0, 0.31945], + "34": [0, 0.69444, 0.00316, 0, 0.5], + "35": [0.19444, 0.69444, 0.05087, 0, 0.83334], + "36": [0.05556, 0.75, 0.11156, 0, 0.5], + "37": [0.05556, 0.75, 0.03126, 0, 0.83334], + "38": [0, 0.69444, 0.03058, 0, 0.75834], + "39": [0, 0.69444, 0.07816, 0, 0.27778], + "40": [0.25, 0.75, 0.13164, 0, 0.38889], + "41": [0.25, 0.75, 0.02536, 0, 0.38889], + "42": [0, 0.75, 0.11775, 0, 0.5], + "43": [0.08333, 0.58333, 0.02536, 0, 0.77778], + "44": [0.125, 0.08333, 0, 0, 0.27778], + "45": [0, 0.44444, 0.01946, 0, 0.33333], + "46": [0, 0.08333, 0, 0, 0.27778], + "47": [0.25, 0.75, 0.13164, 0, 0.5], + "48": [0, 0.65556, 0.11156, 0, 0.5], + "49": [0, 0.65556, 0.11156, 0, 0.5], + "50": [0, 0.65556, 0.11156, 0, 0.5], + "51": [0, 0.65556, 0.11156, 0, 0.5], + "52": [0, 0.65556, 0.11156, 0, 0.5], + "53": [0, 0.65556, 0.11156, 0, 0.5], + "54": [0, 0.65556, 0.11156, 0, 0.5], + "55": [0, 0.65556, 0.11156, 0, 0.5], + "56": [0, 0.65556, 0.11156, 0, 0.5], + "57": [0, 0.65556, 0.11156, 0, 0.5], + "58": [0, 0.44444, 0.02502, 0, 0.27778], + "59": [0.125, 0.44444, 0.02502, 0, 0.27778], + "61": [-0.13, 0.37, 0.05087, 0, 0.77778], + "63": [0, 0.69444, 0.11809, 0, 0.47222], + "64": [0, 0.69444, 0.07555, 0, 0.66667], + "65": [0, 0.69444, 0, 0, 0.66667], + "66": [0, 0.69444, 0.08293, 0, 0.66667], + "67": [0, 0.69444, 0.11983, 0, 0.63889], + "68": [0, 0.69444, 0.07555, 0, 0.72223], + "69": [0, 0.69444, 0.11983, 0, 0.59722], + "70": [0, 0.69444, 0.13372, 0, 0.56945], + "71": [0, 0.69444, 0.11983, 0, 0.66667], + "72": [0, 0.69444, 0.08094, 0, 0.70834], + "73": [0, 0.69444, 0.13372, 0, 0.27778], + "74": [0, 0.69444, 0.08094, 0, 0.47222], + "75": [0, 0.69444, 0.11983, 0, 0.69445], + "76": [0, 0.69444, 0, 0, 0.54167], + "77": [0, 0.69444, 0.08094, 0, 0.875], + "78": [0, 0.69444, 0.08094, 0, 0.70834], + "79": [0, 0.69444, 0.07555, 0, 0.73611], + "80": [0, 0.69444, 0.08293, 0, 0.63889], + "81": [0.125, 0.69444, 0.07555, 0, 0.73611], + "82": [0, 0.69444, 0.08293, 0, 0.64584], + "83": [0, 0.69444, 0.09205, 0, 0.55556], + "84": [0, 0.69444, 0.13372, 0, 0.68056], + "85": [0, 0.69444, 0.08094, 0, 0.6875], + "86": [0, 0.69444, 0.1615, 0, 0.66667], + "87": [0, 0.69444, 0.1615, 0, 0.94445], + "88": [0, 0.69444, 0.13372, 0, 0.66667], + "89": [0, 0.69444, 0.17261, 0, 0.66667], + "90": [0, 0.69444, 0.11983, 0, 0.61111], + "91": [0.25, 0.75, 0.15942, 0, 0.28889], + "93": [0.25, 0.75, 0.08719, 0, 0.28889], + "94": [0, 0.69444, 0.0799, 0, 0.5], + "95": [0.35, 0.09444, 0.08616, 0, 0.5], + "97": [0, 0.44444, 0.00981, 0, 0.48056], + "98": [0, 0.69444, 0.03057, 0, 0.51667], + "99": [0, 0.44444, 0.08336, 0, 0.44445], + "100": [0, 0.69444, 0.09483, 0, 0.51667], + "101": [0, 0.44444, 0.06778, 0, 0.44445], + "102": [0, 0.69444, 0.21705, 0, 0.30556], + "103": [0.19444, 0.44444, 0.10836, 0, 0.5], + "104": [0, 0.69444, 0.01778, 0, 0.51667], + "105": [0, 0.67937, 0.09718, 0, 0.23889], + "106": [0.19444, 0.67937, 0.09162, 0, 0.26667], + "107": [0, 0.69444, 0.08336, 0, 0.48889], + "108": [0, 0.69444, 0.09483, 0, 0.23889], + "109": [0, 0.44444, 0.01778, 0, 0.79445], + "110": [0, 0.44444, 0.01778, 0, 0.51667], + "111": [0, 0.44444, 0.06613, 0, 0.5], + "112": [0.19444, 0.44444, 0.0389, 0, 0.51667], + "113": [0.19444, 0.44444, 0.04169, 0, 0.51667], + "114": [0, 0.44444, 0.10836, 0, 0.34167], + "115": [0, 0.44444, 0.0778, 0, 0.38333], + "116": [0, 0.57143, 0.07225, 0, 0.36111], + "117": [0, 0.44444, 0.04169, 0, 0.51667], + "118": [0, 0.44444, 0.10836, 0, 0.46111], + "119": [0, 0.44444, 0.10836, 0, 0.68334], + "120": [0, 0.44444, 0.09169, 0, 0.46111], + "121": [0.19444, 0.44444, 0.10836, 0, 0.46111], + "122": [0, 0.44444, 0.08752, 0, 0.43472], + "126": [0.35, 0.32659, 0.08826, 0, 0.5], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.67937, 0.06385, 0, 0.5], + "176": [0, 0.69444, 0, 0, 0.73752], + "184": [0.17014, 0, 0, 0, 0.44445], + "305": [0, 0.44444, 0.04169, 0, 0.23889], + "567": [0.19444, 0.44444, 0.04169, 0, 0.26667], + "710": [0, 0.69444, 0.0799, 0, 0.5], + "711": [0, 0.63194, 0.08432, 0, 0.5], + "713": [0, 0.60889, 0.08776, 0, 0.5], + "714": [0, 0.69444, 0.09205, 0, 0.5], + "715": [0, 0.69444, 0, 0, 0.5], + "728": [0, 0.69444, 0.09483, 0, 0.5], + "729": [0, 0.67937, 0.07774, 0, 0.27778], + "730": [0, 0.69444, 0, 0, 0.73752], + "732": [0, 0.67659, 0.08826, 0, 0.5], + "733": [0, 0.69444, 0.09205, 0, 0.5], + "915": [0, 0.69444, 0.13372, 0, 0.54167], + "916": [0, 0.69444, 0, 0, 0.83334], + "920": [0, 0.69444, 0.07555, 0, 0.77778], + "923": [0, 0.69444, 0, 0, 0.61111], + "926": [0, 0.69444, 0.12816, 0, 0.66667], + "928": [0, 0.69444, 0.08094, 0, 0.70834], + "931": [0, 0.69444, 0.11983, 0, 0.72222], + "933": [0, 0.69444, 0.09031, 0, 0.77778], + "934": [0, 0.69444, 0.04603, 0, 0.72222], + "936": [0, 0.69444, 0.09031, 0, 0.77778], + "937": [0, 0.69444, 0.08293, 0, 0.72222], + "8211": [0, 0.44444, 0.08616, 0, 0.5], + "8212": [0, 0.44444, 0.08616, 0, 1.0], + "8216": [0, 0.69444, 0.07816, 0, 0.27778], + "8217": [0, 0.69444, 0.07816, 0, 0.27778], + "8220": [0, 0.69444, 0.14205, 0, 0.5], + "8221": [0, 0.69444, 0.00316, 0, 0.5], + }, + "SansSerif-Regular": { + "32": [0, 0, 0, 0, 0.25], + "33": [0, 0.69444, 0, 0, 0.31945], + "34": [0, 0.69444, 0, 0, 0.5], + "35": [0.19444, 0.69444, 0, 0, 0.83334], + "36": [0.05556, 0.75, 0, 0, 0.5], + "37": [0.05556, 0.75, 0, 0, 0.83334], + "38": [0, 0.69444, 0, 0, 0.75834], + "39": [0, 0.69444, 0, 0, 0.27778], + "40": [0.25, 0.75, 0, 0, 0.38889], + "41": [0.25, 0.75, 0, 0, 0.38889], + "42": [0, 0.75, 0, 0, 0.5], + "43": [0.08333, 0.58333, 0, 0, 0.77778], + "44": [0.125, 0.08333, 0, 0, 0.27778], + "45": [0, 0.44444, 0, 0, 0.33333], + "46": [0, 0.08333, 0, 0, 0.27778], + "47": [0.25, 0.75, 0, 0, 0.5], + "48": [0, 0.65556, 0, 0, 0.5], + "49": [0, 0.65556, 0, 0, 0.5], + "50": [0, 0.65556, 0, 0, 0.5], + "51": [0, 0.65556, 0, 0, 0.5], + "52": [0, 0.65556, 0, 0, 0.5], + "53": [0, 0.65556, 0, 0, 0.5], + "54": [0, 0.65556, 0, 0, 0.5], + "55": [0, 0.65556, 0, 0, 0.5], + "56": [0, 0.65556, 0, 0, 0.5], + "57": [0, 0.65556, 0, 0, 0.5], + "58": [0, 0.44444, 0, 0, 0.27778], + "59": [0.125, 0.44444, 0, 0, 0.27778], + "61": [-0.13, 0.37, 0, 0, 0.77778], + "63": [0, 0.69444, 0, 0, 0.47222], + "64": [0, 0.69444, 0, 0, 0.66667], + "65": [0, 0.69444, 0, 0, 0.66667], + "66": [0, 0.69444, 0, 0, 0.66667], + "67": [0, 0.69444, 0, 0, 0.63889], + "68": [0, 0.69444, 0, 0, 0.72223], + "69": [0, 0.69444, 0, 0, 0.59722], + "70": [0, 0.69444, 0, 0, 0.56945], + "71": [0, 0.69444, 0, 0, 0.66667], + "72": [0, 0.69444, 0, 0, 0.70834], + "73": [0, 0.69444, 0, 0, 0.27778], + "74": [0, 0.69444, 0, 0, 0.47222], + "75": [0, 0.69444, 0, 0, 0.69445], + "76": [0, 0.69444, 0, 0, 0.54167], + "77": [0, 0.69444, 0, 0, 0.875], + "78": [0, 0.69444, 0, 0, 0.70834], + "79": [0, 0.69444, 0, 0, 0.73611], + "80": [0, 0.69444, 0, 0, 0.63889], + "81": [0.125, 0.69444, 0, 0, 0.73611], + "82": [0, 0.69444, 0, 0, 0.64584], + "83": [0, 0.69444, 0, 0, 0.55556], + "84": [0, 0.69444, 0, 0, 0.68056], + "85": [0, 0.69444, 0, 0, 0.6875], + "86": [0, 0.69444, 0.01389, 0, 0.66667], + "87": [0, 0.69444, 0.01389, 0, 0.94445], + "88": [0, 0.69444, 0, 0, 0.66667], + "89": [0, 0.69444, 0.025, 0, 0.66667], + "90": [0, 0.69444, 0, 0, 0.61111], + "91": [0.25, 0.75, 0, 0, 0.28889], + "93": [0.25, 0.75, 0, 0, 0.28889], + "94": [0, 0.69444, 0, 0, 0.5], + "95": [0.35, 0.09444, 0.02778, 0, 0.5], + "97": [0, 0.44444, 0, 0, 0.48056], + "98": [0, 0.69444, 0, 0, 0.51667], + "99": [0, 0.44444, 0, 0, 0.44445], + "100": [0, 0.69444, 0, 0, 0.51667], + "101": [0, 0.44444, 0, 0, 0.44445], + "102": [0, 0.69444, 0.06944, 0, 0.30556], + "103": [0.19444, 0.44444, 0.01389, 0, 0.5], + "104": [0, 0.69444, 0, 0, 0.51667], + "105": [0, 0.67937, 0, 0, 0.23889], + "106": [0.19444, 0.67937, 0, 0, 0.26667], + "107": [0, 0.69444, 0, 0, 0.48889], + "108": [0, 0.69444, 0, 0, 0.23889], + "109": [0, 0.44444, 0, 0, 0.79445], + "110": [0, 0.44444, 0, 0, 0.51667], + "111": [0, 0.44444, 0, 0, 0.5], + "112": [0.19444, 0.44444, 0, 0, 0.51667], + "113": [0.19444, 0.44444, 0, 0, 0.51667], + "114": [0, 0.44444, 0.01389, 0, 0.34167], + "115": [0, 0.44444, 0, 0, 0.38333], + "116": [0, 0.57143, 0, 0, 0.36111], + "117": [0, 0.44444, 0, 0, 0.51667], + "118": [0, 0.44444, 0.01389, 0, 0.46111], + "119": [0, 0.44444, 0.01389, 0, 0.68334], + "120": [0, 0.44444, 0, 0, 0.46111], + "121": [0.19444, 0.44444, 0.01389, 0, 0.46111], + "122": [0, 0.44444, 0, 0, 0.43472], + "126": [0.35, 0.32659, 0, 0, 0.5], + "160": [0, 0, 0, 0, 0.25], + "168": [0, 0.67937, 0, 0, 0.5], + "176": [0, 0.69444, 0, 0, 0.66667], + "184": [0.17014, 0, 0, 0, 0.44445], + "305": [0, 0.44444, 0, 0, 0.23889], + "567": [0.19444, 0.44444, 0, 0, 0.26667], + "710": [0, 0.69444, 0, 0, 0.5], + "711": [0, 0.63194, 0, 0, 0.5], + "713": [0, 0.60889, 0, 0, 0.5], + "714": [0, 0.69444, 0, 0, 0.5], + "715": [0, 0.69444, 0, 0, 0.5], + "728": [0, 0.69444, 0, 0, 0.5], + "729": [0, 0.67937, 0, 0, 0.27778], + "730": [0, 0.69444, 0, 0, 0.66667], + "732": [0, 0.67659, 0, 0, 0.5], + "733": [0, 0.69444, 0, 0, 0.5], + "915": [0, 0.69444, 0, 0, 0.54167], + "916": [0, 0.69444, 0, 0, 0.83334], + "920": [0, 0.69444, 0, 0, 0.77778], + "923": [0, 0.69444, 0, 0, 0.61111], + "926": [0, 0.69444, 0, 0, 0.66667], + "928": [0, 0.69444, 0, 0, 0.70834], + "931": [0, 0.69444, 0, 0, 0.72222], + "933": [0, 0.69444, 0, 0, 0.77778], + "934": [0, 0.69444, 0, 0, 0.72222], + "936": [0, 0.69444, 0, 0, 0.77778], + "937": [0, 0.69444, 0, 0, 0.72222], + "8211": [0, 0.44444, 0.02778, 0, 0.5], + "8212": [0, 0.44444, 0.02778, 0, 1.0], + "8216": [0, 0.69444, 0, 0, 0.27778], + "8217": [0, 0.69444, 0, 0, 0.27778], + "8220": [0, 0.69444, 0, 0, 0.5], + "8221": [0, 0.69444, 0, 0, 0.5], + }, + "Script-Regular": { + "32": [0, 0, 0, 0, 0.25], + "65": [0, 0.7, 0.22925, 0, 0.80253], + "66": [0, 0.7, 0.04087, 0, 0.90757], + "67": [0, 0.7, 0.1689, 0, 0.66619], + "68": [0, 0.7, 0.09371, 0, 0.77443], + "69": [0, 0.7, 0.18583, 0, 0.56162], + "70": [0, 0.7, 0.13634, 0, 0.89544], + "71": [0, 0.7, 0.17322, 0, 0.60961], + "72": [0, 0.7, 0.29694, 0, 0.96919], + "73": [0, 0.7, 0.19189, 0, 0.80907], + "74": [0.27778, 0.7, 0.19189, 0, 1.05159], + "75": [0, 0.7, 0.31259, 0, 0.91364], + "76": [0, 0.7, 0.19189, 0, 0.87373], + "77": [0, 0.7, 0.15981, 0, 1.08031], + "78": [0, 0.7, 0.3525, 0, 0.9015], + "79": [0, 0.7, 0.08078, 0, 0.73787], + "80": [0, 0.7, 0.08078, 0, 1.01262], + "81": [0, 0.7, 0.03305, 0, 0.88282], + "82": [0, 0.7, 0.06259, 0, 0.85], + "83": [0, 0.7, 0.19189, 0, 0.86767], + "84": [0, 0.7, 0.29087, 0, 0.74697], + "85": [0, 0.7, 0.25815, 0, 0.79996], + "86": [0, 0.7, 0.27523, 0, 0.62204], + "87": [0, 0.7, 0.27523, 0, 0.80532], + "88": [0, 0.7, 0.26006, 0, 0.94445], + "89": [0, 0.7, 0.2939, 0, 0.70961], + "90": [0, 0.7, 0.24037, 0, 0.8212], + "160": [0, 0, 0, 0, 0.25], + }, + "Size1-Regular": { + "32": [0, 0, 0, 0, 0.25], + "40": [0.35001, 0.85, 0, 0, 0.45834], + "41": [0.35001, 0.85, 0, 0, 0.45834], + "47": [0.35001, 0.85, 0, 0, 0.57778], + "91": [0.35001, 0.85, 0, 0, 0.41667], + "92": [0.35001, 0.85, 0, 0, 0.57778], + "93": [0.35001, 0.85, 0, 0, 0.41667], + "123": [0.35001, 0.85, 0, 0, 0.58334], + "125": [0.35001, 0.85, 0, 0, 0.58334], + "160": [0, 0, 0, 0, 0.25], + "710": [0, 0.72222, 0, 0, 0.55556], + "732": [0, 0.72222, 0, 0, 0.55556], + "770": [0, 0.72222, 0, 0, 0.55556], + "771": [0, 0.72222, 0, 0, 0.55556], + "8214": [-0.00099, 0.601, 0, 0, 0.77778], + "8593": [1e-05, 0.6, 0, 0, 0.66667], + "8595": [1e-05, 0.6, 0, 0, 0.66667], + "8657": [1e-05, 0.6, 0, 0, 0.77778], + "8659": [1e-05, 0.6, 0, 0, 0.77778], + "8719": [0.25001, 0.75, 0, 0, 0.94445], + "8720": [0.25001, 0.75, 0, 0, 0.94445], + "8721": [0.25001, 0.75, 0, 0, 1.05556], + "8730": [0.35001, 0.85, 0, 0, 1.0], + "8739": [-0.00599, 0.606, 0, 0, 0.33333], + "8741": [-0.00599, 0.606, 0, 0, 0.55556], + "8747": [0.30612, 0.805, 0.19445, 0, 0.47222], + "8748": [0.306, 0.805, 0.19445, 0, 0.47222], + "8749": [0.306, 0.805, 0.19445, 0, 0.47222], + "8750": [0.30612, 0.805, 0.19445, 0, 0.47222], + "8896": [0.25001, 0.75, 0, 0, 0.83334], + "8897": [0.25001, 0.75, 0, 0, 0.83334], + "8898": [0.25001, 0.75, 0, 0, 0.83334], + "8899": [0.25001, 0.75, 0, 0, 0.83334], + "8968": [0.35001, 0.85, 0, 0, 0.47222], + "8969": [0.35001, 0.85, 0, 0, 0.47222], + "8970": [0.35001, 0.85, 0, 0, 0.47222], + "8971": [0.35001, 0.85, 0, 0, 0.47222], + "9168": [-0.00099, 0.601, 0, 0, 0.66667], + "10216": [0.35001, 0.85, 0, 0, 0.47222], + "10217": [0.35001, 0.85, 0, 0, 0.47222], + "10752": [0.25001, 0.75, 0, 0, 1.11111], + "10753": [0.25001, 0.75, 0, 0, 1.11111], + "10754": [0.25001, 0.75, 0, 0, 1.11111], + "10756": [0.25001, 0.75, 0, 0, 0.83334], + "10758": [0.25001, 0.75, 0, 0, 0.83334], + }, + "Size2-Regular": { + "32": [0, 0, 0, 0, 0.25], + "40": [0.65002, 1.15, 0, 0, 0.59722], + "41": [0.65002, 1.15, 0, 0, 0.59722], + "47": [0.65002, 1.15, 0, 0, 0.81111], + "91": [0.65002, 1.15, 0, 0, 0.47222], + "92": [0.65002, 1.15, 0, 0, 0.81111], + "93": [0.65002, 1.15, 0, 0, 0.47222], + "123": [0.65002, 1.15, 0, 0, 0.66667], + "125": [0.65002, 1.15, 0, 0, 0.66667], + "160": [0, 0, 0, 0, 0.25], + "710": [0, 0.75, 0, 0, 1.0], + "732": [0, 0.75, 0, 0, 1.0], + "770": [0, 0.75, 0, 0, 1.0], + "771": [0, 0.75, 0, 0, 1.0], + "8719": [0.55001, 1.05, 0, 0, 1.27778], + "8720": [0.55001, 1.05, 0, 0, 1.27778], + "8721": [0.55001, 1.05, 0, 0, 1.44445], + "8730": [0.65002, 1.15, 0, 0, 1.0], + "8747": [0.86225, 1.36, 0.44445, 0, 0.55556], + "8748": [0.862, 1.36, 0.44445, 0, 0.55556], + "8749": [0.862, 1.36, 0.44445, 0, 0.55556], + "8750": [0.86225, 1.36, 0.44445, 0, 0.55556], + "8896": [0.55001, 1.05, 0, 0, 1.11111], + "8897": [0.55001, 1.05, 0, 0, 1.11111], + "8898": [0.55001, 1.05, 0, 0, 1.11111], + "8899": [0.55001, 1.05, 0, 0, 1.11111], + "8968": [0.65002, 1.15, 0, 0, 0.52778], + "8969": [0.65002, 1.15, 0, 0, 0.52778], + "8970": [0.65002, 1.15, 0, 0, 0.52778], + "8971": [0.65002, 1.15, 0, 0, 0.52778], + "10216": [0.65002, 1.15, 0, 0, 0.61111], + "10217": [0.65002, 1.15, 0, 0, 0.61111], + "10752": [0.55001, 1.05, 0, 0, 1.51112], + "10753": [0.55001, 1.05, 0, 0, 1.51112], + "10754": [0.55001, 1.05, 0, 0, 1.51112], + "10756": [0.55001, 1.05, 0, 0, 1.11111], + "10758": [0.55001, 1.05, 0, 0, 1.11111], + }, + "Size3-Regular": { + "32": [0, 0, 0, 0, 0.25], + "40": [0.95003, 1.45, 0, 0, 0.73611], + "41": [0.95003, 1.45, 0, 0, 0.73611], + "47": [0.95003, 1.45, 0, 0, 1.04445], + "91": [0.95003, 1.45, 0, 0, 0.52778], + "92": [0.95003, 1.45, 0, 0, 1.04445], + "93": [0.95003, 1.45, 0, 0, 0.52778], + "123": [0.95003, 1.45, 0, 0, 0.75], + "125": [0.95003, 1.45, 0, 0, 0.75], + "160": [0, 0, 0, 0, 0.25], + "710": [0, 0.75, 0, 0, 1.44445], + "732": [0, 0.75, 0, 0, 1.44445], + "770": [0, 0.75, 0, 0, 1.44445], + "771": [0, 0.75, 0, 0, 1.44445], + "8730": [0.95003, 1.45, 0, 0, 1.0], + "8968": [0.95003, 1.45, 0, 0, 0.58334], + "8969": [0.95003, 1.45, 0, 0, 0.58334], + "8970": [0.95003, 1.45, 0, 0, 0.58334], + "8971": [0.95003, 1.45, 0, 0, 0.58334], + "10216": [0.95003, 1.45, 0, 0, 0.75], + "10217": [0.95003, 1.45, 0, 0, 0.75], + }, + "Size4-Regular": { + "32": [0, 0, 0, 0, 0.25], + "40": [1.25003, 1.75, 0, 0, 0.79167], + "41": [1.25003, 1.75, 0, 0, 0.79167], + "47": [1.25003, 1.75, 0, 0, 1.27778], + "91": [1.25003, 1.75, 0, 0, 0.58334], + "92": [1.25003, 1.75, 0, 0, 1.27778], + "93": [1.25003, 1.75, 0, 0, 0.58334], + "123": [1.25003, 1.75, 0, 0, 0.80556], + "125": [1.25003, 1.75, 0, 0, 0.80556], + "160": [0, 0, 0, 0, 0.25], + "710": [0, 0.825, 0, 0, 1.8889], + "732": [0, 0.825, 0, 0, 1.8889], + "770": [0, 0.825, 0, 0, 1.8889], + "771": [0, 0.825, 0, 0, 1.8889], + "8730": [1.25003, 1.75, 0, 0, 1.0], + "8968": [1.25003, 1.75, 0, 0, 0.63889], + "8969": [1.25003, 1.75, 0, 0, 0.63889], + "8970": [1.25003, 1.75, 0, 0, 0.63889], + "8971": [1.25003, 1.75, 0, 0, 0.63889], + "9115": [0.64502, 1.155, 0, 0, 0.875], + "9116": [1e-05, 0.6, 0, 0, 0.875], + "9117": [0.64502, 1.155, 0, 0, 0.875], + "9118": [0.64502, 1.155, 0, 0, 0.875], + "9119": [1e-05, 0.6, 0, 0, 0.875], + "9120": [0.64502, 1.155, 0, 0, 0.875], + "9121": [0.64502, 1.155, 0, 0, 0.66667], + "9122": [-0.00099, 0.601, 0, 0, 0.66667], + "9123": [0.64502, 1.155, 0, 0, 0.66667], + "9124": [0.64502, 1.155, 0, 0, 0.66667], + "9125": [-0.00099, 0.601, 0, 0, 0.66667], + "9126": [0.64502, 1.155, 0, 0, 0.66667], + "9127": [1e-05, 0.9, 0, 0, 0.88889], + "9128": [0.65002, 1.15, 0, 0, 0.88889], + "9129": [0.90001, 0, 0, 0, 0.88889], + "9130": [0, 0.3, 0, 0, 0.88889], + "9131": [1e-05, 0.9, 0, 0, 0.88889], + "9132": [0.65002, 1.15, 0, 0, 0.88889], + "9133": [0.90001, 0, 0, 0, 0.88889], + "9143": [0.88502, 0.915, 0, 0, 1.05556], + "10216": [1.25003, 1.75, 0, 0, 0.80556], + "10217": [1.25003, 1.75, 0, 0, 0.80556], + "57344": [-0.00499, 0.605, 0, 0, 1.05556], + "57345": [-0.00499, 0.605, 0, 0, 1.05556], + "57680": [0, 0.12, 0, 0, 0.45], + "57681": [0, 0.12, 0, 0, 0.45], + "57682": [0, 0.12, 0, 0, 0.45], + "57683": [0, 0.12, 0, 0, 0.45], + }, + "Typewriter-Regular": { + "32": [0, 0, 0, 0, 0.525], + "33": [0, 0.61111, 0, 0, 0.525], + "34": [0, 0.61111, 0, 0, 0.525], + "35": [0, 0.61111, 0, 0, 0.525], + "36": [0.08333, 0.69444, 0, 0, 0.525], + "37": [0.08333, 0.69444, 0, 0, 0.525], + "38": [0, 0.61111, 0, 0, 0.525], + "39": [0, 0.61111, 0, 0, 0.525], + "40": [0.08333, 0.69444, 0, 0, 0.525], + "41": [0.08333, 0.69444, 0, 0, 0.525], + "42": [0, 0.52083, 0, 0, 0.525], + "43": [-0.08056, 0.53055, 0, 0, 0.525], + "44": [0.13889, 0.125, 0, 0, 0.525], + "45": [-0.08056, 0.53055, 0, 0, 0.525], + "46": [0, 0.125, 0, 0, 0.525], + "47": [0.08333, 0.69444, 0, 0, 0.525], + "48": [0, 0.61111, 0, 0, 0.525], + "49": [0, 0.61111, 0, 0, 0.525], + "50": [0, 0.61111, 0, 0, 0.525], + "51": [0, 0.61111, 0, 0, 0.525], + "52": [0, 0.61111, 0, 0, 0.525], + "53": [0, 0.61111, 0, 0, 0.525], + "54": [0, 0.61111, 0, 0, 0.525], + "55": [0, 0.61111, 0, 0, 0.525], + "56": [0, 0.61111, 0, 0, 0.525], + "57": [0, 0.61111, 0, 0, 0.525], + "58": [0, 0.43056, 0, 0, 0.525], + "59": [0.13889, 0.43056, 0, 0, 0.525], + "60": [-0.05556, 0.55556, 0, 0, 0.525], + "61": [-0.19549, 0.41562, 0, 0, 0.525], + "62": [-0.05556, 0.55556, 0, 0, 0.525], + "63": [0, 0.61111, 0, 0, 0.525], + "64": [0, 0.61111, 0, 0, 0.525], + "65": [0, 0.61111, 0, 0, 0.525], + "66": [0, 0.61111, 0, 0, 0.525], + "67": [0, 0.61111, 0, 0, 0.525], + "68": [0, 0.61111, 0, 0, 0.525], + "69": [0, 0.61111, 0, 0, 0.525], + "70": [0, 0.61111, 0, 0, 0.525], + "71": [0, 0.61111, 0, 0, 0.525], + "72": [0, 0.61111, 0, 0, 0.525], + "73": [0, 0.61111, 0, 0, 0.525], + "74": [0, 0.61111, 0, 0, 0.525], + "75": [0, 0.61111, 0, 0, 0.525], + "76": [0, 0.61111, 0, 0, 0.525], + "77": [0, 0.61111, 0, 0, 0.525], + "78": [0, 0.61111, 0, 0, 0.525], + "79": [0, 0.61111, 0, 0, 0.525], + "80": [0, 0.61111, 0, 0, 0.525], + "81": [0.13889, 0.61111, 0, 0, 0.525], + "82": [0, 0.61111, 0, 0, 0.525], + "83": [0, 0.61111, 0, 0, 0.525], + "84": [0, 0.61111, 0, 0, 0.525], + "85": [0, 0.61111, 0, 0, 0.525], + "86": [0, 0.61111, 0, 0, 0.525], + "87": [0, 0.61111, 0, 0, 0.525], + "88": [0, 0.61111, 0, 0, 0.525], + "89": [0, 0.61111, 0, 0, 0.525], + "90": [0, 0.61111, 0, 0, 0.525], + "91": [0.08333, 0.69444, 0, 0, 0.525], + "92": [0.08333, 0.69444, 0, 0, 0.525], + "93": [0.08333, 0.69444, 0, 0, 0.525], + "94": [0, 0.61111, 0, 0, 0.525], + "95": [0.09514, 0, 0, 0, 0.525], + "96": [0, 0.61111, 0, 0, 0.525], + "97": [0, 0.43056, 0, 0, 0.525], + "98": [0, 0.61111, 0, 0, 0.525], + "99": [0, 0.43056, 0, 0, 0.525], + "100": [0, 0.61111, 0, 0, 0.525], + "101": [0, 0.43056, 0, 0, 0.525], + "102": [0, 0.61111, 0, 0, 0.525], + "103": [0.22222, 0.43056, 0, 0, 0.525], + "104": [0, 0.61111, 0, 0, 0.525], + "105": [0, 0.61111, 0, 0, 0.525], + "106": [0.22222, 0.61111, 0, 0, 0.525], + "107": [0, 0.61111, 0, 0, 0.525], + "108": [0, 0.61111, 0, 0, 0.525], + "109": [0, 0.43056, 0, 0, 0.525], + "110": [0, 0.43056, 0, 0, 0.525], + "111": [0, 0.43056, 0, 0, 0.525], + "112": [0.22222, 0.43056, 0, 0, 0.525], + "113": [0.22222, 0.43056, 0, 0, 0.525], + "114": [0, 0.43056, 0, 0, 0.525], + "115": [0, 0.43056, 0, 0, 0.525], + "116": [0, 0.55358, 0, 0, 0.525], + "117": [0, 0.43056, 0, 0, 0.525], + "118": [0, 0.43056, 0, 0, 0.525], + "119": [0, 0.43056, 0, 0, 0.525], + "120": [0, 0.43056, 0, 0, 0.525], + "121": [0.22222, 0.43056, 0, 0, 0.525], + "122": [0, 0.43056, 0, 0, 0.525], + "123": [0.08333, 0.69444, 0, 0, 0.525], + "124": [0.08333, 0.69444, 0, 0, 0.525], + "125": [0.08333, 0.69444, 0, 0, 0.525], + "126": [0, 0.61111, 0, 0, 0.525], + "127": [0, 0.61111, 0, 0, 0.525], + "160": [0, 0, 0, 0, 0.525], + "176": [0, 0.61111, 0, 0, 0.525], + "184": [0.19445, 0, 0, 0, 0.525], + "305": [0, 0.43056, 0, 0, 0.525], + "567": [0.22222, 0.43056, 0, 0, 0.525], + "711": [0, 0.56597, 0, 0, 0.525], + "713": [0, 0.56555, 0, 0, 0.525], + "714": [0, 0.61111, 0, 0, 0.525], + "715": [0, 0.61111, 0, 0, 0.525], + "728": [0, 0.61111, 0, 0, 0.525], + "730": [0, 0.61111, 0, 0, 0.525], + "770": [0, 0.61111, 0, 0, 0.525], + "771": [0, 0.61111, 0, 0, 0.525], + "776": [0, 0.61111, 0, 0, 0.525], + "915": [0, 0.61111, 0, 0, 0.525], + "916": [0, 0.61111, 0, 0, 0.525], + "920": [0, 0.61111, 0, 0, 0.525], + "923": [0, 0.61111, 0, 0, 0.525], + "926": [0, 0.61111, 0, 0, 0.525], + "928": [0, 0.61111, 0, 0, 0.525], + "931": [0, 0.61111, 0, 0, 0.525], + "933": [0, 0.61111, 0, 0, 0.525], + "934": [0, 0.61111, 0, 0, 0.525], + "936": [0, 0.61111, 0, 0, 0.525], + "937": [0, 0.61111, 0, 0, 0.525], + "8216": [0, 0.61111, 0, 0, 0.525], + "8217": [0, 0.61111, 0, 0, 0.525], + "8242": [0, 0.61111, 0, 0, 0.525], + "9251": [0.11111, 0.21944, 0, 0, 0.525], + }, +}; diff --git a/frontend/node_modules/katex/src/fonts/Makefile b/frontend/node_modules/katex/src/fonts/Makefile new file mode 100644 index 0000000..83c22db --- /dev/null +++ b/frontend/node_modules/katex/src/fonts/Makefile @@ -0,0 +1,139 @@ +#!gmake +# +# Version: Apache License 2.0 +# +# Copyright (c) 2013 MathJax Project +# Copyright (c) 2013 The MathJax Consortium +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +CUSTOM=custom.cfg + +-include $(CUSTOM) + +MFTRACE_MODIFIED=lib/mftrace-modified + +all: config fonts + +$(CUSTOM): + @cp default.cfg $(CUSTOM); + +$(CUSTOM).pl: $(CUSTOM) + @echo "Creating Perl config file..." + @cp $(CUSTOM) $(CUSTOM).pl + @echo >> $(CUSTOM).pl # ensure that the config file ends by a new line + @echo "MFTRACE_PATH=`$(WHICH) $(MFTRACE)`" >> $(CUSTOM).pl + @$(SED) -i "s|^\([A-Z_0-9]*\)=\(.*\)|$$\1='\2';|" $(CUSTOM).pl + @echo "1;" >> $(CUSTOM).pl + +.PHONY: config +config: $(CUSTOM).pl + +blacker: $(MFTRACE_MODIFIED) +$(MFTRACE_MODIFIED): + $(PERL) -I. makeBlacker 15 # values between 10 and 30 seem best + +pfa: $(MFTRACE_MODIFIED) + @echo "cmr10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify cmr10 + + @echo "cmmi10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --encoding $(TETEXENCODING)/aae443f0.enc --simplify cmmi10 + + @echo "cmsy10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --encoding $(TETEXENCODING)/10037936.enc --simplify cmsy10 + + @echo "cmex10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify cmex10 + + @echo "cmbx10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify cmbx10 + + @echo "cmbxti10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify cmbxti10 + + @echo "cmti10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify cmti10 + + @echo "msam10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify --encoding $(TETEXENCODING)/10037936.enc msam10 + + @echo "msbm10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify --encoding $(TETEXENCODING)/10037936.enc msbm10 + + @echo "cmmib10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --encoding $(TETEXENCODING)/aae443f0.enc --simplify cmmib10 + + @echo "cmbsy10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --encoding $(TETEXENCODING)/10037936.enc --simplify cmbsy10 + + @echo "cmtt10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify cmtt10 + + @echo "cmss10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify cmss10 + @echo "cmssi10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify cmssi10 + @echo "cmssbx10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify cmssbx10 + + @echo "eufm10" + cp "`$(KPSEWHICH) eufm10.pfb`" eufm10.pfb + @echo "eufb10" + cp "`$(KPSEWHICH) eufb10.pfb`" eufb10.pfb + + # echo "eusm10" + # $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify eusm10 + # echo "eusb10" + # $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify eusb10 + + @echo "rsfs10" + $(PYTHON) $(MFTRACE_MODIFIED) --magnification 1000 --simplify --encoding $(BASEENCODING)/tex256.enc rsfs10 + + mkdir -p pfa + rm -f pfa/* + mv *.pfa pfa + mv *.pfb pfa + +ff: pfa + mkdir -p ff otf + rm -f ff/* otf/* + $(PERL) -I. makeFF + +.PHONY: fonts +fonts: ff + mkdir -p ttf woff woff2 + rm -f ttf/* woff/* woff2/* + + @for file in `ls ff/*.ff | $(SED) 's|ff/\(.*\)\.ff|\1|'`; do \ + echo ""; \ + echo $$file; \ + $(FONTFORGE) -lang=ff -script ff/$$file.ff; \ + \ + echo "Hinting $$file"; \ + if echo "$$file" | $(GREP) -q -e "Size[1-4]" -e "Typewriter"; then \ + $(TTFAUTOHINT) -f none -S --windows-compatibility --symbol ttf/$$file.ttf ttf/$$file.ttf.hinted; \ + else \ + $(TTFAUTOHINT) -f none -S --windows-compatibility ttf/$$file.ttf ttf/$$file.ttf.hinted; \ + fi; \ + mv ttf/$$file.ttf.hinted ttf/$$file.ttf; \ + \ + echo "Generating $$file..."; \ + $(PYTHON) generate_fonts.py ttf/$$file.ttf; \ + done + +clean: + rm -f $(CUSTOM).pl + rm -f $(MFTRACE_MODIFIED) lib/blacker.mf + rm -rf pfa ff otf ttf woff woff2 diff --git a/frontend/node_modules/katex/src/fonts/default.cfg b/frontend/node_modules/katex/src/fonts/default.cfg new file mode 100644 index 0000000..2c39c31 --- /dev/null +++ b/frontend/node_modules/katex/src/fonts/default.cfg @@ -0,0 +1,20 @@ +# Note: paths should be absolute, unless they point to programs in your $PATH. + +##### Standard programs ##### +GREP=grep +PERL=perl +PYTHON=python3 +SED=sed +WHICH=which +KPSEWHICH=kpsewhich + +##### Font tools ##### +# Most of the tools below are standard and should be available from your package manager. +FONTFORGE=fontforge +MFTRACE=mftrace +TTX=ttx +TTFAUTOHINT=ttfautohint + +##### TeXLive Encoding +TETEXENCODING=/usr/share/texlive/texmf-texlive/fonts/enc/dvips/tetex/ +BASEENCODING=/usr/share/texlive/texmf-texlive/fonts/enc/dvips/base/ diff --git a/frontend/node_modules/katex/src/fonts/generate_fonts.py b/frontend/node_modules/katex/src/fonts/generate_fonts.py new file mode 100755 index 0000000..d606b82 --- /dev/null +++ b/frontend/node_modules/katex/src/fonts/generate_fonts.py @@ -0,0 +1,58 @@ +#!/usr/bin/env python3 + +import sys +import os +import json + +from fontTools.ttLib import TTFont, sfnt +from fontTools.misc.timeTools import timestampNow +sfnt.USE_ZOPFLI = True + +if len(sys.argv) < 2: + print("Usage: %s " % sys.argv[0]) + sys.exit(1) + +font_file = sys.argv[1] +font_name = os.path.splitext(os.path.basename(font_file))[0] + + +font = TTFont(font_file, recalcBBoxes=False, recalcTimestamp=False) + +# fix timestamp to the epoch +font['head'].created = 0 +font['head'].modified = 0 + +# remove fontforge timestamps +if 'FFTM' in font: + del font['FFTM'] + +# remove redundant GDEF table +if 'GDEF' in font: + del font['GDEF'] + +# remove Macintosh table +# https://developer.apple.com/fonts/TrueType-Reference-Manual/RM06/Chap6cmap.html +font['name'].names = [record for record in font['name'].names if record.platformID != 1] +font['cmap'].tables = [table for table in font['cmap'].tables if table.platformID != 1] + +# fix OS/2 and hhea metrics +glyf = font['glyf'] +ascent = int(max(glyf[c].yMax for c in font.getGlyphOrder() if hasattr(glyf[c], "yMax"))) +descent = -int(min(glyf[c].yMin for c in font.getGlyphOrder() if hasattr(glyf[c], "yMin"))) + +font['OS/2'].usWinAscent = ascent +font['OS/2'].usWinDescent = descent + +font['hhea'].ascent = ascent +font['hhea'].descent = -descent + +# save TTF +font.save(font_file, reorderTables=None) + +# save WOFF +font.flavor = 'woff' +font.save(os.path.join('woff', font_name + '.woff'), reorderTables=None) + +# save WOFF2 +font.flavor = 'woff2' +font.save(os.path.join('woff2', font_name + '.woff2'), reorderTables=None) diff --git a/frontend/node_modules/katex/src/fonts/lib/Extra.otf b/frontend/node_modules/katex/src/fonts/lib/Extra.otf new file mode 100644 index 0000000000000000000000000000000000000000..e1c84f8dca8dcc6ddb92479fd1eed3ce215cb1aa GIT binary patch literal 1332 zcmd5+O=uHA6#iy+v#o7Ns;b@`|Yt6r|%i(i3J*zS#g{A6X(!EzFbvJzd=5^zcZh!mY_@!icT(iA(wYvKAd|` zo%zN6QgONL-@V1-y?%-s-2SmBcp>$Jact7VtsJRHoUf+gBqs?L06DMye& z5e3Fd=`zA0T?z@0Ns<%`w zlPp}dK%bF)23Nn`4+wp4v+4c!Lss&?4|#(e{!O;@FBc-9@dky^Th9_-DFMri!#gBA zL-7u)-hj3e6*p>Lq8W`Cn2Z}hkAX}34G^v#fGW2L=;#h8!eE`rKx+7L=lD^*?Zbo;8^_Vx*TkESuyPEPJje>7Kr~HZp Uea43KYEzzPW4rvZB`aG$0W}=GJpcdz literal 0 HcmV?d00001 diff --git a/frontend/node_modules/katex/src/fonts/lib/Space.ttx b/frontend/node_modules/katex/src/fonts/lib/Space.ttx new file mode 100644 index 0000000..cfed4af --- /dev/null +++ b/frontend/node_modules/katex/src/fonts/lib/Space.ttx @@ -0,0 +1,234 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + Copyright (c) 2009-2010 Design Science, Inc. +Copyright (c) 2014-2018 Khan Academy + + + *NAME* + + + *WEIGHT_S* + + + FontForge 2.0 : *NAME*-*WEIGHT* + + + *NAME*-*WEIGHT* + + + Version 1.1 + + + *NAME*-*WEIGHT* + + + Copyright (c) 2009-2010, Design Science, Inc. (<www.mathjax.org>) +Copyright (c) 2014-2018 Khan Academy (<www.khanacademy.org>), +with Reserved Font Name *NAME*. + +This Font Software is licensed under the SIL Open Font License, Version 1.1. +This license available with a FAQ at: +http://scripts.sil.org/OFL + + + http://scripts.sil.org/OFL + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + 0 50 433 50 hstem + 50 50 50 50 vstem + 50 hmoveto + 150 533 -150 hlineto + 50 -483 rmoveto + 433 50 -433 vlineto + endchar + + + endchar + + + endchar + + + + + + + + + + + + + + + + diff --git a/frontend/node_modules/katex/src/fonts/makeBlacker b/frontend/node_modules/katex/src/fonts/makeBlacker new file mode 100755 index 0000000..69b0737 --- /dev/null +++ b/frontend/node_modules/katex/src/fonts/makeBlacker @@ -0,0 +1,49 @@ +#! /usr/bin/perl + +# Creates the metafont file needed for darker copies of the TeX fonts, +# and modifies mftrace to use it. +# +# Usage: ./makeBlacker blackness + +require "custom.cfg.pl"; + +$blacker = shift; +unless ($blacker) { + print stderr "Usage: ./makeBlacker blackness\n"; + exit; +} + +sub editMftrace { + my $oldMFTRACE = $MFTRACE_PATH; + $MFTRACE = "./lib/mftrace-modified"; + print "Editing mftrace\n"; + open(MFT,$oldMFTRACE) || die "Can't read '$oldMFTRACE': $!\n"; + my $MFT = join("",); + close(MFT); + $MFT =~ s!r"mf '\\mode:=(?:[^;]*)(; [^"]*)"!r"""mf '\\smode:="lib/blacker.mf"$1"""!; + open(MFT,">$MFTRACE") || die "Can't write '$MFTRACE': $!\n"; + print MFT $MFT; + close(MFT); + chmod 0755, $MFTRACE; +} + +sub makeBlackerMF { + my $blacker = shift; + print "Using blacker = $blacker\n"; + open(BLACKER,">lib/blacker.mf") || die "Can't write 'lib/blacker.mf': $!\n"; + print BLACKER << " END"; + proofing:=0; + fontmaking:=1; + tracingtitles:=0; + pixels_per_inch:=1200; + blacker:=$blacker; + fillin:=0; + o_correction:=1; + END + close(BLACKER); +} + +editMftrace(); +makeBlackerMF($blacker); + +1; diff --git a/frontend/node_modules/katex/src/fonts/makeFF b/frontend/node_modules/katex/src/fonts/makeFF new file mode 100755 index 0000000..606d5fd --- /dev/null +++ b/frontend/node_modules/katex/src/fonts/makeFF @@ -0,0 +1,2005 @@ +#! /usr/bin/perl + +# Creates the FontForge files needed to create the +# KaTeX fonts from the TeX source files, constructing some +# glyphs from two or more parts, when needed. +# +# Usage: ./makeFF + +require "custom.cfg.pl"; + +######################################################################### + +$map{cmr10} = { + "Main-Regular" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-125,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x2F] => 0x21, # !, ", #, $, %, &, ', (, ), *, +, comma, -, ., / + 0x22 => 0x201D, # " + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-310], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + 0x19 => 0xDF, # sharp S + 0x1A => 0xE6, # ae ligature + 0x1B => 0x153, # oe ligature + 0x1C => 0xF8, # o with slash + 0x1D => 0xC6, # AE ligature + 0x1E => 0x152, # OE ligature + 0x1F => 0xD8, # O with slash + ], +}; + +$map{cmmi10} = { + "Math-Italic" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + [0xB,0xE] => 0x3B1, # \alpha, \beta, \gamma, \delta + 0xF => 0x3F5, # \elpsilon + [0x10,0x18] => 0x3B6, # \zeta, \eta, \theta, \iota, \kappa, \lambda, \mu, \nu, \xi + [0x19,0x1A] => 0x3C0, # \pi, \rho + [0x1B,0x1D] => 0x3C3, # \sigma, \tau, \upsilon + 0x1E => 0x3D5, # \phi + [0x1F,0x21] => 0x3C7, # \chi, \psi, \omega + 0x22 => 0x3B5, # \varepsilon + 0x23 => 0x3D1, # \vartheta + 0x24 => 0x3D6, # \varpi + 0x25 => 0x3F1, # \varrho + 0x26 => 0x3C2, # \varsigma + 0x27 => 0x3C6, # \varphi + + [0x41,0x5A] => 0x41, # A-Z + [0x61,0x7A] => 0x61, # a - z + [0x30,0x39] => 0x30, # Oldstyle 0-9 + + 0x6F => 0x3BF, # omicron + 0x7B => 0xE131, # \imath (These differ from \i and \j, so use PUA character) + 0x7C => 0xE237, # \jmath + ], + + "Main-Regular" => [ + 0x28 => 0x21BC, # \leftharpoonup + 0x29 => 0x21BD, # \leftharpoondown + 0x2A => 0x21C0, # \rightharpoonup + 0x2B => 0x21C1, # \rightharpoondown + + 0x2E => 0x25B9, # \triangleright + 0x2F => 0x25C3, # \triangleleft + + 0x3A => 0x2E, # . + 0x3B => 0x2C, # , + 0x3C => 0x3C, # < + 0x3D => 0x2215, # / + 0x3E => 0x3E, # > + 0x3F => 0x22C6, # \star + 0x40 => 0x2202, # \partial + + [0x5B,0x5D] => 0x266D, # \flat, \natural, \sharp + 0x5E => 0x2323, # \smile + 0x5F => 0x2322, # \frown + 0x60 => 0x2113, # \ell + + 0x7D => 0x2118, # \wp + 0x7E => [0x20D7,-653,0],# \vec + ], +}; + +$map{cmsy10} = { + "Main-Regular" => [ + [0,1] => 0x2212, # - + 1 => 0x22C5, # \cdot + 2 => 0xD7, # \times + 3 => 0x2217, # \ast + 4 => 0xF7, # \div + 5 => 0x22C4, # \diamond + 6 => 0xB1, # \pm + 7 => 0x2213, # \mp + [8,0xC] => 0x2295, # \oplus, \ominus, \otimes, \oslash, \odot + 0xD => 0x25EF, # \bigcirc + [0xE,0xF] => 0x2218, # \circ, \bullet + + 0x10 => 0x224D, # \asymp + 0x11 => 0x2261, # \equiv + [0x12,0x13] => 0x2286, # \subseteq, \supseteq + [0x14,0x15] => 0x2264, # \leq, \geq + [0x16,0x17] => 0x2AAF, # \preceq, \succeq + 0x18 => 0x223C, # \sim + 0x19 => 0x2248, # \approx + [0x1A,0x1B] => 0x2282, # \subset, \supset + [0x1C,0x1D] => 0x226A, # \ll, \gg + [0x1E,0x1F] => 0x227A, # \prec, \succ + + 0x20 => 0x2190, # \leftarrow + 0x21 => 0x2192, # \rightarrow + 0x22 => 0x2191, # \uparrow + 0x23 => 0x2193, # \downarrow + 0x24 => 0x2194, # \leftrightarrow + 0x25 => 0x2197, # \nearrow + 0x26 => 0x2198, # \searrow + 0x27 => 0x2243, # \simeq + + 0x28 => 0x21D0, # \Leftarrow + 0x29 => 0x21D2, # \Rightarrow + 0x2A => 0x21D1, # \Uparrow + 0x2B => 0x21D3, # \Downarrow + 0x2C => 0x21D4, # \Leftrightarrow + 0x2D => 0x2196, # \nwarrow + 0x2E => 0x2199, # \swarrow + 0x2F => 0x221D, # \propto + + 0x30 => 0x2032, # \prime + 0x31 => 0x221E, # \infty + 0x32 => 0x2208, # \in + 0x33 => 0x220B, # \ni + 0x34 => 0x25B3, # \bigtriangleup and \triangle + 0x35 => 0x25BD, # \bigtriangledown + 0x36 => 0xE020, # \not (U+0338 COMBINING LONG SOLIDUS OVERLAY would + # be most natural, but we don't use a negative + # leading space, so use PUA character) + + 0x38 => 0x2200, # \forall + 0x39 => 0x2203, # \exists + 0x3A => 0xAC, # \neg + 0x3B => 0x2205, # \emptyset + 0x3C => 0x211C, # \Re + 0x3D => 0x2111, # \Im + 0x3E => 0x22A4, # \top + 0x3F => 0x22A5, # \bot + + 0x40 => 0x2135, # \aleph + + 0x5B => 0x222A, # \cup + 0x5C => 0x2229, # \cap + 0x5D => 0x228E, # \uplus + [0x5E,0x5F] => 0x2227, # \wedge, \vee + + [0x60,0x61] => 0x22A2, # \vdash, \dashv + [0x62,0x63] => 0x230A, # \lfloor, \rfloor + [0x64,0x65] => 0x2308, # \lceil, \rceil + 0x66 => 0x7B, # { + 0x67 => 0x7D, # } + [0x68,0x69] => 0x27E8, # \langle, \rangle + 0x6A => 0x7C, # | + 0x6A => 0x2223, # \vert + 0x6B => 0x2225, # \Vert + 0x6C => 0x2195, # \updownarrow + 0x6D => 0x21D5, # \Updownarrow + 0x6E => 0x5C, # \backslash + 0x6E => 0x2216, # \setminus + 0x6F => 0x2240, # \wr + + 0x70 => [0x221A,0,760], # \surd ### adjust position so font doesn't have a large depth + 0x71 => 0x2A3F, # \amalg + 0x72 => 0x2207, # \nabla + 0x73 => 0x222B, # \int + 0x74 => 0x2294, # \sqcup + 0x75 => 0x2293, # \sqcap + [0x76,0x77] => 0x2291, # \sqsubseteq, \sqsupseteq + 0x78 => 0xA7, # \S + [0x79,0x7A] => 0x2020, # \dagger, \ddagger + 0x7B => 0xB6, # \P + 0x7C => 0x2663, # \clubsuit + 0x7D => 0x2662, # \diamondsuit + 0x7E => 0x2661, # \heartsuit + 0x7F => 0x2660, # \spadesuit + ], + + "Caligraphic" => [ + [0x41,0x5A] => 0x41, # A-Z + ], +}; + +$map{cmex10} = { + "Size1" => [ + 0 => [0x28,0,810], # ( + 1 => [0x29,0,810], # ) + 2 => [0x5B,0,810], # [ + 3 => [0x5D,0,810], # ] + 4 => [0x230A,0,810], # \lfloor + 5 => [0x230B,0,810], # \rfloor + 6 => [0x2308,0,810], # \lceil + 7 => [0x2309,0,810], # \rceil + 8 => [0x7B,0,810], # { + 9 => [0x7D,0,810], # } + 0xA => [0x27E8,0,810], # \langle + 0xB => [0x27E9,0,810], # \rangle + 0xC => [0x2223,0,606], # \vert + 0xD => [0x2225,0,606], # \Vert + 0xE => [0x2F,0,810], # / + 0xF => [0x5C,0,810], # \ + + 0x46 => [0x2A06,0,750], # \bigsqcup + 0x48 => [0x222E,0,805], # \oint + 0x4A => [0x2A00,0,750], # \bigodot + 0x4C => [0x2A01,0,750], # \bigoplus + 0x4E => [0x2A02,0,750], # \bigotimes + + 0x50 => [0x2211,0,750], # \sum + 0x51 => [0x220F,0,750], # \prod + 0x52 => [0x222B,0,805], # \int + 0x53 => [0x22C3,0,750], # \bigcup + 0x54 => [0x22C2,0,750], # \bigcap + 0x55 => [0x2A04,0,750], # \biguplus + 0x56 => [0x22C0,0,750], # \bigwedge + 0x57 => [0x22C1,0,750], # \bigvee + + 0x60 => [0x2210,0,750], # \coprod + 0x62 => 0x2C6, # \widehat + 0x62 => [0x302,-556,0], # \widehat (combining) + 0x65 => 0x2DC, # \widetilde + 0x65 => [0x303,-556,0], # \widetilde (combining) + + 0x70 => [0x221A,0,810], # surd + 0x3F => [0x23D0,0,601], # arrow extension + 0x77 => [0x2016,0,601], # Arrow extension (non-standard) + 0x78 => [0x2191,0,600], # uparrow top + 0x79 => [0x2193,0,600], # downarrow bottom + 0x7E => [0x21D1,0,600], # Uparrow top + 0x7F => [0x21D3,0,600], # Downarrow bottom + ], + + "Size2" => [ + 0x10 => [0x28,0,1110], # ( + 0x11 => [0x29,0,1110], # ) + 0x2E => [0x2F,0,1110], # / + 0x2F => [0x5C,0,1110], # \ + 0x44 => [0x27E8,0,1110],# \langle + 0x45 => [0x27E9,0,1110],# \rangle + + 0x47 => [0x2A06,0,950], # \bigsqcup + 0x49 => [0x222E,0,1360],# \oint + 0x4B => [0x2A00,0,950], # \bigodot + 0x4D => [0x2A01,0,950], # \bigoplus + 0x4F => [0x2A02,0,950], # \bigotimes + + 0x58 => [0x2211,0,950], # \sum + 0x59 => [0x220F,0,950], # \prod + 0x5A => [0x222B,0,1360],# \int + 0x5B => [0x22C3,0,950], # \bigcup + 0x5C => [0x22C2,0,950], # \bigcap + 0x5D => [0x2A04,0,950], # \biguplus + 0x5E => [0x22C0,0,950], # \bigwedge + 0x5F => [0x22C1,0,950], # \bigvee + 0x61 => [0x2210,0,950], # \coprod + + 0x63 => 0x2C6, # \widehat + 0x63 => [0x302,-1000,0],# \widehat (combining) + 0x66 => 0x2DC, # \widetilde + 0x66 => [0x303,-1000,0],# \widetilde (combining) + + 0x68 => [0x5B,0,1110], # [ + 0x69 => [0x5D,0,1110], # ] + 0x6A => [0x230A,0,1110],# \lfloor + 0x6B => [0x230B,0,1110],# \rfloor + 0x6C => [0x2308,0,1110],# \lceil + 0x6D => [0x2309,0,1110],# \rceil + 0x6E => [0x7B,0,1110], # { + 0x6F => [0x7D,0,1110], # } + 0x71 => [0x221A,0,1110],# surd + ], + + "Size3" => [ + 0x12 => [0x28,0,1410], # ( + 0x13 => [0x29,0,1410], # ) + 0x14 => [0x5B,0,1410], # [ + 0x15 => [0x5D,0,1410], # ] + 0x16 => [0x230A,0,1410],# \lfloor + 0x17 => [0x230B,0,1410],# \rfloor + 0x18 => [0x2308,0,1410],# \lceil + 0x19 => [0x2309,0,1410],# \rceil + 0x1A => [0x7B,0,1410], # { + 0x1B => [0x7D,0,1410], # } + 0x1C => [0x27E8,0,1410],# \langle + 0x1D => [0x27E9,0,1410],# \rangle + 0x1E => [0x2F,0,1410], # / + 0x1F => [0x5C,0,1410], # \ + 0x64 => 0x2C6, # \widehat + 0x64 => [0x302,-1444,0],# \widehat (combining) + 0x67 => 0x2DC, # \widetilde + 0x67 => [0x303,-1444,0],# \widetilde (combining) + 0x72 => [0x221A,0,1410],# surd + ], + + "Size4" => [ + 0x20 => [0x28,0,1710], # ( + 0x21 => [0x29,0,1710], # ) + 0x22 => [0x5B,0,1710], # [ + 0x23 => [0x5D,0,1710], # ] + 0x24 => [0x230A,0,1710],# \lfloor + 0x25 => [0x230B,0,1710],# \rfloor + 0x26 => [0x2308,0,1710],# \lceil + 0x27 => [0x2309,0,1710],# \rceil + 0x28 => [0x7B,0,1710], # { + 0x29 => [0x7D,0,1710], # } + 0x2A => [0x27E8,0,1710],# \langle + 0x2B => [0x27E9,0,1710],# \rangle + 0x2C => [0x2F,0,1710], # / + 0x2D => [0x5C,0,1710], # \ + 0x73 => [0x221A,0,1710],# surd + + 0x30 => [0x239B,0,1115],# left paren upper hook + 0x31 => [0x239E,0,1115],# right paren upper hook + 0x32 => [0x23A1,0,1115],# left square bracket upper corner + 0x33 => [0x23A4,0,1115],# right square bracket upper corner + 0x34 => [0x23A3,0,1115],# left square bracket lower corner + 0x35 => [0x23A6,0,1115],# right square bracket lower hook + 0x36 => [0x23A2,0,601], # left square bracket extension + 0x37 => [0x23A5,0,601], # right square bracket extension + 0x38 => [0x23A7,0,900], # left curly brace upper hook + 0x39 => [0x23AB,0,900], # right curly brace upper hook + 0x3A => 0x23A9, # left curly brace lower hook + 0x3B => 0x23AD, # right curly brace lower hook + 0x3C => [0x23A8,0,1150],# left curly brace middle + 0x3D => [0x23AC,0,1150],# right curly brace middle + 0x3E => [0x23AA,0,300], # curly brace extension + + 0x40 => [0x239D,0,1115],# left paren lower hook + 0x41 => [0x23A0,0,1115],# right paren lower hook + 0x42 => [0x239C,0,600], # left paren extension + 0x43 => [0x239F,0,600], # right paren extension + + 0x74 => [0x23B7,0,915], # radical bottom + 0x75 => [0xE000,0,605], # radical extension (PUA) + 0x76 => [0xE001,0,565], # radical top (PUA) + [0x7A,0x7D] => 0xE150, # \braceld, \bracerd, \bracelu, \braceru (PUA) + ], + + "Main-Regular" => [ + 0x38 => [0x23B0,0,900], # left curly brace upper hook, for lgroup, lmoustache + 0x39 => [0x23B1,0,900], # right curly brace upper hook, for rgroup, rmoustache + 0x3A => 0x23A9, # left curly brace lower hook, for lgroup, rmoustache + 0x3B => 0x23AD, # right curly brace lower hook, for rgroup, lmoustache + ], +}; + +$map{cmti10} = { + "Main-Italic" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-160,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x23] => 0x21, # !, ", #, + 0x22 => 0x201D, # " + [0x25,0x2F] => 0x25, # %, &, ', (, ), *, +, comma, -, ., / + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-310], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + 0x19 => 0xDF, # sharp S + 0x1A => 0xE6, # ae ligature + 0x1B => 0x153, # oe ligature + 0x1C => 0xF8, # o with slash + 0x1D => 0xC6, # AE ligature + 0x1E => 0x152, # OE ligature + 0x1F => 0xD8, # O with slash + ], + + "Main-Regular" => [ + 0x24 => 0xA3, # pound sign + ], +}; + +$map{cmbx10} = { + "Main-Bold" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-147,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x2F] => 0x21, # !, ", #, $, %, &, ', (, ), *, +, comma, -, ., / + 0x22 => 0x201D, # " + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-310], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + 0x19 => 0xDF, # sharp S + 0x1A => 0xE6, # ae ligature + 0x1B => 0x153, # oe ligature + 0x1C => 0xF8, # o with slash + 0x1D => 0xC6, # AE ligature + 0x1E => 0x152, # OE ligature + 0x1F => 0xD8, # O with slash + ], +}; + +$map{cmbxti10} = { + "Main-BoldItalic" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-160,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x23] => 0x21, # !, ", #, + 0x22 => 0x201D, # " + [0x25,0x2F] => 0x25, # %, &, ', (, ), *, +, comma, -, ., / + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-310], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + 0x19 => 0xDF, # sharp S + 0x1A => 0xE6, # ae ligature + 0x1B => 0x153, # oe ligature + 0x1C => 0xF8, # o with slash + 0x1D => 0xC6, # AE ligature + 0x1E => 0x152, # OE ligature + 0x1F => 0xD8, # O with slash + ], + + "Main-Bold" => [ + 0x24 => 0xA3, # pound sign + ], +}; + +$map{cmmib10} = { + "Math-BoldItalic" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + [0xB,0xE] => 0x3B1, # \alpha, \beta, \gamma, \delta + 0xF => 0x3F5, # \elpsilon + [0x10,0x18] => 0x3B6, # \zeta, \eta, \theta, \iota, \kappa, \lambda, \mu, \nu, \xi + [0x19,0x1A] => 0x3C0, # \pi, \rho + [0x1B,0x1D] => 0x3C3, # \sigma, \tau, \upsilon + 0x1E => 0x3D5, # \phi + [0x1F,0x21] => 0x3C7, # \chi, \psi, \omega + 0x22 => 0x3B5, # \varepsilon + 0x23 => 0x3D1, # \vartheta + 0x24 => 0x3D6, # \varpi + 0x25 => 0x3F1, # \varrho + 0x26 => 0x3C2, # \varsigma + 0x27 => 0x3C6, # \varphi + + [0x30,0x39] => 0x30, # Oldstyle 0-9 + [0x41,0x5A] => 0x41, # A-Z + [0x61,0x7A] => 0x61, # a - z + + 0x6F => 0x3BF, # omicron + 0x7B => 0xE131, # \imath (PUA) + 0x7C => 0xE237, # \jmath (PUA) + ], + + "Main-Bold" => [ + 0x28 => 0x21BC, # \leftharpoonup + 0x29 => 0x21BD, # \leftharpoondown + 0x2A => 0x21C0, # \rightharpoonup + 0x2B => 0x21C1, # \rightharpoondown + + 0x2E => 0x25B9, # \triangleright + 0x2F => 0x25C3, # \triangleleft + + 0x3A => 0x2E, # . + 0x3B => 0x2C, # , + 0x3C => 0x3C, # < + 0x3D => 0x2215, # / + 0x3E => 0x3E, # > + 0x3F => 0x22C6, # \star + 0x40 => 0x2202, # \partial + + [0x5B,0x5D] => 0x266D, # \flat, \natural, \sharp + 0x5E => 0x2323, # \smile + 0x5F => 0x2322, # \frown + 0x60 => 0x2113, # \ell + 0x68 => 0x210F, # \hbar (bar added below) + + 0x7D => 0x2118, # \wp + 0x7E => [0x20D7,-729,0],# \vec + ], +}; + +$map{cmbsy10} = { + "Main-Bold" => [ + [0,1] => 0x2212, # - + 1 => 0x22C5, # \cdot + 2 => 0xD7, # \times + 3 => 0x2217, # \ast + 4 => 0xF7, # \div + 5 => 0x22C4, # \diamond + 6 => 0xB1, # \pm + 7 => 0x2213, # \mp + [8,0xC] => 0x2295, # \oplus, \ominus, \otimes, \oslash, \odot + 0xD => 0x25EF, # \bigcirc + [0xE,0xF] => 0x2218, # \circ, \bullet + + 0x10 => 0x224D, # \asymp + 0x11 => 0x2261, # \equiv + [0x12,0x13] => 0x2286, # \subseteq, \supseteq + [0x14,0x15] => 0x2264, # \leq, \geq + [0x16,0x17] => 0x2AAF, # \preceq, \succeq + 0x18 => 0x223C, # \sim + 0x19 => 0x2248, # \approx + [0x1A,0x1B] => 0x2282, # \subset, \supset + [0x1C,0x1D] => 0x226A, # \ll, \gg + [0x1E,0x1F] => 0x227A, # \prec, \succ + + 0x20 => 0x2190, # \leftarrow + 0x21 => 0x2192, # \rightarrow + 0x22 => 0x2191, # \uparrow + 0x23 => 0x2193, # \downarrow + 0x24 => 0x2194, # \leftrightarrow + 0x25 => 0x2197, # \nearrow + 0x26 => 0x2198, # \searrow + 0x27 => 0x2243, # \simeq + + 0x28 => 0x21D0, # \Leftarrow + 0x29 => 0x21D2, # \Rightarrow + 0x2A => 0x21D1, # \Uparrow + 0x2B => 0x21D3, # \Downarrow + 0x2C => 0x21D4, # \Leftrightarrow + 0x2D => 0x2196, # \nwarrow + 0x2E => 0x2199, # \swarrow + 0x2F => 0x221D, # \propto + + 0x30 => 0x2032, # \prime + 0x31 => 0x221E, # \infty + 0x32 => 0x2208, # \in + 0x33 => 0x220B, # \ni + 0x34 => 0x25B3, # \bigtriangleup and \triangle + 0x35 => 0x25BD, # \bigtriangledown + 0x36 => 0xE020, # \not + + 0x38 => 0x2200, # \forall + 0x39 => 0x2203, # \exists + 0x3A => 0xAC, # \neg + 0x3B => 0x2205, # \emptyset + 0x3C => 0x211C, # \Re + 0x3D => 0x2111, # \Im + 0x3E => 0x22A4, # \top + 0x3F => 0x22A5, # \bot + + 0x40 => 0x2135, # \aleph + + 0x5B => 0x222A, # \cup + 0x5C => 0x2229, # \cap + 0x5D => 0x228E, # \uplus + [0x5E,0x5F] => 0x2227, # \wedge, \vee + + [0x60,0x61] => 0x22A2, # \vdash, \dashv + [0x62,0x63] => 0x230A, # \lfloor, \rfloor + [0x64,0x65] => 0x2308, # \lceil, \rceil + 0x66 => 0x7B, # { + 0x67 => 0x7D, # } + [0x68,0x69] => 0x27E8, # \langle, \rangle + 0x6A => 0x7C, # | + 0x6A => 0x2223, # \vert + 0x6B => 0x2225, # \Vert + 0x6C => 0x2195, # \updownarrow + 0x6D => 0x21D5, # \Updownarrow + 0x6E => 0x5C, # \backslash + 0x6E => 0x2216, # \setminus + 0x6F => 0x2240, # \wr + + 0x70 => [0x221A,0,760], # \surd ### adjust position so font doesn't have a large depth + 0x71 => 0x2A3F, # \amalg + 0x72 => 0x2207, # \nabla + 0x73 => 0x222B, # \int + 0x74 => 0x2294, # \sqcup + 0x75 => 0x2293, # \sqcap + [0x76,0x77] => 0x2291, # \sqsubseteq, \sqsupseteq + + [0x79,0x7A] => 0x2020, # \dagger, \ddagger + + 0x7C => 0x2663, # \clubsuit + 0x7D => 0x2662, # \diamondsuit + 0x7E => 0x2661, # \heartsuit + 0x7F => 0x2660, # \spadesuit + ], + + "Caligraphic-Bold" => [ + [0x41,0x5A] => 0x41, # A-Z + ], +}; + +$map{msam10} = { + "Main-Regular" => [ + 0x5C => 0x2220, # \angle + ], + + "Main-Bold" => [ + 0x5C => 0x2220, # \angle (emboldened below) + ], + + "AMS" => [ + 0x00 => 0x22A1, # \boxdot + 0x01 => 0x229E, # \boxplus + 0x02 => 0x22A0, # \boxtimes + 0x03 => 0x25A1, # \square + 0x04 => 0x25A0, # \blacksquare + 0x05 => 0x22C5, # \centerdot + 0x06 => 0x25CA, # \lozenge + 0x07 => 0x29EB, # \blacklozenge + 0x08 => 0x21BB, # \circlearrowright + 0x09 => 0x21BA, # \circlearrowleft + 0x0A => 0x21CC, # \rightleftharpoons + 0x0B => 0x21CB, # \leftrightharpoons + 0x0C => 0x229F, # \boxminus + 0x0D => 0x22A9, # \Vdash + 0x0E => 0x22AA, # \Vvdash + 0x0F => 0x22A8, # \vDash + 0x10 => 0x21A0, # \twoheadrightarrow + 0x11 => 0x219E, # \twoheadleftarrow + 0x12 => 0x21C7, # \leftleftarrows + 0x13 => 0x21C9, # \rightrightarrows + 0x14 => 0x21C8, # \upuparrows + 0x15 => 0x21CA, # \downdownarrows + 0x16 => 0x21BE, # \upharpoonright + 0x17 => 0x21C2, # \downharpoonright + 0x18 => 0x21BF, # \upharpoonleft + 0x19 => 0x21C3, # \downharpoonleft + 0x1A => 0x21A3, # \rightarrowtail + 0x1B => 0x21A2, # \leftarrowtail + 0x1C => 0x21C6, # \leftrightarrows + 0x1D => 0x21C4, # \rightleftarrows + 0x1E => 0x21B0, # \Lsh + 0x1F => 0x21B1, # \Rsh + 0x20 => 0x21DD, # \rightsquigarrow + 0x21 => 0x21AD, # \leftrightsquigarrow + 0x22 => 0x21AB, # \looparrowleft + 0x23 => 0x21AC, # \looparrowright + 0x24 => 0x2257, # \circeq + 0x25 => 0x227F, # \succsim + 0x26 => 0x2273, # \gtrsim + 0x27 => 0x2A86, # \gtrapprox + 0x28 => 0x22B8, # \multimap + 0x29 => 0x2234, # \therefore + 0x2A => 0x2235, # \because + 0x2B => 0x2251, # \doteqdot + 0x2C => 0x225C, # \triangleq + 0x2D => 0x227E, # \precsim + 0x2E => 0x2272, # \lesssim + 0x2F => 0x2A85, # \lessapprox + 0x30 => 0x2A95, # \eqslantless + 0x31 => 0x2A96, # \eqslantgtr + 0x32 => 0x22DE, # \curlyeqprec + 0x33 => 0x22DF, # \curlyeqsucc + 0x34 => 0x227C, # \preccurlyeq + 0x35 => 0x2266, # \leqq + 0x36 => 0x2A7D, # \leqslant + 0x37 => 0x2276, # \lessgtr + 0x38 => 0x2035, # \backprime + 0x39 => 0x2212, # dahsed arrow extension + 0x3A => 0x2253, # \risingdotseq + 0x3B => 0x2252, # \fallingdotseq + 0x3C => 0x227D, # \succcurlyeq + 0x3D => 0x2267, # \geqq + 0x3E => 0x2A7E, # \geqslant + 0x3F => 0x2277, # \gtrless + 0x40 => 0x228F, # \sqsubset + 0x41 => 0x2290, # \sqsupset + 0x42 => 0x22B3, # \vartriangleright + 0x43 => 0x22B2, # \vartriangleleft + 0x44 => 0x22B5, # \trianglerighteq + 0x45 => 0x22B4, # \trianglelefteq + 0x46 => 0x2605, # \bigstar + 0x47 => 0x226C, # \between + 0x48 => 0x25BC, # \blacktriangledown + 0x49 => 0x25B6, # \blacktriangleright + 0x4A => 0x25C0, # \blacktriangleleft + 0x4B => 0x2192, # rightarrow + 0x4C => 0x2190, # leftarrow + 0x4D => 0x25B3, # \vartriangle + 0x4E => 0x25B2, # \blacktriangle + 0x4F => 0x25BD, # \triangledown + 0x50 => 0x2256, # \eqcirc + 0x51 => 0x22DA, # \lesseqgtr + 0x52 => 0x22DB, # \gtreqless + 0x53 => 0x2A8B, # \lesseqqgtr + 0x54 => 0x2A8C, # \gtreqqless + 0x55 => 0x00A5, # yen + 0x56 => 0x21DB, # \Rrightarrow + 0x57 => 0x21DA, # \Lleftarrow + 0x58 => 0x2713, # checkmark + 0x59 => 0x22BB, # \veebar + 0x5A => 0x22BC, # \barwedge + 0x5B => 0x2A5E, # \doublebarwedge + 0x5C => 0x2220, # \angle + 0x5D => 0x2221, # \measuredangle + 0x5E => 0x2222, # \sphericalangle + 0x5F => 0x221D, # \varpropto + 0x60 => 0x2323, # \smallsmile + 0x61 => 0x2322, # \smallfrown + 0x62 => 0x22D0, # \Subset + 0x63 => 0x22D1, # \Supset + 0x64 => 0x22D3, # \Cup + 0x65 => 0x22D2, # \Cap + 0x66 => 0x22CF, # \curlywedge + 0x67 => 0x22CE, # \curlyvee + 0x68 => 0x22CB, # \leftthreetimes + 0x69 => 0x22CC, # \rightthreetimes + 0x6A => 0x2AC5, # \subseteqq + 0x6B => 0x2AC6, # \supseteqq + 0x6C => 0x224F, # \bumpeq + 0x6D => 0x224E, # \Bumpeq + 0x6E => 0x22D8, # \lll + 0x6F => 0x22D9, # \ggg + 0x70 => 0x250C, # \ulcorner + 0x71 => 0x2510, # \urcorner + 0x72 => 0x00AE, # registered sign + 0x73 => 0x24C8, # \circledS + 0x74 => 0x22D4, # \pitchfork + 0x75 => 0x2214, # \dotplus + 0x76 => 0x223D, # \backsim + 0x77 => 0x22CD, # \backsimeq + 0x78 => 0x2514, # \llcorner + 0x79 => 0x2518, # \lrcorner + 0x7A => 0x2720, # maltese cross + 0x7B => 0x2201, # \complement + 0x7C => 0x22BA, # \intercal + 0x7D => 0x229A, # \circledcirc + 0x7E => 0x229B, # \circledast + 0x7F => 0x229D, # \circleddash + ], +}; + +$map{msbm10} = { + "Size4" => [ + 0x5B => 0x2C6, # \widehat + 0x5B => [0x302,-1889,0],# \widehat (combining) + 0x5D => 0x2DC, # \widetilde + 0x5D => [0x303,-1889,0],# \widetilde (combining) + ], + + "Main-Regular" => [ + 0x7E => 0x210F, # \hbar + ], + + "Main-Italic" => [ + 0x7D => 0x210F, # \hbar (with slant) + ], + + "AMS" => [ + 0x00 => 0xE00C, # \lvertneqq + 0x01 => 0xE00D, # \gvertneqq + 0x02 => 0x2270, # \nleq + 0x03 => 0x2271, # \ngeq + 0x04 => 0x226E, # \nless + 0x05 => 0x226F, # \ngtr + 0x06 => 0x2280, # \nprec + 0x07 => 0x2281, # \nsucc + 0x08 => 0x2268, # \lneqq + 0x09 => 0x2269, # \gneqq + 0x0A => 0xE010, # \nleqslant + 0x0B => 0xE00F, # \ngeqslant + 0x0C => 0x2A87, # \lneq + 0x0D => 0x2A88, # \gneq + 0x0E => 0x22E0, # \npreceq + 0x0F => 0x22E1, # \nsucceq + 0x10 => 0x22E8, # \precnsim + 0x11 => 0x22E9, # \succnsim + 0x12 => 0x22E6, # \lnsim + 0x13 => 0x22E7, # \gnsim + 0x14 => 0xE011, # \nleqq + 0x15 => 0xE00E, # \ngeqq + 0x16 => 0x2AB5, # \precneqq + 0x17 => 0x2AB6, # \succneqq + 0x18 => 0x2AB9, # \precnapprox + 0x19 => 0x2ABA, # \succnapprox + 0x1A => 0x2A89, # \lnapprox + 0x1B => 0x2A8A, # \gnapprox + 0x1C => 0x2241, # \nsim + 0x1D => 0x2246, # \ncong + 0x1E => 0x2571, # \diagup + 0x1F => 0x2572, # \diagdown + 0x20 => 0xE01A, # \varsubsetneq + 0x21 => 0xE01B, # \varsupsetneq + 0x22 => 0xE016, # \nsubseteqq + 0x23 => 0xE018, # \nsupseteqq + 0x24 => 0x2ACB, # \subsetneqq + 0x25 => 0x2ACC, # \supsetneqq + 0x26 => 0xE017, # \varsubsetneqq + 0x27 => 0xE019, # \varsupsetneqq + 0x28 => 0x228A, # \subsetneq + 0x29 => 0x228B, # \supsetneq + 0x2A => 0x2288, # \nsubseteq + 0x2B => 0x2289, # \nsupseteq + 0x2C => 0x2226, # \nparallel + 0x2D => 0x2224, # \nmid + 0x2E => 0xE006, # \nshortmid + 0x2F => 0xE007, # \nshortparallel + 0x30 => 0x22AC, # \nvdash + 0x31 => 0x22AE, # \nVdash + 0x32 => 0x22AD, # \nvDash + 0x33 => 0x22AF, # \nVDash + 0x34 => 0x22ED, # \ntrianglerighteq + 0x35 => 0x22EC, # \ntrianglelefteq + 0x36 => 0x22EA, # \ntriangleleft + 0x37 => 0x22EB, # \ntriangleright + 0x38 => 0x219A, # \nleftarrow + 0x39 => 0x219B, # \nrightarrow + 0x3A => 0x21CD, # \nLeftarrow + 0x3B => 0x21CF, # \nRightarrow + 0x3C => 0x21CE, # \nLeftrightarrow + 0x3D => 0x21AE, # \nleftrightarrow + 0x3E => 0x22C7, # \divideontimes + 0x3F => 0x2205, # \varnothing + 0x40 => 0x2204, # \nexists + + [0x41,0x5A] => 0x41, # A-Z + 0x5C => 0x2C6, # \widehat + 0x5C => [0x302,-2333,0],# \widehat (combining) + 0x5E => 0x2DC, # \widetilde + 0x5E => [0x303,-2333,0],# \widetilde (combining) + + 0x60 => 0x2132, # \Finv + 0x61 => 0x2141, # \Game + 0x66 => 0x2127, # \mho + 0x67 => 0x00F0, # \eth + 0x68 => 0x2242, # minus-tilde + 0x69 => 0x2136, # \beth + 0x6A => 0x2137, # \gimel + 0x6B => 0x2138, # \daleth + 0x6C => 0x22D6, # \lessdot + 0x6D => 0x22D7, # \gtrdot + 0x6E => 0x22C9, # \ltimes + 0x6F => 0x22CA, # \rtimes + 0x70 => 0x2223, # \shortmid + 0x71 => 0x2225, # \shortparallel + 0x72 => 0x2216, # \smallsetminus + 0x73 => 0x223C, # \thicksim + 0x74 => 0x2248, # \thickapprox + 0x75 => 0x224A, # \approxeq + 0x76 => 0x2AB8, # \succapprox + 0x77 => 0x2AB7, # \precapprox + 0x78 => 0x21B6, # \curvearrowleft + 0x79 => 0x21B7, # \curvearrowright + 0x7A => 0x03DD, # \digamma + 0x7B => 0x03F0, # \varkappa + 0x7A => 0xE008, # \digamma (non-standard, for IE) + 0x7B => 0xE009, # \varkappa (non-standard, for IE) + 0x7C => 0x006B, # \Bbbk + 0x7D => 0x210F, # \hslash + 0x7E => 0x0127, # \hbar + 0x7F => 0x220D, # \backepsilon + ], +}; + +$map{cmss10} = { + "SansSerif-Regular" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-142,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x2F] => 0x21, # !, ", #, $, %, &, ', (, ), *, +, comma, -, ., / + 0x22 => 0x201D, # " + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-350], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + ], +}; + +$map{cmssi10} = { + "SansSerif-Italic" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-113,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x2F] => 0x21, # !, ", #, $, %, &, ', (, ), *, +, comma, -, ., / + 0x22 => 0x201D, # " + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-350], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + ], +}; + +$map{cmssbx10} = { + "SansSerif-Bold" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x13 => 0xB4, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-58,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x2F] => 0x21, # !, ", #, $, %, &, ', (, ), *, +, comma, -, ., / + 0x22 => 0x201D, # " + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-350], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + ], +}; + +$map{eufm10} = { + "Fraktur-Regular" => [ + [0,7] => 0xE300, # variants + 0x12 => 0x2018, # left quote + 0x13 => 0x2019, # right quote + 0x21 => 0x21, # ! + [0x26,0x2F] => 0x26, # &, ', (, ), *, +, comma, -, ., / + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + 0x3F => 0x3F, # ? + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + [0x5D,0x5E] => 0x5D, # ], ^ + [0x61,0x7A] => 0x61, # a-z + 0x7D => 0x22, # " + ], +}; + +$map{eufb10} = { + "Fraktur-Bold" => [ + [1,5] => 0xE301, # variants + [8,9] => 0xE308, # variants + 0x12 => 0x2018, # left quote + 0x13 => 0x2019, # right quote + 0x21 => 0x21, # ! + [0x26,0x2F] => 0x26, # &, ', (, ), *, +, comma, -, ., / + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + 0x3F => 0x3F, # ? + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + [0x5D,0x5E] => 0x5D, # ], ^ + [0x61,0x7A] => 0x61, # a-z + 0x7D => 0x22, # " + ], +}; + +$map{rsfs10} = { + "Script-Regular" => [ + [0x41,0x5A] => 0x41, # A-Z + ] +}; + +#$map{eusm10} = { +# "Script-Regular" => [ +# 0x3C => 0x211C, # \Re +# 0x3D => 0x2111, # \Im +# 0x40 => 0x2135, # \aleph +# [0x41,0x5A] => 0x41, # A-Z +# 0x66 => 0x7B, # { +# 0x67 => 0x7D, # } +# 0x78 => 0xA7, # \S +# ], +#}; + +#$map{eusb10} = { +# "Script-Bold" => [ +# 0x3C => 0x211C, # \Re +# 0x3D => 0x2111, # \Im +# 0x40 => 0x2135, # \aleph +# [0x41,0x5A] => 0x41, # A-Z +# 0x66 => 0x7B, # { +# 0x67 => 0x7D, # } +# 0x78 => 0xA7, # \S +# ], +#}; + +$map{cmtt10} = { + "Typewriter" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + 0xD => 0x2032, # ' + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => 0xB0, # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + 0x20 => 0x2423, # graphic representation of space + + [0x21,0x7F] => 0x21, + + 0x60 => 0x2018, # left quote + 0x27 => 0x2019, # right quote + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + ] +}; + +######################################################################### + +$extra{'Main-Regular'} = { + cdots => [ + 'Select(0u22C5)','Copy()', + 'Select(0u22EF)','Paste()', + 'PasteWithOffset(447,0)', + 'PasteWithOffset(894,0)', + 'SetRBearing(894,1)', + ], + + ldots => [ + 'Select(0u2E)','Copy()', + 'Select(0u2026)','Paste()', + 'PasteWithOffset(447,0)', + 'PasteWithOffset(894,0)', + 'SetRBearing(894,1)', + ], + + vdots => [ + 'Select(0u2E)','Copy()', + 'Select(0u22EE)','Clear()', + 'PasteWithOffset(0,-30)', + 'PasteWithOffset(0,380)', + 'PasteWithOffset(0,780)', + 'SetRBearing(-722,1)', + ], + + ddots => [ + 'Select(0u2E)','Copy()', + 'Select(0u22F1)','Clear()', + 'PasteWithOffset(55,700)', + 'PasteWithOffset(502,400)', + 'PasteWithOffset(949,100)', + 'SetRBearing(282,1)', + ], + + spaceEn => [ + 'Select(0u2002)', + 'SetRBearing(500)', + ], + + spaceEm => [ + 'Select(0u2003)', + 'SetRBearing(999)', + ], + + space3 => [ + 'Select(0u2004)', + 'SetRBearing(333)', + ], + + space4 => [ + 'Select(0u2005)', + 'SetRBearing(250)', + ], + + space6 => [ + 'Select(0u2006)', + 'SetRBearing(167)', + ], + + thinspace => [ + 'Select(0u2009)', + 'SetRBearing(167)', + ], + + hairspace => [ + 'Select(0u200A)', + 'SetRBearing(83)', + ], + + cong => [ + 'Select(0u223C)','Copy()', + 'Select(0u2245)','Clear()', + 'PasteWithOffset(0,222)', + 'Select(0u3D)','Copy()', + 'Select(0u2245)', + 'PasteWithOffset(0,-111)', + 'SetWidth(778)', + ], + + bowtie => [ + 'Select(0u25B9)','Copy()', + 'Select(0u22C8)','Paste()', + 'Select(0u25C3)','Copy()', + 'Select(0u22C8)', + 'PasteWithOffset(400,0)', + 'SetRBearing(400,1)', + 'RemoveOverlap()', + ], + + models => [ + 'Select(0u2223)','Copy()', + 'Select(0u22A8)','Paste()', + 'Select(0u3D)','Copy()', + 'Select(0u22A8)', + 'PasteWithOffset(89,0)', + 'SetRBearing(589,1)', + 'RemoveOverlap()', + ], + + doteq => [ + 'Select(0u3D)','Copy()', + 'Select(0u2250)','Paste()', + 'Select(0u2E)','Copy()', + 'Select(0u2250)', + 'PasteWithOffset(251,550)', + ], + + not => [ + 'Select(0uE020)', + 'SetRBearing(778,1)', + ], + + #notin => [ + # 'Select(0u2208)','Copy()', + # 'Select(0u2209)','Paste()', + # 'Select(0u338)','Copy()', + # 'Select(0u2209)', + # 'PasteWithOffset(-55,0)', + # 'RemoveOverlap()', + #], + + #noteq => [ + # 'Select(0u3D)','Copy()', + # 'Select(0u2260)','Paste()', + # 'Select(0u338)','Copy()', + # 'Select(0u2260)', + # 'PasteWithOffset(0,0)', + # 'RemoveOverlap()', + #], + + longleftarrow => [ + 'Select(0u2190)','Copy()', + 'Select(0u27F5)','Paste()', + 'Select(0u2212)','Copy()', + 'Select(0u27F5)', + 'PasteWithOffset(831,0)', + 'SetRBearing(609,1)', + 'RemoveOverlap()','Simplify()', + ], + + Longleftarrow => [ + 'Select(0u21D0)','Copy()', + 'Select(0u27F8)','Paste()', + 'Select(0u3D)','Copy()', + 'Select(0u27F8)', + 'PasteWithOffset(831,0)', + 'SetRBearing(609,1)', + 'RemoveOverlap()','Simplify()', + ], + + longrightarrow => [ + 'Select(0u2212)','Copy()', + 'Select(0u27F6)','Paste()', + 'Select(0u2192)','Copy()', + 'Select(0u27F6)', + 'PasteWithOffset(609,0)', + 'SetRBearing(860,1)', + 'RemoveOverlap()','Simplify()', + ], + + Longrightarrow => [ + 'Select(0u3D)','Copy()', + 'Select(0u27F9)','Paste()', + 'Select(0u21D2)','Copy()', + 'Select(0u27F9)', + 'PasteWithOffset(638,0)', + 'SetRBearing(860,1)', + 'RemoveOverlap()','Simplify()', + ], + + leftrightarrow => [ + 'Select(0u2190)','Copy()', + 'Select(0u27F7)','Paste()', + 'Select(0u2192)','Copy()', + 'Select(0u27F7)', + 'PasteWithOffset(859,0)', + 'SetRBearing(859,1)', + 'RemoveOverlap()','Simplify()', + ], + + Leftrightarrow => [ + 'Select(0u21D0)','Copy()', + 'Select(0u27FA)','Paste()', + 'Select(0u21D2)','Copy()', + 'Select(0u27FA)', + 'PasteWithOffset(858,0)', + 'SetRBearing(858,1)', + 'RemoveOverlap()','Simplify()', + ], + + mapsto => [ + 'Select(0u2192)','Copy()', + 'Select(0u21A6)','Paste()', + 'Generate("otf/KaTeX_Main-Regular.otf")', + 'Open("pfa/cmsy10.pfa")', + 'Select(0x37)','Copy()', + 'Open("otf/KaTeX_Main-Regular.otf")', + 'Select(0u21A6)', + 'PasteWithOffset(0,0)', + 'RemoveOverlap()','Simplify()', + ], + + xlongmapsto => [ + 'Select(0u27F6)','Copy()', + 'Select(0u27FC)','Paste()', + 'Generate("otf/KaTeX_Main-Regular.otf")', + 'Open("pfa/cmsy10.pfa")', + 'Select(0x37)','Copy()', + 'Open("otf/KaTeX_Main-Regular.otf")', + 'Select(0u27FC)', + 'PasteWithOffset(0,0)', + 'RemoveOverlap()','Simplify()', + ], + + hookleftarrow => [ + 'Select(0u2190)','Copy()', + 'Select(0u21A9)','Paste()', + 'Generate("otf/KaTeX_Main-Regular.otf")', + 'Open("pfa/cmmi10.pfa")', + 'Select(0x2D)','Copy()', + 'Open("otf/KaTeX_Main-Regular.otf")', + 'Select(0u21A9)', + 'PasteWithOffset(848,0)', + 'SetRBearing(126,1)', + 'RemoveOverlap()','Simplify()', + ], + + hookrightarrow => [ + 'Generate("otf/KaTeX_Main-Regular.otf")', + 'Open("pfa/cmmi10.pfa")', + 'Select(0x2C)','Copy()', + 'Open("otf/KaTeX_Main-Regular.otf")', + 'Select(0u21AA)','Paste()', + 'Select(0u2192)','Copy()', + 'Select(0u21AA)', + 'PasteWithOffset(126,0)', + 'SetRBearing(848,1)', + 'RemoveOverlap()','Simplify()', + ], + + rightleftharpoons => [ + 'Select(0u21BD)','Copy()', + 'Select(0u21CC)','Paste()', + 'Select(0u21C0)','Copy()', + 'Select(0u21CC)', + 'PasteWithOffset(0,160)', + 'RemoveOverlap()','Simplify()', + ], + + lgroup => [ + 'Select(0u23B0)','Copy()', + 'Select(0u27EE)','Paste()', + 'Select(0u23A9)','Copy()', + 'Select(0u27EE)', + 'PasteWithOffset(0,0)', + 'Scale(55,0,0)','RoundToInt()','Move(-38,250)', + 'RemoveOverlap()','Simplify()', + 'SetRBearing(-38,1)', + ], + + rgroup => [ + 'Select(0u23B1)','Copy()', + 'Select(0u27EF)','Paste()', + 'Select(0u23AD)','Copy()', + 'Select(0u27EF)', + 'PasteWithOffset(1,0)', + 'Scale(55,0,0)','RoundToInt()','Move(-38,250)', + 'RemoveOverlap()','Simplify()', + 'SetRBearing(-38,1)', + ], + + lmoustache => [ + 'Select(0u23AD)','Copy()', + 'Select(0u23B0)', + 'PasteWithOffset(0,0)', + 'Scale(55,0,0)','RoundToInt()','Move(-38,250)', + 'RemoveOverlap()','Simplify()', + 'SetRBearing(-38,1)', + ], + + rmoustache => [ + 'Select(0u23A9)','Copy()', + 'Select(0u23B1)', + 'PasteWithOffset(0,0)', + 'Scale(55,0,0)','RoundToInt()','Move(-38,250)', + 'RemoveOverlap()','Simplify()', + 'SetRBearing(-38,1)', + ], + + diacriticals => [ + 'Select(0uB0)', 'SetRBearing(-125,1)', # \degree + 'Select(0u20D7)','SetRBearing(153,1)', # \vec + ], + +}; + +$extra{'Main-Bold'} = { + cdots => [ + 'Select(0u22C5)','Copy()', + 'Select(0u22EF)','Paste()', + 'PasteWithOffset(488,0)', + 'PasteWithOffset(976,0)', + 'SetRBearing(976,1)', + ], + + ldots => [ + 'Select(0u2E)','Copy()', + 'Select(0u2026)','Paste()', + 'PasteWithOffset(488,0)', + 'PasteWithOffset(976,0)', + 'SetRBearing(976,1)', + ], + + vdots => [ + 'Select(0u2E)','Copy()', + 'Select(0u22EE)','Clear()', + 'PasteWithOffset(0,-30)', + 'PasteWithOffset(0,380)', + 'PasteWithOffset(0,780)', + 'SetRBearing(-681,1)', + ], + + ddots => [ + 'Select(0u2E)','Copy()', + 'Select(0u22F1)','Clear()', + 'PasteWithOffset(55,700)', + 'PasteWithOffset(502,400)', + 'PasteWithOffset(949,100)', + 'SetRBearing(323,1)', + ], + + spaceEn => [ + 'Select(0u2002)', + 'SetRBearing(500)', + ], + + spaceEm => [ + 'Select(0u2003)', + 'SetRBearing(999)', + ], + + space3 => [ + 'Select(0u2004)', + 'SetRBearing(333)', + ], + + space4 => [ + 'Select(0u2005)', + 'SetRBearing(250)', + ], + + space6 => [ + 'Select(0u2006)', + 'SetRBearing(167)', + ], + + thinspace => [ + 'Select(0u2009)', + 'SetRBearing(167)', + ], + + hairspace => [ + 'Select(0u200A)', + 'SetRBearing(83)', + ], + + cong => [ + 'Select(0u223C)','Copy()', + 'Select(0u2245)','Clear()', + 'PasteWithOffset(0,247)', + 'Select(0u3D)','Copy()', + 'Select(0u2245)', + 'PasteWithOffset(0,-136)', + 'SetWidth(894)', + ], + + bowtie => [ + 'Select(0u25B9)','Copy()', + 'Select(0u22C8)','Paste()', + 'Select(0u25C3)','Copy()', + 'Select(0u22C8)', + 'PasteWithOffset(425,0)', + 'SetRBearing(425,1)', + 'RemoveOverlap()', + ], + + models => [ + 'Select(0u2223)','Copy()', + 'Select(0u22A8)','Paste()', + 'Select(0u3D)','Copy()', + 'Select(0u22A8)', + 'PasteWithOffset(89,0)', + 'SetRBearing(655,1)', + 'RemoveOverlap()', + ], + + doteq => [ + 'Select(0u3D)','Copy()', + 'Select(0u2250)','Paste()', + 'Select(0u2E)','Copy()', + 'Select(0u2250)', + 'PasteWithOffset(288,550)', + ], + + not => [ + 'Select(0uE020)', + 'SetRBearing(894,1)', + ], + +# notin => [ +# 'Select(0u2208)','Copy()', +# 'Select(0u2209)','Paste()', +# 'Select(0u338)','Copy()', +# 'Select(0u2209)', +# 'PasteWithOffset(-63,0)', +# 'PasteWithOffset(831,0)', +# 'RemoveOverlap()', +# ], + +# noteq => [ +# 'Select(0u3D)','Copy()', +# 'Select(0u2260)','Paste()', +# 'Select(0u338)','Copy()', +# 'Select(0u2260)', +# 'PasteWithOffset(0,0)', +# 'PasteWithOffset(894,0)', +# 'RemoveOverlap()', +# ], + + longleftarrow => [ + 'Select(0u2190)','Copy()', + 'Select(0u27F5)','Paste()', + 'Select(0u2212)','Copy()', + 'Select(0u27F5)', + 'PasteWithOffset(944,0)', + 'SetRBearing(655,1)', + 'RemoveOverlap()','Simplify()', + ], + + Longleftarrow => [ + 'Select(0u21D0)','Copy()', + 'Select(0u27F8)','Paste()', + 'Select(0u3D)','Copy()', + 'Select(0u27F8)', + 'PasteWithOffset(975,0)', + 'SetRBearing(718,1)', + 'RemoveOverlap()','Simplify()', + ], + + longrightarrow => [ + 'Select(0u2212)','Copy()', + 'Select(0u27F6)','Paste()', + 'Select(0u2192)','Copy()', + 'Select(0u27F6)', + 'PasteWithOffset(688,0)', + 'SetRBearing(939,1)', + 'RemoveOverlap()','Simplify()', + ], + + Longrightarrow => [ + 'Select(0u3D)','Copy()', + 'Select(0u27F9)','Paste()', + 'Select(0u21D2)','Copy()', + 'Select(0u27F9)', + 'PasteWithOffset(720,0)', + 'SetRBearing(976,1)', + 'RemoveOverlap()','Simplify()', + ], + + leftrightarrow => [ + 'Select(0u2190)','Copy()', + 'Select(0u27F7)','Paste()', + 'Select(0u2192)','Copy()', + 'Select(0u27F7)', + 'PasteWithOffset(976,0)', + 'SetRBearing(976,1)', + 'RemoveOverlap()','Simplify()', + ], + + Leftrightarrow => [ + 'Select(0u21D0)','Copy()', + 'Select(0u27FA)','Paste()', + 'Select(0u21D2)','Copy()', + 'Select(0u27FA)', + 'PasteWithOffset(976,0)', + 'SetRBearing(976,1)', + 'RemoveOverlap()','Simplify()', + ], + + mapsto => [ + 'Select(0u2192)','Copy()', + 'Select(0u21A6)','Paste()', + 'Generate("otf/KaTeX_Main-Bold.otf")', + 'Open("pfa/cmbsy10.pfa")', + 'Select(0x37)','Copy()', + 'Open("otf/KaTeX_Main-Bold.otf")', + 'Select(0u21A6)', + 'PasteWithOffset(0,0)', + 'RemoveOverlap()','Simplify()', + ], + + xlongmapsto => [ + 'Select(0u27F6)','Copy()', + 'Select(0u27FC)','Paste()', + 'Generate("otf/KaTeX_Main-Bold.otf")', + 'Open("pfa/cmbsy10.pfa")', + 'Select(0x37)','Copy()', + 'Open("otf/KaTeX_Main-Bold.otf")', + 'Select(0u27FC)', + 'PasteWithOffset(0,0)', + 'RemoveOverlap()','Simplify()', + ], + + hookleftarrow => [ + 'Select(0u2190)','Copy()', + 'Select(0u21A9)','Paste()', + 'Generate("otf/KaTeX_Main-Bold.otf")', + 'Open("pfa/cmmib10.pfa")', + 'Select(0x2D)','Copy()', + 'Open("otf/KaTeX_Main-Bold.otf")', + 'Select(0u21A9)', + 'PasteWithOffset(965,0)', + 'SetRBearing(132,1)', + 'RemoveOverlap()','Simplify()', + ], + + hookrightarrow => [ + 'Generate("otf/KaTeX_Main-Bold.otf")', + 'Open("pfa/cmmib10.pfa")', + 'Select(0x2C)','Copy()', + 'Open("otf/KaTeX_Main-Bold.otf")', + 'Select(0u21AA)','Paste()', + 'Select(0u2192)','Copy()', + 'Select(0u21AA)', + 'PasteWithOffset(132,0)', + 'SetRBearing(963,1)', + 'RemoveOverlap()','Simplify()', + ], + + rightleftharpoons => [ + 'Select(0u21BD)','Copy()', + 'Select(0u21CC)','Paste()', + 'Select(0u21C0)','Copy()', + 'Select(0u21CC)', + 'PasteWithOffset(0,200)', + 'RemoveOverlap()','Simplify()', + ], + + hbar => [ + 'Select(0u2C9)','Copy()', + 'Select(0u210F)','PasteWithOffset(0,0)', + 'RemoveOverlap()','Simplify()', + ], + + angle => [ + 'Select(0u2220)','Copy()', + 'PasteWithOffset(0,10)', + 'PasteWithOffset(0,20)', + 'RemoveOverlap()','Simplify()', + 'PasteWithOffset(10,0)', + 'RemoveOverlap()','Simplify()', + ], + + diacriticals => [ + 'Select(0uB0)', 'SetRBearing(-147,1)', # \degree + 'Select(0u20D7)','SetRBearing(154,1)', # \vec + ], +}; + +$extra{'Main-Italic'} = { + diacriticals => [ + 'Select(0uB0)', 'SetRBearing(-160,1)', # \degree + ], +}; + +$extra{'Size1'} = { + iint => [ + 'Select(0u222B)', 'Copy()', + 'Select(0u222C)', 'Paste()', + 'PasteWithOffset(347,0)', + 'SetRBearing(347,1)', + ], + + iiint => [ + 'Select(0u222B)', 'Copy()', + 'Select(0u222D)', 'Paste()', + 'PasteWithOffset(347,0)', + 'PasteWithOffset(694,0)', + 'SetRBearing(694,1)', + ], +}; + +$extra{'Size2'} = { + iint => [ + 'Select(0u222B)', 'Copy()', + 'Select(0u222C)', 'Paste()', + 'PasteWithOffset(528,0)', + 'SetRBearing(528,1)', + ], + + iiint => [ + 'Select(0u222B)', 'Copy()', + 'Select(0u222D)', 'Paste()', + 'PasteWithOffset(528,0)', + 'PasteWithOffset(1036,0)', + 'SetRBearing(1036,1)', + ], +}; + +$extra{'Size4'} = { + braceext => [ + 'Open("lib/Extra.otf")', + 'Select(0u5F)','Copy()', + 'Open("otf/KaTeX_Size4-Regular.otf")', + 'Select(0uE154)','Paste()', + ], +}; + +$extra{"AMS"} = { + dashleftarrow => [ + 'Select(0u2190)', 'Copy()', + 'Select(0u21E0)', 'Paste()', + 'Select(0u2212)','Copy()', + 'Select(0u21E0)', + 'PasteWithOffset(417,0)', + 'PasteWithOffset(834,0)', + 'SetRBearing(834,1)', + ], + + dashrightarrow => [ + 'Select(0u2212)', 'Copy()', + 'Select(0u21E2)', 'Paste()', + 'PasteWithOffset(417,0)', + 'Select(0u2192)','Copy()', + 'Select(0u21E2)','PasteWithOffset(834,0)', + 'SetRBearing(834,1)', + ], +}; + +$extra{'Typewriter'} = { + space => [ + 'Select(0u20)','Clear()', + 'SetRBearing(525)', + ], + + spaceNB => [ + 'Select(0uA0)','Clear()', + 'SetRBearing(525)', + ], +}; + +$extra{"SansSerif-Regular"} = { + diacriticals => [ + 'Select(0uB0)', 'SetRBearing(-142,1)', # \degree + ], +}; + +$extra{"SansSerif-Italic"} = { + diacriticals => [ + 'Select(0uB0)', 'SetRBearing(-113,1)', # \degree + ], +}; + +$extra{"SansSerif-Bold"} = { + diacriticals => [ + 'Select(0uB0)', 'SetRBearing(-58,1)', # \degree + ], +}; + +######################################################################### + +foreach $cmfont (sort (keys %map)) { + print "Reading $cmfont...\n"; + foreach $mjfont (keys %{$map{$cmfont}}) { + $fontname = "KaTeX_$mjfont"; + $style = $fontname; $style =~ s/.*?(-|$)//; $style = "Regular" unless $style; + $normal = "Normal"; $normal = "Bold" if style =~ m/Bold/; + $family = $fontname; $family =~ s/-.*//; + $fontname = "$family-$style"; + $STYLE = $style; $STYLE = "Bold Italic" if $STYLE eq "BoldItalic"; + $otf = "otf/$fontname.otf"; + unless (defined($script{$mjfont})) { + open(SPACE,"lib/Space.ttx"); $lines = join("",); close(SPACE); + $lines =~ s/\*NAME\*/$family/g; $lines =~ s/\*WEIGHT\*/$style/g; + $lines =~ s/\*WEIGHT_S\*/$STYLE/g; $lines =~ s/\*NORMAL\*/$normal/g; + if ($style eq "Regular") {$lines =~ s/\* WEIGHT\*//g} else {$lines =~ s/\* WEIGHT\*/ $STYLE/g} + open(SPACE,">Space.ttx"); print SPACE $lines; close(SPACE); + `$TTX -f Space.ttx; mv Space.otf '$otf'`; unlink("Space.ttx"); + $script{$mjfont} = [ + 'Open("'.$otf.'")', + 'SetPanose([0,0,'.($style eq 'Bold' ? '8' : '0').',0,0,0,0,0,0,0])', + 'SetOS2Value("Weight",'.($style =~ m/Bold/ ? 700 : 400).')', + 'SetGasp(8,2,16,1,65535,3)', + 'Reencode("unicode")', + 'Generate("'.$otf.'")', + ]; + } + $script = $script{$mjfont}; + @remap = @{$map{$cmfont}{$mjfont}}; + while (defined($item = shift(@remap))) { + $remap = shift(@remap); + if ($cmfont =~ /^eu/) { + push(@$script,'Open("pfa/'.$cmfont.'.pfb")'); + } else { + push(@$script,'Open("pfa/'.$cmfont.'.pfa")'); + } + if (ref($item) eq "ARRAY") { + push(@$script,'Select('.sprintf("%d,%d",@$item).')'); + } else { + push(@$script,'Select('.$item.')'); + } + push(@$script,"Copy()",'Open("'.$otf.'")'); + if (ref($item) eq "ARRAY") { + push(@$script, + 'Select('.sprintf("0u%04x,0u%04x",$remap,$remap+($item->[1]-$item->[0])).')', + 'Paste()', + ); + } elsif (ref($remap) eq "ARRAY") { + push(@$script, + 'Select('.sprintf("0u%04x",$remap->[0]).')', + 'Paste()', + 'Move('.$remap->[1].','.$remap->[2].')', + ); + } else { + push(@$script,'Select('.sprintf("0u%04x",$remap).')','Paste()'); + } + push(@$script,'Generate("'.$otf.'")'); + } + } +} +print "\n"; + + +# +# Add extra characters by hand +# +foreach $font (keys %extra) { + foreach $char (sort(keys %{$extra{$font}})) { + push(@{$script{$font}},join(";\n",@{$extra{$font}{$char}}),""); + } +} + +# Cleanup temporary glyphs +push(@{$script{'Main-Regular'}}, + 'Select(0u23A9)', + 'Clear()', + 'Select(0u23AD)', + 'Clear()', +); + +# +# Write all scripts +# +foreach $font (sort keys %script) { + $family = $font; $family .= "-Regular" unless $family =~ m/-/; + print "KaTeX_$font\n"; + open(SCRIPT,">","ff/KaTeX_$family.ff"); + print SCRIPT join(";\n",@{$script{$font}},"", + 'SelectAll()','RoundToInt()', + 'Simplify()','AddExtrema()','Simplify()', + 'ClearHints()','AutoHint()','RoundToInt()', + 'Generate("otf/KaTeX_'.$family.'.otf")', + 'SelectAll()','AutoInstr()', + 'Generate("ttf/KaTeX_'.$family.'.ttf")'),"\n"; + close(SCRIPT); +} + +1; diff --git a/frontend/node_modules/katex/src/fonts/xbbold.mf b/frontend/node_modules/katex/src/fonts/xbbold.mf new file mode 100644 index 0000000..64a6683 --- /dev/null +++ b/frontend/node_modules/katex/src/fonts/xbbold.mf @@ -0,0 +1,182 @@ +%% filename: xbbold.mf +%% version: 2.2 +%% date: 1995/01/04 +%% +%% (katex-fonts) The line 69 is modified to prevent overflow +%% +%% American Mathematical Society +%% Technical Support +%% Publications Technical Group +%% 201 Charles Street +%% Providence, RI 02904 +%% USA +%% tel: (401) 455-4080 +%% (800) 321-4267 (USA and Canada only) +%% fax: (401) 331-3842 +%% email: tech-support@ams.org +%% +%% Copyright 1995, 2009 American Mathematical Society. +%% +%% This Font Software is licensed under the SIL Open Font License, +%% Version 1.1. This license is in the accompanying file OFL.txt, and +%% is also available with a FAQ at: http://scripts.sil.org/OFL. +%% +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + +% Changes of minimal parameters in outlined characters for version 2.1 +% done by Stefan Lindner, 18-April-1991 + +input xbbase; +%%mode_setup; %called by amsyb.mf; two calls confuse Metafont. NGB 15-OCT-1991 + +%%%%designsize:= font_size; % was 10pt#; +width#:= designsize; % was 10pt#; +unit#:= width#/18; +u#:= width#/54; +smallu#:= width#/162; +ascender#:= 37/3*unit#; +cap#:= 37/3*unit#; +number#:= 36/3*unit#; +xheight#:= 25/3*unit#; +descender#:= 12/4*unit#; +define_whole_vertical_pixels + (width,unit,u,smallu,ascender,cap,number,xheight,descender); +wpix(1.90u) (linethickness); +wpix(0.65u) (Sover_bot); +wpix(1.00u) (Aapex,Napex,Vapex,Wapex,Cover,Gover,Oover,Sover_top,Uover); +wpix(9.00u) (Uthin_bracket); +wpix(8.00u) (Kthin_diag_bracket,Xthin_diag_bracket,Ythin_diag_bracket); +wpix(7.00u) (k_thin_diag); +wpix(6.00u) (c_thin_stem_bracket); +wpix(5.00u) (c_thick_stem_bracket,c_inner_bracket,lc_thick_stem_bracket); +wpix(4.00u) (c_round_bracket); +adjpix(1.35u) (serif_thickness); +adjpix(1.30u) (Emid_tip,inbeak); +adjpix(1.50u) (Atip,Btopthin,Bmidthin,Ebot_tip,Ltip,Mapex, + Ntip,Ttip,Vtip,Wtip,Ztip,outbeak); +adjpix(1.65u) (Bbotthin,Gbotthin,Stopthin); +adjpix(1.75u) (Dtopthin,Ebotarm,Lthin,Tthin); +adjpix(1.80u) (Abar,Ctopthin,Dbotthin,Gtopthin,Jbotthin,Pmidarm,Sbotthin); +adjpix(1.90u) (Emidarm,Etoparm,Othin,Pthin,Rthin,Ydiag,Zthin); +adjpix(2.00u) (kthin,Mthin_diag,Wleftthin); +adjpix(2.10u) (Ctip); +adjpix(2.25u) (Athin,Kthin,Mthin_vert,Nthin,Uthin,Vthin,Wrightthin,Xthin); +adjpix(2.50u) (Hbar); +adjpix(2.60u) (Cbotthin); + + +%%%% Begin of changes for version 2.1 +%(katex-fonts) Originally was pixels_per_inch*designsize < 1500: +if pixels_per_inch < 1500/designsize: + if pixels_per_inch*designsize < 1000: + if pixels_per_inch*designsize < 800: + if pixels_per_inch*designsize < 700: + minadjpix(0)(8.80u) (stem); + minadjpix(0)(6.80u) (kdiag); + minadjpix(0)(7.40u) (kstem); + minadjpix(0)(7.80u) (Jbulb,Mdiag); + minadjpix(0)(8.20u) (Kdiag); + minadjpix(0)(8.30u) (Gstem,Mstem); + minadjpix(0)(8.60u) (Lstem,Ustem,Ythick_diag); + minadjpix(0)(8.50u) (Bstem,Estem,Fstem,Ndiag,Rdiag,Xdiag,Zdiag); + minadjpix(0)(8.90u) (Btopcurve); + minadjpix(1)(9.30u) (Bbotcurve,Pcurve,Rcurve); + minadjpix(1)(9.50u) (Ccurve,Dcurve,Gcurve,Ocurve); + else: + minadjpix(1)(8.80u) (stem); + minadjpix(1)(6.80u) (kdiag); + minadjpix(1)(7.40u) (kstem); + minadjpix(1)(7.80u) (Jbulb,Mdiag); + minadjpix(1)(8.20u) (Kdiag); + minadjpix(1)(8.30u) (Gstem,Mstem); + minadjpix(1)(8.60u) (Lstem,Ustem,Ythick_diag); + minadjpix(1)(8.50u) (Bstem,Estem,Fstem,Ndiag,Rdiag,Xdiag,Zdiag); + minadjpix(1)(8.90u) (Btopcurve); + minadjpix(2)(9.30u) (Bbotcurve,Pcurve,Rcurve); + minadjpix(2)(9.50u) (Ccurve,Dcurve,Gcurve,Ocurve); + fi + else: + adjpix(3.0u) (Mapex); + minadjpix(1)(8.80u) (stem); + minadjpix(2)(6.80u) (kdiag); + minadjpix(2)(7.40u) (kstem); + minadjpix(2)(7.80u) (Jbulb); + minadjpix(1)(6.00u) (Mdiag); + minadjpix(2)(8.20u) (Kdiag); + minadjpix(2)(8.30u) (Gstem) + minadjpix(2)(8.30u) (Mstem); + minadjpix(2)(8.60u) (Lstem,Ustem,Ythick_diag); + minadjpix(2)(8.50u) (Bstem,Ndiag,Rdiag,Xdiag,Zdiag); + minadjpix(1)(8.50u) (Estem, Fstem); + minadjpix(2)(8.90u) (Btopcurve); + minadjpix(3)(9.30u) (Bbotcurve,Pcurve,Rcurve); + minadjpix(3)(9.50u) (Ccurve,Dcurve,Gcurve,Ocurve); + fi + else: + adjpix(3.0u) (Mapex); + minadjpix(2)(8.80u) (stem); + minadjpix(3)(6.80u) (kdiag); + minadjpix(3)(7.40u) (kstem); + minadjpix(3)(7.80u) (Jbulb); + minadjpix(1)(5.00u) (Mdiag); + minadjpix(3)(8.20u) (Kdiag); + minadjpix(3)(8.30u) (Gstem); + minadjpix(2)(8.30u) (Mstem); + minadjpix(3)(8.60u) (Lstem,Ustem,Ythick_diag); + minadjpix(3)(8.50u) (Estem,Fstem,Ndiag,Rdiag,Xdiag,Zdiag); + minadjpix(2)(8.50u) (Bstem); + minadjpix(3)(8.90u) (Btopcurve); + minadjpix(3)(9.30u) (Bbotcurve,Pcurve,Rcurve); + minadjpix(3)(9.50u) (Ccurve,Dcurve,Gcurve,Ocurve) + fi +else: + minadjpix(4)(8.80u) (stem); + minadjpix(4)(6.80u) (kdiag); + minadjpix(4)(7.40u) (kstem); + minadjpix(4)(7.80u) (Jbulb,Mdiag); + minadjpix(4)(8.20u) (Kdiag); + minadjpix(4)(8.30u) (Gstem,Mstem); + minadjpix(4)(8.60u) (Lstem,Ustem,Ythick_diag); + minadjpix(4)(8.50u) (Bstem,Estem,Fstem,Ndiag,Rdiag,Xdiag,Zdiag); + minadjpix(4)(8.90u) (Btopcurve); + minadjpix(5)(9.30u) (Bbotcurve,Pcurve,Rcurve); + minadjpix(5)(9.50u) (Ccurve,Dcurve,Gcurve,Ocurve) +fi; +%%%% end of changes for version 2.1 + +boolean lowres; lowres:=width<50; +highres_lowres(pullin) (.85)(1); % Emidarm +highres_lowres(pulleven) (1)(1.3); % Etoparm,Tarms,Zarms +highres_lowres(pullout) (1.1)(1); % Ebotarm,Lbotarm +highres_lowres(bracket0) (.0)(0); % Ntopleft +highres_lowres(bracket3) (.3)(0); % Nthinstems +highres_lowres(bracket01) (.0)(.1); % Uthin +highres_lowres(bracket32) (.3)(.2); % Vstems +highres_lowres(bracket4) (.4)(0); % P-all,R-all,I-all,F-all +highres_lowres(bracket42) (.4)(.2); % Xdiag + +bool(ctrls):=false; +entasis:=inlimit(0)(0,1); +serif_constant_amt:=0pt; +join_radius:=1; +bool(softpath):=true; + +c_thick_stem_bracket:=min(.5cap-eps,c_thick_stem_bracket); +rulepen:=pensquare scaled 1; +extra_beginchar:=extra_beginchar&"save t,p,ref; path p[],p[]',p[]'',ref[];"; +extra_beginchar:=extra_beginchar&"pickup pencircle scaled linethickness;"; + +for x:="R": + wanted[byte x]:=true; endfor % test these characters + let iff=always_iff; % tests all chars in the file + +font_normal_space .3width#; % TeX fontdimen 2 normal word space +font_normal_stretch .15width#; % TeX fontdimen 3 interword stretch +font_normal_shrink .1width#; % TeX fontdimen 4 interword shrink +font_x_height xheight#; % Tex fontdinem 5 for accents +font_quad width#; % TeX fontdimen 6 quad width +font_extra_space .1width#; % TeX fontdimen 7 extra space(period) + + +input xbcaps +bye % changed from "end" 26 Aug 93; bnb diff --git a/frontend/node_modules/katex/src/functions.js b/frontend/node_modules/katex/src/functions.js new file mode 100644 index 0000000..8e14cba --- /dev/null +++ b/frontend/node_modules/katex/src/functions.js @@ -0,0 +1,55 @@ +// @flow +/** Include this to ensure that all functions are defined. */ +import {_functions} from "./defineFunction"; + +const functions = _functions; +export default functions; + +// TODO(kevinb): have functions return an object and call defineFunction with +// that object in this file instead of relying on side-effects. +import "./functions/accent"; +import "./functions/accentunder"; +import "./functions/arrow"; +import "./functions/pmb"; +import "./environments/cd"; +import "./functions/char"; +import "./functions/color"; +import "./functions/cr"; +import "./functions/def"; +import "./functions/delimsizing"; +import "./functions/enclose"; +import "./functions/environment"; +import "./functions/font"; +import "./functions/genfrac"; +import "./functions/horizBrace"; +import "./functions/href"; +import "./functions/hbox"; +import "./functions/html"; +import "./functions/htmlmathml"; +import "./functions/includegraphics"; +import "./functions/kern"; +import "./functions/lap"; +import "./functions/math"; +import "./functions/mathchoice"; +import "./functions/mclass"; +import "./functions/op"; +import "./functions/operatorname"; +import "./functions/ordgroup"; +import "./functions/overline"; +import "./functions/phantom"; +import "./functions/raisebox"; +import "./functions/relax"; +import "./functions/rule"; +import "./functions/sizing"; +import "./functions/smash"; +import "./functions/sqrt"; +import "./functions/styling"; +import "./functions/supsub"; +import "./functions/symbolsOp"; +import "./functions/symbolsOrd"; +import "./functions/symbolsSpacing"; +import "./functions/tag"; +import "./functions/text"; +import "./functions/underline"; +import "./functions/vcenter"; +import "./functions/verb"; diff --git a/frontend/node_modules/katex/src/functions/accent.js b/frontend/node_modules/katex/src/functions/accent.js new file mode 100644 index 0000000..8be7bd7 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/accent.js @@ -0,0 +1,284 @@ +// @flow +import defineFunction, {normalizeArgument} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import utils from "../utils"; +import stretchy from "../stretchy"; +import {assertNodeType} from "../parseNode"; +import {assertSpan, assertSymbolDomNode} from "../domTree"; +import {makeEm} from "../units"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +import type {ParseNode, AnyParseNode} from "../parseNode"; +import type {HtmlBuilderSupSub, MathMLBuilder} from "../defineFunction"; + +// NOTE: Unlike most `htmlBuilder`s, this one handles not only "accent", but +// also "supsub" since an accent can affect super/subscripting. +export const htmlBuilder: HtmlBuilderSupSub<"accent"> = (grp, options) => { + // Accents are handled in the TeXbook pg. 443, rule 12. + let base: AnyParseNode; + let group: ParseNode<"accent">; + + let supSubGroup; + if (grp && grp.type === "supsub") { + // If our base is a character box, and we have superscripts and + // subscripts, the supsub will defer to us. In particular, we want + // to attach the superscripts and subscripts to the inner body (so + // that the position of the superscripts and subscripts won't be + // affected by the height of the accent). We accomplish this by + // sticking the base of the accent into the base of the supsub, and + // rendering that, while keeping track of where the accent is. + + // The real accent group is the base of the supsub group + group = assertNodeType(grp.base, "accent"); + // The character box is the base of the accent group + base = group.base; + // Stick the character box into the base of the supsub group + grp.base = base; + + // Rerender the supsub group with its new base, and store that + // result. + supSubGroup = assertSpan(html.buildGroup(grp, options)); + + // reset original base + grp.base = group; + } else { + group = assertNodeType(grp, "accent"); + base = group.base; + } + + // Build the base group + const body = html.buildGroup(base, options.havingCrampedStyle()); + + // Does the accent need to shift for the skew of a character? + const mustShift = group.isShifty && utils.isCharacterBox(base); + + // Calculate the skew of the accent. This is based on the line "If the + // nucleus is not a single character, let s = 0; otherwise set s to the + // kern amount for the nucleus followed by the \skewchar of its font." + // Note that our skew metrics are just the kern between each character + // and the skewchar. + let skew = 0; + if (mustShift) { + // If the base is a character box, then we want the skew of the + // innermost character. To do that, we find the innermost character: + const baseChar = utils.getBaseElem(base); + // Then, we render its group to get the symbol inside it + const baseGroup = html.buildGroup(baseChar, options.havingCrampedStyle()); + // Finally, we pull the skew off of the symbol. + skew = assertSymbolDomNode(baseGroup).skew; + // Note that we now throw away baseGroup, because the layers we + // removed with getBaseElem might contain things like \color which + // we can't get rid of. + // TODO(emily): Find a better way to get the skew + } + + const accentBelow = group.label === "\\c"; + + // calculate the amount of space between the body and the accent + let clearance = accentBelow + ? body.height + body.depth + : Math.min( + body.height, + options.fontMetrics().xHeight); + + // Build the accent + let accentBody; + if (!group.isStretchy) { + let accent; + let width: number; + if (group.label === "\\vec") { + // Before version 0.9, \vec used the combining font glyph U+20D7. + // But browsers, especially Safari, are not consistent in how they + // render combining characters when not preceded by a character. + // So now we use an SVG. + // If Safari reforms, we should consider reverting to the glyph. + accent = buildCommon.staticSvg("vec", options); + width = buildCommon.svgData.vec[1]; + } else { + accent = buildCommon.makeOrd({mode: group.mode, text: group.label}, + options, "textord"); + accent = assertSymbolDomNode(accent); + // Remove the italic correction of the accent, because it only serves to + // shift the accent over to a place we don't want. + accent.italic = 0; + width = accent.width; + if (accentBelow) { + clearance += accent.depth; + } + } + + accentBody = buildCommon.makeSpan(["accent-body"], [accent]); + + // "Full" accents expand the width of the resulting symbol to be + // at least the width of the accent, and overlap directly onto the + // character without any vertical offset. + const accentFull = (group.label === "\\textcircled"); + if (accentFull) { + accentBody.classes.push('accent-full'); + clearance = body.height; + } + + // Shift the accent over by the skew. + let left = skew; + + // CSS defines `.katex .accent .accent-body:not(.accent-full) { width: 0 }` + // so that the accent doesn't contribute to the bounding box. + // We need to shift the character by its width (effectively half + // its width) to compensate. + if (!accentFull) { + left -= width / 2; + } + + accentBody.style.left = makeEm(left); + + // \textcircled uses the \bigcirc glyph, so it needs some + // vertical adjustment to match LaTeX. + if (group.label === "\\textcircled") { + accentBody.style.top = ".2em"; + } + + accentBody = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [ + {type: "elem", elem: body}, + {type: "kern", size: -clearance}, + {type: "elem", elem: accentBody}, + ], + }, options); + + } else { + accentBody = stretchy.svgSpan(group, options); + + accentBody = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [ + {type: "elem", elem: body}, + { + type: "elem", + elem: accentBody, + wrapperClasses: ["svg-align"], + wrapperStyle: skew > 0 + ? { + width: `calc(100% - ${makeEm(2 * skew)})`, + marginLeft: makeEm(2 * skew), + } + : undefined, + }, + ], + }, options); + } + + const accentWrap = + buildCommon.makeSpan(["mord", "accent"], [accentBody], options); + + if (supSubGroup) { + // Here, we replace the "base" child of the supsub with our newly + // generated accent. + supSubGroup.children[0] = accentWrap; + + // Since we don't rerun the height calculation after replacing the + // accent, we manually recalculate height. + supSubGroup.height = Math.max(accentWrap.height, supSubGroup.height); + + // Accents should always be ords, even when their innards are not. + supSubGroup.classes[0] = "mord"; + + return supSubGroup; + } else { + return accentWrap; + } +}; + +const mathmlBuilder: MathMLBuilder<"accent"> = (group, options) => { + const accentNode = + group.isStretchy ? + stretchy.mathMLnode(group.label) : + new mathMLTree.MathNode("mo", [mml.makeText(group.label, group.mode)]); + + const node = new mathMLTree.MathNode( + "mover", + [mml.buildGroup(group.base, options), accentNode]); + + node.setAttribute("accent", "true"); + + return node; +}; + +const NON_STRETCHY_ACCENT_REGEX = new RegExp([ + "\\acute", "\\grave", "\\ddot", "\\tilde", "\\bar", "\\breve", + "\\check", "\\hat", "\\vec", "\\dot", "\\mathring", +].map(accent => `\\${accent}`).join("|")); + +// Accents +defineFunction({ + type: "accent", + names: [ + "\\acute", "\\grave", "\\ddot", "\\tilde", "\\bar", "\\breve", + "\\check", "\\hat", "\\vec", "\\dot", "\\mathring", "\\widecheck", + "\\widehat", "\\widetilde", "\\overrightarrow", "\\overleftarrow", + "\\Overrightarrow", "\\overleftrightarrow", "\\overgroup", + "\\overlinesegment", "\\overleftharpoon", "\\overrightharpoon", + ], + props: { + numArgs: 1, + }, + handler: (context, args) => { + const base = normalizeArgument(args[0]); + + const isStretchy = !NON_STRETCHY_ACCENT_REGEX.test(context.funcName); + const isShifty = !isStretchy || + context.funcName === "\\widehat" || + context.funcName === "\\widetilde" || + context.funcName === "\\widecheck"; + + return { + type: "accent", + mode: context.parser.mode, + label: context.funcName, + isStretchy: isStretchy, + isShifty: isShifty, + base: base, + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +// Text-mode accents +defineFunction({ + type: "accent", + names: [ + "\\'", "\\`", "\\^", "\\~", "\\=", "\\u", "\\.", '\\"', + "\\c", "\\r", "\\H", "\\v", "\\textcircled", + ], + props: { + numArgs: 1, + allowedInText: true, + allowedInMath: true, // unless in strict mode + argTypes: ["primitive"], + }, + handler: (context, args) => { + const base = args[0]; + let mode = context.parser.mode; + + if (mode === "math") { + context.parser.settings.reportNonstrict("mathVsTextAccents", + `LaTeX's accent ${context.funcName} works only in text mode`); + mode = "text"; + } + + return { + type: "accent", + mode: mode, + label: context.funcName, + isStretchy: false, + isShifty: true, + base: base, + }; + }, + htmlBuilder, + mathmlBuilder, +}); diff --git a/frontend/node_modules/katex/src/functions/accentunder.js b/frontend/node_modules/katex/src/functions/accentunder.js new file mode 100644 index 0000000..3e8c840 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/accentunder.js @@ -0,0 +1,60 @@ +// @flow +// Horizontal overlap functions +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import stretchy from "../stretchy"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +import type {ParseNode} from "../parseNode"; + +defineFunction({ + type: "accentUnder", + names: [ + "\\underleftarrow", "\\underrightarrow", "\\underleftrightarrow", + "\\undergroup", "\\underlinesegment", "\\utilde", + ], + props: { + numArgs: 1, + }, + handler: ({parser, funcName}, args) => { + const base = args[0]; + return { + type: "accentUnder", + mode: parser.mode, + label: funcName, + base: base, + }; + }, + htmlBuilder: (group: ParseNode<"accentUnder">, options) => { + // Treat under accents much like underlines. + const innerGroup = html.buildGroup(group.base, options); + + const accentBody = stretchy.svgSpan(group, options); + const kern = group.label === "\\utilde" ? 0.12 : 0; + + // Generate the vlist, with the appropriate kerns + const vlist = buildCommon.makeVList({ + positionType: "top", + positionData: innerGroup.height, + children: [ + {type: "elem", elem: accentBody, wrapperClasses: ["svg-align"]}, + {type: "kern", size: kern}, + {type: "elem", elem: innerGroup}, + ], + }, options); + + return buildCommon.makeSpan(["mord", "accentunder"], [vlist], options); + }, + mathmlBuilder: (group, options) => { + const accentNode = stretchy.mathMLnode(group.label); + const node = new mathMLTree.MathNode( + "munder", + [mml.buildGroup(group.base, options), accentNode] + ); + node.setAttribute("accentunder", "true"); + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/arrow.js b/frontend/node_modules/katex/src/functions/arrow.js new file mode 100644 index 0000000..88b5b1b --- /dev/null +++ b/frontend/node_modules/katex/src/functions/arrow.js @@ -0,0 +1,144 @@ +// @flow +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import stretchy from "../stretchy"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +import type {ParseNode} from "../parseNode"; + +// Helper function +const paddedNode = group => { + const node = new mathMLTree.MathNode("mpadded", group ? [group] : []); + node.setAttribute("width", "+0.6em"); + node.setAttribute("lspace", "0.3em"); + return node; +}; + +// Stretchy arrows with an optional argument +defineFunction({ + type: "xArrow", + names: [ + "\\xleftarrow", "\\xrightarrow", "\\xLeftarrow", "\\xRightarrow", + "\\xleftrightarrow", "\\xLeftrightarrow", "\\xhookleftarrow", + "\\xhookrightarrow", "\\xmapsto", "\\xrightharpoondown", + "\\xrightharpoonup", "\\xleftharpoondown", "\\xleftharpoonup", + "\\xrightleftharpoons", "\\xleftrightharpoons", "\\xlongequal", + "\\xtwoheadrightarrow", "\\xtwoheadleftarrow", "\\xtofrom", + // The next 3 functions are here to support the mhchem extension. + // Direct use of these functions is discouraged and may break someday. + "\\xrightleftarrows", "\\xrightequilibrium", "\\xleftequilibrium", + // The next 3 functions are here only to support the {CD} environment. + "\\\\cdrightarrow", "\\\\cdleftarrow", "\\\\cdlongequal", + ], + props: { + numArgs: 1, + numOptionalArgs: 1, + }, + handler({parser, funcName}, args, optArgs) { + return { + type: "xArrow", + mode: parser.mode, + label: funcName, + body: args[0], + below: optArgs[0], + }; + }, + // Flow is unable to correctly infer the type of `group`, even though it's + // unambiguously determined from the passed-in `type` above. + htmlBuilder(group: ParseNode<"xArrow">, options) { + const style = options.style; + + // Build the argument groups in the appropriate style. + // Ref: amsmath.dtx: \hbox{$\scriptstyle\mkern#3mu{#6}\mkern#4mu$}% + + // Some groups can return document fragments. Handle those by wrapping + // them in a span. + let newOptions = options.havingStyle(style.sup()); + const upperGroup = buildCommon.wrapFragment( + html.buildGroup(group.body, newOptions, options), options); + const arrowPrefix = group.label.slice(0, 2) === "\\x" ? "x" : "cd"; + upperGroup.classes.push(arrowPrefix + "-arrow-pad"); + + let lowerGroup; + if (group.below) { + // Build the lower group + newOptions = options.havingStyle(style.sub()); + lowerGroup = buildCommon.wrapFragment( + html.buildGroup(group.below, newOptions, options), options); + lowerGroup.classes.push(arrowPrefix + "-arrow-pad"); + } + + const arrowBody = stretchy.svgSpan(group, options); + + // Re shift: Note that stretchy.svgSpan returned arrowBody.depth = 0. + // The point we want on the math axis is at 0.5 * arrowBody.height. + const arrowShift = -options.fontMetrics().axisHeight + + 0.5 * arrowBody.height; + // 2 mu kern. Ref: amsmath.dtx: #7\if0#2\else\mkern#2mu\fi + let upperShift = -options.fontMetrics().axisHeight + - 0.5 * arrowBody.height - 0.111; // 0.111 em = 2 mu + if (upperGroup.depth > 0.25 || group.label === "\\xleftequilibrium") { + upperShift -= upperGroup.depth; // shift up if depth encroaches + } + + // Generate the vlist + let vlist; + if (lowerGroup) { + const lowerShift = -options.fontMetrics().axisHeight + + lowerGroup.height + 0.5 * arrowBody.height + + 0.111; + vlist = buildCommon.makeVList({ + positionType: "individualShift", + children: [ + {type: "elem", elem: upperGroup, shift: upperShift}, + {type: "elem", elem: arrowBody, shift: arrowShift}, + {type: "elem", elem: lowerGroup, shift: lowerShift}, + ], + }, options); + } else { + vlist = buildCommon.makeVList({ + positionType: "individualShift", + children: [ + {type: "elem", elem: upperGroup, shift: upperShift}, + {type: "elem", elem: arrowBody, shift: arrowShift}, + ], + }, options); + } + + // $FlowFixMe: Replace this with passing "svg-align" into makeVList. + vlist.children[0].children[0].children[1].classes.push("svg-align"); + + return buildCommon.makeSpan(["mrel", "x-arrow"], [vlist], options); + }, + mathmlBuilder(group, options) { + const arrowNode = stretchy.mathMLnode(group.label); + arrowNode.setAttribute( + "minsize", group.label.charAt(0) === "x" ? "1.75em" : "3.0em" + ); + let node; + + if (group.body) { + const upperNode = paddedNode(mml.buildGroup(group.body, options)); + if (group.below) { + const lowerNode = paddedNode(mml.buildGroup(group.below, options)); + node = new mathMLTree.MathNode( + "munderover", [arrowNode, lowerNode, upperNode] + ); + } else { + node = new mathMLTree.MathNode("mover", [arrowNode, upperNode]); + } + } else if (group.below) { + const lowerNode = paddedNode(mml.buildGroup(group.below, options)); + node = new mathMLTree.MathNode("munder", [arrowNode, lowerNode]); + } else { + // This should never happen. + // Parser.js throws an error if there is no argument. + node = paddedNode(); + node = new mathMLTree.MathNode("mover", [arrowNode, node]); + } + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/char.js b/frontend/node_modules/katex/src/functions/char.js new file mode 100644 index 0000000..1600ffb --- /dev/null +++ b/frontend/node_modules/katex/src/functions/char.js @@ -0,0 +1,45 @@ +// @flow +import defineFunction from "../defineFunction"; +import ParseError from "../ParseError"; +import {assertNodeType} from "../parseNode"; + +// \@char is an internal function that takes a grouped decimal argument like +// {123} and converts into symbol with code 123. It is used by the *macro* +// \char defined in macros.js. +defineFunction({ + type: "textord", + names: ["\\@char"], + props: { + numArgs: 1, + allowedInText: true, + }, + handler({parser}, args) { + const arg = assertNodeType(args[0], "ordgroup"); + const group = arg.body; + let number = ""; + for (let i = 0; i < group.length; i++) { + const node = assertNodeType(group[i], "textord"); + number += node.text; + } + let code = parseInt(number); + let text; + if (isNaN(code)) { + throw new ParseError(`\\@char has non-numeric argument ${number}`); + // If we drop IE support, the following code could be replaced with + // text = String.fromCodePoint(code) + } else if (code < 0 || code >= 0x10ffff) { + throw new ParseError(`\\@char with invalid code point ${number}`); + } else if (code <= 0xffff) { + text = String.fromCharCode(code); + } else { // Astral code point; split into surrogate halves + code -= 0x10000; + text = String.fromCharCode((code >> 10) + 0xd800, + (code & 0x3ff) + 0xdc00); + } + return { + type: "textord", + mode: parser.mode, + text: text, + }; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/color.js b/frontend/node_modules/katex/src/functions/color.js new file mode 100644 index 0000000..ad65838 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/color.js @@ -0,0 +1,88 @@ +// @flow +import defineFunction, {ordargument} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import {assertNodeType} from "../parseNode"; + +import type {AnyParseNode} from '../parseNode'; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +const htmlBuilder = (group, options) => { + const elements = html.buildExpression( + group.body, + options.withColor(group.color), + false + ); + + // \color isn't supposed to affect the type of the elements it contains. + // To accomplish this, we wrap the results in a fragment, so the inner + // elements will be able to directly interact with their neighbors. For + // example, `\color{red}{2 +} 3` has the same spacing as `2 + 3` + return buildCommon.makeFragment(elements); +}; + +const mathmlBuilder = (group, options) => { + const inner = mml.buildExpression(group.body, + options.withColor(group.color)); + + const node = new mathMLTree.MathNode("mstyle", inner); + + node.setAttribute("mathcolor", group.color); + + return node; +}; + +defineFunction({ + type: "color", + names: ["\\textcolor"], + props: { + numArgs: 2, + allowedInText: true, + argTypes: ["color", "original"], + }, + handler({parser}, args) { + const color = assertNodeType(args[0], "color-token").color; + const body = args[1]; + return { + type: "color", + mode: parser.mode, + color, + body: (ordargument(body): AnyParseNode[]), + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +defineFunction({ + type: "color", + names: ["\\color"], + props: { + numArgs: 1, + allowedInText: true, + argTypes: ["color"], + }, + handler({parser, breakOnTokenText}, args) { + const color = assertNodeType(args[0], "color-token").color; + + // Set macro \current@color in current namespace to store the current + // color, mimicking the behavior of color.sty. + // This is currently used just to correctly color a \right + // that follows a \color command. + parser.gullet.macros.set("\\current@color", color); + + // Parse out the implicit body that should be colored. + const body: AnyParseNode[] = parser.parseExpression(true, breakOnTokenText); + + return { + type: "color", + mode: parser.mode, + color, + body, + }; + }, + htmlBuilder, + mathmlBuilder, +}); diff --git a/frontend/node_modules/katex/src/functions/cr.js b/frontend/node_modules/katex/src/functions/cr.js new file mode 100644 index 0000000..bf25f26 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/cr.js @@ -0,0 +1,61 @@ +//@flow +// Row breaks within tabular environments, and line breaks at top level + +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import {calculateSize, makeEm} from "../units"; +import {assertNodeType} from "../parseNode"; + +// \DeclareRobustCommand\\{...\@xnewline} +defineFunction({ + type: "cr", + names: ["\\\\"], + props: { + numArgs: 0, + numOptionalArgs: 0, + allowedInText: true, + }, + + handler({parser}, args, optArgs) { + const size = parser.gullet.future().text === "[" ? + parser.parseSizeGroup(true) : null; + const newLine = !parser.settings.displayMode || + !parser.settings.useStrictBehavior( + "newLineInDisplayMode", "In LaTeX, \\\\ or \\newline " + + "does nothing in display mode"); + return { + type: "cr", + mode: parser.mode, + newLine, + size: size && assertNodeType(size, "size").value, + }; + }, + + // The following builders are called only at the top level, + // not within tabular/array environments. + + htmlBuilder(group, options) { + const span = buildCommon.makeSpan(["mspace"], [], options); + if (group.newLine) { + span.classes.push("newline"); + if (group.size) { + span.style.marginTop = + makeEm(calculateSize(group.size, options)); + } + } + return span; + }, + + mathmlBuilder(group, options) { + const node = new mathMLTree.MathNode("mspace"); + if (group.newLine) { + node.setAttribute("linebreak", "newline"); + if (group.size) { + node.setAttribute("height", + makeEm(calculateSize(group.size, options))); + } + } + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/def.js b/frontend/node_modules/katex/src/functions/def.js new file mode 100644 index 0000000..2717a64 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/def.js @@ -0,0 +1,210 @@ +//@flow +import defineFunction from "../defineFunction"; +import ParseError from "../ParseError"; +import {assertNodeType} from "../parseNode"; + +const globalMap = { + "\\global": "\\global", + "\\long": "\\\\globallong", + "\\\\globallong": "\\\\globallong", + "\\def": "\\gdef", + "\\gdef": "\\gdef", + "\\edef": "\\xdef", + "\\xdef": "\\xdef", + "\\let": "\\\\globallet", + "\\futurelet": "\\\\globalfuture", +}; + +const checkControlSequence = (tok) => { + const name = tok.text; + if (/^(?:[\\{}$&#^_]|EOF)$/.test(name)) { + throw new ParseError("Expected a control sequence", tok); + } + return name; +}; + +const getRHS = (parser) => { + let tok = parser.gullet.popToken(); + if (tok.text === "=") { // consume optional equals + tok = parser.gullet.popToken(); + if (tok.text === " ") { // consume one optional space + tok = parser.gullet.popToken(); + } + } + return tok; +}; + +const letCommand = (parser, name, tok, global) => { + let macro = parser.gullet.macros.get(tok.text); + if (macro == null) { + // don't expand it later even if a macro with the same name is defined + // e.g., \let\foo=\frac \def\frac{\relax} \frac12 + tok.noexpand = true; + macro = { + tokens: [tok], + numArgs: 0, + // reproduce the same behavior in expansion + unexpandable: !parser.gullet.isExpandable(tok.text), + }; + } + parser.gullet.macros.set(name, macro, global); +}; + +// -> | +// -> |\global +// -> | +// -> \global|\long|\outer +defineFunction({ + type: "internal", + names: [ + "\\global", "\\long", + "\\\\globallong", // can’t be entered directly + ], + props: { + numArgs: 0, + allowedInText: true, + }, + handler({parser, funcName}) { + parser.consumeSpaces(); + const token = parser.fetch(); + if (globalMap[token.text]) { + // KaTeX doesn't have \par, so ignore \long + if (funcName === "\\global" || funcName === "\\\\globallong") { + token.text = globalMap[token.text]; + } + return assertNodeType(parser.parseFunction(), "internal"); + } + throw new ParseError(`Invalid token after macro prefix`, token); + }, +}); + +// Basic support for macro definitions: \def, \gdef, \edef, \xdef +// -> +// -> \def|\gdef|\edef|\xdef +// -> +defineFunction({ + type: "internal", + names: ["\\def", "\\gdef", "\\edef", "\\xdef"], + props: { + numArgs: 0, + allowedInText: true, + primitive: true, + }, + handler({parser, funcName}) { + let tok = parser.gullet.popToken(); + const name = tok.text; + if (/^(?:[\\{}$&#^_]|EOF)$/.test(name)) { + throw new ParseError("Expected a control sequence", tok); + } + + let numArgs = 0; + let insert; + const delimiters = [[]]; + // contains no braces + while (parser.gullet.future().text !== "{") { + tok = parser.gullet.popToken(); + if (tok.text === "#") { + // If the very last character of the is #, so that + // this # is immediately followed by {, TeX will behave as if the { + // had been inserted at the right end of both the parameter text + // and the replacement text. + if (parser.gullet.future().text === "{") { + insert = parser.gullet.future(); + delimiters[numArgs].push("{"); + break; + } + + // A parameter, the first appearance of # must be followed by 1, + // the next by 2, and so on; up to nine #’s are allowed + tok = parser.gullet.popToken(); + if (!(/^[1-9]$/.test(tok.text))) { + throw new ParseError(`Invalid argument number "${tok.text}"`); + } + if (parseInt(tok.text) !== numArgs + 1) { + throw new ParseError( + `Argument number "${tok.text}" out of order`); + } + numArgs++; + delimiters.push([]); + } else if (tok.text === "EOF") { + throw new ParseError("Expected a macro definition"); + } else { + delimiters[numArgs].push(tok.text); + } + } + // replacement text, enclosed in '{' and '}' and properly nested + let {tokens} = parser.gullet.consumeArg(); + if (insert) { + tokens.unshift(insert); + } + + if (funcName === "\\edef" || funcName === "\\xdef") { + tokens = parser.gullet.expandTokens(tokens); + tokens.reverse(); // to fit in with stack order + } + // Final arg is the expansion of the macro + parser.gullet.macros.set(name, { + tokens, + numArgs, + delimiters, + }, funcName === globalMap[funcName]); + + return { + type: "internal", + mode: parser.mode, + }; + }, +}); + +// -> +// -> \futurelet +// | \let +// -> |= +defineFunction({ + type: "internal", + names: [ + "\\let", + "\\\\globallet", // can’t be entered directly + ], + props: { + numArgs: 0, + allowedInText: true, + primitive: true, + }, + handler({parser, funcName}) { + const name = checkControlSequence(parser.gullet.popToken()); + parser.gullet.consumeSpaces(); + const tok = getRHS(parser); + letCommand(parser, name, tok, funcName === "\\\\globallet"); + return { + type: "internal", + mode: parser.mode, + }; + }, +}); + +// ref: https://www.tug.org/TUGboat/tb09-3/tb22bechtolsheim.pdf +defineFunction({ + type: "internal", + names: [ + "\\futurelet", + "\\\\globalfuture", // can’t be entered directly + ], + props: { + numArgs: 0, + allowedInText: true, + primitive: true, + }, + handler({parser, funcName}) { + const name = checkControlSequence(parser.gullet.popToken()); + const middle = parser.gullet.popToken(); + const tok = parser.gullet.popToken(); + letCommand(parser, name, tok, funcName === "\\\\globalfuture"); + parser.gullet.pushToken(tok); + parser.gullet.pushToken(middle); + return { + type: "internal", + mode: parser.mode, + }; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/delimsizing.js b/frontend/node_modules/katex/src/functions/delimsizing.js new file mode 100644 index 0000000..4d1be97 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/delimsizing.js @@ -0,0 +1,360 @@ +// @flow +import buildCommon from "../buildCommon"; +import defineFunction from "../defineFunction"; +import delimiter from "../delimiter"; +import mathMLTree from "../mathMLTree"; +import ParseError from "../ParseError"; +import utils from "../utils"; +import {assertNodeType, checkSymbolNodeType} from "../parseNode"; +import {makeEm} from "../units"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +import type Options from "../Options"; +import type {AnyParseNode, ParseNode, SymbolParseNode} from "../parseNode"; +import type {FunctionContext} from "../defineFunction"; + +// Extra data needed for the delimiter handler down below +const delimiterSizes = { + "\\bigl" : {mclass: "mopen", size: 1}, + "\\Bigl" : {mclass: "mopen", size: 2}, + "\\biggl": {mclass: "mopen", size: 3}, + "\\Biggl": {mclass: "mopen", size: 4}, + "\\bigr" : {mclass: "mclose", size: 1}, + "\\Bigr" : {mclass: "mclose", size: 2}, + "\\biggr": {mclass: "mclose", size: 3}, + "\\Biggr": {mclass: "mclose", size: 4}, + "\\bigm" : {mclass: "mrel", size: 1}, + "\\Bigm" : {mclass: "mrel", size: 2}, + "\\biggm": {mclass: "mrel", size: 3}, + "\\Biggm": {mclass: "mrel", size: 4}, + "\\big" : {mclass: "mord", size: 1}, + "\\Big" : {mclass: "mord", size: 2}, + "\\bigg" : {mclass: "mord", size: 3}, + "\\Bigg" : {mclass: "mord", size: 4}, +}; + +const delimiters = [ + "(", "\\lparen", ")", "\\rparen", + "[", "\\lbrack", "]", "\\rbrack", + "\\{", "\\lbrace", "\\}", "\\rbrace", + "\\lfloor", "\\rfloor", "\u230a", "\u230b", + "\\lceil", "\\rceil", "\u2308", "\u2309", + "<", ">", "\\langle", "\u27e8", "\\rangle", "\u27e9", "\\lt", "\\gt", + "\\lvert", "\\rvert", "\\lVert", "\\rVert", + "\\lgroup", "\\rgroup", "\u27ee", "\u27ef", + "\\lmoustache", "\\rmoustache", "\u23b0", "\u23b1", + "/", "\\backslash", + "|", "\\vert", "\\|", "\\Vert", + "\\uparrow", "\\Uparrow", + "\\downarrow", "\\Downarrow", + "\\updownarrow", "\\Updownarrow", + ".", +]; + +type IsMiddle = {delim: string, options: Options}; + +// Delimiter functions +function checkDelimiter( + delim: AnyParseNode, + context: FunctionContext, +): SymbolParseNode { + const symDelim = checkSymbolNodeType(delim); + if (symDelim && utils.contains(delimiters, symDelim.text)) { + return symDelim; + } else if (symDelim) { + throw new ParseError( + `Invalid delimiter '${symDelim.text}' after '${context.funcName}'`, + delim); + } else { + throw new ParseError(`Invalid delimiter type '${delim.type}'`, delim); + } +} + +defineFunction({ + type: "delimsizing", + names: [ + "\\bigl", "\\Bigl", "\\biggl", "\\Biggl", + "\\bigr", "\\Bigr", "\\biggr", "\\Biggr", + "\\bigm", "\\Bigm", "\\biggm", "\\Biggm", + "\\big", "\\Big", "\\bigg", "\\Bigg", + ], + props: { + numArgs: 1, + argTypes: ["primitive"], + }, + handler: (context, args) => { + const delim = checkDelimiter(args[0], context); + + return { + type: "delimsizing", + mode: context.parser.mode, + size: delimiterSizes[context.funcName].size, + mclass: delimiterSizes[context.funcName].mclass, + delim: delim.text, + }; + }, + htmlBuilder: (group, options) => { + if (group.delim === ".") { + // Empty delimiters still count as elements, even though they don't + // show anything. + return buildCommon.makeSpan([group.mclass]); + } + + // Use delimiter.sizedDelim to generate the delimiter. + return delimiter.sizedDelim( + group.delim, group.size, options, group.mode, [group.mclass]); + }, + mathmlBuilder: (group) => { + const children = []; + + if (group.delim !== ".") { + children.push(mml.makeText(group.delim, group.mode)); + } + + const node = new mathMLTree.MathNode("mo", children); + + if (group.mclass === "mopen" || + group.mclass === "mclose") { + // Only some of the delimsizing functions act as fences, and they + // return "mopen" or "mclose" mclass. + node.setAttribute("fence", "true"); + } else { + // Explicitly disable fencing if it's not a fence, to override the + // defaults. + node.setAttribute("fence", "false"); + } + + node.setAttribute("stretchy", "true"); + const size = makeEm(delimiter.sizeToMaxHeight[group.size]); + node.setAttribute("minsize", size); + node.setAttribute("maxsize", size); + + return node; + }, +}); + + +function assertParsed(group: ParseNode<"leftright">) { + if (!group.body) { + throw new Error("Bug: The leftright ParseNode wasn't fully parsed."); + } +} + + +defineFunction({ + type: "leftright-right", + names: ["\\right"], + props: { + numArgs: 1, + primitive: true, + }, + handler: (context, args) => { + // \left case below triggers parsing of \right in + // `const right = parser.parseFunction();` + // uses this return value. + const color = context.parser.gullet.macros.get("\\current@color"); + if (color && typeof color !== "string") { + throw new ParseError( + "\\current@color set to non-string in \\right"); + } + return { + type: "leftright-right", + mode: context.parser.mode, + delim: checkDelimiter(args[0], context).text, + color, // undefined if not set via \color + }; + }, +}); + + +defineFunction({ + type: "leftright", + names: ["\\left"], + props: { + numArgs: 1, + primitive: true, + }, + handler: (context, args) => { + const delim = checkDelimiter(args[0], context); + + const parser = context.parser; + // Parse out the implicit body + ++parser.leftrightDepth; + // parseExpression stops before '\\right' + const body = parser.parseExpression(false); + --parser.leftrightDepth; + // Check the next token + parser.expect("\\right", false); + const right = assertNodeType(parser.parseFunction(), "leftright-right"); + return { + type: "leftright", + mode: parser.mode, + body, + left: delim.text, + right: right.delim, + rightColor: right.color, + }; + }, + htmlBuilder: (group, options) => { + assertParsed(group); + // Build the inner expression + const inner = html.buildExpression(group.body, options, true, + ["mopen", "mclose"]); + + let innerHeight = 0; + let innerDepth = 0; + let hadMiddle = false; + + // Calculate its height and depth + for (let i = 0; i < inner.length; i++) { + // Property `isMiddle` not defined on `span`. See comment in + // "middle"'s htmlBuilder. + // $FlowFixMe + if (inner[i].isMiddle) { + hadMiddle = true; + } else { + innerHeight = Math.max(inner[i].height, innerHeight); + innerDepth = Math.max(inner[i].depth, innerDepth); + } + } + + // The size of delimiters is the same, regardless of what style we are + // in. Thus, to correctly calculate the size of delimiter we need around + // a group, we scale down the inner size based on the size. + innerHeight *= options.sizeMultiplier; + innerDepth *= options.sizeMultiplier; + + let leftDelim; + if (group.left === ".") { + // Empty delimiters in \left and \right make null delimiter spaces. + leftDelim = html.makeNullDelimiter(options, ["mopen"]); + } else { + // Otherwise, use leftRightDelim to generate the correct sized + // delimiter. + leftDelim = delimiter.leftRightDelim( + group.left, innerHeight, innerDepth, options, + group.mode, ["mopen"]); + } + // Add it to the beginning of the expression + inner.unshift(leftDelim); + + // Handle middle delimiters + if (hadMiddle) { + for (let i = 1; i < inner.length; i++) { + const middleDelim = inner[i]; + // Property `isMiddle` not defined on `span`. See comment in + // "middle"'s htmlBuilder. + // $FlowFixMe + const isMiddle: IsMiddle = middleDelim.isMiddle; + if (isMiddle) { + // Apply the options that were active when \middle was called + inner[i] = delimiter.leftRightDelim( + isMiddle.delim, innerHeight, innerDepth, + isMiddle.options, group.mode, []); + } + } + } + + let rightDelim; + // Same for the right delimiter, but using color specified by \color + if (group.right === ".") { + rightDelim = html.makeNullDelimiter(options, ["mclose"]); + } else { + const colorOptions = group.rightColor ? + options.withColor(group.rightColor) : options; + rightDelim = delimiter.leftRightDelim( + group.right, innerHeight, innerDepth, colorOptions, + group.mode, ["mclose"]); + } + // Add it to the end of the expression. + inner.push(rightDelim); + + return buildCommon.makeSpan(["minner"], inner, options); + }, + mathmlBuilder: (group, options) => { + assertParsed(group); + const inner = mml.buildExpression(group.body, options); + + if (group.left !== ".") { + const leftNode = new mathMLTree.MathNode( + "mo", [mml.makeText(group.left, group.mode)]); + + leftNode.setAttribute("fence", "true"); + + inner.unshift(leftNode); + } + + if (group.right !== ".") { + const rightNode = new mathMLTree.MathNode( + "mo", [mml.makeText(group.right, group.mode)]); + + rightNode.setAttribute("fence", "true"); + + if (group.rightColor) { + rightNode.setAttribute("mathcolor", group.rightColor); + } + + inner.push(rightNode); + } + + return mml.makeRow(inner); + }, +}); + +defineFunction({ + type: "middle", + names: ["\\middle"], + props: { + numArgs: 1, + primitive: true, + }, + handler: (context, args) => { + const delim = checkDelimiter(args[0], context); + if (!context.parser.leftrightDepth) { + throw new ParseError("\\middle without preceding \\left", delim); + } + + return { + type: "middle", + mode: context.parser.mode, + delim: delim.text, + }; + }, + htmlBuilder: (group, options) => { + let middleDelim; + if (group.delim === ".") { + middleDelim = html.makeNullDelimiter(options, []); + } else { + middleDelim = delimiter.sizedDelim( + group.delim, 1, options, + group.mode, []); + + const isMiddle: IsMiddle = {delim: group.delim, options}; + // Property `isMiddle` not defined on `span`. It is only used in + // this file above. + // TODO: Fix this violation of the `span` type and possibly rename + // things since `isMiddle` sounds like a boolean, but is a struct. + // $FlowFixMe + middleDelim.isMiddle = isMiddle; + } + return middleDelim; + }, + mathmlBuilder: (group, options) => { + // A Firefox \middle will stretch a character vertically only if it + // is in the fence part of the operator dictionary at: + // https://www.w3.org/TR/MathML3/appendixc.html. + // So we need to avoid U+2223 and use plain "|" instead. + const textNode = (group.delim === "\\vert" || group.delim === "|") + ? mml.makeText("|", "text") + : mml.makeText(group.delim, group.mode); + const middleNode = new mathMLTree.MathNode("mo", [textNode]); + middleNode.setAttribute("fence", "true"); + // MathML gives 5/18em spacing to each element. + // \middle should get delimiter spacing instead. + middleNode.setAttribute("lspace", "0.05em"); + middleNode.setAttribute("rspace", "0.05em"); + return middleNode; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/enclose.js b/frontend/node_modules/katex/src/functions/enclose.js new file mode 100644 index 0000000..eb586f8 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/enclose.js @@ -0,0 +1,323 @@ +// @flow +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import utils from "../utils"; +import stretchy from "../stretchy"; +import {phasePath} from "../svgGeometry"; +import {PathNode, SvgNode} from "../domTree"; +import {calculateSize, makeEm} from "../units"; +import {assertNodeType} from "../parseNode"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + + +const htmlBuilder = (group, options) => { + // \cancel, \bcancel, \xcancel, \sout, \fbox, \colorbox, \fcolorbox, \phase + // Some groups can return document fragments. Handle those by wrapping + // them in a span. + const inner = buildCommon.wrapFragment( + html.buildGroup(group.body, options), options); + + const label = group.label.slice(1); + let scale = options.sizeMultiplier; + let img; + let imgShift = 0; + + // In the LaTeX cancel package, line geometry is slightly different + // depending on whether the subject is wider than it is tall, or vice versa. + // We don't know the width of a group, so as a proxy, we test if + // the subject is a single character. This captures most of the + // subjects that should get the "tall" treatment. + const isSingleChar = utils.isCharacterBox(group.body); + + if (label === "sout") { + img = buildCommon.makeSpan(["stretchy", "sout"]); + img.height = options.fontMetrics().defaultRuleThickness / scale; + imgShift = -0.5 * options.fontMetrics().xHeight; + + } else if (label === "phase") { + // Set a couple of dimensions from the steinmetz package. + const lineWeight = calculateSize({number: 0.6, unit: "pt"}, options); + const clearance = calculateSize({number: 0.35, unit: "ex"}, options); + + // Prevent size changes like \Huge from affecting line thickness + const newOptions = options.havingBaseSizing(); + scale = scale / newOptions.sizeMultiplier; + + const angleHeight = inner.height + inner.depth + lineWeight + clearance; + // Reserve a left pad for the angle. + inner.style.paddingLeft = makeEm(angleHeight / 2 + lineWeight); + + // Create an SVG + const viewBoxHeight = Math.floor(1000 * angleHeight * scale); + const path = phasePath(viewBoxHeight); + const svgNode = new SvgNode([new PathNode("phase", path)], { + "width": "400em", + "height": makeEm(viewBoxHeight / 1000), + "viewBox": `0 0 400000 ${viewBoxHeight}`, + "preserveAspectRatio": "xMinYMin slice", + }); + // Wrap it in a span with overflow: hidden. + img = buildCommon.makeSvgSpan(["hide-tail"], [svgNode], options); + img.style.height = makeEm(angleHeight); + imgShift = inner.depth + lineWeight + clearance; + + } else { + // Add horizontal padding + if (/cancel/.test(label)) { + if (!isSingleChar) { + inner.classes.push("cancel-pad"); + } + } else if (label === "angl") { + inner.classes.push("anglpad"); + } else { + inner.classes.push("boxpad"); + } + + // Add vertical padding + let topPad = 0; + let bottomPad = 0; + let ruleThickness = 0; + // ref: cancel package: \advance\totalheight2\p@ % "+2" + if (/box/.test(label)) { + ruleThickness = Math.max( + options.fontMetrics().fboxrule, // default + options.minRuleThickness, // User override. + ); + topPad = options.fontMetrics().fboxsep + + (label === "colorbox" ? 0 : ruleThickness); + bottomPad = topPad; + } else if (label === "angl") { + ruleThickness = Math.max( + options.fontMetrics().defaultRuleThickness, + options.minRuleThickness + ); + topPad = 4 * ruleThickness; // gap = 3 × line, plus the line itself. + bottomPad = Math.max(0, 0.25 - inner.depth); + } else { + topPad = isSingleChar ? 0.2 : 0; + bottomPad = topPad; + } + + img = stretchy.encloseSpan(inner, label, topPad, bottomPad, options); + if (/fbox|boxed|fcolorbox/.test(label)) { + img.style.borderStyle = "solid"; + img.style.borderWidth = makeEm(ruleThickness); + } else if (label === "angl" && ruleThickness !== 0.049) { + img.style.borderTopWidth = makeEm(ruleThickness); + img.style.borderRightWidth = makeEm(ruleThickness); + } + imgShift = inner.depth + bottomPad; + + if (group.backgroundColor) { + img.style.backgroundColor = group.backgroundColor; + if (group.borderColor) { + img.style.borderColor = group.borderColor; + } + } + } + + let vlist; + if (group.backgroundColor) { + vlist = buildCommon.makeVList({ + positionType: "individualShift", + children: [ + // Put the color background behind inner; + {type: "elem", elem: img, shift: imgShift}, + {type: "elem", elem: inner, shift: 0}, + ], + }, options); + } else { + const classes = /cancel|phase/.test(label) ? ["svg-align"] : []; + vlist = buildCommon.makeVList({ + positionType: "individualShift", + children: [ + // Write the \cancel stroke on top of inner. + { + type: "elem", + elem: inner, + shift: 0, + }, + { + type: "elem", + elem: img, + shift: imgShift, + wrapperClasses: classes, + }, + ], + }, options); + } + + if (/cancel/.test(label)) { + // The cancel package documentation says that cancel lines add their height + // to the expression, but tests show that isn't how it actually works. + vlist.height = inner.height; + vlist.depth = inner.depth; + } + + if (/cancel/.test(label) && !isSingleChar) { + // cancel does not create horiz space for its line extension. + return buildCommon.makeSpan(["mord", "cancel-lap"], [vlist], options); + } else { + return buildCommon.makeSpan(["mord"], [vlist], options); + } +}; + +const mathmlBuilder = (group, options) => { + let fboxsep = 0; + const node = new mathMLTree.MathNode( + (group.label.indexOf("colorbox") > -1) ? "mpadded" : "menclose", + [mml.buildGroup(group.body, options)] + ); + switch (group.label) { + case "\\cancel": + node.setAttribute("notation", "updiagonalstrike"); + break; + case "\\bcancel": + node.setAttribute("notation", "downdiagonalstrike"); + break; + case "\\phase": + node.setAttribute("notation", "phasorangle"); + break; + case "\\sout": + node.setAttribute("notation", "horizontalstrike"); + break; + case "\\fbox": + node.setAttribute("notation", "box"); + break; + case "\\angl": + node.setAttribute("notation", "actuarial"); + break; + case "\\fcolorbox": + case "\\colorbox": + // doesn't have a good notation option. So use + // instead. Set some attributes that come included with . + fboxsep = options.fontMetrics().fboxsep * + options.fontMetrics().ptPerEm; + node.setAttribute("width", `+${2 * fboxsep}pt`); + node.setAttribute("height", `+${2 * fboxsep}pt`); + node.setAttribute("lspace", `${fboxsep}pt`); // + node.setAttribute("voffset", `${fboxsep}pt`); + if (group.label === "\\fcolorbox") { + const thk = Math.max( + options.fontMetrics().fboxrule, // default + options.minRuleThickness, // user override + ); + node.setAttribute("style", "border: " + thk + "em solid " + + String(group.borderColor)); + } + break; + case "\\xcancel": + node.setAttribute("notation", "updiagonalstrike downdiagonalstrike"); + break; + } + if (group.backgroundColor) { + node.setAttribute("mathbackground", group.backgroundColor); + } + return node; +}; + +defineFunction({ + type: "enclose", + names: ["\\colorbox"], + props: { + numArgs: 2, + allowedInText: true, + argTypes: ["color", "text"], + }, + handler({parser, funcName}, args, optArgs) { + const color = assertNodeType(args[0], "color-token").color; + const body = args[1]; + return { + type: "enclose", + mode: parser.mode, + label: funcName, + backgroundColor: color, + body, + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +defineFunction({ + type: "enclose", + names: ["\\fcolorbox"], + props: { + numArgs: 3, + allowedInText: true, + argTypes: ["color", "color", "text"], + }, + handler({parser, funcName}, args, optArgs) { + const borderColor = assertNodeType(args[0], "color-token").color; + const backgroundColor = assertNodeType(args[1], "color-token").color; + const body = args[2]; + return { + type: "enclose", + mode: parser.mode, + label: funcName, + backgroundColor, + borderColor, + body, + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +defineFunction({ + type: "enclose", + names: ["\\fbox"], + props: { + numArgs: 1, + argTypes: ["hbox"], + allowedInText: true, + }, + handler({parser}, args) { + return { + type: "enclose", + mode: parser.mode, + label: "\\fbox", + body: args[0], + }; + }, +}); + +defineFunction({ + type: "enclose", + names: ["\\cancel", "\\bcancel", "\\xcancel", "\\sout", "\\phase"], + props: { + numArgs: 1, + }, + handler({parser, funcName}, args) { + const body = args[0]; + return { + type: "enclose", + mode: parser.mode, + label: funcName, + body, + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +defineFunction({ + type: "enclose", + names: ["\\angl"], + props: { + numArgs: 1, + argTypes: ["hbox"], + allowedInText: false, + }, + handler({parser}, args) { + return { + type: "enclose", + mode: parser.mode, + label: "\\angl", + body: args[0], + }; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/environment.js b/frontend/node_modules/katex/src/functions/environment.js new file mode 100644 index 0000000..192d4db --- /dev/null +++ b/frontend/node_modules/katex/src/functions/environment.js @@ -0,0 +1,62 @@ +// @flow +import defineFunction from "../defineFunction"; +import ParseError from "../ParseError"; +import {assertNodeType} from "../parseNode"; +import environments from "../environments"; + +// Environment delimiters. HTML/MathML rendering is defined in the corresponding +// defineEnvironment definitions. +defineFunction({ + type: "environment", + names: ["\\begin", "\\end"], + props: { + numArgs: 1, + argTypes: ["text"], + }, + handler({parser, funcName}, args) { + const nameGroup = args[0]; + if (nameGroup.type !== "ordgroup") { + throw new ParseError("Invalid environment name", nameGroup); + } + let envName = ""; + for (let i = 0; i < nameGroup.body.length; ++i) { + envName += assertNodeType(nameGroup.body[i], "textord").text; + } + + if (funcName === "\\begin") { + // begin...end is similar to left...right + if (!environments.hasOwnProperty(envName)) { + throw new ParseError( + "No such environment: " + envName, nameGroup); + } + // Build the environment object. Arguments and other information will + // be made available to the begin and end methods using properties. + const env = environments[envName]; + const {args, optArgs} = + parser.parseArguments("\\begin{" + envName + "}", env); + const context = { + mode: parser.mode, + envName, + parser, + }; + const result = env.handler(context, args, optArgs); + parser.expect("\\end", false); + const endNameToken = parser.nextToken; + const end = assertNodeType(parser.parseFunction(), "environment"); + if (end.name !== envName) { + throw new ParseError( + `Mismatch: \\begin{${envName}} matched by \\end{${end.name}}`, + endNameToken); + } + // $FlowFixMe, "environment" handler returns an environment ParseNode + return result; + } + + return { + type: "environment", + mode: parser.mode, + name: envName, + nameGroup, + }; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/font.js b/frontend/node_modules/katex/src/functions/font.js new file mode 100644 index 0000000..bdc0e7d --- /dev/null +++ b/frontend/node_modules/katex/src/functions/font.js @@ -0,0 +1,120 @@ +// @flow +// TODO(kevinb): implement \\sl and \\sc + +import {binrelClass} from "./mclass"; +import defineFunction, {normalizeArgument} from "../defineFunction"; +import utils from "../utils"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +import type {ParseNode} from "../parseNode"; + +const htmlBuilder = (group: ParseNode<"font">, options) => { + const font = group.font; + const newOptions = options.withFont(font); + return html.buildGroup(group.body, newOptions); +}; + +const mathmlBuilder = (group: ParseNode<"font">, options) => { + const font = group.font; + const newOptions = options.withFont(font); + return mml.buildGroup(group.body, newOptions); +}; + +const fontAliases = { + "\\Bbb": "\\mathbb", + "\\bold": "\\mathbf", + "\\frak": "\\mathfrak", + "\\bm": "\\boldsymbol", +}; + +defineFunction({ + type: "font", + names: [ + // styles, except \boldsymbol defined below + "\\mathrm", "\\mathit", "\\mathbf", "\\mathnormal", "\\mathsfit", + + // families + "\\mathbb", "\\mathcal", "\\mathfrak", "\\mathscr", "\\mathsf", + "\\mathtt", + + // aliases, except \bm defined below + "\\Bbb", "\\bold", "\\frak", + ], + props: { + numArgs: 1, + allowedInArgument: true, + }, + handler: ({parser, funcName}, args) => { + const body = normalizeArgument(args[0]); + let func = funcName; + if (func in fontAliases) { + func = fontAliases[func]; + } + return { + type: "font", + mode: parser.mode, + font: func.slice(1), + body, + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +defineFunction({ + type: "mclass", + names: ["\\boldsymbol", "\\bm"], + props: { + numArgs: 1, + }, + handler: ({parser}, args) => { + const body = args[0]; + const isCharacterBox = utils.isCharacterBox(body); + // amsbsy.sty's \boldsymbol uses \binrel spacing to inherit the + // argument's bin|rel|ord status + return { + type: "mclass", + mode: parser.mode, + mclass: binrelClass(body), + body: [ + { + type: "font", + mode: parser.mode, + font: "boldsymbol", + body, + }, + ], + isCharacterBox: isCharacterBox, + }; + }, +}); + +// Old font changing functions +defineFunction({ + type: "font", + names: ["\\rm", "\\sf", "\\tt", "\\bf", "\\it", "\\cal"], + props: { + numArgs: 0, + allowedInText: true, + }, + handler: ({parser, funcName, breakOnTokenText}, args) => { + const {mode} = parser; + const body = parser.parseExpression(true, breakOnTokenText); + const style = `math${funcName.slice(1)}`; + + return { + type: "font", + mode: mode, + font: style, + body: { + type: "ordgroup", + mode: parser.mode, + body, + }, + }; + }, + htmlBuilder, + mathmlBuilder, +}); diff --git a/frontend/node_modules/katex/src/functions/genfrac.js b/frontend/node_modules/katex/src/functions/genfrac.js new file mode 100644 index 0000000..ce87554 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/genfrac.js @@ -0,0 +1,510 @@ +// @flow +import defineFunction, {normalizeArgument} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import delimiter from "../delimiter"; +import mathMLTree from "../mathMLTree"; +import Style from "../Style"; +import {assertNodeType} from "../parseNode"; +import {assert} from "../utils"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; +import {calculateSize, makeEm} from "../units"; + +const adjustStyle = (size, originalStyle) => { + // Figure out what style this fraction should be in based on the + // function used + let style = originalStyle; + if (size === "display") { + // Get display style as a default. + // If incoming style is sub/sup, use style.text() to get correct size. + style = style.id >= Style.SCRIPT.id ? style.text() : Style.DISPLAY; + } else if (size === "text" && + style.size === Style.DISPLAY.size) { + // We're in a \tfrac but incoming style is displaystyle, so: + style = Style.TEXT; + } else if (size === "script") { + style = Style.SCRIPT; + } else if (size === "scriptscript") { + style = Style.SCRIPTSCRIPT; + } + return style; +}; + +const htmlBuilder = (group, options) => { + // Fractions are handled in the TeXbook on pages 444-445, rules 15(a-e). + const style = adjustStyle(group.size, options.style); + + const nstyle = style.fracNum(); + const dstyle = style.fracDen(); + let newOptions; + + newOptions = options.havingStyle(nstyle); + const numerm = html.buildGroup(group.numer, newOptions, options); + + if (group.continued) { + // \cfrac inserts a \strut into the numerator. + // Get \strut dimensions from TeXbook page 353. + const hStrut = 8.5 / options.fontMetrics().ptPerEm; + const dStrut = 3.5 / options.fontMetrics().ptPerEm; + numerm.height = numerm.height < hStrut ? hStrut : numerm.height; + numerm.depth = numerm.depth < dStrut ? dStrut : numerm.depth; + } + + newOptions = options.havingStyle(dstyle); + const denomm = html.buildGroup(group.denom, newOptions, options); + + let rule; + let ruleWidth; + let ruleSpacing; + if (group.hasBarLine) { + if (group.barSize) { + ruleWidth = calculateSize(group.barSize, options); + rule = buildCommon.makeLineSpan("frac-line", options, ruleWidth); + } else { + rule = buildCommon.makeLineSpan("frac-line", options); + } + ruleWidth = rule.height; + ruleSpacing = rule.height; + } else { + rule = null; + ruleWidth = 0; + ruleSpacing = options.fontMetrics().defaultRuleThickness; + } + + // Rule 15b + let numShift; + let clearance; + let denomShift; + if (style.size === Style.DISPLAY.size || group.size === "display") { + numShift = options.fontMetrics().num1; + if (ruleWidth > 0) { + clearance = 3 * ruleSpacing; + } else { + clearance = 7 * ruleSpacing; + } + denomShift = options.fontMetrics().denom1; + } else { + if (ruleWidth > 0) { + numShift = options.fontMetrics().num2; + clearance = ruleSpacing; + } else { + numShift = options.fontMetrics().num3; + clearance = 3 * ruleSpacing; + } + denomShift = options.fontMetrics().denom2; + } + + let frac; + if (!rule) { + // Rule 15c + const candidateClearance = + (numShift - numerm.depth) - (denomm.height - denomShift); + if (candidateClearance < clearance) { + numShift += 0.5 * (clearance - candidateClearance); + denomShift += 0.5 * (clearance - candidateClearance); + } + + frac = buildCommon.makeVList({ + positionType: "individualShift", + children: [ + {type: "elem", elem: denomm, shift: denomShift}, + {type: "elem", elem: numerm, shift: -numShift}, + ], + }, options); + } else { + // Rule 15d + const axisHeight = options.fontMetrics().axisHeight; + + if ((numShift - numerm.depth) - (axisHeight + 0.5 * ruleWidth) < + clearance) { + numShift += + clearance - ((numShift - numerm.depth) - + (axisHeight + 0.5 * ruleWidth)); + } + + if ((axisHeight - 0.5 * ruleWidth) - (denomm.height - denomShift) < + clearance) { + denomShift += + clearance - ((axisHeight - 0.5 * ruleWidth) - + (denomm.height - denomShift)); + } + + const midShift = -(axisHeight - 0.5 * ruleWidth); + + frac = buildCommon.makeVList({ + positionType: "individualShift", + children: [ + {type: "elem", elem: denomm, shift: denomShift}, + {type: "elem", elem: rule, shift: midShift}, + {type: "elem", elem: numerm, shift: -numShift}, + ], + }, options); + } + + // Since we manually change the style sometimes (with \dfrac or \tfrac), + // account for the possible size change here. + newOptions = options.havingStyle(style); + frac.height *= newOptions.sizeMultiplier / options.sizeMultiplier; + frac.depth *= newOptions.sizeMultiplier / options.sizeMultiplier; + + // Rule 15e + let delimSize; + if (style.size === Style.DISPLAY.size) { + delimSize = options.fontMetrics().delim1; + } else if (style.size === Style.SCRIPTSCRIPT.size) { + delimSize = options.havingStyle(Style.SCRIPT).fontMetrics().delim2; + } else { + delimSize = options.fontMetrics().delim2; + } + + let leftDelim; + let rightDelim; + if (group.leftDelim == null) { + leftDelim = html.makeNullDelimiter(options, ["mopen"]); + } else { + leftDelim = delimiter.customSizedDelim( + group.leftDelim, delimSize, true, + options.havingStyle(style), group.mode, ["mopen"]); + } + + if (group.continued) { + rightDelim = buildCommon.makeSpan([]); // zero width for \cfrac + } else if (group.rightDelim == null) { + rightDelim = html.makeNullDelimiter(options, ["mclose"]); + } else { + rightDelim = delimiter.customSizedDelim( + group.rightDelim, delimSize, true, + options.havingStyle(style), group.mode, ["mclose"]); + } + + return buildCommon.makeSpan( + ["mord"].concat(newOptions.sizingClasses(options)), + [leftDelim, buildCommon.makeSpan(["mfrac"], [frac]), rightDelim], + options); +}; + +const mathmlBuilder = (group, options) => { + let node = new mathMLTree.MathNode( + "mfrac", + [ + mml.buildGroup(group.numer, options), + mml.buildGroup(group.denom, options), + ]); + + if (!group.hasBarLine) { + node.setAttribute("linethickness", "0px"); + } else if (group.barSize) { + const ruleWidth = calculateSize(group.barSize, options); + node.setAttribute("linethickness", makeEm(ruleWidth)); + } + + const style = adjustStyle(group.size, options.style); + if (style.size !== options.style.size) { + node = new mathMLTree.MathNode("mstyle", [node]); + const isDisplay = (style.size === Style.DISPLAY.size) ? "true" : "false"; + node.setAttribute("displaystyle", isDisplay); + node.setAttribute("scriptlevel", "0"); + } + + if (group.leftDelim != null || group.rightDelim != null) { + const withDelims = []; + + if (group.leftDelim != null) { + const leftOp = new mathMLTree.MathNode( + "mo", + [new mathMLTree.TextNode(group.leftDelim.replace("\\", ""))] + ); + + leftOp.setAttribute("fence", "true"); + + withDelims.push(leftOp); + } + + withDelims.push(node); + + if (group.rightDelim != null) { + const rightOp = new mathMLTree.MathNode( + "mo", + [new mathMLTree.TextNode(group.rightDelim.replace("\\", ""))] + ); + + rightOp.setAttribute("fence", "true"); + + withDelims.push(rightOp); + } + + return mml.makeRow(withDelims); + } + + return node; +}; + +defineFunction({ + type: "genfrac", + names: [ + "\\dfrac", "\\frac", "\\tfrac", + "\\dbinom", "\\binom", "\\tbinom", + "\\\\atopfrac", // can’t be entered directly + "\\\\bracefrac", "\\\\brackfrac", // ditto + ], + props: { + numArgs: 2, + allowedInArgument: true, + }, + handler: ({parser, funcName}, args) => { + const numer = args[0]; + const denom = args[1]; + let hasBarLine; + let leftDelim = null; + let rightDelim = null; + let size = "auto"; + + switch (funcName) { + case "\\dfrac": + case "\\frac": + case "\\tfrac": + hasBarLine = true; + break; + case "\\\\atopfrac": + hasBarLine = false; + break; + case "\\dbinom": + case "\\binom": + case "\\tbinom": + hasBarLine = false; + leftDelim = "("; + rightDelim = ")"; + break; + case "\\\\bracefrac": + hasBarLine = false; + leftDelim = "\\{"; + rightDelim = "\\}"; + break; + case "\\\\brackfrac": + hasBarLine = false; + leftDelim = "["; + rightDelim = "]"; + break; + default: + throw new Error("Unrecognized genfrac command"); + } + + switch (funcName) { + case "\\dfrac": + case "\\dbinom": + size = "display"; + break; + case "\\tfrac": + case "\\tbinom": + size = "text"; + break; + } + + return { + type: "genfrac", + mode: parser.mode, + continued: false, + numer, + denom, + hasBarLine, + leftDelim, + rightDelim, + size, + barSize: null, + }; + }, + + htmlBuilder, + mathmlBuilder, +}); + +defineFunction({ + type: "genfrac", + names: ["\\cfrac"], + props: { + numArgs: 2, + }, + handler: ({parser, funcName}, args) => { + const numer = args[0]; + const denom = args[1]; + + return { + type: "genfrac", + mode: parser.mode, + continued: true, + numer, + denom, + hasBarLine: true, + leftDelim: null, + rightDelim: null, + size: "display", + barSize: null, + }; + }, +}); + +// Infix generalized fractions -- these are not rendered directly, but replaced +// immediately by one of the variants above. +defineFunction({ + type: "infix", + names: ["\\over", "\\choose", "\\atop", "\\brace", "\\brack"], + props: { + numArgs: 0, + infix: true, + }, + handler({parser, funcName, token}) { + let replaceWith; + switch (funcName) { + case "\\over": + replaceWith = "\\frac"; + break; + case "\\choose": + replaceWith = "\\binom"; + break; + case "\\atop": + replaceWith = "\\\\atopfrac"; + break; + case "\\brace": + replaceWith = "\\\\bracefrac"; + break; + case "\\brack": + replaceWith = "\\\\brackfrac"; + break; + default: + throw new Error("Unrecognized infix genfrac command"); + } + return { + type: "infix", + mode: parser.mode, + replaceWith, + token, + }; + }, +}); + +const stylArray = ["display", "text", "script", "scriptscript"]; + +const delimFromValue = function(delimString: string): string | null { + let delim = null; + if (delimString.length > 0) { + delim = delimString; + delim = delim === "." ? null : delim; + } + return delim; +}; + +defineFunction({ + type: "genfrac", + names: ["\\genfrac"], + props: { + numArgs: 6, + allowedInArgument: true, + argTypes: ["math", "math", "size", "text", "math", "math"], + }, + handler({parser}, args) { + const numer = args[4]; + const denom = args[5]; + + // Look into the parse nodes to get the desired delimiters. + const leftNode = normalizeArgument(args[0]); + const leftDelim = leftNode.type === "atom" && leftNode.family === "open" + ? delimFromValue(leftNode.text) : null; + const rightNode = normalizeArgument(args[1]); + const rightDelim = rightNode.type === "atom" && rightNode.family === "close" + ? delimFromValue(rightNode.text) : null; + + const barNode = assertNodeType(args[2], "size"); + let hasBarLine; + let barSize = null; + if (barNode.isBlank) { + // \genfrac acts differently than \above. + // \genfrac treats an empty size group as a signal to use a + // standard bar size. \above would see size = 0 and omit the bar. + hasBarLine = true; + } else { + barSize = barNode.value; + hasBarLine = barSize.number > 0; + } + + // Find out if we want displaystyle, textstyle, etc. + let size = "auto"; + let styl = args[3]; + if (styl.type === "ordgroup") { + if (styl.body.length > 0) { + const textOrd = assertNodeType(styl.body[0], "textord"); + size = stylArray[Number(textOrd.text)]; + } + } else { + styl = assertNodeType(styl, "textord"); + size = stylArray[Number(styl.text)]; + } + + return { + type: "genfrac", + mode: parser.mode, + numer, + denom, + continued: false, + hasBarLine, + barSize, + leftDelim, + rightDelim, + size, + }; + }, + + htmlBuilder, + mathmlBuilder, +}); + +// \above is an infix fraction that also defines a fraction bar size. +defineFunction({ + type: "infix", + names: ["\\above"], + props: { + numArgs: 1, + argTypes: ["size"], + infix: true, + }, + handler({parser, funcName, token}, args) { + return { + type: "infix", + mode: parser.mode, + replaceWith: "\\\\abovefrac", + size: assertNodeType(args[0], "size").value, + token, + }; + }, +}); + +defineFunction({ + type: "genfrac", + names: ["\\\\abovefrac"], + props: { + numArgs: 3, + argTypes: ["math", "size", "math"], + }, + handler: ({parser, funcName}, args) => { + const numer = args[0]; + const barSize = assert(assertNodeType(args[1], "infix").size); + const denom = args[2]; + + const hasBarLine = barSize.number > 0; + return { + type: "genfrac", + mode: parser.mode, + numer, + denom, + continued: false, + hasBarLine, + barSize, + leftDelim: null, + rightDelim: null, + size: "auto", + }; + }, + + htmlBuilder, + mathmlBuilder, +}); diff --git a/frontend/node_modules/katex/src/functions/hbox.js b/frontend/node_modules/katex/src/functions/hbox.js new file mode 100644 index 0000000..400638b --- /dev/null +++ b/frontend/node_modules/katex/src/functions/hbox.js @@ -0,0 +1,39 @@ +// @flow +import defineFunction, {ordargument} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +// \hbox is provided for compatibility with LaTeX \vcenter. +// In LaTeX, \vcenter can act only on a box, as in +// \vcenter{\hbox{$\frac{a+b}{\dfrac{c}{d}}$}} +// This function by itself doesn't do anything but prevent a soft line break. + +defineFunction({ + type: "hbox", + names: ["\\hbox"], + props: { + numArgs: 1, + argTypes: ["text"], + allowedInText: true, + primitive: true, + }, + handler({parser}, args) { + return { + type: "hbox", + mode: parser.mode, + body: ordargument(args[0]), + }; + }, + htmlBuilder(group, options) { + const elements = html.buildExpression(group.body, options, false); + return buildCommon.makeFragment(elements); + }, + mathmlBuilder(group, options) { + return new mathMLTree.MathNode( + "mrow", mml.buildExpression(group.body, options) + ); + }, +}); diff --git a/frontend/node_modules/katex/src/functions/horizBrace.js b/frontend/node_modules/katex/src/functions/horizBrace.js new file mode 100644 index 0000000..259f0d6 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/horizBrace.js @@ -0,0 +1,137 @@ +// @flow +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import stretchy from "../stretchy"; +import Style from "../Style"; +import {assertNodeType} from "../parseNode"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +import type {HtmlBuilderSupSub, MathMLBuilder} from "../defineFunction"; +import type {ParseNode} from "../parseNode"; + +// NOTE: Unlike most `htmlBuilder`s, this one handles not only "horizBrace", but +// also "supsub" since an over/underbrace can affect super/subscripting. +export const htmlBuilder: HtmlBuilderSupSub<"horizBrace"> = (grp, options) => { + const style = options.style; + + // Pull out the `ParseNode<"horizBrace">` if `grp` is a "supsub" node. + let supSubGroup; + let group: ParseNode<"horizBrace">; + if (grp.type === "supsub") { + // Ref: LaTeX source2e: }}}}\limits} + // i.e. LaTeX treats the brace similar to an op and passes it + // with \limits, so we need to assign supsub style. + supSubGroup = grp.sup ? + html.buildGroup(grp.sup, options.havingStyle(style.sup()), options) : + html.buildGroup(grp.sub, options.havingStyle(style.sub()), options); + group = assertNodeType(grp.base, "horizBrace"); + } else { + group = assertNodeType(grp, "horizBrace"); + } + + // Build the base group + const body = html.buildGroup( + group.base, options.havingBaseStyle(Style.DISPLAY)); + + // Create the stretchy element + const braceBody = stretchy.svgSpan(group, options); + + // Generate the vlist, with the appropriate kerns ┏━━━━━━━━┓ + // This first vlist contains the content and the brace: equation + let vlist; + if (group.isOver) { + vlist = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [ + {type: "elem", elem: body}, + {type: "kern", size: 0.1}, + {type: "elem", elem: braceBody}, + ], + }, options); + // $FlowFixMe: Replace this with passing "svg-align" into makeVList. + vlist.children[0].children[0].children[1].classes.push("svg-align"); + } else { + vlist = buildCommon.makeVList({ + positionType: "bottom", + positionData: body.depth + 0.1 + braceBody.height, + children: [ + {type: "elem", elem: braceBody}, + {type: "kern", size: 0.1}, + {type: "elem", elem: body}, + ], + }, options); + // $FlowFixMe: Replace this with passing "svg-align" into makeVList. + vlist.children[0].children[0].children[0].classes.push("svg-align"); + } + + if (supSubGroup) { + // To write the supsub, wrap the first vlist in another vlist: + // They can't all go in the same vlist, because the note might be + // wider than the equation. We want the equation to control the + // brace width. + + // note long note long note + // ┏━━━━━━━━┓ or ┏━━━┓ not ┏━━━━━━━━━┓ + // equation eqn eqn + + const vSpan = buildCommon.makeSpan( + ["mord", (group.isOver ? "mover" : "munder")], + [vlist], options); + + if (group.isOver) { + vlist = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [ + {type: "elem", elem: vSpan}, + {type: "kern", size: 0.2}, + {type: "elem", elem: supSubGroup}, + ], + }, options); + } else { + vlist = buildCommon.makeVList({ + positionType: "bottom", + positionData: vSpan.depth + 0.2 + supSubGroup.height + + supSubGroup.depth, + children: [ + {type: "elem", elem: supSubGroup}, + {type: "kern", size: 0.2}, + {type: "elem", elem: vSpan}, + ], + }, options); + } + } + + return buildCommon.makeSpan( + ["mord", (group.isOver ? "mover" : "munder")], [vlist], options); +}; + +const mathmlBuilder: MathMLBuilder<"horizBrace"> = (group, options) => { + const accentNode = stretchy.mathMLnode(group.label); + return new mathMLTree.MathNode( + (group.isOver ? "mover" : "munder"), + [mml.buildGroup(group.base, options), accentNode] + ); +}; + +// Horizontal stretchy braces +defineFunction({ + type: "horizBrace", + names: ["\\overbrace", "\\underbrace"], + props: { + numArgs: 1, + }, + handler({parser, funcName}, args) { + return { + type: "horizBrace", + mode: parser.mode, + label: funcName, + isOver: /^\\over/.test(funcName), + base: args[0], + }; + }, + htmlBuilder, + mathmlBuilder, +}); diff --git a/frontend/node_modules/katex/src/functions/href.js b/frontend/node_modules/katex/src/functions/href.js new file mode 100644 index 0000000..d2cd2df --- /dev/null +++ b/frontend/node_modules/katex/src/functions/href.js @@ -0,0 +1,93 @@ +// @flow +import defineFunction, {ordargument} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import {assertNodeType} from "../parseNode"; +import {MathNode} from "../mathMLTree"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +defineFunction({ + type: "href", + names: ["\\href"], + props: { + numArgs: 2, + argTypes: ["url", "original"], + allowedInText: true, + }, + handler: ({parser}, args) => { + const body = args[1]; + const href = assertNodeType(args[0], "url").url; + + if (!parser.settings.isTrusted({ + command: "\\href", + url: href, + })) { + return parser.formatUnsupportedCmd("\\href"); + } + + return { + type: "href", + mode: parser.mode, + href, + body: ordargument(body), + }; + }, + htmlBuilder: (group, options) => { + const elements = html.buildExpression(group.body, options, false); + return buildCommon.makeAnchor(group.href, [], elements, options); + }, + mathmlBuilder: (group, options) => { + let math = mml.buildExpressionRow(group.body, options); + if (!(math instanceof MathNode)) { + math = new MathNode("mrow", [math]); + } + math.setAttribute("href", group.href); + return math; + }, +}); + +defineFunction({ + type: "href", + names: ["\\url"], + props: { + numArgs: 1, + argTypes: ["url"], + allowedInText: true, + }, + handler: ({parser}, args) => { + const href = assertNodeType(args[0], "url").url; + + if (!parser.settings.isTrusted({ + command: "\\url", + url: href, + })) { + return parser.formatUnsupportedCmd("\\url"); + } + + const chars = []; + for (let i = 0; i < href.length; i++) { + let c = href[i]; + if (c === "~") { + c = "\\textasciitilde"; + } + chars.push({ + type: "textord", + mode: "text", + text: c, + }); + } + const body = { + type: "text", + mode: parser.mode, + font: "\\texttt", + body: chars, + }; + return { + type: "href", + mode: parser.mode, + href, + body: ordargument(body), + }; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/html.js b/frontend/node_modules/katex/src/functions/html.js new file mode 100644 index 0000000..c8d316a --- /dev/null +++ b/frontend/node_modules/katex/src/functions/html.js @@ -0,0 +1,102 @@ +// @flow +import defineFunction, {ordargument} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import {assertNodeType} from "../parseNode"; +import ParseError from "../ParseError"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +defineFunction({ + type: "html", + names: ["\\htmlClass", "\\htmlId", "\\htmlStyle", "\\htmlData"], + props: { + numArgs: 2, + argTypes: ["raw", "original"], + allowedInText: true, + }, + handler: ({parser, funcName, token}, args) => { + const value = assertNodeType(args[0], "raw").string; + const body = args[1]; + + if (parser.settings.strict) { + parser.settings.reportNonstrict("htmlExtension", + "HTML extension is disabled on strict mode"); + } + + let trustContext; + const attributes = {}; + + switch (funcName) { + case "\\htmlClass": + attributes.class = value; + trustContext = { + command: "\\htmlClass", + class: value, + }; + break; + case "\\htmlId": + attributes.id = value; + trustContext = { + command: "\\htmlId", + id: value, + }; + break; + case "\\htmlStyle": + attributes.style = value; + trustContext = { + command: "\\htmlStyle", + style: value, + }; + break; + case "\\htmlData": { + const data = value.split(","); + for (let i = 0; i < data.length; i++) { + const keyVal = data[i].split("="); + if (keyVal.length !== 2) { + throw new ParseError( + "Error parsing key-value for \\htmlData"); + } + attributes["data-" + keyVal[0].trim()] = keyVal[1].trim(); + } + + trustContext = { + command: "\\htmlData", + attributes, + }; + break; + } + default: + throw new Error("Unrecognized html command"); + } + + if (!parser.settings.isTrusted(trustContext)) { + return parser.formatUnsupportedCmd(funcName); + } + return { + type: "html", + mode: parser.mode, + attributes, + body: ordargument(body), + }; + }, + htmlBuilder: (group, options) => { + const elements = html.buildExpression(group.body, options, false); + + const classes = ["enclosing"]; + if (group.attributes.class) { + classes.push(...group.attributes.class.trim().split(/\s+/)); + } + + const span = buildCommon.makeSpan(classes, elements, options); + for (const attr in group.attributes) { + if (attr !== "class" && group.attributes.hasOwnProperty(attr)) { + span.setAttribute(attr, group.attributes[attr]); + } + } + return span; + }, + mathmlBuilder: (group, options) => { + return mml.buildExpressionRow(group.body, options); + }, +}); diff --git a/frontend/node_modules/katex/src/functions/htmlmathml.js b/frontend/node_modules/katex/src/functions/htmlmathml.js new file mode 100644 index 0000000..5c08bb5 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/htmlmathml.js @@ -0,0 +1,34 @@ +// @flow +import defineFunction, {ordargument} from "../defineFunction"; +import buildCommon from "../buildCommon"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +defineFunction({ + type: "htmlmathml", + names: ["\\html@mathml"], + props: { + numArgs: 2, + allowedInText: true, + }, + handler: ({parser}, args) => { + return { + type: "htmlmathml", + mode: parser.mode, + html: ordargument(args[0]), + mathml: ordargument(args[1]), + }; + }, + htmlBuilder: (group, options) => { + const elements = html.buildExpression( + group.html, + options, + false + ); + return buildCommon.makeFragment(elements); + }, + mathmlBuilder: (group, options) => { + return mml.buildExpressionRow(group.mathml, options); + }, +}); diff --git a/frontend/node_modules/katex/src/functions/includegraphics.js b/frontend/node_modules/katex/src/functions/includegraphics.js new file mode 100644 index 0000000..daf6537 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/includegraphics.js @@ -0,0 +1,151 @@ +// @flow +import defineFunction from "../defineFunction"; +import type {Measurement} from "../units"; +import {calculateSize, validUnit, makeEm} from "../units"; +import ParseError from "../ParseError"; +import {Img} from "../domTree"; +import mathMLTree from "../mathMLTree"; +import {assertNodeType} from "../parseNode"; +import type {CssStyle} from "../domTree"; + +const sizeData = function(str: string): Measurement { + if (/^[-+]? *(\d+(\.\d*)?|\.\d+)$/.test(str)) { + // str is a number with no unit specified. + // default unit is bp, per graphix package. + return {number: +str, unit: "bp"}; + } else { + const match = (/([-+]?) *(\d+(?:\.\d*)?|\.\d+) *([a-z]{2})/).exec(str); + if (!match) { + throw new ParseError("Invalid size: '" + str + + "' in \\includegraphics"); + } + const data = { + number: +(match[1] + match[2]), // sign + magnitude, cast to number + unit: match[3], + }; + if (!validUnit(data)) { + throw new ParseError("Invalid unit: '" + data.unit + + "' in \\includegraphics."); + } + return data; + } +}; + +defineFunction({ + type: "includegraphics", + names: ["\\includegraphics"], + props: { + numArgs: 1, + numOptionalArgs: 1, + argTypes: ["raw", "url"], + allowedInText: false, + }, + handler: ({parser}, args, optArgs) => { + let width = {number: 0, unit: "em"}; + let height = {number: 0.9, unit: "em"}; // sorta character sized. + let totalheight = {number: 0, unit: "em"}; + let alt = ""; + + if (optArgs[0]) { + const attributeStr = assertNodeType(optArgs[0], "raw").string; + + // Parser.js does not parse key/value pairs. We get a string. + const attributes = attributeStr.split(","); + for (let i = 0; i < attributes.length; i++) { + const keyVal = attributes[i].split("="); + if (keyVal.length === 2) { + const str = keyVal[1].trim(); + switch (keyVal[0].trim()) { + case "alt": + alt = str; + break; + case "width": + width = sizeData(str); + break; + case "height": + height = sizeData(str); + break; + case "totalheight": + totalheight = sizeData(str); + break; + default: + throw new ParseError("Invalid key: '" + keyVal[0] + + "' in \\includegraphics."); + } + } + } + } + + const src = assertNodeType(args[0], "url").url; + + if (alt === "") { + // No alt given. Use the file name. Strip away the path. + alt = src; + alt = alt.replace(/^.*[\\/]/, ''); + alt = alt.substring(0, alt.lastIndexOf('.')); + } + + if (!parser.settings.isTrusted({ + command: "\\includegraphics", + url: src, + })) { + return parser.formatUnsupportedCmd("\\includegraphics"); + } + + return { + type: "includegraphics", + mode: parser.mode, + alt: alt, + width: width, + height: height, + totalheight: totalheight, + src: src, + }; + }, + htmlBuilder: (group, options) => { + const height = calculateSize(group.height, options); + let depth = 0; + + if (group.totalheight.number > 0) { + depth = calculateSize(group.totalheight, options) - height; + } + + let width = 0; + if (group.width.number > 0) { + width = calculateSize(group.width, options); + } + + const style: CssStyle = {height: makeEm(height + depth)}; + if (width > 0) { + style.width = makeEm(width); + } + if (depth > 0) { + style.verticalAlign = makeEm(-depth); + } + + const node = new Img(group.src, group.alt, style); + node.height = height; + node.depth = depth; + + return node; + }, + mathmlBuilder: (group, options) => { + const node = new mathMLTree.MathNode("mglyph", []); + node.setAttribute("alt", group.alt); + + const height = calculateSize(group.height, options); + let depth = 0; + if (group.totalheight.number > 0) { + depth = calculateSize(group.totalheight, options) - height; + node.setAttribute("valign", makeEm(-depth)); + } + node.setAttribute("height", makeEm(height + depth)); + + if (group.width.number > 0) { + const width = calculateSize(group.width, options); + node.setAttribute("width", makeEm(width)); + } + node.setAttribute("src", group.src); + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/kern.js b/frontend/node_modules/katex/src/functions/kern.js new file mode 100644 index 0000000..1f4abb6 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/kern.js @@ -0,0 +1,56 @@ +//@flow +// Horizontal spacing commands + +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import {calculateSize} from "../units"; +import {assertNodeType} from "../parseNode"; + +// TODO: \hskip and \mskip should support plus and minus in lengths + +defineFunction({ + type: "kern", + names: ["\\kern", "\\mkern", "\\hskip", "\\mskip"], + props: { + numArgs: 1, + argTypes: ["size"], + primitive: true, + allowedInText: true, + }, + handler({parser, funcName}, args) { + const size = assertNodeType(args[0], "size"); + if (parser.settings.strict) { + const mathFunction = (funcName[1] === 'm'); // \mkern, \mskip + const muUnit = (size.value.unit === 'mu'); + if (mathFunction) { + if (!muUnit) { + parser.settings.reportNonstrict("mathVsTextUnits", + `LaTeX's ${funcName} supports only mu units, ` + + `not ${size.value.unit} units`); + } + if (parser.mode !== "math") { + parser.settings.reportNonstrict("mathVsTextUnits", + `LaTeX's ${funcName} works only in math mode`); + } + } else { // !mathFunction + if (muUnit) { + parser.settings.reportNonstrict("mathVsTextUnits", + `LaTeX's ${funcName} doesn't support mu units`); + } + } + } + return { + type: "kern", + mode: parser.mode, + dimension: size.value, + }; + }, + htmlBuilder(group, options) { + return buildCommon.makeGlue(group.dimension, options); + }, + mathmlBuilder(group, options) { + const dimension = calculateSize(group.dimension, options); + return new mathMLTree.SpaceNode(dimension); + }, +}); diff --git a/frontend/node_modules/katex/src/functions/lap.js b/frontend/node_modules/katex/src/functions/lap.js new file mode 100644 index 0000000..3d89e99 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/lap.js @@ -0,0 +1,74 @@ +// @flow +// Horizontal overlap functions +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import {makeEm} from "../units"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +defineFunction({ + type: "lap", + names: ["\\mathllap", "\\mathrlap", "\\mathclap"], + props: { + numArgs: 1, + allowedInText: true, + }, + handler: ({parser, funcName}, args) => { + const body = args[0]; + return { + type: "lap", + mode: parser.mode, + alignment: funcName.slice(5), + body, + }; + }, + htmlBuilder: (group, options) => { + // mathllap, mathrlap, mathclap + let inner; + if (group.alignment === "clap") { + // ref: https://www.math.lsu.edu/~aperlis/publications/mathclap/ + inner = buildCommon.makeSpan( + [], [html.buildGroup(group.body, options)]); + // wrap, since CSS will center a .clap > .inner > span + inner = buildCommon.makeSpan(["inner"], [inner], options); + } else { + inner = buildCommon.makeSpan( + ["inner"], [html.buildGroup(group.body, options)]); + } + const fix = buildCommon.makeSpan(["fix"], []); + let node = buildCommon.makeSpan( + [group.alignment], [inner, fix], options); + + // At this point, we have correctly set horizontal alignment of the + // two items involved in the lap. + // Next, use a strut to set the height of the HTML bounding box. + // Otherwise, a tall argument may be misplaced. + // This code resolved issue #1153 + const strut = buildCommon.makeSpan(["strut"]); + strut.style.height = makeEm(node.height + node.depth); + if (node.depth) { + strut.style.verticalAlign = makeEm(-node.depth); + } + node.children.unshift(strut); + + // Next, prevent vertical misplacement when next to something tall. + // This code resolves issue #1234 + node = buildCommon.makeSpan(["thinbox"], [node], options); + return buildCommon.makeSpan(["mord", "vbox"], [node], options); + }, + mathmlBuilder: (group, options) => { + // mathllap, mathrlap, mathclap + const node = new mathMLTree.MathNode( + "mpadded", [mml.buildGroup(group.body, options)]); + + if (group.alignment !== "rlap") { + const offset = (group.alignment === "llap" ? "-1" : "-0.5"); + node.setAttribute("lspace", offset + "width"); + } + node.setAttribute("width", "0px"); + + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/math.js b/frontend/node_modules/katex/src/functions/math.js new file mode 100644 index 0000000..e0d08d5 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/math.js @@ -0,0 +1,42 @@ +// @flow +import defineFunction from "../defineFunction"; +import ParseError from "../ParseError"; + +// Switching from text mode back to math mode +defineFunction({ + type: "styling", + names: ["\\(", "$"], + props: { + numArgs: 0, + allowedInText: true, + allowedInMath: false, + }, + handler({funcName, parser}, args) { + const outerMode = parser.mode; + parser.switchMode("math"); + const close = (funcName === "\\(" ? "\\)" : "$"); + const body = parser.parseExpression(false, close); + parser.expect(close); + parser.switchMode(outerMode); + return { + type: "styling", + mode: parser.mode, + style: "text", + body, + }; + }, +}); + +// Check for extra closing math delimiters +defineFunction({ + type: "text", // Doesn't matter what this is. + names: ["\\)", "\\]"], + props: { + numArgs: 0, + allowedInText: true, + allowedInMath: false, + }, + handler(context, args) { + throw new ParseError(`Mismatched ${context.funcName}`); + }, +}); diff --git a/frontend/node_modules/katex/src/functions/mathchoice.js b/frontend/node_modules/katex/src/functions/mathchoice.js new file mode 100644 index 0000000..7f86859 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/mathchoice.js @@ -0,0 +1,51 @@ +// @flow +import defineFunction, {ordargument} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import Style from "../Style"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +import type {ParseNode} from "../parseNode"; + +const chooseMathStyle = (group: ParseNode<"mathchoice">, options) => { + switch (options.style.size) { + case Style.DISPLAY.size: return group.display; + case Style.TEXT.size: return group.text; + case Style.SCRIPT.size: return group.script; + case Style.SCRIPTSCRIPT.size: return group.scriptscript; + default: return group.text; + } +}; + +defineFunction({ + type: "mathchoice", + names: ["\\mathchoice"], + props: { + numArgs: 4, + primitive: true, + }, + handler: ({parser}, args) => { + return { + type: "mathchoice", + mode: parser.mode, + display: ordargument(args[0]), + text: ordargument(args[1]), + script: ordargument(args[2]), + scriptscript: ordargument(args[3]), + }; + }, + htmlBuilder: (group, options) => { + const body = chooseMathStyle(group, options); + const elements = html.buildExpression( + body, + options, + false + ); + return buildCommon.makeFragment(elements); + }, + mathmlBuilder: (group, options) => { + const body = chooseMathStyle(group, options); + return mml.buildExpressionRow(body, options); + }, +}); diff --git a/frontend/node_modules/katex/src/functions/mclass.js b/frontend/node_modules/katex/src/functions/mclass.js new file mode 100644 index 0000000..96cdb37 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/mclass.js @@ -0,0 +1,168 @@ +// @flow +import defineFunction, {ordargument} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import utils from "../utils"; +import type {AnyParseNode} from "../parseNode"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +import type {ParseNode} from "../parseNode"; + +const makeSpan = buildCommon.makeSpan; + +function htmlBuilder(group: ParseNode<"mclass">, options) { + const elements = html.buildExpression(group.body, options, true); + return makeSpan([group.mclass], elements, options); +} + +function mathmlBuilder(group: ParseNode<"mclass">, options) { + let node: mathMLTree.MathNode; + const inner = mml.buildExpression(group.body, options); + + if (group.mclass === "minner") { + node = new mathMLTree.MathNode("mpadded", inner); + } else if (group.mclass === "mord") { + if (group.isCharacterBox) { + node = inner[0]; + node.type = "mi"; + } else { + node = new mathMLTree.MathNode("mi", inner); + } + } else { + if (group.isCharacterBox) { + node = inner[0]; + node.type = "mo"; + } else { + node = new mathMLTree.MathNode("mo", inner); + } + + // Set spacing based on what is the most likely adjacent atom type. + // See TeXbook p170. + if (group.mclass === "mbin") { + node.attributes.lspace = "0.22em"; // medium space + node.attributes.rspace = "0.22em"; + } else if (group.mclass === "mpunct") { + node.attributes.lspace = "0em"; + node.attributes.rspace = "0.17em"; // thinspace + } else if (group.mclass === "mopen" || group.mclass === "mclose") { + node.attributes.lspace = "0em"; + node.attributes.rspace = "0em"; + } else if (group.mclass === "minner") { + node.attributes.lspace = "0.0556em"; // 1 mu is the most likely option + node.attributes.width = "+0.1111em"; + } + // MathML default space is 5/18 em, so needs no action. + // Ref: https://developer.mozilla.org/en-US/docs/Web/MathML/Element/mo + } + return node; +} + +// Math class commands except \mathop +defineFunction({ + type: "mclass", + names: [ + "\\mathord", "\\mathbin", "\\mathrel", "\\mathopen", + "\\mathclose", "\\mathpunct", "\\mathinner", + ], + props: { + numArgs: 1, + primitive: true, + }, + handler({parser, funcName}, args) { + const body = args[0]; + return { + type: "mclass", + mode: parser.mode, + mclass: "m" + funcName.slice(5), // TODO(kevinb): don't prefix with 'm' + body: ordargument(body), + isCharacterBox: utils.isCharacterBox(body), + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +export const binrelClass = (arg: AnyParseNode): string => { + // \binrel@ spacing varies with (bin|rel|ord) of the atom in the argument. + // (by rendering separately and with {}s before and after, and measuring + // the change in spacing). We'll do roughly the same by detecting the + // atom type directly. + const atom = (arg.type === "ordgroup" && arg.body.length ? arg.body[0] : arg); + if (atom.type === "atom" && (atom.family === "bin" || atom.family === "rel")) { + return "m" + atom.family; + } else { + return "mord"; + } +}; + +// \@binrel{x}{y} renders like y but as mbin/mrel/mord if x is mbin/mrel/mord. +// This is equivalent to \binrel@{x}\binrel@@{y} in AMSTeX. +defineFunction({ + type: "mclass", + names: ["\\@binrel"], + props: { + numArgs: 2, + }, + handler({parser}, args) { + return { + type: "mclass", + mode: parser.mode, + mclass: binrelClass(args[0]), + body: ordargument(args[1]), + isCharacterBox: utils.isCharacterBox(args[1]), + }; + }, +}); + +// Build a relation or stacked op by placing one symbol on top of another +defineFunction({ + type: "mclass", + names: ["\\stackrel", "\\overset", "\\underset"], + props: { + numArgs: 2, + }, + handler({parser, funcName}, args) { + const baseArg = args[1]; + const shiftedArg = args[0]; + + let mclass; + if (funcName !== "\\stackrel") { + // LaTeX applies \binrel spacing to \overset and \underset. + mclass = binrelClass(baseArg); + } else { + mclass = "mrel"; // for \stackrel + } + + const baseOp = { + type: "op", + mode: baseArg.mode, + limits: true, + alwaysHandleSupSub: true, + parentIsSupSub: false, + symbol: false, + suppressBaseShift: funcName !== "\\stackrel", + body: ordargument(baseArg), + }; + + const supsub = { + type: "supsub", + mode: shiftedArg.mode, + base: baseOp, + sup: funcName === "\\underset" ? null : shiftedArg, + sub: funcName === "\\underset" ? shiftedArg : null, + }; + + return { + type: "mclass", + mode: parser.mode, + mclass, + body: [supsub], + isCharacterBox: utils.isCharacterBox(supsub), + }; + }, + htmlBuilder, + mathmlBuilder, +}); + diff --git a/frontend/node_modules/katex/src/functions/op.js b/frontend/node_modules/katex/src/functions/op.js new file mode 100644 index 0000000..9dcf94e --- /dev/null +++ b/frontend/node_modules/katex/src/functions/op.js @@ -0,0 +1,334 @@ +// @flow +// Limits, symbols +import defineFunction, {ordargument} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import {SymbolNode} from "../domTree"; +import * as mathMLTree from "../mathMLTree"; +import utils from "../utils"; +import Style from "../Style"; +import {assembleSupSub} from "./utils/assembleSupSub"; +import {assertNodeType} from "../parseNode"; +import {makeEm} from "../units"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +import type {HtmlBuilderSupSub, MathMLBuilder} from "../defineFunction"; +import type {ParseNode} from "../parseNode"; + +// Most operators have a large successor symbol, but these don't. +const noSuccessor = [ + "\\smallint", +]; + +// NOTE: Unlike most `htmlBuilder`s, this one handles not only "op", but also +// "supsub" since some of them (like \int) can affect super/subscripting. +export const htmlBuilder: HtmlBuilderSupSub<"op"> = (grp, options) => { + // Operators are handled in the TeXbook pg. 443-444, rule 13(a). + let supGroup; + let subGroup; + let hasLimits = false; + let group: ParseNode<"op">; + if (grp.type === "supsub") { + // If we have limits, supsub will pass us its group to handle. Pull + // out the superscript and subscript and set the group to the op in + // its base. + supGroup = grp.sup; + subGroup = grp.sub; + group = assertNodeType(grp.base, "op"); + hasLimits = true; + } else { + group = assertNodeType(grp, "op"); + } + + const style = options.style; + + let large = false; + if (style.size === Style.DISPLAY.size && + group.symbol && + !utils.contains(noSuccessor, group.name)) { + + // Most symbol operators get larger in displaystyle (rule 13) + large = true; + } + + let base; + if (group.symbol) { + // If this is a symbol, create the symbol. + const fontName = large ? "Size2-Regular" : "Size1-Regular"; + + let stash = ""; + if (group.name === "\\oiint" || group.name === "\\oiiint") { + // No font glyphs yet, so use a glyph w/o the oval. + // TODO: When font glyphs are available, delete this code. + stash = group.name.slice(1); + group.name = stash === "oiint" ? "\\iint" : "\\iiint"; + } + + base = buildCommon.makeSymbol( + group.name, fontName, "math", options, + ["mop", "op-symbol", large ? "large-op" : "small-op"]); + + if (stash.length > 0) { + // We're in \oiint or \oiiint. Overlay the oval. + // TODO: When font glyphs are available, delete this code. + const italic = base.italic; + const oval = buildCommon.staticSvg(stash + "Size" + + (large ? "2" : "1"), options); + base = buildCommon.makeVList({ + positionType: "individualShift", + children: [ + {type: "elem", elem: base, shift: 0}, + {type: "elem", elem: oval, shift: large ? 0.08 : 0}, + ], + }, options); + group.name = "\\" + stash; + base.classes.unshift("mop"); + // $FlowFixMe + base.italic = italic; + } + } else if (group.body) { + // If this is a list, compose that list. + const inner = html.buildExpression(group.body, options, true); + if (inner.length === 1 && inner[0] instanceof SymbolNode) { + base = inner[0]; + base.classes[0] = "mop"; // replace old mclass + } else { + base = buildCommon.makeSpan(["mop"], inner, options); + } + } else { + // Otherwise, this is a text operator. Build the text from the + // operator's name. + const output = []; + for (let i = 1; i < group.name.length; i++) { + output.push(buildCommon.mathsym(group.name[i], group.mode, options)); + } + base = buildCommon.makeSpan(["mop"], output, options); + } + + // If content of op is a single symbol, shift it vertically. + let baseShift = 0; + let slant = 0; + if ((base instanceof SymbolNode + || group.name === "\\oiint" || group.name === "\\oiiint") + && !group.suppressBaseShift) { + // We suppress the shift of the base of \overset and \underset. Otherwise, + // shift the symbol so its center lies on the axis (rule 13). It + // appears that our fonts have the centers of the symbols already + // almost on the axis, so these numbers are very small. Note we + // don't actually apply this here, but instead it is used either in + // the vlist creation or separately when there are no limits. + baseShift = (base.height - base.depth) / 2 - + options.fontMetrics().axisHeight; + + // The slant of the symbol is just its italic correction. + // $FlowFixMe + slant = base.italic; + } + + if (hasLimits) { + return assembleSupSub(base, supGroup, subGroup, options, + style, slant, baseShift); + + } else { + if (baseShift) { + base.style.position = "relative"; + base.style.top = makeEm(baseShift); + } + + return base; + } +}; + +const mathmlBuilder: MathMLBuilder<"op"> = (group, options) => { + let node; + + if (group.symbol) { + // This is a symbol. Just add the symbol. + node = new mathMLTree.MathNode( + "mo", [mml.makeText(group.name, group.mode)]); + if (utils.contains(noSuccessor, group.name)) { + node.setAttribute("largeop", "false"); + } + } else if (group.body) { + // This is an operator with children. Add them. + node = new mathMLTree.MathNode( + "mo", mml.buildExpression(group.body, options)); + } else { + // This is a text operator. Add all of the characters from the + // operator's name. + node = new mathMLTree.MathNode( + "mi", [new mathMLTree.TextNode(group.name.slice(1))]); + // Append an . + // ref: https://www.w3.org/TR/REC-MathML/chap3_2.html#sec3.2.4 + const operator = new mathMLTree.MathNode("mo", + [mml.makeText("\u2061", "text")]); + if (group.parentIsSupSub) { + node = new mathMLTree.MathNode("mrow", [node, operator]); + } else { + node = mathMLTree.newDocumentFragment([node, operator]); + } + } + + return node; +}; + +const singleCharBigOps: {[string]: string} = { + "\u220F": "\\prod", + "\u2210": "\\coprod", + "\u2211": "\\sum", + "\u22c0": "\\bigwedge", + "\u22c1": "\\bigvee", + "\u22c2": "\\bigcap", + "\u22c3": "\\bigcup", + "\u2a00": "\\bigodot", + "\u2a01": "\\bigoplus", + "\u2a02": "\\bigotimes", + "\u2a04": "\\biguplus", + "\u2a06": "\\bigsqcup", +}; + +defineFunction({ + type: "op", + names: [ + "\\coprod", "\\bigvee", "\\bigwedge", "\\biguplus", "\\bigcap", + "\\bigcup", "\\intop", "\\prod", "\\sum", "\\bigotimes", + "\\bigoplus", "\\bigodot", "\\bigsqcup", "\\smallint", "\u220F", + "\u2210", "\u2211", "\u22c0", "\u22c1", "\u22c2", "\u22c3", "\u2a00", + "\u2a01", "\u2a02", "\u2a04", "\u2a06", + ], + props: { + numArgs: 0, + }, + handler: ({parser, funcName}, args) => { + let fName = funcName; + if (fName.length === 1) { + fName = singleCharBigOps[fName]; + } + return { + type: "op", + mode: parser.mode, + limits: true, + parentIsSupSub: false, + symbol: true, + name: fName, + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +// Note: calling defineFunction with a type that's already been defined only +// works because the same htmlBuilder and mathmlBuilder are being used. +defineFunction({ + type: "op", + names: ["\\mathop"], + props: { + numArgs: 1, + primitive: true, + }, + handler: ({parser}, args) => { + const body = args[0]; + return { + type: "op", + mode: parser.mode, + limits: false, + parentIsSupSub: false, + symbol: false, + body: ordargument(body), + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +// There are 2 flags for operators; whether they produce limits in +// displaystyle, and whether they are symbols and should grow in +// displaystyle. These four groups cover the four possible choices. + +const singleCharIntegrals: {[string]: string} = { + "\u222b": "\\int", + "\u222c": "\\iint", + "\u222d": "\\iiint", + "\u222e": "\\oint", + "\u222f": "\\oiint", + "\u2230": "\\oiiint", +}; + +// No limits, not symbols +defineFunction({ + type: "op", + names: [ + "\\arcsin", "\\arccos", "\\arctan", "\\arctg", "\\arcctg", + "\\arg", "\\ch", "\\cos", "\\cosec", "\\cosh", "\\cot", "\\cotg", + "\\coth", "\\csc", "\\ctg", "\\cth", "\\deg", "\\dim", "\\exp", + "\\hom", "\\ker", "\\lg", "\\ln", "\\log", "\\sec", "\\sin", + "\\sinh", "\\sh", "\\tan", "\\tanh", "\\tg", "\\th", + ], + props: { + numArgs: 0, + }, + handler({parser, funcName}) { + return { + type: "op", + mode: parser.mode, + limits: false, + parentIsSupSub: false, + symbol: false, + name: funcName, + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +// Limits, not symbols +defineFunction({ + type: "op", + names: [ + "\\det", "\\gcd", "\\inf", "\\lim", "\\max", "\\min", "\\Pr", "\\sup", + ], + props: { + numArgs: 0, + }, + handler({parser, funcName}) { + return { + type: "op", + mode: parser.mode, + limits: true, + parentIsSupSub: false, + symbol: false, + name: funcName, + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +// No limits, symbols +defineFunction({ + type: "op", + names: [ + "\\int", "\\iint", "\\iiint", "\\oint", "\\oiint", "\\oiiint", + "\u222b", "\u222c", "\u222d", "\u222e", "\u222f", "\u2230", + ], + props: { + numArgs: 0, + }, + handler({parser, funcName}) { + let fName = funcName; + if (fName.length === 1) { + fName = singleCharIntegrals[fName]; + } + return { + type: "op", + mode: parser.mode, + limits: false, + parentIsSupSub: false, + symbol: true, + name: fName, + }; + }, + htmlBuilder, + mathmlBuilder, +}); diff --git a/frontend/node_modules/katex/src/functions/operatorname.js b/frontend/node_modules/katex/src/functions/operatorname.js new file mode 100644 index 0000000..fa401e7 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/operatorname.js @@ -0,0 +1,164 @@ +// @flow +import defineFunction, {ordargument} from "../defineFunction"; +import defineMacro from "../defineMacro"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import {SymbolNode} from "../domTree"; +import {assembleSupSub} from "./utils/assembleSupSub"; +import {assertNodeType} from "../parseNode"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +import type {HtmlBuilderSupSub, MathMLBuilder} from "../defineFunction"; +import type {ParseNode} from "../parseNode"; + +// NOTE: Unlike most `htmlBuilder`s, this one handles not only +// "operatorname", but also "supsub" since \operatorname* can +// affect super/subscripting. +export const htmlBuilder: HtmlBuilderSupSub<"operatorname"> = (grp, options) => { + // Operators are handled in the TeXbook pg. 443-444, rule 13(a). + let supGroup; + let subGroup; + let hasLimits = false; + let group: ParseNode<"operatorname">; + if (grp.type === "supsub") { + // If we have limits, supsub will pass us its group to handle. Pull + // out the superscript and subscript and set the group to the op in + // its base. + supGroup = grp.sup; + subGroup = grp.sub; + group = assertNodeType(grp.base, "operatorname"); + hasLimits = true; + } else { + group = assertNodeType(grp, "operatorname"); + } + + let base; + if (group.body.length > 0) { + const body = group.body.map(child => { + // $FlowFixMe: Check if the node has a string `text` property. + const childText = child.text; + if (typeof childText === "string") { + return { + type: "textord", + mode: child.mode, + text: childText, + }; + } else { + return child; + } + }); + + // Consolidate function names into symbol characters. + const expression = html.buildExpression( + body, options.withFont("mathrm"), true); + + for (let i = 0; i < expression.length; i++) { + const child = expression[i]; + if (child instanceof SymbolNode) { + // Per amsopn package, + // change minus to hyphen and \ast to asterisk + child.text = child.text.replace(/\u2212/, "-") + .replace(/\u2217/, "*"); + } + } + base = buildCommon.makeSpan(["mop"], expression, options); + } else { + base = buildCommon.makeSpan(["mop"], [], options); + } + + if (hasLimits) { + return assembleSupSub(base, supGroup, subGroup, options, + options.style, 0, 0); + + } else { + return base; + } +}; + +const mathmlBuilder: MathMLBuilder<"operatorname"> = (group, options) => { + // The steps taken here are similar to the html version. + let expression = mml.buildExpression( + group.body, options.withFont("mathrm")); + + // Is expression a string or has it something like a fraction? + let isAllString = true; // default + for (let i = 0; i < expression.length; i++) { + const node = expression[i]; + if (node instanceof mathMLTree.SpaceNode) { + // Do nothing + } else if (node instanceof mathMLTree.MathNode) { + switch (node.type) { + case "mi": + case "mn": + case "ms": + case "mspace": + case "mtext": + break; // Do nothing yet. + case "mo": { + const child = node.children[0]; + if (node.children.length === 1 && + child instanceof mathMLTree.TextNode) { + child.text = + child.text.replace(/\u2212/, "-") + .replace(/\u2217/, "*"); + } else { + isAllString = false; + } + break; + } + default: + isAllString = false; + } + } else { + isAllString = false; + } + } + + if (isAllString) { + // Write a single TextNode instead of multiple nested tags. + const word = expression.map(node => node.toText()).join(""); + expression = [new mathMLTree.TextNode(word)]; + } + + const identifier = new mathMLTree.MathNode("mi", expression); + identifier.setAttribute("mathvariant", "normal"); + + // \u2061 is the same as ⁡ + // ref: https://www.w3schools.com/charsets/ref_html_entities_a.asp + const operator = new mathMLTree.MathNode("mo", + [mml.makeText("\u2061", "text")]); + + if (group.parentIsSupSub) { + return new mathMLTree.MathNode("mrow", [identifier, operator]); + } else { + return mathMLTree.newDocumentFragment([identifier, operator]); + } +}; + +// \operatorname +// amsopn.dtx: \mathop{#1\kern\z@\operator@font#3}\newmcodes@ +defineFunction({ + type: "operatorname", + names: ["\\operatorname@", "\\operatornamewithlimits"], + props: { + numArgs: 1, + }, + handler: ({parser, funcName}, args) => { + const body = args[0]; + return { + type: "operatorname", + mode: parser.mode, + body: ordargument(body), + alwaysHandleSupSub: (funcName === "\\operatornamewithlimits"), + limits: false, + parentIsSupSub: false, + }; + }, + htmlBuilder, + mathmlBuilder, +}); + +defineMacro("\\operatorname", + "\\@ifstar\\operatornamewithlimits\\operatorname@"); diff --git a/frontend/node_modules/katex/src/functions/ordgroup.js b/frontend/node_modules/katex/src/functions/ordgroup.js new file mode 100644 index 0000000..f355578 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/ordgroup.js @@ -0,0 +1,22 @@ +// @flow +import {defineFunctionBuilders} from "../defineFunction"; +import buildCommon from "../buildCommon"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +defineFunctionBuilders({ + type: "ordgroup", + htmlBuilder(group, options) { + if (group.semisimple) { + return buildCommon.makeFragment( + html.buildExpression(group.body, options, false)); + } + return buildCommon.makeSpan( + ["mord"], html.buildExpression(group.body, options, true), options); + }, + mathmlBuilder(group, options) { + return mml.buildExpressionRow(group.body, options, true); + }, +}); + diff --git a/frontend/node_modules/katex/src/functions/overline.js b/frontend/node_modules/katex/src/functions/overline.js new file mode 100644 index 0000000..4c11c14 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/overline.js @@ -0,0 +1,59 @@ +// @flow +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +defineFunction({ + type: "overline", + names: ["\\overline"], + props: { + numArgs: 1, + }, + handler({parser}, args) { + const body = args[0]; + return { + type: "overline", + mode: parser.mode, + body, + }; + }, + htmlBuilder(group, options) { + // Overlines are handled in the TeXbook pg 443, Rule 9. + + // Build the inner group in the cramped style. + const innerGroup = html.buildGroup(group.body, + options.havingCrampedStyle()); + + // Create the line above the body + const line = buildCommon.makeLineSpan("overline-line", options); + + // Generate the vlist, with the appropriate kerns + const defaultRuleThickness = options.fontMetrics().defaultRuleThickness; + const vlist = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [ + {type: "elem", elem: innerGroup}, + {type: "kern", size: 3 * defaultRuleThickness}, + {type: "elem", elem: line}, + {type: "kern", size: defaultRuleThickness}, + ], + }, options); + + return buildCommon.makeSpan(["mord", "overline"], [vlist], options); + }, + mathmlBuilder(group, options) { + const operator = new mathMLTree.MathNode( + "mo", [new mathMLTree.TextNode("\u203e")]); + operator.setAttribute("stretchy", "true"); + + const node = new mathMLTree.MathNode( + "mover", + [mml.buildGroup(group.body, options), operator]); + node.setAttribute("accent", "true"); + + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/phantom.js b/frontend/node_modules/katex/src/functions/phantom.js new file mode 100644 index 0000000..9d54a0e --- /dev/null +++ b/frontend/node_modules/katex/src/functions/phantom.js @@ -0,0 +1,117 @@ +// @flow +import defineFunction, {ordargument} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +defineFunction({ + type: "phantom", + names: ["\\phantom"], + props: { + numArgs: 1, + allowedInText: true, + }, + handler: ({parser}, args) => { + const body = args[0]; + return { + type: "phantom", + mode: parser.mode, + body: ordargument(body), + }; + }, + htmlBuilder: (group, options) => { + const elements = html.buildExpression( + group.body, + options.withPhantom(), + false + ); + + // \phantom isn't supposed to affect the elements it contains. + // See "color" for more details. + return buildCommon.makeFragment(elements); + }, + mathmlBuilder: (group, options) => { + const inner = mml.buildExpression(group.body, options); + return new mathMLTree.MathNode("mphantom", inner); + }, +}); + +defineFunction({ + type: "hphantom", + names: ["\\hphantom"], + props: { + numArgs: 1, + allowedInText: true, + }, + handler: ({parser}, args) => { + const body = args[0]; + return { + type: "hphantom", + mode: parser.mode, + body, + }; + }, + htmlBuilder: (group, options) => { + let node = buildCommon.makeSpan( + [], [html.buildGroup(group.body, options.withPhantom())]); + node.height = 0; + node.depth = 0; + if (node.children) { + for (let i = 0; i < node.children.length; i++) { + node.children[i].height = 0; + node.children[i].depth = 0; + } + } + + // See smash for comment re: use of makeVList + node = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{type: "elem", elem: node}], + }, options); + + // For spacing, TeX treats \smash as a math group (same spacing as ord). + return buildCommon.makeSpan(["mord"], [node], options); + }, + mathmlBuilder: (group, options) => { + const inner = mml.buildExpression(ordargument(group.body), options); + const phantom = new mathMLTree.MathNode("mphantom", inner); + const node = new mathMLTree.MathNode("mpadded", [phantom]); + node.setAttribute("height", "0px"); + node.setAttribute("depth", "0px"); + return node; + }, +}); + +defineFunction({ + type: "vphantom", + names: ["\\vphantom"], + props: { + numArgs: 1, + allowedInText: true, + }, + handler: ({parser}, args) => { + const body = args[0]; + return { + type: "vphantom", + mode: parser.mode, + body, + }; + }, + htmlBuilder: (group, options) => { + const inner = buildCommon.makeSpan( + ["inner"], + [html.buildGroup(group.body, options.withPhantom())]); + const fix = buildCommon.makeSpan(["fix"], []); + return buildCommon.makeSpan( + ["mord", "rlap"], [inner, fix], options); + }, + mathmlBuilder: (group, options) => { + const inner = mml.buildExpression(ordargument(group.body), options); + const phantom = new mathMLTree.MathNode("mphantom", inner); + const node = new mathMLTree.MathNode("mpadded", [phantom]); + node.setAttribute("width", "0px"); + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/pmb.js b/frontend/node_modules/katex/src/functions/pmb.js new file mode 100644 index 0000000..2be1985 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/pmb.js @@ -0,0 +1,44 @@ +// @flow +import defineFunction, {ordargument} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; +import {binrelClass} from "./mclass"; + +import type {ParseNode} from "../parseNode"; + +// \pmb is a simulation of bold font. +// The version of \pmb in ambsy.sty works by typesetting three copies +// with small offsets. We use CSS text-shadow. +// It's a hack. Not as good as a real bold font. Better than nothing. + +defineFunction({ + type: "pmb", + names: ["\\pmb"], + props: { + numArgs: 1, + allowedInText: true, + }, + handler({parser}, args) { + return { + type: "pmb", + mode: parser.mode, + mclass: binrelClass(args[0]), + body: ordargument(args[0]), + }; + }, + htmlBuilder(group: ParseNode<"pmb">, options) { + const elements = html.buildExpression(group.body, options, true); + const node = buildCommon.makeSpan([group.mclass], elements, options); + node.style.textShadow = "0.02em 0.01em 0.04px"; + return node; + }, + mathmlBuilder(group: ParseNode<"pmb">, style) { + const inner = mml.buildExpression(group.body, style); + // Wrap with an element. + const node = new mathMLTree.MathNode("mstyle", inner); + node.setAttribute("style", "text-shadow: 0.02em 0.01em 0.04px"); + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/raisebox.js b/frontend/node_modules/katex/src/functions/raisebox.js new file mode 100644 index 0000000..c1a15ef --- /dev/null +++ b/frontend/node_modules/katex/src/functions/raisebox.js @@ -0,0 +1,46 @@ +// @flow +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import {assertNodeType} from "../parseNode"; +import {calculateSize} from "../units"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +// Box manipulation +defineFunction({ + type: "raisebox", + names: ["\\raisebox"], + props: { + numArgs: 2, + argTypes: ["size", "hbox"], + allowedInText: true, + }, + handler({parser}, args) { + const amount = assertNodeType(args[0], "size").value; + const body = args[1]; + return { + type: "raisebox", + mode: parser.mode, + dy: amount, + body, + }; + }, + htmlBuilder(group, options) { + const body = html.buildGroup(group.body, options); + const dy = calculateSize(group.dy, options); + return buildCommon.makeVList({ + positionType: "shift", + positionData: -dy, + children: [{type: "elem", elem: body}], + }, options); + }, + mathmlBuilder(group, options) { + const node = new mathMLTree.MathNode( + "mpadded", [mml.buildGroup(group.body, options)]); + const dy = group.dy.number + group.dy.unit; + node.setAttribute("voffset", dy); + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/relax.js b/frontend/node_modules/katex/src/functions/relax.js new file mode 100644 index 0000000..d3bab0f --- /dev/null +++ b/frontend/node_modules/katex/src/functions/relax.js @@ -0,0 +1,18 @@ +//@flow +import defineFunction from "../defineFunction"; + +defineFunction({ + type: "internal", + names: ["\\relax"], + props: { + numArgs: 0, + allowedInText: true, + allowedInArgument: true, + }, + handler({parser}) { + return { + type: "internal", + mode: parser.mode, + }; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/rule.js b/frontend/node_modules/katex/src/functions/rule.js new file mode 100644 index 0000000..1cf85ac --- /dev/null +++ b/frontend/node_modules/katex/src/functions/rule.js @@ -0,0 +1,77 @@ +// @flow +import buildCommon from "../buildCommon"; +import defineFunction from "../defineFunction"; +import mathMLTree from "../mathMLTree"; +import {assertNodeType} from "../parseNode"; +import {calculateSize, makeEm} from "../units"; + +defineFunction({ + type: "rule", + names: ["\\rule"], + props: { + numArgs: 2, + numOptionalArgs: 1, + allowedInText: true, + allowedInMath: true, + argTypes: ["size", "size", "size"], + }, + handler({parser}, args, optArgs) { + const shift = optArgs[0]; + const width = assertNodeType(args[0], "size"); + const height = assertNodeType(args[1], "size"); + return { + type: "rule", + mode: parser.mode, + shift: shift && assertNodeType(shift, "size").value, + width: width.value, + height: height.value, + }; + }, + htmlBuilder(group, options) { + // Make an empty span for the rule + const rule = buildCommon.makeSpan(["mord", "rule"], [], options); + + // Calculate the shift, width, and height of the rule, and account for units + const width = calculateSize(group.width, options); + const height = calculateSize(group.height, options); + const shift = (group.shift) ? calculateSize(group.shift, options) : 0; + + // Style the rule to the right size + rule.style.borderRightWidth = makeEm(width); + rule.style.borderTopWidth = makeEm(height); + rule.style.bottom = makeEm(shift); + + // Record the height and width + rule.width = width; + rule.height = height + shift; + rule.depth = -shift; + // Font size is the number large enough that the browser will + // reserve at least `absHeight` space above the baseline. + // The 1.125 factor was empirically determined + rule.maxFontSize = height * 1.125 * options.sizeMultiplier; + + return rule; + }, + mathmlBuilder(group, options) { + const width = calculateSize(group.width, options); + const height = calculateSize(group.height, options); + const shift = (group.shift) ? calculateSize(group.shift, options) : 0; + const color = options.color && options.getColor() || "black"; + + const rule = new mathMLTree.MathNode("mspace"); + rule.setAttribute("mathbackground", color); + rule.setAttribute("width", makeEm(width)); + rule.setAttribute("height", makeEm(height)); + + const wrapper = new mathMLTree.MathNode("mpadded", [rule]); + if (shift >= 0) { + wrapper.setAttribute("height", makeEm(shift)); + } else { + wrapper.setAttribute("height", makeEm(shift)); + wrapper.setAttribute("depth", makeEm(-shift)); + } + wrapper.setAttribute("voffset", makeEm(shift)); + + return wrapper; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/sizing.js b/frontend/node_modules/katex/src/functions/sizing.js new file mode 100644 index 0000000..4a87c98 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/sizing.js @@ -0,0 +1,91 @@ +// @flow +import buildCommon from "../buildCommon"; +import defineFunction from "../defineFunction"; +import mathMLTree from "../mathMLTree"; +import {makeEm} from "../units"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +import type Options from "../Options"; +import type {AnyParseNode} from "../parseNode"; +import type {HtmlBuilder} from "../defineFunction"; +import type {documentFragment as HtmlDocumentFragment} from "../domTree"; + +export function sizingGroup( + value: AnyParseNode[], + options: Options, + baseOptions: Options, +): HtmlDocumentFragment { + const inner = html.buildExpression(value, options, false); + const multiplier = options.sizeMultiplier / baseOptions.sizeMultiplier; + + // Add size-resetting classes to the inner list and set maxFontSize + // manually. Handle nested size changes. + for (let i = 0; i < inner.length; i++) { + const pos = inner[i].classes.indexOf("sizing"); + if (pos < 0) { + Array.prototype.push.apply(inner[i].classes, + options.sizingClasses(baseOptions)); + } else if (inner[i].classes[pos + 1] === "reset-size" + options.size) { + // This is a nested size change: e.g., inner[i] is the "b" in + // `\Huge a \small b`. Override the old size (the `reset-` class) + // but not the new size. + inner[i].classes[pos + 1] = "reset-size" + baseOptions.size; + } + + inner[i].height *= multiplier; + inner[i].depth *= multiplier; + } + + return buildCommon.makeFragment(inner); +} + +const sizeFuncs = [ + "\\tiny", "\\sixptsize", "\\scriptsize", "\\footnotesize", "\\small", + "\\normalsize", "\\large", "\\Large", "\\LARGE", "\\huge", "\\Huge", +]; + +export const htmlBuilder: HtmlBuilder<"sizing"> = (group, options) => { + // Handle sizing operators like \Huge. Real TeX doesn't actually allow + // these functions inside of math expressions, so we do some special + // handling. + const newOptions = options.havingSize(group.size); + return sizingGroup(group.body, newOptions, options); +}; + +defineFunction({ + type: "sizing", + names: sizeFuncs, + props: { + numArgs: 0, + allowedInText: true, + }, + handler: ({breakOnTokenText, funcName, parser}, args) => { + const body = parser.parseExpression(false, breakOnTokenText); + + return { + type: "sizing", + mode: parser.mode, + // Figure out what size to use based on the list of functions above + size: sizeFuncs.indexOf(funcName) + 1, + body, + }; + }, + htmlBuilder, + mathmlBuilder: (group, options) => { + const newOptions = options.havingSize(group.size); + const inner = mml.buildExpression(group.body, newOptions); + + const node = new mathMLTree.MathNode("mstyle", inner); + + // TODO(emily): This doesn't produce the correct size for nested size + // changes, because we don't keep state of what style we're currently + // in, so we can't reset the size to normal before changing it. Now + // that we're passing an options parameter we should be able to fix + // this. + node.setAttribute("mathsize", makeEm(newOptions.sizeMultiplier)); + + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/smash.js b/frontend/node_modules/katex/src/functions/smash.js new file mode 100644 index 0000000..90bf467 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/smash.js @@ -0,0 +1,110 @@ +// @flow +// smash, with optional [tb], as in AMS +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import {assertNodeType} from "../parseNode"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +defineFunction({ + type: "smash", + names: ["\\smash"], + props: { + numArgs: 1, + numOptionalArgs: 1, + allowedInText: true, + }, + handler: ({parser}, args, optArgs) => { + let smashHeight = false; + let smashDepth = false; + const tbArg = optArgs[0] && assertNodeType(optArgs[0], "ordgroup"); + if (tbArg) { + // Optional [tb] argument is engaged. + // ref: amsmath: \renewcommand{\smash}[1][tb]{% + // def\mb@t{\ht}\def\mb@b{\dp}\def\mb@tb{\ht\z@\z@\dp}% + let letter = ""; + for (let i = 0; i < tbArg.body.length; ++i) { + const node = tbArg.body[i]; + // $FlowFixMe: Not every node type has a `text` property. + letter = node.text; + if (letter === "t") { + smashHeight = true; + } else if (letter === "b") { + smashDepth = true; + } else { + smashHeight = false; + smashDepth = false; + break; + } + } + } else { + smashHeight = true; + smashDepth = true; + } + + const body = args[0]; + return { + type: "smash", + mode: parser.mode, + body, + smashHeight, + smashDepth, + }; + }, + htmlBuilder: (group, options) => { + const node = buildCommon.makeSpan( + [], [html.buildGroup(group.body, options)]); + + if (!group.smashHeight && !group.smashDepth) { + return node; + } + + if (group.smashHeight) { + node.height = 0; + // In order to influence makeVList, we have to reset the children. + if (node.children) { + for (let i = 0; i < node.children.length; i++) { + node.children[i].height = 0; + } + } + } + + if (group.smashDepth) { + node.depth = 0; + if (node.children) { + for (let i = 0; i < node.children.length; i++) { + node.children[i].depth = 0; + } + } + } + + // At this point, we've reset the TeX-like height and depth values. + // But the span still has an HTML line height. + // makeVList applies "display: table-cell", which prevents the browser + // from acting on that line height. So we'll call makeVList now. + + const smashedNode = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [{type: "elem", elem: node}], + }, options); + + // For spacing, TeX treats \hphantom as a math group (same spacing as ord). + return buildCommon.makeSpan(["mord"], [smashedNode], options); + }, + mathmlBuilder: (group, options) => { + const node = new mathMLTree.MathNode( + "mpadded", [mml.buildGroup(group.body, options)]); + + if (group.smashHeight) { + node.setAttribute("height", "0px"); + } + + if (group.smashDepth) { + node.setAttribute("depth", "0px"); + } + + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/sqrt.js b/frontend/node_modules/katex/src/functions/sqrt.js new file mode 100644 index 0000000..95edb73 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/sqrt.js @@ -0,0 +1,125 @@ +// @flow +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import delimiter from "../delimiter"; +import Style from "../Style"; +import {makeEm} from "../units"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +defineFunction({ + type: "sqrt", + names: ["\\sqrt"], + props: { + numArgs: 1, + numOptionalArgs: 1, + }, + handler({parser}, args, optArgs) { + const index = optArgs[0]; + const body = args[0]; + return { + type: "sqrt", + mode: parser.mode, + body, + index, + }; + }, + htmlBuilder(group, options) { + // Square roots are handled in the TeXbook pg. 443, Rule 11. + + // First, we do the same steps as in overline to build the inner group + // and line + let inner = html.buildGroup(group.body, options.havingCrampedStyle()); + if (inner.height === 0) { + // Render a small surd. + inner.height = options.fontMetrics().xHeight; + } + + // Some groups can return document fragments. Handle those by wrapping + // them in a span. + inner = buildCommon.wrapFragment(inner, options); + + // Calculate the minimum size for the \surd delimiter + const metrics = options.fontMetrics(); + const theta = metrics.defaultRuleThickness; + + let phi = theta; + if (options.style.id < Style.TEXT.id) { + phi = options.fontMetrics().xHeight; + } + + // Calculate the clearance between the body and line + let lineClearance = theta + phi / 4; + + const minDelimiterHeight = (inner.height + inner.depth + + lineClearance + theta); + + // Create a sqrt SVG of the required minimum size + const {span: img, ruleWidth, advanceWidth} = + delimiter.sqrtImage(minDelimiterHeight, options); + + const delimDepth = img.height - ruleWidth; + + // Adjust the clearance based on the delimiter size + if (delimDepth > inner.height + inner.depth + lineClearance) { + lineClearance = + (lineClearance + delimDepth - inner.height - inner.depth) / 2; + } + + // Shift the sqrt image + const imgShift = img.height - inner.height - lineClearance - ruleWidth; + + inner.style.paddingLeft = makeEm(advanceWidth); + + // Overlay the image and the argument. + const body = buildCommon.makeVList({ + positionType: "firstBaseline", + children: [ + {type: "elem", elem: inner, wrapperClasses: ["svg-align"]}, + {type: "kern", size: -(inner.height + imgShift)}, + {type: "elem", elem: img}, + {type: "kern", size: ruleWidth}, + ], + }, options); + + if (!group.index) { + return buildCommon.makeSpan(["mord", "sqrt"], [body], options); + } else { + // Handle the optional root index + + // The index is always in scriptscript style + const newOptions = options.havingStyle(Style.SCRIPTSCRIPT); + const rootm = html.buildGroup(group.index, newOptions, options); + + // The amount the index is shifted by. This is taken from the TeX + // source, in the definition of `\r@@t`. + const toShift = 0.6 * (body.height - body.depth); + + // Build a VList with the superscript shifted up correctly + const rootVList = buildCommon.makeVList({ + positionType: "shift", + positionData: -toShift, + children: [{type: "elem", elem: rootm}], + }, options); + // Add a class surrounding it so we can add on the appropriate + // kerning + const rootVListWrap = buildCommon.makeSpan(["root"], [rootVList]); + + return buildCommon.makeSpan(["mord", "sqrt"], + [rootVListWrap, body], options); + } + }, + mathmlBuilder(group, options) { + const {body, index} = group; + return index ? + new mathMLTree.MathNode( + "mroot", [ + mml.buildGroup(body, options), + mml.buildGroup(index, options), + ]) : + new mathMLTree.MathNode( + "msqrt", [mml.buildGroup(body, options)]); + }, +}); diff --git a/frontend/node_modules/katex/src/functions/styling.js b/frontend/node_modules/katex/src/functions/styling.js new file mode 100644 index 0000000..65c0399 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/styling.js @@ -0,0 +1,73 @@ +// @flow +import defineFunction from "../defineFunction"; +import mathMLTree from "../mathMLTree"; +import Style from "../Style"; +import {sizingGroup} from "./sizing"; + +import * as mml from "../buildMathML"; + +const styleMap = { + "display": Style.DISPLAY, + "text": Style.TEXT, + "script": Style.SCRIPT, + "scriptscript": Style.SCRIPTSCRIPT, +}; + +defineFunction({ + type: "styling", + names: [ + "\\displaystyle", "\\textstyle", "\\scriptstyle", + "\\scriptscriptstyle", + ], + props: { + numArgs: 0, + allowedInText: true, + primitive: true, + }, + handler({breakOnTokenText, funcName, parser}, args) { + // parse out the implicit body + const body = parser.parseExpression(true, breakOnTokenText); + + // TODO: Refactor to avoid duplicating styleMap in multiple places (e.g. + // here and in buildHTML and de-dupe the enumeration of all the styles). + // $FlowFixMe: The names above exactly match the styles. + const style: StyleStr = funcName.slice(1, funcName.length - 5); + return { + type: "styling", + mode: parser.mode, + // Figure out what style to use by pulling out the style from + // the function name + style, + body, + }; + }, + htmlBuilder(group, options) { + // Style changes are handled in the TeXbook on pg. 442, Rule 3. + const newStyle = styleMap[group.style]; + const newOptions = options.havingStyle(newStyle).withFont(''); + return sizingGroup(group.body, newOptions, options); + }, + mathmlBuilder(group, options) { + // Figure out what style we're changing to. + const newStyle = styleMap[group.style]; + const newOptions = options.havingStyle(newStyle); + + const inner = mml.buildExpression(group.body, newOptions); + + const node = new mathMLTree.MathNode("mstyle", inner); + + const styleAttributes = { + "display": ["0", "true"], + "text": ["0", "false"], + "script": ["1", "false"], + "scriptscript": ["2", "false"], + }; + + const attr = styleAttributes[group.style]; + + node.setAttribute("scriptlevel", attr[0]); + node.setAttribute("displaystyle", attr[1]); + + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/supsub.js b/frontend/node_modules/katex/src/functions/supsub.js new file mode 100644 index 0000000..6704361 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/supsub.js @@ -0,0 +1,267 @@ +// @flow +import {defineFunctionBuilders} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import {SymbolNode} from "../domTree"; +import mathMLTree from "../mathMLTree"; +import utils from "../utils"; +import {makeEm} from "../units"; +import Style from "../Style"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; +import * as accent from "./accent"; +import * as horizBrace from "./horizBrace"; +import * as op from "./op"; +import * as operatorname from "./operatorname"; + +import type Options from "../Options"; +import type {ParseNode} from "../parseNode"; +import type {HtmlBuilder} from "../defineFunction"; +import type {MathNodeType} from "../mathMLTree"; + +/** + * Sometimes, groups perform special rules when they have superscripts or + * subscripts attached to them. This function lets the `supsub` group know that + * Sometimes, groups perform special rules when they have superscripts or + * its inner element should handle the superscripts and subscripts instead of + * handling them itself. + */ +const htmlBuilderDelegate = function( + group: ParseNode<"supsub">, + options: Options, +): ?HtmlBuilder<*> { + const base = group.base; + if (!base) { + return null; + } else if (base.type === "op") { + // Operators handle supsubs differently when they have limits + // (e.g. `\displaystyle\sum_2^3`) + const delegate = base.limits && + (options.style.size === Style.DISPLAY.size || + base.alwaysHandleSupSub); + return delegate ? op.htmlBuilder : null; + } else if (base.type === "operatorname") { + const delegate = base.alwaysHandleSupSub && + (options.style.size === Style.DISPLAY.size || base.limits); + return delegate ? operatorname.htmlBuilder : null; + } else if (base.type === "accent") { + return utils.isCharacterBox(base.base) ? accent.htmlBuilder : null; + } else if (base.type === "horizBrace") { + const isSup = !group.sub; + return isSup === base.isOver ? horizBrace.htmlBuilder : null; + } else { + return null; + } +}; + +// Super scripts and subscripts, whose precise placement can depend on other +// functions that precede them. +defineFunctionBuilders({ + type: "supsub", + htmlBuilder(group, options) { + // Superscript and subscripts are handled in the TeXbook on page + // 445-446, rules 18(a-f). + + // Here is where we defer to the inner group if it should handle + // superscripts and subscripts itself. + const builderDelegate = htmlBuilderDelegate(group, options); + if (builderDelegate) { + return builderDelegate(group, options); + } + + const {base: valueBase, sup: valueSup, sub: valueSub} = group; + const base = html.buildGroup(valueBase, options); + let supm; + let subm; + + const metrics = options.fontMetrics(); + + // Rule 18a + let supShift = 0; + let subShift = 0; + + const isCharacterBox = valueBase && utils.isCharacterBox(valueBase); + if (valueSup) { + const newOptions = options.havingStyle(options.style.sup()); + supm = html.buildGroup(valueSup, newOptions, options); + if (!isCharacterBox) { + supShift = base.height - newOptions.fontMetrics().supDrop + * newOptions.sizeMultiplier / options.sizeMultiplier; + } + } + + if (valueSub) { + const newOptions = options.havingStyle(options.style.sub()); + subm = html.buildGroup(valueSub, newOptions, options); + if (!isCharacterBox) { + subShift = base.depth + newOptions.fontMetrics().subDrop + * newOptions.sizeMultiplier / options.sizeMultiplier; + } + } + + // Rule 18c + let minSupShift; + if (options.style === Style.DISPLAY) { + minSupShift = metrics.sup1; + } else if (options.style.cramped) { + minSupShift = metrics.sup3; + } else { + minSupShift = metrics.sup2; + } + + // scriptspace is a font-size-independent size, so scale it + // appropriately for use as the marginRight. + const multiplier = options.sizeMultiplier; + const marginRight = makeEm((0.5 / metrics.ptPerEm) / multiplier); + + let marginLeft = null; + if (subm) { + // Subscripts shouldn't be shifted by the base's italic correction. + // Account for that by shifting the subscript back the appropriate + // amount. Note we only do this when the base is a single symbol. + const isOiint = + group.base && group.base.type === "op" && group.base.name && + (group.base.name === "\\oiint" || group.base.name === "\\oiiint"); + if (base instanceof SymbolNode || isOiint) { + // $FlowFixMe + marginLeft = makeEm(-base.italic); + } + } + + let supsub; + if (supm && subm) { + supShift = Math.max( + supShift, minSupShift, supm.depth + 0.25 * metrics.xHeight); + subShift = Math.max(subShift, metrics.sub2); + + const ruleWidth = metrics.defaultRuleThickness; + + // Rule 18e + const maxWidth = 4 * ruleWidth; + if ((supShift - supm.depth) - (subm.height - subShift) < maxWidth) { + subShift = maxWidth - (supShift - supm.depth) + subm.height; + const psi = 0.8 * metrics.xHeight - (supShift - supm.depth); + if (psi > 0) { + supShift += psi; + subShift -= psi; + } + } + + const vlistElem = [ + {type: "elem", elem: subm, shift: subShift, marginRight, + marginLeft}, + {type: "elem", elem: supm, shift: -supShift, marginRight}, + ]; + + supsub = buildCommon.makeVList({ + positionType: "individualShift", + children: vlistElem, + }, options); + } else if (subm) { + // Rule 18b + subShift = Math.max( + subShift, metrics.sub1, + subm.height - 0.8 * metrics.xHeight); + + const vlistElem = + [{type: "elem", elem: subm, marginLeft, marginRight}]; + + supsub = buildCommon.makeVList({ + positionType: "shift", + positionData: subShift, + children: vlistElem, + }, options); + } else if (supm) { + // Rule 18c, d + supShift = Math.max(supShift, minSupShift, + supm.depth + 0.25 * metrics.xHeight); + + supsub = buildCommon.makeVList({ + positionType: "shift", + positionData: -supShift, + children: [{type: "elem", elem: supm, marginRight}], + }, options); + } else { + throw new Error("supsub must have either sup or sub."); + } + + // Wrap the supsub vlist in a span.msupsub to reset text-align. + const mclass = html.getTypeOfDomTree(base, "right") || "mord"; + return buildCommon.makeSpan([mclass], + [base, buildCommon.makeSpan(["msupsub"], [supsub])], + options); + }, + mathmlBuilder(group, options) { + // Is the inner group a relevant horizontal brace? + let isBrace = false; + let isOver; + let isSup; + + if (group.base && group.base.type === "horizBrace") { + isSup = !!group.sup; + if (isSup === group.base.isOver) { + isBrace = true; + isOver = group.base.isOver; + } + } + + if (group.base && + (group.base.type === "op" || group.base.type === "operatorname")) { + group.base.parentIsSupSub = true; + } + + const children = [mml.buildGroup(group.base, options)]; + + if (group.sub) { + children.push(mml.buildGroup(group.sub, options)); + } + + if (group.sup) { + children.push(mml.buildGroup(group.sup, options)); + } + + let nodeType: MathNodeType; + if (isBrace) { + nodeType = (isOver ? "mover" : "munder"); + } else if (!group.sub) { + const base = group.base; + if (base && base.type === "op" && base.limits && + (options.style === Style.DISPLAY || base.alwaysHandleSupSub)) { + nodeType = "mover"; + } else if (base && base.type === "operatorname" && + base.alwaysHandleSupSub && + (base.limits || options.style === Style.DISPLAY)) { + nodeType = "mover"; + } else { + nodeType = "msup"; + } + } else if (!group.sup) { + const base = group.base; + if (base && base.type === "op" && base.limits && + (options.style === Style.DISPLAY || base.alwaysHandleSupSub)) { + nodeType = "munder"; + } else if (base && base.type === "operatorname" && + base.alwaysHandleSupSub && + (base.limits || options.style === Style.DISPLAY)) { + nodeType = "munder"; + } else { + nodeType = "msub"; + } + } else { + const base = group.base; + if (base && base.type === "op" && base.limits && + options.style === Style.DISPLAY) { + nodeType = "munderover"; + } else if (base && base.type === "operatorname" && + base.alwaysHandleSupSub && + (options.style === Style.DISPLAY || base.limits)) { + nodeType = "munderover"; + } else { + nodeType = "msubsup"; + } + } + + return new mathMLTree.MathNode(nodeType, children); + }, +}); + diff --git a/frontend/node_modules/katex/src/functions/symbolsOp.js b/frontend/node_modules/katex/src/functions/symbolsOp.js new file mode 100644 index 0000000..b4b7ec8 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/symbolsOp.js @@ -0,0 +1,34 @@ +// @flow +import {defineFunctionBuilders} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; + +import * as mml from "../buildMathML"; + +// Operator ParseNodes created in Parser.js from symbol Groups in src/symbols.js. + +defineFunctionBuilders({ + type: "atom", + htmlBuilder(group, options) { + return buildCommon.mathsym( + group.text, group.mode, options, ["m" + group.family]); + }, + mathmlBuilder(group, options) { + const node = new mathMLTree.MathNode( + "mo", [mml.makeText(group.text, group.mode)]); + if (group.family === "bin") { + const variant = mml.getVariant(group, options); + if (variant === "bold-italic") { + node.setAttribute("mathvariant", variant); + } + } else if (group.family === "punct") { + node.setAttribute("separator", "true"); + } else if (group.family === "open" || group.family === "close") { + // Delims built here should not stretch vertically. + // See delimsizing.js for stretchy delims. + node.setAttribute("stretchy", "false"); + } + return node; + }, +}); + diff --git a/frontend/node_modules/katex/src/functions/symbolsOrd.js b/frontend/node_modules/katex/src/functions/symbolsOrd.js new file mode 100644 index 0000000..db6ed0c --- /dev/null +++ b/frontend/node_modules/katex/src/functions/symbolsOrd.js @@ -0,0 +1,62 @@ +// @flow +import {defineFunctionBuilders} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; + +import * as mml from "../buildMathML"; + +import type {ParseNode} from "../parseNode"; + +// "mathord" and "textord" ParseNodes created in Parser.js from symbol Groups in +// src/symbols.js. + +const defaultVariant: {[string]: string} = { + "mi": "italic", + "mn": "normal", + "mtext": "normal", +}; + +defineFunctionBuilders({ + type: "mathord", + htmlBuilder(group, options) { + return buildCommon.makeOrd(group, options, "mathord"); + }, + mathmlBuilder(group: ParseNode<"mathord">, options) { + const node = new mathMLTree.MathNode( + "mi", + [mml.makeText(group.text, group.mode, options)]); + + const variant = mml.getVariant(group, options) || "italic"; + if (variant !== defaultVariant[node.type]) { + node.setAttribute("mathvariant", variant); + } + return node; + }, +}); + +defineFunctionBuilders({ + type: "textord", + htmlBuilder(group, options) { + return buildCommon.makeOrd(group, options, "textord"); + }, + mathmlBuilder(group: ParseNode<"textord">, options) { + const text = mml.makeText(group.text, group.mode, options); + const variant = mml.getVariant(group, options) || "normal"; + + let node; + if (group.mode === 'text') { + node = new mathMLTree.MathNode("mtext", [text]); + } else if (/[0-9]/.test(group.text)) { + node = new mathMLTree.MathNode("mn", [text]); + } else if (group.text === "\\prime") { + node = new mathMLTree.MathNode("mo", [text]); + } else { + node = new mathMLTree.MathNode("mi", [text]); + } + if (variant !== defaultVariant[node.type]) { + node.setAttribute("mathvariant", variant); + } + + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/symbolsSpacing.js b/frontend/node_modules/katex/src/functions/symbolsSpacing.js new file mode 100644 index 0000000..b4ddf53 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/symbolsSpacing.js @@ -0,0 +1,73 @@ +// @flow +import {defineFunctionBuilders} from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import ParseError from "../ParseError"; + +// A map of CSS-based spacing functions to their CSS class. +const cssSpace: {[string]: string} = { + "\\nobreak": "nobreak", + "\\allowbreak": "allowbreak", +}; + +// A lookup table to determine whether a spacing function/symbol should be +// treated like a regular space character. If a symbol or command is a key +// in this table, then it should be a regular space character. Furthermore, +// the associated value may have a `className` specifying an extra CSS class +// to add to the created `span`. +const regularSpace: {[string]: { className?: string }} = { + " ": {}, + "\\ ": {}, + "~": { + className: "nobreak", + }, + "\\space": {}, + "\\nobreakspace": { + className: "nobreak", + }, +}; + +// ParseNode<"spacing"> created in Parser.js from the "spacing" symbol Groups in +// src/symbols.js. +defineFunctionBuilders({ + type: "spacing", + htmlBuilder(group, options) { + if (regularSpace.hasOwnProperty(group.text)) { + const className = regularSpace[group.text].className || ""; + // Spaces are generated by adding an actual space. Each of these + // things has an entry in the symbols table, so these will be turned + // into appropriate outputs. + if (group.mode === "text") { + const ord = buildCommon.makeOrd(group, options, "textord"); + ord.classes.push(className); + return ord; + } else { + return buildCommon.makeSpan(["mspace", className], + [buildCommon.mathsym(group.text, group.mode, options)], + options); + } + } else if (cssSpace.hasOwnProperty(group.text)) { + // Spaces based on just a CSS class. + return buildCommon.makeSpan( + ["mspace", cssSpace[group.text]], + [], options); + } else { + throw new ParseError(`Unknown type of space "${group.text}"`); + } + }, + mathmlBuilder(group, options) { + let node; + + if (regularSpace.hasOwnProperty(group.text)) { + node = new mathMLTree.MathNode( + "mtext", [new mathMLTree.TextNode("\u00a0")]); + } else if (cssSpace.hasOwnProperty(group.text)) { + // CSS-based MathML spaces (\nobreak, \allowbreak) are ignored + return new mathMLTree.MathNode("mspace"); + } else { + throw new ParseError(`Unknown type of space "${group.text}"`); + } + + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/tag.js b/frontend/node_modules/katex/src/functions/tag.js new file mode 100644 index 0000000..dc1df24 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/tag.js @@ -0,0 +1,40 @@ +// @flow +import {defineFunctionBuilders} from "../defineFunction"; +import mathMLTree from "../mathMLTree"; + +import * as mml from "../buildMathML"; + +const pad = () => { + const padNode = new mathMLTree.MathNode("mtd", []); + padNode.setAttribute("width", "50%"); + return padNode; +}; + +defineFunctionBuilders({ + type: "tag", + mathmlBuilder(group, options) { + const table = new mathMLTree.MathNode("mtable", [ + new mathMLTree.MathNode("mtr", [ + pad(), + new mathMLTree.MathNode("mtd", [ + mml.buildExpressionRow(group.body, options), + ]), + pad(), + new mathMLTree.MathNode("mtd", [ + mml.buildExpressionRow(group.tag, options), + ]), + ]), + ]); + table.setAttribute("width", "100%"); + return table; + + // TODO: Left-aligned tags. + // Currently, the group and options passed here do not contain + // enough info to set tag alignment. `leqno` is in Settings but it is + // not passed to Options. On the HTML side, leqno is + // set by a CSS class applied in buildTree.js. That would have worked + // in MathML if browsers supported . Since they don't, we + // need to rewrite the way this function is called. + }, +}); + diff --git a/frontend/node_modules/katex/src/functions/text.js b/frontend/node_modules/katex/src/functions/text.js new file mode 100644 index 0000000..9d3c674 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/text.js @@ -0,0 +1,76 @@ +// @flow +import defineFunction, {ordargument} from "../defineFunction"; +import buildCommon from "../buildCommon"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +// Non-mathy text, possibly in a font +const textFontFamilies = { + "\\text": undefined, "\\textrm": "textrm", "\\textsf": "textsf", + "\\texttt": "texttt", "\\textnormal": "textrm", +}; + +const textFontWeights = { + "\\textbf": "textbf", + "\\textmd": "textmd", +}; + +const textFontShapes = { + "\\textit": "textit", + "\\textup": "textup", +}; + +const optionsWithFont = (group, options) => { + const font = group.font; + // Checks if the argument is a font family or a font style. + if (!font) { + return options; + } else if (textFontFamilies[font]) { + return options.withTextFontFamily(textFontFamilies[font]); + } else if (textFontWeights[font]) { + return options.withTextFontWeight(textFontWeights[font]); + } else if (font === "\\emph") { + return options.fontShape === "textit" ? + options.withTextFontShape("textup") : + options.withTextFontShape("textit"); + } + + return options.withTextFontShape(textFontShapes[font]); +}; + +defineFunction({ + type: "text", + names: [ + // Font families + "\\text", "\\textrm", "\\textsf", "\\texttt", "\\textnormal", + // Font weights + "\\textbf", "\\textmd", + // Font Shapes + "\\textit", "\\textup", "\\emph", + ], + props: { + numArgs: 1, + argTypes: ["text"], + allowedInArgument: true, + allowedInText: true, + }, + handler({parser, funcName}, args) { + const body = args[0]; + return { + type: "text", + mode: parser.mode, + body: ordargument(body), + font: funcName, + }; + }, + htmlBuilder(group, options) { + const newOptions = optionsWithFont(group, options); + const inner = html.buildExpression(group.body, newOptions, true); + return buildCommon.makeSpan(["mord", "text"], inner, newOptions); + }, + mathmlBuilder(group, options) { + const newOptions = optionsWithFont(group, options); + return mml.buildExpressionRow(group.body, newOptions); + }, +}); diff --git a/frontend/node_modules/katex/src/functions/underline.js b/frontend/node_modules/katex/src/functions/underline.js new file mode 100644 index 0000000..36c1927 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/underline.js @@ -0,0 +1,58 @@ +// @flow +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +defineFunction({ + type: "underline", + names: ["\\underline"], + props: { + numArgs: 1, + allowedInText: true, + }, + handler({parser}, args) { + return { + type: "underline", + mode: parser.mode, + body: args[0], + }; + }, + htmlBuilder(group, options) { + // Underlines are handled in the TeXbook pg 443, Rule 10. + // Build the inner group. + const innerGroup = html.buildGroup(group.body, options); + + // Create the line to go below the body + const line = buildCommon.makeLineSpan("underline-line", options); + + // Generate the vlist, with the appropriate kerns + const defaultRuleThickness = options.fontMetrics().defaultRuleThickness; + const vlist = buildCommon.makeVList({ + positionType: "top", + positionData: innerGroup.height, + children: [ + {type: "kern", size: defaultRuleThickness}, + {type: "elem", elem: line}, + {type: "kern", size: 3 * defaultRuleThickness}, + {type: "elem", elem: innerGroup}, + ], + }, options); + + return buildCommon.makeSpan(["mord", "underline"], [vlist], options); + }, + mathmlBuilder(group, options) { + const operator = new mathMLTree.MathNode( + "mo", [new mathMLTree.TextNode("\u203e")]); + operator.setAttribute("stretchy", "true"); + + const node = new mathMLTree.MathNode( + "munder", + [mml.buildGroup(group.body, options), operator]); + node.setAttribute("accentunder", "true"); + + return node; + }, +}); diff --git a/frontend/node_modules/katex/src/functions/utils/assembleSupSub.js b/frontend/node_modules/katex/src/functions/utils/assembleSupSub.js new file mode 100644 index 0000000..107c93d --- /dev/null +++ b/frontend/node_modules/katex/src/functions/utils/assembleSupSub.js @@ -0,0 +1,120 @@ +// @flow +import buildCommon from "../../buildCommon"; +import * as html from "../../buildHTML"; +import utils from "../../utils"; +import type {StyleInterface} from "../../Style"; +import type Options from "../../Options"; +import type {DomSpan, SymbolNode} from "../../domTree"; +import type {AnyParseNode} from "../../parseNode"; +import {makeEm} from "../../units"; + +// For an operator with limits, assemble the base, sup, and sub into a span. + +export const assembleSupSub = ( + base: DomSpan | SymbolNode, + supGroup: ?AnyParseNode, + subGroup: ?AnyParseNode, + options: Options, + style: StyleInterface, + slant: number, + baseShift: number, +): DomSpan => { + base = buildCommon.makeSpan([], [base]); + const subIsSingleCharacter = subGroup && utils.isCharacterBox(subGroup); + let sub; + let sup; + // We manually have to handle the superscripts and subscripts. This, + // aside from the kern calculations, is copied from supsub. + if (supGroup) { + const elem = html.buildGroup( + supGroup, options.havingStyle(style.sup()), options); + + sup = { + elem, + kern: Math.max( + options.fontMetrics().bigOpSpacing1, + options.fontMetrics().bigOpSpacing3 - elem.depth), + }; + } + + if (subGroup) { + const elem = html.buildGroup( + subGroup, options.havingStyle(style.sub()), options); + + sub = { + elem, + kern: Math.max( + options.fontMetrics().bigOpSpacing2, + options.fontMetrics().bigOpSpacing4 - elem.height), + }; + } + + // Build the final group as a vlist of the possible subscript, base, + // and possible superscript. + let finalGroup; + if (sup && sub) { + const bottom = options.fontMetrics().bigOpSpacing5 + + sub.elem.height + sub.elem.depth + + sub.kern + + base.depth + baseShift; + + finalGroup = buildCommon.makeVList({ + positionType: "bottom", + positionData: bottom, + children: [ + {type: "kern", size: options.fontMetrics().bigOpSpacing5}, + {type: "elem", elem: sub.elem, marginLeft: makeEm(-slant)}, + {type: "kern", size: sub.kern}, + {type: "elem", elem: base}, + {type: "kern", size: sup.kern}, + {type: "elem", elem: sup.elem, marginLeft: makeEm(slant)}, + {type: "kern", size: options.fontMetrics().bigOpSpacing5}, + ], + }, options); + } else if (sub) { + const top = base.height - baseShift; + + // Shift the limits by the slant of the symbol. Note + // that we are supposed to shift the limits by 1/2 of the slant, + // but since we are centering the limits adding a full slant of + // margin will shift by 1/2 that. + finalGroup = buildCommon.makeVList({ + positionType: "top", + positionData: top, + children: [ + {type: "kern", size: options.fontMetrics().bigOpSpacing5}, + {type: "elem", elem: sub.elem, marginLeft: makeEm(-slant)}, + {type: "kern", size: sub.kern}, + {type: "elem", elem: base}, + ], + }, options); + } else if (sup) { + const bottom = base.depth + baseShift; + + finalGroup = buildCommon.makeVList({ + positionType: "bottom", + positionData: bottom, + children: [ + {type: "elem", elem: base}, + {type: "kern", size: sup.kern}, + {type: "elem", elem: sup.elem, marginLeft: makeEm(slant)}, + {type: "kern", size: options.fontMetrics().bigOpSpacing5}, + ], + }, options); + } else { + // This case probably shouldn't occur (this would mean the + // supsub was sending us a group with no superscript or + // subscript) but be safe. + return base; + } + + const parts = [finalGroup]; + if (sub && slant !== 0 && !subIsSingleCharacter) { + // A negative margin-left was applied to the lower limit. + // Avoid an overlap by placing a spacer on the left on the group. + const spacer = buildCommon.makeSpan(["mspace"], [], options); + spacer.style.marginRight = makeEm(slant); + parts.unshift(spacer); + } + return buildCommon.makeSpan(["mop", "op-limits"], parts, options); +}; diff --git a/frontend/node_modules/katex/src/functions/vcenter.js b/frontend/node_modules/katex/src/functions/vcenter.js new file mode 100644 index 0000000..3afef63 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/vcenter.js @@ -0,0 +1,44 @@ +// @flow +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; + +import * as html from "../buildHTML"; +import * as mml from "../buildMathML"; + +// \vcenter: Vertically center the argument group on the math axis. + +defineFunction({ + type: "vcenter", + names: ["\\vcenter"], + props: { + numArgs: 1, + argTypes: ["original"], // In LaTeX, \vcenter can act only on a box. + allowedInText: false, + }, + handler({parser}, args) { + return { + type: "vcenter", + mode: parser.mode, + body: args[0], + }; + }, + htmlBuilder(group, options) { + const body = html.buildGroup(group.body, options); + const axisHeight = options.fontMetrics().axisHeight; + const dy = 0.5 * ((body.height - axisHeight) - (body.depth + axisHeight)); + return buildCommon.makeVList({ + positionType: "shift", + positionData: dy, + children: [{type: "elem", elem: body}], + }, options); + }, + mathmlBuilder(group, options) { + // There is no way to do this in MathML. + // Write a class as a breadcrumb in case some post-processor wants + // to perform a vcenter adjustment. + return new mathMLTree.MathNode( + "mpadded", [mml.buildGroup(group.body, options)], ["vcenter"]); + }, +}); + diff --git a/frontend/node_modules/katex/src/functions/verb.js b/frontend/node_modules/katex/src/functions/verb.js new file mode 100644 index 0000000..321e585 --- /dev/null +++ b/frontend/node_modules/katex/src/functions/verb.js @@ -0,0 +1,58 @@ +// @flow +import defineFunction from "../defineFunction"; +import buildCommon from "../buildCommon"; +import mathMLTree from "../mathMLTree"; +import ParseError from "../ParseError"; + +import type {ParseNode} from "../parseNode"; + +defineFunction({ + type: "verb", + names: ["\\verb"], + props: { + numArgs: 0, + allowedInText: true, + }, + handler(context, args, optArgs) { + // \verb and \verb* are dealt with directly in Parser.js. + // If we end up here, it's because of a failure to match the two delimiters + // in the regex in Lexer.js. LaTeX raises the following error when \verb is + // terminated by end of line (or file). + throw new ParseError( + "\\verb ended by end of line instead of matching delimiter"); + }, + htmlBuilder(group, options) { + const text = makeVerb(group); + const body = []; + // \verb enters text mode and therefore is sized like \textstyle + const newOptions = options.havingStyle(options.style.text()); + for (let i = 0; i < text.length; i++) { + let c = text[i]; + if (c === '~') { + c = '\\textasciitilde'; + } + body.push(buildCommon.makeSymbol(c, "Typewriter-Regular", + group.mode, newOptions, ["mord", "texttt"])); + } + return buildCommon.makeSpan( + ["mord", "text"].concat(newOptions.sizingClasses(options)), + buildCommon.tryCombineChars(body), + newOptions, + ); + }, + mathmlBuilder(group, options) { + const text = new mathMLTree.TextNode(makeVerb(group)); + const node = new mathMLTree.MathNode("mtext", [text]); + node.setAttribute("mathvariant", "monospace"); + return node; + }, +}); + +/** + * Converts verb group into body string. + * + * \verb* replaces each space with an open box \u2423 + * \verb replaces each space with a no-break space \xA0 + */ +const makeVerb = (group: ParseNode<"verb">): string => + group.body.replace(/ /g, group.star ? '\u2423' : '\xA0'); diff --git a/frontend/node_modules/katex/src/macros.js b/frontend/node_modules/katex/src/macros.js new file mode 100644 index 0000000..182efa6 --- /dev/null +++ b/frontend/node_modules/katex/src/macros.js @@ -0,0 +1,1033 @@ +// @flow +/** + * Predefined macros for KaTeX. + * This can be used to define some commands in terms of others. + */ + +// Export global macros object from defineMacro +import defineMacro, {_macros} from "./defineMacro"; +const macros = _macros; +export default macros; + +import fontMetricsData from "./fontMetricsData"; +import functions from "./functions"; +import symbols from "./symbols"; +import utils from "./utils"; +import {makeEm} from "./units"; +import ParseError from "./ParseError"; + + +////////////////////////////////////////////////////////////////////// +// macro tools + +defineMacro("\\noexpand", function(context) { + // The expansion is the token itself; but that token is interpreted + // as if its meaning were ‘\relax’ if it is a control sequence that + // would ordinarily be expanded by TeX’s expansion rules. + const t = context.popToken(); + if (context.isExpandable(t.text)) { + t.noexpand = true; + t.treatAsRelax = true; + } + return {tokens: [t], numArgs: 0}; +}); + +defineMacro("\\expandafter", function(context) { + // TeX first reads the token that comes immediately after \expandafter, + // without expanding it; let’s call this token t. Then TeX reads the + // token that comes after t (and possibly more tokens, if that token + // has an argument), replacing it by its expansion. Finally TeX puts + // t back in front of that expansion. + const t = context.popToken(); + context.expandOnce(true); // expand only an expandable token + return {tokens: [t], numArgs: 0}; +}); + +// LaTeX's \@firstoftwo{#1}{#2} expands to #1, skipping #2 +// TeX source: \long\def\@firstoftwo#1#2{#1} +defineMacro("\\@firstoftwo", function(context) { + const args = context.consumeArgs(2); + return {tokens: args[0], numArgs: 0}; +}); + +// LaTeX's \@secondoftwo{#1}{#2} expands to #2, skipping #1 +// TeX source: \long\def\@secondoftwo#1#2{#2} +defineMacro("\\@secondoftwo", function(context) { + const args = context.consumeArgs(2); + return {tokens: args[1], numArgs: 0}; +}); + +// LaTeX's \@ifnextchar{#1}{#2}{#3} looks ahead to the next (unexpanded) +// symbol that isn't a space, consuming any spaces but not consuming the +// first nonspace character. If that nonspace character matches #1, then +// the macro expands to #2; otherwise, it expands to #3. +defineMacro("\\@ifnextchar", function(context) { + const args = context.consumeArgs(3); // symbol, if, else + context.consumeSpaces(); + const nextToken = context.future(); + if (args[0].length === 1 && args[0][0].text === nextToken.text) { + return {tokens: args[1], numArgs: 0}; + } else { + return {tokens: args[2], numArgs: 0}; + } +}); + +// LaTeX's \@ifstar{#1}{#2} looks ahead to the next (unexpanded) symbol. +// If it is `*`, then it consumes the symbol, and the macro expands to #1; +// otherwise, the macro expands to #2 (without consuming the symbol). +// TeX source: \def\@ifstar#1{\@ifnextchar *{\@firstoftwo{#1}}} +defineMacro("\\@ifstar", "\\@ifnextchar *{\\@firstoftwo{#1}}"); + +// LaTeX's \TextOrMath{#1}{#2} expands to #1 in text mode, #2 in math mode +defineMacro("\\TextOrMath", function(context) { + const args = context.consumeArgs(2); + if (context.mode === 'text') { + return {tokens: args[0], numArgs: 0}; + } else { + return {tokens: args[1], numArgs: 0}; + } +}); + +// Lookup table for parsing numbers in base 8 through 16 +const digitToNumber = { + "0": 0, "1": 1, "2": 2, "3": 3, "4": 4, "5": 5, "6": 6, "7": 7, "8": 8, + "9": 9, "a": 10, "A": 10, "b": 11, "B": 11, "c": 12, "C": 12, + "d": 13, "D": 13, "e": 14, "E": 14, "f": 15, "F": 15, +}; + +// TeX \char makes a literal character (catcode 12) using the following forms: +// (see The TeXBook, p. 43) +// \char123 -- decimal +// \char'123 -- octal +// \char"123 -- hex +// \char`x -- character that can be written (i.e. isn't active) +// \char`\x -- character that cannot be written (e.g. %) +// These all refer to characters from the font, so we turn them into special +// calls to a function \@char dealt with in the Parser. +defineMacro("\\char", function(context) { + let token = context.popToken(); + let base; + let number = ''; + if (token.text === "'") { + base = 8; + token = context.popToken(); + } else if (token.text === '"') { + base = 16; + token = context.popToken(); + } else if (token.text === "`") { + token = context.popToken(); + if (token.text[0] === "\\") { + number = token.text.charCodeAt(1); + } else if (token.text === "EOF") { + throw new ParseError("\\char` missing argument"); + } else { + number = token.text.charCodeAt(0); + } + } else { + base = 10; + } + if (base) { + // Parse a number in the given base, starting with first `token`. + number = digitToNumber[token.text]; + if (number == null || number >= base) { + throw new ParseError(`Invalid base-${base} digit ${token.text}`); + } + let digit; + while ((digit = digitToNumber[context.future().text]) != null && + digit < base) { + number *= base; + number += digit; + context.popToken(); + } + } + return `\\@char{${number}}`; +}); + +// \newcommand{\macro}[args]{definition} +// \renewcommand{\macro}[args]{definition} +// TODO: Optional arguments: \newcommand{\macro}[args][default]{definition} +const newcommand = ( + context, existsOK: boolean, nonexistsOK: boolean, skipIfExists: boolean +) => { + let arg = context.consumeArg().tokens; + if (arg.length !== 1) { + throw new ParseError( + "\\newcommand's first argument must be a macro name"); + } + const name = arg[0].text; + + const exists = context.isDefined(name); + if (exists && !existsOK) { + throw new ParseError(`\\newcommand{${name}} attempting to redefine ` + + `${name}; use \\renewcommand`); + } + if (!exists && !nonexistsOK) { + throw new ParseError(`\\renewcommand{${name}} when command ${name} ` + + `does not yet exist; use \\newcommand`); + } + + let numArgs = 0; + arg = context.consumeArg().tokens; + if (arg.length === 1 && arg[0].text === "[") { + let argText = ''; + let token = context.expandNextToken(); + while (token.text !== "]" && token.text !== "EOF") { + // TODO: Should properly expand arg, e.g., ignore {}s + argText += token.text; + token = context.expandNextToken(); + } + if (!argText.match(/^\s*[0-9]+\s*$/)) { + throw new ParseError(`Invalid number of arguments: ${argText}`); + } + numArgs = parseInt(argText); + arg = context.consumeArg().tokens; + } + + if (!(exists && skipIfExists)) { + // Final arg is the expansion of the macro + context.macros.set(name, { + tokens: arg, + numArgs, + }); + } + return ''; +}; +defineMacro("\\newcommand", + (context) => newcommand(context, false, true, false)); +defineMacro("\\renewcommand", + (context) => newcommand(context, true, false, false)); +defineMacro("\\providecommand", + (context) => newcommand(context, true, true, true)); + +// terminal (console) tools +defineMacro("\\message", (context) => { + const arg = context.consumeArgs(1)[0]; + // eslint-disable-next-line no-console + console.log(arg.reverse().map(token => token.text).join("")); + return ''; +}); +defineMacro("\\errmessage", (context) => { + const arg = context.consumeArgs(1)[0]; + // eslint-disable-next-line no-console + console.error(arg.reverse().map(token => token.text).join("")); + return ''; +}); +defineMacro("\\show", (context) => { + const tok = context.popToken(); + const name = tok.text; + // eslint-disable-next-line no-console + console.log(tok, context.macros.get(name), functions[name], + symbols.math[name], symbols.text[name]); + return ''; +}); + +////////////////////////////////////////////////////////////////////// +// Grouping +// \let\bgroup={ \let\egroup=} +defineMacro("\\bgroup", "{"); +defineMacro("\\egroup", "}"); + +// Symbols from latex.ltx: +// \def~{\nobreakspace{}} +// \def\lq{`} +// \def\rq{'} +// \def \aa {\r a} +// \def \AA {\r A} +defineMacro("~", "\\nobreakspace"); +defineMacro("\\lq", "`"); +defineMacro("\\rq", "'"); +defineMacro("\\aa", "\\r a"); +defineMacro("\\AA", "\\r A"); + +// Copyright (C) and registered (R) symbols. Use raw symbol in MathML. +// \DeclareTextCommandDefault{\textcopyright}{\textcircled{c}} +// \DeclareTextCommandDefault{\textregistered}{\textcircled{% +// \check@mathfonts\fontsize\sf@size\z@\math@fontsfalse\selectfont R}} +// \DeclareRobustCommand{\copyright}{% +// \ifmmode{\nfss@text{\textcopyright}}\else\textcopyright\fi} +defineMacro("\\textcopyright", "\\html@mathml{\\textcircled{c}}{\\char`©}"); +defineMacro("\\copyright", + "\\TextOrMath{\\textcopyright}{\\text{\\textcopyright}}"); +defineMacro("\\textregistered", + "\\html@mathml{\\textcircled{\\scriptsize R}}{\\char`®}"); + +// Characters omitted from Unicode range 1D400–1D7FF +defineMacro("\u212C", "\\mathscr{B}"); // script +defineMacro("\u2130", "\\mathscr{E}"); +defineMacro("\u2131", "\\mathscr{F}"); +defineMacro("\u210B", "\\mathscr{H}"); +defineMacro("\u2110", "\\mathscr{I}"); +defineMacro("\u2112", "\\mathscr{L}"); +defineMacro("\u2133", "\\mathscr{M}"); +defineMacro("\u211B", "\\mathscr{R}"); +defineMacro("\u212D", "\\mathfrak{C}"); // Fraktur +defineMacro("\u210C", "\\mathfrak{H}"); +defineMacro("\u2128", "\\mathfrak{Z}"); + +// Define \Bbbk with a macro that works in both HTML and MathML. +defineMacro("\\Bbbk", "\\Bbb{k}"); + +// Unicode middle dot +// The KaTeX fonts do not contain U+00B7. Instead, \cdotp displays +// the dot at U+22C5 and gives it punct spacing. +defineMacro("\u00b7", "\\cdotp"); + +// \llap and \rlap render their contents in text mode +defineMacro("\\llap", "\\mathllap{\\textrm{#1}}"); +defineMacro("\\rlap", "\\mathrlap{\\textrm{#1}}"); +defineMacro("\\clap", "\\mathclap{\\textrm{#1}}"); + +// \mathstrut from the TeXbook, p 360 +defineMacro("\\mathstrut", "\\vphantom{(}"); + +// \underbar from TeXbook p 353 +defineMacro("\\underbar", "\\underline{\\text{#1}}"); + +// \not is defined by base/fontmath.ltx via +// \DeclareMathSymbol{\not}{\mathrel}{symbols}{"36} +// It's thus treated like a \mathrel, but defined by a symbol that has zero +// width but extends to the right. We use \rlap to get that spacing. +// For MathML we write U+0338 here. buildMathML.js will then do the overlay. +defineMacro("\\not", '\\html@mathml{\\mathrel{\\mathrlap\\@not}}{\\char"338}'); + +// Negated symbols from base/fontmath.ltx: +// \def\neq{\not=} \let\ne=\neq +// \DeclareRobustCommand +// \notin{\mathrel{\m@th\mathpalette\c@ncel\in}} +// \def\c@ncel#1#2{\m@th\ooalign{$\hfil#1\mkern1mu/\hfil$\crcr$#1#2$}} +defineMacro("\\neq", "\\html@mathml{\\mathrel{\\not=}}{\\mathrel{\\char`≠}}"); +defineMacro("\\ne", "\\neq"); +defineMacro("\u2260", "\\neq"); +defineMacro("\\notin", "\\html@mathml{\\mathrel{{\\in}\\mathllap{/\\mskip1mu}}}" + + "{\\mathrel{\\char`∉}}"); +defineMacro("\u2209", "\\notin"); + +// Unicode stacked relations +defineMacro("\u2258", "\\html@mathml{" + + "\\mathrel{=\\kern{-1em}\\raisebox{0.4em}{$\\scriptsize\\frown$}}" + + "}{\\mathrel{\\char`\u2258}}"); +defineMacro("\u2259", + "\\html@mathml{\\stackrel{\\tiny\\wedge}{=}}{\\mathrel{\\char`\u2258}}"); +defineMacro("\u225A", + "\\html@mathml{\\stackrel{\\tiny\\vee}{=}}{\\mathrel{\\char`\u225A}}"); +defineMacro("\u225B", + "\\html@mathml{\\stackrel{\\scriptsize\\star}{=}}" + + "{\\mathrel{\\char`\u225B}}"); +defineMacro("\u225D", + "\\html@mathml{\\stackrel{\\tiny\\mathrm{def}}{=}}" + + "{\\mathrel{\\char`\u225D}}"); +defineMacro("\u225E", + "\\html@mathml{\\stackrel{\\tiny\\mathrm{m}}{=}}" + + "{\\mathrel{\\char`\u225E}}"); +defineMacro("\u225F", + "\\html@mathml{\\stackrel{\\tiny?}{=}}{\\mathrel{\\char`\u225F}}"); + +// Misc Unicode +defineMacro("\u27C2", "\\perp"); +defineMacro("\u203C", "\\mathclose{!\\mkern-0.8mu!}"); +defineMacro("\u220C", "\\notni"); +defineMacro("\u231C", "\\ulcorner"); +defineMacro("\u231D", "\\urcorner"); +defineMacro("\u231E", "\\llcorner"); +defineMacro("\u231F", "\\lrcorner"); +defineMacro("\u00A9", "\\copyright"); +defineMacro("\u00AE", "\\textregistered"); +defineMacro("\uFE0F", "\\textregistered"); + +// The KaTeX fonts have corners at codepoints that don't match Unicode. +// For MathML purposes, use the Unicode code point. +defineMacro("\\ulcorner", "\\html@mathml{\\@ulcorner}{\\mathop{\\char\"231c}}"); +defineMacro("\\urcorner", "\\html@mathml{\\@urcorner}{\\mathop{\\char\"231d}}"); +defineMacro("\\llcorner", "\\html@mathml{\\@llcorner}{\\mathop{\\char\"231e}}"); +defineMacro("\\lrcorner", "\\html@mathml{\\@lrcorner}{\\mathop{\\char\"231f}}"); + +////////////////////////////////////////////////////////////////////// +// LaTeX_2ε + +// \vdots{\vbox{\baselineskip4\p@ \lineskiplimit\z@ +// \kern6\p@\hbox{.}\hbox{.}\hbox{.}}} +// We'll call \varvdots, which gets a glyph from symbols.js. +// The zero-width rule gets us an equivalent to the vertical 6pt kern. +defineMacro("\\vdots", "{\\varvdots\\rule{0pt}{15pt}}"); +defineMacro("\u22ee", "\\vdots"); + +////////////////////////////////////////////////////////////////////// +// amsmath.sty +// http://mirrors.concertpass.com/tex-archive/macros/latex/required/amsmath/amsmath.pdf + +// Italic Greek capital letters. AMS defines these with \DeclareMathSymbol, +// but they are equivalent to \mathit{\Letter}. +defineMacro("\\varGamma", "\\mathit{\\Gamma}"); +defineMacro("\\varDelta", "\\mathit{\\Delta}"); +defineMacro("\\varTheta", "\\mathit{\\Theta}"); +defineMacro("\\varLambda", "\\mathit{\\Lambda}"); +defineMacro("\\varXi", "\\mathit{\\Xi}"); +defineMacro("\\varPi", "\\mathit{\\Pi}"); +defineMacro("\\varSigma", "\\mathit{\\Sigma}"); +defineMacro("\\varUpsilon", "\\mathit{\\Upsilon}"); +defineMacro("\\varPhi", "\\mathit{\\Phi}"); +defineMacro("\\varPsi", "\\mathit{\\Psi}"); +defineMacro("\\varOmega", "\\mathit{\\Omega}"); + +//\newcommand{\substack}[1]{\subarray{c}#1\endsubarray} +defineMacro("\\substack", "\\begin{subarray}{c}#1\\end{subarray}"); + +// \renewcommand{\colon}{\nobreak\mskip2mu\mathpunct{}\nonscript +// \mkern-\thinmuskip{:}\mskip6muplus1mu\relax} +defineMacro("\\colon", "\\nobreak\\mskip2mu\\mathpunct{}" + + "\\mathchoice{\\mkern-3mu}{\\mkern-3mu}{}{}{:}\\mskip6mu\\relax"); + +// \newcommand{\boxed}[1]{\fbox{\m@th$\displaystyle#1$}} +defineMacro("\\boxed", "\\fbox{$\\displaystyle{#1}$}"); + +// \def\iff{\DOTSB\;\Longleftrightarrow\;} +// \def\implies{\DOTSB\;\Longrightarrow\;} +// \def\impliedby{\DOTSB\;\Longleftarrow\;} +defineMacro("\\iff", "\\DOTSB\\;\\Longleftrightarrow\\;"); +defineMacro("\\implies", "\\DOTSB\\;\\Longrightarrow\\;"); +defineMacro("\\impliedby", "\\DOTSB\\;\\Longleftarrow\\;"); + +// \def\dddot#1{{\mathop{#1}\limits^{\vbox to-1.4\ex@{\kern-\tw@\ex@ +// \hbox{\normalfont ...}\vss}}}} +// We use \overset which avoids the vertical shift of \mathop. +defineMacro("\\dddot", "{\\overset{\\raisebox{-0.1ex}{\\normalsize ...}}{#1}}"); +defineMacro("\\ddddot", "{\\overset{\\raisebox{-0.1ex}{\\normalsize ....}}{#1}}"); + +// AMSMath's automatic \dots, based on \mdots@@ macro. +const dotsByToken = { + ',': '\\dotsc', + '\\not': '\\dotsb', + // \keybin@ checks for the following: + '+': '\\dotsb', + '=': '\\dotsb', + '<': '\\dotsb', + '>': '\\dotsb', + '-': '\\dotsb', + '*': '\\dotsb', + ':': '\\dotsb', + // Symbols whose definition starts with \DOTSB: + '\\DOTSB': '\\dotsb', + '\\coprod': '\\dotsb', + '\\bigvee': '\\dotsb', + '\\bigwedge': '\\dotsb', + '\\biguplus': '\\dotsb', + '\\bigcap': '\\dotsb', + '\\bigcup': '\\dotsb', + '\\prod': '\\dotsb', + '\\sum': '\\dotsb', + '\\bigotimes': '\\dotsb', + '\\bigoplus': '\\dotsb', + '\\bigodot': '\\dotsb', + '\\bigsqcup': '\\dotsb', + '\\And': '\\dotsb', + '\\longrightarrow': '\\dotsb', + '\\Longrightarrow': '\\dotsb', + '\\longleftarrow': '\\dotsb', + '\\Longleftarrow': '\\dotsb', + '\\longleftrightarrow': '\\dotsb', + '\\Longleftrightarrow': '\\dotsb', + '\\mapsto': '\\dotsb', + '\\longmapsto': '\\dotsb', + '\\hookrightarrow': '\\dotsb', + '\\doteq': '\\dotsb', + // Symbols whose definition starts with \mathbin: + '\\mathbin': '\\dotsb', + // Symbols whose definition starts with \mathrel: + '\\mathrel': '\\dotsb', + '\\relbar': '\\dotsb', + '\\Relbar': '\\dotsb', + '\\xrightarrow': '\\dotsb', + '\\xleftarrow': '\\dotsb', + // Symbols whose definition starts with \DOTSI: + '\\DOTSI': '\\dotsi', + '\\int': '\\dotsi', + '\\oint': '\\dotsi', + '\\iint': '\\dotsi', + '\\iiint': '\\dotsi', + '\\iiiint': '\\dotsi', + '\\idotsint': '\\dotsi', + // Symbols whose definition starts with \DOTSX: + '\\DOTSX': '\\dotsx', +}; + +defineMacro("\\dots", function(context) { + // TODO: If used in text mode, should expand to \textellipsis. + // However, in KaTeX, \textellipsis and \ldots behave the same + // (in text mode), and it's unlikely we'd see any of the math commands + // that affect the behavior of \dots when in text mode. So fine for now + // (until we support \ifmmode ... \else ... \fi). + let thedots = '\\dotso'; + const next = context.expandAfterFuture().text; + if (next in dotsByToken) { + thedots = dotsByToken[next]; + } else if (next.slice(0, 4) === '\\not') { + thedots = '\\dotsb'; + } else if (next in symbols.math) { + if (utils.contains(['bin', 'rel'], symbols.math[next].group)) { + thedots = '\\dotsb'; + } + } + return thedots; +}); + +const spaceAfterDots = { + // \rightdelim@ checks for the following: + ')': true, + ']': true, + '\\rbrack': true, + '\\}': true, + '\\rbrace': true, + '\\rangle': true, + '\\rceil': true, + '\\rfloor': true, + '\\rgroup': true, + '\\rmoustache': true, + '\\right': true, + '\\bigr': true, + '\\biggr': true, + '\\Bigr': true, + '\\Biggr': true, + // \extra@ also tests for the following: + '$': true, + // \extrap@ checks for the following: + ';': true, + '.': true, + ',': true, +}; + +defineMacro("\\dotso", function(context) { + const next = context.future().text; + if (next in spaceAfterDots) { + return "\\ldots\\,"; + } else { + return "\\ldots"; + } +}); + +defineMacro("\\dotsc", function(context) { + const next = context.future().text; + // \dotsc uses \extra@ but not \extrap@, instead specially checking for + // ';' and '.', but doesn't check for ','. + if (next in spaceAfterDots && next !== ',') { + return "\\ldots\\,"; + } else { + return "\\ldots"; + } +}); + +defineMacro("\\cdots", function(context) { + const next = context.future().text; + if (next in spaceAfterDots) { + return "\\@cdots\\,"; + } else { + return "\\@cdots"; + } +}); + +defineMacro("\\dotsb", "\\cdots"); +defineMacro("\\dotsm", "\\cdots"); +defineMacro("\\dotsi", "\\!\\cdots"); +// amsmath doesn't actually define \dotsx, but \dots followed by a macro +// starting with \DOTSX implies \dotso, and then \extra@ detects this case +// and forces the added `\,`. +defineMacro("\\dotsx", "\\ldots\\,"); + +// \let\DOTSI\relax +// \let\DOTSB\relax +// \let\DOTSX\relax +defineMacro("\\DOTSI", "\\relax"); +defineMacro("\\DOTSB", "\\relax"); +defineMacro("\\DOTSX", "\\relax"); + +// Spacing, based on amsmath.sty's override of LaTeX defaults +// \DeclareRobustCommand{\tmspace}[3]{% +// \ifmmode\mskip#1#2\else\kern#1#3\fi\relax} +defineMacro("\\tmspace", "\\TextOrMath{\\kern#1#3}{\\mskip#1#2}\\relax"); +// \renewcommand{\,}{\tmspace+\thinmuskip{.1667em}} +// TODO: math mode should use \thinmuskip +defineMacro("\\,", "\\tmspace+{3mu}{.1667em}"); +// \let\thinspace\, +defineMacro("\\thinspace", "\\,"); +// \def\>{\mskip\medmuskip} +// \renewcommand{\:}{\tmspace+\medmuskip{.2222em}} +// TODO: \> and math mode of \: should use \medmuskip = 4mu plus 2mu minus 4mu +defineMacro("\\>", "\\mskip{4mu}"); +defineMacro("\\:", "\\tmspace+{4mu}{.2222em}"); +// \let\medspace\: +defineMacro("\\medspace", "\\:"); +// \renewcommand{\;}{\tmspace+\thickmuskip{.2777em}} +// TODO: math mode should use \thickmuskip = 5mu plus 5mu +defineMacro("\\;", "\\tmspace+{5mu}{.2777em}"); +// \let\thickspace\; +defineMacro("\\thickspace", "\\;"); +// \renewcommand{\!}{\tmspace-\thinmuskip{.1667em}} +// TODO: math mode should use \thinmuskip +defineMacro("\\!", "\\tmspace-{3mu}{.1667em}"); +// \let\negthinspace\! +defineMacro("\\negthinspace", "\\!"); +// \newcommand{\negmedspace}{\tmspace-\medmuskip{.2222em}} +// TODO: math mode should use \medmuskip +defineMacro("\\negmedspace", "\\tmspace-{4mu}{.2222em}"); +// \newcommand{\negthickspace}{\tmspace-\thickmuskip{.2777em}} +// TODO: math mode should use \thickmuskip +defineMacro("\\negthickspace", "\\tmspace-{5mu}{.277em}"); +// \def\enspace{\kern.5em } +defineMacro("\\enspace", "\\kern.5em "); +// \def\enskip{\hskip.5em\relax} +defineMacro("\\enskip", "\\hskip.5em\\relax"); +// \def\quad{\hskip1em\relax} +defineMacro("\\quad", "\\hskip1em\\relax"); +// \def\qquad{\hskip2em\relax} +defineMacro("\\qquad", "\\hskip2em\\relax"); + +// \tag@in@display form of \tag +defineMacro("\\tag", "\\@ifstar\\tag@literal\\tag@paren"); +defineMacro("\\tag@paren", "\\tag@literal{({#1})}"); +defineMacro("\\tag@literal", (context) => { + if (context.macros.get("\\df@tag")) { + throw new ParseError("Multiple \\tag"); + } + return "\\gdef\\df@tag{\\text{#1}}"; +}); + +// \renewcommand{\bmod}{\nonscript\mskip-\medmuskip\mkern5mu\mathbin +// {\operator@font mod}\penalty900 +// \mkern5mu\nonscript\mskip-\medmuskip} +// \newcommand{\pod}[1]{\allowbreak +// \if@display\mkern18mu\else\mkern8mu\fi(#1)} +// \renewcommand{\pmod}[1]{\pod{{\operator@font mod}\mkern6mu#1}} +// \newcommand{\mod}[1]{\allowbreak\if@display\mkern18mu +// \else\mkern12mu\fi{\operator@font mod}\,\,#1} +// TODO: math mode should use \medmuskip = 4mu plus 2mu minus 4mu +defineMacro("\\bmod", + "\\mathchoice{\\mskip1mu}{\\mskip1mu}{\\mskip5mu}{\\mskip5mu}" + + "\\mathbin{\\rm mod}" + + "\\mathchoice{\\mskip1mu}{\\mskip1mu}{\\mskip5mu}{\\mskip5mu}"); +defineMacro("\\pod", "\\allowbreak" + + "\\mathchoice{\\mkern18mu}{\\mkern8mu}{\\mkern8mu}{\\mkern8mu}(#1)"); +defineMacro("\\pmod", "\\pod{{\\rm mod}\\mkern6mu#1}"); +defineMacro("\\mod", "\\allowbreak" + + "\\mathchoice{\\mkern18mu}{\\mkern12mu}{\\mkern12mu}{\\mkern12mu}" + + "{\\rm mod}\\,\\,#1"); + +////////////////////////////////////////////////////////////////////// +// LaTeX source2e + +// \expandafter\let\expandafter\@normalcr +// \csname\expandafter\@gobble\string\\ \endcsname +// \DeclareRobustCommand\newline{\@normalcr\relax} +defineMacro("\\newline", "\\\\\\relax"); + +// \def\TeX{T\kern-.1667em\lower.5ex\hbox{E}\kern-.125emX\@} +// TODO: Doesn't normally work in math mode because \@ fails. KaTeX doesn't +// support \@ yet, so that's omitted, and we add \text so that the result +// doesn't look funny in math mode. +defineMacro("\\TeX", "\\textrm{\\html@mathml{" + + "T\\kern-.1667em\\raisebox{-.5ex}{E}\\kern-.125emX" + + "}{TeX}}"); + +// \DeclareRobustCommand{\LaTeX}{L\kern-.36em% +// {\sbox\z@ T% +// \vbox to\ht\z@{\hbox{\check@mathfonts +// \fontsize\sf@size\z@ +// \math@fontsfalse\selectfont +// A}% +// \vss}% +// }% +// \kern-.15em% +// \TeX} +// This code aligns the top of the A with the T (from the perspective of TeX's +// boxes, though visually the A appears to extend above slightly). +// We compute the corresponding \raisebox when A is rendered in \normalsize +// \scriptstyle, which has a scale factor of 0.7 (see Options.js). +const latexRaiseA = makeEm(fontMetricsData['Main-Regular']["T".charCodeAt(0)][1] - + 0.7 * fontMetricsData['Main-Regular']["A".charCodeAt(0)][1]); +defineMacro("\\LaTeX", "\\textrm{\\html@mathml{" + + `L\\kern-.36em\\raisebox{${latexRaiseA}}{\\scriptstyle A}` + + "\\kern-.15em\\TeX}{LaTeX}}"); + +// New KaTeX logo based on tweaking LaTeX logo +defineMacro("\\KaTeX", "\\textrm{\\html@mathml{" + + `K\\kern-.17em\\raisebox{${latexRaiseA}}{\\scriptstyle A}` + + "\\kern-.15em\\TeX}{KaTeX}}"); + +// \DeclareRobustCommand\hspace{\@ifstar\@hspacer\@hspace} +// \def\@hspace#1{\hskip #1\relax} +// \def\@hspacer#1{\vrule \@width\z@\nobreak +// \hskip #1\hskip \z@skip} +defineMacro("\\hspace", "\\@ifstar\\@hspacer\\@hspace"); +defineMacro("\\@hspace", "\\hskip #1\\relax"); +defineMacro("\\@hspacer", "\\rule{0pt}{0pt}\\hskip #1\\relax"); + +////////////////////////////////////////////////////////////////////// +// mathtools.sty + +//\providecommand\ordinarycolon{:} +defineMacro("\\ordinarycolon", ":"); +//\def\vcentcolon{\mathrel{\mathop\ordinarycolon}} +//TODO(edemaine): Not yet centered. Fix via \raisebox or #726 +defineMacro("\\vcentcolon", "\\mathrel{\\mathop\\ordinarycolon}"); +// \providecommand*\dblcolon{\vcentcolon\mathrel{\mkern-.9mu}\vcentcolon} +defineMacro("\\dblcolon", "\\html@mathml{" + + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-.9mu}\\vcentcolon}}" + + "{\\mathop{\\char\"2237}}"); +// \providecommand*\coloneqq{\vcentcolon\mathrel{\mkern-1.2mu}=} +defineMacro("\\coloneqq", "\\html@mathml{" + + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}=}}" + + "{\\mathop{\\char\"2254}}"); // ≔ +// \providecommand*\Coloneqq{\dblcolon\mathrel{\mkern-1.2mu}=} +defineMacro("\\Coloneqq", "\\html@mathml{" + + "\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}=}}" + + "{\\mathop{\\char\"2237\\char\"3d}}"); +// \providecommand*\coloneq{\vcentcolon\mathrel{\mkern-1.2mu}\mathrel{-}} +defineMacro("\\coloneq", "\\html@mathml{" + + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}\\mathrel{-}}}" + + "{\\mathop{\\char\"3a\\char\"2212}}"); +// \providecommand*\Coloneq{\dblcolon\mathrel{\mkern-1.2mu}\mathrel{-}} +defineMacro("\\Coloneq", "\\html@mathml{" + + "\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}\\mathrel{-}}}" + + "{\\mathop{\\char\"2237\\char\"2212}}"); +// \providecommand*\eqqcolon{=\mathrel{\mkern-1.2mu}\vcentcolon} +defineMacro("\\eqqcolon", "\\html@mathml{" + + "\\mathrel{=\\mathrel{\\mkern-1.2mu}\\vcentcolon}}" + + "{\\mathop{\\char\"2255}}"); // ≕ +// \providecommand*\Eqqcolon{=\mathrel{\mkern-1.2mu}\dblcolon} +defineMacro("\\Eqqcolon", "\\html@mathml{" + + "\\mathrel{=\\mathrel{\\mkern-1.2mu}\\dblcolon}}" + + "{\\mathop{\\char\"3d\\char\"2237}}"); +// \providecommand*\eqcolon{\mathrel{-}\mathrel{\mkern-1.2mu}\vcentcolon} +defineMacro("\\eqcolon", "\\html@mathml{" + + "\\mathrel{\\mathrel{-}\\mathrel{\\mkern-1.2mu}\\vcentcolon}}" + + "{\\mathop{\\char\"2239}}"); +// \providecommand*\Eqcolon{\mathrel{-}\mathrel{\mkern-1.2mu}\dblcolon} +defineMacro("\\Eqcolon", "\\html@mathml{" + + "\\mathrel{\\mathrel{-}\\mathrel{\\mkern-1.2mu}\\dblcolon}}" + + "{\\mathop{\\char\"2212\\char\"2237}}"); +// \providecommand*\colonapprox{\vcentcolon\mathrel{\mkern-1.2mu}\approx} +defineMacro("\\colonapprox", "\\html@mathml{" + + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}\\approx}}" + + "{\\mathop{\\char\"3a\\char\"2248}}"); +// \providecommand*\Colonapprox{\dblcolon\mathrel{\mkern-1.2mu}\approx} +defineMacro("\\Colonapprox", "\\html@mathml{" + + "\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}\\approx}}" + + "{\\mathop{\\char\"2237\\char\"2248}}"); +// \providecommand*\colonsim{\vcentcolon\mathrel{\mkern-1.2mu}\sim} +defineMacro("\\colonsim", "\\html@mathml{" + + "\\mathrel{\\vcentcolon\\mathrel{\\mkern-1.2mu}\\sim}}" + + "{\\mathop{\\char\"3a\\char\"223c}}"); +// \providecommand*\Colonsim{\dblcolon\mathrel{\mkern-1.2mu}\sim} +defineMacro("\\Colonsim", "\\html@mathml{" + + "\\mathrel{\\dblcolon\\mathrel{\\mkern-1.2mu}\\sim}}" + + "{\\mathop{\\char\"2237\\char\"223c}}"); + +// Some Unicode characters are implemented with macros to mathtools functions. +defineMacro("\u2237", "\\dblcolon"); // :: +defineMacro("\u2239", "\\eqcolon"); // -: +defineMacro("\u2254", "\\coloneqq"); // := +defineMacro("\u2255", "\\eqqcolon"); // =: +defineMacro("\u2A74", "\\Coloneqq"); // ::= + +////////////////////////////////////////////////////////////////////// +// colonequals.sty + +// Alternate names for mathtools's macros: +defineMacro("\\ratio", "\\vcentcolon"); +defineMacro("\\coloncolon", "\\dblcolon"); +defineMacro("\\colonequals", "\\coloneqq"); +defineMacro("\\coloncolonequals", "\\Coloneqq"); +defineMacro("\\equalscolon", "\\eqqcolon"); +defineMacro("\\equalscoloncolon", "\\Eqqcolon"); +defineMacro("\\colonminus", "\\coloneq"); +defineMacro("\\coloncolonminus", "\\Coloneq"); +defineMacro("\\minuscolon", "\\eqcolon"); +defineMacro("\\minuscoloncolon", "\\Eqcolon"); +// \colonapprox name is same in mathtools and colonequals. +defineMacro("\\coloncolonapprox", "\\Colonapprox"); +// \colonsim name is same in mathtools and colonequals. +defineMacro("\\coloncolonsim", "\\Colonsim"); + +// Additional macros, implemented by analogy with mathtools definitions: +defineMacro("\\simcolon", + "\\mathrel{\\sim\\mathrel{\\mkern-1.2mu}\\vcentcolon}"); +defineMacro("\\simcoloncolon", + "\\mathrel{\\sim\\mathrel{\\mkern-1.2mu}\\dblcolon}"); +defineMacro("\\approxcolon", + "\\mathrel{\\approx\\mathrel{\\mkern-1.2mu}\\vcentcolon}"); +defineMacro("\\approxcoloncolon", + "\\mathrel{\\approx\\mathrel{\\mkern-1.2mu}\\dblcolon}"); + +// Present in newtxmath, pxfonts and txfonts +defineMacro("\\notni", "\\html@mathml{\\not\\ni}{\\mathrel{\\char`\u220C}}"); +defineMacro("\\limsup", "\\DOTSB\\operatorname*{lim\\,sup}"); +defineMacro("\\liminf", "\\DOTSB\\operatorname*{lim\\,inf}"); + +////////////////////////////////////////////////////////////////////// +// From amsopn.sty +defineMacro("\\injlim", "\\DOTSB\\operatorname*{inj\\,lim}"); +defineMacro("\\projlim", "\\DOTSB\\operatorname*{proj\\,lim}"); +defineMacro("\\varlimsup", "\\DOTSB\\operatorname*{\\overline{lim}}"); +defineMacro("\\varliminf", "\\DOTSB\\operatorname*{\\underline{lim}}"); +defineMacro("\\varinjlim", "\\DOTSB\\operatorname*{\\underrightarrow{lim}}"); +defineMacro("\\varprojlim", "\\DOTSB\\operatorname*{\\underleftarrow{lim}}"); + +////////////////////////////////////////////////////////////////////// +// MathML alternates for KaTeX glyphs in the Unicode private area +defineMacro("\\gvertneqq", "\\html@mathml{\\@gvertneqq}{\u2269}"); +defineMacro("\\lvertneqq", "\\html@mathml{\\@lvertneqq}{\u2268}"); +defineMacro("\\ngeqq", "\\html@mathml{\\@ngeqq}{\u2271}"); +defineMacro("\\ngeqslant", "\\html@mathml{\\@ngeqslant}{\u2271}"); +defineMacro("\\nleqq", "\\html@mathml{\\@nleqq}{\u2270}"); +defineMacro("\\nleqslant", "\\html@mathml{\\@nleqslant}{\u2270}"); +defineMacro("\\nshortmid", "\\html@mathml{\\@nshortmid}{∤}"); +defineMacro("\\nshortparallel", "\\html@mathml{\\@nshortparallel}{∦}"); +defineMacro("\\nsubseteqq", "\\html@mathml{\\@nsubseteqq}{\u2288}"); +defineMacro("\\nsupseteqq", "\\html@mathml{\\@nsupseteqq}{\u2289}"); +defineMacro("\\varsubsetneq", "\\html@mathml{\\@varsubsetneq}{⊊}"); +defineMacro("\\varsubsetneqq", "\\html@mathml{\\@varsubsetneqq}{⫋}"); +defineMacro("\\varsupsetneq", "\\html@mathml{\\@varsupsetneq}{⊋}"); +defineMacro("\\varsupsetneqq", "\\html@mathml{\\@varsupsetneqq}{⫌}"); +defineMacro("\\imath", "\\html@mathml{\\@imath}{\u0131}"); +defineMacro("\\jmath", "\\html@mathml{\\@jmath}{\u0237}"); + +////////////////////////////////////////////////////////////////////// +// stmaryrd and semantic + +// The stmaryrd and semantic packages render the next four items by calling a +// glyph. Those glyphs do not exist in the KaTeX fonts. Hence the macros. + +defineMacro("\\llbracket", "\\html@mathml{" + + "\\mathopen{[\\mkern-3.2mu[}}" + + "{\\mathopen{\\char`\u27e6}}"); +defineMacro("\\rrbracket", "\\html@mathml{" + + "\\mathclose{]\\mkern-3.2mu]}}" + + "{\\mathclose{\\char`\u27e7}}"); + +defineMacro("\u27e6", "\\llbracket"); // blackboard bold [ +defineMacro("\u27e7", "\\rrbracket"); // blackboard bold ] + +defineMacro("\\lBrace", "\\html@mathml{" + + "\\mathopen{\\{\\mkern-3.2mu[}}" + + "{\\mathopen{\\char`\u2983}}"); +defineMacro("\\rBrace", "\\html@mathml{" + + "\\mathclose{]\\mkern-3.2mu\\}}}" + + "{\\mathclose{\\char`\u2984}}"); + +defineMacro("\u2983", "\\lBrace"); // blackboard bold { +defineMacro("\u2984", "\\rBrace"); // blackboard bold } + +// TODO: Create variable sized versions of the last two items. I believe that +// will require new font glyphs. + +// The stmaryrd function `\minuso` provides a "Plimsoll" symbol that +// superimposes the characters \circ and \mathminus. Used in chemistry. +defineMacro("\\minuso", "\\mathbin{\\html@mathml{" + + "{\\mathrlap{\\mathchoice{\\kern{0.145em}}{\\kern{0.145em}}" + + "{\\kern{0.1015em}}{\\kern{0.0725em}}\\circ}{-}}}" + + "{\\char`⦵}}"); +defineMacro("⦵", "\\minuso"); + +////////////////////////////////////////////////////////////////////// +// texvc.sty + +// The texvc package contains macros available in mediawiki pages. +// We omit the functions deprecated at +// https://en.wikipedia.org/wiki/Help:Displaying_a_formula#Deprecated_syntax + +// We also omit texvc's \O, which conflicts with \text{\O} + +defineMacro("\\darr", "\\downarrow"); +defineMacro("\\dArr", "\\Downarrow"); +defineMacro("\\Darr", "\\Downarrow"); +defineMacro("\\lang", "\\langle"); +defineMacro("\\rang", "\\rangle"); +defineMacro("\\uarr", "\\uparrow"); +defineMacro("\\uArr", "\\Uparrow"); +defineMacro("\\Uarr", "\\Uparrow"); +defineMacro("\\N", "\\mathbb{N}"); +defineMacro("\\R", "\\mathbb{R}"); +defineMacro("\\Z", "\\mathbb{Z}"); +defineMacro("\\alef", "\\aleph"); +defineMacro("\\alefsym", "\\aleph"); +defineMacro("\\Alpha", "\\mathrm{A}"); +defineMacro("\\Beta", "\\mathrm{B}"); +defineMacro("\\bull", "\\bullet"); +defineMacro("\\Chi", "\\mathrm{X}"); +defineMacro("\\clubs", "\\clubsuit"); +defineMacro("\\cnums", "\\mathbb{C}"); +defineMacro("\\Complex", "\\mathbb{C}"); +defineMacro("\\Dagger", "\\ddagger"); +defineMacro("\\diamonds", "\\diamondsuit"); +defineMacro("\\empty", "\\emptyset"); +defineMacro("\\Epsilon", "\\mathrm{E}"); +defineMacro("\\Eta", "\\mathrm{H}"); +defineMacro("\\exist", "\\exists"); +defineMacro("\\harr", "\\leftrightarrow"); +defineMacro("\\hArr", "\\Leftrightarrow"); +defineMacro("\\Harr", "\\Leftrightarrow"); +defineMacro("\\hearts", "\\heartsuit"); +defineMacro("\\image", "\\Im"); +defineMacro("\\infin", "\\infty"); +defineMacro("\\Iota", "\\mathrm{I}"); +defineMacro("\\isin", "\\in"); +defineMacro("\\Kappa", "\\mathrm{K}"); +defineMacro("\\larr", "\\leftarrow"); +defineMacro("\\lArr", "\\Leftarrow"); +defineMacro("\\Larr", "\\Leftarrow"); +defineMacro("\\lrarr", "\\leftrightarrow"); +defineMacro("\\lrArr", "\\Leftrightarrow"); +defineMacro("\\Lrarr", "\\Leftrightarrow"); +defineMacro("\\Mu", "\\mathrm{M}"); +defineMacro("\\natnums", "\\mathbb{N}"); +defineMacro("\\Nu", "\\mathrm{N}"); +defineMacro("\\Omicron", "\\mathrm{O}"); +defineMacro("\\plusmn", "\\pm"); +defineMacro("\\rarr", "\\rightarrow"); +defineMacro("\\rArr", "\\Rightarrow"); +defineMacro("\\Rarr", "\\Rightarrow"); +defineMacro("\\real", "\\Re"); +defineMacro("\\reals", "\\mathbb{R}"); +defineMacro("\\Reals", "\\mathbb{R}"); +defineMacro("\\Rho", "\\mathrm{P}"); +defineMacro("\\sdot", "\\cdot"); +defineMacro("\\sect", "\\S"); +defineMacro("\\spades", "\\spadesuit"); +defineMacro("\\sub", "\\subset"); +defineMacro("\\sube", "\\subseteq"); +defineMacro("\\supe", "\\supseteq"); +defineMacro("\\Tau", "\\mathrm{T}"); +defineMacro("\\thetasym", "\\vartheta"); +// TODO: defineMacro("\\varcoppa", "\\\mbox{\\coppa}"); +defineMacro("\\weierp", "\\wp"); +defineMacro("\\Zeta", "\\mathrm{Z}"); + +////////////////////////////////////////////////////////////////////// +// statmath.sty +// https://ctan.math.illinois.edu/macros/latex/contrib/statmath/statmath.pdf + +defineMacro("\\argmin", "\\DOTSB\\operatorname*{arg\\,min}"); +defineMacro("\\argmax", "\\DOTSB\\operatorname*{arg\\,max}"); +defineMacro("\\plim", "\\DOTSB\\mathop{\\operatorname{plim}}\\limits"); + +////////////////////////////////////////////////////////////////////// +// braket.sty +// http://ctan.math.washington.edu/tex-archive/macros/latex/contrib/braket/braket.pdf + +defineMacro("\\bra", "\\mathinner{\\langle{#1}|}"); +defineMacro("\\ket", "\\mathinner{|{#1}\\rangle}"); +defineMacro("\\braket", "\\mathinner{\\langle{#1}\\rangle}"); +defineMacro("\\Bra", "\\left\\langle#1\\right|"); +defineMacro("\\Ket", "\\left|#1\\right\\rangle"); +const braketHelper = (one) => (context) => { + const left = context.consumeArg().tokens; + const middle = context.consumeArg().tokens; + const middleDouble = context.consumeArg().tokens; + const right = context.consumeArg().tokens; + const oldMiddle = context.macros.get("|"); + const oldMiddleDouble = context.macros.get("\\|"); + context.macros.beginGroup(); + const midMacro = (double) => (context) => { + if (one) { + // Only modify the first instance of | or \| + context.macros.set("|", oldMiddle); + if (middleDouble.length) { + context.macros.set("\\|", oldMiddleDouble); + } + } + let doubled = double; + if (!double && middleDouble.length) { + // Mimic \@ifnextchar + const nextToken = context.future(); + if (nextToken.text === "|") { + context.popToken(); + doubled = true; + } + } + return { + tokens: doubled ? middleDouble : middle, + numArgs: 0, + }; + }; + context.macros.set("|", midMacro(false)); + if (middleDouble.length) { + context.macros.set("\\|", midMacro(true)); + } + const arg = context.consumeArg().tokens; + const expanded = context.expandTokens([ + ...right, ...arg, ...left, // reversed + ]); + context.macros.endGroup(); + return { + tokens: expanded.reverse(), + numArgs: 0, + }; +}; +defineMacro("\\bra@ket", braketHelper(false)); +defineMacro("\\bra@set", braketHelper(true)); +defineMacro("\\Braket", "\\bra@ket{\\left\\langle}" + + "{\\,\\middle\\vert\\,}{\\,\\middle\\vert\\,}{\\right\\rangle}"); +defineMacro("\\Set", "\\bra@set{\\left\\{\\:}" + + "{\\;\\middle\\vert\\;}{\\;\\middle\\Vert\\;}{\\:\\right\\}}"); +defineMacro("\\set", "\\bra@set{\\{\\,}{\\mid}{}{\\,\\}}"); + // has no support for special || or \| + +////////////////////////////////////////////////////////////////////// +// actuarialangle.dtx +defineMacro("\\angln", "{\\angl n}"); + +// Custom Khan Academy colors, should be moved to an optional package +defineMacro("\\blue", "\\textcolor{##6495ed}{#1}"); +defineMacro("\\orange", "\\textcolor{##ffa500}{#1}"); +defineMacro("\\pink", "\\textcolor{##ff00af}{#1}"); +defineMacro("\\red", "\\textcolor{##df0030}{#1}"); +defineMacro("\\green", "\\textcolor{##28ae7b}{#1}"); +defineMacro("\\gray", "\\textcolor{gray}{#1}"); +defineMacro("\\purple", "\\textcolor{##9d38bd}{#1}"); +defineMacro("\\blueA", "\\textcolor{##ccfaff}{#1}"); +defineMacro("\\blueB", "\\textcolor{##80f6ff}{#1}"); +defineMacro("\\blueC", "\\textcolor{##63d9ea}{#1}"); +defineMacro("\\blueD", "\\textcolor{##11accd}{#1}"); +defineMacro("\\blueE", "\\textcolor{##0c7f99}{#1}"); +defineMacro("\\tealA", "\\textcolor{##94fff5}{#1}"); +defineMacro("\\tealB", "\\textcolor{##26edd5}{#1}"); +defineMacro("\\tealC", "\\textcolor{##01d1c1}{#1}"); +defineMacro("\\tealD", "\\textcolor{##01a995}{#1}"); +defineMacro("\\tealE", "\\textcolor{##208170}{#1}"); +defineMacro("\\greenA", "\\textcolor{##b6ffb0}{#1}"); +defineMacro("\\greenB", "\\textcolor{##8af281}{#1}"); +defineMacro("\\greenC", "\\textcolor{##74cf70}{#1}"); +defineMacro("\\greenD", "\\textcolor{##1fab54}{#1}"); +defineMacro("\\greenE", "\\textcolor{##0d923f}{#1}"); +defineMacro("\\goldA", "\\textcolor{##ffd0a9}{#1}"); +defineMacro("\\goldB", "\\textcolor{##ffbb71}{#1}"); +defineMacro("\\goldC", "\\textcolor{##ff9c39}{#1}"); +defineMacro("\\goldD", "\\textcolor{##e07d10}{#1}"); +defineMacro("\\goldE", "\\textcolor{##a75a05}{#1}"); +defineMacro("\\redA", "\\textcolor{##fca9a9}{#1}"); +defineMacro("\\redB", "\\textcolor{##ff8482}{#1}"); +defineMacro("\\redC", "\\textcolor{##f9685d}{#1}"); +defineMacro("\\redD", "\\textcolor{##e84d39}{#1}"); +defineMacro("\\redE", "\\textcolor{##bc2612}{#1}"); +defineMacro("\\maroonA", "\\textcolor{##ffbde0}{#1}"); +defineMacro("\\maroonB", "\\textcolor{##ff92c6}{#1}"); +defineMacro("\\maroonC", "\\textcolor{##ed5fa6}{#1}"); +defineMacro("\\maroonD", "\\textcolor{##ca337c}{#1}"); +defineMacro("\\maroonE", "\\textcolor{##9e034e}{#1}"); +defineMacro("\\purpleA", "\\textcolor{##ddd7ff}{#1}"); +defineMacro("\\purpleB", "\\textcolor{##c6b9fc}{#1}"); +defineMacro("\\purpleC", "\\textcolor{##aa87ff}{#1}"); +defineMacro("\\purpleD", "\\textcolor{##7854ab}{#1}"); +defineMacro("\\purpleE", "\\textcolor{##543b78}{#1}"); +defineMacro("\\mintA", "\\textcolor{##f5f9e8}{#1}"); +defineMacro("\\mintB", "\\textcolor{##edf2df}{#1}"); +defineMacro("\\mintC", "\\textcolor{##e0e5cc}{#1}"); +defineMacro("\\grayA", "\\textcolor{##f6f7f7}{#1}"); +defineMacro("\\grayB", "\\textcolor{##f0f1f2}{#1}"); +defineMacro("\\grayC", "\\textcolor{##e3e5e6}{#1}"); +defineMacro("\\grayD", "\\textcolor{##d6d8da}{#1}"); +defineMacro("\\grayE", "\\textcolor{##babec2}{#1}"); +defineMacro("\\grayF", "\\textcolor{##888d93}{#1}"); +defineMacro("\\grayG", "\\textcolor{##626569}{#1}"); +defineMacro("\\grayH", "\\textcolor{##3b3e40}{#1}"); +defineMacro("\\grayI", "\\textcolor{##21242c}{#1}"); +defineMacro("\\kaBlue", "\\textcolor{##314453}{#1}"); +defineMacro("\\kaGreen", "\\textcolor{##71B307}{#1}"); diff --git a/frontend/node_modules/katex/src/mathMLTree.js b/frontend/node_modules/katex/src/mathMLTree.js new file mode 100644 index 0000000..3b59183 --- /dev/null +++ b/frontend/node_modules/katex/src/mathMLTree.js @@ -0,0 +1,267 @@ +// @flow +/** + * These objects store data about MathML nodes. This is the MathML equivalent + * of the types in domTree.js. Since MathML handles its own rendering, and + * since we're mainly using MathML to improve accessibility, we don't manage + * any of the styling state that the plain DOM nodes do. + * + * The `toNode` and `toMarkup` functions work similarly to how they do in + * domTree.js, creating namespaced DOM nodes and HTML text markup respectively. + */ + +import utils from "./utils"; +import {DocumentFragment} from "./tree"; +import {createClass} from "./domTree"; +import {makeEm} from "./units"; + +import type {VirtualNode} from "./tree"; + +/** + * MathML node types used in KaTeX. For a complete list of MathML nodes, see + * https://developer.mozilla.org/en-US/docs/Web/MathML/Element. + */ +export type MathNodeType = + "math" | "annotation" | "semantics" | + "mtext" | "mn" | "mo" | "mi" | "mspace" | + "mover" | "munder" | "munderover" | "msup" | "msub" | "msubsup" | + "mfrac" | "mroot" | "msqrt" | + "mtable" | "mtr" | "mtd" | "mlabeledtr" | + "mrow" | "menclose" | + "mstyle" | "mpadded" | "mphantom" | "mglyph"; + +export interface MathDomNode extends VirtualNode { + toText(): string; +} + +export type documentFragment = DocumentFragment; +export function newDocumentFragment( + children: $ReadOnlyArray +): documentFragment { + return new DocumentFragment(children); +} + +/** + * This node represents a general purpose MathML node of any type. The + * constructor requires the type of node to create (for example, `"mo"` or + * `"mspace"`, corresponding to `` and `` tags). + */ +export class MathNode implements MathDomNode { + type: MathNodeType; + attributes: {[string]: string}; + children: $ReadOnlyArray; + classes: string[]; + + constructor( + type: MathNodeType, + children?: $ReadOnlyArray, + classes?: string[] + ) { + this.type = type; + this.attributes = {}; + this.children = children || []; + this.classes = classes || []; + } + + /** + * Sets an attribute on a MathML node. MathML depends on attributes to convey a + * semantic content, so this is used heavily. + */ + setAttribute(name: string, value: string) { + this.attributes[name] = value; + } + + /** + * Gets an attribute on a MathML node. + */ + getAttribute(name: string): string { + return this.attributes[name]; + } + + /** + * Converts the math node into a MathML-namespaced DOM element. + */ + toNode(): Node { + const node = document.createElementNS( + "http://www.w3.org/1998/Math/MathML", this.type); + + for (const attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } + + if (this.classes.length > 0) { + node.className = createClass(this.classes); + } + + for (let i = 0; i < this.children.length; i++) { + // Combine multiple TextNodes into one TextNode, to prevent + // screen readers from reading each as a separate word [#3995] + if (this.children[i] instanceof TextNode && + this.children[i + 1] instanceof TextNode) { + let text = this.children[i].toText() + this.children[++i].toText(); + while (this.children[i + 1] instanceof TextNode) { + text += this.children[++i].toText(); + } + node.appendChild(new TextNode(text).toNode()); + } else { + node.appendChild(this.children[i].toNode()); + } + } + + return node; + } + + /** + * Converts the math node into an HTML markup string. + */ + toMarkup(): string { + let markup = "<" + this.type; + + // Add the attributes + for (const attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + markup += " " + attr + "=\""; + markup += utils.escape(this.attributes[attr]); + markup += "\""; + } + } + + if (this.classes.length > 0) { + markup += ` class ="${utils.escape(createClass(this.classes))}"`; + } + + markup += ">"; + + for (let i = 0; i < this.children.length; i++) { + markup += this.children[i].toMarkup(); + } + + markup += ""; + + return markup; + } + + /** + * Converts the math node into a string, similar to innerText, but escaped. + */ + toText(): string { + return this.children.map(child => child.toText()).join(""); + } +} + +/** + * This node represents a piece of text. + */ +export class TextNode implements MathDomNode { + text: string; + + constructor(text: string) { + this.text = text; + } + + /** + * Converts the text node into a DOM text node. + */ + toNode(): Node { + return document.createTextNode(this.text); + } + + /** + * Converts the text node into escaped HTML markup + * (representing the text itself). + */ + toMarkup(): string { + return utils.escape(this.toText()); + } + + /** + * Converts the text node into a string + * (representing the text itself). + */ + toText(): string { + return this.text; + } +} + +/** + * This node represents a space, but may render as or as text, + * depending on the width. + */ +class SpaceNode implements MathDomNode { + width: number; + character: ?string; + + /** + * Create a Space node with width given in CSS ems. + */ + constructor(width: number) { + this.width = width; + // See https://www.w3.org/TR/2000/WD-MathML2-20000328/chapter6.html + // for a table of space-like characters. We use Unicode + // representations instead of &LongNames; as it's not clear how to + // make the latter via document.createTextNode. + if (width >= 0.05555 && width <= 0.05556) { + this.character = "\u200a"; //   + } else if (width >= 0.1666 && width <= 0.1667) { + this.character = "\u2009"; //   + } else if (width >= 0.2222 && width <= 0.2223) { + this.character = "\u2005"; //   + } else if (width >= 0.2777 && width <= 0.2778) { + this.character = "\u2005\u200a"; //    + } else if (width >= -0.05556 && width <= -0.05555) { + this.character = "\u200a\u2063"; // ​ + } else if (width >= -0.1667 && width <= -0.1666) { + this.character = "\u2009\u2063"; // ​ + } else if (width >= -0.2223 && width <= -0.2222) { + this.character = "\u205f\u2063"; // ​ + } else if (width >= -0.2778 && width <= -0.2777) { + this.character = "\u2005\u2063"; // ​ + } else { + this.character = null; + } + } + + /** + * Converts the math node into a MathML-namespaced DOM element. + */ + toNode(): Node { + if (this.character) { + return document.createTextNode(this.character); + } else { + const node = document.createElementNS( + "http://www.w3.org/1998/Math/MathML", "mspace"); + node.setAttribute("width", makeEm(this.width)); + return node; + } + } + + /** + * Converts the math node into an HTML markup string. + */ + toMarkup(): string { + if (this.character) { + return `${this.character}`; + } else { + return ``; + } + } + + /** + * Converts the math node into a string, similar to innerText. + */ + toText(): string { + if (this.character) { + return this.character; + } else { + return " "; + } + } +} + +export default { + MathNode, + TextNode, + SpaceNode, + newDocumentFragment, +}; diff --git a/frontend/node_modules/katex/src/metrics/README.md b/frontend/node_modules/katex/src/metrics/README.md new file mode 100644 index 0000000..c340e72 --- /dev/null +++ b/frontend/node_modules/katex/src/metrics/README.md @@ -0,0 +1,23 @@ +### How to generate new metrics +------------------------------- + +There are several requirements for generating the metrics used by KaTeX. + +- You need to have an installation of TeX which supports kpathsea. You can check + this by running `tex --version`, and seeing if it has a line that looks like + > kpathsea version 6.2.0 + +- You need the Perl module `JSON`. You can install this either from CPAN + (e.g. using the `cpan` command line tool: `cpan install JSON`) + or with your package manager. + +- You need the Python module `fonttools`. You can install this either from PyPI + (using `easy_install` or `pip`: `pip install fonttools`) + or with your package manager. + +Once you have these things, run the following command from the root directory: + + sh ./dockers/fonts/buildMetrics.sh + +which should generate new metrics and place them into `fontMetricsData.json`. +You're done! diff --git a/frontend/node_modules/katex/src/metrics/extract_tfms.py b/frontend/node_modules/katex/src/metrics/extract_tfms.py new file mode 100755 index 0000000..70297dc --- /dev/null +++ b/frontend/node_modules/katex/src/metrics/extract_tfms.py @@ -0,0 +1,114 @@ +#!/usr/bin/env python3 + +import collections +import json +import parse_tfm +import subprocess +import sys + + +def find_font_path(font_name): + try: + font_path = subprocess.check_output(['kpsewhich', font_name]) + except OSError: + raise RuntimeError("Couldn't find kpsewhich program, make sure you" + + " have TeX installed") + except subprocess.CalledProcessError: + raise RuntimeError("Couldn't find font metrics: '%s'" % font_name) + return font_path.strip() + + +def main(): + mapping = json.load(sys.stdin) + + fonts = [ + 'cmbsy10.tfm', + 'cmbx10.tfm', + 'cmbxti10.tfm', + 'cmex10.tfm', + 'cmmi10.tfm', + 'cmmib10.tfm', + 'cmr10.tfm', + 'cmsy10.tfm', + 'cmti10.tfm', + 'msam10.tfm', + 'msbm10.tfm', + 'eufm10.tfm', + 'cmtt10.tfm', + 'rsfs10.tfm', + 'cmss10.tfm', + 'cmssbx10.tfm', + 'cmssi10.tfm', + ] + + # Extracted by running `\font\a=` and then `\showthe\skewchar\a` in + # TeX, where `` is the name of the font listed here. The skewchar + # will be printed out in the output. If it outputs `-1`, that means there + # is no skewchar, so we use `None` here. + font_skewchar = { + 'cmbsy10': None, + 'cmbx10': None, + 'cmbxti10': None, + 'cmex10': None, + 'cmmi10': 127, + 'cmmib10': None, + 'cmr10': None, + 'cmsy10': 48, + 'cmti10': None, + 'msam10': None, + 'msbm10': None, + 'eufm10': None, + 'cmtt10': None, + 'rsfs10': None, + 'cmss10': None, + 'cmssbx10': None, + 'cmssi10': None, + } + + font_name_to_tfm = {} + + for font_name in fonts: + font_basename = font_name.split('.')[0] + font_path = find_font_path(font_name) + font_name_to_tfm[font_basename] = parse_tfm.read_tfm_file(font_path) + + families = collections.defaultdict(dict) + + for family, chars in mapping.items(): + for char, char_data in chars.items(): + char_num = int(char) + + font = char_data['font'] + tex_char_num = int(char_data['char']) + yshift = float(char_data['yshift']) + + if family == "Script-Regular": + tfm_char = font_name_to_tfm[font].get_char_metrics(tex_char_num, + fix_rsfs=True) + else: + tfm_char = font_name_to_tfm[font].get_char_metrics(tex_char_num) + + height = round(tfm_char.height + yshift / 1000.0, 5) + depth = round(tfm_char.depth - yshift / 1000.0, 5) + italic = round(tfm_char.italic_correction, 5) + width = round(tfm_char.width, 5) + + skewkern = 0.0 + if (font_skewchar[font] and + font_skewchar[font] in tfm_char.kern_table): + skewkern = round( + tfm_char.kern_table[font_skewchar[font]], 5) + + families[family][char_num] = { + 'height': height, + 'depth': depth, + 'italic': italic, + 'skew': skewkern, + 'width': width + } + + sys.stdout.write( + json.dumps(families, separators=(',', ':'), sort_keys=True)) + +if __name__ == '__main__': + main() diff --git a/frontend/node_modules/katex/src/metrics/extract_ttfs.py b/frontend/node_modules/katex/src/metrics/extract_ttfs.py new file mode 100755 index 0000000..29f9225 --- /dev/null +++ b/frontend/node_modules/katex/src/metrics/extract_ttfs.py @@ -0,0 +1,122 @@ +#!/usr/bin/env python3 + +from fontTools.ttLib import TTFont +import sys +import json + +# map of characters to extract +metrics_to_extract = { + # Font name + "AMS-Regular": { + u"\u21e2": None, # \dashrightarrow + u"\u21e0": None, # \dashleftarrow + }, + "Main-Regular": { + # Skew and italic metrics can't be easily parsed from the TTF. Instead, + # we map each character to a "base character", which is a character + # from the same font with correct italic and skew metrics. A character + # maps to None if it doesn't have a base. + + #u"\u2209": None, # \notin + #u"\u2260": None, # \neq + u"\u2245": None, # \cong + u"\u2026": None, # \ldots + u"\u22ef": None, # \cdots + u"\u22f1": None, # \ddots + u"\u22ee": None, # \vdots + u"\u22ee": None, # \vdots + u"\u22a8": None, # \models + u"\u22c8": None, # \bowtie + u"\u2250": None, # \doteq + u"\u23b0": None, # \lmoustache + u"\u23b1": None, # \rmoustache + u"\u27ee": None, # \lgroup + u"\u27ef": None, # \rgroup + u"\u27f5": None, # \longleftarrow + u"\u27f8": None, # \Longleftarrow + u"\u27f6": None, # \longrightarrow + u"\u27f9": None, # \Longrightarrow + u"\u27f7": None, # \longleftrightarrow + u"\u27fa": None, # \Longleftrightarrow + u"\u21a6": None, # \mapsto + u"\u27fc": None, # \longmapsto + u"\u21a9": None, # \hookleftarrow + u"\u21aa": None, # \hookrightarrow + u"\u21cc": None, # \rightleftharpoons + }, + "Main-Bold": { + u"\u2245": None, # \cong + }, + "Size1-Regular": { + u"\u222c": u"\u222b", # \iint, based on \int + u"\u222d": u"\u222b", # \iiint, based on \int + }, + "Size2-Regular": { + u"\u222c": u"\u222b", # \iint, based on \int + u"\u222d": u"\u222b", # \iiint, based on \int + }, +} + + +def main(): + start_json = json.load(sys.stdin) + + for font in start_json: + fontInfo = TTFont("../../fonts/KaTeX_" + font + ".ttf") + glyf = fontInfo["glyf"] + widths = fontInfo.getGlyphSet() + unitsPerEm = float(fontInfo["head"].unitsPerEm) + + # We keep ALL Unicode cmaps, not just fontInfo["cmap"].getcmap(3, 1). + # This is playing it extra safe, since it reports inconsistencies. + # Platform 0 is Unicode, platform 3 is Windows. For platform 3, + # encoding 1 is UCS-2 and encoding 10 is UCS-4. + cmap = [t.cmap for t in fontInfo["cmap"].tables + if (t.platformID == 0) + or (t.platformID == 3 and t.platEncID in (1, 10))] + + chars = metrics_to_extract.get(font, {}) + chars[u"\u0020"] = None # space + chars[u"\u00a0"] = None # nbsp + + for char, base_char in chars.items(): + code = ord(char) + names = set(t.get(code) for t in cmap) + if not names: + sys.stderr.write( + "Codepoint {} of font {} maps to no name\n" + .format(code, font)) + continue + if len(names) != 1: + sys.stderr.write( + "Codepoint {} of font {} maps to multiple names: {}\n" + .format(code, font, ", ".join(sorted(names)))) + continue + name = names.pop() + + height = depth = italic = skew = width = 0 + glyph = glyf[name] + if glyph.numberOfContours: + height = glyph.yMax / unitsPerEm + depth = -glyph.yMin / unitsPerEm + width = widths[name].width / unitsPerEm + if base_char: + base_char_str = str(ord(base_char)) + base_metrics = start_json[font][base_char_str] + italic = base_metrics["italic"] + skew = base_metrics["skew"] + width = base_metrics["width"] + + start_json[font][str(code)] = { + "height": height, + "depth": depth, + "italic": italic, + "skew": skew, + "width": width + } + + sys.stdout.write( + json.dumps(start_json, separators=(',', ':'), sort_keys=True)) + +if __name__ == "__main__": + main() diff --git a/frontend/node_modules/katex/src/metrics/format_json.py b/frontend/node_modules/katex/src/metrics/format_json.py new file mode 100755 index 0000000..0918d4d --- /dev/null +++ b/frontend/node_modules/katex/src/metrics/format_json.py @@ -0,0 +1,28 @@ +#!/usr/bin/env python3 + +import sys +import json + +props = ['depth', 'height', 'italic', 'skew'] + +if len(sys.argv) > 1: + if sys.argv[1] == '--width': + props.append('width') + +data = json.load(sys.stdin) +sys.stdout.write( + "// This file is GENERATED by buildMetrics.sh. DO NOT MODIFY.\n") +sep = "export default {\n " +for font in sorted(data): + sys.stdout.write(sep + json.dumps(font)) + sep = ": {\n " + for glyph in sorted(data[font], key=int): + sys.stdout.write(sep + json.dumps(glyph) + ": ") + + values = [value if value != 0.0 else 0 for value in + [data[font][glyph][key] for key in props]] + + sys.stdout.write(json.dumps(values)) + sep = ",\n " + sep = ",\n },\n " +sys.stdout.write(",\n },\n};\n") diff --git a/frontend/node_modules/katex/src/metrics/mapping.pl b/frontend/node_modules/katex/src/metrics/mapping.pl new file mode 100755 index 0000000..dabc7ce --- /dev/null +++ b/frontend/node_modules/katex/src/metrics/mapping.pl @@ -0,0 +1,1224 @@ +#! /usr/bin/perl + +# Adapted from the MathJax-dev repository file /fonts/OTF/TeX/makeFF under the +# Apache 2 license + +# We use this file to recover the mapping from TeX fonts to KaTeX fonts, to +# accurately extract the metrics from the corresponding .tfm (TeX font metric) +# files + +use JSON; + +$map{cmr10} = { + "Main-Regular" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-125,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x2F] => 0x21, # !, ", #, $, %, &, ', (, ), *, +, comma, -, ., / + 0x22 => 0x201D, # " + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-310], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + 0x19 => 0xDF, # sharp S + 0x1A => 0xE6, # ae ligature + 0x1B => 0x153, # oe ligature + 0x1C => 0xF8, # o with slash + 0x1D => 0xC6, # AE ligature + 0x1E => 0x152, # OE ligature + 0x1F => 0xD8, # O with slash + ], +}; + +$map{cmmi10} = { + "Math-Italic" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + [0xB,0xE] => 0x3B1, # \alpha, \beta, \gamma, \delta + 0xF => 0x3F5, # \elpsilon + [0x10,0x18] => 0x3B6, # \zeta, \eta, \theta, \iota, \kappa, \lambda, \mu, \nu, \xi + [0x19,0x1A] => 0x3C0, # \pi, \rho + [0x1B,0x1D] => 0x3C3, # \sigma, \tau, \upsilon + 0x1E => 0x3D5, # \phi + [0x1F,0x21] => 0x3C7, # \chi, \psi, \omega + 0x22 => 0x3B5, # \varepsilon + 0x23 => 0x3D1, # \vartheta + 0x24 => 0x3D6, # \varpi + 0x25 => 0x3F1, # \varrho + 0x26 => 0x3C2, # \varsigma + 0x27 => 0x3C6, # \varphi + + [0x30,0x39] => 0x30, # Oldstyle 0-9 + [0x41,0x5A] => 0x41, # A-Z + [0x61,0x7A] => 0x61, # a - z + + 0x6F => 0x3BF, # omicron + 0x7B => 0xE131, # \imath (PUA) + 0x7C => 0xE237, # \jmath (PUA) + ], + + "Main-Regular" => [ + 0x28 => 0x21BC, # \leftharpoonup + 0x29 => 0x21BD, # \leftharpoondown + 0x2A => 0x21C0, # \rightharpoonup + 0x2B => 0x21C1, # \rightharpoondown + + 0x2E => 0x25B9, # \triangleright + 0x2F => 0x25C3, # \triangleleft + + 0x3C => 0x3C, # < + 0x3D => 0x2215, # / + 0x3E => 0x3E, # > + 0x3F => 0x22C6, # \star + 0x40 => 0x2202, # \partial + + [0x5B,0x5D] => 0x266D, # \flat, \natural, \sharp + 0x5E => 0x2323, # \smile + 0x5F => 0x2322, # \frown + 0x60 => 0x2113, # \ell + + 0x7D => 0x2118, # \wp + 0x7E => [0x20D7,-653,0],# \vec + ], +}; + +$map{cmsy10} = { + "Main-Regular" => [ + 0 => 0x2212, # - + 1 => 0x22C5, # \cdot + 2 => 0xD7, # \times + 3 => 0x2217, # \ast + 4 => 0xF7, # \div + 5 => 0x22C4, # \diamond + 6 => 0xB1, # \pm + 7 => 0x2213, # \mp + [8,0xC] => 0x2295, # \oplus, \ominus, \otimes, \oslash, \odot + 0xD => 0x25EF, # \bigcirc + [0xE,0xF] => 0x2218, # \circ, \bullet + + 0x10 => 0x224D, # \asymp + 0x11 => 0x2261, # \equiv + [0x12,0x13] => 0x2286, # \subseteq, \supseteq + [0x14,0x15] => 0x2264, # \leq, \geq + [0x16,0x17] => 0x2AAF, # \preceq, \succeq + 0x18 => 0x223C, # \sim + 0x19 => 0x2248, # \approx + [0x1A,0x1B] => 0x2282, # \subset, \supset + [0x1C,0x1D] => 0x226A, # \ll, \gg + [0x1E,0x1F] => 0x227A, # \prec, \succ + + 0x20 => 0x2190, # \leftarrow + 0x21 => 0x2192, # \rightarrow + 0x22 => 0x2191, # \uparrow + 0x23 => 0x2193, # \downarrow + 0x24 => 0x2194, # \leftrightarrow + 0x25 => 0x2197, # \nearrow + 0x26 => 0x2198, # \searrow + 0x27 => 0x2243, # \simeq + + 0x28 => 0x21D0, # \Leftarrow + 0x29 => 0x21D2, # \Rightarrow + 0x2A => 0x21D1, # \Uparrow + 0x2B => 0x21D3, # \Downarrow + 0x2C => 0x21D4, # \Leftrightarrow + 0x2D => 0x2196, # \nwarrow + 0x2E => 0x2199, # \swarrow + 0x2F => 0x221D, # \propto + + 0x30 => 0x2032, # \prime + 0x31 => 0x221E, # \infty + 0x32 => 0x2208, # \in + 0x33 => 0x220B, # \ni + 0x34 => 0x25B3, # \bigtriangleup and \triangle + 0x35 => 0x25BD, # \bigtriangledown + 0x36 => 0xE020, # \not + + 0x38 => 0x2200, # \forall + 0x39 => 0x2203, # \exists + 0x3A => 0xAC, # \neg + 0x3B => 0x2205, # \emptyset + 0x3C => 0x211C, # \Re + 0x3D => 0x2111, # \Im + 0x3E => 0x22A4, # \top + 0x3F => 0x22A5, # \bot + + 0x40 => 0x2135, # \aleph + + 0x5B => 0x222A, # \cup + 0x5C => 0x2229, # \cap + 0x5D => 0x228E, # \uplus + [0x5E,0x5F] => 0x2227, # \wedge, \vee + + [0x60,0x61] => 0x22A2, # \vdash, \dashv + [0x62,0x63] => 0x230A, # \lfloor, \rfloor + [0x64,0x65] => 0x2308, # \lceil, \rceil + 0x66 => 0x7B, # { + 0x67 => 0x7D, # } + [0x68,0x69] => 0x27E8, # \langle, \rangle + 0x6A => 0x7C, # | + 0x6A => 0x2223, # \vert + 0x6B => 0x2225, # \Vert + 0x6C => 0x2195, # \updownarrow + 0x6D => 0x21D5, # \Updownarrow + 0x6E => 0x5C, # \backslash + 0x6E => 0x2216, # \setminus + 0x6F => 0x2240, # \wr + + 0x70 => [0x221A,0,760], # \surd ### adjust position so font doesn't have a large depth + 0x71 => 0x2A3F, # \amalg + 0x72 => 0x2207, # \nabla + 0x73 => 0x222B, # \int + 0x74 => 0x2294, # \sqcup + 0x75 => 0x2293, # \sqcap + [0x76,0x77] => 0x2291, # \sqsubseteq, \sqsupseteq + 0x78 => 0xA7, # \S + [0x79,0x7A] => 0x2020, # \dagger, \ddagger + 0x7B => 0xB6, # \P + 0x7C => 0x2663, # \clubsuit + 0x7D => 0x2662, # \diamondsuit + 0x7E => 0x2661, # \heartsuit + 0x7F => 0x2660, # \spadesuit + ], + + "Caligraphic-Regular" => [ + [0x41,0x5A] => 0x41, # A-Z + ], +}; + +$map{cmex10} = { + "Size1" => [ + 0 => [0x28,0,810], # ( + 1 => [0x29,0,810], # ) + 2 => [0x5B,0,810], # [ + 3 => [0x5D,0,810], # ] + 4 => [0x230A,0,810], # \lfloor + 5 => [0x230B,0,810], # \rfloor + 6 => [0x2308,0,810], # \lceil + 7 => [0x2309,0,810], # \rceil + 8 => [0x7B,0,810], # { + 9 => [0x7D,0,810], # } + 0xA => [0x27E8,0,810], # \langle + 0xB => [0x27E9,0,810], # \rangle + 0xC => [0x2223,0,606], # \vert + 0xD => [0x2225,0,606], # \Vert + 0xE => [0x2F,0,810], # / + 0xF => [0x5C,0,810], # \ + + 0x46 => [0x2A06,0,750], # \bigsqcup + 0x48 => [0x222E,0,805], # \oint + 0x4A => [0x2A00,0,750], # \bigodot + 0x4C => [0x2A01,0,750], # \bigoplus + 0x4E => [0x2A02,0,750], # \bigotimes + + 0x50 => [0x2211,0,750], # \sum + 0x51 => [0x220F,0,750], # \prod + 0x52 => [0x222B,0,805], # \int + 0x53 => [0x22C3,0,750], # \bigcup + 0x54 => [0x22C2,0,750], # \bigcap + 0x55 => [0x2A04,0,750], # \biguplus + 0x56 => [0x22C0,0,750], # \bigwedge + 0x57 => [0x22C1,0,750], # \bigvee + + 0x60 => [0x2210,0,750], # \coprod + 0x62 => 0x2C6, # \widehat + 0x62 => [0x302,-556,0], # \widehat (combining) + 0x65 => 0x2DC, # \widetilde + 0x65 => [0x303,-556,0], # \widetilde (combining) + + 0x70 => [0x221A,0,810], # surd + 0x3F => [0x23D0,0,601], # arrow extension + 0x77 => [0x2016,0,601], # Arrow extension (non-standard) + 0x78 => [0x2191,0,600], # uparrow top + 0x79 => [0x2193,0,600], # downarrow bottom + 0x7E => [0x21D1,0,600], # Uparrow top + 0x7F => [0x21D3,0,600], # Downarrow bottom + ], + + "Size2" => [ + 0x10 => [0x28,0,1110], # ( + 0x11 => [0x29,0,1110], # ) + 0x2E => [0x2F,0,1110], # / + 0x2F => [0x5C,0,1110], # \ + 0x44 => [0x27E8,0,1110],# \langle + 0x45 => [0x27E9,0,1110],# \rangle + + 0x47 => [0x2A06,0,950], # \bigsqcup + 0x49 => [0x222E,0,1360],# \oint + 0x4B => [0x2A00,0,950], # \bigodot + 0x4D => [0x2A01,0,950], # \bigoplus + 0x4F => [0x2A02,0,950], # \bigotimes + + 0x58 => [0x2211,0,950], # \sum + 0x59 => [0x220F,0,950], # \prod + 0x5A => [0x222B,0,1360],# \int + 0x5B => [0x22C3,0,950], # \bigcup + 0x5C => [0x22C2,0,950], # \bigcap + 0x5D => [0x2A04,0,950], # \biguplus + 0x5E => [0x22C0,0,950], # \bigwedge + 0x5F => [0x22C1,0,950], # \bigvee + 0x61 => [0x2210,0,950], # \coprod + + 0x63 => 0x2C6, # \widehat + 0x63 => [0x302,-1000,0],# \widehat (combining) + 0x66 => 0x2DC, # \widetilde + 0x66 => [0x303,-1000,0],# \widetilde (combining) + + 0x68 => [0x5B,0,1110], # [ + 0x69 => [0x5D,0,1110], # ] + 0x6A => [0x230A,0,1110],# \lfloor + 0x6B => [0x230B,0,1110],# \rfloor + 0x6C => [0x2308,0,1110],# \lceil + 0x6D => [0x2309,0,1110],# \rceil + 0x6E => [0x7B,0,1110], # { + 0x6F => [0x7D,0,1110], # } + 0x71 => [0x221A,0,1110],# surd + ], + + "Size3" => [ + 0x12 => [0x28,0,1410], # ( + 0x13 => [0x29,0,1410], # ) + 0x14 => [0x5B,0,1410], # [ + 0x15 => [0x5D,0,1410], # ] + 0x16 => [0x230A,0,1410],# \lfloor + 0x17 => [0x230B,0,1410],# \rfloor + 0x18 => [0x2308,0,1410],# \lceil + 0x19 => [0x2309,0,1410],# \rceil + 0x1A => [0x7B,0,1410], # { + 0x1B => [0x7D,0,1410], # } + 0x1C => [0x27E8,0,1410],# \langle + 0x1D => [0x27E9,0,1410],# \rangle + 0x1E => [0x2F,0,1410], # / + 0x1F => [0x5C,0,1410], # \ + 0x64 => 0x2C6, # \widehat + 0x64 => [0x302,-1444,0],# \widehat (combining) + 0x67 => 0x2DC, # \widetilde + 0x67 => [0x303,-1444,0],# \widetilde (combining) + 0x72 => [0x221A,0,1410],# surd + ], + + "Size4" => [ + 0x20 => [0x28,0,1710], # ( + 0x21 => [0x29,0,1710], # ) + 0x22 => [0x5B,0,1710], # [ + 0x23 => [0x5D,0,1710], # ] + 0x24 => [0x230A,0,1710],# \lfloor + 0x25 => [0x230B,0,1710],# \rfloor + 0x26 => [0x2308,0,1710],# \lceil + 0x27 => [0x2309,0,1710],# \rceil + 0x28 => [0x7B,0,1710], # { + 0x29 => [0x7D,0,1710], # } + 0x2A => [0x27E8,0,1710],# \langle + 0x2B => [0x27E9,0,1710],# \rangle + 0x2C => [0x2F,0,1710], # / + 0x2D => [0x5C,0,1710], # \ + 0x73 => [0x221A,0,1710],# surd + + 0x30 => [0x239B,0,1115],# left paren upper hook + 0x31 => [0x239E,0,1115],# right paren upper hook + 0x32 => [0x23A1,0,1115],# left square bracket upper corner + 0x33 => [0x23A4,0,1115],# right square bracket upper corner + 0x34 => [0x23A3,0,1115],# left square bracket lower corner + 0x35 => [0x23A6,0,1115],# right square bracket lower hook + 0x36 => [0x23A2,0,601], # left square bracket extension + 0x37 => [0x23A5,0,601], # right square bracket extension + 0x38 => [0x23A7,0,900], # left curly brace upper hook + 0x39 => [0x23AB,0,900], # right curly brace upper hook + 0x3A => 0x23A9, # left curly brace lower hook + 0x3B => 0x23AD, # right curly brace lower hook + 0x3C => [0x23A8,0,1150],# left curly brace middle + 0x3D => [0x23AC,0,1150],# right curly brace middle + 0x3E => [0x23AA,0,300], # curly brace extension + + 0x40 => [0x239D,0,1115],# left paren lower hook + 0x41 => [0x23A0,0,1115],# right paren lower hook + 0x42 => [0x239C,0,600], # left paren extension + 0x43 => [0x239F,0,600], # right paren extension + + 0x74 => [0x23B7,0,915], # radical bottom + 0x75 => [0xE000,0,605], # radical extension (PUA) + 0x76 => [0xE001,0,565], # radical top (PUA) + [0x7A,0x7D] => 0xE150, # \braceld, \bracerd, \bracelu, \braceru (PUA) + ], +}; + +$map{cmti10} = { + "Main-Italic" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-160,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x23] => 0x21, # !, ", #, + 0x22 => 0x201D, # " + [0x25,0x2F] => 0x25, # %, &, ', (, ), *, +, comma, -, ., / + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-310], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + 0x19 => 0xDF, # sharp S + 0x1A => 0xE6, # ae ligature + 0x1B => 0x153, # oe ligature + 0x1C => 0xF8, # o with slash + 0x1D => 0xC6, # AE ligature + 0x1E => 0x152, # OE ligature + 0x1F => 0xD8, # O with slash + ], + + "Main-Regular" => [ + 0x24 => 0xA3, # pound sign + ], +}; + +$map{cmbx10} = { + "Main-Bold" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-147,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x2F] => 0x21, # !, ", #, $, %, &, ', (, ), *, +, comma, -, ., / + 0x22 => 0x201D, # " + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-310], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + 0x19 => 0xDF, # sharp S + 0x1A => 0xE6, # ae ligature + 0x1B => 0x153, # oe ligature + 0x1C => 0xF8, # o with slash + 0x1D => 0xC6, # AE ligature + 0x1E => 0x152, # OE ligature + 0x1F => 0xD8, # O with slash + ], +}; + +$map{cmbxti10} = { + "Main-BoldItalic" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-160,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x23] => 0x21, # !, ", #, + 0x22 => 0x201D, # " + [0x25,0x2F] => 0x25, # %, &, ', (, ), *, +, comma, -, ., / + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-310], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + 0x19 => 0xDF, # sharp S + 0x1A => 0xE6, # ae ligature + 0x1B => 0x153, # oe ligature + 0x1C => 0xF8, # o with slash + 0x1D => 0xC6, # AE ligature + 0x1E => 0x152, # OE ligature + 0x1F => 0xD8, # O with slash + ], + + "Main-Bold" => [ + 0x24 => 0xA3, # pound sign + ], +}; + +$map{cmmib10} = { + "Math-BoldItalic" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + [0xB,0xE] => 0x3B1, # \alpha, \beta, \gamma, \delta + 0xF => 0x3F5, # \elpsilon + [0x10,0x18] => 0x3B6, # \zeta, \eta, \theta, \iota, \kappa, \lambda, \mu, \nu, \xi + [0x19,0x1A] => 0x3C0, # \pi, \rho + [0x1B,0x1D] => 0x3C3, # \sigma, \tau, \upsilon + 0x1E => 0x3D5, # \phi + [0x1F,0x21] => 0x3C7, # \chi, \psi, \omega + 0x22 => 0x3B5, # \varepsilon + 0x23 => 0x3D1, # \vartheta + 0x24 => 0x3D6, # \varpi + 0x25 => 0x3F1, # \varrho + 0x26 => 0x3C2, # \varsigma + 0x27 => 0x3C6, # \varphi + + [0x41,0x5A] => 0x41, # A-Z + [0x61,0x7A] => 0x61, # a - z + [0x30,0x39] => 0x30, # Oldstyle 0-9 + + 0x6F => 0x3BF, # omicron + 0x7B => 0xE131, # \imath (PUA) + 0x7C => 0xE237, # \jmath (PUA) + ], + + "Main-Bold" => [ + 0x28 => 0x21BC, # \leftharpoonup + 0x29 => 0x21BD, # \leftharpoondown + 0x2A => 0x21C0, # \rightharpoonup + 0x2B => 0x21C1, # \rightharpoondown + + 0x2E => 0x25B9, # \triangleright + 0x2F => 0x25C3, # \triangleleft + + 0x3C => 0x3C, # < + 0x3D => 0x2215, # / + 0x3E => 0x3E, # > + 0x3F => 0x22C6, # \star + 0x40 => 0x2202, # \partial + + [0x5B,0x5D] => 0x266D, # \flat, \natural, \sharp + 0x5E => 0x2323, # \smile + 0x5F => 0x2322, # \frown + 0x60 => 0x2113, # \ell + 0x68 => 0x210F, # \hbar (bar added below) + + 0x7D => 0x2118, # \wp + 0x7E => [0x20D7,-729,0],# \vec + ], +}; + +$map{cmbsy10} = { + "Main-Bold" => [ + 0 => 0x2212, # - + 1 => 0x22C5, # \cdot + 2 => 0xD7, # \times + 3 => 0x2217, # \ast + 4 => 0xF7, # \div + 5 => 0x22C4, # \diamond + 6 => 0xB1, # \pm + 7 => 0x2213, # \mp + [8,0xC] => 0x2295, # \oplus, \ominus, \otimes, \oslash, \odot + 0xD => 0x25EF, # \bigcirc + [0xE,0xF] => 0x2218, # \circ, \bullet + + 0x10 => 0x224D, # \asymp + 0x11 => 0x2261, # \equiv + [0x12,0x13] => 0x2286, # \subseteq, \supseteq + [0x14,0x15] => 0x2264, # \leq, \geq + [0x16,0x17] => 0x2AAF, # \preceq, \succeq + 0x18 => 0x223C, # \sim + 0x19 => 0x2248, # \approx + [0x1A,0x1B] => 0x2282, # \subset, \supset + [0x1C,0x1D] => 0x226A, # \ll, \gg + [0x1E,0x1F] => 0x227A, # \prec, \succ + + 0x20 => 0x2190, # \leftarrow + 0x21 => 0x2192, # \rightarrow + 0x22 => 0x2191, # \uparrow + 0x23 => 0x2193, # \downarrow + 0x24 => 0x2194, # \leftrightarrow + 0x25 => 0x2197, # \nearrow + 0x26 => 0x2198, # \searrow + 0x27 => 0x2243, # \simeq + + 0x28 => 0x21D0, # \Leftarrow + 0x29 => 0x21D2, # \Rightarrow + 0x2A => 0x21D1, # \Uparrow + 0x2B => 0x21D3, # \Downarrow + 0x2C => 0x21D4, # \Leftrightarrow + 0x2D => 0x2196, # \nwarrow + 0x2E => 0x2199, # \swarrow + 0x2F => 0x221D, # \propto + + 0x30 => 0x2032, # \prime + 0x31 => 0x221E, # \infty + 0x32 => 0x2208, # \in + 0x33 => 0x220B, # \ni + 0x34 => 0x25B3, # \bigtriangleup and \triangle + 0x35 => 0x25BD, # \bigtriangledown + 0x36 => 0xE020, # \not + + 0x38 => 0x2200, # \forall + 0x39 => 0x2203, # \exists + 0x3A => 0xAC, # \neg + 0x3B => 0x2205, # \emptyset + 0x3C => 0x211C, # \Re + 0x3D => 0x2111, # \Im + 0x3E => 0x22A4, # \top + 0x3F => 0x22A5, # \bot + + 0x40 => 0x2135, # \aleph + + 0x5B => 0x222A, # \cup + 0x5C => 0x2229, # \cap + 0x5D => 0x228E, # \uplus + [0x5E,0x5F] => 0x2227, # \wedge, \vee + + [0x60,0x61] => 0x22A2, # \vdash, \dashv + [0x62,0x63] => 0x230A, # \lfloor, \rfloor + [0x64,0x65] => 0x2308, # \lceil, \rceil + 0x66 => 0x7B, # { + 0x67 => 0x7D, # } + [0x68,0x69] => 0x27E8, # \langle, \rangle + 0x6A => 0x7C, # | + 0x6A => 0x2223, # \vert + 0x6B => 0x2225, # \Vert + 0x6C => 0x2195, # \updownarrow + 0x6D => 0x21D5, # \Updownarrow + 0x6E => 0x5C, # \backslash + 0x6E => 0x2216, # \setminus + 0x6F => 0x2240, # \wr + + 0x70 => [0x221A,0,760], # \surd ### adjust position so font doesn't have a large depth + 0x71 => 0x2A3F, # \amalg + 0x72 => 0x2207, # \nabla + 0x73 => 0x222B, # \int + 0x74 => 0x2294, # \sqcup + 0x75 => 0x2293, # \sqcap + [0x76,0x77] => 0x2291, # \sqsubseteq, \sqsupseteq + + [0x79,0x7A] => 0x2020, # \dagger, \ddagger + + 0x7C => 0x2663, # \clubsuit + 0x7D => 0x2662, # \diamondsuit + 0x7E => 0x2661, # \heartsuit + 0x7F => 0x2660, # \spadesuit + ], +}; + +$map{msam10} = { + "Main-Regular" => [ + 0x5C => 0x2220, # \angle + ], + + "Main-Bold" => [ + 0x5C => 0x2220, # \angle (emboldened below) + ], + + "AMS" => [ + 0x00 => 0x22A1, # \boxdot + 0x01 => 0x229E, # \boxplus + 0x02 => 0x22A0, # \boxtimes + 0x03 => 0x25A1, # \square + 0x04 => 0x25A0, # \blacksquare + 0x05 => 0x22C5, # \centerdot + 0x06 => 0x25CA, # \lozenge + 0x07 => 0x29EB, # \blacklozenge + 0x08 => 0x21BB, # \circlearrowright + 0x09 => 0x21BA, # \circlearrowleft + 0x0A => 0x21CC, # \rightleftharpoons + 0x0B => 0x21CB, # \leftrightharpoons + 0x0C => 0x229F, # \boxminus + 0x0D => 0x22A9, # \Vdash + 0x0E => 0x22AA, # \Vvdash + 0x0F => 0x22A8, # \vDash + 0x10 => 0x21A0, # \twoheadrightarrow + 0x11 => 0x219E, # \twoheadleftarrow + 0x12 => 0x21C7, # \leftleftarrows + 0x13 => 0x21C9, # \rightrightarrows + 0x14 => 0x21C8, # \upuparrows + 0x15 => 0x21CA, # \downdownarrows + 0x16 => 0x21BE, # \upharpoonright + 0x17 => 0x21C2, # \downharpoonright + 0x18 => 0x21BF, # \upharpoonleft + 0x19 => 0x21C3, # \downharpoonleft + 0x1A => 0x21A3, # \rightarrowtail + 0x1B => 0x21A2, # \leftarrowtail + 0x1C => 0x21C6, # \leftrightarrows + 0x1D => 0x21C4, # \rightleftarrows + 0x1E => 0x21B0, # \Lsh + 0x1F => 0x21B1, # \Rsh + 0x20 => 0x21DD, # \rightsquigarrow + 0x21 => 0x21AD, # \leftrightsquigarrow + 0x22 => 0x21AB, # \looparrowleft + 0x23 => 0x21AC, # \looparrowright + 0x24 => 0x2257, # \circeq + 0x25 => 0x227F, # \succsim + 0x26 => 0x2273, # \gtrsim + 0x27 => 0x2A86, # \gtrapprox + 0x28 => 0x22B8, # \multimap + 0x29 => 0x2234, # \therefore + 0x2A => 0x2235, # \because + 0x2B => 0x2251, # \doteqdot + 0x2C => 0x225C, # \triangleq + 0x2D => 0x227E, # \precsim + 0x2E => 0x2272, # \lesssim + 0x2F => 0x2A85, # \lessapprox + 0x30 => 0x2A95, # \eqslantless + 0x31 => 0x2A96, # \eqslantgtr + 0x32 => 0x22DE, # \curlyeqprec + 0x33 => 0x22DF, # \curlyeqsucc + 0x34 => 0x227C, # \preccurlyeq + 0x35 => 0x2266, # \leqq + 0x36 => 0x2A7D, # \leqslant + 0x37 => 0x2276, # \lessgtr + 0x38 => 0x2035, # \backprime + 0x39 => 0x2212, # dahsed arrow extension + 0x3A => 0x2253, # \risingdotseq + 0x3B => 0x2252, # \fallingdotseq + 0x3C => 0x227D, # \succcurlyeq + 0x3D => 0x2267, # \geqq + 0x3E => 0x2A7E, # \geqslant + 0x3F => 0x2277, # \gtrless + 0x40 => 0x228F, # \sqsubset + 0x41 => 0x2290, # \sqsupset + 0x42 => 0x22B3, # \vartriangleright + 0x43 => 0x22B2, # \vartriangleleft + 0x44 => 0x22B5, # \trianglerighteq + 0x45 => 0x22B4, # \trianglelefteq + 0x46 => 0x2605, # \bigstar + 0x47 => 0x226C, # \between + 0x48 => 0x25BC, # \blacktriangledown + 0x49 => 0x25B6, # \blacktriangleright + 0x4A => 0x25C0, # \blacktriangleleft + 0x4B => 0x2192, # rightarrow + 0x4C => 0x2190, # leftarrow + 0x4D => 0x25B3, # \vartriangle + 0x4E => 0x25B2, # \blacktriangle + 0x4F => 0x25BD, # \triangledown + 0x50 => 0x2256, # \eqcirc + 0x51 => 0x22DA, # \lesseqgtr + 0x52 => 0x22DB, # \gtreqless + 0x53 => 0x2A8B, # \lesseqqgtr + 0x54 => 0x2A8C, # \gtreqqless + 0x55 => 0x00A5, # yen + 0x56 => 0x21DB, # \Rrightarrow + 0x57 => 0x21DA, # \Lleftarrow + 0x58 => 0x2713, # checkmark + 0x59 => 0x22BB, # \veebar + 0x5A => 0x22BC, # \barwedge + 0x5B => 0x2A5E, # \doublebarwedge + 0x5C => 0x2220, # \angle + 0x5D => 0x2221, # \measuredangle + 0x5E => 0x2222, # \sphericalangle + 0x5F => 0x221D, # \varpropto + 0x60 => 0x2323, # \smallsmile + 0x61 => 0x2322, # \smallfrown + 0x62 => 0x22D0, # \Subset + 0x63 => 0x22D1, # \Supset + 0x64 => 0x22D3, # \Cup + 0x65 => 0x22D2, # \Cap + 0x66 => 0x22CF, # \curlywedge + 0x67 => 0x22CE, # \curlyvee + 0x68 => 0x22CB, # \leftthreetimes + 0x69 => 0x22CC, # \rightthreetimes + 0x6A => 0x2AC5, # \subseteqq + 0x6B => 0x2AC6, # \supseteqq + 0x6C => 0x224F, # \bumpeq + 0x6D => 0x224E, # \Bumpeq + 0x6E => 0x22D8, # \lll + 0x6F => 0x22D9, # \ggg + 0x70 => 0x250C, # \ulcorner + 0x71 => 0x2510, # \urcorner + 0x72 => 0x00AE, # registered sign + 0x73 => 0x24C8, # \circledS + 0x74 => 0x22D4, # \pitchfork + 0x75 => 0x2214, # \dotplus + 0x76 => 0x223D, # \backsim + 0x77 => 0x22CD, # \backsimeq + 0x78 => 0x2514, # \llcorner + 0x79 => 0x2518, # \lrcorner + 0x7A => 0x2720, # maltese cross + 0x7B => 0x2201, # \complement + 0x7C => 0x22BA, # \intercal + 0x7D => 0x229A, # \circledcirc + 0x7E => 0x229B, # \circledast + 0x7F => 0x229D, # \circleddash + ], +}; + +$map{msbm10} = { + "Size4" => [ + 0x5B => 0x2C6, # \widehat + 0x5B => [0x302,-1889,0],# \widehat (combining) + 0x5D => 0x2DC, # \widetilde + 0x5D => [0x303,-1889,0],# \widetilde (combining) + ], + + "Main-Regular" => [ + 0x7E => 0x210F, # \hbar + ], + + "Main-Italic" => [ + 0x7D => 0x210F, # \hbar (with slant) + ], + + "AMS" => [ + 0x00 => 0xE00C, # \lvertneqq + 0x01 => 0xE00D, # \gvertneqq + 0x02 => 0x2270, # \nleq + 0x03 => 0x2271, # \ngeq + 0x04 => 0x226E, # \nless + 0x05 => 0x226F, # \ngtr + 0x06 => 0x2280, # \nprec + 0x07 => 0x2281, # \nsucc + 0x08 => 0x2268, # \lneqq + 0x09 => 0x2269, # \gneqq + 0x0A => 0xE010, # \nleqslant + 0x0B => 0xE00F, # \ngeqslant + 0x0C => 0x2A87, # \lneq + 0x0D => 0x2A88, # \gneq + 0x0E => 0x22E0, # \npreceq + 0x0F => 0x22E1, # \nsucceq + 0x10 => 0x22E8, # \precnsim + 0x11 => 0x22E9, # \succnsim + 0x12 => 0x22E6, # \lnsim + 0x13 => 0x22E7, # \gnsim + 0x14 => 0xE011, # \nleqq + 0x15 => 0xE00E, # \ngeqq + 0x16 => 0x2AB5, # \precneqq + 0x17 => 0x2AB6, # \succneqq + 0x18 => 0x2AB9, # \precnapprox + 0x19 => 0x2ABA, # \succnapprox + 0x1A => 0x2A89, # \lnapprox + 0x1B => 0x2A8A, # \gnapprox + 0x1C => 0x2241, # \nsim + 0x1D => 0x2246, # \ncong + 0x1E => 0x2571, # \diagup + 0x1F => 0x2572, # \diagdown + 0x20 => 0xE01A, # \varsubsetneq + 0x21 => 0xE01B, # \varsupsetneq + 0x22 => 0xE016, # \nsubseteqq + 0x23 => 0xE018, # \nsupseteqq + 0x24 => 0x2ACB, # \subsetneqq + 0x25 => 0x2ACC, # \supsetneqq + 0x26 => 0xE017, # \varsubsetneqq + 0x27 => 0xE019, # \varsupsetneqq + 0x28 => 0x228A, # \subsetneq + 0x29 => 0x228B, # \supsetneq + 0x2A => 0x2288, # \nsubseteq + 0x2B => 0x2289, # \nsupseteq + 0x2C => 0x2226, # \nparallel + 0x2D => 0x2224, # \nmid + 0x2E => 0xE006, # \nshortmid + 0x2F => 0xE007, # \nshortparallel + 0x30 => 0x22AC, # \nvdash + 0x31 => 0x22AE, # \nVdash + 0x32 => 0x22AD, # \nvDash + 0x33 => 0x22AF, # \nVDash + 0x34 => 0x22ED, # \ntrianglerighteq + 0x35 => 0x22EC, # \ntrianglelefteq + 0x36 => 0x22EA, # \ntriangleleft + 0x37 => 0x22EB, # \ntriangleright + 0x38 => 0x219A, # \nleftarrow + 0x39 => 0x219B, # \nrightarrow + 0x3A => 0x21CD, # \nLeftarrow + 0x3B => 0x21CF, # \nRightarrow + 0x3C => 0x21CE, # \nLeftrightarrow + 0x3D => 0x21AE, # \nleftrightarrow + 0x3E => 0x22C7, # \divideontimes + 0x3F => 0x2205, # \varnothing + 0x40 => 0x2204, # \nexists + + [0x41,0x5A] => 0x41, # A-Z + 0x5C => 0x2C6, # \widehat + 0x5C => [0x302,-2333,0],# \widehat (combining) + 0x5E => 0x2DC, # \widetilde + 0x5E => [0x303,-2333,0],# \widetilde (combining) + + 0x60 => 0x2132, # \Finv + 0x61 => 0x2141, # \Game + 0x66 => 0x2127, # \mho + 0x67 => 0x00F0, # \eth + 0x68 => 0x2242, # minus-tilde + 0x69 => 0x2136, # \beth + 0x6A => 0x2137, # \gimel + 0x6B => 0x2138, # \daleth + 0x6C => 0x22D6, # \lessdot + 0x6D => 0x22D7, # \gtrdot + 0x6E => 0x22C9, # \ltimes + 0x6F => 0x22CA, # \rtimes + 0x70 => 0x2223, # \shortmid + 0x71 => 0x2225, # \shortparallel + 0x72 => 0x2216, # \smallsetminus + 0x73 => 0x223C, # \thicksim + 0x74 => 0x2248, # \thickapprox + 0x75 => 0x224A, # \approxeq + 0x76 => 0x2AB8, # \succapprox + 0x77 => 0x2AB7, # \precapprox + 0x78 => 0x21B6, # \curvearrowleft + 0x79 => 0x21B7, # \curvearrowright + 0x7A => 0x03DD, # \digamma + 0x7B => 0x03F0, # \varkappa + 0x7A => 0xE008, # \digamma (non-standard, for IE) + 0x7B => 0xE009, # \varkappa (non-standard, for IE) + 0x7C => 0x006B, # \Bbbk + 0x7D => 0x210F, # \hslash + 0x7E => 0x0127, # \hbar + 0x7F => 0x220D, # \backepsilon + ], +}; + +$map{eufm10} = { + "Fraktur-Regular" => [ + [0,7] => 0xE300, # variants + 0x12 => 0x2018, # left quote + 0x13 => 0x2019, # right quote + 0x21 => 0x21, # ! + [0x26,0x2F] => 0x26, # &, ', (, ), *, +, comma, -, ., / + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + 0x3F => 0x3F, # ? + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + [0x5D,0x5E] => 0x5D, # ], ^ + [0x61,0x7A] => 0x61, # a-z + 0x7D => 0x22, # " + ], +}; + +$map{cmtt10} = { + "Typewriter-Regular" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + 0xD => 0x2032, # ' + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => 0xB0, # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + 0x20 => 0x2423, # graphic representation of space + + [0x21,0x7F] => 0x21, + + 0x27 => 0x2018, # left quote + 0x60 => 0x2019, # right quote + 0x5E => [0x302,-525,0], # \hat (combining) + 0x7E => [0x303,-525,0], # \tilde (combining) + 0x7F => [0x308,-525,0], # \ddot (combining) + ], +}; + +$map{rsfs10} = { + "Script-Regular" => [ + [0x41,0x5A] => 0x41, # A-Z + ], +}; + +$map{cmssbx10} = { + "SansSerif-Bold" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x13 => 0xB4, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-58,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x2F] => 0x21, # !, ", #, $, %, &, ', (, ), *, +, comma, -, ., / + 0x22 => 0x201D, # " + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-350], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + ], +}; + +$map{cmss10} = { + "SansSerif-Regular" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-142,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x2F] => 0x21, # !, ", #, $, %, &, ', (, ), *, +, comma, -, ., / + 0x22 => 0x201D, # " + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-350], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + ], +}; + +$map{cmssi10} = { + "SansSerif-Italic" => [ + [0,1] => 0x393, # \Gamma, \Delta + 2 => 0x398, # \Theta + 3 => 0x39B, # \Lambda + 4 => 0x39E, # \Xi + 5 => 0x3A0, # \Pi + 6 => 0x3A3, # \Sigma + [7,8] => 0x3A5, # \Upsilon, \Phi + [9,0xA] => 0x3A8, # \Psi, \Omega + + 0x10 => 0x131, # \i + 0x11 => 0x237, # \j + 0x12 => 0x2CB, # \grave + 0x13 => 0x2CA, # \acute + 0x14 => 0x2C7, # \check + 0x15 => 0x2D8, # \breve + 0x16 => 0x2C9, # \bar + 0x17 => [0xB0,-113,0], # \degree + 0x17 => 0x02DA, # \r, ring above + 0x18 => 0xB8, # \c, cedilla + + [0x21,0x2F] => 0x21, # !, ", #, $, %, &, ', (, ), *, +, comma, -, ., / + 0x22 => 0x201D, # " + 0x27 => 0x2019, # ' + [0x30,0x39] => 0x30, # 0-9 + [0x3A,0x3B] => 0x3A, # :, ; + 0x3D => 0x3D, # = + [0x3F,0x40] => 0x3F, # ?, @ + [0x41,0x5A] => 0x41, # A-Z + 0x5B => 0x5B, # [ + 0x5C => 0x201C, # `` + [0x5D,0x5E] => 0x5D, # ], ^ + 0x5E => 0x2C6, # \hat + 0x5F => 0x2D9, # \dot + 0x60 => 0x2018, # ` + [0x61,0x7A] => 0x61, # a-z + [0x7B,0x7C] => 0x2013, # \endash, \emdash + 0x7B => [0x5F,0,-350], # underline + 0x7D => 0x2DD, # double acute + 0x7E => [0x7E,0,-350], # ~ + 0x7E => 0x2DC, # \tilde + 0x7F => 0xA8, # \ddot + ], +}; + +foreach $cmfont (keys %map) { + foreach $mjfont (keys %{$map{$cmfont}}) { + $style = $mjfont; $style =~ s/.*?(-|$)//; $style = "Regular" unless $style; + $family = $mjfont; $family =~ s/-.*//; + $fontname = "$family-$style"; + @{$reverse{$fontname}{$cmfont}} = @{$map{$cmfont}{$mjfont}}; + } +} + +my %output; + +sub add_to_output { + my ($mjfont,$cmfont,$from,$to) = @_; + + my $xshift = 0, $yshift = 0; + + if (ref($to) eq "ARRAY") { + $xshift = $to->[1]; + $yshift = $to->[2]; + $to = $to->[0]; + } + + $data = { + "font" => $cmfont, + "char" => $from, + "xshift" => $xshift, + "yshift" => $yshift + }; + + if (defined($output{$mjfont}{$to})) { + print STDERR "Duplicate mapping $to for $mjfont: " . + $output{$mjfont}{$to}{font} . ":" . + $output{$mjfont}{$to}{char} . " vs. $cmfont:$from\n"; + die "Duplicate mapping!"; # disable this line to see all of them + } + $output{$mjfont}{$to} = $data; +} + +foreach $mjfont (keys %reverse) { + foreach $cmfont (keys %{$reverse{$mjfont}}) { + @remap = @{$reverse{$mjfont}{$cmfont}}; + while (defined($item = shift(@remap))) { + $remap = shift(@remap); + + if (ref($item) eq "ARRAY") { + foreach $from ($item->[0]...$item->[1]) { + $to = $from - $item->[0] + $remap; + add_to_output($mjfont, $cmfont, $from, $to); + } + } else { + add_to_output($mjfont, $cmfont, $item, $remap); + } + } + } +} + +print(encode_json(\%output)); diff --git a/frontend/node_modules/katex/src/metrics/parse_tfm.py b/frontend/node_modules/katex/src/metrics/parse_tfm.py new file mode 100644 index 0000000..56f2db0 --- /dev/null +++ b/frontend/node_modules/katex/src/metrics/parse_tfm.py @@ -0,0 +1,211 @@ +class CharInfoWord(object): + def __init__(self, word): + b1, b2, b3, b4 = (word >> 24, + (word & 0xff0000) >> 16, + (word & 0xff00) >> 8, + word & 0xff) + + self.width_index = b1 + self.height_index = b2 >> 4 + self.depth_index = b2 & 0x0f + self.italic_index = (b3 & 0b11111100) >> 2 + self.tag = b3 & 0b11 + self.remainder = b4 + + def has_ligkern(self): + return self.tag == 1 + + def ligkern_start(self): + return self.remainder + + +class LigKernProgram(object): + def __init__(self, program): + self.program = program + + def execute(self, start, next_char): + curr_instruction = start + while True: + instruction = self.program[curr_instruction] + (skip, inst_next_char, op, remainder) = instruction + + if inst_next_char == next_char: + if op < 128: + # Don't worry about ligatures for now, we only need kerns + return None + else: + return 256 * (op - 128) + remainder + elif skip >= 128: + return None + else: + curr_instruction += 1 + skip + + +class TfmCharMetrics(object): + def __init__(self, width, height, depth, italic, kern_table): + self.width = width + self.height = height + self.depth = depth + self.italic_correction = italic + self.kern_table = kern_table + + +class TfmFile(object): + def __init__(self, start_char, end_char, char_info, width_table, + height_table, depth_table, italic_table, ligkern_table, + kern_table): + self.start_char = start_char + self.end_char = end_char + self.char_info = char_info + self.width_table = width_table + self.height_table = height_table + self.depth_table = depth_table + self.italic_table = italic_table + self.ligkern_program = LigKernProgram(ligkern_table) + self.kern_table = kern_table + + def get_char_metrics(self, char_num, fix_rsfs=False): + """Return glyph metrics for a unicode code point. + + Arguments: + char_num: a unicode code point + fix_rsfs: adjust for rsfs10.tfm's different indexing system + """ + if char_num < self.start_char or char_num > self.end_char: + raise RuntimeError("Invalid character number") + + if fix_rsfs: + # all of the char_nums contained start from zero in rsfs10.tfm + info = self.char_info[char_num - self.start_char] + else: + info = self.char_info[char_num + self.start_char] + + char_kern_table = {} + if info.has_ligkern(): + for char in range(self.start_char, self.end_char + 1): + kern = self.ligkern_program.execute(info.ligkern_start(), char) + if kern: + char_kern_table[char] = self.kern_table[kern] + + return TfmCharMetrics( + self.width_table[info.width_index], + self.height_table[info.height_index], + self.depth_table[info.depth_index], + self.italic_table[info.italic_index], + char_kern_table) + + +class TfmReader(object): + def __init__(self, f): + self.f = f + + def read_byte(self): + return ord(self.f.read(1)) + + def read_halfword(self): + b1 = self.read_byte() + b2 = self.read_byte() + return (b1 << 8) | b2 + + def read_word(self): + b1 = self.read_byte() + b2 = self.read_byte() + b3 = self.read_byte() + b4 = self.read_byte() + return (b1 << 24) | (b2 << 16) | (b3 << 8) | b4 + + def read_fixword(self): + word = self.read_word() + + neg = False + if word & 0x80000000: + neg = True + word = (-word & 0xffffffff) + + return (-1 if neg else 1) * word / float(1 << 20) + + def read_bcpl(self, length): + str_length = self.read_byte() + data = self.f.read(length - 1) + return data[:str_length] + + +def read_tfm_file(file_name): + with open(file_name, 'rb') as f: + reader = TfmReader(f) + + # file_size + reader.read_halfword() + header_size = reader.read_halfword() + + start_char = reader.read_halfword() + end_char = reader.read_halfword() + + width_table_size = reader.read_halfword() + height_table_size = reader.read_halfword() + depth_table_size = reader.read_halfword() + italic_table_size = reader.read_halfword() + + ligkern_table_size = reader.read_halfword() + kern_table_size = reader.read_halfword() + + # extensible_table_size + reader.read_halfword() + # parameter_table_size + reader.read_halfword() + + # checksum + reader.read_word() + # design_size + reader.read_fixword() + + if header_size > 2: + # coding_scheme + reader.read_bcpl(40) + + if header_size > 12: + # font_family + reader.read_bcpl(20) + + for i in range(header_size - 17): + reader.read_word() + + char_info = [] + for i in range(start_char, end_char + 1): + char_info.append(CharInfoWord(reader.read_word())) + + width_table = [] + for i in range(width_table_size): + width_table.append(reader.read_fixword()) + + height_table = [] + for i in range(height_table_size): + height_table.append(reader.read_fixword()) + + depth_table = [] + for i in range(depth_table_size): + depth_table.append(reader.read_fixword()) + + italic_table = [] + for i in range(italic_table_size): + italic_table.append(reader.read_fixword()) + + ligkern_table = [] + for i in range(ligkern_table_size): + skip = reader.read_byte() + next_char = reader.read_byte() + op = reader.read_byte() + remainder = reader.read_byte() + + ligkern_table.append((skip, next_char, op, remainder)) + + kern_table = [] + for i in range(kern_table_size): + kern_table.append(reader.read_fixword()) + + # There is more information, like the ligkern, kern, extensible, and + # param table, but we don't need these for now + + return TfmFile(start_char, end_char, char_info, width_table, + height_table, depth_table, italic_table, + ligkern_table, kern_table) diff --git a/frontend/node_modules/katex/src/parseNode.js b/frontend/node_modules/katex/src/parseNode.js new file mode 100644 index 0000000..f1fe7b6 --- /dev/null +++ b/frontend/node_modules/katex/src/parseNode.js @@ -0,0 +1,524 @@ +// @flow +import {NON_ATOMS} from "./symbols"; +import type SourceLocation from "./SourceLocation"; +import type {AlignSpec, ColSeparationType} from "./environments/array"; +import type {Atom} from "./symbols"; +import type {Mode, StyleStr} from "./types"; +import type {Token} from "./Token"; +import type {Measurement} from "./units"; + +export type NodeType = $Keys; +export type ParseNode = $ElementType; + +// ParseNode's corresponding to Symbol `Group`s in symbols.js. +export type SymbolParseNode = + ParseNode<"atom"> | + ParseNode<"accent-token"> | + ParseNode<"mathord"> | + ParseNode<"op-token"> | + ParseNode<"spacing"> | + ParseNode<"textord">; + +// ParseNode from `Parser.formatUnsupportedCmd` +export type UnsupportedCmdParseNode = ParseNode<"color">; + +// Union of all possible `ParseNode<>` types. +export type AnyParseNode = $Values; + +// Map from `NodeType` to the corresponding `ParseNode`. +type ParseNodeTypes = { + "array": {| + type: "array", + mode: Mode, + loc?: ?SourceLocation, + colSeparationType?: ColSeparationType, + hskipBeforeAndAfter?: boolean, + addJot?: boolean, + cols?: AlignSpec[], + arraystretch: number, + body: AnyParseNode[][], // List of rows in the (2D) array. + rowGaps: (?Measurement)[], + hLinesBeforeRow: Array, + // Whether each row should be automatically numbered, or an explicit tag + tags?: (boolean | AnyParseNode[])[], + leqno?: boolean, + isCD?: boolean, + |}, + "cdlabel": {| + type: "cdlabel", + mode: Mode, + loc?: ?SourceLocation, + side: string, + label: AnyParseNode, + |}, + "cdlabelparent": {| + type: "cdlabelparent", + mode: Mode, + loc?: ?SourceLocation, + fragment: AnyParseNode, + |}, + "color": {| + type: "color", + mode: Mode, + loc?: ?SourceLocation, + color: string, + body: AnyParseNode[], + |}, + "color-token": {| + type: "color-token", + mode: Mode, + loc?: ?SourceLocation, + color: string, + |}, + // To avoid requiring run-time type assertions, this more carefully captures + // the requirements on the fields per the op.js htmlBuilder logic: + // - `body` and `value` are NEVER set simultaneously. + // - When `symbol` is true, `body` is set. + "op": {| + type: "op", + mode: Mode, + loc?: ?SourceLocation, + limits: boolean, + alwaysHandleSupSub?: boolean, + suppressBaseShift?: boolean, + parentIsSupSub: boolean, + symbol: boolean, + name: string, + body?: void, + |} | {| + type: "op", + mode: Mode, + loc?: ?SourceLocation, + limits: boolean, + alwaysHandleSupSub?: boolean, + suppressBaseShift?: boolean, + parentIsSupSub: boolean, + symbol: false, // If 'symbol' is true, `body` *must* be set. + name?: void, + body: AnyParseNode[], + |}, + "ordgroup": {| + type: "ordgroup", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode[], + semisimple?: boolean, + |}, + "raw": {| + type: "raw", + mode: Mode, + loc?: ?SourceLocation, + string: string, + |}, + "size": {| + type: "size", + mode: Mode, + loc?: ?SourceLocation, + value: Measurement, + isBlank: boolean, + |}, + "styling": {| + type: "styling", + mode: Mode, + loc?: ?SourceLocation, + style: StyleStr, + body: AnyParseNode[], + |}, + "supsub": {| + type: "supsub", + mode: Mode, + loc?: ?SourceLocation, + base: ?AnyParseNode, + sup?: ?AnyParseNode, + sub?: ?AnyParseNode, + |}, + "tag": {| + type: "tag", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode[], + tag: AnyParseNode[], + |}, + "text": {| + type: "text", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode[], + font?: string, + |}, + "url": {| + type: "url", + mode: Mode, + loc?: ?SourceLocation, + url: string, + |}, + "verb": {| + type: "verb", + mode: Mode, + loc?: ?SourceLocation, + body: string, + star: boolean, + |}, + // From symbol groups, constructed in Parser.js via `symbols` lookup. + // (Some of these have "-token" suffix to distinguish them from existing + // `ParseNode` types.) + "atom": {| + type: "atom", + family: Atom, + mode: Mode, + loc?: ?SourceLocation, + text: string, + |}, + "mathord": {| + type: "mathord", + mode: Mode, + loc?: ?SourceLocation, + text: string, + |}, + "spacing": {| + type: "spacing", + mode: Mode, + loc?: ?SourceLocation, + text: string, + |}, + "textord": {| + type: "textord", + mode: Mode, + loc?: ?SourceLocation, + text: string, + |}, + // These "-token" types don't have corresponding HTML/MathML builders. + "accent-token": {| + type: "accent-token", + mode: Mode, + loc?: ?SourceLocation, + text: string, + |}, + "op-token": {| + type: "op-token", + mode: Mode, + loc?: ?SourceLocation, + text: string, + |}, + // From functions.js and functions/*.js. See also "color", "op", "styling", + // and "text" above. + "accent": {| + type: "accent", + mode: Mode, + loc?: ?SourceLocation, + label: string, + isStretchy?: boolean, + isShifty?: boolean, + base: AnyParseNode, + |}, + "accentUnder": {| + type: "accentUnder", + mode: Mode, + loc?: ?SourceLocation, + label: string, + isStretchy?: boolean, + isShifty?: boolean, + base: AnyParseNode, + |}, + "cr": {| + type: "cr", + mode: Mode, + loc?: ?SourceLocation, + newLine: boolean, + size: ?Measurement, + |}, + "delimsizing": {| + type: "delimsizing", + mode: Mode, + loc?: ?SourceLocation, + size: 1 | 2 | 3 | 4, + mclass: "mopen" | "mclose" | "mrel" | "mord", + delim: string, + |}, + "enclose": {| + type: "enclose", + mode: Mode, + loc?: ?SourceLocation, + label: string, + backgroundColor?: string, + borderColor?: string, + body: AnyParseNode, + |}, + "environment": {| + type: "environment", + mode: Mode, + loc?: ?SourceLocation, + name: string, + nameGroup: AnyParseNode, + |}, + "font": {| + type: "font", + mode: Mode, + loc?: ?SourceLocation, + font: string, + body: AnyParseNode, + |}, + "genfrac": {| + type: "genfrac", + mode: Mode, + loc?: ?SourceLocation, + continued: boolean, + numer: AnyParseNode, + denom: AnyParseNode, + hasBarLine: boolean, + leftDelim: ?string, + rightDelim: ?string, + size: StyleStr | "auto", + barSize: Measurement | null, + |}, + "hbox": {| + type: "hbox", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode[], + |}, + "horizBrace": {| + type: "horizBrace", + mode: Mode, + loc?: ?SourceLocation, + label: string, + isOver: boolean, + base: AnyParseNode, + |}, + "href": {| + type: "href", + mode: Mode, + loc?: ?SourceLocation, + href: string, + body: AnyParseNode[], + |}, + "html": {| + type: "html", + mode: Mode, + loc?: ?SourceLocation, + attributes: {[string]: string}, + body: AnyParseNode[], + |}, + "htmlmathml": {| + type: "htmlmathml", + mode: Mode, + loc?: ?SourceLocation, + html: AnyParseNode[], + mathml: AnyParseNode[], + |}, + "includegraphics": {| + type: "includegraphics", + mode: Mode, + loc?: ?SourceLocation, + alt: string, + width: Measurement, + height: Measurement, + totalheight: Measurement, + src: string, + |}, + "infix": {| + type: "infix", + mode: Mode, + loc?: ?SourceLocation, + replaceWith: string, + size?: Measurement, + token: ?Token, + |}, + "internal": {| + type: "internal", + mode: Mode, + loc?: ?SourceLocation, + |}, + "kern": {| + type: "kern", + mode: Mode, + loc?: ?SourceLocation, + dimension: Measurement, + |}, + "lap": {| + type: "lap", + mode: Mode, + loc?: ?SourceLocation, + alignment: string, + body: AnyParseNode, + |}, + "leftright": {| + type: "leftright", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode[], + left: string, + right: string, + rightColor: ?string, // undefined means "inherit" + |}, + "leftright-right": {| + type: "leftright-right", + mode: Mode, + loc?: ?SourceLocation, + delim: string, + color: ?string, // undefined means "inherit" + |}, + "mathchoice": {| + type: "mathchoice", + mode: Mode, + loc?: ?SourceLocation, + display: AnyParseNode[], + text: AnyParseNode[], + script: AnyParseNode[], + scriptscript: AnyParseNode[], + |}, + "middle": {| + type: "middle", + mode: Mode, + loc?: ?SourceLocation, + delim: string, + |}, + "mclass": {| + type: "mclass", + mode: Mode, + loc?: ?SourceLocation, + mclass: string, + body: AnyParseNode[], + isCharacterBox: boolean, + |}, + "operatorname": {| + type: "operatorname", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode[], + alwaysHandleSupSub: boolean, + limits: boolean, + parentIsSupSub: boolean, + |}, + "overline": {| + type: "overline", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode, + |}, + "phantom": {| + type: "phantom", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode[], + |}, + "hphantom": {| + type: "hphantom", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode, + |}, + "vphantom": {| + type: "vphantom", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode, + |}, + "pmb": {| + type: "pmb", + mode: Mode, + loc?: ?SourceLocation, + mclass: string, + body: AnyParseNode[], + |}, + "raisebox": {| + type: "raisebox", + mode: Mode, + loc?: ?SourceLocation, + dy: Measurement, + body: AnyParseNode, + |}, + "rule": {| + type: "rule", + mode: Mode, + loc?: ?SourceLocation, + shift: ?Measurement, + width: Measurement, + height: Measurement, + |}, + "sizing": {| + type: "sizing", + mode: Mode, + loc?: ?SourceLocation, + size: number, + body: AnyParseNode[], + |}, + "smash": {| + type: "smash", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode, + smashHeight: boolean, + smashDepth: boolean, + |}, + "sqrt": {| + type: "sqrt", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode, + index: ?AnyParseNode, + |}, + "underline": {| + type: "underline", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode, + |}, + "vcenter": {| + type: "vcenter", + mode: Mode, + loc?: ?SourceLocation, + body: AnyParseNode, + |}, + "xArrow": {| + type: "xArrow", + mode: Mode, + loc?: ?SourceLocation, + label: string, + body: AnyParseNode, + below: ?AnyParseNode, + |}, +}; + +/** + * Asserts that the node is of the given type and returns it with stricter + * typing. Throws if the node's type does not match. + */ +export function assertNodeType( + node: ?AnyParseNode, + type: NODETYPE, +): ParseNode { + if (!node || node.type !== type) { + throw new Error( + `Expected node of type ${type}, but got ` + + (node ? `node of type ${node.type}` : String(node))); + } + // $FlowFixMe, >=0.125 + return node; +} + +/** + * Returns the node more strictly typed iff it is of the given type. Otherwise, + * returns null. + */ +export function assertSymbolNodeType(node: ?AnyParseNode): SymbolParseNode { + const typedNode = checkSymbolNodeType(node); + if (!typedNode) { + throw new Error( + `Expected node of symbol group type, but got ` + + (node ? `node of type ${node.type}` : String(node))); + } + return typedNode; +} + +/** + * Returns the node more strictly typed iff it is of the given type. Otherwise, + * returns null. + */ +export function checkSymbolNodeType(node: ?AnyParseNode): ?SymbolParseNode { + if (node && (node.type === "atom" || NON_ATOMS.hasOwnProperty(node.type))) { + // $FlowFixMe + return node; + } + return null; +} diff --git a/frontend/node_modules/katex/src/parseTree.js b/frontend/node_modules/katex/src/parseTree.js new file mode 100644 index 0000000..cec4438 --- /dev/null +++ b/frontend/node_modules/katex/src/parseTree.js @@ -0,0 +1,49 @@ +// @flow +/** + * Provides a single function for parsing an expression using a Parser + * TODO(emily): Remove this + */ + +import Parser from "./Parser"; +import ParseError from "./ParseError"; +import {Token} from "./Token"; + +import type Settings from "./Settings"; +import type {AnyParseNode} from "./parseNode"; + +/** + * Parses an expression using a Parser, then returns the parsed result. + */ +const parseTree = function(toParse: string, settings: Settings): AnyParseNode[] { + if (!(typeof toParse === 'string' || toParse instanceof String)) { + throw new TypeError('KaTeX can only parse string typed expression'); + } + const parser = new Parser(toParse, settings); + + // Blank out any \df@tag to avoid spurious "Duplicate \tag" errors + delete parser.gullet.macros.current["\\df@tag"]; + + let tree = parser.parse(); + + // Prevent a color definition from persisting between calls to katex.render(). + delete parser.gullet.macros.current["\\current@color"]; + delete parser.gullet.macros.current["\\color"]; + + // If the input used \tag, it will set the \df@tag macro to the tag. + // In this case, we separately parse the tag and wrap the tree. + if (parser.gullet.macros.get("\\df@tag")) { + if (!settings.displayMode) { + throw new ParseError("\\tag works only in display equations"); + } + tree = [{ + type: "tag", + mode: "text", + body: tree, + tag: parser.subparse([new Token("\\df@tag")]), + }]; + } + + return tree; +}; + +export default parseTree; diff --git a/frontend/node_modules/katex/src/spacingData.js b/frontend/node_modules/katex/src/spacingData.js new file mode 100644 index 0000000..9a04401 --- /dev/null +++ b/frontend/node_modules/katex/src/spacingData.js @@ -0,0 +1,108 @@ +// @flow +/** + * Describes spaces between different classes of atoms. + */ +import type {Measurement} from "./units"; + +const thinspace: Measurement = { + number: 3, + unit: "mu", +}; +const mediumspace: Measurement = { + number: 4, + unit: "mu", +}; +const thickspace: Measurement = { + number: 5, + unit: "mu", +}; + +// Making the type below exact with all optional fields doesn't work due to +// - https://github.com/facebook/flow/issues/4582 +// - https://github.com/facebook/flow/issues/5688 +// However, since *all* fields are optional, $Shape<> works as suggested in 5688 +// above. +export type Spacings = $Shape<{ + mord: Measurement, + mop: Measurement, + mbin: Measurement, + mrel: Measurement, + mopen: Measurement, + mclose: Measurement, + mpunct: Measurement, + minner: Measurement, +}> & {}; + +// Spacing relationships for display and text styles +export const spacings: {[$Keys]: Spacings} = { + mord: { + mop: thinspace, + mbin: mediumspace, + mrel: thickspace, + minner: thinspace, + }, + mop: { + mord: thinspace, + mop: thinspace, + mrel: thickspace, + minner: thinspace, + }, + mbin: { + mord: mediumspace, + mop: mediumspace, + mopen: mediumspace, + minner: mediumspace, + }, + mrel: { + mord: thickspace, + mop: thickspace, + mopen: thickspace, + minner: thickspace, + }, + mopen: {}, + mclose: { + mop: thinspace, + mbin: mediumspace, + mrel: thickspace, + minner: thinspace, + }, + mpunct: { + mord: thinspace, + mop: thinspace, + mrel: thickspace, + mopen: thinspace, + mclose: thinspace, + mpunct: thinspace, + minner: thinspace, + }, + minner: { + mord: thinspace, + mop: thinspace, + mbin: mediumspace, + mrel: thickspace, + mopen: thinspace, + mpunct: thinspace, + minner: thinspace, + }, +}; + +// Spacing relationships for script and scriptscript styles +export const tightSpacings: {[$Keys]: Spacings} = { + mord: { + mop: thinspace, + }, + mop: { + mord: thinspace, + mop: thinspace, + }, + mbin: {}, + mrel: {}, + mopen: {}, + mclose: { + mop: thinspace, + }, + mpunct: {}, + minner: { + mop: thinspace, + }, +}; diff --git a/frontend/node_modules/katex/src/stretchy.js b/frontend/node_modules/katex/src/stretchy.js new file mode 100644 index 0000000..69d81ab --- /dev/null +++ b/frontend/node_modules/katex/src/stretchy.js @@ -0,0 +1,378 @@ +// @flow +/** + * This file provides support to buildMathML.js and buildHTML.js + * for stretchy wide elements rendered from SVG files + * and other CSS trickery. + */ + +import {LineNode, PathNode, SvgNode} from "./domTree"; +import buildCommon from "./buildCommon"; +import mathMLTree from "./mathMLTree"; +import utils from "./utils"; +import {makeEm} from "./units"; + +import type Options from "./Options"; +import type {ParseNode, AnyParseNode} from "./parseNode"; +import type {DomSpan, HtmlDomNode, SvgSpan} from "./domTree"; + +const stretchyCodePoint: {[string]: string} = { + widehat: "^", + widecheck: "ˇ", + widetilde: "~", + utilde: "~", + overleftarrow: "\u2190", + underleftarrow: "\u2190", + xleftarrow: "\u2190", + overrightarrow: "\u2192", + underrightarrow: "\u2192", + xrightarrow: "\u2192", + underbrace: "\u23df", + overbrace: "\u23de", + overgroup: "\u23e0", + undergroup: "\u23e1", + overleftrightarrow: "\u2194", + underleftrightarrow: "\u2194", + xleftrightarrow: "\u2194", + Overrightarrow: "\u21d2", + xRightarrow: "\u21d2", + overleftharpoon: "\u21bc", + xleftharpoonup: "\u21bc", + overrightharpoon: "\u21c0", + xrightharpoonup: "\u21c0", + xLeftarrow: "\u21d0", + xLeftrightarrow: "\u21d4", + xhookleftarrow: "\u21a9", + xhookrightarrow: "\u21aa", + xmapsto: "\u21a6", + xrightharpoondown: "\u21c1", + xleftharpoondown: "\u21bd", + xrightleftharpoons: "\u21cc", + xleftrightharpoons: "\u21cb", + xtwoheadleftarrow: "\u219e", + xtwoheadrightarrow: "\u21a0", + xlongequal: "=", + xtofrom: "\u21c4", + xrightleftarrows: "\u21c4", + xrightequilibrium: "\u21cc", // Not a perfect match. + xleftequilibrium: "\u21cb", // None better available. + "\\cdrightarrow": "\u2192", + "\\cdleftarrow": "\u2190", + "\\cdlongequal": "=", +}; + +const mathMLnode = function(label: string): mathMLTree.MathNode { + const node = new mathMLTree.MathNode( + "mo", + [new mathMLTree.TextNode(stretchyCodePoint[label.replace(/^\\/, '')])], + ); + node.setAttribute("stretchy", "true"); + return node; +}; + +// Many of the KaTeX SVG images have been adapted from glyphs in KaTeX fonts. +// Copyright (c) 2009-2010, Design Science, Inc. () +// Copyright (c) 2014-2017 Khan Academy () +// Licensed under the SIL Open Font License, Version 1.1. +// See \nhttp://scripts.sil.org/OFL + +// Very Long SVGs +// Many of the KaTeX stretchy wide elements use a long SVG image and an +// overflow: hidden tactic to achieve a stretchy image while avoiding +// distortion of arrowheads or brace corners. + +// The SVG typically contains a very long (400 em) arrow. + +// The SVG is in a container span that has overflow: hidden, so the span +// acts like a window that exposes only part of the SVG. + +// The SVG always has a longer, thinner aspect ratio than the container span. +// After the SVG fills 100% of the height of the container span, +// there is a long arrow shaft left over. That left-over shaft is not shown. +// Instead, it is sliced off because the span's CSS has overflow: hidden. + +// Thus, the reader sees an arrow that matches the subject matter width +// without distortion. + +// Some functions, such as \cancel, need to vary their aspect ratio. These +// functions do not get the overflow SVG treatment. + +// Second Brush Stroke +// Low resolution monitors struggle to display images in fine detail. +// So browsers apply anti-aliasing. A long straight arrow shaft therefore +// will sometimes appear as if it has a blurred edge. + +// To mitigate this, these SVG files contain a second "brush-stroke" on the +// arrow shafts. That is, a second long thin rectangular SVG path has been +// written directly on top of each arrow shaft. This reinforcement causes +// some of the screen pixels to display as black instead of the anti-aliased +// gray pixel that a single path would generate. So we get arrow shafts +// whose edges appear to be sharper. + +// In the katexImagesData object just below, the dimensions all +// correspond to path geometry inside the relevant SVG. +// For example, \overrightarrow uses the same arrowhead as glyph U+2192 +// from the KaTeX Main font. The scaling factor is 1000. +// That is, inside the font, that arrowhead is 522 units tall, which +// corresponds to 0.522 em inside the document. + +const katexImagesData: { + [string]: ([string[], number, number] | [[string], number, number, string]) +} = { + // path(s), minWidth, height, align + overrightarrow: [["rightarrow"], 0.888, 522, "xMaxYMin"], + overleftarrow: [["leftarrow"], 0.888, 522, "xMinYMin"], + underrightarrow: [["rightarrow"], 0.888, 522, "xMaxYMin"], + underleftarrow: [["leftarrow"], 0.888, 522, "xMinYMin"], + xrightarrow: [["rightarrow"], 1.469, 522, "xMaxYMin"], + "\\cdrightarrow": [["rightarrow"], 3.0, 522, "xMaxYMin"], // CD minwwidth2.5pc + xleftarrow: [["leftarrow"], 1.469, 522, "xMinYMin"], + "\\cdleftarrow": [["leftarrow"], 3.0, 522, "xMinYMin"], + Overrightarrow: [["doublerightarrow"], 0.888, 560, "xMaxYMin"], + xRightarrow: [["doublerightarrow"], 1.526, 560, "xMaxYMin"], + xLeftarrow: [["doubleleftarrow"], 1.526, 560, "xMinYMin"], + overleftharpoon: [["leftharpoon"], 0.888, 522, "xMinYMin"], + xleftharpoonup: [["leftharpoon"], 0.888, 522, "xMinYMin"], + xleftharpoondown: [["leftharpoondown"], 0.888, 522, "xMinYMin"], + overrightharpoon: [["rightharpoon"], 0.888, 522, "xMaxYMin"], + xrightharpoonup: [["rightharpoon"], 0.888, 522, "xMaxYMin"], + xrightharpoondown: [["rightharpoondown"], 0.888, 522, "xMaxYMin"], + xlongequal: [["longequal"], 0.888, 334, "xMinYMin"], + "\\cdlongequal": [["longequal"], 3.0, 334, "xMinYMin"], + xtwoheadleftarrow: [["twoheadleftarrow"], 0.888, 334, "xMinYMin"], + xtwoheadrightarrow: [["twoheadrightarrow"], 0.888, 334, "xMaxYMin"], + + overleftrightarrow: [["leftarrow", "rightarrow"], 0.888, 522], + overbrace: [["leftbrace", "midbrace", "rightbrace"], 1.6, 548], + underbrace: [["leftbraceunder", "midbraceunder", "rightbraceunder"], + 1.6, 548], + underleftrightarrow: [["leftarrow", "rightarrow"], 0.888, 522], + xleftrightarrow: [["leftarrow", "rightarrow"], 1.75, 522], + xLeftrightarrow: [["doubleleftarrow", "doublerightarrow"], 1.75, 560], + xrightleftharpoons: [["leftharpoondownplus", "rightharpoonplus"], 1.75, 716], + xleftrightharpoons: [["leftharpoonplus", "rightharpoondownplus"], + 1.75, 716], + xhookleftarrow: [["leftarrow", "righthook"], 1.08, 522], + xhookrightarrow: [["lefthook", "rightarrow"], 1.08, 522], + overlinesegment: [["leftlinesegment", "rightlinesegment"], 0.888, 522], + underlinesegment: [["leftlinesegment", "rightlinesegment"], 0.888, 522], + overgroup: [["leftgroup", "rightgroup"], 0.888, 342], + undergroup: [["leftgroupunder", "rightgroupunder"], 0.888, 342], + xmapsto: [["leftmapsto", "rightarrow"], 1.5, 522], + xtofrom: [["leftToFrom", "rightToFrom"], 1.75, 528], + + // The next three arrows are from the mhchem package. + // In mhchem.sty, min-length is 2.0em. But these arrows might appear in the + // document as \xrightarrow or \xrightleftharpoons. Those have + // min-length = 1.75em, so we set min-length on these next three to match. + xrightleftarrows: [["baraboveleftarrow", "rightarrowabovebar"], 1.75, 901], + xrightequilibrium: [["baraboveshortleftharpoon", + "rightharpoonaboveshortbar"], 1.75, 716], + xleftequilibrium: [["shortbaraboveleftharpoon", + "shortrightharpoonabovebar"], 1.75, 716], +}; + +const groupLength = function(arg: AnyParseNode): number { + if (arg.type === "ordgroup") { + return arg.body.length; + } else { + return 1; + } +}; + +const svgSpan = function( + group: ParseNode<"accent"> | ParseNode<"accentUnder"> | ParseNode<"xArrow"> + | ParseNode<"horizBrace">, + options: Options, +): DomSpan | SvgSpan { + // Create a span with inline SVG for the element. + function buildSvgSpan_(): { + span: DomSpan | SvgSpan, + minWidth: number, + height: number, + } { + let viewBoxWidth = 400000; // default + const label = group.label.slice(1); + if (utils.contains(["widehat", "widecheck", "widetilde", "utilde"], + label)) { + // Each type in the `if` statement corresponds to one of the ParseNode + // types below. This narrowing is required to access `grp.base`. + // $FlowFixMe + const grp: ParseNode<"accent"> | ParseNode<"accentUnder"> = group; + // There are four SVG images available for each function. + // Choose a taller image when there are more characters. + const numChars = groupLength(grp.base); + let viewBoxHeight; + let pathName; + let height; + + if (numChars > 5) { + if (label === "widehat" || label === "widecheck") { + viewBoxHeight = 420; + viewBoxWidth = 2364; + height = 0.42; + pathName = label + "4"; + } else { + viewBoxHeight = 312; + viewBoxWidth = 2340; + height = 0.34; + pathName = "tilde4"; + } + } else { + const imgIndex = [1, 1, 2, 2, 3, 3][numChars]; + if (label === "widehat" || label === "widecheck") { + viewBoxWidth = [0, 1062, 2364, 2364, 2364][imgIndex]; + viewBoxHeight = [0, 239, 300, 360, 420][imgIndex]; + height = [0, 0.24, 0.3, 0.3, 0.36, 0.42][imgIndex]; + pathName = label + imgIndex; + } else { + viewBoxWidth = [0, 600, 1033, 2339, 2340][imgIndex]; + viewBoxHeight = [0, 260, 286, 306, 312][imgIndex]; + height = [0, 0.26, 0.286, 0.3, 0.306, 0.34][imgIndex]; + pathName = "tilde" + imgIndex; + } + } + const path = new PathNode(pathName); + const svgNode = new SvgNode([path], { + "width": "100%", + "height": makeEm(height), + "viewBox": `0 0 ${viewBoxWidth} ${viewBoxHeight}`, + "preserveAspectRatio": "none", + }); + return { + span: buildCommon.makeSvgSpan([], [svgNode], options), + minWidth: 0, + height, + }; + } else { + const spans = []; + + const data = katexImagesData[label]; + const [paths, minWidth, viewBoxHeight] = data; + const height = viewBoxHeight / 1000; + + const numSvgChildren = paths.length; + let widthClasses; + let aligns; + if (numSvgChildren === 1) { + // $FlowFixMe: All these cases must be of the 4-tuple type. + const align1: string = data[3]; + widthClasses = ["hide-tail"]; + aligns = [align1]; + } else if (numSvgChildren === 2) { + widthClasses = ["halfarrow-left", "halfarrow-right"]; + aligns = ["xMinYMin", "xMaxYMin"]; + } else if (numSvgChildren === 3) { + widthClasses = ["brace-left", "brace-center", "brace-right"]; + aligns = ["xMinYMin", "xMidYMin", "xMaxYMin"]; + } else { + throw new Error( + `Correct katexImagesData or update code here to support + ${numSvgChildren} children.`); + } + + for (let i = 0; i < numSvgChildren; i++) { + const path = new PathNode(paths[i]); + + const svgNode = new SvgNode([path], { + "width": "400em", + "height": makeEm(height), + "viewBox": `0 0 ${viewBoxWidth} ${viewBoxHeight}`, + "preserveAspectRatio": aligns[i] + " slice", + }); + + const span = buildCommon.makeSvgSpan( + [widthClasses[i]], [svgNode], options); + if (numSvgChildren === 1) { + return {span, minWidth, height}; + } else { + span.style.height = makeEm(height); + spans.push(span); + } + } + + return { + span: buildCommon.makeSpan(["stretchy"], spans, options), + minWidth, + height, + }; + } + } // buildSvgSpan_() + const {span, minWidth, height} = buildSvgSpan_(); + + // Note that we are returning span.depth = 0. + // Any adjustments relative to the baseline must be done in buildHTML. + span.height = height; + span.style.height = makeEm(height); + if (minWidth > 0) { + span.style.minWidth = makeEm(minWidth); + } + + return span; +}; + +const encloseSpan = function( + inner: HtmlDomNode, + label: string, + topPad: number, + bottomPad: number, + options: Options, +): DomSpan | SvgSpan { + // Return an image span for \cancel, \bcancel, \xcancel, \fbox, or \angl + let img; + const totalHeight = inner.height + inner.depth + topPad + bottomPad; + + if (/fbox|color|angl/.test(label)) { + img = buildCommon.makeSpan(["stretchy", label], [], options); + + if (label === "fbox") { + const color = options.color && options.getColor(); + if (color) { + img.style.borderColor = color; + } + } + + } else { + // \cancel, \bcancel, or \xcancel + // Since \cancel's SVG is inline and it omits the viewBox attribute, + // its stroke-width will not vary with span area. + + const lines = []; + if (/^[bx]cancel$/.test(label)) { + lines.push(new LineNode({ + "x1": "0", + "y1": "0", + "x2": "100%", + "y2": "100%", + "stroke-width": "0.046em", + })); + } + + if (/^x?cancel$/.test(label)) { + lines.push(new LineNode({ + "x1": "0", + "y1": "100%", + "x2": "100%", + "y2": "0", + "stroke-width": "0.046em", + })); + } + + const svgNode = new SvgNode(lines, { + "width": "100%", + "height": makeEm(totalHeight), + }); + + img = buildCommon.makeSvgSpan([], [svgNode], options); + } + + img.height = totalHeight; + img.style.height = makeEm(totalHeight); + + return img; +}; + +export default { + encloseSpan, + mathMLnode, + svgSpan, +}; diff --git a/frontend/node_modules/katex/src/styles/fonts.scss b/frontend/node_modules/katex/src/styles/fonts.scss new file mode 100644 index 0000000..99f5150 --- /dev/null +++ b/frontend/node_modules/katex/src/styles/fonts.scss @@ -0,0 +1,71 @@ +$font-folder: "../../fonts" !default; +$use-woff2: true !default; +$use-woff: true !default; +$use-ttf: true !default; + +@function generate-src($family, $family-suffix) { + $src: null; + @if $use-woff2 { + $src: append($src, url('#{$font-folder}/KaTeX_#{$family}-#{$family-suffix}.woff2') format('woff2'), comma); + } + @if $use-woff { + $src: append($src, url('#{$font-folder}/KaTeX_#{$family}-#{$family-suffix}.woff') format('woff'), comma); + } + @if $use-ttf { + $src: append($src, url('#{$font-folder}/KaTeX_#{$family}-#{$family-suffix}.ttf') format('truetype'), comma); + } + + @return $src; +} + +@function generate-suffix($weight, $style) { + $suffix: null; + + @if $weight == normal and $style == normal { + $suffix: 'Regular'; + } + @if $weight == normal and $style == italic { + $suffix: 'Italic'; + } + @if $weight == bold and $style == normal { + $suffix: 'Bold'; + } + @if $weight == bold and $style == italic { + $suffix: 'BoldItalic'; + } + + @return $suffix; +} + +@mixin font-face($family, $weight, $style) { + $suffix: generate-suffix($weight, $style); + $src: generate-src($family, $suffix); + + @font-face { + font-family: 'KaTeX_#{$family}'; + src: $src; + font-weight: $weight; + font-style: $style; + } +} + +@include font-face('AMS', normal, normal); +@include font-face('Caligraphic', bold, normal); +@include font-face('Caligraphic', normal, normal); +@include font-face('Fraktur', bold, normal); +@include font-face('Fraktur', normal, normal); +@include font-face('Main', bold, normal); +@include font-face('Main', bold, italic); +@include font-face('Main', normal, italic); +@include font-face('Main', normal, normal); +@include font-face('Math', bold, italic); +@include font-face('Math', normal, italic); +@include font-face('SansSerif', bold, normal); +@include font-face('SansSerif', normal, italic); +@include font-face('SansSerif', normal, normal); +@include font-face('Script', normal, normal); +@include font-face('Size1', normal, normal); +@include font-face('Size2', normal, normal); +@include font-face('Size3', normal, normal); +@include font-face('Size4', normal, normal); +@include font-face('Typewriter', normal, normal); diff --git a/frontend/node_modules/katex/src/styles/katex.scss b/frontend/node_modules/katex/src/styles/katex.scss new file mode 100644 index 0000000..6647cb3 --- /dev/null +++ b/frontend/node_modules/katex/src/styles/katex.scss @@ -0,0 +1,664 @@ +/* stylelint-disable font-family-no-missing-generic-family-keyword */ +@import "./fonts.scss"; + +// The mu unit is defined as 1/18 em +$mu: calc(1em / 18); + +// The version is dynamically set from package.json via webpack.common.js +$version: "" !default; + +// CSS margin property for math in display mode +$display-margin: 1em 0 !default; + +.katex { + font: normal 1.21em KaTeX_Main, Times New Roman, serif; + line-height: 1.2; + + // Protect elements inside .katex from inheriting text-indent. + text-indent: 0; + + // Prevent a rendering bug that misplaces \vec in Chrome. + text-rendering: auto; + + * { + // Prevent background resetting on elements in Windows's high-contrast + // mode, while still allowing background/foreground setting on root .katex + -ms-high-contrast-adjust: none !important; + + // Insulate fraction bars and rules from CSS that sets border-color. + border-color: currentColor; + } + + .katex-version::after { + content: $version; + } + + .katex-mathml { + /* Accessibility hack to only show to screen readers + Found at: http://a11yproject.com/posts/how-to-hide-content/ */ + position: absolute; + clip: rect(1px, 1px, 1px, 1px); + padding: 0; + border: 0; + height: 1px; + width: 1px; + overflow: hidden; + } + + .katex-html { + /* \newline is an empty block at top level, between .base elements */ + > .newline { + display: block; + } + } + + .base { + position: relative; + display: inline-block; + white-space: nowrap; + + // Fix width of containers of negative spaces, working around Chrome bug. + width: min-content; + } + + .strut { + display: inline-block; + } + + // Text font weights + .textbf { + font-weight: bold; + } + + // Text font shapes. + .textit { + font-style: italic; + } + + // Text font families. + .textrm { + font-family: KaTeX_Main; + } + + .textsf { + font-family: KaTeX_SansSerif; + } + + .texttt { + font-family: KaTeX_Typewriter; + } + + // Math fonts. + .mathnormal { + font-family: KaTeX_Math; + font-style: italic; + } + + .mathit { + font-family: KaTeX_Main; + font-style: italic; + } + + .mathrm { + font-style: normal; + } + + .mathbf { + font-family: KaTeX_Main; + font-weight: bold; + } + + .boldsymbol { + font-family: KaTeX_Math; + font-weight: bold; + font-style: italic; + } + + .amsrm { + font-family: KaTeX_AMS; + } + + .mathbb, + .textbb { + font-family: KaTeX_AMS; + } + + .mathcal { + font-family: KaTeX_Caligraphic; + } + + .mathfrak, + .textfrak { + font-family: KaTeX_Fraktur; + } + + .mathboldfrak, + .textboldfrak { + font-family: KaTeX_Fraktur; + font-weight: bold; + } + + .mathtt { + font-family: KaTeX_Typewriter; + } + + .mathscr, + .textscr { + font-family: KaTeX_Script; + } + + .mathsf, + .textsf { + font-family: KaTeX_SansSerif; + } + + .mathboldsf, + .textboldsf { + font-family: KaTeX_SansSerif; + font-weight: bold; + } + + .mathsfit, + .mathitsf, + .textitsf { + font-family: KaTeX_SansSerif; + font-style: italic; + } + + .mainrm { + font-family: KaTeX_Main; + font-style: normal; + } + + // This value is also used in fontMetrics.js, if you change it make sure the + // values match. + $ptperem: 10; + $nulldelimiterspace: calc(1.2em / $ptperem); + + $muspace: 0.055556em; // 1mu + $thinspace: 0.16667em; // 3mu + $mediumspace: 0.22222em; // 4mu + $thickspace: 0.27778em; // 5mu + + .vlist-t { + display: inline-table; + table-layout: fixed; + border-collapse: collapse; + } + + .vlist-r { + display: table-row; + } + + .vlist { + display: table-cell; + vertical-align: bottom; + position: relative; + + > span { + display: block; + height: 0; + position: relative; + + > span { + display: inline-block; + } + + > .pstrut { + overflow: hidden; + width: 0; + } + } + } + + .vlist-t2 { + margin-right: -2px; + } + + .vlist-s { + // This cell solves Safari rendering problems. It has text content, so + // its baseline is used for the table. A very small font avoids line-box + // issues; absolute units prevent user font-size overrides from breaking + // rendering. Safari refuses to make the box zero-width, so we give it + // a known width and compensate with negative right margin on the + // inline-table. To prevent the "width: min-content" Chrome workaround + // from shrinking this box, we also set min-width. + display: table-cell; + vertical-align: bottom; + font-size: 1px; + width: 2px; + min-width: 2px; + } + + .vbox { + display: inline-flex; + flex-direction: column; + align-items: baseline; + } + + .hbox { + display: inline-flex; + flex-direction: row; + width: 100%; + } + + .thinbox { + display: inline-flex; + flex-direction: row; + width: 0; + max-width: 0; // necessary for Safari + } + + .msupsub { + text-align: left; + } + + .mfrac { + > span > span { + text-align: center; + } + + .frac-line { + display: inline-block; + width: 100%; + border-bottom-style: solid; + } + } + + // Prevent Chrome from disappearing frac-lines, rules, etc. + .mfrac .frac-line, + .overline .overline-line, + .underline .underline-line, + .hline, + .hdashline, + .rule { + min-height: 1px; + } + + .mspace { + display: inline-block; + } + + .llap, + .rlap, + .clap { + width: 0; + position: relative; + + > .inner { + position: absolute; + } + + > .fix { + display: inline-block; + } + } + + .llap > .inner { + right: 0; + } + + .rlap > .inner, + .clap > .inner { + left: 0; + } + + .clap > .inner > span { + margin-left: -50%; + margin-right: 50%; + } + + .rule { + display: inline-block; + border: solid 0; + position: relative; + } + + .overline .overline-line, + .underline .underline-line, + .hline { + display: inline-block; + width: 100%; + border-bottom-style: solid; + } + + .hdashline { + display: inline-block; + width: 100%; + border-bottom-style: dashed; + } + + .sqrt { + > .root { + /* These values are taken from the definition of `\r@@t`, + `\mkern 5mu` and `\mkern -10mu`. */ + margin-left: calc(5*$mu); + margin-right: calc(-10*$mu); + } + } + + .sizing, + .fontsize-ensurer { + $sizes: 0.5, 0.6, 0.7, 0.8, 0.9, 1, 1.2, 1.44, 1.728, 2.074, 2.488; + + @for $from from 1 through length($sizes) { + @for $to from 1 through length($sizes) { + &.reset-size#{$from}.size#{$to} { + /* stylelint-disable-next-line */ + font-size: calc((nth($sizes, $to) / nth($sizes, $from)) * 1em); + } + } + } + } + + .delimsizing { + &.size1 { font-family: KaTeX_Size1; } + &.size2 { font-family: KaTeX_Size2; } + &.size3 { font-family: KaTeX_Size3; } + &.size4 { font-family: KaTeX_Size4; } + + &.mult { + .delim-size1 > span { + font-family: KaTeX_Size1; + } + + .delim-size4 > span { + font-family: KaTeX_Size4; + } + } + } + + .nulldelimiter { + display: inline-block; + width: $nulldelimiterspace; + } + + .delimcenter { + position: relative; + } + + .op-symbol { + position: relative; + + &.small-op { + font-family: KaTeX_Size1; + } + + &.large-op { + font-family: KaTeX_Size2; + } + } + + .op-limits { + > .vlist-t { + text-align: center; + } + } + + .accent { + > .vlist-t { + text-align: center; + } + + .accent-body { + position: relative; // so that 'left' can shift the accent + } + + // Accents that are not of the accent-full class have zero width + // (do not contribute to the width of the final symbol). + .accent-body:not(.accent-full) { + width: 0; + } + } + + .overlay { + display: block; + } + + .mtable { + .vertical-separator { + display: inline-block; + // margin and border-right are set in JavaScript + min-width: 1px; // Prevent Chrome from omitting a line. + } + + .arraycolsep { + display: inline-block; + } + + .col-align-c > .vlist-t { + text-align: center; + } + + .col-align-l > .vlist-t { + text-align: left; + } + + .col-align-r > .vlist-t { + text-align: right; + } + } + + .svg-align { + text-align: left; + } + + svg { + display: block; + position: absolute; // absolute relative to parent + width: 100%; + height: inherit; + + // We want to inherit colors from our environment + fill: currentColor; + stroke: currentColor; + + // But path elements should not have an outline by default + // that would make them bigger than we expect. + path { + stroke: none; + } + + // And we don't want to inherit any other style properties + // that could affect SVG rendering without affecting font + // rendering. So we reset these properties to their default + // values for every element. + // See https://www.w3.org/TR/SVG/painting.html + fill-rule: nonzero; + fill-opacity: 1; + stroke-width: 1; + stroke-linecap: butt; + stroke-linejoin: miter; + stroke-miterlimit: 4; + stroke-dasharray: none; + stroke-dashoffset: 0; + stroke-opacity: 1; + } + + img { + border-style: none; + min-width: 0; + min-height: 0; + max-width: none; + max-height: none; + } + + // Define CSS for image whose width will match its span width. + .stretchy { + width: 100%; + display: block; + position: relative; + overflow: hidden; + + &::before, + &::after { + content: ""; + } + } + + // Hide the long tail of a stretchy SVG. + .hide-tail { + width: 100%; // necessary only to get IE to work properly + position: relative; // ditto + overflow: hidden; // This line applies to all browsers. + } + + .halfarrow-left { + position: absolute; + left: 0; + width: 50.2%; + overflow: hidden; + } + + .halfarrow-right { + position: absolute; + right: 0; + width: 50.2%; + overflow: hidden; + } + + .brace-left { + position: absolute; + left: 0; + width: 25.1%; + overflow: hidden; + } + + .brace-center { + position: absolute; + left: 25%; + width: 50%; + overflow: hidden; + } + + .brace-right { + position: absolute; + right: 0; + width: 25.1%; + overflow: hidden; + } + + // Lengthen the extensible arrows via padding. + .x-arrow-pad { + padding: 0 0.5em; + } + + .cd-arrow-pad { + padding: 0 0.55556em 0 0.27778em; // \;{#1}\;\; + } + + .x-arrow, + .mover, + .munder { + text-align: center; + } + + .boxpad { + padding: 0 0.3em; // \fboxsep = 3pt + } + + .fbox, + .fcolorbox { + box-sizing: border-box; + border: 0.04em solid; // \fboxrule = 0.4pt + } + + .cancel-pad { + padding: 0 0.2em; // ref: cancel package \advance\dimen@ 2\p@ % "+2" + } + + .cancel-lap { + margin-left: -0.2em; // \cancel does not affect horizontal spacing. + margin-right: -0.2em; // Apply negative margin to correct for 0.2em padding + } // inside the \cancel group. + + .sout { + border-bottom-style: solid; + border-bottom-width: 0.08em; + } + + .angl { + // from package actuarialangle, which is always used in a subscript. + box-sizing: border-box; + border-top: 0.049em solid; // defaultRuleThickness in scriptstyle + border-right: 0.049em solid; // ditto + margin-right: 0.03889em; // 1 mu + } + + .anglpad { + padding: 0 0.03889em; // pad 1mu left and right (in scriptstyle) + } + + .eqn-num::before { + counter-increment: katexEqnNo; + content: "(" counter(katexEqnNo) ")"; + } + + .mml-eqn-num::before { + counter-increment: mmlEqnNo; + content: "(" counter(mmlEqnNo) ")"; + } + + .mtr-glue { + width: 50%; + } + + .cd-vert-arrow { + display: inline-block; + position: relative; + } + + .cd-label-left { + display: inline-block; + position: absolute; + right: calc(50% + 0.3em); + text-align: left; + } + + .cd-label-right { + display: inline-block; + position: absolute; + left: calc(50% + 0.3em); + text-align: right; + } +} + +.katex-display { + display: block; + margin: $display-margin; + text-align: center; + + > .katex { + display: block; + text-align: center; + white-space: nowrap; + + > .katex-html { + display: block; + position: relative; + + > .tag { + position: absolute; + right: 0; + } + } + } +} + +// Left-justified tags (default is right-justified) +.katex-display.leqno > .katex > .katex-html > .tag { + left: 0; + right: auto; +} + +// Flush-left display math +.katex-display.fleqn > .katex { + text-align: left; + padding-left: 2em; +} + +// Automatic equation numbers for some environments. +// Use parallel counters for HTML and MathML. +body { + counter-reset: katexEqnNo mmlEqnNo; +} diff --git a/frontend/node_modules/katex/src/svgGeometry.js b/frontend/node_modules/katex/src/svgGeometry.js new file mode 100644 index 0000000..649e486 --- /dev/null +++ b/frontend/node_modules/katex/src/svgGeometry.js @@ -0,0 +1,545 @@ +// @flow +/** + * This file provides support to domTree.js and delimiter.js. + * It's a storehouse of path geometry for SVG images. + */ + +// In all paths below, the viewBox-to-em scale is 1000:1. + +const hLinePad = 80; // padding above a sqrt vinculum. Prevents image cropping. + +// The vinculum of a \sqrt can be made thicker by a KaTeX rendering option. +// Think of variable extraVinculum as two detours in the SVG path. +// The detour begins at the lower left of the area labeled extraVinculum below. +// The detour proceeds one extraVinculum distance up and slightly to the right, +// displacing the radiused corner between surd and vinculum. The radius is +// traversed as usual, then the detour resumes. It goes right, to the end of +// the very long vinculum, then down one extraVinculum distance, +// after which it resumes regular path geometry for the radical. +/* vinculum + / + /▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒←extraVinculum + / █████████████████████←0.04em (40 unit) std vinculum thickness + / / + / / + / /\ + / / surd +*/ + +const sqrtMain = function(extraVinculum: number, hLinePad: number): string { + // sqrtMain path geometry is from glyph U221A in the font KaTeX Main + return `M95,${622 + extraVinculum + hLinePad} +c-2.7,0,-7.17,-2.7,-13.5,-8c-5.8,-5.3,-9.5,-10,-9.5,-14 +c0,-2,0.3,-3.3,1,-4c1.3,-2.7,23.83,-20.7,67.5,-54 +c44.2,-33.3,65.8,-50.3,66.5,-51c1.3,-1.3,3,-2,5,-2c4.7,0,8.7,3.3,12,10 +s173,378,173,378c0.7,0,35.3,-71,104,-213c68.7,-142,137.5,-285,206.5,-429 +c69,-144,104.5,-217.7,106.5,-221 +l${extraVinculum / 2.075} -${extraVinculum} +c5.3,-9.3,12,-14,20,-14 +H400000v${40 + extraVinculum}H845.2724 +s-225.272,467,-225.272,467s-235,486,-235,486c-2.7,4.7,-9,7,-19,7 +c-6,0,-10,-1,-12,-3s-194,-422,-194,-422s-65,47,-65,47z +M${834 + extraVinculum} ${hLinePad}h400000v${40 + extraVinculum}h-400000z`; +}; + +const sqrtSize1 = function(extraVinculum: number, hLinePad: number): string { + // size1 is from glyph U221A in the font KaTeX_Size1-Regular + return `M263,${601 + extraVinculum + hLinePad}c0.7,0,18,39.7,52,119 +c34,79.3,68.167,158.7,102.5,238c34.3,79.3,51.8,119.3,52.5,120 +c340,-704.7,510.7,-1060.3,512,-1067 +l${extraVinculum / 2.084} -${extraVinculum} +c4.7,-7.3,11,-11,19,-11 +H40000v${40 + extraVinculum}H1012.3 +s-271.3,567,-271.3,567c-38.7,80.7,-84,175,-136,283c-52,108,-89.167,185.3,-111.5,232 +c-22.3,46.7,-33.8,70.3,-34.5,71c-4.7,4.7,-12.3,7,-23,7s-12,-1,-12,-1 +s-109,-253,-109,-253c-72.7,-168,-109.3,-252,-110,-252c-10.7,8,-22,16.7,-34,26 +c-22,17.3,-33.3,26,-34,26s-26,-26,-26,-26s76,-59,76,-59s76,-60,76,-60z +M${1001 + extraVinculum} ${hLinePad}h400000v${40 + extraVinculum}h-400000z`; +}; + +const sqrtSize2 = function(extraVinculum: number, hLinePad: number): string { + // size2 is from glyph U221A in the font KaTeX_Size2-Regular + return `M983 ${10 + extraVinculum + hLinePad} +l${extraVinculum / 3.13} -${extraVinculum} +c4,-6.7,10,-10,18,-10 H400000v${40 + extraVinculum} +H1013.1s-83.4,268,-264.1,840c-180.7,572,-277,876.3,-289,913c-4.7,4.7,-12.7,7,-24,7 +s-12,0,-12,0c-1.3,-3.3,-3.7,-11.7,-7,-25c-35.3,-125.3,-106.7,-373.3,-214,-744 +c-10,12,-21,25,-33,39s-32,39,-32,39c-6,-5.3,-15,-14,-27,-26s25,-30,25,-30 +c26.7,-32.7,52,-63,76,-91s52,-60,52,-60s208,722,208,722 +c56,-175.3,126.3,-397.3,211,-666c84.7,-268.7,153.8,-488.2,207.5,-658.5 +c53.7,-170.3,84.5,-266.8,92.5,-289.5z +M${1001 + extraVinculum} ${hLinePad}h400000v${40 + extraVinculum}h-400000z`; +}; + +const sqrtSize3 = function(extraVinculum: number, hLinePad: number): string { + // size3 is from glyph U221A in the font KaTeX_Size3-Regular + return `M424,${2398 + extraVinculum + hLinePad} +c-1.3,-0.7,-38.5,-172,-111.5,-514c-73,-342,-109.8,-513.3,-110.5,-514 +c0,-2,-10.7,14.3,-32,49c-4.7,7.3,-9.8,15.7,-15.5,25c-5.7,9.3,-9.8,16,-12.5,20 +s-5,7,-5,7c-4,-3.3,-8.3,-7.7,-13,-13s-13,-13,-13,-13s76,-122,76,-122s77,-121,77,-121 +s209,968,209,968c0,-2,84.7,-361.7,254,-1079c169.3,-717.3,254.7,-1077.7,256,-1081 +l${extraVinculum / 4.223} -${extraVinculum}c4,-6.7,10,-10,18,-10 H400000 +v${40 + extraVinculum}H1014.6 +s-87.3,378.7,-272.6,1166c-185.3,787.3,-279.3,1182.3,-282,1185 +c-2,6,-10,9,-24,9 +c-8,0,-12,-0.7,-12,-2z M${1001 + extraVinculum} ${hLinePad} +h400000v${40 + extraVinculum}h-400000z`; +}; + +const sqrtSize4 = function(extraVinculum: number, hLinePad: number): string { + // size4 is from glyph U221A in the font KaTeX_Size4-Regular + return `M473,${2713 + extraVinculum + hLinePad} +c339.3,-1799.3,509.3,-2700,510,-2702 l${extraVinculum / 5.298} -${extraVinculum} +c3.3,-7.3,9.3,-11,18,-11 H400000v${40 + extraVinculum}H1017.7 +s-90.5,478,-276.2,1466c-185.7,988,-279.5,1483,-281.5,1485c-2,6,-10,9,-24,9 +c-8,0,-12,-0.7,-12,-2c0,-1.3,-5.3,-32,-16,-92c-50.7,-293.3,-119.7,-693.3,-207,-1200 +c0,-1.3,-5.3,8.7,-16,30c-10.7,21.3,-21.3,42.7,-32,64s-16,33,-16,33s-26,-26,-26,-26 +s76,-153,76,-153s77,-151,77,-151c0.7,0.7,35.7,202,105,604c67.3,400.7,102,602.7,104, +606zM${1001 + extraVinculum} ${hLinePad}h400000v${40 + extraVinculum}H1017.7z`; +}; + +export const phasePath = function(y: number): string { + const x = y / 2; // x coordinate at top of angle + return `M400000 ${y} H0 L${x} 0 l65 45 L145 ${y - 80} H400000z`; +}; + +const sqrtTall = function( + extraVinculum: number, + hLinePad: number, + viewBoxHeight: number +): string { + // sqrtTall is from glyph U23B7 in the font KaTeX_Size4-Regular + // One path edge has a variable length. It runs vertically from the vinculum + // to a point near (14 units) the bottom of the surd. The vinculum + // is normally 40 units thick. So the length of the line in question is: + const vertSegment = viewBoxHeight - 54 - hLinePad - extraVinculum; + + return `M702 ${extraVinculum + hLinePad}H400000${40 + extraVinculum} +H742v${vertSegment}l-4 4-4 4c-.667.7 -2 1.5-4 2.5s-4.167 1.833-6.5 2.5-5.5 1-9.5 1 +h-12l-28-84c-16.667-52-96.667 -294.333-240-727l-212 -643 -85 170 +c-4-3.333-8.333-7.667-13 -13l-13-13l77-155 77-156c66 199.333 139 419.667 +219 661 l218 661zM702 ${hLinePad}H400000v${40 + extraVinculum}H742z`; +}; + +export const sqrtPath = function( + size: string, + extraVinculum: number, + viewBoxHeight: number +): string { + extraVinculum = 1000 * extraVinculum; // Convert from document ems to viewBox. + let path = ""; + + switch (size) { + case "sqrtMain": + path = sqrtMain(extraVinculum, hLinePad); + break; + case "sqrtSize1": + path = sqrtSize1(extraVinculum, hLinePad); + break; + case "sqrtSize2": + path = sqrtSize2(extraVinculum, hLinePad); + break; + case "sqrtSize3": + path = sqrtSize3(extraVinculum, hLinePad); + break; + case "sqrtSize4": + path = sqrtSize4(extraVinculum, hLinePad); + break; + case "sqrtTall": + path = sqrtTall(extraVinculum, hLinePad, viewBoxHeight); + } + return path; +}; + +export const innerPath = function(name: string, height: number): string { + // The inner part of stretchy tall delimiters + switch (name) { + case "\u239c": + return `M291 0 H417 V${height} H291z M291 0 H417 V${height} H291z`; + case "\u2223": + return `M145 0 H188 V${height} H145z M145 0 H188 V${height} H145z`; + case "\u2225": + return `M145 0 H188 V${height} H145z M145 0 H188 V${height} H145z` + + `M367 0 H410 V${height} H367z M367 0 H410 V${height} H367z`; + case "\u239f": + return `M457 0 H583 V${height} H457z M457 0 H583 V${height} H457z`; + case "\u23a2": + return `M319 0 H403 V${height} H319z M319 0 H403 V${height} H319z`; + case "\u23a5": + return `M263 0 H347 V${height} H263z M263 0 H347 V${height} H263z`; + case "\u23aa": + return `M384 0 H504 V${height} H384z M384 0 H504 V${height} H384z`; + case "\u23d0": + return `M312 0 H355 V${height} H312z M312 0 H355 V${height} H312z`; + case "\u2016": + return `M257 0 H300 V${height} H257z M257 0 H300 V${height} H257z` + + `M478 0 H521 V${height} H478z M478 0 H521 V${height} H478z`; + default: + return ""; + } +}; + +export const path: {[string]: string} = { + // The doubleleftarrow geometry is from glyph U+21D0 in the font KaTeX Main + doubleleftarrow: `M262 157 +l10-10c34-36 62.7-77 86-123 3.3-8 5-13.3 5-16 0-5.3-6.7-8-20-8-7.3 + 0-12.2.5-14.5 1.5-2.3 1-4.8 4.5-7.5 10.5-49.3 97.3-121.7 169.3-217 216-28 + 14-57.3 25-88 33-6.7 2-11 3.8-13 5.5-2 1.7-3 4.2-3 7.5s1 5.8 3 7.5 +c2 1.7 6.3 3.5 13 5.5 68 17.3 128.2 47.8 180.5 91.5 52.3 43.7 93.8 96.2 124.5 + 157.5 9.3 8 15.3 12.3 18 13h6c12-.7 18-4 18-10 0-2-1.7-7-5-15-23.3-46-52-87 +-86-123l-10-10h399738v-40H218c328 0 0 0 0 0l-10-8c-26.7-20-65.7-43-117-69 2.7 +-2 6-3.7 10-5 36.7-16 72.3-37.3 107-64l10-8h399782v-40z +m8 0v40h399730v-40zm0 194v40h399730v-40z`, + + // doublerightarrow is from glyph U+21D2 in font KaTeX Main + doublerightarrow: `M399738 392l +-10 10c-34 36-62.7 77-86 123-3.3 8-5 13.3-5 16 0 5.3 6.7 8 20 8 7.3 0 12.2-.5 + 14.5-1.5 2.3-1 4.8-4.5 7.5-10.5 49.3-97.3 121.7-169.3 217-216 28-14 57.3-25 88 +-33 6.7-2 11-3.8 13-5.5 2-1.7 3-4.2 3-7.5s-1-5.8-3-7.5c-2-1.7-6.3-3.5-13-5.5-68 +-17.3-128.2-47.8-180.5-91.5-52.3-43.7-93.8-96.2-124.5-157.5-9.3-8-15.3-12.3-18 +-13h-6c-12 .7-18 4-18 10 0 2 1.7 7 5 15 23.3 46 52 87 86 123l10 10H0v40h399782 +c-328 0 0 0 0 0l10 8c26.7 20 65.7 43 117 69-2.7 2-6 3.7-10 5-36.7 16-72.3 37.3 +-107 64l-10 8H0v40zM0 157v40h399730v-40zm0 194v40h399730v-40z`, + + // leftarrow is from glyph U+2190 in font KaTeX Main + leftarrow: `M400000 241H110l3-3c68.7-52.7 113.7-120 + 135-202 4-14.7 6-23 6-25 0-7.3-7-11-21-11-8 0-13.2.8-15.5 2.5-2.3 1.7-4.2 5.8 +-5.5 12.5-1.3 4.7-2.7 10.3-4 17-12 48.7-34.8 92-68.5 130S65.3 228.3 18 247 +c-10 4-16 7.7-18 11 0 8.7 6 14.3 18 17 47.3 18.7 87.8 47 121.5 85S196 441.3 208 + 490c.7 2 1.3 5 2 9s1.2 6.7 1.5 8c.3 1.3 1 3.3 2 6s2.2 4.5 3.5 5.5c1.3 1 3.3 + 1.8 6 2.5s6 1 10 1c14 0 21-3.7 21-11 0-2-2-10.3-6-25-20-79.3-65-146.7-135-202 + l-3-3h399890zM100 241v40h399900v-40z`, + + // overbrace is from glyphs U+23A9/23A8/23A7 in font KaTeX_Size4-Regular + leftbrace: `M6 548l-6-6v-35l6-11c56-104 135.3-181.3 238-232 57.3-28.7 117 +-45 179-50h399577v120H403c-43.3 7-81 15-113 26-100.7 33-179.7 91-237 174-2.7 + 5-6 9-10 13-.7 1-7.3 1-20 1H6z`, + + leftbraceunder: `M0 6l6-6h17c12.688 0 19.313.3 20 1 4 4 7.313 8.3 10 13 + 35.313 51.3 80.813 93.8 136.5 127.5 55.688 33.7 117.188 55.8 184.5 66.5.688 + 0 2 .3 4 1 18.688 2.7 76 4.3 172 5h399450v120H429l-6-1c-124.688-8-235-61.7 +-331-161C60.687 138.7 32.312 99.3 7 54L0 41V6z`, + + // overgroup is from the MnSymbol package (public domain) + leftgroup: `M400000 80 +H435C64 80 168.3 229.4 21 260c-5.9 1.2-18 0-18 0-2 0-3-1-3-3v-38C76 61 257 0 + 435 0h399565z`, + + leftgroupunder: `M400000 262 +H435C64 262 168.3 112.6 21 82c-5.9-1.2-18 0-18 0-2 0-3 1-3 3v38c76 158 257 219 + 435 219h399565z`, + + // Harpoons are from glyph U+21BD in font KaTeX Main + leftharpoon: `M0 267c.7 5.3 3 10 7 14h399993v-40H93c3.3 +-3.3 10.2-9.5 20.5-18.5s17.8-15.8 22.5-20.5c50.7-52 88-110.3 112-175 4-11.3 5 +-18.3 3-21-1.3-4-7.3-6-18-6-8 0-13 .7-15 2s-4.7 6.7-8 16c-42 98.7-107.3 174.7 +-196 228-6.7 4.7-10.7 8-12 10-1.3 2-2 5.7-2 11zm100-26v40h399900v-40z`, + + leftharpoonplus: `M0 267c.7 5.3 3 10 7 14h399993v-40H93c3.3-3.3 10.2-9.5 + 20.5-18.5s17.8-15.8 22.5-20.5c50.7-52 88-110.3 112-175 4-11.3 5-18.3 3-21-1.3 +-4-7.3-6-18-6-8 0-13 .7-15 2s-4.7 6.7-8 16c-42 98.7-107.3 174.7-196 228-6.7 4.7 +-10.7 8-12 10-1.3 2-2 5.7-2 11zm100-26v40h399900v-40zM0 435v40h400000v-40z +m0 0v40h400000v-40z`, + + leftharpoondown: `M7 241c-4 4-6.333 8.667-7 14 0 5.333.667 9 2 11s5.333 + 5.333 12 10c90.667 54 156 130 196 228 3.333 10.667 6.333 16.333 9 17 2 .667 5 + 1 9 1h5c10.667 0 16.667-2 18-6 2-2.667 1-9.667-3-21-32-87.333-82.667-157.667 +-152-211l-3-3h399907v-40zM93 281 H400000 v-40L7 241z`, + + leftharpoondownplus: `M7 435c-4 4-6.3 8.7-7 14 0 5.3.7 9 2 11s5.3 5.3 12 + 10c90.7 54 156 130 196 228 3.3 10.7 6.3 16.3 9 17 2 .7 5 1 9 1h5c10.7 0 16.7 +-2 18-6 2-2.7 1-9.7-3-21-32-87.3-82.7-157.7-152-211l-3-3h399907v-40H7zm93 0 +v40h399900v-40zM0 241v40h399900v-40zm0 0v40h399900v-40z`, + + // hook is from glyph U+21A9 in font KaTeX Main + lefthook: `M400000 281 H103s-33-11.2-61-33.5S0 197.3 0 164s14.2-61.2 42.5 +-83.5C70.8 58.2 104 47 142 47 c16.7 0 25 6.7 25 20 0 12-8.7 18.7-26 20-40 3.3 +-68.7 15.7-86 37-10 12-15 25.3-15 40 0 22.7 9.8 40.7 29.5 54 19.7 13.3 43.5 21 + 71.5 23h399859zM103 281v-40h399897v40z`, + + leftlinesegment: `M40 281 V428 H0 V94 H40 V241 H400000 v40z +M40 281 V428 H0 V94 H40 V241 H400000 v40z`, + + leftmapsto: `M40 281 V448H0V74H40V241H400000v40z +M40 281 V448H0V74H40V241H400000v40z`, + + // tofrom is from glyph U+21C4 in font KaTeX AMS Regular + leftToFrom: `M0 147h400000v40H0zm0 214c68 40 115.7 95.7 143 167h22c15.3 0 23 +-.3 23-1 0-1.3-5.3-13.7-16-37-18-35.3-41.3-69-70-101l-7-8h399905v-40H95l7-8 +c28.7-32 52-65.7 70-101 10.7-23.3 16-35.7 16-37 0-.7-7.7-1-23-1h-22C115.7 265.3 + 68 321 0 361zm0-174v-40h399900v40zm100 154v40h399900v-40z`, + + longequal: `M0 50 h400000 v40H0z m0 194h40000v40H0z +M0 50 h400000 v40H0z m0 194h40000v40H0z`, + + midbrace: `M200428 334 +c-100.7-8.3-195.3-44-280-108-55.3-42-101.7-93-139-153l-9-14c-2.7 4-5.7 8.7-9 14 +-53.3 86.7-123.7 153-211 199-66.7 36-137.3 56.3-212 62H0V214h199568c178.3-11.7 + 311.7-78.3 403-201 6-8 9.7-12 11-12 .7-.7 6.7-1 18-1s17.3.3 18 1c1.3 0 5 4 11 + 12 44.7 59.3 101.3 106.3 170 141s145.3 54.3 229 60h199572v120z`, + + midbraceunder: `M199572 214 +c100.7 8.3 195.3 44 280 108 55.3 42 101.7 93 139 153l9 14c2.7-4 5.7-8.7 9-14 + 53.3-86.7 123.7-153 211-199 66.7-36 137.3-56.3 212-62h199568v120H200432c-178.3 + 11.7-311.7 78.3-403 201-6 8-9.7 12-11 12-.7.7-6.7 1-18 1s-17.3-.3-18-1c-1.3 0 +-5-4-11-12-44.7-59.3-101.3-106.3-170-141s-145.3-54.3-229-60H0V214z`, + + oiintSize1: `M512.6 71.6c272.6 0 320.3 106.8 320.3 178.2 0 70.8-47.7 177.6 +-320.3 177.6S193.1 320.6 193.1 249.8c0-71.4 46.9-178.2 319.5-178.2z +m368.1 178.2c0-86.4-60.9-215.4-368.1-215.4-306.4 0-367.3 129-367.3 215.4 0 85.8 +60.9 214.8 367.3 214.8 307.2 0 368.1-129 368.1-214.8z`, + + oiintSize2: `M757.8 100.1c384.7 0 451.1 137.6 451.1 230 0 91.3-66.4 228.8 +-451.1 228.8-386.3 0-452.7-137.5-452.7-228.8 0-92.4 66.4-230 452.7-230z +m502.4 230c0-111.2-82.4-277.2-502.4-277.2s-504 166-504 277.2 +c0 110 84 276 504 276s502.4-166 502.4-276z`, + + oiiintSize1: `M681.4 71.6c408.9 0 480.5 106.8 480.5 178.2 0 70.8-71.6 177.6 +-480.5 177.6S202.1 320.6 202.1 249.8c0-71.4 70.5-178.2 479.3-178.2z +m525.8 178.2c0-86.4-86.8-215.4-525.7-215.4-437.9 0-524.7 129-524.7 215.4 0 +85.8 86.8 214.8 524.7 214.8 438.9 0 525.7-129 525.7-214.8z`, + + oiiintSize2: `M1021.2 53c603.6 0 707.8 165.8 707.8 277.2 0 110-104.2 275.8 +-707.8 275.8-606 0-710.2-165.8-710.2-275.8C311 218.8 415.2 53 1021.2 53z +m770.4 277.1c0-131.2-126.4-327.6-770.5-327.6S248.4 198.9 248.4 330.1 +c0 130 128.8 326.4 772.7 326.4s770.5-196.4 770.5-326.4z`, + + rightarrow: `M0 241v40h399891c-47.3 35.3-84 78-110 128 +-16.7 32-27.7 63.7-33 95 0 1.3-.2 2.7-.5 4-.3 1.3-.5 2.3-.5 3 0 7.3 6.7 11 20 + 11 8 0 13.2-.8 15.5-2.5 2.3-1.7 4.2-5.5 5.5-11.5 2-13.3 5.7-27 11-41 14.7-44.7 + 39-84.5 73-119.5s73.7-60.2 119-75.5c6-2 9-5.7 9-11s-3-9-9-11c-45.3-15.3-85 +-40.5-119-75.5s-58.3-74.8-73-119.5c-4.7-14-8.3-27.3-11-40-1.3-6.7-3.2-10.8-5.5 +-12.5-2.3-1.7-7.5-2.5-15.5-2.5-14 0-21 3.7-21 11 0 2 2 10.3 6 25 20.7 83.3 67 + 151.7 139 205zm0 0v40h399900v-40z`, + + rightbrace: `M400000 542l +-6 6h-17c-12.7 0-19.3-.3-20-1-4-4-7.3-8.3-10-13-35.3-51.3-80.8-93.8-136.5-127.5 +s-117.2-55.8-184.5-66.5c-.7 0-2-.3-4-1-18.7-2.7-76-4.3-172-5H0V214h399571l6 1 +c124.7 8 235 61.7 331 161 31.3 33.3 59.7 72.7 85 118l7 13v35z`, + + rightbraceunder: `M399994 0l6 6v35l-6 11c-56 104-135.3 181.3-238 232-57.3 + 28.7-117 45-179 50H-300V214h399897c43.3-7 81-15 113-26 100.7-33 179.7-91 237 +-174 2.7-5 6-9 10-13 .7-1 7.3-1 20-1h17z`, + + rightgroup: `M0 80h399565c371 0 266.7 149.4 414 180 5.9 1.2 18 0 18 0 2 0 + 3-1 3-3v-38c-76-158-257-219-435-219H0z`, + + rightgroupunder: `M0 262h399565c371 0 266.7-149.4 414-180 5.9-1.2 18 0 18 + 0 2 0 3 1 3 3v38c-76 158-257 219-435 219H0z`, + + rightharpoon: `M0 241v40h399993c4.7-4.7 7-9.3 7-14 0-9.3 +-3.7-15.3-11-18-92.7-56.7-159-133.7-199-231-3.3-9.3-6-14.7-8-16-2-1.3-7-2-15-2 +-10.7 0-16.7 2-18 6-2 2.7-1 9.7 3 21 15.3 42 36.7 81.8 64 119.5 27.3 37.7 58 + 69.2 92 94.5zm0 0v40h399900v-40z`, + + rightharpoonplus: `M0 241v40h399993c4.7-4.7 7-9.3 7-14 0-9.3-3.7-15.3-11 +-18-92.7-56.7-159-133.7-199-231-3.3-9.3-6-14.7-8-16-2-1.3-7-2-15-2-10.7 0-16.7 + 2-18 6-2 2.7-1 9.7 3 21 15.3 42 36.7 81.8 64 119.5 27.3 37.7 58 69.2 92 94.5z +m0 0v40h399900v-40z m100 194v40h399900v-40zm0 0v40h399900v-40z`, + + rightharpoondown: `M399747 511c0 7.3 6.7 11 20 11 8 0 13-.8 15-2.5s4.7-6.8 + 8-15.5c40-94 99.3-166.3 178-217 13.3-8 20.3-12.3 21-13 5.3-3.3 8.5-5.8 9.5 +-7.5 1-1.7 1.5-5.2 1.5-10.5s-2.3-10.3-7-15H0v40h399908c-34 25.3-64.7 57-92 95 +-27.3 38-48.7 77.7-64 119-3.3 8.7-5 14-5 16zM0 241v40h399900v-40z`, + + rightharpoondownplus: `M399747 705c0 7.3 6.7 11 20 11 8 0 13-.8 + 15-2.5s4.7-6.8 8-15.5c40-94 99.3-166.3 178-217 13.3-8 20.3-12.3 21-13 5.3-3.3 + 8.5-5.8 9.5-7.5 1-1.7 1.5-5.2 1.5-10.5s-2.3-10.3-7-15H0v40h399908c-34 25.3 +-64.7 57-92 95-27.3 38-48.7 77.7-64 119-3.3 8.7-5 14-5 16zM0 435v40h399900v-40z +m0-194v40h400000v-40zm0 0v40h400000v-40z`, + + righthook: `M399859 241c-764 0 0 0 0 0 40-3.3 68.7-15.7 86-37 10-12 15-25.3 + 15-40 0-22.7-9.8-40.7-29.5-54-19.7-13.3-43.5-21-71.5-23-17.3-1.3-26-8-26-20 0 +-13.3 8.7-20 26-20 38 0 71 11.2 99 33.5 0 0 7 5.6 21 16.7 14 11.2 21 33.5 21 + 66.8s-14 61.2-42 83.5c-28 22.3-61 33.5-99 33.5L0 241z M0 281v-40h399859v40z`, + + rightlinesegment: `M399960 241 V94 h40 V428 h-40 V281 H0 v-40z +M399960 241 V94 h40 V428 h-40 V281 H0 v-40z`, + + rightToFrom: `M400000 167c-70.7-42-118-97.7-142-167h-23c-15.3 0-23 .3-23 + 1 0 1.3 5.3 13.7 16 37 18 35.3 41.3 69 70 101l7 8H0v40h399905l-7 8c-28.7 32 +-52 65.7-70 101-10.7 23.3-16 35.7-16 37 0 .7 7.7 1 23 1h23c24-69.3 71.3-125 142 +-167z M100 147v40h399900v-40zM0 341v40h399900v-40z`, + + // twoheadleftarrow is from glyph U+219E in font KaTeX AMS Regular + twoheadleftarrow: `M0 167c68 40 + 115.7 95.7 143 167h22c15.3 0 23-.3 23-1 0-1.3-5.3-13.7-16-37-18-35.3-41.3-69 +-70-101l-7-8h125l9 7c50.7 39.3 85 86 103 140h46c0-4.7-6.3-18.7-19-42-18-35.3 +-40-67.3-66-96l-9-9h399716v-40H284l9-9c26-28.7 48-60.7 66-96 12.7-23.333 19 +-37.333 19-42h-46c-18 54-52.3 100.7-103 140l-9 7H95l7-8c28.7-32 52-65.7 70-101 + 10.7-23.333 16-35.7 16-37 0-.7-7.7-1-23-1h-22C115.7 71.3 68 127 0 167z`, + + twoheadrightarrow: `M400000 167 +c-68-40-115.7-95.7-143-167h-22c-15.3 0-23 .3-23 1 0 1.3 5.3 13.7 16 37 18 35.3 + 41.3 69 70 101l7 8h-125l-9-7c-50.7-39.3-85-86-103-140h-46c0 4.7 6.3 18.7 19 42 + 18 35.3 40 67.3 66 96l9 9H0v40h399716l-9 9c-26 28.7-48 60.7-66 96-12.7 23.333 +-19 37.333-19 42h46c18-54 52.3-100.7 103-140l9-7h125l-7 8c-28.7 32-52 65.7-70 + 101-10.7 23.333-16 35.7-16 37 0 .7 7.7 1 23 1h22c27.3-71.3 75-127 143-167z`, + + // tilde1 is a modified version of a glyph from the MnSymbol package + tilde1: `M200 55.538c-77 0-168 73.953-177 73.953-3 0-7 +-2.175-9-5.437L2 97c-1-2-2-4-2-6 0-4 2-7 5-9l20-12C116 12 171 0 207 0c86 0 + 114 68 191 68 78 0 168-68 177-68 4 0 7 2 9 5l12 19c1 2.175 2 4.35 2 6.525 0 + 4.35-2 7.613-5 9.788l-19 13.05c-92 63.077-116.937 75.308-183 76.128 +-68.267.847-113-73.952-191-73.952z`, + + // ditto tilde2, tilde3, & tilde4 + tilde2: `M344 55.266c-142 0-300.638 81.316-311.5 86.418 +-8.01 3.762-22.5 10.91-23.5 5.562L1 120c-1-2-1-3-1-4 0-5 3-9 8-10l18.4-9C160.9 + 31.9 283 0 358 0c148 0 188 122 331 122s314-97 326-97c4 0 8 2 10 7l7 21.114 +c1 2.14 1 3.21 1 4.28 0 5.347-3 9.626-7 10.696l-22.3 12.622C852.6 158.372 751 + 181.476 676 181.476c-149 0-189-126.21-332-126.21z`, + + tilde3: `M786 59C457 59 32 175.242 13 175.242c-6 0-10-3.457 +-11-10.37L.15 138c-1-7 3-12 10-13l19.2-6.4C378.4 40.7 634.3 0 804.3 0c337 0 + 411.8 157 746.8 157 328 0 754-112 773-112 5 0 10 3 11 9l1 14.075c1 8.066-.697 + 16.595-6.697 17.492l-21.052 7.31c-367.9 98.146-609.15 122.696-778.15 122.696 + -338 0-409-156.573-744-156.573z`, + + tilde4: `M786 58C457 58 32 177.487 13 177.487c-6 0-10-3.345 +-11-10.035L.15 143c-1-7 3-12 10-13l22-6.7C381.2 35 637.15 0 807.15 0c337 0 409 + 177 744 177 328 0 754-127 773-127 5 0 10 3 11 9l1 14.794c1 7.805-3 13.38-9 + 14.495l-20.7 5.574c-366.85 99.79-607.3 139.372-776.3 139.372-338 0-409 + -175.236-744-175.236z`, + + // vec is from glyph U+20D7 in font KaTeX Main + vec: `M377 20c0-5.333 1.833-10 5.5-14S391 0 397 0c4.667 0 8.667 1.667 12 5 +3.333 2.667 6.667 9 10 19 6.667 24.667 20.333 43.667 41 57 7.333 4.667 11 +10.667 11 18 0 6-1 10-3 12s-6.667 5-14 9c-28.667 14.667-53.667 35.667-75 63 +-1.333 1.333-3.167 3.5-5.5 6.5s-4 4.833-5 5.5c-1 .667-2.5 1.333-4.5 2s-4.333 1 +-7 1c-4.667 0-9.167-1.833-13.5-5.5S337 184 337 178c0-12.667 15.667-32.333 47-59 +H213l-171-1c-8.667-6-13-12.333-13-19 0-4.667 4.333-11.333 13-20h359 +c-16-25.333-24-45-24-59z`, + + // widehat1 is a modified version of a glyph from the MnSymbol package + widehat1: `M529 0h5l519 115c5 1 9 5 9 10 0 1-1 2-1 3l-4 22 +c-1 5-5 9-11 9h-2L532 67 19 159h-2c-5 0-9-4-11-9l-5-22c-1-6 2-12 8-13z`, + + // ditto widehat2, widehat3, & widehat4 + widehat2: `M1181 0h2l1171 176c6 0 10 5 10 11l-2 23c-1 6-5 10 +-11 10h-1L1182 67 15 220h-1c-6 0-10-4-11-10l-2-23c-1-6 4-11 10-11z`, + + widehat3: `M1181 0h2l1171 236c6 0 10 5 10 11l-2 23c-1 6-5 10 +-11 10h-1L1182 67 15 280h-1c-6 0-10-4-11-10l-2-23c-1-6 4-11 10-11z`, + + widehat4: `M1181 0h2l1171 296c6 0 10 5 10 11l-2 23c-1 6-5 10 +-11 10h-1L1182 67 15 340h-1c-6 0-10-4-11-10l-2-23c-1-6 4-11 10-11z`, + + // widecheck paths are all inverted versions of widehat + widecheck1: `M529,159h5l519,-115c5,-1,9,-5,9,-10c0,-1,-1,-2,-1,-3l-4,-22c-1, +-5,-5,-9,-11,-9h-2l-512,92l-513,-92h-2c-5,0,-9,4,-11,9l-5,22c-1,6,2,12,8,13z`, + + widecheck2: `M1181,220h2l1171,-176c6,0,10,-5,10,-11l-2,-23c-1,-6,-5,-10, +-11,-10h-1l-1168,153l-1167,-153h-1c-6,0,-10,4,-11,10l-2,23c-1,6,4,11,10,11z`, + + widecheck3: `M1181,280h2l1171,-236c6,0,10,-5,10,-11l-2,-23c-1,-6,-5,-10, +-11,-10h-1l-1168,213l-1167,-213h-1c-6,0,-10,4,-11,10l-2,23c-1,6,4,11,10,11z`, + + widecheck4: `M1181,340h2l1171,-296c6,0,10,-5,10,-11l-2,-23c-1,-6,-5,-10, +-11,-10h-1l-1168,273l-1167,-273h-1c-6,0,-10,4,-11,10l-2,23c-1,6,4,11,10,11z`, + + // The next ten paths support reaction arrows from the mhchem package. + + // Arrows for \ce{<-->} are offset from xAxis by 0.22ex, per mhchem in LaTeX + // baraboveleftarrow is mostly from glyph U+2190 in font KaTeX Main + baraboveleftarrow: `M400000 620h-399890l3 -3c68.7 -52.7 113.7 -120 135 -202 +c4 -14.7 6 -23 6 -25c0 -7.3 -7 -11 -21 -11c-8 0 -13.2 0.8 -15.5 2.5 +c-2.3 1.7 -4.2 5.8 -5.5 12.5c-1.3 4.7 -2.7 10.3 -4 17c-12 48.7 -34.8 92 -68.5 130 +s-74.2 66.3 -121.5 85c-10 4 -16 7.7 -18 11c0 8.7 6 14.3 18 17c47.3 18.7 87.8 47 +121.5 85s56.5 81.3 68.5 130c0.7 2 1.3 5 2 9s1.2 6.7 1.5 8c0.3 1.3 1 3.3 2 6 +s2.2 4.5 3.5 5.5c1.3 1 3.3 1.8 6 2.5s6 1 10 1c14 0 21 -3.7 21 -11 +c0 -2 -2 -10.3 -6 -25c-20 -79.3 -65 -146.7 -135 -202l-3 -3h399890z +M100 620v40h399900v-40z M0 241v40h399900v-40zM0 241v40h399900v-40z`, + + // rightarrowabovebar is mostly from glyph U+2192, KaTeX Main + rightarrowabovebar: `M0 241v40h399891c-47.3 35.3-84 78-110 128-16.7 32 +-27.7 63.7-33 95 0 1.3-.2 2.7-.5 4-.3 1.3-.5 2.3-.5 3 0 7.3 6.7 11 20 11 8 0 +13.2-.8 15.5-2.5 2.3-1.7 4.2-5.5 5.5-11.5 2-13.3 5.7-27 11-41 14.7-44.7 39 +-84.5 73-119.5s73.7-60.2 119-75.5c6-2 9-5.7 9-11s-3-9-9-11c-45.3-15.3-85-40.5 +-119-75.5s-58.3-74.8-73-119.5c-4.7-14-8.3-27.3-11-40-1.3-6.7-3.2-10.8-5.5 +-12.5-2.3-1.7-7.5-2.5-15.5-2.5-14 0-21 3.7-21 11 0 2 2 10.3 6 25 20.7 83.3 67 +151.7 139 205zm96 379h399894v40H0zm0 0h399904v40H0z`, + + // The short left harpoon has 0.5em (i.e. 500 units) kern on the left end. + // Ref from mhchem.sty: \rlap{\raisebox{-.22ex}{$\kern0.5em + baraboveshortleftharpoon: `M507,435c-4,4,-6.3,8.7,-7,14c0,5.3,0.7,9,2,11 +c1.3,2,5.3,5.3,12,10c90.7,54,156,130,196,228c3.3,10.7,6.3,16.3,9,17 +c2,0.7,5,1,9,1c0,0,5,0,5,0c10.7,0,16.7,-2,18,-6c2,-2.7,1,-9.7,-3,-21 +c-32,-87.3,-82.7,-157.7,-152,-211c0,0,-3,-3,-3,-3l399351,0l0,-40 +c-398570,0,-399437,0,-399437,0z M593 435 v40 H399500 v-40z +M0 281 v-40 H399908 v40z M0 281 v-40 H399908 v40z`, + + rightharpoonaboveshortbar: `M0,241 l0,40c399126,0,399993,0,399993,0 +c4.7,-4.7,7,-9.3,7,-14c0,-9.3,-3.7,-15.3,-11,-18c-92.7,-56.7,-159,-133.7,-199, +-231c-3.3,-9.3,-6,-14.7,-8,-16c-2,-1.3,-7,-2,-15,-2c-10.7,0,-16.7,2,-18,6 +c-2,2.7,-1,9.7,3,21c15.3,42,36.7,81.8,64,119.5c27.3,37.7,58,69.2,92,94.5z +M0 241 v40 H399908 v-40z M0 475 v-40 H399500 v40z M0 475 v-40 H399500 v40z`, + + shortbaraboveleftharpoon: `M7,435c-4,4,-6.3,8.7,-7,14c0,5.3,0.7,9,2,11 +c1.3,2,5.3,5.3,12,10c90.7,54,156,130,196,228c3.3,10.7,6.3,16.3,9,17c2,0.7,5,1,9, +1c0,0,5,0,5,0c10.7,0,16.7,-2,18,-6c2,-2.7,1,-9.7,-3,-21c-32,-87.3,-82.7,-157.7, +-152,-211c0,0,-3,-3,-3,-3l399907,0l0,-40c-399126,0,-399993,0,-399993,0z +M93 435 v40 H400000 v-40z M500 241 v40 H400000 v-40z M500 241 v40 H400000 v-40z`, + + shortrightharpoonabovebar: `M53,241l0,40c398570,0,399437,0,399437,0 +c4.7,-4.7,7,-9.3,7,-14c0,-9.3,-3.7,-15.3,-11,-18c-92.7,-56.7,-159,-133.7,-199, +-231c-3.3,-9.3,-6,-14.7,-8,-16c-2,-1.3,-7,-2,-15,-2c-10.7,0,-16.7,2,-18,6 +c-2,2.7,-1,9.7,3,21c15.3,42,36.7,81.8,64,119.5c27.3,37.7,58,69.2,92,94.5z +M500 241 v40 H399408 v-40z M500 435 v40 H400000 v-40z`, +}; + +export const tallDelim = function(label: string, midHeight: number): string { + switch (label) { + case "lbrack": + return `M403 1759 V84 H666 V0 H319 V1759 v${midHeight} v1759 h347 v-84 +H403z M403 1759 V0 H319 V1759 v${midHeight} v1759 h84z`; + case "rbrack": + return `M347 1759 V0 H0 V84 H263 V1759 v${midHeight} v1759 H0 v84 H347z +M347 1759 V0 H263 V1759 v${midHeight} v1759 h84z`; + case "vert": + return `M145 15 v585 v${midHeight} v585 c2.667,10,9.667,15,21,15 +c10,0,16.667,-5,20,-15 v-585 v${-midHeight} v-585 c-2.667,-10,-9.667,-15,-21,-15 +c-10,0,-16.667,5,-20,15z M188 15 H145 v585 v${midHeight} v585 h43z`; + case "doublevert": + return `M145 15 v585 v${midHeight} v585 c2.667,10,9.667,15,21,15 +c10,0,16.667,-5,20,-15 v-585 v${-midHeight} v-585 c-2.667,-10,-9.667,-15,-21,-15 +c-10,0,-16.667,5,-20,15z M188 15 H145 v585 v${midHeight} v585 h43z +M367 15 v585 v${midHeight} v585 c2.667,10,9.667,15,21,15 +c10,0,16.667,-5,20,-15 v-585 v${-midHeight} v-585 c-2.667,-10,-9.667,-15,-21,-15 +c-10,0,-16.667,5,-20,15z M410 15 H367 v585 v${midHeight} v585 h43z`; + case "lfloor": + return `M319 602 V0 H403 V602 v${midHeight} v1715 h263 v84 H319z +MM319 602 V0 H403 V602 v${midHeight} v1715 H319z`; + case "rfloor": + return `M319 602 V0 H403 V602 v${midHeight} v1799 H0 v-84 H319z +MM319 602 V0 H403 V602 v${midHeight} v1715 H319z`; + case "lceil": + return `M403 1759 V84 H666 V0 H319 V1759 v${midHeight} v602 h84z +M403 1759 V0 H319 V1759 v${midHeight} v602 h84z`; + case "rceil": + return `M347 1759 V0 H0 V84 H263 V1759 v${midHeight} v602 h84z +M347 1759 V0 h-84 V1759 v${midHeight} v602 h84z`; + case "lparen": + return `M863,9c0,-2,-2,-5,-6,-9c0,0,-17,0,-17,0c-12.7,0,-19.3,0.3,-20,1 +c-5.3,5.3,-10.3,11,-15,17c-242.7,294.7,-395.3,682,-458,1162c-21.3,163.3,-33.3,349, +-36,557 l0,${midHeight + 84}c0.2,6,0,26,0,60c2,159.3,10,310.7,24,454c53.3,528,210, +949.7,470,1265c4.7,6,9.7,11.7,15,17c0.7,0.7,7,1,19,1c0,0,18,0,18,0c4,-4,6,-7,6,-9 +c0,-2.7,-3.3,-8.7,-10,-18c-135.3,-192.7,-235.5,-414.3,-300.5,-665c-65,-250.7,-102.5, +-544.7,-112.5,-882c-2,-104,-3,-167,-3,-189 +l0,-${midHeight + 92}c0,-162.7,5.7,-314,17,-454c20.7,-272,63.7,-513,129,-723c65.3, +-210,155.3,-396.3,270,-559c6.7,-9.3,10,-15.3,10,-18z`; + case "rparen": + return `M76,0c-16.7,0,-25,3,-25,9c0,2,2,6.3,6,13c21.3,28.7,42.3,60.3, +63,95c96.7,156.7,172.8,332.5,228.5,527.5c55.7,195,92.8,416.5,111.5,664.5 +c11.3,139.3,17,290.7,17,454c0,28,1.7,43,3.3,45l0,${midHeight + 9} +c-3,4,-3.3,16.7,-3.3,38c0,162,-5.7,313.7,-17,455c-18.7,248,-55.8,469.3,-111.5,664 +c-55.7,194.7,-131.8,370.3,-228.5,527c-20.7,34.7,-41.7,66.3,-63,95c-2,3.3,-4,7,-6,11 +c0,7.3,5.7,11,17,11c0,0,11,0,11,0c9.3,0,14.3,-0.3,15,-1c5.3,-5.3,10.3,-11,15,-17 +c242.7,-294.7,395.3,-681.7,458,-1161c21.3,-164.7,33.3,-350.7,36,-558 +l0,-${midHeight + 144}c-2,-159.3,-10,-310.7,-24,-454c-53.3,-528,-210,-949.7, +-470,-1265c-4.7,-6,-9.7,-11.7,-15,-17c-0.7,-0.7,-6.7,-1,-18,-1z`; + default: + // We should not ever get here. + throw new Error("Unknown stretchy delimiter."); + } +}; diff --git a/frontend/node_modules/katex/src/symbols.js b/frontend/node_modules/katex/src/symbols.js new file mode 100644 index 0000000..43bbc23 --- /dev/null +++ b/frontend/node_modules/katex/src/symbols.js @@ -0,0 +1,890 @@ +// @flow +/** + * This file holds a list of all no-argument functions and single-character + * symbols (like 'a' or ';'). + * + * For each of the symbols, there are three properties they can have: + * - font (required): the font to be used for this symbol. Either "main" (the + normal font), or "ams" (the ams fonts). + * - group (required): the ParseNode group type the symbol should have (i.e. + "textord", "mathord", etc). + See https://github.com/KaTeX/KaTeX/wiki/Examining-TeX#group-types + * - replace: the character that this symbol or function should be + * replaced with (i.e. "\phi" has a replace value of "\u03d5", the phi + * character in the main font). + * + * The outermost map in the table indicates what mode the symbols should be + * accepted in (e.g. "math" or "text"). + */ + +import type {Mode} from "./types"; + +type Font = "main" | "ams"; +// Some of these have a "-token" suffix since these are also used as `ParseNode` +// types for raw text tokens, and we want to avoid conflicts with higher-level +// `ParseNode` types. These `ParseNode`s are constructed within `Parser` by +// looking up the `symbols` map. +export const ATOMS = { + "bin": 1, + "close": 1, + "inner": 1, + "open": 1, + "punct": 1, + "rel": 1, +}; +export const NON_ATOMS = { + "accent-token": 1, + "mathord": 1, + "op-token": 1, + "spacing": 1, + "textord": 1, +}; + +export type Atom = $Keys; +export type NonAtom = $Keys +export type Group = Atom | NonAtom; +type CharInfoMap = {[string]: {font: Font, group: Group, replace: ?string}}; + +const symbols: {[Mode]: CharInfoMap} = { + "math": {}, + "text": {}, +}; +export default symbols; + +/** `acceptUnicodeChar = true` is only applicable if `replace` is set. */ +export function defineSymbol( + mode: Mode, + font: Font, + group: Group, + replace: ?string, + name: string, + acceptUnicodeChar?: boolean, +) { + symbols[mode][name] = {font, group, replace}; + + if (acceptUnicodeChar && replace) { + symbols[mode][replace] = symbols[mode][name]; + } +} + +// Some abbreviations for commonly used strings. +// This helps minify the code, and also spotting typos using jshint. + +// modes: +const math = "math"; +const text = "text"; + +// fonts: +const main = "main"; +const ams = "ams"; + +// groups: +const accent = "accent-token"; +const bin = "bin"; +const close = "close"; +const inner = "inner"; +const mathord = "mathord"; +const op = "op-token"; +const open = "open"; +const punct = "punct"; +const rel = "rel"; +const spacing = "spacing"; +const textord = "textord"; + +// Now comes the symbol table + +// Relation Symbols +defineSymbol(math, main, rel, "\u2261", "\\equiv", true); +defineSymbol(math, main, rel, "\u227a", "\\prec", true); +defineSymbol(math, main, rel, "\u227b", "\\succ", true); +defineSymbol(math, main, rel, "\u223c", "\\sim", true); +defineSymbol(math, main, rel, "\u22a5", "\\perp"); +defineSymbol(math, main, rel, "\u2aaf", "\\preceq", true); +defineSymbol(math, main, rel, "\u2ab0", "\\succeq", true); +defineSymbol(math, main, rel, "\u2243", "\\simeq", true); +defineSymbol(math, main, rel, "\u2223", "\\mid", true); +defineSymbol(math, main, rel, "\u226a", "\\ll", true); +defineSymbol(math, main, rel, "\u226b", "\\gg", true); +defineSymbol(math, main, rel, "\u224d", "\\asymp", true); +defineSymbol(math, main, rel, "\u2225", "\\parallel"); +defineSymbol(math, main, rel, "\u22c8", "\\bowtie", true); +defineSymbol(math, main, rel, "\u2323", "\\smile", true); +defineSymbol(math, main, rel, "\u2291", "\\sqsubseteq", true); +defineSymbol(math, main, rel, "\u2292", "\\sqsupseteq", true); +defineSymbol(math, main, rel, "\u2250", "\\doteq", true); +defineSymbol(math, main, rel, "\u2322", "\\frown", true); +defineSymbol(math, main, rel, "\u220b", "\\ni", true); +defineSymbol(math, main, rel, "\u221d", "\\propto", true); +defineSymbol(math, main, rel, "\u22a2", "\\vdash", true); +defineSymbol(math, main, rel, "\u22a3", "\\dashv", true); +defineSymbol(math, main, rel, "\u220b", "\\owns"); + +// Punctuation +defineSymbol(math, main, punct, "\u002e", "\\ldotp"); +defineSymbol(math, main, punct, "\u22c5", "\\cdotp"); + +// Misc Symbols +defineSymbol(math, main, textord, "\u0023", "\\#"); +defineSymbol(text, main, textord, "\u0023", "\\#"); +defineSymbol(math, main, textord, "\u0026", "\\&"); +defineSymbol(text, main, textord, "\u0026", "\\&"); +defineSymbol(math, main, textord, "\u2135", "\\aleph", true); +defineSymbol(math, main, textord, "\u2200", "\\forall", true); +defineSymbol(math, main, textord, "\u210f", "\\hbar", true); +defineSymbol(math, main, textord, "\u2203", "\\exists", true); +defineSymbol(math, main, textord, "\u2207", "\\nabla", true); +defineSymbol(math, main, textord, "\u266d", "\\flat", true); +defineSymbol(math, main, textord, "\u2113", "\\ell", true); +defineSymbol(math, main, textord, "\u266e", "\\natural", true); +defineSymbol(math, main, textord, "\u2663", "\\clubsuit", true); +defineSymbol(math, main, textord, "\u2118", "\\wp", true); +defineSymbol(math, main, textord, "\u266f", "\\sharp", true); +defineSymbol(math, main, textord, "\u2662", "\\diamondsuit", true); +defineSymbol(math, main, textord, "\u211c", "\\Re", true); +defineSymbol(math, main, textord, "\u2661", "\\heartsuit", true); +defineSymbol(math, main, textord, "\u2111", "\\Im", true); +defineSymbol(math, main, textord, "\u2660", "\\spadesuit", true); +defineSymbol(math, main, textord, "\u00a7", "\\S", true); +defineSymbol(text, main, textord, "\u00a7", "\\S"); +defineSymbol(math, main, textord, "\u00b6", "\\P", true); +defineSymbol(text, main, textord, "\u00b6", "\\P"); + +// Math and Text +defineSymbol(math, main, textord, "\u2020", "\\dag"); +defineSymbol(text, main, textord, "\u2020", "\\dag"); +defineSymbol(text, main, textord, "\u2020", "\\textdagger"); +defineSymbol(math, main, textord, "\u2021", "\\ddag"); +defineSymbol(text, main, textord, "\u2021", "\\ddag"); +defineSymbol(text, main, textord, "\u2021", "\\textdaggerdbl"); + +// Large Delimiters +defineSymbol(math, main, close, "\u23b1", "\\rmoustache", true); +defineSymbol(math, main, open, "\u23b0", "\\lmoustache", true); +defineSymbol(math, main, close, "\u27ef", "\\rgroup", true); +defineSymbol(math, main, open, "\u27ee", "\\lgroup", true); + +// Binary Operators +defineSymbol(math, main, bin, "\u2213", "\\mp", true); +defineSymbol(math, main, bin, "\u2296", "\\ominus", true); +defineSymbol(math, main, bin, "\u228e", "\\uplus", true); +defineSymbol(math, main, bin, "\u2293", "\\sqcap", true); +defineSymbol(math, main, bin, "\u2217", "\\ast"); +defineSymbol(math, main, bin, "\u2294", "\\sqcup", true); +defineSymbol(math, main, bin, "\u25ef", "\\bigcirc", true); +defineSymbol(math, main, bin, "\u2219", "\\bullet", true); +defineSymbol(math, main, bin, "\u2021", "\\ddagger"); +defineSymbol(math, main, bin, "\u2240", "\\wr", true); +defineSymbol(math, main, bin, "\u2a3f", "\\amalg"); +defineSymbol(math, main, bin, "\u0026", "\\And"); // from amsmath + +// Arrow Symbols +defineSymbol(math, main, rel, "\u27f5", "\\longleftarrow", true); +defineSymbol(math, main, rel, "\u21d0", "\\Leftarrow", true); +defineSymbol(math, main, rel, "\u27f8", "\\Longleftarrow", true); +defineSymbol(math, main, rel, "\u27f6", "\\longrightarrow", true); +defineSymbol(math, main, rel, "\u21d2", "\\Rightarrow", true); +defineSymbol(math, main, rel, "\u27f9", "\\Longrightarrow", true); +defineSymbol(math, main, rel, "\u2194", "\\leftrightarrow", true); +defineSymbol(math, main, rel, "\u27f7", "\\longleftrightarrow", true); +defineSymbol(math, main, rel, "\u21d4", "\\Leftrightarrow", true); +defineSymbol(math, main, rel, "\u27fa", "\\Longleftrightarrow", true); +defineSymbol(math, main, rel, "\u21a6", "\\mapsto", true); +defineSymbol(math, main, rel, "\u27fc", "\\longmapsto", true); +defineSymbol(math, main, rel, "\u2197", "\\nearrow", true); +defineSymbol(math, main, rel, "\u21a9", "\\hookleftarrow", true); +defineSymbol(math, main, rel, "\u21aa", "\\hookrightarrow", true); +defineSymbol(math, main, rel, "\u2198", "\\searrow", true); +defineSymbol(math, main, rel, "\u21bc", "\\leftharpoonup", true); +defineSymbol(math, main, rel, "\u21c0", "\\rightharpoonup", true); +defineSymbol(math, main, rel, "\u2199", "\\swarrow", true); +defineSymbol(math, main, rel, "\u21bd", "\\leftharpoondown", true); +defineSymbol(math, main, rel, "\u21c1", "\\rightharpoondown", true); +defineSymbol(math, main, rel, "\u2196", "\\nwarrow", true); +defineSymbol(math, main, rel, "\u21cc", "\\rightleftharpoons", true); + +// AMS Negated Binary Relations +defineSymbol(math, ams, rel, "\u226e", "\\nless", true); +// Symbol names preceded by "@" each have a corresponding macro. +defineSymbol(math, ams, rel, "\ue010", "\\@nleqslant"); +defineSymbol(math, ams, rel, "\ue011", "\\@nleqq"); +defineSymbol(math, ams, rel, "\u2a87", "\\lneq", true); +defineSymbol(math, ams, rel, "\u2268", "\\lneqq", true); +defineSymbol(math, ams, rel, "\ue00c", "\\@lvertneqq"); +defineSymbol(math, ams, rel, "\u22e6", "\\lnsim", true); +defineSymbol(math, ams, rel, "\u2a89", "\\lnapprox", true); +defineSymbol(math, ams, rel, "\u2280", "\\nprec", true); +// unicode-math maps \u22e0 to \npreccurlyeq. We'll use the AMS synonym. +defineSymbol(math, ams, rel, "\u22e0", "\\npreceq", true); +defineSymbol(math, ams, rel, "\u22e8", "\\precnsim", true); +defineSymbol(math, ams, rel, "\u2ab9", "\\precnapprox", true); +defineSymbol(math, ams, rel, "\u2241", "\\nsim", true); +defineSymbol(math, ams, rel, "\ue006", "\\@nshortmid"); +defineSymbol(math, ams, rel, "\u2224", "\\nmid", true); +defineSymbol(math, ams, rel, "\u22ac", "\\nvdash", true); +defineSymbol(math, ams, rel, "\u22ad", "\\nvDash", true); +defineSymbol(math, ams, rel, "\u22ea", "\\ntriangleleft"); +defineSymbol(math, ams, rel, "\u22ec", "\\ntrianglelefteq", true); +defineSymbol(math, ams, rel, "\u228a", "\\subsetneq", true); +defineSymbol(math, ams, rel, "\ue01a", "\\@varsubsetneq"); +defineSymbol(math, ams, rel, "\u2acb", "\\subsetneqq", true); +defineSymbol(math, ams, rel, "\ue017", "\\@varsubsetneqq"); +defineSymbol(math, ams, rel, "\u226f", "\\ngtr", true); +defineSymbol(math, ams, rel, "\ue00f", "\\@ngeqslant"); +defineSymbol(math, ams, rel, "\ue00e", "\\@ngeqq"); +defineSymbol(math, ams, rel, "\u2a88", "\\gneq", true); +defineSymbol(math, ams, rel, "\u2269", "\\gneqq", true); +defineSymbol(math, ams, rel, "\ue00d", "\\@gvertneqq"); +defineSymbol(math, ams, rel, "\u22e7", "\\gnsim", true); +defineSymbol(math, ams, rel, "\u2a8a", "\\gnapprox", true); +defineSymbol(math, ams, rel, "\u2281", "\\nsucc", true); +// unicode-math maps \u22e1 to \nsucccurlyeq. We'll use the AMS synonym. +defineSymbol(math, ams, rel, "\u22e1", "\\nsucceq", true); +defineSymbol(math, ams, rel, "\u22e9", "\\succnsim", true); +defineSymbol(math, ams, rel, "\u2aba", "\\succnapprox", true); +// unicode-math maps \u2246 to \simneqq. We'll use the AMS synonym. +defineSymbol(math, ams, rel, "\u2246", "\\ncong", true); +defineSymbol(math, ams, rel, "\ue007", "\\@nshortparallel"); +defineSymbol(math, ams, rel, "\u2226", "\\nparallel", true); +defineSymbol(math, ams, rel, "\u22af", "\\nVDash", true); +defineSymbol(math, ams, rel, "\u22eb", "\\ntriangleright"); +defineSymbol(math, ams, rel, "\u22ed", "\\ntrianglerighteq", true); +defineSymbol(math, ams, rel, "\ue018", "\\@nsupseteqq"); +defineSymbol(math, ams, rel, "\u228b", "\\supsetneq", true); +defineSymbol(math, ams, rel, "\ue01b", "\\@varsupsetneq"); +defineSymbol(math, ams, rel, "\u2acc", "\\supsetneqq", true); +defineSymbol(math, ams, rel, "\ue019", "\\@varsupsetneqq"); +defineSymbol(math, ams, rel, "\u22ae", "\\nVdash", true); +defineSymbol(math, ams, rel, "\u2ab5", "\\precneqq", true); +defineSymbol(math, ams, rel, "\u2ab6", "\\succneqq", true); +defineSymbol(math, ams, rel, "\ue016", "\\@nsubseteqq"); +defineSymbol(math, ams, bin, "\u22b4", "\\unlhd"); +defineSymbol(math, ams, bin, "\u22b5", "\\unrhd"); + +// AMS Negated Arrows +defineSymbol(math, ams, rel, "\u219a", "\\nleftarrow", true); +defineSymbol(math, ams, rel, "\u219b", "\\nrightarrow", true); +defineSymbol(math, ams, rel, "\u21cd", "\\nLeftarrow", true); +defineSymbol(math, ams, rel, "\u21cf", "\\nRightarrow", true); +defineSymbol(math, ams, rel, "\u21ae", "\\nleftrightarrow", true); +defineSymbol(math, ams, rel, "\u21ce", "\\nLeftrightarrow", true); + +// AMS Misc +defineSymbol(math, ams, rel, "\u25b3", "\\vartriangle"); +defineSymbol(math, ams, textord, "\u210f", "\\hslash"); +defineSymbol(math, ams, textord, "\u25bd", "\\triangledown"); +defineSymbol(math, ams, textord, "\u25ca", "\\lozenge"); +defineSymbol(math, ams, textord, "\u24c8", "\\circledS"); +defineSymbol(math, ams, textord, "\u00ae", "\\circledR"); +defineSymbol(text, ams, textord, "\u00ae", "\\circledR"); +defineSymbol(math, ams, textord, "\u2221", "\\measuredangle", true); +defineSymbol(math, ams, textord, "\u2204", "\\nexists"); +defineSymbol(math, ams, textord, "\u2127", "\\mho"); +defineSymbol(math, ams, textord, "\u2132", "\\Finv", true); +defineSymbol(math, ams, textord, "\u2141", "\\Game", true); +defineSymbol(math, ams, textord, "\u2035", "\\backprime"); +defineSymbol(math, ams, textord, "\u25b2", "\\blacktriangle"); +defineSymbol(math, ams, textord, "\u25bc", "\\blacktriangledown"); +defineSymbol(math, ams, textord, "\u25a0", "\\blacksquare"); +defineSymbol(math, ams, textord, "\u29eb", "\\blacklozenge"); +defineSymbol(math, ams, textord, "\u2605", "\\bigstar"); +defineSymbol(math, ams, textord, "\u2222", "\\sphericalangle", true); +defineSymbol(math, ams, textord, "\u2201", "\\complement", true); +// unicode-math maps U+F0 to \matheth. We map to AMS function \eth +defineSymbol(math, ams, textord, "\u00f0", "\\eth", true); +defineSymbol(text, main, textord, "\u00f0", "\u00f0"); +defineSymbol(math, ams, textord, "\u2571", "\\diagup"); +defineSymbol(math, ams, textord, "\u2572", "\\diagdown"); +defineSymbol(math, ams, textord, "\u25a1", "\\square"); +defineSymbol(math, ams, textord, "\u25a1", "\\Box"); +defineSymbol(math, ams, textord, "\u25ca", "\\Diamond"); +// unicode-math maps U+A5 to \mathyen. We map to AMS function \yen +defineSymbol(math, ams, textord, "\u00a5", "\\yen", true); +defineSymbol(text, ams, textord, "\u00a5", "\\yen", true); +defineSymbol(math, ams, textord, "\u2713", "\\checkmark", true); +defineSymbol(text, ams, textord, "\u2713", "\\checkmark"); + +// AMS Hebrew +defineSymbol(math, ams, textord, "\u2136", "\\beth", true); +defineSymbol(math, ams, textord, "\u2138", "\\daleth", true); +defineSymbol(math, ams, textord, "\u2137", "\\gimel", true); + +// AMS Greek +defineSymbol(math, ams, textord, "\u03dd", "\\digamma", true); +defineSymbol(math, ams, textord, "\u03f0", "\\varkappa"); + +// AMS Delimiters +defineSymbol(math, ams, open, "\u250c", "\\@ulcorner", true); +defineSymbol(math, ams, close, "\u2510", "\\@urcorner", true); +defineSymbol(math, ams, open, "\u2514", "\\@llcorner", true); +defineSymbol(math, ams, close, "\u2518", "\\@lrcorner", true); + +// AMS Binary Relations +defineSymbol(math, ams, rel, "\u2266", "\\leqq", true); +defineSymbol(math, ams, rel, "\u2a7d", "\\leqslant", true); +defineSymbol(math, ams, rel, "\u2a95", "\\eqslantless", true); +defineSymbol(math, ams, rel, "\u2272", "\\lesssim", true); +defineSymbol(math, ams, rel, "\u2a85", "\\lessapprox", true); +defineSymbol(math, ams, rel, "\u224a", "\\approxeq", true); +defineSymbol(math, ams, bin, "\u22d6", "\\lessdot"); +defineSymbol(math, ams, rel, "\u22d8", "\\lll", true); +defineSymbol(math, ams, rel, "\u2276", "\\lessgtr", true); +defineSymbol(math, ams, rel, "\u22da", "\\lesseqgtr", true); +defineSymbol(math, ams, rel, "\u2a8b", "\\lesseqqgtr", true); +defineSymbol(math, ams, rel, "\u2251", "\\doteqdot"); +defineSymbol(math, ams, rel, "\u2253", "\\risingdotseq", true); +defineSymbol(math, ams, rel, "\u2252", "\\fallingdotseq", true); +defineSymbol(math, ams, rel, "\u223d", "\\backsim", true); +defineSymbol(math, ams, rel, "\u22cd", "\\backsimeq", true); +defineSymbol(math, ams, rel, "\u2ac5", "\\subseteqq", true); +defineSymbol(math, ams, rel, "\u22d0", "\\Subset", true); +defineSymbol(math, ams, rel, "\u228f", "\\sqsubset", true); +defineSymbol(math, ams, rel, "\u227c", "\\preccurlyeq", true); +defineSymbol(math, ams, rel, "\u22de", "\\curlyeqprec", true); +defineSymbol(math, ams, rel, "\u227e", "\\precsim", true); +defineSymbol(math, ams, rel, "\u2ab7", "\\precapprox", true); +defineSymbol(math, ams, rel, "\u22b2", "\\vartriangleleft"); +defineSymbol(math, ams, rel, "\u22b4", "\\trianglelefteq"); +defineSymbol(math, ams, rel, "\u22a8", "\\vDash", true); +defineSymbol(math, ams, rel, "\u22aa", "\\Vvdash", true); +defineSymbol(math, ams, rel, "\u2323", "\\smallsmile"); +defineSymbol(math, ams, rel, "\u2322", "\\smallfrown"); +defineSymbol(math, ams, rel, "\u224f", "\\bumpeq", true); +defineSymbol(math, ams, rel, "\u224e", "\\Bumpeq", true); +defineSymbol(math, ams, rel, "\u2267", "\\geqq", true); +defineSymbol(math, ams, rel, "\u2a7e", "\\geqslant", true); +defineSymbol(math, ams, rel, "\u2a96", "\\eqslantgtr", true); +defineSymbol(math, ams, rel, "\u2273", "\\gtrsim", true); +defineSymbol(math, ams, rel, "\u2a86", "\\gtrapprox", true); +defineSymbol(math, ams, bin, "\u22d7", "\\gtrdot"); +defineSymbol(math, ams, rel, "\u22d9", "\\ggg", true); +defineSymbol(math, ams, rel, "\u2277", "\\gtrless", true); +defineSymbol(math, ams, rel, "\u22db", "\\gtreqless", true); +defineSymbol(math, ams, rel, "\u2a8c", "\\gtreqqless", true); +defineSymbol(math, ams, rel, "\u2256", "\\eqcirc", true); +defineSymbol(math, ams, rel, "\u2257", "\\circeq", true); +defineSymbol(math, ams, rel, "\u225c", "\\triangleq", true); +defineSymbol(math, ams, rel, "\u223c", "\\thicksim"); +defineSymbol(math, ams, rel, "\u2248", "\\thickapprox"); +defineSymbol(math, ams, rel, "\u2ac6", "\\supseteqq", true); +defineSymbol(math, ams, rel, "\u22d1", "\\Supset", true); +defineSymbol(math, ams, rel, "\u2290", "\\sqsupset", true); +defineSymbol(math, ams, rel, "\u227d", "\\succcurlyeq", true); +defineSymbol(math, ams, rel, "\u22df", "\\curlyeqsucc", true); +defineSymbol(math, ams, rel, "\u227f", "\\succsim", true); +defineSymbol(math, ams, rel, "\u2ab8", "\\succapprox", true); +defineSymbol(math, ams, rel, "\u22b3", "\\vartriangleright"); +defineSymbol(math, ams, rel, "\u22b5", "\\trianglerighteq"); +defineSymbol(math, ams, rel, "\u22a9", "\\Vdash", true); +defineSymbol(math, ams, rel, "\u2223", "\\shortmid"); +defineSymbol(math, ams, rel, "\u2225", "\\shortparallel"); +defineSymbol(math, ams, rel, "\u226c", "\\between", true); +defineSymbol(math, ams, rel, "\u22d4", "\\pitchfork", true); +defineSymbol(math, ams, rel, "\u221d", "\\varpropto"); +defineSymbol(math, ams, rel, "\u25c0", "\\blacktriangleleft"); +// unicode-math says that \therefore is a mathord atom. +// We kept the amssymb atom type, which is rel. +defineSymbol(math, ams, rel, "\u2234", "\\therefore", true); +defineSymbol(math, ams, rel, "\u220d", "\\backepsilon"); +defineSymbol(math, ams, rel, "\u25b6", "\\blacktriangleright"); +// unicode-math says that \because is a mathord atom. +// We kept the amssymb atom type, which is rel. +defineSymbol(math, ams, rel, "\u2235", "\\because", true); +defineSymbol(math, ams, rel, "\u22d8", "\\llless"); +defineSymbol(math, ams, rel, "\u22d9", "\\gggtr"); +defineSymbol(math, ams, bin, "\u22b2", "\\lhd"); +defineSymbol(math, ams, bin, "\u22b3", "\\rhd"); +defineSymbol(math, ams, rel, "\u2242", "\\eqsim", true); +defineSymbol(math, main, rel, "\u22c8", "\\Join"); +defineSymbol(math, ams, rel, "\u2251", "\\Doteq", true); + +// AMS Binary Operators +defineSymbol(math, ams, bin, "\u2214", "\\dotplus", true); +defineSymbol(math, ams, bin, "\u2216", "\\smallsetminus"); +defineSymbol(math, ams, bin, "\u22d2", "\\Cap", true); +defineSymbol(math, ams, bin, "\u22d3", "\\Cup", true); +defineSymbol(math, ams, bin, "\u2a5e", "\\doublebarwedge", true); +defineSymbol(math, ams, bin, "\u229f", "\\boxminus", true); +defineSymbol(math, ams, bin, "\u229e", "\\boxplus", true); +defineSymbol(math, ams, bin, "\u22c7", "\\divideontimes", true); +defineSymbol(math, ams, bin, "\u22c9", "\\ltimes", true); +defineSymbol(math, ams, bin, "\u22ca", "\\rtimes", true); +defineSymbol(math, ams, bin, "\u22cb", "\\leftthreetimes", true); +defineSymbol(math, ams, bin, "\u22cc", "\\rightthreetimes", true); +defineSymbol(math, ams, bin, "\u22cf", "\\curlywedge", true); +defineSymbol(math, ams, bin, "\u22ce", "\\curlyvee", true); +defineSymbol(math, ams, bin, "\u229d", "\\circleddash", true); +defineSymbol(math, ams, bin, "\u229b", "\\circledast", true); +defineSymbol(math, ams, bin, "\u22c5", "\\centerdot"); +defineSymbol(math, ams, bin, "\u22ba", "\\intercal", true); +defineSymbol(math, ams, bin, "\u22d2", "\\doublecap"); +defineSymbol(math, ams, bin, "\u22d3", "\\doublecup"); +defineSymbol(math, ams, bin, "\u22a0", "\\boxtimes", true); + +// AMS Arrows +// Note: unicode-math maps \u21e2 to their own function \rightdasharrow. +// We'll map it to AMS function \dashrightarrow. It produces the same atom. +defineSymbol(math, ams, rel, "\u21e2", "\\dashrightarrow", true); +// unicode-math maps \u21e0 to \leftdasharrow. We'll use the AMS synonym. +defineSymbol(math, ams, rel, "\u21e0", "\\dashleftarrow", true); +defineSymbol(math, ams, rel, "\u21c7", "\\leftleftarrows", true); +defineSymbol(math, ams, rel, "\u21c6", "\\leftrightarrows", true); +defineSymbol(math, ams, rel, "\u21da", "\\Lleftarrow", true); +defineSymbol(math, ams, rel, "\u219e", "\\twoheadleftarrow", true); +defineSymbol(math, ams, rel, "\u21a2", "\\leftarrowtail", true); +defineSymbol(math, ams, rel, "\u21ab", "\\looparrowleft", true); +defineSymbol(math, ams, rel, "\u21cb", "\\leftrightharpoons", true); +defineSymbol(math, ams, rel, "\u21b6", "\\curvearrowleft", true); +// unicode-math maps \u21ba to \acwopencirclearrow. We'll use the AMS synonym. +defineSymbol(math, ams, rel, "\u21ba", "\\circlearrowleft", true); +defineSymbol(math, ams, rel, "\u21b0", "\\Lsh", true); +defineSymbol(math, ams, rel, "\u21c8", "\\upuparrows", true); +defineSymbol(math, ams, rel, "\u21bf", "\\upharpoonleft", true); +defineSymbol(math, ams, rel, "\u21c3", "\\downharpoonleft", true); +defineSymbol(math, main, rel, "\u22b6", "\\origof", true); // not in font +defineSymbol(math, main, rel, "\u22b7", "\\imageof", true); // not in font +defineSymbol(math, ams, rel, "\u22b8", "\\multimap", true); +defineSymbol(math, ams, rel, "\u21ad", "\\leftrightsquigarrow", true); +defineSymbol(math, ams, rel, "\u21c9", "\\rightrightarrows", true); +defineSymbol(math, ams, rel, "\u21c4", "\\rightleftarrows", true); +defineSymbol(math, ams, rel, "\u21a0", "\\twoheadrightarrow", true); +defineSymbol(math, ams, rel, "\u21a3", "\\rightarrowtail", true); +defineSymbol(math, ams, rel, "\u21ac", "\\looparrowright", true); +defineSymbol(math, ams, rel, "\u21b7", "\\curvearrowright", true); +// unicode-math maps \u21bb to \cwopencirclearrow. We'll use the AMS synonym. +defineSymbol(math, ams, rel, "\u21bb", "\\circlearrowright", true); +defineSymbol(math, ams, rel, "\u21b1", "\\Rsh", true); +defineSymbol(math, ams, rel, "\u21ca", "\\downdownarrows", true); +defineSymbol(math, ams, rel, "\u21be", "\\upharpoonright", true); +defineSymbol(math, ams, rel, "\u21c2", "\\downharpoonright", true); +defineSymbol(math, ams, rel, "\u21dd", "\\rightsquigarrow", true); +defineSymbol(math, ams, rel, "\u21dd", "\\leadsto"); +defineSymbol(math, ams, rel, "\u21db", "\\Rrightarrow", true); +defineSymbol(math, ams, rel, "\u21be", "\\restriction"); + +defineSymbol(math, main, textord, "\u2018", "`"); +defineSymbol(math, main, textord, "$", "\\$"); +defineSymbol(text, main, textord, "$", "\\$"); +defineSymbol(text, main, textord, "$", "\\textdollar"); +defineSymbol(math, main, textord, "%", "\\%"); +defineSymbol(text, main, textord, "%", "\\%"); +defineSymbol(math, main, textord, "_", "\\_"); +defineSymbol(text, main, textord, "_", "\\_"); +defineSymbol(text, main, textord, "_", "\\textunderscore"); +defineSymbol(math, main, textord, "\u2220", "\\angle", true); +defineSymbol(math, main, textord, "\u221e", "\\infty", true); +defineSymbol(math, main, textord, "\u2032", "\\prime"); +defineSymbol(math, main, textord, "\u25b3", "\\triangle"); +defineSymbol(math, main, textord, "\u0393", "\\Gamma", true); +defineSymbol(math, main, textord, "\u0394", "\\Delta", true); +defineSymbol(math, main, textord, "\u0398", "\\Theta", true); +defineSymbol(math, main, textord, "\u039b", "\\Lambda", true); +defineSymbol(math, main, textord, "\u039e", "\\Xi", true); +defineSymbol(math, main, textord, "\u03a0", "\\Pi", true); +defineSymbol(math, main, textord, "\u03a3", "\\Sigma", true); +defineSymbol(math, main, textord, "\u03a5", "\\Upsilon", true); +defineSymbol(math, main, textord, "\u03a6", "\\Phi", true); +defineSymbol(math, main, textord, "\u03a8", "\\Psi", true); +defineSymbol(math, main, textord, "\u03a9", "\\Omega", true); +defineSymbol(math, main, textord, "A", "\u0391"); +defineSymbol(math, main, textord, "B", "\u0392"); +defineSymbol(math, main, textord, "E", "\u0395"); +defineSymbol(math, main, textord, "Z", "\u0396"); +defineSymbol(math, main, textord, "H", "\u0397"); +defineSymbol(math, main, textord, "I", "\u0399"); +defineSymbol(math, main, textord, "K", "\u039A"); +defineSymbol(math, main, textord, "M", "\u039C"); +defineSymbol(math, main, textord, "N", "\u039D"); +defineSymbol(math, main, textord, "O", "\u039F"); +defineSymbol(math, main, textord, "P", "\u03A1"); +defineSymbol(math, main, textord, "T", "\u03A4"); +defineSymbol(math, main, textord, "X", "\u03A7"); +defineSymbol(math, main, textord, "\u00ac", "\\neg", true); +defineSymbol(math, main, textord, "\u00ac", "\\lnot"); +defineSymbol(math, main, textord, "\u22a4", "\\top"); +defineSymbol(math, main, textord, "\u22a5", "\\bot"); +defineSymbol(math, main, textord, "\u2205", "\\emptyset"); +defineSymbol(math, ams, textord, "\u2205", "\\varnothing"); +defineSymbol(math, main, mathord, "\u03b1", "\\alpha", true); +defineSymbol(math, main, mathord, "\u03b2", "\\beta", true); +defineSymbol(math, main, mathord, "\u03b3", "\\gamma", true); +defineSymbol(math, main, mathord, "\u03b4", "\\delta", true); +defineSymbol(math, main, mathord, "\u03f5", "\\epsilon", true); +defineSymbol(math, main, mathord, "\u03b6", "\\zeta", true); +defineSymbol(math, main, mathord, "\u03b7", "\\eta", true); +defineSymbol(math, main, mathord, "\u03b8", "\\theta", true); +defineSymbol(math, main, mathord, "\u03b9", "\\iota", true); +defineSymbol(math, main, mathord, "\u03ba", "\\kappa", true); +defineSymbol(math, main, mathord, "\u03bb", "\\lambda", true); +defineSymbol(math, main, mathord, "\u03bc", "\\mu", true); +defineSymbol(math, main, mathord, "\u03bd", "\\nu", true); +defineSymbol(math, main, mathord, "\u03be", "\\xi", true); +defineSymbol(math, main, mathord, "\u03bf", "\\omicron", true); +defineSymbol(math, main, mathord, "\u03c0", "\\pi", true); +defineSymbol(math, main, mathord, "\u03c1", "\\rho", true); +defineSymbol(math, main, mathord, "\u03c3", "\\sigma", true); +defineSymbol(math, main, mathord, "\u03c4", "\\tau", true); +defineSymbol(math, main, mathord, "\u03c5", "\\upsilon", true); +defineSymbol(math, main, mathord, "\u03d5", "\\phi", true); +defineSymbol(math, main, mathord, "\u03c7", "\\chi", true); +defineSymbol(math, main, mathord, "\u03c8", "\\psi", true); +defineSymbol(math, main, mathord, "\u03c9", "\\omega", true); +defineSymbol(math, main, mathord, "\u03b5", "\\varepsilon", true); +defineSymbol(math, main, mathord, "\u03d1", "\\vartheta", true); +defineSymbol(math, main, mathord, "\u03d6", "\\varpi", true); +defineSymbol(math, main, mathord, "\u03f1", "\\varrho", true); +defineSymbol(math, main, mathord, "\u03c2", "\\varsigma", true); +defineSymbol(math, main, mathord, "\u03c6", "\\varphi", true); +defineSymbol(math, main, bin, "\u2217", "*", true); +defineSymbol(math, main, bin, "+", "+"); +defineSymbol(math, main, bin, "\u2212", "-", true); +defineSymbol(math, main, bin, "\u22c5", "\\cdot", true); +defineSymbol(math, main, bin, "\u2218", "\\circ", true); +defineSymbol(math, main, bin, "\u00f7", "\\div", true); +defineSymbol(math, main, bin, "\u00b1", "\\pm", true); +defineSymbol(math, main, bin, "\u00d7", "\\times", true); +defineSymbol(math, main, bin, "\u2229", "\\cap", true); +defineSymbol(math, main, bin, "\u222a", "\\cup", true); +defineSymbol(math, main, bin, "\u2216", "\\setminus", true); +defineSymbol(math, main, bin, "\u2227", "\\land"); +defineSymbol(math, main, bin, "\u2228", "\\lor"); +defineSymbol(math, main, bin, "\u2227", "\\wedge", true); +defineSymbol(math, main, bin, "\u2228", "\\vee", true); +defineSymbol(math, main, textord, "\u221a", "\\surd"); +defineSymbol(math, main, open, "\u27e8", "\\langle", true); +defineSymbol(math, main, open, "\u2223", "\\lvert"); +defineSymbol(math, main, open, "\u2225", "\\lVert"); +defineSymbol(math, main, close, "?", "?"); +defineSymbol(math, main, close, "!", "!"); +defineSymbol(math, main, close, "\u27e9", "\\rangle", true); +defineSymbol(math, main, close, "\u2223", "\\rvert"); +defineSymbol(math, main, close, "\u2225", "\\rVert"); +defineSymbol(math, main, rel, "=", "="); +defineSymbol(math, main, rel, ":", ":"); +defineSymbol(math, main, rel, "\u2248", "\\approx", true); +defineSymbol(math, main, rel, "\u2245", "\\cong", true); +defineSymbol(math, main, rel, "\u2265", "\\ge"); +defineSymbol(math, main, rel, "\u2265", "\\geq", true); +defineSymbol(math, main, rel, "\u2190", "\\gets"); +defineSymbol(math, main, rel, ">", "\\gt", true); +defineSymbol(math, main, rel, "\u2208", "\\in", true); +defineSymbol(math, main, rel, "\ue020", "\\@not"); +defineSymbol(math, main, rel, "\u2282", "\\subset", true); +defineSymbol(math, main, rel, "\u2283", "\\supset", true); +defineSymbol(math, main, rel, "\u2286", "\\subseteq", true); +defineSymbol(math, main, rel, "\u2287", "\\supseteq", true); +defineSymbol(math, ams, rel, "\u2288", "\\nsubseteq", true); +defineSymbol(math, ams, rel, "\u2289", "\\nsupseteq", true); +defineSymbol(math, main, rel, "\u22a8", "\\models"); +defineSymbol(math, main, rel, "\u2190", "\\leftarrow", true); +defineSymbol(math, main, rel, "\u2264", "\\le"); +defineSymbol(math, main, rel, "\u2264", "\\leq", true); +defineSymbol(math, main, rel, "<", "\\lt", true); +defineSymbol(math, main, rel, "\u2192", "\\rightarrow", true); +defineSymbol(math, main, rel, "\u2192", "\\to"); +defineSymbol(math, ams, rel, "\u2271", "\\ngeq", true); +defineSymbol(math, ams, rel, "\u2270", "\\nleq", true); +defineSymbol(math, main, spacing, "\u00a0", "\\ "); +defineSymbol(math, main, spacing, "\u00a0", "\\space"); +// Ref: LaTeX Source 2e: \DeclareRobustCommand{\nobreakspace}{% +defineSymbol(math, main, spacing, "\u00a0", "\\nobreakspace"); +defineSymbol(text, main, spacing, "\u00a0", "\\ "); +defineSymbol(text, main, spacing, "\u00a0", " "); +defineSymbol(text, main, spacing, "\u00a0", "\\space"); +defineSymbol(text, main, spacing, "\u00a0", "\\nobreakspace"); +defineSymbol(math, main, spacing, null, "\\nobreak"); +defineSymbol(math, main, spacing, null, "\\allowbreak"); +defineSymbol(math, main, punct, ",", ","); +defineSymbol(math, main, punct, ";", ";"); +defineSymbol(math, ams, bin, "\u22bc", "\\barwedge", true); +defineSymbol(math, ams, bin, "\u22bb", "\\veebar", true); +defineSymbol(math, main, bin, "\u2299", "\\odot", true); +defineSymbol(math, main, bin, "\u2295", "\\oplus", true); +defineSymbol(math, main, bin, "\u2297", "\\otimes", true); +defineSymbol(math, main, textord, "\u2202", "\\partial", true); +defineSymbol(math, main, bin, "\u2298", "\\oslash", true); +defineSymbol(math, ams, bin, "\u229a", "\\circledcirc", true); +defineSymbol(math, ams, bin, "\u22a1", "\\boxdot", true); +defineSymbol(math, main, bin, "\u25b3", "\\bigtriangleup"); +defineSymbol(math, main, bin, "\u25bd", "\\bigtriangledown"); +defineSymbol(math, main, bin, "\u2020", "\\dagger"); +defineSymbol(math, main, bin, "\u22c4", "\\diamond"); +defineSymbol(math, main, bin, "\u22c6", "\\star"); +defineSymbol(math, main, bin, "\u25c3", "\\triangleleft"); +defineSymbol(math, main, bin, "\u25b9", "\\triangleright"); +defineSymbol(math, main, open, "{", "\\{"); +defineSymbol(text, main, textord, "{", "\\{"); +defineSymbol(text, main, textord, "{", "\\textbraceleft"); +defineSymbol(math, main, close, "}", "\\}"); +defineSymbol(text, main, textord, "}", "\\}"); +defineSymbol(text, main, textord, "}", "\\textbraceright"); +defineSymbol(math, main, open, "{", "\\lbrace"); +defineSymbol(math, main, close, "}", "\\rbrace"); +defineSymbol(math, main, open, "[", "\\lbrack", true); +defineSymbol(text, main, textord, "[", "\\lbrack", true); +defineSymbol(math, main, close, "]", "\\rbrack", true); +defineSymbol(text, main, textord, "]", "\\rbrack", true); +defineSymbol(math, main, open, "(", "\\lparen", true); +defineSymbol(math, main, close, ")", "\\rparen", true); +defineSymbol(text, main, textord, "<", "\\textless", true); // in T1 fontenc +defineSymbol(text, main, textord, ">", "\\textgreater", true); // in T1 fontenc +defineSymbol(math, main, open, "\u230a", "\\lfloor", true); +defineSymbol(math, main, close, "\u230b", "\\rfloor", true); +defineSymbol(math, main, open, "\u2308", "\\lceil", true); +defineSymbol(math, main, close, "\u2309", "\\rceil", true); +defineSymbol(math, main, textord, "\\", "\\backslash"); +defineSymbol(math, main, textord, "\u2223", "|"); +defineSymbol(math, main, textord, "\u2223", "\\vert"); +defineSymbol(text, main, textord, "|", "\\textbar", true); // in T1 fontenc +defineSymbol(math, main, textord, "\u2225", "\\|"); +defineSymbol(math, main, textord, "\u2225", "\\Vert"); +defineSymbol(text, main, textord, "\u2225", "\\textbardbl"); +defineSymbol(text, main, textord, "~", "\\textasciitilde"); +defineSymbol(text, main, textord, "\\", "\\textbackslash"); +defineSymbol(text, main, textord, "^", "\\textasciicircum"); +defineSymbol(math, main, rel, "\u2191", "\\uparrow", true); +defineSymbol(math, main, rel, "\u21d1", "\\Uparrow", true); +defineSymbol(math, main, rel, "\u2193", "\\downarrow", true); +defineSymbol(math, main, rel, "\u21d3", "\\Downarrow", true); +defineSymbol(math, main, rel, "\u2195", "\\updownarrow", true); +defineSymbol(math, main, rel, "\u21d5", "\\Updownarrow", true); +defineSymbol(math, main, op, "\u2210", "\\coprod"); +defineSymbol(math, main, op, "\u22c1", "\\bigvee"); +defineSymbol(math, main, op, "\u22c0", "\\bigwedge"); +defineSymbol(math, main, op, "\u2a04", "\\biguplus"); +defineSymbol(math, main, op, "\u22c2", "\\bigcap"); +defineSymbol(math, main, op, "\u22c3", "\\bigcup"); +defineSymbol(math, main, op, "\u222b", "\\int"); +defineSymbol(math, main, op, "\u222b", "\\intop"); +defineSymbol(math, main, op, "\u222c", "\\iint"); +defineSymbol(math, main, op, "\u222d", "\\iiint"); +defineSymbol(math, main, op, "\u220f", "\\prod"); +defineSymbol(math, main, op, "\u2211", "\\sum"); +defineSymbol(math, main, op, "\u2a02", "\\bigotimes"); +defineSymbol(math, main, op, "\u2a01", "\\bigoplus"); +defineSymbol(math, main, op, "\u2a00", "\\bigodot"); +defineSymbol(math, main, op, "\u222e", "\\oint"); +defineSymbol(math, main, op, "\u222f", "\\oiint"); +defineSymbol(math, main, op, "\u2230", "\\oiiint"); +defineSymbol(math, main, op, "\u2a06", "\\bigsqcup"); +defineSymbol(math, main, op, "\u222b", "\\smallint"); +defineSymbol(text, main, inner, "\u2026", "\\textellipsis"); +defineSymbol(math, main, inner, "\u2026", "\\mathellipsis"); +defineSymbol(text, main, inner, "\u2026", "\\ldots", true); +defineSymbol(math, main, inner, "\u2026", "\\ldots", true); +defineSymbol(math, main, inner, "\u22ef", "\\@cdots", true); +defineSymbol(math, main, inner, "\u22f1", "\\ddots", true); +// \vdots is a macro that uses one of these two symbols (with made-up names): +defineSymbol(math, main, textord, "\u22ee", "\\varvdots"); +defineSymbol(text, main, textord, "\u22ee", "\\varvdots"); +defineSymbol(math, main, accent, "\u02ca", "\\acute"); +defineSymbol(math, main, accent, "\u02cb", "\\grave"); +defineSymbol(math, main, accent, "\u00a8", "\\ddot"); +defineSymbol(math, main, accent, "\u007e", "\\tilde"); +defineSymbol(math, main, accent, "\u02c9", "\\bar"); +defineSymbol(math, main, accent, "\u02d8", "\\breve"); +defineSymbol(math, main, accent, "\u02c7", "\\check"); +defineSymbol(math, main, accent, "\u005e", "\\hat"); +defineSymbol(math, main, accent, "\u20d7", "\\vec"); +defineSymbol(math, main, accent, "\u02d9", "\\dot"); +defineSymbol(math, main, accent, "\u02da", "\\mathring"); +// \imath and \jmath should be invariant to \mathrm, \mathbf, etc., so use PUA +defineSymbol(math, main, mathord, "\ue131", "\\@imath"); +defineSymbol(math, main, mathord, "\ue237", "\\@jmath"); +defineSymbol(math, main, textord, "\u0131", "\u0131"); +defineSymbol(math, main, textord, "\u0237", "\u0237"); +defineSymbol(text, main, textord, "\u0131", "\\i", true); +defineSymbol(text, main, textord, "\u0237", "\\j", true); +defineSymbol(text, main, textord, "\u00df", "\\ss", true); +defineSymbol(text, main, textord, "\u00e6", "\\ae", true); +defineSymbol(text, main, textord, "\u0153", "\\oe", true); +defineSymbol(text, main, textord, "\u00f8", "\\o", true); +defineSymbol(text, main, textord, "\u00c6", "\\AE", true); +defineSymbol(text, main, textord, "\u0152", "\\OE", true); +defineSymbol(text, main, textord, "\u00d8", "\\O", true); +defineSymbol(text, main, accent, "\u02ca", "\\'"); // acute +defineSymbol(text, main, accent, "\u02cb", "\\`"); // grave +defineSymbol(text, main, accent, "\u02c6", "\\^"); // circumflex +defineSymbol(text, main, accent, "\u02dc", "\\~"); // tilde +defineSymbol(text, main, accent, "\u02c9", "\\="); // macron +defineSymbol(text, main, accent, "\u02d8", "\\u"); // breve +defineSymbol(text, main, accent, "\u02d9", "\\."); // dot above +defineSymbol(text, main, accent, "\u00b8", "\\c"); // cedilla +defineSymbol(text, main, accent, "\u02da", "\\r"); // ring above +defineSymbol(text, main, accent, "\u02c7", "\\v"); // caron +defineSymbol(text, main, accent, "\u00a8", '\\"'); // diaeresis +defineSymbol(text, main, accent, "\u02dd", "\\H"); // double acute +defineSymbol(text, main, accent, "\u25ef", "\\textcircled"); // \bigcirc glyph + +// These ligatures are detected and created in Parser.js's `formLigatures`. +export const ligatures = { + "--": true, + "---": true, + "``": true, + "''": true, +}; + +defineSymbol(text, main, textord, "\u2013", "--", true); +defineSymbol(text, main, textord, "\u2013", "\\textendash"); +defineSymbol(text, main, textord, "\u2014", "---", true); +defineSymbol(text, main, textord, "\u2014", "\\textemdash"); +defineSymbol(text, main, textord, "\u2018", "`", true); +defineSymbol(text, main, textord, "\u2018", "\\textquoteleft"); +defineSymbol(text, main, textord, "\u2019", "'", true); +defineSymbol(text, main, textord, "\u2019", "\\textquoteright"); +defineSymbol(text, main, textord, "\u201c", "``", true); +defineSymbol(text, main, textord, "\u201c", "\\textquotedblleft"); +defineSymbol(text, main, textord, "\u201d", "''", true); +defineSymbol(text, main, textord, "\u201d", "\\textquotedblright"); +// \degree from gensymb package +defineSymbol(math, main, textord, "\u00b0", "\\degree", true); +defineSymbol(text, main, textord, "\u00b0", "\\degree"); +// \textdegree from inputenc package +defineSymbol(text, main, textord, "\u00b0", "\\textdegree", true); +// TODO: In LaTeX, \pounds can generate a different character in text and math +// mode, but among our fonts, only Main-Regular defines this character "163". +defineSymbol(math, main, textord, "\u00a3", "\\pounds"); +defineSymbol(math, main, textord, "\u00a3", "\\mathsterling", true); +defineSymbol(text, main, textord, "\u00a3", "\\pounds"); +defineSymbol(text, main, textord, "\u00a3", "\\textsterling", true); +defineSymbol(math, ams, textord, "\u2720", "\\maltese"); +defineSymbol(text, ams, textord, "\u2720", "\\maltese"); + +// There are lots of symbols which are the same, so we add them in afterwards. +// All of these are textords in math mode +const mathTextSymbols = "0123456789/@.\""; +for (let i = 0; i < mathTextSymbols.length; i++) { + const ch = mathTextSymbols.charAt(i); + defineSymbol(math, main, textord, ch, ch); +} + +// All of these are textords in text mode +const textSymbols = "0123456789!@*()-=+\";:?/.,"; +for (let i = 0; i < textSymbols.length; i++) { + const ch = textSymbols.charAt(i); + defineSymbol(text, main, textord, ch, ch); +} + +// All of these are textords in text mode, and mathords in math mode +const letters = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; +for (let i = 0; i < letters.length; i++) { + const ch = letters.charAt(i); + defineSymbol(math, main, mathord, ch, ch); + defineSymbol(text, main, textord, ch, ch); +} + +// Blackboard bold and script letters in Unicode range +defineSymbol(math, ams, textord, "C", "\u2102"); // blackboard bold +defineSymbol(text, ams, textord, "C", "\u2102"); +defineSymbol(math, ams, textord, "H", "\u210D"); +defineSymbol(text, ams, textord, "H", "\u210D"); +defineSymbol(math, ams, textord, "N", "\u2115"); +defineSymbol(text, ams, textord, "N", "\u2115"); +defineSymbol(math, ams, textord, "P", "\u2119"); +defineSymbol(text, ams, textord, "P", "\u2119"); +defineSymbol(math, ams, textord, "Q", "\u211A"); +defineSymbol(text, ams, textord, "Q", "\u211A"); +defineSymbol(math, ams, textord, "R", "\u211D"); +defineSymbol(text, ams, textord, "R", "\u211D"); +defineSymbol(math, ams, textord, "Z", "\u2124"); +defineSymbol(text, ams, textord, "Z", "\u2124"); +defineSymbol(math, main, mathord, "h", "\u210E"); // italic h, Planck constant +defineSymbol(text, main, mathord, "h", "\u210E"); + +// The next loop loads wide (surrogate pair) characters. +// We support some letters in the Unicode range U+1D400 to U+1D7FF, +// Mathematical Alphanumeric Symbols. +// Some editors do not deal well with wide characters. So don't write the +// string into this file. Instead, create the string from the surrogate pair. +let wideChar = ""; +for (let i = 0; i < letters.length; i++) { + const ch = letters.charAt(i); + + // The hex numbers in the next line are a surrogate pair. + // 0xD835 is the high surrogate for all letters in the range we support. + // 0xDC00 is the low surrogate for bold A. + wideChar = String.fromCharCode(0xD835, 0xDC00 + i); // A-Z a-z bold + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + wideChar = String.fromCharCode(0xD835, 0xDC34 + i); // A-Z a-z italic + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + wideChar = String.fromCharCode(0xD835, 0xDC68 + i); // A-Z a-z bold italic + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + wideChar = String.fromCharCode(0xD835, 0xDD04 + i); // A-Z a-z Fraktur + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + wideChar = String.fromCharCode(0xD835, 0xDD6C + i); // A-Z a-z bold Fraktur + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + wideChar = String.fromCharCode(0xD835, 0xDDA0 + i); // A-Z a-z sans-serif + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + wideChar = String.fromCharCode(0xD835, 0xDDD4 + i); // A-Z a-z sans bold + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + wideChar = String.fromCharCode(0xD835, 0xDE08 + i); // A-Z a-z sans italic + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + wideChar = String.fromCharCode(0xD835, 0xDE70 + i); // A-Z a-z monospace + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + if (i < 26) { + // KaTeX fonts have only capital letters for blackboard bold and script. + // See exception for k below. + wideChar = String.fromCharCode(0xD835, 0xDD38 + i); // A-Z double struck + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + wideChar = String.fromCharCode(0xD835, 0xDC9C + i); // A-Z script + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + } + + // TODO: Add bold script when it is supported by a KaTeX font. +} +// "k" is the only double struck lower case letter in the KaTeX fonts. +wideChar = String.fromCharCode(0xD835, 0xDD5C); // k double struck +defineSymbol(math, main, mathord, "k", wideChar); +defineSymbol(text, main, textord, "k", wideChar); + +// Next, some wide character numerals +for (let i = 0; i < 10; i++) { + const ch = i.toString(); + + wideChar = String.fromCharCode(0xD835, 0xDFCE + i); // 0-9 bold + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + wideChar = String.fromCharCode(0xD835, 0xDFE2 + i); // 0-9 sans serif + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + wideChar = String.fromCharCode(0xD835, 0xDFEC + i); // 0-9 bold sans + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); + + wideChar = String.fromCharCode(0xD835, 0xDFF6 + i); // 0-9 monospace + defineSymbol(math, main, mathord, ch, wideChar); + defineSymbol(text, main, textord, ch, wideChar); +} + +// We add these Latin-1 letters as symbols for backwards-compatibility, +// but they are not actually in the font, nor are they supported by the +// Unicode accent mechanism, so they fall back to Times font and look ugly. +// TODO(edemaine): Fix this. +export const extraLatin = "\u00d0\u00de\u00fe"; +for (let i = 0; i < extraLatin.length; i++) { + const ch = extraLatin.charAt(i); + defineSymbol(math, main, mathord, ch, ch); + defineSymbol(text, main, textord, ch, ch); +} diff --git a/frontend/node_modules/katex/src/tree.js b/frontend/node_modules/katex/src/tree.js new file mode 100644 index 0000000..940a44d --- /dev/null +++ b/frontend/node_modules/katex/src/tree.js @@ -0,0 +1,78 @@ +// @flow + +import utils from "./utils"; + +import type {CssStyle, HtmlDomNode} from "./domTree"; +import type {MathDomNode} from "./mathMLTree"; + + +// To ensure that all nodes have compatible signatures for these methods. +export interface VirtualNode { + toNode(): Node; + toMarkup(): string; +} + + +/** + * This node represents a document fragment, which contains elements, but when + * placed into the DOM doesn't have any representation itself. It only contains + * children and doesn't have any DOM node properties. + */ +export class DocumentFragment + implements HtmlDomNode, MathDomNode { + children: $ReadOnlyArray; + // HtmlDomNode + classes: string[]; + height: number; + depth: number; + maxFontSize: number; + style: CssStyle; // Never used; needed for satisfying interface. + + constructor(children: $ReadOnlyArray) { + this.children = children; + this.classes = []; + this.height = 0; + this.depth = 0; + this.maxFontSize = 0; + this.style = {}; + } + + hasClass(className: string): boolean { + return utils.contains(this.classes, className); + } + + /** Convert the fragment into a node. */ + toNode(): Node { + const frag = document.createDocumentFragment(); + + for (let i = 0; i < this.children.length; i++) { + frag.appendChild(this.children[i].toNode()); + } + + return frag; + } + + /** Convert the fragment into HTML markup. */ + toMarkup(): string { + let markup = ""; + + // Simply concatenate the markup for the children together. + for (let i = 0; i < this.children.length; i++) { + markup += this.children[i].toMarkup(); + } + + return markup; + } + + /** + * Converts the math node into a string, similar to innerText. Applies to + * MathDomNode's only. + */ + toText(): string { + // To avoid this, we would subclass documentFragment separately for + // MathML, but polyfills for subclassing is expensive per PR 1469. + // $FlowFixMe: Only works for ChildType = MathDomNode. + const toText = (child: ChildType): string => child.toText(); + return this.children.map(toText).join(""); + } +} diff --git a/frontend/node_modules/katex/src/types.js b/frontend/node_modules/katex/src/types.js new file mode 100644 index 0000000..51e2508 --- /dev/null +++ b/frontend/node_modules/katex/src/types.js @@ -0,0 +1,36 @@ +// @flow + +/** + * This file consists only of basic flow types used in multiple places. + * For types with javascript, create separate files by themselves. + */ + +export type Mode = "math" | "text"; + +// LaTeX argument type. +// - "size": A size-like thing, such as "1em" or "5ex" +// - "color": An html color, like "#abc" or "blue" +// - "url": An url string, in which "\" will be ignored +// - if it precedes [#$%&~_^\{}] +// - "raw": A string, allowing single character, percent sign, +// and nested braces +// - "original": The same type as the environment that the +// function being parsed is in (e.g. used for the +// bodies of functions like \textcolor where the +// first argument is special and the second +// argument is parsed normally) +// - Mode: Node group parsed in given mode. +export type ArgType = "color" | "size" | "url" | "raw" | "original" | "hbox" | + "primitive" | Mode; + +// LaTeX display style. +export type StyleStr = "text" | "display" | "script" | "scriptscript"; + +// Allowable token text for "break" arguments in parser. +export type BreakToken = "]" | "}" | "\\endgroup" | "$" | "\\)" | "\\\\" | "\\end" | + "EOF"; + +// Math font variants. +export type FontVariant = "bold" | "bold-italic" | "bold-sans-serif" | + "double-struck" | "fraktur" | "italic" | "monospace" | "normal" | "sans-serif" | + "sans-serif-bold-italic" | "sans-serif-italic" | "script"; diff --git a/frontend/node_modules/katex/src/unicodeAccents.js b/frontend/node_modules/katex/src/unicodeAccents.js new file mode 100644 index 0000000..e8f15ce --- /dev/null +++ b/frontend/node_modules/katex/src/unicodeAccents.js @@ -0,0 +1,18 @@ +// Mapping of Unicode accent characters to their LaTeX equivalent in text and +// math mode (when they exist). +// This exports a CommonJS module, allowing to be required in unicodeSymbols +// without transpiling. +module.exports = { + '\u0301': {text: "\\'", math: '\\acute'}, + '\u0300': {text: '\\`', math: '\\grave'}, + '\u0308': {text: '\\"', math: '\\ddot'}, + '\u0303': {text: '\\~', math: '\\tilde'}, + '\u0304': {text: '\\=', math: '\\bar'}, + '\u0306': {text: '\\u', math: '\\breve'}, + '\u030c': {text: '\\v', math: '\\check'}, + '\u0302': {text: '\\^', math: '\\hat'}, + '\u0307': {text: '\\.', math: '\\dot'}, + '\u030a': {text: '\\r', math: '\\mathring'}, + '\u030b': {text: '\\H'}, + '\u0327': {text: '\\c'}, +}; diff --git a/frontend/node_modules/katex/src/unicodeScripts.js b/frontend/node_modules/katex/src/unicodeScripts.js new file mode 100644 index 0000000..59b05e5 --- /dev/null +++ b/frontend/node_modules/katex/src/unicodeScripts.js @@ -0,0 +1,126 @@ +// @flow + +/* + * This file defines the Unicode scripts and script families that we + * support. To add new scripts or families, just add a new entry to the + * scriptData array below. Adding scripts to the scriptData array allows + * characters from that script to appear in \text{} environments. + */ + +/** + * Each script or script family has a name and an array of blocks. + * Each block is an array of two numbers which specify the start and + * end points (inclusive) of a block of Unicode codepoints. + */ +type Script = { + name: string; + blocks: Array>; +}; + +/** + * Unicode block data for the families of scripts we support in \text{}. + * Scripts only need to appear here if they do not have font metrics. + */ +const scriptData: Array

    inserted

    ' +``` + +_Differences in browser._ If you load script directly into the page, without +package system, module will add itself globally as `window.markdownitIns`. + + +## License + +[MIT](https://github.com/markdown-it/markdown-it-ins/blob/master/LICENSE) diff --git a/frontend/node_modules/markdown-it-ins/dist/index.cjs.js b/frontend/node_modules/markdown-it-ins/dist/index.cjs.js new file mode 100644 index 0000000..0435c85 --- /dev/null +++ b/frontend/node_modules/markdown-it-ins/dist/index.cjs.js @@ -0,0 +1,113 @@ +'use strict'; + +function ins_plugin(md) { + // Insert each marker as a separate text token, and add it to delimiter list + // + function tokenize(state, silent) { + const start = state.pos; + const marker = state.src.charCodeAt(start); + if (silent) { + return false; + } + if (marker !== 0x2B /* + */) { + return false; + } + const scanned = state.scanDelims(state.pos, true); + let len = scanned.length; + const ch = String.fromCharCode(marker); + if (len < 2) { + return false; + } + if (len % 2) { + const token = state.push('text', '', 0); + token.content = ch; + len--; + } + for (let i = 0; i < len; i += 2) { + const token = state.push('text', '', 0); + token.content = ch + ch; + if (!scanned.can_open && !scanned.can_close) { + continue; + } + state.delimiters.push({ + marker, + length: 0, + // disable "rule of 3" length checks meant for emphasis + jump: i / 2, + // 1 delimiter = 2 characters + token: state.tokens.length - 1, + end: -1, + open: scanned.can_open, + close: scanned.can_close + }); + } + state.pos += scanned.length; + return true; + } + + // Walk through delimiter list and replace text tokens with tags + // + function postProcess(state, delimiters) { + let token; + const loneMarkers = []; + const max = delimiters.length; + for (let i = 0; i < max; i++) { + const startDelim = delimiters[i]; + if (startDelim.marker !== 0x2B /* + */) { + continue; + } + if (startDelim.end === -1) { + continue; + } + const endDelim = delimiters[startDelim.end]; + token = state.tokens[startDelim.token]; + token.type = 'ins_open'; + token.tag = 'ins'; + token.nesting = 1; + token.markup = '++'; + token.content = ''; + token = state.tokens[endDelim.token]; + token.type = 'ins_close'; + token.tag = 'ins'; + token.nesting = -1; + token.markup = '++'; + token.content = ''; + if (state.tokens[endDelim.token - 1].type === 'text' && state.tokens[endDelim.token - 1].content === '+') { + loneMarkers.push(endDelim.token - 1); + } + } + + // If a marker sequence has an odd number of characters, it's splitted + // like this: `~~~~~` -> `~` + `~~` + `~~`, leaving one marker at the + // start of the sequence. + // + // So, we have to move all those markers after subsequent s_close tags. + // + while (loneMarkers.length) { + const i = loneMarkers.pop(); + let j = i + 1; + while (j < state.tokens.length && state.tokens[j].type === 'ins_close') { + j++; + } + j--; + if (i !== j) { + token = state.tokens[j]; + state.tokens[j] = state.tokens[i]; + state.tokens[i] = token; + } + } + } + md.inline.ruler.before('emphasis', 'ins', tokenize); + md.inline.ruler2.before('emphasis', 'ins', function (state) { + const tokens_meta = state.tokens_meta; + const max = (state.tokens_meta || []).length; + postProcess(state, state.delimiters); + for (let curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + postProcess(state, tokens_meta[curr].delimiters); + } + } + }); +} + +module.exports = ins_plugin; diff --git a/frontend/node_modules/markdown-it-ins/dist/markdown-it-ins.js b/frontend/node_modules/markdown-it-ins/dist/markdown-it-ins.js new file mode 100644 index 0000000..8049e43 --- /dev/null +++ b/frontend/node_modules/markdown-it-ins/dist/markdown-it-ins.js @@ -0,0 +1,114 @@ +/*! markdown-it-ins 4.0.0 https://github.com/markdown-it/markdown-it-ins @license MIT */ +(function(global, factory) { + typeof exports === "object" && typeof module !== "undefined" ? module.exports = factory() : typeof define === "function" && define.amd ? define(factory) : (global = typeof globalThis !== "undefined" ? globalThis : global || self, + global.markdownitIns = factory()); +})(this, (function() { + "use strict"; + function ins_plugin(md) { + // Insert each marker as a separate text token, and add it to delimiter list + function tokenize(state, silent) { + const start = state.pos; + const marker = state.src.charCodeAt(start); + if (silent) { + return false; + } + if (marker !== 43 /* + */) { + return false; + } + const scanned = state.scanDelims(state.pos, true); + let len = scanned.length; + const ch = String.fromCharCode(marker); + if (len < 2) { + return false; + } + if (len % 2) { + const token = state.push("text", "", 0); + token.content = ch; + len--; + } + for (let i = 0; i < len; i += 2) { + const token = state.push("text", "", 0); + token.content = ch + ch; + if (!scanned.can_open && !scanned.can_close) { + continue; + } + state.delimiters.push({ + marker: marker, + length: 0, + // disable "rule of 3" length checks meant for emphasis + jump: i / 2, + // 1 delimiter = 2 characters + token: state.tokens.length - 1, + end: -1, + open: scanned.can_open, + close: scanned.can_close + }); + } + state.pos += scanned.length; + return true; + } + // Walk through delimiter list and replace text tokens with tags + + function postProcess(state, delimiters) { + let token; + const loneMarkers = []; + const max = delimiters.length; + for (let i = 0; i < max; i++) { + const startDelim = delimiters[i]; + if (startDelim.marker !== 43 /* + */) { + continue; + } + if (startDelim.end === -1) { + continue; + } + const endDelim = delimiters[startDelim.end]; + token = state.tokens[startDelim.token]; + token.type = "ins_open"; + token.tag = "ins"; + token.nesting = 1; + token.markup = "++"; + token.content = ""; + token = state.tokens[endDelim.token]; + token.type = "ins_close"; + token.tag = "ins"; + token.nesting = -1; + token.markup = "++"; + token.content = ""; + if (state.tokens[endDelim.token - 1].type === "text" && state.tokens[endDelim.token - 1].content === "+") { + loneMarkers.push(endDelim.token - 1); + } + } + // If a marker sequence has an odd number of characters, it's splitted + // like this: `~~~~~` -> `~` + `~~` + `~~`, leaving one marker at the + // start of the sequence. + + // So, we have to move all those markers after subsequent s_close tags. + + while (loneMarkers.length) { + const i = loneMarkers.pop(); + let j = i + 1; + while (j < state.tokens.length && state.tokens[j].type === "ins_close") { + j++; + } + j--; + if (i !== j) { + token = state.tokens[j]; + state.tokens[j] = state.tokens[i]; + state.tokens[i] = token; + } + } + } + md.inline.ruler.before("emphasis", "ins", tokenize); + md.inline.ruler2.before("emphasis", "ins", (function(state) { + const tokens_meta = state.tokens_meta; + const max = (state.tokens_meta || []).length; + postProcess(state, state.delimiters); + for (let curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + postProcess(state, tokens_meta[curr].delimiters); + } + } + })); + } + return ins_plugin; +})); diff --git a/frontend/node_modules/markdown-it-ins/dist/markdown-it-ins.min.js b/frontend/node_modules/markdown-it-ins/dist/markdown-it-ins.min.js new file mode 100644 index 0000000..5a220f6 --- /dev/null +++ b/frontend/node_modules/markdown-it-ins/dist/markdown-it-ins.min.js @@ -0,0 +1,2 @@ +/*! markdown-it-ins 4.0.0 https://github.com/markdown-it/markdown-it-ins @license MIT */ +!function(e,n){"object"==typeof exports&&"undefined"!=typeof module?module.exports=n():"function"==typeof define&&define.amd?define(n):(e="undefined"!=typeof globalThis?globalThis:e||self).markdownitIns=n()}(this,(function(){"use strict";return function(e){function n(e,n){let t;const o=[],s=n.length;for(let i=0;i `~` + `~~` + `~~`, leaving one marker at the + // start of the sequence. + // + // So, we have to move all those markers after subsequent s_close tags. + // + while (loneMarkers.length) { + const i = loneMarkers.pop() + let j = i + 1 + + while (j < state.tokens.length && state.tokens[j].type === 'ins_close') { + j++ + } + + j-- + + if (i !== j) { + token = state.tokens[j] + state.tokens[j] = state.tokens[i] + state.tokens[i] = token + } + } + } + + md.inline.ruler.before('emphasis', 'ins', tokenize) + md.inline.ruler2.before('emphasis', 'ins', function (state) { + const tokens_meta = state.tokens_meta + const max = (state.tokens_meta || []).length + + postProcess(state, state.delimiters) + + for (let curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + postProcess(state, tokens_meta[curr].delimiters) + } + } + }) +}; diff --git a/frontend/node_modules/markdown-it-ins/package.json b/frontend/node_modules/markdown-it-ins/package.json new file mode 100644 index 0000000..fe306dc --- /dev/null +++ b/frontend/node_modules/markdown-it-ins/package.json @@ -0,0 +1,49 @@ +{ + "name": "markdown-it-ins", + "version": "4.0.0", + "description": " tag for markdown-it markdown parser.", + "keywords": [ + "markdown-it-plugin", + "markdown-it", + "markdown", + "insert", + "ins" + ], + "repository": "markdown-it/markdown-it-ins", + "license": "MIT", + "main": "dist/index.cjs.js", + "module": "index.mjs", + "exports": { + ".": { + "require": "./dist/index.cjs.js", + "import": "./index.mjs" + }, + "./*": { + "require": "./*", + "import": "./*" + } + }, + "files": [ + "index.mjs", + "lib/", + "dist/" + ], + "scripts": { + "lint": "eslint .", + "build": "rollup -c", + "test": "npm run lint && npm run build && c8 --exclude dist --exclude test -r text -r html -r lcov mocha", + "prepublishOnly": "npm run lint && npm run build" + }, + "devDependencies": { + "@rollup/plugin-babel": "^6.0.4", + "@rollup/plugin-node-resolve": "^15.2.3", + "@rollup/plugin-terser": "^0.4.4", + "c8": "^8.0.1", + "eslint": "^8.55.0", + "eslint-config-standard": "^17.1.0", + "markdown-it": "^13.0.2", + "markdown-it-testgen": "^0.1.6", + "mocha": "^10.2.0", + "rollup": "^4.6.1" + } +} diff --git a/frontend/node_modules/markdown-it-mark/LICENSE b/frontend/node_modules/markdown-it-mark/LICENSE new file mode 100644 index 0000000..2fd4e3d --- /dev/null +++ b/frontend/node_modules/markdown-it-mark/LICENSE @@ -0,0 +1,22 @@ +Copyright (c) 2014-2015 Vitaly Puzrin, Alex Kocharin. + +Permission is hereby granted, free of charge, to any person +obtaining a copy of this software and associated documentation +files (the "Software"), to deal in the Software without +restriction, including without limitation the rights to use, +copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the +Software is furnished to do so, subject to the following +conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES +OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT +HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +OTHER DEALINGS IN THE SOFTWARE. diff --git a/frontend/node_modules/markdown-it-mark/README.md b/frontend/node_modules/markdown-it-mark/README.md new file mode 100644 index 0000000..2274165 --- /dev/null +++ b/frontend/node_modules/markdown-it-mark/README.md @@ -0,0 +1,40 @@ +# markdown-it-mark + +[![CI](https://github.com/markdown-it/markdown-it-mark/workflows/CI/badge.svg?branch=master)](https://github.com/markdown-it/markdown-it-mark/actions) +[![NPM version](https://img.shields.io/npm/v/markdown-it-mark.svg?style=flat)](https://www.npmjs.org/package/markdown-it-mark) +[![Coverage Status](https://img.shields.io/coveralls/markdown-it/markdown-it-mark/master.svg?style=flat)](https://coveralls.io/r/markdown-it/markdown-it-mark?branch=master) + +> `` tag plugin for [markdown-it](https://github.com/markdown-it/markdown-it) markdown parser. + +__v3.+ requires `markdown-it` v10.+, see changelog.__ + +`==marked==` => `inserted` + +Markup uses the same conditions as CommonMark [emphasis](http://spec.commonmark.org/0.15/#emphasis-and-strong-emphasis). + + +## Install + +node.js, browser: + +```bash +npm install markdown-it-mark --save +bower install markdown-it-mark --save +``` + +## Use + +```js +var md = require('markdown-it')() + .use(require('markdown-it-mark')); + +md.render('==marked==') // => '

    marked

    ' +``` + +_Differences in browser._ If you load script directly into the page, without +package system, module will add itself globally as `window.markdownitMark`. + + +## License + +[MIT](https://github.com/markdown-it/markdown-it-mark/blob/master/LICENSE) diff --git a/frontend/node_modules/markdown-it-mark/dist/index.cjs.js b/frontend/node_modules/markdown-it-mark/dist/index.cjs.js new file mode 100644 index 0000000..b9d6a29 --- /dev/null +++ b/frontend/node_modules/markdown-it-mark/dist/index.cjs.js @@ -0,0 +1,113 @@ +'use strict'; + +function ins_plugin(md) { + // Insert each marker as a separate text token, and add it to delimiter list + // + function tokenize(state, silent) { + const start = state.pos; + const marker = state.src.charCodeAt(start); + if (silent) { + return false; + } + if (marker !== 0x3D /* = */) { + return false; + } + const scanned = state.scanDelims(state.pos, true); + let len = scanned.length; + const ch = String.fromCharCode(marker); + if (len < 2) { + return false; + } + if (len % 2) { + const token = state.push('text', '', 0); + token.content = ch; + len--; + } + for (let i = 0; i < len; i += 2) { + const token = state.push('text', '', 0); + token.content = ch + ch; + if (!scanned.can_open && !scanned.can_close) { + continue; + } + state.delimiters.push({ + marker, + length: 0, + // disable "rule of 3" length checks meant for emphasis + jump: i / 2, + // 1 delimiter = 2 characters + token: state.tokens.length - 1, + end: -1, + open: scanned.can_open, + close: scanned.can_close + }); + } + state.pos += scanned.length; + return true; + } + + // Walk through delimiter list and replace text tokens with tags + // + function postProcess(state, delimiters) { + const loneMarkers = []; + const max = delimiters.length; + for (let i = 0; i < max; i++) { + const startDelim = delimiters[i]; + if (startDelim.marker !== 0x3D /* = */) { + continue; + } + if (startDelim.end === -1) { + continue; + } + const endDelim = delimiters[startDelim.end]; + const token_o = state.tokens[startDelim.token]; + token_o.type = 'mark_open'; + token_o.tag = 'mark'; + token_o.nesting = 1; + token_o.markup = '=='; + token_o.content = ''; + const token_c = state.tokens[endDelim.token]; + token_c.type = 'mark_close'; + token_c.tag = 'mark'; + token_c.nesting = -1; + token_c.markup = '=='; + token_c.content = ''; + if (state.tokens[endDelim.token - 1].type === 'text' && state.tokens[endDelim.token - 1].content === '=') { + loneMarkers.push(endDelim.token - 1); + } + } + + // If a marker sequence has an odd number of characters, it's splitted + // like this: `~~~~~` -> `~` + `~~` + `~~`, leaving one marker at the + // start of the sequence. + // + // So, we have to move all those markers after subsequent s_close tags. + // + while (loneMarkers.length) { + const i = loneMarkers.pop(); + let j = i + 1; + while (j < state.tokens.length && state.tokens[j].type === 'mark_close') { + j++; + } + j--; + if (i !== j) { + const token = state.tokens[j]; + state.tokens[j] = state.tokens[i]; + state.tokens[i] = token; + } + } + } + md.inline.ruler.before('emphasis', 'mark', tokenize); + md.inline.ruler2.before('emphasis', 'mark', function (state) { + let curr; + const tokens_meta = state.tokens_meta; + const max = (state.tokens_meta || []).length; + postProcess(state, state.delimiters); + for (curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + postProcess(state, tokens_meta[curr].delimiters); + } + } + }); +} + +module.exports = ins_plugin; diff --git a/frontend/node_modules/markdown-it-mark/dist/markdown-it-mark.js b/frontend/node_modules/markdown-it-mark/dist/markdown-it-mark.js new file mode 100644 index 0000000..62f920f --- /dev/null +++ b/frontend/node_modules/markdown-it-mark/dist/markdown-it-mark.js @@ -0,0 +1,114 @@ +/*! markdown-it-mark 4.0.0 https://github.com/markdown-it/markdown-it-mark @license MIT */ +(function(global, factory) { + typeof exports === "object" && typeof module !== "undefined" ? module.exports = factory() : typeof define === "function" && define.amd ? define(factory) : (global = typeof globalThis !== "undefined" ? globalThis : global || self, + global.markdownitMark = factory()); +})(this, (function() { + "use strict"; + function ins_plugin(md) { + // Insert each marker as a separate text token, and add it to delimiter list + function tokenize(state, silent) { + const start = state.pos; + const marker = state.src.charCodeAt(start); + if (silent) { + return false; + } + if (marker !== 61 /* = */) { + return false; + } + const scanned = state.scanDelims(state.pos, true); + let len = scanned.length; + const ch = String.fromCharCode(marker); + if (len < 2) { + return false; + } + if (len % 2) { + const token = state.push("text", "", 0); + token.content = ch; + len--; + } + for (let i = 0; i < len; i += 2) { + const token = state.push("text", "", 0); + token.content = ch + ch; + if (!scanned.can_open && !scanned.can_close) { + continue; + } + state.delimiters.push({ + marker: marker, + length: 0, + // disable "rule of 3" length checks meant for emphasis + jump: i / 2, + // 1 delimiter = 2 characters + token: state.tokens.length - 1, + end: -1, + open: scanned.can_open, + close: scanned.can_close + }); + } + state.pos += scanned.length; + return true; + } + // Walk through delimiter list and replace text tokens with tags + + function postProcess(state, delimiters) { + const loneMarkers = []; + const max = delimiters.length; + for (let i = 0; i < max; i++) { + const startDelim = delimiters[i]; + if (startDelim.marker !== 61 /* = */) { + continue; + } + if (startDelim.end === -1) { + continue; + } + const endDelim = delimiters[startDelim.end]; + const token_o = state.tokens[startDelim.token]; + token_o.type = "mark_open"; + token_o.tag = "mark"; + token_o.nesting = 1; + token_o.markup = "=="; + token_o.content = ""; + const token_c = state.tokens[endDelim.token]; + token_c.type = "mark_close"; + token_c.tag = "mark"; + token_c.nesting = -1; + token_c.markup = "=="; + token_c.content = ""; + if (state.tokens[endDelim.token - 1].type === "text" && state.tokens[endDelim.token - 1].content === "=") { + loneMarkers.push(endDelim.token - 1); + } + } + // If a marker sequence has an odd number of characters, it's splitted + // like this: `~~~~~` -> `~` + `~~` + `~~`, leaving one marker at the + // start of the sequence. + + // So, we have to move all those markers after subsequent s_close tags. + + while (loneMarkers.length) { + const i = loneMarkers.pop(); + let j = i + 1; + while (j < state.tokens.length && state.tokens[j].type === "mark_close") { + j++; + } + j--; + if (i !== j) { + const token = state.tokens[j]; + state.tokens[j] = state.tokens[i]; + state.tokens[i] = token; + } + } + } + md.inline.ruler.before("emphasis", "mark", tokenize); + md.inline.ruler2.before("emphasis", "mark", (function(state) { + let curr; + const tokens_meta = state.tokens_meta; + const max = (state.tokens_meta || []).length; + postProcess(state, state.delimiters); + for (curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + postProcess(state, tokens_meta[curr].delimiters); + } + } + })); + } + return ins_plugin; +})); diff --git a/frontend/node_modules/markdown-it-mark/dist/markdown-it-mark.min.js b/frontend/node_modules/markdown-it-mark/dist/markdown-it-mark.min.js new file mode 100644 index 0000000..dc768ef --- /dev/null +++ b/frontend/node_modules/markdown-it-mark/dist/markdown-it-mark.min.js @@ -0,0 +1,2 @@ +/*! markdown-it-mark 4.0.0 https://github.com/markdown-it/markdown-it-mark @license MIT */ +!function(e,n){"object"==typeof exports&&"undefined"!=typeof module?module.exports=n():"function"==typeof define&&define.amd?define(n):(e="undefined"!=typeof globalThis?globalThis:e||self).markdownitMark=n()}(this,(function(){"use strict";return function(e){function n(e,n){const t=[],o=n.length;for(let s=0;s `~` + `~~` + `~~`, leaving one marker at the + // start of the sequence. + // + // So, we have to move all those markers after subsequent s_close tags. + // + while (loneMarkers.length) { + const i = loneMarkers.pop() + let j = i + 1 + + while (j < state.tokens.length && state.tokens[j].type === 'mark_close') { + j++ + } + + j-- + + if (i !== j) { + const token = state.tokens[j] + state.tokens[j] = state.tokens[i] + state.tokens[i] = token + } + } + } + + md.inline.ruler.before('emphasis', 'mark', tokenize) + md.inline.ruler2.before('emphasis', 'mark', function (state) { + let curr + const tokens_meta = state.tokens_meta + const max = (state.tokens_meta || []).length + + postProcess(state, state.delimiters) + + for (curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + postProcess(state, tokens_meta[curr].delimiters) + } + } + }) +}; diff --git a/frontend/node_modules/markdown-it-mark/package.json b/frontend/node_modules/markdown-it-mark/package.json new file mode 100644 index 0000000..42e1ef1 --- /dev/null +++ b/frontend/node_modules/markdown-it-mark/package.json @@ -0,0 +1,48 @@ +{ + "name": "markdown-it-mark", + "version": "4.0.0", + "description": " tag for markdown-it markdown parser.", + "keywords": [ + "markdown-it-plugin", + "markdown-it", + "markdown", + "mark" + ], + "repository": "markdown-it/markdown-it-mark", + "license": "MIT", + "main": "dist/index.cjs.js", + "module": "index.mjs", + "exports": { + ".": { + "require": "./dist/index.cjs.js", + "import": "./index.mjs" + }, + "./*": { + "require": "./*", + "import": "./*" + } + }, + "files": [ + "index.mjs", + "lib/", + "dist/" + ], + "scripts": { + "lint": "eslint .", + "build": "rollup -c", + "test": "npm run lint && npm run build && c8 --exclude dist --exclude test -r text -r html -r lcov mocha", + "prepublishOnly": "npm run lint && npm run build" + }, + "devDependencies": { + "@rollup/plugin-babel": "^6.0.4", + "@rollup/plugin-node-resolve": "^15.2.3", + "@rollup/plugin-terser": "^0.4.4", + "c8": "^8.0.1", + "eslint": "^8.55.0", + "eslint-config-standard": "^17.1.0", + "markdown-it": "^13.0.2", + "markdown-it-testgen": "^0.1.6", + "mocha": "^10.2.0", + "rollup": "^4.6.1" + } +} diff --git a/frontend/node_modules/markdown-it-sub/LICENSE b/frontend/node_modules/markdown-it-sub/LICENSE new file mode 100644 index 0000000..2fd4e3d --- /dev/null +++ b/frontend/node_modules/markdown-it-sub/LICENSE @@ -0,0 +1,22 @@ +Copyright (c) 2014-2015 Vitaly Puzrin, Alex Kocharin. + +Permission is hereby granted, free of charge, to any person +obtaining a copy of this software and associated documentation +files (the "Software"), to deal in the Software without +restriction, including without limitation the rights to use, +copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the +Software is furnished to do so, subject to the following +conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES +OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT +HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +OTHER DEALINGS IN THE SOFTWARE. diff --git a/frontend/node_modules/markdown-it-sub/README.md b/frontend/node_modules/markdown-it-sub/README.md new file mode 100644 index 0000000..1dd760c --- /dev/null +++ b/frontend/node_modules/markdown-it-sub/README.md @@ -0,0 +1,40 @@ +# markdown-it-sub + +[![Build Status](https://img.shields.io/travis/markdown-it/markdown-it-sub/master.svg?style=flat)](https://travis-ci.org/markdown-it/markdown-it-sub) +[![NPM version](https://img.shields.io/npm/v/markdown-it-sub.svg?style=flat)](https://www.npmjs.org/package/markdown-it-sub) +[![Coverage Status](https://img.shields.io/coveralls/markdown-it/markdown-it-sub/master.svg?style=flat)](https://coveralls.io/r/markdown-it/markdown-it-sub?branch=master) + +> Subscript (``) tag plugin for [markdown-it](https://github.com/markdown-it/markdown-it) markdown parser. + +__v1.+ requires `markdown-it` v4.+, see changelog.__ + +`H~2~0` => `H2O` + +Markup is based on [pandoc](http://johnmacfarlane.net/pandoc/README.html#superscripts-and-subscripts) definition. But nested markup is currently not supported. + + +## Install + +node.js, browser: + +```bash +npm install markdown-it-sub --save +bower install markdown-it-sub --save +``` + +## Use + +```js +var md = require('markdown-it')() + .use(require('markdown-it-sub')); + +md.render('H~2~0') // => '

    H2O

    ' +``` + +_Differences in browser._ If you load script directly into the page, without +package system, module will add itself globally as `window.markdownitSub`. + + +## License + +[MIT](https://github.com/markdown-it/markdown-it-sub/blob/master/LICENSE) diff --git a/frontend/node_modules/markdown-it-sub/dist/index.cjs.js b/frontend/node_modules/markdown-it-sub/dist/index.cjs.js new file mode 100644 index 0000000..cdb8d85 --- /dev/null +++ b/frontend/node_modules/markdown-it-sub/dist/index.cjs.js @@ -0,0 +1,59 @@ +'use strict'; + +// Process ~subscript~ + +// same as UNESCAPE_MD_RE plus a space +const UNESCAPE_RE = /\\([ \\!"#$%&'()*+,./:;<=>?@[\]^_`{|}~-])/g; +function subscript(state, silent) { + const max = state.posMax; + const start = state.pos; + if (state.src.charCodeAt(start) !== 0x7E /* ~ */) { + return false; + } + if (silent) { + return false; + } // don't run any pairs in validation mode + if (start + 2 >= max) { + return false; + } + state.pos = start + 1; + let found = false; + while (state.pos < max) { + if (state.src.charCodeAt(state.pos) === 0x7E /* ~ */) { + found = true; + break; + } + state.md.inline.skipToken(state); + } + if (!found || start + 1 === state.pos) { + state.pos = start; + return false; + } + const content = state.src.slice(start + 1, state.pos); + + // don't allow unescaped spaces/newlines inside + if (content.match(/(^|[^\\])(\\\\)*\s/)) { + state.pos = start; + return false; + } + + // found! + state.posMax = state.pos; + state.pos = start + 1; + + // Earlier we checked !silent, but this implementation does not need it + const token_so = state.push('sub_open', 'sub', 1); + token_so.markup = '~'; + const token_t = state.push('text', '', 0); + token_t.content = content.replace(UNESCAPE_RE, '$1'); + const token_sc = state.push('sub_close', 'sub', -1); + token_sc.markup = '~'; + state.pos = state.posMax + 1; + state.posMax = max; + return true; +} +function sub_plugin(md) { + md.inline.ruler.after('emphasis', 'sub', subscript); +} + +module.exports = sub_plugin; diff --git a/frontend/node_modules/markdown-it-sub/dist/markdown-it-sub.js b/frontend/node_modules/markdown-it-sub/dist/markdown-it-sub.js new file mode 100644 index 0000000..3217251 --- /dev/null +++ b/frontend/node_modules/markdown-it-sub/dist/markdown-it-sub.js @@ -0,0 +1,60 @@ +/*! markdown-it-sub 2.0.0 https://github.com/markdown-it/markdown-it-sub @license MIT */ +(function(global, factory) { + typeof exports === "object" && typeof module !== "undefined" ? module.exports = factory() : typeof define === "function" && define.amd ? define(factory) : (global = typeof globalThis !== "undefined" ? globalThis : global || self, + global.markdownitSub = factory()); +})(this, (function() { + "use strict"; + // Process ~subscript~ + // same as UNESCAPE_MD_RE plus a space + const UNESCAPE_RE = /\\([ \\!"#$%&'()*+,./:;<=>?@[\]^_`{|}~-])/g; + function subscript(state, silent) { + const max = state.posMax; + const start = state.pos; + if (state.src.charCodeAt(start) !== 126 /* ~ */) { + return false; + } + if (silent) { + return false; + } + // don't run any pairs in validation mode + if (start + 2 >= max) { + return false; + } + state.pos = start + 1; + let found = false; + while (state.pos < max) { + if (state.src.charCodeAt(state.pos) === 126 /* ~ */) { + found = true; + break; + } + state.md.inline.skipToken(state); + } + if (!found || start + 1 === state.pos) { + state.pos = start; + return false; + } + const content = state.src.slice(start + 1, state.pos); + // don't allow unescaped spaces/newlines inside + if (content.match(/(^|[^\\])(\\\\)*\s/)) { + state.pos = start; + return false; + } + // found! + state.posMax = state.pos; + state.pos = start + 1; + // Earlier we checked !silent, but this implementation does not need it + const token_so = state.push("sub_open", "sub", 1); + token_so.markup = "~"; + const token_t = state.push("text", "", 0); + token_t.content = content.replace(UNESCAPE_RE, "$1"); + const token_sc = state.push("sub_close", "sub", -1); + token_sc.markup = "~"; + state.pos = state.posMax + 1; + state.posMax = max; + return true; + } + function sub_plugin(md) { + md.inline.ruler.after("emphasis", "sub", subscript); + } + return sub_plugin; +})); diff --git a/frontend/node_modules/markdown-it-sub/dist/markdown-it-sub.min.js b/frontend/node_modules/markdown-it-sub/dist/markdown-it-sub.min.js new file mode 100644 index 0000000..a8396da --- /dev/null +++ b/frontend/node_modules/markdown-it-sub/dist/markdown-it-sub.min.js @@ -0,0 +1,2 @@ +/*! markdown-it-sub 2.0.0 https://github.com/markdown-it/markdown-it-sub @license MIT */ +!function(e,s){"object"==typeof exports&&"undefined"!=typeof module?module.exports=s():"function"==typeof define&&define.amd?define(s):(e="undefined"!=typeof globalThis?globalThis:e||self).markdownitSub=s()}(this,(function(){"use strict";const e=/\\([ \\!"#$%&'()*+,./:;<=>?@[\]^_`{|}~-])/g;function s(s,o){const n=s.posMax,t=s.pos;if(126!==s.src.charCodeAt(t))return!1;if(o)return!1;if(t+2>=n)return!1;s.pos=t+1;let r=!1;for(;s.pos?@[\]^_`{|}~-])/g + +function subscript (state, silent) { + const max = state.posMax + const start = state.pos + + if (state.src.charCodeAt(start) !== 0x7E/* ~ */) { return false } + if (silent) { return false } // don't run any pairs in validation mode + if (start + 2 >= max) { return false } + + state.pos = start + 1 + let found = false + + while (state.pos < max) { + if (state.src.charCodeAt(state.pos) === 0x7E/* ~ */) { + found = true + break + } + + state.md.inline.skipToken(state) + } + + if (!found || start + 1 === state.pos) { + state.pos = start + return false + } + + const content = state.src.slice(start + 1, state.pos) + + // don't allow unescaped spaces/newlines inside + if (content.match(/(^|[^\\])(\\\\)*\s/)) { + state.pos = start + return false + } + + // found! + state.posMax = state.pos + state.pos = start + 1 + + // Earlier we checked !silent, but this implementation does not need it + const token_so = state.push('sub_open', 'sub', 1) + token_so.markup = '~' + + const token_t = state.push('text', '', 0) + token_t.content = content.replace(UNESCAPE_RE, '$1') + + const token_sc = state.push('sub_close', 'sub', -1) + token_sc.markup = '~' + + state.pos = state.posMax + 1 + state.posMax = max + return true +} + +export default function sub_plugin (md) { + md.inline.ruler.after('emphasis', 'sub', subscript) +}; diff --git a/frontend/node_modules/markdown-it-sub/package.json b/frontend/node_modules/markdown-it-sub/package.json new file mode 100644 index 0000000..73a7f14 --- /dev/null +++ b/frontend/node_modules/markdown-it-sub/package.json @@ -0,0 +1,49 @@ +{ + "name": "markdown-it-sub", + "version": "2.0.0", + "description": " tag for markdown-it markdown parser.", + "keywords": [ + "markdown-it-plugin", + "markdown-it", + "markdown", + "subscript", + "sub" + ], + "repository": "markdown-it/markdown-it-sub", + "license": "MIT", + "main": "dist/index.cjs.js", + "module": "index.mjs", + "exports": { + ".": { + "require": "./dist/index.cjs.js", + "import": "./index.mjs" + }, + "./*": { + "require": "./*", + "import": "./*" + } + }, + "files": [ + "index.mjs", + "lib/", + "dist/" + ], + "scripts": { + "lint": "eslint .", + "build": "rollup -c", + "test": "npm run lint && npm run build && c8 --exclude dist --exclude test -r text -r html -r lcov mocha", + "prepublishOnly": "npm run lint && npm run build" + }, + "devDependencies": { + "@rollup/plugin-babel": "^6.0.4", + "@rollup/plugin-node-resolve": "^15.2.3", + "@rollup/plugin-terser": "^0.4.4", + "c8": "^8.0.1", + "eslint": "^8.55.0", + "eslint-config-standard": "^17.1.0", + "markdown-it": "^13.0.2", + "markdown-it-testgen": "^0.1.6", + "mocha": "^10.2.0", + "rollup": "^4.6.1" + } +} diff --git a/frontend/node_modules/markdown-it-sup/LICENSE b/frontend/node_modules/markdown-it-sup/LICENSE new file mode 100644 index 0000000..2fd4e3d --- /dev/null +++ b/frontend/node_modules/markdown-it-sup/LICENSE @@ -0,0 +1,22 @@ +Copyright (c) 2014-2015 Vitaly Puzrin, Alex Kocharin. + +Permission is hereby granted, free of charge, to any person +obtaining a copy of this software and associated documentation +files (the "Software"), to deal in the Software without +restriction, including without limitation the rights to use, +copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the +Software is furnished to do so, subject to the following +conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES +OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT +HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +OTHER DEALINGS IN THE SOFTWARE. diff --git a/frontend/node_modules/markdown-it-sup/README.md b/frontend/node_modules/markdown-it-sup/README.md new file mode 100644 index 0000000..c0ef3c1 --- /dev/null +++ b/frontend/node_modules/markdown-it-sup/README.md @@ -0,0 +1,40 @@ +# markdown-it-sup + +[![CI](https://github.com/markdown-it/markdown-it-sup/actions/workflows/ci.yml/badge.svg)](https://github.com/markdown-it/markdown-it-sup/actions/workflows/ci.yml) +[![NPM version](https://img.shields.io/npm/v/markdown-it-sup.svg?style=flat)](https://www.npmjs.org/package/markdown-it-sup) +[![Coverage Status](https://img.shields.io/coveralls/markdown-it/markdown-it-sup/master.svg?style=flat)](https://coveralls.io/r/markdown-it/markdown-it-sup?branch=master) + +> Superscript (``) tag plugin for [markdown-it](https://github.com/markdown-it/markdown-it) markdown parser. + +__v1.+ requires `markdown-it` v4.+, see changelog.__ + +`29^th^` => `29th` + +Markup is based on [pandoc](http://johnmacfarlane.net/pandoc/README.html#superscripts-and-subscripts) definition. But nested markup is currently not supported. + + +## Install + +node.js, browser: + +```bash +npm install markdown-it-sup --save +bower install markdown-it-sup --save +``` + +## Use + +```js +var md = require('markdown-it')() + .use(require('markdown-it-sup')); + +md.render('29^th^') // => '

    29th

    ' +``` + +_Differences in browser._ If you load script directly into the page, without +package system, module will add itself globally as `window.markdownitSup`. + + +## License + +[MIT](https://github.com/markdown-it/markdown-it-sup/blob/master/LICENSE) diff --git a/frontend/node_modules/markdown-it-sup/dist/index.cjs.js b/frontend/node_modules/markdown-it-sup/dist/index.cjs.js new file mode 100644 index 0000000..a7b424f --- /dev/null +++ b/frontend/node_modules/markdown-it-sup/dist/index.cjs.js @@ -0,0 +1,59 @@ +'use strict'; + +// Process ^superscript^ + +// same as UNESCAPE_MD_RE plus a space +const UNESCAPE_RE = /\\([ \\!"#$%&'()*+,./:;<=>?@[\]^_`{|}~-])/g; +function superscript(state, silent) { + const max = state.posMax; + const start = state.pos; + if (state.src.charCodeAt(start) !== 0x5E /* ^ */) { + return false; + } + if (silent) { + return false; + } // don't run any pairs in validation mode + if (start + 2 >= max) { + return false; + } + state.pos = start + 1; + let found = false; + while (state.pos < max) { + if (state.src.charCodeAt(state.pos) === 0x5E /* ^ */) { + found = true; + break; + } + state.md.inline.skipToken(state); + } + if (!found || start + 1 === state.pos) { + state.pos = start; + return false; + } + const content = state.src.slice(start + 1, state.pos); + + // don't allow unescaped spaces/newlines inside + if (content.match(/(^|[^\\])(\\\\)*\s/)) { + state.pos = start; + return false; + } + + // found! + state.posMax = state.pos; + state.pos = start + 1; + + // Earlier we checked !silent, but this implementation does not need it + const token_so = state.push('sup_open', 'sup', 1); + token_so.markup = '^'; + const token_t = state.push('text', '', 0); + token_t.content = content.replace(UNESCAPE_RE, '$1'); + const token_sc = state.push('sup_close', 'sup', -1); + token_sc.markup = '^'; + state.pos = state.posMax + 1; + state.posMax = max; + return true; +} +function sup_plugin(md) { + md.inline.ruler.after('emphasis', 'sup', superscript); +} + +module.exports = sup_plugin; diff --git a/frontend/node_modules/markdown-it-sup/dist/markdown-it-sup.js b/frontend/node_modules/markdown-it-sup/dist/markdown-it-sup.js new file mode 100644 index 0000000..2e18aa0 --- /dev/null +++ b/frontend/node_modules/markdown-it-sup/dist/markdown-it-sup.js @@ -0,0 +1,60 @@ +/*! markdown-it-sup 2.0.0 https://github.com/markdown-it/markdown-it-sup @license MIT */ +(function(global, factory) { + typeof exports === "object" && typeof module !== "undefined" ? module.exports = factory() : typeof define === "function" && define.amd ? define(factory) : (global = typeof globalThis !== "undefined" ? globalThis : global || self, + global.markdownitSup = factory()); +})(this, (function() { + "use strict"; + // Process ^superscript^ + // same as UNESCAPE_MD_RE plus a space + const UNESCAPE_RE = /\\([ \\!"#$%&'()*+,./:;<=>?@[\]^_`{|}~-])/g; + function superscript(state, silent) { + const max = state.posMax; + const start = state.pos; + if (state.src.charCodeAt(start) !== 94 /* ^ */) { + return false; + } + if (silent) { + return false; + } + // don't run any pairs in validation mode + if (start + 2 >= max) { + return false; + } + state.pos = start + 1; + let found = false; + while (state.pos < max) { + if (state.src.charCodeAt(state.pos) === 94 /* ^ */) { + found = true; + break; + } + state.md.inline.skipToken(state); + } + if (!found || start + 1 === state.pos) { + state.pos = start; + return false; + } + const content = state.src.slice(start + 1, state.pos); + // don't allow unescaped spaces/newlines inside + if (content.match(/(^|[^\\])(\\\\)*\s/)) { + state.pos = start; + return false; + } + // found! + state.posMax = state.pos; + state.pos = start + 1; + // Earlier we checked !silent, but this implementation does not need it + const token_so = state.push("sup_open", "sup", 1); + token_so.markup = "^"; + const token_t = state.push("text", "", 0); + token_t.content = content.replace(UNESCAPE_RE, "$1"); + const token_sc = state.push("sup_close", "sup", -1); + token_sc.markup = "^"; + state.pos = state.posMax + 1; + state.posMax = max; + return true; + } + function sup_plugin(md) { + md.inline.ruler.after("emphasis", "sup", superscript); + } + return sup_plugin; +})); diff --git a/frontend/node_modules/markdown-it-sup/dist/markdown-it-sup.min.js b/frontend/node_modules/markdown-it-sup/dist/markdown-it-sup.min.js new file mode 100644 index 0000000..604b7a8 --- /dev/null +++ b/frontend/node_modules/markdown-it-sup/dist/markdown-it-sup.min.js @@ -0,0 +1,2 @@ +/*! markdown-it-sup 2.0.0 https://github.com/markdown-it/markdown-it-sup @license MIT */ +!function(e,s){"object"==typeof exports&&"undefined"!=typeof module?module.exports=s():"function"==typeof define&&define.amd?define(s):(e="undefined"!=typeof globalThis?globalThis:e||self).markdownitSup=s()}(this,(function(){"use strict";const e=/\\([ \\!"#$%&'()*+,./:;<=>?@[\]^_`{|}~-])/g;function s(s,o){const n=s.posMax,p=s.pos;if(94!==s.src.charCodeAt(p))return!1;if(o)return!1;if(p+2>=n)return!1;s.pos=p+1;let t=!1;for(;s.pos?@[\]^_`{|}~-])/g + +function superscript (state, silent) { + const max = state.posMax + const start = state.pos + + if (state.src.charCodeAt(start) !== 0x5E/* ^ */) { return false } + if (silent) { return false } // don't run any pairs in validation mode + if (start + 2 >= max) { return false } + + state.pos = start + 1 + let found = false + + while (state.pos < max) { + if (state.src.charCodeAt(state.pos) === 0x5E/* ^ */) { + found = true + break + } + + state.md.inline.skipToken(state) + } + + if (!found || start + 1 === state.pos) { + state.pos = start + return false + } + + const content = state.src.slice(start + 1, state.pos) + + // don't allow unescaped spaces/newlines inside + if (content.match(/(^|[^\\])(\\\\)*\s/)) { + state.pos = start + return false + } + + // found! + state.posMax = state.pos + state.pos = start + 1 + + // Earlier we checked !silent, but this implementation does not need it + const token_so = state.push('sup_open', 'sup', 1) + token_so.markup = '^' + + const token_t = state.push('text', '', 0) + token_t.content = content.replace(UNESCAPE_RE, '$1') + + const token_sc = state.push('sup_close', 'sup', -1) + token_sc.markup = '^' + + state.pos = state.posMax + 1 + state.posMax = max + return true +} + +export default function sup_plugin (md) { + md.inline.ruler.after('emphasis', 'sup', superscript) +}; diff --git a/frontend/node_modules/markdown-it-sup/package.json b/frontend/node_modules/markdown-it-sup/package.json new file mode 100644 index 0000000..63a6474 --- /dev/null +++ b/frontend/node_modules/markdown-it-sup/package.json @@ -0,0 +1,49 @@ +{ + "name": "markdown-it-sup", + "version": "2.0.0", + "description": " tag for markdown-it markdown parser.", + "keywords": [ + "markdown-it-plugin", + "markdown-it", + "markdown", + "superscript", + "sup" + ], + "repository": "markdown-it/markdown-it-sup", + "license": "MIT", + "main": "dist/index.cjs.js", + "module": "index.mjs", + "exports": { + ".": { + "require": "./dist/index.cjs.js", + "import": "./index.mjs" + }, + "./*": { + "require": "./*", + "import": "./*" + } + }, + "files": [ + "index.mjs", + "lib/", + "dist/" + ], + "scripts": { + "lint": "eslint .", + "build": "rollup -c", + "test": "npm run lint && npm run build && c8 --exclude dist --exclude test -r text -r html -r lcov mocha", + "prepublishOnly": "npm run lint && npm run build" + }, + "devDependencies": { + "@rollup/plugin-babel": "^6.0.4", + "@rollup/plugin-node-resolve": "^15.2.3", + "@rollup/plugin-terser": "^0.4.4", + "c8": "^8.0.1", + "eslint": "^8.55.0", + "eslint-config-standard": "^17.1.0", + "markdown-it": "^13.0.2", + "markdown-it-testgen": "^0.1.6", + "mocha": "^10.2.0", + "rollup": "^4.6.1" + } +} diff --git a/frontend/node_modules/markdown-it/LICENSE b/frontend/node_modules/markdown-it/LICENSE new file mode 100644 index 0000000..7ffa058 --- /dev/null +++ b/frontend/node_modules/markdown-it/LICENSE @@ -0,0 +1,22 @@ +Copyright (c) 2014 Vitaly Puzrin, Alex Kocharin. + +Permission is hereby granted, free of charge, to any person +obtaining a copy of this software and associated documentation +files (the "Software"), to deal in the Software without +restriction, including without limitation the rights to use, +copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the +Software is furnished to do so, subject to the following +conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES +OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT +HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +OTHER DEALINGS IN THE SOFTWARE. diff --git a/frontend/node_modules/markdown-it/README.md b/frontend/node_modules/markdown-it/README.md new file mode 100644 index 0000000..6c79f3c --- /dev/null +++ b/frontend/node_modules/markdown-it/README.md @@ -0,0 +1,324 @@ +# markdown-it + +[![CI](https://github.com/markdown-it/markdown-it/actions/workflows/ci.yml/badge.svg)](https://github.com/markdown-it/markdown-it/actions/workflows/ci.yml) +[![NPM version](https://img.shields.io/npm/v/markdown-it.svg?style=flat)](https://www.npmjs.org/package/markdown-it) +[![Coverage Status](https://coveralls.io/repos/markdown-it/markdown-it/badge.svg?branch=master&service=github)](https://coveralls.io/github/markdown-it/markdown-it?branch=master) +[![Gitter](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/markdown-it/markdown-it) + +> Markdown parser done right. Fast and easy to extend. + +__[Live demo](https://markdown-it.github.io)__ + +- Follows the __[CommonMark spec](http://spec.commonmark.org/)__ + adds syntax extensions & sugar (URL autolinking, typographer). +- Configurable syntax! You can add new rules and even replace existing ones. +- High speed. +- [Safe](https://github.com/markdown-it/markdown-it/tree/master/docs/security.md) by default. +- Community-written __[plugins](https://www.npmjs.org/browse/keyword/markdown-it-plugin)__ and [other packages](https://www.npmjs.org/browse/keyword/markdown-it) on npm. + +__Table of content__ + +- [Install](#install) +- [Usage examples](#usage-examples) + - [Simple](#simple) + - [Init with presets and options](#init-with-presets-and-options) + - [Plugins load](#plugins-load) + - [Syntax highlighting](#syntax-highlighting) + - [Linkify](#linkify) +- [API](#api) +- [Syntax extensions](#syntax-extensions) + - [Manage rules](#manage-rules) +- [Benchmark](#benchmark) +- [markdown-it for enterprise](#markdown-it-for-enterprise) +- [Authors](#authors) +- [References / Thanks](#references--thanks) + +## Install + +**node.js**: + +```bash +npm install markdown-it +``` + +**browser (CDN):** + +- [jsDeliver CDN](http://www.jsdelivr.com/#!markdown-it "jsDelivr CDN") +- [cdnjs.com CDN](https://cdnjs.com/libraries/markdown-it "cdnjs.com") + + +## Usage examples + +See also: + +- __[API documentation](https://markdown-it.github.io/markdown-it/)__ - for more + info and examples. +- [Development info](https://github.com/markdown-it/markdown-it/tree/master/docs) - + for plugins writers. + + +### Simple + +```js +// node.js +// can use `require('markdown-it')` for CJS +import markdownit from 'markdown-it' +const md = markdownit() +const result = md.render('# markdown-it rulezz!'); + +// browser with UMD build, added to "window" on script load +// Note, there is no dash in "markdownit". +const md = window.markdownit(); +const result = md.render('# markdown-it rulezz!'); +``` + +Single line rendering, without paragraph wrap: + +```js +import markdownit from 'markdown-it' +const md = markdownit() +const result = md.renderInline('__markdown-it__ rulezz!'); +``` + + +### Init with presets and options + +(*) presets define combinations of active rules and options. Can be +`"commonmark"`, `"zero"` or `"default"` (if skipped). See +[API docs](https://markdown-it.github.io/markdown-it/#MarkdownIt.new) for more details. + +```js +import markdownit from 'markdown-it' + +// commonmark mode +const md = markdownit('commonmark') + +// default mode +const md = markdownit() + +// enable everything +const md = markdownit({ + html: true, + linkify: true, + typographer: true +}) + +// full options list (defaults) +const md = markdownit({ + // Enable HTML tags in source + html: false, + + // Use '/' to close single tags (
    ). + // This is only for full CommonMark compatibility. + xhtmlOut: false, + + // Convert '\n' in paragraphs into
    + breaks: false, + + // CSS language prefix for fenced blocks. Can be + // useful for external highlighters. + langPrefix: 'language-', + + // Autoconvert URL-like text to links + linkify: false, + + // Enable some language-neutral replacement + quotes beautification + // For the full list of replacements, see https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/replacements.mjs + typographer: false, + + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: '“”‘’', + + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externally. + // If result starts with ` or ``): + +```js +import markdownit from 'markdown-it' +import hljs from 'highlight.js' // https://highlightjs.org + +// Actual default values +const md = markdownit({ + highlight: function (str, lang) { + if (lang && hljs.getLanguage(lang)) { + try { + return '
    ' +
    +               hljs.highlight(str, { language: lang, ignoreIllegals: true }).value +
    +               '
    '; + } catch (__) {} + } + + return '
    ' + md.utils.escapeHtml(str) + '
    '; + } +}); +``` + +### Linkify + +`linkify: true` uses [linkify-it](https://github.com/markdown-it/linkify-it). To +configure linkify-it, access the linkify instance through `md.linkify`: + +```js +md.linkify.set({ fuzzyEmail: false }); // disables converting email to link +``` + + +## API + +__[API documentation](https://markdown-it.github.io/markdown-it/)__ + +If you are going to write plugins, please take a look at +[Development info](https://github.com/markdown-it/markdown-it/tree/master/docs). + + +## Syntax extensions + +Embedded (enabled by default): + +- [Tables](https://help.github.com/articles/organizing-information-with-tables/) (GFM) +- [Strikethrough](https://help.github.com/articles/basic-writing-and-formatting-syntax/#styling-text) (GFM) + +Via plugins: + +- [subscript](https://github.com/markdown-it/markdown-it-sub) +- [superscript](https://github.com/markdown-it/markdown-it-sup) +- [footnote](https://github.com/markdown-it/markdown-it-footnote) +- [definition list](https://github.com/markdown-it/markdown-it-deflist) +- [abbreviation](https://github.com/markdown-it/markdown-it-abbr) +- [emoji](https://github.com/markdown-it/markdown-it-emoji) +- [custom container](https://github.com/markdown-it/markdown-it-container) +- [insert](https://github.com/markdown-it/markdown-it-ins) +- [mark](https://github.com/markdown-it/markdown-it-mark) +- ... and [others](https://www.npmjs.org/browse/keyword/markdown-it-plugin) + + +### Manage rules + +By default all rules are enabled, but can be restricted by options. On plugin +load all its rules are enabled automatically. + +```js +import markdownit from 'markdown-it' + +// Activate/deactivate rules, with currying +const md = markdownit() + .disable(['link', 'image']) + .enable(['link']) + .enable('image'); + +// Enable everything +const md = markdownit({ + html: true, + linkify: true, + typographer: true, +}); +``` + +You can find all rules in sources: + +- [`parser_core.mjs`](lib/parser_core.mjs) +- [`parser_block.mjs`](lib/parser_block.mjs) +- [`parser_inline.mjs`](lib/parser_inline.mjs) + + +## Benchmark + +Here is the result of readme parse at MB Pro Retina 2013 (2.4 GHz): + +```bash +npm run benchmark-deps +benchmark/benchmark.mjs readme + +Selected samples: (1 of 28) + > README + +Sample: README.md (7774 bytes) + > commonmark-reference x 1,222 ops/sec ±0.96% (97 runs sampled) + > current x 743 ops/sec ±0.84% (97 runs sampled) + > current-commonmark x 1,568 ops/sec ±0.84% (98 runs sampled) + > marked x 1,587 ops/sec ±4.31% (93 runs sampled) +``` + +__Note.__ CommonMark version runs with [simplified link normalizers](https://github.com/markdown-it/markdown-it/blob/master/benchmark/implementations/current-commonmark/index.mjs) +for more "honest" compare. Difference is ≈1.5×. + +As you can see, `markdown-it` doesn't pay with speed for its flexibility. +Slowdown of "full" version caused by additional features not available in +other implementations. + + +## markdown-it for enterprise + +Available as part of the Tidelift Subscription. + +The maintainers of `markdown-it` and thousands of other packages are working with Tidelift to deliver commercial support and maintenance for the open source dependencies you use to build your applications. Save time, reduce risk, and improve code health, while paying the maintainers of the exact dependencies you use. [Learn more.](https://tidelift.com/subscription/pkg/npm-markdown-it?utm_source=npm-markdown-it&utm_medium=referral&utm_campaign=enterprise&utm_term=repo) + + +## Authors + +- Alex Kocharin [github/rlidwka](https://github.com/rlidwka) +- Vitaly Puzrin [github/puzrin](https://github.com/puzrin) + +_markdown-it_ is the result of the decision of the authors who contributed to +99% of the _Remarkable_ code to move to a project with the same authorship but +new leadership (Vitaly and Alex). It's not a fork. + +## References / Thanks + +Big thanks to [John MacFarlane](https://github.com/jgm) for his work on the +CommonMark spec and reference implementations. His work saved us a lot of time +during this project's development. + +**Related Links:** + +- https://github.com/jgm/CommonMark - reference CommonMark implementations in C & JS, + also contains latest spec & online demo. +- http://talk.commonmark.org - CommonMark forum, good place to collaborate + developers' efforts. + +**Ports** + +- [motion-markdown-it](https://github.com/digitalmoksha/motion-markdown-it) - Ruby/RubyMotion +- [markdown-it-py](https://github.com/ExecutableBookProject/markdown-it-py)- Python diff --git a/frontend/node_modules/markdown-it/bin/markdown-it.mjs b/frontend/node_modules/markdown-it/bin/markdown-it.mjs new file mode 100755 index 0000000..84626f1 --- /dev/null +++ b/frontend/node_modules/markdown-it/bin/markdown-it.mjs @@ -0,0 +1,107 @@ +#!/usr/bin/env node +/* eslint no-console:0 */ + +import fs from 'node:fs' +import argparse from 'argparse' +import markdownit from '../index.mjs' + +const cli = new argparse.ArgumentParser({ + prog: 'markdown-it', + add_help: true +}) + +cli.add_argument('-v', '--version', { + action: 'version', + version: JSON.parse(fs.readFileSync(new URL('../package.json', import.meta.url))).version +}) + +cli.add_argument('--no-html', { + help: 'Disable embedded HTML', + action: 'store_true' +}) + +cli.add_argument('-l', '--linkify', { + help: 'Autolink text', + action: 'store_true' +}) + +cli.add_argument('-t', '--typographer', { + help: 'Enable smartquotes and other typographic replacements', + action: 'store_true' +}) + +cli.add_argument('--trace', { + help: 'Show stack trace on error', + action: 'store_true' +}) + +cli.add_argument('file', { + help: 'File to read', + nargs: '?', + default: '-' +}) + +cli.add_argument('-o', '--output', { + help: 'File to write', + default: '-' +}) + +const options = cli.parse_args() + +function readFile (filename, encoding, callback) { + if (options.file === '-') { + // read from stdin + const chunks = [] + + process.stdin.on('data', function (chunk) { chunks.push(chunk) }) + + process.stdin.on('end', function () { + return callback(null, Buffer.concat(chunks).toString(encoding)) + }) + } else { + fs.readFile(filename, encoding, callback) + } +} + +readFile(options.file, 'utf8', function (err, input) { + let output + + if (err) { + if (err.code === 'ENOENT') { + console.error('File not found: ' + options.file) + process.exit(2) + } + + console.error( + (options.trace && err.stack) || + err.message || + String(err)) + + process.exit(1) + } + + const md = markdownit({ + html: !options.no_html, + xhtmlOut: false, + typographer: options.typographer, + linkify: options.linkify + }) + + try { + output = md.render(input) + } catch (e) { + console.error( + (options.trace && e.stack) || + e.message || + String(e)) + + process.exit(1) + } + + if (options.output === '-') { + // write to stdout + process.stdout.write(output) + } else { + fs.writeFileSync(options.output, output) + } +}) diff --git a/frontend/node_modules/markdown-it/dist/index.cjs.js b/frontend/node_modules/markdown-it/dist/index.cjs.js new file mode 100644 index 0000000..5ba2eaa --- /dev/null +++ b/frontend/node_modules/markdown-it/dist/index.cjs.js @@ -0,0 +1,5540 @@ +'use strict'; + +var mdurl = require('mdurl'); +var ucmicro = require('uc.micro'); +var entities = require('entities'); +var LinkifyIt = require('linkify-it'); +var punycode = require('punycode.js'); + +function _interopNamespaceDefault(e) { + var n = Object.create(null); + if (e) { + Object.keys(e).forEach(function (k) { + if (k !== 'default') { + var d = Object.getOwnPropertyDescriptor(e, k); + Object.defineProperty(n, k, d.get ? d : { + enumerable: true, + get: function () { return e[k]; } + }); + } + }); + } + n.default = e; + return Object.freeze(n); +} + +var mdurl__namespace = /*#__PURE__*/_interopNamespaceDefault(mdurl); +var ucmicro__namespace = /*#__PURE__*/_interopNamespaceDefault(ucmicro); + +// Utilities +// + +function _class(obj) { + return Object.prototype.toString.call(obj); +} +function isString(obj) { + return _class(obj) === '[object String]'; +} +const _hasOwnProperty = Object.prototype.hasOwnProperty; +function has(object, key) { + return _hasOwnProperty.call(object, key); +} + +// Merge objects +// +function assign(obj /* from1, from2, from3, ... */) { + const sources = Array.prototype.slice.call(arguments, 1); + sources.forEach(function (source) { + if (!source) { + return; + } + if (typeof source !== 'object') { + throw new TypeError(source + 'must be object'); + } + Object.keys(source).forEach(function (key) { + obj[key] = source[key]; + }); + }); + return obj; +} + +// Remove element from array and put another array at those position. +// Useful for some operations with tokens +function arrayReplaceAt(src, pos, newElements) { + return [].concat(src.slice(0, pos), newElements, src.slice(pos + 1)); +} +function isValidEntityCode(c) { + /* eslint no-bitwise:0 */ + // broken sequence + if (c >= 0xD800 && c <= 0xDFFF) { + return false; + } + // never used + if (c >= 0xFDD0 && c <= 0xFDEF) { + return false; + } + if ((c & 0xFFFF) === 0xFFFF || (c & 0xFFFF) === 0xFFFE) { + return false; + } + // control codes + if (c >= 0x00 && c <= 0x08) { + return false; + } + if (c === 0x0B) { + return false; + } + if (c >= 0x0E && c <= 0x1F) { + return false; + } + if (c >= 0x7F && c <= 0x9F) { + return false; + } + // out of range + if (c > 0x10FFFF) { + return false; + } + return true; +} +function fromCodePoint(c) { + /* eslint no-bitwise:0 */ + if (c > 0xffff) { + c -= 0x10000; + const surrogate1 = 0xd800 + (c >> 10); + const surrogate2 = 0xdc00 + (c & 0x3ff); + return String.fromCharCode(surrogate1, surrogate2); + } + return String.fromCharCode(c); +} +const UNESCAPE_MD_RE = /\\([!"#$%&'()*+,\-./:;<=>?@[\\\]^_`{|}~])/g; +const ENTITY_RE = /&([a-z#][a-z0-9]{1,31});/gi; +const UNESCAPE_ALL_RE = new RegExp(UNESCAPE_MD_RE.source + '|' + ENTITY_RE.source, 'gi'); +const DIGITAL_ENTITY_TEST_RE = /^#((?:x[a-f0-9]{1,8}|[0-9]{1,8}))$/i; +function replaceEntityPattern(match, name) { + if (name.charCodeAt(0) === 0x23 /* # */ && DIGITAL_ENTITY_TEST_RE.test(name)) { + const code = name[1].toLowerCase() === 'x' ? parseInt(name.slice(2), 16) : parseInt(name.slice(1), 10); + if (isValidEntityCode(code)) { + return fromCodePoint(code); + } + return match; + } + const decoded = entities.decodeHTML(match); + if (decoded !== match) { + return decoded; + } + return match; +} + +/* function replaceEntities(str) { + if (str.indexOf('&') < 0) { return str; } + + return str.replace(ENTITY_RE, replaceEntityPattern); +} */ + +function unescapeMd(str) { + if (str.indexOf('\\') < 0) { + return str; + } + return str.replace(UNESCAPE_MD_RE, '$1'); +} +function unescapeAll(str) { + if (str.indexOf('\\') < 0 && str.indexOf('&') < 0) { + return str; + } + return str.replace(UNESCAPE_ALL_RE, function (match, escaped, entity) { + if (escaped) { + return escaped; + } + return replaceEntityPattern(match, entity); + }); +} +const HTML_ESCAPE_TEST_RE = /[&<>"]/; +const HTML_ESCAPE_REPLACE_RE = /[&<>"]/g; +const HTML_REPLACEMENTS = { + '&': '&', + '<': '<', + '>': '>', + '"': '"' +}; +function replaceUnsafeChar(ch) { + return HTML_REPLACEMENTS[ch]; +} +function escapeHtml(str) { + if (HTML_ESCAPE_TEST_RE.test(str)) { + return str.replace(HTML_ESCAPE_REPLACE_RE, replaceUnsafeChar); + } + return str; +} +const REGEXP_ESCAPE_RE = /[.?*+^$[\]\\(){}|-]/g; +function escapeRE(str) { + return str.replace(REGEXP_ESCAPE_RE, '\\$&'); +} +function isSpace(code) { + switch (code) { + case 0x09: + case 0x20: + return true; + } + return false; +} + +// Zs (unicode class) || [\t\f\v\r\n] +function isWhiteSpace(code) { + if (code >= 0x2000 && code <= 0x200A) { + return true; + } + switch (code) { + case 0x09: // \t + case 0x0A: // \n + case 0x0B: // \v + case 0x0C: // \f + case 0x0D: // \r + case 0x20: + case 0xA0: + case 0x1680: + case 0x202F: + case 0x205F: + case 0x3000: + return true; + } + return false; +} + +/* eslint-disable max-len */ + +// Currently without astral characters support. +function isPunctChar(ch) { + return ucmicro__namespace.P.test(ch) || ucmicro__namespace.S.test(ch); +} + +// Markdown ASCII punctuation characters. +// +// !, ", #, $, %, &, ', (, ), *, +, ,, -, ., /, :, ;, <, =, >, ?, @, [, \, ], ^, _, `, {, |, }, or ~ +// http://spec.commonmark.org/0.15/#ascii-punctuation-character +// +// Don't confuse with unicode punctuation !!! It lacks some chars in ascii range. +// +function isMdAsciiPunct(ch) { + switch (ch) { + case 0x21 /* ! */: + case 0x22 /* " */: + case 0x23 /* # */: + case 0x24 /* $ */: + case 0x25 /* % */: + case 0x26 /* & */: + case 0x27 /* ' */: + case 0x28 /* ( */: + case 0x29 /* ) */: + case 0x2A /* * */: + case 0x2B /* + */: + case 0x2C /* , */: + case 0x2D /* - */: + case 0x2E /* . */: + case 0x2F /* / */: + case 0x3A /* : */: + case 0x3B /* ; */: + case 0x3C /* < */: + case 0x3D /* = */: + case 0x3E /* > */: + case 0x3F /* ? */: + case 0x40 /* @ */: + case 0x5B /* [ */: + case 0x5C /* \ */: + case 0x5D /* ] */: + case 0x5E /* ^ */: + case 0x5F /* _ */: + case 0x60 /* ` */: + case 0x7B /* { */: + case 0x7C /* | */: + case 0x7D /* } */: + case 0x7E /* ~ */: + return true; + default: + return false; + } +} + +// Hepler to unify [reference labels]. +// +function normalizeReference(str) { + // Trim and collapse whitespace + // + str = str.trim().replace(/\s+/g, ' '); + + // In node v10 'ẞ'.toLowerCase() === 'Ṿ', which is presumed to be a bug + // fixed in v12 (couldn't find any details). + // + // So treat this one as a special case + // (remove this when node v10 is no longer supported). + // + if ('ẞ'.toLowerCase() === 'Ṿ') { + str = str.replace(/ẞ/g, 'ß'); + } + + // .toLowerCase().toUpperCase() should get rid of all differences + // between letter variants. + // + // Simple .toLowerCase() doesn't normalize 125 code points correctly, + // and .toUpperCase doesn't normalize 6 of them (list of exceptions: + // İ, ϴ, ẞ, Ω, K, Å - those are already uppercased, but have differently + // uppercased versions). + // + // Here's an example showing how it happens. Lets take greek letter omega: + // uppercase U+0398 (Θ), U+03f4 (ϴ) and lowercase U+03b8 (θ), U+03d1 (ϑ) + // + // Unicode entries: + // 0398;GREEK CAPITAL LETTER THETA;Lu;0;L;;;;;N;;;;03B8; + // 03B8;GREEK SMALL LETTER THETA;Ll;0;L;;;;;N;;;0398;;0398 + // 03D1;GREEK THETA SYMBOL;Ll;0;L; 03B8;;;;N;GREEK SMALL LETTER SCRIPT THETA;;0398;;0398 + // 03F4;GREEK CAPITAL THETA SYMBOL;Lu;0;L; 0398;;;;N;;;;03B8; + // + // Case-insensitive comparison should treat all of them as equivalent. + // + // But .toLowerCase() doesn't change ϑ (it's already lowercase), + // and .toUpperCase() doesn't change ϴ (already uppercase). + // + // Applying first lower then upper case normalizes any character: + // '\u0398\u03f4\u03b8\u03d1'.toLowerCase().toUpperCase() === '\u0398\u0398\u0398\u0398' + // + // Note: this is equivalent to unicode case folding; unicode normalization + // is a different step that is not required here. + // + // Final result should be uppercased, because it's later stored in an object + // (this avoid a conflict with Object.prototype members, + // most notably, `__proto__`) + // + return str.toLowerCase().toUpperCase(); +} + +// Re-export libraries commonly used in both markdown-it and its plugins, +// so plugins won't have to depend on them explicitly, which reduces their +// bundled size (e.g. a browser build). +// +const lib = { + mdurl: mdurl__namespace, + ucmicro: ucmicro__namespace +}; + +var utils = /*#__PURE__*/Object.freeze({ + __proto__: null, + arrayReplaceAt: arrayReplaceAt, + assign: assign, + escapeHtml: escapeHtml, + escapeRE: escapeRE, + fromCodePoint: fromCodePoint, + has: has, + isMdAsciiPunct: isMdAsciiPunct, + isPunctChar: isPunctChar, + isSpace: isSpace, + isString: isString, + isValidEntityCode: isValidEntityCode, + isWhiteSpace: isWhiteSpace, + lib: lib, + normalizeReference: normalizeReference, + unescapeAll: unescapeAll, + unescapeMd: unescapeMd +}); + +// Parse link label +// +// this function assumes that first character ("[") already matches; +// returns the end of the label +// + +function parseLinkLabel(state, start, disableNested) { + let level, found, marker, prevPos; + const max = state.posMax; + const oldPos = state.pos; + state.pos = start + 1; + level = 1; + while (state.pos < max) { + marker = state.src.charCodeAt(state.pos); + if (marker === 0x5D /* ] */) { + level--; + if (level === 0) { + found = true; + break; + } + } + prevPos = state.pos; + state.md.inline.skipToken(state); + if (marker === 0x5B /* [ */) { + if (prevPos === state.pos - 1) { + // increase level if we find text `[`, which is not a part of any token + level++; + } else if (disableNested) { + state.pos = oldPos; + return -1; + } + } + } + let labelEnd = -1; + if (found) { + labelEnd = state.pos; + } + + // restore old state + state.pos = oldPos; + return labelEnd; +} + +// Parse link destination +// + +function parseLinkDestination(str, start, max) { + let code; + let pos = start; + const result = { + ok: false, + pos: 0, + str: '' + }; + if (str.charCodeAt(pos) === 0x3C /* < */) { + pos++; + while (pos < max) { + code = str.charCodeAt(pos); + if (code === 0x0A /* \n */) { + return result; + } + if (code === 0x3C /* < */) { + return result; + } + if (code === 0x3E /* > */) { + result.pos = pos + 1; + result.str = unescapeAll(str.slice(start + 1, pos)); + result.ok = true; + return result; + } + if (code === 0x5C /* \ */ && pos + 1 < max) { + pos += 2; + continue; + } + pos++; + } + + // no closing '>' + return result; + } + + // this should be ... } else { ... branch + + let level = 0; + while (pos < max) { + code = str.charCodeAt(pos); + if (code === 0x20) { + break; + } + + // ascii control characters + if (code < 0x20 || code === 0x7F) { + break; + } + if (code === 0x5C /* \ */ && pos + 1 < max) { + if (str.charCodeAt(pos + 1) === 0x20) { + break; + } + pos += 2; + continue; + } + if (code === 0x28 /* ( */) { + level++; + if (level > 32) { + return result; + } + } + if (code === 0x29 /* ) */) { + if (level === 0) { + break; + } + level--; + } + pos++; + } + if (start === pos) { + return result; + } + if (level !== 0) { + return result; + } + result.str = unescapeAll(str.slice(start, pos)); + result.pos = pos; + result.ok = true; + return result; +} + +// Parse link title +// + + +// Parse link title within `str` in [start, max] range, +// or continue previous parsing if `prev_state` is defined (equal to result of last execution). +// +function parseLinkTitle(str, start, max, prev_state) { + let code; + let pos = start; + const state = { + // if `true`, this is a valid link title + ok: false, + // if `true`, this link can be continued on the next line + can_continue: false, + // if `ok`, it's the position of the first character after the closing marker + pos: 0, + // if `ok`, it's the unescaped title + str: '', + // expected closing marker character code + marker: 0 + }; + if (prev_state) { + // this is a continuation of a previous parseLinkTitle call on the next line, + // used in reference links only + state.str = prev_state.str; + state.marker = prev_state.marker; + } else { + if (pos >= max) { + return state; + } + let marker = str.charCodeAt(pos); + if (marker !== 0x22 /* " */ && marker !== 0x27 /* ' */ && marker !== 0x28 /* ( */) { + return state; + } + start++; + pos++; + + // if opening marker is "(", switch it to closing marker ")" + if (marker === 0x28) { + marker = 0x29; + } + state.marker = marker; + } + while (pos < max) { + code = str.charCodeAt(pos); + if (code === state.marker) { + state.pos = pos + 1; + state.str += unescapeAll(str.slice(start, pos)); + state.ok = true; + return state; + } else if (code === 0x28 /* ( */ && state.marker === 0x29 /* ) */) { + return state; + } else if (code === 0x5C /* \ */ && pos + 1 < max) { + pos++; + } + pos++; + } + + // no closing marker found, but this link title may continue on the next line (for references) + state.can_continue = true; + state.str += unescapeAll(str.slice(start, pos)); + return state; +} + +// Just a shortcut for bulk export + +var helpers = /*#__PURE__*/Object.freeze({ + __proto__: null, + parseLinkDestination: parseLinkDestination, + parseLinkLabel: parseLinkLabel, + parseLinkTitle: parseLinkTitle +}); + +/** + * class Renderer + * + * Generates HTML from parsed token stream. Each instance has independent + * copy of rules. Those can be rewritten with ease. Also, you can add new + * rules if you create plugin and adds new token types. + **/ + +const default_rules = {}; +default_rules.code_inline = function (tokens, idx, options, env, slf) { + const token = tokens[idx]; + return '' + escapeHtml(token.content) + '
    '; +}; +default_rules.code_block = function (tokens, idx, options, env, slf) { + const token = tokens[idx]; + return '' + escapeHtml(tokens[idx].content) + '\n'; +}; +default_rules.fence = function (tokens, idx, options, env, slf) { + const token = tokens[idx]; + const info = token.info ? unescapeAll(token.info).trim() : ''; + let langName = ''; + let langAttrs = ''; + if (info) { + const arr = info.split(/(\s+)/g); + langName = arr[0]; + langAttrs = arr.slice(2).join(''); + } + let highlighted; + if (options.highlight) { + highlighted = options.highlight(token.content, langName, langAttrs) || escapeHtml(token.content); + } else { + highlighted = escapeHtml(token.content); + } + if (highlighted.indexOf('${highlighted}\n`; + } + return `
    ${highlighted}
    \n`; +}; +default_rules.image = function (tokens, idx, options, env, slf) { + const token = tokens[idx]; + + // "alt" attr MUST be set, even if empty. Because it's mandatory and + // should be placed on proper position for tests. + // + // Replace content with actual value + + token.attrs[token.attrIndex('alt')][1] = slf.renderInlineAsText(token.children, options, env); + return slf.renderToken(tokens, idx, options); +}; +default_rules.hardbreak = function (tokens, idx, options /*, env */) { + return options.xhtmlOut ? '
    \n' : '
    \n'; +}; +default_rules.softbreak = function (tokens, idx, options /*, env */) { + return options.breaks ? options.xhtmlOut ? '
    \n' : '
    \n' : '\n'; +}; +default_rules.text = function (tokens, idx /*, options, env */) { + return escapeHtml(tokens[idx].content); +}; +default_rules.html_block = function (tokens, idx /*, options, env */) { + return tokens[idx].content; +}; +default_rules.html_inline = function (tokens, idx /*, options, env */) { + return tokens[idx].content; +}; + +/** + * new Renderer() + * + * Creates new [[Renderer]] instance and fill [[Renderer#rules]] with defaults. + **/ +function Renderer() { + /** + * Renderer#rules -> Object + * + * Contains render rules for tokens. Can be updated and extended. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.renderer.rules.strong_open = function () { return ''; }; + * md.renderer.rules.strong_close = function () { return ''; }; + * + * var result = md.renderInline(...); + * ``` + * + * Each rule is called as independent static function with fixed signature: + * + * ```javascript + * function my_token_render(tokens, idx, options, env, renderer) { + * // ... + * return renderedHTML; + * } + * ``` + * + * See [source code](https://github.com/markdown-it/markdown-it/blob/master/lib/renderer.mjs) + * for more details and examples. + **/ + this.rules = assign({}, default_rules); +} + +/** + * Renderer.renderAttrs(token) -> String + * + * Render token attributes to string. + **/ +Renderer.prototype.renderAttrs = function renderAttrs(token) { + let i, l, result; + if (!token.attrs) { + return ''; + } + result = ''; + for (i = 0, l = token.attrs.length; i < l; i++) { + result += ' ' + escapeHtml(token.attrs[i][0]) + '="' + escapeHtml(token.attrs[i][1]) + '"'; + } + return result; +}; + +/** + * Renderer.renderToken(tokens, idx, options) -> String + * - tokens (Array): list of tokens + * - idx (Numbed): token index to render + * - options (Object): params of parser instance + * + * Default token renderer. Can be overriden by custom function + * in [[Renderer#rules]]. + **/ +Renderer.prototype.renderToken = function renderToken(tokens, idx, options) { + const token = tokens[idx]; + let result = ''; + + // Tight list paragraphs + if (token.hidden) { + return ''; + } + + // Insert a newline between hidden paragraph and subsequent opening + // block-level tag. + // + // For example, here we should insert a newline before blockquote: + // - a + // > + // + if (token.block && token.nesting !== -1 && idx && tokens[idx - 1].hidden) { + result += '\n'; + } + + // Add token name, e.g. ``. + // + needLf = false; + } + } + } + } + result += needLf ? '>\n' : '>'; + return result; +}; + +/** + * Renderer.renderInline(tokens, options, env) -> String + * - tokens (Array): list on block tokens to render + * - options (Object): params of parser instance + * - env (Object): additional data from parsed input (references, for example) + * + * The same as [[Renderer.render]], but for single token of `inline` type. + **/ +Renderer.prototype.renderInline = function (tokens, options, env) { + let result = ''; + const rules = this.rules; + for (let i = 0, len = tokens.length; i < len; i++) { + const type = tokens[i].type; + if (typeof rules[type] !== 'undefined') { + result += rules[type](tokens, i, options, env, this); + } else { + result += this.renderToken(tokens, i, options); + } + } + return result; +}; + +/** internal + * Renderer.renderInlineAsText(tokens, options, env) -> String + * - tokens (Array): list on block tokens to render + * - options (Object): params of parser instance + * - env (Object): additional data from parsed input (references, for example) + * + * Special kludge for image `alt` attributes to conform CommonMark spec. + * Don't try to use it! Spec requires to show `alt` content with stripped markup, + * instead of simple escaping. + **/ +Renderer.prototype.renderInlineAsText = function (tokens, options, env) { + let result = ''; + for (let i = 0, len = tokens.length; i < len; i++) { + switch (tokens[i].type) { + case 'text': + result += tokens[i].content; + break; + case 'image': + result += this.renderInlineAsText(tokens[i].children, options, env); + break; + case 'html_inline': + case 'html_block': + result += tokens[i].content; + break; + case 'softbreak': + case 'hardbreak': + result += '\n'; + break; + // all other tokens are skipped + } + } + return result; +}; + +/** + * Renderer.render(tokens, options, env) -> String + * - tokens (Array): list on block tokens to render + * - options (Object): params of parser instance + * - env (Object): additional data from parsed input (references, for example) + * + * Takes token stream and generates HTML. Probably, you will never need to call + * this method directly. + **/ +Renderer.prototype.render = function (tokens, options, env) { + let result = ''; + const rules = this.rules; + for (let i = 0, len = tokens.length; i < len; i++) { + const type = tokens[i].type; + if (type === 'inline') { + result += this.renderInline(tokens[i].children, options, env); + } else if (typeof rules[type] !== 'undefined') { + result += rules[type](tokens, i, options, env, this); + } else { + result += this.renderToken(tokens, i, options, env); + } + } + return result; +}; + +/** + * class Ruler + * + * Helper class, used by [[MarkdownIt#core]], [[MarkdownIt#block]] and + * [[MarkdownIt#inline]] to manage sequences of functions (rules): + * + * - keep rules in defined order + * - assign the name to each rule + * - enable/disable rules + * - add/replace rules + * - allow assign rules to additional named chains (in the same) + * - cacheing lists of active rules + * + * You will not need use this class directly until write plugins. For simple + * rules control use [[MarkdownIt.disable]], [[MarkdownIt.enable]] and + * [[MarkdownIt.use]]. + **/ + +/** + * new Ruler() + **/ +function Ruler() { + // List of added rules. Each element is: + // + // { + // name: XXX, + // enabled: Boolean, + // fn: Function(), + // alt: [ name2, name3 ] + // } + // + this.__rules__ = []; + + // Cached rule chains. + // + // First level - chain name, '' for default. + // Second level - diginal anchor for fast filtering by charcodes. + // + this.__cache__ = null; +} + +// Helper methods, should not be used directly + +// Find rule index by name +// +Ruler.prototype.__find__ = function (name) { + for (let i = 0; i < this.__rules__.length; i++) { + if (this.__rules__[i].name === name) { + return i; + } + } + return -1; +}; + +// Build rules lookup cache +// +Ruler.prototype.__compile__ = function () { + const self = this; + const chains = ['']; + + // collect unique names + self.__rules__.forEach(function (rule) { + if (!rule.enabled) { + return; + } + rule.alt.forEach(function (altName) { + if (chains.indexOf(altName) < 0) { + chains.push(altName); + } + }); + }); + self.__cache__ = {}; + chains.forEach(function (chain) { + self.__cache__[chain] = []; + self.__rules__.forEach(function (rule) { + if (!rule.enabled) { + return; + } + if (chain && rule.alt.indexOf(chain) < 0) { + return; + } + self.__cache__[chain].push(rule.fn); + }); + }); +}; + +/** + * Ruler.at(name, fn [, options]) + * - name (String): rule name to replace. + * - fn (Function): new rule function. + * - options (Object): new rule options (not mandatory). + * + * Replace rule by name with new function & options. Throws error if name not + * found. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * Replace existing typographer replacement rule with new one: + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.core.ruler.at('replacements', function replace(state) { + * //... + * }); + * ``` + **/ +Ruler.prototype.at = function (name, fn, options) { + const index = this.__find__(name); + const opt = options || {}; + if (index === -1) { + throw new Error('Parser rule not found: ' + name); + } + this.__rules__[index].fn = fn; + this.__rules__[index].alt = opt.alt || []; + this.__cache__ = null; +}; + +/** + * Ruler.before(beforeName, ruleName, fn [, options]) + * - beforeName (String): new rule will be added before this one. + * - ruleName (String): name of added rule. + * - fn (Function): rule function. + * - options (Object): rule options (not mandatory). + * + * Add new rule to chain before one with given name. See also + * [[Ruler.after]], [[Ruler.push]]. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.block.ruler.before('paragraph', 'my_rule', function replace(state) { + * //... + * }); + * ``` + **/ +Ruler.prototype.before = function (beforeName, ruleName, fn, options) { + const index = this.__find__(beforeName); + const opt = options || {}; + if (index === -1) { + throw new Error('Parser rule not found: ' + beforeName); + } + this.__rules__.splice(index, 0, { + name: ruleName, + enabled: true, + fn, + alt: opt.alt || [] + }); + this.__cache__ = null; +}; + +/** + * Ruler.after(afterName, ruleName, fn [, options]) + * - afterName (String): new rule will be added after this one. + * - ruleName (String): name of added rule. + * - fn (Function): rule function. + * - options (Object): rule options (not mandatory). + * + * Add new rule to chain after one with given name. See also + * [[Ruler.before]], [[Ruler.push]]. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.inline.ruler.after('text', 'my_rule', function replace(state) { + * //... + * }); + * ``` + **/ +Ruler.prototype.after = function (afterName, ruleName, fn, options) { + const index = this.__find__(afterName); + const opt = options || {}; + if (index === -1) { + throw new Error('Parser rule not found: ' + afterName); + } + this.__rules__.splice(index + 1, 0, { + name: ruleName, + enabled: true, + fn, + alt: opt.alt || [] + }); + this.__cache__ = null; +}; + +/** + * Ruler.push(ruleName, fn [, options]) + * - ruleName (String): name of added rule. + * - fn (Function): rule function. + * - options (Object): rule options (not mandatory). + * + * Push new rule to the end of chain. See also + * [[Ruler.before]], [[Ruler.after]]. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.core.ruler.push('my_rule', function replace(state) { + * //... + * }); + * ``` + **/ +Ruler.prototype.push = function (ruleName, fn, options) { + const opt = options || {}; + this.__rules__.push({ + name: ruleName, + enabled: true, + fn, + alt: opt.alt || [] + }); + this.__cache__ = null; +}; + +/** + * Ruler.enable(list [, ignoreInvalid]) -> Array + * - list (String|Array): list of rule names to enable. + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Enable rules with given names. If any rule name not found - throw Error. + * Errors can be disabled by second param. + * + * Returns list of found rule names (if no exception happened). + * + * See also [[Ruler.disable]], [[Ruler.enableOnly]]. + **/ +Ruler.prototype.enable = function (list, ignoreInvalid) { + if (!Array.isArray(list)) { + list = [list]; + } + const result = []; + + // Search by name and enable + list.forEach(function (name) { + const idx = this.__find__(name); + if (idx < 0) { + if (ignoreInvalid) { + return; + } + throw new Error('Rules manager: invalid rule name ' + name); + } + this.__rules__[idx].enabled = true; + result.push(name); + }, this); + this.__cache__ = null; + return result; +}; + +/** + * Ruler.enableOnly(list [, ignoreInvalid]) + * - list (String|Array): list of rule names to enable (whitelist). + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Enable rules with given names, and disable everything else. If any rule name + * not found - throw Error. Errors can be disabled by second param. + * + * See also [[Ruler.disable]], [[Ruler.enable]]. + **/ +Ruler.prototype.enableOnly = function (list, ignoreInvalid) { + if (!Array.isArray(list)) { + list = [list]; + } + this.__rules__.forEach(function (rule) { + rule.enabled = false; + }); + this.enable(list, ignoreInvalid); +}; + +/** + * Ruler.disable(list [, ignoreInvalid]) -> Array + * - list (String|Array): list of rule names to disable. + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Disable rules with given names. If any rule name not found - throw Error. + * Errors can be disabled by second param. + * + * Returns list of found rule names (if no exception happened). + * + * See also [[Ruler.enable]], [[Ruler.enableOnly]]. + **/ +Ruler.prototype.disable = function (list, ignoreInvalid) { + if (!Array.isArray(list)) { + list = [list]; + } + const result = []; + + // Search by name and disable + list.forEach(function (name) { + const idx = this.__find__(name); + if (idx < 0) { + if (ignoreInvalid) { + return; + } + throw new Error('Rules manager: invalid rule name ' + name); + } + this.__rules__[idx].enabled = false; + result.push(name); + }, this); + this.__cache__ = null; + return result; +}; + +/** + * Ruler.getRules(chainName) -> Array + * + * Return array of active functions (rules) for given chain name. It analyzes + * rules configuration, compiles caches if not exists and returns result. + * + * Default chain name is `''` (empty string). It can't be skipped. That's + * done intentionally, to keep signature monomorphic for high speed. + **/ +Ruler.prototype.getRules = function (chainName) { + if (this.__cache__ === null) { + this.__compile__(); + } + + // Chain can be empty, if rules disabled. But we still have to return Array. + return this.__cache__[chainName] || []; +}; + +// Token class + +/** + * class Token + **/ + +/** + * new Token(type, tag, nesting) + * + * Create new token and fill passed properties. + **/ +function Token(type, tag, nesting) { + /** + * Token#type -> String + * + * Type of the token (string, e.g. "paragraph_open") + **/ + this.type = type; + + /** + * Token#tag -> String + * + * html tag name, e.g. "p" + **/ + this.tag = tag; + + /** + * Token#attrs -> Array + * + * Html attributes. Format: `[ [ name1, value1 ], [ name2, value2 ] ]` + **/ + this.attrs = null; + + /** + * Token#map -> Array + * + * Source map info. Format: `[ line_begin, line_end ]` + **/ + this.map = null; + + /** + * Token#nesting -> Number + * + * Level change (number in {-1, 0, 1} set), where: + * + * - `1` means the tag is opening + * - `0` means the tag is self-closing + * - `-1` means the tag is closing + **/ + this.nesting = nesting; + + /** + * Token#level -> Number + * + * nesting level, the same as `state.level` + **/ + this.level = 0; + + /** + * Token#children -> Array + * + * An array of child nodes (inline and img tokens) + **/ + this.children = null; + + /** + * Token#content -> String + * + * In a case of self-closing tag (code, html, fence, etc.), + * it has contents of this tag. + **/ + this.content = ''; + + /** + * Token#markup -> String + * + * '*' or '_' for emphasis, fence string for fence, etc. + **/ + this.markup = ''; + + /** + * Token#info -> String + * + * Additional information: + * + * - Info string for "fence" tokens + * - The value "auto" for autolink "link_open" and "link_close" tokens + * - The string value of the item marker for ordered-list "list_item_open" tokens + **/ + this.info = ''; + + /** + * Token#meta -> Object + * + * A place for plugins to store an arbitrary data + **/ + this.meta = null; + + /** + * Token#block -> Boolean + * + * True for block-level tokens, false for inline tokens. + * Used in renderer to calculate line breaks + **/ + this.block = false; + + /** + * Token#hidden -> Boolean + * + * If it's true, ignore this element when rendering. Used for tight lists + * to hide paragraphs. + **/ + this.hidden = false; +} + +/** + * Token.attrIndex(name) -> Number + * + * Search attribute index by name. + **/ +Token.prototype.attrIndex = function attrIndex(name) { + if (!this.attrs) { + return -1; + } + const attrs = this.attrs; + for (let i = 0, len = attrs.length; i < len; i++) { + if (attrs[i][0] === name) { + return i; + } + } + return -1; +}; + +/** + * Token.attrPush(attrData) + * + * Add `[ name, value ]` attribute to list. Init attrs if necessary + **/ +Token.prototype.attrPush = function attrPush(attrData) { + if (this.attrs) { + this.attrs.push(attrData); + } else { + this.attrs = [attrData]; + } +}; + +/** + * Token.attrSet(name, value) + * + * Set `name` attribute to `value`. Override old value if exists. + **/ +Token.prototype.attrSet = function attrSet(name, value) { + const idx = this.attrIndex(name); + const attrData = [name, value]; + if (idx < 0) { + this.attrPush(attrData); + } else { + this.attrs[idx] = attrData; + } +}; + +/** + * Token.attrGet(name) + * + * Get the value of attribute `name`, or null if it does not exist. + **/ +Token.prototype.attrGet = function attrGet(name) { + const idx = this.attrIndex(name); + let value = null; + if (idx >= 0) { + value = this.attrs[idx][1]; + } + return value; +}; + +/** + * Token.attrJoin(name, value) + * + * Join value to existing attribute via space. Or create new attribute if not + * exists. Useful to operate with token classes. + **/ +Token.prototype.attrJoin = function attrJoin(name, value) { + const idx = this.attrIndex(name); + if (idx < 0) { + this.attrPush([name, value]); + } else { + this.attrs[idx][1] = this.attrs[idx][1] + ' ' + value; + } +}; + +// Core state object +// + +function StateCore(src, md, env) { + this.src = src; + this.env = env; + this.tokens = []; + this.inlineMode = false; + this.md = md; // link to parser instance +} + +// re-export Token class to use in core rules +StateCore.prototype.Token = Token; + +// Normalize input string + +// https://spec.commonmark.org/0.29/#line-ending +const NEWLINES_RE = /\r\n?|\n/g; +const NULL_RE = /\0/g; +function normalize(state) { + let str; + + // Normalize newlines + str = state.src.replace(NEWLINES_RE, '\n'); + + // Replace NULL characters + str = str.replace(NULL_RE, '\uFFFD'); + state.src = str; +} + +function block(state) { + let token; + if (state.inlineMode) { + token = new state.Token('inline', '', 0); + token.content = state.src; + token.map = [0, 1]; + token.children = []; + state.tokens.push(token); + } else { + state.md.block.parse(state.src, state.md, state.env, state.tokens); + } +} + +function inline(state) { + const tokens = state.tokens; + + // Parse inlines + for (let i = 0, l = tokens.length; i < l; i++) { + const tok = tokens[i]; + if (tok.type === 'inline') { + state.md.inline.parse(tok.content, state.md, state.env, tok.children); + } + } +} + +// Replace link-like texts with link nodes. +// +// Currently restricted by `md.validateLink()` to http/https/ftp +// + +function isLinkOpen$1(str) { + return /^\s]/i.test(str); +} +function isLinkClose$1(str) { + return /^<\/a\s*>/i.test(str); +} +function linkify$1(state) { + const blockTokens = state.tokens; + if (!state.md.options.linkify) { + return; + } + for (let j = 0, l = blockTokens.length; j < l; j++) { + if (blockTokens[j].type !== 'inline' || !state.md.linkify.pretest(blockTokens[j].content)) { + continue; + } + let tokens = blockTokens[j].children; + let htmlLinkLevel = 0; + + // We scan from the end, to keep position when new tags added. + // Use reversed logic in links start/end match + for (let i = tokens.length - 1; i >= 0; i--) { + const currentToken = tokens[i]; + + // Skip content of markdown links + if (currentToken.type === 'link_close') { + i--; + while (tokens[i].level !== currentToken.level && tokens[i].type !== 'link_open') { + i--; + } + continue; + } + + // Skip content of html tag links + if (currentToken.type === 'html_inline') { + if (isLinkOpen$1(currentToken.content) && htmlLinkLevel > 0) { + htmlLinkLevel--; + } + if (isLinkClose$1(currentToken.content)) { + htmlLinkLevel++; + } + } + if (htmlLinkLevel > 0) { + continue; + } + if (currentToken.type === 'text' && state.md.linkify.test(currentToken.content)) { + const text = currentToken.content; + let links = state.md.linkify.match(text); + + // Now split string to nodes + const nodes = []; + let level = currentToken.level; + let lastPos = 0; + + // forbid escape sequence at the start of the string, + // this avoids http\://example.com/ from being linkified as + // http://example.com/ + if (links.length > 0 && links[0].index === 0 && i > 0 && tokens[i - 1].type === 'text_special') { + links = links.slice(1); + } + for (let ln = 0; ln < links.length; ln++) { + const url = links[ln].url; + const fullUrl = state.md.normalizeLink(url); + if (!state.md.validateLink(fullUrl)) { + continue; + } + let urlText = links[ln].text; + + // Linkifier might send raw hostnames like "example.com", where url + // starts with domain name. So we prepend http:// in those cases, + // and remove it afterwards. + // + if (!links[ln].schema) { + urlText = state.md.normalizeLinkText('http://' + urlText).replace(/^http:\/\//, ''); + } else if (links[ln].schema === 'mailto:' && !/^mailto:/i.test(urlText)) { + urlText = state.md.normalizeLinkText('mailto:' + urlText).replace(/^mailto:/, ''); + } else { + urlText = state.md.normalizeLinkText(urlText); + } + const pos = links[ln].index; + if (pos > lastPos) { + const token = new state.Token('text', '', 0); + token.content = text.slice(lastPos, pos); + token.level = level; + nodes.push(token); + } + const token_o = new state.Token('link_open', 'a', 1); + token_o.attrs = [['href', fullUrl]]; + token_o.level = level++; + token_o.markup = 'linkify'; + token_o.info = 'auto'; + nodes.push(token_o); + const token_t = new state.Token('text', '', 0); + token_t.content = urlText; + token_t.level = level; + nodes.push(token_t); + const token_c = new state.Token('link_close', 'a', -1); + token_c.level = --level; + token_c.markup = 'linkify'; + token_c.info = 'auto'; + nodes.push(token_c); + lastPos = links[ln].lastIndex; + } + if (lastPos < text.length) { + const token = new state.Token('text', '', 0); + token.content = text.slice(lastPos); + token.level = level; + nodes.push(token); + } + + // replace current node + blockTokens[j].children = tokens = arrayReplaceAt(tokens, i, nodes); + } + } + } +} + +// Simple typographic replacements +// +// (c) (C) → © +// (tm) (TM) → ™ +// (r) (R) → ® +// +- → ± +// ... → … (also ?.... → ?.., !.... → !..) +// ???????? → ???, !!!!! → !!!, `,,` → `,` +// -- → –, --- → — +// + +// TODO: +// - fractionals 1/2, 1/4, 3/4 -> ½, ¼, ¾ +// - multiplications 2 x 4 -> 2 × 4 + +const RARE_RE = /\+-|\.\.|\?\?\?\?|!!!!|,,|--/; + +// Workaround for phantomjs - need regex without /g flag, +// or root check will fail every second time +const SCOPED_ABBR_TEST_RE = /\((c|tm|r)\)/i; +const SCOPED_ABBR_RE = /\((c|tm|r)\)/ig; +const SCOPED_ABBR = { + c: '©', + r: '®', + tm: '™' +}; +function replaceFn(match, name) { + return SCOPED_ABBR[name.toLowerCase()]; +} +function replace_scoped(inlineTokens) { + let inside_autolink = 0; + for (let i = inlineTokens.length - 1; i >= 0; i--) { + const token = inlineTokens[i]; + if (token.type === 'text' && !inside_autolink) { + token.content = token.content.replace(SCOPED_ABBR_RE, replaceFn); + } + if (token.type === 'link_open' && token.info === 'auto') { + inside_autolink--; + } + if (token.type === 'link_close' && token.info === 'auto') { + inside_autolink++; + } + } +} +function replace_rare(inlineTokens) { + let inside_autolink = 0; + for (let i = inlineTokens.length - 1; i >= 0; i--) { + const token = inlineTokens[i]; + if (token.type === 'text' && !inside_autolink) { + if (RARE_RE.test(token.content)) { + token.content = token.content.replace(/\+-/g, '±') + // .., ..., ....... -> … + // but ?..... & !..... -> ?.. & !.. + .replace(/\.{2,}/g, '…').replace(/([?!])…/g, '$1..').replace(/([?!]){4,}/g, '$1$1$1').replace(/,{2,}/g, ',') + // em-dash + .replace(/(^|[^-])---(?=[^-]|$)/mg, '$1\u2014') + // en-dash + .replace(/(^|\s)--(?=\s|$)/mg, '$1\u2013').replace(/(^|[^-\s])--(?=[^-\s]|$)/mg, '$1\u2013'); + } + } + if (token.type === 'link_open' && token.info === 'auto') { + inside_autolink--; + } + if (token.type === 'link_close' && token.info === 'auto') { + inside_autolink++; + } + } +} +function replace(state) { + let blkIdx; + if (!state.md.options.typographer) { + return; + } + for (blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) { + if (state.tokens[blkIdx].type !== 'inline') { + continue; + } + if (SCOPED_ABBR_TEST_RE.test(state.tokens[blkIdx].content)) { + replace_scoped(state.tokens[blkIdx].children); + } + if (RARE_RE.test(state.tokens[blkIdx].content)) { + replace_rare(state.tokens[blkIdx].children); + } + } +} + +// Convert straight quotation marks to typographic ones +// + +const QUOTE_TEST_RE = /['"]/; +const QUOTE_RE = /['"]/g; +const APOSTROPHE = '\u2019'; /* ’ */ + +function replaceAt(str, index, ch) { + return str.slice(0, index) + ch + str.slice(index + 1); +} +function process_inlines(tokens, state) { + let j; + const stack = []; + for (let i = 0; i < tokens.length; i++) { + const token = tokens[i]; + const thisLevel = tokens[i].level; + for (j = stack.length - 1; j >= 0; j--) { + if (stack[j].level <= thisLevel) { + break; + } + } + stack.length = j + 1; + if (token.type !== 'text') { + continue; + } + let text = token.content; + let pos = 0; + let max = text.length; + + /* eslint no-labels:0,block-scoped-var:0 */ + OUTER: while (pos < max) { + QUOTE_RE.lastIndex = pos; + const t = QUOTE_RE.exec(text); + if (!t) { + break; + } + let canOpen = true; + let canClose = true; + pos = t.index + 1; + const isSingle = t[0] === "'"; + + // Find previous character, + // default to space if it's the beginning of the line + // + let lastChar = 0x20; + if (t.index - 1 >= 0) { + lastChar = text.charCodeAt(t.index - 1); + } else { + for (j = i - 1; j >= 0; j--) { + if (tokens[j].type === 'softbreak' || tokens[j].type === 'hardbreak') break; // lastChar defaults to 0x20 + if (!tokens[j].content) continue; // should skip all tokens except 'text', 'html_inline' or 'code_inline' + + lastChar = tokens[j].content.charCodeAt(tokens[j].content.length - 1); + break; + } + } + + // Find next character, + // default to space if it's the end of the line + // + let nextChar = 0x20; + if (pos < max) { + nextChar = text.charCodeAt(pos); + } else { + for (j = i + 1; j < tokens.length; j++) { + if (tokens[j].type === 'softbreak' || tokens[j].type === 'hardbreak') break; // nextChar defaults to 0x20 + if (!tokens[j].content) continue; // should skip all tokens except 'text', 'html_inline' or 'code_inline' + + nextChar = tokens[j].content.charCodeAt(0); + break; + } + } + const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar)); + const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar)); + const isLastWhiteSpace = isWhiteSpace(lastChar); + const isNextWhiteSpace = isWhiteSpace(nextChar); + if (isNextWhiteSpace) { + canOpen = false; + } else if (isNextPunctChar) { + if (!(isLastWhiteSpace || isLastPunctChar)) { + canOpen = false; + } + } + if (isLastWhiteSpace) { + canClose = false; + } else if (isLastPunctChar) { + if (!(isNextWhiteSpace || isNextPunctChar)) { + canClose = false; + } + } + if (nextChar === 0x22 /* " */ && t[0] === '"') { + if (lastChar >= 0x30 /* 0 */ && lastChar <= 0x39 /* 9 */) { + // special case: 1"" - count first quote as an inch + canClose = canOpen = false; + } + } + if (canOpen && canClose) { + // Replace quotes in the middle of punctuation sequence, but not + // in the middle of the words, i.e.: + // + // 1. foo " bar " baz - not replaced + // 2. foo-"-bar-"-baz - replaced + // 3. foo"bar"baz - not replaced + // + canOpen = isLastPunctChar; + canClose = isNextPunctChar; + } + if (!canOpen && !canClose) { + // middle of word + if (isSingle) { + token.content = replaceAt(token.content, t.index, APOSTROPHE); + } + continue; + } + if (canClose) { + // this could be a closing quote, rewind the stack to get a match + for (j = stack.length - 1; j >= 0; j--) { + let item = stack[j]; + if (stack[j].level < thisLevel) { + break; + } + if (item.single === isSingle && stack[j].level === thisLevel) { + item = stack[j]; + let openQuote; + let closeQuote; + if (isSingle) { + openQuote = state.md.options.quotes[2]; + closeQuote = state.md.options.quotes[3]; + } else { + openQuote = state.md.options.quotes[0]; + closeQuote = state.md.options.quotes[1]; + } + + // replace token.content *before* tokens[item.token].content, + // because, if they are pointing at the same token, replaceAt + // could mess up indices when quote length != 1 + token.content = replaceAt(token.content, t.index, closeQuote); + tokens[item.token].content = replaceAt(tokens[item.token].content, item.pos, openQuote); + pos += closeQuote.length - 1; + if (item.token === i) { + pos += openQuote.length - 1; + } + text = token.content; + max = text.length; + stack.length = j; + continue OUTER; + } + } + } + if (canOpen) { + stack.push({ + token: i, + pos: t.index, + single: isSingle, + level: thisLevel + }); + } else if (canClose && isSingle) { + token.content = replaceAt(token.content, t.index, APOSTROPHE); + } + } + } +} +function smartquotes(state) { + /* eslint max-depth:0 */ + if (!state.md.options.typographer) { + return; + } + for (let blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) { + if (state.tokens[blkIdx].type !== 'inline' || !QUOTE_TEST_RE.test(state.tokens[blkIdx].content)) { + continue; + } + process_inlines(state.tokens[blkIdx].children, state); + } +} + +// Join raw text tokens with the rest of the text +// +// This is set as a separate rule to provide an opportunity for plugins +// to run text replacements after text join, but before escape join. +// +// For example, `\:)` shouldn't be replaced with an emoji. +// + +function text_join(state) { + let curr, last; + const blockTokens = state.tokens; + const l = blockTokens.length; + for (let j = 0; j < l; j++) { + if (blockTokens[j].type !== 'inline') continue; + const tokens = blockTokens[j].children; + const max = tokens.length; + for (curr = 0; curr < max; curr++) { + if (tokens[curr].type === 'text_special') { + tokens[curr].type = 'text'; + } + } + for (curr = last = 0; curr < max; curr++) { + if (tokens[curr].type === 'text' && curr + 1 < max && tokens[curr + 1].type === 'text') { + // collapse two adjacent text nodes + tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content; + } else { + if (curr !== last) { + tokens[last] = tokens[curr]; + } + last++; + } + } + if (curr !== last) { + tokens.length = last; + } + } +} + +/** internal + * class Core + * + * Top-level rules executor. Glues block/inline parsers and does intermediate + * transformations. + **/ + +const _rules$2 = [['normalize', normalize], ['block', block], ['inline', inline], ['linkify', linkify$1], ['replacements', replace], ['smartquotes', smartquotes], +// `text_join` finds `text_special` tokens (for escape sequences) +// and joins them with the rest of the text +['text_join', text_join]]; + +/** + * new Core() + **/ +function Core() { + /** + * Core#ruler -> Ruler + * + * [[Ruler]] instance. Keep configuration of core rules. + **/ + this.ruler = new Ruler(); + for (let i = 0; i < _rules$2.length; i++) { + this.ruler.push(_rules$2[i][0], _rules$2[i][1]); + } +} + +/** + * Core.process(state) + * + * Executes core chain rules. + **/ +Core.prototype.process = function (state) { + const rules = this.ruler.getRules(''); + for (let i = 0, l = rules.length; i < l; i++) { + rules[i](state); + } +}; +Core.prototype.State = StateCore; + +// Parser state class + +function StateBlock(src, md, env, tokens) { + this.src = src; + + // link to parser instance + this.md = md; + this.env = env; + + // + // Internal state vartiables + // + + this.tokens = tokens; + this.bMarks = []; // line begin offsets for fast jumps + this.eMarks = []; // line end offsets for fast jumps + this.tShift = []; // offsets of the first non-space characters (tabs not expanded) + this.sCount = []; // indents for each line (tabs expanded) + + // An amount of virtual spaces (tabs expanded) between beginning + // of each line (bMarks) and real beginning of that line. + // + // It exists only as a hack because blockquotes override bMarks + // losing information in the process. + // + // It's used only when expanding tabs, you can think about it as + // an initial tab length, e.g. bsCount=21 applied to string `\t123` + // means first tab should be expanded to 4-21%4 === 3 spaces. + // + this.bsCount = []; + + // block parser variables + + // required block content indent (for example, if we are + // inside a list, it would be positioned after list marker) + this.blkIndent = 0; + this.line = 0; // line index in src + this.lineMax = 0; // lines count + this.tight = false; // loose/tight mode for lists + this.ddIndent = -1; // indent of the current dd block (-1 if there isn't any) + this.listIndent = -1; // indent of the current list block (-1 if there isn't any) + + // can be 'blockquote', 'list', 'root', 'paragraph' or 'reference' + // used in lists to determine if they interrupt a paragraph + this.parentType = 'root'; + this.level = 0; + + // Create caches + // Generate markers. + const s = this.src; + for (let start = 0, pos = 0, indent = 0, offset = 0, len = s.length, indent_found = false; pos < len; pos++) { + const ch = s.charCodeAt(pos); + if (!indent_found) { + if (isSpace(ch)) { + indent++; + if (ch === 0x09) { + offset += 4 - offset % 4; + } else { + offset++; + } + continue; + } else { + indent_found = true; + } + } + if (ch === 0x0A || pos === len - 1) { + if (ch !== 0x0A) { + pos++; + } + this.bMarks.push(start); + this.eMarks.push(pos); + this.tShift.push(indent); + this.sCount.push(offset); + this.bsCount.push(0); + indent_found = false; + indent = 0; + offset = 0; + start = pos + 1; + } + } + + // Push fake entry to simplify cache bounds checks + this.bMarks.push(s.length); + this.eMarks.push(s.length); + this.tShift.push(0); + this.sCount.push(0); + this.bsCount.push(0); + this.lineMax = this.bMarks.length - 1; // don't count last fake line +} + +// Push new token to "stream". +// +StateBlock.prototype.push = function (type, tag, nesting) { + const token = new Token(type, tag, nesting); + token.block = true; + if (nesting < 0) this.level--; // closing tag + token.level = this.level; + if (nesting > 0) this.level++; // opening tag + + this.tokens.push(token); + return token; +}; +StateBlock.prototype.isEmpty = function isEmpty(line) { + return this.bMarks[line] + this.tShift[line] >= this.eMarks[line]; +}; +StateBlock.prototype.skipEmptyLines = function skipEmptyLines(from) { + for (let max = this.lineMax; from < max; from++) { + if (this.bMarks[from] + this.tShift[from] < this.eMarks[from]) { + break; + } + } + return from; +}; + +// Skip spaces from given position. +StateBlock.prototype.skipSpaces = function skipSpaces(pos) { + for (let max = this.src.length; pos < max; pos++) { + const ch = this.src.charCodeAt(pos); + if (!isSpace(ch)) { + break; + } + } + return pos; +}; + +// Skip spaces from given position in reverse. +StateBlock.prototype.skipSpacesBack = function skipSpacesBack(pos, min) { + if (pos <= min) { + return pos; + } + while (pos > min) { + if (!isSpace(this.src.charCodeAt(--pos))) { + return pos + 1; + } + } + return pos; +}; + +// Skip char codes from given position +StateBlock.prototype.skipChars = function skipChars(pos, code) { + for (let max = this.src.length; pos < max; pos++) { + if (this.src.charCodeAt(pos) !== code) { + break; + } + } + return pos; +}; + +// Skip char codes reverse from given position - 1 +StateBlock.prototype.skipCharsBack = function skipCharsBack(pos, code, min) { + if (pos <= min) { + return pos; + } + while (pos > min) { + if (code !== this.src.charCodeAt(--pos)) { + return pos + 1; + } + } + return pos; +}; + +// cut lines range from source. +StateBlock.prototype.getLines = function getLines(begin, end, indent, keepLastLF) { + if (begin >= end) { + return ''; + } + const queue = new Array(end - begin); + for (let i = 0, line = begin; line < end; line++, i++) { + let lineIndent = 0; + const lineStart = this.bMarks[line]; + let first = lineStart; + let last; + if (line + 1 < end || keepLastLF) { + // No need for bounds check because we have fake entry on tail. + last = this.eMarks[line] + 1; + } else { + last = this.eMarks[line]; + } + while (first < last && lineIndent < indent) { + const ch = this.src.charCodeAt(first); + if (isSpace(ch)) { + if (ch === 0x09) { + lineIndent += 4 - (lineIndent + this.bsCount[line]) % 4; + } else { + lineIndent++; + } + } else if (first - lineStart < this.tShift[line]) { + // patched tShift masked characters to look like spaces (blockquotes, list markers) + lineIndent++; + } else { + break; + } + first++; + } + if (lineIndent > indent) { + // partially expanding tabs in code blocks, e.g '\t\tfoobar' + // with indent=2 becomes ' \tfoobar' + queue[i] = new Array(lineIndent - indent + 1).join(' ') + this.src.slice(first, last); + } else { + queue[i] = this.src.slice(first, last); + } + } + return queue.join(''); +}; + +// re-export Token class to use in block rules +StateBlock.prototype.Token = Token; + +// GFM table, https://github.github.com/gfm/#tables-extension- + + +// Limit the amount of empty autocompleted cells in a table, +// see https://github.com/markdown-it/markdown-it/issues/1000, +// +// Both pulldown-cmark and commonmark-hs limit the number of cells this way to ~200k. +// We set it to 65k, which can expand user input by a factor of x370 +// (256x256 square is 1.8kB expanded into 650kB). +const MAX_AUTOCOMPLETED_CELLS = 0x10000; +function getLine(state, line) { + const pos = state.bMarks[line] + state.tShift[line]; + const max = state.eMarks[line]; + return state.src.slice(pos, max); +} +function escapedSplit(str) { + const result = []; + const max = str.length; + let pos = 0; + let ch = str.charCodeAt(pos); + let isEscaped = false; + let lastPos = 0; + let current = ''; + while (pos < max) { + if (ch === 0x7c /* | */) { + if (!isEscaped) { + // pipe separating cells, '|' + result.push(current + str.substring(lastPos, pos)); + current = ''; + lastPos = pos + 1; + } else { + // escaped pipe, '\|' + current += str.substring(lastPos, pos - 1); + lastPos = pos; + } + } + isEscaped = ch === 0x5c /* \ */; + pos++; + ch = str.charCodeAt(pos); + } + result.push(current + str.substring(lastPos)); + return result; +} +function table(state, startLine, endLine, silent) { + // should have at least two lines + if (startLine + 2 > endLine) { + return false; + } + let nextLine = startLine + 1; + if (state.sCount[nextLine] < state.blkIndent) { + return false; + } + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[nextLine] - state.blkIndent >= 4) { + return false; + } + + // first character of the second line should be '|', '-', ':', + // and no other characters are allowed but spaces; + // basically, this is the equivalent of /^[-:|][-:|\s]*$/ regexp + + let pos = state.bMarks[nextLine] + state.tShift[nextLine]; + if (pos >= state.eMarks[nextLine]) { + return false; + } + const firstCh = state.src.charCodeAt(pos++); + if (firstCh !== 0x7C /* | */ && firstCh !== 0x2D /* - */ && firstCh !== 0x3A /* : */) { + return false; + } + if (pos >= state.eMarks[nextLine]) { + return false; + } + const secondCh = state.src.charCodeAt(pos++); + if (secondCh !== 0x7C /* | */ && secondCh !== 0x2D /* - */ && secondCh !== 0x3A /* : */ && !isSpace(secondCh)) { + return false; + } + + // if first character is '-', then second character must not be a space + // (due to parsing ambiguity with list) + if (firstCh === 0x2D /* - */ && isSpace(secondCh)) { + return false; + } + while (pos < state.eMarks[nextLine]) { + const ch = state.src.charCodeAt(pos); + if (ch !== 0x7C /* | */ && ch !== 0x2D /* - */ && ch !== 0x3A /* : */ && !isSpace(ch)) { + return false; + } + pos++; + } + let lineText = getLine(state, startLine + 1); + let columns = lineText.split('|'); + const aligns = []; + for (let i = 0; i < columns.length; i++) { + const t = columns[i].trim(); + if (!t) { + // allow empty columns before and after table, but not in between columns; + // e.g. allow ` |---| `, disallow ` ---||--- ` + if (i === 0 || i === columns.length - 1) { + continue; + } else { + return false; + } + } + if (!/^:?-+:?$/.test(t)) { + return false; + } + if (t.charCodeAt(t.length - 1) === 0x3A /* : */) { + aligns.push(t.charCodeAt(0) === 0x3A /* : */ ? 'center' : 'right'); + } else if (t.charCodeAt(0) === 0x3A /* : */) { + aligns.push('left'); + } else { + aligns.push(''); + } + } + lineText = getLine(state, startLine).trim(); + if (lineText.indexOf('|') === -1) { + return false; + } + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + columns = escapedSplit(lineText); + if (columns.length && columns[0] === '') columns.shift(); + if (columns.length && columns[columns.length - 1] === '') columns.pop(); + + // header row will define an amount of columns in the entire table, + // and align row should be exactly the same (the rest of the rows can differ) + const columnCount = columns.length; + if (columnCount === 0 || columnCount !== aligns.length) { + return false; + } + if (silent) { + return true; + } + const oldParentType = state.parentType; + state.parentType = 'table'; + + // use 'blockquote' lists for termination because it's + // the most similar to tables + const terminatorRules = state.md.block.ruler.getRules('blockquote'); + const token_to = state.push('table_open', 'table', 1); + const tableLines = [startLine, 0]; + token_to.map = tableLines; + const token_tho = state.push('thead_open', 'thead', 1); + token_tho.map = [startLine, startLine + 1]; + const token_htro = state.push('tr_open', 'tr', 1); + token_htro.map = [startLine, startLine + 1]; + for (let i = 0; i < columns.length; i++) { + const token_ho = state.push('th_open', 'th', 1); + if (aligns[i]) { + token_ho.attrs = [['style', 'text-align:' + aligns[i]]]; + } + const token_il = state.push('inline', '', 0); + token_il.content = columns[i].trim(); + token_il.children = []; + state.push('th_close', 'th', -1); + } + state.push('tr_close', 'tr', -1); + state.push('thead_close', 'thead', -1); + let tbodyLines; + let autocompletedCells = 0; + for (nextLine = startLine + 2; nextLine < endLine; nextLine++) { + if (state.sCount[nextLine] < state.blkIndent) { + break; + } + let terminate = false; + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { + break; + } + lineText = getLine(state, nextLine).trim(); + if (!lineText) { + break; + } + if (state.sCount[nextLine] - state.blkIndent >= 4) { + break; + } + columns = escapedSplit(lineText); + if (columns.length && columns[0] === '') columns.shift(); + if (columns.length && columns[columns.length - 1] === '') columns.pop(); + + // note: autocomplete count can be negative if user specifies more columns than header, + // but that does not affect intended use (which is limiting expansion) + autocompletedCells += columnCount - columns.length; + if (autocompletedCells > MAX_AUTOCOMPLETED_CELLS) { + break; + } + if (nextLine === startLine + 2) { + const token_tbo = state.push('tbody_open', 'tbody', 1); + token_tbo.map = tbodyLines = [startLine + 2, 0]; + } + const token_tro = state.push('tr_open', 'tr', 1); + token_tro.map = [nextLine, nextLine + 1]; + for (let i = 0; i < columnCount; i++) { + const token_tdo = state.push('td_open', 'td', 1); + if (aligns[i]) { + token_tdo.attrs = [['style', 'text-align:' + aligns[i]]]; + } + const token_il = state.push('inline', '', 0); + token_il.content = columns[i] ? columns[i].trim() : ''; + token_il.children = []; + state.push('td_close', 'td', -1); + } + state.push('tr_close', 'tr', -1); + } + if (tbodyLines) { + state.push('tbody_close', 'tbody', -1); + tbodyLines[1] = nextLine; + } + state.push('table_close', 'table', -1); + tableLines[1] = nextLine; + state.parentType = oldParentType; + state.line = nextLine; + return true; +} + +// Code block (4 spaces padded) + +function code(state, startLine, endLine /*, silent */) { + if (state.sCount[startLine] - state.blkIndent < 4) { + return false; + } + let nextLine = startLine + 1; + let last = nextLine; + while (nextLine < endLine) { + if (state.isEmpty(nextLine)) { + nextLine++; + continue; + } + if (state.sCount[nextLine] - state.blkIndent >= 4) { + nextLine++; + last = nextLine; + continue; + } + break; + } + state.line = last; + const token = state.push('code_block', 'code', 0); + token.content = state.getLines(startLine, last, 4 + state.blkIndent, false) + '\n'; + token.map = [startLine, state.line]; + return true; +} + +// fences (``` lang, ~~~ lang) + +function fence(state, startLine, endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine]; + let max = state.eMarks[startLine]; + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + if (pos + 3 > max) { + return false; + } + const marker = state.src.charCodeAt(pos); + if (marker !== 0x7E /* ~ */ && marker !== 0x60 /* ` */) { + return false; + } + + // scan marker length + let mem = pos; + pos = state.skipChars(pos, marker); + let len = pos - mem; + if (len < 3) { + return false; + } + const markup = state.src.slice(mem, pos); + const params = state.src.slice(pos, max); + if (marker === 0x60 /* ` */) { + if (params.indexOf(String.fromCharCode(marker)) >= 0) { + return false; + } + } + + // Since start is found, we can report success here in validation mode + if (silent) { + return true; + } + + // search end of block + let nextLine = startLine; + let haveEndMarker = false; + for (;;) { + nextLine++; + if (nextLine >= endLine) { + // unclosed block should be autoclosed by end of document. + // also block seems to be autoclosed by end of parent + break; + } + pos = mem = state.bMarks[nextLine] + state.tShift[nextLine]; + max = state.eMarks[nextLine]; + if (pos < max && state.sCount[nextLine] < state.blkIndent) { + // non-empty line with negative indent should stop the list: + // - ``` + // test + break; + } + if (state.src.charCodeAt(pos) !== marker) { + continue; + } + if (state.sCount[nextLine] - state.blkIndent >= 4) { + // closing fence should be indented less than 4 spaces + continue; + } + pos = state.skipChars(pos, marker); + + // closing code fence must be at least as long as the opening one + if (pos - mem < len) { + continue; + } + + // make sure tail has spaces only + pos = state.skipSpaces(pos); + if (pos < max) { + continue; + } + haveEndMarker = true; + // found! + break; + } + + // If a fence has heading spaces, they should be removed from its inner block + len = state.sCount[startLine]; + state.line = nextLine + (haveEndMarker ? 1 : 0); + const token = state.push('fence', 'code', 0); + token.info = params; + token.content = state.getLines(startLine + 1, nextLine, len, true); + token.markup = markup; + token.map = [startLine, state.line]; + return true; +} + +// Block quotes + +function blockquote(state, startLine, endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine]; + let max = state.eMarks[startLine]; + const oldLineMax = state.lineMax; + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + + // check the block quote marker + if (state.src.charCodeAt(pos) !== 0x3E /* > */) { + return false; + } + + // we know that it's going to be a valid blockquote, + // so no point trying to find the end of it in silent mode + if (silent) { + return true; + } + const oldBMarks = []; + const oldBSCount = []; + const oldSCount = []; + const oldTShift = []; + const terminatorRules = state.md.block.ruler.getRules('blockquote'); + const oldParentType = state.parentType; + state.parentType = 'blockquote'; + let lastLineEmpty = false; + let nextLine; + + // Search the end of the block + // + // Block ends with either: + // 1. an empty line outside: + // ``` + // > test + // + // ``` + // 2. an empty line inside: + // ``` + // > + // test + // ``` + // 3. another tag: + // ``` + // > test + // - - - + // ``` + for (nextLine = startLine; nextLine < endLine; nextLine++) { + // check if it's outdented, i.e. it's inside list item and indented + // less than said list item: + // + // ``` + // 1. anything + // > current blockquote + // 2. checking this line + // ``` + const isOutdented = state.sCount[nextLine] < state.blkIndent; + pos = state.bMarks[nextLine] + state.tShift[nextLine]; + max = state.eMarks[nextLine]; + if (pos >= max) { + // Case 1: line is not inside the blockquote, and this line is empty. + break; + } + if (state.src.charCodeAt(pos++) === 0x3E /* > */ && !isOutdented) { + // This line is inside the blockquote. + + // set offset past spaces and ">" + let initial = state.sCount[nextLine] + 1; + let spaceAfterMarker; + let adjustTab; + + // skip one optional space after '>' + if (state.src.charCodeAt(pos) === 0x20 /* space */) { + // ' > test ' + // ^ -- position start of line here: + pos++; + initial++; + adjustTab = false; + spaceAfterMarker = true; + } else if (state.src.charCodeAt(pos) === 0x09 /* tab */) { + spaceAfterMarker = true; + if ((state.bsCount[nextLine] + initial) % 4 === 3) { + // ' >\t test ' + // ^ -- position start of line here (tab has width===1) + pos++; + initial++; + adjustTab = false; + } else { + // ' >\t test ' + // ^ -- position start of line here + shift bsCount slightly + // to make extra space appear + adjustTab = true; + } + } else { + spaceAfterMarker = false; + } + let offset = initial; + oldBMarks.push(state.bMarks[nextLine]); + state.bMarks[nextLine] = pos; + while (pos < max) { + const ch = state.src.charCodeAt(pos); + if (isSpace(ch)) { + if (ch === 0x09) { + offset += 4 - (offset + state.bsCount[nextLine] + (adjustTab ? 1 : 0)) % 4; + } else { + offset++; + } + } else { + break; + } + pos++; + } + lastLineEmpty = pos >= max; + oldBSCount.push(state.bsCount[nextLine]); + state.bsCount[nextLine] = state.sCount[nextLine] + 1 + (spaceAfterMarker ? 1 : 0); + oldSCount.push(state.sCount[nextLine]); + state.sCount[nextLine] = offset - initial; + oldTShift.push(state.tShift[nextLine]); + state.tShift[nextLine] = pos - state.bMarks[nextLine]; + continue; + } + + // Case 2: line is not inside the blockquote, and the last line was empty. + if (lastLineEmpty) { + break; + } + + // Case 3: another tag found. + let terminate = false; + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { + // Quirk to enforce "hard termination mode" for paragraphs; + // normally if you call `tokenize(state, startLine, nextLine)`, + // paragraphs will look below nextLine for paragraph continuation, + // but if blockquote is terminated by another tag, they shouldn't + state.lineMax = nextLine; + if (state.blkIndent !== 0) { + // state.blkIndent was non-zero, we now set it to zero, + // so we need to re-calculate all offsets to appear as + // if indent wasn't changed + oldBMarks.push(state.bMarks[nextLine]); + oldBSCount.push(state.bsCount[nextLine]); + oldTShift.push(state.tShift[nextLine]); + oldSCount.push(state.sCount[nextLine]); + state.sCount[nextLine] -= state.blkIndent; + } + break; + } + oldBMarks.push(state.bMarks[nextLine]); + oldBSCount.push(state.bsCount[nextLine]); + oldTShift.push(state.tShift[nextLine]); + oldSCount.push(state.sCount[nextLine]); + + // A negative indentation means that this is a paragraph continuation + // + state.sCount[nextLine] = -1; + } + const oldIndent = state.blkIndent; + state.blkIndent = 0; + const token_o = state.push('blockquote_open', 'blockquote', 1); + token_o.markup = '>'; + const lines = [startLine, 0]; + token_o.map = lines; + state.md.block.tokenize(state, startLine, nextLine); + const token_c = state.push('blockquote_close', 'blockquote', -1); + token_c.markup = '>'; + state.lineMax = oldLineMax; + state.parentType = oldParentType; + lines[1] = state.line; + + // Restore original tShift; this might not be necessary since the parser + // has already been here, but just to make sure we can do that. + for (let i = 0; i < oldTShift.length; i++) { + state.bMarks[i + startLine] = oldBMarks[i]; + state.tShift[i + startLine] = oldTShift[i]; + state.sCount[i + startLine] = oldSCount[i]; + state.bsCount[i + startLine] = oldBSCount[i]; + } + state.blkIndent = oldIndent; + return true; +} + +// Horizontal rule + +function hr(state, startLine, endLine, silent) { + const max = state.eMarks[startLine]; + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + let pos = state.bMarks[startLine] + state.tShift[startLine]; + const marker = state.src.charCodeAt(pos++); + + // Check hr marker + if (marker !== 0x2A /* * */ && marker !== 0x2D /* - */ && marker !== 0x5F /* _ */) { + return false; + } + + // markers can be mixed with spaces, but there should be at least 3 of them + + let cnt = 1; + while (pos < max) { + const ch = state.src.charCodeAt(pos++); + if (ch !== marker && !isSpace(ch)) { + return false; + } + if (ch === marker) { + cnt++; + } + } + if (cnt < 3) { + return false; + } + if (silent) { + return true; + } + state.line = startLine + 1; + const token = state.push('hr', 'hr', 0); + token.map = [startLine, state.line]; + token.markup = Array(cnt + 1).join(String.fromCharCode(marker)); + return true; +} + +// Lists + + +// Search `[-+*][\n ]`, returns next pos after marker on success +// or -1 on fail. +function skipBulletListMarker(state, startLine) { + const max = state.eMarks[startLine]; + let pos = state.bMarks[startLine] + state.tShift[startLine]; + const marker = state.src.charCodeAt(pos++); + // Check bullet + if (marker !== 0x2A /* * */ && marker !== 0x2D /* - */ && marker !== 0x2B /* + */) { + return -1; + } + if (pos < max) { + const ch = state.src.charCodeAt(pos); + if (!isSpace(ch)) { + // " -test " - is not a list item + return -1; + } + } + return pos; +} + +// Search `\d+[.)][\n ]`, returns next pos after marker on success +// or -1 on fail. +function skipOrderedListMarker(state, startLine) { + const start = state.bMarks[startLine] + state.tShift[startLine]; + const max = state.eMarks[startLine]; + let pos = start; + + // List marker should have at least 2 chars (digit + dot) + if (pos + 1 >= max) { + return -1; + } + let ch = state.src.charCodeAt(pos++); + if (ch < 0x30 /* 0 */ || ch > 0x39 /* 9 */) { + return -1; + } + for (;;) { + // EOL -> fail + if (pos >= max) { + return -1; + } + ch = state.src.charCodeAt(pos++); + if (ch >= 0x30 /* 0 */ && ch <= 0x39 /* 9 */) { + // List marker should have no more than 9 digits + // (prevents integer overflow in browsers) + if (pos - start >= 10) { + return -1; + } + continue; + } + + // found valid marker + if (ch === 0x29 /* ) */ || ch === 0x2e /* . */) { + break; + } + return -1; + } + if (pos < max) { + ch = state.src.charCodeAt(pos); + if (!isSpace(ch)) { + // " 1.test " - is not a list item + return -1; + } + } + return pos; +} +function markTightParagraphs(state, idx) { + const level = state.level + 2; + for (let i = idx + 2, l = state.tokens.length - 2; i < l; i++) { + if (state.tokens[i].level === level && state.tokens[i].type === 'paragraph_open') { + state.tokens[i + 2].hidden = true; + state.tokens[i].hidden = true; + i += 2; + } + } +} +function list(state, startLine, endLine, silent) { + let max, pos, start, token; + let nextLine = startLine; + let tight = true; + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[nextLine] - state.blkIndent >= 4) { + return false; + } + + // Special case: + // - item 1 + // - item 2 + // - item 3 + // - item 4 + // - this one is a paragraph continuation + if (state.listIndent >= 0 && state.sCount[nextLine] - state.listIndent >= 4 && state.sCount[nextLine] < state.blkIndent) { + return false; + } + let isTerminatingParagraph = false; + + // limit conditions when list can interrupt + // a paragraph (validation mode only) + if (silent && state.parentType === 'paragraph') { + // Next list item should still terminate previous list item; + // + // This code can fail if plugins use blkIndent as well as lists, + // but I hope the spec gets fixed long before that happens. + // + if (state.sCount[nextLine] >= state.blkIndent) { + isTerminatingParagraph = true; + } + } + + // Detect list type and position after marker + let isOrdered; + let markerValue; + let posAfterMarker; + if ((posAfterMarker = skipOrderedListMarker(state, nextLine)) >= 0) { + isOrdered = true; + start = state.bMarks[nextLine] + state.tShift[nextLine]; + markerValue = Number(state.src.slice(start, posAfterMarker - 1)); + + // If we're starting a new ordered list right after + // a paragraph, it should start with 1. + if (isTerminatingParagraph && markerValue !== 1) return false; + } else if ((posAfterMarker = skipBulletListMarker(state, nextLine)) >= 0) { + isOrdered = false; + } else { + return false; + } + + // If we're starting a new unordered list right after + // a paragraph, first line should not be empty. + if (isTerminatingParagraph) { + if (state.skipSpaces(posAfterMarker) >= state.eMarks[nextLine]) return false; + } + + // For validation mode we can terminate immediately + if (silent) { + return true; + } + + // We should terminate list on style change. Remember first one to compare. + const markerCharCode = state.src.charCodeAt(posAfterMarker - 1); + + // Start list + const listTokIdx = state.tokens.length; + if (isOrdered) { + token = state.push('ordered_list_open', 'ol', 1); + if (markerValue !== 1) { + token.attrs = [['start', markerValue]]; + } + } else { + token = state.push('bullet_list_open', 'ul', 1); + } + const listLines = [nextLine, 0]; + token.map = listLines; + token.markup = String.fromCharCode(markerCharCode); + + // + // Iterate list items + // + + let prevEmptyEnd = false; + const terminatorRules = state.md.block.ruler.getRules('list'); + const oldParentType = state.parentType; + state.parentType = 'list'; + while (nextLine < endLine) { + pos = posAfterMarker; + max = state.eMarks[nextLine]; + const initial = state.sCount[nextLine] + posAfterMarker - (state.bMarks[nextLine] + state.tShift[nextLine]); + let offset = initial; + while (pos < max) { + const ch = state.src.charCodeAt(pos); + if (ch === 0x09) { + offset += 4 - (offset + state.bsCount[nextLine]) % 4; + } else if (ch === 0x20) { + offset++; + } else { + break; + } + pos++; + } + const contentStart = pos; + let indentAfterMarker; + if (contentStart >= max) { + // trimming space in "- \n 3" case, indent is 1 here + indentAfterMarker = 1; + } else { + indentAfterMarker = offset - initial; + } + + // If we have more than 4 spaces, the indent is 1 + // (the rest is just indented code block) + if (indentAfterMarker > 4) { + indentAfterMarker = 1; + } + + // " - test" + // ^^^^^ - calculating total length of this thing + const indent = initial + indentAfterMarker; + + // Run subparser & write tokens + token = state.push('list_item_open', 'li', 1); + token.markup = String.fromCharCode(markerCharCode); + const itemLines = [nextLine, 0]; + token.map = itemLines; + if (isOrdered) { + token.info = state.src.slice(start, posAfterMarker - 1); + } + + // change current state, then restore it after parser subcall + const oldTight = state.tight; + const oldTShift = state.tShift[nextLine]; + const oldSCount = state.sCount[nextLine]; + + // - example list + // ^ listIndent position will be here + // ^ blkIndent position will be here + // + const oldListIndent = state.listIndent; + state.listIndent = state.blkIndent; + state.blkIndent = indent; + state.tight = true; + state.tShift[nextLine] = contentStart - state.bMarks[nextLine]; + state.sCount[nextLine] = offset; + if (contentStart >= max && state.isEmpty(nextLine + 1)) { + // workaround for this case + // (list item is empty, list terminates before "foo"): + // ~~~~~~~~ + // - + // + // foo + // ~~~~~~~~ + state.line = Math.min(state.line + 2, endLine); + } else { + state.md.block.tokenize(state, nextLine, endLine, true); + } + + // If any of list item is tight, mark list as tight + if (!state.tight || prevEmptyEnd) { + tight = false; + } + // Item become loose if finish with empty line, + // but we should filter last element, because it means list finish + prevEmptyEnd = state.line - nextLine > 1 && state.isEmpty(state.line - 1); + state.blkIndent = state.listIndent; + state.listIndent = oldListIndent; + state.tShift[nextLine] = oldTShift; + state.sCount[nextLine] = oldSCount; + state.tight = oldTight; + token = state.push('list_item_close', 'li', -1); + token.markup = String.fromCharCode(markerCharCode); + nextLine = state.line; + itemLines[1] = nextLine; + if (nextLine >= endLine) { + break; + } + + // + // Try to check if list is terminated or continued. + // + if (state.sCount[nextLine] < state.blkIndent) { + break; + } + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[nextLine] - state.blkIndent >= 4) { + break; + } + + // fail if terminating block found + let terminate = false; + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { + break; + } + + // fail if list has another type + if (isOrdered) { + posAfterMarker = skipOrderedListMarker(state, nextLine); + if (posAfterMarker < 0) { + break; + } + start = state.bMarks[nextLine] + state.tShift[nextLine]; + } else { + posAfterMarker = skipBulletListMarker(state, nextLine); + if (posAfterMarker < 0) { + break; + } + } + if (markerCharCode !== state.src.charCodeAt(posAfterMarker - 1)) { + break; + } + } + + // Finalize list + if (isOrdered) { + token = state.push('ordered_list_close', 'ol', -1); + } else { + token = state.push('bullet_list_close', 'ul', -1); + } + token.markup = String.fromCharCode(markerCharCode); + listLines[1] = nextLine; + state.line = nextLine; + state.parentType = oldParentType; + + // mark paragraphs tight if needed + if (tight) { + markTightParagraphs(state, listTokIdx); + } + return true; +} + +function reference(state, startLine, _endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine]; + let max = state.eMarks[startLine]; + let nextLine = startLine + 1; + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + if (state.src.charCodeAt(pos) !== 0x5B /* [ */) { + return false; + } + function getNextLine(nextLine) { + const endLine = state.lineMax; + if (nextLine >= endLine || state.isEmpty(nextLine)) { + // empty line or end of input + return null; + } + let isContinuation = false; + + // this would be a code block normally, but after paragraph + // it's considered a lazy continuation regardless of what's there + if (state.sCount[nextLine] - state.blkIndent > 3) { + isContinuation = true; + } + + // quirk for blockquotes, this line should already be checked by that rule + if (state.sCount[nextLine] < 0) { + isContinuation = true; + } + if (!isContinuation) { + const terminatorRules = state.md.block.ruler.getRules('reference'); + const oldParentType = state.parentType; + state.parentType = 'reference'; + + // Some tags can terminate paragraph without empty line. + let terminate = false; + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + state.parentType = oldParentType; + if (terminate) { + // terminated by another block + return null; + } + } + const pos = state.bMarks[nextLine] + state.tShift[nextLine]; + const max = state.eMarks[nextLine]; + + // max + 1 explicitly includes the newline + return state.src.slice(pos, max + 1); + } + let str = state.src.slice(pos, max + 1); + max = str.length; + let labelEnd = -1; + for (pos = 1; pos < max; pos++) { + const ch = str.charCodeAt(pos); + if (ch === 0x5B /* [ */) { + return false; + } else if (ch === 0x5D /* ] */) { + labelEnd = pos; + break; + } else if (ch === 0x0A /* \n */) { + const lineContent = getNextLine(nextLine); + if (lineContent !== null) { + str += lineContent; + max = str.length; + nextLine++; + } + } else if (ch === 0x5C /* \ */) { + pos++; + if (pos < max && str.charCodeAt(pos) === 0x0A) { + const lineContent = getNextLine(nextLine); + if (lineContent !== null) { + str += lineContent; + max = str.length; + nextLine++; + } + } + } + } + if (labelEnd < 0 || str.charCodeAt(labelEnd + 1) !== 0x3A /* : */) { + return false; + } + + // [label]: destination 'title' + // ^^^ skip optional whitespace here + for (pos = labelEnd + 2; pos < max; pos++) { + const ch = str.charCodeAt(pos); + if (ch === 0x0A) { + const lineContent = getNextLine(nextLine); + if (lineContent !== null) { + str += lineContent; + max = str.length; + nextLine++; + } + } else if (isSpace(ch)) ; else { + break; + } + } + + // [label]: destination 'title' + // ^^^^^^^^^^^ parse this + const destRes = state.md.helpers.parseLinkDestination(str, pos, max); + if (!destRes.ok) { + return false; + } + const href = state.md.normalizeLink(destRes.str); + if (!state.md.validateLink(href)) { + return false; + } + pos = destRes.pos; + + // save cursor state, we could require to rollback later + const destEndPos = pos; + const destEndLineNo = nextLine; + + // [label]: destination 'title' + // ^^^ skipping those spaces + const start = pos; + for (; pos < max; pos++) { + const ch = str.charCodeAt(pos); + if (ch === 0x0A) { + const lineContent = getNextLine(nextLine); + if (lineContent !== null) { + str += lineContent; + max = str.length; + nextLine++; + } + } else if (isSpace(ch)) ; else { + break; + } + } + + // [label]: destination 'title' + // ^^^^^^^ parse this + let titleRes = state.md.helpers.parseLinkTitle(str, pos, max); + while (titleRes.can_continue) { + const lineContent = getNextLine(nextLine); + if (lineContent === null) break; + str += lineContent; + pos = max; + max = str.length; + nextLine++; + titleRes = state.md.helpers.parseLinkTitle(str, pos, max, titleRes); + } + let title; + if (pos < max && start !== pos && titleRes.ok) { + title = titleRes.str; + pos = titleRes.pos; + } else { + title = ''; + pos = destEndPos; + nextLine = destEndLineNo; + } + + // skip trailing spaces until the rest of the line + while (pos < max) { + const ch = str.charCodeAt(pos); + if (!isSpace(ch)) { + break; + } + pos++; + } + if (pos < max && str.charCodeAt(pos) !== 0x0A) { + if (title) { + // garbage at the end of the line after title, + // but it could still be a valid reference if we roll back + title = ''; + pos = destEndPos; + nextLine = destEndLineNo; + while (pos < max) { + const ch = str.charCodeAt(pos); + if (!isSpace(ch)) { + break; + } + pos++; + } + } + } + if (pos < max && str.charCodeAt(pos) !== 0x0A) { + // garbage at the end of the line + return false; + } + const label = normalizeReference(str.slice(1, labelEnd)); + if (!label) { + // CommonMark 0.20 disallows empty labels + return false; + } + + // Reference can not terminate anything. This check is for safety only. + /* istanbul ignore if */ + if (silent) { + return true; + } + if (typeof state.env.references === 'undefined') { + state.env.references = {}; + } + if (typeof state.env.references[label] === 'undefined') { + state.env.references[label] = { + title, + href + }; + } + state.line = nextLine; + return true; +} + +// List of valid html blocks names, according to commonmark spec +// https://spec.commonmark.org/0.30/#html-blocks + +var block_names = ['address', 'article', 'aside', 'base', 'basefont', 'blockquote', 'body', 'caption', 'center', 'col', 'colgroup', 'dd', 'details', 'dialog', 'dir', 'div', 'dl', 'dt', 'fieldset', 'figcaption', 'figure', 'footer', 'form', 'frame', 'frameset', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'head', 'header', 'hr', 'html', 'iframe', 'legend', 'li', 'link', 'main', 'menu', 'menuitem', 'nav', 'noframes', 'ol', 'optgroup', 'option', 'p', 'param', 'search', 'section', 'summary', 'table', 'tbody', 'td', 'tfoot', 'th', 'thead', 'title', 'tr', 'track', 'ul']; + +// Regexps to match html elements + +const attr_name = '[a-zA-Z_:][a-zA-Z0-9:._-]*'; +const unquoted = '[^"\'=<>`\\x00-\\x20]+'; +const single_quoted = "'[^']*'"; +const double_quoted = '"[^"]*"'; +const attr_value = '(?:' + unquoted + '|' + single_quoted + '|' + double_quoted + ')'; +const attribute = '(?:\\s+' + attr_name + '(?:\\s*=\\s*' + attr_value + ')?)'; +const open_tag = '<[A-Za-z][A-Za-z0-9\\-]*' + attribute + '*\\s*\\/?>'; +const close_tag = '<\\/[A-Za-z][A-Za-z0-9\\-]*\\s*>'; +const comment = ''; +const processing = '<[?][\\s\\S]*?[?]>'; +const declaration = ']*>'; +const cdata = ''; +const HTML_TAG_RE = new RegExp('^(?:' + open_tag + '|' + close_tag + '|' + comment + '|' + processing + '|' + declaration + '|' + cdata + ')'); +const HTML_OPEN_CLOSE_TAG_RE = new RegExp('^(?:' + open_tag + '|' + close_tag + ')'); + +// HTML block + + +// An array of opening and corresponding closing sequences for html tags, +// last argument defines whether it can terminate a paragraph or not +// +const HTML_SEQUENCES = [[/^<(script|pre|style|textarea)(?=(\s|>|$))/i, /<\/(script|pre|style|textarea)>/i, true], [/^/, true], [/^<\?/, /\?>/, true], [/^/, true], [/^/, true], [new RegExp('^|$))', 'i'), /^$/, true], [new RegExp(HTML_OPEN_CLOSE_TAG_RE.source + '\\s*$'), /^$/, false]]; +function html_block(state, startLine, endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine]; + let max = state.eMarks[startLine]; + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + if (!state.md.options.html) { + return false; + } + if (state.src.charCodeAt(pos) !== 0x3C /* < */) { + return false; + } + let lineText = state.src.slice(pos, max); + let i = 0; + for (; i < HTML_SEQUENCES.length; i++) { + if (HTML_SEQUENCES[i][0].test(lineText)) { + break; + } + } + if (i === HTML_SEQUENCES.length) { + return false; + } + if (silent) { + // true if this sequence can be a terminator, false otherwise + return HTML_SEQUENCES[i][2]; + } + let nextLine = startLine + 1; + + // If we are here - we detected HTML block. + // Let's roll down till block end. + if (!HTML_SEQUENCES[i][1].test(lineText)) { + for (; nextLine < endLine; nextLine++) { + if (state.sCount[nextLine] < state.blkIndent) { + break; + } + pos = state.bMarks[nextLine] + state.tShift[nextLine]; + max = state.eMarks[nextLine]; + lineText = state.src.slice(pos, max); + if (HTML_SEQUENCES[i][1].test(lineText)) { + if (lineText.length !== 0) { + nextLine++; + } + break; + } + } + } + state.line = nextLine; + const token = state.push('html_block', '', 0); + token.map = [startLine, nextLine]; + token.content = state.getLines(startLine, nextLine, state.blkIndent, true); + return true; +} + +// heading (#, ##, ...) + +function heading(state, startLine, endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine]; + let max = state.eMarks[startLine]; + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + let ch = state.src.charCodeAt(pos); + if (ch !== 0x23 /* # */ || pos >= max) { + return false; + } + + // count heading level + let level = 1; + ch = state.src.charCodeAt(++pos); + while (ch === 0x23 /* # */ && pos < max && level <= 6) { + level++; + ch = state.src.charCodeAt(++pos); + } + if (level > 6 || pos < max && !isSpace(ch)) { + return false; + } + if (silent) { + return true; + } + + // Let's cut tails like ' ### ' from the end of string + + max = state.skipSpacesBack(max, pos); + const tmp = state.skipCharsBack(max, 0x23, pos); // # + if (tmp > pos && isSpace(state.src.charCodeAt(tmp - 1))) { + max = tmp; + } + state.line = startLine + 1; + const token_o = state.push('heading_open', 'h' + String(level), 1); + token_o.markup = '########'.slice(0, level); + token_o.map = [startLine, state.line]; + const token_i = state.push('inline', '', 0); + token_i.content = state.src.slice(pos, max).trim(); + token_i.map = [startLine, state.line]; + token_i.children = []; + const token_c = state.push('heading_close', 'h' + String(level), -1); + token_c.markup = '########'.slice(0, level); + return true; +} + +// lheading (---, ===) + +function lheading(state, startLine, endLine /*, silent */) { + const terminatorRules = state.md.block.ruler.getRules('paragraph'); + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + const oldParentType = state.parentType; + state.parentType = 'paragraph'; // use paragraph to match terminatorRules + + // jump line-by-line until empty one or EOF + let level = 0; + let marker; + let nextLine = startLine + 1; + for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) { + // this would be a code block normally, but after paragraph + // it's considered a lazy continuation regardless of what's there + if (state.sCount[nextLine] - state.blkIndent > 3) { + continue; + } + + // + // Check for underline in setext header + // + if (state.sCount[nextLine] >= state.blkIndent) { + let pos = state.bMarks[nextLine] + state.tShift[nextLine]; + const max = state.eMarks[nextLine]; + if (pos < max) { + marker = state.src.charCodeAt(pos); + if (marker === 0x2D /* - */ || marker === 0x3D /* = */) { + pos = state.skipChars(pos, marker); + pos = state.skipSpaces(pos); + if (pos >= max) { + level = marker === 0x3D /* = */ ? 1 : 2; + break; + } + } + } + } + + // quirk for blockquotes, this line should already be checked by that rule + if (state.sCount[nextLine] < 0) { + continue; + } + + // Some tags can terminate paragraph without empty line. + let terminate = false; + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { + break; + } + } + if (!level) { + // Didn't find valid underline + return false; + } + const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim(); + state.line = nextLine + 1; + const token_o = state.push('heading_open', 'h' + String(level), 1); + token_o.markup = String.fromCharCode(marker); + token_o.map = [startLine, state.line]; + const token_i = state.push('inline', '', 0); + token_i.content = content; + token_i.map = [startLine, state.line - 1]; + token_i.children = []; + const token_c = state.push('heading_close', 'h' + String(level), -1); + token_c.markup = String.fromCharCode(marker); + state.parentType = oldParentType; + return true; +} + +// Paragraph + +function paragraph(state, startLine, endLine) { + const terminatorRules = state.md.block.ruler.getRules('paragraph'); + const oldParentType = state.parentType; + let nextLine = startLine + 1; + state.parentType = 'paragraph'; + + // jump line-by-line until empty one or EOF + for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) { + // this would be a code block normally, but after paragraph + // it's considered a lazy continuation regardless of what's there + if (state.sCount[nextLine] - state.blkIndent > 3) { + continue; + } + + // quirk for blockquotes, this line should already be checked by that rule + if (state.sCount[nextLine] < 0) { + continue; + } + + // Some tags can terminate paragraph without empty line. + let terminate = false; + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { + break; + } + } + const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim(); + state.line = nextLine; + const token_o = state.push('paragraph_open', 'p', 1); + token_o.map = [startLine, state.line]; + const token_i = state.push('inline', '', 0); + token_i.content = content; + token_i.map = [startLine, state.line]; + token_i.children = []; + state.push('paragraph_close', 'p', -1); + state.parentType = oldParentType; + return true; +} + +/** internal + * class ParserBlock + * + * Block-level tokenizer. + **/ + +const _rules$1 = [ +// First 2 params - rule name & source. Secondary array - list of rules, +// which can be terminated by this one. +['table', table, ['paragraph', 'reference']], ['code', code], ['fence', fence, ['paragraph', 'reference', 'blockquote', 'list']], ['blockquote', blockquote, ['paragraph', 'reference', 'blockquote', 'list']], ['hr', hr, ['paragraph', 'reference', 'blockquote', 'list']], ['list', list, ['paragraph', 'reference', 'blockquote']], ['reference', reference], ['html_block', html_block, ['paragraph', 'reference', 'blockquote']], ['heading', heading, ['paragraph', 'reference', 'blockquote']], ['lheading', lheading], ['paragraph', paragraph]]; + +/** + * new ParserBlock() + **/ +function ParserBlock() { + /** + * ParserBlock#ruler -> Ruler + * + * [[Ruler]] instance. Keep configuration of block rules. + **/ + this.ruler = new Ruler(); + for (let i = 0; i < _rules$1.length; i++) { + this.ruler.push(_rules$1[i][0], _rules$1[i][1], { + alt: (_rules$1[i][2] || []).slice() + }); + } +} + +// Generate tokens for input range +// +ParserBlock.prototype.tokenize = function (state, startLine, endLine) { + const rules = this.ruler.getRules(''); + const len = rules.length; + const maxNesting = state.md.options.maxNesting; + let line = startLine; + let hasEmptyLines = false; + while (line < endLine) { + state.line = line = state.skipEmptyLines(line); + if (line >= endLine) { + break; + } + + // Termination condition for nested calls. + // Nested calls currently used for blockquotes & lists + if (state.sCount[line] < state.blkIndent) { + break; + } + + // If nesting level exceeded - skip tail to the end. That's not ordinary + // situation and we should not care about content. + if (state.level >= maxNesting) { + state.line = endLine; + break; + } + + // Try all possible rules. + // On success, rule should: + // + // - update `state.line` + // - update `state.tokens` + // - return true + const prevLine = state.line; + let ok = false; + for (let i = 0; i < len; i++) { + ok = rules[i](state, line, endLine, false); + if (ok) { + if (prevLine >= state.line) { + throw new Error("block rule didn't increment state.line"); + } + break; + } + } + + // this can only happen if user disables paragraph rule + if (!ok) throw new Error('none of the block rules matched'); + + // set state.tight if we had an empty line before current tag + // i.e. latest empty line should not count + state.tight = !hasEmptyLines; + + // paragraph might "eat" one newline after it in nested lists + if (state.isEmpty(state.line - 1)) { + hasEmptyLines = true; + } + line = state.line; + if (line < endLine && state.isEmpty(line)) { + hasEmptyLines = true; + line++; + state.line = line; + } + } +}; + +/** + * ParserBlock.parse(str, md, env, outTokens) + * + * Process input string and push block tokens into `outTokens` + **/ +ParserBlock.prototype.parse = function (src, md, env, outTokens) { + if (!src) { + return; + } + const state = new this.State(src, md, env, outTokens); + this.tokenize(state, state.line, state.lineMax); +}; +ParserBlock.prototype.State = StateBlock; + +// Inline parser state + +function StateInline(src, md, env, outTokens) { + this.src = src; + this.env = env; + this.md = md; + this.tokens = outTokens; + this.tokens_meta = Array(outTokens.length); + this.pos = 0; + this.posMax = this.src.length; + this.level = 0; + this.pending = ''; + this.pendingLevel = 0; + + // Stores { start: end } pairs. Useful for backtrack + // optimization of pairs parse (emphasis, strikes). + this.cache = {}; + + // List of emphasis-like delimiters for current tag + this.delimiters = []; + + // Stack of delimiter lists for upper level tags + this._prev_delimiters = []; + + // backtick length => last seen position + this.backticks = {}; + this.backticksScanned = false; + + // Counter used to disable inline linkify-it execution + // inside and markdown links + this.linkLevel = 0; +} + +// Flush pending text +// +StateInline.prototype.pushPending = function () { + const token = new Token('text', '', 0); + token.content = this.pending; + token.level = this.pendingLevel; + this.tokens.push(token); + this.pending = ''; + return token; +}; + +// Push new token to "stream". +// If pending text exists - flush it as text token +// +StateInline.prototype.push = function (type, tag, nesting) { + if (this.pending) { + this.pushPending(); + } + const token = new Token(type, tag, nesting); + let token_meta = null; + if (nesting < 0) { + // closing tag + this.level--; + this.delimiters = this._prev_delimiters.pop(); + } + token.level = this.level; + if (nesting > 0) { + // opening tag + this.level++; + this._prev_delimiters.push(this.delimiters); + this.delimiters = []; + token_meta = { + delimiters: this.delimiters + }; + } + this.pendingLevel = this.level; + this.tokens.push(token); + this.tokens_meta.push(token_meta); + return token; +}; + +// Scan a sequence of emphasis-like markers, and determine whether +// it can start an emphasis sequence or end an emphasis sequence. +// +// - start - position to scan from (it should point at a valid marker); +// - canSplitWord - determine if these markers can be found inside a word +// +StateInline.prototype.scanDelims = function (start, canSplitWord) { + const max = this.posMax; + const marker = this.src.charCodeAt(start); + + // treat beginning of the line as a whitespace + const lastChar = start > 0 ? this.src.charCodeAt(start - 1) : 0x20; + let pos = start; + while (pos < max && this.src.charCodeAt(pos) === marker) { + pos++; + } + const count = pos - start; + + // treat end of the line as a whitespace + const nextChar = pos < max ? this.src.charCodeAt(pos) : 0x20; + const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar)); + const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar)); + const isLastWhiteSpace = isWhiteSpace(lastChar); + const isNextWhiteSpace = isWhiteSpace(nextChar); + const left_flanking = !isNextWhiteSpace && (!isNextPunctChar || isLastWhiteSpace || isLastPunctChar); + const right_flanking = !isLastWhiteSpace && (!isLastPunctChar || isNextWhiteSpace || isNextPunctChar); + const can_open = left_flanking && (canSplitWord || !right_flanking || isLastPunctChar); + const can_close = right_flanking && (canSplitWord || !left_flanking || isNextPunctChar); + return { + can_open, + can_close, + length: count + }; +}; + +// re-export Token class to use in block rules +StateInline.prototype.Token = Token; + +// Skip text characters for text token, place those to pending buffer +// and increment current pos + +// Rule to skip pure text +// '{}$%@~+=:' reserved for extentions + +// !, ", #, $, %, &, ', (, ), *, +, ,, -, ., /, :, ;, <, =, >, ?, @, [, \, ], ^, _, `, {, |, }, or ~ + +// !!!! Don't confuse with "Markdown ASCII Punctuation" chars +// http://spec.commonmark.org/0.15/#ascii-punctuation-character +function isTerminatorChar(ch) { + switch (ch) { + case 0x0A /* \n */: + case 0x21 /* ! */: + case 0x23 /* # */: + case 0x24 /* $ */: + case 0x25 /* % */: + case 0x26 /* & */: + case 0x2A /* * */: + case 0x2B /* + */: + case 0x2D /* - */: + case 0x3A /* : */: + case 0x3C /* < */: + case 0x3D /* = */: + case 0x3E /* > */: + case 0x40 /* @ */: + case 0x5B /* [ */: + case 0x5C /* \ */: + case 0x5D /* ] */: + case 0x5E /* ^ */: + case 0x5F /* _ */: + case 0x60 /* ` */: + case 0x7B /* { */: + case 0x7D /* } */: + case 0x7E /* ~ */: + return true; + default: + return false; + } +} +function text(state, silent) { + let pos = state.pos; + while (pos < state.posMax && !isTerminatorChar(state.src.charCodeAt(pos))) { + pos++; + } + if (pos === state.pos) { + return false; + } + if (!silent) { + state.pending += state.src.slice(state.pos, pos); + } + state.pos = pos; + return true; +} + +// Alternative implementation, for memory. +// +// It costs 10% of performance, but allows extend terminators list, if place it +// to `ParserInline` property. Probably, will switch to it sometime, such +// flexibility required. + +/* +var TERMINATOR_RE = /[\n!#$%&*+\-:<=>@[\\\]^_`{}~]/; + +module.exports = function text(state, silent) { + var pos = state.pos, + idx = state.src.slice(pos).search(TERMINATOR_RE); + + // first char is terminator -> empty text + if (idx === 0) { return false; } + + // no terminator -> text till end of string + if (idx < 0) { + if (!silent) { state.pending += state.src.slice(pos); } + state.pos = state.src.length; + return true; + } + + if (!silent) { state.pending += state.src.slice(pos, pos + idx); } + + state.pos += idx; + + return true; +}; */ + +// Process links like https://example.org/ + +// RFC3986: scheme = ALPHA *( ALPHA / DIGIT / "+" / "-" / "." ) +const SCHEME_RE = /(?:^|[^a-z0-9.+-])([a-z][a-z0-9.+-]*)$/i; +function linkify(state, silent) { + if (!state.md.options.linkify) return false; + if (state.linkLevel > 0) return false; + const pos = state.pos; + const max = state.posMax; + if (pos + 3 > max) return false; + if (state.src.charCodeAt(pos) !== 0x3A /* : */) return false; + if (state.src.charCodeAt(pos + 1) !== 0x2F /* / */) return false; + if (state.src.charCodeAt(pos + 2) !== 0x2F /* / */) return false; + const match = state.pending.match(SCHEME_RE); + if (!match) return false; + const proto = match[1]; + const link = state.md.linkify.matchAtStart(state.src.slice(pos - proto.length)); + if (!link) return false; + let url = link.url; + + // invalid link, but still detected by linkify somehow; + // need to check to prevent infinite loop below + if (url.length <= proto.length) return false; + + // disallow '*' at the end of the link (conflicts with emphasis) + url = url.replace(/\*+$/, ''); + const fullUrl = state.md.normalizeLink(url); + if (!state.md.validateLink(fullUrl)) return false; + if (!silent) { + state.pending = state.pending.slice(0, -proto.length); + const token_o = state.push('link_open', 'a', 1); + token_o.attrs = [['href', fullUrl]]; + token_o.markup = 'linkify'; + token_o.info = 'auto'; + const token_t = state.push('text', '', 0); + token_t.content = state.md.normalizeLinkText(url); + const token_c = state.push('link_close', 'a', -1); + token_c.markup = 'linkify'; + token_c.info = 'auto'; + } + state.pos += url.length - proto.length; + return true; +} + +// Proceess '\n' + +function newline(state, silent) { + let pos = state.pos; + if (state.src.charCodeAt(pos) !== 0x0A /* \n */) { + return false; + } + const pmax = state.pending.length - 1; + const max = state.posMax; + + // ' \n' -> hardbreak + // Lookup in pending chars is bad practice! Don't copy to other rules! + // Pending string is stored in concat mode, indexed lookups will cause + // convertion to flat mode. + if (!silent) { + if (pmax >= 0 && state.pending.charCodeAt(pmax) === 0x20) { + if (pmax >= 1 && state.pending.charCodeAt(pmax - 1) === 0x20) { + // Find whitespaces tail of pending chars. + let ws = pmax - 1; + while (ws >= 1 && state.pending.charCodeAt(ws - 1) === 0x20) ws--; + state.pending = state.pending.slice(0, ws); + state.push('hardbreak', 'br', 0); + } else { + state.pending = state.pending.slice(0, -1); + state.push('softbreak', 'br', 0); + } + } else { + state.push('softbreak', 'br', 0); + } + } + pos++; + + // skip heading spaces for next line + while (pos < max && isSpace(state.src.charCodeAt(pos))) { + pos++; + } + state.pos = pos; + return true; +} + +// Process escaped chars and hardbreaks + +const ESCAPED = []; +for (let i = 0; i < 256; i++) { + ESCAPED.push(0); +} +'\\!"#$%&\'()*+,./:;<=>?@[]^_`{|}~-'.split('').forEach(function (ch) { + ESCAPED[ch.charCodeAt(0)] = 1; +}); +function escape(state, silent) { + let pos = state.pos; + const max = state.posMax; + if (state.src.charCodeAt(pos) !== 0x5C /* \ */) return false; + pos++; + + // '\' at the end of the inline block + if (pos >= max) return false; + let ch1 = state.src.charCodeAt(pos); + if (ch1 === 0x0A) { + if (!silent) { + state.push('hardbreak', 'br', 0); + } + pos++; + // skip leading whitespaces from next line + while (pos < max) { + ch1 = state.src.charCodeAt(pos); + if (!isSpace(ch1)) break; + pos++; + } + state.pos = pos; + return true; + } + let escapedStr = state.src[pos]; + if (ch1 >= 0xD800 && ch1 <= 0xDBFF && pos + 1 < max) { + const ch2 = state.src.charCodeAt(pos + 1); + if (ch2 >= 0xDC00 && ch2 <= 0xDFFF) { + escapedStr += state.src[pos + 1]; + pos++; + } + } + const origStr = '\\' + escapedStr; + if (!silent) { + const token = state.push('text_special', '', 0); + if (ch1 < 256 && ESCAPED[ch1] !== 0) { + token.content = escapedStr; + } else { + token.content = origStr; + } + token.markup = origStr; + token.info = 'escape'; + } + state.pos = pos + 1; + return true; +} + +// Parse backticks + +function backtick(state, silent) { + let pos = state.pos; + const ch = state.src.charCodeAt(pos); + if (ch !== 0x60 /* ` */) { + return false; + } + const start = pos; + pos++; + const max = state.posMax; + + // scan marker length + while (pos < max && state.src.charCodeAt(pos) === 0x60 /* ` */) { + pos++; + } + const marker = state.src.slice(start, pos); + const openerLength = marker.length; + if (state.backticksScanned && (state.backticks[openerLength] || 0) <= start) { + if (!silent) state.pending += marker; + state.pos += openerLength; + return true; + } + let matchEnd = pos; + let matchStart; + + // Nothing found in the cache, scan until the end of the line (or until marker is found) + while ((matchStart = state.src.indexOf('`', matchEnd)) !== -1) { + matchEnd = matchStart + 1; + + // scan marker length + while (matchEnd < max && state.src.charCodeAt(matchEnd) === 0x60 /* ` */) { + matchEnd++; + } + const closerLength = matchEnd - matchStart; + if (closerLength === openerLength) { + // Found matching closer length. + if (!silent) { + const token = state.push('code_inline', 'code', 0); + token.markup = marker; + token.content = state.src.slice(pos, matchStart).replace(/\n/g, ' ').replace(/^ (.+) $/, '$1'); + } + state.pos = matchEnd; + return true; + } + + // Some different length found, put it in cache as upper limit of where closer can be found + state.backticks[closerLength] = matchStart; + } + + // Scanned through the end, didn't find anything + state.backticksScanned = true; + if (!silent) state.pending += marker; + state.pos += openerLength; + return true; +} + +// ~~strike through~~ +// + +// Insert each marker as a separate text token, and add it to delimiter list +// +function strikethrough_tokenize(state, silent) { + const start = state.pos; + const marker = state.src.charCodeAt(start); + if (silent) { + return false; + } + if (marker !== 0x7E /* ~ */) { + return false; + } + const scanned = state.scanDelims(state.pos, true); + let len = scanned.length; + const ch = String.fromCharCode(marker); + if (len < 2) { + return false; + } + let token; + if (len % 2) { + token = state.push('text', '', 0); + token.content = ch; + len--; + } + for (let i = 0; i < len; i += 2) { + token = state.push('text', '', 0); + token.content = ch + ch; + state.delimiters.push({ + marker, + length: 0, + // disable "rule of 3" length checks meant for emphasis + token: state.tokens.length - 1, + end: -1, + open: scanned.can_open, + close: scanned.can_close + }); + } + state.pos += scanned.length; + return true; +} +function postProcess$1(state, delimiters) { + let token; + const loneMarkers = []; + const max = delimiters.length; + for (let i = 0; i < max; i++) { + const startDelim = delimiters[i]; + if (startDelim.marker !== 0x7E /* ~ */) { + continue; + } + if (startDelim.end === -1) { + continue; + } + const endDelim = delimiters[startDelim.end]; + token = state.tokens[startDelim.token]; + token.type = 's_open'; + token.tag = 's'; + token.nesting = 1; + token.markup = '~~'; + token.content = ''; + token = state.tokens[endDelim.token]; + token.type = 's_close'; + token.tag = 's'; + token.nesting = -1; + token.markup = '~~'; + token.content = ''; + if (state.tokens[endDelim.token - 1].type === 'text' && state.tokens[endDelim.token - 1].content === '~') { + loneMarkers.push(endDelim.token - 1); + } + } + + // If a marker sequence has an odd number of characters, it's splitted + // like this: `~~~~~` -> `~` + `~~` + `~~`, leaving one marker at the + // start of the sequence. + // + // So, we have to move all those markers after subsequent s_close tags. + // + while (loneMarkers.length) { + const i = loneMarkers.pop(); + let j = i + 1; + while (j < state.tokens.length && state.tokens[j].type === 's_close') { + j++; + } + j--; + if (i !== j) { + token = state.tokens[j]; + state.tokens[j] = state.tokens[i]; + state.tokens[i] = token; + } + } +} + +// Walk through delimiter list and replace text tokens with tags +// +function strikethrough_postProcess(state) { + const tokens_meta = state.tokens_meta; + const max = state.tokens_meta.length; + postProcess$1(state, state.delimiters); + for (let curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + postProcess$1(state, tokens_meta[curr].delimiters); + } + } +} +var r_strikethrough = { + tokenize: strikethrough_tokenize, + postProcess: strikethrough_postProcess +}; + +// Process *this* and _that_ +// + +// Insert each marker as a separate text token, and add it to delimiter list +// +function emphasis_tokenize(state, silent) { + const start = state.pos; + const marker = state.src.charCodeAt(start); + if (silent) { + return false; + } + if (marker !== 0x5F /* _ */ && marker !== 0x2A /* * */) { + return false; + } + const scanned = state.scanDelims(state.pos, marker === 0x2A); + for (let i = 0; i < scanned.length; i++) { + const token = state.push('text', '', 0); + token.content = String.fromCharCode(marker); + state.delimiters.push({ + // Char code of the starting marker (number). + // + marker, + // Total length of these series of delimiters. + // + length: scanned.length, + // A position of the token this delimiter corresponds to. + // + token: state.tokens.length - 1, + // If this delimiter is matched as a valid opener, `end` will be + // equal to its position, otherwise it's `-1`. + // + end: -1, + // Boolean flags that determine if this delimiter could open or close + // an emphasis. + // + open: scanned.can_open, + close: scanned.can_close + }); + } + state.pos += scanned.length; + return true; +} +function postProcess(state, delimiters) { + const max = delimiters.length; + for (let i = max - 1; i >= 0; i--) { + const startDelim = delimiters[i]; + if (startDelim.marker !== 0x5F /* _ */ && startDelim.marker !== 0x2A /* * */) { + continue; + } + + // Process only opening markers + if (startDelim.end === -1) { + continue; + } + const endDelim = delimiters[startDelim.end]; + + // If the previous delimiter has the same marker and is adjacent to this one, + // merge those into one strong delimiter. + // + // `whatever` -> `whatever` + // + const isStrong = i > 0 && delimiters[i - 1].end === startDelim.end + 1 && + // check that first two markers match and adjacent + delimiters[i - 1].marker === startDelim.marker && delimiters[i - 1].token === startDelim.token - 1 && + // check that last two markers are adjacent (we can safely assume they match) + delimiters[startDelim.end + 1].token === endDelim.token + 1; + const ch = String.fromCharCode(startDelim.marker); + const token_o = state.tokens[startDelim.token]; + token_o.type = isStrong ? 'strong_open' : 'em_open'; + token_o.tag = isStrong ? 'strong' : 'em'; + token_o.nesting = 1; + token_o.markup = isStrong ? ch + ch : ch; + token_o.content = ''; + const token_c = state.tokens[endDelim.token]; + token_c.type = isStrong ? 'strong_close' : 'em_close'; + token_c.tag = isStrong ? 'strong' : 'em'; + token_c.nesting = -1; + token_c.markup = isStrong ? ch + ch : ch; + token_c.content = ''; + if (isStrong) { + state.tokens[delimiters[i - 1].token].content = ''; + state.tokens[delimiters[startDelim.end + 1].token].content = ''; + i--; + } + } +} + +// Walk through delimiter list and replace text tokens with tags +// +function emphasis_post_process(state) { + const tokens_meta = state.tokens_meta; + const max = state.tokens_meta.length; + postProcess(state, state.delimiters); + for (let curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + postProcess(state, tokens_meta[curr].delimiters); + } + } +} +var r_emphasis = { + tokenize: emphasis_tokenize, + postProcess: emphasis_post_process +}; + +// Process [link]( "stuff") + +function link(state, silent) { + let code, label, res, ref; + let href = ''; + let title = ''; + let start = state.pos; + let parseReference = true; + if (state.src.charCodeAt(state.pos) !== 0x5B /* [ */) { + return false; + } + const oldPos = state.pos; + const max = state.posMax; + const labelStart = state.pos + 1; + const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos, true); + + // parser failed to find ']', so it's not a valid link + if (labelEnd < 0) { + return false; + } + let pos = labelEnd + 1; + if (pos < max && state.src.charCodeAt(pos) === 0x28 /* ( */) { + // + // Inline link + // + + // might have found a valid shortcut link, disable reference parsing + parseReference = false; + + // [link]( "title" ) + // ^^ skipping these spaces + pos++; + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 0x0A) { + break; + } + } + if (pos >= max) { + return false; + } + + // [link]( "title" ) + // ^^^^^^ parsing link destination + start = pos; + res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax); + if (res.ok) { + href = state.md.normalizeLink(res.str); + if (state.md.validateLink(href)) { + pos = res.pos; + } else { + href = ''; + } + + // [link]( "title" ) + // ^^ skipping these spaces + start = pos; + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 0x0A) { + break; + } + } + + // [link]( "title" ) + // ^^^^^^^ parsing link title + res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax); + if (pos < max && start !== pos && res.ok) { + title = res.str; + pos = res.pos; + + // [link]( "title" ) + // ^^ skipping these spaces + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 0x0A) { + break; + } + } + } + } + if (pos >= max || state.src.charCodeAt(pos) !== 0x29 /* ) */) { + // parsing a valid shortcut link failed, fallback to reference + parseReference = true; + } + pos++; + } + if (parseReference) { + // + // Link reference + // + if (typeof state.env.references === 'undefined') { + return false; + } + if (pos < max && state.src.charCodeAt(pos) === 0x5B /* [ */) { + start = pos + 1; + pos = state.md.helpers.parseLinkLabel(state, pos); + if (pos >= 0) { + label = state.src.slice(start, pos++); + } else { + pos = labelEnd + 1; + } + } else { + pos = labelEnd + 1; + } + + // covers label === '' and label === undefined + // (collapsed reference link and shortcut reference link respectively) + if (!label) { + label = state.src.slice(labelStart, labelEnd); + } + ref = state.env.references[normalizeReference(label)]; + if (!ref) { + state.pos = oldPos; + return false; + } + href = ref.href; + title = ref.title; + } + + // + // We found the end of the link, and know for a fact it's a valid link; + // so all that's left to do is to call tokenizer. + // + if (!silent) { + state.pos = labelStart; + state.posMax = labelEnd; + const token_o = state.push('link_open', 'a', 1); + const attrs = [['href', href]]; + token_o.attrs = attrs; + if (title) { + attrs.push(['title', title]); + } + state.linkLevel++; + state.md.inline.tokenize(state); + state.linkLevel--; + state.push('link_close', 'a', -1); + } + state.pos = pos; + state.posMax = max; + return true; +} + +// Process ![image]( "title") + +function image(state, silent) { + let code, content, label, pos, ref, res, title, start; + let href = ''; + const oldPos = state.pos; + const max = state.posMax; + if (state.src.charCodeAt(state.pos) !== 0x21 /* ! */) { + return false; + } + if (state.src.charCodeAt(state.pos + 1) !== 0x5B /* [ */) { + return false; + } + const labelStart = state.pos + 2; + const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos + 1, false); + + // parser failed to find ']', so it's not a valid link + if (labelEnd < 0) { + return false; + } + pos = labelEnd + 1; + if (pos < max && state.src.charCodeAt(pos) === 0x28 /* ( */) { + // + // Inline link + // + + // [link]( "title" ) + // ^^ skipping these spaces + pos++; + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 0x0A) { + break; + } + } + if (pos >= max) { + return false; + } + + // [link]( "title" ) + // ^^^^^^ parsing link destination + start = pos; + res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax); + if (res.ok) { + href = state.md.normalizeLink(res.str); + if (state.md.validateLink(href)) { + pos = res.pos; + } else { + href = ''; + } + } + + // [link]( "title" ) + // ^^ skipping these spaces + start = pos; + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 0x0A) { + break; + } + } + + // [link]( "title" ) + // ^^^^^^^ parsing link title + res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax); + if (pos < max && start !== pos && res.ok) { + title = res.str; + pos = res.pos; + + // [link]( "title" ) + // ^^ skipping these spaces + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 0x0A) { + break; + } + } + } else { + title = ''; + } + if (pos >= max || state.src.charCodeAt(pos) !== 0x29 /* ) */) { + state.pos = oldPos; + return false; + } + pos++; + } else { + // + // Link reference + // + if (typeof state.env.references === 'undefined') { + return false; + } + if (pos < max && state.src.charCodeAt(pos) === 0x5B /* [ */) { + start = pos + 1; + pos = state.md.helpers.parseLinkLabel(state, pos); + if (pos >= 0) { + label = state.src.slice(start, pos++); + } else { + pos = labelEnd + 1; + } + } else { + pos = labelEnd + 1; + } + + // covers label === '' and label === undefined + // (collapsed reference link and shortcut reference link respectively) + if (!label) { + label = state.src.slice(labelStart, labelEnd); + } + ref = state.env.references[normalizeReference(label)]; + if (!ref) { + state.pos = oldPos; + return false; + } + href = ref.href; + title = ref.title; + } + + // + // We found the end of the link, and know for a fact it's a valid link; + // so all that's left to do is to call tokenizer. + // + if (!silent) { + content = state.src.slice(labelStart, labelEnd); + const tokens = []; + state.md.inline.parse(content, state.md, state.env, tokens); + const token = state.push('image', 'img', 0); + const attrs = [['src', href], ['alt', '']]; + token.attrs = attrs; + token.children = tokens; + token.content = content; + if (title) { + attrs.push(['title', title]); + } + } + state.pos = pos; + state.posMax = max; + return true; +} + +// Process autolinks '' + +/* eslint max-len:0 */ +const EMAIL_RE = /^([a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*)$/; +/* eslint-disable-next-line no-control-regex */ +const AUTOLINK_RE = /^([a-zA-Z][a-zA-Z0-9+.-]{1,31}):([^<>\x00-\x20]*)$/; +function autolink(state, silent) { + let pos = state.pos; + if (state.src.charCodeAt(pos) !== 0x3C /* < */) { + return false; + } + const start = state.pos; + const max = state.posMax; + for (;;) { + if (++pos >= max) return false; + const ch = state.src.charCodeAt(pos); + if (ch === 0x3C /* < */) return false; + if (ch === 0x3E /* > */) break; + } + const url = state.src.slice(start + 1, pos); + if (AUTOLINK_RE.test(url)) { + const fullUrl = state.md.normalizeLink(url); + if (!state.md.validateLink(fullUrl)) { + return false; + } + if (!silent) { + const token_o = state.push('link_open', 'a', 1); + token_o.attrs = [['href', fullUrl]]; + token_o.markup = 'autolink'; + token_o.info = 'auto'; + const token_t = state.push('text', '', 0); + token_t.content = state.md.normalizeLinkText(url); + const token_c = state.push('link_close', 'a', -1); + token_c.markup = 'autolink'; + token_c.info = 'auto'; + } + state.pos += url.length + 2; + return true; + } + if (EMAIL_RE.test(url)) { + const fullUrl = state.md.normalizeLink('mailto:' + url); + if (!state.md.validateLink(fullUrl)) { + return false; + } + if (!silent) { + const token_o = state.push('link_open', 'a', 1); + token_o.attrs = [['href', fullUrl]]; + token_o.markup = 'autolink'; + token_o.info = 'auto'; + const token_t = state.push('text', '', 0); + token_t.content = state.md.normalizeLinkText(url); + const token_c = state.push('link_close', 'a', -1); + token_c.markup = 'autolink'; + token_c.info = 'auto'; + } + state.pos += url.length + 2; + return true; + } + return false; +} + +// Process html tags + +function isLinkOpen(str) { + return /^\s]/i.test(str); +} +function isLinkClose(str) { + return /^<\/a\s*>/i.test(str); +} +function isLetter(ch) { + /* eslint no-bitwise:0 */ + const lc = ch | 0x20; // to lower case + return lc >= 0x61 /* a */ && lc <= 0x7a /* z */; +} +function html_inline(state, silent) { + if (!state.md.options.html) { + return false; + } + + // Check start + const max = state.posMax; + const pos = state.pos; + if (state.src.charCodeAt(pos) !== 0x3C /* < */ || pos + 2 >= max) { + return false; + } + + // Quick fail on second char + const ch = state.src.charCodeAt(pos + 1); + if (ch !== 0x21 /* ! */ && ch !== 0x3F /* ? */ && ch !== 0x2F /* / */ && !isLetter(ch)) { + return false; + } + const match = state.src.slice(pos).match(HTML_TAG_RE); + if (!match) { + return false; + } + if (!silent) { + const token = state.push('html_inline', '', 0); + token.content = match[0]; + if (isLinkOpen(token.content)) state.linkLevel++; + if (isLinkClose(token.content)) state.linkLevel--; + } + state.pos += match[0].length; + return true; +} + +// Process html entity - {, ¯, ", ... + +const DIGITAL_RE = /^&#((?:x[a-f0-9]{1,6}|[0-9]{1,7}));/i; +const NAMED_RE = /^&([a-z][a-z0-9]{1,31});/i; +function entity(state, silent) { + const pos = state.pos; + const max = state.posMax; + if (state.src.charCodeAt(pos) !== 0x26 /* & */) return false; + if (pos + 1 >= max) return false; + const ch = state.src.charCodeAt(pos + 1); + if (ch === 0x23 /* # */) { + const match = state.src.slice(pos).match(DIGITAL_RE); + if (match) { + if (!silent) { + const code = match[1][0].toLowerCase() === 'x' ? parseInt(match[1].slice(1), 16) : parseInt(match[1], 10); + const token = state.push('text_special', '', 0); + token.content = isValidEntityCode(code) ? fromCodePoint(code) : fromCodePoint(0xFFFD); + token.markup = match[0]; + token.info = 'entity'; + } + state.pos += match[0].length; + return true; + } + } else { + const match = state.src.slice(pos).match(NAMED_RE); + if (match) { + const decoded = entities.decodeHTML(match[0]); + if (decoded !== match[0]) { + if (!silent) { + const token = state.push('text_special', '', 0); + token.content = decoded; + token.markup = match[0]; + token.info = 'entity'; + } + state.pos += match[0].length; + return true; + } + } + } + return false; +} + +// For each opening emphasis-like marker find a matching closing one +// + +function processDelimiters(delimiters) { + const openersBottom = {}; + const max = delimiters.length; + if (!max) return; + + // headerIdx is the first delimiter of the current (where closer is) delimiter run + let headerIdx = 0; + let lastTokenIdx = -2; // needs any value lower than -1 + const jumps = []; + for (let closerIdx = 0; closerIdx < max; closerIdx++) { + const closer = delimiters[closerIdx]; + jumps.push(0); + + // markers belong to same delimiter run if: + // - they have adjacent tokens + // - AND markers are the same + // + if (delimiters[headerIdx].marker !== closer.marker || lastTokenIdx !== closer.token - 1) { + headerIdx = closerIdx; + } + lastTokenIdx = closer.token; + + // Length is only used for emphasis-specific "rule of 3", + // if it's not defined (in strikethrough or 3rd party plugins), + // we can default it to 0 to disable those checks. + // + closer.length = closer.length || 0; + if (!closer.close) continue; + + // Previously calculated lower bounds (previous fails) + // for each marker, each delimiter length modulo 3, + // and for whether this closer can be an opener; + // https://github.com/commonmark/cmark/commit/34250e12ccebdc6372b8b49c44fab57c72443460 + /* eslint-disable-next-line no-prototype-builtins */ + if (!openersBottom.hasOwnProperty(closer.marker)) { + openersBottom[closer.marker] = [-1, -1, -1, -1, -1, -1]; + } + const minOpenerIdx = openersBottom[closer.marker][(closer.open ? 3 : 0) + closer.length % 3]; + let openerIdx = headerIdx - jumps[headerIdx] - 1; + let newMinOpenerIdx = openerIdx; + for (; openerIdx > minOpenerIdx; openerIdx -= jumps[openerIdx] + 1) { + const opener = delimiters[openerIdx]; + if (opener.marker !== closer.marker) continue; + if (opener.open && opener.end < 0) { + let isOddMatch = false; + + // from spec: + // + // If one of the delimiters can both open and close emphasis, then the + // sum of the lengths of the delimiter runs containing the opening and + // closing delimiters must not be a multiple of 3 unless both lengths + // are multiples of 3. + // + if (opener.close || closer.open) { + if ((opener.length + closer.length) % 3 === 0) { + if (opener.length % 3 !== 0 || closer.length % 3 !== 0) { + isOddMatch = true; + } + } + } + if (!isOddMatch) { + // If previous delimiter cannot be an opener, we can safely skip + // the entire sequence in future checks. This is required to make + // sure algorithm has linear complexity (see *_*_*_*_*_... case). + // + const lastJump = openerIdx > 0 && !delimiters[openerIdx - 1].open ? jumps[openerIdx - 1] + 1 : 0; + jumps[closerIdx] = closerIdx - openerIdx + lastJump; + jumps[openerIdx] = lastJump; + closer.open = false; + opener.end = closerIdx; + opener.close = false; + newMinOpenerIdx = -1; + // treat next token as start of run, + // it optimizes skips in **<...>**a**<...>** pathological case + lastTokenIdx = -2; + break; + } + } + } + if (newMinOpenerIdx !== -1) { + // If match for this delimiter run failed, we want to set lower bound for + // future lookups. This is required to make sure algorithm has linear + // complexity. + // + // See details here: + // https://github.com/commonmark/cmark/issues/178#issuecomment-270417442 + // + openersBottom[closer.marker][(closer.open ? 3 : 0) + (closer.length || 0) % 3] = newMinOpenerIdx; + } + } +} +function link_pairs(state) { + const tokens_meta = state.tokens_meta; + const max = state.tokens_meta.length; + processDelimiters(state.delimiters); + for (let curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + processDelimiters(tokens_meta[curr].delimiters); + } + } +} + +// Clean up tokens after emphasis and strikethrough postprocessing: +// merge adjacent text nodes into one and re-calculate all token levels +// +// This is necessary because initially emphasis delimiter markers (*, _, ~) +// are treated as their own separate text tokens. Then emphasis rule either +// leaves them as text (needed to merge with adjacent text) or turns them +// into opening/closing tags (which messes up levels inside). +// + +function fragments_join(state) { + let curr, last; + let level = 0; + const tokens = state.tokens; + const max = state.tokens.length; + for (curr = last = 0; curr < max; curr++) { + // re-calculate levels after emphasis/strikethrough turns some text nodes + // into opening/closing tags + if (tokens[curr].nesting < 0) level--; // closing tag + tokens[curr].level = level; + if (tokens[curr].nesting > 0) level++; // opening tag + + if (tokens[curr].type === 'text' && curr + 1 < max && tokens[curr + 1].type === 'text') { + // collapse two adjacent text nodes + tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content; + } else { + if (curr !== last) { + tokens[last] = tokens[curr]; + } + last++; + } + } + if (curr !== last) { + tokens.length = last; + } +} + +/** internal + * class ParserInline + * + * Tokenizes paragraph content. + **/ + + +// Parser rules + +const _rules = [['text', text], ['linkify', linkify], ['newline', newline], ['escape', escape], ['backticks', backtick], ['strikethrough', r_strikethrough.tokenize], ['emphasis', r_emphasis.tokenize], ['link', link], ['image', image], ['autolink', autolink], ['html_inline', html_inline], ['entity', entity]]; + +// `rule2` ruleset was created specifically for emphasis/strikethrough +// post-processing and may be changed in the future. +// +// Don't use this for anything except pairs (plugins working with `balance_pairs`). +// +const _rules2 = [['balance_pairs', link_pairs], ['strikethrough', r_strikethrough.postProcess], ['emphasis', r_emphasis.postProcess], +// rules for pairs separate '**' into its own text tokens, which may be left unused, +// rule below merges unused segments back with the rest of the text +['fragments_join', fragments_join]]; + +/** + * new ParserInline() + **/ +function ParserInline() { + /** + * ParserInline#ruler -> Ruler + * + * [[Ruler]] instance. Keep configuration of inline rules. + **/ + this.ruler = new Ruler(); + for (let i = 0; i < _rules.length; i++) { + this.ruler.push(_rules[i][0], _rules[i][1]); + } + + /** + * ParserInline#ruler2 -> Ruler + * + * [[Ruler]] instance. Second ruler used for post-processing + * (e.g. in emphasis-like rules). + **/ + this.ruler2 = new Ruler(); + for (let i = 0; i < _rules2.length; i++) { + this.ruler2.push(_rules2[i][0], _rules2[i][1]); + } +} + +// Skip single token by running all rules in validation mode; +// returns `true` if any rule reported success +// +ParserInline.prototype.skipToken = function (state) { + const pos = state.pos; + const rules = this.ruler.getRules(''); + const len = rules.length; + const maxNesting = state.md.options.maxNesting; + const cache = state.cache; + if (typeof cache[pos] !== 'undefined') { + state.pos = cache[pos]; + return; + } + let ok = false; + if (state.level < maxNesting) { + for (let i = 0; i < len; i++) { + // Increment state.level and decrement it later to limit recursion. + // It's harmless to do here, because no tokens are created. But ideally, + // we'd need a separate private state variable for this purpose. + // + state.level++; + ok = rules[i](state, true); + state.level--; + if (ok) { + if (pos >= state.pos) { + throw new Error("inline rule didn't increment state.pos"); + } + break; + } + } + } else { + // Too much nesting, just skip until the end of the paragraph. + // + // NOTE: this will cause links to behave incorrectly in the following case, + // when an amount of `[` is exactly equal to `maxNesting + 1`: + // + // [[[[[[[[[[[[[[[[[[[[[foo]() + // + // TODO: remove this workaround when CM standard will allow nested links + // (we can replace it by preventing links from being parsed in + // validation mode) + // + state.pos = state.posMax; + } + if (!ok) { + state.pos++; + } + cache[pos] = state.pos; +}; + +// Generate tokens for input range +// +ParserInline.prototype.tokenize = function (state) { + const rules = this.ruler.getRules(''); + const len = rules.length; + const end = state.posMax; + const maxNesting = state.md.options.maxNesting; + while (state.pos < end) { + // Try all possible rules. + // On success, rule should: + // + // - update `state.pos` + // - update `state.tokens` + // - return true + const prevPos = state.pos; + let ok = false; + if (state.level < maxNesting) { + for (let i = 0; i < len; i++) { + ok = rules[i](state, false); + if (ok) { + if (prevPos >= state.pos) { + throw new Error("inline rule didn't increment state.pos"); + } + break; + } + } + } + if (ok) { + if (state.pos >= end) { + break; + } + continue; + } + state.pending += state.src[state.pos++]; + } + if (state.pending) { + state.pushPending(); + } +}; + +/** + * ParserInline.parse(str, md, env, outTokens) + * + * Process input string and push inline tokens into `outTokens` + **/ +ParserInline.prototype.parse = function (str, md, env, outTokens) { + const state = new this.State(str, md, env, outTokens); + this.tokenize(state); + const rules = this.ruler2.getRules(''); + const len = rules.length; + for (let i = 0; i < len; i++) { + rules[i](state); + } +}; +ParserInline.prototype.State = StateInline; + +// markdown-it default options + +var cfg_default = { + options: { + // Enable HTML tags in source + html: false, + // Use '/' to close single tags (
    ) + xhtmlOut: false, + // Convert '\n' in paragraphs into
    + breaks: false, + // CSS language prefix for fenced blocks + langPrefix: 'language-', + // autoconvert URL-like texts to links + linkify: false, + // Enable some language-neutral replacements + quotes beautification + typographer: false, + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: '\u201c\u201d\u2018\u2019', + /* “”‘’ */ + + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externaly. + // If result starts with ) + xhtmlOut: false, + // Convert '\n' in paragraphs into
    + breaks: false, + // CSS language prefix for fenced blocks + langPrefix: 'language-', + // autoconvert URL-like texts to links + linkify: false, + // Enable some language-neutral replacements + quotes beautification + typographer: false, + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: '\u201c\u201d\u2018\u2019', + /* “”‘’ */ + + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externaly. + // If result starts with ) + xhtmlOut: true, + // Convert '\n' in paragraphs into
    + breaks: false, + // CSS language prefix for fenced blocks + langPrefix: 'language-', + // autoconvert URL-like texts to links + linkify: false, + // Enable some language-neutral replacements + quotes beautification + typographer: false, + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: '\u201c\u201d\u2018\u2019', + /* “”‘’ */ + + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externaly. + // If result starts with = 0) { + try { + parsed.hostname = punycode.toASCII(parsed.hostname); + } catch (er) {/**/} + } + } + return mdurl__namespace.encode(mdurl__namespace.format(parsed)); +} +function normalizeLinkText(url) { + const parsed = mdurl__namespace.parse(url, true); + if (parsed.hostname) { + // Encode hostnames in urls like: + // `http://host/`, `https://host/`, `mailto:user@host`, `//host/` + // + // We don't encode unknown schemas, because it's likely that we encode + // something we shouldn't (e.g. `skype:name` treated as `skype:host`) + // + if (!parsed.protocol || RECODE_HOSTNAME_FOR.indexOf(parsed.protocol) >= 0) { + try { + parsed.hostname = punycode.toUnicode(parsed.hostname); + } catch (er) {/**/} + } + } + + // add '%' to exclude list because of https://github.com/markdown-it/markdown-it/issues/720 + return mdurl__namespace.decode(mdurl__namespace.format(parsed), mdurl__namespace.decode.defaultChars + '%'); +} + +/** + * class MarkdownIt + * + * Main parser/renderer class. + * + * ##### Usage + * + * ```javascript + * // node.js, "classic" way: + * var MarkdownIt = require('markdown-it'), + * md = new MarkdownIt(); + * var result = md.render('# markdown-it rulezz!'); + * + * // node.js, the same, but with sugar: + * var md = require('markdown-it')(); + * var result = md.render('# markdown-it rulezz!'); + * + * // browser without AMD, added to "window" on script load + * // Note, there are no dash. + * var md = window.markdownit(); + * var result = md.render('# markdown-it rulezz!'); + * ``` + * + * Single line rendering, without paragraph wrap: + * + * ```javascript + * var md = require('markdown-it')(); + * var result = md.renderInline('__markdown-it__ rulezz!'); + * ``` + **/ + +/** + * new MarkdownIt([presetName, options]) + * - presetName (String): optional, `commonmark` / `zero` + * - options (Object) + * + * Creates parser instanse with given config. Can be called without `new`. + * + * ##### presetName + * + * MarkdownIt provides named presets as a convenience to quickly + * enable/disable active syntax rules and options for common use cases. + * + * - ["commonmark"](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/commonmark.mjs) - + * configures parser to strict [CommonMark](http://commonmark.org/) mode. + * - [default](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/default.mjs) - + * similar to GFM, used when no preset name given. Enables all available rules, + * but still without html, typographer & autolinker. + * - ["zero"](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/zero.mjs) - + * all rules disabled. Useful to quickly setup your config via `.enable()`. + * For example, when you need only `bold` and `italic` markup and nothing else. + * + * ##### options: + * + * - __html__ - `false`. Set `true` to enable HTML tags in source. Be careful! + * That's not safe! You may need external sanitizer to protect output from XSS. + * It's better to extend features via plugins, instead of enabling HTML. + * - __xhtmlOut__ - `false`. Set `true` to add '/' when closing single tags + * (`
    `). This is needed only for full CommonMark compatibility. In real + * world you will need HTML output. + * - __breaks__ - `false`. Set `true` to convert `\n` in paragraphs into `
    `. + * - __langPrefix__ - `language-`. CSS language class prefix for fenced blocks. + * Can be useful for external highlighters. + * - __linkify__ - `false`. Set `true` to autoconvert URL-like text to links. + * - __typographer__ - `false`. Set `true` to enable [some language-neutral + * replacement](https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/replacements.mjs) + + * quotes beautification (smartquotes). + * - __quotes__ - `“”‘’`, String or Array. Double + single quotes replacement + * pairs, when typographer enabled and smartquotes on. For example, you can + * use `'«»„“'` for Russian, `'„“‚‘'` for German, and + * `['«\xA0', '\xA0»', '‹\xA0', '\xA0›']` for French (including nbsp). + * - __highlight__ - `null`. Highlighter function for fenced code blocks. + * Highlighter `function (str, lang)` should return escaped HTML. It can also + * return empty string if the source was not changed and should be escaped + * externaly. If result starts with ` or ``): + * + * ```javascript + * var hljs = require('highlight.js') // https://highlightjs.org/ + * + * // Actual default values + * var md = require('markdown-it')({ + * highlight: function (str, lang) { + * if (lang && hljs.getLanguage(lang)) { + * try { + * return '
    ' +
    + *                hljs.highlight(str, { language: lang, ignoreIllegals: true }).value +
    + *                '
    '; + * } catch (__) {} + * } + * + * return '
    ' + md.utils.escapeHtml(str) + '
    '; + * } + * }); + * ``` + * + **/ +function MarkdownIt(presetName, options) { + if (!(this instanceof MarkdownIt)) { + return new MarkdownIt(presetName, options); + } + if (!options) { + if (!isString(presetName)) { + options = presetName || {}; + presetName = 'default'; + } + } + + /** + * MarkdownIt#inline -> ParserInline + * + * Instance of [[ParserInline]]. You may need it to add new rules when + * writing plugins. For simple rules control use [[MarkdownIt.disable]] and + * [[MarkdownIt.enable]]. + **/ + this.inline = new ParserInline(); + + /** + * MarkdownIt#block -> ParserBlock + * + * Instance of [[ParserBlock]]. You may need it to add new rules when + * writing plugins. For simple rules control use [[MarkdownIt.disable]] and + * [[MarkdownIt.enable]]. + **/ + this.block = new ParserBlock(); + + /** + * MarkdownIt#core -> Core + * + * Instance of [[Core]] chain executor. You may need it to add new rules when + * writing plugins. For simple rules control use [[MarkdownIt.disable]] and + * [[MarkdownIt.enable]]. + **/ + this.core = new Core(); + + /** + * MarkdownIt#renderer -> Renderer + * + * Instance of [[Renderer]]. Use it to modify output look. Or to add rendering + * rules for new token types, generated by plugins. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * function myToken(tokens, idx, options, env, self) { + * //... + * return result; + * }; + * + * md.renderer.rules['my_token'] = myToken + * ``` + * + * See [[Renderer]] docs and [source code](https://github.com/markdown-it/markdown-it/blob/master/lib/renderer.mjs). + **/ + this.renderer = new Renderer(); + + /** + * MarkdownIt#linkify -> LinkifyIt + * + * [linkify-it](https://github.com/markdown-it/linkify-it) instance. + * Used by [linkify](https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/linkify.mjs) + * rule. + **/ + this.linkify = new LinkifyIt(); + + /** + * MarkdownIt#validateLink(url) -> Boolean + * + * Link validation function. CommonMark allows too much in links. By default + * we disable `javascript:`, `vbscript:`, `file:` schemas, and almost all `data:...` schemas + * except some embedded image types. + * + * You can change this behaviour: + * + * ```javascript + * var md = require('markdown-it')(); + * // enable everything + * md.validateLink = function () { return true; } + * ``` + **/ + this.validateLink = validateLink; + + /** + * MarkdownIt#normalizeLink(url) -> String + * + * Function used to encode link url to a machine-readable format, + * which includes url-encoding, punycode, etc. + **/ + this.normalizeLink = normalizeLink; + + /** + * MarkdownIt#normalizeLinkText(url) -> String + * + * Function used to decode link url to a human-readable format` + **/ + this.normalizeLinkText = normalizeLinkText; + + // Expose utils & helpers for easy acces from plugins + + /** + * MarkdownIt#utils -> utils + * + * Assorted utility functions, useful to write plugins. See details + * [here](https://github.com/markdown-it/markdown-it/blob/master/lib/common/utils.mjs). + **/ + this.utils = utils; + + /** + * MarkdownIt#helpers -> helpers + * + * Link components parser functions, useful to write plugins. See details + * [here](https://github.com/markdown-it/markdown-it/blob/master/lib/helpers). + **/ + this.helpers = assign({}, helpers); + this.options = {}; + this.configure(presetName); + if (options) { + this.set(options); + } +} + +/** chainable + * MarkdownIt.set(options) + * + * Set parser options (in the same format as in constructor). Probably, you + * will never need it, but you can change options after constructor call. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')() + * .set({ html: true, breaks: true }) + * .set({ typographer, true }); + * ``` + * + * __Note:__ To achieve the best possible performance, don't modify a + * `markdown-it` instance options on the fly. If you need multiple configurations + * it's best to create multiple instances and initialize each with separate + * config. + **/ +MarkdownIt.prototype.set = function (options) { + assign(this.options, options); + return this; +}; + +/** chainable, internal + * MarkdownIt.configure(presets) + * + * Batch load of all options and compenent settings. This is internal method, + * and you probably will not need it. But if you will - see available presets + * and data structure [here](https://github.com/markdown-it/markdown-it/tree/master/lib/presets) + * + * We strongly recommend to use presets instead of direct config loads. That + * will give better compatibility with next versions. + **/ +MarkdownIt.prototype.configure = function (presets) { + const self = this; + if (isString(presets)) { + const presetName = presets; + presets = config[presetName]; + if (!presets) { + throw new Error('Wrong `markdown-it` preset "' + presetName + '", check name'); + } + } + if (!presets) { + throw new Error('Wrong `markdown-it` preset, can\'t be empty'); + } + if (presets.options) { + self.set(presets.options); + } + if (presets.components) { + Object.keys(presets.components).forEach(function (name) { + if (presets.components[name].rules) { + self[name].ruler.enableOnly(presets.components[name].rules); + } + if (presets.components[name].rules2) { + self[name].ruler2.enableOnly(presets.components[name].rules2); + } + }); + } + return this; +}; + +/** chainable + * MarkdownIt.enable(list, ignoreInvalid) + * - list (String|Array): rule name or list of rule names to enable + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Enable list or rules. It will automatically find appropriate components, + * containing rules with given names. If rule not found, and `ignoreInvalid` + * not set - throws exception. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')() + * .enable(['sub', 'sup']) + * .disable('smartquotes'); + * ``` + **/ +MarkdownIt.prototype.enable = function (list, ignoreInvalid) { + let result = []; + if (!Array.isArray(list)) { + list = [list]; + } + ['core', 'block', 'inline'].forEach(function (chain) { + result = result.concat(this[chain].ruler.enable(list, true)); + }, this); + result = result.concat(this.inline.ruler2.enable(list, true)); + const missed = list.filter(function (name) { + return result.indexOf(name) < 0; + }); + if (missed.length && !ignoreInvalid) { + throw new Error('MarkdownIt. Failed to enable unknown rule(s): ' + missed); + } + return this; +}; + +/** chainable + * MarkdownIt.disable(list, ignoreInvalid) + * - list (String|Array): rule name or list of rule names to disable. + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * The same as [[MarkdownIt.enable]], but turn specified rules off. + **/ +MarkdownIt.prototype.disable = function (list, ignoreInvalid) { + let result = []; + if (!Array.isArray(list)) { + list = [list]; + } + ['core', 'block', 'inline'].forEach(function (chain) { + result = result.concat(this[chain].ruler.disable(list, true)); + }, this); + result = result.concat(this.inline.ruler2.disable(list, true)); + const missed = list.filter(function (name) { + return result.indexOf(name) < 0; + }); + if (missed.length && !ignoreInvalid) { + throw new Error('MarkdownIt. Failed to disable unknown rule(s): ' + missed); + } + return this; +}; + +/** chainable + * MarkdownIt.use(plugin, params) + * + * Load specified plugin with given params into current parser instance. + * It's just a sugar to call `plugin(md, params)` with curring. + * + * ##### Example + * + * ```javascript + * var iterator = require('markdown-it-for-inline'); + * var md = require('markdown-it')() + * .use(iterator, 'foo_replace', 'text', function (tokens, idx) { + * tokens[idx].content = tokens[idx].content.replace(/foo/g, 'bar'); + * }); + * ``` + **/ +MarkdownIt.prototype.use = function (plugin /*, params, ... */) { + const args = [this].concat(Array.prototype.slice.call(arguments, 1)); + plugin.apply(plugin, args); + return this; +}; + +/** internal + * MarkdownIt.parse(src, env) -> Array + * - src (String): source string + * - env (Object): environment sandbox + * + * Parse input string and return list of block tokens (special token type + * "inline" will contain list of inline tokens). You should not call this + * method directly, until you write custom renderer (for example, to produce + * AST). + * + * `env` is used to pass data between "distributed" rules and return additional + * metadata like reference info, needed for the renderer. It also can be used to + * inject data in specific cases. Usually, you will be ok to pass `{}`, + * and then pass updated object to renderer. + **/ +MarkdownIt.prototype.parse = function (src, env) { + if (typeof src !== 'string') { + throw new Error('Input data should be a String'); + } + const state = new this.core.State(src, this, env); + this.core.process(state); + return state.tokens; +}; + +/** + * MarkdownIt.render(src [, env]) -> String + * - src (String): source string + * - env (Object): environment sandbox + * + * Render markdown string into html. It does all magic for you :). + * + * `env` can be used to inject additional metadata (`{}` by default). + * But you will not need it with high probability. See also comment + * in [[MarkdownIt.parse]]. + **/ +MarkdownIt.prototype.render = function (src, env) { + env = env || {}; + return this.renderer.render(this.parse(src, env), this.options, env); +}; + +/** internal + * MarkdownIt.parseInline(src, env) -> Array + * - src (String): source string + * - env (Object): environment sandbox + * + * The same as [[MarkdownIt.parse]] but skip all block rules. It returns the + * block tokens list with the single `inline` element, containing parsed inline + * tokens in `children` property. Also updates `env` object. + **/ +MarkdownIt.prototype.parseInline = function (src, env) { + const state = new this.core.State(src, this, env); + state.inlineMode = true; + this.core.process(state); + return state.tokens; +}; + +/** + * MarkdownIt.renderInline(src [, env]) -> String + * - src (String): source string + * - env (Object): environment sandbox + * + * Similar to [[MarkdownIt.render]] but for single paragraph content. Result + * will NOT be wrapped into `

    ` tags. + **/ +MarkdownIt.prototype.renderInline = function (src, env) { + env = env || {}; + return this.renderer.render(this.parseInline(src, env), this.options, env); +}; + +module.exports = MarkdownIt; diff --git a/frontend/node_modules/markdown-it/dist/markdown-it.js b/frontend/node_modules/markdown-it/dist/markdown-it.js new file mode 100644 index 0000000..3a9d89c --- /dev/null +++ b/frontend/node_modules/markdown-it/dist/markdown-it.js @@ -0,0 +1,6963 @@ +/*! markdown-it 14.1.0 https://github.com/markdown-it/markdown-it @license MIT */ +(function(global, factory) { + typeof exports === "object" && typeof module !== "undefined" ? module.exports = factory() : typeof define === "function" && define.amd ? define(factory) : (global = typeof globalThis !== "undefined" ? globalThis : global || self, + global.markdownit = factory()); +})(this, (function() { + "use strict"; + /* eslint-disable no-bitwise */ const decodeCache = {}; + function getDecodeCache(exclude) { + let cache = decodeCache[exclude]; + if (cache) { + return cache; + } + cache = decodeCache[exclude] = []; + for (let i = 0; i < 128; i++) { + const ch = String.fromCharCode(i); + cache.push(ch); + } + for (let i = 0; i < exclude.length; i++) { + const ch = exclude.charCodeAt(i); + cache[ch] = "%" + ("0" + ch.toString(16).toUpperCase()).slice(-2); + } + return cache; + } + // Decode percent-encoded string. + + function decode$1(string, exclude) { + if (typeof exclude !== "string") { + exclude = decode$1.defaultChars; + } + const cache = getDecodeCache(exclude); + return string.replace(/(%[a-f0-9]{2})+/gi, (function(seq) { + let result = ""; + for (let i = 0, l = seq.length; i < l; i += 3) { + const b1 = parseInt(seq.slice(i + 1, i + 3), 16); + if (b1 < 128) { + result += cache[b1]; + continue; + } + if ((b1 & 224) === 192 && i + 3 < l) { + // 110xxxxx 10xxxxxx + const b2 = parseInt(seq.slice(i + 4, i + 6), 16); + if ((b2 & 192) === 128) { + const chr = b1 << 6 & 1984 | b2 & 63; + if (chr < 128) { + result += "\ufffd\ufffd"; + } else { + result += String.fromCharCode(chr); + } + i += 3; + continue; + } + } + if ((b1 & 240) === 224 && i + 6 < l) { + // 1110xxxx 10xxxxxx 10xxxxxx + const b2 = parseInt(seq.slice(i + 4, i + 6), 16); + const b3 = parseInt(seq.slice(i + 7, i + 9), 16); + if ((b2 & 192) === 128 && (b3 & 192) === 128) { + const chr = b1 << 12 & 61440 | b2 << 6 & 4032 | b3 & 63; + if (chr < 2048 || chr >= 55296 && chr <= 57343) { + result += "\ufffd\ufffd\ufffd"; + } else { + result += String.fromCharCode(chr); + } + i += 6; + continue; + } + } + if ((b1 & 248) === 240 && i + 9 < l) { + // 111110xx 10xxxxxx 10xxxxxx 10xxxxxx + const b2 = parseInt(seq.slice(i + 4, i + 6), 16); + const b3 = parseInt(seq.slice(i + 7, i + 9), 16); + const b4 = parseInt(seq.slice(i + 10, i + 12), 16); + if ((b2 & 192) === 128 && (b3 & 192) === 128 && (b4 & 192) === 128) { + let chr = b1 << 18 & 1835008 | b2 << 12 & 258048 | b3 << 6 & 4032 | b4 & 63; + if (chr < 65536 || chr > 1114111) { + result += "\ufffd\ufffd\ufffd\ufffd"; + } else { + chr -= 65536; + result += String.fromCharCode(55296 + (chr >> 10), 56320 + (chr & 1023)); + } + i += 9; + continue; + } + } + result += "\ufffd"; + } + return result; + })); + } + decode$1.defaultChars = ";/?:@&=+$,#"; + decode$1.componentChars = ""; + const encodeCache = {}; + // Create a lookup array where anything but characters in `chars` string + // and alphanumeric chars is percent-encoded. + + function getEncodeCache(exclude) { + let cache = encodeCache[exclude]; + if (cache) { + return cache; + } + cache = encodeCache[exclude] = []; + for (let i = 0; i < 128; i++) { + const ch = String.fromCharCode(i); + if (/^[0-9a-z]$/i.test(ch)) { + // always allow unencoded alphanumeric characters + cache.push(ch); + } else { + cache.push("%" + ("0" + i.toString(16).toUpperCase()).slice(-2)); + } + } + for (let i = 0; i < exclude.length; i++) { + cache[exclude.charCodeAt(i)] = exclude[i]; + } + return cache; + } + // Encode unsafe characters with percent-encoding, skipping already + // encoded sequences. + + // - string - string to encode + // - exclude - list of characters to ignore (in addition to a-zA-Z0-9) + // - keepEscaped - don't encode '%' in a correct escape sequence (default: true) + + function encode$1(string, exclude, keepEscaped) { + if (typeof exclude !== "string") { + // encode(string, keepEscaped) + keepEscaped = exclude; + exclude = encode$1.defaultChars; + } + if (typeof keepEscaped === "undefined") { + keepEscaped = true; + } + const cache = getEncodeCache(exclude); + let result = ""; + for (let i = 0, l = string.length; i < l; i++) { + const code = string.charCodeAt(i); + if (keepEscaped && code === 37 /* % */ && i + 2 < l) { + if (/^[0-9a-f]{2}$/i.test(string.slice(i + 1, i + 3))) { + result += string.slice(i, i + 3); + i += 2; + continue; + } + } + if (code < 128) { + result += cache[code]; + continue; + } + if (code >= 55296 && code <= 57343) { + if (code >= 55296 && code <= 56319 && i + 1 < l) { + const nextCode = string.charCodeAt(i + 1); + if (nextCode >= 56320 && nextCode <= 57343) { + result += encodeURIComponent(string[i] + string[i + 1]); + i++; + continue; + } + } + result += "%EF%BF%BD"; + continue; + } + result += encodeURIComponent(string[i]); + } + return result; + } + encode$1.defaultChars = ";/?:@&=+$,-_.!~*'()#"; + encode$1.componentChars = "-_.!~*'()"; + function format(url) { + let result = ""; + result += url.protocol || ""; + result += url.slashes ? "//" : ""; + result += url.auth ? url.auth + "@" : ""; + if (url.hostname && url.hostname.indexOf(":") !== -1) { + // ipv6 address + result += "[" + url.hostname + "]"; + } else { + result += url.hostname || ""; + } + result += url.port ? ":" + url.port : ""; + result += url.pathname || ""; + result += url.search || ""; + result += url.hash || ""; + return result; + } + // Copyright Joyent, Inc. and other Node contributors. + + // Permission is hereby granted, free of charge, to any person obtaining a + // copy of this software and associated documentation files (the + // "Software"), to deal in the Software without restriction, including + // without limitation the rights to use, copy, modify, merge, publish, + // distribute, sublicense, and/or sell copies of the Software, and to permit + // persons to whom the Software is furnished to do so, subject to the + // following conditions: + + // The above copyright notice and this permission notice shall be included + // in all copies or substantial portions of the Software. + + // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS + // OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN + // NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, + // DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR + // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE + // USE OR OTHER DEALINGS IN THE SOFTWARE. + + // Changes from joyent/node: + + // 1. No leading slash in paths, + // e.g. in `url.parse('http://foo?bar')` pathname is ``, not `/` + + // 2. Backslashes are not replaced with slashes, + // so `http:\\example.org\` is treated like a relative path + + // 3. Trailing colon is treated like a part of the path, + // i.e. in `http://example.org:foo` pathname is `:foo` + + // 4. Nothing is URL-encoded in the resulting object, + // (in joyent/node some chars in auth and paths are encoded) + + // 5. `url.parse()` does not have `parseQueryString` argument + + // 6. Removed extraneous result properties: `host`, `path`, `query`, etc., + // which can be constructed using other parts of the url. + + function Url() { + this.protocol = null; + this.slashes = null; + this.auth = null; + this.port = null; + this.hostname = null; + this.hash = null; + this.search = null; + this.pathname = null; + } + // Reference: RFC 3986, RFC 1808, RFC 2396 + // define these here so at least they only have to be + // compiled once on the first module load. + const protocolPattern = /^([a-z0-9.+-]+:)/i; + const portPattern = /:[0-9]*$/; + // Special case for a simple path URL + /* eslint-disable-next-line no-useless-escape */ const simplePathPattern = /^(\/\/?(?!\/)[^\?\s]*)(\?[^\s]*)?$/; + // RFC 2396: characters reserved for delimiting URLs. + // We actually just auto-escape these. + const delims = [ "<", ">", '"', "`", " ", "\r", "\n", "\t" ]; + // RFC 2396: characters not allowed for various reasons. + const unwise = [ "{", "}", "|", "\\", "^", "`" ].concat(delims); + // Allowed by RFCs, but cause of XSS attacks. Always escape these. + const autoEscape = [ "'" ].concat(unwise); + // Characters that are never ever allowed in a hostname. + // Note that any invalid chars are also handled, but these + // are the ones that are *expected* to be seen, so we fast-path + // them. + const nonHostChars = [ "%", "/", "?", ";", "#" ].concat(autoEscape); + const hostEndingChars = [ "/", "?", "#" ]; + const hostnameMaxLen = 255; + const hostnamePartPattern = /^[+a-z0-9A-Z_-]{0,63}$/; + const hostnamePartStart = /^([+a-z0-9A-Z_-]{0,63})(.*)$/; + // protocols that can allow "unsafe" and "unwise" chars. + // protocols that never have a hostname. + const hostlessProtocol = { + javascript: true, + "javascript:": true + }; + // protocols that always contain a // bit. + const slashedProtocol = { + http: true, + https: true, + ftp: true, + gopher: true, + file: true, + "http:": true, + "https:": true, + "ftp:": true, + "gopher:": true, + "file:": true + }; + function urlParse(url, slashesDenoteHost) { + if (url && url instanceof Url) return url; + const u = new Url; + u.parse(url, slashesDenoteHost); + return u; + } + Url.prototype.parse = function(url, slashesDenoteHost) { + let lowerProto, hec, slashes; + let rest = url; + // trim before proceeding. + // This is to support parse stuff like " http://foo.com \n" + rest = rest.trim(); + if (!slashesDenoteHost && url.split("#").length === 1) { + // Try fast path regexp + const simplePath = simplePathPattern.exec(rest); + if (simplePath) { + this.pathname = simplePath[1]; + if (simplePath[2]) { + this.search = simplePath[2]; + } + return this; + } + } + let proto = protocolPattern.exec(rest); + if (proto) { + proto = proto[0]; + lowerProto = proto.toLowerCase(); + this.protocol = proto; + rest = rest.substr(proto.length); + } + // figure out if it's got a host + // user@server is *always* interpreted as a hostname, and url + // resolution will treat //foo/bar as host=foo,path=bar because that's + // how the browser resolves relative URLs. + /* eslint-disable-next-line no-useless-escape */ if (slashesDenoteHost || proto || rest.match(/^\/\/[^@\/]+@[^@\/]+/)) { + slashes = rest.substr(0, 2) === "//"; + if (slashes && !(proto && hostlessProtocol[proto])) { + rest = rest.substr(2); + this.slashes = true; + } + } + if (!hostlessProtocol[proto] && (slashes || proto && !slashedProtocol[proto])) { + // there's a hostname. + // the first instance of /, ?, ;, or # ends the host. + // If there is an @ in the hostname, then non-host chars *are* allowed + // to the left of the last @ sign, unless some host-ending character + // comes *before* the @-sign. + // URLs are obnoxious. + // ex: + // http://a@b@c/ => user:a@b host:c + // http://a@b?@c => user:a host:c path:/?@c + // v0.12 TODO(isaacs): This is not quite how Chrome does things. + // Review our test case against browsers more comprehensively. + // find the first instance of any hostEndingChars + let hostEnd = -1; + for (let i = 0; i < hostEndingChars.length; i++) { + hec = rest.indexOf(hostEndingChars[i]); + if (hec !== -1 && (hostEnd === -1 || hec < hostEnd)) { + hostEnd = hec; + } + } + // at this point, either we have an explicit point where the + // auth portion cannot go past, or the last @ char is the decider. + let auth, atSign; + if (hostEnd === -1) { + // atSign can be anywhere. + atSign = rest.lastIndexOf("@"); + } else { + // atSign must be in auth portion. + // http://a@b/c@d => host:b auth:a path:/c@d + atSign = rest.lastIndexOf("@", hostEnd); + } + // Now we have a portion which is definitely the auth. + // Pull that off. + if (atSign !== -1) { + auth = rest.slice(0, atSign); + rest = rest.slice(atSign + 1); + this.auth = auth; + } + // the host is the remaining to the left of the first non-host char + hostEnd = -1; + for (let i = 0; i < nonHostChars.length; i++) { + hec = rest.indexOf(nonHostChars[i]); + if (hec !== -1 && (hostEnd === -1 || hec < hostEnd)) { + hostEnd = hec; + } + } + // if we still have not hit it, then the entire thing is a host. + if (hostEnd === -1) { + hostEnd = rest.length; + } + if (rest[hostEnd - 1] === ":") { + hostEnd--; + } + const host = rest.slice(0, hostEnd); + rest = rest.slice(hostEnd); + // pull out port. + this.parseHost(host); + // we've indicated that there is a hostname, + // so even if it's empty, it has to be present. + this.hostname = this.hostname || ""; + // if hostname begins with [ and ends with ] + // assume that it's an IPv6 address. + const ipv6Hostname = this.hostname[0] === "[" && this.hostname[this.hostname.length - 1] === "]"; + // validate a little. + if (!ipv6Hostname) { + const hostparts = this.hostname.split(/\./); + for (let i = 0, l = hostparts.length; i < l; i++) { + const part = hostparts[i]; + if (!part) { + continue; + } + if (!part.match(hostnamePartPattern)) { + let newpart = ""; + for (let j = 0, k = part.length; j < k; j++) { + if (part.charCodeAt(j) > 127) { + // we replace non-ASCII char with a temporary placeholder + // we need this to make sure size of hostname is not + // broken by replacing non-ASCII by nothing + newpart += "x"; + } else { + newpart += part[j]; + } + } + // we test again with ASCII char only + if (!newpart.match(hostnamePartPattern)) { + const validParts = hostparts.slice(0, i); + const notHost = hostparts.slice(i + 1); + const bit = part.match(hostnamePartStart); + if (bit) { + validParts.push(bit[1]); + notHost.unshift(bit[2]); + } + if (notHost.length) { + rest = notHost.join(".") + rest; + } + this.hostname = validParts.join("."); + break; + } + } + } + } + if (this.hostname.length > hostnameMaxLen) { + this.hostname = ""; + } + // strip [ and ] from the hostname + // the host field still retains them, though + if (ipv6Hostname) { + this.hostname = this.hostname.substr(1, this.hostname.length - 2); + } + } + // chop off from the tail first. + const hash = rest.indexOf("#"); + if (hash !== -1) { + // got a fragment string. + this.hash = rest.substr(hash); + rest = rest.slice(0, hash); + } + const qm = rest.indexOf("?"); + if (qm !== -1) { + this.search = rest.substr(qm); + rest = rest.slice(0, qm); + } + if (rest) { + this.pathname = rest; + } + if (slashedProtocol[lowerProto] && this.hostname && !this.pathname) { + this.pathname = ""; + } + return this; + }; + Url.prototype.parseHost = function(host) { + let port = portPattern.exec(host); + if (port) { + port = port[0]; + if (port !== ":") { + this.port = port.substr(1); + } + host = host.substr(0, host.length - port.length); + } + if (host) { + this.hostname = host; + } + }; + var mdurl = Object.freeze({ + __proto__: null, + decode: decode$1, + encode: encode$1, + format: format, + parse: urlParse + }); + var Any = /[\0-\uD7FF\uE000-\uFFFF]|[\uD800-\uDBFF][\uDC00-\uDFFF]|[\uD800-\uDBFF](?![\uDC00-\uDFFF])|(?:[^\uD800-\uDBFF]|^)[\uDC00-\uDFFF]/; + var Cc = /[\0-\x1F\x7F-\x9F]/; + var regex$1 = /[\xAD\u0600-\u0605\u061C\u06DD\u070F\u0890\u0891\u08E2\u180E\u200B-\u200F\u202A-\u202E\u2060-\u2064\u2066-\u206F\uFEFF\uFFF9-\uFFFB]|\uD804[\uDCBD\uDCCD]|\uD80D[\uDC30-\uDC3F]|\uD82F[\uDCA0-\uDCA3]|\uD834[\uDD73-\uDD7A]|\uDB40[\uDC01\uDC20-\uDC7F]/; + var P = /[!-#%-\*,-\/:;\?@\[-\]_\{\}\xA1\xA7\xAB\xB6\xB7\xBB\xBF\u037E\u0387\u055A-\u055F\u0589\u058A\u05BE\u05C0\u05C3\u05C6\u05F3\u05F4\u0609\u060A\u060C\u060D\u061B\u061D-\u061F\u066A-\u066D\u06D4\u0700-\u070D\u07F7-\u07F9\u0830-\u083E\u085E\u0964\u0965\u0970\u09FD\u0A76\u0AF0\u0C77\u0C84\u0DF4\u0E4F\u0E5A\u0E5B\u0F04-\u0F12\u0F14\u0F3A-\u0F3D\u0F85\u0FD0-\u0FD4\u0FD9\u0FDA\u104A-\u104F\u10FB\u1360-\u1368\u1400\u166E\u169B\u169C\u16EB-\u16ED\u1735\u1736\u17D4-\u17D6\u17D8-\u17DA\u1800-\u180A\u1944\u1945\u1A1E\u1A1F\u1AA0-\u1AA6\u1AA8-\u1AAD\u1B5A-\u1B60\u1B7D\u1B7E\u1BFC-\u1BFF\u1C3B-\u1C3F\u1C7E\u1C7F\u1CC0-\u1CC7\u1CD3\u2010-\u2027\u2030-\u2043\u2045-\u2051\u2053-\u205E\u207D\u207E\u208D\u208E\u2308-\u230B\u2329\u232A\u2768-\u2775\u27C5\u27C6\u27E6-\u27EF\u2983-\u2998\u29D8-\u29DB\u29FC\u29FD\u2CF9-\u2CFC\u2CFE\u2CFF\u2D70\u2E00-\u2E2E\u2E30-\u2E4F\u2E52-\u2E5D\u3001-\u3003\u3008-\u3011\u3014-\u301F\u3030\u303D\u30A0\u30FB\uA4FE\uA4FF\uA60D-\uA60F\uA673\uA67E\uA6F2-\uA6F7\uA874-\uA877\uA8CE\uA8CF\uA8F8-\uA8FA\uA8FC\uA92E\uA92F\uA95F\uA9C1-\uA9CD\uA9DE\uA9DF\uAA5C-\uAA5F\uAADE\uAADF\uAAF0\uAAF1\uABEB\uFD3E\uFD3F\uFE10-\uFE19\uFE30-\uFE52\uFE54-\uFE61\uFE63\uFE68\uFE6A\uFE6B\uFF01-\uFF03\uFF05-\uFF0A\uFF0C-\uFF0F\uFF1A\uFF1B\uFF1F\uFF20\uFF3B-\uFF3D\uFF3F\uFF5B\uFF5D\uFF5F-\uFF65]|\uD800[\uDD00-\uDD02\uDF9F\uDFD0]|\uD801\uDD6F|\uD802[\uDC57\uDD1F\uDD3F\uDE50-\uDE58\uDE7F\uDEF0-\uDEF6\uDF39-\uDF3F\uDF99-\uDF9C]|\uD803[\uDEAD\uDF55-\uDF59\uDF86-\uDF89]|\uD804[\uDC47-\uDC4D\uDCBB\uDCBC\uDCBE-\uDCC1\uDD40-\uDD43\uDD74\uDD75\uDDC5-\uDDC8\uDDCD\uDDDB\uDDDD-\uDDDF\uDE38-\uDE3D\uDEA9]|\uD805[\uDC4B-\uDC4F\uDC5A\uDC5B\uDC5D\uDCC6\uDDC1-\uDDD7\uDE41-\uDE43\uDE60-\uDE6C\uDEB9\uDF3C-\uDF3E]|\uD806[\uDC3B\uDD44-\uDD46\uDDE2\uDE3F-\uDE46\uDE9A-\uDE9C\uDE9E-\uDEA2\uDF00-\uDF09]|\uD807[\uDC41-\uDC45\uDC70\uDC71\uDEF7\uDEF8\uDF43-\uDF4F\uDFFF]|\uD809[\uDC70-\uDC74]|\uD80B[\uDFF1\uDFF2]|\uD81A[\uDE6E\uDE6F\uDEF5\uDF37-\uDF3B\uDF44]|\uD81B[\uDE97-\uDE9A\uDFE2]|\uD82F\uDC9F|\uD836[\uDE87-\uDE8B]|\uD83A[\uDD5E\uDD5F]/; + var regex = /[\$\+<->\^`\|~\xA2-\xA6\xA8\xA9\xAC\xAE-\xB1\xB4\xB8\xD7\xF7\u02C2-\u02C5\u02D2-\u02DF\u02E5-\u02EB\u02ED\u02EF-\u02FF\u0375\u0384\u0385\u03F6\u0482\u058D-\u058F\u0606-\u0608\u060B\u060E\u060F\u06DE\u06E9\u06FD\u06FE\u07F6\u07FE\u07FF\u0888\u09F2\u09F3\u09FA\u09FB\u0AF1\u0B70\u0BF3-\u0BFA\u0C7F\u0D4F\u0D79\u0E3F\u0F01-\u0F03\u0F13\u0F15-\u0F17\u0F1A-\u0F1F\u0F34\u0F36\u0F38\u0FBE-\u0FC5\u0FC7-\u0FCC\u0FCE\u0FCF\u0FD5-\u0FD8\u109E\u109F\u1390-\u1399\u166D\u17DB\u1940\u19DE-\u19FF\u1B61-\u1B6A\u1B74-\u1B7C\u1FBD\u1FBF-\u1FC1\u1FCD-\u1FCF\u1FDD-\u1FDF\u1FED-\u1FEF\u1FFD\u1FFE\u2044\u2052\u207A-\u207C\u208A-\u208C\u20A0-\u20C0\u2100\u2101\u2103-\u2106\u2108\u2109\u2114\u2116-\u2118\u211E-\u2123\u2125\u2127\u2129\u212E\u213A\u213B\u2140-\u2144\u214A-\u214D\u214F\u218A\u218B\u2190-\u2307\u230C-\u2328\u232B-\u2426\u2440-\u244A\u249C-\u24E9\u2500-\u2767\u2794-\u27C4\u27C7-\u27E5\u27F0-\u2982\u2999-\u29D7\u29DC-\u29FB\u29FE-\u2B73\u2B76-\u2B95\u2B97-\u2BFF\u2CE5-\u2CEA\u2E50\u2E51\u2E80-\u2E99\u2E9B-\u2EF3\u2F00-\u2FD5\u2FF0-\u2FFF\u3004\u3012\u3013\u3020\u3036\u3037\u303E\u303F\u309B\u309C\u3190\u3191\u3196-\u319F\u31C0-\u31E3\u31EF\u3200-\u321E\u322A-\u3247\u3250\u3260-\u327F\u328A-\u32B0\u32C0-\u33FF\u4DC0-\u4DFF\uA490-\uA4C6\uA700-\uA716\uA720\uA721\uA789\uA78A\uA828-\uA82B\uA836-\uA839\uAA77-\uAA79\uAB5B\uAB6A\uAB6B\uFB29\uFBB2-\uFBC2\uFD40-\uFD4F\uFDCF\uFDFC-\uFDFF\uFE62\uFE64-\uFE66\uFE69\uFF04\uFF0B\uFF1C-\uFF1E\uFF3E\uFF40\uFF5C\uFF5E\uFFE0-\uFFE6\uFFE8-\uFFEE\uFFFC\uFFFD]|\uD800[\uDD37-\uDD3F\uDD79-\uDD89\uDD8C-\uDD8E\uDD90-\uDD9C\uDDA0\uDDD0-\uDDFC]|\uD802[\uDC77\uDC78\uDEC8]|\uD805\uDF3F|\uD807[\uDFD5-\uDFF1]|\uD81A[\uDF3C-\uDF3F\uDF45]|\uD82F\uDC9C|\uD833[\uDF50-\uDFC3]|\uD834[\uDC00-\uDCF5\uDD00-\uDD26\uDD29-\uDD64\uDD6A-\uDD6C\uDD83\uDD84\uDD8C-\uDDA9\uDDAE-\uDDEA\uDE00-\uDE41\uDE45\uDF00-\uDF56]|\uD835[\uDEC1\uDEDB\uDEFB\uDF15\uDF35\uDF4F\uDF6F\uDF89\uDFA9\uDFC3]|\uD836[\uDC00-\uDDFF\uDE37-\uDE3A\uDE6D-\uDE74\uDE76-\uDE83\uDE85\uDE86]|\uD838[\uDD4F\uDEFF]|\uD83B[\uDCAC\uDCB0\uDD2E\uDEF0\uDEF1]|\uD83C[\uDC00-\uDC2B\uDC30-\uDC93\uDCA0-\uDCAE\uDCB1-\uDCBF\uDCC1-\uDCCF\uDCD1-\uDCF5\uDD0D-\uDDAD\uDDE6-\uDE02\uDE10-\uDE3B\uDE40-\uDE48\uDE50\uDE51\uDE60-\uDE65\uDF00-\uDFFF]|\uD83D[\uDC00-\uDED7\uDEDC-\uDEEC\uDEF0-\uDEFC\uDF00-\uDF76\uDF7B-\uDFD9\uDFE0-\uDFEB\uDFF0]|\uD83E[\uDC00-\uDC0B\uDC10-\uDC47\uDC50-\uDC59\uDC60-\uDC87\uDC90-\uDCAD\uDCB0\uDCB1\uDD00-\uDE53\uDE60-\uDE6D\uDE70-\uDE7C\uDE80-\uDE88\uDE90-\uDEBD\uDEBF-\uDEC5\uDECE-\uDEDB\uDEE0-\uDEE8\uDEF0-\uDEF8\uDF00-\uDF92\uDF94-\uDFCA]/; + var Z = /[ \xA0\u1680\u2000-\u200A\u2028\u2029\u202F\u205F\u3000]/; + var ucmicro = Object.freeze({ + __proto__: null, + Any: Any, + Cc: Cc, + Cf: regex$1, + P: P, + S: regex, + Z: Z + }); + // Generated using scripts/write-decode-map.ts + var htmlDecodeTree = new Uint16Array( + // prettier-ignore + '\u1d41<\xd5\u0131\u028a\u049d\u057b\u05d0\u0675\u06de\u07a2\u07d6\u080f\u0a4a\u0a91\u0da1\u0e6d\u0f09\u0f26\u10ca\u1228\u12e1\u1415\u149d\u14c3\u14df\u1525\0\0\0\0\0\0\u156b\u16cd\u198d\u1c12\u1ddd\u1f7e\u2060\u21b0\u228d\u23c0\u23fb\u2442\u2824\u2912\u2d08\u2e48\u2fce\u3016\u32ba\u3639\u37ac\u38fe\u3a28\u3a71\u3ae0\u3b2e\u0800EMabcfglmnoprstu\\bfms\x7f\x84\x8b\x90\x95\x98\xa6\xb3\xb9\xc8\xcflig\u803b\xc6\u40c6P\u803b&\u4026cute\u803b\xc1\u40c1reve;\u4102\u0100iyx}rc\u803b\xc2\u40c2;\u4410r;\uc000\ud835\udd04rave\u803b\xc0\u40c0pha;\u4391acr;\u4100d;\u6a53\u0100gp\x9d\xa1on;\u4104f;\uc000\ud835\udd38plyFunction;\u6061ing\u803b\xc5\u40c5\u0100cs\xbe\xc3r;\uc000\ud835\udc9cign;\u6254ilde\u803b\xc3\u40c3ml\u803b\xc4\u40c4\u0400aceforsu\xe5\xfb\xfe\u0117\u011c\u0122\u0127\u012a\u0100cr\xea\xf2kslash;\u6216\u0176\xf6\xf8;\u6ae7ed;\u6306y;\u4411\u0180crt\u0105\u010b\u0114ause;\u6235noullis;\u612ca;\u4392r;\uc000\ud835\udd05pf;\uc000\ud835\udd39eve;\u42d8c\xf2\u0113mpeq;\u624e\u0700HOacdefhilorsu\u014d\u0151\u0156\u0180\u019e\u01a2\u01b5\u01b7\u01ba\u01dc\u0215\u0273\u0278\u027ecy;\u4427PY\u803b\xa9\u40a9\u0180cpy\u015d\u0162\u017aute;\u4106\u0100;i\u0167\u0168\u62d2talDifferentialD;\u6145leys;\u612d\u0200aeio\u0189\u018e\u0194\u0198ron;\u410cdil\u803b\xc7\u40c7rc;\u4108nint;\u6230ot;\u410a\u0100dn\u01a7\u01adilla;\u40b8terDot;\u40b7\xf2\u017fi;\u43a7rcle\u0200DMPT\u01c7\u01cb\u01d1\u01d6ot;\u6299inus;\u6296lus;\u6295imes;\u6297o\u0100cs\u01e2\u01f8kwiseContourIntegral;\u6232eCurly\u0100DQ\u0203\u020foubleQuote;\u601duote;\u6019\u0200lnpu\u021e\u0228\u0247\u0255on\u0100;e\u0225\u0226\u6237;\u6a74\u0180git\u022f\u0236\u023aruent;\u6261nt;\u622fourIntegral;\u622e\u0100fr\u024c\u024e;\u6102oduct;\u6210nterClockwiseContourIntegral;\u6233oss;\u6a2fcr;\uc000\ud835\udc9ep\u0100;C\u0284\u0285\u62d3ap;\u624d\u0580DJSZacefios\u02a0\u02ac\u02b0\u02b4\u02b8\u02cb\u02d7\u02e1\u02e6\u0333\u048d\u0100;o\u0179\u02a5trahd;\u6911cy;\u4402cy;\u4405cy;\u440f\u0180grs\u02bf\u02c4\u02c7ger;\u6021r;\u61a1hv;\u6ae4\u0100ay\u02d0\u02d5ron;\u410e;\u4414l\u0100;t\u02dd\u02de\u6207a;\u4394r;\uc000\ud835\udd07\u0100af\u02eb\u0327\u0100cm\u02f0\u0322ritical\u0200ADGT\u0300\u0306\u0316\u031ccute;\u40b4o\u0174\u030b\u030d;\u42d9bleAcute;\u42ddrave;\u4060ilde;\u42dcond;\u62c4ferentialD;\u6146\u0470\u033d\0\0\0\u0342\u0354\0\u0405f;\uc000\ud835\udd3b\u0180;DE\u0348\u0349\u034d\u40a8ot;\u60dcqual;\u6250ble\u0300CDLRUV\u0363\u0372\u0382\u03cf\u03e2\u03f8ontourIntegra\xec\u0239o\u0274\u0379\0\0\u037b\xbb\u0349nArrow;\u61d3\u0100eo\u0387\u03a4ft\u0180ART\u0390\u0396\u03a1rrow;\u61d0ightArrow;\u61d4e\xe5\u02cang\u0100LR\u03ab\u03c4eft\u0100AR\u03b3\u03b9rrow;\u67f8ightArrow;\u67faightArrow;\u67f9ight\u0100AT\u03d8\u03derrow;\u61d2ee;\u62a8p\u0241\u03e9\0\0\u03efrrow;\u61d1ownArrow;\u61d5erticalBar;\u6225n\u0300ABLRTa\u0412\u042a\u0430\u045e\u047f\u037crrow\u0180;BU\u041d\u041e\u0422\u6193ar;\u6913pArrow;\u61f5reve;\u4311eft\u02d2\u043a\0\u0446\0\u0450ightVector;\u6950eeVector;\u695eector\u0100;B\u0459\u045a\u61bdar;\u6956ight\u01d4\u0467\0\u0471eeVector;\u695fector\u0100;B\u047a\u047b\u61c1ar;\u6957ee\u0100;A\u0486\u0487\u62a4rrow;\u61a7\u0100ct\u0492\u0497r;\uc000\ud835\udc9frok;\u4110\u0800NTacdfglmopqstux\u04bd\u04c0\u04c4\u04cb\u04de\u04e2\u04e7\u04ee\u04f5\u0521\u052f\u0536\u0552\u055d\u0560\u0565G;\u414aH\u803b\xd0\u40d0cute\u803b\xc9\u40c9\u0180aiy\u04d2\u04d7\u04dcron;\u411arc\u803b\xca\u40ca;\u442dot;\u4116r;\uc000\ud835\udd08rave\u803b\xc8\u40c8ement;\u6208\u0100ap\u04fa\u04fecr;\u4112ty\u0253\u0506\0\0\u0512mallSquare;\u65fberySmallSquare;\u65ab\u0100gp\u0526\u052aon;\u4118f;\uc000\ud835\udd3csilon;\u4395u\u0100ai\u053c\u0549l\u0100;T\u0542\u0543\u6a75ilde;\u6242librium;\u61cc\u0100ci\u0557\u055ar;\u6130m;\u6a73a;\u4397ml\u803b\xcb\u40cb\u0100ip\u056a\u056fsts;\u6203onentialE;\u6147\u0280cfios\u0585\u0588\u058d\u05b2\u05ccy;\u4424r;\uc000\ud835\udd09lled\u0253\u0597\0\0\u05a3mallSquare;\u65fcerySmallSquare;\u65aa\u0370\u05ba\0\u05bf\0\0\u05c4f;\uc000\ud835\udd3dAll;\u6200riertrf;\u6131c\xf2\u05cb\u0600JTabcdfgorst\u05e8\u05ec\u05ef\u05fa\u0600\u0612\u0616\u061b\u061d\u0623\u066c\u0672cy;\u4403\u803b>\u403emma\u0100;d\u05f7\u05f8\u4393;\u43dcreve;\u411e\u0180eiy\u0607\u060c\u0610dil;\u4122rc;\u411c;\u4413ot;\u4120r;\uc000\ud835\udd0a;\u62d9pf;\uc000\ud835\udd3eeater\u0300EFGLST\u0635\u0644\u064e\u0656\u065b\u0666qual\u0100;L\u063e\u063f\u6265ess;\u62dbullEqual;\u6267reater;\u6aa2ess;\u6277lantEqual;\u6a7eilde;\u6273cr;\uc000\ud835\udca2;\u626b\u0400Aacfiosu\u0685\u068b\u0696\u069b\u069e\u06aa\u06be\u06caRDcy;\u442a\u0100ct\u0690\u0694ek;\u42c7;\u405eirc;\u4124r;\u610clbertSpace;\u610b\u01f0\u06af\0\u06b2f;\u610dizontalLine;\u6500\u0100ct\u06c3\u06c5\xf2\u06a9rok;\u4126mp\u0144\u06d0\u06d8ownHum\xf0\u012fqual;\u624f\u0700EJOacdfgmnostu\u06fa\u06fe\u0703\u0707\u070e\u071a\u071e\u0721\u0728\u0744\u0778\u078b\u078f\u0795cy;\u4415lig;\u4132cy;\u4401cute\u803b\xcd\u40cd\u0100iy\u0713\u0718rc\u803b\xce\u40ce;\u4418ot;\u4130r;\u6111rave\u803b\xcc\u40cc\u0180;ap\u0720\u072f\u073f\u0100cg\u0734\u0737r;\u412ainaryI;\u6148lie\xf3\u03dd\u01f4\u0749\0\u0762\u0100;e\u074d\u074e\u622c\u0100gr\u0753\u0758ral;\u622bsection;\u62c2isible\u0100CT\u076c\u0772omma;\u6063imes;\u6062\u0180gpt\u077f\u0783\u0788on;\u412ef;\uc000\ud835\udd40a;\u4399cr;\u6110ilde;\u4128\u01eb\u079a\0\u079ecy;\u4406l\u803b\xcf\u40cf\u0280cfosu\u07ac\u07b7\u07bc\u07c2\u07d0\u0100iy\u07b1\u07b5rc;\u4134;\u4419r;\uc000\ud835\udd0dpf;\uc000\ud835\udd41\u01e3\u07c7\0\u07ccr;\uc000\ud835\udca5rcy;\u4408kcy;\u4404\u0380HJacfos\u07e4\u07e8\u07ec\u07f1\u07fd\u0802\u0808cy;\u4425cy;\u440cppa;\u439a\u0100ey\u07f6\u07fbdil;\u4136;\u441ar;\uc000\ud835\udd0epf;\uc000\ud835\udd42cr;\uc000\ud835\udca6\u0580JTaceflmost\u0825\u0829\u082c\u0850\u0863\u09b3\u09b8\u09c7\u09cd\u0a37\u0a47cy;\u4409\u803b<\u403c\u0280cmnpr\u0837\u083c\u0841\u0844\u084dute;\u4139bda;\u439bg;\u67ealacetrf;\u6112r;\u619e\u0180aey\u0857\u085c\u0861ron;\u413ddil;\u413b;\u441b\u0100fs\u0868\u0970t\u0500ACDFRTUVar\u087e\u08a9\u08b1\u08e0\u08e6\u08fc\u092f\u095b\u0390\u096a\u0100nr\u0883\u088fgleBracket;\u67e8row\u0180;BR\u0899\u089a\u089e\u6190ar;\u61e4ightArrow;\u61c6eiling;\u6308o\u01f5\u08b7\0\u08c3bleBracket;\u67e6n\u01d4\u08c8\0\u08d2eeVector;\u6961ector\u0100;B\u08db\u08dc\u61c3ar;\u6959loor;\u630aight\u0100AV\u08ef\u08f5rrow;\u6194ector;\u694e\u0100er\u0901\u0917e\u0180;AV\u0909\u090a\u0910\u62a3rrow;\u61a4ector;\u695aiangle\u0180;BE\u0924\u0925\u0929\u62b2ar;\u69cfqual;\u62b4p\u0180DTV\u0937\u0942\u094cownVector;\u6951eeVector;\u6960ector\u0100;B\u0956\u0957\u61bfar;\u6958ector\u0100;B\u0965\u0966\u61bcar;\u6952ight\xe1\u039cs\u0300EFGLST\u097e\u098b\u0995\u099d\u09a2\u09adqualGreater;\u62daullEqual;\u6266reater;\u6276ess;\u6aa1lantEqual;\u6a7dilde;\u6272r;\uc000\ud835\udd0f\u0100;e\u09bd\u09be\u62d8ftarrow;\u61daidot;\u413f\u0180npw\u09d4\u0a16\u0a1bg\u0200LRlr\u09de\u09f7\u0a02\u0a10eft\u0100AR\u09e6\u09ecrrow;\u67f5ightArrow;\u67f7ightArrow;\u67f6eft\u0100ar\u03b3\u0a0aight\xe1\u03bfight\xe1\u03caf;\uc000\ud835\udd43er\u0100LR\u0a22\u0a2ceftArrow;\u6199ightArrow;\u6198\u0180cht\u0a3e\u0a40\u0a42\xf2\u084c;\u61b0rok;\u4141;\u626a\u0400acefiosu\u0a5a\u0a5d\u0a60\u0a77\u0a7c\u0a85\u0a8b\u0a8ep;\u6905y;\u441c\u0100dl\u0a65\u0a6fiumSpace;\u605flintrf;\u6133r;\uc000\ud835\udd10nusPlus;\u6213pf;\uc000\ud835\udd44c\xf2\u0a76;\u439c\u0480Jacefostu\u0aa3\u0aa7\u0aad\u0ac0\u0b14\u0b19\u0d91\u0d97\u0d9ecy;\u440acute;\u4143\u0180aey\u0ab4\u0ab9\u0aberon;\u4147dil;\u4145;\u441d\u0180gsw\u0ac7\u0af0\u0b0eative\u0180MTV\u0ad3\u0adf\u0ae8ediumSpace;\u600bhi\u0100cn\u0ae6\u0ad8\xeb\u0ad9eryThi\xee\u0ad9ted\u0100GL\u0af8\u0b06reaterGreate\xf2\u0673essLes\xf3\u0a48Line;\u400ar;\uc000\ud835\udd11\u0200Bnpt\u0b22\u0b28\u0b37\u0b3areak;\u6060BreakingSpace;\u40a0f;\u6115\u0680;CDEGHLNPRSTV\u0b55\u0b56\u0b6a\u0b7c\u0ba1\u0beb\u0c04\u0c5e\u0c84\u0ca6\u0cd8\u0d61\u0d85\u6aec\u0100ou\u0b5b\u0b64ngruent;\u6262pCap;\u626doubleVerticalBar;\u6226\u0180lqx\u0b83\u0b8a\u0b9bement;\u6209ual\u0100;T\u0b92\u0b93\u6260ilde;\uc000\u2242\u0338ists;\u6204reater\u0380;EFGLST\u0bb6\u0bb7\u0bbd\u0bc9\u0bd3\u0bd8\u0be5\u626fqual;\u6271ullEqual;\uc000\u2267\u0338reater;\uc000\u226b\u0338ess;\u6279lantEqual;\uc000\u2a7e\u0338ilde;\u6275ump\u0144\u0bf2\u0bfdownHump;\uc000\u224e\u0338qual;\uc000\u224f\u0338e\u0100fs\u0c0a\u0c27tTriangle\u0180;BE\u0c1a\u0c1b\u0c21\u62eaar;\uc000\u29cf\u0338qual;\u62ecs\u0300;EGLST\u0c35\u0c36\u0c3c\u0c44\u0c4b\u0c58\u626equal;\u6270reater;\u6278ess;\uc000\u226a\u0338lantEqual;\uc000\u2a7d\u0338ilde;\u6274ested\u0100GL\u0c68\u0c79reaterGreater;\uc000\u2aa2\u0338essLess;\uc000\u2aa1\u0338recedes\u0180;ES\u0c92\u0c93\u0c9b\u6280qual;\uc000\u2aaf\u0338lantEqual;\u62e0\u0100ei\u0cab\u0cb9verseElement;\u620cghtTriangle\u0180;BE\u0ccb\u0ccc\u0cd2\u62ebar;\uc000\u29d0\u0338qual;\u62ed\u0100qu\u0cdd\u0d0cuareSu\u0100bp\u0ce8\u0cf9set\u0100;E\u0cf0\u0cf3\uc000\u228f\u0338qual;\u62e2erset\u0100;E\u0d03\u0d06\uc000\u2290\u0338qual;\u62e3\u0180bcp\u0d13\u0d24\u0d4eset\u0100;E\u0d1b\u0d1e\uc000\u2282\u20d2qual;\u6288ceeds\u0200;EST\u0d32\u0d33\u0d3b\u0d46\u6281qual;\uc000\u2ab0\u0338lantEqual;\u62e1ilde;\uc000\u227f\u0338erset\u0100;E\u0d58\u0d5b\uc000\u2283\u20d2qual;\u6289ilde\u0200;EFT\u0d6e\u0d6f\u0d75\u0d7f\u6241qual;\u6244ullEqual;\u6247ilde;\u6249erticalBar;\u6224cr;\uc000\ud835\udca9ilde\u803b\xd1\u40d1;\u439d\u0700Eacdfgmoprstuv\u0dbd\u0dc2\u0dc9\u0dd5\u0ddb\u0de0\u0de7\u0dfc\u0e02\u0e20\u0e22\u0e32\u0e3f\u0e44lig;\u4152cute\u803b\xd3\u40d3\u0100iy\u0dce\u0dd3rc\u803b\xd4\u40d4;\u441eblac;\u4150r;\uc000\ud835\udd12rave\u803b\xd2\u40d2\u0180aei\u0dee\u0df2\u0df6cr;\u414cga;\u43a9cron;\u439fpf;\uc000\ud835\udd46enCurly\u0100DQ\u0e0e\u0e1aoubleQuote;\u601cuote;\u6018;\u6a54\u0100cl\u0e27\u0e2cr;\uc000\ud835\udcaaash\u803b\xd8\u40d8i\u016c\u0e37\u0e3cde\u803b\xd5\u40d5es;\u6a37ml\u803b\xd6\u40d6er\u0100BP\u0e4b\u0e60\u0100ar\u0e50\u0e53r;\u603eac\u0100ek\u0e5a\u0e5c;\u63deet;\u63b4arenthesis;\u63dc\u0480acfhilors\u0e7f\u0e87\u0e8a\u0e8f\u0e92\u0e94\u0e9d\u0eb0\u0efcrtialD;\u6202y;\u441fr;\uc000\ud835\udd13i;\u43a6;\u43a0usMinus;\u40b1\u0100ip\u0ea2\u0eadncareplan\xe5\u069df;\u6119\u0200;eio\u0eb9\u0eba\u0ee0\u0ee4\u6abbcedes\u0200;EST\u0ec8\u0ec9\u0ecf\u0eda\u627aqual;\u6aaflantEqual;\u627cilde;\u627eme;\u6033\u0100dp\u0ee9\u0eeeuct;\u620fortion\u0100;a\u0225\u0ef9l;\u621d\u0100ci\u0f01\u0f06r;\uc000\ud835\udcab;\u43a8\u0200Ufos\u0f11\u0f16\u0f1b\u0f1fOT\u803b"\u4022r;\uc000\ud835\udd14pf;\u611acr;\uc000\ud835\udcac\u0600BEacefhiorsu\u0f3e\u0f43\u0f47\u0f60\u0f73\u0fa7\u0faa\u0fad\u1096\u10a9\u10b4\u10bearr;\u6910G\u803b\xae\u40ae\u0180cnr\u0f4e\u0f53\u0f56ute;\u4154g;\u67ebr\u0100;t\u0f5c\u0f5d\u61a0l;\u6916\u0180aey\u0f67\u0f6c\u0f71ron;\u4158dil;\u4156;\u4420\u0100;v\u0f78\u0f79\u611cerse\u0100EU\u0f82\u0f99\u0100lq\u0f87\u0f8eement;\u620builibrium;\u61cbpEquilibrium;\u696fr\xbb\u0f79o;\u43a1ght\u0400ACDFTUVa\u0fc1\u0feb\u0ff3\u1022\u1028\u105b\u1087\u03d8\u0100nr\u0fc6\u0fd2gleBracket;\u67e9row\u0180;BL\u0fdc\u0fdd\u0fe1\u6192ar;\u61e5eftArrow;\u61c4eiling;\u6309o\u01f5\u0ff9\0\u1005bleBracket;\u67e7n\u01d4\u100a\0\u1014eeVector;\u695dector\u0100;B\u101d\u101e\u61c2ar;\u6955loor;\u630b\u0100er\u102d\u1043e\u0180;AV\u1035\u1036\u103c\u62a2rrow;\u61a6ector;\u695biangle\u0180;BE\u1050\u1051\u1055\u62b3ar;\u69d0qual;\u62b5p\u0180DTV\u1063\u106e\u1078ownVector;\u694feeVector;\u695cector\u0100;B\u1082\u1083\u61bear;\u6954ector\u0100;B\u1091\u1092\u61c0ar;\u6953\u0100pu\u109b\u109ef;\u611dndImplies;\u6970ightarrow;\u61db\u0100ch\u10b9\u10bcr;\u611b;\u61b1leDelayed;\u69f4\u0680HOacfhimoqstu\u10e4\u10f1\u10f7\u10fd\u1119\u111e\u1151\u1156\u1161\u1167\u11b5\u11bb\u11bf\u0100Cc\u10e9\u10eeHcy;\u4429y;\u4428FTcy;\u442ccute;\u415a\u0280;aeiy\u1108\u1109\u110e\u1113\u1117\u6abcron;\u4160dil;\u415erc;\u415c;\u4421r;\uc000\ud835\udd16ort\u0200DLRU\u112a\u1134\u113e\u1149ownArrow\xbb\u041eeftArrow\xbb\u089aightArrow\xbb\u0fddpArrow;\u6191gma;\u43a3allCircle;\u6218pf;\uc000\ud835\udd4a\u0272\u116d\0\0\u1170t;\u621aare\u0200;ISU\u117b\u117c\u1189\u11af\u65a1ntersection;\u6293u\u0100bp\u118f\u119eset\u0100;E\u1197\u1198\u628fqual;\u6291erset\u0100;E\u11a8\u11a9\u6290qual;\u6292nion;\u6294cr;\uc000\ud835\udcaear;\u62c6\u0200bcmp\u11c8\u11db\u1209\u120b\u0100;s\u11cd\u11ce\u62d0et\u0100;E\u11cd\u11d5qual;\u6286\u0100ch\u11e0\u1205eeds\u0200;EST\u11ed\u11ee\u11f4\u11ff\u627bqual;\u6ab0lantEqual;\u627dilde;\u627fTh\xe1\u0f8c;\u6211\u0180;es\u1212\u1213\u1223\u62d1rset\u0100;E\u121c\u121d\u6283qual;\u6287et\xbb\u1213\u0580HRSacfhiors\u123e\u1244\u1249\u1255\u125e\u1271\u1276\u129f\u12c2\u12c8\u12d1ORN\u803b\xde\u40deADE;\u6122\u0100Hc\u124e\u1252cy;\u440by;\u4426\u0100bu\u125a\u125c;\u4009;\u43a4\u0180aey\u1265\u126a\u126fron;\u4164dil;\u4162;\u4422r;\uc000\ud835\udd17\u0100ei\u127b\u1289\u01f2\u1280\0\u1287efore;\u6234a;\u4398\u0100cn\u128e\u1298kSpace;\uc000\u205f\u200aSpace;\u6009lde\u0200;EFT\u12ab\u12ac\u12b2\u12bc\u623cqual;\u6243ullEqual;\u6245ilde;\u6248pf;\uc000\ud835\udd4bipleDot;\u60db\u0100ct\u12d6\u12dbr;\uc000\ud835\udcafrok;\u4166\u0ae1\u12f7\u130e\u131a\u1326\0\u132c\u1331\0\0\0\0\0\u1338\u133d\u1377\u1385\0\u13ff\u1404\u140a\u1410\u0100cr\u12fb\u1301ute\u803b\xda\u40dar\u0100;o\u1307\u1308\u619fcir;\u6949r\u01e3\u1313\0\u1316y;\u440eve;\u416c\u0100iy\u131e\u1323rc\u803b\xdb\u40db;\u4423blac;\u4170r;\uc000\ud835\udd18rave\u803b\xd9\u40d9acr;\u416a\u0100di\u1341\u1369er\u0100BP\u1348\u135d\u0100ar\u134d\u1350r;\u405fac\u0100ek\u1357\u1359;\u63dfet;\u63b5arenthesis;\u63ddon\u0100;P\u1370\u1371\u62c3lus;\u628e\u0100gp\u137b\u137fon;\u4172f;\uc000\ud835\udd4c\u0400ADETadps\u1395\u13ae\u13b8\u13c4\u03e8\u13d2\u13d7\u13f3rrow\u0180;BD\u1150\u13a0\u13a4ar;\u6912ownArrow;\u61c5ownArrow;\u6195quilibrium;\u696eee\u0100;A\u13cb\u13cc\u62a5rrow;\u61a5own\xe1\u03f3er\u0100LR\u13de\u13e8eftArrow;\u6196ightArrow;\u6197i\u0100;l\u13f9\u13fa\u43d2on;\u43a5ing;\u416ecr;\uc000\ud835\udcb0ilde;\u4168ml\u803b\xdc\u40dc\u0480Dbcdefosv\u1427\u142c\u1430\u1433\u143e\u1485\u148a\u1490\u1496ash;\u62abar;\u6aeby;\u4412ash\u0100;l\u143b\u143c\u62a9;\u6ae6\u0100er\u1443\u1445;\u62c1\u0180bty\u144c\u1450\u147aar;\u6016\u0100;i\u144f\u1455cal\u0200BLST\u1461\u1465\u146a\u1474ar;\u6223ine;\u407ceparator;\u6758ilde;\u6240ThinSpace;\u600ar;\uc000\ud835\udd19pf;\uc000\ud835\udd4dcr;\uc000\ud835\udcb1dash;\u62aa\u0280cefos\u14a7\u14ac\u14b1\u14b6\u14bcirc;\u4174dge;\u62c0r;\uc000\ud835\udd1apf;\uc000\ud835\udd4ecr;\uc000\ud835\udcb2\u0200fios\u14cb\u14d0\u14d2\u14d8r;\uc000\ud835\udd1b;\u439epf;\uc000\ud835\udd4fcr;\uc000\ud835\udcb3\u0480AIUacfosu\u14f1\u14f5\u14f9\u14fd\u1504\u150f\u1514\u151a\u1520cy;\u442fcy;\u4407cy;\u442ecute\u803b\xdd\u40dd\u0100iy\u1509\u150drc;\u4176;\u442br;\uc000\ud835\udd1cpf;\uc000\ud835\udd50cr;\uc000\ud835\udcb4ml;\u4178\u0400Hacdefos\u1535\u1539\u153f\u154b\u154f\u155d\u1560\u1564cy;\u4416cute;\u4179\u0100ay\u1544\u1549ron;\u417d;\u4417ot;\u417b\u01f2\u1554\0\u155boWidt\xe8\u0ad9a;\u4396r;\u6128pf;\u6124cr;\uc000\ud835\udcb5\u0be1\u1583\u158a\u1590\0\u15b0\u15b6\u15bf\0\0\0\0\u15c6\u15db\u15eb\u165f\u166d\0\u1695\u169b\u16b2\u16b9\0\u16becute\u803b\xe1\u40e1reve;\u4103\u0300;Ediuy\u159c\u159d\u15a1\u15a3\u15a8\u15ad\u623e;\uc000\u223e\u0333;\u623frc\u803b\xe2\u40e2te\u80bb\xb4\u0306;\u4430lig\u803b\xe6\u40e6\u0100;r\xb2\u15ba;\uc000\ud835\udd1erave\u803b\xe0\u40e0\u0100ep\u15ca\u15d6\u0100fp\u15cf\u15d4sym;\u6135\xe8\u15d3ha;\u43b1\u0100ap\u15dfc\u0100cl\u15e4\u15e7r;\u4101g;\u6a3f\u0264\u15f0\0\0\u160a\u0280;adsv\u15fa\u15fb\u15ff\u1601\u1607\u6227nd;\u6a55;\u6a5clope;\u6a58;\u6a5a\u0380;elmrsz\u1618\u1619\u161b\u161e\u163f\u164f\u1659\u6220;\u69a4e\xbb\u1619sd\u0100;a\u1625\u1626\u6221\u0461\u1630\u1632\u1634\u1636\u1638\u163a\u163c\u163e;\u69a8;\u69a9;\u69aa;\u69ab;\u69ac;\u69ad;\u69ae;\u69aft\u0100;v\u1645\u1646\u621fb\u0100;d\u164c\u164d\u62be;\u699d\u0100pt\u1654\u1657h;\u6222\xbb\xb9arr;\u637c\u0100gp\u1663\u1667on;\u4105f;\uc000\ud835\udd52\u0380;Eaeiop\u12c1\u167b\u167d\u1682\u1684\u1687\u168a;\u6a70cir;\u6a6f;\u624ad;\u624bs;\u4027rox\u0100;e\u12c1\u1692\xf1\u1683ing\u803b\xe5\u40e5\u0180cty\u16a1\u16a6\u16a8r;\uc000\ud835\udcb6;\u402amp\u0100;e\u12c1\u16af\xf1\u0288ilde\u803b\xe3\u40e3ml\u803b\xe4\u40e4\u0100ci\u16c2\u16c8onin\xf4\u0272nt;\u6a11\u0800Nabcdefiklnoprsu\u16ed\u16f1\u1730\u173c\u1743\u1748\u1778\u177d\u17e0\u17e6\u1839\u1850\u170d\u193d\u1948\u1970ot;\u6aed\u0100cr\u16f6\u171ek\u0200ceps\u1700\u1705\u170d\u1713ong;\u624cpsilon;\u43f6rime;\u6035im\u0100;e\u171a\u171b\u623dq;\u62cd\u0176\u1722\u1726ee;\u62bded\u0100;g\u172c\u172d\u6305e\xbb\u172drk\u0100;t\u135c\u1737brk;\u63b6\u0100oy\u1701\u1741;\u4431quo;\u601e\u0280cmprt\u1753\u175b\u1761\u1764\u1768aus\u0100;e\u010a\u0109ptyv;\u69b0s\xe9\u170cno\xf5\u0113\u0180ahw\u176f\u1771\u1773;\u43b2;\u6136een;\u626cr;\uc000\ud835\udd1fg\u0380costuvw\u178d\u179d\u17b3\u17c1\u17d5\u17db\u17de\u0180aiu\u1794\u1796\u179a\xf0\u0760rc;\u65efp\xbb\u1371\u0180dpt\u17a4\u17a8\u17adot;\u6a00lus;\u6a01imes;\u6a02\u0271\u17b9\0\0\u17becup;\u6a06ar;\u6605riangle\u0100du\u17cd\u17d2own;\u65bdp;\u65b3plus;\u6a04e\xe5\u1444\xe5\u14adarow;\u690d\u0180ako\u17ed\u1826\u1835\u0100cn\u17f2\u1823k\u0180lst\u17fa\u05ab\u1802ozenge;\u69ebriangle\u0200;dlr\u1812\u1813\u1818\u181d\u65b4own;\u65beeft;\u65c2ight;\u65b8k;\u6423\u01b1\u182b\0\u1833\u01b2\u182f\0\u1831;\u6592;\u65914;\u6593ck;\u6588\u0100eo\u183e\u184d\u0100;q\u1843\u1846\uc000=\u20e5uiv;\uc000\u2261\u20e5t;\u6310\u0200ptwx\u1859\u185e\u1867\u186cf;\uc000\ud835\udd53\u0100;t\u13cb\u1863om\xbb\u13cctie;\u62c8\u0600DHUVbdhmptuv\u1885\u1896\u18aa\u18bb\u18d7\u18db\u18ec\u18ff\u1905\u190a\u1910\u1921\u0200LRlr\u188e\u1890\u1892\u1894;\u6557;\u6554;\u6556;\u6553\u0280;DUdu\u18a1\u18a2\u18a4\u18a6\u18a8\u6550;\u6566;\u6569;\u6564;\u6567\u0200LRlr\u18b3\u18b5\u18b7\u18b9;\u655d;\u655a;\u655c;\u6559\u0380;HLRhlr\u18ca\u18cb\u18cd\u18cf\u18d1\u18d3\u18d5\u6551;\u656c;\u6563;\u6560;\u656b;\u6562;\u655fox;\u69c9\u0200LRlr\u18e4\u18e6\u18e8\u18ea;\u6555;\u6552;\u6510;\u650c\u0280;DUdu\u06bd\u18f7\u18f9\u18fb\u18fd;\u6565;\u6568;\u652c;\u6534inus;\u629flus;\u629eimes;\u62a0\u0200LRlr\u1919\u191b\u191d\u191f;\u655b;\u6558;\u6518;\u6514\u0380;HLRhlr\u1930\u1931\u1933\u1935\u1937\u1939\u193b\u6502;\u656a;\u6561;\u655e;\u653c;\u6524;\u651c\u0100ev\u0123\u1942bar\u803b\xa6\u40a6\u0200ceio\u1951\u1956\u195a\u1960r;\uc000\ud835\udcb7mi;\u604fm\u0100;e\u171a\u171cl\u0180;bh\u1968\u1969\u196b\u405c;\u69c5sub;\u67c8\u016c\u1974\u197el\u0100;e\u1979\u197a\u6022t\xbb\u197ap\u0180;Ee\u012f\u1985\u1987;\u6aae\u0100;q\u06dc\u06db\u0ce1\u19a7\0\u19e8\u1a11\u1a15\u1a32\0\u1a37\u1a50\0\0\u1ab4\0\0\u1ac1\0\0\u1b21\u1b2e\u1b4d\u1b52\0\u1bfd\0\u1c0c\u0180cpr\u19ad\u19b2\u19ddute;\u4107\u0300;abcds\u19bf\u19c0\u19c4\u19ca\u19d5\u19d9\u6229nd;\u6a44rcup;\u6a49\u0100au\u19cf\u19d2p;\u6a4bp;\u6a47ot;\u6a40;\uc000\u2229\ufe00\u0100eo\u19e2\u19e5t;\u6041\xee\u0693\u0200aeiu\u19f0\u19fb\u1a01\u1a05\u01f0\u19f5\0\u19f8s;\u6a4don;\u410ddil\u803b\xe7\u40e7rc;\u4109ps\u0100;s\u1a0c\u1a0d\u6a4cm;\u6a50ot;\u410b\u0180dmn\u1a1b\u1a20\u1a26il\u80bb\xb8\u01adptyv;\u69b2t\u8100\xa2;e\u1a2d\u1a2e\u40a2r\xe4\u01b2r;\uc000\ud835\udd20\u0180cei\u1a3d\u1a40\u1a4dy;\u4447ck\u0100;m\u1a47\u1a48\u6713ark\xbb\u1a48;\u43c7r\u0380;Ecefms\u1a5f\u1a60\u1a62\u1a6b\u1aa4\u1aaa\u1aae\u65cb;\u69c3\u0180;el\u1a69\u1a6a\u1a6d\u42c6q;\u6257e\u0261\u1a74\0\0\u1a88rrow\u0100lr\u1a7c\u1a81eft;\u61baight;\u61bb\u0280RSacd\u1a92\u1a94\u1a96\u1a9a\u1a9f\xbb\u0f47;\u64c8st;\u629birc;\u629aash;\u629dnint;\u6a10id;\u6aefcir;\u69c2ubs\u0100;u\u1abb\u1abc\u6663it\xbb\u1abc\u02ec\u1ac7\u1ad4\u1afa\0\u1b0aon\u0100;e\u1acd\u1ace\u403a\u0100;q\xc7\xc6\u026d\u1ad9\0\0\u1ae2a\u0100;t\u1ade\u1adf\u402c;\u4040\u0180;fl\u1ae8\u1ae9\u1aeb\u6201\xee\u1160e\u0100mx\u1af1\u1af6ent\xbb\u1ae9e\xf3\u024d\u01e7\u1afe\0\u1b07\u0100;d\u12bb\u1b02ot;\u6a6dn\xf4\u0246\u0180fry\u1b10\u1b14\u1b17;\uc000\ud835\udd54o\xe4\u0254\u8100\xa9;s\u0155\u1b1dr;\u6117\u0100ao\u1b25\u1b29rr;\u61b5ss;\u6717\u0100cu\u1b32\u1b37r;\uc000\ud835\udcb8\u0100bp\u1b3c\u1b44\u0100;e\u1b41\u1b42\u6acf;\u6ad1\u0100;e\u1b49\u1b4a\u6ad0;\u6ad2dot;\u62ef\u0380delprvw\u1b60\u1b6c\u1b77\u1b82\u1bac\u1bd4\u1bf9arr\u0100lr\u1b68\u1b6a;\u6938;\u6935\u0270\u1b72\0\0\u1b75r;\u62dec;\u62dfarr\u0100;p\u1b7f\u1b80\u61b6;\u693d\u0300;bcdos\u1b8f\u1b90\u1b96\u1ba1\u1ba5\u1ba8\u622arcap;\u6a48\u0100au\u1b9b\u1b9ep;\u6a46p;\u6a4aot;\u628dr;\u6a45;\uc000\u222a\ufe00\u0200alrv\u1bb5\u1bbf\u1bde\u1be3rr\u0100;m\u1bbc\u1bbd\u61b7;\u693cy\u0180evw\u1bc7\u1bd4\u1bd8q\u0270\u1bce\0\0\u1bd2re\xe3\u1b73u\xe3\u1b75ee;\u62ceedge;\u62cfen\u803b\xa4\u40a4earrow\u0100lr\u1bee\u1bf3eft\xbb\u1b80ight\xbb\u1bbde\xe4\u1bdd\u0100ci\u1c01\u1c07onin\xf4\u01f7nt;\u6231lcty;\u632d\u0980AHabcdefhijlorstuwz\u1c38\u1c3b\u1c3f\u1c5d\u1c69\u1c75\u1c8a\u1c9e\u1cac\u1cb7\u1cfb\u1cff\u1d0d\u1d7b\u1d91\u1dab\u1dbb\u1dc6\u1dcdr\xf2\u0381ar;\u6965\u0200glrs\u1c48\u1c4d\u1c52\u1c54ger;\u6020eth;\u6138\xf2\u1133h\u0100;v\u1c5a\u1c5b\u6010\xbb\u090a\u016b\u1c61\u1c67arow;\u690fa\xe3\u0315\u0100ay\u1c6e\u1c73ron;\u410f;\u4434\u0180;ao\u0332\u1c7c\u1c84\u0100gr\u02bf\u1c81r;\u61catseq;\u6a77\u0180glm\u1c91\u1c94\u1c98\u803b\xb0\u40b0ta;\u43b4ptyv;\u69b1\u0100ir\u1ca3\u1ca8sht;\u697f;\uc000\ud835\udd21ar\u0100lr\u1cb3\u1cb5\xbb\u08dc\xbb\u101e\u0280aegsv\u1cc2\u0378\u1cd6\u1cdc\u1ce0m\u0180;os\u0326\u1cca\u1cd4nd\u0100;s\u0326\u1cd1uit;\u6666amma;\u43ddin;\u62f2\u0180;io\u1ce7\u1ce8\u1cf8\u40f7de\u8100\xf7;o\u1ce7\u1cf0ntimes;\u62c7n\xf8\u1cf7cy;\u4452c\u026f\u1d06\0\0\u1d0arn;\u631eop;\u630d\u0280lptuw\u1d18\u1d1d\u1d22\u1d49\u1d55lar;\u4024f;\uc000\ud835\udd55\u0280;emps\u030b\u1d2d\u1d37\u1d3d\u1d42q\u0100;d\u0352\u1d33ot;\u6251inus;\u6238lus;\u6214quare;\u62a1blebarwedg\xe5\xfan\u0180adh\u112e\u1d5d\u1d67ownarrow\xf3\u1c83arpoon\u0100lr\u1d72\u1d76ef\xf4\u1cb4igh\xf4\u1cb6\u0162\u1d7f\u1d85karo\xf7\u0f42\u026f\u1d8a\0\0\u1d8ern;\u631fop;\u630c\u0180cot\u1d98\u1da3\u1da6\u0100ry\u1d9d\u1da1;\uc000\ud835\udcb9;\u4455l;\u69f6rok;\u4111\u0100dr\u1db0\u1db4ot;\u62f1i\u0100;f\u1dba\u1816\u65bf\u0100ah\u1dc0\u1dc3r\xf2\u0429a\xf2\u0fa6angle;\u69a6\u0100ci\u1dd2\u1dd5y;\u445fgrarr;\u67ff\u0900Dacdefglmnopqrstux\u1e01\u1e09\u1e19\u1e38\u0578\u1e3c\u1e49\u1e61\u1e7e\u1ea5\u1eaf\u1ebd\u1ee1\u1f2a\u1f37\u1f44\u1f4e\u1f5a\u0100Do\u1e06\u1d34o\xf4\u1c89\u0100cs\u1e0e\u1e14ute\u803b\xe9\u40e9ter;\u6a6e\u0200aioy\u1e22\u1e27\u1e31\u1e36ron;\u411br\u0100;c\u1e2d\u1e2e\u6256\u803b\xea\u40ealon;\u6255;\u444dot;\u4117\u0100Dr\u1e41\u1e45ot;\u6252;\uc000\ud835\udd22\u0180;rs\u1e50\u1e51\u1e57\u6a9aave\u803b\xe8\u40e8\u0100;d\u1e5c\u1e5d\u6a96ot;\u6a98\u0200;ils\u1e6a\u1e6b\u1e72\u1e74\u6a99nters;\u63e7;\u6113\u0100;d\u1e79\u1e7a\u6a95ot;\u6a97\u0180aps\u1e85\u1e89\u1e97cr;\u4113ty\u0180;sv\u1e92\u1e93\u1e95\u6205et\xbb\u1e93p\u01001;\u1e9d\u1ea4\u0133\u1ea1\u1ea3;\u6004;\u6005\u6003\u0100gs\u1eaa\u1eac;\u414bp;\u6002\u0100gp\u1eb4\u1eb8on;\u4119f;\uc000\ud835\udd56\u0180als\u1ec4\u1ece\u1ed2r\u0100;s\u1eca\u1ecb\u62d5l;\u69e3us;\u6a71i\u0180;lv\u1eda\u1edb\u1edf\u43b5on\xbb\u1edb;\u43f5\u0200csuv\u1eea\u1ef3\u1f0b\u1f23\u0100io\u1eef\u1e31rc\xbb\u1e2e\u0269\u1ef9\0\0\u1efb\xed\u0548ant\u0100gl\u1f02\u1f06tr\xbb\u1e5dess\xbb\u1e7a\u0180aei\u1f12\u1f16\u1f1als;\u403dst;\u625fv\u0100;D\u0235\u1f20D;\u6a78parsl;\u69e5\u0100Da\u1f2f\u1f33ot;\u6253rr;\u6971\u0180cdi\u1f3e\u1f41\u1ef8r;\u612fo\xf4\u0352\u0100ah\u1f49\u1f4b;\u43b7\u803b\xf0\u40f0\u0100mr\u1f53\u1f57l\u803b\xeb\u40ebo;\u60ac\u0180cip\u1f61\u1f64\u1f67l;\u4021s\xf4\u056e\u0100eo\u1f6c\u1f74ctatio\xee\u0559nential\xe5\u0579\u09e1\u1f92\0\u1f9e\0\u1fa1\u1fa7\0\0\u1fc6\u1fcc\0\u1fd3\0\u1fe6\u1fea\u2000\0\u2008\u205allingdotse\xf1\u1e44y;\u4444male;\u6640\u0180ilr\u1fad\u1fb3\u1fc1lig;\u8000\ufb03\u0269\u1fb9\0\0\u1fbdg;\u8000\ufb00ig;\u8000\ufb04;\uc000\ud835\udd23lig;\u8000\ufb01lig;\uc000fj\u0180alt\u1fd9\u1fdc\u1fe1t;\u666dig;\u8000\ufb02ns;\u65b1of;\u4192\u01f0\u1fee\0\u1ff3f;\uc000\ud835\udd57\u0100ak\u05bf\u1ff7\u0100;v\u1ffc\u1ffd\u62d4;\u6ad9artint;\u6a0d\u0100ao\u200c\u2055\u0100cs\u2011\u2052\u03b1\u201a\u2030\u2038\u2045\u2048\0\u2050\u03b2\u2022\u2025\u2027\u202a\u202c\0\u202e\u803b\xbd\u40bd;\u6153\u803b\xbc\u40bc;\u6155;\u6159;\u615b\u01b3\u2034\0\u2036;\u6154;\u6156\u02b4\u203e\u2041\0\0\u2043\u803b\xbe\u40be;\u6157;\u615c5;\u6158\u01b6\u204c\0\u204e;\u615a;\u615d8;\u615el;\u6044wn;\u6322cr;\uc000\ud835\udcbb\u0880Eabcdefgijlnorstv\u2082\u2089\u209f\u20a5\u20b0\u20b4\u20f0\u20f5\u20fa\u20ff\u2103\u2112\u2138\u0317\u213e\u2152\u219e\u0100;l\u064d\u2087;\u6a8c\u0180cmp\u2090\u2095\u209dute;\u41f5ma\u0100;d\u209c\u1cda\u43b3;\u6a86reve;\u411f\u0100iy\u20aa\u20aerc;\u411d;\u4433ot;\u4121\u0200;lqs\u063e\u0642\u20bd\u20c9\u0180;qs\u063e\u064c\u20c4lan\xf4\u0665\u0200;cdl\u0665\u20d2\u20d5\u20e5c;\u6aa9ot\u0100;o\u20dc\u20dd\u6a80\u0100;l\u20e2\u20e3\u6a82;\u6a84\u0100;e\u20ea\u20ed\uc000\u22db\ufe00s;\u6a94r;\uc000\ud835\udd24\u0100;g\u0673\u061bmel;\u6137cy;\u4453\u0200;Eaj\u065a\u210c\u210e\u2110;\u6a92;\u6aa5;\u6aa4\u0200Eaes\u211b\u211d\u2129\u2134;\u6269p\u0100;p\u2123\u2124\u6a8arox\xbb\u2124\u0100;q\u212e\u212f\u6a88\u0100;q\u212e\u211bim;\u62e7pf;\uc000\ud835\udd58\u0100ci\u2143\u2146r;\u610am\u0180;el\u066b\u214e\u2150;\u6a8e;\u6a90\u8300>;cdlqr\u05ee\u2160\u216a\u216e\u2173\u2179\u0100ci\u2165\u2167;\u6aa7r;\u6a7aot;\u62d7Par;\u6995uest;\u6a7c\u0280adels\u2184\u216a\u2190\u0656\u219b\u01f0\u2189\0\u218epro\xf8\u209er;\u6978q\u0100lq\u063f\u2196les\xf3\u2088i\xed\u066b\u0100en\u21a3\u21adrtneqq;\uc000\u2269\ufe00\xc5\u21aa\u0500Aabcefkosy\u21c4\u21c7\u21f1\u21f5\u21fa\u2218\u221d\u222f\u2268\u227dr\xf2\u03a0\u0200ilmr\u21d0\u21d4\u21d7\u21dbrs\xf0\u1484f\xbb\u2024il\xf4\u06a9\u0100dr\u21e0\u21e4cy;\u444a\u0180;cw\u08f4\u21eb\u21efir;\u6948;\u61adar;\u610firc;\u4125\u0180alr\u2201\u220e\u2213rts\u0100;u\u2209\u220a\u6665it\xbb\u220alip;\u6026con;\u62b9r;\uc000\ud835\udd25s\u0100ew\u2223\u2229arow;\u6925arow;\u6926\u0280amopr\u223a\u223e\u2243\u225e\u2263rr;\u61fftht;\u623bk\u0100lr\u2249\u2253eftarrow;\u61a9ightarrow;\u61aaf;\uc000\ud835\udd59bar;\u6015\u0180clt\u226f\u2274\u2278r;\uc000\ud835\udcbdas\xe8\u21f4rok;\u4127\u0100bp\u2282\u2287ull;\u6043hen\xbb\u1c5b\u0ae1\u22a3\0\u22aa\0\u22b8\u22c5\u22ce\0\u22d5\u22f3\0\0\u22f8\u2322\u2367\u2362\u237f\0\u2386\u23aa\u23b4cute\u803b\xed\u40ed\u0180;iy\u0771\u22b0\u22b5rc\u803b\xee\u40ee;\u4438\u0100cx\u22bc\u22bfy;\u4435cl\u803b\xa1\u40a1\u0100fr\u039f\u22c9;\uc000\ud835\udd26rave\u803b\xec\u40ec\u0200;ino\u073e\u22dd\u22e9\u22ee\u0100in\u22e2\u22e6nt;\u6a0ct;\u622dfin;\u69dcta;\u6129lig;\u4133\u0180aop\u22fe\u231a\u231d\u0180cgt\u2305\u2308\u2317r;\u412b\u0180elp\u071f\u230f\u2313in\xe5\u078ear\xf4\u0720h;\u4131f;\u62b7ed;\u41b5\u0280;cfot\u04f4\u232c\u2331\u233d\u2341are;\u6105in\u0100;t\u2338\u2339\u621eie;\u69dddo\xf4\u2319\u0280;celp\u0757\u234c\u2350\u235b\u2361al;\u62ba\u0100gr\u2355\u2359er\xf3\u1563\xe3\u234darhk;\u6a17rod;\u6a3c\u0200cgpt\u236f\u2372\u2376\u237by;\u4451on;\u412ff;\uc000\ud835\udd5aa;\u43b9uest\u803b\xbf\u40bf\u0100ci\u238a\u238fr;\uc000\ud835\udcben\u0280;Edsv\u04f4\u239b\u239d\u23a1\u04f3;\u62f9ot;\u62f5\u0100;v\u23a6\u23a7\u62f4;\u62f3\u0100;i\u0777\u23aelde;\u4129\u01eb\u23b8\0\u23bccy;\u4456l\u803b\xef\u40ef\u0300cfmosu\u23cc\u23d7\u23dc\u23e1\u23e7\u23f5\u0100iy\u23d1\u23d5rc;\u4135;\u4439r;\uc000\ud835\udd27ath;\u4237pf;\uc000\ud835\udd5b\u01e3\u23ec\0\u23f1r;\uc000\ud835\udcbfrcy;\u4458kcy;\u4454\u0400acfghjos\u240b\u2416\u2422\u2427\u242d\u2431\u2435\u243bppa\u0100;v\u2413\u2414\u43ba;\u43f0\u0100ey\u241b\u2420dil;\u4137;\u443ar;\uc000\ud835\udd28reen;\u4138cy;\u4445cy;\u445cpf;\uc000\ud835\udd5ccr;\uc000\ud835\udcc0\u0b80ABEHabcdefghjlmnoprstuv\u2470\u2481\u2486\u248d\u2491\u250e\u253d\u255a\u2580\u264e\u265e\u2665\u2679\u267d\u269a\u26b2\u26d8\u275d\u2768\u278b\u27c0\u2801\u2812\u0180art\u2477\u247a\u247cr\xf2\u09c6\xf2\u0395ail;\u691barr;\u690e\u0100;g\u0994\u248b;\u6a8bar;\u6962\u0963\u24a5\0\u24aa\0\u24b1\0\0\0\0\0\u24b5\u24ba\0\u24c6\u24c8\u24cd\0\u24f9ute;\u413amptyv;\u69b4ra\xee\u084cbda;\u43bbg\u0180;dl\u088e\u24c1\u24c3;\u6991\xe5\u088e;\u6a85uo\u803b\xab\u40abr\u0400;bfhlpst\u0899\u24de\u24e6\u24e9\u24eb\u24ee\u24f1\u24f5\u0100;f\u089d\u24e3s;\u691fs;\u691d\xeb\u2252p;\u61abl;\u6939im;\u6973l;\u61a2\u0180;ae\u24ff\u2500\u2504\u6aabil;\u6919\u0100;s\u2509\u250a\u6aad;\uc000\u2aad\ufe00\u0180abr\u2515\u2519\u251drr;\u690crk;\u6772\u0100ak\u2522\u252cc\u0100ek\u2528\u252a;\u407b;\u405b\u0100es\u2531\u2533;\u698bl\u0100du\u2539\u253b;\u698f;\u698d\u0200aeuy\u2546\u254b\u2556\u2558ron;\u413e\u0100di\u2550\u2554il;\u413c\xec\u08b0\xe2\u2529;\u443b\u0200cqrs\u2563\u2566\u256d\u257da;\u6936uo\u0100;r\u0e19\u1746\u0100du\u2572\u2577har;\u6967shar;\u694bh;\u61b2\u0280;fgqs\u258b\u258c\u0989\u25f3\u25ff\u6264t\u0280ahlrt\u2598\u25a4\u25b7\u25c2\u25e8rrow\u0100;t\u0899\u25a1a\xe9\u24f6arpoon\u0100du\u25af\u25b4own\xbb\u045ap\xbb\u0966eftarrows;\u61c7ight\u0180ahs\u25cd\u25d6\u25derrow\u0100;s\u08f4\u08a7arpoon\xf3\u0f98quigarro\xf7\u21f0hreetimes;\u62cb\u0180;qs\u258b\u0993\u25falan\xf4\u09ac\u0280;cdgs\u09ac\u260a\u260d\u261d\u2628c;\u6aa8ot\u0100;o\u2614\u2615\u6a7f\u0100;r\u261a\u261b\u6a81;\u6a83\u0100;e\u2622\u2625\uc000\u22da\ufe00s;\u6a93\u0280adegs\u2633\u2639\u263d\u2649\u264bppro\xf8\u24c6ot;\u62d6q\u0100gq\u2643\u2645\xf4\u0989gt\xf2\u248c\xf4\u099bi\xed\u09b2\u0180ilr\u2655\u08e1\u265asht;\u697c;\uc000\ud835\udd29\u0100;E\u099c\u2663;\u6a91\u0161\u2669\u2676r\u0100du\u25b2\u266e\u0100;l\u0965\u2673;\u696alk;\u6584cy;\u4459\u0280;acht\u0a48\u2688\u268b\u2691\u2696r\xf2\u25c1orne\xf2\u1d08ard;\u696bri;\u65fa\u0100io\u269f\u26a4dot;\u4140ust\u0100;a\u26ac\u26ad\u63b0che\xbb\u26ad\u0200Eaes\u26bb\u26bd\u26c9\u26d4;\u6268p\u0100;p\u26c3\u26c4\u6a89rox\xbb\u26c4\u0100;q\u26ce\u26cf\u6a87\u0100;q\u26ce\u26bbim;\u62e6\u0400abnoptwz\u26e9\u26f4\u26f7\u271a\u272f\u2741\u2747\u2750\u0100nr\u26ee\u26f1g;\u67ecr;\u61fdr\xeb\u08c1g\u0180lmr\u26ff\u270d\u2714eft\u0100ar\u09e6\u2707ight\xe1\u09f2apsto;\u67fcight\xe1\u09fdparrow\u0100lr\u2725\u2729ef\xf4\u24edight;\u61ac\u0180afl\u2736\u2739\u273dr;\u6985;\uc000\ud835\udd5dus;\u6a2dimes;\u6a34\u0161\u274b\u274fst;\u6217\xe1\u134e\u0180;ef\u2757\u2758\u1800\u65cange\xbb\u2758ar\u0100;l\u2764\u2765\u4028t;\u6993\u0280achmt\u2773\u2776\u277c\u2785\u2787r\xf2\u08a8orne\xf2\u1d8car\u0100;d\u0f98\u2783;\u696d;\u600eri;\u62bf\u0300achiqt\u2798\u279d\u0a40\u27a2\u27ae\u27bbquo;\u6039r;\uc000\ud835\udcc1m\u0180;eg\u09b2\u27aa\u27ac;\u6a8d;\u6a8f\u0100bu\u252a\u27b3o\u0100;r\u0e1f\u27b9;\u601arok;\u4142\u8400<;cdhilqr\u082b\u27d2\u2639\u27dc\u27e0\u27e5\u27ea\u27f0\u0100ci\u27d7\u27d9;\u6aa6r;\u6a79re\xe5\u25f2mes;\u62c9arr;\u6976uest;\u6a7b\u0100Pi\u27f5\u27f9ar;\u6996\u0180;ef\u2800\u092d\u181b\u65c3r\u0100du\u2807\u280dshar;\u694ahar;\u6966\u0100en\u2817\u2821rtneqq;\uc000\u2268\ufe00\xc5\u281e\u0700Dacdefhilnopsu\u2840\u2845\u2882\u288e\u2893\u28a0\u28a5\u28a8\u28da\u28e2\u28e4\u0a83\u28f3\u2902Dot;\u623a\u0200clpr\u284e\u2852\u2863\u287dr\u803b\xaf\u40af\u0100et\u2857\u2859;\u6642\u0100;e\u285e\u285f\u6720se\xbb\u285f\u0100;s\u103b\u2868to\u0200;dlu\u103b\u2873\u2877\u287bow\xee\u048cef\xf4\u090f\xf0\u13d1ker;\u65ae\u0100oy\u2887\u288cmma;\u6a29;\u443cash;\u6014asuredangle\xbb\u1626r;\uc000\ud835\udd2ao;\u6127\u0180cdn\u28af\u28b4\u28c9ro\u803b\xb5\u40b5\u0200;acd\u1464\u28bd\u28c0\u28c4s\xf4\u16a7ir;\u6af0ot\u80bb\xb7\u01b5us\u0180;bd\u28d2\u1903\u28d3\u6212\u0100;u\u1d3c\u28d8;\u6a2a\u0163\u28de\u28e1p;\u6adb\xf2\u2212\xf0\u0a81\u0100dp\u28e9\u28eeels;\u62a7f;\uc000\ud835\udd5e\u0100ct\u28f8\u28fdr;\uc000\ud835\udcc2pos\xbb\u159d\u0180;lm\u2909\u290a\u290d\u43bctimap;\u62b8\u0c00GLRVabcdefghijlmoprstuvw\u2942\u2953\u297e\u2989\u2998\u29da\u29e9\u2a15\u2a1a\u2a58\u2a5d\u2a83\u2a95\u2aa4\u2aa8\u2b04\u2b07\u2b44\u2b7f\u2bae\u2c34\u2c67\u2c7c\u2ce9\u0100gt\u2947\u294b;\uc000\u22d9\u0338\u0100;v\u2950\u0bcf\uc000\u226b\u20d2\u0180elt\u295a\u2972\u2976ft\u0100ar\u2961\u2967rrow;\u61cdightarrow;\u61ce;\uc000\u22d8\u0338\u0100;v\u297b\u0c47\uc000\u226a\u20d2ightarrow;\u61cf\u0100Dd\u298e\u2993ash;\u62afash;\u62ae\u0280bcnpt\u29a3\u29a7\u29ac\u29b1\u29ccla\xbb\u02deute;\u4144g;\uc000\u2220\u20d2\u0280;Eiop\u0d84\u29bc\u29c0\u29c5\u29c8;\uc000\u2a70\u0338d;\uc000\u224b\u0338s;\u4149ro\xf8\u0d84ur\u0100;a\u29d3\u29d4\u666el\u0100;s\u29d3\u0b38\u01f3\u29df\0\u29e3p\u80bb\xa0\u0b37mp\u0100;e\u0bf9\u0c00\u0280aeouy\u29f4\u29fe\u2a03\u2a10\u2a13\u01f0\u29f9\0\u29fb;\u6a43on;\u4148dil;\u4146ng\u0100;d\u0d7e\u2a0aot;\uc000\u2a6d\u0338p;\u6a42;\u443dash;\u6013\u0380;Aadqsx\u0b92\u2a29\u2a2d\u2a3b\u2a41\u2a45\u2a50rr;\u61d7r\u0100hr\u2a33\u2a36k;\u6924\u0100;o\u13f2\u13f0ot;\uc000\u2250\u0338ui\xf6\u0b63\u0100ei\u2a4a\u2a4ear;\u6928\xed\u0b98ist\u0100;s\u0ba0\u0b9fr;\uc000\ud835\udd2b\u0200Eest\u0bc5\u2a66\u2a79\u2a7c\u0180;qs\u0bbc\u2a6d\u0be1\u0180;qs\u0bbc\u0bc5\u2a74lan\xf4\u0be2i\xed\u0bea\u0100;r\u0bb6\u2a81\xbb\u0bb7\u0180Aap\u2a8a\u2a8d\u2a91r\xf2\u2971rr;\u61aear;\u6af2\u0180;sv\u0f8d\u2a9c\u0f8c\u0100;d\u2aa1\u2aa2\u62fc;\u62facy;\u445a\u0380AEadest\u2ab7\u2aba\u2abe\u2ac2\u2ac5\u2af6\u2af9r\xf2\u2966;\uc000\u2266\u0338rr;\u619ar;\u6025\u0200;fqs\u0c3b\u2ace\u2ae3\u2aeft\u0100ar\u2ad4\u2ad9rro\xf7\u2ac1ightarro\xf7\u2a90\u0180;qs\u0c3b\u2aba\u2aealan\xf4\u0c55\u0100;s\u0c55\u2af4\xbb\u0c36i\xed\u0c5d\u0100;r\u0c35\u2afei\u0100;e\u0c1a\u0c25i\xe4\u0d90\u0100pt\u2b0c\u2b11f;\uc000\ud835\udd5f\u8180\xac;in\u2b19\u2b1a\u2b36\u40acn\u0200;Edv\u0b89\u2b24\u2b28\u2b2e;\uc000\u22f9\u0338ot;\uc000\u22f5\u0338\u01e1\u0b89\u2b33\u2b35;\u62f7;\u62f6i\u0100;v\u0cb8\u2b3c\u01e1\u0cb8\u2b41\u2b43;\u62fe;\u62fd\u0180aor\u2b4b\u2b63\u2b69r\u0200;ast\u0b7b\u2b55\u2b5a\u2b5flle\xec\u0b7bl;\uc000\u2afd\u20e5;\uc000\u2202\u0338lint;\u6a14\u0180;ce\u0c92\u2b70\u2b73u\xe5\u0ca5\u0100;c\u0c98\u2b78\u0100;e\u0c92\u2b7d\xf1\u0c98\u0200Aait\u2b88\u2b8b\u2b9d\u2ba7r\xf2\u2988rr\u0180;cw\u2b94\u2b95\u2b99\u619b;\uc000\u2933\u0338;\uc000\u219d\u0338ghtarrow\xbb\u2b95ri\u0100;e\u0ccb\u0cd6\u0380chimpqu\u2bbd\u2bcd\u2bd9\u2b04\u0b78\u2be4\u2bef\u0200;cer\u0d32\u2bc6\u0d37\u2bc9u\xe5\u0d45;\uc000\ud835\udcc3ort\u026d\u2b05\0\0\u2bd6ar\xe1\u2b56m\u0100;e\u0d6e\u2bdf\u0100;q\u0d74\u0d73su\u0100bp\u2beb\u2bed\xe5\u0cf8\xe5\u0d0b\u0180bcp\u2bf6\u2c11\u2c19\u0200;Ees\u2bff\u2c00\u0d22\u2c04\u6284;\uc000\u2ac5\u0338et\u0100;e\u0d1b\u2c0bq\u0100;q\u0d23\u2c00c\u0100;e\u0d32\u2c17\xf1\u0d38\u0200;Ees\u2c22\u2c23\u0d5f\u2c27\u6285;\uc000\u2ac6\u0338et\u0100;e\u0d58\u2c2eq\u0100;q\u0d60\u2c23\u0200gilr\u2c3d\u2c3f\u2c45\u2c47\xec\u0bd7lde\u803b\xf1\u40f1\xe7\u0c43iangle\u0100lr\u2c52\u2c5ceft\u0100;e\u0c1a\u2c5a\xf1\u0c26ight\u0100;e\u0ccb\u2c65\xf1\u0cd7\u0100;m\u2c6c\u2c6d\u43bd\u0180;es\u2c74\u2c75\u2c79\u4023ro;\u6116p;\u6007\u0480DHadgilrs\u2c8f\u2c94\u2c99\u2c9e\u2ca3\u2cb0\u2cb6\u2cd3\u2ce3ash;\u62adarr;\u6904p;\uc000\u224d\u20d2ash;\u62ac\u0100et\u2ca8\u2cac;\uc000\u2265\u20d2;\uc000>\u20d2nfin;\u69de\u0180Aet\u2cbd\u2cc1\u2cc5rr;\u6902;\uc000\u2264\u20d2\u0100;r\u2cca\u2ccd\uc000<\u20d2ie;\uc000\u22b4\u20d2\u0100At\u2cd8\u2cdcrr;\u6903rie;\uc000\u22b5\u20d2im;\uc000\u223c\u20d2\u0180Aan\u2cf0\u2cf4\u2d02rr;\u61d6r\u0100hr\u2cfa\u2cfdk;\u6923\u0100;o\u13e7\u13e5ear;\u6927\u1253\u1a95\0\0\0\0\0\0\0\0\0\0\0\0\0\u2d2d\0\u2d38\u2d48\u2d60\u2d65\u2d72\u2d84\u1b07\0\0\u2d8d\u2dab\0\u2dc8\u2dce\0\u2ddc\u2e19\u2e2b\u2e3e\u2e43\u0100cs\u2d31\u1a97ute\u803b\xf3\u40f3\u0100iy\u2d3c\u2d45r\u0100;c\u1a9e\u2d42\u803b\xf4\u40f4;\u443e\u0280abios\u1aa0\u2d52\u2d57\u01c8\u2d5alac;\u4151v;\u6a38old;\u69bclig;\u4153\u0100cr\u2d69\u2d6dir;\u69bf;\uc000\ud835\udd2c\u036f\u2d79\0\0\u2d7c\0\u2d82n;\u42dbave\u803b\xf2\u40f2;\u69c1\u0100bm\u2d88\u0df4ar;\u69b5\u0200acit\u2d95\u2d98\u2da5\u2da8r\xf2\u1a80\u0100ir\u2d9d\u2da0r;\u69beoss;\u69bbn\xe5\u0e52;\u69c0\u0180aei\u2db1\u2db5\u2db9cr;\u414dga;\u43c9\u0180cdn\u2dc0\u2dc5\u01cdron;\u43bf;\u69b6pf;\uc000\ud835\udd60\u0180ael\u2dd4\u2dd7\u01d2r;\u69b7rp;\u69b9\u0380;adiosv\u2dea\u2deb\u2dee\u2e08\u2e0d\u2e10\u2e16\u6228r\xf2\u1a86\u0200;efm\u2df7\u2df8\u2e02\u2e05\u6a5dr\u0100;o\u2dfe\u2dff\u6134f\xbb\u2dff\u803b\xaa\u40aa\u803b\xba\u40bagof;\u62b6r;\u6a56lope;\u6a57;\u6a5b\u0180clo\u2e1f\u2e21\u2e27\xf2\u2e01ash\u803b\xf8\u40f8l;\u6298i\u016c\u2e2f\u2e34de\u803b\xf5\u40f5es\u0100;a\u01db\u2e3as;\u6a36ml\u803b\xf6\u40f6bar;\u633d\u0ae1\u2e5e\0\u2e7d\0\u2e80\u2e9d\0\u2ea2\u2eb9\0\0\u2ecb\u0e9c\0\u2f13\0\0\u2f2b\u2fbc\0\u2fc8r\u0200;ast\u0403\u2e67\u2e72\u0e85\u8100\xb6;l\u2e6d\u2e6e\u40b6le\xec\u0403\u0269\u2e78\0\0\u2e7bm;\u6af3;\u6afdy;\u443fr\u0280cimpt\u2e8b\u2e8f\u2e93\u1865\u2e97nt;\u4025od;\u402eil;\u6030enk;\u6031r;\uc000\ud835\udd2d\u0180imo\u2ea8\u2eb0\u2eb4\u0100;v\u2ead\u2eae\u43c6;\u43d5ma\xf4\u0a76ne;\u660e\u0180;tv\u2ebf\u2ec0\u2ec8\u43c0chfork\xbb\u1ffd;\u43d6\u0100au\u2ecf\u2edfn\u0100ck\u2ed5\u2eddk\u0100;h\u21f4\u2edb;\u610e\xf6\u21f4s\u0480;abcdemst\u2ef3\u2ef4\u1908\u2ef9\u2efd\u2f04\u2f06\u2f0a\u2f0e\u402bcir;\u6a23ir;\u6a22\u0100ou\u1d40\u2f02;\u6a25;\u6a72n\u80bb\xb1\u0e9dim;\u6a26wo;\u6a27\u0180ipu\u2f19\u2f20\u2f25ntint;\u6a15f;\uc000\ud835\udd61nd\u803b\xa3\u40a3\u0500;Eaceinosu\u0ec8\u2f3f\u2f41\u2f44\u2f47\u2f81\u2f89\u2f92\u2f7e\u2fb6;\u6ab3p;\u6ab7u\xe5\u0ed9\u0100;c\u0ece\u2f4c\u0300;acens\u0ec8\u2f59\u2f5f\u2f66\u2f68\u2f7eppro\xf8\u2f43urlye\xf1\u0ed9\xf1\u0ece\u0180aes\u2f6f\u2f76\u2f7approx;\u6ab9qq;\u6ab5im;\u62e8i\xed\u0edfme\u0100;s\u2f88\u0eae\u6032\u0180Eas\u2f78\u2f90\u2f7a\xf0\u2f75\u0180dfp\u0eec\u2f99\u2faf\u0180als\u2fa0\u2fa5\u2faalar;\u632eine;\u6312urf;\u6313\u0100;t\u0efb\u2fb4\xef\u0efbrel;\u62b0\u0100ci\u2fc0\u2fc5r;\uc000\ud835\udcc5;\u43c8ncsp;\u6008\u0300fiopsu\u2fda\u22e2\u2fdf\u2fe5\u2feb\u2ff1r;\uc000\ud835\udd2epf;\uc000\ud835\udd62rime;\u6057cr;\uc000\ud835\udcc6\u0180aeo\u2ff8\u3009\u3013t\u0100ei\u2ffe\u3005rnion\xf3\u06b0nt;\u6a16st\u0100;e\u3010\u3011\u403f\xf1\u1f19\xf4\u0f14\u0a80ABHabcdefhilmnoprstux\u3040\u3051\u3055\u3059\u30e0\u310e\u312b\u3147\u3162\u3172\u318e\u3206\u3215\u3224\u3229\u3258\u326e\u3272\u3290\u32b0\u32b7\u0180art\u3047\u304a\u304cr\xf2\u10b3\xf2\u03ddail;\u691car\xf2\u1c65ar;\u6964\u0380cdenqrt\u3068\u3075\u3078\u307f\u308f\u3094\u30cc\u0100eu\u306d\u3071;\uc000\u223d\u0331te;\u4155i\xe3\u116emptyv;\u69b3g\u0200;del\u0fd1\u3089\u308b\u308d;\u6992;\u69a5\xe5\u0fd1uo\u803b\xbb\u40bbr\u0580;abcfhlpstw\u0fdc\u30ac\u30af\u30b7\u30b9\u30bc\u30be\u30c0\u30c3\u30c7\u30cap;\u6975\u0100;f\u0fe0\u30b4s;\u6920;\u6933s;\u691e\xeb\u225d\xf0\u272el;\u6945im;\u6974l;\u61a3;\u619d\u0100ai\u30d1\u30d5il;\u691ao\u0100;n\u30db\u30dc\u6236al\xf3\u0f1e\u0180abr\u30e7\u30ea\u30eer\xf2\u17e5rk;\u6773\u0100ak\u30f3\u30fdc\u0100ek\u30f9\u30fb;\u407d;\u405d\u0100es\u3102\u3104;\u698cl\u0100du\u310a\u310c;\u698e;\u6990\u0200aeuy\u3117\u311c\u3127\u3129ron;\u4159\u0100di\u3121\u3125il;\u4157\xec\u0ff2\xe2\u30fa;\u4440\u0200clqs\u3134\u3137\u313d\u3144a;\u6937dhar;\u6969uo\u0100;r\u020e\u020dh;\u61b3\u0180acg\u314e\u315f\u0f44l\u0200;ips\u0f78\u3158\u315b\u109cn\xe5\u10bbar\xf4\u0fa9t;\u65ad\u0180ilr\u3169\u1023\u316esht;\u697d;\uc000\ud835\udd2f\u0100ao\u3177\u3186r\u0100du\u317d\u317f\xbb\u047b\u0100;l\u1091\u3184;\u696c\u0100;v\u318b\u318c\u43c1;\u43f1\u0180gns\u3195\u31f9\u31fcht\u0300ahlrst\u31a4\u31b0\u31c2\u31d8\u31e4\u31eerrow\u0100;t\u0fdc\u31ada\xe9\u30c8arpoon\u0100du\u31bb\u31bfow\xee\u317ep\xbb\u1092eft\u0100ah\u31ca\u31d0rrow\xf3\u0feaarpoon\xf3\u0551ightarrows;\u61c9quigarro\xf7\u30cbhreetimes;\u62ccg;\u42daingdotse\xf1\u1f32\u0180ahm\u320d\u3210\u3213r\xf2\u0feaa\xf2\u0551;\u600foust\u0100;a\u321e\u321f\u63b1che\xbb\u321fmid;\u6aee\u0200abpt\u3232\u323d\u3240\u3252\u0100nr\u3237\u323ag;\u67edr;\u61fer\xeb\u1003\u0180afl\u3247\u324a\u324er;\u6986;\uc000\ud835\udd63us;\u6a2eimes;\u6a35\u0100ap\u325d\u3267r\u0100;g\u3263\u3264\u4029t;\u6994olint;\u6a12ar\xf2\u31e3\u0200achq\u327b\u3280\u10bc\u3285quo;\u603ar;\uc000\ud835\udcc7\u0100bu\u30fb\u328ao\u0100;r\u0214\u0213\u0180hir\u3297\u329b\u32a0re\xe5\u31f8mes;\u62cai\u0200;efl\u32aa\u1059\u1821\u32ab\u65b9tri;\u69celuhar;\u6968;\u611e\u0d61\u32d5\u32db\u32df\u332c\u3338\u3371\0\u337a\u33a4\0\0\u33ec\u33f0\0\u3428\u3448\u345a\u34ad\u34b1\u34ca\u34f1\0\u3616\0\0\u3633cute;\u415bqu\xef\u27ba\u0500;Eaceinpsy\u11ed\u32f3\u32f5\u32ff\u3302\u330b\u330f\u331f\u3326\u3329;\u6ab4\u01f0\u32fa\0\u32fc;\u6ab8on;\u4161u\xe5\u11fe\u0100;d\u11f3\u3307il;\u415frc;\u415d\u0180Eas\u3316\u3318\u331b;\u6ab6p;\u6abaim;\u62e9olint;\u6a13i\xed\u1204;\u4441ot\u0180;be\u3334\u1d47\u3335\u62c5;\u6a66\u0380Aacmstx\u3346\u334a\u3357\u335b\u335e\u3363\u336drr;\u61d8r\u0100hr\u3350\u3352\xeb\u2228\u0100;o\u0a36\u0a34t\u803b\xa7\u40a7i;\u403bwar;\u6929m\u0100in\u3369\xf0nu\xf3\xf1t;\u6736r\u0100;o\u3376\u2055\uc000\ud835\udd30\u0200acoy\u3382\u3386\u3391\u33a0rp;\u666f\u0100hy\u338b\u338fcy;\u4449;\u4448rt\u026d\u3399\0\0\u339ci\xe4\u1464ara\xec\u2e6f\u803b\xad\u40ad\u0100gm\u33a8\u33b4ma\u0180;fv\u33b1\u33b2\u33b2\u43c3;\u43c2\u0400;deglnpr\u12ab\u33c5\u33c9\u33ce\u33d6\u33de\u33e1\u33e6ot;\u6a6a\u0100;q\u12b1\u12b0\u0100;E\u33d3\u33d4\u6a9e;\u6aa0\u0100;E\u33db\u33dc\u6a9d;\u6a9fe;\u6246lus;\u6a24arr;\u6972ar\xf2\u113d\u0200aeit\u33f8\u3408\u340f\u3417\u0100ls\u33fd\u3404lsetm\xe9\u336ahp;\u6a33parsl;\u69e4\u0100dl\u1463\u3414e;\u6323\u0100;e\u341c\u341d\u6aaa\u0100;s\u3422\u3423\u6aac;\uc000\u2aac\ufe00\u0180flp\u342e\u3433\u3442tcy;\u444c\u0100;b\u3438\u3439\u402f\u0100;a\u343e\u343f\u69c4r;\u633ff;\uc000\ud835\udd64a\u0100dr\u344d\u0402es\u0100;u\u3454\u3455\u6660it\xbb\u3455\u0180csu\u3460\u3479\u349f\u0100au\u3465\u346fp\u0100;s\u1188\u346b;\uc000\u2293\ufe00p\u0100;s\u11b4\u3475;\uc000\u2294\ufe00u\u0100bp\u347f\u348f\u0180;es\u1197\u119c\u3486et\u0100;e\u1197\u348d\xf1\u119d\u0180;es\u11a8\u11ad\u3496et\u0100;e\u11a8\u349d\xf1\u11ae\u0180;af\u117b\u34a6\u05b0r\u0165\u34ab\u05b1\xbb\u117car\xf2\u1148\u0200cemt\u34b9\u34be\u34c2\u34c5r;\uc000\ud835\udcc8tm\xee\xf1i\xec\u3415ar\xe6\u11be\u0100ar\u34ce\u34d5r\u0100;f\u34d4\u17bf\u6606\u0100an\u34da\u34edight\u0100ep\u34e3\u34eapsilo\xee\u1ee0h\xe9\u2eafs\xbb\u2852\u0280bcmnp\u34fb\u355e\u1209\u358b\u358e\u0480;Edemnprs\u350e\u350f\u3511\u3515\u351e\u3523\u352c\u3531\u3536\u6282;\u6ac5ot;\u6abd\u0100;d\u11da\u351aot;\u6ac3ult;\u6ac1\u0100Ee\u3528\u352a;\u6acb;\u628alus;\u6abfarr;\u6979\u0180eiu\u353d\u3552\u3555t\u0180;en\u350e\u3545\u354bq\u0100;q\u11da\u350feq\u0100;q\u352b\u3528m;\u6ac7\u0100bp\u355a\u355c;\u6ad5;\u6ad3c\u0300;acens\u11ed\u356c\u3572\u3579\u357b\u3326ppro\xf8\u32faurlye\xf1\u11fe\xf1\u11f3\u0180aes\u3582\u3588\u331bppro\xf8\u331aq\xf1\u3317g;\u666a\u0680123;Edehlmnps\u35a9\u35ac\u35af\u121c\u35b2\u35b4\u35c0\u35c9\u35d5\u35da\u35df\u35e8\u35ed\u803b\xb9\u40b9\u803b\xb2\u40b2\u803b\xb3\u40b3;\u6ac6\u0100os\u35b9\u35bct;\u6abeub;\u6ad8\u0100;d\u1222\u35c5ot;\u6ac4s\u0100ou\u35cf\u35d2l;\u67c9b;\u6ad7arr;\u697bult;\u6ac2\u0100Ee\u35e4\u35e6;\u6acc;\u628blus;\u6ac0\u0180eiu\u35f4\u3609\u360ct\u0180;en\u121c\u35fc\u3602q\u0100;q\u1222\u35b2eq\u0100;q\u35e7\u35e4m;\u6ac8\u0100bp\u3611\u3613;\u6ad4;\u6ad6\u0180Aan\u361c\u3620\u362drr;\u61d9r\u0100hr\u3626\u3628\xeb\u222e\u0100;o\u0a2b\u0a29war;\u692alig\u803b\xdf\u40df\u0be1\u3651\u365d\u3660\u12ce\u3673\u3679\0\u367e\u36c2\0\0\0\0\0\u36db\u3703\0\u3709\u376c\0\0\0\u3787\u0272\u3656\0\0\u365bget;\u6316;\u43c4r\xeb\u0e5f\u0180aey\u3666\u366b\u3670ron;\u4165dil;\u4163;\u4442lrec;\u6315r;\uc000\ud835\udd31\u0200eiko\u3686\u369d\u36b5\u36bc\u01f2\u368b\0\u3691e\u01004f\u1284\u1281a\u0180;sv\u3698\u3699\u369b\u43b8ym;\u43d1\u0100cn\u36a2\u36b2k\u0100as\u36a8\u36aeppro\xf8\u12c1im\xbb\u12acs\xf0\u129e\u0100as\u36ba\u36ae\xf0\u12c1rn\u803b\xfe\u40fe\u01ec\u031f\u36c6\u22e7es\u8180\xd7;bd\u36cf\u36d0\u36d8\u40d7\u0100;a\u190f\u36d5r;\u6a31;\u6a30\u0180eps\u36e1\u36e3\u3700\xe1\u2a4d\u0200;bcf\u0486\u36ec\u36f0\u36f4ot;\u6336ir;\u6af1\u0100;o\u36f9\u36fc\uc000\ud835\udd65rk;\u6ada\xe1\u3362rime;\u6034\u0180aip\u370f\u3712\u3764d\xe5\u1248\u0380adempst\u3721\u374d\u3740\u3751\u3757\u375c\u375fngle\u0280;dlqr\u3730\u3731\u3736\u3740\u3742\u65b5own\xbb\u1dbbeft\u0100;e\u2800\u373e\xf1\u092e;\u625cight\u0100;e\u32aa\u374b\xf1\u105aot;\u65ecinus;\u6a3alus;\u6a39b;\u69cdime;\u6a3bezium;\u63e2\u0180cht\u3772\u377d\u3781\u0100ry\u3777\u377b;\uc000\ud835\udcc9;\u4446cy;\u445brok;\u4167\u0100io\u378b\u378ex\xf4\u1777head\u0100lr\u3797\u37a0eftarro\xf7\u084fightarrow\xbb\u0f5d\u0900AHabcdfghlmoprstuw\u37d0\u37d3\u37d7\u37e4\u37f0\u37fc\u380e\u381c\u3823\u3834\u3851\u385d\u386b\u38a9\u38cc\u38d2\u38ea\u38f6r\xf2\u03edar;\u6963\u0100cr\u37dc\u37e2ute\u803b\xfa\u40fa\xf2\u1150r\u01e3\u37ea\0\u37edy;\u445eve;\u416d\u0100iy\u37f5\u37farc\u803b\xfb\u40fb;\u4443\u0180abh\u3803\u3806\u380br\xf2\u13adlac;\u4171a\xf2\u13c3\u0100ir\u3813\u3818sht;\u697e;\uc000\ud835\udd32rave\u803b\xf9\u40f9\u0161\u3827\u3831r\u0100lr\u382c\u382e\xbb\u0957\xbb\u1083lk;\u6580\u0100ct\u3839\u384d\u026f\u383f\0\0\u384arn\u0100;e\u3845\u3846\u631cr\xbb\u3846op;\u630fri;\u65f8\u0100al\u3856\u385acr;\u416b\u80bb\xa8\u0349\u0100gp\u3862\u3866on;\u4173f;\uc000\ud835\udd66\u0300adhlsu\u114b\u3878\u387d\u1372\u3891\u38a0own\xe1\u13b3arpoon\u0100lr\u3888\u388cef\xf4\u382digh\xf4\u382fi\u0180;hl\u3899\u389a\u389c\u43c5\xbb\u13faon\xbb\u389aparrows;\u61c8\u0180cit\u38b0\u38c4\u38c8\u026f\u38b6\0\0\u38c1rn\u0100;e\u38bc\u38bd\u631dr\xbb\u38bdop;\u630eng;\u416fri;\u65f9cr;\uc000\ud835\udcca\u0180dir\u38d9\u38dd\u38e2ot;\u62f0lde;\u4169i\u0100;f\u3730\u38e8\xbb\u1813\u0100am\u38ef\u38f2r\xf2\u38a8l\u803b\xfc\u40fcangle;\u69a7\u0780ABDacdeflnoprsz\u391c\u391f\u3929\u392d\u39b5\u39b8\u39bd\u39df\u39e4\u39e8\u39f3\u39f9\u39fd\u3a01\u3a20r\xf2\u03f7ar\u0100;v\u3926\u3927\u6ae8;\u6ae9as\xe8\u03e1\u0100nr\u3932\u3937grt;\u699c\u0380eknprst\u34e3\u3946\u394b\u3952\u395d\u3964\u3996app\xe1\u2415othin\xe7\u1e96\u0180hir\u34eb\u2ec8\u3959op\xf4\u2fb5\u0100;h\u13b7\u3962\xef\u318d\u0100iu\u3969\u396dgm\xe1\u33b3\u0100bp\u3972\u3984setneq\u0100;q\u397d\u3980\uc000\u228a\ufe00;\uc000\u2acb\ufe00setneq\u0100;q\u398f\u3992\uc000\u228b\ufe00;\uc000\u2acc\ufe00\u0100hr\u399b\u399fet\xe1\u369ciangle\u0100lr\u39aa\u39afeft\xbb\u0925ight\xbb\u1051y;\u4432ash\xbb\u1036\u0180elr\u39c4\u39d2\u39d7\u0180;be\u2dea\u39cb\u39cfar;\u62bbq;\u625alip;\u62ee\u0100bt\u39dc\u1468a\xf2\u1469r;\uc000\ud835\udd33tr\xe9\u39aesu\u0100bp\u39ef\u39f1\xbb\u0d1c\xbb\u0d59pf;\uc000\ud835\udd67ro\xf0\u0efbtr\xe9\u39b4\u0100cu\u3a06\u3a0br;\uc000\ud835\udccb\u0100bp\u3a10\u3a18n\u0100Ee\u3980\u3a16\xbb\u397en\u0100Ee\u3992\u3a1e\xbb\u3990igzag;\u699a\u0380cefoprs\u3a36\u3a3b\u3a56\u3a5b\u3a54\u3a61\u3a6airc;\u4175\u0100di\u3a40\u3a51\u0100bg\u3a45\u3a49ar;\u6a5fe\u0100;q\u15fa\u3a4f;\u6259erp;\u6118r;\uc000\ud835\udd34pf;\uc000\ud835\udd68\u0100;e\u1479\u3a66at\xe8\u1479cr;\uc000\ud835\udccc\u0ae3\u178e\u3a87\0\u3a8b\0\u3a90\u3a9b\0\0\u3a9d\u3aa8\u3aab\u3aaf\0\0\u3ac3\u3ace\0\u3ad8\u17dc\u17dftr\xe9\u17d1r;\uc000\ud835\udd35\u0100Aa\u3a94\u3a97r\xf2\u03c3r\xf2\u09f6;\u43be\u0100Aa\u3aa1\u3aa4r\xf2\u03b8r\xf2\u09eba\xf0\u2713is;\u62fb\u0180dpt\u17a4\u3ab5\u3abe\u0100fl\u3aba\u17a9;\uc000\ud835\udd69im\xe5\u17b2\u0100Aa\u3ac7\u3acar\xf2\u03cer\xf2\u0a01\u0100cq\u3ad2\u17b8r;\uc000\ud835\udccd\u0100pt\u17d6\u3adcr\xe9\u17d4\u0400acefiosu\u3af0\u3afd\u3b08\u3b0c\u3b11\u3b15\u3b1b\u3b21c\u0100uy\u3af6\u3afbte\u803b\xfd\u40fd;\u444f\u0100iy\u3b02\u3b06rc;\u4177;\u444bn\u803b\xa5\u40a5r;\uc000\ud835\udd36cy;\u4457pf;\uc000\ud835\udd6acr;\uc000\ud835\udcce\u0100cm\u3b26\u3b29y;\u444el\u803b\xff\u40ff\u0500acdefhiosw\u3b42\u3b48\u3b54\u3b58\u3b64\u3b69\u3b6d\u3b74\u3b7a\u3b80cute;\u417a\u0100ay\u3b4d\u3b52ron;\u417e;\u4437ot;\u417c\u0100et\u3b5d\u3b61tr\xe6\u155fa;\u43b6r;\uc000\ud835\udd37cy;\u4436grarr;\u61ddpf;\uc000\ud835\udd6bcr;\uc000\ud835\udccf\u0100jn\u3b85\u3b87;\u600dj;\u600c'.split("").map((c => c.charCodeAt(0)))); + // Generated using scripts/write-decode-map.ts + var xmlDecodeTree = new Uint16Array( + // prettier-ignore + "\u0200aglq\t\x15\x18\x1b\u026d\x0f\0\0\x12p;\u4026os;\u4027t;\u403et;\u403cuot;\u4022".split("").map((c => c.charCodeAt(0)))); + // Adapted from https://github.com/mathiasbynens/he/blob/36afe179392226cf1b6ccdb16ebbb7a5a844d93a/src/he.js#L106-L134 + var _a; + const decodeMap = new Map([ [ 0, 65533 ], + // C1 Unicode control character reference replacements + [ 128, 8364 ], [ 130, 8218 ], [ 131, 402 ], [ 132, 8222 ], [ 133, 8230 ], [ 134, 8224 ], [ 135, 8225 ], [ 136, 710 ], [ 137, 8240 ], [ 138, 352 ], [ 139, 8249 ], [ 140, 338 ], [ 142, 381 ], [ 145, 8216 ], [ 146, 8217 ], [ 147, 8220 ], [ 148, 8221 ], [ 149, 8226 ], [ 150, 8211 ], [ 151, 8212 ], [ 152, 732 ], [ 153, 8482 ], [ 154, 353 ], [ 155, 8250 ], [ 156, 339 ], [ 158, 382 ], [ 159, 376 ] ]); + /** + * Polyfill for `String.fromCodePoint`. It is used to create a string from a Unicode code point. + */ const fromCodePoint$1 = + // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition, node/no-unsupported-features/es-builtins + (_a = String.fromCodePoint) !== null && _a !== void 0 ? _a : function(codePoint) { + let output = ""; + if (codePoint > 65535) { + codePoint -= 65536; + output += String.fromCharCode(codePoint >>> 10 & 1023 | 55296); + codePoint = 56320 | codePoint & 1023; + } + output += String.fromCharCode(codePoint); + return output; + }; + /** + * Replace the given code point with a replacement character if it is a + * surrogate or is outside the valid range. Otherwise return the code + * point unchanged. + */ function replaceCodePoint(codePoint) { + var _a; + if (codePoint >= 55296 && codePoint <= 57343 || codePoint > 1114111) { + return 65533; + } + return (_a = decodeMap.get(codePoint)) !== null && _a !== void 0 ? _a : codePoint; + } + var CharCodes; + (function(CharCodes) { + CharCodes[CharCodes["NUM"] = 35] = "NUM"; + CharCodes[CharCodes["SEMI"] = 59] = "SEMI"; + CharCodes[CharCodes["EQUALS"] = 61] = "EQUALS"; + CharCodes[CharCodes["ZERO"] = 48] = "ZERO"; + CharCodes[CharCodes["NINE"] = 57] = "NINE"; + CharCodes[CharCodes["LOWER_A"] = 97] = "LOWER_A"; + CharCodes[CharCodes["LOWER_F"] = 102] = "LOWER_F"; + CharCodes[CharCodes["LOWER_X"] = 120] = "LOWER_X"; + CharCodes[CharCodes["LOWER_Z"] = 122] = "LOWER_Z"; + CharCodes[CharCodes["UPPER_A"] = 65] = "UPPER_A"; + CharCodes[CharCodes["UPPER_F"] = 70] = "UPPER_F"; + CharCodes[CharCodes["UPPER_Z"] = 90] = "UPPER_Z"; + })(CharCodes || (CharCodes = {})); + /** Bit that needs to be set to convert an upper case ASCII character to lower case */ const TO_LOWER_BIT = 32; + var BinTrieFlags; + (function(BinTrieFlags) { + BinTrieFlags[BinTrieFlags["VALUE_LENGTH"] = 49152] = "VALUE_LENGTH"; + BinTrieFlags[BinTrieFlags["BRANCH_LENGTH"] = 16256] = "BRANCH_LENGTH"; + BinTrieFlags[BinTrieFlags["JUMP_TABLE"] = 127] = "JUMP_TABLE"; + })(BinTrieFlags || (BinTrieFlags = {})); + function isNumber(code) { + return code >= CharCodes.ZERO && code <= CharCodes.NINE; + } + function isHexadecimalCharacter(code) { + return code >= CharCodes.UPPER_A && code <= CharCodes.UPPER_F || code >= CharCodes.LOWER_A && code <= CharCodes.LOWER_F; + } + function isAsciiAlphaNumeric(code) { + return code >= CharCodes.UPPER_A && code <= CharCodes.UPPER_Z || code >= CharCodes.LOWER_A && code <= CharCodes.LOWER_Z || isNumber(code); + } + /** + * Checks if the given character is a valid end character for an entity in an attribute. + * + * Attribute values that aren't terminated properly aren't parsed, and shouldn't lead to a parser error. + * See the example in https://html.spec.whatwg.org/multipage/parsing.html#named-character-reference-state + */ function isEntityInAttributeInvalidEnd(code) { + return code === CharCodes.EQUALS || isAsciiAlphaNumeric(code); + } + var EntityDecoderState; + (function(EntityDecoderState) { + EntityDecoderState[EntityDecoderState["EntityStart"] = 0] = "EntityStart"; + EntityDecoderState[EntityDecoderState["NumericStart"] = 1] = "NumericStart"; + EntityDecoderState[EntityDecoderState["NumericDecimal"] = 2] = "NumericDecimal"; + EntityDecoderState[EntityDecoderState["NumericHex"] = 3] = "NumericHex"; + EntityDecoderState[EntityDecoderState["NamedEntity"] = 4] = "NamedEntity"; + })(EntityDecoderState || (EntityDecoderState = {})); + var DecodingMode; + (function(DecodingMode) { + /** Entities in text nodes that can end with any character. */ + DecodingMode[DecodingMode["Legacy"] = 0] = "Legacy"; + /** Only allow entities terminated with a semicolon. */ DecodingMode[DecodingMode["Strict"] = 1] = "Strict"; + /** Entities in attributes have limitations on ending characters. */ DecodingMode[DecodingMode["Attribute"] = 2] = "Attribute"; + })(DecodingMode || (DecodingMode = {})); + /** + * Token decoder with support of writing partial entities. + */ class EntityDecoder { + constructor(/** The tree used to decode entities. */ + decodeTree, + /** + * The function that is called when a codepoint is decoded. + * + * For multi-byte named entities, this will be called multiple times, + * with the second codepoint, and the same `consumed` value. + * + * @param codepoint The decoded codepoint. + * @param consumed The number of bytes consumed by the decoder. + */ + emitCodePoint, /** An object that is used to produce errors. */ + errors) { + this.decodeTree = decodeTree; + this.emitCodePoint = emitCodePoint; + this.errors = errors; + /** The current state of the decoder. */ this.state = EntityDecoderState.EntityStart; + /** Characters that were consumed while parsing an entity. */ this.consumed = 1; + /** + * The result of the entity. + * + * Either the result index of a numeric entity, or the codepoint of a + * numeric entity. + */ this.result = 0; + /** The current index in the decode tree. */ this.treeIndex = 0; + /** The number of characters that were consumed in excess. */ this.excess = 1; + /** The mode in which the decoder is operating. */ this.decodeMode = DecodingMode.Strict; + } + /** Resets the instance to make it reusable. */ startEntity(decodeMode) { + this.decodeMode = decodeMode; + this.state = EntityDecoderState.EntityStart; + this.result = 0; + this.treeIndex = 0; + this.excess = 1; + this.consumed = 1; + } + /** + * Write an entity to the decoder. This can be called multiple times with partial entities. + * If the entity is incomplete, the decoder will return -1. + * + * Mirrors the implementation of `getDecoder`, but with the ability to stop decoding if the + * entity is incomplete, and resume when the next string is written. + * + * @param string The string containing the entity (or a continuation of the entity). + * @param offset The offset at which the entity begins. Should be 0 if this is not the first call. + * @returns The number of characters that were consumed, or -1 if the entity is incomplete. + */ write(str, offset) { + switch (this.state) { + case EntityDecoderState.EntityStart: + { + if (str.charCodeAt(offset) === CharCodes.NUM) { + this.state = EntityDecoderState.NumericStart; + this.consumed += 1; + return this.stateNumericStart(str, offset + 1); + } + this.state = EntityDecoderState.NamedEntity; + return this.stateNamedEntity(str, offset); + } + + case EntityDecoderState.NumericStart: + { + return this.stateNumericStart(str, offset); + } + + case EntityDecoderState.NumericDecimal: + { + return this.stateNumericDecimal(str, offset); + } + + case EntityDecoderState.NumericHex: + { + return this.stateNumericHex(str, offset); + } + + case EntityDecoderState.NamedEntity: + { + return this.stateNamedEntity(str, offset); + } + } + } + /** + * Switches between the numeric decimal and hexadecimal states. + * + * Equivalent to the `Numeric character reference state` in the HTML spec. + * + * @param str The string containing the entity (or a continuation of the entity). + * @param offset The current offset. + * @returns The number of characters that were consumed, or -1 if the entity is incomplete. + */ stateNumericStart(str, offset) { + if (offset >= str.length) { + return -1; + } + if ((str.charCodeAt(offset) | TO_LOWER_BIT) === CharCodes.LOWER_X) { + this.state = EntityDecoderState.NumericHex; + this.consumed += 1; + return this.stateNumericHex(str, offset + 1); + } + this.state = EntityDecoderState.NumericDecimal; + return this.stateNumericDecimal(str, offset); + } + addToNumericResult(str, start, end, base) { + if (start !== end) { + const digitCount = end - start; + this.result = this.result * Math.pow(base, digitCount) + parseInt(str.substr(start, digitCount), base); + this.consumed += digitCount; + } + } + /** + * Parses a hexadecimal numeric entity. + * + * Equivalent to the `Hexademical character reference state` in the HTML spec. + * + * @param str The string containing the entity (or a continuation of the entity). + * @param offset The current offset. + * @returns The number of characters that were consumed, or -1 if the entity is incomplete. + */ stateNumericHex(str, offset) { + const startIdx = offset; + while (offset < str.length) { + const char = str.charCodeAt(offset); + if (isNumber(char) || isHexadecimalCharacter(char)) { + offset += 1; + } else { + this.addToNumericResult(str, startIdx, offset, 16); + return this.emitNumericEntity(char, 3); + } + } + this.addToNumericResult(str, startIdx, offset, 16); + return -1; + } + /** + * Parses a decimal numeric entity. + * + * Equivalent to the `Decimal character reference state` in the HTML spec. + * + * @param str The string containing the entity (or a continuation of the entity). + * @param offset The current offset. + * @returns The number of characters that were consumed, or -1 if the entity is incomplete. + */ stateNumericDecimal(str, offset) { + const startIdx = offset; + while (offset < str.length) { + const char = str.charCodeAt(offset); + if (isNumber(char)) { + offset += 1; + } else { + this.addToNumericResult(str, startIdx, offset, 10); + return this.emitNumericEntity(char, 2); + } + } + this.addToNumericResult(str, startIdx, offset, 10); + return -1; + } + /** + * Validate and emit a numeric entity. + * + * Implements the logic from the `Hexademical character reference start + * state` and `Numeric character reference end state` in the HTML spec. + * + * @param lastCp The last code point of the entity. Used to see if the + * entity was terminated with a semicolon. + * @param expectedLength The minimum number of characters that should be + * consumed. Used to validate that at least one digit + * was consumed. + * @returns The number of characters that were consumed. + */ emitNumericEntity(lastCp, expectedLength) { + var _a; + // Ensure we consumed at least one digit. + if (this.consumed <= expectedLength) { + (_a = this.errors) === null || _a === void 0 ? void 0 : _a.absenceOfDigitsInNumericCharacterReference(this.consumed); + return 0; + } + // Figure out if this is a legit end of the entity + if (lastCp === CharCodes.SEMI) { + this.consumed += 1; + } else if (this.decodeMode === DecodingMode.Strict) { + return 0; + } + this.emitCodePoint(replaceCodePoint(this.result), this.consumed); + if (this.errors) { + if (lastCp !== CharCodes.SEMI) { + this.errors.missingSemicolonAfterCharacterReference(); + } + this.errors.validateNumericCharacterReference(this.result); + } + return this.consumed; + } + /** + * Parses a named entity. + * + * Equivalent to the `Named character reference state` in the HTML spec. + * + * @param str The string containing the entity (or a continuation of the entity). + * @param offset The current offset. + * @returns The number of characters that were consumed, or -1 if the entity is incomplete. + */ stateNamedEntity(str, offset) { + const {decodeTree: decodeTree} = this; + let current = decodeTree[this.treeIndex]; + // The mask is the number of bytes of the value, including the current byte. + let valueLength = (current & BinTrieFlags.VALUE_LENGTH) >> 14; + for (;offset < str.length; offset++, this.excess++) { + const char = str.charCodeAt(offset); + this.treeIndex = determineBranch(decodeTree, current, this.treeIndex + Math.max(1, valueLength), char); + if (this.treeIndex < 0) { + return this.result === 0 || + // If we are parsing an attribute + this.decodeMode === DecodingMode.Attribute && ( + // We shouldn't have consumed any characters after the entity, + valueLength === 0 || + // And there should be no invalid characters. + isEntityInAttributeInvalidEnd(char)) ? 0 : this.emitNotTerminatedNamedEntity(); + } + current = decodeTree[this.treeIndex]; + valueLength = (current & BinTrieFlags.VALUE_LENGTH) >> 14; + // If the branch is a value, store it and continue + if (valueLength !== 0) { + // If the entity is terminated by a semicolon, we are done. + if (char === CharCodes.SEMI) { + return this.emitNamedEntityData(this.treeIndex, valueLength, this.consumed + this.excess); + } + // If we encounter a non-terminated (legacy) entity while parsing strictly, then ignore it. + if (this.decodeMode !== DecodingMode.Strict) { + this.result = this.treeIndex; + this.consumed += this.excess; + this.excess = 0; + } + } + } + return -1; + } + /** + * Emit a named entity that was not terminated with a semicolon. + * + * @returns The number of characters consumed. + */ emitNotTerminatedNamedEntity() { + var _a; + const {result: result, decodeTree: decodeTree} = this; + const valueLength = (decodeTree[result] & BinTrieFlags.VALUE_LENGTH) >> 14; + this.emitNamedEntityData(result, valueLength, this.consumed); + (_a = this.errors) === null || _a === void 0 ? void 0 : _a.missingSemicolonAfterCharacterReference(); + return this.consumed; + } + /** + * Emit a named entity. + * + * @param result The index of the entity in the decode tree. + * @param valueLength The number of bytes in the entity. + * @param consumed The number of characters consumed. + * + * @returns The number of characters consumed. + */ emitNamedEntityData(result, valueLength, consumed) { + const {decodeTree: decodeTree} = this; + this.emitCodePoint(valueLength === 1 ? decodeTree[result] & ~BinTrieFlags.VALUE_LENGTH : decodeTree[result + 1], consumed); + if (valueLength === 3) { + // For multi-byte values, we need to emit the second byte. + this.emitCodePoint(decodeTree[result + 2], consumed); + } + return consumed; + } + /** + * Signal to the parser that the end of the input was reached. + * + * Remaining data will be emitted and relevant errors will be produced. + * + * @returns The number of characters consumed. + */ end() { + var _a; + switch (this.state) { + case EntityDecoderState.NamedEntity: + { + // Emit a named entity if we have one. + return this.result !== 0 && (this.decodeMode !== DecodingMode.Attribute || this.result === this.treeIndex) ? this.emitNotTerminatedNamedEntity() : 0; + } + + // Otherwise, emit a numeric entity if we have one. + case EntityDecoderState.NumericDecimal: + { + return this.emitNumericEntity(0, 2); + } + + case EntityDecoderState.NumericHex: + { + return this.emitNumericEntity(0, 3); + } + + case EntityDecoderState.NumericStart: + { + (_a = this.errors) === null || _a === void 0 ? void 0 : _a.absenceOfDigitsInNumericCharacterReference(this.consumed); + return 0; + } + + case EntityDecoderState.EntityStart: + { + // Return 0 if we have no entity. + return 0; + } + } + } + } + /** + * Creates a function that decodes entities in a string. + * + * @param decodeTree The decode tree. + * @returns A function that decodes entities in a string. + */ function getDecoder(decodeTree) { + let ret = ""; + const decoder = new EntityDecoder(decodeTree, (str => ret += fromCodePoint$1(str))); + return function decodeWithTrie(str, decodeMode) { + let lastIndex = 0; + let offset = 0; + while ((offset = str.indexOf("&", offset)) >= 0) { + ret += str.slice(lastIndex, offset); + decoder.startEntity(decodeMode); + const len = decoder.write(str, + // Skip the "&" + offset + 1); + if (len < 0) { + lastIndex = offset + decoder.end(); + break; + } + lastIndex = offset + len; + // If `len` is 0, skip the current `&` and continue. + offset = len === 0 ? lastIndex + 1 : lastIndex; + } + const result = ret + str.slice(lastIndex); + // Make sure we don't keep a reference to the final string. + ret = ""; + return result; + }; + } + /** + * Determines the branch of the current node that is taken given the current + * character. This function is used to traverse the trie. + * + * @param decodeTree The trie. + * @param current The current node. + * @param nodeIdx The index right after the current node and its value. + * @param char The current character. + * @returns The index of the next node, or -1 if no branch is taken. + */ function determineBranch(decodeTree, current, nodeIdx, char) { + const branchCount = (current & BinTrieFlags.BRANCH_LENGTH) >> 7; + const jumpOffset = current & BinTrieFlags.JUMP_TABLE; + // Case 1: Single branch encoded in jump offset + if (branchCount === 0) { + return jumpOffset !== 0 && char === jumpOffset ? nodeIdx : -1; + } + // Case 2: Multiple branches encoded in jump table + if (jumpOffset) { + const value = char - jumpOffset; + return value < 0 || value >= branchCount ? -1 : decodeTree[nodeIdx + value] - 1; + } + // Case 3: Multiple branches encoded in dictionary + // Binary search for the character. + let lo = nodeIdx; + let hi = lo + branchCount - 1; + while (lo <= hi) { + const mid = lo + hi >>> 1; + const midVal = decodeTree[mid]; + if (midVal < char) { + lo = mid + 1; + } else if (midVal > char) { + hi = mid - 1; + } else { + return decodeTree[mid + branchCount]; + } + } + return -1; + } + const htmlDecoder = getDecoder(htmlDecodeTree); + getDecoder(xmlDecodeTree); + /** + * Decodes an HTML string. + * + * @param str The string to decode. + * @param mode The decoding mode. + * @returns The decoded string. + */ function decodeHTML(str, mode = DecodingMode.Legacy) { + return htmlDecoder(str, mode); + } + // Utilities + + function _class$1(obj) { + return Object.prototype.toString.call(obj); + } + function isString$1(obj) { + return _class$1(obj) === "[object String]"; + } + const _hasOwnProperty = Object.prototype.hasOwnProperty; + function has(object, key) { + return _hasOwnProperty.call(object, key); + } + // Merge objects + + function assign$1(obj /* from1, from2, from3, ... */) { + const sources = Array.prototype.slice.call(arguments, 1); + sources.forEach((function(source) { + if (!source) { + return; + } + if (typeof source !== "object") { + throw new TypeError(source + "must be object"); + } + Object.keys(source).forEach((function(key) { + obj[key] = source[key]; + })); + })); + return obj; + } + // Remove element from array and put another array at those position. + // Useful for some operations with tokens + function arrayReplaceAt(src, pos, newElements) { + return [].concat(src.slice(0, pos), newElements, src.slice(pos + 1)); + } + function isValidEntityCode(c) { + /* eslint no-bitwise:0 */ + // broken sequence + if (c >= 55296 && c <= 57343) { + return false; + } + // never used + if (c >= 64976 && c <= 65007) { + return false; + } + if ((c & 65535) === 65535 || (c & 65535) === 65534) { + return false; + } + // control codes + if (c >= 0 && c <= 8) { + return false; + } + if (c === 11) { + return false; + } + if (c >= 14 && c <= 31) { + return false; + } + if (c >= 127 && c <= 159) { + return false; + } + // out of range + if (c > 1114111) { + return false; + } + return true; + } + function fromCodePoint(c) { + /* eslint no-bitwise:0 */ + if (c > 65535) { + c -= 65536; + const surrogate1 = 55296 + (c >> 10); + const surrogate2 = 56320 + (c & 1023); + return String.fromCharCode(surrogate1, surrogate2); + } + return String.fromCharCode(c); + } + const UNESCAPE_MD_RE = /\\([!"#$%&'()*+,\-./:;<=>?@[\\\]^_`{|}~])/g; + const ENTITY_RE = /&([a-z#][a-z0-9]{1,31});/gi; + const UNESCAPE_ALL_RE = new RegExp(UNESCAPE_MD_RE.source + "|" + ENTITY_RE.source, "gi"); + const DIGITAL_ENTITY_TEST_RE = /^#((?:x[a-f0-9]{1,8}|[0-9]{1,8}))$/i; + function replaceEntityPattern(match, name) { + if (name.charCodeAt(0) === 35 /* # */ && DIGITAL_ENTITY_TEST_RE.test(name)) { + const code = name[1].toLowerCase() === "x" ? parseInt(name.slice(2), 16) : parseInt(name.slice(1), 10); + if (isValidEntityCode(code)) { + return fromCodePoint(code); + } + return match; + } + const decoded = decodeHTML(match); + if (decoded !== match) { + return decoded; + } + return match; + } + /* function replaceEntities(str) { + if (str.indexOf('&') < 0) { return str; } + + return str.replace(ENTITY_RE, replaceEntityPattern); + } */ function unescapeMd(str) { + if (str.indexOf("\\") < 0) { + return str; + } + return str.replace(UNESCAPE_MD_RE, "$1"); + } + function unescapeAll(str) { + if (str.indexOf("\\") < 0 && str.indexOf("&") < 0) { + return str; + } + return str.replace(UNESCAPE_ALL_RE, (function(match, escaped, entity) { + if (escaped) { + return escaped; + } + return replaceEntityPattern(match, entity); + })); + } + const HTML_ESCAPE_TEST_RE = /[&<>"]/; + const HTML_ESCAPE_REPLACE_RE = /[&<>"]/g; + const HTML_REPLACEMENTS = { + "&": "&", + "<": "<", + ">": ">", + '"': """ + }; + function replaceUnsafeChar(ch) { + return HTML_REPLACEMENTS[ch]; + } + function escapeHtml(str) { + if (HTML_ESCAPE_TEST_RE.test(str)) { + return str.replace(HTML_ESCAPE_REPLACE_RE, replaceUnsafeChar); + } + return str; + } + const REGEXP_ESCAPE_RE = /[.?*+^$[\]\\(){}|-]/g; + function escapeRE$1(str) { + return str.replace(REGEXP_ESCAPE_RE, "\\$&"); + } + function isSpace(code) { + switch (code) { + case 9: + case 32: + return true; + } + return false; + } + // Zs (unicode class) || [\t\f\v\r\n] + function isWhiteSpace(code) { + if (code >= 8192 && code <= 8202) { + return true; + } + switch (code) { + case 9: + // \t + case 10: + // \n + case 11: + // \v + case 12: + // \f + case 13: + // \r + case 32: + case 160: + case 5760: + case 8239: + case 8287: + case 12288: + return true; + } + return false; + } + /* eslint-disable max-len */ + // Currently without astral characters support. + function isPunctChar(ch) { + return P.test(ch) || regex.test(ch); + } + // Markdown ASCII punctuation characters. + + // !, ", #, $, %, &, ', (, ), *, +, ,, -, ., /, :, ;, <, =, >, ?, @, [, \, ], ^, _, `, {, |, }, or ~ + // http://spec.commonmark.org/0.15/#ascii-punctuation-character + + // Don't confuse with unicode punctuation !!! It lacks some chars in ascii range. + + function isMdAsciiPunct(ch) { + switch (ch) { + case 33 /* ! */ : + case 34 /* " */ : + case 35 /* # */ : + case 36 /* $ */ : + case 37 /* % */ : + case 38 /* & */ : + case 39 /* ' */ : + case 40 /* ( */ : + case 41 /* ) */ : + case 42 /* * */ : + case 43 /* + */ : + case 44 /* , */ : + case 45 /* - */ : + case 46 /* . */ : + case 47 /* / */ : + case 58 /* : */ : + case 59 /* ; */ : + case 60 /* < */ : + case 61 /* = */ : + case 62 /* > */ : + case 63 /* ? */ : + case 64 /* @ */ : + case 91 /* [ */ : + case 92 /* \ */ : + case 93 /* ] */ : + case 94 /* ^ */ : + case 95 /* _ */ : + case 96 /* ` */ : + case 123 /* { */ : + case 124 /* | */ : + case 125 /* } */ : + case 126 /* ~ */ : + return true; + + default: + return false; + } + } + // Hepler to unify [reference labels]. + + function normalizeReference(str) { + // Trim and collapse whitespace + str = str.trim().replace(/\s+/g, " "); + // In node v10 'ẞ'.toLowerCase() === 'Ṿ', which is presumed to be a bug + // fixed in v12 (couldn't find any details). + + // So treat this one as a special case + // (remove this when node v10 is no longer supported). + + if ("\u1e9e".toLowerCase() === "\u1e7e") { + str = str.replace(/\u1e9e/g, "\xdf"); + } + // .toLowerCase().toUpperCase() should get rid of all differences + // between letter variants. + + // Simple .toLowerCase() doesn't normalize 125 code points correctly, + // and .toUpperCase doesn't normalize 6 of them (list of exceptions: + // İ, ϴ, ẞ, Ω, K, Å - those are already uppercased, but have differently + // uppercased versions). + + // Here's an example showing how it happens. Lets take greek letter omega: + // uppercase U+0398 (Θ), U+03f4 (ϴ) and lowercase U+03b8 (θ), U+03d1 (ϑ) + + // Unicode entries: + // 0398;GREEK CAPITAL LETTER THETA;Lu;0;L;;;;;N;;;;03B8; + // 03B8;GREEK SMALL LETTER THETA;Ll;0;L;;;;;N;;;0398;;0398 + // 03D1;GREEK THETA SYMBOL;Ll;0;L; 03B8;;;;N;GREEK SMALL LETTER SCRIPT THETA;;0398;;0398 + // 03F4;GREEK CAPITAL THETA SYMBOL;Lu;0;L; 0398;;;;N;;;;03B8; + + // Case-insensitive comparison should treat all of them as equivalent. + + // But .toLowerCase() doesn't change ϑ (it's already lowercase), + // and .toUpperCase() doesn't change ϴ (already uppercase). + + // Applying first lower then upper case normalizes any character: + // '\u0398\u03f4\u03b8\u03d1'.toLowerCase().toUpperCase() === '\u0398\u0398\u0398\u0398' + + // Note: this is equivalent to unicode case folding; unicode normalization + // is a different step that is not required here. + + // Final result should be uppercased, because it's later stored in an object + // (this avoid a conflict with Object.prototype members, + // most notably, `__proto__`) + + return str.toLowerCase().toUpperCase(); + } + // Re-export libraries commonly used in both markdown-it and its plugins, + // so plugins won't have to depend on them explicitly, which reduces their + // bundled size (e.g. a browser build). + + const lib = { + mdurl: mdurl, + ucmicro: ucmicro + }; + var utils = Object.freeze({ + __proto__: null, + arrayReplaceAt: arrayReplaceAt, + assign: assign$1, + escapeHtml: escapeHtml, + escapeRE: escapeRE$1, + fromCodePoint: fromCodePoint, + has: has, + isMdAsciiPunct: isMdAsciiPunct, + isPunctChar: isPunctChar, + isSpace: isSpace, + isString: isString$1, + isValidEntityCode: isValidEntityCode, + isWhiteSpace: isWhiteSpace, + lib: lib, + normalizeReference: normalizeReference, + unescapeAll: unescapeAll, + unescapeMd: unescapeMd + }); + // Parse link label + + // this function assumes that first character ("[") already matches; + // returns the end of the label + + function parseLinkLabel(state, start, disableNested) { + let level, found, marker, prevPos; + const max = state.posMax; + const oldPos = state.pos; + state.pos = start + 1; + level = 1; + while (state.pos < max) { + marker = state.src.charCodeAt(state.pos); + if (marker === 93 /* ] */) { + level--; + if (level === 0) { + found = true; + break; + } + } + prevPos = state.pos; + state.md.inline.skipToken(state); + if (marker === 91 /* [ */) { + if (prevPos === state.pos - 1) { + // increase level if we find text `[`, which is not a part of any token + level++; + } else if (disableNested) { + state.pos = oldPos; + return -1; + } + } + } + let labelEnd = -1; + if (found) { + labelEnd = state.pos; + } + // restore old state + state.pos = oldPos; + return labelEnd; + } + // Parse link destination + + function parseLinkDestination(str, start, max) { + let code; + let pos = start; + const result = { + ok: false, + pos: 0, + str: "" + }; + if (str.charCodeAt(pos) === 60 /* < */) { + pos++; + while (pos < max) { + code = str.charCodeAt(pos); + if (code === 10 /* \n */) { + return result; + } + if (code === 60 /* < */) { + return result; + } + if (code === 62 /* > */) { + result.pos = pos + 1; + result.str = unescapeAll(str.slice(start + 1, pos)); + result.ok = true; + return result; + } + if (code === 92 /* \ */ && pos + 1 < max) { + pos += 2; + continue; + } + pos++; + } + // no closing '>' + return result; + } + // this should be ... } else { ... branch + let level = 0; + while (pos < max) { + code = str.charCodeAt(pos); + if (code === 32) { + break; + } + // ascii control characters + if (code < 32 || code === 127) { + break; + } + if (code === 92 /* \ */ && pos + 1 < max) { + if (str.charCodeAt(pos + 1) === 32) { + break; + } + pos += 2; + continue; + } + if (code === 40 /* ( */) { + level++; + if (level > 32) { + return result; + } + } + if (code === 41 /* ) */) { + if (level === 0) { + break; + } + level--; + } + pos++; + } + if (start === pos) { + return result; + } + if (level !== 0) { + return result; + } + result.str = unescapeAll(str.slice(start, pos)); + result.pos = pos; + result.ok = true; + return result; + } + // Parse link title + + // Parse link title within `str` in [start, max] range, + // or continue previous parsing if `prev_state` is defined (equal to result of last execution). + + function parseLinkTitle(str, start, max, prev_state) { + let code; + let pos = start; + const state = { + // if `true`, this is a valid link title + ok: false, + // if `true`, this link can be continued on the next line + can_continue: false, + // if `ok`, it's the position of the first character after the closing marker + pos: 0, + // if `ok`, it's the unescaped title + str: "", + // expected closing marker character code + marker: 0 + }; + if (prev_state) { + // this is a continuation of a previous parseLinkTitle call on the next line, + // used in reference links only + state.str = prev_state.str; + state.marker = prev_state.marker; + } else { + if (pos >= max) { + return state; + } + let marker = str.charCodeAt(pos); + if (marker !== 34 /* " */ && marker !== 39 /* ' */ && marker !== 40 /* ( */) { + return state; + } + start++; + pos++; + // if opening marker is "(", switch it to closing marker ")" + if (marker === 40) { + marker = 41; + } + state.marker = marker; + } + while (pos < max) { + code = str.charCodeAt(pos); + if (code === state.marker) { + state.pos = pos + 1; + state.str += unescapeAll(str.slice(start, pos)); + state.ok = true; + return state; + } else if (code === 40 /* ( */ && state.marker === 41 /* ) */) { + return state; + } else if (code === 92 /* \ */ && pos + 1 < max) { + pos++; + } + pos++; + } + // no closing marker found, but this link title may continue on the next line (for references) + state.can_continue = true; + state.str += unescapeAll(str.slice(start, pos)); + return state; + } + // Just a shortcut for bulk export + var helpers = Object.freeze({ + __proto__: null, + parseLinkDestination: parseLinkDestination, + parseLinkLabel: parseLinkLabel, + parseLinkTitle: parseLinkTitle + }); + /** + * class Renderer + * + * Generates HTML from parsed token stream. Each instance has independent + * copy of rules. Those can be rewritten with ease. Also, you can add new + * rules if you create plugin and adds new token types. + **/ const default_rules = {}; + default_rules.code_inline = function(tokens, idx, options, env, slf) { + const token = tokens[idx]; + return "" + escapeHtml(token.content) + ""; + }; + default_rules.code_block = function(tokens, idx, options, env, slf) { + const token = tokens[idx]; + return "" + escapeHtml(tokens[idx].content) + "\n"; + }; + default_rules.fence = function(tokens, idx, options, env, slf) { + const token = tokens[idx]; + const info = token.info ? unescapeAll(token.info).trim() : ""; + let langName = ""; + let langAttrs = ""; + if (info) { + const arr = info.split(/(\s+)/g); + langName = arr[0]; + langAttrs = arr.slice(2).join(""); + } + let highlighted; + if (options.highlight) { + highlighted = options.highlight(token.content, langName, langAttrs) || escapeHtml(token.content); + } else { + highlighted = escapeHtml(token.content); + } + if (highlighted.indexOf("${highlighted}\n`; + } + return `

    ${highlighted}
    \n`; + }; + default_rules.image = function(tokens, idx, options, env, slf) { + const token = tokens[idx]; + // "alt" attr MUST be set, even if empty. Because it's mandatory and + // should be placed on proper position for tests. + + // Replace content with actual value + token.attrs[token.attrIndex("alt")][1] = slf.renderInlineAsText(token.children, options, env); + return slf.renderToken(tokens, idx, options); + }; + default_rules.hardbreak = function(tokens, idx, options /*, env */) { + return options.xhtmlOut ? "
    \n" : "
    \n"; + }; + default_rules.softbreak = function(tokens, idx, options /*, env */) { + return options.breaks ? options.xhtmlOut ? "
    \n" : "
    \n" : "\n"; + }; + default_rules.text = function(tokens, idx /*, options, env */) { + return escapeHtml(tokens[idx].content); + }; + default_rules.html_block = function(tokens, idx /*, options, env */) { + return tokens[idx].content; + }; + default_rules.html_inline = function(tokens, idx /*, options, env */) { + return tokens[idx].content; + }; + /** + * new Renderer() + * + * Creates new [[Renderer]] instance and fill [[Renderer#rules]] with defaults. + **/ function Renderer() { + /** + * Renderer#rules -> Object + * + * Contains render rules for tokens. Can be updated and extended. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.renderer.rules.strong_open = function () { return ''; }; + * md.renderer.rules.strong_close = function () { return ''; }; + * + * var result = md.renderInline(...); + * ``` + * + * Each rule is called as independent static function with fixed signature: + * + * ```javascript + * function my_token_render(tokens, idx, options, env, renderer) { + * // ... + * return renderedHTML; + * } + * ``` + * + * See [source code](https://github.com/markdown-it/markdown-it/blob/master/lib/renderer.mjs) + * for more details and examples. + **/ + this.rules = assign$1({}, default_rules); + } + /** + * Renderer.renderAttrs(token) -> String + * + * Render token attributes to string. + **/ Renderer.prototype.renderAttrs = function renderAttrs(token) { + let i, l, result; + if (!token.attrs) { + return ""; + } + result = ""; + for (i = 0, l = token.attrs.length; i < l; i++) { + result += " " + escapeHtml(token.attrs[i][0]) + '="' + escapeHtml(token.attrs[i][1]) + '"'; + } + return result; + }; + /** + * Renderer.renderToken(tokens, idx, options) -> String + * - tokens (Array): list of tokens + * - idx (Numbed): token index to render + * - options (Object): params of parser instance + * + * Default token renderer. Can be overriden by custom function + * in [[Renderer#rules]]. + **/ Renderer.prototype.renderToken = function renderToken(tokens, idx, options) { + const token = tokens[idx]; + let result = ""; + // Tight list paragraphs + if (token.hidden) { + return ""; + } + // Insert a newline between hidden paragraph and subsequent opening + // block-level tag. + + // For example, here we should insert a newline before blockquote: + // - a + // > + + if (token.block && token.nesting !== -1 && idx && tokens[idx - 1].hidden) { + result += "\n"; + } + // Add token name, e.g. ``. + needLf = false; + } + } + } + } + result += needLf ? ">\n" : ">"; + return result; + }; + /** + * Renderer.renderInline(tokens, options, env) -> String + * - tokens (Array): list on block tokens to render + * - options (Object): params of parser instance + * - env (Object): additional data from parsed input (references, for example) + * + * The same as [[Renderer.render]], but for single token of `inline` type. + **/ Renderer.prototype.renderInline = function(tokens, options, env) { + let result = ""; + const rules = this.rules; + for (let i = 0, len = tokens.length; i < len; i++) { + const type = tokens[i].type; + if (typeof rules[type] !== "undefined") { + result += rules[type](tokens, i, options, env, this); + } else { + result += this.renderToken(tokens, i, options); + } + } + return result; + }; + /** internal + * Renderer.renderInlineAsText(tokens, options, env) -> String + * - tokens (Array): list on block tokens to render + * - options (Object): params of parser instance + * - env (Object): additional data from parsed input (references, for example) + * + * Special kludge for image `alt` attributes to conform CommonMark spec. + * Don't try to use it! Spec requires to show `alt` content with stripped markup, + * instead of simple escaping. + **/ Renderer.prototype.renderInlineAsText = function(tokens, options, env) { + let result = ""; + for (let i = 0, len = tokens.length; i < len; i++) { + switch (tokens[i].type) { + case "text": + result += tokens[i].content; + break; + + case "image": + result += this.renderInlineAsText(tokens[i].children, options, env); + break; + + case "html_inline": + case "html_block": + result += tokens[i].content; + break; + + case "softbreak": + case "hardbreak": + result += "\n"; + break; + // all other tokens are skipped + } + } + return result; + }; + /** + * Renderer.render(tokens, options, env) -> String + * - tokens (Array): list on block tokens to render + * - options (Object): params of parser instance + * - env (Object): additional data from parsed input (references, for example) + * + * Takes token stream and generates HTML. Probably, you will never need to call + * this method directly. + **/ Renderer.prototype.render = function(tokens, options, env) { + let result = ""; + const rules = this.rules; + for (let i = 0, len = tokens.length; i < len; i++) { + const type = tokens[i].type; + if (type === "inline") { + result += this.renderInline(tokens[i].children, options, env); + } else if (typeof rules[type] !== "undefined") { + result += rules[type](tokens, i, options, env, this); + } else { + result += this.renderToken(tokens, i, options, env); + } + } + return result; + }; + /** + * class Ruler + * + * Helper class, used by [[MarkdownIt#core]], [[MarkdownIt#block]] and + * [[MarkdownIt#inline]] to manage sequences of functions (rules): + * + * - keep rules in defined order + * - assign the name to each rule + * - enable/disable rules + * - add/replace rules + * - allow assign rules to additional named chains (in the same) + * - cacheing lists of active rules + * + * You will not need use this class directly until write plugins. For simple + * rules control use [[MarkdownIt.disable]], [[MarkdownIt.enable]] and + * [[MarkdownIt.use]]. + **/ + /** + * new Ruler() + **/ function Ruler() { + // List of added rules. Each element is: + // { + // name: XXX, + // enabled: Boolean, + // fn: Function(), + // alt: [ name2, name3 ] + // } + this.__rules__ = []; + // Cached rule chains. + + // First level - chain name, '' for default. + // Second level - diginal anchor for fast filtering by charcodes. + + this.__cache__ = null; + } + // Helper methods, should not be used directly + // Find rule index by name + + Ruler.prototype.__find__ = function(name) { + for (let i = 0; i < this.__rules__.length; i++) { + if (this.__rules__[i].name === name) { + return i; + } + } + return -1; + }; + // Build rules lookup cache + + Ruler.prototype.__compile__ = function() { + const self = this; + const chains = [ "" ]; + // collect unique names + self.__rules__.forEach((function(rule) { + if (!rule.enabled) { + return; + } + rule.alt.forEach((function(altName) { + if (chains.indexOf(altName) < 0) { + chains.push(altName); + } + })); + })); + self.__cache__ = {}; + chains.forEach((function(chain) { + self.__cache__[chain] = []; + self.__rules__.forEach((function(rule) { + if (!rule.enabled) { + return; + } + if (chain && rule.alt.indexOf(chain) < 0) { + return; + } + self.__cache__[chain].push(rule.fn); + })); + })); + }; + /** + * Ruler.at(name, fn [, options]) + * - name (String): rule name to replace. + * - fn (Function): new rule function. + * - options (Object): new rule options (not mandatory). + * + * Replace rule by name with new function & options. Throws error if name not + * found. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * Replace existing typographer replacement rule with new one: + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.core.ruler.at('replacements', function replace(state) { + * //... + * }); + * ``` + **/ Ruler.prototype.at = function(name, fn, options) { + const index = this.__find__(name); + const opt = options || {}; + if (index === -1) { + throw new Error("Parser rule not found: " + name); + } + this.__rules__[index].fn = fn; + this.__rules__[index].alt = opt.alt || []; + this.__cache__ = null; + }; + /** + * Ruler.before(beforeName, ruleName, fn [, options]) + * - beforeName (String): new rule will be added before this one. + * - ruleName (String): name of added rule. + * - fn (Function): rule function. + * - options (Object): rule options (not mandatory). + * + * Add new rule to chain before one with given name. See also + * [[Ruler.after]], [[Ruler.push]]. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.block.ruler.before('paragraph', 'my_rule', function replace(state) { + * //... + * }); + * ``` + **/ Ruler.prototype.before = function(beforeName, ruleName, fn, options) { + const index = this.__find__(beforeName); + const opt = options || {}; + if (index === -1) { + throw new Error("Parser rule not found: " + beforeName); + } + this.__rules__.splice(index, 0, { + name: ruleName, + enabled: true, + fn: fn, + alt: opt.alt || [] + }); + this.__cache__ = null; + }; + /** + * Ruler.after(afterName, ruleName, fn [, options]) + * - afterName (String): new rule will be added after this one. + * - ruleName (String): name of added rule. + * - fn (Function): rule function. + * - options (Object): rule options (not mandatory). + * + * Add new rule to chain after one with given name. See also + * [[Ruler.before]], [[Ruler.push]]. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.inline.ruler.after('text', 'my_rule', function replace(state) { + * //... + * }); + * ``` + **/ Ruler.prototype.after = function(afterName, ruleName, fn, options) { + const index = this.__find__(afterName); + const opt = options || {}; + if (index === -1) { + throw new Error("Parser rule not found: " + afterName); + } + this.__rules__.splice(index + 1, 0, { + name: ruleName, + enabled: true, + fn: fn, + alt: opt.alt || [] + }); + this.__cache__ = null; + }; + /** + * Ruler.push(ruleName, fn [, options]) + * - ruleName (String): name of added rule. + * - fn (Function): rule function. + * - options (Object): rule options (not mandatory). + * + * Push new rule to the end of chain. See also + * [[Ruler.before]], [[Ruler.after]]. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.core.ruler.push('my_rule', function replace(state) { + * //... + * }); + * ``` + **/ Ruler.prototype.push = function(ruleName, fn, options) { + const opt = options || {}; + this.__rules__.push({ + name: ruleName, + enabled: true, + fn: fn, + alt: opt.alt || [] + }); + this.__cache__ = null; + }; + /** + * Ruler.enable(list [, ignoreInvalid]) -> Array + * - list (String|Array): list of rule names to enable. + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Enable rules with given names. If any rule name not found - throw Error. + * Errors can be disabled by second param. + * + * Returns list of found rule names (if no exception happened). + * + * See also [[Ruler.disable]], [[Ruler.enableOnly]]. + **/ Ruler.prototype.enable = function(list, ignoreInvalid) { + if (!Array.isArray(list)) { + list = [ list ]; + } + const result = []; + // Search by name and enable + list.forEach((function(name) { + const idx = this.__find__(name); + if (idx < 0) { + if (ignoreInvalid) { + return; + } + throw new Error("Rules manager: invalid rule name " + name); + } + this.__rules__[idx].enabled = true; + result.push(name); + }), this); + this.__cache__ = null; + return result; + }; + /** + * Ruler.enableOnly(list [, ignoreInvalid]) + * - list (String|Array): list of rule names to enable (whitelist). + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Enable rules with given names, and disable everything else. If any rule name + * not found - throw Error. Errors can be disabled by second param. + * + * See also [[Ruler.disable]], [[Ruler.enable]]. + **/ Ruler.prototype.enableOnly = function(list, ignoreInvalid) { + if (!Array.isArray(list)) { + list = [ list ]; + } + this.__rules__.forEach((function(rule) { + rule.enabled = false; + })); + this.enable(list, ignoreInvalid); + }; + /** + * Ruler.disable(list [, ignoreInvalid]) -> Array + * - list (String|Array): list of rule names to disable. + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Disable rules with given names. If any rule name not found - throw Error. + * Errors can be disabled by second param. + * + * Returns list of found rule names (if no exception happened). + * + * See also [[Ruler.enable]], [[Ruler.enableOnly]]. + **/ Ruler.prototype.disable = function(list, ignoreInvalid) { + if (!Array.isArray(list)) { + list = [ list ]; + } + const result = []; + // Search by name and disable + list.forEach((function(name) { + const idx = this.__find__(name); + if (idx < 0) { + if (ignoreInvalid) { + return; + } + throw new Error("Rules manager: invalid rule name " + name); + } + this.__rules__[idx].enabled = false; + result.push(name); + }), this); + this.__cache__ = null; + return result; + }; + /** + * Ruler.getRules(chainName) -> Array + * + * Return array of active functions (rules) for given chain name. It analyzes + * rules configuration, compiles caches if not exists and returns result. + * + * Default chain name is `''` (empty string). It can't be skipped. That's + * done intentionally, to keep signature monomorphic for high speed. + **/ Ruler.prototype.getRules = function(chainName) { + if (this.__cache__ === null) { + this.__compile__(); + } + // Chain can be empty, if rules disabled. But we still have to return Array. + return this.__cache__[chainName] || []; + }; + // Token class + /** + * class Token + **/ + /** + * new Token(type, tag, nesting) + * + * Create new token and fill passed properties. + **/ function Token(type, tag, nesting) { + /** + * Token#type -> String + * + * Type of the token (string, e.g. "paragraph_open") + **/ + this.type = type; + /** + * Token#tag -> String + * + * html tag name, e.g. "p" + **/ this.tag = tag; + /** + * Token#attrs -> Array + * + * Html attributes. Format: `[ [ name1, value1 ], [ name2, value2 ] ]` + **/ this.attrs = null; + /** + * Token#map -> Array + * + * Source map info. Format: `[ line_begin, line_end ]` + **/ this.map = null; + /** + * Token#nesting -> Number + * + * Level change (number in {-1, 0, 1} set), where: + * + * - `1` means the tag is opening + * - `0` means the tag is self-closing + * - `-1` means the tag is closing + **/ this.nesting = nesting; + /** + * Token#level -> Number + * + * nesting level, the same as `state.level` + **/ this.level = 0; + /** + * Token#children -> Array + * + * An array of child nodes (inline and img tokens) + **/ this.children = null; + /** + * Token#content -> String + * + * In a case of self-closing tag (code, html, fence, etc.), + * it has contents of this tag. + **/ this.content = ""; + /** + * Token#markup -> String + * + * '*' or '_' for emphasis, fence string for fence, etc. + **/ this.markup = ""; + /** + * Token#info -> String + * + * Additional information: + * + * - Info string for "fence" tokens + * - The value "auto" for autolink "link_open" and "link_close" tokens + * - The string value of the item marker for ordered-list "list_item_open" tokens + **/ this.info = ""; + /** + * Token#meta -> Object + * + * A place for plugins to store an arbitrary data + **/ this.meta = null; + /** + * Token#block -> Boolean + * + * True for block-level tokens, false for inline tokens. + * Used in renderer to calculate line breaks + **/ this.block = false; + /** + * Token#hidden -> Boolean + * + * If it's true, ignore this element when rendering. Used for tight lists + * to hide paragraphs. + **/ this.hidden = false; + } + /** + * Token.attrIndex(name) -> Number + * + * Search attribute index by name. + **/ Token.prototype.attrIndex = function attrIndex(name) { + if (!this.attrs) { + return -1; + } + const attrs = this.attrs; + for (let i = 0, len = attrs.length; i < len; i++) { + if (attrs[i][0] === name) { + return i; + } + } + return -1; + }; + /** + * Token.attrPush(attrData) + * + * Add `[ name, value ]` attribute to list. Init attrs if necessary + **/ Token.prototype.attrPush = function attrPush(attrData) { + if (this.attrs) { + this.attrs.push(attrData); + } else { + this.attrs = [ attrData ]; + } + }; + /** + * Token.attrSet(name, value) + * + * Set `name` attribute to `value`. Override old value if exists. + **/ Token.prototype.attrSet = function attrSet(name, value) { + const idx = this.attrIndex(name); + const attrData = [ name, value ]; + if (idx < 0) { + this.attrPush(attrData); + } else { + this.attrs[idx] = attrData; + } + }; + /** + * Token.attrGet(name) + * + * Get the value of attribute `name`, or null if it does not exist. + **/ Token.prototype.attrGet = function attrGet(name) { + const idx = this.attrIndex(name); + let value = null; + if (idx >= 0) { + value = this.attrs[idx][1]; + } + return value; + }; + /** + * Token.attrJoin(name, value) + * + * Join value to existing attribute via space. Or create new attribute if not + * exists. Useful to operate with token classes. + **/ Token.prototype.attrJoin = function attrJoin(name, value) { + const idx = this.attrIndex(name); + if (idx < 0) { + this.attrPush([ name, value ]); + } else { + this.attrs[idx][1] = this.attrs[idx][1] + " " + value; + } + }; + // Core state object + + function StateCore(src, md, env) { + this.src = src; + this.env = env; + this.tokens = []; + this.inlineMode = false; + this.md = md; + // link to parser instance + } + // re-export Token class to use in core rules + StateCore.prototype.Token = Token; + // Normalize input string + // https://spec.commonmark.org/0.29/#line-ending + const NEWLINES_RE = /\r\n?|\n/g; + const NULL_RE = /\0/g; + function normalize(state) { + let str; + // Normalize newlines + str = state.src.replace(NEWLINES_RE, "\n"); + // Replace NULL characters + str = str.replace(NULL_RE, "\ufffd"); + state.src = str; + } + function block(state) { + let token; + if (state.inlineMode) { + token = new state.Token("inline", "", 0); + token.content = state.src; + token.map = [ 0, 1 ]; + token.children = []; + state.tokens.push(token); + } else { + state.md.block.parse(state.src, state.md, state.env, state.tokens); + } + } + function inline(state) { + const tokens = state.tokens; + // Parse inlines + for (let i = 0, l = tokens.length; i < l; i++) { + const tok = tokens[i]; + if (tok.type === "inline") { + state.md.inline.parse(tok.content, state.md, state.env, tok.children); + } + } + } + // Replace link-like texts with link nodes. + + // Currently restricted by `md.validateLink()` to http/https/ftp + + function isLinkOpen$1(str) { + return /^\s]/i.test(str); + } + function isLinkClose$1(str) { + return /^<\/a\s*>/i.test(str); + } + function linkify$1(state) { + const blockTokens = state.tokens; + if (!state.md.options.linkify) { + return; + } + for (let j = 0, l = blockTokens.length; j < l; j++) { + if (blockTokens[j].type !== "inline" || !state.md.linkify.pretest(blockTokens[j].content)) { + continue; + } + let tokens = blockTokens[j].children; + let htmlLinkLevel = 0; + // We scan from the end, to keep position when new tags added. + // Use reversed logic in links start/end match + for (let i = tokens.length - 1; i >= 0; i--) { + const currentToken = tokens[i]; + // Skip content of markdown links + if (currentToken.type === "link_close") { + i--; + while (tokens[i].level !== currentToken.level && tokens[i].type !== "link_open") { + i--; + } + continue; + } + // Skip content of html tag links + if (currentToken.type === "html_inline") { + if (isLinkOpen$1(currentToken.content) && htmlLinkLevel > 0) { + htmlLinkLevel--; + } + if (isLinkClose$1(currentToken.content)) { + htmlLinkLevel++; + } + } + if (htmlLinkLevel > 0) { + continue; + } + if (currentToken.type === "text" && state.md.linkify.test(currentToken.content)) { + const text = currentToken.content; + let links = state.md.linkify.match(text); + // Now split string to nodes + const nodes = []; + let level = currentToken.level; + let lastPos = 0; + // forbid escape sequence at the start of the string, + // this avoids http\://example.com/ from being linkified as + // http:
    //example.com/ + if (links.length > 0 && links[0].index === 0 && i > 0 && tokens[i - 1].type === "text_special") { + links = links.slice(1); + } + for (let ln = 0; ln < links.length; ln++) { + const url = links[ln].url; + const fullUrl = state.md.normalizeLink(url); + if (!state.md.validateLink(fullUrl)) { + continue; + } + let urlText = links[ln].text; + // Linkifier might send raw hostnames like "example.com", where url + // starts with domain name. So we prepend http:// in those cases, + // and remove it afterwards. + + if (!links[ln].schema) { + urlText = state.md.normalizeLinkText("http://" + urlText).replace(/^http:\/\//, ""); + } else if (links[ln].schema === "mailto:" && !/^mailto:/i.test(urlText)) { + urlText = state.md.normalizeLinkText("mailto:" + urlText).replace(/^mailto:/, ""); + } else { + urlText = state.md.normalizeLinkText(urlText); + } + const pos = links[ln].index; + if (pos > lastPos) { + const token = new state.Token("text", "", 0); + token.content = text.slice(lastPos, pos); + token.level = level; + nodes.push(token); + } + const token_o = new state.Token("link_open", "a", 1); + token_o.attrs = [ [ "href", fullUrl ] ]; + token_o.level = level++; + token_o.markup = "linkify"; + token_o.info = "auto"; + nodes.push(token_o); + const token_t = new state.Token("text", "", 0); + token_t.content = urlText; + token_t.level = level; + nodes.push(token_t); + const token_c = new state.Token("link_close", "a", -1); + token_c.level = --level; + token_c.markup = "linkify"; + token_c.info = "auto"; + nodes.push(token_c); + lastPos = links[ln].lastIndex; + } + if (lastPos < text.length) { + const token = new state.Token("text", "", 0); + token.content = text.slice(lastPos); + token.level = level; + nodes.push(token); + } + // replace current node + blockTokens[j].children = tokens = arrayReplaceAt(tokens, i, nodes); + } + } + } + } + // Simple typographic replacements + + // (c) (C) → © + // (tm) (TM) → ™ + // (r) (R) → ® + // +- → ± + // ... → … (also ?.... → ?.., !.... → !..) + // ???????? → ???, !!!!! → !!!, `,,` → `,` + // -- → –, --- → — + + // TODO: + // - fractionals 1/2, 1/4, 3/4 -> ½, ¼, ¾ + // - multiplications 2 x 4 -> 2 × 4 + const RARE_RE = /\+-|\.\.|\?\?\?\?|!!!!|,,|--/; + // Workaround for phantomjs - need regex without /g flag, + // or root check will fail every second time + const SCOPED_ABBR_TEST_RE = /\((c|tm|r)\)/i; + const SCOPED_ABBR_RE = /\((c|tm|r)\)/gi; + const SCOPED_ABBR = { + c: "\xa9", + r: "\xae", + tm: "\u2122" + }; + function replaceFn(match, name) { + return SCOPED_ABBR[name.toLowerCase()]; + } + function replace_scoped(inlineTokens) { + let inside_autolink = 0; + for (let i = inlineTokens.length - 1; i >= 0; i--) { + const token = inlineTokens[i]; + if (token.type === "text" && !inside_autolink) { + token.content = token.content.replace(SCOPED_ABBR_RE, replaceFn); + } + if (token.type === "link_open" && token.info === "auto") { + inside_autolink--; + } + if (token.type === "link_close" && token.info === "auto") { + inside_autolink++; + } + } + } + function replace_rare(inlineTokens) { + let inside_autolink = 0; + for (let i = inlineTokens.length - 1; i >= 0; i--) { + const token = inlineTokens[i]; + if (token.type === "text" && !inside_autolink) { + if (RARE_RE.test(token.content)) { + token.content = token.content.replace(/\+-/g, "\xb1").replace(/\.{2,}/g, "\u2026").replace(/([?!])\u2026/g, "$1..").replace(/([?!]){4,}/g, "$1$1$1").replace(/,{2,}/g, ",").replace(/(^|[^-])---(?=[^-]|$)/gm, "$1\u2014").replace(/(^|\s)--(?=\s|$)/gm, "$1\u2013").replace(/(^|[^-\s])--(?=[^-\s]|$)/gm, "$1\u2013"); + } + } + if (token.type === "link_open" && token.info === "auto") { + inside_autolink--; + } + if (token.type === "link_close" && token.info === "auto") { + inside_autolink++; + } + } + } + function replace(state) { + let blkIdx; + if (!state.md.options.typographer) { + return; + } + for (blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) { + if (state.tokens[blkIdx].type !== "inline") { + continue; + } + if (SCOPED_ABBR_TEST_RE.test(state.tokens[blkIdx].content)) { + replace_scoped(state.tokens[blkIdx].children); + } + if (RARE_RE.test(state.tokens[blkIdx].content)) { + replace_rare(state.tokens[blkIdx].children); + } + } + } + // Convert straight quotation marks to typographic ones + + const QUOTE_TEST_RE = /['"]/; + const QUOTE_RE = /['"]/g; + const APOSTROPHE = "\u2019"; + /* ’ */ function replaceAt(str, index, ch) { + return str.slice(0, index) + ch + str.slice(index + 1); + } + function process_inlines(tokens, state) { + let j; + const stack = []; + for (let i = 0; i < tokens.length; i++) { + const token = tokens[i]; + const thisLevel = tokens[i].level; + for (j = stack.length - 1; j >= 0; j--) { + if (stack[j].level <= thisLevel) { + break; + } + } + stack.length = j + 1; + if (token.type !== "text") { + continue; + } + let text = token.content; + let pos = 0; + let max = text.length; + /* eslint no-labels:0,block-scoped-var:0 */ OUTER: while (pos < max) { + QUOTE_RE.lastIndex = pos; + const t = QUOTE_RE.exec(text); + if (!t) { + break; + } + let canOpen = true; + let canClose = true; + pos = t.index + 1; + const isSingle = t[0] === "'"; + // Find previous character, + // default to space if it's the beginning of the line + + let lastChar = 32; + if (t.index - 1 >= 0) { + lastChar = text.charCodeAt(t.index - 1); + } else { + for (j = i - 1; j >= 0; j--) { + if (tokens[j].type === "softbreak" || tokens[j].type === "hardbreak") break; + // lastChar defaults to 0x20 + if (!tokens[j].content) continue; + // should skip all tokens except 'text', 'html_inline' or 'code_inline' + lastChar = tokens[j].content.charCodeAt(tokens[j].content.length - 1); + break; + } + } + // Find next character, + // default to space if it's the end of the line + + let nextChar = 32; + if (pos < max) { + nextChar = text.charCodeAt(pos); + } else { + for (j = i + 1; j < tokens.length; j++) { + if (tokens[j].type === "softbreak" || tokens[j].type === "hardbreak") break; + // nextChar defaults to 0x20 + if (!tokens[j].content) continue; + // should skip all tokens except 'text', 'html_inline' or 'code_inline' + nextChar = tokens[j].content.charCodeAt(0); + break; + } + } + const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar)); + const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar)); + const isLastWhiteSpace = isWhiteSpace(lastChar); + const isNextWhiteSpace = isWhiteSpace(nextChar); + if (isNextWhiteSpace) { + canOpen = false; + } else if (isNextPunctChar) { + if (!(isLastWhiteSpace || isLastPunctChar)) { + canOpen = false; + } + } + if (isLastWhiteSpace) { + canClose = false; + } else if (isLastPunctChar) { + if (!(isNextWhiteSpace || isNextPunctChar)) { + canClose = false; + } + } + if (nextChar === 34 /* " */ && t[0] === '"') { + if (lastChar >= 48 /* 0 */ && lastChar <= 57 /* 9 */) { + // special case: 1"" - count first quote as an inch + canClose = canOpen = false; + } + } + if (canOpen && canClose) { + // Replace quotes in the middle of punctuation sequence, but not + // in the middle of the words, i.e.: + // 1. foo " bar " baz - not replaced + // 2. foo-"-bar-"-baz - replaced + // 3. foo"bar"baz - not replaced + canOpen = isLastPunctChar; + canClose = isNextPunctChar; + } + if (!canOpen && !canClose) { + // middle of word + if (isSingle) { + token.content = replaceAt(token.content, t.index, APOSTROPHE); + } + continue; + } + if (canClose) { + // this could be a closing quote, rewind the stack to get a match + for (j = stack.length - 1; j >= 0; j--) { + let item = stack[j]; + if (stack[j].level < thisLevel) { + break; + } + if (item.single === isSingle && stack[j].level === thisLevel) { + item = stack[j]; + let openQuote; + let closeQuote; + if (isSingle) { + openQuote = state.md.options.quotes[2]; + closeQuote = state.md.options.quotes[3]; + } else { + openQuote = state.md.options.quotes[0]; + closeQuote = state.md.options.quotes[1]; + } + // replace token.content *before* tokens[item.token].content, + // because, if they are pointing at the same token, replaceAt + // could mess up indices when quote length != 1 + token.content = replaceAt(token.content, t.index, closeQuote); + tokens[item.token].content = replaceAt(tokens[item.token].content, item.pos, openQuote); + pos += closeQuote.length - 1; + if (item.token === i) { + pos += openQuote.length - 1; + } + text = token.content; + max = text.length; + stack.length = j; + continue OUTER; + } + } + } + if (canOpen) { + stack.push({ + token: i, + pos: t.index, + single: isSingle, + level: thisLevel + }); + } else if (canClose && isSingle) { + token.content = replaceAt(token.content, t.index, APOSTROPHE); + } + } + } + } + function smartquotes(state) { + /* eslint max-depth:0 */ + if (!state.md.options.typographer) { + return; + } + for (let blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) { + if (state.tokens[blkIdx].type !== "inline" || !QUOTE_TEST_RE.test(state.tokens[blkIdx].content)) { + continue; + } + process_inlines(state.tokens[blkIdx].children, state); + } + } + // Join raw text tokens with the rest of the text + + // This is set as a separate rule to provide an opportunity for plugins + // to run text replacements after text join, but before escape join. + + // For example, `\:)` shouldn't be replaced with an emoji. + + function text_join(state) { + let curr, last; + const blockTokens = state.tokens; + const l = blockTokens.length; + for (let j = 0; j < l; j++) { + if (blockTokens[j].type !== "inline") continue; + const tokens = blockTokens[j].children; + const max = tokens.length; + for (curr = 0; curr < max; curr++) { + if (tokens[curr].type === "text_special") { + tokens[curr].type = "text"; + } + } + for (curr = last = 0; curr < max; curr++) { + if (tokens[curr].type === "text" && curr + 1 < max && tokens[curr + 1].type === "text") { + // collapse two adjacent text nodes + tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content; + } else { + if (curr !== last) { + tokens[last] = tokens[curr]; + } + last++; + } + } + if (curr !== last) { + tokens.length = last; + } + } + } + /** internal + * class Core + * + * Top-level rules executor. Glues block/inline parsers and does intermediate + * transformations. + **/ const _rules$2 = [ [ "normalize", normalize ], [ "block", block ], [ "inline", inline ], [ "linkify", linkify$1 ], [ "replacements", replace ], [ "smartquotes", smartquotes ], + // `text_join` finds `text_special` tokens (for escape sequences) + // and joins them with the rest of the text + [ "text_join", text_join ] ]; + /** + * new Core() + **/ function Core() { + /** + * Core#ruler -> Ruler + * + * [[Ruler]] instance. Keep configuration of core rules. + **/ + this.ruler = new Ruler; + for (let i = 0; i < _rules$2.length; i++) { + this.ruler.push(_rules$2[i][0], _rules$2[i][1]); + } + } + /** + * Core.process(state) + * + * Executes core chain rules. + **/ Core.prototype.process = function(state) { + const rules = this.ruler.getRules(""); + for (let i = 0, l = rules.length; i < l; i++) { + rules[i](state); + } + }; + Core.prototype.State = StateCore; + // Parser state class + function StateBlock(src, md, env, tokens) { + this.src = src; + // link to parser instance + this.md = md; + this.env = env; + + // Internal state vartiables + + this.tokens = tokens; + this.bMarks = []; + // line begin offsets for fast jumps + this.eMarks = []; + // line end offsets for fast jumps + this.tShift = []; + // offsets of the first non-space characters (tabs not expanded) + this.sCount = []; + // indents for each line (tabs expanded) + // An amount of virtual spaces (tabs expanded) between beginning + // of each line (bMarks) and real beginning of that line. + + // It exists only as a hack because blockquotes override bMarks + // losing information in the process. + + // It's used only when expanding tabs, you can think about it as + // an initial tab length, e.g. bsCount=21 applied to string `\t123` + // means first tab should be expanded to 4-21%4 === 3 spaces. + + this.bsCount = []; + // block parser variables + // required block content indent (for example, if we are + // inside a list, it would be positioned after list marker) + this.blkIndent = 0; + this.line = 0; + // line index in src + this.lineMax = 0; + // lines count + this.tight = false; + // loose/tight mode for lists + this.ddIndent = -1; + // indent of the current dd block (-1 if there isn't any) + this.listIndent = -1; + // indent of the current list block (-1 if there isn't any) + // can be 'blockquote', 'list', 'root', 'paragraph' or 'reference' + // used in lists to determine if they interrupt a paragraph + this.parentType = "root"; + this.level = 0; + // Create caches + // Generate markers. + const s = this.src; + for (let start = 0, pos = 0, indent = 0, offset = 0, len = s.length, indent_found = false; pos < len; pos++) { + const ch = s.charCodeAt(pos); + if (!indent_found) { + if (isSpace(ch)) { + indent++; + if (ch === 9) { + offset += 4 - offset % 4; + } else { + offset++; + } + continue; + } else { + indent_found = true; + } + } + if (ch === 10 || pos === len - 1) { + if (ch !== 10) { + pos++; + } + this.bMarks.push(start); + this.eMarks.push(pos); + this.tShift.push(indent); + this.sCount.push(offset); + this.bsCount.push(0); + indent_found = false; + indent = 0; + offset = 0; + start = pos + 1; + } + } + // Push fake entry to simplify cache bounds checks + this.bMarks.push(s.length); + this.eMarks.push(s.length); + this.tShift.push(0); + this.sCount.push(0); + this.bsCount.push(0); + this.lineMax = this.bMarks.length - 1; + // don't count last fake line + } + // Push new token to "stream". + + StateBlock.prototype.push = function(type, tag, nesting) { + const token = new Token(type, tag, nesting); + token.block = true; + if (nesting < 0) this.level--; + // closing tag + token.level = this.level; + if (nesting > 0) this.level++; + // opening tag + this.tokens.push(token); + return token; + }; + StateBlock.prototype.isEmpty = function isEmpty(line) { + return this.bMarks[line] + this.tShift[line] >= this.eMarks[line]; + }; + StateBlock.prototype.skipEmptyLines = function skipEmptyLines(from) { + for (let max = this.lineMax; from < max; from++) { + if (this.bMarks[from] + this.tShift[from] < this.eMarks[from]) { + break; + } + } + return from; + }; + // Skip spaces from given position. + StateBlock.prototype.skipSpaces = function skipSpaces(pos) { + for (let max = this.src.length; pos < max; pos++) { + const ch = this.src.charCodeAt(pos); + if (!isSpace(ch)) { + break; + } + } + return pos; + }; + // Skip spaces from given position in reverse. + StateBlock.prototype.skipSpacesBack = function skipSpacesBack(pos, min) { + if (pos <= min) { + return pos; + } + while (pos > min) { + if (!isSpace(this.src.charCodeAt(--pos))) { + return pos + 1; + } + } + return pos; + }; + // Skip char codes from given position + StateBlock.prototype.skipChars = function skipChars(pos, code) { + for (let max = this.src.length; pos < max; pos++) { + if (this.src.charCodeAt(pos) !== code) { + break; + } + } + return pos; + }; + // Skip char codes reverse from given position - 1 + StateBlock.prototype.skipCharsBack = function skipCharsBack(pos, code, min) { + if (pos <= min) { + return pos; + } + while (pos > min) { + if (code !== this.src.charCodeAt(--pos)) { + return pos + 1; + } + } + return pos; + }; + // cut lines range from source. + StateBlock.prototype.getLines = function getLines(begin, end, indent, keepLastLF) { + if (begin >= end) { + return ""; + } + const queue = new Array(end - begin); + for (let i = 0, line = begin; line < end; line++, i++) { + let lineIndent = 0; + const lineStart = this.bMarks[line]; + let first = lineStart; + let last; + if (line + 1 < end || keepLastLF) { + // No need for bounds check because we have fake entry on tail. + last = this.eMarks[line] + 1; + } else { + last = this.eMarks[line]; + } + while (first < last && lineIndent < indent) { + const ch = this.src.charCodeAt(first); + if (isSpace(ch)) { + if (ch === 9) { + lineIndent += 4 - (lineIndent + this.bsCount[line]) % 4; + } else { + lineIndent++; + } + } else if (first - lineStart < this.tShift[line]) { + // patched tShift masked characters to look like spaces (blockquotes, list markers) + lineIndent++; + } else { + break; + } + first++; + } + if (lineIndent > indent) { + // partially expanding tabs in code blocks, e.g '\t\tfoobar' + // with indent=2 becomes ' \tfoobar' + queue[i] = new Array(lineIndent - indent + 1).join(" ") + this.src.slice(first, last); + } else { + queue[i] = this.src.slice(first, last); + } + } + return queue.join(""); + }; + // re-export Token class to use in block rules + StateBlock.prototype.Token = Token; + // GFM table, https://github.github.com/gfm/#tables-extension- + // Limit the amount of empty autocompleted cells in a table, + // see https://github.com/markdown-it/markdown-it/issues/1000, + + // Both pulldown-cmark and commonmark-hs limit the number of cells this way to ~200k. + // We set it to 65k, which can expand user input by a factor of x370 + // (256x256 square is 1.8kB expanded into 650kB). + const MAX_AUTOCOMPLETED_CELLS = 65536; + function getLine(state, line) { + const pos = state.bMarks[line] + state.tShift[line]; + const max = state.eMarks[line]; + return state.src.slice(pos, max); + } + function escapedSplit(str) { + const result = []; + const max = str.length; + let pos = 0; + let ch = str.charCodeAt(pos); + let isEscaped = false; + let lastPos = 0; + let current = ""; + while (pos < max) { + if (ch === 124 /* | */) { + if (!isEscaped) { + // pipe separating cells, '|' + result.push(current + str.substring(lastPos, pos)); + current = ""; + lastPos = pos + 1; + } else { + // escaped pipe, '\|' + current += str.substring(lastPos, pos - 1); + lastPos = pos; + } + } + isEscaped = ch === 92 /* \ */; + pos++; + ch = str.charCodeAt(pos); + } + result.push(current + str.substring(lastPos)); + return result; + } + function table(state, startLine, endLine, silent) { + // should have at least two lines + if (startLine + 2 > endLine) { + return false; + } + let nextLine = startLine + 1; + if (state.sCount[nextLine] < state.blkIndent) { + return false; + } + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[nextLine] - state.blkIndent >= 4) { + return false; + } + // first character of the second line should be '|', '-', ':', + // and no other characters are allowed but spaces; + // basically, this is the equivalent of /^[-:|][-:|\s]*$/ regexp + let pos = state.bMarks[nextLine] + state.tShift[nextLine]; + if (pos >= state.eMarks[nextLine]) { + return false; + } + const firstCh = state.src.charCodeAt(pos++); + if (firstCh !== 124 /* | */ && firstCh !== 45 /* - */ && firstCh !== 58 /* : */) { + return false; + } + if (pos >= state.eMarks[nextLine]) { + return false; + } + const secondCh = state.src.charCodeAt(pos++); + if (secondCh !== 124 /* | */ && secondCh !== 45 /* - */ && secondCh !== 58 /* : */ && !isSpace(secondCh)) { + return false; + } + // if first character is '-', then second character must not be a space + // (due to parsing ambiguity with list) + if (firstCh === 45 /* - */ && isSpace(secondCh)) { + return false; + } + while (pos < state.eMarks[nextLine]) { + const ch = state.src.charCodeAt(pos); + if (ch !== 124 /* | */ && ch !== 45 /* - */ && ch !== 58 /* : */ && !isSpace(ch)) { + return false; + } + pos++; + } + let lineText = getLine(state, startLine + 1); + let columns = lineText.split("|"); + const aligns = []; + for (let i = 0; i < columns.length; i++) { + const t = columns[i].trim(); + if (!t) { + // allow empty columns before and after table, but not in between columns; + // e.g. allow ` |---| `, disallow ` ---||--- ` + if (i === 0 || i === columns.length - 1) { + continue; + } else { + return false; + } + } + if (!/^:?-+:?$/.test(t)) { + return false; + } + if (t.charCodeAt(t.length - 1) === 58 /* : */) { + aligns.push(t.charCodeAt(0) === 58 /* : */ ? "center" : "right"); + } else if (t.charCodeAt(0) === 58 /* : */) { + aligns.push("left"); + } else { + aligns.push(""); + } + } + lineText = getLine(state, startLine).trim(); + if (lineText.indexOf("|") === -1) { + return false; + } + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + columns = escapedSplit(lineText); + if (columns.length && columns[0] === "") columns.shift(); + if (columns.length && columns[columns.length - 1] === "") columns.pop(); + // header row will define an amount of columns in the entire table, + // and align row should be exactly the same (the rest of the rows can differ) + const columnCount = columns.length; + if (columnCount === 0 || columnCount !== aligns.length) { + return false; + } + if (silent) { + return true; + } + const oldParentType = state.parentType; + state.parentType = "table"; + // use 'blockquote' lists for termination because it's + // the most similar to tables + const terminatorRules = state.md.block.ruler.getRules("blockquote"); + const token_to = state.push("table_open", "table", 1); + const tableLines = [ startLine, 0 ]; + token_to.map = tableLines; + const token_tho = state.push("thead_open", "thead", 1); + token_tho.map = [ startLine, startLine + 1 ]; + const token_htro = state.push("tr_open", "tr", 1); + token_htro.map = [ startLine, startLine + 1 ]; + for (let i = 0; i < columns.length; i++) { + const token_ho = state.push("th_open", "th", 1); + if (aligns[i]) { + token_ho.attrs = [ [ "style", "text-align:" + aligns[i] ] ]; + } + const token_il = state.push("inline", "", 0); + token_il.content = columns[i].trim(); + token_il.children = []; + state.push("th_close", "th", -1); + } + state.push("tr_close", "tr", -1); + state.push("thead_close", "thead", -1); + let tbodyLines; + let autocompletedCells = 0; + for (nextLine = startLine + 2; nextLine < endLine; nextLine++) { + if (state.sCount[nextLine] < state.blkIndent) { + break; + } + let terminate = false; + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { + break; + } + lineText = getLine(state, nextLine).trim(); + if (!lineText) { + break; + } + if (state.sCount[nextLine] - state.blkIndent >= 4) { + break; + } + columns = escapedSplit(lineText); + if (columns.length && columns[0] === "") columns.shift(); + if (columns.length && columns[columns.length - 1] === "") columns.pop(); + // note: autocomplete count can be negative if user specifies more columns than header, + // but that does not affect intended use (which is limiting expansion) + autocompletedCells += columnCount - columns.length; + if (autocompletedCells > MAX_AUTOCOMPLETED_CELLS) { + break; + } + if (nextLine === startLine + 2) { + const token_tbo = state.push("tbody_open", "tbody", 1); + token_tbo.map = tbodyLines = [ startLine + 2, 0 ]; + } + const token_tro = state.push("tr_open", "tr", 1); + token_tro.map = [ nextLine, nextLine + 1 ]; + for (let i = 0; i < columnCount; i++) { + const token_tdo = state.push("td_open", "td", 1); + if (aligns[i]) { + token_tdo.attrs = [ [ "style", "text-align:" + aligns[i] ] ]; + } + const token_il = state.push("inline", "", 0); + token_il.content = columns[i] ? columns[i].trim() : ""; + token_il.children = []; + state.push("td_close", "td", -1); + } + state.push("tr_close", "tr", -1); + } + if (tbodyLines) { + state.push("tbody_close", "tbody", -1); + tbodyLines[1] = nextLine; + } + state.push("table_close", "table", -1); + tableLines[1] = nextLine; + state.parentType = oldParentType; + state.line = nextLine; + return true; + } + // Code block (4 spaces padded) + function code(state, startLine, endLine /*, silent */) { + if (state.sCount[startLine] - state.blkIndent < 4) { + return false; + } + let nextLine = startLine + 1; + let last = nextLine; + while (nextLine < endLine) { + if (state.isEmpty(nextLine)) { + nextLine++; + continue; + } + if (state.sCount[nextLine] - state.blkIndent >= 4) { + nextLine++; + last = nextLine; + continue; + } + break; + } + state.line = last; + const token = state.push("code_block", "code", 0); + token.content = state.getLines(startLine, last, 4 + state.blkIndent, false) + "\n"; + token.map = [ startLine, state.line ]; + return true; + } + // fences (``` lang, ~~~ lang) + function fence(state, startLine, endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine]; + let max = state.eMarks[startLine]; + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + if (pos + 3 > max) { + return false; + } + const marker = state.src.charCodeAt(pos); + if (marker !== 126 /* ~ */ && marker !== 96 /* ` */) { + return false; + } + // scan marker length + let mem = pos; + pos = state.skipChars(pos, marker); + let len = pos - mem; + if (len < 3) { + return false; + } + const markup = state.src.slice(mem, pos); + const params = state.src.slice(pos, max); + if (marker === 96 /* ` */) { + if (params.indexOf(String.fromCharCode(marker)) >= 0) { + return false; + } + } + // Since start is found, we can report success here in validation mode + if (silent) { + return true; + } + // search end of block + let nextLine = startLine; + let haveEndMarker = false; + for (;;) { + nextLine++; + if (nextLine >= endLine) { + // unclosed block should be autoclosed by end of document. + // also block seems to be autoclosed by end of parent + break; + } + pos = mem = state.bMarks[nextLine] + state.tShift[nextLine]; + max = state.eMarks[nextLine]; + if (pos < max && state.sCount[nextLine] < state.blkIndent) { + // non-empty line with negative indent should stop the list: + // - ``` + // test + break; + } + if (state.src.charCodeAt(pos) !== marker) { + continue; + } + if (state.sCount[nextLine] - state.blkIndent >= 4) { + // closing fence should be indented less than 4 spaces + continue; + } + pos = state.skipChars(pos, marker); + // closing code fence must be at least as long as the opening one + if (pos - mem < len) { + continue; + } + // make sure tail has spaces only + pos = state.skipSpaces(pos); + if (pos < max) { + continue; + } + haveEndMarker = true; + // found! + break; + } + // If a fence has heading spaces, they should be removed from its inner block + len = state.sCount[startLine]; + state.line = nextLine + (haveEndMarker ? 1 : 0); + const token = state.push("fence", "code", 0); + token.info = params; + token.content = state.getLines(startLine + 1, nextLine, len, true); + token.markup = markup; + token.map = [ startLine, state.line ]; + return true; + } + // Block quotes + function blockquote(state, startLine, endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine]; + let max = state.eMarks[startLine]; + const oldLineMax = state.lineMax; + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + // check the block quote marker + if (state.src.charCodeAt(pos) !== 62 /* > */) { + return false; + } + // we know that it's going to be a valid blockquote, + // so no point trying to find the end of it in silent mode + if (silent) { + return true; + } + const oldBMarks = []; + const oldBSCount = []; + const oldSCount = []; + const oldTShift = []; + const terminatorRules = state.md.block.ruler.getRules("blockquote"); + const oldParentType = state.parentType; + state.parentType = "blockquote"; + let lastLineEmpty = false; + let nextLine; + // Search the end of the block + + // Block ends with either: + // 1. an empty line outside: + // ``` + // > test + + // ``` + // 2. an empty line inside: + // ``` + // > + // test + // ``` + // 3. another tag: + // ``` + // > test + // - - - + // ``` + for (nextLine = startLine; nextLine < endLine; nextLine++) { + // check if it's outdented, i.e. it's inside list item and indented + // less than said list item: + // ``` + // 1. anything + // > current blockquote + // 2. checking this line + // ``` + const isOutdented = state.sCount[nextLine] < state.blkIndent; + pos = state.bMarks[nextLine] + state.tShift[nextLine]; + max = state.eMarks[nextLine]; + if (pos >= max) { + // Case 1: line is not inside the blockquote, and this line is empty. + break; + } + if (state.src.charCodeAt(pos++) === 62 /* > */ && !isOutdented) { + // This line is inside the blockquote. + // set offset past spaces and ">" + let initial = state.sCount[nextLine] + 1; + let spaceAfterMarker; + let adjustTab; + // skip one optional space after '>' + if (state.src.charCodeAt(pos) === 32 /* space */) { + // ' > test ' + // ^ -- position start of line here: + pos++; + initial++; + adjustTab = false; + spaceAfterMarker = true; + } else if (state.src.charCodeAt(pos) === 9 /* tab */) { + spaceAfterMarker = true; + if ((state.bsCount[nextLine] + initial) % 4 === 3) { + // ' >\t test ' + // ^ -- position start of line here (tab has width===1) + pos++; + initial++; + adjustTab = false; + } else { + // ' >\t test ' + // ^ -- position start of line here + shift bsCount slightly + // to make extra space appear + adjustTab = true; + } + } else { + spaceAfterMarker = false; + } + let offset = initial; + oldBMarks.push(state.bMarks[nextLine]); + state.bMarks[nextLine] = pos; + while (pos < max) { + const ch = state.src.charCodeAt(pos); + if (isSpace(ch)) { + if (ch === 9) { + offset += 4 - (offset + state.bsCount[nextLine] + (adjustTab ? 1 : 0)) % 4; + } else { + offset++; + } + } else { + break; + } + pos++; + } + lastLineEmpty = pos >= max; + oldBSCount.push(state.bsCount[nextLine]); + state.bsCount[nextLine] = state.sCount[nextLine] + 1 + (spaceAfterMarker ? 1 : 0); + oldSCount.push(state.sCount[nextLine]); + state.sCount[nextLine] = offset - initial; + oldTShift.push(state.tShift[nextLine]); + state.tShift[nextLine] = pos - state.bMarks[nextLine]; + continue; + } + // Case 2: line is not inside the blockquote, and the last line was empty. + if (lastLineEmpty) { + break; + } + // Case 3: another tag found. + let terminate = false; + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { + // Quirk to enforce "hard termination mode" for paragraphs; + // normally if you call `tokenize(state, startLine, nextLine)`, + // paragraphs will look below nextLine for paragraph continuation, + // but if blockquote is terminated by another tag, they shouldn't + state.lineMax = nextLine; + if (state.blkIndent !== 0) { + // state.blkIndent was non-zero, we now set it to zero, + // so we need to re-calculate all offsets to appear as + // if indent wasn't changed + oldBMarks.push(state.bMarks[nextLine]); + oldBSCount.push(state.bsCount[nextLine]); + oldTShift.push(state.tShift[nextLine]); + oldSCount.push(state.sCount[nextLine]); + state.sCount[nextLine] -= state.blkIndent; + } + break; + } + oldBMarks.push(state.bMarks[nextLine]); + oldBSCount.push(state.bsCount[nextLine]); + oldTShift.push(state.tShift[nextLine]); + oldSCount.push(state.sCount[nextLine]); + // A negative indentation means that this is a paragraph continuation + + state.sCount[nextLine] = -1; + } + const oldIndent = state.blkIndent; + state.blkIndent = 0; + const token_o = state.push("blockquote_open", "blockquote", 1); + token_o.markup = ">"; + const lines = [ startLine, 0 ]; + token_o.map = lines; + state.md.block.tokenize(state, startLine, nextLine); + const token_c = state.push("blockquote_close", "blockquote", -1); + token_c.markup = ">"; + state.lineMax = oldLineMax; + state.parentType = oldParentType; + lines[1] = state.line; + // Restore original tShift; this might not be necessary since the parser + // has already been here, but just to make sure we can do that. + for (let i = 0; i < oldTShift.length; i++) { + state.bMarks[i + startLine] = oldBMarks[i]; + state.tShift[i + startLine] = oldTShift[i]; + state.sCount[i + startLine] = oldSCount[i]; + state.bsCount[i + startLine] = oldBSCount[i]; + } + state.blkIndent = oldIndent; + return true; + } + // Horizontal rule + function hr(state, startLine, endLine, silent) { + const max = state.eMarks[startLine]; + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + let pos = state.bMarks[startLine] + state.tShift[startLine]; + const marker = state.src.charCodeAt(pos++); + // Check hr marker + if (marker !== 42 /* * */ && marker !== 45 /* - */ && marker !== 95 /* _ */) { + return false; + } + // markers can be mixed with spaces, but there should be at least 3 of them + let cnt = 1; + while (pos < max) { + const ch = state.src.charCodeAt(pos++); + if (ch !== marker && !isSpace(ch)) { + return false; + } + if (ch === marker) { + cnt++; + } + } + if (cnt < 3) { + return false; + } + if (silent) { + return true; + } + state.line = startLine + 1; + const token = state.push("hr", "hr", 0); + token.map = [ startLine, state.line ]; + token.markup = Array(cnt + 1).join(String.fromCharCode(marker)); + return true; + } + // Lists + // Search `[-+*][\n ]`, returns next pos after marker on success + // or -1 on fail. + function skipBulletListMarker(state, startLine) { + const max = state.eMarks[startLine]; + let pos = state.bMarks[startLine] + state.tShift[startLine]; + const marker = state.src.charCodeAt(pos++); + // Check bullet + if (marker !== 42 /* * */ && marker !== 45 /* - */ && marker !== 43 /* + */) { + return -1; + } + if (pos < max) { + const ch = state.src.charCodeAt(pos); + if (!isSpace(ch)) { + // " -test " - is not a list item + return -1; + } + } + return pos; + } + // Search `\d+[.)][\n ]`, returns next pos after marker on success + // or -1 on fail. + function skipOrderedListMarker(state, startLine) { + const start = state.bMarks[startLine] + state.tShift[startLine]; + const max = state.eMarks[startLine]; + let pos = start; + // List marker should have at least 2 chars (digit + dot) + if (pos + 1 >= max) { + return -1; + } + let ch = state.src.charCodeAt(pos++); + if (ch < 48 /* 0 */ || ch > 57 /* 9 */) { + return -1; + } + for (;;) { + // EOL -> fail + if (pos >= max) { + return -1; + } + ch = state.src.charCodeAt(pos++); + if (ch >= 48 /* 0 */ && ch <= 57 /* 9 */) { + // List marker should have no more than 9 digits + // (prevents integer overflow in browsers) + if (pos - start >= 10) { + return -1; + } + continue; + } + // found valid marker + if (ch === 41 /* ) */ || ch === 46 /* . */) { + break; + } + return -1; + } + if (pos < max) { + ch = state.src.charCodeAt(pos); + if (!isSpace(ch)) { + // " 1.test " - is not a list item + return -1; + } + } + return pos; + } + function markTightParagraphs(state, idx) { + const level = state.level + 2; + for (let i = idx + 2, l = state.tokens.length - 2; i < l; i++) { + if (state.tokens[i].level === level && state.tokens[i].type === "paragraph_open") { + state.tokens[i + 2].hidden = true; + state.tokens[i].hidden = true; + i += 2; + } + } + } + function list(state, startLine, endLine, silent) { + let max, pos, start, token; + let nextLine = startLine; + let tight = true; + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[nextLine] - state.blkIndent >= 4) { + return false; + } + // Special case: + // - item 1 + // - item 2 + // - item 3 + // - item 4 + // - this one is a paragraph continuation + if (state.listIndent >= 0 && state.sCount[nextLine] - state.listIndent >= 4 && state.sCount[nextLine] < state.blkIndent) { + return false; + } + let isTerminatingParagraph = false; + // limit conditions when list can interrupt + // a paragraph (validation mode only) + if (silent && state.parentType === "paragraph") { + // Next list item should still terminate previous list item; + // This code can fail if plugins use blkIndent as well as lists, + // but I hope the spec gets fixed long before that happens. + if (state.sCount[nextLine] >= state.blkIndent) { + isTerminatingParagraph = true; + } + } + // Detect list type and position after marker + let isOrdered; + let markerValue; + let posAfterMarker; + if ((posAfterMarker = skipOrderedListMarker(state, nextLine)) >= 0) { + isOrdered = true; + start = state.bMarks[nextLine] + state.tShift[nextLine]; + markerValue = Number(state.src.slice(start, posAfterMarker - 1)); + // If we're starting a new ordered list right after + // a paragraph, it should start with 1. + if (isTerminatingParagraph && markerValue !== 1) return false; + } else if ((posAfterMarker = skipBulletListMarker(state, nextLine)) >= 0) { + isOrdered = false; + } else { + return false; + } + // If we're starting a new unordered list right after + // a paragraph, first line should not be empty. + if (isTerminatingParagraph) { + if (state.skipSpaces(posAfterMarker) >= state.eMarks[nextLine]) return false; + } + // For validation mode we can terminate immediately + if (silent) { + return true; + } + // We should terminate list on style change. Remember first one to compare. + const markerCharCode = state.src.charCodeAt(posAfterMarker - 1); + // Start list + const listTokIdx = state.tokens.length; + if (isOrdered) { + token = state.push("ordered_list_open", "ol", 1); + if (markerValue !== 1) { + token.attrs = [ [ "start", markerValue ] ]; + } + } else { + token = state.push("bullet_list_open", "ul", 1); + } + const listLines = [ nextLine, 0 ]; + token.map = listLines; + token.markup = String.fromCharCode(markerCharCode); + + // Iterate list items + + let prevEmptyEnd = false; + const terminatorRules = state.md.block.ruler.getRules("list"); + const oldParentType = state.parentType; + state.parentType = "list"; + while (nextLine < endLine) { + pos = posAfterMarker; + max = state.eMarks[nextLine]; + const initial = state.sCount[nextLine] + posAfterMarker - (state.bMarks[nextLine] + state.tShift[nextLine]); + let offset = initial; + while (pos < max) { + const ch = state.src.charCodeAt(pos); + if (ch === 9) { + offset += 4 - (offset + state.bsCount[nextLine]) % 4; + } else if (ch === 32) { + offset++; + } else { + break; + } + pos++; + } + const contentStart = pos; + let indentAfterMarker; + if (contentStart >= max) { + // trimming space in "- \n 3" case, indent is 1 here + indentAfterMarker = 1; + } else { + indentAfterMarker = offset - initial; + } + // If we have more than 4 spaces, the indent is 1 + // (the rest is just indented code block) + if (indentAfterMarker > 4) { + indentAfterMarker = 1; + } + // " - test" + // ^^^^^ - calculating total length of this thing + const indent = initial + indentAfterMarker; + // Run subparser & write tokens + token = state.push("list_item_open", "li", 1); + token.markup = String.fromCharCode(markerCharCode); + const itemLines = [ nextLine, 0 ]; + token.map = itemLines; + if (isOrdered) { + token.info = state.src.slice(start, posAfterMarker - 1); + } + // change current state, then restore it after parser subcall + const oldTight = state.tight; + const oldTShift = state.tShift[nextLine]; + const oldSCount = state.sCount[nextLine]; + // - example list + // ^ listIndent position will be here + // ^ blkIndent position will be here + + const oldListIndent = state.listIndent; + state.listIndent = state.blkIndent; + state.blkIndent = indent; + state.tight = true; + state.tShift[nextLine] = contentStart - state.bMarks[nextLine]; + state.sCount[nextLine] = offset; + if (contentStart >= max && state.isEmpty(nextLine + 1)) { + // workaround for this case + // (list item is empty, list terminates before "foo"): + // ~~~~~~~~ + // - + // foo + // ~~~~~~~~ + state.line = Math.min(state.line + 2, endLine); + } else { + state.md.block.tokenize(state, nextLine, endLine, true); + } + // If any of list item is tight, mark list as tight + if (!state.tight || prevEmptyEnd) { + tight = false; + } + // Item become loose if finish with empty line, + // but we should filter last element, because it means list finish + prevEmptyEnd = state.line - nextLine > 1 && state.isEmpty(state.line - 1); + state.blkIndent = state.listIndent; + state.listIndent = oldListIndent; + state.tShift[nextLine] = oldTShift; + state.sCount[nextLine] = oldSCount; + state.tight = oldTight; + token = state.push("list_item_close", "li", -1); + token.markup = String.fromCharCode(markerCharCode); + nextLine = state.line; + itemLines[1] = nextLine; + if (nextLine >= endLine) { + break; + } + + // Try to check if list is terminated or continued. + + if (state.sCount[nextLine] < state.blkIndent) { + break; + } + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[nextLine] - state.blkIndent >= 4) { + break; + } + // fail if terminating block found + let terminate = false; + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { + break; + } + // fail if list has another type + if (isOrdered) { + posAfterMarker = skipOrderedListMarker(state, nextLine); + if (posAfterMarker < 0) { + break; + } + start = state.bMarks[nextLine] + state.tShift[nextLine]; + } else { + posAfterMarker = skipBulletListMarker(state, nextLine); + if (posAfterMarker < 0) { + break; + } + } + if (markerCharCode !== state.src.charCodeAt(posAfterMarker - 1)) { + break; + } + } + // Finalize list + if (isOrdered) { + token = state.push("ordered_list_close", "ol", -1); + } else { + token = state.push("bullet_list_close", "ul", -1); + } + token.markup = String.fromCharCode(markerCharCode); + listLines[1] = nextLine; + state.line = nextLine; + state.parentType = oldParentType; + // mark paragraphs tight if needed + if (tight) { + markTightParagraphs(state, listTokIdx); + } + return true; + } + function reference(state, startLine, _endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine]; + let max = state.eMarks[startLine]; + let nextLine = startLine + 1; + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + if (state.src.charCodeAt(pos) !== 91 /* [ */) { + return false; + } + function getNextLine(nextLine) { + const endLine = state.lineMax; + if (nextLine >= endLine || state.isEmpty(nextLine)) { + // empty line or end of input + return null; + } + let isContinuation = false; + // this would be a code block normally, but after paragraph + // it's considered a lazy continuation regardless of what's there + if (state.sCount[nextLine] - state.blkIndent > 3) { + isContinuation = true; + } + // quirk for blockquotes, this line should already be checked by that rule + if (state.sCount[nextLine] < 0) { + isContinuation = true; + } + if (!isContinuation) { + const terminatorRules = state.md.block.ruler.getRules("reference"); + const oldParentType = state.parentType; + state.parentType = "reference"; + // Some tags can terminate paragraph without empty line. + let terminate = false; + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + state.parentType = oldParentType; + if (terminate) { + // terminated by another block + return null; + } + } + const pos = state.bMarks[nextLine] + state.tShift[nextLine]; + const max = state.eMarks[nextLine]; + // max + 1 explicitly includes the newline + return state.src.slice(pos, max + 1); + } + let str = state.src.slice(pos, max + 1); + max = str.length; + let labelEnd = -1; + for (pos = 1; pos < max; pos++) { + const ch = str.charCodeAt(pos); + if (ch === 91 /* [ */) { + return false; + } else if (ch === 93 /* ] */) { + labelEnd = pos; + break; + } else if (ch === 10 /* \n */) { + const lineContent = getNextLine(nextLine); + if (lineContent !== null) { + str += lineContent; + max = str.length; + nextLine++; + } + } else if (ch === 92 /* \ */) { + pos++; + if (pos < max && str.charCodeAt(pos) === 10) { + const lineContent = getNextLine(nextLine); + if (lineContent !== null) { + str += lineContent; + max = str.length; + nextLine++; + } + } + } + } + if (labelEnd < 0 || str.charCodeAt(labelEnd + 1) !== 58 /* : */) { + return false; + } + // [label]: destination 'title' + // ^^^ skip optional whitespace here + for (pos = labelEnd + 2; pos < max; pos++) { + const ch = str.charCodeAt(pos); + if (ch === 10) { + const lineContent = getNextLine(nextLine); + if (lineContent !== null) { + str += lineContent; + max = str.length; + nextLine++; + } + } else if (isSpace(ch)) ; else { + break; + } + } + // [label]: destination 'title' + // ^^^^^^^^^^^ parse this + const destRes = state.md.helpers.parseLinkDestination(str, pos, max); + if (!destRes.ok) { + return false; + } + const href = state.md.normalizeLink(destRes.str); + if (!state.md.validateLink(href)) { + return false; + } + pos = destRes.pos; + // save cursor state, we could require to rollback later + const destEndPos = pos; + const destEndLineNo = nextLine; + // [label]: destination 'title' + // ^^^ skipping those spaces + const start = pos; + for (;pos < max; pos++) { + const ch = str.charCodeAt(pos); + if (ch === 10) { + const lineContent = getNextLine(nextLine); + if (lineContent !== null) { + str += lineContent; + max = str.length; + nextLine++; + } + } else if (isSpace(ch)) ; else { + break; + } + } + // [label]: destination 'title' + // ^^^^^^^ parse this + let titleRes = state.md.helpers.parseLinkTitle(str, pos, max); + while (titleRes.can_continue) { + const lineContent = getNextLine(nextLine); + if (lineContent === null) break; + str += lineContent; + pos = max; + max = str.length; + nextLine++; + titleRes = state.md.helpers.parseLinkTitle(str, pos, max, titleRes); + } + let title; + if (pos < max && start !== pos && titleRes.ok) { + title = titleRes.str; + pos = titleRes.pos; + } else { + title = ""; + pos = destEndPos; + nextLine = destEndLineNo; + } + // skip trailing spaces until the rest of the line + while (pos < max) { + const ch = str.charCodeAt(pos); + if (!isSpace(ch)) { + break; + } + pos++; + } + if (pos < max && str.charCodeAt(pos) !== 10) { + if (title) { + // garbage at the end of the line after title, + // but it could still be a valid reference if we roll back + title = ""; + pos = destEndPos; + nextLine = destEndLineNo; + while (pos < max) { + const ch = str.charCodeAt(pos); + if (!isSpace(ch)) { + break; + } + pos++; + } + } + } + if (pos < max && str.charCodeAt(pos) !== 10) { + // garbage at the end of the line + return false; + } + const label = normalizeReference(str.slice(1, labelEnd)); + if (!label) { + // CommonMark 0.20 disallows empty labels + return false; + } + // Reference can not terminate anything. This check is for safety only. + /* istanbul ignore if */ if (silent) { + return true; + } + if (typeof state.env.references === "undefined") { + state.env.references = {}; + } + if (typeof state.env.references[label] === "undefined") { + state.env.references[label] = { + title: title, + href: href + }; + } + state.line = nextLine; + return true; + } + // List of valid html blocks names, according to commonmark spec + // https://spec.commonmark.org/0.30/#html-blocks + var block_names = [ "address", "article", "aside", "base", "basefont", "blockquote", "body", "caption", "center", "col", "colgroup", "dd", "details", "dialog", "dir", "div", "dl", "dt", "fieldset", "figcaption", "figure", "footer", "form", "frame", "frameset", "h1", "h2", "h3", "h4", "h5", "h6", "head", "header", "hr", "html", "iframe", "legend", "li", "link", "main", "menu", "menuitem", "nav", "noframes", "ol", "optgroup", "option", "p", "param", "search", "section", "summary", "table", "tbody", "td", "tfoot", "th", "thead", "title", "tr", "track", "ul" ]; + // Regexps to match html elements + const attr_name = "[a-zA-Z_:][a-zA-Z0-9:._-]*"; + const unquoted = "[^\"'=<>`\\x00-\\x20]+"; + const single_quoted = "'[^']*'"; + const double_quoted = '"[^"]*"'; + const attr_value = "(?:" + unquoted + "|" + single_quoted + "|" + double_quoted + ")"; + const attribute = "(?:\\s+" + attr_name + "(?:\\s*=\\s*" + attr_value + ")?)"; + const open_tag = "<[A-Za-z][A-Za-z0-9\\-]*" + attribute + "*\\s*\\/?>"; + const close_tag = "<\\/[A-Za-z][A-Za-z0-9\\-]*\\s*>"; + const comment = "\x3c!---?>|\x3c!--(?:[^-]|-[^-]|--[^>])*--\x3e"; + const processing = "<[?][\\s\\S]*?[?]>"; + const declaration = "]*>"; + const cdata = ""; + const HTML_TAG_RE = new RegExp("^(?:" + open_tag + "|" + close_tag + "|" + comment + "|" + processing + "|" + declaration + "|" + cdata + ")"); + const HTML_OPEN_CLOSE_TAG_RE = new RegExp("^(?:" + open_tag + "|" + close_tag + ")"); + // HTML block + // An array of opening and corresponding closing sequences for html tags, + // last argument defines whether it can terminate a paragraph or not + + const HTML_SEQUENCES = [ [ /^<(script|pre|style|textarea)(?=(\s|>|$))/i, /<\/(script|pre|style|textarea)>/i, true ], [ /^/, true ], [ /^<\?/, /\?>/, true ], [ /^/, true ], [ /^/, true ], [ new RegExp("^|$))", "i"), /^$/, true ], [ new RegExp(HTML_OPEN_CLOSE_TAG_RE.source + "\\s*$"), /^$/, false ] ]; + function html_block(state, startLine, endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine]; + let max = state.eMarks[startLine]; + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + if (!state.md.options.html) { + return false; + } + if (state.src.charCodeAt(pos) !== 60 /* < */) { + return false; + } + let lineText = state.src.slice(pos, max); + let i = 0; + for (;i < HTML_SEQUENCES.length; i++) { + if (HTML_SEQUENCES[i][0].test(lineText)) { + break; + } + } + if (i === HTML_SEQUENCES.length) { + return false; + } + if (silent) { + // true if this sequence can be a terminator, false otherwise + return HTML_SEQUENCES[i][2]; + } + let nextLine = startLine + 1; + // If we are here - we detected HTML block. + // Let's roll down till block end. + if (!HTML_SEQUENCES[i][1].test(lineText)) { + for (;nextLine < endLine; nextLine++) { + if (state.sCount[nextLine] < state.blkIndent) { + break; + } + pos = state.bMarks[nextLine] + state.tShift[nextLine]; + max = state.eMarks[nextLine]; + lineText = state.src.slice(pos, max); + if (HTML_SEQUENCES[i][1].test(lineText)) { + if (lineText.length !== 0) { + nextLine++; + } + break; + } + } + } + state.line = nextLine; + const token = state.push("html_block", "", 0); + token.map = [ startLine, nextLine ]; + token.content = state.getLines(startLine, nextLine, state.blkIndent, true); + return true; + } + // heading (#, ##, ...) + function heading(state, startLine, endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine]; + let max = state.eMarks[startLine]; + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + let ch = state.src.charCodeAt(pos); + if (ch !== 35 /* # */ || pos >= max) { + return false; + } + // count heading level + let level = 1; + ch = state.src.charCodeAt(++pos); + while (ch === 35 /* # */ && pos < max && level <= 6) { + level++; + ch = state.src.charCodeAt(++pos); + } + if (level > 6 || pos < max && !isSpace(ch)) { + return false; + } + if (silent) { + return true; + } + // Let's cut tails like ' ### ' from the end of string + max = state.skipSpacesBack(max, pos); + const tmp = state.skipCharsBack(max, 35, pos); + // # + if (tmp > pos && isSpace(state.src.charCodeAt(tmp - 1))) { + max = tmp; + } + state.line = startLine + 1; + const token_o = state.push("heading_open", "h" + String(level), 1); + token_o.markup = "########".slice(0, level); + token_o.map = [ startLine, state.line ]; + const token_i = state.push("inline", "", 0); + token_i.content = state.src.slice(pos, max).trim(); + token_i.map = [ startLine, state.line ]; + token_i.children = []; + const token_c = state.push("heading_close", "h" + String(level), -1); + token_c.markup = "########".slice(0, level); + return true; + } + // lheading (---, ===) + function lheading(state, startLine, endLine /*, silent */) { + const terminatorRules = state.md.block.ruler.getRules("paragraph"); + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { + return false; + } + const oldParentType = state.parentType; + state.parentType = "paragraph"; + // use paragraph to match terminatorRules + // jump line-by-line until empty one or EOF + let level = 0; + let marker; + let nextLine = startLine + 1; + for (;nextLine < endLine && !state.isEmpty(nextLine); nextLine++) { + // this would be a code block normally, but after paragraph + // it's considered a lazy continuation regardless of what's there + if (state.sCount[nextLine] - state.blkIndent > 3) { + continue; + } + + // Check for underline in setext header + + if (state.sCount[nextLine] >= state.blkIndent) { + let pos = state.bMarks[nextLine] + state.tShift[nextLine]; + const max = state.eMarks[nextLine]; + if (pos < max) { + marker = state.src.charCodeAt(pos); + if (marker === 45 /* - */ || marker === 61 /* = */) { + pos = state.skipChars(pos, marker); + pos = state.skipSpaces(pos); + if (pos >= max) { + level = marker === 61 /* = */ ? 1 : 2; + break; + } + } + } + } + // quirk for blockquotes, this line should already be checked by that rule + if (state.sCount[nextLine] < 0) { + continue; + } + // Some tags can terminate paragraph without empty line. + let terminate = false; + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { + break; + } + } + if (!level) { + // Didn't find valid underline + return false; + } + const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim(); + state.line = nextLine + 1; + const token_o = state.push("heading_open", "h" + String(level), 1); + token_o.markup = String.fromCharCode(marker); + token_o.map = [ startLine, state.line ]; + const token_i = state.push("inline", "", 0); + token_i.content = content; + token_i.map = [ startLine, state.line - 1 ]; + token_i.children = []; + const token_c = state.push("heading_close", "h" + String(level), -1); + token_c.markup = String.fromCharCode(marker); + state.parentType = oldParentType; + return true; + } + // Paragraph + function paragraph(state, startLine, endLine) { + const terminatorRules = state.md.block.ruler.getRules("paragraph"); + const oldParentType = state.parentType; + let nextLine = startLine + 1; + state.parentType = "paragraph"; + // jump line-by-line until empty one or EOF + for (;nextLine < endLine && !state.isEmpty(nextLine); nextLine++) { + // this would be a code block normally, but after paragraph + // it's considered a lazy continuation regardless of what's there + if (state.sCount[nextLine] - state.blkIndent > 3) { + continue; + } + // quirk for blockquotes, this line should already be checked by that rule + if (state.sCount[nextLine] < 0) { + continue; + } + // Some tags can terminate paragraph without empty line. + let terminate = false; + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { + break; + } + } + const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim(); + state.line = nextLine; + const token_o = state.push("paragraph_open", "p", 1); + token_o.map = [ startLine, state.line ]; + const token_i = state.push("inline", "", 0); + token_i.content = content; + token_i.map = [ startLine, state.line ]; + token_i.children = []; + state.push("paragraph_close", "p", -1); + state.parentType = oldParentType; + return true; + } + /** internal + * class ParserBlock + * + * Block-level tokenizer. + **/ const _rules$1 = [ + // First 2 params - rule name & source. Secondary array - list of rules, + // which can be terminated by this one. + [ "table", table, [ "paragraph", "reference" ] ], [ "code", code ], [ "fence", fence, [ "paragraph", "reference", "blockquote", "list" ] ], [ "blockquote", blockquote, [ "paragraph", "reference", "blockquote", "list" ] ], [ "hr", hr, [ "paragraph", "reference", "blockquote", "list" ] ], [ "list", list, [ "paragraph", "reference", "blockquote" ] ], [ "reference", reference ], [ "html_block", html_block, [ "paragraph", "reference", "blockquote" ] ], [ "heading", heading, [ "paragraph", "reference", "blockquote" ] ], [ "lheading", lheading ], [ "paragraph", paragraph ] ]; + /** + * new ParserBlock() + **/ function ParserBlock() { + /** + * ParserBlock#ruler -> Ruler + * + * [[Ruler]] instance. Keep configuration of block rules. + **/ + this.ruler = new Ruler; + for (let i = 0; i < _rules$1.length; i++) { + this.ruler.push(_rules$1[i][0], _rules$1[i][1], { + alt: (_rules$1[i][2] || []).slice() + }); + } + } + // Generate tokens for input range + + ParserBlock.prototype.tokenize = function(state, startLine, endLine) { + const rules = this.ruler.getRules(""); + const len = rules.length; + const maxNesting = state.md.options.maxNesting; + let line = startLine; + let hasEmptyLines = false; + while (line < endLine) { + state.line = line = state.skipEmptyLines(line); + if (line >= endLine) { + break; + } + // Termination condition for nested calls. + // Nested calls currently used for blockquotes & lists + if (state.sCount[line] < state.blkIndent) { + break; + } + // If nesting level exceeded - skip tail to the end. That's not ordinary + // situation and we should not care about content. + if (state.level >= maxNesting) { + state.line = endLine; + break; + } + // Try all possible rules. + // On success, rule should: + + // - update `state.line` + // - update `state.tokens` + // - return true + const prevLine = state.line; + let ok = false; + for (let i = 0; i < len; i++) { + ok = rules[i](state, line, endLine, false); + if (ok) { + if (prevLine >= state.line) { + throw new Error("block rule didn't increment state.line"); + } + break; + } + } + // this can only happen if user disables paragraph rule + if (!ok) throw new Error("none of the block rules matched"); + // set state.tight if we had an empty line before current tag + // i.e. latest empty line should not count + state.tight = !hasEmptyLines; + // paragraph might "eat" one newline after it in nested lists + if (state.isEmpty(state.line - 1)) { + hasEmptyLines = true; + } + line = state.line; + if (line < endLine && state.isEmpty(line)) { + hasEmptyLines = true; + line++; + state.line = line; + } + } + }; + /** + * ParserBlock.parse(str, md, env, outTokens) + * + * Process input string and push block tokens into `outTokens` + **/ ParserBlock.prototype.parse = function(src, md, env, outTokens) { + if (!src) { + return; + } + const state = new this.State(src, md, env, outTokens); + this.tokenize(state, state.line, state.lineMax); + }; + ParserBlock.prototype.State = StateBlock; + // Inline parser state + function StateInline(src, md, env, outTokens) { + this.src = src; + this.env = env; + this.md = md; + this.tokens = outTokens; + this.tokens_meta = Array(outTokens.length); + this.pos = 0; + this.posMax = this.src.length; + this.level = 0; + this.pending = ""; + this.pendingLevel = 0; + // Stores { start: end } pairs. Useful for backtrack + // optimization of pairs parse (emphasis, strikes). + this.cache = {}; + // List of emphasis-like delimiters for current tag + this.delimiters = []; + // Stack of delimiter lists for upper level tags + this._prev_delimiters = []; + // backtick length => last seen position + this.backticks = {}; + this.backticksScanned = false; + // Counter used to disable inline linkify-it execution + // inside and markdown links + this.linkLevel = 0; + } + // Flush pending text + + StateInline.prototype.pushPending = function() { + const token = new Token("text", "", 0); + token.content = this.pending; + token.level = this.pendingLevel; + this.tokens.push(token); + this.pending = ""; + return token; + }; + // Push new token to "stream". + // If pending text exists - flush it as text token + + StateInline.prototype.push = function(type, tag, nesting) { + if (this.pending) { + this.pushPending(); + } + const token = new Token(type, tag, nesting); + let token_meta = null; + if (nesting < 0) { + // closing tag + this.level--; + this.delimiters = this._prev_delimiters.pop(); + } + token.level = this.level; + if (nesting > 0) { + // opening tag + this.level++; + this._prev_delimiters.push(this.delimiters); + this.delimiters = []; + token_meta = { + delimiters: this.delimiters + }; + } + this.pendingLevel = this.level; + this.tokens.push(token); + this.tokens_meta.push(token_meta); + return token; + }; + // Scan a sequence of emphasis-like markers, and determine whether + // it can start an emphasis sequence or end an emphasis sequence. + + // - start - position to scan from (it should point at a valid marker); + // - canSplitWord - determine if these markers can be found inside a word + + StateInline.prototype.scanDelims = function(start, canSplitWord) { + const max = this.posMax; + const marker = this.src.charCodeAt(start); + // treat beginning of the line as a whitespace + const lastChar = start > 0 ? this.src.charCodeAt(start - 1) : 32; + let pos = start; + while (pos < max && this.src.charCodeAt(pos) === marker) { + pos++; + } + const count = pos - start; + // treat end of the line as a whitespace + const nextChar = pos < max ? this.src.charCodeAt(pos) : 32; + const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar)); + const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar)); + const isLastWhiteSpace = isWhiteSpace(lastChar); + const isNextWhiteSpace = isWhiteSpace(nextChar); + const left_flanking = !isNextWhiteSpace && (!isNextPunctChar || isLastWhiteSpace || isLastPunctChar); + const right_flanking = !isLastWhiteSpace && (!isLastPunctChar || isNextWhiteSpace || isNextPunctChar); + const can_open = left_flanking && (canSplitWord || !right_flanking || isLastPunctChar); + const can_close = right_flanking && (canSplitWord || !left_flanking || isNextPunctChar); + return { + can_open: can_open, + can_close: can_close, + length: count + }; + }; + // re-export Token class to use in block rules + StateInline.prototype.Token = Token; + // Skip text characters for text token, place those to pending buffer + // and increment current pos + // Rule to skip pure text + // '{}$%@~+=:' reserved for extentions + // !, ", #, $, %, &, ', (, ), *, +, ,, -, ., /, :, ;, <, =, >, ?, @, [, \, ], ^, _, `, {, |, }, or ~ + // !!!! Don't confuse with "Markdown ASCII Punctuation" chars + // http://spec.commonmark.org/0.15/#ascii-punctuation-character + function isTerminatorChar(ch) { + switch (ch) { + case 10 /* \n */ : + case 33 /* ! */ : + case 35 /* # */ : + case 36 /* $ */ : + case 37 /* % */ : + case 38 /* & */ : + case 42 /* * */ : + case 43 /* + */ : + case 45 /* - */ : + case 58 /* : */ : + case 60 /* < */ : + case 61 /* = */ : + case 62 /* > */ : + case 64 /* @ */ : + case 91 /* [ */ : + case 92 /* \ */ : + case 93 /* ] */ : + case 94 /* ^ */ : + case 95 /* _ */ : + case 96 /* ` */ : + case 123 /* { */ : + case 125 /* } */ : + case 126 /* ~ */ : + return true; + + default: + return false; + } + } + function text(state, silent) { + let pos = state.pos; + while (pos < state.posMax && !isTerminatorChar(state.src.charCodeAt(pos))) { + pos++; + } + if (pos === state.pos) { + return false; + } + if (!silent) { + state.pending += state.src.slice(state.pos, pos); + } + state.pos = pos; + return true; + } + // Alternative implementation, for memory. + + // It costs 10% of performance, but allows extend terminators list, if place it + // to `ParserInline` property. Probably, will switch to it sometime, such + // flexibility required. + /* + var TERMINATOR_RE = /[\n!#$%&*+\-:<=>@[\\\]^_`{}~]/; + + module.exports = function text(state, silent) { + var pos = state.pos, + idx = state.src.slice(pos).search(TERMINATOR_RE); + + // first char is terminator -> empty text + if (idx === 0) { return false; } + + // no terminator -> text till end of string + if (idx < 0) { + if (!silent) { state.pending += state.src.slice(pos); } + state.pos = state.src.length; + return true; + } + + if (!silent) { state.pending += state.src.slice(pos, pos + idx); } + + state.pos += idx; + + return true; + }; */ + // Process links like https://example.org/ + // RFC3986: scheme = ALPHA *( ALPHA / DIGIT / "+" / "-" / "." ) + const SCHEME_RE = /(?:^|[^a-z0-9.+-])([a-z][a-z0-9.+-]*)$/i; + function linkify(state, silent) { + if (!state.md.options.linkify) return false; + if (state.linkLevel > 0) return false; + const pos = state.pos; + const max = state.posMax; + if (pos + 3 > max) return false; + if (state.src.charCodeAt(pos) !== 58 /* : */) return false; + if (state.src.charCodeAt(pos + 1) !== 47 /* / */) return false; + if (state.src.charCodeAt(pos + 2) !== 47 /* / */) return false; + const match = state.pending.match(SCHEME_RE); + if (!match) return false; + const proto = match[1]; + const link = state.md.linkify.matchAtStart(state.src.slice(pos - proto.length)); + if (!link) return false; + let url = link.url; + // invalid link, but still detected by linkify somehow; + // need to check to prevent infinite loop below + if (url.length <= proto.length) return false; + // disallow '*' at the end of the link (conflicts with emphasis) + url = url.replace(/\*+$/, ""); + const fullUrl = state.md.normalizeLink(url); + if (!state.md.validateLink(fullUrl)) return false; + if (!silent) { + state.pending = state.pending.slice(0, -proto.length); + const token_o = state.push("link_open", "a", 1); + token_o.attrs = [ [ "href", fullUrl ] ]; + token_o.markup = "linkify"; + token_o.info = "auto"; + const token_t = state.push("text", "", 0); + token_t.content = state.md.normalizeLinkText(url); + const token_c = state.push("link_close", "a", -1); + token_c.markup = "linkify"; + token_c.info = "auto"; + } + state.pos += url.length - proto.length; + return true; + } + // Proceess '\n' + function newline(state, silent) { + let pos = state.pos; + if (state.src.charCodeAt(pos) !== 10 /* \n */) { + return false; + } + const pmax = state.pending.length - 1; + const max = state.posMax; + // ' \n' -> hardbreak + // Lookup in pending chars is bad practice! Don't copy to other rules! + // Pending string is stored in concat mode, indexed lookups will cause + // convertion to flat mode. + if (!silent) { + if (pmax >= 0 && state.pending.charCodeAt(pmax) === 32) { + if (pmax >= 1 && state.pending.charCodeAt(pmax - 1) === 32) { + // Find whitespaces tail of pending chars. + let ws = pmax - 1; + while (ws >= 1 && state.pending.charCodeAt(ws - 1) === 32) ws--; + state.pending = state.pending.slice(0, ws); + state.push("hardbreak", "br", 0); + } else { + state.pending = state.pending.slice(0, -1); + state.push("softbreak", "br", 0); + } + } else { + state.push("softbreak", "br", 0); + } + } + pos++; + // skip heading spaces for next line + while (pos < max && isSpace(state.src.charCodeAt(pos))) { + pos++; + } + state.pos = pos; + return true; + } + // Process escaped chars and hardbreaks + const ESCAPED = []; + for (let i = 0; i < 256; i++) { + ESCAPED.push(0); + } + "\\!\"#$%&'()*+,./:;<=>?@[]^_`{|}~-".split("").forEach((function(ch) { + ESCAPED[ch.charCodeAt(0)] = 1; + })); + function escape(state, silent) { + let pos = state.pos; + const max = state.posMax; + if (state.src.charCodeAt(pos) !== 92 /* \ */) return false; + pos++; + // '\' at the end of the inline block + if (pos >= max) return false; + let ch1 = state.src.charCodeAt(pos); + if (ch1 === 10) { + if (!silent) { + state.push("hardbreak", "br", 0); + } + pos++; + // skip leading whitespaces from next line + while (pos < max) { + ch1 = state.src.charCodeAt(pos); + if (!isSpace(ch1)) break; + pos++; + } + state.pos = pos; + return true; + } + let escapedStr = state.src[pos]; + if (ch1 >= 55296 && ch1 <= 56319 && pos + 1 < max) { + const ch2 = state.src.charCodeAt(pos + 1); + if (ch2 >= 56320 && ch2 <= 57343) { + escapedStr += state.src[pos + 1]; + pos++; + } + } + const origStr = "\\" + escapedStr; + if (!silent) { + const token = state.push("text_special", "", 0); + if (ch1 < 256 && ESCAPED[ch1] !== 0) { + token.content = escapedStr; + } else { + token.content = origStr; + } + token.markup = origStr; + token.info = "escape"; + } + state.pos = pos + 1; + return true; + } + // Parse backticks + function backtick(state, silent) { + let pos = state.pos; + const ch = state.src.charCodeAt(pos); + if (ch !== 96 /* ` */) { + return false; + } + const start = pos; + pos++; + const max = state.posMax; + // scan marker length + while (pos < max && state.src.charCodeAt(pos) === 96 /* ` */) { + pos++; + } + const marker = state.src.slice(start, pos); + const openerLength = marker.length; + if (state.backticksScanned && (state.backticks[openerLength] || 0) <= start) { + if (!silent) state.pending += marker; + state.pos += openerLength; + return true; + } + let matchEnd = pos; + let matchStart; + // Nothing found in the cache, scan until the end of the line (or until marker is found) + while ((matchStart = state.src.indexOf("`", matchEnd)) !== -1) { + matchEnd = matchStart + 1; + // scan marker length + while (matchEnd < max && state.src.charCodeAt(matchEnd) === 96 /* ` */) { + matchEnd++; + } + const closerLength = matchEnd - matchStart; + if (closerLength === openerLength) { + // Found matching closer length. + if (!silent) { + const token = state.push("code_inline", "code", 0); + token.markup = marker; + token.content = state.src.slice(pos, matchStart).replace(/\n/g, " ").replace(/^ (.+) $/, "$1"); + } + state.pos = matchEnd; + return true; + } + // Some different length found, put it in cache as upper limit of where closer can be found + state.backticks[closerLength] = matchStart; + } + // Scanned through the end, didn't find anything + state.backticksScanned = true; + if (!silent) state.pending += marker; + state.pos += openerLength; + return true; + } + // ~~strike through~~ + + // Insert each marker as a separate text token, and add it to delimiter list + + function strikethrough_tokenize(state, silent) { + const start = state.pos; + const marker = state.src.charCodeAt(start); + if (silent) { + return false; + } + if (marker !== 126 /* ~ */) { + return false; + } + const scanned = state.scanDelims(state.pos, true); + let len = scanned.length; + const ch = String.fromCharCode(marker); + if (len < 2) { + return false; + } + let token; + if (len % 2) { + token = state.push("text", "", 0); + token.content = ch; + len--; + } + for (let i = 0; i < len; i += 2) { + token = state.push("text", "", 0); + token.content = ch + ch; + state.delimiters.push({ + marker: marker, + length: 0, + // disable "rule of 3" length checks meant for emphasis + token: state.tokens.length - 1, + end: -1, + open: scanned.can_open, + close: scanned.can_close + }); + } + state.pos += scanned.length; + return true; + } + function postProcess$1(state, delimiters) { + let token; + const loneMarkers = []; + const max = delimiters.length; + for (let i = 0; i < max; i++) { + const startDelim = delimiters[i]; + if (startDelim.marker !== 126 /* ~ */) { + continue; + } + if (startDelim.end === -1) { + continue; + } + const endDelim = delimiters[startDelim.end]; + token = state.tokens[startDelim.token]; + token.type = "s_open"; + token.tag = "s"; + token.nesting = 1; + token.markup = "~~"; + token.content = ""; + token = state.tokens[endDelim.token]; + token.type = "s_close"; + token.tag = "s"; + token.nesting = -1; + token.markup = "~~"; + token.content = ""; + if (state.tokens[endDelim.token - 1].type === "text" && state.tokens[endDelim.token - 1].content === "~") { + loneMarkers.push(endDelim.token - 1); + } + } + // If a marker sequence has an odd number of characters, it's splitted + // like this: `~~~~~` -> `~` + `~~` + `~~`, leaving one marker at the + // start of the sequence. + + // So, we have to move all those markers after subsequent s_close tags. + + while (loneMarkers.length) { + const i = loneMarkers.pop(); + let j = i + 1; + while (j < state.tokens.length && state.tokens[j].type === "s_close") { + j++; + } + j--; + if (i !== j) { + token = state.tokens[j]; + state.tokens[j] = state.tokens[i]; + state.tokens[i] = token; + } + } + } + // Walk through delimiter list and replace text tokens with tags + + function strikethrough_postProcess(state) { + const tokens_meta = state.tokens_meta; + const max = state.tokens_meta.length; + postProcess$1(state, state.delimiters); + for (let curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + postProcess$1(state, tokens_meta[curr].delimiters); + } + } + } + var r_strikethrough = { + tokenize: strikethrough_tokenize, + postProcess: strikethrough_postProcess + }; + // Process *this* and _that_ + + // Insert each marker as a separate text token, and add it to delimiter list + + function emphasis_tokenize(state, silent) { + const start = state.pos; + const marker = state.src.charCodeAt(start); + if (silent) { + return false; + } + if (marker !== 95 /* _ */ && marker !== 42 /* * */) { + return false; + } + const scanned = state.scanDelims(state.pos, marker === 42); + for (let i = 0; i < scanned.length; i++) { + const token = state.push("text", "", 0); + token.content = String.fromCharCode(marker); + state.delimiters.push({ + // Char code of the starting marker (number). + marker: marker, + // Total length of these series of delimiters. + length: scanned.length, + // A position of the token this delimiter corresponds to. + token: state.tokens.length - 1, + // If this delimiter is matched as a valid opener, `end` will be + // equal to its position, otherwise it's `-1`. + end: -1, + // Boolean flags that determine if this delimiter could open or close + // an emphasis. + open: scanned.can_open, + close: scanned.can_close + }); + } + state.pos += scanned.length; + return true; + } + function postProcess(state, delimiters) { + const max = delimiters.length; + for (let i = max - 1; i >= 0; i--) { + const startDelim = delimiters[i]; + if (startDelim.marker !== 95 /* _ */ && startDelim.marker !== 42 /* * */) { + continue; + } + // Process only opening markers + if (startDelim.end === -1) { + continue; + } + const endDelim = delimiters[startDelim.end]; + // If the previous delimiter has the same marker and is adjacent to this one, + // merge those into one strong delimiter. + + // `whatever` -> `whatever` + + const isStrong = i > 0 && delimiters[i - 1].end === startDelim.end + 1 && + // check that first two markers match and adjacent + delimiters[i - 1].marker === startDelim.marker && delimiters[i - 1].token === startDelim.token - 1 && + // check that last two markers are adjacent (we can safely assume they match) + delimiters[startDelim.end + 1].token === endDelim.token + 1; + const ch = String.fromCharCode(startDelim.marker); + const token_o = state.tokens[startDelim.token]; + token_o.type = isStrong ? "strong_open" : "em_open"; + token_o.tag = isStrong ? "strong" : "em"; + token_o.nesting = 1; + token_o.markup = isStrong ? ch + ch : ch; + token_o.content = ""; + const token_c = state.tokens[endDelim.token]; + token_c.type = isStrong ? "strong_close" : "em_close"; + token_c.tag = isStrong ? "strong" : "em"; + token_c.nesting = -1; + token_c.markup = isStrong ? ch + ch : ch; + token_c.content = ""; + if (isStrong) { + state.tokens[delimiters[i - 1].token].content = ""; + state.tokens[delimiters[startDelim.end + 1].token].content = ""; + i--; + } + } + } + // Walk through delimiter list and replace text tokens with tags + + function emphasis_post_process(state) { + const tokens_meta = state.tokens_meta; + const max = state.tokens_meta.length; + postProcess(state, state.delimiters); + for (let curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + postProcess(state, tokens_meta[curr].delimiters); + } + } + } + var r_emphasis = { + tokenize: emphasis_tokenize, + postProcess: emphasis_post_process + }; + // Process [link]( "stuff") + function link(state, silent) { + let code, label, res, ref; + let href = ""; + let title = ""; + let start = state.pos; + let parseReference = true; + if (state.src.charCodeAt(state.pos) !== 91 /* [ */) { + return false; + } + const oldPos = state.pos; + const max = state.posMax; + const labelStart = state.pos + 1; + const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos, true); + // parser failed to find ']', so it's not a valid link + if (labelEnd < 0) { + return false; + } + let pos = labelEnd + 1; + if (pos < max && state.src.charCodeAt(pos) === 40 /* ( */) { + // Inline link + // might have found a valid shortcut link, disable reference parsing + parseReference = false; + // [link]( "title" ) + // ^^ skipping these spaces + pos++; + for (;pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 10) { + break; + } + } + if (pos >= max) { + return false; + } + // [link]( "title" ) + // ^^^^^^ parsing link destination + start = pos; + res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax); + if (res.ok) { + href = state.md.normalizeLink(res.str); + if (state.md.validateLink(href)) { + pos = res.pos; + } else { + href = ""; + } + // [link]( "title" ) + // ^^ skipping these spaces + start = pos; + for (;pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 10) { + break; + } + } + // [link]( "title" ) + // ^^^^^^^ parsing link title + res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax); + if (pos < max && start !== pos && res.ok) { + title = res.str; + pos = res.pos; + // [link]( "title" ) + // ^^ skipping these spaces + for (;pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 10) { + break; + } + } + } + } + if (pos >= max || state.src.charCodeAt(pos) !== 41 /* ) */) { + // parsing a valid shortcut link failed, fallback to reference + parseReference = true; + } + pos++; + } + if (parseReference) { + // Link reference + if (typeof state.env.references === "undefined") { + return false; + } + if (pos < max && state.src.charCodeAt(pos) === 91 /* [ */) { + start = pos + 1; + pos = state.md.helpers.parseLinkLabel(state, pos); + if (pos >= 0) { + label = state.src.slice(start, pos++); + } else { + pos = labelEnd + 1; + } + } else { + pos = labelEnd + 1; + } + // covers label === '' and label === undefined + // (collapsed reference link and shortcut reference link respectively) + if (!label) { + label = state.src.slice(labelStart, labelEnd); + } + ref = state.env.references[normalizeReference(label)]; + if (!ref) { + state.pos = oldPos; + return false; + } + href = ref.href; + title = ref.title; + } + + // We found the end of the link, and know for a fact it's a valid link; + // so all that's left to do is to call tokenizer. + + if (!silent) { + state.pos = labelStart; + state.posMax = labelEnd; + const token_o = state.push("link_open", "a", 1); + const attrs = [ [ "href", href ] ]; + token_o.attrs = attrs; + if (title) { + attrs.push([ "title", title ]); + } + state.linkLevel++; + state.md.inline.tokenize(state); + state.linkLevel--; + state.push("link_close", "a", -1); + } + state.pos = pos; + state.posMax = max; + return true; + } + // Process ![image]( "title") + function image(state, silent) { + let code, content, label, pos, ref, res, title, start; + let href = ""; + const oldPos = state.pos; + const max = state.posMax; + if (state.src.charCodeAt(state.pos) !== 33 /* ! */) { + return false; + } + if (state.src.charCodeAt(state.pos + 1) !== 91 /* [ */) { + return false; + } + const labelStart = state.pos + 2; + const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos + 1, false); + // parser failed to find ']', so it's not a valid link + if (labelEnd < 0) { + return false; + } + pos = labelEnd + 1; + if (pos < max && state.src.charCodeAt(pos) === 40 /* ( */) { + // Inline link + // [link]( "title" ) + // ^^ skipping these spaces + pos++; + for (;pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 10) { + break; + } + } + if (pos >= max) { + return false; + } + // [link]( "title" ) + // ^^^^^^ parsing link destination + start = pos; + res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax); + if (res.ok) { + href = state.md.normalizeLink(res.str); + if (state.md.validateLink(href)) { + pos = res.pos; + } else { + href = ""; + } + } + // [link]( "title" ) + // ^^ skipping these spaces + start = pos; + for (;pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 10) { + break; + } + } + // [link]( "title" ) + // ^^^^^^^ parsing link title + res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax); + if (pos < max && start !== pos && res.ok) { + title = res.str; + pos = res.pos; + // [link]( "title" ) + // ^^ skipping these spaces + for (;pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 10) { + break; + } + } + } else { + title = ""; + } + if (pos >= max || state.src.charCodeAt(pos) !== 41 /* ) */) { + state.pos = oldPos; + return false; + } + pos++; + } else { + // Link reference + if (typeof state.env.references === "undefined") { + return false; + } + if (pos < max && state.src.charCodeAt(pos) === 91 /* [ */) { + start = pos + 1; + pos = state.md.helpers.parseLinkLabel(state, pos); + if (pos >= 0) { + label = state.src.slice(start, pos++); + } else { + pos = labelEnd + 1; + } + } else { + pos = labelEnd + 1; + } + // covers label === '' and label === undefined + // (collapsed reference link and shortcut reference link respectively) + if (!label) { + label = state.src.slice(labelStart, labelEnd); + } + ref = state.env.references[normalizeReference(label)]; + if (!ref) { + state.pos = oldPos; + return false; + } + href = ref.href; + title = ref.title; + } + + // We found the end of the link, and know for a fact it's a valid link; + // so all that's left to do is to call tokenizer. + + if (!silent) { + content = state.src.slice(labelStart, labelEnd); + const tokens = []; + state.md.inline.parse(content, state.md, state.env, tokens); + const token = state.push("image", "img", 0); + const attrs = [ [ "src", href ], [ "alt", "" ] ]; + token.attrs = attrs; + token.children = tokens; + token.content = content; + if (title) { + attrs.push([ "title", title ]); + } + } + state.pos = pos; + state.posMax = max; + return true; + } + // Process autolinks '' + /* eslint max-len:0 */ const EMAIL_RE = /^([a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*)$/; + /* eslint-disable-next-line no-control-regex */ const AUTOLINK_RE = /^([a-zA-Z][a-zA-Z0-9+.-]{1,31}):([^<>\x00-\x20]*)$/; + function autolink(state, silent) { + let pos = state.pos; + if (state.src.charCodeAt(pos) !== 60 /* < */) { + return false; + } + const start = state.pos; + const max = state.posMax; + for (;;) { + if (++pos >= max) return false; + const ch = state.src.charCodeAt(pos); + if (ch === 60 /* < */) return false; + if (ch === 62 /* > */) break; + } + const url = state.src.slice(start + 1, pos); + if (AUTOLINK_RE.test(url)) { + const fullUrl = state.md.normalizeLink(url); + if (!state.md.validateLink(fullUrl)) { + return false; + } + if (!silent) { + const token_o = state.push("link_open", "a", 1); + token_o.attrs = [ [ "href", fullUrl ] ]; + token_o.markup = "autolink"; + token_o.info = "auto"; + const token_t = state.push("text", "", 0); + token_t.content = state.md.normalizeLinkText(url); + const token_c = state.push("link_close", "a", -1); + token_c.markup = "autolink"; + token_c.info = "auto"; + } + state.pos += url.length + 2; + return true; + } + if (EMAIL_RE.test(url)) { + const fullUrl = state.md.normalizeLink("mailto:" + url); + if (!state.md.validateLink(fullUrl)) { + return false; + } + if (!silent) { + const token_o = state.push("link_open", "a", 1); + token_o.attrs = [ [ "href", fullUrl ] ]; + token_o.markup = "autolink"; + token_o.info = "auto"; + const token_t = state.push("text", "", 0); + token_t.content = state.md.normalizeLinkText(url); + const token_c = state.push("link_close", "a", -1); + token_c.markup = "autolink"; + token_c.info = "auto"; + } + state.pos += url.length + 2; + return true; + } + return false; + } + // Process html tags + function isLinkOpen(str) { + return /^\s]/i.test(str); + } + function isLinkClose(str) { + return /^<\/a\s*>/i.test(str); + } + function isLetter(ch) { + /* eslint no-bitwise:0 */ + const lc = ch | 32; + // to lower case + return lc >= 97 /* a */ && lc <= 122 /* z */; + } + function html_inline(state, silent) { + if (!state.md.options.html) { + return false; + } + // Check start + const max = state.posMax; + const pos = state.pos; + if (state.src.charCodeAt(pos) !== 60 /* < */ || pos + 2 >= max) { + return false; + } + // Quick fail on second char + const ch = state.src.charCodeAt(pos + 1); + if (ch !== 33 /* ! */ && ch !== 63 /* ? */ && ch !== 47 /* / */ && !isLetter(ch)) { + return false; + } + const match = state.src.slice(pos).match(HTML_TAG_RE); + if (!match) { + return false; + } + if (!silent) { + const token = state.push("html_inline", "", 0); + token.content = match[0]; + if (isLinkOpen(token.content)) state.linkLevel++; + if (isLinkClose(token.content)) state.linkLevel--; + } + state.pos += match[0].length; + return true; + } + // Process html entity - {, ¯, ", ... + const DIGITAL_RE = /^&#((?:x[a-f0-9]{1,6}|[0-9]{1,7}));/i; + const NAMED_RE = /^&([a-z][a-z0-9]{1,31});/i; + function entity(state, silent) { + const pos = state.pos; + const max = state.posMax; + if (state.src.charCodeAt(pos) !== 38 /* & */) return false; + if (pos + 1 >= max) return false; + const ch = state.src.charCodeAt(pos + 1); + if (ch === 35 /* # */) { + const match = state.src.slice(pos).match(DIGITAL_RE); + if (match) { + if (!silent) { + const code = match[1][0].toLowerCase() === "x" ? parseInt(match[1].slice(1), 16) : parseInt(match[1], 10); + const token = state.push("text_special", "", 0); + token.content = isValidEntityCode(code) ? fromCodePoint(code) : fromCodePoint(65533); + token.markup = match[0]; + token.info = "entity"; + } + state.pos += match[0].length; + return true; + } + } else { + const match = state.src.slice(pos).match(NAMED_RE); + if (match) { + const decoded = decodeHTML(match[0]); + if (decoded !== match[0]) { + if (!silent) { + const token = state.push("text_special", "", 0); + token.content = decoded; + token.markup = match[0]; + token.info = "entity"; + } + state.pos += match[0].length; + return true; + } + } + } + return false; + } + // For each opening emphasis-like marker find a matching closing one + + function processDelimiters(delimiters) { + const openersBottom = {}; + const max = delimiters.length; + if (!max) return; + // headerIdx is the first delimiter of the current (where closer is) delimiter run + let headerIdx = 0; + let lastTokenIdx = -2; + // needs any value lower than -1 + const jumps = []; + for (let closerIdx = 0; closerIdx < max; closerIdx++) { + const closer = delimiters[closerIdx]; + jumps.push(0); + // markers belong to same delimiter run if: + // - they have adjacent tokens + // - AND markers are the same + + if (delimiters[headerIdx].marker !== closer.marker || lastTokenIdx !== closer.token - 1) { + headerIdx = closerIdx; + } + lastTokenIdx = closer.token; + // Length is only used for emphasis-specific "rule of 3", + // if it's not defined (in strikethrough or 3rd party plugins), + // we can default it to 0 to disable those checks. + + closer.length = closer.length || 0; + if (!closer.close) continue; + // Previously calculated lower bounds (previous fails) + // for each marker, each delimiter length modulo 3, + // and for whether this closer can be an opener; + // https://github.com/commonmark/cmark/commit/34250e12ccebdc6372b8b49c44fab57c72443460 + /* eslint-disable-next-line no-prototype-builtins */ if (!openersBottom.hasOwnProperty(closer.marker)) { + openersBottom[closer.marker] = [ -1, -1, -1, -1, -1, -1 ]; + } + const minOpenerIdx = openersBottom[closer.marker][(closer.open ? 3 : 0) + closer.length % 3]; + let openerIdx = headerIdx - jumps[headerIdx] - 1; + let newMinOpenerIdx = openerIdx; + for (;openerIdx > minOpenerIdx; openerIdx -= jumps[openerIdx] + 1) { + const opener = delimiters[openerIdx]; + if (opener.marker !== closer.marker) continue; + if (opener.open && opener.end < 0) { + let isOddMatch = false; + // from spec: + + // If one of the delimiters can both open and close emphasis, then the + // sum of the lengths of the delimiter runs containing the opening and + // closing delimiters must not be a multiple of 3 unless both lengths + // are multiples of 3. + + if (opener.close || closer.open) { + if ((opener.length + closer.length) % 3 === 0) { + if (opener.length % 3 !== 0 || closer.length % 3 !== 0) { + isOddMatch = true; + } + } + } + if (!isOddMatch) { + // If previous delimiter cannot be an opener, we can safely skip + // the entire sequence in future checks. This is required to make + // sure algorithm has linear complexity (see *_*_*_*_*_... case). + const lastJump = openerIdx > 0 && !delimiters[openerIdx - 1].open ? jumps[openerIdx - 1] + 1 : 0; + jumps[closerIdx] = closerIdx - openerIdx + lastJump; + jumps[openerIdx] = lastJump; + closer.open = false; + opener.end = closerIdx; + opener.close = false; + newMinOpenerIdx = -1; + // treat next token as start of run, + // it optimizes skips in **<...>**a**<...>** pathological case + lastTokenIdx = -2; + break; + } + } + } + if (newMinOpenerIdx !== -1) { + // If match for this delimiter run failed, we want to set lower bound for + // future lookups. This is required to make sure algorithm has linear + // complexity. + // See details here: + // https://github.com/commonmark/cmark/issues/178#issuecomment-270417442 + openersBottom[closer.marker][(closer.open ? 3 : 0) + (closer.length || 0) % 3] = newMinOpenerIdx; + } + } + } + function link_pairs(state) { + const tokens_meta = state.tokens_meta; + const max = state.tokens_meta.length; + processDelimiters(state.delimiters); + for (let curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + processDelimiters(tokens_meta[curr].delimiters); + } + } + } + // Clean up tokens after emphasis and strikethrough postprocessing: + // merge adjacent text nodes into one and re-calculate all token levels + + // This is necessary because initially emphasis delimiter markers (*, _, ~) + // are treated as their own separate text tokens. Then emphasis rule either + // leaves them as text (needed to merge with adjacent text) or turns them + // into opening/closing tags (which messes up levels inside). + + function fragments_join(state) { + let curr, last; + let level = 0; + const tokens = state.tokens; + const max = state.tokens.length; + for (curr = last = 0; curr < max; curr++) { + // re-calculate levels after emphasis/strikethrough turns some text nodes + // into opening/closing tags + if (tokens[curr].nesting < 0) level--; + // closing tag + tokens[curr].level = level; + if (tokens[curr].nesting > 0) level++; + // opening tag + if (tokens[curr].type === "text" && curr + 1 < max && tokens[curr + 1].type === "text") { + // collapse two adjacent text nodes + tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content; + } else { + if (curr !== last) { + tokens[last] = tokens[curr]; + } + last++; + } + } + if (curr !== last) { + tokens.length = last; + } + } + /** internal + * class ParserInline + * + * Tokenizes paragraph content. + **/ + // Parser rules + const _rules = [ [ "text", text ], [ "linkify", linkify ], [ "newline", newline ], [ "escape", escape ], [ "backticks", backtick ], [ "strikethrough", r_strikethrough.tokenize ], [ "emphasis", r_emphasis.tokenize ], [ "link", link ], [ "image", image ], [ "autolink", autolink ], [ "html_inline", html_inline ], [ "entity", entity ] ]; + // `rule2` ruleset was created specifically for emphasis/strikethrough + // post-processing and may be changed in the future. + + // Don't use this for anything except pairs (plugins working with `balance_pairs`). + + const _rules2 = [ [ "balance_pairs", link_pairs ], [ "strikethrough", r_strikethrough.postProcess ], [ "emphasis", r_emphasis.postProcess ], + // rules for pairs separate '**' into its own text tokens, which may be left unused, + // rule below merges unused segments back with the rest of the text + [ "fragments_join", fragments_join ] ]; + /** + * new ParserInline() + **/ function ParserInline() { + /** + * ParserInline#ruler -> Ruler + * + * [[Ruler]] instance. Keep configuration of inline rules. + **/ + this.ruler = new Ruler; + for (let i = 0; i < _rules.length; i++) { + this.ruler.push(_rules[i][0], _rules[i][1]); + } + /** + * ParserInline#ruler2 -> Ruler + * + * [[Ruler]] instance. Second ruler used for post-processing + * (e.g. in emphasis-like rules). + **/ this.ruler2 = new Ruler; + for (let i = 0; i < _rules2.length; i++) { + this.ruler2.push(_rules2[i][0], _rules2[i][1]); + } + } + // Skip single token by running all rules in validation mode; + // returns `true` if any rule reported success + + ParserInline.prototype.skipToken = function(state) { + const pos = state.pos; + const rules = this.ruler.getRules(""); + const len = rules.length; + const maxNesting = state.md.options.maxNesting; + const cache = state.cache; + if (typeof cache[pos] !== "undefined") { + state.pos = cache[pos]; + return; + } + let ok = false; + if (state.level < maxNesting) { + for (let i = 0; i < len; i++) { + // Increment state.level and decrement it later to limit recursion. + // It's harmless to do here, because no tokens are created. But ideally, + // we'd need a separate private state variable for this purpose. + state.level++; + ok = rules[i](state, true); + state.level--; + if (ok) { + if (pos >= state.pos) { + throw new Error("inline rule didn't increment state.pos"); + } + break; + } + } + } else { + // Too much nesting, just skip until the end of the paragraph. + // NOTE: this will cause links to behave incorrectly in the following case, + // when an amount of `[` is exactly equal to `maxNesting + 1`: + // [[[[[[[[[[[[[[[[[[[[[foo]() + // TODO: remove this workaround when CM standard will allow nested links + // (we can replace it by preventing links from being parsed in + // validation mode) + state.pos = state.posMax; + } + if (!ok) { + state.pos++; + } + cache[pos] = state.pos; + }; + // Generate tokens for input range + + ParserInline.prototype.tokenize = function(state) { + const rules = this.ruler.getRules(""); + const len = rules.length; + const end = state.posMax; + const maxNesting = state.md.options.maxNesting; + while (state.pos < end) { + // Try all possible rules. + // On success, rule should: + // - update `state.pos` + // - update `state.tokens` + // - return true + const prevPos = state.pos; + let ok = false; + if (state.level < maxNesting) { + for (let i = 0; i < len; i++) { + ok = rules[i](state, false); + if (ok) { + if (prevPos >= state.pos) { + throw new Error("inline rule didn't increment state.pos"); + } + break; + } + } + } + if (ok) { + if (state.pos >= end) { + break; + } + continue; + } + state.pending += state.src[state.pos++]; + } + if (state.pending) { + state.pushPending(); + } + }; + /** + * ParserInline.parse(str, md, env, outTokens) + * + * Process input string and push inline tokens into `outTokens` + **/ ParserInline.prototype.parse = function(str, md, env, outTokens) { + const state = new this.State(str, md, env, outTokens); + this.tokenize(state); + const rules = this.ruler2.getRules(""); + const len = rules.length; + for (let i = 0; i < len; i++) { + rules[i](state); + } + }; + ParserInline.prototype.State = StateInline; + function reFactory(opts) { + const re = {}; + opts = opts || {}; + re.src_Any = Any.source; + re.src_Cc = Cc.source; + re.src_Z = Z.source; + re.src_P = P.source; + // \p{\Z\P\Cc\CF} (white spaces + control + format + punctuation) + re.src_ZPCc = [ re.src_Z, re.src_P, re.src_Cc ].join("|"); + // \p{\Z\Cc} (white spaces + control) + re.src_ZCc = [ re.src_Z, re.src_Cc ].join("|"); + // Experimental. List of chars, completely prohibited in links + // because can separate it from other part of text + const text_separators = "[><\uff5c]"; + // All possible word characters (everything without punctuation, spaces & controls) + // Defined via punctuation & spaces to save space + // Should be something like \p{\L\N\S\M} (\w but without `_`) + re.src_pseudo_letter = "(?:(?!" + text_separators + "|" + re.src_ZPCc + ")" + re.src_Any + ")"; + // The same as abothe but without [0-9] + // var src_pseudo_letter_non_d = '(?:(?![0-9]|' + src_ZPCc + ')' + src_Any + ')'; + re.src_ip4 = "(?:(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)"; + // Prohibit any of "@/[]()" in user/pass to avoid wrong domain fetch. + re.src_auth = "(?:(?:(?!" + re.src_ZCc + "|[@/\\[\\]()]).)+@)?"; + re.src_port = "(?::(?:6(?:[0-4]\\d{3}|5(?:[0-4]\\d{2}|5(?:[0-2]\\d|3[0-5])))|[1-5]?\\d{1,4}))?"; + re.src_host_terminator = "(?=$|" + text_separators + "|" + re.src_ZPCc + ")" + "(?!" + (opts["---"] ? "-(?!--)|" : "-|") + "_|:\\d|\\.-|\\.(?!$|" + re.src_ZPCc + "))"; + re.src_path = "(?:" + "[/?#]" + "(?:" + "(?!" + re.src_ZCc + "|" + text_separators + "|[()[\\]{}.,\"'?!\\-;]).|" + "\\[(?:(?!" + re.src_ZCc + "|\\]).)*\\]|" + "\\((?:(?!" + re.src_ZCc + "|[)]).)*\\)|" + "\\{(?:(?!" + re.src_ZCc + "|[}]).)*\\}|" + '\\"(?:(?!' + re.src_ZCc + '|["]).)+\\"|' + "\\'(?:(?!" + re.src_ZCc + "|[']).)+\\'|" + + // allow `I'm_king` if no pair found + "\\'(?=" + re.src_pseudo_letter + "|[-])|" + + // google has many dots in "google search" links (#66, #81). + // github has ... in commit range links, + // Restrict to + // - english + // - percent-encoded + // - parts of file path + // - params separator + // until more examples found. + "\\.{2,}[a-zA-Z0-9%/&]|" + "\\.(?!" + re.src_ZCc + "|[.]|$)|" + (opts["---"] ? "\\-(?!--(?:[^-]|$))(?:-*)|" : "\\-+|") + + // allow `,,,` in paths + ",(?!" + re.src_ZCc + "|$)|" + + // allow `;` if not followed by space-like char + ";(?!" + re.src_ZCc + "|$)|" + + // allow `!!!` in paths, but not at the end + "\\!+(?!" + re.src_ZCc + "|[!]|$)|" + "\\?(?!" + re.src_ZCc + "|[?]|$)" + ")+" + "|\\/" + ")?"; + // Allow anything in markdown spec, forbid quote (") at the first position + // because emails enclosed in quotes are far more common + re.src_email_name = '[\\-;:&=\\+\\$,\\.a-zA-Z0-9_][\\-;:&=\\+\\$,\\"\\.a-zA-Z0-9_]*'; + re.src_xn = "xn--[a-z0-9\\-]{1,59}"; + // More to read about domain names + // http://serverfault.com/questions/638260/ + re.src_domain_root = + // Allow letters & digits (http://test1) + "(?:" + re.src_xn + "|" + re.src_pseudo_letter + "{1,63}" + ")"; + re.src_domain = "(?:" + re.src_xn + "|" + "(?:" + re.src_pseudo_letter + ")" + "|" + "(?:" + re.src_pseudo_letter + "(?:-|" + re.src_pseudo_letter + "){0,61}" + re.src_pseudo_letter + ")" + ")"; + re.src_host = "(?:" + + // Don't need IP check, because digits are already allowed in normal domain names + // src_ip4 + + // '|' + + "(?:(?:(?:" + re.src_domain + ")\\.)*" + re.src_domain /* _root */ + ")" + ")"; + re.tpl_host_fuzzy = "(?:" + re.src_ip4 + "|" + "(?:(?:(?:" + re.src_domain + ")\\.)+(?:%TLDS%))" + ")"; + re.tpl_host_no_ip_fuzzy = "(?:(?:(?:" + re.src_domain + ")\\.)+(?:%TLDS%))"; + re.src_host_strict = re.src_host + re.src_host_terminator; + re.tpl_host_fuzzy_strict = re.tpl_host_fuzzy + re.src_host_terminator; + re.src_host_port_strict = re.src_host + re.src_port + re.src_host_terminator; + re.tpl_host_port_fuzzy_strict = re.tpl_host_fuzzy + re.src_port + re.src_host_terminator; + re.tpl_host_port_no_ip_fuzzy_strict = re.tpl_host_no_ip_fuzzy + re.src_port + re.src_host_terminator; + + // Main rules + + // Rude test fuzzy links by host, for quick deny + re.tpl_host_fuzzy_test = "localhost|www\\.|\\.\\d{1,3}\\.|(?:\\.(?:%TLDS%)(?:" + re.src_ZPCc + "|>|$))"; + re.tpl_email_fuzzy = "(^|" + text_separators + '|"|\\(|' + re.src_ZCc + ")" + "(" + re.src_email_name + "@" + re.tpl_host_fuzzy_strict + ")"; + re.tpl_link_fuzzy = + // Fuzzy link can't be prepended with .:/\- and non punctuation. + // but can start with > (markdown blockquote) + "(^|(?![.:/\\-_@])(?:[$+<=>^`|\uff5c]|" + re.src_ZPCc + "))" + "((?![$+<=>^`|\uff5c])" + re.tpl_host_port_fuzzy_strict + re.src_path + ")"; + re.tpl_link_no_ip_fuzzy = + // Fuzzy link can't be prepended with .:/\- and non punctuation. + // but can start with > (markdown blockquote) + "(^|(?![.:/\\-_@])(?:[$+<=>^`|\uff5c]|" + re.src_ZPCc + "))" + "((?![$+<=>^`|\uff5c])" + re.tpl_host_port_no_ip_fuzzy_strict + re.src_path + ")"; + return re; + } + + // Helpers + + // Merge objects + + function assign(obj /* from1, from2, from3, ... */) { + const sources = Array.prototype.slice.call(arguments, 1); + sources.forEach((function(source) { + if (!source) { + return; + } + Object.keys(source).forEach((function(key) { + obj[key] = source[key]; + })); + })); + return obj; + } + function _class(obj) { + return Object.prototype.toString.call(obj); + } + function isString(obj) { + return _class(obj) === "[object String]"; + } + function isObject(obj) { + return _class(obj) === "[object Object]"; + } + function isRegExp(obj) { + return _class(obj) === "[object RegExp]"; + } + function isFunction(obj) { + return _class(obj) === "[object Function]"; + } + function escapeRE(str) { + return str.replace(/[.?*+^$[\]\\(){}|-]/g, "\\$&"); + } + + const defaultOptions = { + fuzzyLink: true, + fuzzyEmail: true, + fuzzyIP: false + }; + function isOptionsObj(obj) { + return Object.keys(obj || {}).reduce((function(acc, k) { + /* eslint-disable-next-line no-prototype-builtins */ + return acc || defaultOptions.hasOwnProperty(k); + }), false); + } + const defaultSchemas = { + "http:": { + validate: function(text, pos, self) { + const tail = text.slice(pos); + if (!self.re.http) { + // compile lazily, because "host"-containing variables can change on tlds update. + self.re.http = new RegExp("^\\/\\/" + self.re.src_auth + self.re.src_host_port_strict + self.re.src_path, "i"); + } + if (self.re.http.test(tail)) { + return tail.match(self.re.http)[0].length; + } + return 0; + } + }, + "https:": "http:", + "ftp:": "http:", + "//": { + validate: function(text, pos, self) { + const tail = text.slice(pos); + if (!self.re.no_http) { + // compile lazily, because "host"-containing variables can change on tlds update. + self.re.no_http = new RegExp("^" + self.re.src_auth + + // Don't allow single-level domains, because of false positives like '//test' + // with code comments + "(?:localhost|(?:(?:" + self.re.src_domain + ")\\.)+" + self.re.src_domain_root + ")" + self.re.src_port + self.re.src_host_terminator + self.re.src_path, "i"); + } + if (self.re.no_http.test(tail)) { + // should not be `://` & `///`, that protects from errors in protocol name + if (pos >= 3 && text[pos - 3] === ":") { + return 0; + } + if (pos >= 3 && text[pos - 3] === "/") { + return 0; + } + return tail.match(self.re.no_http)[0].length; + } + return 0; + } + }, + "mailto:": { + validate: function(text, pos, self) { + const tail = text.slice(pos); + if (!self.re.mailto) { + self.re.mailto = new RegExp("^" + self.re.src_email_name + "@" + self.re.src_host_strict, "i"); + } + if (self.re.mailto.test(tail)) { + return tail.match(self.re.mailto)[0].length; + } + return 0; + } + } + }; + // RE pattern for 2-character tlds (autogenerated by ./support/tlds_2char_gen.js) + /* eslint-disable-next-line max-len */ const tlds_2ch_src_re = "a[cdefgilmnoqrstuwxz]|b[abdefghijmnorstvwyz]|c[acdfghiklmnoruvwxyz]|d[ejkmoz]|e[cegrstu]|f[ijkmor]|g[abdefghilmnpqrstuwy]|h[kmnrtu]|i[delmnoqrst]|j[emop]|k[eghimnprwyz]|l[abcikrstuvy]|m[acdeghklmnopqrstuvwxyz]|n[acefgilopruz]|om|p[aefghklmnrstwy]|qa|r[eosuw]|s[abcdeghijklmnortuvxyz]|t[cdfghjklmnortvwz]|u[agksyz]|v[aceginu]|w[fs]|y[et]|z[amw]"; + // DON'T try to make PRs with changes. Extend TLDs with LinkifyIt.tlds() instead + const tlds_default = "biz|com|edu|gov|net|org|pro|web|xxx|aero|asia|coop|info|museum|name|shop|\u0440\u0444".split("|"); + function resetScanCache(self) { + self.__index__ = -1; + self.__text_cache__ = ""; + } + function createValidator(re) { + return function(text, pos) { + const tail = text.slice(pos); + if (re.test(tail)) { + return tail.match(re)[0].length; + } + return 0; + }; + } + function createNormalizer() { + return function(match, self) { + self.normalize(match); + }; + } + // Schemas compiler. Build regexps. + + function compile(self) { + // Load & clone RE patterns. + const re = self.re = reFactory(self.__opts__); + // Define dynamic patterns + const tlds = self.__tlds__.slice(); + self.onCompile(); + if (!self.__tlds_replaced__) { + tlds.push(tlds_2ch_src_re); + } + tlds.push(re.src_xn); + re.src_tlds = tlds.join("|"); + function untpl(tpl) { + return tpl.replace("%TLDS%", re.src_tlds); + } + re.email_fuzzy = RegExp(untpl(re.tpl_email_fuzzy), "i"); + re.link_fuzzy = RegExp(untpl(re.tpl_link_fuzzy), "i"); + re.link_no_ip_fuzzy = RegExp(untpl(re.tpl_link_no_ip_fuzzy), "i"); + re.host_fuzzy_test = RegExp(untpl(re.tpl_host_fuzzy_test), "i"); + + // Compile each schema + + const aliases = []; + self.__compiled__ = {}; + // Reset compiled data + function schemaError(name, val) { + throw new Error('(LinkifyIt) Invalid schema "' + name + '": ' + val); + } + Object.keys(self.__schemas__).forEach((function(name) { + const val = self.__schemas__[name]; + // skip disabled methods + if (val === null) { + return; + } + const compiled = { + validate: null, + link: null + }; + self.__compiled__[name] = compiled; + if (isObject(val)) { + if (isRegExp(val.validate)) { + compiled.validate = createValidator(val.validate); + } else if (isFunction(val.validate)) { + compiled.validate = val.validate; + } else { + schemaError(name, val); + } + if (isFunction(val.normalize)) { + compiled.normalize = val.normalize; + } else if (!val.normalize) { + compiled.normalize = createNormalizer(); + } else { + schemaError(name, val); + } + return; + } + if (isString(val)) { + aliases.push(name); + return; + } + schemaError(name, val); + })); + + // Compile postponed aliases + + aliases.forEach((function(alias) { + if (!self.__compiled__[self.__schemas__[alias]]) { + // Silently fail on missed schemas to avoid errons on disable. + // schemaError(alias, self.__schemas__[alias]); + return; + } + self.__compiled__[alias].validate = self.__compiled__[self.__schemas__[alias]].validate; + self.__compiled__[alias].normalize = self.__compiled__[self.__schemas__[alias]].normalize; + })); + + // Fake record for guessed links + + self.__compiled__[""] = { + validate: null, + normalize: createNormalizer() + }; + + // Build schema condition + + const slist = Object.keys(self.__compiled__).filter((function(name) { + // Filter disabled & fake schemas + return name.length > 0 && self.__compiled__[name]; + })).map(escapeRE).join("|"); + // (?!_) cause 1.5x slowdown + self.re.schema_test = RegExp("(^|(?!_)(?:[><\uff5c]|" + re.src_ZPCc + "))(" + slist + ")", "i"); + self.re.schema_search = RegExp("(^|(?!_)(?:[><\uff5c]|" + re.src_ZPCc + "))(" + slist + ")", "ig"); + self.re.schema_at_start = RegExp("^" + self.re.schema_search.source, "i"); + self.re.pretest = RegExp("(" + self.re.schema_test.source + ")|(" + self.re.host_fuzzy_test.source + ")|@", "i"); + + // Cleanup + + resetScanCache(self); + } + /** + * class Match + * + * Match result. Single element of array, returned by [[LinkifyIt#match]] + **/ function Match(self, shift) { + const start = self.__index__; + const end = self.__last_index__; + const text = self.__text_cache__.slice(start, end); + /** + * Match#schema -> String + * + * Prefix (protocol) for matched string. + **/ this.schema = self.__schema__.toLowerCase(); + /** + * Match#index -> Number + * + * First position of matched string. + **/ this.index = start + shift; + /** + * Match#lastIndex -> Number + * + * Next position after matched string. + **/ this.lastIndex = end + shift; + /** + * Match#raw -> String + * + * Matched string. + **/ this.raw = text; + /** + * Match#text -> String + * + * Notmalized text of matched string. + **/ this.text = text; + /** + * Match#url -> String + * + * Normalized url of matched string. + **/ this.url = text; + } + function createMatch(self, shift) { + const match = new Match(self, shift); + self.__compiled__[match.schema].normalize(match, self); + return match; + } + /** + * class LinkifyIt + **/ + /** + * new LinkifyIt(schemas, options) + * - schemas (Object): Optional. Additional schemas to validate (prefix/validator) + * - options (Object): { fuzzyLink|fuzzyEmail|fuzzyIP: true|false } + * + * Creates new linkifier instance with optional additional schemas. + * Can be called without `new` keyword for convenience. + * + * By default understands: + * + * - `http(s)://...` , `ftp://...`, `mailto:...` & `//...` links + * - "fuzzy" links and emails (example.com, foo@bar.com). + * + * `schemas` is an object, where each key/value describes protocol/rule: + * + * - __key__ - link prefix (usually, protocol name with `:` at the end, `skype:` + * for example). `linkify-it` makes shure that prefix is not preceeded with + * alphanumeric char and symbols. Only whitespaces and punctuation allowed. + * - __value__ - rule to check tail after link prefix + * - _String_ - just alias to existing rule + * - _Object_ + * - _validate_ - validator function (should return matched length on success), + * or `RegExp`. + * - _normalize_ - optional function to normalize text & url of matched result + * (for example, for @twitter mentions). + * + * `options`: + * + * - __fuzzyLink__ - recognige URL-s without `http(s):` prefix. Default `true`. + * - __fuzzyIP__ - allow IPs in fuzzy links above. Can conflict with some texts + * like version numbers. Default `false`. + * - __fuzzyEmail__ - recognize emails without `mailto:` prefix. + * + **/ function LinkifyIt(schemas, options) { + if (!(this instanceof LinkifyIt)) { + return new LinkifyIt(schemas, options); + } + if (!options) { + if (isOptionsObj(schemas)) { + options = schemas; + schemas = {}; + } + } + this.__opts__ = assign({}, defaultOptions, options); + // Cache last tested result. Used to skip repeating steps on next `match` call. + this.__index__ = -1; + this.__last_index__ = -1; + // Next scan position + this.__schema__ = ""; + this.__text_cache__ = ""; + this.__schemas__ = assign({}, defaultSchemas, schemas); + this.__compiled__ = {}; + this.__tlds__ = tlds_default; + this.__tlds_replaced__ = false; + this.re = {}; + compile(this); + } + /** chainable + * LinkifyIt#add(schema, definition) + * - schema (String): rule name (fixed pattern prefix) + * - definition (String|RegExp|Object): schema definition + * + * Add new rule definition. See constructor description for details. + **/ LinkifyIt.prototype.add = function add(schema, definition) { + this.__schemas__[schema] = definition; + compile(this); + return this; + }; + /** chainable + * LinkifyIt#set(options) + * - options (Object): { fuzzyLink|fuzzyEmail|fuzzyIP: true|false } + * + * Set recognition options for links without schema. + **/ LinkifyIt.prototype.set = function set(options) { + this.__opts__ = assign(this.__opts__, options); + return this; + }; + /** + * LinkifyIt#test(text) -> Boolean + * + * Searches linkifiable pattern and returns `true` on success or `false` on fail. + **/ LinkifyIt.prototype.test = function test(text) { + // Reset scan cache + this.__text_cache__ = text; + this.__index__ = -1; + if (!text.length) { + return false; + } + let m, ml, me, len, shift, next, re, tld_pos, at_pos; + // try to scan for link with schema - that's the most simple rule + if (this.re.schema_test.test(text)) { + re = this.re.schema_search; + re.lastIndex = 0; + while ((m = re.exec(text)) !== null) { + len = this.testSchemaAt(text, m[2], re.lastIndex); + if (len) { + this.__schema__ = m[2]; + this.__index__ = m.index + m[1].length; + this.__last_index__ = m.index + m[0].length + len; + break; + } + } + } + if (this.__opts__.fuzzyLink && this.__compiled__["http:"]) { + // guess schemaless links + tld_pos = text.search(this.re.host_fuzzy_test); + if (tld_pos >= 0) { + // if tld is located after found link - no need to check fuzzy pattern + if (this.__index__ < 0 || tld_pos < this.__index__) { + if ((ml = text.match(this.__opts__.fuzzyIP ? this.re.link_fuzzy : this.re.link_no_ip_fuzzy)) !== null) { + shift = ml.index + ml[1].length; + if (this.__index__ < 0 || shift < this.__index__) { + this.__schema__ = ""; + this.__index__ = shift; + this.__last_index__ = ml.index + ml[0].length; + } + } + } + } + } + if (this.__opts__.fuzzyEmail && this.__compiled__["mailto:"]) { + // guess schemaless emails + at_pos = text.indexOf("@"); + if (at_pos >= 0) { + // We can't skip this check, because this cases are possible: + // 192.168.1.1@gmail.com, my.in@example.com + if ((me = text.match(this.re.email_fuzzy)) !== null) { + shift = me.index + me[1].length; + next = me.index + me[0].length; + if (this.__index__ < 0 || shift < this.__index__ || shift === this.__index__ && next > this.__last_index__) { + this.__schema__ = "mailto:"; + this.__index__ = shift; + this.__last_index__ = next; + } + } + } + } + return this.__index__ >= 0; + }; + /** + * LinkifyIt#pretest(text) -> Boolean + * + * Very quick check, that can give false positives. Returns true if link MAY BE + * can exists. Can be used for speed optimization, when you need to check that + * link NOT exists. + **/ LinkifyIt.prototype.pretest = function pretest(text) { + return this.re.pretest.test(text); + }; + /** + * LinkifyIt#testSchemaAt(text, name, position) -> Number + * - text (String): text to scan + * - name (String): rule (schema) name + * - position (Number): text offset to check from + * + * Similar to [[LinkifyIt#test]] but checks only specific protocol tail exactly + * at given position. Returns length of found pattern (0 on fail). + **/ LinkifyIt.prototype.testSchemaAt = function testSchemaAt(text, schema, pos) { + // If not supported schema check requested - terminate + if (!this.__compiled__[schema.toLowerCase()]) { + return 0; + } + return this.__compiled__[schema.toLowerCase()].validate(text, pos, this); + }; + /** + * LinkifyIt#match(text) -> Array|null + * + * Returns array of found link descriptions or `null` on fail. We strongly + * recommend to use [[LinkifyIt#test]] first, for best speed. + * + * ##### Result match description + * + * - __schema__ - link schema, can be empty for fuzzy links, or `//` for + * protocol-neutral links. + * - __index__ - offset of matched text + * - __lastIndex__ - index of next char after mathch end + * - __raw__ - matched text + * - __text__ - normalized text + * - __url__ - link, generated from matched text + **/ LinkifyIt.prototype.match = function match(text) { + const result = []; + let shift = 0; + // Try to take previous element from cache, if .test() called before + if (this.__index__ >= 0 && this.__text_cache__ === text) { + result.push(createMatch(this, shift)); + shift = this.__last_index__; + } + // Cut head if cache was used + let tail = shift ? text.slice(shift) : text; + // Scan string until end reached + while (this.test(tail)) { + result.push(createMatch(this, shift)); + tail = tail.slice(this.__last_index__); + shift += this.__last_index__; + } + if (result.length) { + return result; + } + return null; + }; + /** + * LinkifyIt#matchAtStart(text) -> Match|null + * + * Returns fully-formed (not fuzzy) link if it starts at the beginning + * of the string, and null otherwise. + **/ LinkifyIt.prototype.matchAtStart = function matchAtStart(text) { + // Reset scan cache + this.__text_cache__ = text; + this.__index__ = -1; + if (!text.length) return null; + const m = this.re.schema_at_start.exec(text); + if (!m) return null; + const len = this.testSchemaAt(text, m[2], m[0].length); + if (!len) return null; + this.__schema__ = m[2]; + this.__index__ = m.index + m[1].length; + this.__last_index__ = m.index + m[0].length + len; + return createMatch(this, 0); + }; + /** chainable + * LinkifyIt#tlds(list [, keepOld]) -> this + * - list (Array): list of tlds + * - keepOld (Boolean): merge with current list if `true` (`false` by default) + * + * Load (or merge) new tlds list. Those are user for fuzzy links (without prefix) + * to avoid false positives. By default this algorythm used: + * + * - hostname with any 2-letter root zones are ok. + * - biz|com|edu|gov|net|org|pro|web|xxx|aero|asia|coop|info|museum|name|shop|рф + * are ok. + * - encoded (`xn--...`) root zones are ok. + * + * If list is replaced, then exact match for 2-chars root zones will be checked. + **/ LinkifyIt.prototype.tlds = function tlds(list, keepOld) { + list = Array.isArray(list) ? list : [ list ]; + if (!keepOld) { + this.__tlds__ = list.slice(); + this.__tlds_replaced__ = true; + compile(this); + return this; + } + this.__tlds__ = this.__tlds__.concat(list).sort().filter((function(el, idx, arr) { + return el !== arr[idx - 1]; + })).reverse(); + compile(this); + return this; + }; + /** + * LinkifyIt#normalize(match) + * + * Default normalizer (if schema does not define it's own). + **/ LinkifyIt.prototype.normalize = function normalize(match) { + // Do minimal possible changes by default. Need to collect feedback prior + // to move forward https://github.com/markdown-it/linkify-it/issues/1 + if (!match.schema) { + match.url = "http://" + match.url; + } + if (match.schema === "mailto:" && !/^mailto:/i.test(match.url)) { + match.url = "mailto:" + match.url; + } + }; + /** + * LinkifyIt#onCompile() + * + * Override to modify basic RegExp-s. + **/ LinkifyIt.prototype.onCompile = function onCompile() {}; + /** Highest positive signed 32-bit float value */ const maxInt = 2147483647; + // aka. 0x7FFFFFFF or 2^31-1 + /** Bootstring parameters */ const base = 36; + const tMin = 1; + const tMax = 26; + const skew = 38; + const damp = 700; + const initialBias = 72; + const initialN = 128; + // 0x80 + const delimiter = "-"; + // '\x2D' + /** Regular expressions */ const regexPunycode = /^xn--/; + const regexNonASCII = /[^\0-\x7F]/; + // Note: U+007F DEL is excluded too. + const regexSeparators = /[\x2E\u3002\uFF0E\uFF61]/g; + // RFC 3490 separators + /** Error messages */ const errors = { + overflow: "Overflow: input needs wider integers to process", + "not-basic": "Illegal input >= 0x80 (not a basic code point)", + "invalid-input": "Invalid input" + }; + /** Convenience shortcuts */ const baseMinusTMin = base - tMin; + const floor = Math.floor; + const stringFromCharCode = String.fromCharCode; + /*--------------------------------------------------------------------------*/ + /** + * A generic error utility function. + * @private + * @param {String} type The error type. + * @returns {Error} Throws a `RangeError` with the applicable error message. + */ function error(type) { + throw new RangeError(errors[type]); + } + /** + * A generic `Array#map` utility function. + * @private + * @param {Array} array The array to iterate over. + * @param {Function} callback The function that gets called for every array + * item. + * @returns {Array} A new array of values returned by the callback function. + */ function map(array, callback) { + const result = []; + let length = array.length; + while (length--) { + result[length] = callback(array[length]); + } + return result; + } + /** + * A simple `Array#map`-like wrapper to work with domain name strings or email + * addresses. + * @private + * @param {String} domain The domain name or email address. + * @param {Function} callback The function that gets called for every + * character. + * @returns {String} A new string of characters returned by the callback + * function. + */ function mapDomain(domain, callback) { + const parts = domain.split("@"); + let result = ""; + if (parts.length > 1) { + // In email addresses, only the domain name should be punycoded. Leave + // the local part (i.e. everything up to `@`) intact. + result = parts[0] + "@"; + domain = parts[1]; + } + // Avoid `split(regex)` for IE8 compatibility. See #17. + domain = domain.replace(regexSeparators, "."); + const labels = domain.split("."); + const encoded = map(labels, callback).join("."); + return result + encoded; + } + /** + * Creates an array containing the numeric code points of each Unicode + * character in the string. While JavaScript uses UCS-2 internally, + * this function will convert a pair of surrogate halves (each of which + * UCS-2 exposes as separate characters) into a single code point, + * matching UTF-16. + * @see `punycode.ucs2.encode` + * @see + * @memberOf punycode.ucs2 + * @name decode + * @param {String} string The Unicode input string (UCS-2). + * @returns {Array} The new array of code points. + */ function ucs2decode(string) { + const output = []; + let counter = 0; + const length = string.length; + while (counter < length) { + const value = string.charCodeAt(counter++); + if (value >= 55296 && value <= 56319 && counter < length) { + // It's a high surrogate, and there is a next character. + const extra = string.charCodeAt(counter++); + if ((extra & 64512) == 56320) { + // Low surrogate. + output.push(((value & 1023) << 10) + (extra & 1023) + 65536); + } else { + // It's an unmatched surrogate; only append this code unit, in case the + // next code unit is the high surrogate of a surrogate pair. + output.push(value); + counter--; + } + } else { + output.push(value); + } + } + return output; + } + /** + * Creates a string based on an array of numeric code points. + * @see `punycode.ucs2.decode` + * @memberOf punycode.ucs2 + * @name encode + * @param {Array} codePoints The array of numeric code points. + * @returns {String} The new Unicode string (UCS-2). + */ const ucs2encode = codePoints => String.fromCodePoint(...codePoints) + /** + * Converts a basic code point into a digit/integer. + * @see `digitToBasic()` + * @private + * @param {Number} codePoint The basic numeric code point value. + * @returns {Number} The numeric value of a basic code point (for use in + * representing integers) in the range `0` to `base - 1`, or `base` if + * the code point does not represent a value. + */; + const basicToDigit = function(codePoint) { + if (codePoint >= 48 && codePoint < 58) { + return 26 + (codePoint - 48); + } + if (codePoint >= 65 && codePoint < 91) { + return codePoint - 65; + } + if (codePoint >= 97 && codePoint < 123) { + return codePoint - 97; + } + return base; + }; + /** + * Converts a digit/integer into a basic code point. + * @see `basicToDigit()` + * @private + * @param {Number} digit The numeric value of a basic code point. + * @returns {Number} The basic code point whose value (when used for + * representing integers) is `digit`, which needs to be in the range + * `0` to `base - 1`. If `flag` is non-zero, the uppercase form is + * used; else, the lowercase form is used. The behavior is undefined + * if `flag` is non-zero and `digit` has no uppercase form. + */ const digitToBasic = function(digit, flag) { + // 0..25 map to ASCII a..z or A..Z + // 26..35 map to ASCII 0..9 + return digit + 22 + 75 * (digit < 26) - ((flag != 0) << 5); + }; + /** + * Bias adaptation function as per section 3.4 of RFC 3492. + * https://tools.ietf.org/html/rfc3492#section-3.4 + * @private + */ const adapt = function(delta, numPoints, firstTime) { + let k = 0; + delta = firstTime ? floor(delta / damp) : delta >> 1; + delta += floor(delta / numPoints); + for (;delta > baseMinusTMin * tMax >> 1; k += base) { + delta = floor(delta / baseMinusTMin); + } + return floor(k + (baseMinusTMin + 1) * delta / (delta + skew)); + }; + /** + * Converts a Punycode string of ASCII-only symbols to a string of Unicode + * symbols. + * @memberOf punycode + * @param {String} input The Punycode string of ASCII-only symbols. + * @returns {String} The resulting string of Unicode symbols. + */ const decode = function(input) { + // Don't use UCS-2. + const output = []; + const inputLength = input.length; + let i = 0; + let n = initialN; + let bias = initialBias; + // Handle the basic code points: let `basic` be the number of input code + // points before the last delimiter, or `0` if there is none, then copy + // the first basic code points to the output. + let basic = input.lastIndexOf(delimiter); + if (basic < 0) { + basic = 0; + } + for (let j = 0; j < basic; ++j) { + // if it's not a basic code point + if (input.charCodeAt(j) >= 128) { + error("not-basic"); + } + output.push(input.charCodeAt(j)); + } + // Main decoding loop: start just after the last delimiter if any basic code + // points were copied; start at the beginning otherwise. + for (let index = basic > 0 ? basic + 1 : 0; index < inputLength; ) { + // `index` is the index of the next character to be consumed. + // Decode a generalized variable-length integer into `delta`, + // which gets added to `i`. The overflow checking is easier + // if we increase `i` as we go, then subtract off its starting + // value at the end to obtain `delta`. + const oldi = i; + for (let w = 1, k = base; ;k += base) { + if (index >= inputLength) { + error("invalid-input"); + } + const digit = basicToDigit(input.charCodeAt(index++)); + if (digit >= base) { + error("invalid-input"); + } + if (digit > floor((maxInt - i) / w)) { + error("overflow"); + } + i += digit * w; + const t = k <= bias ? tMin : k >= bias + tMax ? tMax : k - bias; + if (digit < t) { + break; + } + const baseMinusT = base - t; + if (w > floor(maxInt / baseMinusT)) { + error("overflow"); + } + w *= baseMinusT; + } + const out = output.length + 1; + bias = adapt(i - oldi, out, oldi == 0); + // `i` was supposed to wrap around from `out` to `0`, + // incrementing `n` each time, so we'll fix that now: + if (floor(i / out) > maxInt - n) { + error("overflow"); + } + n += floor(i / out); + i %= out; + // Insert `n` at position `i` of the output. + output.splice(i++, 0, n); + } + return String.fromCodePoint(...output); + }; + /** + * Converts a string of Unicode symbols (e.g. a domain name label) to a + * Punycode string of ASCII-only symbols. + * @memberOf punycode + * @param {String} input The string of Unicode symbols. + * @returns {String} The resulting Punycode string of ASCII-only symbols. + */ const encode = function(input) { + const output = []; + // Convert the input in UCS-2 to an array of Unicode code points. + input = ucs2decode(input); + // Cache the length. + const inputLength = input.length; + // Initialize the state. + let n = initialN; + let delta = 0; + let bias = initialBias; + // Handle the basic code points. + for (const currentValue of input) { + if (currentValue < 128) { + output.push(stringFromCharCode(currentValue)); + } + } + const basicLength = output.length; + let handledCPCount = basicLength; + // `handledCPCount` is the number of code points that have been handled; + // `basicLength` is the number of basic code points. + // Finish the basic string with a delimiter unless it's empty. + if (basicLength) { + output.push(delimiter); + } + // Main encoding loop: + while (handledCPCount < inputLength) { + // All non-basic code points < n have been handled already. Find the next + // larger one: + let m = maxInt; + for (const currentValue of input) { + if (currentValue >= n && currentValue < m) { + m = currentValue; + } + } + // Increase `delta` enough to advance the decoder's state to , + // but guard against overflow. + const handledCPCountPlusOne = handledCPCount + 1; + if (m - n > floor((maxInt - delta) / handledCPCountPlusOne)) { + error("overflow"); + } + delta += (m - n) * handledCPCountPlusOne; + n = m; + for (const currentValue of input) { + if (currentValue < n && ++delta > maxInt) { + error("overflow"); + } + if (currentValue === n) { + // Represent delta as a generalized variable-length integer. + let q = delta; + for (let k = base; ;k += base) { + const t = k <= bias ? tMin : k >= bias + tMax ? tMax : k - bias; + if (q < t) { + break; + } + const qMinusT = q - t; + const baseMinusT = base - t; + output.push(stringFromCharCode(digitToBasic(t + qMinusT % baseMinusT, 0))); + q = floor(qMinusT / baseMinusT); + } + output.push(stringFromCharCode(digitToBasic(q, 0))); + bias = adapt(delta, handledCPCountPlusOne, handledCPCount === basicLength); + delta = 0; + ++handledCPCount; + } + } + ++delta; + ++n; + } + return output.join(""); + }; + /** + * Converts a Punycode string representing a domain name or an email address + * to Unicode. Only the Punycoded parts of the input will be converted, i.e. + * it doesn't matter if you call it on a string that has already been + * converted to Unicode. + * @memberOf punycode + * @param {String} input The Punycoded domain name or email address to + * convert to Unicode. + * @returns {String} The Unicode representation of the given Punycode + * string. + */ const toUnicode = function(input) { + return mapDomain(input, (function(string) { + return regexPunycode.test(string) ? decode(string.slice(4).toLowerCase()) : string; + })); + }; + /** + * Converts a Unicode string representing a domain name or an email address to + * Punycode. Only the non-ASCII parts of the domain name will be converted, + * i.e. it doesn't matter if you call it with a domain that's already in + * ASCII. + * @memberOf punycode + * @param {String} input The domain name or email address to convert, as a + * Unicode string. + * @returns {String} The Punycode representation of the given domain name or + * email address. + */ const toASCII = function(input) { + return mapDomain(input, (function(string) { + return regexNonASCII.test(string) ? "xn--" + encode(string) : string; + })); + }; + /*--------------------------------------------------------------------------*/ + /** Define the public API */ const punycode = { + /** + * A string representing the current Punycode.js version number. + * @memberOf punycode + * @type String + */ + version: "2.3.1", + /** + * An object of methods to convert from JavaScript's internal character + * representation (UCS-2) to Unicode code points, and back. + * @see + * @memberOf punycode + * @type Object + */ + ucs2: { + decode: ucs2decode, + encode: ucs2encode + }, + decode: decode, + encode: encode, + toASCII: toASCII, + toUnicode: toUnicode + }; + // markdown-it default options + var cfg_default = { + options: { + // Enable HTML tags in source + html: false, + // Use '/' to close single tags (
    ) + xhtmlOut: false, + // Convert '\n' in paragraphs into
    + breaks: false, + // CSS language prefix for fenced blocks + langPrefix: "language-", + // autoconvert URL-like texts to links + linkify: false, + // Enable some language-neutral replacements + quotes beautification + typographer: false, + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: "\u201c\u201d\u2018\u2019", + /* “”‘’ */ + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externaly. + // If result starts with ) + xhtmlOut: false, + // Convert '\n' in paragraphs into
    + breaks: false, + // CSS language prefix for fenced blocks + langPrefix: "language-", + // autoconvert URL-like texts to links + linkify: false, + // Enable some language-neutral replacements + quotes beautification + typographer: false, + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: "\u201c\u201d\u2018\u2019", + /* “”‘’ */ + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externaly. + // If result starts with ) + xhtmlOut: true, + // Convert '\n' in paragraphs into
    + breaks: false, + // CSS language prefix for fenced blocks + langPrefix: "language-", + // autoconvert URL-like texts to links + linkify: false, + // Enable some language-neutral replacements + quotes beautification + typographer: false, + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: "\u201c\u201d\u2018\u2019", + /* “”‘’ */ + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externaly. + // If result starts with = 0) { + try { + parsed.hostname = punycode.toASCII(parsed.hostname); + } catch (er) {} + } + } + return encode$1(format(parsed)); + } + function normalizeLinkText(url) { + const parsed = urlParse(url, true); + if (parsed.hostname) { + // Encode hostnames in urls like: + // `http://host/`, `https://host/`, `mailto:user@host`, `//host/` + // We don't encode unknown schemas, because it's likely that we encode + // something we shouldn't (e.g. `skype:name` treated as `skype:host`) + if (!parsed.protocol || RECODE_HOSTNAME_FOR.indexOf(parsed.protocol) >= 0) { + try { + parsed.hostname = punycode.toUnicode(parsed.hostname); + } catch (er) {} + } + } + // add '%' to exclude list because of https://github.com/markdown-it/markdown-it/issues/720 + return decode$1(format(parsed), decode$1.defaultChars + "%"); + } + /** + * class MarkdownIt + * + * Main parser/renderer class. + * + * ##### Usage + * + * ```javascript + * // node.js, "classic" way: + * var MarkdownIt = require('markdown-it'), + * md = new MarkdownIt(); + * var result = md.render('# markdown-it rulezz!'); + * + * // node.js, the same, but with sugar: + * var md = require('markdown-it')(); + * var result = md.render('# markdown-it rulezz!'); + * + * // browser without AMD, added to "window" on script load + * // Note, there are no dash. + * var md = window.markdownit(); + * var result = md.render('# markdown-it rulezz!'); + * ``` + * + * Single line rendering, without paragraph wrap: + * + * ```javascript + * var md = require('markdown-it')(); + * var result = md.renderInline('__markdown-it__ rulezz!'); + * ``` + **/ + /** + * new MarkdownIt([presetName, options]) + * - presetName (String): optional, `commonmark` / `zero` + * - options (Object) + * + * Creates parser instanse with given config. Can be called without `new`. + * + * ##### presetName + * + * MarkdownIt provides named presets as a convenience to quickly + * enable/disable active syntax rules and options for common use cases. + * + * - ["commonmark"](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/commonmark.mjs) - + * configures parser to strict [CommonMark](http://commonmark.org/) mode. + * - [default](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/default.mjs) - + * similar to GFM, used when no preset name given. Enables all available rules, + * but still without html, typographer & autolinker. + * - ["zero"](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/zero.mjs) - + * all rules disabled. Useful to quickly setup your config via `.enable()`. + * For example, when you need only `bold` and `italic` markup and nothing else. + * + * ##### options: + * + * - __html__ - `false`. Set `true` to enable HTML tags in source. Be careful! + * That's not safe! You may need external sanitizer to protect output from XSS. + * It's better to extend features via plugins, instead of enabling HTML. + * - __xhtmlOut__ - `false`. Set `true` to add '/' when closing single tags + * (`
    `). This is needed only for full CommonMark compatibility. In real + * world you will need HTML output. + * - __breaks__ - `false`. Set `true` to convert `\n` in paragraphs into `
    `. + * - __langPrefix__ - `language-`. CSS language class prefix for fenced blocks. + * Can be useful for external highlighters. + * - __linkify__ - `false`. Set `true` to autoconvert URL-like text to links. + * - __typographer__ - `false`. Set `true` to enable [some language-neutral + * replacement](https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/replacements.mjs) + + * quotes beautification (smartquotes). + * - __quotes__ - `“”‘’`, String or Array. Double + single quotes replacement + * pairs, when typographer enabled and smartquotes on. For example, you can + * use `'«»„“'` for Russian, `'„“‚‘'` for German, and + * `['«\xA0', '\xA0»', '‹\xA0', '\xA0›']` for French (including nbsp). + * - __highlight__ - `null`. Highlighter function for fenced code blocks. + * Highlighter `function (str, lang)` should return escaped HTML. It can also + * return empty string if the source was not changed and should be escaped + * externaly. If result starts with ` or ``): + * + * ```javascript + * var hljs = require('highlight.js') // https://highlightjs.org/ + * + * // Actual default values + * var md = require('markdown-it')({ + * highlight: function (str, lang) { + * if (lang && hljs.getLanguage(lang)) { + * try { + * return '
    ' +
    +   *                hljs.highlight(str, { language: lang, ignoreIllegals: true }).value +
    +   *                '
    '; + * } catch (__) {} + * } + * + * return '
    ' + md.utils.escapeHtml(str) + '
    '; + * } + * }); + * ``` + * + **/ function MarkdownIt(presetName, options) { + if (!(this instanceof MarkdownIt)) { + return new MarkdownIt(presetName, options); + } + if (!options) { + if (!isString$1(presetName)) { + options = presetName || {}; + presetName = "default"; + } + } + /** + * MarkdownIt#inline -> ParserInline + * + * Instance of [[ParserInline]]. You may need it to add new rules when + * writing plugins. For simple rules control use [[MarkdownIt.disable]] and + * [[MarkdownIt.enable]]. + **/ this.inline = new ParserInline; + /** + * MarkdownIt#block -> ParserBlock + * + * Instance of [[ParserBlock]]. You may need it to add new rules when + * writing plugins. For simple rules control use [[MarkdownIt.disable]] and + * [[MarkdownIt.enable]]. + **/ this.block = new ParserBlock; + /** + * MarkdownIt#core -> Core + * + * Instance of [[Core]] chain executor. You may need it to add new rules when + * writing plugins. For simple rules control use [[MarkdownIt.disable]] and + * [[MarkdownIt.enable]]. + **/ this.core = new Core; + /** + * MarkdownIt#renderer -> Renderer + * + * Instance of [[Renderer]]. Use it to modify output look. Or to add rendering + * rules for new token types, generated by plugins. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * function myToken(tokens, idx, options, env, self) { + * //... + * return result; + * }; + * + * md.renderer.rules['my_token'] = myToken + * ``` + * + * See [[Renderer]] docs and [source code](https://github.com/markdown-it/markdown-it/blob/master/lib/renderer.mjs). + **/ this.renderer = new Renderer; + /** + * MarkdownIt#linkify -> LinkifyIt + * + * [linkify-it](https://github.com/markdown-it/linkify-it) instance. + * Used by [linkify](https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/linkify.mjs) + * rule. + **/ this.linkify = new LinkifyIt; + /** + * MarkdownIt#validateLink(url) -> Boolean + * + * Link validation function. CommonMark allows too much in links. By default + * we disable `javascript:`, `vbscript:`, `file:` schemas, and almost all `data:...` schemas + * except some embedded image types. + * + * You can change this behaviour: + * + * ```javascript + * var md = require('markdown-it')(); + * // enable everything + * md.validateLink = function () { return true; } + * ``` + **/ this.validateLink = validateLink; + /** + * MarkdownIt#normalizeLink(url) -> String + * + * Function used to encode link url to a machine-readable format, + * which includes url-encoding, punycode, etc. + **/ this.normalizeLink = normalizeLink; + /** + * MarkdownIt#normalizeLinkText(url) -> String + * + * Function used to decode link url to a human-readable format` + **/ this.normalizeLinkText = normalizeLinkText; + // Expose utils & helpers for easy acces from plugins + /** + * MarkdownIt#utils -> utils + * + * Assorted utility functions, useful to write plugins. See details + * [here](https://github.com/markdown-it/markdown-it/blob/master/lib/common/utils.mjs). + **/ this.utils = utils; + /** + * MarkdownIt#helpers -> helpers + * + * Link components parser functions, useful to write plugins. See details + * [here](https://github.com/markdown-it/markdown-it/blob/master/lib/helpers). + **/ this.helpers = assign$1({}, helpers); + this.options = {}; + this.configure(presetName); + if (options) { + this.set(options); + } + } + /** chainable + * MarkdownIt.set(options) + * + * Set parser options (in the same format as in constructor). Probably, you + * will never need it, but you can change options after constructor call. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')() + * .set({ html: true, breaks: true }) + * .set({ typographer, true }); + * ``` + * + * __Note:__ To achieve the best possible performance, don't modify a + * `markdown-it` instance options on the fly. If you need multiple configurations + * it's best to create multiple instances and initialize each with separate + * config. + **/ MarkdownIt.prototype.set = function(options) { + assign$1(this.options, options); + return this; + }; + /** chainable, internal + * MarkdownIt.configure(presets) + * + * Batch load of all options and compenent settings. This is internal method, + * and you probably will not need it. But if you will - see available presets + * and data structure [here](https://github.com/markdown-it/markdown-it/tree/master/lib/presets) + * + * We strongly recommend to use presets instead of direct config loads. That + * will give better compatibility with next versions. + **/ MarkdownIt.prototype.configure = function(presets) { + const self = this; + if (isString$1(presets)) { + const presetName = presets; + presets = config[presetName]; + if (!presets) { + throw new Error('Wrong `markdown-it` preset "' + presetName + '", check name'); + } + } + if (!presets) { + throw new Error("Wrong `markdown-it` preset, can't be empty"); + } + if (presets.options) { + self.set(presets.options); + } + if (presets.components) { + Object.keys(presets.components).forEach((function(name) { + if (presets.components[name].rules) { + self[name].ruler.enableOnly(presets.components[name].rules); + } + if (presets.components[name].rules2) { + self[name].ruler2.enableOnly(presets.components[name].rules2); + } + })); + } + return this; + }; + /** chainable + * MarkdownIt.enable(list, ignoreInvalid) + * - list (String|Array): rule name or list of rule names to enable + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Enable list or rules. It will automatically find appropriate components, + * containing rules with given names. If rule not found, and `ignoreInvalid` + * not set - throws exception. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')() + * .enable(['sub', 'sup']) + * .disable('smartquotes'); + * ``` + **/ MarkdownIt.prototype.enable = function(list, ignoreInvalid) { + let result = []; + if (!Array.isArray(list)) { + list = [ list ]; + } + [ "core", "block", "inline" ].forEach((function(chain) { + result = result.concat(this[chain].ruler.enable(list, true)); + }), this); + result = result.concat(this.inline.ruler2.enable(list, true)); + const missed = list.filter((function(name) { + return result.indexOf(name) < 0; + })); + if (missed.length && !ignoreInvalid) { + throw new Error("MarkdownIt. Failed to enable unknown rule(s): " + missed); + } + return this; + }; + /** chainable + * MarkdownIt.disable(list, ignoreInvalid) + * - list (String|Array): rule name or list of rule names to disable. + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * The same as [[MarkdownIt.enable]], but turn specified rules off. + **/ MarkdownIt.prototype.disable = function(list, ignoreInvalid) { + let result = []; + if (!Array.isArray(list)) { + list = [ list ]; + } + [ "core", "block", "inline" ].forEach((function(chain) { + result = result.concat(this[chain].ruler.disable(list, true)); + }), this); + result = result.concat(this.inline.ruler2.disable(list, true)); + const missed = list.filter((function(name) { + return result.indexOf(name) < 0; + })); + if (missed.length && !ignoreInvalid) { + throw new Error("MarkdownIt. Failed to disable unknown rule(s): " + missed); + } + return this; + }; + /** chainable + * MarkdownIt.use(plugin, params) + * + * Load specified plugin with given params into current parser instance. + * It's just a sugar to call `plugin(md, params)` with curring. + * + * ##### Example + * + * ```javascript + * var iterator = require('markdown-it-for-inline'); + * var md = require('markdown-it')() + * .use(iterator, 'foo_replace', 'text', function (tokens, idx) { + * tokens[idx].content = tokens[idx].content.replace(/foo/g, 'bar'); + * }); + * ``` + **/ MarkdownIt.prototype.use = function(plugin /*, params, ... */) { + const args = [ this ].concat(Array.prototype.slice.call(arguments, 1)); + plugin.apply(plugin, args); + return this; + }; + /** internal + * MarkdownIt.parse(src, env) -> Array + * - src (String): source string + * - env (Object): environment sandbox + * + * Parse input string and return list of block tokens (special token type + * "inline" will contain list of inline tokens). You should not call this + * method directly, until you write custom renderer (for example, to produce + * AST). + * + * `env` is used to pass data between "distributed" rules and return additional + * metadata like reference info, needed for the renderer. It also can be used to + * inject data in specific cases. Usually, you will be ok to pass `{}`, + * and then pass updated object to renderer. + **/ MarkdownIt.prototype.parse = function(src, env) { + if (typeof src !== "string") { + throw new Error("Input data should be a String"); + } + const state = new this.core.State(src, this, env); + this.core.process(state); + return state.tokens; + }; + /** + * MarkdownIt.render(src [, env]) -> String + * - src (String): source string + * - env (Object): environment sandbox + * + * Render markdown string into html. It does all magic for you :). + * + * `env` can be used to inject additional metadata (`{}` by default). + * But you will not need it with high probability. See also comment + * in [[MarkdownIt.parse]]. + **/ MarkdownIt.prototype.render = function(src, env) { + env = env || {}; + return this.renderer.render(this.parse(src, env), this.options, env); + }; + /** internal + * MarkdownIt.parseInline(src, env) -> Array + * - src (String): source string + * - env (Object): environment sandbox + * + * The same as [[MarkdownIt.parse]] but skip all block rules. It returns the + * block tokens list with the single `inline` element, containing parsed inline + * tokens in `children` property. Also updates `env` object. + **/ MarkdownIt.prototype.parseInline = function(src, env) { + const state = new this.core.State(src, this, env); + state.inlineMode = true; + this.core.process(state); + return state.tokens; + }; + /** + * MarkdownIt.renderInline(src [, env]) -> String + * - src (String): source string + * - env (Object): environment sandbox + * + * Similar to [[MarkdownIt.render]] but for single paragraph content. Result + * will NOT be wrapped into `

    ` tags. + **/ MarkdownIt.prototype.renderInline = function(src, env) { + env = env || {}; + return this.renderer.render(this.parseInline(src, env), this.options, env); + }; + return MarkdownIt; +})); diff --git a/frontend/node_modules/markdown-it/dist/markdown-it.min.js b/frontend/node_modules/markdown-it/dist/markdown-it.min.js new file mode 100644 index 0000000..5e6f256 --- /dev/null +++ b/frontend/node_modules/markdown-it/dist/markdown-it.min.js @@ -0,0 +1,2 @@ +/*! markdown-it 14.1.0 https://github.com/markdown-it/markdown-it @license MIT */ +!function(t,e){"object"==typeof exports&&"undefined"!=typeof module?module.exports=e():"function"==typeof define&&define.amd?define(e):(t="undefined"!=typeof globalThis?globalThis:t||self).markdownit=e()}(this,(function(){"use strict";const t={};function e(r,n){"string"!=typeof n&&(n=e.defaultChars);const s=function(e){let r=t[e];if(r)return r;r=t[e]=[];for(let t=0;t<128;t++){const e=String.fromCharCode(t);r.push(e)}for(let t=0;t=55296&&t<=57343?"\ufffd\ufffd\ufffd":String.fromCharCode(t),r+=6;continue}}if(240==(248&i)&&r+91114111?e+="\ufffd\ufffd\ufffd\ufffd":(t-=65536,e+=String.fromCharCode(55296+(t>>10),56320+(1023&t))),r+=9;continue}}e+="\ufffd"}}return e}))}e.defaultChars=";/?:@&=+$,#",e.componentChars="";const r={};function n(t,e,s){"string"!=typeof e&&(s=e,e=n.defaultChars),void 0===s&&(s=!0);const i=function(t){let e=r[t];if(e)return e;e=r[t]=[];for(let t=0;t<128;t++){const r=String.fromCharCode(t);/^[0-9a-z]$/i.test(r)?e.push(r):e.push("%"+("0"+t.toString(16).toUpperCase()).slice(-2))}for(let r=0;r=55296&&n<=57343){if(n>=55296&&n<=56319&&e+1=56320&&r<=57343){o+=encodeURIComponent(t[e]+t[e+1]),e++;continue}}o+="%EF%BF%BD"}else o+=encodeURIComponent(t[e])}return o}function s(t){let e="";return e+=t.protocol||"",e+=t.slashes?"//":"",e+=t.auth?t.auth+"@":"",t.hostname&&-1!==t.hostname.indexOf(":")?e+="["+t.hostname+"]":e+=t.hostname||"",e+=t.port?":"+t.port:"",e+=t.pathname||"",e+=t.search||"",e+=t.hash||"",e}function i(){this.protocol=null,this.slashes=null,this.auth=null,this.port=null,this.hostname=null,this.hash=null,this.search=null,this.pathname=null}n.defaultChars=";/?:@&=+$,-_.!~*'()#",n.componentChars="-_.!~*'()";const o=/^([a-z0-9.+-]+:)/i,u=/:[0-9]*$/,c=/^(\/\/?(?!\/)[^\?\s]*)(\?[^\s]*)?$/,a=["{","}","|","\\","^","`"].concat(["<",">",'"',"`"," ","\r","\n","\t"]),l=["'"].concat(a),h=["%","/","?",";","#"].concat(l),p=["/","?","#"],f=/^[+a-z0-9A-Z_-]{0,63}$/,d=/^([+a-z0-9A-Z_-]{0,63})(.*)$/,_={javascript:!0,"javascript:":!0},m={http:!0,https:!0,ftp:!0,gopher:!0,file:!0,"http:":!0,"https:":!0,"ftp:":!0,"gopher:":!0,"file:":!0};function g(t,e){if(t&&t instanceof i)return t;const r=new i;return r.parse(t,e),r}i.prototype.parse=function(t,e){let r,n,s,i=t;if(i=i.trim(),!e&&1===t.split("#").length){const t=c.exec(i);if(t)return this.pathname=t[1],t[2]&&(this.search=t[2]),this}let u=o.exec(i);if(u&&(u=u[0],r=u.toLowerCase(),this.protocol=u,i=i.substr(u.length)),(e||u||i.match(/^\/\/[^@\/]+@[^@\/]+/))&&(s="//"===i.substr(0,2),!s||u&&_[u]||(i=i.substr(2),this.slashes=!0)),!_[u]&&(s||u&&!m[u])){let t,e,r=-1;for(let t=0;t127?n+="x":n+=r[t];if(!n.match(f)){const n=t.slice(0,e),s=t.slice(e+1),o=r.match(d);o&&(n.push(o[1]),s.unshift(o[2])),s.length&&(i=s.join(".")+i),this.hostname=n.join(".");break}}}}this.hostname.length>255&&(this.hostname=""),o&&(this.hostname=this.hostname.substr(1,this.hostname.length-2))}const a=i.indexOf("#");-1!==a&&(this.hash=i.substr(a),i=i.slice(0,a));const l=i.indexOf("?");return-1!==l&&(this.search=i.substr(l),i=i.slice(0,l)),i&&(this.pathname=i),m[r]&&this.hostname&&!this.pathname&&(this.pathname=""),this},i.prototype.parseHost=function(t){let e=u.exec(t);e&&(e=e[0],":"!==e&&(this.port=e.substr(1)),t=t.substr(0,t.length-e.length)),t&&(this.hostname=t)};var k,D=Object.freeze({__proto__:null,decode:e,encode:n,format:s,parse:g}),C=/[\0-\uD7FF\uE000-\uFFFF]|[\uD800-\uDBFF][\uDC00-\uDFFF]|[\uD800-\uDBFF](?![\uDC00-\uDFFF])|(?:[^\uD800-\uDBFF]|^)[\uDC00-\uDFFF]/,y=/[\0-\x1F\x7F-\x9F]/,E=/[!-#%-\*,-\/:;\?@\[-\]_\{\}\xA1\xA7\xAB\xB6\xB7\xBB\xBF\u037E\u0387\u055A-\u055F\u0589\u058A\u05BE\u05C0\u05C3\u05C6\u05F3\u05F4\u0609\u060A\u060C\u060D\u061B\u061D-\u061F\u066A-\u066D\u06D4\u0700-\u070D\u07F7-\u07F9\u0830-\u083E\u085E\u0964\u0965\u0970\u09FD\u0A76\u0AF0\u0C77\u0C84\u0DF4\u0E4F\u0E5A\u0E5B\u0F04-\u0F12\u0F14\u0F3A-\u0F3D\u0F85\u0FD0-\u0FD4\u0FD9\u0FDA\u104A-\u104F\u10FB\u1360-\u1368\u1400\u166E\u169B\u169C\u16EB-\u16ED\u1735\u1736\u17D4-\u17D6\u17D8-\u17DA\u1800-\u180A\u1944\u1945\u1A1E\u1A1F\u1AA0-\u1AA6\u1AA8-\u1AAD\u1B5A-\u1B60\u1B7D\u1B7E\u1BFC-\u1BFF\u1C3B-\u1C3F\u1C7E\u1C7F\u1CC0-\u1CC7\u1CD3\u2010-\u2027\u2030-\u2043\u2045-\u2051\u2053-\u205E\u207D\u207E\u208D\u208E\u2308-\u230B\u2329\u232A\u2768-\u2775\u27C5\u27C6\u27E6-\u27EF\u2983-\u2998\u29D8-\u29DB\u29FC\u29FD\u2CF9-\u2CFC\u2CFE\u2CFF\u2D70\u2E00-\u2E2E\u2E30-\u2E4F\u2E52-\u2E5D\u3001-\u3003\u3008-\u3011\u3014-\u301F\u3030\u303D\u30A0\u30FB\uA4FE\uA4FF\uA60D-\uA60F\uA673\uA67E\uA6F2-\uA6F7\uA874-\uA877\uA8CE\uA8CF\uA8F8-\uA8FA\uA8FC\uA92E\uA92F\uA95F\uA9C1-\uA9CD\uA9DE\uA9DF\uAA5C-\uAA5F\uAADE\uAADF\uAAF0\uAAF1\uABEB\uFD3E\uFD3F\uFE10-\uFE19\uFE30-\uFE52\uFE54-\uFE61\uFE63\uFE68\uFE6A\uFE6B\uFF01-\uFF03\uFF05-\uFF0A\uFF0C-\uFF0F\uFF1A\uFF1B\uFF1F\uFF20\uFF3B-\uFF3D\uFF3F\uFF5B\uFF5D\uFF5F-\uFF65]|\uD800[\uDD00-\uDD02\uDF9F\uDFD0]|\uD801\uDD6F|\uD802[\uDC57\uDD1F\uDD3F\uDE50-\uDE58\uDE7F\uDEF0-\uDEF6\uDF39-\uDF3F\uDF99-\uDF9C]|\uD803[\uDEAD\uDF55-\uDF59\uDF86-\uDF89]|\uD804[\uDC47-\uDC4D\uDCBB\uDCBC\uDCBE-\uDCC1\uDD40-\uDD43\uDD74\uDD75\uDDC5-\uDDC8\uDDCD\uDDDB\uDDDD-\uDDDF\uDE38-\uDE3D\uDEA9]|\uD805[\uDC4B-\uDC4F\uDC5A\uDC5B\uDC5D\uDCC6\uDDC1-\uDDD7\uDE41-\uDE43\uDE60-\uDE6C\uDEB9\uDF3C-\uDF3E]|\uD806[\uDC3B\uDD44-\uDD46\uDDE2\uDE3F-\uDE46\uDE9A-\uDE9C\uDE9E-\uDEA2\uDF00-\uDF09]|\uD807[\uDC41-\uDC45\uDC70\uDC71\uDEF7\uDEF8\uDF43-\uDF4F\uDFFF]|\uD809[\uDC70-\uDC74]|\uD80B[\uDFF1\uDFF2]|\uD81A[\uDE6E\uDE6F\uDEF5\uDF37-\uDF3B\uDF44]|\uD81B[\uDE97-\uDE9A\uDFE2]|\uD82F\uDC9F|\uD836[\uDE87-\uDE8B]|\uD83A[\uDD5E\uDD5F]/,A=/[\$\+<->\^`\|~\xA2-\xA6\xA8\xA9\xAC\xAE-\xB1\xB4\xB8\xD7\xF7\u02C2-\u02C5\u02D2-\u02DF\u02E5-\u02EB\u02ED\u02EF-\u02FF\u0375\u0384\u0385\u03F6\u0482\u058D-\u058F\u0606-\u0608\u060B\u060E\u060F\u06DE\u06E9\u06FD\u06FE\u07F6\u07FE\u07FF\u0888\u09F2\u09F3\u09FA\u09FB\u0AF1\u0B70\u0BF3-\u0BFA\u0C7F\u0D4F\u0D79\u0E3F\u0F01-\u0F03\u0F13\u0F15-\u0F17\u0F1A-\u0F1F\u0F34\u0F36\u0F38\u0FBE-\u0FC5\u0FC7-\u0FCC\u0FCE\u0FCF\u0FD5-\u0FD8\u109E\u109F\u1390-\u1399\u166D\u17DB\u1940\u19DE-\u19FF\u1B61-\u1B6A\u1B74-\u1B7C\u1FBD\u1FBF-\u1FC1\u1FCD-\u1FCF\u1FDD-\u1FDF\u1FED-\u1FEF\u1FFD\u1FFE\u2044\u2052\u207A-\u207C\u208A-\u208C\u20A0-\u20C0\u2100\u2101\u2103-\u2106\u2108\u2109\u2114\u2116-\u2118\u211E-\u2123\u2125\u2127\u2129\u212E\u213A\u213B\u2140-\u2144\u214A-\u214D\u214F\u218A\u218B\u2190-\u2307\u230C-\u2328\u232B-\u2426\u2440-\u244A\u249C-\u24E9\u2500-\u2767\u2794-\u27C4\u27C7-\u27E5\u27F0-\u2982\u2999-\u29D7\u29DC-\u29FB\u29FE-\u2B73\u2B76-\u2B95\u2B97-\u2BFF\u2CE5-\u2CEA\u2E50\u2E51\u2E80-\u2E99\u2E9B-\u2EF3\u2F00-\u2FD5\u2FF0-\u2FFF\u3004\u3012\u3013\u3020\u3036\u3037\u303E\u303F\u309B\u309C\u3190\u3191\u3196-\u319F\u31C0-\u31E3\u31EF\u3200-\u321E\u322A-\u3247\u3250\u3260-\u327F\u328A-\u32B0\u32C0-\u33FF\u4DC0-\u4DFF\uA490-\uA4C6\uA700-\uA716\uA720\uA721\uA789\uA78A\uA828-\uA82B\uA836-\uA839\uAA77-\uAA79\uAB5B\uAB6A\uAB6B\uFB29\uFBB2-\uFBC2\uFD40-\uFD4F\uFDCF\uFDFC-\uFDFF\uFE62\uFE64-\uFE66\uFE69\uFF04\uFF0B\uFF1C-\uFF1E\uFF3E\uFF40\uFF5C\uFF5E\uFFE0-\uFFE6\uFFE8-\uFFEE\uFFFC\uFFFD]|\uD800[\uDD37-\uDD3F\uDD79-\uDD89\uDD8C-\uDD8E\uDD90-\uDD9C\uDDA0\uDDD0-\uDDFC]|\uD802[\uDC77\uDC78\uDEC8]|\uD805\uDF3F|\uD807[\uDFD5-\uDFF1]|\uD81A[\uDF3C-\uDF3F\uDF45]|\uD82F\uDC9C|\uD833[\uDF50-\uDFC3]|\uD834[\uDC00-\uDCF5\uDD00-\uDD26\uDD29-\uDD64\uDD6A-\uDD6C\uDD83\uDD84\uDD8C-\uDDA9\uDDAE-\uDDEA\uDE00-\uDE41\uDE45\uDF00-\uDF56]|\uD835[\uDEC1\uDEDB\uDEFB\uDF15\uDF35\uDF4F\uDF6F\uDF89\uDFA9\uDFC3]|\uD836[\uDC00-\uDDFF\uDE37-\uDE3A\uDE6D-\uDE74\uDE76-\uDE83\uDE85\uDE86]|\uD838[\uDD4F\uDEFF]|\uD83B[\uDCAC\uDCB0\uDD2E\uDEF0\uDEF1]|\uD83C[\uDC00-\uDC2B\uDC30-\uDC93\uDCA0-\uDCAE\uDCB1-\uDCBF\uDCC1-\uDCCF\uDCD1-\uDCF5\uDD0D-\uDDAD\uDDE6-\uDE02\uDE10-\uDE3B\uDE40-\uDE48\uDE50\uDE51\uDE60-\uDE65\uDF00-\uDFFF]|\uD83D[\uDC00-\uDED7\uDEDC-\uDEEC\uDEF0-\uDEFC\uDF00-\uDF76\uDF7B-\uDFD9\uDFE0-\uDFEB\uDFF0]|\uD83E[\uDC00-\uDC0B\uDC10-\uDC47\uDC50-\uDC59\uDC60-\uDC87\uDC90-\uDCAD\uDCB0\uDCB1\uDD00-\uDE53\uDE60-\uDE6D\uDE70-\uDE7C\uDE80-\uDE88\uDE90-\uDEBD\uDEBF-\uDEC5\uDECE-\uDEDB\uDEE0-\uDEE8\uDEF0-\uDEF8\uDF00-\uDF92\uDF94-\uDFCA]/,b=/[ \xA0\u1680\u2000-\u200A\u2028\u2029\u202F\u205F\u3000]/,F=Object.freeze({__proto__:null,Any:C,Cc:y,Cf:/[\xAD\u0600-\u0605\u061C\u06DD\u070F\u0890\u0891\u08E2\u180E\u200B-\u200F\u202A-\u202E\u2060-\u2064\u2066-\u206F\uFEFF\uFFF9-\uFFFB]|\uD804[\uDCBD\uDCCD]|\uD80D[\uDC30-\uDC3F]|\uD82F[\uDCA0-\uDCA3]|\uD834[\uDD73-\uDD7A]|\uDB40[\uDC01\uDC20-\uDC7F]/,P:E,S:A,Z:b}),x=new Uint16Array('\u1d41<\xd5\u0131\u028a\u049d\u057b\u05d0\u0675\u06de\u07a2\u07d6\u080f\u0a4a\u0a91\u0da1\u0e6d\u0f09\u0f26\u10ca\u1228\u12e1\u1415\u149d\u14c3\u14df\u1525\0\0\0\0\0\0\u156b\u16cd\u198d\u1c12\u1ddd\u1f7e\u2060\u21b0\u228d\u23c0\u23fb\u2442\u2824\u2912\u2d08\u2e48\u2fce\u3016\u32ba\u3639\u37ac\u38fe\u3a28\u3a71\u3ae0\u3b2e\u0800EMabcfglmnoprstu\\bfms\x7f\x84\x8b\x90\x95\x98\xa6\xb3\xb9\xc8\xcflig\u803b\xc6\u40c6P\u803b&\u4026cute\u803b\xc1\u40c1reve;\u4102\u0100iyx}rc\u803b\xc2\u40c2;\u4410r;\uc000\ud835\udd04rave\u803b\xc0\u40c0pha;\u4391acr;\u4100d;\u6a53\u0100gp\x9d\xa1on;\u4104f;\uc000\ud835\udd38plyFunction;\u6061ing\u803b\xc5\u40c5\u0100cs\xbe\xc3r;\uc000\ud835\udc9cign;\u6254ilde\u803b\xc3\u40c3ml\u803b\xc4\u40c4\u0400aceforsu\xe5\xfb\xfe\u0117\u011c\u0122\u0127\u012a\u0100cr\xea\xf2kslash;\u6216\u0176\xf6\xf8;\u6ae7ed;\u6306y;\u4411\u0180crt\u0105\u010b\u0114ause;\u6235noullis;\u612ca;\u4392r;\uc000\ud835\udd05pf;\uc000\ud835\udd39eve;\u42d8c\xf2\u0113mpeq;\u624e\u0700HOacdefhilorsu\u014d\u0151\u0156\u0180\u019e\u01a2\u01b5\u01b7\u01ba\u01dc\u0215\u0273\u0278\u027ecy;\u4427PY\u803b\xa9\u40a9\u0180cpy\u015d\u0162\u017aute;\u4106\u0100;i\u0167\u0168\u62d2talDifferentialD;\u6145leys;\u612d\u0200aeio\u0189\u018e\u0194\u0198ron;\u410cdil\u803b\xc7\u40c7rc;\u4108nint;\u6230ot;\u410a\u0100dn\u01a7\u01adilla;\u40b8terDot;\u40b7\xf2\u017fi;\u43a7rcle\u0200DMPT\u01c7\u01cb\u01d1\u01d6ot;\u6299inus;\u6296lus;\u6295imes;\u6297o\u0100cs\u01e2\u01f8kwiseContourIntegral;\u6232eCurly\u0100DQ\u0203\u020foubleQuote;\u601duote;\u6019\u0200lnpu\u021e\u0228\u0247\u0255on\u0100;e\u0225\u0226\u6237;\u6a74\u0180git\u022f\u0236\u023aruent;\u6261nt;\u622fourIntegral;\u622e\u0100fr\u024c\u024e;\u6102oduct;\u6210nterClockwiseContourIntegral;\u6233oss;\u6a2fcr;\uc000\ud835\udc9ep\u0100;C\u0284\u0285\u62d3ap;\u624d\u0580DJSZacefios\u02a0\u02ac\u02b0\u02b4\u02b8\u02cb\u02d7\u02e1\u02e6\u0333\u048d\u0100;o\u0179\u02a5trahd;\u6911cy;\u4402cy;\u4405cy;\u440f\u0180grs\u02bf\u02c4\u02c7ger;\u6021r;\u61a1hv;\u6ae4\u0100ay\u02d0\u02d5ron;\u410e;\u4414l\u0100;t\u02dd\u02de\u6207a;\u4394r;\uc000\ud835\udd07\u0100af\u02eb\u0327\u0100cm\u02f0\u0322ritical\u0200ADGT\u0300\u0306\u0316\u031ccute;\u40b4o\u0174\u030b\u030d;\u42d9bleAcute;\u42ddrave;\u4060ilde;\u42dcond;\u62c4ferentialD;\u6146\u0470\u033d\0\0\0\u0342\u0354\0\u0405f;\uc000\ud835\udd3b\u0180;DE\u0348\u0349\u034d\u40a8ot;\u60dcqual;\u6250ble\u0300CDLRUV\u0363\u0372\u0382\u03cf\u03e2\u03f8ontourIntegra\xec\u0239o\u0274\u0379\0\0\u037b\xbb\u0349nArrow;\u61d3\u0100eo\u0387\u03a4ft\u0180ART\u0390\u0396\u03a1rrow;\u61d0ightArrow;\u61d4e\xe5\u02cang\u0100LR\u03ab\u03c4eft\u0100AR\u03b3\u03b9rrow;\u67f8ightArrow;\u67faightArrow;\u67f9ight\u0100AT\u03d8\u03derrow;\u61d2ee;\u62a8p\u0241\u03e9\0\0\u03efrrow;\u61d1ownArrow;\u61d5erticalBar;\u6225n\u0300ABLRTa\u0412\u042a\u0430\u045e\u047f\u037crrow\u0180;BU\u041d\u041e\u0422\u6193ar;\u6913pArrow;\u61f5reve;\u4311eft\u02d2\u043a\0\u0446\0\u0450ightVector;\u6950eeVector;\u695eector\u0100;B\u0459\u045a\u61bdar;\u6956ight\u01d4\u0467\0\u0471eeVector;\u695fector\u0100;B\u047a\u047b\u61c1ar;\u6957ee\u0100;A\u0486\u0487\u62a4rrow;\u61a7\u0100ct\u0492\u0497r;\uc000\ud835\udc9frok;\u4110\u0800NTacdfglmopqstux\u04bd\u04c0\u04c4\u04cb\u04de\u04e2\u04e7\u04ee\u04f5\u0521\u052f\u0536\u0552\u055d\u0560\u0565G;\u414aH\u803b\xd0\u40d0cute\u803b\xc9\u40c9\u0180aiy\u04d2\u04d7\u04dcron;\u411arc\u803b\xca\u40ca;\u442dot;\u4116r;\uc000\ud835\udd08rave\u803b\xc8\u40c8ement;\u6208\u0100ap\u04fa\u04fecr;\u4112ty\u0253\u0506\0\0\u0512mallSquare;\u65fberySmallSquare;\u65ab\u0100gp\u0526\u052aon;\u4118f;\uc000\ud835\udd3csilon;\u4395u\u0100ai\u053c\u0549l\u0100;T\u0542\u0543\u6a75ilde;\u6242librium;\u61cc\u0100ci\u0557\u055ar;\u6130m;\u6a73a;\u4397ml\u803b\xcb\u40cb\u0100ip\u056a\u056fsts;\u6203onentialE;\u6147\u0280cfios\u0585\u0588\u058d\u05b2\u05ccy;\u4424r;\uc000\ud835\udd09lled\u0253\u0597\0\0\u05a3mallSquare;\u65fcerySmallSquare;\u65aa\u0370\u05ba\0\u05bf\0\0\u05c4f;\uc000\ud835\udd3dAll;\u6200riertrf;\u6131c\xf2\u05cb\u0600JTabcdfgorst\u05e8\u05ec\u05ef\u05fa\u0600\u0612\u0616\u061b\u061d\u0623\u066c\u0672cy;\u4403\u803b>\u403emma\u0100;d\u05f7\u05f8\u4393;\u43dcreve;\u411e\u0180eiy\u0607\u060c\u0610dil;\u4122rc;\u411c;\u4413ot;\u4120r;\uc000\ud835\udd0a;\u62d9pf;\uc000\ud835\udd3eeater\u0300EFGLST\u0635\u0644\u064e\u0656\u065b\u0666qual\u0100;L\u063e\u063f\u6265ess;\u62dbullEqual;\u6267reater;\u6aa2ess;\u6277lantEqual;\u6a7eilde;\u6273cr;\uc000\ud835\udca2;\u626b\u0400Aacfiosu\u0685\u068b\u0696\u069b\u069e\u06aa\u06be\u06caRDcy;\u442a\u0100ct\u0690\u0694ek;\u42c7;\u405eirc;\u4124r;\u610clbertSpace;\u610b\u01f0\u06af\0\u06b2f;\u610dizontalLine;\u6500\u0100ct\u06c3\u06c5\xf2\u06a9rok;\u4126mp\u0144\u06d0\u06d8ownHum\xf0\u012fqual;\u624f\u0700EJOacdfgmnostu\u06fa\u06fe\u0703\u0707\u070e\u071a\u071e\u0721\u0728\u0744\u0778\u078b\u078f\u0795cy;\u4415lig;\u4132cy;\u4401cute\u803b\xcd\u40cd\u0100iy\u0713\u0718rc\u803b\xce\u40ce;\u4418ot;\u4130r;\u6111rave\u803b\xcc\u40cc\u0180;ap\u0720\u072f\u073f\u0100cg\u0734\u0737r;\u412ainaryI;\u6148lie\xf3\u03dd\u01f4\u0749\0\u0762\u0100;e\u074d\u074e\u622c\u0100gr\u0753\u0758ral;\u622bsection;\u62c2isible\u0100CT\u076c\u0772omma;\u6063imes;\u6062\u0180gpt\u077f\u0783\u0788on;\u412ef;\uc000\ud835\udd40a;\u4399cr;\u6110ilde;\u4128\u01eb\u079a\0\u079ecy;\u4406l\u803b\xcf\u40cf\u0280cfosu\u07ac\u07b7\u07bc\u07c2\u07d0\u0100iy\u07b1\u07b5rc;\u4134;\u4419r;\uc000\ud835\udd0dpf;\uc000\ud835\udd41\u01e3\u07c7\0\u07ccr;\uc000\ud835\udca5rcy;\u4408kcy;\u4404\u0380HJacfos\u07e4\u07e8\u07ec\u07f1\u07fd\u0802\u0808cy;\u4425cy;\u440cppa;\u439a\u0100ey\u07f6\u07fbdil;\u4136;\u441ar;\uc000\ud835\udd0epf;\uc000\ud835\udd42cr;\uc000\ud835\udca6\u0580JTaceflmost\u0825\u0829\u082c\u0850\u0863\u09b3\u09b8\u09c7\u09cd\u0a37\u0a47cy;\u4409\u803b<\u403c\u0280cmnpr\u0837\u083c\u0841\u0844\u084dute;\u4139bda;\u439bg;\u67ealacetrf;\u6112r;\u619e\u0180aey\u0857\u085c\u0861ron;\u413ddil;\u413b;\u441b\u0100fs\u0868\u0970t\u0500ACDFRTUVar\u087e\u08a9\u08b1\u08e0\u08e6\u08fc\u092f\u095b\u0390\u096a\u0100nr\u0883\u088fgleBracket;\u67e8row\u0180;BR\u0899\u089a\u089e\u6190ar;\u61e4ightArrow;\u61c6eiling;\u6308o\u01f5\u08b7\0\u08c3bleBracket;\u67e6n\u01d4\u08c8\0\u08d2eeVector;\u6961ector\u0100;B\u08db\u08dc\u61c3ar;\u6959loor;\u630aight\u0100AV\u08ef\u08f5rrow;\u6194ector;\u694e\u0100er\u0901\u0917e\u0180;AV\u0909\u090a\u0910\u62a3rrow;\u61a4ector;\u695aiangle\u0180;BE\u0924\u0925\u0929\u62b2ar;\u69cfqual;\u62b4p\u0180DTV\u0937\u0942\u094cownVector;\u6951eeVector;\u6960ector\u0100;B\u0956\u0957\u61bfar;\u6958ector\u0100;B\u0965\u0966\u61bcar;\u6952ight\xe1\u039cs\u0300EFGLST\u097e\u098b\u0995\u099d\u09a2\u09adqualGreater;\u62daullEqual;\u6266reater;\u6276ess;\u6aa1lantEqual;\u6a7dilde;\u6272r;\uc000\ud835\udd0f\u0100;e\u09bd\u09be\u62d8ftarrow;\u61daidot;\u413f\u0180npw\u09d4\u0a16\u0a1bg\u0200LRlr\u09de\u09f7\u0a02\u0a10eft\u0100AR\u09e6\u09ecrrow;\u67f5ightArrow;\u67f7ightArrow;\u67f6eft\u0100ar\u03b3\u0a0aight\xe1\u03bfight\xe1\u03caf;\uc000\ud835\udd43er\u0100LR\u0a22\u0a2ceftArrow;\u6199ightArrow;\u6198\u0180cht\u0a3e\u0a40\u0a42\xf2\u084c;\u61b0rok;\u4141;\u626a\u0400acefiosu\u0a5a\u0a5d\u0a60\u0a77\u0a7c\u0a85\u0a8b\u0a8ep;\u6905y;\u441c\u0100dl\u0a65\u0a6fiumSpace;\u605flintrf;\u6133r;\uc000\ud835\udd10nusPlus;\u6213pf;\uc000\ud835\udd44c\xf2\u0a76;\u439c\u0480Jacefostu\u0aa3\u0aa7\u0aad\u0ac0\u0b14\u0b19\u0d91\u0d97\u0d9ecy;\u440acute;\u4143\u0180aey\u0ab4\u0ab9\u0aberon;\u4147dil;\u4145;\u441d\u0180gsw\u0ac7\u0af0\u0b0eative\u0180MTV\u0ad3\u0adf\u0ae8ediumSpace;\u600bhi\u0100cn\u0ae6\u0ad8\xeb\u0ad9eryThi\xee\u0ad9ted\u0100GL\u0af8\u0b06reaterGreate\xf2\u0673essLes\xf3\u0a48Line;\u400ar;\uc000\ud835\udd11\u0200Bnpt\u0b22\u0b28\u0b37\u0b3areak;\u6060BreakingSpace;\u40a0f;\u6115\u0680;CDEGHLNPRSTV\u0b55\u0b56\u0b6a\u0b7c\u0ba1\u0beb\u0c04\u0c5e\u0c84\u0ca6\u0cd8\u0d61\u0d85\u6aec\u0100ou\u0b5b\u0b64ngruent;\u6262pCap;\u626doubleVerticalBar;\u6226\u0180lqx\u0b83\u0b8a\u0b9bement;\u6209ual\u0100;T\u0b92\u0b93\u6260ilde;\uc000\u2242\u0338ists;\u6204reater\u0380;EFGLST\u0bb6\u0bb7\u0bbd\u0bc9\u0bd3\u0bd8\u0be5\u626fqual;\u6271ullEqual;\uc000\u2267\u0338reater;\uc000\u226b\u0338ess;\u6279lantEqual;\uc000\u2a7e\u0338ilde;\u6275ump\u0144\u0bf2\u0bfdownHump;\uc000\u224e\u0338qual;\uc000\u224f\u0338e\u0100fs\u0c0a\u0c27tTriangle\u0180;BE\u0c1a\u0c1b\u0c21\u62eaar;\uc000\u29cf\u0338qual;\u62ecs\u0300;EGLST\u0c35\u0c36\u0c3c\u0c44\u0c4b\u0c58\u626equal;\u6270reater;\u6278ess;\uc000\u226a\u0338lantEqual;\uc000\u2a7d\u0338ilde;\u6274ested\u0100GL\u0c68\u0c79reaterGreater;\uc000\u2aa2\u0338essLess;\uc000\u2aa1\u0338recedes\u0180;ES\u0c92\u0c93\u0c9b\u6280qual;\uc000\u2aaf\u0338lantEqual;\u62e0\u0100ei\u0cab\u0cb9verseElement;\u620cghtTriangle\u0180;BE\u0ccb\u0ccc\u0cd2\u62ebar;\uc000\u29d0\u0338qual;\u62ed\u0100qu\u0cdd\u0d0cuareSu\u0100bp\u0ce8\u0cf9set\u0100;E\u0cf0\u0cf3\uc000\u228f\u0338qual;\u62e2erset\u0100;E\u0d03\u0d06\uc000\u2290\u0338qual;\u62e3\u0180bcp\u0d13\u0d24\u0d4eset\u0100;E\u0d1b\u0d1e\uc000\u2282\u20d2qual;\u6288ceeds\u0200;EST\u0d32\u0d33\u0d3b\u0d46\u6281qual;\uc000\u2ab0\u0338lantEqual;\u62e1ilde;\uc000\u227f\u0338erset\u0100;E\u0d58\u0d5b\uc000\u2283\u20d2qual;\u6289ilde\u0200;EFT\u0d6e\u0d6f\u0d75\u0d7f\u6241qual;\u6244ullEqual;\u6247ilde;\u6249erticalBar;\u6224cr;\uc000\ud835\udca9ilde\u803b\xd1\u40d1;\u439d\u0700Eacdfgmoprstuv\u0dbd\u0dc2\u0dc9\u0dd5\u0ddb\u0de0\u0de7\u0dfc\u0e02\u0e20\u0e22\u0e32\u0e3f\u0e44lig;\u4152cute\u803b\xd3\u40d3\u0100iy\u0dce\u0dd3rc\u803b\xd4\u40d4;\u441eblac;\u4150r;\uc000\ud835\udd12rave\u803b\xd2\u40d2\u0180aei\u0dee\u0df2\u0df6cr;\u414cga;\u43a9cron;\u439fpf;\uc000\ud835\udd46enCurly\u0100DQ\u0e0e\u0e1aoubleQuote;\u601cuote;\u6018;\u6a54\u0100cl\u0e27\u0e2cr;\uc000\ud835\udcaaash\u803b\xd8\u40d8i\u016c\u0e37\u0e3cde\u803b\xd5\u40d5es;\u6a37ml\u803b\xd6\u40d6er\u0100BP\u0e4b\u0e60\u0100ar\u0e50\u0e53r;\u603eac\u0100ek\u0e5a\u0e5c;\u63deet;\u63b4arenthesis;\u63dc\u0480acfhilors\u0e7f\u0e87\u0e8a\u0e8f\u0e92\u0e94\u0e9d\u0eb0\u0efcrtialD;\u6202y;\u441fr;\uc000\ud835\udd13i;\u43a6;\u43a0usMinus;\u40b1\u0100ip\u0ea2\u0eadncareplan\xe5\u069df;\u6119\u0200;eio\u0eb9\u0eba\u0ee0\u0ee4\u6abbcedes\u0200;EST\u0ec8\u0ec9\u0ecf\u0eda\u627aqual;\u6aaflantEqual;\u627cilde;\u627eme;\u6033\u0100dp\u0ee9\u0eeeuct;\u620fortion\u0100;a\u0225\u0ef9l;\u621d\u0100ci\u0f01\u0f06r;\uc000\ud835\udcab;\u43a8\u0200Ufos\u0f11\u0f16\u0f1b\u0f1fOT\u803b"\u4022r;\uc000\ud835\udd14pf;\u611acr;\uc000\ud835\udcac\u0600BEacefhiorsu\u0f3e\u0f43\u0f47\u0f60\u0f73\u0fa7\u0faa\u0fad\u1096\u10a9\u10b4\u10bearr;\u6910G\u803b\xae\u40ae\u0180cnr\u0f4e\u0f53\u0f56ute;\u4154g;\u67ebr\u0100;t\u0f5c\u0f5d\u61a0l;\u6916\u0180aey\u0f67\u0f6c\u0f71ron;\u4158dil;\u4156;\u4420\u0100;v\u0f78\u0f79\u611cerse\u0100EU\u0f82\u0f99\u0100lq\u0f87\u0f8eement;\u620builibrium;\u61cbpEquilibrium;\u696fr\xbb\u0f79o;\u43a1ght\u0400ACDFTUVa\u0fc1\u0feb\u0ff3\u1022\u1028\u105b\u1087\u03d8\u0100nr\u0fc6\u0fd2gleBracket;\u67e9row\u0180;BL\u0fdc\u0fdd\u0fe1\u6192ar;\u61e5eftArrow;\u61c4eiling;\u6309o\u01f5\u0ff9\0\u1005bleBracket;\u67e7n\u01d4\u100a\0\u1014eeVector;\u695dector\u0100;B\u101d\u101e\u61c2ar;\u6955loor;\u630b\u0100er\u102d\u1043e\u0180;AV\u1035\u1036\u103c\u62a2rrow;\u61a6ector;\u695biangle\u0180;BE\u1050\u1051\u1055\u62b3ar;\u69d0qual;\u62b5p\u0180DTV\u1063\u106e\u1078ownVector;\u694feeVector;\u695cector\u0100;B\u1082\u1083\u61bear;\u6954ector\u0100;B\u1091\u1092\u61c0ar;\u6953\u0100pu\u109b\u109ef;\u611dndImplies;\u6970ightarrow;\u61db\u0100ch\u10b9\u10bcr;\u611b;\u61b1leDelayed;\u69f4\u0680HOacfhimoqstu\u10e4\u10f1\u10f7\u10fd\u1119\u111e\u1151\u1156\u1161\u1167\u11b5\u11bb\u11bf\u0100Cc\u10e9\u10eeHcy;\u4429y;\u4428FTcy;\u442ccute;\u415a\u0280;aeiy\u1108\u1109\u110e\u1113\u1117\u6abcron;\u4160dil;\u415erc;\u415c;\u4421r;\uc000\ud835\udd16ort\u0200DLRU\u112a\u1134\u113e\u1149ownArrow\xbb\u041eeftArrow\xbb\u089aightArrow\xbb\u0fddpArrow;\u6191gma;\u43a3allCircle;\u6218pf;\uc000\ud835\udd4a\u0272\u116d\0\0\u1170t;\u621aare\u0200;ISU\u117b\u117c\u1189\u11af\u65a1ntersection;\u6293u\u0100bp\u118f\u119eset\u0100;E\u1197\u1198\u628fqual;\u6291erset\u0100;E\u11a8\u11a9\u6290qual;\u6292nion;\u6294cr;\uc000\ud835\udcaear;\u62c6\u0200bcmp\u11c8\u11db\u1209\u120b\u0100;s\u11cd\u11ce\u62d0et\u0100;E\u11cd\u11d5qual;\u6286\u0100ch\u11e0\u1205eeds\u0200;EST\u11ed\u11ee\u11f4\u11ff\u627bqual;\u6ab0lantEqual;\u627dilde;\u627fTh\xe1\u0f8c;\u6211\u0180;es\u1212\u1213\u1223\u62d1rset\u0100;E\u121c\u121d\u6283qual;\u6287et\xbb\u1213\u0580HRSacfhiors\u123e\u1244\u1249\u1255\u125e\u1271\u1276\u129f\u12c2\u12c8\u12d1ORN\u803b\xde\u40deADE;\u6122\u0100Hc\u124e\u1252cy;\u440by;\u4426\u0100bu\u125a\u125c;\u4009;\u43a4\u0180aey\u1265\u126a\u126fron;\u4164dil;\u4162;\u4422r;\uc000\ud835\udd17\u0100ei\u127b\u1289\u01f2\u1280\0\u1287efore;\u6234a;\u4398\u0100cn\u128e\u1298kSpace;\uc000\u205f\u200aSpace;\u6009lde\u0200;EFT\u12ab\u12ac\u12b2\u12bc\u623cqual;\u6243ullEqual;\u6245ilde;\u6248pf;\uc000\ud835\udd4bipleDot;\u60db\u0100ct\u12d6\u12dbr;\uc000\ud835\udcafrok;\u4166\u0ae1\u12f7\u130e\u131a\u1326\0\u132c\u1331\0\0\0\0\0\u1338\u133d\u1377\u1385\0\u13ff\u1404\u140a\u1410\u0100cr\u12fb\u1301ute\u803b\xda\u40dar\u0100;o\u1307\u1308\u619fcir;\u6949r\u01e3\u1313\0\u1316y;\u440eve;\u416c\u0100iy\u131e\u1323rc\u803b\xdb\u40db;\u4423blac;\u4170r;\uc000\ud835\udd18rave\u803b\xd9\u40d9acr;\u416a\u0100di\u1341\u1369er\u0100BP\u1348\u135d\u0100ar\u134d\u1350r;\u405fac\u0100ek\u1357\u1359;\u63dfet;\u63b5arenthesis;\u63ddon\u0100;P\u1370\u1371\u62c3lus;\u628e\u0100gp\u137b\u137fon;\u4172f;\uc000\ud835\udd4c\u0400ADETadps\u1395\u13ae\u13b8\u13c4\u03e8\u13d2\u13d7\u13f3rrow\u0180;BD\u1150\u13a0\u13a4ar;\u6912ownArrow;\u61c5ownArrow;\u6195quilibrium;\u696eee\u0100;A\u13cb\u13cc\u62a5rrow;\u61a5own\xe1\u03f3er\u0100LR\u13de\u13e8eftArrow;\u6196ightArrow;\u6197i\u0100;l\u13f9\u13fa\u43d2on;\u43a5ing;\u416ecr;\uc000\ud835\udcb0ilde;\u4168ml\u803b\xdc\u40dc\u0480Dbcdefosv\u1427\u142c\u1430\u1433\u143e\u1485\u148a\u1490\u1496ash;\u62abar;\u6aeby;\u4412ash\u0100;l\u143b\u143c\u62a9;\u6ae6\u0100er\u1443\u1445;\u62c1\u0180bty\u144c\u1450\u147aar;\u6016\u0100;i\u144f\u1455cal\u0200BLST\u1461\u1465\u146a\u1474ar;\u6223ine;\u407ceparator;\u6758ilde;\u6240ThinSpace;\u600ar;\uc000\ud835\udd19pf;\uc000\ud835\udd4dcr;\uc000\ud835\udcb1dash;\u62aa\u0280cefos\u14a7\u14ac\u14b1\u14b6\u14bcirc;\u4174dge;\u62c0r;\uc000\ud835\udd1apf;\uc000\ud835\udd4ecr;\uc000\ud835\udcb2\u0200fios\u14cb\u14d0\u14d2\u14d8r;\uc000\ud835\udd1b;\u439epf;\uc000\ud835\udd4fcr;\uc000\ud835\udcb3\u0480AIUacfosu\u14f1\u14f5\u14f9\u14fd\u1504\u150f\u1514\u151a\u1520cy;\u442fcy;\u4407cy;\u442ecute\u803b\xdd\u40dd\u0100iy\u1509\u150drc;\u4176;\u442br;\uc000\ud835\udd1cpf;\uc000\ud835\udd50cr;\uc000\ud835\udcb4ml;\u4178\u0400Hacdefos\u1535\u1539\u153f\u154b\u154f\u155d\u1560\u1564cy;\u4416cute;\u4179\u0100ay\u1544\u1549ron;\u417d;\u4417ot;\u417b\u01f2\u1554\0\u155boWidt\xe8\u0ad9a;\u4396r;\u6128pf;\u6124cr;\uc000\ud835\udcb5\u0be1\u1583\u158a\u1590\0\u15b0\u15b6\u15bf\0\0\0\0\u15c6\u15db\u15eb\u165f\u166d\0\u1695\u169b\u16b2\u16b9\0\u16becute\u803b\xe1\u40e1reve;\u4103\u0300;Ediuy\u159c\u159d\u15a1\u15a3\u15a8\u15ad\u623e;\uc000\u223e\u0333;\u623frc\u803b\xe2\u40e2te\u80bb\xb4\u0306;\u4430lig\u803b\xe6\u40e6\u0100;r\xb2\u15ba;\uc000\ud835\udd1erave\u803b\xe0\u40e0\u0100ep\u15ca\u15d6\u0100fp\u15cf\u15d4sym;\u6135\xe8\u15d3ha;\u43b1\u0100ap\u15dfc\u0100cl\u15e4\u15e7r;\u4101g;\u6a3f\u0264\u15f0\0\0\u160a\u0280;adsv\u15fa\u15fb\u15ff\u1601\u1607\u6227nd;\u6a55;\u6a5clope;\u6a58;\u6a5a\u0380;elmrsz\u1618\u1619\u161b\u161e\u163f\u164f\u1659\u6220;\u69a4e\xbb\u1619sd\u0100;a\u1625\u1626\u6221\u0461\u1630\u1632\u1634\u1636\u1638\u163a\u163c\u163e;\u69a8;\u69a9;\u69aa;\u69ab;\u69ac;\u69ad;\u69ae;\u69aft\u0100;v\u1645\u1646\u621fb\u0100;d\u164c\u164d\u62be;\u699d\u0100pt\u1654\u1657h;\u6222\xbb\xb9arr;\u637c\u0100gp\u1663\u1667on;\u4105f;\uc000\ud835\udd52\u0380;Eaeiop\u12c1\u167b\u167d\u1682\u1684\u1687\u168a;\u6a70cir;\u6a6f;\u624ad;\u624bs;\u4027rox\u0100;e\u12c1\u1692\xf1\u1683ing\u803b\xe5\u40e5\u0180cty\u16a1\u16a6\u16a8r;\uc000\ud835\udcb6;\u402amp\u0100;e\u12c1\u16af\xf1\u0288ilde\u803b\xe3\u40e3ml\u803b\xe4\u40e4\u0100ci\u16c2\u16c8onin\xf4\u0272nt;\u6a11\u0800Nabcdefiklnoprsu\u16ed\u16f1\u1730\u173c\u1743\u1748\u1778\u177d\u17e0\u17e6\u1839\u1850\u170d\u193d\u1948\u1970ot;\u6aed\u0100cr\u16f6\u171ek\u0200ceps\u1700\u1705\u170d\u1713ong;\u624cpsilon;\u43f6rime;\u6035im\u0100;e\u171a\u171b\u623dq;\u62cd\u0176\u1722\u1726ee;\u62bded\u0100;g\u172c\u172d\u6305e\xbb\u172drk\u0100;t\u135c\u1737brk;\u63b6\u0100oy\u1701\u1741;\u4431quo;\u601e\u0280cmprt\u1753\u175b\u1761\u1764\u1768aus\u0100;e\u010a\u0109ptyv;\u69b0s\xe9\u170cno\xf5\u0113\u0180ahw\u176f\u1771\u1773;\u43b2;\u6136een;\u626cr;\uc000\ud835\udd1fg\u0380costuvw\u178d\u179d\u17b3\u17c1\u17d5\u17db\u17de\u0180aiu\u1794\u1796\u179a\xf0\u0760rc;\u65efp\xbb\u1371\u0180dpt\u17a4\u17a8\u17adot;\u6a00lus;\u6a01imes;\u6a02\u0271\u17b9\0\0\u17becup;\u6a06ar;\u6605riangle\u0100du\u17cd\u17d2own;\u65bdp;\u65b3plus;\u6a04e\xe5\u1444\xe5\u14adarow;\u690d\u0180ako\u17ed\u1826\u1835\u0100cn\u17f2\u1823k\u0180lst\u17fa\u05ab\u1802ozenge;\u69ebriangle\u0200;dlr\u1812\u1813\u1818\u181d\u65b4own;\u65beeft;\u65c2ight;\u65b8k;\u6423\u01b1\u182b\0\u1833\u01b2\u182f\0\u1831;\u6592;\u65914;\u6593ck;\u6588\u0100eo\u183e\u184d\u0100;q\u1843\u1846\uc000=\u20e5uiv;\uc000\u2261\u20e5t;\u6310\u0200ptwx\u1859\u185e\u1867\u186cf;\uc000\ud835\udd53\u0100;t\u13cb\u1863om\xbb\u13cctie;\u62c8\u0600DHUVbdhmptuv\u1885\u1896\u18aa\u18bb\u18d7\u18db\u18ec\u18ff\u1905\u190a\u1910\u1921\u0200LRlr\u188e\u1890\u1892\u1894;\u6557;\u6554;\u6556;\u6553\u0280;DUdu\u18a1\u18a2\u18a4\u18a6\u18a8\u6550;\u6566;\u6569;\u6564;\u6567\u0200LRlr\u18b3\u18b5\u18b7\u18b9;\u655d;\u655a;\u655c;\u6559\u0380;HLRhlr\u18ca\u18cb\u18cd\u18cf\u18d1\u18d3\u18d5\u6551;\u656c;\u6563;\u6560;\u656b;\u6562;\u655fox;\u69c9\u0200LRlr\u18e4\u18e6\u18e8\u18ea;\u6555;\u6552;\u6510;\u650c\u0280;DUdu\u06bd\u18f7\u18f9\u18fb\u18fd;\u6565;\u6568;\u652c;\u6534inus;\u629flus;\u629eimes;\u62a0\u0200LRlr\u1919\u191b\u191d\u191f;\u655b;\u6558;\u6518;\u6514\u0380;HLRhlr\u1930\u1931\u1933\u1935\u1937\u1939\u193b\u6502;\u656a;\u6561;\u655e;\u653c;\u6524;\u651c\u0100ev\u0123\u1942bar\u803b\xa6\u40a6\u0200ceio\u1951\u1956\u195a\u1960r;\uc000\ud835\udcb7mi;\u604fm\u0100;e\u171a\u171cl\u0180;bh\u1968\u1969\u196b\u405c;\u69c5sub;\u67c8\u016c\u1974\u197el\u0100;e\u1979\u197a\u6022t\xbb\u197ap\u0180;Ee\u012f\u1985\u1987;\u6aae\u0100;q\u06dc\u06db\u0ce1\u19a7\0\u19e8\u1a11\u1a15\u1a32\0\u1a37\u1a50\0\0\u1ab4\0\0\u1ac1\0\0\u1b21\u1b2e\u1b4d\u1b52\0\u1bfd\0\u1c0c\u0180cpr\u19ad\u19b2\u19ddute;\u4107\u0300;abcds\u19bf\u19c0\u19c4\u19ca\u19d5\u19d9\u6229nd;\u6a44rcup;\u6a49\u0100au\u19cf\u19d2p;\u6a4bp;\u6a47ot;\u6a40;\uc000\u2229\ufe00\u0100eo\u19e2\u19e5t;\u6041\xee\u0693\u0200aeiu\u19f0\u19fb\u1a01\u1a05\u01f0\u19f5\0\u19f8s;\u6a4don;\u410ddil\u803b\xe7\u40e7rc;\u4109ps\u0100;s\u1a0c\u1a0d\u6a4cm;\u6a50ot;\u410b\u0180dmn\u1a1b\u1a20\u1a26il\u80bb\xb8\u01adptyv;\u69b2t\u8100\xa2;e\u1a2d\u1a2e\u40a2r\xe4\u01b2r;\uc000\ud835\udd20\u0180cei\u1a3d\u1a40\u1a4dy;\u4447ck\u0100;m\u1a47\u1a48\u6713ark\xbb\u1a48;\u43c7r\u0380;Ecefms\u1a5f\u1a60\u1a62\u1a6b\u1aa4\u1aaa\u1aae\u65cb;\u69c3\u0180;el\u1a69\u1a6a\u1a6d\u42c6q;\u6257e\u0261\u1a74\0\0\u1a88rrow\u0100lr\u1a7c\u1a81eft;\u61baight;\u61bb\u0280RSacd\u1a92\u1a94\u1a96\u1a9a\u1a9f\xbb\u0f47;\u64c8st;\u629birc;\u629aash;\u629dnint;\u6a10id;\u6aefcir;\u69c2ubs\u0100;u\u1abb\u1abc\u6663it\xbb\u1abc\u02ec\u1ac7\u1ad4\u1afa\0\u1b0aon\u0100;e\u1acd\u1ace\u403a\u0100;q\xc7\xc6\u026d\u1ad9\0\0\u1ae2a\u0100;t\u1ade\u1adf\u402c;\u4040\u0180;fl\u1ae8\u1ae9\u1aeb\u6201\xee\u1160e\u0100mx\u1af1\u1af6ent\xbb\u1ae9e\xf3\u024d\u01e7\u1afe\0\u1b07\u0100;d\u12bb\u1b02ot;\u6a6dn\xf4\u0246\u0180fry\u1b10\u1b14\u1b17;\uc000\ud835\udd54o\xe4\u0254\u8100\xa9;s\u0155\u1b1dr;\u6117\u0100ao\u1b25\u1b29rr;\u61b5ss;\u6717\u0100cu\u1b32\u1b37r;\uc000\ud835\udcb8\u0100bp\u1b3c\u1b44\u0100;e\u1b41\u1b42\u6acf;\u6ad1\u0100;e\u1b49\u1b4a\u6ad0;\u6ad2dot;\u62ef\u0380delprvw\u1b60\u1b6c\u1b77\u1b82\u1bac\u1bd4\u1bf9arr\u0100lr\u1b68\u1b6a;\u6938;\u6935\u0270\u1b72\0\0\u1b75r;\u62dec;\u62dfarr\u0100;p\u1b7f\u1b80\u61b6;\u693d\u0300;bcdos\u1b8f\u1b90\u1b96\u1ba1\u1ba5\u1ba8\u622arcap;\u6a48\u0100au\u1b9b\u1b9ep;\u6a46p;\u6a4aot;\u628dr;\u6a45;\uc000\u222a\ufe00\u0200alrv\u1bb5\u1bbf\u1bde\u1be3rr\u0100;m\u1bbc\u1bbd\u61b7;\u693cy\u0180evw\u1bc7\u1bd4\u1bd8q\u0270\u1bce\0\0\u1bd2re\xe3\u1b73u\xe3\u1b75ee;\u62ceedge;\u62cfen\u803b\xa4\u40a4earrow\u0100lr\u1bee\u1bf3eft\xbb\u1b80ight\xbb\u1bbde\xe4\u1bdd\u0100ci\u1c01\u1c07onin\xf4\u01f7nt;\u6231lcty;\u632d\u0980AHabcdefhijlorstuwz\u1c38\u1c3b\u1c3f\u1c5d\u1c69\u1c75\u1c8a\u1c9e\u1cac\u1cb7\u1cfb\u1cff\u1d0d\u1d7b\u1d91\u1dab\u1dbb\u1dc6\u1dcdr\xf2\u0381ar;\u6965\u0200glrs\u1c48\u1c4d\u1c52\u1c54ger;\u6020eth;\u6138\xf2\u1133h\u0100;v\u1c5a\u1c5b\u6010\xbb\u090a\u016b\u1c61\u1c67arow;\u690fa\xe3\u0315\u0100ay\u1c6e\u1c73ron;\u410f;\u4434\u0180;ao\u0332\u1c7c\u1c84\u0100gr\u02bf\u1c81r;\u61catseq;\u6a77\u0180glm\u1c91\u1c94\u1c98\u803b\xb0\u40b0ta;\u43b4ptyv;\u69b1\u0100ir\u1ca3\u1ca8sht;\u697f;\uc000\ud835\udd21ar\u0100lr\u1cb3\u1cb5\xbb\u08dc\xbb\u101e\u0280aegsv\u1cc2\u0378\u1cd6\u1cdc\u1ce0m\u0180;os\u0326\u1cca\u1cd4nd\u0100;s\u0326\u1cd1uit;\u6666amma;\u43ddin;\u62f2\u0180;io\u1ce7\u1ce8\u1cf8\u40f7de\u8100\xf7;o\u1ce7\u1cf0ntimes;\u62c7n\xf8\u1cf7cy;\u4452c\u026f\u1d06\0\0\u1d0arn;\u631eop;\u630d\u0280lptuw\u1d18\u1d1d\u1d22\u1d49\u1d55lar;\u4024f;\uc000\ud835\udd55\u0280;emps\u030b\u1d2d\u1d37\u1d3d\u1d42q\u0100;d\u0352\u1d33ot;\u6251inus;\u6238lus;\u6214quare;\u62a1blebarwedg\xe5\xfan\u0180adh\u112e\u1d5d\u1d67ownarrow\xf3\u1c83arpoon\u0100lr\u1d72\u1d76ef\xf4\u1cb4igh\xf4\u1cb6\u0162\u1d7f\u1d85karo\xf7\u0f42\u026f\u1d8a\0\0\u1d8ern;\u631fop;\u630c\u0180cot\u1d98\u1da3\u1da6\u0100ry\u1d9d\u1da1;\uc000\ud835\udcb9;\u4455l;\u69f6rok;\u4111\u0100dr\u1db0\u1db4ot;\u62f1i\u0100;f\u1dba\u1816\u65bf\u0100ah\u1dc0\u1dc3r\xf2\u0429a\xf2\u0fa6angle;\u69a6\u0100ci\u1dd2\u1dd5y;\u445fgrarr;\u67ff\u0900Dacdefglmnopqrstux\u1e01\u1e09\u1e19\u1e38\u0578\u1e3c\u1e49\u1e61\u1e7e\u1ea5\u1eaf\u1ebd\u1ee1\u1f2a\u1f37\u1f44\u1f4e\u1f5a\u0100Do\u1e06\u1d34o\xf4\u1c89\u0100cs\u1e0e\u1e14ute\u803b\xe9\u40e9ter;\u6a6e\u0200aioy\u1e22\u1e27\u1e31\u1e36ron;\u411br\u0100;c\u1e2d\u1e2e\u6256\u803b\xea\u40ealon;\u6255;\u444dot;\u4117\u0100Dr\u1e41\u1e45ot;\u6252;\uc000\ud835\udd22\u0180;rs\u1e50\u1e51\u1e57\u6a9aave\u803b\xe8\u40e8\u0100;d\u1e5c\u1e5d\u6a96ot;\u6a98\u0200;ils\u1e6a\u1e6b\u1e72\u1e74\u6a99nters;\u63e7;\u6113\u0100;d\u1e79\u1e7a\u6a95ot;\u6a97\u0180aps\u1e85\u1e89\u1e97cr;\u4113ty\u0180;sv\u1e92\u1e93\u1e95\u6205et\xbb\u1e93p\u01001;\u1e9d\u1ea4\u0133\u1ea1\u1ea3;\u6004;\u6005\u6003\u0100gs\u1eaa\u1eac;\u414bp;\u6002\u0100gp\u1eb4\u1eb8on;\u4119f;\uc000\ud835\udd56\u0180als\u1ec4\u1ece\u1ed2r\u0100;s\u1eca\u1ecb\u62d5l;\u69e3us;\u6a71i\u0180;lv\u1eda\u1edb\u1edf\u43b5on\xbb\u1edb;\u43f5\u0200csuv\u1eea\u1ef3\u1f0b\u1f23\u0100io\u1eef\u1e31rc\xbb\u1e2e\u0269\u1ef9\0\0\u1efb\xed\u0548ant\u0100gl\u1f02\u1f06tr\xbb\u1e5dess\xbb\u1e7a\u0180aei\u1f12\u1f16\u1f1als;\u403dst;\u625fv\u0100;D\u0235\u1f20D;\u6a78parsl;\u69e5\u0100Da\u1f2f\u1f33ot;\u6253rr;\u6971\u0180cdi\u1f3e\u1f41\u1ef8r;\u612fo\xf4\u0352\u0100ah\u1f49\u1f4b;\u43b7\u803b\xf0\u40f0\u0100mr\u1f53\u1f57l\u803b\xeb\u40ebo;\u60ac\u0180cip\u1f61\u1f64\u1f67l;\u4021s\xf4\u056e\u0100eo\u1f6c\u1f74ctatio\xee\u0559nential\xe5\u0579\u09e1\u1f92\0\u1f9e\0\u1fa1\u1fa7\0\0\u1fc6\u1fcc\0\u1fd3\0\u1fe6\u1fea\u2000\0\u2008\u205allingdotse\xf1\u1e44y;\u4444male;\u6640\u0180ilr\u1fad\u1fb3\u1fc1lig;\u8000\ufb03\u0269\u1fb9\0\0\u1fbdg;\u8000\ufb00ig;\u8000\ufb04;\uc000\ud835\udd23lig;\u8000\ufb01lig;\uc000fj\u0180alt\u1fd9\u1fdc\u1fe1t;\u666dig;\u8000\ufb02ns;\u65b1of;\u4192\u01f0\u1fee\0\u1ff3f;\uc000\ud835\udd57\u0100ak\u05bf\u1ff7\u0100;v\u1ffc\u1ffd\u62d4;\u6ad9artint;\u6a0d\u0100ao\u200c\u2055\u0100cs\u2011\u2052\u03b1\u201a\u2030\u2038\u2045\u2048\0\u2050\u03b2\u2022\u2025\u2027\u202a\u202c\0\u202e\u803b\xbd\u40bd;\u6153\u803b\xbc\u40bc;\u6155;\u6159;\u615b\u01b3\u2034\0\u2036;\u6154;\u6156\u02b4\u203e\u2041\0\0\u2043\u803b\xbe\u40be;\u6157;\u615c5;\u6158\u01b6\u204c\0\u204e;\u615a;\u615d8;\u615el;\u6044wn;\u6322cr;\uc000\ud835\udcbb\u0880Eabcdefgijlnorstv\u2082\u2089\u209f\u20a5\u20b0\u20b4\u20f0\u20f5\u20fa\u20ff\u2103\u2112\u2138\u0317\u213e\u2152\u219e\u0100;l\u064d\u2087;\u6a8c\u0180cmp\u2090\u2095\u209dute;\u41f5ma\u0100;d\u209c\u1cda\u43b3;\u6a86reve;\u411f\u0100iy\u20aa\u20aerc;\u411d;\u4433ot;\u4121\u0200;lqs\u063e\u0642\u20bd\u20c9\u0180;qs\u063e\u064c\u20c4lan\xf4\u0665\u0200;cdl\u0665\u20d2\u20d5\u20e5c;\u6aa9ot\u0100;o\u20dc\u20dd\u6a80\u0100;l\u20e2\u20e3\u6a82;\u6a84\u0100;e\u20ea\u20ed\uc000\u22db\ufe00s;\u6a94r;\uc000\ud835\udd24\u0100;g\u0673\u061bmel;\u6137cy;\u4453\u0200;Eaj\u065a\u210c\u210e\u2110;\u6a92;\u6aa5;\u6aa4\u0200Eaes\u211b\u211d\u2129\u2134;\u6269p\u0100;p\u2123\u2124\u6a8arox\xbb\u2124\u0100;q\u212e\u212f\u6a88\u0100;q\u212e\u211bim;\u62e7pf;\uc000\ud835\udd58\u0100ci\u2143\u2146r;\u610am\u0180;el\u066b\u214e\u2150;\u6a8e;\u6a90\u8300>;cdlqr\u05ee\u2160\u216a\u216e\u2173\u2179\u0100ci\u2165\u2167;\u6aa7r;\u6a7aot;\u62d7Par;\u6995uest;\u6a7c\u0280adels\u2184\u216a\u2190\u0656\u219b\u01f0\u2189\0\u218epro\xf8\u209er;\u6978q\u0100lq\u063f\u2196les\xf3\u2088i\xed\u066b\u0100en\u21a3\u21adrtneqq;\uc000\u2269\ufe00\xc5\u21aa\u0500Aabcefkosy\u21c4\u21c7\u21f1\u21f5\u21fa\u2218\u221d\u222f\u2268\u227dr\xf2\u03a0\u0200ilmr\u21d0\u21d4\u21d7\u21dbrs\xf0\u1484f\xbb\u2024il\xf4\u06a9\u0100dr\u21e0\u21e4cy;\u444a\u0180;cw\u08f4\u21eb\u21efir;\u6948;\u61adar;\u610firc;\u4125\u0180alr\u2201\u220e\u2213rts\u0100;u\u2209\u220a\u6665it\xbb\u220alip;\u6026con;\u62b9r;\uc000\ud835\udd25s\u0100ew\u2223\u2229arow;\u6925arow;\u6926\u0280amopr\u223a\u223e\u2243\u225e\u2263rr;\u61fftht;\u623bk\u0100lr\u2249\u2253eftarrow;\u61a9ightarrow;\u61aaf;\uc000\ud835\udd59bar;\u6015\u0180clt\u226f\u2274\u2278r;\uc000\ud835\udcbdas\xe8\u21f4rok;\u4127\u0100bp\u2282\u2287ull;\u6043hen\xbb\u1c5b\u0ae1\u22a3\0\u22aa\0\u22b8\u22c5\u22ce\0\u22d5\u22f3\0\0\u22f8\u2322\u2367\u2362\u237f\0\u2386\u23aa\u23b4cute\u803b\xed\u40ed\u0180;iy\u0771\u22b0\u22b5rc\u803b\xee\u40ee;\u4438\u0100cx\u22bc\u22bfy;\u4435cl\u803b\xa1\u40a1\u0100fr\u039f\u22c9;\uc000\ud835\udd26rave\u803b\xec\u40ec\u0200;ino\u073e\u22dd\u22e9\u22ee\u0100in\u22e2\u22e6nt;\u6a0ct;\u622dfin;\u69dcta;\u6129lig;\u4133\u0180aop\u22fe\u231a\u231d\u0180cgt\u2305\u2308\u2317r;\u412b\u0180elp\u071f\u230f\u2313in\xe5\u078ear\xf4\u0720h;\u4131f;\u62b7ed;\u41b5\u0280;cfot\u04f4\u232c\u2331\u233d\u2341are;\u6105in\u0100;t\u2338\u2339\u621eie;\u69dddo\xf4\u2319\u0280;celp\u0757\u234c\u2350\u235b\u2361al;\u62ba\u0100gr\u2355\u2359er\xf3\u1563\xe3\u234darhk;\u6a17rod;\u6a3c\u0200cgpt\u236f\u2372\u2376\u237by;\u4451on;\u412ff;\uc000\ud835\udd5aa;\u43b9uest\u803b\xbf\u40bf\u0100ci\u238a\u238fr;\uc000\ud835\udcben\u0280;Edsv\u04f4\u239b\u239d\u23a1\u04f3;\u62f9ot;\u62f5\u0100;v\u23a6\u23a7\u62f4;\u62f3\u0100;i\u0777\u23aelde;\u4129\u01eb\u23b8\0\u23bccy;\u4456l\u803b\xef\u40ef\u0300cfmosu\u23cc\u23d7\u23dc\u23e1\u23e7\u23f5\u0100iy\u23d1\u23d5rc;\u4135;\u4439r;\uc000\ud835\udd27ath;\u4237pf;\uc000\ud835\udd5b\u01e3\u23ec\0\u23f1r;\uc000\ud835\udcbfrcy;\u4458kcy;\u4454\u0400acfghjos\u240b\u2416\u2422\u2427\u242d\u2431\u2435\u243bppa\u0100;v\u2413\u2414\u43ba;\u43f0\u0100ey\u241b\u2420dil;\u4137;\u443ar;\uc000\ud835\udd28reen;\u4138cy;\u4445cy;\u445cpf;\uc000\ud835\udd5ccr;\uc000\ud835\udcc0\u0b80ABEHabcdefghjlmnoprstuv\u2470\u2481\u2486\u248d\u2491\u250e\u253d\u255a\u2580\u264e\u265e\u2665\u2679\u267d\u269a\u26b2\u26d8\u275d\u2768\u278b\u27c0\u2801\u2812\u0180art\u2477\u247a\u247cr\xf2\u09c6\xf2\u0395ail;\u691barr;\u690e\u0100;g\u0994\u248b;\u6a8bar;\u6962\u0963\u24a5\0\u24aa\0\u24b1\0\0\0\0\0\u24b5\u24ba\0\u24c6\u24c8\u24cd\0\u24f9ute;\u413amptyv;\u69b4ra\xee\u084cbda;\u43bbg\u0180;dl\u088e\u24c1\u24c3;\u6991\xe5\u088e;\u6a85uo\u803b\xab\u40abr\u0400;bfhlpst\u0899\u24de\u24e6\u24e9\u24eb\u24ee\u24f1\u24f5\u0100;f\u089d\u24e3s;\u691fs;\u691d\xeb\u2252p;\u61abl;\u6939im;\u6973l;\u61a2\u0180;ae\u24ff\u2500\u2504\u6aabil;\u6919\u0100;s\u2509\u250a\u6aad;\uc000\u2aad\ufe00\u0180abr\u2515\u2519\u251drr;\u690crk;\u6772\u0100ak\u2522\u252cc\u0100ek\u2528\u252a;\u407b;\u405b\u0100es\u2531\u2533;\u698bl\u0100du\u2539\u253b;\u698f;\u698d\u0200aeuy\u2546\u254b\u2556\u2558ron;\u413e\u0100di\u2550\u2554il;\u413c\xec\u08b0\xe2\u2529;\u443b\u0200cqrs\u2563\u2566\u256d\u257da;\u6936uo\u0100;r\u0e19\u1746\u0100du\u2572\u2577har;\u6967shar;\u694bh;\u61b2\u0280;fgqs\u258b\u258c\u0989\u25f3\u25ff\u6264t\u0280ahlrt\u2598\u25a4\u25b7\u25c2\u25e8rrow\u0100;t\u0899\u25a1a\xe9\u24f6arpoon\u0100du\u25af\u25b4own\xbb\u045ap\xbb\u0966eftarrows;\u61c7ight\u0180ahs\u25cd\u25d6\u25derrow\u0100;s\u08f4\u08a7arpoon\xf3\u0f98quigarro\xf7\u21f0hreetimes;\u62cb\u0180;qs\u258b\u0993\u25falan\xf4\u09ac\u0280;cdgs\u09ac\u260a\u260d\u261d\u2628c;\u6aa8ot\u0100;o\u2614\u2615\u6a7f\u0100;r\u261a\u261b\u6a81;\u6a83\u0100;e\u2622\u2625\uc000\u22da\ufe00s;\u6a93\u0280adegs\u2633\u2639\u263d\u2649\u264bppro\xf8\u24c6ot;\u62d6q\u0100gq\u2643\u2645\xf4\u0989gt\xf2\u248c\xf4\u099bi\xed\u09b2\u0180ilr\u2655\u08e1\u265asht;\u697c;\uc000\ud835\udd29\u0100;E\u099c\u2663;\u6a91\u0161\u2669\u2676r\u0100du\u25b2\u266e\u0100;l\u0965\u2673;\u696alk;\u6584cy;\u4459\u0280;acht\u0a48\u2688\u268b\u2691\u2696r\xf2\u25c1orne\xf2\u1d08ard;\u696bri;\u65fa\u0100io\u269f\u26a4dot;\u4140ust\u0100;a\u26ac\u26ad\u63b0che\xbb\u26ad\u0200Eaes\u26bb\u26bd\u26c9\u26d4;\u6268p\u0100;p\u26c3\u26c4\u6a89rox\xbb\u26c4\u0100;q\u26ce\u26cf\u6a87\u0100;q\u26ce\u26bbim;\u62e6\u0400abnoptwz\u26e9\u26f4\u26f7\u271a\u272f\u2741\u2747\u2750\u0100nr\u26ee\u26f1g;\u67ecr;\u61fdr\xeb\u08c1g\u0180lmr\u26ff\u270d\u2714eft\u0100ar\u09e6\u2707ight\xe1\u09f2apsto;\u67fcight\xe1\u09fdparrow\u0100lr\u2725\u2729ef\xf4\u24edight;\u61ac\u0180afl\u2736\u2739\u273dr;\u6985;\uc000\ud835\udd5dus;\u6a2dimes;\u6a34\u0161\u274b\u274fst;\u6217\xe1\u134e\u0180;ef\u2757\u2758\u1800\u65cange\xbb\u2758ar\u0100;l\u2764\u2765\u4028t;\u6993\u0280achmt\u2773\u2776\u277c\u2785\u2787r\xf2\u08a8orne\xf2\u1d8car\u0100;d\u0f98\u2783;\u696d;\u600eri;\u62bf\u0300achiqt\u2798\u279d\u0a40\u27a2\u27ae\u27bbquo;\u6039r;\uc000\ud835\udcc1m\u0180;eg\u09b2\u27aa\u27ac;\u6a8d;\u6a8f\u0100bu\u252a\u27b3o\u0100;r\u0e1f\u27b9;\u601arok;\u4142\u8400<;cdhilqr\u082b\u27d2\u2639\u27dc\u27e0\u27e5\u27ea\u27f0\u0100ci\u27d7\u27d9;\u6aa6r;\u6a79re\xe5\u25f2mes;\u62c9arr;\u6976uest;\u6a7b\u0100Pi\u27f5\u27f9ar;\u6996\u0180;ef\u2800\u092d\u181b\u65c3r\u0100du\u2807\u280dshar;\u694ahar;\u6966\u0100en\u2817\u2821rtneqq;\uc000\u2268\ufe00\xc5\u281e\u0700Dacdefhilnopsu\u2840\u2845\u2882\u288e\u2893\u28a0\u28a5\u28a8\u28da\u28e2\u28e4\u0a83\u28f3\u2902Dot;\u623a\u0200clpr\u284e\u2852\u2863\u287dr\u803b\xaf\u40af\u0100et\u2857\u2859;\u6642\u0100;e\u285e\u285f\u6720se\xbb\u285f\u0100;s\u103b\u2868to\u0200;dlu\u103b\u2873\u2877\u287bow\xee\u048cef\xf4\u090f\xf0\u13d1ker;\u65ae\u0100oy\u2887\u288cmma;\u6a29;\u443cash;\u6014asuredangle\xbb\u1626r;\uc000\ud835\udd2ao;\u6127\u0180cdn\u28af\u28b4\u28c9ro\u803b\xb5\u40b5\u0200;acd\u1464\u28bd\u28c0\u28c4s\xf4\u16a7ir;\u6af0ot\u80bb\xb7\u01b5us\u0180;bd\u28d2\u1903\u28d3\u6212\u0100;u\u1d3c\u28d8;\u6a2a\u0163\u28de\u28e1p;\u6adb\xf2\u2212\xf0\u0a81\u0100dp\u28e9\u28eeels;\u62a7f;\uc000\ud835\udd5e\u0100ct\u28f8\u28fdr;\uc000\ud835\udcc2pos\xbb\u159d\u0180;lm\u2909\u290a\u290d\u43bctimap;\u62b8\u0c00GLRVabcdefghijlmoprstuvw\u2942\u2953\u297e\u2989\u2998\u29da\u29e9\u2a15\u2a1a\u2a58\u2a5d\u2a83\u2a95\u2aa4\u2aa8\u2b04\u2b07\u2b44\u2b7f\u2bae\u2c34\u2c67\u2c7c\u2ce9\u0100gt\u2947\u294b;\uc000\u22d9\u0338\u0100;v\u2950\u0bcf\uc000\u226b\u20d2\u0180elt\u295a\u2972\u2976ft\u0100ar\u2961\u2967rrow;\u61cdightarrow;\u61ce;\uc000\u22d8\u0338\u0100;v\u297b\u0c47\uc000\u226a\u20d2ightarrow;\u61cf\u0100Dd\u298e\u2993ash;\u62afash;\u62ae\u0280bcnpt\u29a3\u29a7\u29ac\u29b1\u29ccla\xbb\u02deute;\u4144g;\uc000\u2220\u20d2\u0280;Eiop\u0d84\u29bc\u29c0\u29c5\u29c8;\uc000\u2a70\u0338d;\uc000\u224b\u0338s;\u4149ro\xf8\u0d84ur\u0100;a\u29d3\u29d4\u666el\u0100;s\u29d3\u0b38\u01f3\u29df\0\u29e3p\u80bb\xa0\u0b37mp\u0100;e\u0bf9\u0c00\u0280aeouy\u29f4\u29fe\u2a03\u2a10\u2a13\u01f0\u29f9\0\u29fb;\u6a43on;\u4148dil;\u4146ng\u0100;d\u0d7e\u2a0aot;\uc000\u2a6d\u0338p;\u6a42;\u443dash;\u6013\u0380;Aadqsx\u0b92\u2a29\u2a2d\u2a3b\u2a41\u2a45\u2a50rr;\u61d7r\u0100hr\u2a33\u2a36k;\u6924\u0100;o\u13f2\u13f0ot;\uc000\u2250\u0338ui\xf6\u0b63\u0100ei\u2a4a\u2a4ear;\u6928\xed\u0b98ist\u0100;s\u0ba0\u0b9fr;\uc000\ud835\udd2b\u0200Eest\u0bc5\u2a66\u2a79\u2a7c\u0180;qs\u0bbc\u2a6d\u0be1\u0180;qs\u0bbc\u0bc5\u2a74lan\xf4\u0be2i\xed\u0bea\u0100;r\u0bb6\u2a81\xbb\u0bb7\u0180Aap\u2a8a\u2a8d\u2a91r\xf2\u2971rr;\u61aear;\u6af2\u0180;sv\u0f8d\u2a9c\u0f8c\u0100;d\u2aa1\u2aa2\u62fc;\u62facy;\u445a\u0380AEadest\u2ab7\u2aba\u2abe\u2ac2\u2ac5\u2af6\u2af9r\xf2\u2966;\uc000\u2266\u0338rr;\u619ar;\u6025\u0200;fqs\u0c3b\u2ace\u2ae3\u2aeft\u0100ar\u2ad4\u2ad9rro\xf7\u2ac1ightarro\xf7\u2a90\u0180;qs\u0c3b\u2aba\u2aealan\xf4\u0c55\u0100;s\u0c55\u2af4\xbb\u0c36i\xed\u0c5d\u0100;r\u0c35\u2afei\u0100;e\u0c1a\u0c25i\xe4\u0d90\u0100pt\u2b0c\u2b11f;\uc000\ud835\udd5f\u8180\xac;in\u2b19\u2b1a\u2b36\u40acn\u0200;Edv\u0b89\u2b24\u2b28\u2b2e;\uc000\u22f9\u0338ot;\uc000\u22f5\u0338\u01e1\u0b89\u2b33\u2b35;\u62f7;\u62f6i\u0100;v\u0cb8\u2b3c\u01e1\u0cb8\u2b41\u2b43;\u62fe;\u62fd\u0180aor\u2b4b\u2b63\u2b69r\u0200;ast\u0b7b\u2b55\u2b5a\u2b5flle\xec\u0b7bl;\uc000\u2afd\u20e5;\uc000\u2202\u0338lint;\u6a14\u0180;ce\u0c92\u2b70\u2b73u\xe5\u0ca5\u0100;c\u0c98\u2b78\u0100;e\u0c92\u2b7d\xf1\u0c98\u0200Aait\u2b88\u2b8b\u2b9d\u2ba7r\xf2\u2988rr\u0180;cw\u2b94\u2b95\u2b99\u619b;\uc000\u2933\u0338;\uc000\u219d\u0338ghtarrow\xbb\u2b95ri\u0100;e\u0ccb\u0cd6\u0380chimpqu\u2bbd\u2bcd\u2bd9\u2b04\u0b78\u2be4\u2bef\u0200;cer\u0d32\u2bc6\u0d37\u2bc9u\xe5\u0d45;\uc000\ud835\udcc3ort\u026d\u2b05\0\0\u2bd6ar\xe1\u2b56m\u0100;e\u0d6e\u2bdf\u0100;q\u0d74\u0d73su\u0100bp\u2beb\u2bed\xe5\u0cf8\xe5\u0d0b\u0180bcp\u2bf6\u2c11\u2c19\u0200;Ees\u2bff\u2c00\u0d22\u2c04\u6284;\uc000\u2ac5\u0338et\u0100;e\u0d1b\u2c0bq\u0100;q\u0d23\u2c00c\u0100;e\u0d32\u2c17\xf1\u0d38\u0200;Ees\u2c22\u2c23\u0d5f\u2c27\u6285;\uc000\u2ac6\u0338et\u0100;e\u0d58\u2c2eq\u0100;q\u0d60\u2c23\u0200gilr\u2c3d\u2c3f\u2c45\u2c47\xec\u0bd7lde\u803b\xf1\u40f1\xe7\u0c43iangle\u0100lr\u2c52\u2c5ceft\u0100;e\u0c1a\u2c5a\xf1\u0c26ight\u0100;e\u0ccb\u2c65\xf1\u0cd7\u0100;m\u2c6c\u2c6d\u43bd\u0180;es\u2c74\u2c75\u2c79\u4023ro;\u6116p;\u6007\u0480DHadgilrs\u2c8f\u2c94\u2c99\u2c9e\u2ca3\u2cb0\u2cb6\u2cd3\u2ce3ash;\u62adarr;\u6904p;\uc000\u224d\u20d2ash;\u62ac\u0100et\u2ca8\u2cac;\uc000\u2265\u20d2;\uc000>\u20d2nfin;\u69de\u0180Aet\u2cbd\u2cc1\u2cc5rr;\u6902;\uc000\u2264\u20d2\u0100;r\u2cca\u2ccd\uc000<\u20d2ie;\uc000\u22b4\u20d2\u0100At\u2cd8\u2cdcrr;\u6903rie;\uc000\u22b5\u20d2im;\uc000\u223c\u20d2\u0180Aan\u2cf0\u2cf4\u2d02rr;\u61d6r\u0100hr\u2cfa\u2cfdk;\u6923\u0100;o\u13e7\u13e5ear;\u6927\u1253\u1a95\0\0\0\0\0\0\0\0\0\0\0\0\0\u2d2d\0\u2d38\u2d48\u2d60\u2d65\u2d72\u2d84\u1b07\0\0\u2d8d\u2dab\0\u2dc8\u2dce\0\u2ddc\u2e19\u2e2b\u2e3e\u2e43\u0100cs\u2d31\u1a97ute\u803b\xf3\u40f3\u0100iy\u2d3c\u2d45r\u0100;c\u1a9e\u2d42\u803b\xf4\u40f4;\u443e\u0280abios\u1aa0\u2d52\u2d57\u01c8\u2d5alac;\u4151v;\u6a38old;\u69bclig;\u4153\u0100cr\u2d69\u2d6dir;\u69bf;\uc000\ud835\udd2c\u036f\u2d79\0\0\u2d7c\0\u2d82n;\u42dbave\u803b\xf2\u40f2;\u69c1\u0100bm\u2d88\u0df4ar;\u69b5\u0200acit\u2d95\u2d98\u2da5\u2da8r\xf2\u1a80\u0100ir\u2d9d\u2da0r;\u69beoss;\u69bbn\xe5\u0e52;\u69c0\u0180aei\u2db1\u2db5\u2db9cr;\u414dga;\u43c9\u0180cdn\u2dc0\u2dc5\u01cdron;\u43bf;\u69b6pf;\uc000\ud835\udd60\u0180ael\u2dd4\u2dd7\u01d2r;\u69b7rp;\u69b9\u0380;adiosv\u2dea\u2deb\u2dee\u2e08\u2e0d\u2e10\u2e16\u6228r\xf2\u1a86\u0200;efm\u2df7\u2df8\u2e02\u2e05\u6a5dr\u0100;o\u2dfe\u2dff\u6134f\xbb\u2dff\u803b\xaa\u40aa\u803b\xba\u40bagof;\u62b6r;\u6a56lope;\u6a57;\u6a5b\u0180clo\u2e1f\u2e21\u2e27\xf2\u2e01ash\u803b\xf8\u40f8l;\u6298i\u016c\u2e2f\u2e34de\u803b\xf5\u40f5es\u0100;a\u01db\u2e3as;\u6a36ml\u803b\xf6\u40f6bar;\u633d\u0ae1\u2e5e\0\u2e7d\0\u2e80\u2e9d\0\u2ea2\u2eb9\0\0\u2ecb\u0e9c\0\u2f13\0\0\u2f2b\u2fbc\0\u2fc8r\u0200;ast\u0403\u2e67\u2e72\u0e85\u8100\xb6;l\u2e6d\u2e6e\u40b6le\xec\u0403\u0269\u2e78\0\0\u2e7bm;\u6af3;\u6afdy;\u443fr\u0280cimpt\u2e8b\u2e8f\u2e93\u1865\u2e97nt;\u4025od;\u402eil;\u6030enk;\u6031r;\uc000\ud835\udd2d\u0180imo\u2ea8\u2eb0\u2eb4\u0100;v\u2ead\u2eae\u43c6;\u43d5ma\xf4\u0a76ne;\u660e\u0180;tv\u2ebf\u2ec0\u2ec8\u43c0chfork\xbb\u1ffd;\u43d6\u0100au\u2ecf\u2edfn\u0100ck\u2ed5\u2eddk\u0100;h\u21f4\u2edb;\u610e\xf6\u21f4s\u0480;abcdemst\u2ef3\u2ef4\u1908\u2ef9\u2efd\u2f04\u2f06\u2f0a\u2f0e\u402bcir;\u6a23ir;\u6a22\u0100ou\u1d40\u2f02;\u6a25;\u6a72n\u80bb\xb1\u0e9dim;\u6a26wo;\u6a27\u0180ipu\u2f19\u2f20\u2f25ntint;\u6a15f;\uc000\ud835\udd61nd\u803b\xa3\u40a3\u0500;Eaceinosu\u0ec8\u2f3f\u2f41\u2f44\u2f47\u2f81\u2f89\u2f92\u2f7e\u2fb6;\u6ab3p;\u6ab7u\xe5\u0ed9\u0100;c\u0ece\u2f4c\u0300;acens\u0ec8\u2f59\u2f5f\u2f66\u2f68\u2f7eppro\xf8\u2f43urlye\xf1\u0ed9\xf1\u0ece\u0180aes\u2f6f\u2f76\u2f7approx;\u6ab9qq;\u6ab5im;\u62e8i\xed\u0edfme\u0100;s\u2f88\u0eae\u6032\u0180Eas\u2f78\u2f90\u2f7a\xf0\u2f75\u0180dfp\u0eec\u2f99\u2faf\u0180als\u2fa0\u2fa5\u2faalar;\u632eine;\u6312urf;\u6313\u0100;t\u0efb\u2fb4\xef\u0efbrel;\u62b0\u0100ci\u2fc0\u2fc5r;\uc000\ud835\udcc5;\u43c8ncsp;\u6008\u0300fiopsu\u2fda\u22e2\u2fdf\u2fe5\u2feb\u2ff1r;\uc000\ud835\udd2epf;\uc000\ud835\udd62rime;\u6057cr;\uc000\ud835\udcc6\u0180aeo\u2ff8\u3009\u3013t\u0100ei\u2ffe\u3005rnion\xf3\u06b0nt;\u6a16st\u0100;e\u3010\u3011\u403f\xf1\u1f19\xf4\u0f14\u0a80ABHabcdefhilmnoprstux\u3040\u3051\u3055\u3059\u30e0\u310e\u312b\u3147\u3162\u3172\u318e\u3206\u3215\u3224\u3229\u3258\u326e\u3272\u3290\u32b0\u32b7\u0180art\u3047\u304a\u304cr\xf2\u10b3\xf2\u03ddail;\u691car\xf2\u1c65ar;\u6964\u0380cdenqrt\u3068\u3075\u3078\u307f\u308f\u3094\u30cc\u0100eu\u306d\u3071;\uc000\u223d\u0331te;\u4155i\xe3\u116emptyv;\u69b3g\u0200;del\u0fd1\u3089\u308b\u308d;\u6992;\u69a5\xe5\u0fd1uo\u803b\xbb\u40bbr\u0580;abcfhlpstw\u0fdc\u30ac\u30af\u30b7\u30b9\u30bc\u30be\u30c0\u30c3\u30c7\u30cap;\u6975\u0100;f\u0fe0\u30b4s;\u6920;\u6933s;\u691e\xeb\u225d\xf0\u272el;\u6945im;\u6974l;\u61a3;\u619d\u0100ai\u30d1\u30d5il;\u691ao\u0100;n\u30db\u30dc\u6236al\xf3\u0f1e\u0180abr\u30e7\u30ea\u30eer\xf2\u17e5rk;\u6773\u0100ak\u30f3\u30fdc\u0100ek\u30f9\u30fb;\u407d;\u405d\u0100es\u3102\u3104;\u698cl\u0100du\u310a\u310c;\u698e;\u6990\u0200aeuy\u3117\u311c\u3127\u3129ron;\u4159\u0100di\u3121\u3125il;\u4157\xec\u0ff2\xe2\u30fa;\u4440\u0200clqs\u3134\u3137\u313d\u3144a;\u6937dhar;\u6969uo\u0100;r\u020e\u020dh;\u61b3\u0180acg\u314e\u315f\u0f44l\u0200;ips\u0f78\u3158\u315b\u109cn\xe5\u10bbar\xf4\u0fa9t;\u65ad\u0180ilr\u3169\u1023\u316esht;\u697d;\uc000\ud835\udd2f\u0100ao\u3177\u3186r\u0100du\u317d\u317f\xbb\u047b\u0100;l\u1091\u3184;\u696c\u0100;v\u318b\u318c\u43c1;\u43f1\u0180gns\u3195\u31f9\u31fcht\u0300ahlrst\u31a4\u31b0\u31c2\u31d8\u31e4\u31eerrow\u0100;t\u0fdc\u31ada\xe9\u30c8arpoon\u0100du\u31bb\u31bfow\xee\u317ep\xbb\u1092eft\u0100ah\u31ca\u31d0rrow\xf3\u0feaarpoon\xf3\u0551ightarrows;\u61c9quigarro\xf7\u30cbhreetimes;\u62ccg;\u42daingdotse\xf1\u1f32\u0180ahm\u320d\u3210\u3213r\xf2\u0feaa\xf2\u0551;\u600foust\u0100;a\u321e\u321f\u63b1che\xbb\u321fmid;\u6aee\u0200abpt\u3232\u323d\u3240\u3252\u0100nr\u3237\u323ag;\u67edr;\u61fer\xeb\u1003\u0180afl\u3247\u324a\u324er;\u6986;\uc000\ud835\udd63us;\u6a2eimes;\u6a35\u0100ap\u325d\u3267r\u0100;g\u3263\u3264\u4029t;\u6994olint;\u6a12ar\xf2\u31e3\u0200achq\u327b\u3280\u10bc\u3285quo;\u603ar;\uc000\ud835\udcc7\u0100bu\u30fb\u328ao\u0100;r\u0214\u0213\u0180hir\u3297\u329b\u32a0re\xe5\u31f8mes;\u62cai\u0200;efl\u32aa\u1059\u1821\u32ab\u65b9tri;\u69celuhar;\u6968;\u611e\u0d61\u32d5\u32db\u32df\u332c\u3338\u3371\0\u337a\u33a4\0\0\u33ec\u33f0\0\u3428\u3448\u345a\u34ad\u34b1\u34ca\u34f1\0\u3616\0\0\u3633cute;\u415bqu\xef\u27ba\u0500;Eaceinpsy\u11ed\u32f3\u32f5\u32ff\u3302\u330b\u330f\u331f\u3326\u3329;\u6ab4\u01f0\u32fa\0\u32fc;\u6ab8on;\u4161u\xe5\u11fe\u0100;d\u11f3\u3307il;\u415frc;\u415d\u0180Eas\u3316\u3318\u331b;\u6ab6p;\u6abaim;\u62e9olint;\u6a13i\xed\u1204;\u4441ot\u0180;be\u3334\u1d47\u3335\u62c5;\u6a66\u0380Aacmstx\u3346\u334a\u3357\u335b\u335e\u3363\u336drr;\u61d8r\u0100hr\u3350\u3352\xeb\u2228\u0100;o\u0a36\u0a34t\u803b\xa7\u40a7i;\u403bwar;\u6929m\u0100in\u3369\xf0nu\xf3\xf1t;\u6736r\u0100;o\u3376\u2055\uc000\ud835\udd30\u0200acoy\u3382\u3386\u3391\u33a0rp;\u666f\u0100hy\u338b\u338fcy;\u4449;\u4448rt\u026d\u3399\0\0\u339ci\xe4\u1464ara\xec\u2e6f\u803b\xad\u40ad\u0100gm\u33a8\u33b4ma\u0180;fv\u33b1\u33b2\u33b2\u43c3;\u43c2\u0400;deglnpr\u12ab\u33c5\u33c9\u33ce\u33d6\u33de\u33e1\u33e6ot;\u6a6a\u0100;q\u12b1\u12b0\u0100;E\u33d3\u33d4\u6a9e;\u6aa0\u0100;E\u33db\u33dc\u6a9d;\u6a9fe;\u6246lus;\u6a24arr;\u6972ar\xf2\u113d\u0200aeit\u33f8\u3408\u340f\u3417\u0100ls\u33fd\u3404lsetm\xe9\u336ahp;\u6a33parsl;\u69e4\u0100dl\u1463\u3414e;\u6323\u0100;e\u341c\u341d\u6aaa\u0100;s\u3422\u3423\u6aac;\uc000\u2aac\ufe00\u0180flp\u342e\u3433\u3442tcy;\u444c\u0100;b\u3438\u3439\u402f\u0100;a\u343e\u343f\u69c4r;\u633ff;\uc000\ud835\udd64a\u0100dr\u344d\u0402es\u0100;u\u3454\u3455\u6660it\xbb\u3455\u0180csu\u3460\u3479\u349f\u0100au\u3465\u346fp\u0100;s\u1188\u346b;\uc000\u2293\ufe00p\u0100;s\u11b4\u3475;\uc000\u2294\ufe00u\u0100bp\u347f\u348f\u0180;es\u1197\u119c\u3486et\u0100;e\u1197\u348d\xf1\u119d\u0180;es\u11a8\u11ad\u3496et\u0100;e\u11a8\u349d\xf1\u11ae\u0180;af\u117b\u34a6\u05b0r\u0165\u34ab\u05b1\xbb\u117car\xf2\u1148\u0200cemt\u34b9\u34be\u34c2\u34c5r;\uc000\ud835\udcc8tm\xee\xf1i\xec\u3415ar\xe6\u11be\u0100ar\u34ce\u34d5r\u0100;f\u34d4\u17bf\u6606\u0100an\u34da\u34edight\u0100ep\u34e3\u34eapsilo\xee\u1ee0h\xe9\u2eafs\xbb\u2852\u0280bcmnp\u34fb\u355e\u1209\u358b\u358e\u0480;Edemnprs\u350e\u350f\u3511\u3515\u351e\u3523\u352c\u3531\u3536\u6282;\u6ac5ot;\u6abd\u0100;d\u11da\u351aot;\u6ac3ult;\u6ac1\u0100Ee\u3528\u352a;\u6acb;\u628alus;\u6abfarr;\u6979\u0180eiu\u353d\u3552\u3555t\u0180;en\u350e\u3545\u354bq\u0100;q\u11da\u350feq\u0100;q\u352b\u3528m;\u6ac7\u0100bp\u355a\u355c;\u6ad5;\u6ad3c\u0300;acens\u11ed\u356c\u3572\u3579\u357b\u3326ppro\xf8\u32faurlye\xf1\u11fe\xf1\u11f3\u0180aes\u3582\u3588\u331bppro\xf8\u331aq\xf1\u3317g;\u666a\u0680123;Edehlmnps\u35a9\u35ac\u35af\u121c\u35b2\u35b4\u35c0\u35c9\u35d5\u35da\u35df\u35e8\u35ed\u803b\xb9\u40b9\u803b\xb2\u40b2\u803b\xb3\u40b3;\u6ac6\u0100os\u35b9\u35bct;\u6abeub;\u6ad8\u0100;d\u1222\u35c5ot;\u6ac4s\u0100ou\u35cf\u35d2l;\u67c9b;\u6ad7arr;\u697bult;\u6ac2\u0100Ee\u35e4\u35e6;\u6acc;\u628blus;\u6ac0\u0180eiu\u35f4\u3609\u360ct\u0180;en\u121c\u35fc\u3602q\u0100;q\u1222\u35b2eq\u0100;q\u35e7\u35e4m;\u6ac8\u0100bp\u3611\u3613;\u6ad4;\u6ad6\u0180Aan\u361c\u3620\u362drr;\u61d9r\u0100hr\u3626\u3628\xeb\u222e\u0100;o\u0a2b\u0a29war;\u692alig\u803b\xdf\u40df\u0be1\u3651\u365d\u3660\u12ce\u3673\u3679\0\u367e\u36c2\0\0\0\0\0\u36db\u3703\0\u3709\u376c\0\0\0\u3787\u0272\u3656\0\0\u365bget;\u6316;\u43c4r\xeb\u0e5f\u0180aey\u3666\u366b\u3670ron;\u4165dil;\u4163;\u4442lrec;\u6315r;\uc000\ud835\udd31\u0200eiko\u3686\u369d\u36b5\u36bc\u01f2\u368b\0\u3691e\u01004f\u1284\u1281a\u0180;sv\u3698\u3699\u369b\u43b8ym;\u43d1\u0100cn\u36a2\u36b2k\u0100as\u36a8\u36aeppro\xf8\u12c1im\xbb\u12acs\xf0\u129e\u0100as\u36ba\u36ae\xf0\u12c1rn\u803b\xfe\u40fe\u01ec\u031f\u36c6\u22e7es\u8180\xd7;bd\u36cf\u36d0\u36d8\u40d7\u0100;a\u190f\u36d5r;\u6a31;\u6a30\u0180eps\u36e1\u36e3\u3700\xe1\u2a4d\u0200;bcf\u0486\u36ec\u36f0\u36f4ot;\u6336ir;\u6af1\u0100;o\u36f9\u36fc\uc000\ud835\udd65rk;\u6ada\xe1\u3362rime;\u6034\u0180aip\u370f\u3712\u3764d\xe5\u1248\u0380adempst\u3721\u374d\u3740\u3751\u3757\u375c\u375fngle\u0280;dlqr\u3730\u3731\u3736\u3740\u3742\u65b5own\xbb\u1dbbeft\u0100;e\u2800\u373e\xf1\u092e;\u625cight\u0100;e\u32aa\u374b\xf1\u105aot;\u65ecinus;\u6a3alus;\u6a39b;\u69cdime;\u6a3bezium;\u63e2\u0180cht\u3772\u377d\u3781\u0100ry\u3777\u377b;\uc000\ud835\udcc9;\u4446cy;\u445brok;\u4167\u0100io\u378b\u378ex\xf4\u1777head\u0100lr\u3797\u37a0eftarro\xf7\u084fightarrow\xbb\u0f5d\u0900AHabcdfghlmoprstuw\u37d0\u37d3\u37d7\u37e4\u37f0\u37fc\u380e\u381c\u3823\u3834\u3851\u385d\u386b\u38a9\u38cc\u38d2\u38ea\u38f6r\xf2\u03edar;\u6963\u0100cr\u37dc\u37e2ute\u803b\xfa\u40fa\xf2\u1150r\u01e3\u37ea\0\u37edy;\u445eve;\u416d\u0100iy\u37f5\u37farc\u803b\xfb\u40fb;\u4443\u0180abh\u3803\u3806\u380br\xf2\u13adlac;\u4171a\xf2\u13c3\u0100ir\u3813\u3818sht;\u697e;\uc000\ud835\udd32rave\u803b\xf9\u40f9\u0161\u3827\u3831r\u0100lr\u382c\u382e\xbb\u0957\xbb\u1083lk;\u6580\u0100ct\u3839\u384d\u026f\u383f\0\0\u384arn\u0100;e\u3845\u3846\u631cr\xbb\u3846op;\u630fri;\u65f8\u0100al\u3856\u385acr;\u416b\u80bb\xa8\u0349\u0100gp\u3862\u3866on;\u4173f;\uc000\ud835\udd66\u0300adhlsu\u114b\u3878\u387d\u1372\u3891\u38a0own\xe1\u13b3arpoon\u0100lr\u3888\u388cef\xf4\u382digh\xf4\u382fi\u0180;hl\u3899\u389a\u389c\u43c5\xbb\u13faon\xbb\u389aparrows;\u61c8\u0180cit\u38b0\u38c4\u38c8\u026f\u38b6\0\0\u38c1rn\u0100;e\u38bc\u38bd\u631dr\xbb\u38bdop;\u630eng;\u416fri;\u65f9cr;\uc000\ud835\udcca\u0180dir\u38d9\u38dd\u38e2ot;\u62f0lde;\u4169i\u0100;f\u3730\u38e8\xbb\u1813\u0100am\u38ef\u38f2r\xf2\u38a8l\u803b\xfc\u40fcangle;\u69a7\u0780ABDacdeflnoprsz\u391c\u391f\u3929\u392d\u39b5\u39b8\u39bd\u39df\u39e4\u39e8\u39f3\u39f9\u39fd\u3a01\u3a20r\xf2\u03f7ar\u0100;v\u3926\u3927\u6ae8;\u6ae9as\xe8\u03e1\u0100nr\u3932\u3937grt;\u699c\u0380eknprst\u34e3\u3946\u394b\u3952\u395d\u3964\u3996app\xe1\u2415othin\xe7\u1e96\u0180hir\u34eb\u2ec8\u3959op\xf4\u2fb5\u0100;h\u13b7\u3962\xef\u318d\u0100iu\u3969\u396dgm\xe1\u33b3\u0100bp\u3972\u3984setneq\u0100;q\u397d\u3980\uc000\u228a\ufe00;\uc000\u2acb\ufe00setneq\u0100;q\u398f\u3992\uc000\u228b\ufe00;\uc000\u2acc\ufe00\u0100hr\u399b\u399fet\xe1\u369ciangle\u0100lr\u39aa\u39afeft\xbb\u0925ight\xbb\u1051y;\u4432ash\xbb\u1036\u0180elr\u39c4\u39d2\u39d7\u0180;be\u2dea\u39cb\u39cfar;\u62bbq;\u625alip;\u62ee\u0100bt\u39dc\u1468a\xf2\u1469r;\uc000\ud835\udd33tr\xe9\u39aesu\u0100bp\u39ef\u39f1\xbb\u0d1c\xbb\u0d59pf;\uc000\ud835\udd67ro\xf0\u0efbtr\xe9\u39b4\u0100cu\u3a06\u3a0br;\uc000\ud835\udccb\u0100bp\u3a10\u3a18n\u0100Ee\u3980\u3a16\xbb\u397en\u0100Ee\u3992\u3a1e\xbb\u3990igzag;\u699a\u0380cefoprs\u3a36\u3a3b\u3a56\u3a5b\u3a54\u3a61\u3a6airc;\u4175\u0100di\u3a40\u3a51\u0100bg\u3a45\u3a49ar;\u6a5fe\u0100;q\u15fa\u3a4f;\u6259erp;\u6118r;\uc000\ud835\udd34pf;\uc000\ud835\udd68\u0100;e\u1479\u3a66at\xe8\u1479cr;\uc000\ud835\udccc\u0ae3\u178e\u3a87\0\u3a8b\0\u3a90\u3a9b\0\0\u3a9d\u3aa8\u3aab\u3aaf\0\0\u3ac3\u3ace\0\u3ad8\u17dc\u17dftr\xe9\u17d1r;\uc000\ud835\udd35\u0100Aa\u3a94\u3a97r\xf2\u03c3r\xf2\u09f6;\u43be\u0100Aa\u3aa1\u3aa4r\xf2\u03b8r\xf2\u09eba\xf0\u2713is;\u62fb\u0180dpt\u17a4\u3ab5\u3abe\u0100fl\u3aba\u17a9;\uc000\ud835\udd69im\xe5\u17b2\u0100Aa\u3ac7\u3acar\xf2\u03cer\xf2\u0a01\u0100cq\u3ad2\u17b8r;\uc000\ud835\udccd\u0100pt\u17d6\u3adcr\xe9\u17d4\u0400acefiosu\u3af0\u3afd\u3b08\u3b0c\u3b11\u3b15\u3b1b\u3b21c\u0100uy\u3af6\u3afbte\u803b\xfd\u40fd;\u444f\u0100iy\u3b02\u3b06rc;\u4177;\u444bn\u803b\xa5\u40a5r;\uc000\ud835\udd36cy;\u4457pf;\uc000\ud835\udd6acr;\uc000\ud835\udcce\u0100cm\u3b26\u3b29y;\u444el\u803b\xff\u40ff\u0500acdefhiosw\u3b42\u3b48\u3b54\u3b58\u3b64\u3b69\u3b6d\u3b74\u3b7a\u3b80cute;\u417a\u0100ay\u3b4d\u3b52ron;\u417e;\u4437ot;\u417c\u0100et\u3b5d\u3b61tr\xe6\u155fa;\u43b6r;\uc000\ud835\udd37cy;\u4436grarr;\u61ddpf;\uc000\ud835\udd6bcr;\uc000\ud835\udccf\u0100jn\u3b85\u3b87;\u600dj;\u600c'.split("").map((t=>t.charCodeAt(0)))),w=new Uint16Array("\u0200aglq\t\x15\x18\x1b\u026d\x0f\0\0\x12p;\u4026os;\u4027t;\u403et;\u403cuot;\u4022".split("").map((t=>t.charCodeAt(0))));const v=new Map([[0,65533],[128,8364],[130,8218],[131,402],[132,8222],[133,8230],[134,8224],[135,8225],[136,710],[137,8240],[138,352],[139,8249],[140,338],[142,381],[145,8216],[146,8217],[147,8220],[148,8221],[149,8226],[150,8211],[151,8212],[152,732],[153,8482],[154,353],[155,8250],[156,339],[158,382],[159,376]]),z=null!==(k=String.fromCodePoint)&&void 0!==k?k:function(t){let e="";return t>65535&&(t-=65536,e+=String.fromCharCode(t>>>10&1023|55296),t=56320|1023&t),e+=String.fromCharCode(t),e};var S;!function(t){t[t.NUM=35]="NUM",t[t.SEMI=59]="SEMI",t[t.EQUALS=61]="EQUALS",t[t.ZERO=48]="ZERO",t[t.NINE=57]="NINE",t[t.LOWER_A=97]="LOWER_A",t[t.LOWER_F=102]="LOWER_F",t[t.LOWER_X=120]="LOWER_X",t[t.LOWER_Z=122]="LOWER_Z",t[t.UPPER_A=65]="UPPER_A",t[t.UPPER_F=70]="UPPER_F",t[t.UPPER_Z=90]="UPPER_Z"}(S||(S={}));var q,B,L;function I(t){return t>=S.ZERO&&t<=S.NINE}function M(t){return t>=S.UPPER_A&&t<=S.UPPER_F||t>=S.LOWER_A&&t<=S.LOWER_F}function T(t){return t===S.EQUALS||function(t){return t>=S.UPPER_A&&t<=S.UPPER_Z||t>=S.LOWER_A&&t<=S.LOWER_Z||I(t)}(t)}!function(t){t[t.VALUE_LENGTH=49152]="VALUE_LENGTH",t[t.BRANCH_LENGTH=16256]="BRANCH_LENGTH",t[t.JUMP_TABLE=127]="JUMP_TABLE"}(q||(q={})),function(t){t[t.EntityStart=0]="EntityStart",t[t.NumericStart=1]="NumericStart",t[t.NumericDecimal=2]="NumericDecimal",t[t.NumericHex=3]="NumericHex",t[t.NamedEntity=4]="NamedEntity"}(B||(B={})),function(t){t[t.Legacy=0]="Legacy",t[t.Strict=1]="Strict",t[t.Attribute=2]="Attribute"}(L||(L={}));class R{constructor(t,e,r){this.decodeTree=t,this.emitCodePoint=e,this.errors=r,this.state=B.EntityStart,this.consumed=1,this.result=0,this.treeIndex=0,this.excess=1,this.decodeMode=L.Strict}startEntity(t){this.decodeMode=t,this.state=B.EntityStart,this.result=0,this.treeIndex=0,this.excess=1,this.consumed=1}write(t,e){switch(this.state){case B.EntityStart:return t.charCodeAt(e)===S.NUM?(this.state=B.NumericStart,this.consumed+=1,this.stateNumericStart(t,e+1)):(this.state=B.NamedEntity,this.stateNamedEntity(t,e));case B.NumericStart:return this.stateNumericStart(t,e);case B.NumericDecimal:return this.stateNumericDecimal(t,e);case B.NumericHex:return this.stateNumericHex(t,e);case B.NamedEntity:return this.stateNamedEntity(t,e)}}stateNumericStart(t,e){return e>=t.length?-1:(32|t.charCodeAt(e))===S.LOWER_X?(this.state=B.NumericHex,this.consumed+=1,this.stateNumericHex(t,e+1)):(this.state=B.NumericDecimal,this.stateNumericDecimal(t,e))}addToNumericResult(t,e,r,n){if(e!==r){const s=r-e;this.result=this.result*Math.pow(n,s)+parseInt(t.substr(e,s),n),this.consumed+=s}}stateNumericHex(t,e){const r=e;for(;e=55296&&t<=57343||t>1114111?65533:null!==(e=v.get(t))&&void 0!==e?e:t}(this.result),this.consumed),this.errors&&(t!==S.SEMI&&this.errors.missingSemicolonAfterCharacterReference(),this.errors.validateNumericCharacterReference(this.result)),this.consumed}stateNamedEntity(t,e){const{decodeTree:r}=this;let n=r[this.treeIndex],s=(n&q.VALUE_LENGTH)>>14;for(;e>14,0!==s){if(i===S.SEMI)return this.emitNamedEntityData(this.treeIndex,s,this.consumed+this.excess);this.decodeMode!==L.Strict&&(this.result=this.treeIndex,this.consumed+=this.excess,this.excess=0)}}return-1}emitNotTerminatedNamedEntity(){var t;const{result:e,decodeTree:r}=this,n=(r[e]&q.VALUE_LENGTH)>>14;return this.emitNamedEntityData(e,n,this.consumed),null===(t=this.errors)||void 0===t||t.missingSemicolonAfterCharacterReference(),this.consumed}emitNamedEntityData(t,e,r){const{decodeTree:n}=this;return this.emitCodePoint(1===e?n[t]&~q.VALUE_LENGTH:n[t+1],r),3===e&&this.emitCodePoint(n[t+2],r),r}end(){var t;switch(this.state){case B.NamedEntity:return 0===this.result||this.decodeMode===L.Attribute&&this.result!==this.treeIndex?0:this.emitNotTerminatedNamedEntity();case B.NumericDecimal:return this.emitNumericEntity(0,2);case B.NumericHex:return this.emitNumericEntity(0,3);case B.NumericStart:return null===(t=this.errors)||void 0===t||t.absenceOfDigitsInNumericCharacterReference(this.consumed),0;case B.EntityStart:return 0}}}function N(t){let e="";const r=new R(t,(t=>e+=z(t)));return function(t,n){let s=0,i=0;for(;(i=t.indexOf("&",i))>=0;){e+=t.slice(s,i),r.startEntity(n);const o=r.write(t,i+1);if(o<0){s=i+r.end();break}s=i+o,i=0===o?s+1:s}const o=e+t.slice(s);return e="",o}}function P(t,e,r,n){const s=(e&q.BRANCH_LENGTH)>>7,i=e&q.JUMP_TABLE;if(0===s)return 0!==i&&n===i?r:-1;if(i){const e=n-i;return e<0||e>=s?-1:t[r+e]-1}let o=r,u=o+s-1;for(;o<=u;){const e=o+u>>>1,r=t[e];if(rn))return t[e+s];u=e-1}}return-1}const O=N(x);function j(t,e=L.Legacy){return O(t,e)}function Z(t){return"[object String]"===function(t){return Object.prototype.toString.call(t)}(t)}N(w);const $=Object.prototype.hasOwnProperty;function U(t){return Array.prototype.slice.call(arguments,1).forEach((function(e){if(e){if("object"!=typeof e)throw new TypeError(e+"must be object");Object.keys(e).forEach((function(r){t[r]=e[r]}))}})),t}function H(t,e,r){return[].concat(t.slice(0,e),r,t.slice(e+1))}function V(t){return!(t>=55296&&t<=57343)&&(!(t>=64976&&t<=65007)&&(!!(65535&~t&&65534!=(65535&t))&&(!(t>=0&&t<=8)&&(11!==t&&(!(t>=14&&t<=31)&&(!(t>=127&&t<=159)&&!(t>1114111)))))))}function G(t){if(t>65535){const e=55296+((t-=65536)>>10),r=56320+(1023&t);return String.fromCharCode(e,r)}return String.fromCharCode(t)}const W=/\\([!"#$%&'()*+,\-./:;<=>?@[\\\]^_`{|}~])/g,J=new RegExp(W.source+"|"+/&([a-z#][a-z0-9]{1,31});/gi.source,"gi"),Q=/^#((?:x[a-f0-9]{1,8}|[0-9]{1,8}))$/i;function X(t){return t.indexOf("\\")<0&&t.indexOf("&")<0?t:t.replace(J,(function(t,e,r){return e||function(t,e){if(35===e.charCodeAt(0)&&Q.test(e)){const r="x"===e[1].toLowerCase()?parseInt(e.slice(2),16):parseInt(e.slice(1),10);return V(r)?G(r):t}const r=j(t);return r!==t?r:t}(t,r)}))}const Y=/[&<>"]/,K=/[&<>"]/g,tt={"&":"&","<":"<",">":">",'"':"""};function et(t){return tt[t]}function rt(t){return Y.test(t)?t.replace(K,et):t}const nt=/[.?*+^$[\]\\(){}|-]/g;function st(t){switch(t){case 9:case 32:return!0}return!1}function it(t){if(t>=8192&&t<=8202)return!0;switch(t){case 9:case 10:case 11:case 12:case 13:case 32:case 160:case 5760:case 8239:case 8287:case 12288:return!0}return!1}function ot(t){return E.test(t)||A.test(t)}function ut(t){switch(t){case 33:case 34:case 35:case 36:case 37:case 38:case 39:case 40:case 41:case 42:case 43:case 44:case 45:case 46:case 47:case 58:case 59:case 60:case 61:case 62:case 63:case 64:case 91:case 92:case 93:case 94:case 95:case 96:case 123:case 124:case 125:case 126:return!0;default:return!1}}function ct(t){return t=t.trim().replace(/\s+/g," "),"\u1e7e"==="\u1e9e".toLowerCase()&&(t=t.replace(/\u1e9e/g,"\xdf")),t.toLowerCase().toUpperCase()}const at={mdurl:D,ucmicro:F};var lt=Object.freeze({__proto__:null,arrayReplaceAt:H,assign:U,escapeHtml:rt,escapeRE:function(t){return t.replace(nt,"\\$&")},fromCodePoint:G,has:function(t,e){return $.call(t,e)},isMdAsciiPunct:ut,isPunctChar:ot,isSpace:st,isString:Z,isValidEntityCode:V,isWhiteSpace:it,lib:at,normalizeReference:ct,unescapeAll:X,unescapeMd:function(t){return t.indexOf("\\")<0?t:t.replace(W,"$1")}});var ht=Object.freeze({__proto__:null,parseLinkDestination:function(t,e,r){let n,s=e;const i={ok:!1,pos:0,str:""};if(60===t.charCodeAt(s)){for(s++;s32))return i;if(41===n){if(0===o)break;o--}s++}return e===s||0!==o||(i.str=X(t.slice(e,s)),i.pos=s,i.ok=!0),i},parseLinkLabel:function(t,e,r){let n,s,i,o;const u=t.posMax,c=t.pos;for(t.pos=e+1,n=1;t.pos=r)return o;let n=t.charCodeAt(i);if(34!==n&&39!==n&&40!==n)return o;e++,i++,40===n&&(n=41),o.marker=n}for(;i"+rt(i.content)+""},pt.code_block=function(t,e,r,n,s){const i=t[e];return""+rt(t[e].content)+"\n"},pt.fence=function(t,e,r,n,s){const i=t[e],o=i.info?X(i.info).trim():"";let u,c="",a="";if(o){const t=o.split(/(\s+)/g);c=t[0],a=t.slice(2).join("")}if(u=r.highlight&&r.highlight(i.content,c,a)||rt(i.content),0===u.indexOf("${u}\n`}return`

    ${u}
    \n`},pt.image=function(t,e,r,n,s){const i=t[e];return i.attrs[i.attrIndex("alt")][1]=s.renderInlineAsText(i.children,r,n),s.renderToken(t,e,r)},pt.hardbreak=function(t,e,r){return r.xhtmlOut?"
    \n":"
    \n"},pt.softbreak=function(t,e,r){return r.breaks?r.xhtmlOut?"
    \n":"
    \n":"\n"},pt.text=function(t,e){return rt(t[e].content)},pt.html_block=function(t,e){return t[e].content},pt.html_inline=function(t,e){return t[e].content},ft.prototype.renderAttrs=function(t){let e,r,n;if(!t.attrs)return"";for(n="",e=0,r=t.attrs.length;e\n":">",s},ft.prototype.renderInline=function(t,e,r){let n="";const s=this.rules;for(let i=0,o=t.length;i=0&&(r=this.attrs[e][1]),r},_t.prototype.attrJoin=function(t,e){const r=this.attrIndex(t);r<0?this.attrPush([t,e]):this.attrs[r][1]=this.attrs[r][1]+" "+e},mt.prototype.Token=_t;const gt=/\r\n?|\n/g,kt=/\0/g;function Dt(t){return/^<\/a\s*>/i.test(t)}const Ct=/\+-|\.\.|\?\?\?\?|!!!!|,,|--/,yt=/\((c|tm|r)\)/i,Et=/\((c|tm|r)\)/gi,At={c:"\xa9",r:"\xae",tm:"\u2122"};function bt(t,e){return At[e.toLowerCase()]}function Ft(t){let e=0;for(let r=t.length-1;r>=0;r--){const n=t[r];"text"!==n.type||e||(n.content=n.content.replace(Et,bt)),"link_open"===n.type&&"auto"===n.info&&e--,"link_close"===n.type&&"auto"===n.info&&e++}}function xt(t){let e=0;for(let r=t.length-1;r>=0;r--){const n=t[r];"text"!==n.type||e||Ct.test(n.content)&&(n.content=n.content.replace(/\+-/g,"\xb1").replace(/\.{2,}/g,"\u2026").replace(/([?!])\u2026/g,"$1..").replace(/([?!]){4,}/g,"$1$1$1").replace(/,{2,}/g,",").replace(/(^|[^-])---(?=[^-]|$)/gm,"$1\u2014").replace(/(^|\s)--(?=\s|$)/gm,"$1\u2013").replace(/(^|[^-\s])--(?=[^-\s]|$)/gm,"$1\u2013")),"link_open"===n.type&&"auto"===n.info&&e--,"link_close"===n.type&&"auto"===n.info&&e++}}const wt=/['"]/,vt=/['"]/g,zt="\u2019";function St(t,e,r){return t.slice(0,e)+r+t.slice(e+1)}function qt(t,e){let r;const n=[];for(let s=0;s=0&&!(n[r].level<=o);r--);if(n.length=r+1,"text"!==i.type)continue;let u=i.content,c=0,a=u.length;t:for(;c=0)d=u.charCodeAt(l.index-1);else for(r=s-1;r>=0&&("softbreak"!==t[r].type&&"hardbreak"!==t[r].type);r--)if(t[r].content){d=t[r].content.charCodeAt(t[r].content.length-1);break}let _=32;if(c=48&&d<=57&&(p=h=!1),h&&p&&(h=m,p=g),h||p){if(p)for(r=n.length-1;r>=0;r--){let h=n[r];if(n[r].level=0;o--){const u=s[o];if("link_close"!==u.type){if("html_inline"===u.type&&(r=u.content,/^\s]/i.test(r)&&i>0&&i--,Dt(u.content)&&i++),!(i>0)&&"text"===u.type&&t.md.linkify.test(u.content)){const r=u.content;let i=t.md.linkify.match(r);const c=[];let a=u.level,l=0;i.length>0&&0===i[0].index&&o>0&&"text_special"===s[o-1].type&&(i=i.slice(1));for(let e=0;el){const e=new t.Token("text","",0);e.content=r.slice(l,u),e.level=a,c.push(e)}const h=new t.Token("link_open","a",1);h.attrs=[["href",s]],h.level=a++,h.markup="linkify",h.info="auto",c.push(h);const p=new t.Token("text","",0);p.content=o,p.level=a,c.push(p);const f=new t.Token("link_close","a",-1);f.level=--a,f.markup="linkify",f.info="auto",c.push(f),l=i[e].lastIndex}if(l=0;e--)"inline"===t.tokens[e].type&&(yt.test(t.tokens[e].content)&&Ft(t.tokens[e].children),Ct.test(t.tokens[e].content)&&xt(t.tokens[e].children))}],["smartquotes",function(t){if(t.md.options.typographer)for(let e=t.tokens.length-1;e>=0;e--)"inline"===t.tokens[e].type&&wt.test(t.tokens[e].content)&&qt(t.tokens[e].children,t)}],["text_join",function(t){let e,r;const n=t.tokens,s=n.length;for(let t=0;t0&&this.level++,this.tokens.push(n),n},It.prototype.isEmpty=function(t){return this.bMarks[t]+this.tShift[t]>=this.eMarks[t]},It.prototype.skipEmptyLines=function(t){for(let e=this.lineMax;te;)if(!st(this.src.charCodeAt(--t)))return t+1;return t},It.prototype.skipChars=function(t,e){for(let r=this.src.length;tr;)if(e!==this.src.charCodeAt(--t))return t+1;return t},It.prototype.getLines=function(t,e,r,n){if(t>=e)return"";const s=new Array(e-t);for(let i=0,o=t;or?new Array(t-r+1).join(" ")+this.src.slice(a,c):this.src.slice(a,c)}return s.join("")},It.prototype.Token=_t;function Mt(t,e){const r=t.bMarks[e]+t.tShift[e],n=t.eMarks[e];return t.src.slice(r,n)}function Tt(t){const e=[],r=t.length;let n=0,s=t.charCodeAt(n),i=!1,o=0,u="";for(;n=n)return-1;let i=t.src.charCodeAt(s++);if(i<48||i>57)return-1;for(;;){if(s>=n)return-1;if(i=t.src.charCodeAt(s++),!(i>=48&&i<=57)){if(41===i||46===i)break;return-1}if(s-r>=10)return-1}return s`\\x00-\\x20]+|'[^']*'|\"[^\"]*\"))?)*\\s*\\/?>",Ot="<\\/[A-Za-z][A-Za-z0-9\\-]*\\s*>",jt=new RegExp("^(?:"+Pt+"|"+Ot+"|\x3c!---?>|\x3c!--(?:[^-]|-[^-]|--[^>])*--\x3e|<[?][\\s\\S]*?[?]>|]*>|)"),Zt=new RegExp("^(?:"+Pt+"|"+Ot+")"),$t=[[/^<(script|pre|style|textarea)(?=(\s|>|$))/i,/<\/(script|pre|style|textarea)>/i,!0],[/^/,!0],[/^<\?/,/\?>/,!0],[/^/,!0],[/^/,!0],[new RegExp("^|$))","i"),/^$/,!0],[new RegExp(Zt.source+"\\s*$"),/^$/,!1]];const Ut=[["table",function(t,e,r,n){if(e+2>r)return!1;let s=e+1;if(t.sCount[s]=4)return!1;let i=t.bMarks[s]+t.tShift[s];if(i>=t.eMarks[s])return!1;const o=t.src.charCodeAt(i++);if(124!==o&&45!==o&&58!==o)return!1;if(i>=t.eMarks[s])return!1;const u=t.src.charCodeAt(i++);if(124!==u&&45!==u&&58!==u&&!st(u))return!1;if(45===o&&st(u))return!1;for(;i=4)return!1;a=Tt(c),a.length&&""===a[0]&&a.shift(),a.length&&""===a[a.length-1]&&a.pop();const h=a.length;if(0===h||h!==l.length)return!1;if(n)return!0;const p=t.parentType;t.parentType="table";const f=t.md.block.ruler.getRules("blockquote"),d=[e,0];t.push("table_open","table",1).map=d,t.push("thead_open","thead",1).map=[e,e+1],t.push("tr_open","tr",1).map=[e,e+1];for(let e=0;e=4)break;if(a=Tt(c),a.length&&""===a[0]&&a.shift(),a.length&&""===a[a.length-1]&&a.pop(),m+=h-a.length,m>65536)break;if(s===e+2){t.push("tbody_open","tbody",1).map=_=[e+2,0]}t.push("tr_open","tr",1).map=[s,s+1];for(let e=0;e=4))break;n++,s=n}t.line=s;const i=t.push("code_block","code",0);return i.content=t.getLines(e,s,4+t.blkIndent,!1)+"\n",i.map=[e,t.line],!0}],["fence",function(t,e,r,n){let s=t.bMarks[e]+t.tShift[e],i=t.eMarks[e];if(t.sCount[e]-t.blkIndent>=4)return!1;if(s+3>i)return!1;const o=t.src.charCodeAt(s);if(126!==o&&96!==o)return!1;let u=s;s=t.skipChars(s,o);let c=s-u;if(c<3)return!1;const a=t.src.slice(u,s),l=t.src.slice(s,i);if(96===o&&l.indexOf(String.fromCharCode(o))>=0)return!1;if(n)return!0;let h=e,p=!1;for(;(h++,!(h>=r))&&(s=u=t.bMarks[h]+t.tShift[h],i=t.eMarks[h],!(s=4||(s=t.skipChars(s,o),s-u=4)return!1;if(62!==t.src.charCodeAt(s))return!1;if(n)return!0;const u=[],c=[],a=[],l=[],h=t.md.block.ruler.getRules("blockquote"),p=t.parentType;t.parentType="blockquote";let f,d=!1;for(f=e;f=i)break;if(62===t.src.charCodeAt(s++)&&!e){let e,r,n=t.sCount[f]+1;32===t.src.charCodeAt(s)?(s++,n++,r=!1,e=!0):9===t.src.charCodeAt(s)?(e=!0,(t.bsCount[f]+n)%4==3?(s++,n++,r=!1):r=!0):e=!1;let o=n;for(u.push(t.bMarks[f]),t.bMarks[f]=s;s=i,c.push(t.bsCount[f]),t.bsCount[f]=t.sCount[f]+1+(e?1:0),a.push(t.sCount[f]),t.sCount[f]=o-n,l.push(t.tShift[f]),t.tShift[f]=s-t.bMarks[f];continue}if(d)break;let n=!1;for(let e=0,s=h.length;e";const g=[e,0];m.map=g,t.md.block.tokenize(t,e,f),t.push("blockquote_close","blockquote",-1).markup=">",t.lineMax=o,t.parentType=p,g[1]=t.line;for(let r=0;r=4)return!1;let i=t.bMarks[e]+t.tShift[e];const o=t.src.charCodeAt(i++);if(42!==o&&45!==o&&95!==o)return!1;let u=1;for(;i=4)return!1;if(t.listIndent>=0&&t.sCount[c]-t.listIndent>=4&&t.sCount[c]=t.blkIndent&&(f=!0),(p=Nt(t,c))>=0){if(l=!0,o=t.bMarks[c]+t.tShift[c],h=Number(t.src.slice(o,p-1)),f&&1!==h)return!1}else{if(!((p=Rt(t,c))>=0))return!1;l=!1}if(f&&t.skipSpaces(p)>=t.eMarks[c])return!1;if(n)return!0;const d=t.src.charCodeAt(p-1),_=t.tokens.length;l?(u=t.push("ordered_list_open","ol",1),1!==h&&(u.attrs=[["start",h]])):u=t.push("bullet_list_open","ul",1);const m=[c,0];u.map=m,u.markup=String.fromCharCode(d);let g=!1;const k=t.md.block.ruler.getRules("list"),D=t.parentType;for(t.parentType="list";c=s?1:n-e,f>4&&(f=1);const _=e+f;u=t.push("list_item_open","li",1),u.markup=String.fromCharCode(d);const m=[c,0];u.map=m,l&&(u.info=t.src.slice(o,p-1));const D=t.tight,C=t.tShift[c],y=t.sCount[c],E=t.listIndent;if(t.listIndent=t.blkIndent,t.blkIndent=_,t.tight=!0,t.tShift[c]=h-t.bMarks[c],t.sCount[c]=n,h>=s&&t.isEmpty(c+1)?t.line=Math.min(t.line+2,r):t.md.block.tokenize(t,c,r,!0),t.tight&&!g||(a=!1),g=t.line-c>1&&t.isEmpty(t.line-1),t.blkIndent=t.listIndent,t.listIndent=E,t.tShift[c]=C,t.sCount[c]=y,t.tight=D,u=t.push("list_item_close","li",-1),u.markup=String.fromCharCode(d),c=t.line,m[1]=c,c>=r)break;if(t.sCount[c]=4)break;let A=!1;for(let e=0,n=k.length;e=4)return!1;if(91!==t.src.charCodeAt(s))return!1;function u(e){const r=t.lineMax;if(e>=r||t.isEmpty(e))return null;let n=!1;if(t.sCount[e]-t.blkIndent>3&&(n=!0),t.sCount[e]<0&&(n=!0),!n){const n=t.md.block.ruler.getRules("reference"),s=t.parentType;t.parentType="reference";let i=!1;for(let s=0,o=n.length;s=4)return!1;if(!t.md.options.html)return!1;if(60!==t.src.charCodeAt(s))return!1;let o=t.src.slice(s,i),u=0;for(;u<$t.length&&!$t[u][0].test(o);u++);if(u===$t.length)return!1;if(n)return $t[u][2];let c=e+1;if(!$t[u][1].test(o))for(;c=4)return!1;let o=t.src.charCodeAt(s);if(35!==o||s>=i)return!1;let u=1;for(o=t.src.charCodeAt(++s);35===o&&s6||ss&&st(t.src.charCodeAt(c-1))&&(i=c),t.line=e+1;const a=t.push("heading_open","h"+String(u),1);a.markup="########".slice(0,u),a.map=[e,t.line];const l=t.push("inline","",0);return l.content=t.src.slice(s,i).trim(),l.map=[e,t.line],l.children=[],t.push("heading_close","h"+String(u),-1).markup="########".slice(0,u),!0},["paragraph","reference","blockquote"]],["lheading",function(t,e,r){const n=t.md.block.ruler.getRules("paragraph");if(t.sCount[e]-t.blkIndent>=4)return!1;const s=t.parentType;t.parentType="paragraph";let i,o=0,u=e+1;for(;u3)continue;if(t.sCount[u]>=t.blkIndent){let e=t.bMarks[u]+t.tShift[u];const r=t.eMarks[u];if(e=r))){o=61===i?1:2;break}}if(t.sCount[u]<0)continue;let e=!1;for(let s=0,i=n.length;s3)continue;if(t.sCount[i]<0)continue;let e=!1;for(let s=0,o=n.length;s=r))&&!(t.sCount[o]=i){t.line=r;break}const e=t.line;let c=!1;for(let i=0;i=t.line)throw new Error("block rule didn't increment state.line");break}if(!c)throw new Error("none of the block rules matched");t.tight=!u,t.isEmpty(t.line-1)&&(u=!0),o=t.line,o0&&(this.level++,this._prev_delimiters.push(this.delimiters),this.delimiters=[],s={delimiters:this.delimiters}),this.pendingLevel=this.level,this.tokens.push(n),this.tokens_meta.push(s),n},Vt.prototype.scanDelims=function(t,e){const r=this.posMax,n=this.src.charCodeAt(t),s=t>0?this.src.charCodeAt(t-1):32;let i=t;for(;i?@[]^_`{|}~-".split("").forEach((function(t){Jt[t.charCodeAt(0)]=1}));var Xt={tokenize:function(t,e){const r=t.pos,n=t.src.charCodeAt(r);if(e)return!1;if(126!==n)return!1;const s=t.scanDelims(t.pos,!0);let i=s.length;const o=String.fromCharCode(n);if(i<2)return!1;let u;i%2&&(u=t.push("text","",0),u.content=o,i--);for(let e=0;e=0;r--){const n=e[r];if(95!==n.marker&&42!==n.marker)continue;if(-1===n.end)continue;const s=e[n.end],i=r>0&&e[r-1].end===n.end+1&&e[r-1].marker===n.marker&&e[r-1].token===n.token-1&&e[n.end+1].token===s.token+1,o=String.fromCharCode(n.marker),u=t.tokens[n.token];u.type=i?"strong_open":"em_open",u.tag=i?"strong":"em",u.nesting=1,u.markup=i?o+o:o,u.content="";const c=t.tokens[s.token];c.type=i?"strong_close":"em_close",c.tag=i?"strong":"em",c.nesting=-1,c.markup=i?o+o:o,c.content="",i&&(t.tokens[e[r-1].token].content="",t.tokens[e[n.end+1].token].content="",r--)}}var Kt={tokenize:function(t,e){const r=t.pos,n=t.src.charCodeAt(r);if(e)return!1;if(95!==n&&42!==n)return!1;const s=t.scanDelims(t.pos,42===n);for(let e=0;e\x00-\x20]*)$/;const re=/^&#((?:x[a-f0-9]{1,6}|[0-9]{1,7}));/i,ne=/^&([a-z][a-z0-9]{1,31});/i;function se(t){const e={},r=t.length;if(!r)return;let n=0,s=-2;const i=[];for(let o=0;ou;c-=i[c]+1){const e=t[c];if(e.marker===r.marker&&(e.open&&e.end<0)){let n=!1;if((e.close||r.open)&&(e.length+r.length)%3==0&&(e.length%3==0&&r.length%3==0||(n=!0)),!n){const n=c>0&&!t[c-1].open?i[c-1]+1:0;i[o]=o-c+n,i[c]=n,r.open=!1,e.end=o,e.close=!1,a=-1,s=-2;break}}}-1!==a&&(e[r.marker][(r.open?3:0)+(r.length||0)%3]=a)}}const ie=[["text",function(t,e){let r=t.pos;for(;r0)return!1;const r=t.pos;if(r+3>t.posMax)return!1;if(58!==t.src.charCodeAt(r))return!1;if(47!==t.src.charCodeAt(r+1))return!1;if(47!==t.src.charCodeAt(r+2))return!1;const n=t.pending.match(Wt);if(!n)return!1;const s=n[1],i=t.md.linkify.matchAtStart(t.src.slice(r-s.length));if(!i)return!1;let o=i.url;if(o.length<=s.length)return!1;o=o.replace(/\*+$/,"");const u=t.md.normalizeLink(o);if(!t.md.validateLink(u))return!1;if(!e){t.pending=t.pending.slice(0,-s.length);const e=t.push("link_open","a",1);e.attrs=[["href",u]],e.markup="linkify",e.info="auto";t.push("text","",0).content=t.md.normalizeLinkText(o);const r=t.push("link_close","a",-1);r.markup="linkify",r.info="auto"}return t.pos+=o.length-s.length,!0}],["newline",function(t,e){let r=t.pos;if(10!==t.src.charCodeAt(r))return!1;const n=t.pending.length-1,s=t.posMax;if(!e)if(n>=0&&32===t.pending.charCodeAt(n))if(n>=1&&32===t.pending.charCodeAt(n-1)){let e=n-1;for(;e>=1&&32===t.pending.charCodeAt(e-1);)e--;t.pending=t.pending.slice(0,e),t.push("hardbreak","br",0)}else t.pending=t.pending.slice(0,-1),t.push("softbreak","br",0);else t.push("softbreak","br",0);for(r++;r=n)return!1;let s=t.src.charCodeAt(r);if(10===s){for(e||t.push("hardbreak","br",0),r++;r=55296&&s<=56319&&r+1=56320&&e<=57343&&(i+=t.src[r+1],r++)}const o="\\"+i;if(!e){const e=t.push("text_special","",0);s<256&&0!==Jt[s]?e.content=i:e.content=o,e.markup=o,e.info="escape"}return t.pos=r+1,!0}],["backticks",function(t,e){let r=t.pos;if(96!==t.src.charCodeAt(r))return!1;const n=r;r++;const s=t.posMax;for(;r=h)return!1;if(c=d,s=t.md.helpers.parseLinkDestination(t.src,d,t.posMax),s.ok){for(o=t.md.normalizeLink(s.str),t.md.validateLink(o)?d=s.pos:o="",c=d;d=h||41!==t.src.charCodeAt(d))&&(a=!0),d++}if(a){if(void 0===t.env.references)return!1;if(d=0?n=t.src.slice(c,d++):d=f+1):d=f+1,n||(n=t.src.slice(p,f)),i=t.env.references[ct(n)],!i)return t.pos=l,!1;o=i.href,u=i.title}if(!e){t.pos=p,t.posMax=f;const e=[["href",o]];t.push("link_open","a",1).attrs=e,u&&e.push(["title",u]),t.linkLevel++,t.md.inline.tokenize(t),t.linkLevel--,t.push("link_close","a",-1)}return t.pos=d,t.posMax=h,!0}],["image",function(t,e){let r,n,s,i,o,u,c,a,l="";const h=t.pos,p=t.posMax;if(33!==t.src.charCodeAt(t.pos))return!1;if(91!==t.src.charCodeAt(t.pos+1))return!1;const f=t.pos+2,d=t.md.helpers.parseLinkLabel(t,t.pos+1,!1);if(d<0)return!1;if(i=d+1,i=p)return!1;for(a=i,u=t.md.helpers.parseLinkDestination(t.src,i,t.posMax),u.ok&&(l=t.md.normalizeLink(u.str),t.md.validateLink(l)?i=u.pos:l=""),a=i;i=p||41!==t.src.charCodeAt(i))return t.pos=h,!1;i++}else{if(void 0===t.env.references)return!1;if(i=0?s=t.src.slice(a,i++):i=d+1):i=d+1,s||(s=t.src.slice(f,d)),o=t.env.references[ct(s)],!o)return t.pos=h,!1;l=o.href,c=o.title}if(!e){n=t.src.slice(f,d);const e=[];t.md.inline.parse(n,t.md,t.env,e);const r=t.push("image","img",0),s=[["src",l],["alt",""]];r.attrs=s,r.children=e,r.content=n,c&&s.push(["title",c])}return t.pos=i,t.posMax=p,!0}],["autolink",function(t,e){let r=t.pos;if(60!==t.src.charCodeAt(r))return!1;const n=t.pos,s=t.posMax;for(;;){if(++r>=s)return!1;const e=t.src.charCodeAt(r);if(60===e)return!1;if(62===e)break}const i=t.src.slice(n+1,r);if(ee.test(i)){const r=t.md.normalizeLink(i);if(!t.md.validateLink(r))return!1;if(!e){const e=t.push("link_open","a",1);e.attrs=[["href",r]],e.markup="autolink",e.info="auto";t.push("text","",0).content=t.md.normalizeLinkText(i);const n=t.push("link_close","a",-1);n.markup="autolink",n.info="auto"}return t.pos+=i.length+2,!0}if(te.test(i)){const r=t.md.normalizeLink("mailto:"+i);if(!t.md.validateLink(r))return!1;if(!e){const e=t.push("link_open","a",1);e.attrs=[["href",r]],e.markup="autolink",e.info="auto";t.push("text","",0).content=t.md.normalizeLinkText(i);const n=t.push("link_close","a",-1);n.markup="autolink",n.info="auto"}return t.pos+=i.length+2,!0}return!1}],["html_inline",function(t,e){if(!t.md.options.html)return!1;const r=t.posMax,n=t.pos;if(60!==t.src.charCodeAt(n)||n+2>=r)return!1;const s=t.src.charCodeAt(n+1);if(33!==s&&63!==s&&47!==s&&!function(t){const e=32|t;return e>=97&&e<=122}(s))return!1;const i=t.src.slice(n).match(jt);if(!i)return!1;if(!e){const e=t.push("html_inline","",0);e.content=i[0],o=e.content,/^\s]/i.test(o)&&t.linkLevel++,function(t){return/^<\/a\s*>/i.test(t)}(e.content)&&t.linkLevel--}var o;return t.pos+=i[0].length,!0}],["entity",function(t,e){const r=t.pos,n=t.posMax;if(38!==t.src.charCodeAt(r))return!1;if(r+1>=n)return!1;if(35===t.src.charCodeAt(r+1)){const n=t.src.slice(r).match(re);if(n){if(!e){const e="x"===n[1][0].toLowerCase()?parseInt(n[1].slice(1),16):parseInt(n[1],10),r=t.push("text_special","",0);r.content=V(e)?G(e):G(65533),r.markup=n[0],r.info="entity"}return t.pos+=n[0].length,!0}}else{const n=t.src.slice(r).match(ne);if(n){const r=j(n[0]);if(r!==n[0]){if(!e){const e=t.push("text_special","",0);e.content=r,e.markup=n[0],e.info="entity"}return t.pos+=n[0].length,!0}}}return!1}]],oe=[["balance_pairs",function(t){const e=t.tokens_meta,r=t.tokens_meta.length;se(t.delimiters);for(let t=0;t0&&n++,"text"===s[e].type&&e+1=t.pos)throw new Error("inline rule didn't increment state.pos");break}}else t.pos=t.posMax;o||t.pos++,i[e]=t.pos},ue.prototype.tokenize=function(t){const e=this.ruler.getRules(""),r=e.length,n=t.posMax,s=t.md.options.maxNesting;for(;t.pos=t.pos)throw new Error("inline rule didn't increment state.pos");break}if(o){if(t.pos>=n)break}else t.pending+=t.src[t.pos++]}t.pending&&t.pushPending()},ue.prototype.parse=function(t,e,r,n){const s=new this.State(t,e,r,n);this.tokenize(s);const i=this.ruler2.getRules(""),o=i.length;for(let t=0;t=3&&":"===t[e-3]||e>=3&&"/"===t[e-3]?0:n.match(r.re.no_http)[0].length:0}},"mailto:":{validate:function(t,e,r){const n=t.slice(e);return r.re.mailto||(r.re.mailto=new RegExp("^"+r.re.src_email_name+"@"+r.re.src_host_strict,"i")),r.re.mailto.test(n)?n.match(r.re.mailto)[0].length:0}}},de="a[cdefgilmnoqrstuwxz]|b[abdefghijmnorstvwyz]|c[acdfghiklmnoruvwxyz]|d[ejkmoz]|e[cegrstu]|f[ijkmor]|g[abdefghilmnpqrstuwy]|h[kmnrtu]|i[delmnoqrst]|j[emop]|k[eghimnprwyz]|l[abcikrstuvy]|m[acdeghklmnopqrstuvwxyz]|n[acefgilopruz]|om|p[aefghklmnrstwy]|qa|r[eosuw]|s[abcdeghijklmnortuvxyz]|t[cdfghjklmnortvwz]|u[agksyz]|v[aceginu]|w[fs]|y[et]|z[amw]",_e="biz|com|edu|gov|net|org|pro|web|xxx|aero|asia|coop|info|museum|name|shop|\u0440\u0444".split("|");function me(t){const e=t.re=function(t){const e={};t=t||{},e.src_Any=C.source,e.src_Cc=y.source,e.src_Z=b.source,e.src_P=E.source,e.src_ZPCc=[e.src_Z,e.src_P,e.src_Cc].join("|"),e.src_ZCc=[e.src_Z,e.src_Cc].join("|");const r="[><\uff5c]";return e.src_pseudo_letter="(?:(?![><\uff5c]|"+e.src_ZPCc+")"+e.src_Any+")",e.src_ip4="(?:(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)",e.src_auth="(?:(?:(?!"+e.src_ZCc+"|[@/\\[\\]()]).)+@)?",e.src_port="(?::(?:6(?:[0-4]\\d{3}|5(?:[0-4]\\d{2}|5(?:[0-2]\\d|3[0-5])))|[1-5]?\\d{1,4}))?",e.src_host_terminator="(?=$|[><\uff5c]|"+e.src_ZPCc+")(?!"+(t["---"]?"-(?!--)|":"-|")+"_|:\\d|\\.-|\\.(?!$|"+e.src_ZPCc+"))",e.src_path="(?:[/?#](?:(?!"+e.src_ZCc+"|"+r+"|[()[\\]{}.,\"'?!\\-;]).|\\[(?:(?!"+e.src_ZCc+"|\\]).)*\\]|\\((?:(?!"+e.src_ZCc+"|[)]).)*\\)|\\{(?:(?!"+e.src_ZCc+'|[}]).)*\\}|\\"(?:(?!'+e.src_ZCc+'|["]).)+\\"|\\\'(?:(?!'+e.src_ZCc+"|[']).)+\\'|\\'(?="+e.src_pseudo_letter+"|[-])|\\.{2,}[a-zA-Z0-9%/&]|\\.(?!"+e.src_ZCc+"|[.]|$)|"+(t["---"]?"\\-(?!--(?:[^-]|$))(?:-*)|":"\\-+|")+",(?!"+e.src_ZCc+"|$)|;(?!"+e.src_ZCc+"|$)|\\!+(?!"+e.src_ZCc+"|[!]|$)|\\?(?!"+e.src_ZCc+"|[?]|$))+|\\/)?",e.src_email_name='[\\-;:&=\\+\\$,\\.a-zA-Z0-9_][\\-;:&=\\+\\$,\\"\\.a-zA-Z0-9_]*',e.src_xn="xn--[a-z0-9\\-]{1,59}",e.src_domain_root="(?:"+e.src_xn+"|"+e.src_pseudo_letter+"{1,63})",e.src_domain="(?:"+e.src_xn+"|(?:"+e.src_pseudo_letter+")|(?:"+e.src_pseudo_letter+"(?:-|"+e.src_pseudo_letter+"){0,61}"+e.src_pseudo_letter+"))",e.src_host="(?:(?:(?:(?:"+e.src_domain+")\\.)*"+e.src_domain+"))",e.tpl_host_fuzzy="(?:"+e.src_ip4+"|(?:(?:(?:"+e.src_domain+")\\.)+(?:%TLDS%)))",e.tpl_host_no_ip_fuzzy="(?:(?:(?:"+e.src_domain+")\\.)+(?:%TLDS%))",e.src_host_strict=e.src_host+e.src_host_terminator,e.tpl_host_fuzzy_strict=e.tpl_host_fuzzy+e.src_host_terminator,e.src_host_port_strict=e.src_host+e.src_port+e.src_host_terminator,e.tpl_host_port_fuzzy_strict=e.tpl_host_fuzzy+e.src_port+e.src_host_terminator,e.tpl_host_port_no_ip_fuzzy_strict=e.tpl_host_no_ip_fuzzy+e.src_port+e.src_host_terminator,e.tpl_host_fuzzy_test="localhost|www\\.|\\.\\d{1,3}\\.|(?:\\.(?:%TLDS%)(?:"+e.src_ZPCc+"|>|$))",e.tpl_email_fuzzy='(^|[><\uff5c]|"|\\(|'+e.src_ZCc+")("+e.src_email_name+"@"+e.tpl_host_fuzzy_strict+")",e.tpl_link_fuzzy="(^|(?![.:/\\-_@])(?:[$+<=>^`|\uff5c]|"+e.src_ZPCc+"))((?![$+<=>^`|\uff5c])"+e.tpl_host_port_fuzzy_strict+e.src_path+")",e.tpl_link_no_ip_fuzzy="(^|(?![.:/\\-_@])(?:[$+<=>^`|\uff5c]|"+e.src_ZPCc+"))((?![$+<=>^`|\uff5c])"+e.tpl_host_port_no_ip_fuzzy_strict+e.src_path+")",e}(t.__opts__),r=t.__tlds__.slice();function n(t){return t.replace("%TLDS%",e.src_tlds)}t.onCompile(),t.__tlds_replaced__||r.push(de),r.push(e.src_xn),e.src_tlds=r.join("|"),e.email_fuzzy=RegExp(n(e.tpl_email_fuzzy),"i"),e.link_fuzzy=RegExp(n(e.tpl_link_fuzzy),"i"),e.link_no_ip_fuzzy=RegExp(n(e.tpl_link_no_ip_fuzzy),"i"),e.host_fuzzy_test=RegExp(n(e.tpl_host_fuzzy_test),"i");const s=[];function i(t,e){throw new Error('(LinkifyIt) Invalid schema "'+t+'": '+e)}t.__compiled__={},Object.keys(t.__schemas__).forEach((function(e){const r=t.__schemas__[e];if(null===r)return;const n={validate:null,link:null};if(t.__compiled__[e]=n,"[object Object]"===ae(r))return!function(t){return"[object RegExp]"===ae(t)}(r.validate)?le(r.validate)?n.validate=r.validate:i(e,r):n.validate=function(t){return function(e,r){const n=e.slice(r);return t.test(n)?n.match(t)[0].length:0}}(r.validate),void(le(r.normalize)?n.normalize=r.normalize:r.normalize?i(e,r):n.normalize=function(t,e){e.normalize(t)});!function(t){return"[object String]"===ae(t)}(r)?i(e,r):s.push(e)})),s.forEach((function(e){t.__compiled__[t.__schemas__[e]]&&(t.__compiled__[e].validate=t.__compiled__[t.__schemas__[e]].validate,t.__compiled__[e].normalize=t.__compiled__[t.__schemas__[e]].normalize)})),t.__compiled__[""]={validate:null,normalize:function(t,e){e.normalize(t)}};const o=Object.keys(t.__compiled__).filter((function(e){return e.length>0&&t.__compiled__[e]})).map(he).join("|");t.re.schema_test=RegExp("(^|(?!_)(?:[><\uff5c]|"+e.src_ZPCc+"))("+o+")","i"),t.re.schema_search=RegExp("(^|(?!_)(?:[><\uff5c]|"+e.src_ZPCc+"))("+o+")","ig"),t.re.schema_at_start=RegExp("^"+t.re.schema_search.source,"i"),t.re.pretest=RegExp("("+t.re.schema_test.source+")|("+t.re.host_fuzzy_test.source+")|@","i"),function(t){t.__index__=-1,t.__text_cache__=""}(t)}function ge(t,e){const r=t.__index__,n=t.__last_index__,s=t.__text_cache__.slice(r,n);this.schema=t.__schema__.toLowerCase(),this.index=r+e,this.lastIndex=n+e,this.raw=s,this.text=s,this.url=s}function ke(t,e){const r=new ge(t,e);return t.__compiled__[r.schema].normalize(r,t),r}function De(t,e){if(!(this instanceof De))return new De(t,e);var r;e||(r=t,Object.keys(r||{}).reduce((function(t,e){return t||pe.hasOwnProperty(e)}),!1)&&(e=t,t={})),this.__opts__=ce({},pe,e),this.__index__=-1,this.__last_index__=-1,this.__schema__="",this.__text_cache__="",this.__schemas__=ce({},fe,t),this.__compiled__={},this.__tlds__=_e,this.__tlds_replaced__=!1,this.re={},me(this)}De.prototype.add=function(t,e){return this.__schemas__[t]=e,me(this),this},De.prototype.set=function(t){return this.__opts__=ce(this.__opts__,t),this},De.prototype.test=function(t){if(this.__text_cache__=t,this.__index__=-1,!t.length)return!1;let e,r,n,s,i,o,u,c,a;if(this.re.schema_test.test(t))for(u=this.re.schema_search,u.lastIndex=0;null!==(e=u.exec(t));)if(s=this.testSchemaAt(t,e[2],u.lastIndex),s){this.__schema__=e[2],this.__index__=e.index+e[1].length,this.__last_index__=e.index+e[0].length+s;break}return this.__opts__.fuzzyLink&&this.__compiled__["http:"]&&(c=t.search(this.re.host_fuzzy_test),c>=0&&(this.__index__<0||c=0&&null!==(n=t.match(this.re.email_fuzzy))&&(i=n.index+n[1].length,o=n.index+n[0].length,(this.__index__<0||ithis.__last_index__)&&(this.__schema__="mailto:",this.__index__=i,this.__last_index__=o))),this.__index__>=0},De.prototype.pretest=function(t){return this.re.pretest.test(t)},De.prototype.testSchemaAt=function(t,e,r){return this.__compiled__[e.toLowerCase()]?this.__compiled__[e.toLowerCase()].validate(t,r,this):0},De.prototype.match=function(t){const e=[];let r=0;this.__index__>=0&&this.__text_cache__===t&&(e.push(ke(this,r)),r=this.__last_index__);let n=r?t.slice(r):t;for(;this.test(n);)e.push(ke(this,r)),n=n.slice(this.__last_index__),r+=this.__last_index__;return e.length?e:null},De.prototype.matchAtStart=function(t){if(this.__text_cache__=t,this.__index__=-1,!t.length)return null;const e=this.re.schema_at_start.exec(t);if(!e)return null;const r=this.testSchemaAt(t,e[2],e[0].length);return r?(this.__schema__=e[2],this.__index__=e.index+e[1].length,this.__last_index__=e.index+e[0].length+r,ke(this,0)):null},De.prototype.tlds=function(t,e){return t=Array.isArray(t)?t:[t],e?(this.__tlds__=this.__tlds__.concat(t).sort().filter((function(t,e,r){return t!==r[e-1]})).reverse(),me(this),this):(this.__tlds__=t.slice(),this.__tlds_replaced__=!0,me(this),this)},De.prototype.normalize=function(t){t.schema||(t.url="http://"+t.url),"mailto:"!==t.schema||/^mailto:/i.test(t.url)||(t.url="mailto:"+t.url)},De.prototype.onCompile=function(){};const Ce=2147483647,ye=36,Ee=/^xn--/,Ae=/[^\0-\x7F]/,be=/[\x2E\u3002\uFF0E\uFF61]/g,Fe={overflow:"Overflow: input needs wider integers to process","not-basic":"Illegal input >= 0x80 (not a basic code point)","invalid-input":"Invalid input"},xe=Math.floor,we=String.fromCharCode;function ve(t){throw new RangeError(Fe[t])}function ze(t,e){const r=t.split("@");let n="";r.length>1&&(n=r[0]+"@",t=r[1]);const s=function(t,e){const r=[];let n=t.length;for(;n--;)r[n]=e(t[n]);return r}((t=t.replace(be,".")).split("."),e).join(".");return n+s}function Se(t){const e=[];let r=0;const n=t.length;for(;r=55296&&s<=56319&&r>1,t+=xe(t/e);t>455;n+=ye)t=xe(t/35);return xe(n+36*t/(t+38))},Le=function(t){const e=[],r=t.length;let n=0,s=128,i=72,o=t.lastIndexOf("-");o<0&&(o=0);for(let r=0;r=128&&ve("not-basic"),e.push(t.charCodeAt(r));for(let c=o>0?o+1:0;c=r&&ve("invalid-input");const o=(u=t.charCodeAt(c++))>=48&&u<58?u-48+26:u>=65&&u<91?u-65:u>=97&&u<123?u-97:ye;o>=ye&&ve("invalid-input"),o>xe((Ce-n)/e)&&ve("overflow"),n+=o*e;const a=s<=i?1:s>=i+26?26:s-i;if(oxe(Ce/l)&&ve("overflow"),e*=l}const a=e.length+1;i=Be(n-o,a,0==o),xe(n/a)>Ce-s&&ve("overflow"),s+=xe(n/a),n%=a,e.splice(n++,0,s)}var u;return String.fromCodePoint(...e)},Ie=function(t){const e=[],r=(t=Se(t)).length;let n=128,s=0,i=72;for(const r of t)r<128&&e.push(we(r));const o=e.length;let u=o;for(o&&e.push("-");u=n&&exe((Ce-s)/c)&&ve("overflow"),s+=(r-n)*c,n=r;for(const r of t)if(rCe&&ve("overflow"),r===n){let t=s;for(let r=ye;;r+=ye){const n=r<=i?1:r>=i+26?26:r-i;if(tString.fromCodePoint(...t)},decode:Le,encode:Ie,toASCII:function(t){return ze(t,(function(t){return Ae.test(t)?"xn--"+Ie(t):t}))},toUnicode:function(t){return ze(t,(function(t){return Ee.test(t)?Le(t.slice(4).toLowerCase()):t}))}};const Te={default:{options:{html:!1,xhtmlOut:!1,breaks:!1,langPrefix:"language-",linkify:!1,typographer:!1,quotes:"\u201c\u201d\u2018\u2019",highlight:null,maxNesting:100},components:{core:{},block:{},inline:{}}},zero:{options:{html:!1,xhtmlOut:!1,breaks:!1,langPrefix:"language-",linkify:!1,typographer:!1,quotes:"\u201c\u201d\u2018\u2019",highlight:null,maxNesting:20},components:{core:{rules:["normalize","block","inline","text_join"]},block:{rules:["paragraph"]},inline:{rules:["text"],rules2:["balance_pairs","fragments_join"]}}},commonmark:{options:{html:!0,xhtmlOut:!0,breaks:!1,langPrefix:"language-",linkify:!1,typographer:!1,quotes:"\u201c\u201d\u2018\u2019",highlight:null,maxNesting:20},components:{core:{rules:["normalize","block","inline","text_join"]},block:{rules:["blockquote","code","fence","heading","hr","html_block","lheading","list","reference","paragraph"]},inline:{rules:["autolink","backticks","emphasis","entity","escape","html_inline","image","link","newline","text"],rules2:["balance_pairs","emphasis","fragments_join"]}}}},Re=/^(vbscript|javascript|file|data):/,Ne=/^data:image\/(gif|png|jpeg|webp);/;function Pe(t){const e=t.trim().toLowerCase();return!Re.test(e)||Ne.test(e)}const Oe=["http:","https:","mailto:"];function je(t){const e=g(t,!0);if(e.hostname&&(!e.protocol||Oe.indexOf(e.protocol)>=0))try{e.hostname=Me.toASCII(e.hostname)}catch(t){}return n(s(e))}function Ze(t){const r=g(t,!0);if(r.hostname&&(!r.protocol||Oe.indexOf(r.protocol)>=0))try{r.hostname=Me.toUnicode(r.hostname)}catch(t){}return e(s(r),e.defaultChars+"%")}function $e(t,e){if(!(this instanceof $e))return new $e(t,e);e||Z(t)||(e=t||{},t="default"),this.inline=new ue,this.block=new Ht,this.core=new Lt,this.renderer=new ft,this.linkify=new De,this.validateLink=Pe,this.normalizeLink=je,this.normalizeLinkText=Ze,this.utils=lt,this.helpers=U({},ht),this.options={},this.configure(t),e&&this.set(e)}return $e.prototype.set=function(t){return U(this.options,t),this},$e.prototype.configure=function(t){const e=this;if(Z(t)){const e=t;if(!(t=Te[e]))throw new Error('Wrong `markdown-it` preset "'+e+'", check name')}if(!t)throw new Error("Wrong `markdown-it` preset, can't be empty");return t.options&&e.set(t.options),t.components&&Object.keys(t.components).forEach((function(r){t.components[r].rules&&e[r].ruler.enableOnly(t.components[r].rules),t.components[r].rules2&&e[r].ruler2.enableOnly(t.components[r].rules2)})),this},$e.prototype.enable=function(t,e){let r=[];Array.isArray(t)||(t=[t]),["core","block","inline"].forEach((function(e){r=r.concat(this[e].ruler.enable(t,!0))}),this),r=r.concat(this.inline.ruler2.enable(t,!0));const n=t.filter((function(t){return r.indexOf(t)<0}));if(n.length&&!e)throw new Error("MarkdownIt. Failed to enable unknown rule(s): "+n);return this},$e.prototype.disable=function(t,e){let r=[];Array.isArray(t)||(t=[t]),["core","block","inline"].forEach((function(e){r=r.concat(this[e].ruler.disable(t,!0))}),this),r=r.concat(this.inline.ruler2.disable(t,!0));const n=t.filter((function(t){return r.indexOf(t)<0}));if(n.length&&!e)throw new Error("MarkdownIt. Failed to disable unknown rule(s): "+n);return this},$e.prototype.use=function(t){const e=[this].concat(Array.prototype.slice.call(arguments,1));return t.apply(t,e),this},$e.prototype.parse=function(t,e){if("string"!=typeof t)throw new Error("Input data should be a String");const r=new this.core.State(t,this,e);return this.core.process(r),r.tokens},$e.prototype.render=function(t,e){return e=e||{},this.renderer.render(this.parse(t,e),this.options,e)},$e.prototype.parseInline=function(t,e){const r=new this.core.State(t,this,e);return r.inlineMode=!0,this.core.process(r),r.tokens},$e.prototype.renderInline=function(t,e){return e=e||{},this.renderer.render(this.parseInline(t,e),this.options,e)},$e})); diff --git a/frontend/node_modules/markdown-it/index.mjs b/frontend/node_modules/markdown-it/index.mjs new file mode 100644 index 0000000..f7ba45f --- /dev/null +++ b/frontend/node_modules/markdown-it/index.mjs @@ -0,0 +1 @@ +export { default } from './lib/index.mjs' diff --git a/frontend/node_modules/markdown-it/lib/common/html_blocks.mjs b/frontend/node_modules/markdown-it/lib/common/html_blocks.mjs new file mode 100644 index 0000000..1e27a7f --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/common/html_blocks.mjs @@ -0,0 +1,67 @@ +// List of valid html blocks names, according to commonmark spec +// https://spec.commonmark.org/0.30/#html-blocks + +export default [ + 'address', + 'article', + 'aside', + 'base', + 'basefont', + 'blockquote', + 'body', + 'caption', + 'center', + 'col', + 'colgroup', + 'dd', + 'details', + 'dialog', + 'dir', + 'div', + 'dl', + 'dt', + 'fieldset', + 'figcaption', + 'figure', + 'footer', + 'form', + 'frame', + 'frameset', + 'h1', + 'h2', + 'h3', + 'h4', + 'h5', + 'h6', + 'head', + 'header', + 'hr', + 'html', + 'iframe', + 'legend', + 'li', + 'link', + 'main', + 'menu', + 'menuitem', + 'nav', + 'noframes', + 'ol', + 'optgroup', + 'option', + 'p', + 'param', + 'search', + 'section', + 'summary', + 'table', + 'tbody', + 'td', + 'tfoot', + 'th', + 'thead', + 'title', + 'tr', + 'track', + 'ul' +] diff --git a/frontend/node_modules/markdown-it/lib/common/html_re.mjs b/frontend/node_modules/markdown-it/lib/common/html_re.mjs new file mode 100644 index 0000000..ccfbf87 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/common/html_re.mjs @@ -0,0 +1,25 @@ +// Regexps to match html elements + +const attr_name = '[a-zA-Z_:][a-zA-Z0-9:._-]*' + +const unquoted = '[^"\'=<>`\\x00-\\x20]+' +const single_quoted = "'[^']*'" +const double_quoted = '"[^"]*"' + +const attr_value = '(?:' + unquoted + '|' + single_quoted + '|' + double_quoted + ')' + +const attribute = '(?:\\s+' + attr_name + '(?:\\s*=\\s*' + attr_value + ')?)' + +const open_tag = '<[A-Za-z][A-Za-z0-9\\-]*' + attribute + '*\\s*\\/?>' + +const close_tag = '<\\/[A-Za-z][A-Za-z0-9\\-]*\\s*>' +const comment = '' +const processing = '<[?][\\s\\S]*?[?]>' +const declaration = ']*>' +const cdata = '' + +const HTML_TAG_RE = new RegExp('^(?:' + open_tag + '|' + close_tag + '|' + comment + + '|' + processing + '|' + declaration + '|' + cdata + ')') +const HTML_OPEN_CLOSE_TAG_RE = new RegExp('^(?:' + open_tag + '|' + close_tag + ')') + +export { HTML_TAG_RE, HTML_OPEN_CLOSE_TAG_RE } diff --git a/frontend/node_modules/markdown-it/lib/common/utils.mjs b/frontend/node_modules/markdown-it/lib/common/utils.mjs new file mode 100644 index 0000000..b78c9b0 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/common/utils.mjs @@ -0,0 +1,304 @@ +// Utilities +// + +import * as mdurl from 'mdurl' +import * as ucmicro from 'uc.micro' +import { decodeHTML } from 'entities' + +function _class (obj) { return Object.prototype.toString.call(obj) } + +function isString (obj) { return _class(obj) === '[object String]' } + +const _hasOwnProperty = Object.prototype.hasOwnProperty + +function has (object, key) { + return _hasOwnProperty.call(object, key) +} + +// Merge objects +// +function assign (obj /* from1, from2, from3, ... */) { + const sources = Array.prototype.slice.call(arguments, 1) + + sources.forEach(function (source) { + if (!source) { return } + + if (typeof source !== 'object') { + throw new TypeError(source + 'must be object') + } + + Object.keys(source).forEach(function (key) { + obj[key] = source[key] + }) + }) + + return obj +} + +// Remove element from array and put another array at those position. +// Useful for some operations with tokens +function arrayReplaceAt (src, pos, newElements) { + return [].concat(src.slice(0, pos), newElements, src.slice(pos + 1)) +} + +function isValidEntityCode (c) { + /* eslint no-bitwise:0 */ + // broken sequence + if (c >= 0xD800 && c <= 0xDFFF) { return false } + // never used + if (c >= 0xFDD0 && c <= 0xFDEF) { return false } + if ((c & 0xFFFF) === 0xFFFF || (c & 0xFFFF) === 0xFFFE) { return false } + // control codes + if (c >= 0x00 && c <= 0x08) { return false } + if (c === 0x0B) { return false } + if (c >= 0x0E && c <= 0x1F) { return false } + if (c >= 0x7F && c <= 0x9F) { return false } + // out of range + if (c > 0x10FFFF) { return false } + return true +} + +function fromCodePoint (c) { + /* eslint no-bitwise:0 */ + if (c > 0xffff) { + c -= 0x10000 + const surrogate1 = 0xd800 + (c >> 10) + const surrogate2 = 0xdc00 + (c & 0x3ff) + + return String.fromCharCode(surrogate1, surrogate2) + } + return String.fromCharCode(c) +} + +const UNESCAPE_MD_RE = /\\([!"#$%&'()*+,\-./:;<=>?@[\\\]^_`{|}~])/g +const ENTITY_RE = /&([a-z#][a-z0-9]{1,31});/gi +const UNESCAPE_ALL_RE = new RegExp(UNESCAPE_MD_RE.source + '|' + ENTITY_RE.source, 'gi') + +const DIGITAL_ENTITY_TEST_RE = /^#((?:x[a-f0-9]{1,8}|[0-9]{1,8}))$/i + +function replaceEntityPattern (match, name) { + if (name.charCodeAt(0) === 0x23/* # */ && DIGITAL_ENTITY_TEST_RE.test(name)) { + const code = name[1].toLowerCase() === 'x' + ? parseInt(name.slice(2), 16) + : parseInt(name.slice(1), 10) + + if (isValidEntityCode(code)) { + return fromCodePoint(code) + } + + return match + } + + const decoded = decodeHTML(match) + if (decoded !== match) { + return decoded + } + + return match +} + +/* function replaceEntities(str) { + if (str.indexOf('&') < 0) { return str; } + + return str.replace(ENTITY_RE, replaceEntityPattern); +} */ + +function unescapeMd (str) { + if (str.indexOf('\\') < 0) { return str } + return str.replace(UNESCAPE_MD_RE, '$1') +} + +function unescapeAll (str) { + if (str.indexOf('\\') < 0 && str.indexOf('&') < 0) { return str } + + return str.replace(UNESCAPE_ALL_RE, function (match, escaped, entity) { + if (escaped) { return escaped } + return replaceEntityPattern(match, entity) + }) +} + +const HTML_ESCAPE_TEST_RE = /[&<>"]/ +const HTML_ESCAPE_REPLACE_RE = /[&<>"]/g +const HTML_REPLACEMENTS = { + '&': '&', + '<': '<', + '>': '>', + '"': '"' +} + +function replaceUnsafeChar (ch) { + return HTML_REPLACEMENTS[ch] +} + +function escapeHtml (str) { + if (HTML_ESCAPE_TEST_RE.test(str)) { + return str.replace(HTML_ESCAPE_REPLACE_RE, replaceUnsafeChar) + } + return str +} + +const REGEXP_ESCAPE_RE = /[.?*+^$[\]\\(){}|-]/g + +function escapeRE (str) { + return str.replace(REGEXP_ESCAPE_RE, '\\$&') +} + +function isSpace (code) { + switch (code) { + case 0x09: + case 0x20: + return true + } + return false +} + +// Zs (unicode class) || [\t\f\v\r\n] +function isWhiteSpace (code) { + if (code >= 0x2000 && code <= 0x200A) { return true } + switch (code) { + case 0x09: // \t + case 0x0A: // \n + case 0x0B: // \v + case 0x0C: // \f + case 0x0D: // \r + case 0x20: + case 0xA0: + case 0x1680: + case 0x202F: + case 0x205F: + case 0x3000: + return true + } + return false +} + +/* eslint-disable max-len */ + +// Currently without astral characters support. +function isPunctChar (ch) { + return ucmicro.P.test(ch) || ucmicro.S.test(ch) +} + +// Markdown ASCII punctuation characters. +// +// !, ", #, $, %, &, ', (, ), *, +, ,, -, ., /, :, ;, <, =, >, ?, @, [, \, ], ^, _, `, {, |, }, or ~ +// http://spec.commonmark.org/0.15/#ascii-punctuation-character +// +// Don't confuse with unicode punctuation !!! It lacks some chars in ascii range. +// +function isMdAsciiPunct (ch) { + switch (ch) { + case 0x21/* ! */: + case 0x22/* " */: + case 0x23/* # */: + case 0x24/* $ */: + case 0x25/* % */: + case 0x26/* & */: + case 0x27/* ' */: + case 0x28/* ( */: + case 0x29/* ) */: + case 0x2A/* * */: + case 0x2B/* + */: + case 0x2C/* , */: + case 0x2D/* - */: + case 0x2E/* . */: + case 0x2F/* / */: + case 0x3A/* : */: + case 0x3B/* ; */: + case 0x3C/* < */: + case 0x3D/* = */: + case 0x3E/* > */: + case 0x3F/* ? */: + case 0x40/* @ */: + case 0x5B/* [ */: + case 0x5C/* \ */: + case 0x5D/* ] */: + case 0x5E/* ^ */: + case 0x5F/* _ */: + case 0x60/* ` */: + case 0x7B/* { */: + case 0x7C/* | */: + case 0x7D/* } */: + case 0x7E/* ~ */: + return true + default: + return false + } +} + +// Hepler to unify [reference labels]. +// +function normalizeReference (str) { + // Trim and collapse whitespace + // + str = str.trim().replace(/\s+/g, ' ') + + // In node v10 'ẞ'.toLowerCase() === 'Ṿ', which is presumed to be a bug + // fixed in v12 (couldn't find any details). + // + // So treat this one as a special case + // (remove this when node v10 is no longer supported). + // + if ('ẞ'.toLowerCase() === 'Ṿ') { + str = str.replace(/ẞ/g, 'ß') + } + + // .toLowerCase().toUpperCase() should get rid of all differences + // between letter variants. + // + // Simple .toLowerCase() doesn't normalize 125 code points correctly, + // and .toUpperCase doesn't normalize 6 of them (list of exceptions: + // İ, ϴ, ẞ, Ω, K, Å - those are already uppercased, but have differently + // uppercased versions). + // + // Here's an example showing how it happens. Lets take greek letter omega: + // uppercase U+0398 (Θ), U+03f4 (ϴ) and lowercase U+03b8 (θ), U+03d1 (ϑ) + // + // Unicode entries: + // 0398;GREEK CAPITAL LETTER THETA;Lu;0;L;;;;;N;;;;03B8; + // 03B8;GREEK SMALL LETTER THETA;Ll;0;L;;;;;N;;;0398;;0398 + // 03D1;GREEK THETA SYMBOL;Ll;0;L; 03B8;;;;N;GREEK SMALL LETTER SCRIPT THETA;;0398;;0398 + // 03F4;GREEK CAPITAL THETA SYMBOL;Lu;0;L; 0398;;;;N;;;;03B8; + // + // Case-insensitive comparison should treat all of them as equivalent. + // + // But .toLowerCase() doesn't change ϑ (it's already lowercase), + // and .toUpperCase() doesn't change ϴ (already uppercase). + // + // Applying first lower then upper case normalizes any character: + // '\u0398\u03f4\u03b8\u03d1'.toLowerCase().toUpperCase() === '\u0398\u0398\u0398\u0398' + // + // Note: this is equivalent to unicode case folding; unicode normalization + // is a different step that is not required here. + // + // Final result should be uppercased, because it's later stored in an object + // (this avoid a conflict with Object.prototype members, + // most notably, `__proto__`) + // + return str.toLowerCase().toUpperCase() +} + +// Re-export libraries commonly used in both markdown-it and its plugins, +// so plugins won't have to depend on them explicitly, which reduces their +// bundled size (e.g. a browser build). +// +const lib = { mdurl, ucmicro } + +export { + lib, + assign, + isString, + has, + unescapeMd, + unescapeAll, + isValidEntityCode, + fromCodePoint, + escapeHtml, + arrayReplaceAt, + isSpace, + isWhiteSpace, + isMdAsciiPunct, + isPunctChar, + escapeRE, + normalizeReference +} diff --git a/frontend/node_modules/markdown-it/lib/helpers/index.mjs b/frontend/node_modules/markdown-it/lib/helpers/index.mjs new file mode 100644 index 0000000..7ea30af --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/helpers/index.mjs @@ -0,0 +1,11 @@ +// Just a shortcut for bulk export + +import parseLinkLabel from './parse_link_label.mjs' +import parseLinkDestination from './parse_link_destination.mjs' +import parseLinkTitle from './parse_link_title.mjs' + +export { + parseLinkLabel, + parseLinkDestination, + parseLinkTitle +} diff --git a/frontend/node_modules/markdown-it/lib/helpers/parse_link_destination.mjs b/frontend/node_modules/markdown-it/lib/helpers/parse_link_destination.mjs new file mode 100644 index 0000000..6a723a6 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/helpers/parse_link_destination.mjs @@ -0,0 +1,77 @@ +// Parse link destination +// + +import { unescapeAll } from '../common/utils.mjs' + +export default function parseLinkDestination (str, start, max) { + let code + let pos = start + + const result = { + ok: false, + pos: 0, + str: '' + } + + if (str.charCodeAt(pos) === 0x3C /* < */) { + pos++ + while (pos < max) { + code = str.charCodeAt(pos) + if (code === 0x0A /* \n */) { return result } + if (code === 0x3C /* < */) { return result } + if (code === 0x3E /* > */) { + result.pos = pos + 1 + result.str = unescapeAll(str.slice(start + 1, pos)) + result.ok = true + return result + } + if (code === 0x5C /* \ */ && pos + 1 < max) { + pos += 2 + continue + } + + pos++ + } + + // no closing '>' + return result + } + + // this should be ... } else { ... branch + + let level = 0 + while (pos < max) { + code = str.charCodeAt(pos) + + if (code === 0x20) { break } + + // ascii control characters + if (code < 0x20 || code === 0x7F) { break } + + if (code === 0x5C /* \ */ && pos + 1 < max) { + if (str.charCodeAt(pos + 1) === 0x20) { break } + pos += 2 + continue + } + + if (code === 0x28 /* ( */) { + level++ + if (level > 32) { return result } + } + + if (code === 0x29 /* ) */) { + if (level === 0) { break } + level-- + } + + pos++ + } + + if (start === pos) { return result } + if (level !== 0) { return result } + + result.str = unescapeAll(str.slice(start, pos)) + result.pos = pos + result.ok = true + return result +} diff --git a/frontend/node_modules/markdown-it/lib/helpers/parse_link_label.mjs b/frontend/node_modules/markdown-it/lib/helpers/parse_link_label.mjs new file mode 100644 index 0000000..f1a53fa --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/helpers/parse_link_label.mjs @@ -0,0 +1,49 @@ +// Parse link label +// +// this function assumes that first character ("[") already matches; +// returns the end of the label +// + +export default function parseLinkLabel (state, start, disableNested) { + let level, found, marker, prevPos + + const max = state.posMax + const oldPos = state.pos + + state.pos = start + 1 + level = 1 + + while (state.pos < max) { + marker = state.src.charCodeAt(state.pos) + if (marker === 0x5D /* ] */) { + level-- + if (level === 0) { + found = true + break + } + } + + prevPos = state.pos + state.md.inline.skipToken(state) + if (marker === 0x5B /* [ */) { + if (prevPos === state.pos - 1) { + // increase level if we find text `[`, which is not a part of any token + level++ + } else if (disableNested) { + state.pos = oldPos + return -1 + } + } + } + + let labelEnd = -1 + + if (found) { + labelEnd = state.pos + } + + // restore old state + state.pos = oldPos + + return labelEnd +} diff --git a/frontend/node_modules/markdown-it/lib/helpers/parse_link_title.mjs b/frontend/node_modules/markdown-it/lib/helpers/parse_link_title.mjs new file mode 100644 index 0000000..4605647 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/helpers/parse_link_title.mjs @@ -0,0 +1,66 @@ +// Parse link title +// + +import { unescapeAll } from '../common/utils.mjs' + +// Parse link title within `str` in [start, max] range, +// or continue previous parsing if `prev_state` is defined (equal to result of last execution). +// +export default function parseLinkTitle (str, start, max, prev_state) { + let code + let pos = start + + const state = { + // if `true`, this is a valid link title + ok: false, + // if `true`, this link can be continued on the next line + can_continue: false, + // if `ok`, it's the position of the first character after the closing marker + pos: 0, + // if `ok`, it's the unescaped title + str: '', + // expected closing marker character code + marker: 0 + } + + if (prev_state) { + // this is a continuation of a previous parseLinkTitle call on the next line, + // used in reference links only + state.str = prev_state.str + state.marker = prev_state.marker + } else { + if (pos >= max) { return state } + + let marker = str.charCodeAt(pos) + if (marker !== 0x22 /* " */ && marker !== 0x27 /* ' */ && marker !== 0x28 /* ( */) { return state } + + start++ + pos++ + + // if opening marker is "(", switch it to closing marker ")" + if (marker === 0x28) { marker = 0x29 } + + state.marker = marker + } + + while (pos < max) { + code = str.charCodeAt(pos) + if (code === state.marker) { + state.pos = pos + 1 + state.str += unescapeAll(str.slice(start, pos)) + state.ok = true + return state + } else if (code === 0x28 /* ( */ && state.marker === 0x29 /* ) */) { + return state + } else if (code === 0x5C /* \ */ && pos + 1 < max) { + pos++ + } + + pos++ + } + + // no closing marker found, but this link title may continue on the next line (for references) + state.can_continue = true + state.str += unescapeAll(str.slice(start, pos)) + return state +} diff --git a/frontend/node_modules/markdown-it/lib/index.mjs b/frontend/node_modules/markdown-it/lib/index.mjs new file mode 100644 index 0000000..8a8af9d --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/index.mjs @@ -0,0 +1,565 @@ +// Main parser class + +import * as utils from './common/utils.mjs' +import * as helpers from './helpers/index.mjs' +import Renderer from './renderer.mjs' +import ParserCore from './parser_core.mjs' +import ParserBlock from './parser_block.mjs' +import ParserInline from './parser_inline.mjs' +import LinkifyIt from 'linkify-it' +import * as mdurl from 'mdurl' +import punycode from 'punycode.js' + +import cfg_default from './presets/default.mjs' +import cfg_zero from './presets/zero.mjs' +import cfg_commonmark from './presets/commonmark.mjs' + +const config = { + default: cfg_default, + zero: cfg_zero, + commonmark: cfg_commonmark +} + +// +// This validator can prohibit more than really needed to prevent XSS. It's a +// tradeoff to keep code simple and to be secure by default. +// +// If you need different setup - override validator method as you wish. Or +// replace it with dummy function and use external sanitizer. +// + +const BAD_PROTO_RE = /^(vbscript|javascript|file|data):/ +const GOOD_DATA_RE = /^data:image\/(gif|png|jpeg|webp);/ + +function validateLink (url) { + // url should be normalized at this point, and existing entities are decoded + const str = url.trim().toLowerCase() + + return BAD_PROTO_RE.test(str) ? GOOD_DATA_RE.test(str) : true +} + +const RECODE_HOSTNAME_FOR = ['http:', 'https:', 'mailto:'] + +function normalizeLink (url) { + const parsed = mdurl.parse(url, true) + + if (parsed.hostname) { + // Encode hostnames in urls like: + // `http://host/`, `https://host/`, `mailto:user@host`, `//host/` + // + // We don't encode unknown schemas, because it's likely that we encode + // something we shouldn't (e.g. `skype:name` treated as `skype:host`) + // + if (!parsed.protocol || RECODE_HOSTNAME_FOR.indexOf(parsed.protocol) >= 0) { + try { + parsed.hostname = punycode.toASCII(parsed.hostname) + } catch (er) { /**/ } + } + } + + return mdurl.encode(mdurl.format(parsed)) +} + +function normalizeLinkText (url) { + const parsed = mdurl.parse(url, true) + + if (parsed.hostname) { + // Encode hostnames in urls like: + // `http://host/`, `https://host/`, `mailto:user@host`, `//host/` + // + // We don't encode unknown schemas, because it's likely that we encode + // something we shouldn't (e.g. `skype:name` treated as `skype:host`) + // + if (!parsed.protocol || RECODE_HOSTNAME_FOR.indexOf(parsed.protocol) >= 0) { + try { + parsed.hostname = punycode.toUnicode(parsed.hostname) + } catch (er) { /**/ } + } + } + + // add '%' to exclude list because of https://github.com/markdown-it/markdown-it/issues/720 + return mdurl.decode(mdurl.format(parsed), mdurl.decode.defaultChars + '%') +} + +/** + * class MarkdownIt + * + * Main parser/renderer class. + * + * ##### Usage + * + * ```javascript + * // node.js, "classic" way: + * var MarkdownIt = require('markdown-it'), + * md = new MarkdownIt(); + * var result = md.render('# markdown-it rulezz!'); + * + * // node.js, the same, but with sugar: + * var md = require('markdown-it')(); + * var result = md.render('# markdown-it rulezz!'); + * + * // browser without AMD, added to "window" on script load + * // Note, there are no dash. + * var md = window.markdownit(); + * var result = md.render('# markdown-it rulezz!'); + * ``` + * + * Single line rendering, without paragraph wrap: + * + * ```javascript + * var md = require('markdown-it')(); + * var result = md.renderInline('__markdown-it__ rulezz!'); + * ``` + **/ + +/** + * new MarkdownIt([presetName, options]) + * - presetName (String): optional, `commonmark` / `zero` + * - options (Object) + * + * Creates parser instanse with given config. Can be called without `new`. + * + * ##### presetName + * + * MarkdownIt provides named presets as a convenience to quickly + * enable/disable active syntax rules and options for common use cases. + * + * - ["commonmark"](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/commonmark.mjs) - + * configures parser to strict [CommonMark](http://commonmark.org/) mode. + * - [default](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/default.mjs) - + * similar to GFM, used when no preset name given. Enables all available rules, + * but still without html, typographer & autolinker. + * - ["zero"](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/zero.mjs) - + * all rules disabled. Useful to quickly setup your config via `.enable()`. + * For example, when you need only `bold` and `italic` markup and nothing else. + * + * ##### options: + * + * - __html__ - `false`. Set `true` to enable HTML tags in source. Be careful! + * That's not safe! You may need external sanitizer to protect output from XSS. + * It's better to extend features via plugins, instead of enabling HTML. + * - __xhtmlOut__ - `false`. Set `true` to add '/' when closing single tags + * (`
    `). This is needed only for full CommonMark compatibility. In real + * world you will need HTML output. + * - __breaks__ - `false`. Set `true` to convert `\n` in paragraphs into `
    `. + * - __langPrefix__ - `language-`. CSS language class prefix for fenced blocks. + * Can be useful for external highlighters. + * - __linkify__ - `false`. Set `true` to autoconvert URL-like text to links. + * - __typographer__ - `false`. Set `true` to enable [some language-neutral + * replacement](https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/replacements.mjs) + + * quotes beautification (smartquotes). + * - __quotes__ - `“”‘’`, String or Array. Double + single quotes replacement + * pairs, when typographer enabled and smartquotes on. For example, you can + * use `'«»„“'` for Russian, `'„“‚‘'` for German, and + * `['«\xA0', '\xA0»', '‹\xA0', '\xA0›']` for French (including nbsp). + * - __highlight__ - `null`. Highlighter function for fenced code blocks. + * Highlighter `function (str, lang)` should return escaped HTML. It can also + * return empty string if the source was not changed and should be escaped + * externaly. If result starts with ` or ``): + * + * ```javascript + * var hljs = require('highlight.js') // https://highlightjs.org/ + * + * // Actual default values + * var md = require('markdown-it')({ + * highlight: function (str, lang) { + * if (lang && hljs.getLanguage(lang)) { + * try { + * return '
    ' +
    + *                hljs.highlight(str, { language: lang, ignoreIllegals: true }).value +
    + *                '
    '; + * } catch (__) {} + * } + * + * return '
    ' + md.utils.escapeHtml(str) + '
    '; + * } + * }); + * ``` + * + **/ +function MarkdownIt (presetName, options) { + if (!(this instanceof MarkdownIt)) { + return new MarkdownIt(presetName, options) + } + + if (!options) { + if (!utils.isString(presetName)) { + options = presetName || {} + presetName = 'default' + } + } + + /** + * MarkdownIt#inline -> ParserInline + * + * Instance of [[ParserInline]]. You may need it to add new rules when + * writing plugins. For simple rules control use [[MarkdownIt.disable]] and + * [[MarkdownIt.enable]]. + **/ + this.inline = new ParserInline() + + /** + * MarkdownIt#block -> ParserBlock + * + * Instance of [[ParserBlock]]. You may need it to add new rules when + * writing plugins. For simple rules control use [[MarkdownIt.disable]] and + * [[MarkdownIt.enable]]. + **/ + this.block = new ParserBlock() + + /** + * MarkdownIt#core -> Core + * + * Instance of [[Core]] chain executor. You may need it to add new rules when + * writing plugins. For simple rules control use [[MarkdownIt.disable]] and + * [[MarkdownIt.enable]]. + **/ + this.core = new ParserCore() + + /** + * MarkdownIt#renderer -> Renderer + * + * Instance of [[Renderer]]. Use it to modify output look. Or to add rendering + * rules for new token types, generated by plugins. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * function myToken(tokens, idx, options, env, self) { + * //... + * return result; + * }; + * + * md.renderer.rules['my_token'] = myToken + * ``` + * + * See [[Renderer]] docs and [source code](https://github.com/markdown-it/markdown-it/blob/master/lib/renderer.mjs). + **/ + this.renderer = new Renderer() + + /** + * MarkdownIt#linkify -> LinkifyIt + * + * [linkify-it](https://github.com/markdown-it/linkify-it) instance. + * Used by [linkify](https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/linkify.mjs) + * rule. + **/ + this.linkify = new LinkifyIt() + + /** + * MarkdownIt#validateLink(url) -> Boolean + * + * Link validation function. CommonMark allows too much in links. By default + * we disable `javascript:`, `vbscript:`, `file:` schemas, and almost all `data:...` schemas + * except some embedded image types. + * + * You can change this behaviour: + * + * ```javascript + * var md = require('markdown-it')(); + * // enable everything + * md.validateLink = function () { return true; } + * ``` + **/ + this.validateLink = validateLink + + /** + * MarkdownIt#normalizeLink(url) -> String + * + * Function used to encode link url to a machine-readable format, + * which includes url-encoding, punycode, etc. + **/ + this.normalizeLink = normalizeLink + + /** + * MarkdownIt#normalizeLinkText(url) -> String + * + * Function used to decode link url to a human-readable format` + **/ + this.normalizeLinkText = normalizeLinkText + + // Expose utils & helpers for easy acces from plugins + + /** + * MarkdownIt#utils -> utils + * + * Assorted utility functions, useful to write plugins. See details + * [here](https://github.com/markdown-it/markdown-it/blob/master/lib/common/utils.mjs). + **/ + this.utils = utils + + /** + * MarkdownIt#helpers -> helpers + * + * Link components parser functions, useful to write plugins. See details + * [here](https://github.com/markdown-it/markdown-it/blob/master/lib/helpers). + **/ + this.helpers = utils.assign({}, helpers) + + this.options = {} + this.configure(presetName) + + if (options) { this.set(options) } +} + +/** chainable + * MarkdownIt.set(options) + * + * Set parser options (in the same format as in constructor). Probably, you + * will never need it, but you can change options after constructor call. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')() + * .set({ html: true, breaks: true }) + * .set({ typographer, true }); + * ``` + * + * __Note:__ To achieve the best possible performance, don't modify a + * `markdown-it` instance options on the fly. If you need multiple configurations + * it's best to create multiple instances and initialize each with separate + * config. + **/ +MarkdownIt.prototype.set = function (options) { + utils.assign(this.options, options) + return this +} + +/** chainable, internal + * MarkdownIt.configure(presets) + * + * Batch load of all options and compenent settings. This is internal method, + * and you probably will not need it. But if you will - see available presets + * and data structure [here](https://github.com/markdown-it/markdown-it/tree/master/lib/presets) + * + * We strongly recommend to use presets instead of direct config loads. That + * will give better compatibility with next versions. + **/ +MarkdownIt.prototype.configure = function (presets) { + const self = this + + if (utils.isString(presets)) { + const presetName = presets + presets = config[presetName] + if (!presets) { throw new Error('Wrong `markdown-it` preset "' + presetName + '", check name') } + } + + if (!presets) { throw new Error('Wrong `markdown-it` preset, can\'t be empty') } + + if (presets.options) { self.set(presets.options) } + + if (presets.components) { + Object.keys(presets.components).forEach(function (name) { + if (presets.components[name].rules) { + self[name].ruler.enableOnly(presets.components[name].rules) + } + if (presets.components[name].rules2) { + self[name].ruler2.enableOnly(presets.components[name].rules2) + } + }) + } + return this +} + +/** chainable + * MarkdownIt.enable(list, ignoreInvalid) + * - list (String|Array): rule name or list of rule names to enable + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Enable list or rules. It will automatically find appropriate components, + * containing rules with given names. If rule not found, and `ignoreInvalid` + * not set - throws exception. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')() + * .enable(['sub', 'sup']) + * .disable('smartquotes'); + * ``` + **/ +MarkdownIt.prototype.enable = function (list, ignoreInvalid) { + let result = [] + + if (!Array.isArray(list)) { list = [list] } + + ['core', 'block', 'inline'].forEach(function (chain) { + result = result.concat(this[chain].ruler.enable(list, true)) + }, this) + + result = result.concat(this.inline.ruler2.enable(list, true)) + + const missed = list.filter(function (name) { return result.indexOf(name) < 0 }) + + if (missed.length && !ignoreInvalid) { + throw new Error('MarkdownIt. Failed to enable unknown rule(s): ' + missed) + } + + return this +} + +/** chainable + * MarkdownIt.disable(list, ignoreInvalid) + * - list (String|Array): rule name or list of rule names to disable. + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * The same as [[MarkdownIt.enable]], but turn specified rules off. + **/ +MarkdownIt.prototype.disable = function (list, ignoreInvalid) { + let result = [] + + if (!Array.isArray(list)) { list = [list] } + + ['core', 'block', 'inline'].forEach(function (chain) { + result = result.concat(this[chain].ruler.disable(list, true)) + }, this) + + result = result.concat(this.inline.ruler2.disable(list, true)) + + const missed = list.filter(function (name) { return result.indexOf(name) < 0 }) + + if (missed.length && !ignoreInvalid) { + throw new Error('MarkdownIt. Failed to disable unknown rule(s): ' + missed) + } + return this +} + +/** chainable + * MarkdownIt.use(plugin, params) + * + * Load specified plugin with given params into current parser instance. + * It's just a sugar to call `plugin(md, params)` with curring. + * + * ##### Example + * + * ```javascript + * var iterator = require('markdown-it-for-inline'); + * var md = require('markdown-it')() + * .use(iterator, 'foo_replace', 'text', function (tokens, idx) { + * tokens[idx].content = tokens[idx].content.replace(/foo/g, 'bar'); + * }); + * ``` + **/ +MarkdownIt.prototype.use = function (plugin /*, params, ... */) { + const args = [this].concat(Array.prototype.slice.call(arguments, 1)) + plugin.apply(plugin, args) + return this +} + +/** internal + * MarkdownIt.parse(src, env) -> Array + * - src (String): source string + * - env (Object): environment sandbox + * + * Parse input string and return list of block tokens (special token type + * "inline" will contain list of inline tokens). You should not call this + * method directly, until you write custom renderer (for example, to produce + * AST). + * + * `env` is used to pass data between "distributed" rules and return additional + * metadata like reference info, needed for the renderer. It also can be used to + * inject data in specific cases. Usually, you will be ok to pass `{}`, + * and then pass updated object to renderer. + **/ +MarkdownIt.prototype.parse = function (src, env) { + if (typeof src !== 'string') { + throw new Error('Input data should be a String') + } + + const state = new this.core.State(src, this, env) + + this.core.process(state) + + return state.tokens +} + +/** + * MarkdownIt.render(src [, env]) -> String + * - src (String): source string + * - env (Object): environment sandbox + * + * Render markdown string into html. It does all magic for you :). + * + * `env` can be used to inject additional metadata (`{}` by default). + * But you will not need it with high probability. See also comment + * in [[MarkdownIt.parse]]. + **/ +MarkdownIt.prototype.render = function (src, env) { + env = env || {} + + return this.renderer.render(this.parse(src, env), this.options, env) +} + +/** internal + * MarkdownIt.parseInline(src, env) -> Array + * - src (String): source string + * - env (Object): environment sandbox + * + * The same as [[MarkdownIt.parse]] but skip all block rules. It returns the + * block tokens list with the single `inline` element, containing parsed inline + * tokens in `children` property. Also updates `env` object. + **/ +MarkdownIt.prototype.parseInline = function (src, env) { + const state = new this.core.State(src, this, env) + + state.inlineMode = true + this.core.process(state) + + return state.tokens +} + +/** + * MarkdownIt.renderInline(src [, env]) -> String + * - src (String): source string + * - env (Object): environment sandbox + * + * Similar to [[MarkdownIt.render]] but for single paragraph content. Result + * will NOT be wrapped into `

    ` tags. + **/ +MarkdownIt.prototype.renderInline = function (src, env) { + env = env || {} + + return this.renderer.render(this.parseInline(src, env), this.options, env) +} + +export default MarkdownIt diff --git a/frontend/node_modules/markdown-it/lib/parser_block.mjs b/frontend/node_modules/markdown-it/lib/parser_block.mjs new file mode 100644 index 0000000..486d68f --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/parser_block.mjs @@ -0,0 +1,134 @@ +/** internal + * class ParserBlock + * + * Block-level tokenizer. + **/ + +import Ruler from './ruler.mjs' +import StateBlock from './rules_block/state_block.mjs' + +import r_table from './rules_block/table.mjs' +import r_code from './rules_block/code.mjs' +import r_fence from './rules_block/fence.mjs' +import r_blockquote from './rules_block/blockquote.mjs' +import r_hr from './rules_block/hr.mjs' +import r_list from './rules_block/list.mjs' +import r_reference from './rules_block/reference.mjs' +import r_html_block from './rules_block/html_block.mjs' +import r_heading from './rules_block/heading.mjs' +import r_lheading from './rules_block/lheading.mjs' +import r_paragraph from './rules_block/paragraph.mjs' + +const _rules = [ + // First 2 params - rule name & source. Secondary array - list of rules, + // which can be terminated by this one. + ['table', r_table, ['paragraph', 'reference']], + ['code', r_code], + ['fence', r_fence, ['paragraph', 'reference', 'blockquote', 'list']], + ['blockquote', r_blockquote, ['paragraph', 'reference', 'blockquote', 'list']], + ['hr', r_hr, ['paragraph', 'reference', 'blockquote', 'list']], + ['list', r_list, ['paragraph', 'reference', 'blockquote']], + ['reference', r_reference], + ['html_block', r_html_block, ['paragraph', 'reference', 'blockquote']], + ['heading', r_heading, ['paragraph', 'reference', 'blockquote']], + ['lheading', r_lheading], + ['paragraph', r_paragraph] +] + +/** + * new ParserBlock() + **/ +function ParserBlock () { + /** + * ParserBlock#ruler -> Ruler + * + * [[Ruler]] instance. Keep configuration of block rules. + **/ + this.ruler = new Ruler() + + for (let i = 0; i < _rules.length; i++) { + this.ruler.push(_rules[i][0], _rules[i][1], { alt: (_rules[i][2] || []).slice() }) + } +} + +// Generate tokens for input range +// +ParserBlock.prototype.tokenize = function (state, startLine, endLine) { + const rules = this.ruler.getRules('') + const len = rules.length + const maxNesting = state.md.options.maxNesting + let line = startLine + let hasEmptyLines = false + + while (line < endLine) { + state.line = line = state.skipEmptyLines(line) + if (line >= endLine) { break } + + // Termination condition for nested calls. + // Nested calls currently used for blockquotes & lists + if (state.sCount[line] < state.blkIndent) { break } + + // If nesting level exceeded - skip tail to the end. That's not ordinary + // situation and we should not care about content. + if (state.level >= maxNesting) { + state.line = endLine + break + } + + // Try all possible rules. + // On success, rule should: + // + // - update `state.line` + // - update `state.tokens` + // - return true + const prevLine = state.line + let ok = false + + for (let i = 0; i < len; i++) { + ok = rules[i](state, line, endLine, false) + if (ok) { + if (prevLine >= state.line) { + throw new Error("block rule didn't increment state.line") + } + break + } + } + + // this can only happen if user disables paragraph rule + if (!ok) throw new Error('none of the block rules matched') + + // set state.tight if we had an empty line before current tag + // i.e. latest empty line should not count + state.tight = !hasEmptyLines + + // paragraph might "eat" one newline after it in nested lists + if (state.isEmpty(state.line - 1)) { + hasEmptyLines = true + } + + line = state.line + + if (line < endLine && state.isEmpty(line)) { + hasEmptyLines = true + line++ + state.line = line + } + } +} + +/** + * ParserBlock.parse(str, md, env, outTokens) + * + * Process input string and push block tokens into `outTokens` + **/ +ParserBlock.prototype.parse = function (src, md, env, outTokens) { + if (!src) { return } + + const state = new this.State(src, md, env, outTokens) + + this.tokenize(state, state.line, state.lineMax) +} + +ParserBlock.prototype.State = StateBlock + +export default ParserBlock diff --git a/frontend/node_modules/markdown-it/lib/parser_core.mjs b/frontend/node_modules/markdown-it/lib/parser_core.mjs new file mode 100644 index 0000000..df61d67 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/parser_core.mjs @@ -0,0 +1,62 @@ +/** internal + * class Core + * + * Top-level rules executor. Glues block/inline parsers and does intermediate + * transformations. + **/ + +import Ruler from './ruler.mjs' +import StateCore from './rules_core/state_core.mjs' + +import r_normalize from './rules_core/normalize.mjs' +import r_block from './rules_core/block.mjs' +import r_inline from './rules_core/inline.mjs' +import r_linkify from './rules_core/linkify.mjs' +import r_replacements from './rules_core/replacements.mjs' +import r_smartquotes from './rules_core/smartquotes.mjs' +import r_text_join from './rules_core/text_join.mjs' + +const _rules = [ + ['normalize', r_normalize], + ['block', r_block], + ['inline', r_inline], + ['linkify', r_linkify], + ['replacements', r_replacements], + ['smartquotes', r_smartquotes], + // `text_join` finds `text_special` tokens (for escape sequences) + // and joins them with the rest of the text + ['text_join', r_text_join] +] + +/** + * new Core() + **/ +function Core () { + /** + * Core#ruler -> Ruler + * + * [[Ruler]] instance. Keep configuration of core rules. + **/ + this.ruler = new Ruler() + + for (let i = 0; i < _rules.length; i++) { + this.ruler.push(_rules[i][0], _rules[i][1]) + } +} + +/** + * Core.process(state) + * + * Executes core chain rules. + **/ +Core.prototype.process = function (state) { + const rules = this.ruler.getRules('') + + for (let i = 0, l = rules.length; i < l; i++) { + rules[i](state) + } +} + +Core.prototype.State = StateCore + +export default Core diff --git a/frontend/node_modules/markdown-it/lib/parser_inline.mjs b/frontend/node_modules/markdown-it/lib/parser_inline.mjs new file mode 100644 index 0000000..c2cc6a1 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/parser_inline.mjs @@ -0,0 +1,197 @@ +/** internal + * class ParserInline + * + * Tokenizes paragraph content. + **/ + +import Ruler from './ruler.mjs' +import StateInline from './rules_inline/state_inline.mjs' + +import r_text from './rules_inline/text.mjs' +import r_linkify from './rules_inline/linkify.mjs' +import r_newline from './rules_inline/newline.mjs' +import r_escape from './rules_inline/escape.mjs' +import r_backticks from './rules_inline/backticks.mjs' +import r_strikethrough from './rules_inline/strikethrough.mjs' +import r_emphasis from './rules_inline/emphasis.mjs' +import r_link from './rules_inline/link.mjs' +import r_image from './rules_inline/image.mjs' +import r_autolink from './rules_inline/autolink.mjs' +import r_html_inline from './rules_inline/html_inline.mjs' +import r_entity from './rules_inline/entity.mjs' + +import r_balance_pairs from './rules_inline/balance_pairs.mjs' +import r_fragments_join from './rules_inline/fragments_join.mjs' + +// Parser rules + +const _rules = [ + ['text', r_text], + ['linkify', r_linkify], + ['newline', r_newline], + ['escape', r_escape], + ['backticks', r_backticks], + ['strikethrough', r_strikethrough.tokenize], + ['emphasis', r_emphasis.tokenize], + ['link', r_link], + ['image', r_image], + ['autolink', r_autolink], + ['html_inline', r_html_inline], + ['entity', r_entity] +] + +// `rule2` ruleset was created specifically for emphasis/strikethrough +// post-processing and may be changed in the future. +// +// Don't use this for anything except pairs (plugins working with `balance_pairs`). +// +const _rules2 = [ + ['balance_pairs', r_balance_pairs], + ['strikethrough', r_strikethrough.postProcess], + ['emphasis', r_emphasis.postProcess], + // rules for pairs separate '**' into its own text tokens, which may be left unused, + // rule below merges unused segments back with the rest of the text + ['fragments_join', r_fragments_join] +] + +/** + * new ParserInline() + **/ +function ParserInline () { + /** + * ParserInline#ruler -> Ruler + * + * [[Ruler]] instance. Keep configuration of inline rules. + **/ + this.ruler = new Ruler() + + for (let i = 0; i < _rules.length; i++) { + this.ruler.push(_rules[i][0], _rules[i][1]) + } + + /** + * ParserInline#ruler2 -> Ruler + * + * [[Ruler]] instance. Second ruler used for post-processing + * (e.g. in emphasis-like rules). + **/ + this.ruler2 = new Ruler() + + for (let i = 0; i < _rules2.length; i++) { + this.ruler2.push(_rules2[i][0], _rules2[i][1]) + } +} + +// Skip single token by running all rules in validation mode; +// returns `true` if any rule reported success +// +ParserInline.prototype.skipToken = function (state) { + const pos = state.pos + const rules = this.ruler.getRules('') + const len = rules.length + const maxNesting = state.md.options.maxNesting + const cache = state.cache + + if (typeof cache[pos] !== 'undefined') { + state.pos = cache[pos] + return + } + + let ok = false + + if (state.level < maxNesting) { + for (let i = 0; i < len; i++) { + // Increment state.level and decrement it later to limit recursion. + // It's harmless to do here, because no tokens are created. But ideally, + // we'd need a separate private state variable for this purpose. + // + state.level++ + ok = rules[i](state, true) + state.level-- + + if (ok) { + if (pos >= state.pos) { throw new Error("inline rule didn't increment state.pos") } + break + } + } + } else { + // Too much nesting, just skip until the end of the paragraph. + // + // NOTE: this will cause links to behave incorrectly in the following case, + // when an amount of `[` is exactly equal to `maxNesting + 1`: + // + // [[[[[[[[[[[[[[[[[[[[[foo]() + // + // TODO: remove this workaround when CM standard will allow nested links + // (we can replace it by preventing links from being parsed in + // validation mode) + // + state.pos = state.posMax + } + + if (!ok) { state.pos++ } + cache[pos] = state.pos +} + +// Generate tokens for input range +// +ParserInline.prototype.tokenize = function (state) { + const rules = this.ruler.getRules('') + const len = rules.length + const end = state.posMax + const maxNesting = state.md.options.maxNesting + + while (state.pos < end) { + // Try all possible rules. + // On success, rule should: + // + // - update `state.pos` + // - update `state.tokens` + // - return true + const prevPos = state.pos + let ok = false + + if (state.level < maxNesting) { + for (let i = 0; i < len; i++) { + ok = rules[i](state, false) + if (ok) { + if (prevPos >= state.pos) { throw new Error("inline rule didn't increment state.pos") } + break + } + } + } + + if (ok) { + if (state.pos >= end) { break } + continue + } + + state.pending += state.src[state.pos++] + } + + if (state.pending) { + state.pushPending() + } +} + +/** + * ParserInline.parse(str, md, env, outTokens) + * + * Process input string and push inline tokens into `outTokens` + **/ +ParserInline.prototype.parse = function (str, md, env, outTokens) { + const state = new this.State(str, md, env, outTokens) + + this.tokenize(state) + + const rules = this.ruler2.getRules('') + const len = rules.length + + for (let i = 0; i < len; i++) { + rules[i](state) + } +} + +ParserInline.prototype.State = StateInline + +export default ParserInline diff --git a/frontend/node_modules/markdown-it/lib/presets/commonmark.mjs b/frontend/node_modules/markdown-it/lib/presets/commonmark.mjs new file mode 100644 index 0000000..7e705ad --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/presets/commonmark.mjs @@ -0,0 +1,88 @@ +// Commonmark default options + +export default { + options: { + // Enable HTML tags in source + html: true, + + // Use '/' to close single tags (
    ) + xhtmlOut: true, + + // Convert '\n' in paragraphs into
    + breaks: false, + + // CSS language prefix for fenced blocks + langPrefix: 'language-', + + // autoconvert URL-like texts to links + linkify: false, + + // Enable some language-neutral replacements + quotes beautification + typographer: false, + + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: '\u201c\u201d\u2018\u2019', /* “”‘’ */ + + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externaly. + // If result starts with ) + xhtmlOut: false, + + // Convert '\n' in paragraphs into
    + breaks: false, + + // CSS language prefix for fenced blocks + langPrefix: 'language-', + + // autoconvert URL-like texts to links + linkify: false, + + // Enable some language-neutral replacements + quotes beautification + typographer: false, + + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: '\u201c\u201d\u2018\u2019', /* “”‘’ */ + + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externaly. + // If result starts with ) + xhtmlOut: false, + + // Convert '\n' in paragraphs into
    + breaks: false, + + // CSS language prefix for fenced blocks + langPrefix: 'language-', + + // autoconvert URL-like texts to links + linkify: false, + + // Enable some language-neutral replacements + quotes beautification + typographer: false, + + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: '\u201c\u201d\u2018\u2019', /* “”‘’ */ + + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externaly. + // If result starts with ' + + escapeHtml(token.content) + + '
    ' +} + +default_rules.code_block = function (tokens, idx, options, env, slf) { + const token = tokens[idx] + + return '' + + escapeHtml(tokens[idx].content) + + '\n' +} + +default_rules.fence = function (tokens, idx, options, env, slf) { + const token = tokens[idx] + const info = token.info ? unescapeAll(token.info).trim() : '' + let langName = '' + let langAttrs = '' + + if (info) { + const arr = info.split(/(\s+)/g) + langName = arr[0] + langAttrs = arr.slice(2).join('') + } + + let highlighted + if (options.highlight) { + highlighted = options.highlight(token.content, langName, langAttrs) || escapeHtml(token.content) + } else { + highlighted = escapeHtml(token.content) + } + + if (highlighted.indexOf('${highlighted}\n` + } + + return `

    ${highlighted}
    \n` +} + +default_rules.image = function (tokens, idx, options, env, slf) { + const token = tokens[idx] + + // "alt" attr MUST be set, even if empty. Because it's mandatory and + // should be placed on proper position for tests. + // + // Replace content with actual value + + token.attrs[token.attrIndex('alt')][1] = + slf.renderInlineAsText(token.children, options, env) + + return slf.renderToken(tokens, idx, options) +} + +default_rules.hardbreak = function (tokens, idx, options /*, env */) { + return options.xhtmlOut ? '
    \n' : '
    \n' +} +default_rules.softbreak = function (tokens, idx, options /*, env */) { + return options.breaks ? (options.xhtmlOut ? '
    \n' : '
    \n') : '\n' +} + +default_rules.text = function (tokens, idx /*, options, env */) { + return escapeHtml(tokens[idx].content) +} + +default_rules.html_block = function (tokens, idx /*, options, env */) { + return tokens[idx].content +} +default_rules.html_inline = function (tokens, idx /*, options, env */) { + return tokens[idx].content +} + +/** + * new Renderer() + * + * Creates new [[Renderer]] instance and fill [[Renderer#rules]] with defaults. + **/ +function Renderer () { + /** + * Renderer#rules -> Object + * + * Contains render rules for tokens. Can be updated and extended. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.renderer.rules.strong_open = function () { return ''; }; + * md.renderer.rules.strong_close = function () { return ''; }; + * + * var result = md.renderInline(...); + * ``` + * + * Each rule is called as independent static function with fixed signature: + * + * ```javascript + * function my_token_render(tokens, idx, options, env, renderer) { + * // ... + * return renderedHTML; + * } + * ``` + * + * See [source code](https://github.com/markdown-it/markdown-it/blob/master/lib/renderer.mjs) + * for more details and examples. + **/ + this.rules = assign({}, default_rules) +} + +/** + * Renderer.renderAttrs(token) -> String + * + * Render token attributes to string. + **/ +Renderer.prototype.renderAttrs = function renderAttrs (token) { + let i, l, result + + if (!token.attrs) { return '' } + + result = '' + + for (i = 0, l = token.attrs.length; i < l; i++) { + result += ' ' + escapeHtml(token.attrs[i][0]) + '="' + escapeHtml(token.attrs[i][1]) + '"' + } + + return result +} + +/** + * Renderer.renderToken(tokens, idx, options) -> String + * - tokens (Array): list of tokens + * - idx (Numbed): token index to render + * - options (Object): params of parser instance + * + * Default token renderer. Can be overriden by custom function + * in [[Renderer#rules]]. + **/ +Renderer.prototype.renderToken = function renderToken (tokens, idx, options) { + const token = tokens[idx] + let result = '' + + // Tight list paragraphs + if (token.hidden) { + return '' + } + + // Insert a newline between hidden paragraph and subsequent opening + // block-level tag. + // + // For example, here we should insert a newline before blockquote: + // - a + // > + // + if (token.block && token.nesting !== -1 && idx && tokens[idx - 1].hidden) { + result += '\n' + } + + // Add token name, e.g. ``. + // + needLf = false + } + } + } + } + + result += needLf ? '>\n' : '>' + + return result +} + +/** + * Renderer.renderInline(tokens, options, env) -> String + * - tokens (Array): list on block tokens to render + * - options (Object): params of parser instance + * - env (Object): additional data from parsed input (references, for example) + * + * The same as [[Renderer.render]], but for single token of `inline` type. + **/ +Renderer.prototype.renderInline = function (tokens, options, env) { + let result = '' + const rules = this.rules + + for (let i = 0, len = tokens.length; i < len; i++) { + const type = tokens[i].type + + if (typeof rules[type] !== 'undefined') { + result += rules[type](tokens, i, options, env, this) + } else { + result += this.renderToken(tokens, i, options) + } + } + + return result +} + +/** internal + * Renderer.renderInlineAsText(tokens, options, env) -> String + * - tokens (Array): list on block tokens to render + * - options (Object): params of parser instance + * - env (Object): additional data from parsed input (references, for example) + * + * Special kludge for image `alt` attributes to conform CommonMark spec. + * Don't try to use it! Spec requires to show `alt` content with stripped markup, + * instead of simple escaping. + **/ +Renderer.prototype.renderInlineAsText = function (tokens, options, env) { + let result = '' + + for (let i = 0, len = tokens.length; i < len; i++) { + switch (tokens[i].type) { + case 'text': + result += tokens[i].content + break + case 'image': + result += this.renderInlineAsText(tokens[i].children, options, env) + break + case 'html_inline': + case 'html_block': + result += tokens[i].content + break + case 'softbreak': + case 'hardbreak': + result += '\n' + break + default: + // all other tokens are skipped + } + } + + return result +} + +/** + * Renderer.render(tokens, options, env) -> String + * - tokens (Array): list on block tokens to render + * - options (Object): params of parser instance + * - env (Object): additional data from parsed input (references, for example) + * + * Takes token stream and generates HTML. Probably, you will never need to call + * this method directly. + **/ +Renderer.prototype.render = function (tokens, options, env) { + let result = '' + const rules = this.rules + + for (let i = 0, len = tokens.length; i < len; i++) { + const type = tokens[i].type + + if (type === 'inline') { + result += this.renderInline(tokens[i].children, options, env) + } else if (typeof rules[type] !== 'undefined') { + result += rules[type](tokens, i, options, env, this) + } else { + result += this.renderToken(tokens, i, options, env) + } + } + + return result +} + +export default Renderer diff --git a/frontend/node_modules/markdown-it/lib/ruler.mjs b/frontend/node_modules/markdown-it/lib/ruler.mjs new file mode 100644 index 0000000..92c98e9 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/ruler.mjs @@ -0,0 +1,340 @@ +/** + * class Ruler + * + * Helper class, used by [[MarkdownIt#core]], [[MarkdownIt#block]] and + * [[MarkdownIt#inline]] to manage sequences of functions (rules): + * + * - keep rules in defined order + * - assign the name to each rule + * - enable/disable rules + * - add/replace rules + * - allow assign rules to additional named chains (in the same) + * - cacheing lists of active rules + * + * You will not need use this class directly until write plugins. For simple + * rules control use [[MarkdownIt.disable]], [[MarkdownIt.enable]] and + * [[MarkdownIt.use]]. + **/ + +/** + * new Ruler() + **/ +function Ruler () { + // List of added rules. Each element is: + // + // { + // name: XXX, + // enabled: Boolean, + // fn: Function(), + // alt: [ name2, name3 ] + // } + // + this.__rules__ = [] + + // Cached rule chains. + // + // First level - chain name, '' for default. + // Second level - diginal anchor for fast filtering by charcodes. + // + this.__cache__ = null +} + +// Helper methods, should not be used directly + +// Find rule index by name +// +Ruler.prototype.__find__ = function (name) { + for (let i = 0; i < this.__rules__.length; i++) { + if (this.__rules__[i].name === name) { + return i + } + } + return -1 +} + +// Build rules lookup cache +// +Ruler.prototype.__compile__ = function () { + const self = this + const chains = [''] + + // collect unique names + self.__rules__.forEach(function (rule) { + if (!rule.enabled) { return } + + rule.alt.forEach(function (altName) { + if (chains.indexOf(altName) < 0) { + chains.push(altName) + } + }) + }) + + self.__cache__ = {} + + chains.forEach(function (chain) { + self.__cache__[chain] = [] + self.__rules__.forEach(function (rule) { + if (!rule.enabled) { return } + + if (chain && rule.alt.indexOf(chain) < 0) { return } + + self.__cache__[chain].push(rule.fn) + }) + }) +} + +/** + * Ruler.at(name, fn [, options]) + * - name (String): rule name to replace. + * - fn (Function): new rule function. + * - options (Object): new rule options (not mandatory). + * + * Replace rule by name with new function & options. Throws error if name not + * found. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * Replace existing typographer replacement rule with new one: + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.core.ruler.at('replacements', function replace(state) { + * //... + * }); + * ``` + **/ +Ruler.prototype.at = function (name, fn, options) { + const index = this.__find__(name) + const opt = options || {} + + if (index === -1) { throw new Error('Parser rule not found: ' + name) } + + this.__rules__[index].fn = fn + this.__rules__[index].alt = opt.alt || [] + this.__cache__ = null +} + +/** + * Ruler.before(beforeName, ruleName, fn [, options]) + * - beforeName (String): new rule will be added before this one. + * - ruleName (String): name of added rule. + * - fn (Function): rule function. + * - options (Object): rule options (not mandatory). + * + * Add new rule to chain before one with given name. See also + * [[Ruler.after]], [[Ruler.push]]. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.block.ruler.before('paragraph', 'my_rule', function replace(state) { + * //... + * }); + * ``` + **/ +Ruler.prototype.before = function (beforeName, ruleName, fn, options) { + const index = this.__find__(beforeName) + const opt = options || {} + + if (index === -1) { throw new Error('Parser rule not found: ' + beforeName) } + + this.__rules__.splice(index, 0, { + name: ruleName, + enabled: true, + fn, + alt: opt.alt || [] + }) + + this.__cache__ = null +} + +/** + * Ruler.after(afterName, ruleName, fn [, options]) + * - afterName (String): new rule will be added after this one. + * - ruleName (String): name of added rule. + * - fn (Function): rule function. + * - options (Object): rule options (not mandatory). + * + * Add new rule to chain after one with given name. See also + * [[Ruler.before]], [[Ruler.push]]. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.inline.ruler.after('text', 'my_rule', function replace(state) { + * //... + * }); + * ``` + **/ +Ruler.prototype.after = function (afterName, ruleName, fn, options) { + const index = this.__find__(afterName) + const opt = options || {} + + if (index === -1) { throw new Error('Parser rule not found: ' + afterName) } + + this.__rules__.splice(index + 1, 0, { + name: ruleName, + enabled: true, + fn, + alt: opt.alt || [] + }) + + this.__cache__ = null +} + +/** + * Ruler.push(ruleName, fn [, options]) + * - ruleName (String): name of added rule. + * - fn (Function): rule function. + * - options (Object): rule options (not mandatory). + * + * Push new rule to the end of chain. See also + * [[Ruler.before]], [[Ruler.after]]. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.core.ruler.push('my_rule', function replace(state) { + * //... + * }); + * ``` + **/ +Ruler.prototype.push = function (ruleName, fn, options) { + const opt = options || {} + + this.__rules__.push({ + name: ruleName, + enabled: true, + fn, + alt: opt.alt || [] + }) + + this.__cache__ = null +} + +/** + * Ruler.enable(list [, ignoreInvalid]) -> Array + * - list (String|Array): list of rule names to enable. + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Enable rules with given names. If any rule name not found - throw Error. + * Errors can be disabled by second param. + * + * Returns list of found rule names (if no exception happened). + * + * See also [[Ruler.disable]], [[Ruler.enableOnly]]. + **/ +Ruler.prototype.enable = function (list, ignoreInvalid) { + if (!Array.isArray(list)) { list = [list] } + + const result = [] + + // Search by name and enable + list.forEach(function (name) { + const idx = this.__find__(name) + + if (idx < 0) { + if (ignoreInvalid) { return } + throw new Error('Rules manager: invalid rule name ' + name) + } + this.__rules__[idx].enabled = true + result.push(name) + }, this) + + this.__cache__ = null + return result +} + +/** + * Ruler.enableOnly(list [, ignoreInvalid]) + * - list (String|Array): list of rule names to enable (whitelist). + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Enable rules with given names, and disable everything else. If any rule name + * not found - throw Error. Errors can be disabled by second param. + * + * See also [[Ruler.disable]], [[Ruler.enable]]. + **/ +Ruler.prototype.enableOnly = function (list, ignoreInvalid) { + if (!Array.isArray(list)) { list = [list] } + + this.__rules__.forEach(function (rule) { rule.enabled = false }) + + this.enable(list, ignoreInvalid) +} + +/** + * Ruler.disable(list [, ignoreInvalid]) -> Array + * - list (String|Array): list of rule names to disable. + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Disable rules with given names. If any rule name not found - throw Error. + * Errors can be disabled by second param. + * + * Returns list of found rule names (if no exception happened). + * + * See also [[Ruler.enable]], [[Ruler.enableOnly]]. + **/ +Ruler.prototype.disable = function (list, ignoreInvalid) { + if (!Array.isArray(list)) { list = [list] } + + const result = [] + + // Search by name and disable + list.forEach(function (name) { + const idx = this.__find__(name) + + if (idx < 0) { + if (ignoreInvalid) { return } + throw new Error('Rules manager: invalid rule name ' + name) + } + this.__rules__[idx].enabled = false + result.push(name) + }, this) + + this.__cache__ = null + return result +} + +/** + * Ruler.getRules(chainName) -> Array + * + * Return array of active functions (rules) for given chain name. It analyzes + * rules configuration, compiles caches if not exists and returns result. + * + * Default chain name is `''` (empty string). It can't be skipped. That's + * done intentionally, to keep signature monomorphic for high speed. + **/ +Ruler.prototype.getRules = function (chainName) { + if (this.__cache__ === null) { + this.__compile__() + } + + // Chain can be empty, if rules disabled. But we still have to return Array. + return this.__cache__[chainName] || [] +} + +export default Ruler diff --git a/frontend/node_modules/markdown-it/lib/rules_block/blockquote.mjs b/frontend/node_modules/markdown-it/lib/rules_block/blockquote.mjs new file mode 100644 index 0000000..b61da02 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_block/blockquote.mjs @@ -0,0 +1,209 @@ +// Block quotes + +import { isSpace } from '../common/utils.mjs' + +export default function blockquote (state, startLine, endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine] + let max = state.eMarks[startLine] + + const oldLineMax = state.lineMax + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { return false } + + // check the block quote marker + if (state.src.charCodeAt(pos) !== 0x3E/* > */) { return false } + + // we know that it's going to be a valid blockquote, + // so no point trying to find the end of it in silent mode + if (silent) { return true } + + const oldBMarks = [] + const oldBSCount = [] + const oldSCount = [] + const oldTShift = [] + + const terminatorRules = state.md.block.ruler.getRules('blockquote') + + const oldParentType = state.parentType + state.parentType = 'blockquote' + let lastLineEmpty = false + let nextLine + + // Search the end of the block + // + // Block ends with either: + // 1. an empty line outside: + // ``` + // > test + // + // ``` + // 2. an empty line inside: + // ``` + // > + // test + // ``` + // 3. another tag: + // ``` + // > test + // - - - + // ``` + for (nextLine = startLine; nextLine < endLine; nextLine++) { + // check if it's outdented, i.e. it's inside list item and indented + // less than said list item: + // + // ``` + // 1. anything + // > current blockquote + // 2. checking this line + // ``` + const isOutdented = state.sCount[nextLine] < state.blkIndent + + pos = state.bMarks[nextLine] + state.tShift[nextLine] + max = state.eMarks[nextLine] + + if (pos >= max) { + // Case 1: line is not inside the blockquote, and this line is empty. + break + } + + if (state.src.charCodeAt(pos++) === 0x3E/* > */ && !isOutdented) { + // This line is inside the blockquote. + + // set offset past spaces and ">" + let initial = state.sCount[nextLine] + 1 + let spaceAfterMarker + let adjustTab + + // skip one optional space after '>' + if (state.src.charCodeAt(pos) === 0x20 /* space */) { + // ' > test ' + // ^ -- position start of line here: + pos++ + initial++ + adjustTab = false + spaceAfterMarker = true + } else if (state.src.charCodeAt(pos) === 0x09 /* tab */) { + spaceAfterMarker = true + + if ((state.bsCount[nextLine] + initial) % 4 === 3) { + // ' >\t test ' + // ^ -- position start of line here (tab has width===1) + pos++ + initial++ + adjustTab = false + } else { + // ' >\t test ' + // ^ -- position start of line here + shift bsCount slightly + // to make extra space appear + adjustTab = true + } + } else { + spaceAfterMarker = false + } + + let offset = initial + oldBMarks.push(state.bMarks[nextLine]) + state.bMarks[nextLine] = pos + + while (pos < max) { + const ch = state.src.charCodeAt(pos) + + if (isSpace(ch)) { + if (ch === 0x09) { + offset += 4 - (offset + state.bsCount[nextLine] + (adjustTab ? 1 : 0)) % 4 + } else { + offset++ + } + } else { + break + } + + pos++ + } + + lastLineEmpty = pos >= max + + oldBSCount.push(state.bsCount[nextLine]) + state.bsCount[nextLine] = state.sCount[nextLine] + 1 + (spaceAfterMarker ? 1 : 0) + + oldSCount.push(state.sCount[nextLine]) + state.sCount[nextLine] = offset - initial + + oldTShift.push(state.tShift[nextLine]) + state.tShift[nextLine] = pos - state.bMarks[nextLine] + continue + } + + // Case 2: line is not inside the blockquote, and the last line was empty. + if (lastLineEmpty) { break } + + // Case 3: another tag found. + let terminate = false + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true + break + } + } + + if (terminate) { + // Quirk to enforce "hard termination mode" for paragraphs; + // normally if you call `tokenize(state, startLine, nextLine)`, + // paragraphs will look below nextLine for paragraph continuation, + // but if blockquote is terminated by another tag, they shouldn't + state.lineMax = nextLine + + if (state.blkIndent !== 0) { + // state.blkIndent was non-zero, we now set it to zero, + // so we need to re-calculate all offsets to appear as + // if indent wasn't changed + oldBMarks.push(state.bMarks[nextLine]) + oldBSCount.push(state.bsCount[nextLine]) + oldTShift.push(state.tShift[nextLine]) + oldSCount.push(state.sCount[nextLine]) + state.sCount[nextLine] -= state.blkIndent + } + + break + } + + oldBMarks.push(state.bMarks[nextLine]) + oldBSCount.push(state.bsCount[nextLine]) + oldTShift.push(state.tShift[nextLine]) + oldSCount.push(state.sCount[nextLine]) + + // A negative indentation means that this is a paragraph continuation + // + state.sCount[nextLine] = -1 + } + + const oldIndent = state.blkIndent + state.blkIndent = 0 + + const token_o = state.push('blockquote_open', 'blockquote', 1) + token_o.markup = '>' + const lines = [startLine, 0] + token_o.map = lines + + state.md.block.tokenize(state, startLine, nextLine) + + const token_c = state.push('blockquote_close', 'blockquote', -1) + token_c.markup = '>' + + state.lineMax = oldLineMax + state.parentType = oldParentType + lines[1] = state.line + + // Restore original tShift; this might not be necessary since the parser + // has already been here, but just to make sure we can do that. + for (let i = 0; i < oldTShift.length; i++) { + state.bMarks[i + startLine] = oldBMarks[i] + state.tShift[i + startLine] = oldTShift[i] + state.sCount[i + startLine] = oldSCount[i] + state.bsCount[i + startLine] = oldBSCount[i] + } + state.blkIndent = oldIndent + + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_block/code.mjs b/frontend/node_modules/markdown-it/lib/rules_block/code.mjs new file mode 100644 index 0000000..e45e6f9 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_block/code.mjs @@ -0,0 +1,30 @@ +// Code block (4 spaces padded) + +export default function code (state, startLine, endLine/*, silent */) { + if (state.sCount[startLine] - state.blkIndent < 4) { return false } + + let nextLine = startLine + 1 + let last = nextLine + + while (nextLine < endLine) { + if (state.isEmpty(nextLine)) { + nextLine++ + continue + } + + if (state.sCount[nextLine] - state.blkIndent >= 4) { + nextLine++ + last = nextLine + continue + } + break + } + + state.line = last + + const token = state.push('code_block', 'code', 0) + token.content = state.getLines(startLine, last, 4 + state.blkIndent, false) + '\n' + token.map = [startLine, state.line] + + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_block/fence.mjs b/frontend/node_modules/markdown-it/lib/rules_block/fence.mjs new file mode 100644 index 0000000..930f7b3 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_block/fence.mjs @@ -0,0 +1,94 @@ +// fences (``` lang, ~~~ lang) + +export default function fence (state, startLine, endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine] + let max = state.eMarks[startLine] + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { return false } + + if (pos + 3 > max) { return false } + + const marker = state.src.charCodeAt(pos) + + if (marker !== 0x7E/* ~ */ && marker !== 0x60 /* ` */) { + return false + } + + // scan marker length + let mem = pos + pos = state.skipChars(pos, marker) + + let len = pos - mem + + if (len < 3) { return false } + + const markup = state.src.slice(mem, pos) + const params = state.src.slice(pos, max) + + if (marker === 0x60 /* ` */) { + if (params.indexOf(String.fromCharCode(marker)) >= 0) { + return false + } + } + + // Since start is found, we can report success here in validation mode + if (silent) { return true } + + // search end of block + let nextLine = startLine + let haveEndMarker = false + + for (;;) { + nextLine++ + if (nextLine >= endLine) { + // unclosed block should be autoclosed by end of document. + // also block seems to be autoclosed by end of parent + break + } + + pos = mem = state.bMarks[nextLine] + state.tShift[nextLine] + max = state.eMarks[nextLine] + + if (pos < max && state.sCount[nextLine] < state.blkIndent) { + // non-empty line with negative indent should stop the list: + // - ``` + // test + break + } + + if (state.src.charCodeAt(pos) !== marker) { continue } + + if (state.sCount[nextLine] - state.blkIndent >= 4) { + // closing fence should be indented less than 4 spaces + continue + } + + pos = state.skipChars(pos, marker) + + // closing code fence must be at least as long as the opening one + if (pos - mem < len) { continue } + + // make sure tail has spaces only + pos = state.skipSpaces(pos) + + if (pos < max) { continue } + + haveEndMarker = true + // found! + break + } + + // If a fence has heading spaces, they should be removed from its inner block + len = state.sCount[startLine] + + state.line = nextLine + (haveEndMarker ? 1 : 0) + + const token = state.push('fence', 'code', 0) + token.info = params + token.content = state.getLines(startLine + 1, nextLine, len, true) + token.markup = markup + token.map = [startLine, state.line] + + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_block/heading.mjs b/frontend/node_modules/markdown-it/lib/rules_block/heading.mjs new file mode 100644 index 0000000..d2f7b79 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_block/heading.mjs @@ -0,0 +1,51 @@ +// heading (#, ##, ...) + +import { isSpace } from '../common/utils.mjs' + +export default function heading (state, startLine, endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine] + let max = state.eMarks[startLine] + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { return false } + + let ch = state.src.charCodeAt(pos) + + if (ch !== 0x23/* # */ || pos >= max) { return false } + + // count heading level + let level = 1 + ch = state.src.charCodeAt(++pos) + while (ch === 0x23/* # */ && pos < max && level <= 6) { + level++ + ch = state.src.charCodeAt(++pos) + } + + if (level > 6 || (pos < max && !isSpace(ch))) { return false } + + if (silent) { return true } + + // Let's cut tails like ' ### ' from the end of string + + max = state.skipSpacesBack(max, pos) + const tmp = state.skipCharsBack(max, 0x23, pos) // # + if (tmp > pos && isSpace(state.src.charCodeAt(tmp - 1))) { + max = tmp + } + + state.line = startLine + 1 + + const token_o = state.push('heading_open', 'h' + String(level), 1) + token_o.markup = '########'.slice(0, level) + token_o.map = [startLine, state.line] + + const token_i = state.push('inline', '', 0) + token_i.content = state.src.slice(pos, max).trim() + token_i.map = [startLine, state.line] + token_i.children = [] + + const token_c = state.push('heading_close', 'h' + String(level), -1) + token_c.markup = '########'.slice(0, level) + + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_block/hr.mjs b/frontend/node_modules/markdown-it/lib/rules_block/hr.mjs new file mode 100644 index 0000000..d467b21 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_block/hr.mjs @@ -0,0 +1,40 @@ +// Horizontal rule + +import { isSpace } from '../common/utils.mjs' + +export default function hr (state, startLine, endLine, silent) { + const max = state.eMarks[startLine] + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { return false } + + let pos = state.bMarks[startLine] + state.tShift[startLine] + const marker = state.src.charCodeAt(pos++) + + // Check hr marker + if (marker !== 0x2A/* * */ && + marker !== 0x2D/* - */ && + marker !== 0x5F/* _ */) { + return false + } + + // markers can be mixed with spaces, but there should be at least 3 of them + + let cnt = 1 + while (pos < max) { + const ch = state.src.charCodeAt(pos++) + if (ch !== marker && !isSpace(ch)) { return false } + if (ch === marker) { cnt++ } + } + + if (cnt < 3) { return false } + + if (silent) { return true } + + state.line = startLine + 1 + + const token = state.push('hr', 'hr', 0) + token.map = [startLine, state.line] + token.markup = Array(cnt + 1).join(String.fromCharCode(marker)) + + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_block/html_block.mjs b/frontend/node_modules/markdown-it/lib/rules_block/html_block.mjs new file mode 100644 index 0000000..197520f --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_block/html_block.mjs @@ -0,0 +1,69 @@ +// HTML block + +import block_names from '../common/html_blocks.mjs' +import { HTML_OPEN_CLOSE_TAG_RE } from '../common/html_re.mjs' + +// An array of opening and corresponding closing sequences for html tags, +// last argument defines whether it can terminate a paragraph or not +// +const HTML_SEQUENCES = [ + [/^<(script|pre|style|textarea)(?=(\s|>|$))/i, /<\/(script|pre|style|textarea)>/i, true], + [/^/, true], + [/^<\?/, /\?>/, true], + [/^/, true], + [/^/, true], + [new RegExp('^|$))', 'i'), /^$/, true], + [new RegExp(HTML_OPEN_CLOSE_TAG_RE.source + '\\s*$'), /^$/, false] +] + +export default function html_block (state, startLine, endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine] + let max = state.eMarks[startLine] + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { return false } + + if (!state.md.options.html) { return false } + + if (state.src.charCodeAt(pos) !== 0x3C/* < */) { return false } + + let lineText = state.src.slice(pos, max) + + let i = 0 + for (; i < HTML_SEQUENCES.length; i++) { + if (HTML_SEQUENCES[i][0].test(lineText)) { break } + } + if (i === HTML_SEQUENCES.length) { return false } + + if (silent) { + // true if this sequence can be a terminator, false otherwise + return HTML_SEQUENCES[i][2] + } + + let nextLine = startLine + 1 + + // If we are here - we detected HTML block. + // Let's roll down till block end. + if (!HTML_SEQUENCES[i][1].test(lineText)) { + for (; nextLine < endLine; nextLine++) { + if (state.sCount[nextLine] < state.blkIndent) { break } + + pos = state.bMarks[nextLine] + state.tShift[nextLine] + max = state.eMarks[nextLine] + lineText = state.src.slice(pos, max) + + if (HTML_SEQUENCES[i][1].test(lineText)) { + if (lineText.length !== 0) { nextLine++ } + break + } + } + } + + state.line = nextLine + + const token = state.push('html_block', '', 0) + token.map = [startLine, nextLine] + token.content = state.getLines(startLine, nextLine, state.blkIndent, true) + + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_block/lheading.mjs b/frontend/node_modules/markdown-it/lib/rules_block/lheading.mjs new file mode 100644 index 0000000..ee3b9a3 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_block/lheading.mjs @@ -0,0 +1,82 @@ +// lheading (---, ===) + +export default function lheading (state, startLine, endLine/*, silent */) { + const terminatorRules = state.md.block.ruler.getRules('paragraph') + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { return false } + + const oldParentType = state.parentType + state.parentType = 'paragraph' // use paragraph to match terminatorRules + + // jump line-by-line until empty one or EOF + let level = 0 + let marker + let nextLine = startLine + 1 + + for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) { + // this would be a code block normally, but after paragraph + // it's considered a lazy continuation regardless of what's there + if (state.sCount[nextLine] - state.blkIndent > 3) { continue } + + // + // Check for underline in setext header + // + if (state.sCount[nextLine] >= state.blkIndent) { + let pos = state.bMarks[nextLine] + state.tShift[nextLine] + const max = state.eMarks[nextLine] + + if (pos < max) { + marker = state.src.charCodeAt(pos) + + if (marker === 0x2D/* - */ || marker === 0x3D/* = */) { + pos = state.skipChars(pos, marker) + pos = state.skipSpaces(pos) + + if (pos >= max) { + level = (marker === 0x3D/* = */ ? 1 : 2) + break + } + } + } + } + + // quirk for blockquotes, this line should already be checked by that rule + if (state.sCount[nextLine] < 0) { continue } + + // Some tags can terminate paragraph without empty line. + let terminate = false + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true + break + } + } + if (terminate) { break } + } + + if (!level) { + // Didn't find valid underline + return false + } + + const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim() + + state.line = nextLine + 1 + + const token_o = state.push('heading_open', 'h' + String(level), 1) + token_o.markup = String.fromCharCode(marker) + token_o.map = [startLine, state.line] + + const token_i = state.push('inline', '', 0) + token_i.content = content + token_i.map = [startLine, state.line - 1] + token_i.children = [] + + const token_c = state.push('heading_close', 'h' + String(level), -1) + token_c.markup = String.fromCharCode(marker) + + state.parentType = oldParentType + + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_block/list.mjs b/frontend/node_modules/markdown-it/lib/rules_block/list.mjs new file mode 100644 index 0000000..fb53abd --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_block/list.mjs @@ -0,0 +1,331 @@ +// Lists + +import { isSpace } from '../common/utils.mjs' + +// Search `[-+*][\n ]`, returns next pos after marker on success +// or -1 on fail. +function skipBulletListMarker (state, startLine) { + const max = state.eMarks[startLine] + let pos = state.bMarks[startLine] + state.tShift[startLine] + + const marker = state.src.charCodeAt(pos++) + // Check bullet + if (marker !== 0x2A/* * */ && + marker !== 0x2D/* - */ && + marker !== 0x2B/* + */) { + return -1 + } + + if (pos < max) { + const ch = state.src.charCodeAt(pos) + + if (!isSpace(ch)) { + // " -test " - is not a list item + return -1 + } + } + + return pos +} + +// Search `\d+[.)][\n ]`, returns next pos after marker on success +// or -1 on fail. +function skipOrderedListMarker (state, startLine) { + const start = state.bMarks[startLine] + state.tShift[startLine] + const max = state.eMarks[startLine] + let pos = start + + // List marker should have at least 2 chars (digit + dot) + if (pos + 1 >= max) { return -1 } + + let ch = state.src.charCodeAt(pos++) + + if (ch < 0x30/* 0 */ || ch > 0x39/* 9 */) { return -1 } + + for (;;) { + // EOL -> fail + if (pos >= max) { return -1 } + + ch = state.src.charCodeAt(pos++) + + if (ch >= 0x30/* 0 */ && ch <= 0x39/* 9 */) { + // List marker should have no more than 9 digits + // (prevents integer overflow in browsers) + if (pos - start >= 10) { return -1 } + + continue + } + + // found valid marker + if (ch === 0x29/* ) */ || ch === 0x2e/* . */) { + break + } + + return -1 + } + + if (pos < max) { + ch = state.src.charCodeAt(pos) + + if (!isSpace(ch)) { + // " 1.test " - is not a list item + return -1 + } + } + return pos +} + +function markTightParagraphs (state, idx) { + const level = state.level + 2 + + for (let i = idx + 2, l = state.tokens.length - 2; i < l; i++) { + if (state.tokens[i].level === level && state.tokens[i].type === 'paragraph_open') { + state.tokens[i + 2].hidden = true + state.tokens[i].hidden = true + i += 2 + } + } +} + +export default function list (state, startLine, endLine, silent) { + let max, pos, start, token + let nextLine = startLine + let tight = true + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[nextLine] - state.blkIndent >= 4) { return false } + + // Special case: + // - item 1 + // - item 2 + // - item 3 + // - item 4 + // - this one is a paragraph continuation + if (state.listIndent >= 0 && + state.sCount[nextLine] - state.listIndent >= 4 && + state.sCount[nextLine] < state.blkIndent) { + return false + } + + let isTerminatingParagraph = false + + // limit conditions when list can interrupt + // a paragraph (validation mode only) + if (silent && state.parentType === 'paragraph') { + // Next list item should still terminate previous list item; + // + // This code can fail if plugins use blkIndent as well as lists, + // but I hope the spec gets fixed long before that happens. + // + if (state.sCount[nextLine] >= state.blkIndent) { + isTerminatingParagraph = true + } + } + + // Detect list type and position after marker + let isOrdered + let markerValue + let posAfterMarker + if ((posAfterMarker = skipOrderedListMarker(state, nextLine)) >= 0) { + isOrdered = true + start = state.bMarks[nextLine] + state.tShift[nextLine] + markerValue = Number(state.src.slice(start, posAfterMarker - 1)) + + // If we're starting a new ordered list right after + // a paragraph, it should start with 1. + if (isTerminatingParagraph && markerValue !== 1) return false + } else if ((posAfterMarker = skipBulletListMarker(state, nextLine)) >= 0) { + isOrdered = false + } else { + return false + } + + // If we're starting a new unordered list right after + // a paragraph, first line should not be empty. + if (isTerminatingParagraph) { + if (state.skipSpaces(posAfterMarker) >= state.eMarks[nextLine]) return false + } + + // For validation mode we can terminate immediately + if (silent) { return true } + + // We should terminate list on style change. Remember first one to compare. + const markerCharCode = state.src.charCodeAt(posAfterMarker - 1) + + // Start list + const listTokIdx = state.tokens.length + + if (isOrdered) { + token = state.push('ordered_list_open', 'ol', 1) + if (markerValue !== 1) { + token.attrs = [['start', markerValue]] + } + } else { + token = state.push('bullet_list_open', 'ul', 1) + } + + const listLines = [nextLine, 0] + token.map = listLines + token.markup = String.fromCharCode(markerCharCode) + + // + // Iterate list items + // + + let prevEmptyEnd = false + const terminatorRules = state.md.block.ruler.getRules('list') + + const oldParentType = state.parentType + state.parentType = 'list' + + while (nextLine < endLine) { + pos = posAfterMarker + max = state.eMarks[nextLine] + + const initial = state.sCount[nextLine] + posAfterMarker - (state.bMarks[nextLine] + state.tShift[nextLine]) + let offset = initial + + while (pos < max) { + const ch = state.src.charCodeAt(pos) + + if (ch === 0x09) { + offset += 4 - (offset + state.bsCount[nextLine]) % 4 + } else if (ch === 0x20) { + offset++ + } else { + break + } + + pos++ + } + + const contentStart = pos + let indentAfterMarker + + if (contentStart >= max) { + // trimming space in "- \n 3" case, indent is 1 here + indentAfterMarker = 1 + } else { + indentAfterMarker = offset - initial + } + + // If we have more than 4 spaces, the indent is 1 + // (the rest is just indented code block) + if (indentAfterMarker > 4) { indentAfterMarker = 1 } + + // " - test" + // ^^^^^ - calculating total length of this thing + const indent = initial + indentAfterMarker + + // Run subparser & write tokens + token = state.push('list_item_open', 'li', 1) + token.markup = String.fromCharCode(markerCharCode) + const itemLines = [nextLine, 0] + token.map = itemLines + if (isOrdered) { + token.info = state.src.slice(start, posAfterMarker - 1) + } + + // change current state, then restore it after parser subcall + const oldTight = state.tight + const oldTShift = state.tShift[nextLine] + const oldSCount = state.sCount[nextLine] + + // - example list + // ^ listIndent position will be here + // ^ blkIndent position will be here + // + const oldListIndent = state.listIndent + state.listIndent = state.blkIndent + state.blkIndent = indent + + state.tight = true + state.tShift[nextLine] = contentStart - state.bMarks[nextLine] + state.sCount[nextLine] = offset + + if (contentStart >= max && state.isEmpty(nextLine + 1)) { + // workaround for this case + // (list item is empty, list terminates before "foo"): + // ~~~~~~~~ + // - + // + // foo + // ~~~~~~~~ + state.line = Math.min(state.line + 2, endLine) + } else { + state.md.block.tokenize(state, nextLine, endLine, true) + } + + // If any of list item is tight, mark list as tight + if (!state.tight || prevEmptyEnd) { + tight = false + } + // Item become loose if finish with empty line, + // but we should filter last element, because it means list finish + prevEmptyEnd = (state.line - nextLine) > 1 && state.isEmpty(state.line - 1) + + state.blkIndent = state.listIndent + state.listIndent = oldListIndent + state.tShift[nextLine] = oldTShift + state.sCount[nextLine] = oldSCount + state.tight = oldTight + + token = state.push('list_item_close', 'li', -1) + token.markup = String.fromCharCode(markerCharCode) + + nextLine = state.line + itemLines[1] = nextLine + + if (nextLine >= endLine) { break } + + // + // Try to check if list is terminated or continued. + // + if (state.sCount[nextLine] < state.blkIndent) { break } + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[nextLine] - state.blkIndent >= 4) { break } + + // fail if terminating block found + let terminate = false + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true + break + } + } + if (terminate) { break } + + // fail if list has another type + if (isOrdered) { + posAfterMarker = skipOrderedListMarker(state, nextLine) + if (posAfterMarker < 0) { break } + start = state.bMarks[nextLine] + state.tShift[nextLine] + } else { + posAfterMarker = skipBulletListMarker(state, nextLine) + if (posAfterMarker < 0) { break } + } + + if (markerCharCode !== state.src.charCodeAt(posAfterMarker - 1)) { break } + } + + // Finalize list + if (isOrdered) { + token = state.push('ordered_list_close', 'ol', -1) + } else { + token = state.push('bullet_list_close', 'ul', -1) + } + token.markup = String.fromCharCode(markerCharCode) + + listLines[1] = nextLine + state.line = nextLine + + state.parentType = oldParentType + + // mark paragraphs tight if needed + if (tight) { + markTightParagraphs(state, listTokIdx) + } + + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_block/paragraph.mjs b/frontend/node_modules/markdown-it/lib/rules_block/paragraph.mjs new file mode 100644 index 0000000..6ecdcef --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_block/paragraph.mjs @@ -0,0 +1,46 @@ +// Paragraph + +export default function paragraph (state, startLine, endLine) { + const terminatorRules = state.md.block.ruler.getRules('paragraph') + const oldParentType = state.parentType + let nextLine = startLine + 1 + state.parentType = 'paragraph' + + // jump line-by-line until empty one or EOF + for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) { + // this would be a code block normally, but after paragraph + // it's considered a lazy continuation regardless of what's there + if (state.sCount[nextLine] - state.blkIndent > 3) { continue } + + // quirk for blockquotes, this line should already be checked by that rule + if (state.sCount[nextLine] < 0) { continue } + + // Some tags can terminate paragraph without empty line. + let terminate = false + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true + break + } + } + if (terminate) { break } + } + + const content = state.getLines(startLine, nextLine, state.blkIndent, false).trim() + + state.line = nextLine + + const token_o = state.push('paragraph_open', 'p', 1) + token_o.map = [startLine, state.line] + + const token_i = state.push('inline', '', 0) + token_i.content = content + token_i.map = [startLine, state.line] + token_i.children = [] + + state.push('paragraph_close', 'p', -1) + + state.parentType = oldParentType + + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_block/reference.mjs b/frontend/node_modules/markdown-it/lib/rules_block/reference.mjs new file mode 100644 index 0000000..4166286 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_block/reference.mjs @@ -0,0 +1,212 @@ +import { isSpace, normalizeReference } from '../common/utils.mjs' + +export default function reference (state, startLine, _endLine, silent) { + let pos = state.bMarks[startLine] + state.tShift[startLine] + let max = state.eMarks[startLine] + let nextLine = startLine + 1 + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[startLine] - state.blkIndent >= 4) { return false } + + if (state.src.charCodeAt(pos) !== 0x5B/* [ */) { return false } + + function getNextLine (nextLine) { + const endLine = state.lineMax + + if (nextLine >= endLine || state.isEmpty(nextLine)) { + // empty line or end of input + return null + } + + let isContinuation = false + + // this would be a code block normally, but after paragraph + // it's considered a lazy continuation regardless of what's there + if (state.sCount[nextLine] - state.blkIndent > 3) { isContinuation = true } + + // quirk for blockquotes, this line should already be checked by that rule + if (state.sCount[nextLine] < 0) { isContinuation = true } + + if (!isContinuation) { + const terminatorRules = state.md.block.ruler.getRules('reference') + const oldParentType = state.parentType + state.parentType = 'reference' + + // Some tags can terminate paragraph without empty line. + let terminate = false + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true + break + } + } + + state.parentType = oldParentType + if (terminate) { + // terminated by another block + return null + } + } + + const pos = state.bMarks[nextLine] + state.tShift[nextLine] + const max = state.eMarks[nextLine] + + // max + 1 explicitly includes the newline + return state.src.slice(pos, max + 1) + } + + let str = state.src.slice(pos, max + 1) + + max = str.length + let labelEnd = -1 + + for (pos = 1; pos < max; pos++) { + const ch = str.charCodeAt(pos) + if (ch === 0x5B /* [ */) { + return false + } else if (ch === 0x5D /* ] */) { + labelEnd = pos + break + } else if (ch === 0x0A /* \n */) { + const lineContent = getNextLine(nextLine) + if (lineContent !== null) { + str += lineContent + max = str.length + nextLine++ + } + } else if (ch === 0x5C /* \ */) { + pos++ + if (pos < max && str.charCodeAt(pos) === 0x0A) { + const lineContent = getNextLine(nextLine) + if (lineContent !== null) { + str += lineContent + max = str.length + nextLine++ + } + } + } + } + + if (labelEnd < 0 || str.charCodeAt(labelEnd + 1) !== 0x3A/* : */) { return false } + + // [label]: destination 'title' + // ^^^ skip optional whitespace here + for (pos = labelEnd + 2; pos < max; pos++) { + const ch = str.charCodeAt(pos) + if (ch === 0x0A) { + const lineContent = getNextLine(nextLine) + if (lineContent !== null) { + str += lineContent + max = str.length + nextLine++ + } + } else if (isSpace(ch)) { + /* eslint no-empty:0 */ + } else { + break + } + } + + // [label]: destination 'title' + // ^^^^^^^^^^^ parse this + const destRes = state.md.helpers.parseLinkDestination(str, pos, max) + if (!destRes.ok) { return false } + + const href = state.md.normalizeLink(destRes.str) + if (!state.md.validateLink(href)) { return false } + + pos = destRes.pos + + // save cursor state, we could require to rollback later + const destEndPos = pos + const destEndLineNo = nextLine + + // [label]: destination 'title' + // ^^^ skipping those spaces + const start = pos + for (; pos < max; pos++) { + const ch = str.charCodeAt(pos) + if (ch === 0x0A) { + const lineContent = getNextLine(nextLine) + if (lineContent !== null) { + str += lineContent + max = str.length + nextLine++ + } + } else if (isSpace(ch)) { + /* eslint no-empty:0 */ + } else { + break + } + } + + // [label]: destination 'title' + // ^^^^^^^ parse this + let titleRes = state.md.helpers.parseLinkTitle(str, pos, max) + while (titleRes.can_continue) { + const lineContent = getNextLine(nextLine) + if (lineContent === null) break + str += lineContent + pos = max + max = str.length + nextLine++ + titleRes = state.md.helpers.parseLinkTitle(str, pos, max, titleRes) + } + let title + + if (pos < max && start !== pos && titleRes.ok) { + title = titleRes.str + pos = titleRes.pos + } else { + title = '' + pos = destEndPos + nextLine = destEndLineNo + } + + // skip trailing spaces until the rest of the line + while (pos < max) { + const ch = str.charCodeAt(pos) + if (!isSpace(ch)) { break } + pos++ + } + + if (pos < max && str.charCodeAt(pos) !== 0x0A) { + if (title) { + // garbage at the end of the line after title, + // but it could still be a valid reference if we roll back + title = '' + pos = destEndPos + nextLine = destEndLineNo + while (pos < max) { + const ch = str.charCodeAt(pos) + if (!isSpace(ch)) { break } + pos++ + } + } + } + + if (pos < max && str.charCodeAt(pos) !== 0x0A) { + // garbage at the end of the line + return false + } + + const label = normalizeReference(str.slice(1, labelEnd)) + if (!label) { + // CommonMark 0.20 disallows empty labels + return false + } + + // Reference can not terminate anything. This check is for safety only. + /* istanbul ignore if */ + if (silent) { return true } + + if (typeof state.env.references === 'undefined') { + state.env.references = {} + } + if (typeof state.env.references[label] === 'undefined') { + state.env.references[label] = { title, href } + } + + state.line = nextLine + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_block/state_block.mjs b/frontend/node_modules/markdown-it/lib/rules_block/state_block.mjs new file mode 100644 index 0000000..3c2a876 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_block/state_block.mjs @@ -0,0 +1,220 @@ +// Parser state class + +import Token from '../token.mjs' +import { isSpace } from '../common/utils.mjs' + +function StateBlock (src, md, env, tokens) { + this.src = src + + // link to parser instance + this.md = md + + this.env = env + + // + // Internal state vartiables + // + + this.tokens = tokens + + this.bMarks = [] // line begin offsets for fast jumps + this.eMarks = [] // line end offsets for fast jumps + this.tShift = [] // offsets of the first non-space characters (tabs not expanded) + this.sCount = [] // indents for each line (tabs expanded) + + // An amount of virtual spaces (tabs expanded) between beginning + // of each line (bMarks) and real beginning of that line. + // + // It exists only as a hack because blockquotes override bMarks + // losing information in the process. + // + // It's used only when expanding tabs, you can think about it as + // an initial tab length, e.g. bsCount=21 applied to string `\t123` + // means first tab should be expanded to 4-21%4 === 3 spaces. + // + this.bsCount = [] + + // block parser variables + + // required block content indent (for example, if we are + // inside a list, it would be positioned after list marker) + this.blkIndent = 0 + this.line = 0 // line index in src + this.lineMax = 0 // lines count + this.tight = false // loose/tight mode for lists + this.ddIndent = -1 // indent of the current dd block (-1 if there isn't any) + this.listIndent = -1 // indent of the current list block (-1 if there isn't any) + + // can be 'blockquote', 'list', 'root', 'paragraph' or 'reference' + // used in lists to determine if they interrupt a paragraph + this.parentType = 'root' + + this.level = 0 + + // Create caches + // Generate markers. + const s = this.src + + for (let start = 0, pos = 0, indent = 0, offset = 0, len = s.length, indent_found = false; pos < len; pos++) { + const ch = s.charCodeAt(pos) + + if (!indent_found) { + if (isSpace(ch)) { + indent++ + + if (ch === 0x09) { + offset += 4 - offset % 4 + } else { + offset++ + } + continue + } else { + indent_found = true + } + } + + if (ch === 0x0A || pos === len - 1) { + if (ch !== 0x0A) { pos++ } + this.bMarks.push(start) + this.eMarks.push(pos) + this.tShift.push(indent) + this.sCount.push(offset) + this.bsCount.push(0) + + indent_found = false + indent = 0 + offset = 0 + start = pos + 1 + } + } + + // Push fake entry to simplify cache bounds checks + this.bMarks.push(s.length) + this.eMarks.push(s.length) + this.tShift.push(0) + this.sCount.push(0) + this.bsCount.push(0) + + this.lineMax = this.bMarks.length - 1 // don't count last fake line +} + +// Push new token to "stream". +// +StateBlock.prototype.push = function (type, tag, nesting) { + const token = new Token(type, tag, nesting) + token.block = true + + if (nesting < 0) this.level-- // closing tag + token.level = this.level + if (nesting > 0) this.level++ // opening tag + + this.tokens.push(token) + return token +} + +StateBlock.prototype.isEmpty = function isEmpty (line) { + return this.bMarks[line] + this.tShift[line] >= this.eMarks[line] +} + +StateBlock.prototype.skipEmptyLines = function skipEmptyLines (from) { + for (let max = this.lineMax; from < max; from++) { + if (this.bMarks[from] + this.tShift[from] < this.eMarks[from]) { + break + } + } + return from +} + +// Skip spaces from given position. +StateBlock.prototype.skipSpaces = function skipSpaces (pos) { + for (let max = this.src.length; pos < max; pos++) { + const ch = this.src.charCodeAt(pos) + if (!isSpace(ch)) { break } + } + return pos +} + +// Skip spaces from given position in reverse. +StateBlock.prototype.skipSpacesBack = function skipSpacesBack (pos, min) { + if (pos <= min) { return pos } + + while (pos > min) { + if (!isSpace(this.src.charCodeAt(--pos))) { return pos + 1 } + } + return pos +} + +// Skip char codes from given position +StateBlock.prototype.skipChars = function skipChars (pos, code) { + for (let max = this.src.length; pos < max; pos++) { + if (this.src.charCodeAt(pos) !== code) { break } + } + return pos +} + +// Skip char codes reverse from given position - 1 +StateBlock.prototype.skipCharsBack = function skipCharsBack (pos, code, min) { + if (pos <= min) { return pos } + + while (pos > min) { + if (code !== this.src.charCodeAt(--pos)) { return pos + 1 } + } + return pos +} + +// cut lines range from source. +StateBlock.prototype.getLines = function getLines (begin, end, indent, keepLastLF) { + if (begin >= end) { + return '' + } + + const queue = new Array(end - begin) + + for (let i = 0, line = begin; line < end; line++, i++) { + let lineIndent = 0 + const lineStart = this.bMarks[line] + let first = lineStart + let last + + if (line + 1 < end || keepLastLF) { + // No need for bounds check because we have fake entry on tail. + last = this.eMarks[line] + 1 + } else { + last = this.eMarks[line] + } + + while (first < last && lineIndent < indent) { + const ch = this.src.charCodeAt(first) + + if (isSpace(ch)) { + if (ch === 0x09) { + lineIndent += 4 - (lineIndent + this.bsCount[line]) % 4 + } else { + lineIndent++ + } + } else if (first - lineStart < this.tShift[line]) { + // patched tShift masked characters to look like spaces (blockquotes, list markers) + lineIndent++ + } else { + break + } + + first++ + } + + if (lineIndent > indent) { + // partially expanding tabs in code blocks, e.g '\t\tfoobar' + // with indent=2 becomes ' \tfoobar' + queue[i] = new Array(lineIndent - indent + 1).join(' ') + this.src.slice(first, last) + } else { + queue[i] = this.src.slice(first, last) + } + } + + return queue.join('') +} + +// re-export Token class to use in block rules +StateBlock.prototype.Token = Token + +export default StateBlock diff --git a/frontend/node_modules/markdown-it/lib/rules_block/table.mjs b/frontend/node_modules/markdown-it/lib/rules_block/table.mjs new file mode 100644 index 0000000..be0ba0a --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_block/table.mjs @@ -0,0 +1,228 @@ +// GFM table, https://github.github.com/gfm/#tables-extension- + +import { isSpace } from '../common/utils.mjs' + +// Limit the amount of empty autocompleted cells in a table, +// see https://github.com/markdown-it/markdown-it/issues/1000, +// +// Both pulldown-cmark and commonmark-hs limit the number of cells this way to ~200k. +// We set it to 65k, which can expand user input by a factor of x370 +// (256x256 square is 1.8kB expanded into 650kB). +const MAX_AUTOCOMPLETED_CELLS = 0x10000 + +function getLine (state, line) { + const pos = state.bMarks[line] + state.tShift[line] + const max = state.eMarks[line] + + return state.src.slice(pos, max) +} + +function escapedSplit (str) { + const result = [] + const max = str.length + + let pos = 0 + let ch = str.charCodeAt(pos) + let isEscaped = false + let lastPos = 0 + let current = '' + + while (pos < max) { + if (ch === 0x7c/* | */) { + if (!isEscaped) { + // pipe separating cells, '|' + result.push(current + str.substring(lastPos, pos)) + current = '' + lastPos = pos + 1 + } else { + // escaped pipe, '\|' + current += str.substring(lastPos, pos - 1) + lastPos = pos + } + } + + isEscaped = (ch === 0x5c/* \ */) + pos++ + + ch = str.charCodeAt(pos) + } + + result.push(current + str.substring(lastPos)) + + return result +} + +export default function table (state, startLine, endLine, silent) { + // should have at least two lines + if (startLine + 2 > endLine) { return false } + + let nextLine = startLine + 1 + + if (state.sCount[nextLine] < state.blkIndent) { return false } + + // if it's indented more than 3 spaces, it should be a code block + if (state.sCount[nextLine] - state.blkIndent >= 4) { return false } + + // first character of the second line should be '|', '-', ':', + // and no other characters are allowed but spaces; + // basically, this is the equivalent of /^[-:|][-:|\s]*$/ regexp + + let pos = state.bMarks[nextLine] + state.tShift[nextLine] + if (pos >= state.eMarks[nextLine]) { return false } + + const firstCh = state.src.charCodeAt(pos++) + if (firstCh !== 0x7C/* | */ && firstCh !== 0x2D/* - */ && firstCh !== 0x3A/* : */) { return false } + + if (pos >= state.eMarks[nextLine]) { return false } + + const secondCh = state.src.charCodeAt(pos++) + if (secondCh !== 0x7C/* | */ && secondCh !== 0x2D/* - */ && secondCh !== 0x3A/* : */ && !isSpace(secondCh)) { + return false + } + + // if first character is '-', then second character must not be a space + // (due to parsing ambiguity with list) + if (firstCh === 0x2D/* - */ && isSpace(secondCh)) { return false } + + while (pos < state.eMarks[nextLine]) { + const ch = state.src.charCodeAt(pos) + + if (ch !== 0x7C/* | */ && ch !== 0x2D/* - */ && ch !== 0x3A/* : */ && !isSpace(ch)) { return false } + + pos++ + } + + let lineText = getLine(state, startLine + 1) + let columns = lineText.split('|') + const aligns = [] + for (let i = 0; i < columns.length; i++) { + const t = columns[i].trim() + if (!t) { + // allow empty columns before and after table, but not in between columns; + // e.g. allow ` |---| `, disallow ` ---||--- ` + if (i === 0 || i === columns.length - 1) { + continue + } else { + return false + } + } + + if (!/^:?-+:?$/.test(t)) { return false } + if (t.charCodeAt(t.length - 1) === 0x3A/* : */) { + aligns.push(t.charCodeAt(0) === 0x3A/* : */ ? 'center' : 'right') + } else if (t.charCodeAt(0) === 0x3A/* : */) { + aligns.push('left') + } else { + aligns.push('') + } + } + + lineText = getLine(state, startLine).trim() + if (lineText.indexOf('|') === -1) { return false } + if (state.sCount[startLine] - state.blkIndent >= 4) { return false } + columns = escapedSplit(lineText) + if (columns.length && columns[0] === '') columns.shift() + if (columns.length && columns[columns.length - 1] === '') columns.pop() + + // header row will define an amount of columns in the entire table, + // and align row should be exactly the same (the rest of the rows can differ) + const columnCount = columns.length + if (columnCount === 0 || columnCount !== aligns.length) { return false } + + if (silent) { return true } + + const oldParentType = state.parentType + state.parentType = 'table' + + // use 'blockquote' lists for termination because it's + // the most similar to tables + const terminatorRules = state.md.block.ruler.getRules('blockquote') + + const token_to = state.push('table_open', 'table', 1) + const tableLines = [startLine, 0] + token_to.map = tableLines + + const token_tho = state.push('thead_open', 'thead', 1) + token_tho.map = [startLine, startLine + 1] + + const token_htro = state.push('tr_open', 'tr', 1) + token_htro.map = [startLine, startLine + 1] + + for (let i = 0; i < columns.length; i++) { + const token_ho = state.push('th_open', 'th', 1) + if (aligns[i]) { + token_ho.attrs = [['style', 'text-align:' + aligns[i]]] + } + + const token_il = state.push('inline', '', 0) + token_il.content = columns[i].trim() + token_il.children = [] + + state.push('th_close', 'th', -1) + } + + state.push('tr_close', 'tr', -1) + state.push('thead_close', 'thead', -1) + + let tbodyLines + let autocompletedCells = 0 + + for (nextLine = startLine + 2; nextLine < endLine; nextLine++) { + if (state.sCount[nextLine] < state.blkIndent) { break } + + let terminate = false + for (let i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true + break + } + } + + if (terminate) { break } + lineText = getLine(state, nextLine).trim() + if (!lineText) { break } + if (state.sCount[nextLine] - state.blkIndent >= 4) { break } + columns = escapedSplit(lineText) + if (columns.length && columns[0] === '') columns.shift() + if (columns.length && columns[columns.length - 1] === '') columns.pop() + + // note: autocomplete count can be negative if user specifies more columns than header, + // but that does not affect intended use (which is limiting expansion) + autocompletedCells += columnCount - columns.length + if (autocompletedCells > MAX_AUTOCOMPLETED_CELLS) { break } + + if (nextLine === startLine + 2) { + const token_tbo = state.push('tbody_open', 'tbody', 1) + token_tbo.map = tbodyLines = [startLine + 2, 0] + } + + const token_tro = state.push('tr_open', 'tr', 1) + token_tro.map = [nextLine, nextLine + 1] + + for (let i = 0; i < columnCount; i++) { + const token_tdo = state.push('td_open', 'td', 1) + if (aligns[i]) { + token_tdo.attrs = [['style', 'text-align:' + aligns[i]]] + } + + const token_il = state.push('inline', '', 0) + token_il.content = columns[i] ? columns[i].trim() : '' + token_il.children = [] + + state.push('td_close', 'td', -1) + } + state.push('tr_close', 'tr', -1) + } + + if (tbodyLines) { + state.push('tbody_close', 'tbody', -1) + tbodyLines[1] = nextLine + } + + state.push('table_close', 'table', -1) + tableLines[1] = nextLine + + state.parentType = oldParentType + state.line = nextLine + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_core/block.mjs b/frontend/node_modules/markdown-it/lib/rules_core/block.mjs new file mode 100644 index 0000000..526cb48 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_core/block.mjs @@ -0,0 +1,13 @@ +export default function block (state) { + let token + + if (state.inlineMode) { + token = new state.Token('inline', '', 0) + token.content = state.src + token.map = [0, 1] + token.children = [] + state.tokens.push(token) + } else { + state.md.block.parse(state.src, state.md, state.env, state.tokens) + } +} diff --git a/frontend/node_modules/markdown-it/lib/rules_core/inline.mjs b/frontend/node_modules/markdown-it/lib/rules_core/inline.mjs new file mode 100644 index 0000000..efd6c07 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_core/inline.mjs @@ -0,0 +1,11 @@ +export default function inline (state) { + const tokens = state.tokens + + // Parse inlines + for (let i = 0, l = tokens.length; i < l; i++) { + const tok = tokens[i] + if (tok.type === 'inline') { + state.md.inline.parse(tok.content, state.md, state.env, tok.children) + } + } +} diff --git a/frontend/node_modules/markdown-it/lib/rules_core/linkify.mjs b/frontend/node_modules/markdown-it/lib/rules_core/linkify.mjs new file mode 100644 index 0000000..a225280 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_core/linkify.mjs @@ -0,0 +1,134 @@ +// Replace link-like texts with link nodes. +// +// Currently restricted by `md.validateLink()` to http/https/ftp +// + +import { arrayReplaceAt } from '../common/utils.mjs' + +function isLinkOpen (str) { + return /^\s]/i.test(str) +} +function isLinkClose (str) { + return /^<\/a\s*>/i.test(str) +} + +export default function linkify (state) { + const blockTokens = state.tokens + + if (!state.md.options.linkify) { return } + + for (let j = 0, l = blockTokens.length; j < l; j++) { + if (blockTokens[j].type !== 'inline' || + !state.md.linkify.pretest(blockTokens[j].content)) { + continue + } + + let tokens = blockTokens[j].children + + let htmlLinkLevel = 0 + + // We scan from the end, to keep position when new tags added. + // Use reversed logic in links start/end match + for (let i = tokens.length - 1; i >= 0; i--) { + const currentToken = tokens[i] + + // Skip content of markdown links + if (currentToken.type === 'link_close') { + i-- + while (tokens[i].level !== currentToken.level && tokens[i].type !== 'link_open') { + i-- + } + continue + } + + // Skip content of html tag links + if (currentToken.type === 'html_inline') { + if (isLinkOpen(currentToken.content) && htmlLinkLevel > 0) { + htmlLinkLevel-- + } + if (isLinkClose(currentToken.content)) { + htmlLinkLevel++ + } + } + if (htmlLinkLevel > 0) { continue } + + if (currentToken.type === 'text' && state.md.linkify.test(currentToken.content)) { + const text = currentToken.content + let links = state.md.linkify.match(text) + + // Now split string to nodes + const nodes = [] + let level = currentToken.level + let lastPos = 0 + + // forbid escape sequence at the start of the string, + // this avoids http\://example.com/ from being linkified as + // http:
    //example.com/ + if (links.length > 0 && + links[0].index === 0 && + i > 0 && + tokens[i - 1].type === 'text_special') { + links = links.slice(1) + } + + for (let ln = 0; ln < links.length; ln++) { + const url = links[ln].url + const fullUrl = state.md.normalizeLink(url) + if (!state.md.validateLink(fullUrl)) { continue } + + let urlText = links[ln].text + + // Linkifier might send raw hostnames like "example.com", where url + // starts with domain name. So we prepend http:// in those cases, + // and remove it afterwards. + // + if (!links[ln].schema) { + urlText = state.md.normalizeLinkText('http://' + urlText).replace(/^http:\/\//, '') + } else if (links[ln].schema === 'mailto:' && !/^mailto:/i.test(urlText)) { + urlText = state.md.normalizeLinkText('mailto:' + urlText).replace(/^mailto:/, '') + } else { + urlText = state.md.normalizeLinkText(urlText) + } + + const pos = links[ln].index + + if (pos > lastPos) { + const token = new state.Token('text', '', 0) + token.content = text.slice(lastPos, pos) + token.level = level + nodes.push(token) + } + + const token_o = new state.Token('link_open', 'a', 1) + token_o.attrs = [['href', fullUrl]] + token_o.level = level++ + token_o.markup = 'linkify' + token_o.info = 'auto' + nodes.push(token_o) + + const token_t = new state.Token('text', '', 0) + token_t.content = urlText + token_t.level = level + nodes.push(token_t) + + const token_c = new state.Token('link_close', 'a', -1) + token_c.level = --level + token_c.markup = 'linkify' + token_c.info = 'auto' + nodes.push(token_c) + + lastPos = links[ln].lastIndex + } + if (lastPos < text.length) { + const token = new state.Token('text', '', 0) + token.content = text.slice(lastPos) + token.level = level + nodes.push(token) + } + + // replace current node + blockTokens[j].children = tokens = arrayReplaceAt(tokens, i, nodes) + } + } + } +} diff --git a/frontend/node_modules/markdown-it/lib/rules_core/normalize.mjs b/frontend/node_modules/markdown-it/lib/rules_core/normalize.mjs new file mode 100644 index 0000000..dfb67ef --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_core/normalize.mjs @@ -0,0 +1,17 @@ +// Normalize input string + +// https://spec.commonmark.org/0.29/#line-ending +const NEWLINES_RE = /\r\n?|\n/g +const NULL_RE = /\0/g + +export default function normalize (state) { + let str + + // Normalize newlines + str = state.src.replace(NEWLINES_RE, '\n') + + // Replace NULL characters + str = str.replace(NULL_RE, '\uFFFD') + + state.src = str +} diff --git a/frontend/node_modules/markdown-it/lib/rules_core/replacements.mjs b/frontend/node_modules/markdown-it/lib/rules_core/replacements.mjs new file mode 100644 index 0000000..b18ecd9 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_core/replacements.mjs @@ -0,0 +1,101 @@ +// Simple typographic replacements +// +// (c) (C) → © +// (tm) (TM) → ™ +// (r) (R) → ® +// +- → ± +// ... → … (also ?.... → ?.., !.... → !..) +// ???????? → ???, !!!!! → !!!, `,,` → `,` +// -- → –, --- → — +// + +// TODO: +// - fractionals 1/2, 1/4, 3/4 -> ½, ¼, ¾ +// - multiplications 2 x 4 -> 2 × 4 + +const RARE_RE = /\+-|\.\.|\?\?\?\?|!!!!|,,|--/ + +// Workaround for phantomjs - need regex without /g flag, +// or root check will fail every second time +const SCOPED_ABBR_TEST_RE = /\((c|tm|r)\)/i + +const SCOPED_ABBR_RE = /\((c|tm|r)\)/ig +const SCOPED_ABBR = { + c: '©', + r: '®', + tm: '™' +} + +function replaceFn (match, name) { + return SCOPED_ABBR[name.toLowerCase()] +} + +function replace_scoped (inlineTokens) { + let inside_autolink = 0 + + for (let i = inlineTokens.length - 1; i >= 0; i--) { + const token = inlineTokens[i] + + if (token.type === 'text' && !inside_autolink) { + token.content = token.content.replace(SCOPED_ABBR_RE, replaceFn) + } + + if (token.type === 'link_open' && token.info === 'auto') { + inside_autolink-- + } + + if (token.type === 'link_close' && token.info === 'auto') { + inside_autolink++ + } + } +} + +function replace_rare (inlineTokens) { + let inside_autolink = 0 + + for (let i = inlineTokens.length - 1; i >= 0; i--) { + const token = inlineTokens[i] + + if (token.type === 'text' && !inside_autolink) { + if (RARE_RE.test(token.content)) { + token.content = token.content + .replace(/\+-/g, '±') + // .., ..., ....... -> … + // but ?..... & !..... -> ?.. & !.. + .replace(/\.{2,}/g, '…').replace(/([?!])…/g, '$1..') + .replace(/([?!]){4,}/g, '$1$1$1').replace(/,{2,}/g, ',') + // em-dash + .replace(/(^|[^-])---(?=[^-]|$)/mg, '$1\u2014') + // en-dash + .replace(/(^|\s)--(?=\s|$)/mg, '$1\u2013') + .replace(/(^|[^-\s])--(?=[^-\s]|$)/mg, '$1\u2013') + } + } + + if (token.type === 'link_open' && token.info === 'auto') { + inside_autolink-- + } + + if (token.type === 'link_close' && token.info === 'auto') { + inside_autolink++ + } + } +} + +export default function replace (state) { + let blkIdx + + if (!state.md.options.typographer) { return } + + for (blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) { + if (state.tokens[blkIdx].type !== 'inline') { continue } + + if (SCOPED_ABBR_TEST_RE.test(state.tokens[blkIdx].content)) { + replace_scoped(state.tokens[blkIdx].children) + } + + if (RARE_RE.test(state.tokens[blkIdx].content)) { + replace_rare(state.tokens[blkIdx].children) + } + } +} diff --git a/frontend/node_modules/markdown-it/lib/rules_core/smartquotes.mjs b/frontend/node_modules/markdown-it/lib/rules_core/smartquotes.mjs new file mode 100644 index 0000000..3b990ed --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_core/smartquotes.mjs @@ -0,0 +1,193 @@ +// Convert straight quotation marks to typographic ones +// + +import { isWhiteSpace, isPunctChar, isMdAsciiPunct } from '../common/utils.mjs' + +const QUOTE_TEST_RE = /['"]/ +const QUOTE_RE = /['"]/g +const APOSTROPHE = '\u2019' /* ’ */ + +function replaceAt (str, index, ch) { + return str.slice(0, index) + ch + str.slice(index + 1) +} + +function process_inlines (tokens, state) { + let j + + const stack = [] + + for (let i = 0; i < tokens.length; i++) { + const token = tokens[i] + + const thisLevel = tokens[i].level + + for (j = stack.length - 1; j >= 0; j--) { + if (stack[j].level <= thisLevel) { break } + } + stack.length = j + 1 + + if (token.type !== 'text') { continue } + + let text = token.content + let pos = 0 + let max = text.length + + /* eslint no-labels:0,block-scoped-var:0 */ + OUTER: + while (pos < max) { + QUOTE_RE.lastIndex = pos + const t = QUOTE_RE.exec(text) + if (!t) { break } + + let canOpen = true + let canClose = true + pos = t.index + 1 + const isSingle = (t[0] === "'") + + // Find previous character, + // default to space if it's the beginning of the line + // + let lastChar = 0x20 + + if (t.index - 1 >= 0) { + lastChar = text.charCodeAt(t.index - 1) + } else { + for (j = i - 1; j >= 0; j--) { + if (tokens[j].type === 'softbreak' || tokens[j].type === 'hardbreak') break // lastChar defaults to 0x20 + if (!tokens[j].content) continue // should skip all tokens except 'text', 'html_inline' or 'code_inline' + + lastChar = tokens[j].content.charCodeAt(tokens[j].content.length - 1) + break + } + } + + // Find next character, + // default to space if it's the end of the line + // + let nextChar = 0x20 + + if (pos < max) { + nextChar = text.charCodeAt(pos) + } else { + for (j = i + 1; j < tokens.length; j++) { + if (tokens[j].type === 'softbreak' || tokens[j].type === 'hardbreak') break // nextChar defaults to 0x20 + if (!tokens[j].content) continue // should skip all tokens except 'text', 'html_inline' or 'code_inline' + + nextChar = tokens[j].content.charCodeAt(0) + break + } + } + + const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar)) + const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar)) + + const isLastWhiteSpace = isWhiteSpace(lastChar) + const isNextWhiteSpace = isWhiteSpace(nextChar) + + if (isNextWhiteSpace) { + canOpen = false + } else if (isNextPunctChar) { + if (!(isLastWhiteSpace || isLastPunctChar)) { + canOpen = false + } + } + + if (isLastWhiteSpace) { + canClose = false + } else if (isLastPunctChar) { + if (!(isNextWhiteSpace || isNextPunctChar)) { + canClose = false + } + } + + if (nextChar === 0x22 /* " */ && t[0] === '"') { + if (lastChar >= 0x30 /* 0 */ && lastChar <= 0x39 /* 9 */) { + // special case: 1"" - count first quote as an inch + canClose = canOpen = false + } + } + + if (canOpen && canClose) { + // Replace quotes in the middle of punctuation sequence, but not + // in the middle of the words, i.e.: + // + // 1. foo " bar " baz - not replaced + // 2. foo-"-bar-"-baz - replaced + // 3. foo"bar"baz - not replaced + // + canOpen = isLastPunctChar + canClose = isNextPunctChar + } + + if (!canOpen && !canClose) { + // middle of word + if (isSingle) { + token.content = replaceAt(token.content, t.index, APOSTROPHE) + } + continue + } + + if (canClose) { + // this could be a closing quote, rewind the stack to get a match + for (j = stack.length - 1; j >= 0; j--) { + let item = stack[j] + if (stack[j].level < thisLevel) { break } + if (item.single === isSingle && stack[j].level === thisLevel) { + item = stack[j] + + let openQuote + let closeQuote + if (isSingle) { + openQuote = state.md.options.quotes[2] + closeQuote = state.md.options.quotes[3] + } else { + openQuote = state.md.options.quotes[0] + closeQuote = state.md.options.quotes[1] + } + + // replace token.content *before* tokens[item.token].content, + // because, if they are pointing at the same token, replaceAt + // could mess up indices when quote length != 1 + token.content = replaceAt(token.content, t.index, closeQuote) + tokens[item.token].content = replaceAt( + tokens[item.token].content, item.pos, openQuote) + + pos += closeQuote.length - 1 + if (item.token === i) { pos += openQuote.length - 1 } + + text = token.content + max = text.length + + stack.length = j + continue OUTER + } + } + } + + if (canOpen) { + stack.push({ + token: i, + pos: t.index, + single: isSingle, + level: thisLevel + }) + } else if (canClose && isSingle) { + token.content = replaceAt(token.content, t.index, APOSTROPHE) + } + } + } +} + +export default function smartquotes (state) { + /* eslint max-depth:0 */ + if (!state.md.options.typographer) { return } + + for (let blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) { + if (state.tokens[blkIdx].type !== 'inline' || + !QUOTE_TEST_RE.test(state.tokens[blkIdx].content)) { + continue + } + + process_inlines(state.tokens[blkIdx].children, state) + } +} diff --git a/frontend/node_modules/markdown-it/lib/rules_core/state_core.mjs b/frontend/node_modules/markdown-it/lib/rules_core/state_core.mjs new file mode 100644 index 0000000..a96c8fb --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_core/state_core.mjs @@ -0,0 +1,17 @@ +// Core state object +// + +import Token from '../token.mjs' + +function StateCore (src, md, env) { + this.src = src + this.env = env + this.tokens = [] + this.inlineMode = false + this.md = md // link to parser instance +} + +// re-export Token class to use in core rules +StateCore.prototype.Token = Token + +export default StateCore diff --git a/frontend/node_modules/markdown-it/lib/rules_core/text_join.mjs b/frontend/node_modules/markdown-it/lib/rules_core/text_join.mjs new file mode 100644 index 0000000..ee8f872 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_core/text_join.mjs @@ -0,0 +1,43 @@ +// Join raw text tokens with the rest of the text +// +// This is set as a separate rule to provide an opportunity for plugins +// to run text replacements after text join, but before escape join. +// +// For example, `\:)` shouldn't be replaced with an emoji. +// + +export default function text_join (state) { + let curr, last + const blockTokens = state.tokens + const l = blockTokens.length + + for (let j = 0; j < l; j++) { + if (blockTokens[j].type !== 'inline') continue + + const tokens = blockTokens[j].children + const max = tokens.length + + for (curr = 0; curr < max; curr++) { + if (tokens[curr].type === 'text_special') { + tokens[curr].type = 'text' + } + } + + for (curr = last = 0; curr < max; curr++) { + if (tokens[curr].type === 'text' && + curr + 1 < max && + tokens[curr + 1].type === 'text') { + // collapse two adjacent text nodes + tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content + } else { + if (curr !== last) { tokens[last] = tokens[curr] } + + last++ + } + } + + if (curr !== last) { + tokens.length = last + } + } +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/autolink.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/autolink.mjs new file mode 100644 index 0000000..e71e66f --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/autolink.mjs @@ -0,0 +1,72 @@ +// Process autolinks '' + +/* eslint max-len:0 */ +const EMAIL_RE = /^([a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*)$/ +/* eslint-disable-next-line no-control-regex */ +const AUTOLINK_RE = /^([a-zA-Z][a-zA-Z0-9+.-]{1,31}):([^<>\x00-\x20]*)$/ + +export default function autolink (state, silent) { + let pos = state.pos + + if (state.src.charCodeAt(pos) !== 0x3C/* < */) { return false } + + const start = state.pos + const max = state.posMax + + for (;;) { + if (++pos >= max) return false + + const ch = state.src.charCodeAt(pos) + + if (ch === 0x3C /* < */) return false + if (ch === 0x3E /* > */) break + } + + const url = state.src.slice(start + 1, pos) + + if (AUTOLINK_RE.test(url)) { + const fullUrl = state.md.normalizeLink(url) + if (!state.md.validateLink(fullUrl)) { return false } + + if (!silent) { + const token_o = state.push('link_open', 'a', 1) + token_o.attrs = [['href', fullUrl]] + token_o.markup = 'autolink' + token_o.info = 'auto' + + const token_t = state.push('text', '', 0) + token_t.content = state.md.normalizeLinkText(url) + + const token_c = state.push('link_close', 'a', -1) + token_c.markup = 'autolink' + token_c.info = 'auto' + } + + state.pos += url.length + 2 + return true + } + + if (EMAIL_RE.test(url)) { + const fullUrl = state.md.normalizeLink('mailto:' + url) + if (!state.md.validateLink(fullUrl)) { return false } + + if (!silent) { + const token_o = state.push('link_open', 'a', 1) + token_o.attrs = [['href', fullUrl]] + token_o.markup = 'autolink' + token_o.info = 'auto' + + const token_t = state.push('text', '', 0) + token_t.content = state.md.normalizeLinkText(url) + + const token_c = state.push('link_close', 'a', -1) + token_c.markup = 'autolink' + token_c.info = 'auto' + } + + state.pos += url.length + 2 + return true + } + + return false +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/backticks.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/backticks.mjs new file mode 100644 index 0000000..5b926d0 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/backticks.mjs @@ -0,0 +1,60 @@ +// Parse backticks + +export default function backtick (state, silent) { + let pos = state.pos + const ch = state.src.charCodeAt(pos) + + if (ch !== 0x60/* ` */) { return false } + + const start = pos + pos++ + const max = state.posMax + + // scan marker length + while (pos < max && state.src.charCodeAt(pos) === 0x60/* ` */) { pos++ } + + const marker = state.src.slice(start, pos) + const openerLength = marker.length + + if (state.backticksScanned && (state.backticks[openerLength] || 0) <= start) { + if (!silent) state.pending += marker + state.pos += openerLength + return true + } + + let matchEnd = pos + let matchStart + + // Nothing found in the cache, scan until the end of the line (or until marker is found) + while ((matchStart = state.src.indexOf('`', matchEnd)) !== -1) { + matchEnd = matchStart + 1 + + // scan marker length + while (matchEnd < max && state.src.charCodeAt(matchEnd) === 0x60/* ` */) { matchEnd++ } + + const closerLength = matchEnd - matchStart + + if (closerLength === openerLength) { + // Found matching closer length. + if (!silent) { + const token = state.push('code_inline', 'code', 0) + token.markup = marker + token.content = state.src.slice(pos, matchStart) + .replace(/\n/g, ' ') + .replace(/^ (.+) $/, '$1') + } + state.pos = matchEnd + return true + } + + // Some different length found, put it in cache as upper limit of where closer can be found + state.backticks[closerLength] = matchStart + } + + // Scanned through the end, didn't find anything + state.backticksScanned = true + + if (!silent) state.pending += marker + state.pos += openerLength + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/balance_pairs.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/balance_pairs.mjs new file mode 100644 index 0000000..8638d21 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/balance_pairs.mjs @@ -0,0 +1,124 @@ +// For each opening emphasis-like marker find a matching closing one +// + +function processDelimiters (delimiters) { + const openersBottom = {} + const max = delimiters.length + + if (!max) return + + // headerIdx is the first delimiter of the current (where closer is) delimiter run + let headerIdx = 0 + let lastTokenIdx = -2 // needs any value lower than -1 + const jumps = [] + + for (let closerIdx = 0; closerIdx < max; closerIdx++) { + const closer = delimiters[closerIdx] + + jumps.push(0) + + // markers belong to same delimiter run if: + // - they have adjacent tokens + // - AND markers are the same + // + if (delimiters[headerIdx].marker !== closer.marker || lastTokenIdx !== closer.token - 1) { + headerIdx = closerIdx + } + + lastTokenIdx = closer.token + + // Length is only used for emphasis-specific "rule of 3", + // if it's not defined (in strikethrough or 3rd party plugins), + // we can default it to 0 to disable those checks. + // + closer.length = closer.length || 0 + + if (!closer.close) continue + + // Previously calculated lower bounds (previous fails) + // for each marker, each delimiter length modulo 3, + // and for whether this closer can be an opener; + // https://github.com/commonmark/cmark/commit/34250e12ccebdc6372b8b49c44fab57c72443460 + /* eslint-disable-next-line no-prototype-builtins */ + if (!openersBottom.hasOwnProperty(closer.marker)) { + openersBottom[closer.marker] = [-1, -1, -1, -1, -1, -1] + } + + const minOpenerIdx = openersBottom[closer.marker][(closer.open ? 3 : 0) + (closer.length % 3)] + + let openerIdx = headerIdx - jumps[headerIdx] - 1 + + let newMinOpenerIdx = openerIdx + + for (; openerIdx > minOpenerIdx; openerIdx -= jumps[openerIdx] + 1) { + const opener = delimiters[openerIdx] + + if (opener.marker !== closer.marker) continue + + if (opener.open && opener.end < 0) { + let isOddMatch = false + + // from spec: + // + // If one of the delimiters can both open and close emphasis, then the + // sum of the lengths of the delimiter runs containing the opening and + // closing delimiters must not be a multiple of 3 unless both lengths + // are multiples of 3. + // + if (opener.close || closer.open) { + if ((opener.length + closer.length) % 3 === 0) { + if (opener.length % 3 !== 0 || closer.length % 3 !== 0) { + isOddMatch = true + } + } + } + + if (!isOddMatch) { + // If previous delimiter cannot be an opener, we can safely skip + // the entire sequence in future checks. This is required to make + // sure algorithm has linear complexity (see *_*_*_*_*_... case). + // + const lastJump = openerIdx > 0 && !delimiters[openerIdx - 1].open + ? jumps[openerIdx - 1] + 1 + : 0 + + jumps[closerIdx] = closerIdx - openerIdx + lastJump + jumps[openerIdx] = lastJump + + closer.open = false + opener.end = closerIdx + opener.close = false + newMinOpenerIdx = -1 + // treat next token as start of run, + // it optimizes skips in **<...>**a**<...>** pathological case + lastTokenIdx = -2 + break + } + } + } + + if (newMinOpenerIdx !== -1) { + // If match for this delimiter run failed, we want to set lower bound for + // future lookups. This is required to make sure algorithm has linear + // complexity. + // + // See details here: + // https://github.com/commonmark/cmark/issues/178#issuecomment-270417442 + // + openersBottom[closer.marker][(closer.open ? 3 : 0) + ((closer.length || 0) % 3)] = newMinOpenerIdx + } + } +} + +export default function link_pairs (state) { + const tokens_meta = state.tokens_meta + const max = state.tokens_meta.length + + processDelimiters(state.delimiters) + + for (let curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + processDelimiters(tokens_meta[curr].delimiters) + } + } +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/emphasis.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/emphasis.mjs new file mode 100644 index 0000000..4e3b273 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/emphasis.mjs @@ -0,0 +1,123 @@ +// Process *this* and _that_ +// + +// Insert each marker as a separate text token, and add it to delimiter list +// +function emphasis_tokenize (state, silent) { + const start = state.pos + const marker = state.src.charCodeAt(start) + + if (silent) { return false } + + if (marker !== 0x5F /* _ */ && marker !== 0x2A /* * */) { return false } + + const scanned = state.scanDelims(state.pos, marker === 0x2A) + + for (let i = 0; i < scanned.length; i++) { + const token = state.push('text', '', 0) + token.content = String.fromCharCode(marker) + + state.delimiters.push({ + // Char code of the starting marker (number). + // + marker, + + // Total length of these series of delimiters. + // + length: scanned.length, + + // A position of the token this delimiter corresponds to. + // + token: state.tokens.length - 1, + + // If this delimiter is matched as a valid opener, `end` will be + // equal to its position, otherwise it's `-1`. + // + end: -1, + + // Boolean flags that determine if this delimiter could open or close + // an emphasis. + // + open: scanned.can_open, + close: scanned.can_close + }) + } + + state.pos += scanned.length + + return true +} + +function postProcess (state, delimiters) { + const max = delimiters.length + + for (let i = max - 1; i >= 0; i--) { + const startDelim = delimiters[i] + + if (startDelim.marker !== 0x5F/* _ */ && startDelim.marker !== 0x2A/* * */) { + continue + } + + // Process only opening markers + if (startDelim.end === -1) { + continue + } + + const endDelim = delimiters[startDelim.end] + + // If the previous delimiter has the same marker and is adjacent to this one, + // merge those into one strong delimiter. + // + // `whatever` -> `whatever` + // + const isStrong = i > 0 && + delimiters[i - 1].end === startDelim.end + 1 && + // check that first two markers match and adjacent + delimiters[i - 1].marker === startDelim.marker && + delimiters[i - 1].token === startDelim.token - 1 && + // check that last two markers are adjacent (we can safely assume they match) + delimiters[startDelim.end + 1].token === endDelim.token + 1 + + const ch = String.fromCharCode(startDelim.marker) + + const token_o = state.tokens[startDelim.token] + token_o.type = isStrong ? 'strong_open' : 'em_open' + token_o.tag = isStrong ? 'strong' : 'em' + token_o.nesting = 1 + token_o.markup = isStrong ? ch + ch : ch + token_o.content = '' + + const token_c = state.tokens[endDelim.token] + token_c.type = isStrong ? 'strong_close' : 'em_close' + token_c.tag = isStrong ? 'strong' : 'em' + token_c.nesting = -1 + token_c.markup = isStrong ? ch + ch : ch + token_c.content = '' + + if (isStrong) { + state.tokens[delimiters[i - 1].token].content = '' + state.tokens[delimiters[startDelim.end + 1].token].content = '' + i-- + } + } +} + +// Walk through delimiter list and replace text tokens with tags +// +function emphasis_post_process (state) { + const tokens_meta = state.tokens_meta + const max = state.tokens_meta.length + + postProcess(state, state.delimiters) + + for (let curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + postProcess(state, tokens_meta[curr].delimiters) + } + } +} + +export default { + tokenize: emphasis_tokenize, + postProcess: emphasis_post_process +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/entity.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/entity.mjs new file mode 100644 index 0000000..e65191d --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/entity.mjs @@ -0,0 +1,51 @@ +// Process html entity - {, ¯, ", ... + +import { decodeHTML } from 'entities' +import { isValidEntityCode, fromCodePoint } from '../common/utils.mjs' + +const DIGITAL_RE = /^&#((?:x[a-f0-9]{1,6}|[0-9]{1,7}));/i +const NAMED_RE = /^&([a-z][a-z0-9]{1,31});/i + +export default function entity (state, silent) { + const pos = state.pos + const max = state.posMax + + if (state.src.charCodeAt(pos) !== 0x26/* & */) return false + + if (pos + 1 >= max) return false + + const ch = state.src.charCodeAt(pos + 1) + + if (ch === 0x23 /* # */) { + const match = state.src.slice(pos).match(DIGITAL_RE) + if (match) { + if (!silent) { + const code = match[1][0].toLowerCase() === 'x' ? parseInt(match[1].slice(1), 16) : parseInt(match[1], 10) + + const token = state.push('text_special', '', 0) + token.content = isValidEntityCode(code) ? fromCodePoint(code) : fromCodePoint(0xFFFD) + token.markup = match[0] + token.info = 'entity' + } + state.pos += match[0].length + return true + } + } else { + const match = state.src.slice(pos).match(NAMED_RE) + if (match) { + const decoded = decodeHTML(match[0]) + if (decoded !== match[0]) { + if (!silent) { + const token = state.push('text_special', '', 0) + token.content = decoded + token.markup = match[0] + token.info = 'entity' + } + state.pos += match[0].length + return true + } + } + } + + return false +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/escape.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/escape.mjs new file mode 100644 index 0000000..aa3728e --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/escape.mjs @@ -0,0 +1,69 @@ +// Process escaped chars and hardbreaks + +import { isSpace } from '../common/utils.mjs' + +const ESCAPED = [] + +for (let i = 0; i < 256; i++) { ESCAPED.push(0) } + +'\\!"#$%&\'()*+,./:;<=>?@[]^_`{|}~-' + .split('').forEach(function (ch) { ESCAPED[ch.charCodeAt(0)] = 1 }) + +export default function escape (state, silent) { + let pos = state.pos + const max = state.posMax + + if (state.src.charCodeAt(pos) !== 0x5C/* \ */) return false + pos++ + + // '\' at the end of the inline block + if (pos >= max) return false + + let ch1 = state.src.charCodeAt(pos) + + if (ch1 === 0x0A) { + if (!silent) { + state.push('hardbreak', 'br', 0) + } + + pos++ + // skip leading whitespaces from next line + while (pos < max) { + ch1 = state.src.charCodeAt(pos) + if (!isSpace(ch1)) break + pos++ + } + + state.pos = pos + return true + } + + let escapedStr = state.src[pos] + + if (ch1 >= 0xD800 && ch1 <= 0xDBFF && pos + 1 < max) { + const ch2 = state.src.charCodeAt(pos + 1) + + if (ch2 >= 0xDC00 && ch2 <= 0xDFFF) { + escapedStr += state.src[pos + 1] + pos++ + } + } + + const origStr = '\\' + escapedStr + + if (!silent) { + const token = state.push('text_special', '', 0) + + if (ch1 < 256 && ESCAPED[ch1] !== 0) { + token.content = escapedStr + } else { + token.content = origStr + } + + token.markup = origStr + token.info = 'escape' + } + + state.pos = pos + 1 + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/fragments_join.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/fragments_join.mjs new file mode 100644 index 0000000..e89ef9e --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/fragments_join.mjs @@ -0,0 +1,38 @@ +// Clean up tokens after emphasis and strikethrough postprocessing: +// merge adjacent text nodes into one and re-calculate all token levels +// +// This is necessary because initially emphasis delimiter markers (*, _, ~) +// are treated as their own separate text tokens. Then emphasis rule either +// leaves them as text (needed to merge with adjacent text) or turns them +// into opening/closing tags (which messes up levels inside). +// + +export default function fragments_join (state) { + let curr, last + let level = 0 + const tokens = state.tokens + const max = state.tokens.length + + for (curr = last = 0; curr < max; curr++) { + // re-calculate levels after emphasis/strikethrough turns some text nodes + // into opening/closing tags + if (tokens[curr].nesting < 0) level-- // closing tag + tokens[curr].level = level + if (tokens[curr].nesting > 0) level++ // opening tag + + if (tokens[curr].type === 'text' && + curr + 1 < max && + tokens[curr + 1].type === 'text') { + // collapse two adjacent text nodes + tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content + } else { + if (curr !== last) { tokens[last] = tokens[curr] } + + last++ + } + } + + if (curr !== last) { + tokens.length = last + } +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/html_inline.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/html_inline.mjs new file mode 100644 index 0000000..256efad --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/html_inline.mjs @@ -0,0 +1,50 @@ +// Process html tags + +import { HTML_TAG_RE } from '../common/html_re.mjs' + +function isLinkOpen (str) { + return /^\s]/i.test(str) +} +function isLinkClose (str) { + return /^<\/a\s*>/i.test(str) +} + +function isLetter (ch) { + /* eslint no-bitwise:0 */ + const lc = ch | 0x20 // to lower case + return (lc >= 0x61/* a */) && (lc <= 0x7a/* z */) +} + +export default function html_inline (state, silent) { + if (!state.md.options.html) { return false } + + // Check start + const max = state.posMax + const pos = state.pos + if (state.src.charCodeAt(pos) !== 0x3C/* < */ || + pos + 2 >= max) { + return false + } + + // Quick fail on second char + const ch = state.src.charCodeAt(pos + 1) + if (ch !== 0x21/* ! */ && + ch !== 0x3F/* ? */ && + ch !== 0x2F/* / */ && + !isLetter(ch)) { + return false + } + + const match = state.src.slice(pos).match(HTML_TAG_RE) + if (!match) { return false } + + if (!silent) { + const token = state.push('html_inline', '', 0) + token.content = match[0] + + if (isLinkOpen(token.content)) state.linkLevel++ + if (isLinkClose(token.content)) state.linkLevel-- + } + state.pos += match[0].length + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/image.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/image.mjs new file mode 100644 index 0000000..32cbb31 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/image.mjs @@ -0,0 +1,138 @@ +// Process ![image]( "title") + +import { normalizeReference, isSpace } from '../common/utils.mjs' + +export default function image (state, silent) { + let code, content, label, pos, ref, res, title, start + let href = '' + const oldPos = state.pos + const max = state.posMax + + if (state.src.charCodeAt(state.pos) !== 0x21/* ! */) { return false } + if (state.src.charCodeAt(state.pos + 1) !== 0x5B/* [ */) { return false } + + const labelStart = state.pos + 2 + const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos + 1, false) + + // parser failed to find ']', so it's not a valid link + if (labelEnd < 0) { return false } + + pos = labelEnd + 1 + if (pos < max && state.src.charCodeAt(pos) === 0x28/* ( */) { + // + // Inline link + // + + // [link]( "title" ) + // ^^ skipping these spaces + pos++ + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos) + if (!isSpace(code) && code !== 0x0A) { break } + } + if (pos >= max) { return false } + + // [link]( "title" ) + // ^^^^^^ parsing link destination + start = pos + res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax) + if (res.ok) { + href = state.md.normalizeLink(res.str) + if (state.md.validateLink(href)) { + pos = res.pos + } else { + href = '' + } + } + + // [link]( "title" ) + // ^^ skipping these spaces + start = pos + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos) + if (!isSpace(code) && code !== 0x0A) { break } + } + + // [link]( "title" ) + // ^^^^^^^ parsing link title + res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax) + if (pos < max && start !== pos && res.ok) { + title = res.str + pos = res.pos + + // [link]( "title" ) + // ^^ skipping these spaces + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos) + if (!isSpace(code) && code !== 0x0A) { break } + } + } else { + title = '' + } + + if (pos >= max || state.src.charCodeAt(pos) !== 0x29/* ) */) { + state.pos = oldPos + return false + } + pos++ + } else { + // + // Link reference + // + if (typeof state.env.references === 'undefined') { return false } + + if (pos < max && state.src.charCodeAt(pos) === 0x5B/* [ */) { + start = pos + 1 + pos = state.md.helpers.parseLinkLabel(state, pos) + if (pos >= 0) { + label = state.src.slice(start, pos++) + } else { + pos = labelEnd + 1 + } + } else { + pos = labelEnd + 1 + } + + // covers label === '' and label === undefined + // (collapsed reference link and shortcut reference link respectively) + if (!label) { label = state.src.slice(labelStart, labelEnd) } + + ref = state.env.references[normalizeReference(label)] + if (!ref) { + state.pos = oldPos + return false + } + href = ref.href + title = ref.title + } + + // + // We found the end of the link, and know for a fact it's a valid link; + // so all that's left to do is to call tokenizer. + // + if (!silent) { + content = state.src.slice(labelStart, labelEnd) + + const tokens = [] + state.md.inline.parse( + content, + state.md, + state.env, + tokens + ) + + const token = state.push('image', 'img', 0) + const attrs = [['src', href], ['alt', '']] + token.attrs = attrs + token.children = tokens + token.content = content + + if (title) { + attrs.push(['title', title]) + } + } + + state.pos = pos + state.posMax = max + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/link.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/link.mjs new file mode 100644 index 0000000..b145173 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/link.mjs @@ -0,0 +1,139 @@ +// Process [link]( "stuff") + +import { normalizeReference, isSpace } from '../common/utils.mjs' + +export default function link (state, silent) { + let code, label, res, ref + let href = '' + let title = '' + let start = state.pos + let parseReference = true + + if (state.src.charCodeAt(state.pos) !== 0x5B/* [ */) { return false } + + const oldPos = state.pos + const max = state.posMax + const labelStart = state.pos + 1 + const labelEnd = state.md.helpers.parseLinkLabel(state, state.pos, true) + + // parser failed to find ']', so it's not a valid link + if (labelEnd < 0) { return false } + + let pos = labelEnd + 1 + if (pos < max && state.src.charCodeAt(pos) === 0x28/* ( */) { + // + // Inline link + // + + // might have found a valid shortcut link, disable reference parsing + parseReference = false + + // [link]( "title" ) + // ^^ skipping these spaces + pos++ + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos) + if (!isSpace(code) && code !== 0x0A) { break } + } + if (pos >= max) { return false } + + // [link]( "title" ) + // ^^^^^^ parsing link destination + start = pos + res = state.md.helpers.parseLinkDestination(state.src, pos, state.posMax) + if (res.ok) { + href = state.md.normalizeLink(res.str) + if (state.md.validateLink(href)) { + pos = res.pos + } else { + href = '' + } + + // [link]( "title" ) + // ^^ skipping these spaces + start = pos + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos) + if (!isSpace(code) && code !== 0x0A) { break } + } + + // [link]( "title" ) + // ^^^^^^^ parsing link title + res = state.md.helpers.parseLinkTitle(state.src, pos, state.posMax) + if (pos < max && start !== pos && res.ok) { + title = res.str + pos = res.pos + + // [link]( "title" ) + // ^^ skipping these spaces + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos) + if (!isSpace(code) && code !== 0x0A) { break } + } + } + } + + if (pos >= max || state.src.charCodeAt(pos) !== 0x29/* ) */) { + // parsing a valid shortcut link failed, fallback to reference + parseReference = true + } + pos++ + } + + if (parseReference) { + // + // Link reference + // + if (typeof state.env.references === 'undefined') { return false } + + if (pos < max && state.src.charCodeAt(pos) === 0x5B/* [ */) { + start = pos + 1 + pos = state.md.helpers.parseLinkLabel(state, pos) + if (pos >= 0) { + label = state.src.slice(start, pos++) + } else { + pos = labelEnd + 1 + } + } else { + pos = labelEnd + 1 + } + + // covers label === '' and label === undefined + // (collapsed reference link and shortcut reference link respectively) + if (!label) { label = state.src.slice(labelStart, labelEnd) } + + ref = state.env.references[normalizeReference(label)] + if (!ref) { + state.pos = oldPos + return false + } + href = ref.href + title = ref.title + } + + // + // We found the end of the link, and know for a fact it's a valid link; + // so all that's left to do is to call tokenizer. + // + if (!silent) { + state.pos = labelStart + state.posMax = labelEnd + + const token_o = state.push('link_open', 'a', 1) + const attrs = [['href', href]] + token_o.attrs = attrs + if (title) { + attrs.push(['title', title]) + } + + state.linkLevel++ + state.md.inline.tokenize(state) + state.linkLevel-- + + state.push('link_close', 'a', -1) + } + + state.pos = pos + state.posMax = max + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/linkify.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/linkify.mjs new file mode 100644 index 0000000..fdc817a --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/linkify.mjs @@ -0,0 +1,56 @@ +// Process links like https://example.org/ + +// RFC3986: scheme = ALPHA *( ALPHA / DIGIT / "+" / "-" / "." ) +const SCHEME_RE = /(?:^|[^a-z0-9.+-])([a-z][a-z0-9.+-]*)$/i + +export default function linkify (state, silent) { + if (!state.md.options.linkify) return false + if (state.linkLevel > 0) return false + + const pos = state.pos + const max = state.posMax + + if (pos + 3 > max) return false + if (state.src.charCodeAt(pos) !== 0x3A/* : */) return false + if (state.src.charCodeAt(pos + 1) !== 0x2F/* / */) return false + if (state.src.charCodeAt(pos + 2) !== 0x2F/* / */) return false + + const match = state.pending.match(SCHEME_RE) + if (!match) return false + + const proto = match[1] + + const link = state.md.linkify.matchAtStart(state.src.slice(pos - proto.length)) + if (!link) return false + + let url = link.url + + // invalid link, but still detected by linkify somehow; + // need to check to prevent infinite loop below + if (url.length <= proto.length) return false + + // disallow '*' at the end of the link (conflicts with emphasis) + url = url.replace(/\*+$/, '') + + const fullUrl = state.md.normalizeLink(url) + if (!state.md.validateLink(fullUrl)) return false + + if (!silent) { + state.pending = state.pending.slice(0, -proto.length) + + const token_o = state.push('link_open', 'a', 1) + token_o.attrs = [['href', fullUrl]] + token_o.markup = 'linkify' + token_o.info = 'auto' + + const token_t = state.push('text', '', 0) + token_t.content = state.md.normalizeLinkText(url) + + const token_c = state.push('link_close', 'a', -1) + token_c.markup = 'linkify' + token_c.info = 'auto' + } + + state.pos += url.length - proto.length + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/newline.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/newline.mjs new file mode 100644 index 0000000..2c0e3ae --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/newline.mjs @@ -0,0 +1,42 @@ +// Proceess '\n' + +import { isSpace } from '../common/utils.mjs' + +export default function newline (state, silent) { + let pos = state.pos + + if (state.src.charCodeAt(pos) !== 0x0A/* \n */) { return false } + + const pmax = state.pending.length - 1 + const max = state.posMax + + // ' \n' -> hardbreak + // Lookup in pending chars is bad practice! Don't copy to other rules! + // Pending string is stored in concat mode, indexed lookups will cause + // convertion to flat mode. + if (!silent) { + if (pmax >= 0 && state.pending.charCodeAt(pmax) === 0x20) { + if (pmax >= 1 && state.pending.charCodeAt(pmax - 1) === 0x20) { + // Find whitespaces tail of pending chars. + let ws = pmax - 1 + while (ws >= 1 && state.pending.charCodeAt(ws - 1) === 0x20) ws-- + + state.pending = state.pending.slice(0, ws) + state.push('hardbreak', 'br', 0) + } else { + state.pending = state.pending.slice(0, -1) + state.push('softbreak', 'br', 0) + } + } else { + state.push('softbreak', 'br', 0) + } + } + + pos++ + + // skip heading spaces for next line + while (pos < max && isSpace(state.src.charCodeAt(pos))) { pos++ } + + state.pos = pos + return true +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/state_inline.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/state_inline.mjs new file mode 100644 index 0000000..80cb3c5 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/state_inline.mjs @@ -0,0 +1,123 @@ +// Inline parser state + +import Token from '../token.mjs' +import { isWhiteSpace, isPunctChar, isMdAsciiPunct } from '../common/utils.mjs' + +function StateInline (src, md, env, outTokens) { + this.src = src + this.env = env + this.md = md + this.tokens = outTokens + this.tokens_meta = Array(outTokens.length) + + this.pos = 0 + this.posMax = this.src.length + this.level = 0 + this.pending = '' + this.pendingLevel = 0 + + // Stores { start: end } pairs. Useful for backtrack + // optimization of pairs parse (emphasis, strikes). + this.cache = {} + + // List of emphasis-like delimiters for current tag + this.delimiters = [] + + // Stack of delimiter lists for upper level tags + this._prev_delimiters = [] + + // backtick length => last seen position + this.backticks = {} + this.backticksScanned = false + + // Counter used to disable inline linkify-it execution + // inside and markdown links + this.linkLevel = 0 +} + +// Flush pending text +// +StateInline.prototype.pushPending = function () { + const token = new Token('text', '', 0) + token.content = this.pending + token.level = this.pendingLevel + this.tokens.push(token) + this.pending = '' + return token +} + +// Push new token to "stream". +// If pending text exists - flush it as text token +// +StateInline.prototype.push = function (type, tag, nesting) { + if (this.pending) { + this.pushPending() + } + + const token = new Token(type, tag, nesting) + let token_meta = null + + if (nesting < 0) { + // closing tag + this.level-- + this.delimiters = this._prev_delimiters.pop() + } + + token.level = this.level + + if (nesting > 0) { + // opening tag + this.level++ + this._prev_delimiters.push(this.delimiters) + this.delimiters = [] + token_meta = { delimiters: this.delimiters } + } + + this.pendingLevel = this.level + this.tokens.push(token) + this.tokens_meta.push(token_meta) + return token +} + +// Scan a sequence of emphasis-like markers, and determine whether +// it can start an emphasis sequence or end an emphasis sequence. +// +// - start - position to scan from (it should point at a valid marker); +// - canSplitWord - determine if these markers can be found inside a word +// +StateInline.prototype.scanDelims = function (start, canSplitWord) { + const max = this.posMax + const marker = this.src.charCodeAt(start) + + // treat beginning of the line as a whitespace + const lastChar = start > 0 ? this.src.charCodeAt(start - 1) : 0x20 + + let pos = start + while (pos < max && this.src.charCodeAt(pos) === marker) { pos++ } + + const count = pos - start + + // treat end of the line as a whitespace + const nextChar = pos < max ? this.src.charCodeAt(pos) : 0x20 + + const isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar)) + const isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar)) + + const isLastWhiteSpace = isWhiteSpace(lastChar) + const isNextWhiteSpace = isWhiteSpace(nextChar) + + const left_flanking = + !isNextWhiteSpace && (!isNextPunctChar || isLastWhiteSpace || isLastPunctChar) + const right_flanking = + !isLastWhiteSpace && (!isLastPunctChar || isNextWhiteSpace || isNextPunctChar) + + const can_open = left_flanking && (canSplitWord || !right_flanking || isLastPunctChar) + const can_close = right_flanking && (canSplitWord || !left_flanking || isNextPunctChar) + + return { can_open, can_close, length: count } +} + +// re-export Token class to use in block rules +StateInline.prototype.Token = Token + +export default StateInline diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/strikethrough.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/strikethrough.mjs new file mode 100644 index 0000000..45f3c1b --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/strikethrough.mjs @@ -0,0 +1,127 @@ +// ~~strike through~~ +// + +// Insert each marker as a separate text token, and add it to delimiter list +// +function strikethrough_tokenize (state, silent) { + const start = state.pos + const marker = state.src.charCodeAt(start) + + if (silent) { return false } + + if (marker !== 0x7E/* ~ */) { return false } + + const scanned = state.scanDelims(state.pos, true) + let len = scanned.length + const ch = String.fromCharCode(marker) + + if (len < 2) { return false } + + let token + + if (len % 2) { + token = state.push('text', '', 0) + token.content = ch + len-- + } + + for (let i = 0; i < len; i += 2) { + token = state.push('text', '', 0) + token.content = ch + ch + + state.delimiters.push({ + marker, + length: 0, // disable "rule of 3" length checks meant for emphasis + token: state.tokens.length - 1, + end: -1, + open: scanned.can_open, + close: scanned.can_close + }) + } + + state.pos += scanned.length + + return true +} + +function postProcess (state, delimiters) { + let token + const loneMarkers = [] + const max = delimiters.length + + for (let i = 0; i < max; i++) { + const startDelim = delimiters[i] + + if (startDelim.marker !== 0x7E/* ~ */) { + continue + } + + if (startDelim.end === -1) { + continue + } + + const endDelim = delimiters[startDelim.end] + + token = state.tokens[startDelim.token] + token.type = 's_open' + token.tag = 's' + token.nesting = 1 + token.markup = '~~' + token.content = '' + + token = state.tokens[endDelim.token] + token.type = 's_close' + token.tag = 's' + token.nesting = -1 + token.markup = '~~' + token.content = '' + + if (state.tokens[endDelim.token - 1].type === 'text' && + state.tokens[endDelim.token - 1].content === '~') { + loneMarkers.push(endDelim.token - 1) + } + } + + // If a marker sequence has an odd number of characters, it's splitted + // like this: `~~~~~` -> `~` + `~~` + `~~`, leaving one marker at the + // start of the sequence. + // + // So, we have to move all those markers after subsequent s_close tags. + // + while (loneMarkers.length) { + const i = loneMarkers.pop() + let j = i + 1 + + while (j < state.tokens.length && state.tokens[j].type === 's_close') { + j++ + } + + j-- + + if (i !== j) { + token = state.tokens[j] + state.tokens[j] = state.tokens[i] + state.tokens[i] = token + } + } +} + +// Walk through delimiter list and replace text tokens with tags +// +function strikethrough_postProcess (state) { + const tokens_meta = state.tokens_meta + const max = state.tokens_meta.length + + postProcess(state, state.delimiters) + + for (let curr = 0; curr < max; curr++) { + if (tokens_meta[curr] && tokens_meta[curr].delimiters) { + postProcess(state, tokens_meta[curr].delimiters) + } + } +} + +export default { + tokenize: strikethrough_tokenize, + postProcess: strikethrough_postProcess +} diff --git a/frontend/node_modules/markdown-it/lib/rules_inline/text.mjs b/frontend/node_modules/markdown-it/lib/rules_inline/text.mjs new file mode 100644 index 0000000..9be4227 --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/rules_inline/text.mjs @@ -0,0 +1,86 @@ +// Skip text characters for text token, place those to pending buffer +// and increment current pos + +// Rule to skip pure text +// '{}$%@~+=:' reserved for extentions + +// !, ", #, $, %, &, ', (, ), *, +, ,, -, ., /, :, ;, <, =, >, ?, @, [, \, ], ^, _, `, {, |, }, or ~ + +// !!!! Don't confuse with "Markdown ASCII Punctuation" chars +// http://spec.commonmark.org/0.15/#ascii-punctuation-character +function isTerminatorChar (ch) { + switch (ch) { + case 0x0A/* \n */: + case 0x21/* ! */: + case 0x23/* # */: + case 0x24/* $ */: + case 0x25/* % */: + case 0x26/* & */: + case 0x2A/* * */: + case 0x2B/* + */: + case 0x2D/* - */: + case 0x3A/* : */: + case 0x3C/* < */: + case 0x3D/* = */: + case 0x3E/* > */: + case 0x40/* @ */: + case 0x5B/* [ */: + case 0x5C/* \ */: + case 0x5D/* ] */: + case 0x5E/* ^ */: + case 0x5F/* _ */: + case 0x60/* ` */: + case 0x7B/* { */: + case 0x7D/* } */: + case 0x7E/* ~ */: + return true + default: + return false + } +} + +export default function text (state, silent) { + let pos = state.pos + + while (pos < state.posMax && !isTerminatorChar(state.src.charCodeAt(pos))) { + pos++ + } + + if (pos === state.pos) { return false } + + if (!silent) { state.pending += state.src.slice(state.pos, pos) } + + state.pos = pos + + return true +} + +// Alternative implementation, for memory. +// +// It costs 10% of performance, but allows extend terminators list, if place it +// to `ParserInline` property. Probably, will switch to it sometime, such +// flexibility required. + +/* +var TERMINATOR_RE = /[\n!#$%&*+\-:<=>@[\\\]^_`{}~]/; + +module.exports = function text(state, silent) { + var pos = state.pos, + idx = state.src.slice(pos).search(TERMINATOR_RE); + + // first char is terminator -> empty text + if (idx === 0) { return false; } + + // no terminator -> text till end of string + if (idx < 0) { + if (!silent) { state.pending += state.src.slice(pos); } + state.pos = state.src.length; + return true; + } + + if (!silent) { state.pending += state.src.slice(pos, pos + idx); } + + state.pos += idx; + + return true; +}; */ diff --git a/frontend/node_modules/markdown-it/lib/token.mjs b/frontend/node_modules/markdown-it/lib/token.mjs new file mode 100644 index 0000000..706ae1d --- /dev/null +++ b/frontend/node_modules/markdown-it/lib/token.mjs @@ -0,0 +1,191 @@ +// Token class + +/** + * class Token + **/ + +/** + * new Token(type, tag, nesting) + * + * Create new token and fill passed properties. + **/ +function Token (type, tag, nesting) { + /** + * Token#type -> String + * + * Type of the token (string, e.g. "paragraph_open") + **/ + this.type = type + + /** + * Token#tag -> String + * + * html tag name, e.g. "p" + **/ + this.tag = tag + + /** + * Token#attrs -> Array + * + * Html attributes. Format: `[ [ name1, value1 ], [ name2, value2 ] ]` + **/ + this.attrs = null + + /** + * Token#map -> Array + * + * Source map info. Format: `[ line_begin, line_end ]` + **/ + this.map = null + + /** + * Token#nesting -> Number + * + * Level change (number in {-1, 0, 1} set), where: + * + * - `1` means the tag is opening + * - `0` means the tag is self-closing + * - `-1` means the tag is closing + **/ + this.nesting = nesting + + /** + * Token#level -> Number + * + * nesting level, the same as `state.level` + **/ + this.level = 0 + + /** + * Token#children -> Array + * + * An array of child nodes (inline and img tokens) + **/ + this.children = null + + /** + * Token#content -> String + * + * In a case of self-closing tag (code, html, fence, etc.), + * it has contents of this tag. + **/ + this.content = '' + + /** + * Token#markup -> String + * + * '*' or '_' for emphasis, fence string for fence, etc. + **/ + this.markup = '' + + /** + * Token#info -> String + * + * Additional information: + * + * - Info string for "fence" tokens + * - The value "auto" for autolink "link_open" and "link_close" tokens + * - The string value of the item marker for ordered-list "list_item_open" tokens + **/ + this.info = '' + + /** + * Token#meta -> Object + * + * A place for plugins to store an arbitrary data + **/ + this.meta = null + + /** + * Token#block -> Boolean + * + * True for block-level tokens, false for inline tokens. + * Used in renderer to calculate line breaks + **/ + this.block = false + + /** + * Token#hidden -> Boolean + * + * If it's true, ignore this element when rendering. Used for tight lists + * to hide paragraphs. + **/ + this.hidden = false +} + +/** + * Token.attrIndex(name) -> Number + * + * Search attribute index by name. + **/ +Token.prototype.attrIndex = function attrIndex (name) { + if (!this.attrs) { return -1 } + + const attrs = this.attrs + + for (let i = 0, len = attrs.length; i < len; i++) { + if (attrs[i][0] === name) { return i } + } + return -1 +} + +/** + * Token.attrPush(attrData) + * + * Add `[ name, value ]` attribute to list. Init attrs if necessary + **/ +Token.prototype.attrPush = function attrPush (attrData) { + if (this.attrs) { + this.attrs.push(attrData) + } else { + this.attrs = [attrData] + } +} + +/** + * Token.attrSet(name, value) + * + * Set `name` attribute to `value`. Override old value if exists. + **/ +Token.prototype.attrSet = function attrSet (name, value) { + const idx = this.attrIndex(name) + const attrData = [name, value] + + if (idx < 0) { + this.attrPush(attrData) + } else { + this.attrs[idx] = attrData + } +} + +/** + * Token.attrGet(name) + * + * Get the value of attribute `name`, or null if it does not exist. + **/ +Token.prototype.attrGet = function attrGet (name) { + const idx = this.attrIndex(name) + let value = null + if (idx >= 0) { + value = this.attrs[idx][1] + } + return value +} + +/** + * Token.attrJoin(name, value) + * + * Join value to existing attribute via space. Or create new attribute if not + * exists. Useful to operate with token classes. + **/ +Token.prototype.attrJoin = function attrJoin (name, value) { + const idx = this.attrIndex(name) + + if (idx < 0) { + this.attrPush([name, value]) + } else { + this.attrs[idx][1] = this.attrs[idx][1] + ' ' + value + } +} + +export default Token diff --git a/frontend/node_modules/markdown-it/node_modules/argparse/CHANGELOG.md b/frontend/node_modules/markdown-it/node_modules/argparse/CHANGELOG.md new file mode 100644 index 0000000..dc39ed6 --- /dev/null +++ b/frontend/node_modules/markdown-it/node_modules/argparse/CHANGELOG.md @@ -0,0 +1,216 @@ +# Changelog + +All notable changes to this project will be documented in this file. + +The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), +and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). + + +## [2.0.1] - 2020-08-29 +### Fixed +- Fix issue with `process.argv` when used with interpreters (`coffee`, `ts-node`, etc.), #150. + + +## [2.0.0] - 2020-08-14 +### Changed +- Full rewrite. Now port from python 3.9.0 & more precise following. + See [doc](./doc) for difference and migration info. +- node.js 10+ required +- Removed most of local docs in favour of original ones. + + +## [1.0.10] - 2018-02-15 +### Fixed +- Use .concat instead of + for arrays, #122. + + +## [1.0.9] - 2016-09-29 +### Changed +- Rerelease after 1.0.8 - deps cleanup. + + +## [1.0.8] - 2016-09-29 +### Changed +- Maintenance (deps bump, fix node 6.5+ tests, coverage report). + + +## [1.0.7] - 2016-03-17 +### Changed +- Teach `addArgument` to accept string arg names. #97, @tomxtobin. + + +## [1.0.6] - 2016-02-06 +### Changed +- Maintenance: moved to eslint & updated CS. + + +## [1.0.5] - 2016-02-05 +### Changed +- Removed lodash dependency to significantly reduce install size. + Thanks to @mourner. + + +## [1.0.4] - 2016-01-17 +### Changed +- Maintenance: lodash update to 4.0.0. + + +## [1.0.3] - 2015-10-27 +### Fixed +- Fix parse `=` in args: `--examplepath="C:\myfolder\env=x64"`. #84, @CatWithApple. + + +## [1.0.2] - 2015-03-22 +### Changed +- Relaxed lodash version dependency. + + +## [1.0.1] - 2015-02-20 +### Changed +- Changed dependencies to be compatible with ancient nodejs. + + +## [1.0.0] - 2015-02-19 +### Changed +- Maintenance release. +- Replaced `underscore` with `lodash`. +- Bumped version to 1.0.0 to better reflect semver meaning. +- HISTORY.md -> CHANGELOG.md + + +## [0.1.16] - 2013-12-01 +### Changed +- Maintenance release. Updated dependencies and docs. + + +## [0.1.15] - 2013-05-13 +### Fixed +- Fixed #55, @trebor89 + + +## [0.1.14] - 2013-05-12 +### Fixed +- Fixed #62, @maxtaco + + +## [0.1.13] - 2013-04-08 +### Changed +- Added `.npmignore` to reduce package size + + +## [0.1.12] - 2013-02-10 +### Fixed +- Fixed conflictHandler (#46), @hpaulj + + +## [0.1.11] - 2013-02-07 +### Added +- Added 70+ tests (ported from python), @hpaulj +- Added conflictHandler, @applepicke +- Added fromfilePrefixChar, @hpaulj + +### Fixed +- Multiple bugfixes, @hpaulj + + +## [0.1.10] - 2012-12-30 +### Added +- Added [mutual exclusion](http://docs.python.org/dev/library/argparse.html#mutual-exclusion) + support, thanks to @hpaulj + +### Fixed +- Fixed options check for `storeConst` & `appendConst` actions, thanks to @hpaulj + + +## [0.1.9] - 2012-12-27 +### Fixed +- Fixed option dest interferens with other options (issue #23), thanks to @hpaulj +- Fixed default value behavior with `*` positionals, thanks to @hpaulj +- Improve `getDefault()` behavior, thanks to @hpaulj +- Improve negative argument parsing, thanks to @hpaulj + + +## [0.1.8] - 2012-12-01 +### Fixed +- Fixed parser parents (issue #19), thanks to @hpaulj +- Fixed negative argument parse (issue #20), thanks to @hpaulj + + +## [0.1.7] - 2012-10-14 +### Fixed +- Fixed 'choices' argument parse (issue #16) +- Fixed stderr output (issue #15) + + +## [0.1.6] - 2012-09-09 +### Fixed +- Fixed check for conflict of options (thanks to @tomxtobin) + + +## [0.1.5] - 2012-09-03 +### Fixed +- Fix parser #setDefaults method (thanks to @tomxtobin) + + +## [0.1.4] - 2012-07-30 +### Fixed +- Fixed pseudo-argument support (thanks to @CGamesPlay) +- Fixed addHelp default (should be true), if not set (thanks to @benblank) + + +## [0.1.3] - 2012-06-27 +### Fixed +- Fixed formatter api name: Formatter -> HelpFormatter + + +## [0.1.2] - 2012-05-29 +### Fixed +- Removed excess whitespace in help +- Fixed error reporting, when parcer with subcommands + called with empty arguments + +### Added +- Added basic tests + + +## [0.1.1] - 2012-05-23 +### Fixed +- Fixed line wrapping in help formatter +- Added better error reporting on invalid arguments + + +## [0.1.0] - 2012-05-16 +### Added +- First release. + + +[2.0.1]: https://github.com/nodeca/argparse/compare/2.0.0...2.0.1 +[2.0.0]: https://github.com/nodeca/argparse/compare/1.0.10...2.0.0 +[1.0.10]: https://github.com/nodeca/argparse/compare/1.0.9...1.0.10 +[1.0.9]: https://github.com/nodeca/argparse/compare/1.0.8...1.0.9 +[1.0.8]: https://github.com/nodeca/argparse/compare/1.0.7...1.0.8 +[1.0.7]: https://github.com/nodeca/argparse/compare/1.0.6...1.0.7 +[1.0.6]: https://github.com/nodeca/argparse/compare/1.0.5...1.0.6 +[1.0.5]: https://github.com/nodeca/argparse/compare/1.0.4...1.0.5 +[1.0.4]: https://github.com/nodeca/argparse/compare/1.0.3...1.0.4 +[1.0.3]: https://github.com/nodeca/argparse/compare/1.0.2...1.0.3 +[1.0.2]: https://github.com/nodeca/argparse/compare/1.0.1...1.0.2 +[1.0.1]: https://github.com/nodeca/argparse/compare/1.0.0...1.0.1 +[1.0.0]: https://github.com/nodeca/argparse/compare/0.1.16...1.0.0 +[0.1.16]: https://github.com/nodeca/argparse/compare/0.1.15...0.1.16 +[0.1.15]: https://github.com/nodeca/argparse/compare/0.1.14...0.1.15 +[0.1.14]: https://github.com/nodeca/argparse/compare/0.1.13...0.1.14 +[0.1.13]: https://github.com/nodeca/argparse/compare/0.1.12...0.1.13 +[0.1.12]: https://github.com/nodeca/argparse/compare/0.1.11...0.1.12 +[0.1.11]: https://github.com/nodeca/argparse/compare/0.1.10...0.1.11 +[0.1.10]: https://github.com/nodeca/argparse/compare/0.1.9...0.1.10 +[0.1.9]: https://github.com/nodeca/argparse/compare/0.1.8...0.1.9 +[0.1.8]: https://github.com/nodeca/argparse/compare/0.1.7...0.1.8 +[0.1.7]: https://github.com/nodeca/argparse/compare/0.1.6...0.1.7 +[0.1.6]: https://github.com/nodeca/argparse/compare/0.1.5...0.1.6 +[0.1.5]: https://github.com/nodeca/argparse/compare/0.1.4...0.1.5 +[0.1.4]: https://github.com/nodeca/argparse/compare/0.1.3...0.1.4 +[0.1.3]: https://github.com/nodeca/argparse/compare/0.1.2...0.1.3 +[0.1.2]: https://github.com/nodeca/argparse/compare/0.1.1...0.1.2 +[0.1.1]: https://github.com/nodeca/argparse/compare/0.1.0...0.1.1 +[0.1.0]: https://github.com/nodeca/argparse/releases/tag/0.1.0 diff --git a/frontend/node_modules/markdown-it/node_modules/argparse/LICENSE b/frontend/node_modules/markdown-it/node_modules/argparse/LICENSE new file mode 100644 index 0000000..66a3ac8 --- /dev/null +++ b/frontend/node_modules/markdown-it/node_modules/argparse/LICENSE @@ -0,0 +1,254 @@ +A. HISTORY OF THE SOFTWARE +========================== + +Python was created in the early 1990s by Guido van Rossum at Stichting +Mathematisch Centrum (CWI, see http://www.cwi.nl) in the Netherlands +as a successor of a language called ABC. Guido remains Python's +principal author, although it includes many contributions from others. + +In 1995, Guido continued his work on Python at the Corporation for +National Research Initiatives (CNRI, see http://www.cnri.reston.va.us) +in Reston, Virginia where he released several versions of the +software. + +In May 2000, Guido and the Python core development team moved to +BeOpen.com to form the BeOpen PythonLabs team. In October of the same +year, the PythonLabs team moved to Digital Creations, which became +Zope Corporation. In 2001, the Python Software Foundation (PSF, see +https://www.python.org/psf/) was formed, a non-profit organization +created specifically to own Python-related Intellectual Property. +Zope Corporation was a sponsoring member of the PSF. + +All Python releases are Open Source (see http://www.opensource.org for +the Open Source Definition). Historically, most, but not all, Python +releases have also been GPL-compatible; the table below summarizes +the various releases. + + Release Derived Year Owner GPL- + from compatible? (1) + + 0.9.0 thru 1.2 1991-1995 CWI yes + 1.3 thru 1.5.2 1.2 1995-1999 CNRI yes + 1.6 1.5.2 2000 CNRI no + 2.0 1.6 2000 BeOpen.com no + 1.6.1 1.6 2001 CNRI yes (2) + 2.1 2.0+1.6.1 2001 PSF no + 2.0.1 2.0+1.6.1 2001 PSF yes + 2.1.1 2.1+2.0.1 2001 PSF yes + 2.1.2 2.1.1 2002 PSF yes + 2.1.3 2.1.2 2002 PSF yes + 2.2 and above 2.1.1 2001-now PSF yes + +Footnotes: + +(1) GPL-compatible doesn't mean that we're distributing Python under + the GPL. All Python licenses, unlike the GPL, let you distribute + a modified version without making your changes open source. The + GPL-compatible licenses make it possible to combine Python with + other software that is released under the GPL; the others don't. + +(2) According to Richard Stallman, 1.6.1 is not GPL-compatible, + because its license has a choice of law clause. According to + CNRI, however, Stallman's lawyer has told CNRI's lawyer that 1.6.1 + is "not incompatible" with the GPL. + +Thanks to the many outside volunteers who have worked under Guido's +direction to make these releases possible. + + +B. TERMS AND CONDITIONS FOR ACCESSING OR OTHERWISE USING PYTHON +=============================================================== + +PYTHON SOFTWARE FOUNDATION LICENSE VERSION 2 +-------------------------------------------- + +1. This LICENSE AGREEMENT is between the Python Software Foundation +("PSF"), and the Individual or Organization ("Licensee") accessing and +otherwise using this software ("Python") in source or binary form and +its associated documentation. + +2. Subject to the terms and conditions of this License Agreement, PSF hereby +grants Licensee a nonexclusive, royalty-free, world-wide license to reproduce, +analyze, test, perform and/or display publicly, prepare derivative works, +distribute, and otherwise use Python alone or in any derivative version, +provided, however, that PSF's License Agreement and PSF's notice of copyright, +i.e., "Copyright (c) 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, +2011, 2012, 2013, 2014, 2015, 2016, 2017, 2018, 2019, 2020 Python Software Foundation; +All Rights Reserved" are retained in Python alone or in any derivative version +prepared by Licensee. + +3. In the event Licensee prepares a derivative work that is based on +or incorporates Python or any part thereof, and wants to make +the derivative work available to others as provided herein, then +Licensee hereby agrees to include in any such work a brief summary of +the changes made to Python. + +4. PSF is making Python available to Licensee on an "AS IS" +basis. PSF MAKES NO REPRESENTATIONS OR WARRANTIES, EXPRESS OR +IMPLIED. BY WAY OF EXAMPLE, BUT NOT LIMITATION, PSF MAKES NO AND +DISCLAIMS ANY REPRESENTATION OR WARRANTY OF MERCHANTABILITY OR FITNESS +FOR ANY PARTICULAR PURPOSE OR THAT THE USE OF PYTHON WILL NOT +INFRINGE ANY THIRD PARTY RIGHTS. + +5. PSF SHALL NOT BE LIABLE TO LICENSEE OR ANY OTHER USERS OF PYTHON +FOR ANY INCIDENTAL, SPECIAL, OR CONSEQUENTIAL DAMAGES OR LOSS AS +A RESULT OF MODIFYING, DISTRIBUTING, OR OTHERWISE USING PYTHON, +OR ANY DERIVATIVE THEREOF, EVEN IF ADVISED OF THE POSSIBILITY THEREOF. + +6. This License Agreement will automatically terminate upon a material +breach of its terms and conditions. + +7. Nothing in this License Agreement shall be deemed to create any +relationship of agency, partnership, or joint venture between PSF and +Licensee. This License Agreement does not grant permission to use PSF +trademarks or trade name in a trademark sense to endorse or promote +products or services of Licensee, or any third party. + +8. By copying, installing or otherwise using Python, Licensee +agrees to be bound by the terms and conditions of this License +Agreement. + + +BEOPEN.COM LICENSE AGREEMENT FOR PYTHON 2.0 +------------------------------------------- + +BEOPEN PYTHON OPEN SOURCE LICENSE AGREEMENT VERSION 1 + +1. This LICENSE AGREEMENT is between BeOpen.com ("BeOpen"), having an +office at 160 Saratoga Avenue, Santa Clara, CA 95051, and the +Individual or Organization ("Licensee") accessing and otherwise using +this software in source or binary form and its associated +documentation ("the Software"). + +2. Subject to the terms and conditions of this BeOpen Python License +Agreement, BeOpen hereby grants Licensee a non-exclusive, +royalty-free, world-wide license to reproduce, analyze, test, perform +and/or display publicly, prepare derivative works, distribute, and +otherwise use the Software alone or in any derivative version, +provided, however, that the BeOpen Python License is retained in the +Software, alone or in any derivative version prepared by Licensee. + +3. BeOpen is making the Software available to Licensee on an "AS IS" +basis. BEOPEN MAKES NO REPRESENTATIONS OR WARRANTIES, EXPRESS OR +IMPLIED. BY WAY OF EXAMPLE, BUT NOT LIMITATION, BEOPEN MAKES NO AND +DISCLAIMS ANY REPRESENTATION OR WARRANTY OF MERCHANTABILITY OR FITNESS +FOR ANY PARTICULAR PURPOSE OR THAT THE USE OF THE SOFTWARE WILL NOT +INFRINGE ANY THIRD PARTY RIGHTS. + +4. BEOPEN SHALL NOT BE LIABLE TO LICENSEE OR ANY OTHER USERS OF THE +SOFTWARE FOR ANY INCIDENTAL, SPECIAL, OR CONSEQUENTIAL DAMAGES OR LOSS +AS A RESULT OF USING, MODIFYING OR DISTRIBUTING THE SOFTWARE, OR ANY +DERIVATIVE THEREOF, EVEN IF ADVISED OF THE POSSIBILITY THEREOF. + +5. This License Agreement will automatically terminate upon a material +breach of its terms and conditions. + +6. This License Agreement shall be governed by and interpreted in all +respects by the law of the State of California, excluding conflict of +law provisions. Nothing in this License Agreement shall be deemed to +create any relationship of agency, partnership, or joint venture +between BeOpen and Licensee. This License Agreement does not grant +permission to use BeOpen trademarks or trade names in a trademark +sense to endorse or promote products or services of Licensee, or any +third party. As an exception, the "BeOpen Python" logos available at +http://www.pythonlabs.com/logos.html may be used according to the +permissions granted on that web page. + +7. By copying, installing or otherwise using the software, Licensee +agrees to be bound by the terms and conditions of this License +Agreement. + + +CNRI LICENSE AGREEMENT FOR PYTHON 1.6.1 +--------------------------------------- + +1. This LICENSE AGREEMENT is between the Corporation for National +Research Initiatives, having an office at 1895 Preston White Drive, +Reston, VA 20191 ("CNRI"), and the Individual or Organization +("Licensee") accessing and otherwise using Python 1.6.1 software in +source or binary form and its associated documentation. + +2. Subject to the terms and conditions of this License Agreement, CNRI +hereby grants Licensee a nonexclusive, royalty-free, world-wide +license to reproduce, analyze, test, perform and/or display publicly, +prepare derivative works, distribute, and otherwise use Python 1.6.1 +alone or in any derivative version, provided, however, that CNRI's +License Agreement and CNRI's notice of copyright, i.e., "Copyright (c) +1995-2001 Corporation for National Research Initiatives; All Rights +Reserved" are retained in Python 1.6.1 alone or in any derivative +version prepared by Licensee. Alternately, in lieu of CNRI's License +Agreement, Licensee may substitute the following text (omitting the +quotes): "Python 1.6.1 is made available subject to the terms and +conditions in CNRI's License Agreement. This Agreement together with +Python 1.6.1 may be located on the Internet using the following +unique, persistent identifier (known as a handle): 1895.22/1013. This +Agreement may also be obtained from a proxy server on the Internet +using the following URL: http://hdl.handle.net/1895.22/1013". + +3. In the event Licensee prepares a derivative work that is based on +or incorporates Python 1.6.1 or any part thereof, and wants to make +the derivative work available to others as provided herein, then +Licensee hereby agrees to include in any such work a brief summary of +the changes made to Python 1.6.1. + +4. CNRI is making Python 1.6.1 available to Licensee on an "AS IS" +basis. CNRI MAKES NO REPRESENTATIONS OR WARRANTIES, EXPRESS OR +IMPLIED. BY WAY OF EXAMPLE, BUT NOT LIMITATION, CNRI MAKES NO AND +DISCLAIMS ANY REPRESENTATION OR WARRANTY OF MERCHANTABILITY OR FITNESS +FOR ANY PARTICULAR PURPOSE OR THAT THE USE OF PYTHON 1.6.1 WILL NOT +INFRINGE ANY THIRD PARTY RIGHTS. + +5. CNRI SHALL NOT BE LIABLE TO LICENSEE OR ANY OTHER USERS OF PYTHON +1.6.1 FOR ANY INCIDENTAL, SPECIAL, OR CONSEQUENTIAL DAMAGES OR LOSS AS +A RESULT OF MODIFYING, DISTRIBUTING, OR OTHERWISE USING PYTHON 1.6.1, +OR ANY DERIVATIVE THEREOF, EVEN IF ADVISED OF THE POSSIBILITY THEREOF. + +6. This License Agreement will automatically terminate upon a material +breach of its terms and conditions. + +7. This License Agreement shall be governed by the federal +intellectual property law of the United States, including without +limitation the federal copyright law, and, to the extent such +U.S. federal law does not apply, by the law of the Commonwealth of +Virginia, excluding Virginia's conflict of law provisions. +Notwithstanding the foregoing, with regard to derivative works based +on Python 1.6.1 that incorporate non-separable material that was +previously distributed under the GNU General Public License (GPL), the +law of the Commonwealth of Virginia shall govern this License +Agreement only as to issues arising under or with respect to +Paragraphs 4, 5, and 7 of this License Agreement. Nothing in this +License Agreement shall be deemed to create any relationship of +agency, partnership, or joint venture between CNRI and Licensee. This +License Agreement does not grant permission to use CNRI trademarks or +trade name in a trademark sense to endorse or promote products or +services of Licensee, or any third party. + +8. By clicking on the "ACCEPT" button where indicated, or by copying, +installing or otherwise using Python 1.6.1, Licensee agrees to be +bound by the terms and conditions of this License Agreement. + + ACCEPT + + +CWI LICENSE AGREEMENT FOR PYTHON 0.9.0 THROUGH 1.2 +-------------------------------------------------- + +Copyright (c) 1991 - 1995, Stichting Mathematisch Centrum Amsterdam, +The Netherlands. All rights reserved. + +Permission to use, copy, modify, and distribute this software and its +documentation for any purpose and without fee is hereby granted, +provided that the above copyright notice appear in all copies and that +both that copyright notice and this permission notice appear in +supporting documentation, and that the name of Stichting Mathematisch +Centrum or CWI not be used in advertising or publicity pertaining to +distribution of the software without specific, written prior +permission. + +STICHTING MATHEMATISCH CENTRUM DISCLAIMS ALL WARRANTIES WITH REGARD TO +THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND +FITNESS, IN NO EVENT SHALL STICHTING MATHEMATISCH CENTRUM BE LIABLE +FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT +OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. diff --git a/frontend/node_modules/markdown-it/node_modules/argparse/README.md b/frontend/node_modules/markdown-it/node_modules/argparse/README.md new file mode 100644 index 0000000..550b5c9 --- /dev/null +++ b/frontend/node_modules/markdown-it/node_modules/argparse/README.md @@ -0,0 +1,84 @@ +argparse +======== + +[![Build Status](https://secure.travis-ci.org/nodeca/argparse.svg?branch=master)](http://travis-ci.org/nodeca/argparse) +[![NPM version](https://img.shields.io/npm/v/argparse.svg)](https://www.npmjs.org/package/argparse) + +CLI arguments parser for node.js, with [sub-commands](https://docs.python.org/3.9/library/argparse.html#sub-commands) support. Port of python's [argparse](http://docs.python.org/dev/library/argparse.html) (version [3.9.0](https://github.com/python/cpython/blob/v3.9.0rc1/Lib/argparse.py)). + +**Difference with original.** + +- JS has no keyword arguments support. + - Pass options instead: `new ArgumentParser({ description: 'example', add_help: true })`. +- JS has no python's types `int`, `float`, ... + - Use string-typed names: `.add_argument('-b', { type: 'int', help: 'help' })`. +- `%r` format specifier uses `require('util').inspect()`. + +More details in [doc](./doc). + + +Example +------- + +`test.js` file: + +```javascript +#!/usr/bin/env node +'use strict'; + +const { ArgumentParser } = require('argparse'); +const { version } = require('./package.json'); + +const parser = new ArgumentParser({ + description: 'Argparse example' +}); + +parser.add_argument('-v', '--version', { action: 'version', version }); +parser.add_argument('-f', '--foo', { help: 'foo bar' }); +parser.add_argument('-b', '--bar', { help: 'bar foo' }); +parser.add_argument('--baz', { help: 'baz bar' }); + +console.dir(parser.parse_args()); +``` + +Display help: + +``` +$ ./test.js -h +usage: test.js [-h] [-v] [-f FOO] [-b BAR] [--baz BAZ] + +Argparse example + +optional arguments: + -h, --help show this help message and exit + -v, --version show program's version number and exit + -f FOO, --foo FOO foo bar + -b BAR, --bar BAR bar foo + --baz BAZ baz bar +``` + +Parse arguments: + +``` +$ ./test.js -f=3 --bar=4 --baz 5 +{ foo: '3', bar: '4', baz: '5' } +``` + + +API docs +-------- + +Since this is a port with minimal divergence, there's no separate documentation. +Use original one instead, with notes about difference. + +1. [Original doc](https://docs.python.org/3.9/library/argparse.html). +2. [Original tutorial](https://docs.python.org/3.9/howto/argparse.html). +3. [Difference with python](./doc). + + +argparse for enterprise +----------------------- + +Available as part of the Tidelift Subscription + +The maintainers of argparse and thousands of other packages are working with Tidelift to deliver commercial support and maintenance for the open source dependencies you use to build your applications. Save time, reduce risk, and improve code health, while paying the maintainers of the exact dependencies you use. [Learn more.](https://tidelift.com/subscription/pkg/npm-argparse?utm_source=npm-argparse&utm_medium=referral&utm_campaign=enterprise&utm_term=repo) diff --git a/frontend/node_modules/markdown-it/node_modules/argparse/argparse.js b/frontend/node_modules/markdown-it/node_modules/argparse/argparse.js new file mode 100644 index 0000000..2b8c8c6 --- /dev/null +++ b/frontend/node_modules/markdown-it/node_modules/argparse/argparse.js @@ -0,0 +1,3707 @@ +// Port of python's argparse module, version 3.9.0: +// https://github.com/python/cpython/blob/v3.9.0rc1/Lib/argparse.py + +'use strict' + +// Copyright (C) 2010-2020 Python Software Foundation. +// Copyright (C) 2020 argparse.js authors + +/* + * Command-line parsing library + * + * This module is an optparse-inspired command-line parsing library that: + * + * - handles both optional and positional arguments + * - produces highly informative usage messages + * - supports parsers that dispatch to sub-parsers + * + * The following is a simple usage example that sums integers from the + * command-line and writes the result to a file:: + * + * parser = argparse.ArgumentParser( + * description='sum the integers at the command line') + * parser.add_argument( + * 'integers', metavar='int', nargs='+', type=int, + * help='an integer to be summed') + * parser.add_argument( + * '--log', default=sys.stdout, type=argparse.FileType('w'), + * help='the file where the sum should be written') + * args = parser.parse_args() + * args.log.write('%s' % sum(args.integers)) + * args.log.close() + * + * The module contains the following public classes: + * + * - ArgumentParser -- The main entry point for command-line parsing. As the + * example above shows, the add_argument() method is used to populate + * the parser with actions for optional and positional arguments. Then + * the parse_args() method is invoked to convert the args at the + * command-line into an object with attributes. + * + * - ArgumentError -- The exception raised by ArgumentParser objects when + * there are errors with the parser's actions. Errors raised while + * parsing the command-line are caught by ArgumentParser and emitted + * as command-line messages. + * + * - FileType -- A factory for defining types of files to be created. As the + * example above shows, instances of FileType are typically passed as + * the type= argument of add_argument() calls. + * + * - Action -- The base class for parser actions. Typically actions are + * selected by passing strings like 'store_true' or 'append_const' to + * the action= argument of add_argument(). However, for greater + * customization of ArgumentParser actions, subclasses of Action may + * be defined and passed as the action= argument. + * + * - HelpFormatter, RawDescriptionHelpFormatter, RawTextHelpFormatter, + * ArgumentDefaultsHelpFormatter -- Formatter classes which + * may be passed as the formatter_class= argument to the + * ArgumentParser constructor. HelpFormatter is the default, + * RawDescriptionHelpFormatter and RawTextHelpFormatter tell the parser + * not to change the formatting for help text, and + * ArgumentDefaultsHelpFormatter adds information about argument defaults + * to the help. + * + * All other classes in this module are considered implementation details. + * (Also note that HelpFormatter and RawDescriptionHelpFormatter are only + * considered public as object names -- the API of the formatter objects is + * still considered an implementation detail.) + */ + +const SUPPRESS = '==SUPPRESS==' + +const OPTIONAL = '?' +const ZERO_OR_MORE = '*' +const ONE_OR_MORE = '+' +const PARSER = 'A...' +const REMAINDER = '...' +const _UNRECOGNIZED_ARGS_ATTR = '_unrecognized_args' + + +// ================================== +// Utility functions used for porting +// ================================== +const assert = require('assert') +const util = require('util') +const fs = require('fs') +const sub = require('./lib/sub') +const path = require('path') +const repr = util.inspect + +function get_argv() { + // omit first argument (which is assumed to be interpreter - `node`, `coffee`, `ts-node`, etc.) + return process.argv.slice(1) +} + +function get_terminal_size() { + return { + columns: +process.env.COLUMNS || process.stdout.columns || 80 + } +} + +function hasattr(object, name) { + return Object.prototype.hasOwnProperty.call(object, name) +} + +function getattr(object, name, value) { + return hasattr(object, name) ? object[name] : value +} + +function setattr(object, name, value) { + object[name] = value +} + +function setdefault(object, name, value) { + if (!hasattr(object, name)) object[name] = value + return object[name] +} + +function delattr(object, name) { + delete object[name] +} + +function range(from, to, step=1) { + // range(10) is equivalent to range(0, 10) + if (arguments.length === 1) [ to, from ] = [ from, 0 ] + if (typeof from !== 'number' || typeof to !== 'number' || typeof step !== 'number') { + throw new TypeError('argument cannot be interpreted as an integer') + } + if (step === 0) throw new TypeError('range() arg 3 must not be zero') + + let result = [] + if (step > 0) { + for (let i = from; i < to; i += step) result.push(i) + } else { + for (let i = from; i > to; i += step) result.push(i) + } + return result +} + +function splitlines(str, keepends = false) { + let result + if (!keepends) { + result = str.split(/\r\n|[\n\r\v\f\x1c\x1d\x1e\x85\u2028\u2029]/) + } else { + result = [] + let parts = str.split(/(\r\n|[\n\r\v\f\x1c\x1d\x1e\x85\u2028\u2029])/) + for (let i = 0; i < parts.length; i += 2) { + result.push(parts[i] + (i + 1 < parts.length ? parts[i + 1] : '')) + } + } + if (!result[result.length - 1]) result.pop() + return result +} + +function _string_lstrip(string, prefix_chars) { + let idx = 0 + while (idx < string.length && prefix_chars.includes(string[idx])) idx++ + return idx ? string.slice(idx) : string +} + +function _string_split(string, sep, maxsplit) { + let result = string.split(sep) + if (result.length > maxsplit) { + result = result.slice(0, maxsplit).concat([ result.slice(maxsplit).join(sep) ]) + } + return result +} + +function _array_equal(array1, array2) { + if (array1.length !== array2.length) return false + for (let i = 0; i < array1.length; i++) { + if (array1[i] !== array2[i]) return false + } + return true +} + +function _array_remove(array, item) { + let idx = array.indexOf(item) + if (idx === -1) throw new TypeError(sub('%r not in list', item)) + array.splice(idx, 1) +} + +// normalize choices to array; +// this isn't required in python because `in` and `map` operators work with anything, +// but in js dealing with multiple types here is too clunky +function _choices_to_array(choices) { + if (choices === undefined) { + return [] + } else if (Array.isArray(choices)) { + return choices + } else if (choices !== null && typeof choices[Symbol.iterator] === 'function') { + return Array.from(choices) + } else if (typeof choices === 'object' && choices !== null) { + return Object.keys(choices) + } else { + throw new Error(sub('invalid choices value: %r', choices)) + } +} + +// decorator that allows a class to be called without new +function _callable(cls) { + let result = { // object is needed for inferred class name + [cls.name]: function (...args) { + let this_class = new.target === result || !new.target + return Reflect.construct(cls, args, this_class ? cls : new.target) + } + } + result[cls.name].prototype = cls.prototype + // fix default tag for toString, e.g. [object Action] instead of [object Object] + cls.prototype[Symbol.toStringTag] = cls.name + return result[cls.name] +} + +function _alias(object, from, to) { + try { + let name = object.constructor.name + Object.defineProperty(object, from, { + value: util.deprecate(object[to], sub('%s.%s() is renamed to %s.%s()', + name, from, name, to)), + enumerable: false + }) + } catch {} +} + +// decorator that allows snake_case class methods to be called with camelCase and vice versa +function _camelcase_alias(_class) { + for (let name of Object.getOwnPropertyNames(_class.prototype)) { + let camelcase = name.replace(/\w_[a-z]/g, s => s[0] + s[2].toUpperCase()) + if (camelcase !== name) _alias(_class.prototype, camelcase, name) + } + return _class +} + +function _to_legacy_name(key) { + key = key.replace(/\w_[a-z]/g, s => s[0] + s[2].toUpperCase()) + if (key === 'default') key = 'defaultValue' + if (key === 'const') key = 'constant' + return key +} + +function _to_new_name(key) { + if (key === 'defaultValue') key = 'default' + if (key === 'constant') key = 'const' + key = key.replace(/[A-Z]/g, c => '_' + c.toLowerCase()) + return key +} + +// parse options +let no_default = Symbol('no_default_value') +function _parse_opts(args, descriptor) { + function get_name() { + let stack = new Error().stack.split('\n') + .map(x => x.match(/^ at (.*) \(.*\)$/)) + .filter(Boolean) + .map(m => m[1]) + .map(fn => fn.match(/[^ .]*$/)[0]) + + if (stack.length && stack[0] === get_name.name) stack.shift() + if (stack.length && stack[0] === _parse_opts.name) stack.shift() + return stack.length ? stack[0] : '' + } + + args = Array.from(args) + let kwargs = {} + let result = [] + let last_opt = args.length && args[args.length - 1] + + if (typeof last_opt === 'object' && last_opt !== null && !Array.isArray(last_opt) && + (!last_opt.constructor || last_opt.constructor.name === 'Object')) { + kwargs = Object.assign({}, args.pop()) + } + + // LEGACY (v1 compatibility): camelcase + let renames = [] + for (let key of Object.keys(descriptor)) { + let old_name = _to_legacy_name(key) + if (old_name !== key && (old_name in kwargs)) { + if (key in kwargs) { + // default and defaultValue specified at the same time, happens often in old tests + //throw new TypeError(sub('%s() got multiple values for argument %r', get_name(), key)) + } else { + kwargs[key] = kwargs[old_name] + } + renames.push([ old_name, key ]) + delete kwargs[old_name] + } + } + if (renames.length) { + let name = get_name() + deprecate('camelcase_' + name, sub('%s(): following options are renamed: %s', + name, renames.map(([ a, b ]) => sub('%r -> %r', a, b)))) + } + // end + + let missing_positionals = [] + let positional_count = args.length + + for (let [ key, def ] of Object.entries(descriptor)) { + if (key[0] === '*') { + if (key.length > 0 && key[1] === '*') { + // LEGACY (v1 compatibility): camelcase + let renames = [] + for (let key of Object.keys(kwargs)) { + let new_name = _to_new_name(key) + if (new_name !== key && (key in kwargs)) { + if (new_name in kwargs) { + // default and defaultValue specified at the same time, happens often in old tests + //throw new TypeError(sub('%s() got multiple values for argument %r', get_name(), new_name)) + } else { + kwargs[new_name] = kwargs[key] + } + renames.push([ key, new_name ]) + delete kwargs[key] + } + } + if (renames.length) { + let name = get_name() + deprecate('camelcase_' + name, sub('%s(): following options are renamed: %s', + name, renames.map(([ a, b ]) => sub('%r -> %r', a, b)))) + } + // end + result.push(kwargs) + kwargs = {} + } else { + result.push(args) + args = [] + } + } else if (key in kwargs && args.length > 0) { + throw new TypeError(sub('%s() got multiple values for argument %r', get_name(), key)) + } else if (key in kwargs) { + result.push(kwargs[key]) + delete kwargs[key] + } else if (args.length > 0) { + result.push(args.shift()) + } else if (def !== no_default) { + result.push(def) + } else { + missing_positionals.push(key) + } + } + + if (Object.keys(kwargs).length) { + throw new TypeError(sub('%s() got an unexpected keyword argument %r', + get_name(), Object.keys(kwargs)[0])) + } + + if (args.length) { + let from = Object.entries(descriptor).filter(([ k, v ]) => k[0] !== '*' && v !== no_default).length + let to = Object.entries(descriptor).filter(([ k ]) => k[0] !== '*').length + throw new TypeError(sub('%s() takes %s positional argument%s but %s %s given', + get_name(), + from === to ? sub('from %s to %s', from, to) : to, + from === to && to === 1 ? '' : 's', + positional_count, + positional_count === 1 ? 'was' : 'were')) + } + + if (missing_positionals.length) { + let strs = missing_positionals.map(repr) + if (strs.length > 1) strs[strs.length - 1] = 'and ' + strs[strs.length - 1] + let str_joined = strs.join(strs.length === 2 ? '' : ', ') + throw new TypeError(sub('%s() missing %i required positional argument%s: %s', + get_name(), strs.length, strs.length === 1 ? '' : 's', str_joined)) + } + + return result +} + +let _deprecations = {} +function deprecate(id, string) { + _deprecations[id] = _deprecations[id] || util.deprecate(() => {}, string) + _deprecations[id]() +} + + +// ============================= +// Utility functions and classes +// ============================= +function _AttributeHolder(cls = Object) { + /* + * Abstract base class that provides __repr__. + * + * The __repr__ method returns a string in the format:: + * ClassName(attr=name, attr=name, ...) + * The attributes are determined either by a class-level attribute, + * '_kwarg_names', or by inspecting the instance __dict__. + */ + + return class _AttributeHolder extends cls { + [util.inspect.custom]() { + let type_name = this.constructor.name + let arg_strings = [] + let star_args = {} + for (let arg of this._get_args()) { + arg_strings.push(repr(arg)) + } + for (let [ name, value ] of this._get_kwargs()) { + if (/^[a-z_][a-z0-9_$]*$/i.test(name)) { + arg_strings.push(sub('%s=%r', name, value)) + } else { + star_args[name] = value + } + } + if (Object.keys(star_args).length) { + arg_strings.push(sub('**%s', repr(star_args))) + } + return sub('%s(%s)', type_name, arg_strings.join(', ')) + } + + toString() { + return this[util.inspect.custom]() + } + + _get_kwargs() { + return Object.entries(this) + } + + _get_args() { + return [] + } + } +} + + +function _copy_items(items) { + if (items === undefined) { + return [] + } + return items.slice(0) +} + + +// =============== +// Formatting Help +// =============== +const HelpFormatter = _camelcase_alias(_callable(class HelpFormatter { + /* + * Formatter for generating usage messages and argument help strings. + * + * Only the name of this class is considered a public API. All the methods + * provided by the class are considered an implementation detail. + */ + + constructor() { + let [ + prog, + indent_increment, + max_help_position, + width + ] = _parse_opts(arguments, { + prog: no_default, + indent_increment: 2, + max_help_position: 24, + width: undefined + }) + + // default setting for width + if (width === undefined) { + width = get_terminal_size().columns + width -= 2 + } + + this._prog = prog + this._indent_increment = indent_increment + this._max_help_position = Math.min(max_help_position, + Math.max(width - 20, indent_increment * 2)) + this._width = width + + this._current_indent = 0 + this._level = 0 + this._action_max_length = 0 + + this._root_section = this._Section(this, undefined) + this._current_section = this._root_section + + this._whitespace_matcher = /[ \t\n\r\f\v]+/g // equivalent to python /\s+/ with ASCII flag + this._long_break_matcher = /\n\n\n+/g + } + + // =============================== + // Section and indentation methods + // =============================== + _indent() { + this._current_indent += this._indent_increment + this._level += 1 + } + + _dedent() { + this._current_indent -= this._indent_increment + assert(this._current_indent >= 0, 'Indent decreased below 0.') + this._level -= 1 + } + + _add_item(func, args) { + this._current_section.items.push([ func, args ]) + } + + // ======================== + // Message building methods + // ======================== + start_section(heading) { + this._indent() + let section = this._Section(this, this._current_section, heading) + this._add_item(section.format_help.bind(section), []) + this._current_section = section + } + + end_section() { + this._current_section = this._current_section.parent + this._dedent() + } + + add_text(text) { + if (text !== SUPPRESS && text !== undefined) { + this._add_item(this._format_text.bind(this), [text]) + } + } + + add_usage(usage, actions, groups, prefix = undefined) { + if (usage !== SUPPRESS) { + let args = [ usage, actions, groups, prefix ] + this._add_item(this._format_usage.bind(this), args) + } + } + + add_argument(action) { + if (action.help !== SUPPRESS) { + + // find all invocations + let invocations = [this._format_action_invocation(action)] + for (let subaction of this._iter_indented_subactions(action)) { + invocations.push(this._format_action_invocation(subaction)) + } + + // update the maximum item length + let invocation_length = Math.max(...invocations.map(invocation => invocation.length)) + let action_length = invocation_length + this._current_indent + this._action_max_length = Math.max(this._action_max_length, + action_length) + + // add the item to the list + this._add_item(this._format_action.bind(this), [action]) + } + } + + add_arguments(actions) { + for (let action of actions) { + this.add_argument(action) + } + } + + // ======================= + // Help-formatting methods + // ======================= + format_help() { + let help = this._root_section.format_help() + if (help) { + help = help.replace(this._long_break_matcher, '\n\n') + help = help.replace(/^\n+|\n+$/g, '') + '\n' + } + return help + } + + _join_parts(part_strings) { + return part_strings.filter(part => part && part !== SUPPRESS).join('') + } + + _format_usage(usage, actions, groups, prefix) { + if (prefix === undefined) { + prefix = 'usage: ' + } + + // if usage is specified, use that + if (usage !== undefined) { + usage = sub(usage, { prog: this._prog }) + + // if no optionals or positionals are available, usage is just prog + } else if (usage === undefined && !actions.length) { + usage = sub('%(prog)s', { prog: this._prog }) + + // if optionals and positionals are available, calculate usage + } else if (usage === undefined) { + let prog = sub('%(prog)s', { prog: this._prog }) + + // split optionals from positionals + let optionals = [] + let positionals = [] + for (let action of actions) { + if (action.option_strings.length) { + optionals.push(action) + } else { + positionals.push(action) + } + } + + // build full usage string + let action_usage = this._format_actions_usage([].concat(optionals).concat(positionals), groups) + usage = [ prog, action_usage ].map(String).join(' ') + + // wrap the usage parts if it's too long + let text_width = this._width - this._current_indent + if (prefix.length + usage.length > text_width) { + + // break usage into wrappable parts + let part_regexp = /\(.*?\)+(?=\s|$)|\[.*?\]+(?=\s|$)|\S+/g + let opt_usage = this._format_actions_usage(optionals, groups) + let pos_usage = this._format_actions_usage(positionals, groups) + let opt_parts = opt_usage.match(part_regexp) || [] + let pos_parts = pos_usage.match(part_regexp) || [] + assert(opt_parts.join(' ') === opt_usage) + assert(pos_parts.join(' ') === pos_usage) + + // helper for wrapping lines + let get_lines = (parts, indent, prefix = undefined) => { + let lines = [] + let line = [] + let line_len + if (prefix !== undefined) { + line_len = prefix.length - 1 + } else { + line_len = indent.length - 1 + } + for (let part of parts) { + if (line_len + 1 + part.length > text_width && line) { + lines.push(indent + line.join(' ')) + line = [] + line_len = indent.length - 1 + } + line.push(part) + line_len += part.length + 1 + } + if (line.length) { + lines.push(indent + line.join(' ')) + } + if (prefix !== undefined) { + lines[0] = lines[0].slice(indent.length) + } + return lines + } + + let lines + + // if prog is short, follow it with optionals or positionals + if (prefix.length + prog.length <= 0.75 * text_width) { + let indent = ' '.repeat(prefix.length + prog.length + 1) + if (opt_parts.length) { + lines = get_lines([prog].concat(opt_parts), indent, prefix) + lines = lines.concat(get_lines(pos_parts, indent)) + } else if (pos_parts.length) { + lines = get_lines([prog].concat(pos_parts), indent, prefix) + } else { + lines = [prog] + } + + // if prog is long, put it on its own line + } else { + let indent = ' '.repeat(prefix.length) + let parts = [].concat(opt_parts).concat(pos_parts) + lines = get_lines(parts, indent) + if (lines.length > 1) { + lines = [] + lines = lines.concat(get_lines(opt_parts, indent)) + lines = lines.concat(get_lines(pos_parts, indent)) + } + lines = [prog].concat(lines) + } + + // join lines into usage + usage = lines.join('\n') + } + } + + // prefix with 'usage:' + return sub('%s%s\n\n', prefix, usage) + } + + _format_actions_usage(actions, groups) { + // find group indices and identify actions in groups + let group_actions = new Set() + let inserts = {} + for (let group of groups) { + let start = actions.indexOf(group._group_actions[0]) + if (start === -1) { + continue + } else { + let end = start + group._group_actions.length + if (_array_equal(actions.slice(start, end), group._group_actions)) { + for (let action of group._group_actions) { + group_actions.add(action) + } + if (!group.required) { + if (start in inserts) { + inserts[start] += ' [' + } else { + inserts[start] = '[' + } + if (end in inserts) { + inserts[end] += ']' + } else { + inserts[end] = ']' + } + } else { + if (start in inserts) { + inserts[start] += ' (' + } else { + inserts[start] = '(' + } + if (end in inserts) { + inserts[end] += ')' + } else { + inserts[end] = ')' + } + } + for (let i of range(start + 1, end)) { + inserts[i] = '|' + } + } + } + } + + // collect all actions format strings + let parts = [] + for (let [ i, action ] of Object.entries(actions)) { + + // suppressed arguments are marked with None + // remove | separators for suppressed arguments + if (action.help === SUPPRESS) { + parts.push(undefined) + if (inserts[+i] === '|') { + delete inserts[+i] + } else if (inserts[+i + 1] === '|') { + delete inserts[+i + 1] + } + + // produce all arg strings + } else if (!action.option_strings.length) { + let default_value = this._get_default_metavar_for_positional(action) + let part = this._format_args(action, default_value) + + // if it's in a group, strip the outer [] + if (group_actions.has(action)) { + if (part[0] === '[' && part[part.length - 1] === ']') { + part = part.slice(1, -1) + } + } + + // add the action string to the list + parts.push(part) + + // produce the first way to invoke the option in brackets + } else { + let option_string = action.option_strings[0] + let part + + // if the Optional doesn't take a value, format is: + // -s or --long + if (action.nargs === 0) { + part = action.format_usage() + + // if the Optional takes a value, format is: + // -s ARGS or --long ARGS + } else { + let default_value = this._get_default_metavar_for_optional(action) + let args_string = this._format_args(action, default_value) + part = sub('%s %s', option_string, args_string) + } + + // make it look optional if it's not required or in a group + if (!action.required && !group_actions.has(action)) { + part = sub('[%s]', part) + } + + // add the action string to the list + parts.push(part) + } + } + + // insert things at the necessary indices + for (let i of Object.keys(inserts).map(Number).sort((a, b) => b - a)) { + parts.splice(+i, 0, inserts[+i]) + } + + // join all the action items with spaces + let text = parts.filter(Boolean).join(' ') + + // clean up separators for mutually exclusive groups + text = text.replace(/([\[(]) /g, '$1') + text = text.replace(/ ([\])])/g, '$1') + text = text.replace(/[\[(] *[\])]/g, '') + text = text.replace(/\(([^|]*)\)/g, '$1', text) + text = text.trim() + + // return the text + return text + } + + _format_text(text) { + if (text.includes('%(prog)')) { + text = sub(text, { prog: this._prog }) + } + let text_width = Math.max(this._width - this._current_indent, 11) + let indent = ' '.repeat(this._current_indent) + return this._fill_text(text, text_width, indent) + '\n\n' + } + + _format_action(action) { + // determine the required width and the entry label + let help_position = Math.min(this._action_max_length + 2, + this._max_help_position) + let help_width = Math.max(this._width - help_position, 11) + let action_width = help_position - this._current_indent - 2 + let action_header = this._format_action_invocation(action) + let indent_first + + // no help; start on same line and add a final newline + if (!action.help) { + let tup = [ this._current_indent, '', action_header ] + action_header = sub('%*s%s\n', ...tup) + + // short action name; start on the same line and pad two spaces + } else if (action_header.length <= action_width) { + let tup = [ this._current_indent, '', action_width, action_header ] + action_header = sub('%*s%-*s ', ...tup) + indent_first = 0 + + // long action name; start on the next line + } else { + let tup = [ this._current_indent, '', action_header ] + action_header = sub('%*s%s\n', ...tup) + indent_first = help_position + } + + // collect the pieces of the action help + let parts = [action_header] + + // if there was help for the action, add lines of help text + if (action.help) { + let help_text = this._expand_help(action) + let help_lines = this._split_lines(help_text, help_width) + parts.push(sub('%*s%s\n', indent_first, '', help_lines[0])) + for (let line of help_lines.slice(1)) { + parts.push(sub('%*s%s\n', help_position, '', line)) + } + + // or add a newline if the description doesn't end with one + } else if (!action_header.endsWith('\n')) { + parts.push('\n') + } + + // if there are any sub-actions, add their help as well + for (let subaction of this._iter_indented_subactions(action)) { + parts.push(this._format_action(subaction)) + } + + // return a single string + return this._join_parts(parts) + } + + _format_action_invocation(action) { + if (!action.option_strings.length) { + let default_value = this._get_default_metavar_for_positional(action) + let metavar = this._metavar_formatter(action, default_value)(1)[0] + return metavar + + } else { + let parts = [] + + // if the Optional doesn't take a value, format is: + // -s, --long + if (action.nargs === 0) { + parts = parts.concat(action.option_strings) + + // if the Optional takes a value, format is: + // -s ARGS, --long ARGS + } else { + let default_value = this._get_default_metavar_for_optional(action) + let args_string = this._format_args(action, default_value) + for (let option_string of action.option_strings) { + parts.push(sub('%s %s', option_string, args_string)) + } + } + + return parts.join(', ') + } + } + + _metavar_formatter(action, default_metavar) { + let result + if (action.metavar !== undefined) { + result = action.metavar + } else if (action.choices !== undefined) { + let choice_strs = _choices_to_array(action.choices).map(String) + result = sub('{%s}', choice_strs.join(',')) + } else { + result = default_metavar + } + + function format(tuple_size) { + if (Array.isArray(result)) { + return result + } else { + return Array(tuple_size).fill(result) + } + } + return format + } + + _format_args(action, default_metavar) { + let get_metavar = this._metavar_formatter(action, default_metavar) + let result + if (action.nargs === undefined) { + result = sub('%s', ...get_metavar(1)) + } else if (action.nargs === OPTIONAL) { + result = sub('[%s]', ...get_metavar(1)) + } else if (action.nargs === ZERO_OR_MORE) { + let metavar = get_metavar(1) + if (metavar.length === 2) { + result = sub('[%s [%s ...]]', ...metavar) + } else { + result = sub('[%s ...]', ...metavar) + } + } else if (action.nargs === ONE_OR_MORE) { + result = sub('%s [%s ...]', ...get_metavar(2)) + } else if (action.nargs === REMAINDER) { + result = '...' + } else if (action.nargs === PARSER) { + result = sub('%s ...', ...get_metavar(1)) + } else if (action.nargs === SUPPRESS) { + result = '' + } else { + let formats + try { + formats = range(action.nargs).map(() => '%s') + } catch (err) { + throw new TypeError('invalid nargs value') + } + result = sub(formats.join(' '), ...get_metavar(action.nargs)) + } + return result + } + + _expand_help(action) { + let params = Object.assign({ prog: this._prog }, action) + for (let name of Object.keys(params)) { + if (params[name] === SUPPRESS) { + delete params[name] + } + } + for (let name of Object.keys(params)) { + if (params[name] && params[name].name) { + params[name] = params[name].name + } + } + if (params.choices !== undefined) { + let choices_str = _choices_to_array(params.choices).map(String).join(', ') + params.choices = choices_str + } + // LEGACY (v1 compatibility): camelcase + for (let key of Object.keys(params)) { + let old_name = _to_legacy_name(key) + if (old_name !== key) { + params[old_name] = params[key] + } + } + // end + return sub(this._get_help_string(action), params) + } + + * _iter_indented_subactions(action) { + if (typeof action._get_subactions === 'function') { + this._indent() + yield* action._get_subactions() + this._dedent() + } + } + + _split_lines(text, width) { + text = text.replace(this._whitespace_matcher, ' ').trim() + // The textwrap module is used only for formatting help. + // Delay its import for speeding up the common usage of argparse. + let textwrap = require('./lib/textwrap') + return textwrap.wrap(text, { width }) + } + + _fill_text(text, width, indent) { + text = text.replace(this._whitespace_matcher, ' ').trim() + let textwrap = require('./lib/textwrap') + return textwrap.fill(text, { width, + initial_indent: indent, + subsequent_indent: indent }) + } + + _get_help_string(action) { + return action.help + } + + _get_default_metavar_for_optional(action) { + return action.dest.toUpperCase() + } + + _get_default_metavar_for_positional(action) { + return action.dest + } +})) + +HelpFormatter.prototype._Section = _callable(class _Section { + + constructor(formatter, parent, heading = undefined) { + this.formatter = formatter + this.parent = parent + this.heading = heading + this.items = [] + } + + format_help() { + // format the indented section + if (this.parent !== undefined) { + this.formatter._indent() + } + let item_help = this.formatter._join_parts(this.items.map(([ func, args ]) => func.apply(null, args))) + if (this.parent !== undefined) { + this.formatter._dedent() + } + + // return nothing if the section was empty + if (!item_help) { + return '' + } + + // add the heading if the section was non-empty + let heading + if (this.heading !== SUPPRESS && this.heading !== undefined) { + let current_indent = this.formatter._current_indent + heading = sub('%*s%s:\n', current_indent, '', this.heading) + } else { + heading = '' + } + + // join the section-initial newline, the heading and the help + return this.formatter._join_parts(['\n', heading, item_help, '\n']) + } +}) + + +const RawDescriptionHelpFormatter = _camelcase_alias(_callable(class RawDescriptionHelpFormatter extends HelpFormatter { + /* + * Help message formatter which retains any formatting in descriptions. + * + * Only the name of this class is considered a public API. All the methods + * provided by the class are considered an implementation detail. + */ + + _fill_text(text, width, indent) { + return splitlines(text, true).map(line => indent + line).join('') + } +})) + + +const RawTextHelpFormatter = _camelcase_alias(_callable(class RawTextHelpFormatter extends RawDescriptionHelpFormatter { + /* + * Help message formatter which retains formatting of all help text. + * + * Only the name of this class is considered a public API. All the methods + * provided by the class are considered an implementation detail. + */ + + _split_lines(text/*, width*/) { + return splitlines(text) + } +})) + + +const ArgumentDefaultsHelpFormatter = _camelcase_alias(_callable(class ArgumentDefaultsHelpFormatter extends HelpFormatter { + /* + * Help message formatter which adds default values to argument help. + * + * Only the name of this class is considered a public API. All the methods + * provided by the class are considered an implementation detail. + */ + + _get_help_string(action) { + let help = action.help + // LEGACY (v1 compatibility): additional check for defaultValue needed + if (!action.help.includes('%(default)') && !action.help.includes('%(defaultValue)')) { + if (action.default !== SUPPRESS) { + let defaulting_nargs = [OPTIONAL, ZERO_OR_MORE] + if (action.option_strings.length || defaulting_nargs.includes(action.nargs)) { + help += ' (default: %(default)s)' + } + } + } + return help + } +})) + + +const MetavarTypeHelpFormatter = _camelcase_alias(_callable(class MetavarTypeHelpFormatter extends HelpFormatter { + /* + * Help message formatter which uses the argument 'type' as the default + * metavar value (instead of the argument 'dest') + * + * Only the name of this class is considered a public API. All the methods + * provided by the class are considered an implementation detail. + */ + + _get_default_metavar_for_optional(action) { + return typeof action.type === 'function' ? action.type.name : action.type + } + + _get_default_metavar_for_positional(action) { + return typeof action.type === 'function' ? action.type.name : action.type + } +})) + + +// ===================== +// Options and Arguments +// ===================== +function _get_action_name(argument) { + if (argument === undefined) { + return undefined + } else if (argument.option_strings.length) { + return argument.option_strings.join('/') + } else if (![ undefined, SUPPRESS ].includes(argument.metavar)) { + return argument.metavar + } else if (![ undefined, SUPPRESS ].includes(argument.dest)) { + return argument.dest + } else { + return undefined + } +} + + +const ArgumentError = _callable(class ArgumentError extends Error { + /* + * An error from creating or using an argument (optional or positional). + * + * The string value of this exception is the message, augmented with + * information about the argument that caused it. + */ + + constructor(argument, message) { + super() + this.name = 'ArgumentError' + this._argument_name = _get_action_name(argument) + this._message = message + this.message = this.str() + } + + str() { + let format + if (this._argument_name === undefined) { + format = '%(message)s' + } else { + format = 'argument %(argument_name)s: %(message)s' + } + return sub(format, { message: this._message, + argument_name: this._argument_name }) + } +}) + + +const ArgumentTypeError = _callable(class ArgumentTypeError extends Error { + /* + * An error from trying to convert a command line string to a type. + */ + + constructor(message) { + super(message) + this.name = 'ArgumentTypeError' + } +}) + + +// ============== +// Action classes +// ============== +const Action = _camelcase_alias(_callable(class Action extends _AttributeHolder(Function) { + /* + * Information about how to convert command line strings to Python objects. + * + * Action objects are used by an ArgumentParser to represent the information + * needed to parse a single argument from one or more strings from the + * command line. The keyword arguments to the Action constructor are also + * all attributes of Action instances. + * + * Keyword Arguments: + * + * - option_strings -- A list of command-line option strings which + * should be associated with this action. + * + * - dest -- The name of the attribute to hold the created object(s) + * + * - nargs -- The number of command-line arguments that should be + * consumed. By default, one argument will be consumed and a single + * value will be produced. Other values include: + * - N (an integer) consumes N arguments (and produces a list) + * - '?' consumes zero or one arguments + * - '*' consumes zero or more arguments (and produces a list) + * - '+' consumes one or more arguments (and produces a list) + * Note that the difference between the default and nargs=1 is that + * with the default, a single value will be produced, while with + * nargs=1, a list containing a single value will be produced. + * + * - const -- The value to be produced if the option is specified and the + * option uses an action that takes no values. + * + * - default -- The value to be produced if the option is not specified. + * + * - type -- A callable that accepts a single string argument, and + * returns the converted value. The standard Python types str, int, + * float, and complex are useful examples of such callables. If None, + * str is used. + * + * - choices -- A container of values that should be allowed. If not None, + * after a command-line argument has been converted to the appropriate + * type, an exception will be raised if it is not a member of this + * collection. + * + * - required -- True if the action must always be specified at the + * command line. This is only meaningful for optional command-line + * arguments. + * + * - help -- The help string describing the argument. + * + * - metavar -- The name to be used for the option's argument with the + * help string. If None, the 'dest' value will be used as the name. + */ + + constructor() { + let [ + option_strings, + dest, + nargs, + const_value, + default_value, + type, + choices, + required, + help, + metavar + ] = _parse_opts(arguments, { + option_strings: no_default, + dest: no_default, + nargs: undefined, + const: undefined, + default: undefined, + type: undefined, + choices: undefined, + required: false, + help: undefined, + metavar: undefined + }) + + // when this class is called as a function, redirect it to .call() method of itself + super('return arguments.callee.call.apply(arguments.callee, arguments)') + + this.option_strings = option_strings + this.dest = dest + this.nargs = nargs + this.const = const_value + this.default = default_value + this.type = type + this.choices = choices + this.required = required + this.help = help + this.metavar = metavar + } + + _get_kwargs() { + let names = [ + 'option_strings', + 'dest', + 'nargs', + 'const', + 'default', + 'type', + 'choices', + 'help', + 'metavar' + ] + return names.map(name => [ name, getattr(this, name) ]) + } + + format_usage() { + return this.option_strings[0] + } + + call(/*parser, namespace, values, option_string = undefined*/) { + throw new Error('.call() not defined') + } +})) + + +const BooleanOptionalAction = _camelcase_alias(_callable(class BooleanOptionalAction extends Action { + + constructor() { + let [ + option_strings, + dest, + default_value, + type, + choices, + required, + help, + metavar + ] = _parse_opts(arguments, { + option_strings: no_default, + dest: no_default, + default: undefined, + type: undefined, + choices: undefined, + required: false, + help: undefined, + metavar: undefined + }) + + let _option_strings = [] + for (let option_string of option_strings) { + _option_strings.push(option_string) + + if (option_string.startsWith('--')) { + option_string = '--no-' + option_string.slice(2) + _option_strings.push(option_string) + } + } + + if (help !== undefined && default_value !== undefined) { + help += ` (default: ${default_value})` + } + + super({ + option_strings: _option_strings, + dest, + nargs: 0, + default: default_value, + type, + choices, + required, + help, + metavar + }) + } + + call(parser, namespace, values, option_string = undefined) { + if (this.option_strings.includes(option_string)) { + setattr(namespace, this.dest, !option_string.startsWith('--no-')) + } + } + + format_usage() { + return this.option_strings.join(' | ') + } +})) + + +const _StoreAction = _callable(class _StoreAction extends Action { + + constructor() { + let [ + option_strings, + dest, + nargs, + const_value, + default_value, + type, + choices, + required, + help, + metavar + ] = _parse_opts(arguments, { + option_strings: no_default, + dest: no_default, + nargs: undefined, + const: undefined, + default: undefined, + type: undefined, + choices: undefined, + required: false, + help: undefined, + metavar: undefined + }) + + if (nargs === 0) { + throw new TypeError('nargs for store actions must be != 0; if you ' + + 'have nothing to store, actions such as store ' + + 'true or store const may be more appropriate') + } + if (const_value !== undefined && nargs !== OPTIONAL) { + throw new TypeError(sub('nargs must be %r to supply const', OPTIONAL)) + } + super({ + option_strings, + dest, + nargs, + const: const_value, + default: default_value, + type, + choices, + required, + help, + metavar + }) + } + + call(parser, namespace, values/*, option_string = undefined*/) { + setattr(namespace, this.dest, values) + } +}) + + +const _StoreConstAction = _callable(class _StoreConstAction extends Action { + + constructor() { + let [ + option_strings, + dest, + const_value, + default_value, + required, + help + //, metavar + ] = _parse_opts(arguments, { + option_strings: no_default, + dest: no_default, + const: no_default, + default: undefined, + required: false, + help: undefined, + metavar: undefined + }) + + super({ + option_strings, + dest, + nargs: 0, + const: const_value, + default: default_value, + required, + help + }) + } + + call(parser, namespace/*, values, option_string = undefined*/) { + setattr(namespace, this.dest, this.const) + } +}) + + +const _StoreTrueAction = _callable(class _StoreTrueAction extends _StoreConstAction { + + constructor() { + let [ + option_strings, + dest, + default_value, + required, + help + ] = _parse_opts(arguments, { + option_strings: no_default, + dest: no_default, + default: false, + required: false, + help: undefined + }) + + super({ + option_strings, + dest, + const: true, + default: default_value, + required, + help + }) + } +}) + + +const _StoreFalseAction = _callable(class _StoreFalseAction extends _StoreConstAction { + + constructor() { + let [ + option_strings, + dest, + default_value, + required, + help + ] = _parse_opts(arguments, { + option_strings: no_default, + dest: no_default, + default: true, + required: false, + help: undefined + }) + + super({ + option_strings, + dest, + const: false, + default: default_value, + required, + help + }) + } +}) + + +const _AppendAction = _callable(class _AppendAction extends Action { + + constructor() { + let [ + option_strings, + dest, + nargs, + const_value, + default_value, + type, + choices, + required, + help, + metavar + ] = _parse_opts(arguments, { + option_strings: no_default, + dest: no_default, + nargs: undefined, + const: undefined, + default: undefined, + type: undefined, + choices: undefined, + required: false, + help: undefined, + metavar: undefined + }) + + if (nargs === 0) { + throw new TypeError('nargs for append actions must be != 0; if arg ' + + 'strings are not supplying the value to append, ' + + 'the append const action may be more appropriate') + } + if (const_value !== undefined && nargs !== OPTIONAL) { + throw new TypeError(sub('nargs must be %r to supply const', OPTIONAL)) + } + super({ + option_strings, + dest, + nargs, + const: const_value, + default: default_value, + type, + choices, + required, + help, + metavar + }) + } + + call(parser, namespace, values/*, option_string = undefined*/) { + let items = getattr(namespace, this.dest, undefined) + items = _copy_items(items) + items.push(values) + setattr(namespace, this.dest, items) + } +}) + + +const _AppendConstAction = _callable(class _AppendConstAction extends Action { + + constructor() { + let [ + option_strings, + dest, + const_value, + default_value, + required, + help, + metavar + ] = _parse_opts(arguments, { + option_strings: no_default, + dest: no_default, + const: no_default, + default: undefined, + required: false, + help: undefined, + metavar: undefined + }) + + super({ + option_strings, + dest, + nargs: 0, + const: const_value, + default: default_value, + required, + help, + metavar + }) + } + + call(parser, namespace/*, values, option_string = undefined*/) { + let items = getattr(namespace, this.dest, undefined) + items = _copy_items(items) + items.push(this.const) + setattr(namespace, this.dest, items) + } +}) + + +const _CountAction = _callable(class _CountAction extends Action { + + constructor() { + let [ + option_strings, + dest, + default_value, + required, + help + ] = _parse_opts(arguments, { + option_strings: no_default, + dest: no_default, + default: undefined, + required: false, + help: undefined + }) + + super({ + option_strings, + dest, + nargs: 0, + default: default_value, + required, + help + }) + } + + call(parser, namespace/*, values, option_string = undefined*/) { + let count = getattr(namespace, this.dest, undefined) + if (count === undefined) { + count = 0 + } + setattr(namespace, this.dest, count + 1) + } +}) + + +const _HelpAction = _callable(class _HelpAction extends Action { + + constructor() { + let [ + option_strings, + dest, + default_value, + help + ] = _parse_opts(arguments, { + option_strings: no_default, + dest: SUPPRESS, + default: SUPPRESS, + help: undefined + }) + + super({ + option_strings, + dest, + default: default_value, + nargs: 0, + help + }) + } + + call(parser/*, namespace, values, option_string = undefined*/) { + parser.print_help() + parser.exit() + } +}) + + +const _VersionAction = _callable(class _VersionAction extends Action { + + constructor() { + let [ + option_strings, + version, + dest, + default_value, + help + ] = _parse_opts(arguments, { + option_strings: no_default, + version: undefined, + dest: SUPPRESS, + default: SUPPRESS, + help: "show program's version number and exit" + }) + + super({ + option_strings, + dest, + default: default_value, + nargs: 0, + help + }) + this.version = version + } + + call(parser/*, namespace, values, option_string = undefined*/) { + let version = this.version + if (version === undefined) { + version = parser.version + } + let formatter = parser._get_formatter() + formatter.add_text(version) + parser._print_message(formatter.format_help(), process.stdout) + parser.exit() + } +}) + + +const _SubParsersAction = _camelcase_alias(_callable(class _SubParsersAction extends Action { + + constructor() { + let [ + option_strings, + prog, + parser_class, + dest, + required, + help, + metavar + ] = _parse_opts(arguments, { + option_strings: no_default, + prog: no_default, + parser_class: no_default, + dest: SUPPRESS, + required: false, + help: undefined, + metavar: undefined + }) + + let name_parser_map = {} + + super({ + option_strings, + dest, + nargs: PARSER, + choices: name_parser_map, + required, + help, + metavar + }) + + this._prog_prefix = prog + this._parser_class = parser_class + this._name_parser_map = name_parser_map + this._choices_actions = [] + } + + add_parser() { + let [ + name, + kwargs + ] = _parse_opts(arguments, { + name: no_default, + '**kwargs': no_default + }) + + // set prog from the existing prefix + if (kwargs.prog === undefined) { + kwargs.prog = sub('%s %s', this._prog_prefix, name) + } + + let aliases = getattr(kwargs, 'aliases', []) + delete kwargs.aliases + + // create a pseudo-action to hold the choice help + if ('help' in kwargs) { + let help = kwargs.help + delete kwargs.help + let choice_action = this._ChoicesPseudoAction(name, aliases, help) + this._choices_actions.push(choice_action) + } + + // create the parser and add it to the map + let parser = new this._parser_class(kwargs) + this._name_parser_map[name] = parser + + // make parser available under aliases also + for (let alias of aliases) { + this._name_parser_map[alias] = parser + } + + return parser + } + + _get_subactions() { + return this._choices_actions + } + + call(parser, namespace, values/*, option_string = undefined*/) { + let parser_name = values[0] + let arg_strings = values.slice(1) + + // set the parser name if requested + if (this.dest !== SUPPRESS) { + setattr(namespace, this.dest, parser_name) + } + + // select the parser + if (hasattr(this._name_parser_map, parser_name)) { + parser = this._name_parser_map[parser_name] + } else { + let args = {parser_name, + choices: this._name_parser_map.join(', ')} + let msg = sub('unknown parser %(parser_name)r (choices: %(choices)s)', args) + throw new ArgumentError(this, msg) + } + + // parse all the remaining options into the namespace + // store any unrecognized options on the object, so that the top + // level parser can decide what to do with them + + // In case this subparser defines new defaults, we parse them + // in a new namespace object and then update the original + // namespace for the relevant parts. + let subnamespace + [ subnamespace, arg_strings ] = parser.parse_known_args(arg_strings, undefined) + for (let [ key, value ] of Object.entries(subnamespace)) { + setattr(namespace, key, value) + } + + if (arg_strings.length) { + setdefault(namespace, _UNRECOGNIZED_ARGS_ATTR, []) + getattr(namespace, _UNRECOGNIZED_ARGS_ATTR).push(...arg_strings) + } + } +})) + + +_SubParsersAction.prototype._ChoicesPseudoAction = _callable(class _ChoicesPseudoAction extends Action { + constructor(name, aliases, help) { + let metavar = name, dest = name + if (aliases.length) { + metavar += sub(' (%s)', aliases.join(', ')) + } + super({ option_strings: [], dest, help, metavar }) + } +}) + + +const _ExtendAction = _callable(class _ExtendAction extends _AppendAction { + call(parser, namespace, values/*, option_string = undefined*/) { + let items = getattr(namespace, this.dest, undefined) + items = _copy_items(items) + items = items.concat(values) + setattr(namespace, this.dest, items) + } +}) + + +// ============== +// Type classes +// ============== +const FileType = _callable(class FileType extends Function { + /* + * Factory for creating file object types + * + * Instances of FileType are typically passed as type= arguments to the + * ArgumentParser add_argument() method. + * + * Keyword Arguments: + * - mode -- A string indicating how the file is to be opened. Accepts the + * same values as the builtin open() function. + * - bufsize -- The file's desired buffer size. Accepts the same values as + * the builtin open() function. + * - encoding -- The file's encoding. Accepts the same values as the + * builtin open() function. + * - errors -- A string indicating how encoding and decoding errors are to + * be handled. Accepts the same value as the builtin open() function. + */ + + constructor() { + let [ + flags, + encoding, + mode, + autoClose, + emitClose, + start, + end, + highWaterMark, + fs + ] = _parse_opts(arguments, { + flags: 'r', + encoding: undefined, + mode: undefined, // 0o666 + autoClose: undefined, // true + emitClose: undefined, // false + start: undefined, // 0 + end: undefined, // Infinity + highWaterMark: undefined, // 64 * 1024 + fs: undefined + }) + + // when this class is called as a function, redirect it to .call() method of itself + super('return arguments.callee.call.apply(arguments.callee, arguments)') + + Object.defineProperty(this, 'name', { + get() { + return sub('FileType(%r)', flags) + } + }) + this._flags = flags + this._options = {} + if (encoding !== undefined) this._options.encoding = encoding + if (mode !== undefined) this._options.mode = mode + if (autoClose !== undefined) this._options.autoClose = autoClose + if (emitClose !== undefined) this._options.emitClose = emitClose + if (start !== undefined) this._options.start = start + if (end !== undefined) this._options.end = end + if (highWaterMark !== undefined) this._options.highWaterMark = highWaterMark + if (fs !== undefined) this._options.fs = fs + } + + call(string) { + // the special argument "-" means sys.std{in,out} + if (string === '-') { + if (this._flags.includes('r')) { + return process.stdin + } else if (this._flags.includes('w')) { + return process.stdout + } else { + let msg = sub('argument "-" with mode %r', this._flags) + throw new TypeError(msg) + } + } + + // all other arguments are used as file names + let fd + try { + fd = fs.openSync(string, this._flags, this._options.mode) + } catch (e) { + let args = { filename: string, error: e.message } + let message = "can't open '%(filename)s': %(error)s" + throw new ArgumentTypeError(sub(message, args)) + } + + let options = Object.assign({ fd, flags: this._flags }, this._options) + if (this._flags.includes('r')) { + return fs.createReadStream(undefined, options) + } else if (this._flags.includes('w')) { + return fs.createWriteStream(undefined, options) + } else { + let msg = sub('argument "%s" with mode %r', string, this._flags) + throw new TypeError(msg) + } + } + + [util.inspect.custom]() { + let args = [ this._flags ] + let kwargs = Object.entries(this._options).map(([ k, v ]) => { + if (k === 'mode') v = { value: v, [util.inspect.custom]() { return '0o' + this.value.toString(8) } } + return [ k, v ] + }) + let args_str = [] + .concat(args.filter(arg => arg !== -1).map(repr)) + .concat(kwargs.filter(([/*kw*/, arg]) => arg !== undefined) + .map(([kw, arg]) => sub('%s=%r', kw, arg))) + .join(', ') + return sub('%s(%s)', this.constructor.name, args_str) + } + + toString() { + return this[util.inspect.custom]() + } +}) + +// =========================== +// Optional and Positional Parsing +// =========================== +const Namespace = _callable(class Namespace extends _AttributeHolder() { + /* + * Simple object for storing attributes. + * + * Implements equality by attribute names and values, and provides a simple + * string representation. + */ + + constructor(options = {}) { + super() + Object.assign(this, options) + } +}) + +// unset string tag to mimic plain object +Namespace.prototype[Symbol.toStringTag] = undefined + + +const _ActionsContainer = _camelcase_alias(_callable(class _ActionsContainer { + + constructor() { + let [ + description, + prefix_chars, + argument_default, + conflict_handler + ] = _parse_opts(arguments, { + description: no_default, + prefix_chars: no_default, + argument_default: no_default, + conflict_handler: no_default + }) + + this.description = description + this.argument_default = argument_default + this.prefix_chars = prefix_chars + this.conflict_handler = conflict_handler + + // set up registries + this._registries = {} + + // register actions + this.register('action', undefined, _StoreAction) + this.register('action', 'store', _StoreAction) + this.register('action', 'store_const', _StoreConstAction) + this.register('action', 'store_true', _StoreTrueAction) + this.register('action', 'store_false', _StoreFalseAction) + this.register('action', 'append', _AppendAction) + this.register('action', 'append_const', _AppendConstAction) + this.register('action', 'count', _CountAction) + this.register('action', 'help', _HelpAction) + this.register('action', 'version', _VersionAction) + this.register('action', 'parsers', _SubParsersAction) + this.register('action', 'extend', _ExtendAction) + // LEGACY (v1 compatibility): camelcase variants + ;[ 'storeConst', 'storeTrue', 'storeFalse', 'appendConst' ].forEach(old_name => { + let new_name = _to_new_name(old_name) + this.register('action', old_name, util.deprecate(this._registry_get('action', new_name), + sub('{action: "%s"} is renamed to {action: "%s"}', old_name, new_name))) + }) + // end + + // raise an exception if the conflict handler is invalid + this._get_handler() + + // action storage + this._actions = [] + this._option_string_actions = {} + + // groups + this._action_groups = [] + this._mutually_exclusive_groups = [] + + // defaults storage + this._defaults = {} + + // determines whether an "option" looks like a negative number + this._negative_number_matcher = /^-\d+$|^-\d*\.\d+$/ + + // whether or not there are any optionals that look like negative + // numbers -- uses a list so it can be shared and edited + this._has_negative_number_optionals = [] + } + + // ==================== + // Registration methods + // ==================== + register(registry_name, value, object) { + let registry = setdefault(this._registries, registry_name, {}) + registry[value] = object + } + + _registry_get(registry_name, value, default_value = undefined) { + return getattr(this._registries[registry_name], value, default_value) + } + + // ================================== + // Namespace default accessor methods + // ================================== + set_defaults(kwargs) { + Object.assign(this._defaults, kwargs) + + // if these defaults match any existing arguments, replace + // the previous default on the object with the new one + for (let action of this._actions) { + if (action.dest in kwargs) { + action.default = kwargs[action.dest] + } + } + } + + get_default(dest) { + for (let action of this._actions) { + if (action.dest === dest && action.default !== undefined) { + return action.default + } + } + return this._defaults[dest] + } + + + // ======================= + // Adding argument actions + // ======================= + add_argument() { + /* + * add_argument(dest, ..., name=value, ...) + * add_argument(option_string, option_string, ..., name=value, ...) + */ + let [ + args, + kwargs + ] = _parse_opts(arguments, { + '*args': no_default, + '**kwargs': no_default + }) + // LEGACY (v1 compatibility), old-style add_argument([ args ], { options }) + if (args.length === 1 && Array.isArray(args[0])) { + args = args[0] + deprecate('argument-array', + sub('use add_argument(%(args)s, {...}) instead of add_argument([ %(args)s ], { ... })', { + args: args.map(repr).join(', ') + })) + } + // end + + // if no positional args are supplied or only one is supplied and + // it doesn't look like an option string, parse a positional + // argument + let chars = this.prefix_chars + if (!args.length || args.length === 1 && !chars.includes(args[0][0])) { + if (args.length && 'dest' in kwargs) { + throw new TypeError('dest supplied twice for positional argument') + } + kwargs = this._get_positional_kwargs(...args, kwargs) + + // otherwise, we're adding an optional argument + } else { + kwargs = this._get_optional_kwargs(...args, kwargs) + } + + // if no default was supplied, use the parser-level default + if (!('default' in kwargs)) { + let dest = kwargs.dest + if (dest in this._defaults) { + kwargs.default = this._defaults[dest] + } else if (this.argument_default !== undefined) { + kwargs.default = this.argument_default + } + } + + // create the action object, and add it to the parser + let action_class = this._pop_action_class(kwargs) + if (typeof action_class !== 'function') { + throw new TypeError(sub('unknown action "%s"', action_class)) + } + // eslint-disable-next-line new-cap + let action = new action_class(kwargs) + + // raise an error if the action type is not callable + let type_func = this._registry_get('type', action.type, action.type) + if (typeof type_func !== 'function') { + throw new TypeError(sub('%r is not callable', type_func)) + } + + if (type_func === FileType) { + throw new TypeError(sub('%r is a FileType class object, instance of it' + + ' must be passed', type_func)) + } + + // raise an error if the metavar does not match the type + if ('_get_formatter' in this) { + try { + this._get_formatter()._format_args(action, undefined) + } catch (err) { + // check for 'invalid nargs value' is an artifact of TypeError and ValueError in js being the same + if (err instanceof TypeError && err.message !== 'invalid nargs value') { + throw new TypeError('length of metavar tuple does not match nargs') + } else { + throw err + } + } + } + + return this._add_action(action) + } + + add_argument_group() { + let group = _ArgumentGroup(this, ...arguments) + this._action_groups.push(group) + return group + } + + add_mutually_exclusive_group() { + // eslint-disable-next-line no-use-before-define + let group = _MutuallyExclusiveGroup(this, ...arguments) + this._mutually_exclusive_groups.push(group) + return group + } + + _add_action(action) { + // resolve any conflicts + this._check_conflict(action) + + // add to actions list + this._actions.push(action) + action.container = this + + // index the action by any option strings it has + for (let option_string of action.option_strings) { + this._option_string_actions[option_string] = action + } + + // set the flag if any option strings look like negative numbers + for (let option_string of action.option_strings) { + if (this._negative_number_matcher.test(option_string)) { + if (!this._has_negative_number_optionals.length) { + this._has_negative_number_optionals.push(true) + } + } + } + + // return the created action + return action + } + + _remove_action(action) { + _array_remove(this._actions, action) + } + + _add_container_actions(container) { + // collect groups by titles + let title_group_map = {} + for (let group of this._action_groups) { + if (group.title in title_group_map) { + let msg = 'cannot merge actions - two groups are named %r' + throw new TypeError(sub(msg, group.title)) + } + title_group_map[group.title] = group + } + + // map each action to its group + let group_map = new Map() + for (let group of container._action_groups) { + + // if a group with the title exists, use that, otherwise + // create a new group matching the container's group + if (!(group.title in title_group_map)) { + title_group_map[group.title] = this.add_argument_group({ + title: group.title, + description: group.description, + conflict_handler: group.conflict_handler + }) + } + + // map the actions to their new group + for (let action of group._group_actions) { + group_map.set(action, title_group_map[group.title]) + } + } + + // add container's mutually exclusive groups + // NOTE: if add_mutually_exclusive_group ever gains title= and + // description= then this code will need to be expanded as above + for (let group of container._mutually_exclusive_groups) { + let mutex_group = this.add_mutually_exclusive_group({ + required: group.required + }) + + // map the actions to their new mutex group + for (let action of group._group_actions) { + group_map.set(action, mutex_group) + } + } + + // add all actions to this container or their group + for (let action of container._actions) { + group_map.get(action)._add_action(action) + } + } + + _get_positional_kwargs() { + let [ + dest, + kwargs + ] = _parse_opts(arguments, { + dest: no_default, + '**kwargs': no_default + }) + + // make sure required is not specified + if ('required' in kwargs) { + let msg = "'required' is an invalid argument for positionals" + throw new TypeError(msg) + } + + // mark positional arguments as required if at least one is + // always required + if (![OPTIONAL, ZERO_OR_MORE].includes(kwargs.nargs)) { + kwargs.required = true + } + if (kwargs.nargs === ZERO_OR_MORE && !('default' in kwargs)) { + kwargs.required = true + } + + // return the keyword arguments with no option strings + return Object.assign(kwargs, { dest, option_strings: [] }) + } + + _get_optional_kwargs() { + let [ + args, + kwargs + ] = _parse_opts(arguments, { + '*args': no_default, + '**kwargs': no_default + }) + + // determine short and long option strings + let option_strings = [] + let long_option_strings = [] + let option_string + for (option_string of args) { + // error on strings that don't start with an appropriate prefix + if (!this.prefix_chars.includes(option_string[0])) { + let args = {option: option_string, + prefix_chars: this.prefix_chars} + let msg = 'invalid option string %(option)r: ' + + 'must start with a character %(prefix_chars)r' + throw new TypeError(sub(msg, args)) + } + + // strings starting with two prefix characters are long options + option_strings.push(option_string) + if (option_string.length > 1 && this.prefix_chars.includes(option_string[1])) { + long_option_strings.push(option_string) + } + } + + // infer destination, '--foo-bar' -> 'foo_bar' and '-x' -> 'x' + let dest = kwargs.dest + delete kwargs.dest + if (dest === undefined) { + let dest_option_string + if (long_option_strings.length) { + dest_option_string = long_option_strings[0] + } else { + dest_option_string = option_strings[0] + } + dest = _string_lstrip(dest_option_string, this.prefix_chars) + if (!dest) { + let msg = 'dest= is required for options like %r' + throw new TypeError(sub(msg, option_string)) + } + dest = dest.replace(/-/g, '_') + } + + // return the updated keyword arguments + return Object.assign(kwargs, { dest, option_strings }) + } + + _pop_action_class(kwargs, default_value = undefined) { + let action = getattr(kwargs, 'action', default_value) + delete kwargs.action + return this._registry_get('action', action, action) + } + + _get_handler() { + // determine function from conflict handler string + let handler_func_name = sub('_handle_conflict_%s', this.conflict_handler) + if (typeof this[handler_func_name] === 'function') { + return this[handler_func_name] + } else { + let msg = 'invalid conflict_resolution value: %r' + throw new TypeError(sub(msg, this.conflict_handler)) + } + } + + _check_conflict(action) { + + // find all options that conflict with this option + let confl_optionals = [] + for (let option_string of action.option_strings) { + if (hasattr(this._option_string_actions, option_string)) { + let confl_optional = this._option_string_actions[option_string] + confl_optionals.push([ option_string, confl_optional ]) + } + } + + // resolve any conflicts + if (confl_optionals.length) { + let conflict_handler = this._get_handler() + conflict_handler.call(this, action, confl_optionals) + } + } + + _handle_conflict_error(action, conflicting_actions) { + let message = conflicting_actions.length === 1 ? + 'conflicting option string: %s' : + 'conflicting option strings: %s' + let conflict_string = conflicting_actions.map(([ option_string/*, action*/ ]) => option_string).join(', ') + throw new ArgumentError(action, sub(message, conflict_string)) + } + + _handle_conflict_resolve(action, conflicting_actions) { + + // remove all conflicting options + for (let [ option_string, action ] of conflicting_actions) { + + // remove the conflicting option + _array_remove(action.option_strings, option_string) + delete this._option_string_actions[option_string] + + // if the option now has no option string, remove it from the + // container holding it + if (!action.option_strings.length) { + action.container._remove_action(action) + } + } + } +})) + + +const _ArgumentGroup = _callable(class _ArgumentGroup extends _ActionsContainer { + + constructor() { + let [ + container, + title, + description, + kwargs + ] = _parse_opts(arguments, { + container: no_default, + title: undefined, + description: undefined, + '**kwargs': no_default + }) + + // add any missing keyword arguments by checking the container + setdefault(kwargs, 'conflict_handler', container.conflict_handler) + setdefault(kwargs, 'prefix_chars', container.prefix_chars) + setdefault(kwargs, 'argument_default', container.argument_default) + super(Object.assign({ description }, kwargs)) + + // group attributes + this.title = title + this._group_actions = [] + + // share most attributes with the container + this._registries = container._registries + this._actions = container._actions + this._option_string_actions = container._option_string_actions + this._defaults = container._defaults + this._has_negative_number_optionals = + container._has_negative_number_optionals + this._mutually_exclusive_groups = container._mutually_exclusive_groups + } + + _add_action(action) { + action = super._add_action(action) + this._group_actions.push(action) + return action + } + + _remove_action(action) { + super._remove_action(action) + _array_remove(this._group_actions, action) + } +}) + + +const _MutuallyExclusiveGroup = _callable(class _MutuallyExclusiveGroup extends _ArgumentGroup { + + constructor() { + let [ + container, + required + ] = _parse_opts(arguments, { + container: no_default, + required: false + }) + + super(container) + this.required = required + this._container = container + } + + _add_action(action) { + if (action.required) { + let msg = 'mutually exclusive arguments must be optional' + throw new TypeError(msg) + } + action = this._container._add_action(action) + this._group_actions.push(action) + return action + } + + _remove_action(action) { + this._container._remove_action(action) + _array_remove(this._group_actions, action) + } +}) + + +const ArgumentParser = _camelcase_alias(_callable(class ArgumentParser extends _AttributeHolder(_ActionsContainer) { + /* + * Object for parsing command line strings into Python objects. + * + * Keyword Arguments: + * - prog -- The name of the program (default: sys.argv[0]) + * - usage -- A usage message (default: auto-generated from arguments) + * - description -- A description of what the program does + * - epilog -- Text following the argument descriptions + * - parents -- Parsers whose arguments should be copied into this one + * - formatter_class -- HelpFormatter class for printing help messages + * - prefix_chars -- Characters that prefix optional arguments + * - fromfile_prefix_chars -- Characters that prefix files containing + * additional arguments + * - argument_default -- The default value for all arguments + * - conflict_handler -- String indicating how to handle conflicts + * - add_help -- Add a -h/-help option + * - allow_abbrev -- Allow long options to be abbreviated unambiguously + * - exit_on_error -- Determines whether or not ArgumentParser exits with + * error info when an error occurs + */ + + constructor() { + let [ + prog, + usage, + description, + epilog, + parents, + formatter_class, + prefix_chars, + fromfile_prefix_chars, + argument_default, + conflict_handler, + add_help, + allow_abbrev, + exit_on_error, + debug, // LEGACY (v1 compatibility), debug mode + version // LEGACY (v1 compatibility), version + ] = _parse_opts(arguments, { + prog: undefined, + usage: undefined, + description: undefined, + epilog: undefined, + parents: [], + formatter_class: HelpFormatter, + prefix_chars: '-', + fromfile_prefix_chars: undefined, + argument_default: undefined, + conflict_handler: 'error', + add_help: true, + allow_abbrev: true, + exit_on_error: true, + debug: undefined, // LEGACY (v1 compatibility), debug mode + version: undefined // LEGACY (v1 compatibility), version + }) + + // LEGACY (v1 compatibility) + if (debug !== undefined) { + deprecate('debug', + 'The "debug" argument to ArgumentParser is deprecated. Please ' + + 'override ArgumentParser.exit function instead.' + ) + } + + if (version !== undefined) { + deprecate('version', + 'The "version" argument to ArgumentParser is deprecated. Please use ' + + "add_argument(..., { action: 'version', version: 'N', ... }) instead." + ) + } + // end + + super({ + description, + prefix_chars, + argument_default, + conflict_handler + }) + + // default setting for prog + if (prog === undefined) { + prog = path.basename(get_argv()[0] || '') + } + + this.prog = prog + this.usage = usage + this.epilog = epilog + this.formatter_class = formatter_class + this.fromfile_prefix_chars = fromfile_prefix_chars + this.add_help = add_help + this.allow_abbrev = allow_abbrev + this.exit_on_error = exit_on_error + // LEGACY (v1 compatibility), debug mode + this.debug = debug + // end + + this._positionals = this.add_argument_group('positional arguments') + this._optionals = this.add_argument_group('optional arguments') + this._subparsers = undefined + + // register types + function identity(string) { + return string + } + this.register('type', undefined, identity) + this.register('type', null, identity) + this.register('type', 'auto', identity) + this.register('type', 'int', function (x) { + let result = Number(x) + if (!Number.isInteger(result)) { + throw new TypeError(sub('could not convert string to int: %r', x)) + } + return result + }) + this.register('type', 'float', function (x) { + let result = Number(x) + if (isNaN(result)) { + throw new TypeError(sub('could not convert string to float: %r', x)) + } + return result + }) + this.register('type', 'str', String) + // LEGACY (v1 compatibility): custom types + this.register('type', 'string', + util.deprecate(String, 'use {type:"str"} or {type:String} instead of {type:"string"}')) + // end + + // add help argument if necessary + // (using explicit default to override global argument_default) + let default_prefix = prefix_chars.includes('-') ? '-' : prefix_chars[0] + if (this.add_help) { + this.add_argument( + default_prefix + 'h', + default_prefix.repeat(2) + 'help', + { + action: 'help', + default: SUPPRESS, + help: 'show this help message and exit' + } + ) + } + // LEGACY (v1 compatibility), version + if (version) { + this.add_argument( + default_prefix + 'v', + default_prefix.repeat(2) + 'version', + { + action: 'version', + default: SUPPRESS, + version: this.version, + help: "show program's version number and exit" + } + ) + } + // end + + // add parent arguments and defaults + for (let parent of parents) { + this._add_container_actions(parent) + Object.assign(this._defaults, parent._defaults) + } + } + + // ======================= + // Pretty __repr__ methods + // ======================= + _get_kwargs() { + let names = [ + 'prog', + 'usage', + 'description', + 'formatter_class', + 'conflict_handler', + 'add_help' + ] + return names.map(name => [ name, getattr(this, name) ]) + } + + // ================================== + // Optional/Positional adding methods + // ================================== + add_subparsers() { + let [ + kwargs + ] = _parse_opts(arguments, { + '**kwargs': no_default + }) + + if (this._subparsers !== undefined) { + this.error('cannot have multiple subparser arguments') + } + + // add the parser class to the arguments if it's not present + setdefault(kwargs, 'parser_class', this.constructor) + + if ('title' in kwargs || 'description' in kwargs) { + let title = getattr(kwargs, 'title', 'subcommands') + let description = getattr(kwargs, 'description', undefined) + delete kwargs.title + delete kwargs.description + this._subparsers = this.add_argument_group(title, description) + } else { + this._subparsers = this._positionals + } + + // prog defaults to the usage message of this parser, skipping + // optional arguments and with no "usage:" prefix + if (kwargs.prog === undefined) { + let formatter = this._get_formatter() + let positionals = this._get_positional_actions() + let groups = this._mutually_exclusive_groups + formatter.add_usage(this.usage, positionals, groups, '') + kwargs.prog = formatter.format_help().trim() + } + + // create the parsers action and add it to the positionals list + let parsers_class = this._pop_action_class(kwargs, 'parsers') + // eslint-disable-next-line new-cap + let action = new parsers_class(Object.assign({ option_strings: [] }, kwargs)) + this._subparsers._add_action(action) + + // return the created parsers action + return action + } + + _add_action(action) { + if (action.option_strings.length) { + this._optionals._add_action(action) + } else { + this._positionals._add_action(action) + } + return action + } + + _get_optional_actions() { + return this._actions.filter(action => action.option_strings.length) + } + + _get_positional_actions() { + return this._actions.filter(action => !action.option_strings.length) + } + + // ===================================== + // Command line argument parsing methods + // ===================================== + parse_args(args = undefined, namespace = undefined) { + let argv + [ args, argv ] = this.parse_known_args(args, namespace) + if (argv && argv.length > 0) { + let msg = 'unrecognized arguments: %s' + this.error(sub(msg, argv.join(' '))) + } + return args + } + + parse_known_args(args = undefined, namespace = undefined) { + if (args === undefined) { + args = get_argv().slice(1) + } + + // default Namespace built from parser defaults + if (namespace === undefined) { + namespace = new Namespace() + } + + // add any action defaults that aren't present + for (let action of this._actions) { + if (action.dest !== SUPPRESS) { + if (!hasattr(namespace, action.dest)) { + if (action.default !== SUPPRESS) { + setattr(namespace, action.dest, action.default) + } + } + } + } + + // add any parser defaults that aren't present + for (let dest of Object.keys(this._defaults)) { + if (!hasattr(namespace, dest)) { + setattr(namespace, dest, this._defaults[dest]) + } + } + + // parse the arguments and exit if there are any errors + if (this.exit_on_error) { + try { + [ namespace, args ] = this._parse_known_args(args, namespace) + } catch (err) { + if (err instanceof ArgumentError) { + this.error(err.message) + } else { + throw err + } + } + } else { + [ namespace, args ] = this._parse_known_args(args, namespace) + } + + if (hasattr(namespace, _UNRECOGNIZED_ARGS_ATTR)) { + args = args.concat(getattr(namespace, _UNRECOGNIZED_ARGS_ATTR)) + delattr(namespace, _UNRECOGNIZED_ARGS_ATTR) + } + + return [ namespace, args ] + } + + _parse_known_args(arg_strings, namespace) { + // replace arg strings that are file references + if (this.fromfile_prefix_chars !== undefined) { + arg_strings = this._read_args_from_files(arg_strings) + } + + // map all mutually exclusive arguments to the other arguments + // they can't occur with + let action_conflicts = new Map() + for (let mutex_group of this._mutually_exclusive_groups) { + let group_actions = mutex_group._group_actions + for (let [ i, mutex_action ] of Object.entries(mutex_group._group_actions)) { + let conflicts = action_conflicts.get(mutex_action) || [] + conflicts = conflicts.concat(group_actions.slice(0, +i)) + conflicts = conflicts.concat(group_actions.slice(+i + 1)) + action_conflicts.set(mutex_action, conflicts) + } + } + + // find all option indices, and determine the arg_string_pattern + // which has an 'O' if there is an option at an index, + // an 'A' if there is an argument, or a '-' if there is a '--' + let option_string_indices = {} + let arg_string_pattern_parts = [] + let arg_strings_iter = Object.entries(arg_strings)[Symbol.iterator]() + for (let [ i, arg_string ] of arg_strings_iter) { + + // all args after -- are non-options + if (arg_string === '--') { + arg_string_pattern_parts.push('-') + for ([ i, arg_string ] of arg_strings_iter) { + arg_string_pattern_parts.push('A') + } + + // otherwise, add the arg to the arg strings + // and note the index if it was an option + } else { + let option_tuple = this._parse_optional(arg_string) + let pattern + if (option_tuple === undefined) { + pattern = 'A' + } else { + option_string_indices[i] = option_tuple + pattern = 'O' + } + arg_string_pattern_parts.push(pattern) + } + } + + // join the pieces together to form the pattern + let arg_strings_pattern = arg_string_pattern_parts.join('') + + // converts arg strings to the appropriate and then takes the action + let seen_actions = new Set() + let seen_non_default_actions = new Set() + let extras + + let take_action = (action, argument_strings, option_string = undefined) => { + seen_actions.add(action) + let argument_values = this._get_values(action, argument_strings) + + // error if this argument is not allowed with other previously + // seen arguments, assuming that actions that use the default + // value don't really count as "present" + if (argument_values !== action.default) { + seen_non_default_actions.add(action) + for (let conflict_action of action_conflicts.get(action) || []) { + if (seen_non_default_actions.has(conflict_action)) { + let msg = 'not allowed with argument %s' + let action_name = _get_action_name(conflict_action) + throw new ArgumentError(action, sub(msg, action_name)) + } + } + } + + // take the action if we didn't receive a SUPPRESS value + // (e.g. from a default) + if (argument_values !== SUPPRESS) { + action(this, namespace, argument_values, option_string) + } + } + + // function to convert arg_strings into an optional action + let consume_optional = start_index => { + + // get the optional identified at this index + let option_tuple = option_string_indices[start_index] + let [ action, option_string, explicit_arg ] = option_tuple + + // identify additional optionals in the same arg string + // (e.g. -xyz is the same as -x -y -z if no args are required) + let action_tuples = [] + let stop + for (;;) { + + // if we found no optional action, skip it + if (action === undefined) { + extras.push(arg_strings[start_index]) + return start_index + 1 + } + + // if there is an explicit argument, try to match the + // optional's string arguments to only this + if (explicit_arg !== undefined) { + let arg_count = this._match_argument(action, 'A') + + // if the action is a single-dash option and takes no + // arguments, try to parse more single-dash options out + // of the tail of the option string + let chars = this.prefix_chars + if (arg_count === 0 && !chars.includes(option_string[1])) { + action_tuples.push([ action, [], option_string ]) + let char = option_string[0] + option_string = char + explicit_arg[0] + let new_explicit_arg = explicit_arg.slice(1) || undefined + let optionals_map = this._option_string_actions + if (hasattr(optionals_map, option_string)) { + action = optionals_map[option_string] + explicit_arg = new_explicit_arg + } else { + let msg = 'ignored explicit argument %r' + throw new ArgumentError(action, sub(msg, explicit_arg)) + } + + // if the action expect exactly one argument, we've + // successfully matched the option; exit the loop + } else if (arg_count === 1) { + stop = start_index + 1 + let args = [ explicit_arg ] + action_tuples.push([ action, args, option_string ]) + break + + // error if a double-dash option did not use the + // explicit argument + } else { + let msg = 'ignored explicit argument %r' + throw new ArgumentError(action, sub(msg, explicit_arg)) + } + + // if there is no explicit argument, try to match the + // optional's string arguments with the following strings + // if successful, exit the loop + } else { + let start = start_index + 1 + let selected_patterns = arg_strings_pattern.slice(start) + let arg_count = this._match_argument(action, selected_patterns) + stop = start + arg_count + let args = arg_strings.slice(start, stop) + action_tuples.push([ action, args, option_string ]) + break + } + } + + // add the Optional to the list and return the index at which + // the Optional's string args stopped + assert(action_tuples.length) + for (let [ action, args, option_string ] of action_tuples) { + take_action(action, args, option_string) + } + return stop + } + + // the list of Positionals left to be parsed; this is modified + // by consume_positionals() + let positionals = this._get_positional_actions() + + // function to convert arg_strings into positional actions + let consume_positionals = start_index => { + // match as many Positionals as possible + let selected_pattern = arg_strings_pattern.slice(start_index) + let arg_counts = this._match_arguments_partial(positionals, selected_pattern) + + // slice off the appropriate arg strings for each Positional + // and add the Positional and its args to the list + for (let i = 0; i < positionals.length && i < arg_counts.length; i++) { + let action = positionals[i] + let arg_count = arg_counts[i] + let args = arg_strings.slice(start_index, start_index + arg_count) + start_index += arg_count + take_action(action, args) + } + + // slice off the Positionals that we just parsed and return the + // index at which the Positionals' string args stopped + positionals = positionals.slice(arg_counts.length) + return start_index + } + + // consume Positionals and Optionals alternately, until we have + // passed the last option string + extras = [] + let start_index = 0 + let max_option_string_index = Math.max(-1, ...Object.keys(option_string_indices).map(Number)) + while (start_index <= max_option_string_index) { + + // consume any Positionals preceding the next option + let next_option_string_index = Math.min( + // eslint-disable-next-line no-loop-func + ...Object.keys(option_string_indices).map(Number).filter(index => index >= start_index) + ) + if (start_index !== next_option_string_index) { + let positionals_end_index = consume_positionals(start_index) + + // only try to parse the next optional if we didn't consume + // the option string during the positionals parsing + if (positionals_end_index > start_index) { + start_index = positionals_end_index + continue + } else { + start_index = positionals_end_index + } + } + + // if we consumed all the positionals we could and we're not + // at the index of an option string, there were extra arguments + if (!(start_index in option_string_indices)) { + let strings = arg_strings.slice(start_index, next_option_string_index) + extras = extras.concat(strings) + start_index = next_option_string_index + } + + // consume the next optional and any arguments for it + start_index = consume_optional(start_index) + } + + // consume any positionals following the last Optional + let stop_index = consume_positionals(start_index) + + // if we didn't consume all the argument strings, there were extras + extras = extras.concat(arg_strings.slice(stop_index)) + + // make sure all required actions were present and also convert + // action defaults which were not given as arguments + let required_actions = [] + for (let action of this._actions) { + if (!seen_actions.has(action)) { + if (action.required) { + required_actions.push(_get_action_name(action)) + } else { + // Convert action default now instead of doing it before + // parsing arguments to avoid calling convert functions + // twice (which may fail) if the argument was given, but + // only if it was defined already in the namespace + if (action.default !== undefined && + typeof action.default === 'string' && + hasattr(namespace, action.dest) && + action.default === getattr(namespace, action.dest)) { + setattr(namespace, action.dest, + this._get_value(action, action.default)) + } + } + } + } + + if (required_actions.length) { + this.error(sub('the following arguments are required: %s', + required_actions.join(', '))) + } + + // make sure all required groups had one option present + for (let group of this._mutually_exclusive_groups) { + if (group.required) { + let no_actions_used = true + for (let action of group._group_actions) { + if (seen_non_default_actions.has(action)) { + no_actions_used = false + break + } + } + + // if no actions were used, report the error + if (no_actions_used) { + let names = group._group_actions + .filter(action => action.help !== SUPPRESS) + .map(action => _get_action_name(action)) + let msg = 'one of the arguments %s is required' + this.error(sub(msg, names.join(' '))) + } + } + } + + // return the updated namespace and the extra arguments + return [ namespace, extras ] + } + + _read_args_from_files(arg_strings) { + // expand arguments referencing files + let new_arg_strings = [] + for (let arg_string of arg_strings) { + + // for regular arguments, just add them back into the list + if (!arg_string || !this.fromfile_prefix_chars.includes(arg_string[0])) { + new_arg_strings.push(arg_string) + + // replace arguments referencing files with the file content + } else { + try { + let args_file = fs.readFileSync(arg_string.slice(1), 'utf8') + let arg_strings = [] + for (let arg_line of splitlines(args_file)) { + for (let arg of this.convert_arg_line_to_args(arg_line)) { + arg_strings.push(arg) + } + } + arg_strings = this._read_args_from_files(arg_strings) + new_arg_strings = new_arg_strings.concat(arg_strings) + } catch (err) { + this.error(err.message) + } + } + } + + // return the modified argument list + return new_arg_strings + } + + convert_arg_line_to_args(arg_line) { + return [arg_line] + } + + _match_argument(action, arg_strings_pattern) { + // match the pattern for this action to the arg strings + let nargs_pattern = this._get_nargs_pattern(action) + let match = arg_strings_pattern.match(new RegExp('^' + nargs_pattern)) + + // raise an exception if we weren't able to find a match + if (match === null) { + let nargs_errors = { + undefined: 'expected one argument', + [OPTIONAL]: 'expected at most one argument', + [ONE_OR_MORE]: 'expected at least one argument' + } + let msg = nargs_errors[action.nargs] + if (msg === undefined) { + msg = sub(action.nargs === 1 ? 'expected %s argument' : 'expected %s arguments', action.nargs) + } + throw new ArgumentError(action, msg) + } + + // return the number of arguments matched + return match[1].length + } + + _match_arguments_partial(actions, arg_strings_pattern) { + // progressively shorten the actions list by slicing off the + // final actions until we find a match + let result = [] + for (let i of range(actions.length, 0, -1)) { + let actions_slice = actions.slice(0, i) + let pattern = actions_slice.map(action => this._get_nargs_pattern(action)).join('') + let match = arg_strings_pattern.match(new RegExp('^' + pattern)) + if (match !== null) { + result = result.concat(match.slice(1).map(string => string.length)) + break + } + } + + // return the list of arg string counts + return result + } + + _parse_optional(arg_string) { + // if it's an empty string, it was meant to be a positional + if (!arg_string) { + return undefined + } + + // if it doesn't start with a prefix, it was meant to be positional + if (!this.prefix_chars.includes(arg_string[0])) { + return undefined + } + + // if the option string is present in the parser, return the action + if (arg_string in this._option_string_actions) { + let action = this._option_string_actions[arg_string] + return [ action, arg_string, undefined ] + } + + // if it's just a single character, it was meant to be positional + if (arg_string.length === 1) { + return undefined + } + + // if the option string before the "=" is present, return the action + if (arg_string.includes('=')) { + let [ option_string, explicit_arg ] = _string_split(arg_string, '=', 1) + if (option_string in this._option_string_actions) { + let action = this._option_string_actions[option_string] + return [ action, option_string, explicit_arg ] + } + } + + // search through all possible prefixes of the option string + // and all actions in the parser for possible interpretations + let option_tuples = this._get_option_tuples(arg_string) + + // if multiple actions match, the option string was ambiguous + if (option_tuples.length > 1) { + let options = option_tuples.map(([ /*action*/, option_string/*, explicit_arg*/ ]) => option_string).join(', ') + let args = {option: arg_string, matches: options} + let msg = 'ambiguous option: %(option)s could match %(matches)s' + this.error(sub(msg, args)) + + // if exactly one action matched, this segmentation is good, + // so return the parsed action + } else if (option_tuples.length === 1) { + let [ option_tuple ] = option_tuples + return option_tuple + } + + // if it was not found as an option, but it looks like a negative + // number, it was meant to be positional + // unless there are negative-number-like options + if (this._negative_number_matcher.test(arg_string)) { + if (!this._has_negative_number_optionals.length) { + return undefined + } + } + + // if it contains a space, it was meant to be a positional + if (arg_string.includes(' ')) { + return undefined + } + + // it was meant to be an optional but there is no such option + // in this parser (though it might be a valid option in a subparser) + return [ undefined, arg_string, undefined ] + } + + _get_option_tuples(option_string) { + let result = [] + + // option strings starting with two prefix characters are only + // split at the '=' + let chars = this.prefix_chars + if (chars.includes(option_string[0]) && chars.includes(option_string[1])) { + if (this.allow_abbrev) { + let option_prefix, explicit_arg + if (option_string.includes('=')) { + [ option_prefix, explicit_arg ] = _string_split(option_string, '=', 1) + } else { + option_prefix = option_string + explicit_arg = undefined + } + for (let option_string of Object.keys(this._option_string_actions)) { + if (option_string.startsWith(option_prefix)) { + let action = this._option_string_actions[option_string] + let tup = [ action, option_string, explicit_arg ] + result.push(tup) + } + } + } + + // single character options can be concatenated with their arguments + // but multiple character options always have to have their argument + // separate + } else if (chars.includes(option_string[0]) && !chars.includes(option_string[1])) { + let option_prefix = option_string + let explicit_arg = undefined + let short_option_prefix = option_string.slice(0, 2) + let short_explicit_arg = option_string.slice(2) + + for (let option_string of Object.keys(this._option_string_actions)) { + if (option_string === short_option_prefix) { + let action = this._option_string_actions[option_string] + let tup = [ action, option_string, short_explicit_arg ] + result.push(tup) + } else if (option_string.startsWith(option_prefix)) { + let action = this._option_string_actions[option_string] + let tup = [ action, option_string, explicit_arg ] + result.push(tup) + } + } + + // shouldn't ever get here + } else { + this.error(sub('unexpected option string: %s', option_string)) + } + + // return the collected option tuples + return result + } + + _get_nargs_pattern(action) { + // in all examples below, we have to allow for '--' args + // which are represented as '-' in the pattern + let nargs = action.nargs + let nargs_pattern + + // the default (None) is assumed to be a single argument + if (nargs === undefined) { + nargs_pattern = '(-*A-*)' + + // allow zero or one arguments + } else if (nargs === OPTIONAL) { + nargs_pattern = '(-*A?-*)' + + // allow zero or more arguments + } else if (nargs === ZERO_OR_MORE) { + nargs_pattern = '(-*[A-]*)' + + // allow one or more arguments + } else if (nargs === ONE_OR_MORE) { + nargs_pattern = '(-*A[A-]*)' + + // allow any number of options or arguments + } else if (nargs === REMAINDER) { + nargs_pattern = '([-AO]*)' + + // allow one argument followed by any number of options or arguments + } else if (nargs === PARSER) { + nargs_pattern = '(-*A[-AO]*)' + + // suppress action, like nargs=0 + } else if (nargs === SUPPRESS) { + nargs_pattern = '(-*-*)' + + // all others should be integers + } else { + nargs_pattern = sub('(-*%s-*)', 'A'.repeat(nargs).split('').join('-*')) + } + + // if this is an optional action, -- is not allowed + if (action.option_strings.length) { + nargs_pattern = nargs_pattern.replace(/-\*/g, '') + nargs_pattern = nargs_pattern.replace(/-/g, '') + } + + // return the pattern + return nargs_pattern + } + + // ======================== + // Alt command line argument parsing, allowing free intermix + // ======================== + + parse_intermixed_args(args = undefined, namespace = undefined) { + let argv + [ args, argv ] = this.parse_known_intermixed_args(args, namespace) + if (argv.length) { + let msg = 'unrecognized arguments: %s' + this.error(sub(msg, argv.join(' '))) + } + return args + } + + parse_known_intermixed_args(args = undefined, namespace = undefined) { + // returns a namespace and list of extras + // + // positional can be freely intermixed with optionals. optionals are + // first parsed with all positional arguments deactivated. The 'extras' + // are then parsed. If the parser definition is incompatible with the + // intermixed assumptions (e.g. use of REMAINDER, subparsers) a + // TypeError is raised. + // + // positionals are 'deactivated' by setting nargs and default to + // SUPPRESS. This blocks the addition of that positional to the + // namespace + + let extras + let positionals = this._get_positional_actions() + let a = positionals.filter(action => [ PARSER, REMAINDER ].includes(action.nargs)) + if (a.length) { + throw new TypeError(sub('parse_intermixed_args: positional arg' + + ' with nargs=%s', a[0].nargs)) + } + + for (let group of this._mutually_exclusive_groups) { + for (let action of group._group_actions) { + if (positionals.includes(action)) { + throw new TypeError('parse_intermixed_args: positional in' + + ' mutuallyExclusiveGroup') + } + } + } + + let save_usage + try { + save_usage = this.usage + let remaining_args + try { + if (this.usage === undefined) { + // capture the full usage for use in error messages + this.usage = this.format_usage().slice(7) + } + for (let action of positionals) { + // deactivate positionals + action.save_nargs = action.nargs + // action.nargs = 0 + action.nargs = SUPPRESS + action.save_default = action.default + action.default = SUPPRESS + } + [ namespace, remaining_args ] = this.parse_known_args(args, + namespace) + for (let action of positionals) { + // remove the empty positional values from namespace + let attr = getattr(namespace, action.dest) + if (Array.isArray(attr) && attr.length === 0) { + // eslint-disable-next-line no-console + console.warn(sub('Do not expect %s in %s', action.dest, namespace)) + delattr(namespace, action.dest) + } + } + } finally { + // restore nargs and usage before exiting + for (let action of positionals) { + action.nargs = action.save_nargs + action.default = action.save_default + } + } + let optionals = this._get_optional_actions() + try { + // parse positionals. optionals aren't normally required, but + // they could be, so make sure they aren't. + for (let action of optionals) { + action.save_required = action.required + action.required = false + } + for (let group of this._mutually_exclusive_groups) { + group.save_required = group.required + group.required = false + } + [ namespace, extras ] = this.parse_known_args(remaining_args, + namespace) + } finally { + // restore parser values before exiting + for (let action of optionals) { + action.required = action.save_required + } + for (let group of this._mutually_exclusive_groups) { + group.required = group.save_required + } + } + } finally { + this.usage = save_usage + } + return [ namespace, extras ] + } + + // ======================== + // Value conversion methods + // ======================== + _get_values(action, arg_strings) { + // for everything but PARSER, REMAINDER args, strip out first '--' + if (![PARSER, REMAINDER].includes(action.nargs)) { + try { + _array_remove(arg_strings, '--') + } catch (err) {} + } + + let value + // optional argument produces a default when not present + if (!arg_strings.length && action.nargs === OPTIONAL) { + if (action.option_strings.length) { + value = action.const + } else { + value = action.default + } + if (typeof value === 'string') { + value = this._get_value(action, value) + this._check_value(action, value) + } + + // when nargs='*' on a positional, if there were no command-line + // args, use the default if it is anything other than None + } else if (!arg_strings.length && action.nargs === ZERO_OR_MORE && + !action.option_strings.length) { + if (action.default !== undefined) { + value = action.default + } else { + value = arg_strings + } + this._check_value(action, value) + + // single argument or optional argument produces a single value + } else if (arg_strings.length === 1 && [undefined, OPTIONAL].includes(action.nargs)) { + let arg_string = arg_strings[0] + value = this._get_value(action, arg_string) + this._check_value(action, value) + + // REMAINDER arguments convert all values, checking none + } else if (action.nargs === REMAINDER) { + value = arg_strings.map(v => this._get_value(action, v)) + + // PARSER arguments convert all values, but check only the first + } else if (action.nargs === PARSER) { + value = arg_strings.map(v => this._get_value(action, v)) + this._check_value(action, value[0]) + + // SUPPRESS argument does not put anything in the namespace + } else if (action.nargs === SUPPRESS) { + value = SUPPRESS + + // all other types of nargs produce a list + } else { + value = arg_strings.map(v => this._get_value(action, v)) + for (let v of value) { + this._check_value(action, v) + } + } + + // return the converted value + return value + } + + _get_value(action, arg_string) { + let type_func = this._registry_get('type', action.type, action.type) + if (typeof type_func !== 'function') { + let msg = '%r is not callable' + throw new ArgumentError(action, sub(msg, type_func)) + } + + // convert the value to the appropriate type + let result + try { + try { + result = type_func(arg_string) + } catch (err) { + // Dear TC39, why would you ever consider making es6 classes not callable? + // We had one universal interface, [[Call]], which worked for anything + // (with familiar this-instanceof guard for classes). Now we have two. + if (err instanceof TypeError && + /Class constructor .* cannot be invoked without 'new'/.test(err.message)) { + // eslint-disable-next-line new-cap + result = new type_func(arg_string) + } else { + throw err + } + } + + } catch (err) { + // ArgumentTypeErrors indicate errors + if (err instanceof ArgumentTypeError) { + //let name = getattr(action.type, 'name', repr(action.type)) + let msg = err.message + throw new ArgumentError(action, msg) + + // TypeErrors or ValueErrors also indicate errors + } else if (err instanceof TypeError) { + let name = getattr(action.type, 'name', repr(action.type)) + let args = {type: name, value: arg_string} + let msg = 'invalid %(type)s value: %(value)r' + throw new ArgumentError(action, sub(msg, args)) + } else { + throw err + } + } + + // return the converted value + return result + } + + _check_value(action, value) { + // converted value must be one of the choices (if specified) + if (action.choices !== undefined && !_choices_to_array(action.choices).includes(value)) { + let args = {value, + choices: _choices_to_array(action.choices).map(repr).join(', ')} + let msg = 'invalid choice: %(value)r (choose from %(choices)s)' + throw new ArgumentError(action, sub(msg, args)) + } + } + + // ======================= + // Help-formatting methods + // ======================= + format_usage() { + let formatter = this._get_formatter() + formatter.add_usage(this.usage, this._actions, + this._mutually_exclusive_groups) + return formatter.format_help() + } + + format_help() { + let formatter = this._get_formatter() + + // usage + formatter.add_usage(this.usage, this._actions, + this._mutually_exclusive_groups) + + // description + formatter.add_text(this.description) + + // positionals, optionals and user-defined groups + for (let action_group of this._action_groups) { + formatter.start_section(action_group.title) + formatter.add_text(action_group.description) + formatter.add_arguments(action_group._group_actions) + formatter.end_section() + } + + // epilog + formatter.add_text(this.epilog) + + // determine help from format above + return formatter.format_help() + } + + _get_formatter() { + // eslint-disable-next-line new-cap + return new this.formatter_class({ prog: this.prog }) + } + + // ===================== + // Help-printing methods + // ===================== + print_usage(file = undefined) { + if (file === undefined) file = process.stdout + this._print_message(this.format_usage(), file) + } + + print_help(file = undefined) { + if (file === undefined) file = process.stdout + this._print_message(this.format_help(), file) + } + + _print_message(message, file = undefined) { + if (message) { + if (file === undefined) file = process.stderr + file.write(message) + } + } + + // =============== + // Exiting methods + // =============== + exit(status = 0, message = undefined) { + if (message) { + this._print_message(message, process.stderr) + } + process.exit(status) + } + + error(message) { + /* + * error(message: string) + * + * Prints a usage message incorporating the message to stderr and + * exits. + * + * If you override this in a subclass, it should not return -- it + * should either exit or raise an exception. + */ + + // LEGACY (v1 compatibility), debug mode + if (this.debug === true) throw new Error(message) + // end + this.print_usage(process.stderr) + let args = {prog: this.prog, message: message} + this.exit(2, sub('%(prog)s: error: %(message)s\n', args)) + } +})) + + +module.exports = { + ArgumentParser, + ArgumentError, + ArgumentTypeError, + BooleanOptionalAction, + FileType, + HelpFormatter, + ArgumentDefaultsHelpFormatter, + RawDescriptionHelpFormatter, + RawTextHelpFormatter, + MetavarTypeHelpFormatter, + Namespace, + Action, + ONE_OR_MORE, + OPTIONAL, + PARSER, + REMAINDER, + SUPPRESS, + ZERO_OR_MORE +} + +// LEGACY (v1 compatibility), Const alias +Object.defineProperty(module.exports, 'Const', { + get() { + let result = {} + Object.entries({ ONE_OR_MORE, OPTIONAL, PARSER, REMAINDER, SUPPRESS, ZERO_OR_MORE }).forEach(([ n, v ]) => { + Object.defineProperty(result, n, { + get() { + deprecate(n, sub('use argparse.%s instead of argparse.Const.%s', n, n)) + return v + } + }) + }) + Object.entries({ _UNRECOGNIZED_ARGS_ATTR }).forEach(([ n, v ]) => { + Object.defineProperty(result, n, { + get() { + deprecate(n, sub('argparse.Const.%s is an internal symbol and will no longer be available', n)) + return v + } + }) + }) + return result + }, + enumerable: false +}) +// end diff --git a/frontend/node_modules/markdown-it/node_modules/argparse/lib/sub.js b/frontend/node_modules/markdown-it/node_modules/argparse/lib/sub.js new file mode 100644 index 0000000..e3eb321 --- /dev/null +++ b/frontend/node_modules/markdown-it/node_modules/argparse/lib/sub.js @@ -0,0 +1,67 @@ +// Limited implementation of python % string operator, supports only %s and %r for now +// (other formats are not used here, but may appear in custom templates) + +'use strict' + +const { inspect } = require('util') + + +module.exports = function sub(pattern, ...values) { + let regex = /%(?:(%)|(-)?(\*)?(?:\((\w+)\))?([A-Za-z]))/g + + let result = pattern.replace(regex, function (_, is_literal, is_left_align, is_padded, name, format) { + if (is_literal) return '%' + + let padded_count = 0 + if (is_padded) { + if (values.length === 0) throw new TypeError('not enough arguments for format string') + padded_count = values.shift() + if (!Number.isInteger(padded_count)) throw new TypeError('* wants int') + } + + let str + if (name !== undefined) { + let dict = values[0] + if (typeof dict !== 'object' || dict === null) throw new TypeError('format requires a mapping') + if (!(name in dict)) throw new TypeError(`no such key: '${name}'`) + str = dict[name] + } else { + if (values.length === 0) throw new TypeError('not enough arguments for format string') + str = values.shift() + } + + switch (format) { + case 's': + str = String(str) + break + case 'r': + str = inspect(str) + break + case 'd': + case 'i': + if (typeof str !== 'number') { + throw new TypeError(`%${format} format: a number is required, not ${typeof str}`) + } + str = String(str.toFixed(0)) + break + default: + throw new TypeError(`unsupported format character '${format}'`) + } + + if (padded_count > 0) { + return is_left_align ? str.padEnd(padded_count) : str.padStart(padded_count) + } else { + return str + } + }) + + if (values.length) { + if (values.length === 1 && typeof values[0] === 'object' && values[0] !== null) { + // mapping + } else { + throw new TypeError('not all arguments converted during string formatting') + } + } + + return result +} diff --git a/frontend/node_modules/markdown-it/node_modules/argparse/lib/textwrap.js b/frontend/node_modules/markdown-it/node_modules/argparse/lib/textwrap.js new file mode 100644 index 0000000..23d51cd --- /dev/null +++ b/frontend/node_modules/markdown-it/node_modules/argparse/lib/textwrap.js @@ -0,0 +1,440 @@ +// Partial port of python's argparse module, version 3.9.0 (only wrap and fill functions): +// https://github.com/python/cpython/blob/v3.9.0b4/Lib/textwrap.py + +'use strict' + +/* + * Text wrapping and filling. + */ + +// Copyright (C) 1999-2001 Gregory P. Ward. +// Copyright (C) 2002, 2003 Python Software Foundation. +// Copyright (C) 2020 argparse.js authors +// Originally written by Greg Ward + +// Hardcode the recognized whitespace characters to the US-ASCII +// whitespace characters. The main reason for doing this is that +// some Unicode spaces (like \u00a0) are non-breaking whitespaces. +// +// This less funky little regex just split on recognized spaces. E.g. +// "Hello there -- you goof-ball, use the -b option!" +// splits into +// Hello/ /there/ /--/ /you/ /goof-ball,/ /use/ /the/ /-b/ /option!/ +const wordsep_simple_re = /([\t\n\x0b\x0c\r ]+)/ + +class TextWrapper { + /* + * Object for wrapping/filling text. The public interface consists of + * the wrap() and fill() methods; the other methods are just there for + * subclasses to override in order to tweak the default behaviour. + * If you want to completely replace the main wrapping algorithm, + * you'll probably have to override _wrap_chunks(). + * + * Several instance attributes control various aspects of wrapping: + * width (default: 70) + * the maximum width of wrapped lines (unless break_long_words + * is false) + * initial_indent (default: "") + * string that will be prepended to the first line of wrapped + * output. Counts towards the line's width. + * subsequent_indent (default: "") + * string that will be prepended to all lines save the first + * of wrapped output; also counts towards each line's width. + * expand_tabs (default: true) + * Expand tabs in input text to spaces before further processing. + * Each tab will become 0 .. 'tabsize' spaces, depending on its position + * in its line. If false, each tab is treated as a single character. + * tabsize (default: 8) + * Expand tabs in input text to 0 .. 'tabsize' spaces, unless + * 'expand_tabs' is false. + * replace_whitespace (default: true) + * Replace all whitespace characters in the input text by spaces + * after tab expansion. Note that if expand_tabs is false and + * replace_whitespace is true, every tab will be converted to a + * single space! + * fix_sentence_endings (default: false) + * Ensure that sentence-ending punctuation is always followed + * by two spaces. Off by default because the algorithm is + * (unavoidably) imperfect. + * break_long_words (default: true) + * Break words longer than 'width'. If false, those words will not + * be broken, and some lines might be longer than 'width'. + * break_on_hyphens (default: true) + * Allow breaking hyphenated words. If true, wrapping will occur + * preferably on whitespaces and right after hyphens part of + * compound words. + * drop_whitespace (default: true) + * Drop leading and trailing whitespace from lines. + * max_lines (default: None) + * Truncate wrapped lines. + * placeholder (default: ' [...]') + * Append to the last line of truncated text. + */ + + constructor(options = {}) { + let { + width = 70, + initial_indent = '', + subsequent_indent = '', + expand_tabs = true, + replace_whitespace = true, + fix_sentence_endings = false, + break_long_words = true, + drop_whitespace = true, + break_on_hyphens = true, + tabsize = 8, + max_lines = undefined, + placeholder=' [...]' + } = options + + this.width = width + this.initial_indent = initial_indent + this.subsequent_indent = subsequent_indent + this.expand_tabs = expand_tabs + this.replace_whitespace = replace_whitespace + this.fix_sentence_endings = fix_sentence_endings + this.break_long_words = break_long_words + this.drop_whitespace = drop_whitespace + this.break_on_hyphens = break_on_hyphens + this.tabsize = tabsize + this.max_lines = max_lines + this.placeholder = placeholder + } + + + // -- Private methods ----------------------------------------------- + // (possibly useful for subclasses to override) + + _munge_whitespace(text) { + /* + * _munge_whitespace(text : string) -> string + * + * Munge whitespace in text: expand tabs and convert all other + * whitespace characters to spaces. Eg. " foo\\tbar\\n\\nbaz" + * becomes " foo bar baz". + */ + if (this.expand_tabs) { + text = text.replace(/\t/g, ' '.repeat(this.tabsize)) // not strictly correct in js + } + if (this.replace_whitespace) { + text = text.replace(/[\t\n\x0b\x0c\r]/g, ' ') + } + return text + } + + _split(text) { + /* + * _split(text : string) -> [string] + * + * Split the text to wrap into indivisible chunks. Chunks are + * not quite the same as words; see _wrap_chunks() for full + * details. As an example, the text + * Look, goof-ball -- use the -b option! + * breaks into the following chunks: + * 'Look,', ' ', 'goof-', 'ball', ' ', '--', ' ', + * 'use', ' ', 'the', ' ', '-b', ' ', 'option!' + * if break_on_hyphens is True, or in: + * 'Look,', ' ', 'goof-ball', ' ', '--', ' ', + * 'use', ' ', 'the', ' ', '-b', ' ', option!' + * otherwise. + */ + let chunks = text.split(wordsep_simple_re) + chunks = chunks.filter(Boolean) + return chunks + } + + _handle_long_word(reversed_chunks, cur_line, cur_len, width) { + /* + * _handle_long_word(chunks : [string], + * cur_line : [string], + * cur_len : int, width : int) + * + * Handle a chunk of text (most likely a word, not whitespace) that + * is too long to fit in any line. + */ + // Figure out when indent is larger than the specified width, and make + // sure at least one character is stripped off on every pass + let space_left + if (width < 1) { + space_left = 1 + } else { + space_left = width - cur_len + } + + // If we're allowed to break long words, then do so: put as much + // of the next chunk onto the current line as will fit. + if (this.break_long_words) { + cur_line.push(reversed_chunks[reversed_chunks.length - 1].slice(0, space_left)) + reversed_chunks[reversed_chunks.length - 1] = reversed_chunks[reversed_chunks.length - 1].slice(space_left) + + // Otherwise, we have to preserve the long word intact. Only add + // it to the current line if there's nothing already there -- + // that minimizes how much we violate the width constraint. + } else if (!cur_line) { + cur_line.push(...reversed_chunks.pop()) + } + + // If we're not allowed to break long words, and there's already + // text on the current line, do nothing. Next time through the + // main loop of _wrap_chunks(), we'll wind up here again, but + // cur_len will be zero, so the next line will be entirely + // devoted to the long word that we can't handle right now. + } + + _wrap_chunks(chunks) { + /* + * _wrap_chunks(chunks : [string]) -> [string] + * + * Wrap a sequence of text chunks and return a list of lines of + * length 'self.width' or less. (If 'break_long_words' is false, + * some lines may be longer than this.) Chunks correspond roughly + * to words and the whitespace between them: each chunk is + * indivisible (modulo 'break_long_words'), but a line break can + * come between any two chunks. Chunks should not have internal + * whitespace; ie. a chunk is either all whitespace or a "word". + * Whitespace chunks will be removed from the beginning and end of + * lines, but apart from that whitespace is preserved. + */ + let lines = [] + let indent + if (this.width <= 0) { + throw Error(`invalid width ${this.width} (must be > 0)`) + } + if (this.max_lines !== undefined) { + if (this.max_lines > 1) { + indent = this.subsequent_indent + } else { + indent = this.initial_indent + } + if (indent.length + this.placeholder.trimStart().length > this.width) { + throw Error('placeholder too large for max width') + } + } + + // Arrange in reverse order so items can be efficiently popped + // from a stack of chucks. + chunks = chunks.reverse() + + while (chunks.length > 0) { + + // Start the list of chunks that will make up the current line. + // cur_len is just the length of all the chunks in cur_line. + let cur_line = [] + let cur_len = 0 + + // Figure out which static string will prefix this line. + let indent + if (lines) { + indent = this.subsequent_indent + } else { + indent = this.initial_indent + } + + // Maximum width for this line. + let width = this.width - indent.length + + // First chunk on line is whitespace -- drop it, unless this + // is the very beginning of the text (ie. no lines started yet). + if (this.drop_whitespace && chunks[chunks.length - 1].trim() === '' && lines.length > 0) { + chunks.pop() + } + + while (chunks.length > 0) { + let l = chunks[chunks.length - 1].length + + // Can at least squeeze this chunk onto the current line. + if (cur_len + l <= width) { + cur_line.push(chunks.pop()) + cur_len += l + + // Nope, this line is full. + } else { + break + } + } + + // The current line is full, and the next chunk is too big to + // fit on *any* line (not just this one). + if (chunks.length && chunks[chunks.length - 1].length > width) { + this._handle_long_word(chunks, cur_line, cur_len, width) + cur_len = cur_line.map(l => l.length).reduce((a, b) => a + b, 0) + } + + // If the last chunk on this line is all whitespace, drop it. + if (this.drop_whitespace && cur_line.length > 0 && cur_line[cur_line.length - 1].trim() === '') { + cur_len -= cur_line[cur_line.length - 1].length + cur_line.pop() + } + + if (cur_line) { + if (this.max_lines === undefined || + lines.length + 1 < this.max_lines || + (chunks.length === 0 || + this.drop_whitespace && + chunks.length === 1 && + !chunks[0].trim()) && cur_len <= width) { + // Convert current line back to a string and store it in + // list of all lines (return value). + lines.push(indent + cur_line.join('')) + } else { + let had_break = false + while (cur_line) { + if (cur_line[cur_line.length - 1].trim() && + cur_len + this.placeholder.length <= width) { + cur_line.push(this.placeholder) + lines.push(indent + cur_line.join('')) + had_break = true + break + } + cur_len -= cur_line[-1].length + cur_line.pop() + } + if (!had_break) { + if (lines) { + let prev_line = lines[lines.length - 1].trimEnd() + if (prev_line.length + this.placeholder.length <= + this.width) { + lines[lines.length - 1] = prev_line + this.placeholder + break + } + } + lines.push(indent + this.placeholder.lstrip()) + } + break + } + } + } + + return lines + } + + _split_chunks(text) { + text = this._munge_whitespace(text) + return this._split(text) + } + + // -- Public interface ---------------------------------------------- + + wrap(text) { + /* + * wrap(text : string) -> [string] + * + * Reformat the single paragraph in 'text' so it fits in lines of + * no more than 'self.width' columns, and return a list of wrapped + * lines. Tabs in 'text' are expanded with string.expandtabs(), + * and all other whitespace characters (including newline) are + * converted to space. + */ + let chunks = this._split_chunks(text) + // not implemented in js + //if (this.fix_sentence_endings) { + // this._fix_sentence_endings(chunks) + //} + return this._wrap_chunks(chunks) + } + + fill(text) { + /* + * fill(text : string) -> string + * + * Reformat the single paragraph in 'text' to fit in lines of no + * more than 'self.width' columns, and return a new string + * containing the entire wrapped paragraph. + */ + return this.wrap(text).join('\n') + } +} + + +// -- Convenience interface --------------------------------------------- + +function wrap(text, options = {}) { + /* + * Wrap a single paragraph of text, returning a list of wrapped lines. + * + * Reformat the single paragraph in 'text' so it fits in lines of no + * more than 'width' columns, and return a list of wrapped lines. By + * default, tabs in 'text' are expanded with string.expandtabs(), and + * all other whitespace characters (including newline) are converted to + * space. See TextWrapper class for available keyword args to customize + * wrapping behaviour. + */ + let { width = 70, ...kwargs } = options + let w = new TextWrapper(Object.assign({ width }, kwargs)) + return w.wrap(text) +} + +function fill(text, options = {}) { + /* + * Fill a single paragraph of text, returning a new string. + * + * Reformat the single paragraph in 'text' to fit in lines of no more + * than 'width' columns, and return a new string containing the entire + * wrapped paragraph. As with wrap(), tabs are expanded and other + * whitespace characters converted to space. See TextWrapper class for + * available keyword args to customize wrapping behaviour. + */ + let { width = 70, ...kwargs } = options + let w = new TextWrapper(Object.assign({ width }, kwargs)) + return w.fill(text) +} + +// -- Loosely related functionality ------------------------------------- + +let _whitespace_only_re = /^[ \t]+$/mg +let _leading_whitespace_re = /(^[ \t]*)(?:[^ \t\n])/mg + +function dedent(text) { + /* + * Remove any common leading whitespace from every line in `text`. + * + * This can be used to make triple-quoted strings line up with the left + * edge of the display, while still presenting them in the source code + * in indented form. + * + * Note that tabs and spaces are both treated as whitespace, but they + * are not equal: the lines " hello" and "\\thello" are + * considered to have no common leading whitespace. + * + * Entirely blank lines are normalized to a newline character. + */ + // Look for the longest leading string of spaces and tabs common to + // all lines. + let margin = undefined + text = text.replace(_whitespace_only_re, '') + let indents = text.match(_leading_whitespace_re) || [] + for (let indent of indents) { + indent = indent.slice(0, -1) + + if (margin === undefined) { + margin = indent + + // Current line more deeply indented than previous winner: + // no change (previous winner is still on top). + } else if (indent.startsWith(margin)) { + // pass + + // Current line consistent with and no deeper than previous winner: + // it's the new winner. + } else if (margin.startsWith(indent)) { + margin = indent + + // Find the largest common whitespace between current line and previous + // winner. + } else { + for (let i = 0; i < margin.length && i < indent.length; i++) { + if (margin[i] !== indent[i]) { + margin = margin.slice(0, i) + break + } + } + } + } + + if (margin) { + text = text.replace(new RegExp('^' + margin, 'mg'), '') + } + return text +} + +module.exports = { wrap, fill, dedent } diff --git a/frontend/node_modules/markdown-it/node_modules/argparse/package.json b/frontend/node_modules/markdown-it/node_modules/argparse/package.json new file mode 100644 index 0000000..647d2af --- /dev/null +++ b/frontend/node_modules/markdown-it/node_modules/argparse/package.json @@ -0,0 +1,31 @@ +{ + "name": "argparse", + "description": "CLI arguments parser. Native port of python's argparse.", + "version": "2.0.1", + "keywords": [ + "cli", + "parser", + "argparse", + "option", + "args" + ], + "main": "argparse.js", + "files": [ + "argparse.js", + "lib/" + ], + "license": "Python-2.0", + "repository": "nodeca/argparse", + "scripts": { + "lint": "eslint .", + "test": "npm run lint && nyc mocha", + "coverage": "npm run test && nyc report --reporter html" + }, + "devDependencies": { + "@babel/eslint-parser": "^7.11.0", + "@babel/plugin-syntax-class-properties": "^7.10.4", + "eslint": "^7.5.0", + "mocha": "^8.0.1", + "nyc": "^15.1.0" + } +} diff --git a/frontend/node_modules/markdown-it/package.json b/frontend/node_modules/markdown-it/package.json new file mode 100644 index 0000000..4d55a3e --- /dev/null +++ b/frontend/node_modules/markdown-it/package.json @@ -0,0 +1,92 @@ +{ + "name": "markdown-it", + "version": "14.1.0", + "description": "Markdown-it - modern pluggable markdown parser.", + "keywords": [ + "markdown", + "parser", + "commonmark", + "markdown-it", + "markdown-it-plugin" + ], + "repository": "markdown-it/markdown-it", + "license": "MIT", + "main": "dist/index.cjs.js", + "module": "index.mjs", + "exports": { + ".": { + "import": "./index.mjs", + "require": "./dist/index.cjs.js" + }, + "./*": { + "require": "./*", + "import": "./*" + } + }, + "bin": { + "markdown-it": "bin/markdown-it.mjs" + }, + "scripts": { + "lint": "eslint .", + "test": "npm run lint && CJS_ONLY=1 npm run build && c8 --exclude dist --exclude test -r text -r html -r lcov mocha && node support/specsplit.mjs", + "doc": "node support/build_doc.mjs", + "gh-doc": "npm run doc && gh-pages -d apidoc -f", + "demo": "npm run lint && node support/build_demo.mjs", + "gh-demo": "npm run demo && gh-pages -d demo -f -b master -r git@github.com:markdown-it/markdown-it.github.io.git", + "build": "rollup -c support/rollup.config.mjs", + "benchmark-deps": "npm install --prefix benchmark/extra/ -g marked@0.3.6 commonmark@0.26.0 markdown-it/markdown-it.git#2.2.1", + "specsplit": "support/specsplit.mjs good -o test/fixtures/commonmark/good.txt && support/specsplit.mjs bad -o test/fixtures/commonmark/bad.txt && support/specsplit.mjs", + "todo": "grep 'TODO' -n -r ./lib 2>/dev/null", + "prepublishOnly": "npm test && npm run build && npm run gh-demo && npm run gh-doc" + }, + "files": [ + "index.mjs", + "lib/", + "dist/" + ], + "dependencies": { + "argparse": "^2.0.1", + "entities": "^4.4.0", + "linkify-it": "^5.0.0", + "mdurl": "^2.0.0", + "punycode.js": "^2.3.1", + "uc.micro": "^2.1.0" + }, + "devDependencies": { + "@rollup/plugin-babel": "^6.0.4", + "@rollup/plugin-commonjs": "^25.0.7", + "@rollup/plugin-node-resolve": "^15.2.3", + "@rollup/plugin-terser": "^0.4.4", + "ansi": "^0.3.0", + "benchmark": "~2.1.0", + "c8": "^8.0.1", + "chai": "^4.2.0", + "eslint": "^8.4.1", + "eslint-config-standard": "^17.1.0", + "express": "^4.14.0", + "gh-pages": "^6.1.0", + "highlight.js": "^11.9.0", + "jest-worker": "^29.7.0", + "markdown-it-abbr": "^2.0.0", + "markdown-it-container": "^4.0.0", + "markdown-it-deflist": "^3.0.0", + "markdown-it-emoji": "^3.0.0", + "markdown-it-footnote": "^4.0.0", + "markdown-it-for-inline": "^2.0.1", + "markdown-it-ins": "^4.0.0", + "markdown-it-mark": "^4.0.0", + "markdown-it-sub": "^2.0.0", + "markdown-it-sup": "^2.0.0", + "markdown-it-testgen": "^0.1.3", + "mocha": "^10.2.0", + "ndoc": "^6.0.0", + "needle": "^3.0.0", + "rollup": "^4.5.0", + "shelljs": "^0.8.4", + "supertest": "^6.0.1" + }, + "mocha": { + "inline-diffs": true, + "timeout": 60000 + } +} diff --git a/frontend/node_modules/markmap-common/LICENSE b/frontend/node_modules/markmap-common/LICENSE new file mode 100644 index 0000000..b438139 --- /dev/null +++ b/frontend/node_modules/markmap-common/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2020 Gerald + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/frontend/node_modules/markmap-common/README.md b/frontend/node_modules/markmap-common/README.md new file mode 100644 index 0000000..edf47e5 --- /dev/null +++ b/frontend/node_modules/markmap-common/README.md @@ -0,0 +1,3 @@ +# markmap-common + +Common types and utility functions used by markmap packages. diff --git a/frontend/node_modules/markmap-common/dist/hook.d.ts b/frontend/node_modules/markmap-common/dist/hook.d.ts new file mode 100644 index 0000000..bab0ecb --- /dev/null +++ b/frontend/node_modules/markmap-common/dist/hook.d.ts @@ -0,0 +1,8 @@ +export type HookCallback = (...args: T) => void; +export declare class Hook { + protected listeners: Array>; + tap(fn: HookCallback): () => void; + revoke(fn: HookCallback): void; + revokeAll(): void; + call(...args: T): void; +} diff --git a/frontend/node_modules/markmap-common/dist/html.d.ts b/frontend/node_modules/markmap-common/dist/html.d.ts new file mode 100644 index 0000000..8ca474a --- /dev/null +++ b/frontend/node_modules/markmap-common/dist/html.d.ts @@ -0,0 +1,9 @@ +import { JSItem, CSSItem } from './types'; +export declare function escapeHtml(html: string): string; +export declare function escapeScript(content: string): string; +export declare function htmlOpen(tagName: string, attrs?: Record): string; +export declare function htmlClose(tagName: string): string; +export declare function wrapHtml(tagName: string, content?: string | null, attrs?: Record): string; +export declare function buildCode(fn: (...args: T) => void, args: T): string; +export declare function persistJS(items: JSItem[], context?: unknown): string[]; +export declare function persistCSS(items: CSSItem[]): string[]; diff --git a/frontend/node_modules/markmap-common/dist/index.d.ts b/frontend/node_modules/markmap-common/dist/index.d.ts new file mode 100644 index 0000000..caff762 --- /dev/null +++ b/frontend/node_modules/markmap-common/dist/index.d.ts @@ -0,0 +1,6 @@ +export * from 'npm2url'; +export * from './hook'; +export * from './html'; +export * from './util'; +export * from './loader'; +export * from './types'; diff --git a/frontend/node_modules/markmap-common/dist/index.js b/frontend/node_modules/markmap-common/dist/index.js new file mode 100644 index 0000000..7668049 --- /dev/null +++ b/frontend/node_modules/markmap-common/dist/index.js @@ -0,0 +1,523 @@ +"use strict"; +Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" }); +const testPath = "npm2url/dist/index.cjs"; +const defaultProviders = { + jsdelivr: (path) => `https://cdn.jsdelivr.net/npm/${path}`, + unpkg: (path) => `https://unpkg.com/${path}` +}; +async function checkUrl(url, signal) { + const res = await fetch(url, { + signal + }); + if (!res.ok) { + throw res; + } + await res.text(); +} +class UrlBuilder { + constructor() { + this.providers = { ...defaultProviders }; + this.provider = "jsdelivr"; + } + /** + * Get the fastest provider name. + * If none of the providers returns a valid response within `timeout`, an error will be thrown. + */ + async getFastestProvider(timeout = 5e3, path = testPath) { + const controller = new AbortController(); + let timer = 0; + try { + return await new Promise((resolve, reject) => { + Promise.all( + Object.entries(this.providers).map(async ([name, factory]) => { + try { + await checkUrl(factory(path), controller.signal); + resolve(name); + } catch { + } + }) + ).then(() => reject(new Error("All providers failed"))); + timer = setTimeout(reject, timeout, new Error("Timed out")); + }); + } finally { + controller.abort(); + clearTimeout(timer); + } + } + /** + * Set the current provider to the fastest provider found by `getFastestProvider`. + */ + async findFastestProvider(timeout, path) { + this.provider = await this.getFastestProvider(timeout, path); + return this.provider; + } + setProvider(name, factory) { + if (factory) { + this.providers[name] = factory; + } else { + delete this.providers[name]; + } + } + getFullUrl(path, provider = this.provider) { + if (path.includes("://")) { + return path; + } + const factory = this.providers[provider]; + if (!factory) { + throw new Error(`Provider ${provider} not found`); + } + return factory(path); + } +} +const urlBuilder = new UrlBuilder(); +class Hook { + constructor() { + this.listeners = []; + } + tap(fn) { + this.listeners.push(fn); + return () => this.revoke(fn); + } + revoke(fn) { + const i = this.listeners.indexOf(fn); + if (i >= 0) this.listeners.splice(i, 1); + } + revokeAll() { + this.listeners.splice(0); + } + call(...args) { + for (const fn of this.listeners) { + fn(...args); + } + } +} +const escapeChars = { + "&": "&", + "<": "<", + '"': """ +}; +function escapeHtml(html) { + return html.replace(/[&<"]/g, (m) => escapeChars[m]); +} +function escapeScript(content) { + return content.replace(/<(\/script>)/g, "\\x3c$2"); +} +function htmlOpen(tagName, attrs) { + const attrStr = attrs ? Object.entries(attrs).map(([key, value]) => { + if (value == null || value === false) return; + key = ` ${escapeHtml(key)}`; + if (value === true) return key; + return `${key}="${escapeHtml(value)}"`; + }).filter(Boolean).join("") : ""; + return `<${tagName}${attrStr}>`; +} +function htmlClose(tagName) { + return ``; +} +function wrapHtml(tagName, content, attrs) { + if (content == null) return htmlOpen(tagName, attrs); + return htmlOpen(tagName, attrs) + (content || "") + htmlClose(tagName); +} +function buildCode(fn, args) { + const params = args.map((arg) => { + if (typeof arg === "function") return arg.toString(); + return JSON.stringify(arg ?? null); + }).join(","); + return `(${fn.toString()})(${params})`; +} +function persistJS(items, context) { + return items.map((item) => { + if (item.type === "script") { + const { textContent, ...rest } = item.data; + return wrapHtml( + "script", + textContent || "", + rest + ); + } + if (item.type === "iife") { + const { fn, getParams } = item.data; + return wrapHtml( + "script", + escapeScript(buildCode(fn, (getParams == null ? void 0 : getParams(context)) || [])) + ); + } + return ""; + }); +} +function persistCSS(items) { + return items.map((item) => { + if (item.type === "stylesheet") { + return wrapHtml("link", null, { + rel: "stylesheet", + ...item.data + }); + } + return wrapHtml("style", item.data); + }); +} +const uniqId = Math.random().toString(36).slice(2, 8); +let globalIndex = 0; +function getId() { + globalIndex += 1; + return `mm-${uniqId}-${globalIndex}`; +} +function noop() { +} +function walkTree(tree, callback) { + const walk = (item, parent) => callback( + item, + () => { + var _a; + return (_a = item.children) == null ? void 0 : _a.map((child) => walk(child, item)); + }, + parent + ); + return walk(tree); +} +function addClass(className, ...rest) { + const classList = (className || "").split(" ").filter(Boolean); + rest.forEach((item) => { + if (item && classList.indexOf(item) < 0) classList.push(item); + }); + return classList.join(" "); +} +function wrapFunction(fn, wrapper) { + return (...args) => wrapper(fn, ...args); +} +function defer() { + const obj = {}; + obj.promise = new Promise((resolve, reject) => { + obj.resolve = resolve; + obj.reject = reject; + }); + return obj; +} +function memoize(fn) { + const cache = {}; + return function memoized(...args) { + const key = `${args[0]}`; + let data = cache[key]; + if (!data) { + data = { + value: fn(...args) + }; + cache[key] = data; + } + return data.value; + }; +} +function debounce(fn, time) { + const state = { + timer: 0 + }; + function reset() { + if (state.timer) { + window.clearTimeout(state.timer); + state.timer = 0; + } + } + function run() { + reset(); + if (state.args) state.result = fn(...state.args); + } + return function debounced(...args) { + reset(); + state.args = args; + state.timer = window.setTimeout(run, time); + return state.result; + }; +} +/*! @gera2ld/jsx-dom v2.2.2 | ISC License */ +const VTYPE_ELEMENT = 1; +const VTYPE_FUNCTION = 2; +const SVG_NS = "http://www.w3.org/2000/svg"; +const XLINK_NS = "http://www.w3.org/1999/xlink"; +const NS_ATTRS = { + show: XLINK_NS, + actuate: XLINK_NS, + href: XLINK_NS +}; +const isLeaf = (c) => typeof c === "string" || typeof c === "number"; +const isElement = (c) => (c == null ? void 0 : c.vtype) === VTYPE_ELEMENT; +const isRenderFunction = (c) => (c == null ? void 0 : c.vtype) === VTYPE_FUNCTION; +function h(type, props, ...children) { + props = Object.assign({}, props, { + children: children.length === 1 ? children[0] : children + }); + return jsx(type, props); +} +function jsx(type, props) { + let vtype; + if (typeof type === "string") vtype = VTYPE_ELEMENT; + else if (typeof type === "function") vtype = VTYPE_FUNCTION; + else throw new Error("Invalid VNode type"); + return { + vtype, + type, + props + }; +} +function Fragment(props) { + return props.children; +} +const DEFAULT_ENV = { + isSvg: false +}; +function insertDom(parent, nodes) { + if (!Array.isArray(nodes)) nodes = [nodes]; + nodes = nodes.filter(Boolean); + if (nodes.length) parent.append(...nodes); +} +function mountAttributes(domElement, props, env) { + for (const key in props) { + if (key === "key" || key === "children" || key === "ref") continue; + if (key === "dangerouslySetInnerHTML") { + domElement.innerHTML = props[key].__html; + } else if (key === "innerHTML" || key === "textContent" || key === "innerText" || key === "value" && ["textarea", "select"].includes(domElement.tagName)) { + const value = props[key]; + if (value != null) domElement[key] = value; + } else if (key.startsWith("on")) { + domElement[key.toLowerCase()] = props[key]; + } else { + setDOMAttribute(domElement, key, props[key], env.isSvg); + } + } +} +const attrMap = { + className: "class", + labelFor: "for" +}; +function setDOMAttribute(el, attr, value, isSVG) { + attr = attrMap[attr] || attr; + if (value === true) { + el.setAttribute(attr, ""); + } else if (value === false) { + el.removeAttribute(attr); + } else { + const namespace = isSVG ? NS_ATTRS[attr] : void 0; + if (namespace !== void 0) { + el.setAttributeNS(namespace, attr, value); + } else { + el.setAttribute(attr, value); + } + } +} +function flatten(arr) { + return arr.reduce((prev, item) => prev.concat(item), []); +} +function mountChildren(children, env) { + return Array.isArray(children) ? flatten(children.map((child) => mountChildren(child, env))) : mount(children, env); +} +function mount(vnode, env = DEFAULT_ENV) { + if (vnode == null || typeof vnode === "boolean") { + return null; + } + if (vnode instanceof Node) { + return vnode; + } + if (isRenderFunction(vnode)) { + const { + type, + props + } = vnode; + if (type === Fragment) { + const node = document.createDocumentFragment(); + if (props.children) { + const children = mountChildren(props.children, env); + insertDom(node, children); + } + return node; + } + const childVNode = type(props); + return mount(childVNode, env); + } + if (isLeaf(vnode)) { + return document.createTextNode(`${vnode}`); + } + if (isElement(vnode)) { + let node; + const { + type, + props + } = vnode; + if (!env.isSvg && type === "svg") { + env = Object.assign({}, env, { + isSvg: true + }); + } + if (!env.isSvg) { + node = document.createElement(type); + } else { + node = document.createElementNS(SVG_NS, type); + } + mountAttributes(node, props, env); + if (props.children) { + let childEnv = env; + if (env.isSvg && type === "foreignObject") { + childEnv = Object.assign({}, childEnv, { + isSvg: false + }); + } + const children = mountChildren(props.children, childEnv); + if (children != null) insertDom(node, children); + } + const { + ref + } = props; + if (typeof ref === "function") ref(node); + return node; + } + throw new Error("mount: Invalid Vnode!"); +} +function mountDom(vnode) { + return mount(vnode); +} +function hm(...args) { + return mountDom(h(...args)); +} +const memoizedPreloadJS = memoize((url) => { + document.head.append( + hm("link", { + rel: "preload", + as: "script", + href: url + }) + ); +}); +const jsCache = {}; +const cssCache = {}; +async function loadJSItem(item, context) { + var _a; + const src = item.type === "script" && ((_a = item.data) == null ? void 0 : _a.src) || ""; + item.loaded || (item.loaded = jsCache[src]); + if (!item.loaded) { + const deferred = defer(); + item.loaded = deferred.promise; + if (item.type === "script") { + document.head.append( + hm("script", { + ...item.data, + onLoad: () => deferred.resolve(), + onError: deferred.reject + }) + ); + if (!src) { + deferred.resolve(); + } else { + jsCache[src] = item.loaded; + } + } + if (item.type === "iife") { + const { fn, getParams } = item.data; + fn(...(getParams == null ? void 0 : getParams(context)) || []); + deferred.resolve(); + } + } + await item.loaded; +} +async function loadCSSItem(item) { + const url = item.type === "stylesheet" && item.data.href || ""; + item.loaded || (item.loaded = cssCache[url]); + if (!item.loaded) { + const deferred = defer(); + item.loaded = deferred.promise; + if (url) cssCache[url] = item.loaded; + if (item.type === "style") { + document.head.append( + hm("style", { + textContent: item.data + }) + ); + deferred.resolve(); + } else if (url) { + document.head.append( + hm("link", { + rel: "stylesheet", + ...item.data + }) + ); + fetch(url).then((res) => { + if (res.ok) return res.text(); + throw res; + }).then(() => deferred.resolve(), deferred.reject); + } + } + await item.loaded; +} +async function loadJS(items, context) { + items.forEach((item) => { + var _a; + if (item.type === "script" && ((_a = item.data) == null ? void 0 : _a.src)) { + memoizedPreloadJS(item.data.src); + } + }); + context = { + getMarkmap: () => window.markmap, + ...context + }; + for (const item of items) { + await loadJSItem(item, context); + } +} +async function loadCSS(items) { + await Promise.all(items.map((item) => loadCSSItem(item))); +} +function buildJSItem(path) { + return { + type: "script", + data: { + src: path + } + }; +} +function buildCSSItem(path) { + return { + type: "stylesheet", + data: { + href: path + } + }; +} +function extractAssets(assets) { + var _a, _b; + return [ + ...((_a = assets.scripts) == null ? void 0 : _a.map( + (item) => item.type === "script" && item.data.src || "" + )) || [], + ...((_b = assets.styles) == null ? void 0 : _b.map( + (item) => item.type === "stylesheet" && item.data.href || "" + )) || [] + ].filter(Boolean); +} +function mergeAssets(...args) { + return { + styles: args.flatMap((arg) => (arg == null ? void 0 : arg.styles) || []), + scripts: args.flatMap((arg) => (arg == null ? void 0 : arg.scripts) || []) + }; +} +exports.Hook = Hook; +exports.UrlBuilder = UrlBuilder; +exports.addClass = addClass; +exports.buildCSSItem = buildCSSItem; +exports.buildCode = buildCode; +exports.buildJSItem = buildJSItem; +exports.debounce = debounce; +exports.defer = defer; +exports.escapeHtml = escapeHtml; +exports.escapeScript = escapeScript; +exports.extractAssets = extractAssets; +exports.getId = getId; +exports.htmlClose = htmlClose; +exports.htmlOpen = htmlOpen; +exports.loadCSS = loadCSS; +exports.loadJS = loadJS; +exports.memoize = memoize; +exports.mergeAssets = mergeAssets; +exports.noop = noop; +exports.persistCSS = persistCSS; +exports.persistJS = persistJS; +exports.urlBuilder = urlBuilder; +exports.walkTree = walkTree; +exports.wrapFunction = wrapFunction; +exports.wrapHtml = wrapHtml; diff --git a/frontend/node_modules/markmap-common/dist/index.mjs b/frontend/node_modules/markmap-common/dist/index.mjs new file mode 100644 index 0000000..f42fa1f --- /dev/null +++ b/frontend/node_modules/markmap-common/dist/index.mjs @@ -0,0 +1,523 @@ +const testPath = "npm2url/dist/index.cjs"; +const defaultProviders = { + jsdelivr: (path) => `https://cdn.jsdelivr.net/npm/${path}`, + unpkg: (path) => `https://unpkg.com/${path}` +}; +async function checkUrl(url, signal) { + const res = await fetch(url, { + signal + }); + if (!res.ok) { + throw res; + } + await res.text(); +} +class UrlBuilder { + constructor() { + this.providers = { ...defaultProviders }; + this.provider = "jsdelivr"; + } + /** + * Get the fastest provider name. + * If none of the providers returns a valid response within `timeout`, an error will be thrown. + */ + async getFastestProvider(timeout = 5e3, path = testPath) { + const controller = new AbortController(); + let timer = 0; + try { + return await new Promise((resolve, reject) => { + Promise.all( + Object.entries(this.providers).map(async ([name, factory]) => { + try { + await checkUrl(factory(path), controller.signal); + resolve(name); + } catch { + } + }) + ).then(() => reject(new Error("All providers failed"))); + timer = setTimeout(reject, timeout, new Error("Timed out")); + }); + } finally { + controller.abort(); + clearTimeout(timer); + } + } + /** + * Set the current provider to the fastest provider found by `getFastestProvider`. + */ + async findFastestProvider(timeout, path) { + this.provider = await this.getFastestProvider(timeout, path); + return this.provider; + } + setProvider(name, factory) { + if (factory) { + this.providers[name] = factory; + } else { + delete this.providers[name]; + } + } + getFullUrl(path, provider = this.provider) { + if (path.includes("://")) { + return path; + } + const factory = this.providers[provider]; + if (!factory) { + throw new Error(`Provider ${provider} not found`); + } + return factory(path); + } +} +const urlBuilder = new UrlBuilder(); +class Hook { + constructor() { + this.listeners = []; + } + tap(fn) { + this.listeners.push(fn); + return () => this.revoke(fn); + } + revoke(fn) { + const i = this.listeners.indexOf(fn); + if (i >= 0) this.listeners.splice(i, 1); + } + revokeAll() { + this.listeners.splice(0); + } + call(...args) { + for (const fn of this.listeners) { + fn(...args); + } + } +} +const escapeChars = { + "&": "&", + "<": "<", + '"': """ +}; +function escapeHtml(html) { + return html.replace(/[&<"]/g, (m) => escapeChars[m]); +} +function escapeScript(content) { + return content.replace(/<(\/script>)/g, "\\x3c$2"); +} +function htmlOpen(tagName, attrs) { + const attrStr = attrs ? Object.entries(attrs).map(([key, value]) => { + if (value == null || value === false) return; + key = ` ${escapeHtml(key)}`; + if (value === true) return key; + return `${key}="${escapeHtml(value)}"`; + }).filter(Boolean).join("") : ""; + return `<${tagName}${attrStr}>`; +} +function htmlClose(tagName) { + return ``; +} +function wrapHtml(tagName, content, attrs) { + if (content == null) return htmlOpen(tagName, attrs); + return htmlOpen(tagName, attrs) + (content || "") + htmlClose(tagName); +} +function buildCode(fn, args) { + const params = args.map((arg) => { + if (typeof arg === "function") return arg.toString(); + return JSON.stringify(arg ?? null); + }).join(","); + return `(${fn.toString()})(${params})`; +} +function persistJS(items, context) { + return items.map((item) => { + if (item.type === "script") { + const { textContent, ...rest } = item.data; + return wrapHtml( + "script", + textContent || "", + rest + ); + } + if (item.type === "iife") { + const { fn, getParams } = item.data; + return wrapHtml( + "script", + escapeScript(buildCode(fn, (getParams == null ? void 0 : getParams(context)) || [])) + ); + } + return ""; + }); +} +function persistCSS(items) { + return items.map((item) => { + if (item.type === "stylesheet") { + return wrapHtml("link", null, { + rel: "stylesheet", + ...item.data + }); + } + return wrapHtml("style", item.data); + }); +} +const uniqId = Math.random().toString(36).slice(2, 8); +let globalIndex = 0; +function getId() { + globalIndex += 1; + return `mm-${uniqId}-${globalIndex}`; +} +function noop() { +} +function walkTree(tree, callback) { + const walk = (item, parent) => callback( + item, + () => { + var _a; + return (_a = item.children) == null ? void 0 : _a.map((child) => walk(child, item)); + }, + parent + ); + return walk(tree); +} +function addClass(className, ...rest) { + const classList = (className || "").split(" ").filter(Boolean); + rest.forEach((item) => { + if (item && classList.indexOf(item) < 0) classList.push(item); + }); + return classList.join(" "); +} +function wrapFunction(fn, wrapper) { + return (...args) => wrapper(fn, ...args); +} +function defer() { + const obj = {}; + obj.promise = new Promise((resolve, reject) => { + obj.resolve = resolve; + obj.reject = reject; + }); + return obj; +} +function memoize(fn) { + const cache = {}; + return function memoized(...args) { + const key = `${args[0]}`; + let data = cache[key]; + if (!data) { + data = { + value: fn(...args) + }; + cache[key] = data; + } + return data.value; + }; +} +function debounce(fn, time) { + const state = { + timer: 0 + }; + function reset() { + if (state.timer) { + window.clearTimeout(state.timer); + state.timer = 0; + } + } + function run() { + reset(); + if (state.args) state.result = fn(...state.args); + } + return function debounced(...args) { + reset(); + state.args = args; + state.timer = window.setTimeout(run, time); + return state.result; + }; +} +/*! @gera2ld/jsx-dom v2.2.2 | ISC License */ +const VTYPE_ELEMENT = 1; +const VTYPE_FUNCTION = 2; +const SVG_NS = "http://www.w3.org/2000/svg"; +const XLINK_NS = "http://www.w3.org/1999/xlink"; +const NS_ATTRS = { + show: XLINK_NS, + actuate: XLINK_NS, + href: XLINK_NS +}; +const isLeaf = (c) => typeof c === "string" || typeof c === "number"; +const isElement = (c) => (c == null ? void 0 : c.vtype) === VTYPE_ELEMENT; +const isRenderFunction = (c) => (c == null ? void 0 : c.vtype) === VTYPE_FUNCTION; +function h(type, props, ...children) { + props = Object.assign({}, props, { + children: children.length === 1 ? children[0] : children + }); + return jsx(type, props); +} +function jsx(type, props) { + let vtype; + if (typeof type === "string") vtype = VTYPE_ELEMENT; + else if (typeof type === "function") vtype = VTYPE_FUNCTION; + else throw new Error("Invalid VNode type"); + return { + vtype, + type, + props + }; +} +function Fragment(props) { + return props.children; +} +const DEFAULT_ENV = { + isSvg: false +}; +function insertDom(parent, nodes) { + if (!Array.isArray(nodes)) nodes = [nodes]; + nodes = nodes.filter(Boolean); + if (nodes.length) parent.append(...nodes); +} +function mountAttributes(domElement, props, env) { + for (const key in props) { + if (key === "key" || key === "children" || key === "ref") continue; + if (key === "dangerouslySetInnerHTML") { + domElement.innerHTML = props[key].__html; + } else if (key === "innerHTML" || key === "textContent" || key === "innerText" || key === "value" && ["textarea", "select"].includes(domElement.tagName)) { + const value = props[key]; + if (value != null) domElement[key] = value; + } else if (key.startsWith("on")) { + domElement[key.toLowerCase()] = props[key]; + } else { + setDOMAttribute(domElement, key, props[key], env.isSvg); + } + } +} +const attrMap = { + className: "class", + labelFor: "for" +}; +function setDOMAttribute(el, attr, value, isSVG) { + attr = attrMap[attr] || attr; + if (value === true) { + el.setAttribute(attr, ""); + } else if (value === false) { + el.removeAttribute(attr); + } else { + const namespace = isSVG ? NS_ATTRS[attr] : void 0; + if (namespace !== void 0) { + el.setAttributeNS(namespace, attr, value); + } else { + el.setAttribute(attr, value); + } + } +} +function flatten(arr) { + return arr.reduce((prev, item) => prev.concat(item), []); +} +function mountChildren(children, env) { + return Array.isArray(children) ? flatten(children.map((child) => mountChildren(child, env))) : mount(children, env); +} +function mount(vnode, env = DEFAULT_ENV) { + if (vnode == null || typeof vnode === "boolean") { + return null; + } + if (vnode instanceof Node) { + return vnode; + } + if (isRenderFunction(vnode)) { + const { + type, + props + } = vnode; + if (type === Fragment) { + const node = document.createDocumentFragment(); + if (props.children) { + const children = mountChildren(props.children, env); + insertDom(node, children); + } + return node; + } + const childVNode = type(props); + return mount(childVNode, env); + } + if (isLeaf(vnode)) { + return document.createTextNode(`${vnode}`); + } + if (isElement(vnode)) { + let node; + const { + type, + props + } = vnode; + if (!env.isSvg && type === "svg") { + env = Object.assign({}, env, { + isSvg: true + }); + } + if (!env.isSvg) { + node = document.createElement(type); + } else { + node = document.createElementNS(SVG_NS, type); + } + mountAttributes(node, props, env); + if (props.children) { + let childEnv = env; + if (env.isSvg && type === "foreignObject") { + childEnv = Object.assign({}, childEnv, { + isSvg: false + }); + } + const children = mountChildren(props.children, childEnv); + if (children != null) insertDom(node, children); + } + const { + ref + } = props; + if (typeof ref === "function") ref(node); + return node; + } + throw new Error("mount: Invalid Vnode!"); +} +function mountDom(vnode) { + return mount(vnode); +} +function hm(...args) { + return mountDom(h(...args)); +} +const memoizedPreloadJS = memoize((url) => { + document.head.append( + hm("link", { + rel: "preload", + as: "script", + href: url + }) + ); +}); +const jsCache = {}; +const cssCache = {}; +async function loadJSItem(item, context) { + var _a; + const src = item.type === "script" && ((_a = item.data) == null ? void 0 : _a.src) || ""; + item.loaded || (item.loaded = jsCache[src]); + if (!item.loaded) { + const deferred = defer(); + item.loaded = deferred.promise; + if (item.type === "script") { + document.head.append( + hm("script", { + ...item.data, + onLoad: () => deferred.resolve(), + onError: deferred.reject + }) + ); + if (!src) { + deferred.resolve(); + } else { + jsCache[src] = item.loaded; + } + } + if (item.type === "iife") { + const { fn, getParams } = item.data; + fn(...(getParams == null ? void 0 : getParams(context)) || []); + deferred.resolve(); + } + } + await item.loaded; +} +async function loadCSSItem(item) { + const url = item.type === "stylesheet" && item.data.href || ""; + item.loaded || (item.loaded = cssCache[url]); + if (!item.loaded) { + const deferred = defer(); + item.loaded = deferred.promise; + if (url) cssCache[url] = item.loaded; + if (item.type === "style") { + document.head.append( + hm("style", { + textContent: item.data + }) + ); + deferred.resolve(); + } else if (url) { + document.head.append( + hm("link", { + rel: "stylesheet", + ...item.data + }) + ); + fetch(url).then((res) => { + if (res.ok) return res.text(); + throw res; + }).then(() => deferred.resolve(), deferred.reject); + } + } + await item.loaded; +} +async function loadJS(items, context) { + items.forEach((item) => { + var _a; + if (item.type === "script" && ((_a = item.data) == null ? void 0 : _a.src)) { + memoizedPreloadJS(item.data.src); + } + }); + context = { + getMarkmap: () => window.markmap, + ...context + }; + for (const item of items) { + await loadJSItem(item, context); + } +} +async function loadCSS(items) { + await Promise.all(items.map((item) => loadCSSItem(item))); +} +function buildJSItem(path) { + return { + type: "script", + data: { + src: path + } + }; +} +function buildCSSItem(path) { + return { + type: "stylesheet", + data: { + href: path + } + }; +} +function extractAssets(assets) { + var _a, _b; + return [ + ...((_a = assets.scripts) == null ? void 0 : _a.map( + (item) => item.type === "script" && item.data.src || "" + )) || [], + ...((_b = assets.styles) == null ? void 0 : _b.map( + (item) => item.type === "stylesheet" && item.data.href || "" + )) || [] + ].filter(Boolean); +} +function mergeAssets(...args) { + return { + styles: args.flatMap((arg) => (arg == null ? void 0 : arg.styles) || []), + scripts: args.flatMap((arg) => (arg == null ? void 0 : arg.scripts) || []) + }; +} +export { + Hook, + UrlBuilder, + addClass, + buildCSSItem, + buildCode, + buildJSItem, + debounce, + defer, + escapeHtml, + escapeScript, + extractAssets, + getId, + htmlClose, + htmlOpen, + loadCSS, + loadJS, + memoize, + mergeAssets, + noop, + persistCSS, + persistJS, + urlBuilder, + walkTree, + wrapFunction, + wrapHtml +}; diff --git a/frontend/node_modules/markmap-common/dist/loader.d.ts b/frontend/node_modules/markmap-common/dist/loader.d.ts new file mode 100644 index 0000000..8acf78c --- /dev/null +++ b/frontend/node_modules/markmap-common/dist/loader.d.ts @@ -0,0 +1,7 @@ +import { CSSItem, CSSStylesheetItem, IAssets, JSItem, JSScriptItem } from './types'; +export declare function loadJS(items: JSItem[], context?: object): Promise; +export declare function loadCSS(items: CSSItem[]): Promise; +export declare function buildJSItem(path: string): JSScriptItem; +export declare function buildCSSItem(path: string): CSSStylesheetItem; +export declare function extractAssets(assets: IAssets): string[]; +export declare function mergeAssets(...args: (IAssets | null | undefined)[]): IAssets; diff --git a/frontend/node_modules/markmap-common/dist/types/common.d.ts b/frontend/node_modules/markmap-common/dist/types/common.d.ts new file mode 100644 index 0000000..1104785 --- /dev/null +++ b/frontend/node_modules/markmap-common/dist/types/common.d.ts @@ -0,0 +1,96 @@ +export interface IPureNode { + /** + * HTML of the node content. + */ + content: string; + /** + * Additional data created on transformation. + */ + payload?: { + [key: string]: unknown; + /** + * The folding status of this node. + * + * 0 - not folded + * 1 - folded + * 2 - folded along with all its child nodes + */ + fold?: number; + }; + children: IPureNode[]; +} +export interface INode extends IPureNode { + /** + * Store temporary data that helps rendering. + */ + state: INodeState; + children: INode[]; +} +export interface INodeState { + /** + * An auto-increment unique ID for each node. + */ + id: number; + /** + * A dot separated sequence of the node and its ancestors. + */ + path: string; + /** + * The unique identifier of a node, supposed to be based on content. + */ + key: string; + /** + * 0-based depth of the node in the tree. + */ + depth: number; + /** DOM element size */ + size: [width: number, height: number]; + /** Position info, only available after layout */ + rect: { + x: number; + y: number; + width: number; + height: number; + }; +} +export type JSScriptItem = { + type: 'script'; + loaded?: Promise; + data: { + src?: string; + textContent?: string; + async?: boolean; + defer?: boolean; + }; +}; +export type JSIIFEItem = { + type: 'iife'; + loaded?: Promise; + data: { + fn: (...args: unknown[]) => void; + getParams?: (context: unknown) => void | unknown[]; + }; +}; +export type JSItem = JSScriptItem | JSIIFEItem; +export type CSSStyleItem = { + type: 'style'; + loaded?: Promise; + data: string; +}; +export type CSSStylesheetItem = { + type: 'stylesheet'; + loaded?: Promise; + data: { + href: string; + }; +}; +export type CSSItem = CSSStyleItem | CSSStylesheetItem; +export interface IDeferred { + promise: Promise; + resolve: (value: T) => void; + reject: (error?: unknown) => void; +} +export interface IAssets { + styles?: CSSItem[]; + scripts?: JSItem[]; +} diff --git a/frontend/node_modules/markmap-common/dist/types/index.d.ts b/frontend/node_modules/markmap-common/dist/types/index.d.ts new file mode 100644 index 0000000..d0b9323 --- /dev/null +++ b/frontend/node_modules/markmap-common/dist/types/index.d.ts @@ -0,0 +1 @@ +export * from './common'; diff --git a/frontend/node_modules/markmap-common/dist/util.d.ts b/frontend/node_modules/markmap-common/dist/util.d.ts new file mode 100644 index 0000000..bfbebfa --- /dev/null +++ b/frontend/node_modules/markmap-common/dist/util.d.ts @@ -0,0 +1,11 @@ +import { IDeferred } from './types'; +export declare function getId(): string; +export declare function noop(): void; +export declare function walkTree(tree: T, callback: (item: T, next: () => U[] | undefined, parent?: T) => U): U; +export declare function addClass(className: string, ...rest: string[]): string; +export declare function wrapFunction(fn: (...args: T) => U, wrapper: (fn: (...args: T) => U, ...args: T) => U): (...args: T) => U; +export declare function defer(): IDeferred; +export declare function memoize(fn: (...args: T) => U): (...args: T) => U; +export declare function debounce(fn: (...args: T) => U, time: number): (...args: T) => U | undefined; diff --git a/frontend/node_modules/markmap-common/package.json b/frontend/node_modules/markmap-common/package.json new file mode 100644 index 0000000..7725ce6 --- /dev/null +++ b/frontend/node_modules/markmap-common/package.json @@ -0,0 +1,38 @@ +{ + "name": "markmap-common", + "version": "0.18.9", + "description": "", + "author": "", + "license": "MIT", + "scripts": { + "clean": "del-cli dist tsconfig.tsbuildinfo", + "build:types": "tsc", + "build:js": "vite build", + "build": "pnpm clean && pnpm /^build:/", + "prepublishOnly": "pnpm build" + }, + "main": "dist/index.js", + "module": "dist/index.mjs", + "files": [ + "dist" + ], + "publishConfig": { + "access": "public", + "registry": "https://registry.npmjs.org/" + }, + "homepage": "https://github.com/markmap/markmap/packages/markmap-common#readme", + "repository": { + "type": "git", + "url": "git+https://github.com/markmap/markmap.git" + }, + "bugs": { + "url": "https://github.com/markmap/markmap/issues" + }, + "typings": "dist/index.d.ts", + "dependencies": { + "@babel/runtime": "^7.22.6", + "@gera2ld/jsx-dom": "^2.2.2", + "npm2url": "^0.2.4" + }, + "gitHead": "4247555f57017ffc9297e5e5e031c4119de3ebaf" +} diff --git a/frontend/node_modules/markmap-html-parser/LICENSE b/frontend/node_modules/markmap-html-parser/LICENSE new file mode 100644 index 0000000..b438139 --- /dev/null +++ b/frontend/node_modules/markmap-html-parser/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2020 Gerald + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/frontend/node_modules/markmap-html-parser/README.md b/frontend/node_modules/markmap-html-parser/README.md new file mode 100644 index 0000000..f5d5c5a --- /dev/null +++ b/frontend/node_modules/markmap-html-parser/README.md @@ -0,0 +1,9 @@ +# markmap-html-parser + +![NPM](https://img.shields.io/npm/v/markmap-html-parser.svg) +![License](https://img.shields.io/npm/l/markmap-html-parser.svg) +![Downloads](https://img.shields.io/npm/dt/markmap-html-parser.svg) + +Parse HTML into markmap data structure. + +👉 [Read the documentation](https://markmap.js.org/docs) for more detail. diff --git a/frontend/node_modules/markmap-html-parser/dist/index.d.ts b/frontend/node_modules/markmap-html-parser/dist/index.d.ts new file mode 100644 index 0000000..7d93655 --- /dev/null +++ b/frontend/node_modules/markmap-html-parser/dist/index.d.ts @@ -0,0 +1,48 @@ +import { Cheerio, CheerioAPI } from 'cheerio/slim'; +import { IPureNode } from 'markmap-common'; +export declare enum Levels { + None = 0, + H1 = 1, + H2 = 2, + H3 = 3, + H4 = 4, + H5 = 5, + H6 = 6, + Block = 7, + List = 8, + ListItem = 9 +} +export interface IHtmlNode { + id: number; + tag: string; + html: string; + level: Levels; + parent: number; + childrenLevel: Levels; + children?: IHtmlNode[]; + comments?: string[]; + data?: Record; +} +export interface IHtmlParserContext { + $node: Cheerio; + $: CheerioAPI; + getContent($node: Cheerio, preserveTag?: boolean): { + html?: string; + comments?: string[]; + }; +} +export interface IHtmlParserResult { + html?: string | null; + comments?: string[]; + queue?: Cheerio; + nesting?: boolean; +} +export type IHtmlParserSelectorRules = Record IHtmlParserResult>; +export interface IHtmlParserOptions { + selector: string; + selectorRules: IHtmlParserSelectorRules; +} +export declare const defaultOptions: IHtmlParserOptions; +export declare function parseHtml(html: string, opts?: Partial): IHtmlNode; +export declare function convertNode(htmlRoot: IHtmlNode): IPureNode; +export declare function buildTree(html: string, opts?: Partial): IPureNode; diff --git a/frontend/node_modules/markmap-html-parser/dist/index.js b/frontend/node_modules/markmap-html-parser/dist/index.js new file mode 100644 index 0000000..ed27bf3 --- /dev/null +++ b/frontend/node_modules/markmap-html-parser/dist/index.js @@ -0,0 +1,6000 @@ +"use strict"; +Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" }); +const markmapCommon = require("markmap-common"); +const defaultOpts$1 = { + _useHtmlParser2: false +}; +function flattenOptions(options, baseOptions) { + if (!options) { + return baseOptions !== null && baseOptions !== void 0 ? baseOptions : defaultOpts$1; + } + const opts = { + _useHtmlParser2: !!options.xmlMode, + ...baseOptions, + ...options + }; + if (options.xml) { + opts._useHtmlParser2 = true; + opts.xmlMode = true; + if (options.xml !== true) { + Object.assign(opts, options.xml); + } + } else if (options.xmlMode) { + opts._useHtmlParser2 = true; + } + return opts; +} +var ElementType; +(function(ElementType2) { + ElementType2["Root"] = "root"; + ElementType2["Text"] = "text"; + ElementType2["Directive"] = "directive"; + ElementType2["Comment"] = "comment"; + ElementType2["Script"] = "script"; + ElementType2["Style"] = "style"; + ElementType2["Tag"] = "tag"; + ElementType2["CDATA"] = "cdata"; + ElementType2["Doctype"] = "doctype"; +})(ElementType || (ElementType = {})); +function isTag$1(elem) { + return elem.type === ElementType.Tag || elem.type === ElementType.Script || elem.type === ElementType.Style; +} +const Root = ElementType.Root; +const Text$1 = ElementType.Text; +const Directive = ElementType.Directive; +const Comment$1 = ElementType.Comment; +const Script = ElementType.Script; +const Style = ElementType.Style; +const Tag = ElementType.Tag; +const CDATA$1 = ElementType.CDATA; +const Doctype = ElementType.Doctype; +class Node { + constructor() { + this.parent = null; + this.prev = null; + this.next = null; + this.startIndex = null; + this.endIndex = null; + } + // Read-write aliases for properties + /** + * Same as {@link parent}. + * [DOM spec](https://dom.spec.whatwg.org)-compatible alias. + */ + get parentNode() { + return this.parent; + } + set parentNode(parent2) { + this.parent = parent2; + } + /** + * Same as {@link prev}. + * [DOM spec](https://dom.spec.whatwg.org)-compatible alias. + */ + get previousSibling() { + return this.prev; + } + set previousSibling(prev2) { + this.prev = prev2; + } + /** + * Same as {@link next}. + * [DOM spec](https://dom.spec.whatwg.org)-compatible alias. + */ + get nextSibling() { + return this.next; + } + set nextSibling(next2) { + this.next = next2; + } + /** + * Clone this node, and optionally its children. + * + * @param recursive Clone child nodes as well. + * @returns A clone of the node. + */ + cloneNode(recursive = false) { + return cloneNode(this, recursive); + } +} +class DataNode extends Node { + /** + * @param data The content of the data node + */ + constructor(data2) { + super(); + this.data = data2; + } + /** + * Same as {@link data}. + * [DOM spec](https://dom.spec.whatwg.org)-compatible alias. + */ + get nodeValue() { + return this.data; + } + set nodeValue(data2) { + this.data = data2; + } +} +class Text extends DataNode { + constructor() { + super(...arguments); + this.type = ElementType.Text; + } + get nodeType() { + return 3; + } +} +class Comment extends DataNode { + constructor() { + super(...arguments); + this.type = ElementType.Comment; + } + get nodeType() { + return 8; + } +} +class ProcessingInstruction extends DataNode { + constructor(name, data2) { + super(data2); + this.name = name; + this.type = ElementType.Directive; + } + get nodeType() { + return 1; + } +} +class NodeWithChildren extends Node { + /** + * @param children Children of the node. Only certain node types can have children. + */ + constructor(children2) { + super(); + this.children = children2; + } + // Aliases + /** First child of the node. */ + get firstChild() { + var _a2; + return (_a2 = this.children[0]) !== null && _a2 !== void 0 ? _a2 : null; + } + /** Last child of the node. */ + get lastChild() { + return this.children.length > 0 ? this.children[this.children.length - 1] : null; + } + /** + * Same as {@link children}. + * [DOM spec](https://dom.spec.whatwg.org)-compatible alias. + */ + get childNodes() { + return this.children; + } + set childNodes(children2) { + this.children = children2; + } +} +class CDATA extends NodeWithChildren { + constructor() { + super(...arguments); + this.type = ElementType.CDATA; + } + get nodeType() { + return 4; + } +} +class Document extends NodeWithChildren { + constructor() { + super(...arguments); + this.type = ElementType.Root; + } + get nodeType() { + return 9; + } +} +class Element extends NodeWithChildren { + /** + * @param name Name of the tag, eg. `div`, `span`. + * @param attribs Object mapping attribute names to attribute values. + * @param children Children of the node. + */ + constructor(name, attribs, children2 = [], type = name === "script" ? ElementType.Script : name === "style" ? ElementType.Style : ElementType.Tag) { + super(children2); + this.name = name; + this.attribs = attribs; + this.type = type; + } + get nodeType() { + return 1; + } + // DOM Level 1 aliases + /** + * Same as {@link name}. + * [DOM spec](https://dom.spec.whatwg.org)-compatible alias. + */ + get tagName() { + return this.name; + } + set tagName(name) { + this.name = name; + } + get attributes() { + return Object.keys(this.attribs).map((name) => { + var _a2, _b; + return { + name, + value: this.attribs[name], + namespace: (_a2 = this["x-attribsNamespace"]) === null || _a2 === void 0 ? void 0 : _a2[name], + prefix: (_b = this["x-attribsPrefix"]) === null || _b === void 0 ? void 0 : _b[name] + }; + }); + } +} +function isTag(node) { + return isTag$1(node); +} +function isCDATA(node) { + return node.type === ElementType.CDATA; +} +function isText(node) { + return node.type === ElementType.Text; +} +function isComment(node) { + return node.type === ElementType.Comment; +} +function isDirective(node) { + return node.type === ElementType.Directive; +} +function isDocument(node) { + return node.type === ElementType.Root; +} +function hasChildren(node) { + return Object.prototype.hasOwnProperty.call(node, "children"); +} +function cloneNode(node, recursive = false) { + let result; + if (isText(node)) { + result = new Text(node.data); + } else if (isComment(node)) { + result = new Comment(node.data); + } else if (isTag(node)) { + const children2 = recursive ? cloneChildren(node.children) : []; + const clone2 = new Element(node.name, { ...node.attribs }, children2); + children2.forEach((child) => child.parent = clone2); + if (node.namespace != null) { + clone2.namespace = node.namespace; + } + if (node["x-attribsNamespace"]) { + clone2["x-attribsNamespace"] = { ...node["x-attribsNamespace"] }; + } + if (node["x-attribsPrefix"]) { + clone2["x-attribsPrefix"] = { ...node["x-attribsPrefix"] }; + } + result = clone2; + } else if (isCDATA(node)) { + const children2 = recursive ? cloneChildren(node.children) : []; + const clone2 = new CDATA(children2); + children2.forEach((child) => child.parent = clone2); + result = clone2; + } else if (isDocument(node)) { + const children2 = recursive ? cloneChildren(node.children) : []; + const clone2 = new Document(children2); + children2.forEach((child) => child.parent = clone2); + if (node["x-mode"]) { + clone2["x-mode"] = node["x-mode"]; + } + result = clone2; + } else if (isDirective(node)) { + const instruction = new ProcessingInstruction(node.name, node.data); + if (node["x-name"] != null) { + instruction["x-name"] = node["x-name"]; + instruction["x-publicId"] = node["x-publicId"]; + instruction["x-systemId"] = node["x-systemId"]; + } + result = instruction; + } else { + throw new Error(`Not implemented yet: ${node.type}`); + } + result.startIndex = node.startIndex; + result.endIndex = node.endIndex; + if (node.sourceCodeLocation != null) { + result.sourceCodeLocation = node.sourceCodeLocation; + } + return result; +} +function cloneChildren(childs) { + const children2 = childs.map((child) => cloneNode(child, true)); + for (let i = 1; i < children2.length; i++) { + children2[i].prev = children2[i - 1]; + children2[i - 1].next = children2[i]; + } + return children2; +} +const defaultOpts = { + withStartIndices: false, + withEndIndices: false, + xmlMode: false +}; +class DomHandler { + /** + * @param callback Called once parsing has completed. + * @param options Settings for the handler. + * @param elementCB Callback whenever a tag is closed. + */ + constructor(callback, options, elementCB) { + this.dom = []; + this.root = new Document(this.dom); + this.done = false; + this.tagStack = [this.root]; + this.lastNode = null; + this.parser = null; + if (typeof options === "function") { + elementCB = options; + options = defaultOpts; + } + if (typeof callback === "object") { + options = callback; + callback = void 0; + } + this.callback = callback !== null && callback !== void 0 ? callback : null; + this.options = options !== null && options !== void 0 ? options : defaultOpts; + this.elementCB = elementCB !== null && elementCB !== void 0 ? elementCB : null; + } + onparserinit(parser) { + this.parser = parser; + } + // Resets the handler back to starting state + onreset() { + this.dom = []; + this.root = new Document(this.dom); + this.done = false; + this.tagStack = [this.root]; + this.lastNode = null; + this.parser = null; + } + // Signals the handler that parsing is done + onend() { + if (this.done) + return; + this.done = true; + this.parser = null; + this.handleCallback(null); + } + onerror(error) { + this.handleCallback(error); + } + onclosetag() { + this.lastNode = null; + const elem = this.tagStack.pop(); + if (this.options.withEndIndices) { + elem.endIndex = this.parser.endIndex; + } + if (this.elementCB) + this.elementCB(elem); + } + onopentag(name, attribs) { + const type = this.options.xmlMode ? ElementType.Tag : void 0; + const element = new Element(name, attribs, void 0, type); + this.addNode(element); + this.tagStack.push(element); + } + ontext(data2) { + const { lastNode } = this; + if (lastNode && lastNode.type === ElementType.Text) { + lastNode.data += data2; + if (this.options.withEndIndices) { + lastNode.endIndex = this.parser.endIndex; + } + } else { + const node = new Text(data2); + this.addNode(node); + this.lastNode = node; + } + } + oncomment(data2) { + if (this.lastNode && this.lastNode.type === ElementType.Comment) { + this.lastNode.data += data2; + return; + } + const node = new Comment(data2); + this.addNode(node); + this.lastNode = node; + } + oncommentend() { + this.lastNode = null; + } + oncdatastart() { + const text2 = new Text(""); + const node = new CDATA([text2]); + this.addNode(node); + text2.parent = node; + this.lastNode = text2; + } + oncdataend() { + this.lastNode = null; + } + onprocessinginstruction(name, data2) { + const node = new ProcessingInstruction(name, data2); + this.addNode(node); + } + handleCallback(error) { + if (typeof this.callback === "function") { + this.callback(error, this.dom); + } else if (error) { + throw error; + } + } + addNode(node) { + const parent2 = this.tagStack[this.tagStack.length - 1]; + const previousSibling = parent2.children[parent2.children.length - 1]; + if (this.options.withStartIndices) { + node.startIndex = this.parser.startIndex; + } + if (this.options.withEndIndices) { + node.endIndex = this.parser.endIndex; + } + parent2.children.push(node); + if (previousSibling) { + node.prev = previousSibling; + previousSibling.next = node; + } + node.parent = parent2; + this.lastNode = null; + } +} +const htmlDecodeTree = new Uint16Array( + // prettier-ignore + 'ᵁ<Õıʊҝջאٵ۞ޢߖࠏ੊ઑඡ๭༉༦჊ረዡᐕᒝᓃᓟᔥ\0\0\0\0\0\0ᕫᛍᦍᰒᷝ὾⁠↰⊍⏀⏻⑂⠤⤒ⴈ⹈⿎〖㊺㘹㞬㣾㨨㩱㫠㬮ࠀEMabcfglmnoprstu\\bfms„‹•˜¦³¹ÈÏlig耻Æ䃆P耻&䀦cute耻Á䃁reve;䄂Āiyx}rc耻Â䃂;䐐r;쀀𝔄rave耻À䃀pha;䎑acr;䄀d;橓Āgp¡on;䄄f;쀀𝔸plyFunction;恡ing耻Å䃅Ācs¾Ãr;쀀𝒜ign;扔ilde耻Ã䃃ml耻Ä䃄ЀaceforsuåûþėĜĢħĪĀcrêòkslash;或Ŷöø;櫧ed;挆y;䐑ƀcrtąċĔause;戵noullis;愬a;䎒r;쀀𝔅pf;쀀𝔹eve;䋘còēmpeq;扎܀HOacdefhilorsuōőŖƀƞƢƵƷƺǜȕɳɸɾcy;䐧PY耻©䂩ƀcpyŝŢźute;䄆Ā;iŧŨ拒talDifferentialD;慅leys;愭ȀaeioƉƎƔƘron;䄌dil耻Ç䃇rc;䄈nint;戰ot;䄊ĀdnƧƭilla;䂸terDot;䂷òſi;䎧rcleȀDMPTLJNjǑǖot;抙inus;抖lus;投imes;抗oĀcsǢǸkwiseContourIntegral;戲eCurlyĀDQȃȏoubleQuote;思uote;怙ȀlnpuȞȨɇɕonĀ;eȥȦ户;橴ƀgitȯȶȺruent;扡nt;戯ourIntegral;戮ĀfrɌɎ;愂oduct;成nterClockwiseContourIntegral;戳oss;樯cr;쀀𝒞pĀ;Cʄʅ拓ap;才րDJSZacefiosʠʬʰʴʸˋ˗ˡ˦̳ҍĀ;oŹʥtrahd;椑cy;䐂cy;䐅cy;䐏ƀgrsʿ˄ˇger;怡r;憡hv;櫤Āayː˕ron;䄎;䐔lĀ;t˝˞戇a;䎔r;쀀𝔇Āaf˫̧Ācm˰̢riticalȀADGT̖̜̀̆cute;䂴oŴ̋̍;䋙bleAcute;䋝rave;䁠ilde;䋜ond;拄ferentialD;慆Ѱ̽\0\0\0͔͂\0Ѕf;쀀𝔻ƀ;DE͈͉͍䂨ot;惜qual;扐blèCDLRUVͣͲ΂ϏϢϸontourIntegraìȹoɴ͹\0\0ͻ»͉nArrow;懓Āeo·ΤftƀARTΐΖΡrrow;懐ightArrow;懔eåˊngĀLRΫτeftĀARγιrrow;柸ightArrow;柺ightArrow;柹ightĀATϘϞrrow;懒ee;抨pɁϩ\0\0ϯrrow;懑ownArrow;懕erticalBar;戥ǹABLRTaВЪаўѿͼrrowƀ;BUНОТ憓ar;椓pArrow;懵reve;䌑eft˒к\0ц\0ѐightVector;楐eeVector;楞ectorĀ;Bљњ憽ar;楖ightǔѧ\0ѱeeVector;楟ectorĀ;BѺѻ懁ar;楗eeĀ;A҆҇护rrow;憧ĀctҒҗr;쀀𝒟rok;䄐ࠀNTacdfglmopqstuxҽӀӄӋӞӢӧӮӵԡԯԶՒ՝ՠեG;䅊H耻Ð䃐cute耻É䃉ƀaiyӒӗӜron;䄚rc耻Ê䃊;䐭ot;䄖r;쀀𝔈rave耻È䃈ement;戈ĀapӺӾcr;䄒tyɓԆ\0\0ԒmallSquare;旻erySmallSquare;斫ĀgpԦԪon;䄘f;쀀𝔼silon;䎕uĀaiԼՉlĀ;TՂՃ橵ilde;扂librium;懌Āci՗՚r;愰m;橳a;䎗ml耻Ë䃋Āipժկsts;戃onentialE;慇ʀcfiosօֈ֍ֲ׌y;䐤r;쀀𝔉lledɓ֗\0\0֣mallSquare;旼erySmallSquare;斪Ͱֺ\0ֿ\0\0ׄf;쀀𝔽All;戀riertrf;愱cò׋؀JTabcdfgorstר׬ׯ׺؀ؒؖ؛؝أ٬ٲcy;䐃耻>䀾mmaĀ;d׷׸䎓;䏜reve;䄞ƀeiy؇،ؐdil;䄢rc;䄜;䐓ot;䄠r;쀀𝔊;拙pf;쀀𝔾eater̀EFGLSTصلَٖٛ٦qualĀ;Lؾؿ扥ess;招ullEqual;执reater;檢ess;扷lantEqual;橾ilde;扳cr;쀀𝒢;扫ЀAacfiosuڅڋږڛڞڪھۊRDcy;䐪Āctڐڔek;䋇;䁞irc;䄤r;愌lbertSpace;愋ǰگ\0ڲf;愍izontalLine;攀Āctۃۅòکrok;䄦mpńېۘownHumðįqual;扏܀EJOacdfgmnostuۺ۾܃܇܎ܚܞܡܨ݄ݸދޏޕcy;䐕lig;䄲cy;䐁cute耻Í䃍Āiyܓܘrc耻Î䃎;䐘ot;䄰r;愑rave耻Ì䃌ƀ;apܠܯܿĀcgܴܷr;䄪inaryI;慈lieóϝǴ݉\0ݢĀ;eݍݎ戬Āgrݓݘral;戫section;拂isibleĀCTݬݲomma;恣imes;恢ƀgptݿރވon;䄮f;쀀𝕀a;䎙cr;愐ilde;䄨ǫޚ\0ޞcy;䐆l耻Ï䃏ʀcfosuެ޷޼߂ߐĀiyޱ޵rc;䄴;䐙r;쀀𝔍pf;쀀𝕁ǣ߇\0ߌr;쀀𝒥rcy;䐈kcy;䐄΀HJacfosߤߨ߽߬߱ࠂࠈcy;䐥cy;䐌ppa;䎚Āey߶߻dil;䄶;䐚r;쀀𝔎pf;쀀𝕂cr;쀀𝒦րJTaceflmostࠥࠩࠬࡐࡣ঳সে্਷ੇcy;䐉耻<䀼ʀcmnpr࠷࠼ࡁࡄࡍute;䄹bda;䎛g;柪lacetrf;愒r;憞ƀaeyࡗ࡜ࡡron;䄽dil;䄻;䐛Āfsࡨ॰tԀACDFRTUVarࡾࢩࢱࣦ࣠ࣼयज़ΐ४Ānrࢃ࢏gleBracket;柨rowƀ;BR࢙࢚࢞憐ar;懤ightArrow;懆eiling;挈oǵࢷ\0ࣃbleBracket;柦nǔࣈ\0࣒eeVector;楡ectorĀ;Bࣛࣜ懃ar;楙loor;挊ightĀAV࣯ࣵrrow;憔ector;楎Āerँगeƀ;AVउऊऐ抣rrow;憤ector;楚iangleƀ;BEतथऩ抲ar;槏qual;抴pƀDTVषूौownVector;楑eeVector;楠ectorĀ;Bॖॗ憿ar;楘ectorĀ;B॥०憼ar;楒ightáΜs̀EFGLSTॾঋকঝঢভqualGreater;拚ullEqual;扦reater;扶ess;檡lantEqual;橽ilde;扲r;쀀𝔏Ā;eঽা拘ftarrow;懚idot;䄿ƀnpw৔ਖਛgȀLRlr৞৷ਂਐeftĀAR০৬rrow;柵ightArrow;柷ightArrow;柶eftĀarγਊightáοightáϊf;쀀𝕃erĀLRਢਬeftArrow;憙ightArrow;憘ƀchtਾੀੂòࡌ;憰rok;䅁;扪Ѐacefiosuਗ਼੝੠੷੼અઋ઎p;椅y;䐜Ādl੥੯iumSpace;恟lintrf;愳r;쀀𝔐nusPlus;戓pf;쀀𝕄cò੶;䎜ҀJacefostuણધભીଔଙඑ඗ඞcy;䐊cute;䅃ƀaey઴હાron;䅇dil;䅅;䐝ƀgswે૰଎ativeƀMTV૓૟૨ediumSpace;怋hiĀcn૦૘ë૙eryThiî૙tedĀGL૸ଆreaterGreateòٳessLesóੈLine;䀊r;쀀𝔑ȀBnptଢନଷ଺reak;恠BreakingSpace;䂠f;愕ڀ;CDEGHLNPRSTV୕ୖ୪୼஡௫ఄ౞಄ದ೘ൡඅ櫬Āou୛୤ngruent;扢pCap;扭oubleVerticalBar;戦ƀlqxஃஊ஛ement;戉ualĀ;Tஒஓ扠ilde;쀀≂̸ists;戄reater΀;EFGLSTஶஷ஽௉௓௘௥扯qual;扱ullEqual;쀀≧̸reater;쀀≫̸ess;批lantEqual;쀀⩾̸ilde;扵umpń௲௽ownHump;쀀≎̸qual;쀀≏̸eĀfsఊధtTriangleƀ;BEచఛడ拪ar;쀀⧏̸qual;括s̀;EGLSTవశ఼ౄోౘ扮qual;扰reater;扸ess;쀀≪̸lantEqual;쀀⩽̸ilde;扴estedĀGL౨౹reaterGreater;쀀⪢̸essLess;쀀⪡̸recedesƀ;ESಒಓಛ技qual;쀀⪯̸lantEqual;拠ĀeiಫಹverseElement;戌ghtTriangleƀ;BEೋೌ೒拫ar;쀀⧐̸qual;拭ĀquೝഌuareSuĀbp೨೹setĀ;E೰ೳ쀀⊏̸qual;拢ersetĀ;Eഃആ쀀⊐̸qual;拣ƀbcpഓതൎsetĀ;Eഛഞ쀀⊂⃒qual;抈ceedsȀ;ESTലള഻െ抁qual;쀀⪰̸lantEqual;拡ilde;쀀≿̸ersetĀ;E൘൛쀀⊃⃒qual;抉ildeȀ;EFT൮൯൵ൿ扁qual;扄ullEqual;扇ilde;扉erticalBar;戤cr;쀀𝒩ilde耻Ñ䃑;䎝܀Eacdfgmoprstuvලෂ෉෕ෛ෠෧෼ขภยา฿ไlig;䅒cute耻Ó䃓Āiy෎ීrc耻Ô䃔;䐞blac;䅐r;쀀𝔒rave耻Ò䃒ƀaei෮ෲ෶cr;䅌ga;䎩cron;䎟pf;쀀𝕆enCurlyĀDQฎบoubleQuote;怜uote;怘;橔Āclวฬr;쀀𝒪ash耻Ø䃘iŬื฼de耻Õ䃕es;樷ml耻Ö䃖erĀBP๋๠Āar๐๓r;怾acĀek๚๜;揞et;掴arenthesis;揜Ҁacfhilors๿ງຊຏຒດຝະ໼rtialD;戂y;䐟r;쀀𝔓i;䎦;䎠usMinus;䂱Āipຢອncareplanåڝf;愙Ȁ;eio຺ູ໠໤檻cedesȀ;EST່້໏໚扺qual;檯lantEqual;扼ilde;找me;怳Ādp໩໮uct;戏ortionĀ;aȥ໹l;戝Āci༁༆r;쀀𝒫;䎨ȀUfos༑༖༛༟OT耻"䀢r;쀀𝔔pf;愚cr;쀀𝒬؀BEacefhiorsu༾གྷཇའཱིྦྷྪྭ႖ႩႴႾarr;椐G耻®䂮ƀcnrཎནབute;䅔g;柫rĀ;tཛྷཝ憠l;椖ƀaeyཧཬཱron;䅘dil;䅖;䐠Ā;vླྀཹ愜erseĀEUྂྙĀlq྇ྎement;戋uilibrium;懋pEquilibrium;楯r»ཹo;䎡ghtЀACDFTUVa࿁࿫࿳ဢဨၛႇϘĀnr࿆࿒gleBracket;柩rowƀ;BL࿜࿝࿡憒ar;懥eftArrow;懄eiling;按oǵ࿹\0စbleBracket;柧nǔည\0နeeVector;楝ectorĀ;Bဝသ懂ar;楕loor;挋Āerိ၃eƀ;AVဵံြ抢rrow;憦ector;楛iangleƀ;BEၐၑၕ抳ar;槐qual;抵pƀDTVၣၮၸownVector;楏eeVector;楜ectorĀ;Bႂႃ憾ar;楔ectorĀ;B႑႒懀ar;楓Āpuႛ႞f;愝ndImplies;楰ightarrow;懛ĀchႹႼr;愛;憱leDelayed;槴ڀHOacfhimoqstuფჱჷჽᄙᄞᅑᅖᅡᅧᆵᆻᆿĀCcჩხHcy;䐩y;䐨FTcy;䐬cute;䅚ʀ;aeiyᄈᄉᄎᄓᄗ檼ron;䅠dil;䅞rc;䅜;䐡r;쀀𝔖ortȀDLRUᄪᄴᄾᅉownArrow»ОeftArrow»࢚ightArrow»࿝pArrow;憑gma;䎣allCircle;战pf;쀀𝕊ɲᅭ\0\0ᅰt;戚areȀ;ISUᅻᅼᆉᆯ斡ntersection;抓uĀbpᆏᆞsetĀ;Eᆗᆘ抏qual;抑ersetĀ;Eᆨᆩ抐qual;抒nion;抔cr;쀀𝒮ar;拆ȀbcmpᇈᇛሉላĀ;sᇍᇎ拐etĀ;Eᇍᇕqual;抆ĀchᇠህeedsȀ;ESTᇭᇮᇴᇿ扻qual;檰lantEqual;扽ilde;承Tháྌ;我ƀ;esሒሓሣ拑rsetĀ;Eሜም抃qual;抇et»ሓրHRSacfhiorsሾቄ቉ቕ቞ቱቶኟዂወዑORN耻Þ䃞ADE;愢ĀHc቎ቒcy;䐋y;䐦Ābuቚቜ;䀉;䎤ƀaeyብቪቯron;䅤dil;䅢;䐢r;쀀𝔗Āeiቻ኉Dzኀ\0ኇefore;戴a;䎘Ācn኎ኘkSpace;쀀  Space;怉ldeȀ;EFTካኬኲኼ戼qual;扃ullEqual;扅ilde;扈pf;쀀𝕋ipleDot;惛Āctዖዛr;쀀𝒯rok;䅦ૡዷጎጚጦ\0ጬጱ\0\0\0\0\0ጸጽ፷ᎅ\0᏿ᐄᐊᐐĀcrዻጁute耻Ú䃚rĀ;oጇገ憟cir;楉rǣጓ\0጖y;䐎ve;䅬Āiyጞጣrc耻Û䃛;䐣blac;䅰r;쀀𝔘rave耻Ù䃙acr;䅪Ādiፁ፩erĀBPፈ፝Āarፍፐr;䁟acĀekፗፙ;揟et;掵arenthesis;揝onĀ;P፰፱拃lus;抎Āgp፻፿on;䅲f;쀀𝕌ЀADETadps᎕ᎮᎸᏄϨᏒᏗᏳrrowƀ;BDᅐᎠᎤar;椒ownArrow;懅ownArrow;憕quilibrium;楮eeĀ;AᏋᏌ报rrow;憥ownáϳerĀLRᏞᏨeftArrow;憖ightArrow;憗iĀ;lᏹᏺ䏒on;䎥ing;䅮cr;쀀𝒰ilde;䅨ml耻Ü䃜ҀDbcdefosvᐧᐬᐰᐳᐾᒅᒊᒐᒖash;披ar;櫫y;䐒ashĀ;lᐻᐼ抩;櫦Āerᑃᑅ;拁ƀbtyᑌᑐᑺar;怖Ā;iᑏᑕcalȀBLSTᑡᑥᑪᑴar;戣ine;䁼eparator;杘ilde;所ThinSpace;怊r;쀀𝔙pf;쀀𝕍cr;쀀𝒱dash;抪ʀcefosᒧᒬᒱᒶᒼirc;䅴dge;拀r;쀀𝔚pf;쀀𝕎cr;쀀𝒲Ȁfiosᓋᓐᓒᓘr;쀀𝔛;䎞pf;쀀𝕏cr;쀀𝒳ҀAIUacfosuᓱᓵᓹᓽᔄᔏᔔᔚᔠcy;䐯cy;䐇cy;䐮cute耻Ý䃝Āiyᔉᔍrc;䅶;䐫r;쀀𝔜pf;쀀𝕐cr;쀀𝒴ml;䅸ЀHacdefosᔵᔹᔿᕋᕏᕝᕠᕤcy;䐖cute;䅹Āayᕄᕉron;䅽;䐗ot;䅻Dzᕔ\0ᕛoWidtè૙a;䎖r;愨pf;愤cr;쀀𝒵௡ᖃᖊᖐ\0ᖰᖶᖿ\0\0\0\0ᗆᗛᗫᙟ᙭\0ᚕ᚛ᚲᚹ\0ᚾcute耻á䃡reve;䄃̀;Ediuyᖜᖝᖡᖣᖨᖭ戾;쀀∾̳;房rc耻â䃢te肻´̆;䐰lig耻æ䃦Ā;r²ᖺ;쀀𝔞rave耻à䃠ĀepᗊᗖĀfpᗏᗔsym;愵èᗓha;䎱ĀapᗟcĀclᗤᗧr;䄁g;樿ɤᗰ\0\0ᘊʀ;adsvᗺᗻᗿᘁᘇ戧nd;橕;橜lope;橘;橚΀;elmrszᘘᘙᘛᘞᘿᙏᙙ戠;榤e»ᘙsdĀ;aᘥᘦ戡ѡᘰᘲᘴᘶᘸᘺᘼᘾ;榨;榩;榪;榫;榬;榭;榮;榯tĀ;vᙅᙆ戟bĀ;dᙌᙍ抾;榝Āptᙔᙗh;戢»¹arr;捼Āgpᙣᙧon;䄅f;쀀𝕒΀;Eaeiop዁ᙻᙽᚂᚄᚇᚊ;橰cir;橯;扊d;手s;䀧roxĀ;e዁ᚒñᚃing耻å䃥ƀctyᚡᚦᚨr;쀀𝒶;䀪mpĀ;e዁ᚯñʈilde耻ã䃣ml耻ä䃤Āciᛂᛈoninôɲnt;樑ࠀNabcdefiklnoprsu᛭ᛱᜰ᜼ᝃᝈ᝸᝽០៦ᠹᡐᜍ᤽᥈ᥰot;櫭Ācrᛶ᜞kȀcepsᜀᜅᜍᜓong;扌psilon;䏶rime;怵imĀ;e᜚᜛戽q;拍Ŷᜢᜦee;抽edĀ;gᜬᜭ挅e»ᜭrkĀ;t፜᜷brk;掶Āoyᜁᝁ;䐱quo;怞ʀcmprtᝓ᝛ᝡᝤᝨausĀ;eĊĉptyv;榰séᜌnoõēƀahwᝯ᝱ᝳ;䎲;愶een;扬r;쀀𝔟g΀costuvwឍឝឳេ៕៛៞ƀaiuបពរðݠrc;旯p»፱ƀdptឤឨឭot;樀lus;樁imes;樂ɱឹ\0\0ើcup;樆ar;昅riangleĀdu៍្own;施p;斳plus;樄eåᑄåᒭarow;植ƀako៭ᠦᠵĀcn៲ᠣkƀlst៺֫᠂ozenge;槫riangleȀ;dlr᠒᠓᠘᠝斴own;斾eft;旂ight;斸k;搣Ʊᠫ\0ᠳƲᠯ\0ᠱ;斒;斑4;斓ck;斈ĀeoᠾᡍĀ;qᡃᡆ쀀=⃥uiv;쀀≡⃥t;挐Ȁptwxᡙᡞᡧᡬf;쀀𝕓Ā;tᏋᡣom»Ꮜtie;拈؀DHUVbdhmptuvᢅᢖᢪᢻᣗᣛᣬ᣿ᤅᤊᤐᤡȀLRlrᢎᢐᢒᢔ;敗;敔;敖;敓ʀ;DUduᢡᢢᢤᢦᢨ敐;敦;敩;敤;敧ȀLRlrᢳᢵᢷᢹ;敝;敚;敜;教΀;HLRhlrᣊᣋᣍᣏᣑᣓᣕ救;敬;散;敠;敫;敢;敟ox;槉ȀLRlrᣤᣦᣨᣪ;敕;敒;攐;攌ʀ;DUduڽ᣷᣹᣻᣽;敥;敨;攬;攴inus;抟lus;択imes;抠ȀLRlrᤙᤛᤝ᤟;敛;敘;攘;攔΀;HLRhlrᤰᤱᤳᤵᤷ᤻᤹攂;敪;敡;敞;攼;攤;攜Āevģ᥂bar耻¦䂦Ȁceioᥑᥖᥚᥠr;쀀𝒷mi;恏mĀ;e᜚᜜lƀ;bhᥨᥩᥫ䁜;槅sub;柈Ŭᥴ᥾lĀ;e᥹᥺怢t»᥺pƀ;Eeįᦅᦇ;檮Ā;qۜۛೡᦧ\0᧨ᨑᨕᨲ\0ᨷᩐ\0\0᪴\0\0᫁\0\0ᬡᬮ᭍᭒\0᯽\0ᰌƀcpr᦭ᦲ᧝ute;䄇̀;abcdsᦿᧀᧄ᧊᧕᧙戩nd;橄rcup;橉Āau᧏᧒p;橋p;橇ot;橀;쀀∩︀Āeo᧢᧥t;恁îړȀaeiu᧰᧻ᨁᨅǰ᧵\0᧸s;橍on;䄍dil耻ç䃧rc;䄉psĀ;sᨌᨍ橌m;橐ot;䄋ƀdmnᨛᨠᨦil肻¸ƭptyv;榲t脀¢;eᨭᨮ䂢räƲr;쀀𝔠ƀceiᨽᩀᩍy;䑇ckĀ;mᩇᩈ朓ark»ᩈ;䏇r΀;Ecefms᩟᩠ᩢᩫ᪤᪪᪮旋;槃ƀ;elᩩᩪᩭ䋆q;扗eɡᩴ\0\0᪈rrowĀlr᩼᪁eft;憺ight;憻ʀRSacd᪒᪔᪖᪚᪟»ཇ;擈st;抛irc;抚ash;抝nint;樐id;櫯cir;槂ubsĀ;u᪻᪼晣it»᪼ˬ᫇᫔᫺\0ᬊonĀ;eᫍᫎ䀺Ā;qÇÆɭ᫙\0\0᫢aĀ;t᫞᫟䀬;䁀ƀ;fl᫨᫩᫫戁îᅠeĀmx᫱᫶ent»᫩eóɍǧ᫾\0ᬇĀ;dኻᬂot;橭nôɆƀfryᬐᬔᬗ;쀀𝕔oäɔ脀©;sŕᬝr;愗Āaoᬥᬩrr;憵ss;朗Ācuᬲᬷr;쀀𝒸Ābpᬼ᭄Ā;eᭁᭂ櫏;櫑Ā;eᭉᭊ櫐;櫒dot;拯΀delprvw᭠᭬᭷ᮂᮬᯔ᯹arrĀlr᭨᭪;椸;椵ɰ᭲\0\0᭵r;拞c;拟arrĀ;p᭿ᮀ憶;椽̀;bcdosᮏᮐᮖᮡᮥᮨ截rcap;橈Āauᮛᮞp;橆p;橊ot;抍r;橅;쀀∪︀Ȁalrv᮵ᮿᯞᯣrrĀ;mᮼᮽ憷;椼yƀevwᯇᯔᯘqɰᯎ\0\0ᯒreã᭳uã᭵ee;拎edge;拏en耻¤䂤earrowĀlrᯮ᯳eft»ᮀight»ᮽeäᯝĀciᰁᰇoninôǷnt;戱lcty;挭ঀAHabcdefhijlorstuwz᰸᰻᰿ᱝᱩᱵᲊᲞᲬᲷ᳻᳿ᴍᵻᶑᶫᶻ᷆᷍rò΁ar;楥Ȁglrs᱈ᱍ᱒᱔ger;怠eth;愸òᄳhĀ;vᱚᱛ怐»ऊūᱡᱧarow;椏aã̕Āayᱮᱳron;䄏;䐴ƀ;ao̲ᱼᲄĀgrʿᲁr;懊tseq;橷ƀglmᲑᲔᲘ耻°䂰ta;䎴ptyv;榱ĀirᲣᲨsht;楿;쀀𝔡arĀlrᲳᲵ»ࣜ»သʀaegsv᳂͸᳖᳜᳠mƀ;oș᳊᳔ndĀ;ș᳑uit;晦amma;䏝in;拲ƀ;io᳧᳨᳸䃷de脀÷;o᳧ᳰntimes;拇nø᳷cy;䑒cɯᴆ\0\0ᴊrn;挞op;挍ʀlptuwᴘᴝᴢᵉᵕlar;䀤f;쀀𝕕ʀ;emps̋ᴭᴷᴽᵂqĀ;d͒ᴳot;扑inus;戸lus;戔quare;抡blebarwedgåúnƀadhᄮᵝᵧownarrowóᲃarpoonĀlrᵲᵶefôᲴighôᲶŢᵿᶅkaro÷གɯᶊ\0\0ᶎrn;挟op;挌ƀcotᶘᶣᶦĀryᶝᶡ;쀀𝒹;䑕l;槶rok;䄑Ādrᶰᶴot;拱iĀ;fᶺ᠖斿Āah᷀᷃ròЩaòྦangle;榦Āci᷒ᷕy;䑟grarr;柿ऀDacdefglmnopqrstuxḁḉḙḸոḼṉṡṾấắẽỡἪἷὄ὎὚ĀDoḆᴴoôᲉĀcsḎḔute耻é䃩ter;橮ȀaioyḢḧḱḶron;䄛rĀ;cḭḮ扖耻ê䃪lon;払;䑍ot;䄗ĀDrṁṅot;扒;쀀𝔢ƀ;rsṐṑṗ檚ave耻è䃨Ā;dṜṝ檖ot;檘Ȁ;ilsṪṫṲṴ檙nters;揧;愓Ā;dṹṺ檕ot;檗ƀapsẅẉẗcr;䄓tyƀ;svẒẓẕ戅et»ẓpĀ1;ẝẤijạả;怄;怅怃ĀgsẪẬ;䅋p;怂ĀgpẴẸon;䄙f;쀀𝕖ƀalsỄỎỒrĀ;sỊị拕l;槣us;橱iƀ;lvỚớở䎵on»ớ;䏵ȀcsuvỪỳἋἣĀioữḱrc»Ḯɩỹ\0\0ỻíՈantĀglἂἆtr»ṝess»Ṻƀaeiἒ἖Ἒls;䀽st;扟vĀ;DȵἠD;橸parsl;槥ĀDaἯἳot;打rr;楱ƀcdiἾὁỸr;愯oô͒ĀahὉὋ;䎷耻ð䃰Āmrὓὗl耻ë䃫o;悬ƀcipὡὤὧl;䀡sôծĀeoὬὴctatioîՙnentialåչৡᾒ\0ᾞ\0ᾡᾧ\0\0ῆῌ\0ΐ\0ῦῪ \0 ⁚llingdotseñṄy;䑄male;晀ƀilrᾭᾳ῁lig;耀ffiɩᾹ\0\0᾽g;耀ffig;耀ffl;쀀𝔣lig;耀filig;쀀fjƀaltῙ῜ῡt;晭ig;耀flns;斱of;䆒ǰ΅\0ῳf;쀀𝕗ĀakֿῷĀ;vῼ´拔;櫙artint;樍Āao‌⁕Ācs‑⁒ႉ‸⁅⁈\0⁐β•‥‧‪‬\0‮耻½䂽;慓耻¼䂼;慕;慙;慛Ƴ‴\0‶;慔;慖ʴ‾⁁\0\0⁃耻¾䂾;慗;慜5;慘ƶ⁌\0⁎;慚;慝8;慞l;恄wn;挢cr;쀀𝒻ࢀEabcdefgijlnorstv₂₉₟₥₰₴⃰⃵⃺⃿℃ℒℸ̗ℾ⅒↞Ā;lٍ₇;檌ƀcmpₐₕ₝ute;䇵maĀ;dₜ᳚䎳;檆reve;䄟Āiy₪₮rc;䄝;䐳ot;䄡Ȁ;lqsؾق₽⃉ƀ;qsؾٌ⃄lanô٥Ȁ;cdl٥⃒⃥⃕c;檩otĀ;o⃜⃝檀Ā;l⃢⃣檂;檄Ā;e⃪⃭쀀⋛︀s;檔r;쀀𝔤Ā;gٳ؛mel;愷cy;䑓Ȁ;Eajٚℌℎℐ;檒;檥;檤ȀEaesℛℝ℩ℴ;扩pĀ;p℣ℤ檊rox»ℤĀ;q℮ℯ檈Ā;q℮ℛim;拧pf;쀀𝕘Āci⅃ⅆr;愊mƀ;el٫ⅎ⅐;檎;檐茀>;cdlqr׮ⅠⅪⅮⅳⅹĀciⅥⅧ;檧r;橺ot;拗Par;榕uest;橼ʀadelsↄⅪ←ٖ↛ǰ↉\0↎proø₞r;楸qĀlqؿ↖lesó₈ií٫Āen↣↭rtneqq;쀀≩︀Å↪ԀAabcefkosy⇄⇇⇱⇵⇺∘∝∯≨≽ròΠȀilmr⇐⇔⇗⇛rsðᒄf»․ilôکĀdr⇠⇤cy;䑊ƀ;cwࣴ⇫⇯ir;楈;憭ar;意irc;䄥ƀalr∁∎∓rtsĀ;u∉∊晥it»∊lip;怦con;抹r;쀀𝔥sĀew∣∩arow;椥arow;椦ʀamopr∺∾≃≞≣rr;懿tht;戻kĀlr≉≓eftarrow;憩ightarrow;憪f;쀀𝕙bar;怕ƀclt≯≴≸r;쀀𝒽asè⇴rok;䄧Ābp⊂⊇ull;恃hen»ᱛૡ⊣\0⊪\0⊸⋅⋎\0⋕⋳\0\0⋸⌢⍧⍢⍿\0⎆⎪⎴cute耻í䃭ƀ;iyݱ⊰⊵rc耻î䃮;䐸Ācx⊼⊿y;䐵cl耻¡䂡ĀfrΟ⋉;쀀𝔦rave耻ì䃬Ȁ;inoܾ⋝⋩⋮Āin⋢⋦nt;樌t;戭fin;槜ta;愩lig;䄳ƀaop⋾⌚⌝ƀcgt⌅⌈⌗r;䄫ƀelpܟ⌏⌓inåގarôܠh;䄱f;抷ed;䆵ʀ;cfotӴ⌬⌱⌽⍁are;愅inĀ;t⌸⌹戞ie;槝doô⌙ʀ;celpݗ⍌⍐⍛⍡al;抺Āgr⍕⍙eróᕣã⍍arhk;樗rod;樼Ȁcgpt⍯⍲⍶⍻y;䑑on;䄯f;쀀𝕚a;䎹uest耻¿䂿Āci⎊⎏r;쀀𝒾nʀ;EdsvӴ⎛⎝⎡ӳ;拹ot;拵Ā;v⎦⎧拴;拳Ā;iݷ⎮lde;䄩ǫ⎸\0⎼cy;䑖l耻ï䃯̀cfmosu⏌⏗⏜⏡⏧⏵Āiy⏑⏕rc;䄵;䐹r;쀀𝔧ath;䈷pf;쀀𝕛ǣ⏬\0⏱r;쀀𝒿rcy;䑘kcy;䑔Ѐacfghjos␋␖␢␧␭␱␵␻ppaĀ;v␓␔䎺;䏰Āey␛␠dil;䄷;䐺r;쀀𝔨reen;䄸cy;䑅cy;䑜pf;쀀𝕜cr;쀀𝓀஀ABEHabcdefghjlmnoprstuv⑰⒁⒆⒍⒑┎┽╚▀♎♞♥♹♽⚚⚲⛘❝❨➋⟀⠁⠒ƀart⑷⑺⑼rò৆òΕail;椛arr;椎Ā;gঔ⒋;檋ar;楢ॣ⒥\0⒪\0⒱\0\0\0\0\0⒵Ⓔ\0ⓆⓈⓍ\0⓹ute;䄺mptyv;榴raîࡌbda;䎻gƀ;dlࢎⓁⓃ;榑åࢎ;檅uo耻«䂫rЀ;bfhlpst࢙ⓞⓦⓩ⓫⓮⓱⓵Ā;f࢝ⓣs;椟s;椝ë≒p;憫l;椹im;楳l;憢ƀ;ae⓿─┄檫il;椙Ā;s┉┊檭;쀀⪭︀ƀabr┕┙┝rr;椌rk;杲Āak┢┬cĀek┨┪;䁻;䁛Āes┱┳;榋lĀdu┹┻;榏;榍Ȁaeuy╆╋╖╘ron;䄾Ādi═╔il;䄼ìࢰâ┩;䐻Ȁcqrs╣╦╭╽a;椶uoĀ;rนᝆĀdu╲╷har;楧shar;楋h;憲ʀ;fgqs▋▌উ◳◿扤tʀahlrt▘▤▷◂◨rrowĀ;t࢙□aé⓶arpoonĀdu▯▴own»њp»०eftarrows;懇ightƀahs◍◖◞rrowĀ;sࣴࢧarpoonó྘quigarro÷⇰hreetimes;拋ƀ;qs▋ও◺lanôবʀ;cdgsব☊☍☝☨c;檨otĀ;o☔☕橿Ā;r☚☛檁;檃Ā;e☢☥쀀⋚︀s;檓ʀadegs☳☹☽♉♋pproøⓆot;拖qĀgq♃♅ôউgtò⒌ôছiíলƀilr♕࣡♚sht;楼;쀀𝔩Ā;Eজ♣;檑š♩♶rĀdu▲♮Ā;l॥♳;楪lk;斄cy;䑙ʀ;achtੈ⚈⚋⚑⚖rò◁orneòᴈard;楫ri;旺Āio⚟⚤dot;䅀ustĀ;a⚬⚭掰che»⚭ȀEaes⚻⚽⛉⛔;扨pĀ;p⛃⛄檉rox»⛄Ā;q⛎⛏檇Ā;q⛎⚻im;拦Ѐabnoptwz⛩⛴⛷✚✯❁❇❐Ānr⛮⛱g;柬r;懽rëࣁgƀlmr⛿✍✔eftĀar০✇ightá৲apsto;柼ightá৽parrowĀlr✥✩efô⓭ight;憬ƀafl✶✹✽r;榅;쀀𝕝us;樭imes;樴š❋❏st;戗áፎƀ;ef❗❘᠀旊nge»❘arĀ;l❤❥䀨t;榓ʀachmt❳❶❼➅➇ròࢨorneòᶌarĀ;d྘➃;業;怎ri;抿̀achiqt➘➝ੀ➢➮➻quo;怹r;쀀𝓁mƀ;egল➪➬;檍;檏Ābu┪➳oĀ;rฟ➹;怚rok;䅂萀<;cdhilqrࠫ⟒☹⟜⟠⟥⟪⟰Āci⟗⟙;檦r;橹reå◲mes;拉arr;楶uest;橻ĀPi⟵⟹ar;榖ƀ;ef⠀भ᠛旃rĀdu⠇⠍shar;楊har;楦Āen⠗⠡rtneqq;쀀≨︀Å⠞܀Dacdefhilnopsu⡀⡅⢂⢎⢓⢠⢥⢨⣚⣢⣤ઃ⣳⤂Dot;戺Ȁclpr⡎⡒⡣⡽r耻¯䂯Āet⡗⡙;時Ā;e⡞⡟朠se»⡟Ā;sျ⡨toȀ;dluျ⡳⡷⡻owîҌefôएðᏑker;斮Āoy⢇⢌mma;権;䐼ash;怔asuredangle»ᘦr;쀀𝔪o;愧ƀcdn⢯⢴⣉ro耻µ䂵Ȁ;acdᑤ⢽⣀⣄sôᚧir;櫰ot肻·Ƶusƀ;bd⣒ᤃ⣓戒Ā;uᴼ⣘;横ţ⣞⣡p;櫛ò−ðઁĀdp⣩⣮els;抧f;쀀𝕞Āct⣸⣽r;쀀𝓂pos»ᖝƀ;lm⤉⤊⤍䎼timap;抸ఀGLRVabcdefghijlmoprstuvw⥂⥓⥾⦉⦘⧚⧩⨕⨚⩘⩝⪃⪕⪤⪨⬄⬇⭄⭿⮮ⰴⱧⱼ⳩Āgt⥇⥋;쀀⋙̸Ā;v⥐௏쀀≫⃒ƀelt⥚⥲⥶ftĀar⥡⥧rrow;懍ightarrow;懎;쀀⋘̸Ā;v⥻ే쀀≪⃒ightarrow;懏ĀDd⦎⦓ash;抯ash;抮ʀbcnpt⦣⦧⦬⦱⧌la»˞ute;䅄g;쀀∠⃒ʀ;Eiop඄⦼⧀⧅⧈;쀀⩰̸d;쀀≋̸s;䅉roø඄urĀ;a⧓⧔普lĀ;s⧓ସdz⧟\0⧣p肻 ଷmpĀ;e௹ఀʀaeouy⧴⧾⨃⨐⨓ǰ⧹\0⧻;橃on;䅈dil;䅆ngĀ;dൾ⨊ot;쀀⩭̸p;橂;䐽ash;怓΀;Aadqsxஒ⨩⨭⨻⩁⩅⩐rr;懗rĀhr⨳⨶k;椤Ā;oᏲᏰot;쀀≐̸uiöୣĀei⩊⩎ar;椨í஘istĀ;s஠டr;쀀𝔫ȀEest௅⩦⩹⩼ƀ;qs஼⩭௡ƀ;qs஼௅⩴lanô௢ií௪Ā;rஶ⪁»ஷƀAap⪊⪍⪑rò⥱rr;憮ar;櫲ƀ;svྍ⪜ྌĀ;d⪡⪢拼;拺cy;䑚΀AEadest⪷⪺⪾⫂⫅⫶⫹rò⥦;쀀≦̸rr;憚r;急Ȁ;fqs఻⫎⫣⫯tĀar⫔⫙rro÷⫁ightarro÷⪐ƀ;qs఻⪺⫪lanôౕĀ;sౕ⫴»శiíౝĀ;rవ⫾iĀ;eచథiäඐĀpt⬌⬑f;쀀𝕟膀¬;in⬙⬚⬶䂬nȀ;Edvஉ⬤⬨⬮;쀀⋹̸ot;쀀⋵̸ǡஉ⬳⬵;拷;拶iĀ;vಸ⬼ǡಸ⭁⭃;拾;拽ƀaor⭋⭣⭩rȀ;ast୻⭕⭚⭟lleì୻l;쀀⫽⃥;쀀∂̸lint;樔ƀ;ceಒ⭰⭳uåಥĀ;cಘ⭸Ā;eಒ⭽ñಘȀAait⮈⮋⮝⮧rò⦈rrƀ;cw⮔⮕⮙憛;쀀⤳̸;쀀↝̸ghtarrow»⮕riĀ;eೋೖ΀chimpqu⮽⯍⯙⬄୸⯤⯯Ȁ;cerല⯆ഷ⯉uå൅;쀀𝓃ortɭ⬅\0\0⯖ará⭖mĀ;e൮⯟Ā;q൴൳suĀbp⯫⯭å೸åഋƀbcp⯶ⰑⰙȀ;Ees⯿ⰀഢⰄ抄;쀀⫅̸etĀ;eഛⰋqĀ;qണⰀcĀ;eലⰗñസȀ;EesⰢⰣൟⰧ抅;쀀⫆̸etĀ;e൘ⰮqĀ;qൠⰣȀgilrⰽⰿⱅⱇìௗlde耻ñ䃱çృiangleĀlrⱒⱜeftĀ;eచⱚñదightĀ;eೋⱥñ೗Ā;mⱬⱭ䎽ƀ;esⱴⱵⱹ䀣ro;愖p;怇ҀDHadgilrsⲏⲔⲙⲞⲣⲰⲶⳓⳣash;抭arr;椄p;쀀≍⃒ash;抬ĀetⲨⲬ;쀀≥⃒;쀀>⃒nfin;槞ƀAetⲽⳁⳅrr;椂;쀀≤⃒Ā;rⳊⳍ쀀<⃒ie;쀀⊴⃒ĀAtⳘⳜrr;椃rie;쀀⊵⃒im;쀀∼⃒ƀAan⳰⳴ⴂrr;懖rĀhr⳺⳽k;椣Ā;oᏧᏥear;椧ቓ᪕\0\0\0\0\0\0\0\0\0\0\0\0\0ⴭ\0ⴸⵈⵠⵥ⵲ⶄᬇ\0\0ⶍⶫ\0ⷈⷎ\0ⷜ⸙⸫⸾⹃Ācsⴱ᪗ute耻ó䃳ĀiyⴼⵅrĀ;c᪞ⵂ耻ô䃴;䐾ʀabios᪠ⵒⵗLjⵚlac;䅑v;樸old;榼lig;䅓Ācr⵩⵭ir;榿;쀀𝔬ͯ⵹\0\0⵼\0ⶂn;䋛ave耻ò䃲;槁Ābmⶈ෴ar;榵Ȁacitⶕ⶘ⶥⶨrò᪀Āir⶝ⶠr;榾oss;榻nå๒;槀ƀaeiⶱⶵⶹcr;䅍ga;䏉ƀcdnⷀⷅǍron;䎿;榶pf;쀀𝕠ƀaelⷔ⷗ǒr;榷rp;榹΀;adiosvⷪⷫⷮ⸈⸍⸐⸖戨rò᪆Ȁ;efmⷷⷸ⸂⸅橝rĀ;oⷾⷿ愴f»ⷿ耻ª䂪耻º䂺gof;抶r;橖lope;橗;橛ƀclo⸟⸡⸧ò⸁ash耻ø䃸l;折iŬⸯ⸴de耻õ䃵esĀ;aǛ⸺s;樶ml耻ö䃶bar;挽ૡ⹞\0⹽\0⺀⺝\0⺢⺹\0\0⻋ຜ\0⼓\0\0⼫⾼\0⿈rȀ;astЃ⹧⹲຅脀¶;l⹭⹮䂶leìЃɩ⹸\0\0⹻m;櫳;櫽y;䐿rʀcimpt⺋⺏⺓ᡥ⺗nt;䀥od;䀮il;怰enk;怱r;쀀𝔭ƀimo⺨⺰⺴Ā;v⺭⺮䏆;䏕maô੶ne;明ƀ;tv⺿⻀⻈䏀chfork»´;䏖Āau⻏⻟nĀck⻕⻝kĀ;h⇴⻛;愎ö⇴sҀ;abcdemst⻳⻴ᤈ⻹⻽⼄⼆⼊⼎䀫cir;樣ir;樢Āouᵀ⼂;樥;橲n肻±ຝim;樦wo;樧ƀipu⼙⼠⼥ntint;樕f;쀀𝕡nd耻£䂣Ԁ;Eaceinosu່⼿⽁⽄⽇⾁⾉⾒⽾⾶;檳p;檷uå໙Ā;c໎⽌̀;acens່⽙⽟⽦⽨⽾pproø⽃urlyeñ໙ñ໎ƀaes⽯⽶⽺pprox;檹qq;檵im;拨iíໟmeĀ;s⾈ຮ怲ƀEas⽸⾐⽺ð⽵ƀdfp໬⾙⾯ƀals⾠⾥⾪lar;挮ine;挒urf;挓Ā;t໻⾴ï໻rel;抰Āci⿀⿅r;쀀𝓅;䏈ncsp;怈̀fiopsu⿚⋢⿟⿥⿫⿱r;쀀𝔮pf;쀀𝕢rime;恗cr;쀀𝓆ƀaeo⿸〉〓tĀei⿾々rnionóڰnt;樖stĀ;e【】䀿ñἙô༔઀ABHabcdefhilmnoprstux぀けさすムㄎㄫㅇㅢㅲㆎ㈆㈕㈤㈩㉘㉮㉲㊐㊰㊷ƀartぇおがròႳòϝail;検aròᱥar;楤΀cdenqrtとふへみわゔヌĀeuねぱ;쀀∽̱te;䅕iãᅮmptyv;榳gȀ;del࿑らるろ;榒;榥å࿑uo耻»䂻rր;abcfhlpstw࿜ガクシスゼゾダッデナp;極Ā;f࿠ゴs;椠;椳s;椞ë≝ð✮l;楅im;楴l;憣;憝Āaiパフil;椚oĀ;nホボ戶aló༞ƀabrョリヮrò៥rk;杳ĀakンヽcĀekヹ・;䁽;䁝Āes㄂㄄;榌lĀduㄊㄌ;榎;榐Ȁaeuyㄗㄜㄧㄩron;䅙Ādiㄡㄥil;䅗ì࿲âヺ;䑀Ȁclqsㄴㄷㄽㅄa;椷dhar;楩uoĀ;rȎȍh;憳ƀacgㅎㅟངlȀ;ipsླྀㅘㅛႜnåႻarôྩt;断ƀilrㅩဣㅮsht;楽;쀀𝔯ĀaoㅷㆆrĀduㅽㅿ»ѻĀ;l႑ㆄ;楬Ā;vㆋㆌ䏁;䏱ƀgns㆕ㇹㇼht̀ahlrstㆤㆰ㇂㇘㇤㇮rrowĀ;t࿜ㆭaéトarpoonĀduㆻㆿowîㅾp»႒eftĀah㇊㇐rrowó࿪arpoonóՑightarrows;應quigarro÷ニhreetimes;拌g;䋚ingdotseñἲƀahm㈍㈐㈓rò࿪aòՑ;怏oustĀ;a㈞㈟掱che»㈟mid;櫮Ȁabpt㈲㈽㉀㉒Ānr㈷㈺g;柭r;懾rëဃƀafl㉇㉊㉎r;榆;쀀𝕣us;樮imes;樵Āap㉝㉧rĀ;g㉣㉤䀩t;榔olint;樒arò㇣Ȁachq㉻㊀Ⴜ㊅quo;怺r;쀀𝓇Ābu・㊊oĀ;rȔȓƀhir㊗㊛㊠reåㇸmes;拊iȀ;efl㊪ၙᠡ㊫方tri;槎luhar;楨;愞ൡ㋕㋛㋟㌬㌸㍱\0㍺㎤\0\0㏬㏰\0㐨㑈㑚㒭㒱㓊㓱\0㘖\0\0㘳cute;䅛quï➺Ԁ;Eaceinpsyᇭ㋳㋵㋿㌂㌋㌏㌟㌦㌩;檴ǰ㋺\0㋼;檸on;䅡uåᇾĀ;dᇳ㌇il;䅟rc;䅝ƀEas㌖㌘㌛;檶p;檺im;择olint;樓iíሄ;䑁otƀ;be㌴ᵇ㌵担;橦΀Aacmstx㍆㍊㍗㍛㍞㍣㍭rr;懘rĀhr㍐㍒ë∨Ā;oਸ਼਴t耻§䂧i;䀻war;椩mĀin㍩ðnuóñt;朶rĀ;o㍶⁕쀀𝔰Ȁacoy㎂㎆㎑㎠rp;景Āhy㎋㎏cy;䑉;䑈rtɭ㎙\0\0㎜iäᑤaraì⹯耻­䂭Āgm㎨㎴maƀ;fv㎱㎲㎲䏃;䏂Ѐ;deglnprካ㏅㏉㏎㏖㏞㏡㏦ot;橪Ā;q኱ኰĀ;E㏓㏔檞;檠Ā;E㏛㏜檝;檟e;扆lus;樤arr;楲aròᄽȀaeit㏸㐈㐏㐗Āls㏽㐄lsetmé㍪hp;樳parsl;槤Ādlᑣ㐔e;挣Ā;e㐜㐝檪Ā;s㐢㐣檬;쀀⪬︀ƀflp㐮㐳㑂tcy;䑌Ā;b㐸㐹䀯Ā;a㐾㐿槄r;挿f;쀀𝕤aĀdr㑍ЂesĀ;u㑔㑕晠it»㑕ƀcsu㑠㑹㒟Āau㑥㑯pĀ;sᆈ㑫;쀀⊓︀pĀ;sᆴ㑵;쀀⊔︀uĀbp㑿㒏ƀ;esᆗᆜ㒆etĀ;eᆗ㒍ñᆝƀ;esᆨᆭ㒖etĀ;eᆨ㒝ñᆮƀ;afᅻ㒦ְrť㒫ֱ»ᅼaròᅈȀcemt㒹㒾㓂㓅r;쀀𝓈tmîñiì㐕aræᆾĀar㓎㓕rĀ;f㓔ឿ昆Āan㓚㓭ightĀep㓣㓪psiloîỠhé⺯s»⡒ʀbcmnp㓻㕞ሉ㖋㖎Ҁ;Edemnprs㔎㔏㔑㔕㔞㔣㔬㔱㔶抂;櫅ot;檽Ā;dᇚ㔚ot;櫃ult;櫁ĀEe㔨㔪;櫋;把lus;檿arr;楹ƀeiu㔽㕒㕕tƀ;en㔎㕅㕋qĀ;qᇚ㔏eqĀ;q㔫㔨m;櫇Ābp㕚㕜;櫕;櫓c̀;acensᇭ㕬㕲㕹㕻㌦pproø㋺urlyeñᇾñᇳƀaes㖂㖈㌛pproø㌚qñ㌗g;晪ڀ123;Edehlmnps㖩㖬㖯ሜ㖲㖴㗀㗉㗕㗚㗟㗨㗭耻¹䂹耻²䂲耻³䂳;櫆Āos㖹㖼t;檾ub;櫘Ā;dሢ㗅ot;櫄sĀou㗏㗒l;柉b;櫗arr;楻ult;櫂ĀEe㗤㗦;櫌;抋lus;櫀ƀeiu㗴㘉㘌tƀ;enሜ㗼㘂qĀ;qሢ㖲eqĀ;q㗧㗤m;櫈Ābp㘑㘓;櫔;櫖ƀAan㘜㘠㘭rr;懙rĀhr㘦㘨ë∮Ā;oਫ਩war;椪lig耻ß䃟௡㙑㙝㙠ዎ㙳㙹\0㙾㛂\0\0\0\0\0㛛㜃\0㜉㝬\0\0\0㞇ɲ㙖\0\0㙛get;挖;䏄rë๟ƀaey㙦㙫㙰ron;䅥dil;䅣;䑂lrec;挕r;쀀𝔱Ȁeiko㚆㚝㚵㚼Dz㚋\0㚑eĀ4fኄኁaƀ;sv㚘㚙㚛䎸ym;䏑Ācn㚢㚲kĀas㚨㚮pproø዁im»ኬsðኞĀas㚺㚮ð዁rn耻þ䃾Ǭ̟㛆⋧es膀×;bd㛏㛐㛘䃗Ā;aᤏ㛕r;樱;樰ƀeps㛡㛣㜀á⩍Ȁ;bcf҆㛬㛰㛴ot;挶ir;櫱Ā;o㛹㛼쀀𝕥rk;櫚á㍢rime;怴ƀaip㜏㜒㝤dåቈ΀adempst㜡㝍㝀㝑㝗㝜㝟ngleʀ;dlqr㜰㜱㜶㝀㝂斵own»ᶻeftĀ;e⠀㜾ñम;扜ightĀ;e㊪㝋ñၚot;旬inus;樺lus;樹b;槍ime;樻ezium;揢ƀcht㝲㝽㞁Āry㝷㝻;쀀𝓉;䑆cy;䑛rok;䅧Āio㞋㞎xô᝷headĀlr㞗㞠eftarro÷ࡏightarrow»ཝऀAHabcdfghlmoprstuw㟐㟓㟗㟤㟰㟼㠎㠜㠣㠴㡑㡝㡫㢩㣌㣒㣪㣶ròϭar;楣Ācr㟜㟢ute耻ú䃺òᅐrǣ㟪\0㟭y;䑞ve;䅭Āiy㟵㟺rc耻û䃻;䑃ƀabh㠃㠆㠋ròᎭlac;䅱aòᏃĀir㠓㠘sht;楾;쀀𝔲rave耻ù䃹š㠧㠱rĀlr㠬㠮»ॗ»ႃlk;斀Āct㠹㡍ɯ㠿\0\0㡊rnĀ;e㡅㡆挜r»㡆op;挏ri;旸Āal㡖㡚cr;䅫肻¨͉Āgp㡢㡦on;䅳f;쀀𝕦̀adhlsuᅋ㡸㡽፲㢑㢠ownáᎳarpoonĀlr㢈㢌efô㠭ighô㠯iƀ;hl㢙㢚㢜䏅»ᏺon»㢚parrows;懈ƀcit㢰㣄㣈ɯ㢶\0\0㣁rnĀ;e㢼㢽挝r»㢽op;挎ng;䅯ri;旹cr;쀀𝓊ƀdir㣙㣝㣢ot;拰lde;䅩iĀ;f㜰㣨»᠓Āam㣯㣲rò㢨l耻ü䃼angle;榧ހABDacdeflnoprsz㤜㤟㤩㤭㦵㦸㦽㧟㧤㧨㧳㧹㧽㨁㨠ròϷarĀ;v㤦㤧櫨;櫩asèϡĀnr㤲㤷grt;榜΀eknprst㓣㥆㥋㥒㥝㥤㦖appá␕othinçẖƀhir㓫⻈㥙opô⾵Ā;hᎷ㥢ïㆍĀiu㥩㥭gmá㎳Ābp㥲㦄setneqĀ;q㥽㦀쀀⊊︀;쀀⫋︀setneqĀ;q㦏㦒쀀⊋︀;쀀⫌︀Āhr㦛㦟etá㚜iangleĀlr㦪㦯eft»थight»ၑy;䐲ash»ံƀelr㧄㧒㧗ƀ;beⷪ㧋㧏ar;抻q;扚lip;拮Ābt㧜ᑨaòᑩr;쀀𝔳tré㦮suĀbp㧯㧱»ജ»൙pf;쀀𝕧roð໻tré㦴Ācu㨆㨋r;쀀𝓋Ābp㨐㨘nĀEe㦀㨖»㥾nĀEe㦒㨞»㦐igzag;榚΀cefoprs㨶㨻㩖㩛㩔㩡㩪irc;䅵Ādi㩀㩑Ābg㩅㩉ar;機eĀ;qᗺ㩏;扙erp;愘r;쀀𝔴pf;쀀𝕨Ā;eᑹ㩦atèᑹcr;쀀𝓌ૣណ㪇\0㪋\0㪐㪛\0\0㪝㪨㪫㪯\0\0㫃㫎\0㫘ៜ៟tré៑r;쀀𝔵ĀAa㪔㪗ròσrò৶;䎾ĀAa㪡㪤ròθrò৫að✓is;拻ƀdptឤ㪵㪾Āfl㪺ឩ;쀀𝕩imåឲĀAa㫇㫊ròώròਁĀcq㫒ីr;쀀𝓍Āpt៖㫜ré។Ѐacefiosu㫰㫽㬈㬌㬑㬕㬛㬡cĀuy㫶㫻te耻ý䃽;䑏Āiy㬂㬆rc;䅷;䑋n耻¥䂥r;쀀𝔶cy;䑗pf;쀀𝕪cr;쀀𝓎Ācm㬦㬩y;䑎l耻ÿ䃿Ԁacdefhiosw㭂㭈㭔㭘㭤㭩㭭㭴㭺㮀cute;䅺Āay㭍㭒ron;䅾;䐷ot;䅼Āet㭝㭡træᕟa;䎶r;쀀𝔷cy;䐶grarr;懝pf;쀀𝕫cr;쀀𝓏Ājn㮅㮇;怍j;怌'.split("").map((c) => c.charCodeAt(0)) +); +const xmlDecodeTree = new Uint16Array( + // prettier-ignore + "Ȁaglq \x1Bɭ\0\0p;䀦os;䀧t;䀾t;䀼uot;䀢".split("").map((c) => c.charCodeAt(0)) +); +var _a; +const decodeMap = /* @__PURE__ */ new Map([ + [0, 65533], + // C1 Unicode control character reference replacements + [128, 8364], + [130, 8218], + [131, 402], + [132, 8222], + [133, 8230], + [134, 8224], + [135, 8225], + [136, 710], + [137, 8240], + [138, 352], + [139, 8249], + [140, 338], + [142, 381], + [145, 8216], + [146, 8217], + [147, 8220], + [148, 8221], + [149, 8226], + [150, 8211], + [151, 8212], + [152, 732], + [153, 8482], + [154, 353], + [155, 8250], + [156, 339], + [158, 382], + [159, 376] +]); +const fromCodePoint = ( + // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition, node/no-unsupported-features/es-builtins + (_a = String.fromCodePoint) !== null && _a !== void 0 ? _a : function(codePoint) { + let output = ""; + if (codePoint > 65535) { + codePoint -= 65536; + output += String.fromCharCode(codePoint >>> 10 & 1023 | 55296); + codePoint = 56320 | codePoint & 1023; + } + output += String.fromCharCode(codePoint); + return output; + } +); +function replaceCodePoint(codePoint) { + var _a2; + if (codePoint >= 55296 && codePoint <= 57343 || codePoint > 1114111) { + return 65533; + } + return (_a2 = decodeMap.get(codePoint)) !== null && _a2 !== void 0 ? _a2 : codePoint; +} +var CharCodes$1; +(function(CharCodes2) { + CharCodes2[CharCodes2["NUM"] = 35] = "NUM"; + CharCodes2[CharCodes2["SEMI"] = 59] = "SEMI"; + CharCodes2[CharCodes2["EQUALS"] = 61] = "EQUALS"; + CharCodes2[CharCodes2["ZERO"] = 48] = "ZERO"; + CharCodes2[CharCodes2["NINE"] = 57] = "NINE"; + CharCodes2[CharCodes2["LOWER_A"] = 97] = "LOWER_A"; + CharCodes2[CharCodes2["LOWER_F"] = 102] = "LOWER_F"; + CharCodes2[CharCodes2["LOWER_X"] = 120] = "LOWER_X"; + CharCodes2[CharCodes2["LOWER_Z"] = 122] = "LOWER_Z"; + CharCodes2[CharCodes2["UPPER_A"] = 65] = "UPPER_A"; + CharCodes2[CharCodes2["UPPER_F"] = 70] = "UPPER_F"; + CharCodes2[CharCodes2["UPPER_Z"] = 90] = "UPPER_Z"; +})(CharCodes$1 || (CharCodes$1 = {})); +const TO_LOWER_BIT = 32; +var BinTrieFlags; +(function(BinTrieFlags2) { + BinTrieFlags2[BinTrieFlags2["VALUE_LENGTH"] = 49152] = "VALUE_LENGTH"; + BinTrieFlags2[BinTrieFlags2["BRANCH_LENGTH"] = 16256] = "BRANCH_LENGTH"; + BinTrieFlags2[BinTrieFlags2["JUMP_TABLE"] = 127] = "JUMP_TABLE"; +})(BinTrieFlags || (BinTrieFlags = {})); +function isNumber(code) { + return code >= CharCodes$1.ZERO && code <= CharCodes$1.NINE; +} +function isHexadecimalCharacter(code) { + return code >= CharCodes$1.UPPER_A && code <= CharCodes$1.UPPER_F || code >= CharCodes$1.LOWER_A && code <= CharCodes$1.LOWER_F; +} +function isAsciiAlphaNumeric(code) { + return code >= CharCodes$1.UPPER_A && code <= CharCodes$1.UPPER_Z || code >= CharCodes$1.LOWER_A && code <= CharCodes$1.LOWER_Z || isNumber(code); +} +function isEntityInAttributeInvalidEnd(code) { + return code === CharCodes$1.EQUALS || isAsciiAlphaNumeric(code); +} +var EntityDecoderState; +(function(EntityDecoderState2) { + EntityDecoderState2[EntityDecoderState2["EntityStart"] = 0] = "EntityStart"; + EntityDecoderState2[EntityDecoderState2["NumericStart"] = 1] = "NumericStart"; + EntityDecoderState2[EntityDecoderState2["NumericDecimal"] = 2] = "NumericDecimal"; + EntityDecoderState2[EntityDecoderState2["NumericHex"] = 3] = "NumericHex"; + EntityDecoderState2[EntityDecoderState2["NamedEntity"] = 4] = "NamedEntity"; +})(EntityDecoderState || (EntityDecoderState = {})); +var DecodingMode; +(function(DecodingMode2) { + DecodingMode2[DecodingMode2["Legacy"] = 0] = "Legacy"; + DecodingMode2[DecodingMode2["Strict"] = 1] = "Strict"; + DecodingMode2[DecodingMode2["Attribute"] = 2] = "Attribute"; +})(DecodingMode || (DecodingMode = {})); +class EntityDecoder { + constructor(decodeTree, emitCodePoint, errors) { + this.decodeTree = decodeTree; + this.emitCodePoint = emitCodePoint; + this.errors = errors; + this.state = EntityDecoderState.EntityStart; + this.consumed = 1; + this.result = 0; + this.treeIndex = 0; + this.excess = 1; + this.decodeMode = DecodingMode.Strict; + } + /** Resets the instance to make it reusable. */ + startEntity(decodeMode) { + this.decodeMode = decodeMode; + this.state = EntityDecoderState.EntityStart; + this.result = 0; + this.treeIndex = 0; + this.excess = 1; + this.consumed = 1; + } + /** + * Write an entity to the decoder. This can be called multiple times with partial entities. + * If the entity is incomplete, the decoder will return -1. + * + * Mirrors the implementation of `getDecoder`, but with the ability to stop decoding if the + * entity is incomplete, and resume when the next string is written. + * + * @param string The string containing the entity (or a continuation of the entity). + * @param offset The offset at which the entity begins. Should be 0 if this is not the first call. + * @returns The number of characters that were consumed, or -1 if the entity is incomplete. + */ + write(str, offset) { + switch (this.state) { + case EntityDecoderState.EntityStart: { + if (str.charCodeAt(offset) === CharCodes$1.NUM) { + this.state = EntityDecoderState.NumericStart; + this.consumed += 1; + return this.stateNumericStart(str, offset + 1); + } + this.state = EntityDecoderState.NamedEntity; + return this.stateNamedEntity(str, offset); + } + case EntityDecoderState.NumericStart: { + return this.stateNumericStart(str, offset); + } + case EntityDecoderState.NumericDecimal: { + return this.stateNumericDecimal(str, offset); + } + case EntityDecoderState.NumericHex: { + return this.stateNumericHex(str, offset); + } + case EntityDecoderState.NamedEntity: { + return this.stateNamedEntity(str, offset); + } + } + } + /** + * Switches between the numeric decimal and hexadecimal states. + * + * Equivalent to the `Numeric character reference state` in the HTML spec. + * + * @param str The string containing the entity (or a continuation of the entity). + * @param offset The current offset. + * @returns The number of characters that were consumed, or -1 if the entity is incomplete. + */ + stateNumericStart(str, offset) { + if (offset >= str.length) { + return -1; + } + if ((str.charCodeAt(offset) | TO_LOWER_BIT) === CharCodes$1.LOWER_X) { + this.state = EntityDecoderState.NumericHex; + this.consumed += 1; + return this.stateNumericHex(str, offset + 1); + } + this.state = EntityDecoderState.NumericDecimal; + return this.stateNumericDecimal(str, offset); + } + addToNumericResult(str, start, end2, base) { + if (start !== end2) { + const digitCount = end2 - start; + this.result = this.result * Math.pow(base, digitCount) + parseInt(str.substr(start, digitCount), base); + this.consumed += digitCount; + } + } + /** + * Parses a hexadecimal numeric entity. + * + * Equivalent to the `Hexademical character reference state` in the HTML spec. + * + * @param str The string containing the entity (or a continuation of the entity). + * @param offset The current offset. + * @returns The number of characters that were consumed, or -1 if the entity is incomplete. + */ + stateNumericHex(str, offset) { + const startIdx = offset; + while (offset < str.length) { + const char = str.charCodeAt(offset); + if (isNumber(char) || isHexadecimalCharacter(char)) { + offset += 1; + } else { + this.addToNumericResult(str, startIdx, offset, 16); + return this.emitNumericEntity(char, 3); + } + } + this.addToNumericResult(str, startIdx, offset, 16); + return -1; + } + /** + * Parses a decimal numeric entity. + * + * Equivalent to the `Decimal character reference state` in the HTML spec. + * + * @param str The string containing the entity (or a continuation of the entity). + * @param offset The current offset. + * @returns The number of characters that were consumed, or -1 if the entity is incomplete. + */ + stateNumericDecimal(str, offset) { + const startIdx = offset; + while (offset < str.length) { + const char = str.charCodeAt(offset); + if (isNumber(char)) { + offset += 1; + } else { + this.addToNumericResult(str, startIdx, offset, 10); + return this.emitNumericEntity(char, 2); + } + } + this.addToNumericResult(str, startIdx, offset, 10); + return -1; + } + /** + * Validate and emit a numeric entity. + * + * Implements the logic from the `Hexademical character reference start + * state` and `Numeric character reference end state` in the HTML spec. + * + * @param lastCp The last code point of the entity. Used to see if the + * entity was terminated with a semicolon. + * @param expectedLength The minimum number of characters that should be + * consumed. Used to validate that at least one digit + * was consumed. + * @returns The number of characters that were consumed. + */ + emitNumericEntity(lastCp, expectedLength) { + var _a2; + if (this.consumed <= expectedLength) { + (_a2 = this.errors) === null || _a2 === void 0 ? void 0 : _a2.absenceOfDigitsInNumericCharacterReference(this.consumed); + return 0; + } + if (lastCp === CharCodes$1.SEMI) { + this.consumed += 1; + } else if (this.decodeMode === DecodingMode.Strict) { + return 0; + } + this.emitCodePoint(replaceCodePoint(this.result), this.consumed); + if (this.errors) { + if (lastCp !== CharCodes$1.SEMI) { + this.errors.missingSemicolonAfterCharacterReference(); + } + this.errors.validateNumericCharacterReference(this.result); + } + return this.consumed; + } + /** + * Parses a named entity. + * + * Equivalent to the `Named character reference state` in the HTML spec. + * + * @param str The string containing the entity (or a continuation of the entity). + * @param offset The current offset. + * @returns The number of characters that were consumed, or -1 if the entity is incomplete. + */ + stateNamedEntity(str, offset) { + const { decodeTree } = this; + let current = decodeTree[this.treeIndex]; + let valueLength = (current & BinTrieFlags.VALUE_LENGTH) >> 14; + for (; offset < str.length; offset++, this.excess++) { + const char = str.charCodeAt(offset); + this.treeIndex = determineBranch(decodeTree, current, this.treeIndex + Math.max(1, valueLength), char); + if (this.treeIndex < 0) { + return this.result === 0 || // If we are parsing an attribute + this.decodeMode === DecodingMode.Attribute && // We shouldn't have consumed any characters after the entity, + (valueLength === 0 || // And there should be no invalid characters. + isEntityInAttributeInvalidEnd(char)) ? 0 : this.emitNotTerminatedNamedEntity(); + } + current = decodeTree[this.treeIndex]; + valueLength = (current & BinTrieFlags.VALUE_LENGTH) >> 14; + if (valueLength !== 0) { + if (char === CharCodes$1.SEMI) { + return this.emitNamedEntityData(this.treeIndex, valueLength, this.consumed + this.excess); + } + if (this.decodeMode !== DecodingMode.Strict) { + this.result = this.treeIndex; + this.consumed += this.excess; + this.excess = 0; + } + } + } + return -1; + } + /** + * Emit a named entity that was not terminated with a semicolon. + * + * @returns The number of characters consumed. + */ + emitNotTerminatedNamedEntity() { + var _a2; + const { result, decodeTree } = this; + const valueLength = (decodeTree[result] & BinTrieFlags.VALUE_LENGTH) >> 14; + this.emitNamedEntityData(result, valueLength, this.consumed); + (_a2 = this.errors) === null || _a2 === void 0 ? void 0 : _a2.missingSemicolonAfterCharacterReference(); + return this.consumed; + } + /** + * Emit a named entity. + * + * @param result The index of the entity in the decode tree. + * @param valueLength The number of bytes in the entity. + * @param consumed The number of characters consumed. + * + * @returns The number of characters consumed. + */ + emitNamedEntityData(result, valueLength, consumed) { + const { decodeTree } = this; + this.emitCodePoint(valueLength === 1 ? decodeTree[result] & ~BinTrieFlags.VALUE_LENGTH : decodeTree[result + 1], consumed); + if (valueLength === 3) { + this.emitCodePoint(decodeTree[result + 2], consumed); + } + return consumed; + } + /** + * Signal to the parser that the end of the input was reached. + * + * Remaining data will be emitted and relevant errors will be produced. + * + * @returns The number of characters consumed. + */ + end() { + var _a2; + switch (this.state) { + case EntityDecoderState.NamedEntity: { + return this.result !== 0 && (this.decodeMode !== DecodingMode.Attribute || this.result === this.treeIndex) ? this.emitNotTerminatedNamedEntity() : 0; + } + // Otherwise, emit a numeric entity if we have one. + case EntityDecoderState.NumericDecimal: { + return this.emitNumericEntity(0, 2); + } + case EntityDecoderState.NumericHex: { + return this.emitNumericEntity(0, 3); + } + case EntityDecoderState.NumericStart: { + (_a2 = this.errors) === null || _a2 === void 0 ? void 0 : _a2.absenceOfDigitsInNumericCharacterReference(this.consumed); + return 0; + } + case EntityDecoderState.EntityStart: { + return 0; + } + } + } +} +function getDecoder(decodeTree) { + let ret = ""; + const decoder = new EntityDecoder(decodeTree, (str) => ret += fromCodePoint(str)); + return function decodeWithTrie(str, decodeMode) { + let lastIndex = 0; + let offset = 0; + while ((offset = str.indexOf("&", offset)) >= 0) { + ret += str.slice(lastIndex, offset); + decoder.startEntity(decodeMode); + const len = decoder.write( + str, + // Skip the "&" + offset + 1 + ); + if (len < 0) { + lastIndex = offset + decoder.end(); + break; + } + lastIndex = offset + len; + offset = len === 0 ? lastIndex + 1 : lastIndex; + } + const result = ret + str.slice(lastIndex); + ret = ""; + return result; + }; +} +function determineBranch(decodeTree, current, nodeIdx, char) { + const branchCount = (current & BinTrieFlags.BRANCH_LENGTH) >> 7; + const jumpOffset = current & BinTrieFlags.JUMP_TABLE; + if (branchCount === 0) { + return jumpOffset !== 0 && char === jumpOffset ? nodeIdx : -1; + } + if (jumpOffset) { + const value = char - jumpOffset; + return value < 0 || value >= branchCount ? -1 : decodeTree[nodeIdx + value] - 1; + } + let lo = nodeIdx; + let hi = lo + branchCount - 1; + while (lo <= hi) { + const mid = lo + hi >>> 1; + const midVal = decodeTree[mid]; + if (midVal < char) { + lo = mid + 1; + } else if (midVal > char) { + hi = mid - 1; + } else { + return decodeTree[mid + branchCount]; + } + } + return -1; +} +getDecoder(htmlDecodeTree); +getDecoder(xmlDecodeTree); +const xmlReplacer = /["&'<>$\x80-\uFFFF]/g; +const xmlCodeMap = /* @__PURE__ */ new Map([ + [34, """], + [38, "&"], + [39, "'"], + [60, "<"], + [62, ">"] +]); +const getCodePoint = ( + // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition + String.prototype.codePointAt != null ? (str, index2) => str.codePointAt(index2) : ( + // http://mathiasbynens.be/notes/javascript-encoding#surrogate-formulae + (c, index2) => (c.charCodeAt(index2) & 64512) === 55296 ? (c.charCodeAt(index2) - 55296) * 1024 + c.charCodeAt(index2 + 1) - 56320 + 65536 : c.charCodeAt(index2) + ) +); +function encodeXML(str) { + let ret = ""; + let lastIdx = 0; + let match; + while ((match = xmlReplacer.exec(str)) !== null) { + const i = match.index; + const char = str.charCodeAt(i); + const next2 = xmlCodeMap.get(char); + if (next2 !== void 0) { + ret += str.substring(lastIdx, i) + next2; + lastIdx = i + 1; + } else { + ret += `${str.substring(lastIdx, i)}&#x${getCodePoint(str, i).toString(16)};`; + lastIdx = xmlReplacer.lastIndex += Number((char & 64512) === 55296); + } + } + return ret + str.substr(lastIdx); +} +function getEscaper(regex, map2) { + return function escape(data2) { + let match; + let lastIdx = 0; + let result = ""; + while (match = regex.exec(data2)) { + if (lastIdx !== match.index) { + result += data2.substring(lastIdx, match.index); + } + result += map2.get(match[0].charCodeAt(0)); + lastIdx = match.index + 1; + } + return result + data2.substring(lastIdx); + }; +} +const escapeAttribute = getEscaper(/["&\u00A0]/g, /* @__PURE__ */ new Map([ + [34, """], + [38, "&"], + [160, " "] +])); +const escapeText = getEscaper(/[&<>\u00A0]/g, /* @__PURE__ */ new Map([ + [38, "&"], + [60, "<"], + [62, ">"], + [160, " "] +])); +const elementNames = new Map([ + "altGlyph", + "altGlyphDef", + "altGlyphItem", + "animateColor", + "animateMotion", + "animateTransform", + "clipPath", + "feBlend", + "feColorMatrix", + "feComponentTransfer", + "feComposite", + "feConvolveMatrix", + "feDiffuseLighting", + "feDisplacementMap", + "feDistantLight", + "feDropShadow", + "feFlood", + "feFuncA", + "feFuncB", + "feFuncG", + "feFuncR", + "feGaussianBlur", + "feImage", + "feMerge", + "feMergeNode", + "feMorphology", + "feOffset", + "fePointLight", + "feSpecularLighting", + "feSpotLight", + "feTile", + "feTurbulence", + "foreignObject", + "glyphRef", + "linearGradient", + "radialGradient", + "textPath" +].map((val2) => [val2.toLowerCase(), val2])); +const attributeNames = new Map([ + "definitionURL", + "attributeName", + "attributeType", + "baseFrequency", + "baseProfile", + "calcMode", + "clipPathUnits", + "diffuseConstant", + "edgeMode", + "filterUnits", + "glyphRef", + "gradientTransform", + "gradientUnits", + "kernelMatrix", + "kernelUnitLength", + "keyPoints", + "keySplines", + "keyTimes", + "lengthAdjust", + "limitingConeAngle", + "markerHeight", + "markerUnits", + "markerWidth", + "maskContentUnits", + "maskUnits", + "numOctaves", + "pathLength", + "patternContentUnits", + "patternTransform", + "patternUnits", + "pointsAtX", + "pointsAtY", + "pointsAtZ", + "preserveAlpha", + "preserveAspectRatio", + "primitiveUnits", + "refX", + "refY", + "repeatCount", + "repeatDur", + "requiredExtensions", + "requiredFeatures", + "specularConstant", + "specularExponent", + "spreadMethod", + "startOffset", + "stdDeviation", + "stitchTiles", + "surfaceScale", + "systemLanguage", + "tableValues", + "targetX", + "targetY", + "textLength", + "viewBox", + "viewTarget", + "xChannelSelector", + "yChannelSelector", + "zoomAndPan" +].map((val2) => [val2.toLowerCase(), val2])); +const unencodedElements = /* @__PURE__ */ new Set([ + "style", + "script", + "xmp", + "iframe", + "noembed", + "noframes", + "plaintext", + "noscript" +]); +function replaceQuotes(value) { + return value.replace(/"/g, """); +} +function formatAttributes(attributes2, opts) { + var _a2; + if (!attributes2) + return; + const encode = ((_a2 = opts.encodeEntities) !== null && _a2 !== void 0 ? _a2 : opts.decodeEntities) === false ? replaceQuotes : opts.xmlMode || opts.encodeEntities !== "utf8" ? encodeXML : escapeAttribute; + return Object.keys(attributes2).map((key) => { + var _a3, _b; + const value = (_a3 = attributes2[key]) !== null && _a3 !== void 0 ? _a3 : ""; + if (opts.xmlMode === "foreign") { + key = (_b = attributeNames.get(key)) !== null && _b !== void 0 ? _b : key; + } + if (!opts.emptyAttrs && !opts.xmlMode && value === "") { + return key; + } + return `${key}="${encode(value)}"`; + }).join(" "); +} +const singleTag = /* @__PURE__ */ new Set([ + "area", + "base", + "basefont", + "br", + "col", + "command", + "embed", + "frame", + "hr", + "img", + "input", + "isindex", + "keygen", + "link", + "meta", + "param", + "source", + "track", + "wbr" +]); +function render$1(node, options = {}) { + const nodes = "length" in node ? node : [node]; + let output = ""; + for (let i = 0; i < nodes.length; i++) { + output += renderNode(nodes[i], options); + } + return output; +} +function renderNode(node, options) { + switch (node.type) { + case Root: + return render$1(node.children, options); + // @ts-expect-error We don't use `Doctype` yet + case Doctype: + case Directive: + return renderDirective(node); + case Comment$1: + return renderComment(node); + case CDATA$1: + return renderCdata(node); + case Script: + case Style: + case Tag: + return renderTag(node, options); + case Text$1: + return renderText(node, options); + } +} +const foreignModeIntegrationPoints = /* @__PURE__ */ new Set([ + "mi", + "mo", + "mn", + "ms", + "mtext", + "annotation-xml", + "foreignObject", + "desc", + "title" +]); +const foreignElements = /* @__PURE__ */ new Set(["svg", "math"]); +function renderTag(elem, opts) { + var _a2; + if (opts.xmlMode === "foreign") { + elem.name = (_a2 = elementNames.get(elem.name)) !== null && _a2 !== void 0 ? _a2 : elem.name; + if (elem.parent && foreignModeIntegrationPoints.has(elem.parent.name)) { + opts = { ...opts, xmlMode: false }; + } + } + if (!opts.xmlMode && foreignElements.has(elem.name)) { + opts = { ...opts, xmlMode: "foreign" }; + } + let tag = `<${elem.name}`; + const attribs = formatAttributes(elem.attribs, opts); + if (attribs) { + tag += ` ${attribs}`; + } + if (elem.children.length === 0 && (opts.xmlMode ? ( + // In XML mode or foreign mode, and user hasn't explicitly turned off self-closing tags + opts.selfClosingTags !== false + ) : ( + // User explicitly asked for self-closing tags, even in HTML mode + opts.selfClosingTags && singleTag.has(elem.name) + ))) { + if (!opts.xmlMode) + tag += " "; + tag += "/>"; + } else { + tag += ">"; + if (elem.children.length > 0) { + tag += render$1(elem.children, opts); + } + if (opts.xmlMode || !singleTag.has(elem.name)) { + tag += ``; + } + } + return tag; +} +function renderDirective(elem) { + return `<${elem.data}>`; +} +function renderText(elem, opts) { + var _a2; + let data2 = elem.data || ""; + if (((_a2 = opts.encodeEntities) !== null && _a2 !== void 0 ? _a2 : opts.decodeEntities) !== false && !(!opts.xmlMode && elem.parent && unencodedElements.has(elem.parent.name))) { + data2 = opts.xmlMode || opts.encodeEntities !== "utf8" ? encodeXML(data2) : escapeText(data2); + } + return data2; +} +function renderCdata(elem) { + return ``; +} +function renderComment(elem) { + return ``; +} +function getOuterHTML(node, options) { + return render$1(node, options); +} +function getInnerHTML(node, options) { + return hasChildren(node) ? node.children.map((node2) => getOuterHTML(node2, options)).join("") : ""; +} +function getText(node) { + if (Array.isArray(node)) + return node.map(getText).join(""); + if (isTag(node)) + return node.name === "br" ? "\n" : getText(node.children); + if (isCDATA(node)) + return getText(node.children); + if (isText(node)) + return node.data; + return ""; +} +function textContent(node) { + if (Array.isArray(node)) + return node.map(textContent).join(""); + if (hasChildren(node) && !isComment(node)) { + return textContent(node.children); + } + if (isText(node)) + return node.data; + return ""; +} +function innerText(node) { + if (Array.isArray(node)) + return node.map(innerText).join(""); + if (hasChildren(node) && (node.type === ElementType.Tag || isCDATA(node))) { + return innerText(node.children); + } + if (isText(node)) + return node.data; + return ""; +} +function getChildren(elem) { + return hasChildren(elem) ? elem.children : []; +} +function getParent(elem) { + return elem.parent || null; +} +function getSiblings(elem) { + const parent2 = getParent(elem); + if (parent2 != null) + return getChildren(parent2); + const siblings2 = [elem]; + let { prev: prev2, next: next2 } = elem; + while (prev2 != null) { + siblings2.unshift(prev2); + ({ prev: prev2 } = prev2); + } + while (next2 != null) { + siblings2.push(next2); + ({ next: next2 } = next2); + } + return siblings2; +} +function getAttributeValue(elem, name) { + var _a2; + return (_a2 = elem.attribs) === null || _a2 === void 0 ? void 0 : _a2[name]; +} +function hasAttrib(elem, name) { + return elem.attribs != null && Object.prototype.hasOwnProperty.call(elem.attribs, name) && elem.attribs[name] != null; +} +function getName(elem) { + return elem.name; +} +function nextElementSibling(elem) { + let { next: next2 } = elem; + while (next2 !== null && !isTag(next2)) + ({ next: next2 } = next2); + return next2; +} +function prevElementSibling(elem) { + let { prev: prev2 } = elem; + while (prev2 !== null && !isTag(prev2)) + ({ prev: prev2 } = prev2); + return prev2; +} +function removeElement(elem) { + if (elem.prev) + elem.prev.next = elem.next; + if (elem.next) + elem.next.prev = elem.prev; + if (elem.parent) { + const childs = elem.parent.children; + const childsIndex = childs.lastIndexOf(elem); + if (childsIndex >= 0) { + childs.splice(childsIndex, 1); + } + } + elem.next = null; + elem.prev = null; + elem.parent = null; +} +function replaceElement(elem, replacement) { + const prev2 = replacement.prev = elem.prev; + if (prev2) { + prev2.next = replacement; + } + const next2 = replacement.next = elem.next; + if (next2) { + next2.prev = replacement; + } + const parent2 = replacement.parent = elem.parent; + if (parent2) { + const childs = parent2.children; + childs[childs.lastIndexOf(elem)] = replacement; + elem.parent = null; + } +} +function appendChild(parent2, child) { + removeElement(child); + child.next = null; + child.parent = parent2; + if (parent2.children.push(child) > 1) { + const sibling = parent2.children[parent2.children.length - 2]; + sibling.next = child; + child.prev = sibling; + } else { + child.prev = null; + } +} +function append$1(elem, next2) { + removeElement(next2); + const { parent: parent2 } = elem; + const currNext = elem.next; + next2.next = currNext; + next2.prev = elem; + elem.next = next2; + next2.parent = parent2; + if (currNext) { + currNext.prev = next2; + if (parent2) { + const childs = parent2.children; + childs.splice(childs.lastIndexOf(currNext), 0, next2); + } + } else if (parent2) { + parent2.children.push(next2); + } +} +function prependChild(parent2, child) { + removeElement(child); + child.parent = parent2; + child.prev = null; + if (parent2.children.unshift(child) !== 1) { + const sibling = parent2.children[1]; + sibling.prev = child; + child.next = sibling; + } else { + child.next = null; + } +} +function prepend$1(elem, prev2) { + removeElement(prev2); + const { parent: parent2 } = elem; + if (parent2) { + const childs = parent2.children; + childs.splice(childs.indexOf(elem), 0, prev2); + } + if (elem.prev) { + elem.prev.next = prev2; + } + prev2.parent = parent2; + prev2.prev = elem.prev; + prev2.next = elem; + elem.prev = prev2; +} +function filter$2(test, node, recurse = true, limit = Infinity) { + return find$2(test, Array.isArray(node) ? node : [node], recurse, limit); +} +function find$2(test, nodes, recurse, limit) { + const result = []; + const nodeStack = [nodes]; + const indexStack = [0]; + for (; ; ) { + if (indexStack[0] >= nodeStack[0].length) { + if (indexStack.length === 1) { + return result; + } + nodeStack.shift(); + indexStack.shift(); + continue; + } + const elem = nodeStack[0][indexStack[0]++]; + if (test(elem)) { + result.push(elem); + if (--limit <= 0) + return result; + } + if (recurse && hasChildren(elem) && elem.children.length > 0) { + indexStack.unshift(0); + nodeStack.unshift(elem.children); + } + } +} +function findOneChild(test, nodes) { + return nodes.find(test); +} +function findOne(test, nodes, recurse = true) { + let elem = null; + for (let i = 0; i < nodes.length && !elem; i++) { + const node = nodes[i]; + if (!isTag(node)) { + continue; + } else if (test(node)) { + elem = node; + } else if (recurse && node.children.length > 0) { + elem = findOne(test, node.children, true); + } + } + return elem; +} +function existsOne(test, nodes) { + return nodes.some((checked) => isTag(checked) && (test(checked) || existsOne(test, checked.children))); +} +function findAll(test, nodes) { + const result = []; + const nodeStack = [nodes]; + const indexStack = [0]; + for (; ; ) { + if (indexStack[0] >= nodeStack[0].length) { + if (nodeStack.length === 1) { + return result; + } + nodeStack.shift(); + indexStack.shift(); + continue; + } + const elem = nodeStack[0][indexStack[0]++]; + if (!isTag(elem)) + continue; + if (test(elem)) + result.push(elem); + if (elem.children.length > 0) { + indexStack.unshift(0); + nodeStack.unshift(elem.children); + } + } +} +const Checks = { + tag_name(name) { + if (typeof name === "function") { + return (elem) => isTag(elem) && name(elem.name); + } else if (name === "*") { + return isTag; + } + return (elem) => isTag(elem) && elem.name === name; + }, + tag_type(type) { + if (typeof type === "function") { + return (elem) => type(elem.type); + } + return (elem) => elem.type === type; + }, + tag_contains(data2) { + if (typeof data2 === "function") { + return (elem) => isText(elem) && data2(elem.data); + } + return (elem) => isText(elem) && elem.data === data2; + } +}; +function getAttribCheck(attrib, value) { + if (typeof value === "function") { + return (elem) => isTag(elem) && value(elem.attribs[attrib]); + } + return (elem) => isTag(elem) && elem.attribs[attrib] === value; +} +function combineFuncs(a, b) { + return (elem) => a(elem) || b(elem); +} +function compileTest(options) { + const funcs = Object.keys(options).map((key) => { + const value = options[key]; + return Object.prototype.hasOwnProperty.call(Checks, key) ? Checks[key](value) : getAttribCheck(key, value); + }); + return funcs.length === 0 ? null : funcs.reduce(combineFuncs); +} +function testElement(options, node) { + const test = compileTest(options); + return test ? test(node) : true; +} +function getElements(options, nodes, recurse, limit = Infinity) { + const test = compileTest(options); + return test ? filter$2(test, nodes, recurse, limit) : []; +} +function getElementById(id, nodes, recurse = true) { + if (!Array.isArray(nodes)) + nodes = [nodes]; + return findOne(getAttribCheck("id", id), nodes, recurse); +} +function getElementsByTagName(tagName, nodes, recurse = true, limit = Infinity) { + return filter$2(Checks["tag_name"](tagName), nodes, recurse, limit); +} +function getElementsByTagType(type, nodes, recurse = true, limit = Infinity) { + return filter$2(Checks["tag_type"](type), nodes, recurse, limit); +} +function removeSubsets(nodes) { + let idx = nodes.length; + while (--idx >= 0) { + const node = nodes[idx]; + if (idx > 0 && nodes.lastIndexOf(node, idx - 1) >= 0) { + nodes.splice(idx, 1); + continue; + } + for (let ancestor = node.parent; ancestor; ancestor = ancestor.parent) { + if (nodes.includes(ancestor)) { + nodes.splice(idx, 1); + break; + } + } + } + return nodes; +} +var DocumentPosition; +(function(DocumentPosition2) { + DocumentPosition2[DocumentPosition2["DISCONNECTED"] = 1] = "DISCONNECTED"; + DocumentPosition2[DocumentPosition2["PRECEDING"] = 2] = "PRECEDING"; + DocumentPosition2[DocumentPosition2["FOLLOWING"] = 4] = "FOLLOWING"; + DocumentPosition2[DocumentPosition2["CONTAINS"] = 8] = "CONTAINS"; + DocumentPosition2[DocumentPosition2["CONTAINED_BY"] = 16] = "CONTAINED_BY"; +})(DocumentPosition || (DocumentPosition = {})); +function compareDocumentPosition(nodeA, nodeB) { + const aParents = []; + const bParents = []; + if (nodeA === nodeB) { + return 0; + } + let current = hasChildren(nodeA) ? nodeA : nodeA.parent; + while (current) { + aParents.unshift(current); + current = current.parent; + } + current = hasChildren(nodeB) ? nodeB : nodeB.parent; + while (current) { + bParents.unshift(current); + current = current.parent; + } + const maxIdx = Math.min(aParents.length, bParents.length); + let idx = 0; + while (idx < maxIdx && aParents[idx] === bParents[idx]) { + idx++; + } + if (idx === 0) { + return DocumentPosition.DISCONNECTED; + } + const sharedParent = aParents[idx - 1]; + const siblings2 = sharedParent.children; + const aSibling = aParents[idx]; + const bSibling = bParents[idx]; + if (siblings2.indexOf(aSibling) > siblings2.indexOf(bSibling)) { + if (sharedParent === nodeB) { + return DocumentPosition.FOLLOWING | DocumentPosition.CONTAINED_BY; + } + return DocumentPosition.FOLLOWING; + } + if (sharedParent === nodeA) { + return DocumentPosition.PRECEDING | DocumentPosition.CONTAINS; + } + return DocumentPosition.PRECEDING; +} +function uniqueSort(nodes) { + nodes = nodes.filter((node, i, arr) => !arr.includes(node, i + 1)); + nodes.sort((a, b) => { + const relative = compareDocumentPosition(a, b); + if (relative & DocumentPosition.PRECEDING) { + return -1; + } else if (relative & DocumentPosition.FOLLOWING) { + return 1; + } + return 0; + }); + return nodes; +} +function getFeed(doc) { + const feedRoot = getOneElement(isValidFeed, doc); + return !feedRoot ? null : feedRoot.name === "feed" ? getAtomFeed(feedRoot) : getRssFeed(feedRoot); +} +function getAtomFeed(feedRoot) { + var _a2; + const childs = feedRoot.children; + const feed = { + type: "atom", + items: getElementsByTagName("entry", childs).map((item) => { + var _a3; + const { children: children2 } = item; + const entry = { media: getMediaElements(children2) }; + addConditionally(entry, "id", "id", children2); + addConditionally(entry, "title", "title", children2); + const href2 = (_a3 = getOneElement("link", children2)) === null || _a3 === void 0 ? void 0 : _a3.attribs["href"]; + if (href2) { + entry.link = href2; + } + const description = fetch("summary", children2) || fetch("content", children2); + if (description) { + entry.description = description; + } + const pubDate = fetch("updated", children2); + if (pubDate) { + entry.pubDate = new Date(pubDate); + } + return entry; + }) + }; + addConditionally(feed, "id", "id", childs); + addConditionally(feed, "title", "title", childs); + const href = (_a2 = getOneElement("link", childs)) === null || _a2 === void 0 ? void 0 : _a2.attribs["href"]; + if (href) { + feed.link = href; + } + addConditionally(feed, "description", "subtitle", childs); + const updated = fetch("updated", childs); + if (updated) { + feed.updated = new Date(updated); + } + addConditionally(feed, "author", "email", childs, true); + return feed; +} +function getRssFeed(feedRoot) { + var _a2, _b; + const childs = (_b = (_a2 = getOneElement("channel", feedRoot.children)) === null || _a2 === void 0 ? void 0 : _a2.children) !== null && _b !== void 0 ? _b : []; + const feed = { + type: feedRoot.name.substr(0, 3), + id: "", + items: getElementsByTagName("item", feedRoot.children).map((item) => { + const { children: children2 } = item; + const entry = { media: getMediaElements(children2) }; + addConditionally(entry, "id", "guid", children2); + addConditionally(entry, "title", "title", children2); + addConditionally(entry, "link", "link", children2); + addConditionally(entry, "description", "description", children2); + const pubDate = fetch("pubDate", children2) || fetch("dc:date", children2); + if (pubDate) + entry.pubDate = new Date(pubDate); + return entry; + }) + }; + addConditionally(feed, "title", "title", childs); + addConditionally(feed, "link", "link", childs); + addConditionally(feed, "description", "description", childs); + const updated = fetch("lastBuildDate", childs); + if (updated) { + feed.updated = new Date(updated); + } + addConditionally(feed, "author", "managingEditor", childs, true); + return feed; +} +const MEDIA_KEYS_STRING = ["url", "type", "lang"]; +const MEDIA_KEYS_INT = [ + "fileSize", + "bitrate", + "framerate", + "samplingrate", + "channels", + "duration", + "height", + "width" +]; +function getMediaElements(where) { + return getElementsByTagName("media:content", where).map((elem) => { + const { attribs } = elem; + const media = { + medium: attribs["medium"], + isDefault: !!attribs["isDefault"] + }; + for (const attrib of MEDIA_KEYS_STRING) { + if (attribs[attrib]) { + media[attrib] = attribs[attrib]; + } + } + for (const attrib of MEDIA_KEYS_INT) { + if (attribs[attrib]) { + media[attrib] = parseInt(attribs[attrib], 10); + } + } + if (attribs["expression"]) { + media.expression = attribs["expression"]; + } + return media; + }); +} +function getOneElement(tagName, node) { + return getElementsByTagName(tagName, node, true, 1)[0]; +} +function fetch(tagName, where, recurse = false) { + return textContent(getElementsByTagName(tagName, where, recurse, 1)).trim(); +} +function addConditionally(obj, prop2, tagName, where, recurse = false) { + const val2 = fetch(tagName, where, recurse); + if (val2) + obj[prop2] = val2; +} +function isValidFeed(value) { + return value === "rss" || value === "feed" || value === "rdf:RDF"; +} +const DomUtils = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({ + __proto__: null, + get DocumentPosition() { + return DocumentPosition; + }, + append: append$1, + appendChild, + compareDocumentPosition, + existsOne, + filter: filter$2, + find: find$2, + findAll, + findOne, + findOneChild, + getAttributeValue, + getChildren, + getElementById, + getElements, + getElementsByTagName, + getElementsByTagType, + getFeed, + getInnerHTML, + getName, + getOuterHTML, + getParent, + getSiblings, + getText, + hasAttrib, + hasChildren, + innerText, + isCDATA, + isComment, + isDocument, + isTag, + isText, + nextElementSibling, + prepend: prepend$1, + prependChild, + prevElementSibling, + removeElement, + removeSubsets, + replaceElement, + testElement, + textContent, + uniqueSort +}, Symbol.toStringTag, { value: "Module" })); +function render(that, dom, options) { + if (!that) + return ""; + return that(dom !== null && dom !== void 0 ? dom : that._root.children, null, void 0, options).toString(); +} +function isOptions(dom, options) { + return typeof dom === "object" && dom != null && !("length" in dom) && !("type" in dom); +} +function html$1(dom, options) { + const toRender = isOptions(dom) ? (options = dom, void 0) : dom; + const opts = { + ...this === null || this === void 0 ? void 0 : this._options, + ...flattenOptions(options) + }; + return render(this, toRender, opts); +} +function xml(dom) { + const options = { ...this._options, xmlMode: true }; + return render(this, dom, options); +} +function text$1(elements) { + const elems = elements !== null && elements !== void 0 ? elements : this ? this.root() : []; + let ret = ""; + for (let i = 0; i < elems.length; i++) { + ret += textContent(elems[i]); + } + return ret; +} +function parseHTML(data2, context, keepScripts = typeof context === "boolean" ? context : false) { + if (!data2 || typeof data2 !== "string") { + return null; + } + if (typeof context === "boolean") { + keepScripts = context; + } + const parsed = this.load(data2, this._options, false); + if (!keepScripts) { + parsed("script").remove(); + } + return [...parsed.root()[0].children]; +} +function root() { + return this(this._root); +} +function contains(container, contained) { + if (contained === container) { + return false; + } + let next2 = contained; + while (next2 && next2 !== next2.parent) { + next2 = next2.parent; + if (next2 === container) { + return true; + } + } + return false; +} +function extract$1(map2) { + return this.root().extract(map2); +} +function merge(arr1, arr2) { + if (!isArrayLike(arr1) || !isArrayLike(arr2)) { + return; + } + let newLength = arr1.length; + const len = +arr2.length; + for (let i = 0; i < len; i++) { + arr1[newLength++] = arr2[i]; + } + arr1.length = newLength; + return arr1; +} +function isArrayLike(item) { + if (Array.isArray(item)) { + return true; + } + if (typeof item !== "object" || item === null || !("length" in item) || typeof item.length !== "number" || item.length < 0) { + return false; + } + for (let i = 0; i < item.length; i++) { + if (!(i in item)) { + return false; + } + } + return true; +} +const staticMethods = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({ + __proto__: null, + contains, + extract: extract$1, + html: html$1, + merge, + parseHTML, + root, + text: text$1, + xml +}, Symbol.toStringTag, { value: "Module" })); +function isCheerio(maybeCheerio) { + return maybeCheerio.cheerio != null; +} +function camelCase(str) { + return str.replace(/[._-](\w|$)/g, (_, x) => x.toUpperCase()); +} +function cssCase(str) { + return str.replace(/[A-Z]/g, "-$&").toLowerCase(); +} +function domEach(array, fn) { + const len = array.length; + for (let i = 0; i < len; i++) + fn(array[i], i); + return array; +} +var CharacterCodes; +(function(CharacterCodes2) { + CharacterCodes2[CharacterCodes2["LowerA"] = 97] = "LowerA"; + CharacterCodes2[CharacterCodes2["LowerZ"] = 122] = "LowerZ"; + CharacterCodes2[CharacterCodes2["UpperA"] = 65] = "UpperA"; + CharacterCodes2[CharacterCodes2["UpperZ"] = 90] = "UpperZ"; + CharacterCodes2[CharacterCodes2["Exclamation"] = 33] = "Exclamation"; +})(CharacterCodes || (CharacterCodes = {})); +function isHtml(str) { + const tagStart = str.indexOf("<"); + if (tagStart < 0 || tagStart > str.length - 3) + return false; + const tagChar = str.charCodeAt(tagStart + 1); + return (tagChar >= CharacterCodes.LowerA && tagChar <= CharacterCodes.LowerZ || tagChar >= CharacterCodes.UpperA && tagChar <= CharacterCodes.UpperZ || tagChar === CharacterCodes.Exclamation) && str.includes(">", tagStart + 2); +} +const hasOwn = Object.prototype.hasOwnProperty; +const rspace = /\s+/; +const dataAttrPrefix = "data-"; +const rboolean = /^(?:autofocus|autoplay|async|checked|controls|defer|disabled|hidden|loop|multiple|open|readonly|required|scoped|selected)$/i; +const rbrace = /^{[^]*}$|^\[[^]*]$/; +function getAttr(elem, name, xmlMode) { + var _a2; + if (!elem || !isTag(elem)) + return void 0; + (_a2 = elem.attribs) !== null && _a2 !== void 0 ? _a2 : elem.attribs = {}; + if (!name) { + return elem.attribs; + } + if (hasOwn.call(elem.attribs, name)) { + return !xmlMode && rboolean.test(name) ? name : elem.attribs[name]; + } + if (elem.name === "option" && name === "value") { + return text$1(elem.children); + } + if (elem.name === "input" && (elem.attribs["type"] === "radio" || elem.attribs["type"] === "checkbox") && name === "value") { + return "on"; + } + return void 0; +} +function setAttr(el, name, value) { + if (value === null) { + removeAttribute(el, name); + } else { + el.attribs[name] = `${value}`; + } +} +function attr(name, value) { + if (typeof name === "object" || value !== void 0) { + if (typeof value === "function") { + if (typeof name !== "string") { + { + throw new Error("Bad combination of arguments."); + } + } + return domEach(this, (el, i) => { + if (isTag(el)) + setAttr(el, name, value.call(el, i, el.attribs[name])); + }); + } + return domEach(this, (el) => { + if (!isTag(el)) + return; + if (typeof name === "object") { + for (const objName of Object.keys(name)) { + const objValue = name[objName]; + setAttr(el, objName, objValue); + } + } else { + setAttr(el, name, value); + } + }); + } + return arguments.length > 1 ? this : getAttr(this[0], name, this.options.xmlMode); +} +function getProp(el, name, xmlMode) { + return name in el ? ( + // @ts-expect-error TS doesn't like us accessing the value directly here. + el[name] + ) : !xmlMode && rboolean.test(name) ? getAttr(el, name, false) !== void 0 : getAttr(el, name, xmlMode); +} +function setProp(el, name, value, xmlMode) { + if (name in el) { + el[name] = value; + } else { + setAttr(el, name, !xmlMode && rboolean.test(name) ? value ? "" : null : `${value}`); + } +} +function prop(name, value) { + var _a2; + if (typeof name === "string" && value === void 0) { + const el = this[0]; + if (!el || !isTag(el)) + return void 0; + switch (name) { + case "style": { + const property = this.css(); + const keys = Object.keys(property); + for (let i = 0; i < keys.length; i++) { + property[i] = keys[i]; + } + property.length = keys.length; + return property; + } + case "tagName": + case "nodeName": { + return el.name.toUpperCase(); + } + case "href": + case "src": { + const prop2 = (_a2 = el.attribs) === null || _a2 === void 0 ? void 0 : _a2[name]; + if (typeof URL !== "undefined" && (name === "href" && (el.tagName === "a" || el.tagName === "link") || name === "src" && (el.tagName === "img" || el.tagName === "iframe" || el.tagName === "audio" || el.tagName === "video" || el.tagName === "source")) && prop2 !== void 0 && this.options.baseURI) { + return new URL(prop2, this.options.baseURI).href; + } + return prop2; + } + case "innerText": { + return innerText(el); + } + case "textContent": { + return textContent(el); + } + case "outerHTML": { + return this.clone().wrap("").parent().html(); + } + case "innerHTML": { + return this.html(); + } + default: { + return getProp(el, name, this.options.xmlMode); + } + } + } + if (typeof name === "object" || value !== void 0) { + if (typeof value === "function") { + if (typeof name === "object") { + throw new TypeError("Bad combination of arguments."); + } + return domEach(this, (el, i) => { + if (isTag(el)) { + setProp(el, name, value.call(el, i, getProp(el, name, this.options.xmlMode)), this.options.xmlMode); + } + }); + } + return domEach(this, (el) => { + if (!isTag(el)) + return; + if (typeof name === "object") { + for (const key of Object.keys(name)) { + const val2 = name[key]; + setProp(el, key, val2, this.options.xmlMode); + } + } else { + setProp(el, name, value, this.options.xmlMode); + } + }); + } + return void 0; +} +function setData(elem, name, value) { + var _a2; + (_a2 = elem.data) !== null && _a2 !== void 0 ? _a2 : elem.data = {}; + if (typeof name === "object") + Object.assign(elem.data, name); + else if (typeof name === "string" && value !== void 0) { + elem.data[name] = value; + } +} +function readAllData(el) { + for (const domName of Object.keys(el.attribs)) { + if (!domName.startsWith(dataAttrPrefix)) { + continue; + } + const jsName = camelCase(domName.slice(dataAttrPrefix.length)); + if (!hasOwn.call(el.data, jsName)) { + el.data[jsName] = parseDataValue(el.attribs[domName]); + } + } + return el.data; +} +function readData(el, name) { + const domName = dataAttrPrefix + cssCase(name); + const data2 = el.data; + if (hasOwn.call(data2, name)) { + return data2[name]; + } + if (hasOwn.call(el.attribs, domName)) { + return data2[name] = parseDataValue(el.attribs[domName]); + } + return void 0; +} +function parseDataValue(value) { + if (value === "null") + return null; + if (value === "true") + return true; + if (value === "false") + return false; + const num = Number(value); + if (value === String(num)) + return num; + if (rbrace.test(value)) { + try { + return JSON.parse(value); + } catch { + } + } + return value; +} +function data(name, value) { + var _a2; + const elem = this[0]; + if (!elem || !isTag(elem)) + return; + const dataEl = elem; + (_a2 = dataEl.data) !== null && _a2 !== void 0 ? _a2 : dataEl.data = {}; + if (name == null) { + return readAllData(dataEl); + } + if (typeof name === "object" || value !== void 0) { + domEach(this, (el) => { + if (isTag(el)) { + if (typeof name === "object") + setData(el, name); + else + setData(el, name, value); + } + }); + return this; + } + return readData(dataEl, name); +} +function val(value) { + const querying = arguments.length === 0; + const element = this[0]; + if (!element || !isTag(element)) + return querying ? void 0 : this; + switch (element.name) { + case "textarea": { + return this.text(value); + } + case "select": { + const option = this.find("option:selected"); + if (!querying) { + if (this.attr("multiple") == null && typeof value === "object") { + return this; + } + this.find("option").removeAttr("selected"); + const values = typeof value === "object" ? value : [value]; + for (const val2 of values) { + this.find(`option[value="${val2}"]`).attr("selected", ""); + } + return this; + } + return this.attr("multiple") ? option.toArray().map((el) => text$1(el.children)) : option.attr("value"); + } + case "input": + case "option": { + return querying ? this.attr("value") : this.attr("value", value); + } + } + return void 0; +} +function removeAttribute(elem, name) { + if (!elem.attribs || !hasOwn.call(elem.attribs, name)) + return; + delete elem.attribs[name]; +} +function splitNames(names) { + return names ? names.trim().split(rspace) : []; +} +function removeAttr(name) { + const attrNames = splitNames(name); + for (const attrName of attrNames) { + domEach(this, (elem) => { + if (isTag(elem)) + removeAttribute(elem, attrName); + }); + } + return this; +} +function hasClass(className) { + return this.toArray().some((elem) => { + const clazz = isTag(elem) && elem.attribs["class"]; + let idx = -1; + if (clazz && className.length > 0) { + while ((idx = clazz.indexOf(className, idx + 1)) > -1) { + const end2 = idx + className.length; + if ((idx === 0 || rspace.test(clazz[idx - 1])) && (end2 === clazz.length || rspace.test(clazz[end2]))) { + return true; + } + } + } + return false; + }); +} +function addClass(value) { + if (typeof value === "function") { + return domEach(this, (el, i) => { + if (isTag(el)) { + const className = el.attribs["class"] || ""; + addClass.call([el], value.call(el, i, className)); + } + }); + } + if (!value || typeof value !== "string") + return this; + const classNames = value.split(rspace); + const numElements = this.length; + for (let i = 0; i < numElements; i++) { + const el = this[i]; + if (!isTag(el)) + continue; + const className = getAttr(el, "class", false); + if (className) { + let setClass = ` ${className} `; + for (const cn of classNames) { + const appendClass = `${cn} `; + if (!setClass.includes(` ${appendClass}`)) + setClass += appendClass; + } + setAttr(el, "class", setClass.trim()); + } else { + setAttr(el, "class", classNames.join(" ").trim()); + } + } + return this; +} +function removeClass(name) { + if (typeof name === "function") { + return domEach(this, (el, i) => { + if (isTag(el)) { + removeClass.call([el], name.call(el, i, el.attribs["class"] || "")); + } + }); + } + const classes = splitNames(name); + const numClasses = classes.length; + const removeAll = arguments.length === 0; + return domEach(this, (el) => { + if (!isTag(el)) + return; + if (removeAll) { + el.attribs["class"] = ""; + } else { + const elClasses = splitNames(el.attribs["class"]); + let changed = false; + for (let j = 0; j < numClasses; j++) { + const index2 = elClasses.indexOf(classes[j]); + if (index2 >= 0) { + elClasses.splice(index2, 1); + changed = true; + j--; + } + } + if (changed) { + el.attribs["class"] = elClasses.join(" "); + } + } + }); +} +function toggleClass(value, stateVal) { + if (typeof value === "function") { + return domEach(this, (el, i) => { + if (isTag(el)) { + toggleClass.call([el], value.call(el, i, el.attribs["class"] || "", stateVal), stateVal); + } + }); + } + if (!value || typeof value !== "string") + return this; + const classNames = value.split(rspace); + const numClasses = classNames.length; + const state = typeof stateVal === "boolean" ? stateVal ? 1 : -1 : 0; + const numElements = this.length; + for (let i = 0; i < numElements; i++) { + const el = this[i]; + if (!isTag(el)) + continue; + const elementClasses = splitNames(el.attribs["class"]); + for (let j = 0; j < numClasses; j++) { + const index2 = elementClasses.indexOf(classNames[j]); + if (state >= 0 && index2 < 0) { + elementClasses.push(classNames[j]); + } else if (state <= 0 && index2 >= 0) { + elementClasses.splice(index2, 1); + } + } + el.attribs["class"] = elementClasses.join(" "); + } + return this; +} +const Attributes = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({ + __proto__: null, + addClass, + attr, + data, + hasClass, + prop, + removeAttr, + removeClass, + toggleClass, + val +}, Symbol.toStringTag, { value: "Module" })); +var SelectorType; +(function(SelectorType2) { + SelectorType2["Attribute"] = "attribute"; + SelectorType2["Pseudo"] = "pseudo"; + SelectorType2["PseudoElement"] = "pseudo-element"; + SelectorType2["Tag"] = "tag"; + SelectorType2["Universal"] = "universal"; + SelectorType2["Adjacent"] = "adjacent"; + SelectorType2["Child"] = "child"; + SelectorType2["Descendant"] = "descendant"; + SelectorType2["Parent"] = "parent"; + SelectorType2["Sibling"] = "sibling"; + SelectorType2["ColumnCombinator"] = "column-combinator"; +})(SelectorType || (SelectorType = {})); +var AttributeAction; +(function(AttributeAction2) { + AttributeAction2["Any"] = "any"; + AttributeAction2["Element"] = "element"; + AttributeAction2["End"] = "end"; + AttributeAction2["Equals"] = "equals"; + AttributeAction2["Exists"] = "exists"; + AttributeAction2["Hyphen"] = "hyphen"; + AttributeAction2["Not"] = "not"; + AttributeAction2["Start"] = "start"; +})(AttributeAction || (AttributeAction = {})); +const reName = /^[^\\#]?(?:\\(?:[\da-f]{1,6}\s?|.)|[\w\-\u00b0-\uFFFF])+/; +const reEscape = /\\([\da-f]{1,6}\s?|(\s)|.)/gi; +const actionTypes = /* @__PURE__ */ new Map([ + [126, AttributeAction.Element], + [94, AttributeAction.Start], + [36, AttributeAction.End], + [42, AttributeAction.Any], + [33, AttributeAction.Not], + [124, AttributeAction.Hyphen] +]); +const unpackPseudos = /* @__PURE__ */ new Set([ + "has", + "not", + "matches", + "is", + "where", + "host", + "host-context" +]); +function isTraversal$1(selector) { + switch (selector.type) { + case SelectorType.Adjacent: + case SelectorType.Child: + case SelectorType.Descendant: + case SelectorType.Parent: + case SelectorType.Sibling: + case SelectorType.ColumnCombinator: + return true; + default: + return false; + } +} +const stripQuotesFromPseudos = /* @__PURE__ */ new Set(["contains", "icontains"]); +function funescape(_, escaped, escapedWhitespace) { + const high = parseInt(escaped, 16) - 65536; + return high !== high || escapedWhitespace ? escaped : high < 0 ? ( + // BMP codepoint + String.fromCharCode(high + 65536) + ) : ( + // Supplemental Plane codepoint (surrogate pair) + String.fromCharCode(high >> 10 | 55296, high & 1023 | 56320) + ); +} +function unescapeCSS(str) { + return str.replace(reEscape, funescape); +} +function isQuote(c) { + return c === 39 || c === 34; +} +function isWhitespace$1(c) { + return c === 32 || c === 9 || c === 10 || c === 12 || c === 13; +} +function parse$2(selector) { + const subselects2 = []; + const endIndex = parseSelector(subselects2, `${selector}`, 0); + if (endIndex < selector.length) { + throw new Error(`Unmatched selector: ${selector.slice(endIndex)}`); + } + return subselects2; +} +function parseSelector(subselects2, selector, selectorIndex) { + let tokens = []; + function getName2(offset) { + const match = selector.slice(selectorIndex + offset).match(reName); + if (!match) { + throw new Error(`Expected name, found ${selector.slice(selectorIndex)}`); + } + const [name] = match; + selectorIndex += offset + name.length; + return unescapeCSS(name); + } + function stripWhitespace(offset) { + selectorIndex += offset; + while (selectorIndex < selector.length && isWhitespace$1(selector.charCodeAt(selectorIndex))) { + selectorIndex++; + } + } + function readValueWithParenthesis() { + selectorIndex += 1; + const start = selectorIndex; + let counter = 1; + for (; counter > 0 && selectorIndex < selector.length; selectorIndex++) { + if (selector.charCodeAt(selectorIndex) === 40 && !isEscaped(selectorIndex)) { + counter++; + } else if (selector.charCodeAt(selectorIndex) === 41 && !isEscaped(selectorIndex)) { + counter--; + } + } + if (counter) { + throw new Error("Parenthesis not matched"); + } + return unescapeCSS(selector.slice(start, selectorIndex - 1)); + } + function isEscaped(pos) { + let slashCount = 0; + while (selector.charCodeAt(--pos) === 92) + slashCount++; + return (slashCount & 1) === 1; + } + function ensureNotTraversal() { + if (tokens.length > 0 && isTraversal$1(tokens[tokens.length - 1])) { + throw new Error("Did not expect successive traversals."); + } + } + function addTraversal(type) { + if (tokens.length > 0 && tokens[tokens.length - 1].type === SelectorType.Descendant) { + tokens[tokens.length - 1].type = type; + return; + } + ensureNotTraversal(); + tokens.push({ type }); + } + function addSpecialAttribute(name, action) { + tokens.push({ + type: SelectorType.Attribute, + name, + action, + value: getName2(1), + namespace: null, + ignoreCase: "quirks" + }); + } + function finalizeSubselector() { + if (tokens.length && tokens[tokens.length - 1].type === SelectorType.Descendant) { + tokens.pop(); + } + if (tokens.length === 0) { + throw new Error("Empty sub-selector"); + } + subselects2.push(tokens); + } + stripWhitespace(0); + if (selector.length === selectorIndex) { + return selectorIndex; + } + loop: while (selectorIndex < selector.length) { + const firstChar = selector.charCodeAt(selectorIndex); + switch (firstChar) { + // Whitespace + case 32: + case 9: + case 10: + case 12: + case 13: { + if (tokens.length === 0 || tokens[0].type !== SelectorType.Descendant) { + ensureNotTraversal(); + tokens.push({ type: SelectorType.Descendant }); + } + stripWhitespace(1); + break; + } + // Traversals + case 62: { + addTraversal(SelectorType.Child); + stripWhitespace(1); + break; + } + case 60: { + addTraversal(SelectorType.Parent); + stripWhitespace(1); + break; + } + case 126: { + addTraversal(SelectorType.Sibling); + stripWhitespace(1); + break; + } + case 43: { + addTraversal(SelectorType.Adjacent); + stripWhitespace(1); + break; + } + // Special attribute selectors: .class, #id + case 46: { + addSpecialAttribute("class", AttributeAction.Element); + break; + } + case 35: { + addSpecialAttribute("id", AttributeAction.Equals); + break; + } + case 91: { + stripWhitespace(1); + let name; + let namespace = null; + if (selector.charCodeAt(selectorIndex) === 124) { + name = getName2(1); + } else if (selector.startsWith("*|", selectorIndex)) { + namespace = "*"; + name = getName2(2); + } else { + name = getName2(0); + if (selector.charCodeAt(selectorIndex) === 124 && selector.charCodeAt(selectorIndex + 1) !== 61) { + namespace = name; + name = getName2(1); + } + } + stripWhitespace(0); + let action = AttributeAction.Exists; + const possibleAction = actionTypes.get(selector.charCodeAt(selectorIndex)); + if (possibleAction) { + action = possibleAction; + if (selector.charCodeAt(selectorIndex + 1) !== 61) { + throw new Error("Expected `=`"); + } + stripWhitespace(2); + } else if (selector.charCodeAt(selectorIndex) === 61) { + action = AttributeAction.Equals; + stripWhitespace(1); + } + let value = ""; + let ignoreCase = null; + if (action !== "exists") { + if (isQuote(selector.charCodeAt(selectorIndex))) { + const quote = selector.charCodeAt(selectorIndex); + let sectionEnd = selectorIndex + 1; + while (sectionEnd < selector.length && (selector.charCodeAt(sectionEnd) !== quote || isEscaped(sectionEnd))) { + sectionEnd += 1; + } + if (selector.charCodeAt(sectionEnd) !== quote) { + throw new Error("Attribute value didn't end"); + } + value = unescapeCSS(selector.slice(selectorIndex + 1, sectionEnd)); + selectorIndex = sectionEnd + 1; + } else { + const valueStart = selectorIndex; + while (selectorIndex < selector.length && (!isWhitespace$1(selector.charCodeAt(selectorIndex)) && selector.charCodeAt(selectorIndex) !== 93 || isEscaped(selectorIndex))) { + selectorIndex += 1; + } + value = unescapeCSS(selector.slice(valueStart, selectorIndex)); + } + stripWhitespace(0); + const forceIgnore = selector.charCodeAt(selectorIndex) | 32; + if (forceIgnore === 115) { + ignoreCase = false; + stripWhitespace(1); + } else if (forceIgnore === 105) { + ignoreCase = true; + stripWhitespace(1); + } + } + if (selector.charCodeAt(selectorIndex) !== 93) { + throw new Error("Attribute selector didn't terminate"); + } + selectorIndex += 1; + const attributeSelector = { + type: SelectorType.Attribute, + name, + action, + value, + namespace, + ignoreCase + }; + tokens.push(attributeSelector); + break; + } + case 58: { + if (selector.charCodeAt(selectorIndex + 1) === 58) { + tokens.push({ + type: SelectorType.PseudoElement, + name: getName2(2).toLowerCase(), + data: selector.charCodeAt(selectorIndex) === 40 ? readValueWithParenthesis() : null + }); + continue; + } + const name = getName2(1).toLowerCase(); + let data2 = null; + if (selector.charCodeAt(selectorIndex) === 40) { + if (unpackPseudos.has(name)) { + if (isQuote(selector.charCodeAt(selectorIndex + 1))) { + throw new Error(`Pseudo-selector ${name} cannot be quoted`); + } + data2 = []; + selectorIndex = parseSelector(data2, selector, selectorIndex + 1); + if (selector.charCodeAt(selectorIndex) !== 41) { + throw new Error(`Missing closing parenthesis in :${name} (${selector})`); + } + selectorIndex += 1; + } else { + data2 = readValueWithParenthesis(); + if (stripQuotesFromPseudos.has(name)) { + const quot = data2.charCodeAt(0); + if (quot === data2.charCodeAt(data2.length - 1) && isQuote(quot)) { + data2 = data2.slice(1, -1); + } + } + data2 = unescapeCSS(data2); + } + } + tokens.push({ type: SelectorType.Pseudo, name, data: data2 }); + break; + } + case 44: { + finalizeSubselector(); + tokens = []; + stripWhitespace(1); + break; + } + default: { + if (selector.startsWith("/*", selectorIndex)) { + const endIndex = selector.indexOf("*/", selectorIndex + 2); + if (endIndex < 0) { + throw new Error("Comment was not terminated"); + } + selectorIndex = endIndex + 2; + if (tokens.length === 0) { + stripWhitespace(0); + } + break; + } + let namespace = null; + let name; + if (firstChar === 42) { + selectorIndex += 1; + name = "*"; + } else if (firstChar === 124) { + name = ""; + if (selector.charCodeAt(selectorIndex + 1) === 124) { + addTraversal(SelectorType.ColumnCombinator); + stripWhitespace(2); + break; + } + } else if (reName.test(selector.slice(selectorIndex))) { + name = getName2(0); + } else { + break loop; + } + if (selector.charCodeAt(selectorIndex) === 124 && selector.charCodeAt(selectorIndex + 1) !== 124) { + namespace = name; + if (selector.charCodeAt(selectorIndex + 1) === 42) { + name = "*"; + selectorIndex += 2; + } else { + name = getName2(1); + } + } + tokens.push(name === "*" ? { type: SelectorType.Universal, namespace } : { type: SelectorType.Tag, name, namespace }); + } + } + } + finalizeSubselector(); + return selectorIndex; +} +function getDefaultExportFromCjs(x) { + return x && x.__esModule && Object.prototype.hasOwnProperty.call(x, "default") ? x["default"] : x; +} +var boolbase$1; +var hasRequiredBoolbase; +function requireBoolbase() { + if (hasRequiredBoolbase) return boolbase$1; + hasRequiredBoolbase = 1; + boolbase$1 = { + trueFunc: function trueFunc() { + return true; + }, + falseFunc: function falseFunc() { + return false; + } + }; + return boolbase$1; +} +var boolbaseExports = requireBoolbase(); +const boolbase = /* @__PURE__ */ getDefaultExportFromCjs(boolbaseExports); +const procedure = /* @__PURE__ */ new Map([ + [SelectorType.Universal, 50], + [SelectorType.Tag, 30], + [SelectorType.Attribute, 1], + [SelectorType.Pseudo, 0] +]); +function isTraversal(token) { + return !procedure.has(token.type); +} +const attributes = /* @__PURE__ */ new Map([ + [AttributeAction.Exists, 10], + [AttributeAction.Equals, 8], + [AttributeAction.Not, 7], + [AttributeAction.Start, 6], + [AttributeAction.End, 6], + [AttributeAction.Any, 5] +]); +function sortByProcedure(arr) { + const procs = arr.map(getProcedure); + for (let i = 1; i < arr.length; i++) { + const procNew = procs[i]; + if (procNew < 0) + continue; + for (let j = i - 1; j >= 0 && procNew < procs[j]; j--) { + const token = arr[j + 1]; + arr[j + 1] = arr[j]; + arr[j] = token; + procs[j + 1] = procs[j]; + procs[j] = procNew; + } + } +} +function getProcedure(token) { + var _a2, _b; + let proc = (_a2 = procedure.get(token.type)) !== null && _a2 !== void 0 ? _a2 : -1; + if (token.type === SelectorType.Attribute) { + proc = (_b = attributes.get(token.action)) !== null && _b !== void 0 ? _b : 4; + if (token.action === AttributeAction.Equals && token.name === "id") { + proc = 9; + } + if (token.ignoreCase) { + proc >>= 1; + } + } else if (token.type === SelectorType.Pseudo) { + if (!token.data) { + proc = 3; + } else if (token.name === "has" || token.name === "contains") { + proc = 0; + } else if (Array.isArray(token.data)) { + proc = Math.min(...token.data.map((d) => Math.min(...d.map(getProcedure)))); + if (proc < 0) { + proc = 0; + } + } else { + proc = 2; + } + } + return proc; +} +const reChars = /[-[\]{}()*+?.,\\^$|#\s]/g; +function escapeRegex(value) { + return value.replace(reChars, "\\$&"); +} +const caseInsensitiveAttributes = /* @__PURE__ */ new Set([ + "accept", + "accept-charset", + "align", + "alink", + "axis", + "bgcolor", + "charset", + "checked", + "clear", + "codetype", + "color", + "compact", + "declare", + "defer", + "dir", + "direction", + "disabled", + "enctype", + "face", + "frame", + "hreflang", + "http-equiv", + "lang", + "language", + "link", + "media", + "method", + "multiple", + "nohref", + "noresize", + "noshade", + "nowrap", + "readonly", + "rel", + "rev", + "rules", + "scope", + "scrolling", + "selected", + "shape", + "target", + "text", + "type", + "valign", + "valuetype", + "vlink" +]); +function shouldIgnoreCase(selector, options) { + return typeof selector.ignoreCase === "boolean" ? selector.ignoreCase : selector.ignoreCase === "quirks" ? !!options.quirksMode : !options.xmlMode && caseInsensitiveAttributes.has(selector.name); +} +const attributeRules = { + equals(next2, data2, options) { + const { adapter } = options; + const { name } = data2; + let { value } = data2; + if (shouldIgnoreCase(data2, options)) { + value = value.toLowerCase(); + return (elem) => { + const attr2 = adapter.getAttributeValue(elem, name); + return attr2 != null && attr2.length === value.length && attr2.toLowerCase() === value && next2(elem); + }; + } + return (elem) => adapter.getAttributeValue(elem, name) === value && next2(elem); + }, + hyphen(next2, data2, options) { + const { adapter } = options; + const { name } = data2; + let { value } = data2; + const len = value.length; + if (shouldIgnoreCase(data2, options)) { + value = value.toLowerCase(); + return function hyphenIC(elem) { + const attr2 = adapter.getAttributeValue(elem, name); + return attr2 != null && (attr2.length === len || attr2.charAt(len) === "-") && attr2.substr(0, len).toLowerCase() === value && next2(elem); + }; + } + return function hyphen(elem) { + const attr2 = adapter.getAttributeValue(elem, name); + return attr2 != null && (attr2.length === len || attr2.charAt(len) === "-") && attr2.substr(0, len) === value && next2(elem); + }; + }, + element(next2, data2, options) { + const { adapter } = options; + const { name, value } = data2; + if (/\s/.test(value)) { + return boolbase.falseFunc; + } + const regex = new RegExp(`(?:^|\\s)${escapeRegex(value)}(?:$|\\s)`, shouldIgnoreCase(data2, options) ? "i" : ""); + return function element(elem) { + const attr2 = adapter.getAttributeValue(elem, name); + return attr2 != null && attr2.length >= value.length && regex.test(attr2) && next2(elem); + }; + }, + exists(next2, { name }, { adapter }) { + return (elem) => adapter.hasAttrib(elem, name) && next2(elem); + }, + start(next2, data2, options) { + const { adapter } = options; + const { name } = data2; + let { value } = data2; + const len = value.length; + if (len === 0) { + return boolbase.falseFunc; + } + if (shouldIgnoreCase(data2, options)) { + value = value.toLowerCase(); + return (elem) => { + const attr2 = adapter.getAttributeValue(elem, name); + return attr2 != null && attr2.length >= len && attr2.substr(0, len).toLowerCase() === value && next2(elem); + }; + } + return (elem) => { + var _a2; + return !!((_a2 = adapter.getAttributeValue(elem, name)) === null || _a2 === void 0 ? void 0 : _a2.startsWith(value)) && next2(elem); + }; + }, + end(next2, data2, options) { + const { adapter } = options; + const { name } = data2; + let { value } = data2; + const len = -value.length; + if (len === 0) { + return boolbase.falseFunc; + } + if (shouldIgnoreCase(data2, options)) { + value = value.toLowerCase(); + return (elem) => { + var _a2; + return ((_a2 = adapter.getAttributeValue(elem, name)) === null || _a2 === void 0 ? void 0 : _a2.substr(len).toLowerCase()) === value && next2(elem); + }; + } + return (elem) => { + var _a2; + return !!((_a2 = adapter.getAttributeValue(elem, name)) === null || _a2 === void 0 ? void 0 : _a2.endsWith(value)) && next2(elem); + }; + }, + any(next2, data2, options) { + const { adapter } = options; + const { name, value } = data2; + if (value === "") { + return boolbase.falseFunc; + } + if (shouldIgnoreCase(data2, options)) { + const regex = new RegExp(escapeRegex(value), "i"); + return function anyIC(elem) { + const attr2 = adapter.getAttributeValue(elem, name); + return attr2 != null && attr2.length >= value.length && regex.test(attr2) && next2(elem); + }; + } + return (elem) => { + var _a2; + return !!((_a2 = adapter.getAttributeValue(elem, name)) === null || _a2 === void 0 ? void 0 : _a2.includes(value)) && next2(elem); + }; + }, + not(next2, data2, options) { + const { adapter } = options; + const { name } = data2; + let { value } = data2; + if (value === "") { + return (elem) => !!adapter.getAttributeValue(elem, name) && next2(elem); + } else if (shouldIgnoreCase(data2, options)) { + value = value.toLowerCase(); + return (elem) => { + const attr2 = adapter.getAttributeValue(elem, name); + return (attr2 == null || attr2.length !== value.length || attr2.toLowerCase() !== value) && next2(elem); + }; + } + return (elem) => adapter.getAttributeValue(elem, name) !== value && next2(elem); + } +}; +const whitespace = /* @__PURE__ */ new Set([9, 10, 12, 13, 32]); +const ZERO = "0".charCodeAt(0); +const NINE = "9".charCodeAt(0); +function parse$1(formula) { + formula = formula.trim().toLowerCase(); + if (formula === "even") { + return [2, 0]; + } else if (formula === "odd") { + return [2, 1]; + } + let idx = 0; + let a = 0; + let sign = readSign(); + let number = readNumber(); + if (idx < formula.length && formula.charAt(idx) === "n") { + idx++; + a = sign * (number !== null && number !== void 0 ? number : 1); + skipWhitespace(); + if (idx < formula.length) { + sign = readSign(); + skipWhitespace(); + number = readNumber(); + } else { + sign = number = 0; + } + } + if (number === null || idx < formula.length) { + throw new Error(`n-th rule couldn't be parsed ('${formula}')`); + } + return [a, sign * number]; + function readSign() { + if (formula.charAt(idx) === "-") { + idx++; + return -1; + } + if (formula.charAt(idx) === "+") { + idx++; + } + return 1; + } + function readNumber() { + const start = idx; + let value = 0; + while (idx < formula.length && formula.charCodeAt(idx) >= ZERO && formula.charCodeAt(idx) <= NINE) { + value = value * 10 + (formula.charCodeAt(idx) - ZERO); + idx++; + } + return idx === start ? null : value; + } + function skipWhitespace() { + while (idx < formula.length && whitespace.has(formula.charCodeAt(idx))) { + idx++; + } + } +} +function compile(parsed) { + const a = parsed[0]; + const b = parsed[1] - 1; + if (b < 0 && a <= 0) + return boolbase.falseFunc; + if (a === -1) + return (index2) => index2 <= b; + if (a === 0) + return (index2) => index2 === b; + if (a === 1) + return b < 0 ? boolbase.trueFunc : (index2) => index2 >= b; + const absA = Math.abs(a); + const bMod = (b % absA + absA) % absA; + return a > 1 ? (index2) => index2 >= b && index2 % absA === bMod : (index2) => index2 <= b && index2 % absA === bMod; +} +function nthCheck(formula) { + return compile(parse$1(formula)); +} +function getChildFunc(next2, adapter) { + return (elem) => { + const parent2 = adapter.getParent(elem); + return parent2 != null && adapter.isTag(parent2) && next2(elem); + }; +} +const filters = { + contains(next2, text2, { adapter }) { + return function contains2(elem) { + return next2(elem) && adapter.getText(elem).includes(text2); + }; + }, + icontains(next2, text2, { adapter }) { + const itext = text2.toLowerCase(); + return function icontains(elem) { + return next2(elem) && adapter.getText(elem).toLowerCase().includes(itext); + }; + }, + // Location specific methods + "nth-child"(next2, rule, { adapter, equals }) { + const func = nthCheck(rule); + if (func === boolbase.falseFunc) + return boolbase.falseFunc; + if (func === boolbase.trueFunc) + return getChildFunc(next2, adapter); + return function nthChild(elem) { + const siblings2 = adapter.getSiblings(elem); + let pos = 0; + for (let i = 0; i < siblings2.length; i++) { + if (equals(elem, siblings2[i])) + break; + if (adapter.isTag(siblings2[i])) { + pos++; + } + } + return func(pos) && next2(elem); + }; + }, + "nth-last-child"(next2, rule, { adapter, equals }) { + const func = nthCheck(rule); + if (func === boolbase.falseFunc) + return boolbase.falseFunc; + if (func === boolbase.trueFunc) + return getChildFunc(next2, adapter); + return function nthLastChild(elem) { + const siblings2 = adapter.getSiblings(elem); + let pos = 0; + for (let i = siblings2.length - 1; i >= 0; i--) { + if (equals(elem, siblings2[i])) + break; + if (adapter.isTag(siblings2[i])) { + pos++; + } + } + return func(pos) && next2(elem); + }; + }, + "nth-of-type"(next2, rule, { adapter, equals }) { + const func = nthCheck(rule); + if (func === boolbase.falseFunc) + return boolbase.falseFunc; + if (func === boolbase.trueFunc) + return getChildFunc(next2, adapter); + return function nthOfType(elem) { + const siblings2 = adapter.getSiblings(elem); + let pos = 0; + for (let i = 0; i < siblings2.length; i++) { + const currentSibling = siblings2[i]; + if (equals(elem, currentSibling)) + break; + if (adapter.isTag(currentSibling) && adapter.getName(currentSibling) === adapter.getName(elem)) { + pos++; + } + } + return func(pos) && next2(elem); + }; + }, + "nth-last-of-type"(next2, rule, { adapter, equals }) { + const func = nthCheck(rule); + if (func === boolbase.falseFunc) + return boolbase.falseFunc; + if (func === boolbase.trueFunc) + return getChildFunc(next2, adapter); + return function nthLastOfType(elem) { + const siblings2 = adapter.getSiblings(elem); + let pos = 0; + for (let i = siblings2.length - 1; i >= 0; i--) { + const currentSibling = siblings2[i]; + if (equals(elem, currentSibling)) + break; + if (adapter.isTag(currentSibling) && adapter.getName(currentSibling) === adapter.getName(elem)) { + pos++; + } + } + return func(pos) && next2(elem); + }; + }, + // TODO determine the actual root element + root(next2, _rule, { adapter }) { + return (elem) => { + const parent2 = adapter.getParent(elem); + return (parent2 == null || !adapter.isTag(parent2)) && next2(elem); + }; + }, + scope(next2, rule, options, context) { + const { equals } = options; + if (!context || context.length === 0) { + return filters["root"](next2, rule, options); + } + if (context.length === 1) { + return (elem) => equals(context[0], elem) && next2(elem); + } + return (elem) => context.includes(elem) && next2(elem); + }, + hover: dynamicStatePseudo("isHovered"), + visited: dynamicStatePseudo("isVisited"), + active: dynamicStatePseudo("isActive") +}; +function dynamicStatePseudo(name) { + return function dynamicPseudo(next2, _rule, { adapter }) { + const func = adapter[name]; + if (typeof func !== "function") { + return boolbase.falseFunc; + } + return function active(elem) { + return func(elem) && next2(elem); + }; + }; +} +const pseudos = { + empty(elem, { adapter }) { + return !adapter.getChildren(elem).some((elem2) => ( + // FIXME: `getText` call is potentially expensive. + adapter.isTag(elem2) || adapter.getText(elem2) !== "" + )); + }, + "first-child"(elem, { adapter, equals }) { + if (adapter.prevElementSibling) { + return adapter.prevElementSibling(elem) == null; + } + const firstChild = adapter.getSiblings(elem).find((elem2) => adapter.isTag(elem2)); + return firstChild != null && equals(elem, firstChild); + }, + "last-child"(elem, { adapter, equals }) { + const siblings2 = adapter.getSiblings(elem); + for (let i = siblings2.length - 1; i >= 0; i--) { + if (equals(elem, siblings2[i])) + return true; + if (adapter.isTag(siblings2[i])) + break; + } + return false; + }, + "first-of-type"(elem, { adapter, equals }) { + const siblings2 = adapter.getSiblings(elem); + const elemName = adapter.getName(elem); + for (let i = 0; i < siblings2.length; i++) { + const currentSibling = siblings2[i]; + if (equals(elem, currentSibling)) + return true; + if (adapter.isTag(currentSibling) && adapter.getName(currentSibling) === elemName) { + break; + } + } + return false; + }, + "last-of-type"(elem, { adapter, equals }) { + const siblings2 = adapter.getSiblings(elem); + const elemName = adapter.getName(elem); + for (let i = siblings2.length - 1; i >= 0; i--) { + const currentSibling = siblings2[i]; + if (equals(elem, currentSibling)) + return true; + if (adapter.isTag(currentSibling) && adapter.getName(currentSibling) === elemName) { + break; + } + } + return false; + }, + "only-of-type"(elem, { adapter, equals }) { + const elemName = adapter.getName(elem); + return adapter.getSiblings(elem).every((sibling) => equals(elem, sibling) || !adapter.isTag(sibling) || adapter.getName(sibling) !== elemName); + }, + "only-child"(elem, { adapter, equals }) { + return adapter.getSiblings(elem).every((sibling) => equals(elem, sibling) || !adapter.isTag(sibling)); + } +}; +function verifyPseudoArgs(func, name, subselect, argIndex) { + if (subselect === null) { + if (func.length > argIndex) { + throw new Error(`Pseudo-class :${name} requires an argument`); + } + } else if (func.length === argIndex) { + throw new Error(`Pseudo-class :${name} doesn't have any arguments`); + } +} +const aliases = { + // Links + "any-link": ":is(a, area, link)[href]", + link: ":any-link:not(:visited)", + // Forms + // https://html.spec.whatwg.org/multipage/scripting.html#disabled-elements + disabled: `:is( + :is(button, input, select, textarea, optgroup, option)[disabled], + optgroup[disabled] > option, + fieldset[disabled]:not(fieldset[disabled] legend:first-of-type *) + )`, + enabled: ":not(:disabled)", + checked: ":is(:is(input[type=radio], input[type=checkbox])[checked], option:selected)", + required: ":is(input, select, textarea)[required]", + optional: ":is(input, select, textarea):not([required])", + // JQuery extensions + // https://html.spec.whatwg.org/multipage/form-elements.html#concept-option-selectedness + selected: "option:is([selected], select:not([multiple]):not(:has(> option[selected])) > :first-of-type)", + checkbox: "[type=checkbox]", + file: "[type=file]", + password: "[type=password]", + radio: "[type=radio]", + reset: "[type=reset]", + image: "[type=image]", + submit: "[type=submit]", + parent: ":not(:empty)", + header: ":is(h1, h2, h3, h4, h5, h6)", + button: ":is(button, input[type=button])", + input: ":is(input, textarea, select, button)", + text: "input:is(:not([type!='']), [type=text])" +}; +const PLACEHOLDER_ELEMENT = {}; +function ensureIsTag(next2, adapter) { + if (next2 === boolbase.falseFunc) + return boolbase.falseFunc; + return (elem) => adapter.isTag(elem) && next2(elem); +} +function getNextSiblings(elem, adapter) { + const siblings2 = adapter.getSiblings(elem); + if (siblings2.length <= 1) + return []; + const elemIndex = siblings2.indexOf(elem); + if (elemIndex < 0 || elemIndex === siblings2.length - 1) + return []; + return siblings2.slice(elemIndex + 1).filter(adapter.isTag); +} +function copyOptions(options) { + return { + xmlMode: !!options.xmlMode, + lowerCaseAttributeNames: !!options.lowerCaseAttributeNames, + lowerCaseTags: !!options.lowerCaseTags, + quirksMode: !!options.quirksMode, + cacheResults: !!options.cacheResults, + pseudos: options.pseudos, + adapter: options.adapter, + equals: options.equals + }; +} +const is$2 = (next2, token, options, context, compileToken2) => { + const func = compileToken2(token, copyOptions(options), context); + return func === boolbase.trueFunc ? next2 : func === boolbase.falseFunc ? boolbase.falseFunc : (elem) => func(elem) && next2(elem); +}; +const subselects = { + is: is$2, + /** + * `:matches` and `:where` are aliases for `:is`. + */ + matches: is$2, + where: is$2, + not(next2, token, options, context, compileToken2) { + const func = compileToken2(token, copyOptions(options), context); + return func === boolbase.falseFunc ? next2 : func === boolbase.trueFunc ? boolbase.falseFunc : (elem) => !func(elem) && next2(elem); + }, + has(next2, subselect, options, _context, compileToken2) { + const { adapter } = options; + const opts = copyOptions(options); + opts.relativeSelector = true; + const context = subselect.some((s) => s.some(isTraversal)) ? ( + // Used as a placeholder. Will be replaced with the actual element. + [PLACEHOLDER_ELEMENT] + ) : void 0; + const compiled = compileToken2(subselect, opts, context); + if (compiled === boolbase.falseFunc) + return boolbase.falseFunc; + const hasElement = ensureIsTag(compiled, adapter); + if (context && compiled !== boolbase.trueFunc) { + const { shouldTestNextSiblings = false } = compiled; + return (elem) => { + if (!next2(elem)) + return false; + context[0] = elem; + const childs = adapter.getChildren(elem); + const nextElements = shouldTestNextSiblings ? [...childs, ...getNextSiblings(elem, adapter)] : childs; + return adapter.existsOne(hasElement, nextElements); + }; + } + return (elem) => next2(elem) && adapter.existsOne(hasElement, adapter.getChildren(elem)); + } +}; +function compilePseudoSelector(next2, selector, options, context, compileToken2) { + var _a2; + const { name, data: data2 } = selector; + if (Array.isArray(data2)) { + if (!(name in subselects)) { + throw new Error(`Unknown pseudo-class :${name}(${data2})`); + } + return subselects[name](next2, data2, options, context, compileToken2); + } + const userPseudo = (_a2 = options.pseudos) === null || _a2 === void 0 ? void 0 : _a2[name]; + const stringPseudo = typeof userPseudo === "string" ? userPseudo : aliases[name]; + if (typeof stringPseudo === "string") { + if (data2 != null) { + throw new Error(`Pseudo ${name} doesn't have any arguments`); + } + const alias = parse$2(stringPseudo); + return subselects["is"](next2, alias, options, context, compileToken2); + } + if (typeof userPseudo === "function") { + verifyPseudoArgs(userPseudo, name, data2, 1); + return (elem) => userPseudo(elem, data2) && next2(elem); + } + if (name in filters) { + return filters[name](next2, data2, options, context); + } + if (name in pseudos) { + const pseudo = pseudos[name]; + verifyPseudoArgs(pseudo, name, data2, 2); + return (elem) => pseudo(elem, options, data2) && next2(elem); + } + throw new Error(`Unknown pseudo-class :${name}`); +} +function getElementParent(node, adapter) { + const parent2 = adapter.getParent(node); + if (parent2 && adapter.isTag(parent2)) { + return parent2; + } + return null; +} +function compileGeneralSelector(next2, selector, options, context, compileToken2) { + const { adapter, equals } = options; + switch (selector.type) { + case SelectorType.PseudoElement: { + throw new Error("Pseudo-elements are not supported by css-select"); + } + case SelectorType.ColumnCombinator: { + throw new Error("Column combinators are not yet supported by css-select"); + } + case SelectorType.Attribute: { + if (selector.namespace != null) { + throw new Error("Namespaced attributes are not yet supported by css-select"); + } + if (!options.xmlMode || options.lowerCaseAttributeNames) { + selector.name = selector.name.toLowerCase(); + } + return attributeRules[selector.action](next2, selector, options); + } + case SelectorType.Pseudo: { + return compilePseudoSelector(next2, selector, options, context, compileToken2); + } + // Tags + case SelectorType.Tag: { + if (selector.namespace != null) { + throw new Error("Namespaced tag names are not yet supported by css-select"); + } + let { name } = selector; + if (!options.xmlMode || options.lowerCaseTags) { + name = name.toLowerCase(); + } + return function tag(elem) { + return adapter.getName(elem) === name && next2(elem); + }; + } + // Traversal + case SelectorType.Descendant: { + if (options.cacheResults === false || typeof WeakSet === "undefined") { + return function descendant(elem) { + let current = elem; + while (current = getElementParent(current, adapter)) { + if (next2(current)) { + return true; + } + } + return false; + }; + } + const isFalseCache = /* @__PURE__ */ new WeakSet(); + return function cachedDescendant(elem) { + let current = elem; + while (current = getElementParent(current, adapter)) { + if (!isFalseCache.has(current)) { + if (adapter.isTag(current) && next2(current)) { + return true; + } + isFalseCache.add(current); + } + } + return false; + }; + } + case "_flexibleDescendant": { + return function flexibleDescendant(elem) { + let current = elem; + do { + if (next2(current)) + return true; + } while (current = getElementParent(current, adapter)); + return false; + }; + } + case SelectorType.Parent: { + return function parent2(elem) { + return adapter.getChildren(elem).some((elem2) => adapter.isTag(elem2) && next2(elem2)); + }; + } + case SelectorType.Child: { + return function child(elem) { + const parent2 = adapter.getParent(elem); + return parent2 != null && adapter.isTag(parent2) && next2(parent2); + }; + } + case SelectorType.Sibling: { + return function sibling(elem) { + const siblings2 = adapter.getSiblings(elem); + for (let i = 0; i < siblings2.length; i++) { + const currentSibling = siblings2[i]; + if (equals(elem, currentSibling)) + break; + if (adapter.isTag(currentSibling) && next2(currentSibling)) { + return true; + } + } + return false; + }; + } + case SelectorType.Adjacent: { + if (adapter.prevElementSibling) { + return function adjacent(elem) { + const previous = adapter.prevElementSibling(elem); + return previous != null && next2(previous); + }; + } + return function adjacent(elem) { + const siblings2 = adapter.getSiblings(elem); + let lastElement; + for (let i = 0; i < siblings2.length; i++) { + const currentSibling = siblings2[i]; + if (equals(elem, currentSibling)) + break; + if (adapter.isTag(currentSibling)) { + lastElement = currentSibling; + } + } + return !!lastElement && next2(lastElement); + }; + } + case SelectorType.Universal: { + if (selector.namespace != null && selector.namespace !== "*") { + throw new Error("Namespaced universal selectors are not yet supported by css-select"); + } + return next2; + } + } +} +function includesScopePseudo(t) { + return t.type === SelectorType.Pseudo && (t.name === "scope" || Array.isArray(t.data) && t.data.some((data2) => data2.some(includesScopePseudo))); +} +const DESCENDANT_TOKEN = { type: SelectorType.Descendant }; +const FLEXIBLE_DESCENDANT_TOKEN = { + type: "_flexibleDescendant" +}; +const SCOPE_TOKEN = { + type: SelectorType.Pseudo, + name: "scope", + data: null +}; +function absolutize(token, { adapter }, context) { + const hasContext = !!(context === null || context === void 0 ? void 0 : context.every((e) => { + const parent2 = adapter.isTag(e) && adapter.getParent(e); + return e === PLACEHOLDER_ELEMENT || parent2 && adapter.isTag(parent2); + })); + for (const t of token) { + if (t.length > 0 && isTraversal(t[0]) && t[0].type !== SelectorType.Descendant) ; + else if (hasContext && !t.some(includesScopePseudo)) { + t.unshift(DESCENDANT_TOKEN); + } else { + continue; + } + t.unshift(SCOPE_TOKEN); + } +} +function compileToken(token, options, context) { + var _a2; + token.forEach(sortByProcedure); + context = (_a2 = options.context) !== null && _a2 !== void 0 ? _a2 : context; + const isArrayContext = Array.isArray(context); + const finalContext = context && (Array.isArray(context) ? context : [context]); + if (options.relativeSelector !== false) { + absolutize(token, options, finalContext); + } else if (token.some((t) => t.length > 0 && isTraversal(t[0]))) { + throw new Error("Relative selectors are not allowed when the `relativeSelector` option is disabled"); + } + let shouldTestNextSiblings = false; + const query = token.map((rules) => { + if (rules.length >= 2) { + const [first2, second] = rules; + if (first2.type !== SelectorType.Pseudo || first2.name !== "scope") ; + else if (isArrayContext && second.type === SelectorType.Descendant) { + rules[1] = FLEXIBLE_DESCENDANT_TOKEN; + } else if (second.type === SelectorType.Adjacent || second.type === SelectorType.Sibling) { + shouldTestNextSiblings = true; + } + } + return compileRules(rules, options, finalContext); + }).reduce(reduceRules, boolbase.falseFunc); + query.shouldTestNextSiblings = shouldTestNextSiblings; + return query; +} +function compileRules(rules, options, context) { + var _a2; + return rules.reduce((previous, rule) => previous === boolbase.falseFunc ? boolbase.falseFunc : compileGeneralSelector(previous, rule, options, context, compileToken), (_a2 = options.rootFunc) !== null && _a2 !== void 0 ? _a2 : boolbase.trueFunc); +} +function reduceRules(a, b) { + if (b === boolbase.falseFunc || a === boolbase.trueFunc) { + return a; + } + if (a === boolbase.falseFunc || b === boolbase.trueFunc) { + return b; + } + return function combine(elem) { + return a(elem) || b(elem); + }; +} +const defaultEquals = (a, b) => a === b; +const defaultOptions$1 = { + adapter: DomUtils, + equals: defaultEquals +}; +function convertOptionFormats(options) { + var _a2, _b, _c, _d; + const opts = options !== null && options !== void 0 ? options : defaultOptions$1; + (_a2 = opts.adapter) !== null && _a2 !== void 0 ? _a2 : opts.adapter = DomUtils; + (_b = opts.equals) !== null && _b !== void 0 ? _b : opts.equals = (_d = (_c = opts.adapter) === null || _c === void 0 ? void 0 : _c.equals) !== null && _d !== void 0 ? _d : defaultEquals; + return opts; +} +function wrapCompile(func) { + return function addAdapter(selector, options, context) { + const opts = convertOptionFormats(options); + return func(selector, opts, context); + }; +} +const _compileToken = wrapCompile(compileToken); +function prepareContext(elems, adapter, shouldTestNextSiblings = false) { + if (shouldTestNextSiblings) { + elems = appendNextSiblings(elems, adapter); + } + return Array.isArray(elems) ? adapter.removeSubsets(elems) : adapter.getChildren(elems); +} +function appendNextSiblings(elem, adapter) { + const elems = Array.isArray(elem) ? elem.slice(0) : [elem]; + const elemsLength = elems.length; + for (let i = 0; i < elemsLength; i++) { + const nextSiblings = getNextSiblings(elems[i], adapter); + elems.push(...nextSiblings); + } + return elems; +} +const filterNames = /* @__PURE__ */ new Set([ + "first", + "last", + "eq", + "gt", + "nth", + "lt", + "even", + "odd" +]); +function isFilter(s) { + if (s.type !== "pseudo") + return false; + if (filterNames.has(s.name)) + return true; + if (s.name === "not" && Array.isArray(s.data)) { + return s.data.some((s2) => s2.some(isFilter)); + } + return false; +} +function getLimit(filter2, data2, partLimit) { + const num = data2 != null ? parseInt(data2, 10) : NaN; + switch (filter2) { + case "first": + return 1; + case "nth": + case "eq": + return isFinite(num) ? num >= 0 ? num + 1 : Infinity : 0; + case "lt": + return isFinite(num) ? num >= 0 ? Math.min(num, partLimit) : Infinity : 0; + case "gt": + return isFinite(num) ? Infinity : 0; + case "odd": + return 2 * partLimit; + case "even": + return 2 * partLimit - 1; + case "last": + case "not": + return Infinity; + } +} +function getDocumentRoot(node) { + while (node.parent) + node = node.parent; + return node; +} +function groupSelectors(selectors) { + const filteredSelectors = []; + const plainSelectors = []; + for (const selector of selectors) { + if (selector.some(isFilter)) { + filteredSelectors.push(selector); + } else { + plainSelectors.push(selector); + } + } + return [plainSelectors, filteredSelectors]; +} +const UNIVERSAL_SELECTOR = { + type: SelectorType.Universal, + namespace: null +}; +const SCOPE_PSEUDO = { + type: SelectorType.Pseudo, + name: "scope", + data: null +}; +function is$1(element, selector, options = {}) { + return some([element], selector, options); +} +function some(elements, selector, options = {}) { + if (typeof selector === "function") + return elements.some(selector); + const [plain, filtered] = groupSelectors(parse$2(selector)); + return plain.length > 0 && elements.some(_compileToken(plain, options)) || filtered.some((sel) => filterBySelector(sel, elements, options).length > 0); +} +function filterByPosition(filter2, elems, data2, options) { + const num = typeof data2 === "string" ? parseInt(data2, 10) : NaN; + switch (filter2) { + case "first": + case "lt": + return elems; + case "last": + return elems.length > 0 ? [elems[elems.length - 1]] : elems; + case "nth": + case "eq": + return isFinite(num) && Math.abs(num) < elems.length ? [num < 0 ? elems[elems.length + num] : elems[num]] : []; + case "gt": + return isFinite(num) ? elems.slice(num + 1) : []; + case "even": + return elems.filter((_, i) => i % 2 === 0); + case "odd": + return elems.filter((_, i) => i % 2 === 1); + case "not": { + const filtered = new Set(filterParsed(data2, elems, options)); + return elems.filter((e) => !filtered.has(e)); + } + } +} +function filter$1(selector, elements, options = {}) { + return filterParsed(parse$2(selector), elements, options); +} +function filterParsed(selector, elements, options) { + if (elements.length === 0) + return []; + const [plainSelectors, filteredSelectors] = groupSelectors(selector); + let found; + if (plainSelectors.length) { + const filtered = filterElements(elements, plainSelectors, options); + if (filteredSelectors.length === 0) { + return filtered; + } + if (filtered.length) { + found = new Set(filtered); + } + } + for (let i = 0; i < filteredSelectors.length && (found === null || found === void 0 ? void 0 : found.size) !== elements.length; i++) { + const filteredSelector = filteredSelectors[i]; + const missing = found ? elements.filter((e) => isTag(e) && !found.has(e)) : elements; + if (missing.length === 0) + break; + const filtered = filterBySelector(filteredSelector, elements, options); + if (filtered.length) { + if (!found) { + if (i === filteredSelectors.length - 1) { + return filtered; + } + found = new Set(filtered); + } else { + filtered.forEach((el) => found.add(el)); + } + } + } + return typeof found !== "undefined" ? found.size === elements.length ? elements : ( + // Filter elements to preserve order + elements.filter((el) => found.has(el)) + ) : []; +} +function filterBySelector(selector, elements, options) { + var _a2; + if (selector.some(isTraversal$1)) { + const root2 = (_a2 = options.root) !== null && _a2 !== void 0 ? _a2 : getDocumentRoot(elements[0]); + const opts = { ...options, context: elements, relativeSelector: false }; + selector.push(SCOPE_PSEUDO); + return findFilterElements(root2, selector, opts, true, elements.length); + } + return findFilterElements(elements, selector, options, false, elements.length); +} +function select(selector, root2, options = {}, limit = Infinity) { + if (typeof selector === "function") { + return find$1(root2, selector); + } + const [plain, filtered] = groupSelectors(parse$2(selector)); + const results = filtered.map((sel) => findFilterElements(root2, sel, options, true, limit)); + if (plain.length) { + results.push(findElements(root2, plain, options, limit)); + } + if (results.length === 0) { + return []; + } + if (results.length === 1) { + return results[0]; + } + return uniqueSort(results.reduce((a, b) => [...a, ...b])); +} +function findFilterElements(root2, selector, options, queryForSelector, totalLimit) { + const filterIndex = selector.findIndex(isFilter); + const sub = selector.slice(0, filterIndex); + const filter2 = selector[filterIndex]; + const partLimit = selector.length - 1 === filterIndex ? totalLimit : Infinity; + const limit = getLimit(filter2.name, filter2.data, partLimit); + if (limit === 0) + return []; + const elemsNoLimit = sub.length === 0 && !Array.isArray(root2) ? getChildren(root2).filter(isTag) : sub.length === 0 ? (Array.isArray(root2) ? root2 : [root2]).filter(isTag) : queryForSelector || sub.some(isTraversal$1) ? findElements(root2, [sub], options, limit) : filterElements(root2, [sub], options); + const elems = elemsNoLimit.slice(0, limit); + let result = filterByPosition(filter2.name, elems, filter2.data, options); + if (result.length === 0 || selector.length === filterIndex + 1) { + return result; + } + const remainingSelector = selector.slice(filterIndex + 1); + const remainingHasTraversal = remainingSelector.some(isTraversal$1); + if (remainingHasTraversal) { + if (isTraversal$1(remainingSelector[0])) { + const { type } = remainingSelector[0]; + if (type === SelectorType.Sibling || type === SelectorType.Adjacent) { + result = prepareContext(result, DomUtils, true); + } + remainingSelector.unshift(UNIVERSAL_SELECTOR); + } + options = { + ...options, + // Avoid absolutizing the selector + relativeSelector: false, + /* + * Add a custom root func, to make sure traversals don't match elements + * that aren't a part of the considered tree. + */ + rootFunc: (el) => result.includes(el) + }; + } else if (options.rootFunc && options.rootFunc !== boolbaseExports.trueFunc) { + options = { ...options, rootFunc: boolbaseExports.trueFunc }; + } + return remainingSelector.some(isFilter) ? findFilterElements(result, remainingSelector, options, false, totalLimit) : remainingHasTraversal ? ( + // Query existing elements to resolve traversal. + findElements(result, [remainingSelector], options, totalLimit) + ) : ( + // If we don't have any more traversals, simply filter elements. + filterElements(result, [remainingSelector], options) + ); +} +function findElements(root2, sel, options, limit) { + const query = _compileToken(sel, options, root2); + return find$1(root2, query, limit); +} +function find$1(root2, query, limit = Infinity) { + const elems = prepareContext(root2, DomUtils, query.shouldTestNextSiblings); + return find$2((node) => isTag(node) && query(node), elems, true, limit); +} +function filterElements(elements, sel, options) { + const els = (Array.isArray(elements) ? elements : [elements]).filter(isTag); + if (els.length === 0) + return els; + const query = _compileToken(sel, options); + return query === boolbaseExports.trueFunc ? els : els.filter(query); +} +const reSiblingSelector = /^\s*[+~]/; +function find(selectorOrHaystack) { + if (!selectorOrHaystack) { + return this._make([]); + } + if (typeof selectorOrHaystack !== "string") { + const haystack = isCheerio(selectorOrHaystack) ? selectorOrHaystack.toArray() : [selectorOrHaystack]; + const context = this.toArray(); + return this._make(haystack.filter((elem) => context.some((node) => contains(node, elem)))); + } + return this._findBySelector(selectorOrHaystack, Number.POSITIVE_INFINITY); +} +function _findBySelector(selector, limit) { + var _a2; + const context = this.toArray(); + const elems = reSiblingSelector.test(selector) ? context : this.children().toArray(); + const options = { + context, + root: (_a2 = this._root) === null || _a2 === void 0 ? void 0 : _a2[0], + // Pass options that are recognized by `cheerio-select` + xmlMode: this.options.xmlMode, + lowerCaseTags: this.options.lowerCaseTags, + lowerCaseAttributeNames: this.options.lowerCaseAttributeNames, + pseudos: this.options.pseudos, + quirksMode: this.options.quirksMode + }; + return this._make(select(selector, elems, options, limit)); +} +function _getMatcher(matchMap) { + return function(fn, ...postFns) { + return function(selector) { + var _a2; + let matched = matchMap(fn, this); + if (selector) { + matched = filterArray(matched, selector, this.options.xmlMode, (_a2 = this._root) === null || _a2 === void 0 ? void 0 : _a2[0]); + } + return this._make( + // Post processing is only necessary if there is more than one element. + this.length > 1 && matched.length > 1 ? postFns.reduce((elems, fn2) => fn2(elems), matched) : matched + ); + }; + }; +} +const _matcher = _getMatcher((fn, elems) => { + let ret = []; + for (let i = 0; i < elems.length; i++) { + const value = fn(elems[i]); + if (value.length > 0) + ret = ret.concat(value); + } + return ret; +}); +const _singleMatcher = _getMatcher((fn, elems) => { + const ret = []; + for (let i = 0; i < elems.length; i++) { + const value = fn(elems[i]); + if (value !== null) { + ret.push(value); + } + } + return ret; +}); +function _matchUntil(nextElem, ...postFns) { + let matches = null; + const innerMatcher = _getMatcher((nextElem2, elems) => { + const matched = []; + domEach(elems, (elem) => { + for (let next2; next2 = nextElem2(elem); elem = next2) { + if (matches === null || matches === void 0 ? void 0 : matches(next2, matched.length)) + break; + matched.push(next2); + } + }); + return matched; + })(nextElem, ...postFns); + return function(selector, filterSelector) { + matches = typeof selector === "string" ? (elem) => is$1(elem, selector, this.options) : selector ? getFilterFn(selector) : null; + const ret = innerMatcher.call(this, filterSelector); + matches = null; + return ret; + }; +} +function _removeDuplicates(elems) { + return elems.length > 1 ? Array.from(new Set(elems)) : elems; +} +const parent = _singleMatcher(({ parent: parent2 }) => parent2 && !isDocument(parent2) ? parent2 : null, _removeDuplicates); +const parents = _matcher((elem) => { + const matched = []; + while (elem.parent && !isDocument(elem.parent)) { + matched.push(elem.parent); + elem = elem.parent; + } + return matched; +}, uniqueSort, (elems) => elems.reverse()); +const parentsUntil = _matchUntil(({ parent: parent2 }) => parent2 && !isDocument(parent2) ? parent2 : null, uniqueSort, (elems) => elems.reverse()); +function closest(selector) { + var _a2; + const set = []; + if (!selector) { + return this._make(set); + } + const selectOpts = { + xmlMode: this.options.xmlMode, + root: (_a2 = this._root) === null || _a2 === void 0 ? void 0 : _a2[0] + }; + const selectFn = typeof selector === "string" ? (elem) => is$1(elem, selector, selectOpts) : getFilterFn(selector); + domEach(this, (elem) => { + if (elem && !isDocument(elem) && !isTag(elem)) { + elem = elem.parent; + } + while (elem && isTag(elem)) { + if (selectFn(elem, 0)) { + if (!set.includes(elem)) { + set.push(elem); + } + break; + } + elem = elem.parent; + } + }); + return this._make(set); +} +const next = _singleMatcher((elem) => nextElementSibling(elem)); +const nextAll = _matcher((elem) => { + const matched = []; + while (elem.next) { + elem = elem.next; + if (isTag(elem)) + matched.push(elem); + } + return matched; +}, _removeDuplicates); +const nextUntil = _matchUntil((el) => nextElementSibling(el), _removeDuplicates); +const prev = _singleMatcher((elem) => prevElementSibling(elem)); +const prevAll = _matcher((elem) => { + const matched = []; + while (elem.prev) { + elem = elem.prev; + if (isTag(elem)) + matched.push(elem); + } + return matched; +}, _removeDuplicates); +const prevUntil = _matchUntil((el) => prevElementSibling(el), _removeDuplicates); +const siblings = _matcher((elem) => getSiblings(elem).filter((el) => isTag(el) && el !== elem), uniqueSort); +const children = _matcher((elem) => getChildren(elem).filter(isTag), _removeDuplicates); +function contents() { + const elems = this.toArray().reduce((newElems, elem) => hasChildren(elem) ? newElems.concat(elem.children) : newElems, []); + return this._make(elems); +} +function each(fn) { + let i = 0; + const len = this.length; + while (i < len && fn.call(this[i], i, this[i]) !== false) + ++i; + return this; +} +function map(fn) { + let elems = []; + for (let i = 0; i < this.length; i++) { + const el = this[i]; + const val2 = fn.call(el, i, el); + if (val2 != null) { + elems = elems.concat(val2); + } + } + return this._make(elems); +} +function getFilterFn(match) { + if (typeof match === "function") { + return (el, i) => match.call(el, i, el); + } + if (isCheerio(match)) { + return (el) => Array.prototype.includes.call(match, el); + } + return function(el) { + return match === el; + }; +} +function filter(match) { + var _a2; + return this._make(filterArray(this.toArray(), match, this.options.xmlMode, (_a2 = this._root) === null || _a2 === void 0 ? void 0 : _a2[0])); +} +function filterArray(nodes, match, xmlMode, root2) { + return typeof match === "string" ? filter$1(match, nodes, { xmlMode, root: root2 }) : nodes.filter(getFilterFn(match)); +} +function is(selector) { + const nodes = this.toArray(); + return typeof selector === "string" ? some(nodes.filter(isTag), selector, this.options) : selector ? nodes.some(getFilterFn(selector)) : false; +} +function not(match) { + let nodes = this.toArray(); + if (typeof match === "string") { + const matches = new Set(filter$1(match, nodes, this.options)); + nodes = nodes.filter((el) => !matches.has(el)); + } else { + const filterFn = getFilterFn(match); + nodes = nodes.filter((el, i) => !filterFn(el, i)); + } + return this._make(nodes); +} +function has(selectorOrHaystack) { + return this.filter(typeof selectorOrHaystack === "string" ? ( + // Using the `:has` selector here short-circuits searches. + `:has(${selectorOrHaystack})` + ) : (_, el) => this._make(el).find(selectorOrHaystack).length > 0); +} +function first() { + return this.length > 1 ? this._make(this[0]) : this; +} +function last() { + return this.length > 0 ? this._make(this[this.length - 1]) : this; +} +function eq(i) { + var _a2; + i = +i; + if (i === 0 && this.length <= 1) + return this; + if (i < 0) + i = this.length + i; + return this._make((_a2 = this[i]) !== null && _a2 !== void 0 ? _a2 : []); +} +function get(i) { + if (i == null) { + return this.toArray(); + } + return this[i < 0 ? this.length + i : i]; +} +function toArray() { + return Array.prototype.slice.call(this); +} +function index(selectorOrNeedle) { + let $haystack; + let needle; + if (selectorOrNeedle == null) { + $haystack = this.parent().children(); + needle = this[0]; + } else if (typeof selectorOrNeedle === "string") { + $haystack = this._make(selectorOrNeedle); + needle = this[0]; + } else { + $haystack = this; + needle = isCheerio(selectorOrNeedle) ? selectorOrNeedle[0] : selectorOrNeedle; + } + return Array.prototype.indexOf.call($haystack, needle); +} +function slice(start, end2) { + return this._make(Array.prototype.slice.call(this, start, end2)); +} +function end() { + var _a2; + return (_a2 = this.prevObject) !== null && _a2 !== void 0 ? _a2 : this._make([]); +} +function add(other, context) { + const selection = this._make(other, context); + const contents2 = uniqueSort([...this.get(), ...selection.get()]); + return this._make(contents2); +} +function addBack(selector) { + return this.prevObject ? this.add(selector ? this.prevObject.filter(selector) : this.prevObject) : this; +} +const Traversing = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({ + __proto__: null, + _findBySelector, + add, + addBack, + children, + closest, + contents, + each, + end, + eq, + filter, + filterArray, + find, + first, + get, + has, + index, + is, + last, + map, + next, + nextAll, + nextUntil, + not, + parent, + parents, + parentsUntil, + prev, + prevAll, + prevUntil, + siblings, + slice, + toArray +}, Symbol.toStringTag, { value: "Module" })); +function getParse(parser) { + return function parse2(content, options, isDocument$1, context) { + if (typeof Buffer !== "undefined" && Buffer.isBuffer(content)) { + content = content.toString(); + } + if (typeof content === "string") { + return parser(content, options, isDocument$1, context); + } + const doc = content; + if (!Array.isArray(doc) && isDocument(doc)) { + return doc; + } + const root2 = new Document([]); + update(doc, root2); + return root2; + }; +} +function update(newChilds, parent2) { + const arr = Array.isArray(newChilds) ? newChilds : [newChilds]; + if (parent2) { + parent2.children = arr; + } else { + parent2 = null; + } + for (let i = 0; i < arr.length; i++) { + const node = arr[i]; + if (node.parent && node.parent.children !== arr) { + removeElement(node); + } + if (parent2) { + node.prev = arr[i - 1] || null; + node.next = arr[i + 1] || null; + } else { + node.prev = node.next = null; + } + node.parent = parent2; + } + return parent2; +} +function _makeDomArray(elem, clone2) { + if (elem == null) { + return []; + } + if (typeof elem === "string") { + return this._parse(elem, this.options, false, null).children.slice(0); + } + if ("length" in elem) { + if (elem.length === 1) { + return this._makeDomArray(elem[0], clone2); + } + const result = []; + for (let i = 0; i < elem.length; i++) { + const el = elem[i]; + if (typeof el === "object") { + if (el == null) { + continue; + } + if (!("length" in el)) { + result.push(clone2 ? cloneNode(el, true) : el); + continue; + } + } + result.push(...this._makeDomArray(el, clone2)); + } + return result; + } + return [clone2 ? cloneNode(elem, true) : elem]; +} +function _insert(concatenator) { + return function(...elems) { + const lastIdx = this.length - 1; + return domEach(this, (el, i) => { + if (!hasChildren(el)) + return; + const domSrc = typeof elems[0] === "function" ? elems[0].call(el, i, this._render(el.children)) : elems; + const dom = this._makeDomArray(domSrc, i < lastIdx); + concatenator(dom, el.children, el); + }); + }; +} +function uniqueSplice(array, spliceIdx, spliceCount, newElems, parent2) { + var _a2, _b; + const spliceArgs = [ + spliceIdx, + spliceCount, + ...newElems + ]; + const prev2 = spliceIdx === 0 ? null : array[spliceIdx - 1]; + const next2 = spliceIdx + spliceCount >= array.length ? null : array[spliceIdx + spliceCount]; + for (let idx = 0; idx < newElems.length; ++idx) { + const node = newElems[idx]; + const oldParent = node.parent; + if (oldParent) { + const oldSiblings = oldParent.children; + const prevIdx = oldSiblings.indexOf(node); + if (prevIdx > -1) { + oldParent.children.splice(prevIdx, 1); + if (parent2 === oldParent && spliceIdx > prevIdx) { + spliceArgs[0]--; + } + } + } + node.parent = parent2; + if (node.prev) { + node.prev.next = (_a2 = node.next) !== null && _a2 !== void 0 ? _a2 : null; + } + if (node.next) { + node.next.prev = (_b = node.prev) !== null && _b !== void 0 ? _b : null; + } + node.prev = idx === 0 ? prev2 : newElems[idx - 1]; + node.next = idx === newElems.length - 1 ? next2 : newElems[idx + 1]; + } + if (prev2) { + prev2.next = newElems[0]; + } + if (next2) { + next2.prev = newElems[newElems.length - 1]; + } + return array.splice(...spliceArgs); +} +function appendTo(target) { + const appendTarget = isCheerio(target) ? target : this._make(target); + appendTarget.append(this); + return this; +} +function prependTo(target) { + const prependTarget = isCheerio(target) ? target : this._make(target); + prependTarget.prepend(this); + return this; +} +const append = _insert((dom, children2, parent2) => { + uniqueSplice(children2, children2.length, 0, dom, parent2); +}); +const prepend = _insert((dom, children2, parent2) => { + uniqueSplice(children2, 0, 0, dom, parent2); +}); +function _wrap(insert) { + return function(wrapper) { + const lastIdx = this.length - 1; + const lastParent = this.parents().last(); + for (let i = 0; i < this.length; i++) { + const el = this[i]; + const wrap2 = typeof wrapper === "function" ? wrapper.call(el, i, el) : typeof wrapper === "string" && !isHtml(wrapper) ? lastParent.find(wrapper).clone() : wrapper; + const [wrapperDom] = this._makeDomArray(wrap2, i < lastIdx); + if (!wrapperDom || !hasChildren(wrapperDom)) + continue; + let elInsertLocation = wrapperDom; + let j = 0; + while (j < elInsertLocation.children.length) { + const child = elInsertLocation.children[j]; + if (isTag(child)) { + elInsertLocation = child; + j = 0; + } else { + j++; + } + } + insert(el, elInsertLocation, [wrapperDom]); + } + return this; + }; +} +const wrap = _wrap((el, elInsertLocation, wrapperDom) => { + const { parent: parent2 } = el; + if (!parent2) + return; + const siblings2 = parent2.children; + const index2 = siblings2.indexOf(el); + update([el], elInsertLocation); + uniqueSplice(siblings2, index2, 0, wrapperDom, parent2); +}); +const wrapInner = _wrap((el, elInsertLocation, wrapperDom) => { + if (!hasChildren(el)) + return; + update(el.children, elInsertLocation); + update(wrapperDom, el); +}); +function unwrap(selector) { + this.parent(selector).not("body").each((_, el) => { + this._make(el).replaceWith(el.children); + }); + return this; +} +function wrapAll(wrapper) { + const el = this[0]; + if (el) { + const wrap2 = this._make(typeof wrapper === "function" ? wrapper.call(el, 0, el) : wrapper).insertBefore(el); + let elInsertLocation; + for (let i = 0; i < wrap2.length; i++) { + if (wrap2[i].type === "tag") + elInsertLocation = wrap2[i]; + } + let j = 0; + while (elInsertLocation && j < elInsertLocation.children.length) { + const child = elInsertLocation.children[j]; + if (child.type === "tag") { + elInsertLocation = child; + j = 0; + } else { + j++; + } + } + if (elInsertLocation) + this._make(elInsertLocation).append(this); + } + return this; +} +function after(...elems) { + const lastIdx = this.length - 1; + return domEach(this, (el, i) => { + if (!hasChildren(el) || !el.parent) { + return; + } + const siblings2 = el.parent.children; + const index2 = siblings2.indexOf(el); + if (index2 < 0) + return; + const domSrc = typeof elems[0] === "function" ? elems[0].call(el, i, this._render(el.children)) : elems; + const dom = this._makeDomArray(domSrc, i < lastIdx); + uniqueSplice(siblings2, index2 + 1, 0, dom, el.parent); + }); +} +function insertAfter(target) { + if (typeof target === "string") { + target = this._make(target); + } + this.remove(); + const clones = []; + for (const el of this._makeDomArray(target)) { + const clonedSelf = this.clone().toArray(); + const { parent: parent2 } = el; + if (!parent2) { + continue; + } + const siblings2 = parent2.children; + const index2 = siblings2.indexOf(el); + if (index2 < 0) + continue; + uniqueSplice(siblings2, index2 + 1, 0, clonedSelf, parent2); + clones.push(...clonedSelf); + } + return this._make(clones); +} +function before(...elems) { + const lastIdx = this.length - 1; + return domEach(this, (el, i) => { + if (!hasChildren(el) || !el.parent) { + return; + } + const siblings2 = el.parent.children; + const index2 = siblings2.indexOf(el); + if (index2 < 0) + return; + const domSrc = typeof elems[0] === "function" ? elems[0].call(el, i, this._render(el.children)) : elems; + const dom = this._makeDomArray(domSrc, i < lastIdx); + uniqueSplice(siblings2, index2, 0, dom, el.parent); + }); +} +function insertBefore(target) { + const targetArr = this._make(target); + this.remove(); + const clones = []; + domEach(targetArr, (el) => { + const clonedSelf = this.clone().toArray(); + const { parent: parent2 } = el; + if (!parent2) { + return; + } + const siblings2 = parent2.children; + const index2 = siblings2.indexOf(el); + if (index2 < 0) + return; + uniqueSplice(siblings2, index2, 0, clonedSelf, parent2); + clones.push(...clonedSelf); + }); + return this._make(clones); +} +function remove(selector) { + const elems = selector ? this.filter(selector) : this; + domEach(elems, (el) => { + removeElement(el); + el.prev = el.next = el.parent = null; + }); + return this; +} +function replaceWith(content) { + return domEach(this, (el, i) => { + const { parent: parent2 } = el; + if (!parent2) { + return; + } + const siblings2 = parent2.children; + const cont = typeof content === "function" ? content.call(el, i, el) : content; + const dom = this._makeDomArray(cont); + update(dom, null); + const index2 = siblings2.indexOf(el); + uniqueSplice(siblings2, index2, 1, dom, parent2); + if (!dom.includes(el)) { + el.parent = el.prev = el.next = null; + } + }); +} +function empty() { + return domEach(this, (el) => { + if (!hasChildren(el)) + return; + for (const child of el.children) { + child.next = child.prev = child.parent = null; + } + el.children.length = 0; + }); +} +function html(str) { + if (str === void 0) { + const el = this[0]; + if (!el || !hasChildren(el)) + return null; + return this._render(el.children); + } + return domEach(this, (el) => { + if (!hasChildren(el)) + return; + for (const child of el.children) { + child.next = child.prev = child.parent = null; + } + const content = isCheerio(str) ? str.toArray() : this._parse(`${str}`, this.options, false, el).children; + update(content, el); + }); +} +function toString() { + return this._render(this); +} +function text(str) { + if (str === void 0) { + return text$1(this); + } + if (typeof str === "function") { + return domEach(this, (el, i) => this._make(el).text(str.call(el, i, text$1([el])))); + } + return domEach(this, (el) => { + if (!hasChildren(el)) + return; + for (const child of el.children) { + child.next = child.prev = child.parent = null; + } + const textNode = new Text(`${str}`); + update(textNode, el); + }); +} +function clone() { + const clone2 = Array.prototype.map.call(this.get(), (el) => cloneNode(el, true)); + const root2 = new Document(clone2); + for (const node of clone2) { + node.parent = root2; + } + return this._make(clone2); +} +const Manipulation = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({ + __proto__: null, + _makeDomArray, + after, + append, + appendTo, + before, + clone, + empty, + html, + insertAfter, + insertBefore, + prepend, + prependTo, + remove, + replaceWith, + text, + toString, + unwrap, + wrap, + wrapAll, + wrapInner +}, Symbol.toStringTag, { value: "Module" })); +function css(prop2, val2) { + if (prop2 != null && val2 != null || // When `prop` is a "plain" object + typeof prop2 === "object" && !Array.isArray(prop2)) { + return domEach(this, (el, i) => { + if (isTag(el)) { + setCss(el, prop2, val2, i); + } + }); + } + if (this.length === 0) { + return void 0; + } + return getCss(this[0], prop2); +} +function setCss(el, prop2, value, idx) { + if (typeof prop2 === "string") { + const styles = getCss(el); + const val2 = typeof value === "function" ? value.call(el, idx, styles[prop2]) : value; + if (val2 === "") { + delete styles[prop2]; + } else if (val2 != null) { + styles[prop2] = val2; + } + el.attribs["style"] = stringify(styles); + } else if (typeof prop2 === "object") { + const keys = Object.keys(prop2); + for (let i = 0; i < keys.length; i++) { + const k = keys[i]; + setCss(el, k, prop2[k], i); + } + } +} +function getCss(el, prop2) { + if (!el || !isTag(el)) + return; + const styles = parse(el.attribs["style"]); + if (typeof prop2 === "string") { + return styles[prop2]; + } + if (Array.isArray(prop2)) { + const newStyles = {}; + for (const item of prop2) { + if (styles[item] != null) { + newStyles[item] = styles[item]; + } + } + return newStyles; + } + return styles; +} +function stringify(obj) { + return Object.keys(obj).reduce((str, prop2) => `${str}${str ? " " : ""}${prop2}: ${obj[prop2]};`, ""); +} +function parse(styles) { + styles = (styles || "").trim(); + if (!styles) + return {}; + const obj = {}; + let key; + for (const str of styles.split(";")) { + const n = str.indexOf(":"); + if (n < 1 || n === str.length - 1) { + const trimmed = str.trimEnd(); + if (trimmed.length > 0 && key !== void 0) { + obj[key] += `;${trimmed}`; + } + } else { + key = str.slice(0, n).trim(); + obj[key] = str.slice(n + 1).trim(); + } + } + return obj; +} +const Css = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({ + __proto__: null, + css +}, Symbol.toStringTag, { value: "Module" })); +const submittableSelector = "input,select,textarea,keygen"; +const r20 = /%20/g; +const rCRLF = /\r?\n/g; +function serialize() { + const arr = this.serializeArray(); + const retArr = arr.map((data2) => `${encodeURIComponent(data2.name)}=${encodeURIComponent(data2.value)}`); + return retArr.join("&").replace(r20, "+"); +} +function serializeArray() { + return this.map((_, elem) => { + const $elem = this._make(elem); + if (isTag(elem) && elem.name === "form") { + return $elem.find(submittableSelector).toArray(); + } + return $elem.filter(submittableSelector).toArray(); + }).filter( + // Verify elements have a name (`attr.name`) and are not disabled (`:enabled`) + '[name!=""]:enabled:not(:submit, :button, :image, :reset, :file):matches([checked], :not(:checkbox, :radio))' + ).map((_, elem) => { + var _a2; + const $elem = this._make(elem); + const name = $elem.attr("name"); + const value = (_a2 = $elem.val()) !== null && _a2 !== void 0 ? _a2 : ""; + if (Array.isArray(value)) { + return value.map((val2) => ( + /* + * We trim replace any line endings (e.g. `\r` or `\r\n` with `\r\n`) to guarantee consistency across platforms + * These can occur inside of `